import { describe, expect, it } from "vitest"; import { BOUNDED_POLLING_CEILINGS, assertBoundedPollOperation, definePollLeasePolicy, type BoundedPollOperationContract, } from "../../../src/application/policies/bounded-polling.ts"; const input = { operationId: "GET_JOB_STATUS", owner: "reference-job", minimumIntervalMs: 5_000, successIntervalMs: 10_000, maxIntervalMs: 60_000, maxAttempts: 5, maxElapsedMs: 120_000, maxResponseBytes: 16_384, visibility: "VISIBLE_ONLY", fallbackReason: "CONVERGENCE", terminalStates: ["COMPLETED", "FAILED"], } as const; describe("bounded polling policy", () => { it("copies and freezes a finite immutable lease", () => { const terminalStates = ["COMPLETED", "FAILED"]; const policy = definePollLeasePolicy({ ...input, terminalStates, }); terminalStates.push("CANCELLED"); expect(policy.terminalStates).toEqual(["COMPLETED", "FAILED"]); expect(Object.isFrozen(policy)).toBe(true); expect(Object.isFrozen(policy.terminalStates)).toBe(true); }); it("rejects push-like cadence and unbounded convergence", () => { expect(() => definePollLeasePolicy({ ...input, minimumIntervalMs: 4_999, }), ).toThrow(TypeError); expect(() => definePollLeasePolicy({ ...input, terminalStates: [], }), ).toThrow(TypeError); expect(() => definePollLeasePolicy({ ...input, maxAttempts: 121, }), ).toThrow(TypeError); }); it("admits only a one-request terminal replay-safe REST query", () => { const policy = definePollLeasePolicy(input); const operation: BoundedPollOperationContract = { operationId: "GET_JOB_STATUS", contractVersion: 2, protocol: "REST", semantics: "QUERY", method: "GET", replayPolicy: "SAFE", retry: "never", maxResponseBytes: 16_384, transportMaxAttempts: 1, authRecoveryCount: 0, maxCumulativeSleepMs: 0, serverStream: false, }; expect(() => assertBoundedPollOperation(policy, operation), ).not.toThrow(); expect(() => assertBoundedPollOperation(policy, { ...operation, transportMaxAttempts: 2 as 1, }), ).toThrow(TypeError); expect(() => assertBoundedPollOperation(policy, { ...operation, maxResponseBytes: 8_192, }), ).not.toThrow(); expect(() => assertBoundedPollOperation(policy, { ...operation, maxResponseBytes: 0, }), ).toThrow(TypeError); expect(() => assertBoundedPollOperation(policy, { ...operation, maxResponseBytes: BOUNDED_POLLING_CEILINGS.maxResponseBytes + 1, }), ).toThrow(TypeError); }); });