2 * Copyright (c) 2010-2020 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.shelly.internal.discovery;
15 import static org.openhab.binding.shelly.internal.ShellyBindingConstants.*;
16 import static org.openhab.binding.shelly.internal.api.ShellyApiJsonDTO.*;
17 import static org.openhab.binding.shelly.internal.util.ShellyUtils.*;
19 import java.util.LinkedHashMap;
22 import org.eclipse.jdt.annotation.NonNullByDefault;
23 import org.openhab.core.thing.ThingTypeUID;
24 import org.openhab.core.thing.ThingUID;
27 * The {@link ShellyThingCreator} maps the device id into the thing type id
29 * @author Markus Michels - Initial contribution
32 public class ShellyThingCreator {
33 private static final Map<String, String> THING_TYPE_MAPPING = new LinkedHashMap<>();
35 // mapping by device type id
36 THING_TYPE_MAPPING.put(SHELLYDT_1PM, THING_TYPE_SHELLY1PM_STR);
37 THING_TYPE_MAPPING.put(SHELLYDT_1, THING_TYPE_SHELLY1_STR);
38 THING_TYPE_MAPPING.put(SHELLYDT_3EM, THING_TYPE_SHELLY3EM_STR);
39 THING_TYPE_MAPPING.put(SHELLYDT_EM, THING_TYPE_SHELLYEM_STR);
40 THING_TYPE_MAPPING.put(SHELLYDT_SHPLG_S, THING_TYPE_SHELLYPLUGS_STR);
41 THING_TYPE_MAPPING.put(SHELLYDT_SHPLG_U1, THING_TYPE_SHELLYPLUGU1_STR);
42 THING_TYPE_MAPPING.put(SHELLYDT_GAS, THING_TYPE_SHELLYGAS_STR);
43 THING_TYPE_MAPPING.put(SHELLYDT_DW, THING_TYPE_SHELLYDOORWIN_STR);
44 THING_TYPE_MAPPING.put(SHELLYDT_DW2, THING_TYPE_SHELLYDOORWIN2_STR);
45 THING_TYPE_MAPPING.put(SHELLYDT_DUO, THING_TYPE_SHELLYDUO_STR);
46 THING_TYPE_MAPPING.put(SHELLYDT_BULB, THING_TYPE_SHELLYBULB_STR);
47 THING_TYPE_MAPPING.put(SHELLYDT_VINTAGE, THING_TYPE_SHELLYVINTAGE_STR);
48 THING_TYPE_MAPPING.put(SHELLYDT_DIMMER, THING_TYPE_SHELLYDIMMER_STR);
49 THING_TYPE_MAPPING.put(SHELLYDT_DIMMER2, THING_TYPE_SHELLYDIMMER2_STR);
50 THING_TYPE_MAPPING.put(SHELLYDT_IX3, THING_TYPE_SHELLYIX3_STR);
51 THING_TYPE_MAPPING.put(SHELLYDT_BUTTON1, THING_TYPE_SHELLYBUTTON1_STR);
53 // mapping by thing type
54 THING_TYPE_MAPPING.put(THING_TYPE_SHELLY1_STR, THING_TYPE_SHELLY1_STR);
55 THING_TYPE_MAPPING.put(THING_TYPE_SHELLY1PM_STR, THING_TYPE_SHELLY1PM_STR);
56 THING_TYPE_MAPPING.put(THING_TYPE_SHELLY4PRO_STR, THING_TYPE_SHELLY4PRO_STR);
57 THING_TYPE_MAPPING.put(THING_TYPE_SHELLYDIMMER2_STR, THING_TYPE_SHELLYDIMMER2_STR);
58 THING_TYPE_MAPPING.put(THING_TYPE_SHELLYDIMMER_STR, THING_TYPE_SHELLYDIMMER_STR);
59 THING_TYPE_MAPPING.put(THING_TYPE_SHELLYIX3_STR, THING_TYPE_SHELLYIX3_STR);
60 THING_TYPE_MAPPING.put(THING_TYPE_SHELLY3EM_STR, THING_TYPE_SHELLY3EM_STR);
61 THING_TYPE_MAPPING.put(THING_TYPE_SHELLYEM_STR, THING_TYPE_SHELLYEM_STR);
62 THING_TYPE_MAPPING.put(THING_TYPE_SHELLYDUO_STR, THING_TYPE_SHELLYDUO_STR);
63 THING_TYPE_MAPPING.put(THING_TYPE_SHELLYVINTAGE_STR, THING_TYPE_SHELLYVINTAGE_STR);
64 THING_TYPE_MAPPING.put(THING_TYPE_SHELLYBULB_STR, THING_TYPE_SHELLYBULB_STR);
65 THING_TYPE_MAPPING.put(THING_TYPE_SHELLYDUO_STR, THING_TYPE_SHELLYDUO_STR);
66 THING_TYPE_MAPPING.put(THING_TYPE_SHELLYHT_STR, THING_TYPE_SHELLYHT_STR);
67 THING_TYPE_MAPPING.put(THING_TYPE_SHELLYSMOKE_STR, THING_TYPE_SHELLYSMOKE_STR);
68 THING_TYPE_MAPPING.put(THING_TYPE_SHELLYGAS_STR, THING_TYPE_SHELLYGAS_STR);
69 THING_TYPE_MAPPING.put(THING_TYPE_SHELLYFLOOD_STR, THING_TYPE_SHELLYFLOOD_STR);
70 THING_TYPE_MAPPING.put(THING_TYPE_SHELLYDOORWIN_STR, THING_TYPE_SHELLYDOORWIN_STR);
71 THING_TYPE_MAPPING.put(THING_TYPE_SHELLYDOORWIN2_STR, THING_TYPE_SHELLYDOORWIN2_STR);
72 THING_TYPE_MAPPING.put(THING_TYPE_SHELLYSENSE_STR, THING_TYPE_SHELLYSENSE_STR);
73 THING_TYPE_MAPPING.put(THING_TYPE_SHELLYEYE_STR, THING_TYPE_SHELLYEYE_STR);
74 THING_TYPE_MAPPING.put(THING_TYPE_SHELLYBUTTON1_STR, THING_TYPE_SHELLYBUTTON1_STR);
76 THING_TYPE_MAPPING.put(THING_TYPE_SHELLYPROTECTED_STR, THING_TYPE_SHELLYPROTECTED_STR);
79 public static ThingUID getThingUID(String serviceName, String deviceType, String mode, boolean unknown) {
80 String devid = substringAfterLast(serviceName, "-");
81 if (devid.isEmpty()) {
82 throw new IllegalArgumentException("serviceName has improper format: " + serviceName);
84 return new ThingUID(!unknown ? getThingTypeUID(serviceName, deviceType, mode)
85 : getThingTypeUID(THING_TYPE_SHELLYPROTECTED_STR + "-" + devid, deviceType, mode), devid);
88 public static ThingTypeUID getThingTypeUID(String serviceName, String deviceType, String mode) {
89 return new ThingTypeUID(BINDING_ID, getThingType(serviceName, deviceType, mode));
92 public static ThingTypeUID getUnknownTTUID() {
93 return new ThingTypeUID(BINDING_ID, THING_TYPE_SHELLYPROTECTED_STR);
96 public static String getThingType(String hostname, String deviceType, String mode) {
97 String name = hostname.toLowerCase();
98 String type = substringBefore(name, "-").toLowerCase();
99 String devid = substringAfterLast(name, "-");
100 if ((devid == null) || (type == null)) {
101 throw new IllegalArgumentException("Invalid device name format: " + hostname);
104 // First check for special handling
105 if (name.startsWith(THING_TYPE_SHELLY25_PREFIX)) { // Shelly v2.5
106 return mode.equals(SHELLY_MODE_RELAY) ? THING_TYPE_SHELLY25_RELAY_STR : THING_TYPE_SHELLY25_ROLLER_STR;
108 if (name.startsWith(THING_TYPE_SHELLY2_PREFIX)) { // Shelly v2
109 return mode.equals(SHELLY_MODE_RELAY) ? THING_TYPE_SHELLY2_RELAY_STR : THING_TYPE_SHELLY2_ROLLER_STR;
111 if (name.startsWith(THING_TYPE_SHELLYPLUG_STR)) {
112 // shellyplug-s needs to be mapped to shellyplugs to follow the schema
113 // for the thing types: <thing type>-<mode>
114 if (name.startsWith(THING_TYPE_SHELLYPLUGS_STR) || name.contains("-s")) {
115 return THING_TYPE_SHELLYPLUGS_STR;
117 if (name.startsWith(THING_TYPE_SHELLYPLUGU1_STR)) {
118 return THING_TYPE_SHELLYPLUGU1_STR;
120 return THING_TYPE_SHELLYPLUG_STR;
122 if (name.startsWith(THING_TYPE_SHELLYRGBW2_PREFIX)) {
123 return mode.equals(SHELLY_MODE_COLOR) ? THING_TYPE_SHELLYRGBW2_COLOR_STR : THING_TYPE_SHELLYRGBW2_WHITE_STR;
126 // Check general mapping
127 if (!deviceType.isEmpty()) {
128 String str = THING_TYPE_MAPPING.get(deviceType);
134 return THING_TYPE_MAPPING.getOrDefault(type, THING_TYPE_SHELLYUNKNOWN_STR);