Virtual meter that is the sum of two other meters

Post Reply
benbammens
Posts: 30
Joined: Tuesday 30 May 2017 19:43
Target OS: Raspberry Pi
Domoticz version:
Contact:

Virtual meter that is the sum of two other meters

Post by benbammens » Friday 04 August 2017 21:05

Is there a way to create a virtual energy meter that is the sum/subtraction of 2 or more other meters?

I now have a meter that logs the production of my solar panels , one that logs the exported electricity and one that logs the imported energy from the grid.

From this I could calculate my total consumption as: total = generated - exported + imported.

Seems easy enough, but I don't know if this is possible in Domoticz...

niceandeasy
Posts: 147
Joined: Thursday 28 January 2016 23:25
Target OS: Raspberry Pi
Domoticz version: 3.8153
Location: NL
Contact:

Re: Virtual meter that is the sum of two other meters

Post by niceandeasy » Sunday 06 August 2017 23:39

I don't think Domoticz has a ready-made virtual meter that can add up the values of a list of other meters. However, you can do that with scripting.

freijn
Posts: 378
Joined: Friday 23 December 2016 17:40
Target OS: Raspberry Pi
Domoticz version:
Location: Netherlands Purmerend
Contact:

Re: Virtual meter that is the sum of two other meters

Post by freijn » Monday 07 August 2017 8:48

This is the lua code I am using to do this virtual meter, however.....

Updates from my solare panel are much slower than from my P1 smart meter.
On a steady ( no clouds ) day it works great. On a cloudy day it could be the solar panels are still reporting "no power" and the house
is consuming a lot, while on my P1 updates I do see a different indication. So this can only be used as a guideline but gives you a good
indication during the day.

Cheers,

Frank

Code: Select all

--
-- Domoticz passes information to scripts through a number of global tables
--
-- device changed contains state and svalues for the device that changed.
--   devicechanged['yourdevicename'] = state 
--   devicechanged['svalues'] = svalues string 
--
commandArray = {}

--powersensor = "Power"

--if (devicechanged[powersensor]) then
 --  print( " ####Power debug: "..devicechanged[powersensor])
   -- commandArray['Variable:LUX']=tostring(devicechanged[luxsensor])
--  var1, var2,var3,var4,var5,var6 = string.match(otherdevices_svalues['Power'], "(%d+%.*%d*);(%d+%.*%d*);(%d+%.*%d*);(%d+%.*%d*);(%d+%.*%d*);(%d+%.*%d*)")
--   print( " ####Power debug: "..var6)
 --  end

solarsensor = "SolarEdge kWh"
if (devicechanged[solarsensor]) then
   --print( " ####Solar debug: "..devicechanged[solarsensor])
   Solarvar1, var2 = string.match(otherdevices_svalues[solarsensor], "(%d+%.*%d*);(%d+%.*%d*)")
   print( " ####Solar debug: "..Solarvar1)

   powersensor = "Power"
   -- if (devicechanged[powersensor]) then
   --print( " ####Power debug: "..devicechanged[powersensor])
   var1, var2,var3,var4,Powervar5,Powervar6 = string.match(otherdevices_svalues['Power'], "(%d+%.*%d*);(%d+%.*%d*);(%d+%.*%d*);(%d+%.*%d*);(%d+%.*%d*);(%d+%.*%d*)")
   print( " ####Power debug: "..Powervar5)

   powercount = tonumber(Powervar6)
   solarcount = tonumber(Solarvar1)
 
   consume = solarcount - powercount
   print( " ####Consume debug: "..consume)
 
   ttidx = otherdevices_idx['PowerConsumtion']
   commandArray['UpdateDevice'] = ttidx..'|0|'..consume
end

return commandArray

gajotnt
Posts: 68
Joined: Monday 06 February 2017 13:48
Target OS: Raspberry Pi
Domoticz version: V4.9700
Location: Azores
Contact:

Re: Virtual meter that is the sum of two other meters

Post by gajotnt » Wednesday 13 December 2017 15:49

Hello, tried to figure out the code you provided :/

I have a meter for the main house, and another meter for a small apartement on the back (that is connected to the main house)
So i would like to subtract the apartment meter from the main house meter, so the resulte gives me what i im actualy using in the main house.
But by looking at the code above i have no ideia how to do this :/

l0gic
Posts: 148
Joined: Tuesday 08 October 2013 9:35
Target OS: Linux
Domoticz version: Latest
Contact:

Re: Virtual meter that is the sum of two other meters

Post by l0gic » Wednesday 13 December 2017 16:20

Hi,
I've also done something similar.
I've a number of power clamps monitoring power into my main consumer unit, outside consumer unit plus I have a feed from my SunnyBoy solar.
I use these to indicate via a dummy power devices the instantaneous usage (Kw) and historical (Kwh).
The devices indicate the total house load (House + Outside) as well as the incoming demand (Total - Solar).

My script also writes out to a csv file, not necessary for the script though.
As it stands the script writes out to the log a lot, change it by setting the printdata / printdebug values to false.

Code: Select all

-- demo time script

-- Set printing to log options (true / false)
printData = true
-- printData = false						-- writes execution information to the log for script performance information
-- printDebug = false						-- writes detailed information for fault finding purposes
 printDebug = true

-- Get current date & time
t1 = os.time()
local currentDate = os.date("*t");  -- sets up currentDate.[table] 
-- (currentDate.year [full], .month [1-12], .day [1-31], .hour [0-23], .min [0-59], .sec [0-59], .wday [0-6 {Sun-Sat}])
sCurrentTime = currentDate.year .. "-" .. currentDate.month .. "-" .. currentDate.day .. " " .. currentDate.hour .. ":" .. currentDate.min .. ":" .. currentDate.sec

function update(device, id, power, energy, index)
commandArray[index] = {['UpdateDevice'] = id .. "|0|" .. power .. ";" .. energy}
end 


commandArray = {}

SolarPowerGeneration, SolarEnergyGeneration = otherdevices_svalues["Solar Generation"]:match("([^;]+);([^;]+)")

if printDebug == true then
	print(" ----- SolarPowerGeneration = " .. SolarPowerGeneration .. " W");
	print(" ----- SolarEnergyGeneration = " .. SolarEnergyGeneration .. " Wh");
end

MainCUPowerUsage, MainCUEnergyUsage = otherdevices_svalues["Main Consumer Unit"]:match("([^;]+);([^;]+)")

if printDebug == true then
	print(" ----- MainCUPowerUsage = " .. MainCUPowerUsage .. " W");
	print(" ----- MainCUEnergyUsage = " .. MainCUEnergyUsage .. " Wh");
end

GardenCUPowerUsage, GardenCUEnergyUsage = otherdevices_svalues["Garden Consumer Unit"]:match("([^;]+);([^;]+)")

if printDebug == true then
print(" ----- GardenCUPowerUsage = " .. GardenCUPowerUsage .. " W");
print(" ----- GardenCUEnergyUsage = " .. GardenCUEnergyUsage .. " Wh");
end
-- Do the calculations
-- CurrentPowerBalance = SolarPowerGeneration - (MainCUPowerUsage + GardenCUPowerUsage)
-- CurrentEnergyBalance = SolarEnergyGeneration - (MainCUEnergyUsage + GardenCUEnergyUsage)
CurrentPowerBalance = (MainCUPowerUsage + GardenCUPowerUsage) - SolarPowerGeneration
CurrentEnergyBalance = (MainCUEnergyUsage + GardenCUEnergyUsage) - SolarEnergyGeneration

HousePower = (MainCUPowerUsage + GardenCUPowerUsage)
HouseEnergy = (MainCUEnergyUsage + GardenCUEnergyUsage)

if printDebug == true then	
	print(" ----- CurrentPowerBalance = " .. CurrentPowerBalance .. " W");
	print(" ----- CurrentEnergyBalance = " .. CurrentEnergyBalance .. " Wh");
end

if printData == true then	

	if CurrentPowerBalance <0 then
		print("FREE Electric - Whoop!    " .. CurrentPowerBalance .. "W");
	end
end
	
-- update the counters	
-- Total power 
update("House Power Incoming", 475, CurrentPowerBalance, CurrentEnergyBalance, 1) -- 475 is the ID of the dummy incoming device
-- Load of the House	
update("House Load", 518, HousePower, HouseEnergy, 2) -- 518 is the ID of dummy house consumption device

-- update the user variables (used to write to a csv for futher analysis)
-- House Load
commandArray['Variable:VarHouseLoad_Power'] = tostring(HousePower)
commandArray['Variable:VarHouseLoad_Energy'] = tostring(HouseEnergy)
-- Grid Load
commandArray['Variable:VarGridLoad_Power'] = tostring(CurrentPowerBalance)
commandArray['Variable:VarGridLoad_Energy'] = tostring(CurrentEnergyBalance)
-- MainCU Load
commandArray['Variable:VarMainCU_Power'] = tostring(MainCUPowerUsage)
commandArray['Variable:VarMainCU_Energy'] = tostring(MainCUEnergyUsage)
-- Garden CU Load
commandArray['Variable:VarGardenCU_Power'] = tostring(GardenCUPowerUsage)
commandArray['Variable:VarGardenCU_Energy'] = tostring(GardenCUEnergyUsage)
	


	
   -- save new values to file

   file = io.open("/opt/scripts/housepower.csv", "a") -- append
   file:write("\n")  -- new line
   file:write (sCurrentTime)
   file:write(",")
   file:write(HousePower) -- Total House Load
   file:write(",")
   file:write(MainCUPowerUsage) -- Main CU
   file:write(",")
   file:write(GardenCUPowerUsage) --  Garden CU
   file:write(",")
   file:write(CurrentPowerBalance) -- Grid Demand
   file:close()
   

return commandArray
Be careful with the type of dummy device you create, you need the Type = Usage and Energy Read = From Device

HTH

Kevin
Non credus crepitus

gajotnt
Posts: 68
Joined: Monday 06 February 2017 13:48
Target OS: Raspberry Pi
Domoticz version: V4.9700
Location: Azores
Contact:

Re: Virtual meter that is the sum of two other meters

Post by gajotnt » Wednesday 13 December 2017 17:43

-MainCU
-GardenCU
-Solar

are the names of your meter sensors in domoticz right?

gajotnt
Posts: 68
Joined: Monday 06 February 2017 13:48
Target OS: Raspberry Pi
Domoticz version: V4.9700
Location: Azores
Contact:

Re: Virtual meter that is the sum of two other meters

Post by gajotnt » Wednesday 13 December 2017 19:13

Got it working, thanks :D

l0gic
Posts: 148
Joined: Tuesday 08 October 2013 9:35
Target OS: Linux
Domoticz version: Latest
Contact:

Re: Virtual meter that is the sum of two other meters

Post by l0gic » Wednesday 13 December 2017 19:40

gajotnt wrote:
Wednesday 13 December 2017 17:43
-MainCU
-GardenCU
-Solar

are the names of your meter sensors in domoticz right?
Yeah, I'm a bit late in replying.
Glad it's all working.
Non credus crepitus

gajotnt
Posts: 68
Joined: Monday 06 February 2017 13:48
Target OS: Raspberry Pi
Domoticz version: V4.9700
Location: Azores
Contact:

Re: Virtual meter that is the sum of two other meters

Post by gajotnt » Friday 15 December 2017 13:13

Did some tweaking, in the sense i removed all of the CVS log stuff.
But have there some douts.
-- Total power
update("House Power Incoming", 475, CurrentPowerBalance, CurrentEnergyBalance, 1) -- 475 is the ID of the dummy incoming device
-- Load of the House
update("House Load", 518, HousePower, HouseEnergy, 2) -- 518 is the ID of dummy house consumption device
What does the 1 (in total power) and 2 (in House), mean?

Also im doing some troubleshooting because arround the time i started using this, the TOTAL meter stopped updating the "Energy Usage" graph, but i think its because of the firmware of the metering device and not the script, since i guess it only reads the value does the calculations and writes it to another virtual meter, but still can you take a look?

Total: is the meter that gets information from the whole house
Apartamento: is the meter that gets information from a apartment
Casa: the result of the subtration of the apartment from the Total value

This is the code im using:

Code: Select all

-- demo time script

-- Get current date & time
t1 = os.time()
local currentDate = os.date("*t");  -- sets up currentDate.[table] 
-- (currentDate.year [full], .month [1-12], .day [1-31], .hour [0-23], .min [0-59], .sec [0-59], .wday [0-6 {Sun-Sat}])
sCurrentTime = currentDate.year .. "-" .. currentDate.month .. "-" .. currentDate.day .. " " .. currentDate.hour .. ":" .. currentDate.min .. ":" .. currentDate.sec

function update(device, id, power, energy, index)
commandArray[index] = {['UpdateDevice'] = id .. "|0|" .. power .. ";" .. energy}
end 

commandArray = {}

TotalPowerUsage, TotalEnergyUsage = otherdevices_svalues["Total"]:match("([^;]+);([^;]+)")

ApartamentoPowerUsage, ApartamentoEnergyUsage = otherdevices_svalues["Apartamento"]:match("([^;]+);([^;]+)")

CurrentPowerBalance = TotalPowerUsage - ApartamentoPowerUsage
CurrentEnergyBalance = TotalEnergyUsage - ApartamentoEnergyUsage

update("Casa", 50, CurrentPowerBalance, CurrentEnergyBalance, 2) -- 50 is the ID of the dummy incoming device


return commandArray

l0gic
Posts: 148
Joined: Tuesday 08 October 2013 9:35
Target OS: Linux
Domoticz version: Latest
Contact:

Re: Virtual meter that is the sum of two other meters

Post by l0gic » Friday 15 December 2017 17:21

Hi,
The 1 and 2 refer to the commandArray[x] values.
If you only update one value when running the script then this value can be 1.
If you chose to update 2 or more values then they all need their own commandArray[x] value. Otherwise only the last commandArray value will be updated.

Your script looks fine to me, I can't see any reason why it wouldn't work.
Try putting some print commands in so you can see in the logs if the expected values are in there.

ATB

Kevin
Non credus crepitus

gajotnt
Posts: 68
Joined: Monday 06 February 2017 13:48
Target OS: Raspberry Pi
Domoticz version: V4.9700
Location: Azores
Contact:

Re: Virtual meter that is the sum of two other meters

Post by gajotnt » Friday 15 December 2017 18:39

Thanks :)
After some testing it was the FW of the sonoff that was sending the KWhToday instead of the KWhTotal, everything is working now :)
Thanks

SunnyBoy
Posts: 1
Joined: Friday 11 May 2018 19:21
Target OS: Raspberry Pi
Domoticz version:
Contact:

Re: Virtual meter that is the sum of two other meters

Post by SunnyBoy » Friday 11 May 2018 23:28

I wanted to do the same, and using this thread and some other links I managed to get it to work as well.

I documented this in the wiki here for future reference, please expand where you can: https://www.domoticz.com/wiki/Virtual_meter. Hope this helps others :)

Post Reply

Who is online

Users browsing this forum: No registered users and 5 guests