Description
Hi, thanks for this wonderful library.
I have a problem.
Whenever I try to revert one of my models in a programatic way to a past version of it, I get Key (id)=(da7304bb-64c9-4f6b-91d5-195bec1389a1) already exists
. This is not happening when the model uses the default AutoField from django as its primary key and this is also not happening when I revert it from the admin interface (whether with AutoField or UUIDField as primary keys).
To Reproduce
Steps to reproduce the behavior:
- Just create two models. Both of them need to have the history field. But just one of them is going to have its primary key overrided with a UUIDField.
from simple_history.models import HistoricalRecords
from django.db import models
import uuid
class ModelOne(models.Model):
"""
This model can be reverted programatically.
"""
name = models.CharField(max_length=255)
history = HistoricalRecords()
class ModelTwo(models.Model):
"""
This model cannot be reverted programatically.
"""
id = models.UUIDField(
primary_key=True,
default=uuid.uuid4,
editable=False
)
name = models.CharField(max_length=255)
history = HistoricalRecords()
- Run makemigrations, then migrate.
- Go to a fresh command line interface. Create new records and try to revert to a previous one.
>>> from testing_simple.models import ModelTwo
>>> mt = ModelTwo.objects.create(name="name 1")
>>> mt.name = "name 2"
>>> mt.save()
>>> mt.history.all()
<QuerySet [<HistoricalModelTwo: ModelTwo object (921d5275-9ded-4295-9716-f1cc0f6b72ab) as of 2019-12-28 06:20:12.254575+00:00>, <HistoricalModelTwo: ModelTwo object (921d5275-9ded-4295-9716-f1cc0f6b72ab) as of 2019-12-28 06:20:03.498981+00:00>]>
>>> mt_earliest = mt.history.earliest()
>>> mt_earliest.instance.save()
Traceback (most recent call last):
File "/home/disonante/pjs/tests/simple_history_test/venv/lib/python3.6/site-packages/django/db/backends/utils.py", line 86, in _execute
return self.cursor.execute(sql, params)
File "/home/disonante/pjs/tests/simple_history_test/venv/lib/python3.6/site-packages/django/db/backends/sqlite3/base.py", line 396, in execute
return Database.Cursor.execute(self, query, params)
sqlite3.IntegrityError: UNIQUE constraint failed: testing_simple_modeltwo.id
The above exception was the direct cause of the following exception:
Traceback (most recent call last):
File "<console>", line 1, in <module>
File "/home/disonante/pjs/tests/simple_history_test/venv/lib/python3.6/site-packages/django/db/models/base.py", line 746, in save
force_update=force_update, update_fields=update_fields)
File "/home/disonante/pjs/tests/simple_history_test/venv/lib/python3.6/site-packages/django/db/models/base.py", line 784, in save_base
force_update, using, update_fields,
File "/home/disonante/pjs/tests/simple_history_test/venv/lib/python3.6/site-packages/django/db/models/base.py", line 886, in _save_table
results = self._do_insert(cls._base_manager, using, fields, returning_fields, raw)
File "/home/disonante/pjs/tests/simple_history_test/venv/lib/python3.6/site-packages/django/db/models/base.py", line 925, in _do_insert
using=using, raw=raw,
File "/home/disonante/pjs/tests/simple_history_test/venv/lib/python3.6/site-packages/django/db/models/manager.py", line 82, in manager_method
return getattr(self.get_queryset(), name)(*args, **kwargs)
File "/home/disonante/pjs/tests/simple_history_test/venv/lib/python3.6/site-packages/django/db/models/query.py", line 1204, in _insert
return query.get_compiler(using=using).execute_sql(returning_fields)
File "/home/disonante/pjs/tests/simple_history_test/venv/lib/python3.6/site-packages/django/db/models/sql/compiler.py", line 1377, in execute_sql
cursor.execute(sql, params)
File "/home/disonante/pjs/tests/simple_history_test/venv/lib/python3.6/site-packages/django/db/backends/utils.py", line 100, in execute
return super().execute(sql, params)
File "/home/disonante/pjs/tests/simple_history_test/venv/lib/python3.6/site-packages/django/db/backends/utils.py", line 68, in execute
return self._execute_with_wrappers(sql, params, many=False, executor=self._execute)
File "/home/disonante/pjs/tests/simple_history_test/venv/lib/python3.6/site-packages/django/db/backends/utils.py", line 77, in _execute_with_wrappers
return executor(sql, params, many, context)
File "/home/disonante/pjs/tests/simple_history_test/venv/lib/python3.6/site-packages/django/db/backends/utils.py", line 86, in _execute
return self.cursor.execute(sql, params)
File "/home/disonante/pjs/tests/simple_history_test/venv/lib/python3.6/site-packages/django/db/utils.py", line 90, in __exit__
raise dj_exc_value.with_traceback(traceback) from exc_value
File "/home/disonante/pjs/tests/simple_history_test/venv/lib/python3.6/site-packages/django/db/backends/utils.py", line 86, in _execute
return self.cursor.execute(sql, params)
File "/home/disonante/pjs/tests/simple_history_test/venv/lib/python3.6/site-packages/django/db/backends/sqlite3/base.py", line 396, in execute
return Database.Cursor.execute(self, query, params)
django.db.utils.IntegrityError: UNIQUE constraint failed: testing_simple_modeltwo.id
Environment
- OS: Ubuntu 18.04
- Database: tested with both, PostgreSQL latest and SQLlite.
- asgiref==3.2.3
- Django==3.0.1
- django-simple-history==2.8.0
- pytz==2019.3
- six==1.13.0
- sqlparse==0.3.0
Additional context
The code above was tested in an isolated virtual environment, with a brand new
django project and django-simple-history installation.
Things I have tried:
- Exclude the id from the HistoricalRecords with the excluded_fields option.
- Set the UUIDField as the primary key to the historical model too (with history_id_field).
Non of them have worked.
I would appreciate some workaround that I can follow for the moment.
Thank you.