ラピロをWeb APIでON/OFFできるようにする

th_rapiro-wio-node-11

ラピロを24時間365日利用しようと思ったときに個人的に一番気になるのは、ラピロ本体に常時通電することによるRaspberry PiとArduino基盤の発熱です。特にArduino基盤の方は、ラピロのボディを触ると「熱っ!」となるぐらいに熱くなるので、かなり心配です。

過去に一ヶ月ほど常時通電を試したことがあるのですが、その時は背中に冷却ファンを取り付けることで対応していました。これはこれでアリだったのですが、どうしても装備としてラピロがゴツくなってしまうので、ラピロのバランスも悪くなるし、外部電源も必要になるわで、ラピロで気軽に遊ぶのがちょっと難しくなってしまいました。

そういうわけで、常時通電はちょっと諦めて、その代わりに、ラピロ本体の電源のON/OFF自体を、Web APIで制御できるようにしようと思います。この仕組みを入れておけば、ラピロとは別の常時通電サーバから必要に応じてWeb APIを叩くことで、必要なときにだけラピロに動いてもらうことができるようになります。

ではでは早速、やってみましょう。

 

とりあえずこんなものを用意してみました。

th_rapiro-wio-node-1

今回のキモになるのが、Wio Nodeです。

これは以前にご紹介したWio Linkの簡易版です。Wio Linkは日本国内ではあまり流通していませんが(技適絡み?)、Wio Nodeはスイッチサイエンスでも秋月でも簡単に手に入ります。ベースはESP-WROOM-02なので、技適についての心配も無用です。当然Wio Nodeに比べて接続できるGroveモジュール数は少なくなりますが、今回はリレーを使いたいだけなので特に問題なしです。

それから、Groveのリレーモジュールです。

 Wio NodeとGroveリレーだけで、大電流を簡単に遠隔制御できる環境が整ってしまいます。ありがたいというか、恐ろしいというか。

th_rapiro-wio-node-2

この2つは、街の電子部品屋さんで購入してきました。自分のラピロは常にDCジャックから電力を供給しているので、これらのケーブルを加工してリレーと接続し、ラピロ本体と電源ケーブルの間に挟むようにします。

 

th_rapiro-wio-node-3

マイナスの方はそのまま噛み合わせてカバーを被せます。

th_rapiro-wio-node-4

プラスの方はクリップの部分を切ってしまって、線出ししたら間にリレーを挟みます。加工はこれだけです。あとはこれをWio Nodeに繋ぐだけ。

 

続いてWio Nodeの設定ですが、やることは前にWio Linkをご紹介した時とほぼ同じなので、詳しい手順は省略します。

rapiro-wio-node-5

こんな感じで、Wio NodeにGroveリレーを設定して、ファームウェアをアップデートすればOK。これだけでもう、リレーのON/OFF、すなわちラピロの大元の電源のON/OFFがWeb APIで操作できるようになってしまいます。

 

th_rapiro-wio-node-7

実際に接続して試してみます。これはあくまで仮接続で、実際はもう少し綺麗に整理するつもりです。ちょっと大きめの電圧と電流が流れるので(12V, 4A)。

th_rapiro-wio-node-6

Wio Linkのアプリの方に戻って、リレーの状態を取得するWeb APIを叩いてみると、現在はOFFという状態が返ってきます({“onoff”: 0})。

リレーの状態を変更するWeb APIを叩いてみます。

th_rapiro-wio-node-8

「成功」と返ってきて({“result”:”ok”})、

 th_rapiro-wio-node-9

無事にラピロが起動しました。

th_rapiro-wio-node-10

実験成功、めでたしめでたし。。。と言いたいところなのですが、このままだと片手落ちです。現時点で、確かにWeb APIでのON操作については問題ありません。問題なのはOFF操作です。現状のOFF操作は、言うなればRaspberry Piが起動している状態でシャットダウン処理をすることなく、いきなり電源コードをブチっと抜いてしまっている状態です。これを回避するには、同じようにWeb APIでシャットダウン処理を実行できるようにして、

  1. シャットダウン用Web API呼び出し
  2. 30秒〜1分ぐらい待機
  3. 電源OFF用Web API呼び出し

という手順を踏む必要があります。

 

シャットダウン用Web APIは、Bottleフレームワークを使って作成すると、だいたいこんな感じになります。

# -*- coding: utf-8 -*-
from bottle import route,run,request,response,hook
import serial
import os
import threading
import time
import json

com = serial.Serial('/dev/ttyAMA0', 57600, timeout=10)

@hook('after_request')
def header_json():
  response.content_type = 'application/json'

class ShutdownThread(threading.Thread):
  def __init__(self):
    threading.Thread.__init__(self)

  def run(self):
    print("OK, Shutdown.")
    time.sleep(3)
    os.system('sudo shutdown -h now')

def control_response_json(value):
  obj = {'control':value}
  return json.dumps(obj)

@route('/v1/robots/rapiro/control/shutdown')
def control_shutdown():
  com.write("#M0")
  time.sleep(1)
  th = ShutdownThread()
  th.start()
  return control_response_json("shutdown")

run(host='192.168.24.xxx', port=10080, debug=True)

自分のソースコードから関係しそうな部分だけ抜粋してきました。このプログラムを実行してからブラウザで”http://192.168.24.xxx:10080/v1/robots/rapiro/control/shutdown”を叩くと、control_shutdown関数が呼ばれるようになっています。control_shutdown関数内では、シリアル通信でラピロの動作を停止させた後、別スレッドで少し待ってからシャットダウンコマンドを実行させるようにしています。別スレッドで終了させるようにしないと、Web APIを叩かれた直後にRaspberry Piが終了してしまい、Web APIを叩いた側には通信エラーが返されてしまうことになるので。

 

ここまで用意してあげれば、一応はラピロをWeb APIでON/OFF制御できるようになります。一つ課題があるとすれば、Wio Nodeが用意してくれたWeb APIは宅内だろうが宅外だろうがどこからでも叩けるのに対し、自前で用意したシャットダウン用のWeb APIは、現状だと同じローカルネット内からしか叩けないということです。つまり、宅外からラピロをOFFしようとすると、いきなり電源コードをブチっと抜いてしまうことになってしまいます。

これについては回避策は色々あると思いますが、自分の場合はとりあえずは現状の実装で充分なので、とりあえずこのまま据え置いておきます。

 

さて、これでラピロを日常的に使うための準備は整いました。同じローカルネット内で常時通電のサーバを用意しておいて、そちらからCRONでも使って指定時間にWeb APIを叩く(HTTPリクエストを発行する)ようにしておけば、例えば朝夜に自分が家にいるときはラピロをONにしておいて、会社に行っている間はOFFにしておく、ということが簡単にできるようになります。

あとは、ラピロをどう日常に組み込んでいくか。どういうアプリケーション、サービスを作っていくかですが、これはまたおいおい、ということで。