【初心者向け】ゼロからできる!PythonでAWS SAMによるAPI作成とOpenAPIドキュメントの出力


はじめに

以前、Swaggerツールを使ったOpenAPIドキュメント作成とAPI自動生成の流れを紹介しました。
【超初心者向け】5分で試せる!OpenAPI(Swagger3.0)ドキュメント作成〜API自動生成

今回は、AWS SAM(Serverless Application Model)を使ってAPI Gateway + AWS LambdaのサーバレスなwebAPIを作成し、OpenAPIドキュメントを出力してみます。
AWS SAMを使うのは初めてです。ゼロからできるように書いてみます。

AWS SAMとは

AWS サーバーレスアプリケーションモデル (SAM、Serverless Application Model) は、サーバーレスアプリケーション構築用のオープンソースフレームワークです。迅速に記述可能な構文で関数、API、データベース、イベントソースマッピングを表現できます。リソースごとにわずか数行で、任意のアプリケーションを定義して YAML を使用してモデリングできます。デプロイ中、SAM が SAM 構文を AWS CloudFormation 構文に変換および拡張することで、サーバーレスアプリケーションの構築を高速化することができます。

SAM ベースのアプリケーションの構築を開始するには、AWS SAM CLI を使用します。SAM CLI により Lambda に似た実行環境が提供され、SAM テンプレートで定義されたアプリケーションの構築、テスト、デバッグをローカルで実行できます。お使いのアプリケーションを SAM CLI を使用して AWS にデプロイすることもできます。

CloudFormationをサーバーレスアプリケーションで利用しやすくしたフレームワークのようです。
API Gateway , AWS Lambda , DynamoDB をひとまとめに管理できます。

前提

OS:Mac
AWSアカウント作成済み

やること

  1. 環境構築(pyenv, pipenv)
  2. AWS CLIを使えるようにする
  3. AWS SAM CLIを使えるようにする
  4. AWS SAMでHello Worldしてみる
  5. OpenAPIドキュメントを出力する

環境構築(pyenv, pipenv)

1. pyenvのインストール

$ brew install pyenv

brewコマンドが使えない場合は、以下からHomebrewをインストール
https://brew.sh/index_ja.html

2. pyenvのバージョン確認

$ pyenv --version
pyenv 1.2.15

3. pyenvでpython3.7.0をインストール

$ pyenv install 3.7.0

4. pyenvでインストールしたバージョンに切り替え

localの場合は今いるディレクトリに、globalの場合は全体に反映されます。

$ pyenv global 3.7.0
$ pyenv local 3.7.0

5. 反映されているか確認

$ pyenv versions
  system
* 3.7.0 (set by /Users/yusaku/.pyenv/version)

6. pipenvのインストール

$ brew install pipenv

7. pipenvの仮想環境に入る

$ pipenv shell

AWS CLIを使えるようにする

1. aws cliのインストール

$ pipenv install awscli

2. aws cliのバージョン確認

$ aws --version
aws-cli/1.16.294 Python/3.7.5 Darwin/19.0.0 botocore/1.13.30

3. アクセスキーIDとシークレットアクセスキーの確認

https://console.aws.amazon.com/iam/home?#/security_credentials
アクセスキー(アクセスキーIDとシークレットアクセスキー)新しいアクセスキーの作成からアクセスキーを作成し、アクセスキーIDとシークレットアクセスキーを確認します。

4. awscliの設定

3で確認した情報で設定します。
https://docs.aws.amazon.com/ja_jp/cli/latest/userguide/cli-chap-welcome.html

$ aws configure
AWS Access Key ID [None]: XXXXXXXXXXXXXXXXXXXX
AWS Secret Access Key [None]: XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
Default region name [None]: ap-northeast-1
Default output format [None]: json

AWS SAM CLIを使えるようにする

1. AWS SAM CLIのインストール

$ pipenv install aws-sam-cli

2. AWS SAM CLIのバージョン確認

sam --version
SAM CLI, version 0.34.0

AWS SAMでHello Worldしてみる

今回はpipenv環境にインストールしたpython3.7を使います。

1. アプリケーションの初期化

$ sam init

    SAM CLI now collects telemetry to better understand customer needs.

    You can OPT OUT and disable telemetry collection by setting the
    environment variable SAM_CLI_TELEMETRY=0 in your shell.
    Thanks for your help!

    Learn More: https://docs.aws.amazon.com/serverless-application-model/latest/developerguide/serverless-sam-telemetry.html

Which template source would you like to use?
    1 - AWS Quick Start Templates
    2 - Custom Template Location
Choice: 1

Which runtime would you like to use?
    1 - nodejs12.x
    2 - python3.8
    3 - ruby2.5
    4 - go1.x
    5 - java11
    6 - dotnetcore2.1
    7 - nodejs10.x
    8 - nodejs8.10
    9 - nodejs6.10
    10 - python3.7
    11 - python3.6
    12 - python2.7
    13 - java8
    14 - dotnetcore2.0
    15 - dotnetcore1.0
Runtime: 10

Project name [sam-app]: AWSsam_test    

Allow SAM CLI to download AWS-provided quick start templates from Github [Y/n]: y

-----------------------
Generating application:
-----------------------
Name: AWSsam_test
Runtime: python3.7
Dependency Manager: pip
Application Template: hello-world
Output Directory: .

Next steps can be found in the README file at ./AWSsam_test/README.md

2. アプリケーションをビルドする

$ cd AWSsam_test/
$ sam build

3. アプリケーションをデプロイする

$ sam deploy --guided

2回目以降はsam deployでOKです。

4. 動作確認

3で出力されるエンドポイントにアクセスしてみます。

$ curl https://hoge.hoge-api.ap-northeast-1.amazonaws.com/Prod/hello/
{"message": "hello world"}

hello worldが返ってきました!
AWSコンソールにログインしてLambdaを見てみると、以下のようにAPI GatewayとLambdaが起動していました。

5.Lambda関数を少し変えて実行してみる

hello_world/app.pyを以下のように変更してみます。

hello_world/app.py
import json

# import requests


def lambda_handler(event, context):
    return {
        "statusCode": 200,
        "body": json.dumps({
            "message": "hello Qiita",
            # "location": ip.text.replace("\n", "")
        }),
    }

ビルドしてデプロイします。

$ sam build
$ sam deploy

エンドポイントにアクセスしてみます。

$ curl https://hoge.hoge-api.ap-northeast-1.amazonaws.com/Prod/hello/
{"message": "hello Qiita"}

変更が反映されていることが確認できました。

OpenAPIドキュメントを出力する

AWSコンソールからAmazon API Gatewayを選択し、デプロイしたAPIを選びます。
以下の画面が表示されるので、ステージをクリックしてエクスポートを選ぶと、Swagger仕様やOpenAPI仕様のドキュメントをjson形式やyaml形式で出力できます。

おわりに

今回はAWS SAMでREST APIを作成し、OpenAPI仕様ドキュメントをエクスポートしました。
逆にOpenAPI仕様をインポートしてAWS SAMを使ったAPI作成も実施してみたいです。
以下の記事で紹介されていますが、そんなに楽ではなさそう。。
https://dev.classmethod.jp/cloud/aws/serverless-swagger-apigateway/

参考

Tutorial: Deploying a Hello World Application
https://dev.classmethod.jp/cloud/aws/aws-sam-simplifies-deployment/