AWS CDK Aspect中如何获取并修改EC2/LaunchConfiguration的UserData内容
你看到的${Token[TOKEN.xxx]}是CDK的延迟求值占位符,这类动态值要到cdk synth合成阶段才会被替换为实际的CloudFormation表达式结构,运行时无法直接解析为明文字符串。
方案1:仅追加命令(最简便)
node.user_data本身就是aws_cdk.aws_ec2.UserData类的实例,直接调用它的内置方法就可以追加内容,CDK会自动合并到原有UserData结构中,不需要手动解析Token:
def visit(self, node: IConstruct): if ( CfnResource.is_cfn_resource(node) and node.cfn_resource_type in self.resource_types ): # 直接调用UserData内置方法追加命令 node.user_data.add_commands("echo 'injected command' > /tmp/test.log") # 也可以调用其他内置方法,比如下载S3文件、运行脚本等 # node.user_data.add_s3_download_command(bucket=bucket, key="script.sh")
方案2:修改原有命令内容
如果需要修改已经存在的命令,可通过栈的resolve方法解析Token为CloudFormation结构,修改完成后通过属性覆盖写回即可:
from aws_cdk import Stack @jsii.implements(IAspect) class CfnInitAspect: resource_types = [ "AWS::AutoScaling::LaunchConfiguration", "AWS::EC2::Instance" ] def visit(self, node: IConstruct): if ( CfnResource.is_cfn_resource(node) and node.cfn_resource_type in self.resource_types ): stack = Stack.of(node) # 解析Token为可操作的CloudFormation嵌套结构 resolved_ud = stack.resolve(node.user_data) # 取出命令列表:UserData结构为 Fn::Base64 -> Fn::Join -> 第二个元素是命令数组 cmd_list = resolved_ud["Fn::Base64"]["Fn::Join"][1] # 在这里按需修改命令列表,比如插入、删除、替换原有内容 # 示例:在原有命令开头插入自定义命令 cmd_list.insert(1, "set -x\n") # 示例:修改原有cfn-init命令的参数 for idx, part in enumerate(cmd_list): if isinstance(part, str) and "cfn-init -v" in part: cmd_list[idx] = part.replace("cfn-init -v", "cfn-init -v --debug") # 将修改后的结构覆盖回资源属性 node.add_property_override("UserData", resolved_ud)
内容的提问来源于stack exchange,提问作者maafk
相关产品推荐
相关产品推荐

