データを収集するためのホームハブとして、 Centerm GI-945シンクライアントを使用しました 。 その利点は、x86アーキテクチャ(atom 1.6 GHz)、5 USB、1Gイーサネット、ミニpcie(wifiカードを挿入)です。 Ubuntu Server 14.04はフラッシュドライブからロードされます。
USB-RS485アダプターを介して、電気メーターが「サーバー」に接続されます。 ポーリングカウンターは、 この例に基づいてPythonでスクリプトを作成します。 スクリプトにはpyModbusライブラリが必要です
ライブラリのインストール
sudo add-apt-repository ppa:fkrull / deadsnakes-python2.7
sudo apt-get update
sudo apt-get upgrade
apt-get -y python-pipのインストール
apt-get install python2.7-dev
pip install -U pymodbus
sudo apt-get update
sudo apt-get upgrade
apt-get -y python-pipのインストール
apt-get install python2.7-dev
pip install -U pymodbus
スクリプトは1分に1回cronを実行し、カウンターからデータ(電圧、電流、電力、エネルギーを考慮)を取得して、 ThingSpeak Webサイトに送信します。
最初に登録する必要があるサイトで、独自のチャネルデータチャネルを作成し、フィールドにfieldsという名前を付けます 。 また、チャネルにデータを書き込むには、 書き込みAPIキーが必要です。
Pythonスクリプトコード
#!/ usr / bin / python2
インポート構造
pymodbus.client.syncをインポートする
インポートbinascii
輸入時間
インポートシステム
urllibをインポートする
def read_float_reg(クライアント、basereg、ユニット= 1):
resp = client.read_input_registers(basereg、2、unit = 1)
resp ==なしの場合:
何も返さない
#仕様によると、レジスタの各ペアが返されました
#IEEE754フロートをエンコードします。最初のレジスターは、
#最上位16ビット、2番目のレジスタは
#最下位16ビット。
return struct.unpack( '> f'、struct.pack( '> HH'、* resp.registers))
def fmt_or_dummy(regfmt、val):
valがNoneの場合:
return '。' * len(regfmt [2]%(0))
regfmt [2]%(val)を返します
def main():
regs = [
#Symbol Reg#フォーマット
(「V:」、0x00、「%6.2f」)、#電圧[V]
(「Curr:」、0x06、「%6.2f」)、#Current [A]
( 'Pact:'、0x0c、 '%6.0f')、#有効電力(「Wirkleistung」)[W]
(「Papp:」、0x12、「%6.0f」)、#皮相電力(「シャイン」)[W]
(「Prea:」、0x18、「%6.0f」)、#無効電力(「ブリンドル」)[W]
(「PF:」、0x1e、「%6.3f」)、#力率[1]
(「Phi:」、0x24、「%6.1f」)、#cos(Phi)? [1]
(「Freq:」、0x46、「%6.2f」)、#ライン周波数[Hz]
(「Wact:」、0x0156、「%6.2f」)、#エネルギー[kWh]
( 'Wrea:'、0x0158、 '%6.2f')、#エネルギー反応[kvarh]
]
cl = pymodbus.client.sync.ModbusSerialClient( 'rtu'、
ポート= '/ dev / ttyUSB0'、ボーレート= 9600、パリティ= 'N'、ストップビット= 1
タイムアウト= 0.8)
値= [regsのregのread_float_reg(cl、reg [1]、単位= 1)]
outvals =リスト(( '' .join([fmt_or_dummy(* t)for t in zip(regs、values)]))。split())
params = urllib.urlencode({'key': 'xxxxxxxxxxxxxxxx'、 'field1':outvals [0]、 'field2':outvals [1]、 'field3':outvals [2]、 'field4':outvals [8] })
f = urllib.urlopen( " api.thingspeak.com/update "、データ= params)
印刷(アウトバル)
sys.stdout.flush()
__name__ == '__main__'の場合:
メイン()
インポート構造
pymodbus.client.syncをインポートする
インポートbinascii
輸入時間
インポートシステム
urllibをインポートする
def read_float_reg(クライアント、basereg、ユニット= 1):
resp = client.read_input_registers(basereg、2、unit = 1)
resp ==なしの場合:
何も返さない
#仕様によると、レジスタの各ペアが返されました
#IEEE754フロートをエンコードします。最初のレジスターは、
#最上位16ビット、2番目のレジスタは
#最下位16ビット。
return struct.unpack( '> f'、struct.pack( '> HH'、* resp.registers))
def fmt_or_dummy(regfmt、val):
valがNoneの場合:
return '。' * len(regfmt [2]%(0))
regfmt [2]%(val)を返します
def main():
regs = [
#Symbol Reg#フォーマット
(「V:」、0x00、「%6.2f」)、#電圧[V]
(「Curr:」、0x06、「%6.2f」)、#Current [A]
( 'Pact:'、0x0c、 '%6.0f')、#有効電力(「Wirkleistung」)[W]
(「Papp:」、0x12、「%6.0f」)、#皮相電力(「シャイン」)[W]
(「Prea:」、0x18、「%6.0f」)、#無効電力(「ブリンドル」)[W]
(「PF:」、0x1e、「%6.3f」)、#力率[1]
(「Phi:」、0x24、「%6.1f」)、#cos(Phi)? [1]
(「Freq:」、0x46、「%6.2f」)、#ライン周波数[Hz]
(「Wact:」、0x0156、「%6.2f」)、#エネルギー[kWh]
( 'Wrea:'、0x0158、 '%6.2f')、#エネルギー反応[kvarh]
]
cl = pymodbus.client.sync.ModbusSerialClient( 'rtu'、
ポート= '/ dev / ttyUSB0'、ボーレート= 9600、パリティ= 'N'、ストップビット= 1
タイムアウト= 0.8)
値= [regsのregのread_float_reg(cl、reg [1]、単位= 1)]
outvals =リスト(( '' .join([fmt_or_dummy(* t)for t in zip(regs、values)]))。split())
params = urllib.urlencode({'key': 'xxxxxxxxxxxxxxxx'、 'field1':outvals [0]、 'field2':outvals [1]、 'field3':outvals [2]、 'field4':outvals [8] })
f = urllib.urlopen( " api.thingspeak.com/update "、データ= params)
印刷(アウトバル)
sys.stdout.flush()
__name__ == '__main__'の場合:
メイン()
スクリプトは使用可能なすべてのパラメーターをカウンターから取得しますが、メインのパラメーターのみがサイトに転送されます。必要に応じて、すべてを転送できます。
結果はすぐにサイトに表示されます(画面にはしばらくの間統計が表示されます。最初の調査では、値を持つポイントは1つだけです)
デフォルトでは、グラフには最新の60個の測定値が表示され、1分に1回ポーリングすると、過去1時間の結果が表示されます。 チャートごとに、表示を構成できます
電圧の場合、10個以上の値を平均し、曲線(スプライン)を平滑化して6時間の統計を設定します。
消費されるエネルギーのグラフは増え続ける曲線であることがわかりますが、1時間、1日、1か月の消費量を確認したいと思います。これには、MATLABエンジンとイベントを時間内に実行する機能に基づいたサイトの分析があります。
時間ごとの統計を収集するために、次のことを行いました。
- 2番目のPowerStatisticチャネルを作成しました。
- Apps-> MATLAB Analysisで 、現在のエネルギー値を取得し、1時間前に値を減算するスクリプトを作成しました。 結果はチャネルフィールドに入力されます。
- Apps- > Time ControlでGetPowerPerHourイベントを作成し、1時間ごとに00分にmatlabスクリプトを実行します。
PowerPerHourスクリプト
カウンターからのデータが配置されるソースチャネルのID。チャネルがプライベートの場合、Read API Keyを指定する必要があります。
readChannelID = 154291;
処理されたデータを記録するための%チャネルID(PowerStatistic)
writeChannelID = 157182;
writeAPIKey = 'xxxxxxxxxxxxxxxxxx';
%%データの読み取り%%
data1 = thingSpeakRead(readChannelID、 'Fields'、4);
data2 = thingSpeakRead(readChannelID、 'Fields'、4、 'NumMinutes'、60);
値= data1-data2(1);
data1の%は、4番目のフィールドから最後の値を読み取ります(エネルギー)
data2の%読み取りは曲がって行われますが、私はまだ別の方法を思いつきません。最後の60個の値が(1時間あたり)読み取られ、最初の値が取得されます
%%データ分析%%
%元の配列の値は小数点以下2桁に丸められるという事実にもかかわらず、何らかの理由で減算の結果は次のようになったため、2桁に丸める必要がありました:0.2700000000000031
analysedData = round(値、2);
%dispはデータのデバッグに使用できます
%disp(analyzedData);
analysedDataにベクトルではなく1つの値がある場合、チャネルの最初のフィールドに書き込まれます。 他のフィールドに書き込むには、たとえば「Fields」(2)を追加します。
%%データの書き込み%%
thingSpeakWrite(writeChannelID、分析されたデータ、 'WriteKey'、writeAPIKey);
readChannelID = 154291;
処理されたデータを記録するための%チャネルID(PowerStatistic)
writeChannelID = 157182;
writeAPIKey = 'xxxxxxxxxxxxxxxxxx';
%%データの読み取り%%
data1 = thingSpeakRead(readChannelID、 'Fields'、4);
data2 = thingSpeakRead(readChannelID、 'Fields'、4、 'NumMinutes'、60);
値= data1-data2(1);
data1の%は、4番目のフィールドから最後の値を読み取ります(エネルギー)
data2の%読み取りは曲がって行われますが、私はまだ別の方法を思いつきません。最後の60個の値が(1時間あたり)読み取られ、最初の値が取得されます
%%データ分析%%
%元の配列の値は小数点以下2桁に丸められるという事実にもかかわらず、何らかの理由で減算の結果は次のようになったため、2桁に丸める必要がありました:0.2700000000000031
analysedData = round(値、2);
%dispはデータのデバッグに使用できます
%disp(analyzedData);
analysedDataにベクトルではなく1つの値がある場合、チャネルの最初のフィールドに書き込まれます。 他のフィールドに書き込むには、たとえば「Fields」(2)を追加します。
%%データの書き込み%%
thingSpeakWrite(writeChannelID、分析されたデータ、 'WriteKey'、writeAPIKey);
サイトに不快な妨害があり、スクリプトを適用するための[ 保存して実行 ]ボタンがあり、 実行するたびにチャネルに書き込みます。したがって、デバッグを完了する前に記録行をコメントアウトすることをお勧めしますが、スクリプトの準備ができていても、開始せずに保存するだけで、スクリプトはすぐにデータを入力しますチャンネルに。 また、チャネルから個々のデータを削除することもできません。 この問題はプロジェクトフォーラムで既に提起されていますが、まだ修正されていません。
スケジュールされた起動設定。スクリプトは1時間ごとに実行されます。 12.00での起動の開始は無視できます。
チャンネルで結果を確認します。
このグラフでは、 タイプ:列が設定に示されており、電力消費量が1時間ごとに表示されます。 ポップアップウィンドウは、12時の消費のピークに対応しています(画面上のカーソルは表示されませんでした)。
1日あたりの統計を収集するスクリプトも同様に機能します。 スクリプトは毎日00:01に実行され、1時間ごとのアーカイブから24の読み取り値を要約します。
PowerPerDayスクリプト
readChannelID = 157182;
readAPIKey = 'zzzzzzzzzzzzzzzzzzzzzzz';
writeChannelID = 157182;
writeAPIKey = 'xxxxxxxxxxxxxxxxxxxx';
%%データの読み取り%%
%チャネルの最初のフィールドから最後の24個の値を読み取ります
data = thingSpeakRead(readChannelID、 'ReadKey'、readAPIKey、 'Fields'、1、 'NumPoints'、24);
%%データ分析%%
合計する
analysedData = sum(data);
%disp(analyzedData);
%%データの書き込み%%
thingSpeakWrite(writeChannelID、分析されたデータ、「WriteKey」、writeAPIKey、「Fields」、2);
readAPIKey = 'zzzzzzzzzzzzzzzzzzzzzzz';
writeChannelID = 157182;
writeAPIKey = 'xxxxxxxxxxxxxxxxxxxx';
%%データの読み取り%%
%チャネルの最初のフィールドから最後の24個の値を読み取ります
data = thingSpeakRead(readChannelID、 'ReadKey'、readAPIKey、 'Fields'、1、 'NumPoints'、24);
%%データ分析%%
合計する
analysedData = sum(data);
%disp(analyzedData);
%%データの書き込み%%
thingSpeakWrite(writeChannelID、分析されたデータ、「WriteKey」、writeAPIKey、「Fields」、2);
ThingSpeakにはAndroidアプリもあります。 最新の値を表示するPocket IoTと、グラフのThingViewが好きでした。 ウィジェットもいくつかありますが、それらはある種の曲線です。
» PowerMeterチャンネル
» PowerStatisticチャネル
おそらくそれだけです。 この記事はチュートリアルのふりをするものではありません。ThingSpeakの機能に精通し始めたばかりなので、追加、コメント、編集は大歓迎です。