Skip to content

<!-- Authored per the the-loop:writing skill. -->

Testing plan: roll running sessions onto a refreshed environment ​

Derived from requirements.md and design.md. Planned at test-planning, results recorded at verification (below).

Test matrix ​

#TypeApplies?Scope / what it provesWhere it runs
T1Unityesenvstate: declared re-parses the file and never consults os.environ; fingerprint is stable, truncated and reveals nothing; compare names only the differing variables, in name order; process_environ reads this test's own pid and returns None for a pid that cannot be readmake test (tests/test_envstate.py)
T2UnityesTmuxRunner.respawn_in builds respawn-pane -k -t … -c … -e … with the resume argv, and spawn_in folds env_provider's names in behind _supports_env, with the-loop's own three names lastmake test (tests/test_tmux_runner.py)
T3Integrationyesrestart_sessions end to end over a registry and a fake runner: one row per outcome (restarted, skipped, failed, unverified, stale), the exit code each implies, and --dry-run touching nothingmake test (tests/test_sessions_restart_integration.py)
T4Integrationyesenvironment_drift and the status line: drift counted from live panes, no line when clean, JSON carrying the same facts, ok unmovedmake test (tests/test_sessions_restart_integration.py)
T5Contract (CLI ↔ docs parity)yesthe new subcommand and its options are documented; test_docs_parity stays greenmake test
T6Security / redactionyesno declared value appears in any message, event-log record or rendered status, on any path including every failure pathmake test (tests/test_sessions_restart_integration.py)
T7End-to-end against real tmuxyesa real pane respawned in place on a real tmux: the session keeps its name, the new process carries the new value, the old one is gonedocs/specs/issue-410/evidence/verification.md (recorded transcript)
T8Regression (full suite)yesevery suite stays green; ruff, ruff format, pyright, markdownlint, validate_configmake check
T9UI / visualn/a — no product UI
T10Snapshotn/a — messages asserted directly (T3)
T11Accessibilityn/a — CLI text only
T12Migration / upgradeyesno config key, no state file and no registry field is added, so an existing deployment needs no migration; a deployment with no env.file spawns exactly as before (asserted in T2)with T2/T8
T13Manual exploratoryno — T7 covers the only surface the fakes cannot reach

Scenarios & requirement trace ​

RowRequirement(s)Scenario / case
T1R1.1declared re-reads the file after it is rewritten, and returns the new value while os.environ still holds the old
T1R1.7a config naming no env.file → declared returns None, distinct from a file that declares nothing
T1R5.2fingerprint of two different values differs, of the same value matches, and its output contains no part of the input
T1R2.1compare over equal mappings → (); over one differing name → exactly that name
T1R2.3process_environ(<this pid>) finds a variable this test exported; process_environ(<unused pid>) → None, no exception
T2R1.4respawn_in argv carries -k, the target, the recorded cwd and --resume <id>
T2R4.1spawn_in with a provider emits -e NAME=VALUE for each declared name
T2R4.2spawn_in with no provider emits exactly today's argv
T2R4.3a tmux below 3.2 emits no -e at all and still spawns
T2R5.1the-loop's own THE_LOOP_* names survive an env file that declares them
T3R1.1, R1.2--all restarts every live session; a ref restarts that one and leaves the others running
T3R1.3neither --all nor a ref → refusal naming both, nothing respawned
T3R1.5a session with no resumable conversation is skipped and its pane is still alive afterwards
T3R1.6a registered but dead session is skipped: not running, never spawned
T3R1.7no env.file → exit 2, no pane touched
T3R2.2a session whose environment still differs after the respawn → row names the variables, exit 1
T3R2.3an unreadable environment → unverified, exit 0
T3R2.4--dry-run reports the same selection and calls no respawn
T3R1.5, design § Error handlinga respawned pane that dies inside the probe window → failed, exit 1
T4R3.1two of six running sessions stale → one status line naming 2, 6 and the fixing command
T4R3.2every session fresh → status prints no environment line
T4R3.3status --format json carries sessionEnvironment with the per-session rows
T4R3.4environments unreadable → no drift claimed, no failure
T4R3.5drift present → ok and the exit code are what they were without it
T6R5.1, R5.3every message, event record and status line from T3/T4 is asserted not to contain any declared value; a differing name appears by name and fingerprint
T7R1.4, R2.1a real loop-* session: same session name and window before and after, new pid, new value read back from /proc
T8allmake check green

Requirements not covered by an automated test ​

  • R5.1 on the logging path is asserted over the messages, the event log and the rendered status (T6); the assertion is a substring search for each declared value, so it covers any path that reaches those three sinks and nothing beyond them. Direct logger output is read at review — envstate holds every value-handling line and is small enough to read in full.

Verification environment ​

The suite's own fake tmux for T2–T6; a real tmux 3.4 on the development host for T7, against a scratch TMUX_TMPDIR so nothing touches the operator's server.

Verification results ​

Recorded at the verification gate in evidence/verification.md.

Released under the MIT License.