Secrets Management & KMS

🔥 Vibe Prompt

"Set up KMS with automatic key rotation. Store secrets in AWS Secrets Manager. Implement envelope encryption."

KMS (Key Management Service)

resource "aws_kms_key" "app" {
  description             = "Application encryption key"
  deletion_window_in_days = 30
  enable_key_rotation     = true  # Auto rotate yearly
  
  policy = jsonencode({
    Statement = [{
      Effect = "Allow"
      Principal = {
        AWS = "arn:aws:iam::${data.aws_caller_identity.current.account_id}:root"
      }
      Action = ["kms:*"]
      Resource = "*"
    }, {
      Effect = "Allow"
      Principal = { Service = "logs.${data.aws_region.current.name}.amazonaws.com" }
      Action = ["kms:Encrypt*"]
      Resource = "*"
    }]
  })
}

resource "aws_kms_alias" "app" {
  name          = "alias/app-key"
  target_key_id = aws_kms_key.app.key_id
}

Envelope Encryption

# 1. Generate a data key (DEK) via KMS
import boto3
kms = boto3.client('kms')

response = kms.generate_data_key(
    KeyId='alias/app-key',
    KeySpec='AES_256'
)
plaintext_dek = response['Plaintext']  # USE ONCE then discard
ciphertext_dek = response['CiphertextBlob']  # Store with data

# 2. Encrypt data with DEK (locally)
from cryptography.fernet import Fernet
fernet = Fernet(plaintext_dek)
encrypted_data = fernet.encrypt(b"Sensitive data")

# 3. Store: encrypted_data + ciphertext_dek
# Store both together

# 4. Decrypt: decrypt DEK first, then data
plaintext_dek = kms.decrypt(CiphertextBlob=ciphertext_dek)['Plaintext']
fernet = Fernet(plaintext_dek)
data = fernet.decrypt(encrypted_data)
print(f"Decrypted: {data.decode()}")

AWS Secrets Manager

resource "aws_secretsmanager_secret" "db" {
  name                    = "prod/db_password"
  rotation_rules {
    automatically_after_days = 30
  }
}

resource "aws_secretsmanager_secret_version" "db" {
  secret_id = aws_secretsmanager_secret.db.id
  secret_string = jsonencode({
    username = "admin"
    password = random_password.db.result
    host     = aws_db_instance.postgres.address
    port     = 5432
  })
}

# Lambda rotation
resource "aws_secretsmanager_secret_rotation" "db" {
  secret_id           = aws_secretsmanager_secret.db.id
  rotation_lambda_arn = aws_lambda_function.rotate_db.arn
}

AWS Parameter Store (Cheaper Alternative)

import boto3

ssm = boto3.client('ssm')

# Write (SecureString)
ssm.put_parameter(
    Name="/prod/app/api_key",
    Value="sk-1234...",
    Type="SecureString",
    KeyId="alias/app-key"
)

# Read
response = ssm.get_parameter(
    Name="/prod/app/api_key",
    WithDecryption=True
)
api_key = response['Parameter']['Value']

Secrets Manager vs Parameter Store

| Feature | Secrets Manager | Parameter Store | |---------|----------------|----------------| | Max secret size | 64 KB | 8 KB (free), 8 KB (advanced) | | Rotation | Built-in | Manual | | Cross-account | Yes | Yes | | Price | $0.40/secret/month | Free (standard) | | Auto-generate | Yes (random password) | No |

Best Practices

  • Use envelope encryption for large data
  • Rotate keys and secrets regularly
  • Use least privilege KMS key policies
  • Never hardcode secrets in code/config
  • Use IAM roles for EC2/Lambda (not keys)
  • Separate keys by environment (dev/prod)
  • Enable CloudTrail for KMS API calls


為什麼要學金鑰管理與 Secrets?

金鑰管理與 Secrets 是 security-cloud-security 課程的核心章節之一。

在真實世界中

金鑰管理與 Secrets 並不是課本上的理論——它在真實的軟體開發中頻繁出現。無論你是正在接案、準備面試,還是想要提升自己的技術深度,理解這個主題都能讓你直接受益。

你將從本章獲得

  • 🎯 完整的知識體系:從核心原理到實作細節,條理分明
  • 💻 可運行的程式碼:每段程式碼都是完整的,可直接執行
  • 🔍 除錯技巧:常見錯誤的分析與解決方案
  • 🚀 下一步指引:學完後該往哪個方向繼續深入

銜接下一章

本章為你建立了 金鑰管理與 Secrets 的完整知識基礎。下一章將在此基礎上,帶你探索更進階的真實世界應用場景——你將學會如何將本章所學應用到更複雜的問題中。

解鎖完整教學內容

本章為付費內容。加入專案即可解鎖超過 5000 字的深度解析,包含 10 個以上神級 Prompt 與真實 Source Code 範例!