Django test: TransactionManagementError: you cannot execute queries until the end of an atomic block

Django newbie here. I am trying to implement unit tests for a simple API that I have developed. Below you can find my test implementation that works great:

from django.test import TestCase
from my_app.models import MyModel


class TestMyViewSet(TestCase):
    """
    Unit tests for endpoints in MyViewSet.
    """
    fixtures = ['my_app/fixtures/data.yaml']

    def setUp(self):
        # Making setup for the test case here.


    def test_post_my_resource(self):

        # Checking that fixture is loaded correctly.
        self.assertEqual(MyModel.objects.all().count(),1)

        request_body = {
            'my_resource': "input_for_my_resource"
        }

        response = self.client.post('/my_resources/', data=request_body)
        self.assertEqual(response.status_code, 201)
        # self.assertEqual(MyModel.objects.all().count(),2)

      

But when I removed the last line self.assertEqual(MyModel.objects.all().count(),2)

from the comment to verify that it was my_resource

successfully created in the corresponding model by checking the number of instances, I got the error:

TransactionManagementError: An error occurred in the current transaction. You cannot execute queries until the end of the atomic block.

What am I missing here?

Thanks in advance!

PS: I come across the following question: TransactionManagementError "You cannot execute queries to the end of the atomic block when using signals, but only during unit testing, but I'm not sure what happens the same in my case.

+3


source to share


1 answer


Obviously moving from django.test.TestCase

to has django.test.TransactionTestCase

solved the problem. Here are some important points regarding the differences between django.test.TestCase

and django.test.TransactionTestCase

:

TransactionTestCase

and are TestCase

identical, except that the reset database is known and the test code's ability to test the consequences of a commit and rollback is:

  • TransactionTestCase

    dumps the database after running the test by truncating all tables. A TransactionTestCase

    can call commit and rollback and observe the effects of those calls on the database.

  • A TestCase

    , on the other hand, does not truncate tables after the test. Instead, it includes the test code in a database transaction that is rolled back at the end of the test. This ensures that a rollback at the end of the test restores the database to its original state.



You can find more details here from the TransactionTestCase docs

+4


source







All Articles