@shgroup/dsh-serenity-hooks 1.24.4 → 1.24.6
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dsh.plugin.json +1 -1
- package/lib/client.js +2556 -4
- package/lib/index.js +11 -29
- package/package.json +9 -2
package/lib/index.js
CHANGED
|
@@ -7944,23 +7944,6 @@ function registerOpencodeSkills(ctx) {
|
|
|
7944
7944
|
};
|
|
7945
7945
|
ctx.skills.registerProvider(() => provider);
|
|
7946
7946
|
}
|
|
7947
|
-
//#endregion
|
|
7948
|
-
//#region src/gateway-auth.ts
|
|
7949
|
-
/**
|
|
7950
|
-
* gateway-auth.ts — F1 双端口网关:认证域纯逻辑(v1.22.4 安全加固)
|
|
7951
|
-
*
|
|
7952
|
-
* 从 gateway.ts 拆分(S142 熵点治理,v1.22.8):认证纯逻辑独立成模块——
|
|
7953
|
-
* 登录验证(scrypt)/ 会话 token(滑动 TTL + 吊销)/ 失败锁定(账号维度指数退避)/
|
|
7954
|
-
* CSRF(双提交 + Origin 校验)/ cookie 解析 / 登录页 HTML。
|
|
7955
|
-
* gateway.ts 保留 HTTP 装配(startGateway/registerGateway)并从本模块 import。
|
|
7956
|
-
*
|
|
7957
|
-
* 纯函数设计(可单测):无 socket/无 HTTP 依赖,全部导出可注入测试。
|
|
7958
|
-
*/
|
|
7959
|
-
function verifyGatewayLogin(accounts, user, password) {
|
|
7960
|
-
const account = accounts.find((a) => a.user === user);
|
|
7961
|
-
if (!account) return false;
|
|
7962
|
-
return verifyPassword(password, account.passHash);
|
|
7963
|
-
}
|
|
7964
7947
|
/** 内存会话表(重启即清空——用户决策) */
|
|
7965
7948
|
const sessions = /* @__PURE__ */ new Map();
|
|
7966
7949
|
/** 颁发会话 token(Hex 32 字节) */
|
|
@@ -8127,13 +8110,13 @@ button:active{background:#2563eb}
|
|
|
8127
8110
|
${csrf ? `<input type="hidden" name="csrf" value="${csrf}">` : ""}
|
|
8128
8111
|
<label for="f-user">用户名</label>
|
|
8129
8112
|
<input id="f-user" type="text" name="user" placeholder="用户名" autocomplete="username" autocapitalize="none" autocorrect="off" required autofocus enterkeyhint="next">
|
|
8130
|
-
<label for="f-pass"
|
|
8131
|
-
<input id="f-pass" type="password" name="password" placeholder="密码" autocomplete="current-password"
|
|
8113
|
+
<label for="f-pass">密码(或下方验证码,二选一)</label>
|
|
8114
|
+
<input id="f-pass" type="password" name="password" placeholder="密码" autocomplete="current-password" enterkeyhint="next">
|
|
8132
8115
|
<label for="f-code">验证码(已绑定 Authenticator 时填写)</label>
|
|
8133
8116
|
<input id="f-code" type="text" name="code" placeholder="6 位验证码" inputmode="numeric" pattern="[0-9]{6}" maxlength="6" autocomplete="one-time-code" enterkeyhint="go">
|
|
8134
8117
|
<button type="submit">登录</button>
|
|
8135
8118
|
<div class="error">${extra}</div>
|
|
8136
|
-
<p class="hint"
|
|
8119
|
+
<p class="hint">已绑定验证器的账号:密码 或 6 位验证码任一即可登录(二选一)</p>
|
|
8137
8120
|
</form>
|
|
8138
8121
|
<p class="foot">Serenity ACC · dsh-serenity-hooks</p>
|
|
8139
8122
|
</div></body></html>`;
|
|
@@ -8488,17 +8471,16 @@ function startGateway(config, getAccounts) {
|
|
|
8488
8471
|
res.end(loginPageHtml(`账号已锁定,请 ${Math.ceil(lockedRemaining / 6e4)} 分钟后再试`));
|
|
8489
8472
|
return;
|
|
8490
8473
|
}
|
|
8491
|
-
const
|
|
8492
|
-
const
|
|
8493
|
-
|
|
8494
|
-
|
|
8495
|
-
if (totpEnabled && passOk && account !== void 0 && typeof account.totpSecret === "string" && account.totpSecret !== "") {
|
|
8474
|
+
const account = getAccounts().find((a) => a.user === user);
|
|
8475
|
+
const passOk = account !== void 0 && password !== "" && verifyPassword(password, account.passHash);
|
|
8476
|
+
let totpOk = false;
|
|
8477
|
+
if (totpEnabled && account !== void 0 && typeof account.totpSecret === "string" && account.totpSecret !== "") {
|
|
8496
8478
|
const hit = verifyTotpCode(account.totpSecret, code);
|
|
8497
8479
|
totpOk = hit !== null;
|
|
8498
8480
|
if (totpOk && hit !== null && lastTotpCounter.get(account.id) === hit) totpOk = false;
|
|
8499
8481
|
if (totpOk && hit !== null) lastTotpCounter.set(account.id, hit);
|
|
8500
8482
|
}
|
|
8501
|
-
if (passOk
|
|
8483
|
+
if (passOk || totpOk) {
|
|
8502
8484
|
resetFailState(user);
|
|
8503
8485
|
const token = issueToken(user);
|
|
8504
8486
|
res.writeHead(302, {
|
|
@@ -8506,12 +8488,12 @@ function startGateway(config, getAccounts) {
|
|
|
8506
8488
|
"set-cookie": `${cookieName}=${token}; HttpOnly; SameSite=Strict; Path=/${cookieSecure ? "; Secure" : ""}`
|
|
8507
8489
|
});
|
|
8508
8490
|
res.end();
|
|
8509
|
-
console.log(`[serenity-hooks] 登录成功: user=${user} ip=${remote}`);
|
|
8491
|
+
console.log(`[serenity-hooks] 登录成功: user=${user} ip=${remote} via=${passOk ? "password" : "totp"}`);
|
|
8510
8492
|
return;
|
|
8511
8493
|
}
|
|
8512
8494
|
const lockMs = recordLoginFailure(user);
|
|
8513
|
-
console.warn(`[serenity-hooks] 登录失败: user=${user} ip=${remote}
|
|
8514
|
-
const msg = lockMs > 0 ? `尝试过多,账号已锁定 ${Math.ceil(lockMs / 6e4)} 分钟` :
|
|
8495
|
+
console.warn(`[serenity-hooks] 登录失败: user=${user} ip=${remote}${lockMs > 0 ? ` 锁定=${Math.ceil(lockMs / 6e4)}min` : ""}`);
|
|
8496
|
+
const msg = lockMs > 0 ? `尝试过多,账号已锁定 ${Math.ceil(lockMs / 6e4)} 分钟` : "用户名、密码或验证码错误";
|
|
8515
8497
|
res.writeHead(401, { "content-type": "text/html; charset=utf-8" });
|
|
8516
8498
|
res.end(loginPageHtml(msg));
|
|
8517
8499
|
});
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@shgroup/dsh-serenity-hooks",
|
|
3
|
-
"version": "1.24.
|
|
3
|
+
"version": "1.24.6",
|
|
4
4
|
"description": "宁静号 ACC harness — Native Cordis 插件(DeepSeek Harness 运行时)。真实 DSH 工具注册(cc_fs/session/acc_msm 等 9 工具)+ 拦截缝机械约束(safe-mode/路径守卫/会话落盘)+ 系统提示词注入(ACC/CCE/Constraints/SKILL/Session 五块)。适配 DSH 公开版(deepseek-ai/deepseek-harness 0.1.0-rc)。",
|
|
5
5
|
"license": "MIT",
|
|
6
6
|
"repository": {
|
|
@@ -55,9 +55,9 @@
|
|
|
55
55
|
"@deepseek-ai/dsh-host-webserver": "^0.1.0-rc.5",
|
|
56
56
|
"@deepseek-ai/dsh-llm": "^0.1.0-rc.5",
|
|
57
57
|
"@deepseek-ai/dsh-session": "^0.1.0-rc.5",
|
|
58
|
+
"@deepseek-ai/dsh-session-title": "^0.1.0-rc.5",
|
|
58
59
|
"@deepseek-ai/dsh-shell": "^0.1.0-rc.5",
|
|
59
60
|
"@deepseek-ai/dsh-shell-env": "^0.1.0-rc.5",
|
|
60
|
-
"@deepseek-ai/dsh-session-title": "^0.1.0-rc.5",
|
|
61
61
|
"@deepseek-ai/dsh-skill": "^0.1.0-rc.5",
|
|
62
62
|
"@deepseek-ai/dsh-system-prompt": "^0.1.0-rc.5",
|
|
63
63
|
"@deepseek-ai/dsh-tools": "^0.1.0-rc.5",
|
|
@@ -86,11 +86,18 @@
|
|
|
86
86
|
},
|
|
87
87
|
"devDependencies": {
|
|
88
88
|
"@types/node": "^20.0.0",
|
|
89
|
+
"@types/qrcode-generator": "^1.0.6",
|
|
89
90
|
"@types/react": "^18.2.0",
|
|
91
|
+
"qrcode-generator": "^2.0.4",
|
|
90
92
|
"react": "^18.2.0",
|
|
91
93
|
"tsdown": "^0.22.14",
|
|
92
94
|
"typescript": "^5.4.0",
|
|
93
95
|
"unrun": "^0.3.1",
|
|
94
96
|
"vitest": "^1.6.0"
|
|
97
|
+
},
|
|
98
|
+
"pnpm": {
|
|
99
|
+
"onlyBuiltDependencies": [
|
|
100
|
+
"esbuild"
|
|
101
|
+
]
|
|
95
102
|
}
|
|
96
103
|
}
|