libravatarserv/src/http.cpp

112 lines
3.1 KiB
C++

/* This file is part of libravatarserv.
* Copyright © 2018 tastytea <tastytea@tastytea.de>
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, version 3.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
#include <iostream>
#include <algorithm>
#include <cstdlib>
#include "libravatarserv.hpp"
using std::cout;
using std::cerr;
using namespace http;
const Request http::parse_request(const string &request)
{
if (request.substr(0, 8) != "/avatar/" ||
request.find("..", 8) != std::string::npos)
{
cout << "Status: 404 Not Found\n\n";
cerr << "Error: Invalid URL.\n";
std::exit(0);
}
uint16_t size = 80;
string fallback;
string digest = request.substr(8);
std::transform(digest.begin(), digest.end(), digest.begin(), ::tolower);
std::size_t pos_digest = digest.find('?');
if (pos_digest != std::string::npos)
{
digest = digest.substr(0, pos_digest);
pos_digest = digest.find('.');
if (pos_digest != std::string::npos)
{
digest = digest.substr(0, pos_digest);
}
string answer;
{
answer = get_parameter(request, "s");
if (!answer.empty())
{
try
{
size = static_cast<uint16_t>(std::stoul(answer));
} catch (const std::exception &) {}
}
else
{
answer = get_parameter(request, "size");
if (!answer.empty())
{
try
{
size = static_cast<uint16_t>(std::stoul(answer));
} catch (const std::exception &) {}
}
}
if (size > 512)
{
size = 512;
}
if (size < 1)
{
size = 1;
}
}
{
answer = get_parameter(request, "d");
if (!answer.empty())
{
fallback = answer;
}
else
{
answer = get_parameter(request, "default");
if (!answer.empty())
{
fallback = answer;
}
}
}
}
return { digest, size, fallback };
}
const string http::get_parameter(const string &request, const string &parameter)
{
std::size_t pos = request.find(parameter + "=");
if (pos != std::string::npos)
{
pos += (1 + parameter.length());
return request.substr(pos, request.find('&', pos));
}
return "";
}