PropertyDamage.Replay (PropertyDamage v0.1.0)
View SourceStep-by-step replay of failure sequences for debugging.
Replay mode lets you execute a failing sequence one command at a time, inspecting the state after each step. This is invaluable for understanding exactly how the system reached the failure state.
Usage Modes
Functional Mode (Recommended for scripts)
# Get all steps at once
{:ok, steps} = PropertyDamage.replay(failure)
for step <- steps do
IO.puts("Command #{step.index}: #{step.command_name}")
IO.inspect(step.projections, label: "State")
endInteractive Mode (For LiveBook/IEx)
{:ok, session} = Replay.start(failure)
{:ok, session, step} = Replay.step(session) # Execute first command
IO.inspect(step.projections) # Inspect state
{:ok, session, step} = Replay.step(session) # Next command
# ...continue stepping...Jump to Failure Point
{:ok, session} = Replay.start(failure)
{:ok, session, steps} = Replay.step_to(session, failure.failed_at_index)
# Now at the exact point where the failure occurredStep Information
Each step returns:
index- Command index in sequencecommand- The command structcommand_name- Short name for displayevents- Events produced by this commandprojections- Projection states after this commandrefs- Ref resolution mapresult-:ok,{:check_failed, ...}, or error
Summary
Functions
Get the current state of projections.
Format all steps for display.
Format a step for display.
Get all executed steps so far.
Get the command at a specific index (without executing).
Replay an entire failure sequence, returning all steps.
Start an interactive replay session.
Execute the next command in the sequence.
Execute commands up to (and including) the specified index.
Clean up session resources.
Types
@type t() :: %PropertyDamage.Replay{ adapter: module(), adapter_config: map(), commands: [struct()], current_index: integer(), event_log: [term()], event_queue: pid(), failure: PropertyDamage.FailureReport.t(), model: module(), projections: map(), refs: map(), status: :ready | :in_progress | :completed | :failed, steps: [step()] }
Functions
Get the current state of projections.
Format all steps for display.
Format a step for display.
Get all executed steps so far.
@spec peek(t(), non_neg_integer()) :: {:ok, struct()} | {:error, :out_of_bounds}
Get the command at a specific index (without executing).
@spec run( PropertyDamage.FailureReport.t(), keyword() ) :: {:ok, [step()]} | {:error, term()}
Replay an entire failure sequence, returning all steps.
This is the simplest way to replay - it executes all commands and returns structured information about each step.
Options
:adapter_config- Override adapter configuration:stop_on_failure- Stop at first failure (default: true):include_projections- Include projection states (default: true)
Returns
{:ok, [step]} where each step contains command, events, and state info.
Example
{:ok, steps} = PropertyDamage.replay(failure)
# Find where things went wrong
Enum.each(steps, fn step ->
IO.puts("[#{step.index}] #{step.command_name}")
case step.result do
:ok -> IO.puts(" -> OK")
{:check_failed, check, msg} -> IO.puts(" -> FAILED: #{check} - #{msg}")
end
end)
@spec start( PropertyDamage.FailureReport.t(), keyword() ) :: {:ok, t()} | {:error, term()}
Start an interactive replay session.
Use step/1 to advance through commands one at a time.
Options
:adapter_config- Override adapter configuration
Example
{:ok, session} = Replay.start(failure)
{:ok, session, step1} = Replay.step(session)
{:ok, session, step2} = Replay.step(session)
Execute the next command in the sequence.
Returns
{:ok, session, step}- Command executed, step contains results{:done, session}- No more commands to execute{:error, reason}- Execution failed
@spec step_to(t(), non_neg_integer()) :: {:ok, t(), [step()]} | {:error, term()}
Execute commands up to (and including) the specified index.
Returns
{:ok, session, [step]}- Commands executed{:error, reason}- Execution failed
@spec stop(t()) :: :ok
Clean up session resources.
Call this when done with an interactive session.