http_message.h 4.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138
  1. // Copyright (c) 2014 Baidu, Inc.
  2. //
  3. // Licensed under the Apache License, Version 2.0 (the "License");
  4. // you may not use this file except in compliance with the License.
  5. // You may obtain a copy of the License at
  6. //
  7. // http://www.apache.org/licenses/LICENSE-2.0
  8. //
  9. // Unless required by applicable law or agreed to in writing, software
  10. // distributed under the License is distributed on an "AS IS" BASIS,
  11. // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  12. // See the License for the specific language governing permissions and
  13. // limitations under the License.
  14. // Authors: Zhangyi Chen (chenzhangyi01@baidu.com)
  15. // Ge,Jun (gejun@baidu.com)
  16. #ifndef BRPC_HTTP_MESSAGE_H
  17. #define BRPC_HTTP_MESSAGE_H
  18. #include <string> // std::string
  19. #include "butil/macros.h"
  20. #include "butil/iobuf.h" // butil::IOBuf
  21. #include "butil/scoped_lock.h" // butil::unique_lock
  22. #include "brpc/details/http_parser.h" // http_parser
  23. #include "brpc/http_header.h" // HttpHeader
  24. #include "brpc/progressive_reader.h" // ProgressiveReader
  25. namespace brpc {
  26. enum HttpParserStage {
  27. HTTP_ON_MESSAGE_BEGIN,
  28. HTTP_ON_URL,
  29. HTTP_ON_STATUS,
  30. HTTP_ON_HEADER_FIELD,
  31. HTTP_ON_HEADER_VALUE,
  32. HTTP_ON_HEADERS_COMPLELE,
  33. HTTP_ON_BODY,
  34. HTTP_ON_MESSAGE_COMPLELE
  35. };
  36. class HttpMessage {
  37. public:
  38. // If read_body_progressively is true, the body will be read progressively
  39. // by using SetBodyReader().
  40. explicit HttpMessage(bool read_body_progressively = false);
  41. ~HttpMessage();
  42. const butil::IOBuf &body() const { return _body; }
  43. butil::IOBuf &body() { return _body; }
  44. // Parse from array, length=0 is treated as EOF.
  45. // Returns bytes parsed, -1 on failure.
  46. ssize_t ParseFromArray(const char *data, const size_t length);
  47. // Parse from butil::IOBuf.
  48. // Emtpy `buf' is sliently ignored, which is different from ParseFromArray.
  49. // Returns bytes parsed, -1 on failure.
  50. ssize_t ParseFromIOBuf(const butil::IOBuf &buf);
  51. bool Completed() const { return _stage == HTTP_ON_MESSAGE_COMPLELE; }
  52. HttpParserStage stage() const { return _stage; }
  53. HttpHeader &header() { return _header; }
  54. const HttpHeader &header() const { return _header; }
  55. size_t parsed_length() const { return _parsed_length; }
  56. // Http parser callback functions
  57. static int on_message_begin(http_parser *);
  58. static int on_url(http_parser *, const char *, const size_t);
  59. static int on_status(http_parser*, const char *, const size_t);
  60. static int on_header_field(http_parser *, const char *, const size_t);
  61. static int on_header_value(http_parser *, const char *, const size_t);
  62. static int on_headers_complete(http_parser *);
  63. static int on_body_cb(http_parser*, const char *, const size_t);
  64. static int on_message_complete_cb(http_parser *);
  65. const http_parser& parser() const { return _parser; }
  66. bool read_body_progressively() const { return _read_body_progressively; }
  67. // Send new parts of the body to the reader. If the body already has some
  68. // data, feed them to the reader immediately.
  69. // Any error during the setting will destroy the reader.
  70. void SetBodyReader(ProgressiveReader* r);
  71. protected:
  72. int OnBody(const char* data, size_t size);
  73. int OnMessageComplete();
  74. size_t _parsed_length;
  75. private:
  76. DISALLOW_COPY_AND_ASSIGN(HttpMessage);
  77. int UnlockAndFlushToBodyReader(std::unique_lock<butil::Mutex>& locked);
  78. HttpParserStage _stage;
  79. std::string _url;
  80. HttpHeader _header;
  81. bool _read_body_progressively;
  82. // For mutual exclusion between on_body and SetBodyReader.
  83. butil::Mutex _body_mutex;
  84. // Read body progressively
  85. ProgressiveReader* _body_reader;
  86. butil::IOBuf _body;
  87. // Parser related members
  88. struct http_parser _parser;
  89. std::string _cur_header;
  90. std::string *_cur_value;
  91. protected:
  92. // Only valid when -http_verbose is on
  93. butil::IOBufBuilder* _vmsgbuilder;
  94. size_t _body_length;
  95. };
  96. std::ostream& operator<<(std::ostream& os, const http_parser& parser);
  97. // Serialize a http request.
  98. // header: may be modified in some cases
  99. // remote_side: used when "Host" is absent
  100. // content: could be NULL.
  101. void SerializeHttpRequest(butil::IOBuf* request,
  102. HttpHeader* header,
  103. const butil::EndPoint& remote_side,
  104. const butil::IOBuf* content);
  105. // Serialize a http response.
  106. // header: may be modified in some cases
  107. // content: cleared after usage. could be NULL.
  108. void SerializeHttpResponse(butil::IOBuf* response,
  109. HttpHeader* header,
  110. butil::IOBuf* content);
  111. } // namespace brpc
  112. #endif // BRPC_HTTP_MESSAGE_H