diff --git a/cmd/config/testdata/TestGetClusterCmdGoldenOutput/get-all-ephemeral.golden b/cmd/config/testdata/TestGetClusterCmdGoldenOutput/get-all-ephemeral.golden index 2774bd228..36bc8e7ce 100644 --- a/cmd/config/testdata/TestGetClusterCmdGoldenOutput/get-all-ephemeral.golden +++ b/cmd/config/testdata/TestGetClusterCmdGoldenOutput/get-all-ephemeral.golden @@ -2,6 +2,7 @@ Cluster: clusterBar ephemeral: bootstrapInfo: "" clusterKubeconf: clusterBar_ephemeral +managementConfiguration: "" LocationOfOrigin: "" insecure-skip-tls-verify: true @@ -11,6 +12,7 @@ Cluster: clusterBar target: bootstrapInfo: "" clusterKubeconf: clusterBar_target +managementConfiguration: "" LocationOfOrigin: "" insecure-skip-tls-verify: true @@ -20,6 +22,7 @@ Cluster: clusterBaz ephemeral: bootstrapInfo: "" clusterKubeconf: clusterBaz_ephemeral +managementConfiguration: "" LocationOfOrigin: "" insecure-skip-tls-verify: true @@ -29,6 +32,7 @@ Cluster: clusterBaz target: bootstrapInfo: "" clusterKubeconf: clusterBaz_target +managementConfiguration: "" LocationOfOrigin: "" insecure-skip-tls-verify: true @@ -38,6 +42,7 @@ Cluster: clusterFoo ephemeral: bootstrapInfo: "" clusterKubeconf: clusterFoo_ephemeral +managementConfiguration: "" LocationOfOrigin: "" insecure-skip-tls-verify: true @@ -47,6 +52,7 @@ Cluster: clusterFoo target: bootstrapInfo: "" clusterKubeconf: clusterFoo_target +managementConfiguration: "" LocationOfOrigin: "" insecure-skip-tls-verify: true diff --git a/cmd/config/testdata/TestGetClusterCmdGoldenOutput/get-all-target.golden b/cmd/config/testdata/TestGetClusterCmdGoldenOutput/get-all-target.golden index 2774bd228..36bc8e7ce 100644 --- a/cmd/config/testdata/TestGetClusterCmdGoldenOutput/get-all-target.golden +++ b/cmd/config/testdata/TestGetClusterCmdGoldenOutput/get-all-target.golden @@ -2,6 +2,7 @@ Cluster: clusterBar ephemeral: bootstrapInfo: "" clusterKubeconf: clusterBar_ephemeral +managementConfiguration: "" LocationOfOrigin: "" insecure-skip-tls-verify: true @@ -11,6 +12,7 @@ Cluster: clusterBar target: bootstrapInfo: "" clusterKubeconf: clusterBar_target +managementConfiguration: "" LocationOfOrigin: "" insecure-skip-tls-verify: true @@ -20,6 +22,7 @@ Cluster: clusterBaz ephemeral: bootstrapInfo: "" clusterKubeconf: clusterBaz_ephemeral +managementConfiguration: "" LocationOfOrigin: "" insecure-skip-tls-verify: true @@ -29,6 +32,7 @@ Cluster: clusterBaz target: bootstrapInfo: "" clusterKubeconf: clusterBaz_target +managementConfiguration: "" LocationOfOrigin: "" insecure-skip-tls-verify: true @@ -38,6 +42,7 @@ Cluster: clusterFoo ephemeral: bootstrapInfo: "" clusterKubeconf: clusterFoo_ephemeral +managementConfiguration: "" LocationOfOrigin: "" insecure-skip-tls-verify: true @@ -47,6 +52,7 @@ Cluster: clusterFoo target: bootstrapInfo: "" clusterKubeconf: clusterFoo_target +managementConfiguration: "" LocationOfOrigin: "" insecure-skip-tls-verify: true diff --git a/cmd/config/testdata/TestGetClusterCmdGoldenOutput/get-ephemeral.golden b/cmd/config/testdata/TestGetClusterCmdGoldenOutput/get-ephemeral.golden index 04a90037b..e46f14e2a 100644 --- a/cmd/config/testdata/TestGetClusterCmdGoldenOutput/get-ephemeral.golden +++ b/cmd/config/testdata/TestGetClusterCmdGoldenOutput/get-ephemeral.golden @@ -2,6 +2,7 @@ Cluster: clusterFoo ephemeral: bootstrapInfo: "" clusterKubeconf: clusterFoo_ephemeral +managementConfiguration: "" LocationOfOrigin: "" insecure-skip-tls-verify: true diff --git a/cmd/config/testdata/TestGetClusterCmdGoldenOutput/get-multiple-ephemeral.golden b/cmd/config/testdata/TestGetClusterCmdGoldenOutput/get-multiple-ephemeral.golden index 2774bd228..36bc8e7ce 100644 --- a/cmd/config/testdata/TestGetClusterCmdGoldenOutput/get-multiple-ephemeral.golden +++ b/cmd/config/testdata/TestGetClusterCmdGoldenOutput/get-multiple-ephemeral.golden @@ -2,6 +2,7 @@ Cluster: clusterBar ephemeral: bootstrapInfo: "" clusterKubeconf: clusterBar_ephemeral +managementConfiguration: "" LocationOfOrigin: "" insecure-skip-tls-verify: true @@ -11,6 +12,7 @@ Cluster: clusterBar target: bootstrapInfo: "" clusterKubeconf: clusterBar_target +managementConfiguration: "" LocationOfOrigin: "" insecure-skip-tls-verify: true @@ -20,6 +22,7 @@ Cluster: clusterBaz ephemeral: bootstrapInfo: "" clusterKubeconf: clusterBaz_ephemeral +managementConfiguration: "" LocationOfOrigin: "" insecure-skip-tls-verify: true @@ -29,6 +32,7 @@ Cluster: clusterBaz target: bootstrapInfo: "" clusterKubeconf: clusterBaz_target +managementConfiguration: "" LocationOfOrigin: "" insecure-skip-tls-verify: true @@ -38,6 +42,7 @@ Cluster: clusterFoo ephemeral: bootstrapInfo: "" clusterKubeconf: clusterFoo_ephemeral +managementConfiguration: "" LocationOfOrigin: "" insecure-skip-tls-verify: true @@ -47,6 +52,7 @@ Cluster: clusterFoo target: bootstrapInfo: "" clusterKubeconf: clusterFoo_target +managementConfiguration: "" LocationOfOrigin: "" insecure-skip-tls-verify: true diff --git a/cmd/config/testdata/TestGetClusterCmdGoldenOutput/get-multiple-target.golden b/cmd/config/testdata/TestGetClusterCmdGoldenOutput/get-multiple-target.golden index 2774bd228..36bc8e7ce 100644 --- a/cmd/config/testdata/TestGetClusterCmdGoldenOutput/get-multiple-target.golden +++ b/cmd/config/testdata/TestGetClusterCmdGoldenOutput/get-multiple-target.golden @@ -2,6 +2,7 @@ Cluster: clusterBar ephemeral: bootstrapInfo: "" clusterKubeconf: clusterBar_ephemeral +managementConfiguration: "" LocationOfOrigin: "" insecure-skip-tls-verify: true @@ -11,6 +12,7 @@ Cluster: clusterBar target: bootstrapInfo: "" clusterKubeconf: clusterBar_target +managementConfiguration: "" LocationOfOrigin: "" insecure-skip-tls-verify: true @@ -20,6 +22,7 @@ Cluster: clusterBaz ephemeral: bootstrapInfo: "" clusterKubeconf: clusterBaz_ephemeral +managementConfiguration: "" LocationOfOrigin: "" insecure-skip-tls-verify: true @@ -29,6 +32,7 @@ Cluster: clusterBaz target: bootstrapInfo: "" clusterKubeconf: clusterBaz_target +managementConfiguration: "" LocationOfOrigin: "" insecure-skip-tls-verify: true @@ -38,6 +42,7 @@ Cluster: clusterFoo ephemeral: bootstrapInfo: "" clusterKubeconf: clusterFoo_ephemeral +managementConfiguration: "" LocationOfOrigin: "" insecure-skip-tls-verify: true @@ -47,6 +52,7 @@ Cluster: clusterFoo target: bootstrapInfo: "" clusterKubeconf: clusterFoo_target +managementConfiguration: "" LocationOfOrigin: "" insecure-skip-tls-verify: true diff --git a/cmd/config/testdata/TestGetClusterCmdGoldenOutput/get-target.golden b/cmd/config/testdata/TestGetClusterCmdGoldenOutput/get-target.golden index ec5485ad8..086c32799 100644 --- a/cmd/config/testdata/TestGetClusterCmdGoldenOutput/get-target.golden +++ b/cmd/config/testdata/TestGetClusterCmdGoldenOutput/get-target.golden @@ -2,6 +2,7 @@ Cluster: clusterFoo target: bootstrapInfo: "" clusterKubeconf: clusterFoo_target +managementConfiguration: "" LocationOfOrigin: "" insecure-skip-tls-verify: true diff --git a/pkg/config/config.go b/pkg/config/config.go index f3596326a..47c9e49c1 100644 --- a/pkg/config/config.go +++ b/pkg/config/config.go @@ -727,6 +727,27 @@ func (c *Config) CurrentContextBootstrapInfo() (*Bootstrap, error) { return bootstrap, nil } +// CurrentContextManagementConfig returns the management options for the current context +func (c *Config) CurrentContextManagementConfig() (*ManagementConfiguration, error) { + currentCluster, err := c.CurrentContextCluster() + if err != nil { + return nil, err + } + + if currentCluster.ManagementConfiguration == "" { + return nil, ErrMissingConfig{ + What: fmt.Sprintf("No management config listed for cluster %s", currentCluster.NameInKubeconf), + } + } + + managementCfg, exists := c.ManagementConfiguration[currentCluster.ManagementConfiguration] + if !exists { + return nil, ErrMissingManagementConfiguration{cluster: currentCluster} + } + + return managementCfg, nil +} + // Purge removes the config file func (c *Config) Purge() error { return os.Remove(c.loadedConfigPath) @@ -824,6 +845,15 @@ func (b *Bootstrap) String() string { return string(yamlData) } +// Management Configuration functions +func (m *ManagementConfiguration) String() string { + yamlData, err := yaml.Marshal(&m) + if err != nil { + return "" + } + return string(yamlData) +} + // Container functions func (c *Container) String() string { yamlData, err := yaml.Marshal(&c) diff --git a/pkg/config/config_test.go b/pkg/config/config_test.go index 74548e6b4..3488b35a2 100644 --- a/pkg/config/config_test.go +++ b/pkg/config/config_test.go @@ -77,6 +77,10 @@ func TestString(t *testing.T) { name: "bootstrapinfo", stringer: testutil.DummyBootstrapInfo(), }, + { + name: "managementconfiguration", + stringer: testutil.DummyManagementConfiguration(), + }, { name: "builder", stringer: &config.Builder{ diff --git a/pkg/config/errors.go b/pkg/config/errors.go index 57280bfe6..62b563cc4 100644 --- a/pkg/config/errors.go +++ b/pkg/config/errors.go @@ -111,6 +111,16 @@ func (e ErrMissingCurrentContext) Error() string { return "Current context must be set before using --current flag" } +// ErrMissingManagementConfiguration means the management configuration was not defined for the active cluster. +type ErrMissingManagementConfiguration struct { + cluster *Cluster +} + +func (e ErrMissingManagementConfiguration) Error() string { + return fmt.Sprintf("Management configuration %s for cluster %s undefined.", e.cluster.ManagementConfiguration, + e.cluster.NameInKubeconf) +} + // ErrMissingPrimaryRepo returned when Primary Repository is not set in context manifest type ErrMissingPrimaryRepo struct { } diff --git a/pkg/config/testdata/cluster-string.yaml b/pkg/config/testdata/cluster-string.yaml index b9555a30a..7d7fbbfa5 100644 --- a/pkg/config/testdata/cluster-string.yaml +++ b/pkg/config/testdata/cluster-string.yaml @@ -1,5 +1,6 @@ bootstrapInfo: dummy_bootstrap_config clusterKubeconf: dummy_cluster_target +managementConfiguration: dummy_management_config LocationOfOrigin: "" certificate-authority: dummy_ca diff --git a/pkg/config/testdata/config-string.yaml b/pkg/config/testdata/config-string.yaml index 55f2eb20b..83a8bcd19 100644 --- a/pkg/config/testdata/config-string.yaml +++ b/pkg/config/testdata/config-string.yaml @@ -15,15 +15,21 @@ clusters: ephemeral: bootstrapInfo: dummy_bootstrap_config clusterKubeconf: dummy_cluster_ephemeral + managementConfiguration: dummy_management_config target: bootstrapInfo: dummy_bootstrap_config clusterKubeconf: dummy_cluster_target + managementConfiguration: dummy_management_config contexts: dummy_context: contextKubeconf: dummy_cluster_ephemeral manifest: dummy_manifest currentContext: dummy_context kind: Config +managementConfiguration: + dummy_management_config: + insecure: true + type: redfish manifests: dummy_manifest: primaryRepositoryName: primary diff --git a/pkg/config/testdata/managementconfiguration-string.yaml b/pkg/config/testdata/managementconfiguration-string.yaml new file mode 100644 index 000000000..c828c7532 --- /dev/null +++ b/pkg/config/testdata/managementconfiguration-string.yaml @@ -0,0 +1,2 @@ +insecure: true +type: redfish diff --git a/pkg/config/testdata/prettycluster-string.yaml b/pkg/config/testdata/prettycluster-string.yaml index aa8b1cd0b..2645747a1 100644 --- a/pkg/config/testdata/prettycluster-string.yaml +++ b/pkg/config/testdata/prettycluster-string.yaml @@ -2,6 +2,7 @@ Cluster: dummy_cluster target: bootstrapInfo: dummy_bootstrap_config clusterKubeconf: dummy_cluster_target +managementConfiguration: dummy_management_config LocationOfOrigin: "" certificate-authority: dummy_ca diff --git a/pkg/config/types.go b/pkg/config/types.go index e6dc957ae..587ba7eed 100644 --- a/pkg/config/types.go +++ b/pkg/config/types.go @@ -49,6 +49,9 @@ type Config struct { // CurrentContext is the name of the context that you would like to use by default CurrentContext string `json:"currentContext"` + // Management configuration defines management information for all baremetal hosts in a cluster. + ManagementConfiguration map[string]*ManagementConfiguration `json:"managementConfiguration"` + // BootstrapInfo is the configuration for container runtime, ISO builder and remote management BootstrapInfo map[string]*Bootstrap `json:"bootstrapInfo"` @@ -80,6 +83,9 @@ type Cluster struct { // KubeConfig Cluster Object cluster *kubeconfig.Cluster + // Management configuration which will be used for all hosts in the cluster + ManagementConfiguration string `json:"managementConfiguration"` + // Bootstrap configuration this clusters ephemeral hosts will rely on Bootstrap string `json:"bootstrapInfo"` } @@ -176,6 +182,18 @@ type ClusterComplexName struct { Type string } +// ManagementConfiguration defines configuration data for all remote systems within a context. +type ManagementConfiguration struct { + // Insecure indicates whether the SSL certificate should be checked on remote management requests. + Insecure bool `json:"insecure,omitempty"` + // Type indicates the type of out-of-band management that will be used for baremetal orchestration, e.g. + // redfish. + Type string `json:"type"` + // UseProxy indicates whether airshipctl should transmit remote management requests through a proxy server when + // one is configured in an environment. + UseProxy bool `json:"useproxy,omitempty"` +} + // Bootstrap holds configurations for bootstrap steps type Bootstrap struct { // Configuration parameters for container diff --git a/pkg/config/utils.go b/pkg/config/utils.go index 23c0ebc8c..545afa5f1 100644 --- a/pkg/config/utils.go +++ b/pkg/config/utils.go @@ -16,7 +16,11 @@ limitations under the License. package config -import "strings" +import ( + "strings" + + "opendev.org/airship/airshipctl/pkg/remote/redfish" +) const ( DefaultTestPrimaryRepo = "primary" @@ -52,6 +56,13 @@ func NewConfig() *Config { Manifest: AirshipDefaultManifest, }, }, + ManagementConfiguration: map[string]*ManagementConfiguration{ + AirshipDefaultContext: { + Type: redfish.ClientType, + Insecure: true, + UseProxy: false, + }, + }, Manifests: map[string]*Manifest{ AirshipDefaultManifest: { Repositories: map[string]*Repository{ diff --git a/testutil/testconfig.go b/testutil/testconfig.go index 19795626e..a67b85825 100644 --- a/testutil/testconfig.go +++ b/testutil/testconfig.go @@ -26,6 +26,7 @@ import ( "github.com/stretchr/testify/require" "opendev.org/airship/airshipctl/pkg/config" + "opendev.org/airship/airshipctl/pkg/remote/redfish" ) // types cloned directory from pkg/config/types to prevent circular import @@ -41,14 +42,17 @@ func DummyConfig() *config.Config { AuthInfos: map[string]*config.AuthInfo{ "dummy_user": DummyAuthInfo(), }, + BootstrapInfo: map[string]*config.Bootstrap{ + "dummy_bootstrap_config": DummyBootstrapInfo(), + }, Contexts: map[string]*config.Context{ "dummy_context": DummyContext(), }, Manifests: map[string]*config.Manifest{ "dummy_manifest": DummyManifest(), }, - BootstrapInfo: map[string]*config.Bootstrap{ - "dummy_bootstrap_config": DummyBootstrapInfo(), + ManagementConfiguration: map[string]*config.ManagementConfiguration{ + "dummy_management_config": DummyManagementConfiguration(), }, CurrentContext: "dummy_context", } @@ -85,6 +89,7 @@ func DummyCluster() *config.Cluster { c.SetKubeCluster(cluster) c.NameInKubeconf = "dummy_cluster_target" c.Bootstrap = "dummy_bootstrap_config" + c.ManagementConfiguration = "dummy_management_config" return c } @@ -248,6 +253,15 @@ func DummyBootstrapInfo() *config.Bootstrap { return bs } +// DummyManagementConfiguration creates a management configuration for unit testing +func DummyManagementConfiguration() *config.ManagementConfiguration { + return &config.ManagementConfiguration{ + Type: redfish.ClientType, + Insecure: true, + UseProxy: false, + } +} + const ( testConfigYAML = `apiVersion: airshipit.org/v1alpha1 bootstrapInfo: