Technical Controls
This document details the technical security controls implemented in DocuStack for compliance with HIPAA, SOC 2, and other regulatory frameworks.
Service Control Policies (SCPs)
SCPs provide preventive guardrails that cannot be bypassed, even by account administrators.
| SCP | Target | Effect | Compliance Mapping |
|---|---|---|---|
| Region Restriction | All accounts | Only us-east-1 allowed | Data residency, HIPAA |
| S3 Encryption Required | Workloads OU | Block unencrypted S3 uploads | §164.312(a)(2)(iv) |
| CloudTrail Protection | All accounts | Prevent trail deletion/modification | §164.312(b) |
| Log Archive Protection | Log Archive | Deny object deletion | §164.312(b) |
| Deny Public S3 | Workloads OU | Block public bucket policies | §164.312(e)(1) |
Example: S3 Encryption Required SCP
{
"Version": "2012-10-17",
"Statement": [
{
"Sid": "DenyUnencryptedS3Uploads",
"Effect": "Deny",
"Action": "s3:PutObject",
"Resource": "*",
"Condition": {
"Null": {
"s3:x-amz-server-side-encryption": "true"
}
}
}
]
}
AWS Config Rules
AWS Config provides continuous compliance monitoring with automated remediation.
| Rule | Purpose | Auto-Remediation | HIPAA Mapping |
|---|---|---|---|
encrypted-volumes | EBS encryption required | No | §164.312(a)(2)(iv) |
s3-bucket-server-side-encryption-enabled | S3 encryption required | Yes | §164.312(a)(2)(iv) |
rds-storage-encrypted | RDS encryption required | No | §164.312(a)(2)(iv) |
vpc-flow-logs-enabled | Network logging required | Yes | §164.312(b) |
access-keys-rotated | Key rotation (90 days) | No | §164.308(a)(5)(ii)(D) |
cloudtrail-enabled | API logging required | Yes | §164.312(b) |
iam-password-policy | Password complexity | Yes | §164.308(a)(5)(ii)(D) |
mfa-enabled-for-iam-console-access | MFA required | No | §164.312(d) |
root-account-mfa-enabled | Root MFA required | No | §164.312(d) |
Encryption
At Rest
| Resource | Encryption Method | Key Management |
|---|---|---|
| S3 Buckets | SSE-KMS | Customer Managed Key (CMK) |
| RDS PostgreSQL | AES-256 | Customer Managed Key (CMK) |
| EBS Volumes | AES-256 | Customer Managed Key (CMK) |
| Secrets Manager | AES-256 | AWS Managed Key |
| CloudWatch Logs | AES-256 | AWS Managed Key |
KMS Key Policy Example
{
"Version": "2012-10-17",
"Statement": [
{
"Sid": "Enable IAM policies",
"Effect": "Allow",
"Principal": {"AWS": "arn:aws:iam::ACCOUNT_ID:root"},
"Action": "kms:*",
"Resource": "*"
},
{
"Sid": "Allow service usage",
"Effect": "Allow",
"Principal": {"Service": ["s3.amazonaws.com", "rds.amazonaws.com"]},
"Action": ["kms:Encrypt", "kms:Decrypt", "kms:GenerateDataKey*"],
"Resource": "*"
}
]
}
In Transit
| Connection | Protocol | Minimum Version |
|---|---|---|
| Client to ALB | HTTPS | TLS 1.2 |
| ALB to ECS | HTTPS | TLS 1.2 |
| ECS to RDS | TLS | TLS 1.2 (forced via rds.force_ssl=1) |
| ECS to S3 | HTTPS | TLS 1.2 (via VPC endpoint) |
| ECS to AWS APIs | HTTPS | TLS 1.2 (via VPC endpoints) |
Network Security
Architecture
┌─────────────────────────────────────────────────────────────────────────────┐
│ VPC (10.X.0.0/16) │
├─────────────────────────────────────────────────────────────────────────────┤
│ │
│ ┌─────────────────────────────────────────────────────────────────────┐ │
│ │ Public Subnets (Load Balancers Only) │ │
│ │ • ALB (HTTPS 443 only) │ │
│ │ • NAT Gateway (outbound only) │ │
│ └─────────────────────────────────────────────────────────────────────┘ │
│ │ │
│ ┌─────────────────────────────────────────────────────────────────────┐ │
│ │ Private Subnets (Compute) │ │
│ │ • ECS Fargate tasks (NO public IPs) │ │
│ │ • Access AWS services via VPC endpoints │ │
│ └─────────────────────────────────────────────────────────────────────┘ │
│ │ │
│ ┌─────────────────────────────────────────────────────────────────────┐ │
│ │ Database Subnets (Isolated) │ │
│ │ • RDS PostgreSQL │ │
│ │ • No internet access │ │
│ │ • Access only from private subnets │ │
│ └─────────────────────────────────────────────────────────────────────┘ │
│ │
│ ┌─────────────────────────────────────────────────────────────────────┐ │
│ │ VPC Endpoints (PrivateLink) │ │
│ │ • S3, ECR, CloudWatch, Secrets Manager, SSM, KMS │ │
│ │ • Traffic stays within AWS network │ │
│ └─────────────────────────────────────────────────────────────────────┘ │
│ │
└─────────────────────────────────────────────────────────────────────────────┘
CIDR Allocation
| Environment | VPC CIDR | Public Subnets | Private Subnets | Database Subnets |
|---|---|---|---|---|
| Dev | 10.0.0.0/16 | 10.0.1.0/24, 10.0.2.0/24 | 10.0.10.0/24, 10.0.11.0/24 | 10.0.20.0/24, 10.0.21.0/24 |
| Staging | 10.1.0.0/16 | 10.1.1.0/24, 10.1.2.0/24 | 10.1.10.0/24, 10.1.11.0/24 | 10.1.20.0/24, 10.1.21.0/24 |
| Prod | 10.2.0.0/16 | 10.2.1.0/24, 10.2.2.0/24 | 10.2.10.0/24, 10.2.11.0/24 | 10.2.20.0/24, 10.2.21.0/24 |
VPC Endpoints
VPC endpoints reduce NAT Gateway costs and improve security by keeping traffic within AWS:
| Endpoint | Type | Purpose | Cost |
|---|---|---|---|
s3 | Gateway | Document storage access | Free |
dynamodb | Gateway | Terraform state locking | Free |
ecr.api | Interface | Container image pulls | ~$7/mo |
ecr.dkr | Interface | Container image pulls | ~$7/mo |
logs | Interface | CloudWatch logging | ~$7/mo |
secretsmanager | Interface | Credential retrieval | ~$7/mo |
ssm | Interface | Parameter Store access | ~$7/mo |
kms | Interface | Encryption operations | ~$7/mo |
Security Groups
| Security Group | Inbound | Outbound |
|---|---|---|
| ALB | 443 from 0.0.0.0/0 | All to ECS SG |
| ECS | 8080 from ALB SG | All to VPC endpoints, NAT |
| RDS | 5432 from ECS SG | None |
| VPC Endpoints | 443 from private subnets | None |
Key Security Features
- No public IPs: All ECS tasks run in private subnets
- VPC endpoints: AWS service traffic stays within VPC
- Security groups: Least-privilege, explicit allow rules
- NACLs: Additional subnet-level filtering
- VPC Flow Logs: All traffic logged to S3 (Log Archive account)
Audit Logging
| Log Type | Source | Destination | Retention |
|---|---|---|---|
| CloudTrail | All accounts | Log Archive S3 | 7 years |
| VPC Flow Logs | All VPCs | Log Archive S3 | 1 year |
| CloudWatch Logs | Applications | CloudWatch | 90 days |
| S3 Access Logs | Document buckets | Log Archive S3 | 1 year |
| RDS Audit Logs | PostgreSQL | CloudWatch | 90 days |
| ALB Access Logs | Load balancers | Log Archive S3 | 1 year |
Continuous Monitoring
| Tool | Purpose | Alert Threshold |
|---|---|---|
| AWS Config | Configuration compliance | Any non-compliant resource |
| Security Hub | Security findings aggregation | Medium+ severity |
| GuardDuty | Threat detection | All findings |
| CloudWatch | Operational metrics | Custom thresholds |
| CloudTrail | API activity monitoring | Specific events |
Disaster Recovery
Recovery Objectives
| Metric | Target | Implementation |
|---|---|---|
| RTO | 4 hours | Multi-AZ, automated recovery |
| RPO | 1 hour | Continuous replication, hourly backups |
Backup Strategy
| Resource | Backup Method | Frequency | Retention |
|---|---|---|---|
| RDS PostgreSQL | Automated snapshots | Daily | 7 days (35 days prod) |
| RDS PostgreSQL | Transaction logs | Continuous | 7 days |
| S3 Documents | Versioning | Continuous | Indefinite |
| S3 Documents | Cross-region replication | Continuous | Same as source |
| Terraform State | S3 versioning | On change | 30 versions |
DR Scenarios
| Scenario | Recovery Procedure | RTO |
|---|---|---|
| Single AZ failure | Automatic failover to standby AZ | < 5 minutes |
| Region failure | Restore from cross-region backups | 4 hours |
| Data corruption | Point-in-time recovery | 1 hour |
| Ransomware | Restore from immutable backups | 4 hours |