警告
記事内で利用しているライブラリ「
request
」「
request-promise
」は、非推奨(deprecated)になりました。
HTTP リクエストができる他のライブラリ(
axios
など)や、
https.requst
に書き換えることをおすすめします。
はじめに
Cisco Webex Messaging(旧称: Cisco Webex Teams)と cybozu.com の連携シリーズ第 4 弾です。
第 3 弾では、Cisco Webex Messaging の Bot を使って kintone アプリに登録されている自分のタスクを Cisco Webex Messaging に呼び出す方法を紹介しました。
第 4 弾は Cisco Webex Messaging のメンション機能をつかって、担当者を指定してタスクを kintone に登録する方法を紹介します。
似たような Tips として、Slack と kintone を連携させた
Slack から手軽に kintone へレコード登録する方法 や、
Slack-kintone 連携を Azure でもやってみた があります。
連携のしくみや動作もほとんど同じですが、本 Tips ではタスクの担当者を指定できる点がポイントです。
これまでの Cisco Webex Messaging と cybozu.com の連携シリーズはこちらです。
第 1 弾(Garoon との連携) Cisco Webex Messaging から Garoon スケジュールを予約する
第 2 弾(ユーザー連携) Cisco Webex Messaging と cybozu.com でユーザー連結を行う
第 3 弾(kintone との連携) kintone のアプリデータを Cisco Webex Messaging に投稿する方法
連携イメージ
Cisco Webex Messaging にタスク投稿用 Bot を使ってタスクを投稿すると kintone のタスク管理アプリにレコードが登録されます。
Cisco Webex Messaging のメンション機能を使って人を選択すると kintone アプリの担当者欄にメンションされた人の名前が登録されます。
また、誰にもメンションをしない場合は投稿者が担当者欄に登録されるしくみです。
連携概要
Azure fuctions(Node.js)にて、以下の処理を行う。
- Cisco Webex Messaging の Webhook から POST された投稿メッセージ、投稿者のメールアドレス、メンションされた人の Cisco Webex Messaging のユーザーID を取得する。
- Cisco Webex Messaging と cybozu.com のユーザーをマッチングする。
- kintone へのリクエストデータを作成する。
- kintone REST API を実行し、タスク管理アプリにレコードを登録する。
下準備
kintone アプリ
kintone アプリのデータを Cisco Webex Messaging に投稿する方法 で作成したアプリをそのまま使うことも可能です。
誰のタスクかがわかるシンプルなタスク管理アプリを作成します。
フィールド名 | フィールドタイプ | フィールドコード |
---|---|---|
タスク | 文字列(1行) | task |
ステータス | ラジオボタン | status |
担当者 | ユーザー選択 | responsible |
詳細 | 文字列(複数行) | detail |
cybozu.com
kintone アプリのデータを Cisco Webex Messaging に投稿する方法 で用意したユーザーを使えます。
- Cybozu.com の管理権を有するユーザーを用意する。(ユーザー情報を取得できる権限が必要)
Cisco Webex Messaging 用 Bot
- webex for Developers から MyApps を開く。
- 「Create a Bot」をクリックし、以下を参考に設定する。
項目 | 設定例 |
---|---|
Display Name | InputTask(bot) 日本語可 |
Bot Username | 任意文字列@sparkbot.io |
Icon | 任意(URL) |
kintone アプリのデータを Cisco Webex Messaging に投稿する方法 で MyApps の画面ショット付きの説明を記載しています。
Cisco Webex Messaging
- 任意のスペース(タスクを表示させるスペース)のユーザーに作成した Bot を追加する。
- 上記のスペースを利用するユーザーを 1 人以上登録する。
- 登録するユーザーのメールアドレスは、cybozu.com に登録されているメールアドレスと一致させる。 Cisco Webex Messaging と cybozu.com のユーザー連携は、メールアドレスで一致させています。
ユーザー連携の詳細は Cisco Webex Messaging と cybozu.com でユーザー連結を行う を参照してください。
環境作成
Azure Functions
Azure Functions の準備に関しては、 kintone と Microsoft Azure を連携してみよう (Azure Functions その1) の「Azure Functions の準備」欄を参考にしてください。
ここでは簡単にポイントのみ記述します。(アカウント等の準備は省略)
-
関数を作成する。
- Function App の画面からクイックスタート画面を開く。
- シナリオ選択は、「Webhook + API」を選択する。
- 言語の選択は、「JavaScript」を選択する。
-
パケットモジュールのインストールする。
-
「Function App の設定」→「Kudu に移動」を選択する。
-
「site」→作成した関数のフォルダーに移動する。
-
package.json を生成する。
-
npm コマンドを実行し、「request」「request-promise」をインストールする。
-
package.json を開いて下図のようになっているか確認する。(①、②、③)
1 2 3 4 5 6 7 8
// npmコマンド実行 D:\home\site\wwwroot\<function_name>> npm init // requestのインストール D:\home\site\wwwroot\<function_name>> npm install request --save-dev // request-promiseのインストール D:\home\site\wwwroot\<function_name>> npm install request-promise --save-dev
-
-
Node.js
-
次の JavaScrip プログラムをコピーし、作成した関数の「</>開発」のコード欄に貼り付ける。
-
「XXX」で記載されている各パラメーターをご自身の環境に合わせて記入する。
-
「保存」ボタンをクリックする。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235
/* * Cisco Webex Messaging と kintone の連携 * Copyright (c) 2017 Cybozu * * Licensed under the MIT License * https://opensource.org/license/mit/ */ (function() { 'use strict'; const request = require('request-promise'); /* Cisco Webex Messaging用のパラメータ*/ // BotのID const botID = 'XXX'; // Botの Access Token const BEARER = 'XXX'; /* kintone用のパラメータ*/ // API 実行用のユーザー(「ログイン名:パスワード」をBASE64エンコードしたもの) const CYBOZU_AUTH = 'XXX'; // cybozu.com のドメイン const DOMAIN = '{subdomain}.cybozu.com'; // アプリID const APP_ID = XXX; // URI const BASE_URL = 'https://' + DOMAIN + '/k/v1/'; // アプリのAPI Token const APITOKEN = 'XXX'; const headers = {'X-Cybozu-API-Token': APITOKEN}; let context; // Cisco Webex Messaging会議室にメッセージを投稿 function sendSpark(msg, roomid) { // 投稿する内容内容 const body_post_spark = { // "roomId": ROOMID, //会議室ID roomId: roomid, // 会議室ID text: msg // 投稿内容 }; body_post_spark.roomId = roomid; // Cisco Webex Messagingに投稿するためのオブジェクト const postspark = { url: 'https://api.ciscospark.com/v1/messages/', method: 'POST', auth: {bearer: BEARER}, 'Content-type': 'multipart/form-data', json: body_post_spark }; // 投稿を実行する return request(postspark); } // kitoneアプリ「【Cisco Webex Messaging連動】タスク管理」にタスクを登録する function setkintoneTask(task, detail, code) { // kintoneアプリに登録する内容 const body_post_kintone = { app: APP_ID, record: { // 担当者 responsible: { value: [{code: code}] }, // タスク task: { value: task }, // 詳細 detail: { value: detail } } }; // kintoneに登録するためのオブジェクト const postkintone = { url: BASE_URL + 'record.json', method: 'POST', headers: headers, 'Content-Type': 'application/json', json: body_post_kintone }; // 登録を実行する return request(postkintone).then((res) => { sendSpark('kintoneにタスクが登録されました'); context.log('kinotneに登録されました'); }); } // cybozu.com のユーザー情報を取得する function getUser(opt_offset, users) { const offset = opt_offset || 0; const objUser = users || {}; // ユーザー情報を取得するためのオブジェクト const objGetUser = { url: 'https://' + DOMAIN + '/v1/users.json', headers: {'X-Cybozu-Authorization': CYBOZU_AUTH}, method: 'GET', 'Content-Type': 'application/json' }; // ユーザー情報の取得を実行する return request(objGetUser).then((res) => { const resUser = JSON.parse(res); // 取得したユーザー情報をオブジェクトに格納する for (let i = 0; i < resUser.users.length; i += 1) { objUser[resUser.users[i].email] = {code: resUser.users[i].code, name: resUser.users[i].name}; } // 100 件取得してる場合は、offset を 100 ずらして再度ユーザー取得 if (resUser.users.length === 100) { return getUser(offset + 100, objUser); } return objUser; }); } // Cisco Webex Messaging の投稿者とメンションされた人と e-mail が一致する .com のユーザー情報を取得する function getPostingUser(email, roomid) { return getUser().then((rtnUser) => { if (!(rtnUser[email])) { throw Error('cybozu.com上に該当するユーザーが見つかりませんでした。'); } return rtnUser[email]; }); } // Cisco Webex Messagingの投稿データkintoneに登録するデータを作成する function allocation(html, email, roomid) { // taskと詳細に登録するデータの作成 // 取得したデータからtaskと詳細を抜き出す const temp = html.split('</spark-mention>'); const temp2 = temp[temp.length - 1].split('</p>')[0]; // taskと詳細に分割する const message = temp2.split('+'); const task = message[0]; const detail = message[1]; // ユーザー情報を取得する return getPostingUser(email, roomid).then((rtnUser) => { // task、detail、投稿者の.com のユーザーのcode/メンションされたユーザーの.comのcode return setkintoneTask(task, detail, rtnUser.code); }); } // メンションされたユーザーのemailを取得する function getMentionedPeopleEmail(mid) { // メンションされた人のidからemailデータを取得 const getmentionedemail = { url: 'https://api.ciscospark.com/v1/people/' + mid, method: 'GET', auth: {bearer: BEARER}, 'Content-Type': 'application/json' }; // 登録されている最初のemailを取得 return request(getmentionedemail).then((people) => { const objPeople = JSON.parse(people); return objPeople.emails[0]; }); } // Webhook を受けた際の処理 module.exports = function(ct, event) { // var objbody, ids; let objbody, ids, roomid; // context の情報をグローバル変数に保持する context = ct; context.log('start!!'); // 投稿先のroomidを保持しておく // roomid = objbody.roomid; // event.body.data.id で投稿されたメッセージの id を取得する // id を利用してメッセージの詳細を取得する const getmessage = { url: 'https://api.ciscospark.com/v1/messages/' + event.body.data.id, method: 'GET', auth: {bearer: BEARER}, 'Content-Type': 'application/json' }; // メッセージの詳細の取得を実行する return request(getmessage).then((body) => { objbody = JSON.parse(body); // メンションされたIDからBotのIDを除く ids = objbody.mentionedPeople; ids.splice(ids.indexOf(botID), 1); // 担当者欄に登録するユーザーのemailを取得する if (ids.length < 1) { // Bot以外のメンションが無い場合は、投稿者のEmailを取得 return objbody.personEmail; } // Bot以外のメンションがある場合はは、メンション先の1人目のEmailを取得 return getMentionedPeopleEmail(ids[0]); }).then((email) => { // Cisco Webex Messagingのメッセージ本文を解析し、kintoneに登録するデータを準備する return allocation(objbody.html, email, roomid); }).catch((err) => { context.log('Error: ' + err.message); }); }; })();
-
Cisco Webex Messaging Webhook の設定
- Cisco Webex for Developers(旧:Cisco Spark for Developers) から Webhook の Create a Webhook を開く。
- TestMode を「ON」にする。
- 以下の項目を入力し、「Run」をクリックする。
項目 | 設定値 |
---|---|
Authorization | Bearer 「Botのアクセストークン」 *1 |
name | 今回作成する Webhook の名前(任意) |
targetUrl | Azure Functionsの関数のURL *1 |
resource | messages(固定) |
event | created(固定) |
filter | mentionedPeople=me *1 |
*1 詳しくは kintone アプリのデータを Cisco Webex Messaging に投稿する方法 を参照してください。 ^
試してみよう
実際に Cisco Webex Messaging のタスク登録用 Bot が参加しているスペースからタスクを投稿してみましょう。
まず自分が担当するタスクの場合、「@InputTask(Bot)タスク + 詳細」のフォーマットで入力します。
「+」は区切り文字になっており、「+」の前後でタスクと詳細に分けて kintone に登録されます。
kintone アプリを確認してみましょう。
次に自分以外の誰かが担当する ToDo を登録してみましょう。
今度は Cisco Webex Messaging のメンション機能を使って「@InputTask(Bot)@ユーザータスク + 詳細」のフォーマットで入力します。
こちらも kintone アプリを確認してみましょう。
関連技術情報
Cisco Webex Messaging に投稿されたメッセージ(Bot へのメンション)を取得する: Get Message Details
cybozu.com のユーザー情報を取得する: ユーザー情報をエクスポートする
kintone アプリにレコードを登録する: 1 件のレコードを登録する
おわりに
今回は、タスクの担当が一人の場合を想定した例で説明しましたが、担当者が複数いる場合などにもチャレンジしてみてください。