mirror of
https://github.com/Telecominfraproject/wlan-cloud-owprov.git
synced 2025-10-30 18:18:03 +00:00
72 lines
1.8 KiB
C++
72 lines
1.8 KiB
C++
//
|
|
// Created by stephane bourque on 2022-10-25.
|
|
//
|
|
|
|
#pragma once
|
|
|
|
#include "framework/SubSystemServer.h"
|
|
|
|
#include "Poco/ExpireLRUCache.h"
|
|
#include "Poco/Net/HTTPServerRequest.h"
|
|
#include "Poco/URI.h"
|
|
|
|
#include "fmt/format.h"
|
|
|
|
namespace OpenWifi {
|
|
|
|
class RESTAPI_RateLimiter : public SubSystemServer {
|
|
public:
|
|
struct ClientCacheEntry {
|
|
int64_t Start = 0;
|
|
int Count = 0;
|
|
};
|
|
|
|
static auto instance() {
|
|
static auto instance_ = new RESTAPI_RateLimiter;
|
|
return instance_;
|
|
}
|
|
|
|
inline int Start() final { return 0; };
|
|
inline void Stop() final{};
|
|
|
|
inline bool IsRateLimited(const Poco::Net::HTTPServerRequest &R, int64_t Period,
|
|
int64_t MaxCalls) {
|
|
Poco::URI uri(R.getURI());
|
|
auto H = str_hash(uri.getPath() + R.clientAddress().host().toString());
|
|
auto E = Cache_.get(H);
|
|
auto Now = std::chrono::duration_cast<std::chrono::milliseconds>(
|
|
std::chrono::system_clock::now().time_since_epoch())
|
|
.count();
|
|
if (E.isNull()) {
|
|
Cache_.add(H, ClientCacheEntry{.Start = Now, .Count = 1});
|
|
return false;
|
|
}
|
|
if ((Now - E->Start) < Period) {
|
|
E->Count++;
|
|
Cache_.update(H, E);
|
|
if (E->Count > MaxCalls) {
|
|
poco_warning(Logger(), fmt::format("RATE-LIMIT-EXCEEDED: from '{}'",
|
|
R.clientAddress().toString()));
|
|
return true;
|
|
}
|
|
return false;
|
|
}
|
|
E->Start = Now;
|
|
E->Count = 1;
|
|
Cache_.update(H, E);
|
|
return false;
|
|
}
|
|
|
|
inline void Clear() { Cache_.clear(); }
|
|
|
|
private:
|
|
Poco::ExpireLRUCache<uint64_t, ClientCacheEntry> Cache_{2048};
|
|
std::hash<std::string> str_hash;
|
|
|
|
RESTAPI_RateLimiter() noexcept
|
|
: SubSystemServer("RateLimiter", "RATE-LIMITER", "rate.limiter") {}
|
|
};
|
|
|
|
inline auto RESTAPI_RateLimiter() { return RESTAPI_RateLimiter::instance(); }
|
|
|
|
} // namespace OpenWifi
|