2 * Copyright (c) 2010-2023 Contributors to the openHAB project
4 * See the NOTICE file(s) distributed with this work for additional
7 * This program and the accompanying materials are made available under the
8 * terms of the Eclipse Public License 2.0 which is available at
9 * http://www.eclipse.org/legal/epl-2.0
11 * SPDX-License-Identifier: EPL-2.0
13 package org.openhab.binding.solaredge.internal.model;
15 import static org.openhab.binding.solaredge.internal.SolarEdgeBindingConstants.*;
17 import java.util.HashMap;
20 import org.eclipse.jdt.annotation.NonNullByDefault;
21 import org.openhab.binding.solaredge.internal.handler.ChannelProvider;
22 import org.openhab.binding.solaredge.internal.model.LiveDataResponse.BatteryValue;
23 import org.openhab.binding.solaredge.internal.model.LiveDataResponse.Connection;
24 import org.openhab.binding.solaredge.internal.model.LiveDataResponse.SiteCurrentPowerFlow;
25 import org.openhab.binding.solaredge.internal.model.LiveDataResponse.Value;
26 import org.openhab.binding.solaredge.internal.model.LiveDataResponseMeterless.Energy;
27 import org.openhab.binding.solaredge.internal.model.LiveDataResponseMeterless.Overview;
28 import org.openhab.binding.solaredge.internal.model.LiveDataResponseMeterless.Power;
29 import org.openhab.core.thing.Channel;
30 import org.openhab.core.types.State;
33 * transforms the http response into the openhab datamodel (instances of State)
35 * @author Alexander Friese - initial contribution
38 public class LiveDataResponseTransformer extends AbstractDataResponseTransformer {
39 private static final Double ZERO_POWER = 0.0;
41 private final ChannelProvider channelProvider;
43 public LiveDataResponseTransformer(ChannelProvider channelProvider) {
44 this.channelProvider = channelProvider;
47 public Map<Channel, State> transform(LiveDataResponseMeterless response) {
48 Map<Channel, State> result = new HashMap<>(20);
49 Overview overview = response.getOverview();
51 if (overview != null) {
52 Power currentPower = overview.currentPower;
53 if (currentPower != null) {
54 putPowerType(result, channelProvider.getChannel(CHANNEL_GROUP_LIVE, CHANNEL_ID_PRODUCTION),
55 currentPower.power, UNIT_W);
57 putPowerType(result, channelProvider.getChannel(CHANNEL_GROUP_LIVE, CHANNEL_ID_PRODUCTION), null,
61 Energy lastDayData = overview.lastDayData;
62 if (lastDayData != null) {
63 putEnergyType(result, channelProvider.getChannel(CHANNEL_GROUP_AGGREGATE_DAY, CHANNEL_ID_PRODUCTION),
64 lastDayData.energy, UNIT_WH);
66 putEnergyType(result, channelProvider.getChannel(CHANNEL_GROUP_AGGREGATE_DAY, CHANNEL_ID_PRODUCTION),
70 Energy lastMonthData = overview.lastMonthData;
71 if (lastMonthData != null) {
72 putEnergyType(result, channelProvider.getChannel(CHANNEL_GROUP_AGGREGATE_MONTH, CHANNEL_ID_PRODUCTION),
73 lastMonthData.energy, UNIT_WH);
75 putEnergyType(result, channelProvider.getChannel(CHANNEL_GROUP_AGGREGATE_MONTH, CHANNEL_ID_PRODUCTION),
79 Energy lastYearData = overview.lastYearData;
80 if (lastYearData != null) {
81 putEnergyType(result, channelProvider.getChannel(CHANNEL_GROUP_AGGREGATE_YEAR, CHANNEL_ID_PRODUCTION),
82 lastYearData.energy, UNIT_WH);
84 putEnergyType(result, channelProvider.getChannel(CHANNEL_GROUP_AGGREGATE_YEAR, CHANNEL_ID_PRODUCTION),
88 // week production is not available
89 putEnergyType(result, channelProvider.getChannel(CHANNEL_GROUP_AGGREGATE_WEEK, CHANNEL_ID_PRODUCTION), null,
95 public Map<Channel, State> transform(LiveDataResponse response) {
96 Map<Channel, State> result = new HashMap<>(20);
97 SiteCurrentPowerFlow siteCurrentPowerFlow = response.getSiteCurrentPowerFlow();
99 if (siteCurrentPowerFlow != null) {
100 Value pv = siteCurrentPowerFlow.pv;
101 Value load = siteCurrentPowerFlow.load;
102 BatteryValue storage = siteCurrentPowerFlow.storage;
103 Value grid = siteCurrentPowerFlow.grid;
106 putPowerType(result, channelProvider.getChannel(CHANNEL_GROUP_LIVE, CHANNEL_ID_PRODUCTION),
107 pv.currentPower, siteCurrentPowerFlow.unit);
108 putStringType(result, channelProvider.getChannel(CHANNEL_GROUP_LIVE, CHANNEL_ID_PV_STATUS), pv.status);
112 putPowerType(result, channelProvider.getChannel(CHANNEL_GROUP_LIVE, CHANNEL_ID_CONSUMPTION),
113 load.currentPower, siteCurrentPowerFlow.unit);
114 putStringType(result, channelProvider.getChannel(CHANNEL_GROUP_LIVE, CHANNEL_ID_LOAD_STATUS),
118 if (storage != null) {
119 putStringType(result, channelProvider.getChannel(CHANNEL_GROUP_LIVE, CHANNEL_ID_BATTERY_STATUS),
121 putStringType(result, channelProvider.getChannel(CHANNEL_GROUP_LIVE, CHANNEL_ID_BATTERY_CRITICAL),
123 putPercentType(result, channelProvider.getChannel(CHANNEL_GROUP_LIVE, CHANNEL_ID_BATTERY_LEVEL),
124 storage.chargeLevel);
128 putStringType(result, channelProvider.getChannel(CHANNEL_GROUP_LIVE, CHANNEL_ID_GRID_STATUS),
132 // init fields with zero
133 putPowerType(result, channelProvider.getChannel(CHANNEL_GROUP_LIVE, CHANNEL_ID_IMPORT), ZERO_POWER,
134 siteCurrentPowerFlow.unit);
135 putPowerType(result, channelProvider.getChannel(CHANNEL_GROUP_LIVE, CHANNEL_ID_EXPORT), ZERO_POWER,
136 siteCurrentPowerFlow.unit);
137 putPowerType(result, channelProvider.getChannel(CHANNEL_GROUP_LIVE, CHANNEL_ID_BATTERY_CHARGE), ZERO_POWER,
138 siteCurrentPowerFlow.unit);
139 putPowerType(result, channelProvider.getChannel(CHANNEL_GROUP_LIVE, CHANNEL_ID_BATTERY_DISCHARGE),
140 ZERO_POWER, siteCurrentPowerFlow.unit);
141 putPowerType(result, channelProvider.getChannel(CHANNEL_GROUP_LIVE, CHANNEL_ID_BATTERY_CHARGE_DISCHARGE),
142 ZERO_POWER, siteCurrentPowerFlow.unit);
144 // determine power flow from connection list
145 if (siteCurrentPowerFlow.connections != null) {
146 for (Connection con : siteCurrentPowerFlow.connections) {
148 if (con.from != null && con.from.equalsIgnoreCase(LiveDataResponse.GRID)) {
149 putPowerType(result, channelProvider.getChannel(CHANNEL_GROUP_LIVE, CHANNEL_ID_IMPORT),
150 grid.currentPower, siteCurrentPowerFlow.unit);
151 } else if (con.to != null && con.to.equalsIgnoreCase(LiveDataResponse.GRID)) {
152 putPowerType(result, channelProvider.getChannel(CHANNEL_GROUP_LIVE, CHANNEL_ID_EXPORT),
153 grid.currentPower, siteCurrentPowerFlow.unit);
157 if (storage != null) {
158 Double currentPower = storage.currentPower != null ? storage.currentPower : 0;
159 if (con.from != null && con.from.equalsIgnoreCase(LiveDataResponse.STORAGE)) {
161 channelProvider.getChannel(CHANNEL_GROUP_LIVE, CHANNEL_ID_BATTERY_DISCHARGE),
162 currentPower, siteCurrentPowerFlow.unit);
164 channelProvider.getChannel(CHANNEL_GROUP_LIVE, CHANNEL_ID_BATTERY_CHARGE_DISCHARGE),
165 -1 * currentPower, siteCurrentPowerFlow.unit);
166 } else if (con.to != null && con.to.equalsIgnoreCase(LiveDataResponse.STORAGE)) {
168 channelProvider.getChannel(CHANNEL_GROUP_LIVE, CHANNEL_ID_BATTERY_CHARGE),
169 currentPower, siteCurrentPowerFlow.unit);
171 channelProvider.getChannel(CHANNEL_GROUP_LIVE, CHANNEL_ID_BATTERY_CHARGE_DISCHARGE),
172 currentPower, siteCurrentPowerFlow.unit);