security-group-analyzer
Security Group Analyzer
Audit AWS security groups and identify security vulnerabilities.
Quick Start
List security groups, check for 0.0.0.0/0 access, restrict to minimum needed ports and IPs.
Instructions
Security Group Audit Process
- List all security groups
- Identify overly permissive rules
- Check for unused security groups
- Recommend restrictions
- Implement changes
List Security Groups
# List all security groups
aws ec2 describe-security-groups \
--query 'SecurityGroups[].[GroupId,GroupName,Description]' \
--output table
# Get specific security group
aws ec2 describe-security-groups \
--group-ids sg-1234567890abcdef0
Common Security Issues
1. Open to the world (0.0.0.0/0)
Find security groups with unrestricted access:
aws ec2 describe-security-groups \
--filters "Name=ip-permission.cidr,Values=0.0.0.0/0" \
--query 'SecurityGroups[].[GroupId,GroupName,IpPermissions[?IpRanges[?CidrIp==`0.0.0.0/0`]]]'
High-risk ports open to 0.0.0.0/0:
- 22 (SSH)
- 3389 (RDP)
- 3306 (MySQL)
- 5432 (PostgreSQL)
- 27017 (MongoDB)
- 6379 (Redis)
2. Unrestricted outbound rules
Default security groups allow all outbound traffic. Restrict if possible:
# Check outbound rules
aws ec2 describe-security-groups \
--group-ids sg-1234567890abcdef0 \
--query 'SecurityGroups[].IpPermissionsEgress'
3. Unused security groups
Find security groups not attached to any resources:
# List all security groups
aws ec2 describe-security-groups --query 'SecurityGroups[].GroupId' > all-sgs.txt
# List security groups in use
aws ec2 describe-instances --query 'Reservations[].Instances[].SecurityGroups[].GroupId' > used-sgs.txt
aws rds describe-db-instances --query 'DBInstances[].VpcSecurityGroups[].VpcSecurityGroupId' >> used-sgs.txt
# Compare to find unused
Security Best Practices
Principle of least privilege:
- Only allow necessary ports
- Restrict source IPs to minimum needed
- Use security group references instead of CIDR blocks
SSH/RDP access:
# Bad: Open to world
0.0.0.0/0 on port 22
# Good: Restrict to office IP
203.0.113.0/24 on port 22
# Better: Use bastion host or AWS Systems Manager Session Manager
Database access:
# Bad: Open to world
0.0.0.0/0 on port 3306
# Good: Only from application security group
sg-app-12345678 on port 3306
Web servers:
# Acceptable: HTTP/HTTPS from anywhere
0.0.0.0/0 on port 80, 443
# But use CloudFront or ALB for additional protection
Restricting Security Groups
Remove overly permissive rule:
# Revoke SSH from anywhere
aws ec2 revoke-security-group-ingress \
--group-id sg-1234567890abcdef0 \
--protocol tcp \
--port 22 \
--cidr 0.0.0.0/0
Add restricted rule:
# Allow SSH only from office
aws ec2 authorize-security-group-ingress \
--group-id sg-1234567890abcdef0 \
--protocol tcp \
--port 22 \
--cidr 203.0.113.0/24
Use security group references:
# Allow traffic from another security group
aws ec2 authorize-security-group-ingress \
--group-id sg-database-12345678 \
--protocol tcp \
--port 3306 \
--source-group sg-app-12345678
Security Group Rules
Inbound rules structure:
- Protocol: TCP, UDP, ICMP, or All
- Port range: Single port or range
- Source: CIDR block or security group
Example secure configuration:
Web tier (ALB):
Inbound:
- HTTP (80) from 0.0.0.0/0
- HTTPS (443) from 0.0.0.0/0
Outbound:
- All traffic to app-tier-sg
App tier:
Inbound:
- Port 8080 from web-tier-sg
Outbound:
- Port 3306 to db-tier-sg
- HTTPS (443) to 0.0.0.0/0 (for external APIs)
Database tier:
Inbound:
- Port 3306 from app-tier-sg
Outbound:
- None (or minimal)
Audit Checklist
Critical issues:
- SSH (22) open to 0.0.0.0/0
- RDP (3389) open to 0.0.0.0/0
- Database ports open to 0.0.0.0/0
- All ports open to 0.0.0.0/0
High priority:
- Unused security groups
- Overly broad CIDR ranges
- Unnecessary outbound rules
- Missing descriptions
Best practices:
- Use security group references
- Tag security groups
- Document purpose
- Regular audits
Common Patterns
Bastion host:
Bastion SG:
Inbound:
- SSH (22) from office IP only
Private instance SG:
Inbound:
- SSH (22) from bastion-sg only
Load balancer pattern:
ALB SG:
Inbound:
- HTTP/HTTPS from 0.0.0.0/0
App SG:
Inbound:
- App port from alb-sg only
Database pattern:
DB SG:
Inbound:
- DB port from app-sg only
- DB port from bastion-sg (for admin)
Monitoring and Alerts
CloudWatch Events for security group changes:
{
"source": ["aws.ec2"],
"detail-type": ["AWS API Call via CloudTrail"],
"detail": {
"eventName": [
"AuthorizeSecurityGroupIngress",
"RevokeSecurityGroupIngress"
]
}
}
AWS Config rules:
- restricted-ssh: Checks for SSH from 0.0.0.0/0
- restricted-common-ports: Checks for common ports
- vpc-sg-open-only-to-authorized-ports
Remediation Steps
For SSH/RDP open to world:
- Identify who needs access
- Get their IP addresses
- Restrict to those IPs
- Or use AWS Systems Manager Session Manager
For database ports open:
- Identify application security groups
- Remove 0.0.0.0/0 rule
- Add security group reference rules
- Test connectivity
For unused security groups:
- Verify not in use
- Document before deletion
- Delete security group
- Monitor for issues
Tools
AWS Security Hub:
- Automated security checks
- Compliance standards
- Findings aggregation
AWS Config:
- Track security group changes
- Compliance rules
- Automated remediation
Third-party tools:
- Prowler (open source)
- CloudMapper
- ScoutSuite
Example Audit Report
Security Group Audit Report
===========================
Critical Issues:
- sg-12345678: SSH (22) open to 0.0.0.0/0
- sg-23456789: MySQL (3306) open to 0.0.0.0/0
High Priority:
- sg-34567890: Unused security group
- sg-45678901: RDP from broad CIDR (10.0.0.0/8)
Recommendations:
1. Restrict SSH to office IP: 203.0.113.0/24
2. Restrict MySQL to app security group: sg-app-12345
3. Delete unused security group: sg-34567890
4. Narrow RDP access to specific subnet
Estimated risk reduction: High
Best Practices
Regular audits:
- Weekly: Check for new overly permissive rules
- Monthly: Review all security groups
- Quarterly: Clean up unused security groups
Documentation:
- Add descriptions to all security groups
- Document purpose of each rule
- Tag security groups by environment/project
Automation:
- Use AWS Config for continuous monitoring
- Set up CloudWatch alarms for changes
- Automate remediation where possible
Defense in depth:
- Security groups are one layer
- Also use NACLs, WAF, Shield
- Implement application-level security
More from armanzeroeight/fastagent-plugins
gcp-cost-optimizer
Analyzes GCP costs and provides optimization recommendations including committed use discounts, rightsizing, and unused resources. Use when optimizing GCP spending or analyzing GCP costs.
15kubernetes-best-practices
Provides production-ready Kubernetes manifest guidance including resource management, security, high availability, and configuration best practices. This skill should be used when working with Kubernetes YAML files, deployments, pods, services, or when users mention k8s, container orchestration, or cloud-native applications.
11schema-designer
Design database schemas with proper normalization, relationships, constraints, and indexes. Use when creating database tables, modeling data relationships, or designing database structure.
11api-documentation-generator
Generate OpenAPI/Swagger specifications and API documentation from code or design. Use when creating API docs, generating OpenAPI specs, or documenting REST APIs.
9goroutine-patterns
Implement Go concurrency patterns using goroutines, channels, and synchronization primitives. Use when building concurrent systems, implementing parallelism, or managing goroutine lifecycles. Trigger words include "goroutine", "channel", "concurrent", "parallel", "sync", "context".
9inventory-manager
Organizes Ansible inventory files, manages host groups, and configures dynamic inventory. Use when organizing Ansible inventory, managing host groups, or setting up dynamic inventory sources.
9