Documentation
¶
Overview ¶
Package router is a networking-inspired routing model. It's useful for muxing and lots of other things. It enables you to construct your abstractions as you would compose computer networks (endpoints, switches, routing tables). These could represent processing workers, entire subsystems, or even real computers ;).
Index ¶
Constants ¶
This section is empty.
Variables ¶
var ErrNoRoute = errors.New("routing error: no route")
ErrNoRoute signals when there is no Route to a destination
Functions ¶
func HammingDistance ¶
HammingDistance is a DistanceFunc that interprets Addresses as strings and uses their Hamming distance. Return -1 if the Addresses are not strings, or strings length don't match.
Types ¶
type Address ¶
type Address interface{}
Address is our way of knowing where we're headed. Traditionally, addresses are things like IP Addresses, or email addresses. But filepaths, or URLs can be seen as addresses too. We really leave it up to you. Our routing is general, and forces you to pick an addressing scheme, and some logic to discriminate addresses that you'll plug into Routers (Address DistanceFunc).
type DistanceFunc ¶
DistanceFunc returns a measure of distance between two Addresses. Examples: - masked longest prefix match (IP, CIDR) - XOR distance (Kademlia)
type Node ¶
type Node interface { // Address returns the node's address. Address() Address // HandlePacket receives a packet sent by another node. HandlePacket(Packet, Node) error }
Node is an object which has interfaces to connect to networks. This is an "endpoint" object.
type Packet ¶
type Packet interface { // Destination is the Address of the endpoint this Packet is headed to. // They could use the same Addressing throughout (recommended) like the // internet, or face the pain of translating addresses at inter-network // gateways. Destination() Address // Payload is here for completeness. This can be the Packet itself, but this // function encourages the client to think through their packet design. Payload() interface{} }
Packet is the unit of moving things in our network. Anything can be routed in our network, as long as it has a Destination.
type QueueNode ¶
type QueueNode struct {
// contains filtered or unexported fields
}
QueueNode is a trivial node, which accepts packets into a queue
func NewQueueNode ¶
NewQueueNode constructs a node with an internal chan Packet queue
func (*QueueNode) HandlePacket ¶
HandlePacket consumes the incomng packet and adds it to the queue.
type Router ¶
type Router interface { // Route decides how to route a Packet. // It returns the next hop Node chosen to send the Packet to. // Route may return nil, if no route is suitable at all (equivalent of drop). Route(Packet) Node }
Router is an object that decides how a Packet should be Routed. This should be as close to a static table lookup as possible, meaning it would be best to prepare a forwarding table in parallel, instead of blocking.
Our Router captures the entire Control Plane, meaning that we can implement: - Static Routing - forwarding table only - Dynamic Routing - routing table computed with an algorithm or protocol - "SDN" Routing - Control Plane separated from Data Plane And even: - URL Routers (like gorilla.Muxer) - Protocol Muxers entirely within different Router implementations.
Note that this is a break from traditional networking systems. Instead of having the abstractions of FIB, RIB, Routing/Forwarding Tables, Routers, and Switches, we only have the last two: - Router -- the things that "route" (decide where things go) - Switch -- connecting Nodes, "switch" Packets according to a Router.
type SimpleTable ¶
func (*SimpleTable) AddEntry ¶
func (t *SimpleTable) AddEntry(addr Address, nextHop Node)
AddEntry adds an (Address, NextHop) entry to the Table
func (*SimpleTable) AddNode ¶
func (t *SimpleTable) AddNode(n Node)
AddNode calls AddTableEntry for the given Node
func (*SimpleTable) AddNodes ¶
func (t *SimpleTable) AddNodes(ns ...Node)
AddNodes calls AddTableEntry for the given Node
func (*SimpleTable) Distance ¶
func (t *SimpleTable) Distance() DistanceFunc
Distance returns a measure of distance between two Addresses.
func (*SimpleTable) Entries ¶
func (t *SimpleTable) Entries() []TableEntry
Entries are the entries in this routing table
func (*SimpleTable) Route ¶
func (t *SimpleTable) Route(p Packet) Node
Route decides how to route a Packet out of a list of Nodes. It returns the Node chosen to send the Packet to. Route may return nil, if no route is suitable at all (equivalent of drop).
type Switch ¶
type Switch interface { Node // Router returns the Router used to decide where to forward packets. Router() Router }
Switch is the basic forwarding device. It listens to all its interfaces (it is a Node in our network) and Forwards all Packets received by any interface out another interface, according to its ForwardingTable.
type Table ¶
type Table interface { Router // Entries are the entries in this routing table Entries() []TableEntry // Distance returns a measure of distance between two Addresses Distance() DistanceFunc }
Table is a Router (Routing Table, really) based on a distance criterion.
For example:
n1 := NewQueueNode("aaa", make(chan Packet, 10)) n2 := NewQueueNode("aba", make(chan Packet, 10)) n3 := NewQueueNode("abc", make(chan Packet, 10)) var t router.Table t.Distance = router.HammingDistance t.AddNodes(n1, n2) p1 := NewPacket("aaa", "hello1") p2 := NewPacket("aba", "hello2") p3 := NewPacket("abc", "hello3") t.Route(p1) // n1 t.Route(p2) // n2 t.Route(p3) // n2, because we don't have n3 and n2 is closet t.AddNode(n3) t.Route(p3) // n3
type TableEntry ¶
TableEntry is an (Address, Node) pair for a routing Table
func NewTableEntry ¶
func NewTableEntry(addr Address, nexthop Node) TableEntry