AWS Targets¶
SecretZero supports two AWS secret management services: AWS Secrets Manager and AWS Systems Manager Parameter Store. Both provide secure, scalable secret storage with native AWS integration.
Overview¶
AWS targets allow you to:
- Store secrets in AWS cloud infrastructure
- Leverage AWS KMS for encryption
- Integrate with IAM for fine-grained access control
- Enable automatic rotation with AWS Lambda
- Audit access with AWS CloudTrail
- Scale globally with multi-region support
Prerequisites¶
Installation¶
AWS support requires the boto3 library:
# Install with AWS support
pip install secretzero[aws]
# Or install boto3 directly
pip install boto3
Authentication¶
AWS targets use the standard AWS credential chain:
- Environment variables (
AWS_ACCESS_KEY_ID,AWS_SECRET_ACCESS_KEY) - AWS credentials file (
~/.aws/credentials) - IAM instance profile (EC2, ECS, Lambda)
- IAM role (EKS, Fargate)
Required IAM Permissions¶
For Secrets Manager:¶
{
"Version": "2012-10-17",
"Statement": [
{
"Effect": "Allow",
"Action": [
"secretsmanager:CreateSecret",
"secretsmanager:UpdateSecret",
"secretsmanager:GetSecretValue",
"secretsmanager:DeleteSecret",
"secretsmanager:DescribeSecret"
],
"Resource": "arn:aws:secretsmanager:*:*:secret:*"
}
]
}
For Parameter Store:¶
{
"Version": "2012-10-17",
"Statement": [
{
"Effect": "Allow",
"Action": [
"ssm:PutParameter",
"ssm:GetParameter",
"ssm:DeleteParameter",
"ssm:DescribeParameters"
],
"Resource": "arn:aws:ssm:*:*:parameter/*"
},
{
"Effect": "Allow",
"Action": [
"kms:Decrypt",
"kms:Encrypt"
],
"Resource": "arn:aws:kms:*:*:key/*"
}
]
}
AWS Secrets Manager Target¶
AWS Secrets Manager is designed for secrets like database credentials, API keys, and OAuth tokens. It supports automatic rotation and integrates seamlessly with AWS services.
Configuration¶
targets:
- provider: aws
kind: secrets_manager
config:
name: string # Secret name or ARN (required)
description: string # Secret description (optional)
kms_key_id: string # KMS key ARN/ID (optional)
Configuration Options¶
| Option | Type | Required | Default | Description |
|---|---|---|---|---|
name |
string | Yes | - | Secret name or ARN |
description |
string | No | "Managed by SecretZero: {secret_name}" |
Human-readable description |
kms_key_id |
string | No | AWS managed key | KMS key ARN or alias for encryption |
Basic Example¶
version: '1.0'
providers:
aws:
kind: aws
auth:
kind: ambient
region: us-east-1
secrets:
- name: database_password
kind: random_password
config:
length: 32
special: true
exclude_characters: '"@/\'
targets:
- provider: aws
kind: secrets_manager
config:
name: myapp/prod/db/password
description: Production database password
Advanced Example with KMS¶
secrets:
- name: api_key
kind: random_string
config:
length: 32
charset: alphanumeric
targets:
- provider: aws
kind: secrets_manager
config:
name: myapp/api-key
description: External API key for service XYZ
kms_key_id: arn:aws:kms:us-east-1:123456789012:key/12345678-1234-1234-1234-123456789012
Multi-Region Secrets¶
variables:
regions:
- us-east-1
- us-west-2
- eu-west-1
secrets:
- name: global_api_key
kind: random_string
config:
length: 32
targets:
# Deploy to multiple regions
- provider: aws_us_east
kind: secrets_manager
config:
name: global/api-key
- provider: aws_us_west
kind: secrets_manager
config:
name: global/api-key
- provider: aws_eu_west
kind: secrets_manager
config:
name: global/api-key
providers:
aws_us_east:
kind: aws
auth:
kind: ambient
region: us-east-1
aws_us_west:
kind: aws
auth:
kind: ambient
region: us-west-2
aws_eu_west:
kind: aws
auth:
kind: ambient
region: eu-west-1
Structured Secrets¶
Store complex credentials as JSON:
secrets:
- name: database_credentials
kind: templates.db_config
templates:
db_config:
fields:
host:
generator:
kind: static
config:
default: db.example.com
port:
generator:
kind: static
config:
default: "5432"
username:
generator:
kind: static
config:
default: app_user
password:
generator:
kind: random_password
config:
length: 32
targets:
- provider: aws
kind: secrets_manager
config:
name: myapp/database/credentials
Retrieved as:
{
"host": "db.example.com",
"port": "5432",
"username": "app_user",
"password": "randompassword123456789012345678901"
}
AWS Systems Manager Parameter Store Target¶
Parameter Store is ideal for configuration data, feature flags, and secrets that don't require automatic rotation. It's cost-effective and integrates with AWS Systems Manager.
Configuration¶
targets:
- provider: aws
kind: ssm_parameter
config:
name: string # Parameter name/path (required)
type: string # Parameter type (optional)
overwrite: boolean # Overwrite existing (optional)
description: string # Description (optional)
tier: string # Parameter tier (optional)
Configuration Options¶
| Option | Type | Required | Default | Description |
|---|---|---|---|---|
name |
string | Yes | - | Parameter name/path (e.g., /myapp/db/password) |
type |
string | No | SecureString |
Parameter type: String, SecureString, StringList |
overwrite |
boolean | No | true |
Whether to overwrite existing parameters |
description |
string | No | "Managed by SecretZero: {secret_name}" |
Parameter description |
tier |
string | No | Standard |
Parameter tier: Standard, Advanced, Intelligent-Tiering |
Parameter Types¶
String- Plain text parameter (not recommended for secrets)SecureString- Encrypted with KMS (recommended for secrets)StringList- Comma-separated values
Basic Example¶
version: '1.0'
providers:
aws:
kind: aws
auth:
kind: ambient
region: us-east-1
secrets:
- name: app_secret_key
kind: random_string
config:
length: 64
charset: base64
targets:
- provider: aws
kind: ssm_parameter
config:
name: /myapp/prod/secret-key
type: SecureString
overwrite: true
tier: Standard
Hierarchical Organization¶
Use paths to organize parameters:
secrets:
# Database parameters
- name: db_password
kind: random_password
config:
length: 32
targets:
- provider: aws
kind: ssm_parameter
config:
name: /myapp/prod/database/password
type: SecureString
- name: db_host
kind: static
config:
value: prod-db.example.com
targets:
- provider: aws
kind: ssm_parameter
config:
name: /myapp/prod/database/host
type: String
# API parameters
- name: api_key
kind: random_string
config:
length: 32
targets:
- provider: aws
kind: ssm_parameter
config:
name: /myapp/prod/api/key
type: SecureString
# Application parameters
- name: app_debug
kind: static
config:
value: "false"
targets:
- provider: aws
kind: ssm_parameter
config:
name: /myapp/prod/app/debug
type: String
Advanced Tier Usage¶
Use Advanced tier for larger values:
secrets:
- name: large_certificate
kind: static
config:
value: |
-----BEGIN CERTIFICATE-----
MIIEpQIBAAKCAQEA...
(large certificate content)
-----END CERTIFICATE-----
targets:
- provider: aws
kind: ssm_parameter
config:
name: /myapp/certificates/app-cert
type: SecureString
tier: Advanced # Supports up to 8KB
Tier Limits: - Standard: 4 KB, free - Advanced: 8 KB, charges apply - Intelligent-Tiering: Automatically switches based on size
Environment-Based Parameters¶
variables:
environment: prod
app_name: myapp
secrets:
- name: secret_key
kind: random_string
config:
length: 64
targets:
- provider: aws
kind: ssm_parameter
config:
name: /{{var.app_name}}/{{var.environment}}/secret-key
type: SecureString
description: "Secret key for {{var.app_name}} {{var.environment}}"
Comparison: Secrets Manager vs. Parameter Store¶
| Feature | Secrets Manager | Parameter Store (SecureString) |
|---|---|---|
| Encryption | KMS (required) | KMS (optional) |
| Automatic Rotation | Yes (built-in) | No (manual via Lambda) |
| Cross-Region Replication | Yes | No |
| Versioning | Yes (automatic) | Yes (manual) |
| Max Size | 65,536 bytes | 4 KB (Standard), 8 KB (Advanced) |
| Cost | $0.40/secret/month + API calls | Free (Standard), $0.05/param/month (Advanced) |
| Use Case | Sensitive credentials, rotating secrets | Configuration, non-rotating secrets |
| AWS Service Integration | RDS, DocumentDB, Redshift | EC2, ECS, Lambda, Systems Manager |
When to Use Each¶
Use Secrets Manager when: - Secrets require automatic rotation - Managing database credentials - Need cross-region replication - Want built-in integration with RDS/DocumentDB - Compliance requires secret rotation
Use Parameter Store when: - Storing configuration values - Managing application settings - Need hierarchical organization - Cost is a primary concern - Secrets don't require rotation
Complete Examples¶
Multi-Tier Application¶
version: '1.0'
variables:
environment: production
app_name: webapp
providers:
aws:
kind: aws
auth:
kind: ambient
region: us-east-1
secrets:
# Critical secrets → Secrets Manager
- name: database_master_password
kind: random_password
config:
length: 32
special: true
targets:
- provider: aws
kind: secrets_manager
config:
name: "{{var.app_name}}/{{var.environment}}/db/master-password"
description: Master database password
- name: jwt_signing_key
kind: random_string
config:
length: 64
charset: base64
targets:
- provider: aws
kind: secrets_manager
config:
name: "{{var.app_name}}/{{var.environment}}/jwt/signing-key"
# Configuration → Parameter Store
- name: db_connection_pool_size
kind: static
config:
value: "20"
targets:
- provider: aws
kind: ssm_parameter
config:
name: /{{var.app_name}}/{{var.environment}}/db/pool-size
type: String
- name: log_level
kind: static
config:
value: INFO
targets:
- provider: aws
kind: ssm_parameter
config:
name: /{{var.app_name}}/{{var.environment}}/logging/level
type: String
- name: feature_flag_new_ui
kind: static
config:
value: "true"
targets:
- provider: aws
kind: ssm_parameter
config:
name: /{{var.app_name}}/{{var.environment}}/features/new-ui
type: String
Microservices Architecture¶
version: '1.0'
providers:
aws:
kind: aws
auth:
kind: ambient
region: us-east-1
secrets:
# Shared secrets
- name: shared_encryption_key
kind: random_string
config:
length: 64
charset: hex
targets:
- provider: aws
kind: secrets_manager
config:
name: shared/encryption-key
# Service-specific secrets
- name: auth_service_db_password
kind: random_password
config:
length: 32
targets:
- provider: aws
kind: ssm_parameter
config:
name: /services/auth/db/password
type: SecureString
- name: payment_service_api_key
kind: random_string
config:
length: 32
targets:
- provider: aws
kind: secrets_manager
config:
name: services/payment/api-key
- name: notification_service_smtp_password
kind: random_password
config:
length: 24
targets:
- provider: aws
kind: ssm_parameter
config:
name: /services/notification/smtp/password
type: SecureString
Best Practices¶
1. Use Consistent Naming Conventions¶
# Good: hierarchical structure
/myapp/prod/database/password
/myapp/prod/api/key
/myapp/staging/database/password
# Avoid: inconsistent naming
myapp-db-pass
MYAPP_API_KEY
app.secret
2. Leverage Tags for Organization¶
# Note: Tagging requires AWS API calls beyond SecretZero
# Use external tools or scripts to add tags:
# AWS CLI example:
# aws secretsmanager tag-resource \
# --secret-id myapp/api-key \
# --tags Key=Environment,Value=production Key=Owner,Value=platform-team
3. Enable CloudTrail Logging¶
Monitor secret access:
# Enable CloudTrail for Secrets Manager
aws cloudtrail create-trail \
--name secrets-audit \
--s3-bucket-name my-audit-bucket
# Enable logging
aws cloudtrail start-logging --name secrets-audit
4. Use Least Privilege IAM¶
{
"Version": "2012-10-17",
"Statement": [
{
"Effect": "Allow",
"Action": [
"secretsmanager:GetSecretValue"
],
"Resource": "arn:aws:secretsmanager:us-east-1:123456789012:secret:myapp/prod/*"
}
]
}
5. Implement Secret Rotation¶
# Generate rotatable secrets
secrets:
- name: db_password
kind: random_password
rotation_period: 90d # Rotate every 90 days
config:
length: 32
targets:
- provider: aws
kind: secrets_manager
config:
name: myapp/db/password
Troubleshooting¶
Access Denied Errors¶
Problem: AccessDeniedException when storing/retrieving secrets.
Solutions: 1. Verify IAM permissions
2. Check resource-based policies 3. Ensure KMS key permissions if using custom keysSecret Already Exists¶
Problem: ResourceExistsException when creating secrets.
Solution: SecretZero automatically updates existing secrets. If you see this error:
1. Verify the secret name is correct
2. Check if another process is creating secrets
3. Use overwrite: true for Parameter Store
KMS Key Not Found¶
Problem: KMSKeyNotFoundException when using custom KMS keys.
Solutions: 1. Verify KMS key ARN/alias is correct 2. Ensure KMS key is in the same region 3. Check KMS key permissions:
Parameter Size Exceeded¶
Problem: ParameterMaxLength error for Parameter Store.
Solutions: 1. Use Advanced tier for larger parameters:
2. Switch to Secrets Manager (65KB limit) 3. Split large values into multiple parametersSecurity Considerations¶
Encryption¶
Both services encrypt secrets at rest:
- Secrets Manager: Mandatory KMS encryption
- Parameter Store SecureString: KMS encryption (AWS managed or custom key)
# Use custom KMS key
secrets:
- name: sensitive_key
targets:
- provider: aws
kind: secrets_manager
config:
name: sensitive-key
kms_key_id: alias/myapp-secrets
Access Control¶
Use IAM policies and resource tags:
{
"Version": "2012-10-17",
"Statement": [
{
"Effect": "Allow",
"Action": "secretsmanager:GetSecretValue",
"Resource": "*",
"Condition": {
"StringEquals": {
"secretsmanager:ResourceTag/Environment": "production"
}
}
}
]
}
Audit Logging¶
Enable CloudTrail for complete audit trail:
- Secret creation/updates
- Secret access (GetSecretValue, GetParameter)
- Secret deletion
- KMS key usage
Secret Deletion¶
# Secrets Manager: 7-30 day recovery window
# Force immediate deletion in code (use with caution):
# sm.delete_secret(SecretId=secret_id, ForceDeleteWithoutRecovery=True)
# Parameter Store: Immediate deletion
# No recovery period
AWS Service Integration¶
ECS Task Definitions¶
{
"containerDefinitions": [
{
"name": "app",
"secrets": [
{
"name": "DB_PASSWORD",
"valueFrom": "arn:aws:secretsmanager:us-east-1:123456789012:secret:myapp/db/password"
},
{
"name": "API_KEY",
"valueFrom": "arn:aws:ssm:us-east-1:123456789012:parameter/myapp/api-key"
}
]
}
]
}
Lambda Functions¶
import boto3
import json
# Secrets Manager
secrets_client = boto3.client('secretsmanager')
response = secrets_client.get_secret_value(SecretId='myapp/db/password')
secret = json.loads(response['SecretString'])
# Parameter Store
ssm_client = boto3.client('ssm')
response = ssm_client.get_parameter(Name='/myapp/api-key', WithDecryption=True)
api_key = response['Parameter']['Value']
RDS Integration¶
# Create RDS master password
secrets:
- name: rds_master_password
kind: random_password
config:
length: 32
special: true
exclude_characters: '"@/\`'
targets:
- provider: aws
kind: secrets_manager
config:
name: rds/master-password
Then reference in RDS:
aws rds create-db-instance \
--db-instance-identifier mydb \
--manage-master-user-password \
--master-username admin \
--engine postgres
Next Steps¶
- Explore Azure Key Vault for multi-cloud deployments
- Learn about HashiCorp Vault for hybrid environments
- Review Kubernetes secrets for container workloads
- Check examples for complete configurations