fix(secrets): strip control characters from secret input (#96444)

* fix(secrets): strip control characters from secret input

* chore: retrigger PR checks

* fix(web-content): strip controls from provider secrets

---------

Co-authored-by: lin-hongkuan <lin-hongkuan@users.noreply.github.com>
(cherry picked from commit bc7f0f1223)
This commit is contained in:
lin-hongkuan
2026-06-30 01:51:08 +08:00
committed by Dallin Romney
parent 1de19812c4
commit cff2bd8030
4 changed files with 26 additions and 2 deletions
@@ -30,6 +30,15 @@ describe("readWebProviderEnvValue", () => {
it("normalizes env credentials before returning them", () => {
expect(readWebProviderEnvValue(["API_KEY"], { API_KEY: " key\r\nvalue🙂 " })).toBe("keyvalue");
});
it("strips embedded controls from env credentials while preserving ordinary spaces", () => {
expect(readWebProviderEnvValue(["API_KEY"], { API_KEY: " sk-\u0000ab\tc\u007f\u0085 " })).toBe(
"sk-abc",
);
expect(readWebProviderEnvValue(["API_KEY"], { API_KEY: " Bearer token value " })).toBe(
"Bearer token value",
);
});
});
describe("hasWebProviderEntryCredential", () => {
@@ -56,7 +56,12 @@ function normalizeSecretInput(value: unknown): string {
let latin1Only = "";
for (const char of collapsed) {
const codePoint = char.codePointAt(0);
if (typeof codePoint === "number" && codePoint <= 0xff) {
const isControl =
typeof codePoint === "number" &&
((codePoint >= 0x00 && codePoint <= 0x1f) ||
codePoint === 0x7f ||
(codePoint >= 0x80 && codePoint <= 0x9f));
if (typeof codePoint === "number" && codePoint <= 0xff && !isControl) {
latin1Only += char;
}
}
+5
View File
@@ -14,6 +14,11 @@ describe("normalizeSecretInput", () => {
expect(normalizeSecretInput(" sk-\r\nabc\n123 ")).toBe("sk-abc123");
});
it("strips embedded control characters while preserving ordinary spaces", () => {
expect(normalizeSecretInput(" sk-\u0000ab\tc\u007f\u0085 ")).toBe("sk-abc");
expect(normalizeSecretInput(" Bearer token value ")).toBe("Bearer token value");
});
it("drops non-Latin1 code points that can break HTTP ByteString headers", () => {
// U+0417 (Cyrillic З) and U+2502 (box drawing │) are > 255.
expect(normalizeSecretInput("key-\u0417\u2502-token")).toBe("key--token");
+6 -1
View File
@@ -25,7 +25,12 @@ export function normalizeSecretInput(value: unknown): string {
const chars: string[] = [];
for (const char of collapsed) {
const codePoint = char.codePointAt(0);
if (typeof codePoint === "number" && codePoint <= 0xff) {
const isControl =
typeof codePoint === "number" &&
((codePoint >= 0x00 && codePoint <= 0x1f) ||
codePoint === 0x7f ||
(codePoint >= 0x80 && codePoint <= 0x9f));
if (typeof codePoint === "number" && codePoint <= 0xff && !isControl) {
chars.push(char);
}
}