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.*
@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) {
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);
// 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
+ }
}