-
Notifications
You must be signed in to change notification settings - Fork 32
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
feat: configurable API Key K8s secret key name #488
base: main
Are you sure you want to change the base?
Changes from all commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.
Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -26,18 +26,20 @@ type APIKey struct { | |
Name string `yaml:"name"` | ||
LabelSelectors k8s_labels.Selector `yaml:"labelSelectors"` | ||
Namespace string `yaml:"namespace"` | ||
KeySelectors []string `yaml:"keySelectors"` | ||
|
||
secrets map[string]k8s.Secret | ||
mutex sync.RWMutex | ||
k8sClient k8s_client.Reader | ||
} | ||
|
||
func NewApiKeyIdentity(name string, labelSelectors k8s_labels.Selector, namespace string, authCred auth.AuthCredentials, k8sClient k8s_client.Reader, ctx context.Context) *APIKey { | ||
func NewApiKeyIdentity(name string, labelSelectors k8s_labels.Selector, namespace string, keySelectors []string, authCred auth.AuthCredentials, k8sClient k8s_client.Reader, ctx context.Context) *APIKey { | ||
apiKey := &APIKey{ | ||
AuthCredentials: authCred, | ||
Name: name, | ||
LabelSelectors: labelSelectors, | ||
Namespace: namespace, | ||
KeySelectors: append(keySelectors, apiKeySelector), | ||
secrets: make(map[string]k8s.Secret), | ||
k8sClient: k8sClient, | ||
} | ||
|
@@ -103,17 +105,19 @@ func (a *APIKey) AddK8sSecretBasedIdentity(ctx context.Context, new k8s.Secret) | |
logger := log.FromContext(ctx).WithName("apikey") | ||
|
||
// updating existing | ||
newAPIKeyValue := string(new.Data[apiKeySelector]) | ||
for oldAPIKeyValue, current := range a.secrets { | ||
if current.GetNamespace() == new.GetNamespace() && current.GetName() == new.GetName() { | ||
if oldAPIKeyValue != newAPIKeyValue { | ||
a.appendK8sSecretBasedIdentity(new) | ||
delete(a.secrets, oldAPIKeyValue) | ||
logger.V(1).Info("api key updated") | ||
} else { | ||
logger.V(1).Info("api key unchanged") | ||
for _, key := range a.KeySelectors { | ||
newAPIKeyValue := string(new.Data[key]) | ||
for oldAPIKeyValue, current := range a.secrets { | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I wonder if the struct shouldn't store 2 maps – WDYT? |
||
if current.GetNamespace() == new.GetNamespace() && current.GetName() == new.GetName() { | ||
if oldAPIKeyValue != newAPIKeyValue { | ||
a.appendK8sSecretBasedIdentity(new) | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. In the issue I said:
But I guess the part of making it easier to implement key rotation is not really true, is it? In order to properly support rotation, all keys in a Secret must be accepted, otherwise at the moment a new valid key is added to the secret, the old one is automatically deleted and stop being accepted. Should we add to the |
||
delete(a.secrets, oldAPIKeyValue) | ||
KevFan marked this conversation as resolved.
Show resolved
Hide resolved
|
||
logger.V(1).Info("api key updated") | ||
} else { | ||
logger.V(1).Info("api key unchanged") | ||
} | ||
return | ||
} | ||
return | ||
} | ||
} | ||
|
||
|
@@ -146,10 +150,13 @@ func (a *APIKey) withinScope(namespace string) bool { | |
// Appends the K8s Secret to the cache of API keys | ||
// Caution! This function is not thread-safe. Make sure to acquire a lock before calling it. | ||
func (a *APIKey) appendK8sSecretBasedIdentity(secret k8s.Secret) bool { | ||
value, isAPIKeySecret := secret.Data[apiKeySelector] | ||
if isAPIKeySecret && len(value) > 0 { | ||
a.secrets[string(value)] = secret | ||
return true | ||
for _, key := range a.KeySelectors { | ||
value, isAPIKeySecret := secret.Data[key] | ||
if isAPIKeySecret && len(value) > 0 { | ||
a.secrets[string(value)] = secret | ||
return true | ||
} | ||
} | ||
|
||
return false | ||
} |
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.
Minor suggestion:
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.
Sounds good 👍
On a related note, what's your thoughts on instead of doing this
append
, use the kubebuilder default annotation in the API struct instead? Theappend
works but this default value is hidden from the CRD, but not sure is this want we want in general