AWS CDK(v2): Lambda から SystemManagerのパラメーターストアを読めるようにする

AWS 外部の鍵情報などを Lambda で使いたい場合、SystemManager のパラメーターストア経由で渡す方法があります。 環境変数として渡すことも考えられますが、もう少し安全にしたい場合はこちらのやり方が良さそうです。 CDK で簡単にその権限を Lambda に指定することができます。

Version

  • node: 16.13.1
  • aws-cdk: 2.2.0
  • tsc: 4.5.4

書き方

Stack 側

CDK の方では、Lambda に読み込みを許可するパラメータ名を KEY_NAME などの環境変数で渡しつつ、grantRead() を行います。

/// lib/xyz-stack.ts

const KEY_NAME = '/awesome-app/external_key';

export class XyzStack extends Stack {
  constructor(scope: Construct, id: string, props?: StackProps) {
    super(scope, id, props);
...

    const myLambda = new NodejsFunction(this, "MyAwesomeFunction", {
      entry: path.join(__dirname, './lambda/main.ts'),
      handler: "handler",
      environment: {
        KEY_NAME: KEY_NAME,
      },
    });

    const secureStringParameter = StringParameter.fromSecureStringParameterAttributes(this, 'AwesomeKey', {
      parameterName: KEY_NAME,
      version: 1,
    });
    secureStringParameter.grantRead(myLambda);

...

SecureString の場合 version: 1 というように Version 番号が必須です。 Version 番号は、管理コンソールで以下に書かれている数字のことです。

Parameter Version

Lambda 側

Lambda では env.KEY_NAME からパラメータ名を取得して SSM を使って読み出します。 aws-sdk を使うので npm install aws-sdk しておく必要があります。

/// lib/lambda/main.ts
import { env } from "process";
import { SSM } from "aws-sdk";

export const handler = async (event: any = {}): Promise<any> => {
  const awesomeKey = await getAwesomeKey();
  ...

}

async function getAwesomeKey(): Promise<string> {
    const ssm = new SSM({ region: 'ap-northeast-1' });
    const request = {
        Name: env.KEY_NAME!,
        WithDecryption: true,
    };
    const response = await ssm.getParameter(request).promise();
    return response.Parameter!.Value!;
}

Reference