Unverified Commit 342628b2 authored by Dennis Jenkins's avatar Dennis Jenkins Committed by GitHub

Merge pull request #370 from knowledge4igor/http_headers_refactoring

Refactoring and code improvements in http headers
parents ecebd782 88647015
......@@ -68,5 +68,5 @@ private:
};
int main() {
Header::Registry::registerHeader<XProtocolVersion>();
Header::Registry::instance().registerHeader<XProtocolVersion>();
}
......@@ -13,6 +13,7 @@
#include <memory>
#include <pistache/http_header.h>
#include <pistache/type_checkers.h>
namespace Pistache {
namespace Http {
......@@ -128,28 +129,40 @@ private:
std::unordered_map<std::string, Raw> rawHeaders;
};
struct Registry {
class Registry {
typedef std::function<std::unique_ptr<Header>()> RegistryFunc;
public:
Registry(const Registry&) = delete;
Registry& operator=(const Registry&) = delete;
static Registry& instance();
template<typename H>
static
typename std::enable_if<
IsHeader<H>::value, void
>::type
registerHeader() {
template<typename H, REQUIRES(IsHeader<H>::value)>
void registerHeader() {
registerHeader(H::Name, []() -> std::unique_ptr<Header> {
return std::unique_ptr<Header>(new H());
});
}
static void registerHeader(std::string name, RegistryFunc func);
std::vector<std::string> headersList();
std::unique_ptr<Header> makeHeader(const std::string& name);
bool isRegistered(const std::string& name);
private:
Registry();
~Registry();
using RegistryFunc = std::function<std::unique_ptr<Header>()>;
using RegistryStorageType = std::unordered_map<
std::string,
RegistryFunc,
LowercaseHash,
LowercaseEqual>;
static std::vector<std::string> headersList();
void registerHeader(std::string name, RegistryFunc func);
static std::unique_ptr<Header> makeHeader(const std::string& name);
static bool isRegistered(const std::string& name);
RegistryStorageType registry;
};
template<typename H>
......@@ -157,7 +170,7 @@ struct Registrar {
static_assert(IsHeader<H>::value, "Registrar only works with header types");
Registrar() {
Registry::registerHeader<H>();
Registry::instance().registerHeader<H>();
}
};
......
#pragma once
namespace Pistache {
#define REQUIRES(condition) typename std::enable_if<(condition), int>::type = 0
}
\ No newline at end of file
......@@ -300,8 +300,8 @@ namespace Private {
else if (name == "Set-Cookie") {
message->cookies_.add(Cookie::fromRaw(cursor.offset(start), cursor.diff(start)));
}
else if (Header::Registry::isRegistered(name)) {
std::shared_ptr<Header::Header> header = Header::Registry::makeHeader(name);
else if (Header::Registry::instance().isRegistered(name)) {
std::shared_ptr<Header::Header> header = Header::Registry::instance().makeHeader(name);
header->parseRaw(cursor.offset(start), cursor.diff(start));
message->headers_.add(header);
}
......
......@@ -7,7 +7,6 @@
#include <unordered_map>
#include <iterator>
#include <stdexcept>
#include <iostream>
#include <pistache/http_headers.h>
......@@ -15,15 +14,6 @@ namespace Pistache {
namespace Http {
namespace Header {
namespace {
std::unordered_map<
std::string,
Registry::RegistryFunc,
LowercaseHash,
LowercaseEqual
> registry;
}
RegisterHeader(Accept);
RegisterHeader(AccessControlAllowOrigin);
RegisterHeader(AccessControlAllowHeaders);
......@@ -47,6 +37,18 @@ toLowercase(std::string str) {
return str;
}
Registry& Registry::instance() {
static Registry instance;
return instance;
}
Registry::Registry()
{}
Registry::~Registry()
{}
void
Registry::registerHeader(std::string name, Registry::RegistryFunc func)
{
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment