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

Commit

Permalink
[fatekplc] Serial port support
Browse files Browse the repository at this point in the history
Signed-off-by: Slawomir Jaranowski <[email protected]>
  • Loading branch information
slawekjaranowski committed Nov 12, 2019
1 parent 725c3c4 commit 0722944
Show file tree
Hide file tree
Showing 12 changed files with 193 additions and 56 deletions.
1 change: 0 additions & 1 deletion bundles/binding/org.openhab.binding.fatekplc/.classpath
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,5 @@
<classpathentry kind="con" path="org.eclipse.pde.core.requiredPlugins"/>
<classpathentry including="**/*.java" kind="src" path="src/main/java"/>
<classpathentry kind="src" path="src/main/resources"/>
<classpathentry kind="lib" path="lib/jfatek-2.0.0.jar" sourcepath="lib/jfatek-2.0.0-sources.jar"/>
<classpathentry kind="output" path="target/classes"/>
</classpath>
Original file line number Diff line number Diff line change
Expand Up @@ -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,
Expand All @@ -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: .
37 changes: 36 additions & 1 deletion bundles/binding/org.openhab.binding.fatekplc/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -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 |
| `<plcName>`.connectionUri | | Yes | connection URI for the `<plcName>` you provide, so multiple Fatek PLCs can be addressed. Supports either `tcp://` or `udp://` protocol. For example, `udp://192.168.1.100?plcId=1` |
| `<plcName>`.connectionUri | | Yes | connection URI for the `<plcName>` 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=<plcId>param1=value1&paramN=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

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -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/
Binary file not shown.
Binary file not shown.
11 changes: 7 additions & 4 deletions bundles/binding/org.openhab.binding.fatekplc/pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -14,9 +14,12 @@

<name>openHAB Fatek PLC Binding</name>

<properties>
<maven.compiler.source>1.7</maven.compiler.source>
<maven.compiler.target>1.7</maven.compiler.target>
</properties>
<dependencies>
<dependency>
<groupId>org.simplify4u</groupId>
<artifactId>jfatek</artifactId>
<version>3.0.0</version>
</dependency>
</dependencies>

</project>
Original file line number Diff line number Diff line change
Expand Up @@ -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;
Expand Down Expand Up @@ -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;
Expand All @@ -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);
}

/**
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -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<String> 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<String> 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<String> 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<String> 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;
}

}

This file was deleted.

Original file line number Diff line number Diff line change
Expand Up @@ -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
2 changes: 2 additions & 0 deletions features/openhab-addons/src/main/feature/feature.xml
Original file line number Diff line number Diff line change
Expand Up @@ -202,6 +202,8 @@
<feature name="openhab-binding-fatekplc1" description="Fatek PLC Binding" version="${project.version}">
<feature>openhab-runtime-base</feature>
<feature>openhab-runtime-compat1x</feature>
<feature>openhab-transport-serial</feature>
<bundle start-level="80">mvn:org.simplify4u/jfatek/3.0.0</bundle>
<bundle start-level="80">mvn:org.openhab.binding/org.openhab.binding.fatekplc/${project.version}</bundle>
<configfile finalname="${openhab.conf}/services/fatekplc.cfg" override="false">mvn:${project.groupId}/openhab-addons-external/${project.version}/cfg/fatekplc</configfile>
</feature>
Expand Down

0 comments on commit 0722944

Please sign in to comment.