10
8

More than 1 year has passed since last update.

API GatewayをS3のプロキシとして作成してみる。

Last updated at Posted at 2021-09-25

はじめに

先日の記事で LambdaAPI Gateway を利用したREST API経由のS3内のファイルダウンロードは試してみたが、API Gateway のみでも同じ事はできそうと聞いたので、そちらの方も今回試してみた。
 ※先日の記事はこちら

作成の流れ

基本的には以下の公式サイトをベースに作成しているが、いくつか分かりづらかったところは勝手に手順をアレンジしている。
また、公式サイトではバケット内の一覧情報の取得などの方法も含まれているが、今回の記事ではバケット内の指定オブジェクトをダウンロードする ところのみに絞った内容にしている。

① IAMロールの作成
② API Gatewayの作成
 ・リソースの作成
 ・GETメソッドの作成
 ・統合リクエストの設定
 ・メソッドレスポンスの設定
 ・統合レスポンスの設定

① IAMロールの準備

IAMロールの新規作成

AWSサービスのIAMより、ロールの画面を開いてロールを作成する。
下図の様にAPI Gateway をユースケースとして、【次のステップ】をクリック。
Qiita-no055_img01.jpg
『Attached アクセス権限ポリシー』、『タグの追加 (オプション)』の設定画面に遷移するが、デフォルトから特に変更せずに【次のステップ】をクリック。

最後に任意なロール名を付けて【ロールの作成】をクリック。

作成したロールにポリシーアタッチ

作成したロールを開き、『アクセス権限』タブよりポリシーをアタッチする。
今回デフォルト以外に追加でアタッチするポリシーは AmazonS3ReadOnlyAccessのみ。(今回の記事ではS3内オブジェクトのダウンロードしかしないため。)

② APIGatewayの作成

リソースの作成

Root直下に folderリソースを作成する。
URLリクエストの際にバケット名を指定してする部分に相当。
Qiita-no055_img02.jpg

folder の下に item リソースを作成する。
こちらはURLリクエストの際にオブジェクトを指定する部分に相当。
Qiita-no055_img03.jpg

GETメソッドの作成

item リソースの下に GET メソッドを作成。(設定は下図を参照)
Qiita-no055_img04.jpg

※1.AWSリージョンについては、今回GETを試すS3バケットのリージョン。
※2.パス上書きでは、S3で受け取れるパスにしている。
※3.実行ロールの部分には、①で作成したロールの ロールARN をコピペ。

統合リクエストの設定

S3 にバケット名とオブジェクト名を投げるために、URLパスパラをマッピングする。
Qiita-no055_img05.jpg

メソッドレスポンスの設定

200(成功時)のレスポンスヘッダーに、出力時に追加したいHeader名称を追加。
今回は Content-TypeContent-Disposition を追加。

統合レスポンスの設定

上記のメソッドレスポンスにより返すヘッダーを決めたので、その中身のマッピングを行う。
 ・Content-Type ⇒ integration.response.header.Content-Type
 ・Content-Disposition ⇒ 'attachment; filename="download"'
  ※ダウンロードファイルの名前はdownload

(中身のファイル構造が影響を受ける訳ではないため、この段階で拡張子は付ける必要なし。拡張子はローカルに落とした後に単にどのアプリを使って開くかくらいな話なので、ダウンロードしてからリネームすればOK。)
Qiita-no055_img07.jpg

テストを実施

対象のバケット内に適当なテストファイルを入れた後、{folder}{item} を入力して、下図の様なレスポンスがちゃんと返ってくればOK!
Qiita-no055_img08.jpg

テストで特に問題なければAPIをデプロイし、URLからバケットとオブジェクト(今回の場合バケット直下に置いたオブジェクト)を指定してdownloadという名前のファイルがダウンロードできればOK!

      

おまけ

バケット直下より深いオブジェクトを指定する方法

API Gatewayのリソース作成でそもそも folderitem しか作成していない場合は無理そう。
試しにGETテストで {item}test_folder/test.txt を入れてみたが、2つのリソースの情報が含まれているため、これではオブジェクトの情報を取得できなかった。
解決方法としては、バケット内のフォルダ階層に応じたリソース、bucketfolder1folder2item などを作成すれば、後は同じ要領でオブジェクトにちゃんとアクセスできる。

ちゃんとデータを取得できなかったときはエラーステータスを返す方法

メソッドレスポンスより400500のHTTのステータスを追加する。
Qiita-no055_img09.jpg

統合レスポンスの追加より、バックエンドから400番台のステータスコードが返った場合に、メソッドレスポンスのステータス400とマッピングする(500番台も同様に作成)
Qiita-no055_img10.jpg

この状態で試しにテストし、存在しないファイルを指定した場合にステータス400で返ってくれば、ちゃんと設定できている。

バイナリファイルをダウンロードする方法(jpg、zipなど)

以下のサイトを参考に現在試し中。やり方が分かり次第更新予定。

10
8
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
10
8