Module Overview
Estimated Time : 6-8 hours | Difficulty : Intermediate | Prerequisites : Core Concepts
This module covers AWS security from IAM fundamentals to advanced patterns including threat detection, compliance monitoring, and network protection. Security is critical for the AWS certification exams and real-world architecture.
Important : Learning cloud without security is incomplete and can lead to major risks. This module covers core security services and best practices that are essential for any production workload.
What You’ll Learn:
IAM users, groups, roles, and policies
IAM Identity Center (AWS SSO) for centralized access
Policy evaluation logic and troubleshooting
AWS Organizations and SCPs
KMS encryption and key management
Secrets management patterns
Threat Detection : GuardDuty, Inspector, Macie
Compliance & Audit : CloudTrail, AWS Config, Security Hub
Monitoring : CloudWatch logs, metrics, and alarms
Network Protection : WAF, Shield, Firewall Manager
Defense in depth strategies
IAM (Identity and Access Management)
IAM controls WHO can access WHAT in your AWS account. The most fundamental AWS security service.
IAM Components
┌────────────────────────────────────────────────────────────────┐
│ AWS Account │
├────────────────────────────────────────────────────────────────┤
│ │
│ Root User ([email protected] ) - NEVER use for daily tasks │
│ │ │
│ ▼ │
│ ┌──────────────────────────────────────────────────────────┐ │
│ │ IAM │ │
│ │ │ │
│ │ USERS GROUPS ROLES │ │
│ │ ───── ────── ───── │ │
│ │ • John • Admins • EC2-S3-Role │ │
│ │ • Jane • Developers • Lambda-DynamoDB │ │
│ │ • API-User • ReadOnly • Cross-Account │ │
│ │ │ │
│ │ POLICIES │ │
│ │ ──────── │ │
│ │ • AdministratorAccess (AWS Managed) │ │
│ │ • S3ReadOnly (AWS Managed) │ │
│ │ • CustomAppPolicy (Customer Managed) │ │
│ │ │ │
│ └──────────────────────────────────────────────────────────┘ │
│ │
└────────────────────────────────────────────────────────────────┘
Users vs Roles
Feature IAM Users IAM Roles Identity Permanent Temporary Credentials Password/Access Keys Temporary tokens Use Case Humans, CI/CD Services, cross-account Best Practice MFA required Preferred for applications
IAM Policies
JSON documents that define permissions.
Policy Structure
{
"Version" : "2012-10-17" ,
"Statement" : [
{
"Sid" : "AllowS3Read" ,
"Effect" : "Allow" ,
"Action" : [
"s3:GetObject" ,
"s3:ListBucket"
],
"Resource" : [
"arn:aws:s3:::my-bucket" ,
"arn:aws:s3:::my-bucket/*"
],
"Condition" : {
"IpAddress" : {
"aws:SourceIp" : "203.0.113.0/24"
}
}
}
]
}
Policy Elements
Element Description Example Effect Allow or Deny "Effect": "Allow"Action What operations "s3:GetObject"Resource Which resources "arn:aws:s3:::bucket/*"Condition When to apply IP address, time, MFA Principal Who (for resource policies) "AWS": "arn:aws:iam::123:user/Bob"
Common Policy Patterns
// Allow EC2 to assume a role
{
"Version" : "2012-10-17" ,
"Statement" : [
{
"Effect" : "Allow" ,
"Principal" : {
"Service" : "ec2.amazonaws.com"
},
"Action" : "sts:AssumeRole"
}
]
}
// Deny all S3 delete operations
{
"Effect" : "Deny" ,
"Action" : "s3:Delete*" ,
"Resource" : "*"
}
// Allow only with MFA
{
"Effect" : "Allow" ,
"Action" : "*" ,
"Resource" : "*" ,
"Condition" : {
"Bool" : {
"aws:MultiFactorAuthPresent" : "true"
}
}
}
Policy Evaluation Logic
┌────────────────────────────────────────────────────────────────┐
│ Policy Evaluation Flow │
├────────────────────────────────────────────────────────────────┤
│ │
│ Request comes in │
│ │ │
│ ▼ │
│ ┌───────────────────────┐ │
│ │ Explicit DENY exists? │ │
│ └───────────┬───────────┘ │
│ Yes │ No │
│ ┌──────────┴──────────┐ │
│ ▼ ▼ │
│ ┌─────────┐ ┌───────────────────┐ │
│ │ DENY │ │ Explicit ALLOW │ │
│ │ Request │ │ exists? │ │
│ └─────────┘ └─────────┬─────────┘ │
│ Yes │ No │
│ ┌──────────┴──────────┐ │
│ ▼ ▼ │
│ ┌─────────┐ ┌─────────┐ │
│ │ ALLOW │ │ DENY │ │
│ │ Request │ │(implicit)│ │
│ └─────────┘ └─────────┘ │
│ │
│ Key: Explicit DENY always wins! │
│ │
└────────────────────────────────────────────────────────────────┘
IAM Roles for Services
Allow AWS services to access other AWS resources.
EC2 Instance Profile
┌────────────────────────────────────────────────────────────────┐
│ EC2 with IAM Role │
├────────────────────────────────────────────────────────────────┤
│ │
│ ┌─────────────────────────────────────────────────────────┐ │
│ │ EC2 Instance │ │
│ │ │ │
│ │ Instance Profile │ │
│ │ ┌──────────────────────────────────────────────────┐ │ │
│ │ │ IAM Role │ │ │
│ │ │ ┌────────────────────────────────────────────┐ │ │ │
│ │ │ │ Attached Policy │ │ │ │
│ │ │ │ • s3:GetObject on my-bucket │ │ │ │
│ │ │ │ • dynamodb:* on my-table │ │ │ │
│ │ │ └────────────────────────────────────────────┘ │ │ │
│ │ └──────────────────────────────────────────────────┘ │ │
│ │ │ │
│ │ Application code uses SDK - no credentials needed! │ │
│ │ boto3.client('s3') # Automatically uses role │ │
│ │ │ │
│ └─────────────────────────────────────────────────────────┘ │
│ │
└────────────────────────────────────────────────────────────────┘
import boto3
# On EC2 with role - credentials automatically retrieved
s3 = boto3.client( 's3' ) # No access keys needed!
# SDK automatically calls instance metadata service:
# curl http://169.254.169.254/latest/meta-data/iam/security-credentials/MyRole
AWS Organizations
Manage multiple AWS accounts centrally.
┌────────────────────────────────────────────────────────────────┐
│ AWS Organizations │
├────────────────────────────────────────────────────────────────┤
│ │
│ Management Account (Root) │
│ │ │
│ ├── OU: Production │
│ │ ├── Account: Prod-App1 │
│ │ └── Account: Prod-App2 │
│ │ │
│ ├── OU: Development │
│ │ ├── Account: Dev │
│ │ └── Account: Staging │
│ │ │
│ └── OU: Security │
│ ├── Account: Audit │
│ └── Account: Log-Archive │
│ │
│ Service Control Policies (SCPs) │
│ ───────────────────────────── │
│ • Apply guardrails across OUs/Accounts │
│ • Cannot grant permissions, only restrict │
│ • Example: Deny leaving organization │
│ │
└────────────────────────────────────────────────────────────────┘
IAM Identity Center (AWS SSO)
IAM Identity Center provides centralized identity management for workforce users across your AWS Organization. It replaces the need to create individual IAM users in each account.
Why Use IAM Identity Center?
Single Sign-On One login provides access to all AWS accounts and applications
Centralized Management Manage users and permissions from a single place
No Long-Term Credentials Temporary credentials automatically issued and rotated
External IdP Integration Connect to Okta, Azure AD, Google Workspace, and more
Identity Sources
Source Description Best For Identity Center Directory Built-in user directory Small teams, getting started Active Directory AWS Managed AD or AD Connector Enterprises with existing AD External IdP (SAML 2.0) Okta, Azure AD, Google, OneLogin Organizations with existing IdP External IdP (OIDC) OAuth 2.0 / OpenID Connect Modern identity providers
Setting Up External IdP with SAML 2.0
┌─────────────────────────────────────────────────────────────────────┐
│ SAML 2.0 Federation Flow │
├─────────────────────────────────────────────────────────────────────┤
│ │
│ User External IdP AWS Identity Center│
│ │ │ │ │
│ │ 1. Access AWS Portal │ │ │
│ │─────────────────────────────────────────────────────► │
│ │ │ │ │
│ │ 2. Redirect to IdP │ │ │
│ │◄───────────────────────────────────────────────────│ │
│ │ │ │ │
│ │ 3. Authenticate │ │ │
│ │──────────────────────►│ │ │
│ │ │ │ │
│ │ 4. SAML Assertion │ │ │
│ │◄──────────────────────│ │ │
│ │ │ │ │
│ │ 5. SAML + Session │ │ │
│ │─────────────────────────────────────────────────────► │
│ │ │ │ │
│ │ 6. Access Granted (Temp Credentials) │ │
│ │◄───────────────────────────────────────────────────│ │
│ │
└─────────────────────────────────────────────────────────────────────┘
Permission Sets
Permission Sets define what users can do in AWS accounts. They are reusable templates attached to users/groups for specific accounts.
// Example: ReadOnlyAccess Permission Set
{
"Name" : "ReadOnlyAccess" ,
"Description" : "Read-only access across all services" ,
"ManagedPolicies" : [
"arn:aws:iam::aws:policy/ReadOnlyAccess"
],
"SessionDuration" : "PT4H" , // 4 hours
"Tags" : {
"Environment" : "Production"
}
}
// Example: Custom Admin Permission Set with inline policy
{
"Name" : "DatabaseAdmin" ,
"Description" : "Full RDS and DynamoDB access" ,
"InlinePolicy" : {
"Version" : "2012-10-17" ,
"Statement" : [
{
"Effect" : "Allow" ,
"Action" : [
"rds:*" ,
"dynamodb:*"
],
"Resource" : "*"
}
]
},
"PermissionsBoundary" : {
"ManagedPolicyArn" : "arn:aws:iam::aws:policy/PowerUserAccess"
}
}
Identity Center CLI Configuration
# Configure AWS CLI for Identity Center SSO
aws configure sso
# Follow prompts:
# - SSO start URL: https://my-org.awsapps.com/start
# - SSO Region: us-east-1
# - Choose account and role
# Login via SSO
aws sso login --profile my-sso-profile
# Use SSO profile
aws s3 ls --profile my-sso-profile
External IdP Configuration (Okta Example)
┌─────────────────────────────────────────────────────────────────────┐
│ Okta ↔ AWS Identity Center │
├─────────────────────────────────────────────────────────────────────┤
│ │
│ In Okta: │
│ ──────── │
│ 1. Add "AWS IAM Identity Center" application │
│ 2. Configure SAML settings: │
│ • ACS URL: https://[region].signin.aws.amazon.com/saml │
│ • Audience URI: urn:amazon:webservices │
│ 3. Download IdP metadata XML │
│ │
│ In AWS Identity Center: │
│ ───────────────────────── │
│ 1. Settings → Identity source → Change identity source │
│ 2. Select "External identity provider" │
│ 3. Upload IdP metadata │
│ 4. Configure SCIM for automatic user/group provisioning │
│ │
│ SCIM Endpoint: https://scim.[region].amazonaws.com/[instance-id] │
│ │
└─────────────────────────────────────────────────────────────────────┘
ABAC (Attribute-Based Access Control)
Identity Center supports passing user attributes from your IdP for fine-grained access control.
// Session policy using attributes
{
"Version" : "2012-10-17" ,
"Statement" : [
{
"Effect" : "Allow" ,
"Action" : "s3:*" ,
"Resource" : "arn:aws:s3:::company-data/${aws:PrincipalTag/department}/*" ,
"Condition" : {
"StringEquals" : {
"aws:PrincipalTag/team" : "${s3:ExistingObjectTag/team}"
}
}
}
]
}
Encryption
Encryption at Rest
Service Encryption Method S3 SSE-S3, SSE-KMS, SSE-C EBS AES-256 with KMS RDS AES-256 with KMS DynamoDB AWS owned or KMS
Encryption in Transit
TLS/SSL for all API calls
HTTPS endpoints
VPN for hybrid connectivity
AWS KMS (Key Management Service)
┌────────────────────────────────────────────────────────────────┐
│ AWS KMS │
├────────────────────────────────────────────────────────────────┤
│ │
│ Key Types: │
│ ───────── │
│ • AWS Managed Keys (aws/s3, aws/ebs) │
│ - Automatic rotation │
│ - Cannot control policies │
│ │
│ • Customer Managed Keys (CMK) │
│ - You control key policies │
│ - Optional automatic rotation (yearly) │
│ - Audit via CloudTrail │
│ │
│ • Customer Managed Keys (External) │
│ - Bring your own key material │
│ - You manage rotation │
│ │
│ Envelope Encryption: │
│ ┌───────────────────────────────────────────────────────┐ │
│ │ CMK encrypts → Data Key │ │
│ │ Data Key encrypts → Your Data │ │
│ │ │ │
│ │ Store: [Encrypted Data Key] + [Encrypted Data] │ │
│ └───────────────────────────────────────────────────────┘ │
│ │
└────────────────────────────────────────────────────────────────┘
Security Best Practices
Enable MFA Require MFA for root and privileged users
Least Privilege Grant only necessary permissions
Use Roles Prefer roles over long-term credentials
Rotate Keys Regularly rotate access keys
Enable CloudTrail Log all API calls for auditing
Use SCPs Enforce guardrails across accounts
Security Checklist
security_checklist = {
"identity" : [
"✓ MFA on root account" ,
"✓ No access keys on root" ,
"✓ Individual IAM users (no sharing)" ,
"✓ Groups for permissions" ,
"✓ Strong password policy" ,
],
"access" : [
"✓ Least privilege policies" ,
"✓ Roles for applications" ,
"✓ Regular access reviews" ,
"✓ Remove unused credentials" ,
],
"monitoring" : [
"✓ CloudTrail enabled (all regions)" ,
"✓ Config rules for compliance" ,
"✓ GuardDuty for threat detection" ,
"✓ Security Hub for findings" ,
],
"network" : [
"✓ Private subnets for databases" ,
"✓ Security groups (least privilege)" ,
"✓ VPC Flow Logs enabled" ,
"✓ WAF for public applications" ,
],
"data" : [
"✓ Encryption at rest (KMS)" ,
"✓ Encryption in transit (TLS)" ,
"✓ S3 Block Public Access" ,
"✓ Backup and recovery tested" ,
]
}
Security Services Overview
AWS provides a comprehensive suite of security services for threat detection, compliance monitoring, and network protection.
Service Purpose Key Feature IAM Identity and access management Fine-grained permissions IAM Identity Center Centralized SSO for Organizations External IdP integration KMS Key management for encryption Envelope encryption Secrets Manager Store and rotate secrets Automatic rotation CloudTrail API activity logging Who did what, when Config Resource compliance monitoring Continuous compliance GuardDuty Threat detection ML-powered analysis Security Hub Security findings aggregation Unified dashboard WAF Web Application Firewall OWASP protection Shield DDoS protection Layer 3/4/7 Inspector Vulnerability scanning CVE detection Macie Sensitive data discovery PII detection in S3
Threat Detection Services
Amazon GuardDuty
GuardDuty is an intelligent threat detection service that continuously monitors for malicious activity and unauthorized behavior.
┌────────────────────────────────────────────────────────────────────┐
│ Amazon GuardDuty │
├────────────────────────────────────────────────────────────────────┤
│ │
│ Data Sources: Finding Categories: │
│ ───────────── ─────────────────── │
│ • CloudTrail Events • Recon (port scans) │
│ • VPC Flow Logs • Instance Compromise │
│ • DNS Logs • Account Compromise │
│ • S3 Data Events • Bucket Compromise │
│ • EKS Audit Logs • Malware Detection │
│ • RDS Login Activity • Cryptocurrency Mining │
│ │
│ ┌──────────────────────────────────────────────────────────────┐ │
│ │ ML Models analyze behavior patterns to detect anomalies │ │
│ │ Threat intelligence feeds from AWS and third parties │ │
│ │ Automatic updates - no infrastructure to manage │ │
│ └──────────────────────────────────────────────────────────────┘ │
│ │
└────────────────────────────────────────────────────────────────────┘
Key Features:
No agents required : Analyzes AWS logs directly
Multi-account support : Centralized via Organizations
Automated response : Integrate with EventBridge for remediation
30-day free trial : Test before committing
import boto3
# Enable GuardDuty (run in each region)
guardduty = boto3.client( 'guardduty' , region_name = 'us-east-1' )
# Create detector
response = guardduty.create_detector(
Enable = True ,
FindingPublishingFrequency = 'FIFTEEN_MINUTES' ,
DataSources = {
'S3Logs' : { 'Enable' : True },
'Kubernetes' : { 'AuditLogs' : { 'Enable' : True }},
'MalwareProtection' : { 'ScanEc2InstanceWithFindings' : { 'EbsVolumes' : True }}
}
)
# List findings
findings = guardduty.list_findings(
DetectorId = response[ 'DetectorId' ],
FindingCriteria = {
'Criterion' : {
'severity' : { 'Gte' : 7 } # High severity only
}
}
)
Amazon Inspector
Inspector automatically discovers and scans workloads for software vulnerabilities and network exposure.
┌────────────────────────────────────────────────────────────────────┐
│ Amazon Inspector │
├────────────────────────────────────────────────────────────────────┤
│ │
│ Scan Targets: Vulnerability Types: │
│ ───────────── ──────────────────── │
│ • EC2 Instances • CVEs in installed packages │
│ • Lambda Functions • Network reachability issues │
│ • Container Images (ECR) • Code vulnerabilities (Lambda) │
│ │
│ Continuous Scanning: │
│ ┌────────────────────────────────────────────────────────────┐ │
│ │ EC2: Rescans when new CVEs published or package changes │ │
│ │ ECR: Scans on push and when new CVEs discovered │ │
│ │ Lambda: Scans on deploy and when dependencies update │ │
│ └────────────────────────────────────────────────────────────┘ │
│ │
│ Risk Score: 1-10 based on CVSS + network exposure + exploitability│
│ │
└────────────────────────────────────────────────────────────────────┘
Amazon Macie
Macie uses machine learning to discover, classify, and protect sensitive data in S3.
# Macie sensitive data findings example
macie_finding = {
"finding_type" : "SensitiveData:S3Object/Personal" ,
"severity" : "HIGH" ,
"s3_bucket" : "customer-data-bucket" ,
"s3_object" : "exports/users.csv" ,
"sensitive_data" : {
"category" : "PERSONAL_INFORMATION" ,
"detections" : [
{ "type" : "EMAIL_ADDRESS" , "count" : 1547 },
{ "type" : "PHONE_NUMBER" , "count" : 892 },
{ "type" : "CREDIT_CARD_NUMBER" , "count" : 23 },
{ "type" : "AWS_CREDENTIALS" , "count" : 2 }
]
},
"recommendation" : "Enable S3 encryption, review access policies"
}
Logging and Audit Services
AWS CloudTrail
CloudTrail records all API calls made in your AWS account - essential for security analysis, compliance, and troubleshooting.
┌────────────────────────────────────────────────────────────────────┐
│ AWS CloudTrail │
├────────────────────────────────────────────────────────────────────┤
│ │
│ Event Types: │
│ ───────────── │
│ • Management Events: Control plane (CreateBucket, RunInstances) │
│ • Data Events: Data plane (GetObject, PutItem) │
│ • Insights Events: Unusual API activity patterns │
│ │
│ Trail Configuration: │
│ ┌────────────────────────────────────────────────────────────┐ │
│ │ • Multi-region trail (recommended) │ │
│ │ • Organization trail for all accounts │ │
│ │ • Log file validation (integrity) │ │
│ │ • Encrypt with KMS │ │
│ │ • Send to CloudWatch Logs for alerting │ │
│ └────────────────────────────────────────────────────────────┘ │
│ │
│ Storage: S3 bucket (5 years recommended for compliance) │
│ │
└────────────────────────────────────────────────────────────────────┘
CloudTrail Event Example:
{
"eventVersion" : "1.08" ,
"userIdentity" : {
"type" : "AssumedRole" ,
"principalId" : "AROAEXAMPLE:admin-session" ,
"arn" : "arn:aws:sts::123456789012:assumed-role/AdminRole/admin-session" ,
"accountId" : "123456789012"
},
"eventTime" : "2024-01-15T10:30:00Z" ,
"eventSource" : "s3.amazonaws.com" ,
"eventName" : "DeleteBucket" ,
"awsRegion" : "us-east-1" ,
"sourceIPAddress" : "203.0.113.50" ,
"userAgent" : "aws-cli/2.0" ,
"requestParameters" : {
"bucketName" : "important-data-bucket"
},
"responseElements" : null ,
"errorCode" : null
}
CloudTrail Insights Configuration:
import boto3
cloudtrail = boto3.client( 'cloudtrail' )
# Create trail with Insights enabled
trail = cloudtrail.create_trail(
Name = 'organization-trail' ,
S3BucketName = 'cloudtrail-logs-bucket' ,
IsMultiRegionTrail = True ,
EnableLogFileValidation = True ,
KMSKeyId = 'arn:aws:kms:us-east-1:123456789012:key/example-key' ,
IsOrganizationTrail = True
)
# Enable Insights
cloudtrail.put_insight_selectors(
TrailName = 'organization-trail' ,
InsightSelectors = [
{ 'InsightType' : 'ApiCallRateInsight' },
{ 'InsightType' : 'ApiErrorRateInsight' }
]
)
AWS Config
Config continuously monitors and records AWS resource configurations and evaluates them against desired configurations.
┌────────────────────────────────────────────────────────────────────┐
│ AWS Config │
├────────────────────────────────────────────────────────────────────┤
│ │
│ Core Features: │
│ ────────────── │
│ • Configuration Recording: Track all resource changes │
│ • Config Rules: Evaluate compliance (managed + custom) │
│ • Conformance Packs: Collections of rules (CIS, PCI-DSS) │
│ • Aggregator: Multi-account/region view │
│ │
│ Common Managed Rules: │
│ ───────────────────── │
│ • s3-bucket-public-read-prohibited │
│ • encrypted-volumes │
│ • iam-password-policy │
│ • rds-instance-public-access-check │
│ • vpc-flow-logs-enabled │
│ • cloudtrail-enabled │
│ • guardduty-enabled-centralized │
│ │
└────────────────────────────────────────────────────────────────────┘
Config Rules Example:
import boto3
config = boto3.client( 'config' )
# Create a managed rule
config.put_config_rule(
ConfigRule = {
'ConfigRuleName' : 's3-encryption-required' ,
'Description' : 'Checks if S3 buckets have default encryption enabled' ,
'Source' : {
'Owner' : 'AWS' ,
'SourceIdentifier' : 'S3_BUCKET_SERVER_SIDE_ENCRYPTION_ENABLED'
},
'MaximumExecutionFrequency' : 'TwentyFour_Hours' ,
'ConfigRuleState' : 'ACTIVE'
}
)
# Create conformance pack for CIS benchmarks
config.put_conformance_pack(
ConformancePackName = 'CIS-AWS-Foundations' ,
TemplateS3Uri = 's3://config-templates/cis-aws-foundations.yaml'
)
AWS Security Hub
Security Hub provides a comprehensive view of security alerts and compliance status across AWS accounts.
┌────────────────────────────────────────────────────────────────────┐
│ AWS Security Hub │
├────────────────────────────────────────────────────────────────────┤
│ │
│ Aggregates findings from: │
│ ┌─────────────┐ ┌─────────────┐ ┌─────────────┐ │
│ │ GuardDuty │ │ Inspector │ │ Macie │ │
│ └──────┬──────┘ └──────┬──────┘ └──────┬──────┘ │
│ │ │ │ │
│ └────────────────┼────────────────┘ │
│ ▼ │
│ ┌─────────────────────────┐ │
│ │ Security Hub │ │
│ │ ┌───────────────────┐ │ │
│ │ │ Unified Dashboard │ │ │
│ │ │ + ASFF Format │ │ │
│ │ └───────────────────┘ │ │
│ └─────────────────────────┘ │
│ │ │
│ ┌────────────────┼────────────────┐ │
│ ▼ ▼ ▼ │
│ ┌─────────────┐ ┌─────────────┐ ┌─────────────┐ │
│ │ CIS AWS │ │ PCI-DSS │ │ Custom │ │
│ │ Foundations │ │ Standard │ │ Standards │ │
│ └─────────────┘ └─────────────┘ └─────────────┘ │
│ │
│ Security Standards: │
│ • AWS Foundational Security Best Practices │
│ • CIS AWS Foundations Benchmark │
│ • PCI-DSS v3.2.1 │
│ • NIST SP 800-53 │
│ │
└────────────────────────────────────────────────────────────────────┘
Monitoring with CloudWatch
Amazon CloudWatch provides monitoring and observability for AWS resources and applications.
CloudWatch Components
Component Purpose Use Case Metrics Numerical data points CPU, memory, requests Logs Application/system logs Debug, audit, troubleshoot Alarms Threshold notifications Alert on anomalies Dashboards Visual monitoring Operational visibility Events/EventBridge Event routing Automation triggers
Security-Focused CloudWatch Alarms
import boto3
cloudwatch = boto3.client( 'cloudwatch' )
# Alarm for root account usage
cloudwatch.put_metric_alarm(
AlarmName = 'RootAccountUsage' ,
AlarmDescription = 'Alert when root account is used' ,
MetricName = 'RootAccountUsageCount' ,
Namespace = 'CloudTrailMetrics' ,
Statistic = 'Sum' ,
Period = 300 ,
EvaluationPeriods = 1 ,
Threshold = 1 ,
ComparisonOperator = 'GreaterThanOrEqualToThreshold' ,
AlarmActions = [ 'arn:aws:sns:us-east-1:123456789012:security-alerts' ]
)
# Alarm for unauthorized API calls
cloudwatch.put_metric_alarm(
AlarmName = 'UnauthorizedAPICalls' ,
MetricName = 'UnauthorizedAttemptCount' ,
Namespace = 'CloudTrailMetrics' ,
Statistic = 'Sum' ,
Period = 300 ,
EvaluationPeriods = 1 ,
Threshold = 5 ,
ComparisonOperator = 'GreaterThanOrEqualToThreshold' ,
AlarmActions = [ 'arn:aws:sns:us-east-1:123456789012:security-alerts' ]
)
# Alarm for security group changes
cloudwatch.put_metric_alarm(
AlarmName = 'SecurityGroupChanges' ,
MetricName = 'SecurityGroupEventCount' ,
Namespace = 'CloudTrailMetrics' ,
Statistic = 'Sum' ,
Period = 300 ,
EvaluationPeriods = 1 ,
Threshold = 1 ,
ComparisonOperator = 'GreaterThanOrEqualToThreshold' ,
AlarmActions = [ 'arn:aws:sns:us-east-1:123456789012:security-alerts' ]
)
CloudWatch Logs Insights Queries
-- Find failed console logins
fields @timestamp, @message
| filter @message like / ConsoleLogin / and errorMessage like / Failed /
| stats count () by bin(1h)
-- Track IAM policy changes
fields @timestamp, userIdentity . userName , eventName, requestParameters
| filter eventSource = 'iam.amazonaws.com'
| filter eventName in ['CreatePolicy', 'DeletePolicy', 'AttachUserPolicy', 'DetachUserPolicy']
| sort @timestamp desc
-- Find S3 bucket policy modifications
fields @timestamp, userIdentity . arn , eventName, requestParameters . bucketName
| filter eventSource = 's3.amazonaws.com'
| filter eventName in ['PutBucketPolicy', 'DeleteBucketPolicy', 'PutBucketAcl']
| sort @timestamp desc
-- Detect potential data exfiltration (large S3 downloads)
fields @timestamp, requestParameters . bucketName , requestParameters . key , bytesTransferredIn
| filter eventName = 'GetObject'
| filter bytesTransferredIn > 100000000
| sort bytesTransferredIn desc
Database Monitoring
# RDS Performance Insights
rds = boto3.client( 'rds' )
# Enable Performance Insights
rds.modify_db_instance(
DBInstanceIdentifier = 'production-db' ,
EnablePerformanceInsights = True ,
PerformanceInsightsRetentionPeriod = 7 , # 7 days free tier
PerformanceInsightsKMSKeyId = 'arn:aws:kms:us-east-1:123456789012:key/example'
)
# DynamoDB monitoring - create alarm for throttled requests
cloudwatch.put_metric_alarm(
AlarmName = 'DynamoDB-ThrottledRequests' ,
MetricName = 'ThrottledRequests' ,
Namespace = 'AWS/DynamoDB' ,
Dimensions = [{ 'Name' : 'TableName' , 'Value' : 'production-table' }],
Statistic = 'Sum' ,
Period = 60 ,
EvaluationPeriods = 2 ,
Threshold = 10 ,
ComparisonOperator = 'GreaterThanThreshold' ,
AlarmActions = [ 'arn:aws:sns:us-east-1:123456789012:ops-alerts' ]
)
Network Protection Services
AWS WAF (Web Application Firewall)
WAF protects web applications from common exploits that could affect availability, compromise security, or consume excessive resources.
┌────────────────────────────────────────────────────────────────────┐
│ AWS WAF │
├────────────────────────────────────────────────────────────────────┤
│ │
│ Deployment Targets: │
│ ───────────────── │
│ • Amazon CloudFront │
│ • Application Load Balancer │
│ • Amazon API Gateway │
│ • AWS AppSync │
│ │
│ Rule Types: │
│ ─────────── │
│ • AWS Managed Rules (OWASP, Known Bad Inputs, Bot Control) │
│ • Rate-based Rules (DDoS, brute force protection) │
│ • Custom Rules (regex, geo-blocking, IP sets) │
│ │
│ Web ACL Structure: │
│ ┌────────────────────────────────────────────────────────────┐ │
│ │ Rule 1: AWS-AWSManagedRulesCommonRuleSet (Priority: 1) │ │
│ │ Rule 2: AWS-AWSManagedRulesSQLiRuleSet (Priority: 2) │ │
│ │ Rule 3: RateLimit-1000-per-5min (Priority: 3) │ │
│ │ Rule 4: BlockBadCountries (Priority: 4) │ │
│ │ Default Action: ALLOW │ │
│ └────────────────────────────────────────────────────────────┘ │
│ │
└────────────────────────────────────────────────────────────────────┘
WAF Configuration Example:
import boto3
wafv2 = boto3.client( 'wafv2' )
# Create Web ACL with managed rules
web_acl = wafv2.create_web_acl(
Name = 'production-web-acl' ,
Scope = 'REGIONAL' , # or 'CLOUDFRONT'
DefaultAction = { 'Allow' : {}},
Rules = [
{
'Name' : 'AWS-AWSManagedRulesCommonRuleSet' ,
'Priority' : 1 ,
'Statement' : {
'ManagedRuleGroupStatement' : {
'VendorName' : 'AWS' ,
'Name' : 'AWSManagedRulesCommonRuleSet'
}
},
'OverrideAction' : { 'None' : {}},
'VisibilityConfig' : {
'SampledRequestsEnabled' : True ,
'CloudWatchMetricsEnabled' : True ,
'MetricName' : 'CommonRules'
}
},
{
'Name' : 'RateLimitRule' ,
'Priority' : 2 ,
'Statement' : {
'RateBasedStatement' : {
'Limit' : 2000 ,
'AggregateKeyType' : 'IP'
}
},
'Action' : { 'Block' : {}},
'VisibilityConfig' : {
'SampledRequestsEnabled' : True ,
'CloudWatchMetricsEnabled' : True ,
'MetricName' : 'RateLimit'
}
}
],
VisibilityConfig = {
'SampledRequestsEnabled' : True ,
'CloudWatchMetricsEnabled' : True ,
'MetricName' : 'ProductionWebACL'
}
)
AWS Shield
Shield provides DDoS protection for AWS resources.
Feature Shield Standard Shield Advanced Cost Free (included) $3,000/month + data transfer Protection Layer 3/4 Layer 3/4/7 Detection Automatic Real-time detection Response Automatic mitigation 24/7 DDoS Response Team Cost Protection No Yes (scaling cost coverage) WAF Credits No Included Visibility Basic Advanced metrics & reports
AWS Firewall Manager
Centrally manage security rules across your organization.
┌────────────────────────────────────────────────────────────────────┐
│ AWS Firewall Manager │
├────────────────────────────────────────────────────────────────────┤
│ │
│ Manages: Benefits: │
│ ──────── ───────── │
│ • WAF rules • Centralized management │
│ • Shield Advanced • Automatic remediation │
│ • Security Groups • Cross-account deployment │
│ • Network Firewall • Compliance enforcement │
│ • Route 53 Resolver DNS FW • Audit trail via Config │
│ │
│ Policy Example: │
│ ┌────────────────────────────────────────────────────────────┐ │
│ │ "Enforce WAF on all ALBs in Production OU" │ │
│ │ • Scope: OU=Production │ │
│ │ • Resources: AWS::ElasticLoadBalancingV2::LoadBalancer │ │
│ │ • Managed Rule Groups: CommonRuleSet, SQLiRuleSet │ │
│ │ • Auto-remediate: Yes │ │
│ └────────────────────────────────────────────────────────────┘ │
│ │
└────────────────────────────────────────────────────────────────────┘
Golden Rule : Never hardcode credentials in code. Use IAM roles for services, Secrets Manager for applications, and environment variables only for local development.
🎯 Interview Questions
Q1: Explain the difference between IAM Users and Roles
IAM Users:
Permanent identities with long-term credentials
Password and/or access keys
Used for humans or CI/CD systems
Should always have MFA enabled
IAM Roles:
Temporary credentials (15 min - 12 hours)
No password/keys stored
Assumed by users, services, or external identities
Preferred for applications
When to use each:
User: Human access to AWS Console
Role: EC2, Lambda, cross-account access, SSO
Q2: How does IAM policy evaluation work?
Evaluation order:
All applicable policies collected
Check for explicit DENY → DENY wins
Check for explicit ALLOW → ALLOW
No match → Implicit DENY
Key rules:
Explicit DENY always wins
Must have explicit ALLOW to proceed
Default is implicit DENY
Policy types evaluated:
SCPs (Organizations)
Identity-based policies
Resource-based policies
Permission boundaries
Session policies
Q3: How would you implement least privilege?
Strategy:
Start with zero access , add as needed
Use managed policies for common patterns
Use conditions to narrow scope:
"Condition" : {
"StringEquals" : { "aws:RequestedRegion" : "us-east-1" },
"Bool" : { "aws:MultiFactorAuthPresent" : "true" }
}
Use resource-level permissions :
"Resource" : "arn:aws:s3:::my-bucket/users/${aws:username}/*"
Regular access reviews with IAM Access Analyzer
Permission boundaries to cap maximum permissions
Q4: How do you securely manage secrets in AWS?
Options (in order of preference):
IAM Roles (no secrets needed)
Best for AWS service-to-service
Secrets Manager
Automatic rotation
RDS/Aurora integration
$0.40/secret/month
Parameter Store (SecureString)
Free tier available
KMS encryption
No auto-rotation
Environment Variables
Okay for non-sensitive config
Never for passwords/API keys
Anti-patterns:
❌ Hardcoded in source code
❌ Committed to git
❌ Stored in unencrypted files
Q5: Explain cross-account access with IAM roles
Scenario: Account A needs to access S3 in Account BSetup:
Account B : Create role with trust policy
{
"Principal" : { "AWS" : "arn:aws:iam::ACCOUNT_A:root" },
"Action" : "sts:AssumeRole" ,
"Condition" : { "StringEquals" : { "sts:ExternalId" : "secret123" }}
}
Account B : Attach S3 permissions to role
Account A : IAM policy allowing sts:AssumeRole
Account A : Application assumes role
sts = boto3.client( 'sts' )
credentials = sts.assume_role(
RoleArn = 'arn:aws:iam::ACCOUNT_B:role/CrossAccountRole' ,
RoleSessionName = 'MySession' ,
ExternalId = 'secret123'
)
Q6: When would you use IAM Identity Center vs IAM Users?
Use IAM Identity Center when:
Managing access across multiple AWS accounts
You have an existing IdP (Okta, Azure AD, etc.)
You want SSO experience for users
Need centralized permission management
Want to eliminate long-term credentials
Use IAM Users when:
Single AWS account with few users
CI/CD pipelines (though roles are preferred)
Service accounts that can’t use roles
Legacy applications requiring access keys
Best Practice: Prefer Identity Center for human access, IAM roles for applications.
Q7: How would you set up a security monitoring strategy?
Layered approach:
Threat Detection:
GuardDuty for continuous monitoring
Inspector for vulnerability scanning
Macie for sensitive data discovery
Logging & Audit:
CloudTrail for API logging (all regions)
Config for resource compliance
VPC Flow Logs for network visibility
Centralization:
Security Hub to aggregate findings
CloudWatch for metrics/alarms
S3 for long-term log storage
Response:
EventBridge for automated remediation
SNS for alerting
Lambda for custom responses
# Example: Auto-remediate public S3 bucket
def lambda_handler ( event , context ):
bucket = event[ 'detail' ][ 'resourceId' ]
s3.put_public_access_block(
Bucket = bucket,
PublicAccessBlockConfiguration = {
'BlockPublicAcls' : True ,
'IgnorePublicAcls' : True ,
'BlockPublicPolicy' : True ,
'RestrictPublicBuckets' : True
}
)
Q8: Explain AWS WAF vs Shield vs Firewall Manager
AWS WAF:
Layer 7 (application) protection
Protects against: SQL injection, XSS, bad bots
Custom rules for specific threats
Rate limiting
Deployed on: CloudFront, ALB, API Gateway
AWS Shield:
Layer 3/4 (network) DDoS protection
Standard: Free, automatic protection
Advanced: $3K/month, 24/7 DRT support, cost protection
Protects: EC2, ELB, CloudFront, Route 53
Firewall Manager:
Centralized management across Organization
Manages: WAF rules, Shield, Security Groups
Auto-remediation capabilities
Compliance enforcement
When to use together:
WAF + Shield Advanced for comprehensive protection
Firewall Manager to enforce policies across accounts
Q9: How does GuardDuty detect threats?
Data Sources Analyzed:
CloudTrail management and data events
VPC Flow Logs
DNS query logs
S3 data events
EKS audit logs
RDS login activity
Detection Methods:
Machine learning for anomaly detection
Threat intelligence feeds
Known attack patterns
Finding Categories:
Reconnaissance (port scans, API probing)
Instance compromise (crypto mining, C&C)
Account compromise (unusual API calls)
Bucket compromise (public exposure)
Response Integration: # EventBridge rule for high-severity findings
{
"source" : [ "aws.guardduty" ],
"detail-type" : [ "GuardDuty Finding" ],
"detail" : {
"severity" : [{ "numeric" : [ ">=" , 7 ]}]
}
}
🧪 Hands-On Lab: Secure Application Setup
Objective : Configure secure access for a web application with proper IAM roles
Create IAM Role for EC2
Attach policy for S3 read, DynamoDB access
Create Application Secrets
Store database password in Secrets Manager with rotation
Configure KMS Key
Create CMK for application encryption, define key policy
Enable CloudTrail
Enable in all regions, log to S3 with encryption
Configure Access Analyzer
Find and fix overly permissive policies
Security Quick Reference
# Security configuration checklist
security_config = {
"account_level" : {
"mfa_on_root" : True ,
"no_root_access_keys" : True ,
"cloudtrail_all_regions" : True ,
"config_enabled" : True ,
"guardduty_enabled" : True ,
},
"iam_policies" : {
"least_privilege" : True ,
"use_roles_not_keys" : True ,
"mfa_for_privileged" : True ,
"regular_access_review" : True ,
},
"encryption" : {
"s3_default_encryption" : True ,
"ebs_default_encryption" : True ,
"rds_encryption" : True ,
"secrets_in_secrets_manager" : True ,
},
"network" : {
"vpc_flow_logs" : True ,
"security_group_review" : True ,
"waf_for_public_apps" : True ,
}
}
Next Module
Well-Architected Framework Learn the 6 pillars of AWS Well-Architected Framework