前回記事→ LINE BOTでラズパイから部屋の温度を教えてもらう【Push API】【Node.js】
現状と課題
- ラズパイにはMacからwifiでSSH接続している
- SSH接続が切れる・Macがスリープするとプログラムも止まってしまう
- Botが使えなくなる
要件
- Nodeのプログラムを自動起動&永続化させる
- RaspberryPiをサーバーに常時接続させる(ngrokの永続化)
ngrok(トンネリングツール)については→ ngrokでトンネリング
作業概要
- Foreverをインストールし、プログラムを自動起動&永続化
- 無線LANの省電力機能をオフ
- ngrokがタイムアウトしないようにする
- ngrokの永続化(screen コマンドの利用)
1. Foreverをインストールし、プログラムを自動起動&永続化
Raspberry Piにはプログラムを自動起動する方法がたくさんある
- /etc/rc.local
- autostart
- crontab
- /etc/init.d
- systemd
など・・
参照記事 Raspberry Piでプログラムを自動起動する5種類の方法を比較・解説
今回はNodeのプログラムなので、foreverを利用します。
foreverとは、nodeをデーモンとして動かすためのモジュール。バックグラウンドでnodeを動作させるためにインストールします。
デーモン (英語: Daemon) は、UNIX, Linux, MacOSXなどUnix系ののマルチタスクオペレーティングシステム (OS) において動作するプロセス(プログラム)で、主にバックグラウンドで動作するプロセス。- Wikipedia
foreverのインストール
グローバルオプションをつけてインストールします。
$ sudo npm install -g forever
foreverのパスを確認
$ which forever
(例)もちさんの場合
/usr/local/nvm/versions/node/v10.0.0/bin/forever
/etc/rc.localを編集
rc.local
はRaspberry Pi起動時に管理者権限で実行されるファイルです
$ sudo nano /etc/rc.local
下記のようなファイルです
#!/bin/sh -e
#
# rc.local
#
# This script is executed at the end of each multiuser runlevel.
# Make sure that the script will "exit 0" on success or any other
# value on error.
#
# In order to enable or disable this script just change the execution
# bits.
#
# By default this script does nothing.
#
# Print the IP address
_IP=$(hostname -I) || true
if [ "$_IP" ]; then
printf "My IP address is %s\n" "$_IP"
fi
exit 0
ファイル末尾「exit 0」の手前に起動時に実行したいプログラムを指定する
$ sudo -u [ユーザ名] [nodeのパス] [forever のパス] start -a -d [動かしたいスクリプトのパス]
例
_IP=$(hostname -I) || true
if [ "$_IP" ]; then
printf "My IP address is %s\n" "$_IP"
fi
sudo -u username /usr/local/nvm/versions/node/v10.0.0/bin/node /usr/local/nvm/versions/node/v10.0.0/bin/forever start -a -d /home/username/workspace/mylinebot/server.js
exit 0
正しく実行されるか確認
$ sudo /etc/rc.local
info:Forever processing file: 動かしたいスクリプトのパス
と出たら成功!
$ sudo /etc/rc.local
My IP address is 192.000.0.0 000.00.00.00
warn: --minUptime not set. Defaulting to: 1000ms
warn: --spinSleepTime not set. Your script will exit if it does not stay up for at least 1000ms
info: Forever processing file: /home/username/workspace/mylinebot/server.js
Raspberry Piを再起動する
$ sudo reboot
再度ラズパイに接続し、サービスが起動しているか確認しましょう
Foreverのプロセスを確認するコマンド
$ forever list
失敗だと
$ forever list
info: No forever processes running
成功
$ forever list
info: Forever processes running
data: uid command script forever pid id logfile uptime
data: [0] f70E /usr/local/nvm/versions/node/v10.0.0/bin/node /home/username/workspace/mylinebot/server.js 770 941 /home/username/.forever/f70E.log 0:0:0:46.495
参照記事 ラズパイ再起動時にNode.jsアプリを自動起動する
2. 無線LANの省電力機能をオフ
/etc/rc.localに以下を追記する
iwconfig wlan0 power off
無線LANの省電力機能の状態確認。 Power save: off
と表示されたらOK
$ iw dev wlan0 get power_save
Power save: off
Raspberry Piを再起動、再接続し、状態確認しましょう
3. ngrokがタイムアウトしないようにする
ngrokは一定の時間が立つと、接続を解除してしまいます。
ngrokで無料のアカウントを作成し設定ファイルを作成すれば、時間がたってもトンネルが解除されなくなります。
ngrokでアカウントを作成 https://ngrok.com/
作成したアカウントでngrokのwebページへログインするとConnect your accoutというところにauthtokenが表示されます。
設定ファイルの作成。以下のコマンドを実行します。
[ngrokのパス] authtoken [自分のアカウント用Authtoken]
$ ngrok authtoken XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
設定ファイルが、~/.ngrok2/ngrok.yml に作成されます。これでタイムアウトはなくなります!
$ ngrok authtoken XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
Authtoken saved to configuration file: /root/.ngrok2/ngrok.yml
4. ngrokの永続化(screen コマンドの利用)
ngrok(トンネリングサーバー)を常時起動させてラズパイをグローバルに接続しっぱなしにしましょう
Linux では仮想端末を作成するscreen
というコマンドがあります。
「SSH をログアウトしても仮想端末を残す」ことで、仮想端末上にプロセスを残すことができます。
参照記事 Raspberry pi で SSH ログアウト後もプロセスを残したい
インストール
$ sudo apt-get install screen
プロセスを残す
screen を起動
$ screen
ngrokを起動
$ ngrok http 3000(任意のポート)
ngrokのURLを確認。
Ctrl + A、Ctrl + Dで仮想端末からデタッチ(抜け出す)。デタッチ後もプロセスは残り続けます。
デタッチできたら以下のようなメッセージが出ます
[detached from 17974.pts-0.raspberrypi]
仮想端末の確認
$ screen -list
数字(この場合17974)がプロセス番号です
$ screen -list
There is a screen on:
17974.pts-0.raspberrypimochi (2018年06月22日 11時26分49秒) (Detached)
1 Socket in /var/run/screen/S-user.
仮想端末にアタッチ(再接続)したい時は
$ screen -r [プロセス番号]
# もし、セッションが1つだけの時は
$ screen -r
完了です!
前回記事・LINE BOTで利用する場合は、このngrokのURLをLINE DevelopersのWebHookURLに登録すれば、常時BOTが使用できるようになります。
課題
- サーバーを起動しなおしたり、RaspberryPiの再起動が発生したとき、ngrokのURLが変わってしまう
- 有料アカウントにすれば固定ドメインが利用可能
- とりあえず今は保留
参照記事
google-home-notifier周りをほぼ自動化した
10分でSlackからGoogleHomeを喋らせるめちゃ速レシピ