IETF AAT field mapping
Ujex's audit ledger implements the field schema from IETF draft-sharif-agent-audit-trail-00 (Raza Sharif, CyberSecAI, 29 March 2026). This page documents the verbatim mapping so an AAT-compliant verifier can ingest a Ujex bundle without translation.
Field-by-field
| AAT field | Type | Ujex source | Notes |
|---|---|---|---|
record_id | string (32 hex) | audit.{seq}.aat.record_id | Server-minted UUIDv4 (random 16 bytes hex). |
agent_id | string | audit.{seq}.payload.agentId | Empty/null when actor is human (admin) |
agent_version | string | audit.{seq}.aat.agent_version | Caller-supplied; defaults to "unspecified" |
session_id | string | null | audit.{seq}.aat.session_id | Correlates rows within a session |
action_type | enum | audit.{seq}.aat.action_type | tool_call | approval | memory_write | outbound_email | inbound_email | policy_decision | human_override | governor_block | other |
outcome | enum | audit.{seq}.aat.outcome | success | denied | error | pending |
trust_level | enum | audit.{seq}.aat.trust_level | high | medium | low | unknown |
parent_record_id | string | null | audit.{seq}.aat.parent_record_id | Chains causality across rows |
prev_hash | string (64 hex) | audit.{seq}.prevHash | Empty string for the genesis row |
hash | string (64 hex) | audit.{seq}.hash | sha256(prevHash ‖ payloadHash ‖ timestamp ‖ seq) |
payload_hash | string (64 hex) | audit.{seq}.payloadHash | sha256(canonical_json(payload)) |
timestamp | ISO-8601 | derived from audit.{seq}.timestamp (unix ms) | Serialized as ISO-8601 in the export |
action | string | audit.{seq}.payload.action | Ujex-native action string (e.g. postbox.send) |
actor_kind | string | audit.{seq}.payload.actorKind | human / agent / system |
actor_id | string | audit.{seq}.payload.actorId | Firebase uid OR agent:<agentId> |
target | string | null | audit.{seq}.payload.target | Optional |
meta | object | audit.{seq}.payload.meta | Free-form |
Canonical-JSON serialization
Ujex uses the same canonical-JSON form as @ujexdev/audit-chain: keys sorted lexicographically at every level, no whitespace, Unicode kept verbatim. This matches RFC 8785 (JCS) for AAT compatibility.
Verifier
# Offline, language-agnostic
pip install ujex-audit-chain
python -m ujex_audit_chain verify records.jsonl
# Or, via Ujex CLI (extracted bundle dir, or records.jsonl)
ujex audit verify ./bundle/
Optional signatures
AAT § 5 permits per-record ECDSA P-256 signatures. Ujex doesn't sign each row inline — the chain itself is integrity-proving, and per-row signatures inflate storage. Instead, the bundle manifest (manifest.json) can be signed at export time with auditExportAATBundle({signManifest: true}). Signed manifests bind the export range, record count, bundle hash, chain head, latest audit anchor, issuer, and trust key id.