import { describe, expect, it } from "vitest"; import { ContractContributionError, composeContractContributions, type InstalledContractContribution, } from "../../src/contracts/external-contract-runtime.ts"; import { TEST_CONTRACT_CONTRIBUTION } from "../helpers/external-contract-fixture.ts"; function contribution( contributionId: string, http: InstalledContractContribution["http"], ): InstalledContractContribution & Readonly<{ contributionId: string }> { return Object.freeze({ ...TEST_CONTRACT_CONTRIBUTION, contributionId, http: Object.freeze([...http]), }); } function captureContributionError(operation: () => unknown): ContractContributionError { try { operation(); } catch (error) { expect(error).toBeInstanceOf(ContractContributionError); return error as ContractContributionError; } throw new Error("Expected contract composition to fail."); } describe("external contract contribution composition", () => { it("allows one feature to install multiple uniquely identified contributions", () => { const operations = TEST_CONTRACT_CONTRIBUTION.http; const composed = composeContractContributions([ contribution("test-read-contracts", operations.slice(0, 2)), contribution("test-command-contracts", operations.slice(2)), ]); expect(composed.contributions).toHaveLength(2); expect(composed.httpByOperationId.size).toBe(3); }); it("rejects duplicate contribution identities even across different feature entries", () => { const first = contribution( "test-contracts", TEST_CONTRACT_CONTRIBUTION.http.slice(0, 1), ); const second = contribution( "test-contracts", TEST_CONTRACT_CONTRIBUTION.http.slice(1), ); const error = captureContributionError(() => composeContractContributions([first, second]), ); expect(error.reason).toContain("duplicate contributionId"); }); it("maps malformed source values to the closed composition error", () => { const malformed = { ...contribution("malformed-source", []), source: null, } as unknown as InstalledContractContribution; const error = captureContributionError(() => composeContractContributions([malformed]), ); expect(error.reason).toContain("source"); }); it("rejects method and body vocabulary outside the runtime protocol", () => { const installed = TEST_CONTRACT_CONTRIBUTION.http[0]!; const malformedOperation = { ...installed, contract: { ...installed.contract, method: "TRACE" }, } as unknown as InstalledContractContribution["http"][number]; const error = captureContributionError(() => composeContractContributions([ contribution("invalid-http-vocabulary", [malformedOperation]), ]), ); expect(error.reason).toContain("method"); }); });