AWS
Amazon API Gatewayを使ってAPIを作る

はじめに

AWSのlambdaとAPIゲートウェイを使って独自APIを作成する仕事があったので、基本的な作成方法をまとめておこうかと思う

今回は、前提としてLambdaで以下のような簡単な「fruit」という関数をpython3.7で作り、API Gatewayで接続して値をもらう方法をまとめる。


import json

def lambda_handler(event, context):
    fruit = event["fruit"];
    if fruit == 'みかん':
        status = {"status": "食べた"}
        return status
    elif fruit == 'りんご':
        status = {"status": "食べてない"}
        return status

API Gatewayで設定する

APIを作成する

  1. APIメニューから、APIの作成をクリック
  2. Choose the protocolは、「REST API」 を選択
  3. 新しい API の作成では、今回は「新しいAPI」の作成を選択
  4. 名前と説明で、APIの名前とAPIの説明を入力します。エンドポイントは、「リージョン」を選択します。「エッジの最適化」を選択するとcloudfrontに作成できます
  5. APIの作成をクリック

APIの設定を行う

次にAPIの設定を行っていきます。

  1. アクションからメソッドの作成を選択します
  2. リソース枠にセレクトメニューが出てくるので、POSTを選択してチェックボタンをクリック
  3. POSTのセットアップを行います。Lambdaを使うので、統合タイプをLambda関数にします
  4. 作成したLambdaのリージョンを選択して、Lambda関数に作成した関数名を入力します。文字入力し始めるとリストが出るのでそこから選択すると楽かも
  5. ほかの項目はデフォルトの状態で、保存をクリック
  6. lambda関数に権限を与えるか聞かれるので、OKします

APIのテストを行う

これで最低限の動きをするAPIが作成され、テストが行える状態になります。まだ公開はされていません。正しく動くかテストを行い、その上で公開作業を行います。

  1. 先ほど作成したPOSTのメソッドの実行画面に移動すると、左にテストと書かれた箇所があるのでクリックします。
  2. リクエスト本文にlambdaでテストするときと同じリクエストを書きます。
    
    {
        "fruit":"みかん"
    }
    
    
    というリクエストを本文に作成して、テストボタンを押します
  3. レスポンス本文にLambdaのテスト時と同じ以下の様な値が帰ってきたら成功です。fruitをりんごに換えると、「食べてない」が帰ってきます。
    
    {
      "status": "食べた"
    }
    
    

APIをデプロイする

テストを行い動作を確認したら、デプロイを行い、実際にURLを叩いて動く状態にしていきます。

  1. リソースのアクションボタンより、APIのデプロイを選択します
  2. デプロイする場所を新しいステージを選び、任意のデプロイ名を入力します。説明などは分かりやすいものを入力しましょう

成功すると、ステージエディターに移動します。URLの呼び出しにエンドポイントが表示されています。クリックすると、以下のようなメッセージが表示されると思います。


{"message":"Missing Authentication Token"}

手っ取り早くPOSTしてちゃんと動いているか確認したいので、curlコマンドを使って以下のようなものを叩きます。


curl -d '{"リクエスト値"}'  APIのURL

日本語だと正しく表示されないかもしれませんが、値が帰ってくれば成功です。

CORSの有効化

ブラウザを使って値を取得する場合、デフォルトでは取得できない為、CORSの設定が必要となります。CORSの説明についてはここでは割愛します。

  1. API Gatewayに戻って、リソースのアクションを開きます。その中にCORSの有効化があるので選択します。

  2. 続いて、CORSの設定画面がでます。デフォルト設定では、Access-Control-Allow-Origin: '*' になっています。これだとどのドメインからもアクセスができてしまうので、アクセス元のドメインが決まっているなら、設定した方がいいでしょう。設定後、【CORSを有効にして既存のCORSヘッダーを置換】を選択します
  3. 自動的に指定したCORSの設定に切り替えてくれるので、設定が終わったらデプロイを行います。

jqueryを使って値を受け取る

jqueryで値を受け取るには、ajax関数を使ってAPIに値をPOSTして取得します。


<html lang="ja">
<head>
	<meta charset="UTF-8" />
	<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.2/jquery.min.js"></script>
<script type="text/javascript">
$(function() {
    $("#btn").click(function(){	
        var params = {
		  "fruit": "みかん"
		};
        $.ajax({
	    url: 'API URLを挿入',
	    type: 'POST',
	    data: JSON.stringify(params),
	 dataType: "json",
		    success: function(json) {			 
			var stringData = JSON.stringify(json);
     		var parseData = JSON.parse(stringData);
			$('#test').text(parseData.status);  //parseData. の後に取得したいJSONの項目を入力。
		    },
		    error: function() {
		       alert("error");
		    },
	  	});	
    });
});
</script>
</head>
	<body>
		  <button id="btn">test</button>
		<div>
			<h1>結果を表示</h1>
			<p id="os"></p>
			<p><span id="test"></span></p>
			
		</div>
	</body>
</html>

ajax関数経由でapiに必要な情報をpostします。成功すればlambdaで設定したリターン値が帰ってくるので、JSON.stringifyとJSON.parseで分解して、#test に挿入しています。もし、失敗した場合はerrorがアラートで表示されるようになっています。

PHPを使って値を受け取る

PHPの場合はcurlを使ってAPIのエンドポイントにデータをポストします。

色々とやり方はあると思いますが、下記のやり方だと、formから受け取ったデータをAPI用にJSONに直してあります。

その後、curlを使用して、データを取得します。curl_closeをする前に、受け取ったjsonデータをエンコードして変数に入れ込んでおきます。


$primary = htmlspecialchars($_POST['primary']);
$data = array('primary'=>$primary);
$data_json = json_encode($data);
$ch = curl_init();
curl_setopt($ch, CURLOPT_CUSTOMREQUEST, 'POST');
curl_setopt($ch, CURLOPT_POSTFIELDS, $data_json);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
curl_setopt($ch, CURLOPT_URL, 'APIのURL');
$result=curl_exec($ch);
$res_json = json_decode($result , true );	
curl_close ($ch);

APIキーを使う場合

APIキーを使ってアクセス制限を行う方法も記載しておきます

  1. APIを選択し、リソースのPOSTを選択します
  2. メソッドリクエストを選択します
  3. API キーの必要性の項目をtrueにしてチェックボタンを選択し変更します。CORSを有効化した場合、optionができていると思いますが、こちらは何も設定しないでおきます
  4. デプロイします
  5. 次にキーを発行して、デプロイしたAPIに使用料プランを割り当てます
  6. API Gatewayを開いて、使用料プランを選択します
  7. 作成ボタンを選択します
  8. 名前を入力します
  9. スロットリングの有効化に値を入れます。レートは1秒間あたりのリクエスト上限数、バーストはパケットの上限数になります。クォーターは、一ヶ月間でリクエストできる上限数です。必要に応じて各項目の数字を入力し、次ぎに進みます
  10. APIステージの追加を選択肢、APIキーを使いたいAPIとステージを選択し、チェックマークボタンを選択します。設定されたら次へ
  11. APIキーを作成していないので、「APIキーを作成して使用料プラン」に追加を選択します
  12. 名前を入力し、APIキーの作成方法を選択します。自動生成が楽です。設定したら保存します
  13. APIキーが設定されますので、完了を選択します
  14. これで設定が完了しましたが、自動生成にした場合キーが分からないと思いますので、メニューのAPIキーを選択し、作成したAPIキーを選択します
  15. APIキーの表示ボタンをクリックすると、APIキーが表示されるのでコピーします

正しくできているかチェックします。


curl -d '{リクエスト値}' APIのURL

でAPIキーを設定するまではできていましたが、制限がかかっているので、forbiddenで帰ってきます。

curlコマンドにheaderを追記し、apiキーを記載します。


curl -d '{リクエスト値}' APIのURL --header "x-api-key:APIキー"

これで、値が帰ってくれば成功です

ajaxで行いたい場合は、


headers: {"x-api-key":'APIキー'},

をdataTypeの上とかに追記します。

PHPの場合は、


curl_setopt($ch, CURLOPT_HTTPHEADER, array('x-api-key:APIキー'));

を追記してあげます。

設定しているはずなのに、うまくいかない場合は、「使用料プラン」でAPIキーを再び付け直したりするとうまくいったりします。

APIキー自体、jqueryなどを使う場合ソースを見れば簡単に分かってしまうので、見えない様に工夫しないと、好きなだけリクエストできてしまうので、注意が必要です。