KMS简介与密钥管理归纳总结
说到加密,很多人第一反应是“我把数据加密就安全了”。嗯,想法没错,但实现起来掉坑的人可不少。我见过不少团队直接把密钥硬编码在配置文件里,或者所有服务共用一把密钥——那跟没加密也差不了多少。
AWS Key Management Service(KMS)就是为了解决这些问题而生的。它不只是一个密钥存储柜,更是整个加密权限的管控中心。说白了,你得先管好密钥,才能管好数据。
为什么需要KMS?
你想想看,在云上做加密,最头疼的是啥?
- 密钥放哪儿? 不能放代码里,不能存本地文件,更不能明文传。
- 谁有权用? 同一个密钥,开发环境能解密生产数据?那不乱套了。
- 怎么轮转? 换了密钥,历史数据怎么读?
- 审计去哪儿了? 谁在什么时候用了哪把密钥,必须能追溯。
KMS 把这些问题全包了。它帮你生成、存储、轮转、审计密钥,而且和IAM深度集成 —— 你可以精确控制哪个角色能用哪个密钥,甚至限定只能加密不能解密。
我个人习惯是,只要涉及敏感数据,第一件事就是先想好KMS密钥策略,而不是先用再补。早期项目吃过亏——后来改权限,所有上下游服务都要同步更新,那叫一个痛苦。
KMS的核心概念
这里简单梳理几个你马上要面对的术语:
| 概念 | 说明 |
|---|---|
| CMK(Customer Master Key) | KMS里的主子密钥,实际咱们管理的是CMK的元数据和访问权限,底层硬件安全模块(HSM)负责真正的加密运算。 |
| 数据密钥(Data Key) | CMK的派生产物,用于业务数据加密。CMK本身不直接加密大量数据,而是加密数据密钥再交付给你用。 |
| 密钥策略(Key Policy) | 访问CMK的权限主文档,可以理解成密钥上的IAM策略。 |
| 授权(Grant) | 临时把CMK使用权给某些IAM身份,比密钥策略更细粒度也更灵活。 |
我的小经验: 数据密钥的明文在内存里用完后立即清零,别拖着。我在一个压测项目里发现,程序把数据密钥明文留在堆里不释放,结果被JVM dump出来——虽然没出事,但吓得我赶紧加了SecureRandom覆盖。
密钥类型一览
KMS提供三种“口味”的CMK,选错可是要付出代价的。我一般这样区分:
- AWS托管密钥(AWS Managed Key) —— 服务自动创建,你基本改不了策略。适合啥?就像“一次性碗筷”,图省事但别指望长期用。典型场景:SSE-S3默认加密,S3帮你管。
- 客户管理密钥(Customer Managed Key) —— 你自己创建、控制策略、启用/禁用、配置轮转。适合大多数生产环境。注意:轮转只产生新版本,旧版本保留,你还能解密历史数据。
- 自定义密钥存储(Custom Key Store) —— 用你自己的CloudHSM集群保管密钥。合规要求极高的公司才会用,比如金融、政务。成本不低,但密钥完全不在AWS侧可见。
| 特性 | AWS托管密钥 | 客户管理密钥 | 自定义密钥存储 |
|---|---|---|---|
| 谁创建 | AWS服务 | 你 | 你(需要CloudHSM) |
| 策略控制 | 只读(自动生成) | 完全控制 | 完全控制 |
| 自动轮转 | 可选(服务决定) | 可选(按年轮转) | 手动 |
| 审计 | CloudTrail记录 | CloudTrail记录 | CloudTrail + HSM日志 |
| 适用场景 | 轻量快速启动 | 大多数生产 | 高合规要求 |
关键提醒: 用客户管理密钥,千万别删!删除CMK有7~30天等待期,但一旦删除,所有用这把密钥加密的数据都会永久丢失。我之前辅助过一个同事,他在清理测试账号时顺手删了一把测试密钥,结果跑批任务全挂,回滚了三天数据——最后发现那把密钥还关联了RDS备份加密。
密钥管理实操要点
1. 创建CMK时就把策略写清楚
我建议先写key policy再创建。默认key policy允许AWS账户所有IAM用户管理,这通常是过度授权。应该遵循最小权限:只有指定角色才能管理,只有指定IAM身份才能加密/解密。
2. 开启自动轮转(对于客户管理密钥)
AWS支持每年自动轮转一次。开启了之后你基本不用操心,旧版本的密钥仍然可用,数据解密时KMS自动选择正确版本。嗯,这里要特别注意:你的业务代码不需要改,KMS SDK会自动解析密钥ID里的版本信息。
3. 用Grant给跨账户或临时权限
如果你需要让一个Lambda函数在几小时内访问某个CMK,但不想修改key policy,那就用Grant。它更轻量,且能设置过期时间。
# 创建一个Grant:允许IAM角色arn:aws:iam::123456789:role/MyLambdaRole使用指定CMK进行加密
aws kms create-grant \
--key-id 1234abcd-12ab-34cd-56ef-1234567890ab \
--grantee-principal arn:aws:iam::123456789:role/MyLambdaRole \
--operations Encrypt Decrypt \
--retiring-principal arn:aws:iam::123456789:role/AdminRole
我曾经踩过的一个坑: Grant不会自动同步到IAM控制台,你只能通过API查看。所以最好把Grant信息记录到配置文档里,不然几个月后想清理都不知道谁还有临时权限。我现在会在代码仓库里维护一个grant清单,用脚本定期校验。
知识体系图
下面这张图能帮你快速看清KMS密钥管理的大致框架。节点关系对应着“策略控制 + 密钥类型 + 使用方式”三层。
还有一个常被忽略的点:IAM和KMS策略的叠加关系
你写IAM策略时给了用户kms:Decrypt权限,但KMS密钥策略没允许这个用户——结果还是拒绝。很多人在排查权限时只查IAM,差点把键盘砸了。记住:IAM策略和密钥策略必须同时放行,两个都允许才能通过。
我从刚开始用KMS时就养成一个习惯:先在密钥策略里给一个IAM角色full access,然后再用IAM策略做更细的限定(比如只能解密特定前缀的加密数据)。这样密钥策略不用频繁改,所有权限变动都集中在IAM侧。
最后一点心法: KMS不是只用来加密S3的。RDS、Lambda环境变量、EC2启动卷、Secrets Manager、SQS……几乎每个AWS服务都能集成KMS。你只要花功夫梳理出一份“哪些数据需要加密、用哪把密钥”的清单,然后通过密钥策略统一管控,整个安全水位就能提一大截。
好了,这一章的核心内容就是这些。记住以后用KMS的时候,先想权限,再想操作,中间别忘了加批审计。