Skip to content
This repository has been archived by the owner on May 7, 2020. It is now read-only.

[Tradfri] Added support for remote controller and motion sensor devices #4373

Merged
merged 5 commits into from Nov 3, 2017
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
Expand Up @@ -142,8 +142,8 @@ public void handleConfigurationUpdate(Map<String, Object> configurationParameter

// can be overridden by subclasses
Configuration configuration = editConfiguration();
for (Entry<String, Object> configurationParmeter : configurationParameters.entrySet()) {
configuration.put(configurationParmeter.getKey(), configurationParmeter.getValue());
for (Entry<String, Object> configurationParameter : configurationParameters.entrySet()) {
configuration.put(configurationParameter.getKey(), configurationParameter.getValue());
}

if (isInitialized()) {
Expand Down
@@ -1,6 +1,6 @@
Manifest-Version: 1.0
Bundle-ManifestVersion: 2
Bundle-Name: Tradfri Binding Tests
Bundle-Name: TRÅDFRI Binding Tests
Bundle-RequiredExecutionEnvironment: JavaSE-1.8
Bundle-SymbolicName: org.eclipse.smarthome.binding.tradfri.test;singleto
n:=true
Expand Down
Expand Up @@ -14,7 +14,7 @@
<version>0.9.0-SNAPSHOT</version>
<packaging>eclipse-test-plugin</packaging>

<name>Tradfri Binding Tests</name>
<name>TRÅDFRI Binding Tests</name>

<properties>
<bundle.symbolicName>org.eclipse.smarthome.binding.tradfri.test</bundle.symbolicName>
Expand Down
Expand Up @@ -7,6 +7,9 @@
*/
package org.eclipse.smarthome.binding.tradfri;

import static org.eclipse.smarthome.binding.tradfri.TradfriBindingConstants.*;
import static org.eclipse.smarthome.binding.tradfri.internal.config.TradfriDeviceConfig.*;
import static org.eclipse.smarthome.binding.tradfri.internal.config.TradfriGatewayConfig.*;
import static org.hamcrest.CoreMatchers.*;
import static org.hamcrest.core.Is.is;
import static org.junit.Assert.assertThat;
Expand Down Expand Up @@ -46,14 +49,15 @@ public void setUp() {
managedThingProvider = getService(ThingProvider.class, ManagedThingProvider.class);

Map<String, Object> properties = new HashMap<>();
properties.put(GatewayConfig.HOST, "1.2.3.4");
properties.put(GatewayConfig.CODE, "abc");
bridge = BridgeBuilder.create(TradfriBindingConstants.GATEWAY_TYPE_UID, "1").withLabel("My Gateway")
properties.put(CONFIG_HOST, "1.2.3.4");
properties.put(CONFIG_CODE, "abc");
bridge = BridgeBuilder.create(GATEWAY_TYPE_UID, "1").withLabel("My Gateway")
.withConfiguration(new Configuration(properties)).build();

properties = new HashMap<>();
properties.put(DeviceConfig.ID, "65537");
thing = ThingBuilder.create(TradfriBindingConstants.THING_TYPE_DIMMABLE_LIGHT, "1").withLabel("My Bulb")
.withBridge(bridge.getUID()).withConfiguration(new Configuration(properties)).build();
properties.put(CONFIG_ID, "65537");
thing = ThingBuilder.create(THING_TYPE_DIMMABLE_LIGHT, "1").withLabel("My Bulb").withBridge(bridge.getUID())
.withConfiguration(new Configuration(properties)).build();
}

@After
Expand All @@ -68,6 +72,16 @@ public void creationOfTradfriGatewayHandler() {
assertThat(bridge.getHandler(), is(nullValue()));
managedThingProvider.add(bridge);
waitForAssert(() -> assertThat(bridge.getHandler(), notNullValue()));

configurationOfTradfriGatewayHandler();
}

private void configurationOfTradfriGatewayHandler() {
Configuration configuration = bridge.getConfiguration();
assertThat(configuration, is(notNullValue()));

assertThat(configuration.get(CONFIG_HOST), is("1.2.3.4"));
assertThat(configuration.get(CONFIG_CODE), is("abc"));
}

@Test
Expand All @@ -76,5 +90,14 @@ public void creationOfTradfriLightHandler() {
managedThingProvider.add(bridge);
managedThingProvider.add(thing);
waitForAssert(() -> assertThat(thing.getHandler(), notNullValue()));

configurationOfTradfriLightHandler();
}

private void configurationOfTradfriLightHandler() {
Configuration configuration = thing.getConfiguration();
assertThat(configuration, is(notNullValue()));

assertThat(configuration.get(CONFIG_ID), is("65537"));
}
}
Expand Up @@ -7,15 +7,15 @@
*/
package org.eclipse.smarthome.binding.tradfri.discovery;

import static org.eclipse.smarthome.binding.tradfri.TradfriBindingConstants.*;
import static org.eclipse.smarthome.binding.tradfri.internal.config.TradfriGatewayConfig.*;
import static org.hamcrest.CoreMatchers.*;
import static org.junit.Assert.*;
import static org.mockito.Mockito.when;
import static org.mockito.MockitoAnnotations.initMocks;

import javax.jmdns.ServiceInfo;

import org.eclipse.smarthome.binding.tradfri.GatewayConfig;
import org.eclipse.smarthome.binding.tradfri.TradfriBindingConstants;
import org.eclipse.smarthome.binding.tradfri.internal.discovery.TradfriDiscoveryParticipant;
import org.eclipse.smarthome.config.discovery.DiscoveryResult;
import org.eclipse.smarthome.config.discovery.DiscoveryResultFlag;
Expand Down Expand Up @@ -63,8 +63,7 @@ public void setUp() {
@Test
public void correctSupportedTypes() {
assertThat(discoveryParticipant.getSupportedThingTypeUIDs().size(), is(1));
assertThat(discoveryParticipant.getSupportedThingTypeUIDs().iterator().next(),
is(TradfriBindingConstants.GATEWAY_TYPE_UID));
assertThat(discoveryParticipant.getSupportedThingTypeUIDs().iterator().next(), is(GATEWAY_TYPE_UID));
}

@Test
Expand All @@ -81,12 +80,12 @@ public void validDiscoveryResult() {
assertThat(result.getProperties().get(Thing.PROPERTY_FIRMWARE_VERSION), is("1.1"));
assertThat(result.getFlag(), is(DiscoveryResultFlag.NEW));
assertThat(result.getThingUID(), is(new ThingUID("tradfri:gateway:gw1234567890ab")));
assertThat(result.getThingTypeUID(), is(TradfriBindingConstants.GATEWAY_TYPE_UID));
assertThat(result.getThingTypeUID(), is(GATEWAY_TYPE_UID));
assertThat(result.getBridgeUID(), is(nullValue()));
assertThat(result.getProperties().get(Thing.PROPERTY_VENDOR), is("IKEA of Sweden"));
assertThat(result.getProperties().get(GatewayConfig.HOST), is("192.168.0.5"));
assertThat(result.getProperties().get(GatewayConfig.PORT), is(1234));
assertThat(result.getRepresentationProperty(), is(GatewayConfig.HOST));
assertThat(result.getProperties().get(CONFIG_HOST), is("192.168.0.5"));
assertThat(result.getProperties().get(CONFIG_PORT), is(1234));
assertThat(result.getRepresentationProperty(), is(CONFIG_HOST));
}

@Test
Expand Down
Expand Up @@ -7,15 +7,15 @@
*/
package org.eclipse.smarthome.binding.tradfri.discovery;

import static org.eclipse.smarthome.binding.tradfri.TradfriBindingConstants.*;
import static org.eclipse.smarthome.binding.tradfri.internal.config.TradfriDeviceConfig.*;
import static org.hamcrest.CoreMatchers.is;
import static org.junit.Assert.*;
import static org.mockito.Mockito.when;
import static org.mockito.MockitoAnnotations.initMocks;

import java.util.Collection;

import org.eclipse.smarthome.binding.tradfri.DeviceConfig;
import org.eclipse.smarthome.binding.tradfri.TradfriBindingConstants;
import org.eclipse.smarthome.binding.tradfri.handler.TradfriGatewayHandler;
import org.eclipse.smarthome.binding.tradfri.internal.discovery.TradfriDiscoveryService;
import org.eclipse.smarthome.config.discovery.DiscoveryListener;
Expand All @@ -37,9 +37,12 @@
* Tests for {@link TradfriDiscoveryService}.
*
* @author Kai Kreuzer - Initial contribution
* @author Christoph Weitkamp - Added support for remote controller and motion sensor devices (read-only battery level)
*/
public class TradfriDiscoveryServiceTest {

private static final ThingUID GATEWAY_THING_UID = new ThingUID("tradfri:gateway:1");

@Mock
private TradfriGatewayHandler handler;

Expand All @@ -51,8 +54,7 @@ public class TradfriDiscoveryServiceTest {
@Before
public void setUp() {
initMocks(this);
when(handler.getThing())
.thenReturn(BridgeBuilder.create(TradfriBindingConstants.GATEWAY_TYPE_UID, "1").build());
when(handler.getThing()).thenReturn(BridgeBuilder.create(GATEWAY_TYPE_UID, "1").build());
discovery = new TradfriDiscoveryService(handler);

listener = new DiscoveryListener() {
Expand Down Expand Up @@ -81,26 +83,63 @@ public void cleanUp() {

@Test
public void correctSupportedTypes() {
assertThat(discovery.getSupportedThingTypes().size(), is(3));
assertTrue(discovery.getSupportedThingTypes().contains(TradfriBindingConstants.THING_TYPE_DIMMABLE_LIGHT));
assertTrue(discovery.getSupportedThingTypes().contains(TradfriBindingConstants.THING_TYPE_COLOR_TEMP_LIGHT));
assertTrue(discovery.getSupportedThingTypes().contains(TradfriBindingConstants.THING_TYPE_COLOR_LIGHT));
assertThat(discovery.getSupportedThingTypes().size(), is(6));
assertTrue(discovery.getSupportedThingTypes().contains(THING_TYPE_DIMMABLE_LIGHT));
assertTrue(discovery.getSupportedThingTypes().contains(THING_TYPE_COLOR_TEMP_LIGHT));
assertTrue(discovery.getSupportedThingTypes().contains(THING_TYPE_COLOR_LIGHT));
assertTrue(discovery.getSupportedThingTypes().contains(THING_TYPE_DIMMER));
assertTrue(discovery.getSupportedThingTypes().contains(THING_TYPE_MOTION_SENSOR));
assertTrue(discovery.getSupportedThingTypes().contains(THING_TYPE_REMOTE_CONTROL));
}

@Test
public void validDiscoveryResultWhiteLightW() {
String json = "{\"9001\":\"TRADFRI bulb E27 W opal 1000lm\",\"9002\":1492856270,\"9020\":1507194357,\"9003\":65537,\"3311\":[{\"5850\":1,\"5851\":254,\"9003\":0}],\"9054\":0,\"5750\":2,\"9019\":1,\"3\":{\"0\":\"IKEA of Sweden\",\"1\":\"TRADFRI bulb E27 W opal 1000lm\",\"2\":\"\",\"3\":\"1.2.214\",\"6\":1}}";
JsonObject data = new JsonParser().parse(json).getAsJsonObject();

discovery.onUpdate("65537", data);

assertNotNull(discoveryResult);
assertThat(discoveryResult.getFlag(), is(DiscoveryResultFlag.NEW));
assertThat(discoveryResult.getThingUID(), is(new ThingUID("tradfri:0100:1:65537")));
assertThat(discoveryResult.getThingTypeUID(), is(THING_TYPE_DIMMABLE_LIGHT));
assertThat(discoveryResult.getBridgeUID(), is(GATEWAY_THING_UID));
assertThat(discoveryResult.getProperties().get(CONFIG_ID), is(65537));
assertThat(discoveryResult.getRepresentationProperty(), is(CONFIG_ID));
}

@Test
public void validDiscoveryResultWhiteLightWS() {
String json = "{\"9001\":\"TRADFRI bulb E27 WS opal 980lm\",\"9002\":1492955148,\"9020\":1507200447,\"9003\":65537,\"3311\":[{\"5710\":26909,\"5850\":1,\"5851\":203,\"5707\":0,\"5708\":0,\"5709\":30140,\"5711\":370,\"5706\":\"f1e0b5\",\"9003\":0}],\"9054\":0,\"5750\":2,\"9019\":1,\"3\":{\"0\":\"IKEA of Sweden\",\"1\":\"TRADFRI bulb E27 WS opal 980lm\",\"2\":\"\",\"3\":\"1.2.217\",\"6\":1}}";
JsonObject data = new JsonParser().parse(json).getAsJsonObject();

discovery.onUpdate("65537", data);

assertNotNull(discoveryResult);
assertThat(discoveryResult.getFlag(), is(DiscoveryResultFlag.NEW));
assertThat(discoveryResult.getThingUID(), is(new ThingUID("tradfri:0220:1:65537")));
assertThat(discoveryResult.getThingTypeUID(), is(THING_TYPE_COLOR_TEMP_LIGHT));
assertThat(discoveryResult.getBridgeUID(), is(GATEWAY_THING_UID));
assertThat(discoveryResult.getProperties().get(CONFIG_ID), is(65537));
assertThat(discoveryResult.getRepresentationProperty(), is(CONFIG_ID));
}

@Test
public void validDiscoveryResult() {
String json = "{\"9054\":0,\"9001\":\"LR\",\"5750\":2,\"9002\":1490983446,\"9020\":1491055861,\"9003\":65537,\"9019\":1,\"3\":{\"1\":\"TRADFRI bulb E27 WS opal 980lm\",\"0\":\"IKEA of Sweden\",\"2\":\"\",\"3\":\"1.1.1.1-5.7.2.0\",\"6\":1},\"3311\":[{\"5850\":1,\"5851\":254,\"5707\":0,\"5708\":0,\"5709\":33135,\"5710\":27211,\"9003\":0,\"5711\":0,\"5706\":\"efd275\"}]}";
public void validDiscoveryResultWhiteLightWSWithIncompleteJson() {
// We do not always receive a COLOR = "5706" attribute, even the light supports it - but the gateway does not
// seem to have this information, if the bulb is unreachable.
String json = "{\"9001\":\"TRADFRI bulb E27 WS opal 980lm\",\"9002\":1492955148,\"9020\":1506968670,\"9003\":65537,\"3311\":[{\"9003\":0}],\"9054\":0,\"5750\":2,\"9019\":0,\"3\":{\"0\":\"IKEA of Sweden\",\"1\":\"TRADFRI bulb E27 WS opal 980lm\",\"2\":\"\",\"3\":\"1.2.217\",\"6\":1}}";
JsonObject data = new JsonParser().parse(json).getAsJsonObject();

discovery.onUpdate("65537", data);

assertNotNull(discoveryResult);
assertThat(discoveryResult.getFlag(), is(DiscoveryResultFlag.NEW));
assertThat(discoveryResult.getThingUID(), is(new ThingUID("tradfri:0220:1:65537")));
assertThat(discoveryResult.getThingTypeUID(), is(TradfriBindingConstants.THING_TYPE_COLOR_TEMP_LIGHT));
assertThat(discoveryResult.getBridgeUID(), is(new ThingUID("tradfri:gateway:1")));
assertThat(discoveryResult.getProperties().get(DeviceConfig.ID), is(65537));
assertThat(discoveryResult.getRepresentationProperty(), is(DeviceConfig.ID));
assertThat(discoveryResult.getThingTypeUID(), is(THING_TYPE_COLOR_TEMP_LIGHT));
assertThat(discoveryResult.getBridgeUID(), is(GATEWAY_THING_UID));
assertThat(discoveryResult.getProperties().get(CONFIG_ID), is(65537));
assertThat(discoveryResult.getRepresentationProperty(), is(CONFIG_ID));
}

@Test
Expand All @@ -113,10 +152,57 @@ public void validDiscoveryResultColorLightCWS() {
assertNotNull(discoveryResult);
assertThat(discoveryResult.getFlag(), is(DiscoveryResultFlag.NEW));
assertThat(discoveryResult.getThingUID(), is(new ThingUID("tradfri:0210:1:65550")));
assertThat(discoveryResult.getThingTypeUID(), is(TradfriBindingConstants.THING_TYPE_COLOR_LIGHT));
assertThat(discoveryResult.getBridgeUID(), is(new ThingUID("tradfri:gateway:1")));
assertThat(discoveryResult.getProperties().get(DeviceConfig.ID), is(65550));
assertThat(discoveryResult.getRepresentationProperty(), is(DeviceConfig.ID));
assertThat(discoveryResult.getThingTypeUID(), is(THING_TYPE_COLOR_LIGHT));
assertThat(discoveryResult.getBridgeUID(), is(GATEWAY_THING_UID));
assertThat(discoveryResult.getProperties().get(CONFIG_ID), is(65550));
assertThat(discoveryResult.getRepresentationProperty(), is(CONFIG_ID));
}

@Test
public void validDiscoveryResultRemoteControl() {
String json = "{\"9001\":\"TRADFRI remote control\",\"9002\":1492843083,\"9020\":1506977986,\"9003\":65536,\"9054\":0,\"5750\":0,\"9019\":1,\"3\":{\"0\":\"IKEA of Sweden\",\"1\":\"TRADFRI remote control\",\"2\":\"\",\"3\":\"1.2.214\",\"6\":3,\"9\":47},\"15009\":[{\"9003\":0}]}";
JsonObject data = new JsonParser().parse(json).getAsJsonObject();

discovery.onUpdate("65536", data);

assertNotNull(discoveryResult);
assertThat(discoveryResult.getFlag(), is(DiscoveryResultFlag.NEW));
assertThat(discoveryResult.getThingUID(), is(new ThingUID("tradfri:0830:1:65536")));
assertThat(discoveryResult.getThingTypeUID(), is(THING_TYPE_REMOTE_CONTROL));
assertThat(discoveryResult.getBridgeUID(), is(GATEWAY_THING_UID));
assertThat(discoveryResult.getProperties().get(CONFIG_ID), is(65536));
assertThat(discoveryResult.getRepresentationProperty(), is(CONFIG_ID));
}

@Test
public void validDiscoveryResultWirelessDimmer() {
String json = "{\"9001\":\"TRADFRI wireless dimmer\",\"9002\":1492843083,\"9020\":1506977986,\"9003\":65536,\"9054\":0,\"5750\":0,\"9019\":1,\"3\":{\"0\":\"IKEA of Sweden\",\"1\":\"TRADFRI wireless dimmer\",\"2\":\"\",\"3\":\"1.2.214\",\"6\":3,\"9\":47},\"15009\":[{\"9003\":0}]}";
JsonObject data = new JsonParser().parse(json).getAsJsonObject();

discovery.onUpdate("65536", data);

assertNotNull(discoveryResult);
assertThat(discoveryResult.getFlag(), is(DiscoveryResultFlag.NEW));
assertThat(discoveryResult.getThingUID(), is(new ThingUID("tradfri:0820:1:65536")));
assertThat(discoveryResult.getThingTypeUID(), is(THING_TYPE_DIMMER));
assertThat(discoveryResult.getBridgeUID(), is(GATEWAY_THING_UID));
assertThat(discoveryResult.getProperties().get(CONFIG_ID), is(65536));
assertThat(discoveryResult.getRepresentationProperty(), is(CONFIG_ID));
}

@Test
public void validDiscoveryResultMotionSensor() {
String json = "{\"9001\":\"TRADFRI motion sensor\",\"9002\":1492955083,\"9020\":1507120083,\"9003\":65538,\"9054\":0,\"5750\":4,\"9019\":1,\"3\":{\"0\":\"IKEA of Sweden\",\"1\":\"TRADFRI motion sensor\",\"2\":\"\",\"3\":\"1.2.214\",\"6\":3,\"9\":60},\"3300\":[{\"9003\":0}]}";
JsonObject data = new JsonParser().parse(json).getAsJsonObject();

discovery.onUpdate("65538", data);

assertNotNull(discoveryResult);
assertThat(discoveryResult.getFlag(), is(DiscoveryResultFlag.NEW));
assertThat(discoveryResult.getThingUID(), is(new ThingUID("tradfri:0107:1:65538")));
assertThat(discoveryResult.getThingTypeUID(), is(THING_TYPE_MOTION_SENSOR));
assertThat(discoveryResult.getBridgeUID(), is(GATEWAY_THING_UID));
assertThat(discoveryResult.getProperties().get(CONFIG_ID), is(65538));
assertThat(discoveryResult.getRepresentationProperty(), is(CONFIG_ID));
}
}
@@ -1,8 +1,27 @@
<?xml version="1.0" encoding="UTF-8"?>
<config-description:config-descriptions
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:config-description="http://eclipse.org/smarthome/schemas/config-description/v1.0.0"
<config-description:config-descriptions xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:config-description="http://eclipse.org/smarthome/schemas/config-description/v1.0.0"
xsi:schemaLocation="http://eclipse.org/smarthome/schemas/config-description/v1.0.0 http://eclipse.org/smarthome/schemas/config-description-1.0.0.xsd">

<config-description uri="bridge-type:tradfri:gateway">
<parameter name="host" type="text" required="true">
<context>network-address</context>
<label>Host</label>
<description>Hostname or IP address of the IKEA TRÅDFRI gateway</description>
</parameter>
<parameter name="port" type="integer" required="false">
<label>Port</label>
<description>Port for accessing the gateway</description>
<advanced>true</advanced>
<default>5684</default>
</parameter>
<parameter name="code" type="text" required="true">
<context>password</context>
<label>Security Code</label>
<description>Security code printed on the label underneath the gateway.</description>
</parameter>
</config-description>

<config-description uri="thing-type:tradfri:device">
<parameter name="id" type="integer" required="true">
<label>ID</label>
Expand Down