I modified some examples for a :
- counter of electric meter MT174 (one impulse to low via LED per 1 Wh, impuls lenght is 20 ms) connected to GPIO 0
- counter of gas meter (one impuls with reed contact per 0.01m³) connected to GPIO 2
-webserver with output:
Up time [s]: 32348
NODE.HEAP : 7440
El. counter [Wh]: 1527
Gas counter [0.01m³]: 113
-UDP broadcast at every event with the actual data.
---------------
-- install a webserver
-- Use as : httpserver()
httpserver = function ()
srv=net.createServer(net.TCP)
srv:listen(80,function(conn)
conn:on("receive", function(conn,payload)
--print(payload)
conn:send('HTTP/1.1 200 OK\r\n Content-type: text/html\r\n\r\n\
<!DOCTYPE HTML>\
<html>\
<head><meta content="text/html; charset=utf-8">\
<title>ESP8266 Smart meter</title>\
</head><body>\
Up time [s]: ' .. upseconds .. '<BR>\
NODE.HEAP : ' .. node.heap() .. '<BR>\
El. counter [Wh]: ' .. ecounter .. '<BR>\
Gas counter [0.01m³]: ' .. gcounter .. '<BR>\
</body></html>'
)
end)
conn:on("sent",function(conn) conn:close() end)
end)
print("httpserver installed. Browse to ")
print(wifi.sta.getip())
end
tLastEl=0
ecounter=0
function IntElectric(level)
if level==1 then return end -- only level 0
if (tmr.now()<tLastEl) or (tmr.now()-tLastEl > 200000) then -- only 1x per 0.2 sec, or overflow of tmr.now
tLastEl=tmr.now()
ecounter=ecounter+1
print('GPIO0/El.:' .. ecounter .. ' Level:' .. level)
SendUDP()
end
end
tLastGas=0
gcounter=0
function IntGas(level)
if level==1 then return end --only level 0
if upseconds-tLastGas >= 2 then -- only 1x per 2sec
tLastGas=upseconds
gcounter=gcounter+1
print('GPIO0/Gas:' .. gcounter .. ' Level:' .. level)
SendUDP()
end
end
function InitGPIO()
-- Count GPIO at level change to 0
-- set GPIO0 to Interrupt mode and define interrupt procedure
gpio.mode(3,gpio.INT,gpio.PULLUP)
gpio.trig(3, "down", IntElectric)
-- set GPIO2 to Interrupt mode and define interrupt procedure
gpio.mode(4,gpio.INT,gpio.PULLUP)
gpio.trig(4, "down", IntGas)
end
lastsend=0 -- contain upsecond of last send, if -1 if send is in progress
function SendUDP()
if lastsend < 0 then return end -- no reentrent call
if upseconds-lastsend >= 1 then --send only 1 per second
lastsend=-1 -- no reentrent call
conn=net.createConnection(net.UDP, 0)
conn:connect(15000,"255.255.255.255")
s= 'up=' .. upseconds .. ';heap=' .. node.heap() .. ';E=' .. ecounter .. ';G=' .. gcounter
conn:send(s)
conn:close()
print('Broadcast send:' .. s)
lastsend=upseconds
end
end
-- MAIN
InitGPIO()
wifi.setmode(wifi.STATION)
wifi.sta.config('AP','password') --<< set your data
ServerCreated=false
upseconds=0
-- wait until get IP and timer for system up time in second (tmr.now overflow after 2^31 us = 35.8 min
tmr.alarm(0,1000, 1, function()
upseconds = upseconds+1
if not ServerCreated then
if wifi.sta.getip()==nil then
print("Connect AP, Waiting...")
else
httpserver()
ServerCreated=true
end
end
end)
The UDP broadcast can received with an UDP client (i.e TCP/UDP Terminal from play store: set to UDP and incoming Port to 15000) or the C# code:
using System;
using System.Text;
using System.Net;
using System.Net.Sockets;
class Program
{
const int port = 15000;
static UdpClient udp= new UdpClient(port);
static IPEndPoint ep = new IPEndPoint(IPAddress.Any, port);
static void Main(string[] args)
{
udp.BeginReceive(Receive,null);
Console.WriteLine("Started listening at Port " + port + ". Press any key to exit");
Console.ReadKey();
udp.Close();
}
private static void Receive(IAsyncResult ar)
{
byte[] buffer = udp.EndReceive(ar, ref ep);
Console.WriteLine("{0} {1}:{2} ", DateTime.Now, ep.Address.ToString(), Encoding.UTF8.GetString(buffer));
udp.BeginReceive(Receive, null);
}
}