AWS CDK跨区域多堆栈之间如何传递跨栈引用属性
CDK跨区域堆栈引用解决方案(基于SSM Parameter Store)
实现逻辑
CloudFormation原生不支持跨区域的输出导入和栈引用,所以通过父区域的SSM参数存储需要传递的ARN值,子堆栈跨区域读取该参数值完成属性传递。
步骤1:父堆栈写入SSM参数
在部署于us-east-1的父堆栈中,创建过多区域KMS主密钥后,将ARN写入同区域的SSM参数:
// lib/KmsMultiregionPrincipalKey.ts 代码 import * as cdk from 'aws-cdk-lib'; import * as kms from 'aws-cdk-lib/aws-kms'; import * as ssm from 'aws-cdk-lib/aws-ssm'; export class KmsMultiregionPrincipalKey extends cdk.Stack { // 对外暴露SSM参数名,供子堆栈引用 public readonly principalKeySsmParamName = '/kms/multiregion/principal-key-arn'; constructor(scope: cdk.App, id: string, props?: cdk.StackProps) { super(scope, id, props); // 原有多区域主密钥创建逻辑 const principalKey = new kms.Key(this, 'MultiregionPrincipalKey', { multiRegion: true, enableKeyRotation: true }); // 将ARN写入SSM参数 new ssm.StringParameter(this, 'PrincipalKeyArnParam', { parameterName: this.principalKeySsmParamName, stringValue: principalKey.keyArn }); } }
步骤2:子堆栈跨区域读取SSM参数
子堆栈定义时指定父区域参数属性,调用跨区域SSM参数读取接口获取ARN:
// lib/KmsReplicaKey.ts 代码 import * as cdk from 'aws-cdk-lib'; import * as kms from 'aws-cdk-lib/aws-kms'; import * as ssm from 'aws-cdk-lib/aws-ssm'; export interface KmsReplicaKeyProps extends cdk.StackProps { principalKeySsmParamName: string; parentStackRegion: string; } export class KmsReplicaKey extends cdk.Stack { constructor(scope: cdk.App, id: string, props: KmsReplicaKeyProps) { super(scope, id, props); // 跨区域读取父区域SSM参数中的ARN const principalKeyArn = ssm.StringParameter.fromStringParameterAttributes(this, 'ImportPrincipalArn', { parameterName: props.principalKeySsmParamName, region: props.parentStackRegion }).stringValue; // 用读取到的ARN创建副本密钥 new kms.ReplicaKey(this, 'ReplicaKey', { primaryKey: kms.Key.fromKeyArn(this, 'PrimaryKey', principalKeyArn), replicaRegion: this.region }); } }
步骤3:调整入口部署代码
修改bin目录下的入口文件,按顺序关联父子堆栈:
// bin/myapp.ts 代码 import * as cdk from 'aws-cdk-lib'; import { KmsMultiregionPrincipalKey } from '../lib/KmsMultiregionPrincipalKey'; import { KmsReplicaKey } from '../lib/KmsReplicaKey'; const app = new cdk.App(); const ACCOUNT_ID = '123456789123'; const PARENT_REGION = 'us-east-1'; const CHILD_REGIONS = ['us-east-2', 'us-west-2']; // 按需添加部署区域 // 先实例化父堆栈 const primaryKeyStack = new KmsMultiregionPrincipalKey(app, 'KmsMultiregionKeyStack', { env: { account: ACCOUNT_ID, region: PARENT_REGION } }); // 循环实例化各区域子堆栈 for (const region of CHILD_REGIONS) { new KmsReplicaKey(app, `KmsReplicaKey-${region}`, { env: { account: ACCOUNT_ID, region: region }, principalKeySsmParamName: primaryKeyStack.principalKeySsmParamName, parentStackRegion: PARENT_REGION }); }
部署要求
- 必须先部署父堆栈,等待SSM参数创建完成后再部署子堆栈,避免子堆栈读取参数失败
- 若主密钥ARN发生变更,需先更新父堆栈刷新SSM参数值,再重新部署子堆栈同步最新配置
- 如传递敏感参数,可改用SSM SecureString类型存储,对应使用
fromSecureStringParameterAttributes方法读取,同时为子堆栈执行角色授予SSM参数的读取权限
内容的提问来源于stack exchange,提问作者MasterOfTheHouse
相关产品推荐
相关产品推荐

