diff --git a/Dockerfile b/Dockerfile new file mode 100644 index 0000000..c757f58 --- /dev/null +++ b/Dockerfile @@ -0,0 +1,18 @@ +FROM docker.io/golang:1.16-alpine AS base + +RUN apk --update --no-cache add bash build-base + +WORKDIR /build +COPY . /build + +RUN CGO_ENABLED=0 go build -ldflags="-extldflags=-static" -o proxy ./cmd/proxy +RUN CGO_ENABLED=0 go build -ldflags="-extldflags=-static" -o coap ./cmd/coap +RUN CGO_ENABLED=0 go build -ldflags="-extldflags=-static" -o jc ./cmd/jc + +FROM alpine:latest + +COPY --from=base /build/proxy /usr/bin +COPY --from=base /build/coap /usr/bin +COPY --from=base /build/jc /usr/bin + +ENTRYPOINT [ "/usr/bin/proxy" ] diff --git a/cbor_v1.go b/cbor_v1.go index 0a2c0c0..07dff7c 100644 --- a/cbor_v1.go +++ b/cbor_v1.go @@ -119,4 +119,50 @@ var cborv1Keys = map[string]int{ "errcode": 102, "error": 103, "room_alias": 104, + "server": 105, + "version": 106, + "method": 107, + "old_verify_keys": 108, + "server_name": 109, + "valid_until_ts": 110, + "verify_keys": 111, + "expired_ts": 112, + "key": 113, + "server_keys": 114, + "destination": 115, + "edus": 116, + "pdus": 117, + "edu_type": 118, + "auth_chain": 119, + "earliest_events": 120, + "latest_events": 121, + "limit": 122, + "min_depth": 123, + "auth_chain_ids": 124, + "pdu_ids": 125, + "invite_room_state": 126, + "invites": 127, + "mxid": 128, + "signed": 129, + "aliases": 130, + "total_room_count_estimate": 131, + "canonical_alias": 132, + "guest_can_join": 133, + "num_joined_members": 134, + "world_readable": 135, + "push": 136, + "currently_active": 137, + "last_active_ago": 138, + "status_msg": 139, + "ts": 140, + "master_key": 141, + "self_signing_keys": 142, + "stream_id": 143, + "keys": 144, + "algorithms": 145, + "usage": 146, + "deleted": 147, + "prev_id": 148, + "master_keys": 149, + "self_signing_key": 151, } diff --git a/cmd/proxy/main.go b/cmd/proxy/main.go index a4453e5..5772876 100644 --- a/cmd/proxy/main.go +++ b/cmd/proxy/main.go @@ -18,7 +18,9 @@ import ( "crypto/tls" "flag" "io" + "net" "os" + "strconv" "strings" "github.com/matrix-org/lb" @@ -26,9 +28,10 @@ import ( ) var ( - dtlsBindAddr = flag.String("dtls-bind-addr", ":8008", "The DTLS UDP listening port for the server") - localAddr = flag.String("local", "", "The HTTP server to forward inbound CoAP requests to e.g http://localhost:8008") - advertise = flag.String("advertise", "", + dtlsBindAddr = flag.String("dtls-bind-addr", ":8008", "The DTLS UDP listening port for the server") + proxyBindAddr = flag.String("proxy-bind-addr", "", "The HTTP server to act as a transparent proxy for outbound requests") + localAddr = flag.String("local", "", "The HTTP server to forward inbound CoAP requests to e.g http://localhost:8008") + advertise = flag.String("advertise", "", "Optional: the public address of this proxy. If set, sniffs logins/registrations for homeserver discovery information and replaces the base_url with this advertising address. "+ "This is useful when the local server is not on the same machine as the proxy.") certFile = flag.String("tls-cert", "", "The PEM formatted X509 certificate to use for TLS") @@ -62,15 +65,26 @@ func main() { } } + _, outboundStr, err := net.SplitHostPort(*dtlsBindAddr) + if err != nil { + panic(err) + } + outboundPort, err := strconv.Atoi(outboundStr) + if err != nil { + panic(err) + } + err = RunProxyServer(&Config{ - ListenDTLS: *dtlsBindAddr, - LocalAddr: *localAddr, - Certificates: certs, - KeyLogWriter: keyLogWriter, - Advertise: *advertise, - AdvertiseOnHTTPS: *advertise != "" && strings.HasPrefix(*advertise, "https://"), - CBORCodec: lb.NewCBORCodecV1(false), - CoAPHTTP: lb.NewCoAPHTTP(lb.NewCoAPPathV1()), + ListenDTLS: *dtlsBindAddr, + ListenProxy: *proxyBindAddr, + LocalAddr: *localAddr, + OutboundFederationPort: outboundPort, + Certificates: certs, + KeyLogWriter: keyLogWriter, + Advertise: *advertise, + AdvertiseOnHTTPS: *advertise != "" && strings.HasPrefix(*advertise, "https://"), + CBORCodec: lb.NewCBORCodecV1(true), + CoAPHTTP: lb.NewCoAPHTTP(lb.NewCoAPPathV1()), }) if err != nil { logrus.Panicf("RunProxyServer: %s", err) diff --git a/cmd/proxy/proxy.go b/cmd/proxy/proxy.go index fdc392d..cdfe959 100644 --- a/cmd/proxy/proxy.go +++ b/cmd/proxy/proxy.go @@ -19,25 +19,33 @@ import ( "bytes" "context" "crypto/tls" + "fmt" "io" "io/ioutil" + "net" "net/http" "net/http/httputil" "net/url" + "os" + "os/signal" + "strings" "sync/atomic" + "syscall" "time" + "github.com/matrix-org/go-coap/v2/coap" "github.com/matrix-org/go-coap/v2/dtls" "github.com/matrix-org/go-coap/v2/message" "github.com/matrix-org/go-coap/v2/message/codes" "github.com/matrix-org/go-coap/v2/mux" coapmux "github.com/matrix-org/go-coap/v2/mux" - "github.com/matrix-org/go-coap/v2/net" + coapNet "github.com/matrix-org/go-coap/v2/net" "github.com/matrix-org/go-coap/v2/net/blockwise" "github.com/matrix-org/go-coap/v2/udp/client" udpMessage "github.com/matrix-org/go-coap/v2/udp/message" "github.com/matrix-org/go-coap/v2/udp/message/pool" "github.com/matrix-org/lb" + "github.com/matrix-org/lb/mobile" piondtls "github.com/pion/dtls/v2" "github.com/sirupsen/logrus" "github.com/tidwall/gjson" @@ -46,10 +54,12 @@ import ( // Config is the configuration options for the proxy type Config struct { - ListenDTLS string // :8008 - LocalAddr string // http://localhost:1234 - Certificates []tls.Certificate // Certs to use - Advertise string // optional: Where this proxy is running publicly + ListenDTLS string // UDP :8008 + ListenProxy string // TCP :8009 + LocalAddr string // Where Synapse is located: http://localhost:1234 + OutboundFederationPort int // which UDP port will we expect to find DTLS on? + Certificates []tls.Certificate // Certs to use + Advertise string // optional: Where this proxy is running publicly // how long to wait for the server to send a response before sending an ACK back // If this is too short, the proxy server will send more packets than it should (1x ACK, 1x Response) // and not do any piggybacking. @@ -62,10 +72,10 @@ type Config struct { CoAPHTTP *lb.CoAPHTTP KeyLogWriter io.Writer Client *http.Client -} - -type handler interface { - ServeCOAP(w client.ResponseWriter, r *message.Message, udpMsg *pool.Message) + // Optional. If set, will route federation requests via this packet conn instead of DTLS + OutgoingFederationPacketConn net.PacketConn + IncomingFederationPacketConn net.PacketConn + FederationAddrResolver func(host string) net.Addr } type muxResponseWriter struct { @@ -90,7 +100,7 @@ func forwardToLocalAddr(cfg *Config) http.HandlerFunc { if err != nil { logrus.WithError(err).Error("failed to read incoming request body") w.WriteHeader(500) - w.Write([]byte(`Failed to read request body: ` + err.Error())) + _, _ = w.Write([]byte(`Failed to read request body: ` + err.Error())) return } if req.Header.Get("Content-Type") == "application/cbor" { @@ -98,19 +108,21 @@ func forwardToLocalAddr(cfg *Config) http.HandlerFunc { if err != nil { logrus.WithError(err).Error("failed to convert incoming request body from JSON to CBOR") w.WriteHeader(500) - w.Write([]byte(`Failed to convert CBOR to JSON: ` + err.Error())) + _, _ = w.Write([]byte(`Failed to convert CBOR to JSON: ` + err.Error())) return } } reqURL := *req.URL reqURL.Scheme = localURL.Scheme reqURL.Host = localURL.Host + reqURL.ForceQuery = false + reqURL.RawQuery = req.URL.RawQuery newReq, err := http.NewRequest(req.Method, reqURL.String(), bytes.NewBuffer(body)) if err != nil { logrus.WithError(err).Error("failed to form proxy HTTP request") w.WriteHeader(500) - w.Write([]byte("failed to form corresponding HTTP request")) + _, _ = w.Write([]byte("failed to form corresponding HTTP request")) return } // copy headers @@ -123,7 +135,7 @@ func forwardToLocalAddr(cfg *Config) http.HandlerFunc { if err != nil { logrus.WithError(err).Error("failed to contact local address") w.WriteHeader(http.StatusBadGateway) - w.Write([]byte("Failed to contact local address")) + _, _ = w.Write([]byte("Failed to contact local address")) return } resBody := writeResponse(cfg, res, w) @@ -144,7 +156,7 @@ func writeResponse(cfg *Config, res *http.Response, w http.ResponseWriter) []byt if err != nil { logrus.WithError(err).Error("failed to read local response body") w.WriteHeader(http.StatusBadGateway) - w.Write([]byte("Failed to read local response body")) + _, _ = w.Write([]byte("Failed to read local response body")) return resBody } if cfg.Advertise != "" { @@ -170,7 +182,7 @@ func writeResponse(cfg *Config, res *http.Response, w http.ResponseWriter) []byt if err != nil { logrus.WithError(err).WithField("body", string(jsonBody)).Error("failed to convert response body from JSON to CBOR") w.WriteHeader(http.StatusBadGateway) - w.Write([]byte("Failed to convert response body from JSON to CBOR")) + _, _ = w.Write([]byte("Failed to convert response body from JSON to CBOR")) return resBody } } @@ -181,7 +193,7 @@ func writeResponse(cfg *Config, res *http.Response, w http.ResponseWriter) []byt } } w.WriteHeader(res.StatusCode) - w.Write(resBody) + _, _ = w.Write(resBody) return resBody } @@ -194,7 +206,7 @@ func (l *logger) Printf(format string, v ...interface{}) { // listenAndServeDTLS Starts a server on address and network over DTLS specified Invoke handler // for incoming queries. func listenAndServeDTLS(network string, addr string, config *piondtls.Config, waitACK time.Duration, handler coapmux.Handler) error { - l, err := net.NewDTLSListener(network, addr, config) + l, err := coapNet.NewDTLSListener(network, addr, config) if err != nil { return err } @@ -246,6 +258,29 @@ func listenAndServeDTLS(network string, addr string, config *piondtls.Config, wa return s.Serve(l) } +func (cfg *Config) proxyToDTLS(w http.ResponseWriter, r *http.Request) { + logrus.Debugf("Federation proxy %s", r.URL.RequestURI()) + body, err := ioutil.ReadAll(r.Body) + if err != nil { + w.WriteHeader(500) + } + res := mobile.SendRequest( + r.Method, + fmt.Sprintf("https://%s:%d%s", r.Host, cfg.OutboundFederationPort, r.URL.RequestURI()), // TODO: make less yuck + strings.TrimPrefix(r.Header.Get("Authorization"), "X-Matrix "), + string(body), + true, + ) + if res == nil { + logrus.Warnf("request %s failed", r.URL.RequestURI()) + w.WriteHeader(500) + return + } + w.Header().Set("Content-Type", "application/json") + w.WriteHeader(res.Code) + _, _ = w.Write([]byte(res.Body)) +} + func RunProxyServer(cfg *Config) error { // run the DTLS server dtlsConfig := &piondtls.Config{ @@ -263,36 +298,90 @@ func RunProxyServer(cfg *Config) error { cfg.WaitTimeBeforeACK = 5 * time.Second } - go func() { - r := coapmux.NewRouter() - handler := http.HandlerFunc(forwardToLocalAddr(cfg)) - observations := lb.NewSyncObservations(handler, cfg.CoAPHTTP.Paths, cfg.CBORCodec) - observations.Log = &logger{} - cfg.CoAPHTTP.Log = &logger{} - r.DefaultHandle(cfg.CoAPHTTP.CoAPHTTPHandler( - handler, observations, - )) - logrus.Infof("Listening for DTLS on %s - ACK piggyback period: %v", cfg.ListenDTLS, cfg.WaitTimeBeforeACK) - if err := listenAndServeDTLS("udp", cfg.ListenDTLS, dtlsConfig, cfg.WaitTimeBeforeACK, r); err != nil { - logrus.WithError(err).Panicf("Failed to ListenAndServeDTLS") - } - }() + if cfg.ListenDTLS != "" { + go func() { + dtlsRouter := coapmux.NewRouter() + handler := http.HandlerFunc(forwardToLocalAddr(cfg)) + observations := lb.NewSyncObservations(handler, cfg.CoAPHTTP.Paths, cfg.CBORCodec) + observations.Log = &logger{} + cfg.CoAPHTTP.Log = &logger{} + dtlsRouter.DefaultHandle(cfg.CoAPHTTP.CoAPHTTPHandler( + handler, observations, + )) + logrus.Infof("Proxying inbound DTLS->HTTP on %s (ACK piggyback period: %v)", cfg.ListenDTLS, cfg.WaitTimeBeforeACK) + if err := listenAndServeDTLS("udp", cfg.ListenDTLS, dtlsConfig, cfg.WaitTimeBeforeACK, dtlsRouter); err != nil { + logrus.WithError(err).Panicf("Failed to ListenAndServeDTLS") + } + }() + } + + if cfg.ListenProxy != "" { + go func() { + logrus.Infof("Proxying outbound HTTP->DTLS on %s", cfg.ListenProxy) + logrus.Infof("Outbound federation will go to port UDP/%d", cfg.OutboundFederationPort) + proxyRouter := http.NewServeMux() + proxyRouter.HandleFunc("/", cfg.proxyToDTLS) + + if cfg.OutgoingFederationPacketConn != nil && cfg.FederationAddrResolver != nil { + logrus.Infof("Custom OutgoingFederationPacketConn in use") + mobile.SetCustomConn(cfg.OutgoingFederationPacketConn, cfg.FederationAddrResolver) + } + + if err := http.ListenAndServe(cfg.ListenProxy, proxyRouter); err != nil { + logrus.WithError(err).Panicf("failed to ListenAndServe for proxy") + } + }() + } + + if cfg.IncomingFederationPacketConn != nil { + go func() { + logrus.Infof("Listening for CoAP messages on IncomingFederationPacketConn") + activeConnectionParams := mobile.Params() + newCfg := coap.NewConfig( + coap.WithErrors(func(err error) { + logrus.Warnf("coap error: %s", err) + }), + coap.WithHeartBeat(time.Duration(activeConnectionParams.HeartbeatTimeoutSecs)*time.Second), + coap.WithKeepAlive(uint32(activeConnectionParams.KeepAliveMaxRetries), time.Duration(activeConnectionParams.KeepAliveTimeoutSecs)*time.Second, func(cc interface { + Close() error + Context() context.Context + }) { + return + }), + coap.WithTransmission( + // FIXME? https://github.com/plgd-dev/go-coap/issues/226 + time.Duration(activeConnectionParams.TransmissionNStart)*time.Second, + time.Duration(activeConnectionParams.TransmissionACKTimeoutSecs)*time.Second, + activeConnectionParams.TransmissionMaxRetransmits, + ), + coap.WithBlockwise(true, blockwise.SZX1024, 2*time.Minute), + coap.WithLogger(&logger{}), + ) + srv := newCfg.NewServer(cfg.IncomingFederationPacketConn) + if err := srv.Serve(); err != nil { + logrus.Errorf("failed to Serve: %s", err) + } + }() + } if cfg.Advertise != "" { - logrus.Infof("Listening on %s/tcp to reverse proxy from %s to %s - HTTPS enabled: %v", cfg.ListenDTLS, cfg.Advertise, cfg.LocalAddr, cfg.AdvertiseOnHTTPS) + logrus.Infof("Proxying inbound HTTP on %s (forward to %s)", cfg.LocalAddr, cfg.Advertise) localURL, err := url.Parse(cfg.LocalAddr) if err != nil { panic(err) } - rp2 := httputil.NewSingleHostReverseProxy(localURL) + rp := &httputil.ReverseProxy{ + Transport: &http.Transport{}, Director: func(req *http.Request) { - rp2.Director(req) - logrus.Infof("TCP proxy %v", req.URL.String()) + httputil.NewSingleHostReverseProxy(localURL).Director(req) + logrus.Debugf("Reverse proxy %s", req.URL.String()) req.Host = localURL.Host }, } + if cfg.AdvertiseOnHTTPS { + logrus.Infof("Listening for TCP+TLS on %s", cfg.ListenDTLS) tlsServer := &http.Server{ Addr: cfg.ListenDTLS, Handler: rp, @@ -304,11 +393,15 @@ func RunProxyServer(cfg *Config) error { logrus.WithError(err).Panicf("failed to ListenAndServeTLS") } } else { + logrus.Infof("Listening for TCP on %s", cfg.ListenDTLS) if err := http.ListenAndServe(cfg.ListenDTLS, rp); err != nil { logrus.WithError(err).Panicf("failed to ListenAndServe") } } } - select {} // block forever + c := make(chan os.Signal, 1) + signal.Notify(c, os.Interrupt, syscall.SIGTERM) + <-c + return fmt.Errorf("interrupted by signal") } diff --git a/cmd/proxy/proxy_test.go b/cmd/proxy/proxy_test.go new file mode 100644 index 0000000..b109104 --- /dev/null +++ b/cmd/proxy/proxy_test.go @@ -0,0 +1,165 @@ +package main + +import ( + "bytes" + "context" + "fmt" + "io/ioutil" + "net" + "net/http" + "testing" + "time" + + "github.com/matrix-org/go-coap/v2/message" + "github.com/matrix-org/go-coap/v2/message/codes" + udpMessage "github.com/matrix-org/go-coap/v2/udp/message" + "github.com/matrix-org/go-coap/v2/udp/message/pool" + "github.com/matrix-org/lb" +) + +type customAddr struct { + host string +} + +func (a *customAddr) Network() string { + return "test" +} + +func (a *customAddr) String() string { + return a.host +} + +// channelPacketConn is a net.PacketConn using channels. It can only talk to one remote addr marked +// by 'raddr'. +type channelPacketConn struct { + reads chan []byte + writes chan []byte + laddr net.Addr + raddr net.Addr +} + +// ReadFrom reads a packet from the connection, +// copying the payload into p. It returns the number of +// bytes copied into p and the return address that +// was on the packet. +// It returns the number of bytes read (0 <= n <= len(p)) +// and any error encountered. Callers should always process +// the n > 0 bytes returned before considering the error err. +// ReadFrom can be made to time out and return +// an Error with Timeout() == true after a fixed time limit; +// see SetDeadline and SetReadDeadline. +func (c *channelPacketConn) ReadFrom(p []byte) (n int, addr net.Addr, err error) { + for data := range c.reads { + n = copy(p, data) + return n, c.raddr, nil + } + return 0, nil, fmt.Errorf("read on closed chan: %+v", c.reads) +} + +// WriteTo writes a packet with payload p to addr. +// WriteTo can be made to time out and return +// an Error with Timeout() == true after a fixed time limit; +// see SetDeadline and SetWriteDeadline. +// On packet-oriented connections, write timeouts are rare. +func (c *channelPacketConn) WriteTo(p []byte, addr net.Addr) (n int, err error) { + c.writes <- p + return len(p), nil +} +func (c *channelPacketConn) SetDeadline(t time.Time) error { return nil } +func (c *channelPacketConn) SetReadDeadline(t time.Time) error { return nil } +func (c *channelPacketConn) SetWriteDeadline(t time.Time) error { return nil } +func (c *channelPacketConn) Close() error { + close(c.reads) + close(c.writes) + return nil +} +func (c *channelPacketConn) LocalAddr() net.Addr { + return c.laddr +} + +// Test that a custom packet conn can be used to make client requests. Tested by hitting a fake /versions +func TestOutboundCustomPacketConn(t *testing.T) { + pconn := &channelPacketConn{ + reads: make(chan []byte), + writes: make(chan []byte), + laddr: &customAddr{"local"}, + raddr: &customAddr{"remote"}, + } + cborCodec := lb.NewCBORCodecV1(true) + cfg := &Config{ + ListenProxy: ":8091", + CBORCodec: cborCodec, + CoAPHTTP: lb.NewCoAPHTTP(lb.NewCoAPPathV1()), + OutgoingFederationPacketConn: pconn, + FederationAddrResolver: func(host string) net.Addr { + return &customAddr{host} + }, + } + + go func() { + if err := RunProxyServer(cfg); err != nil { + t.Errorf("RunProxyServer returned error: %s", err) + } + }() + time.Sleep(100 * time.Millisecond) // yuck + + jsonBody := []byte(`{"versions":["0.6.0"]}`) + cborBody, err := cborCodec.JSONToCBOR(bytes.NewBuffer(jsonBody)) + if err != nil { + t.Fatalf("failed to convert json to cbor: %s", err) + } + + go func() { + // we expect a write for GET /versions + for data := range pconn.writes { + input := pool.AcquireMessage(context.Background()) + _, err := input.Unmarshal(data) + if err != nil { + t.Errorf("failed to unmarshal msg: %s", err) + return + } + if input.Code() != codes.GET { + t.Errorf("proxied wrong code, got %v want %v", input.Code(), codes.GET) + } + path, err := input.Options().Path() + if err != nil { + t.Errorf("failed to get path: %s", err) + } + fmt.Printf("recv %+v \n", input) + + // important that mid, token, path, type, etc are set else go-coap won't know this is + // a response to the request + msg := pool.AcquireMessage(context.Background()) + msg.SetCode(codes.Content) + msg.SetContentFormat(message.TextPlain) + msg.SetMessageID(input.MessageID()) + msg.SetToken(input.Token()) + msg.SetPath(path) + msg.SetType(udpMessage.Acknowledgement) + msg.SetBody(bytes.NewReader(cborBody)) + output, err := msg.Marshal() + if err != nil { + t.Errorf("failed to marshal output msg: %s", err) + } + fmt.Printf("responding %x\n", output) + pconn.reads <- output + } + }() + + // send in some HTTP, expect it to be proxied + resp, err := http.Get("http://localhost:8091/_matrix/client/versions") + if err != nil { + t.Fatalf("failed to GET: %s", err) + } + if resp.StatusCode != 200 { + t.Fatalf("Bad response status code, got %d want 200", resp.StatusCode) + } + defer resp.Body.Close() + body, err := ioutil.ReadAll(resp.Body) + if err != nil { + t.Fatalf("failed to read HTTP response: %s", err) + } + if !bytes.Equal(body, jsonBody) { + t.Fatalf("bad response body, got %s want %s", string(body), string(jsonBody)) + } +} diff --git a/coap.go b/coap.go index 0e54fc6..7e4a9fc 100644 --- a/coap.go +++ b/coap.go @@ -26,7 +26,8 @@ import ( const ctxValAccessToken = "ctxValAccessToken" // The CoAP Option ID corresponding to the access_token for Matrix requests -var OptionIDAccessToken = message.OptionID(256) +var OptionIDAuthorizationBearerToken = message.OptionID(256) +var OptionIDAuthorizationXMatrixToken = message.OptionID(257) var methodCodes = map[codes.Code]string{ codes.POST: "POST", diff --git a/coap_http.go b/coap_http.go index de4e5d0..6654a83 100644 --- a/coap_http.go +++ b/coap_http.go @@ -22,7 +22,6 @@ import ( "io" "io/ioutil" "net/http" - "net/url" "strings" "github.com/matrix-org/go-coap/v2/message" @@ -172,28 +171,13 @@ func (co *CoAPHTTP) CoAPToHTTPRequest(r *message.Message) *http.Request { if !strings.HasPrefix(optPath, "/") { optPath = "/" + optPath } - path := co.Paths.CoAPPathToHTTPPath(optPath) - if strings.HasPrefix(path, "/") { - path = path[1:] - } + path := strings.TrimPrefix(co.Paths.CoAPPathToHTTPPath(optPath), "/") // go-coap doesn't combine queries nor does it separate key/values queries, err := r.Options.Queries() if err != nil && err != message.ErrOptionNotFound { co.log("failed to extract Uri-Query option: %s", err) return nil } - query := make(url.Values) - for _, qs := range queries { - kvs := strings.SplitN(qs, "=", 2) - if len(kvs) != 2 { - co.log("ignoring malformed query string: %s", qs) - continue - } - // allow repeating query params e.g ?foo=1&foo=2 => { "foo": [ "1", "2" ]} - q := query[kvs[0]] - q = append(q, kvs[1]) - query[kvs[0]] = q - } var body []byte if r.Body != nil { body, err = ioutil.ReadAll(r.Body) @@ -202,7 +186,11 @@ func (co *CoAPHTTP) CoAPToHTTPRequest(r *message.Message) *http.Request { return nil } } - req, err := http.NewRequest(method, "https://localhost/"+path+"?"+query.Encode(), bytes.NewReader(body)) + localURL := "https://localhost/" + path + if len(queries) > 0 { + localURL += "?" + strings.Join(queries, "&") + } + req, err := http.NewRequest(method, localURL, bytes.NewReader(body)) if err != nil { co.log("CoAPToHTTPRequest: failed to create HTTP request: %s", err) } @@ -215,10 +203,16 @@ func (co *CoAPHTTP) CoAPToHTTPRequest(r *message.Message) *http.Request { } } - accessToken, _ := r.Options.GetString(OptionIDAccessToken) + accessToken, _ := r.Options.GetString(OptionIDAuthorizationBearerToken) if accessToken != "" { req.Header.Set("Authorization", "Bearer "+accessToken) } + + federationAuth, _ := r.Options.GetString(OptionIDAuthorizationXMatrixToken) + if federationAuth != "" { + req.Header.Set("Authorization", "X-Matrix "+federationAuth) + } + return req } @@ -255,11 +249,12 @@ func (co *CoAPHTTP) HTTPRequestToCoAP(req *http.Request, doFn func(*pool.Message msg.SetToken(co.NextToken()) msg.SetCode(code) msg.SetPath(co.Paths.HTTPPathToCoapPath(req.URL.Path)) - queries := req.URL.Query() - for k, vs := range queries { - for _, v := range vs { - msg.AddQuery(k + "=" + v) - } + // We have to use req.URL.RawQuery here to ensure that the + // query options get added to the message in order. Using + // req.URL.Query() returns them in a map which loses the + // ordering. + for _, q := range strings.Split(req.URL.RawQuery, "&") { + msg.AddQuery(q) } if req.Body != nil { body, err := ioutil.ReadAll(req.Body) @@ -276,8 +271,11 @@ func (co *CoAPHTTP) HTTPRequestToCoAP(req *http.Request, doFn func(*pool.Message } msg.SetContentFormat(contentFormat) authHeader := req.Header.Get("Authorization") - if strings.HasPrefix(authHeader, "Bearer ") { - msg.SetOptionString(OptionIDAccessToken, strings.TrimPrefix(authHeader, "Bearer ")) + switch { + case strings.HasPrefix(authHeader, "Bearer "): + msg.SetOptionString(OptionIDAuthorizationBearerToken, strings.TrimPrefix(authHeader, "Bearer ")) + case strings.HasPrefix(authHeader, "X-Matrix "): + msg.SetOptionString(OptionIDAuthorizationXMatrixToken, strings.TrimPrefix(authHeader, "X-Matrix ")) } return doFn(msg) } diff --git a/coap_paths.go b/coap_paths.go index 68b5a10..1c8256a 100644 --- a/coap_paths.go +++ b/coap_paths.go @@ -96,7 +96,11 @@ func (c *CoAPPath) CoAPPathToHTTPPath(p string) string { break } if strings.HasPrefix(httpSegments[i], "{") { - httpSegments[i] = url.PathEscape(segments[coapSegIndex]) + // TODO: url.PathEscape is probably the right thing to have here, and that's + // probably what Dendrite uses, but Synapse seems to query-encode everything. + // If we don't match what the origin server does then the federation request + // signatures break, which is helpful. + httpSegments[i] = url.QueryEscape(segments[coapSegIndex]) coapSegIndex++ } } diff --git a/coap_paths_v1.go b/coap_paths_v1.go index 99dd5bd..71b3274 100644 --- a/coap_paths_v1.go +++ b/coap_paths_v1.go @@ -72,4 +72,34 @@ var coapv1pathMappings = map[string]string{ "s": "/_matrix/client/r0/user/{userId}/rooms/{roomId}/account_data/{type}", "t": "/_matrix/client/r0/rooms/{roomId}/context/{eventId}", "u": "/_matrix/client/r0/rooms/{roomId}/report/{eventId}", + + "f0": "/_matrix/federation/v1/version", + "f1": "/_matrix/federation/key/v2/server", + "f2": "/_matrix/federation/key/v2/server/{keyId}", + "f3": "/_matrix/federation/key/v2/query/{serverName}/{keyId}", + "f4": "/_matrix/federation/v1/send/{txnId}", + "f5": "/_matrix/federation/v1/event_auth/{roomId}/{eventId}", + "f6": "/_matrix/federation/v1/backfill/{roomId}", + "f7": "/_matrix/federation/v1/get_missing_events/{roomId}", + "f8": "/_matrix/federation/v1/state/{roomId}", + "f9": "/_matrix/federation/v1/state_ids/{roomId}", + "fA": "/_matrix/federation/v1/event/{eventId}", + "fB": "/_matrix/federation/v1/make_join/{roomId}/{userId}", + "fC": "/_matrix/federation/v1/send_join/{roomId}/{eventId}", + "fD": "/_matrix/federation/v2/send_join/{roomId}/{eventId}", + "fE": "/_matrix/federation/v1/invite/{roomId}/{eventId}", + "fF": "/_matrix/federation/v2/invite/{roomId}/{eventId}", + "fG": "/_matrix/federation/v1/make_leave/{roomId}/{userId}", + "fH": "/_matrix/federation/v1/send_leave/{roomId}/{eventId}", + "fI": "/_matrix/federation/v2/send_leave/{roomId}/{eventId}", + "fJ": "/_matrix/federation/v1/exchange_third_party_invite/{roomId}", + "fK": "/_matrix/federation/v1/3pid/onbind", + "fL": "/_matrix/federation/v1/publicRooms", + "fM": "/_matrix/federation/v1/query/{queryType}", + "fN": "/_matrix/federation/v1/query/directory", + "fO": "/_matrix/federation/v1/query/profile", + "fP": "/_matrix/federation/v1/openid/userinfo", + "fQ": "/_matrix/federation/v1/user/devices/{userId}", + "fR": "/_matrix/federation/v1/user/keys/claim", + "fS": "/_matrix/federation/v1/user/keys/query", } diff --git a/go.mod b/go.mod index 47372dc..14ea60a 100644 --- a/go.mod +++ b/go.mod @@ -5,18 +5,19 @@ go 1.14 require ( github.com/dsnet/golib/memfile v1.0.0 // indirect github.com/fxamacker/cbor/v2 v2.3.0 + github.com/go-ocf/go-coap/v2 v2.0.4-0.20200728125043-f38b86f047a7 github.com/json-iterator/go v1.1.11 - github.com/matrix-org/go-coap/v2 v2.0.0-20210608155919-691db5a1ade4 + github.com/matrix-org/go-coap/v2 v2.0.0-20210622133725-61108bb7222d github.com/matrix-org/gomatrixserverlib v0.0.0-20210302161955-6142fe3f8c2c github.com/matrix-org/util v0.0.0-20200807132607-55161520e1d4 // indirect github.com/pion/dtls/v2 v2.0.10-0.20210502094952-3dc563b9aede - github.com/plgd-dev/kit v0.0.0-20210517115726-034a62788317 // indirect + github.com/plgd-dev/kit v0.0.0-20210614190235-99984a49de48 // indirect github.com/sirupsen/logrus v1.4.2 github.com/tidwall/gjson v1.6.0 github.com/tidwall/sjson v1.0.3 - go.uber.org/atomic v1.7.0 // indirect - golang.org/x/crypto v0.0.0-20210513164829-c07d793c2f9a // indirect - golang.org/x/net v0.0.0-20210525063256-abc453219eb5 // indirect + go.uber.org/atomic v1.8.0 // indirect + golang.org/x/crypto v0.0.0-20210616213533-5ff15b29337e // indirect + golang.org/x/net v0.0.0-20210614182718-04defd469f4e // indirect golang.org/x/sync v0.0.0-20210220032951-036812b2e83c // indirect - golang.org/x/sys v0.0.0-20210608053332-aa57babbf139 // indirect + golang.org/x/sys v0.0.0-20210616094352-59db8d763f22 // indirect ) diff --git a/go.sum b/go.sum index 03969d8..2fb960e 100644 --- a/go.sum +++ b/go.sum @@ -27,6 +27,7 @@ github.com/fxamacker/cbor/v2 v2.3.0/go.mod h1:TA1xS00nchWmaBnEIxPSE5oHLuJBAVvqrt github.com/go-acme/lego v2.7.2+incompatible/go.mod h1:yzMNe9CasVUhkquNvti5nAtPmG94USbYxYrZfTkIn0M= github.com/go-kit/kit v0.9.0/go.mod h1:xBxKIO96dXMWWy0MnWVtmwkA9/13aqxPnvrjFYMA2as= github.com/go-logfmt/logfmt v0.4.0/go.mod h1:3RMwSq7FuexP4Kalkev3ejPJsZTpXXBr9+V4qmtdjCk= +github.com/go-ocf/go-coap/v2 v2.0.4-0.20200728125043-f38b86f047a7 h1:AKdudU3gkKJ+eoESnMWcdyH43liYFXmwva8EMlbmOqc= github.com/go-ocf/go-coap/v2 v2.0.4-0.20200728125043-f38b86f047a7/go.mod h1:X9wVKcaOSx7wBxKcvrWgMQq1R2DNeA7NBLW2osIb8TM= github.com/go-ocf/kit v0.0.0-20200728130040-4aebdb6982bc/go.mod h1:TIsoMT/iB7t9P6ahkcOnsmvS83SIJsv9qXRfz/yLf6M= github.com/go-stack/stack v1.8.0/go.mod h1:v0f6uXyyMGvRgIKkXu+yp6POWl0qKG85gN/melR3HDY= @@ -78,6 +79,12 @@ github.com/lestrrat-go/jwx v1.0.2/go.mod h1:TPF17WiSFegZo+c20fdpw49QD+/7n4/IsGvE github.com/lestrrat-go/pdebug v0.0.0-20200204225717-4d6bd78da58d/go.mod h1:B06CSso/AWxiPejj+fheUINGeBKeeEZNt8w+EoU7+L8= github.com/matrix-org/go-coap/v2 v2.0.0-20210608155919-691db5a1ade4 h1:SwJtJ7XktZNBL7s0rReaxuCoI9PWfW+JG/Zal35ZYa4= github.com/matrix-org/go-coap/v2 v2.0.0-20210608155919-691db5a1ade4/go.mod h1:GC7TQJU2vxrJhItiu5pjhNxmMqPm97wP1rk+xqK60eM= +github.com/matrix-org/go-coap/v2 v2.0.0-20210621174329-40d192016217 h1:wMDRxMNCkIhTLmUy0MuO7rY2cZJdE8H1KXGfSM+skk4= +github.com/matrix-org/go-coap/v2 v2.0.0-20210621174329-40d192016217/go.mod h1:GC7TQJU2vxrJhItiu5pjhNxmMqPm97wP1rk+xqK60eM= +github.com/matrix-org/go-coap/v2 v2.0.0-20210621191305-b4056b077d04 h1:quGOx1hvh30snMvm6eaxY0wSfPD8S/HlieOqPZ0a2/E= +github.com/matrix-org/go-coap/v2 v2.0.0-20210621191305-b4056b077d04/go.mod h1:GC7TQJU2vxrJhItiu5pjhNxmMqPm97wP1rk+xqK60eM= +github.com/matrix-org/go-coap/v2 v2.0.0-20210622133725-61108bb7222d h1:yts0DZ0q40B2YwSZ8C3kGQQ0kWI5BXMtQn0WWdnafy8= +github.com/matrix-org/go-coap/v2 v2.0.0-20210622133725-61108bb7222d/go.mod h1:GC7TQJU2vxrJhItiu5pjhNxmMqPm97wP1rk+xqK60eM= github.com/matrix-org/gomatrix v0.0.0-20190528120928-7df988a63f26 h1:Hr3zjRsq2bhrnp3Ky1qgx/fzCtCALOoGYylh2tpS9K4= github.com/matrix-org/gomatrix v0.0.0-20190528120928-7df988a63f26/go.mod h1:3fxX6gUjWyI/2Bt7J1OLhpCzOfO/bB3AiX0cJtEKud0= github.com/matrix-org/gomatrixserverlib v0.0.0-20210302161955-6142fe3f8c2c h1:vW3jBp1PnZ4uUqyS+JatJRYIl73ZLHkUkRzf1JdGxOI= @@ -95,9 +102,11 @@ github.com/modern-go/reflect2 v0.0.0-20180701023420-4b7aa43c6742/go.mod h1:bx2lN github.com/nbio/st v0.0.0-20140626010706-e9e8d9816f32 h1:W6apQkHrMkS0Muv8G/TipAy/FJl/rCYT0+EuS8+Z0z4= github.com/nbio/st v0.0.0-20140626010706-e9e8d9816f32/go.mod h1:9wM+0iRr9ahx58uYLpLIr5fm8diHn0JbqRycJi6w0Ms= github.com/opentracing/opentracing-go v1.1.0/go.mod h1:UkNAQd3GIcIGf0SeVgPpRdFStlNbqXla1AfSYxPUl2o= +github.com/panjf2000/ants/v2 v2.4.3/go.mod h1:f6F0NZVFsGCp5A7QW/Zj/m92atWwOkY0OIhFxRNFr4A= github.com/patrickmn/go-cache v2.1.0+incompatible h1:HRMgzkcYKYpi3C8ajMPV8OFXaaRUnok+kx1WdO15EQc= github.com/patrickmn/go-cache v2.1.0+incompatible/go.mod h1:3Qf8kWWT7OJRJbdiICTKqZju1ZixQ/KpMGzzAfe6+WQ= github.com/pion/dtls/v2 v2.0.1-0.20200503085337-8e86b3a7d585/go.mod h1:/GahSOC8ZY/+17zkaGJIG4OUkSGAcZu/N/g3roBOCkM= +github.com/pion/dtls/v2 v2.0.9/go.mod h1:O0Wr7si/Zj5/EBFlDzDd6UtVxx25CE1r7XM7BQKYQho= github.com/pion/dtls/v2 v2.0.10-0.20210502094952-3dc563b9aede h1:f/uKAVo6gUJMw00gOWEolJy/0h8LfoaxouHD+Rq4EQo= github.com/pion/dtls/v2 v2.0.10-0.20210502094952-3dc563b9aede/go.mod h1:86wv5dgx2J/z871nUR+5fTTY9tISLUlo+C5Gm86r1Hs= github.com/pion/logging v0.2.2 h1:M9+AIj/+pxNsDfAT64+MAVgJO0rsyLnoJKCqf//DoeY= @@ -112,9 +121,12 @@ github.com/pkg/errors v0.8.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINE github.com/pkg/errors v0.9.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0= github.com/plgd-dev/go-coap/v2 v2.0.4-0.20200819112225-8eb712b901bc/go.mod h1:+tCi9Q78H/orWRtpVWyBgrr4vKFo2zYtbbxUllerBp4= github.com/plgd-dev/go-coap/v2 v2.1.4-0.20201201213140-b8c428d8fccf/go.mod h1:DccQmYY6swDlNlOCQOAX+SXTI9laSfGytskmeeNWmms= +github.com/plgd-dev/go-coap/v2 v2.4.1-0.20210517130748-95c37ac8e1fa/go.mod h1:rA7fc7ar+B/qa+Q0hRqv7yj/EMtIlmo1l7vkQGSrHPU= github.com/plgd-dev/kit v0.0.0-20200819113605-d5fcf3e94f63/go.mod h1:Yl9zisyXfPdtP9hTWlJqjJYXmgU/jtSDKttz9/CeD90= github.com/plgd-dev/kit v0.0.0-20210517115726-034a62788317 h1:A4kLG/LGlL0cpG2Xt0n8k1C8IWibWvIe53VnCsf60Qg= github.com/plgd-dev/kit v0.0.0-20210517115726-034a62788317/go.mod h1:2hMgcklG0UX+HyPAVyodx5cFsQiLN0CbRcmuS0SggDE= +github.com/plgd-dev/kit v0.0.0-20210614190235-99984a49de48 h1:QpSqIE6a1qDAuORDklEYxLh1vHbHGRIWbr0/oyLpJPw= +github.com/plgd-dev/kit v0.0.0-20210614190235-99984a49de48/go.mod h1:9q1iKipCaPTfEYI6eebZiXjuIZbclbA2tggRBzwP71Q= github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZbAQM= github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4= github.com/prometheus/client_model v0.0.0-20190812154241-14fe0d1b01d4/go.mod h1:xMI15A0UPsDsEKsMN9yxemIoYk6Tm2C1GtYGdfGttqA= @@ -151,6 +163,8 @@ go.uber.org/atomic v1.4.0/go.mod h1:gD2HeocX3+yG+ygLZcrzQJaqmWj9AIm7n08wl/qW/PE= go.uber.org/atomic v1.6.0/go.mod h1:sABNBOSYdrvTF6hTgEIbc7YasKWGhgEQZyfxyTvoXHQ= go.uber.org/atomic v1.7.0 h1:ADUqmZGgLDDfbSL9ZmPxKTybcoEYHgpYfELNoN+7hsw= go.uber.org/atomic v1.7.0/go.mod h1:fEN4uk6kAWBTFdckzkM89CLk9XfWZrxpCo0nPH17wJc= +go.uber.org/atomic v1.8.0 h1:CUhrE4N1rqSE6FM9ecihEjRkLQu8cDfgDyoOs83mEY4= +go.uber.org/atomic v1.8.0/go.mod h1:fEN4uk6kAWBTFdckzkM89CLk9XfWZrxpCo0nPH17wJc= go.uber.org/multierr v1.1.0/go.mod h1:wR5kodmAFQ0UK8QlbwjlSNy0Z68gJhDJUG5sjR94q/0= go.uber.org/multierr v1.5.0/go.mod h1:FeouvMocqHpRaaGuG9EjoKcStLC43Zu/fmqdUMPcKYU= go.uber.org/tools v0.0.0-20190618225709-2cfd321de3ee/go.mod h1:vJERXedbb3MVM5f9Ejo0C68/HhF8uaILCdgjnY+goOA= @@ -168,6 +182,8 @@ golang.org/x/crypto v0.0.0-20210322153248-0c34fe9e7dc2/go.mod h1:T9bdIzuCu7OtxOm golang.org/x/crypto v0.0.0-20210421170649-83a5a9bb288b/go.mod h1:T9bdIzuCu7OtxOm1hfPfRQxPLYneinmdGuTeoZ9dtd4= golang.org/x/crypto v0.0.0-20210513164829-c07d793c2f9a h1:kr2P4QFmQr29mSLA43kwrOcgcReGTfbE9N577tCTuBc= golang.org/x/crypto v0.0.0-20210513164829-c07d793c2f9a/go.mod h1:P+XmwS30IXTQdn5tA2iutPOUgjI07+tq3H3K9MVA1s8= +golang.org/x/crypto v0.0.0-20210616213533-5ff15b29337e h1:gsTQYXdTw2Gq7RBsWvlQ91b+aEQ6bXFUngBGuR8sPpI= +golang.org/x/crypto v0.0.0-20210616213533-5ff15b29337e/go.mod h1:GvvjBRRGRdwPK5ydBHafDWAxML/pGHZbMvKqRZ5+Abc= golang.org/x/exp v0.0.0-20190121172915-509febef88a4/go.mod h1:CJ0aWSM057203Lf6IL+f9T1iT9GByDxfZKAQTCR3kQA= golang.org/x/lint v0.0.0-20181026193005-c67002cb31c3/go.mod h1:UVdnD1Gm6xHRNCYTkRU2/jEulfH38KcIWyp/GAMgvoE= golang.org/x/lint v0.0.0-20190227174305-5b3e6a55c961/go.mod h1:wehouNa3lNwaWXcvxsM5YxQ5yQlVC4a0KAMCusXpPoU= @@ -191,9 +207,12 @@ golang.org/x/net v0.0.0-20200506145744-7e3656a0809f/go.mod h1:qpuaurCH72eLCgpAm/ golang.org/x/net v0.0.0-20201201195509-5d6afe98e0b7/go.mod h1:sp8m0HH+o8qH0wwXwYZr8TS3Oi6o0r6Gce1SSxlDquU= golang.org/x/net v0.0.0-20210119194325-5f4716e94777/go.mod h1:m0MpNAwzfU5UDzcl9v0D8zg8gWTRqZa9RBIspLL5mdg= golang.org/x/net v0.0.0-20210226172049-e18ecbb05110/go.mod h1:m0MpNAwzfU5UDzcl9v0D8zg8gWTRqZa9RBIspLL5mdg= +golang.org/x/net v0.0.0-20210331212208-0fccb6fa2b5c/go.mod h1:p54w0d4576C0XHj96bSt6lcn1PtDYWL6XObtHCRCNQM= golang.org/x/net v0.0.0-20210502030024-e5908800b52b/go.mod h1:OJAsFXCWl8Ukc7SiCT/9KSuxbyM7479/AVlXFRxuMCk= golang.org/x/net v0.0.0-20210525063256-abc453219eb5 h1:wjuX4b5yYQnEQHzd+CBcrcC6OVR2J1CN6mUy0oSxIPo= golang.org/x/net v0.0.0-20210525063256-abc453219eb5/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y= +golang.org/x/net v0.0.0-20210614182718-04defd469f4e h1:XpT3nA5TvE525Ne3hInMh6+GETgn27Zfm9dxsThnX2Q= +golang.org/x/net v0.0.0-20210614182718-04defd469f4e/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y= golang.org/x/oauth2 v0.0.0-20180821212333-d2e6202438be/go.mod h1:N/0e6XlmueqKjAGxoOufVs8QHGRruUQn6yWY3a++T0U= golang.org/x/oauth2 v0.0.0-20200107190931-bf48bf16ab8d/go.mod h1:gOpvHmFTYa4IltrdGE7lF6nIHvwfUNPOp7c8zoXwtLw= golang.org/x/sync v0.0.0-20180314180146-1d60e4601c6f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= @@ -213,9 +232,13 @@ golang.org/x/sys v0.0.0-20200223170610-d5e6a3e2c0ae/go.mod h1:h1NjWce9XRLGQEsW7w golang.org/x/sys v0.0.0-20200323222414-85ca7c5b95cd/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20200930185726-fdedc70b468f/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20201119102817-f84b799fce68/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20210330210617-4fbd30eecc44/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20210423082822-04245dca01da/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20210608053332-aa57babbf139 h1:C+AwYEtBp/VQwoLntUmQ/yx3MS9vmZaKNdw5eOpoQe8= golang.org/x/sys v0.0.0-20210608053332-aa57babbf139/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20210615035016-665e8c7367d1/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20210616094352-59db8d763f22 h1:RqytpXGR1iVNX7psjB3ff8y7sNFinVFvkx1c8SjBkio= +golang.org/x/sys v0.0.0-20210616094352-59db8d763f22/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo= golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= golang.org/x/text v0.3.3/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ= @@ -265,8 +288,10 @@ gopkg.in/h2non/gock.v1 v1.0.14/go.mod h1:sX4zAkdYX1TRGJ2JY156cFspQn4yRWn6p9EMdOD gopkg.in/macaroon.v2 v2.1.0/go.mod h1:OUb+TQP/OP0WOerC2Jp/3CwhIKyIa9kQjuc7H24e6/o= gopkg.in/square/go-jose.v2 v2.5.1/go.mod h1:M9dMgbHiYLoDGQrXy7OpJDJWiKiU//h+vD76mk0e1AI= gopkg.in/yaml.v2 v2.2.2/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI= +gopkg.in/yaml.v2 v2.2.7/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.4.0/go.mod h1:RDklbk79AGWmwhnvt/jBztapEOGDOx6ZbXqjP6csGnQ= 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= honnef.co/go/tools v0.0.0-20190102054323-c2f93a96b099/go.mod h1:rf3lG4BRIbNafJWhAfAdb/ePZxsR/4RtNHQocxwk9r4= diff --git a/mobile/client.go b/mobile/client.go index a2c5657..1178ca7 100644 --- a/mobile/client.go +++ b/mobile/client.go @@ -20,12 +20,14 @@ import ( "context" "io" "io/ioutil" + "net" "net/http" "net/url" "strings" "sync" "time" + "github.com/matrix-org/go-coap/v2/coap" "github.com/matrix-org/go-coap/v2/dtls" "github.com/matrix-org/go-coap/v2/message" "github.com/matrix-org/go-coap/v2/net/blockwise" @@ -36,6 +38,15 @@ import ( "github.com/sirupsen/logrus" ) +// FIXME: This is a gut wrenching hack; we should be exposing this more nicely +var customPacketConn net.PacketConn +var customAddrFunc func(host string) net.Addr + +func SetCustomConn(pc net.PacketConn, addr func(host string) net.Addr) { + customPacketConn = pc + customAddrFunc = addr +} + // ConnectionParams contains parameters for the entire low bandwidth stack, including DTLS, CoAP and OBSERVE. type ConnectionParams struct { // If true, skips TLS certificate checks allowing this library to be used with self-signed certificates. @@ -96,7 +107,7 @@ type ConnectionParams struct { } var activeConnectionParams = ConnectionParams{ - InsecureSkipVerify: false, + InsecureSkipVerify: true, ObserveEnabled: false, FlightIntervalSecs: 2, HeartbeatTimeoutSecs: 60, @@ -144,7 +155,7 @@ type Response struct { // case clients should use normal Matrix over HTTP to send this request. // // This function will block until the response is returned, or the request times out. -func SendRequest(method, hsURL, token, body string) *Response { +func SendRequest(method, hsURL, token, body string, federation bool) *Response { logrus.Infof("DTLS SendRequest -> %s %s", method, hsURL) // convert JSON to CBOR @@ -185,10 +196,15 @@ func SendRequest(method, hsURL, token, body string) *Response { } // Check if we've sent an access token and set it if we need to - sentAccessToken := conn.Context().Value(ctxValSentAccessToken) - if sentAccessToken == nil || sentAccessToken != token { - req.Header.Set("Authorization", "Bearer "+token) - conn.SetContextValue(ctxValSentAccessToken, token) + switch federation { + case false: // We only need to send one if it changed since last time + sentAccessToken := conn.Context().Value(ctxValSentAccessToken) + if sentAccessToken == nil || sentAccessToken != token { + req.Header.Set("Authorization", "Bearer "+token) + conn.SetContextValue(ctxValSentAccessToken, token) + } + case true: // We always need to send one + req.Header.Set("Authorization", "X-Matrix "+token) } // Check for /sync OBSERVE requests @@ -236,7 +252,11 @@ func SendRequest(method, hsURL, token, body string) *Response { logrus.WithError(err).Errorf("Failed to get DTLS client for host %s", u.Host) return nil } - req.Header.Set("Authorization", "Bearer "+token) + if federation { + req.Header.Set("Authorization", "X-Matrix "+token) + } else { + req.Header.Set("Authorization", "Bearer "+token) + } conn.SetContextValue(ctxValSentAccessToken, token) if reqBody != nil { _, _ = reqBody.Seek(0, 0) @@ -287,7 +307,7 @@ func observe(conn *client.ClientConn, path, token string, queries url.Values) ch logrus.Infof("Observing path: %s", path) opts := []message.Option{ { - ID: lb.OptionIDAccessToken, + ID: lb.OptionIDAuthorizationBearerToken, Value: []byte(token), }, } @@ -376,35 +396,66 @@ func (c *dtlsClients) getClientForHost(host string) (*client.ClientConn, error) if ok { return co, nil } - co, err := dtls.Dial( - host, c.dtlsConfig, dtls.WithHeartBeat(time.Duration(activeConnectionParams.HeartbeatTimeoutSecs)*time.Second), - dtls.WithKeepAlive(uint32(activeConnectionParams.KeepAliveMaxRetries), time.Duration(activeConnectionParams.KeepAliveTimeoutSecs)*time.Second, func(cc interface { - Close() error - Context() context.Context - }) { - return - }), - dtls.WithTransmission( - // FIXME? https://github.com/plgd-dev/go-coap/issues/226 - time.Duration(activeConnectionParams.TransmissionNStart)*time.Second, - time.Duration(activeConnectionParams.TransmissionACKTimeoutSecs)*time.Second, - activeConnectionParams.TransmissionMaxRetransmits, - ), - // long blockwise timeout to handle large sync responses which take a huge number of blocks - dtls.WithBlockwise(true, blockwise.SZX1024, 2*time.Minute), - dtls.WithLogger(&logger{}), - ) - if err == nil { - c.conns[host] = co - // delete the entry when the connection is closed so we'll make a new one - co.AddOnClose(func() { - c.mu.Lock() - defer c.mu.Unlock() - delete(c.conns, host) - logrus.Infof("Removed dead connection for host %s", host) - }) + var err error + if customPacketConn != nil && customAddrFunc != nil { + newCfg := coap.NewConfig( + coap.WithErrors(func(err error) { + logrus.Warnf("coap error: %s", err) + }), + coap.WithHeartBeat(time.Duration(activeConnectionParams.HeartbeatTimeoutSecs)*time.Second), + coap.WithKeepAlive(uint32(activeConnectionParams.KeepAliveMaxRetries), time.Duration(activeConnectionParams.KeepAliveTimeoutSecs)*time.Second, func(cc interface { + Close() error + Context() context.Context + }) { + return + }), + coap.WithTransmission( + // FIXME? https://github.com/plgd-dev/go-coap/issues/226 + time.Duration(activeConnectionParams.TransmissionNStart)*time.Second, + time.Duration(activeConnectionParams.TransmissionACKTimeoutSecs)*time.Second, + activeConnectionParams.TransmissionMaxRetransmits, + ), + coap.WithBlockwise(true, blockwise.SZX1024, 2*time.Minute), + coap.WithLogger(&logger{}), + ) + co = newCfg.NewSessionWithPacketConn(customPacketConn, customAddrFunc(host)) + go func() { + if runErr := co.Run(); runErr != nil { + logrus.Warnf("NewWithPacketConn Run for %s returned error: %s", host, runErr) + } + }() + } else { + co, err = dtls.Dial( + host, c.dtlsConfig, dtls.WithHeartBeat(time.Duration(activeConnectionParams.HeartbeatTimeoutSecs)*time.Second), + dtls.WithKeepAlive(uint32(activeConnectionParams.KeepAliveMaxRetries), time.Duration(activeConnectionParams.KeepAliveTimeoutSecs)*time.Second, func(cc interface { + Close() error + Context() context.Context + }) { + return + }), + dtls.WithTransmission( + // FIXME? https://github.com/plgd-dev/go-coap/issues/226 + time.Duration(activeConnectionParams.TransmissionNStart)*time.Second, + time.Duration(activeConnectionParams.TransmissionACKTimeoutSecs)*time.Second, + activeConnectionParams.TransmissionMaxRetransmits, + ), + // long blockwise timeout to handle large sync responses which take a huge number of blocks + dtls.WithBlockwise(true, blockwise.SZX1024, 2*time.Minute), + dtls.WithLogger(&logger{}), + ) + if err != nil { + return nil, err + } } - return co, err + c.conns[host] = co + // delete the entry when the connection is closed so we'll make a new one + co.AddOnClose(func() { + c.mu.Lock() + defer c.mu.Unlock() + delete(c.conns, host) + logrus.Infof("Removed dead connection for host %s", host) + }) + return co, nil } type logger struct{} diff --git a/mobile/go.mod b/mobile/go.mod deleted file mode 100644 index 60e2d42..0000000 --- a/mobile/go.mod +++ /dev/null @@ -1,16 +0,0 @@ -module github.com/matrix-org/lb/mobile - -go 1.14 - -replace github.com/matrix-org/lb => ../ - -require ( - github.com/matrix-org/go-coap/v2 v2.0.0-20210608155919-691db5a1ade4 - github.com/matrix-org/lb v0.0.0-00010101000000-000000000000 - github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd // indirect - github.com/modern-go/reflect2 v1.0.1 // indirect - github.com/pion/dtls/v2 v2.0.10-0.20210502094952-3dc563b9aede - github.com/sirupsen/logrus v1.7.0 - github.com/tidwall/gjson v1.6.7 // indirect - golang.org/x/sys v0.0.0-20210608053332-aa57babbf139 // indirect -) diff --git a/mobile/go.sum b/mobile/go.sum deleted file mode 100644 index 81be9bf..0000000 --- a/mobile/go.sum +++ /dev/null @@ -1,328 +0,0 @@ -cloud.google.com/go v0.26.0/go.mod h1:aQUYkXzVsufM+DwF1aE+0xfcU+56JwCaLick0ClmMTw= -cloud.google.com/go v0.34.0/go.mod h1:aQUYkXzVsufM+DwF1aE+0xfcU+56JwCaLick0ClmMTw= -github.com/BurntSushi/toml v0.3.1/go.mod h1:xHWCNGjB5oqiDr8zfno3MHue2Ht5sIBksp03qcyfWMU= -github.com/BurntSushi/xgb v0.0.0-20160522181843-27f122750802/go.mod h1:IVnqGOEym/WlBOVXweHU+Q+/VP0lqqI8lqeDx9IjBqo= -github.com/cenkalti/backoff v2.2.1+incompatible/go.mod h1:90ReRw6GdpyfrHakVjL/QHaoyV4aDUVVkXQJJJ3NXXM= -github.com/census-instrumentation/opencensus-proto v0.2.1/go.mod h1:f6KPmirojxKA12rnyqOA5BBL4O983OfeGPqjHWSTneU= -github.com/client9/misspell v0.3.4/go.mod h1:qj6jICC3Q7zFZvVWo7KLAzC3yx5G7kyvSDkc90ppPyw= -github.com/cncf/udpa/go v0.0.0-20191209042840-269d4d468f6f/go.mod h1:M8M6+tZqaGXZJjfX53e64911xZQV5JYwmTeXPW+k8Sc= -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= -github.com/dgrijalva/jwt-go v3.2.0+incompatible/go.mod h1:E3ru+11k8xSBh+hMPgOLZmtrrCbhqsmaPHjLKYnJCaQ= -github.com/dsnet/golib/memfile v0.0.0-20190531212259-571cdbcff553/go.mod h1:tXGNW9q3RwvWt1VV2qrRKlSSz0npnh12yftCSCy2T64= -github.com/dsnet/golib/memfile v0.0.0-20200723050859-c110804dfa93 h1:I48YLRgQEeWsjF7LmNcl62vTHSUfUfEVe3I1oHXiS5o= -github.com/dsnet/golib/memfile v0.0.0-20200723050859-c110804dfa93/go.mod h1:tXGNW9q3RwvWt1VV2qrRKlSSz0npnh12yftCSCy2T64= -github.com/dsnet/golib/memfile v1.0.0 h1:J9pUspY2bDCbF9o+YGwcf3uG6MdyITfh/Fk3/CaEiFs= -github.com/dsnet/golib/memfile v1.0.0/go.mod h1:tXGNW9q3RwvWt1VV2qrRKlSSz0npnh12yftCSCy2T64= -github.com/envoyproxy/go-control-plane v0.9.0/go.mod h1:YTl/9mNaCwkRvm6d1a2C3ymFceY/DCBVvsKhRF0iEA4= -github.com/envoyproxy/go-control-plane v0.9.1-0.20191026205805-5f8ba28d4473/go.mod h1:YTl/9mNaCwkRvm6d1a2C3ymFceY/DCBVvsKhRF0iEA4= -github.com/envoyproxy/go-control-plane v0.9.4/go.mod h1:6rpuAdCZL397s3pYoYcLgu1mIlRU8Am5FuJP05cCM98= -github.com/envoyproxy/protoc-gen-validate v0.1.0/go.mod h1:iSmxcyjqTsJpI2R4NaDN7+kN2VEUnK/pcBlmesArF7c= -github.com/flynn/noise v1.0.0/go.mod h1:xbMo+0i6+IGbYdJhF31t2eR1BIU0CYc12+BNAKwUTag= -github.com/frankban/quicktest v1.0.0/go.mod h1:R98jIehRai+d1/3Hv2//jOVCTJhW1VBavT6B6CuGq2k= -github.com/frankban/quicktest v1.7.2/go.mod h1:jaStnuzAqU1AJdCO0l53JDCJrVDKcS03DbaAcR7Ks/o= -github.com/fsnotify/fsnotify v1.4.9/go.mod h1:znqG4EE+3YCdAaPaxE2ZRY/06pZUdp0tY4IgpuI1SZQ= -github.com/fxamacker/cbor/v2 v2.2.0 h1:6eXqdDDe588rSYAi1HfZKbx6YYQO4mxQ9eC6xYpU/JQ= -github.com/fxamacker/cbor/v2 v2.2.0/go.mod h1:TA1xS00nchWmaBnEIxPSE5oHLuJBAVvqrtAnWBwBCVo= -github.com/go-acme/lego v2.7.2+incompatible/go.mod h1:yzMNe9CasVUhkquNvti5nAtPmG94USbYxYrZfTkIn0M= -github.com/go-kit/kit v0.9.0/go.mod h1:xBxKIO96dXMWWy0MnWVtmwkA9/13aqxPnvrjFYMA2as= -github.com/go-logfmt/logfmt v0.4.0/go.mod h1:3RMwSq7FuexP4Kalkev3ejPJsZTpXXBr9+V4qmtdjCk= -github.com/go-ocf/go-coap/v2 v2.0.4-0.20200728125043-f38b86f047a7/go.mod h1:X9wVKcaOSx7wBxKcvrWgMQq1R2DNeA7NBLW2osIb8TM= -github.com/go-ocf/kit v0.0.0-20200728130040-4aebdb6982bc/go.mod h1:TIsoMT/iB7t9P6ahkcOnsmvS83SIJsv9qXRfz/yLf6M= -github.com/go-stack/stack v1.8.0/go.mod h1:v0f6uXyyMGvRgIKkXu+yp6POWl0qKG85gN/melR3HDY= -github.com/gofrs/uuid v3.3.0+incompatible/go.mod h1:b2aQJv3Z4Fp6yNu3cdSllBxTCLRxnplIgP/c0N/04lM= -github.com/gogo/protobuf v1.2.1/go.mod h1:hp+jE20tsWTFYpLwKvXlhS1hjn+gTNwPg2I6zVXpSg4= -github.com/gogo/protobuf v1.3.1/go.mod h1:SlYgWuQ5SjCEi6WLHjHCa1yvBfUnHcTbrrZtXPKa29o= -github.com/golang/glog v0.0.0-20160126235308-23def4e6c14b/go.mod h1:SBH7ygxi8pfUlaOkMMuAQtPIUF8ecWP5IEl/CR7VP2Q= -github.com/golang/mock v1.1.1/go.mod h1:oTYuIxOrZwtPieC+H1uAHpcLFnEyAGVDL/k47Jfbm0A= -github.com/golang/protobuf v1.2.0/go.mod h1:6lQm79b+lXiMfvg/cZm0SGofjICqVBUtrP5yJMmIC1U= -github.com/golang/protobuf v1.3.2/go.mod h1:6lQm79b+lXiMfvg/cZm0SGofjICqVBUtrP5yJMmIC1U= -github.com/golang/protobuf v1.3.3/go.mod h1:vzj43D7+SQXF/4pzW/hwtAqwc6iTitCiVSaWz5lYuqw= -github.com/golang/protobuf v1.4.0-rc.1/go.mod h1:ceaxUfeHdC40wWswd/P6IGgMaK3YpKi5j83Wpe3EHw8= -github.com/golang/protobuf v1.4.0-rc.1.0.20200221234624-67d41d38c208/go.mod h1:xKAWHe0F5eneWXFV3EuXVDTCmh+JuBKY0li0aMyXATA= -github.com/golang/protobuf v1.4.0-rc.2/go.mod h1:LlEzMj4AhA7rCAGe4KMBDvJI+AwstrUpVNzEA03Pprs= -github.com/golang/protobuf v1.4.0-rc.4.0.20200313231945-b860323f09d0/go.mod h1:WU3c8KckQ9AFe+yFwt9sWVRKCVIyN9cPHBJSNnbL67w= -github.com/golang/protobuf v1.4.0/go.mod h1:jodUvKwWbYaEsadDk5Fwe5c77LiNKVO9IDvqG2KuDX0= -github.com/golang/protobuf v1.4.1/go.mod h1:U8fpvMrcmy5pZrNK1lt4xCsGvpyWQ/VVv6QDs8UjoX8= -github.com/google/go-cmp v0.2.0/go.mod h1:oXzfMopK8JAjlY9xF4vHSVASa0yLyX7SntLO5aqRK0M= -github.com/google/go-cmp v0.3.0/go.mod h1:8QqcDgzrUqlUb/G2PQTWiueGozuR1884gddMywk6iLU= -github.com/google/go-cmp v0.3.1/go.mod h1:8QqcDgzrUqlUb/G2PQTWiueGozuR1884gddMywk6iLU= -github.com/google/go-cmp v0.4.0/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= -github.com/google/gofuzz v1.0.0/go.mod h1:dBl0BpW6vV/+mYPU4Po3pmUjxk6FQPldtuIdl/M65Eg= -github.com/google/renameio v0.1.0/go.mod h1:KWCgfxg9yswjAJkECMjeO8J8rahYeXnNhOm40UhjYkI= -github.com/gorilla/mux v1.7.4/go.mod h1:DVbg23sWSpFRCP0SfiEN6jmj59UnW/n46BH5rLB71So= -github.com/grpc-ecosystem/go-grpc-middleware v1.2.0/go.mod h1:mJzapYve32yjrKlk9GbyCZHuPgZsrbyIbyKhSzOpg6s= -github.com/h2non/parth v0.0.0-20190131123155-b4df798d6542 h1:2VTzZjLZBgl62/EtslCrtky5vbi9dd7HrQPQIx6wqiw= -github.com/h2non/parth v0.0.0-20190131123155-b4df798d6542/go.mod h1:Ow0tF8D4Kplbc8s8sSb3V2oUCygFHVp8gC3Dn6U4MNI= -github.com/jessevdk/go-flags v1.4.0/go.mod h1:4FA24M0QyGHXBuZZK/XkWh8h0e1EYbRYJSGM75WSRxI= -github.com/json-iterator/go v1.1.11 h1:uVUAXhF2To8cbw/3xN3pxj6kk7TYKs98NIrTqPlMWAQ= -github.com/json-iterator/go v1.1.11/go.mod h1:KdQUCv79m/52Kvf8AW2vK1V8akMuk1QjK/uOdHXbAo4= -github.com/kelseyhightower/envconfig v1.4.0/go.mod h1:cccZRl6mQpaq41TPp5QxidR+Sa3axMbJDNb//FQX6Gg= -github.com/kisielk/errcheck v1.1.0/go.mod h1:EZBBE59ingxPouuu3KfxchcWSUPOHkagtvWXihfKN4Q= -github.com/kisielk/errcheck v1.2.0/go.mod h1:/BMXB+zMLi60iA8Vv6Ksmxu/1UDYcXs4uQLJ+jE2L00= -github.com/kisielk/gotool v1.0.0/go.mod h1:XhKaO+MFFWcvkIS/tQcRk01m1F5IRFswLeQ+oQHNcck= -github.com/klauspost/compress v1.10.4/go.mod h1:aoV0uJVorq1K+umq18yTdKaF57EivdYsUV+/s2qKfXs= -github.com/konsorten/go-windows-terminal-sequences v1.0.1/go.mod h1:T0+1ngSBFLxvqU3pZ+m/2kptfBszLMUkC4ZK/EgS/cQ= -github.com/konsorten/go-windows-terminal-sequences v1.0.2/go.mod h1:T0+1ngSBFLxvqU3pZ+m/2kptfBszLMUkC4ZK/EgS/cQ= -github.com/kr/logfmt v0.0.0-20140226030751-b84e30acd515/go.mod h1:+0opPa2QZZtGFBFZlji/RkVcI2GknAs/DXo4wKdlNEc= -github.com/kr/pretty v0.1.0 h1:L/CwN0zerZDmRFUapSPitk6f+Q3+0za1rQkzVuMiMFI= -github.com/kr/pretty v0.1.0/go.mod h1:dAy3ld7l9f0ibDNOQOHHMYYIIbhfbHSm3C4ZsoJORNo= -github.com/kr/pretty v0.2.0 h1:s5hAObm+yFO5uHYt5dYjxi2rXrsnmRpJx4OYvIWUaQs= -github.com/kr/pretty v0.2.0/go.mod h1:ipq/a2n7PKx3OHsz4KJII5eveXtPO4qwEXGdVfWzfnI= -github.com/kr/pretty v0.2.1 h1:Fmg33tUaq4/8ym9TJN1x7sLJnHVwhP33CNkpYV/7rwI= -github.com/kr/pretty v0.2.1/go.mod h1:ipq/a2n7PKx3OHsz4KJII5eveXtPO4qwEXGdVfWzfnI= -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/lestrrat-go/iter v0.0.0-20200422075355-fc1769541911/go.mod h1:zIdgO1mRKhn8l9vrZJZz9TUMMFbQbLeTsbqPDrJ/OJc= -github.com/lestrrat-go/jwx v1.0.2/go.mod h1:TPF17WiSFegZo+c20fdpw49QD+/7n4/IsGvEmCSWwT0= -github.com/lestrrat-go/pdebug v0.0.0-20200204225717-4d6bd78da58d/go.mod h1:B06CSso/AWxiPejj+fheUINGeBKeeEZNt8w+EoU7+L8= -github.com/matrix-org/go-coap/v2 v2.0.0-20210607153635-05743a0702b6 h1:/JWtXldUfDUgI0bNOJ8lCXC+77afwxN6IYG04liVDUI= -github.com/matrix-org/go-coap/v2 v2.0.0-20210607153635-05743a0702b6/go.mod h1:GC7TQJU2vxrJhItiu5pjhNxmMqPm97wP1rk+xqK60eM= -github.com/matrix-org/go-coap/v2 v2.0.0-20210607160830-dd828aaa40cd h1:oJdU/jKZMm7ihGJ7v8DBiun17j9puitjN1PbP5Jxe9k= -github.com/matrix-org/go-coap/v2 v2.0.0-20210607160830-dd828aaa40cd/go.mod h1:GC7TQJU2vxrJhItiu5pjhNxmMqPm97wP1rk+xqK60eM= -github.com/matrix-org/go-coap/v2 v2.0.0-20210608155919-691db5a1ade4 h1:SwJtJ7XktZNBL7s0rReaxuCoI9PWfW+JG/Zal35ZYa4= -github.com/matrix-org/go-coap/v2 v2.0.0-20210608155919-691db5a1ade4/go.mod h1:GC7TQJU2vxrJhItiu5pjhNxmMqPm97wP1rk+xqK60eM= -github.com/matrix-org/gomatrix v0.0.0-20190528120928-7df988a63f26 h1:Hr3zjRsq2bhrnp3Ky1qgx/fzCtCALOoGYylh2tpS9K4= -github.com/matrix-org/gomatrix v0.0.0-20190528120928-7df988a63f26/go.mod h1:3fxX6gUjWyI/2Bt7J1OLhpCzOfO/bB3AiX0cJtEKud0= -github.com/matrix-org/gomatrixserverlib v0.0.0-20210302161955-6142fe3f8c2c h1:vW3jBp1PnZ4uUqyS+JatJRYIl73ZLHkUkRzf1JdGxOI= -github.com/matrix-org/gomatrixserverlib v0.0.0-20210302161955-6142fe3f8c2c/go.mod h1:JsAzE1Ll3+gDWS9JSUHPJiiyAksvOOnGWF2nXdg4ZzU= -github.com/matrix-org/util v0.0.0-20190711121626-527ce5ddefc7/go.mod h1:vVQlW/emklohkZnOPwD3LrZUBqdfsbiyO3p1lNV8F6U= -github.com/matrix-org/util v0.0.0-20200807132607-55161520e1d4 h1:eCEHXWDv9Rm335MSuB49mFUK44bwZPFSDde3ORE3syk= -github.com/matrix-org/util v0.0.0-20200807132607-55161520e1d4/go.mod h1:vVQlW/emklohkZnOPwD3LrZUBqdfsbiyO3p1lNV8F6U= -github.com/miekg/dns v1.1.12/go.mod h1:W1PPwlIAgtquWBMBEV9nkV9Cazfe8ScdGz/Lj7v3Nrg= -github.com/miekg/dns v1.1.29 h1:xHBEhR+t5RzcFJjBLJlax2daXOrTYtr9z4WdKEfWFzg= -github.com/miekg/dns v1.1.29/go.mod h1:KNUDUusw/aVsxyTYZM1oqvCicbwhgbNgztCETuNZ7xM= -github.com/modern-go/concurrent v0.0.0-20180228061459-e0a39a4cb421/go.mod h1:6dJC0mAP4ikYIbvyc7fijjWJddQyLn8Ig3JB5CqoB9Q= -github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd h1:TRLaZ9cD/w8PVh93nsPXa1VrQ6jlwL5oN8l14QlcNfg= -github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd/go.mod h1:6dJC0mAP4ikYIbvyc7fijjWJddQyLn8Ig3JB5CqoB9Q= -github.com/modern-go/reflect2 v0.0.0-20180701023420-4b7aa43c6742/go.mod h1:bx2lNnkwVCuqBIxFjflWJWanXIb3RllmbCylyMrvgv0= -github.com/modern-go/reflect2 v1.0.1 h1:9f412s+6RmYXLWZSEzVVgPGK7C2PphHj5RJrvfx9AWI= -github.com/modern-go/reflect2 v1.0.1/go.mod h1:bx2lNnkwVCuqBIxFjflWJWanXIb3RllmbCylyMrvgv0= -github.com/nbio/st v0.0.0-20140626010706-e9e8d9816f32 h1:W6apQkHrMkS0Muv8G/TipAy/FJl/rCYT0+EuS8+Z0z4= -github.com/nbio/st v0.0.0-20140626010706-e9e8d9816f32/go.mod h1:9wM+0iRr9ahx58uYLpLIr5fm8diHn0JbqRycJi6w0Ms= -github.com/opentracing/opentracing-go v1.1.0/go.mod h1:UkNAQd3GIcIGf0SeVgPpRdFStlNbqXla1AfSYxPUl2o= -github.com/patrickmn/go-cache v2.1.0+incompatible h1:HRMgzkcYKYpi3C8ajMPV8OFXaaRUnok+kx1WdO15EQc= -github.com/patrickmn/go-cache v2.1.0+incompatible/go.mod h1:3Qf8kWWT7OJRJbdiICTKqZju1ZixQ/KpMGzzAfe6+WQ= -github.com/pion/dtls/v2 v2.0.1-0.20200503085337-8e86b3a7d585 h1:0v1k/bHrth28TctdEWnrCgLehYn3nOvFAwOwtwmyC34= -github.com/pion/dtls/v2 v2.0.1-0.20200503085337-8e86b3a7d585/go.mod h1:/GahSOC8ZY/+17zkaGJIG4OUkSGAcZu/N/g3roBOCkM= -github.com/pion/dtls/v2 v2.0.9/go.mod h1:O0Wr7si/Zj5/EBFlDzDd6UtVxx25CE1r7XM7BQKYQho= -github.com/pion/dtls/v2 v2.0.10-0.20210502094952-3dc563b9aede h1:f/uKAVo6gUJMw00gOWEolJy/0h8LfoaxouHD+Rq4EQo= -github.com/pion/dtls/v2 v2.0.10-0.20210502094952-3dc563b9aede/go.mod h1:86wv5dgx2J/z871nUR+5fTTY9tISLUlo+C5Gm86r1Hs= -github.com/pion/logging v0.2.2 h1:M9+AIj/+pxNsDfAT64+MAVgJO0rsyLnoJKCqf//DoeY= -github.com/pion/logging v0.2.2/go.mod h1:k0/tDVsRCX2Mb2ZEmTqNa7CWsQPc+YYCB7Q+5pahoms= -github.com/pion/transport v0.10.0 h1:9M12BSneJm6ggGhJyWpDveFOstJsTiQjkLf4M44rm80= -github.com/pion/transport v0.10.0/go.mod h1:BnHnUipd0rZQyTVB2SBGojFHT9CBt5C5TcsJSQGkvSE= -github.com/pion/transport v0.12.2 h1:WYEjhloRHt1R86LhUKjC5y+P52Y11/QqEUalvtzVoys= -github.com/pion/transport v0.12.2/go.mod h1:N3+vZQD9HlDP5GWkZ85LohxNsDcNgofQmyL6ojX5d8Q= -github.com/pion/transport v0.12.3 h1:vdBfvfU/0Wq8kd2yhUMSDB/x+O4Z9MYVl2fJ5BT4JZw= -github.com/pion/transport v0.12.3/go.mod h1:OViWW9SP2peE/HbwBvARicmAVnesphkNkCVZIWJ6q9A= -github.com/pion/udp v0.1.1 h1:8UAPvyqmsxK8oOjloDk4wUt63TzFe9WEJkg5lChlj7o= -github.com/pion/udp v0.1.1/go.mod h1:6AFo+CMdKQm7UiA0eUPA8/eVCTx8jBIITLZHc9DWX5M= -github.com/pkg/errors v0.8.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0= -github.com/pkg/errors v0.9.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0= -github.com/plgd-dev/go-coap/v2 v2.0.4-0.20200819112225-8eb712b901bc/go.mod h1:+tCi9Q78H/orWRtpVWyBgrr4vKFo2zYtbbxUllerBp4= -github.com/plgd-dev/go-coap/v2 v2.1.4-0.20201201213140-b8c428d8fccf/go.mod h1:DccQmYY6swDlNlOCQOAX+SXTI9laSfGytskmeeNWmms= -github.com/plgd-dev/kit v0.0.0-20200819113605-d5fcf3e94f63 h1:cI6kESUBU1KUHtufZepEkaTsSkLN2kE6xz+Ec5V17q0= -github.com/plgd-dev/kit v0.0.0-20200819113605-d5fcf3e94f63/go.mod h1:Yl9zisyXfPdtP9hTWlJqjJYXmgU/jtSDKttz9/CeD90= -github.com/plgd-dev/kit v0.0.0-20210517115726-034a62788317 h1:A4kLG/LGlL0cpG2Xt0n8k1C8IWibWvIe53VnCsf60Qg= -github.com/plgd-dev/kit v0.0.0-20210517115726-034a62788317/go.mod h1:2hMgcklG0UX+HyPAVyodx5cFsQiLN0CbRcmuS0SggDE= -github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZbAQM= -github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4= -github.com/prometheus/client_model v0.0.0-20190812154241-14fe0d1b01d4/go.mod h1:xMI15A0UPsDsEKsMN9yxemIoYk6Tm2C1GtYGdfGttqA= -github.com/rogpeppe/go-internal v1.3.0/go.mod h1:M8bDsm7K2OlrFYOpmOWEs/qY81heoFRclV5y23lUDJ4= -github.com/sirupsen/logrus v1.4.2/go.mod h1:tLMulIdttU9McNUspp0xgXVQah82FyeX6MwdIuYE2rE= -github.com/sirupsen/logrus v1.7.0 h1:ShrD1U9pZB12TX0cVy0DtePoCH97K8EtX+mg7ZARUtM= -github.com/sirupsen/logrus v1.7.0/go.mod h1:yWOB1SBYBC5VeMP7gHvWumXLIWorT60ONWic61uBYv0= -github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME= -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/go.mod h1:M5WIy9Dh21IEIfnGCwXGc5bZfKNJtfHm1UVUgZn+9EI= -github.com/stretchr/testify v1.4.0/go.mod h1:j7eGeouHqKxXV5pUuKE4zz7dFj8WfuZ+81PSLYec5m4= -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/stretchr/testify v1.7.0 h1:nwc3DEeHmmLAfoZucVR881uASk0Mfjw8xYJ99tb5CcY= -github.com/stretchr/testify v1.7.0/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg= -github.com/tidwall/gjson v1.6.0/go.mod h1:P256ACg0Mn+j1RXIDXoss50DeIABTYK1PULOJHhxOls= -github.com/tidwall/gjson v1.6.7 h1:Mb1M9HZCRWEcXQ8ieJo7auYyyiSux6w9XN3AdTpxJrE= -github.com/tidwall/gjson v1.6.7/go.mod h1:zeFuBCIqD4sN/gmqBzZ4j7Jd6UcA2Fc56x7QFsv+8fI= -github.com/tidwall/match v1.0.1/go.mod h1:LujAq0jyVjBy028G1WhWfIzbpQfMO8bBZ6Tyb0+pL9E= -github.com/tidwall/match v1.0.3 h1:FQUVvBImDutD8wJLN6c5eMzWtjgONK9MwIBCOrUJKeE= -github.com/tidwall/match v1.0.3/go.mod h1:eRSPERbgtNPcGhD8UCthc6PmLEQXEWd3PRB5JTxsfmM= -github.com/tidwall/pretty v1.0.0/go.mod h1:XNkn88O1ChpSDQmQeStsy+sBenx6DDtFZJxhVysOjyk= -github.com/tidwall/pretty v1.0.1/go.mod h1:XNkn88O1ChpSDQmQeStsy+sBenx6DDtFZJxhVysOjyk= -github.com/tidwall/pretty v1.0.2 h1:Z7S3cePv9Jwm1KwS0513MRaoUe3S01WPbLNV40pwWZU= -github.com/tidwall/pretty v1.0.2/go.mod h1:XNkn88O1ChpSDQmQeStsy+sBenx6DDtFZJxhVysOjyk= -github.com/tidwall/sjson v1.0.3 h1:DeF+0LZqvIt4fKYw41aPB29ZGlvwVkHKktoXJ1YW9Y8= -github.com/tidwall/sjson v1.0.3/go.mod h1:bURseu1nuBkFpIES5cz6zBtjmYeOQmEESshn7VpF15Y= -github.com/ugorji/go v1.1.7/go.mod h1:kZn38zHttfInRq0xu/PH0az30d+z6vm202qpg1oXVMw= -github.com/ugorji/go/codec v1.1.7/go.mod h1:Ax+UKWsSmolVDwsd+7N3ZtXu+yMGCf907BLYF3GoBXY= -github.com/valyala/bytebufferpool v1.0.0/go.mod h1:6bBcMArwyJ5K/AmCkWv1jt77kVWyCJ6HpOuEn7z0Csc= -github.com/valyala/fasthttp v1.12.0/go.mod h1:229t1eWu9UXTPmoUkbpN/fctKPBY4IJoFXQnxHGXy6E= -github.com/valyala/tcplisten v0.0.0-20161114210144-ceec8f93295a/go.mod h1:v3UYOV9WzVtRmSR+PDvWpU/qWl4Wa5LApYYX4ZtKbio= -github.com/x448/float16 v0.8.4 h1:qLwI1I70+NjRFUR3zs1JPUCgaCXSh3SW62uAKT1mSBM= -github.com/x448/float16 v0.8.4/go.mod h1:14CWIYCyZA/cWjXOioeEpHeN/83MdbZDRQHoFcYsOfg= -github.com/yuin/goldmark v1.1.27/go.mod h1:3hX8gzYuyVAZsxl0MRgGTJEmQBFcNTphYh9decYSb74= -github.com/yuin/goldmark v1.3.5/go.mod h1:mwnBkeHKe2W/ZEtQ+71ViKU8L12m81fl3OWwC1Zlc8k= -go.uber.org/atomic v1.4.0/go.mod h1:gD2HeocX3+yG+ygLZcrzQJaqmWj9AIm7n08wl/qW/PE= -go.uber.org/atomic v1.6.0 h1:Ezj3JGmsOnG1MoRWQkPBsKLe9DwWD9QeXzTRzzldNVk= -go.uber.org/atomic v1.6.0/go.mod h1:sABNBOSYdrvTF6hTgEIbc7YasKWGhgEQZyfxyTvoXHQ= -go.uber.org/atomic v1.7.0 h1:ADUqmZGgLDDfbSL9ZmPxKTybcoEYHgpYfELNoN+7hsw= -go.uber.org/atomic v1.7.0/go.mod h1:fEN4uk6kAWBTFdckzkM89CLk9XfWZrxpCo0nPH17wJc= -go.uber.org/multierr v1.1.0/go.mod h1:wR5kodmAFQ0UK8QlbwjlSNy0Z68gJhDJUG5sjR94q/0= -go.uber.org/multierr v1.5.0/go.mod h1:FeouvMocqHpRaaGuG9EjoKcStLC43Zu/fmqdUMPcKYU= -go.uber.org/tools v0.0.0-20190618225709-2cfd321de3ee/go.mod h1:vJERXedbb3MVM5f9Ejo0C68/HhF8uaILCdgjnY+goOA= -go.uber.org/zap v1.10.0/go.mod h1:vwi/ZaCAaUcBkycHslxD9B2zi4UTXhF60s6SWpuDF0Q= -go.uber.org/zap v1.15.0/go.mod h1:Mb2vm2krFEG5DV0W9qcHBYFtp/Wku1cvYaqPsS/WYfc= -golang.org/x/crypto v0.0.0-20180723164146-c126467f60eb/go.mod h1:6SG95UA2DQfeDnfUPMdvaQW0Q7yPrPDi9nlGo2tz2b4= -golang.org/x/crypto v0.0.0-20190308221718-c2843e01d9a2/go.mod h1:djNgcEr1/C05ACkg1iLfiJU5Ep61QUkGW8qpdssI0+w= -golang.org/x/crypto v0.0.0-20190510104115-cbcb75029529/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI= -golang.org/x/crypto v0.0.0-20191011191535-87dc89f01550/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI= -golang.org/x/crypto v0.0.0-20200221231518-2aa609cf4a9d/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto= -golang.org/x/crypto v0.0.0-20200323165209-0ec3e9974c59/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto= -golang.org/x/crypto v0.0.0-20200510223506-06a226fb4e37 h1:cg5LA/zNPRzIXIWSCxQW10Rvpy94aQh3LT/ShoCpkHw= -golang.org/x/crypto v0.0.0-20200510223506-06a226fb4e37/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto= -golang.org/x/crypto v0.0.0-20200622213623-75b288015ac9/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto= -golang.org/x/crypto v0.0.0-20210322153248-0c34fe9e7dc2 h1:It14KIkyBFYkHkwZ7k45minvA9aorojkyjGk9KJ5B/w= -golang.org/x/crypto v0.0.0-20210322153248-0c34fe9e7dc2/go.mod h1:T9bdIzuCu7OtxOm1hfPfRQxPLYneinmdGuTeoZ9dtd4= -golang.org/x/crypto v0.0.0-20210421170649-83a5a9bb288b/go.mod h1:T9bdIzuCu7OtxOm1hfPfRQxPLYneinmdGuTeoZ9dtd4= -golang.org/x/crypto v0.0.0-20210513164829-c07d793c2f9a h1:kr2P4QFmQr29mSLA43kwrOcgcReGTfbE9N577tCTuBc= -golang.org/x/crypto v0.0.0-20210513164829-c07d793c2f9a/go.mod h1:P+XmwS30IXTQdn5tA2iutPOUgjI07+tq3H3K9MVA1s8= -golang.org/x/exp v0.0.0-20190121172915-509febef88a4/go.mod h1:CJ0aWSM057203Lf6IL+f9T1iT9GByDxfZKAQTCR3kQA= -golang.org/x/exp v0.0.0-20190731235908-ec7cb31e5a56/go.mod h1:JhuoJpWY28nO4Vef9tZUw9qufEGTyX1+7lmHxV5q5G4= -golang.org/x/image v0.0.0-20190227222117-0694c2d4d067/go.mod h1:kZ7UVZpmo3dzQBMxlp+ypCbDeSB+sBbTgSJuh5dn5js= -golang.org/x/image v0.0.0-20190802002840-cff245a6509b/go.mod h1:FeLwcggjj3mMvU+oOTbSwawSJRM1uh48EjtB4UJZlP0= -golang.org/x/lint v0.0.0-20181026193005-c67002cb31c3/go.mod h1:UVdnD1Gm6xHRNCYTkRU2/jEulfH38KcIWyp/GAMgvoE= -golang.org/x/lint v0.0.0-20190227174305-5b3e6a55c961/go.mod h1:wehouNa3lNwaWXcvxsM5YxQ5yQlVC4a0KAMCusXpPoU= -golang.org/x/lint v0.0.0-20190313153728-d0100b6bd8b3/go.mod h1:6SW0HCj/g11FgYtHlgUYUwCkIfeOF89ocIRzGO/8vkc= -golang.org/x/lint v0.0.0-20190930215403-16217165b5de h1:5hukYrvBGR8/eNkX5mdUezrA6JiaEZDtJb9Ei+1LlBs= -golang.org/x/lint v0.0.0-20190930215403-16217165b5de/go.mod h1:6SW0HCj/g11FgYtHlgUYUwCkIfeOF89ocIRzGO/8vkc= -golang.org/x/mobile v0.0.0-20190312151609-d3739f865fa6/go.mod h1:z+o9i4GpDbdi3rU15maQ/Ox0txvL9dWGYEHz965HBQE= -golang.org/x/mobile v0.0.0-20210527171505-7e972142eb43 h1:YfX4EDYuRrJhCu1S8M+jsXVoQj+koh5ZIwpI7bzeQ38= -golang.org/x/mobile v0.0.0-20210527171505-7e972142eb43/go.mod h1:jFTmtFYCV0MFtXBU+J5V/+5AUeVS0ON/0WkE/KSrl6E= -golang.org/x/mod v0.0.0-20190513183733-4bf6d317e70e/go.mod h1:mXi4GBBbnImb6dmsKGUJ2LatrhH/nqhxcFungHvyanc= -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.2.0 h1:KU7oHjnv3XNWfa5COkzUifxZmxp1TyI7ImMXqFxLwvQ= -golang.org/x/mod v0.2.0/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA= -golang.org/x/mod v0.4.2 h1:Gz96sIWK3OalVv/I/qNygP42zyoKp3xptRVCWRFEBvo= -golang.org/x/mod v0.4.2/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA= -golang.org/x/net v0.0.0-20180724234803-3673e40ba225/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= -golang.org/x/net v0.0.0-20180826012351-8a410e7b638d/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= -golang.org/x/net v0.0.0-20190108225652-1e06a53dbb7e/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= -golang.org/x/net v0.0.0-20190213061140-3a22650c66bd/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= -golang.org/x/net v0.0.0-20190311183353-d8887717615a/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg= -golang.org/x/net v0.0.0-20190404232315-eb5bcb51f2a3/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg= -golang.org/x/net v0.0.0-20190620200207-3b0461eec859/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= -golang.org/x/net v0.0.0-20190923162816-aa69164e4478/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= -golang.org/x/net v0.0.0-20200226121028-0de0cce0169b/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= -golang.org/x/net v0.0.0-20200324143707-d3edc9973b7e/go.mod h1:qpuaurCH72eLCgpAm/N6yyVIVM9cpaDIP3A8BGJEC5A= -golang.org/x/net v0.0.0-20200501053045-e0ff5e5a1de5/go.mod h1:qpuaurCH72eLCgpAm/N6yyVIVM9cpaDIP3A8BGJEC5A= -golang.org/x/net v0.0.0-20200506145744-7e3656a0809f h1:QBjCr1Fz5kw158VqdE9JfI9cJnl/ymnJWAdMuinqL7Y= -golang.org/x/net v0.0.0-20200506145744-7e3656a0809f/go.mod h1:qpuaurCH72eLCgpAm/N6yyVIVM9cpaDIP3A8BGJEC5A= -golang.org/x/net v0.0.0-20201201195509-5d6afe98e0b7/go.mod h1:sp8m0HH+o8qH0wwXwYZr8TS3Oi6o0r6Gce1SSxlDquU= -golang.org/x/net v0.0.0-20210119194325-5f4716e94777 h1:003p0dJM77cxMSyCPFphvZf/Y5/NXf5fzg6ufd1/Oew= -golang.org/x/net v0.0.0-20210119194325-5f4716e94777/go.mod h1:m0MpNAwzfU5UDzcl9v0D8zg8gWTRqZa9RBIspLL5mdg= -golang.org/x/net v0.0.0-20210226172049-e18ecbb05110/go.mod h1:m0MpNAwzfU5UDzcl9v0D8zg8gWTRqZa9RBIspLL5mdg= -golang.org/x/net v0.0.0-20210331212208-0fccb6fa2b5c/go.mod h1:p54w0d4576C0XHj96bSt6lcn1PtDYWL6XObtHCRCNQM= -golang.org/x/net v0.0.0-20210405180319-a5a99cb37ef4 h1:4nGaVu0QrbjT/AK2PRLuQfQuh6DJve+pELhqTdAj3x0= -golang.org/x/net v0.0.0-20210405180319-a5a99cb37ef4/go.mod h1:p54w0d4576C0XHj96bSt6lcn1PtDYWL6XObtHCRCNQM= -golang.org/x/net v0.0.0-20210502030024-e5908800b52b/go.mod h1:OJAsFXCWl8Ukc7SiCT/9KSuxbyM7479/AVlXFRxuMCk= -golang.org/x/net v0.0.0-20210525063256-abc453219eb5 h1:wjuX4b5yYQnEQHzd+CBcrcC6OVR2J1CN6mUy0oSxIPo= -golang.org/x/net v0.0.0-20210525063256-abc453219eb5/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y= -golang.org/x/oauth2 v0.0.0-20180821212333-d2e6202438be/go.mod h1:N/0e6XlmueqKjAGxoOufVs8QHGRruUQn6yWY3a++T0U= -golang.org/x/oauth2 v0.0.0-20200107190931-bf48bf16ab8d/go.mod h1:gOpvHmFTYa4IltrdGE7lF6nIHvwfUNPOp7c8zoXwtLw= -golang.org/x/sync v0.0.0-20180314180146-1d60e4601c6f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= -golang.org/x/sync v0.0.0-20181108010431-42b317875d0f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= -golang.org/x/sync v0.0.0-20181221193216-37e7f081c4d4/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= -golang.org/x/sync v0.0.0-20190423024810-112230192c58/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= -golang.org/x/sync v0.0.0-20190911185100-cd5d95a43a6e h1:vcxGaoTs7kV8m5Np9uUNQin4BrLOthgV7252N8V+FwY= -golang.org/x/sync v0.0.0-20190911185100-cd5d95a43a6e/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= -golang.org/x/sync v0.0.0-20210220032951-036812b2e83c h1:5KslGYwFpkhGh+Q16bwMP3cOontH8FOep7tGV86Y7SQ= -golang.org/x/sync v0.0.0-20210220032951-036812b2e83c/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= -golang.org/x/sys v0.0.0-20180830151530-49385e6e1522/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= -golang.org/x/sys v0.0.0-20190215142949-d0b11bdaac8a/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= -golang.org/x/sys v0.0.0-20190412213103-97732733099d/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= -golang.org/x/sys v0.0.0-20190422165155-953cdadca894/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= -golang.org/x/sys v0.0.0-20190924154521-2837fb4f24fe/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= -golang.org/x/sys v0.0.0-20191005200804-aed5e4c7ecf9/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= -golang.org/x/sys v0.0.0-20191026070338-33540a1f6037/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= -golang.org/x/sys v0.0.0-20200223170610-d5e6a3e2c0ae/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= -golang.org/x/sys v0.0.0-20200323222414-85ca7c5b95cd h1:xhmwyvizuTgC2qz7ZlMluP20uW+C3Rm0FD/WLDX8884= -golang.org/x/sys v0.0.0-20200323222414-85ca7c5b95cd/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= -golang.org/x/sys v0.0.0-20200930185726-fdedc70b468f/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= -golang.org/x/sys v0.0.0-20201119102817-f84b799fce68/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= -golang.org/x/sys v0.0.0-20210330210617-4fbd30eecc44 h1:Bli41pIlzTzf3KEY06n+xnzK/BESIg2ze4Pgfh/aI8c= -golang.org/x/sys v0.0.0-20210330210617-4fbd30eecc44/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= -golang.org/x/sys v0.0.0-20210423082822-04245dca01da/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= -golang.org/x/sys v0.0.0-20210510120138-977fb7262007/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= -golang.org/x/sys v0.0.0-20210603125802-9665404d3644 h1:CA1DEQ4NdKphKeL70tvsWNdT5oFh1lOjihRcEDROi0I= -golang.org/x/sys v0.0.0-20210603125802-9665404d3644/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= -golang.org/x/sys v0.0.0-20210608053332-aa57babbf139 h1:C+AwYEtBp/VQwoLntUmQ/yx3MS9vmZaKNdw5eOpoQe8= -golang.org/x/sys v0.0.0-20210608053332-aa57babbf139/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= -golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo= -golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= -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/text v0.3.6/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ= -golang.org/x/tools v0.0.0-20180221164845-07fd8470d635/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ= -golang.org/x/tools v0.0.0-20180917221912-90fa682c2a6e/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ= -golang.org/x/tools v0.0.0-20181030221726-6c7e314b6563/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ= -golang.org/x/tools v0.0.0-20190114222345-bf090417da8b/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ= -golang.org/x/tools v0.0.0-20190226205152-f727befe758c/go.mod h1:9Yl7xja0Znq3iFh3HoIrodX9oNMXvdceNzlUR8zjMvY= -golang.org/x/tools v0.0.0-20190311212946-11955173bddd/go.mod h1:LCzVGOaR6xXOjkQ3onu1FJEFr0SW1gC7cKk1uF8kGRs= -golang.org/x/tools v0.0.0-20190312151545-0bb0c0a6e846/go.mod h1:LCzVGOaR6xXOjkQ3onu1FJEFr0SW1gC7cKk1uF8kGRs= -golang.org/x/tools v0.0.0-20190524140312-2c0ae7006135/go.mod h1:RgjU9mgBXZiqYHBnxXauZ1Gv1EHHAz9KjViQ78xBX0Q= -golang.org/x/tools v0.0.0-20190621195816-6e04913cbbac/go.mod h1:/rFqwRUd4F7ZHNgwSSTFct+R/Kf4OFW1sUzUTQQTgfc= -golang.org/x/tools v0.0.0-20191029041327-9cc4af7d6b2c/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= -golang.org/x/tools v0.0.0-20191029190741-b9c20aec41a5/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= -golang.org/x/tools v0.0.0-20191119224855-298f0cb1881e/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= -golang.org/x/tools v0.0.0-20191216052735-49a3e744a425/go.mod h1:TB2adYChydJhpapKDTa4BR/hXlZSLoq2Wpct/0txZ28= -golang.org/x/tools v0.0.0-20200417140056-c07e33ef3290 h1:NXNmtp0ToD36cui5IqWy95LC4Y6vT/4y3RnPxlQPinU= -golang.org/x/tools v0.0.0-20200417140056-c07e33ef3290/go.mod h1:EkVYQZoAsY45+roYkvgYkIh4xh/qjgUK9TdY2XT94GE= -golang.org/x/tools v0.1.2 h1:kRBLX7v7Af8W7Gdbbc908OJcdgtK8bOz9Uaj8/F1ACA= -golang.org/x/tools v0.1.2/go.mod h1:o0xws9oXOQQZyjljx8fwUC0k7L1pTE6eaCbjGeHmOkk= -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= -golang.org/x/xerrors v0.0.0-20200804184101-5ec99f83aff1 h1:go1bK/D/BFZV2I8cIQd1NKEZ+0owSTG1fDTci4IqFcE= -golang.org/x/xerrors v0.0.0-20200804184101-5ec99f83aff1/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= -google.golang.org/appengine v1.1.0/go.mod h1:EbEs0AVv82hx2wNQdGPgUI5lhzA/G0D9YwlJXL52JkM= -google.golang.org/appengine v1.4.0/go.mod h1:xpcJRLb0r/rnEns0DIKYYv+WjYCduHsrkT7/EB5XEv4= -google.golang.org/genproto v0.0.0-20180817151627-c66870c02cf8/go.mod h1:JiN7NxoALGmiZfu7CAH4rXhgtRTLTxftemlI0sWmxmc= -google.golang.org/genproto v0.0.0-20190819201941-24fa4b261c55/go.mod h1:DMBHOl98Agz4BDEuKkezgsaosCRResVns1a3J2ZsMNc= -google.golang.org/genproto v0.0.0-20200511104702-f5ebc3bea380/go.mod h1:55QSHmfGQM9UVYDPBsyGGes0y52j32PQ3BqQfXhyH3c= -google.golang.org/grpc v1.19.0/go.mod h1:mqu4LbDTu4XGKhr4mRzUsmM4RtVoemTSY81AxZiDr8c= -google.golang.org/grpc v1.23.0/go.mod h1:Y5yQAOtifL1yxbo5wqy6BxZv8vAUGQwXBOALyacEbxg= -google.golang.org/grpc v1.25.1/go.mod h1:c3i+UQWmh7LiEpx4sFZnkU36qjEYZ0imhYfXVyQciAY= -google.golang.org/grpc v1.27.0/go.mod h1:qbnxyOmOxrQa7FizSgH+ReBfzJrCY1pSN7KXBS8abTk= -google.golang.org/grpc v1.29.1/go.mod h1:itym6AZVZYACWQqET3MqgPpjcuV5QH3BxFS3IjizoKk= -google.golang.org/protobuf v0.0.0-20200109180630-ec00e32a8dfd/go.mod h1:DFci5gLYBciE7Vtevhsrf46CRTquxDuWsQurQQe4oz8= -google.golang.org/protobuf v0.0.0-20200221191635-4d8936d0db64/go.mod h1:kwYJMbMJ01Woi6D6+Kah6886xMZcty6N08ah7+eCXa0= -google.golang.org/protobuf v0.0.0-20200228230310-ab0ca4ff8a60/go.mod h1:cfTl7dwQJ+fmap5saPgwCLgHXTUD7jkjRqWcaiX5VyM= -google.golang.org/protobuf v1.20.1-0.20200309200217-e05f789c0967/go.mod h1:A+miEFZTKqfCUM6K7xSMQL9OKL/b6hQv+e19PK+JZNE= -google.golang.org/protobuf v1.21.0/go.mod h1:47Nbq4nVaFHyn7ilMalzfO3qCViNmqZ2kzikPIcrTAo= -google.golang.org/protobuf v1.22.0/go.mod h1:EGpADcykh3NcUnDUJcl1+ZksZNG86OlYog2l/sGQquU= -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-20190902080502-41f04d3bba15 h1:YR8cESwS4TdDjEe65xsg0ogRM/Nc3DYOhEAlW+xobZo= -gopkg.in/check.v1 v1.0.0-20190902080502-41f04d3bba15/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= -gopkg.in/check.v1 v1.0.0-20201130134442-10cb98267c6c h1:Hei/4ADfdWqJk1ZMxUNpqntNwaWcugrBjAiHlqqRiVk= -gopkg.in/check.v1 v1.0.0-20201130134442-10cb98267c6c/go.mod h1:JHkPIbrfpd72SG/EVd6muEfDQjcINNoR0C8j2r3qZ4Q= -gopkg.in/errgo.v2 v2.1.0/go.mod h1:hNsd1EY+bozCKY1Ytp96fpM3vjJbqLJn88ws8XvfDNI= -gopkg.in/h2non/gock.v1 v1.0.14 h1:fTeu9fcUvSnLNacYvYI54h+1/XEteDyHvrVCZEEEYNM= -gopkg.in/h2non/gock.v1 v1.0.14/go.mod h1:sX4zAkdYX1TRGJ2JY156cFspQn4yRWn6p9EMdODlynE= -gopkg.in/macaroon.v2 v2.1.0/go.mod h1:OUb+TQP/OP0WOerC2Jp/3CwhIKyIa9kQjuc7H24e6/o= -gopkg.in/square/go-jose.v2 v2.5.1/go.mod h1:M9dMgbHiYLoDGQrXy7OpJDJWiKiU//h+vD76mk0e1AI= -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.v3 v3.0.0-20200313102051-9f266ea9e77c h1:dUUwHk2QECo/6vqA44rthZ8ie2QXMNeKRTHCNY2nXvo= -gopkg.in/yaml.v3 v3.0.0-20200313102051-9f266ea9e77c/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= -honnef.co/go/tools v0.0.0-20190102054323-c2f93a96b099/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=