You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

未硬编码Instance ID时Lambda调用SSM执行失败问题排查

问题

需求是通过EventBridge规则捕获新启动EC2实例的Instance ID,再触发Lambda执行指定SSM文档。目前Lambda能正确提取到实例ID(CloudWatch日志已验证),但直接使用提取的ID时无法执行SSM文档;如果硬编码Instance ID则可以正常执行。相关代码及日志如下:

未硬编码的代码(执行失败)

import boto3
import json

def lambda_handler(event, context):
    # Extract the instance ID from the event (assuming it's already extracted as shown in your previous code)
    if event.get("detail", {}).get("eventName") == "RunInstances":
        # Extract the instance ID and event details
        instance_id = event["detail"]["responseElements"]["instancesSet"]["items"][0]["instanceId"]
        event_details = json.dumps(event["detail"], indent=2)

        # You can now process the instance ID and event details as needed
        print(f"{instance_id}")
        # print(f"Event Details:
{event_details}")

    return {
        "statusCode": 200,
        "body": json.dumps("Event processed successfully")
    }


    # Initialize the SSM client
    ssm_client = boto3.client('ssm')
    # instance_id = 'i-08be0407d47363235' # hard-code for example

    # Define the SSM document name and parameters
    document_name = "prisma-cloud-agent-ssm-doc"  # Replace with your SSM document name
    ssm_parameters = {
        "InstanceId": [instance_id],
        # Add more parameters as needed
    }

    try:
        # Send the command using the SSM document and parameters
        response = ssm_client.send_command(
            InstanceIds=[instance_id],
            DocumentName=document_name,
            Parameters=ssm_parameters,
        )

        # Process the response as needed
        command_id = response["Command"]["CommandId"]
        print(f"SSM Command sent with Command ID: {command_id}")

        return {
            "statusCode": 200,
            "body": json.dumps(f"SSM Command sent with Command ID: {command_id}")
        }
    except Exception as e:
        print(f"Error sending SSM command: {str(e)}")
        return {
            "statusCode": 500,
            "body": json.dumps("Error sending SSM command")
        }

硬编码的代码(执行正常)

import boto3
import json

def lambda_handler(event, context):
    # Extract the instance ID from the event (assuming it's already extracted as shown in your previous code)
    # if event.get("detail", {}).get("eventName") == "RunInstances":
    #     # Extract the instance ID and event details
    #     instance_id = event["detail"]["responseElements"]["instancesSet"]["items"][0]["instanceId"]
    #     event_details = json.dumps(event["detail"], indent=2)

    #     # You can now process the instance ID and event details as needed
    #     print(f"{instance_id}")
    #     # print(f"Event Details:
{event_details}")

    # return {
    #     "statusCode": 200,
    #     "body": json.dumps("Event processed successfully")
    # }


    # Initialize the SSM client
    ssm_client = boto3.client('ssm')
    instance_id = 'i-08be0407d47363235' # hard-code for example

    # Define the SSM document name and parameters
    document_name = "xyz-doc"  # Replace with your SSM document name
    ssm_parameters = {
        "InstanceId": [instance_id],
        # Add more parameters as needed
    }

    try:
        # Send the command using the SSM document and parameters
        response = ssm_client.send_command(
            InstanceIds=[instance_id],
            DocumentName=document_name,
            Parameters=ssm_parameters,
        )

        # Process the response as needed
        command_id = response["Command"]["CommandId"]
        print(f"SSM Command sent with Command ID: {command_id}")

        return {
            "statusCode": 200,
            "body": json.dumps(f"SSM Command sent with Command ID: {command_id}")
        }
    except Exception as e:
        print(f"Error sending SSM command: {str(e)}")
        return {
            "statusCode": 500,
            "body": json.dumps("Error sending SSM command")
        }

CloudWatch日志输出

Instance ID: i-006aba8d1200a8bce

原因与解决方法

核心原因

未硬编码的代码中,提取完Instance ID后直接执行了return语句,导致后续的SSM客户端初始化、发送命令等代码完全没有被执行。Lambda函数在遇到return时会立即终止,所以虽然能打印出Instance ID,但永远走不到发送SSM命令的逻辑。

修正后的代码

把提前返回的return块删除或移到SSM命令执行逻辑之后,确保提取ID后能继续执行SSM相关代码:

import boto3
import json

def lambda_handler(event, context):
    instance_id = None
    # 提取Instance ID
    if event.get("detail", {}).get("eventName") == "RunInstances":
        instance_id = event["detail"]["responseElements"]["instancesSet"]["items"][0]["instanceId"]
        print(f"{instance_id}")

    if not instance_id:
        return {
            "statusCode": 400,
            "body": json.dumps("No valid instance ID found in event")
        }

    # 初始化SSM客户端并发送命令
    ssm_client = boto3.client('ssm')
    document_name = "prisma-cloud-agent-ssm-doc"
    ssm_parameters = {
        "InstanceId": [instance_id],
    }

    try:
        response = ssm_client.send_command(
            InstanceIds=[instance_id],
            DocumentName=document_name,
            Parameters=ssm_parameters,
        )
        command_id = response["Command"]["CommandId"]
        print(f"SSM Command sent with Command ID: {command_id}")
        return {
            "statusCode": 200,
            "body": json.dumps(f"SSM Command sent with Command ID: {command_id}")
        }
    except Exception as e:
        print(f"Error sending SSM command: {str(e)}")
        return {
            "statusCode": 500,
            "body": json.dumps("Error sending SSM command")
        }

额外注意事项

  • 确保Lambda角色拥有ssm:SendCommand权限,以及目标EC2实例已安装SSM Agent并能正常连接到SSM服务
  • 添加对instance_id的非空校验,避免因事件格式异常导致后续报错

内容的提问来源于stack exchange,提问作者code userit

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.09 03:17:12