Skip to content
This repository has been archived by the owner on Sep 6, 2022. It is now read-only.

add connection gating interfaces and types. #139

Merged
merged 11 commits into from
May 13, 2020
90 changes: 90 additions & 0 deletions connmgr/gater.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,90 @@
package connmgr

import (
ma "github.com/multiformats/go-multiaddr"

"github.com/libp2p/go-libp2p-core/control"
"github.com/libp2p/go-libp2p-core/network"
"github.com/libp2p/go-libp2p-core/peer"
)

// ConnectionGater can be implemented by a type that supports active
// inbound or outbound connection gating.
//
// ConnectionGaters are active, whereas ConnManagers tend to be passive.
//
// A ConnectionGater will be consulted during different states in the lifecycle
// of a connection being established/upgraded. Specific functions will be called
// throughout the process, to allow you to intercept the connection at that stage.
//
// InterceptPeerDial is called on an imminent outbound peer dial request, prior
// to the addresses of that peer being available/resolved. Blocking connections
// at this stage is typical for blacklisting scenarios.
//
// InterceptAddrDial is called on an imminent outbound dial to a peer on a
// particular address. Blocking connections at this stage is typical for
// address filtering.
//
// InterceptAccept is called as soon as a transport listener receives an
// inbound connection request, before any upgrade takes place. Transports who
// accept already secure and/or multiplexed connections (e.g. possibly QUIC)
// MUST call this method regardless, for correctness/consistency.
//
// InterceptSecured is called for both inbound and outbound connections,
// after a security handshake has taken place and we've authenticated the peer.
//
// InterceptUpgraded is called for inbound and outbound connections, after
// libp2p has finished upgrading the connection entirely to a secure,
// multiplexed channel.
//
// This interface can be used to implement *strict/active* connection management
// policies, such as hard limiting of connections once a maximum count has been
// reached, maintaining a peer blacklist, or limiting connections by transport
// quotas.
//
// EXPERIMENTAL: a DISCONNECT protocol/message will be supported in the future.
// This allows gaters and other components to communicate the intention behind
// a connection closure, to curtail potential reconnection attempts.
//
// For now, InterceptUpgraded can return a non-zero DisconnectReason when
// blocking a connection, but this interface is likely to change in the future
// as we solidify this feature. The reason why only this method can handle
// DisconnectReasons is that we require stream multiplexing capability to open a
// control protocol stream to transmit the message.
type ConnectionGater interface {

// InterceptPeerDial tests whether we're permitted to Dial the specified peer.
//
// This is called by the network.Network implementation when dialling a peer.
InterceptPeerDial(p peer.ID) (allow bool)

// InterceptAddrDial tests whether we're permitted to dial the specified
// multiaddr for the given peer.
//
// This is called by the network.Network implementation after it has
// resolved the peer's addrs, and prior to dialling each.
InterceptAddrDial(peer.ID, ma.Multiaddr) (allow bool)

// InterceptAccept tests whether an incipient inbound connection is allowed.
//
// This is called by the upgrader, or by the transport directly (e.g. QUIC,
// Bluetooth), straight after it has accepted a connection from its socket.
InterceptAccept(network.ConnMultiaddrs) (allow bool)

// InterceptSecured tests whether a given connection, now authenticated,
// is allowed.
//
// This is called by the upgrader, after it has performed the security
// handshake, and before it negotiates the muxer, or by the directly by the
// transport, at the exact same checkpoint.
InterceptSecured(network.Direction, peer.ID, network.ConnMultiaddrs) (allow bool)

// InterceptUpgraded tests whether a fully capable connection is allowed.
//
// At this point, the connection a multiplexer has been selected.
// When rejecting a connection, the gater can return a DisconnectReason.
// Refer to the godoc on the ConnectionGater type for more information.
//
// NOTE: the go-libp2p implementation currently IGNORES the disconnect reason.
InterceptUpgraded(network.Conn) (allow bool, reason control.DisconnectReason)
}
File renamed without changes.
9 changes: 9 additions & 0 deletions control/disconnect.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
package control

// DisconnectReason communicates the reason why a connection is being closed.
//
// A zero value stands for "no reason" / NA.
//
// This is an EXPERIMENTAL type. It will change in the future. Refer to the
// connmgr.ConnectionGater godoc for more info.
type DisconnectReason int