diff --git a/src/handler/interfaces.cpp b/src/handler/interfaces.cpp index 3a5c3ec7f..27be645d5 100644 --- a/src/handler/interfaces.cpp +++ b/src/handler/interfaces.cpp @@ -1003,7 +1003,7 @@ std::string surgeConfToClash(RESPONSE_CALLBACK_ARGS) name = x.first; content = x.second; dummy_str_array = split(content, ","); - if(!dummy_str_array.size()) + if(dummy_str_array.empty()) continue; type = dummy_str_array[0]; if(!(type == "select" || type == "url-test" || type == "fallback" || type == "load-balance")) //remove unsupported types diff --git a/src/server/webserver_httplib.cpp b/src/server/webserver_httplib.cpp index e8450d92b..49d36eda6 100644 --- a/src/server/webserver_httplib.cpp +++ b/src/server/webserver_httplib.cpp @@ -12,6 +12,20 @@ #include "../utils/urlencode.h" #include "webserver.h" +static const char *request_header_blacklist[] = {"host", "accept", "accept-encoding"}; + +static inline bool is_request_header_blacklisted(const std::string &header) +{ + for (auto &x : request_header_blacklist) + { + if (strcasecmp(x, header.c_str()) == 0) + { + return true; + } + } + return false; +} + void WebServer::stop_web_server() { SERVER_EXIT_FLAG = true; @@ -27,17 +41,27 @@ static httplib::Server::Handler makeHandler(const responseRoute &rr) req.url = request.path; for (auto &h: request.headers) { + if (startsWith(h.first, "LOCAL_") + || startsWith(h.first, "REMOTE_") + || is_request_header_blacklisted(h.first)) + { + continue; + } req.headers[h.first] = h.second; } req.argument = request.params; - req.postdata = request.body; if (request.get_header_value("Content-Type") == "application/x-www-form-urlencoded") { req.postdata = urlDecode(req.postdata); } + else + { + req.postdata = request.body; + } auto result = rr.rc(req, resp); response.status = resp.status_code; - for (auto &h: resp.headers) { + for (auto &h: resp.headers) + { response.set_header(h.first, h.second); } auto content_type = resp.content_type; @@ -73,10 +97,12 @@ int WebServer::start_web_server_multi(listener_args *args) break; } } - server.Options(R"(.*)", [&](const httplib::Request &req, httplib::Response &res) { + server.Options(R"(.*)", [&](const httplib::Request &req, httplib::Response &res) + { auto path = req.path; std::string allowed; - for (auto &rr : responses) { + for (auto &rr : responses) + { if (rr.path == path) { allowed += rr.method + ","; @@ -91,19 +117,10 @@ int WebServer::start_web_server_multi(listener_args *args) res.set_header("Access-Control-Allow-Headers", "Content-Type,Authorization"); } }); - server.set_pre_routing_handler([&](const httplib::Request &req, httplib::Response &res) { - std::string params; - for (auto &p: req.params) - { - params += p.first + "=" + urlEncode(p.second) + "&"; - } - if (!params.empty()) - { - params.pop_back(); - params = "?" + params; - } + server.set_pre_routing_handler([&](const httplib::Request &req, httplib::Response &res) + { writeLog(0, "Accept connection from client " + req.remote_addr + ":" + std::to_string(req.remote_port), LOG_LEVEL_DEBUG); - writeLog(0, "handle_cmd: " + req.method + " handle_uri: " + req.path + params, LOG_LEVEL_VERBOSE); + writeLog(0, "handle_cmd: " + req.method + " handle_uri: " + req.target, LOG_LEVEL_VERBOSE); if (req.has_header("SubConverter-Request")) { @@ -137,7 +154,8 @@ int WebServer::start_web_server_multi(listener_args *args) res.set_redirect(x.second); }); } - server.set_exception_handler([](const httplib::Request &req, httplib::Response &res, const std::exception_ptr &e) { + server.set_exception_handler([](const httplib::Request &req, httplib::Response &res, const std::exception_ptr &e) + { try { std::rethrow_exception(e); @@ -148,17 +166,12 @@ int WebServer::start_web_server_multi(listener_args *args) } catch (const std::exception &ex) { - std::string params; - for (auto &p: req.params) - { - params += p.first + "=" + p.second + "&"; - } - params.pop_back(); - std::string return_data = "Internal server error while processing request path '" + req.path + "' with arguments '" + params + "'!\n"; + std::string return_data = "Internal server error while processing request '" + req.target + "'!\n"; return_data += "\n exception: "; return_data += type(ex); return_data += "\n what(): "; return_data += ex.what(); + res.status = 500; res.set_content(return_data, "text/plain"); } catch (...) @@ -172,12 +185,10 @@ int WebServer::start_web_server_multi(listener_args *args) } server.bind_to_port(args->listen_address, args->port, 0); - pthread_t tid; - pthread_create(&tid, nullptr, [](void *args) -> void * { - auto *server = (httplib::Server *)args; - server->listen_after_bind(); - return nullptr; - }, &server); + std::thread thread([&]() + { + server.listen_after_bind(); + }); while (!SERVER_EXIT_FLAG) { @@ -189,6 +200,7 @@ int WebServer::start_web_server_multi(listener_args *args) } server.stop(); + thread.join(); return 0; }