逆引きマニュアル: AWSで独自ドメインからアクセスできるServerless APIを作ってみた

投稿日:

やりたいこと

AWS Lambdaを使ったサーバレスAPIを実装し、 それを独自ドメインに割り当てる方法です。

前提条件

  • AWS CLIがインストールされていること

概要

以下のサービスを使います。

  • AWS Lambda
  • Amazon API Gateway
  • AWS Certificate Manager
  • Amazon Route 53

また、フレームワークにServerless Frameworkを使います。

手順(サービスの作成)

もしCAAレコードを設定していて、値にamazon.comがない場合、 キャッシュが切れるまで時間がかかるため、先に設定した方がいいです。

Serverless Frameworkのインストール

npm install -g serverless

以下のコマンドでバージョンが確認できます。 今回は1.32.0でした。

  • serverless -v
  • sls -v

以下では打つのが簡単な、slsコマンドを使用します。

アクセスキーの作成

こちらの記事を参考にしてください。

ただし自分は、profileを明示的に指定しました。

aws configure --profile sls

サービスの作成

sls create -t aws-python -p slstest

オプションは以下になります。その他のオプションはsls create --helpで。

  • -t: テンプレート
  • -p: パス

serverless.ymlの編集

cd slstest
vi serverless.yml

以下のようにprofileとregionを設定してください。 ただし環境に依存するので、--aws-profileオプションの方がいいかもしれません。

provider:
  name: aws
  runtime: python2.7
  profile: sls
  region: ap-northeast-1

デプロイ

sls deploy
sls deploy --aws-profile sls # 明示的にprofileを指定する場合

この時に、以下のリソースが作成されます。

  • S3: バケット。中身はjsonとzipの模様。
  • CloudFormation: スタック。
  • Lambda: 関数。

あとIAMやログ関連の設定もされるようです。

もし見つからない場合は、リージョン指定が漏れている可能性があります。 'us-east-1' リージョンに作成されていないか確認してください。

テスト

sls invoke -f hello

削除

sls remove

手順(サービスのAPI化)

serverless.ymlを編集し、以下のようにeventsを追加します。

functions:
  hello:
    handler: handler.hello
    events:
      - http:
          path: hello
          method: get

編集したらデプロイします。

コンソールに以下のように書かれるので、このURLにアクセスすることで、サービスが使えます。

endpoints:
  GET - https://xxx.execute-api.ap-northeast-1.amazonaws.com/dev/hello

手順(APIの独自ドメインへの割り当て)

このURLを直接使うことも可能ですが、以下の2つの問題があります。

  • AWSが勝手に割り当てたドメインであること
  • パスにステージ名(dev)が含まれていること

そのため、使いやすくするように、独自ドメインに割り当てます。

今回は api-dev.ikemo3.com に割り当てます。

証明書の作成

こちらの記事を参考にしました。

ドメイン名の追加画面で入力するドメイン名に api-dev.ikemo3.com を入れます。

それからRoute 53にCNAMEレコードを追加し、しばらく待ちます。 最大30分ですが、数分でOKでした。

API Gatewayでカスタムドメイン名の設定

これも以下の記事が参考になります。

設定は以下になります。

  • ドメイン名: api-dev.ikemo3.com
  • エンドポイントの設定: Regional
  • ACM証明書: 作成した証明書

作成したら、「編集」リンクをクリックして、 パスマッピングを追加します。

  • パス: /
  • 送信先
    • API: 作成したAPI
    • ステージ: dev

最後に、Route 53に登録します。 Ansibleでは以下になります。 valueにはターゲットドメイン名を入れてください。

- name: api-dev.ikemo3.com
  route53:
    state: present
    zone: ikemo3.com
    record: api-dev.ikemo3.com
    type: CNAME
    overwrite: true
    value: xxx.execute-api.ap-northeast-1.amazonaws.com

これで https://api-dev.ikemo3.com/hello にアクセスすると、サービスが実行されます。

補足

応答が返ってくるまでの時間は200ms〜800ms程度でした。

外部サイト

マニュアル