From 414d7332aa4fb34b5b74a2a00c373beb6f69c8c3 Mon Sep 17 00:00:00 2001
From: qing <1776177662@qq.com>
Date: Tue, 21 Jul 2026 23:32:04 +0800
Subject: [PATCH 1/9] =?UTF-8?q?dnfs=E6=A8=A1=E5=9D=97?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
---
static/public/{main.html => dnfs.html} | 0
static/public/js/login.js | 2 +-
2 files changed, 1 insertion(+), 1 deletion(-)
rename static/public/{main.html => dnfs.html} (100%)
diff --git a/static/public/main.html b/static/public/dnfs.html
similarity index 100%
rename from static/public/main.html
rename to static/public/dnfs.html
diff --git a/static/public/js/login.js b/static/public/js/login.js
index 96522d6..3c70ea8 100644
--- a/static/public/js/login.js
+++ b/static/public/js/login.js
@@ -149,7 +149,7 @@ form.addEventListener('submit', async function(e) {
if (result.success) {
alert(`登陆成功`);
sessionStorage.setItem('token', result.data.token);
- location.href = 'main.html';
+ location.href = 'dnfs.html';
} else {
alert(result.message || '登录失败');
}
From f2e2e59977d4980990c7bf87997f9e6cc8a854b9 Mon Sep 17 00:00:00 2001
From: qing <1776177662@qq.com>
Date: Wed, 22 Jul 2026 10:13:10 +0800
Subject: [PATCH 2/9] =?UTF-8?q?=E5=87=86=E5=A4=87dnfs=E6=A8=A1=E5=9D=97?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
---
_inst.sh | 1 +
dnfs/.gitignore | 5 +++++
dnfs/{_setup.sh => _set.sh} | 1 +
dnfs/requirements.txt | 1 +
4 files changed, 8 insertions(+)
rename dnfs/{_setup.sh => _set.sh} (85%)
diff --git a/_inst.sh b/_inst.sh
index 45c4867..4a4fe8f 100644
--- a/_inst.sh
+++ b/_inst.sh
@@ -30,4 +30,5 @@ inst_module "libhttp"
inst_module "libcrypt"
inst_module "gateway"
inst_module "static"
+inst_module "dnfs"
inst_module "core" # core last
diff --git a/dnfs/.gitignore b/dnfs/.gitignore
index aa67360..817ce2d 100644
--- a/dnfs/.gitignore
+++ b/dnfs/.gitignore
@@ -1,5 +1,10 @@
#prjs
*.db
+*.bin
+*.build
+*.dist
+*.onefile-build
+nuitka-crash-report.xml
# Byte-compiled / optimized / DLL files
__pycache__/
diff --git a/dnfs/_setup.sh b/dnfs/_set.sh
similarity index 85%
rename from dnfs/_setup.sh
rename to dnfs/_set.sh
index cc0b017..2ba8dd3 100755
--- a/dnfs/_setup.sh
+++ b/dnfs/_set.sh
@@ -4,3 +4,4 @@ python3 -m venv .env
#sudo chmod +x .env/bin/activate
source .env/bin/activate
pip install -r requirements.txt -i https://pypi.tuna.tsinghua.edu.cn/simple
+nuitka --onefile --jobs=1 dnfs.py
diff --git a/dnfs/requirements.txt b/dnfs/requirements.txt
index 77f8550..f01363e 100644
--- a/dnfs/requirements.txt
+++ b/dnfs/requirements.txt
@@ -1,3 +1,4 @@
+nuitka
flask
flask-cors
flask_sqlalchemy
From caf2359e5f549ba84b76d1c698cdcbc37851ef25 Mon Sep 17 00:00:00 2001
From: qing <1776177662@qq.com>
Date: Wed, 22 Jul 2026 10:15:35 +0800
Subject: [PATCH 3/9] =?UTF-8?q?=E5=A2=9E=E5=8A=A0dnfs=E5=90=8E=E7=BB=AD?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
---
core/init.txt | 3 ++-
dnfs/_run.sh | 6 +++---
2 files changed, 5 insertions(+), 4 deletions(-)
diff --git a/core/init.txt b/core/init.txt
index d9dd105..92d9a9f 100644
--- a/core/init.txt
+++ b/core/init.txt
@@ -1,2 +1,3 @@
-bash /opt/micro_servers/gateway/_run.sh
bash /opt/micro_servers/static/_run.sh
+bash /opt/micro_servers/dnfs/_run.sh
+bash /opt/micro_servers/gateway/_run.sh
diff --git a/dnfs/_run.sh b/dnfs/_run.sh
index 7be4ff4..befdc00 100755
--- a/dnfs/_run.sh
+++ b/dnfs/_run.sh
@@ -1,5 +1,5 @@
#!/bin/bash
cd "$(dirname "$0")" || exit
-bash ./_setup.sh
-source ./.env/bin/activate
-exec python dnfs.py
+#bash ./_setup.sh
+#source ./.env/bin/activate
+exec ./dnfs.bin
From d60fe533bd80a1d8aa27c50269a8f236eefe941c Mon Sep 17 00:00:00 2001
From: qing <1776177662@qq.com>
Date: Wed, 22 Jul 2026 10:17:33 +0800
Subject: [PATCH 4/9] dnfs_3
---
core/_run.sh | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/core/_run.sh b/core/_run.sh
index cdc554d..6f85ff4 100644
--- a/core/_run.sh
+++ b/core/_run.sh
@@ -1,4 +1,4 @@
#!/bin/bash
cd "$(dirname "$0")" || exit
-./nidus.out -i /etc/Nidus/init.txt --serve 5200
+./nidus.out -i init.txt --serve 5200
From 419ae828583af9076c69f89eee549dd7518610c4 Mon Sep 17 00:00:00 2001
From: qing <1776177662@qq.com>
Date: Wed, 22 Jul 2026 12:47:13 +0800
Subject: [PATCH 5/9] =?UTF-8?q?=E4=BF=AE=E6=94=B9HTTP=20LIBRARY=EF=BC=8C?=
=?UTF-8?q?=E5=A2=9E=E5=8A=A0OPTIONS=E6=94=AF=E6=8C=81=20=E4=BF=AE?=
=?UTF-8?q?=E6=94=B9GATEWAY=EF=BC=8C=E4=BF=AE=E5=A4=8D=E8=BD=AC=E5=8F=91?=
=?UTF-8?q?=20=E4=BF=AE=E6=94=B9dnfs=EF=BC=8C=E6=9A=82=E6=97=B6=E4=B8=8D?=
=?UTF-8?q?=E7=BC=96=E8=AF=91=EF=BC=88=E6=89=BE=E4=B8=8D=E5=88=B0=E6=A8=A1?=
=?UTF-8?q?=E6=9D=BF=EF=BC=89=20=E4=BF=AE=E6=94=B9static=EF=BC=8C=E8=83=BD?=
=?UTF-8?q?=E5=A4=9F=E8=8E=B7=E5=8F=96=E8=8A=82=E7=82=B9?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
---
dnfs/_run.sh | 7 +-
dnfs/index.html | 144 ++++++++++++++++++++++++++++++++++
gateway/src/main.cpp | 41 ++++++----
libhttp/inc/us/HttpServer.hpp | 3 +
libhttp/src/HttpServer.cpp | 87 +++++++++++++++++++-
static/public/dnfs.html | 3 +-
static/public/js/dnfs.js | 46 +++++++++++
static/public/js/login.js | 2 +-
8 files changed, 310 insertions(+), 23 deletions(-)
create mode 100644 dnfs/index.html
create mode 100644 static/public/js/dnfs.js
diff --git a/dnfs/_run.sh b/dnfs/_run.sh
index befdc00..4c0aa75 100755
--- a/dnfs/_run.sh
+++ b/dnfs/_run.sh
@@ -1,5 +1,6 @@
#!/bin/bash
cd "$(dirname "$0")" || exit
-#bash ./_setup.sh
-#source ./.env/bin/activate
-exec ./dnfs.bin
+bash ./_setup.sh
+source ./.env/bin/activate
+#exec ./dnfs.bin
+exec python3 dnfs.py
diff --git a/dnfs/index.html b/dnfs/index.html
new file mode 100644
index 0000000..44262df
--- /dev/null
+++ b/dnfs/index.html
@@ -0,0 +1,144 @@
+
+
+
+
+
+ 树状笔记
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ 正在迁移节点:
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
确定删除该节点吗?
+
+
此节点包含文件,删除后文件将无法恢复
+
此操作不可恢复
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/gateway/src/main.cpp b/gateway/src/main.cpp
index ca8f9f6..5af3a76 100644
--- a/gateway/src/main.cpp
+++ b/gateway/src/main.cpp
@@ -273,6 +273,19 @@ void registerRoutes(HttpServer &server) {
server.post("*", [](const auto& req, const auto& params) {
return handleProxy(req, params, "post");
});
+
+ server.options("*", [](const auto& req, const auto& params) {
+ pmc::net::http::response res;
+ res.result(pmc::net::http::status::ok);
+ res.set(pmc::net::http::field::access_control_allow_origin, "*");
+ res.set(pmc::net::http::field::access_control_allow_methods, "GET, POST, OPTIONS");
+ res.set(pmc::net::http::field::access_control_allow_headers, "Content-Type, Authorization");
+ res.set(pmc::net::http::field::access_control_max_age, "86400");
+ res.body() = "";
+ res.content_length(0);
+ res.prepare_payload();
+ return res;
+ });
}
http::response wrapperHttp(
@@ -444,6 +457,7 @@ http::response handleProxy(
std::string t_url = "";
std::string url = "";
std::string auth = "";
+ json::value jv_t; /* json value of the token */
{
auto flag = false;
auto it = req.base().find("Target-Url");
@@ -456,7 +470,7 @@ http::response handleProxy(
t_url = req["target-url"];
}
- if (url == "") {
+ if (t_url == "") {
t_url = _DEFT_URL;
flag = true;
}
@@ -466,7 +480,7 @@ http::response handleProxy(
url += req.target();
it = req.base().find("Authorization");
- if (it == req.base().end() && !flag) {
+ if (it == req.base().end() && !flag) { /* 不是默认代理地址且无令牌 */
throw std::runtime_error("401");
}
std::string raw = req["Authorization"];
@@ -484,21 +498,20 @@ http::response handleProxy(
}
std::cout << "auth data: " << auth << std::endl;
}
- }
- json::value jv;
- /* 令牌是否过期 */
- {
- /* TODO: 放进try包裹 */
- jv = json::parse(auth);
- json::object& obj = jv.as_object();
+ if (!flag) { /* 令牌是否过期 */
+
+ /* TODO: 放进try包裹 */
+ jv_t = json::parse(auth);
+ json::object& obj = jv_t.as_object();
- auto t = json::value_to(obj["created_at"]);
- bool r = LocalTime::isExpired(t);
+ auto t = json::value_to(obj["created_at"]);
+ bool r = LocalTime::isExpired(t);
- if (r) {
- THROW_EX_CUSTOM(HttpException, 2000, "Authorization Expired",
- 401, "*");
+ if (!r) {
+ THROW_EX_CUSTOM(HttpException, 2000, "Authorization Expired",
+ 401, "*");
+ }
}
}
diff --git a/libhttp/inc/us/HttpServer.hpp b/libhttp/inc/us/HttpServer.hpp
index 7617ff2..f157f38 100644
--- a/libhttp/inc/us/HttpServer.hpp
+++ b/libhttp/inc/us/HttpServer.hpp
@@ -60,6 +60,7 @@ public:
void post(const std::string& path, HttpRequestHandler handler);
void put(const std::string& path, HttpRequestHandler handler);
void del(const std::string& path, HttpRequestHandler handler);
+ void options(const std::string& path, HttpRequestHandler handler); // 新增 OPTIONS
void use(MiddlewareHandler middleware);
void setStaticDirectory(const std::string& path);
@@ -102,6 +103,7 @@ private:
std::vector post_handlers_;
std::vector put_handlers_;
std::vector delete_handlers_;
+ std::vector options_handlers_; // 新增 OPTIONS 路由
std::vector middlewares_;
std::string static_directory_;
@@ -113,6 +115,7 @@ private:
bool matchPath(const std::string& path, const std::regex& pattern);
http::response handleRequest(const http::request& req);
HttpRequestHandler findRoute(const std::string& method, const std::string& path);
+ bool routeExists(const std::string& method, const std::string& path); // 新增辅助方法
void addSession(const std::shared_ptr& session);
void removeSession(const Session* session);
diff --git a/libhttp/src/HttpServer.cpp b/libhttp/src/HttpServer.cpp
index a32fa74..588cad8 100644
--- a/libhttp/src/HttpServer.cpp
+++ b/libhttp/src/HttpServer.cpp
@@ -4,7 +4,7 @@
#include
#include
#include
-#include // SSL_CTX_set_cipher_list
+#include
namespace pmc {
namespace net {
@@ -85,7 +85,6 @@ private:
<< remote_ip_ << ":" << remote_port_
<< " - " << ec.message()
<< " (code=" << ec.value() << ")" << std::endl;
- // 输出 OpenSSL 详细错误堆栈
ERR_print_errors_fp(stderr);
}
}));
@@ -168,7 +167,6 @@ private:
HttpServer* server_;
bool ssl_enabled_;
- // 使用 any_io_executor 兼容多种执行器
asio::strand strand_;
std::string remote_ip_ = "unknown";
@@ -272,7 +270,6 @@ void HttpServer::initSSLContext() {
asio::ssl::context::no_sslv3 |
asio::ssl::context::single_dh_use);
- // 设置现代加密套件,确保兼容主流客户端
SSL_CTX_set_cipher_list(ssl_ctx_->native_handle(),
"ECDHE+AESGCM:ECDHE+CHACHA20:DHE+AESGCM:DHE+CHACHA20:!aNULL:!MD5:!DSS");
@@ -391,6 +388,17 @@ void HttpServer::del(const std::string& path, HttpRequestHandler handler) {
delete_handlers_.push_back(entry);
}
+// ---- 新增 OPTIONS 路由注册 ----
+void HttpServer::options(const std::string& path, HttpRequestHandler handler) {
+ RouteEntry entry;
+ entry.path = path;
+ entry.handler = handler;
+ entry.is_wildcard = (path.find('*') != std::string::npos ||
+ path.find('?') != std::string::npos);
+ if (entry.is_wildcard) entry.pattern = wildcardToRegex(path);
+ options_handlers_.push_back(entry);
+}
+
void HttpServer::use(MiddlewareHandler m) {
middlewares_.push_back(m);
}
@@ -442,6 +450,7 @@ HttpRequestHandler HttpServer::findRoute(const std::string& method, const std::s
else if (method == "POST") handlers = &post_handlers_;
else if (method == "PUT") handlers = &put_handlers_;
else if (method == "DELETE") handlers = &delete_handlers_;
+ else if (method == "OPTIONS") handlers = &options_handlers_;
else return nullptr;
// 精确匹配优先
@@ -455,6 +464,11 @@ HttpRequestHandler HttpServer::findRoute(const std::string& method, const std::s
return nullptr;
}
+// ---- 新增辅助方法:检查路由是否存在 ----
+bool HttpServer::routeExists(const std::string& method, const std::string& path) {
+ return findRoute(method, path) != nullptr;
+}
+
// ---- 请求处理核心 ----
http::response HttpServer::handleRequest(const http::request& req) {
std::string target_path(req.target().data(), req.target().size());
@@ -486,6 +500,68 @@ http::response HttpServer::handleRequest(const http::request<
}
std::string method = http::to_string(req.method());
+
+ // ========== 处理 OPTIONS 预检请求 ==========
+ if (method == "OPTIONS") {
+ // 检查是否有自定义 OPTIONS 路由
+ auto handler = findRoute("OPTIONS", target_path);
+ if (handler) {
+ try {
+ return handler(req, params);
+ } catch (const std::exception& e) {
+ std::cerr << "[Handler] Exception: " << e.what() << std::endl;
+ res.result(http::status::internal_server_error);
+ res.body() = "500 Internal Server Error\n";
+ res.prepare_payload();
+ return res;
+ }
+ }
+
+ // 自动生成 OPTIONS 响应
+ auto origin = req.find(http::field::origin);
+ if (origin != req.end()) {
+ // 构建允许的方法列表
+ std::vector all_methods = {"GET", "POST", "PUT", "DELETE", "OPTIONS"};
+ std::vector allowed_methods;
+
+ // 检查每个方法是否有对应的路由
+ for (const auto& m : all_methods) {
+ if (m == "OPTIONS" || routeExists(m, target_path)) {
+ allowed_methods.push_back(m);
+ }
+ }
+
+ if (!allowed_methods.empty()) {
+ std::string allow_methods;
+ for (size_t i = 0; i < allowed_methods.size(); ++i) {
+ if (i > 0) allow_methods += ", ";
+ allow_methods += allowed_methods[i];
+ }
+
+ res.result(http::status::ok);
+ res.set(http::field::allow, allow_methods);
+ res.set(http::field::access_control_allow_origin,
+ std::string(origin->value()));
+ res.set(http::field::access_control_allow_methods, allow_methods);
+ res.set(http::field::access_control_allow_headers,
+ "Content-Type, Authorization, X-Requested-With, Accept, Origin");
+ res.set(http::field::access_control_max_age, "86400");
+ res.body() = "";
+ res.content_length(0);
+ res.prepare_payload();
+ return res;
+ }
+ }
+
+ // 没有 Origin 头或没有匹配的方法
+ res.result(http::status::not_found);
+ res.body() = "404 Not Found\n";
+ res.prepare_payload();
+ return res;
+ }
+ // ========== OPTIONS 处理结束 ==========
+
+ // 查找普通路由
auto handler = findRoute(method, target_path);
// 静态文件
@@ -562,6 +638,9 @@ void HttpServer::showStatus() const {
std::cout << " DELETE: " << delete_handlers_.size() << " handler(s)" << std::endl;
for (const auto& entry : delete_handlers_)
std::cout << " DELETE " << entry.path << (entry.is_wildcard ? " (wildcard)" : "") << std::endl;
+ std::cout << " OPTIONS: " << options_handlers_.size() << " handler(s)" << std::endl; // 新增
+ for (const auto& entry : options_handlers_)
+ std::cout << " OPTIONS " << entry.path << (entry.is_wildcard ? " (wildcard)" : "") << std::endl;
std::cout << "Middlewares: " << middlewares_.size() << std::endl;
std::cout << "==========================" << std::endl;
}
diff --git a/static/public/dnfs.html b/static/public/dnfs.html
index 6995789..275492a 100644
--- a/static/public/dnfs.html
+++ b/static/public/dnfs.html
@@ -98,5 +98,6 @@
百度推荐
+