# Outbox

Publishes events to other systems, such as Kafka, NATS or SQS, as integration events.

```ts
const TodoOutbox = Outbox.make({
  name: "todo-outbox",
  aggregates: [Todo],
  messages: {
    TodoCreated: ({ title }) => ({ type: "todo.created.v1", payload: { title } })
  },
  publish: (messages) => producer.send(messages)
})


const Publishing = Outbox.layer([TodoOutbox])
```

An outbox is a view model: it reads the store from its checkpoint, so it publishes what was stored while the process was down, and nothing is lost between storing an event and publishing it. Delivery is at least once. After a crash, events published since the last checkpoint are published again, so consumers deduplicate on [Message.id](https://effect-cqrs.dambox.ch/reference/api/outbox/#message), which stays the same.

Messages are published in batches of up to `batchSize`. A batch goes out when it is full or `linger` after its first message, and the checkpoint never moves past a message that wasn’t published. A failed batch is retried, in order, until it succeeds.

## Classes

### OutboxError

Defined in: [src/Outbox.ts:83](https://github.com/davidnussio/effect-cqrs/blob/9d66af7141782f3f89655e6868abe3f141c97632/src/Outbox.ts#L83)

Publishing failed, which the outbox retries.

#### Extends

* `object` & `YieldableError`<`this`>

#### Constructors

##### Constructor

> **new OutboxError**(…`args`): [`OutboxError`](https://effect-cqrs.dambox.ch/reference/api/outbox/#outboxerror)

Defined in: node_modules/.pnpm/effect\@4.0.6/node_modules/effect/dist/Schema.d.ts:10979

###### Parameters

###### args

…\[`props`: `object`, `options?`: `MakeOptions`]

###### Returns

[`OutboxError`](https://effect-cqrs.dambox.ch/reference/api/outbox/#outboxerror)

###### Inherited from

`Schema.TaggedError<OutboxError>()("OutboxError", { outbox: Schema.String, cause: Schema.Defect() }).constructor`

#### Properties

##### cause

> **cause**: `unknown`

Defined in: [src/Outbox.ts:85](https://github.com/davidnussio/effect-cqrs/blob/9d66af7141782f3f89655e6868abe3f141c97632/src/Outbox.ts#L85)

###### Inherited from

`Schema.TaggedError<OutboxError>()("OutboxError", { outbox: Schema.String, cause: Schema.Defect() }).cause`

##### outbox

> `readonly` **outbox**: `string` = `Schema.String`

Defined in: [src/Outbox.ts:84](https://github.com/davidnussio/effect-cqrs/blob/9d66af7141782f3f89655e6868abe3f141c97632/src/Outbox.ts#L84)

###### Inherited from

`Schema.TaggedError<OutboxError>()("OutboxError", { outbox: Schema.String, cause: Schema.Defect() }).outbox`

***

### Outboxes

Defined in: [src/Outbox.ts:142](https://github.com/davidnussio/effect-cqrs/blob/9d66af7141782f3f89655e6868abe3f141c97632/src/Outbox.ts#L142)

#### Extends

* `Shape`<`"effect-cqrs/Outboxes"`, { `status`: `Effect`\<readonly [`Status`](https://effect-cqrs.dambox.ch/reference/api/viewmodel/#status)\[]>; `published`(`position?`): `Effect`<`void`, [`EventStoreError`](https://effect-cqrs.dambox.ch/reference/api/eventstore/#eventstoreerror) | [`OutboxError`](https://effect-cqrs.dambox.ch/reference/api/outbox/#outboxerror)>; }, `this`>

#### Constructors

##### Constructor

> **new Outboxes**(`_`): [`Outboxes`](https://effect-cqrs.dambox.ch/reference/api/outbox/#outboxes)

Defined in: node_modules/.pnpm/effect\@4.0.6/node_modules/effect/dist/Context.d.ts:121

###### Parameters

###### \_

`never`

###### Returns

[`Outboxes`](https://effect-cqrs.dambox.ch/reference/api/outbox/#outboxes)

###### Inherited from

Context.Service\<Outboxes, { /\*\* \* Waits until every event up to \`position\`, by default the latest, is \* published. Mostly for tests. \*/ published(position?: number): Effect.Effect\<void, EventStoreError | OutboxError> /\*\* Where each outbox is, and the failure it is retrying, see \`ViewModel.Status\`. \*/ readonly status: Effect.Effect\<ReadonlyArray\<ViewModel.Status>> }>()(“effect-cqrs/Outboxes”).constructor

## Interfaces

### Mapped

Defined in: [src/Outbox.ts:57](https://github.com/davidnussio/effect-cqrs/blob/9d66af7141782f3f89655e6868abe3f141c97632/src/Outbox.ts#L57)

What a mapping makes of an event. `undefined` publishes nothing for it.

#### Properties

##### payload

> `readonly` **payload**: `unknown`

Defined in: [src/Outbox.ts:59](https://github.com/davidnussio/effect-cqrs/blob/9d66af7141782f3f89655e6868abe3f141c97632/src/Outbox.ts#L59)

##### type

> `readonly` **type**: `string`

Defined in: [src/Outbox.ts:58](https://github.com/davidnussio/effect-cqrs/blob/9d66af7141782f3f89655e6868abe3f141c97632/src/Outbox.ts#L58)

***

### Message

Defined in: [src/Outbox.ts:40](https://github.com/davidnussio/effect-cqrs/blob/9d66af7141782f3f89655e6868abe3f141c97632/src/Outbox.ts#L40)

An integration event, what a publisher sends.

#### Properties

##### aggregateId

> `readonly` **aggregateId**: `string`

Defined in: [src/Outbox.ts:46](https://github.com/davidnussio/effect-cqrs/blob/9d66af7141782f3f89655e6868abe3f141c97632/src/Outbox.ts#L46)

##### aggregateName

> `readonly` **aggregateName**: `string`

Defined in: [src/Outbox.ts:45](https://github.com/davidnussio/effect-cqrs/blob/9d66af7141782f3f89655e6868abe3f141c97632/src/Outbox.ts#L45)

##### causationId

> `readonly` **causationId**: `string` | `null`

Defined in: [src/Outbox.ts:53](https://github.com/davidnussio/effect-cqrs/blob/9d66af7141782f3f89655e6868abe3f141c97632/src/Outbox.ts#L53)

##### correlationId

> `readonly` **correlationId**: `string` | `null`

Defined in: [src/Outbox.ts:52](https://github.com/davidnussio/effect-cqrs/blob/9d66af7141782f3f89655e6868abe3f141c97632/src/Outbox.ts#L52)

##### id

> `readonly` **id**: `string`

Defined in: [src/Outbox.ts:42](https://github.com/davidnussio/effect-cqrs/blob/9d66af7141782f3f89655e6868abe3f141c97632/src/Outbox.ts#L42)

The id of the event it comes from, the same however often it is published: `todo/a@1`.

##### payload

> `readonly` **payload**: `unknown`

Defined in: [src/Outbox.ts:44](https://github.com/davidnussio/effect-cqrs/blob/9d66af7141782f3f89655e6868abe3f141c97632/src/Outbox.ts#L44)

##### position

> `readonly` **position**: `number`

Defined in: [src/Outbox.ts:50](https://github.com/davidnussio/effect-cqrs/blob/9d66af7141782f3f89655e6868abe3f141c97632/src/Outbox.ts#L50)

The position of the event in the store.

##### timestamp

> `readonly` **timestamp**: `Utc`

Defined in: [src/Outbox.ts:51](https://github.com/davidnussio/effect-cqrs/blob/9d66af7141782f3f89655e6868abe3f141c97632/src/Outbox.ts#L51)

##### type

> `readonly` **type**: `string`

Defined in: [src/Outbox.ts:43](https://github.com/davidnussio/effect-cqrs/blob/9d66af7141782f3f89655e6868abe3f141c97632/src/Outbox.ts#L43)

##### version

> `readonly` **version**: `number`

Defined in: [src/Outbox.ts:48](https://github.com/davidnussio/effect-cqrs/blob/9d66af7141782f3f89655e6868abe3f141c97632/src/Outbox.ts#L48)

The version of the event in its stream.

***

### Outbox

Defined in: [src/Outbox.ts:69](https://github.com/davidnussio/effect-cqrs/blob/9d66af7141782f3f89655e6868abe3f141c97632/src/Outbox.ts#L69)

#### Type Parameters

##### Name

`Name` *extends* `string`

##### E

`E`

##### R

`R`

#### Properties

##### aggregates

> `readonly` **aggregates**: readonly [`Any`](https://effect-cqrs.dambox.ch/reference/api/aggregate/#any)\[]

Defined in: [src/Outbox.ts:71](https://github.com/davidnussio/effect-cqrs/blob/9d66af7141782f3f89655e6868abe3f141c97632/src/Outbox.ts#L71)

##### batchSize

> `readonly` **batchSize**: `number`

Defined in: [src/Outbox.ts:74](https://github.com/davidnussio/effect-cqrs/blob/9d66af7141782f3f89655e6868abe3f141c97632/src/Outbox.ts#L74)

##### linger

> `readonly` **linger**: `Duration`

Defined in: [src/Outbox.ts:75](https://github.com/davidnussio/effect-cqrs/blob/9d66af7141782f3f89655e6868abe3f141c97632/src/Outbox.ts#L75)

##### mappings

> `readonly` **mappings**: `Record`<`string`, (`event`, `meta`) => [`Mapped`](https://effect-cqrs.dambox.ch/reference/api/outbox/#mapped) | `undefined`>

Defined in: [src/Outbox.ts:72](https://github.com/davidnussio/effect-cqrs/blob/9d66af7141782f3f89655e6868abe3f141c97632/src/Outbox.ts#L72)

##### name

> `readonly` **name**: `Name`

Defined in: [src/Outbox.ts:70](https://github.com/davidnussio/effect-cqrs/blob/9d66af7141782f3f89655e6868abe3f141c97632/src/Outbox.ts#L70)

##### publish

> `readonly` **publish**: (`messages`) => `Effect`<`void`, `E`, `R`>

Defined in: [src/Outbox.ts:73](https://github.com/davidnussio/effect-cqrs/blob/9d66af7141782f3f89655e6868abe3f141c97632/src/Outbox.ts#L73)

###### Parameters

###### messages

readonly [`Message`](https://effect-cqrs.dambox.ch/reference/api/outbox/#message)\[]

###### Returns

`Effect`<`void`, `E`, `R`>

## Type Aliases

### Any

> **Any** = [`Outbox`](https://effect-cqrs.dambox.ch/reference/api/outbox/#outbox-1)<`string`, `any`, `any`>

Defined in: [src/Outbox.ts:78](https://github.com/davidnussio/effect-cqrs/blob/9d66af7141782f3f89655e6868abe3f141c97632/src/Outbox.ts#L78)

***

### Context

> **Context**<`O`> = `O` *extends* [`Outbox`](https://effect-cqrs.dambox.ch/reference/api/outbox/#outbox-1)<`any`, `any`, infer R> ? `R` : `never`

Defined in: [src/Outbox.ts:80](https://github.com/davidnussio/effect-cqrs/blob/9d66af7141782f3f89655e6868abe3f141c97632/src/Outbox.ts#L80)

#### Type Parameters

##### O

`O` *extends* [`Any`](https://effect-cqrs.dambox.ch/reference/api/outbox/#any)

***

### Mappings

> **Mappings**<`Event`> = { readonly \[Tag in Event\[“\_tag”]]?: (event: Extract\<Event, { \_tag: Tag }>, meta: EventMeta) => Mapped | undefined }

Defined in: [src/Outbox.ts:62](https://github.com/davidnussio/effect-cqrs/blob/9d66af7141782f3f89655e6868abe3f141c97632/src/Outbox.ts#L62)

#### Type Parameters

##### Event

`Event` *extends* [`Tagged`](https://effect-cqrs.dambox.ch/reference/api/aggregate/#tagged)

## Functions

### layer()

> **layer**<`Os`>(`outboxes`): `Layer`<[`Outboxes`](https://effect-cqrs.dambox.ch/reference/api/outbox/#outboxes), [`EventStoreError`](https://effect-cqrs.dambox.ch/reference/api/eventstore/#eventstoreerror), [`EventStore`](https://effect-cqrs.dambox.ch/reference/api/eventstore/#eventstore) | [`Checkpoints`](https://effect-cqrs.dambox.ch/reference/api/checkpoints/#checkpoints) | [`Context`](https://effect-cqrs.dambox.ch/reference/api/outbox/#context)<`Os`\[`number`]>>

Defined in: [src/Outbox.ts:233](https://github.com/davidnussio/effect-cqrs/blob/9d66af7141782f3f89655e6868abe3f141c97632/src/Outbox.ts#L233)

Runs the outboxes in the background for as long as the layer lives. Each one keeps a checkpoint under its name in `Checkpoints`, which should be durable: with an in-memory checkpoint an outbox publishes everything again on restart.

#### Type Parameters

##### Os

`Os` *extends* readonly [`Any`](https://effect-cqrs.dambox.ch/reference/api/outbox/#any)\[]

#### Parameters

##### outboxes

`Os`

#### Returns

`Layer`<[`Outboxes`](https://effect-cqrs.dambox.ch/reference/api/outbox/#outboxes), [`EventStoreError`](https://effect-cqrs.dambox.ch/reference/api/eventstore/#eventstoreerror), [`EventStore`](https://effect-cqrs.dambox.ch/reference/api/eventstore/#eventstore) | [`Checkpoints`](https://effect-cqrs.dambox.ch/reference/api/checkpoints/#checkpoints) | [`Context`](https://effect-cqrs.dambox.ch/reference/api/outbox/#context)<`Os`\[`number`]>>

***

### make()

> **make**<`Name`, `Aggregates`, `E`, `R`>(`options`): [`Outbox`](https://effect-cqrs.dambox.ch/reference/api/outbox/#outbox-1)<`Name`, `E`, `R`>

Defined in: [src/Outbox.ts:99](https://github.com/davidnussio/effect-cqrs/blob/9d66af7141782f3f89655e6868abe3f141c97632/src/Outbox.ts#L99)

Defines an outbox. `messages` maps events, by tag, to integration events, and only those are published. Without it every event of the aggregates is published, typed `<aggregate>.<tag>`, with its JSON form as payload.

Mapping is where domain events become a contract with other teams, and where personal data is left out: events reach it decrypted, see `PersonalData`.

#### Type Parameters

##### Name

`Name` *extends* `string`

##### Aggregates

`Aggregates` *extends* readonly [`Any`](https://effect-cqrs.dambox.ch/reference/api/aggregate/#any)\[]

##### E

`E` = `never`

##### R

`R` = `never`

#### Parameters

##### options

###### aggregates

`Aggregates`

###### batchSize?

`number`

The most messages in one call to `publish`. Defaults to 100.

###### linger?

`Input`

How long a batch waits for more messages before it is published. Defaults to 10 milliseconds.

###### messages?

[`Mappings`](https://effect-cqrs.dambox.ch/reference/api/outbox/#mappings-1)<[`Event`](https://effect-cqrs.dambox.ch/reference/api/aggregate/#event-2)<`Aggregates`\[`number`]>>

###### name

`Name`

###### publish

(`messages`) => `Effect`<`void`, `E`, `R`>

#### Returns

[`Outbox`](https://effect-cqrs.dambox.ch/reference/api/outbox/#outbox-1)<`Name`, `E`, `R`>
