ESP32とラズパイ5をMQTT連携|AM2302の温湿度をSSD1306へ表示【中編:ESP32送信編】

当ページのリンクには広告が含まれています。

前編では、ESP32とラズパイ5をMQTT連携するために、

  • Mosquittoの導入
  • MicroPython環境構築
  • umqtt.simple の準備

などを行い、MQTT通信の土台を整えました。

続いて、AM2302で取得した温湿度データをESP32からMQTT送信していきます。

本記事【中編:ESP32送信編】では、ESP32側コードの作成、MQTT Publishによるデータ送信、実際に送信データを確認した様子などをまとめていきます。

目次

MQTTで温湿度データを送信するコード

それでは、ESP32からAM2302で取得した温湿度データをMQTT送信するサンプルコードを紹介します。

今回は、以下のようなコードをESP32側で動作させました。

import network
import time
import json
import dht
from machine import Pin
from umqtt.simple import MQTTClient

# Wi-Fi設定
SSID = "xxxxxxxxx"
PASSWORD = "xxxxxxxxx"

# MQTT設定
MQTT_BROKER = "192.168.1.10"
CLIENT_ID = "esp32_am2302"
TOPIC = b"sensor/temperature"

# AM2302設定
sensor = dht.DHT22(Pin(26))

# Wi-Fi接続
wifi = network.WLAN(network.STA_IF)
wifi.active(True)

wifi.disconnect() #現在のWi-Fi接続を切断
time.sleep(0.5)
wifi.connect(SSID, PASSWORD)

print("Wi-Fi接続中...")

while not wifi.isconnected():
    time.sleep(1)

print("Wi-Fi接続完了")
print(wifi.ifconfig())

# MQTT接続
client = MQTTClient(CLIENT_ID, MQTT_BROKER)
client.connect()

print("MQTT接続完了")

while True:
    try:
        sensor.measure()

        temperature = sensor.temperature()
        humidity = sensor.humidity()

        payload = {
            "temperature": temperature,
            "humidity": humidity
        }

        message = json.dumps(payload)

        client.publish(TOPIC, message)
        print("送信:", message)

    except Exception as e:
        print("エラー:", e)

    time.sleep(10)

上のコードでは、

  • Wi-Fi接続
  • MQTT Broker接続
  • 温湿度取得
  • JSON形式への変換
  • MQTT Publish

といった処理をやっています。

測定データは温度と湿度をJSON形式でまとめて送信しています。IoTの処理が入ってコード量が多い印象がありますが、役割ごとに見るとそこまで難しくないと思います。

次のセクションで、コードの各部分の内容を簡単に確認していきます。

コードの内容を簡単に解説

ライブラリの読み込み

まず、必要なライブラリをインポートします。それぞれの役割は以下のとおりです。

各ライブラリの役割
  • network :Wi-Fi接続
  • time :待ち時間処理
  • json :JSONデータ作成
  • dht :AM2302制御
  • machine.Pin :GPIO制御
  • MQTTClient :MQTT通信

MQTTClient は、前記事でESP32内部へ配置した umqtt.simple から読み込んでいます。

パラメータ設定とAM2302初期化

各種パラメータに値を設定すると共に、AM2302の初期化を行います。

Wi-Fi設定

接続するWi-Fi情報を設定しています。ここは自宅Wi-Fi環境に合わせて変更してください。

SSID = "xxxxxxxxx"
PASSWORD = "xxxxxxxxx"

MQTT Broker設定

MQTT_BROKER = "192.168.x.xx"
CLIENT_ID = "esp32_am2302"
TOPIC = b"sensor/temperature"
  • MQTT_BROKER → ラズパイ5のIPアドレスを指定します。
  • CLIENT_ID → MQTT接続時の識別名です。複数ESP32を接続する場合は、それぞれ異なる名前にします。
  • TOPIC → MQTT通信のトピック名です。
    今回は、

    sensor/temperature

    というトピックに温湿度データを送信します。

AM2302の初期化

GPIO26に接続したAM2302を初期化します。

sensor = dht.DHT22(Pin(26))

GPIO番号は実際の配線に合わせて変更してください。

Wi-Fiに接続

ESP32をWi-Fiに接続します。

wifi = network.WLAN(network.STA_IF)
wifi.active(True)

wifi.disconnect()
time.sleep(0.5)
wifi.connect(SSID, PASSWORD)

while not wifi.isconnected():
    time.sleep(1)

Wi-Fi接続時に「wifi internal error」が発生することがあったため、以下のように一度切断処理(ウェイト付)を入れて対策しました。

wifi.disconnect()
time.sleep(0.5)

ESP32は再起動直後などにWi-Fi状態が不安定になることがあるようで、一度接続状態をリセットすることで改善する場合があるようです。

当方の環境ではこれで安定して接続するようになりましたが、環境に応じて試行錯誤が必要かもしれません。

MQTT Brokerに接続

Wi-Fi接続後、MQTT Brokerへ接続します。

client = MQTTClient(CLIENT_ID, MQTT_BROKER)
client.connect()

ここでラズパイ5上のMosquittoへ接続しています。

温湿度の取得→送信の繰り返し

while文で、以下のデータ取得と送信を繰り返し行います。

温湿度データの取得

AM2302から温湿度データを取得します。取得した値は、温度と湿度に分けて変数に保存します。

sensor.measure()

temperature = sensor.temperature()
humidity = sensor.humidity()

さらに、以下のようにJSON形式に変換します。JSON形式にしておくことで、後からデータ項目を増やしやすくなります。

payload = {
    "temperature": temperature,
    "humidity": humidity
}

message = json.dumps(payload)

MQTTでデータ送信

測定データをMQTTで送信(publish)します。このとき、今回のデータのトピックも指定しています。

client.publish(TOPIC, message)

最後にtime.sleep()を入れて、5秒ごとにデータ送信を繰り返しています。

送信間隔は用途に合わせて変更可能です。ただ、あまり短くするとWi-Fi通信量やBroker負荷が増えてしまうので、適宜調整してください。

例外処理

Wi-Fi切断やセンサー読み取り失敗時に原因確認しやすくなるため、簡単な例外処理も追加しています。

except Exception as e:
    print("エラー:", e)

実際に動かしてみた

いよいよ、上で紹介したESP32のコードを実際に動作させます。

ラズパイ5を準備

まずは、ラズパイ5のmosquittoを動作状態にしておきます。

前回の記事で説明した環境構築が完了してそのままの状態なら問題ありません。

そうでなければ、ラズパイ5を起動してターミナルから

systemctl status mosquitto

と入力し、mosquittoがactiveになっていることを確認しておきます。

Thonnyから実行

冒頭で紹介したコードをThonnyのエディタ部分に貼り付け、Tonnyの実行ボタンを押すと実行されます。

実際に試したところ、最初は

OSError: [Errno 104] ECONNRESET

が発生し、ESP32からMQTT接続できませんでした。

そこで、前編で説明したようにMosquitto側のローカル接続制限を解除してみました。

そして再度試したところ…動作しました!Thonnyのシェルに「MQTT接続完了」と表示され、続いて温湿度データの値が5秒ごとに更新されていきます。

定期的にデータをpublishしているようです。

ラズパイ5側の受信確認はこれからですが、ひとまずMQTTでデータを送信するところまでは確認できました。

コードをmain.pyとして保存

今後コードを自動的に開始させるために、ESP32内部に「main.py」として保存しておきます。

main.pyとして保存することで、ESP32が起動したときに自動的にコードが開始されます。

まとめ

今回は、ESP32とAM2302を使って取得した温湿度データを、MQTTでラズパイ5へ送信してみました。

実際にやってみると、

  • Wi-Fi接続
  • MQTT Broker接続
  • Topic指定
  • Publish処理

のように処理が一気に増えて、ESP32がIoT対応デバイスとして動作している感覚が強くなってきましたね。

次回の【後編:ラズパイ表示編】では、MQTTで受信した温湿度データをSSD1306へ表示し、リアルタイムで更新される小型IoTモニタを作成していきます。

目次