HomeAssistantのご紹介とコマンド調教劇

この記事はYづドン・Rintarnet合同 Advent Calendar 2022の一部です。

時にはOSSの紹介でもしましょうや。何もZero9乗り回してるだけじゃないんや。

Home Assistantって、知ってる?

https://www.home-assistant.io/

Open sourceなlocal controlでprivacy firstなhome automationなんです。

それがHome Assistantなんです!!!!

_________________アホはほうっとれ__________________

Home Assistantっていうのは、要するにGoogleHomeとか、Alexaとか、Apple Home Kitのような代物をオープンソースに、みんなで開発しようぜー!っていう代物です。オープンソースだからと侮るなかれ。かなりの汎用性とかなりの拡張性、コミュニティも活発で透明性にも優れた非常に優秀なソフトウェアの一つなんです。

私もごく最近これを使ってみようと思い立って、今年の8月ぐらいに本格的に整備を始めたところです。現状、なかなか便利な構成に仕上がってるので当環境もご紹介と構成設備を色々とご紹介しようと思いましたが、インストールとNatureRemoの連携書いてたらいっぱいいっぱいになってしまいました。すみません。

弊宅環境のインストール

HomeAssistantは、本当に様々なハードウェアで動作します。

https://www.home-assistant.io/installation/

ここを見ると、本当に多種多様なインストールが可能であることが確認できますね。家を守ってもらうために常に起動が可能なマシンである前提ではありますが、一応どんなOSでもいいしDockerを使ってしまうこともできます。

私は手元に半サーバーと化したArchLinux(AlterLinux)があったため、これをベースにしました。

ArchWikiにもしっかり記述がありますのでこれも参考に進めました。

https://wiki.archlinux.jp/index.php/Home_Assistant

yay -S home-assistant
sudo systemctl enable home-assistant
sudo systemctl start home-assistant

本当にそれだけでマシンの8132ポートにアクセスするだけで立ちました。正直びっくりです。dockerとか使えばもっと楽なんだろうなぁ。

さて、いろいろ設定をすると上の画像のようなトップページが表示されます。一般的にはここにカードを追加し家電を制御します。どうやら開発側には「lovelace」という名前で浸透しているようです。

拡張機能とかのページでこのlovelaceという単語を見かけることがあれば、現行のホーム画面のことだと思って大丈夫です。

デバイスを追加しよう

基本的には設定→デバイスとサービスの右下の+から追加したり、そもそも検出されて画面に出てきているかもしれません。そこからいろいろなデバイスを登録できます。

  • キャストデバイス(Google Home Mini/chromeCast)
    • Google系のキャストプロトコルを積んでいればなんでもOKな様子。
  • SwitchBotハードウェア(開閉センサー/温度センサー)
    • 注:SwitchBot Hub系統は接続できません。リモコンではなくその周辺のBluetoothデバイスのみの対応となります。
    • Bluetooth経由で接続するためには対応するBluetoothアダプタが必要です。手元のパソコンで動くかもしれませんが動かないかもしれません。弊宅では動いたり動かなかったりしています。

その他、家とどう考えても無関係なコンテンツも追加できました.....

  • コロナウイルス感染者データベース
    • 一応公開されてはいるものの、日本のデータが更新されている気配がないのでAPI的に失敗してるのかな?とか推測。
  • Githubのコミット/PRなど表示
    • 結構リアルタイムに表示してくれてる。毎回API叩いてるのかな?
    • マジで要るのかこれw
  • Homekit HASS Bridge
    • Home Assistantに登録しているデバイスをApple Homekitで利用可能にしてくれる。
    • HomeKit非対応なハードがHomeKitで操作できちゃう...!?
  • お天気表示
    • Meteorologisk提供:海外筋なのでおまけ程度に捉えておきましょう。ただそこそこちゃんと天気は表示してくれてます。

ただし、弊宅ではあまりデフォルトで対応しているデバイスはなかったのでAPIを追加したり外部アドオンを追加しました。

オススメはとりあえずHACS(HomeAssistantCommunityStore)という非公式ストアです。ここには日々大量のデバイス対応アドオンが公開されておりワンクリックで導入が可能となっております。

本来のスタイルとしてはAdd-onのSSHを入れて作業するとなっているのですが、どうもArchLinuxで入れたHomeAssistantはcoreのようで少し制限されており...

ここのcoreを選んでコマンドラインに貼り付けて導入。ただ、ユーザー名を変更する必要があるので

sudo -u hass bash

で一旦hassユーザーとして入ってからwgetを実行する。

wget -O - https://get.hacs.xyz | bash -

Home Assistant本体の再起動をすると

左にメニューが追加され、新しいHACS専用の画面が利用可能になる。

Tuya Smartの連携

Tuya Smartの連携自体は純正機能にあるものの、色々APIキーの作成などが必要となり...

https://www.home-assistant.io/integrations/tuya/#create-a-project

色々あるとはいっても、公式に書いてあるだけマシですね。一応書いてあるとおりにやってればOKです。アカウントの作成と、既にハードを登録したTuya Smartアプリが必要になります。

各APIキーなどを用意してHome Assistantに登録すればすぐ利用ができます。

注意:どうやらAPIに制限とか期限の概念があり、その時には動作しなくなったのですが、このTuya IoT Platformで更新申請を出したらきまぐれで許可してくれました。右上の通知ボタンから可能ですので動作しなくなった場合は見てみてください。

Nature Remoの連携

Nature Remoの連携機能自体は公式にもHACSにも存在しなかったため、連携には正直苦労しました。

かんたん編:エアコンを使えるようにしよう

エアコンに関しては有志の皆様がプラグインを作成しているようで、これを一旦採用させてもらうこととしました。

https://github.com/yutoyazaki/hass-nature-remo

これのGit Submoduleを利用して私は導入しました。このときも、作業するアカウントを自分でなくhassユーザーになってから作業をすべきですね。

git submodule add https://github.com/yutoyazaki/hass-nature-remo.git {path_to_custom_component}/nature_remo

このpath_to_custom_componentどこぞい?といいますと、 `本体のパス/custom_component` です。

つまりArchでの場合は/var/lib/hassなので

/var/lib/hass/custom_components/

となります。hacsのセットアップが済んでいればこのディレクトリはあるかもしれませんが、なければ作成してください。ディレクトリのユーザーも勿論hassで。

このような階層になればOKですね。hassの下にcustom_componentsがあり、その下にnature_remoがあればOKです。

https://home.nature.global/
この妙ちきりんな ページにアクセスし、nature-remoアプリで利用しているメールアドレスを入力するとメールが送信されますのでそこからアクセスするとGenerateボタンがあるのでそれを押してください。そうするとアクセスキーが発行されます。
これは一度しか表示されないのですぐにどこかにコピーしておいてください。

それをhassの中にあるconfiguration.yamlに書き込みます。

nature_remo:
  access_token:  コピーした文字列

このように記述します。nature_remoの前には隙間あってはならないし、確実にその次の行に空白2つ開けてaccess_token:そして空白2つで記述してください。

私はこのyaml特有の書き方がわからず四苦八苦しました....

これで一応準備は完了です。NatureRemoのアプリからエアコンを登録した上で、このhomeassistantを再起動させると無事エアコンが利用可能となります。

注意:アプリの設定画面から再起動させようとするとエラーを吐くかもしれませんが新規追加したnature-remoの拡張機能が読み込まれていないためなので代わりにsystemctl restart home-assistantを実行するとよいです。

設定が完了しても、画面には特に変化はないはずです。早速画面に追加しましょう。

ダッシュボードの右上の…を押してダッシュボードの編集を押しましょう。

そうするとこんなカードを追加ボタンが出現するので押して

カードの一覧にサーモスタットがあると思います。もし無ければ何らかの理由でAPIとの接続がうまくいっていない可能性もあります。

エンティティがNatureRemoエアコンになっていることを確認して保存。これでもうエアコンの操作ができますね。上が現在の気温、下がエアコンの設定温度です。

むずかしい編:curlとstate保存でオリジナル信号登録

NatureRemoが赤外線を学習できるのならそれを遠隔で操作できるんちゃう?というお話です。

https://smartlife99.netlify.app/nature-remoを-home-assistantで使う-2-2

この記事がかなり参考になりました。これも見てみてください。

  1. まず現状のデータを見よう
 curl -X GET "https://api.nature.global/1/devices" -H "authorization: Bearer ここにアクセストークン" | jq

(curlとかjqが無いよってエラーは各位aptなりで入れてくださいな)
これで正常にデータが帰ってくると、あなたの名前や部屋の温度などが表示されると思います。もし帰ってこずunauthorizedが表示されるならキーの設定とかが問題あるかもしれません。
2. 現状の登録されているデバイスを見よう

 curl -X GET "https://api.nature.global/1/appliances" -H "authorization: Bearer ここにアクセストークン" | jq

これで現状登録されているすべてのデバイスの情報が表示されます。
今回は以下のようなコードが帰ってきました。

[
  {
    "id": "今回のターゲットのid",
    "device": {
      "name": "なまえ",
      "id": "#######",
      "created_at": "###########",
      "updated_at": "#############",
      "mac_address": "############",
      "serial_number": "###########",
      "firmware_version": "############",
      "temperature_offset": 0,
      "humidity_offset": 0
    },
    "model": {
      "id": "##########",
      "country": "JP",
      "manufacturer": "panasonic",
      "remote_name": "tottara-ch-a",
      "name": "Panasonic LIGHT 301",
      "image": "ico_light"
    },
    "type": "LIGHT",
    "nickname": "照明",
    "image": "ico_light",
    "settings": null,
    "aircon": null,
    "signals": [],
    "light": {
      "buttons": [
        {
          "name": "on",
          "image": "ico_on",
          "label": "Light_on"
        },
        {
          "name": "off",
          "image": "ico_off",
          "label": "Light_off"
        },
        {
          "name": "on-100",
          "image": "ico_light_all",
          "label": "Light_all"
        },
        {
          "name": "on-favorite",
          "image": "ico_light_favorite",
          "label": "Light_favorite"
        },
        {
          "name": "onoff",
          "image": "ico_io",
          "label": "Light_onoff"
        },
        {
          "name": "bright-up",
          "image": "ico_arrow_top",
          "label": "Light_bright"
        },
        {
          "name": "bright-down",
          "image": "ico_arrow_bottom",
          "label": "Light_dark"
        }
      ],
      "state": {
        "brightness": "100",
        "power": "off",
        "last_button": "off"
      }
    }
  },
  {
    "id": "##################",
....以下略

こんな感じのjson配列が返却されます。今回はこのライトを利用しようと思います。きちんととったらリモコンと表示されていますね。オリジナルで値を登録するとまた多少変化すると思われますが、ある程度は参考になると思います。

とりあえず控えておくのは、今回であれば「今回のターゲットid」に相当するid。それと、light buttonsの中身が重要そうに見えるのでそれもコピーだ。

備考:いくつかidがあるものの、それぞれのidの役割を推測と共にメモしておく。
上から、
1. 登録したコンテンツID(NatureRemoの画面上に存在するそれぞれのアイテに割り振られる固有のID)
2. 接続先のNatureRemo本体のID(信号が登録されているNatureRemo本体に登録されているので一つのNatureRemoで複数デバイスの赤外線を登録すると同じIDを複数のコンテンツ内で表示されることとなる)
3. NatureRemo本家サーバー側に保存されている信号データベースのID(今回はとったらリモコンの赤外線を2回ほど食べさせると認識したので本家サーバーから信号パターンをまとめて抽出してきたものと推測され、そのIDが入力されている。全ユーザー内でおそらく共通) 

3. 信号のcurlコマンドを作成し動作テストをしてみよう

curl -X POST 'https://api.nature.global/1/appliances/今回のターゲットのID/light' -d 'button=on'  -H 'authorization: Bearer ここにアクセストークン'

今回の場合はコンテンツがライトだったからか、appliances/id/lightを指定してbuttonを先程のbuttonリストの任意のnameを指定すればOKだった。

そして今回、このコマンドを実行すると電気がつき、逆にbutton=offを指定して実行すると電気が消え、button=onoffを指定するとついたり消えたりする。

因みに完全手動で登録した場合は次のようになる。

curl -X POST "https://api.nature.global/1/signals/信号の登録ID/send" -H "authorization: Bearer ここにアクセストークン"

signals:[]の中にid,name,imagesが入っている場合にこのパターンが使えるっぽい。

一通りの検証ができたので、これを実装してみよう!

さて、curlコマンドでの準備ができたのであとはこれを設定ファイルに書き込めば、理論上はHomeAssistantから呼び出すことが可能となります。

configuration.yamlの一番下にとりあえず次を記述。

shell_command:
  sample_on:"上に書いたcurlコマンドでon指定"
  sample_off:"curlコマンドでoff指定"

shell_command:を入力し、その下でインテントした上でidを指定しコマンドを入力する。

注意: もとのshellコマンドに文字列の引数(")を使用していますが、ここのshell_commandでダブルクオーテーション("")を使用しているため、コマンド内引数文字列はダブルクオーテーションより立ち位置が下のシングルクオーテーション('')を使用して記述してください。文字列同士で競合して正常に動作しないことを防ぐためです。
参考: このidに指定する条件があり、onやoffを指定するとtrue/false扱いになってしまいidとして利用できない。また、このidはネストは出来ず_(アンダーバー)で名前をわかりやすく連結ができるっぽい。ここらへんはyamlの構文なのですがおじさんはよくわからないのでエラーを吐きまくりました。おじさん構文は受け入れてもらえなかったようです。

とりあえずこのコマンド指定がきちんとできた状態でHomeAssistantを再起動させると、一応HomeAssistantの管理下から呼び出すことが可能となります。

開発者ツール→サービスの画面でshellと検索をするとこのように登録したコマンドのIDが出現するのでそれを実行してみましょう。右下の実行ボタンがチェックマークになれば正常にコマンドは実行され、信号が送信されるはずです。

実装したコマンドをライトのスイッチとしてHomeAssistantに登録しよう

まず、スイッチとして使うためにはスイッチがオンかオフかの情報をHomeAssistantに設定する必要があります。input_booleanの下にid名指定、その下にnameで名前を設定できます。

input_boolean:
   mainlight:
     name: メインルームの電気

逆に、オンオフの概念が無くただのプッシュスイッチとして使う場合はこれが不要になるともとれますね。

これで、オンオフ特に意味のないbooleanが完成しました。設定→デバイスとサービス→エンティティで検索窓にid名を入力すると、nameの名前がついたエンティティが出現するはずです。

これを開くと無意味なスイッチが現れます。これをオンオフしても何も起きません。

ライトのスイッチにライトの信号を割り当てよう

switch:
   platform: template
   switches:
     room_light:
       value_template: >
         {{ is_state('input_boolean.mainlight', 'on') }}
       turn_on:
         - service: input_boolean.turn_on
           entity_id: input_boolean.mainlight
         - service: shell_command.mainlight_on
       turn_off:
         - service: input_boolean.turn_off
           entity_id: input_boolean.mainlight
         - service: shell_command.mainlight_off

これでただのbooleanをスイッチにして、色々な設定ができます。ここが最高レベルに難しい! 

上から、switch:とplatform:templateはまぁお約束文だと思ってください。

次にswitches:が複数形になっているように、switchesの中の高さに複数置くことでswitchを何個か纏めて設置が可能なのだろうと思われます(未確認)

room_light:は自由に設定してOKです。これが追加されるスイッチのIDになります。

以下value_template:は先程のmainlightのbooleanの値がonかoffかでスイッチの状態を定義している模様。このinput_boolean.mainlightを各位のbooleanの項目に合わせて書き換えてください。

turn_onとturn_offは字の通り、それぞれのコマンドを実行した時のアクションです。serviceは実行される処理でentity_idは実行される処理の依存のようなものを定義しているようです。このserviceもハイフンスペースを利用すると複数件の登録が可能なようですね。この複数登録を活用して、「booleanをoffにする」「シェルコマンドを実行する」を同時に実行する、というわけです。

これで電源がオンオフするスイッチが完成しました!

エンティティ画面で同じように検索をすると今度はスイッチも見つかると思います。これをスイッチをオンオフしてみると電気が動くぞ!!!!!!!!!!!

これであとは、カードをボタンとして実装してあげれば、オンオフが光ってくれるボタンの完成です!

というわけで今回はこの敷居が高いnatureremo方面の設定を自分の覚書を兼ねてここに記述しておきます。勿論ですが、これ以外にももっとかんたんに便利な機能とか色々あるんですが書いたところでかんたんなのでみなさんHomeAssistantを実装してみましょ!

因みに:

仮想のboolean+switchbotの近接センサー = 外置きの宅配ボックスの荷物配達通知システム

tuyasmart+AppleHomekit+AppleWatch = 非対応デバイスがAppleHome対応になってAppleWatchで制御可能

NFCカードに翳してあらゆるコマンドを実行!

そもそもとして、GoogleHomeが便利に使えたらよかったんだよ....NFCタグの一つも、Appleシステムからのろくな遠隔操作もできないんだから....これだからこの会社達は....まぁ結果GoogleHomeなんて比じゃないぐらいに機能が横に拡張されて凄い便利なのでOKです!