【Angularユーザーのための認証API自作講座②】Serverless FrameworkでCognitoオーソライザー付きRestAPIを構築する


※ 当ページには【広告/PR】を含む場合があります。
2021/06/30
2022/08/10
【Angularユーザーのための認証API自作講座①】AWS Cognitoでセキュアなユーザー認証を自力で構築する
Serverless Framework v2で作った古いプロジェクトを深く考えずにv3に移行してみる
蛸壺の技術ブログ|Serverless FrameworkでCognitoオーソライザー付きRestAPIを構築する

前回に引き続きAWS Cognitoを利用したAngularアプリケーションの作成の話の第二弾です。

合同会社タコスキングダム|蛸壺の技術ブログ
【Angularユーザーのための認証API自作講座①】AWS Cognitoでセキュアなユーザー認証を自力で構築する

今回はユーザー認証を他のサービスからCognitoへマイグレーションする際に行う作業をまとめます。

前の回では手動でCognito及びAPI Gatewayの設定しながら基本的な手順を説明しましたが、その内容はなかなか煩雑で毎回同じような作業ではやってられない...

そんなわけで今回はまっさらのAngularプロジェクトからServerless Framework(以降SLS)でCognitoオーソライザ付きのAPI関数を呼び出すアプリをステップ・バイ・ステップで作成する方法を検証します。


合同会社タコスキングダム|蛸壺の技術ブログ【AWS独習術】AWSをじっくり独学したい人のためのオススメ書籍&教材特集

図解即戦力 Amazon Web Servicesのしくみと技術がこれ1冊でしっかりわかる教科書

SLSで簡単なAPI作成

まずはとりあえずCurlでエンドポイントを叩いて、シンプルなJSONレスポンスが返ってくるAPIをSLSで立ち上げます。

お手元の環境に既にnode.jsは導入済みであるとして、以下のコマンドでSLSがグローバル環境にも導入できます。

            
            $ npm install -g serverless
$ serverless --version
Framework Core: 2.48.0
Plugin: 5.4.2
SDK: 4.2.3
Components: 3.12.0
        
グローバル環境で入れて使ってもOKですが、SLSのバージョン管理を後々しやすいように、今回はpackage.jsonからローカルインストールして利用します。ローカルインストールの場合、CLI的に利用するには/node_modules/.bin/から使うことになります。

            
            $./node_modules/.bin/sls --version
Framework Core: 2.48.0 (local)
Plugin: 5.4.2
SDK: 4.2.3
Components: 3.12.0
        
まずプロジェクトフォルダの最小の構成は以下のような感じに空のリソースを配置しておきます。

            
            $ tree
.
├── package.json
├── functions
│   └── get_public.js
├── resources
│   └── functions.yml
└── serverless.yml
        

各ソースコードの実装

では以下で新規作成したファイルの中身を具体的に実装していきます。

package.json

まずはpackage.jsonを以下のようにしておきます。

            
            {
    "name": "my_sls_learning",
    "version": "0.0.1",
    "scripts": {
        "deploy": "serverless deploy -v",
        "remove": "serverless remove -v",
        "deploy:fn": "serverless deploy function -f",
        "invoke": "serverless invoke --function",
        "invoke:lcl": "serverless invoke local --function",
        "logs": "serverless logs --function",
        "pkg": "serverless package -p tmp",
    },
    "private": false,
    "dependencies": {
        "aws-sdk": "^2.7.0"
    },
    "devDependencies": {
        "@types/aws-sdk": "^2.7.0",
        "@types/node": "^15.0.0",
        "serverless": "^2.0.0"
    }
}
        
としておいて、

            
            $ yarn install
        
するとnpmパッケージがインストールされます。

serverless.yml

以下のようにserverless.ymlを与えます。

            
            service: my-sls-learning
frameworkVersion: "2"

provider:
  name: aws
  runtime: nodejs12.x
  lambdaHashingVersion: 20201221
  memorySize: 128
  timeout: 10
  stage: ${opt:stage,"dev"}
  region: ap-northeast-1
  httpApi:
    cors: true

functions:
  - ${file(./resources/functions.yml)}

package:
  exclude:
    - '**'
  include:
    - 'functions/**'
    - 'package.json'
        
なおここではserverless.ymlのファイル分割や、zipパッケージのファイル選別などのテクニックを使っていますが、本ブログでは詳細に説明していませんのでご了承ください。

functions.yml

APIのハンドラ関数のみ定義した設定はfunctions.ymlで取りまとめています。

            
            getPublic:
  #👇リソースはserverless.ymlから見た相対パスで指定
  handler: functions/get_public.handler
  events:
    - http: GET /
    - http: GET /public
        
エンドポイントのルーティングパターンは//publicの二つを兼用するように指定しています。

get_public.js

先程のgetPublic関数のハンドラの中身は以下で与えます。

            
            module.exports.handler = async (event, context, callback) => {
    callback(null, {
        statusCode: 200,
        body: JSON.stringify({
            result: 'Greeting!'
        }),
        headers: {
            'Access-Control-Allow-Origin': '*',
            'Access-Control-Allow-Credentials': 'true'
        },
    })
}
        
これだけでAPI Gayeway & Lambda周りを手動でポチポチしてダッシュボードを行ったり来たりしなくても、認証なしのRestAPIが出来上がってしまいました。改めてSLSの便利さが実感できます。

余談 ~ serverless createコマンド

今回は利用しませんが、用意されたテンプレートからServerlessサービスを始める場合には
serverless createコマンドも利用できます。例えばaws-nodejsテンプレートから新規サービスを作る場合、

            
            $ serverless create --template aws-nodejs \
    --name [新規作成するSLSサービス名] \
    --path [新規作成するSLSサービスのプロジェクトフォルダ]
        
すると、--pathで指定したフォルダの中にそのまま利用できるリソースが以下の内容で生成されます。

            
            + serverless.yml
+ handler.js
+ event.json
        

関数のローカルテスト

さて、package.jsonのscriptにいくつか便利なコマンドを仕込んでいましたが、デプロイ前に動作確認を行うためのコマンドで
invoke localというものがあります。

            
            $ yarn invoke:lcl getPublic
#👇ローカルでレスポンスが正常に返ることを確認する
{
    "statusCode": 200,
    "body": "{\"result\":\"Greeting!\"}",
    "headers": {
        "Access-Control-Allow-Origin": "*",
        "Access-Control-Allow-Credentials": "true"
    }
}
Done in 18.02s.
        

デプロイ

それでは上記の最低限のリソースでSLSサービスをAWS上にデプロイさせてみます。

ここでは詳細は解説しませんが、AWSのサインアップの方法は
公式にいくつかの方法で載っています。

個人的には
Quick Setupで紹介されているようにSLSの読み取る環境変数を予めAWSアカウントで設定したIAMロールで置き換えておくのが手っ取り早いと思います。

            
            export AWS_ACCESS_KEY_ID="[IAMロールのID値]"
export AWS_SECRET_ACCESS_KEY: "[IAMロールのアクセスキー]"
export AWS_DEFAULT_REGION: "ap-northeast-1(例)"
        
AWSアカウントの設定が終わったら、以下のコマンドでデプロイしてみます。

            
            $ yarn deploy
Serverless: Packaging service...
Serverless: Excluding development dependencies...
Serverless: Creating Stack...
Serverless: Checking Stack create progress...
........
Serverless: Stack create finished...
Serverless: Uploading CloudFormation file to S3...
Serverless: Uploading artifacts...
Serverless: Uploading service my-serverless-learning.zip file to S3 (52.57 KB)...
Serverless: Validating template...
Serverless: Updating Stack...
Serverless: Checking Stack update progress...
..................................
Serverless: Stack update finished...
Service Information
service: my-serverless-learning
stage: dev
region: ap-northeast-1
stack: my-serverless-learning-dev
resources: 12
api keys:
  None
endpoints:
  GET - https://**********.execute-api.ap-northeast-1.amazonaws.com/dev
  GET - https://**********.execute-api.ap-northeast-1.amazonaws.com/dev/public
functions:
  getPublic: my-serverless-learning-dev-getPublic
layers:
  None

**************************************************************************************************************************************
Serverless: Announcing Metrics, CI/CD, Secrets and more built into Serverless Framework. Run "serverless login" to activate for free..
**************************************************************************************************************************************

Done in 140.42s.
        
ビルドが正常終わってエンドポイントが与えられていたらデプロイ完了です。

もし、ここでビルドやデプロイに問題がある場合には、利用しているIAMユーザーの権限が不足している場合があります。IAMロールに
AdministratorAccessの管理ポリシー相当の権限が付いているか今一度ルートアカウントで確認したり、管理者に問い合わせしたりしてみてください。

成功していれば以下のようにAPI Gatewayのダッシュボードに新しいインスタンスが出来上がっているのも確認できます。

合同会社タコスキングダム|蛸壺の技術ブログ

関数部の部分的デプロイ

もし関数のリソースだけ一部修正して再度デプロイしたい場合、再び
serverless deployコマンドすると重いプロジェクトほど処理に時間が掛かります。

そんな場合には、
deploy functionや、修正が複数の関数にまたがる時のためのdeploy list functionsがあります。

            
            $ yarn deploy:fn getPublic
Serverless: Packaging function: getPublic...
Serverless: Excluding development dependencies...
Serverless: Uploading function: getPublic (1.58 KB)...
Serverless: Successfully deployed function: getPublic
Serverless: Configuration did not change. Skipping function configuration update.
Done in 113.55s.
        
現状、関数は1つしかないのでほぼsls deployコマンドとの処理時間に大差はありません。

デプロイ前にアップロードされるzipの中身を確認する

packageコマンドを使うと、zipされるリソースを事前にローカルに出力することができます。ここではtmpというフォルダの中にzipを出力してみます。

            
            $ yarn pkg
Serverless: Packaging service...
Serverless: Excluding development dependencies...
Done in 113.05s.

#👇zipinfoコマンドで中身を確認
$ zipinfo -1 tmp/my-serverless-learning.zip
functions/get_public.js
functions/lambda.js
functions/local.js
functions/server.js
        

デプロイされた関数のテスト

デプロイ後の動作確認を行うためのコマンドで
invokeを使います。

            
            $ yarn invoke getPublic
#👇レスポンスが正常に返ることを確認する
{
    "statusCode": 200,
    "body": "{\"result\":\"Greeting!\"}",
    "headers": {
        "Access-Control-Allow-Origin": "*",
        "Access-Control-Allow-Credentials": "true"
    }
}
Done in 17.04s.
        
実行後のログをみたい場合には、logsコマンドを使いましょう。エラーが起こっていたら、何かと役にたつと思います。

            
            $ yarn logs getPublic
START RequestId: 310e2a2a-cb3c-4908-aeda-4b86d6c789ba Version: $LATEST
END RequestId: 310e2a2a-cb3c-4908-aeda-4b86d6c789ba
REPORT RequestId: 310e2a2a-cb3c-4908-aeda-4b86d6c789ba  Duration: 3.64 ms       Billed Duration: 4 ms   Memory Size: 128 MB     Max Memory Used: 64 MB  Init Duration: 133.48 ms
#...
        

Curlでエンドポイントを叩く

ではこのAPIが正常に動作しているかCurlでレスポンスを見てみます。

            
            $ curl --include https://*************.execute-api.ap-northeast-1.amazonaws.com/dev/public
HTTP/2 200
content-type: application/json
content-length: 22
date: Mon, 28 Jun 2021 17:48:34 GMT
x-amzn-requestid: a215270c-7ef8-4e63-89ab-f7eccb38bf56
access-control-allow-origin: *
x-amz-apigw-id: Bpa52FurNjMFjGA=
x-amzn-trace-id: Root=1-60da0b72-7111879c1c6117853b43330a;Sampled=0
access-control-allow-credentials: true
x-cache: Miss from cloudfront
x-amz-cf-pop: NRT57-C4
x-amz-cf-id: O0mXVZtOwvDwYm4oMgmhDbVdkWjX_8hy0CtMrvRX0D978UltmNSsaQ==

{"result":"Greeting!"}
        
と、正常にAPIが稼働しています。


合同会社タコスキングダム|蛸壺の技術ブログ【AWS独習術】AWSをじっくり独学したい人のためのオススメ書籍&教材特集

図解即戦力 Amazon Web Servicesのしくみと技術がこれ1冊でしっかりわかる教科書

Cognitoオーソライザー付きAPIの作成

今のままでは誰にでもエンドポイントを叩けてしまうため、ユーザー認証付きのエンドポイントを作成してみます。

既存のCognitoユーザープールからオーソライザーを作成する

こちらのチュートリアルで紹介されてあるように既存のユーザープールからの認証機能を共有させることも可能です。

一例として
前回の記事で利用していたCognitoユーザープールをオーソライザーに指定してみます。

CognitoユーザープールのARN値を使って、以下のようにリソースからオーソライザーを定義して利用します。

            
            Resources:
  ApiGatewaySharedAuthorizer:
    Type: AWS::ApiGateway::Authorizer
    Properties:
      Name: ApiGatewaySharedAuthorizer
      RestApiId:
        Ref: ApiGatewayRestApi
      IdentitySource: method.request.header.Authorization
      Type: COGNITO_USER_POOLS
      ProviderARNs:
        #👇CognitoユーザープールのARN値
        - !Join
          - ''
          - - '[ユーザープールのARN]'
        
なお、「ApiGatewayRestApi」は何処からともなく出てきている値を使っています。

場合によっては、RestAPIが複数あったり、別のAWSアカウントのものを使ったりと、いうケースでRestApiIdを細かく指定するようですが、特に利用したいRestAPIが指定がないと
ApiGatewayRestApiという名前が暗黙的に利用される仕様なのでこう記述するようです。

この設定を
shared-authorizer.ymlとしてresources以下に配置しておきます。

            
            $ tree
.
├── package.json
├── functions
│   └── get_public.js
├── resources
│   ├── shared-authorizer.yml #👈新規作成
│   └── functions.yml
└── serverless.yml
        
更に以下のように、このshared-authorizer.ymlserverless.yml側のresourcesタグにリソースとして反映させます。

            
            #...中略

resources:
  #👇Cognitoオーソライザー
  - ${file(resources/shared-authorizer.yml)}

#...以下略
        
さらに新しいAPIハンドラ関数用にget_private.jsをfunctionsフォルダに追加します。

            
            $ tree
.
├── package.json
├── functions
│   ├── get_private.js #👈新規作成
│   └── get_public.js
├── resources
│   ├── shared-authorizer.yml
│   └── functions.yml
└── serverless.yml
        
このget_private.jsファイルには以下のように編集しておきます。

            
            module.exports.handler = async (event, context, callback) => {
    callback(null, {
        statusCode: 200,
        body: JSON.stringify({
            result: 'Greeting!!'
        }),
        headers: {
            'Access-Control-Allow-Origin': '*',
            'Access-Control-Allow-Credentials': 'true'
        },
    })
}
        
このハンドラ関数を使って、functions.ymlへ新しいAPI関数を登録しておきます。

            
            #...中略

getPrivate:
  handler: functions/get_private.handler
  events:
    - http:
        path: /private
        method: get
        authorizer:
          type: COGNITO_USER_POOLS
          authorizerId:
            Ref: ApiGatewaySharedAuthorizer
        
ここでローカルでビルドエラーが無いかinvoke localで確認しておきます。

            
            $ yarn invoke:lcl getPrivate
{
    "statusCode": 200,
    "body": "{\"result\":\"Greeting!!\"}",
    "headers": {
        "Access-Control-Allow-Origin": "*",
        "Access-Control-Allow-Credentials": "true"
    }
}
        
ローカル環境ではバックエンドで動いているサービスが無いのでエンドポイントで認証させることはできませんが、シンタックスエラーが無いかなどを確認するのに便利です。

特にエラーなど問題なければコードとしてはコンパイルできています。

ではApi Gateway側へデプロイしてみます。

            
            $ yarn deploy
Serverless: Packaging service...
Serverless: Excluding development dependencies...
Serverless: Uploading CloudFormation file to S3...
#...中略
endpoints:
  GET - https://**********.execute-api.ap-northeast-1.amazonaws.com/dev
  GET - https://**********.execute-api.ap-northeast-1.amazonaws.com/dev/public
  GET - https://**********.execute-api.ap-northeast-1.amazonaws.com/dev/private
functions:
  getPublic: my-serverless-learning-dev-getPublic
  getPrivate: my-serverless-learning-dev-getPrivate
layers:
  None
#...
        
このhttps://**********.execute-api.ap-northeast-1.amazonaws.com/dev/privateで指定したエンドポイントがCognioオーソライザーで認証されているかを確認する作業は前回と全く同じ内容になりますので、以下のようにきちんと動作している結果だけお見せして次に進みます。

            
            $ curl --include https://*********.execute-api.ap-northeast-1.amazonaws.com/dev/private \
    -H "Authorization:[正しいIdトークン]"
HTTP/2 200
content-type: application/json
#...中略
{"result":"Greeting!!"}

$ curl --include https://*********.execute-api.ap-northeast-1.amazonaws.com/dev/private \
    -H "Authorization:[間違ったIdトークン]"
HTTP/2 401
content-type: application/json
#...中略
{"message":"Unauthorized"}
        

新規作成したCognitoユーザープールでオーソライザーを作成する

前回紹介した
手動でCognitoユーザープールを設定する手順をやってみると分かりますが、細かくマウスでポチポチと設定していくのには手間がかかり、しばらくCognitoを使ってないならば直ぐに手順を忘れてしまいそうになります。

そこでCognitoユーザープールの構築もymlで書ければ再生産性も上がり、後々管理しやすいというメリットがあります。

ということで、先程の既存のCognitoユーザープールを、新規作成したCognitoユーザープールに置き換えて、新しくCognitoオーソライザーを設定してみます。

shared-authorizer.ymlserverless.yml側のresourcesタグにリソースとして反映させます。

            
            #...中略

resources:
  #👇前のCognitoオーソライザーはコメントアウト
  #- ${file(resources/shared-authorizer.yml)}
  #👇新しいCognitoオーソライザー
  - ${file(resources/cognito-authorizer.yml)}
  #👇Cognitoユーザープール構築用
  - ${file(resources/cognito-user-pool.yml)}

#...以下略
        
ではこのymlの中身を以降で作成していきます。

cognito-user-pool.yml

まずはCognitoユーザープールの設計図にあたるyamlファイルを以下のように与えます。

だいたい
前回のCognitoユーザープールの手動による設定を再現できるようにCloudFormation形式の属性をマニュアルを参考に諸元の割り当てを行いました。

            
            Resources:
  #👇新規Cognito User Pool作成の宣言
  MySLSAuthUserPool:
    Type: 'AWS::Cognito::UserPool'
    Properties:
      #👇ユーザーパスワード復旧方法
      AccountRecoverySetting:
        RecoveryMechanisms:
          - Name: 'verified_email'
            Priority: 1
      #👇管理者権限を持つLambdaでのみユーザー作成
      AdminCreateUserConfig:
        #👇ユーザーがSDKでサインアップする場合はfalse
        AllowAdminCreateUserOnly: false
        InviteMessageTemplate:
          EmailMessage: 'Your username is {username} and temporary password is {####}.'
          EmailSubject: 'Your temporary password'
          SMSMessage: 'Your username is {username} and temporary password is {####}.'
      AliasAttributes:
        - email
        - preferred_username
      #👇ユーザーのサインアップ方法(EmailかSMSを選択)
      AutoVerifiedAttributes:
        #👇今回はEmailタイプを指定
        - email
      DeviceConfiguration:
        #👇ユーザーデバイスは記憶しない
        ChallengeRequiredOnNewDevice: false
        DeviceOnlyRememberedOnUserPrompt: false
      EmailConfiguration:
        EmailSendingAccount: COGNITO_DEFAULT
      EmailVerificationMessage: 'Your verification code is {####}.'
      EmailVerificationSubject: 'Your verification code'
      #👇MFA認証は利用しない
      MfaConfiguration: OFF
      #👇パスワードの強さを設定
      Policies:
        PasswordPolicy:
          MinimumLength: 8
          RequireLowercase: false
          RequireNumbers: false
          RequireSymbols: false
          RequireUppercase: false
          #👇一時パスワードはとりあえず最長の1年で設定
          TemporaryPasswordValidityDays: 365
      Schema:
        - AttributeDataType: String
          DeveloperOnlyAttribute: false
          #👇IDプロバイダを追加し属性マッピングを拡張する場合には変更可能に設定
          Mutable: true
          Name: email
          Required: true
      SmsAuthenticationMessage: 'Your verification code is {####}.'
      SmsVerificationMessage: 'Your verification code is {####}.'
      UsernameConfiguration:
        CaseSensitive: true
      UserPoolAddOns:
        #👇CloudWatchにてログ確認のみに設定
        AdvancedSecurityMode: AUDIT
      #👇ユーザープールの名前(サービス名&ステージ付き)を指定
      UserPoolName: ${self:service}-${self:provider.stage}-user-pool
      UserPoolTags:
        Service: ${self:service}-${self:provider.stage}
      VerificationMessageTemplate:
        #👇認証リンクなしでコード送信のみ
        DefaultEmailOption: CONFIRM_WITH_CODE
        EmailMessage: 'Your verification code is {####}.'
        EmailSubject: 'Your verification code'
        SmsMessage: 'Your verification code is {####}.'

  #👇アプリクライアントの設定
  MySLSAuthUserPoolClient:
    Type: AWS::Cognito::UserPoolClient
    Properties:
      #👇クライアント名(ステージ別)
      ClientName: ${self:service}-${self:provider.stage}-user-pool-client
      #👇認証フローの指定
      ExplicitAuthFlows:
        - ALLOW_ADMIN_USER_PASSWORD_AUTH
        - ALLOW_CUSTOM_AUTH
        - ALLOW_USER_SRP_AUTH
        - ALLOW_REFRESH_TOKEN_AUTH
      GenerateSecret: false
      #👇Cognitoから返却するエラー内容を返す
      PreventUserExistenceErrors: ENABLED
      ReadAttributes:
        - email
        - preferred_username
      #👇リフレッシュトークンの生存日数
      RefreshTokenValidity: 10
      SupportedIdentityProviders:
        - COGNITO
      #👇どのPoolに帰属するClientかをRef関数を使って先ほど設定したPoolと関連付け
      UserPoolId:
        Ref: MySLSAuthUserPool
      #👇外部のIDプロバイダー利用時に以下の属性情報の書き込みを有効化
      WriteAttributes:
        - email
        - preferred_username
        
各属性の大体の説明書きはコメントに残してありますので、何かしらの参考になる程度で、詳しい詳細はCloudFormationのドキュメントをお調べください。

cognito-authorizer.yml

次に先ほど構築したCognitoユーザープールを使ってCognitoオーソライザーを作成します。

オーソライザーの書き方は上記の項目で述べた内容とほぼ同じですが、
Fn::GetAttから新規作成したユーザープールのarn値を取り込んで利用している点が違うだけです。

            
            Resources:
  MySLSAuthAuthorizer:
    Type: AWS::ApiGateway::Authorizer
    Properties:
      Name: MySLSAuthAuthorizer
      RestApiId:
        Ref: ApiGatewayRestApi
      IdentitySource: method.request.header.Authorization
      Type: COGNITO_USER_POOLS
      ProviderARNs:
        - { Fn::GetAtt: [MySLSAuthUserPool, Arn] }
        

functions.ymlの修正

            
            #...中略
getPrivate:
  handler: functions/get_private.handler
  events:
    - http:
        path: /private
        method: get
        # integration: lambda ... x
        # integration: lambda-proxy も可
        authorizer:
          type: COGNITO_USER_POOLS
          authorizerId:
            # Ref: ApiGatewaySharedAuthorizer
            Ref: MySLSAuthAuthorizer
        
ちなみに、API GatewayにLambdaを設定する際にLambdaプロキシ統合をするかしないかが選択できます。

デフォルトではLambdaプロキシ有りの設定になります(
integration: lambda-proxyと明示に設定しても同じ)。

Lambdaプロキシ統合を選択すると、レスポンスの出力フォーマットが既に定義されているものを使うことが出来るようになります。よって基本は全てAPI Gatewayにレスポンスをお任せすることで、開発者にリソースの設計まで深く考えることなしにAPIを利用することが可能です。

一方、ここでは利用しませんが、非プロキシ統合(
integration: lambda)を選択すると自前で定義した出力レスポンスのフォーマットが別途要求されます。

マッピングテンプレートなどで任意の出力フォーマットでレスポンス返したいときに利用します。

デプロイ

これらのリソースを追加・修正してみたらデプロイを行ってみましょう。

            
            $ yarn deploy
        
正常にデプロイが完了すると、Cognitoユーザープールが以下のように新規追加されてることがわかります。

合同会社タコスキングダム|蛸壺の技術ブログ

手っ取り早く試すため
前回同様にユーザーを登録〜パスワードを設定まで行って、エンドポイントにアクセスしてみます。

            
            $ curl --include https://************.execute-api.ap-northeast-1.amazonaws.com/dev/public
HTTP/2 200
content-type: application/json
#...中略
{"result":"Greeting!"}

$ curl --include https://************.execute-api.ap-northeast-1.amazonaws.com/dev/private \
    -H "Authorization:[正しいIdトークン]"
HTTP/2 200
content-type: application/json
#...中略
{"result":"Greeting!!"}

$ curl --include https://************.execute-api.ap-northeast-1.amazonaws.com/dev/private \
    -H "Authorization:[間違ったIdトークン]"
HTTP/2 401
content-type: application/json
#...中略
{"message":"Unauthorized"}
        
以上のようなレスポンスになっていたら万事OKです。


合同会社タコスキングダム|蛸壺の技術ブログ【AWS独習術】AWSをじっくり独学したい人のためのオススメ書籍&教材特集

図解即戦力 Amazon Web Servicesのしくみと技術がこれ1冊でしっかりわかる教科書

まとめ

今回はCognitoユーザープールを自動構築したい人のためのSLSの設定ファイルの書き方について、手動構築の場合と比較しながら解説していきました。

構築したCognitoユーザープールはもっとも単純な構成のあり、Idプールなどとの連携機能もこれから盛り込んで色々と拡張してみたいところですが、次回以降はAngularプロジェクトでサーバーサイドレンダリングしたページの認証操作をどう実現していくか見ていこうと思います。

参考サイト

Serverless Framework Documentation

AWS CloudFormation Documentation

Serverless Framework の API Gateway Authorizer 実装を解説します!😎