diff --git a/bundles/binding/org.openhab.binding.fatekplc/.classpath b/bundles/binding/org.openhab.binding.fatekplc/.classpath
index 72932f1c79d..b446a74d746 100644
--- a/bundles/binding/org.openhab.binding.fatekplc/.classpath
+++ b/bundles/binding/org.openhab.binding.fatekplc/.classpath
@@ -4,6 +4,5 @@
-
diff --git a/bundles/binding/org.openhab.binding.fatekplc/META-INF/MANIFEST.MF b/bundles/binding/org.openhab.binding.fatekplc/META-INF/MANIFEST.MF
index b94f066306e..58a95c5fb70 100644
--- a/bundles/binding/org.openhab.binding.fatekplc/META-INF/MANIFEST.MF
+++ b/bundles/binding/org.openhab.binding.fatekplc/META-INF/MANIFEST.MF
@@ -9,7 +9,11 @@ Bundle-Version: 1.14.0.qualifier
Bundle-ManifestVersion: 2
Bundle-Description: This is the Fatek PLC binding of the open Home
Automation Bus (openHAB)
-Import-Package: org.apache.commons.lang,
+Import-Package: gnu.io,
+ org.simplify4u.jfatek,
+ org.simplify4u.jfatek.io,
+ org.simplify4u.jfatek.registers,
+ org.apache.commons.lang,
org.openhab.core.binding,
org.openhab.core.events,
org.openhab.core.items,
@@ -25,8 +29,7 @@ Import-Package: org.apache.commons.lang,
org.slf4j
Export-Package: org.openhab.binding.fatekplc
Bundle-DocURL: http://www.openhab.org
-Bundle-RequiredExecutionEnvironment: JavaSE-1.7
+Bundle-RequiredExecutionEnvironment: JavaSE-1.8
Service-Component: OSGI-INF/binding.xml, OSGI-INF/genericbindingprovider.xml
Bundle-Activator: org.openhab.binding.fatekplc.internal.FatekPLCActivator
-Bundle-ClassPath: .,
- lib/jfatek-2.0.0.jar
+Bundle-ClassPath: .
diff --git a/bundles/binding/org.openhab.binding.fatekplc/README.md b/bundles/binding/org.openhab.binding.fatekplc/README.md
index 6e51b9bb442..c4bdd2bc64e 100644
--- a/bundles/binding/org.openhab.binding.fatekplc/README.md
+++ b/bundles/binding/org.openhab.binding.fatekplc/README.md
@@ -9,7 +9,42 @@ The binding can be configured in the file `services/fatekplc.cfg`.
| Property | Default | Required | Description |
|----------|---------|:--------:|-------------|
| refresh | 60000 | No | refresh interval in milliseconds which is used to poll values from the Fatek PLC server |
-| ``.connectionUri | | Yes | connection URI for the `` you provide, so multiple Fatek PLCs can be addressed. Supports either `tcp://` or `udp://` protocol. For example, `udp://192.168.1.100?plcId=1` |
+| ``.connectionUri | | Yes | connection URI for the `` you provide, so multiple Fatek PLCs can be addressed. Supports either `tcp://`, `udp://` or `serial://` protocol. |
+
+The common `connectionUri` syntax is:
+```
+protocol://address:[port]?plcId=param1=value1¶mN=ValueN
+```
+| Name | Description | Default |
+|---------|-----------------------------------------|-------|
+| plcId | PLC id, must be set | - |
+| timeout | connection/read timeout in milliseconds | 5000 |
+
+### `tcp` or `udp` parameters
+
+There are not more parameters for this connection protocols.
+
+Example, `udp://192.168.1.100?plcId=1&timeout=1000`
+Default `port` is `500`
+
+### serial parameters
+
+| Name | Description | Default |
+|---------|-------------|---------|
+| baudRate | serial connection speed bit/s | 9600 |
+| dataBits | number of data bits in each character | 7 |
+| stopBits | number of bits sent at the end of each character, can be `1`, `2` or `1.5` | 1 |
+| parity | control bit set, can be: `NONE`, `ODD`, `EVEN`, `MARK` or `SPACE` | EVEN |
+
+Serial port name is given as address of connectionUri.
+You can write begin name of port, first matched will be used.
+
+Examples:
+
+`serial:///dev/tty-usbserial?plcId=1&baudRate=19200`
+
+`serial://COM1?plcId=1&baudRate=19200&timeout=1000`
+
## Item Configuration
diff --git a/bundles/binding/org.openhab.binding.fatekplc/build.properties b/bundles/binding/org.openhab.binding.fatekplc/build.properties
index 605fecd09b7..cddd6d05b0f 100644
--- a/bundles/binding/org.openhab.binding.fatekplc/build.properties
+++ b/bundles/binding/org.openhab.binding.fatekplc/build.properties
@@ -3,6 +3,5 @@ source.. = src/main/java/,\
bin.includes = META-INF/,\
.,\
OSGI-INF/,\
- NOTICE,\
- lib/jfatek-2.0.0.jar
+ NOTICE
output.. = target/classes/
diff --git a/bundles/binding/org.openhab.binding.fatekplc/lib/jfatek-2.0.0-sources.jar b/bundles/binding/org.openhab.binding.fatekplc/lib/jfatek-2.0.0-sources.jar
deleted file mode 100644
index 01ce3bdb18b..00000000000
Binary files a/bundles/binding/org.openhab.binding.fatekplc/lib/jfatek-2.0.0-sources.jar and /dev/null differ
diff --git a/bundles/binding/org.openhab.binding.fatekplc/lib/jfatek-2.0.0.jar b/bundles/binding/org.openhab.binding.fatekplc/lib/jfatek-2.0.0.jar
deleted file mode 100644
index 56673fc1158..00000000000
Binary files a/bundles/binding/org.openhab.binding.fatekplc/lib/jfatek-2.0.0.jar and /dev/null differ
diff --git a/bundles/binding/org.openhab.binding.fatekplc/pom.xml b/bundles/binding/org.openhab.binding.fatekplc/pom.xml
index 5b8b860bbab..be20d697151 100644
--- a/bundles/binding/org.openhab.binding.fatekplc/pom.xml
+++ b/bundles/binding/org.openhab.binding.fatekplc/pom.xml
@@ -14,9 +14,12 @@
openHAB Fatek PLC Binding
-
- 1.7
- 1.7
-
+
+
+ org.simplify4u
+ jfatek
+ 3.0.0
+
+
diff --git a/bundles/binding/org.openhab.binding.fatekplc/src/main/java/org/openhab/binding/fatekplc/internal/FatekPLCSlave.java b/bundles/binding/org.openhab.binding.fatekplc/src/main/java/org/openhab/binding/fatekplc/internal/FatekPLCSlave.java
index 25ba81e3db1..15d4ab7e763 100644
--- a/bundles/binding/org.openhab.binding.fatekplc/src/main/java/org/openhab/binding/fatekplc/internal/FatekPLCSlave.java
+++ b/bundles/binding/org.openhab.binding.fatekplc/src/main/java/org/openhab/binding/fatekplc/internal/FatekPLCSlave.java
@@ -19,6 +19,7 @@
import org.openhab.binding.fatekplc.items.CommandException;
import org.openhab.binding.fatekplc.items.FatekPLCItem;
+import org.openhab.binding.fatekplc.serial.SerialFatekConnectionFactory;
import org.openhab.core.events.EventPublisher;
import org.openhab.core.types.Command;
import org.openhab.core.types.State;
@@ -53,6 +54,10 @@ public class FatekPLCSlave {
private FatekPLC fatekPLC = null;
+ static {
+ FatekPLC.registerConnectionFactory(new SerialFatekConnectionFactory());
+ }
+
public FatekPLCSlave(String name, EventPublisher eventPublisher) {
this.name = name;
this.eventPublisher = eventPublisher;
@@ -73,28 +78,28 @@ public void disconnect() throws FatekIOException {
/**
* Configure slave property
*
- * @param name property name
+ * @param configName property configName
* @param value config value
* @throws ConfigurationException if something wrong with configuration, eg. Unknown property
*/
- public void configure(String name, Object value) throws ConfigurationException {
+ public void configure(String configName, Object value) throws ConfigurationException {
- logger.debug("Configure item: {} to {}", name, value);
+ logger.debug("Configure item: {} to {}", configName, value);
- if ("connectionUri".equals(name)) {
+ if ("connectionUri".equals(configName)) {
try {
disconnect();
fatekPLC = new FatekPLC((String) value);
- logger.info("New Fatek PLC connectionUri={}", value);
+ logger.info("New Fatek PLC name={}, connectionUri={}", name, value);
} catch (Exception e) {
fatekPLC = null;
- throw new ConfigurationException(name, e.getMessage());
+ throw new ConfigurationException(configName, e.getMessage(), e);
}
} else {
- throw new ConfigurationException(name, "Unknown property");
+ throw new ConfigurationException(configName, "Unknown property");
}
- logger.debug("Configure item: {} end", name);
+ logger.debug("Configure item: {} end", configName);
}
/**
diff --git a/bundles/binding/org.openhab.binding.fatekplc/src/main/java/org/openhab/binding/fatekplc/serial/SerialFatekConnectionFactory.java b/bundles/binding/org.openhab.binding.fatekplc/src/main/java/org/openhab/binding/fatekplc/serial/SerialFatekConnectionFactory.java
index 56659afec5a..0f91c52b318 100644
--- a/bundles/binding/org.openhab.binding.fatekplc/src/main/java/org/openhab/binding/fatekplc/serial/SerialFatekConnectionFactory.java
+++ b/bundles/binding/org.openhab.binding.fatekplc/src/main/java/org/openhab/binding/fatekplc/serial/SerialFatekConnectionFactory.java
@@ -12,58 +12,150 @@
*/
package org.openhab.binding.fatekplc.serial;
-import java.io.IOException;
-import java.io.InputStream;
-import java.io.OutputStream;
-
+import gnu.io.CommPortIdentifier;
+import gnu.io.NoSuchPortException;
+import gnu.io.PortInUseException;
+import gnu.io.SerialPort;
+import gnu.io.UnsupportedCommOperationException;
import org.simplify4u.jfatek.io.FatekConfig;
import org.simplify4u.jfatek.io.FatekConnection;
import org.simplify4u.jfatek.io.FatekConnectionFactory;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.OutputStream;
+import java.util.ArrayList;
+import java.util.Enumeration;
+import java.util.List;
+import java.util.Optional;
/**
* Serial connection for Fatek PLC binding.
*
- * TODO - to implemented.
- *
* @author Slawomir Jaranowski
* @since 1.9.0
- *
*/
public class SerialFatekConnectionFactory implements FatekConnectionFactory {
- class Connection extends FatekConnection {
+ private static final Logger logger = LoggerFactory.getLogger(SerialFatekConnectionFactory.class);
+
+ private static final String SCHEMA_NAME = "serial";
+
+ class Connection extends FatekConnection {
+
+ private SerialPort serialPort;
+
+ Connection(FatekConfig fatekConfig) throws IOException, PortInUseException, UnsupportedCommOperationException {
+ super(fatekConfig);
+
+ final CommPortIdentifier commPortIdentifier = findComPort();
+
+ serialPort = commPortIdentifier.open("openHAB-FatekPLC", 2000);
+ serialPort.setSerialPortParams(getBaud(), getDataBits(), getStopBits(), getParity());
+ serialPort.enableReceiveTimeout(getTimeout());
+
+ logger.info("New connection to: {} opened", serialPort.getName());
+ }
+
+ private int getBaud() {
+ return getParamAsInt("baudRate").orElse(9600);
+ }
+
+ private int getDataBits() {
+ return getParamAsInt("dataBits").orElse(SerialPort.DATABITS_7);
+ }
+
+ private int getStopBits() throws IOException {
+ final Optional stopBits = getParam("stopBits");
+ switch (stopBits.orElse("1")) {
+ case "1":
+ return SerialPort.STOPBITS_1;
+ case "2":
+ return SerialPort.STOPBITS_2;
+ case "1.5":
+ return SerialPort.STOPBITS_1_5;
+ default:
+ throw new IOException("Unknown stopBits=" + stopBits);
+ }
+ }
+
+ private int getParity() throws IOException {
+ final Optional parity = getParam("parity");
+ switch (parity.map(String::toUpperCase).orElse("EVEN")) {
+ case "NONE":
+ return SerialPort.PARITY_NONE;
+ case "ODD":
+ return SerialPort.PARITY_ODD;
+ case "EVEN":
+ return SerialPort.PARITY_EVEN;
+ case "MARK":
+ return SerialPort.PARITY_MARK;
+ case "SPACE":
+ return SerialPort.PARITY_SPACE;
+ default:
+ throw new IOException("Unknown parity=" + parity);
+ }
+ }
+
+ @Override
+ protected InputStream getInputStream() throws IOException {
+ return serialPort.getInputStream();
+ }
+
+ @Override
+ protected OutputStream getOutputStream() throws IOException {
+ return serialPort.getOutputStream();
+ }
- protected Connection(FatekConfig fatekConfig) {
- super(fatekConfig);
+ @Override
+ protected void closeConnection() throws IOException {
+ serialPort.close();
+ logger.info("Connection to: {} closed", serialPort.getName());
+ serialPort = null;
+ }
- // TODO - init and open serial port here
- }
+ @Override
+ public boolean isConnected() {
+ return serialPort != null;
+ }
- @Override
- protected InputStream getInputStream() throws IOException {
- throw new IOException("Not implemented");
- }
+ private CommPortIdentifier findComPort() throws IOException {
- @Override
- protected OutputStream getOutputStream() throws IOException {
- throw new IOException("Not implemented");
- }
+ // list all available serial ports
+ final List availableNames = new ArrayList<>();
+ final Enumeration portIdentifiers = CommPortIdentifier.getPortIdentifiers();
+ while (portIdentifiers.hasMoreElements()) {
+ final CommPortIdentifier id = (CommPortIdentifier) portIdentifiers.nextElement();
+ if (id.getPortType() == CommPortIdentifier.PORT_SERIAL) {
+ availableNames.add(id.getName());
+ }
+ }
- @Override
- protected void closeConnection() throws IOException {
- throw new IOException("Not implemented");
- }
+ final String portNameCandidate = getFullName();
+ // find first matching port name, on some system usb serial port can have suffix depends on which usb port we use
+ final Optional portName = availableNames.stream().filter(name -> name.startsWith(portNameCandidate)).findFirst();
- @Override
- public boolean isConnected() {
- return false;
- }
- }
+ try {
+ return CommPortIdentifier.getPortIdentifier(portName.orElseThrow(NoSuchPortException::new));
+ } catch (NoSuchPortException e) {
+ throw new IOException("Serial port '" + portNameCandidate + "' could not be found. Available ports are:\n" + availableNames);
+ }
+ }
+ }
- @Override
- public FatekConnection getConnection(FatekConfig fatekConfig)
- throws IOException {
- return new Connection(fatekConfig);
- }
+ @Override
+ public FatekConnection getConnection(FatekConfig fatekConfig) throws IOException {
+ try {
+ return new Connection(fatekConfig);
+ } catch (PortInUseException | UnsupportedCommOperationException e) {
+ throw new IOException(e);
+ }
+ }
+ @Override
+ public String getSchema() {
+ return SCHEMA_NAME;
+ }
}
diff --git a/bundles/binding/org.openhab.binding.fatekplc/src/main/resources/jfatek/SERIALFatekConnectionFactory b/bundles/binding/org.openhab.binding.fatekplc/src/main/resources/jfatek/SERIALFatekConnectionFactory
deleted file mode 100644
index 775b652329a..00000000000
--- a/bundles/binding/org.openhab.binding.fatekplc/src/main/resources/jfatek/SERIALFatekConnectionFactory
+++ /dev/null
@@ -1 +0,0 @@
-org.openhab.binding.fatekplc.serial.SerialFatekConnectionFactory
diff --git a/features/openhab-addons-external/src/main/resources/conf/fatekplc.cfg b/features/openhab-addons-external/src/main/resources/conf/fatekplc.cfg
index 0c4b42e301e..9e9da4128a7 100644
--- a/features/openhab-addons-external/src/main/resources/conf/fatekplc.cfg
+++ b/features/openhab-addons-external/src/main/resources/conf/fatekplc.cfg
@@ -4,5 +4,5 @@
# (optional, defaults to 60000ms / 60 seconds)
# fatekplc:refresh=60000
#
-# fatek connection uri, support tcp and udp
+# fatek connection uri, support tcp, udp and serial
# fatekplc:plc1.connectionUri=udp://192.168.1.100?plcId=1
diff --git a/features/openhab-addons/src/main/feature/feature.xml b/features/openhab-addons/src/main/feature/feature.xml
index e95a204fd1e..598bd404f8a 100644
--- a/features/openhab-addons/src/main/feature/feature.xml
+++ b/features/openhab-addons/src/main/feature/feature.xml
@@ -202,6 +202,8 @@
openhab-runtime-base
openhab-runtime-compat1x
+ openhab-transport-serial
+ mvn:org.simplify4u/jfatek/3.0.0
mvn:org.openhab.binding/org.openhab.binding.fatekplc/${project.version}
mvn:${project.groupId}/openhab-addons-external/${project.version}/cfg/fatekplc