|
@@ -1,164 +1,228 @@
|
1
|
1
|
#include <Arduino.h>
|
2
|
2
|
#include <Wire.h>
|
3
|
3
|
#include <ESP8266WiFi.h>
|
4
|
|
-#include <InfluxDb.h>
|
5
|
4
|
#include <ESP8266WebServer.h>
|
6
|
5
|
#include <ESP8266mDNS.h>
|
|
6
|
+#include <ESP8266HTTPUpdateServer.h>
|
7
|
7
|
#include <Adafruit_BME280.h>
|
8
|
8
|
#include <SHT2x.h>
|
|
9
|
+#include "config.h"
|
9
|
10
|
|
10
|
|
-const char* sensor_location = "SENSOR_NAME_GOES_HERE";
|
11
|
|
-
|
12
|
|
-const char* ssid = "YOUR_SSID_HERE";
|
13
|
|
-const char* password = "YOUR_PASS_HERE";
|
14
|
|
-
|
15
|
|
-#define INFLUXDB_HOST "INFLUX_DB_SERVER_IP_HERE"
|
16
|
|
-#define INFLUXDB_PORT 8086
|
17
|
|
-#define INFLUXDB_DATABASE "INFLUX_DB_DATABASE_NAME_HERE"
|
18
|
|
-
|
19
|
|
-#define SENSOR_HOSTNAME_PREFIX "ESP-"
|
20
|
|
-
|
|
11
|
+#ifdef ENABLE_DATABASE_WRITES
|
|
12
|
+#include <InfluxDb.h>
|
21
|
13
|
Influxdb influx(INFLUXDB_HOST, INFLUXDB_PORT);
|
|
14
|
+#endif // ENABLE_DATABASE_WRITES
|
|
15
|
+
|
22
|
16
|
ESP8266WebServer server(80);
|
|
17
|
+ESP8266HTTPUpdateServer updater;
|
|
18
|
+
|
23
|
19
|
TwoWire Wire2;
|
24
|
20
|
SHT2x sht(HTDU21D_ADDRESS, &Wire2);
|
25
|
21
|
Adafruit_BME280 bme;
|
|
22
|
+
|
26
|
23
|
bool found_bme = false;
|
27
|
24
|
bool found_sht = false;
|
28
|
25
|
|
|
26
|
+unsigned long last_server_handle_time = 0;
|
|
27
|
+unsigned long last_db_write_time = 0;
|
|
28
|
+unsigned long last_led_blink_time = 0;
|
|
29
|
+
|
29
|
30
|
void handleRoot() {
|
30
|
|
- String message = "ESP8266 BME280 Sensor";
|
31
|
|
- message += "\n\nLocation: ";
|
|
31
|
+ String message = F("ESP8266 Environment Sensor");
|
|
32
|
+ message += F("\n\n");
|
|
33
|
+ message += F("Version: ");
|
|
34
|
+ message += esp_env_version;
|
|
35
|
+ message += F("\n");
|
|
36
|
+ message += F("Location: ");
|
32
|
37
|
message += sensor_location;
|
33
|
|
- message += "\nMAC: ";
|
|
38
|
+ message += F("\n");
|
|
39
|
+ message += F("MAC: ");
|
34
|
40
|
message += WiFi.macAddress();
|
35
|
41
|
|
|
42
|
+#ifdef HTTP_SHOW_ESP_STATS
|
|
43
|
+ message += F("\n");
|
|
44
|
+ message += F("Reset reason: ");
|
|
45
|
+ message += ESP.getResetReason();
|
|
46
|
+ message += F("\n");
|
|
47
|
+ message += F("Free heap: ");
|
|
48
|
+ message += String(ESP.getFreeHeap());
|
|
49
|
+ message += F(" (");
|
|
50
|
+ message += String(ESP.getHeapFragmentation());
|
|
51
|
+ message += F("% fragmentation)");
|
|
52
|
+ message += F("\n");
|
|
53
|
+ message += F("Free sketch space: ");
|
|
54
|
+ message += String(ESP.getFreeSketchSpace());
|
|
55
|
+ message += F("\n");
|
|
56
|
+ message += F("Flash chip real size: ");
|
|
57
|
+ message += String(ESP.getFlashChipRealSize());
|
|
58
|
+
|
|
59
|
+ if (ESP.getFlashChipSize() != ESP.getFlashChipRealSize()) {
|
|
60
|
+ message += F("\n");
|
|
61
|
+ message += F("WARNING: sdk chip size (");
|
|
62
|
+ message += (ESP.getFlashChipSize());
|
|
63
|
+ message += F(") does not match!");
|
|
64
|
+ }
|
|
65
|
+#endif // HTTP_SHOW_ESP_STATS
|
|
66
|
+
|
36
|
67
|
if (found_bme) {
|
37
|
|
- message += "\n\nBME280:";
|
38
|
|
- message += "\nTemperature: ";
|
|
68
|
+ message += F("\n\n");
|
|
69
|
+ message += F("BME280:");
|
|
70
|
+ message += F("\n");
|
|
71
|
+ message += F("Temperature: ");
|
39
|
72
|
message += String(bme.readTemperature());
|
40
|
|
- message += "\nHumidity: ";
|
|
73
|
+ message += F("\n");
|
|
74
|
+ message += F("Humidity: ");
|
41
|
75
|
message += String(bme.readHumidity());
|
42
|
|
- message += "\nPressure: ";
|
|
76
|
+ message += F("\n");
|
|
77
|
+ message += F("Pressure: ");
|
43
|
78
|
message += String(bme.readPressure());
|
44
|
79
|
}
|
45
|
80
|
|
46
|
81
|
if (found_sht) {
|
47
|
|
- message += "\n\nSHT21:";
|
48
|
|
- message += "\nTemperature: ";
|
|
82
|
+ message += F("\n\n");
|
|
83
|
+ message += F("SHT21:");
|
|
84
|
+ message += F("\n");
|
|
85
|
+ message += F("Temperature: ");
|
49
|
86
|
message += String(sht.GetTemperature());
|
50
|
|
- message += "\nHumidity: ";
|
|
87
|
+ message += F("\n");
|
|
88
|
+ message += F("Humidity: ");
|
51
|
89
|
message += String(sht.GetHumidity());
|
52
|
90
|
}
|
53
|
91
|
|
54
|
92
|
if ((!found_bme) && (!found_sht)) {
|
55
|
|
- message += "\n\nNo Sensor available!";
|
|
93
|
+ message += F("\n\n");
|
|
94
|
+ message += F("No Sensor available!");
|
56
|
95
|
}
|
57
|
96
|
|
58
|
|
- message += "\n";
|
|
97
|
+ message += F("\n\n");
|
|
98
|
+ message += F("Try /update for OTA firmware updates!");
|
|
99
|
+ message += F("\n");
|
|
100
|
+
|
59
|
101
|
server.send(200, "text/plain", message);
|
60
|
102
|
}
|
61
|
103
|
|
62
|
104
|
void setup() {
|
63
|
105
|
pinMode(1, OUTPUT);
|
64
|
|
- digitalWrite(1, LOW); // LED on
|
65
|
|
- delay(500);
|
66
|
|
- digitalWrite(1, HIGH); // LED off
|
67
|
|
- delay(500);
|
68
|
|
- digitalWrite(1, LOW); // LED on
|
69
|
|
- delay(500);
|
70
|
|
- digitalWrite(1, HIGH); // LED off
|
71
|
|
- delay(500);
|
72
|
106
|
|
|
107
|
+ // Blink LED for init
|
|
108
|
+ for (int i = 0; i < 2; i++) {
|
|
109
|
+ digitalWrite(1, LOW); // LED on
|
|
110
|
+ delay(LED_INIT_BLINK_INTERVAL);
|
|
111
|
+ digitalWrite(1, HIGH); // LED off
|
|
112
|
+ delay(LED_INIT_BLINK_INTERVAL);
|
|
113
|
+ }
|
|
114
|
+
|
|
115
|
+ // Init I2C and try to connect to sensors
|
73
|
116
|
Wire2.begin(2, 0);
|
74
|
117
|
found_bme = (!bme.begin(0x76, &Wire2)) ? false : true;
|
75
|
118
|
found_sht = sht.GetAlive();
|
76
|
119
|
|
|
120
|
+#ifdef DONT_RUN_WITHOUT_SENSORS
|
77
|
121
|
if ((!found_bme) && (!found_sht)) {
|
78
|
122
|
// no sensor available
|
79
|
123
|
while (1) {
|
80
|
124
|
digitalWrite(1, !digitalRead(1));
|
81
|
|
- delay(100);
|
|
125
|
+ delay(LED_ERROR_BLINK_INTERVAL);
|
82
|
126
|
}
|
83
|
127
|
}
|
|
128
|
+#endif // DONT_RUN_WITHOUT_SENSORS
|
84
|
129
|
|
|
130
|
+ // Set hostname
|
85
|
131
|
String hostname = SENSOR_HOSTNAME_PREFIX;
|
86
|
132
|
hostname += sensor_location;
|
87
|
133
|
WiFi.hostname(hostname);
|
88
|
134
|
|
|
135
|
+ // Connect to WiFi AP
|
89
|
136
|
WiFi.mode(WIFI_STA);
|
90
|
137
|
WiFi.begin(ssid, password);
|
91
|
|
-
|
92
|
|
- MDNS.begin(hostname);
|
93
|
|
-
|
94
|
138
|
while (WiFi.status() != WL_CONNECTED) {
|
95
|
|
- delay(250);
|
|
139
|
+ delay(LED_CONNECT_BLINK_INTERVAL);
|
96
|
140
|
digitalWrite(1, !digitalRead(1));
|
97
|
141
|
}
|
98
|
142
|
|
|
143
|
+#ifdef ENABLE_DATABASE_WRITES
|
|
144
|
+ // Setup InfluxDB Client
|
99
|
145
|
influx.setDb(INFLUXDB_DATABASE);
|
|
146
|
+#endif // ENABLE_DATABASE_WRITES
|
100
|
147
|
|
|
148
|
+ // Setup HTTP Server
|
|
149
|
+ MDNS.begin(hostname);
|
|
150
|
+ updater.setup(&server);
|
101
|
151
|
server.on("/", handleRoot);
|
102
|
152
|
server.begin();
|
|
153
|
+ MDNS.addService("http", "tcp", 80);
|
103
|
154
|
}
|
104
|
155
|
|
105
|
|
-#define SERVER_HANDLE_INTERVAL 10 // in ms
|
106
|
|
-#define DB_WRITE_INTERVAL (30 * 1000) // in ms
|
107
|
|
-#define LED_BLINK_INTERVAL (2 * 1000) // in ms
|
|
156
|
+void handleServers() {
|
|
157
|
+ server.handleClient();
|
|
158
|
+ MDNS.update();
|
|
159
|
+}
|
108
|
160
|
|
109
|
|
-unsigned long last_server_handle_time = 0;
|
110
|
|
-unsigned long last_db_write_time = 0;
|
111
|
|
-unsigned long last_led_blink_time = 0;
|
|
161
|
+#ifdef ENABLE_DATABASE_WRITES
|
|
162
|
+void writeDatabase() {
|
|
163
|
+ if (found_bme) {
|
|
164
|
+ InfluxData measurement("environment");
|
|
165
|
+ measurement.addTag("location", sensor_location);
|
|
166
|
+ measurement.addTag("device", WiFi.macAddress());
|
|
167
|
+ measurement.addTag("sensor", "bme280");
|
|
168
|
+
|
|
169
|
+ measurement.addValue("temperature", bme.readTemperature());
|
|
170
|
+ measurement.addValue("pressure", bme.readPressure());
|
|
171
|
+ measurement.addValue("humidity", bme.readHumidity());
|
|
172
|
+
|
|
173
|
+ boolean success = influx.write(measurement);
|
|
174
|
+ if (!success) {
|
|
175
|
+ for (int i = 0; i < 10; i++) {
|
|
176
|
+ digitalWrite(1, LOW); // LED on
|
|
177
|
+ delay(LED_ERROR_BLINK_INTERVAL);
|
|
178
|
+ digitalWrite(1, HIGH); // LED off
|
|
179
|
+ delay(LED_ERROR_BLINK_INTERVAL);
|
|
180
|
+ }
|
|
181
|
+ }
|
|
182
|
+ }
|
|
183
|
+
|
|
184
|
+ if (found_sht) {
|
|
185
|
+ InfluxData measurement("environment");
|
|
186
|
+ measurement.addTag("location", sensor_location);
|
|
187
|
+ measurement.addTag("device", WiFi.macAddress());
|
|
188
|
+ measurement.addTag("sensor", "sht21");
|
|
189
|
+
|
|
190
|
+ measurement.addValue("temperature", sht.GetTemperature());
|
|
191
|
+ measurement.addValue("humidity", sht.GetHumidity());
|
|
192
|
+
|
|
193
|
+ boolean success = influx.write(measurement);
|
|
194
|
+ if (!success) {
|
|
195
|
+ for (int i = 0; i < 10; i++) {
|
|
196
|
+ digitalWrite(1, LOW); // LED on
|
|
197
|
+ delay(LED_ERROR_BLINK_INTERVAL);
|
|
198
|
+ digitalWrite(1, HIGH); // LED off
|
|
199
|
+ delay(LED_ERROR_BLINK_INTERVAL);
|
|
200
|
+ }
|
|
201
|
+ }
|
|
202
|
+ }
|
|
203
|
+}
|
|
204
|
+#endif // ENABLE_DATABASE_WRITES
|
112
|
205
|
|
113
|
206
|
void loop() {
|
114
|
207
|
unsigned long time = millis();
|
115
|
208
|
|
116
|
209
|
if ((time - last_server_handle_time) >= SERVER_HANDLE_INTERVAL) {
|
117
|
210
|
last_server_handle_time = time;
|
118
|
|
-
|
119
|
|
- server.handleClient();
|
120
|
|
- MDNS.update();
|
|
211
|
+ handleServers();
|
121
|
212
|
}
|
122
|
213
|
|
|
214
|
+#ifdef ENABLE_DATABASE_WRITES
|
123
|
215
|
if ((time - last_db_write_time) >= DB_WRITE_INTERVAL) {
|
124
|
216
|
last_db_write_time = time;
|
125
|
|
-
|
126
|
|
- if (found_bme) {
|
127
|
|
- InfluxData measurement("environment");
|
128
|
|
- measurement.addTag("location", sensor_location);
|
129
|
|
- measurement.addTag("device", WiFi.macAddress());
|
130
|
|
- measurement.addTag("sensor", "bme280");
|
131
|
|
-
|
132
|
|
- measurement.addValue("temperature", bme.readTemperature());
|
133
|
|
- measurement.addValue("pressure", bme.readPressure());
|
134
|
|
- measurement.addValue("humidity", bme.readHumidity());
|
135
|
|
-
|
136
|
|
- boolean success = influx.write(measurement);
|
137
|
|
- if (!success) {
|
138
|
|
- digitalWrite(1, !digitalRead(1));
|
139
|
|
- }
|
140
|
|
- }
|
141
|
|
-
|
142
|
|
- if (found_sht) {
|
143
|
|
- InfluxData measurement("environment");
|
144
|
|
- measurement.addTag("location", sensor_location);
|
145
|
|
- measurement.addTag("device", WiFi.macAddress());
|
146
|
|
- measurement.addTag("sensor", "sht21");
|
147
|
|
-
|
148
|
|
- measurement.addValue("temperature", sht.GetTemperature());
|
149
|
|
- measurement.addValue("humidity", sht.GetHumidity());
|
150
|
|
-
|
151
|
|
- boolean success = influx.write(measurement);
|
152
|
|
- if (!success) {
|
153
|
|
- digitalWrite(1, !digitalRead(1));
|
154
|
|
- }
|
155
|
|
- }
|
|
217
|
+ writeDatabase();
|
156
|
218
|
}
|
|
219
|
+#endif // ENABLE_DATABASE_WRITES
|
157
|
220
|
|
|
221
|
+#ifdef ENABLE_LED_HEARTBEAT_BLINK
|
158
|
222
|
if ((time - last_led_blink_time) >= LED_BLINK_INTERVAL) {
|
159
|
223
|
last_led_blink_time = time;
|
160
|
|
-
|
161
|
224
|
digitalWrite(1, !digitalRead(1));
|
162
|
225
|
}
|
|
226
|
+#endif // ENABLE_LED_HEARTBEAT_BLINK
|
163
|
227
|
}
|
164
|
228
|
|