TP-LINK WiFiスマートプラグをESP32(Arduino)から制御する

家電の電源制御のために市販の赤外線リモコン・コンセントに自作の赤外線リモコン送信機を組み合わせて使っていたが、2つのHWの設置場所の制約に加えコンセントも余計に占有してしまうため、なんとかならんもんかなと常々思っていたところ、な~んと、TP-LINKのスマートプラグ(HS100/105/110)のプロトコルを解析してしまった猛者がいるのを発見してしまった。世の中には凄い人がいるもんだ。(/・ω・)/

Reverse Engineering the TP-Link HS110

早速、その内容を元に試して見た所、WiFiスマートプラグ(HS105)をESP32(Arduino)から制御することに見事に成功。(/・ω・)/

TPLinkSmartPlugクラスは家電制御向けに有用と思われる機能をESP32に依存しないよう汎用的な実装を心がけたつもりなのでTCPが使える全てのArduinoで使えるはず。試してないけど...

未実装な機能は沢山あるが使うのが面倒な機能や管理系機能が多いので初期設定やその他の機能についてはKasaアプリを利用するのが良いだろう。ちなみにローカルLAN上で直接スマートプラグと通信するためKasaのクラウド・アカウントは必要ない。それと、スマートプラグのプロトコル仕様が変更されたりすると動作しなくなる可能性が考えられるので気になる人はファームウェア更新はしないほうが良いとは思うが、仕様変更などしたら稼働中の全世界中のTP-LINKスマートホーム・デバイスが一斉に動作しなくなるという大問題が発生するためそう気にする必要もないだろう。

昨今、IoTと呼ばれる様々な手法があるが家電制御するためになんでもかんでもインターネットに繋ぐというのはセキュリティ的に問題があるばかりでなく動作遅延や故障率的にも問題がありすぎると言わざる得ない。家の中と外のネットワークは明確にわけて必要な機能のみ部分的に連携するべきと思うがそんなことを考えるのは私だけだろうか...

【約1秒毎にオンオフを切り替えるサンプルスケッチ】

【修正履歴】
2021-09-15
read()とdiscovery_response()でWDT例外が発生する場合がある点を修正。

2020-01-18
ライセンスを変更。それとインクルード順序の関係でコンパイル・エラーになる場合があったので順序を変更。Arduinoのインクルードは標準インクルードファイルの後でインクルードしたほうが良いみたいだ。

2018-09-03
複数端末へアクセスする場合、途中で動作を停止した端末があったりすると、その後、アクセス毎に即時的discoveryを実行し無駄に時間を消費してしまうため、即時的discoveryは最初の一回のみに制限してみた。
★ちなみに原因不明の動作遅延についてはESP32が原因だった...PCから操作してみたところ全く問題なし。ESP8266のようにESP32も通信処理の遅延がそれなりに起こるようだ。このCPUは何をするにも簡単なんだけど、品質的、電気的、ソフトウェア的に洗練しきれていないように感じる。なので実験用としてはいいかもしれないが実用には使いものにならない。我が家でも一時は8個ぐらい常時稼働してみたことがあったが2年も経過しないうちに3個も壊れてしまったので運用的に問題なさそうな2個を残し全て他のCPUに入れ替えている。個人的な所感ではあるがこのCPUで実用システムを組むことはお勧めできない。と思う。

2018-09-02
複数端末が存在する場合、一回のDiscovery処理では端末の見落としが発生しやすいことがわかりポーリング方式に変更。さらに一定時間間隔(60秒)毎にDiscoveryを繰り返すように変更。追加関数は下記の通り。
下記のどちらかををloop()内で呼び出さなければならない。
handle()
delay(uint32_t ms)
ついでに端末名のほかにMACアドレスでも発見できるように改良。

2018-09-01
ArduinoのEthernetクラスにも対応できるようコンストラクタで指定していた引数をbegin()で指定するように変更。それにともないbegin()で指定した引数は新たなsetTarget()により指定するように変更。
それと、より確実なDiscoveryのためにロジックを若干修正。

2018-08-31
端末を発見できない可能性があったので確実に発見できるように改良。

2018-08-30
TP-Link Smart plug Discovery Protocol に対応し、Kasaアプリの初期設定にて設定した端末名をbegin()にて指定出来るようにした。これに伴い同じ名前を持つ全ての端末を同時制御する仕様に変更。

2018-08-25
TCPクライアント指定をコンストラクタで指定できるように変更。スマートプラグのアドレス指定にIPAdressを使っていたが、より柔軟性のある文字列指定に変更。バイトオーダー変更のためのhtonl()/ntohl()が存在しないボード環境があったので自前の関数に置き換え。同じくvsprintf()が存在しないボード環境があったのでsnprintf()へ変更。
あと、失敗するわけではないが、時々、送信に時間がかかることがあるので試しに受信ループにdelay(1)を入れてみたが状況変わらず。失敗しないということはスマートプラグの反応が遅いだけかな?

【ライブラリの概要説明】

【サンプル・スケッチ】

【ライブラリ】

【関連投稿】
TP-LINK WiFiスマートプラグをESP32(Arduino)から制御する
TP-LINK WiFiスマートプラグをLinux/Windowsから直接制御する
TP-LINK TAPO P100/P105をESP32から直接制御する
TP-LINK TAPO P100/P105をLinux/Windowsから直接制御する

“TP-LINK WiFiスマートプラグをESP32(Arduino)から制御する” への6件の返信

  1. こんにちは.私用でTP-LINKをESP32から操作しようと試みている者です.恥ずかしいことにプログラム初心者でライブラリファイルの製作の仕方などがわからずに公開されているプログラムの扱い方がよくわかりません・・・
    Githubや何らかの手段でcppファイルとともにライブラリをzip形式でダウロードできるようにしていただけないでしょうか?
    検討違いなコメントしていたらすいません.

    1. コメント頂きありがとうございます。
      当サイトでの初コメントです。(/・ω・)/
      さて、ご質問の件ですが、コード量が多く掲載できない場合などはzip等での公開も例外的にはあり得ますが、当サイトはコードが読める人を対象に参考用に公開しているだけですのでGithub等での公開等は今後も予定しておりません。
      公開されているコードをそのまま利用したい場合は【サンプル・スケッチ】や【ライブラリ】のコード上にマウスを移動すると表示される上部のCopyアイコンをクリック&することでクリップボードにコピーすることができるので同じく上部に表示されるファイル名にてそれぞれ保存してください。
      Arduinoの場合、ライブラリは.inoファイルと同じフォルダに保存します。Arduinoのライブラリ形式にはなっていませんがコード的にはライブラリと同じものです。
      以上、参考になれば幸いです。

      1. 返信ありがとうございます。色々と勉強して扱えるように頑張ってみます(´・ω・`)

        1. なんでも初めは大変なものですが時間をかけて取り組めばいつかは目標が達成できるはずです。他の人のコードを読んで理解することも大変な努力が必要となりますがそれが出来るようになると一気に世界が開けてきます。頑張ってみてください。

  2. スマートコンセントをM5(ESP32)等から制御したく、何日もムゾムゾしていました。
    むき出しのリレーユニットでは体裁や安全性が
    ないので、市販品を利用した記事を探していました。
    とっても助かりました。

    1. コメントありがとうございます。
      やはりむき出しは気にはなりますよね...
      ちなみに我が家ではトイレの照明、ポタ電の充放電、クリスマスのイルミネーションの点灯などをスマートコンセントで制御してます。
      何かのお役に立てれば幸いです。

コメントを残す

メールアドレスが公開されることはありません。 が付いている欄は必須項目です

CAPTCHA


このサイトはスパムを低減するために Akismet を使っています。コメントデータの処理方法の詳細はこちらをご覧ください