2
2

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 3 years have passed since last update.

Azure Static Web AppsのAPI作成でLINE BOTを作る

Posted at

前に書いた記事でAzure Static Web Appsを簡単に試してみましたが、後半の手順でAPIの作成も出来ました。

参考: たぶん10分で試せる。Azure Static Web AppsにWebサイトをデプロイして独自ドメイン設定とFunctionsでAPI公開まで

今回はこれを使ってLINE BOTを作ってみようと思います。

ちなみにStatic Web AppsのAPIの中身はAzure Functionsになる模様です。

参考: Azure Functions による Azure Static Web Apps プレビューでの API のサポート

環境

  • macOS Catalina
  • Node.js v12系

現状だとローカル実行やAzure FunctionsがNode.js v12までしか対応してなさそうでした。

APIエンドポイントを作ってみる(おさらい)

こんな手順です。

  • まずは参考記事をもとに、Azure Static Web Appで静的サイトを作成してみる
  • apiフォルダを作成し、さらにlinebotフォルダを作成
  • linebotフォルダ内にindex.jsfunction.jsonを作成
index.js
module.exports = async function (context, req) {
    context.res = {
       body: { 
         text: "Hello from the API" 
       }
    };
  };
function.json
{
    "bindings": [
      {
        "authLevel": "anonymous",
        "type": "httpTrigger",
        "direction": "in",
        "name": "req",
        "methods": [
          "get"
        ],
        "route": "linebot"
      },
      {
        "type": "http",
        "direction": "out",
        "name": "res"
      }
    ]
  }

この状態でプッシュしてしばらくするとAPIが有効になります。

https://<APP ID>.azurestaticapps.net/api/linebotにアクセスするとAPIが見えます。

ローカル実行まで

まずはローカルで実行できる環境を整えます。

Azure Functionsの拡張機能のインストールと設定

VScodeにAzure Functionsの拡張機能をインストールします。

インストールが完了するとAzureマークがVSCodeのサイドバーに表示されます。選択するとサインインしましょう的なボタンがあるのでサインインします。

サインインすると少し読み込み待ち

Create New Project...のボタンを選択し、Browseを選択。

作成したapiフォルダを選択

言語選択でJavaScriptを選択

スクリーンショット 2020-08-17 1.27.33.png

テンプレート選択でHTTP triggerを選択

スクリーンショット 2020-08-17 1.27.28.png

関数名をwebhookとし、承認レベルをanonymousにします。

こんな感じでapiフォルダ内にwebhookフォルダやその他ファイルが作成されます。

Azure Functions拡張機能のタブに戻るとこのような表示になっています。

core toolsでローカル実行

Azure Functions Core Toolsというツールを使ってローカル実行をする模様です。

VScodeのコマンドパレットを開き(macだとcommand+shift+p)、core toolsと入力しインストールします。

スクリーンショット 2020-08-17 1.43.35.png

バージョン選択ですが、レコメンドされてるのでAzure Functions v3を選択します。

スクリーンショット 2020-08-17 1.43.44.png

しばらくするとインストールが完了します。

VSCodeのメニューのRun > Start Debuggingを選択するとローカルサーバーが起動します。

スクリーンショット 2020-08-17 1.55.28.png

ちなみに、このときにNode.js v14を利用してたらエラーが出ました。執筆時点ではv12までの対応らしいのでv12に切り替えたらうまく行きました。

ターミナルではこんな感じで作成したwebhooklinebotのエンドポイントが有効になったような表示になります。

ブラウザでアクセスしてみるとちゃんと表示されました。

LINE BOTプログラムの作成

現状だとルートディレクトリにapiフォルダindex.htmlがありますが、apiフォルダ内にpackage.jsonがあるのでそこでnpm installを実行していきます。

  • ルートからapiフォルダへ
$ ls
api        index.html
$ cd api
$ ls
host.json           local.settings.json package.json        webhook
linebot             package-lock.json   proxies.json
  • apiフォルダでモジュールのインストール
npm i @line/bot-sdk express azure-function-express

通常だとAzure Functionsのお作法で書く必要がありますが、azure-function-expressを利用することで、Azure Functionsっぽい書き方に依存せずに通常のexpressの利用っぽい雰囲気で書くことが出来ます。ひらりんさんの記事が参考になりました!

参考: LINE Bot を Azure Functions (Node.js) で作る際のオウム返しテンプレ

  • api/webhook/index.jsにコードを記述

'use strict';

const line = require('@line/bot-sdk');
const createHandler = require("azure-function-express").createHandler;
const express = require('express');

const config = {
    channelSecret: '作成したBOTのチャンネルシークレット',
    channelAccessToken: '作成したBOTのチャンネルアクセストークン'
};

const app = express();

app.get('/api/webhook', (req, res) => res.send('Hello LINE BOT!(GET)')); //ブラウザ確認用(無くても問題ない)
app.post('/api/webhook', line.middleware(config), (req, res) => {
    console.log(req.body.events);

    //ここのif分はdeveloper consoleの"接続確認"用なので削除して問題ないです。
    if(req.body.events[0].replyToken === '00000000000000000000000000000000' && req.body.events[1].replyToken === 'ffffffffffffffffffffffffffffffff'){
        res.send('Hello LINE BOT!(POST)');
        console.log('疎通確認用');
        return;
    }

    Promise
      .all(req.body.events.map(handleEvent))
      .then((result) => res.json(result));
});

const client = new line.Client(config);

async function handleEvent(event) {
  if (event.type !== 'message' || event.message.type !== 'text') {
    return Promise.resolve(null);
  }

  return client.replyMessage(event.replyToken, {
    type: 'text',
    text: event.message.text //実際に返信の言葉を入れる箇所
  });
}

module.exports = createHandler(app);

大元はこちらの1時間でLINE BOTを作るハンズオンの記事のコードになっています。

参考記事をもとにLINE BOTのチャンネルシークレットとアクセストークンもコードに記載しておきます。

参考: 1時間でLINE BOTを作るハンズオン

おうむ返し

ngrokでトンネリングして試してみましょう。

コードが出来たら先ほどと同様にRun > Start Debuggingでローカルサーバーを起動させます。

今回(デフォ?)7071ポートで起動したのでngrokで7071ポートにトンネリングさせます。

$ npx ngrok http 7071

これは別のターミナルで実行しておいた方が良いと思います。

こんな感じでhttps://35027c542caa.ngrok.ioというURLが発行されました。

このURLを使ってLINE DevelopersでWebhook URLの設定を行います。

今回はエンドポイントが/api/webhookになっているので、この場合はhttps://35027c542caa.ngrok.io/api/webhookとなります。

この状態(ローカルサーバー起動中 + ngrok起動中 + Webhook URL登録済)でLINE BOTに話しかけると無事におうむ返しをしてくれました。

ひとまずローカルで実行できて一安心。。

デプロイして永続化する

デプロイは簡単で、もともとGitHub連携ありきでAzure Static Web Appsを作っているのでローカルで作ったものをプッシュすればOKです。

裏側でGitHub Actionsでビルドされる模様なので少し待ちましょう。

しばらくするとポータルの画面にもwebhook関数が表示されます。

https://<APP ID>.azurestaticapps.net/api/webhookにブラウザでアクセスするとHello LINE BOT!の表示が見えるようになると思います。

最終的にこのアドレスをLINE BOTの管理画面からWebhook URLに登録します。

これでデプロイも完了し永続化まで出来ました。

念のため最後におうむ返しがちゃんと動くか確認しましょう。

おまけ 環境変数の利用

ソースコードのチャンネルシークレットチャンネルアクセストークンをコードに直書きしてましたが環境変数置き換えも出来ます。

//省略

const config = {
    channelSecret: process.env.CHANNEL_SECRET,
    channelAccessToken: process.env.CHANNEL_ACCESS_TOKEN,
};

//省略

ポータルの構成の箇所から環境変数の追加ができます。

パスワードやトークンはここを活用すると良さそうです。

最後にチェックをして保存を押すことで保存されるのですが、これを忘れると値が保存されないので注意です。

まとめと所感

Static Web AppsでLINE BOTを作成することが出来ました。

当たり前ですがMSエコシステムということでVSCodeを使わないと厳しいかもしれないですね。
この辺は趣味趣向ありそうです。

内部はAzure Functionsを使ってるっぽいですが、Azure Functionsのリソースは一個も作っていないので金額とかは特に発生せずに使えてるのかな......

Static Web Appsの管理画面がシンプルすぎて稼働状況もいまいちわからないですが、とりあえずしばらく稼働させてみます。

2
2
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
2
2

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?