Foundation.Events (foundation v0.1.0)

Public API for event management and storage.

Thin wrapper around EventStore that provides a clean, documented interface. All business logic is delegated to the service layer.

Summary

Functions

Check if the Events service is available.

Create a new event for debugging/testing (returns event directly, not tuple).

Deserialize binary data back to an event.

Create a function entry event (convenience function).

Create a function exit event (convenience function).

Retrieve an event by ID.

Get events by correlation ID.

Extract correlation chain from stored events.

Get recent events with optional limit.

Get events within a time range.

Initialize the event store service.

Create a new event with the given type and data.

Delete events older than the specified timestamp.

Query events with filters and pagination.

Serialize an event to binary format.

Calculate the serialized size of an event.

Create a state change event (convenience function).

Get storage statistics.

Get event store service status.

Store a single event.

Store multiple events atomically.

Types

correlation_id()

@type correlation_id() :: Foundation.Types.Event.correlation_id()

event_id()

@type event_id() :: Foundation.Types.Event.event_id()

event_query()

@type event_query() :: map()

Functions

available?()

@spec available?() :: boolean()

Check if the Events service is available.

Examples

iex> Foundation.Events.available?()
true

debug_new_event(event_type, data, opts \\ [])

@spec debug_new_event(atom(), term(), keyword()) :: Foundation.Types.Event.t()

Create a new event for debugging/testing (returns event directly, not tuple).

Examples

iex> Foundation.Events.debug_new_event(:test_event, %{key: "value"})
%Event{event_type: :test_event, data: %{key: "value"}}

deserialize(binary)

@spec deserialize(binary()) ::
  {:ok, Foundation.Types.Event.t()} | {:error, Foundation.Types.Error.t()}

Deserialize binary data back to an event.

Examples

iex> {:ok, serialized} = Events.serialize(event)
iex> Foundation.Events.deserialize(serialized)
{:ok, %Event{...}}

function_entry(module, function, arity, args, opts \\ [])

@spec function_entry(module(), atom(), arity(), [term()], keyword()) ::
  {:ok, Foundation.Types.Event.t()} | {:error, Foundation.Types.Error.t()}

Create a function entry event (convenience function).

Examples

iex> Foundation.Events.function_entry(MyModule, :my_func, 2, [arg1, arg2])
{:ok, %Event{event_type: :function_entry, ...}}

function_exit(module, function, arity, call_id, result, duration_ns, exit_reason)

@spec function_exit(
  module(),
  atom(),
  arity(),
  pos_integer(),
  term(),
  non_neg_integer(),
  atom()
) ::
  {:ok, Foundation.Types.Event.t()} | {:error, Foundation.Types.Error.t()}

Create a function exit event (convenience function).

Examples

iex> Foundation.Events.function_exit(MyModule, :my_func, 2, 123, :ok, 1000, :normal)
{:ok, %Event{event_type: :function_exit, ...}}

get(event_id)

@spec get(event_id()) ::
  {:ok, Foundation.Types.Event.t()} | {:error, Foundation.Types.Error.t()}

Retrieve an event by ID.

Examples

iex> Foundation.Events.get(12345)
{:ok, %Event{event_id: 12345, ...}}

iex> Foundation.Events.get(99999)
{:error, %Error{error_type: :not_found}}

get_by_correlation(correlation_id)

@spec get_by_correlation(correlation_id()) ::
  {:ok, [Foundation.Types.Event.t()]} | {:error, Foundation.Types.Error.t()}

Get events by correlation ID.

Examples

iex> Foundation.Events.get_by_correlation("req-123")
{:ok, [%Event{correlation_id: "req-123"}, ...]}

get_correlation_chain(correlation_id)

@spec get_correlation_chain(correlation_id()) ::
  {:ok, [Foundation.Types.Event.t()]} | {:error, Foundation.Types.Error.t()}

Extract correlation chain from stored events.

Examples

iex> Foundation.Events.get_correlation_chain("req-123")
{:ok, [%Event{}, ...]}  # Events in chronological order

get_recent(limit \\ 100)

@spec get_recent(non_neg_integer()) ::
  {:ok, [Foundation.Types.Event.t()]} | {:error, Foundation.Types.Error.t()}

Get recent events with optional limit.

Examples

iex> Foundation.Events.get_recent(50)
{:ok, [%Event{}, ...]}  # Last 50 events

get_time_range(start_time, end_time)

@spec get_time_range(integer(), integer()) ::
  {:ok, [Foundation.Types.Event.t()]} | {:error, Foundation.Types.Error.t()}

Get events within a time range.

Examples

iex> start_time = System.monotonic_time() - 3600_000
iex> end_time = System.monotonic_time()
iex> Foundation.Events.get_time_range(start_time, end_time)
{:ok, [%Event{}, ...]}

initialize()

@spec initialize() :: :ok | {:error, Foundation.Types.Error.t()}

Initialize the event store service.

Examples

iex> Foundation.Events.initialize()
:ok

new_event(event_type, data, opts \\ [])

Create a new event with the given type and data.

Examples

iex> Foundation.Events.new_event(:test_event, %{key: "value"})
{:ok, %Event{event_type: :test_event, data: %{key: "value"}}}

iex> Foundation.Events.new_event(:invalid, nil)
{:error, %Error{error_type: :invalid_event_data}}

prune_before(timestamp)

@spec prune_before(integer()) ::
  {:ok, non_neg_integer()} | {:error, Foundation.Types.Error.t()}

Delete events older than the specified timestamp.

Examples

iex> cutoff = System.monotonic_time() - 3600_000  # 1 hour ago
iex> Foundation.Events.prune_before(cutoff)
{:ok, 150}  # 150 events pruned

query(query_opts)

@spec query(event_query()) ::
  {:ok, [Foundation.Types.Event.t()]} | {:error, Foundation.Types.Error.t()}

Query events with filters and pagination.

Examples

iex> query = [event_type: :function_entry, limit: 10]
iex> Foundation.Events.query(query)
{:ok, [%Event{}, ...]}

iex> query = [time_range: {start_time, end_time}, order_by: :timestamp]
iex> Foundation.Events.query(query)
{:ok, [%Event{}, ...]}

serialize(event)

@spec serialize(Foundation.Types.Event.t()) ::
  {:ok, binary()} | {:error, Foundation.Types.Error.t()}

Serialize an event to binary format.

Examples

iex> {:ok, event} = Events.new_event(:test, %{})
iex> Foundation.Events.serialize(event)
{:ok, <<...>>}

serialized_size(event)

@spec serialized_size(Foundation.Types.Event.t()) ::
  {:ok, non_neg_integer()} | {:error, Foundation.Types.Error.t()}

Calculate the serialized size of an event.

Examples

iex> {:ok, event} = Events.new_event(:test, %{})
iex> Foundation.Events.serialized_size(event)
{:ok, 156}

state_change(server_pid, callback, old_state, new_state, opts \\ [])

@spec state_change(pid(), atom(), term(), term(), keyword()) ::
  {:ok, Foundation.Types.Event.t()} | {:error, Foundation.Types.Error.t()}

Create a state change event (convenience function).

Examples

iex> Foundation.Events.state_change(self(), :handle_call, old_state, new_state)
{:ok, %Event{event_type: :state_change, ...}}

stats()

@spec stats() :: {:ok, map()} | {:error, Foundation.Types.Error.t()}

Get storage statistics.

Examples

iex> Foundation.Events.stats()
{:ok, %{
  current_event_count: 1000,
  events_stored: 5000,
  events_pruned: 200,
  memory_usage_estimate: 1024000,
  uptime_ms: 3600000
}}

status()

@spec status() :: {:ok, map()} | {:error, Foundation.Types.Error.t()}

Get event store service status.

Examples

iex> Foundation.Events.status()
{:ok, %{status: :running, uptime: 12345}}

store(event)

@spec store(Foundation.Types.Event.t()) ::
  {:ok, event_id()} | {:error, Foundation.Types.Error.t()}

Store a single event.

Examples

iex> {:ok, event} = Event.new(event_type: :test, data: %{key: "value"})
iex> Foundation.Events.store(event)
{:ok, 12345}

store_batch(events)

@spec store_batch([Foundation.Types.Event.t()]) ::
  {:ok, [event_id()]} | {:error, Foundation.Types.Error.t()}

Store multiple events atomically.

Examples

iex> events = [event1, event2, event3]
iex> Foundation.Events.store_batch(events)
{:ok, [12345, 12346, 12347]}