2 * Copyright © 2017 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.renderer.provisiondevice;
11 import com.google.common.util.concurrent.CheckedFuture;
13 import java.util.HashSet;
14 import java.util.List;
16 import java.util.concurrent.Future;
18 import org.opendaylight.controller.md.sal.binding.api.DataBroker;
19 import org.opendaylight.controller.md.sal.binding.api.MountPointService;
20 import org.opendaylight.controller.md.sal.binding.api.ReadWriteTransaction;
21 import org.opendaylight.controller.md.sal.binding.api.WriteTransaction;
22 import org.opendaylight.controller.md.sal.common.api.data.LogicalDatastoreType;
23 import org.opendaylight.controller.md.sal.common.api.data.TransactionCommitFailedException;
24 import org.opendaylight.transportpce.renderer.mapping.PortMapping;
25 import org.opendaylight.yang.gen.v1.http.org.openroadm.common.types.rev161014.OpticalControlMode;
26 import org.opendaylight.yang.gen.v1.http.org.openroadm.device.rev170206.connection.DestinationBuilder;
27 import org.opendaylight.yang.gen.v1.http.org.openroadm.device.rev170206.connection.SourceBuilder;
28 import org.opendaylight.yang.gen.v1.http.org.openroadm.device.rev170206.interfaces.grp.Interface;
29 import org.opendaylight.yang.gen.v1.http.org.openroadm.device.rev170206.interfaces.grp.InterfaceKey;
30 import org.opendaylight.yang.gen.v1.http.org.openroadm.device.rev170206.org.openroadm.device.container.OrgOpenroadmDevice;
31 import org.opendaylight.yang.gen.v1.http.org.openroadm.device.rev170206.org.openroadm.device.container.org.openroadm.device.RoadmConnections;
32 import org.opendaylight.yang.gen.v1.http.org.openroadm.device.rev170206.org.openroadm.device.container.org.openroadm.device.RoadmConnectionsBuilder;
33 import org.opendaylight.yang.gen.v1.http.org.openroadm.device.rev170206.org.openroadm.device.container.org.openroadm.device.RoadmConnectionsKey;
34 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.renderer.rev170228.RendererService;
35 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.renderer.rev170228.ServicePathInput;
36 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.renderer.rev170228.ServicePathOutput;
37 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.renderer.rev170228.ServicePathOutputBuilder;
38 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.renderer.rev170228.service.path.input.Nodes;
39 import org.opendaylight.yangtools.yang.binding.InstanceIdentifier;
40 import org.opendaylight.yangtools.yang.common.RpcResult;
41 import org.opendaylight.yangtools.yang.common.RpcResultBuilder;
43 import org.slf4j.Logger;
44 import org.slf4j.LoggerFactory;
46 public class DeviceRenderer implements RendererService {
48 private final DataBroker db;
49 private final MountPointService mps;
50 private static final Logger LOG = LoggerFactory.getLogger(RendererService.class);
51 private final Set<String> currentMountedDevice;
52 private final Set<String> nodesProvisioned;
54 public DeviceRenderer(DataBroker db, MountPointService mps, Set<String> currentMountedDevice) {
57 this.currentMountedDevice = currentMountedDevice;
58 this.nodesProvisioned = new HashSet<>();
62 * This method is the implementation of the 'service-path' RESTCONF service,
63 * which is one of the external APIs into the renderer application. The
64 * service provides two functions:
68 * This operation results in provisioning the device for a given wavelength and a
69 * list of nodes with each node listing its termination points.
73 * This operation results in de-provisioning the device for a given wavelength and a
74 * list of nodes with each node listing its termination points.
77 * The signature for this method was generated by yang tools from the
80 * @param input Input parameter from the service-path yang model
82 * @return Result of the request
85 public Future<RpcResult<ServicePathOutput>> servicePath(ServicePathInput input) {
87 if (input.getOperation().getIntValue() == 1) {
88 LOG.info("Create operation request received");
89 return RpcResultBuilder.success(setupServicePath(input)).buildFuture();
90 } else if (input.getOperation().getIntValue() == 2) {
91 LOG.info("Delete operation request received");
92 return RpcResultBuilder.success(deleteServicePath(input)).buildFuture();
94 return RpcResultBuilder.success(new ServicePathOutputBuilder().setResult("Invalid operation")).buildFuture();
98 * This method set's wavelength path based on following steps:
102 * 1. Create Och interface on source termination point.
103 * 2. Create Och interface on destination termination point.
104 * 3. Create cross connect between source and destination
105 * tps created in step 1 and 2.
108 * Naming convention used for OCH interfaces name : tp-wavenumber
109 * Naming convention used for cross connect name : src-dest-wavenumber
111 * @param input Input parameter from the service-path yang model
113 * @return Result list of all nodes if request successful
114 * otherwise specific reason of failure.
116 public ServicePathOutputBuilder setupServicePath(ServicePathInput input) {
118 List<Nodes> nodes = input.getNodes();
119 ServicePathOutputBuilder setServBldr = new ServicePathOutputBuilder();
120 LOG.info(currentMountedDevice.toString());
121 for (Nodes n : nodes) {
122 LOG.info("Starting provisioning for node : " + n.getNodeId());
123 //if the node is currently mounted then proceed
124 if (currentMountedDevice.contains(n.getNodeId())) {
125 String srcTp = n.getSrcTp();
126 String destTp = n.getDestTp();
127 Long waveNumber = input.getWaveNumber();
128 String srcIf = new OpenRoadmInterfaces(db, mps, n.getNodeId(), srcTp).createOchInterface(waveNumber);
129 //if source interface creation was successful then proceed otherwise return.
131 LOG.warn("Unable to create OCH interface on " + n.getNodeId() + " at " + srcTp);
132 return setServBldr.setResult("Unable to create OCH interface on " + n.getNodeId() + " at " + srcTp);
134 //if destination interface creation was then proceed otherwise return.
135 String dstIf = new OpenRoadmInterfaces(db, mps, n.getNodeId(), destTp).createOchInterface(waveNumber);
137 LOG.warn("Unable to create OCH interface on " + n.getNodeId() + " at " + destTp);
138 return setServBldr.setResult("Unable to create OCH interface on " + n.getNodeId() + " at "
141 LOG.info("Creating cross connect between source :" + srcTp + " destination " + destTp + " for node " + n
143 //Build cross connect object
144 RoadmConnectionsBuilder rdmConnBldr = new RoadmConnectionsBuilder();
145 rdmConnBldr.setConnectionNumber(srcTp + "-" + destTp + "-" + waveNumber);
146 rdmConnBldr.setWavelengthNumber(waveNumber);
147 rdmConnBldr.setOpticalControlMode(OpticalControlMode.Off);
148 rdmConnBldr.setSource(new SourceBuilder().setSrcIf(srcIf).build());
149 rdmConnBldr.setDestination(new DestinationBuilder().setDstIf(dstIf).build());
150 InstanceIdentifier<RoadmConnections> rdmConnectionIID = InstanceIdentifier.create(
151 OrgOpenroadmDevice.class).child(RoadmConnections.class, new RoadmConnectionsKey(rdmConnBldr
152 .getConnectionNumber()));
153 DataBroker netconfNodeDataBroker = PortMapping.getDeviceDataBroker(n.getNodeId(), mps);
154 if (netconfNodeDataBroker != null) {
155 final WriteTransaction writeTransaction = netconfNodeDataBroker.newWriteOnlyTransaction();
156 //post the cross connect on the device
157 writeTransaction.put(LogicalDatastoreType.CONFIGURATION, rdmConnectionIID, rdmConnBldr.build());
158 final CheckedFuture<Void, TransactionCommitFailedException> submit = writeTransaction.submit();
161 nodesProvisioned.add(n.getNodeId());
162 LOG.info("Roadm-connection successfully created: " + srcTp + "-" + destTp);
164 } catch (TransactionCommitFailedException ex) {
165 LOG.warn("Failed to post {} ", rdmConnBldr.build(), ex);
166 return setServBldr.setResult("Unable to post Roadm-connection for node " + n.getNodeId());
169 LOG.error("Unable to get device broker for node " + n.getNodeId());
170 return setServBldr.setResult("Unable to get device broker for node " + n.getNodeId());
173 LOG.warn(n.getNodeId() + " is not mounted on the controller");
174 return setServBldr.setResult(n.getNodeId() + " is not mounted on the controller");
177 return setServBldr.setResult("Roadm-connection successfully created for nodes " + nodesProvisioned.toString());
181 * This method removes wavelength path based on following steps:
185 * 1. Delete Cross connect between source and destination tps.
186 * 2. Delete Och interface on source termination point.
187 * 3. Delete Och interface on destination termination point.
190 * Naming convention used for OCH interfaces name : tp-wavenumber
191 * Naming convention used for cross connect name : src-dest-wavenumber
193 * @param input Input parameter from the service-path yang model
195 * @return Result result of the request.
197 public ServicePathOutputBuilder deleteServicePath(ServicePathInput input) {
198 List<Nodes> nodes = input.getNodes();
199 ServicePathOutputBuilder delServBldr = new ServicePathOutputBuilder();
200 LOG.info(currentMountedDevice.toString());
201 for (Nodes n : nodes) {
202 LOG.info("Deleting service setup on node " + n.getNodeId());
203 String srcTp = n.getSrcTp();
204 String destTp = n.getDestTp();
205 Long waveNumber = input.getWaveNumber();
206 //if the node is currently mounted then proceed.
207 if (currentMountedDevice.contains(n.getNodeId())) {
208 DataBroker netconfNodeDataBroker = PortMapping.getDeviceDataBroker(n.getNodeId(), mps);
209 if (netconfNodeDataBroker != null) {
210 // Deleting roadm connection
211 InstanceIdentifier<RoadmConnections> rdmConnectionIID = InstanceIdentifier.create(
212 OrgOpenroadmDevice.class).child(RoadmConnections.class, new RoadmConnectionsKey(srcTp + "-"
213 + destTp + "-" + waveNumber));
214 ReadWriteTransaction writeTx = netconfNodeDataBroker.newReadWriteTransaction();
215 writeTx.delete(LogicalDatastoreType.CONFIGURATION, rdmConnectionIID);
216 final CheckedFuture<Void, TransactionCommitFailedException> submit = writeTx.submit();
219 LOG.info("Successfully deleted interface " + srcTp + "-" + destTp + "-" + waveNumber);
221 } catch (TransactionCommitFailedException ex) {
222 LOG.error("Failed to delete {} ", srcTp + "-" + destTp + "-" + waveNumber, ex);
224 // Deleting interface on source termination point
225 writeTx = netconfNodeDataBroker.newReadWriteTransaction();
226 InstanceIdentifier<Interface> srcInterfacesIID = InstanceIdentifier.create(OrgOpenroadmDevice.class)
227 .child(Interface.class, new InterfaceKey(srcTp + "-" + waveNumber.toString()));
228 writeTx.delete(LogicalDatastoreType.CONFIGURATION, srcInterfacesIID);
229 final CheckedFuture<Void, TransactionCommitFailedException> submitSrcDel = writeTx.submit();
232 submitSrcDel.checkedGet();
233 LOG.info("Successfully deleted " + srcTp + "-" + waveNumber.toString());
234 } catch (TransactionCommitFailedException ex) {
235 LOG.error("Failed to delete interface {} ", srcTp + "-" + waveNumber.toString(), ex);
237 // Deleting interface on destination termination point
238 writeTx = netconfNodeDataBroker.newReadWriteTransaction();
239 InstanceIdentifier<Interface> destInterfacesIID = InstanceIdentifier.create(
240 OrgOpenroadmDevice.class).child(Interface.class, new InterfaceKey(destTp + "-" + waveNumber
242 writeTx.delete(LogicalDatastoreType.CONFIGURATION, destInterfacesIID);
243 final CheckedFuture<Void, TransactionCommitFailedException> submitDestDel = writeTx.submit();
246 submitDestDel.checkedGet();
247 LOG.info("Successfully deleted " + destTp + "-" + waveNumber.toString());
249 } catch (TransactionCommitFailedException ex) {
250 LOG.error("Failed to delete interface {} ", destTp + "-" + waveNumber.toString(), ex);
254 LOG.warn(n.getNodeId() + " is not mounted on the controller");
255 return delServBldr.setResult(n.getNodeId() + " is not mounted on the controller");
258 return delServBldr.setResult("Request processed");