diff --git a/charts/postgres-operator-ui/templates/deployment.yaml b/charts/postgres-operator-ui/templates/deployment.yaml index 29bf2e670..9b5faea90 100644 --- a/charts/postgres-operator-ui/templates/deployment.yaml +++ b/charts/postgres-operator-ui/templates/deployment.yaml @@ -18,7 +18,7 @@ spec: labels: app.kubernetes.io/name: {{ template "postgres-operator-ui.name" . }} app.kubernetes.io/instance: {{ .Release.Name }} - team: "acid" # Parameterize? + team: "{{ join "," .Values.envs.teams }}" spec: serviceAccountName: {{ include "postgres-operator-ui.serviceAccountName" . }} {{- if .Values.imagePullSecrets }} @@ -54,7 +54,10 @@ spec: - name: "TEAMS" value: |- [ - "acid" + {{- range(initial .Values.envs.teams) }} + {{ . | quote }}, + {{- end }} + {{ last .Values.envs.teams | quote }} ] - name: "OPERATOR_UI_CONFIG" value: |- diff --git a/charts/postgres-operator-ui/values.yaml b/charts/postgres-operator-ui/values.yaml index 926d99b39..b8e147c05 100644 --- a/charts/postgres-operator-ui/values.yaml +++ b/charts/postgres-operator-ui/values.yaml @@ -15,7 +15,7 @@ image: # Secrets must be manually created in the namespace. # ref: https://kubernetes.io/docs/concepts/containers/images/#specifying-imagepullsecrets-on-a-pod # imagePullSecrets: -# - name: +# - name: rbac: # Specifies whether RBAC resources should be created @@ -45,6 +45,8 @@ envs: operatorClusterNameLabel: "cluster-name" resourcesVisible: "False" targetNamespace: "default" + teams: + - "acid" # configure UI service service: diff --git a/charts/postgres-operator/crds/operatorconfigurations.yaml b/charts/postgres-operator/crds/operatorconfigurations.yaml index d5af19e2d..0b9b56fb6 100644 --- a/charts/postgres-operator/crds/operatorconfigurations.yaml +++ b/charts/postgres-operator/crds/operatorconfigurations.yaml @@ -264,6 +264,9 @@ spec: secret_name_template: type: string default: "{username}.{cluster}.credentials.{tprkind}.{tprgroup}" + spilo_allow_privilege_escalation: + type: boolean + default: true spilo_runasuser: type: integer spilo_runasgroup: diff --git a/charts/postgres-operator/values-crd.yaml b/charts/postgres-operator/values-crd.yaml index b18c3a386..33fe83cb0 100644 --- a/charts/postgres-operator/values-crd.yaml +++ b/charts/postgres-operator/values-crd.yaml @@ -155,6 +155,9 @@ configKubernetes: # whether the Spilo container should run in privileged mode spilo_privileged: false + # whether the Spilo container should run with additional permissions other than parent. + # required by cron which needs setuid + spilo_allow_privilege_escalation: true # storage resize strategy, available options are: ebs, pvc, off storage_resize_mode: pvc # operator watches for postgres objects in the given namespace diff --git a/charts/postgres-operator/values.yaml b/charts/postgres-operator/values.yaml index 7669ec64a..20bdc405e 100644 --- a/charts/postgres-operator/values.yaml +++ b/charts/postgres-operator/values.yaml @@ -147,6 +147,9 @@ configKubernetes: # whether the Spilo container should run in privileged mode spilo_privileged: "false" + # whether the Spilo container should run with additional permissions other than parent. + # required by cron which needs setuid + spilo_allow_privilege_escalation: true # storage resize strategy, available options are: ebs, pvc, off storage_resize_mode: pvc # operator watches for postgres objects in the given namespace diff --git a/docs/reference/operator_parameters.md b/docs/reference/operator_parameters.md index 13402d15f..ace6eae81 100644 --- a/docs/reference/operator_parameters.md +++ b/docs/reference/operator_parameters.md @@ -374,6 +374,11 @@ configuration they are grouped under the `kubernetes` key. used for AWS volume resizing and not required if you don't need that capability. The default is `false`. +* **spilo_allow_privilege_escalation** + Controls whether a process can gain more privileges than its parent + process. Required by cron which needs setuid. Without this parameter, + certification rotation & backups will not be done. The default is `true`. + * **additional_pod_capabilities** list of additional capabilities to be added to the postgres container's SecurityContext (e.g. SYS_NICE etc.). Please, make sure first that the diff --git a/manifests/configmap.yaml b/manifests/configmap.yaml index 02803123a..6a98bbb48 100644 --- a/manifests/configmap.yaml +++ b/manifests/configmap.yaml @@ -114,6 +114,7 @@ data: secret_name_template: "{username}.{cluster}.credentials" # sidecar_docker_images: "" # set_memory_request_to_limit: "false" + spilo_allow_privilege_escalation: "true" # spilo_runasuser: 101 # spilo_runasgroup: 103 # spilo_fsgroup: 103 diff --git a/manifests/operatorconfiguration.crd.yaml b/manifests/operatorconfiguration.crd.yaml index 2c6d0ccac..2a2e4c980 100644 --- a/manifests/operatorconfiguration.crd.yaml +++ b/manifests/operatorconfiguration.crd.yaml @@ -260,6 +260,9 @@ spec: secret_name_template: type: string default: "{username}.{cluster}.credentials.{tprkind}.{tprgroup}" + spilo_allow_privilege_escalation: + type: boolean + default: true spilo_runasuser: type: integer spilo_runasgroup: diff --git a/manifests/postgresql-operator-default-configuration.yaml b/manifests/postgresql-operator-default-configuration.yaml index 535d9a4ea..39fa6bb48 100644 --- a/manifests/postgresql-operator-default-configuration.yaml +++ b/manifests/postgresql-operator-default-configuration.yaml @@ -79,6 +79,7 @@ configuration: # pod_service_account_role_binding_definition: "" pod_terminate_grace_period: 5m secret_name_template: "{username}.{cluster}.credentials.{tprkind}.{tprgroup}" + spilo_allow_privilege_escalation: true # spilo_runasuser: 101 # spilo_runasgroup: 103 # spilo_fsgroup: 103 diff --git a/pkg/apis/acid.zalan.do/v1/crds.go b/pkg/apis/acid.zalan.do/v1/crds.go index ef376653d..89d71eef5 100644 --- a/pkg/apis/acid.zalan.do/v1/crds.go +++ b/pkg/apis/acid.zalan.do/v1/crds.go @@ -1162,6 +1162,9 @@ var OperatorConfigCRDResourceValidation = apiextv1.CustomResourceValidation{ "spilo_privileged": { Type: "boolean", }, + "spilo_allow_privilege_escalation": { + Type: "boolean", + }, "storage_resize_mode": { Type: "string", Enum: []apiextv1.JSON{ diff --git a/pkg/apis/acid.zalan.do/v1/operator_configuration_type.go b/pkg/apis/acid.zalan.do/v1/operator_configuration_type.go index 5400e6f0e..3d40373ac 100644 --- a/pkg/apis/acid.zalan.do/v1/operator_configuration_type.go +++ b/pkg/apis/acid.zalan.do/v1/operator_configuration_type.go @@ -56,6 +56,7 @@ type KubernetesMetaConfiguration struct { PodServiceAccountRoleBindingDefinition string `json:"pod_service_account_role_binding_definition,omitempty"` PodTerminateGracePeriod Duration `json:"pod_terminate_grace_period,omitempty"` SpiloPrivileged bool `json:"spilo_privileged,omitempty"` + SpiloAllowPrivilegeEscalation bool `json:"spilo_allow_privilege_escalation,omitempty"` SpiloRunAsUser *int64 `json:"spilo_runasuser,omitempty"` SpiloRunAsGroup *int64 `json:"spilo_runasgroup,omitempty"` SpiloFSGroup *int64 `json:"spilo_fsgroup,omitempty"` diff --git a/pkg/cluster/k8sres.go b/pkg/cluster/k8sres.go index ae689d0f9..9d74cf77a 100644 --- a/pkg/cluster/k8sres.go +++ b/pkg/cluster/k8sres.go @@ -442,6 +442,7 @@ func generateContainer( envVars []v1.EnvVar, volumeMounts []v1.VolumeMount, privilegedMode bool, + privilegeEscalationMode bool, additionalPodCapabilities *v1.Capabilities, ) *v1.Container { return &v1.Container{ @@ -466,7 +467,7 @@ func generateContainer( VolumeMounts: volumeMounts, Env: envVars, SecurityContext: &v1.SecurityContext{ - AllowPrivilegeEscalation: &privilegedMode, + AllowPrivilegeEscalation: &privilegeEscalationMode, Privileged: &privilegedMode, ReadOnlyRootFilesystem: util.False(), Capabilities: additionalPodCapabilities, @@ -1162,6 +1163,7 @@ func (c *Cluster) generateStatefulSet(spec *acidv1.PostgresSpec) (*appsv1.Statef deduplicateEnvVars(spiloEnvVars, c.containerName(), c.logger), volumeMounts, c.OpConfig.Resources.SpiloPrivileged, + c.OpConfig.Resources.SpiloAllowPrivilegeEscalation, generateCapabilities(c.OpConfig.AdditionalPodCapabilities), ) @@ -1915,6 +1917,7 @@ func (c *Cluster) generateLogicalBackupJob() (*batchv1beta1.CronJob, error) { envVars, []v1.VolumeMount{}, c.OpConfig.SpiloPrivileged, // use same value as for normal DB pods + c.OpConfig.SpiloAllowPrivilegeEscalation, nil, ) diff --git a/pkg/controller/operator_config.go b/pkg/controller/operator_config.go index 85890c022..4388110db 100644 --- a/pkg/controller/operator_config.go +++ b/pkg/controller/operator_config.go @@ -68,6 +68,7 @@ func (c *Controller) importConfigurationFromCRD(fromCRD *acidv1.OperatorConfigur result.PodEnvironmentSecret = fromCRD.Kubernetes.PodEnvironmentSecret result.PodTerminateGracePeriod = util.CoalesceDuration(time.Duration(fromCRD.Kubernetes.PodTerminateGracePeriod), "5m") result.SpiloPrivileged = fromCRD.Kubernetes.SpiloPrivileged + result.SpiloAllowPrivilegeEscalation = fromCRD.Kubernetes.SpiloAllowPrivilegeEscalation result.SpiloRunAsUser = fromCRD.Kubernetes.SpiloRunAsUser result.SpiloRunAsGroup = fromCRD.Kubernetes.SpiloRunAsGroup result.SpiloFSGroup = fromCRD.Kubernetes.SpiloFSGroup diff --git a/pkg/util/config/config.go b/pkg/util/config/config.go index 10e2b35c0..356ad60ba 100644 --- a/pkg/util/config/config.go +++ b/pkg/util/config/config.go @@ -34,6 +34,7 @@ type Resources struct { PodPriorityClassName string `name:"pod_priority_class_name"` ClusterDomain string `name:"cluster_domain" default:"cluster.local"` SpiloPrivileged bool `name:"spilo_privileged" default:"false"` + SpiloAllowPrivilegeEscalation bool `name:"spilo_allow_privilege_escalation" default:"false"` AdditionalPodCapabilities []string `name:"additional_pod_capabilities" default:""` ClusterLabels map[string]string `name:"cluster_labels" default:"application:spilo"` InheritedLabels []string `name:"inherited_labels" default:""`