Maintenance
Ongoing maintenance tasks for keeping your Serverless CMS healthy, secure, and cost-effective.
On This Page
Backup Procedures
DynamoDB Backups
DynamoDB supports point-in-time recovery and on-demand backups.
Enable Point-in-Time Recovery
aws dynamodb update-continuous-backups \
--table-name serverless-cms-content-store \
--point-in-time-recovery-specification PointInTimeRecoveryEnabled=true \
--region eu-west-2 \
--profile cms-deploy
This enables continuous backups for the last 35 days.
Create On-Demand Backup
aws dynamodb create-backup \
--table-name serverless-cms-content-store \
--backup-name cms-backup-$(date +%Y%m%d-%H%M%S) \
--region eu-west-2 \
--profile cms-deploy
List Backups
aws dynamodb list-backups \
--table-name serverless-cms-content-store \
--region eu-west-2 \
--profile cms-deploy
Restore from Backup
aws dynamodb restore-table-from-backup \
--target-table-name serverless-cms-content-store-restored \
--backup-arn arn:aws:dynamodb:eu-west-2:123456789012:table/serverless-cms-content-store/backup/01234567890123-abcdef12 \
--region eu-west-2 \
--profile cms-deploy
S3 Backups
Enable Versioning
# Enable versioning on Component Store
aws s3api put-bucket-versioning \
--bucket serverless-cms-component-store \
--versioning-configuration Status=Enabled \
--profile cms-deploy
# Enable versioning on Publish Store
aws s3api put-bucket-versioning \
--bucket serverless-cms-publish-store \
--versioning-configuration Status=Enabled \
--profile cms-deploy
Cross-Region Replication (Optional)
For disaster recovery, set up cross-region replication:
- Create destination bucket in another region
- Enable versioning on both buckets
- Create replication rule in S3 console
- Configure IAM role for replication
Export S3 Data
# Sync bucket to local directory
aws s3 sync s3://serverless-cms-component-store ./backups/components/ \
--profile cms-deploy
# Create compressed archive
tar -czf cms-backup-$(date +%Y%m%d).tar.gz ./backups/
Automated Backup Script
Create a backup script to run daily:
#!/bin/bash
# backup-cms.sh
DATE=$(date +%Y%m%d-%H%M%S)
BACKUP_DIR="./backups/$DATE"
# Create backup directory
mkdir -p "$BACKUP_DIR"
# Backup DynamoDB
aws dynamodb create-backup \
--table-name serverless-cms-content-store \
--backup-name "cms-backup-$DATE" \
--region eu-west-2 \
--profile cms-deploy
# Sync S3 buckets
aws s3 sync s3://serverless-cms-component-store "$BACKUP_DIR/components/" \
--profile cms-deploy
aws s3 sync s3://serverless-cms-publish-store "$BACKUP_DIR/publish/" \
--profile cms-deploy
# Compress backup
tar -czf "cms-backup-$DATE.tar.gz" "$BACKUP_DIR"
# Upload to backup bucket (optional)
aws s3 cp "cms-backup-$DATE.tar.gz" s3://my-backup-bucket/ \
--profile cms-deploy
echo "Backup completed: cms-backup-$DATE.tar.gz"
Schedule with cron:
# Run daily at 2 AM
0 2 * * * /path/to/backup-cms.sh
Update Procedures
Update Lambda Functions
To deploy code updates:
# Pull latest code
git pull origin main
# Rebuild project
mvn clean package
# Preview changes
mvn serverless:plan
# Deploy updates
mvn serverless:deploy
Update Node.js Dependencies
# Update Admin UI dependencies
cd src/main/admin-ui
npm update
npm audit fix
# Update Lambda function dependencies
cd ../../functions/cms-functions
npm update
npm audit fix
# Rebuild and redeploy
cd ../..
mvn clean package
mvn serverless:deploy
Update Admin UI
To update only the Admin UI without redeploying Lambda functions:
# Build Admin UI
cd src/main/admin-ui
npm run build
# Upload to S3
aws s3 sync dist/ s3://serverless-cms-admin-tool/ \
--delete \
--profile cms-deploy
# Invalidate CloudFront cache
aws cloudfront create-invalidation \
--distribution-id E1234567890ABC \
--paths "/*" \
--profile cms-deploy
Database Schema Updates
DynamoDB is schemaless, but if you need to migrate data:
- Create backup before migration
- Write migration script using AWS SDK
- Test on development environment first
- Run migration during low-traffic period
- Verify data integrity after migration
Monitoring and Logging
CloudWatch Dashboards
Create a custom dashboard for monitoring:
- Go to CloudWatch → Dashboards
- Create dashboard: "Serverless CMS"
- Add widgets for:
- Lambda invocations
- Lambda errors
- Lambda duration
- API Gateway requests
- API Gateway 4xx/5xx errors
- DynamoDB read/write capacity
- S3 bucket size
- CloudFront requests
CloudWatch Alarms
Set up alarms for critical metrics:
Lambda Error Rate Alarm
aws cloudwatch put-metric-alarm \
--alarm-name cms-lambda-errors \
--alarm-description "Alert when Lambda error rate exceeds 5%" \
--metric-name Errors \
--namespace AWS/Lambda \
--statistic Sum \
--period 300 \
--threshold 5 \
--comparison-operator GreaterThanThreshold \
--evaluation-periods 2 \
--region eu-west-2 \
--profile cms-deploy
API Gateway 5xx Errors
aws cloudwatch put-metric-alarm \
--alarm-name cms-api-5xx-errors \
--alarm-description "Alert on API Gateway 5xx errors" \
--metric-name 5XXError \
--namespace AWS/ApiGateway \
--statistic Sum \
--period 300 \
--threshold 10 \
--comparison-operator GreaterThanThreshold \
--evaluation-periods 1 \
--region eu-west-2 \
--profile cms-deploy
Log Retention
Configure log retention to control costs:
# Set retention to 30 days
aws logs put-retention-policy \
--log-group-name /aws/lambda/serverless-cms-cms-functions-sites-create \
--retention-in-days 30 \
--region eu-west-2 \
--profile cms-deploy
Log Insights Queries
Useful CloudWatch Insights queries:
Find Errors
fields @timestamp, @message
| filter @message like /ERROR/
| sort @timestamp desc
| limit 100
Slow Requests
fields @timestamp, @duration
| filter @duration > 1000
| sort @duration desc
| limit 50
Most Invoked Functions
stats count() by @log
| sort count desc
Performance Optimization
Lambda Optimization
Right-Size Memory
- Monitor Lambda memory usage in CloudWatch
- Adjust memory allocation in
pom.xml - Higher memory = faster CPU but higher cost
- Find optimal balance through testing
Reduce Cold Starts
- Keep deployment packages small (< 10 MB)
- Use Lambda layers for shared dependencies
- Enable provisioned concurrency for critical functions (costs more)
- Minimize initialization code outside handler
DynamoDB Optimization
Use Efficient Access Patterns
- Query instead of Scan when possible
- Use composite keys for efficient queries
- Implement pagination for large result sets
- Use BatchGetItem for multiple items
Monitor Capacity
# Check consumed capacity
aws dynamodb describe-table \
--table-name serverless-cms-content-store \
--region eu-west-2 \
--profile cms-deploy
CloudFront Optimization
Cache Settings
- Set appropriate TTL for static content (1 year)
- Use cache invalidation sparingly (costs money)
- Configure cache behaviors for different content types
Compression
- Enable Gzip/Brotli compression in CloudFront
- Reduces bandwidth and improves load times
Security Updates
Dependency Updates
Regularly update dependencies to patch security vulnerabilities:
# Check for vulnerabilities
npm audit
# Fix vulnerabilities automatically
npm audit fix
# For breaking changes, update manually
npm update package-name
IAM Policy Review
Periodically review IAM policies:
- Remove unused permissions
- Apply principle of least privilege
- Rotate access keys every 90 days
- Enable MFA for all users
Security Scanning
Use AWS security tools:
- AWS Security Hub: Centralized security findings
- AWS Inspector: Automated security assessments
- AWS GuardDuty: Threat detection
- AWS Config: Resource configuration compliance
SSL Certificate Renewal
ACM certificates auto-renew, but verify:
aws acm describe-certificate \
--certificate-arn arn:aws:acm:us-east-1:123456789012:certificate/abc123... \
--region us-east-1 \
--profile cms-deploy
Check RenewalEligibility and Status fields.
Cost Optimization
Monitor Costs
Set up AWS Cost Explorer:
- Go to AWS Cost Management → Cost Explorer
- Enable Cost Explorer (free)
- Create cost reports by service
- Set up budget alerts
Optimize S3 Costs
Lifecycle Policies
# Move old backups to Glacier after 90 days
aws s3api put-bucket-lifecycle-configuration \
--bucket my-backup-bucket \
--lifecycle-configuration file://lifecycle.json \
--profile cms-deploy
lifecycle.json:
{
"Rules": [
{
"Id": "ArchiveOldBackups",
"Status": "Enabled",
"Transitions": [
{
"Days": 90,
"StorageClass": "GLACIER"
}
],
"Expiration": {
"Days": 365
}
}
]
}
Delete Unused Objects
# List old versions
aws s3api list-object-versions \
--bucket serverless-cms-component-store \
--profile cms-deploy
# Delete old versions (be careful!)
aws s3api delete-object \
--bucket serverless-cms-component-store \
--key path/to/object \
--version-id version-id \
--profile cms-deploy
Optimize Lambda Costs
- Right-size memory allocation
- Reduce execution time through optimization
- Use Lambda layers to reduce package size
- Consider reserved concurrency for predictable workloads
Optimize DynamoDB Costs
- Use on-demand billing for unpredictable workloads
- Use provisioned capacity for steady workloads (cheaper)
- Enable auto-scaling for provisioned capacity
- Archive old data to S3
CloudFront Cost Optimization
- Use price class to limit edge locations (e.g., US/Europe only)
- Optimize cache hit ratio to reduce origin requests
- Compress content to reduce data transfer
Maintenance Checklist
Daily
- Check CloudWatch dashboard for anomalies
- Review error logs
- Monitor costs in billing dashboard
Weekly
- Review CloudWatch alarms
- Check backup completion
- Review security findings
- Update npm dependencies
Monthly
- Review and optimize costs
- Update Lambda functions with latest code
- Review IAM policies and permissions
- Test disaster recovery procedures
- Review CloudWatch metrics and adjust alarms
Quarterly
- Rotate IAM access keys
- Review and update security policies
- Perform security audit
- Review and optimize architecture
- Update documentation