マンガでわかるLINE Clova開発 第4話 Azure Functionsでバックエンドを作ろう
(アイキャッチイラスト・マンガ・解説:湊川あい)
※「サーバーレスって何?」「Azure Functionsって何?」という方は、マンガでわかるLINE Clova開発 第1話を読んでみてね!
開発環境を用意しよう
Windowsの場合
- Visual Studio Code
- .NET Core 2.1
- Node.js 8.5 以降
- Azure Functions Core Tools
- ngrok(ローカルで Clova のテストをするために使用)
Azure Functions Core Tools は、Node.js までインストールした後、次のコマンドでインストールできます。
terminal
$ npm install -g azure-functions-core-tools
macOSの場合
- Visual Studio Code
- .NET Core 2.1
- Homebrew
- Azure Functions Core Tools
- ngrok(ローカルで Clova のテストをするために使用)
Azure Functions Core Tools は、Homebrew までインストールした後、次のコマンドでインストールできます。
terminal
$ brew tap azure/functions
$ brew install azure-functions-core-tools
Visual Studio Code の設定をしよう
- C#
- Azure Functions
Azure Functionsでサポートされている言語について、詳しくはこちら:
Azure Functions でサポートされている言語 | Microsoft Docs
Visual Studio Codeに、拡張機能 C#を追加
Visual Studio Codeに、拡張機能 Azure Functionsを追加
【コラム】Visual Studio Codeのおすすめ拡張機能
- Paste Image
Ctrl+Alt+V (Cmd+Alt+V) でMarkdownにクリップボードから画像を貼り付けることができる拡張機能。Markdown書くのが捗ります。 - VS Live Share(公式紹介サイト)
複数人とコード共有して作業できるようになる拡張機能です。 - VS Live Share Extension Pack
Live Share するときに、チャットやボイスチャットができるようになる拡張機能です。 - EditorConfig for VS Code
EditorConfig のVisual Studio Code用の拡張機能です。チームでコーディングスタイルを共有するのに役立ちます。 - GitLens
Git のリポジトリのブランチやリモートや履歴などを確認するのに便利です。 - GitHub Pull Requests
2019年1月22日時点でプレビューですがVisual Studio CodeからGitHubのプルリクエストを見たり編集したり作成したりできてすごく便利です。
コードを書こう
1. 新規プロジェクトを作ろう
▼作業用のフォルダを作り、Visual Studio Codeで開きます。画面左にあるAzureのアイコンをクリックします。
Sign in to AzureをクリックしてAzureにログインします。
(画面左のアイコンが見当たらない場合は、Visual Studio Codeを再起動してみてください)
▼ブラウザが開くので、Azureに登録済みの自分のメールアドレスを入力します。このような画面になればログイン完了です。
▼FunctionsのCreate New Project... (フォルダのアイコン)をクリックします。
▼今開いている作業用のフォルダを選択します
▼続いて、使う言語を選びます。今回はC#を選択します。
▼以上で、新規プロジェクトができました。先ほど選択したフォルダの中身を見てみましょう。
2. 関数を作ろう
プロジェクトができたので、続いて関数を作成していきます。
▼Create Function (稲妻のアイコン)をクリックします。
▼先ほど作成したプロジェクトのフォルダを選択します。
▼HttpTrigger を選択します。
▼関数名を入力します。今回はClovaとしました。
▼関数の名前空間を入力します。今回はMangaClovaとしました。
▼認証方法はFunctionを選択します。
▼数秒後、Clova.cs が作成されます!
3. ライブラリを追加しよう
コードの編集に入る前に、Clova の Extension(スキル)を作るための CEK.CSharp というライブラリを追加しておきましょう。
C# のライブラリは NuGet でホストされています。
ライブラリを追加するにはdotnet add package コマンドを使います。
Visual Studio Code のターミナルを開いて、次のコマンドを入力しましょう。
terminal
$ dotnet add package CEK.CSharp
※ Visual Studio Code上のターミナルの開き方
上部メニューの View > Terminal から開けます。
試しにビルドしてみましょう。
Ctrl + Shift + B でビルドします。(macOSの場合は ⌘ + Shift + B)
「ビルドに成功しました」と表示され、エラーが出ないことを確認します。
4. Clova.cs の中のRunメソッドを書こう
Clova.csの中のRunメソッドを書いていきます。
元々のコード
C#
using System;
using System.IO;
using System.Threading.Tasks;
using Microsoft.AspNetCore.Mvc;
using Microsoft.Azure.WebJobs;
using Microsoft.Azure.WebJobs.Extensions.Http;
using Microsoft.AspNetCore.Http;
using Microsoft.Extensions.Logging;
using Newtonsoft.Json;
namespace MangaClova
{
public static class Clova
{
[FunctionName("Clova")]
public static async Task Run(
[HttpTrigger(AuthorizationLevel.Function, "get", "post", Route = null)] HttpRequest req,
ILogger log)
{
// ここに実行したい処理を書く
}
}
}
▼例:まだ using namespace していないクラスを使うとき
(JavaScript でいうところの、importしていないクラスを使うとき)
① クラス名を打つ
② Ctrl + . を入力
③ using namespace を追加する選択肢が出るので選択
・・・(この例では、先ほど追加したライブラリ CEK.CSharp
が候補に表示されている)
④ コード上部に using namespace; が追加される
・・・(この例では、using CEK.CSharp;
)
何が来ても「こんにちは」を返す関数
C#
using System;
using System.IO;
using System.Threading.Tasks;
using Microsoft.AspNetCore.Mvc;
using Microsoft.Azure.WebJobs;
using Microsoft.Azure.WebJobs.Extensions.Http;
using Microsoft.AspNetCore.Http;
using Microsoft.Extensions.Logging;
using Newtonsoft.Json;
using CEK.CSharp;
using CEK.CSharp.Models;
namespace MangaClova
{
public static class Clova
{
[FunctionName("Clova")]
public static async Task Run(
[HttpTrigger(AuthorizationLevel.Function, "get", "post", Route = null)] HttpRequest req,
ILogger log)
{
// リクエストのボディの JSON を検証して C# のクラスに変換。
var clovaClient = new ClovaClient();
var clovaRequest = await clovaClient.GetRequest(req.Headers["SignatureCEK"], req.Body);
// 返事を作成
var clovaResponse = new CEKResponse();
clovaResponse.AddText("こんにちは。");
// レスポンスとして作成した返事の内容を返す
return new OkObjectResult(clovaResponse);
}
}
}
5. デバッグを実行
コードを実行してみましょう。
画面左のメニューからデバッグを選択し、緑の三角形をクリックして実行します。
6. ngrokを使ってインターネットからアクセスできるようにしよう
ngrok を使ってインターネットからアクセスできるようにします。VSCode のターミナルで新しいターミナルを開いて、次のコマンドを実行します。
terminal
$ ngrok http 7071
※ ngrok: command not found になった場合・・・ローカルでngrokを参照できていない可能性があります。たとえばngrokをアプリケーションフォルダに保存した場合は $ cd /Applications
してから $ ./ngrok http 7071
してみてください。
成功すると、ターミナル上にこのように表示されます。
https://b71XXXXX.ngrok.io
というURLがあるはずです。今からこのURLをClova Extension Kitに登録します。
ブラウザで Clova Extension Kit を開きましょう。スキルの基本情報 > 修正 > サーバ―設定 の、WebhookのURLを入れるところに ngrokで表示されたURL + /api/Clovaを入力します。
例:https://b71XXXXX.ngrok.io/api/Clova
では、Clova Extension Kitの対話モデルのテスト機能で話しかけてみましょう。
▼テストしてみた様子
◆おみくじ機能を追加しよう
C#
using System;
using System.IO;
using System.Threading.Tasks;
using Microsoft.AspNetCore.Mvc;
using Microsoft.Azure.WebJobs;
using Microsoft.Azure.WebJobs.Extensions.Http;
using Microsoft.AspNetCore.Http;
using Microsoft.Extensions.Logging;
using Newtonsoft.Json;
using CEK.CSharp;
using CEK.CSharp.Models;
namespace MangaClova
{
public static class Clova
{
[FunctionName("Clova")]
public static async Task Run(
[HttpTrigger(AuthorizationLevel.Function, "get", "post", Route = null)] HttpRequest req,
ILogger log)
{
// リクエストのボディの JSON を検証して C# のクラスに変換。
var clovaClient = new ClovaClient();
var clovaRequest = await clovaClient.GetRequest(req.Headers["SignatureCEK"], req.Body);
// 返事を作成
var clovaResponse = new CEKResponse();
switch (clovaRequest.Request.Type)
{
case RequestType.LaunchRequest:
// 起動時の処理
clovaResponse.AddText("こんにちは。何を占ってほしいですか?");
clovaResponse.AddText("健康運と恋愛運と金運を占えるよ。");
clovaResponse.AddText("例えば健康運を占ってって聞いてみてね。");
clovaResponse.ShouldEndSession = false; // スキルを終わらせないように設定する
break;
case RequestType.SessionEndedRequest:
// 終了時の処理。スキルが終了したときに何かしたい時は、ここに処理を追加します
break;
case RequestType.IntentRequest:
// インテントの処理
switch (clovaRequest.Request.Intent.Name)
{
case "FortuneTellingIntent":
// 占いのインテント
// 占い対象がスロットに無い場合は総合運勢を占う
var fortune = "総合運勢";
if (clovaRequest.Request.Intent.Slots.TryGetValue("FortuneSlot", out var fortuneSlot))
{
// 占いの対象がある場合は、それをスロットから取得する
fortune = fortuneSlot.Value;
}
// 占いの結果を返す
var result = new[]{ "大吉", "中吉", "小吉", "末吉" }[new Random().Next(4)];
clovaResponse.AddText($"{fortune} は {result} です。");
break;
default:
// 認識できなかったインテント
clovaResponse.AddText("ごめんなさい。よくわかりませんでした。例えば健康運を占ってと言うと健康運を占います。");
clovaResponse.ShouldEndSession = false; // スキルを終わらせないように設定する
break;
}
break;
}
// レスポンスとして作成した返事の内容を返す
return new OkObjectResult(clovaResponse);
}
}
}
コードを保存したらデバッグを実行してください。 これで話しかけると、毎回違った結果が返ってくるようになります。
デプロイしよう
1. Azureにデプロイしよう
テストしてみて正常に動いたので、いよいよ本番環境にデプロイしてみましょう。
▼Visual Studio Codeの左側にあるAzureのアイコンをクリックし、Deploy to Function App...(上向き矢印のアイコン)をクリックします。
▼Create New Function App を選択します。
Function App の名前の入力を求められます。URL に使われるので世界中で一意である必要があります。使える文字は、a-z
、0-9
、-
です。
▼リソースグループを作成します。Create new resource group を選択します。 リソースグループとは、Azure 上の作成するアプリや DB をひとまとめにして管理するフォルダのようなものです。
▼リソースグループ名を入力します。
▼Azure Functions が内部で使うストレージを作ります。Create new storage account を選択します。
▼ストレージアカウント名を入れます。これも世界中で一意の名前である必要があります。
▼続けてリージョンを選択します。日本はJapan WestとJapan Eastがあります。
▼リージョンを選択するとデプロイが始まります。画面右下にポップアップが表示されます。
▼出力ウィンドウ(OUTPUTウィンドウ)でAzure Functionsを選択するとデプロイの状況が確認できます。
▼デプロイが完了するとVisual Studio CodeのAzure Functions拡張機能から関数(Functions)が確認できます。
▼関数Clovaを右クリックして関数のURLをコピーします。
▼このURLを Clova Extension Kitの スキルの基本情報 > 修正 > サーバ設定 に設定することで、Azure FunctionsでLINE Clovaのスキルが動くようになります!
▼無事、Azure Functionsを介して返答が返ってきました。
▼ちなみに、ブラウザから Azureポータルを確認してみると、デプロイできているのが確認できます。
※ 本記事は2019年1月作成時点での情報です。
次回、第5話へ続く
- 第1話:Clova開発の全体像・サーバーレスって何?
- 第2話:スキルの基本情報を登録しよう
- 第3話:対話モデルを作ろう
- 第4話:バックエンドをつくろう(本記事) ←今ココ!
- 第5話:実機で動かしてみよう
- 第6話:審査に出して公開してみよう
- 第7話:Clovaのスキルをもっとリッチにしてみよう
マンガ・解説: 湊川あい
他にもある「わかばちゃんと学ぶ」シリーズ
マンガと図解で技術がわかる「わかばちゃんと学ぶ」シリーズ。
全国の書店・Amazonで発売中です。
著者プロフィール
湊川あい
絵を描くWebデザイナー。高等学校教諭免許状 “情報科” 取得済。マンガと図解の力で、物事をわかりやすく伝えることが好き。2014年より「マンガでわかるWebデザイン」をインターネット上に公開していたところ、出版社より声がかかる。
Twitter: @llminatoll
Webサイト: マンガでわかるWebデザイン
ちょまど(千代田まどか)
エンジニア兼マンガ家。Microsoft 社のソフトウェアエンジニアとしての本業のかたわら、マンガ家やイラストレーター、松屋エバンジェリスト(非公式)としても活動。MS入社前から Twitter 廃人であり、フォロワーは4万人を超える。
Twitter: @chomado
ホームページ: http://chomado.com/