🔍 Django Audit Logger
A reusable Django package that automatically tracks CREATE, UPDATE, and DELETE operations across registered models using dynamic signal registration, decorators, JSON-based change tracking, admin filters, and CSV export.
✨ Features
- ✅ Tracks CREATE, UPDATE, and DELETE operations automatically
- ✅ Field-level change tracking with old and new values in JSON
- ✅ Simple
@audit_modeldecorator for registering any model - ✅ Works across multiple apps in the same Django project
- ✅ Built-in Django Admin dashboard with filters and search
- ✅ CSV export for audit logs
- ✅ Date-based navigation (year → month → day)
- ✅ Zero changes required to existing business logic
Dependencies
- Python 3.9+
- Django 4.2+
All required dependencies are installed automatically when you install the package.
📦 Installation
Install from PyPI
pip install audit-logger-jatin
⚙️ Setup
1. Add to INSTALLED_APPS
# settings.py
INSTALLED_APPS = [
...
'audit_logger',
...
]
2. Run migrations
python manage.py makemigrations
python manage.py migrate
🚀 Usage
Register a model for auditing
Simply apply the @audit_model decorator to any model you want to track:
# models.py
from django.db import models
from audit_logger.decorators import audit_model
@audit_model
class Product(models.Model):
name = models.CharField(max_length=255)
price = models.DecimalField(max_digits=10, decimal_places=2)
stock = models.IntegerField()
def __str__(self):
return self.name
That's it — no signal wiring, no custom save methods. The decorator handles everything.
Register models across multiple apps
# inventory/models.py
@audit_model
class Product(models.Model):
...
# sales/models.py
@audit_model
class Order(models.Model):
...
# hr/models.py
@audit_model
class Employee(models.Model):
...
Logs will be stored with app_name and model_name so you can always tell them apart:
inventory | Product
sales | Order
hr | Employee
📋 How It Works
The package uses Django Signals under the hood:
| Signal | Purpose |
|---|---|
pre_save |
Captures old field values before an update |
post_save |
Logs CREATE or UPDATE after saving |
post_delete |
Logs DELETE after an object is removed |
Signals are connected dynamically inside AppConfig.ready() for every model registered via @audit_model.
📊 AuditLog Model
Each audit event is stored as a record with the following fields:
| Field | Description |
|---|---|
action |
CREATE, UPDATE, or DELETE |
app_name |
The Django app the model belongs to |
model_name |
The model class name |
object_id |
Primary key of the affected object |
object_name |
String representation of the object |
changed_fields |
JSON diff of changed fields |
timestamp |
When the action occurred |
Example — UPDATE log entry
{
"price": {
"old": "10.00",
"new": "20.00"
},
"stock": {
"old": "100",
"new": "85"
}
}
🖥️ Django Admin
Access the audit dashboard at:
http://localhost:8000/admin/audit_logger/auditlog/
Available filters
- Action —
CREATE/UPDATE/DELETE - Model Name — filter by specific model
- App Name — filter by Django app
Search
Search logs by object name or model name.
Date navigation
Browse logs by year → month → day using Django's built-in date hierarchy.
CSV Export
Select any logs and use the "Export selected logs as CSV" admin action.
The export includes: Action, App, Model, Object, Changes, Timestamp.
🗂️ Project Structure
audit_logger/
├── __init__.py
├── apps.py # AppConfig — connects signals on startup
├── models.py # AuditLog model
├── signals.py # pre_save / post_save / post_delete handlers
├── decorators.py # @audit_model decorator
├── registry.py # Model registry
├── admin.py # Admin dashboard, filters, CSV export
├── migrations/
README.md
LICENSE
setup.py
pyproject.toml
MANIFEST.in
🛠️ Technologies Used
| Technology | Purpose |
|---|---|
| Python | Core language |
| Django | Web framework |
| Django Signals | Automatic change detection |
| Django Admin | Audit dashboard |
| JSONField | Storing field-level diffs |
| CSV Export | Log download functionality |
| Git & GitHub | Version control |
| PyPI Packaging | Open-source distribution |
📝 Example — Full Workflow
# 1. Register your model
@audit_model
class Product(models.Model):
name = models.CharField(max_length=255)
price = models.DecimalField(max_digits=10, decimal_places=2)
# 2. Create a product — automatically logged as CREATE
p = Product.objects.create(name="Widget", price=10.00)
# 3. Update the product — automatically logged as UPDATE
p.price = 20.00
p.save()
# 4. Delete the product — automatically logged as DELETE
p.delete()
# 5. Query the audit trail
from audit_logger.models import AuditLog
logs = AuditLog.objects.filter(model_name="Product")
for log in logs:
print(log.action, log.object_name, log.changed_fields)
📄 License
This project is licensed under the MIT License — see the LICENSE file for details.
🤝 Contributing
Contributions, issues, and feature requests are welcome!
Feel free to open an issue or submit a pull request on GitHub.
👤 Author
Jatin Agrawal
GitHub · LinkedIn
Developed a reusable Django Audit Logger package that automatically tracks CREATE, UPDATE, and DELETE operations across registered models using dynamic signal registration, decorators, JSON-based change tracking, admin filters, and CSV export functionality.
Metadata
Release files for audit-logger-jatin 0.1.3
For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.
Source distribution (sdist)
| File | Size | Uploaded | Provenance | Actions |
|---|---|---|---|---|
| audit_logger_jatin-0.1.3.tar.gz | 11.9 kB | Without provenance | Details for audit_logger_jatin-0.1.3.tar.gz |
Built distribution (wheel)
| File | Interpreter | ABI | Platform | Actions Reset |
|---|---|---|---|---|
| audit_logger_jatin-0.1.3-py3-none-any.whl | Python 3 | none | any | Details for audit_logger_jatin-0.1.3-py3-none-any.whl |
Total release size: 21.1 kB
Release files / audit_logger_jatin-0.1.3.tar.gz
| Download URL | audit_logger_jatin-0.1.3.tar.gz |
|---|---|
| Size | 11.9 kB |
| Tags | Source |
|
SHA-256 checksum How to use checksums |
0f2249b68af2e9d94b617da41be615fb6eade89b43cf9d66f310158c6be20dd4
|
|
BLAKE2b-256 checksum How to use checksums |
ee2e79e2b970453c29163a968039fa08be6e940abfd9d67ea10726b1a096334b
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
No |
| Uploaded via |
twine/6.2.0 CPython/3.13.5
|
Release files / audit_logger_jatin-0.1.3-py3-none-any.whl
| Download URL | audit_logger_jatin-0.1.3-py3-none-any.whl |
|---|---|
| Size | 9.2 kB |
| Tags | Python 3 |
|
SHA-256 checksum How to use checksums |
bb7e6f25a1c00f8cec267349c843534d4978875e50e2a001a9b3abcf8c126a47
|
|
BLAKE2b-256 checksum How to use checksums |
b218305998d79bf08a7c0717b34137769154f58df1a887426f269f202de6f621
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
No |
| Uploaded via |
twine/6.2.0 CPython/3.13.5
|
Security for audit-logger-jatin 0.1.3
Provenance
Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.
No provenance found
None of the files in this release were uploaded with provenance metadata.
A note on package security
PyPI is a repository for distributing packages, not a service for auditing them. While third-party security researchers and our staff do their best to detect and remove malicious packages, PyPI cannot guarantee the quality, security or suitability of any given package.
To learn more about protecting yourself from malicious actors, visit our package security documentation.