From 3fe67b836edba0073c277a9c7d809f8422d4ff79 Mon Sep 17 00:00:00 2001 From: Jens Alm Date: Tue, 3 Dec 2024 15:51:06 -0500 Subject: [PATCH 01/16] 2515 Added import and export --- go.mod | 5 + go.sum | 10 ++ internal/rest/mgmt/helpers.go | 189 ++++++++++++++++++++++++-- ziti/cmd/cmd.go | 4 +- ziti/cmd/edge/quickstart.go | 1 + ziti/cmd/verify/common.go | 42 ------ ziti/cmd/verify/ops_verify_network.go | 25 ++-- ziti/cmd/verify/ops_verify_traffic.go | 5 +- zititest/go.mod | 6 +- zititest/go.sum | 3 + 10 files changed, 215 insertions(+), 75 deletions(-) delete mode 100644 ziti/cmd/verify/common.go diff --git a/go.mod b/go.mod index 5aa1f0558..16a153920 100644 --- a/go.mod +++ b/go.mod @@ -102,6 +102,8 @@ require ( github.com/MichaelMure/go-term-text v0.3.1 // indirect github.com/alecthomas/chroma v0.10.0 // indirect github.com/andybalholm/brotli v1.1.0 // indirect + github.com/antchfx/jsonquery v1.3.6 // indirect + github.com/antchfx/xpath v1.3.2 // indirect github.com/antlr4-go/antlr/v4 v4.13.1 // indirect github.com/armon/go-metrics v0.4.1 // indirect github.com/asaskevich/govalidator v0.0.0-20230301143203-a9d515a09cc2 // indirect @@ -124,6 +126,7 @@ require ( github.com/go-openapi/analysis v0.23.0 // indirect github.com/go-openapi/jsonpointer v0.21.0 // indirect github.com/go-openapi/jsonreference v0.21.0 // indirect + github.com/golang/groupcache v0.0.0-20210331224755-41bb18bfe9da // indirect github.com/golang/protobuf v1.5.4 // indirect github.com/gomarkdown/markdown v0.0.0-20230922112808-5421fefb8386 // indirect github.com/gorilla/schema v1.4.1 // indirect @@ -137,6 +140,7 @@ require ( github.com/inconshreveable/mousetrap v1.1.0 // indirect github.com/josharian/intern v1.0.0 // indirect github.com/josharian/native v1.1.0 // indirect + github.com/judedaryl/go-arrayutils v0.0.1 // indirect github.com/kballard/go-shellquote v0.0.0-20180428030007-95032a82bc51 // indirect github.com/kr/pty v1.1.8 // indirect github.com/kyokomi/emoji/v2 v2.2.12 // indirect @@ -159,6 +163,7 @@ require ( github.com/openziti-incubator/cf v0.0.3 // indirect github.com/openziti/dilithium v0.3.5 // indirect github.com/parallaxsecond/parsec-client-go v0.0.0-20221025095442-f0a77d263cf9 // indirect + github.com/patrickmn/go-cache v2.1.0+incompatible // indirect github.com/pelletier/go-toml/v2 v2.2.2 // indirect github.com/pion/dtls/v3 v3.0.4 // indirect github.com/pion/logging v0.2.2 // indirect diff --git a/go.sum b/go.sum index 0e4c13ae1..f93170584 100644 --- a/go.sum +++ b/go.sum @@ -80,6 +80,10 @@ github.com/alecthomas/units v0.0.0-20190717042225-c3de453c63f4/go.mod h1:ybxpYRF github.com/andybalholm/brotli v1.1.0 h1:eLKJA0d02Lf0mVpIDgYnqXcUn0GqVmEFny3VuID1U3M= github.com/andybalholm/brotli v1.1.0/go.mod h1:sms7XGricyQI9K10gOSf56VKKWS4oLer58Q+mhRPtnY= github.com/anmitsu/go-shlex v0.0.0-20161002113705-648efa622239/go.mod h1:2FmKhYUyUczH0OGQWaF5ceTx0UBShxjsH6f8oGKYe2c= +github.com/antchfx/jsonquery v1.3.6 h1:TaSfeAh7n6T11I74bsZ1FswreIfrbJ0X+OyLflx6mx4= +github.com/antchfx/jsonquery v1.3.6/go.mod h1:fGzSGJn9Y826Qd3pC8Wx45avuUwpkePsACQJYy+58BU= +github.com/antchfx/xpath v1.3.2 h1:LNjzlsSjinu3bQpw9hWMY9ocB80oLOWuQqFvO6xt51U= +github.com/antchfx/xpath v1.3.2/go.mod h1:i54GszH55fYfBmoZXapTHN8T8tkcHfRgLyVwwqzXNcs= github.com/antihax/optional v1.0.0/go.mod h1:uupD/76wgC+ih3iEmQUL+0Ugr19nfwCT1kdvxnR2qWY= github.com/antlr4-go/antlr/v4 v4.13.1 h1:SqQKkuVZ+zWkMMNkjy5FZe5mr5WURWnlpmOuzYWrPrQ= github.com/antlr4-go/antlr/v4 v4.13.1/go.mod h1:GKmUxMtwp6ZgGwZSva4eWPC5mS6vUAmOABFgjdkM7Nw= @@ -256,6 +260,8 @@ github.com/golang/groupcache v0.0.0-20190702054246-869f871628b6/go.mod h1:cIg4er github.com/golang/groupcache v0.0.0-20191027212112-611e8accdfc9/go.mod h1:cIg4eruTrX1D+g88fzRXU5OdNfaM+9IcxsU14FzY7Hc= github.com/golang/groupcache v0.0.0-20191227052852-215e87163ea7/go.mod h1:cIg4eruTrX1D+g88fzRXU5OdNfaM+9IcxsU14FzY7Hc= github.com/golang/groupcache v0.0.0-20200121045136-8c9f03a8e57e/go.mod h1:cIg4eruTrX1D+g88fzRXU5OdNfaM+9IcxsU14FzY7Hc= +github.com/golang/groupcache v0.0.0-20210331224755-41bb18bfe9da h1:oI5xCqsCo564l8iNU+DwB5epxmsaqB+rhGL0m5jtYqE= +github.com/golang/groupcache v0.0.0-20210331224755-41bb18bfe9da/go.mod h1:cIg4eruTrX1D+g88fzRXU5OdNfaM+9IcxsU14FzY7Hc= github.com/golang/lint v0.0.0-20180702182130-06c8688daad7/go.mod h1:tluoj9z5200jBnyusfRPU2LqT6J+DAorxEvtC7LHB+E= github.com/golang/mock v1.1.1/go.mod h1:oTYuIxOrZwtPieC+H1uAHpcLFnEyAGVDL/k47Jfbm0A= github.com/golang/mock v1.2.0/go.mod h1:oTYuIxOrZwtPieC+H1uAHpcLFnEyAGVDL/k47Jfbm0A= @@ -427,6 +433,8 @@ github.com/json-iterator/go v1.1.11/go.mod h1:KdQUCv79m/52Kvf8AW2vK1V8akMuk1QjK/ 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/jtolds/gls v4.20.0+incompatible/go.mod h1:QJZ7F/aHp+rZTRtaJ1ow/lLfFfVYBRgL+9YlvaHOwJU= +github.com/judedaryl/go-arrayutils v0.0.1 h1:89rWXRVp1c1gcE1UEWvFuohVMeYwfA0y4TMZtE8dS58= +github.com/judedaryl/go-arrayutils v0.0.1/go.mod h1:vqtnlEkOBpDGHS3U3kQtMJZGTOC+SBFAQYj2KcxLf1A= github.com/julienschmidt/httprouter v1.2.0/go.mod h1:SYymIcj16QtmaHHD7aYtjjsJG7VTCxuUUipMqKk8s4w= github.com/kataras/go-events v0.0.3 h1:o5YK53uURXtrlg7qE/vovxd/yKOJcLuFtPQbf1rYMC4= github.com/kataras/go-events v0.0.3/go.mod h1:bFBgtzwwzrag7kQmGuU1ZaVxhK2qseYPQomXoVEMsj4= @@ -610,6 +618,8 @@ github.com/parallaxsecond/parsec-client-go v0.0.0-20221025095442-f0a77d263cf9/go github.com/pascaldekloe/goe v0.0.0-20180627143212-57f6aae5913c/go.mod h1:lzWF7FIEvWOWxwDKqyGYQf6ZUaNfKdP144TG7ZOy1lc= github.com/pascaldekloe/goe v0.1.0 h1:cBOtyMzM9HTpWjXfbbunk26uA6nG3a8n06Wieeh0MwY= github.com/pascaldekloe/goe v0.1.0/go.mod h1:lzWF7FIEvWOWxwDKqyGYQf6ZUaNfKdP144TG7ZOy1lc= +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/pelletier/go-toml v1.2.0/go.mod h1:5z9KED0ma1S8pY6P1sdut58dfprrGBbd/94hg7ilaic= github.com/pelletier/go-toml v1.9.3/go.mod h1:u1nR/EPcESfeI/szUZKdtJ0xRNbUoANCkoOuaOx1Y+c= github.com/pelletier/go-toml/v2 v2.2.2 h1:aYUidT7k73Pcl9nb2gScu7NSrKCSHIDE89b3+6Wq+LM= diff --git a/internal/rest/mgmt/helpers.go b/internal/rest/mgmt/helpers.go index 006a0871b..65358f4a2 100644 --- a/internal/rest/mgmt/helpers.go +++ b/internal/rest/mgmt/helpers.go @@ -1,17 +1,17 @@ /* - Copyright NetFoundry Inc. +Copyright NetFoundry Inc. - Licensed under the Apache License, Version 2.0 (the "License"); - you may not use this file except in compliance with the License. - You may obtain a copy of the License at +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at - https://www.apache.org/licenses/LICENSE-2.0 +https://www.apache.org/licenses/LICENSE-2.0 - Unless required by applicable law or agreed to in writing, software - distributed under the License is distributed on an "AS IS" BASIS, - WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - See the License for the specific language governing permissions and - limitations under the License. +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. */ package mgmt @@ -20,10 +20,19 @@ import ( "crypto/tls" "crypto/x509" "errors" + "fmt" "github.com/openziti/edge-api/rest_management_api_client" + "github.com/openziti/edge-api/rest_management_api_client/auth_policy" + "github.com/openziti/edge-api/rest_management_api_client/certificate_authority" + "github.com/openziti/edge-api/rest_management_api_client/config" rest_mgmt "github.com/openziti/edge-api/rest_management_api_client/current_api_session" + "github.com/openziti/edge-api/rest_management_api_client/edge_router" + "github.com/openziti/edge-api/rest_management_api_client/edge_router_policy" + "github.com/openziti/edge-api/rest_management_api_client/external_jwt_signer" "github.com/openziti/edge-api/rest_management_api_client/identity" + "github.com/openziti/edge-api/rest_management_api_client/posture_checks" "github.com/openziti/edge-api/rest_management_api_client/service" + "github.com/openziti/edge-api/rest_management_api_client/service_edge_router_policy" "github.com/openziti/edge-api/rest_management_api_client/service_policy" "github.com/openziti/edge-api/rest_model" "github.com/openziti/edge-api/rest_util" @@ -77,7 +86,157 @@ func ServicePolicyFromFilter(client *rest_management_api_client.ZitiEdgeManageme params.SetTimeout(5 * time.Second) resp, err := client.ServicePolicy.ListServicePolicies(params, nil) if err != nil { - log.Errorf("Could not obtain an ID for the service with filter %s: %v", filter, err) + log.Errorf("Could not obtain an ID for the service policy with filter %s: %v", filter, err) + return nil + } + if resp == nil || resp.Payload == nil || resp.Payload.Data == nil || len(resp.Payload.Data) == 0 { + return nil + } + return resp.Payload.Data[0] +} + +func AuthPolicyFromFilter(client *rest_management_api_client.ZitiEdgeManagement, filter string) *rest_model.AuthPolicyDetail { + params := &auth_policy.ListAuthPoliciesParams{ + Filter: &filter, + Context: context.Background(), + } + params.SetTimeout(5 * time.Second) + resp, err := client.AuthPolicy.ListAuthPolicies(params, nil) + if err != nil { + log.Errorf("Could not obtain an ID for the auth policy with filter %s: %v", filter, err) + return nil + } + if resp == nil || resp.Payload == nil || resp.Payload.Data == nil || len(resp.Payload.Data) == 0 { + return nil + } + return resp.Payload.Data[0] +} + +func CertificateAuthorityFromFilter(client *rest_management_api_client.ZitiEdgeManagement, filter string) *rest_model.CaDetail { + params := &certificate_authority.ListCasParams{ + Filter: &filter, + Context: context.Background(), + } + params.SetTimeout(5 * time.Second) + resp, err := client.CertificateAuthority.ListCas(params, nil) + if err != nil { + log.Errorf("Could not obtain an ID for the certificate authority with filter %s: %v", filter, err) + return nil + } + if resp == nil || resp.Payload == nil || resp.Payload.Data == nil || len(resp.Payload.Data) == 0 { + return nil + } + return resp.Payload.Data[0] +} + +func ConfigTypeFromFilter(client *rest_management_api_client.ZitiEdgeManagement, filter string) *rest_model.ConfigTypeDetail { + params := &config.ListConfigTypesParams{ + Filter: &filter, + Context: context.Background(), + } + params.SetTimeout(5 * time.Second) + resp, err := client.Config.ListConfigTypes(params, nil) + if err != nil { + log.Errorf("Could not obtain an ID for the config type with filter %s: %v", filter, err) + return nil + } + if resp == nil || resp.Payload == nil || resp.Payload.Data == nil || len(resp.Payload.Data) == 0 { + return nil + } + return resp.Payload.Data[0] +} + +func ConfigFromFilter(client *rest_management_api_client.ZitiEdgeManagement, filter string) *rest_model.ConfigDetail { + params := &config.ListConfigsParams{ + Filter: &filter, + Context: context.Background(), + } + params.SetTimeout(5 * time.Second) + resp, err := client.Config.ListConfigs(params, nil) + if err != nil { + log.Errorf("Could not obtain an ID for the config with filter %s: %v", filter, err) + return nil + } + if resp == nil || resp.Payload == nil || resp.Payload.Data == nil || len(resp.Payload.Data) == 0 { + return nil + } + return resp.Payload.Data[0] +} + +func ExternalJWTSignerFromFilter(client *rest_management_api_client.ZitiEdgeManagement, filter string) *rest_model.ExternalJWTSignerDetail { + params := &external_jwt_signer.ListExternalJWTSignersParams{ + Filter: &filter, + Context: context.Background(), + } + params.SetTimeout(5 * time.Second) + resp, err := client.ExternalJWTSigner.ListExternalJWTSigners(params, nil) + if err != nil { + log.Errorf("Could not obtain an ID for the external jwt signer with filter %s: %v", filter, err) + return nil + } + if resp == nil || resp.Payload == nil || resp.Payload.Data == nil || len(resp.Payload.Data) == 0 { + return nil + } + return resp.Payload.Data[0] +} + +func PostureCheckFromFilter(client *rest_management_api_client.ZitiEdgeManagement, filter string) *rest_model.PostureCheckDetail { + params := &posture_checks.ListPostureChecksParams{ + Filter: &filter, + Context: context.Background(), + } + params.SetTimeout(5 * time.Second) + resp, err := client.PostureChecks.ListPostureChecks(params, nil) + if err != nil { + log.Errorf("Could not obtain an ID for the posture check with filter %s: %v", filter, err) + return nil + } + if resp == nil || resp.Payload == nil || resp.Payload.Data == nil || len(resp.Payload.Data()) == 0 { + return nil + } + return &resp.Payload.Data()[0] +} + +func EdgeRouterPolicyFromFilter(client *rest_management_api_client.ZitiEdgeManagement, filter string) *rest_model.EdgeRouterPolicyDetail { + params := &edge_router_policy.ListEdgeRouterPoliciesParams{ + Filter: &filter, + } + params.SetTimeout(5 * time.Second) + resp, err := client.EdgeRouterPolicy.ListEdgeRouterPolicies(params, nil) + if err != nil { + log.Errorf("Could not obtain an ID for the edge router policies with filter %s: %v", filter, err) + return nil + } + if resp == nil || resp.Payload == nil || resp.Payload.Data == nil || len(resp.Payload.Data) == 0 { + return nil + } + return resp.Payload.Data[0] +} + +func EdgeRouterFromFilter(client *rest_management_api_client.ZitiEdgeManagement, filter string) *rest_model.EdgeRouterDetail { + params := &edge_router.ListEdgeRoutersParams{ + Filter: &filter, + } + params.SetTimeout(5 * time.Second) + resp, err := client.EdgeRouter.ListEdgeRouters(params, nil) + if err != nil { + log.Errorf("Could not obtain an ID for the edge routers with filter %s: %v", filter, err) + return nil + } + if resp == nil || resp.Payload == nil || resp.Payload.Data == nil || len(resp.Payload.Data) == 0 { + return nil + } + return resp.Payload.Data[0] +} + +func ServiceEdgeRouterPolicyFromFilter(client *rest_management_api_client.ZitiEdgeManagement, filter string) *rest_model.ServiceEdgeRouterPolicyDetail { + params := &service_edge_router_policy.ListServiceEdgeRouterPoliciesParams{ + Filter: &filter, + } + params.SetTimeout(5 * time.Second) + resp, err := client.ServiceEdgeRouterPolicy.ListServiceEdgeRouterPolicies(params, nil) + if err != nil { + log.Errorf("Could not obtain an ID for the ServiceEdgeRouterPolicy routers with filter %s: %v", filter, err) return nil } if resp == nil || resp.Payload == nil || resp.Payload.Data == nil || len(resp.Payload.Data) == 0 { @@ -87,7 +246,7 @@ func ServicePolicyFromFilter(client *rest_management_api_client.ZitiEdgeManageme } func NameFilter(name string) string { - return `name="` + name + `"` + return fmt.Sprintf("name = \"%s\"", name) } func NewClient() (*rest_management_api_client.ZitiEdgeManagement, error) { @@ -100,7 +259,7 @@ func NewClient() (*rest_management_api_client.ZitiEdgeManagement, error) { if cachedId == nil { return nil, errors.New("no identity found") } - + caPool := x509.NewCertPool() if _, cacertErr := os.Stat(cachedId.CaCert); cacertErr == nil { rootPemData, err := os.ReadFile(cachedId.CaCert) @@ -111,7 +270,7 @@ func NewClient() (*rest_management_api_client.ZitiEdgeManagement, error) { } else { return nil, errors.New("CA cert file not found in config file") } - + tlsConfig := &tls.Config{ RootCAs: caPool, } @@ -137,4 +296,4 @@ func NewClient() (*rest_management_api_client.ZitiEdgeManagement, error) { return nil, errors.New("client not authenticated. login with 'ziti edge login' before executing") } return c, nil -} \ No newline at end of file +} diff --git a/ziti/cmd/cmd.go b/ziti/cmd/cmd.go index dddeaa4f5..1131c218e 100644 --- a/ziti/cmd/cmd.go +++ b/ziti/cmd/cmd.go @@ -26,6 +26,7 @@ import ( "github.com/openziti/cobra-to-md" "github.com/openziti/ziti/ziti/cmd/agentcli" + "github.com/openziti/ziti/ziti/cmd/ascode/download" "github.com/openziti/ziti/ziti/cmd/common" "github.com/openziti/ziti/ziti/cmd/create" "github.com/openziti/ziti/ziti/cmd/database" @@ -136,7 +137,7 @@ func NewCmdRoot(in io.Reader, out, err io.Writer, cmd *cobra.Command) *cobra.Com demoCmd := demo.NewDemoCmd(p) opsCommands := &cobra.Command{ - Use: "ops", + Use: "ops", Short: "Various utilities useful when operating a Ziti network", } @@ -145,6 +146,7 @@ func NewCmdRoot(in io.Reader, out, err io.Writer, cmd *cobra.Command) *cobra.Com opsCommands.AddCommand(NewUnwrapIdentityFileCommand(out, err)) opsCommands.AddCommand(verify.NewVerifyNetwork(out, err)) opsCommands.AddCommand(verify.NewVerifyTraffic(out, err)) + opsCommands.AddCommand(download.NewDownloadCmd(out, err)) groups := templates.CommandGroups{ { diff --git a/ziti/cmd/edge/quickstart.go b/ziti/cmd/edge/quickstart.go index ef611c973..51c386b04 100644 --- a/ziti/cmd/edge/quickstart.go +++ b/ziti/cmd/edge/quickstart.go @@ -200,6 +200,7 @@ func (o *QuickstartOpts) run(ctx context.Context) { tmpDir, _ := os.MkdirTemp("", "quickstart") o.Home = tmpDir o.cleanOnExit = true + logrus.Infof("temporary --home '%s'", o.Home) } else { //normalize path if strings.HasPrefix(o.Home, "~") { diff --git a/ziti/cmd/verify/common.go b/ziti/cmd/verify/common.go deleted file mode 100644 index 3f1384c0c..000000000 --- a/ziti/cmd/verify/common.go +++ /dev/null @@ -1,42 +0,0 @@ -/* - Copyright NetFoundry Inc. - - Licensed under the Apache License, Version 2.0 (the "License"); - you may not use this file except in compliance with the License. - You may obtain a copy of the License at - - https://www.apache.org/licenses/LICENSE-2.0 - - Unless required by applicable law or agreed to in writing, software - distributed under the License is distributed on an "AS IS" BASIS, - WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - See the License for the specific language governing permissions and - limitations under the License. -*/ -package verify - -import ( - "github.com/sirupsen/logrus" - "runtime" -) - -func configureLogFormat(level logrus.Level) { - logrus.SetLevel(level) - logrus.SetFormatter(&logrus.TextFormatter{ - ForceColors: true, - DisableColors: false, - ForceQuote: false, - DisableQuote: false, - EnvironmentOverrideColors: false, - DisableTimestamp: true, - FullTimestamp: false, - TimestampFormat: "", - DisableSorting: true, - SortingFunc: nil, - DisableLevelTruncation: true, - PadLevelText: true, - QuoteEmptyFields: false, - FieldMap: nil, - CallerPrettyfier: func(frame *runtime.Frame) (function string, file string) { return "", "" }, - }) -} diff --git a/ziti/cmd/verify/ops_verify_network.go b/ziti/cmd/verify/ops_verify_network.go index e6599248f..3be2eb963 100644 --- a/ziti/cmd/verify/ops_verify_network.go +++ b/ziti/cmd/verify/ops_verify_network.go @@ -1,22 +1,23 @@ /* - Copyright NetFoundry Inc. +Copyright NetFoundry Inc. - Licensed under the Apache License, Version 2.0 (the "License"); - you may not use this file except in compliance with the License. - You may obtain a copy of the License at +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at - https://www.apache.org/licenses/LICENSE-2.0 +https://www.apache.org/licenses/LICENSE-2.0 - Unless required by applicable law or agreed to in writing, software - distributed under the License is distributed on an "AS IS" BASIS, - WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - See the License for the specific language governing permissions and - limitations under the License. +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. */ package verify import ( "fmt" + "github.com/openziti/ziti/internal" "io" "net" "os" @@ -36,7 +37,7 @@ var log = pfxlog.Logger() type network struct { controllerConfig string routerConfig string - verbose bool + verbose bool } type protoHostPort struct { @@ -63,7 +64,7 @@ func NewVerifyNetwork(_ io.Writer, _ io.Writer) *cobra.Command { } pfxlog.GlobalInit(logLvl, pfxlog.DefaultOptions().Color()) - configureLogFormat(logLvl) + internal.ConfigureLogFormat(logLvl) anyFailure := false if n.controllerConfig != "" { diff --git a/ziti/cmd/verify/ops_verify_traffic.go b/ziti/cmd/verify/ops_verify_traffic.go index b22fd4f4d..2e0ff7b63 100644 --- a/ziti/cmd/verify/ops_verify_traffic.go +++ b/ziti/cmd/verify/ops_verify_traffic.go @@ -20,6 +20,7 @@ import ( "context" "fmt" "github.com/michaelquigley/pfxlog" + "github.com/openziti/ziti/internal" "github.com/openziti/ziti/ziti/cmd/edge" "github.com/sirupsen/logrus" "io" @@ -71,7 +72,7 @@ func NewVerifyTraffic(out io.Writer, errOut io.Writer) *cobra.Command { } pfxlog.GlobalInit(logLvl, pfxlog.DefaultOptions().Color()) - configureLogFormat(logLvl) + internal.ConfigureLogFormat(logLvl) timePrefix := time.Now().Format("2006-01-02-1504") if t.prefix == "" { @@ -133,7 +134,7 @@ func NewVerifyTraffic(out io.Writer, errOut io.Writer) *cobra.Command { cmd.Flags().BoolVar(&t.allowMultipleServers, "allow-multiple-servers", false, "Whether to allows the same server multiple times.") cmd.Flags().BoolVar(&t.haEnabled, "ha", false, "Enable high availability mode.") _ = cmd.Flags().MarkHidden("ha") - + edge.AddLoginFlags(cmd, &t.loginOpts) t.loginOpts.Out = out t.loginOpts.Err = errOut diff --git a/zititest/go.mod b/zititest/go.mod index 8ca8e411b..8cd09c63a 100644 --- a/zititest/go.mod +++ b/zititest/go.mod @@ -65,7 +65,7 @@ require ( github.com/fsnotify/fsnotify v1.7.0 // indirect github.com/fullsailor/pkcs7 v0.0.0-20190404230743-d7302db945fa // indirect github.com/gaissmai/extnetip v1.1.0 // indirect - github.com/go-acme/lego/v4 v4.20.2 // indirect + github.com/go-acme/lego/v4 v4.20.4 // indirect github.com/go-jose/go-jose/v4 v4.0.4 // indirect github.com/go-logr/logr v1.4.2 // indirect github.com/go-logr/stdr v1.2.2 // indirect @@ -80,7 +80,7 @@ require ( github.com/go-openapi/strfmt v0.23.0 // indirect github.com/go-openapi/swag v0.23.0 // indirect github.com/go-openapi/validate v0.24.0 // indirect - github.com/go-resty/resty/v2 v2.16.0 // indirect + github.com/go-resty/resty/v2 v2.16.2 // indirect github.com/golang-jwt/jwt/v5 v5.2.1 // indirect github.com/golang/protobuf v1.5.4 // indirect github.com/gomarkdown/markdown v0.0.0-20230922112808-5421fefb8386 // indirect @@ -103,7 +103,7 @@ require ( github.com/influxdata/influxdb-client-go/v2 v2.14.0 // indirect github.com/influxdata/influxdb1-client v0.0.0-20191209144304-8bf82d3c094d // indirect github.com/influxdata/line-protocol v0.0.0-20200327222509-2487e7298839 // indirect - github.com/jedib0t/go-pretty/v6 v6.6.1 // indirect + github.com/jedib0t/go-pretty/v6 v6.6.2 // indirect github.com/jessevdk/go-flags v1.6.1 // indirect github.com/jinzhu/copier v0.4.0 // indirect github.com/jmespath/go-jmespath v0.4.0 // indirect diff --git a/zititest/go.sum b/zititest/go.sum index 31e83993c..07732f5cd 100644 --- a/zititest/go.sum +++ b/zititest/go.sum @@ -207,6 +207,7 @@ github.com/ghodss/yaml v1.0.0/go.mod h1:4dBDuWmgqj2HViK6kFavaiC9ZROes6MMH2rRYeME github.com/gliderlabs/ssh v0.1.1/go.mod h1:U7qILu1NlMHj9FlMhZLlkCdDnU1DBEAqr0aevW3Awn0= github.com/go-acme/lego/v4 v4.20.2 h1:ZwO3oLZb8fL6up1OZVJP3yHuvqhozzlEmyqKmhrPchQ= github.com/go-acme/lego/v4 v4.20.2/go.mod h1:foauPlhnhoq8WUphaWx5U04uDc+JGhk4ZZtPz/Vqsjg= +github.com/go-acme/lego/v4 v4.20.4/go.mod h1:foauPlhnhoq8WUphaWx5U04uDc+JGhk4ZZtPz/Vqsjg= github.com/go-chi/chi v4.0.2+incompatible/go.mod h1:eB3wogJHnLi3x/kFX2A+IbTBlXxmMeXJVKy9tTv1XzQ= github.com/go-errors/errors v1.0.1/go.mod h1:f4zRHt4oKfwPJE5k8C9vpYG+aDHdBFUsgrm6/TyX73Q= github.com/go-gl/glfw v0.0.0-20190409004039-e6da0acd62b1/go.mod h1:vR7hzQXu2zJy9AVAgeJqvqgH9Q5CA+iKCZ2gyEVpxRU= @@ -248,6 +249,7 @@ github.com/go-openapi/validate v0.24.0 h1:LdfDKwNbpB6Vn40xhTdNZAnfLECL81w+VX3Bum github.com/go-openapi/validate v0.24.0/go.mod h1:iyeX1sEufmv3nPbBdX3ieNviWnOZaJ1+zquzJEf2BAQ= github.com/go-resty/resty/v2 v2.16.0 h1:qpKalHWI2bpp9BIKlyT8TYWEJXOk1NuKbfiT3RRnzWc= github.com/go-resty/resty/v2 v2.16.0/go.mod h1:0fHAoK7JoBy/Ch36N8VFeMsK7xQOHhvWaC3iOktwmIU= +github.com/go-resty/resty/v2 v2.16.2/go.mod h1:0fHAoK7JoBy/Ch36N8VFeMsK7xQOHhvWaC3iOktwmIU= github.com/go-stack/stack v1.8.0/go.mod h1:v0f6uXyyMGvRgIKkXu+yp6POWl0qKG85gN/melR3HDY= github.com/godbus/dbus/v5 v5.0.4/go.mod h1:xhWf0FNVPg57R7Z0UbKHbJfkEywrmjJnf7w5xrFpKfA= github.com/gogo/protobuf v1.1.1/go.mod h1:r8qH/GZQm5c6nD/R0oafs1akxWv10x8SbQlK7atdtwQ= @@ -417,6 +419,7 @@ github.com/influxdata/line-protocol v0.0.0-20200327222509-2487e7298839 h1:W9WBk7 github.com/influxdata/line-protocol v0.0.0-20200327222509-2487e7298839/go.mod h1:xaLFMmpvUxqXtVkUJfg9QmT88cDaCJ3ZKgdZ78oO8Qo= github.com/jedib0t/go-pretty/v6 v6.6.1 h1:iJ65Xjb680rHcikRj6DSIbzCex2huitmc7bDtxYVWyc= github.com/jedib0t/go-pretty/v6 v6.6.1/go.mod h1:zbn98qrYlh95FIhwwsbIip0LYpwSG8SUOScs+v9/t0E= +github.com/jedib0t/go-pretty/v6 v6.6.2/go.mod h1:zbn98qrYlh95FIhwwsbIip0LYpwSG8SUOScs+v9/t0E= github.com/jellevandenhooff/dkim v0.0.0-20150330215556-f50fe3d243e1/go.mod h1:E0B/fFc00Y+Rasa88328GlI/XbtyysCtTHZS8h7IrBU= github.com/jeremija/gosubmit v0.2.7 h1:At0OhGCFGPXyjPYAsCchoBUhE099pcBXmsb4iZqROIc= github.com/jeremija/gosubmit v0.2.7/go.mod h1:Ui+HS073lCFREXBbdfrJzMB57OI/bdxTiLtrDHHhFPI= From d5d073758c6ad80a859af6838200ad07e37c2033 Mon Sep 17 00:00:00 2001 From: Jens Alm Date: Tue, 3 Dec 2024 15:53:28 -0500 Subject: [PATCH 02/16] 2515 fixed lint issues --- internal/rest/mgmt/helpers.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/internal/rest/mgmt/helpers.go b/internal/rest/mgmt/helpers.go index 65358f4a2..7746b5ab3 100644 --- a/internal/rest/mgmt/helpers.go +++ b/internal/rest/mgmt/helpers.go @@ -191,7 +191,7 @@ func PostureCheckFromFilter(client *rest_management_api_client.ZitiEdgeManagemen log.Errorf("Could not obtain an ID for the posture check with filter %s: %v", filter, err) return nil } - if resp == nil || resp.Payload == nil || resp.Payload.Data == nil || len(resp.Payload.Data()) == 0 { + if resp == nil || resp.Payload == nil || len(resp.Payload.Data()) == 0 { return nil } return &resp.Payload.Data()[0] From 1a895a2f19835948ac82125304378c2054aff8f2 Mon Sep 17 00:00:00 2001 From: Jens Alm Date: Tue, 3 Dec 2024 16:03:02 -0500 Subject: [PATCH 03/16] 2515 fixed earlier commit --- internal/ascode/cache_util.go | 32 + internal/log_format.go | 42 ++ ziti/cmd/ascode/ascode_test.go | 238 +++++++ ziti/cmd/ascode/download/download.go | 399 +++++++++++ .../ascode/download/download_auth_policies.go | 110 +++ .../download_certificate_authorities.go | 62 ++ .../ascode/download/download_config_types.go | 64 ++ ziti/cmd/ascode/download/download_configs.go | 72 ++ .../download/download_edgerouter_policies.go | 75 +++ .../ascode/download/download_edgerouters.go | 63 ++ .../download/download_external_jwt_signers.go | 64 ++ .../ascode/download/download_identities.go | 88 +++ .../download/download_posture_checks.go | 57 ++ .../download_service_edgerouter_policies.go | 75 +++ .../download/download_service_policies.go | 81 +++ ziti/cmd/ascode/download/download_services.go | 82 +++ ziti/cmd/ascode/download/output.go | 140 ++++ ziti/cmd/ascode/test.yaml | 624 ++++++++++++++++++ ziti/cmd/ascode/upload/upload.go | 445 +++++++++++++ .../cmd/ascode/upload/upload_auth_policies.go | 108 +++ .../upload/upload_certificate_authorities.go | 74 +++ ziti/cmd/ascode/upload/upload_config_types.go | 77 +++ ziti/cmd/ascode/upload/upload_configs.go | 97 +++ .../upload/upload_edgerouter_policies.go | 87 +++ ziti/cmd/ascode/upload/upload_edgerouters.go | 93 +++ .../upload/upload_external_jwt_signers.go | 76 +++ ziti/cmd/ascode/upload/upload_identities.go | 122 ++++ .../cmd/ascode/upload/upload_posture_check.go | 113 ++++ .../upload_service_edgerouter_policies.go | 88 +++ .../ascode/upload/upload_service_policies.go | 86 +++ ziti/cmd/ascode/upload/upload_services.go | 121 ++++ 31 files changed, 3955 insertions(+) create mode 100644 internal/ascode/cache_util.go create mode 100644 internal/log_format.go create mode 100644 ziti/cmd/ascode/ascode_test.go create mode 100644 ziti/cmd/ascode/download/download.go create mode 100644 ziti/cmd/ascode/download/download_auth_policies.go create mode 100644 ziti/cmd/ascode/download/download_certificate_authorities.go create mode 100644 ziti/cmd/ascode/download/download_config_types.go create mode 100644 ziti/cmd/ascode/download/download_configs.go create mode 100644 ziti/cmd/ascode/download/download_edgerouter_policies.go create mode 100644 ziti/cmd/ascode/download/download_edgerouters.go create mode 100644 ziti/cmd/ascode/download/download_external_jwt_signers.go create mode 100644 ziti/cmd/ascode/download/download_identities.go create mode 100644 ziti/cmd/ascode/download/download_posture_checks.go create mode 100644 ziti/cmd/ascode/download/download_service_edgerouter_policies.go create mode 100644 ziti/cmd/ascode/download/download_service_policies.go create mode 100644 ziti/cmd/ascode/download/download_services.go create mode 100644 ziti/cmd/ascode/download/output.go create mode 100644 ziti/cmd/ascode/test.yaml create mode 100644 ziti/cmd/ascode/upload/upload.go create mode 100644 ziti/cmd/ascode/upload/upload_auth_policies.go create mode 100644 ziti/cmd/ascode/upload/upload_certificate_authorities.go create mode 100644 ziti/cmd/ascode/upload/upload_config_types.go create mode 100644 ziti/cmd/ascode/upload/upload_configs.go create mode 100644 ziti/cmd/ascode/upload/upload_edgerouter_policies.go create mode 100644 ziti/cmd/ascode/upload/upload_edgerouters.go create mode 100644 ziti/cmd/ascode/upload/upload_external_jwt_signers.go create mode 100644 ziti/cmd/ascode/upload/upload_identities.go create mode 100644 ziti/cmd/ascode/upload/upload_posture_check.go create mode 100644 ziti/cmd/ascode/upload/upload_service_edgerouter_policies.go create mode 100644 ziti/cmd/ascode/upload/upload_service_policies.go create mode 100644 ziti/cmd/ascode/upload/upload_services.go diff --git a/internal/ascode/cache_util.go b/internal/ascode/cache_util.go new file mode 100644 index 000000000..14557c36e --- /dev/null +++ b/internal/ascode/cache_util.go @@ -0,0 +1,32 @@ +package common + +import ( + "errors" + "github.com/patrickmn/go-cache" + "log/slog" +) + +type CacheGetter func(id string) (interface{}, error) + +func GetItemFromCache(c *cache.Cache, key string, fn CacheGetter) (interface{}, error) { + if key == "" { + return nil, errors.New("key is null, can't resolve from cache or get it from source") + } + detail, found := c.Get(key) + if !found { + slog. + With("key", key). + Debug("Item not in cache, getting from source") + var err error + detail, err = fn(key) + if err != nil { + return nil, errors.Join(errors.New("error reading: "+key), err) + } + c.Set(key, detail, cache.NoExpiration) + return detail, nil + } + slog. + With("key", key). + Debug("Item found in cache") + return detail, nil +} diff --git a/internal/log_format.go b/internal/log_format.go new file mode 100644 index 000000000..291e58c0d --- /dev/null +++ b/internal/log_format.go @@ -0,0 +1,42 @@ +/* +Copyright NetFoundry Inc. + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + +https://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ +package internal + +import ( + "github.com/sirupsen/logrus" + "runtime" +) + +func ConfigureLogFormat(level logrus.Level) { + logrus.SetLevel(level) + logrus.SetFormatter(&logrus.TextFormatter{ + ForceColors: true, + DisableColors: false, + ForceQuote: false, + DisableQuote: false, + EnvironmentOverrideColors: false, + DisableTimestamp: true, + FullTimestamp: false, + TimestampFormat: "", + DisableSorting: true, + SortingFunc: nil, + DisableLevelTruncation: true, + PadLevelText: true, + QuoteEmptyFields: false, + FieldMap: nil, + CallerPrettyfier: func(frame *runtime.Frame) (function string, file string) { return "", "" }, + }) +} diff --git a/ziti/cmd/ascode/ascode_test.go b/ziti/cmd/ascode/ascode_test.go new file mode 100644 index 000000000..9f11bc75b --- /dev/null +++ b/ziti/cmd/ascode/ascode_test.go @@ -0,0 +1,238 @@ +/* + Copyright NetFoundry Inc. + + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at + + https://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. +*/ + +package cmd + +import ( + "context" + "crypto/tls" + "fmt" + "github.com/antchfx/jsonquery" + "github.com/michaelquigley/pfxlog" + "github.com/openziti/ziti/ziti/cmd/ascode/download" + "github.com/openziti/ziti/ziti/cmd/ascode/upload" + "github.com/openziti/ziti/ziti/cmd/edge" + "github.com/stretchr/testify/assert" + "net/http" + "os" + "strings" + "testing" + "time" +) + +var log = pfxlog.Logger() + +func TestYamlUploadAndDownload(t *testing.T) { + ctx, cancel := context.WithCancel(context.Background()) + cmdComplete := make(chan bool) + qsCmd := edge.NewQuickStartCmd(os.Stdout, os.Stderr, ctx) + + tmp, _ := os.MkdirTemp("/tmp", "ziti-") + qsCmd.SetArgs([]string{"--home", tmp, "--ctrl-address", "127.0.0.1"}) + os.Setenv("ZITI_CONFIG_DIR", tmp) + os.Setenv("ZITI_HOME", tmp) + + go func() { + err := qsCmd.Execute() + if err != nil { + log.Fatal(err) + } + cmdComplete <- true + }() + + c := make(chan struct{}) + go waitForController("https://127.0.0.1:1280", c) + timeout, _ := time.ParseDuration("180000000s") + select { + case <-c: + //completed normally + log.Info("controller online") + case <-time.After(timeout): + cancel() + panic("timed out waiting for controller") + } + + login := edge.NewLoginCmd(os.Stdout, os.Stderr) + login.SetArgs([]string{"127.0.0.1:1280", "-y", "--username", "admin", "--password", "admin"}) + err := login.Execute() + if err != nil { + log.Fatal(err) + } + + performTest(t) + + cancel() //terminate the running ctrl/router + + <-cmdComplete + fmt.Println("Operation completed") +} + +func waitForController(ctrlUrl string, done chan struct{}) { + tr := &http.Transport{TLSClientConfig: &tls.Config{InsecureSkipVerify: true}} + client := &http.Client{Transport: tr} + for { + r, e := client.Get(ctrlUrl) + if e != nil || r == nil || r.StatusCode != 200 { + time.Sleep(50 * time.Millisecond) + } else { + break + } + } + done <- struct{}{} + +} + +func performTest(t *testing.T) { + + errWriter := strings.Builder{} + + uploadWriter := strings.Builder{} + uploadCmd := upload.NewUploadCmd(&uploadWriter, &errWriter) + uploadCmd.SetArgs([]string{"--verbose", "--yaml", "./test.yaml"}) + + err := uploadCmd.Execute() + if err != nil { + t.Fail() + log.Fatal(err) + } + + downloadWriter := strings.Builder{} + downloadCmd := download.NewDownloadCmd(&downloadWriter, &errWriter) + downloadCmd.SetArgs([]string{"--json"}) + + err = downloadCmd.Execute() + if err != nil { + t.Fail() + log.Fatal(err) + } + + result := downloadWriter.String() + + log.Debug("Read " + result) + + doc, err := jsonquery.Parse(strings.NewReader(result)) + if err != nil { + panic(err) + } + + assert.NotEqual(t, 0, len(doc.ChildNodes())) + if len(doc.ChildNodes()) == 0 { + // no data, nothing to test + return + } + + externalJwtSigner1 := jsonquery.FindOne(doc, "//externalJwtSigners/*[name='NetFoundry Console Integration External JWT Signer']") + assert.Equal(t, "https://gateway.staging.netfoundry.io/network-auth/v1/public/.well-known/NYFw7IGJKNP9AaG45iwCj/jwks.json", jsonquery.FindOne(externalJwtSigner1, "/jwksEndpoint").Value()) + assert.Equal(t, "https://gateway.staging.netfoundry.io/cloudziti/25ba1aa3-4468-445a-910e-93f5b425f2c1", jsonquery.FindOne(externalJwtSigner1, "/audience").Value()) + + authPolicy1 := jsonquery.FindOne(doc, "//authPolicies/*[name='NetFoundry Console Integration Auth Policy']") + assert.Equal(t, "@NetFoundry Console Integration External JWT Signer", jsonquery.FindOne(authPolicy1, "/primary/extJwt/allowedSigners/*[1]").Value()) + authPolicy2 := jsonquery.FindOne(doc, "//authPolicies/*[name='Test123']") + assert.True(t, jsonquery.FindOne(authPolicy2, "/primary/updb/allowed").Value().(bool)) + + identity1 := jsonquery.FindOne(doc, "//identities/*[externalId='f1505b76-38ec-470b-9819-75984623c23d']") + assert.Equal(t, "Vinay Lakshmaiah", jsonquery.FindOne(identity1, "/name").Value()) + assert.Empty(t, jsonquery.FindOne(identity1, "/roleAttributes").Value()) + assert.Equal(t, "@NetFoundry Console Integration Auth Policy", jsonquery.FindOne(identity1, "/authPolicy").Value()) + + config1 := jsonquery.FindOne(doc, "//configs/*[name='service2-intercept-config']") + assert.Equal(t, "@intercept.v1", jsonquery.FindOne(config1, "/configType").Value()) + config2 := jsonquery.FindOne(doc, "//configs/*[name='ssssimple-intercept-config']") + assert.Equal(t, "@intercept.v1", jsonquery.FindOne(config2, "/configType").Value()) + config3 := jsonquery.FindOne(doc, "//configs/*[name='test-123-host-config']") + assert.Equal(t, "@host.v1", jsonquery.FindOne(config3, "/configType").Value()) + config4 := jsonquery.FindOne(doc, "//configs/*[name='service1-host-config']") + assert.Equal(t, "@host.v1", jsonquery.FindOne(config4, "/configType").Value()) + + postureCheck1 := jsonquery.FindOne(doc, "//postureChecks/*[name='Mac']") + assert.Equal(t, "MAC", jsonquery.FindOne(postureCheck1, "/typeId").Value()) + assert.Equal(t, "0123456789ab", jsonquery.FindOne(postureCheck1, "/macAddresses/*[1]").Value()) + assert.Equal(t, "mac", jsonquery.FindOne(postureCheck1, "/roleAttributes/*[1]").Value()) + + postureCheck2 := jsonquery.FindOne(doc, "//postureChecks/*[name='MFA']") + assert.Equal(t, "MFA", jsonquery.FindOne(postureCheck2, "/typeId").Value()) + assert.Equal(t, "mfa", jsonquery.FindOne(postureCheck2, "/roleAttributes/*[1]").Value()) + + posturecheck3 := jsonquery.FindOne(doc, "//postureChecks/*[name='Process']") + assert.Equal(t, "PROCESS", jsonquery.FindOne(posturecheck3, "/typeId").Value()) + assert.Equal(t, "Linux", jsonquery.FindOne(posturecheck3, "/process/osType").Value()) + assert.Equal(t, "/path/something", jsonquery.FindOne(posturecheck3, "/process/path").Value()) + assert.Empty(t, jsonquery.Find(posturecheck3, "/process/hashes/*[1]")) + assert.Equal(t, "process", jsonquery.FindOne(posturecheck3, "/roleAttributes/*[1]").Value()) + + router1 := jsonquery.FindOne(doc, "//routers/*[name='custroutet2']") + assert.Equal(t, "vis-bind", jsonquery.FindOne(router1, "/roleAttributes/*[1]").Value()) + + router2 := jsonquery.FindOne(doc, "//routers/*[name='asd']") + assert.Empty(t, jsonquery.Find(router2, "/roleAttributes/*[1]")) + + router3 := jsonquery.FindOne(doc, "//routers/*[name='public-router1']") + assert.Equal(t, "public", jsonquery.FindOne(router3, "/roleAttributes/*[1]").Value()) + + router4 := jsonquery.FindOne(doc, "//routers/*[name='enroll']") + assert.Empty(t, jsonquery.FindOne(router4, "/roleAttributes").Value()) + + router5 := jsonquery.FindOne(doc, "//routers/*[name='nfhosted']") + assert.Equal(t, "public", jsonquery.FindOne(router5, "/roleAttributes/*[1]").Value()) + + router6 := jsonquery.FindOne(doc, "//routers/*[name='appdata']") + assert.Empty(t, jsonquery.FindOne(router6, "/roleAttributes").Value()) + assert.Equal(t, "er", jsonquery.FindOne(router6, "/appData/my").Value()) + + router7 := jsonquery.FindOne(doc, "//routers/*[name='vis-customer-router']") + assert.Equal(t, "vis-bind", jsonquery.FindOne(router7, "/roleAttributes/*").Value()) + + serviceRouterPolicy1 := jsonquery.FindOne(doc, "//serviceEdgeRouterPolicies/*[name='ssep2']") + assert.Equal(t, "@custroutet2", jsonquery.FindOne(serviceRouterPolicy1, "/edgeRouterRoles/*[1]").Value()) + assert.Equal(t, "@ssssimple", jsonquery.FindOne(serviceRouterPolicy1, "/serviceRoles/*[1]").Value()) + + serviceRouterPolicy2 := jsonquery.FindOne(doc, "//serviceEdgeRouterPolicies/*[name='sep1']") + assert.Equal(t, "@public-router1", jsonquery.FindOne(serviceRouterPolicy2, "/edgeRouterRoles/*[1]").Value()) + assert.Equal(t, "@ssssimple", jsonquery.FindOne(serviceRouterPolicy2, "/serviceRoles/*[1]").Value()) + + servicePolicy1 := jsonquery.FindOne(doc, "//servicePolicies/*[name='ssssimple-bind-policy']") + assert.Equal(t, "@public-router1", jsonquery.FindOne(servicePolicy1, "/identityRoles/*[1]").Value()) + assert.Equal(t, "@ssssimple", jsonquery.FindOne(servicePolicy1, "/serviceRoles/*[1]").Value()) + assert.Equal(t, "Bind", jsonquery.FindOne(servicePolicy1, "/type").Value()) + + servicePolicy2 := jsonquery.FindOne(doc, "//servicePolicies/*[name='ssssimple-dial-policy']") + assert.Equal(t, "@identity12", jsonquery.FindOne(servicePolicy2, "/identityRoles/*[1]").Value()) + assert.Equal(t, "@ssssimple", jsonquery.FindOne(servicePolicy2, "/serviceRoles/*[1]").Value()) + assert.Equal(t, "Dial", jsonquery.FindOne(servicePolicy2, "/type").Value()) + + routerPolicy1 := jsonquery.FindOne(doc, "//edgeRouterPolicies/*[name='routerpolicy1']") + assert.Equal(t, "@public-router1", jsonquery.FindOne(routerPolicy1, "/edgeRouterRoles/*[1]").Value()) + assert.Equal(t, "@identity12", jsonquery.FindOne(routerPolicy1, "/identityRoles/*[1]").Value()) + + routerPolicy2 := jsonquery.FindOne(doc, "//edgeRouterPolicies/*[name='edge-router-D98X8WmjYH-system']") + assert.Equal(t, "@custroutet2", jsonquery.FindOne(routerPolicy2, "/edgeRouterRoles/*[1]").Value()) + assert.Equal(t, "@custroutet2", jsonquery.FindOne(routerPolicy2, "/identityRoles/*[1]").Value()) + + service1 := jsonquery.FindOne(doc, "//services/*[name='ssssimple']") + assert.Equal(t, "abcd", jsonquery.FindOne(service1, "/roleAttributes/*[1]").Value()) + assert.Equal(t, "service", jsonquery.FindOne(service1, "/roleAttributes/*[2]").Value()) + configs1 := []string{} + for _, node := range jsonquery.Find(service1, "/configs/*") { + configs1 = append(configs1, node.Value().(string)) + } + assert.Contains(t, configs1, "@ssssimple-intercept-config") + assert.Contains(t, configs1, "@ssssimple-host-config") + + service2 := jsonquery.FindOne(doc, "//services/*[name='asdfasdf']") + assert.Equal(t, "bcde", jsonquery.FindOne(service2, "/roleAttributes/*[1]").Value()) + assert.Empty(t, jsonquery.Find(service2, "/configs/*")) + +} diff --git a/ziti/cmd/ascode/download/download.go b/ziti/cmd/ascode/download/download.go new file mode 100644 index 000000000..dcf683787 --- /dev/null +++ b/ziti/cmd/ascode/download/download.go @@ -0,0 +1,399 @@ +/* + Copyright NetFoundry Inc. + + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at + + https://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. +*/ + +package download + +import ( + "encoding/json" + "errors" + "fmt" + "github.com/judedaryl/go-arrayutils" + "github.com/michaelquigley/pfxlog" + "github.com/openziti/edge-api/rest_management_api_client" + "github.com/openziti/ziti/internal" + "github.com/openziti/ziti/internal/rest/mgmt" + "github.com/openziti/ziti/ziti/cmd/edge" + c "github.com/openziti/ziti/ziti/constants" + "github.com/patrickmn/go-cache" + "github.com/sirupsen/logrus" + "github.com/spf13/cobra" + "github.com/spf13/viper" + "io" + "os" + "slices" + "strings" +) + +var log = pfxlog.Logger() + +type Download struct { + loginOpts edge.LoginOptions + client *rest_management_api_client.ZitiEdgeManagement + + verbose bool + + ofJson bool + ofYaml bool + + file *os.File + filename string + + configCache *cache.Cache + configTypeCache *cache.Cache + authPolicyCache *cache.Cache + externalJwtCache *cache.Cache +} + +var output Output + +func NewDownload(loginOpts edge.LoginOptions, client *rest_management_api_client.ZitiEdgeManagement, ofJson bool, ofYaml bool, file *os.File, filename string) Download { + d := Download{} + d.loginOpts = loginOpts + d.client = client + d.ofJson = ofJson + d.ofYaml = ofYaml + d.file = file + d.filename = filename + return d +} + +func NewDownloadCmd(out io.Writer, errOut io.Writer) *cobra.Command { + + d := &Download{} + downloadCmd := &cobra.Command{ + Use: "export [entity]", + Short: "Export Ziti entities", + Long: "Export all or selected Ziti entities.\n" + + "Valid entities are: [all|ca/certificate-authority|identity|edge-router|service|config|config-type|service-policy|edgerouter-policy|service-edgerouter-policy|external-jwt-signer|auth-policy|posture-check] (default all)", + Args: cobra.MinimumNArgs(0), + PersistentPreRun: func(cmd *cobra.Command, args []string) { + err := d.Init(out) + if err != nil { + panic(err) + } + }, + Run: func(cmd *cobra.Command, args []string) { + err := d.Execute(args) + if err != nil { + panic(err) + } + }, + Hidden: true, + } + + v := viper.New() + + // When we bind flags to environment variables expect that the + // environment variables are prefixed, d.g. a flag like --number + // binds to an environment variable STING_NUMBER. This helps + // avoid conflicts. + viper.SetEnvPrefix(c.ZITI) // All env vars we seek will be prefixed with "ZITI_" + + // Environment variables can't have dashes in them, so bind them to their equivalent + // keys with underscores, d.g. --favorite-color to STING_FAVORITE_COLOR + v.SetEnvKeyReplacer(strings.NewReplacer("-", "_")) + + v.AutomaticEnv() + + downloadCmd.Flags().BoolVar(&d.ofJson, "json", true, "Output in JSON") + downloadCmd.Flags().BoolVar(&d.ofYaml, "yaml", false, "Output in YAML") + downloadCmd.MarkFlagsMutuallyExclusive("json", "yaml") + + downloadCmd.PersistentFlags().StringVarP(&d.filename, "output-file", "o", "", "Write output to local file") + + downloadCmd.PersistentFlags().BoolVarP(&d.verbose, "verbose", "v", false, "Enable verbose logging") + + edge.AddLoginFlags(downloadCmd, &d.loginOpts) + d.loginOpts.Out = out + d.loginOpts.Err = errOut + + return downloadCmd +} + +func (d *Download) Init(out io.Writer) error { + logLvl := logrus.InfoLevel + if d.verbose { + logLvl = logrus.DebugLevel + } + + pfxlog.GlobalInit(logLvl, pfxlog.DefaultOptions().Color()) + internal.ConfigureLogFormat(logLvl) + + client, err := mgmt.NewClient() + if err != nil { + loginErr := d.loginOpts.Run() + if loginErr != nil { + log.Fatal(err) + } + client, err = mgmt.NewClient() + if err != nil { + log.Fatal(err) + } + } + d.client = client + + if d.filename != "" { + o, err := NewOutputToFile(d.verbose, d.ofJson, d.ofYaml, d.filename) + if err != nil { + return err + } + output = *o + } else { + o, err := NewOutputToWriter(d.verbose, d.ofJson, d.ofYaml, out) + if err != nil { + return err + } + output = *o + } + + return nil +} + +func (d *Download) Execute(input []string) error { + + args := arrayutils.Map(input, strings.ToLower) + + d.authPolicyCache = cache.New(cache.NoExpiration, cache.NoExpiration) + d.configCache = cache.New(cache.NoExpiration, cache.NoExpiration) + d.configTypeCache = cache.New(cache.NoExpiration, cache.NoExpiration) + d.externalJwtCache = cache.New(cache.NoExpiration, cache.NoExpiration) + + result := map[string]interface{}{} + + all := slices.Contains(args, "all") || len(args) == 0 + if all || + slices.Contains(args, "ca") || slices.Contains(args, "cas") || + slices.Contains(args, "certificate-authority") || slices.Contains(args, "certificate-authorities") { + if d.verbose { + log.Debug("Processing Certificate Authorities") + } + cas, err := d.GetCertificateAuthorities() + if err != nil { + return err + } + result["certificateAuthorities"] = cas + } + if all || + slices.Contains(args, "identity") || slices.Contains(args, "identities") { + if d.verbose { + log.Debug("Processing Identities") + } + identities, err := d.GetIdentities() + if err != nil { + return err + } + result["identities"] = identities + } + + if all || + slices.Contains(args, "edge-router") || slices.Contains(args, "edge-routers") || + slices.Contains(args, "er") || slices.Contains(args, "ers") { + if d.verbose { + log.Debug("Processing Edge Routers") + } + routers, err := d.GetEdgeRouters() + if err != nil { + return err + } + result["routers"] = routers + } + if all || + slices.Contains(args, "service") || slices.Contains(args, "services") { + if d.verbose { + log.Debug("Processing Services") + } + services, err := d.GetServices() + if err != nil { + return err + } + result["services"] = services + } + if all || + slices.Contains(args, "config") || slices.Contains(args, "configs") { + if d.verbose { + log.Debug("Processing Configs") + } + configs, err := d.GetConfigs() + if err != nil { + return err + } + result["configs"] = configs + } + if all || + slices.Contains(args, "config-type") || slices.Contains(args, "config-types") { + if d.verbose { + log.Debug("Processing Config Types") + } + configTypes, err := d.GetConfigTypes() + if err != nil { + return err + } + result["configTypes"] = configTypes + } + if all || + slices.Contains(args, "service-policy") || slices.Contains(args, "service-policies") { + if d.verbose { + log.Debug("Processing Service Policies") + } + servicePolicies, err := d.GetServicePolicies() + if err != nil { + return err + } + result["servicePolicies"] = servicePolicies + } + if all || + slices.Contains(args, "edgerouter-policy") || slices.Contains(args, "edgerouter-policies") { + if d.verbose { + log.Debug("Processing Router Policies") + } + routerPolicies, err := d.GetRouterPolicies() + if err != nil { + return err + } + result["edgeRouterPolicies"] = routerPolicies + } + if all || + slices.Contains(args, "service-edgerouter-policy") || slices.Contains(args, "service-edgerouter-policies") { + if d.verbose { + log.Debug("Processing Service EdgeRouter Policies") + } + serviceRouterPolicies, err := d.GetServiceEdgeRouterPolicies() + if err != nil { + return err + } + result["serviceEdgeRouterPolicies"] = serviceRouterPolicies + } + if all || + slices.Contains(args, "external-jwt-signer") || slices.Contains(args, "external-jwt-signers") { + if d.verbose { + log.Debug("Processing External JWT Signers") + } + externalJwtSigners, err := d.GetExternalJwtSigners() + if err != nil { + return err + } + result["externalJwtSigners"] = externalJwtSigners + } + if all || + slices.Contains(args, "auth-policy") || slices.Contains(args, "auth-policies") { + if d.verbose { + log.Debug("Processing Auth Policies") + } + authPolicies, err := d.GetAuthPolicies() + if err != nil { + return err + } + result["authPolicies"] = authPolicies + } + if all || + slices.Contains(args, "posture-check") || slices.Contains(args, "posture-checks") { + if d.verbose { + log.Debug("Processing Posture Checks") + } + postureChecks, err := d.GetPostureChecks() + if err != nil { + return err + } + result["postureChecks"] = postureChecks + } + + if d.verbose { + log.Debug("Download complete") + } + + err := output.Write(result) + if err != nil { + return err + } + if d.file != nil { + err := d.file.Close() + if err != nil { + return err + } + } + + return nil +} + +type ClientCount func() (int64, error) +type ClientList func(offset *int64, limit *int64) ([]interface{}, error) +type EntityProcessor func(item interface{}) (map[string]interface{}, error) + +func (d *Download) getEntities(entityName string, count ClientCount, list ClientList, processor EntityProcessor) ([]map[string]interface{}, error) { + + totalCount, countErr := count() + if countErr != nil { + return nil, errors.Join(errors.New("error reading total number of "+entityName), countErr) + } + + result := []map[string]interface{}{} + + offset := int64(0) + limit := int64(500) + more := true + for more { + resp, err := list(&offset, &limit) + _, _ = fmt.Fprintf(os.Stderr, "\u001B[2KReading %d/%d %s\r", offset, totalCount, entityName) + if err != nil { + return nil, errors.Join(errors.New("error reading "+entityName), err) + } + + for _, item := range resp { + m, err := processor(item) + if err != nil { + return nil, err + } + if m != nil { + result = append(result, m) + } + } + + more = offset < totalCount + offset += limit + } + + _, _ = fmt.Fprintf(os.Stderr, "\u001B[2KRead %d %s\r\n", len(result), entityName) + + return result, nil + +} + +func (d *Download) ToMap(input interface{}) map[string]interface{} { + jsonData, _ := json.MarshalIndent(input, "", "") + m := map[string]interface{}{} + err := json.Unmarshal(jsonData, &m) + if err != nil { + log.WithError(err).Error("error converting input to map") + return map[string]interface{}{} + } + return m +} + +func (d *Download) defaultRoleAttributes(m map[string]interface{}) { + if m["roleAttributes"] == nil { + m["roleAttributes"] = []string{} + } +} + +func (d *Download) Filter(m map[string]interface{}, properties []string) { + + // remove any properties that are not requested + for k := range m { + if slices.Contains(properties, k) { + delete(m, k) + } + } +} diff --git a/ziti/cmd/ascode/download/download_auth_policies.go b/ziti/cmd/ascode/download/download_auth_policies.go new file mode 100644 index 000000000..f04fe94aa --- /dev/null +++ b/ziti/cmd/ascode/download/download_auth_policies.go @@ -0,0 +1,110 @@ +/* + Copyright NetFoundry Inc. + + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at + + https://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. +*/ + +package download + +import ( + "github.com/openziti/edge-api/rest_management_api_client/auth_policy" + "github.com/openziti/edge-api/rest_management_api_client/external_jwt_signer" + "github.com/openziti/edge-api/rest_model" + common "github.com/openziti/ziti/internal/ascode" +) + +func (d Download) GetAuthPolicies() ([]map[string]interface{}, error) { + + return d.getEntities( + "AuthPolicies", + func() (int64, error) { + limit := int64(1) + resp, err := d.client.AuthPolicy.ListAuthPolicies( + &auth_policy.ListAuthPoliciesParams{Limit: &limit}, nil) + if err != nil { + return -1, err + } + return *resp.GetPayload().Meta.Pagination.TotalCount, nil + + }, + func(offset *int64, limit *int64) ([]interface{}, error) { + resp, err := d.client.AuthPolicy.ListAuthPolicies( + &auth_policy.ListAuthPoliciesParams{Limit: limit, Offset: offset}, nil) + if err != nil { + return nil, err + } + entities := make([]interface{}, len(resp.GetPayload().Data)) + for i, c := range resp.GetPayload().Data { + entities[i] = interface{}(c) + } + return entities, nil + }, + func(entity interface{}) (map[string]interface{}, error) { + + item := entity.(*rest_model.AuthPolicyDetail) + + if *item.Name != "Default" { + // convert to a map of values + m := d.ToMap(item) + + // filter unwanted properties + d.Filter(m, []string{"id", "_links", "createdAt", "updatedAt"}) + + // deleting Primary so we can reconstruct it + delete(m, "primary") + primary := d.ToMap(item.Primary) + m["primary"] = primary + // deleting ExtJwt so we can reconstruct it + delete(primary, "extJwt") + extJwt := d.ToMap(item.Primary.ExtJWT) + primary["extJwt"] = extJwt + // deleting AllowedSigners because it needs to use a reference to the name instead of the ID + delete(extJwt, "allowedSigners") + signers := []string{} + for _, signer := range item.Primary.ExtJWT.AllowedSigners { + extJwtSigner, lookupErr := common.GetItemFromCache(d.externalJwtCache, signer, func(id string) (interface{}, error) { + return d.client.ExternalJWTSigner.DetailExternalJWTSigner( + &external_jwt_signer.DetailExternalJWTSignerParams{ID: id}, nil) + }) + if lookupErr != nil { + return nil, lookupErr + } + signers = append(signers, "@"+*extJwtSigner.(*external_jwt_signer.DetailExternalJWTSignerOK).Payload.Data.Name) + } + extJwt["allowedSigners"] = signers + + // if a secondary jwt signer is set, update it with a name reference instead of the id + if item.Secondary.RequireExtJWTSigner != nil { + // deleting Secondary so we can reconstruct it + delete(m, "secondary") + secondary := d.ToMap(item.Secondary) + m["secondary"] = secondary + + // deleting RequiredExtJwtSigner because it needs to use a reference to the name instead of the ID + delete(secondary, "requiredExtJwtSigner") + requiredExtJwtSigner := d.ToMap(item.Secondary.RequireExtJWTSigner) + extJwtSigner, lookupErr := common.GetItemFromCache(d.externalJwtCache, *item.Secondary.RequireExtJWTSigner, func(id string) (interface{}, error) { + return d.client.ExternalJWTSigner.DetailExternalJWTSigner(&external_jwt_signer.DetailExternalJWTSignerParams{ID: id}, nil) + }) + if lookupErr != nil { + return nil, lookupErr + } + requiredExtJwtSigner["requiredExtJwtSigner"] = "@" + *extJwtSigner.(*external_jwt_signer.DetailExternalJWTSignerOK).Payload.Data.Name + } + + return m, nil + } + return nil, nil + }) + +} diff --git a/ziti/cmd/ascode/download/download_certificate_authorities.go b/ziti/cmd/ascode/download/download_certificate_authorities.go new file mode 100644 index 000000000..d172c418b --- /dev/null +++ b/ziti/cmd/ascode/download/download_certificate_authorities.go @@ -0,0 +1,62 @@ +/* + Copyright NetFoundry Inc. + + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at + + https://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. +*/ + +package download + +import ( + "github.com/openziti/edge-api/rest_management_api_client/certificate_authority" + "github.com/openziti/edge-api/rest_model" +) + +func (d Download) GetCertificateAuthorities() ([]map[string]interface{}, error) { + + return d.getEntities( + "CertificateAuthorities", + + func() (int64, error) { + limit := int64(1) + resp, err := d.client.CertificateAuthority.ListCas(&certificate_authority.ListCasParams{Limit: &limit}, nil) + if err != nil { + return -1, err + } + return *resp.GetPayload().Meta.Pagination.TotalCount, nil + }, + + func(offset *int64, limit *int64) ([]interface{}, error) { + resp, err := d.client.CertificateAuthority.ListCas(&certificate_authority.ListCasParams{Offset: offset, Limit: limit}, nil) + if err != nil { + return nil, err + } + entities := make([]interface{}, len(resp.GetPayload().Data)) + for i, c := range resp.GetPayload().Data { + entities[i] = interface{}(c) + } + return entities, nil + }, + + func(entity interface{}) (map[string]interface{}, error) { + + item := entity.(*rest_model.CaDetail) + + // convert to a map of values + m := d.ToMap(item) + + // filter unwanted properties + d.Filter(m, []string{"id", "_links", "createdAt", "updatedAt"}) + + return m, nil + }) +} diff --git a/ziti/cmd/ascode/download/download_config_types.go b/ziti/cmd/ascode/download/download_config_types.go new file mode 100644 index 000000000..ea4d5f4c4 --- /dev/null +++ b/ziti/cmd/ascode/download/download_config_types.go @@ -0,0 +1,64 @@ +/* + Copyright NetFoundry Inc. + + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at + + https://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. +*/ + +package download + +import ( + "github.com/openziti/edge-api/rest_management_api_client/config" + "github.com/openziti/edge-api/rest_model" + "slices" +) + +func (d Download) GetConfigTypes() ([]map[string]interface{}, error) { + + return d.getEntities( + "ConfigTypes", + + func() (int64, error) { + limit := int64(1) + resp, err := d.client.Config.ListConfigTypes(&config.ListConfigTypesParams{Limit: &limit}, nil) + if err != nil { + return -1, err + } + return *resp.GetPayload().Meta.Pagination.TotalCount, nil + }, + + func(offset *int64, limit *int64) ([]interface{}, error) { + resp, _ := d.client.Config.ListConfigTypes(&config.ListConfigTypesParams{Limit: limit, Offset: offset}, nil) + entities := make([]interface{}, len(resp.GetPayload().Data)) + for i, c := range resp.GetPayload().Data { + entities[i] = interface{}(c) + } + return entities, nil + }, + + func(entity interface{}) (map[string]interface{}, error) { + + item := entity.(*rest_model.ConfigTypeDetail) + wellknownTypes := []string{"intercept.v1", "host.v1", "host.v2", "ziti-tunneler-server.v1", "ziti-tunneler-client.v1"} + + // don't include the wellknown types, they already exist when a network is created + if slices.Contains(wellknownTypes, *item.Name) { + return nil, nil + } + + // convert to a map of values + m := d.ToMap(item) + d.Filter(m, []string{"id", "_links", "createdAt", "updatedAt"}) + + return m, nil + }) +} diff --git a/ziti/cmd/ascode/download/download_configs.go b/ziti/cmd/ascode/download/download_configs.go new file mode 100644 index 000000000..410b4d7ac --- /dev/null +++ b/ziti/cmd/ascode/download/download_configs.go @@ -0,0 +1,72 @@ +/* + Copyright NetFoundry Inc. + + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at + + https://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. +*/ + +package download + +import ( + "errors" + "github.com/openziti/edge-api/rest_management_api_client/config" + "github.com/openziti/edge-api/rest_model" + common "github.com/openziti/ziti/internal/ascode" +) + +func (d Download) GetConfigs() ([]map[string]interface{}, error) { + + return d.getEntities( + "Configs", + + func() (int64, error) { + limit := int64(1) + resp, err := d.client.Config.ListConfigs(&config.ListConfigsParams{Limit: &limit}, nil) + if err != nil { + return -1, err + } + return *resp.GetPayload().Meta.Pagination.TotalCount, nil + }, + + func(offset *int64, limit *int64) ([]interface{}, error) { + resp, _ := d.client.Config.ListConfigs(&config.ListConfigsParams{Limit: limit, Offset: offset}, nil) + entities := make([]interface{}, len(resp.GetPayload().Data)) + for i, c := range resp.GetPayload().Data { + entities[i] = interface{}(c) + } + return entities, nil + }, + + func(entity interface{}) (map[string]interface{}, error) { + + item := entity.(*rest_model.ConfigDetail) + + // convert to a map of values + m := d.ToMap(item) + + // filter unwanted properties + d.Filter(m, []string{"id", "_links", "createdAt", "updatedAt"}) + + // translate ids to names + delete(m, "configType") + delete(m, "configTypeId") + configType, lookupErr := common.GetItemFromCache(d.configTypeCache, *item.ConfigTypeID, func(id string) (interface{}, error) { + return d.client.Config.DetailConfigType(&config.DetailConfigTypeParams{ID: id}, nil) + }) + if lookupErr != nil { + return nil, errors.Join(errors.New("error reading Auth Policy: "+*item.ConfigTypeID), lookupErr) + } + m["configType"] = "@" + *configType.(*config.DetailConfigTypeOK).Payload.Data.Name + + return m, nil + }) +} diff --git a/ziti/cmd/ascode/download/download_edgerouter_policies.go b/ziti/cmd/ascode/download/download_edgerouter_policies.go new file mode 100644 index 000000000..a1e82fa74 --- /dev/null +++ b/ziti/cmd/ascode/download/download_edgerouter_policies.go @@ -0,0 +1,75 @@ +/* + Copyright NetFoundry Inc. + + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at + + https://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. +*/ + +package download + +import ( + "github.com/openziti/edge-api/rest_management_api_client/edge_router_policy" + "github.com/openziti/edge-api/rest_model" +) + +func (d Download) GetRouterPolicies() ([]map[string]interface{}, error) { + + return d.getEntities( + "EdgeRouterPolicies", + + func() (int64, error) { + limit := int64(1) + resp, err := d.client.EdgeRouterPolicy.ListEdgeRouterPolicies(&edge_router_policy.ListEdgeRouterPoliciesParams{Limit: &limit}, nil) + if err != nil { + return -1, err + } + return *resp.GetPayload().Meta.Pagination.TotalCount, nil + }, + + func(offset *int64, limit *int64) ([]interface{}, error) { + resp, err := d.client.EdgeRouterPolicy.ListEdgeRouterPolicies(&edge_router_policy.ListEdgeRouterPoliciesParams{Limit: limit, Offset: offset}, nil) + if err != nil { + return nil, err + } + entities := make([]interface{}, len(resp.GetPayload().Data)) + for i, c := range resp.GetPayload().Data { + entities[i] = interface{}(c) + } + return entities, nil + }, + + func(entity interface{}) (map[string]interface{}, error) { + + item := entity.(*rest_model.EdgeRouterPolicyDetail) + + // convert to a map of values + m := d.ToMap(item) + + // translate attributes so they don't reference ids + identityRoles := []string{} + for _, role := range item.IdentityRolesDisplay { + identityRoles = append(identityRoles, role.Name) + } + m["identityRoles"] = identityRoles + edgeRouterRoles := []string{} + for _, role := range item.EdgeRouterRolesDisplay { + edgeRouterRoles = append(edgeRouterRoles, role.Name) + } + m["edgeRouterRoles"] = edgeRouterRoles + + // filter unwanted properties + d.Filter(m, []string{"id", "_links", "createdAt", "updatedAt", + "edgeRouterRolesDisplay", "identityRolesDisplay", "isSystem"}) + + return m, nil + }) +} diff --git a/ziti/cmd/ascode/download/download_edgerouters.go b/ziti/cmd/ascode/download/download_edgerouters.go new file mode 100644 index 000000000..15b5981e0 --- /dev/null +++ b/ziti/cmd/ascode/download/download_edgerouters.go @@ -0,0 +1,63 @@ +/* + Copyright NetFoundry Inc. + + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at + + https://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. +*/ + +package download + +import ( + "github.com/openziti/edge-api/rest_management_api_client/edge_router" + "github.com/openziti/edge-api/rest_model" +) + +func (d Download) GetEdgeRouters() ([]map[string]interface{}, error) { + + return d.getEntities( + "EdgeRouters", + func() (int64, error) { + limit := int64(1) + resp, err := d.client.EdgeRouter.ListEdgeRouters(&edge_router.ListEdgeRoutersParams{Limit: &limit}, nil) + if err != nil { + return -1, err + } + return *resp.GetPayload().Meta.Pagination.TotalCount, nil + }, + + func(offset *int64, limit *int64) ([]interface{}, error) { + resp, err := d.client.EdgeRouter.ListEdgeRouters(&edge_router.ListEdgeRoutersParams{Limit: limit, Offset: offset}, nil) + if err != nil { + return nil, err + } + entities := make([]interface{}, len(resp.GetPayload().Data)) + for i, c := range resp.GetPayload().Data { + entities[i] = interface{}(c) + } + return entities, nil + }, + + func(entity interface{}) (map[string]interface{}, error) { + + item := entity.(*rest_model.EdgeRouterDetail) + + // convert to a map of values + m := d.ToMap(item) + d.defaultRoleAttributes(m) + + // filter unwanted properties + d.Filter(m, []string{"id", "_links", "createdAt", "updatedAt", + "cost", "fingerprint", "isVerified", "isOnline", "enrollmentJwt", "enrollmentCreatedAt", "enrollmentExpiresAt", "syncStatus", "versionInfo", "certPem", "supportedProtocols"}) + + return m, nil + }) +} diff --git a/ziti/cmd/ascode/download/download_external_jwt_signers.go b/ziti/cmd/ascode/download/download_external_jwt_signers.go new file mode 100644 index 000000000..75efeb9d8 --- /dev/null +++ b/ziti/cmd/ascode/download/download_external_jwt_signers.go @@ -0,0 +1,64 @@ +/* + Copyright NetFoundry Inc. + + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at + + https://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. +*/ + +package download + +import ( + "github.com/openziti/edge-api/rest_management_api_client/external_jwt_signer" + "github.com/openziti/edge-api/rest_model" +) + +func (d Download) GetExternalJwtSigners() ([]map[string]interface{}, error) { + + return d.getEntities( + "ExtJWTSigners", + + func() (int64, error) { + limit := int64(1) + resp, err := d.client.ExternalJWTSigner.ListExternalJWTSigners(&external_jwt_signer.ListExternalJWTSignersParams{Limit: &limit}, nil) + if err != nil { + return -1, err + } + return *resp.GetPayload().Meta.Pagination.TotalCount, nil + }, + + func(offset *int64, limit *int64) ([]interface{}, error) { + resp, err := d.client.ExternalJWTSigner.ListExternalJWTSigners( + &external_jwt_signer.ListExternalJWTSignersParams{Offset: offset, Limit: limit}, nil) + if err != nil { + return nil, err + } + entities := make([]interface{}, len(resp.GetPayload().Data)) + for i, c := range resp.GetPayload().Data { + entities[i] = interface{}(c) + } + return entities, nil + }, + + func(entity interface{}) (map[string]interface{}, error) { + + item := entity.(*rest_model.ExternalJWTSignerDetail) + + // convert to a map of values + m := d.ToMap(item) + + // filter unwanted properties + d.Filter(m, []string{"id", "_links", "createdAt", "updatedAt", + "notBefore", "notAfter", "commonName"}) + + return m, nil + }) +} diff --git a/ziti/cmd/ascode/download/download_identities.go b/ziti/cmd/ascode/download/download_identities.go new file mode 100644 index 000000000..7c453f548 --- /dev/null +++ b/ziti/cmd/ascode/download/download_identities.go @@ -0,0 +1,88 @@ +/* + Copyright NetFoundry Inc. + + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at + + https://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. +*/ + +package download + +import ( + "errors" + "github.com/openziti/edge-api/rest_management_api_client/auth_policy" + "github.com/openziti/edge-api/rest_management_api_client/identity" + "github.com/openziti/edge-api/rest_model" + common "github.com/openziti/ziti/internal/ascode" +) + +func (d Download) GetIdentities() ([]map[string]interface{}, error) { + + return d.getEntities( + "Identities", + + func() (int64, error) { + limit := int64(1) + resp, err := d.client.Identity.ListIdentities(&identity.ListIdentitiesParams{Limit: &limit}, nil) + if err != nil { + return -1, err + } + return *resp.GetPayload().Meta.Pagination.TotalCount, nil + }, + + func(offset *int64, limit *int64) ([]interface{}, error) { + resp, err := d.client.Identity.ListIdentities(&identity.ListIdentitiesParams{Offset: offset, Limit: limit}, nil) + if err != nil { + return nil, err + } + entities := make([]interface{}, len(resp.GetPayload().Data)) + for i, c := range resp.GetPayload().Data { + entities[i] = interface{}(c) + } + return entities, nil + }, + + func(entity interface{}) (map[string]interface{}, error) { + + item := entity.(*rest_model.IdentityDetail) + + // only download Default identities and not the default admin + if *item.TypeID != "Router" && !*item.IsDefaultAdmin { + + // convert to a map of values + m := d.ToMap(item) + d.defaultRoleAttributes(m) + + // filter unwanted properties + d.Filter(m, []string{"id", "_links", "createdAt", "updatedAt", + "defaultHostingCost", "defaultHostingPrecedence", "hasApiSession", "serviceHostingPrecedences", "enrollment", + "appData", "sdkInfo", "disabledAt", "disabledUntil", "serviceHostingCosts", "envInfo", "authenticators", "type", "authPolicyId", + "hasRouterConnection", "hasEdgeRouterConnection"}) + + if item.DisabledUntil != nil { + m["disabledUntil"] = item.DisabledUntil + } + + // translate ids to names + authPolicy, lookupErr := common.GetItemFromCache(d.authPolicyCache, *item.AuthPolicyID, func(id string) (interface{}, error) { + return d.client.AuthPolicy.DetailAuthPolicy(&auth_policy.DetailAuthPolicyParams{ID: id}, nil) + }) + if lookupErr != nil { + return nil, errors.Join(errors.New("error reading Auth Policy: "+*item.AuthPolicyID), lookupErr) + } + m["authPolicy"] = "@" + *authPolicy.(*auth_policy.DetailAuthPolicyOK).GetPayload().Data.Name + return m, nil + } + + return nil, nil + }) + +} diff --git a/ziti/cmd/ascode/download/download_posture_checks.go b/ziti/cmd/ascode/download/download_posture_checks.go new file mode 100644 index 000000000..e139726e0 --- /dev/null +++ b/ziti/cmd/ascode/download/download_posture_checks.go @@ -0,0 +1,57 @@ +/* + Copyright NetFoundry Inc. + + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at + + https://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. +*/ + +package download + +import ( + "github.com/openziti/edge-api/rest_management_api_client/posture_checks" +) + +func (d Download) GetPostureChecks() ([]map[string]interface{}, error) { + + return d.getEntities( + "PostureChecks", + + func() (int64, error) { + limit := int64(1) + resp, err := d.client.PostureChecks.ListPostureChecks(&posture_checks.ListPostureChecksParams{Limit: &limit}, nil) + if err != nil { + return -1, err + } + return *resp.GetPayload().Meta.Pagination.TotalCount, nil + }, + + func(offset *int64, limit *int64) ([]interface{}, error) { + resp, _ := d.client.PostureChecks.ListPostureChecks(&posture_checks.ListPostureChecksParams{Limit: limit, Offset: offset}, nil) + entities := make([]interface{}, len(resp.GetPayload().Data())) + for i, c := range resp.GetPayload().Data() { + entities[i] = interface{}(c) + } + return entities, nil + }, + + func(entity interface{}) (map[string]interface{}, error) { + + // convert to a map of values + m := d.ToMap(entity) + + // filter unwanted properties + d.Filter(m, []string{"id", "_links", "createdAt", "updatedAt", + "version"}) + + return m, nil + }) +} diff --git a/ziti/cmd/ascode/download/download_service_edgerouter_policies.go b/ziti/cmd/ascode/download/download_service_edgerouter_policies.go new file mode 100644 index 000000000..284633879 --- /dev/null +++ b/ziti/cmd/ascode/download/download_service_edgerouter_policies.go @@ -0,0 +1,75 @@ +/* + Copyright NetFoundry Inc. + + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at + + https://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. +*/ + +package download + +import ( + "github.com/openziti/edge-api/rest_management_api_client/service_edge_router_policy" + "github.com/openziti/edge-api/rest_model" +) + +func (d Download) GetServiceEdgeRouterPolicies() ([]map[string]interface{}, error) { + + return d.getEntities( + "ServiceEdgeRouterPolicies", + + func() (int64, error) { + limit := int64(1) + resp, err := d.client.ServiceEdgeRouterPolicy.ListServiceEdgeRouterPolicies(&service_edge_router_policy.ListServiceEdgeRouterPoliciesParams{Limit: &limit}, nil) + if err != nil { + return -1, err + } + return *resp.GetPayload().Meta.Pagination.TotalCount, nil + }, + + func(offset *int64, limit *int64) ([]interface{}, error) { + resp, err := d.client.ServiceEdgeRouterPolicy.ListServiceEdgeRouterPolicies(&service_edge_router_policy.ListServiceEdgeRouterPoliciesParams{Limit: limit, Offset: offset}, nil) + if err != nil { + return nil, err + } + entities := make([]interface{}, len(resp.GetPayload().Data)) + for i, c := range resp.GetPayload().Data { + entities[i] = interface{}(c) + } + return entities, nil + }, + + func(entity interface{}) (map[string]interface{}, error) { + + item := entity.(*rest_model.ServiceEdgeRouterPolicyDetail) + + // convert to a map of values + m := d.ToMap(item) + + // translate attributes so they don't reference ids + serviceRoles := []string{} + for _, role := range item.ServiceRolesDisplay { + serviceRoles = append(serviceRoles, role.Name) + } + m["serviceRoles"] = serviceRoles + edgeRouterRoles := []string{} + for _, role := range item.EdgeRouterRolesDisplay { + edgeRouterRoles = append(edgeRouterRoles, role.Name) + } + m["edgeRouterRoles"] = edgeRouterRoles + + // filter unwanted properties + d.Filter(m, []string{"id", "_links", "createdAt", "updatedAt", + "edgeRouterRolesDisplay", "serviceRolesDisplay", "isSystem"}) + + return m, nil + }) +} diff --git a/ziti/cmd/ascode/download/download_service_policies.go b/ziti/cmd/ascode/download/download_service_policies.go new file mode 100644 index 000000000..94b2cacc8 --- /dev/null +++ b/ziti/cmd/ascode/download/download_service_policies.go @@ -0,0 +1,81 @@ +/* + Copyright NetFoundry Inc. + + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at + + https://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. +*/ + +package download + +import ( + "github.com/openziti/edge-api/rest_management_api_client/service_policy" + "github.com/openziti/edge-api/rest_model" +) + +func (d Download) GetServicePolicies() ([]map[string]interface{}, error) { + + return d.getEntities( + "ServicePolicies", + + func() (int64, error) { + limit := int64(1) + resp, err := d.client.ServicePolicy.ListServicePolicies(&service_policy.ListServicePoliciesParams{Limit: &limit}, nil) + if err != nil { + return -1, err + } + return *resp.GetPayload().Meta.Pagination.TotalCount, nil + }, + + func(offset *int64, limit *int64) ([]interface{}, error) { + resp, err := d.client.ServicePolicy.ListServicePolicies(&service_policy.ListServicePoliciesParams{Limit: limit, Offset: offset}, nil) + if err != nil { + return nil, err + } + entities := make([]interface{}, len(resp.GetPayload().Data)) + for i, c := range resp.GetPayload().Data { + entities[i] = interface{}(c) + } + return entities, nil + }, + + func(entity interface{}) (map[string]interface{}, error) { + + item := entity.(*rest_model.ServicePolicyDetail) + + // convert to a map of values + m := d.ToMap(item) + + // translate attributes so they don't reference ids + identityRoles := []string{} + for _, role := range item.IdentityRolesDisplay { + identityRoles = append(identityRoles, role.Name) + } + m["identityRoles"] = identityRoles + serviceRoles := []string{} + for _, role := range item.ServiceRolesDisplay { + serviceRoles = append(serviceRoles, role.Name) + } + m["serviceRoles"] = serviceRoles + postureCheckRoles := []string{} + for _, role := range item.PostureCheckRolesDisplay { + identityRoles = append(identityRoles, role.Name) + } + m["postureCheckRoles"] = postureCheckRoles + + // filter unwanted properties + d.Filter(m, []string{"id", "_links", "createdAt", "updatedAt", + "serviceRolesDisplay", "identityRolesDisplay", "postureCheckRolesDisplay", "isSystem"}) + + return m, nil + }, + ) +} diff --git a/ziti/cmd/ascode/download/download_services.go b/ziti/cmd/ascode/download/download_services.go new file mode 100644 index 000000000..50d18bd45 --- /dev/null +++ b/ziti/cmd/ascode/download/download_services.go @@ -0,0 +1,82 @@ +/* + Copyright NetFoundry Inc. + + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at + + https://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. +*/ + +package download + +import ( + "errors" + "github.com/openziti/edge-api/rest_management_api_client/config" + "github.com/openziti/edge-api/rest_management_api_client/service" + "github.com/openziti/edge-api/rest_model" + common "github.com/openziti/ziti/internal/ascode" +) + +func (d Download) GetServices() ([]map[string]interface{}, error) { + + return d.getEntities( + "Services", + + func() (int64, error) { + limit := int64(1) + resp, err := d.client.Service.ListServices(&service.ListServicesParams{Limit: &limit}, nil) + if err != nil { + return -1, err + } + return *resp.GetPayload().Meta.Pagination.TotalCount, nil + }, + + func(offset *int64, limit *int64) ([]interface{}, error) { + resp, err := d.client.Service.ListServices(&service.ListServicesParams{Limit: limit, Offset: offset}, nil) + if err != nil { + return nil, err + } + entities := make([]interface{}, len(resp.GetPayload().Data)) + for i, c := range resp.GetPayload().Data { + entities[i] = interface{}(c) + } + return entities, nil + }, + + func(entity interface{}) (map[string]interface{}, error) { + + item := entity.(*rest_model.ServiceDetail) + + // convert to a map of values + m := d.ToMap(item) + + d.defaultRoleAttributes(m) + + // filter unwanted properties + d.Filter(m, []string{"id", "_links", "createdAt", "updatedAt", + "configs", "config", "data", "postureQueries", "permissions", "maxIdleTimeMillis"}) + + // translate ids to names + var configNames []string + for _, c := range item.Configs { + configDetail, lookupErr := common.GetItemFromCache(d.configCache, c, func(id string) (interface{}, error) { + return d.client.Config.DetailConfig(&config.DetailConfigParams{ID: id}, nil) + }) + if lookupErr != nil { + return nil, errors.Join(errors.New("error reading Config: "+c), lookupErr) + } + configNames = append(configNames, "@"+*configDetail.(*config.DetailConfigOK).Payload.Data.Name) + } + delete(m, "configs") + m["configs"] = configNames + + return m, nil + }) +} diff --git a/ziti/cmd/ascode/download/output.go b/ziti/cmd/ascode/download/output.go new file mode 100644 index 000000000..99a5a8fa2 --- /dev/null +++ b/ziti/cmd/ascode/download/output.go @@ -0,0 +1,140 @@ +/* + Copyright NetFoundry Inc. + + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at + + https://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. +*/ + +package download + +import ( + "bufio" + "encoding/json" + "fmt" + "gopkg.in/yaml.v3" + + "io" + "os" +) + +type Output struct { + outputJson bool + outputYaml bool + filename string + writer *bufio.Writer + verbose bool +} + +func NewOutputToFile(verbose bool, outputJson bool, outputYaml bool, filename string) (*Output, error) { + file, err := os.Create(filename) + if err != nil { + log.WithError(err).Error("Error creating file for writing") + return nil, err + } + writer := bufio.NewWriter(file) + output, err := NewOutputToWriter(verbose, outputJson, outputYaml, writer) + output.filename = filename + return output, err +} + +func NewOutputToWriter(verbose bool, outputJson bool, outputYaml bool, writer io.Writer) (*Output, error) { + output := Output{} + output.verbose = verbose + output.outputJson = outputJson + output.outputYaml = outputYaml + output.writer = bufio.NewWriter(writer) + return &output, nil +} + +func (output Output) Write(data any) error { + var formatted []byte + var err error + if output.outputYaml { + if output.verbose { + _, _ = fmt.Fprintf(os.Stderr, "\u001B[2KFormatting as Yaml\r\n") + } + formatted, err = output.ToYaml(data) + } else { + if output.verbose { + _, _ = fmt.Fprintf(os.Stderr, "\u001B[2KFormatting as JSON\r\n") + } + formatted, err = output.ToJson(data) + } + if err != nil { + return err + } + + if output.verbose { + if output.filename != "" { + _, _ = fmt.Fprintf(os.Stderr, "\u001B[2KWriting to file: %s\r\n", output.filename) + } else { + _, _ = fmt.Fprintf(os.Stderr, "\u001B[2KWriting output to writer\r\n") + } + } + bytes, err := output.writer.Write(formatted) + if err != nil { + log.WithError(err).Error("Error writing data to output") + return err + } + + if output.verbose { + if output.filename != "" { + log. + WithError(err). + WithFields(map[string]interface{}{ + "bytes": bytes, + "filename": output.filename, + }). + Debug("Wrote json data") + } else { + log. + WithField("bytes", bytes). + Debug("Wrote json data") + } + } + + err = output.writer.Flush() + if err != nil { + log. + WithError(err). + Error("Error flushing data to output") + return err + } + + return nil +} + +func (output Output) ToJson(data any) ([]byte, error) { + + jsonData, err := json.MarshalIndent(data, "", " ") + if err != nil { + log. + WithError(err). + Error("Error writing data as JSON") + return nil, err + } + + return jsonData, nil +} + +func (output Output) ToYaml(data any) ([]byte, error) { + + yamlData, err := yaml.Marshal(data) + if err != nil { + log. + WithError(err). + Error("Error writing data as Yaml") + return nil, err + } + + return yamlData, nil +} diff --git a/ziti/cmd/ascode/test.yaml b/ziti/cmd/ascode/test.yaml new file mode 100644 index 000000000..42381b7b8 --- /dev/null +++ b/ziti/cmd/ascode/test.yaml @@ -0,0 +1,624 @@ +authPolicies: + - name: NetFoundry Console Integration Auth Policy + primary: + cert: + allowExpiredCerts: false + allowed: false + extJwt: + allowed: true + allowedSigners: + - '@NetFoundry Console Integration External JWT Signer' + updb: + allowed: false + lockoutDurationMinutes: 0 + maxAttempts: 0 + minPasswordLength: 5 + requireMixedCase: false + requireNumberChar: false + requireSpecialChar: false + secondary: + requireTotp: false + tags: + network-id: 25ba1aa3-4468-445a-910e-93f5b425f2c1 + resource-id: 0b511399-82f4-416c-a074-0e3aba711e22 + - name: Test123 + primary: + cert: + allowExpiredCerts: false + allowed: false + extJwt: + allowed: true + allowedSigners: [] + updb: + allowed: true + lockoutDurationMinutes: 0 + maxAttempts: 5 + minPasswordLength: 5 + requireMixedCase: false + requireNumberChar: false + requireSpecialChar: false + secondary: + requireTotp: false + tags: {} +certificateAuthorities: [] +configTypes: + - name: Empty Config Type + schema: null + tags: {} +configs: + - configType: '@intercept.v1' + data: + addresses: + - mylocal.com + portRanges: + - high: 547 + low: 547 + protocols: + - tcp + - udp + name: service2-intercept-config + tags: {} + - configType: '@intercept.v1' + data: + addresses: + - testservice.com + portRanges: + - high: 8083 + low: 8083 + protocols: + - tcp + - udp + name: ssssimple-intercept-config + tags: {} + - configType: '@host.v1' + data: + address: docker-ac-web-server-1 + allowedProtocols: + - tcp + forwardProtocol: true + port: 80 + name: ssssimple-host-config + tags: {} + - configType: '@host.v1' + data: + address: 127.0.0.1 + allowedProtocols: + - tcp + forwardProtocol: true + port: 123 + name: test-123-host-config + tags: {} + - configType: '@intercept.v1' + data: + addresses: + - jettylocal.com + portRanges: + - high: 8080 + low: 8080 + protocols: + - tcp + - udp + name: service1-intercept-config + tags: {} + - configType: '@host.v1' + data: + address: localhost + allowedProtocols: + - tcp + forwardProtocol: true + port: 8080 + name: service1-host-config + tags: {} + - configType: '@host.v1' + data: + address: localhost + allowedProtocols: + - tcp + forwardProtocol: true + port: 546 + name: service2-host-config + tags: {} + - configType: '@ziti-tunneler-client.v1' + data: + hostname: 192.168.242.2 + port: 502 + name: json + tags: {} + - configType: '@intercept.v1' + data: + addresses: + - simplesvctest1.ziti + portRanges: + - high: 321 + low: 321 + protocols: + - tcp + - udp + name: rg-test-123-intercept-config + tags: {} + - configType: '@intercept.v1' + data: + addresses: + - simplesvctest1.ziti + portRanges: + - high: 123 + low: 123 + protocols: + - tcp + - udp + name: test-123-intercept-config + tags: {} + - configType: '@host.v1' + data: + address: 127.0.0.1 + allowedProtocols: + - tcp + forwardProtocol: true + port: 321 + name: rg-test-123-host-config + tags: {} +edgeRouterPolicies: + - edgeRouterRoles: + - '@public-router1' + identityRoles: + - '@identity12' + name: routerpolicy1 + semantic: AnyOf + tags: {} + - edgeRouterRoles: + - '@custroutet2' + identityRoles: + - '@custroutet2' + name: edge-router-D98X8WmjYH-system + semantic: AnyOf + tags: {} + - edgeRouterRoles: + - '@asd' + identityRoles: + - '@asd' + name: edge-router-ORKiRq5WIU-system + semantic: AnyOf + tags: {} + - edgeRouterRoles: + - '@public-router1' + identityRoles: + - '@public-router1' + name: edge-router-Qo6blWsoY-system + semantic: AnyOf + tags: {} + - edgeRouterRoles: + - '@vis-customer-router' + identityRoles: + - '@vis-customer-router' + name: edge-router-w0OpEWmoY-system + semantic: AnyOf + tags: {} +externalJwtSigners: + - audience: https://gateway.staging.netfoundry.io/cloudziti/25ba1aa3-4468-445a-910e-93f5b425f2c1 + certPem: null + claimsProperty: sub + clientId: null + enabled: true + externalAuthUrl: null + fingerprint: null + issuer: https://netfoundry.io/jwt/NYFw7IGJKNP9AaG45iwCj + jwksEndpoint: https://gateway.staging.netfoundry.io/network-auth/v1/public/.well-known/NYFw7IGJKNP9AaG45iwCj/jwks.json + kid: null + name: NetFoundry Console Integration External JWT Signer + scopes: null + tags: {} + useExternalId: false +identities: + - authPolicy: '@Default' + disabled: false + edgeRouterConnectionStatus: null + externalId: null + isDefaultAdmin: false + isMfaEnabled: false + isAdmin: false + name: vis-client + roleAttributes: + - client + tags: {} + typeId: Default + - authPolicy: '@NetFoundry Console Integration Auth Policy' + disabled: false + edgeRouterConnectionStatus: null + externalId: f1505b76-38ec-470b-9819-75984623c23d + isDefaultAdmin: false + isMfaEnabled: false + isAdmin: false + name: Vinay Lakshmaiah + roleAttributes: [] + tags: {} + typeId: Default + - authPolicy: '@NetFoundry Console Integration Auth Policy' + disabled: false + edgeRouterConnectionStatus: null + externalId: 962818be-b8d5-4c37-8e5b-e5082aa4ddbf + isDefaultAdmin: false + isMfaEnabled: false + isAdmin: false + name: harish donepudi + roleAttributes: [] + tags: {} + typeId: Default + - authPolicy: '@Default' + disabled: false + edgeRouterConnectionStatus: null + externalId: null + isDefaultAdmin: false + isMfaEnabled: false + isAdmin: false + name: identity12 + roleAttributes: + - bind + tags: {} + typeId: Default + - authPolicy: '@Default' + disabled: false + edgeRouterConnectionStatus: null + externalId: null + isDefaultAdmin: false + isMfaEnabled: false + isAdmin: false + name: Prashant + roleAttributes: [] + tags: {} + typeId: Default + - authPolicy: '@NetFoundry Console Integration Auth Policy' + disabled: false + edgeRouterConnectionStatus: null + externalId: 19fae786-dd8e-4d13-9864-588cee15be95 + isDefaultAdmin: false + isMfaEnabled: false + isAdmin: false + name: Loren Fouts + roleAttributes: [] + tags: {} + typeId: Default + - authPolicy: '@NetFoundry Console Integration Auth Policy' + disabled: false + edgeRouterConnectionStatus: null + externalId: 1faad12a-1fc0-4d8a-a1e6-b2f993907017 + isDefaultAdmin: false + isMfaEnabled: false + isAdmin: false + name: kenneth.bingham+kentest@netfoundry.io + roleAttributes: [] + tags: {} + typeId: Default + - authPolicy: '@NetFoundry Console Integration Auth Policy' + disabled: false + edgeRouterConnectionStatus: null + externalId: 8466464f-dcd4-46e9-a794-2bf68acc144b + isDefaultAdmin: false + isMfaEnabled: false + isAdmin: false + name: ryan galletto + roleAttributes: [] + tags: {} + typeId: Default + - authPolicy: '@NetFoundry Console Integration Auth Policy' + disabled: false + edgeRouterConnectionStatus: null + externalId: 489ff3ee-52ec-11e8-aa95-12c0467c47be + isDefaultAdmin: false + isMfaEnabled: false + isAdmin: false + name: Mike Guthrie + roleAttributes: [] + tags: {} + typeId: Default + - authPolicy: '@NetFoundry Console Integration Auth Policy' + disabled: false + edgeRouterConnectionStatus: null + externalId: 5f854c49-b5fd-44a1-b14f-a9c4aa5a7eba + isDefaultAdmin: false + isMfaEnabled: false + isAdmin: false + name: 0dRsg5oRswW9gxv4H_8MX + roleAttributes: [] + tags: {} + typeId: Default + - authPolicy: '@Default' + disabled: false + edgeRouterConnectionStatus: null + externalId: null + isDefaultAdmin: false + isMfaEnabled: false + isAdmin: false + name: Newone + roleAttributes: [] + tags: {} + typeId: Default + - authPolicy: '@NetFoundry Console Integration Auth Policy' + disabled: false + edgeRouterConnectionStatus: null + externalId: 356e0534-7fb8-4a48-b637-8a8821aa8035 + isDefaultAdmin: false + isMfaEnabled: false + isAdmin: false + name: Jens Alm + roleAttributes: [] + tags: {} + typeId: Default + - authPolicy: '@NetFoundry Console Integration Auth Policy' + disabled: false + edgeRouterConnectionStatus: null + externalId: e37b3dc5-f375-4403-bf6d-e95a0a85d8e3 + isDefaultAdmin: false + isMfaEnabled: false + isAdmin: false + name: mahesh eranna + roleAttributes: [] + tags: {} + typeId: Default + - authPolicy: '@Default' + disabled: false + edgeRouterConnectionStatus: null + externalId: null + isDefaultAdmin: false + isMfaEnabled: false + isAdmin: false + name: admin2_user + roleAttributes: + - client + tags: {} + typeId: Default + - authPolicy: '@NetFoundry Console Integration Auth Policy' + disabled: false + edgeRouterConnectionStatus: null + externalId: e3b92baa-0530-4ad9-80fd-57e5b3283bf9 + isDefaultAdmin: false + isMfaEnabled: false + isAdmin: false + name: Russell Allen + roleAttributes: [] + tags: {} + typeId: Default + - authPolicy: '@Default' + disabled: false + edgeRouterConnectionStatus: null + externalId: null + isDefaultAdmin: false + isMfaEnabled: false + isAdmin: false + name: AnewAdmin + roleAttributes: + - client + tags: {} + typeId: Default + - authPolicy: '@NetFoundry Console Integration Auth Policy' + disabled: false + edgeRouterConnectionStatus: null + externalId: dab489a7-63d8-4e64-85b4-004ec0448037 + isDefaultAdmin: false + isMfaEnabled: false + isAdmin: false + name: Prashant Savadi + roleAttributes: [] + tags: {} + typeId: Default + - authPolicy: '@NetFoundry Console Integration Auth Policy' + disabled: false + edgeRouterConnectionStatus: null + externalId: 988c2c94-f6dc-42ff-b1a1-8977915194db + isDefaultAdmin: false + isMfaEnabled: false + isAdmin: false + name: Edward Moscardini + roleAttributes: [] + tags: {} + typeId: Default + - authPolicy: '@NetFoundry Console Integration Auth Policy' + disabled: false + edgeRouterConnectionStatus: null + externalId: 0ed768fa-7214-4404-8335-a715156dff45 + isDefaultAdmin: false + isMfaEnabled: false + isAdmin: false + name: MOP Ziti Metrics Processor Service + roleAttributes: [] + tags: {} + typeId: Default + - authPolicy: '@NetFoundry Console Integration Auth Policy' + disabled: false + edgeRouterConnectionStatus: null + externalId: 468153e2-1f07-498e-999d-4511e3d3a771 + isDefaultAdmin: false + isMfaEnabled: false + isAdmin: false + name: Tod Burtchell + roleAttributes: [] + tags: {} + typeId: Default + - authPolicy: '@Default' + disabled: false + edgeRouterConnectionStatus: null + externalId: null + isDefaultAdmin: false + isMfaEnabled: false + isAdmin: false + name: rg-windows-dt + roleAttributes: [] + tags: + foo: bar + typeId: Default + - authPolicy: '@Default' + disabled: false + edgeRouterConnectionStatus: null + externalId: null + isDefaultAdmin: false + isMfaEnabled: false + isAdmin: false + name: Admin-Registered + roleAttributes: [] + tags: {} + typeId: Default +postureChecks: + - macAddresses: + - 0123456789ab + name: Mac + roleAttributes: + - mac + tags: {} + typeId: MAC + - name: OS + operatingSystems: + - type: macOS + versions: + - 10.3.1 + - 11.2.3 + roleAttributes: + - os + tags: {} + typeId: OS + - name: MFA + roleAttributes: + - mfa + tags: {} + timeoutSeconds: 30 + typeId: MFA + - name: Process + process: + hashes: null + osType: Linux + path: /path/something + roleAttributes: + - process + tags: {} + typeId: PROCESS +edgeRouters: + - appData: {} + disabled: false + enrollmentToken: 29818c67-fc39-4f7b-bb05-9db895719107 + hostname: "" + isTunnelerEnabled: true + name: custroutet2 + noTraversal: false + roleAttributes: + - vis-bind + tags: + hello: world + unverifiedCertPem: null + unverifiedFingerprint: null + - appData: {} + disabled: false + enrollmentToken: 5564c079-d089-4e4b-8c76-7fe57b1967da + hostname: "" + isTunnelerEnabled: true + name: asd + noTraversal: false + roleAttributes: [] + tags: {} + unverifiedCertPem: null + unverifiedFingerprint: null + - appData: {} + disabled: false + hostname: e08afdef-cb84-4a7e-b991-10a78575c2fc.staging.netfoundry.io + isTunnelerEnabled: true + name: public-router1 + noTraversal: false + roleAttributes: + - public + tags: {} + unverifiedCertPem: null + unverifiedFingerprint: null + - appData: {} + disabled: false + hostname: 565288cb-039e-47fa-b4d6-cb10d3864d14.staging.netfoundry.io + isTunnelerEnabled: false + name: enroll + noTraversal: false + roleAttributes: [] + tags: {} + unverifiedCertPem: null + unverifiedFingerprint: null + - appData: {} + disabled: false + hostname: c609f216-d095-4752-844e-52dd8fe022ea.staging.netfoundry.io + isTunnelerEnabled: false + name: nfhosted + noTraversal: false + roleAttributes: + - public + tags: {} + unverifiedCertPem: null + unverifiedFingerprint: null + - appData: + my: er + disabled: false + enrollmentToken: 43bf0e64-62c2-4c6a-a602-58b46c538471 + hostname: "" + isTunnelerEnabled: false + name: appdata + noTraversal: true + roleAttributes: [] + tags: {} + unverifiedCertPem: null + unverifiedFingerprint: null + - appData: {} + disabled: false + hostname: e6a40617-8394-49c1-82d3-ed78388551c5.staging.netfoundry.io + isTunnelerEnabled: true + name: vis-customer-router + noTraversal: false + roleAttributes: + - vis-bind + tags: {} + unverifiedCertPem: null + unverifiedFingerprint: null +serviceEdgeRouterPolicies: + - edgeRouterRoles: + - '@custroutet2' + name: ssep2 + semantic: AnyOf + serviceRoles: + - '@ssssimple' + tags: {} + - edgeRouterRoles: + - '@public-router1' + name: sep1 + semantic: AnyOf + serviceRoles: + - '@ssssimple' + tags: {} +servicePolicies: + - identityRoles: + - '@public-router1' + name: ssssimple-bind-policy + postureCheckRoles: null + semantic: AnyOf + serviceRoles: + - '@ssssimple' + tags: {} + type: Bind + - identityRoles: + - '@identity12' + name: ssssimple-dial-policy + postureCheckRoles: null + semantic: AnyOf + serviceRoles: + - '@ssssimple' + tags: {} + type: Dial +services: + - configs: [] + encryptionRequired: true + name: asdfasdf + roleAttributes: + - bcde + tags: {} + terminatorStrategy: smartrouting + - configs: + - '@ssssimple-intercept-config' + - '@ssssimple-host-config' + encryptionRequired: true + name: ssssimple + roleAttributes: + - abcd + - service + tags: + foo: bar + terminatorStrategy: smartrouting diff --git a/ziti/cmd/ascode/upload/upload.go b/ziti/cmd/ascode/upload/upload.go new file mode 100644 index 000000000..ac3d77e70 --- /dev/null +++ b/ziti/cmd/ascode/upload/upload.go @@ -0,0 +1,445 @@ +/* + Copyright NetFoundry Inc. + + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at + + https://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. +*/ + +package upload + +import ( + "encoding/json" + "errors" + "github.com/judedaryl/go-arrayutils" + "github.com/michaelquigley/pfxlog" + "github.com/openziti/edge-api/rest_management_api_client" + "github.com/openziti/ziti/internal" + "github.com/openziti/ziti/internal/rest/mgmt" + "github.com/openziti/ziti/ziti/cmd/edge" + c "github.com/openziti/ziti/ziti/constants" + "github.com/patrickmn/go-cache" + "github.com/sirupsen/logrus" + "github.com/spf13/cobra" + "github.com/spf13/viper" + "gopkg.in/yaml.v3" + "io" + "os" + "slices" + "strings" + "time" +) + +type Upload struct { + loginOpts edge.LoginOptions + client *rest_management_api_client.ZitiEdgeManagement + reader Reader + + verbose bool + + ofJson bool + ofYaml bool + + configCache *cache.Cache + serviceCache *cache.Cache + edgeRouterCache *cache.Cache + authPolicyCache *cache.Cache + extJwtSignersCache *cache.Cache + identityCache *cache.Cache +} + +var log = pfxlog.Logger() + +func NewUploadCmd(out io.Writer, errOut io.Writer) *cobra.Command { + + u := &Upload{} + uploadCmd := &cobra.Command{ + Use: "import filename [entity]", + Short: "Import ziti entities", + Long: "Import all or selected ziti entities from the specified file.\n" + + "Valid entities are: [all|ca/certificate-authority|identity|edge-router|service|config|config-type|service-policy|edgerouter-policy|service-edgerouter-policy|external-jwt-signer|auth-policy|posture-check] (default all)", + Args: cobra.MinimumNArgs(1), + PersistentPreRun: func(cmd *cobra.Command, args []string) { + u.Init() + }, + Run: func(cmd *cobra.Command, args []string) { + data, err := u.reader.read(args[0]) + if err != nil { + panic(errors.Join(errors.New("unable to read input"), err)) + } + m := map[string][]interface{}{} + + if u.ofYaml { + err = yaml.Unmarshal(data, &m) + if err != nil { + panic(errors.Join(errors.New("unable to parse input data as yaml"), err)) + } + } else { + err = json.Unmarshal(data, &m) + if err != nil { + panic(errors.Join(errors.New("unable to parse input data as json"), err)) + } + } + + result, executeErr := u.Execute(m, args[1:]) + if executeErr != nil { + panic(executeErr) + } + if u.verbose { + log. + WithField("results", result). + Debug("Finished") + } + }, + Hidden: true, + } + + v := viper.New() + + viper.SetEnvPrefix(c.ZITI) // All env vars we seek will be prefixed with "ZITI_" + v.SetEnvKeyReplacer(strings.NewReplacer("-", "_")) + v.AutomaticEnv() + + uploadCmd.Flags().BoolVar(&u.ofJson, "json", true, "Input parsed as JSON") + uploadCmd.Flags().BoolVar(&u.ofYaml, "yaml", false, "Input parsed as YAML") + uploadCmd.MarkFlagsMutuallyExclusive("json", "yaml") + + uploadCmd.PersistentFlags().BoolVarP(&u.verbose, "verbose", "v", false, "Enable verbose logging") + + edge.AddLoginFlags(uploadCmd, &u.loginOpts) + u.loginOpts.Out = out + u.loginOpts.Err = errOut + + return uploadCmd +} + +func (u *Upload) Init() { + logLvl := logrus.InfoLevel + if u.verbose { + logLvl = logrus.DebugLevel + } + + pfxlog.GlobalInit(logLvl, pfxlog.DefaultOptions().Color()) + internal.ConfigureLogFormat(logLvl) + + client, err := mgmt.NewClient() + if err != nil { + loginErr := u.loginOpts.Run() + if loginErr != nil { + log.Fatal(err) + } + client, err = mgmt.NewClient() + if err != nil { + log.Fatal(err) + } + } + u.client = client + u.reader = FileReader{} +} + +func (u *Upload) Execute(data map[string][]interface{}, inputArgs []string) (map[string]any, error) { + + args := arrayutils.Map(inputArgs, strings.ToLower) + + u.configCache = cache.New(time.Duration(-1), time.Duration(-1)) + u.serviceCache = cache.New(time.Duration(-1), time.Duration(-1)) + u.edgeRouterCache = cache.New(time.Duration(-1), time.Duration(-1)) + u.authPolicyCache = cache.New(time.Duration(-1), time.Duration(-1)) + u.extJwtSignersCache = cache.New(time.Duration(-1), time.Duration(-1)) + u.identityCache = cache.New(time.Duration(-1), time.Duration(-1)) + + result := map[string]any{} + all := slices.Contains(args, "all") || len(args) == 0 + + cas := map[string]string{} + if all || + slices.Contains(args, "ca") || slices.Contains(args, "cas") || + slices.Contains(args, "certificate-authority") || slices.Contains(args, "certificate-authorities") { + if u.verbose { + log. + Debug("Processing CertificateAuthorities") + } + var err error + cas, err = u.ProcessCertificateAuthorities(data) + if err != nil { + return nil, err + } + if u.verbose { + log. + WithField("certificateAuthorities", cas). + Debug("CertificateAuthorities created") + } + } + result["certificateAuthorities"] = cas + + externalJwtSigners := map[string]string{} + if all || + slices.Contains(args, "external-jwt-signer") || slices.Contains(args, "external-jwt-signers") || + slices.Contains(args, "auth-policy") || slices.Contains(args, "auth-policies") || + slices.Contains(args, "identity") || slices.Contains(args, "identities") { + if u.verbose { + log. + Debug("Processing ExtJWTSigners") + } + var err error + externalJwtSigners, err = u.ProcessExternalJwtSigners(data) + if err != nil { + return nil, err + } + if u.verbose { + log. + WithField("externalJwtSigners", externalJwtSigners). + Debug("ExtJWTSigners created") + } + } + result["externalJwtSigners"] = externalJwtSigners + + authPolicies := map[string]string{} + if all || + slices.Contains(args, "auth-policy") || slices.Contains(args, "auth-policies") || + slices.Contains(args, "identity") || slices.Contains(args, "identities") { + if u.verbose { + log. + Debug("Processing AuthPolicies") + } + var err error + authPolicies, err = u.ProcessAuthPolicies(data) + if err != nil { + return nil, err + } + if u.verbose { + log. + WithField("authPolicies", authPolicies). + Debug("AuthPolicies created") + } + } + result["authPolicies"] = authPolicies + + identities := map[string]string{} + if all || + slices.Contains(args, "identity") || slices.Contains(args, "identities") { + if u.verbose { + log. + Debug("Processing Identities") + } + var err error + identities, err = u.ProcessIdentities(data) + if err != nil { + return nil, err + } + if u.verbose { + log. + WithField("identities", identities). + Debug("Identities created") + } + } + result["identities"] = identities + + configTypes := map[string]string{} + if all || + slices.Contains(args, "config-type") || slices.Contains(args, "config-types") || + slices.Contains(args, "config") || slices.Contains(args, "configs") || + slices.Contains(args, "service") || slices.Contains(args, "services") { + if u.verbose { + log. + Debug("Processing ConfigTypes") + } + var err error + configTypes, err = u.ProcessConfigTypes(data) + if err != nil { + return nil, err + } + if u.verbose { + log. + WithField("configTypes", configTypes). + Debug("ConfigTypes created") + } + } + result["configTypes"] = configTypes + + configs := map[string]string{} + if all || + slices.Contains(args, "config") || slices.Contains(args, "configs") || + slices.Contains(args, "service") || slices.Contains(args, "services") { + if u.verbose { + log. + Debug("Processing Configs") + } + var err error + configs, err = u.ProcessConfigs(data) + if err != nil { + return nil, err + } + if u.verbose { + log. + WithField("configs", configs). + Debug("Configs created") + } + } + result["configs"] = configs + + services := map[string]string{} + if all || + slices.Contains(args, "service") || slices.Contains(args, "services") { + if u.verbose { + log. + Debug("Processing Services") + } + var err error + services, err = u.ProcessServices(data) + if err != nil { + return nil, err + } + if u.verbose { + log. + WithField("services", services). + Debug("Services created") + } + } + result["services"] = services + + postureChecks := map[string]string{} + if all || + slices.Contains(args, "posture-check") || slices.Contains(args, "posture-checks") { + if u.verbose { + log. + Debug("Processing PostureChecks") + } + var err error + postureChecks, err = u.ProcessPostureChecks(data) + if err != nil { + return nil, err + } + if u.verbose { + log. + WithField("postureChecks", postureChecks). + Debug("PostureChecks created") + } + } + result["postureChecks"] = postureChecks + + routers := map[string]string{} + if all || + slices.Contains(args, "edge-router") || slices.Contains(args, "edge-routers") || + slices.Contains(args, "ers") || slices.Contains(args, "ers") { + if u.verbose { + log. + Debug("Processing EdgeRouters") + } + var err error + routers, err = u.ProcessEdgeRouters(data) + if err != nil { + return nil, err + } + if u.verbose { + log. + WithField("edgeRouters", routers). + Debug("EdgeRouters created") + } + } + result["edgeRouters"] = routers + + serviceEdgeRouterPolicies := map[string]string{} + if all || + slices.Contains(args, "service-edgerouter-policy") || slices.Contains(args, "service-edgerouter-policies") { + if u.verbose { + log. + Debug("Processing ServiceRouterPolicies") + } + var err error + serviceEdgeRouterPolicies, err = u.ProcessServiceEdgeRouterPolicies(data) + if err != nil { + return nil, err + } + if u.verbose { + log. + WithField("serviceEdgeRouterPolicies", serviceEdgeRouterPolicies). + Debug("ServiceEdgeRouterPolicies created") + } + } + result["serviceEdgeRouterPolicies"] = serviceEdgeRouterPolicies + + servicePolicies := map[string]string{} + if all || + slices.Contains(args, "service-policy") || slices.Contains(args, "service-policies") { + if u.verbose { + log. + Debug("Processing ServicePolicies") + } + var err error + servicePolicies, err = u.ProcessServicePolicies(data) + if err != nil { + return nil, err + } + if u.verbose { + log. + WithField("servicePolicies", servicePolicies). + Debug("ServicePolicies created") + } + } + result["servicePolicies"] = servicePolicies + + routerPolicies := map[string]string{} + if all || + slices.Contains(args, "edgerouter-policy") || slices.Contains(args, "edgerouter-policies") { + if u.verbose { + log. + Debug("Processing EdgeRouterPolicies") + } + var err error + routerPolicies, err = u.ProcessEdgeRouterPolicies(data) + if err != nil { + return nil, err + } + if u.verbose { + log. + WithField("routerPolicies", routerPolicies). + Debug("EdgeRouterPolicies created") + } + } + result["edgeRouterPolicies"] = routerPolicies + + if u.verbose { + log. + Info("Upload complete") + } + + return result, nil +} + +func FromMap[T interface{}](input interface{}, v T) *T { + jsonData, _ := json.MarshalIndent(input, "", " ") + create := new(T) + err := json.Unmarshal(jsonData, &create) + if err != nil { + log. + WithField("err", err). + Error("error converting input to object") + return nil + } + return create +} + +type Reader interface { + read(input any) ([]byte, error) +} + +type FileReader struct { +} + +func (i FileReader) read(input any) ([]byte, error) { + file, err := os.ReadFile(input.(string)) + if err != nil { + return nil, err + } + + return file, nil +} diff --git a/ziti/cmd/ascode/upload/upload_auth_policies.go b/ziti/cmd/ascode/upload/upload_auth_policies.go new file mode 100644 index 000000000..23dc3b888 --- /dev/null +++ b/ziti/cmd/ascode/upload/upload_auth_policies.go @@ -0,0 +1,108 @@ +/* + Copyright NetFoundry Inc. + + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at + + https://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. +*/ + +package upload + +import ( + "encoding/json" + "github.com/antchfx/jsonquery" + "github.com/openziti/edge-api/rest_management_api_client/auth_policy" + "github.com/openziti/edge-api/rest_model" + "github.com/openziti/edge-api/rest_util" + common "github.com/openziti/ziti/internal/ascode" + "github.com/openziti/ziti/internal/rest/mgmt" + "strings" +) + +func (u *Upload) ProcessAuthPolicies(input map[string][]interface{}) (map[string]string, error) { + + if u.verbose { + log.Debug("Listing all AuthPolicies") + } + + result := map[string]string{} + + for _, data := range input["authPolicies"] { + create := FromMap(data, rest_model.AuthPolicyCreate{}) + + // see if the auth policy already exists + existing := mgmt.AuthPolicyFromFilter(u.client, mgmt.NameFilter(*create.Name)) + if existing != nil { + if u.verbose { + log.WithFields(map[string]interface{}{ + "name": *create.Name, + "authPolicyId": *existing.ID, + }).Info("Found existing Auth Policy, skipping create") + } + continue + } + + // convert to a jsonquery doc so we can query inside the json + jsonData, _ := json.Marshal(data) + doc, jsonQueryErr := jsonquery.Parse(strings.NewReader(string(jsonData))) + if jsonQueryErr != nil { + log.WithError(jsonQueryErr).Error("Unable to list AuthPolicies") + return nil, jsonQueryErr + } + allowedSigners := jsonquery.FindOne(doc, "/primary/extJwt/allowedSigners") + + // look up each signer by name and add to the create + allowedSignerIds := []string{} + for _, signer := range allowedSigners.ChildNodes() { + value := signer.Value().(string)[1:] + extJwtSigner, err := common.GetItemFromCache(u.extJwtSignersCache, value, func(name string) (interface{}, error) { + return mgmt.ExternalJWTSignerFromFilter(u.client, mgmt.NameFilter(name)), nil + }) + if err != nil { + log.WithField("name", *create.Name).Warn("Unable to read ExtJwtSigner") + return nil, err + } + allowedSignerIds = append(allowedSignerIds, *extJwtSigner.(*rest_model.ExternalJWTSignerDetail).ID) + } + create.Primary.ExtJWT.AllowedSigners = allowedSignerIds + + // do the actual create since it doesn't exist + if u.verbose { + log.WithField("name", *create.Name). + Debug("Creating AuthPolicy") + } + created, createErr := u.client.AuthPolicy.CreateAuthPolicy(&auth_policy.CreateAuthPolicyParams{AuthPolicy: create}, nil) + if createErr != nil { + if payloadErr, ok := createErr.(rest_util.ApiErrorPayload); ok { + log.WithFields(map[string]interface{}{ + "field": payloadErr.GetPayload().Error.Cause.APIFieldError.Field, + "reason": payloadErr.GetPayload().Error.Cause.APIFieldError.Reason, + "err": payloadErr, + }).Error("Unable to create AuthPolicy") + return nil, createErr + } else { + log.WithError(createErr).Error("Unable to create AuthPolicy") + return nil, createErr + } + } + + if u.verbose { + log.WithFields(map[string]interface{}{ + "name": *create.Name, + "authPolicyId": created.Payload.Data.ID, + }).Info("Created AuthPolicy") + } + + result[*create.Name] = created.Payload.Data.ID + } + + return result, nil +} diff --git a/ziti/cmd/ascode/upload/upload_certificate_authorities.go b/ziti/cmd/ascode/upload/upload_certificate_authorities.go new file mode 100644 index 000000000..748f9ce52 --- /dev/null +++ b/ziti/cmd/ascode/upload/upload_certificate_authorities.go @@ -0,0 +1,74 @@ +/* + Copyright NetFoundry Inc. + + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at + + https://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. +*/ + +package upload + +import ( + "github.com/openziti/edge-api/rest_management_api_client/certificate_authority" + "github.com/openziti/edge-api/rest_model" + "github.com/openziti/edge-api/rest_util" + "github.com/openziti/ziti/internal/rest/mgmt" +) + +func (u *Upload) ProcessCertificateAuthorities(input map[string][]interface{}) (map[string]string, error) { + + var result = map[string]string{} + for _, data := range input["certificateAuthorities"] { + create := FromMap(data, rest_model.CaCreate{}) + + // see if the CA already exists + existing := mgmt.CertificateAuthorityFromFilter(u.client, mgmt.NameFilter(*create.Name)) + if existing != nil { + if u.verbose { + log.WithFields(map[string]interface{}{ + "name": *create.Name, + "certificateAuthorityId": *existing.ID, + }). + Info("Found existing CertificateAuthority, skipping create") + } + continue + } + + // do the actual create since it doesn't exist + created, createErr := u.client.CertificateAuthority.CreateCa(&certificate_authority.CreateCaParams{Ca: create}, nil) + if createErr != nil { + if payloadErr, ok := createErr.(rest_util.ApiErrorPayload); ok { + log. + WithError(createErr). + WithFields(map[string]interface{}{ + "field": payloadErr.GetPayload().Error.Cause.APIFieldError.Field, + "reason": payloadErr.GetPayload().Error.Cause.APIFieldError.Reason, + }). + Error("Unable to create CertificateAuthority") + return nil, createErr + } else { + log.WithError(createErr).Error("Unable to create CertificateAuthority") + return nil, createErr + } + } + if u.verbose { + log.WithFields(map[string]interface{}{ + "name": *create.Name, + "certificateAuthorityId": created.Payload.Data.ID, + }). + Info("Created CertificateAuthority") + } + + result[*create.Name] = created.Payload.Data.ID + } + + return result, nil +} diff --git a/ziti/cmd/ascode/upload/upload_config_types.go b/ziti/cmd/ascode/upload/upload_config_types.go new file mode 100644 index 000000000..d09fec5fc --- /dev/null +++ b/ziti/cmd/ascode/upload/upload_config_types.go @@ -0,0 +1,77 @@ +/* + Copyright NetFoundry Inc. + + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at + + https://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. +*/ + +package upload + +import ( + "github.com/openziti/edge-api/rest_management_api_client/config" + "github.com/openziti/edge-api/rest_model" + "github.com/openziti/edge-api/rest_util" + "github.com/openziti/ziti/internal/rest/mgmt" +) + +func (u *Upload) ProcessConfigTypes(input map[string][]interface{}) (map[string]string, error) { + + var result = map[string]string{} + for _, data := range input["configTypes"] { + create := FromMap(data, rest_model.ConfigTypeCreate{}) + + // see if the config type already exists + existing := mgmt.ConfigTypeFromFilter(u.client, mgmt.NameFilter(*create.Name)) + if existing != nil { + if u.verbose { + log.WithFields(map[string]interface{}{ + "name": *create.Name, + "configTypeId": *existing.ID, + }). + Info("Found existing ConfigType, skipping create") + } + continue + } + + // do the actual create since it doesn't exist + if u.verbose { + log.WithField("name", *create.Name). + Debug("Creating ConfigType") + } + created, createErr := u.client.Config.CreateConfigType(&config.CreateConfigTypeParams{ConfigType: create}, nil) + if createErr != nil { + if payloadErr, ok := createErr.(rest_util.ApiErrorPayload); ok { + log.WithFields(map[string]interface{}{ + "field": payloadErr.GetPayload().Error.Cause.APIFieldError.Field, + "reason": payloadErr.GetPayload().Error.Cause.APIFieldError.Reason, + }). + Error("Unable to create ConfigType") + } else { + log.WithError(createErr). + Error("Unable to create ConfigType") + } + return nil, createErr + } + + if u.verbose { + log.WithFields(map[string]interface{}{ + "name": *create.Name, + "configTypeId": created.Payload.Data.ID, + }). + Info("Created Config Type") + } + + result[*create.Name] = created.Payload.Data.ID + } + + return result, nil +} diff --git a/ziti/cmd/ascode/upload/upload_configs.go b/ziti/cmd/ascode/upload/upload_configs.go new file mode 100644 index 000000000..5156bf9e7 --- /dev/null +++ b/ziti/cmd/ascode/upload/upload_configs.go @@ -0,0 +1,97 @@ +/* + Copyright NetFoundry Inc. + + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at + + https://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. +*/ + +package upload + +import ( + "encoding/json" + "errors" + "github.com/antchfx/jsonquery" + "github.com/openziti/edge-api/rest_management_api_client/config" + "github.com/openziti/edge-api/rest_model" + "github.com/openziti/edge-api/rest_util" + common "github.com/openziti/ziti/internal/ascode" + "github.com/openziti/ziti/internal/rest/mgmt" + "strings" +) + +func (u *Upload) ProcessConfigs(input map[string][]interface{}) (map[string]string, error) { + + var result = map[string]string{} + for _, data := range input["configs"] { + create := FromMap(data, rest_model.ConfigCreate{}) + + // see if the config already exists + existing := mgmt.ConfigFromFilter(u.client, mgmt.NameFilter(*create.Name)) + if existing != nil { + if u.verbose { + log. + WithFields(map[string]interface{}{ + "name": *create.Name, + "configId": *existing.ID, + }). + Info("Found existing Config, skipping create") + } + continue + } + + // convert to a jsonquery doc so we can query inside the json + jsonData, _ := json.Marshal(data) + doc, jsonQueryErr := jsonquery.Parse(strings.NewReader(string(jsonData))) + if jsonQueryErr != nil { + log.WithError(jsonQueryErr).Error("Unable to parse json") + return nil, jsonQueryErr + } + + // look up the config type id from the name and add to the create + value := jsonquery.FindOne(doc, "/configType").Value().(string)[1:] + configType, _ := common.GetItemFromCache(u.configCache, value, func(name string) (interface{}, error) { + return mgmt.ConfigTypeFromFilter(u.client, mgmt.NameFilter(name)), nil + }) + if u.configCache == nil { + return nil, errors.New("error reading ConfigType: " + value) + } + create.ConfigTypeID = configType.(*rest_model.ConfigTypeDetail).ID + + // do the actual create since it doesn't exist + if u.verbose { + log.WithField("name", *create.Name).Debug("Creating Config") + } + created, createErr := u.client.Config.CreateConfig(&config.CreateConfigParams{Config: create}, nil) + if createErr != nil { + if payloadErr, ok := createErr.(rest_util.ApiErrorPayload); ok { + log.WithFields(map[string]interface{}{ + "field": payloadErr.GetPayload().Error.Cause.APIFieldError.Field, + "reason": payloadErr.GetPayload().Error.Cause.APIFieldError.Reason}). + Error("Unable to create Config") + return nil, createErr + } else { + log.WithError(createErr).Error("Unable to list Configs") + return nil, createErr + } + } + if u.verbose { + log.WithFields(map[string]interface{}{ + "name": *create.Name, + "configId": created.Payload.Data.ID, + }). + Info("Created Config") + } + result[*create.Name] = created.Payload.Data.ID + } + + return result, nil +} diff --git a/ziti/cmd/ascode/upload/upload_edgerouter_policies.go b/ziti/cmd/ascode/upload/upload_edgerouter_policies.go new file mode 100644 index 000000000..ced071757 --- /dev/null +++ b/ziti/cmd/ascode/upload/upload_edgerouter_policies.go @@ -0,0 +1,87 @@ +/* + Copyright NetFoundry Inc. + + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at + + https://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. +*/ + +package upload + +import ( + "github.com/openziti/edge-api/rest_management_api_client/edge_router_policy" + "github.com/openziti/edge-api/rest_model" + "github.com/openziti/edge-api/rest_util" + "github.com/openziti/ziti/internal/rest/mgmt" +) + +func (u *Upload) ProcessEdgeRouterPolicies(input map[string][]interface{}) (map[string]string, error) { + + var result = map[string]string{} + for _, data := range input["edgeRouterPolicies"] { + create := FromMap(data, rest_model.EdgeRouterPolicyCreate{}) + + // see if the router already exists + existing := mgmt.EdgeRouterPolicyFromFilter(u.client, mgmt.NameFilter(*create.Name)) + if existing != nil { + log.WithFields(map[string]interface{}{ + "name": *create.Name, + "edgeRouterPolicyId": *existing.ID, + }). + Info("Found existing EdgeRouterPolicy, skipping create") + continue + } + + // look up the edgeRouter ids from the name and add to the create + edgeRouterRoles, err := u.lookupEdgeRouters(create.EdgeRouterRoles) + if err != nil { + return nil, err + } + create.EdgeRouterRoles = edgeRouterRoles + + // look up the identity ids from the name and add to the create + identityRoles, err := u.lookupIdentities(create.IdentityRoles) + if err != nil { + return nil, err + } + create.IdentityRoles = identityRoles + + // do the actual create since it doesn't exist + if u.verbose { + log.WithField("name", *create.Name).Debug("Creating EdgeRouterPolicy") + } + created, createErr := u.client.EdgeRouterPolicy.CreateEdgeRouterPolicy(&edge_router_policy.CreateEdgeRouterPolicyParams{Policy: create}, nil) + if createErr != nil { + if payloadErr, ok := createErr.(rest_util.ApiErrorPayload); ok { + log.WithFields(map[string]interface{}{ + "field": payloadErr.GetPayload().Error.Cause.APIFieldError.Field, + "reason": payloadErr.GetPayload().Error.Cause.APIFieldError.Reason, + }). + Error("Unable to create EdgeRouterPolicy") + return nil, createErr + } else { + log.WithError(createErr).Error("Unable to create EdgeRouterPolicy") + return nil, createErr + } + } + if u.verbose { + log.WithFields(map[string]interface{}{ + "name": *create.Name, + "routerPolicyId": created.Payload.Data.ID, + }). + Info("Created EdgeRouterPolicy") + } + + result[*create.Name] = created.Payload.Data.ID + } + + return result, nil +} diff --git a/ziti/cmd/ascode/upload/upload_edgerouters.go b/ziti/cmd/ascode/upload/upload_edgerouters.go new file mode 100644 index 000000000..6538db19d --- /dev/null +++ b/ziti/cmd/ascode/upload/upload_edgerouters.go @@ -0,0 +1,93 @@ +/* + Copyright NetFoundry Inc. + + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at + + https://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. +*/ + +package upload + +import ( + "errors" + "github.com/openziti/edge-api/rest_management_api_client/edge_router" + "github.com/openziti/edge-api/rest_model" + "github.com/openziti/edge-api/rest_util" + common "github.com/openziti/ziti/internal/ascode" + "github.com/openziti/ziti/internal/rest/mgmt" +) + +func (u *Upload) ProcessEdgeRouters(input map[string][]interface{}) (map[string]string, error) { + + var result = map[string]string{} + for _, data := range input["edgeRouters"] { + create := FromMap(data, rest_model.EdgeRouterCreate{}) + + // see if the router already exists + existing := mgmt.EdgeRouterFromFilter(u.client, mgmt.NameFilter(*create.Name)) + if existing != nil { + log.WithFields(map[string]interface{}{ + "name": *create.Name, + "edgeRouterId": *existing.ID, + }). + Info("Found existing EdgeRouter, skipping create") + continue + } + + // do the actual create since it doesn't exist + if u.verbose { + log.WithField("name", *create.Name).Debug("Creating EdgeRouter") + } + created, createErr := u.client.EdgeRouter.CreateEdgeRouter(&edge_router.CreateEdgeRouterParams{EdgeRouter: create}, nil) + if createErr != nil { + if payloadErr, ok := createErr.(rest_util.ApiErrorPayload); ok { + log.WithFields(map[string]interface{}{ + "field": payloadErr.GetPayload().Error.Cause.APIFieldError.Field, + "reason": payloadErr.GetPayload().Error.Cause.APIFieldError.Reason, + }).Error("Unable to create EdgeRouter") + } else { + log.WithField("err", createErr).Error("Unable to create EdgeRouter") + return nil, createErr + } + } + if u.verbose { + log.WithFields(map[string]interface{}{ + "name": *create.Name, + "edgeRouterId": created.Payload.Data.ID, + }). + Info("Created EdgeRouter") + } + + result[*create.Name] = created.Payload.Data.ID + } + + return result, nil +} + +func (u *Upload) lookupEdgeRouters(roles []string) ([]string, error) { + edgeRouterRoles := []string{} + for _, role := range roles { + if role[0:1] == "@" { + value := role[1:] + edgeRouter, _ := common.GetItemFromCache(u.edgeRouterCache, value, func(name string) (interface{}, error) { + return mgmt.EdgeRouterFromFilter(u.client, mgmt.NameFilter(name)), nil + }) + if edgeRouter == nil { + return nil, errors.New("error reading EdgeRouter: " + value) + } + edgeRouterId := edgeRouter.(*rest_model.EdgeRouterDetail).ID + edgeRouterRoles = append(edgeRouterRoles, "@"+*edgeRouterId) + } else { + edgeRouterRoles = append(edgeRouterRoles, role) + } + } + return edgeRouterRoles, nil +} diff --git a/ziti/cmd/ascode/upload/upload_external_jwt_signers.go b/ziti/cmd/ascode/upload/upload_external_jwt_signers.go new file mode 100644 index 000000000..a7bd1473a --- /dev/null +++ b/ziti/cmd/ascode/upload/upload_external_jwt_signers.go @@ -0,0 +1,76 @@ +/* + Copyright NetFoundry Inc. + + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at + + https://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. +*/ + +package upload + +import ( + "github.com/openziti/edge-api/rest_management_api_client/external_jwt_signer" + "github.com/openziti/edge-api/rest_model" + "github.com/openziti/edge-api/rest_util" + "github.com/openziti/ziti/internal/rest/mgmt" +) + +func (u *Upload) ProcessExternalJwtSigners(input map[string][]interface{}) (map[string]string, error) { + + var result = map[string]string{} + for _, data := range input["externalJwtSigners"] { + create := FromMap(data, rest_model.ExternalJWTSignerCreate{}) + + // see if the signer already exists + existing := mgmt.ExternalJWTSignerFromFilter(u.client, mgmt.NameFilter(*create.Name)) + if existing != nil { + if u.verbose { + log.WithFields(map[string]interface{}{ + "name": *create.Name, + "externalJwtSignerId": *existing.ID, + }). + Info("Found existing ExtJWTSigner, skipping create") + } + continue + } + + // do the actual create since it doesn't exist + if u.verbose { + log.WithField("name", *create.Name).Debug("Creating ExtJWTSigner") + } + created, createErr := u.client.ExternalJWTSigner.CreateExternalJWTSigner(&external_jwt_signer.CreateExternalJWTSignerParams{ExternalJWTSigner: create}, nil) + if createErr != nil { + if payloadErr, ok := createErr.(rest_util.ApiErrorPayload); ok { + log.WithFields(map[string]interface{}{ + "field": payloadErr.GetPayload().Error.Cause.APIFieldError.Field, + "reason": payloadErr.GetPayload().Error.Cause.APIFieldError.Reason, + "err": payloadErr, + }). + Error("Unable to create ExtJWTSigner") + return nil, createErr + } else { + log.Error("Unable to create ExtJWTSigner") + return nil, createErr + } + } + if u.verbose { + log.WithFields(map[string]interface{}{ + "name": *create.Name, + "externalJwtSignerId": created.Payload.Data.ID, + }). + Info("Created ExtJWTSigner") + } + + result[*create.Name] = created.Payload.Data.ID + } + + return result, nil +} diff --git a/ziti/cmd/ascode/upload/upload_identities.go b/ziti/cmd/ascode/upload/upload_identities.go new file mode 100644 index 000000000..2c090ed0d --- /dev/null +++ b/ziti/cmd/ascode/upload/upload_identities.go @@ -0,0 +1,122 @@ +/* + Copyright NetFoundry Inc. + + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at + + https://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. +*/ + +package upload + +import ( + "encoding/json" + "errors" + "github.com/antchfx/jsonquery" + "github.com/openziti/edge-api/rest_management_api_client/identity" + "github.com/openziti/edge-api/rest_model" + "github.com/openziti/edge-api/rest_util" + common "github.com/openziti/ziti/internal/ascode" + "github.com/openziti/ziti/internal/rest/mgmt" + "strings" +) + +func (u *Upload) ProcessIdentities(input map[string][]interface{}) (map[string]string, error) { + + var result = map[string]string{} + + for _, data := range input["identities"] { + create := FromMap(data, rest_model.IdentityCreate{}) + + existing := mgmt.IdentityFromFilter(u.client, mgmt.NameFilter(*create.Name)) + if existing != nil { + if u.verbose { + log.WithFields(map[string]interface{}{ + "name": *create.Name, + "identityId": *existing.ID, + }). + Info("Found existing Identity, skipping create") + } + continue + } + + // set the type because it is not in the input + typ := rest_model.IdentityTypeDefault + create.Type = &typ + + // convert to a jsonquery doc so we can query inside the json + jsonData, _ := json.Marshal(data) + doc, jsonQueryErr := jsonquery.Parse(strings.NewReader(string(jsonData))) + if jsonQueryErr != nil { + log.WithError(jsonQueryErr). + Error("Unable to list Identities") + return nil, jsonQueryErr + } + policyName := jsonquery.FindOne(doc, "/authPolicy").Value().(string)[1:] + + // look up the auth policy id from the name and add to the create, omit if it's the "Default" policy + policy, _ := common.GetItemFromCache(u.authPolicyCache, policyName, func(name string) (interface{}, error) { + return mgmt.AuthPolicyFromFilter(u.client, mgmt.NameFilter(name)), nil + }) + if policy == nil { + return nil, errors.New("error reading Auth Policy: " + policyName) + } + if policy != "" && policy != "Default" { + create.AuthPolicyID = policy.(*rest_model.AuthPolicyDetail).ID + } + + // do the actual create since it doesn't exist + created, createErr := u.client.Identity.CreateIdentity(&identity.CreateIdentityParams{Identity: create}, nil) + if createErr != nil { + if payloadErr, ok := createErr.(rest_util.ApiErrorPayload); ok { + log.WithFields(map[string]interface{}{ + "field": payloadErr.GetPayload().Error.Cause.APIFieldError.Field, + "reason": payloadErr.GetPayload().Error.Cause.APIFieldError.Reason, + }). + Error("Unable to create Identity") + return nil, createErr + } else { + log.WithError(createErr).Error("Unable to create Identity") + return nil, createErr + } + } + if u.verbose { + log.WithFields(map[string]interface{}{ + "name": *create.Name, + "identityId": created.Payload.Data.ID, + }). + Info("Created identity") + } + + result[*create.Name] = created.Payload.Data.ID + } + + return result, nil +} + +func (u *Upload) lookupIdentities(roles []string) ([]string, error) { + identityRoles := []string{} + for _, role := range roles { + if role[0:1] == "@" { + value := role[1:] + identity, _ := common.GetItemFromCache(u.identityCache, value, func(name string) (interface{}, error) { + return mgmt.IdentityFromFilter(u.client, mgmt.NameFilter(name)), nil + }) + if identity == nil { + return nil, errors.New("error reading Identity: " + value) + } + identityId := identity.(*rest_model.IdentityDetail).ID + identityRoles = append(identityRoles, "@"+*identityId) + } else { + identityRoles = append(identityRoles, role) + } + } + return identityRoles, nil +} diff --git a/ziti/cmd/ascode/upload/upload_posture_check.go b/ziti/cmd/ascode/upload/upload_posture_check.go new file mode 100644 index 000000000..7a4d3ef3b --- /dev/null +++ b/ziti/cmd/ascode/upload/upload_posture_check.go @@ -0,0 +1,113 @@ +/* + Copyright NetFoundry Inc. + + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at + + https://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. +*/ + +package upload + +import ( + "encoding/json" + "github.com/antchfx/jsonquery" + "github.com/openziti/edge-api/rest_management_api_client/posture_checks" + "github.com/openziti/edge-api/rest_model" + "github.com/openziti/edge-api/rest_util" + "github.com/openziti/ziti/internal/rest/mgmt" + "strings" +) + +func (u *Upload) ProcessPostureChecks(input map[string][]interface{}) (map[string]string, error) { + + var result = map[string]string{} + for _, data := range input["postureChecks"] { + + // convert to a jsonquery doc so we can query inside the json + jsonData, _ := json.Marshal(data) + doc, jsonQueryErr := jsonquery.Parse(strings.NewReader(string(jsonData))) + if jsonQueryErr != nil { + log.WithError(jsonQueryErr).Error("Unable to list ") + return nil, jsonQueryErr + } + typeNode := jsonquery.FindOne(doc, "/typeId") + + var create rest_model.PostureCheckCreate + switch strings.ToUpper(typeNode.Value().(string)) { + case "DOMAIN": + create = FromMap(data, rest_model.PostureCheckDomainCreate{}) + case "MAC": + create = FromMap(data, rest_model.PostureCheckMacAddressCreate{}) + case "MFA": + create = FromMap(data, rest_model.PostureCheckMfaCreate{}) + case "OS": + create = FromMap(data, rest_model.PostureCheckOperatingSystemCreate{}) + case "PROCESS": + create = FromMap(data, rest_model.PostureCheckProcessCreate{}) + case "PROCESS-MULTI": + create = FromMap(data, rest_model.PostureCheckProcessMultiCreate{}) + default: + log.WithFields(map[string]interface{}{ + "name": *create.Name(), + "typeId": create.TypeID, + }). + Error("Unknown PostureCheck type") + } + + // see if the posture check already exists + existing := mgmt.PostureCheckFromFilter(u.client, mgmt.NameFilter(*create.Name())) + if existing != nil { + if u.verbose { + log.WithFields(map[string]interface{}{ + "name": *create.Name(), + "postureCheckId": (*existing).ID(), + "typeId": create.TypeID(), + }). + Info("Found existing PostureCheck, skipping create") + } + continue + } + + // do the actual create since it doesn't exist + if u.verbose { + log.WithFields(map[string]interface{}{ + "name": *create.Name(), + "typeId": create.TypeID(), + }). + Debug("Creating PostureCheck") + } + created, createErr := u.client.PostureChecks.CreatePostureCheck(&posture_checks.CreatePostureCheckParams{PostureCheck: create}, nil) + if createErr != nil { + if payloadErr, ok := createErr.(rest_util.ApiErrorPayload); ok { + log.WithFields(map[string]interface{}{ + "field": payloadErr.GetPayload().Error.Cause.APIFieldError.Field, + "reason": payloadErr.GetPayload().Error.Cause.APIFieldError.Reason, + }). + Error("Unable to create PostureCheck") + } else { + log.WithError(createErr).Error("Unable to ") + return nil, createErr + } + } + if u.verbose { + log.WithFields(map[string]interface{}{ + "name": *create.Name(), + "postureCheckId": created.Payload.Data.ID, + "typeId": create.TypeID(), + }). + Info("Created PostureCheck") + } + + result[*create.Name()] = created.Payload.Data.ID + } + + return result, nil +} diff --git a/ziti/cmd/ascode/upload/upload_service_edgerouter_policies.go b/ziti/cmd/ascode/upload/upload_service_edgerouter_policies.go new file mode 100644 index 000000000..55f7194d0 --- /dev/null +++ b/ziti/cmd/ascode/upload/upload_service_edgerouter_policies.go @@ -0,0 +1,88 @@ +/* + Copyright NetFoundry Inc. + + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at + + https://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. +*/ + +package upload + +import ( + "github.com/openziti/edge-api/rest_management_api_client/service_edge_router_policy" + "github.com/openziti/edge-api/rest_model" + "github.com/openziti/edge-api/rest_util" + "github.com/openziti/ziti/internal/rest/mgmt" +) + +func (u *Upload) ProcessServiceEdgeRouterPolicies(input map[string][]interface{}) (map[string]string, error) { + + var result = map[string]string{} + for _, data := range input["serviceEdgeRouterPolicies"] { + create := FromMap(data, rest_model.ServiceEdgeRouterPolicyCreate{}) + + // see if the service router policy already exists + existing := mgmt.ServiceEdgeRouterPolicyFromFilter(u.client, mgmt.NameFilter(*create.Name)) + if existing != nil { + log.WithFields(map[string]interface{}{ + "name": *create.Name, + "serviceRouterPolicyId": *existing.ID, + }). + Info("Found existing ServiceEdgeRouterPolicy, skipping create") + continue + } + + // look up the service ids from the name and add to the create + serviceRoles, err := u.lookupServices(create.ServiceRoles) + if err != nil { + return nil, err + } + create.ServiceRoles = serviceRoles + + // look up the edgeRouter ids from the name and add to the create + edgeRouterRoles, err := u.lookupEdgeRouters(create.EdgeRouterRoles) + if err != nil { + return nil, err + } + create.EdgeRouterRoles = edgeRouterRoles + + // do the actual create since it doesn't exist + if u.verbose { + log.WithField("name", *create.Name). + Debug("Creating ServiceEdgeRouterPolicy") + } + created, createErr := u.client.ServiceEdgeRouterPolicy.CreateServiceEdgeRouterPolicy(&service_edge_router_policy.CreateServiceEdgeRouterPolicyParams{Policy: create}, nil) + if createErr != nil { + if payloadErr, ok := createErr.(rest_util.ApiErrorPayload); ok { + log.WithFields(map[string]interface{}{ + "field": payloadErr.GetPayload().Error.Cause.APIFieldError.Field, + "reason": payloadErr.GetPayload().Error.Cause.APIFieldError.Reason, + }). + Error("Unable to create ServiceEdgeRouterPolicy") + return nil, createErr + } else { + log.WithError(createErr).Error("Unable to create ServiceEdgeRouterPolicy") + return nil, createErr + } + } + if u.verbose { + log.WithFields(map[string]interface{}{ + "name": *create.Name, + "serviceEdgeRouterPolicyId": created.Payload.Data.ID, + }). + Info("Created ServiceEdgeRouterPolicy") + } + + result[*create.Name] = created.Payload.Data.ID + } + + return result, nil +} diff --git a/ziti/cmd/ascode/upload/upload_service_policies.go b/ziti/cmd/ascode/upload/upload_service_policies.go new file mode 100644 index 000000000..93b21a73b --- /dev/null +++ b/ziti/cmd/ascode/upload/upload_service_policies.go @@ -0,0 +1,86 @@ +/* + Copyright NetFoundry Inc. + + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at + + https://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. +*/ + +package upload + +import ( + "github.com/openziti/edge-api/rest_management_api_client/service_policy" + "github.com/openziti/edge-api/rest_model" + "github.com/openziti/edge-api/rest_util" + "github.com/openziti/ziti/internal/rest/mgmt" +) + +func (u *Upload) ProcessServicePolicies(input map[string][]interface{}) (map[string]string, error) { + + var result = map[string]string{} + for _, data := range input["servicePolicies"] { + create := FromMap(data, rest_model.ServicePolicyCreate{}) + + // see if the service policy already exists + existing := mgmt.ServicePolicyFromFilter(u.client, mgmt.NameFilter(*create.Name)) + if existing != nil { + log.WithFields(map[string]interface{}{ + "name": *create.Name, + "servicePolicyId": *existing.ID, + }). + Info("Found existing ServicePolicy, skipping create") + continue + } + + // look up the service ids from the name and add to the create + serviceRoles, err := u.lookupServices(create.ServiceRoles) + if err != nil { + return nil, err + } + create.ServiceRoles = serviceRoles + + // look up the identity ids from the name and add to the create + identityRoles, err := u.lookupIdentities(create.IdentityRoles) + if err != nil { + return nil, err + } + create.IdentityRoles = identityRoles + + // do the actual create since it doesn't exist + if u.verbose { + log.WithField("name", *create.Name).Debug("Creating ServicePolicy") + } + created, createErr := u.client.ServicePolicy.CreateServicePolicy(&service_policy.CreateServicePolicyParams{Policy: create}, nil) + if createErr != nil { + if payloadErr, ok := createErr.(rest_util.ApiErrorPayload); ok { + log.WithFields(map[string]interface{}{ + "field": payloadErr.GetPayload().Error.Cause.APIFieldError.Field, + "reason": payloadErr.GetPayload().Error.Cause.APIFieldError.Reason, + }). + Error("Unable to create ServicePolicy") + } else { + log.WithError(createErr).Error("Unable to ") + return nil, createErr + } + } + if u.verbose { + log.WithFields(map[string]interface{}{ + "name": *create.Name, + "servicePolicyId": created.Payload.Data.ID, + }). + Info("Created ServicePolicy") + } + + result[*create.Name] = created.Payload.Data.ID + } + + return result, nil +} diff --git a/ziti/cmd/ascode/upload/upload_services.go b/ziti/cmd/ascode/upload/upload_services.go new file mode 100644 index 000000000..e2f776ffb --- /dev/null +++ b/ziti/cmd/ascode/upload/upload_services.go @@ -0,0 +1,121 @@ +/* + Copyright NetFoundry Inc. + + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at + + https://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. +*/ + +package upload + +import ( + "encoding/json" + "errors" + "github.com/antchfx/jsonquery" + "github.com/openziti/edge-api/rest_management_api_client/service" + "github.com/openziti/edge-api/rest_model" + "github.com/openziti/edge-api/rest_util" + common "github.com/openziti/ziti/internal/ascode" + "github.com/openziti/ziti/internal/rest/mgmt" + "strings" +) + +func (u *Upload) ProcessServices(input map[string][]interface{}) (map[string]string, error) { + + var result = map[string]string{} + + for _, data := range input["services"] { + create := FromMap(data, rest_model.ServiceCreate{}) + + // see if the service already exists + existing := mgmt.ServiceFromFilter(u.client, mgmt.NameFilter(*create.Name)) + if existing != nil { + log.WithFields(map[string]interface{}{ + "name": *create.Name, + "serviceId": *existing.ID, + }). + Info("Found existing Service, skipping create") + continue + } + + // convert to a jsonquery doc so we can query inside the json + jsonData, _ := json.Marshal(data) + doc, jsonQueryErr := jsonquery.Parse(strings.NewReader(string(jsonData))) + if jsonQueryErr != nil { + log.WithError(jsonQueryErr).Error("Unable to ") + return nil, jsonQueryErr + } + configsNode := jsonquery.FindOne(doc, "/configs") + + // look up each config by name and add to the create + configIds := []string{} + for _, configName := range configsNode.ChildNodes() { + value := configName.Value().(string)[1:] + config, _ := common.GetItemFromCache(u.configCache, value, func(name string) (interface{}, error) { + return mgmt.ConfigFromFilter(u.client, mgmt.NameFilter(name)), nil + }) + if config == nil { + return nil, errors.New("error reading Config: " + value) + } + configIds = append(configIds, *config.(*rest_model.ConfigDetail).ID) + } + create.Configs = configIds + + // do the actual create since it doesn't exist + if u.verbose { + log.WithField("name", *create.Name).Debug("Creating Service") + } + created, createErr := u.client.Service.CreateService(&service.CreateServiceParams{Service: create}, nil) + if createErr != nil { + if payloadErr, ok := createErr.(rest_util.ApiErrorPayload); ok { + log.WithFields(map[string]interface{}{ + "field": payloadErr.GetPayload().Error.Cause.APIFieldError.Field, + "reason": payloadErr.GetPayload().Error.Cause.APIFieldError.Reason, + }). + Error("Unable to create Service") + } else { + log.WithError(createErr).Error("Unable to create Service") + return nil, createErr + } + } + if u.verbose { + log.WithFields(map[string]interface{}{ + "name": *create.Name, + "serviceId": created.Payload.Data.ID, + }). + Info("Created Service") + } + + result[*create.Name] = created.Payload.Data.ID + } + + return result, nil +} + +func (u *Upload) lookupServices(roles []string) ([]string, error) { + serviceRoles := []string{} + for _, role := range roles { + if role[0:1] == "@" { + value := role[1:] + service, _ := common.GetItemFromCache(u.serviceCache, value, func(name string) (interface{}, error) { + return mgmt.ServiceFromFilter(u.client, mgmt.NameFilter(name)), nil + }) + if service == nil { + return nil, errors.New("error reading Service: " + value) + } + serviceId := service.(*rest_model.ServiceDetail).ID + serviceRoles = append(serviceRoles, "@"+*serviceId) + } else { + serviceRoles = append(serviceRoles, role) + } + } + return serviceRoles, nil +} From 8f3c4e52b1fc25ef01cf8781406a0649fcf28fad Mon Sep 17 00:00:00 2001 From: Jens Alm Date: Wed, 4 Dec 2024 12:01:50 -0500 Subject: [PATCH 04/16] 2515 Fixed verbose flag. Added output when importing. --- ziti/cmd/ascode/download/download.go | 30 +++++++++------ ziti/cmd/ascode/download/output.go | 4 +- ziti/cmd/ascode/upload/upload.go | 37 +++++++++++++++---- .../cmd/ascode/upload/upload_auth_policies.go | 3 ++ .../upload/upload_certificate_authorities.go | 3 ++ ziti/cmd/ascode/upload/upload_config_types.go | 3 ++ ziti/cmd/ascode/upload/upload_configs.go | 3 ++ .../upload/upload_edgerouter_policies.go | 3 ++ ziti/cmd/ascode/upload/upload_edgerouters.go | 3 ++ .../upload/upload_external_jwt_signers.go | 3 ++ ziti/cmd/ascode/upload/upload_identities.go | 12 +++--- .../cmd/ascode/upload/upload_posture_check.go | 3 ++ .../upload_service_edgerouter_policies.go | 3 ++ .../ascode/upload/upload_service_policies.go | 3 ++ ziti/cmd/ascode/upload/upload_services.go | 3 ++ ziti/cmd/cmd.go | 2 + 16 files changed, 92 insertions(+), 26 deletions(-) diff --git a/ziti/cmd/ascode/download/download.go b/ziti/cmd/ascode/download/download.go index dcf683787..fa117e137 100644 --- a/ziti/cmd/ascode/download/download.go +++ b/ziti/cmd/ascode/download/download.go @@ -55,6 +55,9 @@ type Download struct { configTypeCache *cache.Cache authPolicyCache *cache.Cache externalJwtCache *cache.Cache + + Out io.Writer + Err io.Writer } var output Output @@ -73,7 +76,11 @@ func NewDownload(loginOpts edge.LoginOptions, client *rest_management_api_client func NewDownloadCmd(out io.Writer, errOut io.Writer) *cobra.Command { d := &Download{} - downloadCmd := &cobra.Command{ + d.Out = out + d.Err = errOut + d.loginOpts = edge.LoginOptions{} + + cmd := &cobra.Command{ Use: "export [entity]", Short: "Export Ziti entities", Long: "Export all or selected Ziti entities.\n" + @@ -108,22 +115,23 @@ func NewDownloadCmd(out io.Writer, errOut io.Writer) *cobra.Command { v.AutomaticEnv() - downloadCmd.Flags().BoolVar(&d.ofJson, "json", true, "Output in JSON") - downloadCmd.Flags().BoolVar(&d.ofYaml, "yaml", false, "Output in YAML") - downloadCmd.MarkFlagsMutuallyExclusive("json", "yaml") + cmd.Flags().SetInterspersed(true) + cmd.Flags().BoolVar(&d.ofJson, "json", true, "Output in JSON") + cmd.Flags().BoolVar(&d.ofYaml, "yaml", false, "Output in YAML") + cmd.MarkFlagsMutuallyExclusive("json", "yaml") - downloadCmd.PersistentFlags().StringVarP(&d.filename, "output-file", "o", "", "Write output to local file") + cmd.Flags().StringVarP(&d.filename, "output-file", "o", "", "Write output to local file") - downloadCmd.PersistentFlags().BoolVarP(&d.verbose, "verbose", "v", false, "Enable verbose logging") - - edge.AddLoginFlags(downloadCmd, &d.loginOpts) + edge.AddLoginFlags(cmd, &d.loginOpts) d.loginOpts.Out = out d.loginOpts.Err = errOut - return downloadCmd + return cmd } func (d *Download) Init(out io.Writer) error { + d.verbose = d.loginOpts.Verbose + logLvl := logrus.InfoLevel if d.verbose { logLvl = logrus.DebugLevel @@ -346,7 +354,7 @@ func (d *Download) getEntities(entityName string, count ClientCount, list Client more := true for more { resp, err := list(&offset, &limit) - _, _ = fmt.Fprintf(os.Stderr, "\u001B[2KReading %d/%d %s\r", offset, totalCount, entityName) + _, _ = fmt.Fprintf(d.Err, "\u001B[2KReading %d/%d %s\r", offset, totalCount, entityName) if err != nil { return nil, errors.Join(errors.New("error reading "+entityName), err) } @@ -365,7 +373,7 @@ func (d *Download) getEntities(entityName string, count ClientCount, list Client offset += limit } - _, _ = fmt.Fprintf(os.Stderr, "\u001B[2KRead %d %s\r\n", len(result), entityName) + _, _ = fmt.Fprintf(d.Err, "\u001B[2KRead %d %s\r\n", len(result), entityName) return result, nil diff --git a/ziti/cmd/ascode/download/output.go b/ziti/cmd/ascode/download/output.go index 99a5a8fa2..72de5efa9 100644 --- a/ziti/cmd/ascode/download/output.go +++ b/ziti/cmd/ascode/download/output.go @@ -94,11 +94,11 @@ func (output Output) Write(data any) error { "bytes": bytes, "filename": output.filename, }). - Debug("Wrote json data") + Debug("Wrote data") } else { log. WithField("bytes", bytes). - Debug("Wrote json data") + Debug("Wrote data") } } diff --git a/ziti/cmd/ascode/upload/upload.go b/ziti/cmd/ascode/upload/upload.go index ac3d77e70..91016f3d4 100644 --- a/ziti/cmd/ascode/upload/upload.go +++ b/ziti/cmd/ascode/upload/upload.go @@ -19,6 +19,7 @@ package upload import ( "encoding/json" "errors" + "fmt" "github.com/judedaryl/go-arrayutils" "github.com/michaelquigley/pfxlog" "github.com/openziti/edge-api/rest_management_api_client" @@ -54,6 +55,9 @@ type Upload struct { authPolicyCache *cache.Cache extJwtSignersCache *cache.Cache identityCache *cache.Cache + + Out io.Writer + Err io.Writer } var log = pfxlog.Logger() @@ -61,7 +65,11 @@ var log = pfxlog.Logger() func NewUploadCmd(out io.Writer, errOut io.Writer) *cobra.Command { u := &Upload{} - uploadCmd := &cobra.Command{ + u.Out = out + u.Err = errOut + u.loginOpts = edge.LoginOptions{} + + cmd := &cobra.Command{ Use: "import filename [entity]", Short: "Import ziti entities", Long: "Import all or selected ziti entities from the specified file.\n" + @@ -108,20 +116,21 @@ func NewUploadCmd(out io.Writer, errOut io.Writer) *cobra.Command { v.SetEnvKeyReplacer(strings.NewReplacer("-", "_")) v.AutomaticEnv() - uploadCmd.Flags().BoolVar(&u.ofJson, "json", true, "Input parsed as JSON") - uploadCmd.Flags().BoolVar(&u.ofYaml, "yaml", false, "Input parsed as YAML") - uploadCmd.MarkFlagsMutuallyExclusive("json", "yaml") + cmd.Flags().SetInterspersed(true) + cmd.Flags().BoolVar(&u.ofJson, "json", true, "Input parsed as JSON") + cmd.Flags().BoolVar(&u.ofYaml, "yaml", false, "Input parsed as YAML") + cmd.MarkFlagsMutuallyExclusive("json", "yaml") - uploadCmd.PersistentFlags().BoolVarP(&u.verbose, "verbose", "v", false, "Enable verbose logging") - - edge.AddLoginFlags(uploadCmd, &u.loginOpts) + edge.AddLoginFlags(cmd, &u.loginOpts) u.loginOpts.Out = out u.loginOpts.Err = errOut - return uploadCmd + return cmd } func (u *Upload) Init() { + u.verbose = u.loginOpts.Verbose + logLvl := logrus.InfoLevel if u.verbose { logLvl = logrus.DebugLevel @@ -179,6 +188,7 @@ func (u *Upload) Execute(data map[string][]interface{}, inputArgs []string) (map } } result["certificateAuthorities"] = cas + _, _ = fmt.Fprintf(u.Err, "\u001B[2KCreated %d CertificateAuthorities\r\n", len(cas)) externalJwtSigners := map[string]string{} if all || @@ -200,6 +210,7 @@ func (u *Upload) Execute(data map[string][]interface{}, inputArgs []string) (map Debug("ExtJWTSigners created") } } + _, _ = fmt.Fprintf(u.Err, "\u001B[2KCreated %d ExtJWTSigners\r\n", len(externalJwtSigners)) result["externalJwtSigners"] = externalJwtSigners authPolicies := map[string]string{} @@ -221,6 +232,7 @@ func (u *Upload) Execute(data map[string][]interface{}, inputArgs []string) (map Debug("AuthPolicies created") } } + _, _ = fmt.Fprintf(u.Err, "\u001B[2KCreated %d AuthPolicies\r\n", len(authPolicies)) result["authPolicies"] = authPolicies identities := map[string]string{} @@ -241,6 +253,7 @@ func (u *Upload) Execute(data map[string][]interface{}, inputArgs []string) (map Debug("Identities created") } } + _, _ = fmt.Fprintf(u.Err, "\u001B[2KCreated %d Identities\r\n", len(identities)) result["identities"] = identities configTypes := map[string]string{} @@ -263,6 +276,7 @@ func (u *Upload) Execute(data map[string][]interface{}, inputArgs []string) (map Debug("ConfigTypes created") } } + _, _ = fmt.Fprintf(u.Err, "\u001B[2KCreated %d ConfigTypes\r\n", len(configTypes)) result["configTypes"] = configTypes configs := map[string]string{} @@ -284,6 +298,7 @@ func (u *Upload) Execute(data map[string][]interface{}, inputArgs []string) (map Debug("Configs created") } } + _, _ = fmt.Fprintf(u.Err, "\u001B[2KCreated %d Configs\r\n", len(configs)) result["configs"] = configs services := map[string]string{} @@ -304,6 +319,7 @@ func (u *Upload) Execute(data map[string][]interface{}, inputArgs []string) (map Debug("Services created") } } + _, _ = fmt.Fprintf(u.Err, "\u001B[2KCreated %d Services\r\n", len(services)) result["services"] = services postureChecks := map[string]string{} @@ -324,6 +340,7 @@ func (u *Upload) Execute(data map[string][]interface{}, inputArgs []string) (map Debug("PostureChecks created") } } + _, _ = fmt.Fprintf(u.Err, "\u001B[2KCreated %d PostureChecks\r\n", len(postureChecks)) result["postureChecks"] = postureChecks routers := map[string]string{} @@ -345,6 +362,7 @@ func (u *Upload) Execute(data map[string][]interface{}, inputArgs []string) (map Debug("EdgeRouters created") } } + _, _ = fmt.Fprintf(u.Err, "\u001B[2KCreated %d EdgeRouters\r\n", len(routers)) result["edgeRouters"] = routers serviceEdgeRouterPolicies := map[string]string{} @@ -365,6 +383,7 @@ func (u *Upload) Execute(data map[string][]interface{}, inputArgs []string) (map Debug("ServiceEdgeRouterPolicies created") } } + _, _ = fmt.Fprintf(u.Err, "\u001B[2KCreated %d ServiceEdgeRouterPolicies\r\n", len(serviceEdgeRouterPolicies)) result["serviceEdgeRouterPolicies"] = serviceEdgeRouterPolicies servicePolicies := map[string]string{} @@ -385,6 +404,7 @@ func (u *Upload) Execute(data map[string][]interface{}, inputArgs []string) (map Debug("ServicePolicies created") } } + _, _ = fmt.Fprintf(u.Err, "\u001B[2KCreated %d ServicePolicies\r\n", len(servicePolicies)) result["servicePolicies"] = servicePolicies routerPolicies := map[string]string{} @@ -405,6 +425,7 @@ func (u *Upload) Execute(data map[string][]interface{}, inputArgs []string) (map Debug("EdgeRouterPolicies created") } } + _, _ = fmt.Fprintf(u.Err, "\u001B[2KCreated %d EdgeRouterPolicies\r\n", len(routerPolicies)) result["edgeRouterPolicies"] = routerPolicies if u.verbose { diff --git a/ziti/cmd/ascode/upload/upload_auth_policies.go b/ziti/cmd/ascode/upload/upload_auth_policies.go index 23dc3b888..a921df3ec 100644 --- a/ziti/cmd/ascode/upload/upload_auth_policies.go +++ b/ziti/cmd/ascode/upload/upload_auth_policies.go @@ -18,6 +18,7 @@ package upload import ( "encoding/json" + "fmt" "github.com/antchfx/jsonquery" "github.com/openziti/edge-api/rest_management_api_client/auth_policy" "github.com/openziti/edge-api/rest_model" @@ -47,6 +48,7 @@ func (u *Upload) ProcessAuthPolicies(input map[string][]interface{}) (map[string "authPolicyId": *existing.ID, }).Info("Found existing Auth Policy, skipping create") } + _, _ = fmt.Fprintf(u.Err, "\u001B[2KSkipping AuthPolicy %s\r", *create.Name) continue } @@ -75,6 +77,7 @@ func (u *Upload) ProcessAuthPolicies(input map[string][]interface{}) (map[string create.Primary.ExtJWT.AllowedSigners = allowedSignerIds // do the actual create since it doesn't exist + _, _ = fmt.Fprintf(u.Err, "\u001B[2KCreating AuthPolicy %s\r", *create.Name) if u.verbose { log.WithField("name", *create.Name). Debug("Creating AuthPolicy") diff --git a/ziti/cmd/ascode/upload/upload_certificate_authorities.go b/ziti/cmd/ascode/upload/upload_certificate_authorities.go index 748f9ce52..80efb82b8 100644 --- a/ziti/cmd/ascode/upload/upload_certificate_authorities.go +++ b/ziti/cmd/ascode/upload/upload_certificate_authorities.go @@ -17,6 +17,7 @@ package upload import ( + "fmt" "github.com/openziti/edge-api/rest_management_api_client/certificate_authority" "github.com/openziti/edge-api/rest_model" "github.com/openziti/edge-api/rest_util" @@ -39,10 +40,12 @@ func (u *Upload) ProcessCertificateAuthorities(input map[string][]interface{}) ( }). Info("Found existing CertificateAuthority, skipping create") } + _, _ = fmt.Fprintf(u.Err, "\u001B[2KSkipping CertificateAuthority %s\r", *create.Name) continue } // do the actual create since it doesn't exist + _, _ = fmt.Fprintf(u.Err, "\u001B[2KCreating CertificateAuthority %s\r", *create.Name) created, createErr := u.client.CertificateAuthority.CreateCa(&certificate_authority.CreateCaParams{Ca: create}, nil) if createErr != nil { if payloadErr, ok := createErr.(rest_util.ApiErrorPayload); ok { diff --git a/ziti/cmd/ascode/upload/upload_config_types.go b/ziti/cmd/ascode/upload/upload_config_types.go index d09fec5fc..6ba8060e7 100644 --- a/ziti/cmd/ascode/upload/upload_config_types.go +++ b/ziti/cmd/ascode/upload/upload_config_types.go @@ -17,6 +17,7 @@ package upload import ( + "fmt" "github.com/openziti/edge-api/rest_management_api_client/config" "github.com/openziti/edge-api/rest_model" "github.com/openziti/edge-api/rest_util" @@ -39,10 +40,12 @@ func (u *Upload) ProcessConfigTypes(input map[string][]interface{}) (map[string] }). Info("Found existing ConfigType, skipping create") } + _, _ = fmt.Fprintf(u.Err, "\u001B[2KSkipping ConfigType %s\r", *create.Name) continue } // do the actual create since it doesn't exist + _, _ = fmt.Fprintf(u.Err, "\u001B[2KCreating ConfigType %s\r", *create.Name) if u.verbose { log.WithField("name", *create.Name). Debug("Creating ConfigType") diff --git a/ziti/cmd/ascode/upload/upload_configs.go b/ziti/cmd/ascode/upload/upload_configs.go index 5156bf9e7..098bcc418 100644 --- a/ziti/cmd/ascode/upload/upload_configs.go +++ b/ziti/cmd/ascode/upload/upload_configs.go @@ -19,6 +19,7 @@ package upload import ( "encoding/json" "errors" + "fmt" "github.com/antchfx/jsonquery" "github.com/openziti/edge-api/rest_management_api_client/config" "github.com/openziti/edge-api/rest_model" @@ -45,6 +46,7 @@ func (u *Upload) ProcessConfigs(input map[string][]interface{}) (map[string]stri }). Info("Found existing Config, skipping create") } + _, _ = fmt.Fprintf(u.Err, "\u001B[2KSkipping Config %s\r", *create.Name) continue } @@ -67,6 +69,7 @@ func (u *Upload) ProcessConfigs(input map[string][]interface{}) (map[string]stri create.ConfigTypeID = configType.(*rest_model.ConfigTypeDetail).ID // do the actual create since it doesn't exist + _, _ = fmt.Fprintf(u.Err, "\u001B[2KCreating Config %s\r", *create.Name) if u.verbose { log.WithField("name", *create.Name).Debug("Creating Config") } diff --git a/ziti/cmd/ascode/upload/upload_edgerouter_policies.go b/ziti/cmd/ascode/upload/upload_edgerouter_policies.go index ced071757..9ae876245 100644 --- a/ziti/cmd/ascode/upload/upload_edgerouter_policies.go +++ b/ziti/cmd/ascode/upload/upload_edgerouter_policies.go @@ -17,6 +17,7 @@ package upload import ( + "fmt" "github.com/openziti/edge-api/rest_management_api_client/edge_router_policy" "github.com/openziti/edge-api/rest_model" "github.com/openziti/edge-api/rest_util" @@ -37,6 +38,7 @@ func (u *Upload) ProcessEdgeRouterPolicies(input map[string][]interface{}) (map[ "edgeRouterPolicyId": *existing.ID, }). Info("Found existing EdgeRouterPolicy, skipping create") + _, _ = fmt.Fprintf(u.Err, "\u001B[2KSkipping EdgeRouterPolicy %s\r", *create.Name) continue } @@ -55,6 +57,7 @@ func (u *Upload) ProcessEdgeRouterPolicies(input map[string][]interface{}) (map[ create.IdentityRoles = identityRoles // do the actual create since it doesn't exist + _, _ = fmt.Fprintf(u.Err, "\u001B[2KCreating EdgeRouterPolicy %s\r", *create.Name) if u.verbose { log.WithField("name", *create.Name).Debug("Creating EdgeRouterPolicy") } diff --git a/ziti/cmd/ascode/upload/upload_edgerouters.go b/ziti/cmd/ascode/upload/upload_edgerouters.go index 6538db19d..c24802064 100644 --- a/ziti/cmd/ascode/upload/upload_edgerouters.go +++ b/ziti/cmd/ascode/upload/upload_edgerouters.go @@ -18,6 +18,7 @@ package upload import ( "errors" + "fmt" "github.com/openziti/edge-api/rest_management_api_client/edge_router" "github.com/openziti/edge-api/rest_model" "github.com/openziti/edge-api/rest_util" @@ -39,10 +40,12 @@ func (u *Upload) ProcessEdgeRouters(input map[string][]interface{}) (map[string] "edgeRouterId": *existing.ID, }). Info("Found existing EdgeRouter, skipping create") + _, _ = fmt.Fprintf(u.Err, "\u001B[2KSkipping EdgeRouter %s\r", *create.Name) continue } // do the actual create since it doesn't exist + _, _ = fmt.Fprintf(u.Err, "\u001B[2KCreating EdgeRouterPolicy %s\r", *create.Name) if u.verbose { log.WithField("name", *create.Name).Debug("Creating EdgeRouter") } diff --git a/ziti/cmd/ascode/upload/upload_external_jwt_signers.go b/ziti/cmd/ascode/upload/upload_external_jwt_signers.go index a7bd1473a..753c32898 100644 --- a/ziti/cmd/ascode/upload/upload_external_jwt_signers.go +++ b/ziti/cmd/ascode/upload/upload_external_jwt_signers.go @@ -17,6 +17,7 @@ package upload import ( + "fmt" "github.com/openziti/edge-api/rest_management_api_client/external_jwt_signer" "github.com/openziti/edge-api/rest_model" "github.com/openziti/edge-api/rest_util" @@ -39,10 +40,12 @@ func (u *Upload) ProcessExternalJwtSigners(input map[string][]interface{}) (map[ }). Info("Found existing ExtJWTSigner, skipping create") } + _, _ = fmt.Fprintf(u.Err, "\u001B[2KSkipping ExtJWTSigner %s\r", *create.Name) continue } // do the actual create since it doesn't exist + _, _ = fmt.Fprintf(u.Err, "\u001B[2KCreating ExtJWTSigner %s\r", *create.Name) if u.verbose { log.WithField("name", *create.Name).Debug("Creating ExtJWTSigner") } diff --git a/ziti/cmd/ascode/upload/upload_identities.go b/ziti/cmd/ascode/upload/upload_identities.go index 2c090ed0d..a6d50270b 100644 --- a/ziti/cmd/ascode/upload/upload_identities.go +++ b/ziti/cmd/ascode/upload/upload_identities.go @@ -19,6 +19,7 @@ package upload import ( "encoding/json" "errors" + "fmt" "github.com/antchfx/jsonquery" "github.com/openziti/edge-api/rest_management_api_client/identity" "github.com/openziti/edge-api/rest_model" @@ -44,6 +45,7 @@ func (u *Upload) ProcessIdentities(input map[string][]interface{}) (map[string]s }). Info("Found existing Identity, skipping create") } + _, _ = fmt.Fprintf(u.Err, "\u001B[2KSkipping Identity %s\r", *create.Name) continue } @@ -55,8 +57,7 @@ func (u *Upload) ProcessIdentities(input map[string][]interface{}) (map[string]s jsonData, _ := json.Marshal(data) doc, jsonQueryErr := jsonquery.Parse(strings.NewReader(string(jsonData))) if jsonQueryErr != nil { - log.WithError(jsonQueryErr). - Error("Unable to list Identities") + log.WithError(jsonQueryErr).Error("Unable to list Identities") return nil, jsonQueryErr } policyName := jsonquery.FindOne(doc, "/authPolicy").Value().(string)[1:] @@ -73,6 +74,7 @@ func (u *Upload) ProcessIdentities(input map[string][]interface{}) (map[string]s } // do the actual create since it doesn't exist + _, _ = fmt.Fprintf(u.Err, "\u001B[2KCreating Identity %s\r", *create.Name) created, createErr := u.client.Identity.CreateIdentity(&identity.CreateIdentityParams{Identity: create}, nil) if createErr != nil { if payloadErr, ok := createErr.(rest_util.ApiErrorPayload); ok { @@ -106,13 +108,13 @@ func (u *Upload) lookupIdentities(roles []string) ([]string, error) { for _, role := range roles { if role[0:1] == "@" { value := role[1:] - identity, _ := common.GetItemFromCache(u.identityCache, value, func(name string) (interface{}, error) { + ident, _ := common.GetItemFromCache(u.identityCache, value, func(name string) (interface{}, error) { return mgmt.IdentityFromFilter(u.client, mgmt.NameFilter(name)), nil }) - if identity == nil { + if ident == nil { return nil, errors.New("error reading Identity: " + value) } - identityId := identity.(*rest_model.IdentityDetail).ID + identityId := ident.(*rest_model.IdentityDetail).ID identityRoles = append(identityRoles, "@"+*identityId) } else { identityRoles = append(identityRoles, role) diff --git a/ziti/cmd/ascode/upload/upload_posture_check.go b/ziti/cmd/ascode/upload/upload_posture_check.go index 7a4d3ef3b..7281dc5a3 100644 --- a/ziti/cmd/ascode/upload/upload_posture_check.go +++ b/ziti/cmd/ascode/upload/upload_posture_check.go @@ -18,6 +18,7 @@ package upload import ( "encoding/json" + "fmt" "github.com/antchfx/jsonquery" "github.com/openziti/edge-api/rest_management_api_client/posture_checks" "github.com/openziti/edge-api/rest_model" @@ -73,10 +74,12 @@ func (u *Upload) ProcessPostureChecks(input map[string][]interface{}) (map[strin }). Info("Found existing PostureCheck, skipping create") } + _, _ = fmt.Fprintf(u.Err, "\u001B[2KSkipping PostureCheck %s\r", create.Name()) continue } // do the actual create since it doesn't exist + _, _ = fmt.Fprintf(u.Err, "\u001B[2KCreating PostureCheck %s\r", create.Name()) if u.verbose { log.WithFields(map[string]interface{}{ "name": *create.Name(), diff --git a/ziti/cmd/ascode/upload/upload_service_edgerouter_policies.go b/ziti/cmd/ascode/upload/upload_service_edgerouter_policies.go index 55f7194d0..22b3cafec 100644 --- a/ziti/cmd/ascode/upload/upload_service_edgerouter_policies.go +++ b/ziti/cmd/ascode/upload/upload_service_edgerouter_policies.go @@ -17,6 +17,7 @@ package upload import ( + "fmt" "github.com/openziti/edge-api/rest_management_api_client/service_edge_router_policy" "github.com/openziti/edge-api/rest_model" "github.com/openziti/edge-api/rest_util" @@ -37,6 +38,7 @@ func (u *Upload) ProcessServiceEdgeRouterPolicies(input map[string][]interface{} "serviceRouterPolicyId": *existing.ID, }). Info("Found existing ServiceEdgeRouterPolicy, skipping create") + _, _ = fmt.Fprintf(u.Err, "\u001B[2KSkipping ServiceEdgeRouterPolicy %s\r", *create.Name) continue } @@ -55,6 +57,7 @@ func (u *Upload) ProcessServiceEdgeRouterPolicies(input map[string][]interface{} create.EdgeRouterRoles = edgeRouterRoles // do the actual create since it doesn't exist + _, _ = fmt.Fprintf(u.Err, "\u001B[2KCreating ServiceEdgeRouterPolicy %s\r", *create.Name) if u.verbose { log.WithField("name", *create.Name). Debug("Creating ServiceEdgeRouterPolicy") diff --git a/ziti/cmd/ascode/upload/upload_service_policies.go b/ziti/cmd/ascode/upload/upload_service_policies.go index 93b21a73b..51d786783 100644 --- a/ziti/cmd/ascode/upload/upload_service_policies.go +++ b/ziti/cmd/ascode/upload/upload_service_policies.go @@ -17,6 +17,7 @@ package upload import ( + "fmt" "github.com/openziti/edge-api/rest_management_api_client/service_policy" "github.com/openziti/edge-api/rest_model" "github.com/openziti/edge-api/rest_util" @@ -37,6 +38,7 @@ func (u *Upload) ProcessServicePolicies(input map[string][]interface{}) (map[str "servicePolicyId": *existing.ID, }). Info("Found existing ServicePolicy, skipping create") + _, _ = fmt.Fprintf(u.Err, "\u001B[2KSkipping ServicePolicy %s\r", *create.Name) continue } @@ -55,6 +57,7 @@ func (u *Upload) ProcessServicePolicies(input map[string][]interface{}) (map[str create.IdentityRoles = identityRoles // do the actual create since it doesn't exist + _, _ = fmt.Fprintf(u.Err, "\u001B[2KSkipping ServicePolicy %s\r", *create.Name) if u.verbose { log.WithField("name", *create.Name).Debug("Creating ServicePolicy") } diff --git a/ziti/cmd/ascode/upload/upload_services.go b/ziti/cmd/ascode/upload/upload_services.go index e2f776ffb..965523310 100644 --- a/ziti/cmd/ascode/upload/upload_services.go +++ b/ziti/cmd/ascode/upload/upload_services.go @@ -19,6 +19,7 @@ package upload import ( "encoding/json" "errors" + "fmt" "github.com/antchfx/jsonquery" "github.com/openziti/edge-api/rest_management_api_client/service" "github.com/openziti/edge-api/rest_model" @@ -43,6 +44,7 @@ func (u *Upload) ProcessServices(input map[string][]interface{}) (map[string]str "serviceId": *existing.ID, }). Info("Found existing Service, skipping create") + _, _ = fmt.Fprintf(u.Err, "\u001B[2KSkipping Service %s\r", *create.Name) continue } @@ -70,6 +72,7 @@ func (u *Upload) ProcessServices(input map[string][]interface{}) (map[string]str create.Configs = configIds // do the actual create since it doesn't exist + _, _ = fmt.Fprintf(u.Err, "\u001B[2KCreating Service %s\r", *create.Name) if u.verbose { log.WithField("name", *create.Name).Debug("Creating Service") } diff --git a/ziti/cmd/cmd.go b/ziti/cmd/cmd.go index 1131c218e..35cfd8f34 100644 --- a/ziti/cmd/cmd.go +++ b/ziti/cmd/cmd.go @@ -19,6 +19,7 @@ package cmd import ( goflag "flag" "fmt" + "github.com/openziti/ziti/ziti/cmd/ascode/upload" "io" "os" "path/filepath" @@ -147,6 +148,7 @@ func NewCmdRoot(in io.Reader, out, err io.Writer, cmd *cobra.Command) *cobra.Com opsCommands.AddCommand(verify.NewVerifyNetwork(out, err)) opsCommands.AddCommand(verify.NewVerifyTraffic(out, err)) opsCommands.AddCommand(download.NewDownloadCmd(out, err)) + opsCommands.AddCommand(upload.NewUploadCmd(out, err)) groups := templates.CommandGroups{ { From bcd157b382c8c574dcaee152bb0cf01ace227b19 Mon Sep 17 00:00:00 2001 From: Jens Alm Date: Wed, 4 Dec 2024 18:55:13 -0500 Subject: [PATCH 05/16] 2515 Fixed lint issues. --- ziti/cmd/ascode/upload/upload_posture_check.go | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/ziti/cmd/ascode/upload/upload_posture_check.go b/ziti/cmd/ascode/upload/upload_posture_check.go index 7281dc5a3..b0c786d35 100644 --- a/ziti/cmd/ascode/upload/upload_posture_check.go +++ b/ziti/cmd/ascode/upload/upload_posture_check.go @@ -74,12 +74,12 @@ func (u *Upload) ProcessPostureChecks(input map[string][]interface{}) (map[strin }). Info("Found existing PostureCheck, skipping create") } - _, _ = fmt.Fprintf(u.Err, "\u001B[2KSkipping PostureCheck %s\r", create.Name()) + _, _ = fmt.Fprintf(u.Err, "\u001B[2KSkipping PostureCheck %s\r", *create.Name()) continue } // do the actual create since it doesn't exist - _, _ = fmt.Fprintf(u.Err, "\u001B[2KCreating PostureCheck %s\r", create.Name()) + _, _ = fmt.Fprintf(u.Err, "\u001B[2KCreating PostureCheck %s\r", *create.Name()) if u.verbose { log.WithFields(map[string]interface{}{ "name": *create.Name(), From bd1bfe2a4a1644995f0d799d4eb6a0a99945fad4 Mon Sep 17 00:00:00 2001 From: Jens Alm Date: Wed, 4 Dec 2024 18:59:55 -0500 Subject: [PATCH 06/16] 2515 Fixed formatting --- internal/log_format.go | 21 +++++++++++---------- internal/rest/mgmt/helpers.go | 21 +++++++++++---------- ziti/cmd/verify/ops_verify_network.go | 21 +++++++++++---------- 3 files changed, 33 insertions(+), 30 deletions(-) diff --git a/internal/log_format.go b/internal/log_format.go index 291e58c0d..f9d76df30 100644 --- a/internal/log_format.go +++ b/internal/log_format.go @@ -1,18 +1,19 @@ /* -Copyright NetFoundry Inc. + Copyright NetFoundry Inc. -Licensed under the Apache License, Version 2.0 (the "License"); -you may not use this file except in compliance with the License. -You may obtain a copy of the License at + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at -https://www.apache.org/licenses/LICENSE-2.0 + https://www.apache.org/licenses/LICENSE-2.0 -Unless required by applicable law or agreed to in writing, software -distributed under the License is distributed on an "AS IS" BASIS, -WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -See the License for the specific language governing permissions and -limitations under the License. + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. */ + package internal import ( diff --git a/internal/rest/mgmt/helpers.go b/internal/rest/mgmt/helpers.go index 7746b5ab3..782916cc0 100644 --- a/internal/rest/mgmt/helpers.go +++ b/internal/rest/mgmt/helpers.go @@ -1,18 +1,19 @@ /* -Copyright NetFoundry Inc. + Copyright NetFoundry Inc. -Licensed under the Apache License, Version 2.0 (the "License"); -you may not use this file except in compliance with the License. -You may obtain a copy of the License at + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at -https://www.apache.org/licenses/LICENSE-2.0 + https://www.apache.org/licenses/LICENSE-2.0 -Unless required by applicable law or agreed to in writing, software -distributed under the License is distributed on an "AS IS" BASIS, -WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -See the License for the specific language governing permissions and -limitations under the License. + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. */ + package mgmt import ( diff --git a/ziti/cmd/verify/ops_verify_network.go b/ziti/cmd/verify/ops_verify_network.go index 3be2eb963..8fe7a405e 100644 --- a/ziti/cmd/verify/ops_verify_network.go +++ b/ziti/cmd/verify/ops_verify_network.go @@ -1,18 +1,19 @@ /* -Copyright NetFoundry Inc. + Copyright NetFoundry Inc. -Licensed under the Apache License, Version 2.0 (the "License"); -you may not use this file except in compliance with the License. -You may obtain a copy of the License at + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at -https://www.apache.org/licenses/LICENSE-2.0 + https://www.apache.org/licenses/LICENSE-2.0 -Unless required by applicable law or agreed to in writing, software -distributed under the License is distributed on an "AS IS" BASIS, -WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -See the License for the specific language governing permissions and -limitations under the License. + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. */ + package verify import ( From 498c206d76e1b45d28738cc1f1ce0f33b401052c Mon Sep 17 00:00:00 2001 From: Jens Alm Date: Mon, 6 Jan 2025 19:44:56 -0500 Subject: [PATCH 07/16] 2515 Fixed input reference. Fixed error handling for missing identities. --- internal/ascode/cache_util.go | 33 ++++++++++++++----- ziti/cmd/ascode/download/download.go | 2 +- ziti/cmd/ascode/upload/upload_identities.go | 13 +++++--- .../ascode/upload/upload_service_policies.go | 3 +- 4 files changed, 36 insertions(+), 15 deletions(-) diff --git a/internal/ascode/cache_util.go b/internal/ascode/cache_util.go index 14557c36e..cf1c56028 100644 --- a/internal/ascode/cache_util.go +++ b/internal/ascode/cache_util.go @@ -1,9 +1,26 @@ +/* + Copyright NetFoundry Inc. + + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at + + https://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. +*/ + package common import ( "errors" "github.com/patrickmn/go-cache" - "log/slog" + log "github.com/sirupsen/logrus" + "reflect" ) type CacheGetter func(id string) (interface{}, error) @@ -14,19 +31,19 @@ func GetItemFromCache(c *cache.Cache, key string, fn CacheGetter) (interface{}, } detail, found := c.Get(key) if !found { - slog. - With("key", key). - Debug("Item not in cache, getting from source") + log.WithFields(map[string]interface{}{"key": key}).Debug("Item not in cache, getting from source") var err error detail, err = fn(key) if err != nil { + log.WithFields(map[string]interface{}{"key": key}).WithError(err).Debug("Error reading from source, returning error") return nil, errors.Join(errors.New("error reading: "+key), err) } - c.Set(key, detail, cache.NoExpiration) + if detail != nil && !reflect.ValueOf(detail).IsNil() { + log.WithFields(map[string]interface{}{"key": key, "item": detail}).Debug("Item read from source, caching") + c.Set(key, detail, cache.NoExpiration) + } return detail, nil } - slog. - With("key", key). - Debug("Item found in cache") + log.WithFields(map[string]interface{}{"key": key}).Debug("Item found in cache") return detail, nil } diff --git a/ziti/cmd/ascode/download/download.go b/ziti/cmd/ascode/download/download.go index fa117e137..8149292a0 100644 --- a/ziti/cmd/ascode/download/download.go +++ b/ziti/cmd/ascode/download/download.go @@ -216,7 +216,7 @@ func (d *Download) Execute(input []string) error { if err != nil { return err } - result["routers"] = routers + result["edgeRouters"] = routers } if all || slices.Contains(args, "service") || slices.Contains(args, "services") { diff --git a/ziti/cmd/ascode/upload/upload_identities.go b/ziti/cmd/ascode/upload/upload_identities.go index a6d50270b..a1aa8d8cb 100644 --- a/ziti/cmd/ascode/upload/upload_identities.go +++ b/ziti/cmd/ascode/upload/upload_identities.go @@ -107,15 +107,18 @@ func (u *Upload) lookupIdentities(roles []string) ([]string, error) { identityRoles := []string{} for _, role := range roles { if role[0:1] == "@" { - value := role[1:] - ident, _ := common.GetItemFromCache(u.identityCache, value, func(name string) (interface{}, error) { + roleName := role[1:] + value, lookupErr := common.GetItemFromCache(u.identityCache, roleName, func(name string) (interface{}, error) { return mgmt.IdentityFromFilter(u.client, mgmt.NameFilter(name)), nil }) + if lookupErr != nil { + return nil, lookupErr + } + ident := value.(*rest_model.IdentityDetail) if ident == nil { - return nil, errors.New("error reading Identity: " + value) + return nil, errors.New("error reading Identity: " + roleName) } - identityId := ident.(*rest_model.IdentityDetail).ID - identityRoles = append(identityRoles, "@"+*identityId) + identityRoles = append(identityRoles, "@"+*ident.ID) } else { identityRoles = append(identityRoles, role) } diff --git a/ziti/cmd/ascode/upload/upload_service_policies.go b/ziti/cmd/ascode/upload/upload_service_policies.go index 51d786783..923508e90 100644 --- a/ziti/cmd/ascode/upload/upload_service_policies.go +++ b/ziti/cmd/ascode/upload/upload_service_policies.go @@ -17,6 +17,7 @@ package upload import ( + "errors" "fmt" "github.com/openziti/edge-api/rest_management_api_client/service_policy" "github.com/openziti/edge-api/rest_model" @@ -52,7 +53,7 @@ func (u *Upload) ProcessServicePolicies(input map[string][]interface{}) (map[str // look up the identity ids from the name and add to the create identityRoles, err := u.lookupIdentities(create.IdentityRoles) if err != nil { - return nil, err + return nil, errors.Join(errors.New("Unable to read all identities from ServicePolicy"), err) } create.IdentityRoles = identityRoles From 6c26540110819353dd5a6e9fede8a7b4c1bf0fb5 Mon Sep 17 00:00:00 2001 From: Jens Alm Date: Tue, 7 Jan 2025 13:04:01 -0500 Subject: [PATCH 08/16] Refactor internal util usage and improve error handling. --- internal/ascode/cache_util.go | 2 +- internal/print.go | 11 + internal/rest/mgmt/helpers.go | 28 +-- ziti/cmd/ascode/download/download.go | 105 +++------ .../ascode/download/download_auth_policies.go | 6 +- ziti/cmd/ascode/download/download_configs.go | 4 +- .../ascode/download/download_identities.go | 4 +- ziti/cmd/ascode/download/download_services.go | 4 +- ziti/cmd/ascode/download/output.go | 18 +- ziti/cmd/ascode/upload/upload.go | 203 +++++------------- .../cmd/ascode/upload/upload_auth_policies.go | 18 +- .../upload/upload_certificate_authorities.go | 10 +- ziti/cmd/ascode/upload/upload_config_types.go | 12 +- ziti/cmd/ascode/upload/upload_configs.go | 16 +- .../upload/upload_edgerouter_policies.go | 10 +- ziti/cmd/ascode/upload/upload_edgerouters.go | 14 +- .../upload/upload_external_jwt_signers.go | 12 +- ziti/cmd/ascode/upload/upload_identities.go | 16 +- .../cmd/ascode/upload/upload_posture_check.go | 12 +- .../upload_service_edgerouter_policies.go | 10 +- .../ascode/upload/upload_service_policies.go | 10 +- ziti/cmd/ascode/upload/upload_services.go | 16 +- zititest/go.sum | 5 - 23 files changed, 206 insertions(+), 340 deletions(-) create mode 100644 internal/print.go diff --git a/internal/ascode/cache_util.go b/internal/ascode/cache_util.go index cf1c56028..f8bb8aa5c 100644 --- a/internal/ascode/cache_util.go +++ b/internal/ascode/cache_util.go @@ -14,7 +14,7 @@ limitations under the License. */ -package common +package ascode import ( "errors" diff --git a/internal/print.go b/internal/print.go new file mode 100644 index 000000000..8f966255a --- /dev/null +++ b/internal/print.go @@ -0,0 +1,11 @@ +package internal + +import "fmt" +import "io" + +/* +Extends the standard FPrintF with overwriting the current line because it has the `\u001B[2K` +*/ +func FPrintFReusingLine(writer io.Writer, format string, a ...any) (n int, err error) { + return fmt.Fprintf(writer, "\u001B[2K"+format, a) +} diff --git a/internal/rest/mgmt/helpers.go b/internal/rest/mgmt/helpers.go index 782916cc0..128f49838 100644 --- a/internal/rest/mgmt/helpers.go +++ b/internal/rest/mgmt/helpers.go @@ -44,12 +44,16 @@ import ( "time" ) +const ( + DefaultTimeout = 5 * time.Second +) + func IdentityFromFilter(client *rest_management_api_client.ZitiEdgeManagement, filter string) *rest_model.IdentityDetail { params := &identity.ListIdentitiesParams{ Filter: &filter, Context: context.Background(), } - params.SetTimeout(5 * time.Second) + params.SetTimeout(DefaultTimeout) resp, err := client.Identity.ListIdentities(params, nil) if err != nil { log.Debugf("Could not obtain an ID for the identity with filter %s: %v", filter, err) @@ -67,7 +71,7 @@ func ServiceFromFilter(client *rest_management_api_client.ZitiEdgeManagement, fi Filter: &filter, Context: context.Background(), } - params.SetTimeout(5 * time.Second) + params.SetTimeout(DefaultTimeout) resp, err := client.Service.ListServices(params, nil) if err != nil { log.Debugf("Could not obtain an ID for the service with filter %s: %v", filter, err) @@ -84,7 +88,7 @@ func ServicePolicyFromFilter(client *rest_management_api_client.ZitiEdgeManageme Filter: &filter, Context: context.Background(), } - params.SetTimeout(5 * time.Second) + params.SetTimeout(DefaultTimeout) resp, err := client.ServicePolicy.ListServicePolicies(params, nil) if err != nil { log.Errorf("Could not obtain an ID for the service policy with filter %s: %v", filter, err) @@ -101,7 +105,7 @@ func AuthPolicyFromFilter(client *rest_management_api_client.ZitiEdgeManagement, Filter: &filter, Context: context.Background(), } - params.SetTimeout(5 * time.Second) + params.SetTimeout(DefaultTimeout) resp, err := client.AuthPolicy.ListAuthPolicies(params, nil) if err != nil { log.Errorf("Could not obtain an ID for the auth policy with filter %s: %v", filter, err) @@ -118,7 +122,7 @@ func CertificateAuthorityFromFilter(client *rest_management_api_client.ZitiEdgeM Filter: &filter, Context: context.Background(), } - params.SetTimeout(5 * time.Second) + params.SetTimeout(DefaultTimeout) resp, err := client.CertificateAuthority.ListCas(params, nil) if err != nil { log.Errorf("Could not obtain an ID for the certificate authority with filter %s: %v", filter, err) @@ -135,7 +139,7 @@ func ConfigTypeFromFilter(client *rest_management_api_client.ZitiEdgeManagement, Filter: &filter, Context: context.Background(), } - params.SetTimeout(5 * time.Second) + params.SetTimeout(DefaultTimeout) resp, err := client.Config.ListConfigTypes(params, nil) if err != nil { log.Errorf("Could not obtain an ID for the config type with filter %s: %v", filter, err) @@ -152,7 +156,7 @@ func ConfigFromFilter(client *rest_management_api_client.ZitiEdgeManagement, fil Filter: &filter, Context: context.Background(), } - params.SetTimeout(5 * time.Second) + params.SetTimeout(DefaultTimeout) resp, err := client.Config.ListConfigs(params, nil) if err != nil { log.Errorf("Could not obtain an ID for the config with filter %s: %v", filter, err) @@ -169,7 +173,7 @@ func ExternalJWTSignerFromFilter(client *rest_management_api_client.ZitiEdgeMana Filter: &filter, Context: context.Background(), } - params.SetTimeout(5 * time.Second) + params.SetTimeout(DefaultTimeout) resp, err := client.ExternalJWTSigner.ListExternalJWTSigners(params, nil) if err != nil { log.Errorf("Could not obtain an ID for the external jwt signer with filter %s: %v", filter, err) @@ -186,7 +190,7 @@ func PostureCheckFromFilter(client *rest_management_api_client.ZitiEdgeManagemen Filter: &filter, Context: context.Background(), } - params.SetTimeout(5 * time.Second) + params.SetTimeout(DefaultTimeout) resp, err := client.PostureChecks.ListPostureChecks(params, nil) if err != nil { log.Errorf("Could not obtain an ID for the posture check with filter %s: %v", filter, err) @@ -202,7 +206,7 @@ func EdgeRouterPolicyFromFilter(client *rest_management_api_client.ZitiEdgeManag params := &edge_router_policy.ListEdgeRouterPoliciesParams{ Filter: &filter, } - params.SetTimeout(5 * time.Second) + params.SetTimeout(DefaultTimeout) resp, err := client.EdgeRouterPolicy.ListEdgeRouterPolicies(params, nil) if err != nil { log.Errorf("Could not obtain an ID for the edge router policies with filter %s: %v", filter, err) @@ -218,7 +222,7 @@ func EdgeRouterFromFilter(client *rest_management_api_client.ZitiEdgeManagement, params := &edge_router.ListEdgeRoutersParams{ Filter: &filter, } - params.SetTimeout(5 * time.Second) + params.SetTimeout(DefaultTimeout) resp, err := client.EdgeRouter.ListEdgeRouters(params, nil) if err != nil { log.Errorf("Could not obtain an ID for the edge routers with filter %s: %v", filter, err) @@ -234,7 +238,7 @@ func ServiceEdgeRouterPolicyFromFilter(client *rest_management_api_client.ZitiEd params := &service_edge_router_policy.ListServiceEdgeRouterPoliciesParams{ Filter: &filter, } - params.SetTimeout(5 * time.Second) + params.SetTimeout(DefaultTimeout) resp, err := client.ServiceEdgeRouterPolicy.ListServiceEdgeRouterPolicies(params, nil) if err != nil { log.Errorf("Could not obtain an ID for the ServiceEdgeRouterPolicy routers with filter %s: %v", filter, err) diff --git a/ziti/cmd/ascode/download/download.go b/ziti/cmd/ascode/download/download.go index 8149292a0..8cbf6b55d 100644 --- a/ziti/cmd/ascode/download/download.go +++ b/ziti/cmd/ascode/download/download.go @@ -19,14 +19,13 @@ package download import ( "encoding/json" "errors" - "fmt" "github.com/judedaryl/go-arrayutils" "github.com/michaelquigley/pfxlog" "github.com/openziti/edge-api/rest_management_api_client" "github.com/openziti/ziti/internal" "github.com/openziti/ziti/internal/rest/mgmt" "github.com/openziti/ziti/ziti/cmd/edge" - c "github.com/openziti/ziti/ziti/constants" + "github.com/openziti/ziti/ziti/constants" "github.com/patrickmn/go-cache" "github.com/sirupsen/logrus" "github.com/spf13/cobra" @@ -40,50 +39,29 @@ import ( var log = pfxlog.Logger() type Download struct { - loginOpts edge.LoginOptions - client *rest_management_api_client.ZitiEdgeManagement - - verbose bool - - ofJson bool - ofYaml bool - - file *os.File - filename string - + loginOpts edge.LoginOptions + client *rest_management_api_client.ZitiEdgeManagement + ofJson bool + ofYaml bool + file *os.File + filename string configCache *cache.Cache configTypeCache *cache.Cache authPolicyCache *cache.Cache externalJwtCache *cache.Cache - - Out io.Writer - Err io.Writer } var output Output -func NewDownload(loginOpts edge.LoginOptions, client *rest_management_api_client.ZitiEdgeManagement, ofJson bool, ofYaml bool, file *os.File, filename string) Download { - d := Download{} - d.loginOpts = loginOpts - d.client = client - d.ofJson = ofJson - d.ofYaml = ofYaml - d.file = file - d.filename = filename - return d -} - func NewDownloadCmd(out io.Writer, errOut io.Writer) *cobra.Command { d := &Download{} - d.Out = out - d.Err = errOut d.loginOpts = edge.LoginOptions{} cmd := &cobra.Command{ Use: "export [entity]", - Short: "Export Ziti entities", - Long: "Export all or selected Ziti entities.\n" + + Short: "Export entities", + Long: "Export all or selected entities.\n" + "Valid entities are: [all|ca/certificate-authority|identity|edge-router|service|config|config-type|service-policy|edgerouter-policy|service-edgerouter-policy|external-jwt-signer|auth-policy|posture-check] (default all)", Args: cobra.MinimumNArgs(0), PersistentPreRun: func(cmd *cobra.Command, args []string) { @@ -107,7 +85,7 @@ func NewDownloadCmd(out io.Writer, errOut io.Writer) *cobra.Command { // environment variables are prefixed, d.g. a flag like --number // binds to an environment variable STING_NUMBER. This helps // avoid conflicts. - viper.SetEnvPrefix(c.ZITI) // All env vars we seek will be prefixed with "ZITI_" + viper.SetEnvPrefix(constants.ZITI) // All env vars we seek will be prefixed with "ZITI_" // Environment variables can't have dashes in them, so bind them to their equivalent // keys with underscores, d.g. --favorite-color to STING_FAVORITE_COLOR @@ -130,10 +108,9 @@ func NewDownloadCmd(out io.Writer, errOut io.Writer) *cobra.Command { } func (d *Download) Init(out io.Writer) error { - d.verbose = d.loginOpts.Verbose logLvl := logrus.InfoLevel - if d.verbose { + if d.loginOpts.Verbose { logLvl = logrus.DebugLevel } @@ -154,13 +131,13 @@ func (d *Download) Init(out io.Writer) error { d.client = client if d.filename != "" { - o, err := NewOutputToFile(d.verbose, d.ofJson, d.ofYaml, d.filename) + o, err := NewOutputToFile(d.loginOpts.Verbose, d.ofJson, d.ofYaml, d.filename, d.loginOpts.Err) if err != nil { return err } output = *o } else { - o, err := NewOutputToWriter(d.verbose, d.ofJson, d.ofYaml, out) + o, err := NewOutputToWriter(d.loginOpts.Verbose, d.ofJson, d.ofYaml, out, d.loginOpts.Err) if err != nil { return err } @@ -185,9 +162,7 @@ func (d *Download) Execute(input []string) error { if all || slices.Contains(args, "ca") || slices.Contains(args, "cas") || slices.Contains(args, "certificate-authority") || slices.Contains(args, "certificate-authorities") { - if d.verbose { - log.Debug("Processing Certificate Authorities") - } + log.Debug("Processing Certificate Authorities") cas, err := d.GetCertificateAuthorities() if err != nil { return err @@ -196,9 +171,7 @@ func (d *Download) Execute(input []string) error { } if all || slices.Contains(args, "identity") || slices.Contains(args, "identities") { - if d.verbose { - log.Debug("Processing Identities") - } + log.Debug("Processing Identities") identities, err := d.GetIdentities() if err != nil { return err @@ -209,9 +182,7 @@ func (d *Download) Execute(input []string) error { if all || slices.Contains(args, "edge-router") || slices.Contains(args, "edge-routers") || slices.Contains(args, "er") || slices.Contains(args, "ers") { - if d.verbose { - log.Debug("Processing Edge Routers") - } + log.Debug("Processing Edge Routers") routers, err := d.GetEdgeRouters() if err != nil { return err @@ -220,9 +191,7 @@ func (d *Download) Execute(input []string) error { } if all || slices.Contains(args, "service") || slices.Contains(args, "services") { - if d.verbose { - log.Debug("Processing Services") - } + log.Debug("Processing Services") services, err := d.GetServices() if err != nil { return err @@ -231,9 +200,7 @@ func (d *Download) Execute(input []string) error { } if all || slices.Contains(args, "config") || slices.Contains(args, "configs") { - if d.verbose { - log.Debug("Processing Configs") - } + log.Debug("Processing Configs") configs, err := d.GetConfigs() if err != nil { return err @@ -242,9 +209,7 @@ func (d *Download) Execute(input []string) error { } if all || slices.Contains(args, "config-type") || slices.Contains(args, "config-types") { - if d.verbose { - log.Debug("Processing Config Types") - } + log.Debug("Processing Config Types") configTypes, err := d.GetConfigTypes() if err != nil { return err @@ -253,9 +218,7 @@ func (d *Download) Execute(input []string) error { } if all || slices.Contains(args, "service-policy") || slices.Contains(args, "service-policies") { - if d.verbose { - log.Debug("Processing Service Policies") - } + log.Debug("Processing Service Policies") servicePolicies, err := d.GetServicePolicies() if err != nil { return err @@ -264,9 +227,7 @@ func (d *Download) Execute(input []string) error { } if all || slices.Contains(args, "edgerouter-policy") || slices.Contains(args, "edgerouter-policies") { - if d.verbose { - log.Debug("Processing Router Policies") - } + log.Debug("Processing Router Policies") routerPolicies, err := d.GetRouterPolicies() if err != nil { return err @@ -275,9 +236,7 @@ func (d *Download) Execute(input []string) error { } if all || slices.Contains(args, "service-edgerouter-policy") || slices.Contains(args, "service-edgerouter-policies") { - if d.verbose { - log.Debug("Processing Service EdgeRouter Policies") - } + log.Debug("Processing Service EdgeRouter Policies") serviceRouterPolicies, err := d.GetServiceEdgeRouterPolicies() if err != nil { return err @@ -286,9 +245,7 @@ func (d *Download) Execute(input []string) error { } if all || slices.Contains(args, "external-jwt-signer") || slices.Contains(args, "external-jwt-signers") { - if d.verbose { - log.Debug("Processing External JWT Signers") - } + log.Debug("Processing External JWT Signers") externalJwtSigners, err := d.GetExternalJwtSigners() if err != nil { return err @@ -297,9 +254,7 @@ func (d *Download) Execute(input []string) error { } if all || slices.Contains(args, "auth-policy") || slices.Contains(args, "auth-policies") { - if d.verbose { - log.Debug("Processing Auth Policies") - } + log.Debug("Processing Auth Policies") authPolicies, err := d.GetAuthPolicies() if err != nil { return err @@ -308,9 +263,7 @@ func (d *Download) Execute(input []string) error { } if all || slices.Contains(args, "posture-check") || slices.Contains(args, "posture-checks") { - if d.verbose { - log.Debug("Processing Posture Checks") - } + log.Debug("Processing Posture Checks") postureChecks, err := d.GetPostureChecks() if err != nil { return err @@ -318,9 +271,7 @@ func (d *Download) Execute(input []string) error { result["postureChecks"] = postureChecks } - if d.verbose { - log.Debug("Download complete") - } + log.Debug("Download complete") err := output.Write(result) if err != nil { @@ -354,7 +305,7 @@ func (d *Download) getEntities(entityName string, count ClientCount, list Client more := true for more { resp, err := list(&offset, &limit) - _, _ = fmt.Fprintf(d.Err, "\u001B[2KReading %d/%d %s\r", offset, totalCount, entityName) + _, _ = internal.FPrintFReusingLine(d.loginOpts.Err, "Reading %d/%d %s\r", offset, totalCount, entityName) if err != nil { return nil, errors.Join(errors.New("error reading "+entityName), err) } @@ -373,7 +324,7 @@ func (d *Download) getEntities(entityName string, count ClientCount, list Client offset += limit } - _, _ = fmt.Fprintf(d.Err, "\u001B[2KRead %d %s\r\n", len(result), entityName) + _, _ = internal.FPrintFReusingLine(d.loginOpts.Err, "Read %d %s\r\n", len(result), entityName) return result, nil diff --git a/ziti/cmd/ascode/download/download_auth_policies.go b/ziti/cmd/ascode/download/download_auth_policies.go index f04fe94aa..8a03a8161 100644 --- a/ziti/cmd/ascode/download/download_auth_policies.go +++ b/ziti/cmd/ascode/download/download_auth_policies.go @@ -20,7 +20,7 @@ import ( "github.com/openziti/edge-api/rest_management_api_client/auth_policy" "github.com/openziti/edge-api/rest_management_api_client/external_jwt_signer" "github.com/openziti/edge-api/rest_model" - common "github.com/openziti/ziti/internal/ascode" + "github.com/openziti/ziti/internal/ascode" ) func (d Download) GetAuthPolicies() ([]map[string]interface{}, error) { @@ -72,7 +72,7 @@ func (d Download) GetAuthPolicies() ([]map[string]interface{}, error) { delete(extJwt, "allowedSigners") signers := []string{} for _, signer := range item.Primary.ExtJWT.AllowedSigners { - extJwtSigner, lookupErr := common.GetItemFromCache(d.externalJwtCache, signer, func(id string) (interface{}, error) { + extJwtSigner, lookupErr := ascode.GetItemFromCache(d.externalJwtCache, signer, func(id string) (interface{}, error) { return d.client.ExternalJWTSigner.DetailExternalJWTSigner( &external_jwt_signer.DetailExternalJWTSignerParams{ID: id}, nil) }) @@ -93,7 +93,7 @@ func (d Download) GetAuthPolicies() ([]map[string]interface{}, error) { // deleting RequiredExtJwtSigner because it needs to use a reference to the name instead of the ID delete(secondary, "requiredExtJwtSigner") requiredExtJwtSigner := d.ToMap(item.Secondary.RequireExtJWTSigner) - extJwtSigner, lookupErr := common.GetItemFromCache(d.externalJwtCache, *item.Secondary.RequireExtJWTSigner, func(id string) (interface{}, error) { + extJwtSigner, lookupErr := ascode.GetItemFromCache(d.externalJwtCache, *item.Secondary.RequireExtJWTSigner, func(id string) (interface{}, error) { return d.client.ExternalJWTSigner.DetailExternalJWTSigner(&external_jwt_signer.DetailExternalJWTSignerParams{ID: id}, nil) }) if lookupErr != nil { diff --git a/ziti/cmd/ascode/download/download_configs.go b/ziti/cmd/ascode/download/download_configs.go index 410b4d7ac..489f3b9c4 100644 --- a/ziti/cmd/ascode/download/download_configs.go +++ b/ziti/cmd/ascode/download/download_configs.go @@ -20,7 +20,7 @@ import ( "errors" "github.com/openziti/edge-api/rest_management_api_client/config" "github.com/openziti/edge-api/rest_model" - common "github.com/openziti/ziti/internal/ascode" + "github.com/openziti/ziti/internal/ascode" ) func (d Download) GetConfigs() ([]map[string]interface{}, error) { @@ -59,7 +59,7 @@ func (d Download) GetConfigs() ([]map[string]interface{}, error) { // translate ids to names delete(m, "configType") delete(m, "configTypeId") - configType, lookupErr := common.GetItemFromCache(d.configTypeCache, *item.ConfigTypeID, func(id string) (interface{}, error) { + configType, lookupErr := ascode.GetItemFromCache(d.configTypeCache, *item.ConfigTypeID, func(id string) (interface{}, error) { return d.client.Config.DetailConfigType(&config.DetailConfigTypeParams{ID: id}, nil) }) if lookupErr != nil { diff --git a/ziti/cmd/ascode/download/download_identities.go b/ziti/cmd/ascode/download/download_identities.go index 7c453f548..ca22bed54 100644 --- a/ziti/cmd/ascode/download/download_identities.go +++ b/ziti/cmd/ascode/download/download_identities.go @@ -21,7 +21,7 @@ import ( "github.com/openziti/edge-api/rest_management_api_client/auth_policy" "github.com/openziti/edge-api/rest_management_api_client/identity" "github.com/openziti/edge-api/rest_model" - common "github.com/openziti/ziti/internal/ascode" + "github.com/openziti/ziti/internal/ascode" ) func (d Download) GetIdentities() ([]map[string]interface{}, error) { @@ -72,7 +72,7 @@ func (d Download) GetIdentities() ([]map[string]interface{}, error) { } // translate ids to names - authPolicy, lookupErr := common.GetItemFromCache(d.authPolicyCache, *item.AuthPolicyID, func(id string) (interface{}, error) { + authPolicy, lookupErr := ascode.GetItemFromCache(d.authPolicyCache, *item.AuthPolicyID, func(id string) (interface{}, error) { return d.client.AuthPolicy.DetailAuthPolicy(&auth_policy.DetailAuthPolicyParams{ID: id}, nil) }) if lookupErr != nil { diff --git a/ziti/cmd/ascode/download/download_services.go b/ziti/cmd/ascode/download/download_services.go index 50d18bd45..c5402f841 100644 --- a/ziti/cmd/ascode/download/download_services.go +++ b/ziti/cmd/ascode/download/download_services.go @@ -21,7 +21,7 @@ import ( "github.com/openziti/edge-api/rest_management_api_client/config" "github.com/openziti/edge-api/rest_management_api_client/service" "github.com/openziti/edge-api/rest_model" - common "github.com/openziti/ziti/internal/ascode" + "github.com/openziti/ziti/internal/ascode" ) func (d Download) GetServices() ([]map[string]interface{}, error) { @@ -66,7 +66,7 @@ func (d Download) GetServices() ([]map[string]interface{}, error) { // translate ids to names var configNames []string for _, c := range item.Configs { - configDetail, lookupErr := common.GetItemFromCache(d.configCache, c, func(id string) (interface{}, error) { + configDetail, lookupErr := ascode.GetItemFromCache(d.configCache, c, func(id string) (interface{}, error) { return d.client.Config.DetailConfig(&config.DetailConfigParams{ID: id}, nil) }) if lookupErr != nil { diff --git a/ziti/cmd/ascode/download/output.go b/ziti/cmd/ascode/download/output.go index 72de5efa9..b81bde9c8 100644 --- a/ziti/cmd/ascode/download/output.go +++ b/ziti/cmd/ascode/download/output.go @@ -19,7 +19,7 @@ package download import ( "bufio" "encoding/json" - "fmt" + "github.com/openziti/ziti/internal" "gopkg.in/yaml.v3" "io" @@ -31,27 +31,29 @@ type Output struct { outputYaml bool filename string writer *bufio.Writer + errWriter io.Writer verbose bool } -func NewOutputToFile(verbose bool, outputJson bool, outputYaml bool, filename string) (*Output, error) { +func NewOutputToFile(verbose bool, outputJson bool, outputYaml bool, filename string, errWriter io.Writer) (*Output, error) { file, err := os.Create(filename) if err != nil { log.WithError(err).Error("Error creating file for writing") return nil, err } writer := bufio.NewWriter(file) - output, err := NewOutputToWriter(verbose, outputJson, outputYaml, writer) + output, err := NewOutputToWriter(verbose, outputJson, outputYaml, writer, errWriter) output.filename = filename return output, err } -func NewOutputToWriter(verbose bool, outputJson bool, outputYaml bool, writer io.Writer) (*Output, error) { +func NewOutputToWriter(verbose bool, outputJson bool, outputYaml bool, writer io.Writer, errWriter io.Writer) (*Output, error) { output := Output{} output.verbose = verbose output.outputJson = outputJson output.outputYaml = outputYaml output.writer = bufio.NewWriter(writer) + output.errWriter = errWriter return &output, nil } @@ -60,12 +62,12 @@ func (output Output) Write(data any) error { var err error if output.outputYaml { if output.verbose { - _, _ = fmt.Fprintf(os.Stderr, "\u001B[2KFormatting as Yaml\r\n") + _, _ = internal.FPrintFReusingLine(output.errWriter, "Formatting as Yaml\r\n") } formatted, err = output.ToYaml(data) } else { if output.verbose { - _, _ = fmt.Fprintf(os.Stderr, "\u001B[2KFormatting as JSON\r\n") + _, _ = internal.FPrintFReusingLine(output.errWriter, "Formatting as JSON\r\n") } formatted, err = output.ToJson(data) } @@ -75,9 +77,9 @@ func (output Output) Write(data any) error { if output.verbose { if output.filename != "" { - _, _ = fmt.Fprintf(os.Stderr, "\u001B[2KWriting to file: %s\r\n", output.filename) + _, _ = internal.FPrintFReusingLine(output.errWriter, "Writing to file: %s\r\n", output.filename) } else { - _, _ = fmt.Fprintf(os.Stderr, "\u001B[2KWriting output to writer\r\n") + _, _ = internal.FPrintFReusingLine(output.errWriter, "Writing output to writer\r\n") } } bytes, err := output.writer.Write(formatted) diff --git a/ziti/cmd/ascode/upload/upload.go b/ziti/cmd/ascode/upload/upload.go index 91016f3d4..e6667b1e9 100644 --- a/ziti/cmd/ascode/upload/upload.go +++ b/ziti/cmd/ascode/upload/upload.go @@ -19,14 +19,13 @@ package upload import ( "encoding/json" "errors" - "fmt" "github.com/judedaryl/go-arrayutils" "github.com/michaelquigley/pfxlog" "github.com/openziti/edge-api/rest_management_api_client" "github.com/openziti/ziti/internal" "github.com/openziti/ziti/internal/rest/mgmt" "github.com/openziti/ziti/ziti/cmd/edge" - c "github.com/openziti/ziti/ziti/constants" + "github.com/openziti/ziti/ziti/constants" "github.com/patrickmn/go-cache" "github.com/sirupsen/logrus" "github.com/spf13/cobra" @@ -40,24 +39,19 @@ import ( ) type Upload struct { - loginOpts edge.LoginOptions - client *rest_management_api_client.ZitiEdgeManagement - reader Reader - - verbose bool - - ofJson bool - ofYaml bool - + loginOpts edge.LoginOptions + client *rest_management_api_client.ZitiEdgeManagement + reader Reader + ofJson bool + ofYaml bool configCache *cache.Cache serviceCache *cache.Cache edgeRouterCache *cache.Cache authPolicyCache *cache.Cache extJwtSignersCache *cache.Cache identityCache *cache.Cache - - Out io.Writer - Err io.Writer + //Out io.Writer + //Err io.Writer } var log = pfxlog.Logger() @@ -65,14 +59,12 @@ var log = pfxlog.Logger() func NewUploadCmd(out io.Writer, errOut io.Writer) *cobra.Command { u := &Upload{} - u.Out = out - u.Err = errOut u.loginOpts = edge.LoginOptions{} cmd := &cobra.Command{ Use: "import filename [entity]", - Short: "Import ziti entities", - Long: "Import all or selected ziti entities from the specified file.\n" + + Short: "Import entities", + Long: "Import all or selected entities from the specified file.\n" + "Valid entities are: [all|ca/certificate-authority|identity|edge-router|service|config|config-type|service-policy|edgerouter-policy|service-edgerouter-policy|external-jwt-signer|auth-policy|posture-check] (default all)", Args: cobra.MinimumNArgs(1), PersistentPreRun: func(cmd *cobra.Command, args []string) { @@ -101,18 +93,14 @@ func NewUploadCmd(out io.Writer, errOut io.Writer) *cobra.Command { if executeErr != nil { panic(executeErr) } - if u.verbose { - log. - WithField("results", result). - Debug("Finished") - } + log.WithField("results", result).Debug("Finished") }, Hidden: true, } v := viper.New() - viper.SetEnvPrefix(c.ZITI) // All env vars we seek will be prefixed with "ZITI_" + viper.SetEnvPrefix(constants.ZITI) // All env vars we seek will be prefixed with "ZITI_" v.SetEnvKeyReplacer(strings.NewReplacer("-", "_")) v.AutomaticEnv() @@ -129,10 +117,10 @@ func NewUploadCmd(out io.Writer, errOut io.Writer) *cobra.Command { } func (u *Upload) Init() { - u.verbose = u.loginOpts.Verbose + u.loginOpts.Verbose = u.loginOpts.Verbose logLvl := logrus.InfoLevel - if u.verbose { + if u.loginOpts.Verbose { logLvl = logrus.DebugLevel } @@ -172,88 +160,62 @@ func (u *Upload) Execute(data map[string][]interface{}, inputArgs []string) (map if all || slices.Contains(args, "ca") || slices.Contains(args, "cas") || slices.Contains(args, "certificate-authority") || slices.Contains(args, "certificate-authorities") { - if u.verbose { - log. - Debug("Processing CertificateAuthorities") - } + log.Debug("Processing CertificateAuthorities") var err error cas, err = u.ProcessCertificateAuthorities(data) if err != nil { return nil, err } - if u.verbose { - log. - WithField("certificateAuthorities", cas). - Debug("CertificateAuthorities created") - } + log. + WithField("certificateAuthorities", cas). + Debug("CertificateAuthorities created") } result["certificateAuthorities"] = cas - _, _ = fmt.Fprintf(u.Err, "\u001B[2KCreated %d CertificateAuthorities\r\n", len(cas)) + _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Created %d CertificateAuthorities\r\n", len(cas)) externalJwtSigners := map[string]string{} if all || slices.Contains(args, "external-jwt-signer") || slices.Contains(args, "external-jwt-signers") || slices.Contains(args, "auth-policy") || slices.Contains(args, "auth-policies") || slices.Contains(args, "identity") || slices.Contains(args, "identities") { - if u.verbose { - log. - Debug("Processing ExtJWTSigners") - } + log.Debug("Processing ExtJWTSigners") var err error externalJwtSigners, err = u.ProcessExternalJwtSigners(data) if err != nil { return nil, err } - if u.verbose { - log. - WithField("externalJwtSigners", externalJwtSigners). - Debug("ExtJWTSigners created") - } + log.WithField("externalJwtSigners", externalJwtSigners).Debug("ExtJWTSigners created") } - _, _ = fmt.Fprintf(u.Err, "\u001B[2KCreated %d ExtJWTSigners\r\n", len(externalJwtSigners)) + _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Created %d ExtJWTSigners\r\n", len(externalJwtSigners)) result["externalJwtSigners"] = externalJwtSigners authPolicies := map[string]string{} if all || slices.Contains(args, "auth-policy") || slices.Contains(args, "auth-policies") || slices.Contains(args, "identity") || slices.Contains(args, "identities") { - if u.verbose { - log. - Debug("Processing AuthPolicies") - } + log.Debug("Processing AuthPolicies") var err error authPolicies, err = u.ProcessAuthPolicies(data) if err != nil { return nil, err } - if u.verbose { - log. - WithField("authPolicies", authPolicies). - Debug("AuthPolicies created") - } + log.WithField("authPolicies", authPolicies).Debug("AuthPolicies created") } - _, _ = fmt.Fprintf(u.Err, "\u001B[2KCreated %d AuthPolicies\r\n", len(authPolicies)) + _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Created %d AuthPolicies\r\n", len(authPolicies)) result["authPolicies"] = authPolicies identities := map[string]string{} if all || slices.Contains(args, "identity") || slices.Contains(args, "identities") { - if u.verbose { - log. - Debug("Processing Identities") - } + log.Debug("Processing Identities") var err error identities, err = u.ProcessIdentities(data) if err != nil { return nil, err } - if u.verbose { - log. - WithField("identities", identities). - Debug("Identities created") - } + log.WithField("identities", identities).Debug("Identities created") } - _, _ = fmt.Fprintf(u.Err, "\u001B[2KCreated %d Identities\r\n", len(identities)) + _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Created %d Identities\r\n", len(identities)) result["identities"] = identities configTypes := map[string]string{} @@ -261,177 +223,118 @@ func (u *Upload) Execute(data map[string][]interface{}, inputArgs []string) (map slices.Contains(args, "config-type") || slices.Contains(args, "config-types") || slices.Contains(args, "config") || slices.Contains(args, "configs") || slices.Contains(args, "service") || slices.Contains(args, "services") { - if u.verbose { - log. - Debug("Processing ConfigTypes") - } + log.Debug("Processing ConfigTypes") var err error configTypes, err = u.ProcessConfigTypes(data) if err != nil { return nil, err } - if u.verbose { - log. - WithField("configTypes", configTypes). - Debug("ConfigTypes created") - } + log.WithField("configTypes", configTypes).Debug("ConfigTypes created") } - _, _ = fmt.Fprintf(u.Err, "\u001B[2KCreated %d ConfigTypes\r\n", len(configTypes)) + _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Created %d ConfigTypes\r\n", len(configTypes)) result["configTypes"] = configTypes configs := map[string]string{} if all || slices.Contains(args, "config") || slices.Contains(args, "configs") || slices.Contains(args, "service") || slices.Contains(args, "services") { - if u.verbose { - log. - Debug("Processing Configs") - } + log.Debug("Processing Configs") var err error configs, err = u.ProcessConfigs(data) if err != nil { return nil, err } - if u.verbose { - log. - WithField("configs", configs). - Debug("Configs created") - } + log.WithField("configs", configs).Debug("Configs created") } - _, _ = fmt.Fprintf(u.Err, "\u001B[2KCreated %d Configs\r\n", len(configs)) + _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Created %d Configs\r\n", len(configs)) result["configs"] = configs services := map[string]string{} if all || slices.Contains(args, "service") || slices.Contains(args, "services") { - if u.verbose { - log. - Debug("Processing Services") - } + log.Debug("Processing Services") var err error services, err = u.ProcessServices(data) if err != nil { return nil, err } - if u.verbose { - log. - WithField("services", services). - Debug("Services created") - } + log.WithField("services", services).Debug("Services created") } - _, _ = fmt.Fprintf(u.Err, "\u001B[2KCreated %d Services\r\n", len(services)) + _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Created %d Services\r\n", len(services)) result["services"] = services postureChecks := map[string]string{} if all || slices.Contains(args, "posture-check") || slices.Contains(args, "posture-checks") { - if u.verbose { - log. - Debug("Processing PostureChecks") - } + log.Debug("Processing PostureChecks") var err error postureChecks, err = u.ProcessPostureChecks(data) if err != nil { return nil, err } - if u.verbose { - log. - WithField("postureChecks", postureChecks). - Debug("PostureChecks created") - } + log.WithField("postureChecks", postureChecks).Debug("PostureChecks created") } - _, _ = fmt.Fprintf(u.Err, "\u001B[2KCreated %d PostureChecks\r\n", len(postureChecks)) + _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Created %d PostureChecks\r\n", len(postureChecks)) result["postureChecks"] = postureChecks routers := map[string]string{} if all || slices.Contains(args, "edge-router") || slices.Contains(args, "edge-routers") || slices.Contains(args, "ers") || slices.Contains(args, "ers") { - if u.verbose { - log. - Debug("Processing EdgeRouters") - } + log.Debug("Processing EdgeRouters") var err error routers, err = u.ProcessEdgeRouters(data) if err != nil { return nil, err } - if u.verbose { - log. - WithField("edgeRouters", routers). - Debug("EdgeRouters created") - } + log.WithField("edgeRouters", routers).Debug("EdgeRouters created") } - _, _ = fmt.Fprintf(u.Err, "\u001B[2KCreated %d EdgeRouters\r\n", len(routers)) + _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Created %d EdgeRouters\r\n", len(routers)) result["edgeRouters"] = routers serviceEdgeRouterPolicies := map[string]string{} if all || slices.Contains(args, "service-edgerouter-policy") || slices.Contains(args, "service-edgerouter-policies") { - if u.verbose { - log. - Debug("Processing ServiceRouterPolicies") - } + log.Debug("Processing ServiceRouterPolicies") var err error serviceEdgeRouterPolicies, err = u.ProcessServiceEdgeRouterPolicies(data) if err != nil { return nil, err } - if u.verbose { - log. - WithField("serviceEdgeRouterPolicies", serviceEdgeRouterPolicies). - Debug("ServiceEdgeRouterPolicies created") - } + log.WithField("serviceEdgeRouterPolicies", serviceEdgeRouterPolicies).Debug("ServiceEdgeRouterPolicies created") } - _, _ = fmt.Fprintf(u.Err, "\u001B[2KCreated %d ServiceEdgeRouterPolicies\r\n", len(serviceEdgeRouterPolicies)) + _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Created %d ServiceEdgeRouterPolicies\r\n", len(serviceEdgeRouterPolicies)) result["serviceEdgeRouterPolicies"] = serviceEdgeRouterPolicies servicePolicies := map[string]string{} if all || slices.Contains(args, "service-policy") || slices.Contains(args, "service-policies") { - if u.verbose { - log. - Debug("Processing ServicePolicies") - } + log.Debug("Processing ServicePolicies") var err error servicePolicies, err = u.ProcessServicePolicies(data) if err != nil { return nil, err } - if u.verbose { - log. - WithField("servicePolicies", servicePolicies). - Debug("ServicePolicies created") - } + log.WithField("servicePolicies", servicePolicies).Debug("ServicePolicies created") } - _, _ = fmt.Fprintf(u.Err, "\u001B[2KCreated %d ServicePolicies\r\n", len(servicePolicies)) + _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Created %d ServicePolicies\r\n", len(servicePolicies)) result["servicePolicies"] = servicePolicies routerPolicies := map[string]string{} if all || slices.Contains(args, "edgerouter-policy") || slices.Contains(args, "edgerouter-policies") { - if u.verbose { - log. - Debug("Processing EdgeRouterPolicies") - } + log.Debug("Processing EdgeRouterPolicies") var err error routerPolicies, err = u.ProcessEdgeRouterPolicies(data) if err != nil { return nil, err } - if u.verbose { - log. - WithField("routerPolicies", routerPolicies). - Debug("EdgeRouterPolicies created") - } + log.WithField("routerPolicies", routerPolicies).Debug("EdgeRouterPolicies created") } - _, _ = fmt.Fprintf(u.Err, "\u001B[2KCreated %d EdgeRouterPolicies\r\n", len(routerPolicies)) + _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Created %d EdgeRouterPolicies\r\n", len(routerPolicies)) result["edgeRouterPolicies"] = routerPolicies - if u.verbose { - log. - Info("Upload complete") - } + log.Info("Upload complete") return result, nil } diff --git a/ziti/cmd/ascode/upload/upload_auth_policies.go b/ziti/cmd/ascode/upload/upload_auth_policies.go index a921df3ec..14dba466c 100644 --- a/ziti/cmd/ascode/upload/upload_auth_policies.go +++ b/ziti/cmd/ascode/upload/upload_auth_policies.go @@ -18,19 +18,19 @@ package upload import ( "encoding/json" - "fmt" "github.com/antchfx/jsonquery" "github.com/openziti/edge-api/rest_management_api_client/auth_policy" "github.com/openziti/edge-api/rest_model" "github.com/openziti/edge-api/rest_util" - common "github.com/openziti/ziti/internal/ascode" + "github.com/openziti/ziti/internal" + "github.com/openziti/ziti/internal/ascode" "github.com/openziti/ziti/internal/rest/mgmt" "strings" ) func (u *Upload) ProcessAuthPolicies(input map[string][]interface{}) (map[string]string, error) { - if u.verbose { + if u.loginOpts.Verbose { log.Debug("Listing all AuthPolicies") } @@ -42,13 +42,13 @@ func (u *Upload) ProcessAuthPolicies(input map[string][]interface{}) (map[string // see if the auth policy already exists existing := mgmt.AuthPolicyFromFilter(u.client, mgmt.NameFilter(*create.Name)) if existing != nil { - if u.verbose { + if u.loginOpts.Verbose { log.WithFields(map[string]interface{}{ "name": *create.Name, "authPolicyId": *existing.ID, }).Info("Found existing Auth Policy, skipping create") } - _, _ = fmt.Fprintf(u.Err, "\u001B[2KSkipping AuthPolicy %s\r", *create.Name) + _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Skipping AuthPolicy %s\r", *create.Name) continue } @@ -65,7 +65,7 @@ func (u *Upload) ProcessAuthPolicies(input map[string][]interface{}) (map[string allowedSignerIds := []string{} for _, signer := range allowedSigners.ChildNodes() { value := signer.Value().(string)[1:] - extJwtSigner, err := common.GetItemFromCache(u.extJwtSignersCache, value, func(name string) (interface{}, error) { + extJwtSigner, err := ascode.GetItemFromCache(u.extJwtSignersCache, value, func(name string) (interface{}, error) { return mgmt.ExternalJWTSignerFromFilter(u.client, mgmt.NameFilter(name)), nil }) if err != nil { @@ -77,8 +77,8 @@ func (u *Upload) ProcessAuthPolicies(input map[string][]interface{}) (map[string create.Primary.ExtJWT.AllowedSigners = allowedSignerIds // do the actual create since it doesn't exist - _, _ = fmt.Fprintf(u.Err, "\u001B[2KCreating AuthPolicy %s\r", *create.Name) - if u.verbose { + _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Creating AuthPolicy %s\r", *create.Name) + if u.loginOpts.Verbose { log.WithField("name", *create.Name). Debug("Creating AuthPolicy") } @@ -97,7 +97,7 @@ func (u *Upload) ProcessAuthPolicies(input map[string][]interface{}) (map[string } } - if u.verbose { + if u.loginOpts.Verbose { log.WithFields(map[string]interface{}{ "name": *create.Name, "authPolicyId": created.Payload.Data.ID, diff --git a/ziti/cmd/ascode/upload/upload_certificate_authorities.go b/ziti/cmd/ascode/upload/upload_certificate_authorities.go index 80efb82b8..1f4cab36a 100644 --- a/ziti/cmd/ascode/upload/upload_certificate_authorities.go +++ b/ziti/cmd/ascode/upload/upload_certificate_authorities.go @@ -17,10 +17,10 @@ package upload import ( - "fmt" "github.com/openziti/edge-api/rest_management_api_client/certificate_authority" "github.com/openziti/edge-api/rest_model" "github.com/openziti/edge-api/rest_util" + "github.com/openziti/ziti/internal" "github.com/openziti/ziti/internal/rest/mgmt" ) @@ -33,19 +33,19 @@ func (u *Upload) ProcessCertificateAuthorities(input map[string][]interface{}) ( // see if the CA already exists existing := mgmt.CertificateAuthorityFromFilter(u.client, mgmt.NameFilter(*create.Name)) if existing != nil { - if u.verbose { + if u.loginOpts.Verbose { log.WithFields(map[string]interface{}{ "name": *create.Name, "certificateAuthorityId": *existing.ID, }). Info("Found existing CertificateAuthority, skipping create") } - _, _ = fmt.Fprintf(u.Err, "\u001B[2KSkipping CertificateAuthority %s\r", *create.Name) + _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Skipping CertificateAuthority %s\r", *create.Name) continue } // do the actual create since it doesn't exist - _, _ = fmt.Fprintf(u.Err, "\u001B[2KCreating CertificateAuthority %s\r", *create.Name) + _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Creating CertificateAuthority %s\r", *create.Name) created, createErr := u.client.CertificateAuthority.CreateCa(&certificate_authority.CreateCaParams{Ca: create}, nil) if createErr != nil { if payloadErr, ok := createErr.(rest_util.ApiErrorPayload); ok { @@ -62,7 +62,7 @@ func (u *Upload) ProcessCertificateAuthorities(input map[string][]interface{}) ( return nil, createErr } } - if u.verbose { + if u.loginOpts.Verbose { log.WithFields(map[string]interface{}{ "name": *create.Name, "certificateAuthorityId": created.Payload.Data.ID, diff --git a/ziti/cmd/ascode/upload/upload_config_types.go b/ziti/cmd/ascode/upload/upload_config_types.go index 6ba8060e7..9b8e499c2 100644 --- a/ziti/cmd/ascode/upload/upload_config_types.go +++ b/ziti/cmd/ascode/upload/upload_config_types.go @@ -17,10 +17,10 @@ package upload import ( - "fmt" "github.com/openziti/edge-api/rest_management_api_client/config" "github.com/openziti/edge-api/rest_model" "github.com/openziti/edge-api/rest_util" + "github.com/openziti/ziti/internal" "github.com/openziti/ziti/internal/rest/mgmt" ) @@ -33,20 +33,20 @@ func (u *Upload) ProcessConfigTypes(input map[string][]interface{}) (map[string] // see if the config type already exists existing := mgmt.ConfigTypeFromFilter(u.client, mgmt.NameFilter(*create.Name)) if existing != nil { - if u.verbose { + if u.loginOpts.Verbose { log.WithFields(map[string]interface{}{ "name": *create.Name, "configTypeId": *existing.ID, }). Info("Found existing ConfigType, skipping create") } - _, _ = fmt.Fprintf(u.Err, "\u001B[2KSkipping ConfigType %s\r", *create.Name) + _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Skipping ConfigType %s\r", *create.Name) continue } // do the actual create since it doesn't exist - _, _ = fmt.Fprintf(u.Err, "\u001B[2KCreating ConfigType %s\r", *create.Name) - if u.verbose { + _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Creating ConfigType %s\r", *create.Name) + if u.loginOpts.Verbose { log.WithField("name", *create.Name). Debug("Creating ConfigType") } @@ -65,7 +65,7 @@ func (u *Upload) ProcessConfigTypes(input map[string][]interface{}) (map[string] return nil, createErr } - if u.verbose { + if u.loginOpts.Verbose { log.WithFields(map[string]interface{}{ "name": *create.Name, "configTypeId": created.Payload.Data.ID, diff --git a/ziti/cmd/ascode/upload/upload_configs.go b/ziti/cmd/ascode/upload/upload_configs.go index 098bcc418..d55c73ba3 100644 --- a/ziti/cmd/ascode/upload/upload_configs.go +++ b/ziti/cmd/ascode/upload/upload_configs.go @@ -19,12 +19,12 @@ package upload import ( "encoding/json" "errors" - "fmt" "github.com/antchfx/jsonquery" "github.com/openziti/edge-api/rest_management_api_client/config" "github.com/openziti/edge-api/rest_model" "github.com/openziti/edge-api/rest_util" - common "github.com/openziti/ziti/internal/ascode" + "github.com/openziti/ziti/internal" + "github.com/openziti/ziti/internal/ascode" "github.com/openziti/ziti/internal/rest/mgmt" "strings" ) @@ -38,7 +38,7 @@ func (u *Upload) ProcessConfigs(input map[string][]interface{}) (map[string]stri // see if the config already exists existing := mgmt.ConfigFromFilter(u.client, mgmt.NameFilter(*create.Name)) if existing != nil { - if u.verbose { + if u.loginOpts.Verbose { log. WithFields(map[string]interface{}{ "name": *create.Name, @@ -46,7 +46,7 @@ func (u *Upload) ProcessConfigs(input map[string][]interface{}) (map[string]stri }). Info("Found existing Config, skipping create") } - _, _ = fmt.Fprintf(u.Err, "\u001B[2KSkipping Config %s\r", *create.Name) + _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Skipping Config %s\r", *create.Name) continue } @@ -60,7 +60,7 @@ func (u *Upload) ProcessConfigs(input map[string][]interface{}) (map[string]stri // look up the config type id from the name and add to the create value := jsonquery.FindOne(doc, "/configType").Value().(string)[1:] - configType, _ := common.GetItemFromCache(u.configCache, value, func(name string) (interface{}, error) { + configType, _ := ascode.GetItemFromCache(u.configCache, value, func(name string) (interface{}, error) { return mgmt.ConfigTypeFromFilter(u.client, mgmt.NameFilter(name)), nil }) if u.configCache == nil { @@ -69,8 +69,8 @@ func (u *Upload) ProcessConfigs(input map[string][]interface{}) (map[string]stri create.ConfigTypeID = configType.(*rest_model.ConfigTypeDetail).ID // do the actual create since it doesn't exist - _, _ = fmt.Fprintf(u.Err, "\u001B[2KCreating Config %s\r", *create.Name) - if u.verbose { + _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Creating Config %s\r", *create.Name) + if u.loginOpts.Verbose { log.WithField("name", *create.Name).Debug("Creating Config") } created, createErr := u.client.Config.CreateConfig(&config.CreateConfigParams{Config: create}, nil) @@ -86,7 +86,7 @@ func (u *Upload) ProcessConfigs(input map[string][]interface{}) (map[string]stri return nil, createErr } } - if u.verbose { + if u.loginOpts.Verbose { log.WithFields(map[string]interface{}{ "name": *create.Name, "configId": created.Payload.Data.ID, diff --git a/ziti/cmd/ascode/upload/upload_edgerouter_policies.go b/ziti/cmd/ascode/upload/upload_edgerouter_policies.go index 9ae876245..e5e6b6e95 100644 --- a/ziti/cmd/ascode/upload/upload_edgerouter_policies.go +++ b/ziti/cmd/ascode/upload/upload_edgerouter_policies.go @@ -17,10 +17,10 @@ package upload import ( - "fmt" "github.com/openziti/edge-api/rest_management_api_client/edge_router_policy" "github.com/openziti/edge-api/rest_model" "github.com/openziti/edge-api/rest_util" + "github.com/openziti/ziti/internal" "github.com/openziti/ziti/internal/rest/mgmt" ) @@ -38,7 +38,7 @@ func (u *Upload) ProcessEdgeRouterPolicies(input map[string][]interface{}) (map[ "edgeRouterPolicyId": *existing.ID, }). Info("Found existing EdgeRouterPolicy, skipping create") - _, _ = fmt.Fprintf(u.Err, "\u001B[2KSkipping EdgeRouterPolicy %s\r", *create.Name) + _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Skipping EdgeRouterPolicy %s\r", *create.Name) continue } @@ -57,8 +57,8 @@ func (u *Upload) ProcessEdgeRouterPolicies(input map[string][]interface{}) (map[ create.IdentityRoles = identityRoles // do the actual create since it doesn't exist - _, _ = fmt.Fprintf(u.Err, "\u001B[2KCreating EdgeRouterPolicy %s\r", *create.Name) - if u.verbose { + _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Creating EdgeRouterPolicy %s\r", *create.Name) + if u.loginOpts.Verbose { log.WithField("name", *create.Name).Debug("Creating EdgeRouterPolicy") } created, createErr := u.client.EdgeRouterPolicy.CreateEdgeRouterPolicy(&edge_router_policy.CreateEdgeRouterPolicyParams{Policy: create}, nil) @@ -75,7 +75,7 @@ func (u *Upload) ProcessEdgeRouterPolicies(input map[string][]interface{}) (map[ return nil, createErr } } - if u.verbose { + if u.loginOpts.Verbose { log.WithFields(map[string]interface{}{ "name": *create.Name, "routerPolicyId": created.Payload.Data.ID, diff --git a/ziti/cmd/ascode/upload/upload_edgerouters.go b/ziti/cmd/ascode/upload/upload_edgerouters.go index c24802064..addc0943d 100644 --- a/ziti/cmd/ascode/upload/upload_edgerouters.go +++ b/ziti/cmd/ascode/upload/upload_edgerouters.go @@ -18,11 +18,11 @@ package upload import ( "errors" - "fmt" "github.com/openziti/edge-api/rest_management_api_client/edge_router" "github.com/openziti/edge-api/rest_model" "github.com/openziti/edge-api/rest_util" - common "github.com/openziti/ziti/internal/ascode" + "github.com/openziti/ziti/internal" + "github.com/openziti/ziti/internal/ascode" "github.com/openziti/ziti/internal/rest/mgmt" ) @@ -40,13 +40,13 @@ func (u *Upload) ProcessEdgeRouters(input map[string][]interface{}) (map[string] "edgeRouterId": *existing.ID, }). Info("Found existing EdgeRouter, skipping create") - _, _ = fmt.Fprintf(u.Err, "\u001B[2KSkipping EdgeRouter %s\r", *create.Name) + _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Skipping EdgeRouter %s\r", *create.Name) continue } // do the actual create since it doesn't exist - _, _ = fmt.Fprintf(u.Err, "\u001B[2KCreating EdgeRouterPolicy %s\r", *create.Name) - if u.verbose { + _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Creating EdgeRouterPolicy %s\r", *create.Name) + if u.loginOpts.Verbose { log.WithField("name", *create.Name).Debug("Creating EdgeRouter") } created, createErr := u.client.EdgeRouter.CreateEdgeRouter(&edge_router.CreateEdgeRouterParams{EdgeRouter: create}, nil) @@ -61,7 +61,7 @@ func (u *Upload) ProcessEdgeRouters(input map[string][]interface{}) (map[string] return nil, createErr } } - if u.verbose { + if u.loginOpts.Verbose { log.WithFields(map[string]interface{}{ "name": *create.Name, "edgeRouterId": created.Payload.Data.ID, @@ -80,7 +80,7 @@ func (u *Upload) lookupEdgeRouters(roles []string) ([]string, error) { for _, role := range roles { if role[0:1] == "@" { value := role[1:] - edgeRouter, _ := common.GetItemFromCache(u.edgeRouterCache, value, func(name string) (interface{}, error) { + edgeRouter, _ := ascode.GetItemFromCache(u.edgeRouterCache, value, func(name string) (interface{}, error) { return mgmt.EdgeRouterFromFilter(u.client, mgmt.NameFilter(name)), nil }) if edgeRouter == nil { diff --git a/ziti/cmd/ascode/upload/upload_external_jwt_signers.go b/ziti/cmd/ascode/upload/upload_external_jwt_signers.go index 753c32898..db7533447 100644 --- a/ziti/cmd/ascode/upload/upload_external_jwt_signers.go +++ b/ziti/cmd/ascode/upload/upload_external_jwt_signers.go @@ -17,10 +17,10 @@ package upload import ( - "fmt" "github.com/openziti/edge-api/rest_management_api_client/external_jwt_signer" "github.com/openziti/edge-api/rest_model" "github.com/openziti/edge-api/rest_util" + "github.com/openziti/ziti/internal" "github.com/openziti/ziti/internal/rest/mgmt" ) @@ -33,20 +33,20 @@ func (u *Upload) ProcessExternalJwtSigners(input map[string][]interface{}) (map[ // see if the signer already exists existing := mgmt.ExternalJWTSignerFromFilter(u.client, mgmt.NameFilter(*create.Name)) if existing != nil { - if u.verbose { + if u.loginOpts.Verbose { log.WithFields(map[string]interface{}{ "name": *create.Name, "externalJwtSignerId": *existing.ID, }). Info("Found existing ExtJWTSigner, skipping create") } - _, _ = fmt.Fprintf(u.Err, "\u001B[2KSkipping ExtJWTSigner %s\r", *create.Name) + _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Skipping ExtJWTSigner %s\r", *create.Name) continue } // do the actual create since it doesn't exist - _, _ = fmt.Fprintf(u.Err, "\u001B[2KCreating ExtJWTSigner %s\r", *create.Name) - if u.verbose { + _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Creating ExtJWTSigner %s\r", *create.Name) + if u.loginOpts.Verbose { log.WithField("name", *create.Name).Debug("Creating ExtJWTSigner") } created, createErr := u.client.ExternalJWTSigner.CreateExternalJWTSigner(&external_jwt_signer.CreateExternalJWTSignerParams{ExternalJWTSigner: create}, nil) @@ -64,7 +64,7 @@ func (u *Upload) ProcessExternalJwtSigners(input map[string][]interface{}) (map[ return nil, createErr } } - if u.verbose { + if u.loginOpts.Verbose { log.WithFields(map[string]interface{}{ "name": *create.Name, "externalJwtSignerId": created.Payload.Data.ID, diff --git a/ziti/cmd/ascode/upload/upload_identities.go b/ziti/cmd/ascode/upload/upload_identities.go index a1aa8d8cb..8fe9aeed4 100644 --- a/ziti/cmd/ascode/upload/upload_identities.go +++ b/ziti/cmd/ascode/upload/upload_identities.go @@ -19,12 +19,12 @@ package upload import ( "encoding/json" "errors" - "fmt" "github.com/antchfx/jsonquery" "github.com/openziti/edge-api/rest_management_api_client/identity" "github.com/openziti/edge-api/rest_model" "github.com/openziti/edge-api/rest_util" - common "github.com/openziti/ziti/internal/ascode" + "github.com/openziti/ziti/internal" + "github.com/openziti/ziti/internal/ascode" "github.com/openziti/ziti/internal/rest/mgmt" "strings" ) @@ -38,14 +38,14 @@ func (u *Upload) ProcessIdentities(input map[string][]interface{}) (map[string]s existing := mgmt.IdentityFromFilter(u.client, mgmt.NameFilter(*create.Name)) if existing != nil { - if u.verbose { + if u.loginOpts.Verbose { log.WithFields(map[string]interface{}{ "name": *create.Name, "identityId": *existing.ID, }). Info("Found existing Identity, skipping create") } - _, _ = fmt.Fprintf(u.Err, "\u001B[2KSkipping Identity %s\r", *create.Name) + _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Skipping Identity %s\r", *create.Name) continue } @@ -63,7 +63,7 @@ func (u *Upload) ProcessIdentities(input map[string][]interface{}) (map[string]s policyName := jsonquery.FindOne(doc, "/authPolicy").Value().(string)[1:] // look up the auth policy id from the name and add to the create, omit if it's the "Default" policy - policy, _ := common.GetItemFromCache(u.authPolicyCache, policyName, func(name string) (interface{}, error) { + policy, _ := ascode.GetItemFromCache(u.authPolicyCache, policyName, func(name string) (interface{}, error) { return mgmt.AuthPolicyFromFilter(u.client, mgmt.NameFilter(name)), nil }) if policy == nil { @@ -74,7 +74,7 @@ func (u *Upload) ProcessIdentities(input map[string][]interface{}) (map[string]s } // do the actual create since it doesn't exist - _, _ = fmt.Fprintf(u.Err, "\u001B[2KCreating Identity %s\r", *create.Name) + _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Creating Identity %s\r", *create.Name) created, createErr := u.client.Identity.CreateIdentity(&identity.CreateIdentityParams{Identity: create}, nil) if createErr != nil { if payloadErr, ok := createErr.(rest_util.ApiErrorPayload); ok { @@ -89,7 +89,7 @@ func (u *Upload) ProcessIdentities(input map[string][]interface{}) (map[string]s return nil, createErr } } - if u.verbose { + if u.loginOpts.Verbose { log.WithFields(map[string]interface{}{ "name": *create.Name, "identityId": created.Payload.Data.ID, @@ -108,7 +108,7 @@ func (u *Upload) lookupIdentities(roles []string) ([]string, error) { for _, role := range roles { if role[0:1] == "@" { roleName := role[1:] - value, lookupErr := common.GetItemFromCache(u.identityCache, roleName, func(name string) (interface{}, error) { + value, lookupErr := ascode.GetItemFromCache(u.identityCache, roleName, func(name string) (interface{}, error) { return mgmt.IdentityFromFilter(u.client, mgmt.NameFilter(name)), nil }) if lookupErr != nil { diff --git a/ziti/cmd/ascode/upload/upload_posture_check.go b/ziti/cmd/ascode/upload/upload_posture_check.go index b0c786d35..eb8300f0d 100644 --- a/ziti/cmd/ascode/upload/upload_posture_check.go +++ b/ziti/cmd/ascode/upload/upload_posture_check.go @@ -18,11 +18,11 @@ package upload import ( "encoding/json" - "fmt" "github.com/antchfx/jsonquery" "github.com/openziti/edge-api/rest_management_api_client/posture_checks" "github.com/openziti/edge-api/rest_model" "github.com/openziti/edge-api/rest_util" + "github.com/openziti/ziti/internal" "github.com/openziti/ziti/internal/rest/mgmt" "strings" ) @@ -66,7 +66,7 @@ func (u *Upload) ProcessPostureChecks(input map[string][]interface{}) (map[strin // see if the posture check already exists existing := mgmt.PostureCheckFromFilter(u.client, mgmt.NameFilter(*create.Name())) if existing != nil { - if u.verbose { + if u.loginOpts.Verbose { log.WithFields(map[string]interface{}{ "name": *create.Name(), "postureCheckId": (*existing).ID(), @@ -74,13 +74,13 @@ func (u *Upload) ProcessPostureChecks(input map[string][]interface{}) (map[strin }). Info("Found existing PostureCheck, skipping create") } - _, _ = fmt.Fprintf(u.Err, "\u001B[2KSkipping PostureCheck %s\r", *create.Name()) + _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Skipping PostureCheck %s\r", *create.Name()) continue } // do the actual create since it doesn't exist - _, _ = fmt.Fprintf(u.Err, "\u001B[2KCreating PostureCheck %s\r", *create.Name()) - if u.verbose { + _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Creating PostureCheck %s\r", *create.Name()) + if u.loginOpts.Verbose { log.WithFields(map[string]interface{}{ "name": *create.Name(), "typeId": create.TypeID(), @@ -100,7 +100,7 @@ func (u *Upload) ProcessPostureChecks(input map[string][]interface{}) (map[strin return nil, createErr } } - if u.verbose { + if u.loginOpts.Verbose { log.WithFields(map[string]interface{}{ "name": *create.Name(), "postureCheckId": created.Payload.Data.ID, diff --git a/ziti/cmd/ascode/upload/upload_service_edgerouter_policies.go b/ziti/cmd/ascode/upload/upload_service_edgerouter_policies.go index 22b3cafec..9364cb415 100644 --- a/ziti/cmd/ascode/upload/upload_service_edgerouter_policies.go +++ b/ziti/cmd/ascode/upload/upload_service_edgerouter_policies.go @@ -17,10 +17,10 @@ package upload import ( - "fmt" "github.com/openziti/edge-api/rest_management_api_client/service_edge_router_policy" "github.com/openziti/edge-api/rest_model" "github.com/openziti/edge-api/rest_util" + "github.com/openziti/ziti/internal" "github.com/openziti/ziti/internal/rest/mgmt" ) @@ -38,7 +38,7 @@ func (u *Upload) ProcessServiceEdgeRouterPolicies(input map[string][]interface{} "serviceRouterPolicyId": *existing.ID, }). Info("Found existing ServiceEdgeRouterPolicy, skipping create") - _, _ = fmt.Fprintf(u.Err, "\u001B[2KSkipping ServiceEdgeRouterPolicy %s\r", *create.Name) + _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Skipping ServiceEdgeRouterPolicy %s\r", *create.Name) continue } @@ -57,8 +57,8 @@ func (u *Upload) ProcessServiceEdgeRouterPolicies(input map[string][]interface{} create.EdgeRouterRoles = edgeRouterRoles // do the actual create since it doesn't exist - _, _ = fmt.Fprintf(u.Err, "\u001B[2KCreating ServiceEdgeRouterPolicy %s\r", *create.Name) - if u.verbose { + _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Creating ServiceEdgeRouterPolicy %s\r", *create.Name) + if u.loginOpts.Verbose { log.WithField("name", *create.Name). Debug("Creating ServiceEdgeRouterPolicy") } @@ -76,7 +76,7 @@ func (u *Upload) ProcessServiceEdgeRouterPolicies(input map[string][]interface{} return nil, createErr } } - if u.verbose { + if u.loginOpts.Verbose { log.WithFields(map[string]interface{}{ "name": *create.Name, "serviceEdgeRouterPolicyId": created.Payload.Data.ID, diff --git a/ziti/cmd/ascode/upload/upload_service_policies.go b/ziti/cmd/ascode/upload/upload_service_policies.go index 923508e90..59da9ab68 100644 --- a/ziti/cmd/ascode/upload/upload_service_policies.go +++ b/ziti/cmd/ascode/upload/upload_service_policies.go @@ -18,10 +18,10 @@ package upload import ( "errors" - "fmt" "github.com/openziti/edge-api/rest_management_api_client/service_policy" "github.com/openziti/edge-api/rest_model" "github.com/openziti/edge-api/rest_util" + "github.com/openziti/ziti/internal" "github.com/openziti/ziti/internal/rest/mgmt" ) @@ -39,7 +39,7 @@ func (u *Upload) ProcessServicePolicies(input map[string][]interface{}) (map[str "servicePolicyId": *existing.ID, }). Info("Found existing ServicePolicy, skipping create") - _, _ = fmt.Fprintf(u.Err, "\u001B[2KSkipping ServicePolicy %s\r", *create.Name) + _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Skipping ServicePolicy %s\r", *create.Name) continue } @@ -58,8 +58,8 @@ func (u *Upload) ProcessServicePolicies(input map[string][]interface{}) (map[str create.IdentityRoles = identityRoles // do the actual create since it doesn't exist - _, _ = fmt.Fprintf(u.Err, "\u001B[2KSkipping ServicePolicy %s\r", *create.Name) - if u.verbose { + _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Skipping ServicePolicy %s\r", *create.Name) + if u.loginOpts.Verbose { log.WithField("name", *create.Name).Debug("Creating ServicePolicy") } created, createErr := u.client.ServicePolicy.CreateServicePolicy(&service_policy.CreateServicePolicyParams{Policy: create}, nil) @@ -75,7 +75,7 @@ func (u *Upload) ProcessServicePolicies(input map[string][]interface{}) (map[str return nil, createErr } } - if u.verbose { + if u.loginOpts.Verbose { log.WithFields(map[string]interface{}{ "name": *create.Name, "servicePolicyId": created.Payload.Data.ID, diff --git a/ziti/cmd/ascode/upload/upload_services.go b/ziti/cmd/ascode/upload/upload_services.go index 965523310..8ea0f31ca 100644 --- a/ziti/cmd/ascode/upload/upload_services.go +++ b/ziti/cmd/ascode/upload/upload_services.go @@ -19,12 +19,12 @@ package upload import ( "encoding/json" "errors" - "fmt" "github.com/antchfx/jsonquery" "github.com/openziti/edge-api/rest_management_api_client/service" "github.com/openziti/edge-api/rest_model" "github.com/openziti/edge-api/rest_util" - common "github.com/openziti/ziti/internal/ascode" + "github.com/openziti/ziti/internal" + "github.com/openziti/ziti/internal/ascode" "github.com/openziti/ziti/internal/rest/mgmt" "strings" ) @@ -44,7 +44,7 @@ func (u *Upload) ProcessServices(input map[string][]interface{}) (map[string]str "serviceId": *existing.ID, }). Info("Found existing Service, skipping create") - _, _ = fmt.Fprintf(u.Err, "\u001B[2KSkipping Service %s\r", *create.Name) + _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Skipping Service %s\r", *create.Name) continue } @@ -61,7 +61,7 @@ func (u *Upload) ProcessServices(input map[string][]interface{}) (map[string]str configIds := []string{} for _, configName := range configsNode.ChildNodes() { value := configName.Value().(string)[1:] - config, _ := common.GetItemFromCache(u.configCache, value, func(name string) (interface{}, error) { + config, _ := ascode.GetItemFromCache(u.configCache, value, func(name string) (interface{}, error) { return mgmt.ConfigFromFilter(u.client, mgmt.NameFilter(name)), nil }) if config == nil { @@ -72,8 +72,8 @@ func (u *Upload) ProcessServices(input map[string][]interface{}) (map[string]str create.Configs = configIds // do the actual create since it doesn't exist - _, _ = fmt.Fprintf(u.Err, "\u001B[2KCreating Service %s\r", *create.Name) - if u.verbose { + _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Creating Service %s\r", *create.Name) + if u.loginOpts.Verbose { log.WithField("name", *create.Name).Debug("Creating Service") } created, createErr := u.client.Service.CreateService(&service.CreateServiceParams{Service: create}, nil) @@ -89,7 +89,7 @@ func (u *Upload) ProcessServices(input map[string][]interface{}) (map[string]str return nil, createErr } } - if u.verbose { + if u.loginOpts.Verbose { log.WithFields(map[string]interface{}{ "name": *create.Name, "serviceId": created.Payload.Data.ID, @@ -108,7 +108,7 @@ func (u *Upload) lookupServices(roles []string) ([]string, error) { for _, role := range roles { if role[0:1] == "@" { value := role[1:] - service, _ := common.GetItemFromCache(u.serviceCache, value, func(name string) (interface{}, error) { + service, _ := ascode.GetItemFromCache(u.serviceCache, value, func(name string) (interface{}, error) { return mgmt.ServiceFromFilter(u.client, mgmt.NameFilter(name)), nil }) if service == nil { diff --git a/zititest/go.sum b/zititest/go.sum index d9d9bd1b0..a0316a101 100644 --- a/zititest/go.sum +++ b/zititest/go.sum @@ -205,12 +205,7 @@ github.com/gaissmai/extnetip v1.1.0/go.mod h1:Ad+qyjy0r98Uc655JzzWoBTzDW29QR4YZD github.com/getkin/kin-openapi v0.13.0/go.mod h1:WGRs2ZMM1Q8LR1QBEwUxC6RJEfaBcD0s+pcEVXFuAjw= github.com/ghodss/yaml v1.0.0/go.mod h1:4dBDuWmgqj2HViK6kFavaiC9ZROes6MMH2rRYeMEF04= github.com/gliderlabs/ssh v0.1.1/go.mod h1:U7qILu1NlMHj9FlMhZLlkCdDnU1DBEAqr0aevW3Awn0= -<<<<<<< HEAD -github.com/go-acme/lego/v4 v4.20.2 h1:ZwO3oLZb8fL6up1OZVJP3yHuvqhozzlEmyqKmhrPchQ= -github.com/go-acme/lego/v4 v4.20.2/go.mod h1:foauPlhnhoq8WUphaWx5U04uDc+JGhk4ZZtPz/Vqsjg= -======= github.com/go-acme/lego/v4 v4.20.4 h1:yCQGBX9jOfMbriEQUocdYm7EBapdTp8nLXYG8k6SqSU= ->>>>>>> main github.com/go-acme/lego/v4 v4.20.4/go.mod h1:foauPlhnhoq8WUphaWx5U04uDc+JGhk4ZZtPz/Vqsjg= github.com/go-chi/chi v4.0.2+incompatible/go.mod h1:eB3wogJHnLi3x/kFX2A+IbTBlXxmMeXJVKy9tTv1XzQ= github.com/go-errors/errors v1.0.1/go.mod h1:f4zRHt4oKfwPJE5k8C9vpYG+aDHdBFUsgrm6/TyX73Q= From 1a3c2c740472b85d5bd4b282871828d28b77ac87 Mon Sep 17 00:00:00 2001 From: Jens Alm Date: Tue, 7 Jan 2025 14:17:38 -0500 Subject: [PATCH 09/16] Removed cache in favor of maps --- go.mod | 3 -- internal/ascode/cache_util.go | 7 ++--- ziti/cmd/ascode/download/download.go | 17 ++++++----- ziti/cmd/ascode/upload/upload.go | 28 ++++++++----------- .../cmd/ascode/upload/upload_auth_policies.go | 16 +++++++---- 5 files changed, 34 insertions(+), 37 deletions(-) diff --git a/go.mod b/go.mod index 8c73540fd..e43f5ef28 100644 --- a/go.mod +++ b/go.mod @@ -102,8 +102,6 @@ require ( github.com/MichaelMure/go-term-text v0.3.1 // indirect github.com/alecthomas/chroma v0.10.0 // indirect github.com/andybalholm/brotli v1.1.0 // indirect - github.com/antchfx/jsonquery v1.3.6 // indirect - github.com/antchfx/xpath v1.3.2 // indirect github.com/antlr4-go/antlr/v4 v4.13.1 // indirect github.com/armon/go-metrics v0.4.1 // indirect github.com/asaskevich/govalidator v0.0.0-20230301143203-a9d515a09cc2 // indirect @@ -163,7 +161,6 @@ require ( github.com/openziti-incubator/cf v0.0.3 // indirect github.com/openziti/dilithium v0.3.5 // indirect github.com/parallaxsecond/parsec-client-go v0.0.0-20221025095442-f0a77d263cf9 // indirect - github.com/patrickmn/go-cache v2.1.0+incompatible // indirect github.com/pelletier/go-toml/v2 v2.2.2 // indirect github.com/pion/dtls/v3 v3.0.4 // indirect github.com/pion/logging v0.2.2 // indirect diff --git a/internal/ascode/cache_util.go b/internal/ascode/cache_util.go index f8bb8aa5c..054a79e5f 100644 --- a/internal/ascode/cache_util.go +++ b/internal/ascode/cache_util.go @@ -18,18 +18,17 @@ package ascode import ( "errors" - "github.com/patrickmn/go-cache" log "github.com/sirupsen/logrus" "reflect" ) type CacheGetter func(id string) (interface{}, error) -func GetItemFromCache(c *cache.Cache, key string, fn CacheGetter) (interface{}, error) { +func GetItemFromCache(c map[string]interface{}, key string, fn CacheGetter) (interface{}, error) { if key == "" { return nil, errors.New("key is null, can't resolve from cache or get it from source") } - detail, found := c.Get(key) + detail, found := c[key] if !found { log.WithFields(map[string]interface{}{"key": key}).Debug("Item not in cache, getting from source") var err error @@ -40,7 +39,7 @@ func GetItemFromCache(c *cache.Cache, key string, fn CacheGetter) (interface{}, } if detail != nil && !reflect.ValueOf(detail).IsNil() { log.WithFields(map[string]interface{}{"key": key, "item": detail}).Debug("Item read from source, caching") - c.Set(key, detail, cache.NoExpiration) + c[key] = detail } return detail, nil } diff --git a/ziti/cmd/ascode/download/download.go b/ziti/cmd/ascode/download/download.go index 8cbf6b55d..0600e701f 100644 --- a/ziti/cmd/ascode/download/download.go +++ b/ziti/cmd/ascode/download/download.go @@ -26,7 +26,6 @@ import ( "github.com/openziti/ziti/internal/rest/mgmt" "github.com/openziti/ziti/ziti/cmd/edge" "github.com/openziti/ziti/ziti/constants" - "github.com/patrickmn/go-cache" "github.com/sirupsen/logrus" "github.com/spf13/cobra" "github.com/spf13/viper" @@ -45,10 +44,10 @@ type Download struct { ofYaml bool file *os.File filename string - configCache *cache.Cache - configTypeCache *cache.Cache - authPolicyCache *cache.Cache - externalJwtCache *cache.Cache + configCache map[string]any + configTypeCache map[string]any + authPolicyCache map[string]any + externalJwtCache map[string]any } var output Output @@ -151,10 +150,10 @@ func (d *Download) Execute(input []string) error { args := arrayutils.Map(input, strings.ToLower) - d.authPolicyCache = cache.New(cache.NoExpiration, cache.NoExpiration) - d.configCache = cache.New(cache.NoExpiration, cache.NoExpiration) - d.configTypeCache = cache.New(cache.NoExpiration, cache.NoExpiration) - d.externalJwtCache = cache.New(cache.NoExpiration, cache.NoExpiration) + d.authPolicyCache = map[string]any{} + d.configCache = map[string]any{} + d.configTypeCache = map[string]any{} + d.externalJwtCache = map[string]any{} result := map[string]interface{}{} diff --git a/ziti/cmd/ascode/upload/upload.go b/ziti/cmd/ascode/upload/upload.go index e6667b1e9..b8801ecf7 100644 --- a/ziti/cmd/ascode/upload/upload.go +++ b/ziti/cmd/ascode/upload/upload.go @@ -26,7 +26,6 @@ import ( "github.com/openziti/ziti/internal/rest/mgmt" "github.com/openziti/ziti/ziti/cmd/edge" "github.com/openziti/ziti/ziti/constants" - "github.com/patrickmn/go-cache" "github.com/sirupsen/logrus" "github.com/spf13/cobra" "github.com/spf13/viper" @@ -35,7 +34,6 @@ import ( "os" "slices" "strings" - "time" ) type Upload struct { @@ -44,14 +42,12 @@ type Upload struct { reader Reader ofJson bool ofYaml bool - configCache *cache.Cache - serviceCache *cache.Cache - edgeRouterCache *cache.Cache - authPolicyCache *cache.Cache - extJwtSignersCache *cache.Cache - identityCache *cache.Cache - //Out io.Writer - //Err io.Writer + configCache map[string]any + serviceCache map[string]any + edgeRouterCache map[string]any + authPolicyCache map[string]any + extJwtSignersCache map[string]any + identityCache map[string]any } var log = pfxlog.Logger() @@ -146,12 +142,12 @@ func (u *Upload) Execute(data map[string][]interface{}, inputArgs []string) (map args := arrayutils.Map(inputArgs, strings.ToLower) - u.configCache = cache.New(time.Duration(-1), time.Duration(-1)) - u.serviceCache = cache.New(time.Duration(-1), time.Duration(-1)) - u.edgeRouterCache = cache.New(time.Duration(-1), time.Duration(-1)) - u.authPolicyCache = cache.New(time.Duration(-1), time.Duration(-1)) - u.extJwtSignersCache = cache.New(time.Duration(-1), time.Duration(-1)) - u.identityCache = cache.New(time.Duration(-1), time.Duration(-1)) + u.configCache = map[string]any{} + u.serviceCache = map[string]any{} + u.edgeRouterCache = map[string]any{} + u.authPolicyCache = map[string]any{} + u.extJwtSignersCache = map[string]any{} + u.identityCache = map[string]any{} result := map[string]any{} all := slices.Contains(args, "all") || len(args) == 0 diff --git a/ziti/cmd/ascode/upload/upload_auth_policies.go b/ziti/cmd/ascode/upload/upload_auth_policies.go index 14dba466c..fadcc9a2f 100644 --- a/ziti/cmd/ascode/upload/upload_auth_policies.go +++ b/ziti/cmd/ascode/upload/upload_auth_policies.go @@ -18,6 +18,7 @@ package upload import ( "encoding/json" + "github.com/Jeffail/gabs" "github.com/antchfx/jsonquery" "github.com/openziti/edge-api/rest_management_api_client/auth_policy" "github.com/openziti/edge-api/rest_model" @@ -25,6 +26,7 @@ import ( "github.com/openziti/ziti/internal" "github.com/openziti/ziti/internal/ascode" "github.com/openziti/ziti/internal/rest/mgmt" + "github.com/pkg/errors" "strings" ) @@ -54,12 +56,16 @@ func (u *Upload) ProcessAuthPolicies(input map[string][]interface{}) (map[string // convert to a jsonquery doc so we can query inside the json jsonData, _ := json.Marshal(data) - doc, jsonQueryErr := jsonquery.Parse(strings.NewReader(string(jsonData))) - if jsonQueryErr != nil { - log.WithError(jsonQueryErr).Error("Unable to list AuthPolicies") - return nil, jsonQueryErr + doc, jsonParseError := gabs.ParseJSON(strings.NewReader(string(jsonData))) + if jsonParseError != nil { + log.WithError(jsonParseError).Error("Unable to list AuthPolicies") + return nil, jsonParseError + } + allowedSigners, ok := doc.Path("primary.extJwt.allowedSigners").(string[]) + if ok == false { + log.WithField("name", *create.Name).Error("Unable to read allowedSigners") + return nil, errors.New("Unable to read allowedSigners") } - allowedSigners := jsonquery.FindOne(doc, "/primary/extJwt/allowedSigners") // look up each signer by name and add to the create allowedSignerIds := []string{} From a1e1d651c959890031aad06ba7a6d1aa9188fab3 Mon Sep 17 00:00:00 2001 From: Jens Alm Date: Tue, 7 Jan 2025 16:14:26 -0500 Subject: [PATCH 10/16] Changed to using gabs to process json data --- go.mod | 2 ++ .../cmd/ascode/upload/upload_auth_policies.go | 21 +++++++------------ ziti/cmd/ascode/upload/upload_configs.go | 15 +++++++------ ziti/cmd/ascode/upload/upload_identities.go | 15 +++++++------ .../cmd/ascode/upload/upload_posture_check.go | 16 +++++++------- ziti/cmd/ascode/upload/upload_services.go | 19 ++++++++--------- 6 files changed, 40 insertions(+), 48 deletions(-) diff --git a/go.mod b/go.mod index e43f5ef28..3c931a8ef 100644 --- a/go.mod +++ b/go.mod @@ -102,6 +102,8 @@ require ( github.com/MichaelMure/go-term-text v0.3.1 // indirect github.com/alecthomas/chroma v0.10.0 // indirect github.com/andybalholm/brotli v1.1.0 // indirect + github.com/antchfx/jsonquery v1.3.6 // indirect + github.com/antchfx/xpath v1.3.2 // indirect github.com/antlr4-go/antlr/v4 v4.13.1 // indirect github.com/armon/go-metrics v0.4.1 // indirect github.com/asaskevich/govalidator v0.0.0-20230301143203-a9d515a09cc2 // indirect diff --git a/ziti/cmd/ascode/upload/upload_auth_policies.go b/ziti/cmd/ascode/upload/upload_auth_policies.go index fadcc9a2f..2259807a9 100644 --- a/ziti/cmd/ascode/upload/upload_auth_policies.go +++ b/ziti/cmd/ascode/upload/upload_auth_policies.go @@ -18,16 +18,13 @@ package upload import ( "encoding/json" - "github.com/Jeffail/gabs" - "github.com/antchfx/jsonquery" + "github.com/Jeffail/gabs/v2" "github.com/openziti/edge-api/rest_management_api_client/auth_policy" "github.com/openziti/edge-api/rest_model" "github.com/openziti/edge-api/rest_util" "github.com/openziti/ziti/internal" "github.com/openziti/ziti/internal/ascode" "github.com/openziti/ziti/internal/rest/mgmt" - "github.com/pkg/errors" - "strings" ) func (u *Upload) ProcessAuthPolicies(input map[string][]interface{}) (map[string]string, error) { @@ -54,23 +51,19 @@ func (u *Upload) ProcessAuthPolicies(input map[string][]interface{}) (map[string continue } - // convert to a jsonquery doc so we can query inside the json + // convert to a json doc so we can query inside the data jsonData, _ := json.Marshal(data) - doc, jsonParseError := gabs.ParseJSON(strings.NewReader(string(jsonData))) + doc, jsonParseError := gabs.ParseJSON(jsonData) if jsonParseError != nil { - log.WithError(jsonParseError).Error("Unable to list AuthPolicies") + log.WithError(jsonParseError).Error("Unable to parse json") return nil, jsonParseError } - allowedSigners, ok := doc.Path("primary.extJwt.allowedSigners").(string[]) - if ok == false { - log.WithField("name", *create.Name).Error("Unable to read allowedSigners") - return nil, errors.New("Unable to read allowedSigners") - } + allowedSigners := doc.Path("primary.extJwt.allowedSigners") // look up each signer by name and add to the create allowedSignerIds := []string{} - for _, signer := range allowedSigners.ChildNodes() { - value := signer.Value().(string)[1:] + for _, signer := range allowedSigners.Children() { + value := signer.Data().(string)[1:] extJwtSigner, err := ascode.GetItemFromCache(u.extJwtSignersCache, value, func(name string) (interface{}, error) { return mgmt.ExternalJWTSignerFromFilter(u.client, mgmt.NameFilter(name)), nil }) diff --git a/ziti/cmd/ascode/upload/upload_configs.go b/ziti/cmd/ascode/upload/upload_configs.go index d55c73ba3..8b295e539 100644 --- a/ziti/cmd/ascode/upload/upload_configs.go +++ b/ziti/cmd/ascode/upload/upload_configs.go @@ -19,14 +19,13 @@ package upload import ( "encoding/json" "errors" - "github.com/antchfx/jsonquery" + "github.com/Jeffail/gabs/v2" "github.com/openziti/edge-api/rest_management_api_client/config" "github.com/openziti/edge-api/rest_model" "github.com/openziti/edge-api/rest_util" "github.com/openziti/ziti/internal" "github.com/openziti/ziti/internal/ascode" "github.com/openziti/ziti/internal/rest/mgmt" - "strings" ) func (u *Upload) ProcessConfigs(input map[string][]interface{}) (map[string]string, error) { @@ -50,16 +49,16 @@ func (u *Upload) ProcessConfigs(input map[string][]interface{}) (map[string]stri continue } - // convert to a jsonquery doc so we can query inside the json + // convert to a json doc so we can query inside the data jsonData, _ := json.Marshal(data) - doc, jsonQueryErr := jsonquery.Parse(strings.NewReader(string(jsonData))) - if jsonQueryErr != nil { - log.WithError(jsonQueryErr).Error("Unable to parse json") - return nil, jsonQueryErr + doc, jsonParseError := gabs.ParseJSON(jsonData) + if jsonParseError != nil { + log.WithError(jsonParseError).Error("Unable to parse json") + return nil, jsonParseError } // look up the config type id from the name and add to the create - value := jsonquery.FindOne(doc, "/configType").Value().(string)[1:] + value := doc.Path("configType").Data().(string)[1:] configType, _ := ascode.GetItemFromCache(u.configCache, value, func(name string) (interface{}, error) { return mgmt.ConfigTypeFromFilter(u.client, mgmt.NameFilter(name)), nil }) diff --git a/ziti/cmd/ascode/upload/upload_identities.go b/ziti/cmd/ascode/upload/upload_identities.go index 8fe9aeed4..b5eac3099 100644 --- a/ziti/cmd/ascode/upload/upload_identities.go +++ b/ziti/cmd/ascode/upload/upload_identities.go @@ -19,14 +19,13 @@ package upload import ( "encoding/json" "errors" - "github.com/antchfx/jsonquery" + "github.com/Jeffail/gabs/v2" "github.com/openziti/edge-api/rest_management_api_client/identity" "github.com/openziti/edge-api/rest_model" "github.com/openziti/edge-api/rest_util" "github.com/openziti/ziti/internal" "github.com/openziti/ziti/internal/ascode" "github.com/openziti/ziti/internal/rest/mgmt" - "strings" ) func (u *Upload) ProcessIdentities(input map[string][]interface{}) (map[string]string, error) { @@ -53,14 +52,14 @@ func (u *Upload) ProcessIdentities(input map[string][]interface{}) (map[string]s typ := rest_model.IdentityTypeDefault create.Type = &typ - // convert to a jsonquery doc so we can query inside the json + // convert to a json doc so we can query inside the data jsonData, _ := json.Marshal(data) - doc, jsonQueryErr := jsonquery.Parse(strings.NewReader(string(jsonData))) - if jsonQueryErr != nil { - log.WithError(jsonQueryErr).Error("Unable to list Identities") - return nil, jsonQueryErr + doc, jsonParseError := gabs.ParseJSON(jsonData) + if jsonParseError != nil { + log.WithError(jsonParseError).Error("Unable to parse json") + return nil, jsonParseError } - policyName := jsonquery.FindOne(doc, "/authPolicy").Value().(string)[1:] + policyName := doc.Path("authPolicy").Data().(string)[1:] // look up the auth policy id from the name and add to the create, omit if it's the "Default" policy policy, _ := ascode.GetItemFromCache(u.authPolicyCache, policyName, func(name string) (interface{}, error) { diff --git a/ziti/cmd/ascode/upload/upload_posture_check.go b/ziti/cmd/ascode/upload/upload_posture_check.go index eb8300f0d..6045817b6 100644 --- a/ziti/cmd/ascode/upload/upload_posture_check.go +++ b/ziti/cmd/ascode/upload/upload_posture_check.go @@ -18,7 +18,7 @@ package upload import ( "encoding/json" - "github.com/antchfx/jsonquery" + "github.com/Jeffail/gabs/v2" "github.com/openziti/edge-api/rest_management_api_client/posture_checks" "github.com/openziti/edge-api/rest_model" "github.com/openziti/edge-api/rest_util" @@ -32,17 +32,17 @@ func (u *Upload) ProcessPostureChecks(input map[string][]interface{}) (map[strin var result = map[string]string{} for _, data := range input["postureChecks"] { - // convert to a jsonquery doc so we can query inside the json + // convert to a json doc so we can query inside the data jsonData, _ := json.Marshal(data) - doc, jsonQueryErr := jsonquery.Parse(strings.NewReader(string(jsonData))) - if jsonQueryErr != nil { - log.WithError(jsonQueryErr).Error("Unable to list ") - return nil, jsonQueryErr + doc, jsonParseError := gabs.ParseJSON(jsonData) + if jsonParseError != nil { + log.WithError(jsonParseError).Error("Unable to parse json") + return nil, jsonParseError } - typeNode := jsonquery.FindOne(doc, "/typeId") + typeValue := doc.Path("typeId").Data().(string) var create rest_model.PostureCheckCreate - switch strings.ToUpper(typeNode.Value().(string)) { + switch strings.ToUpper(typeValue) { case "DOMAIN": create = FromMap(data, rest_model.PostureCheckDomainCreate{}) case "MAC": diff --git a/ziti/cmd/ascode/upload/upload_services.go b/ziti/cmd/ascode/upload/upload_services.go index 8ea0f31ca..61d656344 100644 --- a/ziti/cmd/ascode/upload/upload_services.go +++ b/ziti/cmd/ascode/upload/upload_services.go @@ -19,14 +19,13 @@ package upload import ( "encoding/json" "errors" - "github.com/antchfx/jsonquery" + "github.com/Jeffail/gabs/v2" "github.com/openziti/edge-api/rest_management_api_client/service" "github.com/openziti/edge-api/rest_model" "github.com/openziti/edge-api/rest_util" "github.com/openziti/ziti/internal" "github.com/openziti/ziti/internal/ascode" "github.com/openziti/ziti/internal/rest/mgmt" - "strings" ) func (u *Upload) ProcessServices(input map[string][]interface{}) (map[string]string, error) { @@ -48,19 +47,19 @@ func (u *Upload) ProcessServices(input map[string][]interface{}) (map[string]str continue } - // convert to a jsonquery doc so we can query inside the json + // convert to a json doc so we can query inside the data jsonData, _ := json.Marshal(data) - doc, jsonQueryErr := jsonquery.Parse(strings.NewReader(string(jsonData))) - if jsonQueryErr != nil { - log.WithError(jsonQueryErr).Error("Unable to ") - return nil, jsonQueryErr + doc, jsonParseError := gabs.ParseJSON(jsonData) + if jsonParseError != nil { + log.WithError(jsonParseError).Error("Unable to parse json") + return nil, jsonParseError } - configsNode := jsonquery.FindOne(doc, "/configs") + configsNode := doc.Path("configs") // look up each config by name and add to the create configIds := []string{} - for _, configName := range configsNode.ChildNodes() { - value := configName.Value().(string)[1:] + for _, configName := range configsNode.Children() { + value := configName.Data().(string)[1:] config, _ := ascode.GetItemFromCache(u.configCache, value, func(name string) (interface{}, error) { return mgmt.ConfigFromFilter(u.client, mgmt.NameFilter(name)), nil }) From 79f908adeb87f2a9e578e967baca42e90cb505d0 Mon Sep 17 00:00:00 2001 From: Jens Alm Date: Tue, 7 Jan 2025 16:21:38 -0500 Subject: [PATCH 11/16] Removed all plural entity names from command --- ziti/cmd/ascode/download/download.go | 34 +++++++++++------------ ziti/cmd/ascode/upload/upload.go | 41 ++++++++++++++-------------- 2 files changed, 37 insertions(+), 38 deletions(-) diff --git a/ziti/cmd/ascode/download/download.go b/ziti/cmd/ascode/download/download.go index 0600e701f..4d19118ab 100644 --- a/ziti/cmd/ascode/download/download.go +++ b/ziti/cmd/ascode/download/download.go @@ -61,7 +61,7 @@ func NewDownloadCmd(out io.Writer, errOut io.Writer) *cobra.Command { Use: "export [entity]", Short: "Export entities", Long: "Export all or selected entities.\n" + - "Valid entities are: [all|ca/certificate-authority|identity|edge-router|service|config|config-type|service-policy|edgerouter-policy|service-edgerouter-policy|external-jwt-signer|auth-policy|posture-check] (default all)", + "Valid entities are: [all|ca/certificate-authority|identity|edge-router|service|config|config-type|service-policy|edge-router-policy|service-edge-router-policy|external-jwt-signer|auth-policy|posture-check] (default all)", Args: cobra.MinimumNArgs(0), PersistentPreRun: func(cmd *cobra.Command, args []string) { err := d.Init(out) @@ -159,8 +159,8 @@ func (d *Download) Execute(input []string) error { all := slices.Contains(args, "all") || len(args) == 0 if all || - slices.Contains(args, "ca") || slices.Contains(args, "cas") || - slices.Contains(args, "certificate-authority") || slices.Contains(args, "certificate-authorities") { + slices.Contains(args, "ca") || + slices.Contains(args, "certificate-authority") { log.Debug("Processing Certificate Authorities") cas, err := d.GetCertificateAuthorities() if err != nil { @@ -169,7 +169,7 @@ func (d *Download) Execute(input []string) error { result["certificateAuthorities"] = cas } if all || - slices.Contains(args, "identity") || slices.Contains(args, "identities") { + slices.Contains(args, "identity") { log.Debug("Processing Identities") identities, err := d.GetIdentities() if err != nil { @@ -179,8 +179,8 @@ func (d *Download) Execute(input []string) error { } if all || - slices.Contains(args, "edge-router") || slices.Contains(args, "edge-routers") || - slices.Contains(args, "er") || slices.Contains(args, "ers") { + slices.Contains(args, "edge-router") || + slices.Contains(args, "er") { log.Debug("Processing Edge Routers") routers, err := d.GetEdgeRouters() if err != nil { @@ -189,7 +189,7 @@ func (d *Download) Execute(input []string) error { result["edgeRouters"] = routers } if all || - slices.Contains(args, "service") || slices.Contains(args, "services") { + slices.Contains(args, "service") { log.Debug("Processing Services") services, err := d.GetServices() if err != nil { @@ -198,7 +198,7 @@ func (d *Download) Execute(input []string) error { result["services"] = services } if all || - slices.Contains(args, "config") || slices.Contains(args, "configs") { + slices.Contains(args, "config") { log.Debug("Processing Configs") configs, err := d.GetConfigs() if err != nil { @@ -207,7 +207,7 @@ func (d *Download) Execute(input []string) error { result["configs"] = configs } if all || - slices.Contains(args, "config-type") || slices.Contains(args, "config-types") { + slices.Contains(args, "config-type") { log.Debug("Processing Config Types") configTypes, err := d.GetConfigTypes() if err != nil { @@ -216,7 +216,7 @@ func (d *Download) Execute(input []string) error { result["configTypes"] = configTypes } if all || - slices.Contains(args, "service-policy") || slices.Contains(args, "service-policies") { + slices.Contains(args, "service-policy") { log.Debug("Processing Service Policies") servicePolicies, err := d.GetServicePolicies() if err != nil { @@ -225,8 +225,8 @@ func (d *Download) Execute(input []string) error { result["servicePolicies"] = servicePolicies } if all || - slices.Contains(args, "edgerouter-policy") || slices.Contains(args, "edgerouter-policies") { - log.Debug("Processing Router Policies") + slices.Contains(args, "edge-router-policy") { + log.Debug("Processing Edge Router Policies") routerPolicies, err := d.GetRouterPolicies() if err != nil { return err @@ -234,8 +234,8 @@ func (d *Download) Execute(input []string) error { result["edgeRouterPolicies"] = routerPolicies } if all || - slices.Contains(args, "service-edgerouter-policy") || slices.Contains(args, "service-edgerouter-policies") { - log.Debug("Processing Service EdgeRouter Policies") + slices.Contains(args, "service-edge-router-policy") { + log.Debug("Processing Service Edge Router Policies") serviceRouterPolicies, err := d.GetServiceEdgeRouterPolicies() if err != nil { return err @@ -243,7 +243,7 @@ func (d *Download) Execute(input []string) error { result["serviceEdgeRouterPolicies"] = serviceRouterPolicies } if all || - slices.Contains(args, "external-jwt-signer") || slices.Contains(args, "external-jwt-signers") { + slices.Contains(args, "external-jwt-signer") { log.Debug("Processing External JWT Signers") externalJwtSigners, err := d.GetExternalJwtSigners() if err != nil { @@ -252,7 +252,7 @@ func (d *Download) Execute(input []string) error { result["externalJwtSigners"] = externalJwtSigners } if all || - slices.Contains(args, "auth-policy") || slices.Contains(args, "auth-policies") { + slices.Contains(args, "auth-policy") { log.Debug("Processing Auth Policies") authPolicies, err := d.GetAuthPolicies() if err != nil { @@ -261,7 +261,7 @@ func (d *Download) Execute(input []string) error { result["authPolicies"] = authPolicies } if all || - slices.Contains(args, "posture-check") || slices.Contains(args, "posture-checks") { + slices.Contains(args, "posture-check") { log.Debug("Processing Posture Checks") postureChecks, err := d.GetPostureChecks() if err != nil { diff --git a/ziti/cmd/ascode/upload/upload.go b/ziti/cmd/ascode/upload/upload.go index b8801ecf7..84944ffde 100644 --- a/ziti/cmd/ascode/upload/upload.go +++ b/ziti/cmd/ascode/upload/upload.go @@ -61,7 +61,7 @@ func NewUploadCmd(out io.Writer, errOut io.Writer) *cobra.Command { Use: "import filename [entity]", Short: "Import entities", Long: "Import all or selected entities from the specified file.\n" + - "Valid entities are: [all|ca/certificate-authority|identity|edge-router|service|config|config-type|service-policy|edgerouter-policy|service-edgerouter-policy|external-jwt-signer|auth-policy|posture-check] (default all)", + "Valid entities are: [all|ca/certificate-authority|identity|edge-router|service|config|config-type|service-policy|edge-router-policy|service-edge-router-policy|external-jwt-signer|auth-policy|posture-check] (default all)", Args: cobra.MinimumNArgs(1), PersistentPreRun: func(cmd *cobra.Command, args []string) { u.Init() @@ -154,8 +154,8 @@ func (u *Upload) Execute(data map[string][]interface{}, inputArgs []string) (map cas := map[string]string{} if all || - slices.Contains(args, "ca") || slices.Contains(args, "cas") || - slices.Contains(args, "certificate-authority") || slices.Contains(args, "certificate-authorities") { + slices.Contains(args, "ca") || + slices.Contains(args, "certificate-authority") { log.Debug("Processing CertificateAuthorities") var err error cas, err = u.ProcessCertificateAuthorities(data) @@ -171,9 +171,9 @@ func (u *Upload) Execute(data map[string][]interface{}, inputArgs []string) (map externalJwtSigners := map[string]string{} if all || - slices.Contains(args, "external-jwt-signer") || slices.Contains(args, "external-jwt-signers") || - slices.Contains(args, "auth-policy") || slices.Contains(args, "auth-policies") || - slices.Contains(args, "identity") || slices.Contains(args, "identities") { + slices.Contains(args, "external-jwt-signer") || + slices.Contains(args, "auth-policy") || + slices.Contains(args, "identity") { log.Debug("Processing ExtJWTSigners") var err error externalJwtSigners, err = u.ProcessExternalJwtSigners(data) @@ -187,8 +187,8 @@ func (u *Upload) Execute(data map[string][]interface{}, inputArgs []string) (map authPolicies := map[string]string{} if all || - slices.Contains(args, "auth-policy") || slices.Contains(args, "auth-policies") || - slices.Contains(args, "identity") || slices.Contains(args, "identities") { + slices.Contains(args, "auth-policy") || + slices.Contains(args, "identity") { log.Debug("Processing AuthPolicies") var err error authPolicies, err = u.ProcessAuthPolicies(data) @@ -202,7 +202,7 @@ func (u *Upload) Execute(data map[string][]interface{}, inputArgs []string) (map identities := map[string]string{} if all || - slices.Contains(args, "identity") || slices.Contains(args, "identities") { + slices.Contains(args, "identity") { log.Debug("Processing Identities") var err error identities, err = u.ProcessIdentities(data) @@ -216,9 +216,9 @@ func (u *Upload) Execute(data map[string][]interface{}, inputArgs []string) (map configTypes := map[string]string{} if all || - slices.Contains(args, "config-type") || slices.Contains(args, "config-types") || - slices.Contains(args, "config") || slices.Contains(args, "configs") || - slices.Contains(args, "service") || slices.Contains(args, "services") { + slices.Contains(args, "config-type") || + slices.Contains(args, "config") || + slices.Contains(args, "service") { log.Debug("Processing ConfigTypes") var err error configTypes, err = u.ProcessConfigTypes(data) @@ -232,8 +232,8 @@ func (u *Upload) Execute(data map[string][]interface{}, inputArgs []string) (map configs := map[string]string{} if all || - slices.Contains(args, "config") || slices.Contains(args, "configs") || - slices.Contains(args, "service") || slices.Contains(args, "services") { + slices.Contains(args, "config") || + slices.Contains(args, "service") { log.Debug("Processing Configs") var err error configs, err = u.ProcessConfigs(data) @@ -247,7 +247,7 @@ func (u *Upload) Execute(data map[string][]interface{}, inputArgs []string) (map services := map[string]string{} if all || - slices.Contains(args, "service") || slices.Contains(args, "services") { + slices.Contains(args, "service") { log.Debug("Processing Services") var err error services, err = u.ProcessServices(data) @@ -261,7 +261,7 @@ func (u *Upload) Execute(data map[string][]interface{}, inputArgs []string) (map postureChecks := map[string]string{} if all || - slices.Contains(args, "posture-check") || slices.Contains(args, "posture-checks") { + slices.Contains(args, "posture-check") { log.Debug("Processing PostureChecks") var err error postureChecks, err = u.ProcessPostureChecks(data) @@ -275,8 +275,7 @@ func (u *Upload) Execute(data map[string][]interface{}, inputArgs []string) (map routers := map[string]string{} if all || - slices.Contains(args, "edge-router") || slices.Contains(args, "edge-routers") || - slices.Contains(args, "ers") || slices.Contains(args, "ers") { + slices.Contains(args, "edge-router") || slices.Contains(args, "er") { log.Debug("Processing EdgeRouters") var err error routers, err = u.ProcessEdgeRouters(data) @@ -290,7 +289,7 @@ func (u *Upload) Execute(data map[string][]interface{}, inputArgs []string) (map serviceEdgeRouterPolicies := map[string]string{} if all || - slices.Contains(args, "service-edgerouter-policy") || slices.Contains(args, "service-edgerouter-policies") { + slices.Contains(args, "service-edge-router-policy") { log.Debug("Processing ServiceRouterPolicies") var err error serviceEdgeRouterPolicies, err = u.ProcessServiceEdgeRouterPolicies(data) @@ -304,7 +303,7 @@ func (u *Upload) Execute(data map[string][]interface{}, inputArgs []string) (map servicePolicies := map[string]string{} if all || - slices.Contains(args, "service-policy") || slices.Contains(args, "service-policies") { + slices.Contains(args, "service-policy") { log.Debug("Processing ServicePolicies") var err error servicePolicies, err = u.ProcessServicePolicies(data) @@ -318,7 +317,7 @@ func (u *Upload) Execute(data map[string][]interface{}, inputArgs []string) (map routerPolicies := map[string]string{} if all || - slices.Contains(args, "edgerouter-policy") || slices.Contains(args, "edgerouter-policies") { + slices.Contains(args, "edge-router-policy") { log.Debug("Processing EdgeRouterPolicies") var err error routerPolicies, err = u.ProcessEdgeRouterPolicies(data) From 309eeb7837b97ff9c33bfbfdcc9b1aef9c46463a Mon Sep 17 00:00:00 2001 From: Jens Alm Date: Tue, 7 Jan 2025 17:07:20 -0500 Subject: [PATCH 12/16] Renamed files/packages/classes to match command --- ziti/cmd/ascode/ascode_test.go | 8 +++---- .../download.go => exporter/exporter.go} | 22 +++++++++---------- .../exporter_auth_policies.go} | 4 ++-- .../exporter_certificate_authorities.go} | 4 ++-- .../exporter_config_types.go} | 4 ++-- .../exporter_configs.go} | 4 ++-- .../exporter_edgerouter_policies.go} | 4 ++-- .../exporter_edgerouters.go} | 4 ++-- .../exporter_external_jwt_signers.go} | 4 ++-- .../exporter_identities.go} | 6 ++--- .../exporter_posture_checks.go} | 4 ++-- .../exporter_service_edgerouter_policies.go} | 4 ++-- .../exporter_service_policies.go} | 4 ++-- .../exporter_services.go} | 4 ++-- .../ascode/{download => exporter}/output.go | 2 +- .../{upload/upload.go => importer/import.go} | 12 +++++----- .../import_auth_policies.go} | 4 ++-- .../import_certificate_authorities.go} | 4 ++-- .../import_config_types.go} | 4 ++-- .../import_configs.go} | 4 ++-- .../import_edgerouter_policies.go} | 4 ++-- .../import_edgerouters.go} | 6 ++--- .../import_external_jwt_signers.go} | 4 ++-- .../import_identities.go} | 6 ++--- .../import_posture_check.go} | 4 ++-- .../import_service_edgerouter_policies.go} | 4 ++-- .../import_service_policies.go} | 4 ++-- .../import_services.go} | 6 ++--- ziti/cmd/cmd.go | 8 +++---- 29 files changed, 78 insertions(+), 78 deletions(-) rename ziti/cmd/ascode/{download/download.go => exporter/exporter.go} (94%) rename ziti/cmd/ascode/{download/download_auth_policies.go => exporter/exporter_auth_policies.go} (97%) rename ziti/cmd/ascode/{download/download_certificate_authorities.go => exporter/exporter_certificate_authorities.go} (95%) rename ziti/cmd/ascode/{download/download_config_types.go => exporter/exporter_config_types.go} (95%) rename ziti/cmd/ascode/{download/download_configs.go => exporter/exporter_configs.go} (96%) rename ziti/cmd/ascode/{download/download_edgerouter_policies.go => exporter/exporter_edgerouter_policies.go} (96%) rename ziti/cmd/ascode/{download/download_edgerouters.go => exporter/exporter_edgerouters.go} (95%) rename ziti/cmd/ascode/{download/download_external_jwt_signers.go => exporter/exporter_external_jwt_signers.go} (95%) rename ziti/cmd/ascode/{download/download_identities.go => exporter/exporter_identities.go} (95%) rename ziti/cmd/ascode/{download/download_posture_checks.go => exporter/exporter_posture_checks.go} (95%) rename ziti/cmd/ascode/{download/download_service_edgerouter_policies.go => exporter/exporter_service_edgerouter_policies.go} (96%) rename ziti/cmd/ascode/{download/download_service_policies.go => exporter/exporter_service_policies.go} (96%) rename ziti/cmd/ascode/{download/download_services.go => exporter/exporter_services.go} (96%) rename ziti/cmd/ascode/{download => exporter}/output.go (99%) rename ziti/cmd/ascode/{upload/upload.go => importer/import.go} (97%) rename ziti/cmd/ascode/{upload/upload_auth_policies.go => importer/import_auth_policies.go} (96%) rename ziti/cmd/ascode/{upload/upload_certificate_authorities.go => importer/import_certificate_authorities.go} (95%) rename ziti/cmd/ascode/{upload/upload_config_types.go => importer/import_config_types.go} (95%) rename ziti/cmd/ascode/{upload/upload_configs.go => importer/import_configs.go} (96%) rename ziti/cmd/ascode/{upload/upload_edgerouter_policies.go => importer/import_edgerouter_policies.go} (96%) rename ziti/cmd/ascode/{upload/upload_edgerouters.go => importer/import_edgerouters.go} (94%) rename ziti/cmd/ascode/{upload/upload_external_jwt_signers.go => importer/import_external_jwt_signers.go} (95%) rename ziti/cmd/ascode/{upload/upload_identities.go => importer/import_identities.go} (95%) rename ziti/cmd/ascode/{upload/upload_posture_check.go => importer/import_posture_check.go} (96%) rename ziti/cmd/ascode/{upload/upload_service_edgerouter_policies.go => importer/import_service_edgerouter_policies.go} (96%) rename ziti/cmd/ascode/{upload/upload_service_policies.go => importer/import_service_policies.go} (96%) rename ziti/cmd/ascode/{upload/upload_services.go => importer/import_services.go} (95%) diff --git a/ziti/cmd/ascode/ascode_test.go b/ziti/cmd/ascode/ascode_test.go index 9f11bc75b..9bd9fbaa4 100644 --- a/ziti/cmd/ascode/ascode_test.go +++ b/ziti/cmd/ascode/ascode_test.go @@ -22,8 +22,8 @@ import ( "fmt" "github.com/antchfx/jsonquery" "github.com/michaelquigley/pfxlog" - "github.com/openziti/ziti/ziti/cmd/ascode/download" - "github.com/openziti/ziti/ziti/cmd/ascode/upload" + "github.com/openziti/ziti/ziti/cmd/ascode/exporter" + "github.com/openziti/ziti/ziti/cmd/ascode/importer" "github.com/openziti/ziti/ziti/cmd/edge" "github.com/stretchr/testify/assert" "net/http" @@ -100,7 +100,7 @@ func performTest(t *testing.T) { errWriter := strings.Builder{} uploadWriter := strings.Builder{} - uploadCmd := upload.NewUploadCmd(&uploadWriter, &errWriter) + uploadCmd := importer.NewImportCmd(&uploadWriter, &errWriter) uploadCmd.SetArgs([]string{"--verbose", "--yaml", "./test.yaml"}) err := uploadCmd.Execute() @@ -110,7 +110,7 @@ func performTest(t *testing.T) { } downloadWriter := strings.Builder{} - downloadCmd := download.NewDownloadCmd(&downloadWriter, &errWriter) + downloadCmd := exporter.NewExportCmd(&downloadWriter, &errWriter) downloadCmd.SetArgs([]string{"--json"}) err = downloadCmd.Execute() diff --git a/ziti/cmd/ascode/download/download.go b/ziti/cmd/ascode/exporter/exporter.go similarity index 94% rename from ziti/cmd/ascode/download/download.go rename to ziti/cmd/ascode/exporter/exporter.go index 4d19118ab..b9fa6cb1e 100644 --- a/ziti/cmd/ascode/download/download.go +++ b/ziti/cmd/ascode/exporter/exporter.go @@ -14,7 +14,7 @@ limitations under the License. */ -package download +package exporter import ( "encoding/json" @@ -37,7 +37,7 @@ import ( var log = pfxlog.Logger() -type Download struct { +type Exporter struct { loginOpts edge.LoginOptions client *rest_management_api_client.ZitiEdgeManagement ofJson bool @@ -52,9 +52,9 @@ type Download struct { var output Output -func NewDownloadCmd(out io.Writer, errOut io.Writer) *cobra.Command { +func NewExportCmd(out io.Writer, errOut io.Writer) *cobra.Command { - d := &Download{} + d := &Exporter{} d.loginOpts = edge.LoginOptions{} cmd := &cobra.Command{ @@ -106,7 +106,7 @@ func NewDownloadCmd(out io.Writer, errOut io.Writer) *cobra.Command { return cmd } -func (d *Download) Init(out io.Writer) error { +func (d *Exporter) Init(out io.Writer) error { logLvl := logrus.InfoLevel if d.loginOpts.Verbose { @@ -146,7 +146,7 @@ func (d *Download) Init(out io.Writer) error { return nil } -func (d *Download) Execute(input []string) error { +func (d *Exporter) Execute(input []string) error { args := arrayutils.Map(input, strings.ToLower) @@ -270,7 +270,7 @@ func (d *Download) Execute(input []string) error { result["postureChecks"] = postureChecks } - log.Debug("Download complete") + log.Debug("Export complete") err := output.Write(result) if err != nil { @@ -290,7 +290,7 @@ type ClientCount func() (int64, error) type ClientList func(offset *int64, limit *int64) ([]interface{}, error) type EntityProcessor func(item interface{}) (map[string]interface{}, error) -func (d *Download) getEntities(entityName string, count ClientCount, list ClientList, processor EntityProcessor) ([]map[string]interface{}, error) { +func (d *Exporter) getEntities(entityName string, count ClientCount, list ClientList, processor EntityProcessor) ([]map[string]interface{}, error) { totalCount, countErr := count() if countErr != nil { @@ -329,7 +329,7 @@ func (d *Download) getEntities(entityName string, count ClientCount, list Client } -func (d *Download) ToMap(input interface{}) map[string]interface{} { +func (d *Exporter) ToMap(input interface{}) map[string]interface{} { jsonData, _ := json.MarshalIndent(input, "", "") m := map[string]interface{}{} err := json.Unmarshal(jsonData, &m) @@ -340,13 +340,13 @@ func (d *Download) ToMap(input interface{}) map[string]interface{} { return m } -func (d *Download) defaultRoleAttributes(m map[string]interface{}) { +func (d *Exporter) defaultRoleAttributes(m map[string]interface{}) { if m["roleAttributes"] == nil { m["roleAttributes"] = []string{} } } -func (d *Download) Filter(m map[string]interface{}, properties []string) { +func (d *Exporter) Filter(m map[string]interface{}, properties []string) { // remove any properties that are not requested for k := range m { diff --git a/ziti/cmd/ascode/download/download_auth_policies.go b/ziti/cmd/ascode/exporter/exporter_auth_policies.go similarity index 97% rename from ziti/cmd/ascode/download/download_auth_policies.go rename to ziti/cmd/ascode/exporter/exporter_auth_policies.go index 8a03a8161..a3cef02e2 100644 --- a/ziti/cmd/ascode/download/download_auth_policies.go +++ b/ziti/cmd/ascode/exporter/exporter_auth_policies.go @@ -14,7 +14,7 @@ limitations under the License. */ -package download +package exporter import ( "github.com/openziti/edge-api/rest_management_api_client/auth_policy" @@ -23,7 +23,7 @@ import ( "github.com/openziti/ziti/internal/ascode" ) -func (d Download) GetAuthPolicies() ([]map[string]interface{}, error) { +func (d Exporter) GetAuthPolicies() ([]map[string]interface{}, error) { return d.getEntities( "AuthPolicies", diff --git a/ziti/cmd/ascode/download/download_certificate_authorities.go b/ziti/cmd/ascode/exporter/exporter_certificate_authorities.go similarity index 95% rename from ziti/cmd/ascode/download/download_certificate_authorities.go rename to ziti/cmd/ascode/exporter/exporter_certificate_authorities.go index d172c418b..430d3869d 100644 --- a/ziti/cmd/ascode/download/download_certificate_authorities.go +++ b/ziti/cmd/ascode/exporter/exporter_certificate_authorities.go @@ -14,14 +14,14 @@ limitations under the License. */ -package download +package exporter import ( "github.com/openziti/edge-api/rest_management_api_client/certificate_authority" "github.com/openziti/edge-api/rest_model" ) -func (d Download) GetCertificateAuthorities() ([]map[string]interface{}, error) { +func (d Exporter) GetCertificateAuthorities() ([]map[string]interface{}, error) { return d.getEntities( "CertificateAuthorities", diff --git a/ziti/cmd/ascode/download/download_config_types.go b/ziti/cmd/ascode/exporter/exporter_config_types.go similarity index 95% rename from ziti/cmd/ascode/download/download_config_types.go rename to ziti/cmd/ascode/exporter/exporter_config_types.go index ea4d5f4c4..41c6afb64 100644 --- a/ziti/cmd/ascode/download/download_config_types.go +++ b/ziti/cmd/ascode/exporter/exporter_config_types.go @@ -14,7 +14,7 @@ limitations under the License. */ -package download +package exporter import ( "github.com/openziti/edge-api/rest_management_api_client/config" @@ -22,7 +22,7 @@ import ( "slices" ) -func (d Download) GetConfigTypes() ([]map[string]interface{}, error) { +func (d Exporter) GetConfigTypes() ([]map[string]interface{}, error) { return d.getEntities( "ConfigTypes", diff --git a/ziti/cmd/ascode/download/download_configs.go b/ziti/cmd/ascode/exporter/exporter_configs.go similarity index 96% rename from ziti/cmd/ascode/download/download_configs.go rename to ziti/cmd/ascode/exporter/exporter_configs.go index 489f3b9c4..fb54ab8b4 100644 --- a/ziti/cmd/ascode/download/download_configs.go +++ b/ziti/cmd/ascode/exporter/exporter_configs.go @@ -14,7 +14,7 @@ limitations under the License. */ -package download +package exporter import ( "errors" @@ -23,7 +23,7 @@ import ( "github.com/openziti/ziti/internal/ascode" ) -func (d Download) GetConfigs() ([]map[string]interface{}, error) { +func (d Exporter) GetConfigs() ([]map[string]interface{}, error) { return d.getEntities( "Configs", diff --git a/ziti/cmd/ascode/download/download_edgerouter_policies.go b/ziti/cmd/ascode/exporter/exporter_edgerouter_policies.go similarity index 96% rename from ziti/cmd/ascode/download/download_edgerouter_policies.go rename to ziti/cmd/ascode/exporter/exporter_edgerouter_policies.go index a1e82fa74..7bb906eab 100644 --- a/ziti/cmd/ascode/download/download_edgerouter_policies.go +++ b/ziti/cmd/ascode/exporter/exporter_edgerouter_policies.go @@ -14,14 +14,14 @@ limitations under the License. */ -package download +package exporter import ( "github.com/openziti/edge-api/rest_management_api_client/edge_router_policy" "github.com/openziti/edge-api/rest_model" ) -func (d Download) GetRouterPolicies() ([]map[string]interface{}, error) { +func (d Exporter) GetRouterPolicies() ([]map[string]interface{}, error) { return d.getEntities( "EdgeRouterPolicies", diff --git a/ziti/cmd/ascode/download/download_edgerouters.go b/ziti/cmd/ascode/exporter/exporter_edgerouters.go similarity index 95% rename from ziti/cmd/ascode/download/download_edgerouters.go rename to ziti/cmd/ascode/exporter/exporter_edgerouters.go index 15b5981e0..651694d8b 100644 --- a/ziti/cmd/ascode/download/download_edgerouters.go +++ b/ziti/cmd/ascode/exporter/exporter_edgerouters.go @@ -14,14 +14,14 @@ limitations under the License. */ -package download +package exporter import ( "github.com/openziti/edge-api/rest_management_api_client/edge_router" "github.com/openziti/edge-api/rest_model" ) -func (d Download) GetEdgeRouters() ([]map[string]interface{}, error) { +func (d Exporter) GetEdgeRouters() ([]map[string]interface{}, error) { return d.getEntities( "EdgeRouters", diff --git a/ziti/cmd/ascode/download/download_external_jwt_signers.go b/ziti/cmd/ascode/exporter/exporter_external_jwt_signers.go similarity index 95% rename from ziti/cmd/ascode/download/download_external_jwt_signers.go rename to ziti/cmd/ascode/exporter/exporter_external_jwt_signers.go index 75efeb9d8..08c0ed945 100644 --- a/ziti/cmd/ascode/download/download_external_jwt_signers.go +++ b/ziti/cmd/ascode/exporter/exporter_external_jwt_signers.go @@ -14,14 +14,14 @@ limitations under the License. */ -package download +package exporter import ( "github.com/openziti/edge-api/rest_management_api_client/external_jwt_signer" "github.com/openziti/edge-api/rest_model" ) -func (d Download) GetExternalJwtSigners() ([]map[string]interface{}, error) { +func (d Exporter) GetExternalJwtSigners() ([]map[string]interface{}, error) { return d.getEntities( "ExtJWTSigners", diff --git a/ziti/cmd/ascode/download/download_identities.go b/ziti/cmd/ascode/exporter/exporter_identities.go similarity index 95% rename from ziti/cmd/ascode/download/download_identities.go rename to ziti/cmd/ascode/exporter/exporter_identities.go index ca22bed54..5f774107d 100644 --- a/ziti/cmd/ascode/download/download_identities.go +++ b/ziti/cmd/ascode/exporter/exporter_identities.go @@ -14,7 +14,7 @@ limitations under the License. */ -package download +package exporter import ( "errors" @@ -24,7 +24,7 @@ import ( "github.com/openziti/ziti/internal/ascode" ) -func (d Download) GetIdentities() ([]map[string]interface{}, error) { +func (d Exporter) GetIdentities() ([]map[string]interface{}, error) { return d.getEntities( "Identities", @@ -54,7 +54,7 @@ func (d Download) GetIdentities() ([]map[string]interface{}, error) { item := entity.(*rest_model.IdentityDetail) - // only download Default identities and not the default admin + // only exporter regular identities and not the default admin if *item.TypeID != "Router" && !*item.IsDefaultAdmin { // convert to a map of values diff --git a/ziti/cmd/ascode/download/download_posture_checks.go b/ziti/cmd/ascode/exporter/exporter_posture_checks.go similarity index 95% rename from ziti/cmd/ascode/download/download_posture_checks.go rename to ziti/cmd/ascode/exporter/exporter_posture_checks.go index e139726e0..a92fe8e17 100644 --- a/ziti/cmd/ascode/download/download_posture_checks.go +++ b/ziti/cmd/ascode/exporter/exporter_posture_checks.go @@ -14,13 +14,13 @@ limitations under the License. */ -package download +package exporter import ( "github.com/openziti/edge-api/rest_management_api_client/posture_checks" ) -func (d Download) GetPostureChecks() ([]map[string]interface{}, error) { +func (d Exporter) GetPostureChecks() ([]map[string]interface{}, error) { return d.getEntities( "PostureChecks", diff --git a/ziti/cmd/ascode/download/download_service_edgerouter_policies.go b/ziti/cmd/ascode/exporter/exporter_service_edgerouter_policies.go similarity index 96% rename from ziti/cmd/ascode/download/download_service_edgerouter_policies.go rename to ziti/cmd/ascode/exporter/exporter_service_edgerouter_policies.go index 284633879..edbc74fce 100644 --- a/ziti/cmd/ascode/download/download_service_edgerouter_policies.go +++ b/ziti/cmd/ascode/exporter/exporter_service_edgerouter_policies.go @@ -14,14 +14,14 @@ limitations under the License. */ -package download +package exporter import ( "github.com/openziti/edge-api/rest_management_api_client/service_edge_router_policy" "github.com/openziti/edge-api/rest_model" ) -func (d Download) GetServiceEdgeRouterPolicies() ([]map[string]interface{}, error) { +func (d Exporter) GetServiceEdgeRouterPolicies() ([]map[string]interface{}, error) { return d.getEntities( "ServiceEdgeRouterPolicies", diff --git a/ziti/cmd/ascode/download/download_service_policies.go b/ziti/cmd/ascode/exporter/exporter_service_policies.go similarity index 96% rename from ziti/cmd/ascode/download/download_service_policies.go rename to ziti/cmd/ascode/exporter/exporter_service_policies.go index 94b2cacc8..ff364fb38 100644 --- a/ziti/cmd/ascode/download/download_service_policies.go +++ b/ziti/cmd/ascode/exporter/exporter_service_policies.go @@ -14,14 +14,14 @@ limitations under the License. */ -package download +package exporter import ( "github.com/openziti/edge-api/rest_management_api_client/service_policy" "github.com/openziti/edge-api/rest_model" ) -func (d Download) GetServicePolicies() ([]map[string]interface{}, error) { +func (d Exporter) GetServicePolicies() ([]map[string]interface{}, error) { return d.getEntities( "ServicePolicies", diff --git a/ziti/cmd/ascode/download/download_services.go b/ziti/cmd/ascode/exporter/exporter_services.go similarity index 96% rename from ziti/cmd/ascode/download/download_services.go rename to ziti/cmd/ascode/exporter/exporter_services.go index c5402f841..0f39a513c 100644 --- a/ziti/cmd/ascode/download/download_services.go +++ b/ziti/cmd/ascode/exporter/exporter_services.go @@ -14,7 +14,7 @@ limitations under the License. */ -package download +package exporter import ( "errors" @@ -24,7 +24,7 @@ import ( "github.com/openziti/ziti/internal/ascode" ) -func (d Download) GetServices() ([]map[string]interface{}, error) { +func (d Exporter) GetServices() ([]map[string]interface{}, error) { return d.getEntities( "Services", diff --git a/ziti/cmd/ascode/download/output.go b/ziti/cmd/ascode/exporter/output.go similarity index 99% rename from ziti/cmd/ascode/download/output.go rename to ziti/cmd/ascode/exporter/output.go index b81bde9c8..2fc4fb226 100644 --- a/ziti/cmd/ascode/download/output.go +++ b/ziti/cmd/ascode/exporter/output.go @@ -14,7 +14,7 @@ limitations under the License. */ -package download +package exporter import ( "bufio" diff --git a/ziti/cmd/ascode/upload/upload.go b/ziti/cmd/ascode/importer/import.go similarity index 97% rename from ziti/cmd/ascode/upload/upload.go rename to ziti/cmd/ascode/importer/import.go index 84944ffde..15cc41e79 100644 --- a/ziti/cmd/ascode/upload/upload.go +++ b/ziti/cmd/ascode/importer/import.go @@ -14,7 +14,7 @@ limitations under the License. */ -package upload +package importer import ( "encoding/json" @@ -36,7 +36,7 @@ import ( "strings" ) -type Upload struct { +type Importer struct { loginOpts edge.LoginOptions client *rest_management_api_client.ZitiEdgeManagement reader Reader @@ -52,9 +52,9 @@ type Upload struct { var log = pfxlog.Logger() -func NewUploadCmd(out io.Writer, errOut io.Writer) *cobra.Command { +func NewImportCmd(out io.Writer, errOut io.Writer) *cobra.Command { - u := &Upload{} + u := &Importer{} u.loginOpts = edge.LoginOptions{} cmd := &cobra.Command{ @@ -112,7 +112,7 @@ func NewUploadCmd(out io.Writer, errOut io.Writer) *cobra.Command { return cmd } -func (u *Upload) Init() { +func (u *Importer) Init() { u.loginOpts.Verbose = u.loginOpts.Verbose logLvl := logrus.InfoLevel @@ -138,7 +138,7 @@ func (u *Upload) Init() { u.reader = FileReader{} } -func (u *Upload) Execute(data map[string][]interface{}, inputArgs []string) (map[string]any, error) { +func (u *Importer) Execute(data map[string][]interface{}, inputArgs []string) (map[string]any, error) { args := arrayutils.Map(inputArgs, strings.ToLower) diff --git a/ziti/cmd/ascode/upload/upload_auth_policies.go b/ziti/cmd/ascode/importer/import_auth_policies.go similarity index 96% rename from ziti/cmd/ascode/upload/upload_auth_policies.go rename to ziti/cmd/ascode/importer/import_auth_policies.go index 2259807a9..2fc7295c6 100644 --- a/ziti/cmd/ascode/upload/upload_auth_policies.go +++ b/ziti/cmd/ascode/importer/import_auth_policies.go @@ -14,7 +14,7 @@ limitations under the License. */ -package upload +package importer import ( "encoding/json" @@ -27,7 +27,7 @@ import ( "github.com/openziti/ziti/internal/rest/mgmt" ) -func (u *Upload) ProcessAuthPolicies(input map[string][]interface{}) (map[string]string, error) { +func (u *Importer) ProcessAuthPolicies(input map[string][]interface{}) (map[string]string, error) { if u.loginOpts.Verbose { log.Debug("Listing all AuthPolicies") diff --git a/ziti/cmd/ascode/upload/upload_certificate_authorities.go b/ziti/cmd/ascode/importer/import_certificate_authorities.go similarity index 95% rename from ziti/cmd/ascode/upload/upload_certificate_authorities.go rename to ziti/cmd/ascode/importer/import_certificate_authorities.go index 1f4cab36a..d503cf260 100644 --- a/ziti/cmd/ascode/upload/upload_certificate_authorities.go +++ b/ziti/cmd/ascode/importer/import_certificate_authorities.go @@ -14,7 +14,7 @@ limitations under the License. */ -package upload +package importer import ( "github.com/openziti/edge-api/rest_management_api_client/certificate_authority" @@ -24,7 +24,7 @@ import ( "github.com/openziti/ziti/internal/rest/mgmt" ) -func (u *Upload) ProcessCertificateAuthorities(input map[string][]interface{}) (map[string]string, error) { +func (u *Importer) ProcessCertificateAuthorities(input map[string][]interface{}) (map[string]string, error) { var result = map[string]string{} for _, data := range input["certificateAuthorities"] { diff --git a/ziti/cmd/ascode/upload/upload_config_types.go b/ziti/cmd/ascode/importer/import_config_types.go similarity index 95% rename from ziti/cmd/ascode/upload/upload_config_types.go rename to ziti/cmd/ascode/importer/import_config_types.go index 9b8e499c2..6960b5964 100644 --- a/ziti/cmd/ascode/upload/upload_config_types.go +++ b/ziti/cmd/ascode/importer/import_config_types.go @@ -14,7 +14,7 @@ limitations under the License. */ -package upload +package importer import ( "github.com/openziti/edge-api/rest_management_api_client/config" @@ -24,7 +24,7 @@ import ( "github.com/openziti/ziti/internal/rest/mgmt" ) -func (u *Upload) ProcessConfigTypes(input map[string][]interface{}) (map[string]string, error) { +func (u *Importer) ProcessConfigTypes(input map[string][]interface{}) (map[string]string, error) { var result = map[string]string{} for _, data := range input["configTypes"] { diff --git a/ziti/cmd/ascode/upload/upload_configs.go b/ziti/cmd/ascode/importer/import_configs.go similarity index 96% rename from ziti/cmd/ascode/upload/upload_configs.go rename to ziti/cmd/ascode/importer/import_configs.go index 8b295e539..a3c25f48f 100644 --- a/ziti/cmd/ascode/upload/upload_configs.go +++ b/ziti/cmd/ascode/importer/import_configs.go @@ -14,7 +14,7 @@ limitations under the License. */ -package upload +package importer import ( "encoding/json" @@ -28,7 +28,7 @@ import ( "github.com/openziti/ziti/internal/rest/mgmt" ) -func (u *Upload) ProcessConfigs(input map[string][]interface{}) (map[string]string, error) { +func (u *Importer) ProcessConfigs(input map[string][]interface{}) (map[string]string, error) { var result = map[string]string{} for _, data := range input["configs"] { diff --git a/ziti/cmd/ascode/upload/upload_edgerouter_policies.go b/ziti/cmd/ascode/importer/import_edgerouter_policies.go similarity index 96% rename from ziti/cmd/ascode/upload/upload_edgerouter_policies.go rename to ziti/cmd/ascode/importer/import_edgerouter_policies.go index e5e6b6e95..a8504f7f1 100644 --- a/ziti/cmd/ascode/upload/upload_edgerouter_policies.go +++ b/ziti/cmd/ascode/importer/import_edgerouter_policies.go @@ -14,7 +14,7 @@ limitations under the License. */ -package upload +package importer import ( "github.com/openziti/edge-api/rest_management_api_client/edge_router_policy" @@ -24,7 +24,7 @@ import ( "github.com/openziti/ziti/internal/rest/mgmt" ) -func (u *Upload) ProcessEdgeRouterPolicies(input map[string][]interface{}) (map[string]string, error) { +func (u *Importer) ProcessEdgeRouterPolicies(input map[string][]interface{}) (map[string]string, error) { var result = map[string]string{} for _, data := range input["edgeRouterPolicies"] { diff --git a/ziti/cmd/ascode/upload/upload_edgerouters.go b/ziti/cmd/ascode/importer/import_edgerouters.go similarity index 94% rename from ziti/cmd/ascode/upload/upload_edgerouters.go rename to ziti/cmd/ascode/importer/import_edgerouters.go index addc0943d..8ef22e058 100644 --- a/ziti/cmd/ascode/upload/upload_edgerouters.go +++ b/ziti/cmd/ascode/importer/import_edgerouters.go @@ -14,7 +14,7 @@ limitations under the License. */ -package upload +package importer import ( "errors" @@ -26,7 +26,7 @@ import ( "github.com/openziti/ziti/internal/rest/mgmt" ) -func (u *Upload) ProcessEdgeRouters(input map[string][]interface{}) (map[string]string, error) { +func (u *Importer) ProcessEdgeRouters(input map[string][]interface{}) (map[string]string, error) { var result = map[string]string{} for _, data := range input["edgeRouters"] { @@ -75,7 +75,7 @@ func (u *Upload) ProcessEdgeRouters(input map[string][]interface{}) (map[string] return result, nil } -func (u *Upload) lookupEdgeRouters(roles []string) ([]string, error) { +func (u *Importer) lookupEdgeRouters(roles []string) ([]string, error) { edgeRouterRoles := []string{} for _, role := range roles { if role[0:1] == "@" { diff --git a/ziti/cmd/ascode/upload/upload_external_jwt_signers.go b/ziti/cmd/ascode/importer/import_external_jwt_signers.go similarity index 95% rename from ziti/cmd/ascode/upload/upload_external_jwt_signers.go rename to ziti/cmd/ascode/importer/import_external_jwt_signers.go index db7533447..209b5e48c 100644 --- a/ziti/cmd/ascode/upload/upload_external_jwt_signers.go +++ b/ziti/cmd/ascode/importer/import_external_jwt_signers.go @@ -14,7 +14,7 @@ limitations under the License. */ -package upload +package importer import ( "github.com/openziti/edge-api/rest_management_api_client/external_jwt_signer" @@ -24,7 +24,7 @@ import ( "github.com/openziti/ziti/internal/rest/mgmt" ) -func (u *Upload) ProcessExternalJwtSigners(input map[string][]interface{}) (map[string]string, error) { +func (u *Importer) ProcessExternalJwtSigners(input map[string][]interface{}) (map[string]string, error) { var result = map[string]string{} for _, data := range input["externalJwtSigners"] { diff --git a/ziti/cmd/ascode/upload/upload_identities.go b/ziti/cmd/ascode/importer/import_identities.go similarity index 95% rename from ziti/cmd/ascode/upload/upload_identities.go rename to ziti/cmd/ascode/importer/import_identities.go index b5eac3099..a8690665d 100644 --- a/ziti/cmd/ascode/upload/upload_identities.go +++ b/ziti/cmd/ascode/importer/import_identities.go @@ -14,7 +14,7 @@ limitations under the License. */ -package upload +package importer import ( "encoding/json" @@ -28,7 +28,7 @@ import ( "github.com/openziti/ziti/internal/rest/mgmt" ) -func (u *Upload) ProcessIdentities(input map[string][]interface{}) (map[string]string, error) { +func (u *Importer) ProcessIdentities(input map[string][]interface{}) (map[string]string, error) { var result = map[string]string{} @@ -102,7 +102,7 @@ func (u *Upload) ProcessIdentities(input map[string][]interface{}) (map[string]s return result, nil } -func (u *Upload) lookupIdentities(roles []string) ([]string, error) { +func (u *Importer) lookupIdentities(roles []string) ([]string, error) { identityRoles := []string{} for _, role := range roles { if role[0:1] == "@" { diff --git a/ziti/cmd/ascode/upload/upload_posture_check.go b/ziti/cmd/ascode/importer/import_posture_check.go similarity index 96% rename from ziti/cmd/ascode/upload/upload_posture_check.go rename to ziti/cmd/ascode/importer/import_posture_check.go index 6045817b6..3a1bf04bf 100644 --- a/ziti/cmd/ascode/upload/upload_posture_check.go +++ b/ziti/cmd/ascode/importer/import_posture_check.go @@ -14,7 +14,7 @@ limitations under the License. */ -package upload +package importer import ( "encoding/json" @@ -27,7 +27,7 @@ import ( "strings" ) -func (u *Upload) ProcessPostureChecks(input map[string][]interface{}) (map[string]string, error) { +func (u *Importer) ProcessPostureChecks(input map[string][]interface{}) (map[string]string, error) { var result = map[string]string{} for _, data := range input["postureChecks"] { diff --git a/ziti/cmd/ascode/upload/upload_service_edgerouter_policies.go b/ziti/cmd/ascode/importer/import_service_edgerouter_policies.go similarity index 96% rename from ziti/cmd/ascode/upload/upload_service_edgerouter_policies.go rename to ziti/cmd/ascode/importer/import_service_edgerouter_policies.go index 9364cb415..58f837841 100644 --- a/ziti/cmd/ascode/upload/upload_service_edgerouter_policies.go +++ b/ziti/cmd/ascode/importer/import_service_edgerouter_policies.go @@ -14,7 +14,7 @@ limitations under the License. */ -package upload +package importer import ( "github.com/openziti/edge-api/rest_management_api_client/service_edge_router_policy" @@ -24,7 +24,7 @@ import ( "github.com/openziti/ziti/internal/rest/mgmt" ) -func (u *Upload) ProcessServiceEdgeRouterPolicies(input map[string][]interface{}) (map[string]string, error) { +func (u *Importer) ProcessServiceEdgeRouterPolicies(input map[string][]interface{}) (map[string]string, error) { var result = map[string]string{} for _, data := range input["serviceEdgeRouterPolicies"] { diff --git a/ziti/cmd/ascode/upload/upload_service_policies.go b/ziti/cmd/ascode/importer/import_service_policies.go similarity index 96% rename from ziti/cmd/ascode/upload/upload_service_policies.go rename to ziti/cmd/ascode/importer/import_service_policies.go index 59da9ab68..47af5ce39 100644 --- a/ziti/cmd/ascode/upload/upload_service_policies.go +++ b/ziti/cmd/ascode/importer/import_service_policies.go @@ -14,7 +14,7 @@ limitations under the License. */ -package upload +package importer import ( "errors" @@ -25,7 +25,7 @@ import ( "github.com/openziti/ziti/internal/rest/mgmt" ) -func (u *Upload) ProcessServicePolicies(input map[string][]interface{}) (map[string]string, error) { +func (u *Importer) ProcessServicePolicies(input map[string][]interface{}) (map[string]string, error) { var result = map[string]string{} for _, data := range input["servicePolicies"] { diff --git a/ziti/cmd/ascode/upload/upload_services.go b/ziti/cmd/ascode/importer/import_services.go similarity index 95% rename from ziti/cmd/ascode/upload/upload_services.go rename to ziti/cmd/ascode/importer/import_services.go index 61d656344..7f1b76c25 100644 --- a/ziti/cmd/ascode/upload/upload_services.go +++ b/ziti/cmd/ascode/importer/import_services.go @@ -14,7 +14,7 @@ limitations under the License. */ -package upload +package importer import ( "encoding/json" @@ -28,7 +28,7 @@ import ( "github.com/openziti/ziti/internal/rest/mgmt" ) -func (u *Upload) ProcessServices(input map[string][]interface{}) (map[string]string, error) { +func (u *Importer) ProcessServices(input map[string][]interface{}) (map[string]string, error) { var result = map[string]string{} @@ -102,7 +102,7 @@ func (u *Upload) ProcessServices(input map[string][]interface{}) (map[string]str return result, nil } -func (u *Upload) lookupServices(roles []string) ([]string, error) { +func (u *Importer) lookupServices(roles []string) ([]string, error) { serviceRoles := []string{} for _, role := range roles { if role[0:1] == "@" { diff --git a/ziti/cmd/cmd.go b/ziti/cmd/cmd.go index 35cfd8f34..464db3ec2 100644 --- a/ziti/cmd/cmd.go +++ b/ziti/cmd/cmd.go @@ -19,7 +19,7 @@ package cmd import ( goflag "flag" "fmt" - "github.com/openziti/ziti/ziti/cmd/ascode/upload" + "github.com/openziti/ziti/ziti/cmd/ascode/importer" "io" "os" "path/filepath" @@ -27,7 +27,7 @@ import ( "github.com/openziti/cobra-to-md" "github.com/openziti/ziti/ziti/cmd/agentcli" - "github.com/openziti/ziti/ziti/cmd/ascode/download" + "github.com/openziti/ziti/ziti/cmd/ascode/exporter" "github.com/openziti/ziti/ziti/cmd/common" "github.com/openziti/ziti/ziti/cmd/create" "github.com/openziti/ziti/ziti/cmd/database" @@ -147,8 +147,8 @@ func NewCmdRoot(in io.Reader, out, err io.Writer, cmd *cobra.Command) *cobra.Com opsCommands.AddCommand(NewUnwrapIdentityFileCommand(out, err)) opsCommands.AddCommand(verify.NewVerifyNetwork(out, err)) opsCommands.AddCommand(verify.NewVerifyTraffic(out, err)) - opsCommands.AddCommand(download.NewDownloadCmd(out, err)) - opsCommands.AddCommand(upload.NewUploadCmd(out, err)) + opsCommands.AddCommand(exporter.NewExportCmd(out, err)) + opsCommands.AddCommand(importer.NewImportCmd(out, err)) groups := templates.CommandGroups{ { From 159fac239f2d999693b00e932788b98a92a10f86 Mon Sep 17 00:00:00 2001 From: Jens Alm Date: Wed, 8 Jan 2025 15:57:52 -0500 Subject: [PATCH 13/16] Refactored checks into functions and added tests. --- internal/ascode/cache_util.go | 4 +- internal/print.go | 7 +- ziti/cmd/ascode/exporter/exporter.go | 45 ++-- .../ascode/exporter/exporter_auth_policies.go | 6 + .../exporter_certificate_authorities.go | 7 + .../ascode/exporter/exporter_config_types.go | 5 + ziti/cmd/ascode/exporter/exporter_configs.go | 6 + .../exporter/exporter_edgerouter_policies.go | 8 +- .../ascode/exporter/exporter_edgerouters.go | 7 + .../exporter/exporter_external_jwt_signers.go | 7 + .../ascode/exporter/exporter_identities.go | 6 + .../exporter/exporter_posture_checks.go | 6 + .../exporter_service_edgerouter_policies.go | 6 + .../exporter/exporter_service_policies.go | 6 + ziti/cmd/ascode/exporter/exporter_services.go | 6 + ziti/cmd/ascode/exporter/exporter_test.go | 223 ++++++++++++++++++ ziti/cmd/ascode/exporter/output.go | 8 +- .../importer/{import.go => importer.go} | 75 +++--- ..._policies.go => importer_auth_policies.go} | 11 +- ...go => importer_certificate_authorities.go} | 11 +- ...nfig_types.go => importer_config_types.go} | 12 +- ...{import_configs.go => importer_configs.go} | 11 +- ...ies.go => importer_edgerouter_policies.go} | 10 +- ...edgerouters.go => importer_edgerouters.go} | 11 +- ...rs.go => importer_external_jwt_signers.go} | 13 +- ...t_identities.go => importer_identities.go} | 10 +- ...ure_check.go => importer_posture_check.go} | 22 +- ...> importer_service_edgerouter_policies.go} | 10 +- ...licies.go => importer_service_policies.go} | 10 +- ...mport_services.go => importer_services.go} | 10 +- ziti/cmd/ascode/importer/importer_test.go | 223 ++++++++++++++++++ 31 files changed, 686 insertions(+), 116 deletions(-) create mode 100644 ziti/cmd/ascode/exporter/exporter_test.go rename ziti/cmd/ascode/importer/{import.go => importer.go} (83%) rename ziti/cmd/ascode/importer/{import_auth_policies.go => importer_auth_policies.go} (90%) rename ziti/cmd/ascode/importer/{import_certificate_authorities.go => importer_certificate_authorities.go} (86%) rename ziti/cmd/ascode/importer/{import_config_types.go => importer_config_types.go} (85%) rename ziti/cmd/ascode/importer/{import_configs.go => importer_configs.go} (89%) rename ziti/cmd/ascode/importer/{import_edgerouter_policies.go => importer_edgerouter_policies.go} (89%) rename ziti/cmd/ascode/importer/{import_edgerouters.go => importer_edgerouters.go} (89%) rename ziti/cmd/ascode/importer/{import_external_jwt_signers.go => importer_external_jwt_signers.go} (84%) rename ziti/cmd/ascode/importer/{import_identities.go => importer_identities.go} (92%) rename ziti/cmd/ascode/importer/{import_posture_check.go => importer_posture_check.go} (85%) rename ziti/cmd/ascode/importer/{import_service_edgerouter_policies.go => importer_service_edgerouter_policies.go} (89%) rename ziti/cmd/ascode/importer/{import_service_policies.go => importer_service_policies.go} (89%) rename ziti/cmd/ascode/importer/{import_services.go => importer_services.go} (92%) create mode 100644 ziti/cmd/ascode/importer/importer_test.go diff --git a/internal/ascode/cache_util.go b/internal/ascode/cache_util.go index 054a79e5f..775670877 100644 --- a/internal/ascode/cache_util.go +++ b/internal/ascode/cache_util.go @@ -18,12 +18,14 @@ package ascode import ( "errors" - log "github.com/sirupsen/logrus" + "github.com/michaelquigley/pfxlog" "reflect" ) type CacheGetter func(id string) (interface{}, error) +var log = pfxlog.Logger() + func GetItemFromCache(c map[string]interface{}, key string, fn CacheGetter) (interface{}, error) { if key == "" { return nil, errors.New("key is null, can't resolve from cache or get it from source") diff --git a/internal/print.go b/internal/print.go index 8f966255a..b54a5ca4c 100644 --- a/internal/print.go +++ b/internal/print.go @@ -6,6 +6,9 @@ import "io" /* Extends the standard FPrintF with overwriting the current line because it has the `\u001B[2K` */ -func FPrintFReusingLine(writer io.Writer, format string, a ...any) (n int, err error) { - return fmt.Fprintf(writer, "\u001B[2K"+format, a) +func FPrintfReusingLine(writer io.Writer, format string, a ...any) (n int, err error) { + return fmt.Fprintf(writer, "\u001B[2K"+format+"\r", a...) +} +func FPrintflnReusingLine(writer io.Writer, format string, a ...any) (n int, err error) { + return FPrintfReusingLine(writer, format+"\n", a...) } diff --git a/ziti/cmd/ascode/exporter/exporter.go b/ziti/cmd/ascode/exporter/exporter.go index b9fa6cb1e..7d0fb7979 100644 --- a/ziti/cmd/ascode/exporter/exporter.go +++ b/ziti/cmd/ascode/exporter/exporter.go @@ -157,10 +157,7 @@ func (d *Exporter) Execute(input []string) error { result := map[string]interface{}{} - all := slices.Contains(args, "all") || len(args) == 0 - if all || - slices.Contains(args, "ca") || - slices.Contains(args, "certificate-authority") { + if d.IsCertificateAuthorityExportRequired(args) { log.Debug("Processing Certificate Authorities") cas, err := d.GetCertificateAuthorities() if err != nil { @@ -168,8 +165,7 @@ func (d *Exporter) Execute(input []string) error { } result["certificateAuthorities"] = cas } - if all || - slices.Contains(args, "identity") { + if d.IsIdentityExportRequired(args) { log.Debug("Processing Identities") identities, err := d.GetIdentities() if err != nil { @@ -178,9 +174,7 @@ func (d *Exporter) Execute(input []string) error { result["identities"] = identities } - if all || - slices.Contains(args, "edge-router") || - slices.Contains(args, "er") { + if d.IsEdgeRouterExportRequired(args) { log.Debug("Processing Edge Routers") routers, err := d.GetEdgeRouters() if err != nil { @@ -188,8 +182,7 @@ func (d *Exporter) Execute(input []string) error { } result["edgeRouters"] = routers } - if all || - slices.Contains(args, "service") { + if d.IsServiceExportRequired(args) { log.Debug("Processing Services") services, err := d.GetServices() if err != nil { @@ -197,8 +190,7 @@ func (d *Exporter) Execute(input []string) error { } result["services"] = services } - if all || - slices.Contains(args, "config") { + if d.IsConfigExportRequired(args) { log.Debug("Processing Configs") configs, err := d.GetConfigs() if err != nil { @@ -206,8 +198,7 @@ func (d *Exporter) Execute(input []string) error { } result["configs"] = configs } - if all || - slices.Contains(args, "config-type") { + if d.IsConfigTypeExportRequired(args) { log.Debug("Processing Config Types") configTypes, err := d.GetConfigTypes() if err != nil { @@ -215,8 +206,7 @@ func (d *Exporter) Execute(input []string) error { } result["configTypes"] = configTypes } - if all || - slices.Contains(args, "service-policy") { + if d.IsServicePolicyExportRequired(args) { log.Debug("Processing Service Policies") servicePolicies, err := d.GetServicePolicies() if err != nil { @@ -224,17 +214,15 @@ func (d *Exporter) Execute(input []string) error { } result["servicePolicies"] = servicePolicies } - if all || - slices.Contains(args, "edge-router-policy") { + if d.IsEdgeRouterExportRequired(args) { log.Debug("Processing Edge Router Policies") - routerPolicies, err := d.GetRouterPolicies() + routerPolicies, err := d.GetEdgeRouterPolicies() if err != nil { return err } result["edgeRouterPolicies"] = routerPolicies } - if all || - slices.Contains(args, "service-edge-router-policy") { + if d.IsServiceEdgeRouterPolicyExportRequired(args) { log.Debug("Processing Service Edge Router Policies") serviceRouterPolicies, err := d.GetServiceEdgeRouterPolicies() if err != nil { @@ -242,8 +230,7 @@ func (d *Exporter) Execute(input []string) error { } result["serviceEdgeRouterPolicies"] = serviceRouterPolicies } - if all || - slices.Contains(args, "external-jwt-signer") { + if d.IsExtJwtSignerExportRequired(args) { log.Debug("Processing External JWT Signers") externalJwtSigners, err := d.GetExternalJwtSigners() if err != nil { @@ -251,8 +238,7 @@ func (d *Exporter) Execute(input []string) error { } result["externalJwtSigners"] = externalJwtSigners } - if all || - slices.Contains(args, "auth-policy") { + if d.IsAuthPolicyExportRequired(args) { log.Debug("Processing Auth Policies") authPolicies, err := d.GetAuthPolicies() if err != nil { @@ -260,8 +246,7 @@ func (d *Exporter) Execute(input []string) error { } result["authPolicies"] = authPolicies } - if all || - slices.Contains(args, "posture-check") { + if d.IsPostureCheckExportRequired(args) { log.Debug("Processing Posture Checks") postureChecks, err := d.GetPostureChecks() if err != nil { @@ -304,7 +289,7 @@ func (d *Exporter) getEntities(entityName string, count ClientCount, list Client more := true for more { resp, err := list(&offset, &limit) - _, _ = internal.FPrintFReusingLine(d.loginOpts.Err, "Reading %d/%d %s\r", offset, totalCount, entityName) + _, _ = internal.FPrintfReusingLine(d.loginOpts.Err, "Reading %d/%d %s", offset, totalCount, entityName) if err != nil { return nil, errors.Join(errors.New("error reading "+entityName), err) } @@ -323,7 +308,7 @@ func (d *Exporter) getEntities(entityName string, count ClientCount, list Client offset += limit } - _, _ = internal.FPrintFReusingLine(d.loginOpts.Err, "Read %d %s\r\n", len(result), entityName) + _, _ = internal.FPrintflnReusingLine(d.loginOpts.Err, "Read %d %s", len(result), entityName) return result, nil diff --git a/ziti/cmd/ascode/exporter/exporter_auth_policies.go b/ziti/cmd/ascode/exporter/exporter_auth_policies.go index a3cef02e2..ee658168c 100644 --- a/ziti/cmd/ascode/exporter/exporter_auth_policies.go +++ b/ziti/cmd/ascode/exporter/exporter_auth_policies.go @@ -21,8 +21,14 @@ import ( "github.com/openziti/edge-api/rest_management_api_client/external_jwt_signer" "github.com/openziti/edge-api/rest_model" "github.com/openziti/ziti/internal/ascode" + "slices" ) +func (d Exporter) IsAuthPolicyExportRequired(args []string) bool { + return slices.Contains(args, "all") || len(args) == 0 || // explicit all or nothing specified + slices.Contains(args, "auth-policy") +} + func (d Exporter) GetAuthPolicies() ([]map[string]interface{}, error) { return d.getEntities( diff --git a/ziti/cmd/ascode/exporter/exporter_certificate_authorities.go b/ziti/cmd/ascode/exporter/exporter_certificate_authorities.go index 430d3869d..11c63495d 100644 --- a/ziti/cmd/ascode/exporter/exporter_certificate_authorities.go +++ b/ziti/cmd/ascode/exporter/exporter_certificate_authorities.go @@ -19,8 +19,15 @@ package exporter import ( "github.com/openziti/edge-api/rest_management_api_client/certificate_authority" "github.com/openziti/edge-api/rest_model" + "slices" ) +func (d Exporter) IsCertificateAuthorityExportRequired(args []string) bool { + return slices.Contains(args, "all") || len(args) == 0 || // explicit all or nothing specified + slices.Contains(args, "ca") || + slices.Contains(args, "certificate-authority") +} + func (d Exporter) GetCertificateAuthorities() ([]map[string]interface{}, error) { return d.getEntities( diff --git a/ziti/cmd/ascode/exporter/exporter_config_types.go b/ziti/cmd/ascode/exporter/exporter_config_types.go index 41c6afb64..0dffd5556 100644 --- a/ziti/cmd/ascode/exporter/exporter_config_types.go +++ b/ziti/cmd/ascode/exporter/exporter_config_types.go @@ -22,6 +22,11 @@ import ( "slices" ) +func (d Exporter) IsConfigTypeExportRequired(args []string) bool { + return slices.Contains(args, "all") || len(args) == 0 || // explicit all or nothing specified + slices.Contains(args, "config-type") +} + func (d Exporter) GetConfigTypes() ([]map[string]interface{}, error) { return d.getEntities( diff --git a/ziti/cmd/ascode/exporter/exporter_configs.go b/ziti/cmd/ascode/exporter/exporter_configs.go index fb54ab8b4..47e6decc8 100644 --- a/ziti/cmd/ascode/exporter/exporter_configs.go +++ b/ziti/cmd/ascode/exporter/exporter_configs.go @@ -21,8 +21,14 @@ import ( "github.com/openziti/edge-api/rest_management_api_client/config" "github.com/openziti/edge-api/rest_model" "github.com/openziti/ziti/internal/ascode" + "slices" ) +func (d Exporter) IsConfigExportRequired(args []string) bool { + return slices.Contains(args, "all") || len(args) == 0 || // explicit all or nothing specified + slices.Contains(args, "config") +} + func (d Exporter) GetConfigs() ([]map[string]interface{}, error) { return d.getEntities( diff --git a/ziti/cmd/ascode/exporter/exporter_edgerouter_policies.go b/ziti/cmd/ascode/exporter/exporter_edgerouter_policies.go index 7bb906eab..57f9d3e03 100644 --- a/ziti/cmd/ascode/exporter/exporter_edgerouter_policies.go +++ b/ziti/cmd/ascode/exporter/exporter_edgerouter_policies.go @@ -19,9 +19,15 @@ package exporter import ( "github.com/openziti/edge-api/rest_management_api_client/edge_router_policy" "github.com/openziti/edge-api/rest_model" + "slices" ) -func (d Exporter) GetRouterPolicies() ([]map[string]interface{}, error) { +func (d Exporter) IsEdgeRouterPolicyExportRequired(args []string) bool { + return slices.Contains(args, "all") || len(args) == 0 || // explicit all or nothing specified + slices.Contains(args, "edge-router-policy") +} + +func (d Exporter) GetEdgeRouterPolicies() ([]map[string]interface{}, error) { return d.getEntities( "EdgeRouterPolicies", diff --git a/ziti/cmd/ascode/exporter/exporter_edgerouters.go b/ziti/cmd/ascode/exporter/exporter_edgerouters.go index 651694d8b..1b0313c0c 100644 --- a/ziti/cmd/ascode/exporter/exporter_edgerouters.go +++ b/ziti/cmd/ascode/exporter/exporter_edgerouters.go @@ -19,8 +19,15 @@ package exporter import ( "github.com/openziti/edge-api/rest_management_api_client/edge_router" "github.com/openziti/edge-api/rest_model" + "slices" ) +func (d Exporter) IsEdgeRouterExportRequired(args []string) bool { + return slices.Contains(args, "all") || len(args) == 0 || // explicit all or nothing specified + slices.Contains(args, "edge-router") || + slices.Contains(args, "er") +} + func (d Exporter) GetEdgeRouters() ([]map[string]interface{}, error) { return d.getEntities( diff --git a/ziti/cmd/ascode/exporter/exporter_external_jwt_signers.go b/ziti/cmd/ascode/exporter/exporter_external_jwt_signers.go index 08c0ed945..5be4eb154 100644 --- a/ziti/cmd/ascode/exporter/exporter_external_jwt_signers.go +++ b/ziti/cmd/ascode/exporter/exporter_external_jwt_signers.go @@ -19,8 +19,15 @@ package exporter import ( "github.com/openziti/edge-api/rest_management_api_client/external_jwt_signer" "github.com/openziti/edge-api/rest_model" + "slices" ) +func (d Exporter) IsExtJwtSignerExportRequired(args []string) bool { + return slices.Contains(args, "all") || len(args) == 0 || // explicit all or nothing specified + slices.Contains(args, "ext-jwt-signer") || + slices.Contains(args, "external-jwt-signer") +} + func (d Exporter) GetExternalJwtSigners() ([]map[string]interface{}, error) { return d.getEntities( diff --git a/ziti/cmd/ascode/exporter/exporter_identities.go b/ziti/cmd/ascode/exporter/exporter_identities.go index 5f774107d..e99451f63 100644 --- a/ziti/cmd/ascode/exporter/exporter_identities.go +++ b/ziti/cmd/ascode/exporter/exporter_identities.go @@ -22,8 +22,14 @@ import ( "github.com/openziti/edge-api/rest_management_api_client/identity" "github.com/openziti/edge-api/rest_model" "github.com/openziti/ziti/internal/ascode" + "slices" ) +func (d Exporter) IsIdentityExportRequired(args []string) bool { + return slices.Contains(args, "all") || len(args) == 0 || // explicit all or nothing specified + slices.Contains(args, "identity") +} + func (d Exporter) GetIdentities() ([]map[string]interface{}, error) { return d.getEntities( diff --git a/ziti/cmd/ascode/exporter/exporter_posture_checks.go b/ziti/cmd/ascode/exporter/exporter_posture_checks.go index a92fe8e17..c96c9cf4d 100644 --- a/ziti/cmd/ascode/exporter/exporter_posture_checks.go +++ b/ziti/cmd/ascode/exporter/exporter_posture_checks.go @@ -18,8 +18,14 @@ package exporter import ( "github.com/openziti/edge-api/rest_management_api_client/posture_checks" + "golang.org/x/exp/slices" ) +func (d Exporter) IsPostureCheckExportRequired(args []string) bool { + return slices.Contains(args, "all") || len(args) == 0 || // explicit all or nothing specified + slices.Contains(args, "posture-check") +} + func (d Exporter) GetPostureChecks() ([]map[string]interface{}, error) { return d.getEntities( diff --git a/ziti/cmd/ascode/exporter/exporter_service_edgerouter_policies.go b/ziti/cmd/ascode/exporter/exporter_service_edgerouter_policies.go index edbc74fce..82e1bb014 100644 --- a/ziti/cmd/ascode/exporter/exporter_service_edgerouter_policies.go +++ b/ziti/cmd/ascode/exporter/exporter_service_edgerouter_policies.go @@ -19,8 +19,14 @@ package exporter import ( "github.com/openziti/edge-api/rest_management_api_client/service_edge_router_policy" "github.com/openziti/edge-api/rest_model" + "slices" ) +func (d Exporter) IsServiceEdgeRouterPolicyExportRequired(args []string) bool { + return slices.Contains(args, "all") || len(args) == 0 || // explicit all or nothing specified + slices.Contains(args, "service-edge-router-policy") +} + func (d Exporter) GetServiceEdgeRouterPolicies() ([]map[string]interface{}, error) { return d.getEntities( diff --git a/ziti/cmd/ascode/exporter/exporter_service_policies.go b/ziti/cmd/ascode/exporter/exporter_service_policies.go index ff364fb38..723c73da7 100644 --- a/ziti/cmd/ascode/exporter/exporter_service_policies.go +++ b/ziti/cmd/ascode/exporter/exporter_service_policies.go @@ -19,8 +19,14 @@ package exporter import ( "github.com/openziti/edge-api/rest_management_api_client/service_policy" "github.com/openziti/edge-api/rest_model" + "slices" ) +func (d Exporter) IsServicePolicyExportRequired(args []string) bool { + return slices.Contains(args, "all") || len(args) == 0 || // explicit all or nothing specified + slices.Contains(args, "service-policy") +} + func (d Exporter) GetServicePolicies() ([]map[string]interface{}, error) { return d.getEntities( diff --git a/ziti/cmd/ascode/exporter/exporter_services.go b/ziti/cmd/ascode/exporter/exporter_services.go index 0f39a513c..60e39ddb0 100644 --- a/ziti/cmd/ascode/exporter/exporter_services.go +++ b/ziti/cmd/ascode/exporter/exporter_services.go @@ -22,8 +22,14 @@ import ( "github.com/openziti/edge-api/rest_management_api_client/service" "github.com/openziti/edge-api/rest_model" "github.com/openziti/ziti/internal/ascode" + "slices" ) +func (d Exporter) IsServiceExportRequired(args []string) bool { + return slices.Contains(args, "all") || len(args) == 0 || // explicit all or nothing specified + slices.Contains(args, "service") +} + func (d Exporter) GetServices() ([]map[string]interface{}, error) { return d.getEntities( diff --git a/ziti/cmd/ascode/exporter/exporter_test.go b/ziti/cmd/ascode/exporter/exporter_test.go new file mode 100644 index 000000000..037066ed8 --- /dev/null +++ b/ziti/cmd/ascode/exporter/exporter_test.go @@ -0,0 +1,223 @@ +package exporter + +import ( + "github.com/stretchr/testify/assert" + "testing" +) + +func Test_InputArgs(t *testing.T) { + + exporter := Exporter{} + + t.Run("service export", func(t *testing.T) { + + assert.True(t, exporter.IsCertificateAuthorityExportRequired([]string{"certificate-authority"}), "should be exported") + assert.True(t, exporter.IsCertificateAuthorityExportRequired([]string{"all"}), "should be exported") + assert.True(t, exporter.IsCertificateAuthorityExportRequired([]string{}), "should be exported") + + assert.False(t, exporter.IsCertificateAuthorityExportRequired([]string{"service"}), "should not be exported") + assert.False(t, exporter.IsCertificateAuthorityExportRequired([]string{"config"}), "should not be exported") + assert.False(t, exporter.IsCertificateAuthorityExportRequired([]string{"config-type"}), "should not be exported") + assert.False(t, exporter.IsCertificateAuthorityExportRequired([]string{"identity"}), "should not be exported") + assert.False(t, exporter.IsCertificateAuthorityExportRequired([]string{"auth-policy"}), "should not be exported") + assert.False(t, exporter.IsCertificateAuthorityExportRequired([]string{"ext-jwt-signer"}), "should not be exported") + assert.False(t, exporter.IsCertificateAuthorityExportRequired([]string{"posture-check"}), "should not be exported") + assert.False(t, exporter.IsCertificateAuthorityExportRequired([]string{"service-policy"}), "should not be exported") + assert.False(t, exporter.IsCertificateAuthorityExportRequired([]string{"edge-router-policy"}), "should not be exported") + assert.False(t, exporter.IsCertificateAuthorityExportRequired([]string{"service-edge-router-policy"}), "should not be exported") + + }) + + t.Run("service export", func(t *testing.T) { + + assert.True(t, exporter.IsServiceExportRequired([]string{"service"}), "should be exported") + assert.True(t, exporter.IsServiceExportRequired([]string{"all"}), "should be exported") + assert.True(t, exporter.IsServiceExportRequired([]string{}), "should be exported") + + assert.False(t, exporter.IsServiceExportRequired([]string{"config"}), "should not be exported") + assert.False(t, exporter.IsServiceExportRequired([]string{"config-type"}), "should not be exported") + assert.False(t, exporter.IsServiceExportRequired([]string{"identity"}), "should not be exported") + assert.False(t, exporter.IsServiceExportRequired([]string{"auth-policy"}), "should not be exported") + assert.False(t, exporter.IsServiceExportRequired([]string{"ext-jwt-signer"}), "should not be exported") + assert.False(t, exporter.IsServiceExportRequired([]string{"posture-check"}), "should not be exported") + assert.False(t, exporter.IsServiceExportRequired([]string{"service-policy"}), "should not be exported") + assert.False(t, exporter.IsServiceExportRequired([]string{"edge-router-policy"}), "should not be exported") + assert.False(t, exporter.IsServiceExportRequired([]string{"service-edge-router-policy"}), "should not be exported") + + }) + + t.Run("config export", func(t *testing.T) { + + assert.True(t, exporter.IsConfigExportRequired([]string{"config"}), "should be exported") + assert.True(t, exporter.IsConfigExportRequired([]string{"all"}), "should be exported") + assert.True(t, exporter.IsConfigExportRequired([]string{}), "should be exported") + + assert.False(t, exporter.IsConfigExportRequired([]string{"service"}), "should not be exported") + assert.False(t, exporter.IsConfigExportRequired([]string{"config-type"}), "should not be exported") + assert.False(t, exporter.IsConfigExportRequired([]string{"identity"}), "should not be exported") + assert.False(t, exporter.IsConfigExportRequired([]string{"certificate-authority"}), "should not be exported") + assert.False(t, exporter.IsConfigExportRequired([]string{"auth-policy"}), "should not be exported") + assert.False(t, exporter.IsConfigExportRequired([]string{"ext-jwt-signer"}), "should not be exported") + assert.False(t, exporter.IsConfigExportRequired([]string{"posture-check"}), "should not be exported") + assert.False(t, exporter.IsConfigExportRequired([]string{"service-policy"}), "should not be exported") + assert.False(t, exporter.IsConfigExportRequired([]string{"edge-router-policy"}), "should not be exported") + assert.False(t, exporter.IsConfigExportRequired([]string{"service-edge-router-policy"}), "should not be exported") + + }) + + t.Run("config-type export", func(t *testing.T) { + + assert.True(t, exporter.IsConfigTypeExportRequired([]string{"config-type"}), "should be exported") + assert.True(t, exporter.IsConfigTypeExportRequired([]string{"all"}), "should be exported") + assert.True(t, exporter.IsConfigTypeExportRequired([]string{}), "should be exported") + + assert.False(t, exporter.IsConfigTypeExportRequired([]string{"service"}), "should not be exported") + assert.False(t, exporter.IsConfigTypeExportRequired([]string{"config"}), "should not be exported") + assert.False(t, exporter.IsConfigTypeExportRequired([]string{"certificate-authority"}), "should not be exported") + assert.False(t, exporter.IsConfigTypeExportRequired([]string{"identity"}), "should not be exported") + assert.False(t, exporter.IsConfigTypeExportRequired([]string{"auth-policy"}), "should not be exported") + assert.False(t, exporter.IsConfigTypeExportRequired([]string{"ext-jwt-signer"}), "should not be exported") + assert.False(t, exporter.IsConfigTypeExportRequired([]string{"posture-check"}), "should not be exported") + assert.False(t, exporter.IsConfigTypeExportRequired([]string{"service-policy"}), "should not be exported") + assert.False(t, exporter.IsConfigTypeExportRequired([]string{"edge-router-policy"}), "should not be exported") + assert.False(t, exporter.IsConfigTypeExportRequired([]string{"service-edge-router-policy"}), "should not be exported") + + }) + + t.Run("identity export", func(t *testing.T) { + + assert.True(t, exporter.IsIdentityExportRequired([]string{"identity"}), "should be exported") + assert.True(t, exporter.IsIdentityExportRequired([]string{"all"}), "should be exported") + assert.True(t, exporter.IsIdentityExportRequired([]string{}), "should be exported") + + assert.False(t, exporter.IsIdentityExportRequired([]string{"auth-policy"}), "should not be exported") + assert.False(t, exporter.IsIdentityExportRequired([]string{"ext-jwt-signer"}), "should not be exported") + assert.False(t, exporter.IsIdentityExportRequired([]string{"external-jwt-signer"}), "should not be exported") + assert.False(t, exporter.IsIdentityExportRequired([]string{"certificate-authority"}), "should not be exported") + assert.False(t, exporter.IsIdentityExportRequired([]string{"service"}), "should not be exported") + assert.False(t, exporter.IsIdentityExportRequired([]string{"config"}), "should not be exported") + assert.False(t, exporter.IsIdentityExportRequired([]string{"config-type"}), "should not be exported") + assert.False(t, exporter.IsIdentityExportRequired([]string{"posture-check"}), "should not be exported") + assert.False(t, exporter.IsIdentityExportRequired([]string{"service-policy"}), "should not be exported") + assert.False(t, exporter.IsIdentityExportRequired([]string{"edge-router-policy"}), "should not be exported") + assert.False(t, exporter.IsIdentityExportRequired([]string{"service-edge-router-policy"}), "should not be exported") + + }) + + t.Run("auth-policy export", func(t *testing.T) { + + assert.True(t, exporter.IsAuthPolicyExportRequired([]string{"auth-policy"}), "should be exported") + assert.True(t, exporter.IsAuthPolicyExportRequired([]string{"all"}), "should be exported") + assert.True(t, exporter.IsAuthPolicyExportRequired([]string{}), "should be exported") + + assert.False(t, exporter.IsAuthPolicyExportRequired([]string{"identity"}), "should not be exported") + assert.False(t, exporter.IsAuthPolicyExportRequired([]string{"ext-jwt-signer"}), "should not be exported") + assert.False(t, exporter.IsAuthPolicyExportRequired([]string{"external-jwt-signer"}), "should not be exported") + assert.False(t, exporter.IsAuthPolicyExportRequired([]string{"certificate-authority"}), "should not be exported") + assert.False(t, exporter.IsAuthPolicyExportRequired([]string{"service"}), "should not be exported") + assert.False(t, exporter.IsAuthPolicyExportRequired([]string{"config"}), "should not be exported") + assert.False(t, exporter.IsAuthPolicyExportRequired([]string{"config-type"}), "should not be exported") + assert.False(t, exporter.IsAuthPolicyExportRequired([]string{"posture-check"}), "should not be exported") + assert.False(t, exporter.IsAuthPolicyExportRequired([]string{"service-policy"}), "should not be exported") + assert.False(t, exporter.IsAuthPolicyExportRequired([]string{"edge-router-policy"}), "should not be exported") + assert.False(t, exporter.IsAuthPolicyExportRequired([]string{"service-edge-router-policy"}), "should not be exported") + + }) + + t.Run("ext-jwt-signer export", func(t *testing.T) { + + assert.True(t, exporter.IsExtJwtSignerExportRequired([]string{"ext-jwt-signer"}), "should be exported") + assert.True(t, exporter.IsExtJwtSignerExportRequired([]string{"external-jwt-signer"}), "should be exported") + assert.True(t, exporter.IsExtJwtSignerExportRequired([]string{"all"}), "should be exported") + assert.True(t, exporter.IsExtJwtSignerExportRequired([]string{}), "should be exported") + + assert.False(t, exporter.IsExtJwtSignerExportRequired([]string{"identity"}), "should not be exported") + assert.False(t, exporter.IsExtJwtSignerExportRequired([]string{"auth-policy"}), "should not be exported") + assert.False(t, exporter.IsExtJwtSignerExportRequired([]string{"certificate-authority"}), "should not be exported") + assert.False(t, exporter.IsExtJwtSignerExportRequired([]string{"service"}), "should not be exported") + assert.False(t, exporter.IsExtJwtSignerExportRequired([]string{"config"}), "should not be exported") + assert.False(t, exporter.IsExtJwtSignerExportRequired([]string{"config-type"}), "should not be exported") + assert.False(t, exporter.IsExtJwtSignerExportRequired([]string{"posture-check"}), "should not be exported") + assert.False(t, exporter.IsExtJwtSignerExportRequired([]string{"service-policy"}), "should not be exported") + assert.False(t, exporter.IsExtJwtSignerExportRequired([]string{"edge-router-policy"}), "should not be exported") + assert.False(t, exporter.IsExtJwtSignerExportRequired([]string{"service-edge-router-policy"}), "should not be exported") + + }) + + t.Run("posture-check export", func(t *testing.T) { + + assert.True(t, exporter.IsPostureCheckExportRequired([]string{"posture-check"}), "should be exported") + assert.True(t, exporter.IsPostureCheckExportRequired([]string{"all"}), "should be exported") + assert.True(t, exporter.IsPostureCheckExportRequired([]string{}), "should be exported") + + assert.False(t, exporter.IsPostureCheckExportRequired([]string{"service"}), "should not be exported") + assert.False(t, exporter.IsPostureCheckExportRequired([]string{"config"}), "should not be exported") + assert.False(t, exporter.IsPostureCheckExportRequired([]string{"config-type"}), "should not be exported") + assert.False(t, exporter.IsPostureCheckExportRequired([]string{"identity"}), "should not be exported") + assert.False(t, exporter.IsPostureCheckExportRequired([]string{"auth-policy"}), "should not be exported") + assert.False(t, exporter.IsPostureCheckExportRequired([]string{"ext-jwt-signer"}), "should not be exported") + assert.False(t, exporter.IsPostureCheckExportRequired([]string{"external-jwt-signer"}), "should not be exported") + assert.False(t, exporter.IsPostureCheckExportRequired([]string{"service-policy"}), "should not be exported") + assert.False(t, exporter.IsPostureCheckExportRequired([]string{"service-edge-router-policy"}), "should not be exported") + assert.False(t, exporter.IsPostureCheckExportRequired([]string{"edge-router-policy"}), "should not be exported") + + }) + + t.Run("service-policy export", func(t *testing.T) { + + assert.True(t, exporter.IsServicePolicyExportRequired([]string{"service-policy"}), "should be exported") + assert.True(t, exporter.IsServicePolicyExportRequired([]string{"all"}), "should be exported") + assert.True(t, exporter.IsServicePolicyExportRequired([]string{}), "should be exported") + + assert.False(t, exporter.IsServicePolicyExportRequired([]string{"service"}), "should not be exported") + assert.False(t, exporter.IsServicePolicyExportRequired([]string{"config"}), "should not be exported") + assert.False(t, exporter.IsServicePolicyExportRequired([]string{"config-type"}), "should not be exported") + assert.False(t, exporter.IsServicePolicyExportRequired([]string{"identity"}), "should not be exported") + assert.False(t, exporter.IsServicePolicyExportRequired([]string{"auth-policy"}), "should not be exported") + assert.False(t, exporter.IsServicePolicyExportRequired([]string{"ext-jwt-signer"}), "should not be exported") + assert.False(t, exporter.IsServicePolicyExportRequired([]string{"external-jwt-signer"}), "should not be exported") + assert.False(t, exporter.IsServicePolicyExportRequired([]string{"posture-check"}), "should not be exported") + assert.False(t, exporter.IsServicePolicyExportRequired([]string{"service-edge-router-policy"}), "should not be exported") + assert.False(t, exporter.IsServicePolicyExportRequired([]string{"edge-router-policy"}), "should not be exported") + + }) + + t.Run("service-edge-router-policy export", func(t *testing.T) { + + assert.True(t, exporter.IsServiceEdgeRouterPolicyExportRequired([]string{"service-edge-router-policy"}), "should be exported") + assert.True(t, exporter.IsServiceEdgeRouterPolicyExportRequired([]string{"all"}), "should be exported") + assert.True(t, exporter.IsServiceEdgeRouterPolicyExportRequired([]string{}), "should be exported") + + assert.False(t, exporter.IsServiceEdgeRouterPolicyExportRequired([]string{"service"}), "should not be exported") + assert.False(t, exporter.IsServiceEdgeRouterPolicyExportRequired([]string{"config"}), "should not be exported") + assert.False(t, exporter.IsServiceEdgeRouterPolicyExportRequired([]string{"config-type"}), "should not be exported") + assert.False(t, exporter.IsServiceEdgeRouterPolicyExportRequired([]string{"identity"}), "should not be exported") + assert.False(t, exporter.IsServiceEdgeRouterPolicyExportRequired([]string{"auth-policy"}), "should not be exported") + assert.False(t, exporter.IsServiceEdgeRouterPolicyExportRequired([]string{"ext-jwt-signer"}), "should not be exported") + assert.False(t, exporter.IsServiceEdgeRouterPolicyExportRequired([]string{"external-jwt-signer"}), "should not be exported") + assert.False(t, exporter.IsServiceEdgeRouterPolicyExportRequired([]string{"posture-check"}), "should not be exported") + assert.False(t, exporter.IsServiceEdgeRouterPolicyExportRequired([]string{"service-policy"}), "should not be exported") + assert.False(t, exporter.IsServiceEdgeRouterPolicyExportRequired([]string{"edge-router-policy"}), "should not be exported") + + }) + + t.Run("service-edge-router-policy export", func(t *testing.T) { + + assert.True(t, exporter.IsEdgeRouterPolicyExportRequired([]string{"edge-router-policy"}), "should be exported") + assert.True(t, exporter.IsEdgeRouterPolicyExportRequired([]string{"all"}), "should be exported") + assert.True(t, exporter.IsEdgeRouterPolicyExportRequired([]string{}), "should be exported") + + assert.False(t, exporter.IsEdgeRouterPolicyExportRequired([]string{"service"}), "should not be exported") + assert.False(t, exporter.IsEdgeRouterPolicyExportRequired([]string{"config"}), "should not be exported") + assert.False(t, exporter.IsEdgeRouterPolicyExportRequired([]string{"config-type"}), "should not be exported") + assert.False(t, exporter.IsEdgeRouterPolicyExportRequired([]string{"identity"}), "should not be exported") + assert.False(t, exporter.IsEdgeRouterPolicyExportRequired([]string{"auth-policy"}), "should not be exported") + assert.False(t, exporter.IsEdgeRouterPolicyExportRequired([]string{"ext-jwt-signer"}), "should not be exported") + assert.False(t, exporter.IsEdgeRouterPolicyExportRequired([]string{"external-jwt-signer"}), "should not be exported") + assert.False(t, exporter.IsEdgeRouterPolicyExportRequired([]string{"posture-check"}), "should not be exported") + assert.False(t, exporter.IsEdgeRouterPolicyExportRequired([]string{"service-policy"}), "should not be exported") + assert.False(t, exporter.IsEdgeRouterPolicyExportRequired([]string{"service-edge-router-policy"}), "should not be exported") + + }) + +} diff --git a/ziti/cmd/ascode/exporter/output.go b/ziti/cmd/ascode/exporter/output.go index 2fc4fb226..6ec2916eb 100644 --- a/ziti/cmd/ascode/exporter/output.go +++ b/ziti/cmd/ascode/exporter/output.go @@ -62,12 +62,12 @@ func (output Output) Write(data any) error { var err error if output.outputYaml { if output.verbose { - _, _ = internal.FPrintFReusingLine(output.errWriter, "Formatting as Yaml\r\n") + _, _ = internal.FPrintfReusingLine(output.errWriter, "Formatting as Yaml\r\n") } formatted, err = output.ToYaml(data) } else { if output.verbose { - _, _ = internal.FPrintFReusingLine(output.errWriter, "Formatting as JSON\r\n") + _, _ = internal.FPrintfReusingLine(output.errWriter, "Formatting as JSON\r\n") } formatted, err = output.ToJson(data) } @@ -77,9 +77,9 @@ func (output Output) Write(data any) error { if output.verbose { if output.filename != "" { - _, _ = internal.FPrintFReusingLine(output.errWriter, "Writing to file: %s\r\n", output.filename) + _, _ = internal.FPrintfReusingLine(output.errWriter, "Writing to file: %s\r\n", output.filename) } else { - _, _ = internal.FPrintFReusingLine(output.errWriter, "Writing output to writer\r\n") + _, _ = internal.FPrintfReusingLine(output.errWriter, "Writing output to writer\r\n") } } bytes, err := output.writer.Write(formatted) diff --git a/ziti/cmd/ascode/importer/import.go b/ziti/cmd/ascode/importer/importer.go similarity index 83% rename from ziti/cmd/ascode/importer/import.go rename to ziti/cmd/ascode/importer/importer.go index 15cc41e79..e8cdf49bd 100644 --- a/ziti/cmd/ascode/importer/import.go +++ b/ziti/cmd/ascode/importer/importer.go @@ -32,10 +32,11 @@ import ( "gopkg.in/yaml.v3" "io" "os" - "slices" "strings" ) +var log = pfxlog.Logger() + type Importer struct { loginOpts edge.LoginOptions client *rest_management_api_client.ZitiEdgeManagement @@ -50,8 +51,6 @@ type Importer struct { identityCache map[string]any } -var log = pfxlog.Logger() - func NewImportCmd(out io.Writer, errOut io.Writer) *cobra.Command { u := &Importer{} @@ -150,12 +149,9 @@ func (u *Importer) Execute(data map[string][]interface{}, inputArgs []string) (m u.identityCache = map[string]any{} result := map[string]any{} - all := slices.Contains(args, "all") || len(args) == 0 cas := map[string]string{} - if all || - slices.Contains(args, "ca") || - slices.Contains(args, "certificate-authority") { + if u.IsCertificateAuthorityImportRequired(args) { log.Debug("Processing CertificateAuthorities") var err error cas, err = u.ProcessCertificateAuthorities(data) @@ -167,13 +163,10 @@ func (u *Importer) Execute(data map[string][]interface{}, inputArgs []string) (m Debug("CertificateAuthorities created") } result["certificateAuthorities"] = cas - _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Created %d CertificateAuthorities\r\n", len(cas)) + _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Created %d CertificateAuthorities\r\n", len(cas)) externalJwtSigners := map[string]string{} - if all || - slices.Contains(args, "external-jwt-signer") || - slices.Contains(args, "auth-policy") || - slices.Contains(args, "identity") { + if u.IsExtJwtSignerImportRequired(args) { log.Debug("Processing ExtJWTSigners") var err error externalJwtSigners, err = u.ProcessExternalJwtSigners(data) @@ -182,13 +175,11 @@ func (u *Importer) Execute(data map[string][]interface{}, inputArgs []string) (m } log.WithField("externalJwtSigners", externalJwtSigners).Debug("ExtJWTSigners created") } - _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Created %d ExtJWTSigners\r\n", len(externalJwtSigners)) + _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Created %d ExtJWTSigners\r\n", len(externalJwtSigners)) result["externalJwtSigners"] = externalJwtSigners authPolicies := map[string]string{} - if all || - slices.Contains(args, "auth-policy") || - slices.Contains(args, "identity") { + if u.IsAuthPolicyImportRequired(args) { log.Debug("Processing AuthPolicies") var err error authPolicies, err = u.ProcessAuthPolicies(data) @@ -197,12 +188,11 @@ func (u *Importer) Execute(data map[string][]interface{}, inputArgs []string) (m } log.WithField("authPolicies", authPolicies).Debug("AuthPolicies created") } - _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Created %d AuthPolicies\r\n", len(authPolicies)) + _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Created %d AuthPolicies\r\n", len(authPolicies)) result["authPolicies"] = authPolicies identities := map[string]string{} - if all || - slices.Contains(args, "identity") { + if u.IsIdentityImportRequired(args) { log.Debug("Processing Identities") var err error identities, err = u.ProcessIdentities(data) @@ -211,14 +201,11 @@ func (u *Importer) Execute(data map[string][]interface{}, inputArgs []string) (m } log.WithField("identities", identities).Debug("Identities created") } - _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Created %d Identities\r\n", len(identities)) + _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Created %d Identities\r\n", len(identities)) result["identities"] = identities configTypes := map[string]string{} - if all || - slices.Contains(args, "config-type") || - slices.Contains(args, "config") || - slices.Contains(args, "service") { + if u.IsConfigTypeImportRequired(args) { log.Debug("Processing ConfigTypes") var err error configTypes, err = u.ProcessConfigTypes(data) @@ -227,13 +214,11 @@ func (u *Importer) Execute(data map[string][]interface{}, inputArgs []string) (m } log.WithField("configTypes", configTypes).Debug("ConfigTypes created") } - _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Created %d ConfigTypes\r\n", len(configTypes)) + _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Created %d ConfigTypes\r\n", len(configTypes)) result["configTypes"] = configTypes configs := map[string]string{} - if all || - slices.Contains(args, "config") || - slices.Contains(args, "service") { + if u.IsConfigImportRequired(args) { log.Debug("Processing Configs") var err error configs, err = u.ProcessConfigs(data) @@ -242,12 +227,11 @@ func (u *Importer) Execute(data map[string][]interface{}, inputArgs []string) (m } log.WithField("configs", configs).Debug("Configs created") } - _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Created %d Configs\r\n", len(configs)) + _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Created %d Configs\r\n", len(configs)) result["configs"] = configs services := map[string]string{} - if all || - slices.Contains(args, "service") { + if u.IsServiceImportRequired(args) { log.Debug("Processing Services") var err error services, err = u.ProcessServices(data) @@ -256,12 +240,11 @@ func (u *Importer) Execute(data map[string][]interface{}, inputArgs []string) (m } log.WithField("services", services).Debug("Services created") } - _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Created %d Services\r\n", len(services)) + _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Created %d Services\r\n", len(services)) result["services"] = services postureChecks := map[string]string{} - if all || - slices.Contains(args, "posture-check") { + if u.IsPostureCheckImportRequired(args) { log.Debug("Processing PostureChecks") var err error postureChecks, err = u.ProcessPostureChecks(data) @@ -270,12 +253,11 @@ func (u *Importer) Execute(data map[string][]interface{}, inputArgs []string) (m } log.WithField("postureChecks", postureChecks).Debug("PostureChecks created") } - _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Created %d PostureChecks\r\n", len(postureChecks)) + _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Created %d PostureChecks\r\n", len(postureChecks)) result["postureChecks"] = postureChecks routers := map[string]string{} - if all || - slices.Contains(args, "edge-router") || slices.Contains(args, "er") { + if u.IsEdgeRouterImportRequired(args) { log.Debug("Processing EdgeRouters") var err error routers, err = u.ProcessEdgeRouters(data) @@ -284,13 +266,12 @@ func (u *Importer) Execute(data map[string][]interface{}, inputArgs []string) (m } log.WithField("edgeRouters", routers).Debug("EdgeRouters created") } - _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Created %d EdgeRouters\r\n", len(routers)) + _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Created %d EdgeRouters\r\n", len(routers)) result["edgeRouters"] = routers serviceEdgeRouterPolicies := map[string]string{} - if all || - slices.Contains(args, "service-edge-router-policy") { - log.Debug("Processing ServiceRouterPolicies") + if u.IsServiceEdgeRouterPolicyImportRequired(args) { + log.Debug("Processing ServiceEdgeRouterPolicies") var err error serviceEdgeRouterPolicies, err = u.ProcessServiceEdgeRouterPolicies(data) if err != nil { @@ -298,12 +279,11 @@ func (u *Importer) Execute(data map[string][]interface{}, inputArgs []string) (m } log.WithField("serviceEdgeRouterPolicies", serviceEdgeRouterPolicies).Debug("ServiceEdgeRouterPolicies created") } - _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Created %d ServiceEdgeRouterPolicies\r\n", len(serviceEdgeRouterPolicies)) + _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Created %d ServiceEdgeRouterPolicies\r\n", len(serviceEdgeRouterPolicies)) result["serviceEdgeRouterPolicies"] = serviceEdgeRouterPolicies servicePolicies := map[string]string{} - if all || - slices.Contains(args, "service-policy") { + if u.IsServicePolicyImportRequired(args) { log.Debug("Processing ServicePolicies") var err error servicePolicies, err = u.ProcessServicePolicies(data) @@ -312,12 +292,11 @@ func (u *Importer) Execute(data map[string][]interface{}, inputArgs []string) (m } log.WithField("servicePolicies", servicePolicies).Debug("ServicePolicies created") } - _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Created %d ServicePolicies\r\n", len(servicePolicies)) + _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Created %d ServicePolicies\r\n", len(servicePolicies)) result["servicePolicies"] = servicePolicies routerPolicies := map[string]string{} - if all || - slices.Contains(args, "edge-router-policy") { + if u.IsEdgeRouterPolicyImportRequired(args) { log.Debug("Processing EdgeRouterPolicies") var err error routerPolicies, err = u.ProcessEdgeRouterPolicies(data) @@ -326,7 +305,7 @@ func (u *Importer) Execute(data map[string][]interface{}, inputArgs []string) (m } log.WithField("routerPolicies", routerPolicies).Debug("EdgeRouterPolicies created") } - _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Created %d EdgeRouterPolicies\r\n", len(routerPolicies)) + _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Created %d EdgeRouterPolicies\r\n", len(routerPolicies)) result["edgeRouterPolicies"] = routerPolicies log.Info("Upload complete") diff --git a/ziti/cmd/ascode/importer/import_auth_policies.go b/ziti/cmd/ascode/importer/importer_auth_policies.go similarity index 90% rename from ziti/cmd/ascode/importer/import_auth_policies.go rename to ziti/cmd/ascode/importer/importer_auth_policies.go index 2fc7295c6..e1aa2e4d7 100644 --- a/ziti/cmd/ascode/importer/import_auth_policies.go +++ b/ziti/cmd/ascode/importer/importer_auth_policies.go @@ -25,8 +25,15 @@ import ( "github.com/openziti/ziti/internal" "github.com/openziti/ziti/internal/ascode" "github.com/openziti/ziti/internal/rest/mgmt" + "slices" ) +func (u *Importer) IsAuthPolicyImportRequired(args []string) bool { + return slices.Contains(args, "all") || len(args) == 0 || // explicit all or nothing specified + slices.Contains(args, "auth-policy") || + slices.Contains(args, "identity") +} + func (u *Importer) ProcessAuthPolicies(input map[string][]interface{}) (map[string]string, error) { if u.loginOpts.Verbose { @@ -47,7 +54,7 @@ func (u *Importer) ProcessAuthPolicies(input map[string][]interface{}) (map[stri "authPolicyId": *existing.ID, }).Info("Found existing Auth Policy, skipping create") } - _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Skipping AuthPolicy %s\r", *create.Name) + _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Skipping AuthPolicy %s\r", *create.Name) continue } @@ -76,7 +83,7 @@ func (u *Importer) ProcessAuthPolicies(input map[string][]interface{}) (map[stri create.Primary.ExtJWT.AllowedSigners = allowedSignerIds // do the actual create since it doesn't exist - _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Creating AuthPolicy %s\r", *create.Name) + _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Creating AuthPolicy %s\r", *create.Name) if u.loginOpts.Verbose { log.WithField("name", *create.Name). Debug("Creating AuthPolicy") diff --git a/ziti/cmd/ascode/importer/import_certificate_authorities.go b/ziti/cmd/ascode/importer/importer_certificate_authorities.go similarity index 86% rename from ziti/cmd/ascode/importer/import_certificate_authorities.go rename to ziti/cmd/ascode/importer/importer_certificate_authorities.go index d503cf260..9c22b9354 100644 --- a/ziti/cmd/ascode/importer/import_certificate_authorities.go +++ b/ziti/cmd/ascode/importer/importer_certificate_authorities.go @@ -22,8 +22,15 @@ import ( "github.com/openziti/edge-api/rest_util" "github.com/openziti/ziti/internal" "github.com/openziti/ziti/internal/rest/mgmt" + "slices" ) +func (u *Importer) IsCertificateAuthorityImportRequired(args []string) bool { + return slices.Contains(args, "all") || len(args) == 0 || // explicit all or nothing specified + slices.Contains(args, "ca") || + slices.Contains(args, "certificate-authority") +} + func (u *Importer) ProcessCertificateAuthorities(input map[string][]interface{}) (map[string]string, error) { var result = map[string]string{} @@ -40,12 +47,12 @@ func (u *Importer) ProcessCertificateAuthorities(input map[string][]interface{}) }). Info("Found existing CertificateAuthority, skipping create") } - _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Skipping CertificateAuthority %s\r", *create.Name) + _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Skipping CertificateAuthority %s\r", *create.Name) continue } // do the actual create since it doesn't exist - _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Creating CertificateAuthority %s\r", *create.Name) + _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Creating CertificateAuthority %s\r", *create.Name) created, createErr := u.client.CertificateAuthority.CreateCa(&certificate_authority.CreateCaParams{Ca: create}, nil) if createErr != nil { if payloadErr, ok := createErr.(rest_util.ApiErrorPayload); ok { diff --git a/ziti/cmd/ascode/importer/import_config_types.go b/ziti/cmd/ascode/importer/importer_config_types.go similarity index 85% rename from ziti/cmd/ascode/importer/import_config_types.go rename to ziti/cmd/ascode/importer/importer_config_types.go index 6960b5964..0c905aa14 100644 --- a/ziti/cmd/ascode/importer/import_config_types.go +++ b/ziti/cmd/ascode/importer/importer_config_types.go @@ -22,8 +22,16 @@ import ( "github.com/openziti/edge-api/rest_util" "github.com/openziti/ziti/internal" "github.com/openziti/ziti/internal/rest/mgmt" + "slices" ) +func (u *Importer) IsConfigTypeImportRequired(args []string) bool { + return slices.Contains(args, "all") || len(args) == 0 || // explicit all or nothing specified + slices.Contains(args, "config-type") || + slices.Contains(args, "config") || + slices.Contains(args, "service") +} + func (u *Importer) ProcessConfigTypes(input map[string][]interface{}) (map[string]string, error) { var result = map[string]string{} @@ -40,12 +48,12 @@ func (u *Importer) ProcessConfigTypes(input map[string][]interface{}) (map[strin }). Info("Found existing ConfigType, skipping create") } - _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Skipping ConfigType %s\r", *create.Name) + _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Skipping ConfigType %s\r", *create.Name) continue } // do the actual create since it doesn't exist - _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Creating ConfigType %s\r", *create.Name) + _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Creating ConfigType %s\r", *create.Name) if u.loginOpts.Verbose { log.WithField("name", *create.Name). Debug("Creating ConfigType") diff --git a/ziti/cmd/ascode/importer/import_configs.go b/ziti/cmd/ascode/importer/importer_configs.go similarity index 89% rename from ziti/cmd/ascode/importer/import_configs.go rename to ziti/cmd/ascode/importer/importer_configs.go index a3c25f48f..ce9e95c0a 100644 --- a/ziti/cmd/ascode/importer/import_configs.go +++ b/ziti/cmd/ascode/importer/importer_configs.go @@ -26,8 +26,15 @@ import ( "github.com/openziti/ziti/internal" "github.com/openziti/ziti/internal/ascode" "github.com/openziti/ziti/internal/rest/mgmt" + "slices" ) +func (u *Importer) IsConfigImportRequired(args []string) bool { + return slices.Contains(args, "all") || len(args) == 0 || // explicit all or nothing specified + slices.Contains(args, "config") || + slices.Contains(args, "service") +} + func (u *Importer) ProcessConfigs(input map[string][]interface{}) (map[string]string, error) { var result = map[string]string{} @@ -45,7 +52,7 @@ func (u *Importer) ProcessConfigs(input map[string][]interface{}) (map[string]st }). Info("Found existing Config, skipping create") } - _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Skipping Config %s\r", *create.Name) + _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Skipping Config %s\r", *create.Name) continue } @@ -68,7 +75,7 @@ func (u *Importer) ProcessConfigs(input map[string][]interface{}) (map[string]st create.ConfigTypeID = configType.(*rest_model.ConfigTypeDetail).ID // do the actual create since it doesn't exist - _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Creating Config %s\r", *create.Name) + _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Creating Config %s\r", *create.Name) if u.loginOpts.Verbose { log.WithField("name", *create.Name).Debug("Creating Config") } diff --git a/ziti/cmd/ascode/importer/import_edgerouter_policies.go b/ziti/cmd/ascode/importer/importer_edgerouter_policies.go similarity index 89% rename from ziti/cmd/ascode/importer/import_edgerouter_policies.go rename to ziti/cmd/ascode/importer/importer_edgerouter_policies.go index a8504f7f1..485b53eff 100644 --- a/ziti/cmd/ascode/importer/import_edgerouter_policies.go +++ b/ziti/cmd/ascode/importer/importer_edgerouter_policies.go @@ -22,8 +22,14 @@ import ( "github.com/openziti/edge-api/rest_util" "github.com/openziti/ziti/internal" "github.com/openziti/ziti/internal/rest/mgmt" + "slices" ) +func (u *Importer) IsEdgeRouterPolicyImportRequired(args []string) bool { + return slices.Contains(args, "all") || len(args) == 0 || // explicit all or nothing specified + slices.Contains(args, "edge-router-policy") +} + func (u *Importer) ProcessEdgeRouterPolicies(input map[string][]interface{}) (map[string]string, error) { var result = map[string]string{} @@ -38,7 +44,7 @@ func (u *Importer) ProcessEdgeRouterPolicies(input map[string][]interface{}) (ma "edgeRouterPolicyId": *existing.ID, }). Info("Found existing EdgeRouterPolicy, skipping create") - _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Skipping EdgeRouterPolicy %s\r", *create.Name) + _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Skipping EdgeRouterPolicy %s\r", *create.Name) continue } @@ -57,7 +63,7 @@ func (u *Importer) ProcessEdgeRouterPolicies(input map[string][]interface{}) (ma create.IdentityRoles = identityRoles // do the actual create since it doesn't exist - _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Creating EdgeRouterPolicy %s\r", *create.Name) + _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Creating EdgeRouterPolicy %s\r", *create.Name) if u.loginOpts.Verbose { log.WithField("name", *create.Name).Debug("Creating EdgeRouterPolicy") } diff --git a/ziti/cmd/ascode/importer/import_edgerouters.go b/ziti/cmd/ascode/importer/importer_edgerouters.go similarity index 89% rename from ziti/cmd/ascode/importer/import_edgerouters.go rename to ziti/cmd/ascode/importer/importer_edgerouters.go index 8ef22e058..e01e814c8 100644 --- a/ziti/cmd/ascode/importer/import_edgerouters.go +++ b/ziti/cmd/ascode/importer/importer_edgerouters.go @@ -24,8 +24,15 @@ import ( "github.com/openziti/ziti/internal" "github.com/openziti/ziti/internal/ascode" "github.com/openziti/ziti/internal/rest/mgmt" + "slices" ) +func (u *Importer) IsEdgeRouterImportRequired(args []string) bool { + return slices.Contains(args, "all") || len(args) == 0 || // explicit all or nothing specified + slices.Contains(args, "edge-router") || + slices.Contains(args, "er") +} + func (u *Importer) ProcessEdgeRouters(input map[string][]interface{}) (map[string]string, error) { var result = map[string]string{} @@ -40,12 +47,12 @@ func (u *Importer) ProcessEdgeRouters(input map[string][]interface{}) (map[strin "edgeRouterId": *existing.ID, }). Info("Found existing EdgeRouter, skipping create") - _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Skipping EdgeRouter %s\r", *create.Name) + _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Skipping EdgeRouter %s\r", *create.Name) continue } // do the actual create since it doesn't exist - _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Creating EdgeRouterPolicy %s\r", *create.Name) + _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Creating EdgeRouterPolicy %s\r", *create.Name) if u.loginOpts.Verbose { log.WithField("name", *create.Name).Debug("Creating EdgeRouter") } diff --git a/ziti/cmd/ascode/importer/import_external_jwt_signers.go b/ziti/cmd/ascode/importer/importer_external_jwt_signers.go similarity index 84% rename from ziti/cmd/ascode/importer/import_external_jwt_signers.go rename to ziti/cmd/ascode/importer/importer_external_jwt_signers.go index 209b5e48c..848347235 100644 --- a/ziti/cmd/ascode/importer/import_external_jwt_signers.go +++ b/ziti/cmd/ascode/importer/importer_external_jwt_signers.go @@ -22,8 +22,17 @@ import ( "github.com/openziti/edge-api/rest_util" "github.com/openziti/ziti/internal" "github.com/openziti/ziti/internal/rest/mgmt" + "slices" ) +func (u *Importer) IsExtJwtSignerImportRequired(args []string) bool { + return slices.Contains(args, "all") || len(args) == 0 || // explicit all or nothing specified + slices.Contains(args, "ext-jwt-signer") || + slices.Contains(args, "external-jwt-signer") || + slices.Contains(args, "auth-policy") || + slices.Contains(args, "identity") +} + func (u *Importer) ProcessExternalJwtSigners(input map[string][]interface{}) (map[string]string, error) { var result = map[string]string{} @@ -40,12 +49,12 @@ func (u *Importer) ProcessExternalJwtSigners(input map[string][]interface{}) (ma }). Info("Found existing ExtJWTSigner, skipping create") } - _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Skipping ExtJWTSigner %s\r", *create.Name) + _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Skipping ExtJWTSigner %s\r", *create.Name) continue } // do the actual create since it doesn't exist - _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Creating ExtJWTSigner %s\r", *create.Name) + _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Creating ExtJWTSigner %s\r", *create.Name) if u.loginOpts.Verbose { log.WithField("name", *create.Name).Debug("Creating ExtJWTSigner") } diff --git a/ziti/cmd/ascode/importer/import_identities.go b/ziti/cmd/ascode/importer/importer_identities.go similarity index 92% rename from ziti/cmd/ascode/importer/import_identities.go rename to ziti/cmd/ascode/importer/importer_identities.go index a8690665d..0ea27fa2b 100644 --- a/ziti/cmd/ascode/importer/import_identities.go +++ b/ziti/cmd/ascode/importer/importer_identities.go @@ -26,8 +26,14 @@ import ( "github.com/openziti/ziti/internal" "github.com/openziti/ziti/internal/ascode" "github.com/openziti/ziti/internal/rest/mgmt" + "slices" ) +func (u *Importer) IsIdentityImportRequired(args []string) bool { + return slices.Contains(args, "all") || len(args) == 0 || // explicit all or nothing specified + slices.Contains(args, "identity") +} + func (u *Importer) ProcessIdentities(input map[string][]interface{}) (map[string]string, error) { var result = map[string]string{} @@ -44,7 +50,7 @@ func (u *Importer) ProcessIdentities(input map[string][]interface{}) (map[string }). Info("Found existing Identity, skipping create") } - _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Skipping Identity %s\r", *create.Name) + _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Skipping Identity %s\r", *create.Name) continue } @@ -73,7 +79,7 @@ func (u *Importer) ProcessIdentities(input map[string][]interface{}) (map[string } // do the actual create since it doesn't exist - _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Creating Identity %s\r", *create.Name) + _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Creating Identity %s\r", *create.Name) created, createErr := u.client.Identity.CreateIdentity(&identity.CreateIdentityParams{Identity: create}, nil) if createErr != nil { if payloadErr, ok := createErr.(rest_util.ApiErrorPayload); ok { diff --git a/ziti/cmd/ascode/importer/import_posture_check.go b/ziti/cmd/ascode/importer/importer_posture_check.go similarity index 85% rename from ziti/cmd/ascode/importer/import_posture_check.go rename to ziti/cmd/ascode/importer/importer_posture_check.go index 3a1bf04bf..20e35c71f 100644 --- a/ziti/cmd/ascode/importer/import_posture_check.go +++ b/ziti/cmd/ascode/importer/importer_posture_check.go @@ -24,9 +24,15 @@ import ( "github.com/openziti/edge-api/rest_util" "github.com/openziti/ziti/internal" "github.com/openziti/ziti/internal/rest/mgmt" + "slices" "strings" ) +func (u *Importer) IsPostureCheckImportRequired(args []string) bool { + return slices.Contains(args, "all") || len(args) == 0 || // explicit all or nothing specified + slices.Contains(args, "posture-check") +} + func (u *Importer) ProcessPostureChecks(input map[string][]interface{}) (map[string]string, error) { var result = map[string]string{} @@ -43,17 +49,17 @@ func (u *Importer) ProcessPostureChecks(input map[string][]interface{}) (map[str var create rest_model.PostureCheckCreate switch strings.ToUpper(typeValue) { - case "DOMAIN": + case string(rest_model.PostureCheckTypeDOMAIN): create = FromMap(data, rest_model.PostureCheckDomainCreate{}) - case "MAC": + case string(rest_model.PostureCheckTypeMAC): create = FromMap(data, rest_model.PostureCheckMacAddressCreate{}) - case "MFA": + case string(rest_model.PostureCheckTypeMFA): create = FromMap(data, rest_model.PostureCheckMfaCreate{}) - case "OS": + case string(rest_model.PostureCheckTypeOS): create = FromMap(data, rest_model.PostureCheckOperatingSystemCreate{}) - case "PROCESS": + case string(rest_model.PostureCheckTypePROCESS): create = FromMap(data, rest_model.PostureCheckProcessCreate{}) - case "PROCESS-MULTI": + case string(rest_model.PostureCheckTypePROCESSMULTI): create = FromMap(data, rest_model.PostureCheckProcessMultiCreate{}) default: log.WithFields(map[string]interface{}{ @@ -74,12 +80,12 @@ func (u *Importer) ProcessPostureChecks(input map[string][]interface{}) (map[str }). Info("Found existing PostureCheck, skipping create") } - _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Skipping PostureCheck %s\r", *create.Name()) + _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Skipping PostureCheck %s\r", *create.Name()) continue } // do the actual create since it doesn't exist - _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Creating PostureCheck %s\r", *create.Name()) + _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Creating PostureCheck %s\r", *create.Name()) if u.loginOpts.Verbose { log.WithFields(map[string]interface{}{ "name": *create.Name(), diff --git a/ziti/cmd/ascode/importer/import_service_edgerouter_policies.go b/ziti/cmd/ascode/importer/importer_service_edgerouter_policies.go similarity index 89% rename from ziti/cmd/ascode/importer/import_service_edgerouter_policies.go rename to ziti/cmd/ascode/importer/importer_service_edgerouter_policies.go index 58f837841..c85afb659 100644 --- a/ziti/cmd/ascode/importer/import_service_edgerouter_policies.go +++ b/ziti/cmd/ascode/importer/importer_service_edgerouter_policies.go @@ -22,8 +22,14 @@ import ( "github.com/openziti/edge-api/rest_util" "github.com/openziti/ziti/internal" "github.com/openziti/ziti/internal/rest/mgmt" + "slices" ) +func (u *Importer) IsServiceEdgeRouterPolicyImportRequired(args []string) bool { + return slices.Contains(args, "all") || len(args) == 0 || // explicit all or nothing specified + slices.Contains(args, "service-edge-router-policy") +} + func (u *Importer) ProcessServiceEdgeRouterPolicies(input map[string][]interface{}) (map[string]string, error) { var result = map[string]string{} @@ -38,7 +44,7 @@ func (u *Importer) ProcessServiceEdgeRouterPolicies(input map[string][]interface "serviceRouterPolicyId": *existing.ID, }). Info("Found existing ServiceEdgeRouterPolicy, skipping create") - _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Skipping ServiceEdgeRouterPolicy %s\r", *create.Name) + _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Skipping ServiceEdgeRouterPolicy %s\r", *create.Name) continue } @@ -57,7 +63,7 @@ func (u *Importer) ProcessServiceEdgeRouterPolicies(input map[string][]interface create.EdgeRouterRoles = edgeRouterRoles // do the actual create since it doesn't exist - _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Creating ServiceEdgeRouterPolicy %s\r", *create.Name) + _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Creating ServiceEdgeRouterPolicy %s\r", *create.Name) if u.loginOpts.Verbose { log.WithField("name", *create.Name). Debug("Creating ServiceEdgeRouterPolicy") diff --git a/ziti/cmd/ascode/importer/import_service_policies.go b/ziti/cmd/ascode/importer/importer_service_policies.go similarity index 89% rename from ziti/cmd/ascode/importer/import_service_policies.go rename to ziti/cmd/ascode/importer/importer_service_policies.go index 47af5ce39..e97db09a7 100644 --- a/ziti/cmd/ascode/importer/import_service_policies.go +++ b/ziti/cmd/ascode/importer/importer_service_policies.go @@ -23,8 +23,14 @@ import ( "github.com/openziti/edge-api/rest_util" "github.com/openziti/ziti/internal" "github.com/openziti/ziti/internal/rest/mgmt" + "slices" ) +func (u *Importer) IsServicePolicyImportRequired(args []string) bool { + return slices.Contains(args, "all") || len(args) == 0 || // explicit all or nothing specified + slices.Contains(args, "service-policy") +} + func (u *Importer) ProcessServicePolicies(input map[string][]interface{}) (map[string]string, error) { var result = map[string]string{} @@ -39,7 +45,7 @@ func (u *Importer) ProcessServicePolicies(input map[string][]interface{}) (map[s "servicePolicyId": *existing.ID, }). Info("Found existing ServicePolicy, skipping create") - _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Skipping ServicePolicy %s\r", *create.Name) + _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Skipping ServicePolicy %s\r", *create.Name) continue } @@ -58,7 +64,7 @@ func (u *Importer) ProcessServicePolicies(input map[string][]interface{}) (map[s create.IdentityRoles = identityRoles // do the actual create since it doesn't exist - _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Skipping ServicePolicy %s\r", *create.Name) + _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Skipping ServicePolicy %s\r", *create.Name) if u.loginOpts.Verbose { log.WithField("name", *create.Name).Debug("Creating ServicePolicy") } diff --git a/ziti/cmd/ascode/importer/import_services.go b/ziti/cmd/ascode/importer/importer_services.go similarity index 92% rename from ziti/cmd/ascode/importer/import_services.go rename to ziti/cmd/ascode/importer/importer_services.go index 7f1b76c25..b1596b3a7 100644 --- a/ziti/cmd/ascode/importer/import_services.go +++ b/ziti/cmd/ascode/importer/importer_services.go @@ -26,8 +26,14 @@ import ( "github.com/openziti/ziti/internal" "github.com/openziti/ziti/internal/ascode" "github.com/openziti/ziti/internal/rest/mgmt" + "slices" ) +func (u *Importer) IsServiceImportRequired(args []string) bool { + return slices.Contains(args, "all") || len(args) == 0 || // explicit all or nothing specified + slices.Contains(args, "service") +} + func (u *Importer) ProcessServices(input map[string][]interface{}) (map[string]string, error) { var result = map[string]string{} @@ -43,7 +49,7 @@ func (u *Importer) ProcessServices(input map[string][]interface{}) (map[string]s "serviceId": *existing.ID, }). Info("Found existing Service, skipping create") - _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Skipping Service %s\r", *create.Name) + _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Skipping Service %s\r", *create.Name) continue } @@ -71,7 +77,7 @@ func (u *Importer) ProcessServices(input map[string][]interface{}) (map[string]s create.Configs = configIds // do the actual create since it doesn't exist - _, _ = internal.FPrintFReusingLine(u.loginOpts.Err, "Creating Service %s\r", *create.Name) + _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Creating Service %s\r", *create.Name) if u.loginOpts.Verbose { log.WithField("name", *create.Name).Debug("Creating Service") } diff --git a/ziti/cmd/ascode/importer/importer_test.go b/ziti/cmd/ascode/importer/importer_test.go new file mode 100644 index 000000000..173d95a3a --- /dev/null +++ b/ziti/cmd/ascode/importer/importer_test.go @@ -0,0 +1,223 @@ +package importer + +import ( + "github.com/stretchr/testify/assert" + "testing" +) + +func Test_InputArgs(t *testing.T) { + + importer := Importer{} + + t.Run("service import", func(t *testing.T) { + + assert.True(t, importer.IsCertificateAuthorityImportRequired([]string{"certificate-authority"}), "should be imported") + assert.True(t, importer.IsCertificateAuthorityImportRequired([]string{"all"}), "should be imported") + assert.True(t, importer.IsCertificateAuthorityImportRequired([]string{}), "should be imported") + + assert.False(t, importer.IsCertificateAuthorityImportRequired([]string{"service"}), "should not be imported") + assert.False(t, importer.IsCertificateAuthorityImportRequired([]string{"config"}), "should not be imported") + assert.False(t, importer.IsCertificateAuthorityImportRequired([]string{"config-type"}), "should not be imported") + assert.False(t, importer.IsCertificateAuthorityImportRequired([]string{"identity"}), "should not be imported") + assert.False(t, importer.IsCertificateAuthorityImportRequired([]string{"auth-policy"}), "should not be imported") + assert.False(t, importer.IsCertificateAuthorityImportRequired([]string{"ext-jwt-signer"}), "should not be imported") + assert.False(t, importer.IsCertificateAuthorityImportRequired([]string{"posture-check"}), "should not be imported") + assert.False(t, importer.IsCertificateAuthorityImportRequired([]string{"service-policy"}), "should not be imported") + assert.False(t, importer.IsCertificateAuthorityImportRequired([]string{"edge-router-policy"}), "should not be imported") + assert.False(t, importer.IsCertificateAuthorityImportRequired([]string{"service-edge-router-policy"}), "should not be imported") + + }) + + t.Run("service import", func(t *testing.T) { + + assert.True(t, importer.IsServiceImportRequired([]string{"service"}), "should be imported") + assert.True(t, importer.IsServiceImportRequired([]string{"all"}), "should be imported") + assert.True(t, importer.IsServiceImportRequired([]string{}), "should be imported") + + assert.False(t, importer.IsServiceImportRequired([]string{"config"}), "should not be imported") + assert.False(t, importer.IsServiceImportRequired([]string{"config-type"}), "should not be imported") + assert.False(t, importer.IsServiceImportRequired([]string{"identity"}), "should not be imported") + assert.False(t, importer.IsServiceImportRequired([]string{"auth-policy"}), "should not be imported") + assert.False(t, importer.IsServiceImportRequired([]string{"ext-jwt-signer"}), "should not be imported") + assert.False(t, importer.IsServiceImportRequired([]string{"posture-check"}), "should not be imported") + assert.False(t, importer.IsServiceImportRequired([]string{"service-policy"}), "should not be imported") + assert.False(t, importer.IsServiceImportRequired([]string{"edge-router-policy"}), "should not be imported") + assert.False(t, importer.IsServiceImportRequired([]string{"service-edge-router-policy"}), "should not be imported") + + }) + + t.Run("config import", func(t *testing.T) { + + assert.True(t, importer.IsConfigImportRequired([]string{"service"}), "should be imported") + assert.True(t, importer.IsConfigImportRequired([]string{"config"}), "should be imported") + assert.True(t, importer.IsConfigImportRequired([]string{"all"}), "should be imported") + assert.True(t, importer.IsConfigImportRequired([]string{}), "should be imported") + + assert.False(t, importer.IsConfigImportRequired([]string{"config-type"}), "should not be imported") + assert.False(t, importer.IsConfigImportRequired([]string{"identity"}), "should not be imported") + assert.False(t, importer.IsConfigImportRequired([]string{"certificate-authority"}), "should not be imported") + assert.False(t, importer.IsConfigImportRequired([]string{"auth-policy"}), "should not be imported") + assert.False(t, importer.IsConfigImportRequired([]string{"ext-jwt-signer"}), "should not be imported") + assert.False(t, importer.IsConfigImportRequired([]string{"posture-check"}), "should not be imported") + assert.False(t, importer.IsConfigImportRequired([]string{"service-policy"}), "should not be imported") + assert.False(t, importer.IsConfigImportRequired([]string{"edge-router-policy"}), "should not be imported") + assert.False(t, importer.IsConfigImportRequired([]string{"service-edge-router-policy"}), "should not be imported") + + }) + + t.Run("config-type import", func(t *testing.T) { + + assert.True(t, importer.IsConfigTypeImportRequired([]string{"service"}), "should be imported") + assert.True(t, importer.IsConfigTypeImportRequired([]string{"config"}), "should be imported") + assert.True(t, importer.IsConfigTypeImportRequired([]string{"config-type"}), "should be imported") + assert.True(t, importer.IsConfigTypeImportRequired([]string{"all"}), "should be imported") + assert.True(t, importer.IsConfigTypeImportRequired([]string{}), "should be imported") + + assert.False(t, importer.IsConfigTypeImportRequired([]string{"certificate-authority"}), "should not be imported") + assert.False(t, importer.IsConfigTypeImportRequired([]string{"identity"}), "should not be imported") + assert.False(t, importer.IsConfigTypeImportRequired([]string{"auth-policy"}), "should not be imported") + assert.False(t, importer.IsConfigTypeImportRequired([]string{"ext-jwt-signer"}), "should not be imported") + assert.False(t, importer.IsConfigTypeImportRequired([]string{"posture-check"}), "should not be imported") + assert.False(t, importer.IsConfigTypeImportRequired([]string{"service-policy"}), "should not be imported") + assert.False(t, importer.IsConfigTypeImportRequired([]string{"edge-router-policy"}), "should not be imported") + assert.False(t, importer.IsConfigTypeImportRequired([]string{"service-edge-router-policy"}), "should not be imported") + + }) + + t.Run("identity import", func(t *testing.T) { + + assert.True(t, importer.IsIdentityImportRequired([]string{"identity"}), "should be imported") + assert.True(t, importer.IsIdentityImportRequired([]string{"all"}), "should be imported") + assert.True(t, importer.IsIdentityImportRequired([]string{}), "should be imported") + + assert.False(t, importer.IsIdentityImportRequired([]string{"auth-policy"}), "should not be imported") + assert.False(t, importer.IsIdentityImportRequired([]string{"ext-jwt-signer"}), "should not be imported") + assert.False(t, importer.IsIdentityImportRequired([]string{"external-jwt-signer"}), "should not be imported") + assert.False(t, importer.IsIdentityImportRequired([]string{"certificate-authority"}), "should not be imported") + assert.False(t, importer.IsIdentityImportRequired([]string{"service"}), "should not be imported") + assert.False(t, importer.IsIdentityImportRequired([]string{"config"}), "should not be imported") + assert.False(t, importer.IsIdentityImportRequired([]string{"config-type"}), "should not be imported") + assert.False(t, importer.IsIdentityImportRequired([]string{"posture-check"}), "should not be imported") + assert.False(t, importer.IsIdentityImportRequired([]string{"service-policy"}), "should not be imported") + assert.False(t, importer.IsIdentityImportRequired([]string{"edge-router-policy"}), "should not be imported") + assert.False(t, importer.IsIdentityImportRequired([]string{"service-edge-router-policy"}), "should not be imported") + + }) + + t.Run("auth-policy import", func(t *testing.T) { + + assert.True(t, importer.IsAuthPolicyImportRequired([]string{"auth-policy"}), "should be imported") + assert.True(t, importer.IsAuthPolicyImportRequired([]string{"identity"}), "should be imported") + assert.True(t, importer.IsAuthPolicyImportRequired([]string{"all"}), "should be imported") + assert.True(t, importer.IsAuthPolicyImportRequired([]string{}), "should be imported") + + assert.False(t, importer.IsAuthPolicyImportRequired([]string{"ext-jwt-signer"}), "should not be imported") + assert.False(t, importer.IsAuthPolicyImportRequired([]string{"external-jwt-signer"}), "should not be imported") + assert.False(t, importer.IsAuthPolicyImportRequired([]string{"certificate-authority"}), "should not be imported") + assert.False(t, importer.IsAuthPolicyImportRequired([]string{"service"}), "should not be imported") + assert.False(t, importer.IsAuthPolicyImportRequired([]string{"config"}), "should not be imported") + assert.False(t, importer.IsAuthPolicyImportRequired([]string{"config-type"}), "should not be imported") + assert.False(t, importer.IsAuthPolicyImportRequired([]string{"posture-check"}), "should not be imported") + assert.False(t, importer.IsAuthPolicyImportRequired([]string{"service-policy"}), "should not be imported") + assert.False(t, importer.IsAuthPolicyImportRequired([]string{"edge-router-policy"}), "should not be imported") + assert.False(t, importer.IsAuthPolicyImportRequired([]string{"service-edge-router-policy"}), "should not be imported") + + }) + + t.Run("ext-jwt-signer import", func(t *testing.T) { + + assert.True(t, importer.IsExtJwtSignerImportRequired([]string{"ext-jwt-signer"}), "should be imported") + assert.True(t, importer.IsExtJwtSignerImportRequired([]string{"external-jwt-signer"}), "should be imported") + assert.True(t, importer.IsExtJwtSignerImportRequired([]string{"auth-policy"}), "should be imported") + assert.True(t, importer.IsExtJwtSignerImportRequired([]string{"identity"}), "should be imported") + assert.True(t, importer.IsExtJwtSignerImportRequired([]string{"all"}), "should be imported") + assert.True(t, importer.IsExtJwtSignerImportRequired([]string{}), "should be imported") + + assert.False(t, importer.IsExtJwtSignerImportRequired([]string{"certificate-authority"}), "should not be imported") + assert.False(t, importer.IsExtJwtSignerImportRequired([]string{"service"}), "should not be imported") + assert.False(t, importer.IsExtJwtSignerImportRequired([]string{"config"}), "should not be imported") + assert.False(t, importer.IsExtJwtSignerImportRequired([]string{"config-type"}), "should not be imported") + assert.False(t, importer.IsExtJwtSignerImportRequired([]string{"posture-check"}), "should not be imported") + assert.False(t, importer.IsExtJwtSignerImportRequired([]string{"service-policy"}), "should not be imported") + assert.False(t, importer.IsExtJwtSignerImportRequired([]string{"edge-router-policy"}), "should not be imported") + assert.False(t, importer.IsExtJwtSignerImportRequired([]string{"service-edge-router-policy"}), "should not be imported") + + }) + + t.Run("posture-check import", func(t *testing.T) { + + assert.True(t, importer.IsPostureCheckImportRequired([]string{"posture-check"}), "should be imported") + assert.True(t, importer.IsPostureCheckImportRequired([]string{"all"}), "should be imported") + assert.True(t, importer.IsPostureCheckImportRequired([]string{}), "should be imported") + + assert.False(t, importer.IsPostureCheckImportRequired([]string{"service"}), "should not be imported") + assert.False(t, importer.IsPostureCheckImportRequired([]string{"config"}), "should not be imported") + assert.False(t, importer.IsPostureCheckImportRequired([]string{"config-type"}), "should not be imported") + assert.False(t, importer.IsPostureCheckImportRequired([]string{"identity"}), "should not be imported") + assert.False(t, importer.IsPostureCheckImportRequired([]string{"auth-policy"}), "should not be imported") + assert.False(t, importer.IsPostureCheckImportRequired([]string{"ext-jwt-signer"}), "should not be imported") + assert.False(t, importer.IsPostureCheckImportRequired([]string{"external-jwt-signer"}), "should not be imported") + assert.False(t, importer.IsPostureCheckImportRequired([]string{"service-policy"}), "should not be imported") + assert.False(t, importer.IsPostureCheckImportRequired([]string{"service-edge-router-policy"}), "should not be imported") + assert.False(t, importer.IsPostureCheckImportRequired([]string{"edge-router-policy"}), "should not be imported") + + }) + + t.Run("service-policy import", func(t *testing.T) { + + assert.True(t, importer.IsServicePolicyImportRequired([]string{"service-policy"}), "should be imported") + assert.True(t, importer.IsServicePolicyImportRequired([]string{"all"}), "should be imported") + assert.True(t, importer.IsServicePolicyImportRequired([]string{}), "should be imported") + + assert.False(t, importer.IsServicePolicyImportRequired([]string{"service"}), "should not be imported") + assert.False(t, importer.IsServicePolicyImportRequired([]string{"config"}), "should not be imported") + assert.False(t, importer.IsServicePolicyImportRequired([]string{"config-type"}), "should not be imported") + assert.False(t, importer.IsServicePolicyImportRequired([]string{"identity"}), "should not be imported") + assert.False(t, importer.IsServicePolicyImportRequired([]string{"auth-policy"}), "should not be imported") + assert.False(t, importer.IsServicePolicyImportRequired([]string{"ext-jwt-signer"}), "should not be imported") + assert.False(t, importer.IsServicePolicyImportRequired([]string{"external-jwt-signer"}), "should not be imported") + assert.False(t, importer.IsServicePolicyImportRequired([]string{"posture-check"}), "should not be imported") + assert.False(t, importer.IsServicePolicyImportRequired([]string{"service-edge-router-policy"}), "should not be imported") + assert.False(t, importer.IsServicePolicyImportRequired([]string{"edge-router-policy"}), "should not be imported") + + }) + + t.Run("service-edge-router-policy import", func(t *testing.T) { + + assert.True(t, importer.IsServiceEdgeRouterPolicyImportRequired([]string{"service-edge-router-policy"}), "should be imported") + assert.True(t, importer.IsServiceEdgeRouterPolicyImportRequired([]string{"all"}), "should be imported") + assert.True(t, importer.IsServiceEdgeRouterPolicyImportRequired([]string{}), "should be imported") + + assert.False(t, importer.IsServiceEdgeRouterPolicyImportRequired([]string{"service"}), "should not be imported") + assert.False(t, importer.IsServiceEdgeRouterPolicyImportRequired([]string{"config"}), "should not be imported") + assert.False(t, importer.IsServiceEdgeRouterPolicyImportRequired([]string{"config-type"}), "should not be imported") + assert.False(t, importer.IsServiceEdgeRouterPolicyImportRequired([]string{"identity"}), "should not be imported") + assert.False(t, importer.IsServiceEdgeRouterPolicyImportRequired([]string{"auth-policy"}), "should not be imported") + assert.False(t, importer.IsServiceEdgeRouterPolicyImportRequired([]string{"ext-jwt-signer"}), "should not be imported") + assert.False(t, importer.IsServiceEdgeRouterPolicyImportRequired([]string{"external-jwt-signer"}), "should not be imported") + assert.False(t, importer.IsServiceEdgeRouterPolicyImportRequired([]string{"posture-check"}), "should not be imported") + assert.False(t, importer.IsServiceEdgeRouterPolicyImportRequired([]string{"service-policy"}), "should not be imported") + assert.False(t, importer.IsServiceEdgeRouterPolicyImportRequired([]string{"edge-router-policy"}), "should not be imported") + + }) + + t.Run("service-edge-router-policy import", func(t *testing.T) { + + assert.True(t, importer.IsEdgeRouterPolicyImportRequired([]string{"edge-router-policy"}), "should be imported") + assert.True(t, importer.IsEdgeRouterPolicyImportRequired([]string{"all"}), "should be imported") + assert.True(t, importer.IsEdgeRouterPolicyImportRequired([]string{}), "should be imported") + + assert.False(t, importer.IsEdgeRouterPolicyImportRequired([]string{"service"}), "should not be imported") + assert.False(t, importer.IsEdgeRouterPolicyImportRequired([]string{"config"}), "should not be imported") + assert.False(t, importer.IsEdgeRouterPolicyImportRequired([]string{"config-type"}), "should not be imported") + assert.False(t, importer.IsEdgeRouterPolicyImportRequired([]string{"identity"}), "should not be imported") + assert.False(t, importer.IsEdgeRouterPolicyImportRequired([]string{"auth-policy"}), "should not be imported") + assert.False(t, importer.IsEdgeRouterPolicyImportRequired([]string{"ext-jwt-signer"}), "should not be imported") + assert.False(t, importer.IsEdgeRouterPolicyImportRequired([]string{"external-jwt-signer"}), "should not be imported") + assert.False(t, importer.IsEdgeRouterPolicyImportRequired([]string{"posture-check"}), "should not be imported") + assert.False(t, importer.IsEdgeRouterPolicyImportRequired([]string{"service-policy"}), "should not be imported") + assert.False(t, importer.IsEdgeRouterPolicyImportRequired([]string{"service-edge-router-policy"}), "should not be imported") + + }) + +} From b9fd8dbf338bd70c3526def90b34509b5144e40b Mon Sep 17 00:00:00 2001 From: Jens Alm Date: Wed, 8 Jan 2025 16:02:52 -0500 Subject: [PATCH 14/16] Fixed conflict in go.sum --- zititest/go.sum | 5 ----- 1 file changed, 5 deletions(-) diff --git a/zititest/go.sum b/zititest/go.sum index a0316a101..de734c142 100644 --- a/zititest/go.sum +++ b/zititest/go.sum @@ -246,12 +246,7 @@ github.com/go-openapi/swag v0.23.0 h1:vsEVJDUo2hPJ2tu0/Xc+4noaxyEffXNIs3cOULZ+Gr github.com/go-openapi/swag v0.23.0/go.mod h1:esZ8ITTYEsH1V2trKHjAN8Ai7xHb8RV+YSZ577vPjgQ= github.com/go-openapi/validate v0.24.0 h1:LdfDKwNbpB6Vn40xhTdNZAnfLECL81w+VX3BumrGD58= github.com/go-openapi/validate v0.24.0/go.mod h1:iyeX1sEufmv3nPbBdX3ieNviWnOZaJ1+zquzJEf2BAQ= -<<<<<<< HEAD -github.com/go-resty/resty/v2 v2.16.0 h1:qpKalHWI2bpp9BIKlyT8TYWEJXOk1NuKbfiT3RRnzWc= -github.com/go-resty/resty/v2 v2.16.0/go.mod h1:0fHAoK7JoBy/Ch36N8VFeMsK7xQOHhvWaC3iOktwmIU= -======= github.com/go-resty/resty/v2 v2.16.2 h1:CpRqTjIzq/rweXUt9+GxzzQdlkqMdt8Lm/fuK/CAbAg= ->>>>>>> main github.com/go-resty/resty/v2 v2.16.2/go.mod h1:0fHAoK7JoBy/Ch36N8VFeMsK7xQOHhvWaC3iOktwmIU= github.com/go-stack/stack v1.8.0/go.mod h1:v0f6uXyyMGvRgIKkXu+yp6POWl0qKG85gN/melR3HDY= github.com/godbus/dbus/v5 v5.0.4/go.mod h1:xhWf0FNVPg57R7Z0UbKHbJfkEywrmjJnf7w5xrFpKfA= From c1915d253fa2f38a5342db8b05dd405fb8079663 Mon Sep 17 00:00:00 2001 From: Jens Alm Date: Wed, 8 Jan 2025 16:36:30 -0500 Subject: [PATCH 15/16] Fixed conflict in go.sum --- zititest/go.sum | 5 ----- 1 file changed, 5 deletions(-) diff --git a/zititest/go.sum b/zititest/go.sum index de734c142..307412d5d 100644 --- a/zititest/go.sum +++ b/zititest/go.sum @@ -415,12 +415,7 @@ github.com/influxdata/influxdb1-client v0.0.0-20191209144304-8bf82d3c094d h1:/WZ github.com/influxdata/influxdb1-client v0.0.0-20191209144304-8bf82d3c094d/go.mod h1:qj24IKcXYK6Iy9ceXlo3Tc+vtHo9lIhSX5JddghvEPo= github.com/influxdata/line-protocol v0.0.0-20200327222509-2487e7298839 h1:W9WBk7wlPfJLvMCdtV4zPulc4uCPrlywQOmbFOhgQNU= github.com/influxdata/line-protocol v0.0.0-20200327222509-2487e7298839/go.mod h1:xaLFMmpvUxqXtVkUJfg9QmT88cDaCJ3ZKgdZ78oO8Qo= -<<<<<<< HEAD -github.com/jedib0t/go-pretty/v6 v6.6.1 h1:iJ65Xjb680rHcikRj6DSIbzCex2huitmc7bDtxYVWyc= -github.com/jedib0t/go-pretty/v6 v6.6.1/go.mod h1:zbn98qrYlh95FIhwwsbIip0LYpwSG8SUOScs+v9/t0E= -======= github.com/jedib0t/go-pretty/v6 v6.6.2 h1:27bLj3nRODzaiA7tPIxy9UVWHoPspFfME9XxgwiiNsM= ->>>>>>> main github.com/jedib0t/go-pretty/v6 v6.6.2/go.mod h1:zbn98qrYlh95FIhwwsbIip0LYpwSG8SUOScs+v9/t0E= github.com/jellevandenhooff/dkim v0.0.0-20150330215556-f50fe3d243e1/go.mod h1:E0B/fFc00Y+Rasa88328GlI/XbtyysCtTHZS8h7IrBU= github.com/jeremija/gosubmit v0.2.7 h1:At0OhGCFGPXyjPYAsCchoBUhE099pcBXmsb4iZqROIc= From fd7c8b74a6cc60f45a209d97c57f2a5db2a59d62 Mon Sep 17 00:00:00 2001 From: Jens Alm Date: Wed, 8 Jan 2025 16:46:13 -0500 Subject: [PATCH 16/16] Fixed lint issue and general cleanup. --- ziti/cmd/ascode/exporter/exporter.go | 108 ++++++++-------- .../ascode/exporter/exporter_auth_policies.go | 30 ++--- .../exporter_certificate_authorities.go | 14 +-- .../ascode/exporter/exporter_config_types.go | 14 +-- ziti/cmd/ascode/exporter/exporter_configs.go | 18 +-- .../exporter/exporter_edgerouter_policies.go | 14 +-- .../ascode/exporter/exporter_edgerouters.go | 16 +-- .../exporter/exporter_external_jwt_signers.go | 14 +-- .../ascode/exporter/exporter_identities.go | 20 +-- .../exporter/exporter_posture_checks.go | 14 +-- .../exporter_service_edgerouter_policies.go | 14 +-- .../exporter/exporter_service_policies.go | 14 +-- ziti/cmd/ascode/exporter/exporter_services.go | 20 +-- ziti/cmd/ascode/importer/importer.go | 119 +++++++++--------- .../ascode/importer/importer_auth_policies.go | 24 ++-- .../importer_certificate_authorities.go | 16 +-- .../ascode/importer/importer_config_types.go | 18 +-- ziti/cmd/ascode/importer/importer_configs.go | 24 ++-- .../importer/importer_edgerouter_policies.go | 20 +-- .../ascode/importer/importer_edgerouters.go | 22 ++-- .../importer/importer_external_jwt_signers.go | 18 +-- .../ascode/importer/importer_identities.go | 26 ++-- .../ascode/importer/importer_posture_check.go | 18 +-- .../importer_service_edgerouter_policies.go | 20 +-- .../importer/importer_service_policies.go | 20 +-- ziti/cmd/ascode/importer/importer_services.go | 26 ++-- 26 files changed, 340 insertions(+), 341 deletions(-) diff --git a/ziti/cmd/ascode/exporter/exporter.go b/ziti/cmd/ascode/exporter/exporter.go index 7d0fb7979..8ac66c229 100644 --- a/ziti/cmd/ascode/exporter/exporter.go +++ b/ziti/cmd/ascode/exporter/exporter.go @@ -54,8 +54,8 @@ var output Output func NewExportCmd(out io.Writer, errOut io.Writer) *cobra.Command { - d := &Exporter{} - d.loginOpts = edge.LoginOptions{} + exporter := &Exporter{} + exporter.loginOpts = edge.LoginOptions{} cmd := &cobra.Command{ Use: "export [entity]", @@ -64,13 +64,13 @@ func NewExportCmd(out io.Writer, errOut io.Writer) *cobra.Command { "Valid entities are: [all|ca/certificate-authority|identity|edge-router|service|config|config-type|service-policy|edge-router-policy|service-edge-router-policy|external-jwt-signer|auth-policy|posture-check] (default all)", Args: cobra.MinimumNArgs(0), PersistentPreRun: func(cmd *cobra.Command, args []string) { - err := d.Init(out) + err := exporter.Init(out) if err != nil { panic(err) } }, Run: func(cmd *cobra.Command, args []string) { - err := d.Execute(args) + err := exporter.Execute(args) if err != nil { panic(err) } @@ -93,23 +93,23 @@ func NewExportCmd(out io.Writer, errOut io.Writer) *cobra.Command { v.AutomaticEnv() cmd.Flags().SetInterspersed(true) - cmd.Flags().BoolVar(&d.ofJson, "json", true, "Output in JSON") - cmd.Flags().BoolVar(&d.ofYaml, "yaml", false, "Output in YAML") + cmd.Flags().BoolVar(&exporter.ofJson, "json", true, "Output in JSON") + cmd.Flags().BoolVar(&exporter.ofYaml, "yaml", false, "Output in YAML") cmd.MarkFlagsMutuallyExclusive("json", "yaml") - cmd.Flags().StringVarP(&d.filename, "output-file", "o", "", "Write output to local file") + cmd.Flags().StringVarP(&exporter.filename, "output-file", "o", "", "Write output to local file") - edge.AddLoginFlags(cmd, &d.loginOpts) - d.loginOpts.Out = out - d.loginOpts.Err = errOut + edge.AddLoginFlags(cmd, &exporter.loginOpts) + exporter.loginOpts.Out = out + exporter.loginOpts.Err = errOut return cmd } -func (d *Exporter) Init(out io.Writer) error { +func (exporter *Exporter) Init(out io.Writer) error { logLvl := logrus.InfoLevel - if d.loginOpts.Verbose { + if exporter.loginOpts.Verbose { logLvl = logrus.DebugLevel } @@ -118,7 +118,7 @@ func (d *Exporter) Init(out io.Writer) error { client, err := mgmt.NewClient() if err != nil { - loginErr := d.loginOpts.Run() + loginErr := exporter.loginOpts.Run() if loginErr != nil { log.Fatal(err) } @@ -127,16 +127,16 @@ func (d *Exporter) Init(out io.Writer) error { log.Fatal(err) } } - d.client = client + exporter.client = client - if d.filename != "" { - o, err := NewOutputToFile(d.loginOpts.Verbose, d.ofJson, d.ofYaml, d.filename, d.loginOpts.Err) + if exporter.filename != "" { + o, err := NewOutputToFile(exporter.loginOpts.Verbose, exporter.ofJson, exporter.ofYaml, exporter.filename, exporter.loginOpts.Err) if err != nil { return err } output = *o } else { - o, err := NewOutputToWriter(d.loginOpts.Verbose, d.ofJson, d.ofYaml, out, d.loginOpts.Err) + o, err := NewOutputToWriter(exporter.loginOpts.Verbose, exporter.ofJson, exporter.ofYaml, out, exporter.loginOpts.Err) if err != nil { return err } @@ -146,109 +146,109 @@ func (d *Exporter) Init(out io.Writer) error { return nil } -func (d *Exporter) Execute(input []string) error { +func (exporter *Exporter) Execute(input []string) error { args := arrayutils.Map(input, strings.ToLower) - d.authPolicyCache = map[string]any{} - d.configCache = map[string]any{} - d.configTypeCache = map[string]any{} - d.externalJwtCache = map[string]any{} + exporter.authPolicyCache = map[string]any{} + exporter.configCache = map[string]any{} + exporter.configTypeCache = map[string]any{} + exporter.externalJwtCache = map[string]any{} result := map[string]interface{}{} - if d.IsCertificateAuthorityExportRequired(args) { + if exporter.IsCertificateAuthorityExportRequired(args) { log.Debug("Processing Certificate Authorities") - cas, err := d.GetCertificateAuthorities() + cas, err := exporter.GetCertificateAuthorities() if err != nil { return err } result["certificateAuthorities"] = cas } - if d.IsIdentityExportRequired(args) { + if exporter.IsIdentityExportRequired(args) { log.Debug("Processing Identities") - identities, err := d.GetIdentities() + identities, err := exporter.GetIdentities() if err != nil { return err } result["identities"] = identities } - if d.IsEdgeRouterExportRequired(args) { + if exporter.IsEdgeRouterExportRequired(args) { log.Debug("Processing Edge Routers") - routers, err := d.GetEdgeRouters() + routers, err := exporter.GetEdgeRouters() if err != nil { return err } result["edgeRouters"] = routers } - if d.IsServiceExportRequired(args) { + if exporter.IsServiceExportRequired(args) { log.Debug("Processing Services") - services, err := d.GetServices() + services, err := exporter.GetServices() if err != nil { return err } result["services"] = services } - if d.IsConfigExportRequired(args) { + if exporter.IsConfigExportRequired(args) { log.Debug("Processing Configs") - configs, err := d.GetConfigs() + configs, err := exporter.GetConfigs() if err != nil { return err } result["configs"] = configs } - if d.IsConfigTypeExportRequired(args) { + if exporter.IsConfigTypeExportRequired(args) { log.Debug("Processing Config Types") - configTypes, err := d.GetConfigTypes() + configTypes, err := exporter.GetConfigTypes() if err != nil { return err } result["configTypes"] = configTypes } - if d.IsServicePolicyExportRequired(args) { + if exporter.IsServicePolicyExportRequired(args) { log.Debug("Processing Service Policies") - servicePolicies, err := d.GetServicePolicies() + servicePolicies, err := exporter.GetServicePolicies() if err != nil { return err } result["servicePolicies"] = servicePolicies } - if d.IsEdgeRouterExportRequired(args) { + if exporter.IsEdgeRouterExportRequired(args) { log.Debug("Processing Edge Router Policies") - routerPolicies, err := d.GetEdgeRouterPolicies() + routerPolicies, err := exporter.GetEdgeRouterPolicies() if err != nil { return err } result["edgeRouterPolicies"] = routerPolicies } - if d.IsServiceEdgeRouterPolicyExportRequired(args) { + if exporter.IsServiceEdgeRouterPolicyExportRequired(args) { log.Debug("Processing Service Edge Router Policies") - serviceRouterPolicies, err := d.GetServiceEdgeRouterPolicies() + serviceRouterPolicies, err := exporter.GetServiceEdgeRouterPolicies() if err != nil { return err } result["serviceEdgeRouterPolicies"] = serviceRouterPolicies } - if d.IsExtJwtSignerExportRequired(args) { + if exporter.IsExtJwtSignerExportRequired(args) { log.Debug("Processing External JWT Signers") - externalJwtSigners, err := d.GetExternalJwtSigners() + externalJwtSigners, err := exporter.GetExternalJwtSigners() if err != nil { return err } result["externalJwtSigners"] = externalJwtSigners } - if d.IsAuthPolicyExportRequired(args) { + if exporter.IsAuthPolicyExportRequired(args) { log.Debug("Processing Auth Policies") - authPolicies, err := d.GetAuthPolicies() + authPolicies, err := exporter.GetAuthPolicies() if err != nil { return err } result["authPolicies"] = authPolicies } - if d.IsPostureCheckExportRequired(args) { + if exporter.IsPostureCheckExportRequired(args) { log.Debug("Processing Posture Checks") - postureChecks, err := d.GetPostureChecks() + postureChecks, err := exporter.GetPostureChecks() if err != nil { return err } @@ -261,8 +261,8 @@ func (d *Exporter) Execute(input []string) error { if err != nil { return err } - if d.file != nil { - err := d.file.Close() + if exporter.file != nil { + err := exporter.file.Close() if err != nil { return err } @@ -275,7 +275,7 @@ type ClientCount func() (int64, error) type ClientList func(offset *int64, limit *int64) ([]interface{}, error) type EntityProcessor func(item interface{}) (map[string]interface{}, error) -func (d *Exporter) getEntities(entityName string, count ClientCount, list ClientList, processor EntityProcessor) ([]map[string]interface{}, error) { +func (exporter *Exporter) getEntities(entityName string, count ClientCount, list ClientList, processor EntityProcessor) ([]map[string]interface{}, error) { totalCount, countErr := count() if countErr != nil { @@ -289,7 +289,7 @@ func (d *Exporter) getEntities(entityName string, count ClientCount, list Client more := true for more { resp, err := list(&offset, &limit) - _, _ = internal.FPrintfReusingLine(d.loginOpts.Err, "Reading %d/%d %s", offset, totalCount, entityName) + _, _ = internal.FPrintfReusingLine(exporter.loginOpts.Err, "Reading %d/%d %s", offset, totalCount, entityName) if err != nil { return nil, errors.Join(errors.New("error reading "+entityName), err) } @@ -308,13 +308,13 @@ func (d *Exporter) getEntities(entityName string, count ClientCount, list Client offset += limit } - _, _ = internal.FPrintflnReusingLine(d.loginOpts.Err, "Read %d %s", len(result), entityName) + _, _ = internal.FPrintflnReusingLine(exporter.loginOpts.Err, "Read %d %s", len(result), entityName) return result, nil } -func (d *Exporter) ToMap(input interface{}) map[string]interface{} { +func (exporter *Exporter) ToMap(input interface{}) map[string]interface{} { jsonData, _ := json.MarshalIndent(input, "", "") m := map[string]interface{}{} err := json.Unmarshal(jsonData, &m) @@ -325,13 +325,13 @@ func (d *Exporter) ToMap(input interface{}) map[string]interface{} { return m } -func (d *Exporter) defaultRoleAttributes(m map[string]interface{}) { +func (exporter *Exporter) defaultRoleAttributes(m map[string]interface{}) { if m["roleAttributes"] == nil { m["roleAttributes"] = []string{} } } -func (d *Exporter) Filter(m map[string]interface{}, properties []string) { +func (exporter *Exporter) Filter(m map[string]interface{}, properties []string) { // remove any properties that are not requested for k := range m { diff --git a/ziti/cmd/ascode/exporter/exporter_auth_policies.go b/ziti/cmd/ascode/exporter/exporter_auth_policies.go index ee658168c..e7ac040bd 100644 --- a/ziti/cmd/ascode/exporter/exporter_auth_policies.go +++ b/ziti/cmd/ascode/exporter/exporter_auth_policies.go @@ -24,18 +24,18 @@ import ( "slices" ) -func (d Exporter) IsAuthPolicyExportRequired(args []string) bool { +func (exporter Exporter) IsAuthPolicyExportRequired(args []string) bool { return slices.Contains(args, "all") || len(args) == 0 || // explicit all or nothing specified slices.Contains(args, "auth-policy") } -func (d Exporter) GetAuthPolicies() ([]map[string]interface{}, error) { +func (exporter Exporter) GetAuthPolicies() ([]map[string]interface{}, error) { - return d.getEntities( + return exporter.getEntities( "AuthPolicies", func() (int64, error) { limit := int64(1) - resp, err := d.client.AuthPolicy.ListAuthPolicies( + resp, err := exporter.client.AuthPolicy.ListAuthPolicies( &auth_policy.ListAuthPoliciesParams{Limit: &limit}, nil) if err != nil { return -1, err @@ -44,7 +44,7 @@ func (d Exporter) GetAuthPolicies() ([]map[string]interface{}, error) { }, func(offset *int64, limit *int64) ([]interface{}, error) { - resp, err := d.client.AuthPolicy.ListAuthPolicies( + resp, err := exporter.client.AuthPolicy.ListAuthPolicies( &auth_policy.ListAuthPoliciesParams{Limit: limit, Offset: offset}, nil) if err != nil { return nil, err @@ -61,25 +61,25 @@ func (d Exporter) GetAuthPolicies() ([]map[string]interface{}, error) { if *item.Name != "Default" { // convert to a map of values - m := d.ToMap(item) + m := exporter.ToMap(item) // filter unwanted properties - d.Filter(m, []string{"id", "_links", "createdAt", "updatedAt"}) + exporter.Filter(m, []string{"id", "_links", "createdAt", "updatedAt"}) // deleting Primary so we can reconstruct it delete(m, "primary") - primary := d.ToMap(item.Primary) + primary := exporter.ToMap(item.Primary) m["primary"] = primary // deleting ExtJwt so we can reconstruct it delete(primary, "extJwt") - extJwt := d.ToMap(item.Primary.ExtJWT) + extJwt := exporter.ToMap(item.Primary.ExtJWT) primary["extJwt"] = extJwt // deleting AllowedSigners because it needs to use a reference to the name instead of the ID delete(extJwt, "allowedSigners") signers := []string{} for _, signer := range item.Primary.ExtJWT.AllowedSigners { - extJwtSigner, lookupErr := ascode.GetItemFromCache(d.externalJwtCache, signer, func(id string) (interface{}, error) { - return d.client.ExternalJWTSigner.DetailExternalJWTSigner( + extJwtSigner, lookupErr := ascode.GetItemFromCache(exporter.externalJwtCache, signer, func(id string) (interface{}, error) { + return exporter.client.ExternalJWTSigner.DetailExternalJWTSigner( &external_jwt_signer.DetailExternalJWTSignerParams{ID: id}, nil) }) if lookupErr != nil { @@ -93,14 +93,14 @@ func (d Exporter) GetAuthPolicies() ([]map[string]interface{}, error) { if item.Secondary.RequireExtJWTSigner != nil { // deleting Secondary so we can reconstruct it delete(m, "secondary") - secondary := d.ToMap(item.Secondary) + secondary := exporter.ToMap(item.Secondary) m["secondary"] = secondary // deleting RequiredExtJwtSigner because it needs to use a reference to the name instead of the ID delete(secondary, "requiredExtJwtSigner") - requiredExtJwtSigner := d.ToMap(item.Secondary.RequireExtJWTSigner) - extJwtSigner, lookupErr := ascode.GetItemFromCache(d.externalJwtCache, *item.Secondary.RequireExtJWTSigner, func(id string) (interface{}, error) { - return d.client.ExternalJWTSigner.DetailExternalJWTSigner(&external_jwt_signer.DetailExternalJWTSignerParams{ID: id}, nil) + requiredExtJwtSigner := exporter.ToMap(item.Secondary.RequireExtJWTSigner) + extJwtSigner, lookupErr := ascode.GetItemFromCache(exporter.externalJwtCache, *item.Secondary.RequireExtJWTSigner, func(id string) (interface{}, error) { + return exporter.client.ExternalJWTSigner.DetailExternalJWTSigner(&external_jwt_signer.DetailExternalJWTSignerParams{ID: id}, nil) }) if lookupErr != nil { return nil, lookupErr diff --git a/ziti/cmd/ascode/exporter/exporter_certificate_authorities.go b/ziti/cmd/ascode/exporter/exporter_certificate_authorities.go index 11c63495d..d15645ea4 100644 --- a/ziti/cmd/ascode/exporter/exporter_certificate_authorities.go +++ b/ziti/cmd/ascode/exporter/exporter_certificate_authorities.go @@ -22,20 +22,20 @@ import ( "slices" ) -func (d Exporter) IsCertificateAuthorityExportRequired(args []string) bool { +func (exporter Exporter) IsCertificateAuthorityExportRequired(args []string) bool { return slices.Contains(args, "all") || len(args) == 0 || // explicit all or nothing specified slices.Contains(args, "ca") || slices.Contains(args, "certificate-authority") } -func (d Exporter) GetCertificateAuthorities() ([]map[string]interface{}, error) { +func (exporter Exporter) GetCertificateAuthorities() ([]map[string]interface{}, error) { - return d.getEntities( + return exporter.getEntities( "CertificateAuthorities", func() (int64, error) { limit := int64(1) - resp, err := d.client.CertificateAuthority.ListCas(&certificate_authority.ListCasParams{Limit: &limit}, nil) + resp, err := exporter.client.CertificateAuthority.ListCas(&certificate_authority.ListCasParams{Limit: &limit}, nil) if err != nil { return -1, err } @@ -43,7 +43,7 @@ func (d Exporter) GetCertificateAuthorities() ([]map[string]interface{}, error) }, func(offset *int64, limit *int64) ([]interface{}, error) { - resp, err := d.client.CertificateAuthority.ListCas(&certificate_authority.ListCasParams{Offset: offset, Limit: limit}, nil) + resp, err := exporter.client.CertificateAuthority.ListCas(&certificate_authority.ListCasParams{Offset: offset, Limit: limit}, nil) if err != nil { return nil, err } @@ -59,10 +59,10 @@ func (d Exporter) GetCertificateAuthorities() ([]map[string]interface{}, error) item := entity.(*rest_model.CaDetail) // convert to a map of values - m := d.ToMap(item) + m := exporter.ToMap(item) // filter unwanted properties - d.Filter(m, []string{"id", "_links", "createdAt", "updatedAt"}) + exporter.Filter(m, []string{"id", "_links", "createdAt", "updatedAt"}) return m, nil }) diff --git a/ziti/cmd/ascode/exporter/exporter_config_types.go b/ziti/cmd/ascode/exporter/exporter_config_types.go index 0dffd5556..94e6bd8f9 100644 --- a/ziti/cmd/ascode/exporter/exporter_config_types.go +++ b/ziti/cmd/ascode/exporter/exporter_config_types.go @@ -22,19 +22,19 @@ import ( "slices" ) -func (d Exporter) IsConfigTypeExportRequired(args []string) bool { +func (exporter Exporter) IsConfigTypeExportRequired(args []string) bool { return slices.Contains(args, "all") || len(args) == 0 || // explicit all or nothing specified slices.Contains(args, "config-type") } -func (d Exporter) GetConfigTypes() ([]map[string]interface{}, error) { +func (exporter Exporter) GetConfigTypes() ([]map[string]interface{}, error) { - return d.getEntities( + return exporter.getEntities( "ConfigTypes", func() (int64, error) { limit := int64(1) - resp, err := d.client.Config.ListConfigTypes(&config.ListConfigTypesParams{Limit: &limit}, nil) + resp, err := exporter.client.Config.ListConfigTypes(&config.ListConfigTypesParams{Limit: &limit}, nil) if err != nil { return -1, err } @@ -42,7 +42,7 @@ func (d Exporter) GetConfigTypes() ([]map[string]interface{}, error) { }, func(offset *int64, limit *int64) ([]interface{}, error) { - resp, _ := d.client.Config.ListConfigTypes(&config.ListConfigTypesParams{Limit: limit, Offset: offset}, nil) + resp, _ := exporter.client.Config.ListConfigTypes(&config.ListConfigTypesParams{Limit: limit, Offset: offset}, nil) entities := make([]interface{}, len(resp.GetPayload().Data)) for i, c := range resp.GetPayload().Data { entities[i] = interface{}(c) @@ -61,8 +61,8 @@ func (d Exporter) GetConfigTypes() ([]map[string]interface{}, error) { } // convert to a map of values - m := d.ToMap(item) - d.Filter(m, []string{"id", "_links", "createdAt", "updatedAt"}) + m := exporter.ToMap(item) + exporter.Filter(m, []string{"id", "_links", "createdAt", "updatedAt"}) return m, nil }) diff --git a/ziti/cmd/ascode/exporter/exporter_configs.go b/ziti/cmd/ascode/exporter/exporter_configs.go index 47e6decc8..ed2dfe0e1 100644 --- a/ziti/cmd/ascode/exporter/exporter_configs.go +++ b/ziti/cmd/ascode/exporter/exporter_configs.go @@ -24,19 +24,19 @@ import ( "slices" ) -func (d Exporter) IsConfigExportRequired(args []string) bool { +func (exporter Exporter) IsConfigExportRequired(args []string) bool { return slices.Contains(args, "all") || len(args) == 0 || // explicit all or nothing specified slices.Contains(args, "config") } -func (d Exporter) GetConfigs() ([]map[string]interface{}, error) { +func (exporter Exporter) GetConfigs() ([]map[string]interface{}, error) { - return d.getEntities( + return exporter.getEntities( "Configs", func() (int64, error) { limit := int64(1) - resp, err := d.client.Config.ListConfigs(&config.ListConfigsParams{Limit: &limit}, nil) + resp, err := exporter.client.Config.ListConfigs(&config.ListConfigsParams{Limit: &limit}, nil) if err != nil { return -1, err } @@ -44,7 +44,7 @@ func (d Exporter) GetConfigs() ([]map[string]interface{}, error) { }, func(offset *int64, limit *int64) ([]interface{}, error) { - resp, _ := d.client.Config.ListConfigs(&config.ListConfigsParams{Limit: limit, Offset: offset}, nil) + resp, _ := exporter.client.Config.ListConfigs(&config.ListConfigsParams{Limit: limit, Offset: offset}, nil) entities := make([]interface{}, len(resp.GetPayload().Data)) for i, c := range resp.GetPayload().Data { entities[i] = interface{}(c) @@ -57,16 +57,16 @@ func (d Exporter) GetConfigs() ([]map[string]interface{}, error) { item := entity.(*rest_model.ConfigDetail) // convert to a map of values - m := d.ToMap(item) + m := exporter.ToMap(item) // filter unwanted properties - d.Filter(m, []string{"id", "_links", "createdAt", "updatedAt"}) + exporter.Filter(m, []string{"id", "_links", "createdAt", "updatedAt"}) // translate ids to names delete(m, "configType") delete(m, "configTypeId") - configType, lookupErr := ascode.GetItemFromCache(d.configTypeCache, *item.ConfigTypeID, func(id string) (interface{}, error) { - return d.client.Config.DetailConfigType(&config.DetailConfigTypeParams{ID: id}, nil) + configType, lookupErr := ascode.GetItemFromCache(exporter.configTypeCache, *item.ConfigTypeID, func(id string) (interface{}, error) { + return exporter.client.Config.DetailConfigType(&config.DetailConfigTypeParams{ID: id}, nil) }) if lookupErr != nil { return nil, errors.Join(errors.New("error reading Auth Policy: "+*item.ConfigTypeID), lookupErr) diff --git a/ziti/cmd/ascode/exporter/exporter_edgerouter_policies.go b/ziti/cmd/ascode/exporter/exporter_edgerouter_policies.go index 57f9d3e03..4087082b3 100644 --- a/ziti/cmd/ascode/exporter/exporter_edgerouter_policies.go +++ b/ziti/cmd/ascode/exporter/exporter_edgerouter_policies.go @@ -22,19 +22,19 @@ import ( "slices" ) -func (d Exporter) IsEdgeRouterPolicyExportRequired(args []string) bool { +func (exporter Exporter) IsEdgeRouterPolicyExportRequired(args []string) bool { return slices.Contains(args, "all") || len(args) == 0 || // explicit all or nothing specified slices.Contains(args, "edge-router-policy") } -func (d Exporter) GetEdgeRouterPolicies() ([]map[string]interface{}, error) { +func (exporter Exporter) GetEdgeRouterPolicies() ([]map[string]interface{}, error) { - return d.getEntities( + return exporter.getEntities( "EdgeRouterPolicies", func() (int64, error) { limit := int64(1) - resp, err := d.client.EdgeRouterPolicy.ListEdgeRouterPolicies(&edge_router_policy.ListEdgeRouterPoliciesParams{Limit: &limit}, nil) + resp, err := exporter.client.EdgeRouterPolicy.ListEdgeRouterPolicies(&edge_router_policy.ListEdgeRouterPoliciesParams{Limit: &limit}, nil) if err != nil { return -1, err } @@ -42,7 +42,7 @@ func (d Exporter) GetEdgeRouterPolicies() ([]map[string]interface{}, error) { }, func(offset *int64, limit *int64) ([]interface{}, error) { - resp, err := d.client.EdgeRouterPolicy.ListEdgeRouterPolicies(&edge_router_policy.ListEdgeRouterPoliciesParams{Limit: limit, Offset: offset}, nil) + resp, err := exporter.client.EdgeRouterPolicy.ListEdgeRouterPolicies(&edge_router_policy.ListEdgeRouterPoliciesParams{Limit: limit, Offset: offset}, nil) if err != nil { return nil, err } @@ -58,7 +58,7 @@ func (d Exporter) GetEdgeRouterPolicies() ([]map[string]interface{}, error) { item := entity.(*rest_model.EdgeRouterPolicyDetail) // convert to a map of values - m := d.ToMap(item) + m := exporter.ToMap(item) // translate attributes so they don't reference ids identityRoles := []string{} @@ -73,7 +73,7 @@ func (d Exporter) GetEdgeRouterPolicies() ([]map[string]interface{}, error) { m["edgeRouterRoles"] = edgeRouterRoles // filter unwanted properties - d.Filter(m, []string{"id", "_links", "createdAt", "updatedAt", + exporter.Filter(m, []string{"id", "_links", "createdAt", "updatedAt", "edgeRouterRolesDisplay", "identityRolesDisplay", "isSystem"}) return m, nil diff --git a/ziti/cmd/ascode/exporter/exporter_edgerouters.go b/ziti/cmd/ascode/exporter/exporter_edgerouters.go index 1b0313c0c..386d80a37 100644 --- a/ziti/cmd/ascode/exporter/exporter_edgerouters.go +++ b/ziti/cmd/ascode/exporter/exporter_edgerouters.go @@ -22,19 +22,19 @@ import ( "slices" ) -func (d Exporter) IsEdgeRouterExportRequired(args []string) bool { +func (exporter Exporter) IsEdgeRouterExportRequired(args []string) bool { return slices.Contains(args, "all") || len(args) == 0 || // explicit all or nothing specified slices.Contains(args, "edge-router") || slices.Contains(args, "er") } -func (d Exporter) GetEdgeRouters() ([]map[string]interface{}, error) { +func (exporter Exporter) GetEdgeRouters() ([]map[string]interface{}, error) { - return d.getEntities( + return exporter.getEntities( "EdgeRouters", func() (int64, error) { limit := int64(1) - resp, err := d.client.EdgeRouter.ListEdgeRouters(&edge_router.ListEdgeRoutersParams{Limit: &limit}, nil) + resp, err := exporter.client.EdgeRouter.ListEdgeRouters(&edge_router.ListEdgeRoutersParams{Limit: &limit}, nil) if err != nil { return -1, err } @@ -42,7 +42,7 @@ func (d Exporter) GetEdgeRouters() ([]map[string]interface{}, error) { }, func(offset *int64, limit *int64) ([]interface{}, error) { - resp, err := d.client.EdgeRouter.ListEdgeRouters(&edge_router.ListEdgeRoutersParams{Limit: limit, Offset: offset}, nil) + resp, err := exporter.client.EdgeRouter.ListEdgeRouters(&edge_router.ListEdgeRoutersParams{Limit: limit, Offset: offset}, nil) if err != nil { return nil, err } @@ -58,11 +58,11 @@ func (d Exporter) GetEdgeRouters() ([]map[string]interface{}, error) { item := entity.(*rest_model.EdgeRouterDetail) // convert to a map of values - m := d.ToMap(item) - d.defaultRoleAttributes(m) + m := exporter.ToMap(item) + exporter.defaultRoleAttributes(m) // filter unwanted properties - d.Filter(m, []string{"id", "_links", "createdAt", "updatedAt", + exporter.Filter(m, []string{"id", "_links", "createdAt", "updatedAt", "cost", "fingerprint", "isVerified", "isOnline", "enrollmentJwt", "enrollmentCreatedAt", "enrollmentExpiresAt", "syncStatus", "versionInfo", "certPem", "supportedProtocols"}) return m, nil diff --git a/ziti/cmd/ascode/exporter/exporter_external_jwt_signers.go b/ziti/cmd/ascode/exporter/exporter_external_jwt_signers.go index 5be4eb154..3163dcfa2 100644 --- a/ziti/cmd/ascode/exporter/exporter_external_jwt_signers.go +++ b/ziti/cmd/ascode/exporter/exporter_external_jwt_signers.go @@ -22,20 +22,20 @@ import ( "slices" ) -func (d Exporter) IsExtJwtSignerExportRequired(args []string) bool { +func (exporter Exporter) IsExtJwtSignerExportRequired(args []string) bool { return slices.Contains(args, "all") || len(args) == 0 || // explicit all or nothing specified slices.Contains(args, "ext-jwt-signer") || slices.Contains(args, "external-jwt-signer") } -func (d Exporter) GetExternalJwtSigners() ([]map[string]interface{}, error) { +func (exporter Exporter) GetExternalJwtSigners() ([]map[string]interface{}, error) { - return d.getEntities( + return exporter.getEntities( "ExtJWTSigners", func() (int64, error) { limit := int64(1) - resp, err := d.client.ExternalJWTSigner.ListExternalJWTSigners(&external_jwt_signer.ListExternalJWTSignersParams{Limit: &limit}, nil) + resp, err := exporter.client.ExternalJWTSigner.ListExternalJWTSigners(&external_jwt_signer.ListExternalJWTSignersParams{Limit: &limit}, nil) if err != nil { return -1, err } @@ -43,7 +43,7 @@ func (d Exporter) GetExternalJwtSigners() ([]map[string]interface{}, error) { }, func(offset *int64, limit *int64) ([]interface{}, error) { - resp, err := d.client.ExternalJWTSigner.ListExternalJWTSigners( + resp, err := exporter.client.ExternalJWTSigner.ListExternalJWTSigners( &external_jwt_signer.ListExternalJWTSignersParams{Offset: offset, Limit: limit}, nil) if err != nil { return nil, err @@ -60,10 +60,10 @@ func (d Exporter) GetExternalJwtSigners() ([]map[string]interface{}, error) { item := entity.(*rest_model.ExternalJWTSignerDetail) // convert to a map of values - m := d.ToMap(item) + m := exporter.ToMap(item) // filter unwanted properties - d.Filter(m, []string{"id", "_links", "createdAt", "updatedAt", + exporter.Filter(m, []string{"id", "_links", "createdAt", "updatedAt", "notBefore", "notAfter", "commonName"}) return m, nil diff --git a/ziti/cmd/ascode/exporter/exporter_identities.go b/ziti/cmd/ascode/exporter/exporter_identities.go index e99451f63..3de50051f 100644 --- a/ziti/cmd/ascode/exporter/exporter_identities.go +++ b/ziti/cmd/ascode/exporter/exporter_identities.go @@ -25,19 +25,19 @@ import ( "slices" ) -func (d Exporter) IsIdentityExportRequired(args []string) bool { +func (exporter Exporter) IsIdentityExportRequired(args []string) bool { return slices.Contains(args, "all") || len(args) == 0 || // explicit all or nothing specified slices.Contains(args, "identity") } -func (d Exporter) GetIdentities() ([]map[string]interface{}, error) { +func (exporter Exporter) GetIdentities() ([]map[string]interface{}, error) { - return d.getEntities( + return exporter.getEntities( "Identities", func() (int64, error) { limit := int64(1) - resp, err := d.client.Identity.ListIdentities(&identity.ListIdentitiesParams{Limit: &limit}, nil) + resp, err := exporter.client.Identity.ListIdentities(&identity.ListIdentitiesParams{Limit: &limit}, nil) if err != nil { return -1, err } @@ -45,7 +45,7 @@ func (d Exporter) GetIdentities() ([]map[string]interface{}, error) { }, func(offset *int64, limit *int64) ([]interface{}, error) { - resp, err := d.client.Identity.ListIdentities(&identity.ListIdentitiesParams{Offset: offset, Limit: limit}, nil) + resp, err := exporter.client.Identity.ListIdentities(&identity.ListIdentitiesParams{Offset: offset, Limit: limit}, nil) if err != nil { return nil, err } @@ -64,11 +64,11 @@ func (d Exporter) GetIdentities() ([]map[string]interface{}, error) { if *item.TypeID != "Router" && !*item.IsDefaultAdmin { // convert to a map of values - m := d.ToMap(item) - d.defaultRoleAttributes(m) + m := exporter.ToMap(item) + exporter.defaultRoleAttributes(m) // filter unwanted properties - d.Filter(m, []string{"id", "_links", "createdAt", "updatedAt", + exporter.Filter(m, []string{"id", "_links", "createdAt", "updatedAt", "defaultHostingCost", "defaultHostingPrecedence", "hasApiSession", "serviceHostingPrecedences", "enrollment", "appData", "sdkInfo", "disabledAt", "disabledUntil", "serviceHostingCosts", "envInfo", "authenticators", "type", "authPolicyId", "hasRouterConnection", "hasEdgeRouterConnection"}) @@ -78,8 +78,8 @@ func (d Exporter) GetIdentities() ([]map[string]interface{}, error) { } // translate ids to names - authPolicy, lookupErr := ascode.GetItemFromCache(d.authPolicyCache, *item.AuthPolicyID, func(id string) (interface{}, error) { - return d.client.AuthPolicy.DetailAuthPolicy(&auth_policy.DetailAuthPolicyParams{ID: id}, nil) + authPolicy, lookupErr := ascode.GetItemFromCache(exporter.authPolicyCache, *item.AuthPolicyID, func(id string) (interface{}, error) { + return exporter.client.AuthPolicy.DetailAuthPolicy(&auth_policy.DetailAuthPolicyParams{ID: id}, nil) }) if lookupErr != nil { return nil, errors.Join(errors.New("error reading Auth Policy: "+*item.AuthPolicyID), lookupErr) diff --git a/ziti/cmd/ascode/exporter/exporter_posture_checks.go b/ziti/cmd/ascode/exporter/exporter_posture_checks.go index c96c9cf4d..ebf2f8c0f 100644 --- a/ziti/cmd/ascode/exporter/exporter_posture_checks.go +++ b/ziti/cmd/ascode/exporter/exporter_posture_checks.go @@ -21,19 +21,19 @@ import ( "golang.org/x/exp/slices" ) -func (d Exporter) IsPostureCheckExportRequired(args []string) bool { +func (exporter Exporter) IsPostureCheckExportRequired(args []string) bool { return slices.Contains(args, "all") || len(args) == 0 || // explicit all or nothing specified slices.Contains(args, "posture-check") } -func (d Exporter) GetPostureChecks() ([]map[string]interface{}, error) { +func (exporter Exporter) GetPostureChecks() ([]map[string]interface{}, error) { - return d.getEntities( + return exporter.getEntities( "PostureChecks", func() (int64, error) { limit := int64(1) - resp, err := d.client.PostureChecks.ListPostureChecks(&posture_checks.ListPostureChecksParams{Limit: &limit}, nil) + resp, err := exporter.client.PostureChecks.ListPostureChecks(&posture_checks.ListPostureChecksParams{Limit: &limit}, nil) if err != nil { return -1, err } @@ -41,7 +41,7 @@ func (d Exporter) GetPostureChecks() ([]map[string]interface{}, error) { }, func(offset *int64, limit *int64) ([]interface{}, error) { - resp, _ := d.client.PostureChecks.ListPostureChecks(&posture_checks.ListPostureChecksParams{Limit: limit, Offset: offset}, nil) + resp, _ := exporter.client.PostureChecks.ListPostureChecks(&posture_checks.ListPostureChecksParams{Limit: limit, Offset: offset}, nil) entities := make([]interface{}, len(resp.GetPayload().Data())) for i, c := range resp.GetPayload().Data() { entities[i] = interface{}(c) @@ -52,10 +52,10 @@ func (d Exporter) GetPostureChecks() ([]map[string]interface{}, error) { func(entity interface{}) (map[string]interface{}, error) { // convert to a map of values - m := d.ToMap(entity) + m := exporter.ToMap(entity) // filter unwanted properties - d.Filter(m, []string{"id", "_links", "createdAt", "updatedAt", + exporter.Filter(m, []string{"id", "_links", "createdAt", "updatedAt", "version"}) return m, nil diff --git a/ziti/cmd/ascode/exporter/exporter_service_edgerouter_policies.go b/ziti/cmd/ascode/exporter/exporter_service_edgerouter_policies.go index 82e1bb014..a069a813a 100644 --- a/ziti/cmd/ascode/exporter/exporter_service_edgerouter_policies.go +++ b/ziti/cmd/ascode/exporter/exporter_service_edgerouter_policies.go @@ -22,19 +22,19 @@ import ( "slices" ) -func (d Exporter) IsServiceEdgeRouterPolicyExportRequired(args []string) bool { +func (exporter Exporter) IsServiceEdgeRouterPolicyExportRequired(args []string) bool { return slices.Contains(args, "all") || len(args) == 0 || // explicit all or nothing specified slices.Contains(args, "service-edge-router-policy") } -func (d Exporter) GetServiceEdgeRouterPolicies() ([]map[string]interface{}, error) { +func (exporter Exporter) GetServiceEdgeRouterPolicies() ([]map[string]interface{}, error) { - return d.getEntities( + return exporter.getEntities( "ServiceEdgeRouterPolicies", func() (int64, error) { limit := int64(1) - resp, err := d.client.ServiceEdgeRouterPolicy.ListServiceEdgeRouterPolicies(&service_edge_router_policy.ListServiceEdgeRouterPoliciesParams{Limit: &limit}, nil) + resp, err := exporter.client.ServiceEdgeRouterPolicy.ListServiceEdgeRouterPolicies(&service_edge_router_policy.ListServiceEdgeRouterPoliciesParams{Limit: &limit}, nil) if err != nil { return -1, err } @@ -42,7 +42,7 @@ func (d Exporter) GetServiceEdgeRouterPolicies() ([]map[string]interface{}, erro }, func(offset *int64, limit *int64) ([]interface{}, error) { - resp, err := d.client.ServiceEdgeRouterPolicy.ListServiceEdgeRouterPolicies(&service_edge_router_policy.ListServiceEdgeRouterPoliciesParams{Limit: limit, Offset: offset}, nil) + resp, err := exporter.client.ServiceEdgeRouterPolicy.ListServiceEdgeRouterPolicies(&service_edge_router_policy.ListServiceEdgeRouterPoliciesParams{Limit: limit, Offset: offset}, nil) if err != nil { return nil, err } @@ -58,7 +58,7 @@ func (d Exporter) GetServiceEdgeRouterPolicies() ([]map[string]interface{}, erro item := entity.(*rest_model.ServiceEdgeRouterPolicyDetail) // convert to a map of values - m := d.ToMap(item) + m := exporter.ToMap(item) // translate attributes so they don't reference ids serviceRoles := []string{} @@ -73,7 +73,7 @@ func (d Exporter) GetServiceEdgeRouterPolicies() ([]map[string]interface{}, erro m["edgeRouterRoles"] = edgeRouterRoles // filter unwanted properties - d.Filter(m, []string{"id", "_links", "createdAt", "updatedAt", + exporter.Filter(m, []string{"id", "_links", "createdAt", "updatedAt", "edgeRouterRolesDisplay", "serviceRolesDisplay", "isSystem"}) return m, nil diff --git a/ziti/cmd/ascode/exporter/exporter_service_policies.go b/ziti/cmd/ascode/exporter/exporter_service_policies.go index 723c73da7..5f39e5734 100644 --- a/ziti/cmd/ascode/exporter/exporter_service_policies.go +++ b/ziti/cmd/ascode/exporter/exporter_service_policies.go @@ -22,19 +22,19 @@ import ( "slices" ) -func (d Exporter) IsServicePolicyExportRequired(args []string) bool { +func (exporter Exporter) IsServicePolicyExportRequired(args []string) bool { return slices.Contains(args, "all") || len(args) == 0 || // explicit all or nothing specified slices.Contains(args, "service-policy") } -func (d Exporter) GetServicePolicies() ([]map[string]interface{}, error) { +func (exporter Exporter) GetServicePolicies() ([]map[string]interface{}, error) { - return d.getEntities( + return exporter.getEntities( "ServicePolicies", func() (int64, error) { limit := int64(1) - resp, err := d.client.ServicePolicy.ListServicePolicies(&service_policy.ListServicePoliciesParams{Limit: &limit}, nil) + resp, err := exporter.client.ServicePolicy.ListServicePolicies(&service_policy.ListServicePoliciesParams{Limit: &limit}, nil) if err != nil { return -1, err } @@ -42,7 +42,7 @@ func (d Exporter) GetServicePolicies() ([]map[string]interface{}, error) { }, func(offset *int64, limit *int64) ([]interface{}, error) { - resp, err := d.client.ServicePolicy.ListServicePolicies(&service_policy.ListServicePoliciesParams{Limit: limit, Offset: offset}, nil) + resp, err := exporter.client.ServicePolicy.ListServicePolicies(&service_policy.ListServicePoliciesParams{Limit: limit, Offset: offset}, nil) if err != nil { return nil, err } @@ -58,7 +58,7 @@ func (d Exporter) GetServicePolicies() ([]map[string]interface{}, error) { item := entity.(*rest_model.ServicePolicyDetail) // convert to a map of values - m := d.ToMap(item) + m := exporter.ToMap(item) // translate attributes so they don't reference ids identityRoles := []string{} @@ -78,7 +78,7 @@ func (d Exporter) GetServicePolicies() ([]map[string]interface{}, error) { m["postureCheckRoles"] = postureCheckRoles // filter unwanted properties - d.Filter(m, []string{"id", "_links", "createdAt", "updatedAt", + exporter.Filter(m, []string{"id", "_links", "createdAt", "updatedAt", "serviceRolesDisplay", "identityRolesDisplay", "postureCheckRolesDisplay", "isSystem"}) return m, nil diff --git a/ziti/cmd/ascode/exporter/exporter_services.go b/ziti/cmd/ascode/exporter/exporter_services.go index 60e39ddb0..2ccdc3804 100644 --- a/ziti/cmd/ascode/exporter/exporter_services.go +++ b/ziti/cmd/ascode/exporter/exporter_services.go @@ -25,19 +25,19 @@ import ( "slices" ) -func (d Exporter) IsServiceExportRequired(args []string) bool { +func (exporter Exporter) IsServiceExportRequired(args []string) bool { return slices.Contains(args, "all") || len(args) == 0 || // explicit all or nothing specified slices.Contains(args, "service") } -func (d Exporter) GetServices() ([]map[string]interface{}, error) { +func (exporter Exporter) GetServices() ([]map[string]interface{}, error) { - return d.getEntities( + return exporter.getEntities( "Services", func() (int64, error) { limit := int64(1) - resp, err := d.client.Service.ListServices(&service.ListServicesParams{Limit: &limit}, nil) + resp, err := exporter.client.Service.ListServices(&service.ListServicesParams{Limit: &limit}, nil) if err != nil { return -1, err } @@ -45,7 +45,7 @@ func (d Exporter) GetServices() ([]map[string]interface{}, error) { }, func(offset *int64, limit *int64) ([]interface{}, error) { - resp, err := d.client.Service.ListServices(&service.ListServicesParams{Limit: limit, Offset: offset}, nil) + resp, err := exporter.client.Service.ListServices(&service.ListServicesParams{Limit: limit, Offset: offset}, nil) if err != nil { return nil, err } @@ -61,19 +61,19 @@ func (d Exporter) GetServices() ([]map[string]interface{}, error) { item := entity.(*rest_model.ServiceDetail) // convert to a map of values - m := d.ToMap(item) + m := exporter.ToMap(item) - d.defaultRoleAttributes(m) + exporter.defaultRoleAttributes(m) // filter unwanted properties - d.Filter(m, []string{"id", "_links", "createdAt", "updatedAt", + exporter.Filter(m, []string{"id", "_links", "createdAt", "updatedAt", "configs", "config", "data", "postureQueries", "permissions", "maxIdleTimeMillis"}) // translate ids to names var configNames []string for _, c := range item.Configs { - configDetail, lookupErr := ascode.GetItemFromCache(d.configCache, c, func(id string) (interface{}, error) { - return d.client.Config.DetailConfig(&config.DetailConfigParams{ID: id}, nil) + configDetail, lookupErr := ascode.GetItemFromCache(exporter.configCache, c, func(id string) (interface{}, error) { + return exporter.client.Config.DetailConfig(&config.DetailConfigParams{ID: id}, nil) }) if lookupErr != nil { return nil, errors.Join(errors.New("error reading Config: "+c), lookupErr) diff --git a/ziti/cmd/ascode/importer/importer.go b/ziti/cmd/ascode/importer/importer.go index e8cdf49bd..64818278e 100644 --- a/ziti/cmd/ascode/importer/importer.go +++ b/ziti/cmd/ascode/importer/importer.go @@ -53,8 +53,8 @@ type Importer struct { func NewImportCmd(out io.Writer, errOut io.Writer) *cobra.Command { - u := &Importer{} - u.loginOpts = edge.LoginOptions{} + importer := &Importer{} + importer.loginOpts = edge.LoginOptions{} cmd := &cobra.Command{ Use: "import filename [entity]", @@ -63,16 +63,16 @@ func NewImportCmd(out io.Writer, errOut io.Writer) *cobra.Command { "Valid entities are: [all|ca/certificate-authority|identity|edge-router|service|config|config-type|service-policy|edge-router-policy|service-edge-router-policy|external-jwt-signer|auth-policy|posture-check] (default all)", Args: cobra.MinimumNArgs(1), PersistentPreRun: func(cmd *cobra.Command, args []string) { - u.Init() + importer.Init() }, Run: func(cmd *cobra.Command, args []string) { - data, err := u.reader.read(args[0]) + data, err := importer.reader.read(args[0]) if err != nil { panic(errors.Join(errors.New("unable to read input"), err)) } m := map[string][]interface{}{} - if u.ofYaml { + if importer.ofYaml { err = yaml.Unmarshal(data, &m) if err != nil { panic(errors.Join(errors.New("unable to parse input data as yaml"), err)) @@ -84,7 +84,7 @@ func NewImportCmd(out io.Writer, errOut io.Writer) *cobra.Command { } } - result, executeErr := u.Execute(m, args[1:]) + result, executeErr := importer.Execute(m, args[1:]) if executeErr != nil { panic(executeErr) } @@ -100,22 +100,21 @@ func NewImportCmd(out io.Writer, errOut io.Writer) *cobra.Command { v.AutomaticEnv() cmd.Flags().SetInterspersed(true) - cmd.Flags().BoolVar(&u.ofJson, "json", true, "Input parsed as JSON") - cmd.Flags().BoolVar(&u.ofYaml, "yaml", false, "Input parsed as YAML") + cmd.Flags().BoolVar(&importer.ofJson, "json", true, "Input parsed as JSON") + cmd.Flags().BoolVar(&importer.ofYaml, "yaml", false, "Input parsed as YAML") cmd.MarkFlagsMutuallyExclusive("json", "yaml") - edge.AddLoginFlags(cmd, &u.loginOpts) - u.loginOpts.Out = out - u.loginOpts.Err = errOut + edge.AddLoginFlags(cmd, &importer.loginOpts) + importer.loginOpts.Out = out + importer.loginOpts.Err = errOut return cmd } -func (u *Importer) Init() { - u.loginOpts.Verbose = u.loginOpts.Verbose +func (importer *Importer) Init() { logLvl := logrus.InfoLevel - if u.loginOpts.Verbose { + if importer.loginOpts.Verbose { logLvl = logrus.DebugLevel } @@ -124,7 +123,7 @@ func (u *Importer) Init() { client, err := mgmt.NewClient() if err != nil { - loginErr := u.loginOpts.Run() + loginErr := importer.loginOpts.Run() if loginErr != nil { log.Fatal(err) } @@ -133,28 +132,28 @@ func (u *Importer) Init() { log.Fatal(err) } } - u.client = client - u.reader = FileReader{} + importer.client = client + importer.reader = FileReader{} } -func (u *Importer) Execute(data map[string][]interface{}, inputArgs []string) (map[string]any, error) { +func (importer *Importer) Execute(data map[string][]interface{}, inputArgs []string) (map[string]any, error) { args := arrayutils.Map(inputArgs, strings.ToLower) - u.configCache = map[string]any{} - u.serviceCache = map[string]any{} - u.edgeRouterCache = map[string]any{} - u.authPolicyCache = map[string]any{} - u.extJwtSignersCache = map[string]any{} - u.identityCache = map[string]any{} + importer.configCache = map[string]any{} + importer.serviceCache = map[string]any{} + importer.edgeRouterCache = map[string]any{} + importer.authPolicyCache = map[string]any{} + importer.extJwtSignersCache = map[string]any{} + importer.identityCache = map[string]any{} result := map[string]any{} cas := map[string]string{} - if u.IsCertificateAuthorityImportRequired(args) { + if importer.IsCertificateAuthorityImportRequired(args) { log.Debug("Processing CertificateAuthorities") var err error - cas, err = u.ProcessCertificateAuthorities(data) + cas, err = importer.ProcessCertificateAuthorities(data) if err != nil { return nil, err } @@ -163,149 +162,149 @@ func (u *Importer) Execute(data map[string][]interface{}, inputArgs []string) (m Debug("CertificateAuthorities created") } result["certificateAuthorities"] = cas - _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Created %d CertificateAuthorities\r\n", len(cas)) + _, _ = internal.FPrintfReusingLine(importer.loginOpts.Err, "Created %d CertificateAuthorities\r\n", len(cas)) externalJwtSigners := map[string]string{} - if u.IsExtJwtSignerImportRequired(args) { + if importer.IsExtJwtSignerImportRequired(args) { log.Debug("Processing ExtJWTSigners") var err error - externalJwtSigners, err = u.ProcessExternalJwtSigners(data) + externalJwtSigners, err = importer.ProcessExternalJwtSigners(data) if err != nil { return nil, err } log.WithField("externalJwtSigners", externalJwtSigners).Debug("ExtJWTSigners created") } - _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Created %d ExtJWTSigners\r\n", len(externalJwtSigners)) + _, _ = internal.FPrintfReusingLine(importer.loginOpts.Err, "Created %d ExtJWTSigners\r\n", len(externalJwtSigners)) result["externalJwtSigners"] = externalJwtSigners authPolicies := map[string]string{} - if u.IsAuthPolicyImportRequired(args) { + if importer.IsAuthPolicyImportRequired(args) { log.Debug("Processing AuthPolicies") var err error - authPolicies, err = u.ProcessAuthPolicies(data) + authPolicies, err = importer.ProcessAuthPolicies(data) if err != nil { return nil, err } log.WithField("authPolicies", authPolicies).Debug("AuthPolicies created") } - _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Created %d AuthPolicies\r\n", len(authPolicies)) + _, _ = internal.FPrintfReusingLine(importer.loginOpts.Err, "Created %d AuthPolicies\r\n", len(authPolicies)) result["authPolicies"] = authPolicies identities := map[string]string{} - if u.IsIdentityImportRequired(args) { + if importer.IsIdentityImportRequired(args) { log.Debug("Processing Identities") var err error - identities, err = u.ProcessIdentities(data) + identities, err = importer.ProcessIdentities(data) if err != nil { return nil, err } log.WithField("identities", identities).Debug("Identities created") } - _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Created %d Identities\r\n", len(identities)) + _, _ = internal.FPrintfReusingLine(importer.loginOpts.Err, "Created %d Identities\r\n", len(identities)) result["identities"] = identities configTypes := map[string]string{} - if u.IsConfigTypeImportRequired(args) { + if importer.IsConfigTypeImportRequired(args) { log.Debug("Processing ConfigTypes") var err error - configTypes, err = u.ProcessConfigTypes(data) + configTypes, err = importer.ProcessConfigTypes(data) if err != nil { return nil, err } log.WithField("configTypes", configTypes).Debug("ConfigTypes created") } - _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Created %d ConfigTypes\r\n", len(configTypes)) + _, _ = internal.FPrintfReusingLine(importer.loginOpts.Err, "Created %d ConfigTypes\r\n", len(configTypes)) result["configTypes"] = configTypes configs := map[string]string{} - if u.IsConfigImportRequired(args) { + if importer.IsConfigImportRequired(args) { log.Debug("Processing Configs") var err error - configs, err = u.ProcessConfigs(data) + configs, err = importer.ProcessConfigs(data) if err != nil { return nil, err } log.WithField("configs", configs).Debug("Configs created") } - _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Created %d Configs\r\n", len(configs)) + _, _ = internal.FPrintfReusingLine(importer.loginOpts.Err, "Created %d Configs\r\n", len(configs)) result["configs"] = configs services := map[string]string{} - if u.IsServiceImportRequired(args) { + if importer.IsServiceImportRequired(args) { log.Debug("Processing Services") var err error - services, err = u.ProcessServices(data) + services, err = importer.ProcessServices(data) if err != nil { return nil, err } log.WithField("services", services).Debug("Services created") } - _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Created %d Services\r\n", len(services)) + _, _ = internal.FPrintfReusingLine(importer.loginOpts.Err, "Created %d Services\r\n", len(services)) result["services"] = services postureChecks := map[string]string{} - if u.IsPostureCheckImportRequired(args) { + if importer.IsPostureCheckImportRequired(args) { log.Debug("Processing PostureChecks") var err error - postureChecks, err = u.ProcessPostureChecks(data) + postureChecks, err = importer.ProcessPostureChecks(data) if err != nil { return nil, err } log.WithField("postureChecks", postureChecks).Debug("PostureChecks created") } - _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Created %d PostureChecks\r\n", len(postureChecks)) + _, _ = internal.FPrintfReusingLine(importer.loginOpts.Err, "Created %d PostureChecks\r\n", len(postureChecks)) result["postureChecks"] = postureChecks routers := map[string]string{} - if u.IsEdgeRouterImportRequired(args) { + if importer.IsEdgeRouterImportRequired(args) { log.Debug("Processing EdgeRouters") var err error - routers, err = u.ProcessEdgeRouters(data) + routers, err = importer.ProcessEdgeRouters(data) if err != nil { return nil, err } log.WithField("edgeRouters", routers).Debug("EdgeRouters created") } - _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Created %d EdgeRouters\r\n", len(routers)) + _, _ = internal.FPrintfReusingLine(importer.loginOpts.Err, "Created %d EdgeRouters\r\n", len(routers)) result["edgeRouters"] = routers serviceEdgeRouterPolicies := map[string]string{} - if u.IsServiceEdgeRouterPolicyImportRequired(args) { + if importer.IsServiceEdgeRouterPolicyImportRequired(args) { log.Debug("Processing ServiceEdgeRouterPolicies") var err error - serviceEdgeRouterPolicies, err = u.ProcessServiceEdgeRouterPolicies(data) + serviceEdgeRouterPolicies, err = importer.ProcessServiceEdgeRouterPolicies(data) if err != nil { return nil, err } log.WithField("serviceEdgeRouterPolicies", serviceEdgeRouterPolicies).Debug("ServiceEdgeRouterPolicies created") } - _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Created %d ServiceEdgeRouterPolicies\r\n", len(serviceEdgeRouterPolicies)) + _, _ = internal.FPrintfReusingLine(importer.loginOpts.Err, "Created %d ServiceEdgeRouterPolicies\r\n", len(serviceEdgeRouterPolicies)) result["serviceEdgeRouterPolicies"] = serviceEdgeRouterPolicies servicePolicies := map[string]string{} - if u.IsServicePolicyImportRequired(args) { + if importer.IsServicePolicyImportRequired(args) { log.Debug("Processing ServicePolicies") var err error - servicePolicies, err = u.ProcessServicePolicies(data) + servicePolicies, err = importer.ProcessServicePolicies(data) if err != nil { return nil, err } log.WithField("servicePolicies", servicePolicies).Debug("ServicePolicies created") } - _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Created %d ServicePolicies\r\n", len(servicePolicies)) + _, _ = internal.FPrintfReusingLine(importer.loginOpts.Err, "Created %d ServicePolicies\r\n", len(servicePolicies)) result["servicePolicies"] = servicePolicies routerPolicies := map[string]string{} - if u.IsEdgeRouterPolicyImportRequired(args) { + if importer.IsEdgeRouterPolicyImportRequired(args) { log.Debug("Processing EdgeRouterPolicies") var err error - routerPolicies, err = u.ProcessEdgeRouterPolicies(data) + routerPolicies, err = importer.ProcessEdgeRouterPolicies(data) if err != nil { return nil, err } log.WithField("routerPolicies", routerPolicies).Debug("EdgeRouterPolicies created") } - _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Created %d EdgeRouterPolicies\r\n", len(routerPolicies)) + _, _ = internal.FPrintfReusingLine(importer.loginOpts.Err, "Created %d EdgeRouterPolicies\r\n", len(routerPolicies)) result["edgeRouterPolicies"] = routerPolicies log.Info("Upload complete") diff --git a/ziti/cmd/ascode/importer/importer_auth_policies.go b/ziti/cmd/ascode/importer/importer_auth_policies.go index e1aa2e4d7..b1faab7ef 100644 --- a/ziti/cmd/ascode/importer/importer_auth_policies.go +++ b/ziti/cmd/ascode/importer/importer_auth_policies.go @@ -28,15 +28,15 @@ import ( "slices" ) -func (u *Importer) IsAuthPolicyImportRequired(args []string) bool { +func (importer *Importer) IsAuthPolicyImportRequired(args []string) bool { return slices.Contains(args, "all") || len(args) == 0 || // explicit all or nothing specified slices.Contains(args, "auth-policy") || slices.Contains(args, "identity") } -func (u *Importer) ProcessAuthPolicies(input map[string][]interface{}) (map[string]string, error) { +func (importer *Importer) ProcessAuthPolicies(input map[string][]interface{}) (map[string]string, error) { - if u.loginOpts.Verbose { + if importer.loginOpts.Verbose { log.Debug("Listing all AuthPolicies") } @@ -46,15 +46,15 @@ func (u *Importer) ProcessAuthPolicies(input map[string][]interface{}) (map[stri create := FromMap(data, rest_model.AuthPolicyCreate{}) // see if the auth policy already exists - existing := mgmt.AuthPolicyFromFilter(u.client, mgmt.NameFilter(*create.Name)) + existing := mgmt.AuthPolicyFromFilter(importer.client, mgmt.NameFilter(*create.Name)) if existing != nil { - if u.loginOpts.Verbose { + if importer.loginOpts.Verbose { log.WithFields(map[string]interface{}{ "name": *create.Name, "authPolicyId": *existing.ID, }).Info("Found existing Auth Policy, skipping create") } - _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Skipping AuthPolicy %s\r", *create.Name) + _, _ = internal.FPrintfReusingLine(importer.loginOpts.Err, "Skipping AuthPolicy %s\r", *create.Name) continue } @@ -71,8 +71,8 @@ func (u *Importer) ProcessAuthPolicies(input map[string][]interface{}) (map[stri allowedSignerIds := []string{} for _, signer := range allowedSigners.Children() { value := signer.Data().(string)[1:] - extJwtSigner, err := ascode.GetItemFromCache(u.extJwtSignersCache, value, func(name string) (interface{}, error) { - return mgmt.ExternalJWTSignerFromFilter(u.client, mgmt.NameFilter(name)), nil + extJwtSigner, err := ascode.GetItemFromCache(importer.extJwtSignersCache, value, func(name string) (interface{}, error) { + return mgmt.ExternalJWTSignerFromFilter(importer.client, mgmt.NameFilter(name)), nil }) if err != nil { log.WithField("name", *create.Name).Warn("Unable to read ExtJwtSigner") @@ -83,12 +83,12 @@ func (u *Importer) ProcessAuthPolicies(input map[string][]interface{}) (map[stri create.Primary.ExtJWT.AllowedSigners = allowedSignerIds // do the actual create since it doesn't exist - _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Creating AuthPolicy %s\r", *create.Name) - if u.loginOpts.Verbose { + _, _ = internal.FPrintfReusingLine(importer.loginOpts.Err, "Creating AuthPolicy %s\r", *create.Name) + if importer.loginOpts.Verbose { log.WithField("name", *create.Name). Debug("Creating AuthPolicy") } - created, createErr := u.client.AuthPolicy.CreateAuthPolicy(&auth_policy.CreateAuthPolicyParams{AuthPolicy: create}, nil) + created, createErr := importer.client.AuthPolicy.CreateAuthPolicy(&auth_policy.CreateAuthPolicyParams{AuthPolicy: create}, nil) if createErr != nil { if payloadErr, ok := createErr.(rest_util.ApiErrorPayload); ok { log.WithFields(map[string]interface{}{ @@ -103,7 +103,7 @@ func (u *Importer) ProcessAuthPolicies(input map[string][]interface{}) (map[stri } } - if u.loginOpts.Verbose { + if importer.loginOpts.Verbose { log.WithFields(map[string]interface{}{ "name": *create.Name, "authPolicyId": created.Payload.Data.ID, diff --git a/ziti/cmd/ascode/importer/importer_certificate_authorities.go b/ziti/cmd/ascode/importer/importer_certificate_authorities.go index 9c22b9354..5a9e46746 100644 --- a/ziti/cmd/ascode/importer/importer_certificate_authorities.go +++ b/ziti/cmd/ascode/importer/importer_certificate_authorities.go @@ -25,35 +25,35 @@ import ( "slices" ) -func (u *Importer) IsCertificateAuthorityImportRequired(args []string) bool { +func (importer *Importer) IsCertificateAuthorityImportRequired(args []string) bool { return slices.Contains(args, "all") || len(args) == 0 || // explicit all or nothing specified slices.Contains(args, "ca") || slices.Contains(args, "certificate-authority") } -func (u *Importer) ProcessCertificateAuthorities(input map[string][]interface{}) (map[string]string, error) { +func (importer *Importer) ProcessCertificateAuthorities(input map[string][]interface{}) (map[string]string, error) { var result = map[string]string{} for _, data := range input["certificateAuthorities"] { create := FromMap(data, rest_model.CaCreate{}) // see if the CA already exists - existing := mgmt.CertificateAuthorityFromFilter(u.client, mgmt.NameFilter(*create.Name)) + existing := mgmt.CertificateAuthorityFromFilter(importer.client, mgmt.NameFilter(*create.Name)) if existing != nil { - if u.loginOpts.Verbose { + if importer.loginOpts.Verbose { log.WithFields(map[string]interface{}{ "name": *create.Name, "certificateAuthorityId": *existing.ID, }). Info("Found existing CertificateAuthority, skipping create") } - _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Skipping CertificateAuthority %s\r", *create.Name) + _, _ = internal.FPrintfReusingLine(importer.loginOpts.Err, "Skipping CertificateAuthority %s\r", *create.Name) continue } // do the actual create since it doesn't exist - _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Creating CertificateAuthority %s\r", *create.Name) - created, createErr := u.client.CertificateAuthority.CreateCa(&certificate_authority.CreateCaParams{Ca: create}, nil) + _, _ = internal.FPrintfReusingLine(importer.loginOpts.Err, "Creating CertificateAuthority %s\r", *create.Name) + created, createErr := importer.client.CertificateAuthority.CreateCa(&certificate_authority.CreateCaParams{Ca: create}, nil) if createErr != nil { if payloadErr, ok := createErr.(rest_util.ApiErrorPayload); ok { log. @@ -69,7 +69,7 @@ func (u *Importer) ProcessCertificateAuthorities(input map[string][]interface{}) return nil, createErr } } - if u.loginOpts.Verbose { + if importer.loginOpts.Verbose { log.WithFields(map[string]interface{}{ "name": *create.Name, "certificateAuthorityId": created.Payload.Data.ID, diff --git a/ziti/cmd/ascode/importer/importer_config_types.go b/ziti/cmd/ascode/importer/importer_config_types.go index 0c905aa14..0c76d4c0f 100644 --- a/ziti/cmd/ascode/importer/importer_config_types.go +++ b/ziti/cmd/ascode/importer/importer_config_types.go @@ -25,40 +25,40 @@ import ( "slices" ) -func (u *Importer) IsConfigTypeImportRequired(args []string) bool { +func (importer *Importer) IsConfigTypeImportRequired(args []string) bool { return slices.Contains(args, "all") || len(args) == 0 || // explicit all or nothing specified slices.Contains(args, "config-type") || slices.Contains(args, "config") || slices.Contains(args, "service") } -func (u *Importer) ProcessConfigTypes(input map[string][]interface{}) (map[string]string, error) { +func (importer *Importer) ProcessConfigTypes(input map[string][]interface{}) (map[string]string, error) { var result = map[string]string{} for _, data := range input["configTypes"] { create := FromMap(data, rest_model.ConfigTypeCreate{}) // see if the config type already exists - existing := mgmt.ConfigTypeFromFilter(u.client, mgmt.NameFilter(*create.Name)) + existing := mgmt.ConfigTypeFromFilter(importer.client, mgmt.NameFilter(*create.Name)) if existing != nil { - if u.loginOpts.Verbose { + if importer.loginOpts.Verbose { log.WithFields(map[string]interface{}{ "name": *create.Name, "configTypeId": *existing.ID, }). Info("Found existing ConfigType, skipping create") } - _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Skipping ConfigType %s\r", *create.Name) + _, _ = internal.FPrintfReusingLine(importer.loginOpts.Err, "Skipping ConfigType %s\r", *create.Name) continue } // do the actual create since it doesn't exist - _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Creating ConfigType %s\r", *create.Name) - if u.loginOpts.Verbose { + _, _ = internal.FPrintfReusingLine(importer.loginOpts.Err, "Creating ConfigType %s\r", *create.Name) + if importer.loginOpts.Verbose { log.WithField("name", *create.Name). Debug("Creating ConfigType") } - created, createErr := u.client.Config.CreateConfigType(&config.CreateConfigTypeParams{ConfigType: create}, nil) + created, createErr := importer.client.Config.CreateConfigType(&config.CreateConfigTypeParams{ConfigType: create}, nil) if createErr != nil { if payloadErr, ok := createErr.(rest_util.ApiErrorPayload); ok { log.WithFields(map[string]interface{}{ @@ -73,7 +73,7 @@ func (u *Importer) ProcessConfigTypes(input map[string][]interface{}) (map[strin return nil, createErr } - if u.loginOpts.Verbose { + if importer.loginOpts.Verbose { log.WithFields(map[string]interface{}{ "name": *create.Name, "configTypeId": created.Payload.Data.ID, diff --git a/ziti/cmd/ascode/importer/importer_configs.go b/ziti/cmd/ascode/importer/importer_configs.go index ce9e95c0a..69f391d98 100644 --- a/ziti/cmd/ascode/importer/importer_configs.go +++ b/ziti/cmd/ascode/importer/importer_configs.go @@ -29,22 +29,22 @@ import ( "slices" ) -func (u *Importer) IsConfigImportRequired(args []string) bool { +func (importer *Importer) IsConfigImportRequired(args []string) bool { return slices.Contains(args, "all") || len(args) == 0 || // explicit all or nothing specified slices.Contains(args, "config") || slices.Contains(args, "service") } -func (u *Importer) ProcessConfigs(input map[string][]interface{}) (map[string]string, error) { +func (importer *Importer) ProcessConfigs(input map[string][]interface{}) (map[string]string, error) { var result = map[string]string{} for _, data := range input["configs"] { create := FromMap(data, rest_model.ConfigCreate{}) // see if the config already exists - existing := mgmt.ConfigFromFilter(u.client, mgmt.NameFilter(*create.Name)) + existing := mgmt.ConfigFromFilter(importer.client, mgmt.NameFilter(*create.Name)) if existing != nil { - if u.loginOpts.Verbose { + if importer.loginOpts.Verbose { log. WithFields(map[string]interface{}{ "name": *create.Name, @@ -52,7 +52,7 @@ func (u *Importer) ProcessConfigs(input map[string][]interface{}) (map[string]st }). Info("Found existing Config, skipping create") } - _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Skipping Config %s\r", *create.Name) + _, _ = internal.FPrintfReusingLine(importer.loginOpts.Err, "Skipping Config %s\r", *create.Name) continue } @@ -66,20 +66,20 @@ func (u *Importer) ProcessConfigs(input map[string][]interface{}) (map[string]st // look up the config type id from the name and add to the create value := doc.Path("configType").Data().(string)[1:] - configType, _ := ascode.GetItemFromCache(u.configCache, value, func(name string) (interface{}, error) { - return mgmt.ConfigTypeFromFilter(u.client, mgmt.NameFilter(name)), nil + configType, _ := ascode.GetItemFromCache(importer.configCache, value, func(name string) (interface{}, error) { + return mgmt.ConfigTypeFromFilter(importer.client, mgmt.NameFilter(name)), nil }) - if u.configCache == nil { + if importer.configCache == nil { return nil, errors.New("error reading ConfigType: " + value) } create.ConfigTypeID = configType.(*rest_model.ConfigTypeDetail).ID // do the actual create since it doesn't exist - _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Creating Config %s\r", *create.Name) - if u.loginOpts.Verbose { + _, _ = internal.FPrintfReusingLine(importer.loginOpts.Err, "Creating Config %s\r", *create.Name) + if importer.loginOpts.Verbose { log.WithField("name", *create.Name).Debug("Creating Config") } - created, createErr := u.client.Config.CreateConfig(&config.CreateConfigParams{Config: create}, nil) + created, createErr := importer.client.Config.CreateConfig(&config.CreateConfigParams{Config: create}, nil) if createErr != nil { if payloadErr, ok := createErr.(rest_util.ApiErrorPayload); ok { log.WithFields(map[string]interface{}{ @@ -92,7 +92,7 @@ func (u *Importer) ProcessConfigs(input map[string][]interface{}) (map[string]st return nil, createErr } } - if u.loginOpts.Verbose { + if importer.loginOpts.Verbose { log.WithFields(map[string]interface{}{ "name": *create.Name, "configId": created.Payload.Data.ID, diff --git a/ziti/cmd/ascode/importer/importer_edgerouter_policies.go b/ziti/cmd/ascode/importer/importer_edgerouter_policies.go index 485b53eff..e0d63ee26 100644 --- a/ziti/cmd/ascode/importer/importer_edgerouter_policies.go +++ b/ziti/cmd/ascode/importer/importer_edgerouter_policies.go @@ -25,49 +25,49 @@ import ( "slices" ) -func (u *Importer) IsEdgeRouterPolicyImportRequired(args []string) bool { +func (importer *Importer) IsEdgeRouterPolicyImportRequired(args []string) bool { return slices.Contains(args, "all") || len(args) == 0 || // explicit all or nothing specified slices.Contains(args, "edge-router-policy") } -func (u *Importer) ProcessEdgeRouterPolicies(input map[string][]interface{}) (map[string]string, error) { +func (importer *Importer) ProcessEdgeRouterPolicies(input map[string][]interface{}) (map[string]string, error) { var result = map[string]string{} for _, data := range input["edgeRouterPolicies"] { create := FromMap(data, rest_model.EdgeRouterPolicyCreate{}) // see if the router already exists - existing := mgmt.EdgeRouterPolicyFromFilter(u.client, mgmt.NameFilter(*create.Name)) + existing := mgmt.EdgeRouterPolicyFromFilter(importer.client, mgmt.NameFilter(*create.Name)) if existing != nil { log.WithFields(map[string]interface{}{ "name": *create.Name, "edgeRouterPolicyId": *existing.ID, }). Info("Found existing EdgeRouterPolicy, skipping create") - _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Skipping EdgeRouterPolicy %s\r", *create.Name) + _, _ = internal.FPrintfReusingLine(importer.loginOpts.Err, "Skipping EdgeRouterPolicy %s\r", *create.Name) continue } // look up the edgeRouter ids from the name and add to the create - edgeRouterRoles, err := u.lookupEdgeRouters(create.EdgeRouterRoles) + edgeRouterRoles, err := importer.lookupEdgeRouters(create.EdgeRouterRoles) if err != nil { return nil, err } create.EdgeRouterRoles = edgeRouterRoles // look up the identity ids from the name and add to the create - identityRoles, err := u.lookupIdentities(create.IdentityRoles) + identityRoles, err := importer.lookupIdentities(create.IdentityRoles) if err != nil { return nil, err } create.IdentityRoles = identityRoles // do the actual create since it doesn't exist - _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Creating EdgeRouterPolicy %s\r", *create.Name) - if u.loginOpts.Verbose { + _, _ = internal.FPrintfReusingLine(importer.loginOpts.Err, "Creating EdgeRouterPolicy %s\r", *create.Name) + if importer.loginOpts.Verbose { log.WithField("name", *create.Name).Debug("Creating EdgeRouterPolicy") } - created, createErr := u.client.EdgeRouterPolicy.CreateEdgeRouterPolicy(&edge_router_policy.CreateEdgeRouterPolicyParams{Policy: create}, nil) + created, createErr := importer.client.EdgeRouterPolicy.CreateEdgeRouterPolicy(&edge_router_policy.CreateEdgeRouterPolicyParams{Policy: create}, nil) if createErr != nil { if payloadErr, ok := createErr.(rest_util.ApiErrorPayload); ok { log.WithFields(map[string]interface{}{ @@ -81,7 +81,7 @@ func (u *Importer) ProcessEdgeRouterPolicies(input map[string][]interface{}) (ma return nil, createErr } } - if u.loginOpts.Verbose { + if importer.loginOpts.Verbose { log.WithFields(map[string]interface{}{ "name": *create.Name, "routerPolicyId": created.Payload.Data.ID, diff --git a/ziti/cmd/ascode/importer/importer_edgerouters.go b/ziti/cmd/ascode/importer/importer_edgerouters.go index e01e814c8..36ec78301 100644 --- a/ziti/cmd/ascode/importer/importer_edgerouters.go +++ b/ziti/cmd/ascode/importer/importer_edgerouters.go @@ -27,36 +27,36 @@ import ( "slices" ) -func (u *Importer) IsEdgeRouterImportRequired(args []string) bool { +func (importer *Importer) IsEdgeRouterImportRequired(args []string) bool { return slices.Contains(args, "all") || len(args) == 0 || // explicit all or nothing specified slices.Contains(args, "edge-router") || slices.Contains(args, "er") } -func (u *Importer) ProcessEdgeRouters(input map[string][]interface{}) (map[string]string, error) { +func (importer *Importer) ProcessEdgeRouters(input map[string][]interface{}) (map[string]string, error) { var result = map[string]string{} for _, data := range input["edgeRouters"] { create := FromMap(data, rest_model.EdgeRouterCreate{}) // see if the router already exists - existing := mgmt.EdgeRouterFromFilter(u.client, mgmt.NameFilter(*create.Name)) + existing := mgmt.EdgeRouterFromFilter(importer.client, mgmt.NameFilter(*create.Name)) if existing != nil { log.WithFields(map[string]interface{}{ "name": *create.Name, "edgeRouterId": *existing.ID, }). Info("Found existing EdgeRouter, skipping create") - _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Skipping EdgeRouter %s\r", *create.Name) + _, _ = internal.FPrintfReusingLine(importer.loginOpts.Err, "Skipping EdgeRouter %s\r", *create.Name) continue } // do the actual create since it doesn't exist - _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Creating EdgeRouterPolicy %s\r", *create.Name) - if u.loginOpts.Verbose { + _, _ = internal.FPrintfReusingLine(importer.loginOpts.Err, "Creating EdgeRouterPolicy %s\r", *create.Name) + if importer.loginOpts.Verbose { log.WithField("name", *create.Name).Debug("Creating EdgeRouter") } - created, createErr := u.client.EdgeRouter.CreateEdgeRouter(&edge_router.CreateEdgeRouterParams{EdgeRouter: create}, nil) + created, createErr := importer.client.EdgeRouter.CreateEdgeRouter(&edge_router.CreateEdgeRouterParams{EdgeRouter: create}, nil) if createErr != nil { if payloadErr, ok := createErr.(rest_util.ApiErrorPayload); ok { log.WithFields(map[string]interface{}{ @@ -68,7 +68,7 @@ func (u *Importer) ProcessEdgeRouters(input map[string][]interface{}) (map[strin return nil, createErr } } - if u.loginOpts.Verbose { + if importer.loginOpts.Verbose { log.WithFields(map[string]interface{}{ "name": *create.Name, "edgeRouterId": created.Payload.Data.ID, @@ -82,13 +82,13 @@ func (u *Importer) ProcessEdgeRouters(input map[string][]interface{}) (map[strin return result, nil } -func (u *Importer) lookupEdgeRouters(roles []string) ([]string, error) { +func (importer *Importer) lookupEdgeRouters(roles []string) ([]string, error) { edgeRouterRoles := []string{} for _, role := range roles { if role[0:1] == "@" { value := role[1:] - edgeRouter, _ := ascode.GetItemFromCache(u.edgeRouterCache, value, func(name string) (interface{}, error) { - return mgmt.EdgeRouterFromFilter(u.client, mgmt.NameFilter(name)), nil + edgeRouter, _ := ascode.GetItemFromCache(importer.edgeRouterCache, value, func(name string) (interface{}, error) { + return mgmt.EdgeRouterFromFilter(importer.client, mgmt.NameFilter(name)), nil }) if edgeRouter == nil { return nil, errors.New("error reading EdgeRouter: " + value) diff --git a/ziti/cmd/ascode/importer/importer_external_jwt_signers.go b/ziti/cmd/ascode/importer/importer_external_jwt_signers.go index 848347235..6abdf40b1 100644 --- a/ziti/cmd/ascode/importer/importer_external_jwt_signers.go +++ b/ziti/cmd/ascode/importer/importer_external_jwt_signers.go @@ -25,7 +25,7 @@ import ( "slices" ) -func (u *Importer) IsExtJwtSignerImportRequired(args []string) bool { +func (importer *Importer) IsExtJwtSignerImportRequired(args []string) bool { return slices.Contains(args, "all") || len(args) == 0 || // explicit all or nothing specified slices.Contains(args, "ext-jwt-signer") || slices.Contains(args, "external-jwt-signer") || @@ -33,32 +33,32 @@ func (u *Importer) IsExtJwtSignerImportRequired(args []string) bool { slices.Contains(args, "identity") } -func (u *Importer) ProcessExternalJwtSigners(input map[string][]interface{}) (map[string]string, error) { +func (importer *Importer) ProcessExternalJwtSigners(input map[string][]interface{}) (map[string]string, error) { var result = map[string]string{} for _, data := range input["externalJwtSigners"] { create := FromMap(data, rest_model.ExternalJWTSignerCreate{}) // see if the signer already exists - existing := mgmt.ExternalJWTSignerFromFilter(u.client, mgmt.NameFilter(*create.Name)) + existing := mgmt.ExternalJWTSignerFromFilter(importer.client, mgmt.NameFilter(*create.Name)) if existing != nil { - if u.loginOpts.Verbose { + if importer.loginOpts.Verbose { log.WithFields(map[string]interface{}{ "name": *create.Name, "externalJwtSignerId": *existing.ID, }). Info("Found existing ExtJWTSigner, skipping create") } - _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Skipping ExtJWTSigner %s\r", *create.Name) + _, _ = internal.FPrintfReusingLine(importer.loginOpts.Err, "Skipping ExtJWTSigner %s\r", *create.Name) continue } // do the actual create since it doesn't exist - _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Creating ExtJWTSigner %s\r", *create.Name) - if u.loginOpts.Verbose { + _, _ = internal.FPrintfReusingLine(importer.loginOpts.Err, "Creating ExtJWTSigner %s\r", *create.Name) + if importer.loginOpts.Verbose { log.WithField("name", *create.Name).Debug("Creating ExtJWTSigner") } - created, createErr := u.client.ExternalJWTSigner.CreateExternalJWTSigner(&external_jwt_signer.CreateExternalJWTSignerParams{ExternalJWTSigner: create}, nil) + created, createErr := importer.client.ExternalJWTSigner.CreateExternalJWTSigner(&external_jwt_signer.CreateExternalJWTSignerParams{ExternalJWTSigner: create}, nil) if createErr != nil { if payloadErr, ok := createErr.(rest_util.ApiErrorPayload); ok { log.WithFields(map[string]interface{}{ @@ -73,7 +73,7 @@ func (u *Importer) ProcessExternalJwtSigners(input map[string][]interface{}) (ma return nil, createErr } } - if u.loginOpts.Verbose { + if importer.loginOpts.Verbose { log.WithFields(map[string]interface{}{ "name": *create.Name, "externalJwtSignerId": created.Payload.Data.ID, diff --git a/ziti/cmd/ascode/importer/importer_identities.go b/ziti/cmd/ascode/importer/importer_identities.go index 0ea27fa2b..af7acd980 100644 --- a/ziti/cmd/ascode/importer/importer_identities.go +++ b/ziti/cmd/ascode/importer/importer_identities.go @@ -29,28 +29,28 @@ import ( "slices" ) -func (u *Importer) IsIdentityImportRequired(args []string) bool { +func (importer *Importer) IsIdentityImportRequired(args []string) bool { return slices.Contains(args, "all") || len(args) == 0 || // explicit all or nothing specified slices.Contains(args, "identity") } -func (u *Importer) ProcessIdentities(input map[string][]interface{}) (map[string]string, error) { +func (importer *Importer) ProcessIdentities(input map[string][]interface{}) (map[string]string, error) { var result = map[string]string{} for _, data := range input["identities"] { create := FromMap(data, rest_model.IdentityCreate{}) - existing := mgmt.IdentityFromFilter(u.client, mgmt.NameFilter(*create.Name)) + existing := mgmt.IdentityFromFilter(importer.client, mgmt.NameFilter(*create.Name)) if existing != nil { - if u.loginOpts.Verbose { + if importer.loginOpts.Verbose { log.WithFields(map[string]interface{}{ "name": *create.Name, "identityId": *existing.ID, }). Info("Found existing Identity, skipping create") } - _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Skipping Identity %s\r", *create.Name) + _, _ = internal.FPrintfReusingLine(importer.loginOpts.Err, "Skipping Identity %s\r", *create.Name) continue } @@ -68,8 +68,8 @@ func (u *Importer) ProcessIdentities(input map[string][]interface{}) (map[string policyName := doc.Path("authPolicy").Data().(string)[1:] // look up the auth policy id from the name and add to the create, omit if it's the "Default" policy - policy, _ := ascode.GetItemFromCache(u.authPolicyCache, policyName, func(name string) (interface{}, error) { - return mgmt.AuthPolicyFromFilter(u.client, mgmt.NameFilter(name)), nil + policy, _ := ascode.GetItemFromCache(importer.authPolicyCache, policyName, func(name string) (interface{}, error) { + return mgmt.AuthPolicyFromFilter(importer.client, mgmt.NameFilter(name)), nil }) if policy == nil { return nil, errors.New("error reading Auth Policy: " + policyName) @@ -79,8 +79,8 @@ func (u *Importer) ProcessIdentities(input map[string][]interface{}) (map[string } // do the actual create since it doesn't exist - _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Creating Identity %s\r", *create.Name) - created, createErr := u.client.Identity.CreateIdentity(&identity.CreateIdentityParams{Identity: create}, nil) + _, _ = internal.FPrintfReusingLine(importer.loginOpts.Err, "Creating Identity %s\r", *create.Name) + created, createErr := importer.client.Identity.CreateIdentity(&identity.CreateIdentityParams{Identity: create}, nil) if createErr != nil { if payloadErr, ok := createErr.(rest_util.ApiErrorPayload); ok { log.WithFields(map[string]interface{}{ @@ -94,7 +94,7 @@ func (u *Importer) ProcessIdentities(input map[string][]interface{}) (map[string return nil, createErr } } - if u.loginOpts.Verbose { + if importer.loginOpts.Verbose { log.WithFields(map[string]interface{}{ "name": *create.Name, "identityId": created.Payload.Data.ID, @@ -108,13 +108,13 @@ func (u *Importer) ProcessIdentities(input map[string][]interface{}) (map[string return result, nil } -func (u *Importer) lookupIdentities(roles []string) ([]string, error) { +func (importer *Importer) lookupIdentities(roles []string) ([]string, error) { identityRoles := []string{} for _, role := range roles { if role[0:1] == "@" { roleName := role[1:] - value, lookupErr := ascode.GetItemFromCache(u.identityCache, roleName, func(name string) (interface{}, error) { - return mgmt.IdentityFromFilter(u.client, mgmt.NameFilter(name)), nil + value, lookupErr := ascode.GetItemFromCache(importer.identityCache, roleName, func(name string) (interface{}, error) { + return mgmt.IdentityFromFilter(importer.client, mgmt.NameFilter(name)), nil }) if lookupErr != nil { return nil, lookupErr diff --git a/ziti/cmd/ascode/importer/importer_posture_check.go b/ziti/cmd/ascode/importer/importer_posture_check.go index 20e35c71f..9e9472d0d 100644 --- a/ziti/cmd/ascode/importer/importer_posture_check.go +++ b/ziti/cmd/ascode/importer/importer_posture_check.go @@ -28,12 +28,12 @@ import ( "strings" ) -func (u *Importer) IsPostureCheckImportRequired(args []string) bool { +func (importer *Importer) IsPostureCheckImportRequired(args []string) bool { return slices.Contains(args, "all") || len(args) == 0 || // explicit all or nothing specified slices.Contains(args, "posture-check") } -func (u *Importer) ProcessPostureChecks(input map[string][]interface{}) (map[string]string, error) { +func (importer *Importer) ProcessPostureChecks(input map[string][]interface{}) (map[string]string, error) { var result = map[string]string{} for _, data := range input["postureChecks"] { @@ -70,9 +70,9 @@ func (u *Importer) ProcessPostureChecks(input map[string][]interface{}) (map[str } // see if the posture check already exists - existing := mgmt.PostureCheckFromFilter(u.client, mgmt.NameFilter(*create.Name())) + existing := mgmt.PostureCheckFromFilter(importer.client, mgmt.NameFilter(*create.Name())) if existing != nil { - if u.loginOpts.Verbose { + if importer.loginOpts.Verbose { log.WithFields(map[string]interface{}{ "name": *create.Name(), "postureCheckId": (*existing).ID(), @@ -80,20 +80,20 @@ func (u *Importer) ProcessPostureChecks(input map[string][]interface{}) (map[str }). Info("Found existing PostureCheck, skipping create") } - _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Skipping PostureCheck %s\r", *create.Name()) + _, _ = internal.FPrintfReusingLine(importer.loginOpts.Err, "Skipping PostureCheck %s\r", *create.Name()) continue } // do the actual create since it doesn't exist - _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Creating PostureCheck %s\r", *create.Name()) - if u.loginOpts.Verbose { + _, _ = internal.FPrintfReusingLine(importer.loginOpts.Err, "Creating PostureCheck %s\r", *create.Name()) + if importer.loginOpts.Verbose { log.WithFields(map[string]interface{}{ "name": *create.Name(), "typeId": create.TypeID(), }). Debug("Creating PostureCheck") } - created, createErr := u.client.PostureChecks.CreatePostureCheck(&posture_checks.CreatePostureCheckParams{PostureCheck: create}, nil) + created, createErr := importer.client.PostureChecks.CreatePostureCheck(&posture_checks.CreatePostureCheckParams{PostureCheck: create}, nil) if createErr != nil { if payloadErr, ok := createErr.(rest_util.ApiErrorPayload); ok { log.WithFields(map[string]interface{}{ @@ -106,7 +106,7 @@ func (u *Importer) ProcessPostureChecks(input map[string][]interface{}) (map[str return nil, createErr } } - if u.loginOpts.Verbose { + if importer.loginOpts.Verbose { log.WithFields(map[string]interface{}{ "name": *create.Name(), "postureCheckId": created.Payload.Data.ID, diff --git a/ziti/cmd/ascode/importer/importer_service_edgerouter_policies.go b/ziti/cmd/ascode/importer/importer_service_edgerouter_policies.go index c85afb659..fa8293ee5 100644 --- a/ziti/cmd/ascode/importer/importer_service_edgerouter_policies.go +++ b/ziti/cmd/ascode/importer/importer_service_edgerouter_policies.go @@ -25,50 +25,50 @@ import ( "slices" ) -func (u *Importer) IsServiceEdgeRouterPolicyImportRequired(args []string) bool { +func (importer *Importer) IsServiceEdgeRouterPolicyImportRequired(args []string) bool { return slices.Contains(args, "all") || len(args) == 0 || // explicit all or nothing specified slices.Contains(args, "service-edge-router-policy") } -func (u *Importer) ProcessServiceEdgeRouterPolicies(input map[string][]interface{}) (map[string]string, error) { +func (importer *Importer) ProcessServiceEdgeRouterPolicies(input map[string][]interface{}) (map[string]string, error) { var result = map[string]string{} for _, data := range input["serviceEdgeRouterPolicies"] { create := FromMap(data, rest_model.ServiceEdgeRouterPolicyCreate{}) // see if the service router policy already exists - existing := mgmt.ServiceEdgeRouterPolicyFromFilter(u.client, mgmt.NameFilter(*create.Name)) + existing := mgmt.ServiceEdgeRouterPolicyFromFilter(importer.client, mgmt.NameFilter(*create.Name)) if existing != nil { log.WithFields(map[string]interface{}{ "name": *create.Name, "serviceRouterPolicyId": *existing.ID, }). Info("Found existing ServiceEdgeRouterPolicy, skipping create") - _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Skipping ServiceEdgeRouterPolicy %s\r", *create.Name) + _, _ = internal.FPrintfReusingLine(importer.loginOpts.Err, "Skipping ServiceEdgeRouterPolicy %s\r", *create.Name) continue } // look up the service ids from the name and add to the create - serviceRoles, err := u.lookupServices(create.ServiceRoles) + serviceRoles, err := importer.lookupServices(create.ServiceRoles) if err != nil { return nil, err } create.ServiceRoles = serviceRoles // look up the edgeRouter ids from the name and add to the create - edgeRouterRoles, err := u.lookupEdgeRouters(create.EdgeRouterRoles) + edgeRouterRoles, err := importer.lookupEdgeRouters(create.EdgeRouterRoles) if err != nil { return nil, err } create.EdgeRouterRoles = edgeRouterRoles // do the actual create since it doesn't exist - _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Creating ServiceEdgeRouterPolicy %s\r", *create.Name) - if u.loginOpts.Verbose { + _, _ = internal.FPrintfReusingLine(importer.loginOpts.Err, "Creating ServiceEdgeRouterPolicy %s\r", *create.Name) + if importer.loginOpts.Verbose { log.WithField("name", *create.Name). Debug("Creating ServiceEdgeRouterPolicy") } - created, createErr := u.client.ServiceEdgeRouterPolicy.CreateServiceEdgeRouterPolicy(&service_edge_router_policy.CreateServiceEdgeRouterPolicyParams{Policy: create}, nil) + created, createErr := importer.client.ServiceEdgeRouterPolicy.CreateServiceEdgeRouterPolicy(&service_edge_router_policy.CreateServiceEdgeRouterPolicyParams{Policy: create}, nil) if createErr != nil { if payloadErr, ok := createErr.(rest_util.ApiErrorPayload); ok { log.WithFields(map[string]interface{}{ @@ -82,7 +82,7 @@ func (u *Importer) ProcessServiceEdgeRouterPolicies(input map[string][]interface return nil, createErr } } - if u.loginOpts.Verbose { + if importer.loginOpts.Verbose { log.WithFields(map[string]interface{}{ "name": *create.Name, "serviceEdgeRouterPolicyId": created.Payload.Data.ID, diff --git a/ziti/cmd/ascode/importer/importer_service_policies.go b/ziti/cmd/ascode/importer/importer_service_policies.go index e97db09a7..dd2458a31 100644 --- a/ziti/cmd/ascode/importer/importer_service_policies.go +++ b/ziti/cmd/ascode/importer/importer_service_policies.go @@ -26,49 +26,49 @@ import ( "slices" ) -func (u *Importer) IsServicePolicyImportRequired(args []string) bool { +func (importer *Importer) IsServicePolicyImportRequired(args []string) bool { return slices.Contains(args, "all") || len(args) == 0 || // explicit all or nothing specified slices.Contains(args, "service-policy") } -func (u *Importer) ProcessServicePolicies(input map[string][]interface{}) (map[string]string, error) { +func (importer *Importer) ProcessServicePolicies(input map[string][]interface{}) (map[string]string, error) { var result = map[string]string{} for _, data := range input["servicePolicies"] { create := FromMap(data, rest_model.ServicePolicyCreate{}) // see if the service policy already exists - existing := mgmt.ServicePolicyFromFilter(u.client, mgmt.NameFilter(*create.Name)) + existing := mgmt.ServicePolicyFromFilter(importer.client, mgmt.NameFilter(*create.Name)) if existing != nil { log.WithFields(map[string]interface{}{ "name": *create.Name, "servicePolicyId": *existing.ID, }). Info("Found existing ServicePolicy, skipping create") - _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Skipping ServicePolicy %s\r", *create.Name) + _, _ = internal.FPrintfReusingLine(importer.loginOpts.Err, "Skipping ServicePolicy %s\r", *create.Name) continue } // look up the service ids from the name and add to the create - serviceRoles, err := u.lookupServices(create.ServiceRoles) + serviceRoles, err := importer.lookupServices(create.ServiceRoles) if err != nil { return nil, err } create.ServiceRoles = serviceRoles // look up the identity ids from the name and add to the create - identityRoles, err := u.lookupIdentities(create.IdentityRoles) + identityRoles, err := importer.lookupIdentities(create.IdentityRoles) if err != nil { return nil, errors.Join(errors.New("Unable to read all identities from ServicePolicy"), err) } create.IdentityRoles = identityRoles // do the actual create since it doesn't exist - _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Skipping ServicePolicy %s\r", *create.Name) - if u.loginOpts.Verbose { + _, _ = internal.FPrintfReusingLine(importer.loginOpts.Err, "Skipping ServicePolicy %s\r", *create.Name) + if importer.loginOpts.Verbose { log.WithField("name", *create.Name).Debug("Creating ServicePolicy") } - created, createErr := u.client.ServicePolicy.CreateServicePolicy(&service_policy.CreateServicePolicyParams{Policy: create}, nil) + created, createErr := importer.client.ServicePolicy.CreateServicePolicy(&service_policy.CreateServicePolicyParams{Policy: create}, nil) if createErr != nil { if payloadErr, ok := createErr.(rest_util.ApiErrorPayload); ok { log.WithFields(map[string]interface{}{ @@ -81,7 +81,7 @@ func (u *Importer) ProcessServicePolicies(input map[string][]interface{}) (map[s return nil, createErr } } - if u.loginOpts.Verbose { + if importer.loginOpts.Verbose { log.WithFields(map[string]interface{}{ "name": *create.Name, "servicePolicyId": created.Payload.Data.ID, diff --git a/ziti/cmd/ascode/importer/importer_services.go b/ziti/cmd/ascode/importer/importer_services.go index b1596b3a7..b00b76103 100644 --- a/ziti/cmd/ascode/importer/importer_services.go +++ b/ziti/cmd/ascode/importer/importer_services.go @@ -29,12 +29,12 @@ import ( "slices" ) -func (u *Importer) IsServiceImportRequired(args []string) bool { +func (importer *Importer) IsServiceImportRequired(args []string) bool { return slices.Contains(args, "all") || len(args) == 0 || // explicit all or nothing specified slices.Contains(args, "service") } -func (u *Importer) ProcessServices(input map[string][]interface{}) (map[string]string, error) { +func (importer *Importer) ProcessServices(input map[string][]interface{}) (map[string]string, error) { var result = map[string]string{} @@ -42,14 +42,14 @@ func (u *Importer) ProcessServices(input map[string][]interface{}) (map[string]s create := FromMap(data, rest_model.ServiceCreate{}) // see if the service already exists - existing := mgmt.ServiceFromFilter(u.client, mgmt.NameFilter(*create.Name)) + existing := mgmt.ServiceFromFilter(importer.client, mgmt.NameFilter(*create.Name)) if existing != nil { log.WithFields(map[string]interface{}{ "name": *create.Name, "serviceId": *existing.ID, }). Info("Found existing Service, skipping create") - _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Skipping Service %s\r", *create.Name) + _, _ = internal.FPrintfReusingLine(importer.loginOpts.Err, "Skipping Service %s\r", *create.Name) continue } @@ -66,8 +66,8 @@ func (u *Importer) ProcessServices(input map[string][]interface{}) (map[string]s configIds := []string{} for _, configName := range configsNode.Children() { value := configName.Data().(string)[1:] - config, _ := ascode.GetItemFromCache(u.configCache, value, func(name string) (interface{}, error) { - return mgmt.ConfigFromFilter(u.client, mgmt.NameFilter(name)), nil + config, _ := ascode.GetItemFromCache(importer.configCache, value, func(name string) (interface{}, error) { + return mgmt.ConfigFromFilter(importer.client, mgmt.NameFilter(name)), nil }) if config == nil { return nil, errors.New("error reading Config: " + value) @@ -77,11 +77,11 @@ func (u *Importer) ProcessServices(input map[string][]interface{}) (map[string]s create.Configs = configIds // do the actual create since it doesn't exist - _, _ = internal.FPrintfReusingLine(u.loginOpts.Err, "Creating Service %s\r", *create.Name) - if u.loginOpts.Verbose { + _, _ = internal.FPrintfReusingLine(importer.loginOpts.Err, "Creating Service %s\r", *create.Name) + if importer.loginOpts.Verbose { log.WithField("name", *create.Name).Debug("Creating Service") } - created, createErr := u.client.Service.CreateService(&service.CreateServiceParams{Service: create}, nil) + created, createErr := importer.client.Service.CreateService(&service.CreateServiceParams{Service: create}, nil) if createErr != nil { if payloadErr, ok := createErr.(rest_util.ApiErrorPayload); ok { log.WithFields(map[string]interface{}{ @@ -94,7 +94,7 @@ func (u *Importer) ProcessServices(input map[string][]interface{}) (map[string]s return nil, createErr } } - if u.loginOpts.Verbose { + if importer.loginOpts.Verbose { log.WithFields(map[string]interface{}{ "name": *create.Name, "serviceId": created.Payload.Data.ID, @@ -108,13 +108,13 @@ func (u *Importer) ProcessServices(input map[string][]interface{}) (map[string]s return result, nil } -func (u *Importer) lookupServices(roles []string) ([]string, error) { +func (importer *Importer) lookupServices(roles []string) ([]string, error) { serviceRoles := []string{} for _, role := range roles { if role[0:1] == "@" { value := role[1:] - service, _ := ascode.GetItemFromCache(u.serviceCache, value, func(name string) (interface{}, error) { - return mgmt.ServiceFromFilter(u.client, mgmt.NameFilter(name)), nil + service, _ := ascode.GetItemFromCache(importer.serviceCache, value, func(name string) (interface{}, error) { + return mgmt.ServiceFromFilter(importer.client, mgmt.NameFilter(name)), nil }) if service == nil { return nil, errors.New("error reading Service: " + value)