@glubean/redaction 0.1.6 → 0.1.7

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md ADDED
@@ -0,0 +1,158 @@
1
+ # @glubean/redaction
2
+
3
+ Scope-based secrets/PII detection and masking for [Glubean](https://glubean.dev).
4
+
5
+ ## Overview
6
+
7
+ Redaction v2 uses a data-driven scope model. Scopes declare **what** to redact (event type + field path + rules). Handlers declare **how** to interpret payloads (JSON, headers, URL query strings). Plugins provide detection logic (sensitive keys, value patterns).
8
+
9
+ All scope declarations — built-in HTTP, gRPC, or any future protocol — use the same shape. No hardcoded protocol knowledge in the redaction package.
10
+
11
+ ## Quick Start
12
+
13
+ ```ts
14
+ import {
15
+ compileScopes,
16
+ redactEvent,
17
+ BUILTIN_SCOPES,
18
+ DEFAULT_GLOBAL_RULES,
19
+ } from "@glubean/redaction";
20
+
21
+ // Compile scopes once at startup
22
+ const scopes = compileScopes({
23
+ builtinScopes: BUILTIN_SCOPES,
24
+ globalRules: DEFAULT_GLOBAL_RULES,
25
+ replacementFormat: "partial",
26
+ });
27
+
28
+ // Redact events
29
+ const event = {
30
+ type: "trace",
31
+ data: {
32
+ requestHeaders: { authorization: "Bearer secret-token" },
33
+ requestBody: { password: "hunter2", username: "alice" },
34
+ },
35
+ };
36
+
37
+ const redacted = redactEvent(event, scopes, "partial");
38
+ // redacted.data.requestHeaders.authorization → "Bea***123"
39
+ // redacted.data.requestBody.password → "hun***er2"
40
+ // redacted.data.requestBody.username → "alice" (not sensitive)
41
+ ```
42
+
43
+ ## Architecture
44
+
45
+ ```
46
+ scope declarations (built-in + plugins + user overrides)
47
+ → compile to CompiledScope[]
48
+ → redactEvent(event, compiledScopes)
49
+ → for each matching scope:
50
+ 1. extract target value via field path
51
+ 2. run the scope's handler
52
+ 3. handler calls engine with per-scope plugin pipeline
53
+ 4. write redacted value back
54
+ ```
55
+
56
+ ### Scopes
57
+
58
+ A scope declares where to redact and what rules apply:
59
+
60
+ ```ts
61
+ {
62
+ id: "http.request.headers",
63
+ name: "HTTP request headers",
64
+ event: "trace",
65
+ target: "data.requestHeaders",
66
+ handler: "headers",
67
+ rules: {
68
+ sensitiveKeys: ["authorization", "cookie"],
69
+ },
70
+ }
71
+ ```
72
+
73
+ - `id` — stable config key for user overrides
74
+ - `event` — which event type to match
75
+ - `target` — dot-path to the payload field
76
+ - `handler` — which handler interprets the payload
77
+ - `rules` — scope-specific sensitive keys and patterns
78
+
79
+ ### Handlers
80
+
81
+ Built-in handlers:
82
+
83
+ | Handler | Purpose |
84
+ |---------|---------|
85
+ | `json` | Recursive JSON object/array walker |
86
+ | `raw-string` | Value-pattern matching on plain strings |
87
+ | `url-query` | Parse URL, redact query params, serialize back |
88
+ | `headers` | Header map with cookie/set-cookie parsing |
89
+
90
+ ### Plugins
91
+
92
+ Detection plugins (unchanged from v1):
93
+
94
+ - **sensitive-keys** — key-level substring matching
95
+ - **jwt** — JWT token detection
96
+ - **bearer** — Bearer token detection
97
+ - **awsKeys** — AWS access key ID
98
+ - **githubTokens** — GitHub PAT tokens
99
+ - **email** — Email address detection
100
+ - **ipAddress** — IPv4 address detection
101
+ - **creditCard** — Credit card number detection
102
+ - **hexKeys** — Hex key detection (32+ chars)
103
+
104
+ ## Plugin Integration
105
+
106
+ Plugins declare their own redaction scopes via `PluginFactory.redaction`:
107
+
108
+ ```ts
109
+ // gRPC plugin
110
+ grpc({
111
+ proto: "./protos/users.proto",
112
+ address: "{{ADDR}}",
113
+ package: "acme.users.v1",
114
+ service: "UsersService",
115
+ });
116
+
117
+ // Plugin internally declares:
118
+ // redaction: [
119
+ // { id: "grpc.metadata", handler: "headers", rules: { sensitiveKeys: ["authorization"] } },
120
+ // { id: "grpc.request", handler: "json" },
121
+ // { id: "grpc.response", handler: "json" },
122
+ // ]
123
+ ```
124
+
125
+ The runner collects all plugin declarations and merges them with built-in scopes at compile time.
126
+
127
+ ## User Overrides
128
+
129
+ Users override scopes by stable `id` in `.glubean/redact.json`:
130
+
131
+ ```json
132
+ {
133
+ "scopes": {
134
+ "grpc.metadata": { "enabled": false },
135
+ "http.request.headers": {
136
+ "rules": { "sensitiveKeys": ["x-custom-secret"] }
137
+ }
138
+ },
139
+ "globalRules": {
140
+ "sensitiveKeys": ["my-internal-key"],
141
+ "customPatterns": [
142
+ { "name": "internal-id", "regex": "INT-[A-Z0-9]{8}" }
143
+ ]
144
+ }
145
+ }
146
+ ```
147
+
148
+ ## Replacement Formats
149
+
150
+ | Format | Example |
151
+ |--------|---------|
152
+ | `simple` | `[REDACTED]` |
153
+ | `labeled` | `[REDACTED:sensitive-keys]` |
154
+ | `partial` | `Bea***123` (smart masking) |
155
+
156
+ ## License
157
+
158
+ MIT
package/dist/adapter.d.ts CHANGED
@@ -1,41 +1,29 @@
1
1
  /**
2
2
  * @module adapter
3
3
  *
4
- * Scope adapter — maps ExecutionEvent types to redaction scopes.
4
+ * Generic event redaction dispatcher.
5
5
  *
6
- * Without this adapter, the engine's scope toggles are decorative.
7
- * This function dispatches each event's payload fields to the correct
8
- * scope so the engine can gate redaction per-scope.
9
- *
10
- * Both the CLI (for --share) and the server (for event ingestion) use
11
- * this adapter. The server adapter may handle additional premium scopes.
6
+ * v2 replaces the hardcoded event-type switch with a data-driven dispatcher
7
+ * that uses compiled scopes to find matching scopes, extract targets,
8
+ * and apply handlers.
12
9
  */
13
- import type { RedactionEngine } from "./engine.js";
14
- import type { RedactionConfig } from "./types.js";
10
+ import type { CompiledScope } from "./types.js";
15
11
  /**
16
- * A generic event shape compatible with both ExecutionEvent (oss runner)
17
- * and RunEvent (server). The adapter only reads `type` and mutates payload
18
- * fields in-place on a clone.
12
+ * A generic event shape. The dispatcher only reads `type` and mutates
13
+ * payload fields on a clone based on compiled scope declarations.
19
14
  */
20
15
  export interface RedactableEvent {
21
16
  type: string;
22
17
  [key: string]: unknown;
23
18
  }
24
19
  /**
25
- * Redact an event by dispatching its payload fields to the appropriate
26
- * scopes. Returns a new event object — the original is not mutated.
27
- *
28
- * Scope mapping:
29
- * - trace → requestHeaders, requestQuery, requestBody, responseHeaders, responseBody
30
- * - log → consoleOutput
31
- * - assertion → errorMessages
32
- * - error / status → errorMessages
33
- * - warning / schema_validation → errorMessages
34
- * - step_end → returnState
35
- * - metric, step_start, start, summary → no redaction
20
+ * Redact an event by dispatching its payload fields to matching scopes.
21
+ * Returns a new event object — the original is not mutated.
36
22
  *
37
- * @example
38
- * const redacted = redactEvent(engine, { type: "trace", data: { ... } });
23
+ * @param event The event to redact.
24
+ * @param scopes Pre-compiled scopes from compileScopes().
25
+ * @param replacementFormat Replacement format for engine instances.
26
+ * @param maxDepth Optional max object depth.
39
27
  */
40
- export declare function redactEvent<C extends RedactionConfig>(engine: RedactionEngine<C>, event: RedactableEvent): RedactableEvent;
28
+ export declare function redactEvent(event: RedactableEvent, scopes: CompiledScope[], replacementFormat?: "simple" | "labeled" | "partial", maxDepth?: number): RedactableEvent;
41
29
  //# sourceMappingURL=adapter.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"adapter.d.ts","sourceRoot":"","sources":["../src/adapter.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;GAWG;AAEH,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,aAAa,CAAC;AACnD,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,YAAY,CAAC;AAElD;;;;GAIG;AACH,MAAM,WAAW,eAAe;IAC9B,IAAI,EAAE,MAAM,CAAC;IACb,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC;CACxB;AAED;;;;;;;;;;;;;;;GAeG;AACH,wBAAgB,WAAW,CAAC,CAAC,SAAS,eAAe,EACnD,MAAM,EAAE,eAAe,CAAC,CAAC,CAAC,EAC1B,KAAK,EAAE,eAAe,GACrB,eAAe,CAgIjB"}
1
+ {"version":3,"file":"adapter.d.ts","sourceRoot":"","sources":["../src/adapter.ts"],"names":[],"mappings":"AAAA;;;;;;;;GAQG;AAEH,OAAO,KAAK,EAAE,aAAa,EAAmC,MAAM,YAAY,CAAC;AAGjF;;;GAGG;AACH,MAAM,WAAW,eAAe;IAC9B,IAAI,EAAE,MAAM,CAAC;IACb,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC;CACxB;AAED;;;;;;;;GAQG;AACH,wBAAgB,WAAW,CACzB,KAAK,EAAE,eAAe,EACtB,MAAM,EAAE,aAAa,EAAE,EACvB,iBAAiB,GAAE,QAAQ,GAAG,SAAS,GAAG,SAAqB,EAC/D,QAAQ,CAAC,EAAE,MAAM,GAChB,eAAe,CA0BjB"}
package/dist/adapter.js CHANGED
@@ -1,110 +1,40 @@
1
1
  /**
2
2
  * @module adapter
3
3
  *
4
- * Scope adapter — maps ExecutionEvent types to redaction scopes.
4
+ * Generic event redaction dispatcher.
5
5
  *
6
- * Without this adapter, the engine's scope toggles are decorative.
7
- * This function dispatches each event's payload fields to the correct
8
- * scope so the engine can gate redaction per-scope.
9
- *
10
- * Both the CLI (for --share) and the server (for event ingestion) use
11
- * this adapter. The server adapter may handle additional premium scopes.
6
+ * v2 replaces the hardcoded event-type switch with a data-driven dispatcher
7
+ * that uses compiled scopes to find matching scopes, extract targets,
8
+ * and apply handlers.
12
9
  */
10
+ import { createScopeEngine } from "./compiler.js";
13
11
  /**
14
- * Redact an event by dispatching its payload fields to the appropriate
15
- * scopes. Returns a new event object — the original is not mutated.
16
- *
17
- * Scope mapping:
18
- * - trace → requestHeaders, requestQuery, requestBody, responseHeaders, responseBody
19
- * - log → consoleOutput
20
- * - assertion → errorMessages
21
- * - error / status → errorMessages
22
- * - warning / schema_validation → errorMessages
23
- * - step_end → returnState
24
- * - metric, step_start, start, summary → no redaction
12
+ * Redact an event by dispatching its payload fields to matching scopes.
13
+ * Returns a new event object — the original is not mutated.
25
14
  *
26
- * @example
27
- * const redacted = redactEvent(engine, { type: "trace", data: { ... } });
15
+ * @param event The event to redact.
16
+ * @param scopes Pre-compiled scopes from compileScopes().
17
+ * @param replacementFormat Replacement format for engine instances.
18
+ * @param maxDepth Optional max object depth.
28
19
  */
29
- export function redactEvent(engine, event) {
30
- const t = event.type;
31
- // Events that don't need redaction return as-is
32
- if (t === "metric" ||
33
- t === "step_start" ||
34
- t === "start" ||
35
- t === "summary" ||
36
- t === "timeout_update") {
20
+ export function redactEvent(event, scopes, replacementFormat = "partial", maxDepth) {
21
+ // Find all enabled scopes matching this event type
22
+ const matching = scopes.filter((scope) => scope.enabled && scope.event === event.type);
23
+ if (matching.length === 0)
37
24
  return event;
38
- }
39
- // step_end: only needs redaction if returnState is present
40
- if (t === "step_end") {
41
- if (event.returnState != null) {
42
- const clone = structuredClone(event);
43
- clone.returnState = engine.redact(clone.returnState, "returnState").value;
44
- return clone;
45
- }
46
- return event;
47
- }
48
25
  // Clone to avoid mutating the original
49
26
  const clone = structuredClone(event);
50
- if (t === "trace") {
51
- // Trace events have data: ApiTrace with headers/bodies
52
- const data = clone.data;
53
- if (data) {
54
- if (data.requestHeaders != null) {
55
- data.requestHeaders = engine.redact(data.requestHeaders, "requestHeaders").value;
56
- }
57
- if (data.requestBody != null) {
58
- data.requestBody = engine.redact(data.requestBody, "requestBody").value;
59
- }
60
- if (data.responseHeaders != null) {
61
- data.responseHeaders = engine.redact(data.responseHeaders, "responseHeaders").value;
62
- }
63
- if (data.responseBody != null) {
64
- data.responseBody = engine.redact(data.responseBody, "responseBody").value;
65
- }
66
- // URL may contain query params with secrets
67
- if (typeof data.url === "string") {
68
- data.url = engine.redact(data.url, "requestQuery").value;
69
- }
70
- }
71
- }
72
- else if (t === "log") {
73
- if (clone.message != null) {
74
- clone.message = engine.redact(clone.message, "consoleOutput").value;
75
- }
76
- if (clone.data != null) {
77
- clone.data = engine.redact(clone.data, "consoleOutput").value;
78
- }
79
- }
80
- else if (t === "assertion") {
81
- if (clone.message != null) {
82
- clone.message = engine.redact(clone.message, "errorMessages").value;
83
- }
84
- if (clone.actual != null) {
85
- clone.actual = engine.redact(clone.actual, "errorMessages").value;
86
- }
87
- if (clone.expected != null) {
88
- clone.expected = engine.redact(clone.expected, "errorMessages").value;
89
- }
90
- }
91
- else if (t === "error") {
92
- if (clone.message != null) {
93
- clone.message = engine.redact(clone.message, "errorMessages").value;
94
- }
95
- }
96
- else if (t === "status") {
97
- if (clone.error != null) {
98
- clone.error = engine.redact(clone.error, "errorMessages").value;
99
- }
100
- if (clone.stack != null) {
101
- clone.stack = engine.redact(clone.stack, "errorMessages").value;
102
- }
103
- }
104
- else if (t === "warning" || t === "schema_validation") {
105
- if (clone.message != null) {
106
- clone.message = engine.redact(clone.message, "errorMessages").value;
107
- }
27
+ for (const scope of matching) {
28
+ const current = scope.get(clone);
29
+ if (current === undefined)
30
+ continue;
31
+ const engine = createScopeEngine(scope, replacementFormat, maxDepth);
32
+ const ctx = {
33
+ scopeId: scope.id,
34
+ scopeName: scope.name,
35
+ };
36
+ const result = scope.handler.process(current, ctx, engine);
37
+ scope.set(clone, result.value);
108
38
  }
109
39
  return clone;
110
40
  }
@@ -1 +1 @@
1
- {"version":3,"file":"adapter.js","sourceRoot":"","sources":["../src/adapter.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"adapter.js","sourceRoot":"","sources":["../src/adapter.ts"],"names":[],"mappings":"AAAA;;;;;;;;GAQG;AAGH,OAAO,EAAE,iBAAiB,EAAE,MAAM,eAAe,CAAC;AAWlD;;;;;;;;GAQG;AACH,MAAM,UAAU,WAAW,CACzB,KAAsB,EACtB,MAAuB,EACvB,oBAAsD,SAAS,EAC/D,QAAiB;IAEjB,mDAAmD;IACnD,MAAM,QAAQ,GAAG,MAAM,CAAC,MAAM,CAC5B,CAAC,KAAK,EAAE,EAAE,CAAC,KAAK,CAAC,OAAO,IAAI,KAAK,CAAC,KAAK,KAAK,KAAK,CAAC,IAAI,CACvD,CAAC;IAEF,IAAI,QAAQ,CAAC,MAAM,KAAK,CAAC;QAAE,OAAO,KAAK,CAAC;IAExC,uCAAuC;IACvC,MAAM,KAAK,GAAG,eAAe,CAAC,KAAK,CAAC,CAAC;IAErC,KAAK,MAAM,KAAK,IAAI,QAAQ,EAAE,CAAC;QAC7B,MAAM,OAAO,GAAG,KAAK,CAAC,GAAG,CAAC,KAAK,CAAC,CAAC;QACjC,IAAI,OAAO,KAAK,SAAS;YAAE,SAAS;QAEpC,MAAM,MAAM,GAAG,iBAAiB,CAAC,KAAK,EAAE,iBAAiB,EAAE,QAAQ,CAAC,CAAC;QACrE,MAAM,GAAG,GAAmB;YAC1B,OAAO,EAAE,KAAK,CAAC,EAAE;YACjB,SAAS,EAAE,KAAK,CAAC,IAAI;SACtB,CAAC;QAEF,MAAM,MAAM,GAAG,KAAK,CAAC,OAAO,CAAC,OAAO,CAAC,OAAO,EAAE,GAAG,EAAE,MAAM,CAAC,CAAC;QAC3D,KAAK,CAAC,GAAG,CAAC,KAAK,EAAE,MAAM,CAAC,KAAK,CAAC,CAAC;IACjC,CAAC;IAED,OAAO,KAAK,CAAC;AACf,CAAC"}
@@ -0,0 +1,47 @@
1
+ /**
2
+ * @module compiler
3
+ *
4
+ * Compiles scope declarations into ready-to-execute CompiledScope[].
5
+ *
6
+ * Flow:
7
+ * 1. Merge built-in + plugin scope declarations
8
+ * 2. Apply user overrides by scope id
9
+ * 3. Resolve handler for each scope
10
+ * 4. Build per-scope plugin pipeline (scope keys + global keys + patterns)
11
+ * 5. Return CompiledScope[] for use by redactEvent()
12
+ */
13
+ import type { CompiledScope, GlobalRules, RedactionHandler, RedactionScopeDeclaration, ScopeRules } from "./types.js";
14
+ import { RedactionEngine } from "./engine.js";
15
+ /** User-provided scope overrides keyed by scope id. */
16
+ export interface ScopeOverride {
17
+ enabled?: boolean;
18
+ rules?: ScopeRules;
19
+ }
20
+ /** Compiler options. */
21
+ export interface CompilerOptions {
22
+ /** Built-in scope declarations (HTTP, log, error, etc.). */
23
+ builtinScopes: RedactionScopeDeclaration[];
24
+ /** Plugin-provided scope declarations. */
25
+ pluginScopes?: RedactionScopeDeclaration[];
26
+ /** Plugin-provided custom handlers. */
27
+ pluginHandlers?: RedactionHandler[];
28
+ /** User overrides by scope id. */
29
+ userOverrides?: Record<string, ScopeOverride>;
30
+ /** Global additive rules. */
31
+ globalRules: GlobalRules;
32
+ /** Replacement format. */
33
+ replacementFormat: "simple" | "labeled" | "partial";
34
+ /** Max object nesting depth. Default: 10. */
35
+ maxDepth?: number;
36
+ }
37
+ /**
38
+ * Compile scope declarations into ready-to-execute CompiledScope[].
39
+ */
40
+ export declare function compileScopes(options: CompilerOptions): CompiledScope[];
41
+ /**
42
+ * Create a scope-specific RedactionEngine instance.
43
+ *
44
+ * Each scope gets its own engine with its own plugin pipeline.
45
+ */
46
+ export declare function createScopeEngine(scope: CompiledScope, replacementFormat: "simple" | "labeled" | "partial", maxDepth?: number): RedactionEngine;
47
+ //# sourceMappingURL=compiler.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"compiler.d.ts","sourceRoot":"","sources":["../src/compiler.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;GAWG;AAEH,OAAO,KAAK,EACV,aAAa,EACb,WAAW,EAEX,gBAAgB,EAGhB,yBAAyB,EACzB,UAAU,EACX,MAAM,YAAY,CAAC;AACpB,OAAO,EAAE,eAAe,EAAE,MAAM,aAAa,CAAC;AAM9C,uDAAuD;AACvD,MAAM,WAAW,aAAa;IAC5B,OAAO,CAAC,EAAE,OAAO,CAAC;IAClB,KAAK,CAAC,EAAE,UAAU,CAAC;CACpB;AAED,wBAAwB;AACxB,MAAM,WAAW,eAAe;IAC9B,4DAA4D;IAC5D,aAAa,EAAE,yBAAyB,EAAE,CAAC;IAC3C,0CAA0C;IAC1C,YAAY,CAAC,EAAE,yBAAyB,EAAE,CAAC;IAC3C,uCAAuC;IACvC,cAAc,CAAC,EAAE,gBAAgB,EAAE,CAAC;IACpC,kCAAkC;IAClC,aAAa,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,aAAa,CAAC,CAAC;IAC9C,6BAA6B;IAC7B,WAAW,EAAE,WAAW,CAAC;IACzB,0BAA0B;IAC1B,iBAAiB,EAAE,QAAQ,GAAG,SAAS,GAAG,SAAS,CAAC;IACpD,6CAA6C;IAC7C,QAAQ,CAAC,EAAE,MAAM,CAAC;CACnB;AA4GD;;GAEG;AACH,wBAAgB,aAAa,CAAC,OAAO,EAAE,eAAe,GAAG,aAAa,EAAE,CA4DvE;AAED;;;;GAIG;AACH,wBAAgB,iBAAiB,CAC/B,KAAK,EAAE,aAAa,EACpB,iBAAiB,EAAE,QAAQ,GAAG,SAAS,GAAG,SAAS,EACnD,QAAQ,CAAC,EAAE,MAAM,GAChB,eAAe,CAMjB"}
@@ -0,0 +1,178 @@
1
+ /**
2
+ * @module compiler
3
+ *
4
+ * Compiles scope declarations into ready-to-execute CompiledScope[].
5
+ *
6
+ * Flow:
7
+ * 1. Merge built-in + plugin scope declarations
8
+ * 2. Apply user overrides by scope id
9
+ * 3. Resolve handler for each scope
10
+ * 4. Build per-scope plugin pipeline (scope keys + global keys + patterns)
11
+ * 5. Return CompiledScope[] for use by redactEvent()
12
+ */
13
+ import { RedactionEngine } from "./engine.js";
14
+ import { BUILTIN_HANDLERS } from "./handlers.js";
15
+ import { sensitiveKeysPlugin } from "./plugins/sensitive-keys.js";
16
+ import { createPatternPlugins } from "./plugins/mod.js";
17
+ /**
18
+ * Resolve field path accessor functions.
19
+ *
20
+ * Supports dot-separated paths (e.g., "data.requestHeaders")
21
+ * and "$self" for the whole event.
22
+ */
23
+ function makeAccessors(target) {
24
+ if (target === "$self") {
25
+ return {
26
+ get: (event) => event,
27
+ set: (event, value) => {
28
+ // $self: merge redacted properties back onto the event
29
+ if (value && typeof value === "object" && !Array.isArray(value)) {
30
+ const redacted = value;
31
+ for (const key of Object.keys(redacted)) {
32
+ event[key] = redacted[key];
33
+ }
34
+ }
35
+ },
36
+ };
37
+ }
38
+ const parts = target.split(".");
39
+ return {
40
+ get(event) {
41
+ let current = event;
42
+ for (const part of parts) {
43
+ if (current == null || typeof current !== "object")
44
+ return undefined;
45
+ current = current[part];
46
+ }
47
+ return current;
48
+ },
49
+ set(event, value) {
50
+ let current = event;
51
+ for (let i = 0; i < parts.length - 1; i++) {
52
+ const next = current[parts[i]];
53
+ if (next == null || typeof next !== "object")
54
+ return;
55
+ current = next;
56
+ }
57
+ current[parts[parts.length - 1]] = value;
58
+ },
59
+ };
60
+ }
61
+ /**
62
+ * Build the plugin pipeline for a specific scope.
63
+ *
64
+ * Order:
65
+ * 1. Sensitive keys plugin (scope-specific + global additive keys)
66
+ * 2. Pattern plugins (scope-specific + global patterns)
67
+ * 3. Custom patterns from global rules
68
+ */
69
+ function buildScopePlugins(scopeRules, globalRules) {
70
+ const plugins = [];
71
+ // Merge sensitive keys: scope-specific + global
72
+ const allKeys = new Set();
73
+ if (scopeRules?.sensitiveKeys) {
74
+ for (const k of scopeRules.sensitiveKeys)
75
+ allKeys.add(k.toLowerCase());
76
+ }
77
+ for (const k of globalRules.sensitiveKeys)
78
+ allKeys.add(k.toLowerCase());
79
+ if (allKeys.size > 0) {
80
+ plugins.push(sensitiveKeysPlugin({
81
+ useBuiltIn: false,
82
+ additional: [...allKeys],
83
+ excluded: [],
84
+ }));
85
+ }
86
+ // Merge pattern names: scope-specific + global
87
+ const enabledPatterns = new Set();
88
+ if (scopeRules?.patterns) {
89
+ for (const p of scopeRules.patterns)
90
+ enabledPatterns.add(p);
91
+ }
92
+ for (const p of globalRules.patterns)
93
+ enabledPatterns.add(p);
94
+ // Add pattern plugins for enabled patterns
95
+ const patternPlugins = createPatternPlugins(enabledPatterns);
96
+ plugins.push(...patternPlugins);
97
+ // Add custom patterns from global rules
98
+ for (const custom of globalRules.customPatterns) {
99
+ try {
100
+ new RegExp(custom.regex, "g");
101
+ plugins.push({
102
+ name: custom.name,
103
+ matchValue: () => new RegExp(custom.regex, "g"),
104
+ });
105
+ }
106
+ catch {
107
+ // Skip invalid regex
108
+ }
109
+ }
110
+ return plugins;
111
+ }
112
+ /**
113
+ * Compile scope declarations into ready-to-execute CompiledScope[].
114
+ */
115
+ export function compileScopes(options) {
116
+ // Merge all scope declarations
117
+ const allDeclarations = [
118
+ ...options.builtinScopes,
119
+ ...(options.pluginScopes ?? []),
120
+ ];
121
+ // Build handler registry
122
+ const handlers = { ...BUILTIN_HANDLERS };
123
+ if (options.pluginHandlers) {
124
+ for (const h of options.pluginHandlers) {
125
+ handlers[h.name] = h;
126
+ }
127
+ }
128
+ // Compile each scope
129
+ const compiled = [];
130
+ for (const decl of allDeclarations) {
131
+ // Apply user overrides
132
+ const override = options.userOverrides?.[decl.id];
133
+ const enabled = override?.enabled ?? true;
134
+ const rules = {
135
+ sensitiveKeys: [
136
+ ...(decl.rules?.sensitiveKeys ?? []),
137
+ ...(override?.rules?.sensitiveKeys ?? []),
138
+ ],
139
+ patterns: [
140
+ ...(decl.rules?.patterns ?? []),
141
+ ...(override?.rules?.patterns ?? []),
142
+ ],
143
+ };
144
+ // Resolve handler
145
+ const handler = handlers[decl.handler];
146
+ if (!handler) {
147
+ throw new Error(`Redaction scope "${decl.id}" references unknown handler "${decl.handler}"`);
148
+ }
149
+ // Build per-scope plugin pipeline
150
+ const plugins = buildScopePlugins(rules, options.globalRules);
151
+ // Build field accessors
152
+ const accessors = makeAccessors(decl.target);
153
+ compiled.push({
154
+ id: decl.id,
155
+ name: decl.name,
156
+ event: decl.event,
157
+ enabled,
158
+ get: accessors.get,
159
+ set: accessors.set,
160
+ handler,
161
+ plugins,
162
+ });
163
+ }
164
+ return compiled;
165
+ }
166
+ /**
167
+ * Create a scope-specific RedactionEngine instance.
168
+ *
169
+ * Each scope gets its own engine with its own plugin pipeline.
170
+ */
171
+ export function createScopeEngine(scope, replacementFormat, maxDepth) {
172
+ return new RedactionEngine({
173
+ plugins: scope.plugins,
174
+ replacementFormat,
175
+ maxDepth,
176
+ });
177
+ }
178
+ //# sourceMappingURL=compiler.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"compiler.js","sourceRoot":"","sources":["../src/compiler.ts"],"names":[],"mappings":"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"}
@@ -1,29 +1,39 @@
1
1
  /**
2
2
  * @module defaults
3
3
  *
4
- * Built-in sensitive keys, pattern source strings, and the default
5
- * redaction configuration used as the mandatory baseline for --share.
4
+ * Built-in scope declarations, pattern source strings, and default config.
5
+ *
6
+ * v2: HTTP scopes are declared as data, not as a fixed interface.
7
+ * They use the same shape as external plugin declarations.
6
8
  */
7
- import type { RedactionConfig } from "./types.js";
9
+ import type { GlobalRules, RedactionConfig, RedactionScopeDeclaration } from "./types.js";
8
10
  /**
9
- * Keys whose values are always redacted when matched (case-insensitive
10
- * substring match). Ported from glubean-v1 RedactionService for parity.
11
+ * Built-in scope declarations for HTTP, log, error, assertion, and step events.
12
+ *
13
+ * These are the "http-plugin" built-in contributor — they use the same
14
+ * declaration model as any external plugin.
11
15
  */
12
- export declare const BUILT_IN_SENSITIVE_KEYS: readonly string[];
16
+ export declare const BUILTIN_SCOPES: RedactionScopeDeclaration[];
13
17
  /**
14
18
  * Regex source strings for built-in value-level patterns.
15
- * Plugins create new RegExp instances from these on each call
16
- * to avoid stale lastIndex state.
19
+ * Plugins create new RegExp instances from these on each call.
17
20
  */
18
21
  export declare const PATTERN_SOURCES: Record<string, {
19
22
  source: string;
20
23
  flags: string;
21
24
  }>;
22
25
  /**
23
- * The mandatory baseline configuration for --share.
26
+ * Default global additive rules.
27
+ *
28
+ * These are intentionally minimal — most sensitive keys now live
29
+ * in scope-specific declarations, not in globals.
30
+ */
31
+ export declare const DEFAULT_GLOBAL_RULES: GlobalRules;
32
+ /**
33
+ * Default redaction config v2.
24
34
  *
25
- * All scopes on, all patterns on, useBuiltIn keys, simple replacement.
26
- * User .glubean/redact.json can only add rules on top — never weaken this.
35
+ * All built-in scopes enabled, all patterns enabled globally,
36
+ * scope-specific sensitive keys declared per scope.
27
37
  */
28
38
  export declare const DEFAULT_CONFIG: RedactionConfig;
29
39
  //# sourceMappingURL=defaults.d.ts.map