園バス待ち中、忘れ物今取りに帰っても大丈夫?が目に見える仕組み!


幼稚園に子供を通わせて9年目、3児のママです。
幼稚園バスのあるあるだと思うのですが

・忘れ物!まだ取りに帰っても間にあう?
・出かけにモタモタ。バス行っちゃった?
・急にトイレ!家に一度帰っても大丈夫かな?

などなど、幼稚園バスの居場所がすぐにわかれば良いのにな~と思ったことが何度もあります。

知りたい時に幼稚園バスの居場所がわかると

・雨の日、寒い日、終わりが見えずに待ち続けるという事がなくなり
・忘れ物など、一度家に取りに帰る事が出来たら、園まで後から送っていかなくても済んだり

メリットは沢山あると思います。

そこで、幼稚園バスの居場所をアプリのインストール不要!LINEからバスの位置情報を受け取れるサービスの開発をしていきたいと思います。

全体のイメージ

必要な技術など

・バスの位置を取得するGPSデバイス(今回はiphone)
・LINEで位置情報を取得する為のLINE Messaging API技術
・開発言語にはnode.jsを利用

位置情報を取得する

MDN WEB Docsを参考に位置情報の取得を行いました。

index.htmlとmap.jsファイル2つのファイルを作りました。

<!DOCTYPE html>
<html lang="ja">

<head>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width,initial-scale=1">
    <title>位置情報取得</title>
    <script src="map.js" defer=""></script>
</head>

<body>
    <button id="find-me">Show my location</button><br/>
    <p id="status"></p>
    <a id="map-link" target="_blank"></a>
</body>

</html>
function geoFindMe() {

    const status = document.querySelector('#status');
    const mapLink = document.querySelector('#map-link');

    mapLink.href = '';
    mapLink.textContent = '';

    function success(position) {
        const latitude = position.coords.latitude;
        const longitude = position.coords.longitude;

        status.textContent = '';
        mapLink.href = `https://www.openstreetmap.org/#map=18/${latitude}/${longitude}`;
        mapLink.textContent = `Latitude: ${latitude} °, Longitude: ${longitude} °`;
    }

    function error() {
        status.textContent = 'Unable to retrieve your location';
    }

    if (!navigator.geolocation) {
        status.textContent = 'Geolocation is not supported by your browser';
    } else {
        status.textContent = 'Locating…';
        navigator.geolocation.getCurrentPosition(success, error);
    }

}

document.querySelector('#find-me').addEventListener('click', geoFindMe);

webブラウザで実装し、【Show my location】をクリックすると位置情報が取得でき

取得した位置情報のリンクをクリックすると地図が表示されました。位置あってる。

次に、取得したデータをデータベースへ保存

Firebaseを利用して、データを保存します
Firebase CloudFirestoreの使い方を初心者が解説してみた
今回は、このような形でデータベースを作成しました。

作成したデータベースにsetします。
setはデータベースのドキュメントの中身を上書きします。
参考にしたサイト
Firebase Cloud Firestoreのデータ更新 setとupdateの違い

await db.collection('map').doc('K9HEdPL7SQukhLGpIgLX').set({
  Latitude: position.coords.latitude,
  Longitude: position.coords.longitude
});

特定のドキュメントに位置情報を更新する仕組みは構築できました。
次に、

Firebaseの情報をLINEで取得

LINEの位置情報APIを利用して位置情報を送ります。
LINE 位置情報メッセージ
リッチメニューを作成して、リッチメニューを押したら位置情報を送るという仕組みにしました。

return client.replyMessage(event.replyToken, {
 type: 'location',
 title: '位置情報',
 address: 'Aバス',
 latitude: text.Latitude,
 longitude: text.Longitude
});

LINEの位置情報メッセージを利用すると、地図が出るのでとても分かりやすいですね。

最後に

デプロイ

位置情報取得ボタンのhtmlファイルは契約しているサーバーへアップロード
左端に位置情報のボタンがあるシンプルなものです。

LINE Messaging APIと連携をとっているnode.jsファイルはHerokuでデプロイしました。

実際に使ってみる

バスに乗って試す事は難しいので、今回は子供と使ってみました。
本来は15秒おきくらいに自動で位置情報を発信していきたいのですが、今回は手動でボタンを押したタイミングでの位置情報で実験をしていきます。

イマドコサーチで親から子供の居場所をいつもは調べるのですが、今回は特別に逆パターン。
意外と子供から聞かれる
「ママいつ帰ってくるの?」

これをLINEで解決してもらいます!

①まずはママがスマホを持ってスーパーへ出かける
②子供は好きなタイミングで【今どこ?】を押す
③帰宅後、LINEを見せてもらう

結果

「ママずっと同じ場所にいた!」

子どものLINEを確認すると、全て同じ地図の場所にピンがありました。
念のため、薬局で位置情報を確認したのですが、薬局に位置が変わっている~!と私は感動しました。

考察

実験をしてみて、子どものLINEでは居場所が変わらなかった

この件に関して、
Firebaseを確認したところ、最後にwebアプリ側から位置情報取得ボタンを押した緯度にちゃんとなっていました。
LINEを立ち上げっぱなしにしていた事により、最新のデータが取得できなかったのではないかな?と思います。

ボタンを押したタイミングではなく、リアルタイムで最新情報を取得する
今度の課題たと思いました。