I would like to create additional tables when I call
INSERT). But I keep getting this error:
django.db.transaction.TransactionManagementError: Executing DDL
statements while in a transaction on databases that can’t perform a
rollback is prohibited.
I tried to create additional tables inside
model.save() and using a
pre_save() signal, I get the same error.
This is a
pre_save solution attempt:
from django.db import connection from django.db.models.signals import pre_save from django.dispatch import receiver @receiver(pre_save, sender=MyModel, dispatch_uid="create_tags") def create_tags(sender, instance, **kwargs): print("debug, signal pre_save works") try: # if obj exists in MyModel table, skip tag table creation existing_obj = MyModel.objects.get(name=instance.name) print("debug, obj exists") except MyModel.DoesNotExist: with connection.schema_editor() as schema_editor: schema_editor.create_model(MyModel2)
Stack: Django, MySQL.
What I want to implement is to create additional tables for the instance that is being inserted.
To clarify how the miscellaneous per-instance tables are generated, this is the code to derive a per-instance table. For example, for every inserted car instance, there are to be generated miscellaneous Tag tables with sensor measurements:
def get_tag(car_url, car_type): class Tag(models.Model): time = models.PositiveIntegerField(primary_key=True) # unix time in seconds # noqa value = models.FloatField() class Meta: db_table = car_url + "_" + car_type def __str__(self) -> str: return str(self.time) + "," + str(self.value) return Tag
I think that the probable solution is to use “nonatomic” somewhere in the code.
Thank you for visiting the Q&A section on Magenaut. Please note that all the answers may not help you solve the issue immediately. So please treat them as advisements. If you found the post helpful (or not), leave a comment & I’ll get back to you as soon as possible.
schema_editor.connection.in_atomic_block = False.
with connection.schema_editor() as schema_editor: in_atomic_block = schema_editor.connection.in_atomic_block schema_editor.connection.in_atomic_block = False try: schema_editor.create_model(MyModel2) finally: schema_editor.connection.in_atomic_block = in_atomic_block
Using a context manager:
with connection.schema_editor() as schema_editor: with non_atomic(schema_editor): schema_editor.create_model(MyModel2)
from contextlib import contextmanager @contextmanager def non_atomic(schema_editor): in_atomic_block = schema_editor.connection.in_atomic_block schema_editor.connection.in_atomic_block = False try: yield finally: schema_editor.connection.in_atomic_block = in_atomic_block