Run outcomes, score, explicit exercise recording, and step captures (RBT-WP-0004-T13)
All checks were successful
CI Smoke / host-smoke (push) Successful in 0s
CI Smoke / container-smoke (push) Successful in 2s
Work Records / validate (push) Successful in 12s

Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>

Assistant: claude-code
Assistant-Model: sonnet
Assistant-Process: 295952@bnt-lap001
Assistant-Session: e93f64ad-516c-46eb-9666-aad8d300c477
This commit is contained in:
tegwick 2026-09-29 11:15:58 +02:00
parent 288e04c192
commit 8a5cbc1c29
7 changed files with 444 additions and 5 deletions

View file

@ -177,7 +177,9 @@ def test_done_steps_fold_to_the_title_line_and_others_stay_open(srv):
_, _, body = req(srv, "GET", base)
assert "<details class='step done'>" in body # done: no 'open' attribute, so folded
assert "1. Read the poem" in body.split("<details class='step done'>")[1].split("</summary>")[0] # title line stays in the summary
assert "Comment: fine" in body.split("<details class='step done'>")[1].split("</details>")[0] # the rest is inside the fold
rest = body.split("<details class='step done'>")[1]
step_end = min(x for x in (rest.find("<details id=current"), rest.find("<details class='step"), rest.find("<div id=close")) if x >= 0)
assert "Comment: fine" in rest[:step_end] # the rest is inside the fold
def _finish_showcase(srv, t, base):
@ -223,3 +225,65 @@ def test_feedback_validation(srv):
st, _, body = req(srv, "POST", base + "/feedback", {"_t": t, "rating": "good", "comment": "hvs.ABCDEFGHIJKLMN"})
assert st == 400 and "secret-looking" in body
assert req(srv, "POST", base + "/feedback", {"rating": "good"})[0] == 403 # CSRF token required
def test_score_runs_list_and_finalize_flow(srv):
t, loc, _ = _showcase_run(srv)
base = loc.split("#")[0]
i = int(base.split("/")[2])
_, _, body = req(srv, "GET", f"/pack/{i}")
assert "tried 1 · succeeded 0" in body and "open 1" in body and "Runs" in body
_, _, body = req(srv, "GET", base)
assert "Abandon run" in body and "Finish: succeeded" not in body # cannot succeed before every step is done
_finish_showcase(srv, t, base)
_, _, body = req(srv, "GET", base)
assert "Finish: succeeded" in body
assert req(srv, "POST", base + "/finalize", {"_t": t, "outcome": "succeeded", "note": "smooth"})[0] == 303
_, _, body = req(srv, "GET", base)
assert "Run finished: succeeded" in body and "smooth" in body
assert "Record pack as exercised" in body and "would set it to" in body # explicit, with the diff in words
assert "Start this step" not in body # read-only now
_, _, body = req(srv, "GET", "/")
assert "succeeded 1" in body
# exercised status is only written on the explicit click
pack_file = srv.app.packs[i].path
assert "exercise_status: unexercised" in pack_file.read_text()
assert req(srv, "POST", base + "/exercise", {"_t": t})[0] == 303
assert "exercise_status: exercised" in pack_file.read_text()
_, _, body = req(srv, "GET", base)
assert "Pack recorded as" in body and "Record pack as exercised" not in body
def test_abandon_and_actions_refused_after_finish(srv):
t, loc, _ = _showcase_run(srv)
base = loc.split("#")[0]
assert req(srv, "POST", base + "/finalize", {"_t": t, "outcome": "abandoned"})[0] == 303
st, _, body = req(srv, "POST", base + "/read-the-sign/start", {"_t": t})
assert st == 400 and "finished" in body
assert req(srv, "POST", base + "/exercise", {"_t": t})[0] == 400 # only a succeeded run may exercise the pack
def test_capture_and_pasted_output_check(srv):
t, loc, _ = _showcase_run(srv)
base = loc.split("#")[0]
st, _, body = req(srv, "POST", base + "/meet-the-keeper/capture", {"_t": t, "output": "x"})
assert st == 400 and "start the step" in body
for sid in ("read-the-sign",):
req(srv, "POST", f"{base}/{sid}/start", {"_t": t})
req(srv, "POST", f"{base}/{sid}/verify", {"_t": t, "ok": "1"})
req(srv, "POST", f"{base}/{sid}/done", {"_t": t})
req(srv, "POST", base + "/meet-the-keeper/start", {"_t": t})
_, _, body = req(srv, "GET", base)
assert "Capture command and output" in body and "Check against this output" in body
assert req(srv, "POST", base + "/meet-the-keeper/capture", {"_t": t, "command": "echo hi", "output": "hello there"})[0] == 303
_, _, body = req(srv, "GET", base)
assert "hello there" in body and "$ echo hi" in body and "1 saved" in body
st, _, body = req(srv, "POST", base + "/meet-the-keeper/verify-pasted", {"_t": t, "output": "wrong text"})
assert st == 303
_, _, body = req(srv, "GET", base)
assert "Check not passed" in body
req(srv, "POST", base + "/meet-the-keeper/verify-pasted", {"_t": t, "output": "Ada climbs the stairs. Motto on the wall - x"})
_, _, body = req(srv, "GET", base)
assert "Check passed" in body
st, _, body = req(srv, "POST", base + "/meet-the-keeper/capture", {"_t": t, "output": "hvs.ABCDEFGHIJKLMN"})
assert st == 400 and "secret-looking" in body