OLD | NEW |
1 // Copyright (c) 2013, 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 part of dart.io; | 5 part of dart.io; |
6 | 6 |
7 const int _OUTGOING_BUFFER_SIZE = 8 * 1024; | 7 const int _OUTGOING_BUFFER_SIZE = 8 * 1024; |
8 | 8 |
9 class _HttpIncoming extends Stream<List<int>> { | 9 class _HttpIncoming extends Stream<List<int>> { |
10 final int _transferLength; | 10 final int _transferLength; |
(...skipping 411 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
422 | 422 |
423 bool _bufferOutput = true; | 423 bool _bufferOutput = true; |
424 | 424 |
425 final Uri _uri; | 425 final Uri _uri; |
426 final _HttpOutgoing _outgoing; | 426 final _HttpOutgoing _outgoing; |
427 | 427 |
428 final _HttpHeaders headers; | 428 final _HttpHeaders headers; |
429 | 429 |
430 _HttpOutboundMessage(Uri uri, | 430 _HttpOutboundMessage(Uri uri, |
431 String protocolVersion, | 431 String protocolVersion, |
432 _HttpOutgoing outgoing) | 432 _HttpOutgoing outgoing, |
| 433 {_HttpHeaders initialHeaders}) |
433 : super(outgoing, null), | 434 : super(outgoing, null), |
434 _uri = uri, | 435 _uri = uri, |
435 headers = new _HttpHeaders( | 436 headers = new _HttpHeaders( |
436 protocolVersion, | 437 protocolVersion, |
437 defaultPortForScheme: uri.scheme == 'https' ? | 438 defaultPortForScheme: uri.scheme == 'https' ? |
438 HttpClient.DEFAULT_HTTPS_PORT : | 439 HttpClient.DEFAULT_HTTPS_PORT : |
439 HttpClient.DEFAULT_HTTP_PORT), | 440 HttpClient.DEFAULT_HTTP_PORT, |
| 441 initialHeaders: initialHeaders), |
440 _outgoing = outgoing { | 442 _outgoing = outgoing { |
441 _outgoing.outbound = this; | 443 _outgoing.outbound = this; |
442 _encodingMutable = false; | 444 _encodingMutable = false; |
443 } | 445 } |
444 | 446 |
445 int get contentLength => headers.contentLength; | 447 int get contentLength => headers.contentLength; |
446 void set contentLength(int contentLength) { | 448 void set contentLength(int contentLength) { |
447 headers.contentLength = contentLength; | 449 headers.contentLength = contentLength; |
448 } | 450 } |
449 | 451 |
(...skipping 46 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
496 int _statusCode = 200; | 498 int _statusCode = 200; |
497 String _reasonPhrase; | 499 String _reasonPhrase; |
498 List<Cookie> _cookies; | 500 List<Cookie> _cookies; |
499 _HttpRequest _httpRequest; | 501 _HttpRequest _httpRequest; |
500 Duration _deadline; | 502 Duration _deadline; |
501 Timer _deadlineTimer; | 503 Timer _deadlineTimer; |
502 | 504 |
503 _HttpResponse(Uri uri, | 505 _HttpResponse(Uri uri, |
504 String protocolVersion, | 506 String protocolVersion, |
505 _HttpOutgoing outgoing, | 507 _HttpOutgoing outgoing, |
| 508 HttpHeaders defaultHeaders, |
506 String serverHeader) | 509 String serverHeader) |
507 : super(uri, protocolVersion, outgoing) { | 510 : super(uri, protocolVersion, outgoing, initialHeaders: defaultHeaders) { |
508 if (serverHeader != null) headers._add('server', serverHeader); | 511 if (serverHeader != null) headers.set('server', serverHeader); |
509 } | 512 } |
510 | 513 |
511 bool get _isConnectionClosed => _httpRequest._httpConnection._isClosing; | 514 bool get _isConnectionClosed => _httpRequest._httpConnection._isClosing; |
512 | 515 |
513 List<Cookie> get cookies { | 516 List<Cookie> get cookies { |
514 if (_cookies == null) _cookies = new List<Cookie>(); | 517 if (_cookies == null) _cookies = new List<Cookie>(); |
515 return _cookies; | 518 return _cookies; |
516 } | 519 } |
517 | 520 |
518 int get statusCode => _statusCode; | 521 int get statusCode => _statusCode; |
(...skipping 1511 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2030 if (closing) destroy(); | 2033 if (closing) destroy(); |
2031 }); | 2034 }); |
2032 // Only handle one incoming request at the time. Keep the | 2035 // Only handle one incoming request at the time. Keep the |
2033 // stream paused until the request has been send. | 2036 // stream paused until the request has been send. |
2034 _subscription.pause(); | 2037 _subscription.pause(); |
2035 _state = _ACTIVE; | 2038 _state = _ACTIVE; |
2036 var outgoing = new _HttpOutgoing(_socket); | 2039 var outgoing = new _HttpOutgoing(_socket); |
2037 var response = new _HttpResponse(incoming.uri, | 2040 var response = new _HttpResponse(incoming.uri, |
2038 incoming.headers.protocolVersion, | 2041 incoming.headers.protocolVersion, |
2039 outgoing, | 2042 outgoing, |
| 2043 _httpServer.defaultResponseHeaders, |
2040 _httpServer.serverHeader); | 2044 _httpServer.serverHeader); |
2041 var request = new _HttpRequest(response, incoming, _httpServer, this); | 2045 var request = new _HttpRequest(response, incoming, _httpServer, this); |
2042 _streamFuture = outgoing.done | 2046 _streamFuture = outgoing.done |
2043 .then((_) { | 2047 .then((_) { |
2044 response.deadline = null; | 2048 response.deadline = null; |
2045 if (_state == _DETACHED) return; | 2049 if (_state == _DETACHED) return; |
2046 if (response.persistentConnection && | 2050 if (response.persistentConnection && |
2047 request.persistentConnection && | 2051 request.persistentConnection && |
2048 incoming.fullBodyRead && | 2052 incoming.fullBodyRead && |
2049 !_httpParser.upgrade && | 2053 !_httpParser.upgrade && |
(...skipping 98 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2148 | 2152 |
2149 | 2153 |
2150 // HTTP server waiting for socket connections. | 2154 // HTTP server waiting for socket connections. |
2151 class _HttpServer | 2155 class _HttpServer |
2152 extends Stream<HttpRequest> with _ServiceObject | 2156 extends Stream<HttpRequest> with _ServiceObject |
2153 implements HttpServer { | 2157 implements HttpServer { |
2154 // Use default Map so we keep order. | 2158 // Use default Map so we keep order. |
2155 static Map<int, _HttpServer> _servers = new Map<int, _HttpServer>(); | 2159 static Map<int, _HttpServer> _servers = new Map<int, _HttpServer>(); |
2156 | 2160 |
2157 String serverHeader; | 2161 String serverHeader; |
| 2162 final HttpHeaders defaultResponseHeaders = _initDefaultResponseHeaders(); |
2158 | 2163 |
2159 Duration _idleTimeout; | 2164 Duration _idleTimeout; |
2160 Timer _idleTimer; | 2165 Timer _idleTimer; |
2161 | 2166 |
2162 static Future<HttpServer> bind(address, int port, int backlog) { | 2167 static Future<HttpServer> bind(address, int port, int backlog) { |
2163 return ServerSocket.bind(address, port, backlog: backlog).then((socket) { | 2168 return ServerSocket.bind(address, port, backlog: backlog).then((socket) { |
2164 return new _HttpServer._(socket, true); | 2169 return new _HttpServer._(socket, true); |
2165 }); | 2170 }); |
2166 } | 2171 } |
2167 | 2172 |
(...skipping 22 matching lines...) Expand all Loading... |
2190 } | 2195 } |
2191 | 2196 |
2192 _HttpServer.listenOn(this._serverSocket) : _closeServer = false { | 2197 _HttpServer.listenOn(this._serverSocket) : _closeServer = false { |
2193 _controller = new StreamController<HttpRequest>(sync: true, | 2198 _controller = new StreamController<HttpRequest>(sync: true, |
2194 onCancel: close); | 2199 onCancel: close); |
2195 idleTimeout = const Duration(seconds: 120); | 2200 idleTimeout = const Duration(seconds: 120); |
2196 _servers[_serviceId] = this; | 2201 _servers[_serviceId] = this; |
2197 try { _serverSocket._owner = this; } catch (_) {} | 2202 try { _serverSocket._owner = this; } catch (_) {} |
2198 } | 2203 } |
2199 | 2204 |
| 2205 static HttpHeaders _initDefaultResponseHeaders() { |
| 2206 var defaultResponseHeaders = new _HttpHeaders('1.1'); |
| 2207 defaultResponseHeaders.contentType = ContentType.TEXT; |
| 2208 defaultResponseHeaders.set('X-Frame-Options', 'SAMEORIGIN'); |
| 2209 defaultResponseHeaders.set('X-Content-Type-Options', 'nosniff'); |
| 2210 defaultResponseHeaders.set('X-XSS-Protection', '1; mode=block'); |
| 2211 return defaultResponseHeaders; |
| 2212 } |
| 2213 |
2200 Duration get idleTimeout => _idleTimeout; | 2214 Duration get idleTimeout => _idleTimeout; |
2201 | 2215 |
2202 void set idleTimeout(Duration duration) { | 2216 void set idleTimeout(Duration duration) { |
2203 if (_idleTimer != null) { | 2217 if (_idleTimer != null) { |
2204 _idleTimer.cancel(); | 2218 _idleTimer.cancel(); |
2205 _idleTimer = null; | 2219 _idleTimer = null; |
2206 } | 2220 } |
2207 _idleTimeout = duration; | 2221 _idleTimeout = duration; |
2208 if (_idleTimeout != null) { | 2222 if (_idleTimeout != null) { |
2209 _idleTimer = new Timer.periodic(_idleTimeout, (_) { | 2223 _idleTimer = new Timer.periodic(_idleTimeout, (_) { |
(...skipping 593 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2803 const _RedirectInfo(this.statusCode, this.method, this.location); | 2817 const _RedirectInfo(this.statusCode, this.method, this.location); |
2804 } | 2818 } |
2805 | 2819 |
2806 String _getHttpVersion() { | 2820 String _getHttpVersion() { |
2807 var version = Platform.version; | 2821 var version = Platform.version; |
2808 // Only include major and minor version numbers. | 2822 // Only include major and minor version numbers. |
2809 int index = version.indexOf('.', version.indexOf('.') + 1); | 2823 int index = version.indexOf('.', version.indexOf('.') + 1); |
2810 version = version.substring(0, index); | 2824 version = version.substring(0, index); |
2811 return 'Dart/$version (dart:io)'; | 2825 return 'Dart/$version (dart:io)'; |
2812 } | 2826 } |
OLD | NEW |