前回、Home AssistantでSwitchBotの温湿度計を扱う方法を紹介しました。

今回はそれを応用して、SwitchBotの開閉センサーを扱えるようにしていきます。
- Home AssistantでSwitchBot開閉センサーを連携する方法
私についてですが、スマートホームにはまってから、今では家中スマートホームデバイスが溢れています。遠隔操作、声で操作、GPSで操作、人が通ったら…などあらゆるシーンをスマート化しています。Home Assistantにも手を出して、色々なデバイスを連携させて、また、自分でコーディングをするくらいハマっています(笑)
そんな私がHome Assistantのノウハウをわかりやすく説明していきます。
Home AssistantとSwitchBot開閉センサーの連携でできること
Home AssistantでSwitchBotの開閉センサーを連携すると開閉センサーのセンサー値を取得できるようになります。
オーバービュー画面にはこのように開閉センサーの開閉状態やボタン押下検知、照度(明るさ)の状態などを表示させることができます。

Home Assistantで開閉センサーのセンサー値を取得できるようになったということは、オートメーションのトリガーとしても使うことができます。
ドアの開閉などを検知して、電気をつけるなどの自動化が可能になります。
SwitchBot開閉センサーを連携する方法
今回の連携のしくみ
前回の記事でSwitchBot温湿度計を連携しました。この時はsbm2mqttを活用させていただきました。
今回はこれを応用して、開閉センサー値を連携できるように改造していきます。
sbm2mqttの使い方や詳細はこちらを参照ください。

基本的な仕組みはsbm2mqttと同じです。
開閉センサーもBLEでセンサー値情報を発信しています。
これをBLEスキャンデバイスでスキャンして取得して、その情報をMQTTでHome Assistantに送ります。
私はBLEスキャンとMQTTの送信、そしてHome AssistantをRaspberry Piで動作させています。

Raspberry PiによるHome Assistantの導入・設定方法などはこちらを読んでみてください。

具体的な連携手順
ここからは早速、具体的な手順を説明していきます。
前提として以下ができているとして説明を進めていきます。
特に最初の3つができていない場合は、アドオンのインストールが必要です。インストール方法はこちらを読んでみてください。インストールが終わったら戻ってきてください。

Home AssistantにSwitchBotの開閉センサーを連携する手順をまとめると以下になります。
- 開閉センサー用のフォルダ作成
- sb_open_sensor.pyを作成
- sbm2mqtt_config.pyを作成
- docker_entrypoint.shの作成
- Dockerfileの作成
- configuration.yamlの編集
開閉センサー用のフォルダ作成
まずは作業フォルダとして開閉センサー用のソースコードを格納するフォルダを作ります。
Home AssistantのConfigフォルダ内に任意のフォルダを作成します。今回作成するファイルは全てこのフォルダに保存します。
この記事では「sb_open_sensor」というフォルダ名にします。
sb_open_sensor.pyを作成
今回の要となる開閉センサーのデータを取得してHome Assistantに送るソースコードを記述します。
File editor等で新規ファイルを作成します。名前は「sb_open_sensor.py」とします。ファイルの場所は「sb_open_sensor」内です。
そして、下記のソースコードをコピーしてください。
なお、xx:xx:xx:xx:xx:xxの部分はご自身の開閉センサーのMACアドレスを入力してください。
MACアドレスはSwitchBotアプリから、開閉センサーの詳細画面→右上の歯車マーク→デバイス情報から確認することができます。確認方法は以下です。
#!/usr/bin/env python3
# -*- coding: utf-8 -*-
#
# sb_open_sensor.py
from bluepy.btle import Scanner, DefaultDelegate, ScanEntry
import datetime
import paho.mqtt.client as mqtt
import json
import time
import binascii
from bluepy.btle import Scanner, DefaultDelegate
# Import configuration variables from sbm2mqtt_config.py file - Must be in the same folder as this script
from sbm2mqtt_config import (
mqtt_host,
mqtt_port,
mqtt_timeout,
mqtt_client,
mqtt_user,
mqtt_pass,
mqtt_topic,
)
class ScanDelegate( DefaultDelegate ):
def __init__( self,macaddr ):
self.macaddr=macaddr
self.isButton=0
self.postButtonCount=0
self.output=[{"isButton":self.isButton}]
DefaultDelegate.__init__( self )
def handleDiscovery( self, dev, isNewDev, isNewData ):
if dev.addr == self.macaddr:
for ( adtype, desc, value ) in dev.getScanData():
if ( adtype == 22 ):
servicedata = bytes.fromhex( value[4:] )
isIlluminance=servicedata[3] & 0b00000001 #照度取得(明るい/暗い)
isOpen=(servicedata[3] & 0b00000010) >> 1 #開閉状態取得
isLeaveOpen=(servicedata[3] & 0b00000100) >> 2 #開けっ放し状態取得
open_time=servicedata[7] #開けっ放しの時間取得
buttonCount=servicedata[8] & 0b00001111 #ボタンが押された回数取得
if self.postButtonCount==0:
self.postButtonCount=buttonCount
#ボタンが押されたかどうか判定
if (buttonCount>=self.postButtonCount+1) or (buttonCount==1 and self.postButtonCount==15):
self.isButton=1
elif buttonCount==self.postButtonCount:
self.isButton=0
if buttonCount!=self.postButtonCount:
self.postButtonCount=buttonCount
#出力データの整形
self.output={"isIlluminance":isIlluminance,"isOpen":isOpen,"isLeaveOpen":isLeaveOpen,"time":open_time,"buttonCount":buttonCount,"isButton":self.isButton}
# MQTT publish as JSON
msg_data = json.dumps({
"isIlluminance": str(isIlluminance),
"isOpen": str(isOpen),
"isLeaveOpen": str(isLeaveOpen),
"time": str(open_time),
"buttonCount": str(buttonCount),
"isButton": str(self.isButton)
})
print(
"\n Publishing MQTT payload to "
+ mqtt_topic
+ "/"
+ self.macaddr
+ " ...\n\n "
+ msg_data
)
mqttc = mqtt.Client(mqtt_client)
mqttc.username_pw_set(mqtt_user, mqtt_pass)
mqttc.connect(mqtt_host, mqtt_port)
mqttc.publish(mqtt_topic + "/" + self.macaddr, msg_data, 1)
def startScan(self,scan,time):
Scanner().withDelegate( self ).scan(time)
if __name__ == '__main__':
macaddr = 'xx:xx:xx:xx:xx:xx' #あなたのデバイスのMACアドレスに書き換えてください(アルファベットは小文字) ※左は記入例
scan=ScanDelegate(macaddr) #BLEスキャンのための初期設定
while True:
try:
scan.startScan(scan,3) #スキャン開始 3秒間
except:
pass
time.sleep(5)
sbm2mqtt_config.pyを作成
環境変数を読み込むコードを記述します。
sbm2mqttで使ったファイルをそのまま持ってきても構いません。
一応、コードを書くと以下になります。(ちょっとアレンジ入れています)
#!/usr/bin/env python3
import os
# MQTT settings
mqtt_host = os.environ.get("MQTT_HOST")
mqtt_port = int(os.environ.get("MQTT_PORT"))
mqtt_timeout = int(os.environ.get("MQTT_TIMEOUT", "30"))
mqtt_client = os.environ.get("MQTT_CLIENT")
mqtt_user = os.environ.get("MQTT_USER")
mqtt_pass = os.environ.get("MQTT_PASS")
mqtt_topic = os.environ.get("MQTT_TOPIC")
docker_entrypoint.shの作成
docker_entrypoint.shは実行するときに最初に実行されるスクリプトです。
sbm2mqttも今回のコードもDockerという仮想環境で実行されます。この仮想環境を実行したときにこのスクリプトを実行し、sb_open_sensor.pyを実行するしくみになっています。
あまり詳しいことはわからなくても、とりあえずコピーでOKです。
まずはFile editorで「sb_open_sensor」フォルダ内に「docker_entrypoint.sh」というファイルを作成します。
#!/bin/bash
service dbus start
bluetoothd &
while true ; do
./sb_open_sensor.py
sleep $REPORTING_INTERVAL || break
done
Dockerfileの作成
Docker仮想環境のビルド設定ファイルを作成します。これもよくわからなくてもとりあえずコピーでOKです。
まずは、「sb_open_sensor」フォルダ内に「Dockerfile」というファイルを作成します。拡張子はありません。
以下の内容を記載して保存します。
なお、ENV内の内容はご自分のMQTT設定に合わせて書き換えてください。
特に、MQTT_USERとMQTT_PASSはMQTTのユーザー名とパスワードを記入してください。
# docker build . -t sb_open_sensor
# docker run --rm --net=host --privileged -it -e MQTT_HOST=xxx.xxx.xxx.xxx -e MQTT_PORT=xxxx -e MQTT_USER=xxxxxx -e MQTT_PASS=xxxxxx sb_open_sensor
FROM python:3.7
RUN apt-get update && apt-get install -y bluez bluetooth
RUN pip install bluepy paho-mqtt
ENV \
MQTT_HOST=127.0.0.1 \
MQTT_PORT=1883 \
MQTT_USER=mqtt_user \
MQTT_PASS=xxxxxxxx \
MQTT_CLIENT=sbo2mqtt \
MQTT_TOPIC=switchbot_open_sensor \
REPORTING_INTERVAL=3
# in seconds
ENTRYPOINT sh docker_entrypoint.sh
COPY . .
configuration.yamlの編集
最後にHome Assistantに開閉センサー情報を表示するためにconfiguration.yamlを編集します。
File editor等でconfiguration.yamlを開き、「sensor:」内に下記を記載してください。
「name:」は表示名です。わかりやすい名前を付けてください。
「state_topic:」のxx:xx:xx:xx:xx:xx(MACアドレス)には先ほど確認した開閉センサーのMACアドレスを入力してください。
sensor:
- platform: mqtt
name: '開閉センサーの開閉'
state_topic: 'switchbot_open_sensor/xx:xx:xx:xx:xx:xx'
value_template: >-
{% set values = { '1':'OPEN', '0':'CLOSE'} %}
{{ values[value_json.isOpen] if value_json.isOpen in values.keys() else 'CLOSE' }}
icon: mdi:door-open
- platform: mqtt
name: '開閉センサーのボタン'
state_topic: 'switchbot_open_sensor/xx:xx:xx:xx:xx:xx'
value_template: >-
{% set values = { '1':'ON', '0':'OFF'} %}
{{ values[value_json.isButton] if value_json.isButton in values.keys() else 'OFF' }}
icon: mdi:door-open
- platform: mqtt
name: '開閉センサーの照度'
state_topic: 'switchbot_open_sensor/xx:xx:xx:xx:xx:xx'
value_template: >-
{% set values = { '1':'明るい', '0':'暗い'} %}
{{ values[value_json.isIlluminance] if value_json.isIlluminance in values.keys() else '暗い' }}
icon: mdi:door-open
- platform: mqtt
name: '開閉センサーの開けっ放し状態'
state_topic: 'switchbot_open_sensor/xx:xx:xx:xx:xx:xx'
value_template: >-
{% set values = { '1':'開けっ放し', '0':'CLOSE'} %}
{{ values[value_json.isLeaveOpen] if value_json.isLeaveOpen in values.keys() else 'CLOSE' }}
icon: mdi:door-open
sb_open_sensorを実行
お疲れさまでした。ここまでのソースコードが書けたら早速実行します。
まずはDockerのビルドを行います。
Terminalで以下のコマンドを実行してください。
cd config/sb_open_sensor
docker build . -t sb_open_sensor
実行するとこんな感じのログが表示されます。最後にSuccessfullyとなっていることを確認してください。

そして、最後に以下のコマンドで実行します。
docker run --rm --net host --privileged -it sb_open_sensor
成功すれば、このようにログが表示されます。

そして、オーバービュー画面に戻ると以下のように表示されています。

まとめ
いかがだったでしょうか?
SwitchBotの開閉センサーの連携ができたと思います。
もしご不明な点があれば、気軽に問い合わせフォームやTwitterでご連絡ください。可能な限り素早く返信します。
SwitchBotに登録したエアコンをコントロールする方法も紹介しています。こちらも読んでみてください。

今回はPythonを使ってコードを書いています。Pythonを知らなくてもほぼコピペするだけで動くように頑張って紹介していくつもりですが、Pythonの基本は知っておくことで、理解も深まりますし、アレンジもできるようになります。少し不安を感じる人は、以下の参考書を使って勉強してみることをおすすめします。
↓超入門書
↓初級本
また、Home Assistantやスマートホーム関連の記事はこちらにまとめていますので、ぜひこちらも読んでみてください。

コメント
検索からたどり着きました。
最近はHAのintegrationにてswitchbotのローカルBT連携が実装されましたね。