From f7fe8c66f950b52b8eb50b7eb1788a0d38c24cd4 Mon Sep 17 00:00:00 2001 From: AJ ONeal Date: Mon, 29 Jun 2020 00:35:19 -0600 Subject: [PATCH] move connection table to own package --- cmd/telebit/admin.go | 172 ++++------------------------------- cmd/telebit/telebit.go | 22 +---- go.mod | 12 ++- go.sum | 39 +++++++- table/table.go | 197 +++++++++++++++++++++++++++++++++++++++++ vendor/modules.txt | 138 +++++++++++++++++++++++++++-- 6 files changed, 393 insertions(+), 187 deletions(-) create mode 100644 table/table.go diff --git a/cmd/telebit/admin.go b/cmd/telebit/admin.go index af66544..81591f9 100644 --- a/cmd/telebit/admin.go +++ b/cmd/telebit/admin.go @@ -4,16 +4,13 @@ import ( "context" "encoding/json" "fmt" - "io" "log" - "net" "net/http" - "strconv" - "strings" "sync" telebit "git.coolaj86.com/coolaj86/go-telebitd/mplexer" "git.coolaj86.com/coolaj86/go-telebitd/mplexer/admin" + "git.coolaj86.com/coolaj86/go-telebitd/table" "github.com/go-chi/chi" "github.com/gorilla/websocket" @@ -21,15 +18,7 @@ import ( var httpsrv *http.Server -// Servers represent actual connections -var Servers *sync.Map - -// Table makes sense to be in-memory, but it could be serialized if needed -var Table *sync.Map - func init() { - Servers = &sync.Map{} - Table = &sync.Map{} r := chi.NewRouter() r.HandleFunc("/ws", upgradeWebsocket) @@ -86,15 +75,15 @@ type SubscriberStatus struct { func getSubscribers(w http.ResponseWriter, r *http.Request) { statuses := []*SubscriberStatus{} - Servers.Range(func(key, value interface{}) bool { + table.Servers.Range(func(key, value interface{}) bool { tunnels := 0 clients := 0 //subject := key.(string) srvMap := value.(*sync.Map) srvMap.Range(func(k, v interface{}) bool { tunnels += 1 - srv := v.(*SubscriberConn) - srv.clients.Range(func(k, v interface{}) bool { + srv := v.(*table.SubscriberConn) + srv.Clients.Range(func(k, v interface{}) bool { clients += 1 return true }) @@ -120,7 +109,7 @@ func getSubscribers(w http.ResponseWriter, r *http.Request) { func delSubscribers(w http.ResponseWriter, r *http.Request) { subject := chi.URLParam(r, "subject") - srvMapX, ok := Servers.Load(subject) + ok := table.Remove(subject) if !ok { // TODO should this be an error? _ = json.NewEncoder(w).Encode(&struct { @@ -131,19 +120,6 @@ func delSubscribers(w http.ResponseWriter, r *http.Request) { return } - srvMap := srvMapX.(*sync.Map) - srvMap.Range(func(k, v interface{}) bool { - srv := v.(*SubscriberConn) - srv.clients.Range(func(k, v interface{}) bool { - conn := v.(net.Conn) - _ = conn.Close() - return true - }) - srv.wsConn.Close() - return true - }) - Servers.Delete(subject) - _ = json.NewEncoder(w).Encode(&struct { Success bool `json:"success"` }{ @@ -151,103 +127,6 @@ func delSubscribers(w http.ResponseWriter, r *http.Request) { }) } -// SubscriberConn represents a tunneled server, its grants, and its clients -type SubscriberConn struct { - remoteAddr string - wsConn *websocket.Conn - wsTun net.Conn // *telebit.WebsocketTunnel - grants *telebit.Grants - clients *sync.Map - - // TODO is this the right codec type? - multiEncoder *telebit.Encoder - multiDecoder *telebit.Decoder - - // to fulfill Router interface -} - -func (s *SubscriberConn) RouteBytes(src, dst telebit.Addr, payload []byte) { - id := src.String() - fmt.Println("Routing some more bytes:") - fmt.Println("src", id, src) - fmt.Println("dst", dst) - clientX, ok := s.clients.Load(id) - if !ok { - // TODO send back closed client error - return - } - - client, _ := clientX.(net.Conn) - for { - n, err := client.Write(payload) - if nil != err { - if n > 0 && io.ErrShortWrite == err { - payload = payload[n:] - continue - } - // TODO send back closed client error - break - } - } -} - -func (s *SubscriberConn) Serve(client net.Conn) error { - var wconn *telebit.ConnWrap - switch conn := client.(type) { - case *telebit.ConnWrap: - wconn = conn - default: - // this probably isn't strictly necessary - panic("*SubscriberConn.Serve is special in that it must receive &ConnWrap{ Conn: conn }") - } - - id := client.RemoteAddr().String() - s.clients.Store(id, client) - - fmt.Println("[debug] cancel all the clients") - _ = client.Close() - - // TODO - // - Encode each client to the tunnel - // - Find the right client for decoded messages - - // TODO which order is remote / local? - srcParts := strings.Split(client.RemoteAddr().String(), ":") - srcAddr := srcParts[0] - srcPort, _ := strconv.Atoi(srcParts[1]) - - dstParts := strings.Split(client.LocalAddr().String(), ":") - dstAddr := dstParts[0] - dstPort, _ := strconv.Atoi(dstParts[1]) - - termination := telebit.Unknown - scheme := telebit.None - if 80 == dstPort { - // TODO dstAddr = wconn.Servername() - scheme = telebit.HTTP - } else if 443 == dstPort { - dstAddr = wconn.Servername() - scheme = telebit.HTTPS - } - - src := telebit.NewAddr( - scheme, - termination, - srcAddr, - srcPort, - ) - dst := telebit.NewAddr( - scheme, - termination, - dstAddr, - dstPort, - ) - - err := s.multiEncoder.Encode(wconn, *src, *dst) - s.clients.Delete(id) - return err -} - func upgradeWebsocket(w http.ResponseWriter, r *http.Request) { log.Println("websocket opening ", r.RemoteAddr, " ", r.Host) w.Header().Set("Content-Type", "application/json") @@ -274,19 +153,19 @@ func upgradeWebsocket(w http.ResponseWriter, r *http.Request) { } wsTun := telebit.NewWebsocketTunnel(conn) - server := SubscriberConn{ - remoteAddr: r.RemoteAddr, - wsConn: conn, - wsTun: wsTun, - grants: grants, - clients: &sync.Map{}, - multiEncoder: telebit.NewEncoder(context.TODO(), wsTun), - multiDecoder: telebit.NewDecoder(wsTun), + server := &table.SubscriberConn{ + RemoteAddr: r.RemoteAddr, + WSConn: conn, + WSTun: wsTun, + Grants: grants, + Clients: &sync.Map{}, + MultiEncoder: telebit.NewEncoder(context.TODO(), wsTun), + MultiDecoder: telebit.NewDecoder(wsTun), } go func() { // (this listener is also a telebit.Router) - err := server.multiDecoder.Decode(&server) + err := server.MultiDecoder.Decode(server) // The tunnel itself must be closed explicitly because // there's an encoder with a callback between the websocket @@ -295,26 +174,5 @@ func upgradeWebsocket(w http.ResponseWriter, r *http.Request) { fmt.Printf("a subscriber stream is done: %q\n", err) }() - var srvMap *sync.Map - srvMapX, ok := Servers.Load(grants.Subject) - if ok { - srvMap = srvMapX.(*sync.Map) - } else { - srvMap = &sync.Map{} - } - srvMap.Store(r.RemoteAddr, server) - Servers.Store(grants.Subject, srvMap) - - // Add this server to the domain name matrix - for _, name := range grants.Domains { - var srvMap *sync.Map - srvMapX, ok := Table.Load(name) - if ok { - srvMap = srvMapX.(*sync.Map) - } else { - srvMap = &sync.Map{} - } - srvMap.Store(r.RemoteAddr, server) - Table.Store(name, srvMap) - } + table.Add(server) } diff --git a/cmd/telebit/telebit.go b/cmd/telebit/telebit.go index 17c82d4..68324b5 100644 --- a/cmd/telebit/telebit.go +++ b/cmd/telebit/telebit.go @@ -16,7 +16,6 @@ import ( "regexp" "strconv" "strings" - "sync" "time" "git.coolaj86.com/coolaj86/go-telebitd/mgmt" @@ -24,6 +23,7 @@ import ( telebit "git.coolaj86.com/coolaj86/go-telebitd/mplexer" "git.coolaj86.com/coolaj86/go-telebitd/mplexer/dns01" httpshim "git.coolaj86.com/coolaj86/go-telebitd/relay/tunnel" + "git.coolaj86.com/coolaj86/go-telebitd/table" "github.com/caddyserver/certmagic" "github.com/denisbrodbeck/machineid" @@ -363,29 +363,11 @@ func routeSubscribersAndClients(client net.Conn) error { // tryToServeName picks the server tunnel with the least connections, if any func tryToServeName(servername string, wconn *telebit.ConnWrap) bool { - var srv *SubscriberConn - load := -1 - srvMapX, ok := Table.Load(servername) + srv, ok := table.GetServer(servername) if !ok { return false } - srvMap := srvMapX.(*sync.Map) - srvMap.Range(func(k, v interface{}) bool { - myLoad := 0 - mySrv := v.(*SubscriberConn) - mySrv.clients.Range(func(k, v interface{}) bool { - load += 1 - return true - }) - // pick the least loaded server - if -1 == load || myLoad < load { - load = myLoad - srv = mySrv - } - return true - }) - // async so that the call stack can complete and be released //srv.clients.Store(wconn.LocalAddr().String(), wconn) go func() { diff --git a/go.mod b/go.mod index 69a6527..3e4a700 100644 --- a/go.mod +++ b/go.mod @@ -11,11 +11,19 @@ require ( github.com/go-chi/chi v4.1.1+incompatible github.com/gorilla/mux v1.7.4 github.com/gorilla/websocket v1.4.2 - github.com/jmoiron/sqlx v1.2.0 + github.com/jmoiron/sqlx v1.2.1-0.20190826204134-d7d95172beb5 github.com/joho/godotenv v1.3.0 + github.com/kr/text v0.2.0 // indirect github.com/lib/pq v1.6.0 + github.com/niemeyer/pretty v0.0.0-20200227124842-a10e7caefd8e // indirect github.com/shurcooL/httpfs v0.0.0-20190707220628-8d4bc4ba7749 // indirect github.com/shurcooL/vfsgen v0.0.0-20181202132449-6a9ea43bcacd - github.com/stretchr/testify v1.5.1 + github.com/stretchr/testify v1.6.1 + golang.org/x/sys v0.0.0-20200625212154-ddb9806d33ae // indirect + golang.org/x/text v0.3.3 // indirect + golang.org/x/tools v0.0.0-20200626171337-aa94e735be7f // indirect + gopkg.in/check.v1 v1.0.0-20200227125254-8fa46927fb4f // indirect gopkg.in/natefinch/lumberjack.v2 v2.0.0 + gopkg.in/yaml.v2 v2.3.0 // indirect + gopkg.in/yaml.v3 v3.0.0-20200615113413-eeeca48fe776 // indirect ) diff --git a/go.sum b/go.sum index 7f1f5a1..11b94eb 100644 --- a/go.sum +++ b/go.sum @@ -46,6 +46,7 @@ github.com/Shopify/toxiproxy v2.1.4+incompatible/go.mod h1:OXgGpZ6Cli1/URJOF1DMx github.com/akamai/AkamaiOPEN-edgegrid-golang v0.9.0/go.mod h1:zpDJeKyp9ScW4NNrbdr+Eyxvry3ilGPewKoXw3XGN1k= github.com/akamai/AkamaiOPEN-edgegrid-golang v0.9.8/go.mod h1:aVvklgKsPENRkl29bNwrHISa1F+YLGTHArMxZMBqWM8= github.com/alecthomas/template v0.0.0-20160405071501-a0175ee3bccc/go.mod h1:LOuyumcjzFXgccqObfd/Ljyb9UuFJ6TxHnclSeseNhc= +github.com/alecthomas/units v0.0.0-20151022065526-2efee857e7cf h1:qet1QNfXsQxTZqLG4oE62mJzwPIB8+Tee4RNCL9ulrY= github.com/alecthomas/units v0.0.0-20151022065526-2efee857e7cf/go.mod h1:ybxpYRFXyAe+OPACYpWeL0wqObRcbAqCMya13uyzqw0= github.com/alexbrainman/sspi v0.0.0-20180613141037-e580b900e9f5 h1:P5U+E4x5OkVEKQDklVPmzs71WM56RTTRqV4OrDC//Y4= github.com/alexbrainman/sspi v0.0.0-20180613141037-e580b900e9f5/go.mod h1:976q2ETgjT2snVCf2ZaBnyBbVoPERGjUz+0sofzEfro= @@ -73,6 +74,7 @@ github.com/cloudflare/cloudflare-go v0.10.2/go.mod h1:qhVI5MKwBGhdNU89ZRz2plgYut github.com/cpu/goacmedns v0.0.1/go.mod h1:sesf/pNnCYwUevQEQfEwY0Y3DydlQWSGZbaMElOWxok= github.com/cpu/goacmedns v0.0.2/go.mod h1:4MipLkI+qScwqtVxcNO6okBhbgRrr7/tKXUSgSL0teQ= github.com/cpuguy83/go-md2man/v2 v2.0.0-20190314233015-f79a8a8ca69d/go.mod h1:maD7wRr/U5Z6m/iR4s+kqSMx2CaBsrgA7czyZG/E6dU= +github.com/creack/pty v1.1.9/go.mod h1:oKZEueFk5CKHvIhNR5MUki03XCEU+Q6VDXinZuGJ33E= github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c= github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= @@ -188,8 +190,8 @@ github.com/jcmturner/rpc/v2 v2.0.2 h1:gMB4IwRXYsWw4Bc6o/az2HJgFUA1ffSh90i26ZJ6Xl github.com/jcmturner/rpc/v2 v2.0.2/go.mod h1:VUJYCIDm3PVOEHw8sgt091/20OJjskO/YJki3ELg/Hc= github.com/jmespath/go-jmespath v0.0.0-20180206201540-c2b33e8439af/go.mod h1:Nht3zPeWKUH0NzdCt2Blrr5ys8VGpn0CEB0cQHVjt7k= github.com/jmespath/go-jmespath v0.3.0/go.mod h1:9QtRXoHjLGCJ5IBSaohpXITPlowMeeYCZ7fLUTSywik= -github.com/jmoiron/sqlx v1.2.0 h1:41Ip0zITnmWNR/vHV+S4m+VoUivnWY5E4OJfLZjCJMA= -github.com/jmoiron/sqlx v1.2.0/go.mod h1:1FEQNm3xlJgrMD+FBdI9+xvCksHtbpVBBw5dYhBSsks= +github.com/jmoiron/sqlx v1.2.1-0.20190826204134-d7d95172beb5 h1:lrdPtrORjGv1HbbEvKWDUAy97mPpFm4B8hp77tcCUJY= +github.com/jmoiron/sqlx v1.2.1-0.20190826204134-d7d95172beb5/go.mod h1:1FEQNm3xlJgrMD+FBdI9+xvCksHtbpVBBw5dYhBSsks= github.com/joho/godotenv v1.3.0 h1:Zjp+RcGpHhGlrMbJzXTrZZPrWj+1vfm90La1wgB6Bhc= github.com/joho/godotenv v1.3.0/go.mod h1:7hK45KPybAkOC6peb+G5yklZfMxEjkZhHbwpqxOKXbg= github.com/json-iterator/go v1.1.5/go.mod h1:+SdeFBvtyEkXs7REEP0seUULqWtbJapLOCVDaaPEHmU= @@ -200,6 +202,7 @@ github.com/jstemmer/go-junit-report v0.9.1/go.mod h1:Brl9GWCQeLvo8nXZwPNNblvFj/X github.com/jtolds/gls v4.20.0+incompatible h1:xdiiI2gbIgH/gLH7ADydsJ1uDOEzR8yvV7C0MuV77Wo= github.com/jtolds/gls v4.20.0+incompatible/go.mod h1:QJZ7F/aHp+rZTRtaJ1ow/lLfFfVYBRgL+9YlvaHOwJU= github.com/julienschmidt/httprouter v1.2.0/go.mod h1:SYymIcj16QtmaHHD7aYtjjsJG7VTCxuUUipMqKk8s4w= +github.com/kisielk/gotool v1.0.0 h1:AV2c/EiW3KqPNT9ZKl07ehoAGi4C5/01Cfbblndcapg= github.com/kisielk/gotool v1.0.0/go.mod h1:XhKaO+MFFWcvkIS/tQcRk01m1F5IRFswLeQ+oQHNcck= github.com/klauspost/cpuid v1.2.3 h1:CCtW0xUnWGVINKvE/WWOYKdsPV6mawAtvQuSl8guwQs= github.com/klauspost/cpuid v1.2.3/go.mod h1:Pj4uuM528wm8OyEC2QMXAi2YiTZ96dNQPGgoMS4s3ek= @@ -212,6 +215,8 @@ github.com/kr/pretty v0.1.0/go.mod h1:dAy3ld7l9f0ibDNOQOHHMYYIIbhfbHSm3C4ZsoJORN github.com/kr/pty v1.1.1/go.mod h1:pFQYn66WHrOpPYNljwOMqo10TkYh1fy3cYio2l3bCsQ= github.com/kr/text v0.1.0 h1:45sCR5RtlFHMR4UwH9sdQ5TC8v0qDQCHnXt+kaKSTVE= github.com/kr/text v0.1.0/go.mod h1:4Jbv+DJW3UT/LiOwJeYQe1efqtUx/iVham/4vfdArNI= +github.com/kr/text v0.2.0 h1:5Nx0Ya0ZqY2ygV366QzturHI13Jq95ApcVaJBhpS+AY= +github.com/kr/text v0.2.0/go.mod h1:eLer722TekiGuMkidMxC/pM04lWEeraHUUmBw8l2grE= github.com/labbsr0x/bindman-dns-webhook v1.0.2/go.mod h1:p6b+VCXIR8NYKpDr8/dg1HKfQoRHCdcsROXKvmoehKA= github.com/labbsr0x/goh v1.0.1/go.mod h1:8K2UhVoaWXcCU7Lxoa2omWnC8gyW8px7/lmO61c027w= github.com/lib/pq v1.0.0/go.mod h1:5WUZQaWbwv1U+lTReE5YruASi9Al49XbQIvNi/34Woo= @@ -219,8 +224,10 @@ github.com/lib/pq v1.6.0 h1:I5DPxhYJChW9KYc66se+oKFFQX6VuQrKiprsX6ivRZc= github.com/lib/pq v1.6.0/go.mod h1:4vXEAYvW1fRQ2/FhZ78H73A60MHw1geSm145z2mdY1g= github.com/linode/linodego v0.10.0/go.mod h1:cziNP7pbvE3mXIPneHj0oRY8L1WtGEIKlZ8LANE4eXA= github.com/liquidweb/liquidweb-go v1.6.0/go.mod h1:UDcVnAMDkZxpw4Y7NOHkqoeiGacVLEIG/i5J9cyixzQ= +github.com/mattn/go-isatty v0.0.3 h1:ns/ykhmWi7G9O+8a448SecJU3nSMBXJfqQkl0upE1jI= github.com/mattn/go-isatty v0.0.3/go.mod h1:M+lRXTBqGeGNdLjl/ufCoiOlB5xdOkqRJdNxMWT7Zi4= github.com/mattn/go-runewidth v0.0.2/go.mod h1:LwmH8dsx7+W8Uxz3IHJYH5QSwggIsqBzpuz5H//U1FU= +github.com/mattn/go-runewidth v0.0.4 h1:2BvfKmzob6Bmd4YsL0zygOqfdFnK7GR4QL06Do4/p7Y= github.com/mattn/go-runewidth v0.0.4/go.mod h1:LwmH8dsx7+W8Uxz3IHJYH5QSwggIsqBzpuz5H//U1FU= github.com/mattn/go-sqlite3 v1.9.0 h1:pDRiWfl+++eC2FEFRy6jXmQlvp4Yh3z1MJKg4UeYM/4= github.com/mattn/go-sqlite3 v1.9.0/go.mod h1:FPy6KqzDD04eiIsT53CuJW3U88zkxoIYsOqkbpncsNc= @@ -229,6 +236,7 @@ github.com/matttproud/golang_protobuf_extensions v1.0.1/go.mod h1:D8He9yQNgCq6Z5 github.com/miekg/dns v1.1.15/go.mod h1:W1PPwlIAgtquWBMBEV9nkV9Cazfe8ScdGz/Lj7v3Nrg= github.com/miekg/dns v1.1.27 h1:aEH/kqUzUxGJ/UHcEKdJY+ugH6WEzsEBBSPa8zuy1aM= github.com/miekg/dns v1.1.27/go.mod h1:KNUDUusw/aVsxyTYZM1oqvCicbwhgbNgztCETuNZ7xM= +github.com/mitchellh/go-homedir v1.1.0 h1:lukF9ziXFxDFPkA1vsr5zpc1XuPDn/wFntq5mG+4E0Y= github.com/mitchellh/go-homedir v1.1.0/go.mod h1:SfyaCUpYCn1Vlf4IUYiD9fPX4A5wJrkLzIz1N1q0pr0= github.com/mitchellh/go-vnc v0.0.0-20150629162542-723ed9867aed/go.mod h1:3rdaFaCv4AyBgu5ALFM0+tSuHrBh6v692nyQe3ikrq0= github.com/mitchellh/mapstructure v1.1.2 h1:fmNYVwqnSfB9mZU6OS2O6GsXM+wcskZDuKQzvN1EDeE= @@ -240,6 +248,8 @@ github.com/modern-go/reflect2 v1.0.1/go.mod h1:bx2lNnkwVCuqBIxFjflWJWanXIb3Rllmb github.com/mwitkow/go-conntrack v0.0.0-20161129095857-cc309e4a2223/go.mod h1:qRWi+5nqEBWmkhHvq77mSJWrCKwh8bxhgT7d/eI7P4U= github.com/namedotcom/go v0.0.0-20180403034216-08470befbe04/go.mod h1:5sN+Lt1CaY4wsPvgQH/jsuJi4XO2ssZbdsIizr4CVC8= github.com/nbio/st v0.0.0-20140626010706-e9e8d9816f32/go.mod h1:9wM+0iRr9ahx58uYLpLIr5fm8diHn0JbqRycJi6w0Ms= +github.com/niemeyer/pretty v0.0.0-20200227124842-a10e7caefd8e h1:fD57ERR4JtEqsWbfPhv4DMiApHyliiK5xCTNVSPiaAs= +github.com/niemeyer/pretty v0.0.0-20200227124842-a10e7caefd8e/go.mod h1:zD1mROLANZcx1PVRCS0qkT7pwLkGfwJo4zjcN/Tysno= github.com/nrdcg/auroradns v1.0.0/go.mod h1:6JPXKzIRzZzMqtTDgueIhTi6rFf1QvYE/HzqidhOhjw= github.com/nrdcg/auroradns v1.0.1/go.mod h1:y4pc0i9QXYlFCWrhWrUSIETnZgrf4KuwjDIWmmXo3JI= github.com/nrdcg/dnspod-go v0.4.0/go.mod h1:vZSoFSFeQVm2gWLMkyX61LZ8HI3BaqtHZWgPTGKr6KQ= @@ -255,6 +265,7 @@ github.com/ovh/go-ovh v0.0.0-20181109152953-ba5adb4cf014/go.mod h1:joRatxRJaZBsY github.com/pierrec/lz4 v2.0.5+incompatible/go.mod h1:pdkljMzZIN41W+lC3N2tnIh5sFi+IEE17M5jbnwPHcY= github.com/pkg/errors v0.8.0/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0= github.com/pkg/errors v0.8.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0= +github.com/pkg/errors v0.9.1 h1:FEBLx1zS214owpjy7qsBeixbURkuhQAwrK5UwLGTwt4= github.com/pkg/errors v0.9.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0= github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZbAQM= github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4= @@ -277,11 +288,13 @@ github.com/rainycape/memcache v0.0.0-20150622160815-1031fa0ce2f2/go.mod h1:7tZKc github.com/rcrowley/go-metrics v0.0.0-20181016184325-3113b8401b8a/go.mod h1:bCqnVzQkZxMG4s8nGwiZ5l3QUCyqpo9Y+/ZMZ9VjZe4= github.com/rogpeppe/fastuuid v0.0.0-20150106093220-6724a57986af/go.mod h1:XWv6SoW27p1b0cqNHllgS5HIMJraePCO15w5zCzIWYg= github.com/rogpeppe/go-internal v1.3.0/go.mod h1:M8bDsm7K2OlrFYOpmOWEs/qY81heoFRclV5y23lUDJ4= +github.com/russross/blackfriday/v2 v2.0.1 h1:lPqVAte+HuHNfhJ/0LC98ESWRz8afy9tM/0RK8m9o+Q= github.com/russross/blackfriday/v2 v2.0.1/go.mod h1:+Rmxgy9KzJVeS9/2gXHxylqXiyQDYRxCVz55jmeOWTM= github.com/sacloud/libsacloud v1.26.1/go.mod h1:79ZwATmHLIFZIMd7sxA3LwzVy/B77uj3LDoToVTxDoQ= github.com/satori/go.uuid v1.2.0/go.mod h1:dA0hQrYB0VpLJoorglMZABFdXlWrHn1NEOzdhQKdks0= github.com/shurcooL/httpfs v0.0.0-20190707220628-8d4bc4ba7749 h1:bUGsEnyNbVPw06Bs80sCeARAlK8lhwqGyi6UT8ymuGk= github.com/shurcooL/httpfs v0.0.0-20190707220628-8d4bc4ba7749/go.mod h1:ZY1cvUeJuFPAdZ/B6v7RHavJWZn2YPVFQ1OSXhCGOkg= +github.com/shurcooL/sanitized_anchor_name v1.0.0 h1:PdmoCO6wvbs+7yrJyMORt4/BmY5IYyJwS/kOiWx8mHo= github.com/shurcooL/sanitized_anchor_name v1.0.0/go.mod h1:1NzhyTcUVG4SuEtjjoZeVRXNmyL/1OwPU0+IJeTBvfc= github.com/shurcooL/vfsgen v0.0.0-20181202132449-6a9ea43bcacd h1:ug7PpSOB5RBPK1Kg6qskGBoP3Vnj/aNYFTznWvlkGo0= github.com/shurcooL/vfsgen v0.0.0-20181202132449-6a9ea43bcacd/go.mod h1:TrYk7fJVaAttu97ZZKrO9UbRa8izdowaMIZcxYMbVaw= @@ -294,6 +307,7 @@ github.com/smartystreets/goconvey v0.0.0-20190330032615-68dc04aab96a/go.mod h1:s github.com/smartystreets/goconvey v1.6.4 h1:fv0U8FUIMPNf1L9lnHLvLhgicrIVChEkdzIKYqbNC9s= github.com/smartystreets/goconvey v1.6.4/go.mod h1:syvi0/a8iFYH4r/RixwvyeAJjdLS9QV7WQ/tjFTllLA= github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME= +github.com/stretchr/objx v0.1.1 h1:2vfRuCMp5sSVIDSqO8oNnWJq7mPa6KVP3iPIwFBuy8A= github.com/stretchr/objx v0.1.1/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME= github.com/stretchr/testify v1.2.2/go.mod h1:a8OnRcib4nhh0OaRAV+Yts87kKdq0PP7pXfy6kDkUVs= github.com/stretchr/testify v1.3.0 h1:TivCn/peBQ7UY8ooIcPgZFpTNSz0Q2U6UrFlUfqbe0Q= @@ -301,6 +315,8 @@ github.com/stretchr/testify v1.3.0/go.mod h1:M5WIy9Dh21IEIfnGCwXGc5bZfKNJtfHm1UV github.com/stretchr/testify v1.4.0/go.mod h1:j7eGeouHqKxXV5pUuKE4zz7dFj8WfuZ+81PSLYec5m4= github.com/stretchr/testify v1.5.1 h1:nOGnQDM7FYENwehXlg/kFVnos3rEvtKTjRvOWSzb6H4= github.com/stretchr/testify v1.5.1/go.mod h1:5W2xD1RspED5o8YsWQXVCued0rvSQ+mT+I5cxcmMvtA= +github.com/stretchr/testify v1.6.1 h1:hDPOHmpOpP40lSULcqw7IrRb/u7w6RpDC9399XyoNd0= +github.com/stretchr/testify v1.6.1/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg= github.com/timewasted/linode v0.0.0-20160829202747-37e84520dcf7/go.mod h1:imsgLplxEC/etjIhdr3dNzV3JeT27LbVu5pYWm0JCBY= github.com/transip/gotransip v0.0.0-20190812104329-6d8d9179b66f/go.mod h1:i0f4R4o2HM0m3DZYQWsj6/MEowD57VzoH0v3d7igeFY= github.com/transip/gotransip/v6 v6.0.2/go.mod h1:pQZ36hWWRahCUXkFWlx9Hs711gLd8J4qdgLdRzmtY+g= @@ -311,6 +327,7 @@ github.com/xeipuuv/gojsonpointer v0.0.0-20180127040702-4e3ac2762d5f/go.mod h1:N2 github.com/xeipuuv/gojsonreference v0.0.0-20180127040603-bd5ef7bd5415/go.mod h1:GwrjFmJcFw6At/Gs6z4yjiIwzuJ1/+UwLxMQDVQXShQ= github.com/xeipuuv/gojsonschema v1.1.0/go.mod h1:5yf86TLmAcydyeJq5YvxkGPE2fm/u4myDekKRoLuqhs= github.com/xeipuuv/gojsonschema v1.2.0/go.mod h1:anYRn/JVcOK2ZgGU+IjEV4nwlhoK5sQluxsYJ78Id3Y= +github.com/yuin/goldmark v1.1.27/go.mod h1:3hX8gzYuyVAZsxl0MRgGTJEmQBFcNTphYh9decYSb74= go.opencensus.io v0.20.1/go.mod h1:6WKK9ahsWS3RSO+PY9ZHZUfv2irvY6gN279GOPZjmmk= go.opencensus.io v0.20.2/go.mod h1:6WKK9ahsWS3RSO+PY9ZHZUfv2irvY6gN279GOPZjmmk= go.opencensus.io v0.21.0/go.mod h1:mSImk1erAIZhrmZN+AvHh14ztQfjbGwt4TtuofqLduU= @@ -353,6 +370,7 @@ golang.org/x/lint v0.0.0-20190909230951-414d861bb4ac/go.mod h1:6SW0HCj/g11FgYtHl golang.org/x/lint v0.0.0-20190930215403-16217165b5de/go.mod h1:6SW0HCj/g11FgYtHlgUYUwCkIfeOF89ocIRzGO/8vkc= golang.org/x/lint v0.0.0-20191125180803-fdd1cda4f05f/go.mod h1:5qLYkcX4OjUUV8bRuDixDT3tpyyb+LUpUlRWLxfhWrs= golang.org/x/lint v0.0.0-20200130185559-910be7a94367/go.mod h1:3xt1FjdF8hUf6vQPIChWIBhFzV8gjjsPE/fR3IyQdNY= +golang.org/x/lint v0.0.0-20200302205851-738671d3881b h1:Wh+f8QHJXR411sJR8/vRBTZ7YapZaRvUcLFFJhusH0k= golang.org/x/lint v0.0.0-20200302205851-738671d3881b/go.mod h1:3xt1FjdF8hUf6vQPIChWIBhFzV8gjjsPE/fR3IyQdNY= golang.org/x/mobile v0.0.0-20190312151609-d3739f865fa6/go.mod h1:z+o9i4GpDbdi3rU15maQ/Ox0txvL9dWGYEHz965HBQE= golang.org/x/mobile v0.0.0-20190719004257-d2bd2a29d028/go.mod h1:E/iHnbuqvinMTCcRqshq8CkpyQDoeVncDDYHnLhea+o= @@ -360,6 +378,7 @@ golang.org/x/mod v0.0.0-20190513183733-4bf6d317e70e/go.mod h1:mXi4GBBbnImb6dmsKG golang.org/x/mod v0.1.0/go.mod h1:0QHyrYULN0/3qlju5TqG8bIK38QM8yzMo5ekMj3DlcY= golang.org/x/mod v0.1.1-0.20191105210325-c90efee705ee/go.mod h1:QqPTAvyqsEbceGzBzNggFXnrqF1CaUcvgkdR5Ot7KZg= golang.org/x/mod v0.1.1-0.20191107180719-034126e5016b/go.mod h1:QqPTAvyqsEbceGzBzNggFXnrqF1CaUcvgkdR5Ot7KZg= +golang.org/x/mod v0.2.0 h1:KU7oHjnv3XNWfa5COkzUifxZmxp1TyI7ImMXqFxLwvQ= golang.org/x/mod v0.2.0/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA= golang.org/x/net v0.0.0-20180611182652-db08ff08e862/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= golang.org/x/net v0.0.0-20180724234803-3673e40ba225/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= @@ -432,12 +451,16 @@ golang.org/x/sys v0.0.0-20200212091648-12a6c2dcc1e4/go.mod h1:h1NjWce9XRLGQEsW7w golang.org/x/sys v0.0.0-20200223170610-d5e6a3e2c0ae/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20200302150141-5c8b2ff67527 h1:uYVVQ9WP/Ds2ROhcaGPeIdVq0RIXVLwsHlnvJ+cT1So= golang.org/x/sys v0.0.0-20200302150141-5c8b2ff67527/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20200625212154-ddb9806d33ae h1:Ih9Yo4hSPImZOpfGuA4bR/ORKTAbhZo2AbWNRCnevdo= +golang.org/x/sys v0.0.0-20200625212154-ddb9806d33ae/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/text v0.0.0-20170915032832-14c0d48ead0c/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= golang.org/x/text v0.3.0 h1:g61tztE5qeGQ89tm6NTjjM9VPIm088od1l6aSorWRWg= golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= golang.org/x/text v0.3.1-0.20180807135948-17ff2d5776d2/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= golang.org/x/text v0.3.2 h1:tW2bmiBqwgJj/UpqtC8EpXEZVYOwU0yG4iWbprSVAcs= golang.org/x/text v0.3.2/go.mod h1:bEr9sfX3Q8Zfm5fL9x+3itogRgK3+ptLWKqgva+5dAk= +golang.org/x/text v0.3.3 h1:cokOdA+Jmi5PJGXLlLllQSgYigAEfHXJAERHVMaCc2k= +golang.org/x/text v0.3.3/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ= golang.org/x/time v0.0.0-20181108054448-85acf8d2951c/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= golang.org/x/time v0.0.0-20190308202827-9d24e82272b4/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= golang.org/x/time v0.0.0-20190921001708-c4c64cad1fd0/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= @@ -477,8 +500,11 @@ golang.org/x/tools v0.0.0-20200212150539-ea181f53ac56/go.mod h1:TB2adYChydJhpapK golang.org/x/tools v0.0.0-20200224181240-023911ca70b2/go.mod h1:TB2adYChydJhpapKDTa4BR/hXlZSLoq2Wpct/0txZ28= golang.org/x/tools v0.0.0-20200304193943-95d2e580d8eb h1:iKlO7ROJc6SttHKlxzwGytRtBUqX4VARrNTgP2YLX5M= golang.org/x/tools v0.0.0-20200304193943-95d2e580d8eb/go.mod h1:o4KQGtdN14AW+yjsvvwRTJJuXz8XRtIHtEnmAXLyFUw= +golang.org/x/tools v0.0.0-20200626171337-aa94e735be7f h1:JcoF/bowzCDI+MXu1yLqQGNO3ibqWsWq+Sk7pOT218w= +golang.org/x/tools v0.0.0-20200626171337-aa94e735be7f/go.mod h1:EkVYQZoAsY45+roYkvgYkIh4xh/qjgUK9TdY2XT94GE= golang.org/x/xerrors v0.0.0-20190717185122-a985d3407aa7/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= golang.org/x/xerrors v0.0.0-20191011141410-1b5146add898/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= +golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543 h1:E7g+9GITq07hpfrRu66IVDexMakfv52eLZ2CXBWiKr4= golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= google.golang.org/api v0.3.1/go.mod h1:6wY9I6uQWHQ8EM57III9mq/AjF+i8G65rmVagqKMtkk= google.golang.org/api v0.4.0/go.mod h1:8k5glujaEP+g9n7WNsDg8QP6cUVNI86fCNMcbazEtwE= @@ -527,6 +553,8 @@ gopkg.in/alecthomas/kingpin.v2 v2.2.6/go.mod h1:FMv+mEhP44yOT+4EoQTLFTRgOQ1FBLks gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= gopkg.in/check.v1 v1.0.0-20180628173108-788fd7840127 h1:qIbj1fsPNlZgppZ+VLlY7N33q108Sa+fhmuc+sWQYwY= gopkg.in/check.v1 v1.0.0-20180628173108-788fd7840127/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= +gopkg.in/check.v1 v1.0.0-20200227125254-8fa46927fb4f h1:BLraFXnmrev5lT+xlilqcH8XK9/i0At2xKjWk4p6zsU= +gopkg.in/check.v1 v1.0.0-20200227125254-8fa46927fb4f/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= gopkg.in/errgo.v2 v2.1.0/go.mod h1:hNsd1EY+bozCKY1Ytp96fpM3vjJbqLJn88ws8XvfDNI= gopkg.in/fsnotify.v1 v1.4.7/go.mod h1:Tz8NjZHkW78fSQdbUxIjBTcgA1z1m8ZHf0WmKUhAMys= gopkg.in/h2non/gock.v1 v1.0.15/go.mod h1:sX4zAkdYX1TRGJ2JY156cFspQn4yRWn6p9EMdODlynE= @@ -552,12 +580,19 @@ gopkg.in/yaml.v2 v2.2.1/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI= gopkg.in/yaml.v2 v2.2.2/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI= gopkg.in/yaml.v2 v2.2.8 h1:obN1ZagJSUGI0Ek/LBmuj4SNLPfIny3KsKFopxRdj10= gopkg.in/yaml.v2 v2.2.8/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI= +gopkg.in/yaml.v2 v2.3.0 h1:clyUAQHOM3G0M3f5vQj7LuJrETvjVot3Z5el9nffUtU= +gopkg.in/yaml.v2 v2.3.0/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI= +gopkg.in/yaml.v3 v3.0.0-20200313102051-9f266ea9e77c h1:dUUwHk2QECo/6vqA44rthZ8ie2QXMNeKRTHCNY2nXvo= +gopkg.in/yaml.v3 v3.0.0-20200313102051-9f266ea9e77c/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= +gopkg.in/yaml.v3 v3.0.0-20200615113413-eeeca48fe776 h1:tQIYjPdBoyREyB9XMu+nnTclpTYkz2zFM+lzLJFO4gQ= +gopkg.in/yaml.v3 v3.0.0-20200615113413-eeeca48fe776/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= honnef.co/go/tools v0.0.0-20180728063816-88497007e858/go.mod h1:rf3lG4BRIbNafJWhAfAdb/ePZxsR/4RtNHQocxwk9r4= honnef.co/go/tools v0.0.0-20190102054323-c2f93a96b099/go.mod h1:rf3lG4BRIbNafJWhAfAdb/ePZxsR/4RtNHQocxwk9r4= honnef.co/go/tools v0.0.0-20190106161140-3f1c8253044a/go.mod h1:rf3lG4BRIbNafJWhAfAdb/ePZxsR/4RtNHQocxwk9r4= honnef.co/go/tools v0.0.0-20190418001031-e561f6794a2a/go.mod h1:rf3lG4BRIbNafJWhAfAdb/ePZxsR/4RtNHQocxwk9r4= honnef.co/go/tools v0.0.0-20190523083050-ea95bdfd59fc/go.mod h1:rf3lG4BRIbNafJWhAfAdb/ePZxsR/4RtNHQocxwk9r4= honnef.co/go/tools v0.0.1-2019.2.3/go.mod h1:a3bituU0lyd329TUQxRnasdCoJDkEUEAqEt0JzvZhAg= +honnef.co/go/tools v0.0.1-2020.1.3 h1:sXmLre5bzIR6ypkjXCDI3jHPssRhc8KD/Ome589sc3U= honnef.co/go/tools v0.0.1-2020.1.3/go.mod h1:X/FiERA/W4tHapMX5mGpAtMSVEeEUOyHaw9vFzvIQ3k= rsc.io/binaryregexp v0.2.0/go.mod h1:qTv7/COck+e2FymRvadv62gMdZztPaShugOCi3I+8D8= rsc.io/quote/v3 v3.1.0/go.mod h1:yEA65RcK8LyAZtP9Kv3t0HmxON59tX3rD+tICJqUlj0= diff --git a/table/table.go b/table/table.go new file mode 100644 index 0000000..477e4c6 --- /dev/null +++ b/table/table.go @@ -0,0 +1,197 @@ +package table + +import ( + "fmt" + "net" + "sync" + + "io" + "strconv" + "strings" + + telebit "git.coolaj86.com/coolaj86/go-telebitd/mplexer" + "github.com/gorilla/websocket" +) + +// Servers represent actual connections +var Servers *sync.Map + +// Table makes sense to be in-memory, but it could be serialized if needed +var Table *sync.Map + +func init() { + Servers = &sync.Map{} + Table = &sync.Map{} +} + +func Add(server *SubscriberConn) { + var srvMap *sync.Map + srvMapX, ok := Servers.Load(server.Grants.Subject) + if ok { + srvMap = srvMapX.(*sync.Map) + } else { + srvMap = &sync.Map{} + } + srvMap.Store(server.RemoteAddr, server) + Servers.Store(server.Grants.Subject, srvMap) + + // Add this server to the domain name matrix + for _, name := range server.Grants.Domains { + var srvMap *sync.Map + srvMapX, ok := Table.Load(name) + if ok { + srvMap = srvMapX.(*sync.Map) + } else { + srvMap = &sync.Map{} + } + srvMap.Store(server.RemoteAddr, server) + Table.Store(name, srvMap) + } +} + +func Remove(subject string) bool { + srvMapX, ok := Servers.Load(subject) + if !ok { + return false + } + + srvMap := srvMapX.(*sync.Map) + srvMap.Range(func(k, v interface{}) bool { + srv := v.(*SubscriberConn) + srv.Clients.Range(func(k, v interface{}) bool { + conn := v.(net.Conn) + _ = conn.Close() + return true + }) + srv.WSConn.Close() + return true + }) + Servers.Delete(subject) + + return true +} + +// SubscriberConn represents a tunneled server, its grants, and its clients +type SubscriberConn struct { + RemoteAddr string + WSConn *websocket.Conn + WSTun net.Conn // *telebit.WebsocketTunnel + Grants *telebit.Grants + Clients *sync.Map + + // TODO is this the right codec type? + MultiEncoder *telebit.Encoder + MultiDecoder *telebit.Decoder + + // to fulfill Router interface +} + +func (s *SubscriberConn) RouteBytes(src, dst telebit.Addr, payload []byte) { + id := src.String() + fmt.Println("Routing some more bytes:") + fmt.Println("src", id, src) + fmt.Println("dst", dst) + clientX, ok := s.Clients.Load(id) + if !ok { + // TODO send back closed client error + return + } + + client, _ := clientX.(net.Conn) + for { + n, err := client.Write(payload) + if nil != err { + if n > 0 && io.ErrShortWrite == err { + payload = payload[n:] + continue + } + // TODO send back closed client error + break + } + } +} + +func (s *SubscriberConn) Serve(client net.Conn) error { + var wconn *telebit.ConnWrap + switch conn := client.(type) { + case *telebit.ConnWrap: + wconn = conn + default: + // this probably isn't strictly necessary + panic("*SubscriberConn.Serve is special in that it must receive &ConnWrap{ Conn: conn }") + } + + id := client.RemoteAddr().String() + s.Clients.Store(id, client) + + fmt.Println("[debug] cancel all the clients") + _ = client.Close() + + // TODO + // - Encode each client to the tunnel + // - Find the right client for decoded messages + + // TODO which order is remote / local? + srcParts := strings.Split(client.RemoteAddr().String(), ":") + srcAddr := srcParts[0] + srcPort, _ := strconv.Atoi(srcParts[1]) + + dstParts := strings.Split(client.LocalAddr().String(), ":") + dstAddr := dstParts[0] + dstPort, _ := strconv.Atoi(dstParts[1]) + + termination := telebit.Unknown + scheme := telebit.None + if 80 == dstPort { + // TODO dstAddr = wconn.Servername() + scheme = telebit.HTTP + } else if 443 == dstPort { + dstAddr = wconn.Servername() + scheme = telebit.HTTPS + } + + src := telebit.NewAddr( + scheme, + termination, + srcAddr, + srcPort, + ) + dst := telebit.NewAddr( + scheme, + termination, + dstAddr, + dstPort, + ) + + err := s.MultiEncoder.Encode(wconn, *src, *dst) + s.Clients.Delete(id) + return err +} + +func GetServer(servername string) (*SubscriberConn, bool) { + var srv *SubscriberConn + load := -1 + // TODO match *.whatever.com + srvMapX, ok := Table.Load(servername) + if !ok { + return nil, false + } + + srvMap := srvMapX.(*sync.Map) + srvMap.Range(func(k, v interface{}) bool { + myLoad := 0 + mySrv := v.(*SubscriberConn) + mySrv.Clients.Range(func(k, v interface{}) bool { + load += 1 + return true + }) + // pick the least loaded server + if -1 == load || myLoad < load { + load = myLoad + srv = mySrv + } + return true + }) + + return srv, true +} diff --git a/vendor/modules.txt b/vendor/modules.txt index 8ed84b2..985eb94 100644 --- a/vendor/modules.txt +++ b/vendor/modules.txt @@ -1,23 +1,47 @@ +# 9fans.net/go v0.0.2 +## explicit # git.rootprojects.org/root/go-gitver v1.1.3 ## explicit git.rootprojects.org/root/go-gitver git.rootprojects.org/root/go-gitver/gitver +# github.com/Djarvur/go-err113 v0.1.0 +## explicit +# github.com/alecthomas/gometalinter v3.0.0+incompatible +## explicit +# github.com/alecthomas/units v0.0.0-20190924025748-f65c72e2690d +## explicit # github.com/alexbrainman/sspi v0.0.0-20180613141037-e580b900e9f5 github.com/alexbrainman/sspi github.com/alexbrainman/sspi/negotiate +# github.com/bombsimon/wsl/v3 v3.1.0 +## explicit # github.com/caddyserver/certmagic v0.10.12 ## explicit github.com/caddyserver/certmagic # github.com/cenkalti/backoff/v4 v4.0.0 github.com/cenkalti/backoff/v4 +# github.com/cosiner/argv v0.1.0 +## explicit # github.com/davecgh/go-spew v1.1.1 github.com/davecgh/go-spew/spew +# github.com/davidrjenni/reftools v0.0.0-20191222082827-65925cf01315 +## explicit # github.com/denisbrodbeck/machineid v1.0.1 ## explicit github.com/denisbrodbeck/machineid # github.com/dgrijalva/jwt-go v3.2.0+incompatible ## explicit github.com/dgrijalva/jwt-go +# github.com/fatih/color v1.9.0 +## explicit +# github.com/fatih/gomodifytags v1.6.0 +## explicit +# github.com/fatih/motion v1.1.0 +## explicit +# github.com/fatih/structtag v1.2.0 +## explicit +# github.com/fsnotify/fsnotify v1.4.9 +## explicit # github.com/go-acme/lego/v3 v3.7.0 ## explicit github.com/go-acme/lego/v3/acme @@ -44,12 +68,30 @@ github.com/go-acme/lego/v3/registration ## explicit github.com/go-chi/chi github.com/go-chi/chi/middleware +# github.com/go-critic/go-critic v0.5.0 +## explicit +# github.com/go-delve/delve v1.4.1 +## explicit +# github.com/gogo/protobuf v1.3.1 +## explicit +# github.com/golangci/gocyclo v0.0.0-20180528144436-0a533e8fa43d +## explicit +# github.com/golangci/golangci-lint v1.27.0 +## explicit +# github.com/golangci/misspell v0.3.5 +## explicit +# github.com/golangci/revgrep v0.0.0-20180812185044-276a5c0a1039 +## explicit +# github.com/google/shlex v0.0.0-20191202100458-e7afc7fbc510 +## explicit # github.com/gorilla/mux v1.7.4 ## explicit github.com/gorilla/mux # github.com/gorilla/websocket v1.4.2 ## explicit github.com/gorilla/websocket +# github.com/gostaticanalysis/analysisutil v0.1.0 +## explicit # github.com/hashicorp/go-uuid v1.0.2 github.com/hashicorp/go-uuid # github.com/jcmturner/aescts/v2 v2.0.0 @@ -97,7 +139,9 @@ github.com/jcmturner/gokrb5/v8/types # github.com/jcmturner/rpc/v2 v2.0.2 github.com/jcmturner/rpc/v2/mstypes github.com/jcmturner/rpc/v2/ndr -# github.com/jmoiron/sqlx v1.2.0 +# github.com/jirfag/go-printf-func-name v0.0.0-20200119135958-7558a9eaa5af +## explicit +# github.com/jmoiron/sqlx v1.2.1-0.20190826204134-d7d95172beb5 ## explicit github.com/jmoiron/sqlx github.com/jmoiron/sqlx/reflectx @@ -105,17 +149,47 @@ github.com/jmoiron/sqlx/reflectx ## explicit github.com/joho/godotenv github.com/joho/godotenv/autoload +# github.com/josharian/impl v1.0.0 +## explicit +# github.com/jstemmer/gotags v1.4.1 +## explicit +# github.com/kisielk/errcheck v1.3.0 +## explicit +# github.com/klauspost/asmfmt v1.2.1 +## explicit # github.com/klauspost/cpuid v1.2.3 github.com/klauspost/cpuid +# github.com/koron/iferr v0.0.0-20180615142939-bb332a3b1d91 +## explicit # github.com/lib/pq v1.6.0 ## explicit github.com/lib/pq github.com/lib/pq/oid github.com/lib/pq/scram +# github.com/mattn/go-colorable v0.1.7 +## explicit +# github.com/mattn/go-runewidth v0.0.9 +## explicit +# github.com/mdempsky/gocode v0.0.0-20200405233807-4acdcbdea79d +## explicit # github.com/miekg/dns v1.1.27 github.com/miekg/dns +# github.com/mitchellh/mapstructure v1.3.2 +## explicit +# github.com/nicksnyder/go-i18n v1.10.1 +## explicit +# github.com/pelletier/go-toml v1.8.0 +## explicit +# github.com/peterh/liner v1.2.0 +## explicit # github.com/pmezard/go-difflib v1.0.0 github.com/pmezard/go-difflib/difflib +# github.com/quasilyte/regex/syntax v0.0.0-20200419152657-af9db7f4a3ab +## explicit +# github.com/rogpeppe/godef v1.1.2 +## explicit +# github.com/ryancurrah/gomodguard v1.1.0 +## explicit # github.com/shurcooL/httpfs v0.0.0-20190707220628-8d4bc4ba7749 ## explicit github.com/shurcooL/httpfs/vfsutil @@ -123,16 +197,48 @@ github.com/shurcooL/httpfs/vfsutil ## explicit github.com/shurcooL/vfsgen github.com/shurcooL/vfsgen/cmd/vfsgendev -# github.com/stretchr/testify v1.5.1 +# github.com/sourcegraph/go-diff v0.5.3 +## explicit +# github.com/spf13/afero v1.3.1 +## explicit +# github.com/spf13/cast v1.3.1 +## explicit +# github.com/spf13/cobra v1.0.0 +## explicit +# github.com/spf13/jwalterweatherman v1.1.0 +## explicit +# github.com/spf13/pflag v1.0.5 +## explicit +# github.com/spf13/viper v1.7.0 +## explicit +# github.com/stamblerre/gocode v1.0.0 +## explicit +# github.com/stretchr/objx v0.2.0 +## explicit +# github.com/stretchr/testify v1.6.1 ## explicit github.com/stretchr/testify/assert github.com/stretchr/testify/require +# github.com/tdakkota/asciicheck v0.0.0-20200416200610-e657995f937b +## explicit +# github.com/tetafro/godot v0.4.2 +## explicit +# github.com/timakin/bodyclose v0.0.0-20200424151742-cb6215831a94 +## explicit +# github.com/zmb3/gogetdoc v0.0.0-20190228002656-b37376c5da6a +## explicit +# go.starlark.net v0.0.0-20200619143648-50ca820fafb9 +## explicit +# golang.org/x/arch v0.0.0-20200511175325-f7c78586839d +## explicit # golang.org/x/crypto v0.0.0-20200311171314-f7b00557c8c4 golang.org/x/crypto/ed25519 golang.org/x/crypto/ed25519/internal/edwards25519 golang.org/x/crypto/md4 golang.org/x/crypto/ocsp golang.org/x/crypto/pbkdf2 +# golang.org/x/mod v0.3.0 +## explicit # golang.org/x/net v0.0.0-20200301022130-244492dfa37a golang.org/x/net/bpf golang.org/x/net/http2/hpack @@ -141,15 +247,26 @@ golang.org/x/net/internal/iana golang.org/x/net/internal/socket golang.org/x/net/ipv4 golang.org/x/net/ipv6 -# golang.org/x/sys v0.0.0-20200302150141-5c8b2ff67527 +# golang.org/x/sys v0.0.0-20200625212154-ddb9806d33ae +## explicit +golang.org/x/sys/internal/unsafeheader golang.org/x/sys/unix golang.org/x/sys/windows golang.org/x/sys/windows/registry -# golang.org/x/text v0.3.2 +# golang.org/x/text v0.3.3 +## explicit golang.org/x/text/secure/bidirule golang.org/x/text/transform golang.org/x/text/unicode/bidi golang.org/x/text/unicode/norm +# golang.org/x/tools v0.0.0-20200626171337-aa94e735be7f +## explicit +# golang.org/x/tools/gopls v0.4.1 +## explicit +# gopkg.in/alecthomas/kingpin.v3-unstable v3.0.0-20191105091915-95d230a53780 +## explicit +# gopkg.in/ini.v1 v1.57.0 +## explicit # gopkg.in/natefinch/lumberjack.v2 v2.0.0 ## explicit gopkg.in/natefinch/lumberjack.v2 @@ -157,5 +274,14 @@ gopkg.in/natefinch/lumberjack.v2 gopkg.in/square/go-jose.v2 gopkg.in/square/go-jose.v2/cipher gopkg.in/square/go-jose.v2/json -# gopkg.in/yaml.v2 v2.2.8 -gopkg.in/yaml.v2 +# gopkg.in/yaml.v2 v2.3.0 +## explicit +# gopkg.in/yaml.v3 v3.0.0-20200615113413-eeeca48fe776 +## explicit +gopkg.in/yaml.v3 +# honnef.co/go/tools v0.0.1-2020.1.4 +## explicit +# mvdan.cc/unparam v0.0.0-20200501210554-b37ab49443f7 +## explicit +# sourcegraph.com/sqs/pbtypes v1.0.0 +## explicit