Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(806)

Side by Side Diff: tests/standalone/io/http_parser_test.dart

Issue 12316036: Merge IO v2 branch to bleeding edge (Closed) Base URL: https://dart.googlecode.com/svn/branches/bleeding_edge/dart
Patch Set: Rebased to r18818 Created 7 years, 10 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
« no previous file with comments | « tests/standalone/io/http_headers_test.dart ('k') | tests/standalone/io/http_proxy_test.dart » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright (c) 2012, the Dart project authors. Please see the AUTHORS file 1 // Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file
2 // for details. All rights reserved. Use of this source code is governed by a 2 // for details. All rights reserved. Use of this source code is governed by a
3 // BSD-style license that can be found in the LICENSE file. 3 // BSD-style license that can be found in the LICENSE file.
4 4
5 import 'dart:async'; 5 import 'dart:async';
6 import 'dart:math'; 6 import 'dart:math';
7 import 'dart:scalarlist'; 7 import 'dart:scalarlist';
8 import 'dart:isolate';
9 import 'dart:uri';
8 10
11 part '../../../sdk/lib/io/io_stream_consumer.dart';
9 part '../../../sdk/lib/io/http.dart'; 12 part '../../../sdk/lib/io/http.dart';
13 part '../../../sdk/lib/io/http_impl.dart';
10 part '../../../sdk/lib/io/http_headers.dart'; 14 part '../../../sdk/lib/io/http_headers.dart';
11 part '../../../sdk/lib/io/http_parser.dart'; 15 part '../../../sdk/lib/io/http_parser.dart';
16 part '../../../sdk/lib/io/socket.dart';
12 17
13 class HttpParserTest { 18 class HttpParserTest {
14 static void runAllTests() { 19 static void runAllTests() {
15 testParseRequest(); 20 testParseRequest();
16 testParseResponse(); 21 testParseResponse();
17 testParseInvalidRequest(); 22 testParseInvalidRequest();
18 testParseInvalidResponse(); 23 testParseInvalidResponse();
19 } 24 }
20 25
21 static void _testParseRequest(String request, 26 static void _testParseRequest(String request,
22 String expectedMethod, 27 String expectedMethod,
23 String expectedUri, 28 String expectedUri,
24 {int expectedContentLength: 0, 29 {int expectedTransferLength: 0,
25 int expectedBytesReceived: 0, 30 int expectedBytesReceived: 0,
26 Map expectedHeaders: null, 31 Map expectedHeaders: null,
27 bool chunked: false, 32 bool chunked: false,
28 bool upgrade: false, 33 bool upgrade: false,
29 int unparsedLength: 0, 34 int unparsedLength: 0,
30 bool connectionClose: false, 35 bool connectionClose: false,
31 String expectedVersion: "1.1"}) { 36 String expectedVersion: "1.1"}) {
32 _HttpParser httpParser; 37 StreamController controller;
33 bool headersCompleteCalled; 38 void reset() {
34 bool dataEndCalled; 39 _HttpParser httpParser = new _HttpParser.requestParser();
35 String method; 40 controller = new StreamController();
36 String uri; 41 var port1 = new ReceivePort();
37 String version; 42 var port2 = new ReceivePort();
38 HttpHeaders headers;
39 int contentLength;
40 int bytesReceived;
41 43
42 void reset() { 44 String method;
43 httpParser = new _HttpParser.requestParser(); 45 Uri uri;
44 httpParser.requestStart = (m, u, v, h, b) { 46 HttpHeaders headers;
45 method = m; 47 int contentLength;
46 uri = u; 48 int bytesReceived;
47 version = v; 49 int unparsedBytesReceived;
48 headers = h; 50 bool upgraded;
49 headersCompleteCalled = true; 51
52 controller.stream.pipe(httpParser);
53 var subscription = httpParser.listen((incoming) {
54 method = incoming.method;
55 uri = incoming.uri;
56 headers = incoming.headers;
57 upgraded = incoming.upgraded;
58 Expect.equals(upgrade, upgraded);
59
50 if (!chunked) { 60 if (!chunked) {
51 Expect.equals(expectedContentLength, httpParser.contentLength); 61 Expect.equals(expectedTransferLength, incoming.transferLength);
52 } else { 62 } else {
53 Expect.equals(-1, httpParser.contentLength); 63 Expect.equals(-1, incoming.transferLength);
54 } 64 }
55 if (expectedHeaders != null) { 65 if (expectedHeaders != null) {
56 expectedHeaders.forEach( 66 expectedHeaders.forEach(
57 (String name, String value) => 67 (String name, String value) =>
58 Expect.equals(value, headers[name][0])); 68 Expect.equals(value, headers[name][0]));
59 } 69 }
60 Expect.equals(upgrade, httpParser.upgrade); 70 incoming.listen(
61 Expect.equals(connectionClose, !httpParser.persistentConnection); 71 (List<int> data) {
62 headersCompleteCalled = true; 72 Expect.isFalse(upgraded);
63 }; 73 bytesReceived += data.length;
64 httpParser.responseStart = (s, r, v, h, b) { 74 },
65 Expect.fail("Expected request"); 75 onDone: () {
66 }; 76 Expect.isFalse(upgraded);
67 httpParser.dataReceived = (List<int> data) { 77 port2.close();
68 Expect.isTrue(headersCompleteCalled); 78 });
69 bytesReceived += data.length;
70 };
71 httpParser.dataEnd = (close) {
72 Expect.isFalse(close);
73 dataEndCalled = true;
74 };
75 httpParser.closed = () { };
76 79
77 headersCompleteCalled = false; 80 if (upgraded) {
78 dataEndCalled = false; 81 port1.close();
82 httpParser.detachIncoming().listen(
83 (List<int> data) {
84 unparsedBytesReceived += data.length;
85 },
86 onDone: () {
87 Expect.equals(unparsedLength, unparsedBytesReceived);
88 port2.close();
89 });
90 }
91
92 incoming.dataDone.then((_) {
93 port1.close();
94 Expect.isFalse(upgraded);
95 Expect.equals(expectedMethod, method);
96 Expect.stringEquals(expectedUri, uri.toString());
97 Expect.equals(expectedVersion, headers.protocolVersion);
98 if (upgrade) {
99 Expect.equals(0, bytesReceived);
100 // port1 is closed by the listener on the detached data.
101 } else {
102 Expect.equals(expectedBytesReceived, bytesReceived);
103 }
104 });
105 });
106
79 method = null; 107 method = null;
80 uri = null; 108 uri = null;
81 headers = null; 109 headers = null;
82 bytesReceived = 0; 110 bytesReceived = 0;
111 unparsedBytesReceived = 0;
112 upgraded = false;
83 } 113 }
84 114
85 void testWrite(List<int> requestData, [int chunkSize = -1]) { 115 void testWrite(List<int> requestData, [int chunkSize = -1]) {
86 if (chunkSize == -1) chunkSize = requestData.length; 116 if (chunkSize == -1) chunkSize = requestData.length;
87 reset(); 117 reset();
88 int written = 0;
89 int unparsed;
90 for (int pos = 0; pos < requestData.length; pos += chunkSize) { 118 for (int pos = 0; pos < requestData.length; pos += chunkSize) {
91 int remaining = requestData.length - pos; 119 int remaining = requestData.length - pos;
92 int writeLength = min(chunkSize, remaining); 120 int writeLength = min(chunkSize, remaining);
93 written += writeLength; 121 controller.add(requestData.getRange(pos, writeLength));
94 httpParser.streamData(requestData.getRange(pos, writeLength));
95 unparsed = httpParser.readUnparsedData().length;
96 if (httpParser.upgrade) {
97 unparsed += requestData.length - written;
98 break;
99 } else {
100 Expect.equals(0, unparsed);
101 }
102 } 122 }
103 Expect.equals(expectedMethod, method); 123 controller.close();
104 Expect.equals(expectedUri, uri);
105 Expect.equals(expectedVersion, version);
106 Expect.isTrue(headersCompleteCalled);
107 Expect.equals(expectedBytesReceived, bytesReceived);
108 if (!upgrade) Expect.isTrue(dataEndCalled);
109 if (unparsedLength == 0) {
110 Expect.equals(0, unparsed);
111 } else {
112 Expect.equals(unparsedLength, unparsed);
113 }
114 } 124 }
115 125
116 // Test parsing the request three times delivering the data in 126 // Test parsing the request three times delivering the data in
117 // different chunks. 127 // different chunks.
118 List<int> requestData = request.charCodes; 128 List<int> requestData = request.charCodes;
119 testWrite(requestData); 129 testWrite(requestData);
120 testWrite(requestData, 10); 130 testWrite(requestData, 10);
121 testWrite(requestData, 1); 131 testWrite(requestData, 1);
122 } 132 }
123 133
124 static void _testParseInvalidRequest(String request) { 134 static void _testParseInvalidRequest(String request) {
125 _HttpParser httpParser; 135 _HttpParser httpParser;
126 bool errorCalled; 136 bool errorCalled;
137 StreamController controller;
127 138
128 void reset() { 139 void reset() {
129 httpParser = new _HttpParser.requestParser(); 140 httpParser = new _HttpParser.requestParser();
130 httpParser.responseStart = (s, r, v, h, b) { 141 controller = new StreamController();
142 var port = new ReceivePort();
143 controller.stream.pipe(httpParser);
144 var subscription = httpParser.listen((incoming) {
131 Expect.fail("Expected request"); 145 Expect.fail("Expected request");
132 }; 146 });
133 httpParser.error = (e) { 147 subscription.onError((e) {
134 errorCalled = true; 148 errorCalled = true;
135 }; 149 });
136 httpParser.closed = () { }; 150 subscription.onDone(() {
137 151 port.close();
152 Expect.isTrue(errorCalled);
153 });
138 errorCalled = false; 154 errorCalled = false;
139 } 155 }
140 156
141 void testWrite(List<int> requestData, [int chunkSize = -1]) { 157 void testWrite(List<int> requestData, [int chunkSize = -1]) {
142 if (chunkSize == -1) chunkSize = requestData.length; 158 if (chunkSize == -1) chunkSize = requestData.length;
143 reset(); 159 reset();
144 for (int pos = 0; 160 for (int pos = 0;
145 pos < requestData.length && !errorCalled; 161 pos < requestData.length && !errorCalled;
146 pos += chunkSize) { 162 pos += chunkSize) {
147 int remaining = requestData.length - pos; 163 int remaining = requestData.length - pos;
148 int writeLength = min(chunkSize, remaining); 164 int writeLength = min(chunkSize, remaining);
149 httpParser.streamData(requestData.getRange(pos, writeLength)); 165 controller.add(requestData.getRange(pos, writeLength));
150 } 166 }
151 Expect.isTrue(errorCalled); 167 controller.close();
152 } 168 }
153 169
154 // Test parsing the request three times delivering the data in 170 // Test parsing the request three times delivering the data in
155 // different chunks. 171 // different chunks.
156 List<int> requestData = request.charCodes; 172 List<int> requestData = request.charCodes;
157 testWrite(requestData); 173 testWrite(requestData);
158 testWrite(requestData, 10); 174 testWrite(requestData, 10);
159 testWrite(requestData, 1); 175 testWrite(requestData, 1);
160 } 176 }
161 177
162 static void _testParseResponse(String response, 178 static void _testParseResponse(String response,
163 int expectedStatusCode, 179 int expectedStatusCode,
164 String expectedReasonPhrase, 180 String expectedReasonPhrase,
165 {int expectedContentLength: -1, 181 {int expectedTransferLength: 0,
166 int expectedBytesReceived: 0, 182 int expectedBytesReceived: 0,
167 Map expectedHeaders: null, 183 Map expectedHeaders: null,
168 bool chunked: false, 184 bool chunked: false,
169 bool close: false, 185 bool close: false,
170 String responseToMethod: null, 186 String responseToMethod: null,
171 bool connectionClose: false, 187 bool connectionClose: false,
172 bool upgrade: false, 188 bool upgrade: false,
173 int unparsedLength: 0, 189 int unparsedLength: 0,
174 String expectedVersion: "1.1"}) { 190 String expectedVersion: "1.1"}) {
175 _HttpParser httpParser; 191 _HttpParser httpParser;
176 bool headersCompleteCalled; 192 bool headersCompleteCalled;
177 bool dataEndCalled; 193 bool dataEndCalled;
178 bool dataEndClose; 194 bool dataEndClose;
179 int statusCode; 195 int statusCode;
180 String reasonPhrase; 196 String reasonPhrase;
181 String version;
182 HttpHeaders headers; 197 HttpHeaders headers;
183 int contentLength; 198 int contentLength;
184 int bytesReceived; 199 int bytesReceived;
200 StreamController controller;
201 bool upgraded;
185 202
186 void reset() { 203 void reset() {
187 httpParser = new _HttpParser.responseParser(); 204 httpParser = new _HttpParser.responseParser();
188 if (responseToMethod != null) { 205 controller = new StreamController();
189 httpParser.responseToMethod = responseToMethod; 206 var port = new ReceivePort();
190 } 207 controller.stream.pipe(httpParser);
191 httpParser.requestStart = (m, u, v, h, b) { 208 var subscription = httpParser.listen((incoming) {
192 Expect.fail("Expected response"); 209 port.close();
193 }; 210 statusCode = incoming.statusCode;
194 httpParser.responseStart = (s, r, v, h, b) { 211 reasonPhrase = incoming.reasonPhrase;
195 statusCode = s; 212 headers = incoming.headers;
196 reasonPhrase = r;
197 version = v;
198 headers = h;
199 Expect.isFalse(headersCompleteCalled); 213 Expect.isFalse(headersCompleteCalled);
200 if (!chunked && !close) { 214 if (!chunked && !close) {
201 Expect.equals(expectedContentLength, httpParser.contentLength); 215 Expect.equals(expectedTransferLength, incoming.transferLength);
202 } else { 216 } else {
203 Expect.equals(-1, httpParser.contentLength); 217 Expect.equals(-1, incoming.transferLength);
204 } 218 }
205 if (expectedHeaders != null) { 219 if (expectedHeaders != null) {
206 expectedHeaders.forEach((String name, String value) { 220 expectedHeaders.forEach((String name, String value) {
207 Expect.equals(value, headers[name][0]); 221 Expect.equals(value, headers[name][0]);
208 }); 222 });
209 } 223 }
210 Expect.equals(upgrade, httpParser.upgrade); 224 Expect.equals(upgrade, httpParser.upgrade);
211 headersCompleteCalled = true; 225 headersCompleteCalled = true;
212 }; 226 incoming.listen(
213 httpParser.dataReceived = (List<int> data) { 227 (List<int> data) {
228 Expect.isTrue(headersCompleteCalled);
229 bytesReceived += data.length;
230 },
231 onDone: () {
232 dataEndCalled = true;
233 dataEndClose = close;
234 });
235 });
236
237 subscription.onDone(() {
238 Expect.equals(expectedVersion, headers.protocolVersion);
239 Expect.equals(expectedStatusCode, statusCode);
240 Expect.equals(expectedReasonPhrase, reasonPhrase);
214 Expect.isTrue(headersCompleteCalled); 241 Expect.isTrue(headersCompleteCalled);
215 bytesReceived += data.length; 242 Expect.equals(expectedBytesReceived, bytesReceived);
216 }; 243 if (!upgrade) {
217 httpParser.dataEnd = (close) { 244 Expect.isTrue(dataEndCalled);
218 dataEndCalled = true; 245 if (close) Expect.isTrue(dataEndClose);
219 dataEndClose = close; 246 Expect.equals(dataEndClose, connectionClose);
220 }; 247 }
221 httpParser.closed = () { }; 248 });
222 249
223 headersCompleteCalled = false; 250 headersCompleteCalled = false;
224 dataEndCalled = false; 251 dataEndCalled = false;
225 dataEndClose = null; 252 dataEndClose = null;
226 statusCode = -1; 253 statusCode = -1;
227 reasonPhrase = null; 254 reasonPhrase = null;
228 headers = null; 255 headers = null;
229 bytesReceived = 0; 256 bytesReceived = 0;
230 } 257 }
231 258
232 void testWrite(List<int> requestData, [int chunkSize = -1]) { 259 void testWrite(List<int> requestData, [int chunkSize = -1]) {
233 if (chunkSize == -1) chunkSize = requestData.length; 260 if (chunkSize == -1) chunkSize = requestData.length;
234 reset(); 261 reset();
235 int written = 0;
236 int unparsed;
237 for (int pos = 0; pos < requestData.length; pos += chunkSize) { 262 for (int pos = 0; pos < requestData.length; pos += chunkSize) {
238 int remaining = requestData.length - pos; 263 int remaining = requestData.length - pos;
239 int writeLength = min(chunkSize, remaining); 264 int writeLength = min(chunkSize, remaining);
240 written += writeLength; 265 controller.add(requestData.getRange(pos, writeLength));
241 httpParser.streamData(requestData.getRange(pos, writeLength)); 266
242 unparsed = httpParser.readUnparsedData().length;
243 if (httpParser.upgrade) {
244 unparsed += requestData.length - written;
245 break;
246 } else {
247 Expect.equals(0, unparsed);
248 }
249 } 267 }
250 if (close) httpParser.streamDone(); 268 if (close) controller.close();
251 Expect.equals(expectedVersion, version);
252 Expect.equals(expectedStatusCode, statusCode);
253 Expect.equals(expectedReasonPhrase, reasonPhrase);
254 Expect.isTrue(headersCompleteCalled);
255 Expect.equals(expectedBytesReceived, bytesReceived);
256 if (!upgrade) {
257 Expect.isTrue(dataEndCalled);
258 if (close) Expect.isTrue(dataEndClose);
259 Expect.equals(dataEndClose, connectionClose);
260 }
261 if (unparsedLength == 0) {
262 Expect.equals(0, unparsed);
263 } else {
264 Expect.equals(unparsedLength, unparsed);
265 }
266 } 269 }
267 270
268 // Test parsing the request three times delivering the data in 271 // Test parsing the request three times delivering the data in
269 // different chunks. 272 // different chunks.
270 List<int> responseData = response.charCodes; 273 List<int> responseData = response.charCodes;
271 testWrite(responseData); 274 testWrite(responseData);
272 testWrite(responseData, 10); 275 testWrite(responseData, 10);
273 testWrite(responseData, 1); 276 testWrite(responseData, 1);
274 } 277 }
275 278
276 static void _testParseInvalidResponse(String response, [bool close = false]) { 279 static void _testParseInvalidResponse(String response, [bool close = false]) {
277 _HttpParser httpParser; 280 _HttpParser httpParser;
278 bool errorCalled; 281 bool errorCalled;
282 StreamController controller;
279 283
280 void reset() { 284 void reset() {
281 httpParser = new _HttpParser.responseParser(); 285 httpParser = new _HttpParser.responseParser();
282 httpParser.requestStart = (m, u, v, h, b) { 286 controller = new StreamController();
283 Expect.fail("Expected response"); 287 var port = new ReceivePort();
284 }; 288 controller.stream.pipe(httpParser);
285 httpParser.error = (e) => errorCalled = true; 289 var subscription = httpParser.listen((incoming) {
286 httpParser.closed = () { }; 290 incoming.listen(
287 291 (data) {},
292 onError: (e) {
293 Expect.isFalse(errorCalled);
294 errorCalled = true;
295 });
296 });
297 subscription.onError((e) {
298 Expect.isFalse(errorCalled);
299 errorCalled = true;
300 });
301 subscription.onDone(() {
302 port.close();
303 Expect.isTrue(errorCalled);
304 });
288 errorCalled = false; 305 errorCalled = false;
289 } 306 }
290 307
291 void testWrite(List<int> requestData, [int chunkSize = -1]) { 308 void testWrite(List<int> requestData, [int chunkSize = -1]) {
292 if (chunkSize == -1) chunkSize = requestData.length; 309 if (chunkSize == -1) chunkSize = requestData.length;
293 reset(); 310 reset();
294 for (int pos = 0; 311 for (int pos = 0;
295 pos < requestData.length && !errorCalled; 312 pos < requestData.length && !errorCalled;
296 pos += chunkSize) { 313 pos += chunkSize) {
297 int remaining = requestData.length - pos; 314 int remaining = requestData.length - pos;
298 int writeLength = min(chunkSize, remaining); 315 int writeLength = min(chunkSize, remaining);
299 httpParser.streamData(requestData.getRange(pos, writeLength)); 316 controller.add(requestData.getRange(pos, writeLength));
300 } 317 }
301 if (close) httpParser.streamDone(); 318 controller.close();
302 Expect.isTrue(errorCalled);
303 } 319 }
304 320
305 // Test parsing the request three times delivering the data in 321 // Test parsing the request three times delivering the data in
306 // different chunks. 322 // different chunks.
307 List<int> responseData = response.charCodes; 323 List<int> responseData = response.charCodes;
308 testWrite(responseData); 324 testWrite(responseData);
309 testWrite(responseData, 10); 325 testWrite(responseData, 10);
310 testWrite(responseData, 1); 326 testWrite(responseData, 1);
311 } 327 }
312 328
313 static void testParseRequest() { 329 static void testParseRequest() {
314 String request; 330 String request;
315 Map headers; 331 Map headers;
316 var methods = [ 332 var methods = [
317 // RFC 2616 methods. 333 // RFC 2616 methods.
318 "OPTIONS", "GET", "HEAD", "POST", "PUT", "DELETE", "TRACE", "CONNECT", 334 "OPTIONS", "GET", "HEAD", "POST", "PUT", "DELETE", "TRACE", "CONNECT",
319 // WebDAV methods from RFC 4918. 335 // WebDAV methods from RFC 4918.
320 "PROPFIND", "PROPPATCH", "MKCOL", "COPY", "MOVE", "LOCK", "UNLOCK", 336 "PROPFIND", "PROPPATCH", "MKCOL", "COPY", "MOVE", "LOCK", "UNLOCK",
321 // WebDAV methods from RFC 5323. 337 // WebDAV methods from RFC 5323.
322 "SEARCH", 338 "SEARCH",
323 // Methods with HTTP prefix. 339 // Methods with HTTP prefix.
324 "H", "HT", "HTT", "HTTP", "HX", "HTX", "HTTX", "HTTPX"]; 340 "H", "HT", "HTT", "HTTP", "HX", "HTX", "HTTX", "HTTPX"];
325 methods.forEach((method) { 341 methods.forEach((method) {
326 request = "$method / HTTP/1.1\r\n\r\n"; 342 request = "$method / HTTP/1.1\r\n\r\n";
327 _testParseRequest(request, method, "/"); 343 _testParseRequest(request, method, "/");
328 request = "$method /index.html HTTP/1.1\r\n\r\n"; 344 request = "$method /index.html HTTP/1.1\r\n\r\n";
329 _testParseRequest(request, method, "/index.html"); 345 _testParseRequest(request, method, "/index.html");
330 }); 346 });
331 347
348
332 request = "GET / HTTP/1.0\r\n\r\n"; 349 request = "GET / HTTP/1.0\r\n\r\n";
333 _testParseRequest(request, "GET", "/", 350 _testParseRequest(request, "GET", "/",
334 expectedVersion: "1.0", 351 expectedVersion: "1.0",
335 connectionClose: true); 352 connectionClose: true);
336 353
337 request = "GET / HTTP/1.0\r\nConnection: keep-alive\r\n\r\n"; 354 request = "GET / HTTP/1.0\r\nConnection: keep-alive\r\n\r\n";
338 _testParseRequest(request, "GET", "/", expectedVersion: "1.0"); 355 _testParseRequest(request, "GET", "/", expectedVersion: "1.0");
339 356
340 request = """ 357 request = """
341 POST /test HTTP/1.1\r 358 POST /test HTTP/1.1\r
(...skipping 57 matching lines...) Expand 10 before | Expand all | Expand 10 after
399 _testParseRequest(request, "POST", "/test", expectedHeaders: headers); 416 _testParseRequest(request, "POST", "/test", expectedHeaders: headers);
400 417
401 request = """ 418 request = """
402 POST /test HTTP/1.1\r 419 POST /test HTTP/1.1\r
403 Content-Length: 10\r 420 Content-Length: 10\r
404 \r 421 \r
405 0123456789"""; 422 0123456789""";
406 _testParseRequest(request, 423 _testParseRequest(request,
407 "POST", 424 "POST",
408 "/test", 425 "/test",
409 expectedContentLength: 10, 426 expectedTransferLength: 10,
410 expectedBytesReceived: 10); 427 expectedBytesReceived: 10);
411 428
412 // Test connection close header. 429 // Test connection close header.
413 request = "GET /test HTTP/1.1\r\nConnection: close\r\n\r\n"; 430 request = "GET /test HTTP/1.1\r\nConnection: close\r\n\r\n";
414 _testParseRequest(request, "GET", "/test", connectionClose: true); 431 _testParseRequest(request, "GET", "/test", connectionClose: true);
415 432
416 // Test chunked encoding. 433 // Test chunked encoding.
417 request = """ 434 request = """
418 POST /test HTTP/1.1\r 435 POST /test HTTP/1.1\r
419 Transfer-Encoding: chunked\r 436 Transfer-Encoding: chunked\r
420 \r 437 \r
421 5\r 438 5\r
422 01234\r 439 01234\r
423 5\r 440 5\r
424 56789\r 441 56789\r
425 0\r\n\r\n"""; 442 0\r\n\r\n""";
426 _testParseRequest(request, 443 _testParseRequest(request,
427 "POST", 444 "POST",
428 "/test", 445 "/test",
429 expectedContentLength: -1, 446 expectedTransferLength: -1,
430 expectedBytesReceived: 10, 447 expectedBytesReceived: 10,
431 chunked: true); 448 chunked: true);
432 449
433 // Test mixing chunked encoding and content length (content length 450 // Test mixing chunked encoding and content length (content length
434 // is ignored). 451 // is ignored).
435 request = """ 452 request = """
436 POST /test HTTP/1.1\r 453 POST /test HTTP/1.1\r
437 Content-Length: 7\r 454 Content-Length: 7\r
438 Transfer-Encoding: chunked\r 455 Transfer-Encoding: chunked\r
439 \r 456 \r
440 5\r 457 5\r
441 01234\r 458 01234\r
442 5\r 459 5\r
443 56789\r 460 56789\r
444 0\r\n\r\n"""; 461 0\r\n\r\n""";
445 _testParseRequest(request, 462 _testParseRequest(request,
446 "POST", 463 "POST",
447 "/test", 464 "/test",
448 expectedContentLength: -1, 465 expectedTransferLength: -1,
449 expectedBytesReceived: 10, 466 expectedBytesReceived: 10,
450 chunked: true); 467 chunked: true);
451 468
452 // Test mixing chunked encoding and content length (content length 469 // Test mixing chunked encoding and content length (content length
453 // is ignored). 470 // is ignored).
454 request = """ 471 request = """
455 POST /test HTTP/1.1\r 472 POST /test HTTP/1.1\r
456 Transfer-Encoding: chunked\r 473 Transfer-Encoding: chunked\r
457 Content-Length: 3\r 474 Content-Length: 3\r
458 \r 475 \r
459 5\r 476 5\r
460 01234\r 477 01234\r
461 5\r 478 5\r
462 56789\r 479 56789\r
463 0\r\n\r\n"""; 480 0\r\n\r\n""";
464 _testParseRequest(request, 481 _testParseRequest(request,
465 "POST", 482 "POST",
466 "/test", 483 "/test",
467 expectedContentLength: -1, 484 expectedTransferLength: -1,
468 expectedBytesReceived: 10, 485 expectedBytesReceived: 10,
469 chunked: true); 486 chunked: true);
470 487
471 // Test upper and lower case hex digits in chunked encoding. 488 // Test upper and lower case hex digits in chunked encoding.
472 request = """ 489 request = """
473 POST /test HTTP/1.1\r 490 POST /test HTTP/1.1\r
474 Transfer-Encoding: chunked\r 491 Transfer-Encoding: chunked\r
475 \r 492 \r
476 1E\r 493 1E\r
477 012345678901234567890123456789\r 494 012345678901234567890123456789\r
478 1e\r 495 1e\r
479 012345678901234567890123456789\r 496 012345678901234567890123456789\r
480 0\r\n\r\n"""; 497 0\r\n\r\n""";
481 _testParseRequest(request, 498 _testParseRequest(request,
482 "POST", 499 "POST",
483 "/test", 500 "/test",
484 expectedContentLength: -1, 501 expectedTransferLength: -1,
485 expectedBytesReceived: 60, 502 expectedBytesReceived: 60,
486 chunked: true); 503 chunked: true);
487 504
488 // Test chunk extensions in chunked encoding. 505 // Test chunk extensions in chunked encoding.
489 request = """ 506 request = """
490 POST /test HTTP/1.1\r 507 POST /test HTTP/1.1\r
491 Transfer-Encoding: chunked\r 508 Transfer-Encoding: chunked\r
492 \r 509 \r
493 1E;xxx\r 510 1E;xxx\r
494 012345678901234567890123456789\r 511 012345678901234567890123456789\r
495 1E;yyy=zzz\r 512 1E;yyy=zzz\r
496 012345678901234567890123456789\r 513 012345678901234567890123456789\r
497 0\r\n\r\n"""; 514 0\r\n\r\n""";
498 _testParseRequest(request, 515 _testParseRequest(request,
499 "POST", 516 "POST",
500 "/test", 517 "/test",
501 expectedContentLength: -1, 518 expectedTransferLength: -1,
502 expectedBytesReceived: 60, 519 expectedBytesReceived: 60,
503 chunked: true); 520 chunked: true);
504 521
505 // Test HTTP upgrade. 522 // Test HTTP upgrade.
506 request = """ 523 request = """
507 GET /irc HTTP/1.1\r 524 GET /irc HTTP/1.1\r
508 Upgrade: irc/1.2\r 525 Upgrade: irc/1.2\r
509 Connection: Upgrade\r 526 Connection: Upgrade\r
510 \r\n\x01\x01\x01\x01\x01\x02\x02\x02\x02\xFF"""; 527 \r\n\x01\x01\x01\x01\x01\x02\x02\x02\x02\xFF""";
511 headers = new Map(); 528 headers = new Map();
(...skipping 67 matching lines...) Expand 10 before | Expand all | Expand 10 after
579 "/chat", 596 "/chat",
580 expectedHeaders: headers, 597 expectedHeaders: headers,
581 upgrade: true, 598 upgrade: true,
582 unparsedLength: 7); 599 unparsedLength: 7);
583 } 600 }
584 601
585 static void testParseResponse() { 602 static void testParseResponse() {
586 String response; 603 String response;
587 Map headers; 604 Map headers;
588 response = "HTTP/1.1 100 Continue\r\nContent-Length: 0\r\n\r\n"; 605 response = "HTTP/1.1 100 Continue\r\nContent-Length: 0\r\n\r\n";
589 _testParseResponse(response, 100, "Continue", expectedContentLength: 0); 606 _testParseResponse(response, 100, "Continue");
607
608 response = "HTTP/1.1 100 Continue\r\nContent-Length: 0\r\n\r\n";
609 _testParseResponse(response, 100, "Continue");
590 610
591 response = "HTTP/1.1 100 Continue\r\nContent-Length: 10\r\n\r\n"; 611 response = "HTTP/1.1 100 Continue\r\nContent-Length: 10\r\n\r\n";
592 _testParseResponse(response, 612 _testParseResponse(response,
593 100, 613 100,
594 "Continue", 614 "Continue",
595 expectedContentLength: 10, 615 expectedTransferLength: 10,
596 expectedBytesReceived: 0); 616 expectedBytesReceived: 0);
597 617
598 response = "HTTP/1.1 200 OK\r\nContent-Length: 0\r\n" 618 response = "HTTP/1.1 200 OK\r\nContent-Length: 0\r\n"
599 "Connection: Close\r\n\r\n"; 619 "Connection: Close\r\n\r\n";
600 _testParseResponse(response, 620 _testParseResponse(response,
601 200, 621 200,
602 "OK", 622 "OK",
603 expectedContentLength: 0,
604 connectionClose: true); 623 connectionClose: true);
605 624
606 response = "HTTP/1.0 200 OK\r\nContent-Length: 0\r\n\r\n"; 625 response = "HTTP/1.0 200 OK\r\nContent-Length: 0\r\n\r\n";
607 _testParseResponse(response, 626 _testParseResponse(response,
608 200, 627 200,
609 "OK", 628 "OK",
610 expectedContentLength: 0,
611 expectedVersion: "1.0", 629 expectedVersion: "1.0",
612 connectionClose: true); 630 connectionClose: true);
613 631
614 response = "HTTP/1.0 200 OK\r\nContent-Length: 0\r\n" 632 response = "HTTP/1.0 200 OK\r\nContent-Length: 0\r\n"
615 "Connection: Keep-Alive\r\n\r\n"; 633 "Connection: Keep-Alive\r\n\r\n";
616 _testParseResponse(response, 634 _testParseResponse(response,
617 200, 635 200,
618 "OK", 636 "OK",
619 expectedContentLength: 0,
620 expectedVersion: "1.0"); 637 expectedVersion: "1.0");
621 638
622 response = "HTTP/1.1 204 No Content\r\nContent-Length: 11\r\n\r\n"; 639 response = "HTTP/1.1 204 No Content\r\nContent-Length: 11\r\n\r\n";
623 _testParseResponse(response, 640 _testParseResponse(response,
624 204, 641 204,
625 "No Content", 642 "No Content",
626 expectedContentLength: 11, 643 expectedTransferLength: 11,
627 expectedBytesReceived: 0); 644 expectedBytesReceived: 0);
628 645
629 response = "HTTP/1.1 304 Not Modified\r\nContent-Length: 12\r\n\r\n"; 646 response = "HTTP/1.1 304 Not Modified\r\nContent-Length: 12\r\n\r\n";
630 _testParseResponse(response, 647 _testParseResponse(response,
631 304, 648 304,
632 "Not Modified", 649 "Not Modified",
633 expectedContentLength: 12, 650 expectedTransferLength: 12,
634 expectedBytesReceived: 0); 651 expectedBytesReceived: 0);
635 652
636 response = "HTTP/1.1 200 OK\r\nContent-Length: 0\r\n\r\n"; 653 response = "HTTP/1.1 200 OK\r\nContent-Length: 0\r\n\r\n";
637 _testParseResponse(response, 200, "OK", expectedContentLength: 0); 654 _testParseResponse(response, 200, "OK");
638 655
639 response = "HTTP/1.1 404 Not found\r\nContent-Length: 0\r\n\r\n"; 656 response = "HTTP/1.1 404 Not found\r\nContent-Length: 0\r\n\r\n";
640 _testParseResponse(response, 404, "Not found", expectedContentLength: 0); 657 _testParseResponse(response, 404, "Not found");
641 658
642 response = "HTTP/1.1 500 Server error\r\nContent-Length: 0\r\n\r\n"; 659 response = "HTTP/1.1 500 Server error\r\nContent-Length: 0\r\n\r\n";
643 _testParseResponse(response, 500, "Server error", expectedContentLength: 0); 660 _testParseResponse(response, 500, "Server error");
644 661
645 // Test response to HEAD request. 662 // Test response to HEAD request.
646 response = """ 663 response = """
647 HTTP/1.1 200 OK\r 664 HTTP/1.1 200 OK\r
648 Content-Length: 20\r 665 Content-Length: 20\r
649 Content-Type: text/html\r 666 Content-Type: text/html\r
650 \r\n"""; 667 \r\n""";
651 headers = new Map(); 668 headers = new Map();
652 headers["content-length"] = "20"; 669 headers["content-length"] = "20";
653 headers["content-type"] = "text/html"; 670 headers["content-type"] = "text/html";
654 _testParseResponse(response, 671 _testParseResponse(response,
655 200, 672 200,
656 "OK", 673 "OK",
657 responseToMethod: "HEAD", 674 responseToMethod: "HEAD",
658 expectedContentLength: 20, 675 expectedTransferLength: 20,
659 expectedBytesReceived: 0, 676 expectedBytesReceived: 0,
660 expectedHeaders: headers); 677 expectedHeaders: headers);
661 678
662 // Test content. 679 // Test content.
663 response = """ 680 response = """
664 HTTP/1.1 200 OK\r 681 HTTP/1.1 200 OK\r
665 Content-Length: 20\r 682 Content-Length: 20\r
666 \r 683 \r
667 01234567890123456789"""; 684 01234567890123456789""";
668 _testParseResponse(response, 685 _testParseResponse(response,
669 200, 686 200,
670 "OK", 687 "OK",
671 expectedContentLength: 20, 688 expectedTransferLength: 20,
672 expectedBytesReceived: 20); 689 expectedBytesReceived: 20);
673 690
674 // Test upper and lower case hex digits in chunked encoding. 691 // Test upper and lower case hex digits in chunked encoding.
675 response = """ 692 response = """
676 HTTP/1.1 200 OK\r 693 HTTP/1.1 200 OK\r
677 Transfer-Encoding: chunked\r 694 Transfer-Encoding: chunked\r
678 \r 695 \r
679 1A\r 696 1A\r
680 01234567890123456789012345\r 697 01234567890123456789012345\r
681 1f\r 698 1f\r
682 0123456789012345678901234567890\r 699 0123456789012345678901234567890\r
683 0\r\n\r\n"""; 700 0\r\n\r\n""";
684 _testParseResponse(response, 701 _testParseResponse(response,
685 200, 702 200,
686 "OK", 703 "OK",
687 expectedContentLength: -1, 704 expectedTransferLength: -1,
688 expectedBytesReceived: 57, 705 expectedBytesReceived: 57,
689 chunked: true); 706 chunked: true);
690 707
691 // Test connection close header. 708 // Test connection close header.
692 response = """ 709 response = """
693 HTTP/1.1 200 OK\r 710 HTTP/1.1 200 OK\r
694 Content-Length: 0\r 711 Content-Length: 0\r
695 Connection: close\r 712 Connection: close\r
696 \r\n"""; 713 \r\n""";
697 _testParseResponse(response, 714 _testParseResponse(response,
698 200, 715 200,
699 "OK", 716 "OK",
700 expectedContentLength: 0,
701 connectionClose: true); 717 connectionClose: true);
702 718
703 // Test HTTP response without any transfer length indications 719 // Test HTTP response without any transfer length indications
704 // where closing the connections indicates end of body. 720 // where closing the connections indicates end of body.
705 response = """ 721 response = """
706 HTTP/1.1 200 OK\r 722 HTTP/1.1 200 OK\r
707 \r 723 \r
708 01234567890123456789012345 724 01234567890123456789012345
709 0123456789012345678901234567890 725 0123456789012345678901234567890
710 """; 726 """;
711 _testParseResponse(response, 727 _testParseResponse(response,
712 200, 728 200,
713 "OK", 729 "OK",
714 expectedContentLength: -1, 730 expectedTransferLength: -1,
715 expectedBytesReceived: 59, 731 expectedBytesReceived: 59,
716 close: true, 732 close: true,
717 connectionClose: true); 733 connectionClose: true);
718 734
719 // Test HTTP upgrade. 735 // Test HTTP upgrade.
720 response = """ 736 response = """
721 HTTP/1.1 101 Switching Protocols\r 737 HTTP/1.1 101 Switching Protocols\r
722 Upgrade: irc/1.2\r 738 Upgrade: irc/1.2\r
723 Connection: Upgrade\r 739 Connection: Upgrade\r
724 \r\n"""; 740 \r\n""";
(...skipping 133 matching lines...) Expand 10 before | Expand all | Expand 10 after
858 0123456789012345678901234567890\r 874 0123456789012345678901234567890\r
859 0\r\n\r\n"""; 875 0\r\n\r\n""";
860 _testParseInvalidResponse(response); 876 _testParseInvalidResponse(response);
861 } 877 }
862 } 878 }
863 879
864 880
865 void main() { 881 void main() {
866 HttpParserTest.runAllTests(); 882 HttpParserTest.runAllTests();
867 } 883 }
OLDNEW
« no previous file with comments | « tests/standalone/io/http_headers_test.dart ('k') | tests/standalone/io/http_proxy_test.dart » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698