mcpField
I
implementing-secrets-management-with-vault

implementing-secrets-management-with-vault

github.com/mukul975安全35.2k82 次安装8 周前更新
代码仓库

关于 implementing-secrets-management-with-vault

这是一份面向平台和 DevOps 团队的 HashiCorp Vault 密钥管理实施指南,介绍动态凭据、Kubernetes 工作负载接入、加密与审计策略的配置。

主要功能

  1. 01部署高可用 Vault
  2. 02配置人员与机器身份验证
  3. 03生成带过期时间的动态凭据
  4. 04向 Kubernetes 工作负载提供密钥
  5. 05使用 Transit 加密并管理 PKI
  6. 06设置最小权限策略与审计

适用场景

  1. 01替换 CI/CD 中的硬编码凭据
  2. 02为数据库生成短期访问凭据
  3. 03向 Kubernetes Pod 提供密钥文件
  4. 04集中审计密钥访问与管理操作

安装

复制下面的命令,在终端中运行。

$npx skills add https://github.com/mukul975/anthropic-cybersecurity-skills --skill implementing-secrets-management-with-vault

安装后在 Claude Code 中输入/implementing-secrets-management-with-vault确认已加载。

包含的文件

除 SKILL.md 外,安装时一起下载的参考资料和脚本。

LICENSE
references/
api-reference.md
scripts/
agent.py

详细介绍

使用 Vault 实现密钥管理

适用场景

  • 当应用将数据库密码、API 密钥或证书存储在环境变量或配置文件中时
  • 当从静态长期凭证迁移到动态短期密钥时
  • 当 Kubernetes 工作负载需要安全访问数据库凭证或云服务商 API 时
  • 当合规要求强制实施带审计日志的集中式凭证管理时
  • 当 CI/CD 流水线包含硬编码密钥,构成供应链风险时

不要使用于仅使用 AWS 且 AWS Secrets Manager 已足够、无需多云需求的场景,也不适用于应用层加密逻辑(尽管 Vault Transit 可提供帮助),或身份联合(参见 managing-cloud-identity-with-okta)。

前提条件

  • 以 HA 模式部署 HashiCorp Vault 服务(Consul 或 Raft 存储后端)
  • 用于 Vault 监听器端点的 TLS 证书
  • 用于命名空间、Sentinel 策略和复制的 Vault Enterprise 许可(可选)
  • 带有 Vault Agent Injector 或 CSI provider 的 Kubernetes 集群,用于工作负载集成

工作流

第 1 步:以高可用模式部署 Vault

使用 Integrated Storage(Raft)部署 Vault,实现无需外部依赖的 HA。配置 TLS、审计日志,并使用云 KMS 进行自动解封。

# vault-config.hcl
storage "raft" {
  path    = "/opt/vault/data"
  node_id = "vault-node-1"

  retry_join {
    leader_api_addr = "https://vault-node-2.internal:8200"
  }
  retry_join {
    leader_api_addr = "https://vault-node-3.internal:8200"
  }
}

listener "tcp" {
  address     = "0.0.0.0:8200"
  tls_cert_file = "/opt/vault/tls/vault.crt"
  tls_key_file  = "/opt/vault/tls/vault.key"
}

seal "awskms" {
  region     = "us-east-1"
  kms_key_id = "alias/vault-unseal-key"
}

api_addr      = "https://vault-node-1.internal:8200"
cluster_addr  = "https://vault-node-1.internal:8201"

telemetry {
  prometheus_retention_time = "30s"
  disable_hostname         = true
}
# Initialize Vault
vault operator init -key-shares=5 -key-threshold=3

# Enable audit logging
vault audit enable file file_path=/var/log/vault/audit.log

# Enable syslog audit for SIEM integration
vault audit enable syslog tag="vault" facility="AUTH"
第 2 步:配置认证方法

为人工操作员、应用和 CI/CD 流水线启用认证后端。使用 AppRole 进行机器认证,使用 OIDC 进行人工访问。

# Enable OIDC auth for human users via Okta
vault auth enable oidc
vault write auth/oidc/config \
  oidc_discovery_url="https://company.okta.com/oauth2/default" \
  oidc_client_id="vault-client-id" \
  oidc_client_secret="vault-client-secret" \
  default_role="default"

# Enable AppRole for application authentication
vault auth enable approle
vault write auth/approle/role/web-app \
  secret_id_ttl=10m \
  token_num_uses=10 \
  token_ttl=20m \
  token_max_ttl=30m \
  secret_id_num_uses=1 \
  token_policies="web-app-policy"

# Enable Kubernetes auth for pod-based access
vault auth enable kubernetes
vault write auth/kubernetes/config \
  kubernetes_host="https://kubernetes.default.svc:443" \
  token_reviewer_jwt=@/var/run/secrets/kubernetes.io/serviceaccount/token \
  kubernetes_ca_cert=@/var/run/secrets/kubernetes.io/serviceaccount/ca.crt
第 3 步:启用动态密钥引擎

配置数据库密钥引擎以按需生成短期凭证。每组凭证都有 TTL,并在过期时自动撤销。

# Enable database secrets engine for PostgreSQL
vault secrets enable database
vault write database/config/production-db \
  plugin_name=postgresql-database-plugin \
  allowed_roles="readonly,readwrite" \
  connection_url="postgresql://{{username}}:{{password}}@db.internal:5432/production?sslmode=require" \
  username="vault_admin" \
  password="initial-password"

# Rotate the root credentials so Vault manages them exclusively
vault write -force database/rotate-root/production-db

# Create a readonly role with 1-hour TTL
vault write database/roles/readonly \
  db_name=production-db \
  creation_statements="CREATE ROLE \"{{name}}\" WITH LOGIN PASSWORD '{{password}}' VALID UNTIL '{{expiration}}'; GRANT SELECT ON ALL TABLES IN SCHEMA public TO \"{{name}}\";" \
  revocation_statements="REVOKE ALL ON ALL TABLES IN SCHEMA public FROM \"{{name}}\"; DROP ROLE IF EXISTS \"{{name}}\";" \
  default_ttl="1h" \
  max_ttl="24h"

# Enable AWS secrets engine for dynamic IAM credentials
vault secrets enable aws
vault write aws/config/root \
  access_key=AKIAEXAMPLE \
  secret_key=secretkey \
  region=us-east-1

vault write aws/roles/deploy-role \
  credential_type=iam_user \
  [email protected] \
  default_sts_ttl=3600
第 4 步:与 Kubernetes 工作负载集成

使用 Vault Agent Injector 或 CSI Provider 将密钥传递给 Pod,而无需更改应用代码。密钥会以文件形式呈现在共享卷中。

# Kubernetes deployment with Vault Agent Injector annotations
apiVersion: apps/v1
kind: Deployment
metadata:
  name: web-app
spec:
  template:
    metadata:
      annotations:
        vault.hashicorp.com/agent-inject: "true"
        vault.hashicorp.com/role: "web-app"
        vault.hashicorp.com/agent-inject-secret-db-creds: "database/creds/readonly"
        vault.hashicorp.com/agent-inject-template-db-creds: |
          {{- with secret "database/creds/readonly" -}}
          export DB_USERNAME="{{ .Data.username }}"
          export DB_PASSWORD="{{ .Data.password }}"
          {{- end }}
    spec:
      serviceAccountName: web-app
      containers:
        - name: web-app
          image: company/web-app:v2.1
          command: ["/bin/sh", "-c", "source /vault/secrets/db-creds && ./start.sh"]
第 5 步:实现 Transit 加密和 PKI

使用 Transit 密钥引擎进行应用层加密,而无需在应用代码中管理密钥。部署 PKI 引擎以实现自动 TLS 证书管理。

# Enable Transit engine for encryption as a service
vault secrets enable transit
vault write -f transit/keys/payment-data type=aes256-gcm96

# Encrypt sensitive data
vault write transit/encrypt/payment-data \
  plaintext=$(echo "card-number-4111-1111-1111-1111" | base64)

# Enable PKI for internal certificate management
vault secrets enable pki
vault secrets tune -max-lease-ttl=87600h pki

# Generate root CA
vault write pki/root/generate/internal \
  common_name="Internal Root CA" \
  ttl=87600h

# Configure intermediate CA for issuing certificates
vault secrets enable -path=pki_int pki
vault write pki_int/intermediate/generate/internal \
  common_name="Internal Intermediate CA" \
  ttl=43800h

# Create a role for issuing certificates
vault write pki_int/roles/internal-services \
  allowed_domains="internal.company.com" \
  allow_subdomains=true \
  max_ttl=720h
第 6 步:建立策略和审计追踪

按照最小权限原则定义细粒度 ACL 策略。为所有密钥访问和管理操作启用全面的审计日志。

# web-app-policy.hcl
path "database/creds/readonly" {
  capabilities = ["read"]
}

path "transit/encrypt/payment-data" {
  capabilities = ["update"]
}

path "transit/decrypt/payment-data" {
  capabilities = ["update"]
}

path "secret/data/web-app/*" {
  capabilities = ["read", "list"]
}

# Deny access to admin paths
path "sys/*" {
  capabilities = ["deny"]
}
# Apply the policy
vault policy write web-app-policy web-app-policy.hcl

# Verify audit log captures all operations
vault audit list -detailed

关键概念

术语定义
动态密钥按需生成并自动过期和撤销的凭证,消除长期静态凭证
密钥引擎用于存储、生成或加密数据的 Vault 组件;包括 KV、database、AWS、PKI 和 Transit 引擎
自动解封基于云 KMS 的机制,可在重启时自动解封 Vault 节点,无需手动输入密钥
AppRole面向机器的认证方法,使用 Role ID 和 Secret ID 进行应用和 CI/CD 流水线访问
Transit 引擎加密即服务引擎,处理加密操作而不向应用暴露加密密钥
租约带 TTL 的限时凭证,除非续期,否则 Vault 会在到期时自动撤销
命名空间Vault Enterprise 功能,通过独立的认证、密钥和策略管理提供租户隔离
响应包装将密钥响应包装在一次性令牌中的技术,以防止投递过程中的中间人暴露

工具与系统

  • HashiCorp Vault:核心密钥管理平台,提供动态密钥、加密和基于身份访问
  • Vault Agent Injector:Kubernetes 变更 webhook,通过 sidecar 容器自动将 Vault 密钥注入 pod 卷
  • Vault CSI Provider:Kubernetes CSI 驱动,无需 sidecar 容器即可将 Vault 密钥直接挂载到 pod 卷
  • consul-template:模板渲染守护进程,监视 Vault 密钥并在密钥更改时重新渲染配置文件
  • Vault Radar:密钥扫描工具,检测源代码、CI/CD 流水线和云配置中的硬编码凭据

常见场景

场景:从 CI/CD 流水线中消除硬编码数据库凭据

背景:一个 DevOps 团队在 GitHub Actions secrets 和 Jenkins 凭据存储中存储 PostgreSQL 凭据。相同的凭据在暂存和生产环境中共享,18 个月未轮换。

方案:

  1. 部署 Vault 并为 CI/CD 系统启用 AppRole 认证
  2. 配置数据库密钥引擎,为暂存(readwrite,2 小时 TTL)和生产(readonly,1 小时 TTL)设置单独的角色
  3. 为每个流水线阶段创建单独的 Vault 策略,限制对相应数据库角色的访问
  4. 更新 GitHub Actions 工作流,通过 AppRole 进行身份验证,并在每个作业开始时请求动态凭据
  5. 轮换静态 PostgreSQL 凭据,并将 root 访问权限完全交给 Vault
  6. 启用审计日志记录,用流水线作业元数据跟踪每次凭据请求

陷阱:迁移到 Vault 后未轮换原始静态凭据会导致旧凭据仍然有效。将 TTL 设置得太短会导致长时间运行的作业在部署中途凭据过期。

输出格式

Vault Secrets Management Audit Report
=======================================
Vault Cluster: vault.internal.company.com
Version: 1.18.1 Enterprise
HA Mode: Raft (3 nodes)
Seal Type: AWS KMS Auto-Unseal
Report Date: 2025-02-23

SECRET ENGINES:
  database/         PostgreSQL dynamic creds   Leases Active: 47
  aws/              Dynamic IAM credentials    Leases Active: 12
  transit/          Encryption as a service    Keys: 8
  pki/              Root CA                    Certs Issued: 0
  pki_int/          Intermediate CA            Certs Issued: 234
  secret/           KV v2 static secrets       Versions: 1,892

AUTH METHODS:
  oidc/             Okta SSO for humans        Active Tokens: 23
  approle/          CI/CD pipelines            Active Tokens: 156
  kubernetes/       Pod-based auth             Active Tokens: 89

AUDIT FINDINGS:
  [WARN] 3 AppRole secret_id_num_uses set to 0 (unlimited)
  [WARN] 12 KV secrets not accessed in 90+ days (potential orphans)
  [PASS] All dynamic secret TTLs under 24 hours
  [PASS] Audit logging enabled on all nodes
  [PASS] Root token revoked after initial setup

CREDENTIAL HYGIENE:
  Static Secrets (KV): 234
  Dynamic Secrets Active: 59
  Average Lease TTL: 2.3 hours
  Secrets Rotated This Month: 12,456

评论

支持 Markdown