From f89e3d62392a3fb8d414fbea708b48574c7015e7 Mon Sep 17 00:00:00 2001 From: Gert Drapers <1533850+gertd@users.noreply.github.com> Date: Wed, 27 Nov 2024 16:32:09 -0800 Subject: [PATCH] upd connection validation --- go.mod | 8 -- go.sum | 12 --- .../template-no-tls/template-no-tls_test.go | 2 + pkg/app/tests/template/template_test.go | 2 + pkg/cli/cc/cc.go | 56 ++++++-------- pkg/cli/cc/health.go | 2 +- pkg/cli/clients/authorizer/client.go | 36 ++------- pkg/cli/clients/common/client.go | 11 --- pkg/cli/clients/config.go | 12 +++ pkg/cli/clients/directory/client.go | 36 ++------- pkg/cli/clients/validate.go | 74 +++++++++++++++++++ pkg/cli/cmd/directory/backup.go | 7 +- pkg/cli/cmd/directory/exporter.go | 7 +- pkg/cli/cmd/directory/importer.go | 6 +- pkg/cli/cmd/directory/manifest.go | 18 +++-- pkg/cli/cmd/directory/restore.go | 6 +- pkg/cli/cmd/templates/install.go | 12 +-- 17 files changed, 161 insertions(+), 146 deletions(-) delete mode 100644 pkg/cli/clients/common/client.go create mode 100644 pkg/cli/clients/config.go create mode 100644 pkg/cli/clients/validate.go diff --git a/go.mod b/go.mod index 555af02b..4b5130a2 100644 --- a/go.mod +++ b/go.mod @@ -29,7 +29,6 @@ require ( github.com/docker/docker v27.3.1+incompatible github.com/docker/go-connections v0.5.0 github.com/fatih/color v1.18.0 - github.com/fullstorydev/grpcurl v1.9.1 github.com/gdamore/tcell/v2 v2.7.4 github.com/go-http-utils/headers v0.0.0-20181008091004-fed159eddc2a github.com/google/uuid v1.6.0 @@ -79,12 +78,10 @@ require ( github.com/antlr4-go/antlr/v4 v4.13.1 // indirect github.com/aserto-dev/go-decision-logs v0.1.2 // indirect github.com/beorn7/perks v1.0.1 // indirect - github.com/bufbuild/protocompile v0.13.0 // indirect github.com/bufbuild/protovalidate-go v0.7.3 // indirect github.com/bytecodealliance/wasmtime-go/v3 v3.0.2 // indirect github.com/cenkalti/backoff/v4 v4.3.0 // indirect github.com/cespare/xxhash/v2 v2.3.0 // indirect - github.com/cncf/xds/go v0.0.0-20240905190251-b4127c9b8d78 // indirect github.com/containerd/containerd v1.7.23 // indirect github.com/containerd/errdefs v0.3.0 // indirect github.com/containerd/log v0.1.0 // indirect @@ -97,8 +94,6 @@ require ( github.com/distribution/reference v0.6.0 // indirect github.com/docker/go-units v0.5.0 // indirect github.com/dustin/go-humanize v1.0.1 // indirect - github.com/envoyproxy/go-control-plane v0.13.0 // indirect - github.com/envoyproxy/protoc-gen-validate v1.1.0 // indirect github.com/felixge/httpsnoop v1.0.4 // indirect github.com/fsnotify/fsnotify v1.7.0 // indirect github.com/gdamore/encoding v1.0.1 // indirect @@ -109,7 +104,6 @@ require ( github.com/gobwas/glob v0.2.3 // indirect github.com/goccy/go-json v0.10.3 // indirect github.com/gogo/protobuf v1.3.2 // indirect - github.com/golang/protobuf v1.5.4 // indirect github.com/google/cel-go v0.22.0 // indirect github.com/google/subcommands v1.2.0 // indirect github.com/gorilla/mux v1.8.1 // indirect @@ -119,7 +113,6 @@ require ( github.com/hashicorp/hcl v1.0.0 // indirect github.com/inconshreveable/mousetrap v1.1.0 // indirect github.com/itchyny/timefmt-go v0.1.6 // indirect - github.com/jhump/protoreflect v1.16.0 // indirect github.com/klauspost/compress v1.17.11 // indirect github.com/lestrrat-go/blackmagic v1.0.2 // indirect github.com/lestrrat-go/httpcc v1.0.1 // indirect @@ -151,7 +144,6 @@ require ( github.com/opencontainers/go-digest v1.0.0 // indirect github.com/panmari/cuckoofilter v1.0.6 // indirect github.com/pelletier/go-toml/v2 v2.2.3 // indirect - github.com/planetscale/vtprotobuf v0.6.1-0.20240319094008-0393e58bdf10 // indirect github.com/pmezard/go-difflib v1.0.1-0.20181226105442-5d4384ee4fb2 // indirect github.com/power-devops/perfstat v0.0.0-20240221224432-82ca36839d55 // indirect github.com/prometheus/client_model v0.6.1 // indirect diff --git a/go.sum b/go.sum index 6f516750..f86554aa 100644 --- a/go.sum +++ b/go.sum @@ -450,8 +450,6 @@ github.com/aserto-dev/self-decision-logger v0.0.9/go.mod h1:tJYUhVtj/LPcbQNgHj8V github.com/benbjohnson/clock v1.1.0/go.mod h1:J11/hYXuz8f4ySSvYwY0FKfm+ezbsZBKZxNJlLklBHA= github.com/beorn7/perks v1.0.1 h1:VlbKKnNfV8bJzeqoa4cOKqO6bYr3WgKZxO8Z16+hsOM= github.com/beorn7/perks v1.0.1/go.mod h1:G2ZrVWU2WbWT9wwq4/hrbKbnv/1ERSJQ0ibhJ6rlkpw= -github.com/bufbuild/protocompile v0.13.0 h1:6cwUB0Y2tSvmNxsbunwzmIto3xOlJOV7ALALuVOs92M= -github.com/bufbuild/protocompile v0.13.0/go.mod h1:dr++fGGeMPWHv7jPeT06ZKukm45NJscd7rUxQVzEKRk= github.com/bufbuild/protovalidate-go v0.7.3 h1:kKnoSueygR3xxppvuBpm9SEwIsP359MMRfMBGmRByPg= github.com/bufbuild/protovalidate-go v0.7.3/go.mod h1:CFv34wMqiBzAHdQ4q/tWYi9ILFYKuaC3/4zh6eqdUck= github.com/bytecodealliance/wasmtime-go/v3 v3.0.2 h1:3uZCA/BLTIu+DqCfguByNMJa2HVHpXvjfy0Dy7g6fuA= @@ -480,8 +478,6 @@ github.com/cncf/xds/go v0.0.0-20210805033703-aa0b78936158/go.mod h1:eXthEFrGJvWH github.com/cncf/xds/go v0.0.0-20210922020428-25de7278fc84/go.mod h1:eXthEFrGJvWHgFFCl3hGmgk+/aYT6PnTQLykKQRLhEs= github.com/cncf/xds/go v0.0.0-20211001041855-01bcc9b48dfe/go.mod h1:eXthEFrGJvWHgFFCl3hGmgk+/aYT6PnTQLykKQRLhEs= github.com/cncf/xds/go v0.0.0-20211011173535-cb28da3451f1/go.mod h1:eXthEFrGJvWHgFFCl3hGmgk+/aYT6PnTQLykKQRLhEs= -github.com/cncf/xds/go v0.0.0-20240905190251-b4127c9b8d78 h1:QVw89YDxXxEe+l8gU8ETbOasdwEV+avkR75ZzsVV9WI= -github.com/cncf/xds/go v0.0.0-20240905190251-b4127c9b8d78/go.mod h1:W+zGtBO5Y1IgJhy4+A9GOqVhqLpfZi+vwmdNXUehLA8= github.com/containerd/cgroups v1.1.0 h1:v8rEWFl6EoqHB+swVNjVoCJE8o3jX7e8nqBGPLaDFBM= github.com/containerd/cgroups/v3 v3.0.2 h1:f5WFqIVSgo5IZmtTT3qVBo6TzI1ON6sycSBKkymb9L0= github.com/containerd/cgroups/v3 v3.0.2/go.mod h1:JUgITrzdFqp42uI2ryGA+ge0ap/nxzYgkGmIcetmErE= @@ -537,8 +533,6 @@ github.com/envoyproxy/go-control-plane v0.9.9-0.20210217033140-668b12f5399d/go.m github.com/envoyproxy/go-control-plane v0.9.9-0.20210512163311-63b5d3c536b0/go.mod h1:hliV/p42l8fGbc6Y9bQ70uLwIvmJyVE5k4iMKlh8wCQ= github.com/envoyproxy/go-control-plane v0.9.10-0.20210907150352-cf90f659a021/go.mod h1:AFq3mo9L8Lqqiid3OhADV3RfLJnjiw63cSpi+fDTRC0= github.com/envoyproxy/go-control-plane v0.10.2-0.20220325020618-49ff273808a1/go.mod h1:KJwIaB5Mv44NWtYuAOFCVOjcI94vtpEz2JU/D2v6IjE= -github.com/envoyproxy/go-control-plane v0.13.0 h1:HzkeUz1Knt+3bK+8LG1bxOO/jzWZmdxpwC51i202les= -github.com/envoyproxy/go-control-plane v0.13.0/go.mod h1:GRaKG3dwvFoTg4nj7aXdZnvMg4d7nvT/wl9WgVXn3Q8= github.com/envoyproxy/protoc-gen-validate v0.1.0/go.mod h1:iSmxcyjqTsJpI2R4NaDN7+kN2VEUnK/pcBlmesArF7c= github.com/envoyproxy/protoc-gen-validate v1.1.0 h1:tntQDh69XqOCOZsDz0lVJQez/2L6Uu2PdjCQwWCJ3bM= github.com/envoyproxy/protoc-gen-validate v1.1.0/go.mod h1:sXRDRVmzEbkM7CVcM06s9shE/m23dg3wzjl0UWqJ2q4= @@ -554,8 +548,6 @@ github.com/frankban/quicktest v1.14.6 h1:7Xjx+VpznH+oBnejlPUj8oUpdxnVs4f8XU8WnHk github.com/frankban/quicktest v1.14.6/go.mod h1:4ptaffx2x8+WTWXmUCuVU6aPUX1/Mz7zb5vbUoiM6w0= github.com/fsnotify/fsnotify v1.7.0 h1:8JEhPFa5W2WU7YfeZzPNqzMP6Lwt7L2715Ggo0nosvA= github.com/fsnotify/fsnotify v1.7.0/go.mod h1:40Bi/Hjc2AVfZrqy+aj+yEI+/bRxZnMJyTJwOpGvigM= -github.com/fullstorydev/grpcurl v1.9.1 h1:YxX1aCcCc4SDBQfj9uoWcTLe8t4NWrZe1y+mk83BQgo= -github.com/fullstorydev/grpcurl v1.9.1/go.mod h1:i8gKLIC6s93WdU3LSmkE5vtsCxyRmihUj5FK1cNW5EM= github.com/gdamore/encoding v1.0.0/go.mod h1:alR0ol34c49FCSBLjhosxzcPHQbf2trDkoo5dl+VrEg= github.com/gdamore/encoding v1.0.1 h1:YzKZckdBL6jVt2Gc+5p82qhrGiqMdG/eNs6Wy0u3Uhw= github.com/gdamore/encoding v1.0.1/go.mod h1:0Z0cMFinngz9kS1QfMjCP8TY7em3bZYeeklsSDPivEo= @@ -722,8 +714,6 @@ github.com/itchyny/gojq v0.12.16 h1:yLfgLxhIr/6sJNVmYfQjTIv0jGctu6/DgDoivmxTr7g= github.com/itchyny/gojq v0.12.16/go.mod h1:6abHbdC2uB9ogMS38XsErnfqJ94UlngIJGlRAIj4jTM= github.com/itchyny/timefmt-go v0.1.6 h1:ia3s54iciXDdzWzwaVKXZPbiXzxxnv1SPGFfM/myJ5Q= github.com/itchyny/timefmt-go v0.1.6/go.mod h1:RRDZYC5s9ErkjQvTvvU7keJjxUYzIISJGxm9/mAERQg= -github.com/jhump/protoreflect v1.16.0 h1:54fZg+49widqXYQ0b+usAFHbMkBGR4PpXrsHc8+TBDg= -github.com/jhump/protoreflect v1.16.0/go.mod h1:oYPd7nPvcBw/5wlDfm/AVmU9zH9BgqGCI469pGxfj/8= github.com/jstemmer/go-junit-report v0.0.0-20190106144839-af01ea7f8024/go.mod h1:6v2b51hI/fHJwM22ozAgKL4VKDeJcHhJFhtBdhmNjmU= github.com/jstemmer/go-junit-report v0.9.1/go.mod h1:Brl9GWCQeLvo8nXZwPNNblvFj/XSXhF0NWZEnDohbsk= github.com/kisielk/errcheck v1.5.0/go.mod h1:pFxgyoBC7bSaBwPgfKdkLd5X25qrDl4LWUI2bnpBCr8= @@ -833,8 +823,6 @@ github.com/pelletier/go-toml/v2 v2.2.3/go.mod h1:MfCQTFTvCcUyyvvwm1+G6H/jORL20Xl github.com/pkg/errors v0.8.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0= github.com/pkg/errors v0.9.1 h1:FEBLx1zS214owpjy7qsBeixbURkuhQAwrK5UwLGTwt4= github.com/pkg/errors v0.9.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0= -github.com/planetscale/vtprotobuf v0.6.1-0.20240319094008-0393e58bdf10 h1:GFCKgmp0tecUJ0sJuv4pzYCqS9+RGSn52M3FUwPs+uo= -github.com/planetscale/vtprotobuf v0.6.1-0.20240319094008-0393e58bdf10/go.mod h1:t/avpk3KcrXxUnYOhZhMXJlSEyie6gQbtLq5NM3loB8= github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4= github.com/pmezard/go-difflib v1.0.1-0.20181226105442-5d4384ee4fb2 h1:Jamvg5psRIccs7FGNTlIRMkT8wgtp5eCXdBlqhYGL6U= github.com/pmezard/go-difflib v1.0.1-0.20181226105442-5d4384ee4fb2/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4= diff --git a/pkg/app/tests/template-no-tls/template-no-tls_test.go b/pkg/app/tests/template-no-tls/template-no-tls_test.go index 10723dcd..e1d9ca04 100644 --- a/pkg/app/tests/template-no-tls/template-no-tls_test.go +++ b/pkg/app/tests/template-no-tls/template-no-tls_test.go @@ -92,12 +92,14 @@ func TestTemplateNoTLS(t *testing.T) { Host: addr, Insecure: false, Plaintext: true, + Timeout: 10 * time.Second, } azConfig := &azc.Config{ Host: addr, Insecure: false, Plaintext: true, + Timeout: 10 * time.Second, } for _, tmpl := range tcs { diff --git a/pkg/app/tests/template/template_test.go b/pkg/app/tests/template/template_test.go index a39a1979..97c97906 100644 --- a/pkg/app/tests/template/template_test.go +++ b/pkg/app/tests/template/template_test.go @@ -92,12 +92,14 @@ func TestTemplate(t *testing.T) { Host: addr, Insecure: true, Plaintext: false, + Timeout: 10 * time.Second, } azConfig := &azc.Config{ Host: addr, Insecure: true, Plaintext: false, + Timeout: 10 * time.Second, } for _, tmpl := range tcs { diff --git a/pkg/cli/cc/cc.go b/pkg/cli/cc/cc.go index 06e19f46..e1a2a2bb 100644 --- a/pkg/cli/cc/cc.go +++ b/pkg/cli/cc/cc.go @@ -8,25 +8,17 @@ import ( "os" "path/filepath" "sync" - "time" - client "github.com/aserto-dev/go-aserto" "github.com/aserto-dev/topaz/pkg/cli/cc/iostream" "github.com/aserto-dev/topaz/pkg/cli/dockerx" - "github.com/aserto-dev/topaz/pkg/version" "github.com/docker/docker/api/types" - "github.com/fullstorydev/grpcurl" "github.com/pkg/errors" "github.com/samber/lo" - "google.golang.org/grpc" - "google.golang.org/grpc/credentials" - "google.golang.org/grpc/credentials/insecure" ) var ( ErrNotRunning = errors.New("topaz is not running, use 'topaz start' or 'topaz run' to start") ErrIsRunning = errors.New("topaz is already running, use 'topaz stop' to stop") - ErrNotServing = errors.New("topaz gRPC endpoint not SERVING") ) type CommonCtx struct { @@ -142,36 +134,36 @@ func (c *CommonCtx) GetRunningContainers() ([]*types.Container, error) { return topazContainers, nil } -func (c *CommonCtx) IsServing(cfg *client.Config) (bool, error) { - if c.Config.Defaults.NoCheck { - return true, nil - } +// func (c *CommonCtx) IsServing(cfg *client.Config) (bool, error) { +// if c.Config.Defaults.NoCheck { +// return true, nil +// } +// common.Validate(c.Context, ) +// var creds credentials.TransportCredentials - var creds credentials.TransportCredentials +// if cfg.Insecure { +// tlsConf, err := grpcurl.ClientTLSConfig(cfg.Insecure, "", "", "") +// if err != nil { +// return false, errors.Wrap(err, "failed to create TLS config") +// } +// creds = credentials.NewTLS(tlsConf) +// } - if cfg.Insecure { - tlsConf, err := grpcurl.ClientTLSConfig(cfg.Insecure, "", "", "") - if err != nil { - return false, errors.Wrap(err, "failed to create TLS config") - } - creds = credentials.NewTLS(tlsConf) - } +// opts := []grpc.DialOption{ +// grpc.WithUserAgent(version.UserAgent()), +// } - opts := []grpc.DialOption{ - grpc.WithUserAgent(version.UserAgent()), - } - - opts = append(opts, grpc.WithTransportCredentials(insecure.NewCredentials())) +// opts = append(opts, grpc.WithTransportCredentials(insecure.NewCredentials())) - ctx, cancel := context.WithTimeout(context.Background(), 30*time.Second) - defer cancel() +// ctx, cancel := context.WithTimeout(context.Background(), 30*time.Second) +// defer cancel() - if _, err := grpcurl.BlockingDial(ctx, "tcp", cfg.Address, creds, opts...); err != nil { - return false, err - } +// if _, err := grpcurl.BlockingDial(ctx, "tcp", cfg.Address, creds, opts...); err != nil { +// return false, err +// } - return true, nil -} +// return true, nil +// } func (c *CommonCtx) SaveContextConfig(configurationFile string) error { cliConfig := filepath.Join(GetTopazDir(), configurationFile) diff --git a/pkg/cli/cc/health.go b/pkg/cli/cc/health.go index e1908576..f7f548b3 100644 --- a/pkg/cli/cc/health.go +++ b/pkg/cli/cc/health.go @@ -30,7 +30,7 @@ func ServiceHealthStatus(ctx context.Context, cfg *client.Config, service string } if resp.GetStatus() != healthpb.HealthCheckResponse_SERVING { - return errors.Errorf("gRPC endpoint not SERVING") + return errors.Errorf("health service %q is %s", service, resp.GetStatus().String()) } return nil diff --git a/pkg/cli/clients/authorizer/client.go b/pkg/cli/clients/authorizer/client.go index 2d5814e5..99b4eabd 100644 --- a/pkg/cli/clients/authorizer/client.go +++ b/pkg/cli/clients/authorizer/client.go @@ -5,15 +5,12 @@ import ( "time" client "github.com/aserto-dev/go-aserto" - "github.com/fullstorydev/grpcurl" "github.com/pkg/errors" "google.golang.org/grpc" - "google.golang.org/grpc/credentials" - "google.golang.org/grpc/credentials/insecure" az2 "github.com/aserto-dev/go-authorizer/aserto/authorizer/v2" "github.com/aserto-dev/topaz/pkg/cli/cc" - "github.com/aserto-dev/topaz/pkg/version" + "github.com/aserto-dev/topaz/pkg/cli/clients" ) type Config struct { @@ -27,6 +24,8 @@ type Config struct { Timeout time.Duration `flag:"timeout" short:"T" default:"${timeout}" env:"TOPAZ_TIMEOUT" help:"command timeout"` } +var _ clients.Config = &Config{} + type Client struct { conn *grpc.ClientConn Authorizer az2.AuthorizerClient @@ -53,36 +52,13 @@ func (cfg *Config) Connect(ctx context.Context) (*grpc.ClientConn, error) { return nil, errors.Errorf("no host specified") } - if err := cfg.validate(ctx); err != nil { + if ok, err := clients.Validate(ctx, cfg); !ok { return nil, err } return cfg.ClientConfig().Connect() } -func (cfg *Config) validate(ctx context.Context) error { - var creds credentials.TransportCredentials - if cfg.Insecure { - tlsConf, err := grpcurl.ClientTLSConfig(cfg.Insecure, "", "", "") - if err != nil { - return errors.Wrap(err, "failed to create TLS config") - } - creds = credentials.NewTLS(tlsConf) - } - - opts := []grpc.DialOption{ - grpc.WithUserAgent(version.UserAgent()), - } - - opts = append(opts, grpc.WithTransportCredentials(insecure.NewCredentials())) - - if _, err := grpcurl.BlockingDial(ctx, "tcp", cfg.Host, creds, opts...); err != nil { - return err - } - - return nil -} - func (cfg *Config) ClientConfig() *client.Config { return &client.Config{ Address: cfg.Host, @@ -94,3 +70,7 @@ func (cfg *Config) ClientConfig() *client.Config { Headers: cfg.Headers, } } + +func (cfg *Config) CommandTimeout() time.Duration { + return cfg.Timeout +} diff --git a/pkg/cli/clients/common/client.go b/pkg/cli/clients/common/client.go deleted file mode 100644 index c8e4cc22..00000000 --- a/pkg/cli/clients/common/client.go +++ /dev/null @@ -1,11 +0,0 @@ -package common - -import ( - "context" - - client "github.com/aserto-dev/go-aserto" -) - -func Validate(ctx context.Context, cfg *client.Config) (bool, error) { - return false, nil -} diff --git a/pkg/cli/clients/config.go b/pkg/cli/clients/config.go new file mode 100644 index 00000000..cb34f77f --- /dev/null +++ b/pkg/cli/clients/config.go @@ -0,0 +1,12 @@ +package clients + +import ( + "time" + + client "github.com/aserto-dev/go-aserto" +) + +type Config interface { + ClientConfig() *client.Config + CommandTimeout() time.Duration +} diff --git a/pkg/cli/clients/directory/client.go b/pkg/cli/clients/directory/client.go index b4504f5d..a43ef6ab 100644 --- a/pkg/cli/clients/directory/client.go +++ b/pkg/cli/clients/directory/client.go @@ -12,13 +12,10 @@ import ( dsr3 "github.com/aserto-dev/go-directory/aserto/directory/reader/v3" dsw3 "github.com/aserto-dev/go-directory/aserto/directory/writer/v3" "github.com/aserto-dev/topaz/pkg/cli/cc" - "github.com/aserto-dev/topaz/pkg/version" + "github.com/aserto-dev/topaz/pkg/cli/clients" - "github.com/fullstorydev/grpcurl" "github.com/pkg/errors" "google.golang.org/grpc" - "google.golang.org/grpc/credentials" - "google.golang.org/grpc/credentials/insecure" ) type Config struct { @@ -32,6 +29,8 @@ type Config struct { Timeout time.Duration `flag:"timeout" short:"T" default:"${timeout}" env:"TOPAZ_TIMEOUT" help:"command timeout"` } +var _ clients.Config = &Config{} + type Client struct { conn *grpc.ClientConn Model dsm3.ModelClient @@ -68,36 +67,13 @@ func (cfg *Config) Connect(ctx context.Context) (*grpc.ClientConn, error) { return nil, errors.Errorf("no host specified") } - if err := cfg.Validate(ctx); err != nil { + if ok, err := clients.Validate(ctx, cfg); !ok { return nil, err } return cfg.ClientConfig().Connect() } -func (cfg *Config) Validate(ctx context.Context) error { - var creds credentials.TransportCredentials - if cfg.Insecure { - tlsConf, err := grpcurl.ClientTLSConfig(cfg.Insecure, "", "", "") - if err != nil { - return errors.Wrap(err, "failed to create TLS config") - } - creds = credentials.NewTLS(tlsConf) - } - - opts := []grpc.DialOption{ - grpc.WithUserAgent(version.UserAgent()), - } - - opts = append(opts, grpc.WithTransportCredentials(insecure.NewCredentials())) - - if _, err := grpcurl.BlockingDial(ctx, "tcp", cfg.Host, creds, opts...); err != nil { - return err - } - - return nil -} - func (cfg *Config) ClientConfig() *client.Config { return &client.Config{ Address: cfg.Host, @@ -109,3 +85,7 @@ func (cfg *Config) ClientConfig() *client.Config { Headers: cfg.Headers, } } + +func (cfg *Config) CommandTimeout() time.Duration { + return cfg.Timeout +} diff --git a/pkg/cli/clients/validate.go b/pkg/cli/clients/validate.go new file mode 100644 index 00000000..35f1338e --- /dev/null +++ b/pkg/cli/clients/validate.go @@ -0,0 +1,74 @@ +package clients + +import ( + "context" + "io" + + client "github.com/aserto-dev/go-aserto" + "github.com/aserto-dev/topaz/pkg/version" + "github.com/pkg/errors" + "golang.org/x/sync/errgroup" + "google.golang.org/grpc" + "google.golang.org/grpc/codes" + "google.golang.org/grpc/reflection/grpc_reflection_v1" + "google.golang.org/grpc/status" +) + +func Validate(ctx context.Context, cfg Config) (bool, error) { + g, ctx := errgroup.WithContext(ctx) + ctx, cancel := context.WithTimeout(ctx, cfg.CommandTimeout()) + defer cancel() + + clientCfg := cfg.ClientConfig() + + conn, err := clientCfg.Connect( + client.WithDialOptions( + grpc.WithUserAgent(version.UserAgent()), + ), + ) + if err != nil { + return false, err + } + + callOpts := []grpc.CallOption{} + + refClient := grpc_reflection_v1.NewServerReflectionClient(conn) + stream, err := refClient.ServerReflectionInfo(ctx, callOpts...) + if err != nil { + if st, ok := status.FromError(err); ok { + return false, errors.Errorf("%s: %s", st.Code().String(), st.Message()) + } + return false, err + } + + g.Go(func() error { + in, err := stream.Recv() + if err == io.EOF { + return nil + } + + if err != nil { + return err + } + + if in.GetValidHost() == "" { + return status.Errorf(codes.Unavailable, "no valid host") + } + return nil + }) + + if err := stream.Send(&grpc_reflection_v1.ServerReflectionRequest{ + Host: clientCfg.Address, + MessageRequest: &grpc_reflection_v1.ServerReflectionRequest_ListServices{}, + }); err != nil { + return false, err + } + + _ = stream.CloseSend() + + if err := g.Wait(); err != nil { + return false, err + } + + return true, nil +} diff --git a/pkg/cli/cmd/directory/backup.go b/pkg/cli/cmd/directory/backup.go index 91922256..acc93560 100644 --- a/pkg/cli/cmd/directory/backup.go +++ b/pkg/cli/cmd/directory/backup.go @@ -5,9 +5,8 @@ import ( "path" "github.com/aserto-dev/topaz/pkg/cli/cc" + "github.com/aserto-dev/topaz/pkg/cli/clients" dsc "github.com/aserto-dev/topaz/pkg/cli/clients/directory" - - "github.com/pkg/errors" ) type BackupCmd struct { @@ -18,8 +17,8 @@ type BackupCmd struct { const defaultFileName = "backup.tar.gz" func (cmd *BackupCmd) Run(c *cc.CommonCtx) error { - if ok, _ := c.IsServing(cmd.ClientConfig()); !ok { - return errors.Wrap(cc.ErrNotServing, cmd.Host) + if ok, err := clients.Validate(c.Context, &cmd.Config); !ok { + return err } dsClient, err := dsc.NewClient(c, &cmd.Config) diff --git a/pkg/cli/cmd/directory/exporter.go b/pkg/cli/cmd/directory/exporter.go index 779ba2f4..31bf2aa5 100644 --- a/pkg/cli/cmd/directory/exporter.go +++ b/pkg/cli/cmd/directory/exporter.go @@ -4,8 +4,8 @@ import ( "path/filepath" "github.com/aserto-dev/topaz/pkg/cli/cc" + "github.com/aserto-dev/topaz/pkg/cli/clients" dsc "github.com/aserto-dev/topaz/pkg/cli/clients/directory" - "github.com/pkg/errors" ) type ExportCmd struct { @@ -14,9 +14,10 @@ type ExportCmd struct { } func (cmd *ExportCmd) Run(c *cc.CommonCtx) error { - if ok, _ := c.IsServing(cmd.ClientConfig()); !ok { - return errors.Wrap(cc.ErrNotServing, cmd.Host) + if ok, err := clients.Validate(c.Context, &cmd.Config); !ok { + return err } + c.Con().Info().Msg(">>> exporting data to %s", cmd.Directory) objectsFile := filepath.Join(cmd.Directory, "objects.json") diff --git a/pkg/cli/cmd/directory/importer.go b/pkg/cli/cmd/directory/importer.go index 12543e0b..e6a1d37c 100644 --- a/pkg/cli/cmd/directory/importer.go +++ b/pkg/cli/cmd/directory/importer.go @@ -5,6 +5,7 @@ import ( "path/filepath" "github.com/aserto-dev/topaz/pkg/cli/cc" + "github.com/aserto-dev/topaz/pkg/cli/clients" dsc "github.com/aserto-dev/topaz/pkg/cli/clients/directory" "github.com/pkg/errors" ) @@ -15,9 +16,10 @@ type ImportCmd struct { } func (cmd *ImportCmd) Run(c *cc.CommonCtx) error { - if ok, _ := c.IsServing(cmd.ClientConfig()); !ok { - return errors.Wrap(cc.ErrNotServing, cmd.Host) + if ok, err := clients.Validate(c.Context, &cmd.Config); !ok { + return err } + c.Con().Info().Msg(">>> importing data from %s", cmd.Directory) if fi, err := os.Stat(cmd.Directory); err != nil || !fi.IsDir() { diff --git a/pkg/cli/cmd/directory/manifest.go b/pkg/cli/cmd/directory/manifest.go index fecf5d44..a4df91db 100644 --- a/pkg/cli/cmd/directory/manifest.go +++ b/pkg/cli/cmd/directory/manifest.go @@ -5,10 +5,9 @@ import ( "os" "github.com/aserto-dev/topaz/pkg/cli/cc" + "github.com/aserto-dev/topaz/pkg/cli/clients" dsc "github.com/aserto-dev/topaz/pkg/cli/clients/directory" "github.com/aserto-dev/topaz/pkg/cli/cmd/common" - - "github.com/pkg/errors" ) type GetManifestCmd struct { @@ -29,9 +28,10 @@ type DeleteManifestCmd struct { } func (cmd *GetManifestCmd) Run(c *cc.CommonCtx) error { - if ok, _ := c.IsServing(cmd.ClientConfig()); !ok { - return errors.Wrap(cc.ErrNotServing, cmd.Host) + if ok, err := clients.Validate(c.Context, &cmd.Config); !ok { + return err } + dsClient, err := dsc.NewClient(c, &cmd.Config) if err != nil { return err @@ -62,9 +62,10 @@ func (cmd *GetManifestCmd) Run(c *cc.CommonCtx) error { } func (cmd *SetManifestCmd) Run(c *cc.CommonCtx) error { - if ok, _ := c.IsServing(cmd.ClientConfig()); !ok { - return errors.Wrap(cc.ErrNotServing, cmd.Host) + if ok, err := clients.Validate(c.Context, &cmd.Config); !ok { + return err } + dsClient, err := dsc.NewClient(c, &cmd.Config) if err != nil { return err @@ -84,9 +85,10 @@ func (cmd *SetManifestCmd) Run(c *cc.CommonCtx) error { } func (cmd *DeleteManifestCmd) Run(c *cc.CommonCtx) error { - if ok, _ := c.IsServing(cmd.ClientConfig()); !ok { - return errors.Wrap(cc.ErrNotServing, cmd.Host) + if ok, err := clients.Validate(c.Context, &cmd.Config); !ok { + return err } + dsClient, err := dsc.NewClient(c, &cmd.Config) if err != nil { return err diff --git a/pkg/cli/cmd/directory/restore.go b/pkg/cli/cmd/directory/restore.go index 9322181a..795cb610 100644 --- a/pkg/cli/cmd/directory/restore.go +++ b/pkg/cli/cmd/directory/restore.go @@ -5,8 +5,8 @@ import ( "path" "github.com/aserto-dev/topaz/pkg/cli/cc" + "github.com/aserto-dev/topaz/pkg/cli/clients" dsc "github.com/aserto-dev/topaz/pkg/cli/clients/directory" - "github.com/pkg/errors" ) type RestoreCmd struct { @@ -15,8 +15,8 @@ type RestoreCmd struct { } func (cmd *RestoreCmd) Run(c *cc.CommonCtx) error { - if ok, _ := c.IsServing(cmd.ClientConfig()); !ok { - return errors.Wrap(cc.ErrNotServing, cmd.Host) + if ok, err := clients.Validate(c.Context, &cmd.Config); !ok { + return err } dsClient, err := dsc.NewClient(c, &cmd.Config) diff --git a/pkg/cli/cmd/templates/install.go b/pkg/cli/cmd/templates/install.go index a559845a..731a0268 100644 --- a/pkg/cli/cmd/templates/install.go +++ b/pkg/cli/cmd/templates/install.go @@ -117,17 +117,17 @@ func (cmd *InstallTemplateCmd) installTemplate(c *cc.CommonCtx, tmpl *template) healthCfg := &client.Config{ Address: cfg.Configuration.APIConfig.Health.ListenAddress, - ClientCertPath: "", // cfg.Configuration.APIConfig.Health.Certificates.TLSCertPath, - ClientKeyPath: "", // cfg.Configuration.APIConfig.Health.Certificates.TLSKeyPath, - CACertPath: "", // cfg.Configuration.APIConfig.Health.Certificates.TLSCACertPath, + ClientCertPath: "", + ClientKeyPath: "", + CACertPath: "", Insecure: false, NoTLS: true, } - if health, err := cc.ServiceHealthStatus(c.Context, healthCfg, "model"); err != nil { + if healthy, err := cc.ServiceHealthStatus(c.Context, healthCfg, "model"); err != nil { return errors.Wrapf(err, "unable to check health status") - } else if !health { - return errors.Errorf("gRPC endpoint not SERVING") + } else if !healthy { + return err } if model, ok := cfg.Configuration.APIConfig.Services["model"]; !ok {