AWSコンソールからAPI Gatewayの設定をいじってたんですが、何を変更したかわからなくなったり、変更した差分が欲しかったりしたのでswagger用のファイルで管理することにしました。
ツールもあるのですんなり出来るかと思いましたが、いくつかハマった部分があるので残しときます。
Export
AWSコンソールから行えます。
エクスポートしたいAPIのStageを選択し、右にあるExport
タブからYAML / JSONがダウンロードできます。
なおエクスポートされるのはそのStageで使用しているリソースやモデルのみで、例えばErrorやEmptyといったデフォルトで用意されているAPI Gatewayのモデルも使ってなければエクスポートしたファイルには含まれません。
Export as Swagger
swaggerの定義ファイルのみ。
これをインポートしてもリソース定義のみでAPI Gateway独自の認証や呼び出すLambda Functionなどの設定はされません。
Export as Swagger + API Gateway Extentions
上記に加えAPI Gateway用の設定もエクスポートされます。
各リソースの設定などを含んでますので後述するaws-apigateway-importer
でインポートするならこれでエクスポートしたファイルを使うのが良さそうです。
Export as Swagger + Postman Extentions
Postman用の設定が追加?
見たところPostmanでテストするのに必要なリクエストヘッダが追加されてるようです。
Chrome Extension版はデバッグ時などによく使いますね。
Import
こちらのツールを使います。
https://github.com/awslabs/aws-apigateway-importer
使い方はクラスメソッドさんの記事がわかりやすいです。
http://dev.classmethod.jp/cloud/api-gateway-swagger-importer/
なお以降の記事は以下の実行環境で試してます。
- aws-apigateway-importer
commit 626a9c98cf05dbd040f6a87e978b9edf71d7209d
- java
homebrewでインストールしたjava version "1.8.0_66"
ハマった部分
ビルド時にjavac: 1.8は無効なターゲット・リリースです
のエラー
- エラーメッセージ
[ERROR] Failure executing javac, but could not parse the error:
javac: 1.8は無効なターゲット・リリースです
使用方法: javac <options> <source files>
使用可能なオプションのリストについては、-helpを使用します
- 原因
java 1.7だとダメみたいです。
homebrewで1.8に更新したら無事ビルド成功しました。
Auth type is required
のエラー
- エラーメッセージ
2015-12-24 15:58:26,839 ERROR - Error creating API, rolling back
com.amazonaws.services.apigateway.model.BadRequestException: AWS_IAM Auth type is required for AWS integrations with identity forwarding specified (Service: null; Status Code: 400; Error Code: null; Request ID: xxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxx)
- 原因
githubのREADME.mdに記載がありますが、各リソースにx-amazon-apigateway-auth
の定義がないことが原因です。
x-amazon-apigateway-integration
と同じ階層に追加してあげればOK。
x-amazon-apigateway-auth:
type: "aws_iam"
x-amazon-apigateway-integration:
Invalid mapping expression
のエラー
- エラーメッセージ
2015-12-24 15:49:42,674 ERROR - Error creating API, rolling back
com.amazonaws.services.apigateway.model.BadRequestException: Invalid mapping expression specified: Validation Result: warnings : [], errors : [Invalid mapping expression parameter specified: method.response.header.Access-Control-Allow-Methods] (Service: null; Status Code: 400; Error Code: null; Request ID: xxxxxx-xxxx-xxxx-xxxxxxxxxx)
- 原因
API GatewayでCORSリクエストを許可するためレスポンスヘッダの設定を入れてたんですが、それがインポート時にうまく処理されてないみたい?
※CORSの設定は公式ドキュメントより補足のあるクラスメソッドさんの記事がわかりやすいです。
(参考:Amazon API Gateway をクロスオリジンで呼び出す (CORS))
さらに、この時はCORSは不要になったのでAWSコンソールからヘッダ設定を削除したんですが、エクスポートしたファイルにはなぜかヘッダが残っている状態。
結局swaggerファイルから直接以下の行を削除してインポートしたらうまくいきました。
responseParameters:
method.response.header.Access-Control-Allow-Methods: "'GET,OPTIONS'"
method.response.header.Access-Control-Allow-Headers: "'Content-Type,X-Amz-Date,Authorization,X-Api-Key'"
method.response.header.Access-Control-Allow-Origin: "'*'"
追記:
これはIntegration Response
のHeader Mappings
から該当ヘッダを削除する前に、Method Response
のヘッダを削除してしまったために発生していた現象でした。
エクスポートしたファイルにヘッダの定義はないのにintegration側にヘッダ設定が残っていて不整合が起きてたのが原因でした。
ヘッダを削除するときには先にマッピングしてる方から削除しましょう。
ヘッダがちゃんと定義されてる状態だとインポートもうまくいきました。
モデルの2階層目のproperties
が消えている
こんな感じで定義してたモデルが、
{
"$schema": "http://json-schema.org/draft-04/schema#",
"type": "object",
"properties": {
"user": {
"type": "object",
"properties": {
"userId": {
"type": "string"
},
"userName": {
"type": "string"
}
}
}
}
}
インポートするとこんな感じになります。
{
"definitions": {},
"type": "object",
"properties": {
"user": {
"type": "object"
}
}
}
要するに2階層目のpropeties
がインポートされてない(エクスポートされたファイルには入っている)。
API Gatewayのドキュメントを見る限りだと2階層の定義もされてるんですが、これはJSON SchemaのルールだとNGなのかも?
未解決なので時間とってちゃんと調べたい。
パスの最上階層に/{stage-name}
が入っている
- 原因
これはAPI GatewayからエクスポートするとswaggerのbasePath
パラメータにStage名が入ってるんですが、インポートの際にはこれをAPIの基底パスとして認識するため発生してます。
Stage名が不要な場合は以下のようにエクスポートしたswaggerのbasePath
を変更しましょう。
basePath: "/prod"
↓
basePath: "/"