仕事から帰る前に、LINEで「今から帰りまーす」とメッセージを送るが、嫁が気づかないことが多いため、Google Homeにメッセージを読み上げてもらうことにしました。
全体像
-
LINEのMessaging APIにある、メッセージ受信(など)した時、指定URLに通知するwebhook機能
-
Google Homeに好きな言葉をしゃべらせるgoogle-home-notifier
を使い、自宅にhttpサーバを起動しておき、LINE@のアカウントからPOSTされたら、google-home-notifierを使ってGoogle Homeにしゃべってもらう。
家のGlobal IPはちょくちょく変わってしまうので、ngrokを使用してURLを公開。
LINE Channelの作成
-
LINE developers で「Messaging API(ボット)をはじめる」を選択し、新規Channelを作成
-
作成したLINE Channelの設定画面で、以下を設定
- Webhook設定を「利用する」
- Webhook URLを、自宅サーバのURL(後ででてくるngrokで生成したURL)
これで、作成したChannelのIDにメッセージを送信すると、webhookイベントが指定したURLに通知されるようになる。
HTTPサーバ準備
Node.js, npmが動作する環境が前提
Install ngrok
ngrokは、localhostをXXXXXXXX.ngrok.comで、外部からアクセス可能にするサービス。
localで作成した環境をサクッと外部に公開できる。
-
https://ngrok.comからdownload
-
downloadした
ngrok
をpathの通った場所に格納
# copy to Applications directory
$ mv ngrok /Applications/
# cd into your local bin directory
$ cd /usr/local/bin
# create symlink
$ ln -s /Applications/ngrok ngrok
Install google-home-notifier
google-home-notifierは、JavaScriptでGoogleHomeに発話させることができるライブラリ。
$ npm install google-home-notifier
ref : Github - Send notifications to Google Home
httpサーバソース
webhook eventはJSON形式で通知され、メッセージ受信時は、
-
events[0].type
に、"message" -
events[0].message.text
に、メッセージ本文 -
events[0].source.userId
に、送信者のUserId
が入る
他のformatは、Messaging API - Webhookイベントオブジェクト参照
const config = require('./config/default.json');
// for http server
const http = require('http');
// for googlehome
const googlehome = require('google-home-notifier');
const language = 'ja';
function googlehome_init() {
googlehome.device(config.googlehome_name, language);
googlehome.ip(config.googlehome_ip, language);
}
function googlehome_speak(text) {
googlehome.notify(text, function (res) {
console.log('googlehome_res : ' + res + ' speech_text : ' + text);
});
}
// main()
googlehome_init();
http.createServer(function (request, response) {
let post_data = '';
request.on('data', function (chunk) {
post_data += chunk;
});
request.on('end', function () {
console.log('post_data : ' + post_data);
const webhook = JSON.parse(post_data).events[0];
if (webhook.type != 'message' || webhook.message.type != 'text') {
return;
}
// 特定の人からのメッセージのみ発話
if (config.speakable_userid == '' || webhook.source.userId == config.speakable_userid) {
const data_text = webhook.message.text;
googlehome_speak(config.beginning_sentence + data_text);
}
response.writeHead(200, { 'Content-Type': 'text/plain' });
response.end();
});
}).listen(config.server_port);
config/default.jsonの
-
server_port
は、webhookのeventを受け取るport。ngrok使用時に指定するport番号とする -
googlehome_ip
に、GoogleHomeのIPアドレス -
googlehome_name
は、GoogleHomeのDeviceNameだが、設定しなくても大丈夫かも -
beginning_sentence
に、メッセージの冒頭に発話したい文を記載(「メッセージが届きました。${メッセージ本文}」) -
speakable_userid
は、特定Userからのメッセージのみ発話させたい場合に記載。空白の場合、誰のメッセージでも発話。UserIdは一度メッセージを受信させ、webhook eventの、source.userId
を見て確認
{
"server_port": "8080",
"googlehome_ip": "192.168.XX.XX",
"googlehome_name": "device name of google home",
"beginning_sentence": "メッセージが届きました。",
"speakable_userid": ""
}
HTTPサーバ起動
start ngrok
# create symlink. default.jsonで指定したportとする。
$ ngrok http 8080
# 起動すると、下記の様な画面が表示される。
# https://XXXXXXXX.ngrok.ioを、LINE Channel設定の webhook URLに設定。
ngrok by @inconshreveable
(Ctrl+C to quit)
Session Status online
Version 2.2.8
Region United States (us)
Web Interface http://127.0.0.1:4040
Forwarding http://XXXXXXXX.ngrok.io -> localhost:8080
Forwarding https://XXXXXXXX.ngrok.io -> localhost:8080
run http_server
$ node server_for_line.js
# LINE message受信すると、下記のようなログが出力される。
# "userId"が、送信者のuserId。
post_data : {"events":[{"type":"message","replyToken":"0f3a5cccea3543f89f502345eb3df90","source":{"userId":"Uxxxxxxxxxxxxxxxxxxxxxxxxx","type":"user"},"timestamp":1515074416236,"message":{"type":"text","id":"7256796266214","text":"メッセージ本文"}}]}
動作
-
作成したLINE Channelのアカウントにメッセージを送り、GoogleHomeがしゃべればOK
-
LINEのGroupを作成し、送りたい相手と、作成したLINE Channelのアカウントを登録しておけば、メッセージ文とGoogle Homeの発話で相手に通知できる
おまけ
逆の、Google Homeにしゃべりかけ、認識した文をLINEメッセージで通知するのは、IFTTTを設定するだけでできます。GitHubのREADMEに、簡単な設定例を記載しました。GitHub - play_w_googlehome#ifttt連携
娘がしゃべるようになったら、Google Homeにしゃべりかけてメッセージを送ってもらうの楽しみ。