-
Notifications
You must be signed in to change notification settings - Fork 7
/
energymonitor.ino
127 lines (106 loc) · 2.81 KB
/
energymonitor.ino
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
/*
* By Hadley Rich
* Released under the MIT license.
* Some ideas taken from arduino.cc example code.
*/
#include <stdio.h>
#include <SPI.h>
#include <Ethernet.h>
#include <PubSubClient.h>
byte mac[6] = { 0x90, 0xA2, 0xDA, 0x44, 0x34, 0x28 };
char macstr[18];
const int chan1_pin = 2;
//My meter flashes 1000 times per kWh
const float w_per_pulse = 1;
const unsigned long ms_per_hour = 3600000UL;
unsigned int chan1_count = 0;
unsigned long report_time = 0;
unsigned long chan1_first_pulse = 0;
unsigned long chan1_last_pulse = 0;
volatile byte chan1_pulse = 0;
EthernetClient ethClient;
PubSubClient client("192.168.1.3", 1883, callback, ethClient);
void callback(char* topic, byte* payload, unsigned int length) {
}
void chan1_isr() {
chan1_pulse = 1;
}
boolean connect_mqtt() {
Serial.print("MQTT...");
if (client.connect(macstr)) {
Serial.println("connected");
char topic[35];
snprintf(topic, 35, "house/node/%s/state", macstr);
client.publish(topic, "start");
return true;
}
Serial.println("Failed.");
return false;
}
void setup() {
pinMode(chan1_pin, INPUT);
attachInterrupt(0, chan1_isr, RISING);
Serial.begin(9600);
delay(1000);
snprintf(macstr, 18, "%02x:%02x:%02x:%02x:%02x:%02x",
mac[0], mac[1], mac[2], mac[3], mac[4], mac[5]);
Serial.print("DHCP (");
Serial.print(macstr);
Serial.print(")...");
if (Ethernet.begin(mac) == 0) {
Serial.println("Failed.");
while(true);
}
Serial.println(Ethernet.localIP());
}
void loop() {
char topic[35];
char value[6];
static unsigned int chan1_watts;
unsigned long chan1_delta; // Time since last pulse
if (!client.connected() && !connect_mqtt()) {
return;
}
client.loop();
if (millis() - chan1_last_pulse > 60000) {
chan1_watts = 0;
}
if (millis() - report_time > 5000) {
chan1_delta = chan1_last_pulse - chan1_first_pulse;
if (chan1_delta && chan1_count) {
chan1_watts = (chan1_count - 1) * w_per_pulse * ms_per_hour / chan1_delta;
chan1_count = 0;
}
if (!(report_time == 0 && chan1_watts == 0)) {
snprintf(topic, 35, "house/power/meter/1/current");
snprintf(value, 6, "%d", chan1_watts);
client.publish(topic, value);
Serial.print("Chan1 ");
Serial.println(chan1_watts);
report_time = millis();
}
}
if (chan1_pulse == 1) {
chan1_count++;
chan1_pulse = 0;
chan1_last_pulse = millis();
if (chan1_count == 1) { // was reset
chan1_first_pulse = chan1_last_pulse;
}
snprintf(topic, 35, "house/power/meter/1/usage");
client.publish(topic, "1");
}
int dhcp_status = Ethernet.maintain();
/*
returns:
0: nothing happened
1: renew failed
2: renew success
3: rebind fail
4: rebind success
*/
if (dhcp_status) {
long now = millis();
Serial.println("DHCP Lease");
}
}