Skip to content

fix: preserve redacted artifact integrity - #2341

Merged
chubes4 merged 1 commit into
mainfrom
fix-2339-artifact-redaction-integrity
Aug 23, 2026
Merged

fix: preserve redacted artifact integrity#2341
chubes4 merged 1 commit into
mainfrom
fix-2339-artifact-redaction-integrity

Conversation

@chubes4

@chubes4 chubes4 commented Aug 23, 2026

Copy link
Copy Markdown
Collaborator

Summary

  • structurally redact JSON artifact content so sensitive-looking domain vocabulary cannot consume JSON delimiters
  • redact typed JSON payloads before materialization records payload/index hashes, keeping final bundle bytes and embedded SHA-256 references aligned
  • verify the original strict consumer shape end to end: named browser screenshots plus a state-transition-ledger typed artifact containing state-loss and authorization-bypass

Root Causes

  1. Named wordpress.browser-actions screenshot steps wrote PNGs under files/browser/, but older browser action results did not expose those paths through BrowserArtifact.files.screenshots, so final manifest assembly could not include them and strict orphan detection rejected the bundle. Main already contains the production registration fix from a6067fca (fix: manifest all browser screenshots); this PR adds strict end-to-end coverage proving every named screenshot is manifested exactly once.
  2. Typed JSON payloads and typed-artifacts/index.json passed through text-oriented redactString(). Its assignment heuristic could interpret values such as state-transition-ledger as secret assignments and replace the following comma, changing valid JSON like \"name\": \"state-transition-ledger\", into malformed \"name\": \"state-transition-ledger\"[redacted]. Typed payload refs were also hashed before that later capture-time mutation, leaving embedded hashes pointed at pre-redaction bytes.

Redaction And Digest Ordering

JSON capture now parses the document, redacts by key/value policy, and serializes valid JSON instead of applying assignment regexes to serialized syntax. Typed JSON bytes are structurally redacted before materializeStructuredArtifactFiles() computes payload hashes and builds the typed index; capture then hashes the final persisted bytes.

Before:

{
  "name": "state-transition-ledger"[redacted]
  "type": "fixture/state-transition-ledger/v1"
}

After:

{
  "name": "state-transition-ledger",
  "type": "fixture/state-transition-ledger/v1",
  "payload": {
    "oracleIds": ["state-loss", "authorization-bypass"],
    "authorization": "[redacted]",
    "api_token": "[redacted]"
  }
}

Secret Safety

The strict integration fixture includes an authorization value and an OpenAI-shaped token. It asserts both are redacted, the token is absent from payload and index bytes, oracle IDs remain exact, the typed payload SHA-256 equals the index reference, both screenshots occur once in manifest.json, and strict verification returns no violations.

Verification

  • npm run test:artifact-redaction-integrity
  • npm run test:browser-artifact-session
  • npm run test:redaction
  • npx tsx tests/structured-artifact-materializer.test.ts
  • npx tsx scripts/artifact-bundle-verifier-smoke.ts
  • npx tsx scripts/artifact-redaction-smoke.ts
  • npx tsx scripts/typed-artifacts-smoke.ts
  • npx tsx tests/adversarial-campaign.test.ts (11 passed)
  • npx tsx tests/recipe-browser-evidence.test.ts
  • npm run test:browser-actions-environment (10 passed)
  • npm run test:browser-transport-faults (5 passed)
  • npm run build:release
  • npm run smoke -- --group=package (passed; Docker-only MySQL E2E skipped because Docker is unavailable)
  • npm run test:release-package-coverage
  • npm run test:cli-build-freshness (7 passed)

The broader artifact smoke group reaches two unrelated existing failures: patch-path expectation #2064 and executable browser DTO fixture #2340. All artifact smoke commands relevant to this change pass.

Consumer Relation

Studio PR #184 remains a valid consumer mitigation for WP Codebox 0.23.3: it removed explicit named screenshot steps and collected ledgers as parsed declared artifacts while keeping strict verification enabled. This PR fixes the typed JSON redaction/hash ordering underneath that mitigation and locks in the already-landed named screenshot registration so consumers can safely restore the original shape.

Closes #2339

@chubes4
chubes4 merged commit 4022e67 into main Aug 23, 2026
4 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Artifact verifier orphans named browser screenshots and corrupts typed index during redaction

1 participant