@shgroup/dsh-serenity-hooks 1.61.0 → 1.63.2
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/README.md +3 -3
- package/assets/serenity-voyage.html +1241 -1073
- package/dsh.plugin.json +2 -2
- package/lib/client.js +103 -89
- package/lib/index.js +198 -96
- package/lib/seams/bootstrap.d.ts +53 -28
- package/package.json +2 -2
package/lib/client.js
CHANGED
|
@@ -8,7 +8,7 @@ window.__ModuleLoader__.load({
|
|
|
8
8
|
let react = require("react");
|
|
9
9
|
let react_jsx_runtime = require("react/jsx-runtime");
|
|
10
10
|
//#region \0sp-css:src/client/SafeModePanel
|
|
11
|
-
const css$5 = "/* SafeModePanel — 会话头部 Serenity 状态胶囊(v1.24.10 胶囊改版,对齐 OcgoDockEntry pill)\n * 胶囊 999px 全圆 → 点击 → 自绘 popover(340px 右上角卡片,外点/Escape 关闭)\n * popover 内:分组(groupTitle 标题 + rowCard 行卡)——看齐官方 settings 设计语言\n * 遵循 web-styling.md:颜色只用 --dsw-alias-* 语义 token(明暗自适应)+ --sp-safe-green 统一绿家族;\n * 前缀 sp- 防冲突。 */\n\n/* ── 统一绿色变量家族(一处改全改;emerald 500~600 区间保证深色对比度) ── */\n\n.sp-root {\n --sp-safe-green: #0ba875; /* emerald-550:SAFE ON 主色 */\n --sp-safe-green-deep: #059669; /* emerald-600:渐变深端 */\n}\n\n/* ── 头部状态胶囊(可点击) ── */\n\n.sp-card {\n display: inline-flex;\n align-items: center;\n gap: 6px;\n padding: 4px 9px; /* 无固定 height:由内容撑高(胶囊) */\n border: 1px solid var(--dsw-alias-border-l1);\n border-radius: 999px;\n background: var(--dsw-alias-bg-layer-2);\n color: inherit;\n font-size: 12px;\n line-height: 1;\n cursor: pointer;\n transition: background var(--ds-transition-duration-fast, 0.1s) var(--ds-ease-in-out, ease),\n border-color var(--ds-transition-duration-fast, 0.1s) var(--ds-ease-in-out, ease);\n}\n\n.sp-card:hover {\n background: var(--dsw-alias-interactive-bg-hover);\n border-color: var(--dsw-alias-border-l2);\n}\n\n.sp-card:focus-visible {\n outline: 2px solid var(--dsw-alias-button-ghost-active-border);\n outline-offset: 1px;\n}\n\n.sp-card:disabled {\n opacity: 0.6;\n cursor: default;\n}\n\n/* 绿点 = Serenity 在线(恒亮绿,不随 SAFE 变);离线/未激活 → 灰 */\n.sp-dot {\n flex: none;\n width: 7px;\n height: 7px;\n border-radius: 50%;\n background: var(--dsw-alias-state-success-primary);\n}\n\n.sp-dotOff {\n background: var(--dsw-alias-label-dimmed);\n}\n\n.sp-cardInactive {\n opacity: 0.85;\n}\n\n.sp-cardInactive .sp-brand {\n color: var(--dsw-alias-label-secondary);\n font-weight: 500;\n}\n\n.sp-brand {\n color: var(--dsw-alias-label-primary);\n font-weight: 500;\n}\n\n/* 版本号:monospace + translateY(1px) 下沉对齐(与文字基线齐平) */\n.sp-ver {\n color: var(--dsw-alias-label-secondary);\n font-size: 11px;\n font-family: var(--ds-font-family-code, monospace);\n transform: translateY(1px);\n}\n\n/* 1px 深灰分隔线(两侧紧凑) */\n.sp-sep {\n flex: none;\n width: 1px;\n height: 12px;\n margin: 0 2px;\n background: var(--dsw-alias-label-tertiary);\n}\n\n.sp-shield {\n display: inline-flex;\n width: 14px;\n height: 14px;\n flex: none;\n}\n\n.sp-shield svg {\n width: 14px;\n height: 14px;\n}\n\n.sp-statusWord {\n font-size: 11px;\n font-weight: 600;\n letter-spacing: 0;\n white-space: nowrap;\n}\n\n/* SAFE OFF(未保护):灰——低姿态提醒,非错误(用户自己的开关选择) */\n.sp-cardUnprotected .sp-shield {\n color: var(--dsw-alias-label-secondary);\n}\n\n.sp-cardUnprotected .sp-statusWord {\n color: var(--dsw-alias-label-secondary);\n}\n\n/* SAFE ON(保护中):emerald 绿——安心(盾牌实色 + SAFE 文字渐变质感) */\n.sp-cardProtected .sp-shield {\n color: var(--sp-safe-green);\n}\n\n.sp-cardProtected .sp-statusWord {\n color: var(--sp-safe-green);\n background: linear-gradient(135deg, var(--sp-safe-green) 0%, var(--sp-safe-green-deep) 100%);\n -webkit-background-clip: text;\n background-clip: text;\n -webkit-text-fill-color: transparent;\n}\n\n/* ── Mac 风格滑块(v1.24.10:轨道 24×13 / thumb 11px 灰白 #f2f4f6 无图标 / cubic-bezier 平滑) ── */\n\n.sp-switch {\n display: inline-block;\n width: 24px;\n height: 13px;\n border-radius: 999px;\n position: relative;\n flex: none;\n cursor: pointer;\n transition: background 0.25s cubic-bezier(0.4, 0, 0.2, 1);\n}\n\n.sp-switchOff {\n background: var(--dsw-alias-border-l2);\n}\n\n.sp-switchOn {\n background: var(--sp-safe-green);\n}\n\n.sp-switchThumb {\n position: absolute;\n top: 1px;\n width: 11px;\n height: 11px;\n border-radius: 50%;\n background: #f2f4f6; /* Mac 灰白 thumb(明暗通用) */\n box-shadow: 0 1px 2px rgba(0, 0, 0, 0.3);\n transition: left 0.25s cubic-bezier(0.4, 0, 0.2, 1);\n}\n\n.sp-switchOff .sp-switchThumb {\n left: 1px;\n}\n\n.sp-switchOn .sp-switchThumb {\n left: 12px; /* 24 - 11 - 1 */\n}\n\n/* CSS 特异性坑(S013 指南):.sp-switch:hover (0,2,0) 会覆盖 .sp-switchOn (0,1,0)\n * → ON 态 hover 绿底消失。必须同特异性且后定义补回。 */\n.sp-switch:hover {\n filter: brightness(1.08);\n}\n\n.sp-switchOn:hover {\n background: var(--sp-safe-green);\n}\n\n.sp-switchBusy {\n opacity: 0.6;\n cursor: default;\n pointer-events: none;\n}\n\n.sp-chev {\n color: var(--dsw-alias-label-dimmed);\n flex: none;\n}\n\n/* ── 自绘 popover(340px 右上角小卡片,替代官方 Modal) ── */\n\n.sp-root {\n position: relative;\n display: inline-flex;\n}\n\n/* ── 自绘 popover(卡片,替代官方 Modal)\n v1.36.1(所有者:「卡片做成双倍宽,左侧是信息,右侧是动画」):340 → **680px**(双倍)。\n v1.39.1(所有者:「下拉 dialog / 弹窗内容过宽后,会被左侧元素遮挡」):\n 🔴 根因 = **祖先 `overflow:hidden` 裁切**,不是 z-index 也不是宽度不够。\n 真机取证(CDP hit-test,1280/1600/1920 三档一致):\n · 胶囊右端 x=954.2、卡片 680 宽 ⇒ 左边界 274.2\n · 而会话中列 `pI_x6G_centerCol` / `wSkVaW_root` 都 `overflow:hidden` 且左边界 = **280**\n ⇒ 左边缘 **5.8px** 被裁掉(左边框线与圆角消失)。\n 加宽前(340px)左边界 614.2 远在 280 右侧 ⇒ **这正是 v1.36.1 加宽引入的回归**。\n 修法:**改为 `position: fixed`** —— fixed 子元素**不受祖先 overflow 裁切**;\n 坐标由 SafeModePanel 用 `getBoundingClientRect()` 算出并夹取进视口(见 .tsx 的 useLayoutEffect)。\n (本仓 client 侧**无 `react-dom` 依赖** ⇒ `createPortal` 不可用;fixed 是等效且更轻的出路。\n 已在真机验证祖先链**无** transform/filter/contain/will-change ⇒ fixed 不会被降级为相对某祖先。)\n 宽度仍走 `min(680px, 100vw-24px)`(窄视口兜底),窄屏退回单栏见文末 @media。 */\n.sp-pop {\n position: fixed; /* 不受祖先 overflow:hidden 裁切;left/top 由 JS 计算 */\n top: 0; /* ← 声明默认值,JS 会覆写(未落位时组件给 -9999 屏外值,不会闪到右下角) */\n left: 0;\n width: min(680px, calc(100vw - 24px));\n z-index: 2000;\n box-sizing: border-box;\n padding: 14px;\n border: 1px solid var(--dsw-alias-border-l1);\n border-radius: 14px;\n background: var(--dsw-alias-bg-overlay);\n box-shadow: 0 12px 40px rgba(0, 0, 0, 0.5);\n}\n\n/* ── 航行动画栏:宁静号心智模型(ACC 层资产 /serenity/voyage,S142 §12.44 → v1.36.1 改右栏)\n v1.36.1 改版(所有者:「卡片做成双倍宽,左侧是信息,右侧是动画」):\n 动画从**背景层**改为**右栏**。这一改动解开了 v1.36.0 的取舍死结——\n 旧布局里动画垫在正文底下,必须靠 0.75 的卡片底色把它压住才读得清字;\n 分段之后两者不再争同一片像素 ⇒ 动画可以亮、正文可以干净,不必再互相妥协。\n ⚠️ 动画本身仍是「卡片模式」(词元压到 22%、铭牌层关闭),本栏只负责**给位置**,不改作品。 */\n.sp-popVoyage {\n overflow: hidden; /* 裁掉 iframe 在 14px 圆角外的溢出 */\n /* 分段后不再需要 0.75 的重压暗:压到 0.9 只压整体观感,不与正文争对比度。\n 若所有者觉得动画太亮/太暗,这仍是主旋钮(次旋钮 = iframe 的 blur)。 */\n background: rgba(6, 11, 14, 0.9);\n display: flex;\n flex-direction: row;\n /* 两栏都从**同一行高**分配(row 轴 cross = 高度):左栏按内容、右栏吃满行高。\n 行高 = 左栏内容高度,且被 max-height 封顶 ⇒ 信息长时内部滚动,动画不把行撑破。 */\n align-items: stretch;\n gap: 12px;\n padding: 12px;\n max-height: calc(100vh - 120px);\n}\n/* 左栏:信息(正文)——固定 340px,与旧卡片同宽,保证原有排印不变 */\n.sp-popVoyage > .sp-popBody {\n position: relative;\n z-index: 1;\n order: 1;\n flex: none;\n width: 340px;\n min-width: 0;\n}\n/* 右栏:动画——吃掉剩余宽度,并吃满左栏高度 */\n.sp-voyage {\n order: 2;\n flex: 1 1 auto;\n min-width: 0;\n position: relative;\n pointer-events: none; /* 纯展示:不挡点击、不抢焦点 */\n overflow: hidden;\n border-radius: 10px;\n min-height: 260px; /* 动画的下限:信息很少时也不塌成一条 */\n}\n.sp-voyage iframe {\n display: block;\n width: 100%;\n height: 100%;\n border: 0;\n /* ⚠️ 用 iframe 自身的 filter 而**不是** backdrop-filter:iframe 内容不参与本文档的\n backdrop(跨文档不采样)⇒ backdrop-filter 对它无效,只有 filter 才是可靠的杠杆。\n v1.36.1:动画移入独立右栏后不再压在文字后面 ⇒ 磨砂可以收得很轻(1.2 → 0.6px),\n 既保留柔化,又让飞船细节(舷窗/引擎环)比旧版清楚。 */\n filter: blur(0.6px);\n}\n\n/* 窄屏(放不下两栏)⇒ 退回单栏:信息在上、动画在下(DOM 顺序即如此,无需改结构) */\n@media (max-width: 860px) {\n .sp-pop {\n /* 两栏放不下时,卡片回到\"不超过视口\"的旧行为 */\n width: min(420px, calc(100vw - 24px));\n }\n .sp-popVoyage {\n flex-direction: column;\n align-items: stretch;\n }\n .sp-popVoyage > .sp-popBody {\n width: auto; /* 单栏下不再固定 340px,跟随卡片宽度 */\n flex: none; /* 按内容高(仍受自身 max-height 约束) */\n }\n .sp-voyage {\n flex: none;\n height: 200px; /* 单栏时给动画明确高度,避免被 flex 压扁 */\n min-height: 0;\n }\n}\n\n.sp-popBody {\n display: flex;\n flex-direction: column;\n gap: 14px;\n max-height: calc(100vh - 140px);\n overflow-y: auto;\n}\n\n/* ── 分组(官方 settings 语言:groupTitle + rows) ── */\n\n.sp-group {\n display: flex;\n flex-direction: column;\n gap: 8px;\n}\n\n.sp-groupHead {\n display: flex;\n align-items: center;\n justify-content: space-between;\n gap: 8px;\n}\n\n.sp-groupTitle {\n margin: 0;\n font-size: 12px;\n line-height: 18px;\n font-weight: 600;\n letter-spacing: 0.02em;\n text-transform: uppercase;\n color: var(--dsw-alias-label-secondary);\n}\n\n.sp-rows {\n display: flex;\n flex-direction: column;\n gap: 6px;\n}\n\n/* 行卡(rowCard:border + radius + padding;值与 label 分离、长内容可换行) */\n.sp-row {\n display: flex;\n align-items: baseline;\n gap: 12px;\n min-width: 0;\n padding: 8px 12px;\n border: 1px solid var(--dsw-alias-border-l1);\n border-radius: 10px;\n background: var(--dsw-alias-bg-layer-2);\n}\n\n.sp-label {\n flex: none;\n width: 76px;\n font-size: 12px;\n font-weight: 500;\n color: var(--dsw-alias-label-secondary);\n white-space: nowrap;\n}\n\n.sp-value {\n flex: 1;\n min-width: 0;\n font-size: 12px;\n line-height: 18px;\n color: var(--dsw-alias-label-primary);\n font-family: var(--ds-font-family-code, monospace);\n word-break: break-all;\n overflow-wrap: anywhere;\n}\n\n/* 安全模式动作区 */\n.sp-actions {\n display: flex;\n align-items: center;\n gap: 12px;\n padding: 8px 12px;\n border: 1px solid var(--dsw-alias-border-l1);\n border-radius: 10px;\n background: var(--dsw-alias-bg-layer-2);\n}\n\n.sp-toggle {\n display: inline-flex;\n align-items: center;\n gap: 6px;\n height: 24px;\n padding: 0 10px;\n border: 1px solid var(--dsw-alias-border-l1);\n border-radius: 6px;\n font-size: 12px;\n cursor: pointer;\n transition: background var(--ds-transition-duration-fast, 0.1s) var(--ds-ease-in-out, ease);\n}\n\n.sp-toggleLg {\n height: 30px;\n padding: 0 16px;\n font-size: 13px;\n}\n\n.sp-toggleOn {\n background: color-mix(in srgb, var(--dsw-alias-state-error-primary) 14%, transparent);\n color: var(--dsw-alias-state-error-primary);\n border-color: color-mix(in srgb, var(--dsw-alias-state-error-primary) 45%, transparent);\n}\n\n.sp-toggleOff {\n background: var(--dsw-alias-interactive-bg-hover);\n color: var(--dsw-alias-label-secondary);\n}\n\n.sp-toggleIcon {\n flex: none;\n}\n\n.sp-toggleDesc {\n flex: 1;\n font-size: 12px;\n line-height: 18px;\n color: var(--dsw-alias-label-tertiary);\n}\n\n/* 🔴 2026-10-14:`.sp-cheapWorkers*` / `.sp-cheapWorker*` 样式区块已随 background 模式删除\n —— 那是「运行中 cheap-worker」列表(进度文件驱动)的样式,而进度文件不再有生产者。 */\n\n/* 底部提示(配置入口引导) */\n.sp-hint {\n margin: 0;\n font-size: 12px;\n line-height: 18px;\n color: var(--dsw-alias-label-tertiary);\n word-break: break-word;\n overflow-wrap: anywhere;\n padding: 8px 12px;\n border: 1px dashed var(--dsw-alias-border-l2);\n border-radius: 10px;\n}\n";
|
|
11
|
+
const css$5 = "/* SafeModePanel — 会话头部 Serenity 状态胶囊(v1.24.10 胶囊改版,对齐 OcgoDockEntry pill)\n * 胶囊 999px 全圆 → 点击 → 自绘 popover(340px 右上角卡片,外点/Escape 关闭)\n * popover 内:分组(groupTitle 标题 + rowCard 行卡)——看齐官方 settings 设计语言\n * 遵循 web-styling.md:颜色只用 --dsw-alias-* 语义 token(明暗自适应)+ --sp-safe-green 统一绿家族;\n * 前缀 sp- 防冲突。 */\n\n/* ── 统一绿色变量家族(一处改全改;emerald 500~600 区间保证深色对比度) ── */\n\n.sp-root {\n --sp-safe-green: #0ba875; /* emerald-550:SAFE ON 主色 */\n --sp-safe-green-deep: #059669; /* emerald-600:渐变深端 */\n}\n\n/* ── 头部状态胶囊(可点击) ── */\n\n.sp-card {\n display: inline-flex;\n align-items: center;\n gap: 6px;\n padding: 4px 9px; /* 无固定 height:由内容撑高(胶囊) */\n border: 1px solid var(--dsw-alias-border-l1);\n border-radius: 999px;\n background: var(--dsw-alias-bg-layer-2);\n color: inherit;\n font-size: 12px;\n line-height: 1;\n cursor: pointer;\n transition: background var(--ds-transition-duration-fast, 0.1s) var(--ds-ease-in-out, ease),\n border-color var(--ds-transition-duration-fast, 0.1s) var(--ds-ease-in-out, ease);\n}\n\n.sp-card:hover {\n background: var(--dsw-alias-interactive-bg-hover);\n border-color: var(--dsw-alias-border-l2);\n}\n\n.sp-card:focus-visible {\n outline: 2px solid var(--dsw-alias-button-ghost-active-border);\n outline-offset: 1px;\n}\n\n.sp-card:disabled {\n opacity: 0.6;\n cursor: default;\n}\n\n/* 绿点 = Serenity 在线(恒亮绿,不随 SAFE 变);离线/未激活 → 灰 */\n.sp-dot {\n flex: none;\n width: 7px;\n height: 7px;\n border-radius: 50%;\n background: var(--dsw-alias-state-success-primary);\n}\n\n.sp-dotOff {\n background: var(--dsw-alias-label-dimmed);\n}\n\n.sp-cardInactive {\n opacity: 0.85;\n}\n\n.sp-cardInactive .sp-brand {\n color: var(--dsw-alias-label-secondary);\n font-weight: 500;\n}\n\n.sp-brand {\n color: var(--dsw-alias-label-primary);\n font-weight: 500;\n}\n\n/* 版本号:monospace + translateY(1px) 下沉对齐(与文字基线齐平) */\n.sp-ver {\n color: var(--dsw-alias-label-secondary);\n font-size: 11px;\n font-family: var(--ds-font-family-code, monospace);\n transform: translateY(1px);\n}\n\n/* 1px 深灰分隔线(两侧紧凑) */\n.sp-sep {\n flex: none;\n width: 1px;\n height: 12px;\n margin: 0 2px;\n background: var(--dsw-alias-label-tertiary);\n}\n\n.sp-shield {\n display: inline-flex;\n width: 14px;\n height: 14px;\n flex: none;\n}\n\n.sp-shield svg {\n width: 14px;\n height: 14px;\n}\n\n.sp-statusWord {\n font-size: 11px;\n font-weight: 600;\n letter-spacing: 0;\n white-space: nowrap;\n}\n\n/* SAFE OFF(未保护):灰——低姿态提醒,非错误(用户自己的开关选择) */\n.sp-cardUnprotected .sp-shield {\n color: var(--dsw-alias-label-secondary);\n}\n\n.sp-cardUnprotected .sp-statusWord {\n color: var(--dsw-alias-label-secondary);\n}\n\n/* SAFE ON(保护中):emerald 绿——安心(盾牌实色 + SAFE 文字渐变质感) */\n.sp-cardProtected .sp-shield {\n color: var(--sp-safe-green);\n}\n\n.sp-cardProtected .sp-statusWord {\n color: var(--sp-safe-green);\n background: linear-gradient(135deg, var(--sp-safe-green) 0%, var(--sp-safe-green-deep) 100%);\n -webkit-background-clip: text;\n background-clip: text;\n -webkit-text-fill-color: transparent;\n}\n\n/* ── Mac 风格滑块(v1.24.10:轨道 24×13 / thumb 11px 灰白 #f2f4f6 无图标 / cubic-bezier 平滑) ── */\n\n.sp-switch {\n display: inline-block;\n width: 24px;\n height: 13px;\n border-radius: 999px;\n position: relative;\n flex: none;\n cursor: pointer;\n transition: background 0.25s cubic-bezier(0.4, 0, 0.2, 1);\n}\n\n.sp-switchOff {\n background: var(--dsw-alias-border-l2);\n}\n\n.sp-switchOn {\n background: var(--sp-safe-green);\n}\n\n.sp-switchThumb {\n position: absolute;\n top: 1px;\n width: 11px;\n height: 11px;\n border-radius: 50%;\n background: #f2f4f6; /* Mac 灰白 thumb(明暗通用) */\n box-shadow: 0 1px 2px rgba(0, 0, 0, 0.3);\n transition: left 0.25s cubic-bezier(0.4, 0, 0.2, 1);\n}\n\n.sp-switchOff .sp-switchThumb {\n left: 1px;\n}\n\n.sp-switchOn .sp-switchThumb {\n left: 12px; /* 24 - 11 - 1 */\n}\n\n/* CSS 特异性坑(S013 指南):.sp-switch:hover (0,2,0) 会覆盖 .sp-switchOn (0,1,0)\n * → ON 态 hover 绿底消失。必须同特异性且后定义补回。 */\n.sp-switch:hover {\n filter: brightness(1.08);\n}\n\n.sp-switchOn:hover {\n background: var(--sp-safe-green);\n}\n\n.sp-switchBusy {\n opacity: 0.6;\n cursor: default;\n pointer-events: none;\n}\n\n.sp-chev {\n color: var(--dsw-alias-label-dimmed);\n flex: none;\n}\n\n/* ── 自绘 popover(340px 右上角小卡片,替代官方 Modal) ── */\n\n.sp-root {\n position: relative;\n display: inline-flex;\n}\n\n/* ── 自绘 popover(卡片,替代官方 Modal)\n v1.36.1(所有者:「卡片做成双倍宽,左侧是信息,右侧是动画」):340 → **680px**(双倍)。\n v1.39.1(所有者:「下拉 dialog / 弹窗内容过宽后,会被左侧元素遮挡」):\n 🔴 根因 = **祖先 `overflow:hidden` 裁切**,不是 z-index 也不是宽度不够。\n 真机取证(CDP hit-test,1280/1600/1920 三档一致):\n · 胶囊右端 x=954.2、卡片 680 宽 ⇒ 左边界 274.2\n · 而会话中列 `pI_x6G_centerCol` / `wSkVaW_root` 都 `overflow:hidden` 且左边界 = **280**\n ⇒ 左边缘 **5.8px** 被裁掉(左边框线与圆角消失)。\n 加宽前(340px)左边界 614.2 远在 280 右侧 ⇒ **这正是 v1.36.1 加宽引入的回归**。\n 修法:**改为 `position: fixed`** —— fixed 子元素**不受祖先 overflow 裁切**;\n 坐标由 SafeModePanel 用 `getBoundingClientRect()` 算出并夹取进视口(见 .tsx 的 useLayoutEffect)。\n (本仓 client 侧**无 `react-dom` 依赖** ⇒ `createPortal` 不可用;fixed 是等效且更轻的出路。\n 已在真机验证祖先链**无** transform/filter/contain/will-change ⇒ fixed 不会被降级为相对某祖先。)\n 宽度仍走 `min(680px, 100vw-24px)`(窄视口兜底),窄屏退回单栏见文末 @media。 */\n.sp-pop {\n position: fixed; /* 不受祖先 overflow:hidden 裁切;left/top 由 JS 计算 */\n top: 0; /* ← 声明默认值,JS 会覆写(未落位时组件给 -9999 屏外值,不会闪到右下角) */\n left: 0;\n width: min(680px, calc(100vw - 24px));\n z-index: 2000;\n box-sizing: border-box;\n padding: 14px;\n border: 1px solid var(--dsw-alias-border-l1);\n border-radius: 14px;\n background: var(--dsw-alias-bg-overlay);\n box-shadow: 0 12px 40px rgba(0, 0, 0, 0.5);\n}\n\n/* ── 航行动画栏:宁静号心智模型(ACC 层资产 /serenity/voyage,S142 §12.44 → v1.36.1 改右栏)\n v1.36.1 改版(所有者:「卡片做成双倍宽,左侧是信息,右侧是动画」):\n 动画从**背景层**改为**右栏**。这一改动解开了 v1.36.0 的取舍死结——\n 旧布局里动画垫在正文底下,必须靠 0.75 的卡片底色把它压住才读得清字;\n 分段之后两者不再争同一片像素 ⇒ 动画可以亮、正文可以干净,不必再互相妥协。\n ⚠️ 动画本身仍是「卡片模式」(词元压到 22%、铭牌层关闭),本栏只负责**给位置**,不改作品。 */\n.sp-popVoyage {\n overflow: hidden; /* 裁掉 iframe 在 14px 圆角外的溢出 */\n /* 分段后不再需要 0.75 的重压暗:压到 0.9 只压整体观感,不与正文争对比度。\n 若所有者觉得动画太亮/太暗,这仍是主旋钮(次旋钮 = iframe 的 blur)。 */\n background: rgba(6, 11, 14, 0.9);\n display: flex;\n flex-direction: row;\n /* 两栏都从**同一行高**分配(row 轴 cross = 高度):左栏按内容、右栏吃满行高。\n 行高 = 左栏内容高度,且被 max-height 封顶 ⇒ 信息长时内部滚动,动画不把行撑破。 */\n align-items: stretch;\n gap: 12px;\n padding: 12px;\n max-height: calc(100vh - 120px);\n}\n/* 左栏:信息(正文)——固定 340px,与旧卡片同宽,保证原有排印不变 */\n.sp-popVoyage > .sp-popBody {\n position: relative;\n z-index: 1;\n order: 1;\n flex: none;\n width: 340px;\n min-width: 0;\n}\n/* 右栏:动画——吃掉剩余宽度,并吃满左栏高度 */\n.sp-voyage {\n order: 2;\n flex: 1 1 auto;\n min-width: 0;\n position: relative;\n pointer-events: none; /* 纯展示:不挡点击、不抢焦点 */\n overflow: hidden;\n border-radius: 10px;\n min-height: 260px; /* 动画的下限:信息很少时也不塌成一条 */\n}\n.sp-voyage iframe {\n display: block;\n width: 100%;\n height: 100%;\n border: 0;\n /* ⚠️ 用 iframe 自身的 filter 而**不是** backdrop-filter:iframe 内容不参与本文档的\n backdrop(跨文档不采样)⇒ backdrop-filter 对它无效,只有 filter 才是可靠的杠杆。\n v1.36.1:动画移入独立右栏后不再压在文字后面 ⇒ 磨砂可以收得很轻(1.2 → 0.6px),\n 既保留柔化,又让飞船细节(舷窗/引擎环)比旧版清楚。 */\n filter: blur(0.6px);\n}\n\n/* 窄屏(放不下两栏)⇒ 退回单栏:信息在上、动画在下(DOM 顺序即如此,无需改结构) */\n@media (max-width: 860px) {\n .sp-pop {\n /* 两栏放不下时,卡片回到\"不超过视口\"的旧行为 */\n width: min(420px, calc(100vw - 24px));\n }\n .sp-popVoyage {\n flex-direction: column;\n align-items: stretch;\n }\n .sp-popVoyage > .sp-popBody {\n width: auto; /* 单栏下不再固定 340px,跟随卡片宽度 */\n flex: none; /* 按内容高(仍受自身 max-height 约束) */\n }\n .sp-voyage {\n flex: none;\n height: 200px; /* 单栏时给动画明确高度,避免被 flex 压扁 */\n min-height: 0;\n }\n}\n\n.sp-popBody {\n display: flex;\n flex-direction: column;\n gap: 14px;\n max-height: calc(100vh - 140px);\n overflow-y: auto;\n}\n\n/* ── 分组(官方 settings 语言:groupTitle + rows) ── */\n\n.sp-group {\n display: flex;\n flex-direction: column;\n gap: 8px;\n}\n\n.sp-groupHead {\n display: flex;\n align-items: center;\n justify-content: space-between;\n gap: 8px;\n}\n\n.sp-groupTitle {\n margin: 0;\n font-size: 12px;\n line-height: 18px;\n font-weight: 600;\n letter-spacing: 0.02em;\n text-transform: uppercase;\n color: var(--dsw-alias-label-secondary);\n}\n\n.sp-rows {\n display: flex;\n flex-direction: column;\n gap: 6px;\n}\n\n/* 行卡(rowCard:border + radius + padding;值与 label 分离、长内容可换行) */\n.sp-row {\n display: flex;\n align-items: baseline;\n gap: 12px;\n min-width: 0;\n padding: 8px 12px;\n border: 1px solid var(--dsw-alias-border-l1);\n border-radius: 10px;\n background: var(--dsw-alias-bg-layer-2);\n}\n\n.sp-label {\n /* 🔴 曾写死 `width: 76px` ⇒ 「CheapWorker 模型」这类长标签会**溢出到数值上**\n (nowrap + 定宽 ⇒ 文字直接压过去,不换行也不报错)。\n 改 `min-width`:短标签仍在同一列对齐,长标签自己撑开,绝不压数值。 */\n flex: none;\n min-width: 76px;\n font-size: 12px;\n font-weight: 500;\n color: var(--dsw-alias-label-secondary);\n white-space: nowrap;\n}\n\n.sp-value {\n flex: 1;\n min-width: 0;\n font-size: 12px;\n line-height: 18px;\n color: var(--dsw-alias-label-primary);\n font-family: var(--ds-font-family-code, monospace);\n word-break: break-all;\n overflow-wrap: anywhere;\n}\n\n/* 安全模式动作区 */\n.sp-actions {\n display: flex;\n align-items: center;\n gap: 12px;\n padding: 8px 12px;\n border: 1px solid var(--dsw-alias-border-l1);\n border-radius: 10px;\n background: var(--dsw-alias-bg-layer-2);\n}\n\n.sp-toggle {\n display: inline-flex;\n align-items: center;\n gap: 6px;\n height: 24px;\n padding: 0 10px;\n border: 1px solid var(--dsw-alias-border-l1);\n border-radius: 6px;\n font-size: 12px;\n cursor: pointer;\n transition: background var(--ds-transition-duration-fast, 0.1s) var(--ds-ease-in-out, ease);\n}\n\n.sp-toggleLg {\n height: 30px;\n padding: 0 16px;\n font-size: 13px;\n}\n\n.sp-toggleOn {\n background: color-mix(in srgb, var(--dsw-alias-state-error-primary) 14%, transparent);\n color: var(--dsw-alias-state-error-primary);\n border-color: color-mix(in srgb, var(--dsw-alias-state-error-primary) 45%, transparent);\n}\n\n.sp-toggleOff {\n background: var(--dsw-alias-interactive-bg-hover);\n color: var(--dsw-alias-label-secondary);\n}\n\n.sp-toggleIcon {\n flex: none;\n}\n\n.sp-toggleDesc {\n flex: 1;\n font-size: 12px;\n line-height: 18px;\n color: var(--dsw-alias-label-tertiary);\n}\n\n/* 🔴 2026-10-14:`.sp-cheapWorkers*` / `.sp-cheapWorker*` 样式区块已随 background 模式删除\n —— 那是「运行中 cheap-worker」列表(进度文件驱动)的样式,而进度文件不再有生产者。 */\n\n/* 底部提示(配置入口引导) */\n.sp-hint {\n margin: 0;\n font-size: 12px;\n line-height: 18px;\n color: var(--dsw-alias-label-tertiary);\n word-break: break-word;\n overflow-wrap: anywhere;\n padding: 8px 12px;\n border: 1px dashed var(--dsw-alias-border-l2);\n border-radius: 10px;\n}\n";
|
|
12
12
|
if (typeof document !== "undefined" && document.querySelector("style[data-sp-css=\"SafeModePanel\"]") === null) {
|
|
13
13
|
const tag = document.createElement("style");
|
|
14
14
|
tag.setAttribute("data-sp-css", "SafeModePanel");
|
|
@@ -275,16 +275,16 @@ window.__ModuleLoader__.load({
|
|
|
275
275
|
]
|
|
276
276
|
}), /* @__PURE__ */ (0, react_jsx_runtime.jsx)("span", {
|
|
277
277
|
className: cx("sp-toggleDesc"),
|
|
278
|
-
children: status.safeModeOn ? "
|
|
278
|
+
children: status.safeModeOn ? "写工具已隐藏,可无人值守运行" : "写工具可用(点击开启)"
|
|
279
279
|
})]
|
|
280
280
|
})]
|
|
281
281
|
}),
|
|
282
282
|
/* @__PURE__ */ (0, react_jsx_runtime.jsxs)("p", {
|
|
283
283
|
className: cx("sp-hint"),
|
|
284
284
|
children: [
|
|
285
|
-
"💡
|
|
285
|
+
"💡 开关 / 阈值 / 账号 / 白名单在 ",
|
|
286
286
|
/* @__PURE__ */ (0, react_jsx_runtime.jsx)("strong", { children: "设置 → Serenity" }),
|
|
287
|
-
"
|
|
287
|
+
" 里配。"
|
|
288
288
|
]
|
|
289
289
|
})
|
|
290
290
|
] }) : /* @__PURE__ */ (0, react_jsx_runtime.jsxs)("div", {
|
|
@@ -3225,7 +3225,7 @@ window.__ModuleLoader__.load({
|
|
|
3225
3225
|
}
|
|
3226
3226
|
//#endregion
|
|
3227
3227
|
//#region \0sp-css:src/client/AccountsEditor
|
|
3228
|
-
const css$4 = "/* AccountsEditor — DSH 设置面板「外部访问」区块(v1.22)\n * 与 SettingsSection ss-* 同设计语言:--dsw-alias-* 语义 token,明暗自适应。 */\n\n.ae-root {\n display: flex;\n flex-direction: column;\n gap: 10px;\n padding: 12px 14px;\n border: 1px solid var(--dsw-alias-border-l2);\n border-radius: 12px;\n font-size: 13px;\n}\n\n/* ── v1.27.5 紧凑化:折叠块(details/summary)── */\n.ae-collapse {\n border: 1px solid var(--dsw-alias-border-l1);\n border-radius: 8px;\n overflow: hidden;\n}\n\n.ae-collapseHead {\n display: flex;\n align-items: baseline;\n gap: 8px;\n padding: 8px 12px;\n cursor: pointer;\n list-style: none;\n user-select: none;\n}\n\n.ae-collapseHead::-webkit-details-marker {\n display: none;\n}\n\n.ae-collapseHead::before {\n content: '▸';\n flex: none;\n font-size: 11px;\n color: var(--dsw-alias-label-dimmed);\n transition: transform 0.15s ease;\n}\n\n.ae-collapse[open] > .ae-collapseHead::before {\n transform: rotate(90deg);\n}\n\n.ae-collapseHead:hover {\n background: var(--dsw-alias-interactive-bg-hover, rgba(128, 128, 128, 0.06));\n}\n\n.ae-collapseDesc {\n font-size: 12px;\n color: var(--dsw-alias-label-tertiary);\n white-space: nowrap;\n overflow: hidden;\n text-overflow: ellipsis;\n min-width: 0;\n}\n\n.ae-collapseBody {\n display: flex;\n flex-direction: column;\n gap: 8px;\n padding: 8px 12px 10px;\n border-top: 1px solid var(--dsw-alias-border-l1);\n}\n\n.ae-warn {\n margin: 0;\n font-size: 12px;\n line-height: 18px;\n color: var(--dsw-alias-state-warn-label);\n word-break: break-word;\n}\n\n.ae-block {\n display: flex;\n flex-direction: column;\n gap: 8px;\n}\n\n.ae-title {\n margin: 0;\n font-size: 12px;\n line-height: 18px;\n font-weight: 600;\n letter-spacing: 0.02em;\n text-transform: uppercase;\n color: var(--dsw-alias-label-secondary);\n}\n\n.ae-desc {\n margin: 0;\n font-size: 12px;\n line-height: 18px;\n color: var(--dsw-alias-label-tertiary);\n word-break: break-word;\n overflow-wrap: anywhere;\n}\n\n.ae-note {\n margin: 0;\n font-size: 12px;\n line-height: 18px;\n color: var(--dsw-alias-label-tertiary);\n}\n\n/* ── 监听设置 / 白名单输入行 ── */\n\n.ae-row {\n display: flex;\n align-items: center;\n gap: 8px;\n}\n\n.ae-label {\n flex: none;\n font-size: 12px;\n font-weight: 500;\n color: var(--dsw-alias-label-secondary);\n white-space: nowrap;\n}\n\n.ae-input {\n flex: 1;\n min-width: 0;\n padding: 6px 10px;\n border: 1px solid var(--dsw-alias-border-l2);\n border-radius: 8px;\n background: var(--dsw-alias-bg-layer-2);\n color: var(--dsw-alias-label-primary);\n font-size: 13px;\n outline: none;\n}\n\n.ae-input:focus {\n border-color: var(--dsw-alias-button-ghost-active-border);\n}\n\n.ae-input::placeholder {\n color: var(--dsw-alias-label-dimmed);\n}\n\n.ae-input.ae-port {\n flex: none;\n width: 76px;\n}\n\n/* ── 账号列表 ── */\n\n.ae-list {\n display: flex;\n flex-direction: column;\n gap: 4px;\n}\n\n.ae-head {\n display: flex;\n gap: 8px;\n font-size: 11px;\n font-weight: 500;\n color: var(--dsw-alias-label-dimmed);\n padding: 0 2px;\n text-transform: uppercase;\n letter-spacing: 0.02em;\n}\n\n.ae-item {\n display: flex;\n gap: 8px;\n align-items: center;\n padding: 6px 2px;\n}\n\n.ae-colUser { flex: 1.2; }\n.ae-colPass { flex: 1.6; }\n.ae-colTotp { flex: 2.2; min-width: 0; }\n.ae-colOp { flex: none; width: 48px; }\n\n/* ── v1.22.4 TOTP 第二因素 ── */\n\n.ae-totpBtn {\n flex: none;\n padding: 4px 10px;\n border: 1px solid var(--dsw-alias-border-l2);\n border-radius: 6px;\n background: transparent;\n color: var(--dsw-alias-label-secondary);\n font-size: 12px;\n cursor: pointer;\n white-space: nowrap;\n}\n\n.ae-totpBtn:hover {\n background: var(--dsw-alias-interactive-bg-hover);\n}\n\n.ae-totpPending {\n display: flex;\n flex-wrap: wrap;\n gap: 6px;\n align-items: center;\n min-width: 0;\n}\n\n/* v1.24.6:TOTP 绑定二维码(扫码即录入;scalable SVG,白底保证扫码识别) */\n.ae-totpQr {\n flex-basis: 100%;\n display: inline-flex;\n justify-content: center;\n padding: 8px;\n background: #fff;\n border: 1px solid var(--dsw-alias-border-l1);\n border-radius: 8px;\n}\n\n.ae-totpQr svg {\n width: 132px;\n height: 132px;\n display: block;\n}\n\n.ae-totpSecret {\n font-family: var(--ds-font-family-code);\n font-size: 11px;\n background: var(--dsw-alias-bg-layer-2);\n border: 1px solid var(--dsw-alias-border-l1);\n border-radius: 4px;\n padding: 2px 6px;\n color: var(--dsw-alias-label-secondary);\n word-break: break-all;\n}\n\n.ae-totpUri {\n font-size: 11px;\n color: var(--dsw-alias-button-info-fill);\n text-decoration: none;\n}\n\n.ae-totpUri:hover {\n text-decoration: underline;\n}\n\n/* v1.24.7:绑定提示(去确认码后——扫码或手动录入,保存即绑定) */\n.ae-totpHint {\n flex-basis: 100%;\n font-size: 11px;\n color: var(--dsw-alias-label-tertiary);\n}\n\n.ae-totpBadge {\n font-size: 12px;\n color: var(--dsw-alias-state-warn-label);\n}\n\n.ae-totpClear {\n display: flex;\n gap: 6px;\n align-items: center;\n}\n\n.ae-check {\n display: flex;\n gap: 8px;\n align-items: center;\n font-size: 12px;\n color: var(--dsw-alias-label-secondary);\n margin-top: 10px;\n cursor: pointer;\n}\n\n.ae-check input {\n accent-color: var(--dsw-alias-button-info-fill);\n}\n\n.ae-del {\n flex: none;\n padding: 4px 10px;\n border: 1px solid var(--dsw-alias-border-l1);\n border-radius: 6px;\n background: transparent;\n color: var(--dsw-alias-state-error-primary);\n font-size: 12px;\n cursor: pointer;\n}\n\n.ae-del:hover {\n background: var(--dsw-alias-interactive-bg-hover-danger);\n}\n\n.ae-add {\n align-self: flex-start;\n padding: 5px 12px;\n border: 1px dashed var(--dsw-alias-border-l2);\n border-radius: 8px;\n background: transparent;\n color: var(--dsw-alias-label-secondary);\n font-size: 12px;\n cursor: pointer;\n}\n\n.ae-add:hover {\n background: var(--dsw-alias-interactive-bg-hover);\n}\n\n.ae-wsSelect {\n margin-top: 8px;\n max-width: 100%;\n cursor: pointer;\n}\n\n/* ── 工作区白名单 chips ── */\n\n.ae-wsList {\n display: flex;\n flex-wrap: wrap;\n gap: 6px;\n}\n\n.ae-wsChip {\n display: inline-flex;\n align-items: center;\n gap: 6px;\n padding: 3px 8px;\n border: 1px solid var(--dsw-alias-border-l2);\n border-radius: 8px;\n background: var(--dsw-alias-interactive-bg-active, rgba(128, 128, 128, 0.14));\n}\n\n.ae-wsPath {\n font-size: 12px;\n color: var(--dsw-alias-label-primary);\n font-family: var(--ds-font-family-code, monospace);\n word-break: break-all;\n}\n\n.ae-wsDel {\n flex: none;\n width: 18px;\n height: 18px;\n border: none;\n border-radius: 50%;\n background: transparent;\n color: var(--dsw-alias-label-dimmed);\n font-size: 13px;\n line-height: 1;\n cursor: pointer;\n}\n\n.ae-wsDel:hover {\n background: var(--dsw-alias-interactive-bg-hover-danger);\n color: var(--dsw-alias-state-error-primary);\n}\n\n/* ── 错误 / 操作区 ── */\n\n.ae-error {\n margin: 0;\n font-size: 12px;\n line-height: 18px;\n color: var(--dsw-alias-state-error-primary);\n word-break: break-word;\n}\n\n.ae-actions {\n display: flex;\n justify-content: flex-end;\n padding-top: 4px;\n border-top: 1px solid var(--dsw-alias-border-l1);\n}\n\n.ae-save {\n padding: 7px 24px;\n border: 0;\n border-radius: 8px;\n background: var(--dsw-alias-button-primary-fill);\n color: var(--dsw-alias-label-primary-foreground);\n font-size: 13px;\n font-weight: 500;\n cursor: pointer;\n}\n\n.ae-save:hover:not(:disabled) {\n filter: brightness(1.08);\n}\n\n.ae-save:disabled {\n opacity: 0.6;\n cursor: default;\n}\n\n/*
|
|
3228
|
+
const css$4 = "/* AccountsEditor — DSH 设置面板「外部访问」区块(v1.22)\n * 与 SettingsSection ss-* 同设计语言:--dsw-alias-* 语义 token,明暗自适应。 */\n\n.ae-root {\n display: flex;\n flex-direction: column;\n gap: 10px;\n padding: 12px 14px;\n border: 1px solid var(--dsw-alias-border-l2);\n border-radius: 12px;\n font-size: 13px;\n}\n\n/* ── v1.27.5 紧凑化:折叠块(details/summary)── */\n.ae-collapse {\n border: 1px solid var(--dsw-alias-border-l1);\n border-radius: 8px;\n overflow: hidden;\n}\n\n.ae-collapseHead {\n display: flex;\n align-items: baseline;\n gap: 8px;\n padding: 8px 12px;\n cursor: pointer;\n list-style: none;\n user-select: none;\n}\n\n.ae-collapseHead::-webkit-details-marker {\n display: none;\n}\n\n.ae-collapseHead::before {\n content: '▸';\n flex: none;\n font-size: 11px;\n color: var(--dsw-alias-label-dimmed);\n transition: transform 0.15s ease;\n}\n\n.ae-collapse[open] > .ae-collapseHead::before {\n transform: rotate(90deg);\n}\n\n.ae-collapseHead:hover {\n background: var(--dsw-alias-interactive-bg-hover, rgba(128, 128, 128, 0.06));\n}\n\n.ae-collapseDesc {\n font-size: 12px;\n color: var(--dsw-alias-label-tertiary);\n white-space: nowrap;\n overflow: hidden;\n text-overflow: ellipsis;\n min-width: 0;\n}\n\n.ae-collapseBody {\n display: flex;\n flex-direction: column;\n gap: 8px;\n padding: 8px 12px 10px;\n border-top: 1px solid var(--dsw-alias-border-l1);\n}\n\n.ae-warn {\n margin: 0;\n font-size: 12px;\n line-height: 18px;\n color: var(--dsw-alias-state-warn-label);\n word-break: break-word;\n}\n\n.ae-block {\n display: flex;\n flex-direction: column;\n gap: 8px;\n}\n\n.ae-title {\n margin: 0;\n font-size: 12px;\n line-height: 18px;\n font-weight: 600;\n letter-spacing: 0.02em;\n text-transform: uppercase;\n color: var(--dsw-alias-label-secondary);\n}\n\n.ae-desc {\n margin: 0;\n font-size: 12px;\n line-height: 18px;\n color: var(--dsw-alias-label-tertiary);\n word-break: break-word;\n overflow-wrap: anywhere;\n}\n\n.ae-note {\n margin: 0;\n font-size: 12px;\n line-height: 18px;\n color: var(--dsw-alias-label-tertiary);\n}\n\n/* ── 监听设置 / 白名单输入行 ── */\n\n.ae-row {\n display: flex;\n align-items: center;\n gap: 8px;\n}\n\n.ae-label {\n flex: none;\n font-size: 12px;\n font-weight: 500;\n color: var(--dsw-alias-label-secondary);\n white-space: nowrap;\n}\n\n.ae-input {\n flex: 1;\n min-width: 0;\n padding: 6px 10px;\n border: 1px solid var(--dsw-alias-border-l2);\n border-radius: 8px;\n background: var(--dsw-alias-bg-layer-2);\n color: var(--dsw-alias-label-primary);\n font-size: 13px;\n outline: none;\n}\n\n.ae-input:focus {\n border-color: var(--dsw-alias-button-ghost-active-border);\n}\n\n.ae-input::placeholder {\n color: var(--dsw-alias-label-dimmed);\n}\n\n.ae-input.ae-port {\n flex: none;\n width: 76px;\n}\n\n/* ── 账号列表 ── */\n\n.ae-list {\n display: flex;\n flex-direction: column;\n gap: 4px;\n}\n\n.ae-head {\n display: flex;\n gap: 8px;\n font-size: 11px;\n font-weight: 500;\n color: var(--dsw-alias-label-dimmed);\n padding: 0 2px;\n text-transform: uppercase;\n letter-spacing: 0.02em;\n}\n\n.ae-item {\n display: flex;\n gap: 8px;\n align-items: center;\n padding: 6px 2px;\n}\n\n.ae-colUser { flex: 1.2; }\n.ae-colPass { flex: 1.6; }\n.ae-colTotp { flex: 2.2; min-width: 0; }\n.ae-colOp { flex: none; width: 48px; }\n\n/* ── v1.22.4 TOTP 第二因素 ── */\n\n.ae-totpBtn {\n flex: none;\n padding: 4px 10px;\n border: 1px solid var(--dsw-alias-border-l2);\n border-radius: 6px;\n background: transparent;\n color: var(--dsw-alias-label-secondary);\n font-size: 12px;\n cursor: pointer;\n white-space: nowrap;\n}\n\n.ae-totpBtn:hover {\n background: var(--dsw-alias-interactive-bg-hover);\n}\n\n.ae-totpPending {\n display: flex;\n flex-wrap: wrap;\n gap: 6px;\n align-items: center;\n min-width: 0;\n}\n\n/* v1.24.6:TOTP 绑定二维码(扫码即录入;scalable SVG,白底保证扫码识别) */\n.ae-totpQr {\n flex-basis: 100%;\n display: inline-flex;\n justify-content: center;\n padding: 8px;\n background: #fff;\n border: 1px solid var(--dsw-alias-border-l1);\n border-radius: 8px;\n}\n\n.ae-totpQr svg {\n width: 132px;\n height: 132px;\n display: block;\n}\n\n.ae-totpSecret {\n font-family: var(--ds-font-family-code);\n font-size: 11px;\n background: var(--dsw-alias-bg-layer-2);\n border: 1px solid var(--dsw-alias-border-l1);\n border-radius: 4px;\n padding: 2px 6px;\n color: var(--dsw-alias-label-secondary);\n word-break: break-all;\n}\n\n.ae-totpUri {\n font-size: 11px;\n color: var(--dsw-alias-button-info-fill);\n text-decoration: none;\n}\n\n.ae-totpUri:hover {\n text-decoration: underline;\n}\n\n/* v1.24.7:绑定提示(去确认码后——扫码或手动录入,保存即绑定) */\n.ae-totpHint {\n flex-basis: 100%;\n font-size: 11px;\n color: var(--dsw-alias-label-tertiary);\n}\n\n.ae-totpBadge {\n font-size: 12px;\n color: var(--dsw-alias-state-warn-label);\n}\n\n.ae-totpClear {\n display: flex;\n gap: 6px;\n align-items: center;\n}\n\n.ae-check {\n display: flex;\n gap: 8px;\n align-items: center;\n font-size: 12px;\n color: var(--dsw-alias-label-secondary);\n margin-top: 10px;\n cursor: pointer;\n}\n\n.ae-check input {\n accent-color: var(--dsw-alias-button-info-fill);\n}\n\n.ae-del {\n flex: none;\n padding: 4px 10px;\n border: 1px solid var(--dsw-alias-border-l1);\n border-radius: 6px;\n background: transparent;\n color: var(--dsw-alias-state-error-primary);\n font-size: 12px;\n cursor: pointer;\n}\n\n.ae-del:hover {\n background: var(--dsw-alias-interactive-bg-hover-danger);\n}\n\n.ae-add {\n align-self: flex-start;\n padding: 5px 12px;\n border: 1px dashed var(--dsw-alias-border-l2);\n border-radius: 8px;\n background: transparent;\n color: var(--dsw-alias-label-secondary);\n font-size: 12px;\n cursor: pointer;\n}\n\n.ae-add:hover {\n background: var(--dsw-alias-interactive-bg-hover);\n}\n\n.ae-wsSelect {\n margin-top: 8px;\n max-width: 100%;\n cursor: pointer;\n}\n\n/* ── 工作区白名单 chips ── */\n\n.ae-wsList {\n display: flex;\n flex-wrap: wrap;\n gap: 6px;\n}\n\n.ae-wsChip {\n display: inline-flex;\n align-items: center;\n gap: 6px;\n padding: 3px 8px;\n border: 1px solid var(--dsw-alias-border-l2);\n border-radius: 8px;\n background: var(--dsw-alias-interactive-bg-active, rgba(128, 128, 128, 0.14));\n}\n\n.ae-wsPath {\n font-size: 12px;\n color: var(--dsw-alias-label-primary);\n font-family: var(--ds-font-family-code, monospace);\n word-break: break-all;\n}\n\n.ae-wsDel {\n flex: none;\n width: 18px;\n height: 18px;\n border: none;\n border-radius: 50%;\n background: transparent;\n color: var(--dsw-alias-label-dimmed);\n font-size: 13px;\n line-height: 1;\n cursor: pointer;\n}\n\n.ae-wsDel:hover {\n background: var(--dsw-alias-interactive-bg-hover-danger);\n color: var(--dsw-alias-state-error-primary);\n}\n\n/* ── 错误 / 操作区 ── */\n\n.ae-error {\n margin: 0;\n font-size: 12px;\n line-height: 18px;\n color: var(--dsw-alias-state-error-primary);\n word-break: break-word;\n}\n\n.ae-actions {\n display: flex;\n justify-content: flex-end;\n padding-top: 4px;\n border-top: 1px solid var(--dsw-alias-border-l1);\n}\n\n.ae-save {\n padding: 7px 24px;\n border: 0;\n border-radius: 8px;\n background: var(--dsw-alias-button-primary-fill);\n color: var(--dsw-alias-label-primary-foreground);\n font-size: 13px;\n font-weight: 500;\n cursor: pointer;\n}\n\n.ae-save:hover:not(:disabled) {\n filter: brightness(1.08);\n}\n\n.ae-save:disabled {\n opacity: 0.6;\n cursor: default;\n}\n\n/* 🔴 2026-10-18:`.ae-chips` / `.ae-chip*` / `.ae-saved` / `.ae-err` / `.ae-key` /\n `.ae-copy*` / `.ae-rotate*` / `.ae-rows` / `.ae-labelDim` 已整段删除 —— 它们只服务于\n `PublicAskEditor`(`src/client/PublicAskEditor.tsx`),而该组件已在 v1.57.1\n 随自造问答面整组退役。保留无人引用的选择器 = 熵,故按「无人引用即删」处理。 */\n";
|
|
3229
3229
|
if (typeof document !== "undefined" && document.querySelector("style[data-sp-css=\"AccountsEditor\"]") === null) {
|
|
3230
3230
|
const tag = document.createElement("style");
|
|
3231
3231
|
tag.setAttribute("data-sp-css", "AccountsEditor");
|
|
@@ -3450,7 +3450,7 @@ window.__ModuleLoader__.load({
|
|
|
3450
3450
|
type: "checkbox",
|
|
3451
3451
|
checked: totpEnabled,
|
|
3452
3452
|
onChange: (e) => setTotpEnabled(e.target.checked)
|
|
3453
|
-
}), /* @__PURE__ */ (0, react_jsx_runtime.jsx)("span", { children: "启用 Authenticator
|
|
3453
|
+
}), /* @__PURE__ */ (0, react_jsx_runtime.jsx)("span", { children: "启用 Authenticator 登录(开启后,已绑定验证器的账号可用密码 或 6 位验证码任一登录;关闭则完全禁用 TOTP,仅密码)" })]
|
|
3454
3454
|
})]
|
|
3455
3455
|
})]
|
|
3456
3456
|
}),
|
|
@@ -3802,11 +3802,15 @@ window.__ModuleLoader__.load({
|
|
|
3802
3802
|
children: [
|
|
3803
3803
|
/* @__PURE__ */ (0, react_jsx_runtime.jsx)("div", {
|
|
3804
3804
|
className: "ss-detailIntro",
|
|
3805
|
-
children: "ACP 账户台账(每台客户端一条:一枚 token ↔ 一个角色)\n· 连接归属哪个 CCC 由
|
|
3805
|
+
children: "ACP 账户台账(每台客户端一条:一枚 token ↔ 一个角色)\n· 连接归属哪个 CCC 由 token 决定(服务端权威),不看客户端填什么\n· 加一台设备 = 这里加一条 ⇒ token 随即生成,保存后当场显示一次,抄进客户端即可\n· 客户端地址:ws://<本机IP>:3200 + Authorization: Bearer <token>(或用 ?token=<token>);working directory 可以只填目录名 —— ACC 会按 token 归属自动归到该 CCC 根\n· 「轮换」会让在用的那台立刻断线 ⇒ 只在怀疑泄露时按;「删除」连带删 token,不可逆"
|
|
3806
3806
|
}),
|
|
3807
3807
|
/* @__PURE__ */ (0, react_jsx_runtime.jsxs)("div", {
|
|
3808
3808
|
className: "ss-switchRow",
|
|
3809
|
-
children: [/* @__PURE__ */ (0, react_jsx_runtime.jsx)("span", {
|
|
3809
|
+
children: [/* @__PURE__ */ (0, react_jsx_runtime.jsx)("span", {
|
|
3810
|
+
className: "ss-fieldLabel",
|
|
3811
|
+
children: "目标 CCC"
|
|
3812
|
+
}), /* @__PURE__ */ (0, react_jsx_runtime.jsxs)("select", {
|
|
3813
|
+
className: "ss-select",
|
|
3810
3814
|
value: selectedRoot,
|
|
3811
3815
|
onChange: (e) => setSelectedRoot(e.target.value),
|
|
3812
3816
|
children: [cccs.length === 0 && /* @__PURE__ */ (0, react_jsx_runtime.jsx)("option", {
|
|
@@ -3819,63 +3823,70 @@ window.__ModuleLoader__.load({
|
|
|
3819
3823
|
})]
|
|
3820
3824
|
}),
|
|
3821
3825
|
loadError && /* @__PURE__ */ (0, react_jsx_runtime.jsx)("p", {
|
|
3822
|
-
className: "ss-
|
|
3826
|
+
className: "ss-error",
|
|
3823
3827
|
children: `读取失败:${loadError}`
|
|
3824
3828
|
}),
|
|
3825
3829
|
status && /* @__PURE__ */ (0, react_jsx_runtime.jsx)("p", {
|
|
3826
3830
|
className: "ss-detailIntro",
|
|
3827
3831
|
children: `通道:${status.channel}${status.channel === "acp" ? "" : "(未选 ACP ⇒ 账户不生效)"} / 面开关:${status.enabled ? "开" : "关"}\n可用账户:${status.accounts.filter((a) => a.usable).length} / ${status.accounts.length}
|
|
3828
|
-
|
|
3832
|
+
每个可用账户在客户端里只看到自己那一条对话(第一次发消息时建立,之后一直用它)。`
|
|
3829
3833
|
}),
|
|
3830
|
-
status && status.accounts.length > 0 && /* @__PURE__ */ (0, react_jsx_runtime.
|
|
3831
|
-
className: "ss-
|
|
3832
|
-
children:
|
|
3833
|
-
|
|
3834
|
-
/* @__PURE__ */ (0, react_jsx_runtime.jsx)("
|
|
3835
|
-
|
|
3836
|
-
|
|
3837
|
-
|
|
3838
|
-
|
|
3839
|
-
|
|
3840
|
-
|
|
3841
|
-
/* @__PURE__ */ (0, react_jsx_runtime.jsx)("
|
|
3842
|
-
|
|
3843
|
-
|
|
3844
|
-
|
|
3845
|
-
|
|
3846
|
-
|
|
3847
|
-
|
|
3848
|
-
|
|
3849
|
-
|
|
3850
|
-
|
|
3851
|
-
|
|
3852
|
-
|
|
3853
|
-
|
|
3854
|
-
|
|
3855
|
-
|
|
3856
|
-
|
|
3857
|
-
|
|
3858
|
-
|
|
3859
|
-
|
|
3860
|
-
|
|
3861
|
-
|
|
3862
|
-
|
|
3863
|
-
|
|
3864
|
-
|
|
3865
|
-
|
|
3866
|
-
|
|
3867
|
-
|
|
3868
|
-
|
|
3834
|
+
status && status.accounts.length > 0 && /* @__PURE__ */ (0, react_jsx_runtime.jsx)("div", {
|
|
3835
|
+
className: "ss-tableWrap",
|
|
3836
|
+
children: /* @__PURE__ */ (0, react_jsx_runtime.jsxs)("table", {
|
|
3837
|
+
className: "ss-table",
|
|
3838
|
+
children: [/* @__PURE__ */ (0, react_jsx_runtime.jsx)("thead", { children: /* @__PURE__ */ (0, react_jsx_runtime.jsxs)("tr", { children: [
|
|
3839
|
+
/* @__PURE__ */ (0, react_jsx_runtime.jsx)("th", { children: "账户" }),
|
|
3840
|
+
/* @__PURE__ */ (0, react_jsx_runtime.jsx)("th", { children: "角色" }),
|
|
3841
|
+
/* @__PURE__ */ (0, react_jsx_runtime.jsx)("th", { children: "状态" }),
|
|
3842
|
+
/* @__PURE__ */ (0, react_jsx_runtime.jsx)("th", { children: "对话" }),
|
|
3843
|
+
/* @__PURE__ */ (0, react_jsx_runtime.jsx)("th", { children: "token" }),
|
|
3844
|
+
/* @__PURE__ */ (0, react_jsx_runtime.jsx)("th", {})
|
|
3845
|
+
] }) }), /* @__PURE__ */ (0, react_jsx_runtime.jsx)("tbody", { children: status.accounts.map((a) => /* @__PURE__ */ (0, react_jsx_runtime.jsxs)("tr", { children: [
|
|
3846
|
+
/* @__PURE__ */ (0, react_jsx_runtime.jsxs)("td", { children: [/* @__PURE__ */ (0, react_jsx_runtime.jsx)("code", { children: a.accountId }), a.name ? ` · ${a.name}` : ""] }),
|
|
3847
|
+
/* @__PURE__ */ (0, react_jsx_runtime.jsx)("td", { children: a.role ?? "—" }),
|
|
3848
|
+
/* @__PURE__ */ (0, react_jsx_runtime.jsx)("td", { children: a.usable ? "✅ 可用" : `⚠️ ${a.blockedBy ?? "不可用"}` }),
|
|
3849
|
+
/* @__PURE__ */ (0, react_jsx_runtime.jsx)("td", {
|
|
3850
|
+
title: a.mainSession ?? void 0,
|
|
3851
|
+
children: a.mainSession ? `…${a.mainSession.slice(-8)}` : "(还没建,客户端发第一条消息时建立)"
|
|
3852
|
+
}),
|
|
3853
|
+
/* @__PURE__ */ (0, react_jsx_runtime.jsx)("td", { children: a.hasToken ? `…${a.tokenFingerprint ?? ""}` : "(无)" }),
|
|
3854
|
+
/* @__PURE__ */ (0, react_jsx_runtime.jsxs)("td", { children: [/* @__PURE__ */ (0, react_jsx_runtime.jsx)("button", {
|
|
3855
|
+
type: "button",
|
|
3856
|
+
disabled: busy,
|
|
3857
|
+
onClick: () => void rotate(a.accountId),
|
|
3858
|
+
children: "轮换"
|
|
3859
|
+
}), confirmRemove === a.accountId ? /* @__PURE__ */ (0, react_jsx_runtime.jsxs)(react_jsx_runtime.Fragment, { children: [/* @__PURE__ */ (0, react_jsx_runtime.jsx)("button", {
|
|
3860
|
+
type: "button",
|
|
3861
|
+
disabled: busy,
|
|
3862
|
+
onClick: () => void remove(a.accountId),
|
|
3863
|
+
children: "确认删除"
|
|
3864
|
+
}), /* @__PURE__ */ (0, react_jsx_runtime.jsx)("button", {
|
|
3865
|
+
type: "button",
|
|
3866
|
+
onClick: () => setConfirmRemove(null),
|
|
3867
|
+
children: "取消"
|
|
3868
|
+
})] }) : /* @__PURE__ */ (0, react_jsx_runtime.jsx)("button", {
|
|
3869
|
+
type: "button",
|
|
3870
|
+
disabled: busy,
|
|
3871
|
+
onClick: () => setConfirmRemove(a.accountId),
|
|
3872
|
+
children: "删除"
|
|
3873
|
+
})] })
|
|
3874
|
+
] }, a.accountId)) })]
|
|
3875
|
+
})
|
|
3869
3876
|
}),
|
|
3870
3877
|
status && status.accounts.length === 0 && /* @__PURE__ */ (0, react_jsx_runtime.jsx)("p", {
|
|
3871
3878
|
className: "ss-detailIntro",
|
|
3872
3879
|
children: "该 CCC 还没有声明任何 ACP 账户 ⇒ 客户端一律连不上(fail-closed)。在下面加一条。"
|
|
3873
3880
|
}),
|
|
3874
3881
|
/* @__PURE__ */ (0, react_jsx_runtime.jsxs)("div", {
|
|
3875
|
-
className: "ss-switchRow",
|
|
3882
|
+
className: "ss-switchRow ss-switchRowWrap",
|
|
3876
3883
|
children: [
|
|
3877
|
-
/* @__PURE__ */ (0, react_jsx_runtime.jsx)("span", {
|
|
3884
|
+
/* @__PURE__ */ (0, react_jsx_runtime.jsx)("span", {
|
|
3885
|
+
className: "ss-fieldLabel",
|
|
3886
|
+
children: "新增账户"
|
|
3887
|
+
}),
|
|
3878
3888
|
/* @__PURE__ */ (0, react_jsx_runtime.jsx)("input", {
|
|
3889
|
+
className: "ss-textInput",
|
|
3879
3890
|
placeholder: "账户 ID(如 agmente-phone)",
|
|
3880
3891
|
value: draft.accountId,
|
|
3881
3892
|
onChange: (e) => setDraft({
|
|
@@ -3884,6 +3895,7 @@ window.__ModuleLoader__.load({
|
|
|
3884
3895
|
})
|
|
3885
3896
|
}),
|
|
3886
3897
|
/* @__PURE__ */ (0, react_jsx_runtime.jsx)("input", {
|
|
3898
|
+
className: "ss-textInput",
|
|
3887
3899
|
placeholder: "角色(必须是本 CCC 已有的)",
|
|
3888
3900
|
value: draft.role,
|
|
3889
3901
|
onChange: (e) => setDraft({
|
|
@@ -3897,6 +3909,7 @@ window.__ModuleLoader__.load({
|
|
|
3897
3909
|
children: rolesForSelected.map((r) => /* @__PURE__ */ (0, react_jsx_runtime.jsx)("option", { value: r }, r))
|
|
3898
3910
|
}),
|
|
3899
3911
|
/* @__PURE__ */ (0, react_jsx_runtime.jsx)("input", {
|
|
3912
|
+
className: "ss-textInput",
|
|
3900
3913
|
placeholder: "显示名(可选)",
|
|
3901
3914
|
value: draft.name,
|
|
3902
3915
|
onChange: (e) => setDraft({
|
|
@@ -3906,6 +3919,7 @@ window.__ModuleLoader__.load({
|
|
|
3906
3919
|
}),
|
|
3907
3920
|
/* @__PURE__ */ (0, react_jsx_runtime.jsx)("button", {
|
|
3908
3921
|
type: "button",
|
|
3922
|
+
className: "ss-wakeBtn",
|
|
3909
3923
|
disabled: busy || !selectedRoot,
|
|
3910
3924
|
onClick: () => void addAccount(),
|
|
3911
3925
|
children: "保存并生成 token"
|
|
@@ -3913,7 +3927,7 @@ window.__ModuleLoader__.load({
|
|
|
3913
3927
|
]
|
|
3914
3928
|
}),
|
|
3915
3929
|
error && /* @__PURE__ */ (0, react_jsx_runtime.jsx)("p", {
|
|
3916
|
-
className: "ss-
|
|
3930
|
+
className: "ss-error",
|
|
3917
3931
|
children: `⚠️ ${error}`
|
|
3918
3932
|
}),
|
|
3919
3933
|
freshToken && /* @__PURE__ */ (0, react_jsx_runtime.jsxs)("div", {
|
|
@@ -3921,19 +3935,20 @@ window.__ModuleLoader__.load({
|
|
|
3921
3935
|
children: [
|
|
3922
3936
|
/* @__PURE__ */ (0, react_jsx_runtime.jsx)("p", {
|
|
3923
3937
|
className: "ss-detailIntro",
|
|
3924
|
-
children: `🔑 ${freshToken.accountId} 的 token
|
|
3938
|
+
children: `🔑 ${freshToken.accountId} 的 token(只显示这一次,复制进客户端)\n记得随客户端配置一起保存。`
|
|
3925
3939
|
}),
|
|
3926
3940
|
/* @__PURE__ */ (0, react_jsx_runtime.jsx)("code", {
|
|
3927
|
-
|
|
3928
|
-
wordBreak: "break-all",
|
|
3929
|
-
userSelect: "all"
|
|
3930
|
-
},
|
|
3941
|
+
className: "ss-tokenBox",
|
|
3931
3942
|
children: freshToken.token
|
|
3932
3943
|
}),
|
|
3933
|
-
/* @__PURE__ */ (0, react_jsx_runtime.jsx)("
|
|
3934
|
-
|
|
3935
|
-
|
|
3936
|
-
|
|
3944
|
+
/* @__PURE__ */ (0, react_jsx_runtime.jsx)("div", {
|
|
3945
|
+
className: "ss-switchRow",
|
|
3946
|
+
children: /* @__PURE__ */ (0, react_jsx_runtime.jsx)("button", {
|
|
3947
|
+
type: "button",
|
|
3948
|
+
className: "ss-wakeBtn",
|
|
3949
|
+
onClick: () => setFreshToken(null),
|
|
3950
|
+
children: "我已抄走,隐藏"
|
|
3951
|
+
})
|
|
3937
3952
|
})
|
|
3938
3953
|
]
|
|
3939
3954
|
})
|
|
@@ -4377,7 +4392,7 @@ Instruction-following style:
|
|
|
4377
4392
|
children: "?"
|
|
4378
4393
|
}), /* @__PURE__ */ (0, react_jsx_runtime.jsx)("span", {
|
|
4379
4394
|
className: "ss-helpTip",
|
|
4380
|
-
children: "微信桥是 CCC
|
|
4395
|
+
children: "微信桥是 CCC 级配置。\n· 一个 dsh 进程可挂多个 CCC,各自独立对接微信桥\n· 在这里显式选择目标,不跟随当前会话\n· 各 CCC 的账号、路由、开关互不影响\n· 切换后自动加载该 CCC 的配置"
|
|
4381
4396
|
})]
|
|
4382
4397
|
})
|
|
4383
4398
|
]
|
|
@@ -4437,7 +4452,7 @@ Instruction-following style:
|
|
|
4437
4452
|
children: "?"
|
|
4438
4453
|
}), /* @__PURE__ */ (0, react_jsx_runtime.jsx)("span", {
|
|
4439
4454
|
className: "ss-helpTip",
|
|
4440
|
-
children: "
|
|
4455
|
+
children: "微信桥总开关。\n· 开启后该 CCC 开始长轮询收消息(35s)\n· 前置:至少一个已扫码绑定的账号\n· 每账号独立轮询;✓ = 已绑定凭据,✗ = 未绑定\n· 关闭 = 停止全部轮询,零资源占用"
|
|
4441
4456
|
})]
|
|
4442
4457
|
})
|
|
4443
4458
|
]
|
|
@@ -4507,7 +4522,7 @@ Instruction-following style:
|
|
|
4507
4522
|
children: "?"
|
|
4508
4523
|
}), /* @__PURE__ */ (0, react_jsx_runtime.jsx)("span", {
|
|
4509
4524
|
className: "ss-helpTip",
|
|
4510
|
-
children: "
|
|
4525
|
+
children: "扫码绑定微信账号。\n· 走腾讯 iLink 开放协议(个人微信 Bot API)\n· 步骤:生成二维码 → 手机微信「扫一扫」→ 手机上确认\n· 每扫一次绑定一个新账号,可多账号,各自独立轮询\n· 二维码 5 分钟有效;不需要平台审核"
|
|
4511
4526
|
})]
|
|
4512
4527
|
})
|
|
4513
4528
|
]
|
|
@@ -4557,7 +4572,7 @@ Instruction-following style:
|
|
|
4557
4572
|
children: "?"
|
|
4558
4573
|
}), /* @__PURE__ */ (0, react_jsx_runtime.jsx)("span", {
|
|
4559
4574
|
className: "ss-helpTip",
|
|
4560
|
-
children: "路由表:微信用户 → skiff
|
|
4575
|
+
children: "路由表:微信用户 → skiff 角色映射。\n· 格式:[{\"user\": \"xxx@im.wechat\", \"role\": \"my-role\"}, ...]\n· user = 微信用户 ID(from_user_id);`*` = 通配兜底\n· role = 该 CCC 已定义的 skiff.roles 角色名\n· 未命中路由的用户不回复(不暴露机器人)"
|
|
4561
4576
|
})]
|
|
4562
4577
|
})
|
|
4563
4578
|
]
|
|
@@ -4595,7 +4610,7 @@ Instruction-following style:
|
|
|
4595
4610
|
}
|
|
4596
4611
|
//#endregion
|
|
4597
4612
|
//#region \0sp-css:src/client/SettingsSection
|
|
4598
|
-
const css$2 = "/* SettingsSection — dsh 原生设置面板 serenity-hooks 简单配置页\n v1.21.1 看齐 dsh 自身:官方 settings 设计语言——\n section > title + intro + group(groupTitle) + rowCard 行卡;\n 全部 --dsw-alias-* token(与 ui-settings-models 同词汇表)。 */\n\n/* 页面容器(官方 .section:flex column gap 12) */\n.ss-section {\n display: flex;\n flex-direction: column;\n gap: 14px;\n max-width: 720px;\n color: var(--dsw-alias-label-primary);\n}\n\n/* 页面标题(官方 .title:16px/24 500) */\n.ss-title {\n margin: 0;\n font-size: 16px;\n line-height: 24px;\n font-weight: 500;\n color: var(--dsw-alias-label-primary);\n}\n\n/* 页面说明(官方 .intro:14px/22 tertiary) */\n.ss-intro {\n margin: 0;\n font-size: 14px;\n line-height: 22px;\n color: var(--dsw-alias-label-tertiary);\n word-break: break-word;\n overflow-wrap: anywhere;\n}\n\n/* 分组(多级标题:分组标题 + 行卡列表) */\n.ss-group {\n display: flex;\n flex-direction: column;\n gap: 8px;\n}\n\n/* 分组标题(二级:12px/18 500 secondary——官方 fieldLabel 风格) */\n.ss-groupTitle {\n margin: 0;\n font-size: 12px;\n line-height: 18px;\n font-weight: 600;\n letter-spacing: 0.02em;\n text-transform: uppercase;\n color: var(--dsw-alias-label-secondary);\n}\n\n/* 行卡列表(官方 .rows:无 marker,gap 8) */\n.ss-rows {\n list-style: none;\n margin: 0;\n padding: 0;\n display: flex;\n flex-direction: column;\n gap: 8px;\n}\n\n/* 行卡(官方 .rowCard:border-l2 r12 padding 12/14) */\n.ss-rowCard {\n border: 1px solid var(--dsw-alias-border-l2);\n border-radius: 12px;\n padding: 12px 14px;\n display: flex;\n align-items: center;\n justify-content: space-between;\n gap: 16px;\n}\n\n/* ── v1.29 需求②:可展开行(整行点击 → 行内详设)── */\n.ss-expandable {\n flex-wrap: wrap; /* detail 换行占满整行 */\n cursor: default;\n}\n.ss-expandable .ss-rowText {\n cursor: pointer;\n}\n.ss-expandable .ss-rowText:hover .ss-rowName {\n color: var(--dsw-alias-state-success-primary, #22c55e);\n}\n.ss-expanded {\n border-color: var(--dsw-alias-state-success-primary, #22c55e);\n}\n.ss-expandMark {\n display: inline-block;\n margin-left: 6px;\n font-size: 10px;\n color: var(--dsw-alias-label-tertiary);\n transition: transform 0.15s ease;\n}\n.ss-expanded .ss-expandMark {\n transform: rotate(90deg);\n}\n.ss-rowDetail {\n flex-basis: 100%;\n width: 100%;\n border-top: 1px solid var(--dsw-alias-border-l2);\n margin-top: 10px;\n padding-top: 12px;\n display: flex;\n flex-direction: column;\n gap: 10px;\n min-width: 0;\n}\n.ss-detailStack {\n display: flex;\n flex-direction: column;\n gap: 10px;\n}\n.ss-detailIntro {\n margin: 0;\n font-size: 12px;\n line-height: 19px;\n color: var(--dsw-alias-label-secondary);\n white-space: pre-line;\n word-break: break-word;\n overflow-wrap: anywhere;\n padding: 8px 10px;\n border-radius: 8px;\n background: var(--dsw-alias-interactive-bg-active, rgba(128, 128, 128, 0.06));\n}\n\n/* 行卡文本(标题 + 说明 左列) */\n.ss-rowText {\n display: flex;\n flex-direction: column;\n gap: 3px;\n min-width: 0;\n flex: 1;\n}\n\n/* 行卡标题(官方 .rowName:14px/22 500) */\n.ss-rowName {\n font-size: 14px;\n line-height: 22px;\n font-weight: 500;\n color: var(--dsw-alias-label-primary);\n}\n\n/* 行卡说明(12px/18 tertiary;v1.27.5 紧凑化:默认单行截断,hover title 看全文) */\n.ss-rowDesc {\n font-size: 12px;\n line-height: 18px;\n color: var(--dsw-alias-label-tertiary);\n word-break: break-word;\n overflow-wrap: anywhere;\n display: -webkit-box;\n -webkit-line-clamp: 2;\n -webkit-box-orient: vertical;\n overflow: hidden;\n}\n\n/* 行卡控件(右置) */\n.ss-rowControl {\n flex: none;\n display: flex;\n align-items: center;\n}\n\n/* 开关(官方 token 的自绘 toggle:track 22px,thumb 16px) */\n.ss-switch {\n position: relative;\n flex: none;\n width: 40px;\n height: 22px;\n cursor: pointer;\n}\n\n.ss-switch input {\n position: absolute;\n opacity: 0;\n width: 100%;\n height: 100%;\n margin: 0;\n cursor: pointer;\n}\n\n.ss-switchTrack {\n position: absolute;\n inset: 0;\n border-radius: 11px;\n background: var(--dsw-alias-border-l3);\n transition: background var(--ds-transition-duration-fast, 0.15s) var(--ds-ease-in-out, ease);\n}\n\n.ss-switchTrack::after {\n content: '';\n position: absolute;\n top: 3px;\n left: 3px;\n width: 16px;\n height: 16px;\n border-radius: 50%;\n background: var(--dsw-alias-label-primary-foreground);\n transition: transform var(--ds-transition-duration-fast, 0.15s) var(--ds-ease-in-out, ease);\n}\n\n.ss-switch input:checked + .ss-switchTrack {\n background: var(--dsw-alias-brand-primary);\n}\n\n.ss-switch input:checked + .ss-switchTrack::after {\n transform: translateX(18px);\n}\n\n.ss-switch input:disabled + .ss-switchTrack {\n opacity: 0.4;\n cursor: default;\n}\n\n/* 阈值行(滑块 + 值) */\n.ss-threshold {\n display: flex;\n align-items: center;\n gap: 12px;\n}\n\n.ss-threshold input[type='range'] {\n width: 160px;\n}\n\n/* Skiff 调试端口输入(number;关闭时跟随 disabled 半透明) */\n.ss-portInput {\n width: 96px;\n padding: 6px 8px;\n border-radius: 8px;\n border: 1px solid var(--dsw-alias-border-l2);\n background: var(--dsw-alias-bg-layer-2);\n color: var(--dsw-alias-label-primary);\n font-size: 13px;\n font-variant-numeric: tabular-nums;\n text-align: right;\n}\n\n.ss-portInput:disabled {\n opacity: 0.4;\n cursor: default;\n}\n\n.ss-value {\n min-width: 40px;\n font-variant-numeric: tabular-nums;\n font-size: 13px;\n font-weight: 600;\n color: var(--dsw-alias-label-primary);\n text-align: right;\n}\n\n/* 自主轨迹「立即唤起」按钮(v1.26.14 调试语义;官方 button 语言:primary 弱化) */\n.ss-wakeBtn {\n flex: none;\n padding: 5px 12px;\n border-radius: 8px;\n border: 1px solid var(--dsw-alias-border-l2);\n background: var(--dsw-alias-interactive-bg-active, rgba(128, 128, 128, 0.12));\n color: var(--dsw-alias-label-primary);\n font-size: 12px;\n line-height: 18px;\n font-weight: 500;\n cursor: pointer;\n transition: opacity var(--ds-transition-duration-fast, 0.15s) ease;\n}\n\n.ss-wakeBtn:hover:not(:disabled) {\n border-color: var(--dsw-alias-state-success-primary, #22c55e);\n color: var(--dsw-alias-state-success-primary, #22c55e);\n}\n\n.ss-wakeBtn:disabled {\n opacity: 0.4;\n cursor: default;\n}\n\n/* 底部帮助行 */\n.ss-hint {\n margin: 0;\n font-size: 12px;\n line-height: 18px;\n color: var(--dsw-alias-label-tertiary);\n word-break: break-word;\n overflow-wrap: anywhere;\n}\n\n/* 降级提示 */\n.ss-degrade {\n margin: 0;\n font-size: 12px;\n line-height: 18px;\n color: var(--dsw-alias-state-warn-label);\n word-break: break-word;\n overflow-wrap: anywhere;\n}\n\n/* 错误提示(v1.29 会话清理等) */\n.ss-error {\n margin: 0;\n font-size: 12px;\n line-height: 18px;\n color: var(--dsw-alias-state-error-primary, #ef4444);\n background: rgba(239, 68, 68, 0.08);\n border-radius: 8px;\n padding: 8px 10px;\n white-space: pre-line;\n word-break: break-word;\n}\n\n/* ── v1.27.5 紧凑化:折叠组(details/summary)── */\n.ss-collapse {\n border: 1px solid var(--dsw-alias-border-l2);\n border-radius: 12px;\n overflow: hidden;\n}\n\n.ss-collapseHead {\n display: flex;\n align-items: baseline;\n gap: 10px;\n padding: 10px 14px;\n cursor: pointer;\n list-style: none;\n user-select: none;\n}\n\n.ss-collapseHead::-webkit-details-marker {\n display: none;\n}\n\n.ss-collapseHead::before {\n content: '▸';\n flex: none;\n font-size: 11px;\n color: var(--dsw-alias-label-tertiary);\n transition: transform 0.15s ease;\n}\n\n.ss-collapse[open] > .ss-collapseHead::before {\n transform: rotate(90deg);\n}\n\n.ss-collapseHead:hover {\n background: var(--dsw-alias-interactive-bg-hover, rgba(128, 128, 128, 0.06));\n}\n\n.ss-collapseTitle {\n font-size: 13px;\n font-weight: 500;\n color: var(--dsw-alias-label-primary);\n}\n\n.ss-collapseDesc {\n font-size: 12px;\n color: var(--dsw-alias-label-tertiary);\n white-space: nowrap;\n overflow: hidden;\n text-overflow: ellipsis;\n min-width: 0;\n}\n\n.ss-collapseBody {\n padding: 10px 14px 14px;\n border-top: 1px solid var(--dsw-alias-border-l1);\n}\n\n/* ── v1.27.5 紧凑化:只读定义列表(dl/dt/dd 2 列网格)── */\n.ss-defList {\n display: grid;\n grid-template-columns: repeat(2, minmax(0, 1fr));\n gap: 6px 20px;\n margin: 0;\n width: 100%;\n min-width: 0;\n}\n\n.ss-defItem {\n display: flex;\n flex-direction: column;\n gap: 1px;\n min-width: 0;\n}\n\n.ss-defTerm {\n font-size: 11px;\n line-height: 16px;\n font-weight: 500;\n letter-spacing: 0.02em;\n text-transform: uppercase;\n color: var(--dsw-alias-label-tertiary);\n}\n\n.ss-defValue {\n margin: 0;\n font-size: 12px;\n line-height: 18px;\n color: var(--dsw-alias-label-primary);\n word-break: break-word;\n overflow-wrap: anywhere;\n display: -webkit-box;\n -webkit-line-clamp: 2;\n -webkit-box-orient: vertical;\n overflow: hidden;\n}\n\n/* ── v1.27.5 紧凑化:开关 + 端口内联行 ── */\n.ss-switchRow {\n display: flex;\n align-items: center;\n gap: 8px;\n}\n\n/* ── v1.59.1 ACP 账户台账表(owner 2026-10-17:「面板里只放个开关不放具体的条目吗?」)\n *\n * 用**表格**而不是卡片列表:台账天生是\"一行一条、列对齐可比\"的数据\n * (账户 / 角色 / 状态 / token 指纹),卡片会把可比性拆散。\n * 窄屏靠横向滚动兜底——不折行,折行后\"哪一格对应哪一列\"就看不出来了。 */\n.ss-table {\n width: 100%;\n border-collapse: collapse;\n font-size: 12px;\n overflow-x: auto;\n display: block;\n}\n\n.ss-table th,\n.ss-table td {\n padding: 4px 8px;\n text-align: left;\n border-bottom: 1px solid var(--dsw-alias-border-l2);\n white-space: nowrap;\n}\n\n.ss-table th {\n color: var(--dsw-alias-label-tertiary);\n font-weight: 600;\n}\n\n.ss-table td code {\n font-size: 11px;\n padding: 1px 4px;\n border-radius: 3px;\n background: var(--dsw-alias-interactive-bg-active, rgba(128, 128, 128, 0.12));\n}\n\n.ss-table button {\n margin-left: 4px;\n}\n\n/* ── v1.27.6 「?」帮助浮层(hover/焦点显示三行以上严谨说明)── */\n.ss-help {\n position: relative;\n display: inline-flex;\n align-items: center;\n margin-top: 2px;\n}\n\n.ss-helpMark {\n flex: none;\n width: 16px;\n height: 16px;\n padding: 0;\n border: 1px solid var(--dsw-alias-border-l2);\n border-radius: 50%;\n background: var(--dsw-alias-interactive-bg-active, rgba(128, 128, 128, 0.12));\n color: var(--dsw-alias-label-tertiary);\n font-size: 10px;\n line-height: 1;\n font-weight: 600;\n cursor: help;\n display: inline-flex;\n align-items: center;\n justify-content: center;\n transition: border-color 0.15s ease, color 0.15s ease;\n}\n\n.ss-helpMark:hover,\n.ss-helpMark:focus-visible {\n border-color: var(--dsw-alias-state-success-primary, #22c55e);\n color: var(--dsw-alias-state-success-primary, #22c55e);\n outline: none;\n}\n\n.ss-helpTip {\n position: absolute;\n left: 0;\n top: calc(100% + 6px);\n z-index: 30;\n width: 300px;\n max-width: 60vw;\n padding: 10px 12px;\n border: 1px solid var(--dsw-alias-border-l2);\n border-radius: 10px;\n background: var(--dsw-alias-bg-overlay);\n box-shadow: 0 6px 24px rgba(0, 0, 0, 0.28);\n font-size: 12px;\n line-height: 19px;\n font-weight: 400;\n color: var(--dsw-alias-label-primary);\n white-space: pre-line;\n word-break: break-word;\n opacity: 0;\n pointer-events: none;\n transform: translateY(-4px);\n transition: opacity 0.15s ease, transform 0.15s ease;\n}\n\n.ss-help:hover .ss-helpTip,\n.ss-helpMark:focus-visible + .ss-helpTip {\n opacity: 1;\n pointer-events: auto;\n transform: translateY(0);\n}\n\n/* 折叠组内帮助浮层定位修正(左侧行卡不会溢出面板) */\n.ss-rowCard .ss-helpTip {\n left: 0;\n}\n\n/* ── 微信桥(F4c-3,v1.27.0 实验性)── */\n\n/* CCC 选择器(下拉) */\n.ss-select {\n max-width: 280px;\n padding: 6px 8px;\n border-radius: 8px;\n border: 1px solid var(--dsw-alias-border-l2);\n background: var(--dsw-alias-bg-layer-2);\n color: var(--dsw-alias-label-primary);\n font-size: 13px;\n}\n\n/* 扫码绑定按钮(复用 wakeBtn 语言) */\n.ss-loginBtn {\n flex: none;\n padding: 5px 12px;\n border-radius: 8px;\n border: 1px solid var(--dsw-alias-border-l2);\n background: var(--dsw-alias-interactive-bg-active, rgba(128, 128, 128, 0.12));\n color: var(--dsw-alias-label-primary);\n font-size: 12px;\n line-height: 18px;\n font-weight: 500;\n cursor: pointer;\n transition: opacity var(--ds-transition-duration-fast, 0.15s) ease;\n}\n\n.ss-loginBtn:hover:not(:disabled) {\n border-color: var(--dsw-alias-state-success-primary, #22c55e);\n color: var(--dsw-alias-state-success-primary, #22c55e);\n}\n\n.ss-loginBtn:disabled {\n opacity: 0.4;\n cursor: default;\n}\n\n/* 移除账号按钮(危险语义:红边框) */\n.ss-removeBtn {\n flex: none;\n padding: 5px 12px;\n border-radius: 8px;\n border: 1px solid var(--dsw-alias-border-l2);\n background: var(--dsw-alias-interactive-bg-active, rgba(128, 128, 128, 0.12));\n color: var(--dsw-alias-label-primary);\n font-size: 12px;\n line-height: 18px;\n font-weight: 500;\n cursor: pointer;\n transition: opacity var(--ds-transition-duration-fast, 0.15s) ease;\n}\n\n.ss-removeBtn:hover:not(:disabled) {\n border-color: var(--dsw-alias-state-error-primary, #ef4444);\n color: var(--dsw-alias-state-error-primary, #ef4444);\n}\n\n/* 二维码展示行 */\n.ss-qrRow {\n align-items: center;\n}\n\n.ss-qrSvg {\n flex: none;\n width: 120px; /* v1.27.5 紧凑化:160 → 120 */\n height: 120px;\n border-radius: 8px;\n border: 1px solid var(--dsw-alias-border-l2);\n background: #fff; /* 二维码需要白底才能被微信扫出 */\n padding: 6px;\n display: flex;\n align-items: center;\n justify-content: center;\n}\n\n.ss-qrSvg svg {\n width: 100%;\n height: 100%;\n}\n\n/* 路由表 JSON 编辑框 */\n.ss-routesEditor {\n width: 100%;\n box-sizing: border-box;\n margin-top: 6px;\n padding: 8px 10px;\n border-radius: 8px;\n border: 1px solid var(--dsw-alias-border-l2);\n background: var(--dsw-alias-bg-layer-2);\n color: var(--dsw-alias-label-primary);\n font-size: 12px;\n line-height: 18px;\n font-family: var(--ds-font-family-code);\n resize: vertical;\n}\n";
|
|
4613
|
+
const css$2 = "/* SettingsSection — dsh 原生设置面板 serenity-hooks 简单配置页\n v1.21.1 看齐 dsh 自身:官方 settings 设计语言——\n section > title + intro + group(groupTitle) + rowCard 行卡;\n 全部 --dsw-alias-* token(与 ui-settings-models 同词汇表)。 */\n\n/* 页面容器(官方 .section:flex column gap 12) */\n.ss-section {\n display: flex;\n flex-direction: column;\n gap: 14px;\n max-width: 720px;\n color: var(--dsw-alias-label-primary);\n}\n\n/* 页面标题(官方 .title:16px/24 500) */\n.ss-title {\n margin: 0;\n font-size: 16px;\n line-height: 24px;\n font-weight: 500;\n color: var(--dsw-alias-label-primary);\n}\n\n/* 页面说明(官方 .intro:14px/22 tertiary) */\n.ss-intro {\n margin: 0;\n font-size: 14px;\n line-height: 22px;\n color: var(--dsw-alias-label-tertiary);\n word-break: break-word;\n overflow-wrap: anywhere;\n}\n\n/* 分组(多级标题:分组标题 + 行卡列表) */\n.ss-group {\n display: flex;\n flex-direction: column;\n gap: 8px;\n}\n\n/* 分组标题(二级:12px/18 500 secondary——官方 fieldLabel 风格) */\n.ss-groupTitle {\n margin: 0;\n font-size: 12px;\n line-height: 18px;\n font-weight: 600;\n letter-spacing: 0.02em;\n text-transform: uppercase;\n color: var(--dsw-alias-label-secondary);\n}\n\n/* 行卡列表(官方 .rows:无 marker,gap 8) */\n.ss-rows {\n list-style: none;\n margin: 0;\n padding: 0;\n display: flex;\n flex-direction: column;\n gap: 8px;\n}\n\n/* 行卡(官方 .rowCard:border-l2 r12 padding 12/14) */\n.ss-rowCard {\n border: 1px solid var(--dsw-alias-border-l2);\n border-radius: 12px;\n padding: 12px 14px;\n display: flex;\n align-items: center;\n justify-content: space-between;\n gap: 16px;\n}\n\n/* ── v1.29 需求②:可展开行(整行点击 → 行内详设)── */\n.ss-expandable {\n flex-wrap: wrap; /* detail 换行占满整行 */\n cursor: default;\n}\n.ss-expandable .ss-rowText {\n cursor: pointer;\n}\n.ss-expandable .ss-rowText:hover .ss-rowName {\n color: var(--dsw-alias-state-success-primary, #22c55e);\n}\n.ss-expanded {\n border-color: var(--dsw-alias-state-success-primary, #22c55e);\n}\n.ss-expandMark {\n display: inline-block;\n margin-left: 6px;\n font-size: 10px;\n color: var(--dsw-alias-label-tertiary);\n transition: transform 0.15s ease;\n}\n.ss-expanded .ss-expandMark {\n transform: rotate(90deg);\n}\n.ss-rowDetail {\n flex-basis: 100%;\n width: 100%;\n border-top: 1px solid var(--dsw-alias-border-l2);\n margin-top: 10px;\n padding-top: 12px;\n display: flex;\n flex-direction: column;\n gap: 10px;\n min-width: 0;\n}\n.ss-detailStack {\n display: flex;\n flex-direction: column;\n gap: 10px;\n}\n.ss-detailIntro {\n margin: 0;\n font-size: 12px;\n line-height: 19px;\n color: var(--dsw-alias-label-secondary);\n white-space: pre-line;\n word-break: break-word;\n overflow-wrap: anywhere;\n padding: 8px 10px;\n border-radius: 8px;\n background: var(--dsw-alias-interactive-bg-active, rgba(128, 128, 128, 0.06));\n}\n\n/* 行卡文本(标题 + 说明 左列) */\n.ss-rowText {\n display: flex;\n flex-direction: column;\n gap: 3px;\n min-width: 0;\n flex: 1;\n}\n\n/* 行卡标题(官方 .rowName:14px/22 500) */\n.ss-rowName {\n font-size: 14px;\n line-height: 22px;\n font-weight: 500;\n color: var(--dsw-alias-label-primary);\n}\n\n/* 行卡说明(12px/18 tertiary;v1.27.5 紧凑化:默认单行截断,hover title 看全文) */\n.ss-rowDesc {\n font-size: 12px;\n line-height: 18px;\n color: var(--dsw-alias-label-tertiary);\n word-break: break-word;\n overflow-wrap: anywhere;\n display: -webkit-box;\n -webkit-line-clamp: 2;\n -webkit-box-orient: vertical;\n overflow: hidden;\n}\n\n/* 行卡控件(右置) */\n.ss-rowControl {\n flex: none;\n display: flex;\n align-items: center;\n}\n\n/* 开关(官方 token 的自绘 toggle:track 22px,thumb 16px) */\n.ss-switch {\n position: relative;\n flex: none;\n width: 40px;\n height: 22px;\n cursor: pointer;\n}\n\n.ss-switch input {\n position: absolute;\n opacity: 0;\n width: 100%;\n height: 100%;\n margin: 0;\n cursor: pointer;\n}\n\n.ss-switchTrack {\n position: absolute;\n inset: 0;\n border-radius: 11px;\n background: var(--dsw-alias-border-l3);\n transition: background var(--ds-transition-duration-fast, 0.15s) var(--ds-ease-in-out, ease);\n}\n\n.ss-switchTrack::after {\n content: '';\n position: absolute;\n top: 3px;\n left: 3px;\n width: 16px;\n height: 16px;\n border-radius: 50%;\n background: var(--dsw-alias-label-primary-foreground);\n transition: transform var(--ds-transition-duration-fast, 0.15s) var(--ds-ease-in-out, ease);\n}\n\n.ss-switch input:checked + .ss-switchTrack {\n background: var(--dsw-alias-brand-primary);\n}\n\n.ss-switch input:checked + .ss-switchTrack::after {\n transform: translateX(18px);\n}\n\n.ss-switch input:disabled + .ss-switchTrack {\n opacity: 0.4;\n cursor: default;\n}\n\n/* Skiff 调试端口输入(number;关闭时跟随 disabled 半透明) */\n.ss-portInput {\n width: 96px;\n padding: 6px 8px;\n border-radius: 8px;\n border: 1px solid var(--dsw-alias-border-l2);\n background: var(--dsw-alias-bg-layer-2);\n color: var(--dsw-alias-label-primary);\n font-size: 13px;\n font-variant-numeric: tabular-nums;\n text-align: right;\n}\n\n.ss-portInput:disabled {\n opacity: 0.4;\n cursor: default;\n}\n\n/* 自主轨迹「立即唤起」按钮(v1.26.14 调试语义;官方 button 语言:primary 弱化) */\n.ss-wakeBtn {\n flex: none;\n padding: 5px 12px;\n border-radius: 8px;\n border: 1px solid var(--dsw-alias-border-l2);\n background: var(--dsw-alias-interactive-bg-active, rgba(128, 128, 128, 0.12));\n color: var(--dsw-alias-label-primary);\n font-size: 12px;\n line-height: 18px;\n font-weight: 500;\n cursor: pointer;\n transition: opacity var(--ds-transition-duration-fast, 0.15s) ease;\n}\n\n.ss-wakeBtn:hover:not(:disabled) {\n border-color: var(--dsw-alias-state-success-primary, #22c55e);\n color: var(--dsw-alias-state-success-primary, #22c55e);\n}\n\n.ss-wakeBtn:disabled {\n opacity: 0.4;\n cursor: default;\n}\n\n/* 错误提示(会话清理等) */\n.ss-error {\n margin: 0;\n font-size: 12px;\n line-height: 18px;\n color: var(--dsw-alias-state-error-primary, #ef4444);\n background: rgba(239, 68, 68, 0.08);\n border-radius: 8px;\n padding: 8px 10px;\n white-space: pre-line;\n word-break: break-word;\n}\n\n/* ── v1.27.5 紧凑化:折叠组(details/summary)── */\n.ss-collapse {\n border: 1px solid var(--dsw-alias-border-l2);\n border-radius: 12px;\n overflow: hidden;\n}\n\n.ss-collapseHead {\n display: flex;\n align-items: baseline;\n gap: 10px;\n padding: 10px 14px;\n cursor: pointer;\n list-style: none;\n user-select: none;\n}\n\n.ss-collapseHead::-webkit-details-marker {\n display: none;\n}\n\n.ss-collapseHead::before {\n content: '▸';\n flex: none;\n font-size: 11px;\n color: var(--dsw-alias-label-tertiary);\n transition: transform 0.15s ease;\n}\n\n.ss-collapse[open] > .ss-collapseHead::before {\n transform: rotate(90deg);\n}\n\n.ss-collapseHead:hover {\n background: var(--dsw-alias-interactive-bg-hover, rgba(128, 128, 128, 0.06));\n}\n\n.ss-collapseTitle {\n font-size: 13px;\n font-weight: 500;\n color: var(--dsw-alias-label-primary);\n}\n\n.ss-collapseDesc {\n font-size: 12px;\n color: var(--dsw-alias-label-tertiary);\n white-space: nowrap;\n overflow: hidden;\n text-overflow: ellipsis;\n min-width: 0;\n}\n\n.ss-collapseBody {\n padding: 10px 14px 14px;\n border-top: 1px solid var(--dsw-alias-border-l1);\n}\n\n/* ── 开关 + 端口内联行 ── */\n.ss-switchRow {\n display: flex;\n align-items: center;\n gap: 8px;\n}\n\n/* 同一行放不下时换行(ACP 新增账户那行有四个控件) */\n.ss-switchRowWrap {\n flex-wrap: wrap;\n}\n\n/* 行内字段名(与 .ss-rowName 同一语域,但不吃行高) */\n.ss-fieldLabel {\n flex: none;\n font-size: 12px;\n font-weight: 500;\n color: var(--dsw-alias-label-secondary);\n white-space: nowrap;\n}\n\n/* 行内文本输入(与 .ss-portInput 同款外观,宽度随内容) */\n.ss-textInput {\n flex: 1 1 140px;\n min-width: 0;\n padding: 6px 8px;\n border-radius: 8px;\n border: 1px solid var(--dsw-alias-border-l2);\n background: var(--dsw-alias-bg-layer-2);\n color: var(--dsw-alias-label-primary);\n font-size: 13px;\n}\n\n.ss-textInput::placeholder {\n color: var(--dsw-alias-label-dimmed);\n}\n\n/* 明文 token 展示块(等宽、可整体选中、长串折行) */\n.ss-tokenBox {\n display: block;\n padding: 8px 10px;\n border-radius: 8px;\n border: 1px solid var(--dsw-alias-border-l2);\n background: var(--dsw-alias-bg-layer-2);\n color: var(--dsw-alias-label-primary);\n font-family: var(--ds-font-family-code);\n font-size: 12px;\n line-height: 18px;\n word-break: break-all;\n user-select: all;\n}\n\n/* ── ACP 账户台账表(owner 2026-10-17:「面板里只放个开关不放具体的条目吗?」)\n *\n * 用表格而不是卡片列表:台账天生是「一行一条、列对齐可比」的数据\n * (账户 / 角色 / 状态 / token 指纹),卡片会把可比性拆散。\n * 🔴 横向滚动必须挂在外层容器上:给 `<table>` 本身加 `display:block` 会连带丢掉\n * `border-collapse`(表格边框塌陷失效),故表格保持 `display:table`,由 .ss-tableWrap 兜滚动。 */\n.ss-tableWrap {\n max-width: 100%;\n overflow-x: auto;\n}\n\n.ss-table {\n width: 100%;\n border-collapse: collapse;\n font-size: 12px;\n}\n\n.ss-table th,\n.ss-table td {\n padding: 6px 10px;\n text-align: left;\n border-bottom: 1px solid var(--dsw-alias-border-l2);\n white-space: nowrap;\n vertical-align: middle;\n}\n\n.ss-table th {\n color: var(--dsw-alias-label-tertiary);\n font-weight: 600;\n}\n\n.ss-table td code {\n font-size: 11px;\n padding: 1px 4px;\n border-radius: 3px;\n background: var(--dsw-alias-interactive-bg-active, rgba(128, 128, 128, 0.12));\n}\n\n.ss-table button {\n margin-left: 4px;\n}\n\n.ss-table button:first-child {\n margin-left: 0;\n}\n\n/* ── v1.27.6 「?」帮助浮层(hover/焦点显示三行以上严谨说明)── */\n.ss-help {\n position: relative;\n display: inline-flex;\n align-items: center;\n margin-top: 2px;\n}\n\n.ss-helpMark {\n flex: none;\n width: 16px;\n height: 16px;\n padding: 0;\n border: 1px solid var(--dsw-alias-border-l2);\n border-radius: 50%;\n background: var(--dsw-alias-interactive-bg-active, rgba(128, 128, 128, 0.12));\n color: var(--dsw-alias-label-tertiary);\n font-size: 10px;\n line-height: 1;\n font-weight: 600;\n cursor: help;\n display: inline-flex;\n align-items: center;\n justify-content: center;\n transition: border-color 0.15s ease, color 0.15s ease;\n}\n\n.ss-helpMark:hover,\n.ss-helpMark:focus-visible {\n border-color: var(--dsw-alias-state-success-primary, #22c55e);\n color: var(--dsw-alias-state-success-primary, #22c55e);\n outline: none;\n}\n\n.ss-helpTip {\n position: absolute;\n left: 0;\n top: calc(100% + 6px);\n z-index: 30;\n width: 300px;\n max-width: 60vw;\n padding: 10px 12px;\n border: 1px solid var(--dsw-alias-border-l2);\n border-radius: 10px;\n background: var(--dsw-alias-bg-overlay);\n box-shadow: 0 6px 24px rgba(0, 0, 0, 0.28);\n font-size: 12px;\n line-height: 19px;\n font-weight: 400;\n color: var(--dsw-alias-label-primary);\n white-space: pre-line;\n word-break: break-word;\n opacity: 0;\n pointer-events: none;\n transform: translateY(-4px);\n transition: opacity 0.15s ease, transform 0.15s ease;\n}\n\n.ss-help:hover .ss-helpTip,\n.ss-helpMark:focus-visible + .ss-helpTip {\n opacity: 1;\n pointer-events: auto;\n transform: translateY(0);\n}\n\n/* 折叠组内帮助浮层定位修正(左侧行卡不会溢出面板) */\n.ss-rowCard .ss-helpTip {\n left: 0;\n}\n\n/* ── 微信桥(F4c-3,v1.27.0 实验性)── */\n\n/* CCC 选择器(下拉) */\n.ss-select {\n max-width: 280px;\n padding: 6px 8px;\n border-radius: 8px;\n border: 1px solid var(--dsw-alias-border-l2);\n background: var(--dsw-alias-bg-layer-2);\n color: var(--dsw-alias-label-primary);\n font-size: 13px;\n}\n\n/* 扫码绑定按钮(复用 wakeBtn 语言) */\n.ss-loginBtn {\n flex: none;\n padding: 5px 12px;\n border-radius: 8px;\n border: 1px solid var(--dsw-alias-border-l2);\n background: var(--dsw-alias-interactive-bg-active, rgba(128, 128, 128, 0.12));\n color: var(--dsw-alias-label-primary);\n font-size: 12px;\n line-height: 18px;\n font-weight: 500;\n cursor: pointer;\n transition: opacity var(--ds-transition-duration-fast, 0.15s) ease;\n}\n\n.ss-loginBtn:hover:not(:disabled) {\n border-color: var(--dsw-alias-state-success-primary, #22c55e);\n color: var(--dsw-alias-state-success-primary, #22c55e);\n}\n\n.ss-loginBtn:disabled {\n opacity: 0.4;\n cursor: default;\n}\n\n/* 移除账号按钮(危险语义:红边框) */\n.ss-removeBtn {\n flex: none;\n padding: 5px 12px;\n border-radius: 8px;\n border: 1px solid var(--dsw-alias-border-l2);\n background: var(--dsw-alias-interactive-bg-active, rgba(128, 128, 128, 0.12));\n color: var(--dsw-alias-label-primary);\n font-size: 12px;\n line-height: 18px;\n font-weight: 500;\n cursor: pointer;\n transition: opacity var(--ds-transition-duration-fast, 0.15s) ease;\n}\n\n.ss-removeBtn:hover:not(:disabled) {\n border-color: var(--dsw-alias-state-error-primary, #ef4444);\n color: var(--dsw-alias-state-error-primary, #ef4444);\n}\n\n/* 二维码展示行 */\n.ss-qrRow {\n align-items: center;\n}\n\n.ss-qrSvg {\n flex: none;\n width: 120px; /* v1.27.5 紧凑化:160 → 120 */\n height: 120px;\n border-radius: 8px;\n border: 1px solid var(--dsw-alias-border-l2);\n background: #fff; /* 二维码需要白底才能被微信扫出 */\n padding: 6px;\n display: flex;\n align-items: center;\n justify-content: center;\n}\n\n.ss-qrSvg svg {\n width: 100%;\n height: 100%;\n}\n\n/* 路由表 JSON 编辑框 */\n.ss-routesEditor {\n width: 100%;\n box-sizing: border-box;\n margin-top: 6px;\n padding: 8px 10px;\n border-radius: 8px;\n border: 1px solid var(--dsw-alias-border-l2);\n background: var(--dsw-alias-bg-layer-2);\n color: var(--dsw-alias-label-primary);\n font-size: 12px;\n line-height: 18px;\n font-family: var(--ds-font-family-code);\n resize: vertical;\n}\n\n/* ── 窄屏(面板被塞进窄栏或手机浏览器)────────────────────────────────────\n * 排版问题只有一个根因:`.ss-rowCard` 是「左文本 + 右控件」的两列 flex,\n * 而控件里有端口输入(96px)/开关(40px)/端口+开关(150px)三档。\n * 窄到放不下时,flex 会先压文字(`min-width: 0` 已开)⇒ 标题被挤成一列竖排字。\n * 处理:窄屏把控件落到第二行(左对齐),文字保住整行宽。 */\n@media (max-width: 560px) {\n .ss-rowCard {\n flex-wrap: wrap;\n gap: 10px;\n }\n\n .ss-rowControl {\n flex-basis: 100%;\n justify-content: flex-start;\n }\n\n /* 行内说明在窄屏不必截断:整行宽足够,截断反而藏信息 */\n .ss-rowDesc {\n -webkit-line-clamp: unset;\n display: block;\n }\n\n /* 详情区与折叠头在窄屏收紧内边距(横向像素更值钱) */\n .ss-rowDetail,\n .ss-collapseBody {\n padding-left: 0;\n padding-right: 0;\n }\n\n .ss-switchRowWrap {\n gap: 6px;\n }\n\n .ss-textInput {\n flex-basis: 100%;\n }\n}\n";
|
|
4599
4614
|
if (typeof document !== "undefined" && document.querySelector("style[data-sp-css=\"SettingsSection\"]") === null) {
|
|
4600
4615
|
const tag = document.createElement("style");
|
|
4601
4616
|
tag.setAttribute("data-sp-css", "SettingsSection");
|
|
@@ -4618,10 +4633,10 @@ Instruction-following style:
|
|
|
4618
4633
|
});
|
|
4619
4634
|
}
|
|
4620
4635
|
/** 一个配置行卡(官方 rowCard:标题+说明 左列 / 控件右置)
|
|
4621
|
-
* help:可选——desc
|
|
4622
|
-
* expandable:可选——整行点击展开 detail
|
|
4623
|
-
* 点击行(标题/desc 区)toggle 展开态;detail
|
|
4624
|
-
*
|
|
4636
|
+
* help:可选——desc 下方渲染「?」帮助浮层(三行以上说明;仅不可展开的行用)
|
|
4637
|
+
* expandable:可选——整行点击展开 detail 内联详设(开关与详设合一)。
|
|
4638
|
+
* 点击行(标题/desc 区)toggle 展开态;detail 渲染在行内下方(含该功能全部配置项/重型编辑器)。
|
|
4639
|
+
* 展开态由标题右侧 ▸/▾ 指示。 */
|
|
4625
4640
|
function RowCard(props) {
|
|
4626
4641
|
const { title, desc, control, help, expandable, detail } = props;
|
|
4627
4642
|
const isControlled = props.open !== void 0;
|
|
@@ -4652,11 +4667,12 @@ Instruction-following style:
|
|
|
4652
4667
|
children: [title, expandable && /* @__PURE__ */ (0, react_jsx_runtime.jsx)("span", {
|
|
4653
4668
|
className: "ss-expandMark",
|
|
4654
4669
|
"aria-hidden": true,
|
|
4655
|
-
children:
|
|
4670
|
+
children: "▸"
|
|
4656
4671
|
})]
|
|
4657
4672
|
}),
|
|
4658
4673
|
/* @__PURE__ */ (0, react_jsx_runtime.jsx)("span", {
|
|
4659
4674
|
className: "ss-rowDesc",
|
|
4675
|
+
title: desc,
|
|
4660
4676
|
children: desc
|
|
4661
4677
|
}),
|
|
4662
4678
|
help && !expandable && /* @__PURE__ */ (0, react_jsx_runtime.jsxs)("span", {
|
|
@@ -4756,7 +4772,7 @@ Instruction-following style:
|
|
|
4756
4772
|
}),
|
|
4757
4773
|
/* @__PURE__ */ (0, react_jsx_runtime.jsx)("p", {
|
|
4758
4774
|
className: "ss-intro",
|
|
4759
|
-
children: "
|
|
4775
|
+
children: "插件级配置,全局生效,不依赖具体 CCC。点任一行展开设定;改动即时保存。"
|
|
4760
4776
|
}),
|
|
4761
4777
|
/* @__PURE__ */ (0, react_jsx_runtime.jsx)(Group, {
|
|
4762
4778
|
title: "访问",
|
|
@@ -4766,7 +4782,6 @@ Instruction-following style:
|
|
|
4766
4782
|
expandable: true,
|
|
4767
4783
|
open: openGateway,
|
|
4768
4784
|
onToggle: setOpenGateway,
|
|
4769
|
-
expandHint: "配置",
|
|
4770
4785
|
control: /* @__PURE__ */ (0, react_jsx_runtime.jsx)(Toggle, {
|
|
4771
4786
|
checked: gatewayOn,
|
|
4772
4787
|
onChange: (on) => toggle("gatewayEnabled", on)
|
|
@@ -4775,7 +4790,7 @@ Instruction-following style:
|
|
|
4775
4790
|
className: "ss-detailStack",
|
|
4776
4791
|
children: [/* @__PURE__ */ (0, react_jsx_runtime.jsx)("p", {
|
|
4777
4792
|
className: "ss-detailIntro",
|
|
4778
|
-
children: "
|
|
4793
|
+
children: "在 3081 端口另起一个监听,让外网/局域网经登录页访问本机 Web UI(3080 只监听本机)。\n· 登录:账号密码 + 可选 TOTP 第二因素\n· 白名单:登录后只看到名单内的工作区(留空 = 全部)\n· 改完立即生效,不用重启"
|
|
4779
4794
|
}), /* @__PURE__ */ (0, react_jsx_runtime.jsx)(AccountsEditor, { gatewayOn })]
|
|
4780
4795
|
})
|
|
4781
4796
|
}) })
|
|
@@ -4788,16 +4803,15 @@ Instruction-following style:
|
|
|
4788
4803
|
expandable: true,
|
|
4789
4804
|
open: openRebuild,
|
|
4790
4805
|
onToggle: setOpenRebuild,
|
|
4791
|
-
expandHint: "配置",
|
|
4792
4806
|
detail: /* @__PURE__ */ (0, react_jsx_runtime.jsxs)("div", {
|
|
4793
4807
|
className: "ss-detailStack",
|
|
4794
4808
|
children: [/* @__PURE__ */ (0, react_jsx_runtime.jsx)("p", {
|
|
4795
4809
|
className: "ss-detailIntro",
|
|
4796
|
-
children: "
|
|
4810
|
+
children: "上下文占用到阈值时,由模型调用 container_trajectory rebuild 原地清空重建。\n· 语义:丢弃当前会话 → 新建 → 注入「继续原 SESSION 的工作」\n· SESSION.md 原位不动,轨迹延续,上下文归零\n· 恒开、无总闸;要调敏感度只改下面的阈值"
|
|
4797
4811
|
}), /* @__PURE__ */ (0, react_jsx_runtime.jsx)(RowCard, {
|
|
4798
4812
|
title: "重建阈值",
|
|
4799
|
-
desc: "
|
|
4800
|
-
help: "
|
|
4813
|
+
desc: "上下文占用到该值(K token,默认 400)时提示重建",
|
|
4814
|
+
help: "重建触发阈值(K token,默认 400,范围 50~4000):\n· 上下文 projected tokens ≥ 阈值 × 1000 时提示\n· 绝对数值,与窗口大小无关\n· 调低更早触发,调高更晚触发",
|
|
4801
4815
|
control: /* @__PURE__ */ (0, react_jsx_runtime.jsx)("input", {
|
|
4802
4816
|
className: "ss-portInput",
|
|
4803
4817
|
type: "number",
|
|
@@ -4828,7 +4842,7 @@ Instruction-following style:
|
|
|
4828
4842
|
className: "ss-detailStack",
|
|
4829
4843
|
children: /* @__PURE__ */ (0, react_jsx_runtime.jsx)("p", {
|
|
4830
4844
|
className: "ss-detailIntro",
|
|
4831
|
-
children: "
|
|
4845
|
+
children: "你走开时,模型停下来又没人接话,会话就挂住;此机制代你回一句让它自己收束。\n· 收束:每轮给一个验证码,只有四种明确收束才放过 —— 干完了 / 已通知并停下等你 / 需确认但可自决(按最保守可逆的做并记理由)/ 撞上不可代批的事(立刻停并写待办)\n· 身份:代理消息自报「无人值守代理 · 非本人」,不会被当成你说的话\n· 不适用:有 CRO 唤醒程序的轨迹、对外面与微信桥会话、子代理会话\n· 默认关:它把「人」从回路里拿掉,失败是静默的 —— 只在要离开时才开"
|
|
4832
4846
|
})
|
|
4833
4847
|
})
|
|
4834
4848
|
}) })
|
|
@@ -4837,7 +4851,7 @@ Instruction-following style:
|
|
|
4837
4851
|
title: "外部能力",
|
|
4838
4852
|
children: [/* @__PURE__ */ (0, react_jsx_runtime.jsx)("li", { children: /* @__PURE__ */ (0, react_jsx_runtime.jsx)(RowCard, {
|
|
4839
4853
|
title: "Skiff 调试",
|
|
4840
|
-
desc: "Skiff
|
|
4854
|
+
desc: "Skiff 认知子集问答页(默认 3099,仅本机,实验性)",
|
|
4841
4855
|
expandable: true,
|
|
4842
4856
|
open: openSkiff,
|
|
4843
4857
|
onToggle: setOpenSkiff,
|
|
@@ -4859,7 +4873,7 @@ Instruction-following style:
|
|
|
4859
4873
|
}),
|
|
4860
4874
|
detail: /* @__PURE__ */ (0, react_jsx_runtime.jsx)("p", {
|
|
4861
4875
|
className: "ss-detailIntro",
|
|
4862
|
-
children: "Skiff
|
|
4876
|
+
children: "Skiff 认知子集角色的问答页,仅监听 127.0.0.1。\n· Skiff = 完整轨迹的任意子集(认知子集角色)\n· 先在 CCC 的 skiff.roles 里配角色,再用此页以角色身份问答\n· 实验性,人工启停,默认关"
|
|
4863
4877
|
})
|
|
4864
4878
|
}) }), /* @__PURE__ */ (0, react_jsx_runtime.jsx)("li", { children: /* @__PURE__ */ (0, react_jsx_runtime.jsx)(RowCard, {
|
|
4865
4879
|
title: "CRO(轨迹自编程唤起)",
|
|
@@ -4875,7 +4889,7 @@ Instruction-following style:
|
|
|
4875
4889
|
className: "ss-detailStack",
|
|
4876
4890
|
children: /* @__PURE__ */ (0, react_jsx_runtime.jsx)("p", {
|
|
4877
4891
|
className: "ss-detailIntro",
|
|
4878
|
-
children: "
|
|
4892
|
+
children: "轨迹目录下放一个 continuous-re-occurrence.ts,调度器每 5 分钟跑它一次,由这段程序决定要不要唤、何时唤、唤的时候说什么。\n· 程序文件在即启用,不必在此配置;本开关只是总闸\n· 关掉只停 CRO 阶段:定时唤醒(send-later)、即时投递(send-now)与唤醒表投递照常\n· 没有程序文件的轨迹本来就不参与"
|
|
4879
4893
|
})
|
|
4880
4894
|
})
|
|
4881
4895
|
}) })]
|
|
@@ -4883,8 +4897,8 @@ Instruction-following style:
|
|
|
4883
4897
|
/* @__PURE__ */ (0, react_jsx_runtime.jsxs)(Group, {
|
|
4884
4898
|
title: "工具",
|
|
4885
4899
|
children: [/* @__PURE__ */ (0, react_jsx_runtime.jsx)("li", { children: /* @__PURE__ */ (0, react_jsx_runtime.jsx)(RowCard, {
|
|
4886
|
-
title: "ACP 面(官方 ACP
|
|
4887
|
-
desc: "让标准 ACP 客户端(如 Agmente
|
|
4900
|
+
title: "ACP 面(官方 ACP,默认 3200)",
|
|
4901
|
+
desc: "让标准 ACP 客户端(如 Agmente)连进本机;每账户一枚 token 把关(默认关)",
|
|
4888
4902
|
expandable: true,
|
|
4889
4903
|
open: openAcpFace,
|
|
4890
4904
|
onToggle: setOpenAcpFace,
|
|
@@ -4896,7 +4910,7 @@ Instruction-following style:
|
|
|
4896
4910
|
className: "ss-detailStack",
|
|
4897
4911
|
children: [/* @__PURE__ */ (0, react_jsx_runtime.jsx)("p", {
|
|
4898
4912
|
className: "ss-detailIntro",
|
|
4899
|
-
children: "
|
|
4913
|
+
children: "把官方 @deepseek-ai/dsh-acp 挂进本进程,标准 ACP 客户端经 WebSocket 登入本机。\n· 与微信桥的关系:两者是入站通道的两个实现,每个 CCC 二选一(在 CCC 的 .opencode/serenity.json 里配 im.channel)。本开关只管端口开不开\n· 🔴 认证:本面绑 0.0.0.0,而 ACP 协议本身不做认证 ⇒ 由 ACC 在握手前用每账户一枚 token(localstore 键 IM_ACP_TOKEN_<账户ID>)把关;没配账户的 CCC 一律连不上\n· 账户在下面那张表里管(加设备/看指纹/轮换/删除),不必改 JSON 或手敲命令\n· ⚠️ 明文 ws:// ⇒ 局域网内可抓包;上公网必须走 wss + Cloudflare Access"
|
|
4900
4914
|
}), /* @__PURE__ */ (0, react_jsx_runtime.jsx)(AcpAccountsEditor, {})]
|
|
4901
4915
|
})
|
|
4902
4916
|
}) }), /* @__PURE__ */ (0, react_jsx_runtime.jsx)("li", { children: /* @__PURE__ */ (0, react_jsx_runtime.jsx)(RowCard, {
|
|
@@ -4913,14 +4927,14 @@ Instruction-following style:
|
|
|
4913
4927
|
className: "ss-detailStack",
|
|
4914
4928
|
children: /* @__PURE__ */ (0, react_jsx_runtime.jsx)("p", {
|
|
4915
4929
|
className: "ss-detailIntro",
|
|
4916
|
-
children: "
|
|
4930
|
+
children: "agent 给一段标签式源码(<diagram> 根 + <rect>/<arrow>/<text>/<color>/<legend>),由 ACC 在进程内画成图并贴进对话 —— 不启浏览器、不截图。\n· 产物:图进对话记录(可回看、可被后续轮次引用、可转微信);另落两份文件在 CCC 的 _tmp/diagram/(.svg 可读可改 / .png 是进对话的那份)\n· 自带体检:重叠块 / 标签溢出 / 悬空端点 / 线压字,四条只告警不拦图;写错的图元被跳过并逐条报错,其余照画\n· 字体随插件内置(约 3.8 MB),因为光栅化引擎看不见系统字体\n· 默认关;关着时工具根本不注册(模型看不到它,不占上下文)\n· 前提:当前模型路由要声明收图像输入。没声明时图照样画、照样落盘,回执里写明原因并给路径"
|
|
4917
4931
|
})
|
|
4918
4932
|
})
|
|
4919
4933
|
}) })]
|
|
4920
4934
|
}),
|
|
4921
4935
|
/* @__PURE__ */ (0, react_jsx_runtime.jsx)(Collapse, {
|
|
4922
4936
|
title: "彩蛋模式",
|
|
4923
|
-
desc: "
|
|
4937
|
+
desc: "替换输出风格提示词(默认关闭)",
|
|
4924
4938
|
children: /* @__PURE__ */ (0, react_jsx_runtime.jsx)(PersonaEditor, {})
|
|
4925
4939
|
}),
|
|
4926
4940
|
/* @__PURE__ */ (0, react_jsx_runtime.jsx)(Collapse, {
|
|
@@ -4930,7 +4944,7 @@ Instruction-following style:
|
|
|
4930
4944
|
}),
|
|
4931
4945
|
/* @__PURE__ */ (0, react_jsx_runtime.jsx)(Collapse, {
|
|
4932
4946
|
title: "会话清理",
|
|
4933
|
-
desc: "
|
|
4947
|
+
desc: "删除 N 天前无活动的 DSH 会话(手动,不可恢复)",
|
|
4934
4948
|
children: /* @__PURE__ */ (0, react_jsx_runtime.jsx)(SessionCleanupBlock, {})
|
|
4935
4949
|
})
|
|
4936
4950
|
]
|
|
@@ -5002,7 +5016,7 @@ Instruction-following style:
|
|
|
5002
5016
|
/* @__PURE__ */ (0, react_jsx_runtime.jsx)(RowCard, {
|
|
5003
5017
|
title: "删除前无活动天数",
|
|
5004
5018
|
desc: "删除最后活动早于该天数的 DSH 会话(默认 30)",
|
|
5005
|
-
help: "
|
|
5019
|
+
help: "删除「最后活动早于 N 天前」的 DSH 会话(对话历史)。\n· lastActive = 会话日志文件最后写入时间(日志只追加,mtime 可靠)\n· 正在运行的会话不会被删(服务端强制跳过)\n· 物理删除不可恢复 —— 先「预览」核列表再执行",
|
|
5006
5020
|
control: /* @__PURE__ */ (0, react_jsx_runtime.jsx)("input", {
|
|
5007
5021
|
className: "ss-portInput",
|
|
5008
5022
|
type: "number",
|