HttpHandler.h 3.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143
  1. #ifndef HV_HTTP_HANDLER_H_
  2. #define HV_HTTP_HANDLER_H_
  3. #include "HttpService.h"
  4. #include "HttpParser.h"
  5. #include "FileCache.h"
  6. #include "WebSocketServer.h"
  7. #include "WebSocketParser.h"
  8. class HttpHandler {
  9. public:
  10. enum ProtocolType {
  11. UNKNOWN,
  12. HTTP_V1,
  13. HTTP_V2,
  14. WEBSOCKET,
  15. } protocol;
  16. enum State {
  17. WANT_RECV,
  18. HANDLE_BEGIN,
  19. HANDLE_CONTINUE,
  20. HANDLE_END,
  21. WANT_SEND,
  22. SEND_HEADER,
  23. SEND_BODY,
  24. SEND_DONE,
  25. } state;
  26. // peeraddr
  27. bool ssl;
  28. char ip[64];
  29. int port;
  30. // for http
  31. HttpService *service;
  32. FileCache *files;
  33. HttpRequestPtr req;
  34. HttpResponsePtr resp;
  35. HttpResponseWriterPtr writer;
  36. HttpParserPtr parser;
  37. // for GetSendData
  38. file_cache_ptr fc;
  39. std::string header;
  40. std::string body;
  41. // for websocket
  42. WebSocketChannelPtr ws_channel;
  43. WebSocketParserPtr ws_parser;
  44. uint64_t last_send_ping_time;
  45. uint64_t last_recv_pong_time;
  46. WebSocketService* ws_service;
  47. HttpHandler() {
  48. protocol = UNKNOWN;
  49. state = WANT_RECV;
  50. ssl = false;
  51. service = NULL;
  52. files = NULL;
  53. ws_service = NULL;
  54. }
  55. ~HttpHandler() {
  56. if (writer) {
  57. writer->status = hv::SocketChannel::DISCONNECTED;
  58. }
  59. }
  60. bool Init(int http_version = 1, hio_t* io = NULL) {
  61. parser.reset(HttpParser::New(HTTP_SERVER, (enum http_version)http_version));
  62. if (parser == NULL) {
  63. return false;
  64. }
  65. protocol = http_version == 1 ? HTTP_V1 : HTTP_V2;
  66. req.reset(new HttpRequest);
  67. resp.reset(new HttpResponse);
  68. if (http_version == 2) {
  69. resp->http_major = req->http_major = 2;
  70. resp->http_minor = req->http_minor = 0;
  71. }
  72. parser->InitRequest(req.get());
  73. if (io) {
  74. writer.reset(new hv::HttpResponseWriter(io, resp));
  75. writer->status = hv::SocketChannel::CONNECTED;
  76. }
  77. return true;
  78. }
  79. bool SwitchHTTP2() {
  80. parser.reset(HttpParser::New(HTTP_SERVER, ::HTTP_V2));
  81. if (parser == NULL) {
  82. return false;
  83. }
  84. protocol = HTTP_V2;
  85. resp->http_major = req->http_major = 2;
  86. resp->http_minor = req->http_minor = 0;
  87. parser->InitRequest(req.get());
  88. return true;
  89. }
  90. void Reset() {
  91. state = WANT_RECV;
  92. req->Reset();
  93. resp->Reset();
  94. parser->InitRequest(req.get());
  95. if (writer) {
  96. writer->Begin();
  97. }
  98. }
  99. int FeedRecvData(const char* data, size_t len);
  100. // @workflow: preprocessor -> api -> web -> postprocessor
  101. // @result: HttpRequest -> HttpResponse/file_cache_t
  102. int HandleHttpRequest();
  103. int GetSendData(char** data, size_t* len);
  104. // websocket
  105. bool SwitchWebSocket(hio_t* io, ws_session_type type = WS_SERVER);
  106. void WebSocketOnOpen() {
  107. ws_channel->status = hv::SocketChannel::CONNECTED;
  108. if (ws_service && ws_service->onopen) {
  109. ws_service->onopen(ws_channel, req->url);
  110. }
  111. }
  112. void WebSocketOnClose() {
  113. ws_channel->status = hv::SocketChannel::DISCONNECTED;
  114. if (ws_service && ws_service->onclose) {
  115. ws_service->onclose(ws_channel);
  116. }
  117. }
  118. private:
  119. int defaultRequestHandler();
  120. int defaultStaticHandler();
  121. int defaultErrorHandler();
  122. int customHttpHandler(const http_handler& handler);
  123. int invokeHttpHandler(const http_handler* handler);
  124. };
  125. #endif // HV_HTTP_HANDLER_H_