Fix for Bug 271
[controller.git] / opendaylight / md-sal / compatibility / sal-compatibility / src / main / java / org / opendaylight / controller / sal / compatibility / FlowProgrammerAdapter.xtend
index 7d9c93908ec8484d502d6ab91d1bd26080c631cb..450c7f1f239c4634b994fd6b71b941492321d8b4 100644 (file)
@@ -9,13 +9,33 @@ import org.opendaylight.controller.sal.utils.Status
 import org.opendaylight.controller.sal.utils.StatusCode
 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.service.rev130819.FlowAdded
 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.service.rev130819.FlowRemoved
+import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.service.rev130819.SwitchFlowRemoved
 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.service.rev130819.FlowUpdated
 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.service.rev130819.SalFlowListener
 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.service.rev130819.SalFlowService
+import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.service.rev130819.NodeErrorNotification
+import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.service.rev130819.NodeExperimenterErrorNotification
 import org.opendaylight.yangtools.yang.common.RpcResult
 import org.slf4j.LoggerFactory
 
-import static org.opendaylight.controller.sal.compatibility.MDFlowMapping.*
+import org.opendaylight.controller.sal.binding.api.data.DataBrokerService
+import org.opendaylight.controller.md.sal.common.api.TransactionStatus
+import org.opendaylight.controller.md.sal.common.api.data.DataModification
+import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.FlowCapableNode
+import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.tables.Table
+import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.tables.TableKey
+import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.tables.table.FlowKey
+import org.opendaylight.yang.gen.v1.urn.opendaylight.inventory.rev130819.Nodes
+import org.opendaylight.yang.gen.v1.urn.opendaylight.inventory.rev130819.nodes.NodeKey
+import org.opendaylight.yangtools.yang.binding.DataObject
+import org.opendaylight.yangtools.yang.binding.InstanceIdentifier
+import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.service.rev130819.AddFlowInput
+import org.opendaylight.yang.gen.v1.urn.opendaylight.inventory.rev130819.NodeId
+import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.tables.table.FlowKey
+import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.FlowId
+
+
+import static extension org.opendaylight.controller.sal.compatibility.MDFlowMapping.*
 
 import static extension org.opendaylight.controller.sal.compatibility.NodeMapping.*
 import static extension org.opendaylight.controller.sal.compatibility.ToSalConversionsUtils.*
@@ -26,64 +46,52 @@ class FlowProgrammerAdapter implements IPluginInFlowProgrammerService, SalFlowLi
 
     @Property
     private SalFlowService delegate;
+
+    @Property
+    private DataBrokerService dataBrokerService;
     
     @Property
     private IPluginOutFlowProgrammerService flowProgrammerPublisher;
 
     override addFlow(Node node, Flow flow) {
-        val input = addFlowInput(node, flow);
-        val future = delegate.addFlow(input);
-        try {
-            val result = future.get();
-            return toStatus(result); // how get status from result? conversion?
-        } catch (Exception e) {
-            return processException(e);
-        }
+        return addFlowAsync(node,flow,0)
     }
 
     override modifyFlow(Node node, Flow oldFlow, Flow newFlow) {
-        val input = updateFlowInput(node, oldFlow, newFlow);
-        val future = delegate.updateFlow(input);
-        try {
-            val result = future.get();
-            return toStatus(result);
-        } catch (Exception e) {
-            return processException(e);
-        }
+        return modifyFlowAsync(node, oldFlow,newFlow,0)
     }
 
     override removeFlow(Node node, Flow flow) {
-        val input = removeFlowInput(node, flow);
-        val future = delegate.removeFlow(input);
-
-        try {
-            val result = future.get();
-            return toStatus(result);
-        } catch (Exception e) {
-            return processException(e);
-        }
+        return removeFlowAsync(node, flow,0);
     }
 
     override addFlowAsync(Node node, Flow flow, long rid) {
-        val input = addFlowInput(node, flow);
-        delegate.addFlow(input);
-        return new Status(StatusCode.SUCCESS);
+        writeFlow(flow.toMDFlow, new NodeKey(new NodeId(node.getNodeIDString())));
+        return toStatus(true);
     }
 
     override modifyFlowAsync(Node node, Flow oldFlow, Flow newFlow, long rid) {
-        val input = updateFlowInput(node, oldFlow, newFlow);
-        delegate.updateFlow(input);
-        return new Status(StatusCode.SUCCESS);
+        writeFlow(newFlow.toMDFlow, new NodeKey(new NodeId(node.getNodeIDString())));
+        return toStatus(true);
     }
 
-    override removeFlowAsync(Node node, Flow flow, long rid) {
-        val input = removeFlowInput(node, flow);
-        delegate.removeFlow(input);
-        return new Status(StatusCode.SUCCESS);
+    override removeFlowAsync(Node node, Flow adflow, long rid) {
+        val flow = adflow.toMDFlow;
+        val modification = this._dataBrokerService.beginTransaction();
+        val flowPath = InstanceIdentifier.builder(Nodes)
+                .child(org.opendaylight.yang.gen.v1.urn.opendaylight.inventory.rev130819.nodes.Node, new NodeKey(new NodeId(node.getNodeIDString())))
+                .augmentation(FlowCapableNode)
+                .child(Table, new TableKey(flow.getTableId()))
+                .child(org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.tables.table.Flow, new FlowKey(flow.id))
+                .build;
+        modification.removeConfigurationData(flowPath);
+        val commitFuture = modification.commit();
+        return toStatus(true);
     }
 
     override removeAllFlows(Node node) {
-        throw new UnsupportedOperationException("Not present in MD-SAL");
+        // I know this looks like a copout... but its exactly what the legacy OFplugin did
+        return new Status(StatusCode.SUCCESS);
     }
 
     override syncSendBarrierMessage(Node node) {
@@ -98,13 +106,38 @@ class FlowProgrammerAdapter implements IPluginInFlowProgrammerService, SalFlowLi
         return null;
     }
 
-    public static def toStatus(RpcResult<?> result) {
-        if (result.isSuccessful()) {
+    private static def toStatus(boolean successful) {
+        if (successful) {
             return new Status(StatusCode.SUCCESS);
         } else {
             return new Status(StatusCode.INTERNALERROR);
         }
     }
+
+
+    private def writeFlow(org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.tables.table.Flow flow, NodeKey nodeKey) {
+        val modification = this._dataBrokerService.beginTransaction();
+        val flowPath = InstanceIdentifier.builder(Nodes)
+                .child(org.opendaylight.yang.gen.v1.urn.opendaylight.inventory.rev130819.nodes.Node, nodeKey)
+                .augmentation(FlowCapableNode)
+                .child(Table, new TableKey(flow.getTableId()))
+                .child(org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.tables.table.Flow, new FlowKey(flow.id))
+                .build;
+        modification.putConfigurationData(flowPath, flow);
+        val commitFuture = modification.commit();
+        try {
+            val result = commitFuture.get();
+            val status = result.getResult();
+        } catch (InterruptedException e) {
+            LOG.error(e.getMessage(), e);
+        } catch (ExecutionException e) {
+            LOG.error(e.getMessage(), e);
+        }
+    }
+
+    public static def toStatus(RpcResult<?> result) {
+        return toStatus(result.isSuccessful());
+    }
     
     private static dispatch def Status processException(InterruptedException e) {
         LOG.error("Interruption occured during processing flow",e);
@@ -132,4 +165,16 @@ class FlowProgrammerAdapter implements IPluginInFlowProgrammerService, SalFlowLi
         // NOOP : Not supported by AD SAL
     }
     
+    override onSwitchFlowRemoved(SwitchFlowRemoved notification) {
+        // NOOP : Not supported by AD SAL
+    }
+    
+     override onNodeErrorNotification(NodeErrorNotification notification) {
+        // NOOP : Not supported by AD SAL
+    }
+    
+     override onNodeExperimenterErrorNotification(
+                NodeExperimenterErrorNotification notification) {
+        // NOOP : Not supported by AD SAL
+    }
 }