概要
このプロジェクトでは、ArduinoのMKRWIFI1010ボードとDFRobotのSEN0287をセットアップして、家庭用排水ポンプの交流電流を監視し、そのオンとオフを追跡します。排水ポンプの状態が変化すると、MKRWIFI1010はWiFiを利用して排水ポンプの状態をIoTデータプラットフォームJEDI OneにHTTPポストします。JEDI Oneは、排水ポンプの状態を遠隔で把握・表示し、時間当たりの排水ポンプが稼働している割合を計算・表示するために使用します。JEDI Oneは、Raspberry Pi 4で動作しています。
ハードウェア
- RASPBERRY PI 4B/4GB
Raspberry PI 4 Model B 4GB SDRAM付き - MKRWIFI1010
ARDUINO MKR WIFI 1010評価ボード - DFRobot SEN0287
SEN0287 5A AC電流センサ
ソフトウェア
- JEDI One
JEDI Oneは、すぐに使えるIoTデータ管理ソフトウェアソリューションです。次のような機能があります。センサ、デバイス、マシンからのデータ収集、直感的なリアルタイムおよび履歴データ、およびシステムビューダッシュボードの構築、データ状況を自動的に監視・対応するルールの作成、電子メールやSMSによるアラート通知の受信などです。 - Arduino
Arduinoは、使いやすいハードウェアとソフトウェアに基づいたオープンソースの電子機器プラットフォームです。
背景
地下室がある多くの住宅でよくある問題は、地下水面の水位が高い、あるいは土台周辺の排水が悪いために、地下室が濡れたり湿ったりすることです。この問題の典型的な解決策は、家の周りにドレンタイルを敷き、排水システムに溜まった水を排水ポンプで汲み上げることです。排水ポンプは、フロート(またはその他の機構)を利用して、水が一定の高さに達するとポンプをオンにし、水が一定の低いレベルまで減少するとオフにする自動排水ポンプが一般的です。
実装
このプロジェクトでは、MKRWIFI1010ボードが交流電流センサボードSEN0287に5V電源を供給し、センサのアナログ出力がボードのA0アナログ入力に配線され、交流電流を測定しています。SEN0287のACカレントトランスは、排水ポンプのAC電源ラインの1つに取り付けられています。以下の回路図は、この回路がどのように配線され実装されているかを示しています。
電気的な接続は以下の通りです。
MKRWIFI1010のピン | 交流電流センサSEN0287のコネクタ |
---|---|
GND | 1 GND |
5 V | 2 Power Input |
A0 | 3 Signal Output |
MKRWIFI1010とセンサSEN0287をセットアップする
1 - MKRWIFI1010にArduinoをセットアップします。リンクGetting started with the MKR WiFi 1010をご参照ください。
2 - アプリケーションに必要なライブラリをインストールします。Arduinoのライブラリマネージャからこれらのライブラリを追加します。
3 - コードウォークスルー(ファイル名:MKR1010wifiACcurrentSEN0287.ino)
初期設定およびWifiネットワークへの接続
#include <Arduino.h>
#include <WiFiNINA.h>
#include <ArduinoHttpClient.h>
#include "arduino_secrets.h"
#include <Wire.h> //this is not needed
#include <ArduinoJson.h> //include Json library
// Create a unique ID for the data from the MKRWIFI1010 running this code
const char* jediID = "MKR1010WiFiSensor_Sump";
///////please enter your sensitive data in the Secret tab/arduino_secrets.h
char ssid[] = SECRET_SSID; // your network SSID (name)
char pass[] = SECRET_PASS; // your network password (use for WPA, or use as key for WEP)
int status = WL_IDLE_STATUS; // the Wifi radio's status
static int wifiConnectTry = 0;
// IP address of server or Raspberry Pi running Machinechat JEDI software
// If you changed the JEDI port number, replace 8100 with the new port
char serverAddress[] = "192.168.1.7"; // server address
int port = 8100;
WiFiClient client;
HttpClient http = HttpClient(client, serverAddress, port);
const int ACPin = A0; //set arduino signal read pin for AC current sensor
#define ACTectionRange 5; //set Non-invasive AC Current Sensor tection range (5A,10A,20A)
// VREF: Analog reference
// For Arduino UNO, Leonardo and mega2560, etc. change VREF to 5
// For Arduino Zero, Due, MKR Family, ESP32, etc. 3V3 controllers, change VREF to 3.3
#define VREF 3.3
unsigned long start, finished, elapsed;
int Istate = 0; //current sensor state 1 = ON, 0 = OFF
int loop_ctr = 0; //counter for wifi connects
AC電流の計算
// routine for reading current from DFRobot code for SEN0287
float readACCurrentValue()
{
float ACCurrtntValue = 0;
float peakVoltage = 0;
float voltageVirtualValue = 0; //Vrms
for (int i = 0; i < 5; i++)
{
peakVoltage += analogRead(ACPin); //read peak voltage
delay(1);
}
peakVoltage = peakVoltage / 5; //average out peak voltage
peakVoltage = peakVoltage - 5.12; //calibrate out 0 current ADC reading (about 5mV)
if (peakVoltage < 0.03) peakVoltage = 0; // zero out 0 current measurement
voltageVirtualValue = peakVoltage * 0.707; //change the peak voltage to the Virtual Value of voltage
/*The circuit is amplified by 2 times, so it is divided by 2.*/
voltageVirtualValue = (voltageVirtualValue / 1024 * VREF ) / 2;
ACCurrtntValue = voltageVirtualValue * ACTectionRange;
return ACCurrtntValue;
}
センサデータをJSON形式で設定し、HTTPポストでJEDI Oneに送信します。
void loop()
{
// prep for sending HTTP post to JEDI One
String postData1; //Json string
StaticJsonDocument <200> doc;
float ACCurrentValue = readACCurrentValue(); //read AC Current Value
Serial.print(ACCurrentValue);
Serial.println(" A");
// try reconnecting if not connected
if (WiFi.status() != WL_CONNECTED) {
Serial.println("not connected to WiFi, try reconnecting");
WiFi.disconnect();
WiFi.end();
delay(5000);
wifiConnect();
}
Serial.print("WiFi status code: ");
Serial.println(WiFi.status());
Serial.print("WiFi reconnect trys = ");
Serial.println(wifiConnectTry);
//check if AC current is ON and current Istate = 0
if ((ACCurrentValue > 0.05) && (Istate == 0)){
digitalWrite(LED_BUILTIN, HIGH);
start = millis();
Istate = 1;
//Following code creates the serialized JSON string to send to JEDI One
//using ArduinoJson library
//StaticJsonDocument <200> doc; //move to start of loop
JsonObject context = doc.createNestedObject("context");
context["target_id"] = String(jediID);
JsonObject data = doc.createNestedObject("data");
data["Isensor"] = Istate;
data["MilliStamp"] = start;
serializeJson(doc, postData1);
Serial.println(postData1); //debug, can be commented out
//format http post to be compatible with JEDI one
String contentType = "application/json";
http.post("/v1/data/mc", contentType, postData1);
// read the status code and body of the response
int statusCode = http.responseStatusCode();
String response = http.responseBody();
Serial.print("Status code: ");
Serial.println(statusCode);
Serial.print("Response: ");
Serial.println(response);
// try disconnecting from server after posting data
http.stop();
Serial.println("disconnect from server");
}
//check if AC current has turned off and current Istate = 1
if ((ACCurrentValue < 0.05) && (Istate == 1)) {
digitalWrite(LED_BUILTIN, LOW);
finished = millis();
elapsed = finished - start;
Istate = 0;
Serial.print("On time = ");
Serial.println(elapsed);
//Following code creates the serialized JSON string to send to JEDI One
//using ArduinoJson library
//StaticJsonDocument <200> doc; //move to start of loop
JsonObject context = doc.createNestedObject("context");
context["target_id"] = String(jediID);
JsonObject data = doc.createNestedObject("data");
data["Isensor"] = Istate;
data["MilliStamp"] = finished;
serializeJson(doc, postData1);
Serial.println(postData1); //debug, can be commented out
//format http post to be compatible with JEDI one
String contentType = "application/json";
http.post("/v1/data/mc", contentType, postData1);
// read the status code and body of the response
int statusCode = http.responseStatusCode();
String response = http.responseBody();
Serial.print("Status code: ");
Serial.println(statusCode);
Serial.print("Response: ");
Serial.println(response);
// try disconnecting from server after posting data
http.stop();
Serial.println("disconnect from server");
}
delay(1000);
}
排水ポンプモニタアプリケーションMKR1010wifiACcurrentSEN0287の最新のソースコードは、以下のリンク先のgithubにあります。
JEDI Oneをセットアップする
1 - machinechat JEDI OneがRaspberry Piにまだインストールされていない場合は、以下をご参照ください。
- Raspberry Pi版JEDI One DK-JEDIONE-RPを入手します。
- Raspberry Pi - Installing JEDI One as a Serviceを参照して、Raspberry Piにインストールしてください。
2 - JEDI Oneルールを設定し、排水ポンプがオンになる1時間あたりの割合をカウントします。
JEDI Oneで「ルール」タブを選択し、「+」を選択して新しいルールを追加し、以下のようにConditionを設定します。データソース「/MKR1010WIFISensor_Sump/Isensor」(注:ソースのリストから「ドラッグ&ドロップ」したもの)と演算子「==」、および値「1」を選択します。
以下のようにActionを設定します。Action Nameを追加し、Action Typeを「Count Events」に設定し、Target IDとMetric Nameに名前をつけ、Counter Resetを「EVERY 1 HOURS」に設定します。
3 - JEDI Oneのダッシュボードをセットアップします。
JEDI Oneで「Dashboards」タブを選択し、「+」を選択して新しいチャートを追加して設定します。
チャートに名前を付け、「Chart Type」を選択し、「Source」(MKR1010WiFiSensor_Sump)を選択し、「Property(Isensor)」を選択し、「Units」を入力、「Refresh Interval(リフレッシュ間隔)」を入力します。完了すると、以下のようなダッシュボードが表示されます。
まとめ
DFRobotのSEN0287交流電流センサとArduinoのハードウェアプラットフォームMKRWIFI1010により、排水ポンプのオン/オフ状態を迅速かつ容易に遠隔監視することができます。センサのデータはWiFiを利用して、Raspberry Pi上で動作するmachinechatのIoTデータ管理ソフトウェアJEDI Oneに簡単に送信し、排水ポンプのデータを追跡して表示します。JEDI Oneでは、設定した時間が経過しても排水ポンプの電源が入らない場合に、メールやSMSで通知する追加アラートを簡単に設定することができます。
参考資料
- Arduino - Getting started with the MKR WiFi 1010
- Getting Started with machinechat’s JEDI One IoT Platform
- DFRobot - Gravity: Analog AC Current Sensor (5A) Product Wiki