
今年はおそろしく暑いですね。寝るときもエアコンが必須です。
ただ、寝てる最中にエアコンが冷やしすぎてしまったりして体に悪いので、設定温度を微調整したいなと思いました。
せっかく自宅には複数台Remo mini 2が置いてあるので、まずは寝ている最中の記録を取ることで適正な設定値を検討するのに役立ててみようと思いました。
これはなに
Nature Remo Cloud APIから室温を取得してGoogleSpreadSheetに記録するスクリプトです。
手順
トークンの取得
トークンをこちらから取得します。
取得したトークンを控えます。
このトークンは外部に漏れないように気をつけて管理してください。
悪用されると自宅の家電を色々操作されたりします。
プロジェクトの作成
$ npm init -y
モジュールの追加
開発自体はローカルで行いつつGitでバージョン管理もしたかったのでclaspを導入します。
併せてVSCodeで補完などができると便利なのでtypes/google-apps-script
も導入しておきます。
ちなみにTypeScriptよくわかってません、なんとなくで書いてます、ご容赦ください。
$ npm install @google/clasp
added 245 packages, and audited 246 packages in 14s
61 packages are looking for funding
run `npm fund` for details
found 0 vulnerabilities
$ npm install @types/google-apps-script
added 1 package, and audited 247 packages in 2s
61 packages are looking for funding
run `npm fund` for details
found 0 vulnerabilities
Googleアカウントの認証
ログイン用のコマンドを実行します。
めちゃくちゃ長いURLがプロンプトに発行されるのでブラウザでアクセスし、認証させるアカウントを選んで先に進みます。
権限の認可の画面に移るので許可
をして先に進みます。
認証コードが発行されるので元のコマンドのプロンプトに入力すれば認証が完了します。
$ npx clasp login --no-localhost
Warning: You seem to already be logged in *globally*. You have a ~/.clasprc.json
Logging in globally…
🔑 Authorize clasp by visiting this url:
https://accounts.google.com/o/oauth2/v2/auth?hogehogehogehoge
Enter the code from that page here:
なお、認証した結果はホームディレクトリに.clasprc.json
として保存されます。このファイルも大切なので外部に漏れないようにしましょう。
GASプロジェクトの作成
claspを使用してプロジェクトを作成します。
コマンドを実行するとスクリプトを紐付けるサービスを聞かれます。今回はスプレッドシートを利用するのでsheets
を選択します。
この段階で空のスプレッドシートがGoogleドライブに、空のプロジェクトがApps Scriptに作成されています。
$ npx clasp create
? Create which script? sheets
Created new Google Sheet: https://drive.google.com/open?id=xxxx
Created new Google Sheets Add-on script: https://script.google.com/d/xxx/edit
タイムゾーンの設定
このままだとプロジェクトの設定が日本時刻になっていないのでタイムゾーンの設定を変更します。
appsscript.jsonで管理されているので変更します。
{
"timeZone": "Asia/Tokyo",
"dependencies": {},
"exceptionLogging": "STACKDRIVER",
"runtimeVersion": "V8"
}
natureのトークンをスクリプトプロパティに登録
スクリプト内にトークンをベタ書きするのはセキュリティの観点で良くないのでGASのスクリプトプロパティを利用します。
GASのプロジェクトの設定からスクリプトプロパティを登録します。
プロパティ名はNatureToken
として、値には最初に取得したトークンを入れます。
これでこれから作成するコードから値を参照することができます。
コード
以下のコードをmain.ts
として保存します。
データを書き込むシート名はdata
となっています。スプレッドシートがまっさらでも必要なものは実行すれば自分で作ってくれるようになっています。
const dataSheetName = "data"
function get_token() {
//nature token
var token = PropertiesService.getScriptProperties().getProperty('NatureToken')
return token
}
function natureApiGetRequest(api: string): [] {
const url: string = 'https://api.nature.global' + api
const token = get_token()
let params = {
'method': 'get',
'accept': 'application/json',
'headers': {
'Authorization': 'Bearer ' + token
}
}
let response = UrlFetchApp.fetch(url, params).getContentText()
return JSON.parse(response)
}
function isSheetExists(sheetName: string): boolean {
let ss = SpreadsheetApp.getActiveSpreadsheet();
let allSheets = ss.getSheets()
for (let i = 0; i < allSheets.length; i++) {
let val = (allSheets[i].getName())
if (val === sheetName) {
return true
}
}
return false
}
function addSheet() {
let ss = SpreadsheetApp.getActiveSpreadsheet();
let rc = isSheetExists(dataSheetName)
if (rc === false) {
ss.insertSheet(dataSheetName)
}
}
function outputData2Sheet(data: [], execdate) {
let ss = SpreadsheetApp.getActiveSpreadsheet()
let sheet = ss.getSheetByName(dataSheetName)
let titles = []
console.log(execdate)
console.log(data)
sheet.getRange("A1").setValue("日時")
let lc = sheet.getLastColumn()
let addrow = sheet.getLastRow() + 1
if (lc > 1) {
let titles = sheet.getRange(1, 2, 1, lc - 1).getValues()[0]
console.log(titles)
}
for (let i = 0; i < data.length; i++) {
let title = data[i].name
let teval = data[i].newest_events.te.val
let timestr = Utilities.formatDate(execdate, 'JST', 'yyyy-MM-dd HH:mm:ss')
let colnum = i + 2
//書き込む列を決める
if (titles.length > 1) {
let num = titles.indexOf(title)
if (num >= 0) {
let colnum = num + 2
} else {
let colnum = lc + 1
lc++
}
}
//タイトル行の生成
sheet.getRange(1, colnum).setValue(title)
sheet.getRange(addrow, 1).setValue(timestr)
sheet.getRange(addrow, colnum).setValue(teval)
}
}
function main() {
const api = '/1/devices'
//APIからデータを取得
let response = natureApiGetRequest(api)
//データ取得した日時を取得
let execdate = new Date()
//必要ならスプレッドシートにシートを作成
addSheet()
//シートにデータを書き込み
outputData2Sheet(response, execdate)
}
デプロイ
ファイルをプロジェクトにアップロードします。
$ npx clasp push
実行
GASのプロジェクト画面からmain
関数を実行します。
途中でGoogleから権限を求められるので許可しましょう。
スプレッドシートを確認すると、日時と各remoの名前を見出しとし、それぞれの下にデータ取得日時と室温が記録されます。
あとはプロジェクトを定期的に実行するように設定すれば自動でデータが追加されてきます。
よしなにグラフ化するなどして、快適に過ごせるように空調の設定を見直すなどしましょう。
コメント