Repository navigation
[duplicate-code] Duplicate Code Pattern: Repeated redact-or-sanitize payload branch across server log call sites #13967
Copy link
Copy link
Description
Part of duplicate code analysis: #13965
Summary
The same "if this is an enclave-redacted session, produce a digested/opaque payload string; otherwise sanitize and use the raw payload string" branch is repeated near-verbatim at 5 call sites across 3 files, instead of being extracted into a single shared helper (e.g., sanitize.PayloadTextForLog(payload []byte, redact bool) string).
Duplication Details
Pattern: Inline if redactPayload/enclaveSession { RedactedPayloadText(...) } else { SanitizeString(...) } branch
- Severity: Medium
- Occurrences: 5 (across 3 files)
- Locations:
internal/server/http_helpers.go(lines 114-117)internal/server/tool_registry.go(lines 313-318, request args)internal/server/tool_registry.go(lines 336-340, response result — same shape,else if/elsevariant)internal/server/sdk_logging.go(lines 51-58, request parse-failure branch — includes an extra error-redaction line)internal/server/sdk_logging.go(lines 140-148, non-JSON response branch — includes extra truncation logic)
- Code Sample:
// internal/server/http_helpers.go:114-117 sanitizedBody := sanitize.SanitizeString(string(bodyBytes)) if sanitize.ShouldRedactPayload(enclaveSession) { sanitizedBody = sanitize.RedactedPayloadText(bodyBytes) } // internal/server/tool_registry.go:313-318 (near-identical shape, inverted if/else) var sanitizedArgs string if redactPayload { sanitizedArgs = sanitize.RedactedPayloadText(argsJSON) } else { sanitizedArgs = sanitize.SanitizeString(string(argsJSON)) } // internal/server/sdk_logging.go:140-146 (same core branch, plus truncation) if redactPayload { logSDK.Printf(" Raw response: %s", sanitize.RedactedPayloadText(responseBody)) } else { sanitizedResp := sanitize.SanitizeString(string(responseBody)) ... }
Impact Analysis
- Maintainability: This is the core "decide how to render a payload for a log line" decision for the enclave data-leak-prevention feature, restated independently 5 times. Any future refinement (e.g., changing the truncation length, adding a size cap to
SanitizeString, or adjusting the redacted format) requires hunting down and updating every occurrence individually. - Bug Risk: Medium — because each occurrence is hand-written rather than calling a shared function, it's easy for one call site to omit the
ShouldRedactPayloadcheck entirely in future edits (a copy-paste base for a new log line might drop the guard), which would leak private enclave payload content into an exported log artifact — the exact failure mode this redaction subsystem exists to prevent (per the design comment ininternal/sanitize/payload_redaction.go). - Code Bloat: Low-to-medium — ~4-5 lines duplicated per site, ~20+ lines total, plus mental overhead correlating the different variable names (
sanitizedBody,sanitizedArgs,sanitizedResp) to the same underlying pattern.
Refactoring Recommendations
-
Extract a shared "redact-or-sanitize payload text" helper into
internal/sanitize- Extract common functionality to:
internal/sanitize/payload_redaction.go, e.g.:// PayloadTextForLog renders payload for a log line: a stable digest when // redact is true, or the sanitized string otherwise. func PayloadTextForLog(payload []byte, redact bool) string { if redact { return RedactedPayloadText(payload) } return SanitizeString(string(payload)) }
- Update the 3-4 straightforward call sites (
http_helpers.go:114-117,tool_registry.go:313-318,tool_registry.go:336-340, and the non-error branch ofsdk_logging.go:140-148, adapting the truncation logic there to wrap the helper's output) to call this single function. - Estimated effort: ~1-2 hours including updating existing tests that assert on these specific log lines (e.g.,
sdk_logging_test.go,tool_registrytests) to cover the shared helper instead of/in addition to the call sites. - Benefits: Single, testable place enforcing the redaction guard; eliminates the risk of a future call site accidentally omitting the
ShouldRedactPayloadcheck; smaller diffs for future redaction-behavior tweaks.
- Extract common functionality to:
-
Leave the
sdk_logging.go:51-58request-parse-failure branch as a distinct case (not merged)- That branch mixes error redaction and payload redaction together (
RedactErrorForLog(err)+RedactedPayloadText(requestBody)), so it's a compound case; still, once (1) lands, it can call the newPayloadTextForLoghelper for the raw-body portion, reducing it to only the error-specific line as distinct logic.
- That branch mixes error redaction and payload redaction together (
Implementation Checklist
- Review duplication findings
- Prioritize refactoring tasks
- Add
sanitize.PayloadTextForLog(or equivalent) helper - Replace the 5 call sites listed above with calls to the shared helper
- Update/extend existing tests to cover the shared helper and confirm redaction still triggers correctly per call site
- Verify no functionality broken (
make agent-finished)
Parent Issue
See parent analysis report: #13965
Related to #13965
Generated by Duplicate Code Detector · copilot · auto · 76.5 AIC · ⊞ 13.4K · ◷
- expires on Oct 4, 2026, 2:48 AM UTC
Reactions are currently unavailable
Activity
refactor(sanitize): consolidate redact-or-sanitize log helpers
[Repo Assist] perf(server): skip redundant sanitize pass + dedupe red…
Centralize redacted payload log rendering (github#13993)