Implement secure secrets management for CI/CD pipelines using Vault, AWS Secrets Manager, or native platform solutions. Use when handling sensitive credentials, rotating secrets, or securing CI/CD environments.
Add this skill
npx mdskills install sickn33/secrets-managementComprehensive secrets management guide with multi-platform examples and security best practices
1---2name: secrets-management3description: Implement secure secrets management for CI/CD pipelines using Vault, AWS Secrets Manager, or native platform solutions. Use when handling sensitive credentials, rotating secrets, or securing CI/CD environments.4---56# Secrets Management78Secure secrets management practices for CI/CD pipelines using Vault, AWS Secrets Manager, and other tools.910## Purpose1112Implement secure secrets management in CI/CD pipelines without hardcoding sensitive information.1314## Use this skill when1516- Store API keys and credentials17- Manage database passwords18- Handle TLS certificates19- Rotate secrets automatically20- Implement least-privilege access2122## Do not use this skill when2324- You plan to hardcode secrets in source control25- You cannot secure access to the secrets backend26- You only need local development values without sharing2728## Instructions29301. Identify secret types, owners, and rotation requirements.312. Choose a secrets backend and access model.323. Integrate CI/CD or runtime retrieval with least privilege.334. Validate rotation and audit logging.3435## Safety3637- Never commit secrets to source control.38- Limit access and log secret usage for auditing.3940## Secrets Management Tools4142### HashiCorp Vault43- Centralized secrets management44- Dynamic secrets generation45- Secret rotation46- Audit logging47- Fine-grained access control4849### AWS Secrets Manager50- AWS-native solution51- Automatic rotation52- Integration with RDS53- CloudFormation support5455### Azure Key Vault56- Azure-native solution57- HSM-backed keys58- Certificate management59- RBAC integration6061### Google Secret Manager62- GCP-native solution63- Versioning64- IAM integration6566## HashiCorp Vault Integration6768### Setup Vault6970```bash71# Start Vault dev server72vault server -dev7374# Set environment75export VAULT_ADDR='http://127.0.0.1:8200'76export VAULT_TOKEN='root'7778# Enable secrets engine79vault secrets enable -path=secret kv-v28081# Store secret82vault kv put secret/database/config username=admin password=secret83```8485### GitHub Actions with Vault8687```yaml88name: Deploy with Vault Secrets8990on: [push]9192jobs:93 deploy:94 runs-on: ubuntu-latest95 steps:96 - uses: actions/checkout@v49798 - name: Import Secrets from Vault99 uses: hashicorp/vault-action@v2100 with:101 url: https://vault.example.com:8200102 token: ${{ secrets.VAULT_TOKEN }}103 secrets: |104 secret/data/database username | DB_USERNAME ;105 secret/data/database password | DB_PASSWORD ;106 secret/data/api key | API_KEY107108 - name: Use secrets109 run: |110 echo "Connecting to database as $DB_USERNAME"111 # Use $DB_PASSWORD, $API_KEY112```113114### GitLab CI with Vault115116```yaml117deploy:118 image: vault:latest119 before_script:120 - export VAULT_ADDR=https://vault.example.com:8200121 - export VAULT_TOKEN=$VAULT_TOKEN122 - apk add curl jq123 script:124 - |125 DB_PASSWORD=$(vault kv get -field=password secret/database/config)126 API_KEY=$(vault kv get -field=key secret/api/credentials)127 echo "Deploying with secrets..."128 # Use $DB_PASSWORD, $API_KEY129```130131**Reference:** See `references/vault-setup.md`132133## AWS Secrets Manager134135### Store Secret136137```bash138aws secretsmanager create-secret \139 --name production/database/password \140 --secret-string "super-secret-password"141```142143### Retrieve in GitHub Actions144145```yaml146- name: Configure AWS credentials147 uses: aws-actions/configure-aws-credentials@v4148 with:149 aws-access-key-id: ${{ secrets.AWS_ACCESS_KEY_ID }}150 aws-secret-access-key: ${{ secrets.AWS_SECRET_ACCESS_KEY }}151 aws-region: us-west-2152153- name: Get secret from AWS154 run: |155 SECRET=$(aws secretsmanager get-secret-value \156 --secret-id production/database/password \157 --query SecretString \158 --output text)159 echo "::add-mask::$SECRET"160 echo "DB_PASSWORD=$SECRET" >> $GITHUB_ENV161162- name: Use secret163 run: |164 # Use $DB_PASSWORD165 ./deploy.sh166```167168### Terraform with AWS Secrets Manager169170```hcl171data "aws_secretsmanager_secret_version" "db_password" {172 secret_id = "production/database/password"173}174175resource "aws_db_instance" "main" {176 allocated_storage = 100177 engine = "postgres"178 instance_class = "db.t3.large"179 username = "admin"180 password = jsondecode(data.aws_secretsmanager_secret_version.db_password.secret_string)["password"]181}182```183184## GitHub Secrets185186### Organization/Repository Secrets187188```yaml189- name: Use GitHub secret190 run: |191 echo "API Key: ${{ secrets.API_KEY }}"192 echo "Database URL: ${{ secrets.DATABASE_URL }}"193```194195### Environment Secrets196197```yaml198deploy:199 runs-on: ubuntu-latest200 environment: production201 steps:202 - name: Deploy203 run: |204 echo "Deploying with ${{ secrets.PROD_API_KEY }}"205```206207**Reference:** See `references/github-secrets.md`208209## GitLab CI/CD Variables210211### Project Variables212213```yaml214deploy:215 script:216 - echo "Deploying with $API_KEY"217 - echo "Database: $DATABASE_URL"218```219220### Protected and Masked Variables221- Protected: Only available in protected branches222- Masked: Hidden in job logs223- File type: Stored as file224225## Best Practices2262271. **Never commit secrets** to Git2282. **Use different secrets** per environment2293. **Rotate secrets regularly**2304. **Implement least-privilege access**2315. **Enable audit logging**2326. **Use secret scanning** (GitGuardian, TruffleHog)2337. **Mask secrets in logs**2348. **Encrypt secrets at rest**2359. **Use short-lived tokens** when possible23610. **Document secret requirements**237238## Secret Rotation239240### Automated Rotation with AWS241242```python243import boto3244import json245246def lambda_handler(event, context):247 client = boto3.client('secretsmanager')248249 # Get current secret250 response = client.get_secret_value(SecretId='my-secret')251 current_secret = json.loads(response['SecretString'])252253 # Generate new password254 new_password = generate_strong_password()255256 # Update database password257 update_database_password(new_password)258259 # Update secret260 client.put_secret_value(261 SecretId='my-secret',262 SecretString=json.dumps({263 'username': current_secret['username'],264 'password': new_password265 })266 )267268 return {'statusCode': 200}269```270271### Manual Rotation Process2722731. Generate new secret2742. Update secret in secret store2753. Update applications to use new secret2764. Verify functionality2775. Revoke old secret278279## External Secrets Operator280281### Kubernetes Integration282283```yaml284apiVersion: external-secrets.io/v1beta1285kind: SecretStore286metadata:287 name: vault-backend288 namespace: production289spec:290 provider:291 vault:292 server: "https://vault.example.com:8200"293 path: "secret"294 version: "v2"295 auth:296 kubernetes:297 mountPath: "kubernetes"298 role: "production"299300---301apiVersion: external-secrets.io/v1beta1302kind: ExternalSecret303metadata:304 name: database-credentials305 namespace: production306spec:307 refreshInterval: 1h308 secretStoreRef:309 name: vault-backend310 kind: SecretStore311 target:312 name: database-credentials313 creationPolicy: Owner314 data:315 - secretKey: username316 remoteRef:317 key: database/config318 property: username319 - secretKey: password320 remoteRef:321 key: database/config322 property: password323```324325## Secret Scanning326327### Pre-commit Hook328329```bash330#!/bin/bash331# .git/hooks/pre-commit332333# Check for secrets with TruffleHog334docker run --rm -v "$(pwd):/repo" \335 trufflesecurity/trufflehog:latest \336 filesystem --directory=/repo337338if [ $? -ne 0 ]; then339 echo "❌ Secret detected! Commit blocked."340 exit 1341fi342```343344### CI/CD Secret Scanning345346```yaml347secret-scan:348 stage: security349 image: trufflesecurity/trufflehog:latest350 script:351 - trufflehog filesystem .352 allow_failure: false353```354355## Reference Files356357- `references/vault-setup.md` - HashiCorp Vault configuration358- `references/github-secrets.md` - GitHub Secrets best practices359360## Related Skills361362- `github-actions-templates` - For GitHub Actions integration363- `gitlab-ci-patterns` - For GitLab CI integration364- `deployment-pipeline-design` - For pipeline architecture365
Full transparency — inspect the skill content before installing.