Initial mqtt version

This commit is contained in:
Magnus Persson 2022-01-11 23:23:43 +01:00
parent a703add227
commit a83a74b5a4
9 changed files with 234 additions and 80 deletions

View File

@ -107,14 +107,14 @@
<form action="/api/config/device" method="post"> <form action="/api/config/device" method="post">
<input type="text" name="id" id="id1" hidden> <input type="text" name="id" id="id1" hidden>
<div class="form-group row"> <div class="form-group row">
<label for="mdns" class="col-sm-4 col-form-label">Device name:</label> <label for="mdns" class="col-sm-3 col-form-label">Device name:</label>
<div class="col-sm-8"> <div class="col-sm-9">
<input type="text" maxlength="12" class="form-control" name="mdns" id="mdns"> <input type="text" maxlength="12" class="form-control" name="mdns" id="mdns">
</div> </div>
</div> </div>
<fieldset class="form-group row"> <fieldset class="form-group row">
<legend class="col-form-label col-sm-4 float-sm-left pt-0">Temperature Format:</legend> <legend class="col-form-label col-sm-3 float-sm-left pt-0">Temperature Format:</legend>
<div class="col-sm-8"> <div class="col-sm-6">
<div class="form-check"> <div class="form-check">
<input class="form-check-input" type="radio" name="temp-format" id="temp-format-c" value="C" checked> <input class="form-check-input" type="radio" name="temp-format" id="temp-format-c" value="C" checked>
<label class="form-check-label" for="temp-format-c"> <label class="form-check-label" for="temp-format-c">
@ -130,14 +130,14 @@
</div> </div>
</fieldset> </fieldset>
<div class="form-group row"> <div class="form-group row">
<label for="sleep-interval" class="col-sm-4 col-form-label">Interval (seconds):</label> <label for="sleep-interval" class="col-sm-3 col-form-label">Interval (seconds):</label>
<div class="col-sm-4"> <div class="col-sm-2">
<input type="number" min="10" max="3600" class="form-control" name="sleep-interval" id="sleep-interval"> <input type="number" min="10" max="3600" class="form-control" name="sleep-interval" id="sleep-interval">
</div> </div>
<label for="sleep-interval" class="col-sm-4 col-form-label" id="sleep-interval-info"></label> <label for="sleep-interval" class="col-sm-3 col-form-label" id="sleep-interval-info"></label>
</div> </div>
<div class="form-group row"> <div class="form-group row">
<div class="col-sm-8 offset-sm-4"> <div class="col-sm-8 offset-sm-3">
<button type="submit" class="btn btn-primary" id="device-btn">Save</button> <button type="submit" class="btn btn-primary" id="device-btn">Save</button>
</div> </div>
</div> </div>
@ -146,10 +146,10 @@
<hr class="my-2"> <hr class="my-2">
<div class="form-group row"> <div class="form-group row">
<label for="calibrate-btn" class="col-sm-4 col-form-label">Current calibration values:</label> <label for="calibrate-btn" class="col-sm-3 col-form-label">Current calibration values:</label>
<label for="calibrate-btn" class="col-sm-4 col-form-label" id="gyro-calibration-data">Loading...</label> <label for="calibrate-btn" class="col-sm-3 col-form-label" id="gyro-calibration-data">Loading...</label>
<label for="gyro-calibration-data" class="col-sm-4 col-form-label" id="angle">Loading...</label> <label for="gyro-calibration-data" class="col-sm-3 col-form-label" id="angle">Loading...</label>
<div class="col-sm-8 offset-sm-4"> <div class="col-sm-8 offset-sm-3">
<button type="button" class="btn btn-warning" id="calibrate-btn">Calibrate device</button> <button type="button" class="btn btn-warning" id="calibrate-btn">Calibrate device</button>
</div> </div>
</div> </div>
@ -171,14 +171,14 @@
<form action="/api/config/push" method="post"> <form action="/api/config/push" method="post">
<input type="text" name="id" id="id2" hidden> <input type="text" name="id" id="id2" hidden>
<div class="form-group row"> <div class="form-group row">
<label for="http-push" class="col-sm-4 col-form-label">Http URL 1:</label> <label for="http-push" class="col-sm-2 col-form-label">Http URL 1:</label>
<div class="col-sm-8"> <div class="col-sm-10">
<input type="url" maxlength="100" class="form-control" name="http-push" id="http-push"> <input type="url" maxlength="100" class="form-control" name="http-push" id="http-push">
</div> </div>
</div> </div>
<div class="form-group row"> <div class="form-group row">
<label for="http-push2" class="col-sm-4 col-form-label">Http URL 2:</label> <label for="http-push2" class="col-sm-2 col-form-label">Http URL 2:</label>
<div class="col-sm-8"> <div class="col-sm-10">
<input type="url" maxlength="100" class="form-control" name="http-push2" id="http-push2"> <input type="url" maxlength="100" class="form-control" name="http-push2" id="http-push2">
</div> </div>
</div> </div>
@ -186,8 +186,8 @@
<hr class="my-2"> <hr class="my-2">
<div class="form-group row"> <div class="form-group row">
<label for="inputBrewfatherPush" class="col-sm-4 col-form-label">Brewfather URL:</label> <label for="inputBrewfatherPush" class="col-sm-2 col-form-label">Brewfather URL:</label>
<div class="col-sm-8"> <div class="col-sm-10">
<input type="url" maxlength="100" class="form-control" name="brewfather-push" id="brewfather-push"> <input type="url" maxlength="100" class="form-control" name="brewfather-push" id="brewfather-push">
</div> </div>
</div> </div>
@ -195,31 +195,61 @@
<hr class="my-2"> <hr class="my-2">
<div class="form-group row"> <div class="form-group row">
<label for="influxdb2-push" class="col-sm-4 col-form-label">InfluxDB v2 URL:</label> <label for="influxdb2-push" class="col-sm-2 col-form-label">InfluxDB v2 URL:</label>
<div class="col-sm-8"> <div class="col-sm-6">
<input type="url" maxlength="100" class="form-control" name="influxdb2-push" id="influxdb2-push"> <input type="url" maxlength="40" class="form-control" name="influxdb2-push" id="influxdb2-push">
</div> </div>
</div> </div>
<div class="form-group row"> <div class="form-group row">
<label for="influxdb2-org" class="col-sm-4 col-form-label">InfluxDB v2 Organisation:</label> <label for="influxdb2-org" class="col-sm-2 col-form-label">InfluxDB v2 Org:</label>
<div class="col-sm-8"> <div class="col-sm-4">
<input type="text" maxlength="50" class="form-control" name="influxdb2-org" id="influxdb2-org"> <input type="text" maxlength="50" class="form-control" name="influxdb2-org" id="influxdb2-org">
</div> </div>
</div> </div>
<div class="form-group row"> <div class="form-group row">
<label for="influxdb2-bucket" class="col-sm-4 col-form-label">InfluxDB v2 Bucket:</label> <label for="influxdb2-bucket" class="col-sm-2 col-form-label">InfluxDB v2 Bucket:</label>
<div class="col-sm-8"> <div class="col-sm-4">
<input type="text" maxlength="50" class="form-control" name="influxdb2-bucket" id="influxdb2-bucket"> <input type="text" maxlength="50" class="form-control" name="influxdb2-bucket" id="influxdb2-bucket">
</div> </div>
</div> </div>
<div class="form-group row"> <div class="form-group row">
<label for="influxdb2-auth" class="col-sm-4 col-form-label">InfluxDB v2 Auth. Token:</label> </div>
<div class="col-sm-8"> <div class="form-group row">
<label for="influxdb2-auth" class="col-sm-2 col-form-label">InfluxDB v2 Auth:</label>
<div class="col-sm-4">
<input type="text" maxlength="100" class="form-control" name="influxdb2-auth" id="influxdb2-auth"> <input type="text" maxlength="100" class="form-control" name="influxdb2-auth" id="influxdb2-auth">
</div> </div>
</div> </div>
<hr class="my-2">
<div class="form-group row"> <div class="form-group row">
<div class="col-sm-8 offset-sm-4"> <label for="mqtt-push" class="col-sm-2 col-form-label">MQTT Server:</label>
<div class="col-sm-4">
<input type="url" maxlength="40" class="form-control" name="mqtt-push" id="mqtt-push">
</div>
</div>
<div class="form-group row">
<label for="mqtt-topic" class="col-sm-2 col-form-label">MQTT Topic:</label>
<div class="col-sm-4">
<input type="text" maxlength="30" class="form-control" name="mqtt-topic" id="mqtt-topic">
</div>
</div>
<div class="form-group row">
<label for="mqtt-user" class="col-sm-2 col-form-label">MQTT User:</label>
<div class="col-sm-4">
<input type="text" maxlength="20" class="form-control" name="mqtt-user" id="mqtt-user">
</div>
</div>
<div class="form-group row">
<label for="mqtt-pass" class="col-sm-2 col-form-label">MQTT Password:</label>
<div class="col-sm-4">
<input type="text" maxlength="20" class="form-control" name="mqtt-pass" id="mqtt-pass">
</div>
</div>
<div class="form-group row">
<div class="col-sm-8 offset-sm-2">
<button type="submit" class="btn btn-primary" id="push-btn">Save</button> <button type="submit" class="btn btn-primary" id="push-btn">Save</button>
</div> </div>
</div> </div>
@ -241,14 +271,13 @@
<form action="/api/config/gravity" method="post"> <form action="/api/config/gravity" method="post">
<input type="text" name="id" id="id3" hidden> <input type="text" name="id" id="id3" hidden>
<div class="form-group row"> <div class="form-group row">
<label for="gravity-formula" class="col-sm-4 col-form-label">Formula</label> <label for="gravity-formula" class="col-sm-2 col-form-label">Formula</label>
<div class="col-sm-8"> <div class="col-sm-10">
<input type="text" maxlength="200" class="form-control" name="gravity-formula" id="gravity-formula"> <input type="text" maxlength="200" class="form-control" name="gravity-formula" id="gravity-formula">
</div> </div>
</div> </div>
<label for="gravity-formula"" class="col-sm-8 offset-sm-4 col-form-label" id="gravity">Loading...</label>
<div class="form-group row"> <div class="form-group row">
<div class="col-sm-8 offset-sm-4"> <div class="col-sm-4 offset-sm-2">
<div class="form-check"> <div class="form-check">
<input class="form-check-input" type="checkbox" name="gravity-temp-adjustment" id="gravity-temp-adjustment"> <input class="form-check-input" type="checkbox" name="gravity-temp-adjustment" id="gravity-temp-adjustment">
<label class="form-check-label" for="gravity-temp-adjustment"> <label class="form-check-label" for="gravity-temp-adjustment">
@ -258,7 +287,7 @@
</div> </div>
</div> </div>
<div class="form-group row"> <div class="form-group row">
<div class="col-sm-8 offset-sm-4"> <div class="col-sm-4 offset-sm-2">
<button type="submit" class="btn btn-primary" id="gravity-btn">Save</button> <button type="submit" class="btn btn-primary" id="gravity-btn">Save</button>
</div> </div>
</div> </div>
@ -280,34 +309,36 @@
<form action="/api/config/hardware" method="post"> <form action="/api/config/hardware" method="post">
<input type="text" name="id" id="id4" hidden> <input type="text" name="id" id="id4" hidden>
<div class="form-group row"> <div class="form-group row">
<label for="voltage-factor" class="col-sm-4 col-form-label">Voltage factor:</label> <label for="voltage-factor" class="col-sm-2 col-form-label">Voltage factor:</label>
<div class="col-sm-4"> <div class="col-sm-2">
<input type="number" step=".01" class="form-control" name="voltage-factor" id="voltage-factor"> <input type="number" step=".01" class="form-control" name="voltage-factor" id="voltage-factor">
</div> </div>
<label for="voltage-factor" class="col-sm-4 col-form-label" id="battery">Loading...</label> <label for="voltage-factor" class="col-sm-3 col-form-label" id="battery">Loading...</label>
</div> </div>
<div class="form-group row"> <div class="form-group row">
<label for="temp-adjustment-value" class="col-sm-4 col-form-label">Temp Sensor Adj:</label> <label for="temp-adjustment-value" class="col-sm-2 col-form-label">Temp Sensor Adj:</label>
<div class="col-sm-8"> <div class="col-sm-2">
<input type="number" step=".1" class="form-control" name="temp-adjustment-value" id="temp-adjustment-value"> <input type="number" step=".1" class="form-control" name="temp-adjustment-value" id="temp-adjustment-value">
</div> </div>
</div> </div>
<div class="form-group row"> <div class="form-group row">
<label class="col-sm-4 form-check-label" for="gyro-temp"> <div class="col-sm-3 offset-sm-2">
Use gyro temperature (Experimental) <div class="form-check">
<input class="form-check-input" type="checkbox" name="gyro-temp" id="gyro-temp">
<label class="form-check-label" for="gyro-temp">
Use gyro temperature
</label> </label>
<div class="col-sm-8 form-check"> </div>
<input class="col-sm-1 form-check-input" type="checkbox" name="gyro-temp" id="gyro-temp">
</div> </div>
</div> </div>
<div class="form-group row"> <div class="form-group row">
<label for="ota-url" class="col-sm-4 col-form-label">OTA base URL:</label> <label for="ota-url" class="col-sm-2 col-form-label">OTA base URL:</label>
<div class="col-sm-8"> <div class="col-sm-10">
<input type="url" maxlength="90" class="form-control" name="ota-url" id="ota-url"> <input type="url" maxlength="90" class="form-control" name="ota-url" id="ota-url">
</div> </div>
</div> </div>
<div class="form-group row"> <div class="form-group row">
<div class="col-sm-8 offset-sm-4"> <div class="col-sm-8 offset-sm-2">
<button type="submit" class="btn btn-primary" id="hardware-btn">Save</button> <button type="submit" class="btn btn-primary" id="hardware-btn">Save</button>
</div> </div>
</div> </div>
@ -397,6 +428,10 @@
$("#influxdb2-org").val(cfg["influxdb2-org"]); $("#influxdb2-org").val(cfg["influxdb2-org"]);
$("#influxdb2-bucket").val(cfg["influxdb2-bucket"]); $("#influxdb2-bucket").val(cfg["influxdb2-bucket"]);
$("#influxdb2-auth").val(cfg["influxdb2-auth"]); $("#influxdb2-auth").val(cfg["influxdb2-auth"]);
$("#mqtt-push").val(cfg["mqtt-push"]);
$("#mqtt-topic").val(cfg["mqtt-topic"]);
$("#mqtt-user").val(cfg["mqtt-user"]);
$("#mqtt-pass").val(cfg["mqtt-pass"]);
$("#sleep-interval").val(cfg["sleep-interval"]); $("#sleep-interval").val(cfg["sleep-interval"]);
$("#voltage-factor").val(cfg["voltage-factor"]); $("#voltage-factor").val(cfg["voltage-factor"]);
$("#gravity-formula").val(cfg["gravity-formula"]); $("#gravity-formula").val(cfg["gravity-formula"]);
@ -406,7 +441,7 @@
$("#gyro-calibration-data").text( cfg["gyro-calibration-data"]["ax"] + "," + cfg["gyro-calibration-data"]["ay"] + "," + cfg["gyro-calibration-data"]["az"] + "," + cfg["gyro-calibration-data"]["gx"] + "," + cfg["gyro-calibration-data"]["gy"] + "," + cfg["gyro-calibration-data"]["gz"] ); $("#gyro-calibration-data").text( cfg["gyro-calibration-data"]["ax"] + "," + cfg["gyro-calibration-data"]["ay"] + "," + cfg["gyro-calibration-data"]["az"] + "," + cfg["gyro-calibration-data"]["gx"] + "," + cfg["gyro-calibration-data"]["gy"] + "," + cfg["gyro-calibration-data"]["gz"] );
$("#battery").text(cfg["battery"] + " V"); $("#battery").text(cfg["battery"] + " V");
$("#angle").text(cfg["angle"]); $("#angle").text(cfg["angle"]);
$("#gravity").text(cfg["gravity"] + " SG"); //$("#gravity").text(cfg["gravity"] + " SG");
}) })
.fail(function () { .fail(function () {
showError('Unable to get data from the device.'); showError('Unable to get data from the device.');

File diff suppressed because one or more lines are too long

View File

@ -52,6 +52,7 @@ lib_deps = # Switched to forks for better version control.
https://github.com/mp-se/OneWire#v2.3.6 # https://github.com/PaulStoffregen/OneWire https://github.com/mp-se/OneWire#v2.3.6 # https://github.com/PaulStoffregen/OneWire
https://github.com/mp-se/Arduino-Temperature-Control-Library#3.9.1 # https://github.com/milesburton/Arduino-Temperature-Control-Library https://github.com/mp-se/Arduino-Temperature-Control-Library#3.9.1 # https://github.com/milesburton/Arduino-Temperature-Control-Library
https://github.com/mp-se/arduinoCurveFitting#v1.0.6 # https://github.com/Rotario/arduinoCurveFitting https://github.com/mp-se/arduinoCurveFitting#v1.0.6 # https://github.com/Rotario/arduinoCurveFitting
https://github.com/256dpi/arduino-mqtt
[env:gravity-debug] [env:gravity-debug]
upload_speed = ${common_env_data.upload_speed} upload_speed = ${common_env_data.upload_speed}
@ -64,8 +65,9 @@ extra_scripts =
script/create_versionjson.py script/create_versionjson.py
build_unflags = build_unflags =
${common_env_data.build_unflags} ${common_env_data.build_unflags}
-D MAIN_DISABLE_LOGGING # -D MAIN_DISABLE_LOGGING
-D WEB_DISABLE_LOGGING -D WEB_DISABLE_LOGGING
-D PUSH_DISABLE_LOGGING
build_flags = build_flags =
${common_env_data.build_flags} ${common_env_data.build_flags}
-D PIO_FRAMEWORK_ARDUINO_ENABLE_EXCEPTIONS -D PIO_FRAMEWORK_ARDUINO_ENABLE_EXCEPTIONS

View File

@ -74,6 +74,10 @@ void Config::createJson(DynamicJsonDocument& doc) {
doc[CFG_PARAM_PUSH_INFLUXDB2_ORG] = getInfluxDb2PushOrg(); doc[CFG_PARAM_PUSH_INFLUXDB2_ORG] = getInfluxDb2PushOrg();
doc[CFG_PARAM_PUSH_INFLUXDB2_BUCKET] = getInfluxDb2PushBucket(); doc[CFG_PARAM_PUSH_INFLUXDB2_BUCKET] = getInfluxDb2PushBucket();
doc[CFG_PARAM_PUSH_INFLUXDB2_AUTH] = getInfluxDb2PushToken(); doc[CFG_PARAM_PUSH_INFLUXDB2_AUTH] = getInfluxDb2PushToken();
doc[CFG_PARAM_PUSH_MQTT] = getMqttUrl();
doc[CFG_PARAM_PUSH_MQTT_TOPIC] = getMqttTopic();
doc[CFG_PARAM_PUSH_MQTT_USER] = getMqttUser();
doc[CFG_PARAM_PUSH_MQTT_PASS] = getMqttPass();
doc[CFG_PARAM_SLEEP_INTERVAL] = getSleepInterval(); doc[CFG_PARAM_SLEEP_INTERVAL] = getSleepInterval();
doc[CFG_PARAM_VOLTAGEFACTOR] = getVoltageFactor(); doc[CFG_PARAM_VOLTAGEFACTOR] = getVoltageFactor();
doc[CFG_PARAM_GRAVITY_FORMULA] = getGravityFormula(); doc[CFG_PARAM_GRAVITY_FORMULA] = getGravityFormula();
@ -189,16 +193,20 @@ bool Config::loadFile() {
if (!doc[CFG_PARAM_MDNS].isNull()) setMDNS(doc[CFG_PARAM_MDNS]); if (!doc[CFG_PARAM_MDNS].isNull()) setMDNS(doc[CFG_PARAM_MDNS]);
if (!doc[CFG_PARAM_SSID].isNull()) setWifiSSID(doc[CFG_PARAM_SSID]); if (!doc[CFG_PARAM_SSID].isNull()) setWifiSSID(doc[CFG_PARAM_SSID]);
if (!doc[CFG_PARAM_PASS].isNull()) setWifiPass(doc[CFG_PARAM_PASS]); if (!doc[CFG_PARAM_PASS].isNull()) setWifiPass(doc[CFG_PARAM_PASS]);
if (!doc[CFG_PARAM_TEMPFORMAT].isNull()) { if (!doc[CFG_PARAM_TEMPFORMAT].isNull()) {
String s = doc[CFG_PARAM_TEMPFORMAT]; String s = doc[CFG_PARAM_TEMPFORMAT];
setTempFormat(s.charAt(0)); setTempFormat(s.charAt(0));
} }
if (!doc[CFG_PARAM_PUSH_BREWFATHER].isNull()) if (!doc[CFG_PARAM_PUSH_BREWFATHER].isNull())
setBrewfatherPushUrl(doc[CFG_PARAM_PUSH_BREWFATHER]); setBrewfatherPushUrl(doc[CFG_PARAM_PUSH_BREWFATHER]);
if (!doc[CFG_PARAM_PUSH_HTTP].isNull()) if (!doc[CFG_PARAM_PUSH_HTTP].isNull())
setHttpPushUrl(doc[CFG_PARAM_PUSH_HTTP]); setHttpPushUrl(doc[CFG_PARAM_PUSH_HTTP]);
if (!doc[CFG_PARAM_PUSH_HTTP2].isNull()) if (!doc[CFG_PARAM_PUSH_HTTP2].isNull())
setHttpPushUrl2(doc[CFG_PARAM_PUSH_HTTP2]); setHttpPushUrl2(doc[CFG_PARAM_PUSH_HTTP2]);
if (!doc[CFG_PARAM_PUSH_INFLUXDB2].isNull()) if (!doc[CFG_PARAM_PUSH_INFLUXDB2].isNull())
setInfluxDb2PushUrl(doc[CFG_PARAM_PUSH_INFLUXDB2]); setInfluxDb2PushUrl(doc[CFG_PARAM_PUSH_INFLUXDB2]);
if (!doc[CFG_PARAM_PUSH_INFLUXDB2_ORG].isNull()) if (!doc[CFG_PARAM_PUSH_INFLUXDB2_ORG].isNull())
@ -207,6 +215,15 @@ bool Config::loadFile() {
setInfluxDb2PushBucket(doc[CFG_PARAM_PUSH_INFLUXDB2_BUCKET]); setInfluxDb2PushBucket(doc[CFG_PARAM_PUSH_INFLUXDB2_BUCKET]);
if (!doc[CFG_PARAM_PUSH_INFLUXDB2_AUTH].isNull()) if (!doc[CFG_PARAM_PUSH_INFLUXDB2_AUTH].isNull())
setInfluxDb2PushToken(doc[CFG_PARAM_PUSH_INFLUXDB2_AUTH]); setInfluxDb2PushToken(doc[CFG_PARAM_PUSH_INFLUXDB2_AUTH]);
if (!doc[CFG_PARAM_PUSH_MQTT].isNull()) setMqttUrl(doc[CFG_PARAM_PUSH_MQTT]);
if (!doc[CFG_PARAM_PUSH_MQTT_TOPIC].isNull())
setMqttTopic(doc[CFG_PARAM_PUSH_MQTT_TOPIC]);
if (!doc[CFG_PARAM_PUSH_MQTT_USER].isNull())
setMqttUser(doc[CFG_PARAM_PUSH_MQTT_USER]);
if (!doc[CFG_PARAM_PUSH_MQTT_PASS].isNull())
setMqttPass(doc[CFG_PARAM_PUSH_MQTT_PASS]);
if (!doc[CFG_PARAM_SLEEP_INTERVAL].isNull()) if (!doc[CFG_PARAM_SLEEP_INTERVAL].isNull())
setSleepInterval(doc[CFG_PARAM_SLEEP_INTERVAL].as<int>()); setSleepInterval(doc[CFG_PARAM_SLEEP_INTERVAL].as<int>());
if (!doc[CFG_PARAM_VOLTAGEFACTOR].isNull()) if (!doc[CFG_PARAM_VOLTAGEFACTOR].isNull())

View File

@ -46,17 +46,21 @@ SOFTWARE.
// These are used in API + Savefile // These are used in API + Savefile
#define CFG_PARAM_ID "id" #define CFG_PARAM_ID "id"
#define CFG_PARAM_MDNS "mdns" // Device name #define CFG_PARAM_MDNS "mdns" // Device name
#define CFG_PARAM_OTA "ota-url" // Base URL for OTA #define CFG_PARAM_OTA "ota-url"
#define CFG_PARAM_SSID "wifi-ssid" // WIFI #define CFG_PARAM_SSID "wifi-ssid"
#define CFG_PARAM_PASS "wifi-pass" // WIFI #define CFG_PARAM_PASS "wifi-pass"
#define CFG_PARAM_PUSH_BREWFATHER "brewfather-push" // URL (brewfather format) #define CFG_PARAM_PUSH_BREWFATHER "brewfather-push"
#define CFG_PARAM_PUSH_HTTP "http-push" // URL (iSpindle format) #define CFG_PARAM_PUSH_HTTP "http-push"
#define CFG_PARAM_PUSH_HTTP2 "http-push2" // URL (iSpindle format) #define CFG_PARAM_PUSH_HTTP2 "http-push2"
#define CFG_PARAM_PUSH_INFLUXDB2 "influxdb2-push" // URL #define CFG_PARAM_PUSH_INFLUXDB2 "influxdb2-push"
#define CFG_PARAM_PUSH_INFLUXDB2_ORG "influxdb2-org" // URL #define CFG_PARAM_PUSH_INFLUXDB2_ORG "influxdb2-org"
#define CFG_PARAM_PUSH_INFLUXDB2_BUCKET "influxdb2-bucket" // URL #define CFG_PARAM_PUSH_INFLUXDB2_BUCKET "influxdb2-bucket"
#define CFG_PARAM_PUSH_INFLUXDB2_AUTH "influxdb2-auth" // URL #define CFG_PARAM_PUSH_INFLUXDB2_AUTH "influxdb2-auth"
#define CFG_PARAM_PUSH_MQTT "mqtt-push"
#define CFG_PARAM_PUSH_MQTT_USER "mqtt-user"
#define CFG_PARAM_PUSH_MQTT_PASS "mqtt-pass"
#define CFG_PARAM_PUSH_MQTT_TOPIC "mqtt-topic"
#define CFG_PARAM_SLEEP_INTERVAL "sleep-interval" // Sleep interval #define CFG_PARAM_SLEEP_INTERVAL "sleep-interval" // Sleep interval
#define CFG_PARAM_TEMPFORMAT "temp-format" // C or F #define CFG_PARAM_TEMPFORMAT "temp-format" // C or F
#define CFG_PARAM_VOLTAGEFACTOR \ #define CFG_PARAM_VOLTAGEFACTOR \
@ -135,6 +139,11 @@ class Config {
String influxDb2Bucket; // Bucket for InfluxDB v2 String influxDb2Bucket; // Bucket for InfluxDB v2
String influxDb2Token; // Auth Token for InfluxDB v2 String influxDb2Token; // Auth Token for InfluxDB v2
String mqttUrl; // Server name
String mqttTopic;
String mqttUser;
String mqttPass;
// Gravity and temperature calculations // Gravity and temperature calculations
String gravityFormula; String gravityFormula;
bool gravityTempAdj; // true, false bool gravityTempAdj; // true, false
@ -229,6 +238,29 @@ class Config {
saveNeeded = true; saveNeeded = true;
} }
// MQTT
bool isMqttActive() { return mqttUrl.length() ? true : false; }
const char* getMqttUrl() { return mqttUrl.c_str(); }
void setMqttUrl(String s) {
mqttUrl = s;
saveNeeded = true;
}
const char* getMqttTopic() { return mqttTopic.c_str(); }
void setMqttTopic(String s) {
mqttTopic = s;
saveNeeded = true;
}
const char* getMqttUser() { return mqttUser.c_str(); }
void setMqttUser(String s) {
mqttUser = s;
saveNeeded = true;
}
const char* getMqttPass() { return mqttPass.c_str(); }
void setMqttPass(String s) {
mqttPass = s;
saveNeeded = true;
}
int getSleepInterval() { return sleepInterval; } int getSleepInterval() { return sleepInterval; }
void setSleepInterval(int v) { void setSleepInterval(int v) {
sleepInterval = v; sleepInterval = v;

View File

@ -21,6 +21,8 @@ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE. SOFTWARE.
*/ */
#include <MQTT.h>
#include <config.hpp> #include <config.hpp>
#include <gyro.hpp> #include <gyro.hpp>
#include <pushtarget.hpp> #include <pushtarget.hpp>
@ -74,6 +76,12 @@ void PushTarget::send(float angle, float gravity, float corrGravity, float temp,
sendInfluxDb2(angle, gravity, corrGravity, temp, runTime); sendInfluxDb2(angle, gravity, corrGravity, temp, runTime);
LOG_PERF_STOP("push-influxdb2"); LOG_PERF_STOP("push-influxdb2");
} }
if (myConfig.isMqttActive()) {
LOG_PERF_START("push-mqtt");
sendMqtt(angle, gravity, corrGravity, temp, runTime);
LOG_PERF_STOP("push-mqtt");
}
} }
// //
@ -98,14 +106,14 @@ void PushTarget::sendInfluxDb2(float angle, float gravity, float corrGravity,
// Create body for influxdb2 // Create body for influxdb2
char buf[1024]; char buf[1024];
snprintf( snprintf(&buf[0], sizeof(buf),
&buf[0], sizeof(buf),
"measurement,host=%s,device=%s,temp-format=%c,gravity-format=%s " "measurement,host=%s,device=%s,temp-format=%c,gravity-format=%s "
"gravity=%.4f,corr-gravity=%.4f,angle=%.2f,temp=%.2f,battery=%.2f,rssi=%d\n", "gravity=%.4f,corr-gravity=%.4f,angle=%.2f,temp=%.2f,battery=%.2f,"
"rssi=%d\n",
// TODO: Add support for plato format // TODO: Add support for plato format
myConfig.getMDNS(), myConfig.getID(), myConfig.getTempFormat(), "SG", myConfig.getMDNS(), myConfig.getID(), myConfig.getTempFormat(), "SG",
myConfig.isGravityTempAdj() ? corrGravity : gravity, corrGravity, angle, myConfig.isGravityTempAdj() ? corrGravity : gravity, corrGravity,
temp, myBatteryVoltage.getVoltage(), WiFi.RSSI()); angle, temp, myBatteryVoltage.getVoltage(), WiFi.RSSI());
#if LOG_LEVEL == 6 && !defined(PUSH_DISABLE_LOGGING) #if LOG_LEVEL == 6 && !defined(PUSH_DISABLE_LOGGING)
Log.verbose(F("PUSH: url %s." CR), serverPath.c_str()); Log.verbose(F("PUSH: url %s." CR), serverPath.c_str());
@ -197,16 +205,9 @@ void PushTarget::sendBrewfather(float angle, float gravity, float corrGravity,
// //
// Send data to http target // Send data to http target
// //
void PushTarget::sendHttp(String serverPath, float angle, float gravity, void PushTarget::createIspindleFormat(DynamicJsonDocument &doc, float angle,
float corrGravity, float temp, float runTime) { float gravity, float corrGravity,
#if !defined(PUSH_DISABLE_LOGGING) float temp, float runTime) {
Log.notice(
F("PUSH: Sending values to http angle=%F, gravity=%F, temp=%F." CR),
angle, gravity, temp);
#endif
DynamicJsonDocument doc(256);
// Use iSpindle format for compatibility // Use iSpindle format for compatibility
doc["name"] = myConfig.getMDNS(); doc["name"] = myConfig.getMDNS();
doc["ID"] = myConfig.getID(); doc["ID"] = myConfig.getID();
@ -225,6 +226,21 @@ void PushTarget::sendHttp(String serverPath, float angle, float gravity,
// Some additional information // Some additional information
doc["gravity-units"] = "SG"; doc["gravity-units"] = "SG";
doc["run-time"] = reduceFloatPrecision(runTime, 2); doc["run-time"] = reduceFloatPrecision(runTime, 2);
}
//
// Send data to http target
//
void PushTarget::sendHttp(String serverPath, float angle, float gravity,
float corrGravity, float temp, float runTime) {
#if !defined(PUSH_DISABLE_LOGGING)
Log.notice(
F("PUSH: Sending values to http angle=%F, gravity=%F, temp=%F." CR),
angle, gravity, temp);
#endif
DynamicJsonDocument doc(256);
createIspindleFormat(doc, angle, gravity, corrGravity, temp, runTime);
WiFiClient client; WiFiClient client;
HTTPClient http; HTTPClient http;
@ -252,4 +268,43 @@ void PushTarget::sendHttp(String serverPath, float angle, float gravity,
http.end(); http.end();
} }
//
// Send data to http target
//
void PushTarget::sendMqtt(float angle, float gravity, float corrGravity,
float temp, float runTime) {
#if !defined(PUSH_DISABLE_LOGGING)
Log.notice(
F("PUSH: Sending values to mqtt angle=%F, gravity=%F, temp=%F." CR),
angle, gravity, temp);
#endif
DynamicJsonDocument doc(256);
createIspindleFormat(doc, angle, gravity, corrGravity, temp, runTime);
WiFiClient client;
MQTTClient mqtt;
mqtt.begin(myConfig.getMqttUrl(), client);
mqtt.connect(myConfig.getMDNS(), myConfig.getMqttUser(),
myConfig.getMqttPass());
String json;
serializeJson(doc, json);
#if LOG_LEVEL == 6 && !defined(PUSH_DISABLE_LOGGING)
Log.verbose(F("PUSH: url %s." CR), serverPath.c_str());
Log.verbose(F("PUSH: json %s." CR), json.c_str());
#endif
// Send MQQT message
mqtt.setTimeout(10); // 10 seconds timeout
if (mqtt.publish(myConfig.getMqttTopic(), json)) {
Log.notice(F("PUSH: MQTT publish successful" CR));
} else {
Log.error(F("PUSH: MQTT publish failed" CR));
}
mqtt.disconnect();
}
// EOF // EOF

View File

@ -43,6 +43,11 @@ class PushTarget {
float corrGravity, float temp, float runTime); float corrGravity, float temp, float runTime);
void sendInfluxDb2(float angle, float gravity, float corrGravity, float temp, void sendInfluxDb2(float angle, float gravity, float corrGravity, float temp,
float runTime); float runTime);
void sendMqtt(float angle, float gravity, float corrGravity, float temp,
float runTime);
void createIspindleFormat(DynamicJsonDocument &doc, float angle,
float gravity, float corrGravity, float temp,
float runTime);
public: public:
PushTarget() { ms = millis(); } PushTarget() { ms = millis(); }

View File

@ -359,6 +359,10 @@ void WebServer::webHandleConfigPush() {
server->arg(CFG_PARAM_PUSH_INFLUXDB2_BUCKET).c_str()); server->arg(CFG_PARAM_PUSH_INFLUXDB2_BUCKET).c_str());
myConfig.setInfluxDb2PushToken( myConfig.setInfluxDb2PushToken(
server->arg(CFG_PARAM_PUSH_INFLUXDB2_AUTH).c_str()); server->arg(CFG_PARAM_PUSH_INFLUXDB2_AUTH).c_str());
myConfig.setMqttUrl(server->arg(CFG_PARAM_PUSH_MQTT).c_str());
myConfig.setMqttTopic(server->arg(CFG_PARAM_PUSH_MQTT_TOPIC).c_str());
myConfig.setMqttUser(server->arg(CFG_PARAM_PUSH_MQTT_USER).c_str());
myConfig.setMqttPass(server->arg(CFG_PARAM_PUSH_MQTT_PASS).c_str());
myConfig.saveFile(); myConfig.saveFile();
server->sendHeader("Location", "/config.htm#collapseTwo", true); server->sendHeader("Location", "/config.htm#collapseTwo", true);
server->send(302, "text/plain", "Push config updated"); server->send(302, "text/plain", "Push config updated");

View File

@ -10,6 +10,10 @@
"influxdb2-org": "hello", "influxdb2-org": "hello",
"influxdb2-bucket": "spann", "influxdb2-bucket": "spann",
"influxdb2-auth": "OijkU((jhfkh", "influxdb2-auth": "OijkU((jhfkh",
"mqtt-push": "192.168.1.10",
"mqtt-topic": "mytopic",
"mqtt-user": "user",
"mqtt-pass": "pass",
"sleep-interval": 30, "sleep-interval": 30,
"voltage-factor": 1.59, "voltage-factor": 1.59,
"gravity-formula": "0.0*tilt^3+0.0*tilt^2+0.0017978*tilt+0.9436", "gravity-formula": "0.0*tilt^3+0.0*tilt^2+0.0017978*tilt+0.9436",