Event triggered multiple times at once

Easy to use, 100% Lua-based event scripting framework.

Moderator: leecollings

Post Reply
galinette
Posts: 68
Joined: Monday 11 December 2017 22:57
Target OS: Raspberry Pi / ODroid
Domoticz version:
Contact:

Event triggered multiple times at once

Post by galinette »

Hi,

I have a first dzvents script which updates 4 virtual sensors (solar angles, direct and diffuse irradiance)
I have another dzvents script which is triggered by the 4 devices

The issue is, each time the first one is executed, the second is fired 4 times in less than a second. This causes issues in the subsequent radio device calls. Even worse, at first call only one device has been updated, at second call another one, etc... This totally messes the script behavior, and I can't even add a condition to stop the script if it has already been called recently, as it then runs with only one of the device values updated.

Is there any solution? I'm using the stable release.

Thanks!
galinette
Posts: 68
Joined: Monday 11 December 2017 22:57
Target OS: Raspberry Pi / ODroid
Domoticz version:
Contact:

Re: Event triggered multiple times at once

Post by galinette »

Fragment of the first script which updates the solar data:

Code: Select all

domoticz.devices(idxDNI).updateRadiation(DNI)
domoticz.devices(idxGHI).updateRadiation(GHI)
domoticz.devices(idxSolarAzimuth).updateCustomSensor(domoticz.round(azimuth,0))
domoticz.devices(idxSolarAltitude).updateCustomSensor(domoticz.round(sunAltitude,0))

And the full event that gets executed four times:

Code: Select all

return {
	logging = {
		level = domoticz.LOG_INFO,
		marker = 'Shading'
	},
	on = {
		timer = {
			'every 10 minutes'
		},
		devices = {
			1150,
			1151,
			1155,
			1156
		}
	},
	data = {
		lastDNI = {initial=0},
		lastGHI = {initial=0},
		lastAlt = {initial=0},
		lastAzi = {initial=0}
	},
	execute = function(domoticz, device)
	    local idxSolarAzimuth = 1150
        local idxSolarAltitude = 1151
        local idxDNI = 1155 -- (Solar Radiation) Direct Normal Irradiance Device ID
        local idxGHI = 1156 -- (Solar Radiation) Global Horizontal Irradiance Device ID
        local groundAlbedo = 0.2

        local solarAzi = domoticz.devices(idxSolarAzimuth).rawData[1]
        local solarAlt = domoticz.devices(idxSolarAltitude).rawData[1]
        local DNI = domoticz.devices(idxDNI).radiation
        local GHI = domoticz.devices(idxGHI).radiation
        local change = false
        
        if solarAzi~=lastAzi then
            domoticz.log('Azimuth changed', domoticz.LOG_INFO)
            change = true
            lastAzi = solarAzi
        end
        if solarAlt~=lastAlt then
            domoticz.log('Altitude changed', domoticz.LOG_INFO)
            change = true
            lastAlt = solarAlt
        end
        if DNI~=lastDNI then
            domoticz.log('DNI changed', domoticz.LOG_INFO)
            change = true
            lastDNI = DNI
        end
        if GHI~=lastGHI then
            domoticz.log('GHI changed', domoticz.LOG_INFO)
            change = true
            lastGHI = GHI
        end

        if change then
            local solarAziRad = solarAzi*3.14159/180
            local solarAltRad = solarAlt*3.14159/180
            local sx = math.cos(solarAziRad)*math.cos(solarAltRad)
            local sy = math.sin(solarAziRad)*math.cos(solarAltRad)
            local sz = math.sin(solarAltRad)
    
            local horizontalDiffuseIrradiance = GHI-DNI*sz
            local verticalDiffuseIrradiance = horizontalDiffuseIrradiance*(groundAlbedo*0.5+0.5)
            
            local sqrthalf = math.sqrt(0.5)
            local GI_SW = verticalDiffuseIrradiance+DNI*math.max(0.0,-sx*sqrthalf+sy*sqrthalf)
            local GI_SE = verticalDiffuseIrradiance+DNI*math.max(0.0,-sx*sqrthalf-sy*sqrthalf)
            local GI_NW = verticalDiffuseIrradiance+DNI*math.max(0.0, sx*sqrthalf+sy*sqrthalf)
            local GI_NE = verticalDiffuseIrradiance+DNI*math.max(0.0, sx*sqrthalf-sy*sqrthalf)
            domoticz.log('SW='..GI_SW, domoticz.LOG_INFO)
            domoticz.log('SE='..GI_SE, domoticz.LOG_INFO)
            domoticz.log('NW='..GI_NW, domoticz.LOG_INFO)
            domoticz.log('NE='..GI_NE, domoticz.LOG_INFO)
        end
	end
}
rrozema
Posts: 470
Joined: Thursday 26 October 2017 13:37
Target OS: Raspberry Pi / ODroid
Domoticz version: beta
Location: Delft
Contact:

Re: Event triggered multiple times at once

Post by rrozema »

Inside your function, use the device parameter to identify the device that actually was changed. Then only update the information for that particular device. Here's a snippet of code (untested) that might serve as an example. It checks only two devices, you'll have to add more elseif's at the location indicated by the comments, plus add some more code in the bottom:

Code: Select all

   execute = function(domoticz, device)
      local change = false
      if (device.idx == idxSolarAzimuth) then
         if (device.rawData[1] ~= domoticz.data.lastAzi) then
            domoticz.log('Azimuth changed', domoticz.LOG_INFO)
            domoticz.data.lastAzi = device.rawData[1]
            change = true
         end
      elseif (device.idx == idxSolarAltitude) then
         if (device.rawData[1] ~= domoticz.data.lastAlt) then
            domoticz.log('Altitude changed', domoticz.LOG_INFO)
            domoticz.data.lastAlt = device.rawData[1]
            change = true
         end
      // add more elseifs, one for each device...
      end
   
      if change then
         // do something
      end
   end
Your code will still be executed 4 times, once for each device, but it will know what data to act upon.
Post Reply

Who is online

Users browsing this forum: No registered users and 1 guest