Mutare.Report.Live.Lines (mutare v0.3.1)

Copy Markdown View Source

The text of the live display, rendered from the reporter's state.

Mutare.Report.Live manages the process, output modes, and terminal writes; every line it draws or leaves in scrollback is rendered here — the animated status block (status_block/2), a mutant's leave-behind or --verbose line, a phase's label or detail note, and compile-poison diagnostics. Nothing here touches the terminal, so each line is testable on its own. Cursor-control sequences are the reporter's, never part of a line.

Summary

Functions

The label announcing the post-stream timeout-confirmation pass.

Renders a verbose detail event as a persistent status line: a phase's completion, or a mix.exs whose inference override did not land.

Estimates remaining seconds from completed work, remaining work, and elapsed seconds.

Milliseconds as one-decimal seconds (e.g. 450 → "0.5s", 3100 → "3.1s").

Seconds as Ns (under a minute) or Nm Ss.

Returns the persistent {label, color} for status, or nil when the status only updates the counter.

A mutant's permanent line: its leave_behind/1 styling (coloured when color?), the mutant descriptor, and — for a harness error — the compact diagnostic.

Renders the macro-expansion poison fallback as a loud, persistent warning: names the inline DSL macro(s) whose argument wouldn't compile with a mutation spliced in, and the copy-paste route to pin the skip up front (Mutare.Poison.Hint.route_tuple/2 — :raw for a call, :skip for a head Mutare analyzes structurally), or a # mutare:ignore pointer when no route can name any of them.

The label of a pre-mutant phase (:scanning, :compiling, :baseline, :coverage_probe), or nil for anything else.

Renders one compile-poison recovery round as a persistent status line: how many mutants were dropped and how many block macros were escalated (skipped wholesale), naming the escalated macros so the line explains why the compile is being retried.

The :running phase's label. In verbose mode it appends the worker count from the stashed :run_config ({:run_config, cfg} always fires just before {:running, total}); the non-verbose label is unchanged.

Renders the app-build seed's outcome (Mutare.Sandbox.Seed.summary/0) as a persistent status line, or nil for a :skipped seed (the broad-run default — no line even in verbose). :seeded shows the reused vs recompiling beam counts; :partial adds how many apps fell back (an umbrella per-app miss); :fallback names the otherwise-silent fall back to a cold compile.

Returns the status-block lines for state at monotonic time now_ms.

Returns the persistent {label, color} for status in verbose mode.

The verbose per-mutant line: every status's verbose_leave/1 label (coloured when color?), the shared descriptor, and a duration suffix for a mutant that actually ran (duration_ms > 0 — so a no-coverage/ignored/poisoned mutant, which launched no suite, shows no time).

Functions

confirming_label(count)

@spec confirming_label(non_neg_integer()) :: String.t()

The label announcing the post-stream timeout-confirmation pass.

detail_line(arg)

@spec detail_line(tuple()) :: String.t()

Renders a verbose detail event as a persistent status line: a phase's completion, or a mix.exs whose inference override did not land.

eta_secs(done, remaining, elapsed)

@spec eta_secs(non_neg_integer(), non_neg_integer(), non_neg_integer()) ::
  non_neg_integer() | nil

Estimates remaining seconds from completed work, remaining work, and elapsed seconds.

Returns nil until at least one item has completed and elapsed time is non-zero.

humanize_ms(ms)

@spec humanize_ms(non_neg_integer()) :: String.t()

Milliseconds as one-decimal seconds (e.g. 450 → "0.5s", 3100 → "3.1s").

humanize_secs(s)

@spec humanize_secs(non_neg_integer()) :: String.t()

Seconds as Ns (under a minute) or Nm Ss.

leave_behind(status)

@spec leave_behind(Mutare.Result.status()) :: {String.t(), atom()} | nil

Returns the persistent {label, color} for status, or nil when the status only updates the counter.

leave_line(styled, result, color?)

@spec leave_line({String.t(), atom()}, Mutare.Result.t(), boolean()) :: String.t()

A mutant's permanent line: its leave_behind/1 styling (coloured when color?), the mutant descriptor, and — for a harness error — the compact diagnostic.

macro_poison_line(map)

@spec macro_poison_line(map()) :: String.t()

Renders the macro-expansion poison fallback as a loud, persistent warning: names the inline DSL macro(s) whose argument wouldn't compile with a mutation spliced in, and the copy-paste route to pin the skip up front (Mutare.Poison.Hint.route_tuple/2 — :raw for a call, :skip for a head Mutare analyzes structurally), or a # mutare:ignore pointer when no route can name any of them.

phase_label(phase)

@spec phase_label(term()) :: String.t() | nil

The label of a pre-mutant phase (:scanning, :compiling, :baseline, :coverage_probe), or nil for anything else.

poison_round_line(map)

@spec poison_round_line(map()) :: String.t()

Renders one compile-poison recovery round as a persistent status line: how many mutants were dropped and how many block macros were escalated (skipped wholesale), naming the escalated macros so the line explains why the compile is being retried.

running_label(arg1, total)

@spec running_label(map(), non_neg_integer()) :: String.t()

The :running phase's label. In verbose mode it appends the worker count from the stashed :run_config ({:run_config, cfg} always fires just before {:running, total}); the non-verbose label is unchanged.

seed_line(map)

@spec seed_line(map()) :: String.t() | nil

Renders the app-build seed's outcome (Mutare.Sandbox.Seed.summary/0) as a persistent status line, or nil for a :skipped seed (the broad-run default — no line even in verbose). :seeded shows the reused vs recompiling beam counts; :partial adds how many apps fell back (an umbrella per-app miss); :fallback names the otherwise-silent fall back to a cold compile.

status_block(state, now)

@spec status_block(map(), integer()) :: [String.t()]

Returns the status-block lines for state at monotonic time now_ms.

A running phase has an activity line and a counter. A pre-run phase has one line. An idle state has none. Cursor-control sequences are not included.

verbose_leave(status)

@spec verbose_leave(Mutare.Result.status()) :: {String.t(), atom()}

Returns the persistent {label, color} for status in verbose mode.

Every registered status has a verbose label. An unknown status raises.

verbose_line(result, color?)

@spec verbose_line(Mutare.Result.t(), boolean()) :: String.t()

The verbose per-mutant line: every status's verbose_leave/1 label (coloured when color?), the shared descriptor, and a duration suffix for a mutant that actually ran (duration_ms > 0 — so a no-coverage/ignored/poisoned mutant, which launched no suite, shows no time).