Grails: transactions in integration tests

I have a very simple setup - a controller that calls a method in the service. In this service, I save the object to the database and also send the JMS message to the queue - after saving it - using the entered JMSTemplate. The service has transactions by default.

When testing this manually - with the ActiveMQ server turned off - an exception is thrown, and the transaction is rolled back - with the network effect that the object is also not saved in the database. All is well.

However, when I run this using the integration test (with ActiveMQ enabled), they say that I have a place to check that the object was not saved in the database using the count query after the controller was called, it was not possible to say that the count is 1 I confirmed that the database does not have any of these objects when the test starts by adding another statement at the beginning of the test to ensure that the counter is 0.

Is this the expected behavior (possibly due to the nature of the transactions in the test integration environment), or can I do something wrong? An exception is still thrown because the JMS server is down - and this is a RuntimeException.

Grails integration tests and transactions give the impression that this is to be expected - in this case, are there any suggestions for best practices for testing transactional behavior in integration tests?

+4
source share
1 answer

Iโ€™m not sure why everyone commented, but didnโ€™t answer, because comments give the answer. I will jump in and try to hook on the answer points!

Yes, in the Spock test, the whole test, including whens, thens, givens, etc., is exhausted by one transaction. This way you wonโ€™t see the rollback you are hoping for until the test is completed.

You can configure your test to be non-transaction by adding "static transactional = false" at the top of the test class. Of course, dropping out is what you will need to clean up the database after running your tests (if sanitation of the database is important to you). One of the big problems is that the Grails IntegrationSpec class has an error that will explode whenever you try to set the transaction to false. This SO has a solution to this problem:

Grails 2.3 IntegrationSpec cannot be transactional false

Basically, copy all the code for grails.test.spock.IntegrationSpec into your own class and replace several methods with versions that take into account the transactional nature of the test.

+7
source

Source: https://habr.com/ru/post/1403388/


All Articles