package com.baiyue.common.event; import java.util.Objects; /** A consumer returns this only after its durable processing transaction commits. */ public record DeliveryAck(String eventId, String payloadHash, Outcome outcome) { public enum Outcome { APPLIED, DUPLICATE, STALE } public DeliveryAck { if (!EventIdentifiers.isSupported(eventId)) throw new IllegalArgumentException("Invalid ACK eventId"); if (payloadHash == null || !payloadHash.matches("sha256:[0-9a-fA-F]{64}")) { throw new IllegalArgumentException("Invalid ACK payloadHash"); } Objects.requireNonNull(outcome, "ACK outcome is required"); } public static DeliveryAck of(EventEnvelope event, Outcome outcome) { return new DeliveryAck(event.eventId(), event.payloadHash(), outcome); } /** HTTP and ApiResponse status must also be checked by the transport. */ public void requireMatches(EventEnvelope sent) { if (!eventId.equals(sent.eventId()) || !payloadHash.equalsIgnoreCase(sent.payloadHash())) { throw new IllegalArgumentException("Consumer ACK does not match the sent event identity and payload"); } EventDeliveryRoute route = EventDeliveryRoute.forEventType(sent.eventType()); if (outcome == Outcome.STALE && !route.acceptsStale()) { throw new IllegalArgumentException("STALE is not an allowed result for " + sent.eventType()); } } }