# Dashboard process identity verification

Use this when maintaining read-only paper-trading dashboards or scorecards that report whether strategy bots are running.

## Problem

A persisted `bot.pid` file can become stale. `os.kill(pid, 0)` only proves that *some* process currently has that PID; after PID reuse it may be an unrelated process. Reporting `running=yes` from that alone can make blocked or stopped strategies appear active in scorecards.

## Durable fix pattern

For each experiment directory:

1. Read `bot.pid`.
2. Check the PID exists.
3. Read `/proc/<pid>/environ`.
4. Mark the bot running only when all expected identity/mode fields match:
   - `CTB_STRATEGY_ID == <experiment dir name>`
   - `CTB_RUNTIME_DIR == <that exact experiment directory>`
   - `CTB_PAPER_TRADING == true`
   - `CTB_DRY_RUN == false`

This keeps dashboards read-only while preventing false process-liveness claims.

## Regression test

Add a test that writes the current test process PID into an experiment `bot.pid`. The current test process is alive, so `os.kill(pid, 0)` would pass, but it is not the strategy process. The dashboard must report `running is False`.

Example assertion shape:

```python
(exp / "bot.pid").write_text(str(os.getpid()), encoding="utf-8")
snapshot = build_dashboard_snapshot(runtime_dir=runtime)
assert snapshot.paper_bots[0].pid == os.getpid()
assert snapshot.paper_bots[0].running is False
```

## Verification checklist

- Scorecard `running=yes/no` agrees with actual `AutoTrader.py` process env, not just PID-file existence.
- Focused paper fleet watchdog remains stricter than the dashboard: exact expected strategy IDs, no unexpected strategy IDs, and paper-only env flags.
- Relevant dashboard/scorecard tests pass after changes.
