mirror of
https://github.com/netbirdio/netbird.git
synced 2026-08-29 02:51:29 +02:00
The relay transport is shared: one connection per relay server carries the streams of every peer using it. When it drops, each of those peers gets a Disconnected verdict from evalConnStatus even when ICE is still carrying its traffic, because peerUsesRelay comes from HasRelayAddress(), which only reports that management offered relay servers, not that we are connected to one. The guard answers Disconnected with the aggressive retry, so every peer starts sending offers over signal for a transport that no offer can restore: the relay client's own guard is what reconnects it. Feed relayManager.Ready() into the status inputs and return PartiallyConnected when ICE is up and the missing side is the shared transport. That is the existing "one path works, the other does not" branch, which retries three times and then hourly instead of walking the exponential ladder forever. Peers are not left waiting for the hourly tick: when the transport comes back, Manager.onServerConnected notifies srWatcher, the guard resets the ticker to 800ms and iceState.reset() clears the hourly mode. The verdict is unchanged when the transport is up but this peer is unreachable over relay - it may have moved to another server, and only an offer carries its new relay address - and in force-relay mode, where relay is the only transport.
46 lines
1.5 KiB
Go
46 lines
1.5 KiB
Go
package peer
|
|
|
|
import (
|
|
log "github.com/sirupsen/logrus"
|
|
)
|
|
|
|
const (
|
|
// StatusIdle indicate the peer is in disconnected state
|
|
StatusIdle ConnStatus = iota
|
|
// StatusConnecting indicate the peer is in connecting state
|
|
StatusConnecting
|
|
// StatusConnected indicate the peer is in connected state
|
|
StatusConnected
|
|
)
|
|
|
|
// connStatusInputs is the primitive-valued snapshot of the state that drives the
|
|
// tri-state connection classification. Extracted so the decision logic can be unit-tested
|
|
// without constructing full Worker/Handshaker objects.
|
|
type connStatusInputs struct {
|
|
forceRelay bool // NB_FORCE_RELAY or JS/WASM
|
|
peerUsesRelay bool // remote peer advertises relay support AND local has relay
|
|
relayConnected bool // statusRelay reports Connected (independent of whether peer uses relay)
|
|
relayTransportConnected bool // the relay transport shared by all peers on that server is up
|
|
remoteSupportsICE bool // remote peer sent ICE credentials
|
|
iceWorkerCreated bool // local WorkerICE exists (false in force-relay mode)
|
|
iceStatusConnecting bool // statusICE is anything other than Disconnected
|
|
iceInProgress bool // a negotiation is currently in flight
|
|
}
|
|
|
|
// ConnStatus describe the status of a peer's connection
|
|
type ConnStatus int32
|
|
|
|
func (s ConnStatus) String() string {
|
|
switch s {
|
|
case StatusConnecting:
|
|
return "Connecting"
|
|
case StatusConnected:
|
|
return "Connected"
|
|
case StatusIdle:
|
|
return "Idle"
|
|
default:
|
|
log.Errorf("unknown status: %d", s)
|
|
return "INVALID_PEER_CONNECTION_STATUS"
|
|
}
|
|
}
|