blob: dc9e8989a7509409b54d2a3640ee7daa91c47674 [file] [log] [blame]
Bri Prebilic Colecdc188d2015-04-24 16:40:11 -07001/*
2 * Copyright 2015 Open Networking Laboratory
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17package org.onosproject.ui.impl;
18
Bri Prebilic Colecdc188d2015-04-24 16:40:11 -070019import com.fasterxml.jackson.databind.node.ObjectNode;
20import com.google.common.collect.ImmutableSet;
21import org.apache.commons.lang.WordUtils;
22import org.onosproject.net.DeviceId;
23import org.onosproject.net.flow.FlowEntry;
24import org.onosproject.net.flow.FlowRuleService;
25import org.onosproject.net.flow.TrafficSelector;
26import org.onosproject.net.flow.TrafficTreatment;
27import org.onosproject.net.flow.criteria.Criterion;
28import org.onosproject.net.flow.instructions.Instruction;
Simon Huntd2747a02015-04-30 22:41:16 -070029import org.onosproject.ui.RequestHandler;
Simon Hunta0ddb022015-05-01 09:53:01 -070030import org.onosproject.ui.UiMessageHandler;
Simon Hunt44aa2f82015-04-30 15:01:35 -070031import org.onosproject.ui.table.AbstractTableRow;
32import org.onosproject.ui.table.RowComparator;
33import org.onosproject.ui.table.TableRow;
34import org.onosproject.ui.table.TableUtils;
Bri Prebilic Colecdc188d2015-04-24 16:40:11 -070035
36import java.util.ArrayList;
37import java.util.Arrays;
Simon Huntd2747a02015-04-30 22:41:16 -070038import java.util.Collection;
Bri Prebilic Colecdc188d2015-04-24 16:40:11 -070039import java.util.List;
40import java.util.Set;
41
42
43/**
44 * Message handler for flow view related messages.
45 */
Simon Hunta0ddb022015-05-01 09:53:01 -070046public class FlowViewMessageHandler extends UiMessageHandler {
Simon Huntd2747a02015-04-30 22:41:16 -070047
48 private static final String FLOW_DATA_REQ = "flowDataRequest";
Bri Prebilic Colecdc188d2015-04-24 16:40:11 -070049
50 private static final String NO_DEV = "none";
51
Bri Prebilic Colecdc188d2015-04-24 16:40:11 -070052 @Override
Simon Huntd2747a02015-04-30 22:41:16 -070053 protected Collection<RequestHandler> getHandlers() {
54 return ImmutableSet.of(new FlowDataRequest());
55 }
56
57 // ======================================================================
58
59 private final class FlowDataRequest extends RequestHandler {
60
61 private FlowDataRequest() {
62 super(FLOW_DATA_REQ);
63 }
64
65 @Override
66 public void process(long sid, ObjectNode payload) {
67 RowComparator rc = TableUtils.createRowComparator(payload);
68 String uri = string(payload, "devId", NO_DEV);
69
70 ObjectNode rootNode;
71 if (uri.equals(NO_DEV)) {
72 rootNode = MAPPER.createObjectNode();
73 rootNode.set("flows", MAPPER.createArrayNode());
74 } else {
75 DeviceId deviceId = DeviceId.deviceId(uri);
76 FlowRuleService service = get(FlowRuleService.class);
77 TableRow[] rows = generateTableRows(service, deviceId);
78 Arrays.sort(rows, rc);
79 rootNode = MAPPER.createObjectNode();
80 rootNode.set("flows", TableUtils.generateArrayNode(rows));
81 }
82
83 sendMessage("flowDataResponse", 0, rootNode);
84 }
85
86 private TableRow[] generateTableRows(FlowRuleService service,
87 DeviceId deviceId) {
88 List<TableRow> list = new ArrayList<>();
89 for (FlowEntry flow : service.getFlowEntries(deviceId)) {
90 list.add(new FlowTableRow(flow));
91 }
92 return list.toArray(new TableRow[list.size()]);
Simon Hunt44aa2f82015-04-30 15:01:35 -070093 }
94 }
95
Simon Huntd2747a02015-04-30 22:41:16 -070096 // ======================================================================
Bri Prebilic Colecdc188d2015-04-24 16:40:11 -070097
98 /**
99 * TableRow implementation for {@link org.onosproject.net.flow.FlowRule flows}.
100 */
101 private static class FlowTableRow extends AbstractTableRow {
102
103 private static final String ID = "id";
104 private static final String APP_ID = "appId";
105 private static final String GROUP_ID = "groupId";
106 private static final String TABLE_ID = "tableId";
107 private static final String PRIORITY = "priority";
108 private static final String SELECTOR = "selector";
109 private static final String TREATMENT = "treatment";
110 private static final String TIMEOUT = "timeout";
111 private static final String PERMANENT = "permanent";
112 private static final String STATE = "state";
113
114 private static final String COMMA = ", ";
115
116 private static final String[] COL_IDS = {
117 ID, APP_ID, GROUP_ID, TABLE_ID, PRIORITY, SELECTOR,
118 TREATMENT, TIMEOUT, PERMANENT, STATE
119 };
120
121 public FlowTableRow(FlowEntry f) {
122 add(ID, Long.toString(f.id().value()));
123 add(APP_ID, Short.toString(f.appId()));
124 add(GROUP_ID, Integer.toString(f.groupId().id()));
125 add(TABLE_ID, Integer.toString(f.tableId()));
126 add(PRIORITY, Integer.toString(f.priority()));
127 add(SELECTOR, getSelectorString(f));
128 add(TREATMENT, getTreatmentString(f));
129 add(TIMEOUT, Integer.toString(f.timeout()));
130 add(PERMANENT, Boolean.toString(f.isPermanent()));
131 add(STATE, WordUtils.capitalizeFully(f.state().toString()));
132 }
133
134 private String getSelectorString(FlowEntry f) {
135 String result;
136 TrafficSelector selector = f.selector();
137 Set<Criterion> criteria = selector.criteria();
138
139 if (criteria.isEmpty()) {
140 result = "(No traffic selectors for this flow)";
141 } else {
142 StringBuilder sb = new StringBuilder("Criteria = ");
143 for (Criterion c : criteria) {
144 sb.append(WordUtils.capitalizeFully(c.type().toString()))
145 .append(COMMA);
146 }
147 result = removeTrailingComma(sb).toString();
148 }
149 return result;
150 }
151
152 private String getTreatmentString(FlowEntry f) {
153 TrafficTreatment treatment = f.treatment();
154 List<Instruction> deferred = treatment.deferred();
155 List<Instruction> immediate = treatment.immediate();
156 boolean haveDef = !deferred.isEmpty();
157 boolean haveImm = !immediate.isEmpty();
158 boolean both = haveDef && haveImm;
159 boolean neither = !haveDef && !haveImm;
160 String result;
161
162 if (neither) {
163 result = "(No traffic treatment instructions for this flow)";
164 } else {
165 StringBuilder sb = new StringBuilder();
166 addDeferred(sb, deferred);
167 if (both) {
168 sb.append(COMMA);
169 }
170 addImmediate(sb, immediate);
171 result = sb.toString();
172 }
173 return result;
174 }
175
176 private void addDeferred(StringBuilder sb, List<Instruction> deferred) {
177 if (!deferred.isEmpty()) {
178 sb.append("Deferred instructions = ");
179 for (Instruction i : deferred) {
180 sb.append(WordUtils.capitalizeFully(i.type().toString()))
181 .append(COMMA);
182 }
183 removeTrailingComma(sb);
184 }
185 }
186
187 private void addImmediate(StringBuilder sb, List<Instruction> immediate) {
188 if (!immediate.isEmpty()) {
189 sb.append("Immediate instructions = ");
190 for (Instruction i : immediate) {
191 sb.append(WordUtils.capitalizeFully(i.type().toString()))
192 .append(COMMA);
193 }
194 removeTrailingComma(sb);
195 }
196 }
197
198 private StringBuilder removeTrailingComma(StringBuilder sb) {
199 int pos = sb.lastIndexOf(COMMA);
200 sb.delete(pos, sb.length());
201 return sb;
202 }
203
Bri Prebilic Colecdc188d2015-04-24 16:40:11 -0700204 @Override
205 protected String[] columnIds() {
206 return COL_IDS;
207 }
208 }
209
210}