better backwards compatibility with old DNS name format for LBs (#2171)

* better backwards compatibility with legacy DNS name format for LBs
* improve docs on DNS string
This commit is contained in:
Felix Kunde 2023-01-17 10:06:11 +01:00 committed by GitHub
parent ce1fee8586
commit 28cd2f188a
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
12 changed files with 110 additions and 42 deletions

View File

@ -434,9 +434,15 @@ spec:
master_dns_name_format:
type: string
default: "{cluster}.{namespace}.{hostedzone}"
master_legacy_dns_name_format:
type: string
default: "{cluster}.{team}.{hostedzone}"
replica_dns_name_format:
type: string
default: "{cluster}-repl.{namespace}.{hostedzone}"
replica_legacy_dns_name_format:
type: string
default: "{cluster}-repl.{team}.{hostedzone}"
aws_or_gcp:
type: object
properties:

View File

@ -277,8 +277,12 @@ configLoadBalancer:
external_traffic_policy: "Cluster"
# defines the DNS name string template for the master load balancer cluster
master_dns_name_format: "{cluster}.{namespace}.{hostedzone}"
# deprecated DNS template for master load balancer using team name
master_legacy_dns_name_format: "{cluster}.{team}.{hostedzone}"
# defines the DNS name string template for the replica load balancer cluster
replica_dns_name_format: "{cluster}-repl.{namespace}.{hostedzone}"
# deprecated DNS template for replica load balancer using team name
replica_legacy_dns_name_format: "{cluster}-repl.{team}.{hostedzone}"
# options to aid debugging of the operator itself
configDebug:

View File

@ -627,22 +627,47 @@ In the CRD-based configuration they are grouped under the `load_balancer` key.
the cluster. Can be overridden by individual cluster settings. The default
is `false`.
* **external_traffic_policy** defines external traffic policy for load
* **external_traffic_policy**
defines external traffic policy for load
balancers. Allowed values are `Cluster` (default) and `Local`.
* **master_dns_name_format** defines the DNS name string template for the
master load balancer cluster. The default is
`{cluster}.{namespace}.{hostedzone}`, where `{cluster}` is replaced by the cluster
name, `{namespace}` is replaced with the namespace and `{hostedzone}` is replaced
with the hosted zone (the value of the `db_hosted_zone` parameter). No other
placeholders are allowed.
* **master_dns_name_format**
defines the DNS name string template for the master load balancer cluster.
The default is `{cluster}.{namespace}.{hostedzone}`, where `{cluster}` is
replaced by the cluster name, `{namespace}` is replaced with the namespace
and `{hostedzone}` is replaced with the hosted zone (the value of the
`db_hosted_zone` parameter). The `{team}` placeholder can still be used,
although it is not recommened because the team of a cluster can change.
If the cluster name starts with the `teamId` it will also be part of the
DNS, aynway. No other placeholders are allowed!
* **replica_dns_name_format** defines the DNS name string template for the
replica load balancer cluster. The default is
`{cluster}-repl.{namespace}.{hostedzone}`, where `{cluster}` is replaced by the
cluster name, `{namespace}` is replaced with the namespace and `{hostedzone}` is
replaced with the hosted zone (the value of the `db_hosted_zone` parameter).
No other placeholders are allowed.
* **master_legacy_dns_name_format**
*deprecated* default master DNS template `{cluster}.{team}.{hostedzone}` as
of pre `v1.9.0`. If cluster name starts with `teamId` then a second DNS
entry will be created using the template defined here to provide backwards
compatibility. The `teamId` prefix will be extracted from the clustername
because it follows later in the DNS string. When using a customized
`master_dns_name_format` make sure to define the legacy DNS format when
switching to v1.9.0.
* **replica_dns_name_format**
defines the DNS name string template for the replica load balancer cluster.
The default is `{cluster}-repl.{namespace}.{hostedzone}`, where `{cluster}`
is replaced by the cluster name, `{namespace}` is replaced with the
namespace and `{hostedzone}` is replaced with the hosted zone (the value of
the `db_hosted_zone` parameter). The `{team}` placeholder can still be used,
although it is not recommened because the team of a cluster can change.
If the cluster name starts with the `teamId` it will also be part of the
DNS, aynway. No other placeholders are allowed!
* **replica_legacy_dns_name_format**
*deprecated* default master DNS template `{cluster}-repl.{team}.{hostedzone}`
as of pre `v1.9.0`. If cluster name starts with `teamId` then a second DNS
entry will be created using the template defined here to provide backwards
compatibility. The `teamId` prefix will be extracted from the clustername
because it follows later in the DNS string. When using a customized
`master_dns_name_format` make sure to define the legacy DNS format when
switching to v1.9.0.
## AWS or GCP interaction

View File

@ -97,6 +97,7 @@ data:
major_version_upgrade_mode: "manual"
# major_version_upgrade_team_allow_list: ""
master_dns_name_format: "{cluster}.{namespace}.{hostedzone}"
# master_legacy_dns_name_format: "{cluster}.{team}.{hostedzone}"
# master_pod_move_timeout: 20m
# max_instances: "-1"
# min_instances: "-1"
@ -135,6 +136,7 @@ data:
ready_wait_timeout: 30s
repair_period: 5m
replica_dns_name_format: "{cluster}-repl.{namespace}.{hostedzone}"
# replica_legacy_dns_name_format: "{cluster}-repl.{team}.{hostedzone}"
replication_username: standby
resource_check_interval: 3s
resource_check_timeout: 10m

View File

@ -432,9 +432,15 @@ spec:
master_dns_name_format:
type: string
default: "{cluster}.{namespace}.{hostedzone}"
master_legacy_dns_name_format:
type: string
default: "{cluster}.{team}.{hostedzone}"
replica_dns_name_format:
type: string
default: "{cluster}-repl.{namespace}.{hostedzone}"
replica_legacy_dns_name_format:
type: string
default: "{cluster}-repl.{team}.{hostedzone}"
aws_or_gcp:
type: object
properties:

View File

@ -137,7 +137,9 @@ configuration:
enable_replica_pooler_load_balancer: false
external_traffic_policy: "Cluster"
master_dns_name_format: "{cluster}.{namespace}.{hostedzone}"
# master_legacy_dns_name_format: "{cluster}.{team}.{hostedzone}"
replica_dns_name_format: "{cluster}-repl.{namespace}.{hostedzone}"
# replica_dns_old_name_format: "{cluster}-repl.{team}.{hostedzone}"
aws_or_gcp:
# additional_secret_mount: "some-secret-name"
# additional_secret_mount_path: "/some/dir"

View File

@ -1594,9 +1594,15 @@ var OperatorConfigCRDResourceValidation = apiextv1.CustomResourceValidation{
"master_dns_name_format": {
Type: "string",
},
"master_legacy_dns_name_format": {
Type: "string",
},
"replica_dns_name_format": {
Type: "string",
},
"replica_legacy_dns_name_format": {
Type: "string",
},
},
},
"aws_or_gcp": {

View File

@ -137,7 +137,9 @@ type LoadBalancerConfiguration struct {
EnableReplicaPoolerLoadBalancer bool `json:"enable_replica_pooler_load_balancer,omitempty"`
CustomServiceAnnotations map[string]string `json:"custom_service_annotations,omitempty"`
MasterDNSNameFormat config.StringTemplate `json:"master_dns_name_format,omitempty"`
MasterLegacyDNSNameFormat config.StringTemplate `json:"master_legacy_dns_name_format,omitempty"`
ReplicaDNSNameFormat config.StringTemplate `json:"replica_dns_name_format,omitempty"`
ReplicaLegacyDNSNameFormat config.StringTemplate `json:"replica_legacy_dns_name_format,omitempty"`
ExternalTrafficPolicy string `json:"external_traffic_policy" default:"Cluster"`
}

View File

@ -549,7 +549,7 @@ func TestServiceAnnotations(t *testing.T) {
operatorAnnotations: make(map[string]string),
serviceAnnotations: make(map[string]string),
expect: map[string]string{
"external-dns.alpha.kubernetes.io/hostname": "acid-test.test.db.example.com,test.acid.db.example.com",
"external-dns.alpha.kubernetes.io/hostname": "acid-test-stg.test.db.example.com,test-stg.acid.db.example.com",
"service.beta.kubernetes.io/aws-load-balancer-connection-idle-timeout": "3600",
},
},
@ -571,7 +571,7 @@ func TestServiceAnnotations(t *testing.T) {
operatorAnnotations: make(map[string]string),
serviceAnnotations: make(map[string]string),
expect: map[string]string{
"external-dns.alpha.kubernetes.io/hostname": "acid-test.test.db.example.com,test.acid.db.example.com",
"external-dns.alpha.kubernetes.io/hostname": "acid-test-stg.test.db.example.com,test-stg.acid.db.example.com",
"service.beta.kubernetes.io/aws-load-balancer-connection-idle-timeout": "3600",
},
},
@ -583,7 +583,7 @@ func TestServiceAnnotations(t *testing.T) {
operatorAnnotations: make(map[string]string),
serviceAnnotations: map[string]string{"foo": "bar"},
expect: map[string]string{
"external-dns.alpha.kubernetes.io/hostname": "acid-test.test.db.example.com,test.acid.db.example.com",
"external-dns.alpha.kubernetes.io/hostname": "acid-test-stg.test.db.example.com,test-stg.acid.db.example.com",
"service.beta.kubernetes.io/aws-load-balancer-connection-idle-timeout": "3600",
"foo": "bar",
},
@ -606,7 +606,7 @@ func TestServiceAnnotations(t *testing.T) {
operatorAnnotations: map[string]string{"foo": "bar"},
serviceAnnotations: make(map[string]string),
expect: map[string]string{
"external-dns.alpha.kubernetes.io/hostname": "acid-test.test.db.example.com,test.acid.db.example.com",
"external-dns.alpha.kubernetes.io/hostname": "acid-test-stg.test.db.example.com,test-stg.acid.db.example.com",
"service.beta.kubernetes.io/aws-load-balancer-connection-idle-timeout": "3600",
"foo": "bar",
},
@ -621,7 +621,7 @@ func TestServiceAnnotations(t *testing.T) {
},
serviceAnnotations: make(map[string]string),
expect: map[string]string{
"external-dns.alpha.kubernetes.io/hostname": "acid-test.test.db.example.com,test.acid.db.example.com",
"external-dns.alpha.kubernetes.io/hostname": "acid-test-stg.test.db.example.com,test-stg.acid.db.example.com",
"service.beta.kubernetes.io/aws-load-balancer-connection-idle-timeout": "1800",
},
},
@ -635,7 +635,7 @@ func TestServiceAnnotations(t *testing.T) {
"service.beta.kubernetes.io/aws-load-balancer-connection-idle-timeout": "1800",
},
expect: map[string]string{
"external-dns.alpha.kubernetes.io/hostname": "acid-test.test.db.example.com,test.acid.db.example.com",
"external-dns.alpha.kubernetes.io/hostname": "acid-test-stg.test.db.example.com,test-stg.acid.db.example.com",
"service.beta.kubernetes.io/aws-load-balancer-connection-idle-timeout": "1800",
},
},
@ -649,7 +649,7 @@ func TestServiceAnnotations(t *testing.T) {
"external-dns.alpha.kubernetes.io/hostname": "wrong.external-dns-name.example.com",
},
expect: map[string]string{
"external-dns.alpha.kubernetes.io/hostname": "acid-test.test.db.example.com,test.acid.db.example.com",
"external-dns.alpha.kubernetes.io/hostname": "acid-test-stg.test.db.example.com,test-stg.acid.db.example.com",
"service.beta.kubernetes.io/aws-load-balancer-connection-idle-timeout": "3600",
},
},
@ -661,7 +661,7 @@ func TestServiceAnnotations(t *testing.T) {
serviceAnnotations: make(map[string]string),
operatorAnnotations: make(map[string]string),
expect: map[string]string{
"external-dns.alpha.kubernetes.io/hostname": "acid-test.test.db.example.com,test.acid.db.example.com",
"external-dns.alpha.kubernetes.io/hostname": "acid-test-stg.test.db.example.com,test-stg.acid.db.example.com",
"service.beta.kubernetes.io/aws-load-balancer-connection-idle-timeout": "3600",
},
},
@ -679,7 +679,7 @@ func TestServiceAnnotations(t *testing.T) {
"service.beta.kubernetes.io/aws-load-balancer-connection-idle-timeout": "2000",
},
expect: map[string]string{
"external-dns.alpha.kubernetes.io/hostname": "acid-test.test.db.example.com,test.acid.db.example.com",
"external-dns.alpha.kubernetes.io/hostname": "acid-test-stg.test.db.example.com,test-stg.acid.db.example.com",
"service.beta.kubernetes.io/aws-load-balancer-nlb-target-type": "ip",
"service.beta.kubernetes.io/aws-load-balancer-connection-idle-timeout": "2000",
},
@ -704,7 +704,7 @@ func TestServiceAnnotations(t *testing.T) {
operatorAnnotations: make(map[string]string),
serviceAnnotations: make(map[string]string),
expect: map[string]string{
"external-dns.alpha.kubernetes.io/hostname": "acid-test-repl.test.db.example.com,test-repl.acid.db.example.com",
"external-dns.alpha.kubernetes.io/hostname": "acid-test-stg-repl.test.db.example.com,test-stg-repl.acid.db.example.com",
"service.beta.kubernetes.io/aws-load-balancer-connection-idle-timeout": "3600",
},
},
@ -726,7 +726,7 @@ func TestServiceAnnotations(t *testing.T) {
operatorAnnotations: make(map[string]string),
serviceAnnotations: make(map[string]string),
expect: map[string]string{
"external-dns.alpha.kubernetes.io/hostname": "acid-test-repl.test.db.example.com,test-repl.acid.db.example.com",
"external-dns.alpha.kubernetes.io/hostname": "acid-test-stg-repl.test.db.example.com,test-stg-repl.acid.db.example.com",
"service.beta.kubernetes.io/aws-load-balancer-connection-idle-timeout": "3600",
},
},
@ -738,7 +738,7 @@ func TestServiceAnnotations(t *testing.T) {
operatorAnnotations: make(map[string]string),
serviceAnnotations: map[string]string{"foo": "bar"},
expect: map[string]string{
"external-dns.alpha.kubernetes.io/hostname": "acid-test-repl.test.db.example.com,test-repl.acid.db.example.com",
"external-dns.alpha.kubernetes.io/hostname": "acid-test-stg-repl.test.db.example.com,test-stg-repl.acid.db.example.com",
"service.beta.kubernetes.io/aws-load-balancer-connection-idle-timeout": "3600",
"foo": "bar",
},
@ -761,7 +761,7 @@ func TestServiceAnnotations(t *testing.T) {
operatorAnnotations: map[string]string{"foo": "bar"},
serviceAnnotations: make(map[string]string),
expect: map[string]string{
"external-dns.alpha.kubernetes.io/hostname": "acid-test-repl.test.db.example.com,test-repl.acid.db.example.com",
"external-dns.alpha.kubernetes.io/hostname": "acid-test-stg-repl.test.db.example.com,test-stg-repl.acid.db.example.com",
"service.beta.kubernetes.io/aws-load-balancer-connection-idle-timeout": "3600",
"foo": "bar",
},
@ -776,7 +776,7 @@ func TestServiceAnnotations(t *testing.T) {
},
serviceAnnotations: make(map[string]string),
expect: map[string]string{
"external-dns.alpha.kubernetes.io/hostname": "acid-test-repl.test.db.example.com,test-repl.acid.db.example.com",
"external-dns.alpha.kubernetes.io/hostname": "acid-test-stg-repl.test.db.example.com,test-stg-repl.acid.db.example.com",
"service.beta.kubernetes.io/aws-load-balancer-connection-idle-timeout": "1800",
},
},
@ -790,7 +790,7 @@ func TestServiceAnnotations(t *testing.T) {
"service.beta.kubernetes.io/aws-load-balancer-connection-idle-timeout": "1800",
},
expect: map[string]string{
"external-dns.alpha.kubernetes.io/hostname": "acid-test-repl.test.db.example.com,test-repl.acid.db.example.com",
"external-dns.alpha.kubernetes.io/hostname": "acid-test-stg-repl.test.db.example.com,test-stg-repl.acid.db.example.com",
"service.beta.kubernetes.io/aws-load-balancer-connection-idle-timeout": "1800",
},
},
@ -804,7 +804,7 @@ func TestServiceAnnotations(t *testing.T) {
"external-dns.alpha.kubernetes.io/hostname": "wrong.external-dns-name.example.com",
},
expect: map[string]string{
"external-dns.alpha.kubernetes.io/hostname": "acid-test-repl.test.db.example.com,test-repl.acid.db.example.com",
"external-dns.alpha.kubernetes.io/hostname": "acid-test-stg-repl.test.db.example.com,test-stg-repl.acid.db.example.com",
"service.beta.kubernetes.io/aws-load-balancer-connection-idle-timeout": "3600",
},
},
@ -816,7 +816,7 @@ func TestServiceAnnotations(t *testing.T) {
serviceAnnotations: make(map[string]string),
operatorAnnotations: make(map[string]string),
expect: map[string]string{
"external-dns.alpha.kubernetes.io/hostname": "acid-test-repl.test.db.example.com,test-repl.acid.db.example.com",
"external-dns.alpha.kubernetes.io/hostname": "acid-test-stg-repl.test.db.example.com,test-stg-repl.acid.db.example.com",
"service.beta.kubernetes.io/aws-load-balancer-connection-idle-timeout": "3600",
},
},
@ -834,7 +834,7 @@ func TestServiceAnnotations(t *testing.T) {
"service.beta.kubernetes.io/aws-load-balancer-connection-idle-timeout": "2000",
},
expect: map[string]string{
"external-dns.alpha.kubernetes.io/hostname": "acid-test-repl.test.db.example.com,test-repl.acid.db.example.com",
"external-dns.alpha.kubernetes.io/hostname": "acid-test-stg-repl.test.db.example.com,test-stg-repl.acid.db.example.com",
"service.beta.kubernetes.io/aws-load-balancer-nlb-target-type": "ip",
"service.beta.kubernetes.io/aws-load-balancer-connection-idle-timeout": "2000",
},
@ -867,8 +867,10 @@ func TestServiceAnnotations(t *testing.T) {
cl.OpConfig.CustomServiceAnnotations = tt.operatorAnnotations
cl.OpConfig.EnableMasterLoadBalancer = tt.enableMasterLoadBalancerOC
cl.OpConfig.EnableReplicaLoadBalancer = tt.enableReplicaLoadBalancerOC
cl.OpConfig.MasterDNSNameFormat = "{cluster}.{namespace}.{hostedzone}"
cl.OpConfig.ReplicaDNSNameFormat = "{cluster}-repl.{namespace}.{hostedzone}"
cl.OpConfig.MasterDNSNameFormat = "{cluster}-stg.{namespace}.{hostedzone}"
cl.OpConfig.MasterLegacyDNSNameFormat = "{cluster}-stg.{team}.{hostedzone}"
cl.OpConfig.ReplicaDNSNameFormat = "{cluster}-stg-repl.{namespace}.{hostedzone}"
cl.OpConfig.ReplicaLegacyDNSNameFormat = "{cluster}-stg-repl.{team}.{hostedzone}"
cl.OpConfig.DbHostedZone = "db.example.com"
cl.Postgresql.Spec.ClusterName = ""

View File

@ -506,7 +506,7 @@ func (c *Cluster) roleLabelsSet(shouldAddExtraLabels bool, role PostgresRole) la
}
func (c *Cluster) dnsName(role PostgresRole) string {
var dnsString string
var dnsString, oldDnsString string
if role == Master {
dnsString = c.masterDNSName()
@ -517,10 +517,12 @@ func (c *Cluster) dnsName(role PostgresRole) string {
// if cluster name starts with teamID we might need to provide backwards compatibility
clusterNameWithoutTeamPrefix, _ := acidv1.ExtractClusterName(c.Name, c.Spec.TeamID)
if clusterNameWithoutTeamPrefix != "" {
if role == Replica {
clusterNameWithoutTeamPrefix = fmt.Sprintf("%s-repl", clusterNameWithoutTeamPrefix)
if role == Master {
oldDnsString = c.oldMasterDNSName(clusterNameWithoutTeamPrefix)
} else {
oldDnsString = c.oldReplicaDNSName(clusterNameWithoutTeamPrefix)
}
dnsString = fmt.Sprintf("%s,%s", dnsString, c.oldDNSFormat(clusterNameWithoutTeamPrefix))
dnsString = fmt.Sprintf("%s,%s", dnsString, oldDnsString)
}
return dnsString
@ -542,11 +544,18 @@ func (c *Cluster) replicaDNSName() string {
"hostedzone", c.OpConfig.DbHostedZone))
}
func (c *Cluster) oldDNSFormat(clusterName string) string {
return fmt.Sprintf("%s.%s.%s",
clusterName,
c.teamName(),
c.OpConfig.DbHostedZone)
func (c *Cluster) oldMasterDNSName(clusterName string) string {
return strings.ToLower(c.OpConfig.MasterLegacyDNSNameFormat.Format(
"cluster", clusterName,
"team", c.teamName(),
"hostedzone", c.OpConfig.DbHostedZone))
}
func (c *Cluster) oldReplicaDNSName(clusterName string) string {
return strings.ToLower(c.OpConfig.ReplicaLegacyDNSNameFormat.Format(
"cluster", clusterName,
"team", c.teamName(),
"hostedzone", c.OpConfig.DbHostedZone))
}
func (c *Cluster) credentialSecretName(username string) string {

View File

@ -154,7 +154,9 @@ func (c *Controller) importConfigurationFromCRD(fromCRD *acidv1.OperatorConfigur
result.EnableReplicaPoolerLoadBalancer = fromCRD.LoadBalancer.EnableReplicaPoolerLoadBalancer
result.CustomServiceAnnotations = fromCRD.LoadBalancer.CustomServiceAnnotations
result.MasterDNSNameFormat = fromCRD.LoadBalancer.MasterDNSNameFormat
result.MasterLegacyDNSNameFormat = fromCRD.LoadBalancer.MasterLegacyDNSNameFormat
result.ReplicaDNSNameFormat = fromCRD.LoadBalancer.ReplicaDNSNameFormat
result.ReplicaLegacyDNSNameFormat = fromCRD.LoadBalancer.ReplicaLegacyDNSNameFormat
result.ExternalTrafficPolicy = util.Coalesce(fromCRD.LoadBalancer.ExternalTrafficPolicy, "Cluster")
// AWS or GCP config

View File

@ -215,7 +215,9 @@ type Config struct {
EnableLoadBalancer *bool `name:"enable_load_balancer"` // deprecated and kept for backward compatibility
ExternalTrafficPolicy string `name:"external_traffic_policy" default:"Cluster"`
MasterDNSNameFormat StringTemplate `name:"master_dns_name_format" default:"{cluster}.{namespace}.{hostedzone}"`
MasterLegacyDNSNameFormat StringTemplate `name:"master_legacy_dns_name_format" default:"{cluster}.{team}.{hostedzone}"`
ReplicaDNSNameFormat StringTemplate `name:"replica_dns_name_format" default:"{cluster}-repl.{namespace}.{hostedzone}"`
ReplicaLegacyDNSNameFormat StringTemplate `name:"replica_legacy_dns_name_format" default:"{cluster}-repl.{team}.{hostedzone}"`
PDBNameFormat StringTemplate `name:"pdb_name_format" default:"postgres-{cluster}-pdb"`
EnablePodDisruptionBudget *bool `name:"enable_pod_disruption_budget" default:"true"`
EnableInitContainers *bool `name:"enable_init_containers" default:"true"`