Skip to content

fix: sanitize secret-bearing data before writing GitHub step summaries - #50777

Merged
pelikhan merged 9 commits into
mainfrom
copilot/sanitize-secret-bearing-data
Aug 6, 2026
Merged

pelikhan merged 9 commits into
mainfrom
copilot/sanitize-secret-bearing-data

Conversation

Copilot AI commented Aug 6, 2026 •

Copy link
Copy Markdown
Contributor

Several paths serialized agent-controlled data directly into $GITHUB_STEP_SUMMARY — tool inputs/outputs via includeDetailedParameters: true, and raw message.body, message.data, and full JSON.stringify(message) in safe-output summaries. Actions ::add-mask:: processing does not reliably scrub step-summary file contents, so secrets could persist in cleartext.

Changes

parse_copilot_log.cjs

  • Disable includeDetailedParameters — tool call rendering now shows only tool name, command summary, duration, and status; raw parameter JSON is never written to the summary

safe_output_summary.cjs

  • Remove body preview (message.body / result.body) from success and fallback paths
  • Remove message.data block (arbitrary structured agent output)
  • Remove JSON.stringify(message, null, 2) from the error path
  • Retain only scalar allowlisted fields: title, labels, url, repo#number, secrecy, integrity

Tests

  • Update expectations broken by the above removals
  • Add sentinel secret exclusion suite asserting SUPERSECRETVALUE_xK9mQ2wR is absent from generated markdown across: message.body, result.body, message.data, error path, multiline strings, URL-embedded values, and base64-encoded values

- parse_copilot_log.cjs: disable includeDetailedParameters to stop rendering
  raw tool inputs/outputs in step summaries
- safe_output_summary.cjs: remove body preview (message.body/result.body),
  message.data rendering, and raw JSON.stringify(message) from error path
  to prevent secret leakage into step summaries
- Update tests to reflect new security-safe behavior and add sentinel
  secret exclusion tests covering body, data, error, multiline, URL, and
  base64-encoded shapes

Co-authored-by: pelikhan <4175913+pelikhan@users.noreply.github.com>
Copilot AI changed the title [WIP] Sanitize secret-bearing data in GitHub step summaries fix: sanitize secret-bearing data before writing GitHub step summaries Aug 6, 2026
Copilot AI requested a review from pelikhan August 6, 2026 05:44
@pelikhan
pelikhan marked this pull request as ready for review August 6, 2026 05:45
Copilot AI balanced review requested due to automatic review settings August 6, 2026 05:45

Copilot AI 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.

🟡 Changes recommended

Raw tool outputs, input-derived summaries, and exception messages can still expose secrets.

Once you've addressed the issues Copilot identified, you can request another Copilot review.

This review doesn't count toward merge requirements. Sign up for the private preview to control whether Copilot approvals count.

Pull request overview

This PR reduces secret exposure in GitHub step summaries.

Changes:

  • Hides detailed tool parameters.
  • Removes raw safe-output bodies, data, and message details.
  • Adds secret-exclusion tests.
File summaries
File Description
parse_copilot_log.cjs Disables detailed tool parameters.
parse_copilot_log.test.cjs Updates parser expectations.
safe_output_summary.cjs Removes unsafe payload rendering.
safe_output_summary.test.cjs Adds secret-exclusion coverage.
Review details
  • Files reviewed: 4/4 changed files
  • Comments generated: 2
  • Review effort level: Balanced

We're testing this review assessment. Please use 👍 or 👎 to tell us if it's correct.

}
} else if (error) {
// Show error information
// Show error information (raw message content is omitted to prevent secret leakage)

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

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

Fixed. The error path now renders only an allowlisted error code — the leading ERR_* / E0xx prefix when it matches a code exported from error_codes.cjs, otherwise UNCLASSIFIED — followed by a pointer to the job logs. Raw exception text is never written to the summary.

Added sentinel tests that place the secret directly in error, for both a classified (ERR_API: ... token <SENTINEL>) and an unclassified (Handler failed: <SENTINEL>) message, and updated the existing tests that asserted on raw error text.

// Generate conversation markdown using shared function
const conversationResult = generateConversationMarkdown(canonicalLogEntries, {
formatToolCallback: (toolUse, toolResult) => formatToolUse(toolUse, toolResult, { includeDetailedParameters: true }),
formatToolCallback: (toolUse, toolResult) => formatToolUse(toolUse, toolResult, { includeDetailedParameters: false }),

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

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

You're right that disabling includeDetailedParameters alone doesn't close this — and the gap is actually wider than formatToolUse: the primary step-summary path in log_parser_bootstrap.cjs is generateCopilotCliStyleSummary, not the formatToolUse markdown (which is only used on the fallback path). That renderer also emits commands, result previews, and agent text, so a summary-safe mode in formatToolUse would have left the main path leaking.

I didn't strip tool inputs/outputs from the rendering, because reproducing them is the point of the agent log summary — removing them would make run triage impossible while still not covering agent-authored text, which can quote a secret just as easily. Instead the redaction is applied at the sink: a shared redactStepSummaryContent helper in redact_secrets.cjs runs the same built-in credential patterns already used for artifact redaction over the markdown immediately before core.summary.addRaw, on the structured path, the fallback path, and the Claude startup-diagnostics path, plus the safe-output summary writer (whose title/label/URL fields are agent-controlled).

Sentinel tests added in log_parser_bootstrap.test.cjs cover a credential in a tool input (Bash command) and in a tool output (tool_result content), on both the structured and fallback paths, asserting the value is replaced by ***REDACTED***.

One limitation worth flagging: this covers credential-shaped values, not workflow-configured secret values, because GH_AW_SECRET_NAMES / SECRET_* are only wired into the dedicated redaction step. Passing those into the log-parser and safe-outputs steps is a compiler change with its own exposure trade-off, so I left it out of this PR.

@github-actions

github-actions Bot commented Aug 6, 2026

Copy link
Copy Markdown
Contributor

Warning

Threat Detection Engine Failure — The analysis engine could not complete. This is a tooling failure, not a security finding.

What happened

The threat detection engine failed to produce results.

Review the workflow run logs for details.

🚀 This PR looks great! You're addressing a real security vulnerability — preventing secrets from leaking into GitHub Actions step summaries. The approach is sound:

  • Clean separation: Disabling includeDetailedParameters and removing body/data fields from summaries removes the attack surface for credential exposure.
  • Comprehensive tests: The sentinel secret exclusion suite is excellent — it verifies the fix works across multiline strings, URL-encoded values, and base64-encoded payloads, not just the happy path.
  • Minimal surface: Changes are focused on the two modules responsible for summary output, with no collateral damage.

This is ready for review and merge. Well done! 👍

Generated by ✅ Contribution Check · auto · 53.8 AIC · ⊞ 8.7K · ◷

@pelikhan

pelikhan commented Aug 6, 2026

Copy link
Copy Markdown
Collaborator

@copilot run pr-finisher skill

Copilot AI and others added 4 commits August 6, 2026 06:14
…mmaries

Co-authored-by: pelikhan <4175913+pelikhan@users.noreply.github.com>
Co-authored-by: pelikhan <4175913+pelikhan@users.noreply.github.com>
Co-authored-by: pelikhan <4175913+pelikhan@users.noreply.github.com>
Co-authored-by: pelikhan <4175913+pelikhan@users.noreply.github.com>
@pelikhan
pelikhan merged commit 31f5463 into main Aug 6, 2026
1 check passed
@pelikhan
pelikhan deleted the copilot/sanitize-secret-bearing-data branch August 6, 2026 06:34
@github-actions

github-actions Bot commented Aug 7, 2026

Copy link
Copy Markdown
Contributor

🎉 This pull request is included in a new release.

Release: v0.86.0

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.

Sanitize secret-bearing data before writing GitHub step summaries

3 participants