From db6d7eb70f5c27f3a72fc31ca9fa65a4c67c78b1 Mon Sep 17 00:00:00 2001 From: Moses Narrow Date: Sun, 19 May 2024 19:09:00 -0500 Subject: [PATCH 01/10] include raw query in url --- cmd/dmsgweb/commands/dmsgweb.go | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/cmd/dmsgweb/commands/dmsgweb.go b/cmd/dmsgweb/commands/dmsgweb.go index 4624c5f1..71520e9a 100644 --- a/cmd/dmsgweb/commands/dmsgweb.go +++ b/cmd/dmsgweb/commands/dmsgweb.go @@ -234,7 +234,7 @@ dmsgweb env file detected: ` + envfile r.Any("/*path", func(c *gin.Context) { var urlStr string if resolveDmsgAddr != "" { - urlStr = fmt.Sprintf("dmsg://%s%s", resolveDmsgAddr, c.Param("path")) + urlStr = fmt.Sprintf("dmsg://%s%s%s", resolveDmsgAddr, c.Param("path"),c.Request.URL.RawQuery) } else { hostParts := strings.Split(c.Request.Host, ":") @@ -244,7 +244,7 @@ dmsgweb env file detected: ` + envfile } else { dmsgp = "80" } - urlStr = fmt.Sprintf("dmsg://%s:%s%s", strings.TrimRight(hostParts[0], filterDomainSuffix), dmsgp, c.Param("path")) + urlStr = fmt.Sprintf("dmsg://%s:%s%s%s", strings.TrimRight(hostParts[0], filterDomainSuffix), dmsgp, c.Param("path"),c.Request.URL.RawQuery) } req, err := http.NewRequest(http.MethodGet, urlStr, nil) if err != nil { From c2bec79e1a5accac39c09c63305c07691bb08025 Mon Sep 17 00:00:00 2001 From: Moses Narrow Date: Sun, 19 May 2024 19:19:32 -0500 Subject: [PATCH 02/10] include raw query correctly in url --- cmd/dmsgweb/commands/dmsgweb.go | 10 ++++++++-- 1 file changed, 8 insertions(+), 2 deletions(-) diff --git a/cmd/dmsgweb/commands/dmsgweb.go b/cmd/dmsgweb/commands/dmsgweb.go index 71520e9a..e06b31bc 100644 --- a/cmd/dmsgweb/commands/dmsgweb.go +++ b/cmd/dmsgweb/commands/dmsgweb.go @@ -234,7 +234,10 @@ dmsgweb env file detected: ` + envfile r.Any("/*path", func(c *gin.Context) { var urlStr string if resolveDmsgAddr != "" { - urlStr = fmt.Sprintf("dmsg://%s%s%s", resolveDmsgAddr, c.Param("path"),c.Request.URL.RawQuery) + urlStr = fmt.Sprintf("dmsg://%s%s", resolveDmsgAddr, c.Param("path")) + if c.Request.URL.RawQuery != "" { + urlStr += fmt.Sprintf("%s?%s", urlStr,c.Request.URL.RawQuery) + } } else { hostParts := strings.Split(c.Request.Host, ":") @@ -244,7 +247,10 @@ dmsgweb env file detected: ` + envfile } else { dmsgp = "80" } - urlStr = fmt.Sprintf("dmsg://%s:%s%s%s", strings.TrimRight(hostParts[0], filterDomainSuffix), dmsgp, c.Param("path"),c.Request.URL.RawQuery) + urlStr = fmt.Sprintf("dmsg://%s:%s%s", strings.TrimRight(hostParts[0], filterDomainSuffix), dmsgp, c.Param("path")) + if c.Request.URL.RawQuery != "" { + urlStr += fmt.Sprintf("%s?%s", urlStr,c.Request.URL.RawQuery) + } } req, err := http.NewRequest(http.MethodGet, urlStr, nil) if err != nil { From 6c1439d7a98eed7388b37f994e154139a9c389af Mon Sep 17 00:00:00 2001 From: Moses Narrow Date: Sun, 19 May 2024 19:22:08 -0500 Subject: [PATCH 03/10] include raw query correctly in url --- cmd/dmsgweb/commands/dmsgweb.go | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/cmd/dmsgweb/commands/dmsgweb.go b/cmd/dmsgweb/commands/dmsgweb.go index e06b31bc..3f74895e 100644 --- a/cmd/dmsgweb/commands/dmsgweb.go +++ b/cmd/dmsgweb/commands/dmsgweb.go @@ -236,7 +236,7 @@ dmsgweb env file detected: ` + envfile if resolveDmsgAddr != "" { urlStr = fmt.Sprintf("dmsg://%s%s", resolveDmsgAddr, c.Param("path")) if c.Request.URL.RawQuery != "" { - urlStr += fmt.Sprintf("%s?%s", urlStr,c.Request.URL.RawQuery) + urlStr = fmt.Sprintf("%s?%s", urlStr, c.Request.URL.RawQuery) } } else { @@ -249,7 +249,7 @@ dmsgweb env file detected: ` + envfile } urlStr = fmt.Sprintf("dmsg://%s:%s%s", strings.TrimRight(hostParts[0], filterDomainSuffix), dmsgp, c.Param("path")) if c.Request.URL.RawQuery != "" { - urlStr += fmt.Sprintf("%s?%s", urlStr,c.Request.URL.RawQuery) + urlStr = fmt.Sprintf("%s?%s", urlStr, c.Request.URL.RawQuery) } } req, err := http.NewRequest(http.MethodGet, urlStr, nil) From 906e2cea5dd159804bb06ef9e7732828661f0f2c Mon Sep 17 00:00:00 2001 From: Moses Narrow Date: Sun, 19 May 2024 19:36:51 -0500 Subject: [PATCH 04/10] handle non GET requests --- cmd/dmsgweb/commands/dmsgweb.go | 91 +++++++++++++++++++++------------ 1 file changed, 57 insertions(+), 34 deletions(-) diff --git a/cmd/dmsgweb/commands/dmsgweb.go b/cmd/dmsgweb/commands/dmsgweb.go index 3f74895e..b1c00ba3 100644 --- a/cmd/dmsgweb/commands/dmsgweb.go +++ b/cmd/dmsgweb/commands/dmsgweb.go @@ -232,40 +232,63 @@ dmsgweb env file detected: ` + envfile r.Use(loggingMiddleware()) r.Any("/*path", func(c *gin.Context) { - var urlStr string - if resolveDmsgAddr != "" { - urlStr = fmt.Sprintf("dmsg://%s%s", resolveDmsgAddr, c.Param("path")) - if c.Request.URL.RawQuery != "" { - urlStr = fmt.Sprintf("%s?%s", urlStr, c.Request.URL.RawQuery) - } - } else { - - hostParts := strings.Split(c.Request.Host, ":") - var dmsgp string - if len(hostParts) > 1 { - dmsgp = hostParts[1] - } else { - dmsgp = "80" - } - urlStr = fmt.Sprintf("dmsg://%s:%s%s", strings.TrimRight(hostParts[0], filterDomainSuffix), dmsgp, c.Param("path")) - if c.Request.URL.RawQuery != "" { - urlStr = fmt.Sprintf("%s?%s", urlStr, c.Request.URL.RawQuery) - } - } - req, err := http.NewRequest(http.MethodGet, urlStr, nil) - if err != nil { - c.String(http.StatusInternalServerError, "Failed to create HTTP request") - return - } - resp, err := httpC.Do(req) - if err != nil { - c.String(http.StatusInternalServerError, "Failed to connect to HTTP server") - return - } - defer resp.Body.Close() //nolint - c.Status(http.StatusOK) - io.Copy(c.Writer, resp.Body) //nolint - }) + var urlStr string + if resolveDmsgAddr != "" { + urlStr = fmt.Sprintf("dmsg://%s%s", resolveDmsgAddr, c.Param("path")) + if c.Request.URL.RawQuery != "" { + urlStr = fmt.Sprintf("%s?%s", urlStr, c.Request.URL.RawQuery) + } + } else { + hostParts := strings.Split(c.Request.Host, ":") + var dmsgp string + if len(hostParts) > 1 { + dmsgp = hostParts[1] + } else { + dmsgp = "80" + } + urlStr = fmt.Sprintf("dmsg://%s:%s%s", strings.TrimRight(hostParts[0], filterDomainSuffix), dmsgp, c.Param("path")) + if c.Request.URL.RawQuery != "" { + urlStr = fmt.Sprintf("%s?%s", urlStr, c.Request.URL.RawQuery) + } + } + + // Create a new request using the original method and body + req, err := http.NewRequest(c.Request.Method, urlStr, c.Request.Body) + if err != nil { + c.String(http.StatusInternalServerError, "Failed to create HTTP request") + return + } + + // Copy headers from the original request + for header, values := range c.Request.Header { + for _, value := range values { + req.Header.Add(header, value) + } + } + + // Perform the request + resp, err := httpC.Do(req) + if err != nil { + c.String(http.StatusInternalServerError, "Failed to connect to HTTP server") + return + } + defer resp.Body.Close() + + // Copy response headers + for header, values := range resp.Header { + for _, value := range values { + c.Writer.Header().Add(header, value) + } + } + + // Set the status code from the proxied response + c.Status(resp.StatusCode) + + // Copy the response body + if _, err := io.Copy(c.Writer, resp.Body); err != nil { + c.String(http.StatusInternalServerError, "Failed to copy response body") + } + }) wg.Add(1) go func() { dmsgWebLog.Debug(fmt.Sprintf("Serving http on: http://127.0.0.1:%v", webPort)) From 6365e8d23ed497a4a417771b60fc2cacbf4e2d7a Mon Sep 17 00:00:00 2001 From: Moses Narrow Date: Sun, 19 May 2024 20:12:40 -0500 Subject: [PATCH 05/10] handle non GET requests --- cmd/dmsgweb/commands/dmsgweb.go | 110 +++++++++++++++----------------- 1 file changed, 53 insertions(+), 57 deletions(-) diff --git a/cmd/dmsgweb/commands/dmsgweb.go b/cmd/dmsgweb/commands/dmsgweb.go index b1c00ba3..5a493411 100644 --- a/cmd/dmsgweb/commands/dmsgweb.go +++ b/cmd/dmsgweb/commands/dmsgweb.go @@ -232,63 +232,59 @@ dmsgweb env file detected: ` + envfile r.Use(loggingMiddleware()) r.Any("/*path", func(c *gin.Context) { - var urlStr string - if resolveDmsgAddr != "" { - urlStr = fmt.Sprintf("dmsg://%s%s", resolveDmsgAddr, c.Param("path")) - if c.Request.URL.RawQuery != "" { - urlStr = fmt.Sprintf("%s?%s", urlStr, c.Request.URL.RawQuery) - } - } else { - hostParts := strings.Split(c.Request.Host, ":") - var dmsgp string - if len(hostParts) > 1 { - dmsgp = hostParts[1] - } else { - dmsgp = "80" - } - urlStr = fmt.Sprintf("dmsg://%s:%s%s", strings.TrimRight(hostParts[0], filterDomainSuffix), dmsgp, c.Param("path")) - if c.Request.URL.RawQuery != "" { - urlStr = fmt.Sprintf("%s?%s", urlStr, c.Request.URL.RawQuery) - } - } - - // Create a new request using the original method and body - req, err := http.NewRequest(c.Request.Method, urlStr, c.Request.Body) - if err != nil { - c.String(http.StatusInternalServerError, "Failed to create HTTP request") - return - } - - // Copy headers from the original request - for header, values := range c.Request.Header { - for _, value := range values { - req.Header.Add(header, value) - } - } - - // Perform the request - resp, err := httpC.Do(req) - if err != nil { - c.String(http.StatusInternalServerError, "Failed to connect to HTTP server") - return - } - defer resp.Body.Close() - - // Copy response headers - for header, values := range resp.Header { - for _, value := range values { - c.Writer.Header().Add(header, value) - } - } - - // Set the status code from the proxied response - c.Status(resp.StatusCode) - - // Copy the response body - if _, err := io.Copy(c.Writer, resp.Body); err != nil { - c.String(http.StatusInternalServerError, "Failed to copy response body") - } - }) + var urlStr string + if resolveDmsgAddr != "" { + urlStr = fmt.Sprintf("dmsg://%s%s", resolveDmsgAddr, c.Param("path")) + if c.Request.URL.RawQuery != "" { + urlStr = fmt.Sprintf("%s?%s", urlStr, c.Request.URL.RawQuery) + } + } else { + hostParts := strings.Split(c.Request.Host, ":") + var dmsgp string + if len(hostParts) > 1 { + dmsgp = hostParts[1] + } else { + dmsgp = "80" + } + urlStr = fmt.Sprintf("dmsg://%s:%s%s", strings.TrimRight(hostParts[0], filterDomainSuffix), dmsgp, c.Param("path")) + if c.Request.URL.RawQuery != "" { + urlStr = fmt.Sprintf("%s?%s", urlStr, c.Request.URL.RawQuery) + } + } + + fmt.Printf("Proxying request: %s %s\n", c.Request.Method, urlStr) + req, err := http.NewRequest(c.Request.Method, urlStr, c.Request.Body) + if err != nil { + c.String(http.StatusInternalServerError, "Failed to create HTTP request") + return + } + + for header, values := range c.Request.Header { + for _, value := range values { + req.Header.Add(header, value) + } + } + + resp, err := httpC.Do(req) + if err != nil { + c.String(http.StatusInternalServerError, "Failed to connect to HTTP server") + fmt.Printf("Error: %v\n", err) + return + } + defer resp.Body.Close() + + for header, values := range resp.Header { + for _, value := range values { + c.Writer.Header().Add(header, value) + } + } + + c.Status(resp.StatusCode) + if _, err := io.Copy(c.Writer, resp.Body); err != nil { + c.String(http.StatusInternalServerError, "Failed to copy response body") + fmt.Printf("Error copying response body: %v\n", err) + } + }) wg.Add(1) go func() { dmsgWebLog.Debug(fmt.Sprintf("Serving http on: http://127.0.0.1:%v", webPort)) From f8b094790fa54b36d7528dbd144f2cacf92c9713 Mon Sep 17 00:00:00 2001 From: Moses Narrow Date: Mon, 20 May 2024 10:16:00 -0500 Subject: [PATCH 06/10] fix CI errors --- cmd/dmsgweb/commands/dmsgweb.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/cmd/dmsgweb/commands/dmsgweb.go b/cmd/dmsgweb/commands/dmsgweb.go index 5a493411..d7b050a2 100644 --- a/cmd/dmsgweb/commands/dmsgweb.go +++ b/cmd/dmsgweb/commands/dmsgweb.go @@ -271,7 +271,7 @@ dmsgweb env file detected: ` + envfile fmt.Printf("Error: %v\n", err) return } - defer resp.Body.Close() + defer resp.Body.Close() //nolint for header, values := range resp.Header { for _, value := range values { From df2dc8cfc74a6628ebfe3774942a79f0e141337f Mon Sep 17 00:00:00 2001 From: Moses Narrow Date: Mon, 20 May 2024 12:50:34 -0500 Subject: [PATCH 07/10] add subcommand for server side implementation of dmsgweb --- cmd/dmsgweb/commands/dmsgweb.go | 336 ++++++++++++++++++++++++++++---- examples/proxified/main.go | 4 +- 2 files changed, 295 insertions(+), 45 deletions(-) diff --git a/cmd/dmsgweb/commands/dmsgweb.go b/cmd/dmsgweb/commands/dmsgweb.go index d7b050a2..3502bd38 100644 --- a/cmd/dmsgweb/commands/dmsgweb.go +++ b/cmd/dmsgweb/commands/dmsgweb.go @@ -8,6 +8,8 @@ import ( "log" "net" "net/http" + "net/http/httputil" + "net/url" "os" "os/signal" "path/filepath" @@ -47,7 +49,7 @@ func (r *customResolver) Resolve(ctx context.Context, name string) (context.Cont return ctx, nil, fmt.Errorf("failed to parse IP address") } // Modify the context to include the desired port - ctx = context.WithValue(ctx, "port", strconv.Itoa(webPort)) //nolint + ctx = context.WithValue(ctx, "port", fmt.Sprintf("%v",webPort)) //nolint return ctx, ip, nil } // Use default name resolution for other domains @@ -60,9 +62,10 @@ var ( dmsgSessions int filterDomainSuffix string sk cipher.SecKey + pk cipher.PubKey dmsgWebLog *logging.Logger logLvl string - webPort int + webPort uint proxyPort uint addProxy string resolveDmsgAddr string @@ -70,25 +73,24 @@ var ( isEnvs bool ) -const envname = "DMSGWEB" - -var envfile = os.Getenv(envname) +const dmsgwebenvname = "DMSGWEB" +var dmsgwebconffile = os.Getenv(dmsgwebenvname) func init() { RootCmd.Flags().StringVarP(&filterDomainSuffix, "filter", "f", ".dmsg", "domain suffix to filter") - RootCmd.Flags().UintVarP(&proxyPort, "socks", "q", scriptExecUint("${PROXYPORT:-4445}"), "port to serve the socks5 proxy") - RootCmd.Flags().StringVarP(&addProxy, "proxy", "r", scriptExecString("${ADDPROXY}"), "configure additional socks5 proxy for dmsgweb (i.e. 127.0.0.1:1080)") - RootCmd.Flags().IntVarP(&webPort, "port", "p", scriptExecInt("${WEBPORT:-8080}"), "port to serve the web application") - RootCmd.Flags().StringVarP(&resolveDmsgAddr, "resolve", "t", scriptExecString("${RESOLVEPK}"), "resolve the specified dmsg address:port on the local port & disable proxy") + RootCmd.Flags().UintVarP(&proxyPort, "socks", "q", scriptExecUint("${PROXYPORT:-4445}", dmsgwebconffile), "port to serve the socks5 proxy") + RootCmd.Flags().StringVarP(&addProxy, "proxy", "r", scriptExecString("${ADDPROXY}", dmsgwebconffile), "configure additional socks5 proxy for dmsgweb (i.e. 127.0.0.1:1080)") + RootCmd.Flags().UintVarP(&webPort, "port", "p", scriptExecUint("${WEBPORT:-8080}",dmsgwebconffile), "port to serve the web application") + RootCmd.Flags().StringVarP(&resolveDmsgAddr, "resolve", "t", scriptExecString("${RESOLVEPK}",dmsgwebconffile), "resolve the specified dmsg address:port on the local port & disable proxy") RootCmd.Flags().StringVarP(&dmsgDisc, "dmsg-disc", "d", skyenv.DmsgDiscAddr, "dmsg discovery url") - RootCmd.Flags().IntVarP(&dmsgSessions, "sess", "e", scriptExecInt("${DMSGSESSIONS:-1}"), "number of dmsg servers to connect to") + RootCmd.Flags().IntVarP(&dmsgSessions, "sess", "e", scriptExecInt("${DMSGSESSIONS:-1}",dmsgwebconffile), "number of dmsg servers to connect to") RootCmd.Flags().StringVarP(&logLvl, "loglvl", "l", "", "[ debug | warn | error | fatal | panic | trace | info ]\033[0m") if os.Getenv("DMSGWEB_SK") != "" { sk.Set(os.Getenv("DMSGWEB_SK")) //nolint } - if scriptExecString("${DMSGWEB_SK}") != "" { - sk.Set(scriptExecString("${DMSGWEB_SK}")) //nolint + if scriptExecString("${DMSGWEB_SK}",dmsgwebconffile) != "" { + sk.Set(scriptExecString("${DMSGWEB_SK}",dmsgwebconffile)) //nolint } RootCmd.Flags().VarP(&sk, "sk", "s", "a random key is generated if unspecified\n\r") RootCmd.Flags().BoolVarP(&isEnvs, "envs", "z", false, "show example .conf file") @@ -105,14 +107,14 @@ var RootCmd = &cobra.Command{ ┌┬┐┌┬┐┌─┐┌─┐┬ ┬┌─┐┌┐ │││││└─┐│ ┬│││├┤ ├┴┐ ─┴┘┴ ┴└─┘└─┘└┴┘└─┘└─┘ -DMSG resolving proxy & browser client - access websites over dmsg` + func() string { - if _, err := os.Stat(envfile); err == nil { +DMSG resolving proxy & browser client - access websites and http interfaces over dmsg` + func() string { + if _, err := os.Stat(dmsgwebconffile); err == nil { return ` -dmsgweb env file detected: ` + envfile +dmsgweb conf file detected: ` + dmsgwebconffile } return ` .conf file may also be specified with -` + envname + `=/path/to/dmsgweb.conf skywire dmsg web` +` + dmsgwebenvname + `=/path/to/dmsgweb.conf skywire dmsg web` }(), SilenceErrors: true, SilenceUsage: true, @@ -121,10 +123,16 @@ dmsgweb env file detected: ` + envfile Version: buildinfo.Version(), Run: func(cmd *cobra.Command, _ []string) { if isEnvs { + envfile := envfileLinux if runtime.GOOS == "windows" { - envfile = envfileWindows - } else { - envfile = envfileLinux + envfileslice, _ := script.Echo(envfile).Slice() + for i, _ := range envfileslice { + efs, _ := script.Echo(envfileslice[i]).Reject("##").Reject("#-").Reject("# ").Replace("#", "#$").String() + if efs != "" && efs != "\n" { + envfileslice[i] = strings.ReplaceAll(efs, "\n", "") + } + } + envfile = strings.Join(envfileslice, "\n") } fmt.Println(envfile) os.Exit(0) @@ -187,7 +195,7 @@ dmsgweb env file detected: ` + envfile if match { port, ok := ctx.Value("port").(string) if !ok { - port = strconv.Itoa(webPort) + port = fmt.Sprintf("%v",webPort) } addr = "localhost:" + port } else { @@ -288,7 +296,7 @@ dmsgweb env file detected: ` + envfile wg.Add(1) go func() { dmsgWebLog.Debug(fmt.Sprintf("Serving http on: http://127.0.0.1:%v", webPort)) - r.Run(":" + strconv.Itoa(webPort)) //nolint + r.Run(":" + fmt.Sprintf("%v",webPort)) //nolint dmsgWebLog.Debug(fmt.Sprintf("Stopped serving http on: http://127.0.0.1:%v", webPort)) wg.Done() }() @@ -296,6 +304,225 @@ dmsgweb env file detected: ` + envfile }, } + + +var ( + startTime = time.Now() + runTime time.Duration + dmsgPort uint + dmsgSess int + wl string + wlkeys []cipher.PubKey + localPort uint + websrvPort uint + err error +) + +const dmsgwebsrvenvname = "DMSGWEBSRV" +var dmsgwebsrvconffile = os.Getenv(dmsgwebsrvenvname) + + +func init() { + RootCmd.AddCommand(srvCmd) + srvCmd.Flags().UintVarP(&localPort, "lport", "l", scriptExecUint("${LOCALPORT:-8086}", dmsgwebsrvconffile), "local application http interface port") + srvCmd.Flags().UintVarP(&websrvPort, "port", "p", scriptExecUint("${WEBPORT:-8081}", dmsgwebsrvconffile), "port to serve") + srvCmd.Flags().UintVarP(&dmsgPort, "dport", "d", scriptExecUint("${DMSGPORT:-80}", dmsgwebsrvconffile), "dmsg port to serve") + srvCmd.Flags().StringVarP(&wl, "wl", "w", scriptExecArray("${WHITELISTPKS[@]}", dmsgwebsrvconffile), "whitelisted keys for dmsg authenticated routes\r") + srvCmd.Flags().StringVarP(&dmsgDisc, "dmsg-disc", "D", skyenv.DmsgDiscAddr, "dmsg discovery url") + srvCmd.Flags().IntVarP(&dmsgSess, "dsess", "e", scriptExecInt("${DMSGSESSIONS:-1}", dmsgwebsrvconffile), "dmsg sessions") + if os.Getenv("DMSGWEBSRV_SK") != "" { sk.Set(os.Getenv("DMSGWEBSRV_SK")) } //nolint + if scriptExecString("${DMSGWEBSRV_SK}", dmsgwebsrvconffile) != "" { sk.Set(scriptExecString("${DMSGWEBSRV_SK}", dmsgwebsrvconffile)) } //nolint + pk, _ = sk.PubKey() + srvCmd.Flags().VarP(&sk, "sk", "s", "a random key is generated if unspecified\n\r") + srvCmd.Flags().BoolVarP(&isEnvs, "envs", "z", false, "show example .conf file") + + srvCmd.CompletionOptions.DisableDefaultCmd = true +} + + +var srvCmd = &cobra.Command{ + Use: "srv", + Short: "serve http from local port over dmsg", + Long: `DMSG web server - serve http interface from local port over dmsg` + func() string { + if _, err := os.Stat(dmsgwebsrvconffile); err == nil { + return ` + dmsgvlcenv file detected: ` + dmsgwebsrvconffile + } + return `dmsg streaming media with vlc + + .conf file may also be specified with + `+dmsgwebsrvenvname+`=/path/to/dmsgwebsrv.conf skywire dmsg web srv` + }(), + Run: func(_ *cobra.Command, _ []string) { + if isEnvs { + envfile := envfileLinux + if runtime.GOOS == "windows" { + envfileslice, _ := script.Echo(envfile).Slice() + for i, _ := range envfileslice { + efs, _ := script.Echo(envfileslice[i]).Reject("##").Reject("#-").Reject("# ").Replace("#", "#$").String() + if efs != "" && efs != "\n" { + envfileslice[i] = strings.ReplaceAll(efs, "\n", "") + } + } + envfile = strings.Join(envfileslice, "\n") + } + fmt.Println(envfile) + os.Exit(0) + } + Server() + }, + +} + +func Server() { + log := logging.MustGetLogger("dmsgvlc") + + ctx, cancel := cmdutil.SignalContext(context.Background(), log) + + defer cancel() + pk, err = sk.PubKey() + if err != nil { + pk, sk = cipher.GenerateKeyPair() + } + if wl != "" { + wlk := strings.Split(wl, ",") + for _, key := range wlk { + var pk0 cipher.PubKey + err := pk0.Set(key) + if err == nil { + wlkeys = append(wlkeys, pk0) + } + } + } + if len(wlkeys) > 0 { + if len(wlkeys) == 1 { + log.Info(fmt.Sprintf("%d key whitelisted", len(wlkeys))) + } else { + log.Info(fmt.Sprintf("%d keys whitelisted", len(wlkeys))) + } + } + + dmsgC := dmsg.NewClient(pk, sk, disc.NewHTTP(dmsgDisc, &http.Client{}, log), dmsg.DefaultConfig()) + defer func() { + if err := dmsgC.Close(); err != nil { + log.WithError(err).Error() + } + }() + + go dmsgC.Serve(context.Background()) + + select { + case <-ctx.Done(): + log.WithError(ctx.Err()).Warn() + return + + case <-dmsgC.Ready(): + } + + lis, err := dmsgC.Listen(uint16(dmsgPort)) + if err != nil { + log.WithError(err).Fatal() + } + go func() { + <-ctx.Done() + if err := lis.Close(); err != nil { + log.WithError(err).Error() + } + }() + + + r1 := gin.New() + r1.Use(gin.Recovery()) + r1.Use(loggingMiddleware()) + + authRoute := r1.Group("/") + if len(wlkeys) > 0 { + authRoute.Use(whitelistAuth(wlkeys)) + } + authRoute.Any("/*path", func(c *gin.Context) { + targetURL, _ := url.Parse(fmt.Sprintf("http://127.0.0.1:%v%s?%s", localPort, c.Request.URL.Path, c.Request.URL.RawQuery)) + proxy := httputil.ReverseProxy{ + Director: func(req *http.Request) { + req.URL = targetURL + req.Host = targetURL.Host + req.Method = c.Request.Method + }, + Transport: &http.Transport{}, + } + proxy.ServeHTTP(c.Writer, c.Request) + }) + + + +serve := &http.Server{ + Handler: &GinHandler{Router: r1}, + ReadHeaderTimeout: 5 * time.Second, + ReadTimeout: 10 * time.Second, + WriteTimeout: 10 * time.Second, +} + + wg := new(sync.WaitGroup) + wg.Add(1) + go func() { + log.WithField("dmsg_addr", lis.Addr().String()).Info("Serving... ") + if err := serve.Serve(lis); err != nil && err != http.ErrServerClosed { + log.Fatalf("Serve1: %v", err) + } + wg.Done() + }() + + wg.Add(1) + go func() { + fmt.Printf("listening on http://127.0.0.1:%d using gin router\n", websrvPort) + r1.Run(fmt.Sprintf(":%d", websrvPort)) + wg.Done() + }() + + wg.Wait() +} + + +func whitelistAuth(whitelistedPKs []cipher.PubKey) gin.HandlerFunc { + return func(c *gin.Context) { + remotePK, _, err := net.SplitHostPort(c.Request.RemoteAddr) + if err != nil { + c.Writer.WriteHeader(http.StatusInternalServerError) + c.Writer.Write([]byte("500 Internal Server Error")) + c.AbortWithStatus(http.StatusInternalServerError) + return + } + whitelisted := false + if len(whitelistedPKs) == 0 { + whitelisted = true + } else { + for _, whitelistedPK := range whitelistedPKs { + if remotePK == whitelistedPK.String() { + whitelisted = true + break + } + } + } + if whitelisted { + c.Next() + } else { + c.Writer.WriteHeader(http.StatusUnauthorized) + c.Writer.Write([]byte("401 Unauthorized")) + c.AbortWithStatus(http.StatusUnauthorized) + return + } + } +} + + +type GinHandler struct { +Router *gin.Engine +} + +func (h *GinHandler) ServeHTTP(w http.ResponseWriter, r *http.Request) { +h.Router.ServeHTTP(w, r) +} + + func startDmsg(ctx context.Context, pk cipher.PubKey, sk cipher.SecKey) (dmsgC *dmsg.Client, stop func(), err error) { dmsgC = dmsg.NewClient(pk, sk, disc.NewHTTP(dmsgDisc, &http.Client{}, dmsgWebLog), &dmsg.Config{MinSessions: dmsgSessions}) go dmsgC.Serve(context.Background()) @@ -408,7 +635,7 @@ func Execute() { } } -func scriptExecString(s string) string { +func scriptExecString(s, envfile string) string { if runtime.GOOS == "windows" { var variable, defaultvalue string if strings.Contains(s, ":-") { @@ -435,7 +662,29 @@ func scriptExecString(s string) string { return "" } -func scriptExecInt(s string) int { +func scriptExecArray(s, envfile string) string { + if runtime.GOOS == "windows" { + variable := s + if strings.Contains(variable, "[@]}") { + variable = strings.TrimRight(variable, "[@]}") + variable = strings.TrimRight(variable, "{") + } + out, err := script.Exec(fmt.Sprintf(`powershell -c '$SKYENV = "%s"; if ($SKYENV -ne "" -and (Test-Path $SKYENV)) { . $SKYENV }; foreach ($item in %s) { Write-Host $item }'`, envfile, variable)).Slice() + if err == nil { + if len(out) != 0 { + return "" + } + return strings.Join(out, ",") + } + } + y, err := script.Exec(fmt.Sprintf(`bash -c 'SKYENV=%s ; if [[ $SKYENV != "" ]] && [[ -f $SKYENV ]] ; then source $SKYENV ; fi ; for _i in %s ; do echo "$_i" ; done'`, envfile, s)).Slice() + if err == nil { + return strings.Join(y, ",") + } + return "" +} + +func scriptExecInt(s, envfile string) int { if runtime.GOOS == "windows" { var variable string if strings.Contains(s, ":-") { @@ -469,7 +718,7 @@ func scriptExecInt(s string) int { } return 0 } -func scriptExecUint(s string) uint { +func scriptExecUint(s, envfile string) uint { if runtime.GOOS == "windows" { var variable string if strings.Contains(s, ":-") { @@ -506,9 +755,9 @@ func scriptExecUint(s string) uint { const envfileLinux = ` ######################################################################### -# DMSGWEB CONFIG TEMPLATE -# Defaults shown -# Uncomment to change default value +#-- DMSGWEB CONFIG TEMPLATE +#-- Defaults shown +#-- Uncomment to change default value ######################################################################### #-- Set port for proxy interface @@ -526,31 +775,34 @@ const envfileLinux = ` #-- Number of dmsg servers to connect to (0 unlimits) #DMSGSESSIONS=1 +#-- Dmsg port to use +#DMSGPORT=80 + #-- Set secret key #DMSGWEB_SK='' ` -const envfileWindows = ` +const srvenvfileLinux = ` ######################################################################### -# DMSGWEB CONFIG TEMPLATE -# Defaults shown -# Uncomment to change default value +#-- DMSGWEB SRV CONFIG TEMPLATE +#-- Defaults shown +#-- Uncomment to change default value ######################################################################### -#-- Set port for proxy interface -#$PROXYPORT=4445 - -#-- Configure additional proxy for dmsgvlc to use -#$ADDPROXY='127.0.0.1:1080' +#-- DMSG port to serve +#DMSGPORT=80 -#-- Web Interface Port -#$WEBPORT=8080 +#-- Port for this application to serve http +#WEBPORT=8081 -#-- Resove a specific PK to the web port (also disables proxy) -#$RESOLVEPK='' +#-- Local Port to serve over dmsg +LOCALPORT=8086 #-- Number of dmsg servers to connect to (0 unlimits) -#$DMSGSESSIONS=1 +#DMSGSESSIONS=1 #-- Set secret key -#$DMSGWEB_SK='' +#DMSGWEBSRV_SK='' + +#-- Whitelisted keys to access the web interface +#WHITELISTPKS=('') ` diff --git a/examples/proxified/main.go b/examples/proxified/main.go index 710eb1ed..56f0975c 100644 --- a/examples/proxified/main.go +++ b/examples/proxified/main.go @@ -2,14 +2,12 @@ package main import ( "context" - "net/http" "time" + "github.com/skycoin/skywire-utilities/pkg/cipher" "github.com/skycoin/skywire-utilities/pkg/logging" "github.com/skycoin/skywire-utilities/pkg/skyenv" - - "github.com/skycoin/skywire-utilities/pkg/cipher" "golang.org/x/net/proxy" "github.com/skycoin/dmsg/pkg/disc" From 7dd38bfd58a0a4ea0f02cea1f3e6632140eb2426 Mon Sep 17 00:00:00 2001 From: Moses Narrow Date: Mon, 20 May 2024 12:51:15 -0500 Subject: [PATCH 08/10] make format --- cmd/dmsgweb/commands/dmsgweb.go | 99 ++++++++++++++++----------------- 1 file changed, 47 insertions(+), 52 deletions(-) diff --git a/cmd/dmsgweb/commands/dmsgweb.go b/cmd/dmsgweb/commands/dmsgweb.go index 3502bd38..0d30c1ae 100644 --- a/cmd/dmsgweb/commands/dmsgweb.go +++ b/cmd/dmsgweb/commands/dmsgweb.go @@ -49,7 +49,7 @@ func (r *customResolver) Resolve(ctx context.Context, name string) (context.Cont return ctx, nil, fmt.Errorf("failed to parse IP address") } // Modify the context to include the desired port - ctx = context.WithValue(ctx, "port", fmt.Sprintf("%v",webPort)) //nolint + ctx = context.WithValue(ctx, "port", fmt.Sprintf("%v", webPort)) //nolint return ctx, ip, nil } // Use default name resolution for other domains @@ -74,6 +74,7 @@ var ( ) const dmsgwebenvname = "DMSGWEB" + var dmsgwebconffile = os.Getenv(dmsgwebenvname) func init() { @@ -81,16 +82,16 @@ func init() { RootCmd.Flags().StringVarP(&filterDomainSuffix, "filter", "f", ".dmsg", "domain suffix to filter") RootCmd.Flags().UintVarP(&proxyPort, "socks", "q", scriptExecUint("${PROXYPORT:-4445}", dmsgwebconffile), "port to serve the socks5 proxy") RootCmd.Flags().StringVarP(&addProxy, "proxy", "r", scriptExecString("${ADDPROXY}", dmsgwebconffile), "configure additional socks5 proxy for dmsgweb (i.e. 127.0.0.1:1080)") - RootCmd.Flags().UintVarP(&webPort, "port", "p", scriptExecUint("${WEBPORT:-8080}",dmsgwebconffile), "port to serve the web application") - RootCmd.Flags().StringVarP(&resolveDmsgAddr, "resolve", "t", scriptExecString("${RESOLVEPK}",dmsgwebconffile), "resolve the specified dmsg address:port on the local port & disable proxy") + RootCmd.Flags().UintVarP(&webPort, "port", "p", scriptExecUint("${WEBPORT:-8080}", dmsgwebconffile), "port to serve the web application") + RootCmd.Flags().StringVarP(&resolveDmsgAddr, "resolve", "t", scriptExecString("${RESOLVEPK}", dmsgwebconffile), "resolve the specified dmsg address:port on the local port & disable proxy") RootCmd.Flags().StringVarP(&dmsgDisc, "dmsg-disc", "d", skyenv.DmsgDiscAddr, "dmsg discovery url") - RootCmd.Flags().IntVarP(&dmsgSessions, "sess", "e", scriptExecInt("${DMSGSESSIONS:-1}",dmsgwebconffile), "number of dmsg servers to connect to") + RootCmd.Flags().IntVarP(&dmsgSessions, "sess", "e", scriptExecInt("${DMSGSESSIONS:-1}", dmsgwebconffile), "number of dmsg servers to connect to") RootCmd.Flags().StringVarP(&logLvl, "loglvl", "l", "", "[ debug | warn | error | fatal | panic | trace | info ]\033[0m") if os.Getenv("DMSGWEB_SK") != "" { sk.Set(os.Getenv("DMSGWEB_SK")) //nolint } - if scriptExecString("${DMSGWEB_SK}",dmsgwebconffile) != "" { - sk.Set(scriptExecString("${DMSGWEB_SK}",dmsgwebconffile)) //nolint + if scriptExecString("${DMSGWEB_SK}", dmsgwebconffile) != "" { + sk.Set(scriptExecString("${DMSGWEB_SK}", dmsgwebconffile)) //nolint } RootCmd.Flags().VarP(&sk, "sk", "s", "a random key is generated if unspecified\n\r") RootCmd.Flags().BoolVarP(&isEnvs, "envs", "z", false, "show example .conf file") @@ -195,7 +196,7 @@ dmsgweb conf file detected: ` + dmsgwebconffile if match { port, ok := ctx.Value("port").(string) if !ok { - port = fmt.Sprintf("%v",webPort) + port = fmt.Sprintf("%v", webPort) } addr = "localhost:" + port } else { @@ -296,7 +297,7 @@ dmsgweb conf file detected: ` + dmsgwebconffile wg.Add(1) go func() { dmsgWebLog.Debug(fmt.Sprintf("Serving http on: http://127.0.0.1:%v", webPort)) - r.Run(":" + fmt.Sprintf("%v",webPort)) //nolint + r.Run(":" + fmt.Sprintf("%v", webPort)) //nolint dmsgWebLog.Debug(fmt.Sprintf("Stopped serving http on: http://127.0.0.1:%v", webPort)) wg.Done() }() @@ -304,23 +305,21 @@ dmsgweb conf file detected: ` + dmsgwebconffile }, } - - var ( - startTime = time.Now() - runTime time.Duration - dmsgPort uint - dmsgSess int - wl string - wlkeys []cipher.PubKey - localPort uint + startTime = time.Now() + runTime time.Duration + dmsgPort uint + dmsgSess int + wl string + wlkeys []cipher.PubKey + localPort uint websrvPort uint - err error + err error ) const dmsgwebsrvenvname = "DMSGWEBSRV" -var dmsgwebsrvconffile = os.Getenv(dmsgwebsrvenvname) +var dmsgwebsrvconffile = os.Getenv(dmsgwebsrvenvname) func init() { RootCmd.AddCommand(srvCmd) @@ -330,8 +329,12 @@ func init() { srvCmd.Flags().StringVarP(&wl, "wl", "w", scriptExecArray("${WHITELISTPKS[@]}", dmsgwebsrvconffile), "whitelisted keys for dmsg authenticated routes\r") srvCmd.Flags().StringVarP(&dmsgDisc, "dmsg-disc", "D", skyenv.DmsgDiscAddr, "dmsg discovery url") srvCmd.Flags().IntVarP(&dmsgSess, "dsess", "e", scriptExecInt("${DMSGSESSIONS:-1}", dmsgwebsrvconffile), "dmsg sessions") - if os.Getenv("DMSGWEBSRV_SK") != "" { sk.Set(os.Getenv("DMSGWEBSRV_SK")) } //nolint - if scriptExecString("${DMSGWEBSRV_SK}", dmsgwebsrvconffile) != "" { sk.Set(scriptExecString("${DMSGWEBSRV_SK}", dmsgwebsrvconffile)) } //nolint + if os.Getenv("DMSGWEBSRV_SK") != "" { + sk.Set(os.Getenv("DMSGWEBSRV_SK")) + } //nolint + if scriptExecString("${DMSGWEBSRV_SK}", dmsgwebsrvconffile) != "" { + sk.Set(scriptExecString("${DMSGWEBSRV_SK}", dmsgwebsrvconffile)) + } //nolint pk, _ = sk.PubKey() srvCmd.Flags().VarP(&sk, "sk", "s", "a random key is generated if unspecified\n\r") srvCmd.Flags().BoolVarP(&isEnvs, "envs", "z", false, "show example .conf file") @@ -339,19 +342,18 @@ func init() { srvCmd.CompletionOptions.DisableDefaultCmd = true } - var srvCmd = &cobra.Command{ Use: "srv", Short: "serve http from local port over dmsg", Long: `DMSG web server - serve http interface from local port over dmsg` + func() string { - if _, err := os.Stat(dmsgwebsrvconffile); err == nil { - return ` + if _, err := os.Stat(dmsgwebsrvconffile); err == nil { + return ` dmsgvlcenv file detected: ` + dmsgwebsrvconffile - } - return `dmsg streaming media with vlc + } + return `dmsg streaming media with vlc .conf file may also be specified with - `+dmsgwebsrvenvname+`=/path/to/dmsgwebsrv.conf skywire dmsg web srv` + ` + dmsgwebsrvenvname + `=/path/to/dmsgwebsrv.conf skywire dmsg web srv` }(), Run: func(_ *cobra.Command, _ []string) { if isEnvs { @@ -371,7 +373,6 @@ var srvCmd = &cobra.Command{ } Server() }, - } func Server() { @@ -430,7 +431,6 @@ func Server() { } }() - r1 := gin.New() r1.Use(gin.Recovery()) r1.Use(loggingMiddleware()) @@ -440,26 +440,24 @@ func Server() { authRoute.Use(whitelistAuth(wlkeys)) } authRoute.Any("/*path", func(c *gin.Context) { - targetURL, _ := url.Parse(fmt.Sprintf("http://127.0.0.1:%v%s?%s", localPort, c.Request.URL.Path, c.Request.URL.RawQuery)) - proxy := httputil.ReverseProxy{ - Director: func(req *http.Request) { - req.URL = targetURL - req.Host = targetURL.Host - req.Method = c.Request.Method - }, - Transport: &http.Transport{}, - } - proxy.ServeHTTP(c.Writer, c.Request) + targetURL, _ := url.Parse(fmt.Sprintf("http://127.0.0.1:%v%s?%s", localPort, c.Request.URL.Path, c.Request.URL.RawQuery)) + proxy := httputil.ReverseProxy{ + Director: func(req *http.Request) { + req.URL = targetURL + req.Host = targetURL.Host + req.Method = c.Request.Method + }, + Transport: &http.Transport{}, + } + proxy.ServeHTTP(c.Writer, c.Request) }) - - -serve := &http.Server{ - Handler: &GinHandler{Router: r1}, - ReadHeaderTimeout: 5 * time.Second, - ReadTimeout: 10 * time.Second, - WriteTimeout: 10 * time.Second, -} + serve := &http.Server{ + Handler: &GinHandler{Router: r1}, + ReadHeaderTimeout: 5 * time.Second, + ReadTimeout: 10 * time.Second, + WriteTimeout: 10 * time.Second, + } wg := new(sync.WaitGroup) wg.Add(1) @@ -481,7 +479,6 @@ serve := &http.Server{ wg.Wait() } - func whitelistAuth(whitelistedPKs []cipher.PubKey) gin.HandlerFunc { return func(c *gin.Context) { remotePK, _, err := net.SplitHostPort(c.Request.RemoteAddr) @@ -513,16 +510,14 @@ func whitelistAuth(whitelistedPKs []cipher.PubKey) gin.HandlerFunc { } } - type GinHandler struct { -Router *gin.Engine + Router *gin.Engine } func (h *GinHandler) ServeHTTP(w http.ResponseWriter, r *http.Request) { -h.Router.ServeHTTP(w, r) + h.Router.ServeHTTP(w, r) } - func startDmsg(ctx context.Context, pk cipher.PubKey, sk cipher.SecKey) (dmsgC *dmsg.Client, stop func(), err error) { dmsgC = dmsg.NewClient(pk, sk, disc.NewHTTP(dmsgDisc, &http.Client{}, dmsgWebLog), &dmsg.Config{MinSessions: dmsgSessions}) go dmsgC.Serve(context.Background()) From eb7f4fa2e3152e83dc1abd1c8f6efa8e55f3427c Mon Sep 17 00:00:00 2001 From: Moses Narrow Date: Mon, 20 May 2024 12:59:33 -0500 Subject: [PATCH 09/10] fix text on help menu --- cmd/dmsgweb/commands/dmsgweb.go | 7 +++---- 1 file changed, 3 insertions(+), 4 deletions(-) diff --git a/cmd/dmsgweb/commands/dmsgweb.go b/cmd/dmsgweb/commands/dmsgweb.go index 0d30c1ae..b97363f9 100644 --- a/cmd/dmsgweb/commands/dmsgweb.go +++ b/cmd/dmsgweb/commands/dmsgweb.go @@ -348,10 +348,9 @@ var srvCmd = &cobra.Command{ Long: `DMSG web server - serve http interface from local port over dmsg` + func() string { if _, err := os.Stat(dmsgwebsrvconffile); err == nil { return ` - dmsgvlcenv file detected: ` + dmsgwebsrvconffile + dmsenv file detected: ` + dmsgwebsrvconffile } - return `dmsg streaming media with vlc - + return ` .conf file may also be specified with ` + dmsgwebsrvenvname + `=/path/to/dmsgwebsrv.conf skywire dmsg web srv` }(), @@ -376,7 +375,7 @@ var srvCmd = &cobra.Command{ } func Server() { - log := logging.MustGetLogger("dmsgvlc") + log := logging.MustGetLogger("dmsgwebsrv") ctx, cancel := cmdutil.SignalContext(context.Background(), log) From 0984ec458d51b968081488ea40fa1b48c559c061 Mon Sep 17 00:00:00 2001 From: Moses Narrow Date: Mon, 20 May 2024 13:10:01 -0500 Subject: [PATCH 10/10] fix ci errors --- cmd/dmsgweb/commands/dmsgweb.go | 44 ++++++++++++++++----------------- 1 file changed, 21 insertions(+), 23 deletions(-) diff --git a/cmd/dmsgweb/commands/dmsgweb.go b/cmd/dmsgweb/commands/dmsgweb.go index b97363f9..fc79bb48 100644 --- a/cmd/dmsgweb/commands/dmsgweb.go +++ b/cmd/dmsgweb/commands/dmsgweb.go @@ -126,9 +126,9 @@ dmsgweb conf file detected: ` + dmsgwebconffile if isEnvs { envfile := envfileLinux if runtime.GOOS == "windows" { - envfileslice, _ := script.Echo(envfile).Slice() - for i, _ := range envfileslice { - efs, _ := script.Echo(envfileslice[i]).Reject("##").Reject("#-").Reject("# ").Replace("#", "#$").String() + envfileslice, _ := script.Echo(envfile).Slice() //nolint + for i := range envfileslice { + efs, _ := script.Echo(envfileslice[i]).Reject("##").Reject("#-").Reject("# ").Replace("#", "#$").String() //nolint if efs != "" && efs != "\n" { envfileslice[i] = strings.ReplaceAll(efs, "\n", "") } @@ -306,8 +306,6 @@ dmsgweb conf file detected: ` + dmsgwebconffile } var ( - startTime = time.Now() - runTime time.Duration dmsgPort uint dmsgSess int wl string @@ -330,12 +328,12 @@ func init() { srvCmd.Flags().StringVarP(&dmsgDisc, "dmsg-disc", "D", skyenv.DmsgDiscAddr, "dmsg discovery url") srvCmd.Flags().IntVarP(&dmsgSess, "dsess", "e", scriptExecInt("${DMSGSESSIONS:-1}", dmsgwebsrvconffile), "dmsg sessions") if os.Getenv("DMSGWEBSRV_SK") != "" { - sk.Set(os.Getenv("DMSGWEBSRV_SK")) - } //nolint + sk.Set(os.Getenv("DMSGWEBSRV_SK")) //nolint + } if scriptExecString("${DMSGWEBSRV_SK}", dmsgwebsrvconffile) != "" { - sk.Set(scriptExecString("${DMSGWEBSRV_SK}", dmsgwebsrvconffile)) - } //nolint - pk, _ = sk.PubKey() + sk.Set(scriptExecString("${DMSGWEBSRV_SK}", dmsgwebsrvconffile)) //nolint + } + pk, _ = sk.PubKey() //nolint srvCmd.Flags().VarP(&sk, "sk", "s", "a random key is generated if unspecified\n\r") srvCmd.Flags().BoolVarP(&isEnvs, "envs", "z", false, "show example .conf file") @@ -356,11 +354,11 @@ var srvCmd = &cobra.Command{ }(), Run: func(_ *cobra.Command, _ []string) { if isEnvs { - envfile := envfileLinux + envfile := srvenvfileLinux if runtime.GOOS == "windows" { - envfileslice, _ := script.Echo(envfile).Slice() - for i, _ := range envfileslice { - efs, _ := script.Echo(envfileslice[i]).Reject("##").Reject("#-").Reject("# ").Replace("#", "#$").String() + envfileslice, _ := script.Echo(envfile).Slice() //nolint + for i := range envfileslice { + efs, _ := script.Echo(envfileslice[i]).Reject("##").Reject("#-").Reject("# ").Replace("#", "#$").String() //nolint if efs != "" && efs != "\n" { envfileslice[i] = strings.ReplaceAll(efs, "\n", "") } @@ -370,11 +368,11 @@ var srvCmd = &cobra.Command{ fmt.Println(envfile) os.Exit(0) } - Server() + server() }, } -func Server() { +func server() { log := logging.MustGetLogger("dmsgwebsrv") ctx, cancel := cmdutil.SignalContext(context.Background(), log) @@ -439,7 +437,7 @@ func Server() { authRoute.Use(whitelistAuth(wlkeys)) } authRoute.Any("/*path", func(c *gin.Context) { - targetURL, _ := url.Parse(fmt.Sprintf("http://127.0.0.1:%v%s?%s", localPort, c.Request.URL.Path, c.Request.URL.RawQuery)) + targetURL, _ := url.Parse(fmt.Sprintf("http://127.0.0.1:%v%s?%s", localPort, c.Request.URL.Path, c.Request.URL.RawQuery)) //nolint proxy := httputil.ReverseProxy{ Director: func(req *http.Request) { req.URL = targetURL @@ -452,7 +450,7 @@ func Server() { }) serve := &http.Server{ - Handler: &GinHandler{Router: r1}, + Handler: &ginHandler{Router: r1}, ReadHeaderTimeout: 5 * time.Second, ReadTimeout: 10 * time.Second, WriteTimeout: 10 * time.Second, @@ -471,7 +469,7 @@ func Server() { wg.Add(1) go func() { fmt.Printf("listening on http://127.0.0.1:%d using gin router\n", websrvPort) - r1.Run(fmt.Sprintf(":%d", websrvPort)) + r1.Run(fmt.Sprintf(":%d", websrvPort)) //nolint wg.Done() }() @@ -483,7 +481,7 @@ func whitelistAuth(whitelistedPKs []cipher.PubKey) gin.HandlerFunc { remotePK, _, err := net.SplitHostPort(c.Request.RemoteAddr) if err != nil { c.Writer.WriteHeader(http.StatusInternalServerError) - c.Writer.Write([]byte("500 Internal Server Error")) + c.Writer.Write([]byte("500 Internal Server Error")) //nolint c.AbortWithStatus(http.StatusInternalServerError) return } @@ -502,18 +500,18 @@ func whitelistAuth(whitelistedPKs []cipher.PubKey) gin.HandlerFunc { c.Next() } else { c.Writer.WriteHeader(http.StatusUnauthorized) - c.Writer.Write([]byte("401 Unauthorized")) + c.Writer.Write([]byte("401 Unauthorized")) //nolint c.AbortWithStatus(http.StatusUnauthorized) return } } } -type GinHandler struct { +type ginHandler struct { Router *gin.Engine } -func (h *GinHandler) ServeHTTP(w http.ResponseWriter, r *http.Request) { +func (h *ginHandler) ServeHTTP(w http.ResponseWriter, r *http.Request) { h.Router.ServeHTTP(w, r) }