Merge "Bug 8293: Add table writer to bulk-o-matic"
[openflowplugin.git] / applications / bulk-o-matic / src / main / java / org / opendaylight / openflowplugin / applications / bulk / o / matic / FlowReader.java
1 /*
2  * Copyright (c) 2016 Ericsson Systems, Inc. and others.  All rights reserved.
3  *
4  * This program and the accompanying materials are made available under the
5  * terms of the Eclipse Public License v1.0 which accompanies this distribution,
6  * and is available at http://www.eclipse.org/legal/epl-v10.html
7  */
8 package org.opendaylight.openflowplugin.applications.bulk.o.matic;
9
10 import com.google.common.base.Optional;
11 import java.util.concurrent.atomic.AtomicInteger;
12 import java.util.concurrent.atomic.AtomicLong;
13 import org.opendaylight.controller.md.sal.binding.api.DataBroker;
14 import org.opendaylight.controller.md.sal.binding.api.ReadOnlyTransaction;
15 import org.opendaylight.controller.md.sal.common.api.data.LogicalDatastoreType;
16 import org.opendaylight.controller.md.sal.common.api.data.ReadFailedException;
17 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.FlowCapableNode;
18 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.FlowId;
19 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.tables.Table;
20 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.tables.TableKey;
21 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.tables.table.Flow;
22 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.tables.table.FlowKey;
23 import org.opendaylight.yang.gen.v1.urn.opendaylight.inventory.rev130819.NodeId;
24 import org.opendaylight.yang.gen.v1.urn.opendaylight.inventory.rev130819.Nodes;
25 import org.opendaylight.yang.gen.v1.urn.opendaylight.inventory.rev130819.nodes.Node;
26 import org.opendaylight.yang.gen.v1.urn.opendaylight.inventory.rev130819.nodes.NodeKey;
27 import org.opendaylight.yangtools.yang.binding.InstanceIdentifier;
28 import org.slf4j.Logger;
29 import org.slf4j.LoggerFactory;
30
31 public class FlowReader implements Runnable, FlowCounterMBean {
32     private static final Logger LOG = LoggerFactory.getLogger(FlowReader.class);
33     private final DataBroker dataBroker;
34     private final Integer dpnCount;
35     private final boolean verbose;
36     private final int flowsPerDpn;
37     private final short startTableId;
38     private final short endTableId;
39     private final boolean isConfigDs;
40     private AtomicLong flowCount = new AtomicLong();
41     private AtomicInteger readOpStatus = new AtomicInteger(FlowCounter.OperationStatus.INIT.status());
42
43     private FlowReader(final DataBroker dataBroker,
44                       final Integer dpnCount,
45                       final int flowsPerDpn,
46                       final boolean verbose,
47                       final boolean isConfigDs,
48                       final short startTableId,
49                       final short endTableId) {
50         this.dataBroker = dataBroker;
51         this.dpnCount = dpnCount;
52         this.verbose = verbose;
53         this.flowsPerDpn = flowsPerDpn;
54         this.startTableId = startTableId;
55         this.endTableId = endTableId;
56         this.isConfigDs = isConfigDs;
57     }
58
59     public static FlowReader getNewInstance(final DataBroker dataBroker,
60                                       final Integer dpnCount,
61                                       final int flowsPerDpn,
62                                       final boolean verbose,
63                                       final boolean isConfigDs,
64                                       final short startTableId,
65                                       final short endTableId) {
66         return new FlowReader(dataBroker, dpnCount, flowsPerDpn, verbose,
67                 isConfigDs, startTableId, endTableId);
68     }
69
70     @Override
71     public void run() {
72         readFlowsX(dpnCount, flowsPerDpn, verbose);
73     }
74
75     private void readFlowsX(Integer dpnCount, Integer flowsPerDPN, boolean verbose) {
76         readOpStatus.set(FlowCounter.OperationStatus.IN_PROGRESS.status());
77         for (int i = 1; i <= dpnCount; i++) {
78             String dpId = BulkOMaticUtils.DEVICE_TYPE_PREFIX + i;
79             for (int j = 0; j < flowsPerDPN; j++) {
80                 short tableRollover = (short)(endTableId - startTableId + 1);
81                 short tableId = (short) (((j) % tableRollover) + startTableId);
82
83                 Integer sourceIp = j + 1;
84
85                 String flowId = "Flow-" + dpId + "." + tableId + "." + sourceIp;
86                 InstanceIdentifier<Flow> flowIid = getFlowInstanceIdentifier(dpId, tableId, flowId);
87
88                 ReadOnlyTransaction readOnlyTransaction = dataBroker.newReadOnlyTransaction();
89                 try {
90                     Optional<Flow> flowOptional;
91                     if(isConfigDs) {
92                         flowOptional = readOnlyTransaction.read(LogicalDatastoreType.CONFIGURATION, flowIid).checkedGet();
93                     } else {
94                         flowOptional = readOnlyTransaction.read(LogicalDatastoreType.OPERATIONAL, flowIid).checkedGet();
95                     }
96
97                     if (flowOptional.isPresent()) {
98                         flowCount.incrementAndGet();
99                         if (verbose) {
100                             LOG.info("Flow found: {}", flowOptional.get());
101                         }
102                     } else {
103                         if (verbose) {
104                             LOG.info("Flow: {} not found", flowIid);
105                         }
106                     }
107                 } catch (ReadFailedException e) {
108                     readOpStatus.set(FlowCounter.OperationStatus.FAILURE.status());
109                     LOG.error(e.getMessage(), e);
110                 }
111             }
112         }
113         if(readOpStatus.get() != FlowCounter.OperationStatus.FAILURE.status()) {
114             readOpStatus.set(FlowCounter.OperationStatus.SUCCESS.status());
115         }
116         LOG.info("Total Flows read: {}", flowCount);
117     }
118
119     private InstanceIdentifier<Flow> getFlowInstanceIdentifier(String dpId, Short tableId, String flowId){
120         return InstanceIdentifier.create(Nodes.class).child(Node.class, new NodeKey(new NodeId(dpId)))
121                 .augmentation(FlowCapableNode.class)
122                 .child(Table.class, new TableKey(tableId))
123                 .child(Flow.class,
124                         new FlowKey(new FlowId(flowId)));
125     }
126
127     @Override
128     public long getFlowCount() {
129         return flowCount.get();
130     }
131
132     @Override
133     public int getReadOpStatus() {
134         return readOpStatus.get();
135     }
136 }