Skip to content
Effect 4.0 is here. One ecosystem. Zero dependencies.

EventJournal unstable

Stores event-log entries and replication state.

EventJournal records committed entries, exposes them for replay, publishes local changes, and tracks the remote metadata needed to exchange entries with other journals. Higher-level event-log schemas and handlers use this service to rebuild projections, sync offline clients, import remote changes, and coordinate writes per store. This module also defines journal errors, entry and remote identifiers, schemas, and in-memory or IndexedDB-backed journal layers.

20 exports Since v4.0.0 Source

Constructors

Since v4.0.0

Creates an EventJournal backed by IndexedDB.

Details

The journal stores entries and remote replication metadata in the configured browser database, publishes local changes, and requires Scope so the database connection can be closed when the scope ends.

Signature

declare function makeIndexedDb(options?: {
readonly database?: string;
}): Effect<{
readonly changes: Effect<Subscription<Entry>, never, Scope>;
readonly destroy: Effect<void, EventJournalError>;
readonly entries: Effect<readonly Array<Entry>, EventJournalError>;
readonly nextRemoteSequence: (remoteId: RemoteId) => Effect<number, EventJournalError>;
readonly withLock: (storeId: StoreId) => <A, E, R>(effect: Effect<A, E, R>) => Effect<A, E, R>;
readonly withRemoteUncommited: <A, E, R>(remoteId: RemoteId, f: (entries: readonly [Entry, Entry]) => Effect<A, E, R>) => Effect<Option<A>, EventJournalError | E, R>;
readonly write: <A, E, R>(options: {
readonly effect: (entry: Entry) => Effect<A, E, R>;
readonly event: string;
readonly payload: Uint8Array;
readonly primaryKey: string;
}) => Effect<A, EventJournalError | E, R>;
readonly writeFromRemote: (options: {
readonly compact?: (uncommitted: readonly Array<RemoteEntry>) => Effect<readonly Array<Entry>, EventJournalError>;
readonly effect: (options: {
readonly conflicts: readonly Array<Entry>;
readonly entry: Entry;
}) => Effect<void, EventJournalError>;
readonly entries: readonly Array<RemoteEntry>;
readonly remoteId: RemoteId;
}) => Effect<{
readonly duplicateEntries: readonly Array<Entry>;
}, EventJournalError>;
}, EventJournalError, Scope>

makeMemory

unstable
Since v4.0.0

Creates an in-memory EventJournal service.

Gotchas

Entries, remote tracking state, and locks live only in the current process and are lost when the service is discarded.

Signature

declare const makeMemory: Effect.Effect<EventJournal["Service"]>

Errors

Since v4.0.0

Error raised by event journal operations.

Details

The error records the journal method that failed and the underlying cause.

Signature

declare class EventJournalError extends YieldableError<this> & {
readonly _tag: "EventJournalError";
} & Readonly<{
readonly cause: unknown;
readonly method: string;
}> {
constructor(args: {
readonly cause: unknown;
readonly method: string;
});
readonly "effect/eventlog/EventJournal/EventJournalError": "effect/eventlog/EventJournal/EventJournalError";
}

Getters

Since v4.0.0

Extracts the millisecond timestamp encoded in a UUID v7 EntryId.

Signature

declare function entryIdMillis(entryId: EntryId): number

Layers

Since v4.0.0

Provides EventJournal using the IndexedDB-backed implementation created by makeIndexedDb.

Signature

declare function layerIndexedDb(options?: {
readonly database?: string;
}): Layer<EventJournal, EventJournalError>

layerMemory

unstable
Since v4.0.0

Layer that provides an in-memory EventJournal.

Gotchas

All journal data is stored in process memory and is not persisted across layer lifetimes.

Signature

declare const layerMemory: Layer.Layer<EventJournal>

Models

EntryId

type unstable
Since v4.0.0

Branded byte identifier for an event journal entry.

Signature

type EntryId = Uint8Array<ArrayBuffer> & Brand<EntryIdTypeId>

RemoteId

type unstable
Since v4.0.0

Branded byte identifier for a remote event journal source.

Signature

type RemoteId = Uint8Array & Brand<RemoteIdTypeId>

Ordering

Since v4.0.0

Provides an Ordering instance for entry identifiers based on their raw UUID bytes.

Signature

declare const EntryIdOrder: Order<EntryId>

Schemas

Entry

unstable
Since v4.0.0

Schema for a committed event journal entry.

Details

An entry records its ID, event tag, primary key, and SchemaBinary-encoded payload, with helpers for array SchemaBinary encoding and creation timestamps.

Signature

declare class Entry extends {
readonly event: string;
readonly id: Uint8Array<ArrayBuffer> & Brand<"effect/eventlog/EventJournal/EntryId">;
readonly payload: Uint8Array<ArrayBufferLike>;
readonly primaryKey: string;
} {
constructor(...args: [props: {
readonly event: string;
readonly id: Uint8Array<ArrayBuffer> & Brand<"effect/eventlog/EventJournal/EntryId">;
readonly payload: Uint8Array<ArrayBufferLike>;
readonly primaryKey: string;
}, options?: MakeOptions]);
static arraySchemaBinary: $Array<toCodec<typeof Entry>>;
static decodeArray: (input: unknown, options?: ParseOptions) => Effect<readonly Array<Entry>, SchemaError, never>;
static encodeArray: (input: unknown, options?: ParseOptions) => Effect<readonly Array<Uint8Array<ArrayBuffer>>, SchemaError, never>;
static Order: Order<Entry>;
createdAt: Utc;
createdAtMillis: number;
idString: string;
}

EntryId

unstable
Since v4.0.0

Schema for branded event journal entry identifiers.

Signature

declare const EntryId: brand<instanceOf<Uint8Array<ArrayBuffer>, Uint8Array<ArrayBuffer>>, "effect/eventlog/EventJournal/EntryId">

RemoteEntry

unstable
Since v4.0.0

Schema for an event journal entry received from a remote source.

Details

It pairs the remote sequence number with the journal entry payload.

Signature

declare class RemoteEntry extends {
readonly entry: Entry;
readonly remoteSequence: number;
} {
constructor(...args: [props: {
readonly entry: Entry;
readonly remoteSequence: number;
}, options?: MakeOptions]);
}

RemoteId

unstable
Since v4.0.0

Schema for branded remote event journal identifiers.

Signature

declare const RemoteId: brand<Uint8Array, "effect/eventlog/EventJournal/RemoteId">

Services

Since v4.0.0

Context service for storing and replaying event journal entries.

Details

The service writes local entries, imports entries from remote journals, exposes a stream of local changes, and provides per-store locking.

Signature

declare class EventJournal extends Shape<"effect/eventlog/EventJournal", {
readonly changes: Effect<Subscription<Entry>, never, Scope>;
readonly destroy: Effect<void, EventJournalError>;
readonly entries: Effect<readonly Array<Entry>, EventJournalError>;
readonly nextRemoteSequence: (remoteId: RemoteId) => Effect<number, EventJournalError>;
readonly withLock: (storeId: StoreId) => <A, E, R>(effect: Effect<A, E, R>) => Effect<A, E, R>;
readonly withRemoteUncommited: <A, E, R>(remoteId: RemoteId, f: (entries: readonly [Entry, Entry]) => Effect<A, E, R>) => Effect<Option<A>, EventJournalError | E, R>;
readonly write: <A, E, R>(options: {
readonly effect: (entry: Entry) => Effect<A, E, R>;
readonly event: string;
readonly payload: Uint8Array;
readonly primaryKey: string;
}) => Effect<A, EventJournalError | E, R>;
readonly writeFromRemote: (options: {
readonly compact?: (uncommitted: readonly Array<RemoteEntry>) => Effect<readonly Array<Entry>, EventJournalError>;
readonly effect: (options: {
readonly conflicts: readonly Array<Entry>;
readonly entry: Entry;
}) => Effect<void, EventJournalError>;
readonly entries: readonly Array<RemoteEntry>;
readonly remoteId: RemoteId;
}) => Effect<{
readonly duplicateEntries: readonly Array<Entry>;
}, EventJournalError>;
}, this> {
constructor(_: never);
}

Type IDs

Since v4.0.0

Runtime brand identifier used for EntryId values.

Signature

declare const EntryIdTypeId: EntryIdTypeId

EntryIdTypeId

type unstable
Since v4.0.0

Brand identifier used for EntryId values.

Signature

type EntryIdTypeId = "effect/eventlog/EventJournal/EntryId"
Since v4.0.0

Runtime brand identifier used for RemoteId values.

Signature

declare const RemoteIdTypeId: "effect/eventlog/EventJournal/RemoteId"

RemoteIdTypeId

type unstable
Since v4.0.0

Brand identifier used for RemoteId values.

Signature

type RemoteIdTypeId = "effect/eventlog/EventJournal/RemoteId"

Unsafe

Since v4.0.0

Generates a UUID v7 EntryId, optionally using the supplied millisecond timestamp.

When to use

Use when generating an event-log entry id internally and the UUID v7 bytes are trusted to satisfy the brand.

Gotchas

This is unsafe because the generated UUID bytes are cast to the brand without schema validation.

Signature

declare function makeEntryIdUnsafe(options: {
msecs?: number;
}): EntryId
Since v4.0.0

Generates a new random RemoteId.

When to use

Use when generating a fresh event-log remote id internally and the UUID bytes are trusted to satisfy the brand.

Gotchas

This is unsafe because the generated UUID bytes are cast to the brand without schema validation.

Signature

declare function makeRemoteIdUnsafe(): RemoteId