# ADR 0004: Harness-neutral bridge core and pluggable adapters

## Status

Accepted — architecture direction. Behavioral migration is phased; current Pi adapter remains compatibility surface.

## Decision

AMQ Bridge has one harness-neutral core and two adapter seams:

```text
harness adapter → bridge core → transport adapter → mailbox/backend
```

The first supported path is:

```text
Pi adapter → bridge core → AMQ filesystem transport
```

Future paths use the same core protocol:

```text
OpenCode/Codex adapter → bridge core → AMQ filesystem transport
Pi adapter → bridge core → future transport
```

## Core owns

- canonical message identity, refs, threads, kinds, and priorities;
- notify-pull receive semantics;
- explicit read/reply/resolve operations;
- processed, active, completed, retry, and recovery state;
- ownership/lease rules and handoff;
- presence freshness and trust policy;
- normalized events and diagnostics.

Core must not import Pi, OpenCode, Codex, TUI, or concrete transport APIs.

## Harness adapter owns

- host lifecycle hooks;
- context injection/follow-up behavior;
- tool and command registration;
- host-specific status rendering;
- model-turn scheduling and interruption capabilities;
- session/transcript persistence.

A harness cannot claim capabilities it does not implement. Presence advertises capabilities; it does not authorize actions.

## Transport adapter owns

- send/list/watch/read/reply/resolve primitives;
- mailbox-specific paths and CLI behavior;
- transport retry and watch mechanics;
- discovery implementation where available.

Transport notifications contain envelopes, never bodies. Core obtains bodies only through explicit `read(messageId)`.

## Identity model

Logical participant identity is separate from runtime identity:

- `participantId`: stable agent identity (`bp`, `ab`);
- `instanceId`: current harness incarnation;
- `leaseId`/epoch: current owner claim.

PID, CWD, Pi session key, and transcript entry are implementation metadata, not protocol identity.

## Lifecycle invariants

1. One owner per `(transport root, participantId)`.
2. Only owner injects notifications and mutates queue state.
3. Secondary sessions are read-only until takeover.
4. Presence is advisory, TTL-bound, and never the sole authorization proof.
5. Reload rotates runtime identity without deleting unfinished work.
6. Active work survives `read`, reload, and owner handoff until explicit completion, cancellation, or abandonment.
7. Reply and resolve are idempotent operations targeted by explicit message ID.

## Migration rules

- Preserve current Pi commands, tools, state migration, and AMQ compatibility exports.
- Extract contracts before moving implementations.
- Keep sidecar drain behavior separate until its own migration.
- Do not add broker/server infrastructure as part of this migration.

## Consequences

Pi remains first-class, but no longer defines protocol semantics. OpenCode and Codex adapters can use the same core without sharing Pi transcript assumptions. Existing filesystem mailbox behavior remains usable while stronger lifecycle guarantees are added incrementally.

## Acceptance

The architecture is considered usable when two different harness adapters can exchange exact messages over one transport, survive reload/takeover without losing unfinished work, and produce independent mailbox/state evidence.
