mirror of
https://github.com/BeamMP/BeamMP-Launcher.git
synced 2025-07-01 23:46:59 +00:00
HTTP proxy improvements
Adds the avatar endpoint and adds the possibility to easily add others
This commit is contained in:
parent
7481ba4539
commit
4678701f42
104
src/Startup.cpp
104
src/Startup.cpp
@ -364,6 +364,19 @@ void set_headers(httplib::Response& res) {
|
||||
res.set_header("Access-Control-Request-Headers", "X-API-Version");
|
||||
}
|
||||
|
||||
std::vector<std::string> split_string(const std::string& s, const char delim) {
|
||||
std::stringstream ss(s);
|
||||
std::string item;
|
||||
std::vector<std::string> elems;
|
||||
while (std::getline(ss, item, delim)) {
|
||||
if (!item.empty()) {
|
||||
elems.push_back(item);
|
||||
}
|
||||
}
|
||||
|
||||
return elems;
|
||||
}
|
||||
|
||||
void StartProxy() {
|
||||
std::thread proxy([&]() {
|
||||
httplib::Server HTTPProxy;
|
||||
@ -371,10 +384,12 @@ void StartProxy() {
|
||||
{ "User-Agent", "BeamMP-Launcher/" + GetVer() + GetPatch() },
|
||||
{ "Accept", "*/*" }
|
||||
};
|
||||
std::string pattern = "/:any1";
|
||||
for (int i = 2; i <= 4; i++) {
|
||||
HTTPProxy.Get(pattern, [&](const httplib::Request& req, httplib::Response& res) {
|
||||
httplib::Client cli("https://backend.beammp.com");
|
||||
httplib::Client backend("https://backend.beammp.com");
|
||||
httplib::Client forum("https://forum.beammp.com");
|
||||
|
||||
const std::string pattern = ".*";
|
||||
|
||||
auto handle_request = [&](const httplib::Request& req, httplib::Response& res) {
|
||||
set_headers(res);
|
||||
if (req.has_header("X-BMP-Authentication")) {
|
||||
headers.emplace("X-BMP-Authentication", PrivateKey);
|
||||
@ -382,33 +397,78 @@ void StartProxy() {
|
||||
if (req.has_header("X-API-Version")) {
|
||||
headers.emplace("X-API-Version", req.get_header_value("X-API-Version"));
|
||||
}
|
||||
if (auto cli_res = cli.Get(req.path, headers); cli_res) {
|
||||
|
||||
const std::vector<std::string> path = split_string(req.path, '/');
|
||||
|
||||
httplib::Result cli_res;
|
||||
const std::string method = req.method;
|
||||
std::string host = "";
|
||||
|
||||
if (!path.empty())
|
||||
host = path[0];
|
||||
|
||||
if (host == "backend") {
|
||||
std::string remaining_path = req.path.substr(std::strlen("/backend"));
|
||||
|
||||
if (method == "GET")
|
||||
cli_res = backend.Get(remaining_path, headers);
|
||||
else if (method == "POST")
|
||||
cli_res = backend.Post(remaining_path, headers);
|
||||
|
||||
} else if (host == "avatar") {
|
||||
std::string username;
|
||||
std::string avatar_size = "100";
|
||||
|
||||
if (1 < path.size())
|
||||
username = path[1];
|
||||
|
||||
if (path.size() > 2) {
|
||||
try {
|
||||
if (std::stoi(path[2]) > 0)
|
||||
avatar_size = path[2];
|
||||
|
||||
} catch (std::exception&) {}
|
||||
}
|
||||
|
||||
auto summary_res = forum.Get("/u/" + username + ".json", headers);
|
||||
nlohmann::json d = nlohmann::json::parse(summary_res->body, nullptr, false);
|
||||
|
||||
if (d.contains("user")) {
|
||||
auto user = d.at("user");
|
||||
auto avatar_link_json = user.at("avatar_template");
|
||||
|
||||
if (avatar_link_json.is_string()) {
|
||||
auto avatar_link = avatar_link_json.get<std::string>();
|
||||
size_t start_pos = avatar_link.find("{size}");
|
||||
if (start_pos != std::string::npos)
|
||||
avatar_link.replace(start_pos, std::strlen("{size}"), avatar_size);
|
||||
|
||||
cli_res = forum.Get(avatar_link, headers);
|
||||
}
|
||||
} else
|
||||
cli_res = forum.Get("/user_avatar/forum.beammp.com/user/0/0.png", headers);
|
||||
} else {
|
||||
res.set_content("Host not found", "text/plain");
|
||||
return;
|
||||
}
|
||||
|
||||
if (cli_res) {
|
||||
res.set_content(cli_res->body, cli_res->get_header_value("Content-Type"));
|
||||
} else {
|
||||
res.set_content(to_string(cli_res.error()), "text/plain");
|
||||
}
|
||||
};
|
||||
|
||||
HTTPProxy.Get(pattern, [&](const httplib::Request& req, httplib::Response& res) {
|
||||
handle_request(req, res);
|
||||
});
|
||||
|
||||
HTTPProxy.Post(pattern, [&](const httplib::Request& req, httplib::Response& res) {
|
||||
httplib::Client cli("https://backend.beammp.com");
|
||||
set_headers(res);
|
||||
if (req.has_header("X-BMP-Authentication")) {
|
||||
headers.emplace("X-BMP-Authentication", PrivateKey);
|
||||
}
|
||||
if (req.has_header("X-API-Version")) {
|
||||
headers.emplace("X-API-Version", req.get_header_value("X-API-Version"));
|
||||
}
|
||||
if (auto cli_res = cli.Post(req.path, headers, req.body,
|
||||
req.get_header_value("Content-Type"));
|
||||
cli_res) {
|
||||
res.set_content(cli_res->body, cli_res->get_header_value("Content-Type"));
|
||||
} else {
|
||||
res.set_content(to_string(cli_res.error()), "text/plain");
|
||||
}
|
||||
handle_request(req, res);
|
||||
});
|
||||
pattern += "/:any" + std::to_string(i);
|
||||
}
|
||||
|
||||
ProxyPort = HTTPProxy.bind_to_any_port("0.0.0.0");
|
||||
debug("HTTP Proxy listening on port " + std::to_string(ProxyPort));
|
||||
HTTPProxy.listen_after_bind();
|
||||
});
|
||||
proxy.detach();
|
||||
|
Loading…
x
Reference in New Issue
Block a user