ClientsFlow pipeline · autonomous E2E test runner

Continuous funnel test → Stripe TEST payment

Branch feature/funnel-automation · live app matyas--clientsflow-pipeline-web.modal.run · 2026-06-20 · ZZ sentinels only

RESULT — GREEN. One unbroken run drove the whole funnel from a real cold email to a received Stripe TEST payment (deposit_paid), self-healing one real product bug + one harness bug along the way. 191 pytest green throughout; deployed v051→v052. A second round then fixed a DocuSeal-sweep safety bug and ran a 20-check Phase-2 layer.

The continuous happy path run_002 · 10 steps · green

Each leg was driven against the real production handlers and asserted before the next. Deal deal_2d460d341b50 — "ZZ E2E — Happy B" (matyas.sarudi00+zze2eb).

#LegHow it was drivenProof
1Cold emailReal HU email matyas@clientsflow.hu+zze2ebGmail msg id returned
2Reply → New-Lead cardReal reply sent; live /missive/incoming handler driven (cold-inbox account)Deal minted, stage new_lead, Notion CRM page created
3Booking/dash/api/call/schedule (GHL retired → dashboard path)Stage booked; Google Meet + invite email delivered
4Call / transcriptHU transcript → /dash/api/transcriptai.extract_transcript_extract: price 450 000 Ft, deposit 225 000, confidence high
5Post-call wizardStep 2 AI proposal preview → step 3 eager DocuSealProposal generated; DocuSeal both sign links + Stripe link (fix)
6Sign bothClient + rep DocuSeal embeds signed via Chrome DevTools MCP"Document has been signed!" ×2 → signed=True, contract_signed
7Proposal email (human gate)/dash/api/seq/arm — the explicit operator actionproposal_chase armed; email queued into the send window (weekend-throttled, by design)
8Stripe TEST paymentCard 4242 on the hosted checkout via Chrome DevTools MCP"Thanks for your payment"; webhook → deposit_paid, paid=True, onboarding fired

Bugs found & fixed self-healed

The runner fixed code, redeployed via snap_deploy.sh, kept 191 pytest green, and (for the funnel bug) restarted the run from scratch.

WhatTypeRoot causeFix
Missing deposit Stripe link in the wizardProductThe post-call wizard (preview→step3) never minted the deposit Stripe link — only the legacy /review page-1 did. So the DocuSeal doc, proposal email & step-3 panel all lost the payment link.flows.ensure_deposit_stripe_link() called inside ensure_docuseal_submission() (parity with /review). v051.
Evidence HTML always emptyHarnesse2e_evidence.py built each step but never appended it to steps[].One-line append fix.
ZZ-DocuSeal sweep was a silent no-opSafetye2e_reset.py detected submissions via a board field the API never exposed → the mandated post-attempt DocuSeal archive never ran. A stale cross-container cache also made the verify lie.Board now exposes has_docuseal; reset detects via it and reads fresh=1. v052. Verified end-to-end.

Phase 2 — rigorous board-card-qa layer 18 / 20 pass

Playwright DOM + API assertions across the funnel mechanics & scenarios (ZZ-gated, send-blocklisted). The 2 "fails" are stale tests, not product bugs.

R3A1/A4/A5 — step-2 preview, [bracket] template, variables, re-render vs AI R3B1/B2/B3/B5/B6 — step-3 DocuSeal both links + Stripe + proposal-email link + define&arm gate + rigorous create→archive I1/I2 — client-stage vs new-lead (ADR-0004) OC3 · K1 · R3C3 · Q1 · E2 · CL1 · HD1 · G1
The 2 stale tests (not product bugs): PC4 waits for #pc-email-draft, an element the R3 split-pane redesign retired — the proposal-email draft now lives in the seq-editor #se-body (covered by R3B3, PASS). B1 seeds a long inbound on S4, but S4 has a logged call-note last_touch that — by the intended LC2 rule ("last_touch wins over last_msg") — correctly renders instead; no truncation exists. The Playwright capture wave's S11 hit the same class of staleness (a step looking for the "Move" button that was intentionally removed — board-card-qa A2 asserts its absence).

Planning & execution weak points

Why some data was missing / testing was thinner than ideal — and what the second round tackled.

Weak pointImpactDisposition
"Real reply → Missive" (Q4=A) locked without verifying feasibilityThe cold-outreach inbox that mints a card isn't authed on the MCP and Missive's webhook is uncontrollable → the fully-real path isn't achievable autonomously.Drove the real production handler via the team's journey_e2e.py inject (only the Missive mailbox-sync hop substituted) + sent a genuine cold email & reply. Flagged transparently.
Stale "use /ghl/event for booking" guidancehandle_ghl_event is an inert stub (GHL retired).Used the live dashboard /dash/api/call/schedule path.
Instance 2 (techspec) never ran — no checklist / per-leg assertion listThe runner derived legs + assertions live, discovering the Stripe-link defect by hitting it.Legs + assertions reconstructed from the code; defect found & fixed.
Harness shipped "smoke-tested" but buggy (evidence append; reset DocuSeal sweep)Empty evidence; safety sweep silently did nothing.Both fixed & verified in this run.
My driver mistakes (preview missing email; passed problems dicts as strings)Two wasted wizard calls.Corrected; not app bugs. Lesson: inspect extract field types before building inputs.

Still open (documented, lower priority)

Not yet exercised: the proposal email's delivered contents (it's correctly weekend-throttled, so only the queued state was observed); the sequence-copy-edit-then-reuse-next-session flow; the legacy /review page-1 path; the onboarding email/portal artifact (stage reached deposit_paid but portal:false). The 2 stale board-card-qa tests (PC4, B1) and the journey S11 "Move" step are left for the team to retire/retarget — editing the assertions just to pass would be gaming them.

Evidence artifacts

FileWhat
.tmp/e2e/run_002_*.htmlThe green run — screen-to-screen, think-aloud, 10 steps, screenshots
.tmp/e2e/run_001_*.htmlThe failed→fixed attempt (red callout at the missing Stripe-link leg)
.tmp/journey-qa/v3_journeys_qa.htmlPlaywright capture wave (S10 clean; S11 stale "Move" step)
plans/e2e-continuous-journey-test/RETROSPECTIVE.mdFull retrospective + second-round plan