Payload-owner guard finds its package root from the file; refusals pinned in the decode tests
The guard test counted its package root from the compiled layout and failed under tsx and for a one-file src; it now walks up to the package.json. The browser's non-messagepack refusal and the cache's codec-and-formatter refusal are pinned by message. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
parent
f1e7b36a39
commit
294469e300
4 changed files with 27 additions and 8 deletions
|
|
@ -31,3 +31,9 @@ test("a payload is read by its definition's formatter, a codec's, or as a plain
|
|||
// Without the definition the codec payload is its positional array, which is why a caller that holds one passes it.
|
||||
assert.deepEqual(decodeDocumentPayload(undefined, encode(["a", 1])), ["a", 1]);
|
||||
});
|
||||
|
||||
test("a definition that declares both a codec and a formatter is refused where its payload is read", () => {
|
||||
const both = { ...codec, formatter: formatted.formatter } as typeof codec;
|
||||
assert.throws(() => decodeDocumentPayload(both, encode(["a", 1])), (error: Error) =>
|
||||
error.message === 'CultCache document type "t.codec" declares both a codec and a formatter.');
|
||||
});
|
||||
|
|
|
|||
|
|
@ -982,3 +982,8 @@ test("decodeCultNetPayload reads a payload through the formatter it is given, an
|
|||
assert.deepEqual(decodeCultNetPayload<{ count: number }>(record, formatter), { count: 7 });
|
||||
assert.deepEqual(decodeCultNetPayload<number[]>(record), [7]);
|
||||
});
|
||||
|
||||
test("decodeCultNetPayload refuses a payload that is not messagepack, naming the encoding and not the payload", () => {
|
||||
const record = { schemaId: "t.v0", recordKey: "k", payloadEncoding: "json", payload: encodeWireValue("secret-value") } as unknown as CultNetRawDocumentRecord;
|
||||
assert.throws(() => decodeCultNetPayload(record), (error: Error) => error.message === "Unsupported CultNet document payload 'json'.");
|
||||
});
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
import assert from "node:assert/strict";
|
||||
import { readdirSync, readFileSync } from "node:fs";
|
||||
import { join } from "node:path";
|
||||
import { existsSync, readdirSync, readFileSync } from "node:fs";
|
||||
import { dirname, join } from "node:path";
|
||||
import { fileURLToPath } from "node:url";
|
||||
import test from "node:test";
|
||||
|
||||
|
|
@ -10,7 +10,11 @@ import test from "node:test";
|
|||
// Limits: a text scan. It reads the package's src files for the module specifier and the manifest for the dependency
|
||||
// name. It does not follow a re-export from another package, a specifier assembled at run time, or a hand-written
|
||||
// decoder; the dependency absence is what makes the specifier unresolvable here when the workspace does not hoist it.
|
||||
const root = fileURLToPath(new URL("../../", import.meta.url));
|
||||
// The package root: the nearest directory above this file (compiled or run in place) that holds a package.json.
|
||||
function packageRoot(from: string): string {
|
||||
return existsSync(join(from, "package.json")) ? from : packageRoot(dirname(from));
|
||||
}
|
||||
const root = packageRoot(dirname(fileURLToPath(import.meta.url)));
|
||||
|
||||
function sourceFiles(dir: string): string[] {
|
||||
return readdirSync(dir, { withFileTypes: true }).flatMap((entry) =>
|
||||
|
|
@ -23,7 +27,7 @@ test("no source file imports msgpack and the manifest does not list it", () => {
|
|||
assert.equal(manifest[section]?.["@msgpack/msgpack"], undefined, section);
|
||||
}
|
||||
const files = sourceFiles(join(root, "src"));
|
||||
assert.ok(files.length > 5, "fixture: the scan reads the package's sources");
|
||||
assert.ok(files.length >= 1, "fixture: the scan reads the package's sources");
|
||||
const offenders = files.filter((file) => /@msgpack\/msgpack/.test(readFileSync(file, "utf8")));
|
||||
assert.deepEqual(offenders, []);
|
||||
});
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
import assert from "node:assert/strict";
|
||||
import { readdirSync, readFileSync } from "node:fs";
|
||||
import { join } from "node:path";
|
||||
import { existsSync, readdirSync, readFileSync } from "node:fs";
|
||||
import { dirname, join } from "node:path";
|
||||
import test from "node:test";
|
||||
|
||||
// A document payload is decoded by cultcache-ts alone (decodeDocumentPayload); every other value on a wire goes through
|
||||
|
|
@ -9,7 +9,11 @@ import test from "node:test";
|
|||
// Limits: a text scan. It reads the package's src files for the module specifier and the manifest for the dependency
|
||||
// name. It does not follow a re-export from another package, a specifier assembled at run time, or a hand-written
|
||||
// decoder; the dependency absence is what makes the specifier unresolvable here when the workspace does not hoist it.
|
||||
const root = join(__dirname, "..", "..");
|
||||
// The package root: the nearest directory above this file (compiled or run in place) that holds a package.json.
|
||||
function packageRoot(from: string): string {
|
||||
return existsSync(join(from, "package.json")) ? from : packageRoot(dirname(from));
|
||||
}
|
||||
const root = packageRoot(__dirname);
|
||||
|
||||
function sourceFiles(dir: string): string[] {
|
||||
return readdirSync(dir, { withFileTypes: true }).flatMap((entry) =>
|
||||
|
|
@ -22,7 +26,7 @@ test("no source file imports msgpack and the manifest does not list it", () => {
|
|||
assert.equal(manifest[section]?.["@msgpack/msgpack"], undefined, section);
|
||||
}
|
||||
const files = sourceFiles(join(root, "src"));
|
||||
assert.ok(files.length > 5, "fixture: the scan reads the package's sources");
|
||||
assert.ok(files.length >= 1, "fixture: the scan reads the package's sources");
|
||||
const offenders = files.filter((file) => /@msgpack\/msgpack/.test(readFileSync(file, "utf8")));
|
||||
assert.deepEqual(offenders, []);
|
||||
});
|
||||
|
|
|
|||
Loading…
Reference in a new issue