Skip to content

Commit

Permalink
feat(kuma-cp): allow missing transparent proxy ConfigMap or empty in k8s
Browse files Browse the repository at this point in the history
Until now you couldn't delete the default transparent proxy
configuration ConfigMap when `transparentProxy.configMap.enabled` was
set. You also couldn't have `transparentProxy.configMap.config` empty
during installation as it would automatically disable this feature.

This commit changes this behavior and allows empty ConfigMaps or
deletions of them, so if you want to enable this feature, but don't want
to initially have anything specified in the configuration now you can.

Signed-off-by: Bart Smykla <[email protected]>
  • Loading branch information
bartsmykla committed Nov 7, 2024
1 parent 409f75c commit af8e27d
Show file tree
Hide file tree
Showing 3 changed files with 49 additions and 59 deletions.
2 changes: 1 addition & 1 deletion deployments/charts/kuma/templates/_helpers.tpl
Original file line number Diff line number Diff line change
Expand Up @@ -265,7 +265,7 @@ env:
- name: KUMA_RUNTIME_KUBERNETES_INJECTOR_BUILTIN_DNS_LOGGING
value: "true"
{{- end }}
{{- if and .Values.transparentProxy.configMap.enabled .Values.transparentProxy.configMap.config }}
{{- if .Values.transparentProxy.configMap.enabled }}
- name: KUMA_RUNTIME_KUBERNETES_INJECTOR_TRANSPARENT_PROXY_CONFIGMAP_NAME
value: {{ include "kuma.transparentProxyConfigMapName" . | quote }}
{{- end }}
Expand Down
4 changes: 3 additions & 1 deletion deployments/charts/kuma/templates/cp-configmap.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -31,7 +31,7 @@ data:
{{- end }}
{{- end }}
{{- end }}
{{- if and .Values.transparentProxy.configMap.enabled .Values.transparentProxy.configMap.config }}
{{- if .Values.transparentProxy.configMap.enabled }}
---
apiVersion: v1
kind: ConfigMap
Expand All @@ -42,5 +42,7 @@ metadata:
{{- $kumaCpLabels | nindent 4 }}
data:
config.yaml: |
{{- if .Values.transparentProxy.configMap.config }}
{{- .Values.transparentProxy.configMap.config | toYaml | nindent 4 }}
{{- end }}
{{- end }}
102 changes: 45 additions & 57 deletions pkg/plugins/runtime/k8s/webhooks/injector/injector.go
Original file line number Diff line number Diff line change
Expand Up @@ -144,7 +144,8 @@ func (i *KumaInjector) InjectKuma(ctx context.Context, pod *kube_core.Pod) error
var injectedInitContainer *kube_core.Container

if i.cfg.TransparentProxyConfigMapName != "" {
tproxyCfg, err := i.getTransparentProxyConfig(ctx, logger, pod)
tproxyCfgConfigMap := i.getTransparentProxyConfig(ctx, logger, pod)
tproxyCfg, err := tproxy_k8s.ConfigForKubernetes(tproxyCfgConfigMap, i.cfg, pod.Annotations, logger)
if err != nil {
return err
}
Expand Down Expand Up @@ -366,93 +367,80 @@ func (i *KumaInjector) getTransparentProxyConfig(
ctx context.Context,
logger logr.Logger,
pod *kube_core.Pod,
) (tproxy_config.Config, error) {
// Skip if the TransparentProxyConfigMapName is not specified in the runtime configuration
) tproxy_config.Config {
if i.cfg.TransparentProxyConfigMapName == "" {
return tproxy_config.Config{}, nil
}

getConfigFromAnnotation := func(name, namespace string) (tproxy_config.Config, bool) {
v, err := i.getTransparentProxyConfigMap(ctx, logger, pod, name, namespace)
if err != nil {
logger.V(1).Info(
"[WARNING]: failed to retrieve transparent proxy config from the ConfigMap specified by annotation",
"annotation", metadata.KumaTrafficTransparentProxyConfigMapName,
"configMapName", name,
"configMapNamespace", namespace,
"error", err,
)

return tproxy_config.Config{}, false
}

return v, true
return tproxy_config.DefaultConfig()
}

// Try to fetch config using the annotation-specified ConfigMap name
if v := pod.Annotations[metadata.KumaTrafficTransparentProxyConfigMapName]; v != "" {
if c, ok := getConfigFromAnnotation(v, pod.Namespace); ok {
return c, nil
if c, err := i.getTransparentProxyConfigMap(ctx, v, pod.Namespace, logger, "annotation"); err == nil {
return c
}

if c, ok := getConfigFromAnnotation(v, i.systemNamespace); ok {
return c, nil
if c, err := i.getTransparentProxyConfigMap(ctx, v, i.systemNamespace, logger, "annotation"); err == nil {
return c
}
}

// Fallback to fetching config using the runtime-specified ConfigMap name
return i.getTransparentProxyConfigMap(
if c, err := i.getTransparentProxyConfigMap(
ctx,
logger,
pod,
i.cfg.TransparentProxyConfigMapName,
i.systemNamespace,
)
logger,
"controlPlaneRuntimeConfig",
); err == nil {
return c
}

return tproxy_config.DefaultConfig()
}

func (i *KumaInjector) getTransparentProxyConfigMap(
ctx context.Context,
logger logr.Logger,
pod *kube_core.Pod,
name string,
namespace string,
logger logr.Logger,
source string,
) (tproxy_config.Config, error) {
var err error
defer func() {
if err != nil {
logger.V(1).Info(
"[WARNING]: unable to retrieve transparent proxy configuration from ConfigMap; applying default configuration",
"configMapName", name,
"configMapNamespace", namespace,
"configMapSource", source,
"error", err,
)
}
}()

cfg := tproxy_config.DefaultConfig()
loader := core_config.NewLoader(&cfg)
namespacedName := kube_types.NamespacedName{Name: name, Namespace: namespace}

var cm kube_core.ConfigMap
if err := i.client.Get(ctx, namespacedName, &cm); err != nil {
return tproxy_config.Config{}, errors.Wrapf(
err,
"failed to retrieve ConfigMap %q in namespace %q",
name,
namespace,
)
if err = i.client.Get(ctx, namespacedName, &cm); err != nil {
return tproxy_config.Config{}, err
}

switch c := cm.Data[tproxy_consts.KubernetesConfigMapDataKey]; c {
case "":
return tproxy_config.Config{}, errors.Errorf(
"ConfigMap %q in namespace %q is missing the required key %q",
name,
namespace,
tproxy_consts.KubernetesConfigMapDataKey,
)
default:
if err := loader.LoadBytes([]byte(c)); err != nil {
return tproxy_config.Config{}, errors.Wrapf(
err,
"failed to load transparent proxy configuration from ConfigMap %q in namespace %q",
name,
namespace,
)
if c := cm.Data[tproxy_consts.KubernetesConfigMapDataKey]; c != "" {
if err = loader.LoadBytes([]byte(c)); err != nil {
return tproxy_config.Config{}, err
}

return cfg, nil
}

return tproxy_k8s.ConfigForKubernetes(cfg, i.cfg, pod.Annotations, logger)
err = errors.Errorf(
"key '%s' is missing or empty",
tproxy_consts.KubernetesConfigMapDataKey,
)

return tproxy_config.Config{}, err
}


// applyCustomPatches applies the block of patches to the given container and returns a new,
// patched container. If patch list is empty, the same unaltered container is returned.
func (i *KumaInjector) applyCustomPatches(
Expand Down

0 comments on commit af8e27d

Please sign in to comment.