React と MQTT.js SDK を使ったデプロイメントへの接続
本記事では、React フレームワーク上で構築されたウェブアプリケーションにおいて MQTT.js を使用し、クライアントと MQTT ブローカー間の接続、サブスクライブ、メッセージ送受信、サブスクライブ解除などの機能を実装する方法を主に紹介します。
前提条件
MQTT ブローカーのデプロイ
- EMQX が提供する無料のパブリック MQTT ブローカーを利用できます。このサービスはEMQX プラットフォームを基に作成されています。ブローカーへのアクセス情報は以下の通りです:
- アドレス:broker.emqx.io
- WebSocket ポート:8083
- TLS/SSL 対応 WebSocket ポート:8084
- また、独自の MQTT ブローカーを作成することも可能です。デプロイメントが稼働状態になった後、デプロイメント概要ページで接続情報を確認できます。後のクライアント接続段階で必要となるユーザー名とパスワードは、アクセス制御 -> 認証 から設定可能です。
React アプリケーションの作成
参考リンク:https://reactjs.org/docs/getting-started.html
Create React App
を使った新規 React アプリケーションの作成shellnpx create-react-app react-mqtt-test
TypeScript を使用する場合は、コマンドの末尾に
--template typescript
パラメータを追加します。shellnpx create-react-app react-mqtt-test --template typescript
さらに、React プロジェクトに必要な TypeScript 型ライブラリを追加します。
shellnpm install --save typescript @types/node @types/react @types/react-dom @types/jest # または yarn add typescript @types/node @types/react @types/react-dom @types/jest
TypeScript の使用は本記事の例の主題ではありませんが、必要に応じて作成例や完全なコード例を参考にして TypeScript 機能を追加できます。
CDN 経由でのインポート
html<script crossorigin src="https://unpkg.com/react@16/umd/react.production.min.js"></script> <script crossorigin src="https://unpkg.com/react-dom@16/umd/react-dom.production.min.js"></script>
依存関係のインストール
MQTT.js は、JavaScript で書かれた MQTT プロトコル用の完全オープンソースのクライアントサイドライブラリで、Node.js とブラウザの両方で利用可能です。MQTT.js
の詳細や使い方は MQTT.js GitHub をご参照ください。
MQTT.js は NPM または Yarn でインストール可能で、CDN や相対パス経由でのインポートも可能です。本例では NPM コマンドによるインストールを行います。CDN 経由で React を使用するプロジェクトには直接ファイルをインポートする方法が適しています。
コマンドラインから npm または yarn のいずれかでインストール
shellnpm install mqtt --save # または yarn add mqtt
CDN 経由でのインポート
html<script src="https://unpkg.com/mqtt/dist/mqtt.min.js"></script>
ローカルにダウンロードし、相対パスでインポート
html<script src="/your/path/to/mqtt.min.js"></script>
WebSocket ポートでの接続
クライアント ID、ユーザー名、パスワードを以下のように設定できます。クライアント ID は一意である必要があります。
const clientId = "emqx_react_" + Math.random().toString(16).substring(2, 8);
const username = "emqx_test";
const password = "emqx_test";
以下のコードでクライアントと MQTT ブローカー間の接続を確立できます。
const client = mqtt.connect("ws://broker.emqx.io:8083/mqtt", {
clientId,
username,
password,
// ...その他のオプション
});
WebSocket セキュアポートでの接続
TLS/SSL 暗号化が有効な場合、接続のパラメーターオプションは WebSocket ポート経由の接続と同じですが、プロトコルを wss
に変更し、正しいポート番号に合わせる必要があります。
以下のコードでクライアントと MQTT ブローカー間の接続を確立できます。
const client = mqtt.connect("wss://broker.emqx.io:8084/mqtt", {
clientId,
username,
password,
// ...その他のオプション
});
サブスクライブとパブリッシュ
トピックのサブスクライブ
サブスクライブするトピックと対応するQoSレベルを指定します。
const mqttSub = (subscription) => {
if (client) {
const { topic, qos } = subscription
client.subscribe(topic, { qos }, (error) => {
if (error) {
console.log('Subscribe to topics error', error)
return
}
console.log(`Subscribe to topics: ${topic}`)
setIsSub(true)
})
}
}
トピックのサブスクライブ解除
以下のコードで、サブスクライブ解除するトピックと対応する QoS レベルを指定して解除できます。
const mqttUnSub = (subscription) => {
if (client) {
const { topic, qos } = subscription
client.unsubscribe(topic, { qos }, (error) => {
if (error) {
console.log('Unsubscribe error', error)
return
}
console.log(`unsubscribed topic: ${topic}`)
setIsSub(false)
})
}
}
メッセージのパブリッシュ
メッセージをパブリッシュする際は、MQTT ブローカーに対象のトピックとメッセージ内容を渡す必要があります。
const mqttPublish = (context) => {
if (client) {
const { topic, qos, payload } = context;
client.publish(topic, payload, { qos }, (error) => {
if (error) {
console.log("Publish error: ", error);
}
});
}
};
メッセージの受信
以下のコードはメッセージイベントを監視し、メッセージ受信時に受信したメッセージとトピックをコンソールに出力します。
client.on("message", (topic: string, message) => {
console.log(`received message: ${message} from topic: ${topic}`);
});
MQTT ブローカーからの切断
クライアントをブローカーから切断するには、以下のコードを使用します。
const mqttDisconnect = () => {
if (client.connected) {
try {
client.end(false, () => {
setConnectStatus('Connect')
console.log('disconnected successfully')
})
} catch (error) {
console.log('disconnect error:', error)
}
}
}
上記は主要なコードスニペットの一部のみを示しています。完全なプロジェクトコードは MQTT Client - React をご参照ください。ダウンロードして実際に試すことが可能です。
接続のテスト
React を使って接続作成、トピックのサブスクライブ、メッセージの送受信、サブスクライブ解除、切断ができる簡単なブラウザアプリケーションを作成しました。
別のクライアントとして MQTT 5.0 クライアントツール - MQTTX を使い、メッセージの送受信テストを行います。
MQTTX はブラウザ側からのメッセージを正常に受信できることが確認でき、MQTTX からトピックへメッセージ送信した際の様子も確認できます。
FAQ
自己署名証明書の使い方は?双方向 TLS/SSL 認証は使えますか?
ブラウザの制限により、現時点ではサポートされていません。詳細は MQTT.js の issue をご参照ください:ブラウザでの TLS/SSL 双方向認証接続の使い方、および Node.js では双方向認証可能だがブラウザは非対応。
まとめ
本記事では、React プロジェクト内で MQTT 接続を作成し、クライアントと MQTT サーバー間でのサブスクライブ、メッセージパブリッシュ、サブスクライブ解除、切断のシナリオをシミュレーションしました。
React v18.2.0 を使用しているため、例示コードは Hook コンポーネント機能を用いています。必要に応じて、完全な例の ClassMqtt
コンポーネントを参照し、クラスコンポーネント機能を使ったプロジェクト構築も可能です。
完全なサンプルソースコードは MQTT Client - React ページからダウンロード可能です。また、他言語でのデモ例も MQTT Client example ページで多数公開していますので、ぜひご覧ください。