openerp-expert-framework team mailing list archive
-
openerp-expert-framework team
-
Mailing list archive
-
Message #00619
Re: Asserting exceptions in YAML tests
Hi,
here in particular I explain what I mentioned earlier about cursor rollbacks
On 09/20/2011 08:28 AM, P. Christeas wrote:
> On Monday 19 September 2011, Georges Racinet wrote:
>> Here's an extract of that discussion (toplevel is Olivier) :
>>> On 08/28/2011 02:19 PM, Georges Racinet wrote:
>>>>> To say it quickly, I'm thinking of an analog of unittest's
>>>>> assertRaises
>>>>> (http://docs.python.org/library/unittest.html#unittest.TestCase.asser
>>>>> tRaises)
>>>
>>> You're right, there's currently no provision for assertRaises-like tests
>>> in YAML, except via a custom !python block with a try/except, as you
>>> noted. (...) That would certainly be a welcome contribution! (...)
>>
>> ...
>> This gives us YAML blocks such as this one :
>>
>> !python {model: ir.model, assert_raises: lxml.etree.ParseError}: |
>> from lxml.etree import fromstring
>> fromstring('definitely not valid xml !')
>>
>> What do you think of this approach ?
>> I'm wondering how to unit-test that. Are there plans to unit-test
>> somehow yaml imports ?
>
> Well, so far I have been using
> try:
> do_something_wrong()
> raise AssertionError("It shouldn't reach here")
> except DoneWrongException:
> # yes, it failed
> pass
>
> As you say, it is a little more bulky to write, but clearly shows the intent
> of this test..
Expliciteness would be higher with a dedicated tag, such as
!assertRaises or !raises :
!raises {model: ir.model, exception: lxml.etree.ParseError}
from lxml.etree import fromstring i
fromstring('definitely not valid xml !')
Maybe that'd be more satisfactory to you ?
I'm now almost convinced that process_python() will get too complicated
anyway and factorizing the most between process_python() and a (new)
process_raises() is not that hard.
As for the problem I mentioned about rollbacks, here it is : some
exceptions are corellated with a cursor rollback, which in turns
prevents normal processing of further tests and demo data.
Namely, while testing validation errors (our primary purpose actually),
we have both to catch the exception (orm.except_orm) and to prevent the
cursor rollback (which the last thing done in osv.orm.orm before raising).
Currently, monkey-patching the cursor is about the only way to do it:
!python {model: 'my.model'} : |
from osv.orm import except_orm
rollback_bak = cr.rollback
cr.rollback = lambda s : None
try:
model.cause_validation_error(...)
except except_orm:
# it passed
except:
cr.rollback = rollback_bak
raise AssertionError('wrong exception raised')
cr.rollback = rollback_bak
that's obviously ugly, but it works.
We'd like the assertions about exceptions to be able to handle that, say
!raises {model: 'my_model', exception=except_orm}: |
model.cause_validation_error(...)
now the question is : how to do that ?
- Monkey patch the cursor as above, but in the test processing.
This would be simply hiding the ugliness in the process method, but
this is the simplest to implement and can be improved later. In the
meanwhile, addons' YAML tests are clean in that respect and don't need
to be upgraded.
- Set a special key in the context and check it in orm.py
I'm not so sure what kind of side effects we can have with the
context. Also that key could be used in other parts of the framework for
special conditions in tests (though I don't appreciate introducing in
code special knowledge that it's actually ran under tests, it can still
be useful).
- Change the framework a lot so that the rollback becomes a consequence
of the exception that we happen to catch before in tests
That's probably a big, dangerous, change.
- Other ideas ?
>
> Nevertheless, your contribution is welcome and my vote would be to merge it in
> the framework. Some developers may prefer your compact approach, why not.
Thank you !
Regards,
--
Georges Racinet
Anybox SAS, http://anybox.fr
Follow ups
References