From e27257daf6b29708904ff2bbc26000285cf463fb Mon Sep 17 00:00:00 2001 From: Michael Quigley Date: Tue, 13 Dec 2022 12:51:04 -0500 Subject: [PATCH] back share public web backend (#95) --- cmd/zrok/share_private.go | 10 +-- cmd/zrok/share_public.go | 66 ++++++++++++++----- cmd/zrok/share_reserved.go | 6 +- endpoints/{backend => proxy_backend}/http.go | 12 ++-- .../{backend => proxy_backend}/metricsconn.go | 2 +- endpoints/web_backend/web.go | 54 +++++++++++++++ 6 files changed, 119 insertions(+), 31 deletions(-) rename endpoints/{backend => proxy_backend}/http.go (91%) rename endpoints/{backend => proxy_backend}/metricsconn.go (97%) create mode 100644 endpoints/web_backend/web.go diff --git a/cmd/zrok/share_private.go b/cmd/zrok/share_private.go index 49e3e1a2..cc903cf7 100644 --- a/cmd/zrok/share_private.go +++ b/cmd/zrok/share_private.go @@ -5,7 +5,7 @@ import ( ui "github.com/gizak/termui/v3" "github.com/go-openapi/runtime" httptransport "github.com/go-openapi/runtime/client" - "github.com/openziti-test-kitchen/zrok/endpoints/backend" + "github.com/openziti-test-kitchen/zrok/endpoints/proxy_backend" "github.com/openziti-test-kitchen/zrok/model" "github.com/openziti-test-kitchen/zrok/rest_client_zrok" "github.com/openziti-test-kitchen/zrok/rest_client_zrok/service" @@ -80,7 +80,7 @@ func (cmd *sharePrivateCommand) run(_ *cobra.Command, args []string) { } panic(err) } - cfg := &backend.Config{ + cfg := &proxy_backend.Config{ IdentityPath: zif, EndpointAddress: target, } @@ -155,8 +155,8 @@ func (cmd *sharePrivateCommand) run(_ *cobra.Command, args []string) { } } -func (cmd *sharePrivateCommand) proxyBackendMode(cfg *backend.Config) (backendHandler, error) { - httpProxy, err := backend.NewHTTP(cfg) +func (cmd *sharePrivateCommand) proxyBackendMode(cfg *proxy_backend.Config) (backendHandler, error) { + httpProxy, err := proxy_backend.NewBackend(cfg) if err != nil { return nil, errors.Wrap(err, "error creating http proxy backend") } @@ -170,7 +170,7 @@ func (cmd *sharePrivateCommand) proxyBackendMode(cfg *backend.Config) (backendHa return httpProxy, nil } -func (cmd *sharePrivateCommand) destroy(id string, cfg *backend.Config, zrok *rest_client_zrok.Zrok, auth runtime.ClientAuthInfoWriter) { +func (cmd *sharePrivateCommand) destroy(id string, cfg *proxy_backend.Config, zrok *rest_client_zrok.Zrok, auth runtime.ClientAuthInfoWriter) { logrus.Debugf("shutting down '%v'", cfg.Service) req := service.NewUnshareParams() req.Body = &rest_model_zrok.UnshareRequest{ diff --git a/cmd/zrok/share_public.go b/cmd/zrok/share_public.go index 906c98f7..d2f61d64 100644 --- a/cmd/zrok/share_public.go +++ b/cmd/zrok/share_public.go @@ -7,7 +7,8 @@ import ( "github.com/go-openapi/runtime" httptransport "github.com/go-openapi/runtime/client" tb "github.com/nsf/termbox-go" - "github.com/openziti-test-kitchen/zrok/endpoints/backend" + "github.com/openziti-test-kitchen/zrok/endpoints/proxy_backend" + "github.com/openziti-test-kitchen/zrok/endpoints/web_backend" "github.com/openziti-test-kitchen/zrok/model" "github.com/openziti-test-kitchen/zrok/rest_client_zrok" "github.com/openziti-test-kitchen/zrok/rest_client_zrok/service" @@ -68,6 +69,9 @@ func (cmd *sharePublicCommand) run(_ *cobra.Command, args []string) { } target = targetEndpoint.String() + case "web": + target = args[0] + default: showError(fmt.Sprintf("invalid backend mode '%v'; expected {proxy, web}", cmd.backendMode), nil) } @@ -99,10 +103,6 @@ func (cmd *sharePublicCommand) run(_ *cobra.Command, args []string) { } panic(err) } - cfg := &backend.Config{ - IdentityPath: zif, - EndpointAddress: target, - } zrok, err := zrokdir.ZrokClient(env.ApiEndpoint) if err != nil { @@ -119,7 +119,7 @@ func (cmd *sharePublicCommand) run(_ *cobra.Command, args []string) { ShareMode: "public", FrontendSelection: cmd.frontendSelection, BackendMode: "proxy", - BackendProxyEndpoint: cfg.EndpointAddress, + BackendProxyEndpoint: target, AuthScheme: string(model.None), } if len(cmd.basicAuth) > 0 { @@ -142,19 +142,23 @@ func (cmd *sharePublicCommand) run(_ *cobra.Command, args []string) { } panic(err) } - cfg.Service = resp.Payload.SvcToken c := make(chan os.Signal) signal.Notify(c, os.Interrupt, syscall.SIGTERM) go func() { <-c - cmd.destroy(env.ZId, cfg, zrok, auth) + cmd.destroy(env.ZId, resp.Payload.SvcToken, zrok, auth) os.Exit(0) }() var bh backendHandler switch cmd.backendMode { case "proxy": + cfg := &proxy_backend.Config{ + IdentityPath: zif, + EndpointAddress: target, + Service: resp.Payload.SvcToken, + } bh, err = cmd.proxyBackendMode(cfg) if err != nil { ui.Close() @@ -164,6 +168,21 @@ func (cmd *sharePublicCommand) run(_ *cobra.Command, args []string) { panic(err) } + case "web": + cfg := &web_backend.Config{ + IdentityPath: zif, + WebRoot: target, + Service: resp.Payload.SvcToken, + } + bh, err = cmd.webBackendMode(cfg) + if err != nil { + ui.Close() + if !panicInstead { + showError("unable to create web backend handler", err) + } + panic(err) + } + default: ui.Close() showError("invalid backend mode", nil) @@ -210,7 +229,7 @@ func (cmd *sharePublicCommand) run(_ *cobra.Command, args []string) { switch e.ID { case "q", "": ui.Close() - cmd.destroy(env.ZId, cfg, zrok, auth) + cmd.destroy(env.ZId, resp.Payload.SvcToken, zrok, auth) os.Exit(0) } } @@ -237,27 +256,42 @@ func (cmd *sharePublicCommand) run(_ *cobra.Command, args []string) { } } -func (cmd *sharePublicCommand) proxyBackendMode(cfg *backend.Config) (backendHandler, error) { - httpProxy, err := backend.NewHTTP(cfg) +func (cmd *sharePublicCommand) proxyBackendMode(cfg *proxy_backend.Config) (backendHandler, error) { + be, err := proxy_backend.NewBackend(cfg) if err != nil { return nil, errors.Wrap(err, "error creating http proxy backend") } go func() { - if err := httpProxy.Run(); err != nil { + if err := be.Run(); err != nil { logrus.Errorf("error running http proxy backend: %v", err) } }() - return httpProxy, nil + return be, nil } -func (cmd *sharePublicCommand) destroy(id string, cfg *backend.Config, zrok *rest_client_zrok.Zrok, auth runtime.ClientAuthInfoWriter) { - logrus.Debugf("shutting down '%v'", cfg.Service) +func (cmd *sharePublicCommand) webBackendMode(cfg *web_backend.Config) (backendHandler, error) { + be, err := web_backend.NewBackend(cfg) + if err != nil { + return nil, errors.Wrap(err, "error creating http web backend") + } + + go func() { + if err := be.Run(); err != nil { + logrus.Errorf("error running http web backend: %v", err) + } + }() + + return be, nil +} + +func (cmd *sharePublicCommand) destroy(id string, svcToken string, zrok *rest_client_zrok.Zrok, auth runtime.ClientAuthInfoWriter) { + logrus.Debugf("shutting down '%v'", svcToken) req := service.NewUnshareParams() req.Body = &rest_model_zrok.UnshareRequest{ EnvZID: id, - SvcToken: cfg.Service, + SvcToken: svcToken, } if _, err := zrok.Service.Unshare(req, auth); err == nil { logrus.Debugf("shutdown complete") diff --git a/cmd/zrok/share_reserved.go b/cmd/zrok/share_reserved.go index f49c9fc1..bd39b19d 100644 --- a/cmd/zrok/share_reserved.go +++ b/cmd/zrok/share_reserved.go @@ -3,7 +3,7 @@ package main import ( ui "github.com/gizak/termui/v3" httptransport "github.com/go-openapi/runtime/client" - "github.com/openziti-test-kitchen/zrok/endpoints/backend" + "github.com/openziti-test-kitchen/zrok/endpoints/proxy_backend" "github.com/openziti-test-kitchen/zrok/rest_client_zrok/service" "github.com/openziti-test-kitchen/zrok/rest_model_zrok" "github.com/openziti-test-kitchen/zrok/zrokdir" @@ -91,7 +91,7 @@ func (cmd *shareReservedCommand) run(_ *cobra.Command, args []string) { } panic(err) } - cfg := &backend.Config{ + cfg := &proxy_backend.Config{ IdentityPath: zif, EndpointAddress: targetEndpoint, Service: svcToken, @@ -115,7 +115,7 @@ func (cmd *shareReservedCommand) run(_ *cobra.Command, args []string) { logrus.Infof("using existing backend proxy endpoint: %v", targetEndpoint) } - httpProxy, err := backend.NewHTTP(cfg) + httpProxy, err := proxy_backend.NewBackend(cfg) if err != nil { ui.Close() if !panicInstead { diff --git a/endpoints/backend/http.go b/endpoints/proxy_backend/http.go similarity index 91% rename from endpoints/backend/http.go rename to endpoints/proxy_backend/http.go index c5e87908..46b44959 100644 --- a/endpoints/backend/http.go +++ b/endpoints/proxy_backend/http.go @@ -1,4 +1,4 @@ -package backend +package proxy_backend import ( "context" @@ -21,14 +21,14 @@ type Config struct { Service string } -type httpBind struct { +type backend struct { cfg *Config requests func() int32 listener edge.Listener handler http.Handler } -func NewHTTP(cfg *Config) (*httpBind, error) { +func NewBackend(cfg *Config) (*backend, error) { options := ziti.ListenOptions{ ConnectTimeout: 5 * time.Minute, MaxConnections: 64, @@ -48,7 +48,7 @@ func NewHTTP(cfg *Config) (*httpBind, error) { } handler := util.NewProxyHandler(proxy) - return &httpBind{ + return &backend{ cfg: cfg, requests: handler.Requests, listener: listener, @@ -56,14 +56,14 @@ func NewHTTP(cfg *Config) (*httpBind, error) { }, nil } -func (self *httpBind) Run() error { +func (self *backend) Run() error { if err := http.Serve(self.listener, self.handler); err != nil { return err } return nil } -func (self *httpBind) Requests() func() int32 { +func (self *backend) Requests() func() int32 { return self.requests } diff --git a/endpoints/backend/metricsconn.go b/endpoints/proxy_backend/metricsconn.go similarity index 97% rename from endpoints/backend/metricsconn.go rename to endpoints/proxy_backend/metricsconn.go index 66a3f661..d1768da0 100644 --- a/endpoints/backend/metricsconn.go +++ b/endpoints/proxy_backend/metricsconn.go @@ -1,4 +1,4 @@ -package backend +package proxy_backend import ( "net" diff --git a/endpoints/web_backend/web.go b/endpoints/web_backend/web.go new file mode 100644 index 00000000..43edb4ba --- /dev/null +++ b/endpoints/web_backend/web.go @@ -0,0 +1,54 @@ +package web_backend + +import ( + "github.com/openziti/sdk-golang/ziti" + "github.com/openziti/sdk-golang/ziti/config" + "github.com/openziti/sdk-golang/ziti/edge" + "github.com/pkg/errors" + "net/http" + "time" +) + +type Config struct { + IdentityPath string + WebRoot string + Service string +} + +type backend struct { + cfg *Config + listener edge.Listener + handler http.Handler +} + +func NewBackend(cfg *Config) (*backend, error) { + options := ziti.ListenOptions{ + ConnectTimeout: 5 * time.Minute, + MaxConnections: 64, + } + zcfg, err := config.NewFromFile(cfg.IdentityPath) + if err != nil { + return nil, errors.Wrap(err, "error loading config") + } + listener, err := ziti.NewContextWithConfig(zcfg).ListenWithOptions(cfg.Service, &options) + if err != nil { + return nil, errors.Wrap(err, "error listening") + } + + return &backend{ + cfg: cfg, + listener: listener, + handler: http.FileServer(http.Dir(cfg.WebRoot)), + }, nil +} + +func (self *backend) Run() error { + if err := http.Serve(self.listener, self.handler); err != nil { + return err + } + return nil +} + +func (self *backend) Requests() func() int32 { + return func() int32 { return 0 } +}