概要
Serverless Frameworkのaws-nodejs-typescriptを導入して、Middyを利用したLambda関数を作成しました。
その単体テストを作成する際に他に同じようなことをしている方のリポジトリを見つけることができず、ハマったのでメモです。
Middyとは?
簡単に説明すると、MiddyはLambdaで使える軽量なミドルウェアエンジンです。
バリデーション処理やロギングなど、様々な共通処理をMiddyに任せることで
業務ロジックだけに専念することができることがメリットです。
詳細はドキュメントを参照ください。
前提
Serverless FrameworkでNode.jsとTypeScriptを利用したテンプレートである
aws-nodejs-typescriptを利用しています。
ここに既にMiddyが導入されています。
Jestを導入する
以下コマンドでJestをインストール
npm install jest ts-jest @types/jest -D
設定ファイルを用意します。
module.exports = {
preset: 'ts-jest',
roots: ['<rootDir>/src/__tests__'],
transform: {
'^.+\\.tsx?$': 'ts-jest',
},
moduleNameMapper: {
'^@src/(.*)$': '<rootDir>/src/$1',
'^@libs/(.*)$': '<rootDir>/src/libs/$1',
'^@functions/(.*)$': '<rootDir>/src/functions/$1'
},
testMatch: ['**/__tests__/**/*.+(ts|js)', '**/?(*.)+(spec|test).+(ts|js)'],
collectCoverageFrom: ['src/**/*.{js,ts}', '!**/node_modules/**', '!**/vendor/**'],
coveragePathIgnorePatterns: ['src/__tests__/', 'src/types/'],
};
テストフォルダ作成
src直下に__test__
というディレクトリを作成し、その中にテストファイルを配置します。
テストファイル名はXXX.spec.ts
またはXXX.test.ts
とします。
テストコードを作成する
import { formatJSONResponse } from '@libs/api-gateway';
import { middyfy } from '@libs/lambda';
const hello = async (event: any) => {
return formatJSONResponse({
message: `Hello ${event.body.name}, welcome to the exciting Serverless world!`
});
};
export const main = middyfy(hello);
上記のようなLambda handlerに対してテストを用意する際は以下のようにします。
jest.mock('@libs/lambda', () => ({
middyfy: jest.fn((handler) => handler),
}));
import { main } from '@functions/hello/handler';
const event: any = {
"headers": {
"Content-Type": "application/json"
},
"body": {
"name": "Frederic"
}
}
describe('hello関数のテスト', () => {
test('正しいレスポンスを返す', async () => {
const context: any = undefined
const actual = await main(event, context);
const expected = {
body: JSON.stringify({
message: `Hello ${event.body.name}, welcome to the exciting Serverless world!`
}),
statusCode: 200
};
expect(actual).toEqual(expected);
});
});
本来TypeScriptの適切な型を定義すべきですが、無理やり通してしまっているためcontext変数などの定義を行っています。
実際にはhandlerのexport値に対してmiddyfyされているため、テストを作成する方法に悩みましたが、最初の3行のようにモック化させることでhandler内のテスト作成ができました。
npx jest
でテスト実行できます。
package.json
に記載してnpm test
とすることもできます。
テストデータをJSONファイルに切り出す
tsconfig.json
のcompilerOptions
に"resolveJsonModule": true
設定することでJSONモジュールを読み込めるようになります。
event.bodyの値をJSONファイルに切り出してテストデータを作れます。
その他
以下のようなSererless Frameworkのドキュメント内に以下のテストライブラリも紹介されていましが、そんなに有名でない&普通にJestをインストールすることと大差ないと判断しました。