diff --git a/drivers/odtn-driver/src/main/java/org/onosproject/drivers/odtn/AdvaFlowRuleProgrammable.java b/drivers/odtn-driver/src/main/java/org/onosproject/drivers/odtn/AdvaFlowRuleProgrammable.java
new file mode 100644
index 0000000..9b3ae83
--- /dev/null
+++ b/drivers/odtn-driver/src/main/java/org/onosproject/drivers/odtn/AdvaFlowRuleProgrammable.java
@@ -0,0 +1,251 @@
+/*
+ * Copyright 2018-present Open Networking Foundation
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+
+ * This work was partially supported by EC H2020 project METRO-HAUL (761727).
+ */
+
+package org.onosproject.drivers.odtn;
+
+import com.google.common.collect.ImmutableList;
+import org.onlab.util.Frequency;
+import org.onosproject.drivers.odtn.impl.DeviceConnectionCache;
+import org.onosproject.drivers.odtn.impl.FlowRuleParser;
+import org.onosproject.net.DeviceId;
+import org.onosproject.net.Port;
+import org.onosproject.net.PortNumber;
+import org.onosproject.net.device.DeviceService;
+import org.onosproject.net.driver.AbstractHandlerBehaviour;
+import org.onosproject.net.flow.DefaultFlowEntry;
+import org.onosproject.net.flow.FlowEntry;
+import org.onosproject.net.flow.FlowRule;
+import org.onosproject.net.flow.FlowRuleProgrammable;
+import org.onosproject.netconf.DatastoreId;
+import org.onosproject.netconf.NetconfController;
+import org.onosproject.netconf.NetconfException;
+import org.onosproject.netconf.NetconfSession;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.List;
+
+import static com.google.common.base.Preconditions.checkNotNull;
+import static org.onosproject.odtn.behaviour.OdtnDeviceDescriptionDiscovery.OC_NAME;
+
+/**
+ * Implementation of FlowRuleProgrammable interface for
+ * OpenConfig terminal devices.
+ */
+public class AdvaFlowRuleProgrammable
+        extends AbstractHandlerBehaviour implements FlowRuleProgrammable {
+
+    private static final Logger log =
+            LoggerFactory.getLogger(AdvaFlowRuleProgrammable.class);
+
+    /**
+     * Apply the flow entries specified in the collection rules.
+     *
+     * @param rules A collection of Flow Rules to be applied
+     * @return The collection of added Flow Entries
+     */
+    @Override
+    public Collection<FlowRule> applyFlowRules(Collection<FlowRule> rules) {
+        NetconfSession session = getNetconfSession();
+        if (session == null) {
+            openConfigError("null session");
+            return ImmutableList.of();
+        }
+        List<FlowRule> added = new ArrayList<>();
+        for (FlowRule r : rules) {
+            try {
+                String connectionId = applyFlowRule(session, r);
+                getConnectionCache().add(did(), connectionId, r);
+                added.add(r);
+            } catch (Exception e) {
+                openConfigError("Error {}", e);
+                continue;
+            }
+        }
+        openConfigLog("applyFlowRules added {}", added.size());
+        return added;
+    }
+
+    /**
+     * Get the flow entries that are present on the device.
+     *
+     * @return A collection of Flow Entries
+     */
+    @Override
+    public Collection<FlowEntry> getFlowEntries() {
+        DeviceConnectionCache cache = getConnectionCache();
+        if (cache.get(did()) == null) {
+            return ImmutableList.of();
+        }
+
+        List<FlowEntry> entries = new ArrayList<>();
+        for (FlowRule r : cache.get(did())) {
+            entries.add(
+                    new DefaultFlowEntry(r, FlowEntry.FlowEntryState.ADDED, 0, 0, 0));
+        }
+        return entries;
+    }
+
+    /**
+     * Remove the specified flow rules.
+     *
+     * @param rules A collection of Flow Rules to be removed
+     * @return The collection of removed Flow Entries
+     */
+    @Override
+    public Collection<FlowRule> removeFlowRules(Collection<FlowRule> rules) {
+        NetconfSession session = getNetconfSession();
+        if (session == null) {
+            openConfigError("null session");
+            return ImmutableList.of();
+        }
+        List<FlowRule> removed = new ArrayList<>();
+        for (FlowRule r : rules) {
+            try {
+                String connectionId = removeFlowRule(session, r);
+                getConnectionCache().remove(did(), connectionId);
+                removed.add(r);
+            } catch (Exception e) {
+                openConfigError("Error {}", e);
+                continue;
+            }
+        }
+        openConfigLog("removedFlowRules removed {}", removed.size());
+        return removed;
+    }
+
+    private DeviceConnectionCache getConnectionCache() {
+        return DeviceConnectionCache.init();
+    }
+
+    /**
+     * Helper method to get the device id.
+     */
+    private DeviceId did() {
+        return data().deviceId();
+    }
+
+    /**
+     * Helper method to log from this class adding DeviceId.
+     */
+    private void openConfigLog(String format, Object... arguments) {
+        log.info("OPENCONFIG {}: " + format, did(), arguments);
+    }
+
+    /**
+     * Helper method to log an error from this class adding DeviceId.
+     */
+    private void openConfigError(String format, Object... arguments) {
+        log.error("OPENCONFIG {}: " + format, did(), arguments);
+    }
+
+
+    /**
+     * Helper method to get the Netconf Session.
+     */
+    private NetconfSession getNetconfSession() {
+        NetconfController controller =
+                checkNotNull(handler().get(NetconfController.class));
+        return controller.getNetconfDevice(did()).getSession();
+    }
+
+    private void setOpticalChannelFrequency(NetconfSession session,
+                                            String optChannel, Frequency freq)
+            throws NetconfException {
+        StringBuilder sb = new StringBuilder();
+        sb.append(
+                    "<components xmlns='http://openconfig.net/yang/platform'>"
+                  + "<component>"
+                  + "<config>"
+                  + "<name>" + optChannel + "</name>"
+                  + "</config>"
+                  + "<optical-channel xmlns='http://openconfig.net/yang/terminal-device'>"
+                  + "<config>"
+                  + "<frequency>" + (long) freq.asMHz() + "</frequency>"
+                  + "</config>"
+                  + "</optical-channel>"
+                  + "</component>"
+                  + "</components>");
+        log.info("Optical Channel Frequency {}", sb.toString());
+        boolean ok = session.editConfig(DatastoreId.RUNNING, null, sb.toString());
+        if (!ok) {
+            throw new NetconfException("error writing channel frequency");
+        }
+        ok = session.commit();
+        if (!ok) {
+            throw new NetconfException("error committing channel frequency");
+        }
+    }
+
+    /**
+     * Get the OpenConfig component name for the OpticalChannel component.
+     *
+     * @param portNumber ONOS port number of the Line port ().
+     * @return the channel component name or null
+     */
+    private String getOpticalChannel(PortNumber portNumber) {
+        Port clientPort = handler().get(DeviceService.class).getPort(did(), portNumber);
+        return clientPort.annotations().value(OC_NAME);
+    }
+
+    /**
+     * Apply the flowrule.
+     * <p>
+     * Note: only bidirectional are supported as of now,
+     * given OpenConfig note (below). In consequence, only the
+     * TX rules are actually mapped to netconf ops.
+     * <p>
+     * https://github.com/openconfig/public/blob/master/release/models
+     * /optical-transport/openconfig-terminal-device.yang
+     * <p>
+     * Directionality:
+     * To maintain simplicity in the model, the configuration is
+     * described from client-to-line direction.  The assumption is that
+     * equivalent reverse configuration is implicit, resulting in
+     * the same line-to-client configuration.
+     *
+     * @param session The Netconf session.
+     * @param r       Flow Rules to be applied.
+     * @return the optical channel + the frequency or just channel as identifier fo the config installed on the device
+     * @throws NetconfException if exchange goes wrong
+     */
+    protected String applyFlowRule(NetconfSession session, FlowRule r) throws NetconfException {
+        FlowRuleParser frp = new FlowRuleParser(r);
+        if (!frp.isReceiver()) {
+            String optChannel = getOpticalChannel(frp.getPortNumber());
+            setOpticalChannelFrequency(session, optChannel,
+                    frp.getCentralFrequency());
+            return optChannel + ":" + frp.getCentralFrequency().asGHz();
+        }
+        return String.valueOf(frp.getCentralFrequency().asGHz());
+    }
+
+
+    protected String removeFlowRule(NetconfSession session, FlowRule r)
+            throws NetconfException {
+        FlowRuleParser frp = new FlowRuleParser(r);
+        if (!frp.isReceiver()) {
+            String optChannel = getOpticalChannel(frp.getPortNumber());
+            setOpticalChannelFrequency(session, optChannel, Frequency.ofMHz(0));
+            return optChannel + ":" + frp.getCentralFrequency().asGHz();
+        }
+        return String.valueOf(frp.getCentralFrequency().asGHz());
+    }
+}
diff --git a/drivers/odtn-driver/src/main/java/org/onosproject/drivers/odtn/AdvaTerminalDeviceDiscovery.java b/drivers/odtn-driver/src/main/java/org/onosproject/drivers/odtn/AdvaTerminalDeviceDiscovery.java
new file mode 100644
index 0000000..a61efe2
--- /dev/null
+++ b/drivers/odtn-driver/src/main/java/org/onosproject/drivers/odtn/AdvaTerminalDeviceDiscovery.java
@@ -0,0 +1,319 @@
+/*
+ * Copyright 2018-present Open Networking Foundation
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ * This work was partially supported by EC H2020 project METRO-HAUL (761727).
+ */
+
+package org.onosproject.drivers.odtn;
+
+import com.google.common.collect.ImmutableList;
+import org.apache.commons.configuration.HierarchicalConfiguration;
+import org.apache.commons.configuration.XMLConfiguration;
+import org.apache.commons.configuration.tree.xpath.XPathExpressionEngine;
+import org.onlab.packet.ChassisId;
+import org.onosproject.drivers.utilities.XmlConfigParser;
+import org.onosproject.net.ChannelSpacing;
+import org.onosproject.net.DefaultAnnotations;
+import org.onosproject.net.Device;
+import org.onosproject.net.DeviceId;
+import org.onosproject.net.OchSignal;
+import org.onosproject.net.OduSignalType;
+import org.onosproject.net.Port.Type;
+import org.onosproject.net.PortNumber;
+import org.onosproject.net.device.DefaultDeviceDescription;
+import org.onosproject.net.device.DefaultPortDescription;
+import org.onosproject.net.device.DefaultPortDescription.Builder;
+import org.onosproject.net.device.DeviceDescription;
+import org.onosproject.net.device.DeviceDescriptionDiscovery;
+import org.onosproject.net.device.PortDescription;
+import org.onosproject.net.driver.AbstractHandlerBehaviour;
+import org.onosproject.net.optical.device.OchPortHelper;
+import org.onosproject.netconf.NetconfController;
+import org.onosproject.netconf.NetconfDevice;
+import org.onosproject.netconf.NetconfSession;
+import org.onosproject.odtn.behaviour.OdtnDeviceDescriptionDiscovery;
+import org.slf4j.Logger;
+
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+import java.util.Objects;
+import java.util.concurrent.CompletableFuture;
+import java.util.regex.Matcher;
+import java.util.regex.Pattern;
+import java.util.stream.Collectors;
+
+import static org.slf4j.LoggerFactory.getLogger;
+
+
+/**
+ * Driver Implementation of the DeviceDescrption discovery for OpenConfig
+ * terminal devices.
+ *
+ */
+public class AdvaTerminalDeviceDiscovery
+    extends AbstractHandlerBehaviour
+    implements OdtnDeviceDescriptionDiscovery, DeviceDescriptionDiscovery {
+
+    private static final String RPC_TAG_NETCONF_BASE =
+        "<rpc xmlns=\"urn:ietf:params:xml:ns:netconf:base:1.0\">";
+
+    private static final String RPC_CLOSE_TAG = "</rpc>";
+
+    private static final String OC_PLATFORM_TYPES_TRANSCEIVER =
+        "oc-platform-types:TRANSCEIVER";
+
+    private static final String OC_PLATFORM_TYPES_PORT =
+        "oc-platform-types:PORT";
+
+    private static final String OC_TRANSPORT_TYPES_OPTICAL_CHANNEL =
+        "oc-opt-types:OPTICAL_CHANNEL";
+
+    private static final Logger log = getLogger(AdvaTerminalDeviceDiscovery.class);
+
+
+    /**
+     * Returns the NetconfSession with the device for which the method was called.
+     *
+     * @param deviceId device indetifier
+     *
+     * @return The netconf session or null
+     */
+    private NetconfSession getNetconfSession(DeviceId deviceId) {
+        NetconfController controller = handler().get(NetconfController.class);
+        NetconfDevice ncdev = controller.getDevicesMap().get(deviceId);
+        if (ncdev == null) {
+            log.trace("No netconf device, returning null session");
+            return null;
+        }
+        return ncdev.getSession();
+    }
+
+
+    /**
+     * Get the deviceId for which the methods apply.
+     *
+     * @return The deviceId as contained in the handler data
+     */
+    private DeviceId did() {
+        return handler().data().deviceId();
+    }
+
+
+    /**
+     * Construct a String with a Netconf filtered get RPC Message.
+     *
+     * @param filter A valid XML tree with the filter to apply in the get
+     * @return a String containing the RPC XML Document
+     */
+    private String filteredGetBuilder(String filter) {
+        StringBuilder rpc = new StringBuilder(RPC_TAG_NETCONF_BASE);
+        rpc.append("<get>");
+        rpc.append("<filter type='subtree'>");
+        rpc.append(filter);
+        rpc.append("</filter>");
+        rpc.append("</get>");
+        rpc.append(RPC_CLOSE_TAG);
+        return rpc.toString();
+    }
+
+
+    /**
+     * Builds a request to get Device Components, config and operational data.
+     *
+     * @return A string with the Netconf RPC for a get with subtree rpcing based on
+     *    /components/
+     */
+    private String getTerminalDeviceBuilder() {
+        return filteredGetBuilder("<terminal-device xmlns='http://openconfig.net/yang/terminal-device'/>");
+    }
+
+
+    @Override
+    public DeviceDescription discoverDeviceDetails() {
+        return new DefaultDeviceDescription(handler().data().deviceId().uri(),
+                                            Device.Type.TERMINAL_DEVICE,
+                                            "ADVA",
+                                            "FSP3000C",
+                                            "3.1",
+                                            "",
+                                            new ChassisId("1"));
+    }
+
+
+
+    /**
+     * Returns a list of PortDescriptions for the device.
+     *
+     * @return a list of descriptions.
+     *
+     * The RPC reply follows the following pattern:
+     * //CHECKSTYLE:OFF
+     * <pre>{@code
+     * <?xml version="1.0" encoding="UTF-8"?>
+     * <rpc-reply xmlns="urn:ietf:params:xml:ns:netconf:base:1.0" message-id="7">
+     * <data>
+     *   <components xmlns="http://openconfig.net/yang/platform">
+     *     <component>....
+     *     </component>
+     *     <component>....
+     *     </component>
+     *   </components>
+     * </data>
+     * </rpc-reply>
+     * }</pre>
+     * //CHECKSTYLE:ON
+     */
+    @Override
+    public List<PortDescription> discoverPortDetails() {
+        try {
+            NetconfSession session = getNetconfSession(did());
+            if (session == null) {
+                log.error("discoverPortDetails called with null session for {}", did());
+                return ImmutableList.of();
+            }
+
+            CompletableFuture<String> fut = session.rpc(getTerminalDeviceBuilder());
+            String rpcReply = fut.get();
+
+            XMLConfiguration xconf = (XMLConfiguration) XmlConfigParser.loadXmlString(rpcReply);
+            xconf.setExpressionEngine(new XPathExpressionEngine());
+
+            HierarchicalConfiguration logicalChannels = xconf.configurationAt("data/terminal-device/logical-channels");
+            return parseLogicalChannels(logicalChannels);
+        } catch (Exception e) {
+            log.error("Exception discoverPortDetails() {}", did(), e);
+            return ImmutableList.of();
+        }
+    }
+
+
+
+
+    /**
+     * Parses transceiver information from OpenConfig XML configuration.
+     *
+     * @param terminalDevice the XML document with components root.
+     * @return List of ports
+     *
+     * //CHECKSTYLE:OFF
+     * <pre>{@code
+     *   <components xmlns="http://openconfig.net/yang/platform">
+     *     <component>....
+     *     </component>
+     *     <component>....
+     *     </component>
+     *   </components>
+     * }</pre>
+     * //CHECKSTYLE:ON
+     */
+    protected List<PortDescription> parseLogicalChannels(HierarchicalConfiguration terminalDevice) {
+        return terminalDevice.configurationsAt("channel")
+            .stream()
+            .filter(channel -> !channel.getString("index", "unknown").equals("unknown"))
+            .map(channel -> {
+                try {
+                    // Pass the root document for cross-reference
+                    return parseLogicalChannel(channel);
+                } catch (Exception e) {
+                    return null;
+                }
+                })
+            .filter(Objects::nonNull)
+            .collect(Collectors.toList());
+    }
+
+
+     /**
+      * Parses a component XML doc into a PortDescription.
+      *
+      * @param channel subtree to parse. It must be a component ot type PORT.
+      *  case we need to check transceivers or optical channels.
+      *
+      * @return PortDescription or null if component does not have onos-index
+      */
+     private PortDescription parseLogicalChannel(
+             HierarchicalConfiguration channel) {
+
+         HierarchicalConfiguration config = channel.configurationAt("config");
+         String logicalChannelIndex = config.getString("index");
+         String description = config.getString("description");
+         String rateClass = config.getString("rate-class");
+         log.info("Parsing Component {} type {} speed {}", logicalChannelIndex, description, rateClass);
+
+         Map<String, String> annotations = new HashMap<>();
+         annotations.put(OdtnDeviceDescriptionDiscovery.OC_LOGICAL_CHANNEL, logicalChannelIndex);
+
+         // Store all properties as port properties
+
+         Pattern clientPattern = Pattern.compile("(\\d*)/(\\d*)/c(\\d)"); // e.g. xe1/1
+         Pattern linePattern = Pattern.compile("(\\d*)/(\\d*)/n(\\d)");
+         Matcher clientMatch = clientPattern.matcher(description);
+         Matcher lineMatch = linePattern.matcher(description);
+
+         Pattern portSpeedPattern = Pattern.compile("TRIB_RATE_([0-9.]*)G");
+         Matcher portSpeedMatch = portSpeedPattern.matcher(rateClass);
+
+         Builder builder = DefaultPortDescription.builder();
+
+         if (portSpeedMatch.find()) {
+             Long speed = Long.parseLong(portSpeedMatch.group(1));
+             builder.portSpeed(speed * 1000);
+         }
+
+         if (clientMatch.find()) {
+             Long num = Long.parseLong(clientMatch.group(1));
+             Long portNum = 100 + num;
+             String connectionId = "connection:" + num.toString();
+
+             annotations.put(OdtnDeviceDescriptionDiscovery.OC_NAME, description);
+             annotations.putIfAbsent(PORT_TYPE, OdtnPortType.CLIENT.value());
+             annotations.putIfAbsent(ONOS_PORT_INDEX, portNum.toString());
+             annotations.putIfAbsent(CONNECTION_ID, connectionId);
+
+             builder.withPortNumber(PortNumber.portNumber(portNum));
+             builder.type(Type.PACKET);
+
+             builder.annotations(DefaultAnnotations.builder().putAll(annotations).build());
+             return builder.build();
+
+         } else if (lineMatch.find()) {
+             Long num = (Long.parseLong(lineMatch.group(1)) - 1) * 2 + Long.parseLong(lineMatch.group(2));
+             Long portNum = 200 + num;
+             String connectionId = "connection:" + num.toString();
+
+             description = description.substring(0, description.length() - 6);
+
+             annotations.putIfAbsent(PORT_TYPE, OdtnPortType.LINE.value());
+             annotations.putIfAbsent(ONOS_PORT_INDEX, portNum.toString());
+             annotations.putIfAbsent(CONNECTION_ID, connectionId);
+             annotations.put(OdtnDeviceDescriptionDiscovery.OC_NAME, "optch " + description);
+
+             OchSignal signalId = OchSignal.newDwdmSlot(ChannelSpacing.CHL_50GHZ, 1);
+             return OchPortHelper.ochPortDescription(
+                     PortNumber.portNumber(portNum),
+                     true,
+                     OduSignalType.ODU4, // TODO Client signal to be discovered
+                     true,
+                     signalId,
+                     DefaultAnnotations.builder().putAll(annotations).build());
+
+         } else {
+             log.warn("Unexpected component description: {}", description);
+             return null;
+         }
+
+     }
+}
diff --git a/drivers/odtn-driver/src/main/java/org/onosproject/drivers/odtn/AdvaTerminalDevicePowerConfig.java b/drivers/odtn-driver/src/main/java/org/onosproject/drivers/odtn/AdvaTerminalDevicePowerConfig.java
new file mode 100644
index 0000000..e76df4e
--- /dev/null
+++ b/drivers/odtn-driver/src/main/java/org/onosproject/drivers/odtn/AdvaTerminalDevicePowerConfig.java
@@ -0,0 +1,465 @@
+/*
+ * Copyright 2018-present Open Networking Foundation
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ * This work was partially supported by EC H2020 project METRO-HAUL (761727).
+ */
+
+package org.onosproject.drivers.odtn;
+
+import com.google.common.collect.Range;
+import org.apache.commons.configuration.ConfigurationException;
+import org.apache.commons.configuration.HierarchicalConfiguration;
+import org.apache.commons.configuration.XMLConfiguration;
+import org.apache.commons.configuration.tree.xpath.XPathExpressionEngine;
+import org.onlab.osgi.DefaultServiceDirectory;
+import org.onosproject.drivers.utilities.XmlConfigParser;
+import org.onosproject.net.DeviceId;
+import org.onosproject.net.PortNumber;
+import org.onosproject.net.behaviour.PowerConfig;
+import org.onosproject.net.device.DeviceService;
+import org.onosproject.net.driver.AbstractHandlerBehaviour;
+import org.onosproject.netconf.DatastoreId;
+import org.onosproject.netconf.NetconfController;
+import org.onosproject.netconf.NetconfDevice;
+import org.onosproject.netconf.NetconfException;
+import org.onosproject.netconf.NetconfSession;
+import org.slf4j.Logger;
+
+import java.io.StringWriter;
+import java.util.ArrayList;
+import java.util.List;
+import java.util.Optional;
+import java.util.concurrent.CompletableFuture;
+import java.util.concurrent.ExecutionException;
+
+import static com.google.common.base.Preconditions.checkNotNull;
+import static org.slf4j.LoggerFactory.getLogger;
+
+/**
+ * Driver Implementation of the PowerConfig for OpenConfig terminal devices.
+ */
+public class AdvaTerminalDevicePowerConfig<T>
+        extends AbstractHandlerBehaviour implements PowerConfig<T> {
+
+    private static final String RPC_TAG_NETCONF_BASE =
+            "<rpc xmlns=\"urn:ietf:params:xml:ns:netconf:base:1.0\">";
+
+    private static final String RPC_CLOSE_TAG = "</rpc>";
+
+    private static final Logger log = getLogger(AdvaTerminalDevicePowerConfig.class);
+
+    private ComponentType state = ComponentType.DIRECTION;
+
+    /**
+     * Returns the NetconfSession with the device for which the method was called.
+     *
+     * @param deviceId device indetifier
+     * @return The netconf session or null
+     */
+    private NetconfSession getNetconfSession(DeviceId deviceId) {
+        NetconfController controller = handler().get(NetconfController.class);
+        NetconfDevice ncdev = controller.getDevicesMap().get(deviceId);
+        if (ncdev == null) {
+            log.trace("No netconf device, returning null session");
+            return null;
+        }
+        return ncdev.getSession();
+    }
+
+    /**
+     * Get the deviceId for which the methods apply.
+     *
+     * @return The deviceId as contained in the handler data
+     */
+    private DeviceId did() {
+        return handler().data().deviceId();
+    }
+
+    /**
+     * Execute RPC request.
+     *
+     * @param session Netconf session
+     * @param message Netconf message in XML format
+     * @return XMLConfiguration object
+     */
+
+    private XMLConfiguration executeRpc(NetconfSession session, String message) {
+        try {
+            if (log.isDebugEnabled()) {
+                try {
+                    StringWriter stringWriter = new StringWriter();
+                    XMLConfiguration xconf = (XMLConfiguration) XmlConfigParser.loadXmlString(message);
+                    xconf.setExpressionEngine(new XPathExpressionEngine());
+                    xconf.save(stringWriter);
+                    log.debug("Request {}", stringWriter.toString());
+                } catch (ConfigurationException e) {
+                    log.error("XML Config Exception ", e);
+                }
+            }
+            CompletableFuture<String> fut = session.rpc(message);
+            String rpcReply = fut.get();
+            XMLConfiguration xconf = (XMLConfiguration) XmlConfigParser.loadXmlString(rpcReply);
+            xconf.setExpressionEngine(new XPathExpressionEngine());
+            if (log.isDebugEnabled()) {
+                try {
+                    StringWriter stringWriter = new StringWriter();
+                    xconf.save(stringWriter);
+                    log.debug("Response {}", stringWriter.toString());
+                } catch (ConfigurationException e) {
+                    log.error("XML Config Exception ", e);
+                }
+            }
+            return xconf;
+        } catch (NetconfException ne) {
+            log.error("Exception on Netconf protocol: {}.", ne);
+        } catch (InterruptedException ie) {
+            log.error("Interrupted Exception: {}.", ie);
+        } catch (ExecutionException ee) {
+            log.error("Concurrent Exception while executing Netconf operation: {}.", ee);
+        }
+        return null;
+    }
+
+    /**
+     * Get the target-output-power value on specific optical-channel.
+     *
+     * @param port      the port
+     * @param component the port component. It should be 'oc-name' in the Annotations of Port.
+     *                  'oc-name' could be mapped to '/component/name' in openconfig yang.
+     * @return target power value
+     */
+    @Override
+    public Optional<Double> getTargetPower(PortNumber port, T component) {
+        checkState(component);
+        return state.getTargetPower(port, component);
+    }
+
+    @Override
+    public void setTargetPower(PortNumber port, T component, double power) {
+        checkState(component);
+        state.setTargetPower(port, component, power);
+    }
+
+    @Override
+    public Optional<Double> currentPower(PortNumber port, T component) {
+        checkState(component);
+        return state.currentPower(port, component);
+    }
+
+  @Override
+  public Optional<Double> currentInputPower(PortNumber port, T component) {
+        checkState(component);
+        return state.currentInputPower(port, component);
+    }
+
+    @Override
+    public Optional<Range<Double>> getTargetPowerRange(PortNumber port, T component) {
+        checkState(component);
+        return state.getTargetPowerRange(port, component);
+    }
+
+    @Override
+   public Optional<Range<Double>> getInputPowerRange(PortNumber port, T component) {
+        checkState(component);
+        return state.getInputPowerRange(port, component);
+    }
+
+    @Override
+    public List<PortNumber> getPorts(T component) {
+        checkState(component);
+        return state.getPorts(component);
+    }
+
+
+    /**
+     * Set the ComponentType to invoke proper methods for different template T.
+     *
+     * @param component the component.
+     */
+    void checkState(Object component) {
+        String clsName = component.getClass().getName();
+        switch (clsName) {
+            case "org.onosproject.net.Direction":
+                state = ComponentType.DIRECTION;
+                break;
+            case "org.onosproject.net.OchSignal":
+                state = ComponentType.OCHSIGNAL;
+                break;
+            default:
+                log.error("Cannot parse the component type {}.", clsName);
+                log.info("The component content is {}.", component.toString());
+        }
+        state.adva = this;
+    }
+
+    /**
+     * Component type.
+     */
+    enum ComponentType {
+
+        /**
+         * Direction.
+         */
+        DIRECTION() {
+            @Override
+            public Optional<Double> getTargetPower(PortNumber port, Object component) {
+                return super.getTargetPower(port, component);
+            }
+
+            @Override
+            public void setTargetPower(PortNumber port, Object component, double power) {
+                super.setTargetPower(port, component, power);
+            }
+        },
+
+        /**
+         * OchSignal.
+         */
+        OCHSIGNAL() {
+            @Override
+            public Optional<Double> getTargetPower(PortNumber port, Object component) {
+                return super.getTargetPower(port, component);
+            }
+
+            @Override
+            public void setTargetPower(PortNumber port, Object component, double power) {
+                super.setTargetPower(port, component, power);
+            }
+        };
+
+
+        AdvaTerminalDevicePowerConfig adva;
+
+        /**
+         * mirror method in the internal class.
+         *
+         * @param port      port
+         * @param component component
+         * @return target power
+         */
+        Optional<Double> getTargetPower(PortNumber port, Object component) {
+            NetconfSession session = adva.getNetconfSession(adva.did());
+            checkNotNull(session);
+            String filter = parsePort(adva, port, null, null);
+            StringBuilder rpcReq = new StringBuilder();
+            rpcReq.append(RPC_TAG_NETCONF_BASE)
+                    .append("<get-config>")
+                    .append("<source>")
+                    .append("<" + DatastoreId.RUNNING + "/>")
+                    .append("</source>")
+                    .append("<filter type='subtree'>")
+                    .append(filter)
+                    .append("</filter>")
+                    .append("</get-config>")
+                    .append(RPC_CLOSE_TAG);
+            XMLConfiguration xconf = adva.executeRpc(session, rpcReq.toString());
+            if (xconf == null) {
+                log.error("Error in executingRpc");
+                return Optional.empty();
+            }
+            try {
+                HierarchicalConfiguration config =
+                        xconf.configurationAt("data/components/component/optical-channel/config");
+                if (config == null || config.getString("target-output-power") == null) {
+                    return Optional.empty();
+                }
+                double power = Float.valueOf(config.getString("target-output-power")).doubleValue();
+                return Optional.of(power);
+            } catch (IllegalArgumentException e) {
+                return Optional.empty();
+            }
+        }
+
+        /**
+         * mirror method in the internal class.
+         *
+         * @param port      port
+         * @param component component
+         * @param power     target value
+         */
+        void setTargetPower(PortNumber port, Object component, double power) {
+            NetconfSession session = adva.getNetconfSession(adva.did());
+            checkNotNull(session);
+            String editConfig = parsePort(adva, port, null, power);
+            StringBuilder rpcReq = new StringBuilder();
+            rpcReq.append(RPC_TAG_NETCONF_BASE)
+                    .append("<edit-config>")
+                    .append("<target><" + DatastoreId.CANDIDATE + "/></target>")
+                    .append("<config>")
+                    .append(editConfig)
+                    .append("</config>")
+                    .append("</edit-config>")
+                    .append(RPC_CLOSE_TAG);
+            log.info("Setting power {}", rpcReq.toString());
+            XMLConfiguration xconf = adva.executeRpc(session, rpcReq.toString());
+            // The successful reply should be "<rpc-reply ...><ok /></rpc-reply>"
+            if (!xconf.getRoot().getChild(0).getName().equals("ok")) {
+                log.error("The <edit-config> operation to set target-output-power of Port({}:{}) is failed.",
+                        port.toString(), component.toString());
+            }
+            try {
+                session.commit();
+            } catch (NetconfException e) {
+                log.error("error committing channel power", e);
+            }
+        }
+
+        /**
+         * mirror method in the internal class.
+         *
+         * @param port      port
+         * @param component the component.
+         * @return current output power.
+         */
+        Optional<Double> currentPower(PortNumber port, Object component) {
+            XMLConfiguration xconf = getOpticalChannelState(
+                    adva, port, "<output-power><instant/></output-power>");
+            try {
+               HierarchicalConfiguration config =
+                        xconf.configurationAt("data/components/component/optical-channel/state/output-power");
+                if (config == null || config.getString("instant") == null) {
+                    return Optional.empty();
+               }
+                double currentPower = Float.valueOf(config.getString("instant")).doubleValue();
+                return Optional.of(currentPower);
+            } catch (IllegalArgumentException e) {
+                return Optional.empty();
+            }
+        }
+
+        /**
+         * mirror method in the internal class.
+         *
+         * @param port      port
+         * @param component the component
+         * @return current input power
+         */
+        Optional<Double> currentInputPower(PortNumber port, Object component) {
+            XMLConfiguration xconf = getOpticalChannelState(
+                    adva, port, "<input-power><instant/></input-power>");
+            try {
+                HierarchicalConfiguration config =
+                        xconf.configurationAt("data/components/component/optical-channel/state/input-power");
+                if (config == null || config.getString("instant") == null) {
+                    return Optional.empty();
+               }
+               double currentPower = Float.valueOf(config.getString("instant")).doubleValue();
+               return Optional.of(currentPower);
+            } catch (IllegalArgumentException e) {
+                return Optional.empty();
+            }
+         }
+
+        Optional<Range<Double>> getTargetPowerRange(PortNumber port, Object component) {
+            double targetMin = -30;
+            double targetMax = 1;
+            return Optional.of(Range.open(targetMin, targetMax));
+        }
+
+        Optional<Range<Double>> getInputPowerRange(PortNumber port, Object component) {
+            double targetMin = -30;
+            double targetMax = 1;
+            return Optional.of(Range.open(targetMin, targetMax));
+        }
+
+        List<PortNumber> getPorts(Object component) {
+            // FIXME
+            log.warn("Not Implemented Yet!");
+            return new ArrayList<PortNumber>();
+        }
+
+        /**
+         * Get filtered content under <optical-channel><state>.
+         *
+         * @param pc         power config instance
+         * @param port       the port number
+         * @param underState the filter condition
+         * @return RPC reply
+         */
+        private static XMLConfiguration getOpticalChannelState(AdvaTerminalDevicePowerConfig pc,
+                                                               PortNumber port, String underState) {
+            NetconfSession session = pc.getNetconfSession(pc.did());
+            checkNotNull(session);
+            String name = ocName(pc, port);
+            StringBuilder rpcReq = new StringBuilder(RPC_TAG_NETCONF_BASE);
+            rpcReq.append("<get><filter><components xmlns=\"http://openconfig.net/yang/platform\"><component>")
+                    .append("<name>").append(name).append("</name>")
+                    .append("<optical-channel xmlns=\"http://openconfig.net/yang/terminal-device\">")
+                    .append("<state>")
+                    .append(underState)
+                    .append("</state></optical-channel></component></components></filter></get>")
+                    .append(RPC_CLOSE_TAG);
+            XMLConfiguration xconf = pc.executeRpc(session, rpcReq.toString());
+            return xconf;
+        }
+
+
+        /**
+         * Extract component name from portNumber's annotations.
+         *
+         * @param pc         power config instance
+         * @param portNumber the port number
+         * @return the component name
+         */
+        private static String ocName(AdvaTerminalDevicePowerConfig pc, PortNumber portNumber) {
+            DeviceService deviceService = DefaultServiceDirectory.getService(DeviceService.class);
+            DeviceId deviceId = pc.handler().data().deviceId();
+            return deviceService.getPort(deviceId, portNumber).annotations().value("oc-name");
+        }
+
+
+        /**
+         * Parse filtering string from port and component.
+         *
+         * @param portNumber Port Number
+         * @param component  port component (optical-channel)
+         * @param power      power value set.
+         * @return filtering string in xml format
+         */
+        private static String parsePort(AdvaTerminalDevicePowerConfig pc, PortNumber portNumber,
+                                        Object component, Double power) {
+            if (component == null) {
+                String name = ocName(pc, portNumber);
+                StringBuilder sb = new StringBuilder("<components xmlns=\"http://openconfig.net/yang/platform\">");
+                sb.append("<component>");
+                if (power != null) {
+                    // This is an edit-config operation.
+                    sb.append("<config>")
+                            .append("<name>")
+                            .append(name)
+                            .append("</name>")
+                            .append("</config>")
+                            .append("<optical-channel xmlns=\"http://openconfig.net/yang/terminal-device\">")
+                            .append("<config>")
+                            .append("<target-output-power>")
+                            .append(power)
+                            .append("</target-output-power>")
+                            .append("</config>")
+                            .append("</optical-channel>");
+                } else {
+                        sb.append("<name>")
+                        .append(name)
+                        .append("</name>");
+                }
+
+                sb.append("</component>").append("</components>");
+                return sb.toString();
+            } else {
+                log.error("Cannot process the component {}.", component.getClass());
+                return null;
+            }
+        }
+    }
+}
diff --git a/drivers/odtn-driver/src/main/resources/odtn-drivers.xml b/drivers/odtn-driver/src/main/resources/odtn-drivers.xml
index 986dd26..174b208 100644
--- a/drivers/odtn-driver/src/main/resources/odtn-drivers.xml
+++ b/drivers/odtn-driver/src/main/resources/odtn-drivers.xml
@@ -178,5 +178,19 @@
             http://openconfig.net/yang/types/yang?module=openconfig-yang-types&amp;revision=2017-07-30|
             urn:ietf:params:xml:ns:yang:ietf-yang-types?module=ietf-yang-types&amp;revision=2013-07-15</property>
     </driver>
+    <driver name="adva" manufacturer="ADVA" hwVersion="Tx" swVersion="3.1">
+    <behaviour api="org.onosproject.net.device.DeviceDescriptionDiscovery"
+               impl="org.onosproject.drivers.odtn.AdvaTerminalDeviceDiscovery"/>
+    <behaviour api ="org.onosproject.net.optical.OpticalDevice"
+               impl="org.onosproject.net.optical.DefaultOpticalDevice"/>
+    <behaviour api ="org.onosproject.net.behaviour.LambdaQuery"
+               impl="org.onosproject.drivers.odtn.openconfig.TerminalDeviceLambdaQuery"/>
+    <behaviour api="org.onosproject.net.flow.FlowRuleProgrammable"
+	       impl="org.onosproject.drivers.odtn.AdvaFlowRuleProgrammable"/>
+    <behaviour api="org.onosproject.net.behaviour.PowerConfig"
+	       impl="org.onosproject.drivers.odtn.AdvaTerminalDevicePowerConfig"/>
+    <behaviour api="org.onosproject.net.behaviour.ModulationConfig"
+               impl="org.onosproject.drivers.odtn.CassiniModulationOpenConfig"/>
+    </driver>
 </drivers>
 
