[epsonprojector] Fix discovery service to prevent erroneous inbox items (#12586)
* Fix discovery service to prevent erroneous inbox items * improve EPSON string matching Signed-off-by: Michael Lobstein <michael.lobstein@gmail.com>
This commit is contained in:
@@ -16,7 +16,6 @@ import static org.openhab.binding.epsonprojector.internal.EpsonProjectorBindingC
|
|||||||
|
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.net.SocketException;
|
import java.net.SocketException;
|
||||||
import java.util.HashMap;
|
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
import java.util.Set;
|
import java.util.Set;
|
||||||
import java.util.concurrent.ScheduledFuture;
|
import java.util.concurrent.ScheduledFuture;
|
||||||
@@ -115,31 +114,27 @@ public class EpsonProjectorDiscoveryService extends AbstractDiscoveryService {
|
|||||||
}
|
}
|
||||||
|
|
||||||
while (!terminate) {
|
while (!terminate) {
|
||||||
boolean beaconReceived;
|
|
||||||
try {
|
try {
|
||||||
// Wait for a discovery beacon.
|
// Wait for a discovery beacon to return properties for an Epson projector.
|
||||||
beaconReceived = epsonMulticastListener.waitForBeacon();
|
Map<String, Object> thingProperties = epsonMulticastListener.waitForBeacon();
|
||||||
|
|
||||||
|
if (thingProperties != null) {
|
||||||
|
// The MulticastListener found a projector, add it as new thing
|
||||||
|
String uid = (String) thingProperties.get(THING_PROPERTY_MAC);
|
||||||
|
String ipAddress = (String) thingProperties.get(THING_PROPERTY_HOST);
|
||||||
|
|
||||||
|
if (uid != null) {
|
||||||
|
logger.trace("Projector with UID {} discovered at IP: {}", uid, ipAddress);
|
||||||
|
|
||||||
|
ThingUID thingUid = new ThingUID(THING_TYPE_PROJECTOR_TCP, uid);
|
||||||
|
logger.trace("Creating epson projector discovery result for: {}, IP={}", uid, ipAddress);
|
||||||
|
thingDiscovered(DiscoveryResultBuilder.create(thingUid).withProperties(thingProperties)
|
||||||
|
.withLabel("Epson Projector " + uid).withRepresentationProperty(THING_PROPERTY_MAC)
|
||||||
|
.build());
|
||||||
|
}
|
||||||
|
}
|
||||||
} catch (IOException ioe) {
|
} catch (IOException ioe) {
|
||||||
logger.debug("Discovery job got exception waiting for beacon: {}", ioe.getMessage());
|
logger.debug("Discovery job got exception waiting for beacon: {}", ioe.getMessage());
|
||||||
beaconReceived = false;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (beaconReceived) {
|
|
||||||
// We got a discovery beacon. Process it as a potential new thing
|
|
||||||
Map<String, Object> properties = new HashMap<>();
|
|
||||||
String uid = epsonMulticastListener.getUID();
|
|
||||||
|
|
||||||
properties.put(THING_PROPERTY_HOST, epsonMulticastListener.getIPAddress());
|
|
||||||
properties.put(THING_PROPERTY_PORT, DEFAULT_PORT);
|
|
||||||
|
|
||||||
logger.trace("Projector with UID {} discovered at IP: {}", uid, epsonMulticastListener.getIPAddress());
|
|
||||||
|
|
||||||
ThingUID thingUid = new ThingUID(THING_TYPE_PROJECTOR_TCP, uid);
|
|
||||||
logger.trace("Creating epson projector discovery result for: {}, IP={}", uid,
|
|
||||||
epsonMulticastListener.getIPAddress());
|
|
||||||
thingDiscovered(DiscoveryResultBuilder.create(thingUid).withProperties(properties)
|
|
||||||
.withLabel("Epson Projector " + uid).withProperty(THING_PROPERTY_MAC, uid)
|
|
||||||
.withRepresentationProperty(THING_PROPERTY_MAC).build());
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
epsonMulticastListener.shutdown();
|
epsonMulticastListener.shutdown();
|
||||||
|
|||||||
@@ -12,6 +12,11 @@
|
|||||||
*/
|
*/
|
||||||
package org.openhab.binding.epsonprojector.internal.discovery;
|
package org.openhab.binding.epsonprojector.internal.discovery;
|
||||||
|
|
||||||
|
import static org.openhab.binding.epsonprojector.internal.EpsonProjectorBindingConstants.DEFAULT_PORT;
|
||||||
|
import static org.openhab.binding.epsonprojector.internal.EpsonProjectorBindingConstants.THING_PROPERTY_HOST;
|
||||||
|
import static org.openhab.binding.epsonprojector.internal.EpsonProjectorBindingConstants.THING_PROPERTY_MAC;
|
||||||
|
import static org.openhab.binding.epsonprojector.internal.EpsonProjectorBindingConstants.THING_PROPERTY_PORT;
|
||||||
|
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.net.DatagramPacket;
|
import java.net.DatagramPacket;
|
||||||
import java.net.InetAddress;
|
import java.net.InetAddress;
|
||||||
@@ -20,8 +25,12 @@ import java.net.NetworkInterface;
|
|||||||
import java.net.SocketException;
|
import java.net.SocketException;
|
||||||
import java.net.SocketTimeoutException;
|
import java.net.SocketTimeoutException;
|
||||||
import java.nio.charset.StandardCharsets;
|
import java.nio.charset.StandardCharsets;
|
||||||
|
import java.util.HashMap;
|
||||||
|
import java.util.Locale;
|
||||||
|
import java.util.Map;
|
||||||
|
|
||||||
import org.eclipse.jdt.annotation.NonNullByDefault;
|
import org.eclipse.jdt.annotation.NonNullByDefault;
|
||||||
|
import org.eclipse.jdt.annotation.Nullable;
|
||||||
import org.slf4j.Logger;
|
import org.slf4j.Logger;
|
||||||
import org.slf4j.LoggerFactory;
|
import org.slf4j.LoggerFactory;
|
||||||
|
|
||||||
@@ -38,10 +47,6 @@ public class MulticastListener {
|
|||||||
|
|
||||||
private MulticastSocket socket;
|
private MulticastSocket socket;
|
||||||
|
|
||||||
// Epson-specific properties defined in this binding
|
|
||||||
private String uid = "";
|
|
||||||
private String ipAddress = "";
|
|
||||||
|
|
||||||
// Epson projector devices announce themselves on a multicast port
|
// Epson projector devices announce themselves on a multicast port
|
||||||
private static final String EPSON_MULTICAST_GROUP = "239.255.250.250";
|
private static final String EPSON_MULTICAST_GROUP = "239.255.250.250";
|
||||||
private static final int EPSON_MULTICAST_PORT = 9131;
|
private static final int EPSON_MULTICAST_PORT = 9131;
|
||||||
@@ -70,10 +75,10 @@ public class MulticastListener {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Wait on the multicast socket for an announcement beacon. Return false on socket timeout or error.
|
* Wait on the multicast socket for an announcement beacon. Return null on socket timeout or error.
|
||||||
* Otherwise, parse the beacon for information about the device.
|
* Otherwise, parse the beacon for information about the device and return the device properties.
|
||||||
*/
|
*/
|
||||||
public boolean waitForBeacon() throws IOException {
|
public @Nullable Map<String, Object> waitForBeacon() throws IOException {
|
||||||
byte[] bytes = new byte[600];
|
byte[] bytes = new byte[600];
|
||||||
boolean beaconFound;
|
boolean beaconFound;
|
||||||
|
|
||||||
@@ -90,11 +95,11 @@ public class MulticastListener {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (beaconFound) {
|
if (beaconFound) {
|
||||||
// Get the device properties from the announcement beacon
|
// Return the device properties from the announcement beacon
|
||||||
parseAnnouncementBeacon(msgPacket);
|
return parseAnnouncementBeacon(msgPacket);
|
||||||
}
|
}
|
||||||
|
|
||||||
return beaconFound;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
@@ -103,47 +108,26 @@ public class MulticastListener {
|
|||||||
* Example Epson beacon:
|
* Example Epson beacon:
|
||||||
* AMXB<-UUID=000048746B33><-SDKClass=VideoProjector><-GUID=EPSON_EMP001><-Revision=1.0.0>
|
* AMXB<-UUID=000048746B33><-SDKClass=VideoProjector><-GUID=EPSON_EMP001><-Revision=1.0.0>
|
||||||
*/
|
*/
|
||||||
private void parseAnnouncementBeacon(DatagramPacket packet) {
|
private @Nullable Map<String, Object> parseAnnouncementBeacon(DatagramPacket packet) {
|
||||||
String beacon = (new String(packet.getData(), StandardCharsets.UTF_8)).trim();
|
String beacon = (new String(packet.getData(), StandardCharsets.UTF_8)).trim();
|
||||||
|
|
||||||
logger.trace("Multicast listener parsing announcement packet: {}", beacon);
|
logger.trace("Multicast listener parsing announcement packet: {}", beacon);
|
||||||
|
|
||||||
clearProperties();
|
if (beacon.toUpperCase(Locale.ENGLISH).contains("EPSON") && beacon.contains("VideoProjector")) {
|
||||||
|
String[] parameterList = beacon.replace(">", "").split("<-");
|
||||||
|
|
||||||
if (beacon.toUpperCase().contains("EPSON") && beacon.toUpperCase().contains("VIDEOPROJECTOR")) {
|
for (String parameter : parameterList) {
|
||||||
ipAddress = packet.getAddress().getHostAddress();
|
String[] keyValue = parameter.split("=");
|
||||||
parseEpsonAnnouncementBeacon(beacon);
|
|
||||||
} else {
|
if (keyValue.length == 2 && keyValue[0].contains("UUID") && !keyValue[1].isEmpty()) {
|
||||||
|
Map<String, Object> properties = new HashMap<>();
|
||||||
|
properties.put(THING_PROPERTY_MAC, keyValue[1]);
|
||||||
|
properties.put(THING_PROPERTY_HOST, packet.getAddress().getHostAddress());
|
||||||
|
properties.put(THING_PROPERTY_PORT, DEFAULT_PORT);
|
||||||
|
return properties;
|
||||||
|
}
|
||||||
|
}
|
||||||
logger.debug("Multicast listener doesn't know how to parse beacon: {}", beacon);
|
logger.debug("Multicast listener doesn't know how to parse beacon: {}", beacon);
|
||||||
}
|
}
|
||||||
}
|
return null;
|
||||||
|
|
||||||
private void parseEpsonAnnouncementBeacon(String beacon) {
|
|
||||||
String[] parameterList = beacon.split("<-");
|
|
||||||
|
|
||||||
for (String parameter : parameterList) {
|
|
||||||
String[] keyValue = parameter.split("=");
|
|
||||||
|
|
||||||
if (keyValue.length != 2) {
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (keyValue[0].contains("UUID")) {
|
|
||||||
uid = keyValue[1].substring(0, keyValue[1].length() - 1);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private void clearProperties() {
|
|
||||||
uid = "";
|
|
||||||
ipAddress = "";
|
|
||||||
}
|
|
||||||
|
|
||||||
public String getUID() {
|
|
||||||
return uid;
|
|
||||||
}
|
|
||||||
|
|
||||||
public String getIPAddress() {
|
|
||||||
return ipAddress;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user