]> git.basschouten.com Git - openhab-addons.git/blob
6d4942e8229089621db8ac9e791d3a52752a87fc
[openhab-addons.git] /
1 /**
2  * Copyright (c) 2010-2020 Contributors to the openHAB project
3  *
4  * See the NOTICE file(s) distributed with this work for additional
5  * information.
6  *
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
10  *
11  * SPDX-License-Identifier: EPL-2.0
12  */
13 package org.openhab.binding.hue.internal.action;
14
15 import java.lang.reflect.Method;
16 import java.lang.reflect.Proxy;
17
18 import org.eclipse.jdt.annotation.NonNullByDefault;
19 import org.eclipse.jdt.annotation.Nullable;
20 import org.openhab.binding.hue.internal.handler.HueLightHandler;
21 import org.openhab.core.automation.annotation.ActionInput;
22 import org.openhab.core.automation.annotation.RuleAction;
23 import org.openhab.core.library.types.DecimalType;
24 import org.openhab.core.thing.binding.ThingActions;
25 import org.openhab.core.thing.binding.ThingActionsScope;
26 import org.openhab.core.thing.binding.ThingHandler;
27 import org.openhab.core.types.Command;
28 import org.slf4j.Logger;
29 import org.slf4j.LoggerFactory;
30
31 /**
32  * The {@link LightActions} defines the thing actions for the hue binding.
33  * <p>
34  * <b>Note:</b>The static method <b>invokeMethodOf</b> handles the case where
35  * the test <i>actions instanceof LightActions</i> fails. This test can fail
36  * due to an issue in openHAB core v2.5.0 where the {@link LightActions} class
37  * can be loaded by a different classloader than the <i>actions</i> instance.
38  *
39  * @author Jochen Leopold - Initial contribution
40  * @author Laurent Garnier - new method invokeMethodOf + interface ILightActions
41  */
42 @ThingActionsScope(name = "hue")
43 @NonNullByDefault
44 public class LightActions implements ThingActions, ILightActions {
45     private final Logger logger = LoggerFactory.getLogger(LightActions.class);
46     private @Nullable HueLightHandler handler;
47
48     @Override
49     public void setThingHandler(@Nullable ThingHandler handler) {
50         this.handler = (HueLightHandler) handler;
51     }
52
53     @Override
54     public @Nullable ThingHandler getThingHandler() {
55         return this.handler;
56     }
57
58     @Override
59     @RuleAction(label = "@text/actionLabel", description = "@text/actionDesc")
60     public void fadingLightCommand(
61             @ActionInput(name = "channel", label = "@text/actionInputChannelLabel", description = "@text/actionInputChannelDesc") @Nullable String channel,
62             @ActionInput(name = "command", label = "@text/actionInputCommandLabel", description = "@text/actionInputCommandDesc") @Nullable Command command,
63             @ActionInput(name = "fadeTime", label = "@text/actionInputFadeTimeLabel", description = "@text/actionInputFadeTimeDesc") @Nullable DecimalType fadeTime) {
64         HueLightHandler lightHandler = handler;
65         if (lightHandler == null) {
66             logger.warn("Hue Action service ThingHandler is null!");
67             return;
68         }
69
70         if (channel == null) {
71             logger.debug("skipping Hue fadingLightCommand to channel '{}' due to null value.", channel);
72             return;
73         }
74
75         if (command == null) {
76             logger.debug("skipping Hue fadingLightCommand to command '{}' due to null value.", command);
77             return;
78         }
79         if (fadeTime == null) {
80             logger.debug("skipping Hue fadingLightCommand to fadeTime '{}' due to null value.", fadeTime);
81             return;
82         }
83
84         lightHandler.handleCommand(channel, command, fadeTime.longValue());
85         logger.debug("send LightAction to {} with {}ms of fadeTime", channel, fadeTime);
86     }
87
88     private static ILightActions invokeMethodOf(@Nullable ThingActions actions) {
89         if (actions == null) {
90             throw new IllegalArgumentException("actions cannot be null");
91         }
92         if (actions.getClass().getName().equals(LightActions.class.getName())) {
93             if (actions instanceof ILightActions) {
94                 return (ILightActions) actions;
95             } else {
96                 return (ILightActions) Proxy.newProxyInstance(ILightActions.class.getClassLoader(),
97                         new Class[] { ILightActions.class }, (Object proxy, Method method, Object[] args) -> {
98                             Method m = actions.getClass().getDeclaredMethod(method.getName(),
99                                     method.getParameterTypes());
100                             return m.invoke(actions, args);
101                         });
102             }
103         }
104         throw new IllegalArgumentException("Actions is not an instance of LightActions");
105     }
106
107     public static void fadingLightCommand(@Nullable ThingActions actions, @Nullable String channel,
108             @Nullable Command command, @Nullable DecimalType fadeTime) {
109         invokeMethodOf(actions).fadingLightCommand(channel, command, fadeTime);
110     }
111 }