Files
Arcrun/console-ui/public/portal/index.html
T
uncle6me-web 47d90c9feb fix: portal 登入頁 lockup 換裁淨版 PNG,字太小問題修正
同 rag/install 問題:官方 PNG 畫布 1840x560 只有 32% 高度是實際字形,
height:44px 時實際字高僅約 14px。改用裁淨版(493x88,長寬比 5.604:1,
四邊已裁到字腔邊緣),height 保持 44px 不變,但現在等於實際字高。

兩處 <div class="brand"> 各兩張圖(wm-ink + wm-paper)全部換裝。

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-01 16:02:30 +08:00

1783 lines
186 KiB
HTML
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
<!doctype html>
<html lang="zh-Hant">
<head>
<meta charset="utf-8"/>
<meta name="viewport" content="width=device-width, initial-scale=1">
<title>Arcrun Portal</title>
<link rel="icon" href="/favicon.svg" type="image/svg+xml">
<link rel="alternate icon" href="/favicon.ico" sizes="16x16 32x32 48x48">
<link rel="apple-touch-icon" href="/apple-touch-icon.png">
<script>
// 主題預載(防閃色):預設淺色,選擇存 localStorage(與 console 同設計語言、不同 key
document.documentElement.setAttribute('data-theme', (function () {
try { return localStorage.getItem('arcrun_portal_theme') === 'dark' ? 'dark' : 'light'; } catch (e) { return 'light'; }
})());
</script>
<style>
* { box-sizing: border-box; }
/* ── 主題色板(2026-08-01 CIS 第三輪:leo 親驗「Portal 裡的色彩都沒改」——
舊「宣紙米白紙紋+墨字+琥珀金」整套換成 Arcrun CIS token。
Ink #17181APaper #FDFCFBCanvas #F2F1EDMuted #9A978F
Relation #B04A2F(唯一強調色,≤5% 螢幕)/Relation-dark #D9784F(暗色底用)。
── */
:root {
--paper-a: #F2F1ED; --paper-b: #ECEAE4;
--ink: #17181A; --ink-rgb: 23,24,26;
--amber: #B04A2F; --amber-rgb: 176,74,47;
--ok: #1d7a48; --ok-rgb: 29,122,72; --ok-soft: #1d6b40;
--err: #b03a26; --err-rgb: 176,58,38;
--well: rgba(23,24,26,.06); --well2: rgba(23,24,26,.08);
--bar-bg: #ECEAE4; --track: rgba(23,24,26,.12); --knob: #FDFCFB;
}
:root[data-theme="dark"] {
--paper-a: #1b1c1e; --paper-b: #1e1f21;
--ink: #FDFCFB; --ink-rgb: 253,252,251;
--amber: #D9784F; --amber-rgb: 217,120,79;
--ok: #7fe0a8; --ok-rgb: 63,190,120; --ok-soft: #a8e8c4;
--err: #e58575; --err-rgb: 217,95,76;
--well: rgba(0,0,0,.25); --well2: rgba(0,0,0,.3);
--bar-bg: #17181A; --track: rgba(255,255,255,.08); --knob: #FDFCFB;
}
html, body { margin: 0; background: repeating-linear-gradient(0deg,var(--paper-a) 0px,var(--paper-a) 3px,var(--paper-b) 3px,var(--paper-b) 4px); color: var(--ink);
font-family: -apple-system, "PingFang TC", "Microsoft JhengHei", system-ui, sans-serif; font-size: 16px; -webkit-font-smoothing: antialiased; }
input, textarea, button { font-family: inherit; }
::placeholder { color: rgba(var(--ink-rgb),.35); }
input:focus { outline: 2px solid rgba(var(--amber-rgb),.5); outline-offset: 1px; }
a { color: var(--amber); }
.serif { font-family: 'Songti TC','LiSong Pro',PMingLiU,serif; }
.mono { font-family: ui-monospace, Menlo, monospace; }
.muted { color: rgba(var(--ink-rgb),.55); }
.dim { color: rgba(var(--ink-rgb),.4); }
.err { color: var(--err); }
.ok { color: var(--ok); }
/* ── auth 全屏(.view.on 的 block 會蓋 flex → 補 .authwrap.view.onconsole 同修)── */
.authwrap { min-height: 100vh; display: flex; align-items: center; justify-content: center; padding: 24px; }
.authbox { width: 100%; max-width: 400px; display: flex; flex-direction: column; gap: 24px; text-align: center; }
/* 08-01 緊急修正:登入頁品牌 lockup 改用官方 PNG(自產 SVG outline 字腔缺失作廢,
見 arcrun-cis/README.md 說明)。mark 不上色(NEVER 用 --amberRelation
當 logo 色——CIS:Relation 是「唯一強調色」不是品牌色,logo 上色是一句謊話),
靠兩張圖(-ink-paper-on-ink)依 data-theme 切換,不用 filter 避免色偏。
08-01 二次修正:官方原始 PNG1840x560)畫布只有 32% 高度是實際字形(上下大留白),
height:44px 時實際字高僅約 14px,看起來過小。改用裁淨版(493x88,長寬比 5.604:1
四邊已裁到字腔邊緣無留白),此時 height:44px=實際字高 44px。 */
.brand { display: flex; justify-content: center; }
.brand img { height: 44px; width: auto; display: block; }
.brand .wm-paper { display: none; }
:root[data-theme="dark"] .brand .wm-ink { display: none; }
:root[data-theme="dark"] .brand .wm-paper { display: block; }
.brand-sub { margin-top: 10px; font-size: 15px; color: rgba(var(--ink-rgb),.55); letter-spacing: .1em; }
/* ── 版面骨架 ── */
#shell { display: none; min-height: 100vh; }
#shell.on { display: flex; }
#sidenav { display: none; }
main { flex: 1; min-width: 0; padding-bottom: 96px; }
.page { max-width: 980px; margin: 0 auto; padding: 0 20px 40px; }
.page.narrow { max-width: 760px; }
.pagehead { padding: 22px 2px 14px; border-bottom: 2px solid rgba(var(--amber-rgb),.4); display: flex; justify-content: space-between; align-items: baseline; gap: 10px; }
.pagehead .t { font-family: 'Songti TC','LiSong Pro',PMingLiU,serif; font-size: 23px; letter-spacing: .2em; white-space: nowrap; }
.pagehead .m { font-size: 13.5px; color: rgba(var(--ink-rgb),.45); }
#tabbar { position: fixed; left: 0; right: 0; bottom: 0; background: var(--bar-bg); border-top: 2px solid rgba(var(--amber-rgb),.4); display: none; z-index: 50; padding-bottom: env(safe-area-inset-bottom); }
#tabbar.on { display: flex; }
#tabbar .tab { flex: 1; text-align: center; padding: 15px 0 13px; font-size: 14.5px; cursor: pointer; min-height: 44px; color: rgba(var(--ink-rgb),.5); border-top: 2px solid transparent; margin-top: -2px; }
#tabbar .tab.on { color: var(--amber); font-weight: 600; border-top-color: var(--amber); }
#tabbar .tab.hide { display: none; }
@media (min-width: 1024px) {
#tabbar.on { display: none; }
main { padding-bottom: 20px; }
#sidenav { display: flex; width: 216px; flex: none; position: sticky; top: 0; height: 100vh; border-right: 2px solid rgba(var(--amber-rgb),.35); padding: 28px 0; flex-direction: column; gap: 4px; }
#sidenav .logo { display: flex; color: var(--ink); padding: 0 24px 20px; }
#sidenav .logo svg { height: 26px; width: auto; display: block; }
#sidenav .nav { padding: 13px 24px; font-size: 16px; cursor: pointer; letter-spacing: .08em; color: rgba(var(--ink-rgb),.6); border-right: 2px solid transparent; }
#sidenav .nav.on { color: var(--amber); background: rgba(var(--amber-rgb),.08); border-right-color: var(--amber); font-family: 'Songti TC','LiSong Pro',PMingLiU,serif; font-weight: 600; }
#sidenav .nav.hide { display: none; }
#sidenav .foot { margin-top: auto; padding: 0 24px; font-size: 12.5px; color: rgba(var(--ink-rgb),.35); line-height: 1.7; }
}
.view { display: none; }
.view.on { display: block; }
.authwrap.view.on { display: flex; }
/* ── 元件 ── */
.btn { padding: 13px; font-size: 16px; font-weight: 600; border-radius: 10px; border: none; background: var(--amber); color: #FDFCFB; cursor: pointer; }
.btn:disabled { opacity: .45; cursor: default; }
.btn3 { padding: 11px 16px; font-size: 15px; border-radius: 10px; border: 1px solid rgba(var(--ink-rgb),.25); background: none; color: rgba(var(--ink-rgb),.7); cursor: pointer; }
.txt { width: 100%; padding: 13px 15px; font-size: 16px; border-radius: 10px; border: 1px solid rgba(var(--ink-rgb),.2); background: rgba(var(--ink-rgb),.05); color: var(--ink); }
.panel { padding: 18px; border-radius: 13px; background: rgba(var(--ink-rgb),.04); border: 1px solid rgba(var(--ink-rgb),.12); }
.tag { display: inline-block; padding: 3px 9px; border-radius: 5px; background: rgba(var(--amber-rgb),.12); color: var(--amber); font-size: 12.5px; }
.tag.green { background: rgba(var(--ok-rgb),.12); color: var(--ok); }
.tag.dim { background: rgba(var(--ink-rgb),.08); color: rgba(var(--ink-rgb),.55); }
.honest { padding: 22px; border-radius: 13px; border: 1px dashed rgba(var(--amber-rgb),.4); background: rgba(var(--amber-rgb),.06); text-align: center; }
.honest .h { font-family: 'Songti TC','LiSong Pro',PMingLiU,serif; font-size: 19px; color: var(--amber); margin-bottom: 8px; }
.honest .b { font-size: 15px; color: rgba(var(--ink-rgb),.6); line-height: 1.7; }
#toast { position: fixed; left: 50%; bottom: 110px; transform: translateX(-50%); z-index: 99; padding: 13px 22px; border-radius: 11px; background: var(--amber); color: #FDFCFB; font-size: 15.5px; font-weight: 600; box-shadow: 0 6px 24px rgba(0,0,0,.5); white-space: nowrap; display: none; }
/* ── 搜尋 ── */
.searchrow { display: flex; gap: 10px; align-items: stretch; }
.searchrow input { flex: 1; min-width: 0; padding: 16px 18px; font-size: 18px; border-radius: 13px; border: 1.5px solid rgba(var(--amber-rgb),.35); background: rgba(var(--ink-rgb),.05); color: var(--ink); }
.modebar { display: flex; gap: 8px; margin-top: 12px; }
.modebtn { flex: none; padding: 9px 18px; font-size: 14.5px; border-radius: 999px; cursor: pointer; border: 1px solid rgba(var(--ink-rgb),.18); background: none; color: rgba(var(--ink-rgb),.6); }
.modebtn.on { border-color: rgba(var(--amber-rgb),.6); background: rgba(var(--amber-rgb),.14); color: var(--amber); font-weight: 600; }
.modebtn.hide { display: none; }
.kgrid { display: grid; grid-template-columns: 1fr; gap: 12px; padding-bottom: 8px; }
@media (min-width: 700px) { .kgrid { grid-template-columns: repeat(auto-fill, minmax(300px, 1fr)); } }
.kcard { padding: 18px; border-radius: 13px; background: rgba(var(--ink-rgb),.045); border: 1px solid rgba(var(--ink-rgb),.1); cursor: pointer; display: flex; flex-direction: column; gap: 9px; }
.kcard:hover { border-color: rgba(var(--amber-rgb),.45); background: rgba(var(--amber-rgb),.06); }
.kcard .kt { font-family: 'Songti TC','LiSong Pro',PMingLiU,serif; font-size: 18.5px; font-weight: 600; line-height: 1.45; word-break: break-word; }
.kcard .ks { font-size: 15px; color: rgba(var(--ink-rgb),.65); line-height: 1.65; word-break: break-word; }
.kcard .km { display: flex; gap: 10px; align-items: center; margin-top: auto; font-size: 13px; flex-wrap: wrap; }
/* ── 卡片詳頁 ── */
.cardtitle { font-family: 'Songti TC','LiSong Pro',PMingLiU,serif; font-size: 28px; font-weight: 600; line-height: 1.4; word-break: break-word; }
.md { margin-top: 18px; }
.md p { font-size: 16.5px; line-height: 1.85; color: rgba(var(--ink-rgb),.82); margin: 8px 0; word-break: break-word; }
.md h1, .md h2, .md h3, .md h4 { font-family: 'Songti TC','LiSong Pro',PMingLiU,serif; font-weight: 600; color: var(--amber); margin: 18px 0 6px; line-height: 1.4; }
.md h1 { font-size: 22px; } .md h2 { font-size: 20px; } .md h3 { font-size: 18px; } .md h4 { font-size: 17px; }
.md ul, .md ol { margin: 8px 0; padding-left: 24px; }
.md li { font-size: 16.5px; line-height: 1.8; color: rgba(var(--ink-rgb),.82); margin: 4px 0; word-break: break-word; }
.md blockquote { margin: 10px 0; padding: 12px 18px; border-left: 3px solid rgba(var(--amber-rgb),.5); font-family: 'Songti TC','LiSong Pro',PMingLiU,serif; font-size: 17px; line-height: 1.8; color: rgba(var(--ink-rgb),.7); }
.md code { font-family: ui-monospace, Menlo, monospace; font-size: 14.5px; background: var(--well2); border-radius: 4px; padding: 1px 6px; word-break: break-all; }
.md pre { background: var(--well2); border: 1px solid rgba(var(--ink-rgb),.1); border-radius: 10px; padding: 14px; overflow-x: auto; }
.md pre code { background: none; padding: 0; }
.srcline { margin-top: 24px; display: flex; align-items: center; gap: 12px; padding: 14px 16px; border-radius: 11px; background: rgba(var(--ink-rgb),.045); border: 1px solid rgba(var(--ink-rgb),.12); }
/* ── graph 模式(console 關聯視圖同款)── */
.graphbox { position: relative; height: 340px; border-radius: 14px; background: var(--well); border: 1px solid rgba(var(--ink-rgb),.1); overflow: hidden; }
.gnode { position: absolute; transform: translate(-50%,-50%); max-width: 96px; padding: 8px 11px; border-radius: 999px; text-align: center; font-size: 12.5px; line-height: 1.3; cursor: pointer; word-break: break-word; background: rgba(var(--ok-rgb),.1); border: 1px solid rgba(var(--ok-rgb),.35); color: var(--ok-soft); }
.gcenter { position: absolute; left: 50%; top: 50%; transform: translate(-50%,-50%); width: 104px; height: 104px; border-radius: 50%; background: radial-gradient(circle at 36% 30%,rgba(217,120,79,.95),rgba(176,74,47,.9) 55%,rgba(120,45,25,.95)); display: grid; place-items: center; text-align: center; padding: 8px; box-shadow: 0 0 30px rgba(var(--amber-rgb),.3); }
.gcenter span { font-family: -apple-system,"PingFang TC","Microsoft JhengHei",system-ui,sans-serif; font-size: 13.5px; font-weight: 600; line-height: 1.35; color: #FDFCFB; word-break: break-word; }
.nbrow { display: flex; align-items: center; gap: 11px; padding: 12px 14px; border-radius: 10px; cursor: pointer; background: rgba(var(--ink-rgb),.045); border: 1px solid rgba(var(--ink-rgb),.1); font-size: 15.5px; }
/* 總圖(Arcrun#39 GUI 切片):沿用紙感語言——green 章印節點、amber 高度數節點 */
.mapbox { position: relative; border-radius: 14px; background: var(--well); border: 1px solid rgba(var(--ink-rgb),.1); overflow: hidden; }
.mapbox svg { display: block; width: 100%; height: auto; }
.mapnode { cursor: pointer; }
.mapnode circle { fill: rgba(var(--ok-rgb),.12); stroke: rgba(var(--ok-rgb),.45); stroke-width: 1.4; transition: stroke-width .15s; }
.mapnode.hub circle { fill: rgba(var(--amber-rgb),.2); stroke: rgba(var(--amber-rgb),.65); }
.mapnode:hover circle { stroke-width: 3; }
.mapnode text { font-size: 12.5px; fill: var(--ink); pointer-events: none; }
.mapedge { stroke: rgba(var(--ink-rgb),.18); stroke-width: 1; stroke-dasharray: 4 4; }
/* ── 管理頁(P4)── */
.sechead { font-family: 'Songti TC','LiSong Pro',PMingLiU,serif; font-size: 19px; letter-spacing: .14em; color: var(--amber); margin: 26px 0 12px; padding-bottom: 8px; border-bottom: 1px solid rgba(var(--amber-rgb),.3); }
.formrow { display: flex; gap: 10px; flex-wrap: wrap; }
.formrow .txt { flex: 1; min-width: 180px; }
.formrow select { padding: 12px 14px; font-size: 15.5px; border-radius: 10px; border: 1px solid rgba(var(--ink-rgb),.2); background: rgba(var(--ink-rgb),.05); color: var(--ink); }
.btnrow { display: flex; gap: 8px; flex-wrap: wrap; margin-top: 12px; }
.btn2 { padding: 9px 14px; font-size: 14px; border-radius: 9px; border: 1px solid rgba(var(--amber-rgb),.45); background: rgba(var(--amber-rgb),.08); color: var(--amber); cursor: pointer; }
.btn2.warn { border-color: rgba(var(--err-rgb),.45); background: rgba(var(--err-rgb),.06); color: var(--err); }
.btn2:disabled { opacity: .45; cursor: default; }
.libgrid { display: flex; gap: 8px 14px; flex-wrap: wrap; margin-top: 10px; }
.libgrid label { display: flex; align-items: center; gap: 7px; font-size: 14.5px; cursor: pointer; padding: 6px 10px; border-radius: 8px; background: rgba(var(--ink-rgb),.05); border: 1px solid rgba(var(--ink-rgb),.12); }
.libgrid input[type=checkbox] { accent-color: var(--amber); width: 16px; height: 16px; }
.otpbox { margin-top: 14px; padding: 18px; border-radius: 13px; border: 2px solid rgba(var(--amber-rgb),.55); background: rgba(var(--amber-rgb),.08); }
.otpbox .pw { font-family: ui-monospace, Menlo, monospace; font-size: 22px; letter-spacing: .12em; color: var(--amber); word-break: break-all; user-select: all; margin: 10px 0; }
/* ── 清單 / 設定 ── */
.listcol { display: flex; flex-direction: column; gap: 10px; padding: 16px 0 8px; }
.card-item { border-radius: 13px; background: rgba(var(--ink-rgb),.045); border: 1px solid rgba(var(--ink-rgb),.1); padding: 16px 18px; }
.setcol { display: flex; flex-direction: column; gap: 14px; padding: 20px 0 40px; }
.switch { flex: none; margin-left: auto; width: 56px; height: 32px; border-radius: 999px; padding: 3px; background: rgba(var(--ink-rgb),.15); transition: background .25s; }
.switch.on { background: rgba(var(--ok-rgb),.5); }
.switch i { display: block; width: 26px; height: 26px; border-radius: 50%; background: var(--knob); box-shadow: 0 1px 3px rgba(0,0,0,.25); transition: transform .25s; }
.switch.on i { transform: translateX(24px); }
.kvline { display: flex; justify-content: space-between; gap: 12px; font-size: 15px; margin: 5px 0; }
</style>
<script src="/config.js"></script>
<script>window.ARCRUN_API_BASE = (window.ARCRUN_CONFIG && window.ARCRUN_CONFIG.apiBase) || "https://cypher.arcrun.dev";</script>
</head>
<body>
<!-- 登入(未登入只見這個殼;本頁不含任何資料)-->
<div class="authwrap view" id="v-login">
<div class="authbox">
<div>
<div class="brand" role="img" aria-label="Arcrun"><img class="wm-ink" src="data:image/png;base64,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" alt="arc>>run" width="493" height="88"><img class="wm-paper" src="data:image/png;base64,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" alt="arc>>run" width="493" height="88"></div>
<div class="brand-sub">知識入口・Portal</div>
</div>
<div style="display:flex;flex-direction:column;gap:12px;text-align:left">
<input type="email" id="login-email" class="txt" placeholder="Email" autocomplete="username" style="padding:15px 16px;font-size:17px;border-radius:11px">
<input type="password" id="login-password" class="txt" placeholder="密碼" autocomplete="current-password" style="padding:15px 16px;font-size:17px;border-radius:11px">
<button class="btn" id="login-submit" style="margin-top:6px;padding:15px;font-size:17px;letter-spacing:.2em">登入</button>
<div id="login-status" class="err" style="font-size:14px;min-height:1.2em"></div>
</div>
<div style="font-size:13.5px;color:rgba(var(--ink-rgb),.4);line-height:1.7">帳號由管理員發放。忘記密碼請聯絡管理員重設。</div>
<button class="btn3 themelabel" data-themetoggle style="align-self:center;padding:8px 16px;font-size:13.5px;border-radius:999px">☾ 切深色</button>
</div>
</div>
<!-- 首次設定(t49leo 07-25:一鍵安裝的用戶打開專屬網址,第一件事就是在這裡建帳號,
不再需要回安裝器那頁。auth-status 說 configured:false 才會出現。)-->
<div class="authwrap view" id="v-firstsetup">
<div class="authbox">
<div>
<div class="brand" role="img" aria-label="Arcrun"><img class="wm-ink" src="data:image/png;base64,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" alt="arc>>run" width="493" height="88"><img class="wm-paper" src="data:image/png;base64,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" alt="arc>>run" width="493" height="88"></div>
<div class="brand-sub">歡迎!先建立你的帳號</div>
</div>
<div style="display:flex;flex-direction:column;gap:12px;text-align:left">
<input type="email" id="fs-email" class="txt" placeholder="你的 Email" autocomplete="username" style="padding:15px 16px;font-size:17px;border-radius:11px">
<input type="password" id="fs-password" class="txt" placeholder="設定密碼(至少 8 碼)" autocomplete="new-password" style="padding:15px 16px;font-size:17px;border-radius:11px">
<input type="password" id="fs-password2" class="txt" placeholder="再輸入一次密碼" autocomplete="new-password" style="padding:15px 16px;font-size:17px;border-radius:11px">
<button class="btn" id="fs-submit" style="margin-top:6px;padding:15px;font-size:17px;letter-spacing:.12em">建立帳號並進入</button>
<div id="fs-status" class="err" style="font-size:14px;min-height:1.2em"></div>
<!-- leo 07-25 實撞:已設定過(409)時這頁是死路——必須有回登入的路 -->
<button class="btn3" id="fs-tologin" style="padding:9px 16px;font-size:14px;border-radius:999px;align-self:center;cursor:pointer">已經有帳號?改用登入</button>
</div>
<div style="font-size:13.5px;color:rgba(var(--ink-rgb),.4);line-height:1.7">這組帳密就是之後登入知識庫用的,只需要設定這一次。</div>
</div>
</div>
<!-- 主應用 -->
<div id="shell">
<div id="sidenav">
<div class="logo" role="img" aria-label="Arcrun"><svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 3505.00 597.32" role="img" aria-label="arc double-chevron run"><title>arc double-chevron run</title><path fill="currentColor" fill-rule="nonzero" d="M2815.02,477.56 L2813.39,481.43 L2811.68,485.26 L2809.88,489.03 L2807.98,492.76 L2805.99,496.43 L2803.92,500.06 L2801.76,503.63 L2799.50,507.16 L2797.14,510.62 L2794.66,514.02 L2792.06,517.34 L2789.34,520.60 L2786.50,523.78 L2783.54,526.90 L2780.46,529.94 L2777.26,532.92 L2773.94,535.82 L2770.50,538.66 L2766.93,541.40 L2763.22,544.02 L2759.37,546.52 L2755.38,548.90 L2751.25,551.16 L2746.98,553.30 L2742.57,555.32 L2738.02,557.22 L2733.33,559.00 L2728.50,560.66 L2723.53,562.18 L2718.40,563.54 L2713.12,564.74 L2707.70,565.78 L2702.12,566.66 L2696.40,567.38 L2690.53,567.94 L2684.50,568.34 L2678.32,568.58 L2672.00,568.66 L2656.18,568.13 L2641.12,566.54 L2626.82,563.89 L2613.28,560.18 L2600.50,555.41 L2588.48,549.58 L2577.22,542.69 L2566.72,534.74 L2556.98,525.73 L2548.00,515.66 L2539.83,504.61 L2532.52,492.66 L2526.07,479.81 L2520.48,466.06 L2515.75,451.41 L2511.88,435.86 L2508.87,419.41 L2506.72,402.06 L2505.43,383.81 L2505.00,364.66 L2505.00,34.66 L2633.00,34.66 L2633.00,351.66 L2633.21,362.20 L2633.84,372.24 L2634.89,381.76 L2636.36,390.78 L2638.25,399.28 L2640.56,407.28 L2643.29,414.76 L2646.44,421.74 L2650.01,428.20 L2654.00,434.16 L2658.45,439.57 L2663.40,444.42 L2668.85,448.69 L2674.80,452.40 L2681.25,455.53 L2688.20,458.10 L2695.65,460.09 L2703.60,461.52 L2712.05,462.37 L2721.00,462.66 L2724.80,462.61 L2728.58,462.46 L2732.36,462.21 L2736.12,461.86 L2739.88,461.41 L2743.62,460.86 L2747.36,460.21 L2751.08,459.46 L2754.80,458.61 L2758.50,457.66 L2762.16,456.60 L2765.72,455.44 L2769.19,454.16 L2772.58,452.78 L2775.88,451.28 L2779.08,449.68 L2782.20,447.96 L2785.22,446.14 L2788.15,444.20 L2791.00,442.16 L2793.75,440.01 L2796.40,437.76 L2798.95,435.41 L2801.40,432.96 L2803.75,430.41 L2806.00,427.76 L2808.15,425.01 L2810.20,422.16 L2812.15,419.21 L2814.00,416.16 L2815.71,413.00 L2817.24,409.74 L2818.59,406.36 L2819.76,402.88 L2820.75,399.28 L2821.56,395.58 L2822.19,391.76 L2822.64,387.84 L2822.91,383.80 L2823.00,379.66 L2823.00,34.66 L2951.00,34.66 L2951.00,556.66 L2823.00,556.66 L2823.00,469.66 L2818.00,469.66 L2816.55,473.63 L2815.02,477.56 Z M1417.34,516.00 L1634.68,298.66 L1417.34,81.32 L1498.66,0.00 L1797.32,298.66 L1498.66,597.32 L1417.34,516.00 Z M1675.34,516.00 L1892.68,298.66 L1675.34,81.32 L1756.66,0.00 L2055.32,298.66 L1756.66,597.32 L1675.34,516.00 Z M397.38,554.45 L390.20,552.74 L383.38,550.53 L376.90,547.84 L370.78,544.65 L365.00,540.98 L359.57,536.81 L354.50,532.16 L349.79,527.09 L345.44,521.70 L341.46,515.97 L337.86,509.92 L334.62,503.53 L331.76,496.82 L329.26,489.77 L327.14,482.40 L325.38,474.69 L324.00,466.66 L318.00,466.66 L315.13,476.60 L311.72,486.04 L307.77,494.96 L303.28,503.38 L298.25,511.28 L292.68,518.68 L286.57,525.56 L279.92,531.94 L272.73,537.80 L265.00,543.16 L256.81,548.00 L248.24,552.34 L239.29,556.16 L229.96,559.48 L220.25,562.28 L210.16,564.58 L199.69,566.36 L188.84,567.64 L177.61,568.40 L166.00,568.66 L150.37,568.24 L135.48,566.98 L121.33,564.88 L107.92,561.94 L95.25,558.16 L83.32,553.54 L72.13,548.08 L61.68,541.78 L51.97,534.64 L43.00,526.66 L34.83,517.98 L27.52,508.74 L21.07,498.94 L15.48,488.58 L10.75,477.66 L6.88,466.18 L3.87,454.14 L1.72,441.54 L0.43,428.38 L0.00,414.66 L0.58,398.87 L2.32,383.92 L5.22,369.79 L9.28,356.50 L14.50,344.03 L20.88,332.40 L28.42,321.59 L37.12,311.62 L46.98,302.47 L58.00,294.16 L70.09,286.65 L83.16,279.94 L97.21,274.01 L112.24,268.88 L128.25,264.53 L145.24,260.98 L163.21,258.21 L182.16,256.24 L202.09,255.05 L223.00,254.66 L312.00,254.66 L312.00,216.66 L311.77,208.06 L311.08,199.86 L309.93,192.06 L308.32,184.66 L306.25,177.66 L303.72,171.06 L300.73,164.86 L297.28,159.06 L293.37,153.66 L289.00,148.66 L284.12,144.10 L278.68,140.02 L272.68,136.42 L266.12,133.30 L259.00,130.66 L251.32,128.50 L243.08,126.82 L234.28,125.62 L224.92,124.90 L215.00,124.66 L206.17,124.85 L197.70,125.44 L189.57,126.41 L181.80,127.78 L174.38,129.53 L167.30,131.68 L160.57,134.21 L154.20,137.14 L148.18,140.45 L142.50,144.16 L137.09,148.13 L131.84,152.26 L126.76,156.53 L121.86,160.96 L117.12,165.53 L112.56,170.26 L108.16,175.13 L103.94,180.16 L99.88,185.33 L96.00,190.66 L20.00,122.66 L25.99,113.83 L32.36,105.36 L39.11,97.23 L46.24,89.46 L53.75,82.03 L61.64,74.96 L69.91,68.23 L78.56,61.86 L87.59,55.83 L97.00,50.16 L106.91,44.93 L117.44,40.26 L128.59,36.13 L140.36,32.56 L152.75,29.53 L165.76,27.06 L179.39,25.13 L193.64,23.76 L208.51,22.93 L224.00,22.66 L244.69,23.14 L264.36,24.58 L283.01,26.98 L300.64,30.34 L317.25,34.66 L332.84,39.94 L347.41,46.18 L360.96,53.38 L373.49,61.54 L385.00,70.66 L395.45,80.68 L404.80,91.54 L413.05,103.24 L420.20,115.78 L426.25,129.16 L431.20,143.38 L435.05,158.44 L437.80,174.34 L439.45,191.08 L440.00,208.66 L440.00,454.66 L492.00,454.66 L492.00,556.66 L421.00,556.66 L412.78,556.41 L404.90,555.68 L397.38,554.45 Z M684.00,142.66 L689.00,142.66 L690.06,138.47 L691.22,134.32 L692.50,130.19 L693.88,126.10 L695.38,122.03 L696.98,118.00 L698.69,113.99 L700.52,110.02 L702.46,106.07 L704.50,102.16 L706.66,98.30 L708.96,94.54 L711.38,90.86 L713.94,87.28 L716.62,83.78 L719.44,80.38 L722.38,77.06 L725.46,73.84 L728.66,70.70 L732.00,67.66 L735.47,64.72 L739.06,61.90 L742.78,59.20 L746.64,56.62 L750.62,54.16 L754.74,51.82 L758.99,49.60 L763.36,47.50 L767.87,45.52 L772.50,43.66 L777.27,41.95 L782.20,40.42 L787.27,39.07 L792.50,37.90 L797.88,36.91 L803.40,36.10 L809.08,35.47 L814.90,35.02 L820.88,34.75 L827.00,34.66 L855.00,34.66 L855.00,155.66 L815.00,155.66 L802.32,155.85 L790.28,156.42 L778.88,157.37 L768.12,158.70 L758.00,160.41 L748.52,162.50 L739.68,164.97 L731.48,167.82 L723.92,171.05 L717.00,174.66 L710.73,178.70 L705.12,183.22 L700.17,188.22 L695.88,193.70 L692.25,199.66 L689.28,206.10 L686.97,213.02 L685.32,220.42 L684.33,228.30 L684.00,236.66 L684.00,556.66 L556.00,556.66 L556.00,34.66 L684.00,34.66 L684.00,142.66 Z M1081.37,566.95 L1070.68,565.62 L1060.25,563.91 L1050.08,561.82 L1040.17,559.35 L1030.52,556.50 L1021.13,553.27 L1012.00,549.66 L1003.14,545.69 L994.58,541.38 L986.30,536.73 L978.32,531.74 L970.62,526.41 L963.22,520.74 L956.11,514.73 L949.28,508.38 L942.75,501.69 L936.50,494.66 L930.54,487.31 L924.88,479.68 L919.50,471.75 L914.42,463.54 L909.62,455.03 L905.12,446.24 L900.90,437.15 L896.98,427.78 L893.35,418.11 L890.00,408.16 L886.96,397.93 L884.24,387.46 L881.84,376.73 L879.76,365.76 L878.00,354.53 L876.56,343.06 L875.44,331.33 L874.64,319.36 L874.16,307.13 L874.00,294.66 L874.16,282.19 L874.64,269.98 L875.44,258.03 L876.56,246.34 L878.00,234.91 L879.76,223.74 L881.84,212.83 L884.24,202.18 L886.96,191.79 L890.00,181.66 L893.35,171.80 L896.98,162.24 L900.90,152.96 L905.12,143.98 L909.62,135.28 L914.42,126.88 L919.50,118.76 L924.88,110.94 L930.54,103.40 L936.50,96.16 L942.75,89.22 L949.28,82.62 L956.11,76.34 L963.22,70.40 L970.62,64.78 L978.32,59.50 L986.31,54.54 L994.58,49.92 L1003.14,45.62 L1012.00,41.66 L1021.13,38.05 L1030.52,34.82 L1040.17,31.97 L1050.08,29.50 L1060.25,27.41 L1070.68,25.70 L1081.37,24.37 L1092.32,23.42 L1103.53,22.85 L1115.00,22.66 L1130.53,23.01 L1145.50,24.06 L1159.92,25.81 L1173.80,28.26 L1187.12,31.41 L1199.90,35.26 L1212.12,39.81 L1223.80,45.06 L1234.92,51.01 L1245.50,57.66 L1255.52,64.93 L1264.96,72.74 L1273.84,81.09 L1282.14,89.98 L1289.88,99.41 L1297.04,109.38 L1303.63,119.89 L1309.66,130.94 L1315.12,142.53 L1320.00,154.66 L1215.00,201.66 L1213.05,195.17 L1210.78,188.92 L1208.20,182.89 L1205.32,177.10 L1202.12,171.53 L1198.62,166.20 L1194.81,161.09 L1190.68,156.22 L1186.24,151.57 L1181.50,147.16 L1176.42,143.07 L1171.00,139.42 L1165.22,136.19 L1159.10,133.40 L1152.62,131.03 L1145.80,129.10 L1138.62,127.59 L1131.10,126.52 L1123.22,125.87 L1115.00,125.66 L1104.47,126.00 L1094.50,127.02 L1085.08,128.72 L1076.20,131.10 L1067.88,134.16 L1060.10,137.90 L1052.88,142.32 L1046.20,147.42 L1040.08,153.20 L1034.50,159.66 L1029.46,166.67 L1024.96,174.10 L1020.98,181.95 L1017.54,190.22 L1014.62,198.91 L1012.24,208.02 L1010.38,217.55 L1009.06,227.50 L1008.26,237.87 L1008.00,248.66 L1008.00,343.66 L1008.27,354.44 L1009.06,364.80 L1010.38,374.72 L1012.24,384.22 L1014.62,393.28 L1017.54,401.92 L1020.99,410.12 L1024.96,417.90 L1029.46,425.24 L1034.50,432.16 L1040.08,438.52 L1046.20,444.22 L1052.88,449.24 L1060.10,453.60 L1067.88,457.28 L1076.20,460.30 L1085.08,462.64 L1094.50,464.32 L1104.47,465.32 L1115.00,465.66 L1123.99,465.42 L1132.56,464.72 L1140.71,463.54 L1148.44,461.90 L1155.75,459.78 L1162.64,457.20 L1169.11,454.14 L1175.16,450.62 L1180.79,446.62 L1186.00,442.16 L1190.89,437.34 L1195.56,432.30 L1200.01,427.02 L1204.24,421.52 L1208.25,415.78 L1212.04,409.82 L1215.61,403.62 L1218.96,397.20 L1222.09,390.54 L1225.00,383.66 L1323.00,430.66 L1317.53,444.11 L1311.52,456.88 L1304.97,468.95 L1297.88,480.34 L1290.25,491.03 L1282.08,501.04 L1273.37,510.35 L1264.12,518.98 L1254.33,526.91 L1244.00,534.16 L1233.17,540.71 L1221.88,546.58 L1210.13,551.75 L1197.92,556.24 L1185.25,560.03 L1172.12,563.14 L1158.53,565.55 L1144.48,567.28 L1129.97,568.31 L1115.00,568.66 L1103.53,568.47 L1092.32,567.90 L1081.37,566.95 Z M2291.00,142.66 L2292.05,138.47 L2293.22,134.32 L2294.49,130.19 L2295.88,126.10 L2297.38,122.03 L2298.98,118.00 L2300.70,113.99 L2302.52,110.02 L2304.45,106.07 L2306.50,102.16 L2308.66,98.30 L2310.96,94.54 L2313.39,90.86 L2315.94,87.28 L2318.62,83.78 L2321.44,80.38 L2324.39,77.06 L2327.46,73.84 L2330.66,70.70 L2334.00,67.66 L2337.47,64.72 L2341.06,61.90 L2344.78,59.20 L2348.64,56.62 L2352.62,54.16 L2356.74,51.82 L2360.99,49.60 L2365.36,47.50 L2369.86,45.52 L2374.50,43.66 L2379.28,41.95 L2384.20,40.42 L2389.28,39.07 L2394.50,37.90 L2399.88,36.91 L2405.40,36.10 L2411.07,35.47 L2416.90,35.02 L2422.88,34.75 L2429.00,34.66 L2457.00,34.66 L2457.00,155.66 L2417.00,155.66 L2404.32,155.85 L2392.28,156.42 L2380.88,157.37 L2370.12,158.70 L2360.00,160.41 L2350.52,162.50 L2341.68,164.97 L2333.48,167.82 L2325.92,171.05 L2319.00,174.66 L2312.73,178.70 L2307.12,183.22 L2302.17,188.22 L2297.88,193.70 L2294.25,199.66 L2291.28,206.10 L2288.97,213.02 L2287.32,220.42 L2286.33,228.30 L2286.00,236.66 L2286.00,556.66 L2158.00,556.66 L2158.00,34.66 L2286.00,34.66 L2286.00,142.66 L2291.00,142.66 Z M3192.00,121.66 L3195.39,113.39 L3199.14,105.40 L3203.26,97.67 L3207.76,90.22 L3212.62,83.03 L3217.86,76.12 L3223.47,69.47 L3229.44,63.10 L3235.78,56.99 L3242.50,51.16 L3249.66,45.74 L3257.36,40.90 L3265.59,36.62 L3274.34,32.92 L3283.62,29.78 L3293.44,27.22 L3303.78,25.22 L3314.66,23.80 L3326.07,22.94 L3338.00,22.66 L3353.82,23.19 L3368.88,24.78 L3383.18,27.43 L3396.72,31.14 L3409.50,35.91 L3421.52,41.74 L3432.78,48.63 L3443.28,56.58 L3453.02,65.59 L3462.00,75.66 L3470.17,86.71 L3477.48,98.66 L3483.93,111.51 L3489.52,125.26 L3494.25,139.91 L3498.12,155.46 L3501.13,171.91 L3503.28,189.26 L3504.57,207.51 L3505.00,226.66 L3505.00,556.66 L3377.00,556.66 L3377.00,239.66 L3376.80,228.74 L3376.20,218.38 L3375.20,208.58 L3373.80,199.34 L3372.00,190.66 L3369.80,182.54 L3367.20,174.98 L3364.20,167.98 L3360.80,161.54 L3357.00,155.66 L3352.74,150.34 L3347.96,145.58 L3342.66,141.38 L3336.84,137.74 L3330.50,134.66 L3323.64,132.14 L3316.26,130.18 L3308.36,128.78 L3299.94,127.94 L3291.00,127.66 L3287.01,127.71 L3283.06,127.88 L3279.13,128.15 L3275.24,128.54 L3271.38,129.03 L3267.54,129.64 L3263.74,130.35 L3259.96,131.18 L3256.22,132.11 L3252.50,133.16 L3248.84,134.31 L3245.26,135.56 L3241.76,136.91 L3238.34,138.36 L3235.00,139.91 L3231.74,141.56 L3228.56,143.31 L3225.46,145.16 L3222.44,147.11 L3219.50,149.16 L3216.66,151.31 L3213.92,153.56 L3211.30,155.91 L3208.78,158.36 L3206.38,160.91 L3204.08,163.56 L3201.89,166.31 L3199.82,169.16 L3197.86,172.11 L3196.00,175.16 L3194.29,178.31 L3192.76,181.58 L3191.41,184.95 L3190.24,188.44 L3189.25,192.03 L3188.44,195.74 L3187.81,199.55 L3187.36,203.48 L3187.09,207.51 L3187.00,211.66 L3187.00,556.66 L3059.00,556.66 L3059.00,34.66 L3187.00,34.66 L3187.00,121.66 L3192.00,121.66 Z"/></svg></div>
<div class="nav" data-nav="search">搜尋</div>
<div class="nav hide" id="nav-map" data-nav="map">總圖</div>
<div class="nav hide" id="nav-upload" data-nav="upload">上傳</div>
<div class="nav hide" id="nav-workflows" data-nav="workflows">工作流</div>
<div class="nav hide" id="nav-admin" data-nav="admin">管理</div>
<div class="nav" data-nav="settings">設定</div>
<div class="nav themelabel" data-themetoggle style="margin-top:8px;font-size:14.5px">☾ 切深色</div>
<div class="foot" id="side-foot"></div>
</div>
<main>
<!-- 搜尋(落地頁)-->
<div class="view page" id="v-search">
<div class="pagehead"><span class="t">搜尋</span><span class="m" id="se-scope"></span></div>
<div style="padding-top:20px">
<div class="searchrow">
<input id="se-q" placeholder="搜尋知識…" autocomplete="off">
<button class="btn" id="se-go" style="flex:none;padding:0 22px;letter-spacing:.2em"></button>
</div>
<div class="modebar">
<button class="modebtn on" data-mode="keyword">關鍵字</button>
<button class="modebtn" data-mode="semantic">語意</button>
<button class="modebtn hide" id="mode-graph" data-mode="graph">圖譜</button>
</div>
<!-- AI 問答(portal-demo-suite)。設計哲學:AI 檢索=用戶手動搜尋同一套——
/portal/data/chat 與 /portal/data/search 走同一個 session 閘、同一個租戶資料面,
AI 只是代查再作答,不多開任何權限。此實例未安裝問答 workflow 時 server 誠實 404。-->
<div style="margin-top:14px;padding:14px;border-radius:13px;background:rgba(var(--amber-rgb),.05);border:1px solid rgba(var(--amber-rgb),.25)">
<div style="font-size:13.5px;letter-spacing:.1em;color:rgba(var(--ink-rgb),.5);margin-bottom:9px">AI 問答・答案附出處,可回搜尋驗證</div>
<div class="searchrow">
<input id="ai-q" placeholder="用一句話問知識庫…" autocomplete="off" style="padding:12px 15px;font-size:16px">
<button class="btn" id="ai-go" style="flex:none;padding:0 20px">問 AI</button>
</div>
<div id="ai-out"></div>
</div>
<div id="se-banner"></div>
<div id="se-count" style="margin:20px 0 12px;font-size:14px;color:rgba(var(--ink-rgb),.5)"></div>
<div class="kgrid" id="se-results"></div>
<div id="se-graphout" style="display:none">
<div id="gr-box"></div>
<div id="gr-edges" style="margin-top:16px;display:flex;flex-direction:column;gap:7px"></div>
</div>
</div>
</div>
<!-- 總圖(Arcrun#39 藏書地圖 GUI 切片;graph 粗閘後可見):全庫三元組一張網。
力導向佈局內聯手刻(demo 量級 ≤ 數百節點),不引外部套件(頁面自足原則)。-->
<div class="view page" id="v-map">
<div class="pagehead"><span class="t">總圖</span><span class="m" id="map-meta"></span></div>
<div style="padding-top:20px">
<div id="map-box"></div>
<div style="margin-top:12px;font-size:13.5px;color:rgba(var(--ink-rgb),.5)">
點節點可跳到該實體的圖譜搜尋。這張圖由知識庫的三元組即時算出——同一份地圖的文字版
(給 AI 注入用的總庫目錄)<span id="map-md-link"></span>
</div>
</div>
</div>
<!-- 卡片詳頁 -->
<div class="view page" id="v-card">
<div class="pagehead" style="justify-content:flex-start;gap:14px">
<button class="btn3" style="border:none;padding:0;font-size:16px;color:var(--amber)" data-nav="search"> 搜尋</button>
<span class="serif" style="font-size:17px;letter-spacing:.14em;color:rgba(var(--ink-rgb),.55)">知識卡片</span>
</div>
<div id="cd-main" style="padding:24px 0 40px"><div class="muted">載入中…</div></div>
</div>
<!-- 上傳(portal-demo-suiteupload bindings 齊全才顯示 nav——/portal/session 的
upload_enabled;藏只是 UX,真閘在 /portal/data/upload 路由層 404-->
<div class="view page narrow" id="v-upload">
<div class="pagehead"><span class="t">上傳</span><span class="m">Markdown / 純文字</span></div>
<div style="margin-top:16px;padding:13px 16px;border-radius:11px;background:rgba(var(--amber-rgb),.06);border:1px dashed rgba(var(--amber-rgb),.35);font-size:14px;line-height:1.7;color:rgba(var(--ink-rgb),.65)">
上傳的文件會進入知識庫收件管線:<b style="color:var(--ink)">約 1 分鐘後可在搜尋頁找到</b>;AI 整理後會以 wiki 卡形式出現。支援 .md / .txt(一律以 .md 收件)。
</div>
<div id="up-drop" style="margin-top:16px;padding:44px 20px;border-radius:13px;border:2px dashed rgba(var(--amber-rgb),.4);background:rgba(var(--amber-rgb),.04);text-align:center;cursor:pointer">
<div style="font-size:16px;color:rgba(var(--ink-rgb),.7)">把 .md / .txt 檔案拖放到這裡</div>
<div class="muted" style="margin-top:8px;font-size:14px"></div>
<button class="btn2" id="up-pick" style="margin-top:10px;padding:11px 22px;font-size:15px">選擇檔案(可多選)</button>
<input type="file" id="up-file" accept=".md,.txt" multiple style="display:none">
</div>
<div class="listcol" id="up-list"></div>
</div>
<!-- 工作流(D-8:預設 admin 才看得到;唯讀,不開 trigger-->
<div class="view page narrow" id="v-workflows">
<div class="pagehead"><span class="t">工作流</span><span class="m">唯讀・系統狀態</span></div>
<div style="margin-top:16px;padding:13px 16px;border-radius:11px;background:rgba(var(--amber-rgb),.06);border:1px dashed rgba(var(--amber-rgb),.35);font-size:14px;line-height:1.7;color:rgba(var(--ink-rgb),.65)">
此頁只顯示系統裡的工作流與最近執行狀態,<b style="color:var(--ink)">不能觸發執行</b>(觸發屬系統擁有者權限)。
</div>
<div class="listcol" id="wf-list"><div class="muted">載入中…</div></div>
</div>
<!-- 設定 -->
<div class="view page narrow" id="v-settings">
<div class="pagehead"><span class="t">設定</span></div>
<div class="setcol">
<div class="panel">
<div style="font-size:17px;font-weight:600;margin-bottom:10px">我的帳號</div>
<div id="st-me"><div class="muted">載入中…</div></div>
</div>
<div class="panel">
<div style="display:flex;align-items:center;gap:14px">
<div style="min-width:0">
<div style="font-size:17px;font-weight:600">深色模式</div>
<div style="margin-top:4px;font-size:14px;line-height:1.65;color:rgba(var(--ink-rgb),.55)">預設淺色(紙感)。切換立即生效,選擇記在這台裝置。</div>
</div>
<div class="switch" id="st-theme-switch" data-themetoggle style="cursor:pointer"><i></i></div>
</div>
</div>
<div class="panel">
<div style="font-size:17px;font-weight:600">更改密碼</div>
<div style="margin-top:4px;font-size:14px;color:rgba(var(--ink-rgb),.55)">需輸入舊密碼驗證身分;新密碼至少 8 碼</div>
<div style="margin-top:14px;display:flex;flex-direction:column;gap:10px">
<input type="password" id="st-pw-old" class="txt" placeholder="舊密碼" autocomplete="current-password">
<input type="password" id="st-pw-new" class="txt" placeholder="新密碼(至少 8 碼)" autocomplete="new-password">
<input type="password" id="st-pw-new2" class="txt" placeholder="再輸入一次新密碼" autocomplete="new-password">
<button class="btn" id="st-pw-save">更新密碼</button>
<div id="st-pw-status" style="font-size:14px;min-height:1.2em"></div>
</div>
</div>
<!-- 07-27 leo:金鑰與下載原本只在一次性的「還差 N 步」卡片裡,按了「稍後再說」
或裝完就再也找不到。換金鑰/換電腦重新下載都需要常駐入口,故搬進設定頁。 -->
<div class="panel">
<!-- t87 07-28 leo:乾淨網址(只有 origin,不含 /portal/# 後綴),供小幫手連線用 -->
<div style="display:flex;align-items:center;gap:8px;margin-bottom:14px;font-size:13.5px">
<span style="color:rgba(var(--ink-rgb),.6);white-space:nowrap">你的知識庫網址(小幫手連線用)</span>
<code id="st-origin-url" style="flex:1;overflow:hidden;text-overflow:ellipsis;white-space:nowrap;font-size:13px;color:var(--ink)"></code>
<button class="btn3" id="st-copy-url" style="padding:5px 12px;font-size:13px;white-space:nowrap;flex:none">複製</button>
</div>
<div style="font-size:17px;font-weight:600">同步小幫手</div>
<div style="margin-top:4px;font-size:14px;line-height:1.65;color:rgba(var(--ink-rgb),.55)">把你電腦上的資料夾變成知識庫。換電腦或重裝時可以再下載一次。</div>
<div style="margin-top:12px">
<a class="btn3" id="st-daemon-dl" href="#" style="display:inline-block;padding:11px 18px;border-radius:10px;text-decoration:none">下載 Mac 版</a>
<div style="margin-top:8px;font-size:13px;line-height:1.7;color:rgba(var(--ink-rgb),.5)">封測版未簽章,第一次請右鍵→打開。裝好第一次開啟時,貼上這個網址+你的帳號密碼就連上了。</div>
</div>
</div>
<!-- t131 合併 AI 設定(Gemini API Key 必填;Claude 加強版視 daemon 回報 enable -->
<div class="panel" id="st-ai-panel">
<div style="font-size:17px;font-weight:600">AI 設定</div>
<div style="margin-top:14px;display:flex;flex-direction:column;gap:16px">
<!-- 第一格:Gemini API Key(必填,聊天+萃取共用) -->
<div>
<div style="font-size:14px;font-weight:500;margin-bottom:4px">Gemini API Key</div>
<div style="font-size:13px;line-height:1.6;color:rgba(var(--ink-rgb),.55);margin-bottom:8px">聊天問答與文件萃取都用這一把。<a href="https://aistudio.google.com/apikey" target="_blank" rel="noopener">免費申請</a>,金鑰只存在你自己的知識庫裡。</div>
<input type="password" id="st-ai-key" class="txt" placeholder="貼上 Gemini API Key" autocomplete="off">
</div>
<!-- 第二格:Claude 加強版(選填,依 daemon 回報 enable -->
<div style="padding-top:12px;border-top:1px solid rgba(var(--ink-rgb),.08)">
<div style="font-size:14px;font-weight:500;margin-bottom:6px">讓知識卡整理得更好(選填)</div>
<label style="display:flex;gap:8px;align-items:flex-start;cursor:pointer">
<input type="checkbox" id="st-ai-use-claude" style="margin-top:3px;flex:none" disabled>
<span style="font-size:14px">本地萃取改用 Claude Code</span>
</label>
<div id="st-ai-claude-desc" style="margin-top:8px;font-size:13px;line-height:1.65;color:rgba(var(--ink-rgb),.55)">
讀你文件、整理成知識卡的那個 AI,換成更強的模型。<b style="color:var(--ink)">卡片會更抓得到重點、關聯也連得更準</b>,之後搜尋和問答的品質跟著提升。需要你的電腦已安裝 Claude Code。不填就用上面那把 Gemini,一樣能用。
</div>
<div id="st-ai-claude-hint" style="margin-top:6px;font-size:13px;color:rgba(var(--ink-rgb),.4);display:none"></div>
</div>
<div>
<button class="btn" id="st-ai-save">儲存 AI 設定</button>
<div id="st-ai-status" style="font-size:14px;min-height:1.2em;margin-top:8px"></div>
</div>
</div>
</div>
<button class="btn3" id="st-logout" style="padding:14px;font-size:16px;border-radius:11px">登出</button>
</div>
</div>
<!-- 管理(P4admin-onlynav 只有 admin 看得到;真閘在 /portal/admin/* role 閘 403-->
<div class="view page" id="v-admin">
<div class="pagehead"><span class="t">管理</span><span class="m">帳號與知識庫授權</span></div>
<div class="sechead">帳號管理</div>
<div class="panel">
<div style="font-size:16px;font-weight:600;margin-bottom:4px">新增同仁帳號</div>
<div style="font-size:13.5px;color:rgba(var(--ink-rgb),.55);margin-bottom:12px">建立後會產生一組一次性密碼——只顯示這一次,請當場轉交同仁(同仁可在「設定」自行改密)。</div>
<div class="formrow">
<input type="email" id="ad-nu-email" class="txt" placeholder="Email" autocomplete="off">
<input type="text" id="ad-nu-name" class="txt" placeholder="顯示名(可留空=用 Email" autocomplete="off">
<select id="ad-nu-role"><option value="user">一般用戶</option><option value="admin">管理員</option></select>
<button class="btn" id="ad-nu-create" style="flex:none;padding:0 20px">建立</button>
</div>
<div id="ad-nu-status" class="err" style="font-size:14px;min-height:1.2em;margin-top:8px"></div>
</div>
<div id="ad-otp"></div>
<div class="listcol" id="ad-users"><div class="muted">載入中…</div></div>
<div class="sechead">庫目錄管理</div>
<div style="display:flex;align-items:center;gap:8px;margin-bottom:10px;font-size:13.5px">
<span style="color:rgba(var(--ink-rgb),.6);white-space:nowrap">你的知識庫網址(小幫手連線用)</span>
<code id="ad-origin-url" style="flex:1;overflow:hidden;text-overflow:ellipsis;white-space:nowrap;font-size:13px;color:var(--ink)"></code>
<button class="btn3" id="ad-copy-url" style="padding:5px 12px;font-size:13px;white-space:nowrap;flex:none">複製</button>
</div>
<div style="margin-bottom:12px;padding:12px 15px;border-radius:11px;background:rgba(var(--amber-rgb),.06);border:1px dashed rgba(var(--amber-rgb),.35);font-size:13.5px;line-height:1.7;color:rgba(var(--ink-rgb),.65)">
<!-- 07-27 leo:拿掉「登記新庫」——庫由「同步小幫手」看守資料夾時自動蓋章產生,
人工登記只會製造對不上的空庫。這裡只做「已存在的庫」的管理。 -->
裝好<b style="color:var(--ink)">同步小幫手</b>並選好要看守的資料夾之後,每個資料夾會自動成為一個「庫」出現在下面——<b style="color:var(--ink)">不需要人工新增</b>。下面還是空的,代表小幫手還沒裝好或還沒選資料夾。
</div>
<div class="listcol" id="ad-libs"><div class="muted">載入中…</div></div>
</div>
</main>
</div>
<!-- 手機底部導覽 -->
<div id="tabbar">
<div class="tab" data-nav="search">搜尋</div>
<div class="tab hide" id="tab-map" data-nav="map">總圖</div>
<div class="tab hide" id="tab-upload" data-nav="upload">上傳</div>
<div class="tab hide" id="tab-workflows" data-nav="workflows">工作流</div>
<div class="tab hide" id="tab-admin" data-nav="admin">管理</div>
<div class="tab" data-nav="settings">設定</div>
</div>
<div id="toast"></div>
<script>
(function () {
var API_BASE = window.ARCRUN_API_BASE || '';
'use strict';
// 台北時間 helperlib/taipei-time.ts 注入,console 同套——顯示不隨裝置時區漂移)
var TAIPEI_OFFSET_MS = 28800000; // UTC+8,台北無 DST
function tpePad(n) { n = String(n); return n.length < 2 ? '0' + n : n; }
function taipeiDayKey(ms) { return new Date(ms + TAIPEI_OFFSET_MS).toISOString().slice(0, 10); }
function taipeiDateStr(ms) { return taipeiDayKey(ms); }
function taipeiDateTimeStr(ms) { var d = new Date(ms + TAIPEI_OFFSET_MS); return taipeiDayKey(ms) + ' ' + tpePad(d.getUTCHours()) + ':' + tpePad(d.getUTCMinutes()); }
function taipeiTimeStr(ms) { var d = new Date(ms + TAIPEI_OFFSET_MS); return tpePad(d.getUTCHours()) + ':' + tpePad(d.getUTCMinutes()) + ':' + tpePad(d.getUTCSeconds()); }
function taipeiMonthDay(ms) { var d = new Date(ms + TAIPEI_OFFSET_MS); return { month: d.getUTCMonth() + 1, day: d.getUTCDate() }; }
var $ = function (id) { return document.getElementById(id); };
// ── 狀態:只有 session token**沒有租戶字串、沒有 API key**design §3.3)──
var S = {
token: localStorage.getItem('arcrun_portal_session') || '',
profile: null, // /portal/session 回應(display_name/role/libraries/graph_allowed/workflows_visible
mode: 'keyword',
cardId: ''
};
function esc(s) {
return String(s == null ? '' : s).replace(/[&<>"']/g, function (c) {
return { '&': '&amp;', '<': '&lt;', '>': '&gt;', '"': '&quot;', "'": '&#39;' }[c];
});
}
function toast(msg) {
var el = $('toast');
el.textContent = msg;
el.style.display = 'block';
clearTimeout(toast._t);
toast._t = setTimeout(function () { el.style.display = 'none'; }, 2000);
}
// safeJson:把回應當 JSON 解析,**解析不了就回空物件而不是拋例外**(t75 ①,2026-07-28)。
//
// 為什麼需要:原本各處都直接 r.json(),但伺服器不一定回 JSON——404 頁、Cloudflare 錯誤頁、
// 反向代理的 HTML 都是純文字。JSON.parse 一爆,錯誤就沿著 .catch 走到 friendlyErr
// **技術訊息原文被噴到畫面上**。leo 同事實測看到的就是:
// 「Unexpected non-whitespace character after JSON at position 4」
// 真正的原因其實是 `/portal/admin/chat-key` 回 404(實例的 cypher 是舊版沒這端點),
// 但使用者只看得到一句看不懂的英文 ⇒ 無從判斷是自己打錯還是系統壞了。
function safeJson(r) {
return r.text().then(function (t) {
if (!t) return {};
try { return JSON.parse(t); } catch (e) { return {}; }
});
}
// friendlyErr:給使用者看的訊息,**不外洩技術細節**(t75 ①)。
// 原本最後一行是 `return m` =把任何例外訊息原樣顯示,包含 JSON parse 錯誤、
// stack 片段這種對使用者毫無意義、只會嚇到人的東西。
function friendlyErr(e) {
var m = e && e.message ? String(e.message) : String(e);
if (/failed to fetch|load failed|networkerror|network request failed/i.test(m)) return '連線中斷——請檢查網路後重試';
// JSON 解析類=伺服器回了非預期內容(多半是 404/代理錯誤頁),對使用者說人話。
if (/json|unexpected token|unexpected non-whitespace/i.test(m)) return '伺服器回應異常,請稍後再試一次(若持續發生請回報)';
// 其餘:只在含中文(=我們自己寫的訊息)時原樣顯示;純英文技術訊息一律收斂。
if (/[\u4e00-\u9fff]/.test(m)) return m;
return '操作失敗,請稍後再試一次';
}
function authHeaders() { return S.token ? { 'Authorization': 'Bearer ' + S.token } : {}; }
// ── 主題(console 同款,key 獨立)──
function getTheme() { return document.documentElement.getAttribute('data-theme') === 'dark' ? 'dark' : 'light'; }
function setTheme(t) {
document.documentElement.setAttribute('data-theme', t);
try { localStorage.setItem('arcrun_portal_theme', t); } catch (e) { /* 私密模式存不了 */ }
syncThemeUI();
}
function syncThemeUI() {
var dark = getTheme() === 'dark';
document.querySelectorAll('.themelabel').forEach(function (el) { el.textContent = dark ? '☀ 切淺色' : '☾ 切深色'; });
var sw = $('st-theme-switch');
if (sw) sw.classList.toggle('on', dark);
}
document.addEventListener('click', function (ev) {
var t = ev.target.closest('[data-themetoggle]');
if (t) setTheme(getTheme() === 'dark' ? 'light' : 'dark');
});
syncThemeUI();
// created_at 容錯(epoch 秒/毫秒/ISO),顯示一律台北時間(console 同款)
function parseAtMs(v) {
if (v == null || v === '') return null;
if (typeof v === 'number') return v < 1e12 ? v * 1000 : v;
if (/^\d+$/.test(v)) { var n = Number(v); return n < 1e12 ? n * 1000 : n; }
var s = /T/.test(v) ? v : String(v).replace(' ', 'T') + 'Z';
var ms = Date.parse(s);
return isNaN(ms) ? null : ms;
}
function fmtDate(v) { var ms = parseAtMs(v); return ms == null ? '' : taipeiDateStr(ms); }
function fmtDateTime(v) { var ms = parseAtMs(v); return ms == null ? '' : taipeiDateTimeStr(ms); }
// ── 極簡 Markdown 渲染(先全 escape 再上格式,防 XSSconsole 同款)──
function mdInline(s) {
return s
.replace(/\*\*([^*]+)\*\*/g, '<b>$1</b>')
.replace(/(^|[^\\])\x60([^\x60]+)\x60/g, '$1<code>$2</code>');
}
function mdRender(src) {
var lines = String(src || '').split(/\r?\n/);
var out = [], inCode = false, listMode = '';
function closeList() { if (listMode) { out.push(listMode === 'ul' ? '</ul>' : '</ol>'); listMode = ''; } }
for (var i = 0; i < lines.length; i++) {
var raw = lines[i];
if (/^\s*\x60\x60\x60/.test(raw)) {
closeList();
if (inCode) { out.push('</code></pre>'); inCode = false; }
else { out.push('<pre><code>'); inCode = true; }
continue;
}
if (inCode) { out.push(esc(raw) + '\n'); continue; }
var line = esc(raw);
var h = raw.match(/^(#{1,4})\s+(.*)$/);
if (h) { closeList(); out.push('<h' + h[1].length + '>' + mdInline(esc(h[2])) + '</h' + h[1].length + '>'); continue; }
if (/^\s*&gt;\s?/.test(line)) { closeList(); out.push('<blockquote>' + mdInline(line.replace(/^\s*&gt;\s?/, '')) + '</blockquote>'); continue; }
var li = raw.match(/^\s*[-*+]\s+(.*)$/);
if (li) { if (listMode !== 'ul') { closeList(); out.push('<ul>'); listMode = 'ul'; } out.push('<li>' + mdInline(esc(li[1])) + '</li>'); continue; }
var oli = raw.match(/^\s*\d+[.)]\s+(.*)$/);
if (oli) { if (listMode !== 'ol') { closeList(); out.push('<ol>'); listMode = 'ol'; } out.push('<li>' + mdInline(esc(oli[1])) + '</li>'); continue; }
if (/^\s*$/.test(raw)) { closeList(); continue; }
closeList();
out.push('<p>' + mdInline(line) + '</p>');
}
closeList();
if (inCode) out.push('</code></pre>');
return out.join('');
}
// ── entry 顯示 helperssource/library 從 metadata_json 取——server 已 enforce 過權限)──
function entryMeta(e) {
try { var m = JSON.parse(e.metadata_json || 'null'); return m && typeof m === 'object' ? m : {}; } catch (er) { return {}; }
}
function entrySource(e) { var m = entryMeta(e); return typeof m.source === 'string' ? m.source : ''; }
// 來源回溯超連結:PORTAL_SOURCE_WEB_BASE 有設且 source 是 gitea:// 才給 href
// 其餘回空字串=維持純文字(行為與未設時一字不變)。chunk 錨點(#n)捨棄。
var SOURCE_WEB_BASE = "";
function srcHref(src) {
if (!SOURCE_WEB_BASE || String(src).indexOf('gitea://') !== 0) return '';
var p = String(src).slice(8).replace(/#\d+$/, '');
return SOURCE_WEB_BASE.replace(/\/+$/, '') + '/' + p.split('/').map(encodeURIComponent).join('/');
}
function entryLib(e) { var m = entryMeta(e); return (typeof m.library === 'string' && m.library) ? m.library : 'general'; }
function entryTitle(e) {
if (e.page_name) return e.page_name;
var first = String(e.content || '').split(/\r?\n/).find(function (l) { return l.trim(); }) || '';
first = first.replace(/^#+\s*/, '').replace(/^[-*>]\s*/, '').trim();
if (first.length > 60) first = first.slice(0, 60) + '…';
return first || '(無標題・' + (e.entry_type || 'entry') + '';
}
function entrySnippet(e) {
var lines = String(e.content || '').split(/\r?\n/).filter(function (l) { return l.trim(); });
var body = lines.slice(1).join(' ').replace(/\s+/g, ' ').trim();
if (!body) body = lines.join(' ');
if (body.length > 140) body = body.slice(0, 140) + '…';
return body;
}
// ── 路由 ──
var VIEWS = ['search', 'map', 'card', 'upload', 'workflows', 'admin', 'settings'];
var HOME = 'search';
function allowedViews() {
// 工作流/管理/上傳頁按 session 能力顯示(真閘在 server/portal/data/workflows 403/404、
// /portal/admin/* role 閘 403、/portal/data/upload 未啟用 404——前端藏只是 UX,curl 直打也繞不過)
return VIEWS.filter(function (v) {
if (v === 'workflows') return !!(S.profile && S.profile.workflows_visible);
if (v === 'admin') return !!(S.profile && S.profile.role === 'admin');
if (v === 'upload') return !!(S.profile && S.profile.upload_enabled);
return true;
});
}
function currentRoute() {
var h = location.hash.replace(/^#\/?/, '');
var seg = h.split('/');
var ok = allowedViews();
return { raw: seg[0] || '', view: ok.indexOf(seg[0]) >= 0 ? seg[0] : HOME, arg: seg.slice(1).join('/') };
}
function nav(view, arg) {
location.hash = '#/' + view + (arg ? '/' + encodeURIComponent(arg) : '');
}
function showView(name) {
VIEWS.forEach(function (v) { $('v-' + v).classList.toggle('on', v === name); });
var activeKey = name === 'card' ? 'search' : name;
document.querySelectorAll('#sidenav .nav, #tabbar .tab').forEach(function (el) {
el.classList.toggle('on', el.getAttribute('data-nav') === activeKey);
});
window.scrollTo(0, 0);
}
var LOADERS = { card: loadCard, map: loadMap, workflows: loadWorkflows, admin: loadAdmin, settings: loadSettings };
function route() {
var r = currentRoute();
if (r.raw && r.raw !== r.view) { location.hash = '#/' + r.view; return; }
if (r.view === 'card' && r.arg) S.cardId = decodeURIComponent(r.arg);
showView(r.view);
if (LOADERS[r.view]) LOADERS[r.view]();
}
window.addEventListener('hashchange', route);
document.addEventListener('click', function (ev) {
var t = ev.target.closest('[data-nav]');
if (t) nav(t.getAttribute('data-nav'));
});
// ── 認證流 ──
function showAuth() {
$('v-firstsetup').classList.remove('on');
$('v-login').classList.add('on');
$('shell').classList.remove('on');
$('tabbar').classList.remove('on');
// t49:全新實例(還沒有任何帳號)→ 換顯示「首次設定」,不讓用戶對著登入殼發呆。
// 探測走 console/auth-statusconfigured 布林,console 首設同一顆;失敗就保持登入殼=誠實降級)。
fetch(API_BASE + '/console/auth-status')
.then(function (r) { return safeJson(r); })
.then(function (d) {
if (d && d.configured === false) {
$('v-login').classList.remove('on');
$('v-firstsetup').classList.add('on');
}
})
.catch(function () { /* 探測不到就維持登入殼 */ });
}
function showApp() {
$('v-login').classList.remove('on');
$('v-firstsetup').classList.remove('on');
$('shell').classList.add('on');
$('tabbar').classList.add('on');
// t53leo 07-25:「進站要做的事——給金鑰、下載 daemon——不然這個安裝沒完成」):
// 常駐「完成安裝」清單卡,三件做完才消失(localStorage 記進度;admin 才看得到——
// 金鑰與 daemon 設定是裝機者的事,同事帳號不顯示)。
try { renderSetupChecklist(); } catch (e) { /* 清單卡失敗不擋主流程 */ }
var p = S.profile || {};
$('side-foot').innerHTML = esc(p.display_name || '') + '<br>' + esc(location.host);
$('nav-workflows').classList.toggle('hide', !p.workflows_visible);
$('tab-workflows').classList.toggle('hide', !p.workflows_visible);
// 上傳 nav:一般用戶可見,但只在實例啟用上傳(bindings 齊全)時顯示(未啟用的實例零影響)
$('nav-upload').classList.toggle('hide', !p.upload_enabled);
$('tab-upload').classList.toggle('hide', !p.upload_enabled);
$('nav-admin').classList.toggle('hide', p.role !== 'admin');
$('tab-admin').classList.toggle('hide', p.role !== 'admin');
$('mode-graph').classList.toggle('hide', !p.graph_allowed);
$('nav-map').classList.toggle('hide', !p.graph_allowed);
$('tab-map').classList.toggle('hide', !p.graph_allowed);
var libs = p.libraries || [];
$('se-scope').textContent = libs.indexOf('*') >= 0 ? '範圍:全部知識庫' : ('範圍:' + libs.join('・'));
if (!location.hash) location.hash = '#/' + HOME;
route();
}
function dropSession() {
S.token = '';
S.profile = null;
try { localStorage.removeItem('arcrun_portal_session'); } catch (e) { /* noop */ }
showAuth();
}
function boot() {
if (!S.token) { showAuth(); return; }
fetch(API_BASE + '/portal/session', { headers: authHeaders() })
.then(function (r) { return safeJson(r).then(function (d) { return { ok: r.ok, status: r.status, d: d }; }); })
.then(function (x) {
if (!x.ok) { dropSession(); return; }
S.profile = x.d;
showApp();
})
.catch(function () {
// 斷網時不清 session(誠實:連不上 ≠ session 失效),顯示登入殼並提示
showAuth();
$('login-status').textContent = '連線中斷——請檢查網路後重新整理';
});
}
$('login-submit').addEventListener('click', doLogin);
$('login-password').addEventListener('keydown', function (ev) { if (ev.key === 'Enter') doLogin(); });
function doLogin() {
var email = $('login-email').value.trim();
var password = $('login-password').value;
if (!email || !password) { $('login-status').textContent = '請輸入 Email 與密碼'; return; }
$('login-submit').disabled = true;
$('login-status').textContent = '';
fetch(API_BASE + '/portal/login', {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({ email: email, password: password })
})
.then(function (r) { return safeJson(r).then(function (d) { return { ok: r.ok, status: r.status, d: d }; }); })
.then(function (x) {
$('login-submit').disabled = false;
if (!x.ok) { $('login-status').textContent = x.d.error || '登入失敗'; return; }
S.token = x.d.session_token;
try { localStorage.setItem('arcrun_portal_session', S.token); } catch (e) { /* 私密模式只活本次 */ }
$('login-password').value = '';
boot();
})
.catch(function (e) { $('login-submit').disabled = false; $('login-status').textContent = friendlyErr(e); });
}
// t72 OS 分流(2026-07-27leo:「客戶是用 windows 的」)——在此之前四處寫死「下載 Mac 版」,
// Windows 客戶按下去會拿到 Mac 的 .app=按了連到錯的東西(leo 判準:那不算友善)。
// 判不出 OS 時**兩個都給**,不替用戶猜;且無論判成哪個,頁面都留「不是這個系統?」的另一版連結
// ——UA 會判錯,判錯時用戶要有路可走(施工圖 §3 注意事項 1、3)。
var DAEMON_BASE_DEFAULT = 'https://raw.githubusercontent.com/youlinhsieh/arcrun-rag-bundles/main/daemon/';
var DAEMON_MAC = 'ArcrunRAG-mac-unsigned.zip';
var DAEMON_WIN = 'ArcrunRAG-win-unsigned.zip';
// Mac 那顆 21MB > jsDelivr 單檔 20MB 上限(實測回 "File size exceeded...")→ 一律走 raw
// Windows 13MB 雖在限內,同走 raw 保持單一來源、少一個會壞的地方。
function daemonBase() {
var cfg = (window.ARCRUN_CONFIG || {});
if (cfg.daemonBase) return String(cfg.daemonBase).replace(/\/?$/, '/');
// 舊 key 相容(施工圖 §3 注意事項 2):daemonDownload 是「單一檔案網址」,
// 有設就尊重它當 Mac 版網址,並由它推出目錄給 Windows 版用。
if (cfg.daemonDownload) {
var s = String(cfg.daemonDownload);
return s.slice(0, s.lastIndexOf('/') + 1) || DAEMON_BASE_DEFAULT;
}
return DAEMON_BASE_DEFAULT;
}
function daemonPick() {
var base = daemonBase();
var ua = navigator.userAgent || '';
// 手機/平板先排除:iOS 的 UA 含 "Mac OS X",不排除會把 iPhone 判成 Mac
// 讓手機用戶下載一個裝不起來的桌面 app(測到才發現,2026-07-27)。
// 手機=判不出桌面 OS → 落到「兩個都給」,用戶回桌機再選。
var isMobile = /iPhone|iPad|iPod|Android|Mobile/i.test(ua);
var isWin = !isMobile && /Windows NT/i.test(ua);
var isMac = !isMobile && /Macintosh|Mac OS X/i.test(ua) && !/Windows/i.test(ua);
var mac = { os: 'mac', label: '下載 Mac 版', url: base + DAEMON_MAC };
var win = { os: 'win', label: '下載 Windows 版', url: base + DAEMON_WIN };
if (isWin) return { pick: win, other: mac, sure: true };
if (isMac) return { pick: mac, other: win, sure: true };
return { pick: null, other: null, sure: false, mac: mac, win: win };
}
// 封測期第一次開啟的擋關提示(未簽章)——Mac/Windows 攔法不同,話術也不同。
function daemonHint(os) {
if (os === 'win') return '(封測版未簽章,Windows 第一次會跳藍色視窗擋下來——點「更多資訊」→「仍要執行」就好)';
return '(封測版未簽章,第一次請右鍵→打開)';
}
// 07-27:設定頁的常駐入口(下載小幫手/換 AI 金鑰)——與一次性卡片同一組 API
(function () {
var dl = $('st-daemon-dl');
if (dl) {
var d = daemonPick();
if (d.sure) {
dl.setAttribute('href', d.pick.url);
dl.textContent = d.pick.label;
// 判對了也要留另一版的路(UA 會判錯)
var alt = document.createElement('span');
alt.className = 'muted';
alt.style.cssText = 'font-size:12.5px;margin-left:8px';
alt.innerHTML = '不是這個系統?<a href="' + d.other.url + '">' + d.other.label + '</a>';
if (dl.parentNode) dl.parentNode.insertBefore(alt, dl.nextSibling);
} else {
// 判不出來=兩個都給,不預設 Mac
dl.setAttribute('href', d.mac.url);
dl.textContent = d.mac.label;
var both = document.createElement('span');
both.className = 'muted';
both.style.cssText = 'font-size:12.5px;margin-left:8px';
both.innerHTML = '或 <a href="' + d.win.url + '">' + d.win.label + '</a>';
if (dl.parentNode) dl.parentNode.insertBefore(both, dl.nextSibling);
}
}
})();
// t131 AI 設定(合併 Gemini API KeyClaude 加強版)
(function () {
// 進入設定頁時讀取現有設定(GET /portal/admin/ai
function loadAiConfig() {
if (!(S.profile && S.profile.role === 'admin')) return;
fetch(API_BASE + '/portal/admin/ai', { headers: authHeaders() })
.then(function (r) { return r.ok ? safeJson(r) : null; })
.then(function (d) {
if (!d) return;
var ki = $('st-ai-key');
if (ki && d.has_key) ki.placeholder = '已設定(留空=不變更)';
var cb = $('st-ai-use-claude');
if (cb) {
// 有 claude 才能勾;沒有則停用並顯示提示
var hint = $('st-ai-claude-hint');
if (d.claude_available) {
cb.disabled = false;
cb.checked = !!d.use_claude_for_extract;
if (hint) hint.style.display = 'none';
} else {
cb.disabled = true;
cb.checked = false;
if (hint) {
hint.style.display = '';
// 區分:從未連上小幫手 vs 有連上但沒裝 Claude
hint.textContent = d.has_key
? '你的電腦沒有偵測到 Claude Code;裝好並讓小幫手重連一次後,這個選項就會開啟。'
: '連上小幫手後才知道你的電腦有沒有 Claude Code。';
}
}
}
})
.catch(function () { /* 讀不到不擋頁面 */ });
}
window._loadAiConfig = loadAiConfig;
// 儲存
var sb = $('st-ai-save');
if (sb) sb.addEventListener('click', function () {
var m = $('st-ai-status');
var k = (($('st-ai-key') && $('st-ai-key').value) || '').trim();
var cb = $('st-ai-use-claude');
var useClaud = cb && !cb.disabled ? cb.checked : undefined;
var body = {};
if (k) body.gemini_api_key = k;
if (useClaud !== undefined) body.use_claude_for_extract = useClaud;
sb.disabled = true; m.textContent = '儲存中…'; m.style.color = '';
fetch(API_BASE + '/portal/admin/ai', {
method: 'POST',
headers: Object.assign({ 'Content-Type': 'application/json' }, authHeaders()),
body: JSON.stringify(body)
}).then(function (r) { return safeJson(r).then(function (d) { return { ok: r.ok, status: r.status, d: d }; }); })
.then(function (x) {
sb.disabled = false;
if (guard401(x.status)) return;
if (!x.ok) { m.textContent = (x.d && x.d.error) || '儲存失敗'; m.style.color = '#b03a26'; return; }
if ($('st-ai-key')) { $('st-ai-key').value = ''; $('st-ai-key').placeholder = '已設定(留空=不變更)'; }
var claudeOn = x.d && x.d.use_claude_for_extract;
m.textContent = claudeOn
? '已儲存,萃取改用 Claude Code。小幫手請重連一次生效。'
: '已儲存,AI 問答與萃取皆可使用。';
m.style.color = '#3f7a4f';
})
.catch(function (e) { sb.disabled = false; m.textContent = friendlyErr(e); m.style.color = '#b03a26'; });
});
})();
$('st-logout').addEventListener('click', function () {
fetch(API_BASE + '/portal/logout', { method: 'POST', headers: authHeaders() }).catch(function () { /* 盡力而為 */ });
dropSession();
});
// t87 07-28 leo:知識庫網址 helper(只有 origin,不含 /portal/# 後綴),兩處 UI 共用
function copyOriginUrl(btn) {
var url = location.origin;
var orig = btn.textContent;
if (!navigator.clipboard || !navigator.clipboard.writeText) {
alert('請手動選取並複製:' + url);
return;
}
navigator.clipboard.writeText(url).then(function () {
btn.textContent = '已複製';
setTimeout(function () { btn.textContent = orig; }, 1500);
}).catch(function () {
alert('請手動選取並複製:' + url);
});
}
(function () {
['st-origin-url', 'ad-origin-url'].forEach(function (id) {
var el = $(id); if (el) el.textContent = location.origin;
});
['st-copy-url', 'ad-copy-url'].forEach(function (id) {
var el = $(id); if (el) el.addEventListener('click', function () { copyOriginUrl(this); });
});
})();
// ── t53 完成安裝清單(進站必見,三件做完才消失)─────────────────────────────
function setupSteps() {
try { return JSON.parse(localStorage.getItem('arcrun_setup_steps') || '{}'); } catch (e) { return {}; }
}
function markStep(k) {
var s = setupSteps(); s[k] = 1;
try { localStorage.setItem('arcrun_setup_steps', JSON.stringify(s)); } catch (e) { /* noop */ }
renderSetupChecklist();
}
function renderSetupChecklist() {
var old = document.getElementById('setup-checklist');
if (old) old.remove();
var p = S.profile || {};
if (p.role !== 'admin') return;
var s = setupSteps();
if (s.daemon && s.key) return; // t54 起只剩兩件:設定改由小幫手輸入帳密自取,不再下載檔案
var cfg = window.ARCRUN_CONFIG || {};
var dpick = daemonPick(); // t72 OS 分流(同一組判定,見上面 daemonPick
var daemonUrl = dpick.sure ? dpick.pick.url : dpick.mac.url;
var row = function (done, id, html) {
return '<div style="display:flex;gap:10px;align-items:baseline;margin-top:10px">'
+ '<span>' + (done ? '✅' : '⬜') + '</span><div style="flex:1">' + html + '</div></div>';
};
var el = document.createElement('div');
el.id = 'setup-checklist';
el.style.cssText = 'position:fixed;right:20px;bottom:20px;z-index:60;max-width:400px;width:calc(100% - 40px);padding:18px 20px;border-radius:14px;background:rgba(var(--amber-rgb),.10);border:1px solid rgba(var(--amber-rgb),.45);backdrop-filter:blur(8px);font-size:14px;line-height:1.65';
el.innerHTML = '<b>還差 ' + (2 - (s.daemon?1:0) - (s.key?1:0)) + ' 步,安裝就真的完成了</b>'
+ row(s.daemon, 'daemon',
'<b>下載同步小幫手</b>(把資料夾變成知識庫)<br>'
+ (daemonUrl
// t72:按鈕字樣+擋關話術都跟著 OS 走;並且一律附「另一個系統」的連結
//(UA 判錯時用戶要有路走;判不出來時=兩個平等並列,不預設 Mac)
? '<a href="' + esc(daemonUrl) + '" id="sc-daemon">'
+ esc(dpick.sure ? dpick.pick.label : dpick.mac.label) + '</a>'
+ '<span class="muted" style="font-size:12.5px">'
+ esc(daemonHint(dpick.sure ? dpick.pick.os : 'mac')) + '</span>'
+ '<div class="muted" style="font-size:12.5px">'
+ (dpick.sure
? '不是這個系統?<a href="' + esc(dpick.other.url) + '">' + esc(dpick.other.label) + '</a>'
: '或 <a href="' + esc(dpick.win.url) + '">' + esc(dpick.win.label) + '</a>')
+ '</div>'
// 誠實降級(leo 判準:按了連到錯的機制=不友善):沒有可用下載點時
// 不放死連結,說明現況並讓這步可手動打勾,不卡住清單。
: '<span class="muted" style="font-size:13px">封測期由我們直接寄給你安裝檔;'
+ '收到後回來按 <a href="#" id="sc-daemon">我已經裝好了</a>。</span>')
// t54(leo:「最好的就是把它的帳密直接輸入」):設定不再是一個要下載的檔案——
// 小幫手第一次開啟會問網址+帳密,自己去換設定。
+ '<div class="muted" style="font-size:12.5px;margin-top:4px">裝好第一次開啟時,貼上這個網址+你的帳號密碼就連上了,不用下載設定檔。</div>')
+ row(s.key, 'key',
'<b>啟用 AI 問答</b><a href="https://aistudio.google.com" target="_blank" rel="noopener">aistudio.google.com</a> 免費申請)<br>'
+ '<input id="sc-key" type="password" placeholder="貼上 Google AI 金鑰" style="width:60%;padding:6px 8px;border-radius:8px;border:1px solid rgba(var(--ink-rgb),.25);background:rgba(var(--ink-rgb),.04);color:var(--ink)"> '
+ '<button class="btn3" id="sc-key-save" style="padding:6px 12px;border-radius:8px;cursor:pointer">啟用</button>'
+ '<div id="sc-key-msg" style="font-size:12.5px;min-height:1.1em"></div>')
+ '<div style="margin-top:10px;text-align:right"><button id="sc-later" style="border:none;background:none;color:inherit;cursor:pointer;font-size:12.5px;text-decoration:underline;opacity:.65">稍後再說</button></div>';
document.body.appendChild(el);
var dl = document.getElementById('sc-daemon');
if (dl) dl.addEventListener('click', function () { markStep('daemon'); });
// t54config.json 下載鈕已移除(設定由小幫手憑帳密自取)
var kb = document.getElementById('sc-key-save');
if (kb) kb.addEventListener('click', function () {
var k = (document.getElementById('sc-key').value || '').trim();
var m = document.getElementById('sc-key-msg');
if (!k) { m.textContent = '請先貼上金鑰'; return; }
kb.disabled = true; m.textContent = '啟用中…';
fetch(API_BASE + '/portal/admin/ai', {
method: 'POST',
headers: Object.assign({ 'Content-Type': 'application/json' }, authHeaders()),
body: JSON.stringify({ gemini_api_key: k })
}).then(function (r) { return safeJson(r).then(function (d) { return { ok: r.ok, status: r.status, d: d }; }); })
.then(function (x) {
kb.disabled = false;
if (!x.ok || !x.d.success) { m.textContent = (x.d && x.d.error) || '啟用失敗,請再試一次'; return; }
markStep('key');
})
.catch(function () { kb.disabled = false; m.textContent = '網路好像有問題,請再試一次'; });
});
var later = document.getElementById('sc-later');
if (later) later.addEventListener('click', function () { el.remove(); }); // 只藏本次,下次進站再提醒
}
// ── t49 首次設定(leo 07-25):console/setup → portal/admin/bootstrap → 預設庫登記 → portal/login
// 四發全是既有端點,一顆按鈕做完;用戶感受=「建一組帳密就進來了」。
$('fs-submit').addEventListener('click', doFirstSetup);
$('fs-password2').addEventListener('keydown', function (ev) { if (ev.key === 'Enter') doFirstSetup(); });
$('fs-tologin').addEventListener('click', function () {
$('v-firstsetup').classList.remove('on');
$('v-login').classList.add('on');
});
function doFirstSetup() {
var email = $('fs-email').value.trim();
var pw = $('fs-password').value;
var st = $('fs-status');
if (!email || pw.length < 8) { st.textContent = '請填 Email,密碼至少 8 碼'; return; }
if (pw !== $('fs-password2').value) { st.textContent = '兩次密碼不一樣'; return; }
$('fs-submit').disabled = true; st.textContent = '';
var post = function (path, body, hdrs) {
return fetch(API_BASE + path, {
method: 'POST',
headers: Object.assign({ 'Content-Type': 'application/json' }, hdrs || {}),
body: JSON.stringify(body)
}).then(function (r) { return r.json().catch(function () { return {}; }).then(function (d) { return { ok: r.ok, status: r.status, d: d }; }); });
};
post('/console/setup', { email: email, password: pw })
.then(function (x) {
// 已設定過(409)=這實例其實有人建過了——自動帶去登入,別把用戶困在死路(leo 實撞)
if (x.status === 409) {
$('fs-submit').disabled = false;
$('v-firstsetup').classList.remove('on');
$('v-login').classList.add('on');
$('login-email').value = email;
$('login-status').textContent = '這個知識庫已經設定過帳號了,直接登入即可。';
throw { handled: true };
}
if (!x.ok || !x.d.session_token) throw new Error(x.d.error || '設定沒有成功,請再試一次');
var ownerTok = x.d.session_token;
return post('/portal/admin/bootstrap', { email: email, password: pw, display_name: email.split('@')[0] }, { Authorization: 'Bearer ' + ownerTok })
.then(function (b) {
// 409=已 bootstrap 過(冪等視為就緒);其餘失敗誠實丟出
if (!b.ok && b.status !== 409) throw new Error(b.d.error || '初始化沒有成功,請再試一次');
return post('/portal/login', { email: email, password: pw });
});
})
.then(function (l) {
if (!l.ok || !l.d.session_token) throw new Error(l.d.error || '帳號建好了,但自動登入沒成功——請用剛設定的帳密登入');
S.token = l.d.session_token;
try { localStorage.setItem('arcrun_portal_session', S.token); } catch (e) { /* noop */ }
})
.then(function () {
$('fs-submit').disabled = false;
try { localStorage.setItem('arcrun_onboarding', '1'); } catch (e) { /* noop */ }
boot();
})
.catch(function (e) {
if (e && e.handled) return; // 409 已自動切登入,不再顯示錯誤
$('fs-submit').disabled = false;
st.textContent = (e && e.message) || friendlyErr(e);
});
}
// 任何 data 請求收到 401 → session 失效 → 回登入殼
function guard401(status) {
if (status === 401) { dropSession(); return true; }
return false;
}
// ── 搜尋 ──
document.querySelectorAll('.modebtn').forEach(function (b) {
b.addEventListener('click', function () {
S.mode = b.getAttribute('data-mode');
document.querySelectorAll('.modebtn').forEach(function (x) { x.classList.toggle('on', x === b); });
if ($('se-q').value.trim()) doSearch();
});
});
$('se-go').addEventListener('click', doSearch);
$('se-q').addEventListener('keydown', function (ev) { if (ev.key === 'Enter') doSearch(); });
function doSearch() {
var q = $('se-q').value.trim();
if (!q) { $('se-count').textContent = '請輸入查詢字'; return; }
$('se-banner').innerHTML = '';
if (S.mode === 'graph') { doGraphSearch(q); return; }
$('se-graphout').style.display = 'none';
$('se-results').style.display = '';
$('se-count').textContent = '查詢中…';
$('se-results').innerHTML = '';
var url = API_BASE + '/portal/data/search?q=' + encodeURIComponent(q) + '&mode=' + (S.mode === 'semantic' ? 'semantic' : 'keyword');
fetch(url, { headers: authHeaders() })
.then(function (r) { return safeJson(r).then(function (d) { return { ok: r.ok, status: r.status, d: d }; }); })
.then(function (x) {
if (guard401(x.status)) return;
if (!x.ok) { $('se-count').innerHTML = '<span class="err">' + esc(x.d.error || ('查詢失敗(HTTP ' + x.status + '')) + '</span>'; return; }
var d = x.d;
if (S.mode === 'semantic' && d.mode === 'keyword') {
$('se-banner').innerHTML = '<div class="honest" style="margin-top:18px"><div class="h">語意搜尋尚未啟用</div><div class="b">語意搜尋用「意思」找資料,不是字面比對。<br>' + esc(d.capability_hint || '系統尚未開啟語意索引——不會假裝有語意結果,以下是關鍵字結果。') + '</div></div>';
}
var entries = d.entries || [];
$('se-count').textContent = '命中 ' + entries.length + ' 筆・模式 ' + (d.mode || 'keyword') + (d.note ? '・' + d.note : '');
if (!entries.length) {
$('se-results').innerHTML = '<div class="muted" style="padding:30px 10px;text-align:center;grid-column:1/-1">找不到「' + esc(q) + '」——換個關鍵字試試。</div>';
return;
}
$('se-results').innerHTML = entries.map(function (e) {
var src = entrySource(e);
return '<div class="kcard" data-card="' + esc(e.id) + '">' +
'<div class="kt">' + esc(entryTitle(e)) + '</div>' +
'<div class="ks">' + esc(entrySnippet(e)) + '</div>' +
'<div class="km">' +
'<span class="tag">' + esc(e.entry_type || 'entry') + '</span>' +
'<span class="tag green">' + esc(entryLib(e)) + '</span>' +
(src ? '<span class="dim" style="word-break:break-all">' + esc(src) + '</span>' : '') +
'<span class="dim mono" style="margin-left:auto">' + esc(fmtDate(e.created_at)) + '</span></div></div>';
}).join('');
})
.catch(function (e) { $('se-count').innerHTML = '<span class="err">請求失敗:' + esc(friendlyErr(e)) + '</span>'; });
}
$('se-results').addEventListener('click', function (ev) {
var t = ev.target.closest('[data-card]');
if (t) nav('card', t.getAttribute('data-card'));
});
// ── AI 問答(portal-demo-suite)──
// 設計哲學:AI 檢索=用戶手動搜尋同一套——同 session token、同 /portal/data/* enforce 面,
// AI 只代查再作答;答案附 sourcesmodepage),點 page 帶回搜尋框讓用戶自己驗證。
$('ai-go').addEventListener('click', doAsk);
$('ai-q').addEventListener('keydown', function (ev) { if (ev.key === 'Enter') doAsk(); });
function doAsk() {
var q = $('ai-q').value.trim();
if (!q) { toast('請先輸入問題'); return; }
$('ai-go').disabled = true;
$('ai-out').innerHTML = '<div class="muted" style="margin-top:12px">AI 查閱知識庫中…</div>';
fetch(API_BASE + '/portal/data/chat?question=' + encodeURIComponent(q), { headers: authHeaders() })
.then(function (r) { return safeJson(r).then(function (d) { return { ok: r.ok, status: r.status, d: d }; }); })
.then(function (x) {
$('ai-go').disabled = false;
if (guard401(x.status)) return;
if (!x.ok) {
// 404=此實例未安裝問答 workflow(server 誠實回報,前端不假裝有 AI)
$('ai-out').innerHTML = '<div class="honest" style="margin-top:12px"><div class="h">問不到</div><div class="b">' + esc(x.d.error || ('問答失敗(HTTP ' + x.status + '')) + '</div></div>';
return;
}
var srcs = x.d.sources || [];
// answer 純文字渲染、保留換行(pre-wrapesc,不走 markdown、防 XSS
var html = '<div class="panel" style="margin-top:12px">' +
'<div style="white-space:pre-wrap;font-size:16px;line-height:1.85;word-break:break-word">' + esc(x.d.answer || 'AI 沒有給出答案)') + '</div>';
if (srcs.length) {
html += '<div style="margin-top:14px;font-size:13px;letter-spacing:.1em;color:rgba(var(--ink-rgb),.5)">出處(點頁名帶入搜尋框)</div>' +
'<div style="margin-top:7px;display:flex;flex-direction:column;gap:6px">' + srcs.map(function (s) {
var page = (s && (s.page || s.page_name)) || '';
var mode = (s && s.mode) || '';
var href = s && s.source ? srcHref(s.source) : '';
return '<div class="nbrow" data-aisrc="' + esc(page) + '">' +
(mode ? '<span class="tag" style="flex:none">' + esc(mode) + '</span>' : '') +
'<span style="word-break:break-word">' + esc(page || '(無頁名)') + '</span>' +
(href ? '<a href="' + esc(href) + '" target="_blank" rel="noopener" style="flex:none;color:var(--amber);font-size:13px" title="開啟來源檔">來源 ↗</a>' : '') +
'<span style="margin-left:auto;color:rgba(var(--amber-rgb),.6);flex:none"></span></div>';
}).join('') + '</div>';
}
html += '</div>';
$('ai-out').innerHTML = html;
})
.catch(function (e) { $('ai-go').disabled = false; $('ai-out').innerHTML = '<div class="err" style="margin-top:12px">請求失敗:' + esc(friendlyErr(e)) + '</div>'; });
}
$('ai-out').addEventListener('click', function (ev) {
if (ev.target.closest('a')) return; // 「來源 ↗」超連結交給瀏覽器,不觸發帶入搜尋框
var t = ev.target.closest('[data-aisrc]');
if (!t) return;
var page = t.getAttribute('data-aisrc');
if (!page) return;
$('se-q').value = page;
$('se-q').focus();
window.scrollTo(0, 0);
});
// ── graph 模式(D-4 粗閘:無權者按鈕根本不顯示;就算 curl 直打 API 也是 403)──
function doGraphSearch(name) {
$('se-results').style.display = 'none';
$('se-graphout').style.display = '';
$('se-count').textContent = '查詢關聯中…';
renderGraphEmpty('查詢關聯中…');
fetch(API_BASE + '/portal/data/graph/neighbors/' + encodeURIComponent(name), { headers: authHeaders() })
.then(function (r) { return safeJson(r).then(function (d) { return { ok: r.ok, status: r.status, d: d }; }); })
.then(function (x) {
if (guard401(x.status)) return;
if (!x.ok) { $('se-count').innerHTML = '<span class="err">' + esc(x.d.error || ('關聯查詢失敗(HTTP ' + x.status + '')) + '</span>'; renderGraphEmpty(x.d.error || '關聯查詢失敗'); return; }
var neighbors = x.d.neighbors || [];
var edges = x.d.edges || [];
// 形狀相容(Arcrun#57 家族):plugin 版 neighbors 是字串、workflow 版是
// { node, predicate, from, depth } 物件——不正規化會渲染成 [object Object]。
var names = neighbors.map(function (nb) {
if (typeof nb === 'string') return nb;
return (nb && (nb.node || nb.name)) || '';
}).filter(Boolean);
// workflow 版 edges 恆空,但 neighbor 物件本身就是一條邊(from --predicate--> node)→ 導出。
if (!edges.length) {
edges = neighbors.filter(function (nb) { return nb && typeof nb === 'object' && nb.predicate; })
.map(function (nb) { return { subject: nb.from || name, predicate: nb.predicate, object: nb.node }; });
}
$('se-count').textContent = '節點「' + name + '」・鄰居 ' + names.length + '・關聯 ' + edges.length;
if (!names.length) { renderGraphEmpty('尚無關聯資料——這個名字還沒有連進知識圖譜。'); return; }
renderGraph(name, names.slice(0, 10));
$('gr-edges').innerHTML = edges.slice(0, 12).map(function (t) {
// 大小寫不敏感比對(graph 查詢已正規化:搜 rag 會命中節點 RAG)
var other = String(t.subject).toLowerCase() === String(name).toLowerCase() ? t.object : t.subject;
return '<div class="nbrow" data-gnode="' + esc(other) + '">' +
'<span class="tag green" style="flex:none">' + esc(t.predicate || '關聯') + '</span>' +
'<span style="word-break:break-word">' + esc(other) + '</span>' +
'<span style="margin-left:auto;color:rgba(var(--amber-rgb),.6);flex:none"></span></div>';
}).join('');
})
.catch(function (e) { $('se-count').innerHTML = '<span class="err">關聯服務不可達:' + esc(friendlyErr(e)) + '</span>'; renderGraphEmpty('關聯服務不可達'); });
}
function renderGraphEmpty(msg) {
$('gr-box').innerHTML = '<div class="graphbox" style="display:grid;place-items:center;height:160px"><span class="muted" style="font-size:14px;padding:0 20px;text-align:center">' + esc(msg) + '</span></div>';
$('gr-edges').innerHTML = '';
}
function renderGraph(center, nodes) {
var n = nodes.length || 1;
var lines = '', chips = '';
for (var i = 0; i < n; i++) {
var a = (-90 + i * (360 / n)) * Math.PI / 180;
var x = 50 + 39 * Math.cos(a), y = 50 + 37 * Math.sin(a);
lines += '<line x1="50" y1="50" x2="' + x.toFixed(2) + '" y2="' + y.toFixed(2) + '" stroke="rgba(var(--ok-rgb),.3)" stroke-width="1" vector-effect="non-scaling-stroke" stroke-dasharray="4 4"/>';
chips += '<div class="gnode" style="left:' + x.toFixed(2) + '%;top:' + y.toFixed(2) + '%" data-gnode="' + esc(nodes[i]) + '">' + esc(nodes[i]) + '</div>';
}
var shortCenter = center.length > 16 ? center.slice(0, 16) + '…' : center;
$('gr-box').innerHTML = '<div class="graphbox">' +
'<svg viewBox="0 0 100 100" preserveAspectRatio="none" style="position:absolute;inset:0;width:100%;height:100%">' + lines + '</svg>' +
'<div class="gcenter"><span>' + esc(shortCenter) + '</span></div>' + chips +
'<div style="position:absolute;right:12px;bottom:10px;font-size:11.5px;color:rgba(var(--ink-rgb),.35)">╌ 知識圖譜鄰居(點節點展開)</div></div>';
}
document.addEventListener('click', function (ev) {
var t = ev.target.closest('[data-gnode]');
if (!t) return;
var name = t.getAttribute('data-gnode');
$('se-q').value = name;
doGraphSearch(name);
});
// ── 卡片詳頁 ──
function loadCard() {
if (!S.cardId) { $('cd-main').innerHTML = '<div class="muted">沒有指定卡片——從「搜尋」點一張進來。</div>'; return; }
$('cd-main').innerHTML = '<div class="muted">載入中…</div>';
fetch(API_BASE + '/portal/data/entries/' + encodeURIComponent(S.cardId), { headers: authHeaders() })
.then(function (r) { return safeJson(r).then(function (d) { return { ok: r.ok, status: r.status, d: d }; }); })
.then(function (x) {
if (guard401(x.status)) return;
if (!x.ok || !x.d.entry) { $('cd-main').innerHTML = '<div class="err">' + esc(x.d.error || '讀不到這張卡片') + '</div>'; return; }
var e = x.d.entry;
var src = entrySource(e);
$('cd-main').innerHTML = '<div class="cardtitle">' + esc(entryTitle(e)) + '</div>' +
'<div style="display:flex;gap:10px;align-items:center;margin-top:12px;font-size:13.5px;flex-wrap:wrap">' +
'<span class="tag">' + esc(e.entry_type || 'entry') + '</span>' +
'<span class="tag green">' + esc(entryLib(e)) + '</span>' +
(e.page_name ? '<span class="tag dim">' + esc(e.page_name) + '</span>' : '') +
'<span class="muted mono">' + esc(fmtDateTime(e.created_at)) + '</span></div>' +
'<div class="md">' + mdRender(e.content || '(此條目沒有內文)') + '</div>' +
(src
? (function () {
var href = srcHref(src);
var body = href
? '<a class="mono" style="font-size:14px;color:var(--amber);word-break:break-all" href="' + esc(href) + '" target="_blank" rel="noopener">' + esc(src) + ' ↗</a>'
: '<span class="mono" style="font-size:14px;color:var(--amber);word-break:break-all">' + esc(src) + '</span>';
return '<div class="srcline"><span style="font-size:13px;letter-spacing:.14em;color:rgba(var(--ink-rgb),.5);flex:none">來源回溯</span>' + body + '</div>';
})()
: '');
})
.catch(function (er) { $('cd-main').innerHTML = '<div class="err">請求失敗:' + esc(friendlyErr(er)) + '</div>'; });
}
// ── 總圖(Arcrun#39 藏書地圖 GUI 切片)──
// 全庫三元組一張網:/portal/data/graph/overview → 手刻力導向佈局(demo 量級,零外部套件)。
// 佈局用固定種子的 PRNG=同一庫每次長一樣(客戶重整不會跳位)。
function jumpToGraph(name) {
S.mode = 'graph';
document.querySelectorAll('.modebtn').forEach(function (x) { x.classList.toggle('on', x.getAttribute('data-mode') === 'graph'); });
nav('search');
$('se-q').value = name;
doGraphSearch(name);
}
function loadMap() {
$('map-box').innerHTML = '<div class="muted" style="padding:30px 10px">載入總圖中…</div>';
$('map-md-link').innerHTML = SOURCE_WEB_BASE
? '<a href="' + esc(SOURCE_WEB_BASE + '/system-dev/wiki/00-MAP.md') + '" target="_blank" rel="noopener" style="color:var(--amber)">00-MAP.md ↗</a>'
: '存在知識庫的 00-MAP.md';
fetch(API_BASE + '/portal/data/graph/overview', { headers: authHeaders() })
.then(function (r) { return safeJson(r).then(function (d) { return { ok: r.ok, status: r.status, d: d }; }); })
.then(function (x) {
if (guard401(x.status)) return;
if (!x.ok) { $('map-box').innerHTML = '<div class="err">' + esc(x.d.error || ('總圖載入失敗(HTTP ' + x.status + '')) + '</div>'; return; }
var nodes = x.d.nodes || [];
var edges = x.d.edges || [];
$('map-meta').textContent = nodes.length + ' 個實體・' + edges.length + ' 條關聯' + (x.d.truncated ? '・已達上限截斷' : '');
if (!nodes.length) { $('map-box').innerHTML = '<div class="muted" style="padding:30px 10px">知識庫還沒有任何關聯——上傳文件後 AI 會自動織網。</div>'; return; }
renderMap(nodes, edges);
})
.catch(function (e) { $('map-box').innerHTML = '<div class="err">請求失敗:' + esc(friendlyErr(e)) + '</div>'; });
}
function renderMap(nodes, edges) {
var N = nodes.length;
var idx = {};
nodes.forEach(function (n, i) { idx[n.name] = i; });
var el = [];
edges.forEach(function (e) {
var a = idx[e.subject], b = idx[e.object];
if (a == null || b == null || a === b) return;
el.push([a, b, e.predicate || '']);
});
// 固定種子 PRNGmulberry32):確定性佈局
var seed = 42;
function rnd() {
seed = (seed + 0x6D2B79F5) | 0;
var t = Math.imul(seed ^ (seed >>> 15), 1 | seed);
t = (t + Math.imul(t ^ (t >>> 7), 61 | t)) ^ t;
return ((t ^ (t >>> 14)) >>> 0) / 4294967296;
}
var W = 1000, H = Math.max(480, Math.min(760, 200 + N * 14));
var px = [], py = [];
for (var i = 0; i < N; i++) {
var ang = 2 * Math.PI * i / N;
var rad = Math.min(W, H) * (0.22 + 0.2 * rnd());
px.push(W / 2 + rad * Math.cos(ang));
py.push(H / 2 + rad * Math.sin(ang) * 0.75);
}
// 力導向:斥力(全對)+彈簧(邊)+向心,260 輪退火
var K = Math.max(75, Math.sqrt(W * H / Math.max(N, 1)) * 0.9);
for (var it = 0; it < 260; it++) {
var cool = Math.max(0.06, 1 - it / 260);
var fx = [], fy = [];
for (var a1 = 0; a1 < N; a1++) { fx.push(0); fy.push(0); }
for (var a2 = 0; a2 < N; a2++) {
for (var b2 = a2 + 1; b2 < N; b2++) {
var dx = px[a2] - px[b2], dy = py[a2] - py[b2];
var d2 = dx * dx + dy * dy + 0.01;
var f = Math.min(28, (K * K) / d2 * 2.2);
var d = Math.sqrt(d2);
fx[a2] += dx / d * f; fy[a2] += dy / d * f;
fx[b2] -= dx / d * f; fy[b2] -= dy / d * f;
}
}
el.forEach(function (e) {
var dx = px[e[0]] - px[e[1]], dy = py[e[0]] - py[e[1]];
var d = Math.sqrt(dx * dx + dy * dy) + 0.01;
var f = (d - K) * 0.045;
fx[e[0]] -= dx / d * f; fy[e[0]] -= dy / d * f;
fx[e[1]] += dx / d * f; fy[e[1]] += dy / d * f;
});
for (var m = 0; m < N; m++) {
fx[m] += (W / 2 - px[m]) * 0.012;
fy[m] += (H / 2 - py[m]) * 0.012;
px[m] += Math.max(-14, Math.min(14, fx[m])) * cool;
py[m] += Math.max(-14, Math.min(14, fy[m])) * cool;
}
}
// 視窗貼合
var minX = 1e9, maxX = -1e9, minY = 1e9, maxY = -1e9;
for (var q = 0; q < N; q++) {
minX = Math.min(minX, px[q]); maxX = Math.max(maxX, px[q]);
minY = Math.min(minY, py[q]); maxY = Math.max(maxY, py[q]);
}
var PAD = 70;
var vb = (minX - PAD) + ' ' + (minY - PAD) + ' ' + (maxX - minX + PAD * 2) + ' ' + (maxY - minY + PAD * 2);
var maxDeg = 1;
nodes.forEach(function (n) { maxDeg = Math.max(maxDeg, n.degree || 1); });
var svg = '<svg viewBox="' + vb + '" preserveAspectRatio="xMidYMid meet">';
el.forEach(function (e) {
svg += '<line class="mapedge" x1="' + px[e[0]].toFixed(1) + '" y1="' + py[e[0]].toFixed(1) +
'" x2="' + px[e[1]].toFixed(1) + '" y2="' + py[e[1]].toFixed(1) + '"><title>' +
esc(nodes[e[0]].name + ' —' + (e[2] || '關聯') + '→ ' + nodes[e[1]].name) + '</title></line>';
});
nodes.forEach(function (n, i2) {
var deg = n.degree || 1;
var r = 9 + Math.sqrt(deg) * 5;
var hub = deg >= Math.max(3, maxDeg * 0.6) ? ' hub' : '';
svg += '<g class="mapnode' + hub + '" data-mapnode="' + esc(n.name) + '">' +
'<circle cx="' + px[i2].toFixed(1) + '" cy="' + py[i2].toFixed(1) + '" r="' + r.toFixed(1) + '"><title>' + esc(n.name + '・' + deg + ' 條關聯') + '</title></circle>' +
'<text x="' + px[i2].toFixed(1) + '" y="' + (py[i2] + r + 15).toFixed(1) + '" text-anchor="middle">' + esc(n.name.length > 14 ? n.name.slice(0, 14) + '…' : n.name) + '</text></g>';
});
svg += '</svg>';
$('map-box').innerHTML = '<div class="mapbox">' + svg +
'<div style="position:absolute;right:12px;bottom:10px;font-size:11.5px;color:rgba(var(--ink-rgb),.35)">╌ 知識庫總圖(點節點看鄰居)</div></div>';
}
document.addEventListener('click', function (ev) {
var t = ev.target.closest('[data-mapnode]');
if (!t) return;
jumpToGraph(t.getAttribute('data-mapnode'));
});
// ── 工作流(唯讀)──
function loadWorkflows() {
$('wf-list').innerHTML = '<div class="muted">載入中…</div>';
fetch(API_BASE + '/portal/data/workflows', { headers: authHeaders() })
.then(function (r) { return safeJson(r).then(function (d) { return { ok: r.ok, status: r.status, d: d }; }); })
.then(function (x) {
if (guard401(x.status)) return;
if (!x.ok) { $('wf-list').innerHTML = '<div class="err">' + esc(x.d.error || ('讀取失敗(HTTP ' + x.status + '')) + '</div>'; return; }
var wfs = x.d.workflows || [];
if (!wfs.length) { $('wf-list').innerHTML = '<div class="muted" style="padding:20px 4px">目前沒有任何工作流。</div>'; return; }
$('wf-list').innerHTML = wfs.map(function (w) {
var lastHtml = '<span class="dim">尚無執行紀錄</span>';
if (w.last_execution) {
var v = w.last_execution.verdict || '';
var cls = v === 'success' ? 'ok' : (v === 'failed' ? 'err' : 'muted');
lastHtml = '<span class="' + cls + '">' + esc(v || '(無 verdict') + '</span> <span class="dim mono">' + esc(fmtDateTime(Number(w.last_execution.timestamp))) + '</span>';
}
return '<div class="card-item">' +
'<div style="display:flex;align-items:baseline;gap:10px;flex-wrap:wrap">' +
'<span class="serif" style="font-size:17px;font-weight:600">' + esc(w.name) + '</span>' +
(w.cron_expr ? '<span class="tag dim mono">' + esc(w.cron_expr) + '</span>' : '') +
'<span style="margin-left:auto;font-size:13.5px">' + lastHtml + '</span></div>' +
(w.description ? '<div style="margin-top:8px;font-size:14.5px;line-height:1.65;color:rgba(var(--ink-rgb),.65)">' + esc(w.description) + '</div>' : '<div class="dim" style="margin-top:8px;font-size:13.5px">(沒有描述)</div>') +
'</div>';
}).join('');
})
.catch(function (e) { $('wf-list').innerHTML = '<div class="err">請求失敗:' + esc(friendlyErr(e)) + '</div>'; });
}
// ── 上傳頁(portal-demo-suite)──
// 前端只讀檔轉 base64 逐檔 POST /portal/data/uploadGitea 位置與 token 全在 server 側,
// 這裡看不到任何 repo/token 字串。逐檔獨立狀態列(一檔失敗不拖累其他檔)。
var UP_OK_MSG = '已收件,約 1 分鐘後可在搜尋頁找到;AI 整理後會以 wiki 卡形式出現。';
function b64FromDataUrl(dataUrl) {
var i = String(dataUrl).indexOf(',');
return i >= 0 ? String(dataUrl).slice(i + 1) : '';
}
function uploadStatusRow(name) {
var row = document.createElement('div');
row.className = 'card-item';
row.innerHTML = '<div style="display:flex;align-items:baseline;gap:10px;flex-wrap:wrap">' +
'<span class="mono" style="font-size:14.5px;word-break:break-all">' + esc(name) + '</span>' +
'<span class="up-st muted" style="margin-left:auto;font-size:14px;flex:none">讀取中…</span></div>' +
'<div class="up-msg" style="margin-top:6px;font-size:13.5px;line-height:1.65;color:rgba(var(--ink-rgb),.6)"></div>';
$('up-list').prepend(row);
return row;
}
function setRowStatus(row, ok, statusText, msg) {
var st = row.querySelector('.up-st');
st.textContent = statusText;
st.className = 'up-st ' + (ok === true ? 'ok' : (ok === false ? 'err' : 'muted'));
row.querySelector('.up-msg').textContent = msg || '';
}
function uploadOneFile(file) {
var row = uploadStatusRow(file.name);
if (!/\.(md|txt)$/i.test(file.name)) {
setRowStatus(row, false, '已略過', '只收 .md / .txt 檔。');
return;
}
var reader = new FileReader();
reader.onerror = function () { setRowStatus(row, false, '讀檔失敗', '瀏覽器讀不到這個檔案。'); };
reader.onload = function () {
setRowStatus(row, null, '上傳中…', '');
fetch(API_BASE + '/portal/data/upload', {
method: 'POST',
headers: Object.assign({ 'Content-Type': 'application/json' }, authHeaders()),
body: JSON.stringify({ filename: file.name, content_b64: b64FromDataUrl(reader.result) })
})
.then(function (r) { return safeJson(r).then(function (d) { return { ok: r.ok, status: r.status, d: d }; }); })
.then(function (x) {
if (guard401(x.status)) return;
if (!x.ok) { setRowStatus(row, false, '失敗', x.d.error || ('HTTP ' + x.status)); return; }
setRowStatus(row, true, '已收件', UP_OK_MSG + (x.d.path ? '' + x.d.path + '' : ''));
})
.catch(function (e) { setRowStatus(row, false, '失敗', friendlyErr(e)); });
};
reader.readAsDataURL(file); // dataURL 尾段即 base64unicode 安全,免手刻 btoa 編碼)
}
function handleUploadFiles(files) {
for (var i = 0; i < files.length; i++) uploadOneFile(files[i]);
}
$('up-pick').addEventListener('click', function (ev) { ev.stopPropagation(); $('up-file').click(); });
$('up-drop').addEventListener('click', function () { $('up-file').click(); });
$('up-file').addEventListener('change', function () { handleUploadFiles(this.files); this.value = ''; });
['dragover', 'dragenter'].forEach(function (t) {
$('up-drop').addEventListener(t, function (ev) { ev.preventDefault(); ev.currentTarget.style.background = 'rgba(var(--amber-rgb),.12)'; });
});
['dragleave', 'drop'].forEach(function (t) {
$('up-drop').addEventListener(t, function (ev) { ev.preventDefault(); ev.currentTarget.style.background = 'rgba(var(--amber-rgb),.04)'; });
});
$('up-drop').addEventListener('drop', function (ev) {
if (ev.dataTransfer && ev.dataTransfer.files && ev.dataTransfer.files.length) handleUploadFiles(ev.dataTransfer.files);
});
// ── 管理頁(P4:帳號管理+庫目錄管理。全走 /portal/admin/*,前端零業務邏輯;
// 一般用戶 nav 不顯示,且 server role 閘 403——藏只是 UX,真閘在後端)──
var adminLibs = []; // 庫目錄快取(渲染每帳號的庫勾選用)
function adminApi(method, path, body) {
path = API_BASE + path;
var opt = { method: method, headers: Object.assign({ 'Content-Type': 'application/json' }, authHeaders()) };
if (body !== undefined) opt.body = JSON.stringify(body);
return fetch(path, opt).then(function (r) {
return safeJson(r).then(function (d) { return { ok: r.ok, status: r.status, d: d }; });
});
}
function loadAdmin() {
$('ad-users').innerHTML = '<div class="muted">載入中…</div>';
$('ad-libs').innerHTML = '<div class="muted">載入中…</div>';
adminApi('GET', '/portal/admin/libraries')
.then(function (x) {
if (guard401(x.status)) return;
if (!x.ok) { $('ad-libs').innerHTML = '<div class="err">' + esc(x.d.error || ('讀取失敗(HTTP ' + x.status + '')) + '</div>'; return; }
adminLibs = x.d.libraries || [];
renderAdminLibs();
return adminApi('GET', '/portal/admin/users').then(function (y) {
if (guard401(y.status)) return;
if (!y.ok) { $('ad-users').innerHTML = '<div class="err">' + esc(y.d.error || ('讀取失敗(HTTP ' + y.status + '')) + '</div>'; return; }
renderAdminUsers(y.d.users || []);
});
})
.catch(function (e) {
$('ad-users').innerHTML = '<div class="err">請求失敗:' + esc(friendlyErr(e)) + '</div>';
$('ad-libs').innerHTML = '';
});
}
// 帳號可勾選的庫=庫目錄啟用中的庫 ∪ general ∪ 該帳號已有的庫(目錄外的舊授權不憑空消失)
function checkableLibs(userLibs) {
var names = ['general'];
adminLibs.forEach(function (l) { if (l.status !== 'disabled' && l.name && names.indexOf(l.name) < 0) names.push(l.name); });
(userLibs || []).forEach(function (n) { if (n !== '*' && names.indexOf(n) < 0) names.push(n); });
return names;
}
function libDisplay(name) {
for (var i = 0; i < adminLibs.length; i++) { if (adminLibs[i].name === name) return adminLibs[i].display_name || name; }
return name;
}
function renderAdminUsers(users) {
if (!users.length) { $('ad-users').innerHTML = '<div class="muted" style="padding:16px 4px">還沒有任何同仁帳號——用上面的表單新增第一個。</div>'; return; }
$('ad-users').innerHTML = users.map(function (u) {
var star = (u.libraries || []).indexOf('*') >= 0;
var disabled = u.status === 'disabled';
var libChips = star
? '<span class="tag green">全部知識庫</span>'
: ((u.libraries || []).length
? (u.libraries || []).map(function (n) { return '<span class="tag green">' + esc(libDisplay(n)) + '</span>'; }).join(' ')
: '<span class="tag dim">尚未授權任何庫</span>');
var boxes = '<label><input type="checkbox" data-star data-uid="' + esc(u.record_id) + '"' + (star ? ' checked' : '') + '> 全部知識庫(*</label>' +
checkableLibs(u.libraries).map(function (n) {
var on = !star && (u.libraries || []).indexOf(n) >= 0;
return '<label><input type="checkbox" data-lib="' + esc(n) + '" data-uid="' + esc(u.record_id) + '"' + (on ? ' checked' : '') + (star ? ' disabled' : '') + '> ' + esc(libDisplay(n)) + ' <span class="dim mono" style="font-size:12px">' + esc(n) + '</span></label>';
}).join('');
return '<div class="card-item"' + (disabled ? ' style="opacity:.6"' : '') + '>' +
'<div style="display:flex;align-items:baseline;gap:10px;flex-wrap:wrap">' +
'<span class="serif" style="font-size:17px;font-weight:600">' + esc(u.display_name || u.email) + '</span>' +
'<span class="muted" style="font-size:14px;word-break:break-all">' + esc(u.email) + '</span>' +
'<span class="tag' + (u.role === 'admin' ? '' : ' dim') + '">' + (u.role === 'admin' ? '管理員' : '一般用戶') + '</span>' +
'<span class="tag ' + (disabled ? 'dim' : 'green') + '">' + (disabled ? '已停用' : '啟用中') + '</span></div>' +
'<div style="margin-top:9px;display:flex;gap:6px;flex-wrap:wrap;align-items:center;font-size:13px"><span class="muted" style="flex:none">可查庫</span>' + libChips + '</div>' +
'<div class="btnrow">' +
'<button class="btn2" data-act="edit-libs" data-uid="' + esc(u.record_id) + '">編輯可查庫</button>' +
'<button class="btn2" data-act="reset-pw" data-uid="' + esc(u.record_id) + '" data-email="' + esc(u.email) + '">重設密碼</button>' +
(disabled
? '<button class="btn2" data-act="set-status" data-next="active" data-uid="' + esc(u.record_id) + '">啟用</button>'
: '<button class="btn2 warn" data-act="set-status" data-next="disabled" data-uid="' + esc(u.record_id) + '" data-email="' + esc(u.email) + '">停用</button>') +
'</div>' +
'<div id="libed-' + esc(u.record_id) + '" style="display:none">' +
'<div class="libgrid">' + boxes + '</div>' +
'<div class="btnrow"><button class="btn2" data-act="save-libs" data-uid="' + esc(u.record_id) + '">儲存庫權限</button>' +
'<span class="dim" style="font-size:13px;align-self:center">勾「全部知識庫」=不限庫;否則至少勾一個。儲存後立即生效。</span></div></div>' +
'</div>';
}).join('');
}
function renderAdminLibs() {
if (!adminLibs.length) { $('ad-libs').innerHTML = '<div class="muted" style="padding:16px 4px">同步小幫手還沒送來任何庫。裝好小幫手並選好資料夾後,庫會自動出現在這裡。</div>'; return; }
$('ad-libs').innerHTML = adminLibs.map(function (l) {
var disabled = l.status === 'disabled';
var notWatching = l.daemon_watching === false; // daemon 有報告但此庫不在其中
var removeBtn = l.auto
? '<button class="btn2" style="color:#b03a26;border-color:#e58575;margin-left:auto" data-act="lib-remove-auto" data-name="' + esc(l.name) + '">移除</button>'
: '<button class="btn2" style="color:#b03a26;border-color:#e58575;margin-left:auto" data-act="lib-remove" data-id="' + esc(l.record_id) + '" data-name="' + esc(l.display_name || l.name) + '">移除</button>';
// t142:卡數+三元組數顯示(政府驗收用)。兩者皆 0 顯示「還沒有內容」,不顯示「0 張」。
var cardCount = typeof l.card_count === 'number' ? l.card_count : undefined;
var tripletCount = typeof l.triplet_count === 'number' ? l.triplet_count : undefined;
var statsHtml = '';
if (cardCount !== undefined || tripletCount !== undefined) {
var parts = [];
if (cardCount > 0) parts.push(cardCount + ' 張知識卡');
if (tripletCount > 0) parts.push(tripletCount + ' 條關聯');
statsHtml = '<div style="margin-top:5px;font-size:13px;color:rgba(var(--ink-rgb),.5)">' +
(parts.length ? parts.join('・') : '還沒有內容') + '</div>';
}
return '<div class="card-item">' +
'<div style="display:flex;align-items:baseline;gap:10px;flex-wrap:wrap">' +
'<span class="serif" style="font-size:17px;font-weight:600">' + esc(l.display_name || l.name) + '</span>' +
'<span class="dim mono" style="font-size:13px">' + esc(l.name) + '</span>' +
(l.auto
? '<span class="tag green">啟用中</span><span class="tag">同步自動出現</span>'
: '<span class="tag ' + (disabled ? 'dim' : 'green') + '">' + (disabled ? '已停用' : '啟用中') + '</span>') +
removeBtn +
'</div>' +
statsHtml +
(!l.auto && l.description ? '<div style="margin-top:8px;font-size:14.5px;line-height:1.65;color:rgba(var(--ink-rgb),.65)">' + esc(l.description) + '</div>' : '') +
(notWatching ? '<div style="margin-top:6px;font-size:13px;color:rgba(var(--ink-rgb),.45)">小幫手目前沒有在同步這個資料夾</div>' : '') +
'</div>';
}).join('');
}
// 一次性密碼顯示(server 不留明碼——關掉就真的沒了,誠實跟 admin 說清楚)
function showOtp(email, password) {
$('ad-otp').innerHTML = '<div class="otpbox">' +
'<div style="font-size:15px;font-weight:600">' + esc(email) + ' 的一次性密碼</div>' +
'<div class="pw">' + esc(password) + '</div>' +
'<div style="font-size:13.5px;line-height:1.7;color:rgba(var(--ink-rgb),.65)">只顯示這一次——關閉後再也調不出來(系統只存雜湊)。請當場轉交同仁,並提醒登入後到「設定」改成自己的密碼。</div>' +
'<div class="btnrow"><button class="btn2" id="ad-otp-close">我已轉交,關閉</button></div></div>';
$('ad-otp').scrollIntoView({ block: 'nearest' });
}
// 新增帳號
$('ad-nu-create').addEventListener('click', function () {
var email = $('ad-nu-email').value.trim();
var name = $('ad-nu-name').value.trim();
var role = $('ad-nu-role').value === 'admin' ? 'admin' : 'user';
var st = $('ad-nu-status');
if (!email) { st.textContent = '請填 Email'; return; }
st.textContent = '';
$('ad-nu-create').disabled = true;
var body = { email: email, role: role };
if (name) body.display_name = name;
adminApi('POST', '/portal/admin/users', body)
.then(function (x) {
$('ad-nu-create').disabled = false;
if (guard401(x.status)) return;
if (!x.ok) { st.textContent = x.d.error || ('建立失敗(HTTP ' + x.status + ''); return; }
$('ad-nu-email').value = ''; $('ad-nu-name').value = ''; $('ad-nu-role').value = 'user';
if (x.d.generated_password) showOtp(email, x.d.generated_password);
toast('帳號已建立');
loadAdmin();
})
.catch(function (e) { $('ad-nu-create').disabled = false; st.textContent = friendlyErr(e); });
});
// 「全部知識庫」勾選 → 其餘庫勾選框連動停用(存的就是 ["*"],個別勾選無意義)
document.addEventListener('change', function (ev) {
var t = ev.target;
if (!t || !t.hasAttribute || !t.hasAttribute('data-star')) return;
var uid = t.getAttribute('data-uid');
document.querySelectorAll('#libed-' + uid + ' input[data-lib]').forEach(function (cb) {
cb.disabled = t.checked;
if (t.checked) cb.checked = false;
});
});
// 管理頁動作(事件委派)
$('v-admin').addEventListener('click', function (ev) {
var t = ev.target.closest('[data-act]');
if (!t) return;
var act = t.getAttribute('data-act');
var uid = t.getAttribute('data-uid');
if (act === 'edit-libs') {
var ed = $('libed-' + uid);
ed.style.display = ed.style.display === 'none' ? '' : 'none';
return;
}
if (act === 'save-libs') {
var star = document.querySelector('#libed-' + uid + ' input[data-star]');
var libs;
if (star && star.checked) { libs = ['*']; }
else {
libs = [];
document.querySelectorAll('#libed-' + uid + ' input[data-lib]').forEach(function (cb) {
if (cb.checked) libs.push(cb.getAttribute('data-lib'));
});
if (!libs.length) { toast('至少勾一個庫,或勾「全部知識庫」'); return; }
}
t.disabled = true;
adminApi('PATCH', '/portal/admin/users/' + encodeURIComponent(uid), { libraries: libs })
.then(function (x) {
t.disabled = false;
if (guard401(x.status)) return;
if (!x.ok) { toast(x.d.error || ('儲存失敗(HTTP ' + x.status + '')); return; }
toast('庫權限已更新,立即生效');
loadAdmin();
})
.catch(function (e) { t.disabled = false; toast(friendlyErr(e)); });
return;
}
if (act === 'set-status') {
var next = t.getAttribute('data-next');
if (next === 'disabled' && !confirm('確定停用 ' + (t.getAttribute('data-email') || '這個帳號') + '?停用後其登入與既有 session 立即失效。')) return;
t.disabled = true;
adminApi('PATCH', '/portal/admin/users/' + encodeURIComponent(uid), { status: next })
.then(function (x) {
t.disabled = false;
if (guard401(x.status)) return;
if (!x.ok) { toast(x.d.error || ('更新失敗(HTTP ' + x.status + '')); return; } // 含最後一個 admin 的 409 訊息
toast(next === 'disabled' ? '已停用' : '已啟用');
loadAdmin();
})
.catch(function (e) { t.disabled = false; toast(friendlyErr(e)); });
return;
}
if (act === 'reset-pw') {
var email = t.getAttribute('data-email') || '';
if (!confirm('確定重設 ' + email + ' 的密碼?舊密碼將立即失效,會產生一組新的一次性密碼。')) return;
t.disabled = true;
adminApi('POST', '/portal/admin/users/' + encodeURIComponent(uid) + '/reset-password')
.then(function (x) {
t.disabled = false;
if (guard401(x.status)) return;
if (!x.ok) { toast(x.d.error || ('重設失敗(HTTP ' + x.status + '')); return; }
showOtp(email, x.d.password);
toast('密碼已重設');
})
.catch(function (e) { t.disabled = false; toast(friendlyErr(e)); });
return;
}
// 移除已登記庫(有 record_id
if (act === 'lib-remove') {
var libId = t.getAttribute('data-id') || '';
var libName = t.getAttribute('data-name') || libId;
if (!confirm('把「' + libName + '」從目錄移除?\n\n資料不會刪除,重新同步時會再出現。')) return;
t.disabled = true;
adminApi('DELETE', '/portal/admin/libraries/' + encodeURIComponent(libId))
.then(function (x) {
t.disabled = false;
if (guard401(x.status)) return;
if (!x.ok) { toast(x.d.error || ('移除失敗(HTTP ' + x.status + '')); return; }
adminLibs = adminLibs.filter(function (l) { return l.record_id !== libId; });
renderAdminLibs();
toast('已從目錄移除');
})
.catch(function (e) { t.disabled = false; toast(friendlyErr(e)); });
return;
}
// 移除 auto 庫(無 record_identries 標 deprecated
if (act === 'lib-remove-auto') {
var autoName = t.getAttribute('data-name') || '';
var input = window.prompt('移除「' + autoName + '」會讓它的內容不再被搜尋到(資料保留可還原)。\n\n請輸入庫名確認:');
if (input === null) return; // 取消
if (input.trim() !== autoName) { toast('庫名輸入不符,取消移除'); return; }
t.disabled = true;
adminApi('DELETE', '/portal/admin/libraries/by-name/' + encodeURIComponent(autoName), { confirm: autoName })
.then(function (x) {
t.disabled = false;
if (guard401(x.status)) return;
if (!x.ok) { toast(x.d.error || ('移除失敗(HTTP ' + x.status + '')); return; }
adminLibs = adminLibs.filter(function (l) { return l.name !== autoName; });
renderAdminLibs();
toast('已移除(' + (x.d.deprecated_count || 0) + ' 筆標為不可搜)');
})
.catch(function (e) { t.disabled = false; toast(friendlyErr(e)); });
return;
}
});
// 一次性密碼關閉鈕(otpbox 動態生成,掛在容器上)
$('ad-otp').addEventListener('click', function (ev) {
if (ev.target && ev.target.id === 'ad-otp-close') $('ad-otp').innerHTML = '';
});
// ── 設定 ──
function loadSettings() {
var p = S.profile;
if (!p) { $('st-me').innerHTML = '<div class="muted">載入中…</div>'; return; }
if (window._loadAiConfig) window._loadAiConfig();
var libs = p.libraries || [];
var libHtml = libs.indexOf('*') >= 0
? '<span class="tag green">全部知識庫</span>'
: (libs.length ? libs.map(function (l) { return '<span class="tag green">' + esc(l) + '</span>'; }).join(' ') : '<span class="tag dim">尚未授權任何庫</span>');
$('st-me').innerHTML =
'<div class="kvline"><span class="muted">名稱</span><span>' + esc(p.display_name || '') + '</span></div>' +
'<div class="kvline"><span class="muted">角色</span><span>' + esc(p.role === 'admin' ? '管理員' : '一般用戶') + '</span></div>' +
'<div class="kvline" style="align-items:flex-start"><span class="muted" style="flex:none">可查庫</span><span style="text-align:right;display:flex;gap:6px;flex-wrap:wrap;justify-content:flex-end">' + libHtml + '</span></div>';
}
$('st-pw-save').addEventListener('click', function () {
var oldPw = $('st-pw-old').value;
var newPw = $('st-pw-new').value;
var newPw2 = $('st-pw-new2').value;
var st = $('st-pw-status');
st.className = 'err';
if (!oldPw || !newPw) { st.textContent = '請填舊密碼與新密碼'; return; }
if (newPw.length < 8) { st.textContent = '新密碼至少 8 碼'; return; }
if (newPw !== newPw2) { st.textContent = '兩次輸入的新密碼不一致'; return; }
$('st-pw-save').disabled = true;
st.textContent = '';
fetch(API_BASE + '/portal/me/password', {
method: 'POST',
headers: Object.assign({ 'Content-Type': 'application/json' }, authHeaders()),
body: JSON.stringify({ current: oldPw, 'new': newPw })
})
.then(function (r) { return safeJson(r).then(function (d) { return { ok: r.ok, status: r.status, d: d }; }); })
.then(function (x) {
$('st-pw-save').disabled = false;
if (guard401(x.status)) return;
if (!x.ok) { st.textContent = x.d.error || '更新失敗'; return; }
st.className = 'ok';
st.textContent = '密碼已更新';
$('st-pw-old').value = ''; $('st-pw-new').value = ''; $('st-pw-new2').value = '';
toast('密碼已更新');
})
.catch(function (e) { $('st-pw-save').disabled = false; st.textContent = friendlyErr(e); });
});
boot();
})();
</script>
</body>
</html>