Skip to main content

Auditoria de eventos rápida e íntegra (hash chain) para apps Python, com core em Rust.

Project description

rust-py-audit

PyPI Python License GitHub

🌐 rust-py-audit.vercel.app

Biblioteca de auditoria de eventos para aplicações Python, com core em Rust.

Registra eventos de auditoria (quem fez o quê, quando, em qual recurso) de forma rápida e estruturada, e encadeia cada evento ao anterior com SHA-256 — qualquer edição, remoção ou reordenação posterior do arquivo de log é detectável com verify().


Features

  • AuditLogger — API simples: log(...), verify(), last_hash()
  • Cadeia de hashes (SHA-256) — cada evento inclui o hash do evento anterior; alterar qualquer evento gravado quebra a cadeia de forma detectável
  • Armazenamento em JSONL — um evento por linha, append-only, sem necessidade de banco de dados
  • metadata livre — qualquer dict JSON-serializável (IP, motivo, request_id, etc.)
  • Middleware FastAPI — registra automaticamente requisições que alteram estado (POST/PUT/PATCH/DELETE)
  • Middleware Django — mesma ideia, suporta WSGI e ASGI
  • Core em Rust — geração de hash, serialização e I/O acontecem em Rust via PyO3; a API Python permanece simples

Requirements

  • Python 3.10+
  • Nenhuma dependência obrigatória em runtime

Opcionais, instaladas separadamente:

  • fastapi + starlette — para rust_py_audit.fastapi.AuditMiddleware
  • django — para rust_py_audit.django.AuditMiddleware

Installation

pip install rust-py-audit

Com extras opcionais:

pip install "rust-py-audit[fastapi]"
pip install "rust-py-audit[django]"

Quick Start

from rust_py_audit import AuditLogger

audit = AuditLogger(app_name="billing-api", file_path="./audit.jsonl")

event = audit.log(
    actor_id="user_123",
    action="DELETE_INVOICE",
    resource="invoice",
    resource_id="inv_987",
    metadata={"ip": "192.168.0.10", "reason": "duplicate invoice"},
)

print(event["id"])     # uuid v4
print(event["hash"])   # sha256, 64 caracteres hex

print(audit.last_hash())  # hash do último evento gravado

result = audit.verify()
print(result)
# {"valid": True, "total_events": 1, "last_hash": "..."}

Integridade da cadeia

Cada evento grava o hash do evento anterior (previous_hash) e o próprio hash (hash), calculado a partir do conteúdo do evento + previous_hash. O primeiro evento da cadeia tem previous_hash = null.

{"id":"evt_123","timestamp":"2026-06-17T10:00:00Z","app_name":"billing-api","actor_id":"user_123","action":"DELETE_INVOICE","resource":"invoice","resource_id":"inv_987","metadata":{"ip":"192.168.0.10"},"previous_hash":null,"hash":"abc123..."}

verify() relê o arquivo do zero e recalcula tudo — não confia em nenhum cache em memória:

result = audit.verify()

Se a cadeia estiver intacta:

{"valid": True, "total_events": 10, "last_hash": "..."}

Se algum evento foi editado, removido ou reordenado:

{"valid": False, "total_events": 10, "error_index": 4, "reason": "hash_mismatch"}
# ou "reason": "broken_chain" (evento removido/reordenado/forjado)

FastAPI

from fastapi import FastAPI
from rust_py_audit.fastapi import AuditMiddleware

app = FastAPI()
app.add_middleware(AuditMiddleware, app_name="billing-api", file_path="./audit.jsonl")


@app.delete("/invoices/{invoice_id}")
async def delete_invoice(invoice_id: str):
    return {"deleted": invoice_id}

Por padrão, só requisições POST/PUT/PATCH/DELETE são registradas. actor_id vem do header X-User-Id (ajustável via actor_header=); cai para "anonymous" se ausente.

Ver exemplo completo em examples/fastapi_app.py.


Django

# settings.py
MIDDLEWARE = [
    "rust_py_audit.django.AuditMiddleware",
    # ... outros middlewares ...
]

# Opcional:
RUST_PY_AUDIT_APP_NAME = "my-django-app"
RUST_PY_AUDIT_FILE_PATH = "./audit.jsonl"
RUST_PY_AUDIT_METHODS = {"POST", "PUT", "PATCH", "DELETE"}

actor_id vem de request.user.pk quando há um usuário autenticado (via django.contrib.auth); cai para "anonymous" caso contrário. O middleware suporta tanto aplicações WSGI quanto ASGI automaticamente.

Ver exemplo completo em examples/django_example/.


API Reference

AuditLogger(app_name, file_path="./audit.jsonl")

Parâmetro Tipo Descrição
app_name str Nome da aplicação, gravado em todo evento
file_path str Caminho do arquivo JSONL. Se já existir, a cadeia é retomada a partir do último hash gravado

audit.log(actor_id, action, resource, resource_id, metadata=None) → dict

Registra um evento e devolve o evento completo (já com id, timestamp, hash, etc.) como dict.

Campo do evento Tipo Descrição
id str UUID v4
timestamp str RFC3339 / UTC, ex: 2026-06-17T10:00:00Z
app_name str Vem do AuditLogger
actor_id str Quem realizou a ação
action str Ex: DELETE_INVOICE
resource str Ex: invoice
resource_id str Ex: inv_987
metadata dict Livre — qualquer JSON serializável
previous_hash str | None Hash do evento anterior na cadeia
hash str SHA-256 (64 hex chars) do evento + previous_hash

audit.verify() → dict

Relê o arquivo e revalida a cadeia inteira do zero. Ver Integridade da cadeia.


audit.last_hash() → str | None

Hash do último evento gravado (cache em memória, O(1)) — None se nenhum evento foi registrado ainda.


Building from Source

Requer Rust e maturin.

git clone https://github.com/robertolima-dev/rust-py-audit
cd rust-py-audit

python3 -m venv .venv
source .venv/bin/activate
pip install maturin

# Build de desenvolvimento (instala no ambiente Python atual)
maturin develop

# Wheel de release
maturin build --release

Running tests

# Testes unitários em Rust
cargo test --no-default-features

# Testes de integração em Python
pip install -e ".[dev]"
pytest tests/

Architecture

Python API (rust_py_audit)
    ├── AuditLogger(...)        ──► src/audit_logger.rs (PyO3 #[pyclass])
    │       ├── log()           ──► src/event.rs    (AuditEvent)
    │       │                   ──► src/hash.rs     (SHA-256 determinístico)
    │       │                   ──► src/storage.rs  (append em JSONL)
    │       ├── verify()        ──► src/verifier.rs (revalida a cadeia)
    │       └── last_hash()     ──► cache em memória
    │
    ├── fastapi.AuditMiddleware ──► audit.log() a cada request mutante
    └── django.AuditMiddleware  ──► idem, WSGI/ASGI

O core é compilado para uma extensão nativa (.so/.pyd) por maturin e PyO3. A camada Python é fina — só roteia chamadas e oferece os adaptadores de framework.


License

MIT — ver LICENSE.

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

rust_py_audit-0.1.1.tar.gz (35.2 kB view details)

Uploaded Source

Built Distributions

If you're not sure about the file name format, learn more about wheel file names.

rust_py_audit-0.1.1-cp310-abi3-win_amd64.whl (235.3 kB view details)

Uploaded CPython 3.10+Windows x86-64

rust_py_audit-0.1.1-cp310-abi3-musllinux_1_2_x86_64.whl (583.7 kB view details)

Uploaded CPython 3.10+musllinux: musl 1.2+ x86-64

rust_py_audit-0.1.1-cp310-abi3-musllinux_1_2_aarch64.whl (543.9 kB view details)

Uploaded CPython 3.10+musllinux: musl 1.2+ ARM64

rust_py_audit-0.1.1-cp310-abi3-manylinux_2_17_x86_64.manylinux2014_x86_64.whl (379.1 kB view details)

Uploaded CPython 3.10+manylinux: glibc 2.17+ x86-64

rust_py_audit-0.1.1-cp310-abi3-manylinux_2_17_aarch64.manylinux2014_aarch64.whl (368.8 kB view details)

Uploaded CPython 3.10+manylinux: glibc 2.17+ ARM64

rust_py_audit-0.1.1-cp310-abi3-macosx_11_0_arm64.whl (328.0 kB view details)

Uploaded CPython 3.10+macOS 11.0+ ARM64

rust_py_audit-0.1.1-cp310-abi3-macosx_10_12_x86_64.whl (335.9 kB view details)

Uploaded CPython 3.10+macOS 10.12+ x86-64

File details

Details for the file rust_py_audit-0.1.1.tar.gz.

File metadata

  • Download URL: rust_py_audit-0.1.1.tar.gz
  • Upload date:
  • Size: 35.2 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? No
  • Uploaded via: maturin/1.14.0

File hashes

Hashes for rust_py_audit-0.1.1.tar.gz
Algorithm Hash digest
SHA256 6ad939b8ceaed59747708c90d720e5b771440ff1451068cd6248d4ef228158f4
MD5 2a9b80e65102f047eafb3d26f408c0d1
BLAKE2b-256 41b44eef93cefc3a87bda0a0e16686b4b20d8d7cbbb792ca985f8549de5fed71

See more details on using hashes here.

File details

Details for the file rust_py_audit-0.1.1-cp310-abi3-win_amd64.whl.

File metadata

File hashes

Hashes for rust_py_audit-0.1.1-cp310-abi3-win_amd64.whl
Algorithm Hash digest
SHA256 13835b7c91d503eb6ed1a0ae482a1831c32bd6841286215154673d1b6539c62c
MD5 bec0e31553346b80ee582dc221ab9361
BLAKE2b-256 015b3dee9ca11ecf0d6f1fb6447fd0c8b44a544cda4afddb0588dd96d5f93197

See more details on using hashes here.

File details

Details for the file rust_py_audit-0.1.1-cp310-abi3-musllinux_1_2_x86_64.whl.

File metadata

File hashes

Hashes for rust_py_audit-0.1.1-cp310-abi3-musllinux_1_2_x86_64.whl
Algorithm Hash digest
SHA256 40797441cf626e80b02be42e3a965d0f63e59815ebc15520bf4ff262e7ddd788
MD5 e038921a01f9edaa317bbf2d9c525615
BLAKE2b-256 1b3ae3e73ce6cc8da066455d7550168c9d8e43628548bd7c65cffe62ef65ea3f

See more details on using hashes here.

File details

Details for the file rust_py_audit-0.1.1-cp310-abi3-musllinux_1_2_aarch64.whl.

File metadata

File hashes

Hashes for rust_py_audit-0.1.1-cp310-abi3-musllinux_1_2_aarch64.whl
Algorithm Hash digest
SHA256 e67af8b4d446560f1e0fd9ced729b8b118ee78966aabb8a47f6705ddd486aeee
MD5 5f91270e4be0a8a2c5e8fa9a69583370
BLAKE2b-256 67476da73c13e6baae15076e357c1b836abc829af5c510b19bd2b39372c63086

See more details on using hashes here.

File details

Details for the file rust_py_audit-0.1.1-cp310-abi3-manylinux_2_17_x86_64.manylinux2014_x86_64.whl.

File metadata

File hashes

Hashes for rust_py_audit-0.1.1-cp310-abi3-manylinux_2_17_x86_64.manylinux2014_x86_64.whl
Algorithm Hash digest
SHA256 cc5dba4c57d702fa145c7c15d5a4c22aa8b9791ad290531873338e1b1a34b12d
MD5 2dfcb26b86b14d2daca89e67c56dbbed
BLAKE2b-256 cc8be3114d49d5edf8a44584ad4e828dfd25344a6174727dbcf5033f9cb69394

See more details on using hashes here.

File details

Details for the file rust_py_audit-0.1.1-cp310-abi3-manylinux_2_17_aarch64.manylinux2014_aarch64.whl.

File metadata

File hashes

Hashes for rust_py_audit-0.1.1-cp310-abi3-manylinux_2_17_aarch64.manylinux2014_aarch64.whl
Algorithm Hash digest
SHA256 3ae64b038b4f2130a8371dd7bb4822d467a471411ef66bc3c887babe8bedc35c
MD5 344869e81405fb152dbb5657a37600fc
BLAKE2b-256 7bbb84dab086d7c3497ac36f338c903df90be85428a5bfe1d2812dfd0250962d

See more details on using hashes here.

File details

Details for the file rust_py_audit-0.1.1-cp310-abi3-macosx_11_0_arm64.whl.

File metadata

File hashes

Hashes for rust_py_audit-0.1.1-cp310-abi3-macosx_11_0_arm64.whl
Algorithm Hash digest
SHA256 dd4b1beb0fe6afdbd26f4b28ebc0574bd0ec4666435e86256d32cd186a7f5f34
MD5 0e5641a3eb6761a0e418312fe01ee2ba
BLAKE2b-256 0990a2093af0845611dc7f246782005e361805d5e88eff4600a552db519737ee

See more details on using hashes here.

File details

Details for the file rust_py_audit-0.1.1-cp310-abi3-macosx_10_12_x86_64.whl.

File metadata

File hashes

Hashes for rust_py_audit-0.1.1-cp310-abi3-macosx_10_12_x86_64.whl
Algorithm Hash digest
SHA256 962d4ed7047f9c0770d9a068c83e1ab0e8964cfbe5afc0046942b2e346a8910e
MD5 7c49c79edf3be3002b8c9901f87472aa
BLAKE2b-256 3111fcc85e4257090b4cd90af7ae31103ad1c4044204e0dbdc4c4e7155653dfa

See more details on using hashes here.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page