別の記事にあるようなCO2/湿度/気温モニタリング装置(環境計測エッジデバイス)を設置したので、次はCO2濃度に基づいて換気警報を出すこととしました。設置後にデータを収集し、傾向を見てから湿度との関係も考慮して、と予定していたのですが、いきなり想定していたしきい値を超えるようなことがあったので慌ててCO2単体で作りました。
普段の連絡にTeamsを用いているので、メンバー全員向けチャネルにCO2濃度が一定以上高くなったら換気するようにメッセージをPOST、一定以下になったら大丈夫と通知するメッセージをPOSTするように考えてみました。
モニタリングデータはGoogle Spreadsheet上にあるので、役割を以下のように分けました。
- Google Spreadsheet / Google Apps Script
- 1枚目のシート
- データ記録用
- 2枚目のシート
- 受信時に直前の値と比較し、しきい値を超えた・しきい値を下回ったタイミングを判定
- その判定結果をセルに格納
- 0 = 異常なし(後述するように発報後には-1になる)
- 1 = 異常あり(後述するように発報後には2になる)
- 1枚目のシート
- Teams / Power Automate
- Spreadsheetの値を読み込んで、0 or 1ならばチャネルに投稿
- 同時に発報済みであるように値を-1 or 2に書き換える
Google Apps Scriptの変更
受信時にCO2濃度、湿度・温度チェックをかけるように変更しました。実際には下のソースコード以外に動作確認を定期的に行うスクリプトも用意しています。
var threCO2 = 1000;
var threHumi = 80;
var threTemp = 28;
function doPost(ee) {
var sheet = SpreadsheetApp.getActiveSpreadsheet().getSheets()[0];
var values = JSON.parse(ee.postData.getDataAsString());
// 格納前に直近行を取得
var prevRow = sheet.getLastRow();
var prevHumi = sheet.getRange(prevRow, 2).getValue();
var prevTemp = sheet.getRange(prevRow, 3).getValue();
var prevCO2 = sheet.getRange(prevRow, 4).getValue();
sheet.appendRow([new Date(), values.humi, values.temp, values.co2]);
cO2Check(prevCO2, values.co2);
humiTempCheck(prevHumi, prevTemp, values.humi, values.temp);
var sheet2 = SpreadsheetApp.getActiveSpreadsheet().getSheets()[1];
sheet2.getRange("B7").setValue(values.co2);
sheet2.getRange("B8").setValue(values.humi);
sheet2.getRange("B9").setValue(values.temp);
}
function cO2Check(prevCO2, lastCO2) {
var sheet2 = SpreadsheetApp.getActiveSpreadsheet().getSheets()[1];
if (prevCO2 > threCO2) {
if (lastCO2 <= threCO2) {
// under now
sheet2.getRange("B2").setValue("0");
}
} else {
if (lastCO2 > threCO2) {
// over now
sheet2.getRange("B2").setValue("1");
}
}
sheet2.getRange("B5").setValue((new Date()));
}
function humiTempCheck(prevHumi, prevTemp, lastHumi, lastTemp) {
var sheet2 = SpreadsheetApp.getActiveSpreadsheet().getSheets()[1];
if ((prevHumi > threHumi) || (prevTemp > threTemp)) {
// 直前に湿度か温度が異常値であった場合
if ((lastHumi <= threHumi) && (lastTemp <= threTemp)) {
// 湿度も温度も正常値に入った場合
sheet2.getRange("B3").setValue("0");
}
} else {
if ((lastHumi > threHumi) || (lastTemp > threTemp)) {
// 湿度か温度が異常値になった場合
sheet2.getRange("B3").setValue("1");
}
}
}
Power Automateの導入とプログラム
TeamsにPower Automateを導入します。
「更に追加されたアプリ」から「Power Automate」を追加します。
「+新しいフロー」を作成します。以下のような内容としました。
定期的にCO2値判定結果をSpreadsheetから取得し、発報すべきタイミングで特定のチャネルに換気警報を出しています。
上以外にも特定のチャネルに「CO2」とメッセージが投稿されると現在値を返信するPower Automateも用意しています。