-
Notifications
You must be signed in to change notification settings - Fork 0
Open
Labels
Description
Story Summary
As a Security Engineer, I want to restrict proxy access to specific Linux users and time windows, so that a compromised application container cannot query the proxy for administrative secrets.
Phase: 3 - Hardened Ongoing Maintenance
✅ Acceptance Criteria
- iptables/nftables rules restrict which users can reach Aembit proxy (port 8080)
- Only
rootandbackupusers can query the proxy - Docker containers cannot directly query proxy (network namespace isolation)
- Aembit policy denies R2 secret requests outside 2:00 AM - 3:00 AM window
- Application secrets (MySQL, mail) available 24/7 to bootstrap service only
- Audit log shows denied requests from unauthorized sources
📝 Additional Context
Threat Model
| Threat | Mitigation |
|---|---|
| Compromised Ghost container queries proxy | Network namespace isolation - containers can't reach host localhost |
| Attacker gets non-root shell | iptables owner match - only root/backup can reach port 8080 |
| Attacker queries backup creds at wrong time | Aembit time-based policy - R2 creds only available 2-3 AM |
| Attacker queries app secrets | Secrets only fetched at boot by root bootstrap service |
iptables Rules
# /opt/bin/setup-proxy-firewall.sh
# Allow root to access proxy
iptables -A OUTPUT -p tcp --dport 8080 -m owner --uid-owner 0 -j ACCEPT
# Allow backup user to access proxy
iptables -A OUTPUT -p tcp --dport 8080 -m owner --uid-owner backup -j ACCEPT
# Deny all other local access to proxy
iptables -A OUTPUT -p tcp --dport 8080 -d 127.0.0.1 -j DROPButane Configuration
systemd:
units:
- name: proxy-firewall.service
enabled: true
contents: |
[Unit]
Description=Configure Aembit proxy access firewall
After=network.target
Before=aembit-proxy.service
[Service]
Type=oneshot
RemainAfterExit=yes
ExecStart=/opt/bin/setup-proxy-firewall.sh
[Install]
WantedBy=multi-user.targetAembit Time-Based Policy
resource "aembit_access_policy" "backup_r2" {
client_workload_id = aembit_client_workload.ghost_dev.id
credential_provider_id = aembit_credential_provider.r2_backup.id
# Time-based condition
conditions {
time_window {
start_time = "02:00"
end_time = "03:00"
timezone = "UTC"
days = ["monday", "tuesday", "wednesday", "thursday", "friday", "saturday", "sunday"]
}
}
}
resource "aembit_access_policy" "app_secrets" {
client_workload_id = aembit_client_workload.ghost_dev.id
credential_provider_id = aembit_credential_provider.app_secrets.id
# No time restriction - available for boot-time bootstrap
# But only root can reach proxy (enforced by iptables)
}Docker Network Isolation
Docker containers use their own network namespace. By default, localhost inside a container refers to the container's loopback, not the host's. This provides natural isolation.
To verify:
# From host - should work (as root)
curl http://localhost:8080/health
# From container - should fail (different network namespace)
docker exec ghost curl http://localhost:8080/health
# curl: (7) Failed to connect to localhost port 8080: Connection refusedDefense in Depth Layers
Layer 1: Network Namespace
└─► Containers can't reach host localhost
Layer 2: iptables Owner Match
└─► Only root/backup users can reach port 8080
Layer 3: Aembit Time-Based Policy
└─► R2 creds only available 2-3 AM
Layer 4: Aembit Audit Logging
└─► All access attempts logged
Dependencies
- GHO-70: JIT backup credentials (defines what needs time restriction)
📦 Definition of Ready
- Acceptance criteria defined
- Blocked by GHO-70 (JIT backup credentials)
- Story is estimated
- Team has necessary skills and access
- Priority is clear
- Business value understood
✅ Definition of Done
- All acceptance criteria met
- iptables rules deployed and verified
- Non-root user cannot reach proxy (tested)
- Container cannot reach proxy (tested)
- R2 creds denied outside time window (tested)
- Aembit audit logs show denied attempts
- Security documentation updated
Reactions are currently unavailable