この記事は公開されてから1年以上経過しています。情報が古い可能性がありますので、ご注意ください。
1 はじめに
昨日、下記の記事を投稿しました。そして、Raspberry.Pi上のMonoで利用しようとしたのですが、M2Mqttをうまく動かせませんでした。
pi@raspberrypi:~ $ mono MonoAWSIotSample.exe
Unhandled Exception:
uPLibrary.Networking.M2Mqtt.Exceptions.MqttConnectionException: Exception connecting to the broker ---> System.IO.IOException: The authentication or decryption has failed. ---> System.IO.IOException: The authentication or decryption has failed. ---> Mono.Security.Protocol.Tls.TlsException: The authentication or decryption has failed.
at Mono.Security.Protocol.Tls.RecordProtocol.EndReceiveRecord (System.IAsyncResult asyncResult) [0x00040] in <1d0bb82c94e7435eb09324cf5ef20e36>:0
・・・略
なんとか、このままRaspberryPiで動かしたいということで・・・.NET Coreでコンパイルすると、うまく行ったので、ちょっと紹介させて下さい。
ソースコードは、まったく変更してません。
2 プロジェクト作成
プロジェクトは、.NET Core > アプリ > コンソールアプリケーションから作成します。
プロジェクト名は、DotNetCoreAWSIotSampleとしました。
3 パッケージ追加
NuGetから追加するパッケージは、M2Mqtt及び、 Pit.M2Mqtt の2つです。
4 実装
ソースコードは、前回と全く同じです。
using System;
using System.Text;
using System.Security.Cryptography.X509Certificates;
using uPLibrary.Networking.M2Mqtt;
using uPLibrary.Networking.M2Mqtt.Messages;
namespace MonoAWSIotSample
{
class MainClass
{
const string endpoint = "xxxxxxxx.iot.us-east-1.amazonaws.com";
const string clientCertFile = "MonoAWSIotSample.pfx";
const string clientCertPassword = "xxxxxx";
const string rootCaFile = "root-CA.crt";
const string topic = "sample_topic";
public static void Main(string[] args)
{
var clientCert = new X509Certificate2(clientCertFile, clientCertPassword);
var rootCa = X509Certificate.CreateFromCertFile(rootCaFile);
AWSIot iot = new AWSIot(endpoint, clientCert, rootCa);
// Subscribe
iot.Recv += Recv;
iot.Subscribe(topic);
// Publish
iot.Publish(topic, "DotNetAWSIotSampleからのメッセージ!");
Console.ReadLine();
}
static void Recv(string message)
{
Console.WriteLine(message);
}
}
delegate void RevcHandler(string message);
class AWSIot
{
public event RevcHandler Recv = null;
// AWS IoTでは、TLS1.2ポートが使用されている
private const int BrokerPort = 8883;
MqttClient client;
public AWSIot(string endpoint, X509Certificate2 clientCert, X509Certificate rootCa)
{
client = new MqttClient(endpoint, BrokerPort, true, rootCa, clientCert, MqttSslProtocols.TLSv1_2);
client.Connect("clientid1");
if (client.IsConnected)
{
Console.WriteLine("AWSIot Connected.");
}
client.MqttMsgPublishReceived += MessageReceived;
}
public void Subscribe(string Topic)
{
client.Subscribe(new[] { Topic }, new[] { MqttMsgBase.QOS_LEVEL_AT_LEAST_ONCE });
}
public void Publish(string Topic, string message)
{
client.Publish(Topic, Encoding.UTF8.GetBytes(message));
}
void MessageReceived(object sender, uPLibrary.Networking.M2Mqtt.Messages.MqttMsgPublishEventArgs e)
{
Recv(new String(Encoding.UTF8.GetChars(e.Message)));
}
}
}
5 動作確認
RaspberryPiには、予め .NET Core (2.1)のランタイムをインストールしています。
pi@raspberrypi:~/dotnet_mqtt $ dotnet --info
Host (useful for support):
Version: 2.1.2
Commit: 811c3ce6c0
.NET Core SDKs installed:
No SDKs were found.
.NET Core runtimes installed:
Microsoft.NETCore.App 2.1.2 [/opt/dotnet/shared/Microsoft.NETCore.App]
To install additional .NET Core runtimes or SDKs:
https://aka.ms/dotnet-download
必要なファイルを転送します。
pi@raspberrypi:~/dotnet_mqtt $ ls -la
drwxr-xr-x 2 pi pi 4096 7月 28 21:56 .
drwxr-xr-x 27 pi pi 4096 7月 28 21:20 ..
-rw-r--r-- 1 pi pi 7168 7月 28 21:52 DotNetCoreAWSIotSample.dll
-rw-r--r-- 1 pi pi 146 7月 28 21:23 DotNetCoreAWSIotSample.runtimeconfig.json
-rwxr--r-- 1 pi pi 50688 7月 28 21:53 M2Mqtt.Net.dll
-rw-r--r-- 1 pi pi 3749 7月 28 21:23 MonoAWSIotSample.pfx
-rw-r--r-- 1 pi pi 1758 7月 28 21:23 root-CA.crt
実行している様子です。 AWS Iot Coreのテスト画面で、メッセージのやり取りを確認できます。
pi@raspberrypi:~/dotnet_mqtt $ dotnet DotNetCoreAWSIotSample.dll
6 最後に
.NET Coreだと、あったり動きました。C#でRaspberryPiからAWS IoTできるのは、個人的に超快適です。私だけでしょうか・・・・
7 参考リンク
MQTT Client Library Encyclopedia – M2Mqtt
Visual Studio for Mac
Visual Studio for Mac(C#)でAWS IoTへ接続してみた。