Difyがアップデートされて、トリガー機能の追加されました。
本記事ではWebhookトリガーでIoTとLLMの組み合わせを考察してみます。
WebhockトリガーでIoTをサクッと試してみる
今回の構成では、マイコン(M5Stack)を IoT デバイスとして利用し、設備の異常を検知したタイミングで各種センサ値を Dify に送信します。
例えば「異常振動」を検出したら、その時点の加速度や温度などの情報を JSON 形式にまとめ、Dify の Webhook トリガー URL へ HTTP POST で送ります。
Dify は Webhook へのリクエストを受信するとトリガーが発火し、ワークフロー(処理)が起動します。ワークフロー内では受信した JSON を LLM に渡し、状況を要約した レポート(状況・所見・対応案など)を生成し、最終的に Slack の指定チャンネルへ投稿する仕様にしました。
動作確認の様子です。IoTデバイスが異常振動を検知してから暫くすると状況報告レポートが生成されSLACKにレポートが投稿されている様子です。
マイコンとDifyの連携方法
マイコン側のプログラムは、使用するマイコンで異なりま。今回使用するM5StackはWiFi接続やHTTP通信するためのライブラリがあるので比較的簡単に実装できます。以下はWebhockにJSON形式のデータを送信するためのサンプルプログラムです。
#include <M5Unified.h>
#include <WiFi.h>
#include <HTTPClient.h>
// ====== ★ここを書き換える(Wi-Fi設定) ======
const char* WIFI_SSID = "YOUR_SSID"; // 例: 自宅や職場のSSID
const char* WIFI_PASS = "YOUR_PASSWORD"; // 例: Wi-Fiパスワード
// ====== ★ここを書き換える(DifyのWebhook URL) ======
const char* DIFY_WEBHOOK_URL = "http://YOUR_HOST/triggers/webhook-debug/XXXX";
// ====== 送信したいキーワード(指定どおり固定) ======
const char* KEYWORD = "HellowDifyWebhock";
// ---- Wi-Fiに接続する ----
void connectWiFi() {
// Wi-FiをSTA(子機)モードで使う
WiFi.mode(WIFI_STA);
// いったん切断して状態をリセット
WiFi.disconnect(true, true);
delay(300);
Serial.printf("WiFi接続中: %s\n", WIFI_SSID);
WiFi.begin(WIFI_SSID, WIFI_PASS);
// 最大15秒待つ
const uint32_t timeoutMs = 15000;
uint32_t start = millis();
// 接続完了するまで待機(タイムアウトあり)
while (WiFi.status() != WL_CONNECTED && (millis() - start) < timeoutMs) {
delay(500);
Serial.print(".");
}
Serial.println();
// 接続結果を表示
if (WiFi.status() == WL_CONNECTED) {
Serial.print("WiFi接続成功。IP: ");
Serial.println(WiFi.localIP());
} else {
Serial.println("WiFi接続失敗。SSID/PASSを確認してください。");
}
}
// ---- DifyのWebhookへキーワードをPOST送信する ----
void postKeyword() {
// Wi-Fi未接続なら送信しない
if (WiFi.status() != WL_CONNECTED) {
Serial.println("送信中止: Wi-Fi未接続です。");
return;
}
// URLが空なら送信しない
if (DIFY_WEBHOOK_URL == nullptr || strlen(DIFY_WEBHOOK_URL) == 0) {
Serial.println("送信中止: Webhook URLが未設定です。");
return;
}
// 送信データをJSONで整形
// 例: {"keyword":"HellowDifyWebhock"}
String payload = String("{\"keyword\":\"") + KEYWORD + "\"}";
// HTTPクライアント開始
HTTPClient http;
http.begin(DIFY_WEBHOOK_URL);
// JSON送信なので Content-Type を application/json にする
http.addHeader("Content-Type", "application/json");
// 送信内容をログ出力(ブログ用に分かりやすく)
Serial.println("POSTするJSON:");
Serial.println(payload);
// POST送信
int httpCode = http.POST(payload);
// HTTPステータスコード表示(200, 201, 4xx, 5xx など)
Serial.printf("HTTP POST code: %d\n", httpCode);
// レスポンス本文も表示(Dify側の応答確認用)
String response = http.getString();
Serial.println("Response:");
Serial.println(response);
// 終了処理
http.end();
}
void setup() {
// M5初期化(最小)
M5.begin();
// シリアル開始
Serial.begin(115200);
delay(500);
// 1) Wi-Fi接続
connectWiFi();
// 2) 起動時に1回だけキーワード送信
postKeyword();
}
void loop() {
// 何もしない(起動時に1回だけ送信するサンプル)
delay(1000);
}
上記の例では単純に以下のJSONを送信しています。
{"keyword":"HellowDifyWebhock"}
実際、JSONを作っているのは以下のコードです。
const char* KEYWORD = "HellowDifyWebhock";
String payload = String("{\"keyword\":\"") + KEYWORD + "\"}";
実際に送信しているのは以下のコードです。DifyのWebhook URLを指定してHTTPライブラリを利用して送信しています。
// DifyのWebhook URL
const char* DIFY_WEBHOOK_URL = "http://YOUR_HOST/triggers/webhook-debug/XXXX";
// HTTPクライアント開始
HTTPClient http;
http.begin(DIFY_WEBHOOK_URL);
// JSON送信なので Content-Type を application/json にする
http.addHeader("Content-Type", "application/json");
// POST送信
int httpCode = http.POST(payload);
DifyのWebhockトリガーについて説明します。Dify には Webhook トリガーが用意されており、指定した Webhook URL に対して HTTP でリクエスト(JSONなど)を送ると、Dify 側でトリガーが発火してワークフローが実行されます。Webhook URL は、外部(マイコンなど)からデータを送信する 送信先エンドポイントです。
Dify をローカル環境にセルフホストしている場合、管理画面に表示される Webhook URL が localhost になります。上の画像の例では、次のような URL です。
http://localhost/triggers/webhook/xd0S52XwDpC-i3Vda3G5KjX9
ただし、マイコン(別端末)から送信する場合は localhost では届きません。localhost は「その端末自身」を指すため、マイコン側から見ると Dify が動いている PC を指しません。そのため、実際にマイコンから送信するときは、localhost の代わりに Dify が動作している PC の IP アドレスを指定します。
http://<Difyが起動しているPCのIPアドレス>/triggers/webhook/xd0S52XwDpC-i3Vda3G5KjX9
マイコンはこの Webhook URL に対して、HTTP POST などで JSON 形式のデータを送信します。Dify は Webhook URL にリクエストが届くとトリガーが発火し、設定した処理が実行されます。最初の例のように、マイコン側で異常(しきい値超過など)を検知したタイミングで、その時点のセンサ値や設備情報といった状況を JSON 形式で送信できます。Dify は受け取ったデータをトリガーとして処理を開始し、内容を整理したうえで LLM によるレポート(状況の要約、考えられる原因、対応案など)を自動生成することも可能です。
画像付きレポートを作る構成(M5Stack カメラ × Dify × Vision LLM)
今回使用した M5Stack はカメラを搭載しているため、現場の画像を取得できます。
ただし Webhook トリガーに画像データを直接送るのは扱いが難しいため、画像は別経路で受け渡す構成にします。
次のように 画像保存用サーバー(ストレージ)を用意し、マイコンで撮影した画像はまずサーバーへアップロードします。
-
マイコン → 画像サーバー:画像をアップロード(保存)
-
マイコン → Dify Webhook:画像そのものではなく、「どこに保存したか」を示す image_url を JSON で送信
Dify 側では、Webhook で受け取った image_url を使って HTTP リクエストで画像を取得します。具体的には画像サーバーのここに保存したよという情報を次のJSONで送信します。
{"image_url":"<サーバーにアップロードした画像のURL>"}
取得した画像を Vision 対応の LLM に渡すことで、「何が映っているか」「異常が起きていそうか」といった画像の内容を元に、レポート(状況要約・所見・対応案など)を生成することも可能です。

例えば、次のマイコンで取得した画像をサーバーにアップロードします。
HTTPリクエストでJSONの含まれるimage_urlの情報を利用し画像をリクエストしLLMに渡します。
LLMではVision対応のモデルを利用し画像に何が映っているのかを解析させます。
LLMの出力は、SLACKに送信します。LLMに画像が渡され画像に何が映っているのかを解析できていることが確認できます。
まとめ
本記事ではDifyのWebhockトリガーでIoT×LLMの可能性を探りました。IoTデータを単に可視化するのではなく、LLMに解析・要約させてレポート化することで、IoT×LLMの新たな活用可能性が見えてくるのではないでしょうか。もう少し実験を続けたいです。






