#include #include "routes.h" #include "../servehelper.h" #include "../pixivclient.h" #include "../hiredis_wrapper.h" static inline std::optional guess_extension(const std::string& path, PixivClient& pixiv_client); void guess_extension_route(const httplib::Request& req, httplib::Response& res, const Config& config, PixivClient& pixiv_client, Redis* redis) { using namespace std::string_literals; std::string path = req.matches.str(1); std::string cache_key = "pixwhile:i.pximg.net:ext:"s + std::to_string(FastHash(path.data(), path.size(), 0)); std::optional extension = redis ? redis->get(cache_key) : std::nullopt; if (!extension) { extension = guess_extension(path, pixiv_client); if (!extension) { res.status = 500; serve_error(req, res, config, "500: Internal Server Error", "Failed to guess file extension for https://i.pximg.net"s + path); return; } if (redis) { redis->set(std::move(cache_key), *extension, 24 * 60 * 60); } } serve_redirect(req, res, config, proxy_image_url(req, config, "https://i.pximg.net" + path + '.' + *extension), true); } static inline std::optional guess_extension(const std::string& path, PixivClient& pixiv_client) { auto guess_extension = [&](const char* extension) { return pixiv_client.i_pximg_url_valid(path + '.' + extension); }; if (guess_extension("png")) { return "png"; } else if (guess_extension("jpg")) { return "jpg"; } else { return std::nullopt; } }