Skip to content

fix(multiscan): authenticate resumed scans and preserve outcomes - #466

Draft
mldangelo-oai wants to merge 9 commits into
mainfrom
mdangelo/codex/authenticate-multiscan-recovery
Draft

fix(multiscan): authenticate resumed scans and preserve outcomes#466
mldangelo-oai wants to merge 9 commits into
mainfrom
mdangelo/codex/authenticate-multiscan-recovery

Conversation

@mldangelo-oai

@mldangelo-oai mldangelo-oai commented Aug 15, 2026

Copy link
Copy Markdown
Collaborator

Summary

Authenticate saved bulk-scan artifacts before reusing them, recover derived reports from validated canonical documents, and preserve complete or incomplete scan outcomes when checkout cleanup fails.

Fixes #30. Fixes #211. Fixes #248. Related proposals: #97, #218, and #255.

Changes

  • Reuse canonical schema and seal validation, then bind resumed output to the pinned task, producer, target identity, revision, mode, complete requested scope, and worktree snapshot.
  • Validate complete ledger records and safe numeric attempts before using them. Require saved reports to remain in the expected canonical campaign artifact directory; malformed records require recovery instead of another paid scan.
  • Preserve valid historical and incomplete results, output aliases, scoped symlinks, and configured plugin archives. Normalize legacy directory scopes with the existing canonical path convention.
  • Recover an unsealed or missing derived report through the SDK-owned Python report projection and the selected plugin schemas. Preserve the actual historical report entry covered by a validated seal, including unambiguous case-insensitive filename aliases.
  • Resume an already-authenticated sealed report without selecting or probing Python. Reuse normalized report-name, directory-entry, and checked-file identity evidence, including Windows behavior.
  • Regenerate distinct unsealed report entries through the existing atomic writer. A shared inode alone does not establish the report role; ambiguous entry relationships stop before writing.
  • Apply invoking-repository, local-source, and campaign exclusions through the existing Python resolver before its usability check, and carry its sanitized environment into report generation. Preserve configured interpreter precedence and unknown v1 fingerprint members.
  • Store redacted scan and cleanup warnings on attempt receipts and count warned tasks across matching historical attempts.
  • Use authenticated coverage as the resume result and one best-effort cleanup path. Report-recovery failures require recovery instead of starting another scan; resume does not rewrite an earned receipt, cost, or attempt count.
  • Bump the bundled and standalone plugin version together to 0.1.21 for the report-only helper.
  • Merge the current main branch additively.

Testing

  • Current follow-up: seven bounded report-role, resume, report-only, configured-schema-archive, cancellation, and checked-file identity regressions with Bun 1.3.14, --no-env-file, and the original 30-second timeout — 7 passed, 46 assertions, 0 failures. New coverage uses isolated metadata, reader, and writer mocks only.
  • pnpm run types — passed.
  • Targeted Prettier checks for the changed TypeScript files — passed.
  • Python AST syntax check for the finalizer — passed.
  • git diff HEAD^ HEAD --check — passed.
  • Current head 7ac503f8: complete fixed-seed SDK suite with Bun 1.3.14, --no-env-file, seed 12345, and the original 30-second timeout — 1,311 passed, 11 skipped, 0 failed; 9,259 assertions across 63 files. JUnit agrees. Live integration and machine-policy opt-ins were disabled.
  • Build, pack, explicit plugin-files.json package inspection, and the unchanged installed real-worker smoke — passed once, sequentially. The packed helper and paired plugin version match the frozen source.
  • Independent exact-head source review and native prepublish review — passed. Fresh pushed-head cross-platform/package CI and repository-supported review remain required.

Risk and rollout

Valid historical plugin output remains resumable, including configured archives that contain schemas without current helper scripts and permitted unknown v1 fingerprint fields. Authenticated report entries retain their historical formatting and do not require Python selection. Distinct unsealed entries are regenerated atomically without changing canonical JSON, seals, SARIF, HTML, receipts, costs, or attempts; ambiguous sealed-entry relationships require recovery before any write. Malformed complete ledger records and projection failures stop with recovery-required errors; cancellation is preserved. Historical dirty-worktree or symlink-scoped receipts without authoritative identity metadata may require one new attempt. The warning count and optional receipt warnings are additive; a cleanup warning does not change the scan's exit outcome. The plugin version advances to 0.1.21; no contract schema or dependency changes are included.

Public disclosure review

Newly authored material was reviewed for public disclosure. Existing automated review comments contain access-restricted report references; maintainer cleanup remains outstanding.

  • No customer, partner, prospect, or user identities, data, or identifying details are included.
  • No credentials, personal data, private source, scan findings, or nonpublic links or tickets are included.
  • I reviewed the branch name, title, description, commits, changes, comments, logs, screenshots, attachments, and links for public disclosure.

@github-actions github-actions Bot added the bug Something isn't working label Aug 15, 2026
@mldangelo-oai

Copy link
Copy Markdown
Collaborator Author

@codex review

@chatgpt-codex-connector

Copy link
Copy Markdown

Security review completed. No security issues were found in this pull request.

Reviewed commit: 0afea57ee1

View security finding report

Only the user who started this review can view the report in Codex.

ℹ️ About Codex security reviews in GitHub

This is an experimental Codex feature. Security reviews are triggered when:

  • You comment "@codex security review"
  • A regular code review gets triggered (for example, "@codex review" or when a PR is opened), and you’re opted in so security review runs alongside code review

Once complete, Codex will leave suggestions, or a comment if no findings are found.

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: 0afea57ee1

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

Comment thread sdk/typescript/src/multiscan.ts Outdated
Comment thread sdk/typescript/src/multiscan.ts Outdated
Comment thread sdk/typescript/src/multiscan.ts Outdated
@mldangelo-oai

Copy link
Copy Markdown
Collaborator Author

@codex review

@chatgpt-codex-connector

Copy link
Copy Markdown

Codex Review: Didn't find any major issues. Breezy!

Reviewed commit: 7a0e18410a

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

@chatgpt-codex-connector

Copy link
Copy Markdown

Security review completed. No security issues were found in this pull request.

Reviewed commit: 7a0e18410a

View security finding report

Only the user who started this review can view the report in Codex.

ℹ️ About Codex security reviews in GitHub

This is an experimental Codex feature. Security reviews are triggered when:

  • You comment "@codex security review"
  • A regular code review gets triggered (for example, "@codex review" or when a PR is opened), and you’re opted in so security review runs alongside code review

Once complete, Codex will leave suggestions, or a comment if no findings are found.

Copy link
Copy Markdown
Collaborator Author

@codex review

Please review the current head, d61658ebcec9e5a8176d3e19200fee020028fd49.

@chatgpt-codex-connector

Copy link
Copy Markdown

Security review completed. No security issues were found in this pull request.

Reviewed commit: d61658ebce

View security finding report

Only the user who started this review can view the report in Codex.

ℹ️ About Codex security reviews in GitHub

This is an experimental Codex feature. Security reviews are triggered when:

  • You comment "@codex security review"
  • A regular code review gets triggered (for example, "@codex review" or when a PR is opened), and you’re opted in so security review runs alongside code review

Once complete, Codex will leave suggestions, or a comment if no findings are found.

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: d61658ebce

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

Comment on lines +760 to +763
const { manifest, coverage } = await loadContract(path, {
pluginRoot,
signal,
});

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P1 Badge Verify the report before accepting a resumed bundle

When an imported or replaced bundle changes only report.md, hasArtifacts still accepts it and this call validates only the canonical JSON documents and their sealed artifacts; report.md is merely checked for existence and is not part of the manifest seal. The campaign therefore skips the scan while preserving an attacker-controlled or stale human-facing report even though the plugin defines that report as a deterministic projection of the validated documents; regenerate the projection or compare it before accepting the resume.

AGENTS.md reference: sdk/typescript/AGENTS.md:L19-L20

Useful? React with 👍 / 👎.

Copy link
Copy Markdown
Collaborator Author

@codex review

Please review the current head, df25b47d2605f0be7babf009343027575edbd459.

@chatgpt-codex-connector

Copy link
Copy Markdown

Security review completed. No security issues were found in this pull request.

Reviewed commit: df25b47d26

View security finding report

Only the user who started this review can view the report in Codex.

ℹ️ About Codex security reviews in GitHub

This is an experimental Codex feature. Security reviews are triggered when:

  • You comment "@codex security review"
  • A regular code review gets triggered (for example, "@codex review" or when a PR is opened), and you’re opted in so security review runs alongside code review

Once complete, Codex will leave suggestions, or a comment if no findings are found.

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: df25b47d26

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

Comment thread sdk/typescript/src/multiscan.ts Outdated
receipt.warning ??
`Scan coverage is ${coverage}; results may be incomplete.`,
});
await restoreReport(canonicalArtifactOutput, schemaPluginRoot);

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Skip recovery when the report is already sealed

When a resumed manifest includes report.md among its sealed artifacts, loadContract has already authenticated that report and the Python helper will immediately return without writing anything. Calling restoreReport unconditionally still resolves and probes a Python interpreter first, so a valid completed campaign becomes impossible to resume if Python was removed or is temporarily misconfigured; inspect the authenticated artifact list and invoke recovery only for an unsealed report.

AGENTS.md reference: sdk/typescript/AGENTS.md:L23-L23

Useful? React with 👍 / 👎.

Copy link
Copy Markdown
Collaborator Author

@codex review

Please review the current head, 4b270e7d3e39c27b61e944af9053a711db3116c5.

@chatgpt-codex-connector

Copy link
Copy Markdown

Security review completed. No security issues were found in this pull request.

Reviewed commit: 4b270e7d3e

View security finding report

Only the user who started this review can view the report in Codex.

ℹ️ About Codex security reviews in GitHub

This is an experimental Codex feature. Security reviews are triggered when:

  • You comment "@codex security review"
  • A regular code review gets triggered (for example, "@codex review" or when a PR is opened), and you’re opted in so security review runs alongside code review

Once complete, Codex will leave suggestions, or a comment if no findings are found.

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: 4b270e7d3e

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

Comment on lines +324 to +330
const sameFile = await sameCheckedFileDevice(
file,
report,
await file.stat(),
);
throwIfAborted(signal);
if (sameFile) return true;

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P1 Badge Regenerate hard-linked report aliases

When an unsealed report.md is a hard link to any sealed artifact, such as findings.json, inode identity makes this return true; runCampaign therefore skips report recovery and resumes with JSON or another artifact masquerading as the human-facing report. The Python --report-only path has the same hard-link exemption, even though its atomic os.replace writer can safely replace the alias without modifying the sealed inode. The newly added hard-link acceptance is fresh evidence for the previously raised report-validation issue; only treat an actual sealed report.md artifact as reusable and regenerate all aliases.

AGENTS.md reference: sdk/typescript/AGENTS.md:L19-L20

Useful? React with 👍 / 👎.

Copy link
Copy Markdown
Collaborator Author

@codex review

@chatgpt-codex-connector

Copy link
Copy Markdown

Codex Review: Didn't find any major issues. Chef's kiss.

Reviewed commit: 7ac503f82f

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

@chatgpt-codex-connector

Copy link
Copy Markdown

Security review completed. No security issues were found in this pull request.

Reviewed commit: 7ac503f82f

View security finding report

Only the user who started this review can view the report in Codex.

ℹ️ About Codex security reviews in GitHub

This is an experimental Codex feature. Security reviews are triggered when:

  • You comment "@codex security review"
  • A regular code review gets triggered (for example, "@codex review" or when a PR is opened), and you’re opted in so security review runs alongside code review

Once complete, Codex will leave suggestions, or a comment if no findings are found.

@zcrab-oai zcrab-oai left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Draft feedback: narrow the authenticated-resume change before adding unrelated result and warning behavior.

cost?: ScanCost;
error?: string;
warning?: string;
warnings?: string[];

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

[P2] Split warning aggregation from authenticated scan recovery

Can we keep this PR focused on verifying resumed scan artifacts and move warning persistence, checkout-cleanup reporting, and the new warned result field into a separate change? The current patch combines resume authentication, report regeneration, Python/runtime changes, and a new result/receipt shape across roughly 1,700 added lines. Splitting the independent warning behavior would make the security-sensitive recovery path substantially easier to review and test.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

bug Something isn't working

Projects

None yet

2 participants