django-simple-history
Store model history and view/revert changes from admin site.
Rank: #2301Downloads: 2,849,304 (30 days)Stars: 2,440Forks: 495
Description
|build-status| |docs| |coverage| |maintainability| |code-style| |downloads| .. |pypi-version| image:: https://img.shields.io/pypi/v/django-simple-history.svg :target: https://pypi.org/project/django-simple-history/ :alt: PyPI Version .. |build-status| image:: https://github.com/django-commons/django-simple-history/actions/workflows/test.yml/badge.svg :target: https://github.com/django-commons/django-simple-history/actions/workflows/test.yml :alt: Build Status .. |docs| image:: https://readthedocs.org/projects/django-simple-history/badge/?version=latest :target: https://django-simple-history.readthedocs.io/en/latest/?badge=latest :alt: Documentation Status .. |coverage| image:: https://img.shields.io/codecov/c/github/django-commons/django-simple-history/master.svg :target: https://app.codecov.io/github/django-commons/django-simple-history?branch=master :alt: Test Coverage .. |maintainability| image:: https://api.codeclimate.com/v1/badges/66cfd94e2db991f2d28a/maintainability :target: https://codeclimate.com/github/django-commons/django-simple-history/maintainability :alt: Maintainability .. |code-style| image:: https://img.shields.io/badge/code%20style-black-000000.svg :target: https://github.com/psf/black :alt: Code Style .. |downloads| image:: https://static.pepy.tech/badge/django-simple-history :target: https://pepy.tech/project/django-simple-history :alt: Downloads ``django-simple-history`` stores Django model state on every create/update/delete. This app supports the following combinations of Django and Python: ========== ======================== Django Python ========== ======================== 4.2 3.10, 3.11, 3.12, 3.13 5.0 3.10, 3.11, 3.12, 3.13 5.1 3.10, 3.11, 3.12, 3.13 5.2 3.10, 3.11, 3.12, 3.13, 3.14 6.0 3.12, 3.13, 3.14 main 3.12, 3.13, 3.14 ========== ======================== Getting Help ------------ Documentation is available at https://django-simple-history.readthedocs.io/en/stable/ Pull requests are welcome. Read the `CONTRIBUTING`_ file for tips on submitting a pull request. .. _CONTRIBUTING: https://github.com/django-commons/django-simple-history/blob/master/CONTRIBUTING.rst License ------- This project is licensed under the `BSD 3-Clause license <https://choosealicense.com/licenses/bsd-3-clause/>`_. ==== Changelog ========= 3.11.0 (2025-12-09) ------------------- - Added support for Python 3.14 (gh-1529) - Added support for Django 6.0 (gh-1529) - Dropped support for Python 3.9, which reached end-of-life on 2025-10-31 (gh-1560) - Added Ukrainian localization (gh-1547) 3.10.1 (2025-06-20) ------------------- - Fixed changelog syntax to support PyPI packaging (gh-1499) 3.10.0 (2025-06-20) ------------------- - Tests are no longer bundled in released wheels (gh-1478) - Move repository to the Django Commons organization (gh-1391) 3.9.0 (2025-01-26) ------------------ - Removed the ``simple_history_admin_list.display_list()`` template tag that was deprecated in version 3.6.0 (gh-1444) 3.8.0 (2025-01-23) ------------------ - Made ``skip_history_when_saving`` work when creating an object - not just when updating an object (gh-1262) - Improved performance of the ``latest_of_each()`` history manager method (gh-1360) - Fixed issue with deferred fields causing DoesNotExist error (gh-678) - Added HistoricOneToOneField (gh-1394) - Updated all djangoproject.com links to reference the stable version (gh-1420) - Dropped support for Python 3.8, which reached end-of-life on 2024-10-07 (gh-1421) - Added support for Django 5.1 (gh-1388) - Added pagination to ``SimpleHistoryAdmin`` (gh-1277) - Fixed issue with history button not working when viewing historical entries in the admin (gh-527) - Added support for Django 5.2 (gh-1441) - ``simple_history_admin_list.display_list()`` *was planned to be removed in this release, but it was overlooked, and will instead be removed in 3.9.0* 3.7.0 (2024-05-29) ------------------ - Dropped support for Django 3.2, which reached end-of-life on 2024-04-01 (gh-1344) - Removed the temporary requirement on ``asgiref>=3.6`` added in 3.5.0, now that the minimum required Django version is 4.2 (gh-1344) - Migrated package building from using the deprecated ``setup.py`` to using ``pyproject.toml`` (with Hatchling as build backend); ``setup.py`` has consequently been removed (gh-1348) - Added ``django>=4.2`` as an installation dependency, to mirror the minimum version tested in our CI (gh-1349) 3.6.0 (2024-05-26) ------------------ - Support custom History ``Manager`` and ``QuerySet`` classes (gh-1280) - Renamed the (previously internal) admin template ``simple_history/_object_history_list.html`` to ``simple_history/object_history_list.html``, and added the field ``SimpleHistoryAdmin.object_history_list_template`` for overriding it (gh-1128) - Deprecated the undocumented template tag ``simple_history_admin_list.display_list()``; it will be removed in version 3.8 (gh-1128) - Added ``SimpleHistoryAdmin.get_history_queryset()`` for overriding which ``QuerySet`` is used to list the historical records (gh-1128) - Added ``SimpleHistoryAdmin.get_history_list_display()`` which returns ``history_list_display`` by default, and made the latter into an actual field (gh-1128) - ``ModelDelta`` and ``ModelChange`` (in ``simple_history.models``) are now immutable dataclasses; their signatures remain unchanged (gh-1128) - ``ModelDelta``'s ``changes`` and ``changed_fields`` are now sorted alphabetically by field name. Also, if ``ModelChange`` is for an M2M field, its ``old`` and ``new`` lists are sorted by the related object. This should help prevent flaky tests. (gh-1128) - ``diff_against()`` has a new keyword argument, ``foreign_keys_are_objs``; see usage in the docs under "History Diffing" (gh-1128) - Added a "Changes" column to ``SimpleHistoryAdmin``'s object history table, listing the changes between each historical record of the object; see the docs under "Customizing the History Admin Templates" for overriding its template context (gh-1128) - Fixed the setting ``SIMPLE_HISTORY_ENABLED = False`` not preventing M2M historical records from being created (gh-1328) - For history-tracked M2M fields, adding M2M objects (using ``add()`` or ``set()``) used to cause a number of database queries that scaled linearly with the number of objects; this has been fixed to now be a constant number of queries (gh-1333) 3.5.0 (2024-02-19) ------------------ - Fixed ``FieldError`` when creating historical records for many-to-many fields with ``to="self"`` (gh-1218) - Allow ``HistoricalRecords.m2m_fields`` as str (gh-1243) - Fixed ``HistoryRequestMiddleware`` deleting non-existent ``HistoricalRecords.context.request`` in very specific circumstances (gh-1256) - Added ``custom_historical_attrs`` to ``bulk_create_with_history()`` and ``bulk_update_with_history()`` for setting additional fields on custom history models (gh-1248) - Passing an empty list as the ``fields`` argument to ``bulk_update_with_history()`` is now allowed; history records will still be created (gh-1248) - Added temporary requirement on ``asgiref>=3.6`` while the minimum required Django version is lower than 4.2 (gh-1261) - Small performance optimization of the ``clean-duplicate_history`` command (gh-1015) - Support Simplified Chinese translation (gh-1281) - Added support for Django 5.0 (gh-1283) - Added support for Python 3.13 (gh-1289) 3.4.0 (2023-08-18) ------------------ - Fixed typos in the docs - Added feature to evaluate ``history`` model permissions explicitly when ``SIMPLE_HISTORY_ENFORCE_HISTORY_MODEL_PERMISSIONS`` is set to ``True`` in ``settings`` (gh-1017). - Fixed ``SimpleHistoryAdmin`` not properly integrating with custom user models (gh-1177) - Support Indonesian translation (gh-1198) - Support Urdu translation (gh-1199) - Support Norwegian Bokmål translation (gh-1210) - Dropped support for Python 3.7, which reached end-of-life on 2023-06-27 (gh-1202) - Dropped support for Django 4.0, which reached end-of-life on 2023-04-01 (gh-1202) - Added support for Django 4.2 (gh-1202) - Made ``bulk_update_with_history()`` return the number of model rows updated (gh-1206) - Fixed ``HistoryRequestMiddleware`` not cleaning up after itself (i.e. deleting ``HistoricalRecords.context.request``) under some circumstances (gh-1188) - Made ``HistoryRequestMiddleware`` async-capable (gh-1209) - Fixed error when setting ``table_name`` with ``inherit=True`` (gh-1195) 3.3.0 (2023-03-08) ------------------ - Made it possible to use the new ``m2m_fields`` with model inheritance (gh-1042) - Added two signals: ``pre_create_historical_m2m_records`` and ``post_create_historical_m2m_records`` (gh-1042) - Added ``tracked_fields`` attribute to historical models (gh-1038) - Fixed ``KeyError`` when running ``clean_duplicate_history`` on models with ``excluded_fields`` (gh-1038) - Added support for Python 3.11 (gh-1053) - Added Arabic translations (gh-1056) - Fixed a code example under "Tracking many to many relationships" (gh-1069) - Added a ``--base-manager`` option to the ``clean_duplicate_history`` management command (gh-1115) 3.2.0 (2022-09-28) ------------------ - Fixed typos in the docs - Removed n+1 query from ``bulk_create_with_history`` utility (gh-975) - Started using ``exists`` query instead of ``count`` in ``populate_history`` command (gh-982) - Add basic support for many-to-many fields (gh-399) - Added support for Django 4.1 (gh-1021) 3.1.1 (2022-04-23) ------------------ Full list of changes: - Fix py36 references in pyproject.toml (gh-960) - Fix local setup.py install versioning issue (gh-960) - Remove py2 universal wheel cfg - only py3 needed now (gh-960) 3.1.0 (2022-04-09) ------------------ Breaking Changes: - Dropped support for Django 2.2 (gh-968) - Dropped support for Django 3.1 (gh-952) - Dropped support for Python 3.6, which reached end-of-lif