Hashicorp Vault 密钥库
本教程演示如何设置一个使用 Vault 的 K/V 引擎 作为持久且安全的密钥存储的 KES 服务器。
先决条件
要启动开发服务器或使用 Vault CLI 与 Vault 进行交互,请下载 Vault 二进制文件。
Vault 服务器
KES 需要 Vault K/V 引擎 v1 或 v2 以及 AppRole 或 Kubernetes 身份验证方法的凭据。
如果您没有可用的现有 Vault 集群,请执行以下操作之一
- 按照 Hashicorp Vault 安装指南 创建一个新的集群。
- 创建一个 单节点开发实例
以下文档讨论了使用 AppRole
身份验证方法为开发目的设置单节点开发实例。
单节点开发 Vault 实例
以下命令以开发模式启动 Vault 服务器。
127.0.0.1:8200
。开发服务器是短暂的,**不**适合在生产环境中运行。将 Vault 连接到 Vault CLI
-
设置
VAULT_ADDR
端点Vault CLI 需要知道 Vault 端点
export VAULT_ADDR='https://127.0.0.1:8200'
-
设置
VAULT_TOKEN
Vault CLI 需要一个身份验证令牌来执行操作。
export VAULT_TOKEN=hvs.O6QNQB33ksXtMxtlRKlRZL0R
将令牌值替换为您自己的 Vault 访问令牌,例如
vault server -dev
命令输出中提供的Root token
。 -
启用
K/V
后端KES 将密钥存储在 Vault K/V 后端。Vault 提供了两个 K/V 引擎,
v1
和v2
。MinIO 建议使用 K/V
v1
引擎。KES 的 Vault 策略取决于所选的 K/V 引擎版本。为 K/V
v1
设计的策略不适用于 K/Vv2
引擎。同样,为 K/Vv2
设计的策略不适用于 K/Vv1
引擎。有关从
v1
迁移到v2
的更多信息,请参阅 有关从 v1 升级的 HashiCorp 文档。
设置 KES 对 Vault 的访问权限
-
创建 Vault 策略
Vault 策略定义了 KES 服务器可以访问的 API 路径。创建一个名为
kes-policy.hcl
的文本文件。策略的内容因使用的 K/V 引擎而异。
-
将策略写入 Vault
以下命令在 Vault 中创建策略
vault policy write kes-policy kes-policy.hcl
-
启用身份验证
此步骤允许 KES 服务器对 Vault 进行身份验证。在本教程中,我们使用
AppRole
身份验证方法。vault auth enable approle
-
创建 KES 角色
以下命令在 Vault 中添加一个名为
kes-server
的新角色vault write auth/approle/role/kes-server token_num_uses=0 secret_id_num_uses=0 period=5m
-
将策略绑定到角色
以下命令将
kes-server
角色绑定到kes-policy
vault write auth/approle/role/kes-server policies=kes-policy
-
生成 AppRole ID
为 KES 服务器请求 AppRole ID
vault read auth/approle/role/kes-server/role-id
-
生成 AppRole 密钥
为 KES 服务器请求 AppRole 密钥
vault write -f auth/approle/role/kes-server/secret-id
AppRole 密钥打印为
secret_id
。您可以忽略secret_id_accessor
。
KES 服务器设置
-
生成 KES 服务器私钥和证书
以下命令为 IP
127.0.0.1
和 DNS 名称localhost
(作为 SAN)生成新的 TLS 私钥server.key
和自签名 X.509 证书server.cert
。如果您想使用其他 IP 或 DNS 名称(例如10.1.2.3
或https://kes.example.net
)引用您的 KES 服务器,请相应地调整--ip
和/或--dns
参数。kes identity new --key server.key --cert server.cert --ip "127.0.0.1" --dns localhost
上述命令生成自签名证书。如果您已经有办法为您的服务器颁发证书,则可以使用这些证书。
其他 X.509 证书生成工具也有效。例如,您可以使用
openssl
openssl ecparam -genkey -name prime256v1 | openssl ec -out server.key openssl req -new -x509 -days 30 -key server.key -out server.cert \ -subj "/C=/ST=/L=/O=/CN=localhost" -addext "subjectAltName = IP:127.0.0.1"
-
生成 API 密钥
以下命令生成新的 KES API 密钥。
kes identity new
输出类似于以下内容
Your API key: kes:v1:ABfa1xsnIV0lltXQC8tHXic8lte7J6hT7EoGv6+s5QCW This is the only time it is shown. Keep it secret and secure! Your Identity: cf6c535e738c1dd47a1d746366fde7f0309d1e0a8471b9f6e909833906afbbfa The identity is not a secret. It can be shared. Any peer needs this identity in order to verify your API key. The identity can be computed again via: kes identity of kes:v1:ABfa1xsnIV0lltXQC8tHXic8lte7J6hT7EoGv6+s5QCW
生成的
identity
**不是**密钥,可以公开共享。它稍后将在 KES 配置文件中用作管理员身份或分配给策略。API 密钥
本身**是**密钥,不应共享。您可以随时重新计算 API 密钥的身份。 -
配置 KES 服务器
创建 KES 服务器配置文件:
config.yml
。确保策略部分中的身份与
client.crt
身份匹配。添加之前获得的 approlerole_id
和secret_id
。admin: # Use the identity generated above by 'kes identity new'. identity: "" # For example: cf6c535e738c1dd47a1d746366fde7f0309d1e0a8471b9f6e909833906afbbfa tls: key: private.key # The KES server TLS private key cert: public.crt # The KES server TLS certificate keystore: vault: endpoint: https://127.0.0.1:8200 version: v1 # The K/V engine version - either "v1" or "v2". engine: kv # The engine path of the K/V engine. The default is "kv". approle: id: "" # Your AppRole ID secret: "" # Your AppRole Secret
-
启动 KES 服务器
KES CLI 访问
-
设置
KES_SERVER
端点以下环境变量指定 KES CLI 应该与之通信的 KES 服务器
export KES_SERVER=https://127.0.0.1:7373
-
定义 CLI 访问凭据
以下环境变量设置客户端用于与 KES 服务器通信的密钥
export KES_API_KEY=kes:v1:ABfa1xsnIV0lltXQC8tHXic8lte7J6hT7EoGv6+s5QCW
将值替换为服务器的 API 密钥。启动服务器时,服务器的 API 密钥会显示在输出中。
-
测试配置
例如,检查服务器的状态
kes status -k
使用密钥生成新的数据加密密钥
kes key dek my-key-1 -k
命令输出类似于以下内容
{ plaintext : UGgcVBgyQYwxKzve7UJNV5x8aTiPJFoR+s828reNjh0= ciphertext: eyJhZWFkIjoiQUVTLTI1Ni1HQ00tSE1BQy1TSEEtMjU2IiwiaWQiOiIxMTc1ZjJjNDMyMjNjNjNmNjY1MDk5ZDExNmU3Yzc4NCIsIml2IjoiVHBtbHpWTDh5a2t4VVREV1RSTU5Tdz09Iiwibm9uY2UiOiJkeGl0R3A3bFB6S21rTE5HIiwiYnl0ZXMiOiJaaWdobEZrTUFuVVBWSG0wZDhSYUNBY3pnRWRsQzJqWFhCK1YxaWl2MXdnYjhBRytuTWx0Y3BGK0RtV1VoNkZaIn0= }
将 KES 与 MinIO 服务器一起使用
MinIO 服务器需要 KES 才能启用服务器端数据加密。
请参阅 KES for MinIO 指南,了解将新的 KES 服务器与 MinIO 服务器一起使用所需的额外步骤。
配置参考
以下部分描述了密钥加密服务 (KES) 配置设置,以使用 HashiCorp Vault 密钥存储作为根 KMS 来存储外部密钥,例如用于 MinIO 服务器上的服务器端加密的密钥。
高级配置
这些其他配置步骤可以解决特定问题。
使用 K/V 前缀的多租户
Vault 可以作为多个隔离的 KES 租户的后端。每个 KES 租户可以由N
个副本组成。可以有M
个 KES 租户连接到同一个 Vault 服务器/集群。
这意味着N × M
个 KES 服务器实例可以连接到单个 Vault。
在这些配置中,每个 KES 租户在 K/V 密钥引擎中都有一个单独的前缀。对于每个 KES 租户,必须有一个对应的 Vault 策略。
-
对于 K/V
v1
path "kv/<tenant-name>/*" { capabilities = [ "create", "read", "delete" ] }
-
对于 K/V
v2
path "kv/data/<tenant-name>/*" { capabilities = [ "create", "read" ] } path "kv/metadata/<tenant-name>/*" { capabilities = [ "list", "delete" ] }
为每个 KES 租户创建一个不同的配置文件。该文件包含租户要使用的 Vault K/V 前缀。
keystore:
vault:
endpoint: https://127.0.0.1:8200
prefix: <tenant-name>
approle:
id: "" # Your AppRole ID
secret: "" # Your AppRole Secret
retry: 15s
status:
ping: 10s
tls:
ca: vault.crt # Manually trust the vault certificate since we use self-signed certificates
使用 Vault 命名空间的多租户
Vault 可以作为多个隔离的 KES 租户的后端。每个 KES 租户可以由N
个副本组成。可以有M
个 KES 租户连接到同一个 Vault 服务器/集群。
这意味着N × M
个 KES 服务器实例可以连接到单个 Vault。
因此,每个 KES 租户在 K/V 密钥引擎中都有一个单独的前缀。对于每个 KES 租户,必须有一个对应的 Vault 策略。
-
对于 K/V
v1
path "kv/<tenant-name>/*" { capabilities = [ "create", "read", "delete" ] }
-
对于 K/V
v2
path "kv/data/<tenant-name>/*" { capabilities = [ "create", "read" ] } path "kv/metadata/<tenant-name>/*" { capabilities = [ "list", "delete" ] }
为每个 KES 租户使用不同的配置文件。该文件包含 KES 租户应使用的 Vault 命名空间。
keystore:
vault:
endpoint: https://127.0.0.1:8200
namespace: <vault-namespace>
approle:
id: "" # Your AppRole ID
secret: "" # Your AppRole Secret
retry: 15s
status:
ping: 10s
tls:
ca: vault.crt # Manually trust the vault certificate since we use self-signed certificates
加密 Vault 存储的密钥
HashiCorp 的Transit 功能提供了一种加密和解密存储在 Vault 中的密钥的方法。这提供了一层额外的加密,在某些特定情况下可能很有用。
启用后,HashiCorp 会在 Vault 中存储一个密钥来加密或解密存储在 Vault 中的其他密钥。然后,KES 使用 Vault 管理的密钥来存储或检索 Vault 中的密钥。
要配置 Transit,请将以下部分添加到 KES 配置 YAML 的keystore.vault
部分
keystore:
vault:
transit: # Optionally encrypt keys stored on the K/V engine with a Vault-managed key.
engine: "" # The path of the transit engine - e.g. "my-transit". If empty, defaults to: transit (Vault default)
key: "" # The key name that should be used to encrypt entries stored on the K/V engine.