etcd 里存着集群的全部秘密
Kubernetes 把全部对象状态存在 etcd 中,包括各类 Secret,很多集群的 ServiceAccount 令牌与证书私钥也在其中。etcd 的客户端端口 2379 如果对外可达且没有证书认证,攻击者可以直接读出 Secret 并据此接管集群,属于最高优先级的收敛项。正确状态是:只监听内网或回环、启用客户端证书认证(mTLS),并对 2379/2380 做来源限制。
基本信息
| 加固项 | 集群数据存储端口收敛与认证 |
|---|---|
| 适用平台 | Linux(etcd、Kubernetes 控制面) |
| 权限要求 | 集群管理员 |
| 达标判据 | 仅内网监听、启用客户端证书认证、端口限源 |
| 端口 | 2379 客户端通信、2380 节点间通信 |
典型使用场景
- 自建 K8s 集群的安全基线核查
- 暴露面扫描发现 2379 对外可达后的紧急处置
- 从 kubeadm 默认配置出发做加固与验证
- 等保测评中容器平台相关条款取证
- 集群迁移或重建后确认认证配置未退化
核查现状
核查现状
ss -tlnp | grep -E ':2379|:2380 ' # 监听地址是否含 0.0.0.0
curl -sk --max-time 5 https://127.0.0.1:2379/version # 服务是否响应
curl -s --max-time 5 http://127.0.0.1:2379/version # 明文可用说明未强制 TLS,风险高
grep -E 'listen-client-urls|client-cert-auth|trusted-ca-file|cert-file' /etc/etcd/etcd.conf 2>/dev/null
systemctl cat etcd 2>/dev/null | grep -E 'listen-client-urls|client-cert-auth' # 参数也可能写在 unit 里加固方向
加固方向
# 监听地址收敛到内网或回环
# --listen-client-urls=https://10.0.1.10:2379,https://127.0.0.1:2379
# 启用客户端证书认证(关键项)
# --client-cert-auth=true --trusted-ca-file=/etc/etcd/ca.crt
# --cert-file=... --key-file=...
# 改完重启并复核:明文 http 访问应被拒绝
systemctl restart etcd && ss -tlnp | grep ':2379 '核查项与判定
| 核查项 | 达标表现 | 风险表现 |
|---|---|---|
| listen-client-urls | 仅内网或回环地址 | 含 0.0.0.0 或对外地址 |
| client-cert-auth | true,且配 trusted-ca-file | false 或缺失,HTTPS 也不校验客户端证书 |
| 明文 HTTP 访问 | 拒绝或不可用 | 可读到 version 等信息 |
| 2379 来源限制 | 安全组或防火墙限源 | 任何来源可连 |
| Secret 存储加密 | 启用静态加密配置 | 默认未开启时 Secret 明文落盘 |
历史上有未授权 etcd 被读取 Secret 导致集群凭据全线泄露的案例,一旦发生通常意味着集群需要重建信任链。因此发现 2379 对外可达时应按最高级别处置:先限源止血,再补认证与会话密钥轮换,而不是仅改监听地址了事。
要注意端口暴露往往来自启动参数里的 0.0.0.0 监听地址:改完参数必须重启服务并用 ss 复核绑定地址确实变化。同时 2380 是节点间通信端口,同样应限制在控制节点网段内,避免被用于伪造集群成员。