# Reproduce evidence pass 2

Target: [#27798](https://git.cafe/pingdotgg/t3code/pull/27798). After cffa192a07c19b904aea4c22a5f16276159cb56a; before actual merge-base d8a829e5ecd6626f8fdee23ef20ca9758e056251.

This archive contains scratch evidence drivers, not product changes. Download into an empty directory, read before running. Some scripts deliberately contain the capture VM's absolute paths/ports/session names. Use a fresh timestamped output directory for every run and adapt those paths; never overwrite previous raw captures. No live T3 state is an input. Every dev command MUST have T3CODE_DEV_SEED=0. Never use migrate-dev-db on this VM.

1. git -C ~/t3code fetch -q origin main; compute git merge-base cffa192a07 origin/main, verify the before SHA above. Make detached ../wt/pr-27798-before2 and after2, vp install each. Do not use the lead checkout.
2. Run fixture.sh. It clones only public microsoft/TypeScript and pins main AND origin/main to 042e0fb9574980bd67964165df295e629f834fe3, clean, ahead0/behind0. Both environments register this identical fixture directory as a project via real app RPC. Do not copy any ~/.t3 database. Create fresh per-checkout .t3 with T3CODE_DEV_SEED=0 vp run dev --host0.0.0.0. Read actual ports from dev-runner output (captured before backend16468/web8428; after backend14657/web6617). Pair with each server's own CLI. Do not upload pairing URLs, raw server logs, or credentials.
3. capture-proxy.mjs inserts page-driver.js before app boot on localhost18181/18182 and proxies WS unchanged. Date is fixed to 2026-11-03T00:00Z; sessionStorage.captureHold=1 holds PR WS callbacks AND fetch completion for /api/pull-requests/diff. sessionStorage.captureHold=0; __capture.release() releases. Payloads are preserved. IndexedDB is the real app t3code:connection-runtime/query store. Seed/prime queries by opening actual UI tabs and expanding code before reload.
4. Run seed-thread.js in authenticated app; seedEvidenceThread(projectId) creates only synthetic stopped evidence-27798-thread and its public 65119 link. P4 thread card uses this state. Both git-control reads run unheld and settle. Later M11 seed-stack.js adds public65017 and schema-valid HARNESS stack snapshots via thread.pull-request-link.sync; stack is synthetic, never a forge write. Clear stack:null before non-stack static captures.
5. P3 web: real Preview1440x900 dark, DPR2, fonts100; whole tool output1280x800. Prime Summary/Timeline/Code including expanded diff, hold, reload, inspect each tab, release, return Summary, clear pointer. p3-actions.js/page-driver.js record timestamps. Save trace with PR methods only. No reduced-motion API is exposed by Preview. P2 timed pointer switched after two failed Preview actions to existing Playwright Chromium148. pointer-capture.mjs drives trusted browser mouse moves through five cold rows, records .webm and pointer/RPC trace. Superseded Preview-hover/drag and synthetic/slow attempts are NOT proof.
6. Desktop: vp run build:desktop; node node_modules/electron/install.js once. start-desktop.sh under headless-desktop launches each real Electron --no-sandbox --disable-gpu, own XDG config/T3 home, CDP19321/19322. Native protocol t3code://app/ . desktop-control.mjs seeds/sets light; native-desktop-capture.mjs installs the same gate before reload, inspects Summary/Timeline/Code, records15fps x11grab, import captures whole1440x900 window. Reduced motion is emulated through CDP.
7. Native: vp run mobile:install ios --prepare in after checkout. Both SHAs have fingerprint887f84d7e8ee2e1063658bf884c9d17f60d6cbb3. Lease iPhone17Pro and iPadPro13-inch(M5) with device-pool. Always same session/cwd. Install via vp run mobile:install ios --session; when root cwd owns lease, invoke the SAME exact checkout script from root: vp exec node /home/ubuntu/wt/pr-27798-after2/scripts/mobile-native-client.ts ensure ios --session <s>. This avoids DEVICE_IN_USE caused by lease ownership at another cwd. Never manually fetch native cache.
8. Import original/mobile-driver.js from apps/mobile/.generated/evidence-driver.js as first import of apps/mobile/index.ts. It freezes Date and delays detail RPC replies6000ms equally. For M11 mobile-stack-driver.js also holds stack answers600000ms equally to preserve the synthetic stack; label HARNESS. Start Metro each checkout on8083/8084, REACT_NATIVE_PACKAGER_HOSTNAME=100.126.160.69, host all interfaces. pair-mobile.py creates a private pairing link and opens it without printing it. Wait app ready before another deep link: links sent during JS download may be lost.
9. P6: open evidence thread, branch sheet, tap linked65119 card. Before is full-screen loading, after seeded known summary. P6-final clips use source P6-correct-before and P6-after, the correct own backend on each side with only the65119 source link. Later multi-link attempts are excluded. P6-final-edit.json records trims; full surfaces remain. M11 capture-stack.py records stack card->65017. M12 capture-expired-tab.py records return to PRs after >=305s away, with actual timestamp assertion; warm quick-tab attempts were negative controls and not accepted as proof. The iPad lease expired before its first cold test and had to be reopened/reinstalled/repaired.
10. Still procedure: network idle/fonts ready on web/Electron, native detail settled. Two full images >=500ms apart must be RGB-identical. Native static captures use ReduceMotion/ReduceTransparency and warm re-entry to the same already-loaded PR: initial spinner-vs-seed entry leaves different Liquid Glass edge rendering even after data settles, so those pairs are rejected. native-matched-stills.py aligns clock to one natural OS minute after warming. Pool offers temporary --normalize-status-bar but no persistent rawsimctl clock override; normalization animated the battery and was discarded. No pixels or chrome are cropped/painted over.
11. make-diffs.py produces channel-amplified Diff0 and >8/255 DiffT, plus settled status. assemble-pass2.py labels full pair sheets with exact SHAs. Open every accepted capture/diff/contact sheet manually before upload. upload-pass2.py runs ghdrop upload -m for each explicit file, retains exact stdout in ghdrop-output-verbatim.md. Raw logs with tokens and native app state never enter uploads. extract-physical-traces.py extracts only relevant public GraphQL spans.
12. Stop only own captured spawn/port PIDs (confirm cwd), close own Preview tabs and both pool sessions. Remove own detached worktrees and scratch only after uploading all accepted evidence, scripts, notes and raw synthetic traces. Do not touch lead checkout or other sessions.

Native recordings use the actual OS clock and are labelled with their differences. A screenshot-only temporary9:41 normalization is not represented as a frozen recording clock. No record is claimed to compare browser and native pixel output.

Final outcome: P6-accessible and M11-accessible are accepted native stills, with actual ReduceMotion/ReduceTransparency verified on only after coordinate taps at339,160 and339,403. P6-matched is superseded because accessibility switches were still off. M12 remains UNVERIFIED: both idle leases ended, process restart lost selection, and pending/warm tab-return diagnostics still showed detail on before. Do not represent M12 diagnostics as positive proof. Native recordings precede verified setting changes; their settings are described separately from accepted stills.
