Skip to content

Commit 62cd137

Browse files
authored
feat: add HTTP_STATUS_CLOSE to support (#816) (#817)
* feat: add HTTP_STATUS_CLOSE to support (#816) * fix: handle HTTP_STATUS_CLOSE before and after postprocessor
1 parent ca2e9e7 commit 62cd137

File tree

3 files changed

+30
-5
lines changed

3 files changed

+30
-5
lines changed

examples/http_server_test.cpp

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -97,6 +97,12 @@ int main(int argc, char** argv) {
9797
writer->End();
9898
});
9999

100+
// curl -v http://ip:port/close
101+
// Test HTTP_STATUS_CLOSE: closes connection without sending any response
102+
router.GET("/close", [](HttpRequest* req, HttpResponse* resp) {
103+
return HTTP_STATUS_CLOSE;
104+
});
105+
100106
// middleware
101107
router.AllowCORS();
102108
router.Use([](HttpRequest* req, HttpResponse* resp) {

http/server/HttpHandler.cpp

Lines changed: 20 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -254,6 +254,10 @@ void HttpHandler::onHeadersComplete() {
254254
handleRequestHeaders();
255255
if (service->headerHandler) {
256256
const int status_code = customHttpHandler(service->headerHandler);
257+
if (status_code == HTTP_STATUS_CLOSE) {
258+
state = WANT_CLOSE;
259+
return;
260+
}
257261
if (status_code != HTTP_STATUS_OK && status_code != HTTP_STATUS_NEXT) {
258262
SetError(ERR_REQUEST, static_cast<http_status>(status_code));
259263
return;
@@ -338,6 +342,10 @@ void HttpHandler::onMessageComplete() {
338342
}
339343
} else {
340344
status_code = HandleHttpRequest();
345+
if (status_code == HTTP_STATUS_CLOSE) {
346+
state = WANT_CLOSE;
347+
return;
348+
}
341349
if (status_code != HTTP_STATUS_NEXT) {
342350
SendHttpResponse();
343351
}
@@ -478,12 +486,17 @@ int HttpHandler::HandleHttpRequest() {
478486
pResp->status_code = (http_status)status_code;
479487
if (pResp->status_code >= 400 && pResp->body.size() == 0 && pReq->method != HTTP_HEAD) {
480488
if (service->errorHandler) {
481-
customHttpHandler(service->errorHandler);
489+
status_code = customHttpHandler(service->errorHandler);
482490
} else {
483491
defaultErrorHandler();
484492
}
485493
}
486494
}
495+
// Handle HTTP_STATUS_CLOSE: close connection without response
496+
if (status_code == HTTP_STATUS_CLOSE) {
497+
state = WANT_CLOSE;
498+
return HTTP_STATUS_CLOSE;
499+
}
487500
if (fc) {
488501
pResp->content = fc->filebuf.base;
489502
pResp->content_length = fc->filebuf.len;
@@ -492,7 +505,11 @@ int HttpHandler::HandleHttpRequest() {
492505
pResp->headers["Etag"] = fc->etag;
493506
}
494507
if (service->postprocessor) {
495-
customHttpHandler(service->postprocessor);
508+
status_code = customHttpHandler(service->postprocessor);
509+
if (status_code == HTTP_STATUS_CLOSE) {
510+
state = WANT_CLOSE;
511+
return HTTP_STATUS_CLOSE;
512+
}
496513
}
497514

498515
if (writer && writer->state != hv::HttpResponseWriter::SEND_BEGIN) {
@@ -760,7 +777,7 @@ int HttpHandler::GetSendData(char** data, size_t* len) {
760777
if (parser->IsComplete()) state = WANT_SEND;
761778
else return 0;
762779
case HANDLE_END:
763-
state = WANT_SEND;
780+
state = WANT_SEND;
764781
case WANT_SEND:
765782
state = SEND_HEADER;
766783
case SEND_HEADER:

http/server/HttpService.h

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -29,11 +29,13 @@
2929
/*
3030
* @param[in] req: parsed structured http request
3131
* @param[out] resp: structured http response
32-
* @return 0: handle next
33-
* http_status_code: handle done
32+
* @return HTTP_STATUS_NEXT: handle next
33+
* HTTP_STATUS_CLOSE: close connection
34+
* http_status_code: handle done
3435
*/
3536
#define HTTP_STATUS_NEXT 0
3637
#define HTTP_STATUS_UNFINISHED 0
38+
#define HTTP_STATUS_CLOSE -100
3739
// NOTE: http_sync_handler run on IO thread
3840
typedef std::function<int(HttpRequest* req, HttpResponse* resp)> http_sync_handler;
3941
// NOTE: http_async_handler run on hv::async threadpool

0 commit comments

Comments
 (0)