はじめに
6ヶ月間の育児休業を取って、育児に専念しているnaka-kazzです。赤ちゃんの子育てをしていると「ミルク何時にあげたかな?」「おむつはいつ変えたかな?」なんていうことを良く考えます。赤ちゃんの成長記録をちゃんと付けることは重要(らしい)なので、ミルクやおむつ交換の時間を記録するスマホアプリも世の中にはいっぱい出ています。
ただ、子育てをしていると、赤ちゃんをだっこしていて両手が塞がっていたり、オムツを変えて手が汚かったりすることが本当多いんです。なので、スマホを手に取って、ロック解除して、記録アプリを開いて、時間・種類などをいちいち入力することはホント面倒なんです。しかも、あとで記録しようとすると忘れますし・・・・。
そこで、今回は赤ちゃんベットに取り付ける「赤ちゃんボタン」を作って、ボタンを押すだけでミルク&おむつ交換の記録がワンプッシュで記録することをやってみたいと思います。
やりたいこと
赤ちゃんベットの横にボタンを取り付け、シングルクリックでミルクの時間を記録、ダブルクリックでおむつ交換の時間を記録する「赤ちゃんボタン」を作ってみます。
「赤ちゃんボタン」開発の全体の流れは以下です。
1.Gravioでボタンセンサーとトリガーの設定
2.Googleカレンダーへの記録用プログラムの作成
3.Node-redのフローの作成
Gravioでボタンセンサーとトリガーの設定
「赤ちゃんボタン」のボタン部分は、センサーを500円でレンタルできて簡単にIoTを試せるGravioを利用しました。Gravioの詳細な設定方法は、Node-redでスマートハウス-Gravioで戸締り確認などに書いているので、こっちを参照して下さい。また、GravioのインストールはGravioのインストール方法など、先人の知恵を借りましょう。
ボタンセンサーの設定
①レイヤの追加
Gravio Studioを開きGravio Hubを選択して、レイヤーの設定画面を開きます。次に、レイヤの追加画面を開き、レイヤー名に「赤ちゃんボタン」、センタータイプにボタンを示す「Aqara-SingleButton」を選択して「追加」ボタンをクリックします。
②ボタンセンサーのペアリング
画面右上のシリアルポートのボタンをクリックして、センサーのペアリング画面を表示します。次に、出てきた画面の「ペアリング」ボタンをクリックします。そして、ボタンセンサーに付いている3mmぐらいの小さなボタンを1秒間隔ぐらいで何回か押します。無事にペアリングができると、接続されているセンサー欄に「lumi remote b1acn01」というモノが表示されるので、「閉じる」ボタンをクリックしましょう。
③デバイスを選択
赤ちゃんボタンのレイヤにボタンセンサーを紐づけます。赤ちゃんレイヤーを選択した状態で、画面右上の「(+)」ボタンをクリックし、表示された画面から「lumi remote b1acn01」を選択して「セット」ボタンをクリックします。
④デバイスをオン
赤ちゃんボタンのレイヤにボタンセンサーが追加されたら「オン」のチェックボックにチェックをつけましょう。
アクションの設定
①アクションの作成
Gravioのアクション画面を開き、右上の「+」ボタンをクリックします。
②ミルクアクションの設定
ミルクを記録するためのアクションを作成します。アクションと言っても、後で設定するNode-redのWebAPIを呼び出すだけのアクションです。なお、URLのIPアドレスはNode-redをインストールしているホストのIPアドレスに変更してください。
・アクション名:ミルクを記録
・URL:http://127.0.0.1:1880/MilkAction
・HTTP Method:POST
③おむつアクションの設定
ミルクアクションと同様にして、おむつを記録するアクションも作成します。
・アクション名:おむつを記録
・URL:http://127.0.0.1:1880/DiapersAction
・HTTP Method:POST
トリガーの設定
①トリガー画面の表示
Gravioのトップ画面まで戻り、Gravio Hubを選択して、トリガー画面を開きます。
②ミルクトリガーの作成
画面右上の「+」ボタンをクリックして、トリガーの追加画面を表示させ、以下のようにトリガーを設定します。
・トリガー名:ミルクを記録
・エリア:エリア
・レイヤー:赤ちゃんボタン
・アクション名:ミルクを記録
・Button press:Single press
③おむつトリガーの作成
同様にして、おむつのトリガーも以下のようにトリガーを設定します。
・トリガー名:おむつを記録
・エリア:エリア
・レイヤー:赤ちゃんボタン
・アクション名:おむつを記録
・Button press:Double press
これでGravioの設定は完了です。
Googleカレンダーへの記録用プログラムの作成
次に、赤ちゃんボタンが押された時にGoogleカレンダに記録するプログラムを作っていきます。Googleカレンダーへの登録処理の詳細は「自分のGoogleカレンダーにJWTを使って予定を追加してみる」に記載しているので、詳細はそっちを参照してください。
Google Calendar APIの有効化
まずは、Google Calendar APIを有効化して、サービスアカウントを取得します。
①Google Calendar APIの有効化
ブラウザでGoogle Cloud プラットフォームにアクセスして、GoogleカレンダーAPIを有効化します。
②認証情報の追加
GoogleカレンダーAPIを利用する認証情報を追加します。
③サービスアカウントの作成
次に、GoogleカレンダーAPIが利用するサービスアカウントを作成します。作成したサービスアカウントのメールアドレスは後ほど利用するので、メモしておきましょう。
④キーファイルの作成とダウンロード
サービスアカウントを利用するための、キー情報をJSON形式で作成してダウンロードします。
Googleカレンダーの作成
次に、ミルクとおむつの時間を記録するためのGoogleカレンダーを作成します。
①Googleカレンダーへのアクセス
ブラウザでGoogleカレンダーにアクセスし、左側のメニューから新しいカレンダーを作成します。
②サービスアカウントの割り当て
作成したGoogleカレンダーの「設定と共有」画面を開き、上で作成したサービスアカウントのメールアドレスを共有ユーザとして追加します。アクセス権限は「予定の変更権限」を設定してください。
③カレンダーIDのメモ
最後にプログラムからこのカレンダーにアクセスするために、カレンダーIDをメモしておきます。
プログラムの作成
Google Calendar APIをキックして、ミルクとおむつの時間をGoogleカレンダーに登録するプログラムを作成します。
なお、今回使用した環境は以下の通りです。
・OS :Ubuntu 18.04.1
・node:10.16.0
・npm :6.11.3
①Google APIのインストール
まずは、nodeからGoogle Calendarを利用するために、GoogleAPIsパッケージをインストールします。
$npm install googleapis
②プログラムの作成
Google Calendarに予定を登録するプログラムを作成します。コマンドライン引数として以下の情報を渡すようにします。
・第2引数:’ミルク’もしくは’おむつ’の文字列
・第3引数:開始時間
・第4引数:終了時間
・第5引数:Googleカレンダー上での色(1 もしくは 2)
なお、以下の変数は適宜、変更してくださいね。
・keyfile変数:上でダウンロードしたサービスアカウントのキーファイル名
・calendarId変数:上でメモしたカレンダーID
また、キーファイルとプログラム「insertCalendar.js」は同じフォルダに格納してくださいね。
const {google} = require('googleapis');
//-----------------------------------------------------------------------
const keyfile='./api-project-xxxxxxxxxxxx-7c5ac86d4f1b.json';
const calendarId='xxxxxxxxxxxxxxx@group.calendar.google.com';
//-----------------------------------------------------------------------
const event = {
'summary': process.argv[2],
'location': 'お家',
'description': '',
'start': {
'dateTime': process.argv[3]+'+09:00',
'timeZone': 'Asia/Tokyo',
},
'end': {
'dateTime': process.argv[4]+'+09:00',
'timeZone': 'Asia/Tokyo',
},
'attendees': [],
'colorId': process.argv[5],
'reminders': {
'useDefault': false,
'overrides': [
{'method': 'email', 'minutes': 24 * 60},
{'method': 'popup', 'minutes': 10},
],
},
};
//-----------------------------------------------------------------------
process.env.GOOGLE_APPLICATION_CREDENTIALS = keyfile
const key = require(keyfile);
const scope = ['https://www.googleapis.com/auth/calendar', 'https://www.googleapis.com/auth/calendar.events'];
const jwt = new google.auth.JWT(key.client_email, null, key.private_key, scope)
const calendar = google.calendar("v3");
jwt.authorize((err, response) => {
calendar.events.insert({
auth: jwt,
calendarId: calendarId,
resource: event,
}, (err, event) => {
if (err) {
console.log('エラー:' + err);
return;
}
console.log('予定を登録しました');
});
})
③シェルでのラッピング
後でNode-redから実行し易くするために、NodeJSのプログラムをシェルスクリプトでラッピングします。「・・・・・」の部分はinsertCalendar.jsの場所を絶対パスで記載してください。また「insertCalendar.sh」にchmodコマンドで実行権限を付与する事を忘れないでくださいね。
#insertCalendar.sh
/usr/local/bin/node /・・・・・・/insertCalendar.js $1 $2 $3 $4
④プログラムのテスト
作成したプログラムが正常に動作するかテストしてみます。
$./insertCalendar.sh 'ミルク' '2019-10-12T10:00:00' '2019-10-12T11:00:00' 1
予定を登録しました
$
これで、Googleカレンダーに予定を追加する部分は完成です。
Node-redのフローの作成
最後に、GravioからのリクエストをWebAPIで受け付けて、先ほど作成したプログラムを呼び出す処理をNode-redで作成します。また、Googleカレンダーに書き込まれたことをAlexaから音声でお知らせすることも追加します。
WebAPIの作成
それではNode-redにノードを追加しながら、WebAPIを作成していきます。なお、ミルクの記録を例に記載しますので、おむつの記録に関しても同様に作成して下さいね。
①http inノードの追加
左側のパレットから「http inノード」をフローに追加し、以下のように設定します。
・メソッド:POST
・URL:/MilkAction ※Gravioのアクションで設定したものに合わせる
・名前:MilkAction
②functionノードの追加
左側のパレットから「functionノード」をフローに追加し、プログラムに渡す引数を生成する処理を設定します。
var dt = new Date();
var fd = formatdate(dt);
dt.setMinutes(dt.getMinutes() - 20);
var fd2 =formatdate(dt);
msg.payload="ミルク "+fd2+" "+fd+" 1"
return msg;
// 日付フォーマットYYYY-MM-DD
function formatdate(dd) {
return dd.getFullYear()+"-"+(("0"+(dd.getMonth()+1)).slice(-2))+"-"+(("0"+dd.getDate()).slice(-2)+"T"+(("0"+(dd.getHours())).slice(-2))+":"+(("0"+(dd.getMinutes())).slice(-2))+":"+(("0"+(dd.getSeconds())).slice(-2)));
}
プログラムの大部分は、日付フォーマットを「YYYY-MM-DD」形式にするformatdate関数です。メインの処理の中では、現在日時と現在日時-20分を取得して、上記で作成したプログラムに渡す引数の形式でmsg.payloadに格納します。
③execノードの追加
左側のパレットから「execノード」をフローに追加し、上で作成したシェルスクリプトを実行するように設定します。
・コマンド:※上で作成したシェルスクリプトのパス
・引数:msg.payloadにチェックを付ける
・名前:登録
Alexaにしゃべらせる
Googleカレンダーに記録したことを、Alexaが音声でお知らせしてくれるようにします。Node-redからAlexaをしゃべらせる処理の詳細は「Alexaをしゃべらせる(node-red編)」に記載していますので、こっちを参照してください。
①Alexa Routineノードの追加
左側のパレットから「Alexa Routineノード」をフローに追加し、以下のように設定します。
・名前:ミルク
・Text:「ミルクを記録しました」
・Device:しゃべらせるAmazon Echoデバイス
②ノードの接続とデプロイ
それでは、追加したノードを以下の図のように接続し「デプロイ」ボタンを押しましょう!!
テスト
それでは、赤ちゃんボタンを押してみましょう!どうですか?Googleカレンダーに予定が追加され、Alexaが「ミルクを記録しました」としゃべれば完成です!!!当然、スマホのGoogleカレンダーアプリからも確認できるので、スマホから確認してもOKです。
おわりに
今回は、Gravioのボタンセンサー+Googleカレンダー+Amazon Alexaを使って「赤ちゃんボタン」を作る事をやってみました。このボタンのおかけで、ミルクを記録したり、おむつを記録する手間が大幅に削減できました。
コメント