Two distinct Anvil contexts are in use; they target different networks.
### Dev stack Anvil (docker-compose)
The `anvil` service in `docker-compose.yml` runs `containers/anvil-entrypoint.sh`, which forks:
```
${FORK_URL:-https://sepolia.base.org}
```
**Default: Base Sepolia.** Uniswap V3 contracts are re-deployed fresh by the `bootstrap` service at start-up, so the fork target only affects block history and chain-id context. The bootstrap deploys all protocol contracts (Kraiken, Stake, LiquidityManager, OptimizerProxy) at addresses written to `tmp/containers/contracts.env`.
To fork Base mainnet instead (required for red-team / backtesting — see below):
```bash
FORK_URL=https://mainnet.base.org docker compose up -d
`red-team.sh` boots the docker-compose stack and then calls protocol operations using **Base mainnet** addresses for the Uniswap V3 periphery (V3_FACTORY, SwapRouter02, NonfungiblePositionManager). These addresses are only valid on a mainnet fork. Before running red-team.sh, set:
`FitnessEvaluator.t.sol` is completely independent of the dev Anvil. It forks Base mainnet once per `forge test` run using the `BASE_RPC_URL` environment variable and has no relationship to the docker-compose stack:
| Variable | Default | Set in docker-compose | Purpose |
|---|---|---|---|
| `VITE_ENABLE_LOCAL_SWAP` | `false` (unset) | `true` | Show inline ETH→$KRK swap widget on Get KRK page instead of the Uniswap link. Enable for local dev; leave unset for production builds. |
The Playwright test setup (`tests/setup/stack.ts`) reads stack coordinates from env vars, falling back to `onchain/deployments-local.json` when they are absent.
When all three of `STACK_KRAIKEN_ADDRESS`, `STACK_STAKE_ADDRESS`, and `STACK_LM_ADDRESS` are set, the deployments file is not read at all, which allows tests to run in containerised environments that have no local checkout.