Chromium Code Reviews| Index: chrome/browser/chromeos/gdata/test_servers/http_request.h |
| diff --git a/chrome/browser/chromeos/gdata/test_servers/http_request.h b/chrome/browser/chromeos/gdata/test_servers/http_request.h |
| new file mode 100644 |
| index 0000000000000000000000000000000000000000..9764fec4f638c35299d8ff74b16e0423337e47d4 |
| --- /dev/null |
| +++ b/chrome/browser/chromeos/gdata/test_servers/http_request.h |
| @@ -0,0 +1,143 @@ |
| +// Copyright (c) 2012 The Chromium Authors. All rights reserved. |
| +// Use of this source code is governed by a BSD-style license that can be |
| +// found in the LICENSE file. |
| + |
| +#ifndef CHROME_BROWSER_CHROMEOS_GDATA_TEST_SERVERS_HTTP_REQUEST_H_ |
| +#define CHROME_BROWSER_CHROMEOS_GDATA_TEST_SERVERS_HTTP_REQUEST_H_ |
| + |
| +#include <map> |
| +#include <string> |
| +#include "base/basictypes.h" |
| +#include "base/memory/scoped_ptr.h" |
| +#include "googleurl/src/gurl.h" |
| + |
| +namespace gdata { |
| +namespace test_servers { |
| + |
| +enum HTTP_METHOD { |
|
satorux1
2012/10/12 08:29:18
HttpMethod
mtomasz
2012/10/12 11:09:46
Here I am confused. On chromium website they sugge
satorux1
2012/10/16 03:12:18
MACRO_STYLE is for members. The enum types should
|
| + UNKNOWN = 0, |
| + OPTIONS = 1, |
| + GET = 2, |
| + HEAD = 4, |
|
satorux1
2012/10/12 08:29:18
The following would be better:
OPTIONS = 1 << 0,
mtomasz
2012/10/12 11:09:46
I wanted to use it in the future for bit sets, lik
|
| + POST = 8, |
| + PUT = 16, |
| + DELETE = 32, |
| + TRACE = 64, |
| + CONNECT = 128, |
| + CUSTOM = 256 |
|
satorux1
2012/10/12 08:29:18
Do we need all the method types? I'd suggest to re
mtomasz
2012/10/12 11:09:46
Done.
|
| +}; |
| + |
| +// Wraps the HTTP request. Since it can be big, use scoped_ptr to pass it |
| +// instead of copying. |
| +class HttpRequest { |
| + public: |
| + HttpRequest() : method(UNKNOWN) {} |
| + virtual ~HttpRequest() {} |
| + |
| + GURL url; |
| + HTTP_METHOD method; |
| + std::string raw_url; |
| + std::string protocol; |
| + std::map<std::string, std::string> headers; |
| + std::string content; |
| + |
| + private: |
| + DISALLOW_COPY_AND_ASSIGN(HttpRequest); |
| +}; |
| + |
| +// Parses the input data and produces valid HttpRequest objects. The common |
| +// use is as below: |
| +// HttpRequestParser parser; |
| +// (...) |
| +// void OnDataChunkReceived(Socket* socket, const char* data, int size) { |
| +// parser.ProcessChunk(data, size); |
| +// STATE parser_state; |
| +// while ((parser_state = ParseRequest()) == HttpRequestParser::READY) { |
| +// scoped_ptr<HttpRequest> request = parser.GetRequest(); |
| +// (... process the request ...) |
| +// } |
| +// if (parser_state == HttpRequestParser::SYNTAX_ERROR) |
| +// socket.Close(); |
| +class HttpRequestParser { |
| + public: |
| + // State of the parser. |
| + enum STATE { |
|
satorux1
2012/10/12 08:29:18
Enum names should look like State
|
| + REQUEST_LINE, |
| + HEADER_LINE, |
| + DATA, |
| + READY, |
| + SYNTAX_ERROR |
|
satorux1
2012/10/12 08:29:18
Please add , at the end. it makes slightly easier
mtomasz
2012/10/12 11:09:46
Done.
|
| + }; |
|
satorux1
2012/10/12 08:29:18
Please add comments for each state.
mtomasz
2012/10/12 11:09:46
Done.
|
| + |
| + HttpRequestParser(); |
| + virtual ~HttpRequestParser(); |
| + |
| + // Adds chunk of data into the internal buffer. |
| + virtual void ProcessChunk(const char *data, int length); |
| + |
| + // Parses the http request (including data - if provided) according to: |
| + // http://www.w3.org/Protocols/rfc2616/rfc2616-sec4.html. |
| + // If returns READY, then it means that the whole request has been found |
| + // in the internal buffer (and parsed). After calling GetRequest(), it will be |
| + // ready to parse another request. If the parser enters the SYNTAX_ERROR |
| + // state, then no further parsing will possible. |
| + STATE ParseRequest(); |
| + |
| + // Retrieves parsed request. Can be only called, when the parser is in READY |
| + // state. You can call it once, since it clears the internal request builder |
| + // after a call. |
| + scoped_ptr<HttpRequest> GetRequest(); |
| + |
| + private: |
| + // This is a type of token for ShiftToken() method. IDENTIFIER is a token |
| + // ended with a space, HEADER_KEY is ended with colon, LINE is a token |
| + // including anything until the first \r\n occurence. |
| + enum SHIFT_TOKEN_TYPE { |
| + IDENTIFIER, |
| + HEADER_KEY, |
| + LINE, |
| + }; |
| + |
| + std::string buffer_; |
| + scoped_ptr<HttpRequest> request_builder_; |
| + STATE state_; |
| + |
| + int buffer_position_; |
| + int crlf_position_; |
| + int crlf_checked_position_; |
| + int current_content_length_; |
| + |
| + // Received a token from the internal buffer and shifts the buffer's pointer. |
| + virtual std::string ShiftToken(SHIFT_TOKEN_TYPE token_type); |
| + |
| + // Shifts \r\n from the current position in the internal buffer. If not found, |
| + // then returns false. |
| + virtual bool ShiftCrLf(); |
| + |
| + // Shifts |length| number of bytes from the current position in the buffer. |
| + // Passed argument's value must be less or equal to available bytes in the |
| + // internal buffer (from the current position). Returned pointer is not a |
| + // string, but a pointer to the requested data. Especially, it is not null- |
| + // terminated. |
| + virtual const char* ShiftData(int length); |
|
satorux1
2012/10/12 08:29:18
You might want to use StringPiece instead of char*
mtomasz
2012/10/12 11:09:46
Done.
|
| + |
| + // Skips all the spaces in the beginning of the current position of the |
| + // internal buffer. |
| + virtual void SkipSpaces(); |
| + |
| + // This helper function tells if there is a reason to process new data in |
| + // the internal buffer. Parsing the request is performed line by line for |
| + // headers, however for content it is parsed as soon as new chunk arrives. |
| + virtual bool ShouldParseBuffer(); |
| + |
| + // Helper function, updates the |crlf_position_| member with a valid value. |
| + // The member stores position of the first \r\n occurence in the internal |
| + // buffer after the previous one. Returns true if the CrLF sequence was |
| + // found. |
| + virtual bool FindNextCrLf(); |
| +}; |
| + |
| +} // namespace test_servers |
| +} // namespace gdata |
| + |
| +#endif // CHROME_BROWSER_CHROMEOS_GDATA_TEST_SERVERS_HTTP_REQUEST_H_ |