Committed by
Gerrit Code Review
[ONOS-3163] Flow classifier web resource UT. and web resource fixes.
Change-Id: Ie23a450e2944c969753af5f5afb38780833b5a7e
Showing
4 changed files
with
117 additions
and
76 deletions
... | @@ -15,15 +15,12 @@ | ... | @@ -15,15 +15,12 @@ |
15 | */ | 15 | */ |
16 | package org.onosproject.vtnweb.resources; | 16 | package org.onosproject.vtnweb.resources; |
17 | 17 | ||
18 | -import static javax.ws.rs.core.Response.Status.INTERNAL_SERVER_ERROR; | ||
19 | -import static org.onlab.util.Tools.nullIsNotFound; | ||
20 | import static javax.ws.rs.core.Response.Status.NOT_FOUND; | 18 | import static javax.ws.rs.core.Response.Status.NOT_FOUND; |
19 | +import static javax.ws.rs.core.Response.Status.OK; | ||
20 | +import static org.onlab.util.Tools.nullIsNotFound; | ||
21 | 21 | ||
22 | import java.io.IOException; | 22 | import java.io.IOException; |
23 | import java.io.InputStream; | 23 | import java.io.InputStream; |
24 | -import java.net.URI; | ||
25 | -import java.net.URISyntaxException; | ||
26 | -import java.util.UUID; | ||
27 | 24 | ||
28 | import javax.ws.rs.Consumes; | 25 | import javax.ws.rs.Consumes; |
29 | import javax.ws.rs.DELETE; | 26 | import javax.ws.rs.DELETE; |
... | @@ -36,13 +33,17 @@ import javax.ws.rs.Produces; | ... | @@ -36,13 +33,17 @@ import javax.ws.rs.Produces; |
36 | import javax.ws.rs.core.MediaType; | 33 | import javax.ws.rs.core.MediaType; |
37 | import javax.ws.rs.core.Response; | 34 | import javax.ws.rs.core.Response; |
38 | 35 | ||
36 | +import org.onosproject.rest.AbstractWebResource; | ||
39 | import org.onosproject.vtnrsc.FlowClassifier; | 37 | import org.onosproject.vtnrsc.FlowClassifier; |
40 | import org.onosproject.vtnrsc.FlowClassifierId; | 38 | import org.onosproject.vtnrsc.FlowClassifierId; |
41 | -import org.onosproject.rest.AbstractWebResource; | ||
42 | import org.onosproject.vtnrsc.flowclassifier.FlowClassifierService; | 39 | import org.onosproject.vtnrsc.flowclassifier.FlowClassifierService; |
43 | import org.onosproject.vtnweb.web.FlowClassifierCodec; | 40 | import org.onosproject.vtnweb.web.FlowClassifierCodec; |
41 | +import org.slf4j.Logger; | ||
42 | +import org.slf4j.LoggerFactory; | ||
44 | 43 | ||
44 | +import com.fasterxml.jackson.databind.JsonNode; | ||
45 | import com.fasterxml.jackson.databind.ObjectMapper; | 45 | import com.fasterxml.jackson.databind.ObjectMapper; |
46 | +import com.fasterxml.jackson.databind.node.ArrayNode; | ||
46 | import com.fasterxml.jackson.databind.node.ObjectNode; | 47 | import com.fasterxml.jackson.databind.node.ObjectNode; |
47 | 48 | ||
48 | /** | 49 | /** |
... | @@ -51,73 +52,51 @@ import com.fasterxml.jackson.databind.node.ObjectNode; | ... | @@ -51,73 +52,51 @@ import com.fasterxml.jackson.databind.node.ObjectNode; |
51 | @Path("flow_classifiers") | 52 | @Path("flow_classifiers") |
52 | public class FlowClassifierWebResource extends AbstractWebResource { | 53 | public class FlowClassifierWebResource extends AbstractWebResource { |
53 | 54 | ||
55 | + private final Logger log = LoggerFactory.getLogger(FlowClassifierWebResource.class); | ||
56 | + | ||
54 | final FlowClassifierService service = get(FlowClassifierService.class); | 57 | final FlowClassifierService service = get(FlowClassifierService.class); |
55 | - final ObjectNode root = mapper().createObjectNode(); | ||
56 | public static final String FLOW_CLASSIFIER_NOT_FOUND = "Flow classifier not found"; | 58 | public static final String FLOW_CLASSIFIER_NOT_FOUND = "Flow classifier not found"; |
57 | 59 | ||
58 | /** | 60 | /** |
59 | - * Get all flow classifiers created. Returns list of all flow classifiers | 61 | + * Get all flow classifiers created. |
60 | - * created. | ||
61 | * | 62 | * |
62 | - * @return 200 OK | 63 | + * @return 200 OK, 404 if given flow classifier does not exist |
63 | */ | 64 | */ |
64 | @GET | 65 | @GET |
65 | @Produces(MediaType.APPLICATION_JSON) | 66 | @Produces(MediaType.APPLICATION_JSON) |
66 | public Response getFlowClassifiers() { | 67 | public Response getFlowClassifiers() { |
67 | - Iterable<FlowClassifier> flowClassifiers = service.getFlowClassifiers(); | 68 | + final Iterable<FlowClassifier> flowClassifiers = service.getFlowClassifiers(); |
68 | ObjectNode result = new ObjectMapper().createObjectNode(); | 69 | ObjectNode result = new ObjectMapper().createObjectNode(); |
69 | - result.set("flow_classifiers", new FlowClassifierCodec().encode(flowClassifiers, this)); | 70 | + ArrayNode flowClassifierEntry = result.putArray("flow_classifiers"); |
71 | + if (flowClassifiers != null) { | ||
72 | + for (final FlowClassifier flowClassifier : flowClassifiers) { | ||
73 | + flowClassifierEntry.add(new FlowClassifierCodec().encode(flowClassifier, this)); | ||
74 | + } | ||
75 | + } | ||
70 | return ok(result.toString()).build(); | 76 | return ok(result.toString()).build(); |
71 | } | 77 | } |
72 | 78 | ||
73 | /** | 79 | /** |
74 | - * Get details of a flow classifier. Returns details of a specified flow | 80 | + * Get details of a flow classifier. |
75 | - * classifier id. | ||
76 | * | 81 | * |
77 | * @param id flow classifier id | 82 | * @param id flow classifier id |
78 | - * @return 200 OK | 83 | + * @return 200 OK , 404 if given identifier does not exist |
79 | */ | 84 | */ |
80 | @GET | 85 | @GET |
81 | @Path("{flow_id}") | 86 | @Path("{flow_id}") |
82 | @Produces(MediaType.APPLICATION_JSON) | 87 | @Produces(MediaType.APPLICATION_JSON) |
83 | public Response getFlowClassifier(@PathParam("flow_id") String id) { | 88 | public Response getFlowClassifier(@PathParam("flow_id") String id) { |
84 | 89 | ||
85 | - if (!service.hasFlowClassifier(FlowClassifierId.of(UUID.fromString(id)))) { | 90 | + if (!service.hasFlowClassifier(FlowClassifierId.of(id))) { |
86 | return Response.status(NOT_FOUND).entity(FLOW_CLASSIFIER_NOT_FOUND).build(); | 91 | return Response.status(NOT_FOUND).entity(FLOW_CLASSIFIER_NOT_FOUND).build(); |
87 | } | 92 | } |
88 | - FlowClassifier flowClassifier = nullIsNotFound( | 93 | + FlowClassifier flowClassifier = nullIsNotFound(service.getFlowClassifier(FlowClassifierId.of(id)), |
89 | - service.getFlowClassifier(FlowClassifierId.of(UUID.fromString(id))), | ||
90 | FLOW_CLASSIFIER_NOT_FOUND); | 94 | FLOW_CLASSIFIER_NOT_FOUND); |
91 | 95 | ||
92 | ObjectNode result = new ObjectMapper().createObjectNode(); | 96 | ObjectNode result = new ObjectMapper().createObjectNode(); |
93 | result.set("flow_classifier", new FlowClassifierCodec().encode(flowClassifier, this)); | 97 | result.set("flow_classifier", new FlowClassifierCodec().encode(flowClassifier, this)); |
94 | - return ok(result.toString()).build(); | ||
95 | - } | ||
96 | - | ||
97 | - /** | ||
98 | - * Creates and stores a new flow classifier. | ||
99 | - * | ||
100 | - * @param flowClassifierId flow classifier identifier | ||
101 | - * @param stream flow classifier from JSON | ||
102 | - * @return status of the request - CREATED if the JSON is correct, | ||
103 | - * BAD_REQUEST if the JSON is invalid | ||
104 | - */ | ||
105 | - @POST | ||
106 | - @Path("{flow_id}") | ||
107 | - @Consumes(MediaType.APPLICATION_JSON) | ||
108 | - @Produces(MediaType.APPLICATION_JSON) | ||
109 | - public Response createFlowClassifier(@PathParam("flow_id") String flowClassifierId, InputStream stream) { | ||
110 | - URI location; | ||
111 | - try { | ||
112 | - ObjectNode jsonTree = (ObjectNode) mapper().readTree(stream); | ||
113 | 98 | ||
114 | - FlowClassifier flowClassifier = codec(FlowClassifier.class).decode(jsonTree, this); | 99 | + return ok(result.toString()).build(); |
115 | - service.createFlowClassifier(flowClassifier); | ||
116 | - location = new URI(flowClassifierId); | ||
117 | - } catch (IOException | URISyntaxException ex) { | ||
118 | - throw new IllegalArgumentException(ex); | ||
119 | - } | ||
120 | - return Response.created(location).build(); | ||
121 | } | 100 | } |
122 | 101 | ||
123 | /** | 102 | /** |
... | @@ -125,32 +104,32 @@ public class FlowClassifierWebResource extends AbstractWebResource { | ... | @@ -125,32 +104,32 @@ public class FlowClassifierWebResource extends AbstractWebResource { |
125 | * | 104 | * |
126 | * @param stream flow classifier from JSON | 105 | * @param stream flow classifier from JSON |
127 | * @return status of the request - CREATED if the JSON is correct, | 106 | * @return status of the request - CREATED if the JSON is correct, |
128 | - * BAD_REQUEST if the JSON is invalid | 107 | + * BAD_REQUEST if the JSON is invalid |
129 | */ | 108 | */ |
130 | @POST | 109 | @POST |
131 | @Consumes(MediaType.APPLICATION_JSON) | 110 | @Consumes(MediaType.APPLICATION_JSON) |
132 | @Produces(MediaType.APPLICATION_JSON) | 111 | @Produces(MediaType.APPLICATION_JSON) |
133 | public Response createFlowClassifier(InputStream stream) { | 112 | public Response createFlowClassifier(InputStream stream) { |
134 | - URI location; | ||
135 | try { | 113 | try { |
136 | - ObjectNode jsonTree = (ObjectNode) mapper().readTree(stream); | 114 | + ObjectMapper mapper = new ObjectMapper(); |
137 | - | 115 | + ObjectNode jsonTree = (ObjectNode) mapper.readTree(stream); |
138 | - FlowClassifier flowClassifier = codec(FlowClassifier.class).decode(jsonTree, this); | 116 | + JsonNode flow = jsonTree.get("flow_classifier"); |
139 | - service.createFlowClassifier(flowClassifier); | 117 | + |
140 | - location = new URI(flowClassifier.flowClassifierId().toString()); | 118 | + FlowClassifier flowClassifier = new FlowClassifierCodec().decode((ObjectNode) flow, this); |
141 | - } catch (IOException | URISyntaxException ex) { | 119 | + Boolean issuccess = nullIsNotFound(service.createFlowClassifier(flowClassifier), FLOW_CLASSIFIER_NOT_FOUND); |
120 | + return Response.status(OK).entity(issuccess.toString()).build(); | ||
121 | + } catch (IOException ex) { | ||
122 | + log.error("Exception while creating flow classifier {}.", ex.toString()); | ||
142 | throw new IllegalArgumentException(ex); | 123 | throw new IllegalArgumentException(ex); |
143 | } | 124 | } |
144 | - return Response.created(location).build(); | ||
145 | } | 125 | } |
146 | 126 | ||
147 | /** | 127 | /** |
148 | - * Update details of a flow classifier. Update details of a specified flow | 128 | + * Update details of a flow classifier. |
149 | - * classifier id. | ||
150 | * | 129 | * |
151 | * @param id flow classifier id | 130 | * @param id flow classifier id |
152 | * @param stream InputStream | 131 | * @param stream InputStream |
153 | - * @return 200 OK | 132 | + * @return 200 OK, 404 if given identifier does not exist |
154 | */ | 133 | */ |
155 | @PUT | 134 | @PUT |
156 | @Path("{flow_id}") | 135 | @Path("{flow_id}") |
... | @@ -158,35 +137,29 @@ public class FlowClassifierWebResource extends AbstractWebResource { | ... | @@ -158,35 +137,29 @@ public class FlowClassifierWebResource extends AbstractWebResource { |
158 | @Consumes(MediaType.APPLICATION_JSON) | 137 | @Consumes(MediaType.APPLICATION_JSON) |
159 | public Response updateFlowClassifier(@PathParam("flow_id") String id, final InputStream stream) { | 138 | public Response updateFlowClassifier(@PathParam("flow_id") String id, final InputStream stream) { |
160 | try { | 139 | try { |
161 | - ObjectNode jsonTree = (ObjectNode) mapper().readTree(stream); | 140 | + |
162 | - FlowClassifier flowClassifier = codec(FlowClassifier.class).decode(jsonTree, this); | 141 | + JsonNode jsonTree = mapper().readTree(stream); |
142 | + JsonNode flow = jsonTree.get("flow_classifier"); | ||
143 | + FlowClassifier flowClassifier = new FlowClassifierCodec().decode((ObjectNode) flow, this); | ||
163 | Boolean result = nullIsNotFound(service.updateFlowClassifier(flowClassifier), FLOW_CLASSIFIER_NOT_FOUND); | 144 | Boolean result = nullIsNotFound(service.updateFlowClassifier(flowClassifier), FLOW_CLASSIFIER_NOT_FOUND); |
164 | - if (!result) { | 145 | + return Response.status(OK).entity(result.toString()).build(); |
165 | - return Response.status(204).entity(FLOW_CLASSIFIER_NOT_FOUND).build(); | 146 | + } catch (IOException e) { |
166 | - } | 147 | + log.error("Update flow classifier failed because of exception {}.", e.toString()); |
167 | - return Response.status(203).entity(result.toString()).build(); | 148 | + throw new IllegalArgumentException(e); |
168 | - } catch (Exception e) { | ||
169 | - return Response.status(INTERNAL_SERVER_ERROR).entity(e.toString()).build(); | ||
170 | } | 149 | } |
171 | } | 150 | } |
172 | 151 | ||
173 | /** | 152 | /** |
174 | - * Delete details of a flow classifier. Delete details of a specified flow | 153 | + * Delete details of a flow classifier. |
175 | - * classifier id. | ||
176 | * | 154 | * |
177 | * @param id flow classifier id | 155 | * @param id flow classifier id |
178 | - * @return 200 OK | ||
179 | - * @throws IOException when input doesn't match. | ||
180 | */ | 156 | */ |
181 | @Path("{flow_id}") | 157 | @Path("{flow_id}") |
182 | @DELETE | 158 | @DELETE |
183 | - public Response deleteFlowClassifier(@PathParam("flow_id") String id) throws IOException { | 159 | + public void deleteFlowClassifier(@PathParam("flow_id") String id) { |
184 | - try { | 160 | + log.debug("Deletes flow classifier by identifier {}.", id); |
185 | - FlowClassifierId flowClassifierId = FlowClassifierId.of(UUID.fromString(id)); | 161 | + FlowClassifierId flowClassifierId = FlowClassifierId.of(id); |
186 | - service.removeFlowClassifier(flowClassifierId); | 162 | + Boolean issuccess = nullIsNotFound(service.removeFlowClassifier(flowClassifierId), FLOW_CLASSIFIER_NOT_FOUND); |
187 | - return Response.status(201).entity("SUCCESS").build(); | 163 | + |
188 | - } catch (Exception e) { | ||
189 | - return Response.status(INTERNAL_SERVER_ERROR).entity(e.toString()).build(); | ||
190 | - } | ||
191 | } | 164 | } |
192 | } | 165 | } | ... | ... |
apps/vtn/vtnweb/src/test/java/org/onosproject/vtnweb/resources/FlowClassifierResourceTest.java
0 → 100644
This diff is collapsed. Click to expand it.
1 | +/* | ||
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 | +package org.onosproject.vtnweb.resources; | ||
17 | + | ||
18 | +import java.io.IOException; | ||
19 | +import java.net.ServerSocket; | ||
20 | + | ||
21 | +import com.sun.jersey.test.framework.AppDescriptor; | ||
22 | +import com.sun.jersey.test.framework.JerseyTest; | ||
23 | +import com.sun.jersey.test.framework.WebAppDescriptor; | ||
24 | + | ||
25 | +/** | ||
26 | + * Base class for VTN REST API tests. Performs common configuration operations. | ||
27 | + */ | ||
28 | +public class VtnResourceTest extends JerseyTest { | ||
29 | + | ||
30 | + /** | ||
31 | + * Assigns an available port for the test. | ||
32 | + * | ||
33 | + * @param defaultPort If a port cannot be determined, this one is used. | ||
34 | + * @return free port | ||
35 | + */ | ||
36 | + @Override | ||
37 | + public int getPort(int defaultPort) { | ||
38 | + try { | ||
39 | + ServerSocket socket = new ServerSocket(0); | ||
40 | + socket.setReuseAddress(true); | ||
41 | + int port = socket.getLocalPort(); | ||
42 | + socket.close(); | ||
43 | + return port; | ||
44 | + } catch (IOException ioe) { | ||
45 | + return defaultPort; | ||
46 | + } | ||
47 | + } | ||
48 | + | ||
49 | + @Override | ||
50 | + public AppDescriptor configure() { | ||
51 | + return new WebAppDescriptor.Builder("org.onosproject.vtnweb.resources").build(); | ||
52 | + } | ||
53 | + | ||
54 | +} |
apps/vtn/vtnweb/src/test/resources/org/onosproject/vtnweb/resources/post-FlowClassifier.json
0 → 100644
1 | +{"flow_classifier": { | ||
2 | + "id": "4a334cd4-fe9c-4fae-af4b-321c5e2eb051", | ||
3 | + "name": "flow1", | ||
4 | + "tenant_id": "1814726e2d22407b8ca76db5e567dcf1", | ||
5 | + "description": "flow classifier", | ||
6 | + "ethertype": "IPv4", | ||
7 | + "protocol": "tcp", | ||
8 | + "source_port_range_min": 22, "source_port_range_max": 4000, | ||
9 | + "destination_port_range_min": 80, "destination_port_range_max": 80, | ||
10 | + "source_ip_prefix": "1.1.1.1/16" , "destination_ip_prefix": "22.12.34.45/16", | ||
11 | + "logical_destination_port": "dace4513-24fc-4fae-af4b-321c5e2eb3d1", | ||
12 | + "logical_source_port": "aef3478a-4a56-2a6e-cd3a-9dee4e2ec345" | ||
13 | + } | ||
14 | +} |
-
Please register or login to post a comment