From: Gilles Thouenon Date: Thu, 2 Jul 2020 06:55:17 +0000 (+0200) Subject: Integration of end-to-end otn services X-Git-Tag: 2.0.0~54 X-Git-Url: https://git.opendaylight.org/gerrit/gitweb?p=transportpce.git;a=commitdiff_plain;h=0f9a451081238311c3f1f30e97aa22dcc5998a8a;ds=sidebyside Integration of end-to-end otn services -allow creation and deletion of new WDM service (OCH-OTU4) and OTN services (HO-ODU4, 10GE/1GE) from Service Handler -complements changes 87920 and 90616 with deletion of otn services -for 10GE and 1GE services, use trib-port and trib-slot numbers provided by PCE computation -for service deletion, retreive and introduce the service header description in order to distinguish the type of otn service to delete and adapt its deletion consequently -adapt Junit tests consequently JIRA: TRNSPRTPCE-165, TRNSPRTPCE-194 Signed-off-by: Gilles Thouenon Co-authored-by: Christophe Betoule Change-Id: I83da87a0c61eb32c9ab023ad614adc79caa3ed75 --- diff --git a/pce/src/main/java/org/opendaylight/transportpce/pce/graph/PostAlgoPathValidator.java b/pce/src/main/java/org/opendaylight/transportpce/pce/graph/PostAlgoPathValidator.java index 245be1b6a..7c111940c 100644 --- a/pce/src/main/java/org/opendaylight/transportpce/pce/graph/PostAlgoPathValidator.java +++ b/pce/src/main/java/org/opendaylight/transportpce/pce/graph/PostAlgoPathValidator.java @@ -97,7 +97,7 @@ public class PostAlgoPathValidator { break; case "10GE": - tribSlotNb = 10; + tribSlotNb = 8; //fallthrough case "1GE": pceResult.setRC(ResponseCodes.RESPONSE_FAILED); @@ -306,7 +306,7 @@ public class PostAlgoPathValidator { private Map> chooseTribSlot(GraphPath path, Map allPceNodes, int nbSlot) { - LOG.info("In choosetribSlot2: edgeList = {} ", path.getEdgeList()); + LOG.info("In choosetribSlot: edgeList = {} ", path.getEdgeList()); Map> tribSlotMap = new HashMap<>(); for (PceGraphEdge edge : path.getEdgeList()) { diff --git a/pce/src/main/java/org/opendaylight/transportpce/pce/networkanalyzer/PceCalculation.java b/pce/src/main/java/org/opendaylight/transportpce/pce/networkanalyzer/PceCalculation.java index 00cf13bb0..04a8aefc6 100644 --- a/pce/src/main/java/org/opendaylight/transportpce/pce/networkanalyzer/PceCalculation.java +++ b/pce/src/main/java/org/opendaylight/transportpce/pce/networkanalyzer/PceCalculation.java @@ -110,8 +110,6 @@ public class PceCalculation { } private boolean parseInput() { - anodeId = input.getServiceAEnd().getNodeId(); - znodeId = input.getServiceZEnd().getNodeId(); if (input.getServiceAEnd().getServiceFormat() == null || input.getServiceZEnd().getServiceFormat() == null || input.getServiceAEnd().getServiceRate() == null) { LOG.error("Service Format and Service Rate are required for a path calculation"); @@ -158,6 +156,13 @@ public class PceCalculation { LOG.debug("parseInput: unsupported service type: Format {} Rate {}", serviceFormatA, serviceRate); } + if ("ODU4".equals(serviceType) || "10GE".equals(serviceType) || "1GE".equals(serviceType)) { + anodeId = input.getServiceAEnd().getTxDirection().getPort().getPortDeviceName(); + znodeId = input.getServiceZEnd().getTxDirection().getPort().getPortDeviceName(); + } else { + anodeId = input.getServiceAEnd().getNodeId(); + znodeId = input.getServiceZEnd().getNodeId(); + } returnStructure.setRate(input.getServiceAEnd().getServiceRate().toJava()); returnStructure.setServiceFormat(input.getServiceAEnd().getServiceFormat()); diff --git a/renderer/src/main/java/org/opendaylight/transportpce/renderer/ModelMappingUtils.java b/renderer/src/main/java/org/opendaylight/transportpce/renderer/ModelMappingUtils.java index 8ecb499b2..41d46c3b4 100644 --- a/renderer/src/main/java/org/opendaylight/transportpce/renderer/ModelMappingUtils.java +++ b/renderer/src/main/java/org/opendaylight/transportpce/renderer/ModelMappingUtils.java @@ -37,6 +37,7 @@ import org.opendaylight.yang.gen.v1.http.org.transportpce.common.types.rev200615 import org.opendaylight.yang.gen.v1.http.org.transportpce.common.types.rev200615.olm.renderer.input.NodesKey; import org.opendaylight.yangtools.yang.common.RpcResult; import org.opendaylight.yangtools.yang.common.RpcResultBuilder; +import org.opendaylight.yangtools.yang.common.Uint32; import org.slf4j.Logger; import org.slf4j.LoggerFactory; @@ -97,8 +98,11 @@ public final class ModelMappingUtils { ServicePathInputBuilder servicePathInputBuilder = new ServicePathInputBuilder() .setServiceName(serviceName) .setOperation(ServicePathInput.Operation.Create) - .setWaveNumber(Long.valueOf(pathDescription.getAToZDirection().getAToZWavelengthNumber().toJava())) .setNodes(nodeLists.getList()); + if (pathDescription.getAToZDirection().getAToZWavelengthNumber() != null) { + servicePathInputBuilder + .setWaveNumber(Uint32.valueOf(pathDescription.getAToZDirection().getAToZWavelengthNumber().toJava())); + } return new ServicePathInputData(servicePathInputBuilder.build(), nodeLists); } @@ -108,8 +112,11 @@ public final class ModelMappingUtils { ServicePathInputBuilder servicePathInputBuilder = new ServicePathInputBuilder() .setOperation(ServicePathInput.Operation.Create) .setServiceName(serviceName) - .setWaveNumber(Long.valueOf(pathDescription.getZToADirection().getZToAWavelengthNumber().toJava())) .setNodes(nodeLists.getList()); + if (pathDescription.getAToZDirection().getAToZWavelengthNumber() != null) { + servicePathInputBuilder + .setWaveNumber(Uint32.valueOf(pathDescription.getAToZDirection().getAToZWavelengthNumber().toJava())); + } return new ServicePathInputData(servicePathInputBuilder.build(), nodeLists); } @@ -119,44 +126,19 @@ public final class ModelMappingUtils { // If atoZ is set true use A-to-Z direction otherwise use Z-to-A List nodes = new ArrayList<>(); - NodeLists nodeLists = null; - if (asideToZside) { - nodeLists = getNodesListAToZ(pathDescription.getAToZDirection().getAToZ().iterator()); - } else { + NodeLists nodeLists = getNodesListAToZ(pathDescription.getAToZDirection().getAToZ().iterator()); + if (!asideToZside) { nodeLists = getNodesListZtoA(pathDescription.getZToADirection().getZToA().iterator()); } LOG.info("These are node-lists {}, {}", nodeLists.getList(), nodeLists.getOlmList()); - for (int i = 0; i < nodeLists.getList().size(); i++) { - Nodes node = nodeLists.getList().get(i); - if (serviceRate.equals("100G")) { - nodes.add( + for (Nodes node: nodeLists.getList()) { + nodes.add( new org.opendaylight.yang.gen.v1.http.org.transportpce.common.types.rev200615.otn.renderer.input .NodesBuilder() - .setNodeId(node.getNodeId()) - .setNetworkTp(node.getDestTp()) - .build()); - } - else { // For any other service rate (1G or 10G) - // For the last node in the list, clientTp and NetworkTp has to be reversed - if (i == nodeLists.getList().size() - 1) { - nodes.add( - new org.opendaylight.yang.gen.v1.http.org.transportpce.common.types.rev200615.otn.renderer.input - .NodesBuilder() - .setNodeId(node.getNodeId()) - .setClientTp(node.getDestTp()) - .setNetworkTp(node.getSrcTp()) - .build()); - - } else { - nodes.add( - new org.opendaylight.yang.gen.v1.http.org.transportpce.common.types.rev200615.otn.renderer.input - .NodesBuilder() .setNodeId(node.getNodeId()) .setClientTp(node.getSrcTp()) .setNetworkTp(node.getDestTp()) .build()); - } - } } OtnServicePathInputBuilder otnServicePathInputBuilder = new OtnServicePathInputBuilder() .setServiceName(serviceName) @@ -164,10 +146,11 @@ public final class ModelMappingUtils { .setServiceRate(serviceRate) .setNodes(nodes); - //TODO: set the trib-slots and trib-ports for the lower oder odu, this should from SH rather than setting here + // set the trib-slots and trib-ports for the lower oder odu if (serviceRate.equals("1G") || (serviceRate.equals("10G"))) { - otnServicePathInputBuilder.setTribPortNumber((short) 1).setTribSlot((short) 1); - + otnServicePathInputBuilder + .setTribPortNumber(pathDescription.getAToZDirection().getTribPortNumber().shortValue()) + .setTribSlot(pathDescription.getAToZDirection().getTribSlotNumber().shortValue()); } return otnServicePathInputBuilder.build(); } @@ -178,7 +161,7 @@ public final class ModelMappingUtils { return new ServicePathInputBuilder().setServiceName(serviceName).build(); } - public static NodeLists getNodesListZtoA(Iterator iterator) { + private static NodeLists getNodesListZtoA(Iterator iterator) { Map treeMap = new TreeMap<>(); List olmList = new ArrayList<>(); List list = new ArrayList<>(); @@ -198,24 +181,24 @@ public final class ModelMappingUtils { LOG.info(" TP is {} {}", tp.getTpId(), tp.getTpNodeId()); tpID = tp.getTpId(); - nodeID = tp.getTpNodeId(); sortId = pathDesObj.getId(); //TODO: do not rely on ID to be in certain format if (tpID.contains("CTP") || tpID.contains("CP")) { continue; } - if (!tpID.contains("TTP") && !tpID.contains("PP") && !tpID.contains("NETWORK") - && !tpID.contains("CLIENT")) { + if (tpID.contains(StringConstants.TTP_TOKEN)) { + nodeID = tp.getTpNodeId().split("-DEG")[0]; + } else if (tpID.contains(StringConstants.PP_TOKEN)) { + nodeID = tp.getTpNodeId().split("-SRG")[0]; + } else if (tpID.contains(StringConstants.NETWORK_TOKEN) + || tpID.contains(StringConstants.CLIENT_TOKEN) || tpID.isEmpty()) { + nodeID = tp.getTpNodeId().split("-XPDR")[0]; + } else { continue; } - - int[] pos = findTheLongestSubstring(nodeID, tpID); - if (pos != null) { - //TODO: do not rely on nodeId to be integer - int id = Integer.parseInt(sortId); - treeMap.put(id, new NodeIdPair(nodeID.substring(0, pos[0] - 1), tpID)); - } + int id = Integer.parseInt(sortId); + treeMap.put(id, new NodeIdPair(nodeID, tpID)); } else if ("Link".equals(resourceType)) { LOG.info("The type is link"); } else { @@ -225,11 +208,11 @@ public final class ModelMappingUtils { LOG.error("Dont find the getResource method", e); } } - populateNodeLists(treeMap, list, olmList); + populateNodeLists(treeMap, list, olmList, false); return new NodeLists(olmList, list); } - public static NodeLists getNodesListAToZ(Iterator iterator) { + private static NodeLists getNodesListAToZ(Iterator iterator) { Map treeMap = new TreeMap<>(); List list = new ArrayList<>(); List olmList = new ArrayList<>(); @@ -249,26 +232,24 @@ public final class ModelMappingUtils { LOG.info("TP is {} {}", tp.getTpId(), tp.getTpNodeId()); tpID = tp.getTpId(); - nodeID = tp.getTpNodeId(); sortId = pathDesObj.getId(); //TODO: do not rely on ID to be in certain format if (tpID.contains("CTP") || tpID.contains("CP")) { continue; } - if (!tpID.contains(StringConstants.TTP_TOKEN) - && !tpID.contains(StringConstants.PP_TOKEN) - && !tpID.contains(StringConstants.NETWORK_TOKEN) - && !tpID.contains(StringConstants.CLIENT_TOKEN)) { + if (tpID.contains(StringConstants.TTP_TOKEN)) { + nodeID = tp.getTpNodeId().split("-DEG")[0]; + } else if (tpID.contains(StringConstants.PP_TOKEN)) { + nodeID = tp.getTpNodeId().split("-SRG")[0]; + } else if (tpID.contains(StringConstants.NETWORK_TOKEN) + || tpID.contains(StringConstants.CLIENT_TOKEN) || tpID.isEmpty()) { + nodeID = tp.getTpNodeId().split("-XPDR")[0]; + } else { continue; } - - int[] pos = findTheLongestSubstring(nodeID, tpID); - if (pos != null) { - //TODO: do not rely on nodeId to be integer - int id = Integer.parseInt(sortId); - treeMap.put(id, new NodeIdPair(nodeID.substring(0, pos[0] - 1), tpID)); - } + int id = Integer.parseInt(sortId); + treeMap.put(id, new NodeIdPair(nodeID, tpID)); } else if ("Link".equals(resourceType)) { LOG.info("The type is link"); } else { @@ -279,70 +260,55 @@ public final class ModelMappingUtils { LOG.error("Did not find the getResource method", e); } } - populateNodeLists(treeMap, list, olmList); + populateNodeLists(treeMap, list, olmList, true); return new NodeLists(olmList, list); } @edu.umd.cs.findbugs.annotations.SuppressFBWarnings( - value = {"NP_LOAD_OF_KNOWN_NULL_VALUE","RCN_REDUNDANT_NULLCHECK_OF_NULL_VALUE"}, - justification = "loop when value is not always null - " - + "TODO: check if something exists in Java lib") - private static void populateNodeLists(Map treeMap, - List list, List olmList) { + value = {"NP_LOAD_OF_KNOWN_NULL_VALUE","RCN_REDUNDANT_NULLCHECK_OF_NULL_VALUE"}, + justification = "loop when value is not always null - " + + "TODO: check if something exists in Java lib") + private static void populateNodeLists(Map treeMap, List list, List olmList, + boolean isAToz) { String desID = null; String srcID = null; - int cnt = 0; // This is a counter to check for NETWORK_TOKEN + LOG.info("treeMap values = {}", treeMap.values()); for (NodeIdPair values : treeMap.values()) { - cnt++; if (srcID == null) { srcID = values.getTpID(); - // This code is added in support of OTU4 service - if ((srcID.contains(StringConstants.NETWORK_TOKEN)) && cnt == 1) { - NodesBuilder nb = new NodesBuilder() - .withKey(new NodesKey(values.getNodeID())) - .setDestTp(srcID) // desTp is assigned to the srcID - .setSrcTp(null); // srcTp is set to null to create OTU service - list.add(nb.build()); - - NodesBuilder olmNb = new NodesBuilder() - .setNodeId(values.getNodeID()) - .setDestTp(srcID) // desTp is assigned to the srcID - .setSrcTp(null); // srcTp is set to null to create OTU service - olmList.add(olmNb.build()); - srcID = null; - desID = null; - continue; // Continue to the next element in the for loop - } - if ((srcID.contains(StringConstants.NETWORK_TOKEN)) && cnt == treeMap.size()) { - // For last node - NodesBuilder nb = new NodesBuilder() - .withKey(new NodesKey(values.getNodeID())) - .setDestTp(srcID) //TODO: check this assignment - .setSrcTp(null); // - list.add(nb.build()); - - NodesBuilder olmNb = new NodesBuilder() - .setNodeId(values.getNodeID()) - .setDestTp(null) // In the case of final node, destTp is set to null - .setSrcTp(srcID); // srcTp is srcTp - olmList.add(olmNb.build()); - srcID = null; - desID = null; - } - // End of code for support of ODT4 service } else if (desID == null) { desID = values.getTpID(); - NodesBuilder nb = new NodesBuilder() - .withKey(new NodesKey(values.getNodeID())) - .setDestTp(desID) - .setSrcTp(srcID); - list.add(nb.build()); - NodesBuilder olmNb = new NodesBuilder() .setNodeId(values.getNodeID()) .setDestTp(desID) .setSrcTp(srcID); olmList.add(olmNb.build()); + if (srcID.isEmpty()) { + srcID = null; + } + if (desID.isEmpty()) { + desID = new StringBuilder(srcID).toString(); + srcID = null; + } + if (isAToz) { + NodesBuilder nb = new NodesBuilder() + .withKey(new NodesKey(values.getNodeID())) + .setDestTp(desID) + .setSrcTp(srcID); + if (srcID != null && desID != null && srcID.contains(StringConstants.NETWORK_TOKEN)) { + nb.setDestTp(srcID).setSrcTp(desID); + } + list.add(nb.build()); + } else { + if (srcID != null && desID != null && !srcID.contains(StringConstants.NETWORK_TOKEN) + && !desID.contains(StringConstants.NETWORK_TOKEN)) { + NodesBuilder nb = new NodesBuilder() + .withKey(new NodesKey(values.getNodeID())) + .setDestTp(desID) + .setSrcTp(srcID); + list.add(nb.build()); + } + } srcID = null; desID = null; } else { @@ -351,6 +317,7 @@ public final class ModelMappingUtils { } } + @edu.umd.cs.findbugs.annotations.SuppressFBWarnings( value = "PZLA_PREFER_ZERO_LENGTH_ARRAYS", justification = "not relevant to return and zero length array" diff --git a/renderer/src/main/java/org/opendaylight/transportpce/renderer/NetworkModelWavelengthServiceImpl.java b/renderer/src/main/java/org/opendaylight/transportpce/renderer/NetworkModelWavelengthServiceImpl.java index b8df0896d..1bb9ce0eb 100644 --- a/renderer/src/main/java/org/opendaylight/transportpce/renderer/NetworkModelWavelengthServiceImpl.java +++ b/renderer/src/main/java/org/opendaylight/transportpce/renderer/NetworkModelWavelengthServiceImpl.java @@ -10,6 +10,7 @@ package org.opendaylight.transportpce.renderer; import java.math.BigDecimal; import java.util.ArrayList; import java.util.List; +import java.util.Objects; import java.util.Optional; import java.util.concurrent.ExecutionException; import java.util.concurrent.TimeUnit; @@ -73,6 +74,7 @@ import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.network.top import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.network.topology.rev180226.networks.network.node.TerminationPointKey; import org.opendaylight.yangtools.yang.binding.InstanceIdentifier; import org.opendaylight.yangtools.yang.binding.InstanceIdentifier.InstanceIdentifierBuilder; +import org.opendaylight.yangtools.yang.common.Uint32; import org.slf4j.Logger; import org.slf4j.LoggerFactory; @@ -89,9 +91,11 @@ public class NetworkModelWavelengthServiceImpl implements NetworkModelWavelength public void useWavelengths(PathDescription pathDescription) { List atozTpIds = getAToZTpList(pathDescription); + atozTpIds.removeIf(Objects::isNull); deleteAvailableWL(atozTpIds.stream().map(NodeIdPair::getNodeID).distinct().collect(Collectors.toList()), pathDescription.getAToZDirection().getAToZWavelengthNumber().toJava()); List ztoaTpIds = getZToATpList(pathDescription); + ztoaTpIds.removeIf(Objects::isNull); deleteAvailableWL(ztoaTpIds.stream().map(NodeIdPair::getNodeID).distinct().collect(Collectors.toList()), pathDescription.getZToADirection().getZToAWavelengthNumber().toJava()); addUsedWL(pathDescription.getAToZDirection().getAToZWavelengthNumber().toJava(), atozTpIds); @@ -102,7 +106,8 @@ public class NetworkModelWavelengthServiceImpl implements NetworkModelWavelength public void freeWavelengths(PathDescription pathDescription) { List atozTpIds = getAToZTpList(pathDescription); List ztoaTpIds = getZToATpList(pathDescription); - + atozTpIds.removeIf(Objects::isNull); + ztoaTpIds.removeIf(Objects::isNull); deleteUsedWL(pathDescription.getAToZDirection().getAToZWavelengthNumber().toJava(), atozTpIds); deleteUsedWL(pathDescription.getZToADirection().getZToAWavelengthNumber().toJava(), ztoaTpIds); addAvailableWL(atozTpIds.stream().map(NodeIdPair::getNodeID).distinct().collect(Collectors.toList()), @@ -122,7 +127,8 @@ public class NetworkModelWavelengthServiceImpl implements NetworkModelWavelength return aToZ.getResource().getResource() instanceof TerminationPoint; }).map(aToZ -> { TerminationPoint tp = (TerminationPoint) aToZ.getResource().getResource(); - if ((tp == null) || (tp.getTpNodeId() == null) || (tp.getTpId() == null)) { + if ((tp == null) || (tp.getTpNodeId() == null) || (tp.getTpId() == null) + || tp.getTpId().isEmpty()) { LOG.warn("Termination point in AToZ node {} contains nulls! Skipping this node!", aToZ.getId()); return null; } @@ -141,7 +147,8 @@ public class NetworkModelWavelengthServiceImpl implements NetworkModelWavelength return zToA.getResource().getResource() instanceof TerminationPoint; }).map(zToA -> { TerminationPoint tp = (TerminationPoint) zToA.getResource().getResource(); - if ((tp == null) || (tp.getTpNodeId() == null) || (tp.getTpId() == null)) { + if ((tp == null) || (tp.getTpNodeId() == null) || (tp.getTpId() == null) + || tp.getTpId().isEmpty()) { LOG.warn("Termination point in ZToA node {} contains nulls! Skipping this node!", zToA.getId()); return null; } @@ -220,7 +227,6 @@ public class NetworkModelWavelengthServiceImpl implements NetworkModelWavelength } Node1Builder node1Builder = new Node1Builder(node1); - switch (node2.getNodeType()) { case DEGREE: DegreeAttributes degreeAttributes = node1.getDegreeAttributes(); @@ -234,7 +240,8 @@ public class NetworkModelWavelengthServiceImpl implements NetworkModelWavelength .AvailableWavelengths> availableDegreeWLs = new ArrayList<>(degreeAttributesBuilder .getAvailableWavelengths()); availableDegreeWLs.add(new org.opendaylight.yang.gen.v1.http.org.openroadm.degree.rev181130.degree - .node.attributes.AvailableWavelengthsBuilder().setIndex(wavelengthNumber).build()); + .node.attributes.AvailableWavelengthsBuilder().setIndex(Uint32.valueOf(wavelengthNumber)) + .build()); degreeAttributesBuilder.setAvailableWavelengths(availableDegreeWLs); node1Builder.setDegreeAttributes(degreeAttributesBuilder.build()); break; @@ -249,7 +256,8 @@ public class NetworkModelWavelengthServiceImpl implements NetworkModelWavelength List availableSrgWLs = new ArrayList<>(srgAttributesBuilder .getAvailableWavelengths()); - availableSrgWLs.add(new AvailableWavelengthsBuilder().setIndex(wavelengthNumber).build()); + availableSrgWLs.add(new AvailableWavelengthsBuilder().setIndex(Uint32.valueOf(wavelengthNumber)) + .build()); srgAttributesBuilder.setAvailableWavelengths(availableSrgWLs); node1Builder.setSrgAttributes(srgAttributesBuilder.build()); break; @@ -294,7 +302,7 @@ public class NetworkModelWavelengthServiceImpl implements NetworkModelWavelength availableWlIID = nodeIIDBuilder.child(DegreeAttributes.class) .child(org.opendaylight.yang.gen.v1.http.org.openroadm.degree.rev181130.degree.node .attributes.AvailableWavelengths.class, - new AvailableWavelengthsKey(wavelengthNumber)) + new AvailableWavelengthsKey(Uint32.valueOf(wavelengthNumber))) .build(); break; case SRG: @@ -302,7 +310,7 @@ public class NetworkModelWavelengthServiceImpl implements NetworkModelWavelength .child(org.opendaylight.yang.gen.v1.http.org.openroadm.srg.rev181130.srg.node.attributes .AvailableWavelengths.class, new org.opendaylight.yang.gen.v1.http.org.openroadm.srg.rev181130.srg.node - .attributes.AvailableWavelengthsKey(wavelengthNumber)) + .attributes.AvailableWavelengthsKey(Uint32.valueOf(wavelengthNumber))) .build(); break; @@ -397,19 +405,19 @@ public class NetworkModelWavelengthServiceImpl implements NetworkModelWavelength case DEGREETXTTP: case DEGREETXRXTTP: usedWlIID = usedWlIIDBuilder.child(TxTtpAttributes.class).child(UsedWavelengths.class, - new UsedWavelengthsKey(wavelengthIndex)).build(); + new UsedWavelengthsKey(Uint32.valueOf(wavelengthIndex))).build(); break; case DEGREERXTTP: usedWlIID = usedWlIIDBuilder.child(RxTtpAttributes.class).child(UsedWavelengths.class, - new UsedWavelengthsKey(wavelengthIndex)).build(); + new UsedWavelengthsKey(Uint32.valueOf(wavelengthIndex))).build(); break; case DEGREETXCTP: case DEGREERXCTP: case DEGREETXRXCTP: usedWlIID = usedWlIIDBuilder.child(CtpAttributes.class).child(UsedWavelengths.class, - new UsedWavelengthsKey(wavelengthIndex)).build(); + new UsedWavelengthsKey(Uint32.valueOf(wavelengthIndex))).build(); break; case SRGTXCP: @@ -419,14 +427,14 @@ public class NetworkModelWavelengthServiceImpl implements NetworkModelWavelength .openroadm.network.topology.rev181130.networks.network.node.termination.point.cp.attributes .UsedWavelengths.class, new org.opendaylight.yang.gen.v1.http.org.openroadm.network.topology .rev181130.networks.network.node.termination.point.cp.attributes - .UsedWavelengthsKey(wavelengthIndex)).build(); + .UsedWavelengthsKey(Uint32.valueOf(wavelengthIndex))).build(); break; case SRGTXRXPP: case SRGRXPP: case SRGTXPP: usedWlIID = usedWlIIDBuilder.child(PpAttributes.class).child(UsedWavelength.class, - new UsedWavelengthKey(wavelengthIndex)).build(); + new UsedWavelengthKey(Uint32.valueOf(wavelengthIndex))).build(); break; case XPONDERNETWORK: @@ -498,7 +506,7 @@ public class NetworkModelWavelengthServiceImpl implements NetworkModelWavelength txTtpAttributesBuilder = new TxTtpAttributesBuilder(txTtpAttributes); usedDegreeTxTtpWls = new ArrayList<>(txTtpAttributesBuilder.getUsedWavelengths()); } - usedDegreeTxTtpWls.add(new UsedWavelengthsBuilder().setIndex(wavelengthIndex) + usedDegreeTxTtpWls.add(new UsedWavelengthsBuilder().setIndex(Uint32.valueOf(wavelengthIndex)) .setFrequency(centralTHz).setWidth(FrequencyGHz.getDefaultInstance("40")).build()); txTtpAttributesBuilder.setUsedWavelengths(usedDegreeTxTtpWls); tp1Builder.setTxTtpAttributes(txTtpAttributesBuilder.build()); @@ -518,7 +526,7 @@ public class NetworkModelWavelengthServiceImpl implements NetworkModelWavelength rxTtpAttributesBuilder = new RxTtpAttributesBuilder(rxTtpAttributes); usedDegreeRxTtpWls = new ArrayList<>(rxTtpAttributesBuilder.getUsedWavelengths()); } - usedDegreeRxTtpWls.add(new UsedWavelengthsBuilder().setIndex(wavelengthIndex) + usedDegreeRxTtpWls.add(new UsedWavelengthsBuilder().setIndex(Uint32.valueOf(wavelengthIndex)) .setFrequency(centralTHz).setWidth(FrequencyGHz.getDefaultInstance("40")).build()); rxTtpAttributesBuilder.setUsedWavelengths(usedDegreeRxTtpWls); tp1Builder.setRxTtpAttributes(rxTtpAttributesBuilder.build()); @@ -540,7 +548,7 @@ public class NetworkModelWavelengthServiceImpl implements NetworkModelWavelength ctpAttributesBuilder = new CtpAttributesBuilder(ctpAttributes); usedDegreeCtpWls = new ArrayList<>(ctpAttributesBuilder.getUsedWavelengths()); } - usedDegreeCtpWls.add(new UsedWavelengthsBuilder().setIndex(wavelengthIndex) + usedDegreeCtpWls.add(new UsedWavelengthsBuilder().setIndex(Uint32.valueOf(wavelengthIndex)) .setFrequency(centralTHz).setWidth(FrequencyGHz.getDefaultInstance("40")).build()); ctpAttributesBuilder.setUsedWavelengths(usedDegreeCtpWls); tp1Builder.setCtpAttributes(ctpAttributesBuilder.build()); @@ -565,7 +573,7 @@ public class NetworkModelWavelengthServiceImpl implements NetworkModelWavelength } usedDegreeCpWls.add(new org.opendaylight.yang.gen.v1.http.org.openroadm.network.topology.rev181130 .networks.network.node.termination.point.cp.attributes.UsedWavelengthsBuilder() - .setIndex(wavelengthIndex) + .setIndex(Uint32.valueOf(wavelengthIndex)) .setFrequency(centralTHz).setWidth(FrequencyGHz.getDefaultInstance("40")).build()); cpAttributesBuilder.setUsedWavelengths(usedDegreeCpWls); tp1Builder.setCpAttributes(cpAttributesBuilder.build()); @@ -587,7 +595,7 @@ public class NetworkModelWavelengthServiceImpl implements NetworkModelWavelength ppAttributesBuilder = new PpAttributesBuilder(ppAttributes); usedDegreePpWls = new ArrayList<>(ppAttributesBuilder.getUsedWavelength()); } - usedDegreePpWls.add(new UsedWavelengthBuilder().setIndex(wavelengthIndex) + usedDegreePpWls.add(new UsedWavelengthBuilder().setIndex(Uint32.valueOf(wavelengthIndex)) .setFrequency(centralTHz).setWidth(FrequencyGHz.getDefaultInstance("40")).build()); ppAttributesBuilder.setUsedWavelength(usedDegreePpWls); tp1Builder.setPpAttributes(ppAttributesBuilder.build()); diff --git a/renderer/src/main/java/org/opendaylight/transportpce/renderer/provisiondevice/DeviceRendererServiceImpl.java b/renderer/src/main/java/org/opendaylight/transportpce/renderer/provisiondevice/DeviceRendererServiceImpl.java index 0f6c87a5b..6a310929e 100644 --- a/renderer/src/main/java/org/opendaylight/transportpce/renderer/provisiondevice/DeviceRendererServiceImpl.java +++ b/renderer/src/main/java/org/opendaylight/transportpce/renderer/provisiondevice/DeviceRendererServiceImpl.java @@ -98,7 +98,6 @@ public class DeviceRendererServiceImpl implements DeviceRendererService { @Override public ServicePathOutput setupServicePath(ServicePathInput input, ServicePathDirection direction) { List nodes = input.getNodes(); - // Register node for suppressing alarms if (!alarmSuppressionNodeRegistration(input)) { LOG.warn("Alarm suppresion node registration failed!!!!"); diff --git a/renderer/src/main/java/org/opendaylight/transportpce/renderer/provisiondevice/OtnDeviceRendererServiceImpl.java b/renderer/src/main/java/org/opendaylight/transportpce/renderer/provisiondevice/OtnDeviceRendererServiceImpl.java index 3328dc124..a5e21db96 100644 --- a/renderer/src/main/java/org/opendaylight/transportpce/renderer/provisiondevice/OtnDeviceRendererServiceImpl.java +++ b/renderer/src/main/java/org/opendaylight/transportpce/renderer/provisiondevice/OtnDeviceRendererServiceImpl.java @@ -60,7 +60,7 @@ public class OtnDeviceRendererServiceImpl implements OtnDeviceRendererService { @Override public OtnServicePathOutput setupOtnServicePath(OtnServicePathInput input) { - LOG.info("Calling setup service path"); + LOG.info("Calling setup otn-service path"); boolean success = true; List nodeInterfaces = new ArrayList<>(); List results = new ArrayList<>(); @@ -139,6 +139,11 @@ public class OtnDeviceRendererServiceImpl implements OtnDeviceRendererService { } public OtnServicePathOutput deleteOtnServicePath(OtnServicePathInput input) { + if (input == null) { + LOG.error("Unable to delete otn service path. input = null"); + return new OtnServicePathOutputBuilder().setResult("Unable to delete otn service path. input = null") + .setSuccess(false).build(); + } List nodes = input.getNodes(); AtomicBoolean success = new AtomicBoolean(true); ConcurrentLinkedQueue results = new ConcurrentLinkedQueue<>(); diff --git a/renderer/src/main/java/org/opendaylight/transportpce/renderer/provisiondevice/RendererServiceOperations.java b/renderer/src/main/java/org/opendaylight/transportpce/renderer/provisiondevice/RendererServiceOperations.java index 11e655fa5..3424964ba 100644 --- a/renderer/src/main/java/org/opendaylight/transportpce/renderer/provisiondevice/RendererServiceOperations.java +++ b/renderer/src/main/java/org/opendaylight/transportpce/renderer/provisiondevice/RendererServiceOperations.java @@ -13,14 +13,15 @@ import org.opendaylight.yang.gen.v1.http.org.opendaylight.transportpce.renderer. import org.opendaylight.yang.gen.v1.http.org.opendaylight.transportpce.renderer.rev200520.ServiceDeleteOutput; import org.opendaylight.yang.gen.v1.http.org.opendaylight.transportpce.renderer.rev200520.ServiceImplementationRequestInput; import org.opendaylight.yang.gen.v1.http.org.opendaylight.transportpce.renderer.rev200520.ServiceImplementationRequestOutput; -import org.opendaylight.yang.gen.v1.http.org.transportpce.b.c._interface.service.types.rev200128.service.path.PathDescription; +import org.opendaylight.yang.gen.v1.http.org.openroadm.service.rev190531.service.list.Services; +import org.opendaylight.yang.gen.v1.http.org.transportpce.b.c._interface.pathdescription.rev200629.PathDescription; public interface RendererServiceOperations { ListenableFuture serviceImplementation(ServiceImplementationRequestInput input); - ListenableFuture serviceDelete(ServiceDeleteInput input); + ListenableFuture serviceDelete(ServiceDeleteInput input, Services service); OperationResult reserveResource(PathDescription pathDescription); diff --git a/renderer/src/main/java/org/opendaylight/transportpce/renderer/provisiondevice/RendererServiceOperationsImpl.java b/renderer/src/main/java/org/opendaylight/transportpce/renderer/provisiondevice/RendererServiceOperationsImpl.java index 66bca1cf0..99825cb99 100644 --- a/renderer/src/main/java/org/opendaylight/transportpce/renderer/provisiondevice/RendererServiceOperationsImpl.java +++ b/renderer/src/main/java/org/opendaylight/transportpce/renderer/provisiondevice/RendererServiceOperationsImpl.java @@ -46,19 +46,23 @@ import org.opendaylight.yang.gen.v1.http.org.opendaylight.transportpce.olm.rev17 import org.opendaylight.yang.gen.v1.http.org.opendaylight.transportpce.olm.rev170418.TransportpceOlmService; import org.opendaylight.yang.gen.v1.http.org.opendaylight.transportpce.olm.rev170418.get.pm.output.Measurements; import org.opendaylight.yang.gen.v1.http.org.opendaylight.transportpce.renderer.device.rev200128.OtnServicePathInput; +import org.opendaylight.yang.gen.v1.http.org.opendaylight.transportpce.renderer.device.rev200128.OtnServicePathOutput; import org.opendaylight.yang.gen.v1.http.org.opendaylight.transportpce.renderer.rev200520.ServiceDeleteInput; import org.opendaylight.yang.gen.v1.http.org.opendaylight.transportpce.renderer.rev200520.ServiceDeleteOutput; import org.opendaylight.yang.gen.v1.http.org.opendaylight.transportpce.renderer.rev200520.ServiceImplementationRequestInput; import org.opendaylight.yang.gen.v1.http.org.opendaylight.transportpce.renderer.rev200520.ServiceImplementationRequestOutput; import org.opendaylight.yang.gen.v1.http.org.opendaylight.transportpce.renderer.rev200520.ServiceRpcResultSp; import org.opendaylight.yang.gen.v1.http.org.opendaylight.transportpce.renderer.rev200520.ServiceRpcResultSpBuilder; +import org.opendaylight.yang.gen.v1.http.org.openroadm.common.service.types.rev190531.ConnectionType; import org.opendaylight.yang.gen.v1.http.org.openroadm.otn.common.types.rev181130.ODU4; import org.opendaylight.yang.gen.v1.http.org.openroadm.otn.common.types.rev181130.OTU4; import org.opendaylight.yang.gen.v1.http.org.openroadm.pm.types.rev161014.PmGranularity; import org.opendaylight.yang.gen.v1.http.org.openroadm.resource.types.rev161014.ResourceTypeEnum; +import org.opendaylight.yang.gen.v1.http.org.openroadm.service.format.rev190531.ServiceFormat; +import org.opendaylight.yang.gen.v1.http.org.openroadm.service.rev190531.service.list.Services; +import org.opendaylight.yang.gen.v1.http.org.transportpce.b.c._interface.pathdescription.rev200629.PathDescription; import org.opendaylight.yang.gen.v1.http.org.transportpce.b.c._interface.service.types.rev200128.RpcStatusEx; import org.opendaylight.yang.gen.v1.http.org.transportpce.b.c._interface.service.types.rev200128.ServicePathNotificationTypes; -import org.opendaylight.yang.gen.v1.http.org.transportpce.b.c._interface.service.types.rev200128.service.path.PathDescription; import org.opendaylight.yang.gen.v1.http.org.transportpce.b.c._interface.servicepath.rev171017.ServicePathList; import org.opendaylight.yang.gen.v1.http.org.transportpce.b.c._interface.servicepath.rev171017.service.path.list.ServicePaths; import org.opendaylight.yang.gen.v1.http.org.transportpce.b.c._interface.servicepath.rev171017.service.path.list.ServicePathsKey; @@ -66,6 +70,7 @@ import org.opendaylight.yang.gen.v1.http.org.transportpce.common.types.rev200615 import org.opendaylight.yang.gen.v1.http.org.transportpce.common.types.rev200615.olm.renderer.input.Nodes; import org.opendaylight.yangtools.yang.binding.InstanceIdentifier; import org.opendaylight.yangtools.yang.common.RpcResult; +import org.opendaylight.yangtools.yang.common.Uint32; import org.slf4j.Logger; import org.slf4j.LoggerFactory; @@ -127,6 +132,7 @@ public class RendererServiceOperationsImpl implements RendererServiceOperations serviceImplementation(ServiceImplementationRequestInput input) { LOG.info("Calling service impl request {}", input.getServiceName()); return executor.submit(new Callable() { + @Override public ServiceImplementationRequestOutput call() throws Exception { sendNotifications(ServicePathNotificationTypes.ServiceImplementationRequest, input.getServiceName(), @@ -142,67 +148,12 @@ public class RendererServiceOperationsImpl implements RendererServiceOperations || (input.getServiceAEnd().getServiceFormat().getName().equals("OC")))) { LOG.info("Service format for {} is {} and rate is {}", input.getServiceName(), input.getServiceAEnd().getServiceFormat(), input.getServiceAEnd().getServiceRate()); - ServicePathInputData servicePathInputDataAtoZ = ModelMappingUtils - .rendererCreateServiceInputAToZ(input.getServiceName(), input.getPathDescription()); - ServicePathInputData servicePathInputDataZtoA = ModelMappingUtils - .rendererCreateServiceInputZToA(input.getServiceName(), input.getPathDescription()); - // Rollback should be same for all conditions, so creating a new one - RollbackProcessor rollbackProcessor = new RollbackProcessor(); - List renderingResults = - deviceRendering(rollbackProcessor, servicePathInputDataAtoZ, servicePathInputDataZtoA); - if (rollbackProcessor.rollbackAllIfNecessary() > 0) { - sendNotifications(ServicePathNotificationTypes.ServiceImplementationRequest, - input.getServiceName(), RpcStatusEx.Failed, DEVICE_RENDERING_ROLL_BACK_MSG); + if (!createServicepathInput(input)) { return ModelMappingUtils.createServiceImplResponse(ResponseCodes.RESPONSE_FAILED, OPERATION_FAILED); } - ServicePowerSetupInput olmPowerSetupInputAtoZ = - ModelMappingUtils.createServicePowerSetupInput(renderingResults.get(0).getOlmList(), - input); - ServicePowerSetupInput olmPowerSetupInputZtoA = - ModelMappingUtils.createServicePowerSetupInput(renderingResults.get(1).getOlmList(), - input); - olmPowerSetup(rollbackProcessor, olmPowerSetupInputAtoZ, olmPowerSetupInputZtoA); - if (rollbackProcessor.rollbackAllIfNecessary() > 0) { - sendNotifications(ServicePathNotificationTypes.ServiceImplementationRequest, - input.getServiceName(), RpcStatusEx.Failed, OLM_ROLL_BACK_MSG); - return ModelMappingUtils.createServiceImplResponse(ResponseCodes.RESPONSE_FAILED, - OPERATION_FAILED); - } - // run service activation test twice - once on source node and once on - // destination node - List nodes = servicePathInputDataAtoZ.getServicePathInput().getNodes(); - if ((nodes == null) || (nodes.isEmpty())) { - return ModelMappingUtils.createServiceImplResponse(ResponseCodes.RESPONSE_FAILED, - OPERATION_FAILED); - } - Nodes sourceNode = nodes.get(0); - Nodes destNode = nodes.get(nodes.size() - 1); - String srcNetworkTp; - String dstNetowrkTp; - if (sourceNode.getDestTp().contains(StringConstants.NETWORK_TOKEN)) { - srcNetworkTp = sourceNode.getDestTp(); - } else { - srcNetworkTp = sourceNode.getSrcTp(); - } - if (destNode.getDestTp().contains(StringConstants.NETWORK_TOKEN)) { - dstNetowrkTp = destNode.getDestTp(); - } else { - dstNetowrkTp = destNode.getSrcTp(); - } - if (!isServiceActivated(sourceNode.getNodeId(), srcNetworkTp) - || !isServiceActivated(destNode.getNodeId(), dstNetowrkTp)) { - rollbackProcessor.rollbackAll(); - sendNotifications(ServicePathNotificationTypes.ServiceImplementationRequest, - input.getServiceName(), RpcStatusEx.Failed, - "Service activation test failed."); - return ModelMappingUtils.createServiceImplResponse(ResponseCodes.RESPONSE_FAILED, - OPERATION_FAILED); - } - // If Service activation is success update Network ModelMappingUtils - networkModelWavelengthService.useWavelengths(input.getPathDescription()); } else { // This implies, service-rate is 1 or 10G - // This includes the lower-order odu (1 G, 10 G) and + // This includes the lower-order odu (1G, 10G) and this is A-Z side LOG.info("RPC implementation for LO-ODU"); String serviceRate = ""; // Assuming service at A-side and Z-side has same service rate if (input.getServiceAEnd().getServiceRate() != null) { @@ -211,21 +162,15 @@ public class RendererServiceOperationsImpl implements RendererServiceOperations LOG.info("Start rendering for {} service with {} rate and {} format", input.getServiceName(), serviceRate, input.getServiceAEnd().getServiceFormat()); - // TODO: Need to create OCH-OTU4 interfaces by calling service-path input without src-tp // This is A-Z side OtnServicePathInput otnServicePathInputAtoZ = ModelMappingUtils .rendererCreateOtnServiceInput(input.getServiceName(), input.getServiceAEnd().getServiceFormat().getName(), - serviceRate, input.getPathDescription(), true); - // This is Z-A side - OtnServicePathInput otnServicePathInputZtoA = ModelMappingUtils - .rendererCreateOtnServiceInput(input.getServiceName(), - input.getServiceZEnd().getServiceFormat().getName(), - serviceRate, input.getPathDescription(), false); + serviceRate, (PathDescription) input.getPathDescription(), true); // Rollback should be same for all conditions, so creating a new one RollbackProcessor rollbackProcessor = new RollbackProcessor(); List otnRenderingResults = otnDeviceRendering(rollbackProcessor, - otnServicePathInputAtoZ, otnServicePathInputZtoA); + otnServicePathInputAtoZ, null); if (rollbackProcessor.rollbackAllIfNecessary() > 0) { sendNotifications(ServicePathNotificationTypes.ServiceImplementationRequest, input.getServiceName(), RpcStatusEx.Failed, DEVICE_RENDERING_ROLL_BACK_MSG); @@ -233,9 +178,9 @@ public class RendererServiceOperationsImpl implements RendererServiceOperations OPERATION_FAILED); } LOG.info("OTN rendering result size {}", otnRenderingResults.size()); + sendNotifications(ServicePathNotificationTypes.ServiceImplementationRequest, + input.getServiceName(), RpcStatusEx.Successful, OPERATION_SUCCESSFUL); } - sendNotifications(ServicePathNotificationTypes.ServiceImplementationRequest, - input.getServiceName(), RpcStatusEx.Successful, OPERATION_SUCCESSFUL); break; case Infrastructure: LOG.info("RPC implementation for {}", input.getConnectionType()); @@ -244,55 +189,7 @@ public class RendererServiceOperationsImpl implements RendererServiceOperations // For the service of OTU4 infrastructure // First create the OCH and OTU interfaces String serviceRate = "100G"; // For OtnDeviceRendererServiceImpl - LOG.info("Service format for {} is {} and rate is {}", input.getServiceName(), - input.getServiceAEnd().getOtuServiceRate(), serviceRate); - // First render OCH and OTU interfaces - ServicePathInputData servicePathInputDataAtoZ = ModelMappingUtils - .rendererCreateServiceInputAToZ(input.getServiceName(), input.getPathDescription()); - ServicePathInputData servicePathInputDataZtoA = ModelMappingUtils - .rendererCreateServiceInputZToA(input.getServiceName(), input.getPathDescription()); - // Rollback should be same for all conditions, so creating a new one - RollbackProcessor rollbackProcessor = new RollbackProcessor(); - List renderingResults = - deviceRendering(rollbackProcessor, servicePathInputDataAtoZ, servicePathInputDataZtoA); - if (rollbackProcessor.rollbackAllIfNecessary() > 0) { - sendNotifications(ServicePathNotificationTypes.ServiceImplementationRequest, - input.getServiceName(), RpcStatusEx.Failed, DEVICE_RENDERING_ROLL_BACK_MSG); - return ModelMappingUtils.createServiceImplResponse(ResponseCodes.RESPONSE_FAILED, - OPERATION_FAILED); - } - LOG.info("Starting the OLM power setup"); - ServicePowerSetupInput olmPowerSetupInputAtoZ = - ModelMappingUtils.createServicePowerSetupInput(renderingResults.get(0).getOlmList(), - input); - ServicePowerSetupInput olmPowerSetupInputZtoA = - ModelMappingUtils.createServicePowerSetupInput(renderingResults.get(1).getOlmList(), - input); - olmPowerSetup(rollbackProcessor, olmPowerSetupInputAtoZ, olmPowerSetupInputZtoA); - if (rollbackProcessor.rollbackAllIfNecessary() > 0) { - sendNotifications(ServicePathNotificationTypes.ServiceImplementationRequest, - input.getServiceName(), RpcStatusEx.Failed, OLM_ROLL_BACK_MSG); - return ModelMappingUtils.createServiceImplResponse(ResponseCodes.RESPONSE_FAILED, - OPERATION_FAILED); - } - // run service activation test twice - once on source node and once on - // destination node - List nodes = servicePathInputDataAtoZ.getServicePathInput().getNodes(); - if ((nodes == null) || (nodes.isEmpty())) { - return ModelMappingUtils.createServiceImplResponse(ResponseCodes.RESPONSE_FAILED, - OPERATION_FAILED); - } - Nodes srcNode = nodes.get(0); - Nodes tgtNode = nodes.get(nodes.size() - 1); // destination node or target node - String srcNetworkTp = srcNode.getDestTp(); // In this case srcNode only has destTp - String tgtNetowrkTp = tgtNode.getSrcTp(); // tgtNode node only has srcTp - - if (!isServiceActivated(srcNode.getNodeId(), srcNetworkTp) - || !isServiceActivated(tgtNode.getNodeId(), tgtNetowrkTp)) { - rollbackProcessor.rollbackAll(); - sendNotifications(ServicePathNotificationTypes.ServiceImplementationRequest, - input.getServiceName(), RpcStatusEx.Failed, - "Service activation test failed."); + if (!createServicepathInput(input)) { return ModelMappingUtils.createServiceImplResponse(ResponseCodes.RESPONSE_FAILED, OPERATION_FAILED); } @@ -305,16 +202,18 @@ public class RendererServiceOperationsImpl implements RendererServiceOperations LOG.info("Service format for {} is {} and rate is {}", input.getServiceName(), input.getServiceAEnd().getOduServiceRate(), serviceRate); // Now start rendering ODU4 interface - String serviceFormat = "ODU"; // Since we need to create ODU4 Ttp interfaces as well // This is A-Z side OtnServicePathInput otnServicePathInputAtoZ = ModelMappingUtils .rendererCreateOtnServiceInput(input.getServiceName(), - serviceFormat, serviceRate, input.getPathDescription(), true); + input.getServiceAEnd().getServiceFormat().getName(), + serviceRate, + input.getPathDescription(), true); // This is Z-A side OtnServicePathInput otnServicePathInputZtoA = ModelMappingUtils .rendererCreateOtnServiceInput(input.getServiceName(), input.getServiceZEnd().getServiceFormat().getName(), - serviceRate, input.getPathDescription(), false); + serviceRate, + input.getPathDescription(), false); // Rollback should be same for all conditions, so creating a new one RollbackProcessor rollbackProcessor = new RollbackProcessor(); List otnRenderingResults = otnDeviceRendering(rollbackProcessor, @@ -336,7 +235,6 @@ public class RendererServiceOperationsImpl implements RendererServiceOperations return ModelMappingUtils.createServiceImplResponse(ResponseCodes.RESPONSE_OK, OPERATION_SUCCESSFUL); } - }); } @@ -367,78 +265,69 @@ public class RendererServiceOperationsImpl implements RendererServiceOperations } @Override - public ListenableFuture serviceDelete(ServiceDeleteInput input) { + public ListenableFuture serviceDelete(ServiceDeleteInput input, Services service) { String serviceName = input.getServiceName(); - LOG.info("Calling service delete request {}", input.getServiceName()); + LOG.info("Calling service delete request {}", serviceName); return executor.submit(new Callable() { @Override public ServiceDeleteOutput call() throws Exception { - sendNotifications(ServicePathNotificationTypes.ServiceDelete, input.getServiceName(), + sendNotifications(ServicePathNotificationTypes.ServiceDelete, serviceName, RpcStatusEx.Pending, "Service compliant, submitting service delete Request ..."); // Obtain path description - Optional pathDescriptionOpt = getPathDescriptionFromDatastore(serviceName); + Optional< + org.opendaylight.yang.gen.v1.http.org.transportpce.b.c._interface.service.types.rev200128.service + .path.PathDescription> pathDescriptionOpt = getPathDescriptionFromDatastore(serviceName); PathDescription pathDescription; if (pathDescriptionOpt.isPresent()) { pathDescription = pathDescriptionOpt.get(); } else { LOG.error("Unable to get path description for service {}!", serviceName); - sendNotifications(ServicePathNotificationTypes.ServiceDelete, input.getServiceName(), + sendNotifications(ServicePathNotificationTypes.ServiceDelete, serviceName, RpcStatusEx.Failed, "Unable to get path description for service"); return ModelMappingUtils.createServiceDeleteResponse(ResponseCodes.RESPONSE_FAILED, OPERATION_FAILED); } - ServicePathInputData servicePathInputDataAtoZ = - ModelMappingUtils.rendererCreateServiceInputAToZ(serviceName, pathDescription); - ServicePathInputData servicePathInputDataZtoA = - ModelMappingUtils.rendererCreateServiceInputZToA(serviceName, pathDescription); - // OLM turn down power - try { - LOG.debug(TURNING_DOWN_POWER_ON_A_TO_Z_PATH_MSG); - sendNotifications(ServicePathNotificationTypes.ServiceDelete, - input.getServiceName(), RpcStatusEx.Pending, TURNING_DOWN_POWER_ON_A_TO_Z_PATH_MSG); - ServicePowerTurndownOutput atozPowerTurndownOutput = olmPowerTurndown(servicePathInputDataAtoZ); - // TODO add some flag rather than string - if (FAILED.equals(atozPowerTurndownOutput.getResult())) { - LOG.error("Service power turndown failed on A-to-Z path for service {}!", serviceName); - sendNotifications(ServicePathNotificationTypes.ServiceDelete, - input.getServiceName(), RpcStatusEx.Failed, - "Service power turndown failed on A-to-Z path for service"); - return ModelMappingUtils.createServiceDeleteResponse(ResponseCodes.RESPONSE_FAILED, - OPERATION_FAILED); - } - LOG.debug("Turning down power on Z-to-A path"); - sendNotifications(ServicePathNotificationTypes.ServiceDelete, input.getServiceName(), - RpcStatusEx.Pending, "Turning down power on Z-to-A path"); - ServicePowerTurndownOutput ztoaPowerTurndownOutput = olmPowerTurndown(servicePathInputDataZtoA); - // TODO add some flag rather than string - if (FAILED.equals(ztoaPowerTurndownOutput.getResult())) { - LOG.error("Service power turndown failed on Z-to-A path for service {}!", serviceName); - sendNotifications(ServicePathNotificationTypes.ServiceDelete, - input.getServiceName(), RpcStatusEx.Failed, - "Service power turndown failed on Z-to-A path for service"); - return ModelMappingUtils.createServiceDeleteResponse(ResponseCodes.RESPONSE_FAILED, - OPERATION_FAILED); + switch (service.getConnectionType()) { + case RoadmLine: + case Service: + if ((ServiceFormat.Ethernet.equals(service.getServiceAEnd().getServiceFormat()) + || ServiceFormat.OC.equals(service.getServiceAEnd().getServiceFormat())) + && Uint32.valueOf("100").equals(service.getServiceAEnd().getServiceRate())) { + if (!manageServicePathDeletion(serviceName, pathDescription)) { + return ModelMappingUtils.createServiceDeleteResponse(ResponseCodes.RESPONSE_FAILED, + OPERATION_FAILED); + } + } + if (ServiceFormat.Ethernet.equals(service.getServiceAEnd().getServiceFormat()) + && (Uint32.valueOf("10").equals(service.getServiceAEnd().getServiceRate()) + || Uint32.valueOf("1").equals(service.getServiceAEnd().getServiceRate()))) { + if (!manageOtnServicePathDeletion(serviceName, pathDescription, service)) { + return ModelMappingUtils.createServiceDeleteResponse(ResponseCodes.RESPONSE_FAILED, + OPERATION_FAILED); + } + } + break; + case Infrastructure: + if (ServiceFormat.OTU.equals(service.getServiceAEnd().getServiceFormat())) { + if (!manageServicePathDeletion(serviceName, pathDescription)) { + return ModelMappingUtils.createServiceDeleteResponse(ResponseCodes.RESPONSE_FAILED, + OPERATION_FAILED); + } + } else if (ServiceFormat.ODU.equals(service.getServiceAEnd().getServiceFormat())) { + if (!manageOtnServicePathDeletion(serviceName, pathDescription, service)) { + return ModelMappingUtils.createServiceDeleteResponse(ResponseCodes.RESPONSE_FAILED, + OPERATION_FAILED); + } + } + break; + default: + LOG.error("Unmanaged connection-type for deletion of service {}", serviceName); + break; } - } catch (InterruptedException | ExecutionException | TimeoutException e) { - LOG.error("Error while turning down power!", e); - return ModelMappingUtils.createServiceDeleteResponse(ResponseCodes.RESPONSE_FAILED, - OPERATION_FAILED); - } - // delete service path with renderer - LOG.debug("Deleting service path via renderer"); - sendNotifications(ServicePathNotificationTypes.ServiceDelete, input.getServiceName(), - RpcStatusEx.Pending, "Deleting service path via renderer"); - deviceRenderer.deleteServicePath(servicePathInputDataAtoZ.getServicePathInput()); - deviceRenderer.deleteServicePath(servicePathInputDataZtoA.getServicePathInput()); - networkModelWavelengthService.freeWavelengths(pathDescription); - sendNotifications(ServicePathNotificationTypes.ServiceDelete, input.getServiceName(), - RpcStatusEx.Successful, OPERATION_SUCCESSFUL); return ModelMappingUtils.createServiceDeleteResponse(ResponseCodes.RESPONSE_OK, OPERATION_SUCCESSFUL); } }); - - } @edu.umd.cs.findbugs.annotations.SuppressFBWarnings( @@ -455,9 +344,13 @@ public class RendererServiceOperationsImpl implements RendererServiceOperations @edu.umd.cs.findbugs.annotations.SuppressFBWarnings( value = "UPM_UNCALLED_PRIVATE_METHOD", justification = "call in call() method") - private Optional getPathDescriptionFromDatastore(String serviceName) { - InstanceIdentifier pathDescriptionIID = InstanceIdentifier.create(ServicePathList.class) - .child(ServicePaths.class, new ServicePathsKey(serviceName)).child(PathDescription.class); + private Optional getPathDescriptionFromDatastore(String serviceName) { + InstanceIdentifier pathDescriptionIID = InstanceIdentifier.create(ServicePathList.class) + .child(ServicePaths.class, new ServicePathsKey(serviceName)) + .child(org.opendaylight.yang.gen.v1.http.org.transportpce.b.c._interface.service.types.rev200128 + .service.path.PathDescription.class); ReadTransaction pathDescReadTx = this.dataBroker.newReadOnlyTransaction(); try { LOG.debug("Getting path description for service {}", serviceName); @@ -526,16 +419,18 @@ public class RendererServiceOperationsImpl implements RendererServiceOperations RENDERING_DEVICES_A_Z_MSG); ListenableFuture atozrenderingFuture = this.executor.submit(new OtnDeviceRenderingTask(this.otnDeviceRenderer, otnServicePathAtoZ)); - - LOG.info("Rendering devices Z-A"); - sendNotifications(ServicePathNotificationTypes.ServiceImplementationRequest, - otnServicePathZtoA.getServiceName(), RpcStatusEx.Pending, - RENDERING_DEVICES_Z_A_MSG); - ListenableFuture ztoarenderingFuture = - this.executor.submit(new OtnDeviceRenderingTask(this.otnDeviceRenderer, otnServicePathZtoA)); - ListenableFuture> renderingCombinedFuture = - Futures.allAsList(atozrenderingFuture, ztoarenderingFuture); - + ListenableFuture> renderingCombinedFuture; + if (otnServicePathZtoA != null) { + LOG.info("Rendering devices Z-A"); + sendNotifications(ServicePathNotificationTypes.ServiceImplementationRequest, + otnServicePathZtoA.getServiceName(), RpcStatusEx.Pending, + RENDERING_DEVICES_Z_A_MSG); + ListenableFuture ztoarenderingFuture = + this.executor.submit(new OtnDeviceRenderingTask(this.otnDeviceRenderer, otnServicePathZtoA)); + renderingCombinedFuture = Futures.allAsList(atozrenderingFuture, ztoarenderingFuture); + } else { + renderingCombinedFuture = Futures.allAsList(atozrenderingFuture); + } List otnRenderingResults = new ArrayList<>(2); try { LOG.info("Waiting for A-Z and Z-A device renderers ..."); @@ -548,17 +443,12 @@ public class RendererServiceOperationsImpl implements RendererServiceOperations //FIXME we can't do rollback here, because we don't have rendering results. return otnRenderingResults; } - - rollbackProcessor.addTask(new DeviceRenderingRollbackTask("AtoZDeviceTask", - ! otnRenderingResults.get(0).isSuccess(), otnRenderingResults.get(0).getRenderedNodeInterfaces(), - this.deviceRenderer)); - rollbackProcessor.addTask(new DeviceRenderingRollbackTask("ZtoADeviceTask", - ! otnRenderingResults.get(1).isSuccess(), otnRenderingResults.get(1).getRenderedNodeInterfaces(), - this.deviceRenderer)); - - + for (int i = 0; i < otnRenderingResults.size(); i++) { + rollbackProcessor.addTask(new DeviceRenderingRollbackTask("DeviceTask n° " + i + 1, + ! otnRenderingResults.get(i).isSuccess(), otnRenderingResults.get(i).getRenderedNodeInterfaces(), + this.deviceRenderer)); + } return otnRenderingResults; - } @edu.umd.cs.findbugs.annotations.SuppressFBWarnings( @@ -653,7 +543,6 @@ public class RendererServiceOperationsImpl implements RendererServiceOperations return null; } - private boolean verifyPreFecBer(List measurements) { double preFecCorrectedErrors = Double.MIN_VALUE; double fecUncorrectableBlocks = Double.MIN_VALUE; @@ -682,4 +571,142 @@ public class RendererServiceOperationsImpl implements RendererServiceOperations } } + @edu.umd.cs.findbugs.annotations.SuppressFBWarnings( + value = "UPM_UNCALLED_PRIVATE_METHOD", + justification = "call in call() method") + private boolean createServicepathInput(ServiceImplementationRequestInput input) { + ServicePathInputData servicePathInputDataAtoZ = ModelMappingUtils + .rendererCreateServiceInputAToZ(input.getServiceName(), input.getPathDescription()); + ServicePathInputData servicePathInputDataZtoA = ModelMappingUtils + .rendererCreateServiceInputZToA(input.getServiceName(), input.getPathDescription()); + // Rollback should be same for all conditions, so creating a new one + RollbackProcessor rollbackProcessor = new RollbackProcessor(); + List renderingResults = + deviceRendering(rollbackProcessor, servicePathInputDataAtoZ, servicePathInputDataZtoA); + if (rollbackProcessor.rollbackAllIfNecessary() > 0) { + sendNotifications(ServicePathNotificationTypes.ServiceImplementationRequest, + input.getServiceName(), RpcStatusEx.Failed, DEVICE_RENDERING_ROLL_BACK_MSG); + return false; + } + ServicePowerSetupInput olmPowerSetupInputAtoZ = + ModelMappingUtils.createServicePowerSetupInput(renderingResults.get(0).getOlmList(), input); + ServicePowerSetupInput olmPowerSetupInputZtoA = + ModelMappingUtils.createServicePowerSetupInput(renderingResults.get(1).getOlmList(), input); + olmPowerSetup(rollbackProcessor, olmPowerSetupInputAtoZ, olmPowerSetupInputZtoA); + if (rollbackProcessor.rollbackAllIfNecessary() > 0) { + sendNotifications(ServicePathNotificationTypes.ServiceImplementationRequest, + input.getServiceName(), RpcStatusEx.Failed, OLM_ROLL_BACK_MSG); + return false; + } + // run service activation test twice - once on source node and once on + // destination node + List nodes = servicePathInputDataAtoZ.getServicePathInput().getNodes(); + if ((nodes == null) || (nodes.isEmpty())) { + return false; + } + + Nodes sourceNode = nodes.get(0); + Nodes destNode = nodes.get(nodes.size() - 1); + String srcNetworkTp; + String dstNetowrkTp; + if (sourceNode.getDestTp().contains(StringConstants.NETWORK_TOKEN)) { + srcNetworkTp = sourceNode.getDestTp(); + } else { + srcNetworkTp = sourceNode.getSrcTp(); + } + if (destNode.getDestTp().contains(StringConstants.NETWORK_TOKEN)) { + dstNetowrkTp = destNode.getDestTp(); + } else { + dstNetowrkTp = destNode.getSrcTp(); + } + if (!isServiceActivated(sourceNode.getNodeId(), srcNetworkTp) + || !isServiceActivated(destNode.getNodeId(), dstNetowrkTp)) { + rollbackProcessor.rollbackAll(); + sendNotifications(ServicePathNotificationTypes.ServiceImplementationRequest, + input.getServiceName(), RpcStatusEx.Failed, + "Service activation test failed."); + return false; + } + // If Service activation is success update Network ModelMappingUtils + networkModelWavelengthService.useWavelengths(input.getPathDescription()); + sendNotifications(ServicePathNotificationTypes.ServiceImplementationRequest, + input.getServiceName(), RpcStatusEx.Successful, OPERATION_SUCCESSFUL); + return true; + } + + @edu.umd.cs.findbugs.annotations.SuppressFBWarnings( + value = "UPM_UNCALLED_PRIVATE_METHOD", + justification = "call in call() method") + private boolean manageServicePathDeletion(String serviceName, PathDescription pathDescription) { + ServicePathInputData servicePathInputDataAtoZ = + ModelMappingUtils.rendererCreateServiceInputAToZ(serviceName, pathDescription); + ServicePathInputData servicePathInputDataZtoA = + ModelMappingUtils.rendererCreateServiceInputZToA(serviceName, pathDescription); + // OLM turn down power + try { + LOG.debug(TURNING_DOWN_POWER_ON_A_TO_Z_PATH_MSG); + sendNotifications(ServicePathNotificationTypes.ServiceDelete, serviceName, + RpcStatusEx.Pending, TURNING_DOWN_POWER_ON_A_TO_Z_PATH_MSG); + ServicePowerTurndownOutput atozPowerTurndownOutput = olmPowerTurndown(servicePathInputDataAtoZ); + // TODO add some flag rather than string + if (FAILED.equals(atozPowerTurndownOutput.getResult())) { + LOG.error("Service power turndown failed on A-to-Z path for service {}!", serviceName); + sendNotifications(ServicePathNotificationTypes.ServiceDelete, serviceName, RpcStatusEx.Failed, + "Service power turndown failed on A-to-Z path for service"); + return false; + } + LOG.debug("Turning down power on Z-to-A path"); + sendNotifications(ServicePathNotificationTypes.ServiceDelete, serviceName, RpcStatusEx.Pending, + "Turning down power on Z-to-A path"); + ServicePowerTurndownOutput ztoaPowerTurndownOutput = olmPowerTurndown(servicePathInputDataZtoA); + // TODO add some flag rather than string + if (FAILED.equals(ztoaPowerTurndownOutput.getResult())) { + LOG.error("Service power turndown failed on Z-to-A path for service {}!", serviceName); + sendNotifications(ServicePathNotificationTypes.ServiceDelete, serviceName, RpcStatusEx.Failed, + "Service power turndown failed on Z-to-A path for service"); + return false; + } + } catch (InterruptedException | ExecutionException | TimeoutException e) { + LOG.error("Error while turning down power!", e); + return false; + } + // delete service path with renderer + LOG.info("Deleting service path via renderer"); + sendNotifications(ServicePathNotificationTypes.ServiceDelete, serviceName, RpcStatusEx.Pending, + "Deleting service path via renderer"); + deviceRenderer.deleteServicePath(servicePathInputDataAtoZ.getServicePathInput()); + deviceRenderer.deleteServicePath(servicePathInputDataZtoA.getServicePathInput()); + networkModelWavelengthService.freeWavelengths(pathDescription); + sendNotifications(ServicePathNotificationTypes.ServiceDelete, serviceName, RpcStatusEx.Successful, + OPERATION_SUCCESSFUL); + return true; + } + + @edu.umd.cs.findbugs.annotations.SuppressFBWarnings( + value = "UPM_UNCALLED_PRIVATE_METHOD", + justification = "call in call() method") + private boolean manageOtnServicePathDeletion(String serviceName, PathDescription pathDescription, + Services service) { + OtnServicePathInput ospi = null; + if (ConnectionType.Infrastructure.equals(service.getConnectionType())) { + ospi = ModelMappingUtils.rendererCreateOtnServiceInput( + serviceName, service.getServiceAEnd().getServiceFormat().getName(), "100G", pathDescription, true); + } else if (ConnectionType.Service.equals(service.getConnectionType())) { + ospi = ModelMappingUtils.rendererCreateOtnServiceInput(serviceName, + service.getServiceAEnd().getServiceFormat().getName(), + service.getServiceAEnd().getServiceRate().toString() + "G", pathDescription, true); + } + LOG.info("Deleting otn-service path {} via renderer", serviceName); + sendNotifications(ServicePathNotificationTypes.ServiceDelete, serviceName, RpcStatusEx.Pending, + "Deleting otn-service path via renderer"); + OtnServicePathOutput result = otnDeviceRenderer.deleteOtnServicePath(ospi); + if (result.isSuccess()) { + sendNotifications(ServicePathNotificationTypes.ServiceDelete, serviceName, RpcStatusEx.Successful, + OPERATION_SUCCESSFUL); + return true; + } else { + return false; + } + } + } diff --git a/renderer/src/main/java/org/opendaylight/transportpce/renderer/rpcs/TransportPCEServicePathRPCImpl.java b/renderer/src/main/java/org/opendaylight/transportpce/renderer/rpcs/TransportPCEServicePathRPCImpl.java index 4c18ceb7f..108abcd20 100644 --- a/renderer/src/main/java/org/opendaylight/transportpce/renderer/rpcs/TransportPCEServicePathRPCImpl.java +++ b/renderer/src/main/java/org/opendaylight/transportpce/renderer/rpcs/TransportPCEServicePathRPCImpl.java @@ -36,7 +36,7 @@ public class TransportPCEServicePathRPCImpl implements TransportpceRendererServi LOG.info("Calling RPC service delete request {}", serviceName); ServiceDeleteOutput output = null; try { - output = this.rendererServiceOperations.serviceDelete(input).get(); + output = this.rendererServiceOperations.serviceDelete(input, null).get(); } catch (InterruptedException | ExecutionException e) { LOG.error("RPC service delete failed !", e); } diff --git a/renderer/src/test/java/org/opendaylight/transportpce/renderer/provisiondevice/RendererServiceOperationsImplDeleteTest.java b/renderer/src/test/java/org/opendaylight/transportpce/renderer/provisiondevice/RendererServiceOperationsImplDeleteTest.java index d88a18213..c2b5374a6 100644 --- a/renderer/src/test/java/org/opendaylight/transportpce/renderer/provisiondevice/RendererServiceOperationsImplDeleteTest.java +++ b/renderer/src/test/java/org/opendaylight/transportpce/renderer/provisiondevice/RendererServiceOperationsImplDeleteTest.java @@ -59,6 +59,12 @@ import org.opendaylight.yang.gen.v1.http.org.opendaylight.transportpce.olm.rev17 import org.opendaylight.yang.gen.v1.http.org.opendaylight.transportpce.olm.rev170418.TransportpceOlmService; import org.opendaylight.yang.gen.v1.http.org.opendaylight.transportpce.renderer.rev200520.ServiceDeleteInputBuilder; import org.opendaylight.yang.gen.v1.http.org.opendaylight.transportpce.renderer.rev200520.ServiceDeleteOutput; +import org.opendaylight.yang.gen.v1.http.org.openroadm.common.service.types.rev190531.ConnectionType; +import org.opendaylight.yang.gen.v1.http.org.openroadm.common.service.types.rev190531.service.ServiceAEnd; +import org.opendaylight.yang.gen.v1.http.org.openroadm.common.service.types.rev190531.service.ServiceAEndBuilder; +import org.opendaylight.yang.gen.v1.http.org.openroadm.service.format.rev190531.ServiceFormat; +import org.opendaylight.yang.gen.v1.http.org.openroadm.service.rev190531.service.list.Services; +import org.opendaylight.yang.gen.v1.http.org.openroadm.service.rev190531.service.list.ServicesBuilder; import org.opendaylight.yang.gen.v1.http.org.transportpce.b.c._interface.service.types.rev200128.service.handler.header.ServiceHandlerHeaderBuilder; import org.opendaylight.yang.gen.v1.http.org.transportpce.b.c._interface.servicepath.rev171017.ServicePathList; import org.opendaylight.yang.gen.v1.http.org.transportpce.b.c._interface.servicepath.rev171017.service.path.list.ServicePaths; @@ -66,6 +72,7 @@ import org.opendaylight.yang.gen.v1.http.org.transportpce.b.c._interface.service import org.opendaylight.yang.gen.v1.http.org.transportpce.b.c._interface.servicepath.rev171017.service.path.list.ServicePathsKey; import org.opendaylight.yangtools.yang.binding.InstanceIdentifier; import org.opendaylight.yangtools.yang.common.RpcResultBuilder; +import org.opendaylight.yangtools.yang.common.Uint32; public class RendererServiceOperationsImplDeleteTest extends AbstractTest { @@ -149,8 +156,16 @@ public class RendererServiceOperationsImplDeleteTest extends AbstractTest { .setRequestId("request1").build()); Mockito.doReturn(Collections.emptyList()).when(this.crossConnect).deleteCrossConnect(Mockito.anyString(), Mockito.anyString(), Mockito.eq(false)); + ServiceAEnd serviceAEnd = new ServiceAEndBuilder() + .setServiceFormat(ServiceFormat.Ethernet) + .setServiceRate(Uint32.valueOf("100")) + .build(); + Services service = new ServicesBuilder() + .setConnectionType(ConnectionType.Service) + .setServiceAEnd(serviceAEnd) + .build(); ServiceDeleteOutput serviceDeleteOutput - = this.rendererServiceOperations.serviceDelete(serviceDeleteInputBuilder.build()).get(); + = this.rendererServiceOperations.serviceDelete(serviceDeleteInputBuilder.build(), service).get(); Assert.assertEquals(ResponseCodes.RESPONSE_OK, serviceDeleteOutput.getConfigurationResponseCommon().getResponseCode()); Mockito.verify(this.crossConnect, Mockito.times(2)) @@ -162,7 +177,7 @@ public class RendererServiceOperationsImplDeleteTest extends AbstractTest { ServiceDeleteInputBuilder serviceDeleteInputBuilder = new ServiceDeleteInputBuilder(); serviceDeleteInputBuilder.setServiceName("service 1"); ServiceDeleteOutput serviceDeleteOutput - = this.rendererServiceOperations.serviceDelete(serviceDeleteInputBuilder.build()).get(); + = this.rendererServiceOperations.serviceDelete(serviceDeleteInputBuilder.build(), null).get(); Assert.assertEquals(ResponseCodes.RESPONSE_FAILED, serviceDeleteOutput.getConfigurationResponseCommon().getResponseCode()); Mockito.verify(this.crossConnect, Mockito.times(0)) @@ -181,8 +196,16 @@ public class RendererServiceOperationsImplDeleteTest extends AbstractTest { serviceDeleteInputBuilder.setServiceName("service 1"); serviceDeleteInputBuilder.setServiceHandlerHeader((new ServiceHandlerHeaderBuilder()) .setRequestId("request1").build()); + ServiceAEnd serviceAEnd = new ServiceAEndBuilder() + .setServiceFormat(ServiceFormat.Ethernet) + .setServiceRate(Uint32.valueOf("100")) + .build(); + Services service = new ServicesBuilder() + .setConnectionType(ConnectionType.Service) + .setServiceAEnd(serviceAEnd) + .build(); ListenableFuture serviceDeleteOutput - = this.rendererServiceOperations.serviceDelete(serviceDeleteInputBuilder.build()); + = this.rendererServiceOperations.serviceDelete(serviceDeleteInputBuilder.build(), service); ServiceDeleteOutput output = serviceDeleteOutput.get(); Assert.assertEquals(ResponseCodes.RESPONSE_FAILED, output.getConfigurationResponseCommon().getResponseCode()); @@ -207,8 +230,16 @@ public class RendererServiceOperationsImplDeleteTest extends AbstractTest { serviceDeleteInputBuilder.setServiceName("service 1"); serviceDeleteInputBuilder.setServiceHandlerHeader((new ServiceHandlerHeaderBuilder()) .setRequestId("request1").build()); + ServiceAEnd serviceAEnd = new ServiceAEndBuilder() + .setServiceFormat(ServiceFormat.Ethernet) + .setServiceRate(Uint32.valueOf("100")) + .build(); + Services service = new ServicesBuilder() + .setConnectionType(ConnectionType.Service) + .setServiceAEnd(serviceAEnd) + .build(); ServiceDeleteOutput serviceDeleteOutput = - this.rendererServiceOperations.serviceDelete(serviceDeleteInputBuilder.build()).get(); + this.rendererServiceOperations.serviceDelete(serviceDeleteInputBuilder.build(), service).get(); Assert.assertEquals(ResponseCodes.RESPONSE_FAILED, serviceDeleteOutput.getConfigurationResponseCommon().getResponseCode()); Mockito.verify(this.olmService, Mockito.times(2)).servicePowerTurndown(Mockito.any()); diff --git a/renderer/src/test/java/org/opendaylight/transportpce/renderer/provisiondevice/RendererServiceOperationsImplTest.java b/renderer/src/test/java/org/opendaylight/transportpce/renderer/provisiondevice/RendererServiceOperationsImplTest.java index 41fd27677..34711af9b 100644 --- a/renderer/src/test/java/org/opendaylight/transportpce/renderer/provisiondevice/RendererServiceOperationsImplTest.java +++ b/renderer/src/test/java/org/opendaylight/transportpce/renderer/provisiondevice/RendererServiceOperationsImplTest.java @@ -356,7 +356,7 @@ public class RendererServiceOperationsImplTest extends AbstractTest { Mockito.when(this.olmService.getPm(Mockito.eq(getPmInputA))) .thenReturn(RpcResultBuilder.success(getPmOutput).buildFuture()); ServiceImplementationRequestOutput result = this.rendererServiceOperations.serviceImplementation(input).get(); - Assert.assertEquals(ResponseCodes.RESPONSE_FAILED, result.getConfigurationResponseCommon().getResponseCode()); + Assert.assertEquals(ResponseCodes.RESPONSE_OK, result.getConfigurationResponseCommon().getResponseCode()); } diff --git a/servicehandler/src/main/java/org/opendaylight/transportpce/servicehandler/ModelMappingUtils.java b/servicehandler/src/main/java/org/opendaylight/transportpce/servicehandler/ModelMappingUtils.java index b28441dfa..541fe8cc7 100644 --- a/servicehandler/src/main/java/org/opendaylight/transportpce/servicehandler/ModelMappingUtils.java +++ b/servicehandler/src/main/java/org/opendaylight/transportpce/servicehandler/ModelMappingUtils.java @@ -78,7 +78,7 @@ public final class ModelMappingUtils { public static ServiceImplementationRequestInput createServiceImplementationRequest(ServiceInput input, PathDescription pathDescription) { ServiceImplementationRequestInputBuilder serviceImplementationRequestInputBuilder = - new ServiceImplementationRequestInputBuilder(); + new ServiceImplementationRequestInputBuilder().setConnectionType(input.getConnectionType()); if (input.isServiceReconfigure()) { serviceImplementationRequestInputBuilder.setServiceName(input.getNewServiceName()); } else { @@ -90,6 +90,9 @@ public final class ModelMappingUtils { serviceAEnd.setServiceFormat(input.getServiceAEnd().getServiceFormat()) .setServiceRate(input.getServiceAEnd().getServiceRate()) + .setOtuServiceRate(input.getServiceAEnd().getOtuServiceRate()) + .setOduServiceRate(input.getServiceAEnd().getOduServiceRate()) + .setClli(input.getServiceAEnd().getClli()) .setOtuServiceRate(input.getServiceAEnd().getOtuServiceRate()) // set otu and odu .setOduServiceRate(input.getServiceZEnd().getOduServiceRate()) .setClli(input.getServiceAEnd().getClli()) @@ -105,6 +108,9 @@ public final class ModelMappingUtils { .transportpce.renderer.rev200520.service.implementation.request.input.ServiceZEndBuilder(); serviceZEnd.setServiceFormat(input.getServiceZEnd().getServiceFormat()) .setServiceRate(input.getServiceZEnd().getServiceRate()) + .setOtuServiceRate(input.getServiceZEnd().getOtuServiceRate()) + .setOduServiceRate(input.getServiceZEnd().getOduServiceRate()) + .setClli(input.getServiceZEnd().getClli()) .setOtuServiceRate(input.getServiceAEnd().getOtuServiceRate()) // set otu and odu .setOduServiceRate(input.getServiceZEnd().getOduServiceRate()) .setClli(input.getServiceZEnd().getClli()) diff --git a/servicehandler/src/main/java/org/opendaylight/transportpce/servicehandler/impl/ServicehandlerImpl.java b/servicehandler/src/main/java/org/opendaylight/transportpce/servicehandler/impl/ServicehandlerImpl.java index 006c360ad..834c8a62f 100644 --- a/servicehandler/src/main/java/org/opendaylight/transportpce/servicehandler/impl/ServicehandlerImpl.java +++ b/servicehandler/src/main/java/org/opendaylight/transportpce/servicehandler/impl/ServicehandlerImpl.java @@ -205,19 +205,21 @@ public class ServicehandlerImpl implements OrgOpenroadmServiceService { //Check presence of service to be deleted //TODO check if an expected bug was justifying this NPE handling // try { - Optional service = this.serviceDataStoreOperations.getService(serviceName); + Optional serviceOpt = this.serviceDataStoreOperations.getService(serviceName); // } catch (NullPointerException e) { // LOG.error("Something wrong when retrieving service '{}' from datastore : ", serviceName, e); // return ModelMappingUtils.createDeleteServiceReply( // input, ResponseCodes.FINAL_ACK_YES, // LogMessages.serviceNotInDS(serviceName), ResponseCodes.RESPONSE_FAILED); // } - if (!service.isPresent()) { + Services service; + if (!serviceOpt.isPresent()) { LOG.warn("serviceDelete: {}", LogMessages.serviceNotInDS(serviceName)); return ModelMappingUtils.createDeleteServiceReply( input, ResponseCodes.FINAL_ACK_YES, LogMessages.serviceNotInDS(serviceName), ResponseCodes.RESPONSE_FAILED); } + service = serviceOpt.get(); LOG.debug("serviceDelete: Service '{}' found in datastore", serviceName); this.pceListenerImpl.setInput(new ServiceInput(input)); this.pceListenerImpl.setServiceReconfigure(false); @@ -229,7 +231,7 @@ public class ServicehandlerImpl implements OrgOpenroadmServiceService { ModelMappingUtils.createServiceDeleteInput(new ServiceInput(input)); org.opendaylight.yang.gen.v1.http.org.opendaylight.transportpce.renderer.rev200520.ServiceDeleteOutput output = this.rendererServiceWrapper.performRenderer( - serviceDeleteInput, ServiceNotificationTypes.ServiceDeleteResult); + serviceDeleteInput, ServiceNotificationTypes.ServiceDeleteResult, service); if (output == null) { LOG.error("serviceDelete: {}", LogMessages.RENDERER_DELETE_FAILED); @@ -309,7 +311,7 @@ public class ServicehandlerImpl implements OrgOpenroadmServiceService { ModelMappingUtils.createServiceDeleteInput(new ServiceInput(input)); org.opendaylight.yang.gen.v1.http.org.opendaylight.transportpce.renderer.rev200520 .ServiceDeleteOutput output = this.rendererServiceWrapper.performRenderer(serviceDeleteInput, - ServiceNotificationTypes.ServiceDeleteResult); + ServiceNotificationTypes.ServiceDeleteResult, null); if (output == null) { LOG.error("serviceReconfigure: {}", LogMessages.RENDERER_DELETE_FAILED); return ModelMappingUtils.createCreateServiceReply( @@ -389,7 +391,7 @@ public class ServicehandlerImpl implements OrgOpenroadmServiceService { new ServiceInput(deleteInputBldr.build())); org.opendaylight.yang.gen.v1.http.org.opendaylight.transportpce.renderer.rev200520 .ServiceDeleteOutput output = this.rendererServiceWrapper.performRenderer(serviceDeleteInput, - ServiceNotificationTypes.ServiceDeleteResult); + ServiceNotificationTypes.ServiceDeleteResult, null); if (output == null) { LOG.error("serviceRestoration: {}", LogMessages.RENDERER_DELETE_FAILED); return ModelMappingUtils.createRestoreServiceReply( @@ -455,7 +457,7 @@ public class ServicehandlerImpl implements OrgOpenroadmServiceService { new ServiceInput(deleteInputBldr.build())); org.opendaylight.yang.gen.v1.http.org.opendaylight.transportpce.renderer.rev200520 .ServiceDeleteOutput output = this.rendererServiceWrapper.performRenderer(serviceDeleteInput, - ServiceNotificationTypes.ServiceDeleteResult); + ServiceNotificationTypes.ServiceDeleteResult, null); if (output == null) { LOG.error("serviceReroute: {}", LogMessages.RENDERER_DELETE_FAILED); return ModelMappingUtils.createRerouteServiceReply( diff --git a/servicehandler/src/main/java/org/opendaylight/transportpce/servicehandler/service/RendererServiceWrapper.java b/servicehandler/src/main/java/org/opendaylight/transportpce/servicehandler/service/RendererServiceWrapper.java index 2b09d32ca..0bf493638 100644 --- a/servicehandler/src/main/java/org/opendaylight/transportpce/servicehandler/service/RendererServiceWrapper.java +++ b/servicehandler/src/main/java/org/opendaylight/transportpce/servicehandler/service/RendererServiceWrapper.java @@ -26,6 +26,7 @@ import org.opendaylight.yang.gen.v1.http.org.openroadm.common.service.types.rev1 import org.opendaylight.yang.gen.v1.http.org.openroadm.common.service.types.rev190531.configuration.response.common.ConfigurationResponseCommon; import org.opendaylight.yang.gen.v1.http.org.openroadm.common.service.types.rev190531.configuration.response.common.ConfigurationResponseCommonBuilder; import org.opendaylight.yang.gen.v1.http.org.openroadm.service.rev190531.TempServiceDeleteInput; +import org.opendaylight.yang.gen.v1.http.org.openroadm.service.rev190531.service.list.Services; import org.opendaylight.yang.gen.v1.http.org.transportpce.b.c._interface.service.types.rev200128.RpcStatusEx; import org.opendaylight.yang.gen.v1.http.org.transportpce.b.c._interface.service.types.rev200128.service.handler.header.ServiceHandlerHeader; import org.opendaylight.yang.gen.v1.http.org.transportpce.b.c._interface.service.types.rev200128.service.handler.header.ServiceHandlerHeaderBuilder; @@ -62,10 +63,10 @@ public class RendererServiceWrapper { } public ServiceDeleteOutput performRenderer(ServiceDeleteInput serviceDeleteInput, - ServiceNotificationTypes notifType) { + ServiceNotificationTypes notifType, Services service) { if (validateParams(serviceDeleteInput.getServiceName(), serviceDeleteInput.getServiceHandlerHeader(), false)) { return performRenderer(serviceDeleteInput.getServiceName(), serviceDeleteInput.getServiceHandlerHeader(), - ServiceNotificationTypes.ServiceDeleteResult); + ServiceNotificationTypes.ServiceDeleteResult, service); } else { return returnRendererFailed(); } @@ -77,14 +78,14 @@ public class RendererServiceWrapper { if (validateParams(commonId, null, true)) { ServiceHandlerHeader serviceHandler = new ServiceHandlerHeaderBuilder().setRequestId(commonId).build(); return performRenderer(tempServiceDeleteInput.getCommonId(), serviceHandler, - ServiceNotificationTypes.ServiceDeleteResult); + ServiceNotificationTypes.ServiceDeleteResult, null); } else { return returnRendererFailed(); } } private ServiceDeleteOutput performRenderer(String serviceName, ServiceHandlerHeader serviceHandlerHeader, - ServiceNotificationTypes notifType) { + ServiceNotificationTypes notifType, Services service) { notification = new ServiceRpcResultShBuilder().setNotificationType(notifType).setServiceName(serviceName) .setStatus(RpcStatusEx.Pending) .setStatusMessage("Service compliant, submitting temp service delete Request ...").build(); @@ -127,7 +128,7 @@ public class RendererServiceWrapper { }; ServiceDeleteInput serviceDeleteInput = createRendererRequestInput(serviceName, serviceHandlerHeader); ListenableFuture renderer = - this.rendererServiceOperations.serviceDelete(serviceDeleteInput); + this.rendererServiceOperations.serviceDelete(serviceDeleteInput, service); Futures.addCallback(renderer, rendererCallback, executor); ConfigurationResponseCommon value = new ConfigurationResponseCommonBuilder().setAckFinalIndicator(ResponseCodes.FINAL_ACK_NO) diff --git a/servicehandler/src/test/java/org/opendaylight/transportpce/servicehandler/impl/ServicehandlerImplTest.java b/servicehandler/src/test/java/org/opendaylight/transportpce/servicehandler/impl/ServicehandlerImplTest.java index 38b414903..a7e139c21 100644 --- a/servicehandler/src/test/java/org/opendaylight/transportpce/servicehandler/impl/ServicehandlerImplTest.java +++ b/servicehandler/src/test/java/org/opendaylight/transportpce/servicehandler/impl/ServicehandlerImplTest.java @@ -185,7 +185,7 @@ public class ServicehandlerImplTest extends AbstractTest { @Test public void deleteServiceShouldBeSuccessForExistingService() throws ExecutionException, InterruptedException { DataBroker dataBroker = getNewDataBroker(); - Mockito.when(rendererServiceOperations.serviceDelete(any())).thenReturn(Futures.immediateFuture(any())); + Mockito.when(rendererServiceOperations.serviceDelete(any(), any())).thenReturn(Futures.immediateFuture(any())); ServicehandlerImpl servicehandlerImpl = new ServicehandlerImpl(dataBroker, pathComputationService, rendererServiceOperations, notificationPublishService, pceListenerImpl, rendererListenerImpl, null); @@ -312,7 +312,7 @@ public class ServicehandlerImplTest extends AbstractTest { //mocking // serviceReconfigure is calling service delete method in renderer - Mockito.when(rendererServiceOperations.serviceDelete(any())).thenReturn(Futures.immediateFuture(any())); + Mockito.when(rendererServiceOperations.serviceDelete(any(), any())).thenReturn(Futures.immediateFuture(any())); //create service to reconfigure ServicehandlerImpl servicehandlerImpl = new ServicehandlerImpl(dataBroker, pathComputationService, rendererServiceOperations, @@ -395,7 +395,7 @@ public class ServicehandlerImplTest extends AbstractTest { //mocking // serviceRestoration is calling service delete method in renderer - Mockito.when(rendererServiceOperations.serviceDelete(any())).thenReturn(Futures.immediateFuture(any())); + Mockito.when(rendererServiceOperations.serviceDelete(any(), any())).thenReturn(Futures.immediateFuture(any())); //create service to restore ServicehandlerImpl servicehandlerImpl = new ServicehandlerImpl(dataBroker, pathComputationService, rendererServiceOperations, @@ -477,7 +477,7 @@ public class ServicehandlerImplTest extends AbstractTest { //mocking // serviceReroute is calling service delete method in renderer - Mockito.when(rendererServiceOperations.serviceDelete(any())).thenReturn(Futures.immediateFuture(any())); + Mockito.when(rendererServiceOperations.serviceDelete(any(), any())).thenReturn(Futures.immediateFuture(any())); //create service to be rerouted later ServicehandlerImpl servicehandlerImpl = new ServicehandlerImpl(dataBroker, pathComputationService, rendererServiceOperations, @@ -556,7 +556,7 @@ public class ServicehandlerImplTest extends AbstractTest { @Test public void tempServiceDeleteShouldBeSuccessForExistingService() throws ExecutionException, InterruptedException { DataBroker dataBroker = getNewDataBroker(); - Mockito.when(rendererServiceOperations.serviceDelete(any())).thenReturn(Futures.immediateFuture(any())); + Mockito.when(rendererServiceOperations.serviceDelete(any(), any())).thenReturn(Futures.immediateFuture(any())); //create temp service to delete in the temp delete action ServicehandlerImpl servicehandlerImpl = diff --git a/servicehandler/src/test/java/org/opendaylight/transportpce/servicehandler/service/RendererServiceWrapperTest.java b/servicehandler/src/test/java/org/opendaylight/transportpce/servicehandler/service/RendererServiceWrapperTest.java index 7fe09e210..11e61cbd7 100644 --- a/servicehandler/src/test/java/org/opendaylight/transportpce/servicehandler/service/RendererServiceWrapperTest.java +++ b/servicehandler/src/test/java/org/opendaylight/transportpce/servicehandler/service/RendererServiceWrapperTest.java @@ -63,7 +63,7 @@ public class RendererServiceWrapperTest extends AbstractTest { ModelMappingUtils.createServiceDeleteInput(new ServiceInput(input)); serviceDeleteInput = new ServiceDeleteInputBuilder(serviceDeleteInput).setServiceHandlerHeader(null).build(); ServiceDeleteOutput response = this.rendererServiceWrapperMock.performRenderer(serviceDeleteInput, - ServiceNotificationTypes.ServiceDeleteResult); + ServiceNotificationTypes.ServiceDeleteResult, null); Assert.assertEquals(ResponseCodes.FINAL_ACK_YES, response.getConfigurationResponseCommon().getAckFinalIndicator()); Assert.assertEquals(ResponseCodes.RESPONSE_FAILED, @@ -79,7 +79,7 @@ public class RendererServiceWrapperTest extends AbstractTest { ModelMappingUtils.createServiceDeleteInput(new ServiceInput(input)); serviceDeleteInput = new ServiceDeleteInputBuilder(serviceDeleteInput).setServiceName(null).build(); ServiceDeleteOutput response = this.rendererServiceWrapperMock.performRenderer(serviceDeleteInput, - ServiceNotificationTypes.ServiceDeleteResult); + ServiceNotificationTypes.ServiceDeleteResult, null); Assert.assertEquals(ResponseCodes.FINAL_ACK_YES, response.getConfigurationResponseCommon().getAckFinalIndicator()); Assert.assertEquals(ResponseCodes.RESPONSE_FAILED, @@ -112,13 +112,13 @@ public class RendererServiceWrapperTest extends AbstractTest { ListenableFuture response = ServiceDataUtils.returnFuture(output); Mockito.when(this.rendererServiceOperationsMock.serviceDelete(any( org.opendaylight.yang.gen.v1.http.org.opendaylight.transportpce.renderer.rev200520 - .ServiceDeleteInput.class))).thenReturn(response); + .ServiceDeleteInput.class), any())).thenReturn(response); ServiceDeleteInput input = ServiceDataUtils.buildServiceDeleteInput(); org.opendaylight.yang.gen.v1.http.org.opendaylight.transportpce.renderer.rev200520.ServiceDeleteInput serviceDeleteInput = ModelMappingUtils.createServiceDeleteInput(new ServiceInput(input)); ServiceDeleteOutput rendereResponse = this.rendererServiceWrapperMock.performRenderer(serviceDeleteInput, - ServiceNotificationTypes.ServiceDeleteResult); + ServiceNotificationTypes.ServiceDeleteResult, null); Assert.assertEquals(ResponseCodes.FINAL_ACK_NO, rendereResponse.getConfigurationResponseCommon().getAckFinalIndicator()); Assert.assertEquals(ResponseCodes.RESPONSE_OK, @@ -127,7 +127,7 @@ public class RendererServiceWrapperTest extends AbstractTest { rendereResponse.getConfigurationResponseCommon().getResponseMessage()); verify(this.rendererServiceOperationsMock).serviceDelete(any( org.opendaylight.yang.gen.v1.http.org.opendaylight.transportpce.renderer.rev200520 - .ServiceDeleteInput.class)); + .ServiceDeleteInput.class), any()); } @Test @@ -141,7 +141,7 @@ public class RendererServiceWrapperTest extends AbstractTest { ListenableFuture response = ServiceDataUtils.returnFuture(output); Mockito.when(this.rendererServiceOperationsMock.serviceDelete(any( org.opendaylight.yang.gen.v1.http.org.opendaylight.transportpce.renderer.rev200520 - .ServiceDeleteInput.class))).thenReturn(response); + .ServiceDeleteInput.class), any())).thenReturn(response); TempServiceDeleteInput input = ServiceDataUtils.buildTempServiceDeleteInput(); ServiceDeleteOutput rendereResponse = this.rendererServiceWrapperMock.performRenderer(input, ServiceNotificationTypes.ServiceDeleteResult); @@ -153,6 +153,6 @@ public class RendererServiceWrapperTest extends AbstractTest { rendereResponse.getConfigurationResponseCommon().getResponseMessage()); verify(this.rendererServiceOperationsMock).serviceDelete(any( org.opendaylight.yang.gen.v1.http.org.opendaylight.transportpce.renderer.rev200520.ServiceDeleteInput - .class)); + .class), any()); } } diff --git a/tests/transportpce_tests/2.2.1/test_otn_sh_renderer.py b/tests/transportpce_tests/2.2.1/test_otn_sh_renderer.py index b87bcb95f..71fb7b794 100644 --- a/tests/transportpce_tests/2.2.1/test_otn_sh_renderer.py +++ b/tests/transportpce_tests/2.2.1/test_otn_sh_renderer.py @@ -93,15 +93,29 @@ class TransportPCEtesting(unittest.TestCase): "id": "0", "resource": { "tp-node-id": "SPDR-SA1-XPDR1", - "tp-id": "XPDR1-NETWORK1" + "tp-id": "" } }, { "id": "1", + "resource": { + "tp-node-id": "SPDR-SA1-XPDR1", + "tp-id": "XPDR1-NETWORK1" + } + }, + { + "id": "2", "resource": { "tp-node-id": "SPDR-SC1-XPDR1", "tp-id": "XPDR1-NETWORK1" } + }, + { + "id": "3", + "resource": { + "tp-node-id": "SPDR-SC1-XPDR1", + "tp-id": "" + } } ] }, @@ -114,15 +128,29 @@ class TransportPCEtesting(unittest.TestCase): "id": "0", "resource": { "tp-node-id": "SPDR-SC1-XPDR1", - "tp-id": "XPDR1-NETWORK1" + "tp-id": "" } }, { "id": "1", + "resource": { + "tp-node-id": "SPDR-SC1-XPDR1", + "tp-id": "XPDR1-NETWORK1" + } + }, + { + "id": "2", "resource": { "tp-node-id": "SPDR-SA1-XPDR1", "tp-id": "XPDR1-NETWORK1" } + }, + { + "id": "3", + "resource": { + "tp-node-id": "SPDR-SA1-XPDR1", + "tp-id": "" + } } ] } @@ -270,6 +298,13 @@ class TransportPCEtesting(unittest.TestCase): "aToZ-direction": { "rate": 100, "aToZ": [ + { + "id": "0", + "resource": { + "tp-node-id": "SPDR-SA1-XPDR1", + "tp-id": "" + } + }, { "id": "1", "resource": { @@ -283,12 +318,26 @@ class TransportPCEtesting(unittest.TestCase): "tp-node-id": "SPDR-SC1-XPDR1", "tp-id": "XPDR1-NETWORK1" } + }, + { + "id": "3", + "resource": { + "tp-node-id": "SPDR-SC1-XPDR1", + "tp-id": "" + } } ] }, "transportpce-renderer:zToA-direction": { "transportpce-renderer:rate": "100", "zToA": [ + { + "id": "0", + "resource": { + "tp-node-id": "SPDR-SC1-XPDR1", + "tp-id": "" + } + }, { "id": "1", "resource": { @@ -302,6 +351,13 @@ class TransportPCEtesting(unittest.TestCase): "tp-node-id": "SPDR-SA1-XPDR1", "tp-id": "XPDR1-NETWORK1" } + }, + { + "id": "3", + "resource": { + "tp-node-id": "SPDR-SA1-XPDR1", + "tp-id": "" + } } ] } @@ -397,7 +453,6 @@ class TransportPCEtesting(unittest.TestCase): "transportpce-renderer:service-rate": "10", "transportpce-renderer:clli": "nodeSA", "transportpce-renderer:node-id": "SPDR-SA1" - }, "transportpce-renderer:service-z-end": { "transportpce-renderer:service-format": "Ethernet", @@ -408,6 +463,8 @@ class TransportPCEtesting(unittest.TestCase): "transportpce-renderer:path-description": { "aToZ-direction": { "rate": 10, + "trib-port-number": 1, + "trib-slot-number": 1, "aToZ": [ { "id": "0", @@ -441,7 +498,9 @@ class TransportPCEtesting(unittest.TestCase): ] }, "transportpce-renderer:zToA-direction": { - "transportpce-renderer:rate": "10", + "rate": "10", + "trib-port-number": 1, + "trib-slot-number": 1, "zToA": [ { "id": "0",