feat(iios): idempotency ledger on outbound egress (409 on key reuse) (P9)
OutboundService.send is now opt-in idempotent: an explicit idempotencyKey routes the send through IdempotencyService.run (Slice 6), so reusing a key with a different target/payload returns a 409 conflict and a same-key/same-request retry replays the cached command. The inner findUnique early-return stays as a backstop so a FAILED-then-retried send never collides on the command's unique key. Keyless sends keep the old behavior (no ledger row). Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
This commit is contained in:
@@ -12,6 +12,7 @@ import { AiJobService } from './ai/ai.service';
|
||||
import { AiBudgetGuard } from './ai/ai-budget.guard';
|
||||
import { CalendarService } from './calendar/calendar.service';
|
||||
import { OutboundService } from './adapters/outbound.service';
|
||||
import { IdempotencyService } from './idempotency/idempotency.service';
|
||||
import { CapabilityBroker } from './capability/capability.broker';
|
||||
import { CapabilityProviderRegistry } from './capability/capability.registry';
|
||||
import type { PrismaService } from './prisma/prisma.service';
|
||||
@@ -27,7 +28,7 @@ const B: MessagePrincipal = { userId: 'b1', orgId: 'org_B', appId: 'portal-demo'
|
||||
const START = '2026-07-02T10:00:00.000Z';
|
||||
|
||||
const ai = () => new AiJobService(asService, makeFakePorts(), makeFakeInference(), new AiBudgetGuard(asService), actors);
|
||||
const outbound = () => new OutboundService(asService, new CapabilityBroker(makeFakePorts(), new CapabilityProviderRegistry()));
|
||||
const outbound = () => new OutboundService(asService, new CapabilityBroker(makeFakePorts(), new CapabilityProviderRegistry()), new IdempotencyService(asService));
|
||||
const routeSvc = () => new RouteService(asService, new RouteSimulator(asService, new RuleEngine()), outbound(), actors);
|
||||
const cal = () => new CalendarService(asService, makeFakePorts(), actors, ai(), outbound());
|
||||
|
||||
|
||||
Reference in New Issue
Block a user