← Files DataARCHIVED FILE
tests/data-app-publication-snapshot-streams.test.mjs
11.2 KB · Sep 30, 2026 · 23:19 UTC
import assert from "node:assert/strict";
import test from "node:test";
import { assertNoPublicationSecrets } from "../skills/publish-artifact-to-sites/scripts/publication-secrets.mjs";
import {
createInlineDataScanner,
createJsonMetadataScanner,
createLiteralScanner,
MAX_DEPTH,
TEXT_WINDOW,
} from "../skills/publish-artifact-to-sites/scripts/publication-scan-streams.mjs";
const disclosure = /synthetic credential rejected/u;
const reject = () => { throw new Error("synthetic credential rejected"); };
const limit = () => { throw new Error("depth limit"); };
const credentialKey = (key, scope) => key === "apikey" || (scope !== "rows" && /^(?:token|secret)$/u.test(key));
const credential = "sk-proj-" + "a".repeat(24);
function harness({ inline = true, ...options } = {}) {
const stats = { maxWrite: 0, decoded: 0, assets: 0, maxDepth: 0 };
const createTextScanner = () => {
const scanner = createLiteralScanner(reject);
return {
write(text) { stats.maxWrite = Math.max(stats.maxWrite, text.length); scanner.write(text); },
finish() { scanner.finish(); },
};
};
const common = { createTextScanner, credentialKey, reject, limit, depthChanged: (depth) => { stats.maxDepth = Math.max(stats.maxDepth, depth); } };
const createInline = () => createInlineDataScanner({
createTextScanner,
createJsonScanner: () => createJsonMetadataScanner(common),
decoded: (units) => { stats.decoded += units; },
inlineAsset: () => { stats.assets += 1; },
});
return {
stats,
parser: createJsonMetadataScanner({ ...common, createTextScanner: inline ? createInline : createTextScanner, rootScope: "snapshot", scanKeys: true, ...options }),
inline: createInline(),
};
}
function scan(json, chunkSize = TEXT_WINDOW, options) {
const { parser, stats } = harness(options);
for (let index = 0; index < json.length; index += chunkSize) parser.write(json.slice(index, index + chunkSize));
parser.finish();
return stats;
}
test("only exact snapshot query rows and their descendants permit generic analytical token fields", () => {
const allowed = [
'{"queries":{"q":{"rows":[{"token":"metric","secret":"category","nested":[{"token":"value"}]}]}}}',
'{"qu\\u0065ries":{"q":{"r\\u006fws":[{"to\\u006ben":"metric"}]}}}',
'{"queries":{"q":{"rows":[{"token":"metric"}]}},"queries":{}}',
'{"queries":{"q":{"rows":[{"source":{"token":"category"}}],"rows":[]}}}',
];
for (const json of allowed) assert.doesNotThrow(() => scan(json, 1));
const rejected = [
'{"queries":{"q":{"rows":[{"api_key":"value"}]}}}',
'{"queries":{"q":{"rows":[{"token":"metric"}],"source":{"token":"credential"}}}}',
'{"queries":{"q":{"rows":{"token":"credential"}}}}',
'{"queries":{"q":{"r-o-w-s":[{"token":"credential"}]}}}',
'{"Queries":{"q":{"rows":[{"token":"credential"}]}}}',
'{"queries":[{"rows":[{"token":"credential"}]}]}',
'{"queries":{"q":[{"rows":[{"token":"credential"}]}]}}',
'{"other":{"queries":{"q":{"rows":[{"token":"credential"}]}}}}',
'{"queries":{"q":{"metadata":{"rows":[{"token":"credential"}]}}}}',
'{"queries":{"q":{"rows":[],"token":"credential"}}}',
'{"queries":{"q":{"rows":[]}},"token":"credential"}',
];
for (const json of rejected) assert.throws(() => scan(json, 3), disclosure);
});
test("duplicate ancestor metadata and escaped key/value literals remain inspected", () => {
const escaped = credential.replace("s", "\\u0073");
const rejected = [
'{"source":{"token":"credential"},"source":{}}',
'{"queries":{"q":{"source":{"api_key":"credential"},"source":{}}}}',
'{"source":[{"token":"credential"}],"source":null}',
'{"sour\\u0063e":{"token":"credential"},"source":{}}',
`{"source":{"${escaped}":0},"source":{}}`,
`{"source":{"x":"${escaped}"},"source":{}}`,
`{"queries":{"q":{"rows":[{"${escaped}":0}]}}}`,
];
for (const json of rejected) assert.throws(() => scan(json, 1), disclosure);
});
test("optional snapshot scope and key scanning leave default metadata semantics unchanged", () => {
const json = '{"queries":{"q":{"rows":[{"token":"category"}]}}}';
assert.doesNotThrow(() => scan(json));
assert.throws(() => scan(json, 7, { rootScope: "metadata", scanKeys: false }), disclosure);
assert.doesNotThrow(() => scan(`{"${credential}":0}`, 7, { rootScope: "metadata", scanKeys: false }));
assert.throws(() => scan(`{"${credential}":0}`), disclosure);
});
test("invalid JSON does not acquire decoded metadata interpretation", () => {
const secret = '{"source":{"api_key":"credential"},"source":{}';
for (const suffix of ["", ',"bad":01}', ',"bad":1e+}', ',"bad":"\\x41"}', "}{}", ",}"]) {
const json = secret + suffix;
assert.throws(() => JSON.parse(json), SyntaxError);
assert.doesNotThrow(() => scan(json, 2));
}
assert.throws(() => scan('{"x":'.repeat(MAX_DEPTH + 1) + "0" + "}".repeat(MAX_DEPTH + 1)), /depth limit/u);
});
const dataUrl = (text, base64, mime = "text/javascript") => base64
? `data:${mime};base64,${Buffer.from(text).toString("base64")}`
: `data:${mime},${Array.from(Buffer.from(text), (byte) => `%${byte.toString(16).padStart(2, "0")}`).join("")}`;
test("JSON-escaped inline headers in overwritten values and keys receive one complete decode layer", () => {
for (const base64 of [true, false]) {
const uri = dataUrl(credential, base64).replace("data", "\\u0064ata");
for (const json of [`{"x":"${uri}","x":""}`, `{"${uri}":0}`]) {
for (const chunk of [1, 2, 3, 7, TEXT_WINDOW]) assert.throws(() => scan(json, chunk), disclosure);
}
const metadataUri = dataUrl('{"to\\u006ben":"credential"}', base64, "application/json").replace("data", "\\u0064ata");
assert.throws(() => scan(`{"x":"${metadataUri}","x":""}`, 1), disclosure);
}
});
test("streamed inline payloads preserve percent UTF-8, base64 quanta, headers and MIME behavior", () => {
const data = "safe λ雪😀 " + "x".repeat(TEXT_WINDOW * 2 + 1);
for (const base64 of [true, false]) {
for (const mime of ["text/javascript", "text/ecmascript", "text/plain", "text/html", "text/css", "application/javascript", "application/ecmascript", "application/json", "image/svg+xml"]) {
const uri = dataUrl(data, base64, mime).replace("data:", "DATA:").replace(mime, `${mime};charset=utf-8`);
const result = scan(JSON.stringify({ x: uri }), 17);
assert.equal(result.assets, 1);
assert.equal(result.decoded, data.length);
assert.ok(result.maxWrite <= TEXT_WINDOW + 1);
}
}
});
test("late malformed inline payloads do not activate a partially decoded credential", () => {
for (const base64 of [true, false]) {
const uri = dataUrl(credential, base64);
const invalidSuffixes = base64 ? ["?", "===", "=A", "_"] : ["%", "%A", "%GG", "%C0%AF", "%E2"];
for (const suffix of invalidSuffixes) {
// These have no raw literal credential; only a valid decoded URI can reject.
const { inline, stats } = harness();
for (const character of uri + suffix) inline.write(character);
assert.doesNotThrow(() => inline.finish());
assert.equal(stats.assets, 0);
}
}
});
test("inline terminators, malformed headers and empty payloads match existing URL boundaries", () => {
const safe = dataUrl("safe", true);
const bad = dataUrl(credential, true);
for (const separator of [" ", "\n", '"', "'", "<", ">", "`", "#", ")"]) {
assert.throws(() => {
const { inline } = harness();
for (const character of safe + separator + bad) inline.write(character);
inline.finish();
}, disclosure);
}
for (const prefix of ["xdata:", "data:application/octet-stream;", "data:text/plain;charset=;", "data:text/plain;unknown=foo;"]) {
const { inline, stats } = harness();
inline.write(prefix + "base64," + Buffer.from(credential).toString("base64"));
assert.doesNotThrow(() => inline.finish());
assert.equal(stats.assets, 0);
}
assert.equal(scan('{"x":"data:text/plain;base64,"}').assets, 0);
});
test("arbitrary charset and key lengths remain bounded without dropping a later credential", () => {
const long = "x".repeat(TEXT_WINDOW * 3);
const uri = `data:text/plain;charset=${long};base64,${Buffer.from(credential).toString("base64")}`;
assert.throws(() => scan(JSON.stringify({ x: uri }), 11), disclosure);
assert.throws(() => scan(JSON.stringify({ [long + " " + credential]: 0 }), 11), disclosure);
const stats = scan(JSON.stringify({ [long]: long }), 11);
assert.ok(stats.maxWrite <= TEXT_WINDOW + 1);
});
test("raw snapshot adapter matches established inline scanning for Unicode headers and malformed payloads", () => {
const base64 = Buffer.from(credential).toString("base64");
const percent = Array.from(Buffer.from(credential), byte => `%${byte.toString(16).padStart(2, "0")}`).join("");
const cases = [
...["utf-8", "UTF_8", "ſ", "K", "-"].map(charset => `data:text/plain;charset=${charset};base64,${base64}`),
`data:text/javaſcript;base64,${base64}`,
`DATA:TEXT/PLAIN;CHARSET=UTF-8;BASE64,${base64}`,
...["", "=", "==", "===", "=A", "_", "?", ")"].map(suffix => `data:text/plain;base64,${base64}${suffix}`),
...["", "%", "%A", "%GG", "%E2", "%E2x", "%C0%AF", "%00", "%EF%BB%BF", "%F0%9F%98%80"].map(suffix => `data:text/plain,${percent}${suffix}`),
...["", " ", "a.b", "/", "a;", "λ"].map(charset => `data:text/plain;charset=${charset};base64,${base64}`),
`prefixdata:text/plain;base64,${base64}`,
`data:application/json;base64,${Buffer.from('{"to\\u006ben":"inert"}').toString("base64")}`,
`data:application/json;base64,${Buffer.from('{"to\\u006ben":"inert",}').toString("base64")}`,
];
const result = input => {
try { assertNoPublicationSecrets({ html: "", seedSnapshot: {}, initialPresentation: {}, ...input }); return "accepted"; }
catch (error) {
assert.match(error.message, /Publication contains a possible credential/u);
return "rejected";
}
};
for (const uri of cases) {
const snapshotText = `{"x":${JSON.stringify(uri).replace(/data/giu, "\\u0064ata")},"x":""}`;
assert.equal(result({ snapshotText, seedSnapshot: JSON.parse(snapshotText) }), result({ html: uri }));
assert.equal(result({ snapshotBytes: Buffer.from(snapshotText), seedSnapshot: JSON.parse(snapshotText) }), result({ html: uri }));
}
});
test("byte snapshot scans carry UTF-8 and escaped duplicate metadata across bounded decode windows", () => {
const prefix = '{"padding":"' + "a".repeat(TEXT_WINDOW - 13) + '🧪",';
for (const ending of [
'"api\\u005fkey":"inert-test-value","api_key":""}',
'"source":{"token":"inert-test-value"},"source":{}}',
'"overwritten":"\\u0064ata:text/plain,sk-proj-' + "a".repeat(24) + '","overwritten":""}',
]) {
const source = prefix + ending;
assert.throws(() => assertNoPublicationSecrets({ html: "", snapshotBytes: Buffer.from(source), seedSnapshot: JSON.parse(source) }),
/Publication contains a possible credential/u);
}
const source = prefix + '"queries":{"q":{"rows":[{"token":"metric"}]}}}';
const result = assertNoPublicationSecrets({ html: "", snapshotBytes: Buffer.from(source), seedSnapshot: JSON.parse(source) });
assert.equal(result.complete, true);
assert.ok(result.maximumTextWindowUnits <= 1024 * 1024);
assert.throws(() => assertNoPublicationSecrets({ html: "", snapshotBytes: Buffer.from([123, 34, 120, 34, 58, 34, 0xc3, 34, 125]) }),
/valid UTF-8 JSON/u);
});
SHA-256: 7925ce55d9903d115e6db78ca8818af3f2ec3c9630dd7618ceedd15d05716e32