Files
WRNexusJS/packages/validation/test/contracts.test.ts
T
Clintchiz 586a6db8ff
Quality / quality (ubuntu-latest) (push) Failing after 21s
Quality / quality (windows-latest) (push) Canceled after 0s
release: WRNexusJS 0.8.0
2026-08-02 23:18:51 +05:30

71 lines
2.2 KiB
TypeScript

import { describe, expect, test } from "bun:test";
import { ContractRegistry, checkContractCompatibility, defineEvent, v } from "../src/index.ts";
describe("boundary contract registry", () => {
test("registers typed, deterministic multi-boundary snapshots", () => {
const registry = new ContractRegistry()
.register(
defineEvent({
name: "user.created",
version: 1,
payload: v.object({ id: v.string().uuid() }),
}),
)
.register({
kind: "queue",
name: "email.send",
version: 1,
payload: v.object({ to: v.string().email() }),
});
expect(registry.snapshot().contracts.map((item) => `${item.kind}:${item.name}`)).toEqual([
"pubsub:user.created",
"queue:email.send",
]);
});
test("rejects duplicate identities", () => {
const registry = new ContractRegistry();
const contract = {
kind: "api",
name: "users",
version: 1,
payload: v.object({ id: v.string() }),
} as const;
registry.register(contract);
expect(() => registry.register(contract)).toThrow("Duplicate contract");
});
test("reports breaking fields, types, requirements, rules, and consumers", () => {
const previous = new ContractRegistry()
.register({
kind: "webhook",
name: "invoice.paid",
version: 1,
consumers: ["accounting", "email"],
payload: v.object({
email: v.string().optional(),
count: v.number().min(0),
legacy: v.string(),
}),
})
.snapshot();
const current = new ContractRegistry()
.register({
kind: "webhook",
name: "invoice.paid",
version: 1,
payload: v.object({ email: v.string(), count: v.string().min(2), added: v.string() }),
})
.snapshot();
const issues = checkContractCompatibility(previous, current);
expect(issues.map((issue) => issue.code)).toEqual([
"WRN-CONTRACT-FIELD-REQUIRED",
"WRN-CONTRACT-FIELD-TYPE",
"WRN-CONTRACT-RULE-TIGHTENED",
"WRN-CONTRACT-FIELD-REMOVED",
"WRN-CONTRACT-FIELD-REQUIRED",
]);
expect(issues.every((issue) => issue.consumers.includes("accounting"))).toBe(true);
});
});