Scala
RaspberryPi
Akka
ScalaDay 22

Scala + Akka + Raspiでで入退室管理をつくった話。

すいません、ScalaJSについて書こうと思ったが、案外情報がまだまとまってないので、以前やった仕事のことについて書きます。これは、Scala関西でも話した内容と重複します。

入退室管理アプリケーションについて

仕事で、生徒への入退室管理アプリケーションをつくりました。機能としては、ざっくり

  • QRコードをかざして入退室
  • 入退室確認したら、保護者等にメール配信
  • 入退室ログ管理
  • 簡易的な会員管理
  • Slack通知
  • 遅刻などの「まだ来てないです」通知
  • QRコード発行

構成

ざっくり構成を。

スクリーンショット 2017-12-24 12.14.34.png

ボタンは起動やらを知らせるやつですね、超音波センサーを近づけて、カメラを起動させます、んで、QRを認識して、それと時間を見て、やります。スピーカーは、案内ですね。

Raspberry PiでAkka動かす話

ぶっちゃけ、これ、とりあえず、Raspberry PiでAkkaを動かす試みをまずしていました。たまたまなんか動いたんで、入退室管理をつくったって感じすね。ほぼ、遊び感覚でつくりました。

僕一人関わったのが僕ひとりで、開発期間的にはのんびりやって、1ヶ月ぐらい。まーちゃっちゃと実装してみました。

Raspberry Piを動かすといっても、そのままRaspberry PiにScalaの環境を入れるわけではなく、開発マシンでscalaを書いてコンパイルしてjarにして、そのjavaを入れたRaspberry Piにjarを入れて動かしました。

また、Raspberry Piは複数台動かしてます。全部おなじプログラムを入れてます。SDカードに同じものを入れてます。

通信の仕組み

ネットワークについて

Raspi同士は通信してます。なのでAkka Remoteを入れました。ローカルネットワークでつなぐので、NAT越える必要がないです。なんで、IoTではないですね(笑)。LoTです。

まぁ、こんど、遊びでNatを越えるようにしても良いですが、面倒なんでやってないです。

あと、Akka Remoteですが、Stableなバージョンじゃなくて、Remoting (codename Artery)の方をつかいました。(https://doc.akka.io/docs/akka/current/remoting-artery.html)

メッセージの設計について

さて、今回はwebカメラでQRの判定をしていますが、実は、監視カメラっぽい機能もつけたかった為、Webカメラの画像もメッセージとして投げることにしました。

メッセージのサイズがそれなりに大きくなりますので、そのように適当な設定にしました。

akka {
  actor {
    provider = remote
  }
  remote {
    large-message-destinations = ["/user/techin/codeReader/camera"]
    advanced {
      maximum-large-frame-size = 4MiB
    }
 }
}

こんな感じの設定しました。

そして、実際にカメラ画像もRaspberry Piの方で圧縮して送受信しています。

メールについて

そういえば、メールはGmailのAPIをぶったたいて送信しています。

それ以外特筆することがないですね。もし希望があれば、別に記事をかこうかな。

データ永続化(Akka Persistence)

Akkaにはデータ永続化の仕組みがありまして、Akka Persitenceというのがあります。Actorの状態を保存できるやつです。(https://doc.akka.io/docs/akka/current/persistence.html)

ドキュメントを読んでいただけたら、だいたい分かると思いますが、簡単に言えば、メッセージのログを記録し続けて、再起動時に、メッセージのログを辿って、元の状態に復元する機能です。

Akka PersitenceのPluginをつくる

Akka Persitenceは仕組みとしてLevel DBを利用しますが、インストールできないらしいので、別のDBを利用して、Pluginを別に実装しました。

その辺は、記事にしようと思いましたが他の方がなんかやっているので、リンクを乗せておきます。

https://gist.github.com/okumin/b591d2bd54470a067349

わりと簡単につくれます。

GUIとAkkaの連携

さて、もろもろ設定したり管理するんで、ScalaFXを利用して、GUIをつくって、Akkaと連携をしています。

この辺がちょっと案外大変だったかなと。というのも、どうやってAkkaのアクターと、メインのGUIのスレッドを通信しようかって問題があました。まぁー、akkaのaskをつかいまくった感じです。

この辺は、Akkaのメッセージではなくて、別の方法で、UIと通信するべきかなぁとか考えました。うーむ。

複数台協調するための考えたこと

そういえば、うーむ、一番やっててたのしかったのが、複数台分散して動いてるので、そのへんの仕組みをかんがえることですね。

どうやって、生徒間の情報を共有するとかそのへんを考えてました。ぶっこわれたときどうするかとか。これだけで大分記事が書けます。

監視

そういえば、複数台管理するので、Raspberry Pi自体も監視する必要があったのですが、テキトーにやりました。(おぼえてない。)

やってみて感想

Erlangでもアクターをつかったことがあるんですが、アクターで実装すると、まず感じるのは、雑に実装しても動くってのがいいなぁって感じるんですよね。

みなさんもたのしいので、ぜひやってみてくださればいいかなと。

あと稼動して、半年ぐらい立つのですが、結構壊れないものですね。すぐ壊れるかと思いましたが。

おわり。