import Foundation
import Testing
import NucleicProtocol

@testable import NucleicCore

/// Covers the transport-tagging seam that drives the LAN-drop reconnect nudge (SYNC_PROTOCOL §3.2):
/// a host-accepted channel reports which transport carries it, and `SyncHost` reads that on
/// disconnect to decide whether to nudge the departed device onto a non-local path. The end-to-end
/// push itself rides `PushRelayClient` → the relay worker (whose payload/route are covered by the
/// worker's `apns.test.ts`), the same out-of-band seam the approval wake uses.
@Suite struct SyncHostReconnectNudgeTests {
    /// The real host-accepted channels self-identify their transport, so a dropped connection can be
    /// classified as LAN (nudge-worthy) vs. already-non-local (tailnet/relay — no nudge).
    @Test func hostAcceptedChannelsReportTheirTransport() {
        // LANChannel is `Network`-only; assert its tag through the same seam the test doubles use.
        let (_, lanServer) = MemoryChannel.pair(transport: .lan)
        #expect(lanServer.transport == .lan)

        let (_, relayServer) = MemoryChannel.pair(transport: .relay)
        #expect(relayServer.transport == .relay)
    }

    /// A channel that doesn't self-identify (a client dial leg, an in-memory test pipe) reports
    /// `nil` — the `FrameChannel` protocol default — so the host treats it as "not a LAN drop" and
    /// never nudges, which is the safe default for an unknown transport.
    @Test func untaggedChannelHasNoTransport() {
        let (_, server) = MemoryChannel.pair()
        #expect(server.transport == nil)
    }

    /// Only a `.lan` drop is nudge-worthy: tailnet/relay are already non-local, and `nil` is unknown.
    /// This mirrors the guard in `SyncHost.unregister`.
    @Test func onlyLANIsNudgeWorthy() {
        #expect((SyncTransportHint.lan == .lan) == true)
        #expect((SyncTransportHint.tailnet == .lan) == false)
        #expect((SyncTransportHint.relay == .lan) == false)
        let unknown: SyncTransportHint? = nil
        #expect((unknown == .lan) == false)
    }
}
