mirror of
https://github.com/openclaw/openclaw.git
synced 2026-08-12 21:53:00 -06:00
fix(logging): redact Telegram tokens across chunk boundaries (#103861)
This commit is contained in:
@@ -955,6 +955,24 @@ describe("redactSensitiveText", () => {
|
||||
}
|
||||
});
|
||||
|
||||
it("masks Telegram bot tokens that cross bounded-replacement chunk boundaries", () => {
|
||||
const chunkSize = 16_384;
|
||||
const credential = `123456:${"A".repeat(28)}WXYZ`;
|
||||
const cases = [
|
||||
{ token: `bot${credential}`, redacted: "bot123456…WXYZ" },
|
||||
{ token: credential, redacted: "123456…WXYZ" },
|
||||
];
|
||||
|
||||
for (const { token, redacted } of cases) {
|
||||
const tokenStart = chunkSize - 12;
|
||||
const prefix = `${"x".repeat(tokenStart - 1)} `;
|
||||
const suffix = ` ${"y".repeat(chunkSize * 2)}`;
|
||||
expect(redactSensitiveText(`${prefix}${token}${suffix}`, { mode: "tools" })).toBe(
|
||||
`${prefix}${redacted}${suffix}`,
|
||||
);
|
||||
}
|
||||
});
|
||||
|
||||
it("does not corrupt base64 blobs that embed token-prefix shapes", () => {
|
||||
// Tiny-PNG base64 contains a gAAAA run from zero-filled IHDR bytes; pure-base64-alphabet
|
||||
// prefixes must not fire mid-blob or media payloads get mangled.
|
||||
|
||||
+11
-3
@@ -127,12 +127,18 @@ const STANDALONE_ASSIGNMENT_REDACT_PATTERN = String.raw`(^|[\s,;])(?:${STANDALON
|
||||
// data-URL media is never corrupted while tokens in URL paths or assignments still redact.
|
||||
const BASE64_SAFE_TOKEN_BOUNDARY = String.raw`(^|[^A-Za-z0-9])(?<!;base64,[A-Za-z0-9+/=]*)`;
|
||||
const IDENTIFIER_SAFE_TOKEN_BOUNDARY = String.raw`(^|[^A-Za-z0-9_])`;
|
||||
const TELEGRAM_BOT_TOKEN_REDACT_PATTERN = String.raw`\bbot(\d{6,}:[A-Za-z0-9_-]{20,})\b`;
|
||||
const TELEGRAM_TOKEN_REDACT_PATTERN = String.raw`\b(\d{6,}:[A-Za-z0-9_-]{20,})\b`;
|
||||
const SHELL_REFERENCE_PRESERVING_PATTERN_SOURCES = new Set([
|
||||
ENV_ASSIGNMENT_REDACT_PATTERN,
|
||||
ESCAPED_ENV_ASSIGNMENT_REDACT_PATTERN,
|
||||
STANDALONE_ASSIGNMENT_QUOTED_REDACT_PATTERN,
|
||||
STANDALONE_ASSIGNMENT_REDACT_PATTERN,
|
||||
]);
|
||||
const CHUNK_UNSAFE_PATTERN_SOURCES = new Set([
|
||||
TELEGRAM_BOT_TOKEN_REDACT_PATTERN,
|
||||
TELEGRAM_TOKEN_REDACT_PATTERN,
|
||||
]);
|
||||
const shellReferencePreservingPatterns = new WeakSet<RegExp>();
|
||||
// Patterns whose left-context assertions or complete token can cross a chunk boundary must run
|
||||
// against the full string; chunking can invent a `^` boundary or split the secret itself.
|
||||
@@ -251,8 +257,8 @@ const DEFAULT_REDACT_PATTERNS: string[] = [
|
||||
String.raw`(api_org_[A-Za-z0-9]{20,})`,
|
||||
String.raw`(r8_[A-Za-z0-9]{10,})`,
|
||||
// Telegram Bot API URLs embed the token as `/bot<token>/...` (no word-boundary before digits).
|
||||
String.raw`\bbot(\d{6,}:[A-Za-z0-9_-]{20,})\b`,
|
||||
String.raw`\b(\d{6,}:[A-Za-z0-9_-]{20,})\b`,
|
||||
TELEGRAM_BOT_TOKEN_REDACT_PATTERN,
|
||||
TELEGRAM_TOKEN_REDACT_PATTERN,
|
||||
];
|
||||
let defaultResolvedPatterns: RegExp[] | undefined;
|
||||
|
||||
@@ -323,7 +329,9 @@ function parsePattern(raw: RedactPattern): RegExp | null {
|
||||
if (
|
||||
pattern &&
|
||||
typeof raw === "string" &&
|
||||
(raw.startsWith(BASE64_SAFE_TOKEN_BOUNDARY) || raw.startsWith(IDENTIFIER_SAFE_TOKEN_BOUNDARY))
|
||||
(raw.startsWith(BASE64_SAFE_TOKEN_BOUNDARY) ||
|
||||
raw.startsWith(IDENTIFIER_SAFE_TOKEN_BOUNDARY) ||
|
||||
CHUNK_UNSAFE_PATTERN_SOURCES.has(raw))
|
||||
) {
|
||||
chunkUnsafePatterns.add(pattern);
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user