add chain hop
This commit is contained in:
145
chain/node.go
145
chain/node.go
@ -1,8 +1,6 @@
|
||||
package chain
|
||||
|
||||
import (
|
||||
"context"
|
||||
|
||||
"github.com/go-gost/core/bypass"
|
||||
"github.com/go-gost/core/hosts"
|
||||
"github.com/go-gost/core/metadata"
|
||||
@ -10,48 +8,76 @@ import (
|
||||
"github.com/go-gost/core/selector"
|
||||
)
|
||||
|
||||
type Node struct {
|
||||
Name string
|
||||
Addr string
|
||||
transport *Transport
|
||||
bypass bypass.Bypass
|
||||
resolver resolver.Resolver
|
||||
hostMapper hosts.HostMapper
|
||||
marker selector.Marker
|
||||
metadata metadata.Metadata
|
||||
type NodeOptions struct {
|
||||
Transport *Transport
|
||||
Bypass bypass.Bypass
|
||||
Resolver resolver.Resolver
|
||||
HostMapper hosts.HostMapper
|
||||
Metadata metadata.Metadata
|
||||
}
|
||||
|
||||
func NewNode(name, addr string) *Node {
|
||||
return &Node{
|
||||
Name: name,
|
||||
Addr: addr,
|
||||
marker: selector.NewFailMarker(),
|
||||
type NodeOption func(*NodeOptions)
|
||||
|
||||
func TransportNodeOption(tr *Transport) NodeOption {
|
||||
return func(o *NodeOptions) {
|
||||
o.Transport = tr
|
||||
}
|
||||
}
|
||||
|
||||
func (node *Node) WithTransport(tr *Transport) *Node {
|
||||
node.transport = tr
|
||||
return node
|
||||
func BypassNodeOption(bp bypass.Bypass) NodeOption {
|
||||
return func(o *NodeOptions) {
|
||||
o.Bypass = bp
|
||||
}
|
||||
}
|
||||
|
||||
func (node *Node) WithBypass(bypass bypass.Bypass) *Node {
|
||||
node.bypass = bypass
|
||||
return node
|
||||
func ResoloverNodeOption(resolver resolver.Resolver) NodeOption {
|
||||
return func(o *NodeOptions) {
|
||||
o.Resolver = resolver
|
||||
}
|
||||
}
|
||||
|
||||
func (node *Node) WithResolver(reslv resolver.Resolver) *Node {
|
||||
node.resolver = reslv
|
||||
return node
|
||||
func HostMapperNodeOption(m hosts.HostMapper) NodeOption {
|
||||
return func(o *NodeOptions) {
|
||||
o.HostMapper = m
|
||||
}
|
||||
}
|
||||
|
||||
func (node *Node) WithHostMapper(m hosts.HostMapper) *Node {
|
||||
node.hostMapper = m
|
||||
return node
|
||||
func MetadataNodeOption(md metadata.Metadata) NodeOption {
|
||||
return func(o *NodeOptions) {
|
||||
o.Metadata = md
|
||||
}
|
||||
}
|
||||
|
||||
func (node *Node) WithMetadata(md metadata.Metadata) *Node {
|
||||
node.metadata = md
|
||||
return node
|
||||
type Node struct {
|
||||
Name string
|
||||
Addr string
|
||||
marker selector.Marker
|
||||
options NodeOptions
|
||||
}
|
||||
|
||||
func NewNode(name string, addr string, opts ...NodeOption) *Node {
|
||||
var options NodeOptions
|
||||
for _, opt := range opts {
|
||||
if opt != nil {
|
||||
opt(&options)
|
||||
}
|
||||
}
|
||||
|
||||
return &Node{
|
||||
Name: name,
|
||||
Addr: addr,
|
||||
marker: selector.NewFailMarker(),
|
||||
options: options,
|
||||
}
|
||||
}
|
||||
|
||||
func (node *Node) Options() *NodeOptions {
|
||||
return &node.options
|
||||
}
|
||||
|
||||
// Metadata implements metadadta.Metadatable interface.
|
||||
func (node *Node) Metadata() metadata.Metadata {
|
||||
return node.options.Metadata
|
||||
}
|
||||
|
||||
// Marker implements selector.Markable interface.
|
||||
@ -59,65 +85,8 @@ func (node *Node) Marker() selector.Marker {
|
||||
return node.marker
|
||||
}
|
||||
|
||||
// Metadata implements metadadta.Metadatable interface.
|
||||
func (node *Node) Metadata() metadata.Metadata {
|
||||
return node.metadata
|
||||
}
|
||||
|
||||
func (node *Node) Copy() *Node {
|
||||
n := &Node{}
|
||||
*n = *node
|
||||
return n
|
||||
}
|
||||
|
||||
type NodeGroup struct {
|
||||
nodes []*Node
|
||||
selector selector.Selector[*Node]
|
||||
bypass bypass.Bypass
|
||||
}
|
||||
|
||||
func NewNodeGroup(nodes ...*Node) *NodeGroup {
|
||||
return &NodeGroup{
|
||||
nodes: nodes,
|
||||
}
|
||||
}
|
||||
|
||||
func (g *NodeGroup) AddNode(node *Node) {
|
||||
g.nodes = append(g.nodes, node)
|
||||
}
|
||||
|
||||
func (g *NodeGroup) Nodes() []*Node {
|
||||
return g.nodes
|
||||
}
|
||||
|
||||
func (g *NodeGroup) WithSelector(selector selector.Selector[*Node]) *NodeGroup {
|
||||
g.selector = selector
|
||||
return g
|
||||
}
|
||||
|
||||
func (g *NodeGroup) WithBypass(bypass bypass.Bypass) *NodeGroup {
|
||||
g.bypass = bypass
|
||||
return g
|
||||
}
|
||||
|
||||
func (g *NodeGroup) FilterAddr(addr string) *NodeGroup {
|
||||
var nodes []*Node
|
||||
for _, node := range g.nodes {
|
||||
if node.bypass == nil || !node.bypass.Contains(addr) {
|
||||
nodes = append(nodes, node)
|
||||
}
|
||||
}
|
||||
return &NodeGroup{
|
||||
nodes: nodes,
|
||||
selector: g.selector,
|
||||
bypass: g.bypass,
|
||||
}
|
||||
}
|
||||
|
||||
func (g *NodeGroup) Next(ctx context.Context) *Node {
|
||||
if g == nil || len(g.nodes) == 0 {
|
||||
return nil
|
||||
}
|
||||
|
||||
return g.selector.Select(ctx, g.nodes...)
|
||||
}
|
||||
|
Reference in New Issue
Block a user