| OLD | NEW |
| 1 // Copyright (c) 2012, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2012, 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 // Global constants. | 5 // Global constants. |
| 6 class _Const { | 6 class _Const { |
| 7 // Bytes for "HTTP/1.0". | 7 // Bytes for "HTTP/1.0". |
| 8 static final HTTP10 = const [72, 84, 84, 80, 47, 49, 46, 48]; | 8 static final HTTP10 = const [72, 84, 84, 80, 47, 49, 46, 48]; |
| 9 // Bytes for "HTTP/1.1". | 9 // Bytes for "HTTP/1.1". |
| 10 static final HTTP11 = const [72, 84, 84, 80, 47, 49, 46, 49]; | 10 static final HTTP11 = const [72, 84, 84, 80, 47, 49, 46, 49]; |
| (...skipping 916 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 927 int available = _socket.available(); | 927 int available = _socket.available(); |
| 928 if (available == 0) { | 928 if (available == 0) { |
| 929 return; | 929 return; |
| 930 } | 930 } |
| 931 | 931 |
| 932 ByteArray buffer = new ByteArray(available); | 932 ByteArray buffer = new ByteArray(available); |
| 933 int bytesRead = _socket.readList(buffer, 0, available); | 933 int bytesRead = _socket.readList(buffer, 0, available); |
| 934 if (bytesRead > 0) { | 934 if (bytesRead > 0) { |
| 935 int parsed = _httpParser.writeList(buffer, 0, bytesRead); | 935 int parsed = _httpParser.writeList(buffer, 0, bytesRead); |
| 936 if (parsed != bytesRead) { | 936 if (parsed != bytesRead) { |
| 937 print("Failed to parse HTTP data $parsed $bytesRead"); | 937 // TODO(sgjesse): Error handling. |
| 938 _socket.close(); | 938 _socket.close(); |
| 939 } | 939 } |
| 940 } | 940 } |
| 941 } | 941 } |
| 942 | 942 |
| 943 void _closeHandler() { | 943 void _closeHandler() { |
| 944 // Client closed socket for writing. Socket should still be open | 944 // Client closed socket for writing. Socket should still be open |
| 945 // for writing the response. | 945 // for writing the response. |
| 946 _closing = true; | 946 _closing = true; |
| 947 if (_disconnectHandlerCallback != null) _disconnectHandlerCallback(); | 947 if (_disconnectHandlerCallback != null) _disconnectHandlerCallback(); |
| (...skipping 77 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1025 HttpResponse _response; | 1025 HttpResponse _response; |
| 1026 | 1026 |
| 1027 // Callbacks. | 1027 // Callbacks. |
| 1028 var requestReceived; | 1028 var requestReceived; |
| 1029 } | 1029 } |
| 1030 | 1030 |
| 1031 | 1031 |
| 1032 // HTTP server waiting for socket connections. The connections are | 1032 // HTTP server waiting for socket connections. The connections are |
| 1033 // managed by the server and as requests are received the request. | 1033 // managed by the server and as requests are received the request. |
| 1034 class _HttpServer implements HttpServer { | 1034 class _HttpServer implements HttpServer { |
| 1035 _HttpServer () : _debugTrace = false; | |
| 1036 | |
| 1037 void listen(String host, int port, [int backlog = 5]) { | 1035 void listen(String host, int port, [int backlog = 5]) { |
| 1038 | 1036 |
| 1039 void connectionHandler(Socket socket) { | 1037 void connectionHandler(Socket socket) { |
| 1040 // Accept the client connection. | 1038 // Accept the client connection. |
| 1041 _HttpConnection connection = new _HttpConnection(); | 1039 _HttpConnection connection = new _HttpConnection(); |
| 1042 connection._connectionEstablished(socket); | 1040 connection._connectionEstablished(socket); |
| 1043 connection.requestReceived = _requestHandler; | 1041 connection.requestReceived = _requestHandler; |
| 1044 _connections.add(connection); | 1042 _connections.add(connection); |
| 1045 if (_debugTrace) { | |
| 1046 print("New connection (total ${_connections.length} connections)"); | |
| 1047 } | |
| 1048 void disconnectHandler() { | 1043 void disconnectHandler() { |
| 1049 for (int i = 0; i < _connections.length; i++) { | 1044 for (int i = 0; i < _connections.length; i++) { |
| 1050 if (_connections[i] == connection) { | 1045 if (_connections[i] == connection) { |
| 1051 _connections.removeRange(i, 1); | 1046 _connections.removeRange(i, 1); |
| 1052 break; | 1047 break; |
| 1053 } | 1048 } |
| 1054 } | 1049 } |
| 1055 if (_debugTrace) { | |
| 1056 print("Closed connection (total ${_connections.length} connections)"); | |
| 1057 } | |
| 1058 } | 1050 } |
| 1059 connection.disconnectHandler = disconnectHandler; | 1051 connection.disconnectHandler = disconnectHandler; |
| 1060 void errorHandler(String errorMessage) { | 1052 void errorHandler(String errorMessage) { |
| 1061 if (_errorHandler != null) _errorHandler(errorMessage); | 1053 if (_errorHandler != null) _errorHandler(errorMessage); |
| 1062 } | 1054 } |
| 1063 connection.errorHandler = errorHandler; | 1055 connection.errorHandler = errorHandler; |
| 1064 } | 1056 } |
| 1065 | 1057 |
| 1066 // TODO(ajohnsen): Use Set once Socket is Hashable. | 1058 // TODO(ajohnsen): Use Set once Socket is Hashable. |
| 1067 _connections = new List<_HttpConnection>(); | 1059 _connections = new List<_HttpConnection>(); |
| 1068 _server = new ServerSocket(host, port, backlog); | 1060 _server = new ServerSocket(host, port, backlog); |
| 1069 _server.connectionHandler = connectionHandler; | 1061 _server.connectionHandler = connectionHandler; |
| 1070 } | 1062 } |
| 1071 | 1063 |
| 1072 void close() => _server.close(); | 1064 void close() => _server.close(); |
| 1073 int get port() => _server.port; | 1065 int get port() => _server.port; |
| 1074 | 1066 |
| 1075 void set errorHandler(void handler(String errorMessage)) { | 1067 void set errorHandler(void handler(String errorMessage)) { |
| 1076 _errorHandler = handler; | 1068 _errorHandler = handler; |
| 1077 } | 1069 } |
| 1078 | 1070 |
| 1079 void set requestHandler(void handler(HttpRequest, HttpResponse)) { | 1071 void set requestHandler(void handler(HttpRequest, HttpResponse)) { |
| 1080 _requestHandler = handler; | 1072 _requestHandler = handler; |
| 1081 } | 1073 } |
| 1082 | 1074 |
| 1083 ServerSocket _server; // The server listen socket. | 1075 ServerSocket _server; // The server listen socket. |
| 1084 List<_HttpConnection> _connections; // List of currently connected clients. | 1076 List<_HttpConnection> _connections; // List of currently connected clients. |
| 1085 Function _requestHandler; | 1077 Function _requestHandler; |
| 1086 Function _errorHandler; | 1078 Function _errorHandler; |
| 1087 bool _debugTrace; | |
| 1088 } | 1079 } |
| 1089 | 1080 |
| 1090 | 1081 |
| 1091 class _HttpClientRequest | 1082 class _HttpClientRequest |
| 1092 extends _HttpRequestResponseBase implements HttpClientRequest { | 1083 extends _HttpRequestResponseBase implements HttpClientRequest { |
| 1093 static final int START = 0; | 1084 static final int START = 0; |
| 1094 static final int HEADERS_SENT = 1; | 1085 static final int HEADERS_SENT = 1; |
| 1095 static final int DONE = 2; | 1086 static final int DONE = 2; |
| 1096 | 1087 |
| 1097 _HttpClientRequest(String this._method, | 1088 _HttpClientRequest(String this._method, |
| (...skipping 417 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1515 Map<String, Queue<_SocketConnection>> _openSockets; | 1506 Map<String, Queue<_SocketConnection>> _openSockets; |
| 1516 Timer _evictionTimer; | 1507 Timer _evictionTimer; |
| 1517 bool _shutdown; // Has this HTTP client been shutdown? | 1508 bool _shutdown; // Has this HTTP client been shutdown? |
| 1518 } | 1509 } |
| 1519 | 1510 |
| 1520 | 1511 |
| 1521 class HttpUtil { | 1512 class HttpUtil { |
| 1522 static String decodeUrlEncodedString(String urlEncoded) { | 1513 static String decodeUrlEncodedString(String urlEncoded) { |
| 1523 void invalidEscape() { | 1514 void invalidEscape() { |
| 1524 // TODO(sgjesse): Handle the error. | 1515 // TODO(sgjesse): Handle the error. |
| 1525 print("Invalid escape code."); | |
| 1526 } | 1516 } |
| 1527 | 1517 |
| 1528 StringBuffer result = new StringBuffer(); | 1518 StringBuffer result = new StringBuffer(); |
| 1529 for (int ii = 0; urlEncoded.length > ii; ++ii) { | 1519 for (int ii = 0; urlEncoded.length > ii; ++ii) { |
| 1530 if ('+' == urlEncoded[ii]) { | 1520 if ('+' == urlEncoded[ii]) { |
| 1531 result.add(' '); | 1521 result.add(' '); |
| 1532 } else if ('%' == urlEncoded[ii] && | 1522 } else if ('%' == urlEncoded[ii] && |
| 1533 urlEncoded.length - 2 > ii) { | 1523 urlEncoded.length - 2 > ii) { |
| 1534 try { | 1524 try { |
| 1535 int charCode = | 1525 int charCode = |
| (...skipping 34 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1570 } else { | 1560 } else { |
| 1571 value = queryString.substring(currentPosition, position); | 1561 value = queryString.substring(currentPosition, position); |
| 1572 currentPosition = position + 1; | 1562 currentPosition = position + 1; |
| 1573 } | 1563 } |
| 1574 result[HttpUtil.decodeUrlEncodedString(name)] = | 1564 result[HttpUtil.decodeUrlEncodedString(name)] = |
| 1575 HttpUtil.decodeUrlEncodedString(value); | 1565 HttpUtil.decodeUrlEncodedString(value); |
| 1576 } | 1566 } |
| 1577 return result; | 1567 return result; |
| 1578 } | 1568 } |
| 1579 } | 1569 } |
| OLD | NEW |