Skip to main content

Documentation Index

Fetch the complete documentation index at: https://docs.lerian.studio/llms.txt

Use this file to discover all available pages before exploring further.

Auditors, compliance officers, and disputes teams use this layer to answer one question: “Why did this transaction get this decision, and can we prove no one tampered with that answer?” What changes in your operation: evidence of a control goes from “let me pull logs from N systems and reconcile timestamps” to “here is the immutable record, cryptographically chained, showing that this transaction got this decision because this specific rule fired at this moment.” That shift is the whole point. Trade-off to be honest about: there is no “delete” or “edit” on audit records — by design. A TRUNCATE trigger at the database level blocks bulk deletion; each record’s SHA-256 hash includes the previous record’s hash, so tampering breaks the chain everywhere downstream. If you need to remove a record for legal reasons (such as GDPR right-to-be-forgotten on PII), the answer is data minimization upfront, not retroactive editing.
Who is this guide for? Compliance officers and auditors checking what Tracer guarantees, disputes teams looking up validation history, and developers building reports against the audit endpoints. The compliance overview and retention sections assume zero API knowledge; the query and verify sections assume basic REST.
Tracer maintains a complete, immutable of all validation decisions. This guide explains how the audit system works and how to query validation history for compliance reporting.

Compliance overview


Tracer is designed to meet the audit requirements of financial regulations including:
RegulationRequirementHow Tracer complies
(Sarbanes-Oxley)Complete audit trail of financial decisionsEvery validation is recorded with full context
GLBA (Gramm-Leach-Bliley)Protection of customer financial dataData encrypted at rest and in transit
General auditAbility to reconstruct decisionsImmutable records with input/output snapshots

Audit trail architecture


Tracer records every validation decision with full context for compliance and investigation.

What gets recorded

Every validation creates an immutable audit record containing:
DataDescription
Request snapshotComplete input payload as received
Response snapshotFull response including decision and details
DecisionALLOW, DENY, or REVIEW
ReasonWhy the decision was made
Evaluated rulesAll rules that were evaluated
Matched rulesRules that triggered (if any)
Limit detailsUsage information for checked limits
Processing timeHow long validation took
TimestampWhen the validation occurred
Audit events are deduplicated for transaction validations. If a validation request is retried with the same requestId, only the first audit event is stored. This ensures the audit trail reflects unique business events, not API retry patterns.

Immutability and hash chain

Audit records are write-once and cryptographically chained:
  • Records cannot be modified after creation.
  • The audit table is protected at the database level: a TRUNCATE trigger blocks bulk deletion.
  • Each record stores a SHA-256 hash that includes the previous record’s hash, forming an append-only chain. Tampering with any past record breaks the chain for every subsequent record.
  • A pg_advisory_xact_lock serializes hash-chain writes to keep the order stable under concurrent inserts.
You can verify the chain at any time using GET /v1/audit-events/{id}/verify, which returns:
{
  "valid": true,
  "totalChecked": 12345,
  "firstInvalidId": null
}
If the chain is intact, valid is true and firstInvalidId is omitted. If a record was modified, valid is false and firstInvalidId points to the first record where the recomputed hash diverges from the stored hash. This is the cryptographic basis for SOX/GLBA tamper-evidence guarantees.
The audit trail is designed for compliance audits. You can reconstruct exactly what happened for any validation, even years later, and prove that the records were not modified after the fact.

Data retention


Tracer retains data according to regulatory requirements and operational needs.

Retention periods

Data typeRetention periodReason
Validation records7 years minimumSOX/GLBA compliance requirement
Rules (active/inactive)IndefiniteOperational continuity
Rules / Limits (deleted)Soft-deleted: row kept indefinitely for audit, excluded from API listingsCompliance trail must outlive operational visibility
LimitsIndefiniteOperational continuity
Application logs90 daysDebugging and troubleshooting

Compliance considerations

  • SOX requirement: Maintain records for 7 years from the date of the audit report
  • GLBA requirement: Retain records demonstrating compliance with privacy rules
  • Data export: Records can be exported for external audit systems

Querying validation history


Use the GET /v1/validations endpoint to query historical validations.

Basic query

GET /v1/validations
X-API-Key: {api_key}
Returns validations in cursor-paginated reverse chronological order. There is no implicit time window — use start_date and end_date to scope the result, otherwise the response covers everything within the retention period.

Filtered query

GET /v1/validations?start_date=2026-01-01T00:00:00Z&end_date=2026-01-31T23:59:59Z&decision=DENY
X-API-Key: {api_key}

Available filters

ParameterTypeDescription
start_dateRFC3339Start of date range (inclusive)
end_dateRFC3339End of date range (exclusive)
decisionenumFilter by ALLOW, DENY, or REVIEW
account_idUUIDFilter by account
segment_idUUIDFilter by segment
portfolio_idUUIDFilter by portfolio
transaction_typeenumFilter by CARD, WIRE, PIX, CRYPTO
matched_rule_idUUIDFilter by rule that matched
exceeded_limit_idUUIDFilter by limit that was exceeded

Date format requirement

Date parameters must use RFC3339 format with mandatory timezone. Date-only formats are rejected.
Valid:
start_date=2026-01-01T00:00:00Z
start_date=2026-01-01T00:00:00-03:00
Invalid:
start_date=2026-01-01  (rejected - missing time and timezone)

Pagination

Results use cursor-based pagination. The response includes nextCursor and hasMore fields to navigate through results.
ParameterDefaultMaximumDescription
limit1001000Results per page
cursor--Pagination cursor from previous response
When using cursor pagination, sort_by and sort_order are fixed from the original query.

Sorting

GET /v1/validations?sort_by=created_at&sort_order=DESC
ParameterOptionsDefault
sort_bycreated_at, processing_time_mscreated_at
sort_orderASC, DESCDESC

Getting validation details


Retrieve complete details for a specific validation using GET /v1/validations/{id}. The response contains everything needed to understand a validation decision:
  • Request snapshot: The complete input payload as received
  • Response snapshot: Full response including decision and reason
  • Evaluated rules: All rules that were checked
  • Matched rules: Rules that triggered (if any)
  • Limit details: Usage information for checked limits
  • Timestamps: When the validation occurred and processing time

Querying audit events


Beyond validation records, Tracer also exposes a generic audit event log via GET /v1/audit-events. This is the only way to see lifecycle changes for rules and limits — who created, updated, activated, deactivated, drafted, or deleted them.

Event types

eventTypeWhen emitted
TRANSACTION_VALIDATEDA validation request was processed (also available via GET /v1/validations)
RULE_CREATED / RULE_UPDATEDRule created or modified
RULE_ACTIVATED / RULE_DEACTIVATEDRule moved into ACTIVE / INACTIVE
RULE_DRAFTEDRule moved from INACTIVE back to DRAFT for re-editing
RULE_DELETEDRule soft-deleted
LIMIT_CREATED / LIMIT_UPDATEDLimit created or modified
LIMIT_ACTIVATED / LIMIT_DEACTIVATEDLimit moved into ACTIVE / INACTIVE
LIMIT_DRAFTEDLimit moved from INACTIVE back to DRAFT for re-editing
LIMIT_DELETEDLimit soft-deleted

Filters

GET /v1/audit-events accepts the same date-range and scope filters as GET /v1/validations, plus filters tailored to lifecycle events:
ParameterTypeDescription
start_date / end_dateRFC3339Date range (inclusive start, exclusive end)
event_typeenumFilter by event type (see table above)
actionenumVALIDATE, CREATE, UPDATE, DELETE, ACTIVATE, DEACTIVATE, DRAFT
resultenumSUCCESS, FAILED (for CRUD) or ALLOW, DENY, REVIEW (for validations)
resource_typeenumtransaction, rule, limit
resource_idUUIDThe affected resource ID
actor_type / actor_idstringuser or system, plus the actor ID
account_id / segment_id / portfolio_id / transaction_type / matched_rule_idUUID/enumSame scope filters as validations
limit, cursor, sort_by, sort_orderCursor pagination (default limit 100, max 1000; sort_by accepts created_at or event_type)

Use cases

  • Who activated this rule? GET /v1/audit-events?resource_type=rule&resource_id={ruleId}&action=ACTIVATE
  • All rule changes last week: GET /v1/audit-events?resource_type=rule&start_date=...&end_date=...
  • All limit deletions in 2026: GET /v1/audit-events?resource_type=limit&action=DELETE&start_date=2026-01-01T00:00:00Z

Single event detail

Use GET /v1/audit-events/{id} to retrieve a specific audit record, including the snapshot of state at the time of the event.

Compliance reporting scenarios


Common queries for audit and compliance reporting.

Scenario 1: Audit investigation

“Why was this transaction denied on January 15th?”
GET /v1/validations/{id}
The response shows the exact request received, all rules evaluated, which rule or limit caused the denial, and the timestamp.

Scenario 2: Monthly compliance report

“Show all denied transactions for corporate accounts in January”
GET /v1/validations?start_date=2026-01-01T00:00:00Z&end_date=2026-02-01T00:00:00Z&decision=DENY&segment_id=corporate-segment-uuid&limit=1000

Scenario 3: Rule effectiveness analysis

“Which transactions were denied by a specific fraud rule?”
GET /v1/validations?matched_rule_id=fraud-rule-uuid&decision=DENY&limit=1000

Scenario 4: Limit utilization review

“Which transactions exceeded spending limits this month?”
GET /v1/validations?start_date=2026-01-01T00:00:00Z&end_date=2026-02-01T00:00:00Z&exceeded_limit_id=daily-limit-uuid

Best practices for compliance


Recommendations for maintaining audit readiness.

Record keeping

  • Store validation IDs in your transaction records for easy cross-reference
  • Log the requestId you send to Tracer for correlation
  • Export regularly if you need records in external audit systems
Common pitfalls when reading the audit trail:
  • “I can see the validation but the rule that fired was already deleted.” Deleted rules are soft-deleted — the row stays in the database, but it doesn’t appear in GET /v1/rules. To investigate, query GET /v1/audit-events?resource_type=rule&resource_id={ruleId} for the lifecycle of that rule, including its activations and the eventual delete.
  • “Two retries of the same requestId only produced one audit event.” This is by design (deduplication via idx_audit_events_validation_dedup). The audit trail reflects unique business events, not API retry patterns. If your retry produced a different decision, that’s worth investigating — Tracer should return the original cached response.
  • /verify says the chain is broken on a record I haven’t touched.” The chain links every record to the previous one, so a tamper or DB corruption anywhere makes everything downstream report invalid. firstInvalidId points to the actual divergence — start the investigation there, not at the record you queried.

Audit preparation

  • Test queries before audit season to ensure you can retrieve needed data
  • Verify date ranges work correctly with your timezone requirements
  • Document your retention policy alignment with Tracer’s 7-year retention

Investigation workflow

When investigating a specific transaction:
  1. Find the validation ID from your transaction logs or Tracer history
  2. Retrieve full details using GET /v1/validations/
  3. Review the request snapshot to see what data was provided
  4. Check matched rules to understand why the decision was made
  5. Verify limit status if limits were involved

No-match behavior and audit


When a validation runs and no rule matches, Tracer returns a configured default decision instead of treating the empty match as an error. This is a per-request fallback, not an infrastructure resilience strategy. The decision is governed by the DEFAULT_DECISION_WHEN_NO_MATCH environment variable (default: ALLOW).
ScenarioBehaviorAudit record
No rules matchReturns DEFAULT_DECISION_WHEN_NO_MATCH (default ALLOW)Recorded with reason: "No matching rules found"
Evaluation budget exceededReturns HTTP 504 with TRC-0229No validation record; an audit failure event may be emitted
Database error during limit checkReturns HTTP 500; the entire validation transaction is rolled backNo validation record persisted
Set DEFAULT_DECISION_WHEN_NO_MATCH=DENY for fail-closed semantics in high-security deployments. The service logs a warning at startup if this remains at the default ALLOW.
Infrastructure failures (database down, cache stale, timeout) do not fall back to ALLOW — they surface as HTTP errors to the client and the original transaction has no audit record. Operators should monitor tracer_audit_persist_failures_total and the /readyz endpoint to detect these cases.

Quick reference


Key endpoints and retention information.

Endpoints

OperationMethodEndpoint
List validationsGET/v1/validations
Get validationGET/v1/validations/{id}
List audit eventsGET/v1/audit-events
Get audit eventGET/v1/audit-events/{id}
Verify hash chainGET/v1/audit-events/{id}/verify

Retention summary

DataRetention
Validation records7+ years
Active rules/limitsIndefinite
Application logs90 days