ElixirScope.Storage.DataAccess (elixir_scope v0.0.1)

High-performance ETS-based storage for ElixirScope events.

Provides multiple indexes for fast querying across different dimensions:

  • Primary index: Event ID -> Event
  • Temporal index: Timestamp -> Event ID
  • Process index: PID -> [Event IDs]
  • Function index: {Module, Function} -> [Event IDs]
  • Correlation index: Correlation ID -> [Event IDs]

Designed for high write throughput and fast range queries.

Summary

Functions

Cleans up old events to maintain memory bounds.

Destroys the storage and cleans up all ETS tables.

Checks if an event exists by ID.

Retrieves an event by its ID.

Queries events since a given timestamp.

Gets the current instrumentation plan.

Gets storage statistics.

Creates a new data access instance with ETS tables.

Queries events by process ID.

Stores an event in the data access layer.

Stores multiple events (simplified interface).

Stores multiple events in batch for better performance.

Stores an instrumentation plan.

Types

event_id()

@type event_id() :: binary()

query_options()

@type query_options() :: keyword()

t()

@type t() :: %ElixirScope.Storage.DataAccess{
  correlation_index: :ets.tid(),
  function_index: :ets.tid(),
  name: table_name(),
  primary_table: :ets.tid(),
  process_index: :ets.tid(),
  stats_table: :ets.tid(),
  temporal_index: :ets.tid()
}

table_name()

@type table_name() :: atom()

Functions

cleanup_old_events(storage, cutoff_timestamp)

@spec cleanup_old_events(t(), non_neg_integer()) ::
  {:ok, non_neg_integer()} | {:error, term()}

Cleans up old events to maintain memory bounds.

Removes events older than the specified timestamp.

destroy(storage)

@spec destroy(t()) :: :ok

Destroys the storage and cleans up all ETS tables.

event_exists?(event_id)

@spec event_exists?(event_id()) :: boolean()

Checks if an event exists by ID.

get_event(storage, event_id)

@spec get_event(t(), event_id()) ::
  {:ok, ElixirScope.Events.event()} | {:error, :not_found}

Retrieves an event by its ID.

get_events_since(since_timestamp)

@spec get_events_since(non_neg_integer()) :: [ElixirScope.Events.event()]

Queries events since a given timestamp.

get_instrumentation_plan()

@spec get_instrumentation_plan() :: {:ok, map()} | {:error, :not_found}

Gets the current instrumentation plan.

get_stats(storage)

@spec get_stats(t()) :: %{
  total_events: non_neg_integer(),
  max_events: non_neg_integer(),
  oldest_timestamp: non_neg_integer() | nil,
  newest_timestamp: non_neg_integer() | nil,
  memory_usage: non_neg_integer()
}

Gets storage statistics.

new(opts \\ [])

@spec new(keyword()) :: {:ok, t()} | {:error, term()}

Creates a new data access instance with ETS tables.

Options

  • :name - Base name for the tables (default: generates unique name)
  • :max_events - Maximum number of events to store (default: 1_000_000)

query_by_correlation(storage, correlation_id, opts \\ [])

@spec query_by_correlation(t(), term(), query_options()) ::
  {:ok, [ElixirScope.Events.event()]} | {:error, term()}

Queries events by correlation ID.

query_by_function(storage, module, function, opts \\ [])

@spec query_by_function(t(), module(), atom(), query_options()) ::
  {:ok, [ElixirScope.Events.event()]} | {:error, term()}

Queries events by function.

query_by_process(storage, pid, opts \\ [])

@spec query_by_process(t(), pid(), query_options()) ::
  {:ok, [ElixirScope.Events.event()]} | {:error, term()}

Queries events by process ID.

query_by_time_range(storage, start_time, end_time, opts \\ [])

@spec query_by_time_range(t(), non_neg_integer(), non_neg_integer(), query_options()) ::
  {:ok, [ElixirScope.Events.event()]} | {:error, term()}

Queries events by time range.

Options

  • :limit - Maximum number of events to return (default: 1000)
  • :order - :asc or :desc (default: :asc)

store_event(storage, event)

@spec store_event(t(), ElixirScope.Events.event()) :: :ok | {:error, term()}

Stores an event in the data access layer.

Automatically creates all necessary indexes for fast querying.

store_events(events)

@spec store_events([ElixirScope.Events.event()]) :: :ok | {:error, term()}

Stores multiple events (simplified interface).

store_events(storage, events)

@spec store_events(t(), [ElixirScope.Events.event()]) ::
  {:ok, non_neg_integer()} | {:error, term()}

Stores multiple events in batch for better performance.

store_instrumentation_plan(plan)

@spec store_instrumentation_plan(map()) :: :ok | {:error, term()}

Stores an instrumentation plan.