From 8426db0da1fcee801b30eec775ce0b90174489b9 Mon Sep 17 00:00:00 2001 From: ZhuangYumin Date: Tue, 12 Dec 2023 04:02:12 +0000 Subject: [PATCH] docs: further setting up structure --- backend/include/bs-utility.h | 12 +++++++++++- backend/include/engine.h | 9 ++++++++- backend/include/schedule.h | 21 ++++++++++++++++++++- backend/src/builtin-cli.cpp | 23 +++++++++++++++++++++-- backend/src/main.cpp | 22 +++++++++++----------- backend/src/schedule.cpp | 13 ++++++++++++- docs/develop/总体设计文档.md | 14 +++++++------- 7 files changed, 90 insertions(+), 24 deletions(-) diff --git a/backend/include/bs-utility.h b/backend/include/bs-utility.h index a7a24ef..2579e88 100644 --- a/backend/include/bs-utility.h +++ b/backend/include/bs-utility.h @@ -5,6 +5,7 @@ #include #include #include +#include #include #include #include @@ -42,7 +43,10 @@ template BlockingStringStream &BlockingStringStream::operator<<(const T &val) { { std::lock_guard lock(mutex); - if (internalStream.peek() == EOF) internalStream.clear(); + if (internalStream.peek() == EOF) { + internalStream.clear(); + internalStream.str(""); + } internalStream << val; } condition.notify_one(); @@ -61,4 +65,10 @@ BlockingStringStream &BlockingStringStream::operator>>(T &val) { return *this; } + +class SessionClass { + std::stack login_stack; + std::string SessionToken; + std::string OuthorizationKey; +}; #endif // PROTECTOR_UTILITY_H \ No newline at end of file diff --git a/backend/include/engine.h b/backend/include/engine.h index f5b5468..a40afdc 100644 --- a/backend/include/engine.h +++ b/backend/include/engine.h @@ -1,4 +1,11 @@ #ifndef PROTECTOR_ENGINE_H #define PROTECTOR_ENGINE_H +#include +class BookStoreEngineClass { + std::string config_dir; -#endif // PROTECTOR_ENGINE_H \ No newline at end of file + public: + BookStoreEngineClass() = delete; + BookStoreEngineClass(std::string config_dir) : config_dir(config_dir) {} +}; +#endif // PROTECTOR_ENGINE_H \ No newline at end of file diff --git a/backend/include/schedule.h b/backend/include/schedule.h index d1f2058..48ad0fc 100644 --- a/backend/include/schedule.h +++ b/backend/include/schedule.h @@ -1,4 +1,23 @@ #ifndef PROTECTOR_SCHEDULE_H #define PROTECTOR_SCHEDULE_H +#include -#endif // PROTECTOR_SCHEDULE_H \ No newline at end of file +#include "bs-utility.h" +#include "engine.h" +class BookStoreBackEndClass { + std::string config_dir; + BlockingStringStream *input_ptr; + BlockingStringStream *output_ptr; + BookStoreEngineClass *engine_ptr; + + public: + BookStoreBackEndClass() = delete; + BookStoreBackEndClass(std::string config_dir, BlockingStringStream *input_ptr, + BlockingStringStream *output_ptr) + : config_dir(config_dir), input_ptr(input_ptr), output_ptr(output_ptr) { + engine_ptr = new BookStoreEngineClass(config_dir); + } + ~BookStoreBackEndClass() { delete engine_ptr; } + void Run(); +}; +#endif // PROTECTOR_SCHEDULE_H \ No newline at end of file diff --git a/backend/src/builtin-cli.cpp b/backend/src/builtin-cli.cpp index c9231b8..92d67ca 100644 --- a/backend/src/builtin-cli.cpp +++ b/backend/src/builtin-cli.cpp @@ -2,15 +2,34 @@ #include -#include "schedule.h" #include "bs-utility.h" +#include "schedule.h" void BookStoreMain(bool is_server, std::string config_dir) { std::ios::sync_with_stdio(false); if (!is_server) { ; // TODO: run as client } else { - throw FatalError("Server mode is not implemented yet", 1); std::cin.tie(nullptr); std::cout.rdbuf(nullptr); + BlockingStringStream input; + BlockingStringStream output; + BookStoreBackEndClass backend(config_dir, &input, &output); + std::thread backend_thread([&backend]() { backend.Run(); }); + std::thread input_thread([&input]() { + std::string data; + while (std::getline(std::cin, data)) { + input << data << '\n'; + } + }); + std::thread output_thread([&output]() { + std::string data; + while (true) { + output.getline(data, '\n'); + std::cout << data << std::endl; + } + }); + input_thread.join(); + output_thread.join(); + backend_thread.join(); } } \ No newline at end of file diff --git a/backend/src/main.cpp b/backend/src/main.cpp index 23d1fec..e97d0f5 100644 --- a/backend/src/main.cpp +++ b/backend/src/main.cpp @@ -7,27 +7,27 @@ void test() { BlockingStringStream bss; + std::thread reader([&bss]() { + std::string data; + for (int i = 1; i <= 5; ++i) { + // Use getline with string delimiter + bss.getline(data, '\n'); + std::cerr << "Received: " << data << std::endl; + } + }); + std::this_thread::sleep_for(std::chrono::seconds(1)); std::thread writer([&bss]() { for (int i = 1; i <= 5; ++i) { bss << "Data " << i << '\n'; std::this_thread::sleep_for(std::chrono::seconds(1)); } }); - - std::thread reader([&bss]() { - std::string data; - for (int i = 1; i <= 5; ++i) { - // Use getline with string delimiter - bss.getline(data, '\n'); - std::cout << "Received: " << data << std::endl; - } - }); reader.join(); writer.join(); } int main(int argc, char **argv) { - test(); - return 0; + // test(); + // return 0; bool is_server = false; std::string config_dir = ""; bool custom_config_dir = false; diff --git a/backend/src/schedule.cpp b/backend/src/schedule.cpp index 5d049a1..62947a8 100644 --- a/backend/src/schedule.cpp +++ b/backend/src/schedule.cpp @@ -1,2 +1,13 @@ #include "schedule.h" -#include "engine.h" \ No newline at end of file +#include "engine.h" + +void BookStoreBackEndClass::Run() +{ + std::string request_data; + while(true) + { + input_ptr->getline(request_data, '\n'); + // std::string response_data = Engine::Process(request_data); + // output_ptr << response_data << '\n'; + } +} \ No newline at end of file diff --git a/docs/develop/总体设计文档.md b/docs/develop/总体设计文档.md index 9d15d34..10ae6de 100644 --- a/docs/develop/总体设计文档.md +++ b/docs/develop/总体设计文档.md @@ -47,14 +47,14 @@ memoryriver类维护一个缓存,简单地缓存高频访问和连续访问; 实际的文件操作只由一个线程负责,万级的IOPS足够应付需求;内存中的资源, ### 引擎模块 -具体执行业务,一次请求对应且只对应一次引擎模块API调用,支持并行(API阻塞但可同时运行)。当API入口函数被调用后,执行相关具体操作(包括会话管理),然后返回响应。 +具体执行业务,一次请求对应且只对应一次引擎模块API调用,支持并行(API阻塞但可同时运行)。当API入口函数被调用后,执行相关具体操作(不包括会话管理、鉴权),然后返回响应。 ### 调度模块 负责对外提供文本模式的交互,以及维护请求级的并行。从流`request`读取文本格式的命令,并把内部数据格式的响应翻译成文本格式,向引擎模块发送请求(调用引擎模块对外提供的API),并把响应返回到流`response`。支持条件允许时的并行: - 输入子模块从`request`读取请求,打上时间戳,分独占式请求和可并行请求按时间戳顺序分批处理。处理一个请求时,启动一个工作线程调用翻译执行子模块。同一个会话的请求不可并行,把`std::thread`move进相应的该会话的工作线程句柄队列,下一个join前一个。成批执行可并行请求时,启动完当前批次所有工作线程后join每个session的最后一个工作线程,结束之后就可以执行下一批了。为了在服务模式下处理时有时无的请求,两个流在读取时是阻塞的(自己封装一个,用`std::condition_variable`通讯),并且读一个处理一个,碰到“不属于自己批次”的东西才算一批结束。 - 翻译执行子模块(入口函数本身阻塞)join完同一个session的上一个请求后,向引擎模块API发送请求,得到响应后把响应数据传给输出子模块的调用接口(阻塞但可并行,处理部分同时运行,上锁后直接输出到`response`,输出本身不同时进行)。 -注意,在`request`流和`response`流中,输入输出仅保证单个请求/响应是完整的,多个请求/响应之间是完全“混杂”的,通过`session token`、`operation token`(操作标识由用户侧会话管理器维护,~~反正`session token`已经划分频道了,用户开F12瞎改后果自负~~)区分,通过`outhentication key`鉴权。`request`流和`response`流始终由信模块控制。注意,通讯模块不负责会话管理。 +注意,在`request`流和`response`流中,输入输出仅保证单个请求/响应是完整的,多个请求/响应之间是完全“混杂”的,通过`session token`、`operation token`(操作标识由用户侧会话管理器维护,~~反正`session token`已经划分频道了,用户开F12瞎改后果自负~~)区分,通过`outhentication key`鉴权。`request`流和`response`流始终由信模块控制。调度模块负责会话管理、鉴权,保证引擎只接受形式合法的简单内部数据。 ### 内置交互模块 当处于server模式下,不负责会话管理,直接把`std::cin`和`std::cout`的内容转发给通信与调度模块;处于interactive模式下时,提供用户侧会话管理,然后再调用通信与调度模块。 @@ -74,10 +74,10 @@ memoryriver类维护一个缓存,简单地缓存高频访问和连续访问; # 用户交互设计 ## 内置命令 -- `# OpenSession `:向引擎申请一个新会话 -- `# CloseSession `:显示地告知引擎停止某个会话 +- `# OpenSession `:向调度模块申请一个新会话 +- `# CloseSession `:显示地告知调度模块停止某个会话 - `# ReRequest `:向服务端重新请求调取某次操作响应的缓存 -- `# Request # `:向引擎发送一个请求 +- `# Request # `:向后端发送一个请求 ## 向用户提供的命令 - `SU `:登录某个用户(登录栈+1) @@ -100,7 +100,7 @@ memoryriver类维护一个缓存,简单地缓存高频访问和连续访问; # 底层数据接口约定(类、结构体设计) ## 请求 -- 引擎接受:内部数据`struct RequestType { std::string SessionToKen, OperationToken, AuthenticationKey; std::any content; };` +- 引擎接受:内部数据`struct RequestType { RequestKindType requestkind; std::any content; };` - 调度模块接受:`! ! ` - 内置交互模块(interactive模式)接受:字符串,`` - 云命令行接受:字符串,`` @@ -108,7 +108,7 @@ memoryriver类维护一个缓存,简单地缓存高频访问和连续访问; ## 响应 注意,对于申请Session时,响应用``替代` ! ` - 内置交互模块(interactive模式)返回:字符串,`` - 云命令行返回:字符串,``