mirror of
https://github.com/bwssytems/ha-bridge.git
synced 2025-12-19 16:41:53 +00:00
Compare commits
6 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
fcb31b8f76 | ||
|
|
0205633684 | ||
|
|
7b48590807 | ||
|
|
5f7cd70710 | ||
|
|
46ad4489ad | ||
|
|
bfd1b94473 |
2
pom.xml
2
pom.xml
@@ -5,7 +5,7 @@
|
|||||||
|
|
||||||
<groupId>com.bwssystems.HABridge</groupId>
|
<groupId>com.bwssystems.HABridge</groupId>
|
||||||
<artifactId>ha-bridge</artifactId>
|
<artifactId>ha-bridge</artifactId>
|
||||||
<version>5.3.0RC2</version>
|
<version>5.3.0RC6</version>
|
||||||
<packaging>jar</packaging>
|
<packaging>jar</packaging>
|
||||||
|
|
||||||
<name>HA Bridge</name>
|
<name>HA Bridge</name>
|
||||||
|
|||||||
@@ -0,0 +1,13 @@
|
|||||||
|
package com.bwssystems.HABridge.plugins.hass;
|
||||||
|
|
||||||
|
public class HassAuth {
|
||||||
|
boolean legacyauth;
|
||||||
|
|
||||||
|
public boolean isLegacyauth() {
|
||||||
|
return legacyauth;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setLegacyauth(boolean legacyauth) {
|
||||||
|
this.legacyauth = legacyauth;
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -16,14 +16,19 @@ import com.bwssystems.HABridge.plugins.http.HTTPHome;
|
|||||||
import com.google.gson.Gson;
|
import com.google.gson.Gson;
|
||||||
|
|
||||||
public class HomeAssistant {
|
public class HomeAssistant {
|
||||||
private static final Logger log = LoggerFactory.getLogger(HomeAssistant.class);
|
private static final Logger log = LoggerFactory.getLogger(HomeAssistant.class);
|
||||||
private NamedIP hassAddress;
|
private NamedIP hassAddress;
|
||||||
private HTTPHandler anHttpHandler;
|
private HTTPHandler anHttpHandler;
|
||||||
|
private HassAuth theAuthType;
|
||||||
|
private NameValue[] headers;
|
||||||
|
|
||||||
public HomeAssistant(NamedIP addressName) {
|
public HomeAssistant(NamedIP addressName) {
|
||||||
super();
|
super();
|
||||||
anHttpHandler = HTTPHome.getHandler();
|
anHttpHandler = HTTPHome.getHandler();
|
||||||
hassAddress = addressName;
|
hassAddress = addressName;
|
||||||
|
theAuthType = null;
|
||||||
|
headers = null;
|
||||||
|
isLegacyAuth();
|
||||||
}
|
}
|
||||||
|
|
||||||
public NamedIP getHassAddress() {
|
public NamedIP getHassAddress() {
|
||||||
@@ -35,38 +40,30 @@ public class HomeAssistant {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public Boolean callCommand(HassCommand aCommand) {
|
public Boolean callCommand(HassCommand aCommand) {
|
||||||
log.debug("calling HomeAssistant: " + aCommand.getHassName() + " - "
|
log.debug("calling HomeAssistant: " + aCommand.getHassName() + " - " + aCommand.getEntityId() + " - "
|
||||||
+ aCommand.getEntityId() + " - " + aCommand.getState() + " - " + aCommand.getBri());
|
+ aCommand.getState() + " - " + aCommand.getBri());
|
||||||
String aUrl = null;
|
String aUrl = null;
|
||||||
String domain = aCommand.getEntityId().substring(0, aCommand.getEntityId().indexOf("."));
|
String domain = aCommand.getEntityId().substring(0, aCommand.getEntityId().indexOf("."));
|
||||||
aUrl = hassAddress.getHttpPreamble() + "/api/services/";
|
aUrl = hassAddress.getHttpPreamble() + "/api/services/";
|
||||||
if(domain.equals("group"))
|
if (domain.equals("group"))
|
||||||
aUrl = aUrl + "homeassistant";
|
aUrl = aUrl + "homeassistant";
|
||||||
else
|
else
|
||||||
aUrl = aUrl + domain;
|
aUrl = aUrl + domain;
|
||||||
String aBody = "{\"entity_id\":\"" + aCommand.getEntityId() + "\"";
|
String aBody = "{\"entity_id\":\"" + aCommand.getEntityId() + "\"";
|
||||||
NameValue[] headers = null;
|
headers = getAuthHeader();
|
||||||
if(hassAddress.getPassword() != null && !hassAddress.getPassword().isEmpty()) {
|
if (aCommand.getState().equalsIgnoreCase("on")) {
|
||||||
NameValue password = new NameValue();
|
|
||||||
password.setName("x-ha-access");
|
|
||||||
password.setValue(hassAddress.getPassword());
|
|
||||||
headers = new NameValue[1];
|
|
||||||
headers[0] = password;
|
|
||||||
}
|
|
||||||
if(aCommand.getState().equalsIgnoreCase("on")) {
|
|
||||||
aUrl = aUrl + "/turn_on";
|
aUrl = aUrl + "/turn_on";
|
||||||
if(aCommand.getBri() != null)
|
if (aCommand.getBri() != null)
|
||||||
aBody = aBody + ",\"brightness\":" + aCommand.getBri() + "}";
|
aBody = aBody + ",\"brightness\":" + aCommand.getBri() + "}";
|
||||||
else
|
else
|
||||||
aBody = aBody + "}";
|
aBody = aBody + "}";
|
||||||
}
|
} else {
|
||||||
else {
|
|
||||||
aUrl = aUrl + "/turn_off";
|
aUrl = aUrl + "/turn_off";
|
||||||
aBody = aBody + "}";
|
aBody = aBody + "}";
|
||||||
}
|
}
|
||||||
log.debug("Calling HomeAssistant with url: " + aUrl);
|
log.debug("Calling HomeAssistant with url: " + aUrl);
|
||||||
String theData = anHttpHandler.doHttpRequest(aUrl, HttpPost.METHOD_NAME, "application/json", aBody, headers);
|
String theData = anHttpHandler.doHttpRequest(aUrl, HttpPost.METHOD_NAME, "application/json", aBody, headers);
|
||||||
log.debug("call Command return is: <" + theData + ">");
|
log.debug("call Command return is: <" + theData + ">");
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -74,39 +71,62 @@ public class HomeAssistant {
|
|||||||
List<State> theDeviceStates = null;
|
List<State> theDeviceStates = null;
|
||||||
State[] theHassStates;
|
State[] theHassStates;
|
||||||
String theUrl = null;
|
String theUrl = null;
|
||||||
String theData;
|
String theData;
|
||||||
NameValue[] headers = null;
|
headers = getAuthHeader();
|
||||||
if(hassAddress.getPassword() != null && !hassAddress.getPassword().isEmpty()) {
|
if (hassAddress.getSecure() != null && hassAddress.getSecure())
|
||||||
NameValue password = new NameValue();
|
|
||||||
password.setName("x-ha-access");
|
|
||||||
password.setValue(hassAddress.getPassword());
|
|
||||||
headers = new NameValue[1];
|
|
||||||
headers[0] = password;
|
|
||||||
}
|
|
||||||
if(hassAddress.getSecure() != null && hassAddress.getSecure())
|
|
||||||
theUrl = "https";
|
theUrl = "https";
|
||||||
else
|
else
|
||||||
theUrl = "http";
|
theUrl = "http";
|
||||||
theUrl = theUrl + "://" + hassAddress.getIp() + ":" + hassAddress.getPort() + "/api/states";
|
theUrl = theUrl + "://" + hassAddress.getIp() + ":" + hassAddress.getPort() + "/api/states";
|
||||||
theData = anHttpHandler.doHttpRequest(theUrl, HttpGet.METHOD_NAME, "application/json", null, headers);
|
theData = anHttpHandler.doHttpRequest(theUrl, HttpGet.METHOD_NAME, "application/json", null, headers);
|
||||||
if(theData != null) {
|
if (theData != null) {
|
||||||
log.debug("GET Hass States - data: " + theData);
|
log.debug("GET Hass States - data: " + theData);
|
||||||
theHassStates = new Gson().fromJson(theData, State[].class);
|
theHassStates = new Gson().fromJson(theData, State[].class);
|
||||||
if(theHassStates == null) {
|
if (theHassStates == null) {
|
||||||
log.warn("Cannot get an devices for HomeAssistant " + hassAddress.getName() + " as response is not parsable.");
|
log.warn("Cannot get an devices for HomeAssistant " + hassAddress.getName()
|
||||||
}
|
+ " as response is not parsable.");
|
||||||
else {
|
} else {
|
||||||
theDeviceStates = new ArrayList<State>(Arrays.asList(theHassStates));
|
theDeviceStates = new ArrayList<State>(Arrays.asList(theHassStates));
|
||||||
}
|
}
|
||||||
}
|
} else
|
||||||
else
|
log.warn("Cannot get an devices for HomeAssistant " + hassAddress.getName() + " http call failed.");
|
||||||
log.warn("Cannot get an devices for HomeAssistant " + hassAddress.getName() + " http call failed.");
|
|
||||||
return theDeviceStates;
|
return theDeviceStates;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
protected void closeClient() {
|
protected void closeClient() {
|
||||||
anHttpHandler.closeHandler();
|
anHttpHandler.closeHandler();
|
||||||
anHttpHandler = null;
|
anHttpHandler = null;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private boolean isLegacyAuth() {
|
||||||
|
if (theAuthType == null) {
|
||||||
|
try {
|
||||||
|
theAuthType = new Gson().fromJson(hassAddress.getExtensions(), HassAuth.class);
|
||||||
|
} catch (Exception e) {
|
||||||
|
log.warn("Could not read hass auth - continuing with defaults.");
|
||||||
|
theAuthType = new HassAuth();
|
||||||
|
theAuthType.setLegacyauth(false);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return theAuthType.isLegacyauth();
|
||||||
|
}
|
||||||
|
|
||||||
|
private NameValue[] getAuthHeader() {
|
||||||
|
if (headers == null) {
|
||||||
|
if (hassAddress.getPassword() != null && !hassAddress.getPassword().isEmpty()) {
|
||||||
|
headers = new NameValue[1];
|
||||||
|
headers[0] = new NameValue();
|
||||||
|
if (isLegacyAuth()) {
|
||||||
|
headers[0].setName("x-ha-access");
|
||||||
|
headers[0].setValue(hassAddress.getPassword());
|
||||||
|
} else {
|
||||||
|
headers[0].setName("Authorization");
|
||||||
|
headers[0].setValue("Bearer " + hassAddress.getPassword());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} else if(hassAddress.getPassword() == null || hassAddress.getPassword().isEmpty()) {
|
||||||
|
headers = null;
|
||||||
|
}
|
||||||
|
return headers;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -61,12 +61,12 @@ public class HomeGenieInstance {
|
|||||||
if (hgModules != null && hgModules.length > 0) {
|
if (hgModules != null && hgModules.length > 0) {
|
||||||
deviceList = new ArrayList<Module>();
|
deviceList = new ArrayList<Module>();
|
||||||
for (int i = 0; i < hgModules.length; i++) {
|
for (int i = 0; i < hgModules.length; i++) {
|
||||||
if (hgModules[i].isSwitch() || hgModules[i].isDimmer())
|
if (hgModules[i].isModuleValid(homegenieIP.getExtensions()))
|
||||||
deviceList.add(hgModules[i]);
|
deviceList.add(hgModules[i]);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
} catch (Exception e) {
|
} catch (Exception e) {
|
||||||
log.warn("Cannot get an devices for Homegenie {} Gson Parse Error.", homegenieIP.getName());
|
log.warn("Cannot get devices for Homegenie {} Gson Parse Error.", homegenieIP.getName(), e);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return deviceList;
|
return deviceList;
|
||||||
|
|||||||
@@ -1,11 +1,20 @@
|
|||||||
|
|
||||||
package com.bwssystems.HABridge.plugins.homegenie;
|
package com.bwssystems.HABridge.plugins.homegenie;
|
||||||
|
|
||||||
|
import java.util.List;
|
||||||
|
|
||||||
// import java.util.List;
|
// import java.util.List;
|
||||||
import com.google.gson.annotations.Expose;
|
import com.google.gson.annotations.Expose;
|
||||||
import com.google.gson.annotations.SerializedName;
|
import com.google.gson.annotations.SerializedName;
|
||||||
|
|
||||||
|
import org.slf4j.Logger;
|
||||||
|
import org.slf4j.LoggerFactory;
|
||||||
|
|
||||||
|
import com.google.gson.Gson;
|
||||||
|
import com.google.gson.JsonObject;
|
||||||
|
|
||||||
public class Module {
|
public class Module {
|
||||||
|
private static final Logger log = LoggerFactory.getLogger(HomeGenieInstance.class);
|
||||||
|
|
||||||
@SerializedName("Name")
|
@SerializedName("Name")
|
||||||
@Expose
|
@Expose
|
||||||
@@ -23,10 +32,10 @@ public class Module {
|
|||||||
@Expose
|
@Expose
|
||||||
private String address;
|
private String address;
|
||||||
/*
|
/*
|
||||||
@SerializedName("Properties")
|
* @SerializedName("Properties")
|
||||||
@Expose
|
*
|
||||||
private List<Property> properties = null;
|
* @Expose private List<Property> properties = null;
|
||||||
*/
|
*/
|
||||||
@SerializedName("RoutingNode")
|
@SerializedName("RoutingNode")
|
||||||
@Expose
|
@Expose
|
||||||
private String routingNode;
|
private String routingNode;
|
||||||
@@ -70,15 +79,13 @@ public class Module {
|
|||||||
public void setAddress(String address) {
|
public void setAddress(String address) {
|
||||||
this.address = address;
|
this.address = address;
|
||||||
}
|
}
|
||||||
/*
|
|
||||||
public List<Property> getProperties() {
|
|
||||||
return properties;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void setProperties(List<Property> properties) {
|
/*
|
||||||
this.properties = properties;
|
* public List<Property> getProperties() { return properties; }
|
||||||
}
|
*
|
||||||
*/
|
* public void setProperties(List<Property> properties) { this.properties =
|
||||||
|
* properties; }
|
||||||
|
*/
|
||||||
public String getRoutingNode() {
|
public String getRoutingNode() {
|
||||||
return routingNode;
|
return routingNode;
|
||||||
}
|
}
|
||||||
@@ -95,10 +102,48 @@ public class Module {
|
|||||||
return isDeviceType("Dimmer");
|
return isDeviceType("Dimmer");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public boolean isLight() {
|
||||||
|
return isDeviceType("Light");
|
||||||
|
}
|
||||||
|
|
||||||
private boolean isDeviceType(String theType) {
|
private boolean isDeviceType(String theType) {
|
||||||
if(deviceType.equals(theType)) {
|
if (deviceType.equals(theType)) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public boolean isModuleValid(JsonObject theExtensions) {
|
||||||
|
ModuleTypes moduleTypes = null;
|
||||||
|
if (this.name == null || this.name.trim().isEmpty())
|
||||||
|
return false;
|
||||||
|
|
||||||
|
if (isSwitch())
|
||||||
|
return true;
|
||||||
|
|
||||||
|
if (isDimmer())
|
||||||
|
return true;
|
||||||
|
|
||||||
|
if (isLight())
|
||||||
|
return true;
|
||||||
|
|
||||||
|
if (theExtensions != null && theExtensions.isJsonObject() && theExtensions.get("moduleTypes").isJsonArray()) {
|
||||||
|
try {
|
||||||
|
moduleTypes = new Gson().fromJson(theExtensions, ModuleTypes.class);
|
||||||
|
} catch (Exception e) {
|
||||||
|
log.warn("Could not parse extensions for {} with {}", this.name, theExtensions);
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (moduleTypes == null)
|
||||||
|
return false;
|
||||||
|
|
||||||
|
for (ModuleType moduleType : moduleTypes.getModuleTypes()) {
|
||||||
|
if (isDeviceType(moduleType.getModuleType()))
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return false;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -0,0 +1,20 @@
|
|||||||
|
package com.bwssystems.HABridge.plugins.homegenie;
|
||||||
|
|
||||||
|
import com.google.gson.annotations.Expose;
|
||||||
|
import com.google.gson.annotations.SerializedName;
|
||||||
|
|
||||||
|
public class ModuleType {
|
||||||
|
|
||||||
|
@SerializedName("moduleType")
|
||||||
|
@Expose
|
||||||
|
private String moduleType;
|
||||||
|
|
||||||
|
public String getModuleType() {
|
||||||
|
return moduleType;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setModuleType(String moduleType) {
|
||||||
|
this.moduleType = moduleType;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
@@ -0,0 +1,21 @@
|
|||||||
|
package com.bwssystems.HABridge.plugins.homegenie;
|
||||||
|
|
||||||
|
import java.util.List;
|
||||||
|
import com.google.gson.annotations.Expose;
|
||||||
|
import com.google.gson.annotations.SerializedName;
|
||||||
|
|
||||||
|
public class ModuleTypes {
|
||||||
|
|
||||||
|
@SerializedName("moduleTypes")
|
||||||
|
@Expose
|
||||||
|
private List<ModuleType> moduleTypes = null;
|
||||||
|
|
||||||
|
public List<ModuleType> getModuleTypes() {
|
||||||
|
return moduleTypes;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setModuleTypes(List<ModuleType> moduleTypes) {
|
||||||
|
this.moduleTypes = moduleTypes;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
@@ -53,6 +53,16 @@ public class UpnpListener {
|
|||||||
+ HueConstants.API_VERSION + "\r\n" + "NTS: ssdp:alive\r\n" + "hue-bridgeid: %s\r\n" + "NT: uuid:"
|
+ HueConstants.API_VERSION + "\r\n" + "NTS: ssdp:alive\r\n" + "hue-bridgeid: %s\r\n" + "NT: uuid:"
|
||||||
+ HueConstants.UUID_PREFIX + "%s\r\n" + "USN: uuid:" + HueConstants.UUID_PREFIX + "%s\r\n\r\n";
|
+ HueConstants.UUID_PREFIX + "%s\r\n" + "USN: uuid:" + HueConstants.UUID_PREFIX + "%s\r\n\r\n";
|
||||||
|
|
||||||
|
private String notifyTemplate2 = "NOTIFY * HTTP/1.1\r\n" + "HOST: %s:%s\r\n" + "CACHE-CONTROL: max-age=100\r\n"
|
||||||
|
+ "LOCATION: http://%s:%s/description.xml\r\n" + "SERVER: Linux/3.14.0 UPnP/1.0 IpBridge/"
|
||||||
|
+ HueConstants.API_VERSION + "\r\n" + "NTS: ssdp:alive\r\n" + "hue-bridgeid: %s\r\n"
|
||||||
|
+ "NT: upnp:rootdevice\r\n" + "USN: uuid:" + HueConstants.UUID_PREFIX + "%s::upnp:rootdevice\r\n\r\n";
|
||||||
|
|
||||||
|
private String notifyTemplate3 = "NOTIFY * HTTP/1.1\r\n" + "HOST: %s:%s\r\n" + "CACHE-CONTROL: max-age=100\r\n"
|
||||||
|
+ "LOCATION: http://%s:%s/description.xml\r\n" + "SERVER: Linux/3.14.0 UPnP/1.0 IpBridge/"
|
||||||
|
+ HueConstants.API_VERSION + "\r\n" + "NTS: ssdp:alive\r\n" + "hue-bridgeid: %s\r\n"
|
||||||
|
+ "NT: urn:schemas-upnp-org:device:basic:1\r\n" + "USN: uuid:" + HueConstants.UUID_PREFIX + "%s\r\n\r\n";
|
||||||
|
|
||||||
public UpnpListener(BridgeSettingsDescriptor theSettings, BridgeControlDescriptor theControl,
|
public UpnpListener(BridgeSettingsDescriptor theSettings, BridgeControlDescriptor theControl,
|
||||||
UDPDatagramSender aUdpDatagramSender) throws IOException {
|
UDPDatagramSender aUdpDatagramSender) throws IOException {
|
||||||
super();
|
super();
|
||||||
@@ -242,21 +252,21 @@ public class UpnpListener {
|
|||||||
discoveryResponse = String.format(responseTemplateOriginal, Configuration.UPNP_MULTICAST_ADDRESS,
|
discoveryResponse = String.format(responseTemplateOriginal, Configuration.UPNP_MULTICAST_ADDRESS,
|
||||||
Configuration.UPNP_DISCOVERY_PORT, httpLocationAddress, httpServerPort, bridgeId, bridgeSNUUID);
|
Configuration.UPNP_DISCOVERY_PORT, httpLocationAddress, httpServerPort, bridgeId, bridgeSNUUID);
|
||||||
if (traceupnp) {
|
if (traceupnp) {
|
||||||
log.info("Traceupnp: send upnp discovery template Original with response address: " + httpLocationAddress + ":"
|
log.info("Traceupnp: send upnp discovery template Original with response address: "
|
||||||
+ httpServerPort + " to address: " + requester + ":" + sourcePort);
|
+ httpLocationAddress + ":" + httpServerPort + " to address: " + requester + ":" + sourcePort);
|
||||||
} else
|
}
|
||||||
log.debug("sendUpnpResponse to address: " + requester + ":" + sourcePort
|
log.debug("sendUpnpResponse to address: " + requester + ":" + sourcePort
|
||||||
+ " with discovery responseTemplateOriginal is <<<" + discoveryResponse + ">>>");
|
+ " with discovery responseTemplateOriginal is <<<" + discoveryResponse + ">>>");
|
||||||
sendUDPResponse(discoveryResponse.getBytes(), requester, sourcePort);
|
sendUDPResponse(discoveryResponse.getBytes(), requester, sourcePort);
|
||||||
} else {
|
} else {
|
||||||
discoveryResponse = String.format(responseTemplateOriginal, Configuration.UPNP_MULTICAST_ADDRESS,
|
discoveryResponse = String.format(responseTemplateOriginal, Configuration.UPNP_MULTICAST_ADDRESS,
|
||||||
Configuration.UPNP_DISCOVERY_PORT, httpLocationAddress, httpServerPort, bridgeId, bridgeSNUUID);
|
Configuration.UPNP_DISCOVERY_PORT, httpLocationAddress, httpServerPort, bridgeId, bridgeSNUUID);
|
||||||
if (traceupnp) {
|
if (traceupnp) {
|
||||||
log.info("Traceupnp: send upnp discovery template Original with response address: " + httpLocationAddress + ":"
|
log.info("Traceupnp: send upnp discovery template Original with response address: "
|
||||||
+ httpServerPort + " to address: " + requester + ":" + sourcePort);
|
+ httpLocationAddress + ":" + httpServerPort + " to address: " + requester + ":" + sourcePort);
|
||||||
} else
|
}
|
||||||
log.debug("sendUpnpResponse to address: " + requester + ":" + sourcePort
|
log.debug("sendUpnpResponse to address: " + requester + ":" + sourcePort
|
||||||
+ " with discovery responseTemplateOriginal is <<<" + discoveryResponse + ">>>");
|
+ " with discovery responseTemplateOriginal is <<<" + discoveryResponse + ">>>");
|
||||||
sendUDPResponse(discoveryResponse.getBytes(), requester, sourcePort);
|
sendUDPResponse(discoveryResponse.getBytes(), requester, sourcePort);
|
||||||
try {
|
try {
|
||||||
Thread.sleep(theUpnpSendDelay);
|
Thread.sleep(theUpnpSendDelay);
|
||||||
@@ -268,9 +278,9 @@ public class UpnpListener {
|
|||||||
if (traceupnp) {
|
if (traceupnp) {
|
||||||
log.info("Traceupnp: send upnp discovery template 1 with response address: " + httpLocationAddress + ":"
|
log.info("Traceupnp: send upnp discovery template 1 with response address: " + httpLocationAddress + ":"
|
||||||
+ httpServerPort + " to address: " + requester + ":" + sourcePort);
|
+ httpServerPort + " to address: " + requester + ":" + sourcePort);
|
||||||
} else
|
}
|
||||||
log.debug("sendUpnpResponse to address: " + requester + ":" + sourcePort
|
log.debug("sendUpnpResponse to address: " + requester + ":" + sourcePort
|
||||||
+ " with discovery responseTemplate1 is <<<" + discoveryResponse + ">>>");
|
+ " with discovery responseTemplate1 is <<<" + discoveryResponse + ">>>");
|
||||||
sendUDPResponse(discoveryResponse.getBytes(), requester, sourcePort);
|
sendUDPResponse(discoveryResponse.getBytes(), requester, sourcePort);
|
||||||
|
|
||||||
try {
|
try {
|
||||||
@@ -284,9 +294,9 @@ public class UpnpListener {
|
|||||||
if (traceupnp) {
|
if (traceupnp) {
|
||||||
log.info("Traceupnp: send upnp discovery template 2 with response address: " + httpLocationAddress + ":"
|
log.info("Traceupnp: send upnp discovery template 2 with response address: " + httpLocationAddress + ":"
|
||||||
+ httpServerPort + " to address: " + requester + ":" + sourcePort);
|
+ httpServerPort + " to address: " + requester + ":" + sourcePort);
|
||||||
} else
|
}
|
||||||
log.debug("sendUpnpResponse to address: " + requester + ":" + sourcePort
|
log.debug("sendUpnpResponse to address: " + requester + ":" + sourcePort
|
||||||
+ " discovery responseTemplate2 is <<<" + discoveryResponse + ">>>");
|
+ " discovery responseTemplate2 is <<<" + discoveryResponse + ">>>");
|
||||||
sendUDPResponse(discoveryResponse.getBytes(), requester, sourcePort);
|
sendUDPResponse(discoveryResponse.getBytes(), requester, sourcePort);
|
||||||
|
|
||||||
try {
|
try {
|
||||||
@@ -299,9 +309,9 @@ public class UpnpListener {
|
|||||||
if (traceupnp) {
|
if (traceupnp) {
|
||||||
log.info("Traceupnp: send upnp discovery template 3 with response address: " + httpLocationAddress + ":"
|
log.info("Traceupnp: send upnp discovery template 3 with response address: " + httpLocationAddress + ":"
|
||||||
+ httpServerPort + " to address: " + requester + ":" + sourcePort);
|
+ httpServerPort + " to address: " + requester + ":" + sourcePort);
|
||||||
} else
|
}
|
||||||
log.debug("sendUpnpResponse to address: " + requester + ":" + sourcePort
|
log.debug("sendUpnpResponse to address: " + requester + ":" + sourcePort
|
||||||
+ " discovery responseTemplate3 is <<<" + discoveryResponse + ">>>");
|
+ " discovery responseTemplate3 is <<<" + discoveryResponse + ">>>");
|
||||||
sendUDPResponse(discoveryResponse.getBytes(), requester, sourcePort);
|
sendUDPResponse(discoveryResponse.getBytes(), requester, sourcePort);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -316,17 +326,50 @@ public class UpnpListener {
|
|||||||
|
|
||||||
protected void sendUpnpNotify(InetAddress aSocketAddress) {
|
protected void sendUpnpNotify(InetAddress aSocketAddress) {
|
||||||
String notifyData = null;
|
String notifyData = null;
|
||||||
|
try {
|
||||||
|
Thread.sleep(theUpnpSendDelay);
|
||||||
|
} catch (InterruptedException e) {
|
||||||
|
// noop
|
||||||
|
}
|
||||||
|
|
||||||
notifyData = String.format(notifyTemplate, Configuration.UPNP_MULTICAST_ADDRESS,
|
notifyData = String.format(notifyTemplate, Configuration.UPNP_MULTICAST_ADDRESS,
|
||||||
Configuration.UPNP_DISCOVERY_PORT, upnpConfigIP, httpServerPort, bridgeId, bridgeSNUUID, bridgeSNUUID);
|
Configuration.UPNP_DISCOVERY_PORT, upnpConfigIP, httpServerPort, bridgeId, bridgeSNUUID, bridgeSNUUID);
|
||||||
log.debug("sendUpnpNotify notifyTemplate is <<<" + notifyData + ">>>");
|
sendNotifyDatagram(notifyData, aSocketAddress, "notifyTemplate1");
|
||||||
|
|
||||||
|
try {
|
||||||
|
Thread.sleep(theUpnpSendDelay);
|
||||||
|
} catch (InterruptedException e) {
|
||||||
|
// noop
|
||||||
|
}
|
||||||
|
|
||||||
|
notifyData = String.format(notifyTemplate2, Configuration.UPNP_MULTICAST_ADDRESS,
|
||||||
|
Configuration.UPNP_DISCOVERY_PORT, upnpConfigIP, httpServerPort, bridgeId, bridgeSNUUID);
|
||||||
|
sendNotifyDatagram(notifyData, aSocketAddress, "notifyTemplate2");
|
||||||
|
|
||||||
|
try {
|
||||||
|
Thread.sleep(theUpnpSendDelay);
|
||||||
|
} catch (InterruptedException e) {
|
||||||
|
// noop
|
||||||
|
}
|
||||||
|
|
||||||
|
notifyData = String.format(notifyTemplate3, Configuration.UPNP_MULTICAST_ADDRESS,
|
||||||
|
Configuration.UPNP_DISCOVERY_PORT, upnpConfigIP, httpServerPort, bridgeId, bridgeSNUUID);
|
||||||
|
sendNotifyDatagram(notifyData, aSocketAddress, "notifyTemplate3");
|
||||||
|
}
|
||||||
|
|
||||||
|
public void sendNotifyDatagram(String notifyData, InetAddress aSocketAddress, String templateNumber) {
|
||||||
|
if (traceupnp) {
|
||||||
|
log.info("Traceupnp: sendUpnpNotify {}", templateNumber);
|
||||||
|
}
|
||||||
|
log.debug("sendUpnpNotify {} is <<<{}>>>", templateNumber, notifyData);
|
||||||
DatagramPacket notifyPacket = new DatagramPacket(notifyData.getBytes(), notifyData.length(), aSocketAddress,
|
DatagramPacket notifyPacket = new DatagramPacket(notifyData.getBytes(), notifyData.length(), aSocketAddress,
|
||||||
Configuration.UPNP_DISCOVERY_PORT);
|
Configuration.UPNP_DISCOVERY_PORT);
|
||||||
try {
|
try {
|
||||||
upnpMulticastSocket.send(notifyPacket);
|
upnpMulticastSocket.send(notifyPacket);
|
||||||
} catch (IOException e1) {
|
} catch (IOException e1) {
|
||||||
log.warn("UpnpListener encountered an error sending upnp notify packet. IP: "
|
log.warn("UpnpListener encountered an error sending upnp {}. IP: {} with message: {}", templateNumber,
|
||||||
+ notifyPacket.getAddress().getHostAddress() + " with message: " + e1.getMessage());
|
notifyPacket.getAddress().getHostAddress(), e1.getMessage());
|
||||||
log.debug("UpnpListener send upnp notify exception: ", e1);
|
log.debug("UpnpListener send {} exception: ", templateNumber, e1);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -29,7 +29,9 @@
|
|||||||
|
|
||||||
.scrollArea {
|
.scrollArea {
|
||||||
height: 100%;
|
height: 100%;
|
||||||
|
/* THis makes the table scroll - disabled as a feature for now
|
||||||
max-height: 800px;
|
max-height: 800px;
|
||||||
|
*/
|
||||||
overflow-x: auto;
|
overflow-x: auto;
|
||||||
overflow-y: auto;
|
overflow-y: auto;
|
||||||
border: 1px solid #d5d5d5;
|
border: 1px solid #d5d5d5;
|
||||||
|
|||||||
@@ -17,7 +17,24 @@
|
|||||||
<link href="css/strength-meter.min.css" rel="stylesheet">
|
<link href="css/strength-meter.min.css" rel="stylesheet">
|
||||||
<link href="css/colorpicker.min.css" rel="stylesheet">
|
<link href="css/colorpicker.min.css" rel="stylesheet">
|
||||||
|
|
||||||
<!--[if lt IE 9]>
|
<style id="compiled-css" type="text/css">
|
||||||
|
.goToTop
|
||||||
|
{
|
||||||
|
position: fixed;
|
||||||
|
width: 100px;
|
||||||
|
height: 40px;
|
||||||
|
bottom: 0;
|
||||||
|
right: 0;
|
||||||
|
z-index: 100000;
|
||||||
|
cursor: pointer;
|
||||||
|
margin: 10px;
|
||||||
|
-moz-opacity: 0.60;
|
||||||
|
opacity: .60;
|
||||||
|
filter: alpha(opacity=60);
|
||||||
|
}
|
||||||
|
</style>
|
||||||
|
|
||||||
|
<!--[if lt IE 9]>
|
||||||
<script type="text/javascript" src="js/html5shiv.min.js"></script>
|
<script type="text/javascript" src="js/html5shiv.min.js"></script>
|
||||||
<script type="text/javascript" src="js/respond.min.js"></script>
|
<script type="text/javascript" src="js/respond.min.js"></script>
|
||||||
<![endif]-->
|
<![endif]-->
|
||||||
@@ -75,8 +92,12 @@
|
|||||||
|
|
||||||
|
|
||||||
</div>
|
</div>
|
||||||
|
<span class="goToTop">
|
||||||
|
<button type="button" class="btn btn-light"><i class="glyphicon glyphicon-chevron-up"></i> Back to Top</button>
|
||||||
|
</span>
|
||||||
|
<!-- <input type="button" class="goToTop" value="Back to Top" style="display:none;background-color:blue" /> -->
|
||||||
|
|
||||||
<script src="js/jquery-1.11.3.min.js"></script>
|
<script src="js/jquery-1.11.3.min.js"></script>
|
||||||
<script src="js/angular.min.js"></script>
|
<script src="js/angular.min.js"></script>
|
||||||
<script src="js/angular-route.min.js"></script>
|
<script src="js/angular-route.min.js"></script>
|
||||||
<script src="js/angular-sanitize.min.js"></script>
|
<script src="js/angular-sanitize.min.js"></script>
|
||||||
@@ -93,5 +114,35 @@
|
|||||||
<script src="js/ng-file-upload-shim.min.js"></script>
|
<script src="js/ng-file-upload-shim.min.js"></script>
|
||||||
<script src="js/ng-file-upload.min.js"></script>
|
<script src="js/ng-file-upload.min.js"></script>
|
||||||
<script src="scripts/app.js"></script>
|
<script src="scripts/app.js"></script>
|
||||||
</body>
|
<script type="text/javascript">
|
||||||
|
$(window).load(function(){
|
||||||
|
|
||||||
|
$(window).scroll(function () {
|
||||||
|
if ($(this).scrollTop() > 100) {
|
||||||
|
$('.goToTop').fadeIn();
|
||||||
|
} else {
|
||||||
|
$('.goToTop').fadeOut();
|
||||||
|
}
|
||||||
|
});
|
||||||
|
$('.goToTop').click(function () {
|
||||||
|
$("html, body").animate({ scrollTop: 0 }, 1000);
|
||||||
|
return false;
|
||||||
|
});
|
||||||
|
|
||||||
|
});
|
||||||
|
|
||||||
|
</script>
|
||||||
|
<script>
|
||||||
|
// tell the embed parent frame the height of the content
|
||||||
|
if (window.parent && window.parent.parent){
|
||||||
|
window.parent.parent.postMessage(["resultsFrame", {
|
||||||
|
height: document.body.getBoundingClientRect().height,
|
||||||
|
slug: "fvdrw83s"
|
||||||
|
}], "*")
|
||||||
|
}
|
||||||
|
|
||||||
|
// always overwrite window.name, in case users try to set it manually
|
||||||
|
window.name = "result"
|
||||||
|
</script>
|
||||||
|
</body>
|
||||||
</html>
|
</html>
|
||||||
@@ -1875,7 +1875,7 @@ app.controller('SystemController', function ($scope, $location, bridgeService, n
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
$scope.addHasstoSettings = function (newhassname, newhassip, newhassport, newhasspassword, newhasssecure) {
|
$scope.addHasstoSettings = function (newhassname, newhassip, newhassport, newhasspassword, newhasssecure, newhassauth) {
|
||||||
if ($scope.bridge.settings.hassaddress === undefined || $scope.bridge.settings.hassaddress === null) {
|
if ($scope.bridge.settings.hassaddress === undefined || $scope.bridge.settings.hassaddress === null) {
|
||||||
$scope.bridge.settings.hassaddress = {
|
$scope.bridge.settings.hassaddress = {
|
||||||
devices: []
|
devices: []
|
||||||
@@ -1886,7 +1886,8 @@ app.controller('SystemController', function ($scope, $location, bridgeService, n
|
|||||||
ip: newhassip,
|
ip: newhassip,
|
||||||
port: newhassport,
|
port: newhassport,
|
||||||
password: newhasspassword,
|
password: newhasspassword,
|
||||||
secure: newhasssecure
|
secure: newhasssecure,
|
||||||
|
extensions: newhassauth
|
||||||
};
|
};
|
||||||
$scope.bridge.settings.hassaddress.devices.push(newhass);
|
$scope.bridge.settings.hassaddress.devices.push(newhass);
|
||||||
$scope.newhassname = null;
|
$scope.newhassname = null;
|
||||||
@@ -2070,12 +2071,39 @@ app.controller('SystemController', function ($scope, $location, bridgeService, n
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
$scope.addHomeGenietoSettings = function (newhomegeniename, newhomegenieip, newhomegenieport, newhomegenieusername, newhomegeniepassword, newhomegeniewebhook, newhomegeniesecure) {
|
$scope.addHomeGenietoSettings = function (newhomegeniename, newhomegenieip, newhomegenieport, newhomegenieusername, newhomegeniepassword, newhomegeniewebhook, newhomegeniesecure, newhomegenieothertypes) {
|
||||||
if ($scope.bridge.settings.homegenieaddress === undefined || $scope.bridge.settings.homegenieaddress === null) {
|
if ($scope.bridge.settings.homegenieaddress === undefined || $scope.bridge.settings.homegenieaddress === null) {
|
||||||
$scope.bridge.settings.homegenieaddress = {
|
$scope.bridge.settings.homegenieaddress = {
|
||||||
devices: []
|
devices: []
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
var othertypes = [];
|
||||||
|
othertypes = newhomegenieothertypes.split(",");
|
||||||
|
var theModuleTypes = [];
|
||||||
|
var count = 0;
|
||||||
|
if (othertypes.length > 0) {
|
||||||
|
for (var i = 0; i < othertypes.length; i++) {
|
||||||
|
var aType = othertypes[i].trim();
|
||||||
|
if (aType.length > 0) {
|
||||||
|
var moduleType = {
|
||||||
|
moduleType: aType
|
||||||
|
};
|
||||||
|
theModuleTypes.push(moduleType);
|
||||||
|
count++;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
var theExtension;
|
||||||
|
if (count == 0) {
|
||||||
|
theExtension = undefined;
|
||||||
|
} else {
|
||||||
|
theExtension = {
|
||||||
|
moduleTypes: theModuleTypes
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
var newhomegenie = {
|
var newhomegenie = {
|
||||||
name: newhomegeniename,
|
name: newhomegeniename,
|
||||||
ip: newhomegenieip,
|
ip: newhomegenieip,
|
||||||
@@ -2083,16 +2111,61 @@ app.controller('SystemController', function ($scope, $location, bridgeService, n
|
|||||||
username: newhomegenieusername,
|
username: newhomegenieusername,
|
||||||
password: newhomegeniepassword,
|
password: newhomegeniepassword,
|
||||||
secure: newhomegeniesecure,
|
secure: newhomegeniesecure,
|
||||||
webhook: newhomegeniewebhook
|
webhook: newhomegeniewebhook,
|
||||||
|
extensions: theExtension
|
||||||
};
|
};
|
||||||
$scope.bridge.settings.homegenieaddress.devices.push(newhomegenie);
|
$scope.bridge.settings.homegenieaddress.devices.push(newhomegenie);
|
||||||
$scope.newhomegeniename = null;
|
$scope.newhomegeniename = null;
|
||||||
$scope.newhomegenieip = null;
|
$scope.newhomegenieip = null;
|
||||||
$scope.newhomegenieport = "8080";
|
$scope.newhomegenieport = null;
|
||||||
$scope.newhomegenieusername = null;
|
$scope.newhomegenieusername = null;
|
||||||
$scope.newhomegeniepassword = null;
|
$scope.newhomegeniepassword = null;
|
||||||
$scope.newhomegeniewebhook = null;
|
$scope.newhomegeniewebhook = null;
|
||||||
|
$scope.newhomegenieextensions = null;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
$scope.updateModuleTypes = function (theIndex, homegenieExtensions) {
|
||||||
|
var othertypes = [];
|
||||||
|
if(homegenieExtensions != undefined)
|
||||||
|
othertypes = homegenieExtensions.split(",");
|
||||||
|
var theModuleTypes = [];
|
||||||
|
var count = 0;
|
||||||
|
if (othertypes.length > 0) {
|
||||||
|
for (var x = 0; x < othertypes.length; x++) {
|
||||||
|
var aType = othertypes[x].trim();
|
||||||
|
if (aType.length > 0) {
|
||||||
|
var moduleType = {
|
||||||
|
moduleType: aType
|
||||||
|
};
|
||||||
|
theModuleTypes.push(moduleType);
|
||||||
|
count++;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
var theExtension;
|
||||||
|
if (count == 0) {
|
||||||
|
theExtension = undefined;
|
||||||
|
} else {
|
||||||
|
theExtension = {
|
||||||
|
moduleTypes: theModuleTypes
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
$scope.bridge.settings.homegenieaddress.devices[theIndex].extensions = theExtension;
|
||||||
|
};
|
||||||
|
|
||||||
|
$scope.convertModuleTypes = function (theIndex) {
|
||||||
|
|
||||||
|
var displayExtension = "";
|
||||||
|
if ($scope.bridge.settings.homegenieaddress.devices[theIndex].extensions != undefined && $scope.bridge.settings.homegenieaddress.devices[theIndex].extensions.moduleTypes != undefined) {
|
||||||
|
for (var i = 0; i < $scope.bridge.settings.homegenieaddress.devices[theIndex].extensions.moduleTypes.length; i++) {
|
||||||
|
displayExtension = displayExtension + $scope.bridge.settings.homegenieaddress.devices[theIndex].extensions.moduleTypes[i].moduleType;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return displayExtension;
|
||||||
|
};
|
||||||
|
|
||||||
$scope.removeHomeGenietoSettings = function (homegeniename, homegenieip) {
|
$scope.removeHomeGenietoSettings = function (homegeniename, homegenieip) {
|
||||||
for (var i = $scope.bridge.settings.homegenieaddress.devices.length - 1; i >= 0; i--) {
|
for (var i = $scope.bridge.settings.homegenieaddress.devices.length - 1; i >= 0; i--) {
|
||||||
if ($scope.bridge.settings.homegenieaddress.devices[i].name === homegeniename && $scope.bridge.settings.homegenieaddress.devices[i].ip === homegenieip) {
|
if ($scope.bridge.settings.homegenieaddress.devices[i].name === homegeniename && $scope.bridge.settings.homegenieaddress.devices[i].ip === homegenieip) {
|
||||||
@@ -2408,7 +2481,7 @@ app.controller('ViewingController', function ($scope, $location, bridgeService,
|
|||||||
bridgeService.editDevice(device);
|
bridgeService.editDevice(device);
|
||||||
$location.path('/editdevice');
|
$location.path('/editdevice');
|
||||||
};
|
};
|
||||||
$scope.setStartupAction = function(device) {
|
$scope.setStartupAction = function (device) {
|
||||||
$scope.bridge.device = device;
|
$scope.bridge.device = device;
|
||||||
ngDialog.open({
|
ngDialog.open({
|
||||||
template: 'startupActionDialog',
|
template: 'startupActionDialog',
|
||||||
@@ -2425,7 +2498,7 @@ app.controller('ViewingController', function ($scope, $location, bridgeService,
|
|||||||
};
|
};
|
||||||
|
|
||||||
$scope.toggleLock = function (device) {
|
$scope.toggleLock = function (device) {
|
||||||
if(device.lockDeviceId) {
|
if (device.lockDeviceId) {
|
||||||
device.lockDeviceId = false;
|
device.lockDeviceId = false;
|
||||||
} else {
|
} else {
|
||||||
device.lockDeviceId = true;
|
device.lockDeviceId = true;
|
||||||
@@ -2566,9 +2639,9 @@ app.controller('StartupActionDialogCtrl', function ($scope, bridgeService, ngDia
|
|||||||
$scope.device = $scope.bridge.device;
|
$scope.device = $scope.bridge.device;
|
||||||
$scope.setDim = false;
|
$scope.setDim = false;
|
||||||
var components = [];
|
var components = [];
|
||||||
if($scope.device.startupActions != undefined) {
|
if ($scope.device.startupActions != undefined) {
|
||||||
components = $scope.device.startupActions.split(":");
|
components = $scope.device.startupActions.split(":");
|
||||||
if(components[1] != undefined && components[1].length > 0)
|
if (components[1] != undefined && components[1].length > 0)
|
||||||
$scope.setDim = true;
|
$scope.setDim = true;
|
||||||
} else {
|
} else {
|
||||||
components = "::".split(":");
|
components = "::".split(":");
|
||||||
@@ -2592,12 +2665,12 @@ app.controller('StartupActionDialogCtrl', function ($scope, bridgeService, ngDia
|
|||||||
console.log("Startup action set for device called: " + device.name);
|
console.log("Startup action set for device called: " + device.name);
|
||||||
ngDialog.close('ngdialog1');
|
ngDialog.close('ngdialog1');
|
||||||
var theValue = 1;
|
var theValue = 1;
|
||||||
if($scope.setDim) {
|
if ($scope.setDim) {
|
||||||
theValue = $scope.theState + ":" + $scope.slider.value + ":" + $scope.rgbPicker.color;
|
theValue = $scope.theState + ":" + $scope.slider.value + ":" + $scope.rgbPicker.color;
|
||||||
} else {
|
} else {
|
||||||
theValue = $scope.theState + "::" + $scope.rgbPicker.color;
|
theValue = $scope.theState + "::" + $scope.rgbPicker.color;
|
||||||
}
|
}
|
||||||
if(theValue == "::")
|
if (theValue == "::")
|
||||||
theValue = "";
|
theValue = "";
|
||||||
device.startupActions = theValue;
|
device.startupActions = theValue;
|
||||||
bridgeService.addDevice(device).then(
|
bridgeService.addDevice(device).then(
|
||||||
|
|||||||
File diff suppressed because it is too large
Load Diff
Reference in New Issue
Block a user