AttributeError is raised when running custom module test suite

Hi,

I am running the test but it will prompt error with the default data get from the context.
It will tell the result is ‘None’. May I know how to write the code so that the test will be passed?

Example of the code:

    currency = fields.Many2One('currency.currency', 'Currency')

    @classmethod
    def default_currency:
    	pool = Pool()
    	comp = Transaction().context.get("company")
    	Company = pool.get("company.company")
    	company = Company(comp)
    	if company:
    		if company.currency:
    			return company.currency.id

Below is the error when running the test:

ERROR: test_field_methods (trytond.modules.wms.tests.test_wms.WmsTestCase)
Test field methods
----------------------------------------------------------------------
Traceback (most recent call last):
  File "/usr/local/lib/python3.6/dist-packages/trytond/model/model.py", line 282, in __getattr__
    return self._values[name]
TypeError: 'NoneType' object is not subscriptable

During handling of the above exception, another exception occurred:

Traceback (most recent call last):
  File "/usr/local/lib/python3.6/dist-packages/trytond/tests/test_tryton.py", line 203, in wrapper
    result = func(*args, **kwargs)
  File "/usr/local/lib/python3.6/dist-packages/trytond/tests/test_tryton.py", line 444, in test_field_methods
    getattr(model, attr)()
  File "/config/workspace/wms/stock_owner.py", line 25, in default_currency
    if company.currency:
  File "/usr/local/lib/python3.6/dist-packages/trytond/model/modelstorage.py", line 1413, in __getattr__
    return super(ModelStorage, self).__getattr__(name)
  File "/usr/local/lib/python3.6/dist-packages/trytond/model/model.py", line 285, in __getattr__
    % (self.__name__, name, self._values))
AttributeError: 'company.company' Model has no attribute 'currency': None

Probably the problem is that you do not have the company value set on the context when running the test.

Then this line:

Sets the value of comp variable to None. This value is latter used to load the company record:

But as comp is None tryton will create a new record instead of reading it from the database. The new record makes this line fail:

because a newly created record does not have any currency set (your code does not set the any value) so when accessing them it crashes.

You should probably only load the company value when there is a value set on the context.

P.S: I updated your title to better describe the problem of your topic.

Hi @pokoli,

Thank you for your explaination.
May I know how to set the context for testing?
or set the user for the testing?

Because I would like to get the user’s company to load the default currency.

The tests of the company include some functions to do so:

If you look at the tests suits of base modules (for example account) you will see examples it’s usage.

Having said that I must admit that is probably too much to add a test just for a default value, so maybe it’s better to create a scenario to test the entire module functionality and ensure that default values are correctly set there.

I think the main problem is that the default method fails if there are no company in the context. So the first thing to do is to make it works without it like this:

    @classmethod
    def default_currency:
    	pool = Pool()
    	Company = pool.get("company.company")
    	company_id = Transaction().context.get("company")
        if company_id is not None:
    	   company = Company(company_id)
    	    if company.currency:
                return company.currency.id

Hi @pokoli,

Thank you for your feedback. However, the test function you provide is when doing doctest.
However, the error I face is when doin then basic test from trytond itself.

Anyway, thank you

Thank @ced,
check for None is working.

Why explicit test for None? Isn’t it better to test for

          if company_id:

Otherwise if company_id is False or 0, the following code would fail, too.

Because real ID could be 0.

This topic was automatically closed 30 days after the last reply. New replies are no longer allowed.