/**
 * RealChannelDriver — the production `ChannelDriver` for the LiveTestHarness
 * (docs/specs/live-user-channel-proof-standard.md §5.4 "Platform-Sanctioned
 * Automation"). It drives a feature end-to-end through the REAL user surfaces by
 * composing one `SurfaceSender` per surface (Telegram, Slack, dashboard) plus:
 *
 *   - a DemoChannelRegistry → `isDemoChannel` (§5.3 isolation), and
 *   - a `resolveResponderMachine` reader → the `responderMachineId` stamped on every
 *     reply, which is the DETERMINISTIC cross-machine proof the harness asserts on
 *     (e.g. "after the transfer, the reply was served FROM the Mini").
 *
 * The driver itself is pure transport composition: it knows nothing about HTTP,
 * Telegram, or Slack — each surface sender + the placement reader are injected, so
 * this module is fully unit-testable with fakes. The real senders (a demo-bot/user
 * Telegram sender, a Slack user-token sender) and the real placement reader (a
 * GET /pool/placement call) are wired at construction in server.ts.
 *
 * Safety: a surface with no registered sender is a hard error on use (never a silent
 * skip that would fabricate a "no reply" FAIL), and `responderMachineId` resolution
 * failures degrade to `undefined` (the harness then simply can't assert on responder)
 * rather than throwing the whole scenario — the SEND/REPLY evidence is still recorded.
 */
export class RealChannelDriver {
    d;
    constructor(deps) { this.d = deps; }
    log(m) { this.d.logger?.(`[real-channel-driver] ${m}`); }
    senderFor(surface) {
        const s = this.d.senders[surface];
        if (!s) {
            // A missing sender is a CONFIGURATION error, surfaced loudly — never a silent
            // skip that the harness would misread as a clean "no reply" FAIL.
            throw new Error(`no real sender configured for surface "${surface}" — cannot drive it`);
        }
        return s;
    }
    isDemoChannel(surface, channelId) {
        return this.d.demoRegistry.isDemoChannel(surface, channelId);
    }
    async send(surface, channelId, text) {
        return this.senderFor(surface).send(channelId, text);
    }
    async awaitReply(surface, channelId, opts) {
        const reply = await this.senderFor(surface).awaitReply(channelId, opts);
        if (!reply)
            return null;
        let responderMachineId;
        try {
            responderMachineId = (await this.d.resolveResponderMachine(surface, channelId)) ?? undefined;
        }
        catch (err) {
            // Degrade, never throw: we still have a real reply; we just can't attribute the
            // responder machine this round. The harness records the reply evidence and
            // (only) any responder-machine assertion can't be satisfied.
            this.log(`responder-machine resolve failed for ${surface}:${channelId} (recording reply without it): ${err instanceof Error ? err.message : String(err)}`);
            responderMachineId = undefined;
        }
        return { ...reply, responderMachineId };
    }
}
//# sourceMappingURL=RealChannelDriver.js.map