Skip to content

feat(shield): drop nodes/proxy from host-shield ClusterRole, gate kubelet log access on Live Logs#2608

Draft
francesco-furlan wants to merge 2 commits intomainfrom
smagent-10349-drop-nodes-proxy-host-shield
Draft

feat(shield): drop nodes/proxy from host-shield ClusterRole, gate kubelet log access on Live Logs#2608
francesco-furlan wants to merge 2 commits intomainfrom
smagent-10349-drop-nodes-proxy-host-shield

Conversation

@francesco-furlan
Copy link
Copy Markdown
Contributor

What this PR does / why we need it

Removes the unconditional nodes/proxy grant from the host-shield ClusterRole — it's been flagged as a Remote Code Execution vector by security scans because it proxies arbitrary requests to the kubelet API. The grant is replaced with a feature-gated, version-aware kubelet-log subresource that fires only when Live Logs is on.

Behaviour matrix

features.investigations.live_logs.enabled K8s ≥ 1.36 K8s < 1.36
false (default) no extra rule no extra rule
true grants nodes/log (KEP-2862, stable in 1.36) grants nodes/proxy (legacy fallback)

A new host.rbac.kubelet_authorization_mode value (auto | fine_grained | legacy, default auto) overrides the version auto-detection — useful for off-cluster rendering (ArgoCD server-side) or clusters that misreport their version.

After this PR, the default deploy satisfies:

kubectl auth can-i get nodes/proxy \
  --as=system:serviceaccount:<ns>:<release>-shield-host
# no

Files

  • templates/host/clusterrole.yaml — drop unconditional nodes/proxy; append a conditional rule using new helpers.
  • templates/host/_helpers.tplhost.kubelet_log_access.{enabled,is_fine_grained_capable,subresource}.
  • values.yamlhost.rbac.kubelet_authorization_mode: auto (with inline docs).
  • tests/host/clusterrole_test.yaml — new helm-unittest suite, 8 cases covering default, version auto-detect, both override modes, live_logs off, and host.rbac.create: false.
  • Chart.yaml — bump 1.37.11.38.0.

Test plan

  • helm unittest -f 'tests/**/*_test.yaml' . — 31/31 suites, 483/483 tests pass (8 new).
  • helm template . --kube-version 1.36.0 (defaults) → host ClusterRole has no nodes/proxy and no nodes/log.
  • helm template . --kube-version 1.36.0 --set features.investigations.live_logs.enabled=true → grants nodes/log, no nodes/proxy.
  • helm template . --kube-version 1.35.0 --set features.investigations.live_logs.enabled=true → grants nodes/proxy (legacy fallback).
  • helm lint . clean.
  • Smoke test on a real cluster: install with defaults, then kubectl auth can-i get nodes/proxy --as=...:hostno; tail host-shield logs for forbidden errors.
  • Same on a Kubernetes 1.36 cluster with live_logs.enabled=true and verify Live Logs functions end-to-end.

Checklist

  • Title of the PR starts with type and scope (feat(shield):)
  • Chart Version bumped (1.37.1 → 1.38.0)
  • Variables are documented (inline comments in values.yaml for the new host.rbac.kubelet_authorization_mode key)
  • All test files are added in the tests folder of their respective chart and have a _test suffix

…elet log access on Live Logs

Removes the unconditional `nodes/proxy` grant from the host-shield ClusterRole
(flagged as a Remote Code Execution vector by security scans) and replaces it
with a feature-gated, version-aware kubelet-log subresource grant.

Behaviour:
- live_logs disabled (default): no kubelet-log RBAC rule. Default deploys now
  satisfy `kubectl auth can-i get nodes/proxy --as=...:host` ⇒ no.
- live_logs enabled, K8s >= 1.36: grants the narrow `nodes/log` subresource
  (KEP-2862, stable in Kubernetes 1.36).
- live_logs enabled, K8s < 1.36: grants `nodes/proxy` as a legacy fallback.
- New `host.rbac.kubelet_authorization_mode` value (`auto` | `fine_grained` |
  `legacy`) overrides the version auto-detection.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant