mirror of
https://github.com/fluencelabs/tendermint
synced 2025-04-25 06:42:16 +00:00
P2P docs
This commit is contained in:
parent
bff93107ef
commit
fa7c83166f
100
p2p/README.md
100
p2p/README.md
@ -1,35 +1,77 @@
|
|||||||
# P2P Module
|
# `tendermint/p2p`
|
||||||
|
|
||||||
P2P provides an abstraction around peer-to-peer communication.<br/>
|
`tendermint/p2p` provides an abstraction around peer-to-peer communication.<br/>
|
||||||
Communication happens via Reactors that react to messages from peers.<br/>
|
|
||||||
Each Reactor has one or more Channels of communication for each Peer.<br/>
|
|
||||||
Channels are multiplexed automatically and can be configured.<br/>
|
|
||||||
A Switch is started upon app start, and handles Peer management.<br/>
|
|
||||||
A PEXReactor implementation is provided to automate peer discovery.<br/>
|
|
||||||
|
|
||||||
## Channels
|
## Peer/MConnection/Channel
|
||||||
|
|
||||||
Each peer connection is multiplexed into channels.
|
Each peer has one `MConnection` (multiplex connection) instance.
|
||||||
The p2p module comes with a channel implementation used for peer
|
|
||||||
discovery (called PEX, short for "peer exchange").
|
|
||||||
|
|
||||||
<table>
|
__multiplex__ *noun* a system or signal involving simultaneous transmission of
|
||||||
<tr>
|
several messages along a single channel of communication.
|
||||||
<td><b>Channel</b></td>
|
|
||||||
<td>"PEX"</td>
|
|
||||||
</tr>
|
|
||||||
<tr>
|
|
||||||
<td><b>Messages</b></td>
|
|
||||||
<td>
|
|
||||||
<ul>
|
|
||||||
<li>pexRequestMsg</li>
|
|
||||||
<li>pexResponseMsg</li>
|
|
||||||
</ul>
|
|
||||||
</td>
|
|
||||||
</tr>
|
|
||||||
</table>
|
|
||||||
<hr />
|
|
||||||
|
|
||||||
## Resources
|
Each `MConnection` handles message transmission on multiple abstract communication
|
||||||
|
`Channel`s. Each channel has a globally unique byte id.
|
||||||
|
The byte id and the relative priorities of each `Channel` are configured upon
|
||||||
|
initialization of the connection.
|
||||||
|
|
||||||
* http://www.upnp-hacks.org/upnp.html
|
There are two methods for sending messages:
|
||||||
|
```go
|
||||||
|
func (m MConnection) Send(chId byte, msg interface{}) bool {}
|
||||||
|
func (m MConnection) TrySend(chId byte, msg interface{}) bool {}
|
||||||
|
```
|
||||||
|
|
||||||
|
`Send(chId, msg)` is a blocking call that waits until `msg` is successfully queued
|
||||||
|
for the channel with the given id byte `chId`. The message `msg` is serialized
|
||||||
|
using the `tendermint/binary` submodule's `WriteBinary()` reflection routine.
|
||||||
|
|
||||||
|
`TrySend(chId, msg)` is a nonblocking call that returns false if the channel's
|
||||||
|
queue is full.
|
||||||
|
|
||||||
|
`Send()` and `TrySend()` are also exposed for each `Peer`.
|
||||||
|
|
||||||
|
## Switch/Reactor
|
||||||
|
|
||||||
|
The `Switch` handles peer connections and exposes an API to receive incoming messages
|
||||||
|
on `Reactors`. Each `Reactor` is responsible for handling incoming messages of one
|
||||||
|
or more `Channels`. So while sending outgoing messages is typically performed on the peer,
|
||||||
|
incoming messages are received on the reactor.
|
||||||
|
|
||||||
|
```go
|
||||||
|
// Declare a MyReactor reactor that handles messages on MyChannelId.
|
||||||
|
type MyReactor struct{}
|
||||||
|
|
||||||
|
func (reactor MyReactor) GetChannels() []*ChannelDescriptor {
|
||||||
|
return []*ChannelDescriptor{ChannelDescriptor{Id:MyChannelId, Priority: 1}}
|
||||||
|
}
|
||||||
|
|
||||||
|
func (reactor MyReactor) Receive(chId byte, peer *Peer, msgBytes []byte) {
|
||||||
|
r, n, err := bytes.NewBuffer(msgBytes), new(int64), new(error)
|
||||||
|
msgString := ReadString(r, n, err)
|
||||||
|
fmt.Println(msgString)
|
||||||
|
}
|
||||||
|
|
||||||
|
// Other Reactor methods omitted for brevity
|
||||||
|
...
|
||||||
|
|
||||||
|
switch := NewSwitch([]Reactor{MyReactor{}})
|
||||||
|
|
||||||
|
...
|
||||||
|
|
||||||
|
// Send a random message to all outbound connections
|
||||||
|
for _, peer := range switch.Peers().List() {
|
||||||
|
if peer.IsOutbound() {
|
||||||
|
peer.Send(MyChannelId, "Here's a random message")
|
||||||
|
}
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
### PexReactor/AddrBook
|
||||||
|
|
||||||
|
A `PEXReactor` reactor implementation is provided to automate peer discovery.
|
||||||
|
|
||||||
|
```go
|
||||||
|
book := p2p.NewAddrBook(config.AddrBookFile())
|
||||||
|
pexReactor := p2p.NewPEXReactor(book)
|
||||||
|
...
|
||||||
|
switch := NewSwitch([]Reactor{pexReactor, myReactor, ...})
|
||||||
|
```
|
||||||
|
@ -34,8 +34,27 @@ type receiveCbFunc func(chId byte, msgBytes []byte)
|
|||||||
type errorCbFunc func(interface{})
|
type errorCbFunc func(interface{})
|
||||||
|
|
||||||
/*
|
/*
|
||||||
A MConnection wraps a network connection and handles buffering and multiplexing.
|
Each peer has one `MConnection` (multiplex connection) instance.
|
||||||
<essages are sent with ".Send(channelId, msg)".
|
|
||||||
|
__multiplex__ *noun* a system or signal involving simultaneous transmission of
|
||||||
|
several messages along a single channel of communication.
|
||||||
|
|
||||||
|
Each `MConnection` handles message transmission on multiple abstract communication
|
||||||
|
`Channel`s. Each channel has a globally unique byte id.
|
||||||
|
The byte id and the relative priorities of each `Channel` are configured upon
|
||||||
|
initialization of the connection.
|
||||||
|
|
||||||
|
There are two methods for sending messages:
|
||||||
|
func (m MConnection) Send(chId byte, msg interface{}) bool {}
|
||||||
|
func (m MConnection) TrySend(chId byte, msg interface{}) bool {}
|
||||||
|
|
||||||
|
`Send(chId, msg)` is a blocking call that waits until `msg` is successfully queued
|
||||||
|
for the channel with the given id byte `chId`. The message `msg` is serialized
|
||||||
|
using the `tendermint/binary` submodule's `WriteBinary()` reflection routine.
|
||||||
|
|
||||||
|
`TrySend(chId, msg)` is a nonblocking call that returns false if the channel's
|
||||||
|
queue is full.
|
||||||
|
|
||||||
Inbound message bytes are handled with an onReceive callback function.
|
Inbound message bytes are handled with an onReceive callback function.
|
||||||
*/
|
*/
|
||||||
type MConnection struct {
|
type MConnection struct {
|
||||||
|
@ -10,18 +10,13 @@ import (
|
|||||||
"github.com/tendermint/tendermint/p2p/upnp"
|
"github.com/tendermint/tendermint/p2p/upnp"
|
||||||
)
|
)
|
||||||
|
|
||||||
/*
|
|
||||||
Listener is part of a Server.
|
|
||||||
*/
|
|
||||||
type Listener interface {
|
type Listener interface {
|
||||||
Connections() <-chan net.Conn
|
Connections() <-chan net.Conn
|
||||||
ExternalAddress() *NetAddress
|
ExternalAddress() *NetAddress
|
||||||
Stop()
|
Stop()
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
// Implements Listener
|
||||||
DefaultListener is an implementation of Listener.
|
|
||||||
*/
|
|
||||||
type DefaultListener struct {
|
type DefaultListener struct {
|
||||||
listener net.Listener
|
listener net.Listener
|
||||||
extAddr *NetAddress
|
extAddr *NetAddress
|
||||||
|
@ -11,8 +11,6 @@ import (
|
|||||||
"time"
|
"time"
|
||||||
)
|
)
|
||||||
|
|
||||||
/* NetAddress */
|
|
||||||
|
|
||||||
type NetAddress struct {
|
type NetAddress struct {
|
||||||
IP net.IP
|
IP net.IP
|
||||||
Port uint16
|
Port uint16
|
||||||
|
@ -10,8 +10,6 @@ import (
|
|||||||
. "github.com/tendermint/tendermint/common"
|
. "github.com/tendermint/tendermint/common"
|
||||||
)
|
)
|
||||||
|
|
||||||
/* Peer */
|
|
||||||
|
|
||||||
type Peer struct {
|
type Peer struct {
|
||||||
outbound bool
|
outbound bool
|
||||||
mconn *MConnection
|
mconn *MConnection
|
||||||
|
@ -4,9 +4,7 @@ import (
|
|||||||
"sync"
|
"sync"
|
||||||
)
|
)
|
||||||
|
|
||||||
/*
|
// IPeerSet has a (immutable) subset of the methods of PeerSet.
|
||||||
IPeerSet has a (immutable) subset of the methods of PeerSet.
|
|
||||||
*/
|
|
||||||
type IPeerSet interface {
|
type IPeerSet interface {
|
||||||
Has(key string) bool
|
Has(key string) bool
|
||||||
List() []*Peer
|
List() []*Peer
|
||||||
@ -15,10 +13,8 @@ type IPeerSet interface {
|
|||||||
|
|
||||||
//-----------------------------------------------------------------------------
|
//-----------------------------------------------------------------------------
|
||||||
|
|
||||||
/*
|
// PeerSet is a special structure for keeping a table of peers.
|
||||||
PeerSet is a special structure for keeping a table of peers.
|
// Iteration over the peers is super fast and thread-safe.
|
||||||
Iteration over the peers is super fast and thread-safe.
|
|
||||||
*/
|
|
||||||
type PeerSet struct {
|
type PeerSet struct {
|
||||||
mtx sync.Mutex
|
mtx sync.Mutex
|
||||||
lookup map[string]*peerSetItem
|
lookup map[string]*peerSetItem
|
||||||
|
@ -22,19 +22,10 @@ type Reactor interface {
|
|||||||
//-----------------------------------------------------------------------------
|
//-----------------------------------------------------------------------------
|
||||||
|
|
||||||
/*
|
/*
|
||||||
All communication amongst peers are multiplexed by "channels".
|
The `Switch` handles peer connections and exposes an API to receive incoming messages
|
||||||
(Not the same as Go "channels")
|
on `Reactors`. Each `Reactor` is responsible for handling incoming messages of one
|
||||||
|
or more `Channels`. So while sending outgoing messages is typically performed on the peer,
|
||||||
To send a message, serialize it into a ByteSlice and send it to each peer.
|
incoming messages are received on the reactor.
|
||||||
For best performance, re-use the same immutable ByteSlice to each peer.
|
|
||||||
You can also use a TypedBytes{} struct for convenience.
|
|
||||||
You can find all connected and active peers by iterating over ".Peers().List()".
|
|
||||||
".Broadcast()" is provided for convenience, but by iterating over
|
|
||||||
the peers manually the caller can decide which subset receives a message.
|
|
||||||
|
|
||||||
Inbound messages are received by calling ".Receive()".
|
|
||||||
The receiver is responsible for decoding the message bytes, which may be preceded
|
|
||||||
by a single type byte if a TypedBytes{} was used.
|
|
||||||
*/
|
*/
|
||||||
type Switch struct {
|
type Switch struct {
|
||||||
reactors []Reactor
|
reactors []Reactor
|
||||||
|
5
p2p/upnp/README.md
Normal file
5
p2p/upnp/README.md
Normal file
@ -0,0 +1,5 @@
|
|||||||
|
# `tendermint/p2p/upnp`
|
||||||
|
|
||||||
|
## Resources
|
||||||
|
|
||||||
|
* http://www.upnp-hacks.org/upnp.html
|
Loading…
x
Reference in New Issue
Block a user