Privacy and sensitive-data handling
Use this page to configure privacy controls for trace persistence in OngoingAI Gateway. It explains safe defaults, redaction behavior, and verification steps.
Privacy guarantees
- Keeps request and response body storage disabled by default.
- Redacts sensitive credential headers before trace persistence.
- Supports storage-stage body redaction with configurable detectors and key denylist.
- Records redaction outcome metadata in trace records.
- Preserves provider credential pass-through while redacting raw credential headers in stored traces.
Operational fit
- You need lower risk for data stored in trace records.
- You need to collect useful operational metadata without storing raw payloads.
- You need privacy controls that still preserve debugging and analytics value.
Redaction pipeline
- Capture middleware records headers and optional body bytes with size limits.
- Sensitive credential headers are replaced with
[REDACTED]before storage. - Built-in credential header redaction is always active.
pii.stages.*_headerscontrols custom header denylist application.- If
tracing.capture_bodies=false, bodies are not persisted in traces. Body bytes can still be parsed transiently for model and usage extraction. - If
tracing.capture_bodies=true, effective PII mode defaults toredact_storagewhenpii.modeis empty. - In
redact_storage, JSON body fields are redacted by key denylist and string detectors (email, phone, SSN, token-like values). - Placeholder values are deterministic hashes scoped by workspace and optional
pii.replacement.hash_salt. - If storage redaction fails, the gateway drops body persistence for that
trace and sets
redaction_storage_drop=truein metadata. - In
redact_upstream, request bodies are redacted before forwarding to provider routes. - In
block, requests are denied when configured detectors find protected content. - Optional
pii.scopes[]can override mode/policy by org/workspace/key, provider, and route prefix.
Supported pii.mode values at runtime:
offredact_storageredact_upstreamblock
Starter privacy profiles
Metadata-only baseline
YAML
tracing:
capture_bodies: false
body_max_size: 1048576
pii:
mode: "" # auto resolves to off when body capture is disabledBody capture with storage redaction
YAML
tracing:
capture_bodies: true
body_max_size: 262144
pii:
mode: redact_storage
policy_id: default/v1
stages:
request_headers: true
request_body: true
response_headers: true
response_body: true
detectors:
email: true
phone: true
ssn: true
token_like: trueDeployment profiles
- Production default:
capture_bodies=falsewith metadata-only traces. - Incident window capture:
capture_bodies=trueandpii.mode=redact_storagewith smallerbody_max_size. - Custom header redaction policy:
add keys to
pii.headers.denylist. - Custom body field coverage:
tune
pii.body.key_denylistfor domain-specific sensitive keys. - Deterministic placeholder stability:
set and keep
pii.replacement.hash_saltconsistent across deployments.
Example policies
Force metadata-only storage in all environments
YAML
tracing:
capture_bodies: false
pii:
mode: offRedact JSON keys and token-like values during capture
YAML
tracing:
capture_bodies: true
body_max_size: 262144
pii:
mode: redact_storage
body:
key_denylist:
- email
- phone
- password
- token
- ssn
- api_key
detectors:
email: true
phone: true
ssn: true
token_like: trueUse a custom placeholder format and stable salt
YAML
pii:
mode: redact_storage
replacement:
format: "[MASK:{type}:{hash}]"
hash_salt: REPLACE_WITH_STABLE_SALTValidation checks
-
Validate and start the gateway.
Bashongoingai config validate ongoingai serve -
Send one provider request that includes sensitive-like values in Terminal B.
Bashcurl http://localhost:8080/openai/v1/chat/completions \ -H "Authorization: Bearer $OPENAI_API_KEY" \ -H "Content-Type: application/json" \ -d '{"model":"gpt-4o-mini","messages":[{"role":"user","content":"email alice@example.com and token sk_test_1234567890"}]}' -
Query recent traces and pick one ID.
Bashcurl "http://localhost:8080/api/traces?limit=1"If
auth.enabled=true, include your gateway key header on API reads. -
Query trace detail.
Bashcurl "http://localhost:8080/api/traces/TRACE_ID"Placeholder:
TRACE_ID: Trace ID from/api/traces.
You should see:
request_headersandresponse_headerswith sensitive keys as[REDACTED].- No raw body content when
capture_bodies=false. - Redacted body placeholders when
capture_bodies=trueandpii.mode=redact_storage. - Metadata fields such as
redaction_mode,redaction_applied,redaction_counts, andredaction_policy_id.
Troubleshooting
Trace body fields are empty when capture is expected
- Symptom:
request_bodyandresponse_bodyare empty. - Cause:
tracing.capture_bodies=false, or redaction failed and storage body persistence was dropped. - Fix: Enable
capture_bodiesfor controlled windows and check metadata forredaction_storage_drop.
Provider request is denied by PII guardrail mode
- Symptom: Proxied provider requests return
403or503with a guardrail denial message. - Cause:
pii.mode=blockdetected protected content, orpii.mode=redact_upstream|blockfailed closed due policy-evaluation uncertainty (for example oversized request body or unsupported content type). - Fix: Keep request bodies within
tracing.body_max_size, use JSON/text request body content on guarded routes, or switch toredact_storageif you only need storage-stage protection.
Status semantics:
403means policy detection succeeded andblockmode denied the request.503means policy uncertainty inredact_upstreamorblockcaused a fail-closed deny.
Custom header denylist entries are not redacted
- Symptom: Custom header keys appear unchanged in traces.
- Cause:
pii.stages.request_headersorpii.stages.response_headersis disabled. - Fix: Enable the relevant header stage flags and keep the denylist keys set.
Placeholder hashes vary across environments
- Symptom: Redacted placeholder hashes differ for similar payloads.
- Cause: Different workspace scope or different
pii.replacement.hash_salt. - Fix: Keep workspace mapping stable and use a consistent hash salt strategy.