はじめに
- Elixirを楽しんでいますか
- SORACOMさんの「Azure IoT Hub と接続する」を参考にAzure IoT Hubにデータを送信してみます
- プロトコルはMQTTを使います
- せっかくなのでウェブチカ1します
Azure IoT Hub と接続する
- まずはSORACOMさんの記事の通りにやってみます
- Elixirでやってみる前にまずは成功体験を積むことにします
- 以下、「Azure IoT Hub と接続する」の見出しごとにコメントしていきます
ステップ 1: Azure IoT Hub を準備する
IoT Hub を作成する
- Azureのコンソール画面の感じが少し異なっているような気がしますがなんとなく、記事を参考に作成できました
IoT Device を作成する
- ここも同じく記事を参考に作成できました
認証情報を確認する
- 「1. 共有アクセスポリシーを利用する」を選択することにしました
- Azure consoleの言語設定を日本語にしている場合は、以下の読み替えをします
記事 | Azureコンソール(日本語) |
---|---|
Settings | 設定 |
Shared access policies | 共有アクセス ポリシー |
ステップ 2: SORACOM Beam を設定する
グループを作成する
- 記載の通り
グループで Beam を設定する
- 基本的に記載の通り
- 認証情報は、以下を入力しました
設定名 | 値 |
---|---|
Access Policy Name | device |
Shared access key | プライマリーキー(or セカンダリキー) |
ステップ 3: Beam を使用して Azure IoT Hub にデータを送信する
デバイスの準備
- 記事の通り、Raspberry Pi 4に
mosquitto-clients
をインストールします
送信されたデータ確認の準備
- ここは私のmacOSでは記事の通りいきませんでした
- 2021/10/19追記:
$ az iot hub monitor-events -n ${iothub-name} -g ${resource-group}
を使うように更新されています 2
- 2021/10/19追記:
- 記事の通り、
IoT Hub Explorer
なるものをインストールして実行したところ以下のエラーが発生しました
$ iothub-explorer monitor-events --login $connection_string
--------
DEPRECATION NOTICE: iothub-explorer will be retired on November 31st, 2018
It has been replaced by the Azure CLI IoT Extension (https://aka.ms/iotcli).
--------
The equivalent command in the Azure CLI is: az iot hub monitor-events
--------
Monitoring events from all devices...
/usr/local/Cellar/nvm/0.38.0/versions/node/v14.17.3/lib/node_modules/iothub-explorer/node_modules/azure-event-hubs/node_modules/azure-iot-common/lib/shared_access_signature.js:45
throw new ReferenceError('Argument \'' + name + '\' is ' + value);
^
-
The equivalent command in the Azure CLI is: az iot hub monitor-events
をたよりに、azをインストールしました - IoT Hub の 共有アクセスポリシー (Shared access policies) の、iothubowner 権限が必要となりますので、プライマリ接続文字列 or セカンダリー接続文字列のどちらかを使います
$ connection_string='HostName=xxxx.azure-devices.net;SharedAccessKeyName=iothubowner;SharedAccessKey=XXXXXXXXXXXXXXXXXXXXX='
$ az iot hub monitor-events --login $connection_string
AK-020の接続
- 「MS2372h-607 をセットアップする」を参考に進めれば3Gに繋がりました
- 以下、Raspberry Pi 4での操作です
pi@raspberrypi: ~$ curl -O https://soracom-files.s3.amazonaws.com/setup_air.sh
pi@raspberrypi: ~$ sudo bash setup_air.sh
pi@raspberrypi: ~$ deviceId=myDevice
pi@raspberrypi: ~$ mosquitto_pub -d -h beam.soracom.io -i $deviceId -t "devices/$deviceId/messages/events/" -m "Hello from SORACOM Beam!" -V mqttv311
- Raspberry Pi 4からAzure IoT Hubにデータを送ることができました
小話
- 「Docker コンテナーで Azure CLI を実行する方法」こちらを進めましたがうまくいきませんでした
- 「Microsoft の目標は、Azure CLI のバグをなくし、使いやすいものにすることです。 バグが見つかった場合は、GitHub で問題を報告していただきますよう、よろしくお願いいたします。」と書いてありましたので報告をしておきました
- https://github.com/Azure/azure-cli/issues/19767
-
az feedback --verbose
を実行すると、問題報告の雛形を作ってくれます - これを大いに活用させてもらいました!
ステップ 4: Azure IoT Hub からのデータを受信する
- 今度はAzure IoT HubからRaspberry Pi 4にデータを送ってみます
- 記事の通りにやるとRaspberry Pi 4で受信を確認できました
あとはここからはいつものように同じことをElixirでやってみます
ElixirでAzure IoT Hub と接続し、Azure IoT Hubから指定された回数分LEDを光らせる
- ウェブチカです
$ mix new hello_mqtt
mix.exs
defp deps do
[
# {:dep_from_hexpm, "~> 0.3.0"},
# {:dep_from_git, git: "https://github.com/elixir-lang/my_dep.git", tag: "0.1.0"}
+ {:tortoise, "~> 0.9"},
+ {:circuits_gpio, "~> 0.4"},
+ {:jason, "~> 1.2"}
]
end
end
$ mix deps.get
MyHandler
-
hello_mqtt/deps/tortoise/lib/tortoise/handler/logger.ex
を参考にしています- というか写しています
- 少し長いですが安心してください
- 95%コピペです
- 変更箇所は、
handle_message/3
関数を変更したのと、do_handle/1
関数を追加しています -
do_handle/1
はやっつけ関数でして、{"cnt": 5}
というようなデータを受け取ったときに、指定されたcnt
回LEDを光らせています
hello_mqtt/lib/hello_mqtt/my_handler.ex
defmodule HelloMqtt.MyHandler do
@moduledoc false
require Logger
use Tortoise.Handler
defstruct []
alias __MODULE__, as: State
def init(_opts) do
Logger.info("Initializing handler")
{:ok, %State{}}
end
def connection(:up, state) do
Logger.info("Connection has been established")
{:ok, state}
end
def connection(:down, state) do
Logger.warn("Connection has been dropped")
{:ok, state}
end
def connection(:terminating, state) do
Logger.warn("Connection is terminating")
{:ok, state}
end
def subscription(:up, topic, state) do
Logger.info("Subscribed to #{topic}")
{:ok, state}
end
def subscription({:warn, [requested: req, accepted: qos]}, topic, state) do
Logger.warn("Subscribed to #{topic}; requested #{req} but got accepted with QoS #{qos}")
{:ok, state}
end
def subscription({:error, reason}, topic, state) do
Logger.error("Error subscribing to #{topic}; #{inspect(reason)}")
{:ok, state}
end
def subscription(:down, topic, state) do
Logger.info("Unsubscribed from #{topic}")
{:ok, state}
end
def handle_message(topic, publish, state) do
Logger.info("#{Enum.join(topic, "/")} #{inspect(publish)}")
do_handle(publish)
{:ok, state}
end
def terminate(reason, _state) do
Logger.warn("Client has been terminated with reason: #{inspect(reason)}")
:ok
end
defp do_handle(publish) do
cnt = Jason.decode!(publish) |> Map.get("cnt")
{:ok, gpio} = Circuits.GPIO.open(25, :output)
1..cnt
|> Enum.each(fn _ ->
Circuits.GPIO.write(gpio, 1)
Process.sleep(1000)
Circuits.GPIO.write(gpio, 0)
Process.sleep(1000)
end)
Circuits.GPIO.close(gpio)
end
end
Run
$ iex -S mix
iex> Tortoise.Supervisor.start_child(
client_id: "myDevice",
handler: {HelloMqtt.MyHandler, []},
server: {Tortoise.Transport.Tcp, host: 'beam.soracom.io', port: 1883},
subscriptions: [{"devices/myDevice/messages/devicebound/#", 0}])
まずはAzure IoT Hubにデータを送ってみます
iex> Tortoise.publish("myDevice", "devices/myDevice/messages/events/", "Hello from the World of Tomorrow !", qos: 0)
-
az iot hub monitor-events
でデータが送られていることを確認できました
Azure IoT Hubからのメッセージを受け取って指定された回数分LEDを光らせてみます
ウェブチカできました
Wrapping Up
-
SORACOMさんの「Azure IoT Hub と接続する」を参考に、ElixirでAzure IoT Hubとの間でデータを送受信することができました
- ついでに私なりのはじめてのウェブチカができました
-
MQTTの通信には、Tortoiseを使いました
- @tuchiro さんの「Elixir製MQTTクライアントtortoiseを使ってみた」を参考にしました
- ありがとうございます!
- 公式ドキュメントの記載内容がわかりやすくてありがたいです!
- $\huge{ありがとうございます!}$
- デバイスとの間でメッセージの送受信ができるようになりましたのでいろいろ楽しみが増えそうです!
- Enjoy Elixir
-
@nishiuchikazuma さんの「NervesにPhoenixを入れてHTTPのGETでLEDをウェブチカ〜準備編1/3〜」によるとウェブチカとは、「とあるURLにアクセスするとNervesにつけているLEDをチカらせることを言ってます」 とのことです。まあこの記事でやっていることもなんとなく雰囲気は似ているということで、ウェブチカの末席に加えさせてください ↩
-
@matsujirushi さんがSORACOMさんに連絡してくださいました 。ありがとうございます。 ↩