diff --git a/pkg/gardener/shoot/extender/extensions/dns.go b/pkg/gardener/shoot/extender/extensions/dns.go new file mode 100644 index 00000000..92b1ca5c --- /dev/null +++ b/pkg/gardener/shoot/extender/extensions/dns.go @@ -0,0 +1,89 @@ +package extensions + +import ( + "encoding/json" + "fmt" + gardener "github.com/gardener/gardener/pkg/apis/core/v1beta1" + apimachineryruntime "k8s.io/apimachinery/pkg/runtime" + "k8s.io/utils/ptr" +) + +const DNSExtensionType = "shoot-dns-service" + +// The types were copied from the following file: https://github.com/gardener/gardener-extension-shoot-dns-service/blob/master/pkg/apis/service/types.go +type DNSExtensionProviderConfig struct { + // APIVersion is gardener extension api version + APIVersion string `json:"apiVersion"` + // Kind is extension type + Kind string `json:"kind"` + + // DnsProviderReplication indicates whether dnsProvider replication is on + DNSProviderReplication *DNSProviderReplication `json:"dnsProviderReplication,omitempty"` + // Providers is a list of additional DNS providers that shall be enabled for this shoot cluster. + // The primary ("external") provider at `spec.dns.provider` is added automatically + Providers []DNSProvider `json:"providers"` + // SyncProvidersFromShootSpecDNS is an optional flag for migrating and synchronising the providers given in the + // shoot manifest at section `spec.dns.providers`. If true, any direct changes on the `providers` section + // are overwritten with the content of section `spec.dns.providers`. + SyncProvidersFromShootSpecDNS *bool `json:"syncProvidersFromShootSpecDNS,omitempty"` +} + +// DNSProvider contains information about a DNS provider. +type DNSProvider struct { + // Domains contains information about which domains shall be included/excluded for this provider. + Domains *DNSIncludeExclude `json:"domains,omitempty"` + // SecretName is a name of a secret containing credentials for the stated domain and the + // provider. + SecretName *string `json:"secretName,omitempty"` + // Type is the DNS provider type. + Type *string `json:"type,omitempty"` + // Zones contains information about which hosted zones shall be included/excluded for this provider. + Zones *DNSIncludeExclude `json:"zones,omitempty"` +} + +// DNSIncludeExclude contains information about which domains shall be included/excluded. +type DNSIncludeExclude struct { + // Include is a list of domains that shall be included. + Include []string `json:"include,omitempty"` + // Exclude is a list of domains that shall be excluded. + Exclude []string `json:"exclude,omitempty"` +} + +type DNSProviderReplication struct { + // Enabled indicates whether replication is on + Enabled bool `json:"enabled"` +} + +func newDNSExtensionConfig(domain, secretName, dnsProviderType string) *DNSExtensionProviderConfig { + return &DNSExtensionProviderConfig{ + APIVersion: "service.dns.extensions.gardener.cloud/v1alpha1", + Kind: "DNSConfig", + DNSProviderReplication: &DNSProviderReplication{Enabled: true}, + SyncProvidersFromShootSpecDNS: ptr.To(true), + Providers: []DNSProvider{ + { + Domains: &DNSIncludeExclude{ + Include: []string{domain}, + }, + SecretName: ptr.To(secretName), + Type: ptr.To(dnsProviderType), + }, + }, + } +} + +func NewDNSExtension(shootName, secretName, domainPrefix, dnsProviderType string) (gardener.Extension, error) { + domain := fmt.Sprintf("%s.%s", shootName, domainPrefix) + + extensionJSON, err := json.Marshal(newDNSExtensionConfig(domain, secretName, dnsProviderType)) + if err != nil { + return gardener.Extension{}, err + } + + return gardener.Extension{ + Type: DNSExtensionType, + ProviderConfig: &apimachineryruntime.RawExtension{ + Raw: extensionJSON, + }, + }, nil +} diff --git a/pkg/gardener/shoot/extender/extensions/extender.go b/pkg/gardener/shoot/extender/extensions/extender.go new file mode 100644 index 00000000..d4fe85e4 --- /dev/null +++ b/pkg/gardener/shoot/extender/extensions/extender.go @@ -0,0 +1,55 @@ +package extensions + +import ( + gardener "github.com/gardener/gardener/pkg/apis/core/v1beta1" + imv1 "github.com/kyma-project/infrastructure-manager/api/v1" + "github.com/kyma-project/infrastructure-manager/pkg/config" + "slices" +) + +type CreateExtension func(runtime imv1.Runtime, shoot *gardener.Shoot) (gardener.Extension, error) + +type Extension struct { + Type string + Factory CreateExtension +} + +func NewExtensionsExtenderForCreate(config config.ConverterConfig) func(runtime imv1.Runtime, shoot *gardener.Shoot) error { + return newExtensionsExtender([]Extension{ + { + Type: DNSExtensionType, + Factory: func(runtime imv1.Runtime, shoot *gardener.Shoot) (gardener.Extension, error) { + return NewDNSExtension(runtime.Spec.Shoot.Name, config.DNS.SecretName, config.DNS.DomainPrefix, config.DNS.ProviderType) + }, + }, + { + Type: OidcExtensionType, + Factory: func(runtime imv1.Runtime, shoot *gardener.Shoot) (gardener.Extension, error) { + return NewOIDCExtension() + }, + }, + }, nil) +} + +func newExtensionsExtender(extensionsToApply []Extension, currentGardenerExtensions []gardener.Extension) func(runtime imv1.Runtime, shoot *gardener.Shoot) error { + return func(runtime imv1.Runtime, shoot *gardener.Shoot) error { + for _, ext := range extensionsToApply { + gardenerExtension, err := ext.Factory(runtime, shoot) + if err != nil { + return err + } + + index := slices.IndexFunc(currentGardenerExtensions, func(e gardener.Extension) bool { + return e.Type == ext.Type + }) + + if index == -1 { + shoot.Spec.Extensions = append(shoot.Spec.Extensions, gardenerExtension) + } else { + shoot.Spec.Extensions[index] = gardenerExtension + } + } + + return nil + } +} diff --git a/pkg/gardener/shoot/extender/extensions/oidc.go b/pkg/gardener/shoot/extender/extensions/oidc.go new file mode 100644 index 00000000..3109f099 --- /dev/null +++ b/pkg/gardener/shoot/extender/extensions/oidc.go @@ -0,0 +1,17 @@ +package extensions + +import ( + gardener "github.com/gardener/gardener/pkg/apis/core/v1beta1" + "k8s.io/utils/ptr" +) + +const ( + OidcExtensionType = "shoot-oidc-service" +) + +func NewOIDCExtension() (gardener.Extension, error) { + return gardener.Extension{ + Type: OidcExtensionType, + Disabled: ptr.To(false), + }, nil +}