#pragma once
#include <mutex>
#include <memory>
#include <thread>
#include <string>
#include <unordered_map>
#define CPPHTTPLIB_THREAD_POOL_COUNT 2
#include <httplib.h>
#include <json/json.h>
#include <ipc/ipc.h>
#include "xsched/types.h"
#include "xsched/utils/waitpid.h"
#include "xsched/sched/scheduler/local.h"
#include "xsched/sched/protocol/status.h"
namespace xsched::service
{
class Server
{
public:
Server(const std::string &policy_name, const std::string &port);
~Server();
void Run();
void Stop();
private:
void RecvWorker();
void CleanUpProcess(PID pid);
void ProcessTerminate(PID pid);
void SendHint(std::shared_ptr<const sched::Hint> hint);
void Execute(std::shared_ptr<const sched::Operation> operation);
XQueueHandle GetXQueueHandle(const Json::Value &request);
bool GetXQueueStatus(XQueueHandle handle, sched::XQueueStatus &status);
void GetXQueue(const httplib::Request &req, httplib::Response &res);
void GetXQueues(const httplib::Request &req, httplib::Response &res);
void PostXQueueConfig(const httplib::Request &req, httplib::Response &res, const httplib::ContentReader &reader);
void GetSchedulerPolicy(const httplib::Request &req, httplib::Response &res);
void PostSchedulerPolicy(const httplib::Request &req, httplib::Response &res, const httplib::ContentReader &reader);
void PostHint(const httplib::Request &req, httplib::Response &res, const httplib::ContentReader &reader);
std::mutex chan_mtx_;
std::unique_ptr<ipc::Node> recv_chan_ = nullptr;
std::unique_ptr<ipc::Node> self_chan_ = nullptr;
std::unordered_map<PID, std::shared_ptr<ipc::Node>> client_chans_;
std::unique_ptr<utils::PidWaiter> pid_waiter_ = nullptr;
std::unique_ptr<sched::LocalScheduler> scheduler_ = nullptr;
uint16_t port_ = 0;
Json::Reader json_reader_;
Json::StreamWriterBuilder json_writer_;
httplib::Server http_server_;
std::unique_ptr<std::thread> http_thread_ = nullptr;
};
}