re:invent2017で発表されたAWS Cloud9でサーバーレスなAPIを作ってみた

AbemaTV Advent Calendar 2017 3日目の記事です。
テーマフリーなので多様な記事が並ぶと思いますよ。

今日は2017年2月にジョインしたiOSエンジニアの服部が担当します。

はじめに

re:Invent 2017で多数のサービスが発表されました。

外部参考エントリ:
【速報】AWS re:Invent 2017 Keynote 1日目で発表された新サービスまとめ #reinvent
【速報】AWS re:Invent 2017 Keynote 2日目で発表された新サービスまとめ #reinvent
クラスメソッドさんの怒涛の速報。早過ぎる。

普段iOSエンジニアの私ですが AWS Cloud9 を試してみたので気軽に見てみてください。
おまけで Amazon Rekognition Videoもブラウザから動かしてみました。

AWS Cloud9 画面例: ブラウザ上で開発が完結

AWS Cloud9

AWS Cloud9 – クラウド開発環境

クラウド上のIDEです。
ブラウザで開発が完結します。これがあるべき未来か。
近いうちにElectronでアプリが出る予感。

Lambda Functionのローカル実行、API Gatewayでのデプロイ、デプロイしたAPIの実行が画面切り替えなしにできるのが神です。

ハッカソンのちょっとしたAPI作成や趣味で作るアプリのバックエンド作成など、高速にできそうですね。
ガチサービスのバックエンド開発でも使えるはず。

まだTokyoリージョンでは使えません。

今回は簡易的なサーバーレスAPIモニタリング機能を作ってみました。

ざっくり手順を。

Step 1. Lambda Function 関連権限付与

Admin権限を持つユーザで進める場合、Step 2. Environment作成へスキップして良いです。

Working with AWS Lambda Functions in the AWS Cloud9 Integrated Development Environment (IDE)

1-1. IAMで開発用ユーザorグループに以下の権限をAttach

Adminユーザで、開発用グループにIAMのページから以下を付与しました。
- AWSLambdaFullAccess
- AmazonAPIGatewayAdministrator
- AmazonAPIGatewayInvokeFullAccess

1-2. AWS CloudFormationでStack作成

Adminユーザで、CloudFormationからStackを作成。

Choose a template > Specify an Amazon S3 template URL に https://s3.amazonaws.com/cloud9-cfn-templates/Cloud9LambdaAccessGroup.yaml をペースト:

Stack nameには AWSCloud9LambdaAccessStack、GroupNameには開発用グループ名:

Optionsは変更なし:

Createをクリックし数秒でStack作成完了:

Step 2. Envioronment作成

Create environmentクリック

"Sample0001"等入れてNext Step。(この名前は後から変えられるのだろうか)

EC2インスタンス上に作ります。VPC作っていなかったら作成してください。Next Step。

Create environment

数十秒待つと...

environmentが出来ます!

Step 3. Lambda Function作成

environmentのWelcome画面からCreate Lambda Function...

Function名入れてNext。

今回はnode.jsで。

Function TriggerにAPI Gateway設定。Resource Pathに/check

Next。

Finish!

以下を実装。
Javascriptは初心者ですみませぬ。
今回はgithubユーザ情報取得APIステータス200を確認しています。

'use strict';

var https = require('https');
var url = require('url');

var targetURLPaths = {
    "githubUsers":"https://api.github.com/users/[githubユーザ名]"
    //,"someAPI": "API URL"
};

var results = {};

function getAPI(key) {
    var urlObj = url.parse(targetURLPaths[key]);
    var options = {
        host: urlObj.host,
        port: 443,
        path: urlObj.pathname,
        headers: {
            "Content-type": "application/json; charset=UTF-8",
            "User-Agent": ""
        },
        method: 'GET'
    };
    return new Promise((resolve, reject) => {
        setTimeout(function () {
            var req = https.request(options, function(res) {
                console.log(res.statusCode);
                if (res.statusCode != 200) {
                    results[key] = "Fail: " + res.statusCode;
                    resolve(key);
                    return;
                }
                var body = '';
                res.on('data', (chunk) => body += chunk);
                res.on('end', () => {
                    //console.log(body);
                    results[key] = "Success";
                    resolve(key);
                });
                res.on('error', function(e) {
                    results[key] = "Fail: " + e;
                    resolve(key);
                    return;
                });
            });
            req.end();
        }, 300);
    });
}

exports.handler = (event, context, callback) => {
    var promises = [];
    Object.keys(targetURLPaths).forEach(function (key) {
        promises.push(getAPI(key));
    });
    Promise.all(promises)
        .then(() => {
            var response = {
                statusCode: 200,
                headers: {
                    "Content-type": "application/json; charset=UTF-8"
                },
                body: JSON.stringify(results, null, 2)
            };
            callback(null, response);
        })
        .catch(callback);
};

Step 4. Deploy

Lambda (local)で動作確認した後...

左から4番目の上向き矢印でデプロイ!簡単だぜ

API Gateway (remote)で動作確認!動いとる

ブラウザからAPI叩いてみても良し。

Lambdaは定期実行できるので、内部APIの生存確認を回してSlack通知などしたいところ。

おまけ: Amazon Rekognition Image / Amazon Rekognition Video

画像解析APIです。
2016年に発表されたAmazon Rekognition Imageは静止画を解析します。

まずはこちらを試してみます。

(シェア可能な画像を使用。問題あったら言ってください...)
スクリーンショット 2017-12-02 3.16.59.png

うむ!
セレブリティとしてばっちり認識されています。

デモなのでブラウザから動かしていますが、APIとしても利用可能です。

続いて先日発表されたAmazon Rekognition Videoで動画を解析してみます。
動画の長さに制限があり1分まで。

研究/調査目的のmp4動画を流し込んでみます。

S3の保存先を生成。

5分程待つと結果が出ました!

稲垣氏が見事パットを決めた名場面ですが Objects and activities はかなり情景を捉えている気がします。

雑感

IDEがクラウド上にありサービスとつながっているのは想像以上に便利。
AWSのアカウントさえあれば、どこでも開発の続きができるという安心感。
Lambdaのローカルテスト、1クリックでのデプロイ、API Gatewayとの連携は嬉しい機能。
手順が手に馴染めば超高速開発ができるのでは。

Amazon Rekognition Imageのイメージ解析の速度と精度はかなりのもの。
Videoは1分の動画解析に5分程掛かるのは仕方ないか。
取り出すべき場面を見つけるシーケンスとそこから解析するシーケンスに分けているようだ。
返却されるJSONは15MBあった。
これはユースケースをまず考えるべき。

AWS楽しいすね。