/** * Copyright (c) 2010-2016, openHAB.org and others. * * All rights reserved. This program and the accompanying materials * are made available under the terms of the Eclipse Public License v1.0 * which accompanies this distribution, and is available at * http://www.eclipse.org/legal/epl-v10.html */ package org.openhab.binding.fatekplc.internal; import java.util.HashSet; import java.util.List; import java.util.Map; import java.util.Set; import org.openhab.binding.fatekplc.items.CommandException; import org.openhab.binding.fatekplc.items.FatekPLCItem; import org.openhab.core.events.EventPublisher; import org.openhab.core.types.Command; import org.openhab.core.types.State; import org.osgi.service.cm.ConfigurationException; import org.simplify4u.jfatek.FatekException; import org.simplify4u.jfatek.FatekPLC; import org.simplify4u.jfatek.FatekReadMixDataCmd; import org.simplify4u.jfatek.io.FatekIOException; import org.simplify4u.jfatek.registers.Reg; import org.simplify4u.jfatek.registers.RegValue; import org.slf4j.Logger; import org.slf4j.LoggerFactory; /** * Implementation of one fatek slave. * * @author Slawomir Jaranowski * @since 1.9.0 */ public class FatekPLCSlave { /** * Main logger. */ private static final Logger logger = LoggerFactory.getLogger(FatekPLCSlave.class); private final StateCache stateCache; private EventPublisher eventPublisher; private String name; private FatekPLC fatekPLC = null; public FatekPLCSlave(String name, EventPublisher eventPublisher) { this.name = name; this.eventPublisher = eventPublisher; this.stateCache = new StateCache(); } public String getName() { return name; } public void disconnect() throws FatekIOException { if (fatekPLC != null) { fatekPLC.close(); } } /** * Configure slave property * * @param name property name * @param value config value * @throws ConfigurationException if something wrong with configuration, eg. Unknown property */ public void configure(String name, Object value) throws ConfigurationException { logger.debug("Configure item: {} to {}", name, value); if ("connectionUri".equals(name)) { try { disconnect(); fatekPLC = new FatekPLC((String) value); logger.info("New Fatek PLC connectionUri={}", value); } catch (Exception e) { fatekPLC = null; throw new ConfigurationException(name, e.getMessage()); } } else { throw new ConfigurationException(name, "Unknown property"); } logger.debug("Configure item: {} end", name); } /** * Read current data from Fatek PLC and publish new state on OpenHab bus. * * @param items items to updates * @throws FatekIOException * @throws FatekException */ public void updateItems(List<FatekPLCItem> items) throws FatekIOException, FatekException { // collect unique register to read from PLC Set<Reg> regsToUpdate = new HashSet<>(); for (FatekPLCItem item : items) { regsToUpdate.addAll(item.getRegs()); } Map<Reg, RegValue> response; synchronized (fatekPLC) { // read register response = new FatekReadMixDataCmd(fatekPLC, regsToUpdate).send(); } // distribute read data for (FatekPLCItem fatekItem : items) { State newState = fatekItem.getState(response); if (stateCache.isStateChange(fatekItem, newState)) { eventPublisher.postUpdate(fatekItem.getItemName(), newState); } } } public void command(FatekPLCItem item, Command command) { logger.debug("FatekPLC command item={}, command={} {}", item, command, command.getClass()); try { synchronized(fatekPLC) { item.command(fatekPLC, command); } } catch (CommandException e) { logger.error(e.getMessage(), e); } } }