MENU

AWS SAM CLI+Messaging API+localtunnelでLINEBot開発が捗った。

こんにちはこんばんは!佐々木です!

プライベートでLINEBot開発に取り組んでみようとしたところ、「AWS SAM CLI」が便利だよ。ということで使ってみたところ、めちゃくちゃ捗どりました!
また、ローカル環境で「MessagingAPI」を検証する際に「localtunnel」を使うとURLが固定できたりともろもろ楽出来たので、今回は僕が使用したサービスの簡単なご紹介とオウム返しBotを作ってローカル環境で検証するところまで書いていこうと思います!

目次

AWS SAM (AWS Serverless Application Model ) とAWS SAM CLI

AWS Serverless Application Model (AWS SAM) は、AWS でサーバーレスアプリケーションを構築するために使用できるオープンソースのフレームワークです。
AWS SAM CLI は、AWS SAM テンプレートおよびアプリケーションコードで動作するコマンドラインツールです。AWS SAM CLI では、ローカルでの Lambda 関数の呼び出し、サーバーレスアプリケーションのデプロイパッケージの作成、サーバーレスアプリケーションの AWS クラウドへのデプロイなどを行うことができます。

https://docs.aws.amazon.com/serverless-application-model/index.html

環境構築から開発、テスト、デプロイがガンガン進められるのでめちゃくちゃ楽です!(逐一アップロードなどやってられry、、

あわせて読みたい
AWS Serverless Application Model (AWS SAM) とは何ですか? - AWS Serverless Application Model AWS Serverless Application Model (AWS SAM) を使用してサーバーレスアプリケーションを構築する方法について説明します。

Messaging API

国内利用者数8900万人超えのSNS、LINEが提供するAPIの一つです。

LINEからは様々なAPIを提供しており、ボット開発やLINEログイン・決済機能と用途は多岐にわたるため、興味があればぜひご利用してみてはいかがでしょうか!

あわせて読みたい
LINE Developers LINE Developersサイトは開発者向けのポータルサイトです。LINEプラットフォームのさまざまな開発者向けプロダクトを利用するための、管理ツールやドキュメントを利用でき...

localtunnel

開発用に利用するローカルサーバをHTTPSとして外部サービスから連携させたりする際に、
ngrok」をよく耳にしますが、無料アカウントだと少し手間がかかる面がありました。

ngrok」は無料アカウントだと、ドメイン指定ができないため、起動のたびにurlがランダムに変更されてしまいます。

それはちょっとなぁ、、ということで今回は「localtunnel」を利用しました!
こちらは、サブドメインが固定できるので起動のたびにWebHookのURLを変えずに済むので重宝しました。

GitHub
GitHub - localtunnel/localtunnel: expose yourself expose yourself. Contribute to localtunnel/localtunnel development by creating an account on GitHub.
【ご注意】

インターネット上にローカルマシンのリソースが公開されますので、ご利用する際はよくご検討ください。
また、開発が終わったら確実にサーバを落として、不用意に公開し続けないようにご注意ください。

事前準備ツール

始める前に以下のツールをインストールしておきましょう!(けっこう多いです)また、Dockerはデバッグなどを実行する際に起動している必要があるので、忘れずに起動しておきましょう!

  • Docker
  • AWS CLI
  • AWS SAM CLI
  • npm ※5.2.0以降

事前登録

環境構築

最初に「sam init」を入力すると対話型で環境構築を進めていくことになります。今回はGoを選択して作成します。(理由は僕がGo好きだからです)

sum init
▶ sam init
Which template source would you like to use?
	1 - AWS Quick Start Templates
	2 - Custom Template Location
Choice: 1 ## 1を選択
What package type would you like to use?
	1 - Zip (artifact is a zip uploaded to S3)
	2 - Image (artifact is an image uploaded to an ECR image repository)
Package type: 1 <meta charset="utf-8">## 1を選択

Which runtime would you like to use?
	1 - nodejs14.x
	2 - python3.9
	3 - ruby2.7
	4 - go1.x
	5 - java11
	6 - dotnetcore3.1
	7 - nodejs12.x
	8 - nodejs10.x
	9 - python3.8
	10 - python3.7
	11 - python3.6
	12 - python2.7
	13 - ruby2.5
	14 - java8.al2
	15 - java8
	16 - dotnetcore2.1
Runtime: 4 <meta charset="utf-8">## 4を選択

Project name [sam-app]: sample<meta charset="utf-8">## 任意の名前を入力

Cloning from https://github.com/aws/aws-sam-cli-app-templates

AWS quick start application templates:
	1 - Hello World Example
	2 - Step Functions Sample App (Stock Trader)
Template selection: 1 <meta charset="utf-8">## 1を選択

    -----------------------
    Generating application:
    -----------------------
    Name: sample
    Runtime: go1.x
    Architectures: x86_64
    Dependency Manager: mod
    Application Template: hello-world
    Output Directory: .

    Next application steps can be found in the README file at ./sample/README.md


    Commands you can use next
    =========================
    [*] Create pipeline: cd sample && sam pipeline init --bootstrap
<meta charset="utf-8">▶ tree .
.
└── sample
    ├── Makefile
    ├── README.md
    ├── hello-world
    │   ├── go.mod
    │   ├── go.sum
    │   ├── main.go
    │   └── main_test.go
    └── template.yaml

上記のようにプロジェクトが作成されました。続けてbuildします。

cd sample/ && make

makeファイルには「sam build」が記載されているため、上記のコマンドでビルドされます。
ビルド後は、デプロイ用のアーティファクトが作成されます(青字部)。

<meta charset="utf-8">▶ tree . -a
.
└── sample
<span class="bold-blue">    ├── .aws-sam
    │   ├── build
    │   │   ├── HelloWorldFunction
    │   │   │   └── hello-world
    │   │   └── template.yaml
    │   └── build.toml</span>
    ├── Makefile
    ├── README.md
    ├── hello-world
    │   ├── go.mod
    │   ├── go.sum
    │   ├── main.go
    │   └── main_test.go
    └── template.yaml

build後は以下のコマンドでlambda関数を起動できます。

sam local invoke

または、以下のコマンドでAPI呼び出しを含めたアプリケーション全体のテストができます。

sam local start-api

この際にhttp://127.0.0.1:3000/にアクセスすると“Hello {使用しているIPアドレス}”が確認できます。

修正・追加

では、前述で作成している内容をLINEBot用に修正・追加していきます(赤字部)。
デプロイ用のアーティファクト(青字部)は再度buildを実行すると作り直されます。
修正後のコードなどは以下を参考にしてください。

GitHub
GitHub - daisuke8000/sample-sam-go Contribute to daisuke8000/sample-sam-go development by creating an account on GitHub.
▶ tree . -a
.
└── sample
<span class="bold-blue">    ├── .aws-sam
    │   ├── build
    │   │   ├── LineBotFunction
    │   │   │   └── line-bot
    │   │   └── template.yaml
    │   └── build.toml</span>
    ├── Makefile
    ├── README.md
    ├── <span class="bold-red">env.json</span>
    ├── <span class="bold-red">line-bot</span>
    │   ├── go.mod
    │   ├── go.sum
    │   ├── <span class="bold-red">main.go</span>
    │   └── main_test.go
    └── <span class="bold-red">template.yaml</span>

中のコードはさておき、重要なのがtemplate.yamlになります。(ここの理解で2日使った、、)
意識しておいたほうが良さそうなところはコメントを入れています。

<meta charset="utf-8">▶ template.yaml
<span class="bold-green">## SAM テンプレートヘッダー(ここにテンプレートのバージョンや説明を書く)</span>
AWSTemplateFormatVersion: '2010-09-09'
Transform: AWS::Serverless-2016-10-31
Description: >
  sample
  
  Sample SAM Template for sample


Globals:
  Function:
    Timeout: 5

<span class="bold-green">## SAM テンプレートリソース(デプロイするリソースの詳細を定義する)</span>
Resources:
  LineBotFunction:
    <span class="bold-red">Type: AWS::Serverless::Function</span> <span class="bold-green">## lambdaを指す。他にもAPI GW,DynamoDB等を指定可。</span>
    Properties:
<span class="bold">      </span><span class="bold-red">CodeUri: line-bot/</span><span class="bold"> <meta charset="utf-8"><span class="bold-green">## <meta charset="utf-8"><span class="bold-green">Lambda関数</span></span></span><span class="bold-green">に<span class="bold">デ</span></span><span class="bold"><span class="bold-green">プロイするコードの場所を指定</span>
      <span class="bold-red">Handler: line-bot </span> </span><span class="bold-green">##</span> <span class="bold-green">Lambda関数のハンドラを指定</span>
      Runtime: go1.x
      Architectures:
        - x86_64
      Tracing: Active
      <span class="bold-red">Events:</span> <meta charset="utf-8"><span class="bold-green">##</span> <span class="bold-green">Lambda関数のトリガーをEvents以下に記載</span>
        CatchAll:
          <span class="bold-red">Type: Api</span> <span class="bold-green">## AWSのどのサービスをイベントソースにするか指定。(この場合はAPI GW)</span>
          Properties:
            <span class="bold-red">Path: /parrot</span> <span class="bold-green">## 実行されるAPI GWのパス</span>
            <span class="bold-red">Method: POST</span> <meta charset="utf-8"> <span class="bold-green">## 実行されるAPI GWのメソッド</span>
      Environment:
        Variables:
          <span class="bold-green">## 以下は<meta charset="utf-8">env.jsonで環境変数を設定・読込を行う。</span>
          <span class="bold-red">LINE_CHANNEL_SECRET: LineChannelSecret</span>
          <span class="bold-red">LINE_CHANNEL_ACCESS_TOKEN: LineChannelAccessToken</span>

<span class="bold-red">Outputs:</span> <span class="bold-green">## SAMによって作成されるものの定義</span>
  LineBotFunctionAPI:
    Description: "API Gateway endpoint URL for Prod environment for LineBotFunction"
    Value: !Sub "https://${ServerlessRestApi}.execute-api.${AWS::Region}.amazonaws.com/Prod/parrot/"
  LineBotFunction:
    Description: "LineBotFunction ARN"
    Value: !GetAtt LineBotFunction.Arn
  LineBotFunctionIamRole:
    Description: "Implicit IAM Role created for LineBotFunction"
    Value: !GetAtt LineBotFunctionRole.Arn

コメントにも記載していますが、事前に用意しているMessaging APIで取得出来る「Channel secret」と「Channel access token」はハードコーディングさせたくないので環境変数として扱い、env.jsonから取得させます。以下のように記載することで環境変数として読み込めるようになります。

<meta charset="utf-8">▶ env.json
{
  "Parameters": {
    "LINE_CHANNEL_SECRET": <span class="bold-red">"xxxxxxxxxx"</span>, <span class="bold-green">## ここに<meta charset="utf-8">Channelsecret</span>
    "LINE_CHANNEL_ACCESS_TOKEN": <span class="bold-red">"yyyyyyyyyy"</span> <span class="bold-green">## <meta charset="utf-8">ここに<meta charset="utf-8">Channelaccess token</span>
  }
}

localtunnelのインストール、外部公開

localtunnelを以下のコマンドでインストールします。

npm i -D localtunnel

次にsamを起動しておきます。修正後に再度buildした後、以下コマンドを実行します。(必ず、sam→localtunnelの順に起動してください)

sam local start-api --env-vars env.json
<meta charset="utf-8"><span class="bold-green">Mounting LineBotFunction at http://127.0.0.1:3000/parrot [POST]</span>

続けて使用しているポート番号を指定してlocaltunnelを起動します。
この際に「–subdomain」オプションを指定することで同一のURLを使うことができます(ただし、他に同じサブドメインを使用している人がいた場合はそちらにURLが払い出されるため使用できません)。

npx lt --port 3000 --subdomain <span class="bold-red">zzzzzzzzz</span>
<span class="bold-green">your url is: https://xxxxx-yyyy-99.loca.lt</span>

MessagingAPI Webhook URLに設定

Webhook URLに「外部公開されているURL」+「/parrot」を入力して登録します!
「Use webhook」をONにするのもお忘れなく、、

以下のように確認できたら成功です!挙動が確認できればどんどん開発すすめていけますね!
AWS SAM CLI めっちゃ便利なのでぜひ皆さん使ってみてくださいね!٩(ˊᗜˋ*)و

よかったらシェアしてね!
  • URLをコピーしました!
  • URLをコピーしました!

この記事を書いた人

miracleaveはワクワクする最高のITサービスをユーザーに提供するテクノロジー集団です。
「ITでワクワクできる未来へ」をミッションに掲げ、楽しいを創り出す組織から、お客様に感動を与えるようなサービスを届けること、そして、新たな挑戦をする人をデジタルコンテンツの力で後押し、幸せな未来を作っていきたいと考えています。

目次