mirror of
https://github.com/Expand-sys/CCash
synced 2026-03-22 20:47:10 +11:00
✨ Intitial Logging Functionality
This commit is contained in:
parent
67098d965d
commit
32ea81bac2
3 changed files with 64 additions and 17 deletions
|
|
@ -4,13 +4,6 @@
|
||||||
"address": "0.0.0.0",
|
"address": "0.0.0.0",
|
||||||
"port": 80,
|
"port": 80,
|
||||||
"https": false
|
"https": false
|
||||||
},
|
|
||||||
{
|
|
||||||
"address": "0.0.0.0",
|
|
||||||
"port": 443,
|
|
||||||
"https": true,
|
|
||||||
"cert": "",
|
|
||||||
"key": ""
|
|
||||||
}
|
}
|
||||||
]
|
]
|
||||||
}
|
}
|
||||||
|
|
@ -1,10 +1,10 @@
|
||||||
#pragma once
|
#pragma once
|
||||||
#include <fstream>
|
#include <fstream>
|
||||||
#include <shared_mutex>
|
#include <shared_mutex>
|
||||||
#include <vector>
|
|
||||||
#include "xxhash.h"
|
#include "xxhash.h"
|
||||||
#include "parallel-hashmap/parallel_hashmap/phmap.h"
|
#include "parallel-hashmap/parallel_hashmap/phmap.h"
|
||||||
#include "user.hpp"
|
#include "user.hpp"
|
||||||
|
#include "log.hpp"
|
||||||
|
|
||||||
class
|
class
|
||||||
{
|
{
|
||||||
|
|
@ -18,11 +18,19 @@ private:
|
||||||
std::mutex>
|
std::mutex>
|
||||||
users;
|
users;
|
||||||
|
|
||||||
|
phmap::parallel_flat_hash_map<
|
||||||
|
std::string, Log,
|
||||||
|
phmap::priv::hash_default_hash<std::string>,
|
||||||
|
phmap::priv::hash_default_eq<std::string>,
|
||||||
|
phmap::priv::Allocator<phmap::priv::Pair<const std::string, Log>>,
|
||||||
|
4UL,
|
||||||
|
std::mutex>
|
||||||
|
logs;
|
||||||
/**
|
/**
|
||||||
* @brief size_lock should be grabbed if the operation MODIFIES the size (shared), this is so that when save claims unique
|
* @brief size_l should be grabbed if the operation MODIFIES the size (shared), this is so that when save claims unique
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
std::shared_mutex size_lock;
|
std::shared_mutex size_l;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief send_funds_l should be grabbed if balances are being MODIFIED (shared) or if an operation needs to READ without the intermediary states that sendfunds has (unique)
|
* @brief send_funds_l should be grabbed if balances are being MODIFIED (shared) or if an operation needs to READ without the intermediary states that sendfunds has (unique)
|
||||||
|
|
@ -35,7 +43,7 @@ public:
|
||||||
|
|
||||||
bool AddUser(const std::string &name, std::string &&init_pass)
|
bool AddUser(const std::string &name, std::string &&init_pass)
|
||||||
{
|
{
|
||||||
std::shared_lock<std::shared_mutex> lock{size_lock};
|
std::shared_lock<std::shared_mutex> lock{size_l};
|
||||||
return users.try_emplace_l(
|
return users.try_emplace_l(
|
||||||
name, [](User &) {}, std::move(init_pass));
|
name, [](User &) {}, std::move(init_pass));
|
||||||
}
|
}
|
||||||
|
|
@ -44,7 +52,7 @@ public:
|
||||||
bool state = (admin_pass == attempt);
|
bool state = (admin_pass == attempt);
|
||||||
if (state)
|
if (state)
|
||||||
{
|
{
|
||||||
std::shared_lock<std::shared_mutex> lock{size_lock};
|
std::shared_lock<std::shared_mutex> lock{size_l};
|
||||||
state = users.try_emplace_l(
|
state = users.try_emplace_l(
|
||||||
name, [](User &) {}, init_bal, std::move(init_pass));
|
name, [](User &) {}, init_bal, std::move(init_pass));
|
||||||
}
|
}
|
||||||
|
|
@ -53,20 +61,20 @@ public:
|
||||||
|
|
||||||
bool DelUser(const std::string &name, const std::string &attempt)
|
bool DelUser(const std::string &name, const std::string &attempt)
|
||||||
{
|
{
|
||||||
std::shared_lock<std::shared_mutex> lock{size_lock};
|
std::shared_lock<std::shared_mutex> lock{size_l};
|
||||||
return users.erase_if(name, [&attempt](const User &u) { return (XXH3_64bits(attempt.data(), attempt.size()) == u.password); });
|
return users.erase_if(name, [&attempt](const User &u) { return (XXH3_64bits(attempt.data(), attempt.size()) == u.password); });
|
||||||
}
|
}
|
||||||
bool AdminDelUser(const std::string &name, const std::string &attempt)
|
bool AdminDelUser(const std::string &name, const std::string &attempt)
|
||||||
{
|
{
|
||||||
std::shared_lock<std::shared_mutex> lock{size_lock};
|
std::shared_lock<std::shared_mutex> lock{size_l};
|
||||||
return users.erase_if(name, [this, &attempt](const User &) { return (admin_pass == attempt); });
|
return users.erase_if(name, [this, &attempt](const User &) { return (admin_pass == attempt); });
|
||||||
}
|
}
|
||||||
|
|
||||||
bool SendFunds(const std::string &a_name, const std::string &b_name, uint_fast32_t amount, const std::string &attempt)
|
bool SendFunds(const std::string &a_name, const std::string &b_name, uint_fast32_t amount, const std::string &attempt)
|
||||||
{
|
{
|
||||||
|
|
||||||
//cant send money to self, from self
|
//cant send money to self, from self or amount is 0
|
||||||
if (a_name == b_name)
|
if (a_name == b_name || !amount)
|
||||||
{
|
{
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
@ -96,6 +104,18 @@ public:
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (state)
|
||||||
|
{
|
||||||
|
Transaction temp(a_name, b_name, amount, false);
|
||||||
|
logs.modify_if(a_name, [&temp](Log &l) {
|
||||||
|
l.AddTrans(temp);
|
||||||
|
});
|
||||||
|
temp.recieving = true;
|
||||||
|
logs.modify_if(b_name, [&temp](Log &l) {
|
||||||
|
l.AddTrans(temp);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
return state;
|
return state;
|
||||||
}
|
}
|
||||||
bool Contains(const std::string &name) const
|
bool Contains(const std::string &name) const
|
||||||
|
|
@ -147,6 +167,33 @@ public:
|
||||||
return res;
|
return res;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Json::Value GetLogs(const std::string &name, const std::string &attempt)
|
||||||
|
{
|
||||||
|
Json::Value res;
|
||||||
|
bool state = false;
|
||||||
|
users.if_contains(name, [&state, &attempt](const User &u) {
|
||||||
|
state = XXH3_64bits(attempt.data(), attempt.size()) == u.password;
|
||||||
|
});
|
||||||
|
|
||||||
|
if (state)
|
||||||
|
{
|
||||||
|
logs.if_contains(name, [&res](const Log &l) {
|
||||||
|
for (uint32_t i = l.data.size() - 1; i >= 0; --i)
|
||||||
|
{
|
||||||
|
if (!l.data[i].amount)
|
||||||
|
{
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
res[99 - i]["to"] = l.data[i].to;
|
||||||
|
res[99 - i]["from"] = l.data[i].from;
|
||||||
|
res[99 - i]["amount"] = l.data[i].amount;
|
||||||
|
res[99 - i]["recieving"] = l.data[i].recieving;
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
return res;
|
||||||
|
}
|
||||||
|
|
||||||
void Save()
|
void Save()
|
||||||
{
|
{
|
||||||
Json::StreamWriterBuilder builder;
|
Json::StreamWriterBuilder builder;
|
||||||
|
|
@ -157,7 +204,7 @@ public:
|
||||||
|
|
||||||
//loading info into json temp
|
//loading info into json temp
|
||||||
{
|
{
|
||||||
std::scoped_lock<std::shared_mutex, std::shared_mutex> lock{size_lock, send_funds_l};
|
std::scoped_lock<std::shared_mutex, std::shared_mutex> lock{size_l, send_funds_l};
|
||||||
for (const auto &u : users)
|
for (const auto &u : users)
|
||||||
{
|
{
|
||||||
//we know it contains this key but we call this func to grab mutex
|
//we know it contains this key but we call this func to grab mutex
|
||||||
|
|
@ -189,6 +236,7 @@ public:
|
||||||
user_save.close();
|
user_save.close();
|
||||||
for (const auto &u : temp.getMemberNames())
|
for (const auto &u : temp.getMemberNames())
|
||||||
{
|
{
|
||||||
|
logs.try_emplace(u);
|
||||||
users.try_emplace(u, temp[u]["balance"].asUInt(), std::move(temp[u]["password"].asUInt64()));
|
users.try_emplace(u, temp[u]["balance"].asUInt(), std::move(temp[u]["password"].asUInt64()));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -111,6 +111,11 @@ public:
|
||||||
GEN_BODY
|
GEN_BODY
|
||||||
JSON(bank.AdminVerifyPass(body["attempt"].asCString()));
|
JSON(bank.AdminVerifyPass(body["attempt"].asCString()));
|
||||||
}
|
}
|
||||||
|
void GetLog(req_args, const std::string &name)
|
||||||
|
{
|
||||||
|
GEN_BODY
|
||||||
|
JSON(bank.GetLogs(name, body["attempt"].asCString()));
|
||||||
|
}
|
||||||
|
|
||||||
METHOD_LIST_BEGIN
|
METHOD_LIST_BEGIN
|
||||||
METHOD_ADD(BankF::Close, "/admin/close", Post, Options);
|
METHOD_ADD(BankF::Close, "/admin/close", Post, Options);
|
||||||
|
|
@ -126,6 +131,7 @@ public:
|
||||||
METHOD_ADD(BankF::Contains, "/contains/{name}", Get, Options);
|
METHOD_ADD(BankF::Contains, "/contains/{name}", Get, Options);
|
||||||
METHOD_ADD(BankF::GetBal, "/{name}/bal", Get, Options);
|
METHOD_ADD(BankF::GetBal, "/{name}/bal", Get, Options);
|
||||||
METHOD_ADD(BankF::AdminVerifyPass, "/admin/vpass", Post, Options);
|
METHOD_ADD(BankF::AdminVerifyPass, "/admin/vpass", Post, Options);
|
||||||
|
METHOD_ADD(BankF::GetLog, "/{name}/log", Post, Options);
|
||||||
|
|
||||||
METHOD_ADD(BankF::DelUser, "/user", Delete, Options);
|
METHOD_ADD(BankF::DelUser, "/user", Delete, Options);
|
||||||
METHOD_ADD(BankF::AdminDelUser, "/admin/user", Delete, Options);
|
METHOD_ADD(BankF::AdminDelUser, "/admin/user", Delete, Options);
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue