Windows と .NET で SORACOM 使おう、というオハナシ

# はじめに
社会人生活 12 年目となりますが、なんだかんだで一番触っているフレームワークは .NET Framework だったりする @ko2a です。

.NET Framework の界隈に近いからか、よく .NET Framework で作られてるシステムを目撃したりしています。
（前職で POS システム保守開発してたり、今だと 3次元 CAD のアドイン開発してたりと）

その割に、 SORACOM と .NET という情報があまり見当たらず悲しいなーと思ったりすることもしばしば。
（実は使っているけどオープンにしてないだけかもしれませんが・・・）

ということで、 .NET から SORACOM サービスを簡単につなげてみたという話を書きたいと思います。

# 前提条件

* SORACOM Air for セルラー でインターネット接続できる Windows PC を用意します。
    * SIM が挿せる端末なら Air SIM をセットしてください
    * なければ USB ドングル などを利用して Air SIM を利用してください。<br>参考： https://soracom.jp/products/module/
* 今回は検証目的で購入した、 [Huawei MS2372h-607](https://soracom.jp/products/module/ms2372h_607/) を使用します。
    * セットアップ方法は [公式ブログの記事](https://blog.soracom.jp/blog/2018/08/17/ms2372/) を参考に。
* 今回は SORACOM Harvest で試してみましたが、 SORACOM Beam / Funnel でも一部いじいじすれば利用可能です。
    * 今回のデモは Harvest + HTTP でしたが、 TCP/UDP の組み合わせも（たぶん）できますよ（試してないけど
* 今回時間がなくて試せていませんが、 .NET Core を利用して macOS/Linux でも開発はできるかもしれません。

# 作ったもの

GitHub に公開しています。
[DotNetSoracomDemo](https://github.com/ko2a/DotNetSoracomDemo)

あくまでデモなので、 Form クラスへ全部べた書きしています。
実際のプロダクト開発するなら、きちんと処理を分けてプログラムを組んでくださいな。

なお、本ソースコードはあくまでデモ用であるため、本コードを参考にして何かトラブルなどあっても責任は負いません。
自己責任でコピペするなり利用してくださいまし。

## 解説

解説するほどのものでもないと思いますが、いちおう簡単に要所について説明を。

* HttpClient を利用したいので追加します

```csharp:FormSoracom.cs
using System.Net.Http;
```

* フォームのメンバーとして HttpClient のインスタンスと SORACOM Harvest のエンドポイントを定義します。

```csharp:FormSoracom.cs
    public partial class FormSoracom : Form
    {
        private static HttpClient client = new HttpClient();
        private const string EndPointHarvest = "http://harvest.soracom.io";
```

* フォームを閉じるときに、 HttpClient のインスタンスを破棄します。

```csharp:FormSoracom.cs
        /// フォームを閉じるときのイベント
        private void FormSoracom_FormClosing(object sender, FormClosingEventArgs e)
        {
            // HTTPクライアントインスタンスを破棄
            client.Dispose();
        }
```

* ボタン押下時にデータを組み立てて Harvest へデータを送ります。PostAsync を利用しているため、ボタン押下のイベントハンドラに async をつけて非同期メソッドとして定義しておきます（あってるかなこれ？

```csharp:FormSoracom.cs
        // Harvestへ送信
        private async void btnSend_ClickAsync(object sender, EventArgs e)
        {
            txtResponse.Text = string.Empty;

            var json = "{\"element1\":\"" + trackBar1.Value.ToString() + "\", \"element2\":\"" + trackBar2.Value.ToString() + "\"}";
            var content = new StringContent(json, Encoding.UTF8, @"application/json");
            var response = await client.PostAsync(EndPointHarvest, content);

            txtResponse.Text = response.ReasonPhrase;
        }
    }
}
```
# 動作

* 送信前。データは当然ありませぬ。
![008.jpg](https://qiita-image-store.s3.amazonaws.com/0/49240/c6b50aaf-33a5-e658-dbbb-1abf50e60bc2.jpeg)

* 1 件送信。element1 と element2 の値を 0 で送信。
![010.jpg](https://qiita-image-store.s3.amazonaws.com/0/49240/d425b221-4dd8-ee3d-6505-96f16432762b.jpeg)

* いくつか値を変えてデータを送信。
![011.jpg](https://qiita-image-store.s3.amazonaws.com/0/49240/df2070c8-57a1-3972-9e7a-b61984e10914.jpeg)

# 注意

Air SIM と WiFi 接続の両方が有効になっていると、WiFi 経由でエンドポイントへアクセスしてしまいエラーとなります。
試すときは Air SIM だけ有効になるように設定をいじいじしてください。

例：
![006.png](https://qiita-image-store.s3.amazonaws.com/0/49240/26b9f168-cfc8-f89e-4281-5d435ce13181.png)

# おわりに
案外簡単に .NET で SORACOM へつなげることができるので、既存で .NET で開発したアプリケーションやシステムを気軽にクラウドへつなげる方法として SORACOM は十分ありなのでは？と試してて実感しました。

最近だと証明書問題で接続障害があったり、ハードウェアを全品回収などありましたが、SIM 自体が認証キーのようなもの＆証明書情報はクラウド側にあるので、何かあってもクラウド側だけで対処できるというのはやはりメリットだなーと。

本当は・・・Windows 10 IoT Core で SORACOM つなげるのを試したかったのですが、arm 版の USB ドングルドライバを見つけれず、Windows 10 IoT Core + .NET + SORACOM というネタは試せずorz
この辺り来年の Advent Calendar で試せたらいいなぁ。