# Internet Missing-Index Interference SOP

This operation measures a real Ride, Food, or Mart business lookup with its
production secondary index present or deliberately omitted. It uses the generic
Operation lifecycle delivered by Issue #65; no case-specific executor path or
public stage is added.

## Business cases

| Case | Business behavior | Exact production index |
|---|---|---|
| `ride_order_history` | Consumer ride-order status history used by support and trip tracking | `ride_order.i_ride_order_consumer_created(consumer_account_id, created_at, order_id)` |
| `food_merchant_order_queue` | Merchant preparation queue ordered by promised deadline | `food_order.i_food_order_merchant_state(merchant_id, state, promised_deadline, order_id)` |
| `mart_order_history` | Consumer retail-order fulfillment history used by customer service | `mart_order.i_mart_order_consumer_created(consumer_account_id, created_at, order_id)` |

Each case binds a real parameter from the prepared database. The paired
`indexed` and `missing` runs use the exact same SQL, arguments, page size,
parameter digest, and prepared snapshot identity.

## Configuration

Ride-only indexed state:

```yaml
operations:
  - id: missing_index
    enabled: true
    prepare:
      page_size: 20
    runtime:
      domains: [ride]
      index_state: indexed
      concurrency_per_case: 1
      offered_qps_per_case: 0.2
      start_after_foreground_ready_seconds: 30
      duration_seconds: 180
      query_timeout_seconds: 30
      max_samples_per_case: 32
```

Food-only missing state changes only these values:

```yaml
    runtime:
      domains: [food]
      index_state: missing
```

`domains` supports one domain or a domain subset. `case_ids` may explicitly
select only the corresponding fixed cases. Domain selection and explicit case
selection replace, rather than extend, stale values from the compiled default.

## Fail-closed evidence

Prepare requires every selected index to exist and verifies its exact ordered
columns from `INFORMATION_SCHEMA.STATISTICS`. It selects one real business key
through a primary-key-leading bounded lookup and retains the indexed `EXPLAIN
ANALYZE` plan.

The `missing` state declares one automatic, target-cluster-once,
before-foreground DDL action. The action:

1. rechecks the exact production index;
2. drops only that named index;
3. proves it is absent;
4. runs `EXPLAIN ANALYZE` for the frozen SQL and arguments;
5. requires a `TableFullScan` without the expected index and actual-row work
   greater than the indexed path.

Workers retain bounded per-attempt latency, drained rows, session-RU provider
evidence, scheduling counters, errors, and cancellation. Session RU is the
statement measurement provider; `ru_v2` is the model identity.

Cleanup always receives the generic opt-in control SQL session. It recreates
any absent production index using its exact name and ordered columns, then
rechecks the metadata. A different existing definition or failed restoration
fails cleanup and blocks the next clean baseline.

## Pair review

Only compare runs when all of the following match:

- `snapshot_identity`;
- `parameter_digest`;
- statement SQL digest and page size;
- concurrency, offered QPS, timeout, and stable window;
- build and prepared data authority.

The intended causal difference is the exact index state. The experiment does
not require a fixed RU or latency ratio. Plan/work amplification is mandatory;
RU and latency are measured outcomes.

## Artifacts

- Prepare binding: `prepare/operations/internet/platform/missing_index/`
- Drop/plan evidence: `run/operations/internet/platform/missing_index/actions/`
- Worker/final receipts: `run/operations/internet/platform/missing_index/receipts/`
- Restoration evidence: `run/operations/internet/platform/missing_index/cleanup-index-restoration.json`
- Cleanup status: `cleanup/operations/internet/platform/missing_index/cleanup.json`

Recovery and rerun-cleanup attempts do not resolve or launch the operation.
Formal 50 GiB execution requires a separately approved E2E run.
