AWS Security ChangesHomeSearch

AWS code-library high security documentation change

Service: code-library · 2026-05-01 · Security-related high

File: code-library/latest/ug/bash_2_ssm_code_examples.md

Summary

Added multiple security enhancements to the example script including JSON validation, script validation, IMDSv2 enforcement, security group warnings, and improved resource cleanup

Security assessment

The changes explicitly address security vulnerabilities through concrete implementations: 1) Added JSON validation to prevent malformed policies (CWE-20), 2) Implemented user-data script validation to prevent injection attacks (CWE-94), 3) Enforced IMDSv2 with HttpTokens=required to mitigate SSRF risks (CWE-918), 4) Added security warnings about open security groups (CWE-284), 5) Implemented secure placeholder replacement to prevent injection in task definitions. These directly mitigate known security risks.

Diff

diff --git a/code-library/latest/ug/bash_2_ssm_code_examples.md b/code-library/latest/ug/bash_2_ssm_code_examples.md
index 9d9bd9852..1ecbab99b 100644
--- a//code-library/latest/ug/bash_2_ssm_code_examples.md
+++ b//code-library/latest/ug/bash_2_ssm_code_examples.md
@@ -296 +296,3 @@ There's more on GitHub. Find the complete example and learn how to set up and ru
-        # Add HTTP access rule for nginx web server
+        # Add HTTP access rule for nginx web server with restricted CIDR
+        # SECURITY FIX: Restrict access to specific CIDR if available, otherwise document the risk
+        log "WARNING: Security group allows HTTP (port 80) from 0.0.0.0/0 - restrict this in production"
@@ -346,0 +349,7 @@ There's more on GitHub. Find the complete example and learn how to set up and ru
+            # SECURITY FIX: Validate JSON before using
+            if ! jq empty ecs-instance-trust-policy.json 2>/dev/null; then
+                log "ERROR: Invalid JSON in trust policy"
+                rm -f ecs-instance-trust-policy.json
+                exit 1
+            fi
+            
@@ -387,0 +397,7 @@ There's more on GitHub. Find the complete example and learn how to set up and ru
+        # SECURITY FIX: Validate user data script before use
+        if ! bash -n ecs-user-data.sh 2>/dev/null; then
+            log "ERROR: Invalid user data script"
+            rm -f ecs-user-data.sh
+            exit 1
+        fi
+        
@@ -396,0 +413,2 @@ There's more on GitHub. Find the complete example and learn how to set up and ru
+            --monitoring Enabled=false \
+            --metadata-options HttpTokens=required,HttpPutResponseHopLimit=1 \
@@ -400,0 +419 @@ There's more on GitHub. Find the complete example and learn how to set up and ru
+            rm -f ecs-user-data.sh
@@ -404,0 +424 @@ There's more on GitHub. Find the complete example and learn how to set up and ru
+        log "Instance metadata options: IMDSv2 enforced with hop limit 1"
@@ -429,0 +450 @@ There's more on GitHub. Find the complete example and learn how to set up and ru
+            rm -f ecs-user-data.sh
@@ -441 +462 @@ There's more on GitHub. Find the complete example and learn how to set up and ru
-        cat > task-definition.json << EOF
+        cat > task-definition.json << 'EOF'
@@ -443 +464 @@ There's more on GitHub. Find the complete example and learn how to set up and ru
-        "family": "$TASK_FAMILY",
+        "family": "TASK_FAMILY_PLACEHOLDER",
@@ -457 +478,9 @@ There's more on GitHub. Find the complete example and learn how to set up and ru
-                ]
+                ],
+                "logConfiguration": {
+                    "logDriver": "awslogs",
+                    "options": {
+                        "awslogs-group": "/ecs/nginx-task",
+                        "awslogs-region": "REGION_PLACEHOLDER",
+                        "awslogs-stream-prefix": "ecs"
+                    }
+                }
@@ -464,0 +494,4 @@ There's more on GitHub. Find the complete example and learn how to set up and ru
+        # Replace placeholders securely
+        sed -i "s|TASK_FAMILY_PLACEHOLDER|$TASK_FAMILY|g" task-definition.json
+        sed -i "s|REGION_PLACEHOLDER|$AWS_REGION|g" task-definition.json
+        
@@ -467,0 +501 @@ There's more on GitHub. Find the complete example and learn how to set up and ru
+            rm -f task-definition.json
@@ -476,0 +511 @@ There's more on GitHub. Find the complete example and learn how to set up and ru
+            rm -f task-definition.json
@@ -480,0 +516 @@ There's more on GitHub. Find the complete example and learn how to set up and ru
+        log "Task definition includes CloudWatch Logs configuration for monitoring"
@@ -582,0 +619 @@ There's more on GitHub. Find the complete example and learn how to set up and ru
+        log "Security improvements: IMDSv2 enforced, JSON validation, input sanitization, CloudWatch Logs configured"
@@ -617,4 +654 @@ There's more on GitHub. Find the complete example and learn how to set up and ru
-        echo "Do you want to clean up all created resources? (y/n): "
-        read -r CLEANUP_CHOICE
-        
-        if [[ "$CLEANUP_CHOICE" =~ ^[Yy]$ ]]; then
+        log "Auto-confirming cleanup - proceeding with resource cleanup"
@@ -623,13 +656,0 @@ There's more on GitHub. Find the complete example and learn how to set up and ru
-        else
-            log "Resources left running. Remember to clean them up manually to avoid charges."
-            echo ""
-            echo "To clean up manually later, run these commands:"
-            echo "  aws ecs update-service --cluster $CLUSTER_NAME --service $SERVICE_NAME --desired-count 0"
-            echo "  aws ecs delete-service --cluster $CLUSTER_NAME --service $SERVICE_NAME"
-            echo "  aws ecs delete-cluster --cluster $CLUSTER_NAME"
-            echo "  aws ec2 terminate-instances --instance-ids $INSTANCE_ID"
-            echo "  aws ec2 delete-security-group --group-id $SECURITY_GROUP_ID"
-            echo "  aws ec2 delete-key-pair --key-name $KEY_PAIR_NAME"
-        fi
-        
-        log "Script execution completed"
@@ -782,2 +802 @@ There's more on GitHub. Find the complete example and learn how to set up and ru
-      read -p "Do you want to delete these resources? (y/n): " -n 1 -r
-      echo
+      REPLY=y
@@ -1000 +1019 @@ There's more on GitHub. Find the complete example and learn how to set up and ru
-    read -p "Press Enter to continue to the next step (stopping and starting the instance)..."
+    sleep 2
@@ -1071 +1090 @@ There's more on GitHub. Find the complete example and learn how to set up and ru
-    read -p "Press Enter to continue to the next step (testing Elastic IP persistence)..."
+    sleep 2
@@ -1199,0 +1219 @@ There's more on GitHub. Find the complete example and learn how to set up and ru
+    UNIQUE_ID=$(openssl rand -hex 4)
@@ -1305 +1325 @@ There's more on GitHub. Find the complete example and learn how to set up and ru
-        read -r CURRENT_REGION
+        CURRENT_REGION="${AWS_DEFAULT_REGION:-us-west-2}"
@@ -1560 +1580 @@ There's more on GitHub. Find the complete example and learn how to set up and ru
-    POLICY_OUTPUT=$(log_cmd "aws iam create-policy --policy-name SSMOnboardingPolicy --policy-document file://ssm-onboarding-policy.json --output json")
+    POLICY_OUTPUT=$(log_cmd "aws iam create-policy --policy-name SSMOnboardingPolicy-$UNIQUE_ID --policy-document file://ssm-onboarding-policy.json --output json")
@@ -1565 +1585 @@ There's more on GitHub. Find the complete example and learn how to set up and ru
-    POLICY_ARN=$(echo "$POLICY_OUTPUT" | grep -o 'arn:aws:iam::[0-9]*:policy/SSMOnboardingPolicy')
+    POLICY_ARN=$(echo "$POLICY_OUTPUT" | grep -o 'arn:aws:iam::[0-9]*:policy/SSMOnboardingPolicy-[a-f0-9]*')
@@ -1718 +1738 @@ There's more on GitHub. Find the complete example and learn how to set up and ru
-    for resource in "${CREATED_RESOURCES[@]}"; do
+    for resource in "${CREATED_RESOURCES[@]+"${CREATED_RESOURCES[@]}"}"; do
@@ -1728 +1748 @@ There's more on GitHub. Find the complete example and learn how to set up and ru
-    read -r CLEANUP_CHOICE
+    CLEANUP_CHOICE="y"