Refer to the manual for details of how to install and use
django-reversion. It includes a list of which version of
django-reversion is compatible with each version of Django - worth keeping
an eye on as the recommended version for the latest version of Django does
On production systems we create a shell script to run django administration
commands where this document refers to
django-admin you should use the
appropriate script on the production system.
from contact.models import Contact contact = Contact.objects.get(pk=12424) from reversion.models import Version versions = Version.objects.get_for_object(contact) for x in versions: print(x.revision.user, x.revision.date_created, x)
x.field_dict will display a dictionary showing changes to
django-reversion version 1.10 the import signature changed from
import reversion to:
from reversion import revisions as reversion
Add reversion to a model¶
reversion on a model e.g:
from reversion import revisions as reversion @reversion.register() class ModelWithReversion(models.Model): # ...
The legacy method is as follows:
class ModelWithReversion(models.Model): # ... reversion.register(ModelWithReversion)
If the reversion is added after a model it was initially created you can create initial revision using the management command
django-admin createinitialrevisions your_app.YourModel --comment="Initial revision."
unregister models (to stop storing versions while you do some
import reversion model_list = [ Contact, ContactAddress, ContactEmail, ContactPhone, ] for m in model_list: if reversion.is_registered(m): reversion.unregister(m)
register the same models:
for m in model_list: if not reversion.is_registered(m): reversion.register(m)
To make this easier, you could
unregister and then
register in a
finally block like this:
try: _unregister() do_something_useful() finally: _register()
Count of Revision records¶
We’ve added a management command to the base app with list the number of revision records for each model in a project.
to use this command, you must be using
django-reversion version 2.0.5 or
To use the command simply change to the project directory and type:
Space used in the database¶
The space used by Postgres can be monitored using the command (the reversion
tables are prefixed by
psql -U postgres <database name> -c "select relname, relpages from pg_class order by relpages desc;" | grep "reversion_"jk
A more detailed breakdown can be obtained using
psql -U postgres <database name> -c "SELECT *, pg_size_pretty(total_bytes) AS total , pg_size_pretty(index_bytes) AS INDEX , pg_size_pretty(toast_bytes) AS toast , pg_size_pretty(table_bytes) AS TABLE FROM ( SELECT *, total_bytes-index_bytes-COALESCE(toast_bytes,0) AS table_bytes FROM ( SELECT c.oid,nspname AS table_schema, relname AS TABLE_NAME , c.reltuples AS row_estimate , pg_total_relation_size(c.oid) AS total_bytes , pg_indexes_size(c.oid) AS index_bytes , pg_total_relation_size(reltoastrelid) AS toast_bytes FROM pg_class c LEFT JOIN pg_namespace n ON n.oid = c.relnamespace WHERE relkind = 'r' ) a ) a order by total_bytes desc limit 50;"
Size of reversion tables in backup¶
To find out how much many lines of the Postgres dump file is given over to reversion:
grep -n "^COPY" <backup file name> > /tmp/bkup-lines.txt
then view the file and search for
reversion_ the difference between the line
number of this copy command and the next one gives the number of lines that the
backup of that table spans.
Reversion in not always appropriate¶
Where a table changes frequently (e.g. for recording stats) it can create a large number of reversion records that serve no useful purpose.
See the next section for how to remove reversion from an existing model.
Remove reversion from an existing model¶
Before removing an existing model from reversion you should remove the existing revision data otherwise this data will be retained but will not be accessable.
To delete existing revision information use the
command as follows:
django-admin deleterevisions <app name>.<Model name>
If there are a large number of records it is better to delete these in chunks
so that we do not create large transaction on which are time consuming on
Postgres e.g. the following script deletes the revision data for a model
Model in the app
app, a day at a time
day=365 while [ $day -gt 0 ]; do day=`expr $day - 1` echo "Deleting reversion older than $day days" django-admin deleterevisions app.Model --days=$day done
This will split the task into smaller chunks.
Once the data is deleted you can then remove the
from the models module.
If you want to delete all revisions, run the
management command without the model parameter.
To check the number of
Version records created:
import reversion qs = reversion.models.Version.objects.all() assert 0 == qs.count()
To filter on
Version for a model:
pks = [ x.pk for x in reversion.models.Version.objects.get_for_model(UserConsent) ]