LoginSignup
6
4

More than 3 years have passed since last update.

AWS Cloud9でオウム返しLINE Botを作る

Last updated at Posted at 2020-09-27

はじめに

AWS Cloud9 上でSAM Localを使い、オウム返しするLINE Botを作るメモ

構成図

こんなの作ります。

image.png

手順の概要

  • [LINE Developers] プロバイダー作成
  • [LINE Developers] 作成したプロバイダーにチャネルを設定
  • [LINE Developers] 作成したチャネルで2つの情報を取得
    • チャネルアクセストークン
    • チャネルシークレット
  • [AWS] Cloud9環境を用意する(東京リージョン: ap-northeast-1)
  • [AWS-Cloud9] Lambdaを作成する
    • Function name
    • Application name
  • [AWS] Lambdaスクリプト更新
  • [AWS] Lambdaに環境変数を設定
    • LINE_CHANNEL_SECRET (チャネルシークレット)
    • LINE_CHANNEL_ACCESS_TOKEN (チャネルアクセストークン)
  • [AWS] API GatewayのURL呼び出し を確認
  • [LINE Developers] チャネルの設定更新
    • Webhook URL (← API GatewayのURL呼び出し)
    • Webhookの利用 無効->有効
    • 応答メッセージ 有効->無効

参考

1.[LINE Developers] プロバイダー作成

LINE Developersでプロバイダーを作成します。

image.png

2.[LINE Developers] 作成したプロバイダーにチャネルを設定

先ほど作成したプロバイダーにチャネルを設定します。

image.png

Messaging APIを選択します。

image.png

3.[LINE Developers] 作成したチャネルで2つの情報を取得

チャネルシークレット、チャネルアクセストークンの情報を取得します。

チャネルシークレットの情報
image.png

チャネルアクセストークンの情報は、発行ボタンをクリックします。
image.png

4.[AWS] Cloud9環境を用意する

AWSコンソールで、Cloud9を作ります。東京リージョン(ap-northeast-1)で作成しました。

image.png

5.[AWS-Cloud9] Lambdaを作成する

SAM Localを使いLambdaを作成します。Cloud9の右側にあるλ -> λ+とクリックし、新規作成します。

image.png

赤枠の欄に、任意の文字列を設定しNextボタンをクリック

image.png

Pythonを選択しました。

image.png

API Gatewayもまとめて作成します。

image.png

デフォルト設定にしました。

image.png

Finishボタンをクリックすると作成が開始されます。

image.png

作成が完了すると、このような画面になります。

image.png

※余談※ [AWS] 作成したAWSリソース確認

これまでで作成したAWSリソースは、CloudFormationスタックで確認できます。2つのスタックが作られていて、最初のスタック(aws-cluod9-xxx)は、Cloud9を作成したときのスタック、次のスタック(cloud9-app1)は、Lambdaを作ったときのスタックです。

image.png

Lambdaを作ったときのスタックのリソースタブで作成されたAWSリソースを確認できます。

image.png

6.[AWS] Lambdaスクリプト更新

今あるLambdaスクリプトを全て削除し、以下のスクリプトをコピーします。

Lambdaスクリプト
# 環境変数
# LINE_CHANNEL_SECRET       チャネルシークレット
# LINE_CHANNEL_ACCESS_TOKEN チャネルアクセストークン

import json  
import os  
import logging  
import urllib.request
import base64  
import hashlib  
import hmac

# ログ出力の準備  
logger = logging.getLogger()  
logger.setLevel(logging.INFO)  

def lambda_handler(event, context):  
    # リクエスト内容をログ出力  
    logger.info(event)  

    ###
    # 環境変数からLINEチャネルシークレットを取得  
    channel_secret = os.environ['LINE_CHANNEL_SECRET']  
    # LINEチャネルシークレットを鍵として、HMAC-SHA256アルゴリズムを使用してリクエストボディのハッシュ値を算出  
    hash = hmac.new(channel_secret.encode('utf-8'), event['body'].encode('utf-8'), hashlib.sha256).digest()
    # ハッシュ値をBase64エンコード  
    signature = base64.b64encode(hash)

    # X-Line-Signatureを取得  
    xLineSignature = event['headers']['X-Line-Signature'].encode('utf-8')  
    # 署名の一致を検証し、不一致の場合はログ出力  
    if xLineSignature != signature:  
        logger.info('署名の不一致')  
        return {  
            'statusCode': 200,  
            'body': json.dumps('署名が正しくないみたいだよ。')  
        } 
    ###

    # 1. Webhookイベントの内容を抽出  
    body = json.loads(event['body'])  

    for event in body['events']:  
        # 応答用のメッセージオブジェクトのリストを定義  
        messages = []  
        # 2. Webhookイベントタイプがmessageであり、  
        if event['type'] == 'message':  
            # 3. メッセージタイプがtextの場合に、  
            if event['message']['type'] == 'text':  
                # 4. 受信したテキストの内容をメッセージオブジェクトとする  
                messages.append({  
                        'type': 'text',  
                        'text': event['message']['text']  
                    })  

                # 応答メッセージのリクエスト情報を定義  
                url = 'https://api.line.me/v2/bot/message/reply'  
                headers = {  
                    'Content-Type': 'application/json',  
                    # 環境変数からLINEチャネルアクセストークンを取得  
                    'Authorization': 'Bearer ' + os.environ['LINE_CHANNEL_ACCESS_TOKEN']  
                    }  
                data = {  
                    # 応答用トークンとメッセージオブジェクトを設定  
                    'replyToken': event['replyToken'],  
                    'messages': messages  
                }  
                request = urllib.request.Request(url, data = json.dumps(data).encode('utf-8'), method = 'POST', headers = headers)  
                with urllib.request.urlopen(request) as response:  
                    # レスポンス内容をログ出力  
                    logger.info(response.read().decode("utf-8"))  

    return {  
        'statusCode': 200,  
        'body': json.dumps('Hello from Lambda!')  
    }

lambdaスクリプトを更新したら、デプロイボタン(上向きの矢印アイコン)でデプロイします。

image.png

7.[AWS] Lambdaに環境変数を設定

AWSコンソールでLambdaを開き、LINE Developersで作成したチャネルの チャネルシークレットチャネルアクセストークンを環境変数として設定します。

image.png

8.[AWS] API GatewayのURL呼び出しを確認

API GatewayのURL呼び出しを確認します。

image.png

9.[LINE Developers] チャネルの設定更新

さきほど確認した API GatewayのURL呼び出し をLINE Developersで作成したチャネルのWebhook URLとして設定とWebhookの利用を有効にします。さらに、応答メッセージを無効にします。

image.png

これで『オウム返しのLINE Bot』の設定が完了です。

[LINE Bot] 動作確認

作成したチャネルをQRコードから友達登録し、オウム返しするか確認します。

image.png

このように、オウム返しをすれば成功

※補足※ [AWS] うまく動かないとき

CloudWatchのロググループでエラーが発生していないか確認するといいことあるかも

image.png

line.png

今回は、これでおわり

6
4
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
6
4