2 * Copyright © 2020 AT&T and others. All rights reserved.
4 * This program and the accompanying materials are made available under the
5 * terms of the Eclipse Public License v1.0 which accompanies this distribution,
6 * and is available at http://www.eclipse.org/legal/epl-v10.html
9 package org.opendaylight.transportpce.olm.power;
11 import com.google.common.util.concurrent.FluentFuture;
12 import java.math.BigDecimal;
13 import java.util.HashMap;
15 import java.util.Optional;
16 import java.util.concurrent.ExecutionException;
17 import java.util.concurrent.Future;
18 import org.eclipse.jdt.annotation.NonNull;
19 import org.opendaylight.mdsal.common.api.CommitInfo;
20 import org.opendaylight.mdsal.common.api.LogicalDatastoreType;
21 import org.opendaylight.transportpce.common.Timeouts;
22 import org.opendaylight.transportpce.common.crossconnect.CrossConnect;
23 import org.opendaylight.transportpce.common.device.DeviceTransaction;
24 import org.opendaylight.transportpce.common.device.DeviceTransactionManager;
25 import org.opendaylight.yang.gen.v1.http.org.openroadm.common.link.types.rev191129.OpticalControlMode;
26 import org.opendaylight.yang.gen.v1.http.org.openroadm.common.link.types.rev191129.PowerDBm;
27 import org.opendaylight.yang.gen.v1.http.org.openroadm.device.rev200529.circuit.pack.Ports;
28 import org.opendaylight.yang.gen.v1.http.org.openroadm.device.rev200529.circuit.pack.PortsKey;
29 import org.opendaylight.yang.gen.v1.http.org.openroadm.device.rev200529.circuit.packs.CircuitPacks;
30 import org.opendaylight.yang.gen.v1.http.org.openroadm.device.rev200529.circuit.packs.CircuitPacksKey;
31 import org.opendaylight.yang.gen.v1.http.org.openroadm.device.rev200529.interfaces.grp.Interface;
32 import org.opendaylight.yang.gen.v1.http.org.openroadm.device.rev200529.interfaces.grp.InterfaceBuilder;
33 import org.opendaylight.yang.gen.v1.http.org.openroadm.device.rev200529.interfaces.grp.InterfaceKey;
34 import org.opendaylight.yang.gen.v1.http.org.openroadm.device.rev200529.org.openroadm.device.container.OrgOpenroadmDevice;
35 import org.opendaylight.yang.gen.v1.http.org.openroadm.device.rev200529.org.openroadm.device.container.org.openroadm.device.RoadmConnections;
36 import org.opendaylight.yang.gen.v1.http.org.openroadm.device.rev200529.org.openroadm.device.container.org.openroadm.device.RoadmConnectionsBuilder;
37 import org.opendaylight.yang.gen.v1.http.org.openroadm.device.rev200529.org.openroadm.device.container.org.openroadm.device.RoadmConnectionsKey;
38 import org.opendaylight.yang.gen.v1.http.org.openroadm.optical.channel.tributary.signal.interfaces.rev200529.Interface1;
39 import org.opendaylight.yang.gen.v1.http.org.openroadm.optical.channel.tributary.signal.interfaces.rev200529.Interface1Builder;
40 import org.opendaylight.yang.gen.v1.http.org.openroadm.optical.channel.tributary.signal.interfaces.rev200529.otsi.container.OtsiBuilder;
41 import org.opendaylight.yangtools.yang.binding.InstanceIdentifier;
42 import org.slf4j.Logger;
43 import org.slf4j.LoggerFactory;
47 public final class PowerMgmtVersion710 {
48 private static final Logger LOG = LoggerFactory.getLogger(PowerMgmtVersion710.class);
50 private PowerMgmtVersion710() {
54 * This method provides Transponder transmit power range.
56 * @param circuitPackName
57 * Transponder circuitPack name
59 * Transponder port name
62 * @param deviceTransactionManager
63 * Device transaction manager to read device data
64 * @return HashMap holding Min and Max transmit power for given port
66 public static Map<String, Double> getXponderPowerRange(String circuitPackName, String portName, String deviceId,
67 DeviceTransactionManager deviceTransactionManager) {
68 InstanceIdentifier<Ports> portIID = InstanceIdentifier.create(OrgOpenroadmDevice.class)
69 .child(CircuitPacks.class, new CircuitPacksKey(circuitPackName))
70 .child(Ports.class, new PortsKey(portName));
71 LOG.debug("Fetching logical Connection Point value for port {} at circuit pack {}", portName, circuitPackName);
72 Optional<Ports> portObject =
73 deviceTransactionManager.getDataFromDevice(deviceId, LogicalDatastoreType.OPERATIONAL, portIID,
74 Timeouts.DEVICE_READ_TIMEOUT, Timeouts.DEVICE_READ_TIMEOUT_UNIT);
75 if (!portObject.isPresent()) {
76 return new HashMap<>();
78 Ports port = portObject.get();
79 if (port.getTransponderPort() == null || port.getTransponderPort().getPortPowerCapabilityMaxTx() == null) {
80 LOG.warn("Logical Connection Point value missing for {} {}", circuitPackName, port.getPortName());
81 return new HashMap<>();
83 Map<String, Double> powerRangeMap = new HashMap<>();
84 powerRangeMap.put("MaxTx", port.getTransponderPort().getPortPowerCapabilityMaxTx().getValue().doubleValue());
85 powerRangeMap.put("MinTx", port.getTransponderPort().getPortPowerCapabilityMinTx().getValue().doubleValue());
90 * This method provides Transponder transmit power range.
93 * Unique identifier for the mounted netconf- node
95 * SRG Id connected to transponder
96 * @param deviceTransactionManager
97 * Device transaction manager to read device data
98 * @param circuitPackName
99 * SRG circuitpack name
102 * @return HashMap holding Min and Max transmit power for given port
104 public static Map<String, Double> getSRGRxPowerRange(String nodeId, String srgId,
105 DeviceTransactionManager deviceTransactionManager,
106 String circuitPackName, String portName) {
107 LOG.debug("Coming inside SRG power range");
108 LOG.debug("Mapping object exists.");
109 InstanceIdentifier<Ports> portIID = InstanceIdentifier.create(OrgOpenroadmDevice.class)
110 .child(CircuitPacks.class, new CircuitPacksKey(circuitPackName))
111 .child(Ports.class, new PortsKey(portName));
112 LOG.debug("Fetching logical Connection Point value for port {} at circuit pack {}{}", portName,
113 circuitPackName, portIID);
114 Optional<Ports> portObject =
115 deviceTransactionManager.getDataFromDevice(nodeId, LogicalDatastoreType.OPERATIONAL, portIID,
116 Timeouts.DEVICE_READ_TIMEOUT, Timeouts.DEVICE_READ_TIMEOUT_UNIT);
117 if (!portObject.isPresent()) {
118 LOG.info("Port not found");
119 return new HashMap<>();
121 Ports port = portObject.get();
122 if (port.getRoadmPort() == null) {
123 LOG.warn("Roadm ports power value is missing for {} {}", circuitPackName, port.getPortName());
124 return new HashMap<>();
126 LOG.debug("Port found on the node ID");
127 Map<String, Double> powerRangeMap = new HashMap<>();
128 powerRangeMap.put("MinRx", port.getRoadmPort().getPortPowerCapabilityMinRx().getValue().doubleValue());
129 powerRangeMap.put("MaxRx", port.getRoadmPort().getPortPowerCapabilityMaxRx().getValue().doubleValue());
130 return powerRangeMap;
134 * This method retrieves transponder OCH interface and
138 * Unique identifier for the mounted netconf- node
139 * @param interfaceName
140 * OCH interface name carrying WL
142 * Calculated transmit power
143 * @param deviceTransactionManager
144 * Device Transaction Manager
145 * @param interfaceObj
148 * @return true/false based on status of operation
150 public static boolean setTransponderPower(String nodeId, String interfaceName, BigDecimal txPower,
151 DeviceTransactionManager deviceTransactionManager,
152 Interface interfaceObj) {
153 LOG.debug("Setting target-power for transponder nodeId: {} InterfaceName: {}",
154 nodeId, interfaceName);
155 InterfaceBuilder otsiInterfaceBuilder = new InterfaceBuilder(interfaceObj);
156 OtsiBuilder otsiBuilder = new OtsiBuilder(otsiInterfaceBuilder.augmentation(Interface1.class).getOtsi());
157 otsiBuilder.setTransmitPower(new PowerDBm(txPower));
158 otsiInterfaceBuilder.addAugmentation(new Interface1Builder().setOtsi(otsiBuilder.build()).build());
159 Future<Optional<DeviceTransaction>> deviceTxFuture = deviceTransactionManager.getDeviceTransaction(nodeId);
160 DeviceTransaction deviceTx;
162 Optional<DeviceTransaction> deviceTxOpt = deviceTxFuture.get();
163 if (deviceTxOpt.isPresent()) {
164 deviceTx = deviceTxOpt.get();
166 LOG.error("Transaction for device {} was not found during transponder power setup for Node:", nodeId);
169 } catch (InterruptedException | ExecutionException e) {
170 LOG.error("Unable to get transaction for device {} during transponder power setup!", nodeId, e);
173 InstanceIdentifier<Interface> interfacesIID = InstanceIdentifier.create(OrgOpenroadmDevice.class)
174 .child(Interface.class, new InterfaceKey(interfaceName));
175 deviceTx.merge(LogicalDatastoreType.CONFIGURATION, interfacesIID, otsiInterfaceBuilder.build());
176 FluentFuture<? extends @NonNull CommitInfo> commit =
177 deviceTx.commit(Timeouts.DEVICE_WRITE_TIMEOUT, Timeouts.DEVICE_WRITE_TIMEOUT_UNIT);
180 LOG.info("Transponder Power update is committed");
182 } catch (InterruptedException | ExecutionException e) {
183 LOG.error("Setting transponder power failed: ", e);
189 * This method does an edit-config on roadm connection subtree for a given
190 * connection number in order to set power level for use by the optical
196 * Optical control modelcan be off, power or gainLoss.
198 * Power value in DBm.
199 * @param connectionNumber
200 * Name of the cross connect.
201 * @param crossConnect
203 * @param deviceTransactionManager
204 * Device Transaction Manager.
206 * @return true/false based on status of operation.
208 public static boolean setPowerLevel(String deviceId, OpticalControlMode mode, BigDecimal powerValue,
209 String connectionNumber, CrossConnect crossConnect,
210 DeviceTransactionManager deviceTransactionManager) {
211 @SuppressWarnings("unchecked") Optional<RoadmConnections> rdmConnOpt =
212 (Optional<RoadmConnections>) crossConnect.getCrossConnect(deviceId, connectionNumber);
213 if (!rdmConnOpt.isPresent()) {
214 LOG.warn("Roadm-Connection is null in set power level ({})", connectionNumber);
217 RoadmConnectionsBuilder rdmConnBldr = new RoadmConnectionsBuilder(rdmConnOpt.get());
218 rdmConnBldr.setOpticalControlMode(mode);
219 if (powerValue != null) {
220 rdmConnBldr.setTargetOutputPower(new PowerDBm(powerValue));
222 RoadmConnections newRdmConn = rdmConnBldr.build();
223 Future<Optional<DeviceTransaction>> deviceTxFuture = deviceTransactionManager.getDeviceTransaction(deviceId);
224 DeviceTransaction deviceTx;
226 Optional<DeviceTransaction> deviceTxOpt = deviceTxFuture.get();
227 if (!deviceTxOpt.isPresent()) {
228 LOG.error("Transaction for device {} was not found!", deviceId);
231 deviceTx = deviceTxOpt.get();
232 } catch (InterruptedException | ExecutionException e) {
233 LOG.error("Unable to get transaction for device {}!", deviceId, e);
236 // post the cross connect on the device
237 InstanceIdentifier<RoadmConnections> roadmConnIID = InstanceIdentifier.create(OrgOpenroadmDevice.class)
238 .child(RoadmConnections.class, new RoadmConnectionsKey(connectionNumber));
239 deviceTx.put(LogicalDatastoreType.CONFIGURATION, roadmConnIID, newRdmConn);
240 FluentFuture<? extends @NonNull CommitInfo> commit =
241 deviceTx.commit(Timeouts.DEVICE_WRITE_TIMEOUT, Timeouts.DEVICE_WRITE_TIMEOUT_UNIT);
244 LOG.info("Roadm connection power level successfully set ");
246 } catch (InterruptedException | ExecutionException ex) {
247 LOG.warn("Failed to post {}", newRdmConn, ex);