LiteBus
Reliable messaging

Reliable Messaging Semantics

Production tier: GA

Deep reference for delivery guarantees, idempotency, and broker behavior in LiteBus v6. For registration and package layout, start with Reliable messaging. For atomic domain + inbox/outbox writes, see Transactional messaging writes.

At-Least-Once

LiteBus durable paths persist before execution (inbox) or before broker publish completes terminal state (outbox). A worker may therefore run the same logical message more than once after crash, lease expiry, or broker redelivery.

Applications must make handlers idempotent or deduplicate using:

  • InboxAcceptMetadata.Idempotency / OutboxEnqueueMetadata.Idempotency (Idempotency.Keyed)
  • Natural keys in domain stores
  • Broker message IDs where consumers support dedup

Inbox Accept vs Execute

StepAPICommitted when
AcceptIInbox.AcceptAsyncRow visible in store (Pending)
ExecutePipelinedInboxProcessor + dispatcherTerminal status after successful dispatch

Accept is durable once the store transaction commits. Execution is at-least-once under lease.

Outbox Enqueue vs Publish

StepAPICommitted when
EnqueueIOutbox.EnqueueAsyncRow in store (often same UoW as domain change)
PublishProcessor + IOutboxDispatcherTerminal Published/Failed/DeadLettered

Transactional outbox: enqueue in the same database transaction as domain entities. EF uses the save-changes interceptor; PostgreSQL uses ITransactionalOutbox with ambient provider or manual bind. See Transactional messaging writes and Domain events and unit of work.

Lease Recovery

Processors lease batches with lease_owner and lease_expires_at. Heartbeat renews leases during long handlers. When lease expires:

  • Another worker may lease the same row
  • Terminal persist uses conditional update (lease_owner match) to avoid overwriting a newer attempt

PostgreSQL and EF Core stores use atomic conditional persist.

Drain Before Stop

Hosted services run IBackgroundService processor loops. On shutdown:

  1. Drain control stops new leases
  2. In-flight dispatches complete (subject to cancellation token policy)
  3. HonorShutdownTokenOnPersist on processor options controls whether cancel aborts terminal persist (default: complete persist)

See Hosted services and Production runbook.

Broker Ingress Ack Policy

BrokerCommit/ack timingFailure before accept
KafkaOffset commit on ackSeek back; no commit
AMQPBasicAck after acceptNack requeue or reject
SQSDelete on ackVisibility timeout extension
AzureComplete/abandon per SDKAbandon for retry

Ingress logs ingress.ack_failed_after_accept when ack fails after successful accept; broker may redeliver (at-least-once).

Schema v1 Greenfield

PostgreSQL inbox and outbox tables use schema version 3; saga uses version 2. Ordered migrations cover older v6 tables. No automatic upgrade exists for LiteBus v5 tables. See Migration Guide v6.

Comparison Table

ConcernIn-process mediatorDurable inbox/outbox
Crash safetyNoneStore + processor
OrderingHandler pipeline orderFIFO-like by created_at; no strict order for ties, retries, or multiple workers
DuplicatesNonePossible; idempotency required
Cross-serviceSingle processStorage + optional broker

Tests

ScenarioLocation
Contract store semanticsLiteBus.Storage.Testing
Concurrent lease / persistPostgreSQL + EF integration tests
Ingress requeueBroker integration tests under LiteBus.Composition.UnitTests

On this page