Skip to content

Capture Time Redaction

aryehcitron@gmail.com edited this page Aug 21, 2026 · 1 revision

Render-time vs capture-time

Kronikol has two kinds of "hide this":

Mechanism Where it acts What it protects
ReportConfigurationOptions.ExcludedHeaders, RequestResponsePostProcessor / MidProcessor, the Request/Response…FormattingProcessor delegates Render time — only the PlantUML diagram note Diagram hygiene. The raw Headers / Content are still stored and still serialised verbatim into TestRunReport.json, the mergeable JSON, and any NDJSON sink. See Filtering and Redacting Diagram Content.
RequestResponseLogger.Redaction (CaptureRedaction) Capture time — before an entry is enqueued The security boundary. A redacted value never reaches the in-memory store or any file derived from it.

If a credential must not land on disk, redact at capture. Treat ExcludedHeaders as cosmetic.


Enable the secure preset

using Kronikol.Tracking;

// Once per process (e.g. in your test pipeline startup / report hook).
RequestResponseLogger.Redaction = CaptureRedaction.Secrets();

CaptureRedaction.Secrets() replaces the values of the well-known credential headers with [REDACTED] (case-insensitive): authorization, proxy-authorization, cookie, set-cookie, x-api-key, x-auth-token, api-key, x-amz-security-token, x-goog-api-key (CaptureRedaction.DefaultSecretHeaders).

Options

RequestResponseLogger.Redaction = new CaptureRedaction(["authorization", "x-internal-token"])
{
    Replacement = "***",        // what replaces a redacted value (default "[REDACTED]")
    DropHeaders = true,         // remove the header instead of replacing its value (default false)
}
.RedactContent(@"Bearer\s+[A-Za-z0-9\-_\.]+", "Bearer ***")   // regex over request/response bodies
.RedactContent(@"Password=[^;]+", "Password=***");
  • Headers — the denylist (mutable HashSet<string>, case-insensitive).
  • ContentPatterns / RedactContent(...) — regular expressions applied to Content; every match is replaced.
  • Custom — a final Func<RequestResponseLog, RequestResponseLog?> hook: rewrite anything, or return null to drop the entry entirely (e.g. health-check noise).
  • Phase variants (SetupVariant / ActionVariant) are redacted with the same rules.

Redaction runs before MaxContentLength truncation, so a secret near the end of a long body is still scrubbed.


Where else it applies

  • kronikol ingest replays NDJSON through RequestResponseLogger.Log, so a raw capture file produced elsewhere is still redacted on the way into the report (the CLI enables the secure preset by default; --no-redact / --redact-header adjust it).
  • Kronikol.Extensions.ProxyTap has its own capture-time denylist (ProxyTapOptions.SecretDenylist, default DefaultSecretHeaders) applied before any sink — including an NDJSON file sink, which the global hook would not see. See Integration ProxyTap Extension.
  • The mergeable JSON (GenerateMergeableData = true) is payload-free (component relationships only) and is safe to share widely regardless.

Verifying

The simplest assertion is against the data file:

var json = File.ReadAllText(Path.Combine(ReportGenerator.ResolveReportsDirectory(options), "TestRunReport.json"));
Assert.DoesNotContain("my-secret-token", json);

Home


Demo


Getting Started

Common Tasks

Integration Guides

Uninstrumentable / polyglot backends

Extensions

Configuration

Features

Reference

Clone this wiki locally