【AWS Lambda+API Gateway】Pythonでslack通知アプリ作ってみた

#はじめに
我が社のCTOが、「エンジニアはみんな`Lambda`くらい使えるようになっていてほしいね〜」
とのありがたいお言葉から、

「自分もエンジニアになったからには、`Lambda`でAPI作ってみよう！」と、
一念発起して、挑戦してみますた(⌒▽⌒)


#LT;DR

- Lambda関数の作成
- Slack Api Incoming WebHooksの作成
- Layerの作成 & 登録
- API GatewayでAPIの作成
- 実践と結果まとめ


#Lambda関数の作成
##Lambdaとは
>AWS Lambda は、サーバーのプロビジョニングや管理の必要なしにコードを実行できるコンピューティングサービスです。
Amazon API Gateway を使用すると HTTP リクエストに応答してコードを実行できます。
参照元：[AWS Lambda とは](https://docs.aws.amazon.com/ja_jp/lambda/latest/dg/welcome.html)

ほうほう、AWSに管理系は丸投げできるんですな。
今回は、`HTTP`リクエストを投げるので、やりがいありそう。

##Lambda関数を作ってみる。
###AWSアカウントのLambdaのページに入って関数の作成を押す。
![スクリーンショット 2021-03-30 10.01.43.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1075243/4e66b3b2-b5bb-37e0-256e-6af7c2f5f7a3.png)

###関数名：`myLambdaFunc`、ランタイム:`Python 3.8`で作成。

![スクリーンショット 2021-03-30 10.15.51.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1075243/55bdf2b5-15c4-ae04-453e-82f440ba2222.png)

###コードソース（エディタ上）に書いた`Python`コード
```python:lambda_function.py
import json
import os
import requests

def lambda_handler(event, context):

    WEBHOOK_URL = os.environ['WEBHOOK_URL']
    WEBHOOK_NAME = os.environ['WEBHOOK_NAME']
    CHANNEL_NAME = os.environ['CHANNEL_NAME']
    
    data = {
            'username': WEBHOOK_NAME,
            'channel': CHANNEL_NAME,
            'attachments': [{
                'title': 'myLambdaFunc',
                "color": 'danger',
                'text': 'myLambdaFunc API was successful!!'
            }]
    }
    requests.post(WEBHOOK_URL, json.dumps(data))
    
    return {
        'statusCode': 200,
        'body': json.dumps(data)
    }
```
####<解説>
環境変数から下記3つを受け取り、
![スクリーンショット 2021-03-30 14.32.42.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1075243/551c3f4a-fa1a-e552-a558-328f4643e7dd.png)
[slack api](https://api.slack.com/apps)で作成した`Incoming Webhooks`のアプリ設定をしたトーク部屋に通知した後、`data`をフロント側に`JSON`で返す
といったものすごくシンプルなやつです。

※コードを編集したら`Deploy`を押さないとダメ
※`import requests`は**レイヤー**が必要なので、後述


#Slack Api Incoming WebHooksの作成
###[slack api](https://api.slack.com/apps)に行って`Create New App`
![スクリーンショット 2021-03-30 14.39.37.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1075243/da2eaade-75b0-1c46-4b2f-2804300ddc0b.png)

###`Incoming Webhooks`を新規追加して、環境変数登録用のURLを取得しておく。
![スクリーンショット 2021-03-30 14.41.20.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1075243/ae634ba8-20e1-bcac-f77c-01a1ce0a1364.png)
![スクリーンショット 2021-03-30 14.41.36.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1075243/52b8d71a-db4d-c060-9cf1-35d25931e2d0.png)

#Layerの作成&登録
自分の場合、上記関数をテストした時に、**requestsライブラリのimportで失敗した**ので、
layerとしてライブラリを取り込んでから実行する。

##Layerとは
>レイヤーは、ライブラリ、カスタムランタイム、その他の依存関係を含む .zip ファイルアーカイブです。レイヤーを使用することで、関数のライブラリを使用することができます。
参照元：[Lambda レイヤー](https://docs.aws.amazon.com/ja_jp/lambda/latest/dg/configuration-layers.html)

つまり、Lambdaでサードパーティ製のライブラリやモジュールを使用する時に、Layerに格納して各Lambda関数から呼び出して使用できるようになる仕組み。



##Layer Zipの作成
自分はローカルでZipファイルを作成しました。

```bash
$ mkdir ./python
$ cd python
$ pip install requests -t . 
$ cd ../ && zip -r Layer.zip python/
```
任意のフォルダを作って、そこに`requests`ライブラリをインストールして、Layer.zipという名前で**Zip化**。
ちなみに、
[pipコマンドのインストール方法はこちら](https://qiita.com/ichi_zamurai/items/dcbac977c1ff367b9094)

https://qiita.com/ichi_zamurai/items/dcbac977c1ff367b9094

##Layerの追加&アップロード
###サイドメニューの`レイヤー`を選択し、レイヤーの作成をする。
先ほど作成した`Layer.zip`をアップロードする。
![スクリーンショット 2021-03-30 14.50.52.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1075243/d04283f0-3045-1012-e5de-7b5575160182.png)
名前と説明は任意。ランタイムはLambda関数で`Python3.8`を選択したので、それに合わせる。

###生成物はこんな感じ
※ランタイム設定を忘れたから、一度削除して、同じ名前で作成し直したら、version2になっちゃいました、、悔やまれるw
![スクリーンショット 2021-03-30 12.03.27.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1075243/a358109c-a22b-77d8-a25f-deb7ef32da54.png)

##Lambda関数にLayerの登録
###`Layers (0)`をおすと、下部のレイヤーに移動、レイヤーの追加をする
![スクリーンショット 2021-03-30 12.00.20.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1075243/e84f366d-829e-8dd4-a718-e45316c803b1.png)
![スクリーンショット 2021-03-30 12.00.48.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1075243/54f110cd-f754-4a48-eaca-3b3f7264ec52.png)
###カスタムレイヤーを選択し、さっき登録した`myRequestLayer`を登録。
version2となってしまったのが悔やまれる。
**※ランタイムが同じじゃないと選択肢に出てこない。**
![スクリーンショット 2021-03-30 12.03.59.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1075243/5171ab43-a0aa-9c86-fde4-3856ab5e211a.png)


##一旦、関数のテスト実行
成功しました◎ Lambda関数の単体的には、実行ができる状態。
![スクリーンショット 2021-03-30 12.14.27.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1075243/e3e16a1d-1b32-2d6b-3758-e31987c67240.png)



#API GatewayでAPIの作成
###Lambda関数の「トリガーを追加」から、`API Gateway`を選択して、下記キャプチャのように設定
※テスト用なのでセキュリティはオープンにしてます。
※ドメインを超えてAPIを叩く予定なので、CORSにチェックしました。
※`HTTP API`と`REST API`の違いはこちら=> [HTTP API と REST API 間で選択する](https://docs.aws.amazon.com/ja_jp/apigateway/latest/developerguide/http-api-vs-rest.html)
![スクリーンショット 2021-03-30 12.18.50.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1075243/18600a62-b6ee-2e35-f00f-0864c56fc644.png)

###トリガーが作成されました!!
![スクリーンショット 2021-03-30 12.28.17.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1075243/cecf6324-2630-a2d8-ceb0-3934db99a152.png)

###エンドポイントを直で叩いてみる
JSONの`data`の中身が返ってきましたな。
![スクリーンショット 2021-03-30 12.27.59.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1075243/75fcd968-e79e-e294-5c90-cc4f8ab4568f.png)

###ここまで来れば、あとは、フロント側でAPIエンドポイント目掛けて叩きまくるのみ＼＼\\٩( 'ω' )و //／／
※叩くたびに課金されてゆきます...

#実践と結果まとめ
##APIエンドポイントを叩いてみる。
ボタンを一つだけ用意したフロント側から
（アプリクソしょぼいorz Google並のシンプルさw Qiitaのh1タグにしか見えないセンスオワタ＼(^O^)／)
![スクリーンショット 2021-03-30 12.35.30.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1075243/26922fdd-4da2-aecf-02f1-c5cf0443f7d3.png)
`Notify`ボタンをポチっとな、と。

###slackの[スコスコスコッ♪]という音と共に通知された。
![スクリーンショット 2021-03-30 12.15.20.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1075243/ec1dc930-cdf6-cdcc-2ff9-90100f5299c7.png)

###ディベロッパーツールで確認してみる
####ちゃんとJSONのdataが返ってきてますねえ〜
![スクリーンショット 2021-03-30 12.35.48.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1075243/c4e59acc-1b47-1a24-0976-c90669e9375a.png)

####HTTPヘッダーもみてみよう。
ちゃんと `GET 200` で成功してますな✨
![スクリーンショット 2021-03-30 12.36.23.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1075243/116481fc-cb8c-ce05-eb21-ee90cb9e0477.png)



#まとめ
あまりハマりどころもなく、ボタンぽちぽちでほぼ行けたので、

ああ、Lambda
なんと簡単なことでしょう。

しかもサーバーレスかつ、保守管理等も気にすることがない。

簡単なアプリ作るだけだったら、料金的にも安いから、フロントだけ作って、APIサーバー抜きで、
Lambdaさんに頼っちゃっても良さそう✨

以上、ありがとうございました。