local scriptVar = 'openWeatherMap' return { on = { timer = { 'every hour' }, devices = { scriptVar .. 'Trigger', }, httpResponses = { scriptVar } }, logging = { level = domoticz.LOG_DEBUG, -- zmien DEBUG na .ERROR po sprawdzeniu dzialania skryptu marker = Prognoza , }, execute = function(dz, item) -- ******** nazwy urzadzen ustaw tak jak utworzyles w domoticz local openWeatherAPIKey = dz.variables('openWeatherAPIKey').value -- Type string var required local currentRain = dz.devices('Deszcz aktualnie') -- optional virtual Custom Sensor local rain48Hours = dz.devices('Deszcz na 48h') -- optional virtual Custom Sensor local rain8Days = dz.devices('Deszcz na 8 dni') -- optional virtual Custom Sensor local rainToday = dz.devices('Deszcz dziś') -- optional virtual Custom Sensor local rainTomorrow = dz.devices('Deszcz jutro') -- optional virtual Custom Sensor local weatherText = dz.devices('Prognoza') -- optional text Sensor local currentTemperature = dz.devices('Aktualna Temperatura') -- Optional virtual Temperature sensor local maxTemperature48Hours = dz.devices('Max Temperatura na 48h') -- Optional virtual Temperature sensor local maxTemperature8Days = dz.devices('Max Temperatura na 8 dni') -- Optional virtual Temperature sensor local minTemperature48Hours = dz.devices('Min Temperatura na 48h') -- Optional virtual Temperature sensor local minTemperature8Days = dz.devices('Min Temperatura na 8 dni') -- Optional virtual Temperature sensor local maxTemperatureToday = dz.devices('Max Temperatura dziś') -- Optional virtual Temperature sensor local maxTemperatureTomorrow = dz.devices('Max Temperatura jutro') -- Optional virtual Temperature sensor local avgTemperature48Hours = dz.devices('Srednia Temperatura na 48h') -- Optional virtual Temperature sensor local avgTemperature8Days = dz.devices('Srednia Temperatura na 8 dni') -- Optional virtual Temperature sensor -- ******** Nic nie zmieniaj ponizej tej linii local openWeatherURL = 'https://api.openweathermap.org/data/2.5/onecall?&units=metric' local DAY_SECONDS = 86400 local endOfToday = os.time{year = dz.time.year, month = dz.time.month, day = dz.time.day, hour = 0} + DAY_SECONDS local endOfTomorrow = endOfToday + DAY_SECONDS local function getCurrentRain(t) if t == nil then return 0 end local totalmm = 0 for key, mm in pairs(t) do totalmm = totalmm + mm end return totalmm end local function getDayNightSeconds(t) t.daySeconds = t.sunset - t.sunrise t.nightSeconds= DAY_SECONDS - t.daySeconds end local function get8DaysTemperatures(t) local maxTemperature = -100 local minTemperature = 100 local avgTemperature, avgHelper = 0, 0 for _, record in ipairs(t) do getDayNightSeconds(record) if record.temp.max > maxTemperature then maxTemperature = record.temp.max end if record.temp.min < minTemperature then minTemperature = record.temp.min end avgTemperature = ( record.temp.day * record.daySeconds + record.temp.night * record.nightSeconds ) / DAY_SECONDS avgHelper = avgHelper + avgTemperature end avgTemperature = avgHelper / #t return dz.utils.round(maxTemperature,1), dz.utils.round(minTemperature,1), dz.utils.round(avgTemperature,1) end local function getHoursTemperatures(t) local maxTemperature, maxTemperatureToday, maxTemperatureTomorrow = -100, -100, -100 local minTemperature = 100 local avgHelper = 0 for _, record in ipairs(t) do if record.dt < endOfToday and record.temp > maxTemperatureToday then maxTemperatureToday = record.temp end if record.dt > endOfToday and record.dt < endOfTomorrow and record.temp > maxTemperatureTomorrow then maxTemperatureTomorrow = record.temp end if record.temp > maxTemperature then maxTemperature = record.temp end if record.temp < minTemperature then minTemperature = record.temp end avgHelper = avgHelper + record.temp end return dz.utils.round(maxTemperature,1), dz.utils.round(minTemperature,1), dz.utils.round((avgHelper / #t),1), dz.utils.round(maxTemperatureToday,1), dz.utils.round(maxTemperatureTomorrow,1) end local function getHoursRain(t) if t == nil then return 0 end local totalmm,todaymm, tomorrowmm = 0,0,0 for key, record in ipairs(t) do if type(record) == 'table' and record.rain ~= nil then for id, mm in pairs(record.rain) do todaymm = todaymm + ( ( record.dt < endOfToday and mm ) or 0 ) tomorrowmm = tomorrowmm + ( ( record.dt > endOfToday and record.dt < endOfTomorrow and mm ) or 0 ) totalmm = totalmm + mm end end end return totalmm, todaymm, tomorrowmm end local function get8DaysRain(t) if t == nil then return 0 end local totalmm = 0 for key, record in ipairs(t) do if type(record) == 'table' and record.rain ~= nil then totalmm = totalmm + record.rain end end return totalmm end local function createResultTable(rt) rt.currentRain = getCurrentRain(rt.current.rain) rt.rain48Hours, rt.todaymm, rt.tomorrowmm = getHoursRain(rt.hourly) rt.rain8Days = get8DaysRain(rt.daily) rt.maxTemperature48Hours, rt.minTemperature48Hours, rt.avgTemperature48Hours, rt.maxTemperatureToday, rt.maxTemperatureTomorrow = getHoursTemperatures(rt.hourly) rt.maxTemperature8Days, rt.minTemperature8Days, rt.avgTemperature8Days = get8DaysTemperatures(rt.daily) rt.maxTemperature8Days = math.max(rt.maxTemperature48Hours, rt.maxTemperature8Days) rt.minTemperature8Days = math.min(rt.minTemperature48Hours, rt.minTemperature8Days) end local function updateTextDevice(t) local text = 'range: rain - max Temp' .. '\n' text = text .. 'current: ' .. t.currentRain .. ' mm, ' .. t.current.temp .. ' °C' .. '\n' text = text .. '48 hours: ' .. t.rain48Hours .. ' mm, ' .. t.maxTemperature48Hours .. ' °C' .. '\n' text = text .. '8 days: ' .. t.rain8Days .. ' mm, ' .. t.maxTemperature8Days .. ' °C' .. '\n' weatherText.updateText(text) end local function deviceExists(dv) if dv == nil then return false else return dz.utils.deviceExists(dv.name) end end local function updateDevice(dv, value) if deviceExists(dv) then if dv.deviceType == 'Temp' then dv.updateTemperature(value) else dv.updateCustomSensor(value) end end end local function updateDevices(rt) updateDevice(currentRain, rt.currentRain) updateDevice(rain48Hours, rt.rain48Hours) updateDevice(rain8Days, rt.rain8Days) updateDevice(rainTomorrow, rt.tomorrowmm) updateDevice(currentTemperature, rt.current.temp) updateDevice(maxTemperature48Hours, rt.maxTemperature48Hours) updateDevice(maxTemperature8Days, rt.maxTemperature8Days) updateDevice(maxTemperatureTomorrow, rt.maxTemperatureTomorrow) updateDevice(minTemperature48Hours, rt.minTemperature48Hours) updateDevice(minTemperature8Days, rt.minTemperature8Days) updateDevice(avgTemperature48Hours, rt.avgTemperature48Hours) updateDevice(avgTemperature8Days, rt.avgTemperature8Days) if deviceExists(rainToday) and rainToday.lastUpdate.dDate < ( endOfToday - DAY_SECONDS ) then updateDevice(rainToday, rt.todaymm) elseif deviceExists(rainToday) then updateDevice(rainToday, math.max(rt.todaymm, tonumber(rainToday.sValue))) end if deviceExists(maxTemperatureToday) and maxTemperatureToday.lastUpdate.dDate < ( endOfToday - DAY_SECONDS ) then updateDevice(maxTemperatureToday, rt.maxTemperatureToday) elseif deviceExists(maxTemperatureToday) then updateDevice(maxTemperatureToday, math.max(rt.maxTemperatureToday, maxTemperatureToday.temperature)) end if deviceExists(weatherText) then updateTextDevice(rt) end end -- main code if item.isHTTPResponse then if item.ok and item.isJSON then local rt = item.json createResultTable(rt) updateDevices(rt) else dz.log('There was a problem with the response from ' .. scriptVar, dz.LOG_ERROR) dz.log(item, dz.LOG_DEBUG) end else -- get the data from openweatherMap dz.openURL({ url = openWeatherURL .. '&lat=' .. dz.settings.location.latitude .. '&lon=' .. dz.settings.location.longitude .. '&appid=' .. openWeatherAPIKey, callback = scriptVar, -- see httpResponses above. }) end end }