-
Notifications
You must be signed in to change notification settings - Fork 602
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Allow customers to specify roles that they want credentials for... #3854
Conversation
fe34050
to
400131c
Compare
pkg/apis/postgres-operator.crunchydata.com/v1beta1/crunchy_bridgecluster_types.go
Outdated
Show resolved
Hide resolved
// The name of the Secret that will hold the role credentials. | ||
// +kubebuilder:validation:Pattern=`^[a-z0-9]([-a-z0-9]*[a-z0-9])?$` | ||
// +kubebuilder:validation:Type=string | ||
SecretName string `json:"secretName"` |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
❓ Secret names are DNS subdomains. Is there a validation rule/shortcut for that?
🤔 We can start with a more limited rule (the one here) and expand it later.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I don't see a specific validation tag in the Kubebuilder docs...
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
According to this, the regex we want is [a-z0-9]([-a-z0-9]*[a-z0-9])?(\.[a-z0-9]([-a-z0-9]*[a-z0-9])?)*
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I would think that the kubebuilder:validation:Format
marker would accept an IsDNS1123Subdomain
option given that the kubebuilder codebase has functions written specifically for validating this, but it doesn't seem to work and I can't find any documentation for what options they actually accept for the "Format" validation...
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
AFAIK, format
comes from OpenAPIv3. I see references to JSON Schema Validation elsewhere. I'm also not sure what Kubernetes has implemented (or not).
-
https://kubernetes.io/docs/tasks/extend-kubernetes/custom-resources/custom-resource-definitions/#validation →
https://github.com/OAI/OpenAPI-Specification/blob/main/versions/3.0.0.md#schema-object →
https://github.com/OAI/OpenAPI-Specification/blob/main/versions/3.0.0.md#dataTypeFormat -
https://kubernetes.io/docs/tasks/extend-kubernetes/custom-resources/custom-resource-definitions/#validation-rules →
https://swagger.io/specification/#data-types →
https://tools.ietf.org/html/draft-bhutton-json-schema-validation-00#section-7.3
hostname
looks close, but I'm not excited by following 3–5 RFCs down to the early internet. :notsure:
I see the same regex you pasted when I look here. So that plus max-length sounds good to me.
775eaca
to
40a3e4d
Compare
internal/bridge/crunchybridgecluster/crunchybridgecluster_controller.go
Outdated
Show resolved
Hide resolved
internal/bridge/crunchybridgecluster/crunchybridgecluster_controller.go
Outdated
Show resolved
Hide resolved
internal/naming/selectors.go
Outdated
LabelCluster: cluster, | ||
}, | ||
MatchExpressions: []metav1.LabelSelectorRequirement{ | ||
{Key: LabelCrunchyBridgeClusterPostgresRole, Operator: metav1.LabelSelectorOpExists}, |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This seems fine to me, though might it be simpler to add
naming.LabelRole: RoleCrunchyBridgeClusterPostgresRole
to the MatchLabels?
pkg/apis/postgres-operator.crunchydata.com/v1beta1/crunchy_bridgecluster_types.go
Show resolved
Hide resolved
pkg/apis/postgres-operator.crunchydata.com/v1beta1/crunchy_bridgecluster_types.go
Show resolved
Hide resolved
…e CrunchyBridgeCluster spec. When specified, create corresponding Secret and fill with role name, password, and connection URI. If role is deleted from spec or secret name is changed, delete unused secret.
…equest and response payload structs. Add fields to CBC status.
…the same name. Rename some API fields. Use pointers for booleans so false values still show up. Other minor changes.
61b876d
to
7964f51
Compare
…alues accepted/returned by bridge API. Co-authored-by: Chris Bandy <[email protected]>
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This all makes sense to me, but I do wish we had some other solution for the secret name only because it seems kind of cumbersome for the operator to
(a) check for secret name uniqueness on the spec,
(b) check for secret name uniqueness in the namespace (ignoring secrets with certain labels -- heck, you could include that in this K8s API list action: list secrets that don't have certain selectors),
(c) and then get the secrets for this cluster to compare against the roles requested.
But I can't really see a way around it. My only other thoughts are
(a) "let's use a UUID" -- which make the secrets hard to use;
(b) "let's transform the disallowed characters from the PG role into allowed characters for K8s" -- which might just collide with another secret. (Unless we add the cluster as part of the secret, and even then, that's not 100% proof against collisions.)
So yeah, I have no other solutions, so won't block on this.
"k8s.io/apimachinery/pkg/api/resource" | ||
) | ||
|
||
func FromCPU(n int64) *resource.Quantity { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
We're not using this right now, are we?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
No, we're not. It would be useful if we ever decide to include CPU on the status... Not sure if I should keep it or just delete it for now.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yeah, I'm on the fence...
for i := range specRoles { | ||
if secretNames[specRoles[i].SecretName] { | ||
// Duplicate secretName found, return early with error | ||
err := errors.New("There are duplicate Role SecretNames in the spec. SecretNames must be unique.") |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I have a vague memory of us preferring fmt.Errorf
, let me check on that...
Yeah, I'm seeing more of that.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Okay, I can switch to using that.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Although when I search the repo I see 74 results for errors.New
and 55 results for fmt.Errorf
...
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Oh, good double-check, ok. I wonder why we prefer one over the other in some places?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Probably just the preference of whoever was writing the code...
in the CrunchyBridgeCluster spec. When specified, PGO will create/update a corresponding Secret and fill with role name, password, and connection URI during the reconcile loop. If role is deleted from spec or secret name is changed, PGO will delete unused secret.
Checklist:
Type of Changes:
What is the current behavior (link to any open issues here)?
There is no user/role functionality.
What is the new behavior (if this is a feature change)?
The customer can now add roles (that correspond to available roles in Bridge) to their spec and specify a secret name and get a Secret in their k8s cluster that contains that role's password and connection URI.
Other Information: