Kubelet Rotate Certificates Argument Not Set To False
More Info:
The kubelet --rotate-certificates argument should not be set to false so the kubelet automatically rotates its client certificates. Disabling rotation increases the risk of using expired or compromised credentials.
Risk Level
High
Address
Security
Compliance Standards
- CIS OKE
Triage and Remediation
- Remediation
Remediation
Manual Steps
-
On every worker node, open the kubelet systemd drop-in config for editing:
sudo vi /etc/systemd/system/kubelet.service.d/00-default.conf -
In that file, locate the
ExecStart=line. If it contains--rotate-certificates=false, remove=falseso it reads--rotate-certificates(or, if the flag is missing entirely, add it), for example:ExecStart=/usr/bin/kubelet \--rotate-certificates \... -
If your kubelet instead reads its options from
/etc/kubernetes/kubelet-config.json, open that file and ensure the feature is not disabled there (do not set it to false):sudo vi /etc/kubernetes/kubelet-config.jsonConfirm there is no line like:
"rotateCertificates": falseIf present, either remove that line or change it to:
"rotateCertificates": true -
Reload systemd and restart the kubelet so the new flag takes effect (this will restart the kubelet on this worker node):
sudo systemctl daemon-reloadsudo systemctl restart kubelet.service -
Confirm the kubelet is healthy on this worker node:
sudo systemctl status kubelet -l -
Verify on this worker node that the kubelet process is no longer running with
--rotate-certificates=falseand that--rotate-certificatesis present:/bin/ps -fC kubeletInspect the command line in the output and ensure
--rotate-certificates=falsedoes not appear and--rotate-certificates(without=false) is included.
Using kubectl
kubectl cannot modify kubelet process arguments or the host-level config file /etc/kubernetes/kubelet-config.json; this setting must be changed directly on every worker node in the systemd drop-in file /etc/systemd/system/kubelet.service.d/00-default.conf. Refer to the Manual Steps section for the exact on-node edits and restart commands needed to enable certificate rotation and then re-run /bin/ps -fC kubelet for verification.
Automation
#!/usr/bin/env bash
#
# Purpose: Ensure kubelet is configured with --rotate-certificates (not set to false)
# Scope: Run on every worker node (as root)
# Safe: Idempotent; can be re-run
#
set -euo pipefail
SYSTEMD_DROPIN_DIR="/etc/systemd/system/kubelet.service.d"
SYSTEMD_DROPIN_FILE="${SYSTEMD_DROPIN_DIR}/00-default.conf"
echo "[INFO] Ensuring kubelet --rotate-certificates is configured on this node"
if [[ ! -f "${SYSTEMD_DROPIN_FILE}" ]]; then
echo "[ERROR] Systemd drop-in not found: ${SYSTEMD_DROPIN_FILE}"
echo " This script expects kubelet to be managed by systemd with that drop-in."
echo " Adjust manually according to your environment."
exit 1
fi
# Ensure drop-in directory exists (usually already does)
mkdir -p "${SYSTEMD_DROPIN_DIR}"
# Backup the existing file once
if [[ ! -f "${SYSTEMD_DROPIN_FILE}.bak" ]]; then
cp "${SYSTEMD_DROPIN_FILE}" "${SYSTEMD_DROPIN_FILE}.bak"
echo "[INFO] Backup created at ${SYSTEMD_DROPIN_FILE}.bak"
fi
# Read current content
current_content="$(cat "${SYSTEMD_DROPIN_FILE}")"
# Remove any explicit --rotate-certificates=false occurrences
modified_content="$(printf '%s\n' "${current_content}" \
| sed -E 's/(^ExecStart=.*)--rotate-certificates=false[[:space:]]*/\1/g')"
# Ensure we have a --rotate-certificates flag somewhere in ExecStart
if echo "${modified_content}" | grep -qE '^ExecStart=.*--rotate-certificates(=|[[:space:]]|$)'; then
echo "[INFO] --rotate-certificates flag already present in ExecStart."
else
echo "[INFO] Adding --rotate-certificates to kubelet ExecStart."
modified_content="$(printf '%s\n' "${modified_content}" \
| sed -E 's|^(ExecStart=.*kubelet)|\1 --rotate-certificates|')"
fi
# Only write if changed
if ! diff -q <(printf '%s\n' "${current_content}") <(printf '%s\n' "${modified_content}") >/dev/null 2>&1; then
printf '%s\n' "${modified_content}" > "${SYSTEMD_DROPIN_FILE}"
echo "[INFO] Updated ${SYSTEMD_DROPIN_FILE}"
else
echo "[INFO] No changes needed in ${SYSTEMD_DROPIN_FILE}"
fi
echo "[INFO] Reloading systemd and restarting kubelet (this will momentarily disrupt kubelet on this node)."
systemctl daemon-reload
systemctl restart kubelet.service
echo "[INFO] Verifying kubelet is running with certificate rotation enabled..."
systemctl status kubelet -l --no-pager || {
echo "[ERROR] kubelet service is not healthy after restart."
exit 1
}
echo "[INFO] Current kubelet process flags:"
/bin/ps -fC kubelet || {
echo "[ERROR] kubelet process not found."
exit 1
}
if /bin/ps -fC kubelet | grep -q -- '--rotate-certificates=false'; then
echo "[ERROR] kubelet still has --rotate-certificates=false in its arguments."
exit 1
fi
if /bin/ps -fC kubelet | grep -q -- '--rotate-certificates'; then
echo "[INFO] kubelet is running with --rotate-certificates and not set to false."
echo "[INFO] Remediation successful on this node."
exit 0
else
echo "[WARN] kubelet process does not show --rotate-certificates flag explicitly."
echo " Review ${SYSTEMD_DROPIN_FILE} and kubelet configuration manually."
exit 1
fi