はじめに
※この記事は、私の個人ブログ(下記)と同じ内容になります。
本ブログは、2025/02/21(金)に開催された「JAWS-UG CDK支部#19 クラスメソッドコラボ回」における私のLT「CDKでカスタムランタイムを作成して、Lambdaをnode.js23+TypeScriptで動かしてみた」の詳細資料になります。
LTの発表資料は、下記で公開しています。(上記Connpassページにもリンクがあります)
なお今回は下記の構成で、何回かに分けて投稿します。
- カスタムランタイム作成 ※前回の記事
- AWS CDKでの実装&TypeScriptで動作させる ※今回はこれ
- AWSリソースにアクセスする(AWS SDK for JavaScript v3を使う)
AWS CDKでLambdaレイヤーを作成する
前回、Node.js ver23.6.0のカスタムランタイムをLambdaレイヤーで作成しましたが、まずはこのLambdaレイヤーをAWS CDK(以下「CDK」)作成する必要があります。
ただAWS CDKは LayerVersion コンストラクタでLambdaレイヤー作成できるので、下記の定義を行うだけでOKです。1
// コンストラクタ変数は後で使います
// 「runtime-tutorial」フォルダは、前回使用したフォルダ(詳細は前回を参照)
// compatibleArchitecturesやcompatibleRuntimesも指定する
const node23RuntimeLayer = new lambda.LayerVersion(this, 'Node23SampleLayer', {
code: lambda.Code.fromAsset(<runtime-tutorialフォルダのパス>),
layerVersionName: 'runtime-node23-jawsug-cdk-event-19',
removalPolicy: cdk.RemovalPolicy.RETAIN_ON_UPDATE_OR_DELETE,
});
Lambda関数を作成する
次にLambda関数(TypeScript)です。
なお今回Lambda関数をTypeScriptで作成しますが、使うコンストラクタは「Function」になりますので注意です。(「NodejsFunction」だとデプロイ時にJavaScriptへのトランスパイルが行われてしまうので)
あとはruntime
に runtime: lambda.Runtime.PROVIDED_AL2023
(Amazon Linux 2023)を選択すればOKです。(その他の項目は以下参照)
もちろん layers
に先ほど作成したLambdaレイヤーを指定するのを忘れないでください。
const node23SampleFunction = new lambda.Function(this, "Node23SampleFunction", {
functionName: 'Node23SampleFunction',
runtime: lambda.Runtime.PROVIDED_AL2023, // Amazon Linux 2023を指定
layers: [node23RuntimeLayer], // ここで上記のLambdaレイヤーを指定
handler: "index.handler",
code: lambda.Code.fromAsset(path.join(__dirname, '../lambda')), // Lambdaソースファイルのパス
});
なおLambdaソースは、前回の「使用しているNode.jsのバージョンを返す」をTypeScriptで書いただけのものです。(1行目の import
については後で触れます)
import type { LambdaFunctionURLEvent, LambdaFunctionURLResult } from 'aws-lambda/trigger/lambda-function-url'
const handler = async function (event: LambdaFunctionURLEvent) {
console.log(event);
const result: LambdaFunctionURLResult = {
statusCode: 200,
body: JSON.stringify({
message: `node version is ${process.version}`
}),
};
return result;
};
module.exports = { handler }
runtime.js を変更する
そしてもう一つ、前回作成したruntime.js
も更新が必要です。
現時点でruntime.jsの内容はJavaScript(*.js)にのみ対応しているので(Node.jsなので)、TypeScriptに対応するように変更する必要があります。
これはruntime.jsの148行目あたりにある下記ソースを、以下の通りに変更すればOKです。2
# 末尾に「.ts」を追加し、TypeScriptファイルを読めるようにする
- const app = require(LAMBDA_TASK_ROOT + '/' + modulePath);
+ const app = require(LAMBDA_TASK_ROOT + '/' + modulePath + ".ts");
「型除去(Type Stripping)」について
1行目のimport文ですが、import type
という見慣れない記載になっています。
これはnode.jsでTypeScriptを動かす際の独自の仕様である「型除去(Type Stripping)」に関わるものです。
「型除去(Type Stripping)」とは、TypeScriptファイルを 「型だけ削除して実行」するためのもの で、以前はオプションでしたが、v23.6.0からデフォルトで有効になっています。3
ただし「型」ということを明示的に示すために、型定義のインポート/エクスポート時はtype
という言葉を明示的に記載する必要があります。(これを忘れると「型」と認識されないため型除去は行われず、エラーになることがあります)
またこの型除去がデフォルトになったことで、tsconfig.json
の下記項目もチェックする必要があります。(今回のLambdaの挙動には影響しません)
設定値 | 説明 | デフォルト値 |
---|---|---|
allowImportingTsExtensions | *.tsファイルからのインポートを可能にする | rewriteRelativeImportExtensionsが有効な場合はtrue,そうでない場合はfalse |
rewriteRelativeImportExtensions | 相対インポートパス内の .ts、.tsx、.mts、および .cts ファイル拡張子を、出力ファイル内の対応する JavaScript に書き換える | 未記載 |
verbatimModuleSyntax | 型のimport/export時に「type」が未記載の場合、エラーとする | 未記載 |
実行する
ここまで来たら、あとはcdk deploy
でデプロイして、前回同様AWSコンソールからLambda関数の「テスト」で実施するだけです。
問題なければ、前回同様「node version is v23.6.0」という結果が返ってくるはずです。
まとめ
というわけで、ここまでで「AWS CDKでの実装&TypeScriptで動作させる」部分まで完了しました。
次回は最終回として「AWS SDK for JavaScript v3を使ってAWSリソースにアクセスする」ことを実施しようと思います。
告知
5/23(金)~5/24(土)に東京・ベルサール神田で実施される「TS Kaigi 2025」にて、「AWS LambdaをTypeScriptで動かして分かった、Node.jsのTypeScriptサポートの利点と課題」登壇させていただくこととなりました。(日時は5/23(金) 15:50 ~ 16:20 の予定です)
ちょうどこのブログで扱っている「【AWS CDK】LambdaをTypeScriptで動かす環境を構築する」で分かったNode.jsのTypeScriptサポートを触ってみてわかったことをお話しさせていただきますので、当日はよろしくお願いいたします。
それでは、今回はこの辺で。
-
発表資料にも書きましたが、AWS CDKでカスタムランタイムを作成すること自体は、全く難しくないです。作成することと自体は、ですが...)) ↩
-
ただし下記の変更だと、今度はJavaScriptファイルが読めないので、柔軟に対応するにはもっと細かい変更が必要です。)) ↩
-
ただしにコマンドラインで実行する場合、--disable-warning=ExperimentalWarning フラグを使用して警告を非表示にしないと「ExperimentalWarning: Type Stripping is an experimental feature and might change at any time」という警告が出ますので注意が必要です。 ↩