1
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

AWS Lambda と ServerlessAdvent Calendar 2024

Day 9

ユーザー認証付きの静的サイトをCognito+CloudFront+Lambda@Edgeで構築する

Last updated at Posted at 2024-12-15

背景

CloudFrontのLambda@Edgeを使うとS3のコンテンツにCognitoユーザープールを使用した認証を手軽に実装できるということで, 試してみました.

基本的にはこちらのページ(Cognito認証を導入した振り返り)を参考にさせていただきました.
進めていく中で以下のような問題が発生したので, 解消方法を整理しておきます.

  1. Lambda@Edgeのサイズ制限について
  2. Lambda@Edgeのログが出力されない
  3. cognito-at-edgeの実行時エラー

1. Lambda@Edgeのサイズ制限について

Viewer Request時に実行するLambda@Edgeには1MBという非常に厳しいサイズ制限があります(参考).
普通に実装するとこの制限に引っかかってしまいました.

解消方法

以下のようにバンドルすることでサイズを削減することができました. これをZIP化してLambdaにデプロイすることで, CloudFrontのViewer Requestに紐づけることができました.

bash
$ npx esbuild --bundle index.ts --minify --outfile=index.js --platform=node
$ zip upload.zip index.js 

2. Lambda@Edgeのログが出力されない

Lambda@EdgeのデプロイとCloudFrontの紐づけまでを完了しドメインにアクセスしたところ, 503エラーが発生しました(このエラーの原因については後述).

Lambdaの実行時エラーが原因ということがわかったのでCloudWatchからログを確認しようとしたのですが, Lambdaの"モニタリング"からアクセスできるus-east-1のCloudWatchには実行された形跡がなく, エラーを確認することができませんでした.

解消方法

こちらの記事(Lambda@Edge の設置によって出力されるログは2種類ある)にあるように, CloudFrontにデプロイしたLambda@EdgeのログはLambda@Edgeを実行したエッジロケーションのCloudWatchに書き込まれるようです.

テスト実行時のログはLambdaをデプロイしたリージョンと同じリージョン(us-east-1)のCloudWatchに書き込まれますが, 実行時のエラーを確認するにはエッジロケーションのCloudFrontを参照する必要があります.

リージョン ロググループ 説明
1 us-east-1 /aws/lambda/<関数名> テスト実行時のログが書き込まれる
2 ap-northeast-1
(エッジロケーション)
/aws/lambda/us-east-1.<関数名> CloudFront実行時のログが書き込まれる

3. cognito-at-edgeの実行時エラー

cognito-at-edgeをインストールし, READMEに従って下記のようなindex.tsを作りました.

index.ts
const { Authenticator } = require("cognito-at-edge");

const authenticator = new Authenticator({
  // Replace these parameter values with those of your own environment
  region: "ap-northeast-1", // user pool region
  userPoolId: "ap-northeast-1_XXXXXX", // user pool ID
  userPoolAppId: "XXXXXX", // user pool app client ID
  userPoolDomain: "XXXXXX" // user pool domain
});

exports.handler = async (request) => authenticator.handle(request);

これをバンドルしてZIP化し, デプロイした後にCloudFrontに紐づけたのですが, ドメインにアクセスすると503エラーが発生しました.
image.png

The Lambda function associated with the CloudFront distribution is invalid or doesn't have the required permissions. We can't connect to the server for this app or website at this time. There might be too much traffic or a configuration error. Try again later, or contact the app or website owner.

解消方法

Authenticatorの引数 userPoolAppSecret にクライアントシークレットを指定することで解消しました.
クライアントシークレットは ユーザープール > クライアントアプリケーション から確認することができます.

README では userPoolAppSecret はOptionalとなっていましたが, これを指定しないと invalid_client エラーが出てしまいました.

index_mod.ts
const { Authenticator } = require("cognito-at-edge");

const authenticator = new Authenticator({
  // Replace these parameter values with those of your own environment
  region: "ap-northeast-1", // user pool region
  userPoolId: "ap-northeast-1_XXXXXX", // user pool ID
  userPoolAppId: "XXXXXX", // user pool app client ID
  userPoolDomain: "XXXXXX" // user pool domain
  userPoolAppSecret: "XXXXXX", // 追加
});

exports.handler = async (request) => authenticator.handle(request);
1
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
1
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?