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.innogysmarthome.internal.client.entity.device;
15 import static org.openhab.binding.innogysmarthome.internal.InnogyBindingConstants.*;
17 import java.util.Collections;
18 import java.util.List;
20 import java.util.Objects;
22 import org.openhab.binding.innogysmarthome.internal.client.entity.capability.Capability;
23 import org.openhab.binding.innogysmarthome.internal.client.entity.location.Location;
24 import org.openhab.binding.innogysmarthome.internal.client.entity.message.Message;
26 import com.google.gson.annotations.SerializedName;
29 * Defines the structure of a {@link Device}.
31 * @author Oliver Kuhl - Initial contribution
35 public static final String DEVICE_MANUFACTURER_RWE = "RWE";
36 public static final String DEVICE_MANUFACTURER_INNOGY = "innogy";
38 protected static final String PROTOCOL_ID_COSIP = "Cosip";
39 protected static final String PROTOCOL_ID_VIRTUAL = "Virtual";
40 protected static final String PROTOCOL_ID_WMBUS = "wMBus";
43 * Unique id for the device, always available in model.
48 * Identifier of the manufacturer, always available in model
50 private String manufacturer;
53 * Version number of the device for the domain model.
55 * If the functionality of the device changes, the version must
56 * be increased to indicate that there are new or changed attributes
57 * of the device. Always available in model.
59 private String version;
62 * Defines the product, which is used as an identifier for selecting the
63 * right add-in to support the functionality of the device.
64 * Remark: one add-in can support multiple devices, e.g.
65 * core.RWE, which supports all RWE hardware devices (also referred to as core devices).
66 * Always available in model.
68 private String product;
71 * Device number or id like SGTIN given by the manufacturer. Optional.
73 private String serialnumber;
76 * Specifies the type of the device, which is defined by the manufacturer. The triple of device type, manufacturer
77 * and the version must be unique.
78 * Always available in model.
82 private DeviceConfig config;
84 private List<String> capabilities;
86 private Map<String, Capability> capabilityMap;
88 private DeviceState deviceState;
91 * The tag container can contain any number of properties for grouping of the devices in the client, e.g. category
92 * of device like “security related”. The tags can be freely chosen by the client and will not be considered by the
93 * system for any business logic.
98 // private List<Property> tagList;
101 * The location contains the link to the location of the device. Optional.
103 @SerializedName("location")
104 private String locationLink;
106 private transient Location location;
108 private List<Message> messageList;
110 private boolean lowBattery;
113 * Stores, if the {@link Device} is battery powered.
115 private boolean batteryPowered = false;
120 public String getId() {
125 * @param id the id to set
127 public void setId(String id) {
132 * @return the manufacturer
134 public String getManufacturer() {
139 * @param manufacturer the manufacturer to set
141 public void setManufacturer(String manufacturer) {
142 this.manufacturer = manufacturer;
146 * @return the version
148 public String getVersion() {
153 * @param version the version to set
155 public void setVersion(String version) {
156 this.version = version;
160 * @return the product
162 public String getProduct() {
167 * @param product the product to set
169 public void setProduct(String product) {
170 this.product = product;
174 * @return the serialnumber
176 public String getSerialnumber() {
181 * @param serialnumber the serialnumber to set
183 public void setSerialnumber(String serialnumber) {
184 this.serialnumber = serialnumber;
188 * Returns true, if the {@link Device} has a serial number.
192 public boolean hasSerialNumber() {
193 return serialnumber != null && !serialnumber.isEmpty();
199 public String getType() {
204 * @param type the type to set
206 public void setType(String type) {
213 public DeviceConfig getConfig() {
218 * @param config the config to set
220 public void setConfig(DeviceConfig config) {
221 this.config = config;
225 * Returns the {@link DeviceState}. Only available, if device has a state. Better check with
226 * {@link Device#hasDeviceState()} first!
228 * @return the entityState or null
230 public DeviceState getDeviceState() {
235 * @param deviceState the deviceState to set
237 public void setDeviceState(DeviceState deviceState) {
238 this.deviceState = deviceState;
242 * Returns, if the {@link Device} has a state. Not all {@link Device}s have a state.
246 public boolean hasDeviceState() {
247 return deviceState != null;
251 * @return the capabilityList
253 public List<String> getCapabilities() {
254 return Objects.requireNonNullElse(capabilities, Collections.emptyList());
258 * @param capabilityList the capabilityList to set
260 public void setCapabilities(List<String> capabilityList) {
261 this.capabilities = capabilityList;
265 * @param capabilityMap the capabilityMap to set
267 public void setCapabilityMap(Map<String, Capability> capabilityMap) {
268 this.capabilityMap = capabilityMap;
272 * @return the capabilityMap
274 public Map<String, Capability> getCapabilityMap() {
275 return this.capabilityMap;
279 * Returns the {@link Capability} with the given id.
284 public Capability getCapabilityWithId(String id) {
285 return this.capabilityMap.get(id);
289 * @return the locationLink
291 public String getLocationLink() {
296 * @param locationLink the locationList to set
298 public void setLocation(String locationLink) {
299 this.locationLink = locationLink;
303 * Returns the id of the {@link Location}
307 public String getLocationId() {
308 if (locationLink != null) {
309 return locationLink.replace("/location/", "");
315 * Returns the {@link Location} of the {@link Device}. Better check with {@link Device#hasLocation()} first, as not
316 * all devices have one.
318 * @return the location
320 public Location getLocation() {
325 * @param location the location to set
327 public void setLocation(Location location) {
328 this.location = location;
332 * Returns, if the {@link Device} has a {@link Location}. Not all devices have a {@link Location}...
334 * @return boolean true, if a {@link Location} is set, else false
336 public boolean hasLocation() {
337 return location != null;
341 * @return the messageList
343 public List<Message> getMessageList() {
348 * @param messageList the messageList to set
350 public void setMessageList(List<Message> messageList) {
351 this.messageList = messageList;
352 applyMessageList(messageList);
355 private void applyMessageList(List<Message> messageList) {
356 if (messageList != null && !messageList.isEmpty()) {
357 boolean isUnreachableMessageFound = false;
358 boolean isLowBatteryMessageFound = false;
359 for (final Message message : messageList) {
360 switch (message.getType()) {
361 case Message.TYPE_DEVICE_UNREACHABLE:
362 isUnreachableMessageFound = true;
364 case Message.TYPE_DEVICE_LOW_BATTERY:
365 isLowBatteryMessageFound = true;
369 if (isUnreachableMessageFound) {
370 setReachable(false); // overwrite only when there is a corresponding message (to keep the state of the
371 // API in other cases)
373 if (isLowBatteryMessageFound) {
374 setLowBattery(true); // overwrite only when there is a corresponding message (to keep the state of the
375 // API in other cases)
381 * Sets if the {@link Device} is reachable;
385 private void setReachable(boolean isReachable) {
386 if (getDeviceState().hasIsReachableState()) {
387 getDeviceState().setReachable(isReachable);
392 * Returns if the {@link Device} is reachable.
396 public boolean isReachable() {
397 return getDeviceState().getState().getIsReachable().getValue();
401 * Sets the low battery state for the {@link Device}.
403 * @param hasLowBattery
405 private void setLowBattery(boolean hasLowBattery) {
406 this.lowBattery = hasLowBattery;
410 * Returns true if the {@link Device} has a low battery warning. Only available on battery devices.
414 public boolean hasLowBattery() {
419 * Returns true, if the {@link Device} is battery powered.
423 public boolean isBatteryPowered() {
424 return batteryPowered;
428 * Sets if the device is battery powered.
432 public void setIsBatteryPowered(boolean hasBattery) {
433 batteryPowered = hasBattery;
437 * Returns true, if the {@link Device} has {@link Message}s.
441 public boolean hasMessages() {
442 return (messageList != null && !messageList.isEmpty());
446 * Returns true if the device is a controller (SHC).
450 public boolean isController() {
451 return DEVICE_SHC.equals(type) || DEVICE_SHCA.equals(type);
455 * Returns true, if the device is made by RWE.
459 public boolean isRWEDevice() {
460 return DEVICE_MANUFACTURER_RWE.equals(manufacturer);
464 * Returns true, if the device is made by innogy.
468 public boolean isInnogyDevice() {
469 return DEVICE_MANUFACTURER_INNOGY.equals(manufacturer);
473 * Returns true, if the {@link Device} is a virtual device (e.g. a VariableActuator).
477 public boolean isVirtualDevice() {
478 return PROTOCOL_ID_VIRTUAL.equals(getConfig().getProtocolId());
482 * Returns true, if the {@link Device} is a radio device.
486 public boolean isRadioDevice() {
487 return PROTOCOL_ID_COSIP.equals(getConfig().getProtocolId())
488 || PROTOCOL_ID_WMBUS.equals(getConfig().getProtocolId());
492 * Returns true, if the {@link Device} is a CoSip device.
496 public boolean isCoSipDevice() {
497 return PROTOCOL_ID_COSIP.equals(getConfig().getProtocolId());
501 * Returns true, if the {@link Device} is a W-Mbus device.
505 public boolean isWMBusDevice() {
506 return PROTOCOL_ID_WMBUS.equals(getConfig().getProtocolId());
510 public String toString() {
511 final String string = "Device [" + "id=" + getId() + " manufacturer=" + getManufacturer() + " version="
512 + getVersion() + " product=" + getProduct() + " serialnumber=" + getSerialnumber() + " type="
513 + getType() + " name=" + getConfig().getName() + "]";