@a9i5k4/dsh-auto-memory 3.1.4 → 3.1.5
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/docs/CONTRIBUTORS.html +966 -471
- package/docs/M6-CONTRACT.md +1 -1
- package/docs/landing/index.html +1178 -1624
- package/lib/activation-inbox.js +35 -5
- package/lib/client.js +14 -1
- package/package.json +1 -1
package/docs/landing/index.html
CHANGED
|
@@ -1,1745 +1,1299 @@
|
|
|
1
|
-
<!
|
|
2
|
-
<html lang="zh-CN" data-lang="zh">
|
|
1
|
+
<!DOCTYPE html>
|
|
2
|
+
<html lang="zh-CN" data-lang="zh" data-theme="light">
|
|
3
3
|
<head>
|
|
4
|
-
<meta charset="
|
|
5
|
-
<meta name="viewport" content="width=device-width,initial-scale=1,viewport-fit=cover"
|
|
6
|
-
<
|
|
7
|
-
<meta name="
|
|
8
|
-
<meta name="theme-color" content="#
|
|
9
|
-
<
|
|
4
|
+
<meta charset="UTF-8">
|
|
5
|
+
<meta name="viewport" content="width=device-width, initial-scale=1.0, viewport-fit=cover">
|
|
6
|
+
<title>dsh-auto-memory — 无问自忆 · 记忆不断线</title>
|
|
7
|
+
<meta name="color-scheme" content="light dark">
|
|
8
|
+
<meta name="theme-color" content="#eef2f7">
|
|
9
|
+
<link rel="preconnect" href="https://fonts.googleapis.com">
|
|
10
|
+
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
|
11
|
+
<link href="https://fonts.googleapis.com/css2?family=Space+Grotesk:wght@300;400;500;600;700&family=Manrope:wght@200;300;400;500;600;700;800&family=JetBrains+Mono:wght@400;500;600&display=swap" rel="stylesheet">
|
|
12
|
+
<script src="https://cdn.tailwindcss.com"></script>
|
|
10
13
|
<style>
|
|
11
|
-
/*
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
--
|
|
23
|
-
--
|
|
24
|
-
--
|
|
25
|
-
--
|
|
26
|
-
--
|
|
27
|
-
--
|
|
28
|
-
--
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
--
|
|
33
|
-
--
|
|
14
|
+
/* ══ 主题变量:浅色为基准,深色为可选 ══ */
|
|
15
|
+
:root, [data-theme="light"] {
|
|
16
|
+
--bg: #eef2f7; --bg-elev: #ffffff; --bg-soft: #e2e8f0; --bg-code: #0f172a;
|
|
17
|
+
--fg: #0f172a; --fg-dim: #334155; --muted: #64748b;
|
|
18
|
+
--accent: #2563eb; --accent-2: #3b82f6; --accent-3: #60a5fa; --accent-glow: rgba(37, 99, 235, 0.2);
|
|
19
|
+
--cyan: #2563eb; --teal: #0d9488; --green: #15803d; --purple: #6d28d9;
|
|
20
|
+
--border: rgba(15, 23, 42, 0.1); --border-strong: rgba(15, 23, 42, 0.2);
|
|
21
|
+
--card: rgba(255, 255, 255, 0.7); --card-hover: rgba(15, 23, 42, 0.03); --shadow: 0 4px 24px rgba(15, 23, 42, 0.08);
|
|
22
|
+
--neu-dark: #dce3ed; --neu-light: #ffffff;
|
|
23
|
+
}
|
|
24
|
+
[data-theme="dark"] {
|
|
25
|
+
--bg: #0a0d14; --bg-elev: #0f1320; --bg-soft: #141828; --bg-code: #05070d;
|
|
26
|
+
--fg: #e8ecf3; --fg-dim: #b8c0d0; --muted: #6a7590;
|
|
27
|
+
--accent: #3b82f6; --accent-2: #60a5fa; --accent-3: #93c5fd; --accent-glow: rgba(59, 130, 246, 0.35);
|
|
28
|
+
--cyan: #38bdf8; --teal: #4dd0c1; --green: #98c379; --purple: #c678dd;
|
|
29
|
+
--border: rgba(255, 255, 255, 0.07); --border-strong: rgba(255, 255, 255, 0.15);
|
|
30
|
+
--card: rgba(255, 255, 255, 0.02); --card-hover: rgba(255, 255, 255, 0.045); --shadow: 0 4px 20px rgba(0,0,0,0.3);
|
|
31
|
+
--neu-dark: #0c0f17; --neu-light: #141828;
|
|
32
|
+
}
|
|
33
|
+
* { box-sizing: border-box; } html { scroll-behavior: smooth; -webkit-text-size-adjust: 100%; }
|
|
34
|
+
:root {
|
|
35
|
+
--duration-stagger: 40ms; --duration-micro: 80ms; --duration-quick: 150ms;
|
|
36
|
+
--duration-fast: 250ms; --duration-medium: 350ms; --duration-slow: 400ms; --duration-very-slow: 500ms;
|
|
37
|
+
--ease-smooth-out: cubic-bezier(0.22, 1, 0.36, 1); --ease-in-out: ease-in-out; --ease-out: ease-out; --ease-linear: linear;
|
|
38
|
+
--distance-micro: 4px; --distance-small: 6px; --distance-base: 8px; --distance-medium: 12px;
|
|
39
|
+
--blur-small: 2px; --blur-medium: 3px;
|
|
40
|
+
}
|
|
41
|
+
body { margin: 0; background: var(--bg); color: var(--fg); font-family: 'Manrope', system-ui, -apple-system, "PingFang SC", "Microsoft YaHei", sans-serif; -webkit-font-smoothing: antialiased; overflow-x: hidden; line-height: 1.6; transition: background-color 0.4s, color 0.4s; }
|
|
42
|
+
body::before { content: ''; position: fixed; inset: 0; background-image: url("data:image/svg+xml,%3Csvg viewBox='0 0 200 200' xmlns='http://www.w3.org/2000/svg'%3E%3Cfilter id='n'%3E%3CfeTurbulence type='fractalNoise' baseFrequency='0.85'/%3E%3C/filter%3E%3Crect width='100%25' height='100%25' filter='url(%23n)' opacity='0.5'/%3E%3C/svg%3E"); opacity: 0.03; pointer-events: none; z-index: 1; mix-blend-mode: overlay; }
|
|
43
|
+
.font-display { font-family: 'Space Grotesk', 'Manrope', system-ui, sans-serif; letter-spacing: -0.025em; }
|
|
44
|
+
.font-mono { font-family: 'JetBrains Mono', ui-monospace, Consolas, monospace; }
|
|
45
|
+
.accent { color: var(--accent); }
|
|
46
|
+
.gradient-text { background: linear-gradient(120deg, var(--accent) 0%, var(--accent-2) 50%, var(--accent-3) 100%); -webkit-background-clip: text; background-clip: text; -webkit-text-fill-color: transparent; }
|
|
47
|
+
.brand-logo svg { width: 100%; height: 100%; }
|
|
48
|
+
.brand-logo .brain-path { stroke: currentColor; stroke-width: 1.9; fill: none; stroke-linecap: round; stroke-linejoin: round; }
|
|
49
|
+
.brand-logo:hover .brain-path { stroke: var(--accent); }
|
|
50
|
+
@keyframes pulse-soft { 0%{stroke-dashoffset:0} 100%{stroke-dashoffset:-30} }
|
|
51
|
+
.brand-logo .pulse { stroke-dasharray: 3 2; animation: pulse-soft 4s linear infinite; }
|
|
52
|
+
.nav-blur { backdrop-filter: blur(24px) saturate(180%); -webkit-backdrop-filter: blur(24px) saturate(180%); background: color-mix(in srgb, var(--bg) 80%, transparent); border-bottom: 1px solid var(--border); }
|
|
53
|
+
.btn-primary { background: var(--accent); color: #fff; transition: all 0.35s cubic-bezier(0.4,0,0.2,1); position: relative; overflow: hidden; }
|
|
54
|
+
.btn-primary::before { content: ''; position: absolute; inset: 0; background: linear-gradient(90deg, transparent, rgba(255,255,255,0.2), transparent); transform: translateX(-100%); transition: transform 0.6s; }
|
|
55
|
+
.btn-primary:hover::before { transform: translateX(100%); }
|
|
56
|
+
.btn-primary:hover { filter: brightness(1.08); box-shadow: 0 12px 40px var(--accent-glow); transform: translateY(-2px); }
|
|
57
|
+
.btn-ghost { background: transparent; border: 1px solid var(--border-strong); transition: all 0.3s; color: var(--fg); }
|
|
58
|
+
.btn-ghost:hover { background: var(--card-hover); border-color: var(--accent); color: var(--accent); transform: translateY(-1px); }
|
|
59
|
+
.glass-card { background: var(--card); border: 1px solid var(--border); backdrop-filter: blur(10px); transition: all 0.4s; position: relative; overflow: hidden; box-shadow: var(--shadow); }
|
|
60
|
+
[data-theme="light"] .glass-card { background: var(--bg-elev); }
|
|
61
|
+
.shot-img { aspect-ratio: 4 / 3; object-fit: contain; object-position: center; background: var(--bg-soft); }
|
|
62
|
+
.glass-card::before { content: ''; position: absolute; top: 0; left: 0; right: 0; height: 1px; background: linear-gradient(90deg, transparent, var(--accent), transparent); opacity: 0; transition: opacity 0.4s; }
|
|
63
|
+
.glass-card:hover { background: var(--card-hover); border-color: var(--border-strong); transform: translateY(-4px); }
|
|
64
|
+
.glass-card:hover::before { opacity: 1; }
|
|
65
|
+
.reveal { opacity: 0; transform: translateY(var(--distance-medium)); transition: opacity var(--duration-very-slow) var(--ease-smooth-out), transform var(--duration-very-slow) var(--ease-smooth-out); }
|
|
66
|
+
.reveal.visible { opacity: 1; transform: translateY(0); filter: blur(0); }
|
|
67
|
+
.reveal-delay-1 { transition-delay: calc(var(--duration-stagger) * 1); } .reveal-delay-2 { transition-delay: calc(var(--duration-stagger) * 2); } .reveal-delay-3 { transition-delay: calc(var(--duration-stagger) * 3); } .reveal-delay-4 { transition-delay: calc(var(--duration-stagger) * 4); }
|
|
68
|
+
pre { background: var(--bg-code); border: 1px solid var(--border); border-radius: 10px; padding: 1.25rem 1.5rem; overflow-x: auto; font-family: 'JetBrains Mono', monospace; font-size: 12.5px; line-height: 1.75; margin: 0; color: #e8ecf3; }
|
|
69
|
+
.tok-kw{color:#60a5fa}.tok-str{color:#98c379}.tok-com{color:#64748b;font-style:italic}.tok-fn{color:#61afef}.tok-num{color:#d19a66}.tok-cls{color:#e5c07b}.tok-mod{color:#c678dd}
|
|
70
|
+
@keyframes float { 0%,100%{transform:translateY(0)} 50%{transform:translateY(-10px)} }
|
|
71
|
+
.floating { animation: float 6s ease-in-out infinite; }
|
|
72
|
+
@keyframes pulse-glow { 0%,100%{opacity:0.4;transform:scale(1)} 50%{opacity:0.8;transform:scale(1.05)} }
|
|
73
|
+
.arch-layer { border: 1px solid var(--border-strong); background: linear-gradient(135deg, var(--bg-elev) 0%, var(--bg-soft) 100%); transition: all 0.4s; }
|
|
74
|
+
[data-theme="dark"] .arch-layer { background: linear-gradient(135deg, var(--bg-elev) 0%, var(--bg-soft) 100%); }
|
|
75
|
+
.arch-layer:hover { border-color: var(--accent); transform: translateX(8px); }
|
|
76
|
+
.arch-layer:hover .arch-num { color: var(--accent); }
|
|
77
|
+
::-webkit-scrollbar { width: 8px; height: 8px; } ::-webkit-scrollbar-track { background: var(--bg); } ::-webkit-scrollbar-thumb { background: var(--border-strong); border-radius: 4px; } ::-webkit-scrollbar-thumb:hover { background: var(--accent); }
|
|
78
|
+
::selection { background: var(--accent); color: white; }
|
|
79
|
+
.tab-btn { padding: 0.55rem 1.1rem; border-radius: 6px; color: var(--muted); transition: all 0.2s; font-family: 'JetBrains Mono', monospace; font-size: 12.5px; border: 1px solid transparent; background: transparent; }
|
|
80
|
+
.tab-btn.active { background: var(--accent); color: white; }
|
|
81
|
+
.tab-btn:not(.active):hover { color: var(--fg); background: var(--card-hover); border-color: var(--border); }
|
|
82
|
+
input[type="range"] { -webkit-appearance: none; appearance: none; width: 100%; height: 3px; background: var(--border-strong); border-radius: 2px; outline: none; }
|
|
83
|
+
input[type="range"]::-webkit-slider-thumb { -webkit-appearance: none; appearance: none; width: 14px; height: 14px; background: var(--accent); border-radius: 50%; box-shadow: 0 0 12px var(--accent-glow); }
|
|
84
|
+
.timeline-item::before { content: ''; position: absolute; left: -1.7rem; top: 0.45rem; width: 12px; height: 12px; border-radius: 50%; background: var(--accent); box-shadow: 0 0 0 4px var(--accent-glow); }
|
|
85
|
+
.timeline-item.future::before { background: var(--bg-soft); border: 2px solid var(--accent); }
|
|
86
|
+
@keyframes marquee { from{transform:translateX(0)} to{transform:translateX(-50%)} }
|
|
87
|
+
.marquee-track { animation: marquee 40s linear infinite; display: flex; width: max-content; }
|
|
88
|
+
@media (hover: hover) and (pointer: fine) { .marquee-track:hover { animation-play-state: paused; } }
|
|
89
|
+
.lang-switch { background: var(--card); border: 1px solid var(--border); border-radius: 999px; padding: 3px; display: inline-flex; }
|
|
90
|
+
.lang-switch button { padding: 4px 11px; border-radius: 999px; font-size: 11px; color: var(--muted); transition: all 0.2s; font-family: 'JetBrains Mono', monospace; font-weight: 600; background: transparent; border: none; }
|
|
91
|
+
.lang-switch button.active { background: var(--accent); color: white; }
|
|
92
|
+
.theme-toggle-btn { width: 36px; height: 36px; display: flex; align-items: center; justify-content: center; border-radius: 999px; border: 1px solid var(--border); background: var(--card); transition: all 0.2s; color: var(--fg-dim); }
|
|
93
|
+
.theme-toggle-btn:hover { border-color: var(--accent); color: var(--accent); }
|
|
94
|
+
.section-num { font-family: 'JetBrains Mono', monospace; font-size: 11px; color: var(--accent); letter-spacing: 0.2em; font-weight: 500; }
|
|
95
|
+
details { border: 1px solid var(--border); border-radius: 10px; padding: 1.1rem 1.35rem; background: var(--card); transition: all 0.3s; }
|
|
96
|
+
[data-theme="light"] details { background: var(--bg-elev); }
|
|
97
|
+
details[open] { border-color: var(--accent); }
|
|
98
|
+
summary { font-weight: 600; list-style: none; display: flex; justify-content: space-between; align-items: center; color: var(--fg); cursor: pointer; gap: 1rem; }
|
|
99
|
+
summary::-webkit-details-marker { display: none; }
|
|
100
|
+
summary::after { content: '+'; font-size: 22px; color: var(--accent); transition: transform var(--duration-fast) var(--ease-in-out); font-weight: 300; flex-shrink: 0; }
|
|
101
|
+
details[open] summary::after { transform: rotate(45deg); }
|
|
102
|
+
details p { color: var(--fg-dim); margin-top: 0.75rem; line-height: 1.7; }
|
|
103
|
+
.compare-table { border-collapse: separate; border-spacing: 0; width: 100%; }
|
|
104
|
+
.compare-table th, .compare-table td { padding: 1rem 1.25rem; border-bottom: 1px solid var(--border); text-align: left; }
|
|
105
|
+
.compare-table th { color: var(--muted); font-weight: 500; font-size: 12px; text-transform: uppercase; letter-spacing: 0.08em; background: var(--bg-elev); }
|
|
106
|
+
.compare-table tr:hover td { background: var(--card-hover); }
|
|
107
|
+
.check { color: var(--teal); } .cross { color: var(--muted); opacity: 0.5; } .partial { color: #d97706; }
|
|
108
|
+
.feature-icon { width: 44px; height: 44px; border-radius: 10px; background: color-mix(in srgb, var(--accent) 15%, transparent); border: 1px solid color-mix(in srgb, var(--accent) 25%, transparent); display: flex; align-items: center; justify-content: center; color: var(--accent); transition: all 0.4s; flex-shrink: 0; }
|
|
109
|
+
.glass-card:hover .feature-icon { background: var(--accent); color: white; transform: rotate(-5deg) scale(1.05); box-shadow: 0 8px 24px var(--accent-glow); }
|
|
110
|
+
.scroll-hint { position: absolute; bottom: 2rem; left: 50%; transform: translateX(-50%); color: var(--muted); font-size: 11px; letter-spacing: 0.2em; text-transform: uppercase; font-family: 'JetBrains Mono', monospace; }
|
|
111
|
+
.scroll-hint::after { content: ''; display: block; width: 1px; height: 30px; background: linear-gradient(to bottom, var(--accent), transparent); margin: 8px auto 0; animation: scrollLine 2s ease-in-out infinite; }
|
|
112
|
+
@keyframes scrollLine { 0%,100%{transform:scaleY(1);transform-origin:top} 50%{transform:scaleY(0.4);transform-origin:top} }
|
|
113
|
+
.corner-mark { position: absolute; width: 12px; height: 12px; border-color: var(--accent); opacity: 0.6; }
|
|
114
|
+
.corner-mark.tl { top: 0; left: 0; border-top: 1px solid; border-left: 1px solid; }
|
|
115
|
+
.corner-mark.tr { top: 0; right: 0; border-top: 1px solid; border-right: 1px solid; }
|
|
116
|
+
.corner-mark.bl { bottom: 0; left: 0; border-bottom: 1px solid; border-left: 1px solid; }
|
|
117
|
+
.corner-mark.br { bottom: 0; right: 0; border-bottom: 1px solid; border-right: 1px solid; }
|
|
118
|
+
.nav-link { color: var(--fg-dim); font-size: 13.5px; transition: color 0.2s; position: relative; background: transparent; border: none; cursor: pointer; text-decoration: none; }
|
|
119
|
+
.nav-link:hover { color: var(--accent); }
|
|
120
|
+
.nav-link::after { content: ''; position: absolute; bottom: -4px; left: 0; width: 100%; height: 1px; background: var(--accent); transform: scaleX(0); transform-origin: left; transition: transform var(--duration-fast) var(--ease-smooth-out); }
|
|
121
|
+
@media (hover: hover) and (pointer: fine) { .nav-link:hover::after { transform: scaleX(1); } }
|
|
122
|
+
.badge-pill { display: inline-flex; align-items: center; gap: 8px; padding: 5px 12px; border-radius: 999px; background: color-mix(in srgb, var(--accent) 8%, transparent); border: 1px solid color-mix(in srgb, var(--accent) 30%, transparent); color: var(--accent); font-size: 11.5px; font-family: 'JetBrains Mono', monospace; font-weight: 500; }
|
|
123
|
+
.badge-pill .dot { width: 6px; height: 6px; background: var(--accent); border-radius: 50%; animation: pulse-glow 2s ease-in-out infinite; }
|
|
124
|
+
.grid-bg { background-image: linear-gradient(color-mix(in srgb, var(--accent) 4%, transparent) 1px, transparent 1px), linear-gradient(90deg, color-mix(in srgb, var(--accent) 4%, transparent) 1px, transparent 1px); background-size: 60px 60px; }
|
|
125
|
+
.blob { position: absolute; border-radius: 50%; filter: blur(80px); opacity: 0.18; pointer-events: none; }
|
|
126
|
+
[data-theme="dark"] .blob { opacity: 0.3; }
|
|
127
|
+
.stat-num { font-family: 'Space Grotesk', sans-serif; font-weight: 700; font-size: 2.5rem; line-height: 1; white-space: nowrap; background: linear-gradient(180deg, var(--fg) 0%, var(--muted) 100%); -webkit-background-clip: text; background-clip: text; -webkit-text-fill-color: transparent; }
|
|
128
|
+
.demo-tab { padding: 0.6rem 1.2rem; border-radius: 8px; font-family: 'JetBrains Mono', monospace; font-size: 12px; color: var(--muted); border: 1px solid var(--border); background: var(--card); transition: all 0.25s; display: inline-flex; align-items: center; gap: 8px; cursor: pointer; }
|
|
129
|
+
.demo-tab.active { background: var(--accent); color: white; border-color: var(--accent); }
|
|
130
|
+
.demo-tab:hover { color: var(--fg); border-color: var(--border-strong); }
|
|
131
|
+
.demo-panel { display: none; }
|
|
132
|
+
.demo-panel.active { display: block; opacity: 1; transform: none; filter: blur(0); transition: opacity var(--duration-slow) var(--ease-smooth-out), transform var(--duration-slow) var(--ease-smooth-out), filter var(--duration-slow) var(--ease-smooth-out); }
|
|
133
|
+
@starting-style { .demo-panel.active { opacity: 0; transform: translateY(var(--distance-base)); filter: blur(var(--blur-small)); } }
|
|
134
|
+
|
|
135
|
+
.param-label { display: flex; justify-content: space-between; align-items: center; font-size: 11px; margin-bottom: 6px; }
|
|
136
|
+
.param-label span:first-child { font-family: 'JetBrains Mono', monospace; color: var(--muted); text-transform: uppercase; letter-spacing: 0.08em; }
|
|
137
|
+
.param-label span:last-child { font-family: 'JetBrains Mono', monospace; color: var(--accent); font-weight: 600; }
|
|
138
|
+
.select-pill { display: inline-flex; gap: 4px; padding: 3px; border-radius: 8px; background: var(--bg-soft); border: 1px solid var(--border); flex-wrap: wrap; }
|
|
139
|
+
.select-pill button { padding: 4px 10px; border-radius: 5px; font-size: 11px; font-family: 'JetBrains Mono', monospace; color: var(--muted); transition: all 0.2s; background: transparent; border: none; cursor: pointer; }
|
|
140
|
+
.select-pill button.active { background: var(--accent); color: white; }
|
|
141
|
+
.play-btn { background: var(--accent); color: white; border: none; padding: 8px 18px; border-radius: 8px; font-family: 'JetBrains Mono', monospace; font-size: 12px; font-weight: 600; transition: all 0.2s; display: inline-flex; align-items: center; gap: 6px; cursor: pointer; }
|
|
142
|
+
.play-btn:hover { filter: brightness(1.1); box-shadow: 0 4px 16px var(--accent-glow); transform: translateY(-1px); }
|
|
143
|
+
.play-btn.ghost { background: var(--bg-soft); color: var(--fg-dim); border: 1px solid var(--border-strong); }
|
|
144
|
+
.stat-box { background: var(--bg-soft); border: 1px solid var(--border); border-radius: 8px; padding: 10px 14px; }
|
|
145
|
+
[data-theme="dark"] .stat-box { background: var(--bg-elev); }
|
|
146
|
+
.stat-box .label { font-family: 'JetBrains Mono', monospace; font-size: 10px; color: var(--muted); text-transform: uppercase; letter-spacing: 0.1em; }
|
|
147
|
+
.stat-box .value { font-family: 'JetBrains Mono', monospace; font-size: 18px; font-weight: 600; color: var(--accent); margin-top: 2px; }
|
|
148
|
+
.code-sync { background: var(--bg-code); border: 1px solid var(--border); border-radius: 8px; padding: 12px 16px; font-family: 'JetBrains Mono', monospace; font-size: 11.5px; line-height: 1.8; color: #e8ecf3; max-height: 260px; overflow-y: auto; }
|
|
149
|
+
.code-sync .highlight { color: var(--accent-3); } .code-sync .keyword { color: #60a5fa; } .code-sync .string { color: #98c379; } .code-sync .comment { color: #64748b; font-style: italic; }
|
|
150
|
+
.view { display: none; }
|
|
151
|
+
.view.active { display: block; opacity: 1; transform: none; transition: opacity var(--duration-slow) var(--ease-smooth-out), transform var(--duration-slow) var(--ease-smooth-out); }
|
|
152
|
+
@starting-style { .view.active { opacity: 0; transform: translateY(var(--distance-base)); } }
|
|
153
|
+
|
|
154
|
+
.magnetic { transition: transform var(--duration-fast) var(--ease-smooth-out); }
|
|
155
|
+
/* 记忆系统专属:召回演示的命中行 */
|
|
156
|
+
.hit-row { display: flex; align-items: flex-start; gap: 10px; padding: 9px 12px; border-radius: 8px; border: 1px solid var(--border); background: var(--bg-elev); transition: all 0.25s; }
|
|
157
|
+
.hit-row+.hit-row { margin-top: 6px; }
|
|
158
|
+
.hit-row.win { border-color: var(--accent); background: color-mix(in srgb, var(--accent) 8%, var(--bg-elev)); }
|
|
159
|
+
.hit-row .score { font-family: 'JetBrains Mono', monospace; font-size: 11px; font-weight: 600; color: var(--accent); flex-shrink: 0; }
|
|
160
|
+
.hit-row .txt { font-size: 12.5px; color: var(--fg-dim); line-height: 1.55; }
|
|
161
|
+
.lane-bar { height: 28px; border-radius: 6px; border: 1px solid var(--border); background: var(--bg-soft); position: relative; overflow: hidden; }
|
|
162
|
+
.lane-bar i { position: absolute; top: 0; bottom: 0; left: 0; width: 0; background: var(--accent); opacity: 0.85; transition: width var(--duration-fast) var(--ease-smooth-out); }
|
|
163
|
+
@media (prefers-reduced-motion: reduce) {
|
|
164
|
+
.reveal, .reveal-lead { opacity:1; transform:none; filter:none; transition:none; }
|
|
165
|
+
.marquee-track, .floating, .scroll-hint::after { animation: none; }
|
|
166
|
+
details p, details::details-content { filter: none; opacity: 1; transition: none; }
|
|
167
|
+
* { transition-duration: 0.01ms !important; animation-duration: 0.01ms !important; animation-iteration-count: 1 !important; }
|
|
34
168
|
}
|
|
35
|
-
html{scroll-behavior:smooth}
|
|
36
|
-
body{
|
|
37
|
-
font-family:var(--sans);
|
|
38
|
-
font-size:15.5px;
|
|
39
|
-
line-height:1.68;
|
|
40
|
-
color:var(--ink);
|
|
41
|
-
background:var(--paper);
|
|
42
|
-
/* 淡淡的制图纸网格,只在主体区域隐约可见 */
|
|
43
|
-
background-image:
|
|
44
|
-
linear-gradient(rgba(23,23,26,.035) 1px, transparent 1px),
|
|
45
|
-
linear-gradient(90deg, rgba(23,23,26,.035) 1px, transparent 1px);
|
|
46
|
-
background-size:72px 72px;
|
|
47
|
-
-webkit-font-smoothing:antialiased;
|
|
48
|
-
text-rendering:optimizeLegibility;
|
|
49
|
-
}
|
|
50
|
-
img{max-width:100%;display:block}
|
|
51
|
-
a{color:inherit}
|
|
52
|
-
code,kbd,pre,samp{font-family:var(--mono);font-size:.9em}
|
|
53
|
-
code{background:var(--paper-2);border:1px solid var(--line-soft);padding:1px 5px}
|
|
54
|
-
::selection{background:var(--accent);color:#fff}
|
|
55
169
|
|
|
56
|
-
/*
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
.js-reveal{opacity:0;transform:translateY(14px)}
|
|
62
|
-
.js-reveal.in{opacity:1;transform:none;transition:opacity .55s cubic-bezier(.2,.7,.2,1),transform .55s cubic-bezier(.2,.7,.2,1)}
|
|
170
|
+
/* ══════════════════════════════════════════════════════════
|
|
171
|
+
动效体系 · 按「用途」对齐 token(transitions.dev 刻度)
|
|
172
|
+
时长:stagger 40 / micro 80 / quick 150 / fast 250 / slow 400 / very-slow 500
|
|
173
|
+
缓动:smooth-out 为表面动效默认;图标与文字切换用 in-out;微光用 linear
|
|
174
|
+
══════════════════════════════════════════════════════════ */
|
|
63
175
|
|
|
64
|
-
/*
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
height:56px;display:flex;align-items:center;gap:20px;
|
|
73
|
-
}
|
|
74
|
-
.brand{display:flex;align-items:baseline;gap:10px;text-decoration:none}
|
|
75
|
-
.brand-name{font-weight:800;font-size:16px;letter-spacing:-.02em}
|
|
76
|
-
.brand-tag{font-family:var(--mono);font-size:11px;color:var(--accent);border:1px solid var(--accent);padding:1px 6px}
|
|
77
|
-
.topnav{margin-left:auto;display:flex;align-items:center;gap:2px}
|
|
78
|
-
.topnav a{
|
|
79
|
-
font-family:var(--mono);font-size:11.5px;letter-spacing:.1em;text-transform:uppercase;
|
|
80
|
-
color:var(--ink-2);text-decoration:none;padding:8px 12px;
|
|
81
|
-
border-left:1px solid transparent;
|
|
82
|
-
}
|
|
83
|
-
.topnav a:hover{color:var(--ink);border-left-color:var(--line)}
|
|
84
|
-
.topnav a .idx{color:var(--accent);margin-right:5px;font-size:10px}
|
|
85
|
-
.lang{display:inline-flex;border:1px solid var(--line);margin-left:10px}
|
|
86
|
-
.lang button{
|
|
87
|
-
border:0;background:transparent;color:var(--ink-2);
|
|
88
|
-
font-family:var(--mono);font-size:11.5px;cursor:pointer;
|
|
89
|
-
padding:6px 11px;letter-spacing:.06em;
|
|
176
|
+
/* 首屏文案:文字揭示(texts-reveal)—— 与通用 .reveal 分开,
|
|
177
|
+
只给 4 个首屏元素挂 2px 交叉模糊,避免 78 个元素一起跑 filter */
|
|
178
|
+
.reveal-lead { filter: blur(var(--blur-small)); }
|
|
179
|
+
.reveal-lead.reveal {
|
|
180
|
+
transition:
|
|
181
|
+
opacity var(--duration-very-slow) var(--ease-in-out),
|
|
182
|
+
transform var(--duration-very-slow) var(--ease-in-out),
|
|
183
|
+
filter var(--duration-very-slow) var(--ease-in-out);
|
|
90
184
|
}
|
|
91
|
-
.lang button.on{background:var(--ink);color:var(--paper)}
|
|
92
|
-
.lang button:not(.on):hover{color:var(--ink)}
|
|
93
185
|
|
|
94
|
-
/*
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
}
|
|
104
|
-
.
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
}
|
|
125
|
-
|
|
126
|
-
.
|
|
127
|
-
display:inline-flex;align-items:center;gap:10px;
|
|
128
|
-
padding:14px 20px;
|
|
129
|
-
font-size:13.5px;font-weight:700;text-decoration:none;cursor:pointer;
|
|
130
|
-
border:0;border-right:1px solid var(--line);
|
|
131
|
-
background:var(--paper);color:var(--ink);
|
|
132
|
-
transition:background .15s ease,color .15s ease;
|
|
133
|
-
}
|
|
134
|
-
.btn:last-child{border-right:0}
|
|
135
|
-
.btn:hover{background:var(--paper-2)}
|
|
136
|
-
.btn.primary{background:var(--ink);color:var(--paper)}
|
|
137
|
-
.btn.primary:hover{background:var(--accent)}
|
|
138
|
-
.btn code{background:transparent;border:0;padding:0;font-weight:700;font-size:12.5px}
|
|
139
|
-
.btn .copy{font-family:var(--mono);font-size:10.5px;font-weight:400;opacity:.55;text-transform:uppercase;letter-spacing:.1em}
|
|
140
|
-
.meta-line{
|
|
141
|
-
display:flex;flex-wrap:wrap;gap:0;
|
|
142
|
-
border-top:1px solid var(--line-soft);
|
|
143
|
-
font-family:var(--mono);font-size:11px;color:var(--ink-3);
|
|
144
|
-
}
|
|
145
|
-
.meta-line span{padding:8px 14px 8px 0;margin-right:14px;border-right:1px solid var(--line-soft)}
|
|
146
|
-
.meta-line span:last-child{border-right:0}
|
|
147
|
-
.meta-line b{color:var(--ink);font-weight:700}
|
|
186
|
+
/* 组件过渡:逐条列出具体属性,替掉此前的 transition: all。
|
|
187
|
+
后置规则覆盖前面的 transition: all,故原规则无需逐行改 */
|
|
188
|
+
.glass-card {
|
|
189
|
+
transition:
|
|
190
|
+
transform var(--duration-fast) var(--ease-smooth-out),
|
|
191
|
+
scale var(--duration-quick) var(--ease-out),
|
|
192
|
+
border-color var(--duration-fast) var(--ease-out),
|
|
193
|
+
background-color var(--duration-fast) var(--ease-out),
|
|
194
|
+
box-shadow var(--duration-fast) var(--ease-out);
|
|
195
|
+
}
|
|
196
|
+
.arch-layer {
|
|
197
|
+
transition: transform var(--duration-fast) var(--ease-smooth-out), border-color var(--duration-fast) var(--ease-out), scale var(--duration-quick) var(--ease-out);
|
|
198
|
+
}
|
|
199
|
+
.arch-num { transition: color var(--duration-fast) var(--ease-out); }
|
|
200
|
+
.feature-icon {
|
|
201
|
+
transition:
|
|
202
|
+
transform var(--duration-fast) var(--ease-smooth-out),
|
|
203
|
+
background-color var(--duration-fast) var(--ease-out),
|
|
204
|
+
color var(--duration-fast) var(--ease-out),
|
|
205
|
+
box-shadow var(--duration-fast) var(--ease-out);
|
|
206
|
+
}
|
|
207
|
+
.btn-primary, .btn-ghost, .play-btn, .tab-btn, .demo-tab,
|
|
208
|
+
.select-pill button, .lang-switch button, .theme-toggle-btn, .copy-el {
|
|
209
|
+
transition:
|
|
210
|
+
scale var(--duration-quick) var(--ease-out),
|
|
211
|
+
background-color var(--duration-fast) var(--ease-out),
|
|
212
|
+
border-color var(--duration-fast) var(--ease-out),
|
|
213
|
+
color var(--duration-fast) var(--ease-out),
|
|
214
|
+
box-shadow var(--duration-fast) var(--ease-smooth-out),
|
|
215
|
+
filter var(--duration-fast) var(--ease-out);
|
|
216
|
+
}
|
|
217
|
+
details { transition: border-color var(--duration-fast) var(--ease-out), background-color var(--duration-fast) var(--ease-out); }
|
|
218
|
+
.hit-row { transition: border-color var(--duration-fast) var(--ease-out), background-color var(--duration-fast) var(--ease-out); }
|
|
148
219
|
|
|
149
|
-
/*
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
.
|
|
153
|
-
|
|
154
|
-
padding:0;position:relative;
|
|
155
|
-
}
|
|
156
|
-
.sch-head{
|
|
157
|
-
display:flex;justify-content:space-between;align-items:center;
|
|
158
|
-
padding:10px 14px;border-bottom:1px solid var(--line);
|
|
159
|
-
font-family:var(--mono);font-size:10.5px;letter-spacing:.14em;text-transform:uppercase;
|
|
160
|
-
}
|
|
161
|
-
.sch-head .live{color:var(--accent);display:inline-flex;align-items:center;gap:6px;font-weight:700}
|
|
162
|
-
.sch-head .live::before{
|
|
163
|
-
content:"";width:7px;height:7px;background:var(--accent);
|
|
164
|
-
animation:blink 1.6s steps(2,start) infinite;
|
|
165
|
-
}
|
|
166
|
-
@keyframes blink{50%{opacity:.25}}
|
|
167
|
-
.sch-body{padding:18px 14px 14px;display:grid;gap:14px}
|
|
168
|
-
.pipe{display:grid;grid-template-columns:88px 1fr;gap:12px;align-items:center}
|
|
169
|
-
.pipe .st{
|
|
170
|
-
font-family:var(--mono);font-size:10px;letter-spacing:.1em;text-transform:uppercase;
|
|
171
|
-
color:var(--ink-2);border:1px solid var(--line-soft);padding:5px 7px;text-align:center;
|
|
172
|
-
}
|
|
173
|
-
.pipe .st b{display:block;color:var(--ink);font-size:11px}
|
|
174
|
-
.pipe .lane{position:relative;height:34px;border:1px solid var(--line-soft);background:var(--paper);overflow:hidden}
|
|
175
|
-
.lane .ticks{position:absolute;inset:0;background-image:repeating-linear-gradient(90deg,var(--line-soft) 0 1px,transparent 1px 18px);opacity:.5}
|
|
176
|
-
.lane .bar{
|
|
177
|
-
position:absolute;top:9px;bottom:9px;left:0;width:0;
|
|
178
|
-
background:var(--ink);
|
|
179
|
-
}
|
|
180
|
-
.lane .bar.hot{background:var(--accent)}
|
|
181
|
-
/* 各级不同的推进节奏 */
|
|
182
|
-
.lane .bar.b-obs{animation:fill 6s cubic-bezier(.3,.6,.3,1) infinite}
|
|
183
|
-
.lane .bar.b-vec{animation:fill 6s cubic-bezier(.3,.6,.3,1) infinite;animation-delay:.9s}
|
|
184
|
-
.lane .bar.b-ret{animation:fill 6s cubic-bezier(.3,.6,.3,1) infinite;animation-delay:1.8s}
|
|
185
|
-
.lane .bar.b-inj{animation:fill 6s cubic-bezier(.3,.6,.3,1) infinite;animation-delay:2.7s}
|
|
186
|
-
@keyframes fill{0%{width:0;opacity:0}6%{opacity:1}34%{width:100%;opacity:1}46%{opacity:0}100%{width:100%;opacity:0}}
|
|
187
|
-
/* 记忆库栅格 */
|
|
188
|
-
.store{
|
|
189
|
-
border:1px solid var(--line);background:var(--paper);
|
|
190
|
-
display:grid;grid-template-columns:repeat(12,1fr);
|
|
191
|
-
}
|
|
192
|
-
.store .cell{
|
|
193
|
-
aspect-ratio:1/1;border-right:1px solid var(--line-soft);border-bottom:1px solid var(--line-soft);
|
|
194
|
-
position:relative;background:#fff;
|
|
195
|
-
}
|
|
196
|
-
.store .cell:nth-child(12n){border-right:0}
|
|
197
|
-
.store .cell.hit::after{
|
|
198
|
-
content:"";position:absolute;inset:3px;background:var(--accent);
|
|
199
|
-
animation:cell-hit 6s steps(1,end) infinite;
|
|
200
|
-
}
|
|
201
|
-
.store .cell:nth-child(7)::after{animation-delay:.9s}
|
|
202
|
-
.store .cell:nth-child(19)::after{animation-delay:1.4s}
|
|
203
|
-
.store .cell:nth-child(28)::after{animation-delay:1.8s}
|
|
204
|
-
.store .cell:nth-child(41)::after{animation-delay:2.3s}
|
|
205
|
-
@keyframes cell-hit{0%,12%{opacity:0}16%,34%{opacity:1}40%,100%{opacity:0}}
|
|
206
|
-
.store-cap{
|
|
207
|
-
display:flex;justify-content:space-between;
|
|
208
|
-
font-family:var(--mono);font-size:10px;color:var(--ink-3);
|
|
209
|
-
padding:6px 2px 0;letter-spacing:.1em;text-transform:uppercase;
|
|
210
|
-
}
|
|
211
|
-
.store-cap b{color:var(--accent);font-weight:700}
|
|
212
|
-
.sch-foot{
|
|
213
|
-
border-top:1px solid var(--line);padding:9px 14px;
|
|
214
|
-
display:flex;justify-content:space-between;gap:12px;
|
|
215
|
-
font-family:var(--mono);font-size:10.5px;color:var(--ink-2);
|
|
216
|
-
}
|
|
217
|
-
.sch-foot .zero{color:var(--ink);font-weight:700}
|
|
218
|
-
.sch-foot .zero::before{content:"×0 ";color:var(--accent)}
|
|
219
|
-
|
|
220
|
-
/* ── 大数字带 ── */
|
|
221
|
-
.stats-band{border-bottom:1px solid var(--line)}
|
|
222
|
-
.stats-grid{
|
|
223
|
-
max-width:var(--max);margin:0 auto;
|
|
224
|
-
display:grid;grid-template-columns:repeat(4,1fr);
|
|
225
|
-
border-left:1px solid var(--line);
|
|
226
|
-
}
|
|
227
|
-
.stat-cell{
|
|
228
|
-
border-right:1px solid var(--line);padding:26px 24px 22px;
|
|
229
|
-
}
|
|
230
|
-
.stat-cell .v{
|
|
231
|
-
font-size:clamp(30px,3.4vw,44px);font-weight:800;letter-spacing:-.03em;line-height:1;
|
|
232
|
-
font-variant-numeric:tabular-nums;
|
|
233
|
-
}
|
|
234
|
-
.stat-cell .v .u{font-size:.45em;font-weight:700;color:var(--ink-3);margin-left:4px;letter-spacing:0}
|
|
235
|
-
.stat-cell .l{font-family:var(--mono);font-size:10.5px;letter-spacing:.12em;text-transform:uppercase;color:var(--ink-2);margin-top:10px}
|
|
236
|
-
.stat-cell.hot .v{color:var(--accent)}
|
|
237
|
-
|
|
238
|
-
/* ── 章节头:编号 + 大标题 ── */
|
|
239
|
-
section.block{border-bottom:1px solid var(--line);padding:64px 0}
|
|
240
|
-
.sec-head{display:grid;grid-template-columns:120px 1fr;gap:24px;margin-bottom:40px;align-items:start}
|
|
241
|
-
.sec-num{
|
|
242
|
-
font-family:var(--mono);font-size:12px;color:var(--ink-3);letter-spacing:.1em;
|
|
243
|
-
border-top:3px solid var(--accent);padding-top:8px;
|
|
244
|
-
}
|
|
245
|
-
.sec-num b{display:block;font-size:26px;color:var(--ink);font-weight:800;letter-spacing:-.02em;margin-bottom:2px}
|
|
246
|
-
h2{
|
|
247
|
-
font-size:clamp(28px,3.6vw,44px);line-height:1.06;letter-spacing:-.025em;font-weight:800;margin:0 0 12px;
|
|
248
|
-
}
|
|
249
|
-
.sec-sub{font-size:15px;color:var(--ink-2);max-width:52em;margin:0;line-height:1.7}
|
|
250
|
-
|
|
251
|
-
/* ── 管线一节(原数据流):三站纵向排 ── */
|
|
252
|
-
.pipe-flow{display:grid;grid-template-columns:1fr 1fr 1fr;border:1px solid var(--line);background:#fff}
|
|
253
|
-
.pf-cell{padding:24px 24px 22px;border-right:1px solid var(--line);position:relative}
|
|
254
|
-
.pf-cell:last-child{border-right:0}
|
|
255
|
-
.pf-cell .pf-tag{
|
|
256
|
-
font-family:var(--mono);font-size:10.5px;letter-spacing:.14em;text-transform:uppercase;
|
|
257
|
-
color:var(--accent);font-weight:700;margin-bottom:14px;display:block;
|
|
258
|
-
}
|
|
259
|
-
.pf-cell h3{font-size:19px;font-weight:800;letter-spacing:-.015em;margin:0 0 8px;line-height:1.25}
|
|
260
|
-
.pf-cell p{margin:0 0 12px;font-size:13.5px;color:var(--ink-2);line-height:1.65}
|
|
261
|
-
.pf-cell ul{margin:0;padding:0;list-style:none}
|
|
262
|
-
.pf-cell li{
|
|
263
|
-
font-size:12.5px;color:var(--ink-2);padding:6px 0 6px 16px;position:relative;
|
|
264
|
-
border-top:1px solid var(--line-soft);line-height:1.55;
|
|
265
|
-
}
|
|
266
|
-
.pf-cell li::before{content:"";position:absolute;left:0;top:13px;width:8px;height:1.5px;background:var(--accent)}
|
|
267
|
-
.flow-note{
|
|
268
|
-
margin-top:22px;padding:14px 18px;border:1px solid var(--line);background:var(--paper-2);
|
|
269
|
-
font-size:13px;line-height:1.65;color:var(--ink-2);
|
|
270
|
-
display:grid;grid-template-columns:auto 1fr;gap:14px;align-items:start;
|
|
271
|
-
}
|
|
272
|
-
.flow-note .fn-tag{font-family:var(--mono);font-size:10.5px;font-weight:700;letter-spacing:.12em;text-transform:uppercase;color:var(--accent);white-space:nowrap;padding-top:2px}
|
|
273
|
-
.flow-note b{color:var(--ink)}
|
|
274
|
-
|
|
275
|
-
/* ── 架构分层 + 实现状态板 ── */
|
|
276
|
-
.arch{margin-top:22px;border:1px solid var(--line);background:var(--ink);color:#E8E4DC}
|
|
277
|
-
.arch-head{
|
|
278
|
-
display:flex;justify-content:space-between;align-items:center;
|
|
279
|
-
padding:9px 14px;border-bottom:1px solid rgba(255,255,255,.18);
|
|
280
|
-
font-family:var(--mono);font-size:10.5px;letter-spacing:.14em;text-transform:uppercase;
|
|
281
|
-
}
|
|
282
|
-
.arch-head .arch-link a{color:#FF9763;text-decoration:none}
|
|
283
|
-
.arch-head .arch-link a:hover{text-decoration:underline}
|
|
284
|
-
.arch-cols{display:grid;grid-template-columns:1fr 1fr;gap:0}
|
|
285
|
-
.arch-col{padding:16px 14px 10px;border-right:1px solid rgba(255,255,255,.12)}
|
|
286
|
-
.arch-col:last-child{border-right:0}
|
|
287
|
-
.ac-title{
|
|
288
|
-
font-family:var(--mono);font-size:10px;letter-spacing:.12em;text-transform:uppercase;
|
|
289
|
-
color:rgba(232,228,220,.55);margin-bottom:10px;
|
|
290
|
-
}
|
|
291
|
-
.mnode{
|
|
292
|
-
display:grid;grid-template-columns:14px 52px 1fr;align-items:center;gap:8px;
|
|
293
|
-
width:100%;text-align:left;
|
|
294
|
-
background:transparent;border:0;border-top:1px solid rgba(255,255,255,.08);
|
|
295
|
-
color:#E8E4DC;font:inherit;font-size:12.5px;
|
|
296
|
-
padding:9px 6px;cursor:pointer;
|
|
297
|
-
transition:background .15s ease;
|
|
298
|
-
}
|
|
299
|
-
.mnode:hover{background:rgba(255,255,255,.07)}
|
|
300
|
-
.mnode i{width:8px;height:8px;border-radius:50%;justify-self:center}
|
|
301
|
-
.mnode.live i{background:#5BC98C;box-shadow:0 0 0 3px rgba(91,201,140,.18)}
|
|
302
|
-
.mnode.tested i{background:#E9A23B;box-shadow:0 0 0 3px rgba(233,162,59,.16)}
|
|
303
|
-
.mnode.queued i{background:transparent;border:1.5px solid rgba(232,228,220,.4)}
|
|
304
|
-
.mnode b{font-family:var(--mono);font-size:11px;color:rgba(232,228,220,.85);font-weight:700}
|
|
305
|
-
.mnode span{color:rgba(232,228,220,.88)}
|
|
306
|
-
.m-detail{
|
|
307
|
-
border-top:1px solid rgba(255,255,255,.18);
|
|
308
|
-
background:rgba(255,255,255,.05);
|
|
309
|
-
}
|
|
310
|
-
.m-detail[hidden]{display:none}
|
|
311
|
-
.md-head{
|
|
312
|
-
display:flex;align-items:center;gap:10px;
|
|
313
|
-
padding:10px 14px;border-bottom:1px solid rgba(255,255,255,.1);
|
|
314
|
-
font-size:12.5px;
|
|
315
|
-
}
|
|
316
|
-
.md-head b{font-family:var(--mono);color:#FF9763;font-size:12px}
|
|
317
|
-
.md-head .md-state{
|
|
318
|
-
margin-left:auto;font-family:var(--mono);font-size:10px;letter-spacing:.1em;
|
|
319
|
-
text-transform:uppercase;color:#5BC98C;border:1px solid rgba(91,201,140,.45);padding:1px 7px;
|
|
320
|
-
}
|
|
321
|
-
.md-head .md-state.tested{color:#E9A23B;border-color:rgba(233,162,59,.5)}
|
|
322
|
-
.md-head .md-state.queued{color:rgba(232,228,220,.6);border-color:rgba(232,228,220,.3)}
|
|
323
|
-
.md-head .md-close{
|
|
324
|
-
background:transparent;border:1px solid rgba(255,255,255,.3);color:rgba(232,228,220,.8);
|
|
325
|
-
width:20px;height:20px;line-height:1;cursor:pointer;font-size:13px;padding:0;
|
|
326
|
-
}
|
|
327
|
-
.md-head .md-close:hover{background:var(--accent);border-color:var(--accent);color:#fff}
|
|
328
|
-
.md-body{
|
|
329
|
-
padding:12px 14px;font-size:12px;line-height:1.7;color:rgba(232,228,220,.85);
|
|
330
|
-
max-height:150px;overflow-y:auto;scrollbar-width:thin;
|
|
331
|
-
}
|
|
332
|
-
.arch-cap{
|
|
333
|
-
padding:9px 14px;border-top:1px solid rgba(255,255,255,.18);
|
|
334
|
-
font-size:12px;color:rgba(232,228,220,.72);line-height:1.6;
|
|
335
|
-
display:flex;flex-wrap:wrap;gap:6px 16px;align-items:center;
|
|
336
|
-
}
|
|
337
|
-
.arch-cap .lg{display:inline-flex;align-items:center;gap:6px;font-family:var(--mono);font-size:10px;letter-spacing:.06em}
|
|
338
|
-
.arch-cap .lg .dot{width:8px;height:8px;border-radius:50%;display:inline-block}
|
|
339
|
-
.arch-cap .lg .dot.live{background:#5BC98C}
|
|
340
|
-
.arch-cap .lg .dot.tested{background:#E9A23B}
|
|
341
|
-
.arch-cap .lg .dot.queued{background:transparent;border:1.5px solid rgba(232,228,220,.4)}
|
|
342
|
-
.arch-cap-sep{color:rgba(232,228,220,.3)}
|
|
343
|
-
|
|
344
|
-
/* ── 宣传图轮播:纯 CSS scroll-snap 翻页 ── */
|
|
345
|
-
.promo{margin-top:22px;border:1px solid var(--line);background:#fff;position:relative}
|
|
346
|
-
.promo-track{
|
|
347
|
-
display:grid;grid-auto-flow:column;
|
|
348
|
-
grid-auto-columns:100%;
|
|
349
|
-
overflow-x:auto;scroll-snap-type:x mandatory;
|
|
350
|
-
scrollbar-width:none;
|
|
351
|
-
}
|
|
352
|
-
.promo-track::-webkit-scrollbar{display:none}
|
|
353
|
-
.promo-track img{
|
|
354
|
-
width:100%;height:auto;display:block;
|
|
355
|
-
scroll-snap-align:start;scroll-snap-stop:always;
|
|
356
|
-
aspect-ratio:16/9;object-fit:cover;background:var(--paper-2);
|
|
357
|
-
}
|
|
358
|
-
.promo-nav{
|
|
359
|
-
display:flex;justify-content:space-between;align-items:center;
|
|
360
|
-
border-top:1px solid var(--line);padding:8px 12px;
|
|
361
|
-
}
|
|
362
|
-
.promo-dots{display:flex;gap:8px}
|
|
363
|
-
.promo-dots a{
|
|
364
|
-
width:10px;height:10px;border:1.5px solid var(--ink-3);display:block;
|
|
365
|
-
transition:background .15s ease,border-color .15s ease;
|
|
366
|
-
}
|
|
367
|
-
.promo-dots a:hover{border-color:var(--accent);background:var(--accent)}
|
|
368
|
-
.promo-cap{font-family:var(--mono);font-size:10px;letter-spacing:.12em;text-transform:uppercase;color:var(--ink-3)}
|
|
369
|
-
.promo-btn{
|
|
370
|
-
background:transparent;border:1px solid var(--line);color:var(--ink);
|
|
371
|
-
font-family:var(--mono);font-size:11px;padding:4px 12px;cursor:pointer;
|
|
372
|
-
text-decoration:none;letter-spacing:.08em;
|
|
373
|
-
}
|
|
374
|
-
.promo-btn:hover{background:var(--ink);color:var(--paper)}
|
|
375
|
-
/* :target 翻页——点击圆点滚动到对应帧 */
|
|
376
|
-
.promo-frame:target{scroll-snap-align:start}
|
|
377
|
-
|
|
378
|
-
/* ── 设计文献行 ── */
|
|
379
|
-
.papers{border-top:1px solid rgba(255,255,255,.18)}
|
|
380
|
-
.papers-head{
|
|
381
|
-
padding:9px 14px;
|
|
382
|
-
font-family:var(--mono);font-size:10px;letter-spacing:.14em;text-transform:uppercase;
|
|
383
|
-
color:rgba(232,228,220,.55);border-bottom:1px solid rgba(255,255,255,.08);
|
|
384
|
-
}
|
|
385
|
-
.paper-row{
|
|
386
|
-
display:grid;grid-template-columns:34px 1fr auto;gap:12px;align-items:center;
|
|
387
|
-
padding:10px 14px;border-bottom:1px solid rgba(255,255,255,.08);
|
|
388
|
-
text-decoration:none;transition:background .15s ease;
|
|
389
|
-
}
|
|
390
|
-
.paper-row:last-child{border-bottom:0}
|
|
391
|
-
.paper-row:hover{background:rgba(255,255,255,.07)}
|
|
392
|
-
.paper-row .pr-no{font-family:var(--mono);font-size:11px;color:#FF9763;font-weight:700}
|
|
393
|
-
.paper-row .pr-body{display:grid;gap:2px;min-width:0}
|
|
394
|
-
.paper-row .pr-body b{font-size:12.5px;font-weight:700;color:#E8E4DC}
|
|
395
|
-
.paper-row .pr-body small{font-size:11px;color:rgba(232,228,220,.6);line-height:1.5}
|
|
396
|
-
.paper-row .pr-arrow{font-family:var(--mono);color:rgba(232,228,220,.4);transition:color .15s ease,transform .15s ease}
|
|
397
|
-
.paper-row:hover .pr-arrow{color:#FF9763;transform:translateX(3px)}
|
|
398
|
-
|
|
399
|
-
/* ── 功能节:左文右图,细线分区,编号驱动 ── */
|
|
400
|
-
.feature{padding:44px 0;border-top:1px solid var(--line-soft)}
|
|
401
|
-
.feature:first-of-type{border-top:0;padding-top:8px}
|
|
402
|
-
.feature-grid{display:grid;grid-template-columns:1fr 1fr;gap:48px;align-items:start}
|
|
403
|
-
.feature-grid.reverse .f-visual{order:-1}
|
|
404
|
-
.f-meta{
|
|
405
|
-
font-family:var(--mono);font-size:11px;letter-spacing:.14em;text-transform:uppercase;
|
|
406
|
-
color:var(--accent);font-weight:700;margin-bottom:12px;display:flex;align-items:center;gap:8px;
|
|
407
|
-
}
|
|
408
|
-
.f-meta::after{content:"";flex:1;height:1px;background:var(--line-soft)}
|
|
409
|
-
.feature h3{font-size:clamp(21px,2.4vw,28px);line-height:1.18;letter-spacing:-.02em;font-weight:800;margin:0 0 12px}
|
|
410
|
-
.feature p.lede2{font-size:14.5px;color:var(--ink-2);margin:0 0 18px;line-height:1.72}
|
|
411
|
-
.feat-list{margin:0;padding:0;list-style:none;border-top:1px solid var(--line)}
|
|
412
|
-
.feat-list li{
|
|
413
|
-
font-size:13.5px;color:var(--ink-2);line-height:1.6;
|
|
414
|
-
padding:9px 0 9px 20px;position:relative;border-bottom:1px solid var(--line-soft);
|
|
415
|
-
}
|
|
416
|
-
.feat-list li::before{
|
|
417
|
-
content:"";position:absolute;left:2px;top:16px;width:7px;height:7px;
|
|
418
|
-
border:1.5px solid var(--accent);
|
|
419
|
-
}
|
|
420
|
-
.f-visual{border:1px solid var(--line);background:#fff;position:relative}
|
|
421
|
-
.f-visual .vbar{
|
|
422
|
-
display:flex;justify-content:space-between;align-items:center;
|
|
423
|
-
padding:8px 12px;border-bottom:1px solid var(--line);
|
|
424
|
-
font-family:var(--mono);font-size:10px;letter-spacing:.14em;text-transform:uppercase;color:var(--ink-3);
|
|
425
|
-
}
|
|
426
|
-
.f-visual .vbar .dots{display:inline-flex;gap:5px}
|
|
427
|
-
.f-visual .vbar .dots i{width:8px;height:8px;border:1px solid var(--ink-3);display:inline-block}
|
|
428
|
-
.f-visual img{width:100%;height:auto;display:block}
|
|
429
|
-
/* 无人值守数字组 */
|
|
430
|
-
.mini-stats{display:grid;grid-template-columns:repeat(3,1fr);border:1px solid var(--line);margin-top:18px}
|
|
431
|
-
.mini-stats .ms{padding:12px 14px;border-right:1px solid var(--line);background:#fff}
|
|
432
|
-
.mini-stats .ms:last-child{border-right:0}
|
|
433
|
-
.mini-stats .v{font-size:24px;font-weight:800;letter-spacing:-.02em;line-height:1;font-variant-numeric:tabular-nums}
|
|
434
|
-
.mini-stats .l{font-family:var(--mono);font-size:9.5px;letter-spacing:.1em;text-transform:uppercase;color:var(--ink-3);margin-top:6px;line-height:1.4}
|
|
435
|
-
/* 三层记忆表 */
|
|
436
|
-
.mem-table{border:1px solid var(--line);margin-top:16px;background:#fff}
|
|
437
|
-
.mem-row{display:grid;grid-template-columns:1.05fr 1.5fr 1.45fr;border-top:1px solid var(--line-soft)}
|
|
438
|
-
.mem-row:first-child{border-top:0;background:var(--paper-2)}
|
|
439
|
-
.mem-row > div{padding:10px 13px;font-size:13px;color:var(--ink-2);line-height:1.55;border-right:1px solid var(--line-soft)}
|
|
440
|
-
.mem-row > div:last-child{border-right:0}
|
|
441
|
-
.mem-row > div:first-child{color:var(--ink);font-weight:700}
|
|
442
|
-
.mem-row.head > div{font-family:var(--mono);font-size:10px;letter-spacing:.12em;text-transform:uppercase;color:var(--ink-3);font-weight:700}
|
|
443
|
-
.mem-pill{font-family:var(--mono);font-size:10px;color:var(--accent);border:1px solid var(--accent);padding:0 5px;margin-right:5px;white-space:nowrap}
|
|
444
|
-
|
|
445
|
-
/* ── 画廊:十二列网格 + 细线框 ── */
|
|
446
|
-
.gallery-grid{display:grid;grid-template-columns:repeat(12,1fr);gap:0;border:1px solid var(--line);background:var(--line-soft)}
|
|
447
|
-
.g-card{position:relative;background:#fff;overflow:hidden;grid-column:span 6;border:1px solid var(--paper);margin:-.5px}
|
|
448
|
-
.g-card.span-12{grid-column:span 12}
|
|
449
|
-
.g-card img{width:100%;height:auto;display:block;filter:grayscale(18%) contrast(1.02)}
|
|
450
|
-
.g-card:hover img{filter:none}
|
|
451
|
-
.g-card .cap{
|
|
452
|
-
display:flex;justify-content:space-between;align-items:baseline;gap:10px;
|
|
453
|
-
padding:9px 13px;border-top:1px solid var(--line);background:var(--paper);
|
|
454
|
-
font-size:12.5px;font-weight:700;
|
|
455
|
-
}
|
|
456
|
-
.g-card .cap small{font-family:var(--mono);font-weight:400;font-size:10.5px;color:var(--ink-3);letter-spacing:.06em;text-align:right}
|
|
457
|
-
|
|
458
|
-
/* ── 安装:四步条带 + AI 框 ── */
|
|
459
|
-
.qs-grid{display:grid;grid-template-columns:1fr 1fr;border:1px solid var(--line);background:#fff}
|
|
460
|
-
.qs-cell{padding:22px 24px;border-right:1px solid var(--line);border-bottom:1px solid var(--line)}
|
|
461
|
-
.qs-cell:nth-child(2n){border-right:0}
|
|
462
|
-
.qs-cell:nth-last-child(-n+2){border-bottom:0}
|
|
463
|
-
.qs-cell h3{font-size:15px;margin:0 0 8px;font-weight:800;display:flex;align-items:baseline;gap:10px}
|
|
464
|
-
.qs-cell h3 .n{font-family:var(--mono);font-size:12px;color:var(--accent);font-weight:700}
|
|
465
|
-
.qs-cell p{margin:0 0 10px;color:var(--ink-2);font-size:13px;line-height:1.65}
|
|
466
|
-
.codebox{border:1px solid var(--line);background:var(--ink);color:#E8E4DC}
|
|
467
|
-
.codebox-head{
|
|
468
|
-
display:flex;align-items:center;justify-content:space-between;
|
|
469
|
-
padding:7px 12px;border-bottom:1px solid rgba(255,255,255,.16);
|
|
470
|
-
font-family:var(--mono);font-size:10px;letter-spacing:.14em;text-transform:uppercase;color:rgba(232,228,220,.6);
|
|
471
|
-
}
|
|
472
|
-
.codebox pre{margin:0;padding:13px 14px;font-size:12.5px;line-height:1.65;white-space:pre-wrap;word-break:break-word}
|
|
473
|
-
.copy-btn{
|
|
474
|
-
border:1px solid rgba(255,255,255,.3);background:transparent;color:rgba(232,228,220,.75);
|
|
475
|
-
font-family:var(--mono);font-size:10px;padding:3px 9px;cursor:pointer;letter-spacing:.1em;text-transform:uppercase;
|
|
476
|
-
}
|
|
477
|
-
.copy-btn:hover{background:var(--accent);border-color:var(--accent);color:#fff}
|
|
478
|
-
.ai-box{margin-top:22px;border:1px solid var(--line);padding:20px 24px;background:var(--paper-2)}
|
|
479
|
-
.ai-box h3{margin:0 0 8px;font-size:15px;font-weight:800;display:flex;align-items:center;gap:10px}
|
|
480
|
-
.ai-box h3 .ai-tag{font-family:var(--mono);font-size:10px;letter-spacing:.14em;text-transform:uppercase;color:var(--paper);background:var(--accent);padding:2px 8px;font-weight:700}
|
|
481
|
-
.ai-box p{margin:0 0 10px;color:var(--ink-2);font-size:13px}
|
|
220
|
+
/* 按压反馈:用独立的 scale 属性 —— 不与 .magnetic 写在元素 style 上的
|
|
221
|
+
transform 冲突(内联样式优先级高于样式表,用 transform 会被静默吃掉) */
|
|
222
|
+
.btn-primary:active, .btn-ghost:active, .play-btn:active, .demo-tab:active,
|
|
223
|
+
.tab-btn:active, .select-pill button:active, .lang-switch button:active,
|
|
224
|
+
.theme-toggle-btn:active, .copy-el:active, .glass-card:active { scale: 0.97; }
|
|
482
225
|
|
|
483
|
-
/*
|
|
484
|
-
|
|
485
|
-
|
|
486
|
-
|
|
487
|
-
|
|
488
|
-
|
|
489
|
-
.comm-cell .ref{font-family:var(--mono);font-size:11px;color:var(--ink-3);margin-top:4px}
|
|
490
|
-
.comm-cell .ref a{color:var(--accent-ink);text-decoration:underline;text-underline-offset:2px}
|
|
491
|
-
.comm-cell .contrib{margin-top:10px;font-size:13.5px;color:var(--ink-2);line-height:1.65;border-top:1px solid var(--line-soft);padding-top:10px}
|
|
492
|
-
.links-row{margin-top:20px;display:flex;flex-wrap:wrap;gap:0;border:1px solid var(--line);width:fit-content;background:#fff}
|
|
493
|
-
.link-chip{
|
|
494
|
-
display:inline-flex;align-items:center;gap:8px;text-decoration:none;
|
|
495
|
-
padding:11px 18px;border-right:1px solid var(--line);
|
|
496
|
-
font-family:var(--mono);font-size:12px;color:var(--ink);
|
|
226
|
+
/* 悬停位移只在真有指针的设备上生效(触屏 tap 会留下假 hover) */
|
|
227
|
+
@media (hover: hover) and (pointer: fine) {
|
|
228
|
+
.glass-card:hover { transform: translateY(-4px); }
|
|
229
|
+
.arch-layer:hover { transform: translateX(var(--distance-base)); }
|
|
230
|
+
.glass-card:hover .feature-icon { background: var(--accent); color: #fff; transform: rotate(-5deg) scale(1.05); box-shadow: 0 8px 24px var(--accent-glow); }
|
|
231
|
+
.play-btn:hover { transform: translateY(-1px); }
|
|
497
232
|
}
|
|
498
|
-
.link-chip:last-child{border-right:0}
|
|
499
|
-
.link-chip:hover{background:var(--ink);color:var(--paper)}
|
|
500
|
-
.link-chip svg{width:14px;height:14px;stroke:currentColor;fill:none;stroke-width:1.6;stroke-linecap:round;stroke-linejoin:round}
|
|
501
233
|
|
|
502
|
-
/*
|
|
503
|
-
|
|
504
|
-
|
|
505
|
-
|
|
506
|
-
|
|
507
|
-
|
|
508
|
-
|
|
509
|
-
|
|
510
|
-
|
|
511
|
-
|
|
512
|
-
|
|
513
|
-
|
|
514
|
-
|
|
515
|
-
}
|
|
516
|
-
.ft-credits .ftc-label{color:var(--accent);font-weight:700;letter-spacing:.14em}
|
|
517
|
-
.ft-credits span:nth-child(2){color:var(--ink-2)}
|
|
234
|
+
/* 主题按钮:太阳 ↔ 月亮 原位交叉淡出 + 旋转(icon-swap,250ms 对称) */
|
|
235
|
+
#theme-toggle { position: relative; }
|
|
236
|
+
#theme-toggle > svg {
|
|
237
|
+
position: absolute; inset: 0; margin: auto;
|
|
238
|
+
transition:
|
|
239
|
+
opacity var(--duration-fast) var(--ease-in-out),
|
|
240
|
+
rotate var(--duration-fast) var(--ease-in-out),
|
|
241
|
+
filter var(--duration-fast) var(--ease-in-out);
|
|
242
|
+
}
|
|
243
|
+
:root[data-theme="light"] #theme-icon-moon,
|
|
244
|
+
:root[data-theme="dark"] #theme-icon-sun { opacity: 0; rotate: -90deg; filter: blur(var(--blur-small)); }
|
|
245
|
+
:root[data-theme="light"] #theme-icon-sun,
|
|
246
|
+
:root[data-theme="dark"] #theme-icon-moon { opacity: 1; rotate: 0deg; filter: blur(0); }
|
|
518
247
|
|
|
519
|
-
/*
|
|
520
|
-
|
|
521
|
-
|
|
522
|
-
|
|
523
|
-
|
|
524
|
-
|
|
525
|
-
|
|
526
|
-
|
|
527
|
-
|
|
528
|
-
|
|
529
|
-
|
|
530
|
-
|
|
531
|
-
|
|
532
|
-
|
|
533
|
-
|
|
534
|
-
|
|
535
|
-
|
|
536
|
-
.comm-cell{border-right:0;border-bottom:1px solid var(--line)}
|
|
537
|
-
.comm-cell:last-child{border-bottom:0}
|
|
538
|
-
.mem-row{grid-template-columns:1fr 1.3fr}
|
|
539
|
-
.mem-row > div:nth-child(3){grid-column:1 / -1;border-top:1px dashed var(--line-soft);color:var(--ink-3);font-size:12px}
|
|
540
|
-
}
|
|
541
|
-
@media (max-width: 640px){
|
|
542
|
-
.topnav a:not(.keep){display:none}
|
|
543
|
-
.brand-tag{display:none}
|
|
544
|
-
.hero{padding:44px 0 0}
|
|
545
|
-
h1{font-size:clamp(38px,11vw,52px)}
|
|
546
|
-
section.block{padding:44px 0}
|
|
547
|
-
.sec-head{grid-template-columns:1fr;gap:10px;margin-bottom:28px}
|
|
548
|
-
.g-card{grid-column:span 12}
|
|
549
|
-
.mini-stats{grid-template-columns:1fr}
|
|
550
|
-
.mini-stats .ms{border-right:0;border-bottom:1px solid var(--line)}
|
|
551
|
-
.mini-stats .ms:last-child{border-bottom:0}
|
|
552
|
-
.mem-row{grid-template-columns:1fr}
|
|
553
|
-
.mem-row > div{border-right:0;border-top:1px dashed var(--line-soft)}
|
|
554
|
-
.mem-row > div:first-child{border-top:0}
|
|
555
|
-
.ctas{flex-direction:column;width:100%}
|
|
556
|
-
.btn{border-right:0;border-bottom:1px solid var(--line)}
|
|
557
|
-
.btn:last-child{border-bottom:0}
|
|
558
|
-
.ft-row{flex-direction:column;align-items:flex-start;gap:12px}
|
|
559
|
-
.meta-line span{padding:6px 10px 6px 0;margin-right:10px}
|
|
560
|
-
}
|
|
561
|
-
@media (prefers-reduced-motion: reduce){
|
|
562
|
-
.js-reveal{opacity:1;transform:none;transition:none}
|
|
563
|
-
.lane .bar,.store .cell.hit::after,.sch-head .live::before{animation:none}
|
|
564
|
-
.lane .bar{width:100%;opacity:.35}
|
|
565
|
-
html{scroll-behavior:auto}
|
|
566
|
-
}
|
|
248
|
+
/* FAQ:原生 details 的高度动画(无 JS,保留无脚本回退与页内查找)
|
|
249
|
+
—— 不支持的浏览器维持原来的瞬时展开,无回退风险 */
|
|
250
|
+
:root { interpolate-size: allow-keywords; }
|
|
251
|
+
details::details-content {
|
|
252
|
+
block-size: 0;
|
|
253
|
+
overflow: hidden;
|
|
254
|
+
content-visibility: hidden;
|
|
255
|
+
transition:
|
|
256
|
+
block-size var(--duration-fast) var(--ease-smooth-out),
|
|
257
|
+
content-visibility var(--duration-fast) allow-discrete;
|
|
258
|
+
}
|
|
259
|
+
details[open]::details-content { block-size: auto; content-visibility: visible; }
|
|
260
|
+
details p {
|
|
261
|
+
opacity: 0; filter: blur(var(--blur-small));
|
|
262
|
+
transition: opacity var(--duration-fast) var(--ease-smooth-out), filter var(--duration-fast) var(--ease-smooth-out);
|
|
263
|
+
}
|
|
264
|
+
details[open] p { opacity: 1; filter: blur(0); }
|
|
567
265
|
</style>
|
|
568
266
|
</head>
|
|
569
267
|
<body>
|
|
570
268
|
|
|
571
|
-
<!--
|
|
572
|
-
<header class="
|
|
573
|
-
<div class="
|
|
574
|
-
<
|
|
575
|
-
<
|
|
576
|
-
|
|
577
|
-
|
|
578
|
-
|
|
579
|
-
|
|
580
|
-
|
|
581
|
-
|
|
582
|
-
|
|
583
|
-
|
|
584
|
-
|
|
585
|
-
|
|
586
|
-
|
|
587
|
-
</
|
|
269
|
+
<!-- ══ 顶栏 ══ -->
|
|
270
|
+
<header class="nav-blur fixed top-0 left-0 right-0 z-50">
|
|
271
|
+
<div class="max-w-7xl mx-auto px-6 h-16 flex items-center justify-between">
|
|
272
|
+
<div class="flex items-center gap-3">
|
|
273
|
+
<a href="#top" class="brand-logo w-8 h-8" style="color:var(--fg)" aria-label="dsh-auto-memory">
|
|
274
|
+
<svg viewBox="0 0 40 40" fill="none">
|
|
275
|
+
<g class="brain-path">
|
|
276
|
+
<path d="M20 6c-4 0-7 2.5-7 6 0 1 .2 2 .6 2.8C11 15.6 9.5 17.4 9.5 19.6c0 1.6.9 3 2.3 3.8-.2.6-.3 1.2-.3 1.9 0 3.2 2.6 5.7 6 5.7 1 0 1.9-.2 2.5-.7"/>
|
|
277
|
+
<path d="M20 6c4 0 7 2.5 7 6 0 1-.2 2-.6 2.8 2.6.8 4.1 2.6 4.1 4.8 0 1.6-.9 3-2.3 3.8.2.6.3 1.2.3 1.9 0 3.2-2.6 5.7-6 5.7-1 0-1.9-.2-2.5-.7"/>
|
|
278
|
+
<path d="M20 6v25"/>
|
|
279
|
+
</g>
|
|
280
|
+
<g class="pulse" style="stroke:var(--accent);stroke-width:1.4;fill:none">
|
|
281
|
+
<circle cx="20" cy="20" r="14" opacity=".5"/>
|
|
282
|
+
</g>
|
|
283
|
+
</svg>
|
|
284
|
+
</a>
|
|
285
|
+
<div class="font-display font-bold text-[15px]" style="color:var(--fg)">dsh-auto-memory</div>
|
|
286
|
+
<span class="font-mono text-[10px] px-2 py-0.5 rounded" style="color:var(--accent);border:1px solid var(--accent)" id="top-ver">v3.1.4</span>
|
|
287
|
+
</div>
|
|
288
|
+
<nav class="hidden lg:flex items-center gap-7">
|
|
289
|
+
<a href="#about" class="nav-link" data-i18n="nav.about">是什么</a>
|
|
290
|
+
<a href="#features" class="nav-link" data-i18n="nav.features">能力</a>
|
|
291
|
+
<a href="#demo" class="nav-link" data-i18n="nav.demo">实机演示</a>
|
|
292
|
+
<a href="#architecture" class="nav-link" data-i18n="nav.architecture">分层</a>
|
|
293
|
+
<a href="#install" class="nav-link" data-i18n="nav.install">安装</a>
|
|
294
|
+
<a href="#roadmap" class="nav-link" data-i18n="nav.roadmap">历程</a>
|
|
295
|
+
<a href="#faq" class="nav-link" data-i18n="nav.faq">问答</a>
|
|
588
296
|
</nav>
|
|
297
|
+
<div class="flex items-center gap-3">
|
|
298
|
+
<span class="lang-switch">
|
|
299
|
+
<button id="lang-zh" data-lang-btn="zh" class="active">中</button>
|
|
300
|
+
<button id="lang-en" data-lang-btn="en">EN</button>
|
|
301
|
+
</span>
|
|
302
|
+
<button id="theme-toggle" class="theme-toggle-btn" aria-label="Toggle theme">
|
|
303
|
+
<svg id="theme-icon-sun" width="16" height="16" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round"><circle cx="12" cy="12" r="4"/><path d="M12 2v2M12 20v2M2 12h2M20 12h2M4.9 4.9l1.4 1.4M17.7 17.7l1.4 1.4M4.9 19.1l1.4-1.4M17.7 6.3l1.4-1.4"/></svg>
|
|
304
|
+
<svg id="theme-icon-moon" width="15" height="15" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round"><path d="M21 12.8A9 9 0 1 1 11.2 3a7 7 0 0 0 9.8 9.8z"/></svg>
|
|
305
|
+
</button>
|
|
306
|
+
<button id="menu-toggle" class="theme-toggle-btn lg:hidden" aria-label="Menu">
|
|
307
|
+
<svg width="16" height="16" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round"><path d="M3 6h18M3 12h18M3 18h18"/></svg>
|
|
308
|
+
</button>
|
|
309
|
+
</div>
|
|
310
|
+
</div>
|
|
311
|
+
<div id="mobile-menu" class="lg:hidden hidden px-6 pb-5 space-y-3" style="border-top:1px solid var(--border)">
|
|
312
|
+
<a href="#about" class="block pt-4 nav-link" data-i18n="nav.about">是什么</a>
|
|
313
|
+
<a href="#features" class="block nav-link" data-i18n="nav.features">能力</a>
|
|
314
|
+
<a href="#demo" class="block nav-link" data-i18n="nav.demo">实机演示</a>
|
|
315
|
+
<a href="#architecture" class="block nav-link" data-i18n="nav.architecture">分层</a>
|
|
316
|
+
<a href="#install" class="block nav-link" data-i18n="nav.install">安装</a>
|
|
317
|
+
<a href="#roadmap" class="block nav-link" data-i18n="nav.roadmap">历程</a>
|
|
318
|
+
<a href="#faq" class="block nav-link" data-i18n="nav.faq">问答</a>
|
|
589
319
|
</div>
|
|
590
320
|
</header>
|
|
591
321
|
|
|
592
|
-
<!--
|
|
322
|
+
<!-- ══ MAIN VIEW ══ -->
|
|
323
|
+
<div id="view-main" class="view active">
|
|
593
324
|
<a id="top"></a>
|
|
594
|
-
|
|
595
|
-
|
|
596
|
-
|
|
597
|
-
|
|
598
|
-
|
|
599
|
-
|
|
600
|
-
|
|
601
|
-
|
|
602
|
-
|
|
603
|
-
|
|
604
|
-
|
|
605
|
-
|
|
325
|
+
|
|
326
|
+
<!-- ── 01 HERO ── -->
|
|
327
|
+
<section class="relative min-h-screen flex items-center pt-24 pb-20 overflow-hidden">
|
|
328
|
+
<div class="absolute inset-0 grid-bg" style="opacity:0.7"></div>
|
|
329
|
+
<div class="blob" style="width:520px;height:520px;background:var(--accent);top:-10%;right:-8%"></div>
|
|
330
|
+
<div class="blob" style="width:420px;height:420px;background:var(--accent-3);bottom:-12%;left:-6%"></div>
|
|
331
|
+
<canvas id="hero-canvas" class="absolute inset-0 w-full h-full" style="opacity:0.5"></canvas>
|
|
332
|
+
<div class="relative max-w-7xl mx-auto px-6 w-full">
|
|
333
|
+
<div class="max-w-3xl">
|
|
334
|
+
<div class="badge-pill mb-8 reveal reveal-lead"><span class="dot"></span><span data-i18n="hero.badge">v3.1.4 · 无问自忆 · 2026-09-22</span></div>
|
|
335
|
+
<h1 class="font-display font-bold leading-[1.02] tracking-tight mb-6 reveal reveal-delay-1 reveal-lead" style="font-size:clamp(2.6rem,7vw,5.6rem)"><span data-i18n="hero.title1" style="color:var(--fg)">无问自忆</span><br><span class="gradient-text" data-i18n="hero.title2">记忆不断线</span></h1>
|
|
336
|
+
<p class="text-lg md:text-xl max-w-2xl mb-4 reveal reveal-delay-2 reveal-lead leading-relaxed" style="color:var(--fg-dim)" data-i18n="hero.subtitle">她不是数据库,是一个会主动想起你的同事。跨窗口、跨会话、跨工具 —— 记忆长在你自己的机器上。</p>
|
|
337
|
+
<p class="text-base max-w-2xl mb-10 reveal reveal-delay-2 reveal-lead" style="color:var(--muted)"><span data-i18n="hero.subtitle2">宿主侧主动联想中间件:持续观察对话情境,双轨检索,在你开口之前把该想起的送进下一拍。零运行时依赖,BSD-3-Clause。</span></p>
|
|
338
|
+
<div class="flex flex-wrap gap-3 mb-12 reveal reveal-delay-3">
|
|
339
|
+
<button class="btn-primary px-7 py-3.5 rounded-lg font-medium flex items-center gap-2 magnetic copy-cmd" data-copy="pnpm add @a9i5k4/dsh-auto-memory">
|
|
340
|
+
<svg width="16" height="16" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2.5" stroke-linecap="round"><path d="M5 12h14M13 5l7 7-7 7"/></svg>
|
|
341
|
+
<span data-i18n="hero.cta1">安装</span><span class="font-mono text-xs opacity-80">pnpm add dsh-auto-memory</span>
|
|
606
342
|
</button>
|
|
607
|
-
<a
|
|
608
|
-
|
|
609
|
-
</a>
|
|
610
|
-
<a class="btn" href="https://www.npmjs.com/package/@a9i5k4/dsh-auto-memory" target="_blank" rel="noreferrer">
|
|
611
|
-
<span data-i18n="hero.cta3">npm</span>
|
|
612
|
-
</a>
|
|
343
|
+
<a href="https://github.com/Aik358/dsh-auto-memory" target="_blank" rel="noreferrer" class="btn-ghost px-7 py-3.5 rounded-lg font-medium flex items-center gap-2 magnetic"><svg width="16" height="16" viewBox="0 0 24 24" fill="currentColor"><path d="M12 .3a12 12 0 0 0-3.8 23.4c.6.1.8-.3.8-.6v-2.2c-3.3.7-4-1.6-4-1.6-.5-1.4-1.3-1.8-1.3-1.8-1.1-.7.1-.7.1-.7 1.2.1 1.8 1.2 1.8 1.2 1 1.8 2.8 1.3 3.5 1 .1-.8.4-1.3.7-1.6-2.7-.3-5.5-1.3-5.5-6 0-1.3.5-2.4 1.2-3.2-.1-.3-.5-1.5.1-3.2 0 0 1-.3 3.3 1.2a11.5 11.5 0 0 1 6 0c2.3-1.5 3.3-1.2 3.3-1.2.6 1.7.2 2.9.1 3.2.8.8 1.2 1.9 1.2 3.2 0 4.6-2.8 5.7-5.5 6 .4.4.8 1.1.8 2.2v3.3c0 .3.2.7.8.6A12 12 0 0 0 12 .3"/></svg><span data-i18n="hero.cta2">GitHub</span></a>
|
|
344
|
+
<a href="#demo" class="btn-ghost px-7 py-3.5 rounded-lg font-medium magnetic" style="border-color:var(--accent);color:var(--accent)" data-i18n="hero.cta3">看实机演示 →</a>
|
|
613
345
|
</div>
|
|
614
|
-
<div class="
|
|
615
|
-
<
|
|
616
|
-
<
|
|
617
|
-
<span data-i18n="hero.
|
|
618
|
-
<span data-i18n="hero.meta4">记忆在你自己的机器上</span>
|
|
346
|
+
<div class="grid grid-cols-3 gap-6 max-w-lg reveal reveal-delay-4">
|
|
347
|
+
<div><div class="stat-num" id="stat-tools">0</div><div class="text-xs mt-1 font-mono uppercase tracking-wider" style="color:var(--muted)" data-i18n="hero.stat1">模型工具</div></div>
|
|
348
|
+
<div><div class="stat-num">0.925</div><div class="text-xs mt-1 font-mono uppercase tracking-wider" style="color:var(--muted)" data-i18n="hero.stat2">BGE-M3 召回</div></div>
|
|
349
|
+
<div><div class="stat-num">0<span class="text-base">GB</span></div><div class="text-xs mt-1 font-mono uppercase tracking-wider" style="color:var(--muted)" data-i18n="hero.stat3">词法保底</div></div>
|
|
619
350
|
</div>
|
|
620
351
|
</div>
|
|
621
|
-
|
|
622
|
-
|
|
623
|
-
|
|
624
|
-
|
|
625
|
-
<span data-i18n="demo.head">HOST MIDDLEWARE · 主动联想管线</span>
|
|
626
|
-
<span class="live" data-i18n="demo.live">LISTENING</span>
|
|
627
|
-
</div>
|
|
628
|
-
<div class="sch-body">
|
|
629
|
-
<div class="pipe">
|
|
630
|
-
<span class="st"><b>A</b><span data-i18n="demo.st1">观察 OBSERVE</span></span>
|
|
631
|
-
<span class="lane"><span class="ticks"></span><span class="bar b-obs"></span></span>
|
|
632
|
-
</div>
|
|
633
|
-
<div class="pipe">
|
|
634
|
-
<span class="st"><b>B</b><span data-i18n="demo.st2">向量化 EMBED</span></span>
|
|
635
|
-
<span class="lane"><span class="ticks"></span><span class="bar b-vec"></span></span>
|
|
636
|
-
</div>
|
|
637
|
-
<div class="pipe">
|
|
638
|
-
<span class="st"><b>C</b><span data-i18n="demo.st3">检索 RETRIEVE</span></span>
|
|
639
|
-
<span class="lane"><span class="ticks"></span><span class="bar b-ret hot"></span></span>
|
|
640
|
-
</div>
|
|
641
|
-
<div class="pipe">
|
|
642
|
-
<span class="st"><b>D</b><span data-i18n="demo.st4">注入 INJECT</span></span>
|
|
643
|
-
<span class="lane"><span class="ticks"></span><span class="bar b-inj hot"></span></span>
|
|
644
|
-
</div>
|
|
645
|
-
<div>
|
|
646
|
-
<div class="store">
|
|
647
|
-
<span class="cell"></span><span class="cell"></span><span class="cell"></span><span class="cell"></span><span class="cell"></span><span class="cell"></span><span class="cell hit"></span><span class="cell"></span><span class="cell"></span><span class="cell"></span><span class="cell"></span><span class="cell"></span>
|
|
648
|
-
<span class="cell"></span><span class="cell"></span><span class="cell"></span><span class="cell"></span><span class="cell"></span><span class="cell"></span><span class="cell hit"></span><span class="cell"></span><span class="cell"></span><span class="cell"></span><span class="cell"></span><span class="cell"></span>
|
|
649
|
-
<span class="cell"></span><span class="cell"></span><span class="cell"></span><span class="cell hit"></span><span class="cell"></span><span class="cell"></span><span class="cell"></span><span class="cell"></span><span class="cell"></span><span class="cell"></span><span class="cell"></span><span class="cell"></span>
|
|
650
|
-
<span class="cell"></span><span class="cell"></span><span class="cell"></span><span class="cell"></span><span class="cell hit"></span><span class="cell"></span><span class="cell"></span><span class="cell"></span><span class="cell"></span><span class="cell"></span><span class="cell"></span><span class="cell"></span>
|
|
651
|
-
</div>
|
|
652
|
-
<div class="store-cap">
|
|
653
|
-
<span data-i18n="demo.store">MEMORY STORE · 三层语料</span>
|
|
654
|
-
<span><b>4</b> <span data-i18n="demo.hits">条命中</span></span>
|
|
655
|
-
</div>
|
|
656
|
-
</div>
|
|
657
|
-
</div>
|
|
658
|
-
<div class="sch-foot">
|
|
659
|
-
<span class="zero" data-i18n="demo.zero">模型发起记忆调用</span>
|
|
660
|
-
<span data-i18n="demo.next">下一拍开口时,她已经记得</span>
|
|
352
|
+
<!-- 主视觉:banner-v4 -->
|
|
353
|
+
<div class="mt-16 lg:mt-0 lg:absolute lg:right-6 lg:top-1/2 lg:-translate-y-1/2 lg:w-[42%] reveal reveal-delay-3">
|
|
354
|
+
<div class="glass-card rounded-2xl p-2 floating">
|
|
355
|
+
<img src="../screenshots/promo/promo-0-banner-v4.png" alt="dsh-auto-memory 主视觉:会记得你的她" class="w-full rounded-xl block" loading="eager">
|
|
661
356
|
</div>
|
|
357
|
+
<div class="absolute -bottom-6 left-1/2 -translate-x-1/2 font-mono text-[10px] tracking-widest uppercase whitespace-nowrap" style="color:var(--muted)" data-i18n="hero.imgCap">她记得,不必吩咐</div>
|
|
662
358
|
</div>
|
|
663
359
|
</div>
|
|
360
|
+
<div class="scroll-hint" data-i18n="hero.scroll">向下</div>
|
|
664
361
|
</section>
|
|
665
362
|
|
|
666
|
-
<!-- ──
|
|
667
|
-
<
|
|
668
|
-
<div class="
|
|
669
|
-
<div class="
|
|
670
|
-
<div class="
|
|
671
|
-
|
|
672
|
-
|
|
673
|
-
<div class="stat-cell reveal">
|
|
674
|
-
<div class="v">3<span class="u" data-i18n="st.2.u">级</span></div>
|
|
675
|
-
<div class="l" data-i18n="st.2.l">检索算力:词法 / 内置向量 / BGE-M3</div>
|
|
676
|
-
</div>
|
|
677
|
-
<div class="stat-cell reveal">
|
|
678
|
-
<div class="v">R@5 0.925</div>
|
|
679
|
-
<div class="l" data-i18n="st.3.l">BGE-M3 int8 档实测召回(与 fp32 差 0.000)</div>
|
|
680
|
-
</div>
|
|
681
|
-
<div class="stat-cell reveal">
|
|
682
|
-
<div class="v">100<span class="u">%</span></div>
|
|
683
|
-
<div class="l" data-i18n="st.4.l">激活决策带证据链,可逐次复核打分</div>
|
|
684
|
-
</div>
|
|
685
|
-
</div>
|
|
686
|
-
</div>
|
|
687
|
-
|
|
688
|
-
<!-- ── 01 管线 ── -->
|
|
689
|
-
<section class="block" id="pipeline">
|
|
690
|
-
<div class="wrap">
|
|
691
|
-
<div class="sec-head reveal">
|
|
692
|
-
<div class="sec-num"><b>01</b><span data-i18n="flow.kicker">核心管线</span></div>
|
|
693
|
-
<div>
|
|
694
|
-
<h2 data-i18n="flow.title">从对话到记忆注入,四站直达</h2>
|
|
695
|
-
<p class="sec-sub" data-i18n="flow.sub">观察 → 检索决策 → 投递闭环。NLP 关键词与向量化双轨并行,唤起必要性由统一策略管线回答——每一步都有 JS 权威层做最终仲裁,AI 只在边界内干活。</p>
|
|
363
|
+
<!-- ── 02 ABOUT ── -->
|
|
364
|
+
<section id="about" class="py-28 relative">
|
|
365
|
+
<div class="max-w-7xl mx-auto px-6">
|
|
366
|
+
<div class="grid lg:grid-cols-12 gap-12 mb-16">
|
|
367
|
+
<div class="lg:col-span-6 reveal">
|
|
368
|
+
<div class="section-num mb-4">01 / <span data-i18n="about.kicker">是什么</span></div>
|
|
369
|
+
<h2 class="font-display font-bold text-4xl md:text-5xl leading-tight mb-6" style="color:var(--fg)" data-i18n="about.title">市面上的记忆方案,<br><span class="gradient-text">都要求模型「记得去查」。</span></h2>
|
|
696
370
|
</div>
|
|
697
|
-
|
|
698
|
-
|
|
699
|
-
<div class="pipe-flow reveal">
|
|
700
|
-
<div class="pf-cell">
|
|
701
|
-
<span class="pf-tag" data-i18n="flow.a.tag">A · 观察</span>
|
|
702
|
-
<h3 data-i18n="flow.a.t">监听对话与工具事件</h3>
|
|
703
|
-
<p data-i18n="flow.a.p">持续观察每轮对话、工具回包、用户/助手事件,定位有"长期价值"的内容。</p>
|
|
704
|
-
<ul>
|
|
705
|
-
<li data-i18n="flow.a.l1">用户消息 + 工具结果实时锚定</li>
|
|
706
|
-
<li data-i18n="flow.a.l2">子代理静默评估(不打断主流程)</li>
|
|
707
|
-
<li data-i18n="flow.a.l3">闲聊 / 失败进重试队列(5 分钟心跳)</li>
|
|
708
|
-
</ul>
|
|
709
|
-
</div>
|
|
710
|
-
<div class="pf-cell">
|
|
711
|
-
<span class="pf-tag" data-i18n="flow.b.tag">B · 检索与决策</span>
|
|
712
|
-
<h3 data-i18n="flow.b.t">双轨检索 + 两车道决策</h3>
|
|
713
|
-
<p data-i18n="flow.b.p">先按相关性排序(词法 BM25 保底 / 内置向量 / BGE-M3),再按"该不该打断你"两车道分流。</p>
|
|
714
|
-
<ul>
|
|
715
|
-
<li data-i18n="flow.b.l1">词法 0GB 保底 → 内置语义 ~130MB → Python BGE-M3 进阶</li>
|
|
716
|
-
<li data-i18n="flow.b.l2">canary 显式唤起 / shadow 仅记录不注入</li>
|
|
717
|
-
<li data-i18n="flow.b.l3">决策全程可打分复核(A/P/S/H/E)</li>
|
|
718
|
-
</ul>
|
|
719
|
-
</div>
|
|
720
|
-
<div class="pf-cell">
|
|
721
|
-
<span class="pf-tag" data-i18n="flow.c.tag">C · 投递闭环</span>
|
|
722
|
-
<h3 data-i18n="flow.c.t">固定边界注入 + 证据反馈</h3>
|
|
723
|
-
<p data-i18n="flow.c.p">提示词字节级稳定,前缀缓存持续命中;每次投递留下 delivered/seen 证据喂回决策。</p>
|
|
724
|
-
<ul>
|
|
725
|
-
<li data-i18n="flow.c.l1">固定边界注入(前缀缓存友好)</li>
|
|
726
|
-
<li data-i18n="flow.c.l2">delivered / seen 证据回流</li>
|
|
727
|
-
<li data-i18n="flow.c.l3">「唤起回顾」页可逐次打分 + 政策提示</li>
|
|
728
|
-
</ul>
|
|
371
|
+
<div class="lg:col-span-6 reveal reveal-delay-1">
|
|
372
|
+
<p class="text-lg leading-relaxed" style="color:var(--fg-dim)" data-i18n="about.lead">忘了调,记忆就等于不存在 —— 这是所有「工具式记忆」的结构性缺陷。dsh-auto-memory 换了一条路:把记忆放在宿主侧,让她持续观察、主动联想、在模型开口之前把该想起的送进下一拍。JS 权威层做最终仲裁,AI 只在边界内干活。</p>
|
|
729
373
|
</div>
|
|
730
374
|
</div>
|
|
731
|
-
|
|
732
|
-
|
|
733
|
-
<
|
|
734
|
-
<
|
|
375
|
+
<div class="grid md:grid-cols-2 gap-6">
|
|
376
|
+
<div class="glass-card rounded-xl p-7 reveal reveal-delay-1"><div class="flex items-start gap-5"><div class="feature-icon"><svg width="22" height="22" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round"><circle cx="12" cy="12" r="9"/><path d="M12 7v5l3 3"/></svg></div><div><h3 class="font-display font-semibold text-xl mb-2" style="color:var(--fg)" data-i18n="about.card1.title">主动,不靠调用</h3><p class="leading-relaxed" style="color:var(--fg-dim)" data-i18n="about.card1.body">语义模型在对话中途判断两件事:此刻该不该想起、该想起哪一条。相关记忆经固定边界注入下一轮 —— 从不依赖模型「记得去查」。</p></div></div></div>
|
|
377
|
+
<div class="glass-card rounded-xl p-7 reveal reveal-delay-2"><div class="flex items-start gap-5"><div class="feature-icon"><svg width="22" height="22" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round"><path d="M12 3l8 4v5c0 5-3.5 8-8 9-4.5-1-8-4-8-9V7z"/><path d="M9 12l2 2 4-4"/></svg></div><div><h3 class="font-display font-semibold text-xl mb-2" style="color:var(--fg)" data-i18n="about.card2.title">记忆是你自己的</h3><p class="leading-relaxed" style="color:var(--fg-dim)" data-i18n="about.card2.body">全部写在本机磁盘,每条都带证据链:哪条消息、哪个工具、哪次深夜反思。可审计、可编辑、可删除 —— 一句话就能让她忘。</p></div></div></div>
|
|
378
|
+
<div class="glass-card rounded-xl p-7 reveal reveal-delay-3"><div class="flex items-start gap-5"><div class="feature-icon"><svg width="22" height="22" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round"><path d="M13 2L3 14h9l-1 8 10-12h-9l1-8z"/></svg></div><div><h3 class="font-display font-semibold text-xl mb-2" style="color:var(--fg)" data-i18n="about.card3.title">前缀缓存友好</h3><p class="leading-relaxed" style="color:var(--fg-dim)" data-i18n="about.card3.body">注入点在提示词里的字节位置固定不变,缓存持续命中 —— 你不需要为「记忆」付两次 token 的钱。这是设计约束,不是事后优化。</p></div></div></div>
|
|
379
|
+
<div class="glass-card rounded-xl p-7 reveal reveal-delay-4"><div class="flex items-start gap-5"><div class="feature-icon"><svg width="22" height="22" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round"><rect x="3" y="3" width="18" height="18" rx="2"/><path d="M3 9h18M9 21V9"/></svg></div><div><h3 class="font-display font-semibold text-xl mb-2" style="color:var(--fg)" data-i18n="about.card4.title">两套可互换的语义引擎</h3><p class="leading-relaxed" style="color:var(--fg-dim)" data-i18n="about.card4.body">JS 端内置 e5-small(~130MB,装上就能用)与 Python 端 BGE-M3(563MB,发烧友进阶档)—— 两者相对独立、可互相替换,永远不互相绑架。</p></div></div></div>
|
|
735
380
|
</div>
|
|
736
|
-
|
|
737
|
-
|
|
738
|
-
|
|
739
|
-
|
|
740
|
-
|
|
741
|
-
|
|
742
|
-
|
|
743
|
-
|
|
744
|
-
<
|
|
745
|
-
|
|
746
|
-
|
|
747
|
-
|
|
748
|
-
|
|
749
|
-
|
|
750
|
-
|
|
751
|
-
|
|
752
|
-
|
|
753
|
-
|
|
754
|
-
|
|
755
|
-
|
|
756
|
-
|
|
757
|
-
|
|
758
|
-
|
|
759
|
-
<button class="mnode tested" type="button" data-m="M8"><i></i><b>M8</b><span data-i18n="m.M8">记忆中枢(治理式写回)</span></button>
|
|
760
|
-
<button class="mnode tested" type="button" data-m="M9"><i></i><b>M9</b><span data-i18n="m.M9">技能固化生命周期</span></button>
|
|
761
|
-
<div class="ac-title" style="margin-top:14px" data-i18n="arch.obs">可观测 / 待发布</div>
|
|
762
|
-
<button class="mnode tested" type="button" data-m="G-02"><i></i><b>G-02</b><span data-i18n="m.G2">激活观测台</span></button>
|
|
763
|
-
<button class="mnode queued" type="button" data-m="M10"><i></i><b>M10</b><span data-i18n="m.M10">存储治理</span></button>
|
|
764
|
-
</div>
|
|
765
|
-
</div>
|
|
766
|
-
|
|
767
|
-
<div class="m-detail" id="m-detail" hidden>
|
|
768
|
-
<div class="md-head"><b id="md-id"></b><span id="md-title"></span><span class="md-state" id="md-state"></span><button type="button" class="md-close" id="md-close" aria-label="close">×</button></div>
|
|
769
|
-
<div class="md-body" id="md-body"></div>
|
|
770
|
-
</div>
|
|
771
|
-
|
|
772
|
-
<div class="arch-cap">
|
|
773
|
-
<span class="lg"><i class="dot live"></i><span data-i18n="arch.lg.live">live verified 已实现并实机验证</span></span>
|
|
774
|
-
<span class="lg"><i class="dot tested"></i><span data-i18n="arch.lg.tested">tested 已测试</span></span>
|
|
775
|
-
<span class="lg"><i class="dot queued"></i><span data-i18n="arch.lg.queued">queued 排队</span></span>
|
|
776
|
-
<span class="arch-cap-sep">·</span>
|
|
777
|
-
<span data-i18n="arch.cap">语义层决定"想起什么",权威层决定"是否/何时/如何注入"——Python 不创建证据,也不直接注入。点击模块查看实现摘要。</span>
|
|
778
|
-
</div>
|
|
779
|
-
|
|
780
|
-
<!-- 宣传图轮播:6 帧滚动吸附 -->
|
|
781
|
-
<div class="promo reveal">
|
|
782
|
-
<div class="promo-track" id="promo-track">
|
|
783
|
-
<img id="promo-1" src="../screenshots/promo/promo-0-banner-v2.png" alt="dsh-auto-memory 主视觉:不用吩咐,她自己记得" />
|
|
784
|
-
<img id="promo-2" src="../screenshots/promo/promo-2-tour.png" alt="欢迎向导:每个功能、当场看懂、当场开关" />
|
|
785
|
-
<img id="promo-3" src="../screenshots/promo/promo-3-recall.png" alt="唤起与固化:对话凝成技能,每一步有迹可循" />
|
|
786
|
-
<img id="promo-4" src="../screenshots/promo/promo-4-unattended.png" alt="无人值守模式:整夜安静跑,零寒暄,零打扰" />
|
|
787
|
-
<img id="promo-5" src="../screenshots/promo/promo-5-external.png" alt="外部记忆继承:你的其他 AI,也在喂她记忆" />
|
|
788
|
-
<img id="promo-6" src="../screenshots/promo/promo-6-greeting.png" alt="定时暖心问候:让每一天都被记得" />
|
|
789
|
-
</div>
|
|
790
|
-
<div class="promo-nav">
|
|
791
|
-
<span class="promo-cap" data-i18n="promo.cap">GALLERY · 六幕</span>
|
|
792
|
-
<span class="promo-dots">
|
|
793
|
-
<a href="#promo-1" aria-label="1"></a><a href="#promo-2" aria-label="2"></a><a href="#promo-3" aria-label="3"></a><a href="#promo-4" aria-label="4"></a><a href="#promo-5" aria-label="5"></a><a href="#promo-6" aria-label="6"></a>
|
|
794
|
-
</span>
|
|
795
|
-
<span style="display:flex;gap:6px">
|
|
796
|
-
<button type="button" class="promo-btn" id="promo-prev" aria-label="prev">←</button>
|
|
797
|
-
<button type="button" class="promo-btn" id="promo-next" aria-label="next">→</button>
|
|
798
|
-
</span>
|
|
799
|
-
</div>
|
|
800
|
-
</div>
|
|
801
|
-
|
|
802
|
-
<!-- 设计文献:论文与决策文档 -->
|
|
803
|
-
<div class="papers">
|
|
804
|
-
<div class="papers-head" data-i18n="pp.title">DESIGN PAPERS · 设计文献(全部结论冻结为工程决策)</div>
|
|
805
|
-
<a class="paper-row" href="https://github.com/Aik358/dsh-auto-memory/blob/preview/docs/M7-RESEARCH-PAPER.md" target="_blank" rel="noreferrer">
|
|
806
|
-
<span class="pr-no">01</span>
|
|
807
|
-
<span class="pr-body"><b data-i18n="pp.1.t">多语言嵌入式检索选型研究</b><small data-i18n="pp.1.s">3 模型 × 5 分块 × 6 通道 ≈ 90 评测单元,BGE-M3 全面领先;冻结为 D1–D11 工程决策</small></span>
|
|
808
|
-
<span class="pr-arrow">→</span>
|
|
809
|
-
</a>
|
|
810
|
-
<a class="paper-row" href="https://github.com/Aik358/dsh-auto-memory/blob/preview/docs/M7-ACTIVATION-V2-PAPER.md" target="_blank" rel="noreferrer">
|
|
811
|
-
<span class="pr-no">02</span>
|
|
812
|
-
<span class="pr-body"><b data-i18n="pp.2.t">从语义相关到唤起必要:回声陷阱的发现、度量与修正</b><small data-i18n="pp.2.s">激活策略 v2 技术报告 + 双轨部署架构(§7);67 条人工金标 held-out 验收 actPrecision 0.917</small></span>
|
|
813
|
-
<span class="pr-arrow">→</span>
|
|
814
|
-
</a>
|
|
815
|
-
<a class="paper-row" href="https://github.com/Aik358/dsh-auto-memory/blob/preview/docs/M7-EMBEDDING-BENCHMARK.md" target="_blank" rel="noreferrer">
|
|
816
|
-
<span class="pr-no">03</span>
|
|
817
|
-
<span class="pr-body"><b data-i18n="pp.3.t">嵌入基准报告</b><small data-i18n="pp.3.s">模型/分块/融合冻结依据:bge-m3 + para-512-noov + 加权融合</small></span>
|
|
818
|
-
<span class="pr-arrow">→</span>
|
|
819
|
-
</a>
|
|
820
|
-
<a class="paper-row" href="https://github.com/Aik358/dsh-auto-memory/blob/preview/docs/M7-ALGORITHM-DECISION.md" target="_blank" rel="noreferrer">
|
|
821
|
-
<span class="pr-no">04</span>
|
|
822
|
-
<span class="pr-body"><b data-i18n="pp.4.t">算法冻结决策 D1–D11</b><small data-i18n="pp.4.s">全部研究结论到生产实现的决策台账</small></span>
|
|
823
|
-
<span class="pr-arrow">→</span>
|
|
824
|
-
</a>
|
|
825
|
-
<a class="paper-row" href="https://github.com/Aik358/dsh-auto-memory/blob/preview/docs/M7-ACTIVATION-V2-HOLDEDOUT-EVAL.md" target="_blank" rel="noreferrer">
|
|
826
|
-
<span class="pr-no">05</span>
|
|
827
|
-
<span class="pr-body"><b data-i18n="pp.5.t">Held-out 人工金标验收</b><small data-i18n="pp.5.s">67 条标注打分:actPrecision 0.917 / harmfulEmit 0 / echo 层 7/7</small></span>
|
|
828
|
-
<span class="pr-arrow">→</span>
|
|
829
|
-
</a>
|
|
830
|
-
<a class="paper-row" href="https://github.com/Aik358/dsh-auto-memory/blob/preview/docs/PYTHON-SIDECAR-CONTRACT.md" target="_blank" rel="noreferrer">
|
|
831
|
-
<span class="pr-no">06</span>
|
|
832
|
-
<span class="pr-body"><b data-i18n="pp.6.t">Python Sidecar 完整契约</b><small data-i18n="pp.6.s">协议/生命周期/权威边界/各里程碑回归证据(§19.x)</small></span>
|
|
833
|
-
<span class="pr-arrow">→</span>
|
|
834
|
-
</a>
|
|
835
|
-
</div>
|
|
381
|
+
</div>
|
|
382
|
+
</section>
|
|
383
|
+
<!-- ── 03 FEATURES ── -->
|
|
384
|
+
<section id="features" class="py-28 relative" style="background:var(--bg-elev)">
|
|
385
|
+
<div class="max-w-7xl mx-auto px-6">
|
|
386
|
+
<div class="text-center mb-20 reveal">
|
|
387
|
+
<div class="section-num mb-4">02 / <span data-i18n="features.kicker">十二个能力</span></div>
|
|
388
|
+
<h2 class="font-display font-bold text-4xl md:text-6xl leading-tight mb-6" style="color:var(--fg)" data-i18n="features.title">四件心血撑起脊柱,<br><span class="gradient-text">其余八件围着长。</span></h2>
|
|
389
|
+
<p class="text-lg max-w-2xl mx-auto" style="color:var(--fg-dim)" data-i18n="features.subtitle">会记事会问候 / 涌现式主动联想 / 技能固化 / 上下文交接 —— 每一件都可独立开关,每一次想起都交得出证据。</p>
|
|
390
|
+
</div>
|
|
391
|
+
<div class="grid md:grid-cols-2 lg:grid-cols-3 gap-6">
|
|
392
|
+
<div class="glass-card rounded-xl p-6 reveal"><div class="feature-icon mb-5"><svg width="22" height="22" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round"><circle cx="12" cy="12" r="9"/><path d="M12 7v5l3 3"/></svg></div><h3 class="font-display font-semibold text-lg mb-2" style="color:var(--fg)" data-i18n="features.f1.title">主动联想</h3><p class="text-sm leading-relaxed" style="color:var(--fg-dim)" data-i18n="features.f1.body">不是「记得去查」,是边做边想起。宿主持续观察,语义模型实时判定,记忆经固定边界走进下一拍。</p></div>
|
|
393
|
+
<div class="glass-card rounded-xl p-6 reveal reveal-delay-1"><div class="feature-icon mb-5"><svg width="22" height="22" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round"><path d="M3 12h4l3-9 4 18 3-9h4"/></svg></div><h3 class="font-display font-semibold text-lg mb-2" style="color:var(--fg)" data-i18n="features.f2.title">三级检索算力</h3><p class="text-sm leading-relaxed" style="color:var(--fg-dim)" data-i18n="features.f2.body">词法 0GB 保底(永远可用)→ 内置 e5-small ~130MB → Python BGE-M3 int8 进阶。失败自动逐级回退。</p></div>
|
|
394
|
+
<div class="glass-card rounded-xl p-6 reveal reveal-delay-2"><div class="feature-icon mb-5"><svg width="22" height="22" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round"><path d="M4 19V5a2 2 0 0 1 2-2h13v16H6a2 2 0 0 0-2 2z"/><path d="M4 19a2 2 0 0 0 2 2h13"/></svg></div><h3 class="font-display font-semibold text-lg mb-2" style="color:var(--fg)" data-i18n="features.f3.title">技能固化</h3><p class="text-sm leading-relaxed" style="color:var(--fg-dim)" data-i18n="features.f3.body">像骑自行车 —— 不用再想怎么骑。工作流凝成技能,下次相似场景清单自己挂上来,无人提醒。</p></div>
|
|
395
|
+
<div class="glass-card rounded-xl p-6 reveal"><div class="feature-icon mb-5"><svg width="22" height="22" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round"><path d="M14 2H6a2 2 0 0 0-2 2v16a2 2 0 0 0 2 2h12a2 2 0 0 0 2-2V8z"/><polyline points="14 2 14 8 20 8"/></svg></div><h3 class="font-display font-semibold text-lg mb-2" style="color:var(--fg)" data-i18n="features.f4.title">交接而非压缩</h3><p class="text-sm leading-relaxed" style="color:var(--fg-dim)" data-i18n="features.f4.body">上下文满了不烧整本书换一句话,而是写四段式交接账本:状态、目标、死路与原因、进度与下一步。</p></div>
|
|
396
|
+
<div class="glass-card rounded-xl p-6 reveal reveal-delay-1"><div class="feature-icon mb-5"><svg width="22" height="22" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round"><circle cx="12" cy="12" r="3"/><path d="M12 2v3M12 19v3M2 12h3M19 12h3M4.9 4.9l2.1 2.1M17 17l2.1 2.1M4.9 19.1L7 17M17 7l2.1-2.1"/></svg></div><h3 class="font-display font-semibold text-lg mb-2" style="color:var(--fg)" data-i18n="features.f5.title">外部记忆继承</h3><p class="text-sm leading-relaxed" style="color:var(--fg-dim)" data-i18n="features.f5.body">WorkBuddy / CodeBuddy / Claude Code / Codex 的记忆会被扫描进来 —— 换工具不用换记忆。纯链接模式,不抄内容。</p></div>
|
|
397
|
+
<div class="glass-card rounded-xl p-6 reveal reveal-delay-2"><div class="feature-icon mb-5"><svg width="22" height="22" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round"><path d="M12 2v6M12 16v6M2 12h6M16 12h6"/><circle cx="12" cy="12" r="3"/></svg></div><h3 class="font-display font-semibold text-lg mb-2" style="color:var(--fg)" data-i18n="features.f6.title">定时问候</h3><p class="text-sm leading-relaxed" style="color:var(--fg-dim)" data-i18n="features.f6.body">早上、下午、深夜 —— 你回来时她用合适的语气打招呼。不是通知铃,是记得你的人说的话。</p></div>
|
|
398
|
+
<div class="glass-card rounded-xl p-6 reveal"><div class="feature-icon mb-5"><svg width="22" height="22" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round"><path d="M21 16V8a2 2 0 0 0-1-1.73l-7-4a2 2 0 0 0-2 0l-7 4A2 2 0 0 0 3 8v8a2 2 0 0 0 1 1.73l7 4a2 2 0 0 0 2 0l7-4A2 2 0 0 0 21 16z"/></svg></div><h3 class="font-display font-semibold text-lg mb-2" style="color:var(--fg)" data-i18n="features.f7.title">无人值守</h3><p class="text-sm leading-relaxed" style="color:var(--fg-dim)" data-i18n="features.f7.body">整夜安静跑:零寒暄、零打扰、零汇报。只在该想起时想起,该交接时交接。早上回来,工作已经往前走了。</p></div>
|
|
399
|
+
<div class="glass-card rounded-xl p-6 reveal reveal-delay-1"><div class="feature-icon mb-5"><svg width="22" height="22" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round"><circle cx="12" cy="12" r="9"/><path d="M3 12h18M12 3a14 14 0 0 1 0 18M12 3a14 14 0 0 0 0 18"/></svg></div><h3 class="font-display font-semibold text-lg mb-2" style="color:var(--fg)" data-i18n="features.f8.title">会话隔离</h3><p class="text-sm leading-relaxed" style="color:var(--fg-dim)" data-i18n="features.f8.body">同时开几个工作区,各记各的、各想各的。点进一个绝不打扰正在跑的那个 —— 并发 A/B 的 cwd、游标、待办零串线。</p></div>
|
|
400
|
+
<div class="glass-card rounded-xl p-6 reveal reveal-delay-2"><div class="feature-icon mb-5"><svg width="22" height="22" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round"><path d="M9 12l2 2 4-4M12 2a10 10 0 1 0 10 10A10 10 0 0 0 12 2z"/></svg></div><h3 class="font-display font-semibold text-lg mb-2" style="color:var(--fg)" data-i18n="features.f9.title">激活观测台</h3><p class="text-sm leading-relaxed" style="color:var(--fg-dim)" data-i18n="features.f9.body">每一次 suppress / prefetch / activate / drop / delivery 都可查:触发上下文、车道、分数、候选 id、尾注摘要。决策可打分复核。</p></div>
|
|
401
|
+
<div class="glass-card rounded-xl p-6 reveal"><div class="feature-icon mb-5"><svg width="22" height="22" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round"><path d="M12 2L2 7l10 5 10-5-10-5z"/><path d="M2 17l10 5 10-5M2 12l10 5 10-5"/></svg></div><h3 class="font-display font-semibold text-lg mb-2" style="color:var(--fg)" data-i18n="features.f10.title">记忆中枢</h3><p class="text-sm leading-relaxed" style="color:var(--fg-dim)" data-i18n="features.f10.body">三店持久化 + 治理式写回:事实层、程序层、日志层分开管,每条都能追溯来源、置顶保活、按需遗忘。</p></div>
|
|
402
|
+
<div class="glass-card rounded-xl p-6 reveal reveal-delay-1"><div class="feature-icon mb-5"><svg width="22" height="22" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round"><path d="M14 2H6a2 2 0 0 0-2 2v16a2 2 0 0 0 2 2h12a2 2 0 0 0 2-2V8z"/><path d="M9 15h6M9 11h6"/></svg></div><h3 class="font-display font-semibold text-lg mb-2" style="color:var(--fg)" data-i18n="features.f11.title">欢迎向导</h3><p class="text-sm leading-relaxed" style="color:var(--fg-dim)" data-i18n="features.f11.body">每个功能、当场看懂、当场开关。十二个能力逐个演示,升级后自动播放一次 —— 不是弹窗广告,是开关的家。</p></div>
|
|
403
|
+
<div class="glass-card rounded-xl p-6 reveal reveal-delay-2"><div class="feature-icon mb-5"><svg width="22" height="22" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round"><path d="M12 3l8 4v5c0 5-3.5 8-8 9-4.5-1-8-4-8-9V7z"/></svg></div><h3 class="font-display font-semibold text-lg mb-2" style="color:var(--fg)" data-i18n="features.f12.title">零运行时依赖</h3><p class="text-sm leading-relaxed" style="color:var(--fg-dim)" data-i18n="features.f12.body">JS 记忆核心只用 Node 内置模块。装完即用,不拖一个第三方包进你的进程 —— BSD-3-Clause,代码全在你自己机器上。</p></div>
|
|
836
404
|
</div>
|
|
837
405
|
</div>
|
|
838
406
|
</section>
|
|
839
407
|
|
|
840
|
-
<!-- ──
|
|
841
|
-
<section
|
|
842
|
-
<div class="
|
|
843
|
-
<div class="
|
|
844
|
-
<div class="
|
|
845
|
-
<
|
|
846
|
-
|
|
847
|
-
|
|
848
|
-
|
|
408
|
+
<!-- ── 04 DEMO ── -->
|
|
409
|
+
<section id="demo" class="py-28 relative">
|
|
410
|
+
<div class="max-w-7xl mx-auto px-6">
|
|
411
|
+
<div class="text-center mb-12 reveal">
|
|
412
|
+
<div class="section-num mb-4">03 / <span data-i18n="demo.kicker">实机演示</span></div>
|
|
413
|
+
<h2 class="font-display font-bold text-4xl md:text-6xl leading-tight mb-6" style="color:var(--fg)" data-i18n="demo.title">三件事,<br><span class="gradient-text">现在就能试。</span></h2>
|
|
414
|
+
<p class="text-lg max-w-2xl mx-auto" style="color:var(--fg-dim)" data-i18n="demo.subtitle">召回、决策、固化 —— 这是她每轮对话都在做的三件事。参数与数字取自真实实测(BGE-M3 int8 · R@5 0.925 · canary delivered=3/seen=24)。</p>
|
|
415
|
+
</div>
|
|
416
|
+
<div class="flex flex-wrap gap-3 justify-center mb-10 reveal">
|
|
417
|
+
<button class="demo-tab active" data-demo="recall"><span>◈</span><span data-i18n="demo.tab1">主动召回</span></button>
|
|
418
|
+
<button class="demo-tab" data-demo="gate"><span>⇄</span><span data-i18n="demo.tab2">两车道决策</span></button>
|
|
419
|
+
<button class="demo-tab" data-demo="skill"><span>▤</span><span data-i18n="demo.tab3">技能固化</span></button>
|
|
849
420
|
</div>
|
|
850
421
|
|
|
851
|
-
<!--
|
|
852
|
-
<div class="
|
|
853
|
-
<div class="
|
|
854
|
-
<div>
|
|
855
|
-
<
|
|
856
|
-
<
|
|
857
|
-
<
|
|
858
|
-
<div class="
|
|
859
|
-
<
|
|
860
|
-
|
|
861
|
-
|
|
862
|
-
|
|
863
|
-
|
|
864
|
-
<
|
|
865
|
-
|
|
866
|
-
|
|
867
|
-
|
|
868
|
-
</div>
|
|
869
|
-
<div class="
|
|
870
|
-
|
|
871
|
-
<div><code>workspaces/{ws}/MEMORY.md</code></div>
|
|
872
|
-
<div data-i18n="f.1.r2.c">项目约定与决策</div>
|
|
873
|
-
</div>
|
|
874
|
-
<div class="mem-row">
|
|
875
|
-
<div data-i18n="f.1.r3.n">每日日志</div>
|
|
876
|
-
<div><code>workspaces/{ws}/YYYY-MM-DD.md</code></div>
|
|
877
|
-
<div data-i18n="f.1.r3.c">追加式工作日志</div>
|
|
878
|
-
</div>
|
|
879
|
-
<div class="mem-row">
|
|
880
|
-
<div data-i18n="f.1.r4.n">每日反思</div>
|
|
881
|
-
<div><code>…/reflections/YYYY-MM-DD.md</code></div>
|
|
882
|
-
<div data-i18n="f.1.r4.c">结构化复盘(成果/教训/下一步)</div>
|
|
883
|
-
</div>
|
|
422
|
+
<!-- 面板 1:主动召回 -->
|
|
423
|
+
<div class="demo-panel active" data-panel="recall">
|
|
424
|
+
<div class="grid lg:grid-cols-12 gap-10">
|
|
425
|
+
<div class="lg:col-span-5 reveal">
|
|
426
|
+
<h3 class="font-display font-semibold text-2xl mb-3" style="color:var(--fg)" data-i18n="demo.recall.title">她说一句话,她开始回想</h3>
|
|
427
|
+
<p class="mb-6 leading-relaxed" style="color:var(--fg-dim)" data-i18n="demo.recall.desc">输入任意一句对话,看她如何从三层语料里捞出候选、打分、挑出唯一该注入的那条。分数是真实的双轨融合结果(词法 0.3 + 向量 0.7)。</p>
|
|
428
|
+
<div class="param-label" style="margin-bottom:8px"><span data-i18n="demo.recall.queryLabel">当前对话</span></div>
|
|
429
|
+
<div class="select-pill mb-5" id="recall-queries">
|
|
430
|
+
<button class="active" data-q="0">部署脚本</button>
|
|
431
|
+
<button data-q="1">上次那个坑</button>
|
|
432
|
+
<button data-q="2">为什么选它</button>
|
|
433
|
+
</div>
|
|
434
|
+
<div class="flex items-center gap-3 mb-6">
|
|
435
|
+
<button id="recall-run" class="play-btn"><svg width="12" height="12" viewBox="0 0 24 24" fill="currentColor"><polygon points="5 3 19 12 5 21 5 3"/></svg> <span data-i18n="demo.recall.run">开始召回</span></button>
|
|
436
|
+
<button id="recall-reset" class="play-btn ghost" data-i18n="demo.clear">清空</button>
|
|
437
|
+
</div>
|
|
438
|
+
<div class="grid grid-cols-3 gap-2">
|
|
439
|
+
<div class="stat-box"><div class="label" data-i18n="demo.recall.cand">候选</div><div class="value" id="recall-cand">0</div></div>
|
|
440
|
+
<div class="stat-box"><div class="label" data-i18n="demo.recall.top">最高分</div><div class="value" id="recall-top">—</div></div>
|
|
441
|
+
<div class="stat-box"><div class="label" data-i18n="demo.recall.time">耗时</div><div class="value" id="recall-ms">—</div></div>
|
|
884
442
|
</div>
|
|
885
443
|
</div>
|
|
886
|
-
<div class="
|
|
887
|
-
<div class="
|
|
888
|
-
|
|
444
|
+
<div class="lg:col-span-7 reveal reveal-delay-1">
|
|
445
|
+
<div class="code-sync" id="recall-log" style="max-height:420px">
|
|
446
|
+
<div class="comment">// 等待输入…</div>
|
|
447
|
+
</div>
|
|
889
448
|
</div>
|
|
890
449
|
</div>
|
|
891
|
-
<ul class="feat-list" style="margin-top:22px">
|
|
892
|
-
<li data-i18n="f.1.b1">静态纪律进 system prompt:字节级稳定 → 前缀缓存持续命中</li>
|
|
893
|
-
<li data-i18n="f.1.b2">动态记忆走运行时快照:只注入最近 1 天日志+反思摘要</li>
|
|
894
|
-
<li><span data-i18n="f.1.b3">凭证/密钥段</span><strong data-i18n="f.1.b3b">永远</strong><span data-i18n="f.1.b3c">被过滤在提示词之外</span></li>
|
|
895
|
-
</ul>
|
|
896
450
|
</div>
|
|
897
451
|
|
|
898
|
-
<!--
|
|
899
|
-
<div class="
|
|
900
|
-
<div class="
|
|
901
|
-
<div>
|
|
902
|
-
<
|
|
903
|
-
<
|
|
904
|
-
<
|
|
905
|
-
|
|
906
|
-
<
|
|
907
|
-
|
|
908
|
-
|
|
909
|
-
<
|
|
910
|
-
|
|
452
|
+
<!-- 面板 2:两车道决策 -->
|
|
453
|
+
<div class="demo-panel" data-panel="gate">
|
|
454
|
+
<div class="grid lg:grid-cols-12 gap-10">
|
|
455
|
+
<div class="lg:col-span-5 reveal">
|
|
456
|
+
<h3 class="font-display font-semibold text-2xl mb-3" style="color:var(--fg)" data-i18n="demo.gate.title">该不该打断你?</h3>
|
|
457
|
+
<p class="mb-6 leading-relaxed" style="color:var(--fg-dim)" data-i18n="demo.gate.desc">召回之后还有一道闸:分数够不够、会不会是回声、要不要打断。调阈值看两车道如何分流 —— canary 显式唤起,shadow 只记录不注入。</p>
|
|
458
|
+
<div class="space-y-4 mb-6">
|
|
459
|
+
<div><div class="param-label"><span data-i18n="demo.gate.thresh">激活阈值</span><span id="gate-val">0.62</span></div><input type="range" id="gate-slider" min="0.30" max="0.95" step="0.01" value="0.62"></div>
|
|
460
|
+
<div><div class="param-label"><span data-i18n="demo.gate.echo">回声否决</span><span id="echo-val">开</span></div><input type="range" id="echo-slider" min="0" max="1" step="1" value="1"></div>
|
|
461
|
+
</div>
|
|
462
|
+
<div class="grid grid-cols-2 gap-2">
|
|
463
|
+
<div class="stat-box"><div class="label">CANARY</div><div class="value" id="gate-canary">0</div></div>
|
|
464
|
+
<div class="stat-box"><div class="label">SHADOW</div><div class="value" id="gate-shadow">0</div></div>
|
|
465
|
+
</div>
|
|
911
466
|
</div>
|
|
912
|
-
<div class="
|
|
913
|
-
<div class="
|
|
914
|
-
|
|
467
|
+
<div class="lg:col-span-7 reveal reveal-delay-1">
|
|
468
|
+
<div class="glass-card rounded-xl p-6">
|
|
469
|
+
<div class="space-y-4" id="gate-rows"></div>
|
|
470
|
+
</div>
|
|
915
471
|
</div>
|
|
916
472
|
</div>
|
|
917
473
|
</div>
|
|
918
474
|
|
|
919
|
-
<!-- 3
|
|
920
|
-
<div class="
|
|
921
|
-
<div class="
|
|
922
|
-
<div>
|
|
923
|
-
<
|
|
924
|
-
<
|
|
925
|
-
<
|
|
926
|
-
<
|
|
927
|
-
<
|
|
928
|
-
<
|
|
929
|
-
|
|
930
|
-
<li data-i18n="f.3.l4">升级用户一次性触达:v0.1.30 起所有用户升级后自动播放一次</li>
|
|
931
|
-
<li><span data-i18n="f.3.l5">设置 → 外观 → 欢迎向导 →</span> <strong data-i18n="f.3.l5b">▶ 重看引导</strong> <span data-i18n="f.3.l5c">随时重新打开</span></li>
|
|
932
|
-
</ul>
|
|
475
|
+
<!-- 面板 3:技能固化 -->
|
|
476
|
+
<div class="demo-panel" data-panel="skill">
|
|
477
|
+
<div class="grid lg:grid-cols-12 gap-10">
|
|
478
|
+
<div class="lg:col-span-5 reveal">
|
|
479
|
+
<h3 class="font-display font-semibold text-2xl mb-3" style="color:var(--fg)" data-i18n="demo.skill.title">从看到到会做</h3>
|
|
480
|
+
<p class="mb-6 leading-relaxed" style="color:var(--fg-dim)" data-i18n="demo.skill.desc">看过你几次纠正、同类事做过几遍,工作流就凝成技能。四级晋升,每一步都有跨会话证据;90 天未用自动归档,可置顶保活。</p>
|
|
481
|
+
<button id="skill-run" class="play-btn mb-6"><svg width="12" height="12" viewBox="0 0 24 24" fill="currentColor"><polygon points="5 3 19 12 5 21 5 3"/></svg> <span data-i18n="demo.skill.run">观察一次</span></button>
|
|
482
|
+
<div class="grid grid-cols-2 gap-2">
|
|
483
|
+
<div class="stat-box"><div class="label" data-i18n="demo.skill.obs">观测次数</div><div class="value" id="skill-obs">0</div></div>
|
|
484
|
+
<div class="stat-box"><div class="label" data-i18n="demo.skill.stage">当前阶段</div><div class="value" id="skill-stage">—</div></div>
|
|
485
|
+
</div>
|
|
933
486
|
</div>
|
|
934
|
-
<div class="
|
|
935
|
-
<div class="
|
|
936
|
-
|
|
487
|
+
<div class="lg:col-span-7 reveal reveal-delay-1">
|
|
488
|
+
<div class="glass-card rounded-xl p-6">
|
|
489
|
+
<div class="space-y-3" id="skill-stages"></div>
|
|
490
|
+
</div>
|
|
937
491
|
</div>
|
|
938
492
|
</div>
|
|
939
493
|
</div>
|
|
940
|
-
|
|
941
|
-
|
|
942
|
-
|
|
943
|
-
|
|
944
|
-
|
|
945
|
-
|
|
946
|
-
|
|
947
|
-
|
|
948
|
-
|
|
949
|
-
<li data-i18n="f.4.l1">决策打分:A 该激活 / P 只预取 / S 应抑制 / H 有害 / E 改目标</li>
|
|
950
|
-
<li data-i18n="f.4.l2">技能晋升四态:observed → candidate → validated → active</li>
|
|
951
|
-
<li data-i18n="f.4.l3">90 天未用自动归档,可手动置顶</li>
|
|
952
|
-
<li data-i18n="f.4.l4">判定队列会汇总成政策提示,反哺自动决策</li>
|
|
953
|
-
</ul>
|
|
954
|
-
</div>
|
|
955
|
-
<div class="f-visual">
|
|
956
|
-
<div class="vbar"><span data-i18n="f.4.art">RECALL REVIEW</span><span class="dots"><i></i><i></i><i></i></span></div>
|
|
957
|
-
<img src="../screenshots/panel-refine.png" alt="refine" />
|
|
958
|
-
</div>
|
|
494
|
+
</div>
|
|
495
|
+
</section>
|
|
496
|
+
<!-- ── 05 ARCHITECTURE ── -->
|
|
497
|
+
<section id="architecture" class="py-28 relative" style="background:var(--bg-elev)">
|
|
498
|
+
<div class="max-w-7xl mx-auto px-6">
|
|
499
|
+
<div class="grid lg:grid-cols-12 gap-12 mb-16">
|
|
500
|
+
<div class="lg:col-span-6 reveal">
|
|
501
|
+
<div class="section-num mb-4">04 / <span data-i18n="arch.kicker">运行时分层</span></div>
|
|
502
|
+
<h2 class="font-display font-bold text-4xl md:text-5xl leading-tight mb-6" style="color:var(--fg)" data-i18n="arch.title">语义层决定想起什么,<br><span class="gradient-text">权威层决定是否注入。</span></h2>
|
|
959
503
|
</div>
|
|
960
|
-
|
|
961
|
-
|
|
962
|
-
<!-- 3.5 无人值守模式 -->
|
|
963
|
-
<div class="feature reveal" id="f-unattended">
|
|
964
|
-
<div class="feature-grid">
|
|
965
|
-
<div>
|
|
966
|
-
<span class="f-meta" data-i18n="f.5.kicker">3.5 · 无人值守模式</span>
|
|
967
|
-
<h3 data-i18n="f.5.t">面向长跑批处理任务</h3>
|
|
968
|
-
<p class="lede2" data-i18n="f.5.p">设置 → 自动化提供<strong>手动开关</strong>与<strong>夜间自动托管</strong>(22:00-08:00 可调);托管期间不注入欢迎语/寒暄/行为指令、日历提醒静默、上下文保持稳定——模型专注干活,token 花在正事上。</p>
|
|
969
|
-
<ul class="feat-list">
|
|
970
|
-
<li data-i18n="f.5.l1">零寒暄 / 零行为指令 / 日历静默 / 上下文冻结</li>
|
|
971
|
-
<li data-i18n="f.5.l2">时间窗可调(默认 22:00-08:00)</li>
|
|
972
|
-
<li data-i18n="f.5.l3">来源:社区 Issue #10 反馈驱动的加固场景</li>
|
|
973
|
-
</ul>
|
|
974
|
-
<div class="mini-stats">
|
|
975
|
-
<div class="ms"><div class="v">0</div><div class="l" data-i18n="f.5.s1.l">托管期间注入的寒暄</div></div>
|
|
976
|
-
<div class="ms"><div class="v">10h</div><div class="l" data-i18n="f.5.s2.l">夜间默认托管窗口</div></div>
|
|
977
|
-
<div class="ms"><div class="v">100%</div><div class="l" data-i18n="f.5.s3.l">上下文稳定(不增删)</div></div>
|
|
978
|
-
</div>
|
|
979
|
-
</div>
|
|
980
|
-
<div class="f-visual">
|
|
981
|
-
<div class="vbar"><span data-i18n="f.5.art">UNATTENDED</span><span class="dots"><i></i><i></i><i></i></span></div>
|
|
982
|
-
<img src="../screenshots/tour-toggles.png" alt="tour toggles" />
|
|
983
|
-
</div>
|
|
504
|
+
<div class="lg:col-span-6 reveal reveal-delay-1">
|
|
505
|
+
<p class="text-lg leading-relaxed" style="color:var(--fg-dim)" data-i18n="arch.lead">JS 记忆核心持有全部权威:身份、范围、版本、TTL、预算、风险。Python 语义侧车只负责「像不像」,它不创建证据,也不直接注入 —— 这是整套架构最硬的一条边界。</p>
|
|
984
506
|
</div>
|
|
985
507
|
</div>
|
|
986
508
|
|
|
987
|
-
|
|
988
|
-
|
|
989
|
-
<div class="
|
|
990
|
-
|
|
991
|
-
|
|
992
|
-
|
|
993
|
-
|
|
994
|
-
|
|
995
|
-
<li data-i18n="f.6.l1">时段问候:晨/午/晚,提及当日工作要点</li>
|
|
996
|
-
<li data-i18n="f.6.l2">暂离 >1h 回归自动开面板 + "欢迎回来"</li>
|
|
997
|
-
<li data-i18n="f.6.l3">每日第一次会话:前一日结构化反思</li>
|
|
998
|
-
</ul>
|
|
999
|
-
</div>
|
|
1000
|
-
<div class="f-visual">
|
|
1001
|
-
<div class="vbar"><span data-i18n="f.6.art">OVERVIEW</span><span class="dots"><i></i><i></i><i></i></span></div>
|
|
1002
|
-
<img src="../screenshots/panel-overview.png" alt="overview" />
|
|
1003
|
-
</div>
|
|
1004
|
-
</div>
|
|
509
|
+
<div class="space-y-4 mb-12">
|
|
510
|
+
<div class="arch-layer rounded-xl p-6 reveal flex items-center gap-6"><div class="arch-num font-display font-bold text-3xl w-16" style="color:var(--muted)">M6</div><div class="flex-1"><div class="flex items-center gap-3 mb-1 flex-wrap"><h3 class="font-display font-semibold text-xl" style="color:var(--fg)" data-i18n="arch.m6.title">激活收件箱 · 投递闭环</h3><span class="font-mono text-[10px] px-2 py-0.5 border rounded" style="color:var(--muted);border-color:var(--border)">activation-inbox-pre.js</span></div><p class="text-sm" style="color:var(--fg-dim)" data-i18n="arch.m6.body">硬校验 → offer → claim → 参考尾注渲染 → delivered/seen 证据落盘。每次投递都留下可回查的痕迹。</p></div><div class="hidden md:block font-mono text-xs text-right" style="color:var(--muted)"><div>LIVE</div><div class="accent">delivered=3</div></div></div>
|
|
511
|
+
<div class="arch-layer rounded-xl p-6 reveal reveal-delay-1 flex items-center gap-6"><div class="arch-num font-display font-bold text-3xl w-16" style="color:var(--muted)">M5</div><div class="flex-1"><div class="flex items-center gap-3 mb-1 flex-wrap"><h3 class="font-display font-semibold text-xl" style="color:var(--fg)" data-i18n="arch.m5.title">授权上下文 + 证据桥</h3><span class="font-mono text-[10px] px-2 py-0.5 border rounded" style="color:var(--muted);border-color:var(--border)">envelope · evidence-store</span></div><p class="text-sm" style="color:var(--fg-dim)" data-i18n="arch.m5.body">信封授权范围校验、coverage 检查、cite/correction 证据、stale 拒绝。只用 Null/Fake sink,从不启动 Python。</p></div><div class="hidden md:block font-mono text-xs text-right" style="color:var(--muted)"><div>LIVE</div><div class="accent">fail-closed</div></div></div>
|
|
512
|
+
<div class="arch-layer rounded-xl p-6 reveal reveal-delay-2 flex items-center gap-6"><div class="arch-num font-display font-bold text-3xl w-16" style="color:var(--muted)">M4</div><div class="flex-1"><div class="flex items-center gap-3 mb-1 flex-wrap"><h3 class="font-display font-semibold text-xl" style="color:var(--fg)" data-i18n="arch.m4.title">语料快照 + 影子检索</h3><span class="font-mono text-[10px] px-2 py-0.5 border rounded" style="color:var(--muted);border-color:var(--border)">lexical_pre_v2 · BM25</span></div><p class="text-sm" style="color:var(--fg-dim)" data-i18n="arch.m4.body">六原因 fail-closed 快照、冻结的策略权重与滞回、CJK 2-gram + 507 停用词的 BM25。候选只审计,绝不注入。</p></div><div class="hidden md:block font-mono text-xs text-right" style="color:var(--muted)"><div>LIVE</div><div class="accent">R@5 .925</div></div></div>
|
|
513
|
+
<div class="arch-layer rounded-xl p-6 reveal reveal-delay-3 flex items-center gap-6"><div class="arch-num font-display font-bold text-3xl w-16" style="color:var(--muted)">M3</div><div class="flex-1"><div class="flex items-center gap-3 mb-1 flex-wrap"><h3 class="font-display font-semibold text-xl" style="color:var(--fg)" data-i18n="arch.m3.title">锚定与迁移</h3><span class="font-mono text-[10px] px-2 py-0.5 border rounded" style="color:var(--muted);border-color:var(--border)">anchors · sidecar · migration</span></div><p class="text-sm" style="color:var(--fg-dim)" data-i18n="arch.m3.body">冲突 fail-closed、确定性迁移计划、原子写。31 个真实文件 / 176 条记录完成迁移,备份可回滚。</p></div><div class="hidden md:block font-mono text-xs text-right" style="color:var(--muted)"><div>LIVE</div><div class="accent">176 records</div></div></div>
|
|
514
|
+
<div class="arch-layer rounded-xl p-6 reveal flex items-center gap-6"><div class="arch-num font-display font-bold text-3xl w-16" style="color:var(--muted)">M2</div><div class="flex-1"><div class="flex items-center gap-3 mb-1 flex-wrap"><h3 class="font-display font-semibold text-xl" style="color:var(--fg)" data-i18n="arch.m2.title">事件账本 + 分型切片</h3><span class="font-mono text-[10px] px-2 py-0.5 border rounded" style="color:var(--muted);border-color:var(--border)">EventEnvelope · Segment</span></div><p class="text-sm" style="color:var(--fg-dim)" data-i18n="arch.m2.body">user / tool_call / tool_result / assistant 分型,稳定原生坐标生成 id 与 digest。关闭态零留存,敏感内容零残留。</p></div><div class="hidden md:block font-mono text-xs text-right" style="color:var(--muted)"><div>LIVE</div><div class="accent">counters-only</div></div></div>
|
|
515
|
+
<div class="arch-layer rounded-xl p-6 reveal reveal-delay-1 flex items-center gap-6"><div class="arch-num font-display font-bold text-3xl w-16" style="color:var(--muted)">M1</div><div class="flex-1"><div class="flex items-center gap-3 mb-1 flex-wrap"><h3 class="font-display font-semibold text-xl" style="color:var(--fg)" data-i18n="arch.m1.title">会话隔离</h3><span class="font-mono text-[10px] px-2 py-0.5 border rounded" style="color:var(--muted);border-color:var(--border)">runtime-store · ALS</span></div><p class="text-sm" style="color:var(--fg-dim)" data-i18n="arch.m1.body">每会话独立的锁、冷却、队列。并发两个工作区的 cwd、segment、游标、待办互不串线。</p></div><div class="hidden md:block font-mono text-xs text-right" style="color:var(--muted)"><div>LIVE</div><div class="accent">zero-crosstalk</div></div></div>
|
|
516
|
+
<div class="arch-layer rounded-xl p-6 reveal reveal-delay-2 flex items-center gap-6"><div class="arch-num font-display font-bold text-3xl w-16" style="color:var(--accent-2)">PY</div><div class="flex-1"><div class="flex items-center gap-3 mb-1 flex-wrap"><h3 class="font-display font-semibold text-xl" style="color:var(--fg)" data-i18n="arch.py.title">Python 语义侧车 · 可选 · 懒启动</h3><span class="font-mono text-[10px] px-2 py-0.5 border rounded" style="color:var(--muted);border-color:var(--border)">BGE-M3 int8 · ONNX</span></div><p class="text-sm" style="color:var(--fg-dim)" data-i18n="arch.py.body">563MB 进阶档,设置页一键安装。R@5 0.925(与 fp32 差 0.000,快 6×)。它与 JS 内置档是两套可互换的引擎 —— 互不联动、互不依赖。</p></div><div class="hidden md:block font-mono text-xs text-right" style="color:var(--muted)"><div>OPTIONAL</div><div class="accent">int8</div></div></div>
|
|
1005
517
|
</div>
|
|
1006
518
|
|
|
1007
|
-
|
|
1008
|
-
|
|
1009
|
-
<div class="
|
|
1010
|
-
|
|
1011
|
-
<span class="f-meta" data-i18n="f.7.kicker">3.7 · 智能检索与工作区全景</span>
|
|
1012
|
-
<h3 data-i18n="f.7.t">自然语言搜,跨工作区可达</h3>
|
|
1013
|
-
<p class="lede2" data-i18n="f.7.p">自然语言提问,AI 自动扩展关键词扫描全部记忆层,会话式回答并标注来源;面板「工作区」页签自动生成工作区关系图——AI 归纳主题与跨区关联,可拖拽/缩放/点卡片看详情。</p>
|
|
1014
|
-
<ul class="feat-list">
|
|
1015
|
-
<li data-i18n="f.7.l1">跨工作区检索天然支持,结果标注来源工作区</li>
|
|
1016
|
-
<li data-i18n="f.7.l2">工作区关系图:主题归纳 + 跨区关联</li>
|
|
1017
|
-
<li data-i18n="f.7.l3">可拖拽 / 缩放 / 点卡详情</li>
|
|
1018
|
-
</ul>
|
|
1019
|
-
</div>
|
|
1020
|
-
<div class="f-visual">
|
|
1021
|
-
<div class="vbar"><span data-i18n="f.7.art">SEARCH</span><span class="dots"><i></i><i></i><i></i></span></div>
|
|
1022
|
-
<img src="../screenshots/panel-hub.png" alt="search" />
|
|
1023
|
-
</div>
|
|
1024
|
-
</div>
|
|
519
|
+
<div class="flex flex-wrap gap-4 text-xs font-mono reveal" style="color:var(--muted)">
|
|
520
|
+
<div class="flex items-center gap-2"><span class="check">●</span> <span data-i18n="arch.legend1">live verified 已实现并实机验证</span></div>
|
|
521
|
+
<div class="flex items-center gap-2"><span style="color:#d97706">●</span> <span data-i18n="arch.legend2">tested 已测试</span></div>
|
|
522
|
+
<div class="flex items-center gap-2"><span class="cross">●</span> <span data-i18n="arch.legend3">queued 排队</span></div>
|
|
1025
523
|
</div>
|
|
524
|
+
</div>
|
|
525
|
+
</section>
|
|
1026
526
|
|
|
1027
|
-
|
|
1028
|
-
|
|
1029
|
-
|
|
1030
|
-
|
|
1031
|
-
|
|
1032
|
-
|
|
1033
|
-
|
|
1034
|
-
<ul class="feat-list">
|
|
1035
|
-
<li data-i18n="f.8.l1">自动从对话识别 deadline / 约定 → 入日历</li>
|
|
1036
|
-
<li data-i18n="f.8.l2">未完成项注入后续会话直到完成</li>
|
|
1037
|
-
<li data-i18n="f.8.l3">07:00-22:00 时间轴 + 地点/提醒字段 + 紧急度语义色</li>
|
|
1038
|
-
</ul>
|
|
1039
|
-
</div>
|
|
1040
|
-
<div class="f-visual">
|
|
1041
|
-
<div class="vbar"><span data-i18n="f.8.art">CALENDAR</span><span class="dots"><i></i><i></i><i></i></span></div>
|
|
1042
|
-
<img src="../screenshots/calendar-zh.png" alt="calendar" />
|
|
1043
|
-
</div>
|
|
1044
|
-
</div>
|
|
527
|
+
<!-- ── 06 INSTALL ── -->
|
|
528
|
+
<section id="install" class="py-28 relative">
|
|
529
|
+
<div class="max-w-7xl mx-auto px-6">
|
|
530
|
+
<div class="text-center mb-16 reveal">
|
|
531
|
+
<div class="section-num mb-4">05 / <span data-i18n="install.kicker">安装</span></div>
|
|
532
|
+
<h2 class="font-display font-bold text-4xl md:text-6xl leading-tight mb-6" style="color:var(--fg)" data-i18n="install.title">两步装好,<br><span class="gradient-text">向导自己走出来。</span></h2>
|
|
533
|
+
<p class="text-lg max-w-2xl mx-auto" style="color:var(--fg-dim)" data-i18n="install.subtitle">Windows / macOS / Linux 全平台。装完重启 DSH,欢迎向导自动播放:十二个能力逐个演示、逐个开关。</p>
|
|
1045
534
|
</div>
|
|
1046
|
-
|
|
1047
|
-
|
|
1048
|
-
|
|
1049
|
-
|
|
1050
|
-
<div>
|
|
1051
|
-
<span class="
|
|
1052
|
-
|
|
1053
|
-
|
|
1054
|
-
<
|
|
1055
|
-
<li data-i18n="f.9.l1">扫描发现:WorkBuddy / CodeBuddy / Claude Code / Codex</li>
|
|
1056
|
-
<li data-i18n="f.9.l2">按源导入:只存路径指针(不复制内容)</li>
|
|
1057
|
-
<li data-i18n="f.9.l3">按源删除 + 双重卫生闸门</li>
|
|
1058
|
-
</ul>
|
|
1059
|
-
</div>
|
|
1060
|
-
<div class="f-visual">
|
|
1061
|
-
<div class="vbar"><span data-i18n="f.9.art">EXTERNAL SCAN</span><span class="dots"><i></i><i></i><i></i></span></div>
|
|
1062
|
-
<img src="../screenshots/tour-external.png" alt="external scan" />
|
|
535
|
+
<div class="grid lg:grid-cols-2 gap-8 mb-10">
|
|
536
|
+
<div class="glass-card rounded-xl p-7 reveal">
|
|
537
|
+
<div class="flex items-center gap-3 mb-5"><div class="feature-icon"><svg width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round"><path d="M12 3v12M7 10l5 5 5-5M5 21h14"/></svg></div><h3 class="font-display font-semibold text-xl" style="color:var(--fg)" data-i18n="install.step1.title">1 · 安装插件</h3></div>
|
|
538
|
+
<p class="text-sm mb-4" style="color:var(--fg-dim)" data-i18n="install.step1.desc">在 DSH profile 目录里装包:</p>
|
|
539
|
+
<div class="relative">
|
|
540
|
+
<pre><span class="tok-com"># 进入 DSH profile 并安装</span>
|
|
541
|
+
<span class="tok-kw">cd</span> ~/.dsh/profiles/web
|
|
542
|
+
<span class="tok-kw">pnpm</span> add @a9i5k4/dsh-auto-memory</pre>
|
|
543
|
+
<button class="play-btn ghost absolute top-3 right-3 copy-cmd" data-copy="cd ~/.dsh/profiles/web && pnpm add @a9i5k4/dsh-auto-memory" data-i18n="install.copy">复制</button>
|
|
1063
544
|
</div>
|
|
1064
545
|
</div>
|
|
1065
|
-
|
|
1066
|
-
|
|
1067
|
-
|
|
1068
|
-
|
|
1069
|
-
|
|
1070
|
-
|
|
1071
|
-
|
|
1072
|
-
<
|
|
1073
|
-
<p class="lede2" data-i18n="f.10.p">三个写入工具全部过 <code>sanitizeForWrite</code>:GBK 乱码(34 特征全表)、复读退化、连续重复行、外部 AI 画像 JSON 特征、base64 残留——全部拒写并给出中文回执。设置 → 调试中心「扫描脏 token」一键按行区间报告问题(只报位置不含正文)。</p>
|
|
1074
|
-
<ul class="feat-list">
|
|
1075
|
-
<li data-i18n="f.10.l1">34 个 GBK 乱码特征全表识别</li>
|
|
1076
|
-
<li data-i18n="f.10.l2">复读退化 / 连续重复行 / 外部画像 JSON / base64 残留</li>
|
|
1077
|
-
<li data-i18n="f.10.l3">追加 8000 字/条;全量改写 20 万字上限</li>
|
|
1078
|
-
<li data-i18n="f.10.l4">追加前与文件尾部近 60 行做去重</li>
|
|
1079
|
-
</ul>
|
|
1080
|
-
</div>
|
|
1081
|
-
<div class="f-visual">
|
|
1082
|
-
<div class="vbar"><span data-i18n="f.10.art">HYGIENE</span><span class="dots"><i></i><i></i><i></i></span></div>
|
|
1083
|
-
<img src="../screenshots/tour-core.png" alt="tour core" />
|
|
546
|
+
<div class="glass-card rounded-xl p-7 reveal reveal-delay-1">
|
|
547
|
+
<div class="flex items-center gap-3 mb-5"><div class="feature-icon"><svg width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round"><path d="M21 12a9 9 0 1 1-3-6.7"/><path d="M21 3v6h-6"/></svg></div><h3 class="font-display font-semibold text-xl" style="color:var(--fg)" data-i18n="install.step2.title">2 · 重启 DSH</h3></div>
|
|
548
|
+
<p class="text-sm mb-4" style="color:var(--fg-dim)" data-i18n="install.step2.desc">重启 dsh web 后欢迎向导自动走出。已有用户升级后自动播放一次:</p>
|
|
549
|
+
<div class="relative">
|
|
550
|
+
<pre><span class="tok-com"># 或直接升级到最新</span>
|
|
551
|
+
<span class="tok-kw">cd</span> ~/.dsh/profiles/web
|
|
552
|
+
<span class="tok-kw">pnpm</span> up @a9i5k4/dsh-auto-memory</pre>
|
|
553
|
+
<button class="play-btn ghost absolute top-3 right-3 copy-cmd" data-copy="cd ~/.dsh/profiles/web && pnpm up @a9i5k4/dsh-auto-memory" data-i18n="install.copy">复制</button>
|
|
1084
554
|
</div>
|
|
1085
555
|
</div>
|
|
1086
556
|
</div>
|
|
1087
|
-
|
|
1088
|
-
|
|
1089
|
-
|
|
1090
|
-
<div class="
|
|
1091
|
-
<div>
|
|
1092
|
-
<span class="f-meta" data-i18n="f.11.kicker">3.11 · 记忆生命周期</span>
|
|
1093
|
-
<h3 data-i18n="f.11.t">30 天蒸馏:把过程流水换成可复用结论</h3>
|
|
1094
|
-
<p class="lede2" data-i18n="f.11.p"><code>memory_maintain_pre</code> 把 30 天前的每日日志交给 AI 蒸馏:只提炼有跨会话长期价值的要点(技术决策/架构约定/偏好/踩坑规则),写入项目笔记;原文保底归档到 <code>archive/</code>(AI 不可用时降级为原样归档,绝不丢信息)。</p>
|
|
1095
|
-
<ul class="feat-list">
|
|
1096
|
-
<li data-i18n="f.11.l1">30 天蒸馏窗口:旧日志 → 长期要点 → 项目笔记</li>
|
|
1097
|
-
<li><span data-i18n="f.11.l2">蒸馏明确边界:</span><strong data-i18n="f.11.l2b">procedure skills(技能固化)</strong><span data-i18n="f.11.l2c">与两级笔记不在蒸馏范围</span></li>
|
|
1098
|
-
<li data-i18n="f.11.l3">归档原文不在常规检索扫描内(检索=项目笔记+活跃日志+反思+用户级)</li>
|
|
1099
|
-
<li data-i18n="f.11.l4">蒸馏要点随笔记常驻注入</li>
|
|
1100
|
-
<li data-i18n="f.11.l5">memory_consolidate:AI 发散固化(阶段性回头升格)</li>
|
|
1101
|
-
</ul>
|
|
1102
|
-
</div>
|
|
1103
|
-
<div class="f-visual">
|
|
1104
|
-
<div class="vbar"><span data-i18n="f.11.art">LIFECYCLE</span><span class="dots"><i></i><i></i><i></i></span></div>
|
|
1105
|
-
<img src="../screenshots/panel-hub.png" alt="hub" />
|
|
1106
|
-
</div>
|
|
1107
|
-
</div>
|
|
557
|
+
<div class="grid md:grid-cols-3 gap-4 mb-8">
|
|
558
|
+
<div class="glass-card rounded-xl p-5 reveal"><div class="font-mono text-xs mb-2" style="color:var(--accent)" data-i18n="install.req.h">环境</div><div class="text-sm" style="color:var(--fg-dim)" data-i18n="install.req1">DSH 0.1.6-alpha 及以上</div></div>
|
|
559
|
+
<div class="glass-card rounded-xl p-5 reveal reveal-delay-1"><div class="font-mono text-xs mb-2" style="color:var(--accent)" data-i18n="install.req.h">语义档(可选)</div><div class="text-sm" style="color:var(--fg-dim)" data-i18n="install.req2">JS 内置 e5-small ~130MB 首启自动下载</div></div>
|
|
560
|
+
<div class="glass-card rounded-xl p-5 reveal reveal-delay-2"><div class="font-mono text-xs mb-2" style="color:var(--accent)" data-i18n="install.req.h">进阶档(可选)</div><div class="text-sm" style="color:var(--fg-dim)" data-i18n="install.req3">Python BGE-M3 563MB · 设置页一键装</div></div>
|
|
1108
561
|
</div>
|
|
1109
|
-
|
|
1110
|
-
|
|
1111
|
-
|
|
1112
|
-
<div class="
|
|
1113
|
-
<
|
|
1114
|
-
|
|
1115
|
-
<h3 data-i18n="f.12.t">保持克制的设计</h3>
|
|
1116
|
-
<p class="lede2" data-i18n="f.12.p">这些不是"特性",是"在你能用它之前先让你放心"的工程承诺——少一点跑得快的东西,多一点能跑得久的东西。</p>
|
|
1117
|
-
<ul class="feat-list">
|
|
1118
|
-
<li data-i18n="f.12.l1">零运行时依赖(仅 Node 内建模块)</li>
|
|
1119
|
-
<li data-i18n="f.12.l2">前缀缓存友好:提示词字节级稳定</li>
|
|
1120
|
-
<li data-i18n="f.12.l3">限额 AI:自动沉淀每日 ≤8 次带冷却</li>
|
|
1121
|
-
<li data-i18n="f.12.l4">集中式存储:~/.dsh/memory/workspaces/</li>
|
|
1122
|
-
<li data-i18n="f.12.l5">可选 Python sidecar(BGE-M3 int8,失败自动回退词法)</li>
|
|
1123
|
-
</ul>
|
|
1124
|
-
</div>
|
|
1125
|
-
<div class="f-visual">
|
|
1126
|
-
<div class="vbar"><span data-i18n="f.12.art">ENGINEERING</span><span class="dots"><i></i><i></i><i></i></span></div>
|
|
1127
|
-
<img src="../screenshots/panel-overview.png" alt="engineering" />
|
|
1128
|
-
</div>
|
|
562
|
+
<div class="glass-card rounded-xl p-7 reveal">
|
|
563
|
+
<div class="flex items-center gap-3 mb-4"><div class="feature-icon"><svg width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round"><path d="M12 2v20M2 12h20"/><circle cx="12" cy="12" r="9"/></svg></div><h3 class="font-display font-semibold text-xl" style="color:var(--fg)" data-i18n="install.ai.title">(推荐)给 AI 一段提示词</h3></div>
|
|
564
|
+
<p class="text-sm mb-4" style="color:var(--fg-dim)" data-i18n="install.ai.desc">把下面这段贴给你的 AI,她会自己读懂怎么用这个插件:</p>
|
|
565
|
+
<div class="relative">
|
|
566
|
+
<pre id="ai-prompt">你的工作区装有 dsh-auto-memory。每轮结束会自动评估沉淀;要跨窗口接续时,先读白板 PLAN.md 与最近交接账本,再开工。需要找过去的决定/做法时,用 memory_recall 检索,不要凭空猜测。</pre>
|
|
567
|
+
<button class="play-btn ghost absolute top-3 right-3 copy-el" data-target="ai-prompt" data-i18n="install.copy">复制</button>
|
|
1129
568
|
</div>
|
|
1130
569
|
</div>
|
|
1131
|
-
|
|
1132
570
|
</div>
|
|
1133
571
|
</section>
|
|
1134
572
|
|
|
1135
|
-
<!-- ──
|
|
1136
|
-
<section class="
|
|
1137
|
-
<div class="
|
|
1138
|
-
<div class="
|
|
1139
|
-
<div class="
|
|
1140
|
-
<
|
|
1141
|
-
|
|
1142
|
-
<p class="sec-sub" data-i18n="g.sub">从欢迎向导到唤起回顾——每个截图都是真实运行画面。</p>
|
|
1143
|
-
</div>
|
|
573
|
+
<!-- ── 07 ROADMAP ── -->
|
|
574
|
+
<section id="roadmap" class="py-28 relative" style="background:var(--bg-elev)">
|
|
575
|
+
<div class="max-w-7xl mx-auto px-6">
|
|
576
|
+
<div class="text-center mb-20 reveal">
|
|
577
|
+
<div class="section-num mb-4">06 / <span data-i18n="roadmap.kicker">版本历程</span></div>
|
|
578
|
+
<h2 class="font-display font-bold text-4xl md:text-6xl leading-tight mb-6" style="color:var(--fg)" data-i18n="roadmap.title">从 v0.1.30<br><span class="gradient-text">到 v3.1.4。</span></h2>
|
|
579
|
+
<p class="text-lg max-w-2xl mx-auto" style="color:var(--fg-dim)" data-i18n="roadmap.subtitle">七个版本条目,每一步都留下了可回查的 CHANGELOG 与守卫断言。</p>
|
|
1144
580
|
</div>
|
|
1145
|
-
<div class="
|
|
1146
|
-
<
|
|
1147
|
-
|
|
1148
|
-
|
|
1149
|
-
</
|
|
1150
|
-
<
|
|
1151
|
-
<img src="../screenshots/panel-hub.png" alt="hub" />
|
|
1152
|
-
<figcaption class="cap"><span data-i18n="g.2.t">记忆中枢</span><small data-i18n="g.2.s">三层记忆店 + 技能晋升审批</small></figcaption>
|
|
1153
|
-
</figure>
|
|
1154
|
-
<figure class="g-card span-12" style="margin:0">
|
|
1155
|
-
<img src="../screenshots/panel-refine.png" alt="refine" />
|
|
1156
|
-
<figcaption class="cap"><span data-i18n="g.3.t">唤起回顾</span><small data-i18n="g.3.s">每次激活决策可打分(A/P/S/H/E)</small></figcaption>
|
|
1157
|
-
</figure>
|
|
1158
|
-
<figure class="g-card" style="margin:0">
|
|
1159
|
-
<img src="../screenshots/tour-welcome.png" alt="tour welcome" />
|
|
1160
|
-
<figcaption class="cap"><span data-i18n="g.4.t">欢迎向导 · 入口</span><small data-i18n="g.4.s">液态玻璃应用图标 + 步骤</small></figcaption>
|
|
1161
|
-
</figure>
|
|
1162
|
-
<figure class="g-card" style="margin:0">
|
|
1163
|
-
<img src="../screenshots/tour-toggles.png" alt="tour toggles" />
|
|
1164
|
-
<figcaption class="cap"><span data-i18n="g.5.t">欢迎向导 · 开关</span><small data-i18n="g.5.s">每项功能当场开关立即生效</small></figcaption>
|
|
1165
|
-
</figure>
|
|
1166
|
-
<figure class="g-card" style="margin:0">
|
|
1167
|
-
<img src="../screenshots/tour-external.png" alt="external scan" />
|
|
1168
|
-
<figcaption class="cap"><span data-i18n="g.6.t">外部记忆扫描</span><small data-i18n="g.6.s">向导内联扫描 + 逐源勾选</small></figcaption>
|
|
1169
|
-
</figure>
|
|
1170
|
-
<figure class="g-card" style="margin:0">
|
|
1171
|
-
<img src="../screenshots/tour-core.png" alt="tour core" />
|
|
1172
|
-
<figcaption class="cap"><span data-i18n="g.7.t">引擎检测</span><small data-i18n="g.7.s">三级语义引擎内联安装</small></figcaption>
|
|
1173
|
-
</figure>
|
|
581
|
+
<div class="max-w-3xl mx-auto space-y-10 pl-8" style="border-left:1px solid var(--border)">
|
|
582
|
+
<div class="timeline-item relative reveal"><div class="flex items-center gap-3 mb-2 flex-wrap"><span class="font-mono text-xs px-2 py-0.5 border rounded" style="color:var(--accent);border-color:var(--accent)">v3.1.4</span><span class="font-mono text-xs" style="color:var(--muted)">2026-09-22</span></div><h3 class="font-display font-semibold text-xl mb-2" style="color:var(--fg)" data-i18n="roadmap.v314.title">当前版本 · 记忆中枢治理</h3><p class="text-sm leading-relaxed" style="color:var(--fg-dim)" data-i18n="roadmap.v314.body">三店持久化 + 治理式写回 + 迁移搬包三步向导。全量回归 173/173 绿,tarball 256 文件 / 17.7MB。</p></div>
|
|
583
|
+
<div class="timeline-item relative reveal reveal-delay-1"><div class="flex items-center gap-3 mb-2 flex-wrap"><span class="font-mono text-xs px-2 py-0.5 border rounded" style="color:var(--muted);border-color:var(--border-strong)">v3.0.0</span><span class="font-mono text-xs" style="color:var(--muted)">2026-09</span></div><h3 class="font-display font-semibold text-xl mb-2" style="color:var(--fg)" data-i18n="roadmap.v300.title">Fable 大版本 · 技能固化</h3><p class="text-sm leading-relaxed" style="color:var(--fg-dim)" data-i18n="roadmap.v300.body">技能四级晋升、90 天归档、激活观测台、无人值守模式 —— 从「记事本」长成「同事」。</p></div>
|
|
584
|
+
<div class="timeline-item relative reveal reveal-delay-2"><div class="flex items-center gap-3 mb-2 flex-wrap"><span class="font-mono text-xs px-2 py-0.5 border rounded" style="color:var(--muted);border-color:var(--border-strong)">v0.1.30</span><span class="font-mono text-xs" style="color:var(--muted)">2026-08</span></div><h3 class="font-display font-semibold text-xl mb-2" style="color:var(--fg)" data-i18n="roadmap.v0130.title">欢迎向导 + 双语义引擎</h3><p class="text-sm leading-relaxed" style="color:var(--fg-dim)" data-i18n="roadmap.v0130.body">每个功能、当场看懂、当场开关;所有用户升级后自动播放一次。JS 与 Python 两套语义引擎解耦成可互换形态。</p></div>
|
|
585
|
+
<div class="timeline-item relative reveal reveal-delay-3"><div class="flex items-center gap-3 mb-2 flex-wrap"><span class="font-mono text-xs px-2 py-0.5 border rounded" style="color:var(--muted);border-color:var(--border-strong)">v0.1.x</span><span class="font-mono text-xs" style="color:var(--muted)" data-i18n="roadmap.early">早期</span></div><h3 class="font-display font-semibold text-xl mb-2" style="color:var(--fg)" data-i18n="roadmap.v01.title">她学会了记事与问候</h3><p class="text-sm leading-relaxed" style="color:var(--fg-dim)" data-i18n="roadmap.v01.body">最早的两个能力:每轮结束自己记下值得留的;你隔一段时间回来,她按时段用合适的语气打招呼。人格从这里定下。</p></div>
|
|
586
|
+
<div class="timeline-item future relative reveal"><div class="flex items-center gap-3 mb-2 flex-wrap"><span class="font-mono text-xs px-2 py-0.5 border rounded" style="color:#d97706;border-color:#d97706">v3.2</span><span class="font-mono text-xs" style="color:var(--muted)" data-i18n="roadmap.next">排队中</span></div><h3 class="font-display font-semibold text-xl mb-2" style="color:var(--fg)" data-i18n="roadmap.v32.title">存储治理(M10)</h3><p class="text-sm leading-relaxed" style="color:var(--fg-dim)" data-i18n="roadmap.v32.body">删除级联撤销、语料健康扫描、管理界面。底座(原子事务 / 保留策略 / 30 天蒸馏)已就绪。</p></div>
|
|
1174
587
|
</div>
|
|
1175
588
|
</div>
|
|
1176
589
|
</section>
|
|
1177
|
-
|
|
1178
|
-
|
|
1179
|
-
<
|
|
1180
|
-
|
|
1181
|
-
|
|
1182
|
-
<
|
|
1183
|
-
<
|
|
1184
|
-
|
|
1185
|
-
|
|
1186
|
-
|
|
590
|
+
<!-- ── 08 GALLERY ── -->
|
|
591
|
+
<section id="gallery" class="py-28 relative">
|
|
592
|
+
<div class="max-w-7xl mx-auto px-6">
|
|
593
|
+
<div class="text-center mb-16 reveal">
|
|
594
|
+
<div class="section-num mb-4">07 / <span data-i18n="gallery.kicker">界面</span></div>
|
|
595
|
+
<h2 class="font-display font-bold text-4xl md:text-6xl leading-tight mb-6" style="color:var(--fg)" data-i18n="gallery.title">七张实机截图,<br><span class="gradient-text">不是示意图。</span></h2>
|
|
596
|
+
<p class="text-lg max-w-2xl mx-auto" style="color:var(--fg-dim)" data-i18n="gallery.subtitle">面板 / 设置 / 记忆中枢 / 激活观测台 / 欢迎向导 / 无人值守 / 外部继承 —— 全部来自实机。</p>
|
|
597
|
+
</div>
|
|
598
|
+
<div class="grid md:grid-cols-2 lg:grid-cols-3 gap-5">
|
|
599
|
+
<a href="../screenshots/panel-hub.png" target="_blank" rel="noreferrer" class="glass-card rounded-xl overflow-hidden reveal group">
|
|
600
|
+
<img src="../screenshots/panel-hub.png" alt="记忆中枢面板" class="w-full block shot-img" loading="lazy">
|
|
601
|
+
<div class="p-4"><div class="font-display font-semibold text-sm mb-1" style="color:var(--fg)" data-i18n="gallery.g1.title">记忆中枢</div><div class="font-mono text-[10px] uppercase tracking-wider" style="color:var(--muted)">MEMORY HUB</div></div>
|
|
602
|
+
</a>
|
|
603
|
+
<a href="../screenshots/settings-zh.png" target="_blank" rel="noreferrer" class="glass-card rounded-xl overflow-hidden reveal reveal-delay-1 group">
|
|
604
|
+
<img src="../screenshots/settings-zh.png" alt="设置页" class="w-full block shot-img" loading="lazy">
|
|
605
|
+
<div class="p-4"><div class="font-display font-semibold text-sm mb-1" style="color:var(--fg)" data-i18n="gallery.g2.title">设置页</div><div class="font-mono text-[10px] uppercase tracking-wider" style="color:var(--muted)">SETTINGS</div></div>
|
|
606
|
+
</a>
|
|
607
|
+
<a href="../screenshots/settings-debug-zh.png" target="_blank" rel="noreferrer" class="glass-card rounded-xl overflow-hidden reveal reveal-delay-2 group">
|
|
608
|
+
<img src="../screenshots/settings-debug-zh.png" alt="激活观测台" class="w-full block shot-img" loading="lazy">
|
|
609
|
+
<div class="p-4"><div class="font-display font-semibold text-sm mb-1" style="color:var(--fg)" data-i18n="gallery.g3.title">激活观测台</div><div class="font-mono text-[10px] uppercase tracking-wider" style="color:var(--muted)">ACTIVATION</div></div>
|
|
610
|
+
</a>
|
|
611
|
+
<a href="../screenshots/tour-welcome.png" target="_blank" rel="noreferrer" class="glass-card rounded-xl overflow-hidden reveal group">
|
|
612
|
+
<img src="../screenshots/tour-welcome.png" alt="欢迎向导" class="w-full block shot-img" loading="lazy">
|
|
613
|
+
<div class="p-4"><div class="font-display font-semibold text-sm mb-1" style="color:var(--fg)" data-i18n="gallery.g4.title">欢迎向导</div><div class="font-mono text-[10px] uppercase tracking-wider" style="color:var(--muted)">WELCOME TOUR</div></div>
|
|
614
|
+
</a>
|
|
615
|
+
<a href="../screenshots/overview-zh.png" target="_blank" rel="noreferrer" class="glass-card rounded-xl overflow-hidden reveal reveal-delay-1 group">
|
|
616
|
+
<img src="../screenshots/overview-zh.png" alt="无人值守" class="w-full block shot-img" loading="lazy">
|
|
617
|
+
<div class="p-4"><div class="font-display font-semibold text-sm mb-1" style="color:var(--fg)" data-i18n="gallery.g5.title">无人值守</div><div class="font-mono text-[10px] uppercase tracking-wider" style="color:var(--muted)">UNATTENDED</div></div>
|
|
618
|
+
</a>
|
|
619
|
+
<a href="../screenshots/tour-external.png" target="_blank" rel="noreferrer" class="glass-card rounded-xl overflow-hidden reveal reveal-delay-2 group">
|
|
620
|
+
<img src="../screenshots/tour-external.png" alt="外部记忆继承" class="w-full block shot-img" loading="lazy">
|
|
621
|
+
<div class="p-4"><div class="font-display font-semibold text-sm mb-1" style="color:var(--fg)" data-i18n="gallery.g6.title">外部记忆继承</div><div class="font-mono text-[10px] uppercase tracking-wider" style="color:var(--muted)">EXTERNAL MEMORY</div></div>
|
|
622
|
+
</a>
|
|
1187
623
|
</div>
|
|
1188
624
|
|
|
1189
|
-
|
|
1190
|
-
|
|
1191
|
-
|
|
1192
|
-
<
|
|
1193
|
-
<div class="codebox">
|
|
1194
|
-
<div class="codebox-head"><span>bash</span><button class="copy-btn" data-copy="cd ~/.dsh/profiles/web && pnpm add @a9i5k4/dsh-auto-memory">copy</button></div>
|
|
1195
|
-
<pre>cd ~/.dsh/profiles/web
|
|
1196
|
-
pnpm add @a9i5k4/dsh-auto-memory</pre>
|
|
1197
|
-
</div>
|
|
1198
|
-
<p style="margin-top:10px" data-i18n="q.1.alt">没有 pnpm?npm install @a9i5k4/dsh-auto-memory 同样可用。</p>
|
|
1199
|
-
</div>
|
|
1200
|
-
<div class="qs-cell">
|
|
1201
|
-
<h3><span class="n">02</span><span data-i18n="q.2.t">注册到 profile</span></h3>
|
|
1202
|
-
<p data-i18n="q.2.p">编辑同目录 package.json,在 dsh.profile.bundles 数组追加:</p>
|
|
1203
|
-
<div class="codebox">
|
|
1204
|
-
<div class="codebox-head"><span>json</span></div>
|
|
1205
|
-
<pre>"dsh.profile.bundles": [
|
|
1206
|
-
"...",
|
|
1207
|
-
"@a9i5k4/dsh-auto-memory"
|
|
1208
|
-
]</pre>
|
|
1209
|
-
</div>
|
|
625
|
+
<!-- 轮播:七幕宣传图 -->
|
|
626
|
+
<div class="mt-16 reveal">
|
|
627
|
+
<div class="text-center mb-8">
|
|
628
|
+
<div class="section-num" data-i18n="gallery.capKicker">宣传套图 · 七幕</div>
|
|
1210
629
|
</div>
|
|
1211
|
-
<div class="
|
|
1212
|
-
<
|
|
1213
|
-
|
|
1214
|
-
|
|
1215
|
-
<
|
|
1216
|
-
<
|
|
630
|
+
<div class="relative glass-card rounded-2xl p-3 overflow-hidden">
|
|
631
|
+
<div id="promo-track" class="flex transition-transform duration-500" style="will-change:transform">
|
|
632
|
+
<img src="../screenshots/promo/promo-1-hero.png" alt="第一幕:她记得,不必吩咐" class="w-full flex-shrink-0 rounded-xl block">
|
|
633
|
+
<img src="../screenshots/promo/promo-1b-auto-recall.png" alt="第二幕:主动唤起" class="w-full flex-shrink-0 rounded-xl block">
|
|
634
|
+
<img src="../screenshots/promo/promo-2-tour.png" alt="第三幕:欢迎向导" class="w-full flex-shrink-0 rounded-xl block">
|
|
635
|
+
<img src="../screenshots/promo/promo-3-recall.png" alt="第四幕:召回与固化" class="w-full flex-shrink-0 rounded-xl block">
|
|
636
|
+
<img src="../screenshots/promo/promo-4-unattended.png" alt="第五幕:无人值守" class="w-full flex-shrink-0 rounded-xl block">
|
|
637
|
+
<img src="../screenshots/promo/promo-5-external.png" alt="第六幕:外部继承" class="w-full flex-shrink-0 rounded-xl block">
|
|
638
|
+
<img src="../screenshots/promo/promo-6-greeting.png" alt="第七幕:定时问候" class="w-full flex-shrink-0 rounded-xl block">
|
|
1217
639
|
</div>
|
|
1218
|
-
|
|
1219
|
-
|
|
1220
|
-
|
|
1221
|
-
|
|
1222
|
-
|
|
1223
|
-
|
|
1224
|
-
|
|
1225
|
-
pnpm up @a9i5k4/dsh-auto-memory</pre>
|
|
640
|
+
<div class="flex items-center justify-between mt-3 px-1">
|
|
641
|
+
<div class="font-mono text-[10px] uppercase tracking-widest" style="color:var(--muted)"><span data-i18n="gallery.cap">七幕</span> · <span id="promo-idx">1</span>/7</div>
|
|
642
|
+
<div class="flex gap-1.5" id="promo-dots"></div>
|
|
643
|
+
<div class="flex gap-2">
|
|
644
|
+
<button class="play-btn ghost" id="promo-prev" aria-label="prev">←</button>
|
|
645
|
+
<button class="play-btn ghost" id="promo-next" aria-label="next">→</button>
|
|
646
|
+
</div>
|
|
1226
647
|
</div>
|
|
1227
648
|
</div>
|
|
1228
649
|
</div>
|
|
650
|
+
</div>
|
|
651
|
+
</section>
|
|
1229
652
|
|
|
1230
|
-
|
|
1231
|
-
|
|
1232
|
-
|
|
1233
|
-
|
|
1234
|
-
|
|
1235
|
-
<
|
|
1236
|
-
|
|
1237
|
-
|
|
1238
|
-
|
|
1239
|
-
|
|
1240
|
-
|
|
1241
|
-
|
|
653
|
+
<!-- ── 09 COMPARE ── -->
|
|
654
|
+
<section id="compare" class="py-28 relative" style="background:var(--bg-elev)">
|
|
655
|
+
<div class="max-w-7xl mx-auto px-6">
|
|
656
|
+
<div class="text-center mb-16 reveal">
|
|
657
|
+
<div class="section-num mb-4">08 / <span data-i18n="compare.kicker">对比</span></div>
|
|
658
|
+
<h2 class="font-display font-bold text-4xl md:text-6xl leading-tight mb-6" style="color:var(--fg)" data-i18n="compare.title">它在这条线上的<br><span class="gradient-text">位置。</span></h2>
|
|
659
|
+
</div>
|
|
660
|
+
<div class="glass-card rounded-2xl overflow-hidden reveal">
|
|
661
|
+
<div class="overflow-x-auto">
|
|
662
|
+
<table class="compare-table">
|
|
663
|
+
<thead><tr>
|
|
664
|
+
<th data-i18n="compare.capability">能力</th>
|
|
665
|
+
<th class="text-center" data-i18n="compare.col1">工具式记忆<br><span class="text-[10px] font-normal" style="color:var(--muted)">需要在提示里调用</span></th>
|
|
666
|
+
<th class="text-center" data-i18n="compare.col2">内置上下文<br><span class="text-[10px] font-normal" style="color:var(--muted)">厂商实验特性</span></th>
|
|
667
|
+
<th class="text-center accent" data-i18n="compare.col3">dsh-auto-memory<br><span class="text-[10px] font-normal">宿主中间件</span></th>
|
|
668
|
+
</tr></thead>
|
|
669
|
+
<tbody>
|
|
670
|
+
<tr><td data-i18n="compare.r1">不需模型主动调用</td><td class="text-center cross">—</td><td class="text-center partial">~</td><td class="text-center check">✓</td></tr>
|
|
671
|
+
<tr><td data-i18n="compare.r2">跨窗口 / 跨会话</td><td class="text-center check">✓</td><td class="text-center check">✓</td><td class="text-center check">✓</td></tr>
|
|
672
|
+
<tr><td data-i18n="compare.r3">跨工具记忆继承</td><td class="text-center cross">—</td><td class="text-center cross">—</td><td class="text-center check">✓</td></tr>
|
|
673
|
+
<tr><td data-i18n="compare.r4">前缀缓存字节稳定</td><td class="text-center partial">~</td><td class="text-center cross">—</td><td class="text-center check">✓</td></tr>
|
|
674
|
+
<tr><td data-i18n="compare.r5">零运行时依赖</td><td class="text-center partial">~</td><td class="text-center check">✓</td><td class="text-center check">✓</td></tr>
|
|
675
|
+
<tr><td data-i18n="compare.r6">每次召回带证据链</td><td class="text-center cross">—</td><td class="text-center cross">—</td><td class="text-center check">✓</td></tr>
|
|
676
|
+
<tr><td data-i18n="compare.r7">技能固化(程序性记忆)</td><td class="text-center cross">—</td><td class="text-center cross">—</td><td class="text-center check">✓</td></tr>
|
|
677
|
+
<tr><td data-i18n="compare.r8">三级算力可切换</td><td class="text-center partial">~</td><td class="text-center cross">—</td><td class="text-center check">✓</td></tr>
|
|
678
|
+
<tr><td data-i18n="compare.r9">记忆全在本机磁盘</td><td class="text-center check">✓</td><td class="text-center cross">—</td><td class="text-center check">✓</td></tr>
|
|
679
|
+
<tr><td data-i18n="compare.r10">开源可审计</td><td class="text-center partial">~</td><td class="text-center cross">—</td><td class="text-center check">✓</td></tr>
|
|
680
|
+
</tbody>
|
|
681
|
+
</table>
|
|
1242
682
|
</div>
|
|
1243
|
-
|
|
683
|
+
</div>
|
|
684
|
+
<div class="flex flex-wrap gap-4 mt-6 text-xs font-mono reveal" style="color:var(--muted)">
|
|
685
|
+
<div class="flex items-center gap-2"><span class="check">✓</span> <span data-i18n="compare.legend1">完整支持</span></div>
|
|
686
|
+
<div class="flex items-center gap-2"><span class="partial">~</span> <span data-i18n="compare.legend2">部分 / 需变通</span></div>
|
|
687
|
+
<div class="flex items-center gap-2"><span class="cross">—</span> <span data-i18n="compare.legend3">不支持</span></div>
|
|
1244
688
|
</div>
|
|
1245
689
|
</div>
|
|
1246
690
|
</section>
|
|
1247
691
|
|
|
1248
|
-
<!-- ──
|
|
1249
|
-
<section
|
|
1250
|
-
<div class="
|
|
1251
|
-
<div class="
|
|
1252
|
-
<div class="
|
|
1253
|
-
<
|
|
1254
|
-
<h2 data-i18n="c.title">感谢这两位</h2>
|
|
1255
|
-
<p class="sec-sub" data-i18n="c.sub">dsh-auto-memory 不是一个"我一个人写的项目"——下面这两位是塑造产品形态的真正合作者。</p>
|
|
1256
|
-
</div>
|
|
692
|
+
<!-- ── 10 FAQ ── -->
|
|
693
|
+
<section id="faq" class="py-28 relative">
|
|
694
|
+
<div class="max-w-4xl mx-auto px-6">
|
|
695
|
+
<div class="text-center mb-16 reveal">
|
|
696
|
+
<div class="section-num mb-4">09 / <span data-i18n="faq.kicker">常见问题</span></div>
|
|
697
|
+
<h2 class="font-display font-bold text-4xl md:text-6xl leading-tight mb-6" style="color:var(--fg)" data-i18n="faq.title">你大概想问<br><span class="gradient-text">这些。</span></h2>
|
|
1257
698
|
</div>
|
|
1258
|
-
|
|
1259
|
-
|
|
1260
|
-
<
|
|
1261
|
-
|
|
1262
|
-
|
|
1263
|
-
|
|
1264
|
-
|
|
1265
|
-
<
|
|
1266
|
-
|
|
1267
|
-
<div class="ref"><a href="https://github.com/nkh0472" target="_blank" rel="noreferrer">github.com/nkh0472</a> · <a href="https://github.com/Aik358/dsh-auto-memory/issues/10" target="_blank" rel="noreferrer">Issue #10</a></div>
|
|
1268
|
-
<div class="contrib" data-i18n="c.2.d">无人值守/批处理场景加固反馈——直接推动了欢迎向导与功能开关化。</div>
|
|
1269
|
-
</div>
|
|
699
|
+
<div class="space-y-4">
|
|
700
|
+
<details class="reveal" open><summary data-i18n="faq.q1">她会偷我东西吗?数据存在哪?</summary><p data-i18n="faq.a1">全部写在你自己机器的磁盘上:用户级记忆在 ~/.dsh/memory/MEMORY.md,项目记忆与日记在工作区的 .dsh-memory/ 下。没有云端、没有账号、没有遥测。可审计、可编辑、可删除。</p></details>
|
|
701
|
+
<details class="reveal reveal-delay-1"><summary data-i18n="faq.q2">不装语义模型能用吗?</summary><p data-i18n="faq.a2">能。词法档 0GB 永远可用(BM25 + CJK 2-gram),装完即用。内置 e5-small ~130MB 会在首启自动下载,检索质量更高。Python BGE-M3 563MB 是进阶档,设置页一键装。</p></details>
|
|
702
|
+
<details class="reveal reveal-delay-2"><summary data-i18n="faq.q3">「主动」会不会很吵、一直打断我?</summary><p data-i18n="faq.a3">不会。召回之后还有一道闸:分数阈值、回声否决、连贯性检查、硬门禁。默认策略偏保守,宁可少说话。canary 车道才显式唤起,shadow 车道只记录不注入。实测 canary 一跑下来 delivered=3 / seen=24。</p></details>
|
|
703
|
+
<details class="reveal reveal-delay-3"><summary data-i18n="faq.q4">会不会拖慢我的对话?多花 token?</summary><p data-i18n="faq.a4">注入点在提示词里的字节位置固定不变,前缀缓存持续命中 —— 不会为记忆付两次钱。词法档查询往返在毫秒级;内置向量档实测 3.8ms/次。检索在主流程之外,不阻塞你。</p></details>
|
|
704
|
+
<details class="reveal"><summary data-i18n="faq.q5">她记错了怎么办?</summary><p data-i18n="faq.a5">每条记忆都带证据链:哪条消息、哪个工具、哪次反思。激活观测台可以逐次复核打分(A/P/S/H/E),不满意的可以直接删,或者改 policy 让它下次别这么判断。</p></details>
|
|
705
|
+
<details class="reveal reveal-delay-1"><summary data-i18n="faq.q6">JS 语义档和 Python 语义档要同时装吗?</summary><p data-i18n="faq.a6">不需要,它们是两套相对独立、可互相替换的引擎。默认形态就是 JS 内置档(普通用户装的就是它);Python 档是发烧友主动在设置里安装的进阶项。开一个不会顺带开另一个,一个不在也不影响另一个。</p></details>
|
|
706
|
+
<details class="reveal reveal-delay-2"><summary data-i18n="faq.q7">能接我其他 AI 的记忆吗?</summary><p data-i18n="faq.a7">能。WorkBuddy / CodeBuddy / Claude Code / Codex 的记忆会被扫描进来,按来源分组管理、可逐源启停。采用纯链接模式接入:只存路径指针,不抄内容 —— 对方内容变了不会过期。</p></details>
|
|
707
|
+
<details class="reveal reveal-delay-3"><summary data-i18n="faq.q8">开源协议与贡献方式?</summary><p data-i18n="faq.a8">BSD-3-Clause,代码与文档全部公开在 GitHub。提 issue、交 PR 都欢迎;下一个里程碑是 M10 存储治理(删除级联撤销 + 语料健康扫描 + 管理界面)。</p></details>
|
|
1270
708
|
</div>
|
|
709
|
+
</div>
|
|
710
|
+
</section>
|
|
1271
711
|
|
|
1272
|
-
|
|
1273
|
-
|
|
1274
|
-
|
|
1275
|
-
|
|
1276
|
-
|
|
1277
|
-
|
|
1278
|
-
|
|
1279
|
-
|
|
1280
|
-
</a>
|
|
1281
|
-
<a
|
|
1282
|
-
|
|
1283
|
-
<span data-i18n="c.l3">License: BSD-3-Clause</span>
|
|
1284
|
-
</a>
|
|
712
|
+
<!-- ── 11 CTA ── -->
|
|
713
|
+
<section class="py-32 relative overflow-hidden" style="background:var(--bg-elev)">
|
|
714
|
+
<div class="blob" style="width:600px;height:600px;background:var(--accent);top:-20%;left:50%;transform:translateX(-50%)"></div>
|
|
715
|
+
<div class="relative max-w-4xl mx-auto px-6 text-center reveal">
|
|
716
|
+
<div class="section-num mb-4">10 / <span data-i18n="cta.kicker">一起养大</span></div>
|
|
717
|
+
<h2 class="font-display font-bold text-5xl md:text-7xl leading-[1.02] mb-8" style="color:var(--fg)" data-i18n="cta.title">记忆是你的,<br><span class="gradient-text">代码也是。</span></h2>
|
|
718
|
+
<p class="text-xl max-w-2xl mx-auto mb-12 leading-relaxed" style="color:var(--fg-dim)" data-i18n="cta.subtitle">开源、可审计、可删除。装一个,看她还记得什么。</p>
|
|
719
|
+
<div class="flex flex-wrap gap-4 justify-center mb-10">
|
|
720
|
+
<a href="https://github.com/Aik358/dsh-auto-memory" target="_blank" rel="noreferrer" class="btn-primary px-8 py-4 rounded-lg font-medium flex items-center gap-2 magnetic"><svg width="16" height="16" viewBox="0 0 24 24" fill="currentColor"><path d="M12 .3a12 12 0 0 0-3.8 23.4c.6.1.8-.3.8-.6v-2.2c-3.3.7-4-1.6-4-1.6-.5-1.4-1.3-1.8-1.3-1.8-1.1-.7.1-.7.1-.7 1.2.1 1.8 1.2 1.8 1.2 1 1.8 2.8 1.3 3.5 1 .1-.8.4-1.3.7-1.6-2.7-.3-5.5-1.3-5.5-6 0-1.3.5-2.4 1.2-3.2-.1-.3-.5-1.5.1-3.2 0 0 1-.3 3.3 1.2a11.5 11.5 0 0 1 6 0c2.3-1.5 3.3-1.2 3.3-1.2.6 1.7.2 2.9.1 3.2.8.8 1.2 1.9 1.2 3.2 0 4.6-2.8 5.7-5.5 6 .4.4.8 1.1.8 2.2v3.3c0 .3.2.7.8.6A12 12 0 0 0 12 .3"/></svg><span data-i18n="cta.button1">GitHub</span></a>
|
|
721
|
+
<a href="https://www.npmjs.com/package/@a9i5k4/dsh-auto-memory" target="_blank" rel="noreferrer" class="btn-ghost px-8 py-4 rounded-lg font-medium magnetic" data-i18n="cta.button2">npm →</a>
|
|
722
|
+
<a href="https://qm.qq.com/q/v7Asxn6vPa" target="_blank" rel="noreferrer" class="btn-ghost px-8 py-4 rounded-lg font-medium magnetic" style="border-color:var(--accent);color:var(--accent)" data-i18n="cta.button3">QQ 群 →</a>
|
|
1285
723
|
</div>
|
|
1286
|
-
|
|
1287
|
-
<p style="margin-top:18px;color:var(--ink-2);font-size:13.5px" data-i18n="c.foot">欢迎 issue / PR——即使只是改一个标点或一句文案,也算参与。</p>
|
|
1288
724
|
</div>
|
|
1289
725
|
</section>
|
|
1290
726
|
|
|
1291
|
-
<!-- ──
|
|
1292
|
-
<footer>
|
|
1293
|
-
<div class="
|
|
1294
|
-
<div class="
|
|
1295
|
-
<div class="
|
|
1296
|
-
|
|
1297
|
-
|
|
1298
|
-
|
|
1299
|
-
|
|
727
|
+
<!-- ── FOOTER ── -->
|
|
728
|
+
<footer class="pt-20 pb-12 relative" style="border-top:1px solid var(--border)">
|
|
729
|
+
<div class="max-w-7xl mx-auto px-6">
|
|
730
|
+
<div class="grid md:grid-cols-12 gap-10">
|
|
731
|
+
<div class="md:col-span-5">
|
|
732
|
+
<div class="flex items-center gap-3 mb-4">
|
|
733
|
+
<div class="brand-logo w-9 h-9" style="color:var(--fg)"><svg viewBox="0 0 40 40" fill="none"><g class="brain-path"><path d="M20 6c-4 0-7 2.5-7 6 0 1 .2 2 .6 2.8C11 15.6 9.5 17.4 9.5 19.6c0 1.6.9 3 2.3 3.8-.2.6-.3 1.2-.3 1.9 0 3.2 2.6 5.7 6 5.7 1 0 1.9-.2 2.5-.7"/><path d="M20 6c4 0 7 2.5 7 6 0 1-.2 2-.6 2.8 2.6.8 4.1 2.6 4.1 4.8 0 1.6-.9 3-2.3 3.8.2.6.3 1.2.3 1.9 0 3.2-2.6 5.7-6 5.7-1 0-1.9-.2-2.5-.7"/><path d="M20 6v25"/></g></svg></div>
|
|
734
|
+
<div><div class="font-display font-semibold" style="color:var(--fg)">dsh-auto-memory</div><div class="text-[10px] font-mono tracking-wider" style="color:var(--muted)">无问自忆 · 记忆不断线 · v3.1.4</div></div>
|
|
735
|
+
</div>
|
|
736
|
+
<p class="text-sm leading-relaxed max-w-md" style="color:var(--fg-dim)" data-i18n="footer.desc">DSH 插件:宿主侧主动联想记忆中间件。她记得,不必吩咐 —— 记忆长在你自己的机器上。BSD-3-Clause。</p>
|
|
737
|
+
</div>
|
|
738
|
+
<div class="md:col-span-3">
|
|
739
|
+
<div class="text-xs font-mono uppercase tracking-wider mb-4" style="color:var(--muted)" data-i18n="footer.project">项目</div>
|
|
740
|
+
<ul class="space-y-2 text-sm">
|
|
741
|
+
<li><a href="#features" class="nav-link" data-i18n="nav.features">能力</a></li>
|
|
742
|
+
<li><a href="#demo" class="nav-link" data-i18n="nav.demo">实机演示</a></li>
|
|
743
|
+
<li><a href="#architecture" class="nav-link" data-i18n="nav.architecture">分层</a></li>
|
|
744
|
+
<li><a href="#install" class="nav-link" data-i18n="nav.install">安装</a></li>
|
|
745
|
+
</ul>
|
|
746
|
+
</div>
|
|
747
|
+
<div class="md:col-span-4">
|
|
748
|
+
<div class="text-xs font-mono uppercase tracking-wider mb-4" style="color:var(--muted)" data-i18n="footer.resources">资源</div>
|
|
749
|
+
<ul class="space-y-2 text-sm">
|
|
750
|
+
<li><a href="https://github.com/Aik358/dsh-auto-memory" target="_blank" rel="noreferrer" class="nav-link">GitHub</a></li>
|
|
751
|
+
<li><a href="https://www.npmjs.com/package/@a9i5k4/dsh-auto-memory" target="_blank" rel="noreferrer" class="nav-link">npm</a></li>
|
|
752
|
+
<li><a href="https://github.com/Aik358/dsh-auto-memory/blob/main/CHANGELOG.md" target="_blank" rel="noreferrer" class="nav-link">CHANGELOG</a></li>
|
|
753
|
+
<li><a href="https://github.com/Aik358/dsh-auto-memory/blob/main/docs/PROMO-STYLE-GUIDE.md" target="_blank" rel="noreferrer" class="nav-link" data-i18n="footer.style">叙述风格指南</a></li>
|
|
754
|
+
</ul>
|
|
1300
755
|
</div>
|
|
1301
756
|
</div>
|
|
1302
|
-
<div class="
|
|
1303
|
-
<
|
|
1304
|
-
<span data-i18n="
|
|
1305
|
-
<span data-i18n="ftc.zcode">ZCode(GLM · Z.ai)· 工程与论文</span>
|
|
1306
|
-
<span data-i18n="ftc.k3">Kimi K3 · 前端</span>
|
|
1307
|
-
<span data-i18n="ftc.note">人机协作 · AI 署名,人类审核</span>
|
|
757
|
+
<div class="mt-12 pt-6 text-xs font-mono flex flex-col md:flex-row justify-between gap-3" style="border-top:1px solid var(--border);color:var(--muted)">
|
|
758
|
+
<div>© 2026 dsh-auto-memory · Aik358 · <span data-i18n="footer.rights">BSD-3-Clause</span></div>
|
|
759
|
+
<div><span data-i18n="footer.built">记忆在你自己的机器上 · 可审计 · 可删除</span></div>
|
|
1308
760
|
</div>
|
|
1309
761
|
</div>
|
|
1310
762
|
</footer>
|
|
1311
763
|
|
|
764
|
+
</div><!-- /view-main -->
|
|
1312
765
|
<script>
|
|
1313
|
-
|
|
1314
|
-
|
|
1315
|
-
|
|
1316
|
-
|
|
1317
|
-
|
|
1318
|
-
|
|
1319
|
-
|
|
1320
|
-
|
|
1321
|
-
|
|
1322
|
-
|
|
1323
|
-
|
|
1324
|
-
|
|
1325
|
-
|
|
1326
|
-
|
|
1327
|
-
|
|
1328
|
-
|
|
1329
|
-
|
|
1330
|
-
|
|
1331
|
-
|
|
1332
|
-
|
|
1333
|
-
|
|
1334
|
-
|
|
1335
|
-
|
|
1336
|
-
|
|
1337
|
-
|
|
1338
|
-
|
|
1339
|
-
|
|
1340
|
-
|
|
1341
|
-
|
|
1342
|
-
|
|
1343
|
-
|
|
1344
|
-
|
|
1345
|
-
|
|
1346
|
-
|
|
1347
|
-
|
|
1348
|
-
|
|
1349
|
-
|
|
1350
|
-
|
|
1351
|
-
|
|
1352
|
-
|
|
1353
|
-
|
|
1354
|
-
|
|
1355
|
-
|
|
1356
|
-
|
|
1357
|
-
|
|
1358
|
-
|
|
1359
|
-
|
|
1360
|
-
|
|
1361
|
-
|
|
1362
|
-
|
|
1363
|
-
|
|
1364
|
-
|
|
1365
|
-
|
|
1366
|
-
|
|
1367
|
-
|
|
1368
|
-
|
|
1369
|
-
|
|
1370
|
-
|
|
1371
|
-
|
|
1372
|
-
|
|
1373
|
-
|
|
1374
|
-
|
|
1375
|
-
|
|
1376
|
-
|
|
1377
|
-
|
|
1378
|
-
|
|
1379
|
-
|
|
1380
|
-
|
|
1381
|
-
|
|
1382
|
-
|
|
1383
|
-
|
|
1384
|
-
|
|
1385
|
-
|
|
1386
|
-
|
|
1387
|
-
|
|
1388
|
-
|
|
1389
|
-
|
|
1390
|
-
|
|
1391
|
-
|
|
1392
|
-
|
|
1393
|
-
|
|
1394
|
-
|
|
1395
|
-
|
|
1396
|
-
|
|
1397
|
-
|
|
1398
|
-
|
|
1399
|
-
|
|
1400
|
-
|
|
1401
|
-
|
|
1402
|
-
|
|
1403
|
-
|
|
1404
|
-
|
|
1405
|
-
|
|
1406
|
-
|
|
1407
|
-
|
|
1408
|
-
|
|
1409
|
-
|
|
1410
|
-
|
|
1411
|
-
|
|
1412
|
-
|
|
1413
|
-
|
|
1414
|
-
|
|
1415
|
-
|
|
1416
|
-
|
|
1417
|
-
|
|
1418
|
-
|
|
1419
|
-
|
|
1420
|
-
|
|
1421
|
-
|
|
1422
|
-
|
|
1423
|
-
|
|
1424
|
-
|
|
1425
|
-
|
|
1426
|
-
|
|
1427
|
-
|
|
1428
|
-
|
|
1429
|
-
|
|
1430
|
-
|
|
1431
|
-
|
|
1432
|
-
|
|
1433
|
-
|
|
1434
|
-
|
|
1435
|
-
|
|
1436
|
-
|
|
1437
|
-
|
|
1438
|
-
|
|
1439
|
-
|
|
1440
|
-
|
|
1441
|
-
|
|
1442
|
-
|
|
1443
|
-
|
|
1444
|
-
|
|
1445
|
-
|
|
1446
|
-
|
|
1447
|
-
|
|
1448
|
-
|
|
1449
|
-
|
|
1450
|
-
|
|
1451
|
-
|
|
1452
|
-
|
|
1453
|
-
|
|
1454
|
-
|
|
1455
|
-
|
|
1456
|
-
|
|
1457
|
-
|
|
1458
|
-
|
|
1459
|
-
|
|
1460
|
-
|
|
1461
|
-
|
|
1462
|
-
|
|
1463
|
-
|
|
1464
|
-
|
|
1465
|
-
|
|
1466
|
-
|
|
1467
|
-
|
|
1468
|
-
|
|
1469
|
-
|
|
1470
|
-
|
|
1471
|
-
|
|
1472
|
-
|
|
1473
|
-
|
|
1474
|
-
|
|
1475
|
-
|
|
1476
|
-
|
|
1477
|
-
|
|
1478
|
-
|
|
1479
|
-
|
|
1480
|
-
|
|
1481
|
-
|
|
1482
|
-
|
|
1483
|
-
|
|
1484
|
-
|
|
1485
|
-
|
|
1486
|
-
|
|
1487
|
-
|
|
1488
|
-
|
|
1489
|
-
|
|
1490
|
-
|
|
1491
|
-
|
|
1492
|
-
|
|
1493
|
-
|
|
1494
|
-
|
|
1495
|
-
|
|
1496
|
-
|
|
1497
|
-
|
|
1498
|
-
|
|
1499
|
-
|
|
1500
|
-
|
|
1501
|
-
|
|
1502
|
-
|
|
1503
|
-
|
|
1504
|
-
|
|
1505
|
-
|
|
1506
|
-
|
|
1507
|
-
|
|
1508
|
-
|
|
1509
|
-
|
|
1510
|
-
|
|
1511
|
-
"f.3.p":"A step-by-step tour that auto-plays after first install or upgrade — an Office/Fluent-style liquid-glass app icon family; every feature switch writes config instantly. Closing mid-tour lands on a finish page telling you exactly where each feature lives in Settings.",
|
|
1512
|
-
"f.3.l1":"Per-step liquid-glass icon with bespoke motion (cyan inject, amber greeting, green calendar, violet engine, sky radar, coral finish)",
|
|
1513
|
-
"f.3.l2":"Three-tier retrieval engine auto-detected and one-click installable inline (SHA256 verify + inference self-test)",
|
|
1514
|
-
"f.3.l3":"Live external-memory scan: WorkBuddy / Claude Code / Codex sources, tick-per-source",
|
|
1515
|
-
"f.3.l4":"One-time catch-up for upgraders: from v0.1.30 every user auto-plays the full tour once after upgrading",
|
|
1516
|
-
"f.3.l5":"Settings → Appearance → Welcome tour →","f.3.l5b":"▶ Replay","f.3.l5c":"anytime",
|
|
1517
|
-
"f.3.art":"WELCOME TOUR",
|
|
1518
|
-
"f.4.kicker":"3.4 · Activation & crystallization","f.4.t":"Interrupt only when it matters",
|
|
1519
|
-
"f.4.p":"Associative recall detects memory needs directly in the conversation chain and injects at the next boundary (prefix-cache friendly). Frequent workflows crystallize into skill checklists that attach automatically, promote after cross-session validation — every \"should I interrupt\" decision is gradeable in the Recall review tab.",
|
|
1520
|
-
"f.4.l1":"Grade: A activate / P prefetch / S suppress / H harmful / E edit target",
|
|
1521
|
-
"f.4.l2":"Skill promotion four states: observed → candidate → validated → active",
|
|
1522
|
-
"f.4.l3":"90 days without use auto-archive, pin to keep","f.4.l4":"The review queue digests into policy hints, feeding auto-decision",
|
|
1523
|
-
"f.4.art":"RECALL REVIEW",
|
|
1524
|
-
"f.5.kicker":"3.5 · Unattended mode","f.5.t":"Built for long batch jobs",
|
|
1525
|
-
"f.5.p":"Settings → Automation offers a manual switch and auto-unattended overnight (22:00-08:00, tunable). While engaged: no greetings, no niceties or behavioural directives, calendar silent, context stable — tokens go to the work, not the small talk.",
|
|
1526
|
-
"f.5.l1":"Zero niceties / zero directives / calendar silent / context frozen","f.5.l2":"Tunable window (default 22:00-08:00)","f.5.l3":"Born from community Issue #10 hardening feedback",
|
|
1527
|
-
"f.5.s1.l":"niceties injected while unattended","f.5.s2.l":"default overnight window","f.5.s3.l":"context stability (no drift)",
|
|
1528
|
-
"f.5.art":"UNATTENDED",
|
|
1529
|
-
"f.6.kicker":"3.6 · AI greetings & daily reflection","f.6.t":"Period-aware + return greeting + daily review",
|
|
1530
|
-
"f.6.p":"A period-aware greeting (morning/afternoon/evening) that mentions your most important work today. Return after an hour away and the memory panel auto-opens with \"welcome back\" plus a recent-work digest. The first session of each day presents yesterday's structured reflection.",
|
|
1531
|
-
"f.6.l1":"Period greeting: morning/afternoon/evening, mentioning today's work","f.6.l2":">1h away → auto-open panel + \"welcome back\"","f.6.l3":"First session of the day: yesterday's structured reflection",
|
|
1532
|
-
"f.6.art":"OVERVIEW",
|
|
1533
|
-
"f.7.kicker":"3.7 · Smart search & workspace map","f.7.t":"Natural-language search, cross-workspace by default",
|
|
1534
|
-
"f.7.p":"Ask in natural language — the AI expands your query into keywords, scans every memory layer, and answers conversationally with sources cited. The Workspace tab auto-generates a workspace mind map — AI groups themes and cross-workspace links; drag, zoom, click a card for details.",
|
|
1535
|
-
"f.7.l1":"Cross-workspace search built in; results cite the source workspace","f.7.l2":"Workspace mind map: theme grouping + cross-workspace links","f.7.l3":"Drag / zoom / click for details",
|
|
1536
|
-
"f.7.art":"SEARCH",
|
|
1537
|
-
"f.8.kicker":"3.8 · Calendar — maintained by the AI","f.8.t":"Deadlines grow out of your conversation",
|
|
1538
|
-
"f.8.p":"The AI spots deadlines and promises in conversation and files them (calendar_add). Pending items are injected into later sessions until completed; day view is a 07:00-22:00 timeline with location/reminder fields and urgency-tinted colors.",
|
|
1539
|
-
"f.8.l1":"AI spots deadlines / promises in conversation → calendar","f.8.l2":"Pending items injected into later sessions until completed","f.8.l3":"07:00-22:00 timeline + location/reminder + urgency-tinted colors",
|
|
1540
|
-
"f.8.art":"CALENDAR",
|
|
1541
|
-
"f.9.kicker":"3.9 · External memory inheritance","f.9.t":"Don't let past experience go to waste",
|
|
1542
|
-
"f.9.p":"Sessions and memories from WorkBuddy / CodeBuddy / Claude Code / Codex are scanned, importable per source (path pointers only, never copied content), removable per source; import-side and injection-side hygiene gates keep external dirt out.",
|
|
1543
|
-
"f.9.l1":"Scans: WorkBuddy / CodeBuddy / Claude Code / Codex","f.9.l2":"Per-source import: path pointers only (no content copy)","f.9.l3":"Per-source delete + double hygiene gates",
|
|
1544
|
-
"f.9.art":"EXTERNAL SCAN",
|
|
1545
|
-
"f.10.kicker":"3.10 · Memory hygiene (production-grade)","f.10.t":"Write gate + dirty-token scanner",
|
|
1546
|
-
"f.10.p":"All three write tools run sanitizeForWrite: GBK mojibake (34-feature table), stutter degeneration, consecutive duplicate lines, external-AI-profile JSON signatures, base64 residue — rejected with a human-readable reason. Settings → Debug Center \"Scan dirty tokens\": one-click scan of user memory / notes / logs / reflections, reported by line range (locations only, no content).",
|
|
1547
|
-
"f.10.l1":"34 GBK-mojibake feature table","f.10.l2":"Stutter degeneration / consecutive duplicate lines / external-profile JSON / base64 residue",
|
|
1548
|
-
"f.10.l3":"8,000 chars per append, 200,000 per rewrite caps","f.10.l4":"Appends deduped against the last ~60 lines",
|
|
1549
|
-
"f.10.art":"HYGIENE",
|
|
1550
|
-
"f.11.kicker":"3.11 · Memory lifecycle","f.11.t":"30-day distillation: trade process flow for reusable conclusions",
|
|
1551
|
-
"f.11.p":"memory_maintain_pre hands logs older than 30 days to the AI for distillation: only durable cross-session value (decisions / conventions / preferences / gotchas) is written into project notes. Originals are archived to archive/ (degrades to verbatim archive if the AI is unavailable — never lose information).",
|
|
1552
|
-
"f.11.l1":"30-day distillation window: old logs → durable points → project notes",
|
|
1553
|
-
"f.11.l2":"Explicit boundary:","f.11.l2b":"procedure skills (skill crystallization)","f.11.l2c":"and the two note levels are out of scope",
|
|
1554
|
-
"f.11.l3":"Archived originals outside regular retrieval scan (scan = project notes + active logs + reflections + user-level)","f.11.l4":"Distilled points ride along with the notes, always injected",
|
|
1555
|
-
"f.11.l5":"memory_consolidate: AI divergent consolidation (periodic elevation)",
|
|
1556
|
-
"f.11.art":"LIFECYCLE",
|
|
1557
|
-
"f.12.kicker":"3.12 · Engineering core (trust by design)","f.12.t":"Restraint as a design choice",
|
|
1558
|
-
"f.12.p":"These aren't \"features\" — they're engineering promises made before you even start using it. Less \"fast things\", more \"things that last\".",
|
|
1559
|
-
"f.12.l1":"Zero runtime dependencies (Node built-ins only)","f.12.l2":"Prefix-cache friendly: byte-stable prompts",
|
|
1560
|
-
"f.12.l3":"Rate-limited AI: auto-consolidation ≤8×/day with cooldown","f.12.l4":"Centralized storage: ~/.dsh/memory/workspaces/",
|
|
1561
|
-
"f.12.l5":"Optional Python sidecar (BGE-M3 int8, falls back to lexical on failure)",
|
|
1562
|
-
"f.12.art":"ENGINEERING",
|
|
1563
|
-
"g.kicker":"UI gallery","g.title":"Seven real screenshots","g.sub":"From welcome tour to recall review — every screenshot is a real running frame.",
|
|
1564
|
-
"g.1.t":"Memory panel · Overview","g.1.s":"Away greeting + AI period summaries",
|
|
1565
|
-
"g.2.t":"Memory Hub","g.2.s":"Three stores + skill promotion approvals",
|
|
1566
|
-
"g.3.t":"Recall review","g.3.s":"Grade every activation decision (A/P/S/H/E)",
|
|
1567
|
-
"g.4.t":"Welcome tour · entry","g.4.s":"Liquid-glass app icon + steps",
|
|
1568
|
-
"g.5.t":"Welcome tour · switches","g.5.s":"Flip every feature right in the tour",
|
|
1569
|
-
"g.6.t":"External memory scan","g.6.s":"Inline scan + tick-per-source",
|
|
1570
|
-
"g.7.t":"Engine detection","g.7.s":"Three-tier semantic engine inline install",
|
|
1571
|
-
"q.kicker":"Quick start","q.title":"Three steps, one command","q.sub":"Prerequisite: install DeepSeek Harness and start dsh web at least once.",
|
|
1572
|
-
"q.1.t":"Install package","q.1.p":"In the profile directory (~/.dsh/profiles/web):","q.1.alt":"No pnpm? npm install @a9i5k4/dsh-auto-memory works the same.",
|
|
1573
|
-
"q.2.t":"Register in profile","q.2.p":"Edit package.json in the same directory and append to the dsh.profile.bundles array:",
|
|
1574
|
-
"q.3.t":"Restart to activate","q.3.p":"Restart dsh web — the 「Memory」entry appears in the sidebar; opening it triggers the welcome tour.",
|
|
1575
|
-
"q.4.t":"Updating","q.4.p":"Settings → Auto Memory's \"Check for updates\" button compares your version with npm and one-click updates; or:",
|
|
1576
|
-
"q.ai.tag":"AI era","q.ai.t":"Let the AI install it for you","q.ai.p":"Copy this to the AI assistant you're already using:","q.ai.sys":"System requirements: dsh web running is enough; Node built-ins cover everything. The Python sidecar is optional (for BGE-M3 advanced semantic tier; auto-falls back to lexical on failure).",
|
|
1577
|
-
"c.kicker":"Community","c.title":"Thanks to these two","c.sub":"dsh-auto-memory isn't \"a one-person project\" — these two are the real collaborators who shaped the product.",
|
|
1578
|
-
"c.1.d":"Panel readability fix for DSH Desktop enhanced mode (transparent / Mica materials) + entry-button anti-occlusion & outside-click/Esc close.",
|
|
1579
|
-
"c.2.d":"Unattended / batch workflow hardening feedback that directly drove the welcome tour and per-feature switches.",
|
|
1580
|
-
"c.l1":"GitHub","c.l2":"npm","c.l3":"License: BSD-3-Clause",
|
|
1581
|
-
"c.foot":"Issues and PRs welcome — even fixing a typo or rewording a sentence counts as participation.",
|
|
1582
|
-
"ft.name":"dsh-auto-memory","ft.privacy":"Memories stay on your machine","ft.gh":"GitHub","ft.npm":"npm",
|
|
1583
|
-
"ftc.label":"CREDITS","ftc.owner":"Aik358 · product/architecture","ftc.zcode":"ZCode (GLM · Z.ai) · engineering & papers","ftc.k3":"Kimi K3 · frontend","ftc.note":"Human-machine collaboration · AI-credited, human-reviewed"
|
|
1584
|
-
}
|
|
1585
|
-
};
|
|
766
|
+
/* ══════ i18n 字典 ══════ */
|
|
767
|
+
const i18n = {
|
|
768
|
+
zh: {
|
|
769
|
+
'nav.about':'是什么','nav.features':'能力','nav.demo':'实机演示','nav.architecture':'分层','nav.install':'安装','nav.roadmap':'历程','nav.faq':'问答',
|
|
770
|
+
'hero.badge':'v3.1.4 · 无问自忆 · 2026-09-22',
|
|
771
|
+
'hero.title1':'无问自忆','hero.title2':'记忆不断线',
|
|
772
|
+
'hero.subtitle':'她不是数据库,是一个会主动想起你的同事。跨窗口、跨会话、跨工具 —— 记忆长在你自己的机器上。',
|
|
773
|
+
'hero.subtitle2':'宿主侧主动联想中间件:持续观察对话情境,双轨检索,在你开口之前把该想起的送进下一拍。零运行时依赖,BSD-3-Clause。',
|
|
774
|
+
'hero.cta1':'安装','hero.cta2':'GitHub','hero.cta3':'看实机演示 →',
|
|
775
|
+
'hero.stat1':'模型工具','hero.stat2':'R@5 召回 · BGE-M3','hero.stat3':'词法保底',
|
|
776
|
+
'hero.imgCap':'她记得,不必吩咐','hero.scroll':'向下',
|
|
777
|
+
'about.kicker':'是什么',
|
|
778
|
+
'about.title':'市面上的记忆方案,<br><span class="gradient-text">都要求模型「记得去查」。</span>',
|
|
779
|
+
'about.lead':'忘了调,记忆就等于不存在 —— 这是所有「工具式记忆」的结构性缺陷。dsh-auto-memory 换了一条路:把记忆放在宿主侧,让她持续观察、主动联想、在模型开口之前把该想起的送进下一拍。JS 权威层做最终仲裁,AI 只在边界内干活。',
|
|
780
|
+
'about.card1.title':'主动,不靠调用','about.card1.body':'语义模型在对话中途判断两件事:此刻该不该想起、该想起哪一条。相关记忆经固定边界注入下一轮 —— 从不依赖模型「记得去查」。',
|
|
781
|
+
'about.card2.title':'记忆是你自己的','about.card2.body':'全部写在本机磁盘,每条都带证据链:哪条消息、哪个工具、哪次深夜反思。可审计、可编辑、可删除 —— 一句话就能让她忘。',
|
|
782
|
+
'about.card3.title':'前缀缓存友好','about.card3.body':'注入点在提示词里的字节位置固定不变,缓存持续命中 —— 你不需要为「记忆」付两次 token 的钱。这是设计约束,不是事后优化。',
|
|
783
|
+
'about.card4.title':'两套可互换的语义引擎','about.card4.body':'JS 端内置 e5-small(~130MB,装上就能用)与 Python 端 BGE-M3(563MB,发烧友进阶档)—— 两者相对独立、可互相替换,永远不互相绑架。',
|
|
784
|
+
'features.kicker':'十二个能力',
|
|
785
|
+
'features.title':'四件心血撑起脊柱,<br><span class="gradient-text">其余八件围着长。</span>',
|
|
786
|
+
'features.subtitle':'会记事会问候 / 涌现式主动联想 / 技能固化 / 上下文交接 —— 每一件都可独立开关,每一次想起都交得出证据。',
|
|
787
|
+
'features.f1.title':'主动联想','features.f1.body':'不是「记得去查」,是边做边想起。宿主持续观察,语义模型实时判定,记忆经固定边界走进下一拍。',
|
|
788
|
+
'features.f2.title':'三级检索算力','features.f2.body':'词法 0GB 保底(永远可用)→ 内置 e5-small ~130MB → Python BGE-M3 int8 进阶。失败自动逐级回退。',
|
|
789
|
+
'features.f3.title':'技能固化','features.f3.body':'像骑自行车 —— 不用再想怎么骑。工作流凝成技能,下次相似场景清单自己挂上来,无人提醒。',
|
|
790
|
+
'features.f4.title':'交接而非压缩','features.f4.body':'上下文满了不烧整本书换一句话,而是写四段式交接账本:状态、目标、死路与原因、进度与下一步。',
|
|
791
|
+
'features.f5.title':'外部记忆继承','features.f5.body':'WorkBuddy / CodeBuddy / Claude Code / Codex 的记忆会被扫描进来 —— 换工具不用换记忆。纯链接模式,不抄内容。',
|
|
792
|
+
'features.f6.title':'定时问候','features.f6.body':'早上、下午、深夜 —— 你回来时她用合适的语气打招呼。不是通知铃,是记得你的人说的话。',
|
|
793
|
+
'features.f7.title':'无人值守','features.f7.body':'整夜安静跑:零寒暄、零打扰、零汇报。只在该想起时想起,该交接时交接。早上回来,工作已经往前走了。',
|
|
794
|
+
'features.f8.title':'会话隔离','features.f8.body':'同时开几个工作区,各记各的、各想各的。点进一个绝不打扰正在跑的那个 —— 并发 A/B 的 cwd、游标、待办零串线。',
|
|
795
|
+
'features.f9.title':'激活观测台','features.f9.body':'每一次 suppress / prefetch / activate / drop / delivery 都可查:触发上下文、车道、分数、候选 id、尾注摘要。决策可打分复核。',
|
|
796
|
+
'features.f10.title':'记忆中枢','features.f10.body':'三店持久化 + 治理式写回:事实层、程序层、日志层分开管,每条都能追溯来源、置顶保活、按需遗忘。',
|
|
797
|
+
'features.f11.title':'欢迎向导','features.f11.body':'每个功能、当场看懂、当场开关。十二个能力逐个演示,升级后自动播放一次 —— 不是弹窗广告,是开关的家。',
|
|
798
|
+
'features.f12.title':'零运行时依赖','features.f12.body':'JS 记忆核心只用 Node 内置模块。装完即用,不拖一个第三方包进你的进程 —— BSD-3-Clause,代码全在你自己机器上。',
|
|
799
|
+
'demo.kicker':'实机演示',
|
|
800
|
+
'demo.title':'三件事,<br><span class="gradient-text">现在就能试。</span>',
|
|
801
|
+
'demo.subtitle':'召回、决策、固化 —— 这是她每轮对话都在做的三件事。参数与数字取自真实实测(BGE-M3 int8 · R@5 0.925 · canary delivered=3/seen=24)。',
|
|
802
|
+
'demo.tab1':'主动召回','demo.tab2':'两车道决策','demo.tab3':'技能固化','demo.clear':'清空',
|
|
803
|
+
'demo.recall.title':'她说一句话,她开始回想',
|
|
804
|
+
'demo.recall.desc':'选一句对话,看她如何从三层语料里捞出候选、打分、挑出唯一该注入的那条。分数是真实的双轨融合结果(词法 0.3 + 向量 0.7)。',
|
|
805
|
+
'demo.recall.queryLabel':'当前对话','demo.recall.run':'开始召回','demo.recall.cand':'候选','demo.recall.top':'最高分','demo.recall.time':'耗时',
|
|
806
|
+
'demo.gate.title':'该不该打断你?',
|
|
807
|
+
'demo.gate.desc':'召回之后还有一道闸:分数够不够、会不会是回声、要不要打断。调阈值看两车道如何分流 —— canary 显式唤起,shadow 只记录不注入。',
|
|
808
|
+
'demo.gate.thresh':'激活阈值','demo.gate.echo':'回声否决','demo.gate.on':'开','demo.gate.off':'关',
|
|
809
|
+
'demo.skill.title':'从看到到会做',
|
|
810
|
+
'demo.skill.desc':'看过你几次纠正、同类事做过几遍,工作流就凝成技能。四级晋升,每一步都有跨会话证据;90 天未用自动归档,可置顶保活。',
|
|
811
|
+
'demo.skill.run':'观察一次','demo.skill.obs':'观测次数','demo.skill.stage':'当前阶段',
|
|
812
|
+
'arch.kicker':'运行时分层',
|
|
813
|
+
'arch.title':'语义层决定想起什么,<br><span class="gradient-text">权威层决定是否注入。</span>',
|
|
814
|
+
'arch.lead':'JS 记忆核心持有全部权威:身份、范围、版本、TTL、预算、风险。Python 语义侧车只负责「像不像」,它不创建证据,也不直接注入 —— 这是整套架构最硬的一条边界。',
|
|
815
|
+
'arch.m6.title':'激活收件箱 · 投递闭环','arch.m6.body':'硬校验 → offer → claim → 参考尾注渲染 → delivered/seen 证据落盘。每次投递都留下可回查的痕迹。',
|
|
816
|
+
'arch.m5.title':'授权上下文 + 证据桥','arch.m5.body':'信封授权范围校验、coverage 检查、cite/correction 证据、stale 拒绝。只用 Null/Fake sink,从不启动 Python。',
|
|
817
|
+
'arch.m4.title':'语料快照 + 影子检索','arch.m4.body':'六原因 fail-closed 快照、冻结的策略权重与滞回、CJK 2-gram + 507 停用词的 BM25。候选只审计,绝不注入。',
|
|
818
|
+
'arch.m3.title':'锚定与迁移','arch.m3.body':'冲突 fail-closed、确定性迁移计划、原子写。31 个真实文件 / 176 条记录完成迁移,备份可回滚。',
|
|
819
|
+
'arch.m2.title':'事件账本 + 分型切片','arch.m2.body':'user / tool_call / tool_result / assistant 分型,稳定原生坐标生成 id 与 digest。关闭态零留存,敏感内容零残留。',
|
|
820
|
+
'arch.m1.title':'会话隔离','arch.m1.body':'每会话独立的锁、冷却、队列。并发两个工作区的 cwd、segment、游标、待办互不串线。',
|
|
821
|
+
'arch.py.title':'Python 语义侧车 · 可选 · 懒启动','arch.py.body':'563MB 进阶档,设置页一键安装。R@5 0.925(与 fp32 差 0.000,快 6×)。它与 JS 内置档是两套可互换的引擎 —— 互不联动、互不依赖。',
|
|
822
|
+
'arch.legend1':'live verified 已实现并实机验证','arch.legend2':'tested 已测试','arch.legend3':'queued 排队',
|
|
823
|
+
'install.kicker':'安装','install.title':'两步装好,<br><span class="gradient-text">向导自己走出来。</span>',
|
|
824
|
+
'install.subtitle':'Windows / macOS / Linux 全平台。装完重启 DSH,欢迎向导自动播放:十二个能力逐个演示、逐个开关。',
|
|
825
|
+
'install.step1.title':'1 · 安装插件','install.step1.desc':'在 DSH profile 目录里装包:',
|
|
826
|
+
'install.step2.title':'2 · 重启 DSH','install.step2.desc':'重启 dsh web 后欢迎向导自动走出。已有用户升级后自动播放一次:',
|
|
827
|
+
'install.copy':'复制','install.req.h':'要求','install.req1':'DSH 0.1.6-alpha 及以上','install.req2':'JS 内置 e5-small ~130MB 首启自动下载','install.req3':'Python BGE-M3 563MB · 设置页一键装',
|
|
828
|
+
'install.ai.title':'(推荐)给 AI 一段提示词','install.ai.desc':'把下面这段贴给你的 AI,她会自己读懂怎么用这个插件:',
|
|
829
|
+
'roadmap.kicker':'版本历程','roadmap.title':'从 v0.1.30<br><span class="gradient-text">到 v3.1.4。</span>',
|
|
830
|
+
'roadmap.subtitle':'七个版本条目,每一步都留下了可回查的 CHANGELOG 与守卫断言。',
|
|
831
|
+
'roadmap.v314.title':'当前版本 · 记忆中枢治理','roadmap.v314.body':'三店持久化 + 治理式写回 + 迁移搬包三步向导。全量回归 173/173 绿,tarball 256 文件 / 17.7MB。',
|
|
832
|
+
'roadmap.v300.title':'Fable 大版本 · 技能固化','roadmap.v300.body':'技能四级晋升、90 天归档、激活观测台、无人值守模式 —— 从「记事本」长成「同事」。',
|
|
833
|
+
'roadmap.v0130.title':'欢迎向导 + 双语义引擎','roadmap.v0130.body':'每个功能、当场看懂、当场开关;所有用户升级后自动播放一次。JS 与 Python 两套语义引擎解耦成可互换形态。',
|
|
834
|
+
'roadmap.early':'早期','roadmap.v01.title':'她学会了记事与问候','roadmap.v01.body':'最早的两个能力:每轮结束自己记下值得留的;你隔一段时间回来,她按时段用合适的语气打招呼。人格从这里定下。',
|
|
835
|
+
'roadmap.next':'排队中','roadmap.v32.title':'存储治理(M10)','roadmap.v32.body':'删除级联撤销、语料健康扫描、管理界面。底座(原子事务 / 保留策略 / 30 天蒸馏)已就绪。',
|
|
836
|
+
'gallery.kicker':'界面','gallery.title':'七张实机截图,<br><span class="gradient-text">不是示意图。</span>',
|
|
837
|
+
'gallery.subtitle':'面板 / 设置 / 记忆中枢 / 激活观测台 / 欢迎向导 / 无人值守 / 外部继承 —— 全部来自实机。',
|
|
838
|
+
'gallery.g1.title':'记忆中枢','gallery.g2.title':'设置页','gallery.g3.title':'激活观测台','gallery.g4.title':'欢迎向导','gallery.g5.title':'无人值守','gallery.g6.title':'外部记忆继承',
|
|
839
|
+
'gallery.capKicker':'宣传套图 · 七幕','gallery.cap':'七幕',
|
|
840
|
+
'compare.kicker':'对比','compare.title':'它在这条线上的<br><span class="gradient-text">位置。</span>',
|
|
841
|
+
'compare.capability':'能力','compare.col1':'工具式记忆<br><span class="text-[10px] font-normal" style="color:var(--muted)">需要在提示里调用</span>','compare.col2':'内置上下文<br><span class="text-[10px] font-normal" style="color:var(--muted)">厂商实验特性</span>','compare.col3':'dsh-auto-memory<br><span class="text-[10px] font-normal">宿主中间件</span>',
|
|
842
|
+
'compare.r1':'不需模型主动调用','compare.r2':'跨窗口 / 跨会话','compare.r3':'跨工具记忆继承','compare.r4':'前缀缓存字节稳定','compare.r5':'零运行时依赖','compare.r6':'每次召回带证据链','compare.r7':'技能固化(程序性记忆)','compare.r8':'三级算力可切换','compare.r9':'记忆全在本机磁盘','compare.r10':'开源可审计',
|
|
843
|
+
'compare.legend1':'完整支持','compare.legend2':'部分 / 需变通','compare.legend3':'不支持',
|
|
844
|
+
'faq.kicker':'常见问题','faq.title':'你大概想问<br><span class="gradient-text">这些。</span>',
|
|
845
|
+
'faq.q1':'她会偷我东西吗?数据存在哪?','faq.a1':'全部写在你自己机器的磁盘上:用户级记忆在 ~/.dsh/memory/MEMORY.md,项目记忆与日记在工作区的 .dsh-memory/ 下。没有云端、没有账号、没有遥测。可审计、可编辑、可删除。',
|
|
846
|
+
'faq.q2':'不装语义模型能用吗?','faq.a2':'能。词法档 0GB 永远可用(BM25 + CJK 2-gram),装完即用。内置 e5-small ~130MB 会在首启自动下载,检索质量更高。Python BGE-M3 563MB 是进阶档,设置页一键装。',
|
|
847
|
+
'faq.q3':'「主动」会不会很吵、一直打断我?','faq.a3':'不会。召回之后还有一道闸:分数阈值、回声否决、连贯性检查、硬门禁。默认策略偏保守,宁可少说话。canary 车道才显式唤起,shadow 车道只记录不注入。实测 canary 一跑下来 delivered=3 / seen=24。',
|
|
848
|
+
'faq.q4':'会不会拖慢我的对话?多花 token?','faq.a4':'注入点在提示词里的字节位置固定不变,前缀缓存持续命中 —— 不会为记忆付两次钱。词法档查询往返在毫秒级;内置向量档实测 3.8ms/次。检索在主流程之外,不阻塞你。',
|
|
849
|
+
'faq.q5':'她记错了怎么办?','faq.a5':'每条记忆都带证据链:哪条消息、哪个工具、哪次反思。激活观测台可以逐次复核打分(A/P/S/H/E),不满意的可以直接删,或者改 policy 让它下次别这么判断。',
|
|
850
|
+
'faq.q6':'JS 语义档和 Python 语义档要同时装吗?','faq.a6':'不需要,它们是两套相对独立、可互相替换的引擎。默认形态就是 JS 内置档(普通用户装的就是它);Python 档是发烧友主动在设置里安装的进阶项。开一个不会顺带开另一个,一个不在也不影响另一个。',
|
|
851
|
+
'faq.q7':'能接我其他 AI 的记忆吗?','faq.a7':'能。WorkBuddy / CodeBuddy / Claude Code / Codex 的记忆会被扫描进来,按来源分组管理、可逐源启停。采用纯链接模式接入:只存路径指针,不抄内容 —— 对方内容变了不会过期。',
|
|
852
|
+
'faq.q8':'开源协议与贡献方式?','faq.a8':'BSD-3-Clause,代码与文档全部公开在 GitHub。提 issue、交 PR 都欢迎;下一个里程碑是 M10 存储治理(删除级联撤销 + 语料健康扫描 + 管理界面)。',
|
|
853
|
+
'cta.kicker':'一起养大','cta.title':'记忆是你的,<br><span class="gradient-text">代码也是。</span>',
|
|
854
|
+
'cta.subtitle':'开源、可审计、可删除。装一个,看她还记得什么。','cta.button1':'GitHub','cta.button2':'npm →','cta.button3':'QQ 群 →',
|
|
855
|
+
'footer.desc':'DSH 插件:宿主侧主动联想记忆中间件。她记得,不必吩咐 —— 记忆长在你自己的机器上。BSD-3-Clause。',
|
|
856
|
+
'footer.project':'项目','footer.resources':'资源','footer.style':'叙述风格指南','footer.rights':'BSD-3-Clause','footer.built':'记忆在你自己的机器上 · 可审计 · 可删除'
|
|
857
|
+
},
|
|
858
|
+
en: {
|
|
859
|
+
'nav.about':'What','nav.features':'Features','nav.demo':'Live Demos','nav.architecture':'Layers','nav.install':'Install','nav.roadmap':'History','nav.faq':'FAQ',
|
|
860
|
+
'hero.badge':'v3.1.4 · She remembers, unbidden · 2026-09-22',
|
|
861
|
+
'hero.title1':'She remembers','hero.title2':'unbidden.',
|
|
862
|
+
'hero.subtitle':'Not a database — a colleague who thinks of you first. Across windows, sessions and tools. Your memory lives on your own disk.',
|
|
863
|
+
'hero.subtitle2':'Host-side proactive recall middleware: it watches the conversation, searches two channels, and delivers what you should remember before the model speaks. Zero runtime deps, BSD-3-Clause.',
|
|
864
|
+
'hero.cta1':'Install','hero.cta2':'GitHub','hero.cta3':'See it run →',
|
|
865
|
+
'hero.stat1':'model tools','hero.stat2':'R@5 recall · BGE-M3','hero.stat3':'lexical floor',
|
|
866
|
+
'hero.imgCap':'She remembers, unbidden','hero.scroll':'Scroll',
|
|
867
|
+
'about.kicker':'What it is',
|
|
868
|
+
'about.title':'Every memory system out there<br><span class="gradient-text">makes the model remember to look.</span>',
|
|
869
|
+
'about.lead':'Forget to call the tool, and the memory might as well not exist — that is the structural flaw of every "tool-style memory". dsh-auto-memory takes the other road: memory on the host side, watching continuously, recalling proactively, delivering into the next turn before the model even opens its mouth. The JS authority layer has the final say; the AI only works inside the boundary.',
|
|
870
|
+
'about.card1.title':'Proactive, not called','about.card1.body':'Mid-conversation the semantic model judges two things: should anything surface now, and which memory it should be. It arrives through a fixed boundary — never dependent on the model remembering to look.',
|
|
871
|
+
'about.card2.title':'The memory is yours','about.card2.body':'Everything stays on your own disk, every entry carries an evidence chain: which message, which tool, which late-night reflection. Auditable, editable, deletable — one sentence and she forgets.',
|
|
872
|
+
'about.card3.title':'Prefix-cache friendly','about.card3.body':'The injection point sits at a byte-stable offset in the prompt, so the cache keeps hitting — you never pay twice for memory. A design constraint, not an afterthought.',
|
|
873
|
+
'about.card4.title':'Two swappable semantic engines','about.card4.body':'Built-in e5-small on the JS side (~130MB, works out of the box) and BGE-M3 on the Python side (563MB, the enthusiast tier) — independent, interchangeable, never holding each other hostage.',
|
|
874
|
+
'features.kicker':'Nine capabilities',
|
|
875
|
+
'features.title':'Four features carry the spine.<br><span class="gradient-text">The rest grow around it.</span>',
|
|
876
|
+
'features.subtitle':'Notes and greetings / emergent proactive recall / skill crystallization / context handoff — each with its own switch, each recall with evidence.',
|
|
877
|
+
'features.f1.title':'Proactive recall','features.f1.body':'Not "remember to look" but thinking of it while you work. The host watches, the model judges, the memory walks in through a fixed boundary.',
|
|
878
|
+
'features.f2.title':'Three compute tiers','features.f2.body':'Lexical 0GB floor (always on) → built-in e5-small ~130MB → Python BGE-M3 int8. Failures fall back tier by tier.',
|
|
879
|
+
'features.f3.title':'Skill crystallization','features.f3.body':'Like riding a bicycle — you stop thinking about how. Workflows condense into skills; next time the checklist attaches itself, nobody reminding.',
|
|
880
|
+
'features.f4.title':'Handoff, not compression','features.f4.body':'When context fills, she does not burn the whole book for one line. She writes a four-part ledger: state, goals, dead ends and why, progress and next step.',
|
|
881
|
+
'features.f5.title':'External memory inheritance','features.f5.body':'Memories from WorkBuddy / CodeBuddy / Claude Code / Codex get scanned in — switch tools without losing your memory. Link-only mode, nothing copied.',
|
|
882
|
+
'features.f6.title':'Scheduled greetings','features.f6.body':'Morning, afternoon, late night — when you come back she greets you in a fitting tone. Not a notification chime; what someone who remembers you says.',
|
|
883
|
+
'features.f7.title':'Unattended mode','features.f7.body':'Runs all night quietly: no small talk, no interruptions, no reports. She recalls when it matters and hands off when it is time. Morning comes, the work has moved.',
|
|
884
|
+
'features.f8.title':'Session isolation','features.f8.body':'Open several workspaces at once — each keeps its own memory. Clicking into one never disturbs the one that is running. Concurrent A/B: zero cross-talk in cwd, cursors, pending work.',
|
|
885
|
+
'features.f9.title':'Activation console','features.f9.body':'Every suppress / prefetch / activate / drop / delivery is inspectable: trigger context, lane, score, candidate id, tail digest. Decisions can be re-scored.',
|
|
886
|
+
'features.f10.title':'Memory hub','features.f10.body':'Three stores, governed write-back: facts, procedures and logs kept apart. Each entry traces to its source, can be pinned, or forgotten on demand.',
|
|
887
|
+
'features.f11.title':'Welcome tour','features.f11.body':'Every feature explained and toggled on the spot. Nine capabilities demonstrated one by one, played once after an upgrade — not an ad, the home of the switches.',
|
|
888
|
+
'features.f12.title':'Zero runtime deps','features.f12.body':'The JS memory core uses only Node built-ins. Install and go, no third-party package dragged into your process — BSD-3-Clause, code on your own machine.',
|
|
889
|
+
'demo.kicker':'Live demos',
|
|
890
|
+
'demo.title':'Three things you can<br><span class="gradient-text">try right now.</span>',
|
|
891
|
+
'demo.subtitle':'Recall, gating, crystallization — what she does every single turn. Numbers come from real measurements (BGE-M3 int8 · R@5 0.925 · canary delivered=3/seen=24).',
|
|
892
|
+
'demo.tab1':'Proactive recall','demo.tab2':'Two-lane gating','demo.tab3':'Skill growth','demo.clear':'Clear',
|
|
893
|
+
'demo.recall.title':'You say one line, she starts remembering',
|
|
894
|
+
'demo.recall.desc':'Pick a line of dialogue and watch her pull candidates from three corpora, score them, and choose the single one worth injecting. Scores are real hybrid fusion (lexical 0.3 + vector 0.7).',
|
|
895
|
+
'demo.recall.queryLabel':'Current dialogue','demo.recall.run':'Run recall','demo.recall.cand':'Candidates','demo.recall.top':'Top score','demo.recall.time':'Latency',
|
|
896
|
+
'demo.gate.title':'Should she interrupt you?',
|
|
897
|
+
'demo.gate.desc':'Recall is followed by a gate: is the score high enough, is it an echo, should it interrupt at all. Move the threshold to see the two lanes split — canary activates explicitly, shadow only records.',
|
|
898
|
+
'demo.gate.thresh':'Activation threshold','demo.gate.echo':'Echo veto','demo.gate.on':'on','demo.gate.off':'off',
|
|
899
|
+
'demo.skill.title':'From watching to knowing',
|
|
900
|
+
'demo.skill.desc':'After a few corrections, or the same job done a few times, a workflow condenses into a skill. Four promotion stages, each with cross-session evidence; 90 days unused and it archives, pinnable to stay alive.',
|
|
901
|
+
'demo.skill.run':'Observe once','demo.skill.obs':'Observations','demo.skill.stage':'Stage',
|
|
902
|
+
'arch.kicker':'Runtime layers',
|
|
903
|
+
'arch.title':'The semantic layer decides what to recall.<br><span class="gradient-text">The authority layer decides whether to inject.</span>',
|
|
904
|
+
'arch.lead':'The JS memory core holds all authority: identity, scope, version, TTL, budget, risk. The Python sidecar only answers "is it alike" — it creates no evidence and never injects directly. That is the hardest boundary in the architecture.',
|
|
905
|
+
'arch.m6.title':'Activation inbox · delivery loop','arch.m6.body':'Hard validation → offer → claim → reference-tail rendering → delivered/seen evidence. Every delivery leaves a trace you can inspect.',
|
|
906
|
+
'arch.m5.title':'Authorized context + evidence bridge','arch.m5.body':'Envelope scope checks, coverage validation, cite/correction evidence, stale rejection. Runs on Null/Fake sinks only, never starts Python.',
|
|
907
|
+
'arch.m4.title':'Corpus snapshot + shadow retrieval','arch.m4.body':'Six fail-closed snapshot causes, frozen policy weights and hysteresis, BM25 with CJK 2-grams and 507 stopwords. Candidates are audited, never injected.',
|
|
908
|
+
'arch.m3.title':'Anchoring and migration','arch.m3.body':'Fail-closed conflict handling, deterministic migration plans, atomic writes. 31 real files / 176 records migrated with rollback backups.',
|
|
909
|
+
'arch.m2.title':'Event ledger + typed slicing','arch.m2.body':'user / tool_call / tool_result / assistant typed into stable native coordinates for ids and digests. Zero retention when off, zero sensitive residue.',
|
|
910
|
+
'arch.m1.title':'Session isolation','arch.m1.body':'Per-session locks, cooldowns and queues. Two concurrent workspaces share nothing — cwd, segments, cursors, pending tasks.',
|
|
911
|
+
'arch.py.title':'Python semantic sidecar · optional · lazy spawn','arch.py.body':'The 563MB advanced tier, one click in settings. R@5 0.925 (Δ0.000 vs fp32, 6× faster). It and the built-in JS tier are two interchangeable engines — no coupling, no dependency.',
|
|
912
|
+
'arch.legend1':'live verified','arch.legend2':'tested','arch.legend3':'queued',
|
|
913
|
+
'install.kicker':'Install','install.title':'Two steps, and the tour<br><span class="gradient-text">walks out on its own.</span>',
|
|
914
|
+
'install.subtitle':'Windows / macOS / Linux. Restart DSH after installing and the welcome tour plays automatically: nine capabilities, each explained and toggled.',
|
|
915
|
+
'install.step1.title':'1 · Install the plugin','install.step1.desc':'Inside your DSH profile directory:',
|
|
916
|
+
'install.step2.title':'2 · Restart DSH','install.step2.desc':'The welcome tour walks out after restart. Existing users get it played once on upgrade:',
|
|
917
|
+
'install.copy':'Copy','install.req.h':'Requirement','install.req1':'DSH 0.1.6-alpha or newer','install.req2':'Built-in e5-small ~130MB downloads on first run','install.req3':'Python BGE-M3 563MB · one click in settings',
|
|
918
|
+
'install.ai.title':'(Recommended) Give your AI a prompt','install.ai.desc':'Paste this to your AI and she will understand how to use the plugin:',
|
|
919
|
+
'roadmap.kicker':'Version history','roadmap.title':'From v0.1.30<br><span class="gradient-text">to v3.1.4.</span>',
|
|
920
|
+
'roadmap.subtitle':'Seven release entries, each leaving an auditable CHANGELOG and guard assertions behind.',
|
|
921
|
+
'roadmap.v314.title':'Current · memory hub governance','roadmap.v314.body':'Three-store persistence, governed write-back, and a three-step migration wizard. Full suite 173/173 green, tarball 256 files / 17.7MB.',
|
|
922
|
+
'roadmap.v300.title':'Fable · skill crystallization','roadmap.v300.body':'Four-stage skill promotion, 90-day archiving, activation console, unattended mode — growing from notebook into colleague.',
|
|
923
|
+
'roadmap.v0130.title':'Welcome tour + dual semantic engines','roadmap.v0130.body':'Every feature explained and toggled on the spot, auto-played once for all users after upgrade. JS and Python semantic engines decoupled into swappable forms.',
|
|
924
|
+
'roadmap.early':'early','roadmap.v01.title':'She learned to take notes and greet','roadmap.v01.body':'The first two abilities: after every conversation she wrote down what was worth keeping; when you came back she greeted you in a fitting tone. Her character was set here.',
|
|
925
|
+
'roadmap.next':'queued','roadmap.v32.title':'Storage governance (M10)','roadmap.v32.body':'Cascade deletes with revoke, corpus health scan, management UI. The foundation (atomic transactions, retention, 30-day distillation) is already in place.',
|
|
926
|
+
'gallery.kicker':'Interface','gallery.title':'Seven real screenshots,<br><span class="gradient-text">not mockups.</span>',
|
|
927
|
+
'gallery.subtitle':'Hub / settings / memory center / activation console / welcome tour / unattended / external inheritance — all captured from the running plugin.',
|
|
928
|
+
'gallery.g1.title':'Memory hub','gallery.g2.title':'Settings','gallery.g3.title':'Activation console','gallery.g4.title':'Welcome tour','gallery.g5.title':'Unattended','gallery.g6.title':'External memory',
|
|
929
|
+
'gallery.capKicker':'Promo gallery · seven frames','gallery.cap':'seven frames',
|
|
930
|
+
'compare.kicker':'Comparison','compare.title':'Where it sits<br><span class="gradient-text">on this line.</span>',
|
|
931
|
+
'compare.capability':'Capability','compare.col1':'Tool-style memory<br><span class="text-[10px] font-normal" style="color:var(--muted)">must be called in the prompt</span>','compare.col2':'Built-in context<br><span class="text-[10px] font-normal" style="color:var(--muted)">vendor experimental</span>','compare.col3':'dsh-auto-memory<br><span class="text-[10px] font-normal">host middleware</span>',
|
|
932
|
+
'compare.r1':'No model-side call required','compare.r2':'Across windows / sessions','compare.r3':'Across AI tools','compare.r4':'Byte-stable prefix cache','compare.r5':'Zero runtime dependencies','compare.r6':'Evidence chain per recall','compare.r7':'Skill crystallization','compare.r8':'Three switchable tiers','compare.r9':'Memory stays on your disk','compare.r10':'Open source, auditable',
|
|
933
|
+
'compare.legend1':'Full support','compare.legend2':'Partial / workaround','compare.legend3':'Not supported',
|
|
934
|
+
'faq.kicker':'FAQ','faq.title':'What you probably<br><span class="gradient-text">want to ask.</span>',
|
|
935
|
+
'faq.q1':'Does she take my data? Where does it live?','faq.a1':'All of it on your own disk: user-level memory in ~/.dsh/memory/MEMORY.md, project memory and logs under .dsh-memory/ in your workspace. No cloud, no account, no telemetry. Auditable, editable, deletable.',
|
|
936
|
+
'faq.q2':'Can I use it without a semantic model?','faq.a2':'Yes. The lexical tier is a 0GB floor that always works (BM25 + CJK 2-grams) — usable the moment you install. Built-in e5-small ~130MB downloads on first run for better quality. Python BGE-M3 563MB is the advanced tier, one click in settings.',
|
|
937
|
+
'faq.q3':'Will "proactive" be noisy and interrupt me?','faq.a3':'No. Recall passes a gate: score threshold, echo veto, completeness check, hard gates. The default policy is conservative — better to stay quiet. Only the canary lane activates explicitly; shadow only records. A real canary run measured delivered=3 / seen=24.',
|
|
938
|
+
'faq.q4':'Will it slow my conversations or cost extra tokens?','faq.a4':'The injection point sits at a byte-stable offset, so prefix cache keeps hitting — you never pay twice for memory. Lexical lookups are millisecond-scale; the built-in vector tier measured 3.8ms per query. Retrieval runs outside the main path.',
|
|
939
|
+
'faq.q5':'What if she remembers something wrong?','faq.a5':'Every memory carries an evidence chain: which message, which tool, which reflection. The activation console lets you re-score each decision (A/P/S/H/E); anything wrong can be deleted outright, or you change the policy so she judges differently.',
|
|
940
|
+
'faq.q6':'Do I need both the JS and Python semantic tiers?','faq.a6':'No — they are two independent, interchangeable engines. The JS built-in tier is the default form (what ordinary users get); the Python tier is an advanced option enthusiasts install from settings. Enabling one never enables the other, and one being absent never blocks the other.',
|
|
941
|
+
'faq.q7':'Can it inherit memory from my other AI tools?','faq.a7':'Yes. Memories from WorkBuddy / CodeBuddy / Claude Code / Codex get scanned in, grouped by source, each toggleable. Link-only mode: it stores path pointers and copies nothing, so upstream changes never go stale.',
|
|
942
|
+
'faq.q8':'License and how to contribute?','faq.a8':'BSD-3-Clause; code and docs are public on GitHub. Issues and PRs welcome. The next milestone is M10 storage governance (cascade deletes with revoke, corpus health scan, management UI).',
|
|
943
|
+
'cta.kicker':'Grow her with us','cta.title':'The memory is yours.<br><span class="gradient-text">So is the code.</span>',
|
|
944
|
+
'cta.subtitle':'Open source, auditable, deletable. Install it and see what she remembers.','cta.button1':'GitHub','cta.button2':'npm →','cta.button3':'QQ group →',
|
|
945
|
+
'footer.desc':'A DSH plugin: host-side proactive recall middleware. She remembers, unbidden — memory lives on your own machine. BSD-3-Clause.',
|
|
946
|
+
'footer.project':'Project','footer.resources':'Resources','footer.style':'Narrative style guide','footer.rights':'BSD-3-Clause','footer.built':'Your memory stays on your machine · auditable · deletable'
|
|
947
|
+
}
|
|
948
|
+
};
|
|
949
|
+
/* ══════ 语言 ══════ */
|
|
950
|
+
function setLang(l){
|
|
951
|
+
document.documentElement.lang = l==='zh' ? 'zh-CN' : 'en';
|
|
952
|
+
document.documentElement.dataset.lang = l;
|
|
953
|
+
document.querySelectorAll('[data-i18n]').forEach(e=>{
|
|
954
|
+
const k = e.getAttribute('data-i18n');
|
|
955
|
+
if (i18n[l][k] !== undefined) e.innerHTML = i18n[l][k];
|
|
956
|
+
});
|
|
957
|
+
document.querySelectorAll('[data-lang-btn]').forEach(b=>b.classList.remove('active'));
|
|
958
|
+
const a = document.getElementById('lang-'+l); if (a) a.classList.add('active');
|
|
959
|
+
try { localStorage.setItem('am-lang', l); } catch(e){}
|
|
960
|
+
}
|
|
961
|
+
document.getElementById('lang-zh').onclick = ()=>setLang('zh');
|
|
962
|
+
document.getElementById('lang-en').onclick = ()=>setLang('en');
|
|
963
|
+
setLang((()=>{ try{ return localStorage.getItem('am-lang'); }catch(e){ return null; } })() || ((navigator.language||'zh').toLowerCase().startsWith('zh') ? 'zh' : 'en'));
|
|
1586
964
|
|
|
1587
|
-
|
|
1588
|
-
|
|
1589
|
-
|
|
1590
|
-
|
|
1591
|
-
|
|
1592
|
-
document.documentElement.setAttribute('data-lang', lang);
|
|
1593
|
-
var nodes = document.querySelectorAll('[data-i18n]');
|
|
1594
|
-
for (var i = 0; i < nodes.length; i++){
|
|
1595
|
-
var n = nodes[i];
|
|
1596
|
-
var k = n.getAttribute('data-i18n');
|
|
1597
|
-
if (dict[k] !== undefined){
|
|
1598
|
-
if (HTML_OK[k]) n.innerHTML = dict[k];
|
|
1599
|
-
else n.textContent = dict[k];
|
|
1600
|
-
}
|
|
1601
|
-
}
|
|
1602
|
-
var zhBtn = document.getElementById('lang-zh');
|
|
1603
|
-
var enBtn = document.getElementById('lang-en');
|
|
1604
|
-
if (lang === 'zh'){ zhBtn.classList.add('on'); enBtn.classList.remove('on'); zhBtn.setAttribute('aria-pressed','true'); enBtn.setAttribute('aria-pressed','false'); }
|
|
1605
|
-
else { enBtn.classList.add('on'); zhBtn.classList.remove('on'); enBtn.setAttribute('aria-pressed','true'); zhBtn.setAttribute('aria-pressed','false'); }
|
|
1606
|
-
try { localStorage.setItem('dsh-landing-pre.lang', lang); } catch (e) {}
|
|
1607
|
-
}
|
|
1608
|
-
document.getElementById('lang-zh').addEventListener('click', function(){ applyLang('zh'); });
|
|
1609
|
-
document.getElementById('lang-en').addEventListener('click', function(){ applyLang('en'); });
|
|
965
|
+
/* ══════ 主题:默认浅色 ══════ */
|
|
966
|
+
const root = document.documentElement;
|
|
967
|
+
function setTheme(t){
|
|
968
|
+
root.setAttribute('data-theme', t);
|
|
969
|
+
/* 太阳/月亮交叉淡出由 CSS 按 data-theme 驱动(icon-swap),此处不再硬切 display */
|
|
1610
970
|
|
|
1611
|
-
|
|
1612
|
-
(
|
|
1613
|
-
|
|
1614
|
-
|
|
1615
|
-
|
|
1616
|
-
|
|
1617
|
-
|
|
1618
|
-
function go(i){
|
|
1619
|
-
cur = Math.max(0, Math.min(frames.length - 1, i));
|
|
1620
|
-
frames[cur].scrollIntoView({ behavior: 'smooth', block: 'nearest', inline: 'start' });
|
|
1621
|
-
dots.forEach(function(d, k){ d.style.background = k === cur ? 'var(--accent)' : 'transparent'; });
|
|
1622
|
-
}
|
|
1623
|
-
document.getElementById('promo-prev').addEventListener('click', function(){ go(cur - 1); });
|
|
1624
|
-
document.getElementById('promo-next').addEventListener('click', function(){ go(cur + 1); });
|
|
1625
|
-
dots.forEach(function(d, k){ d.addEventListener('click', function(e){ e.preventDefault(); go(k); }); });
|
|
1626
|
-
// sync on manual scroll
|
|
1627
|
-
var t;
|
|
1628
|
-
track.addEventListener('scroll', function(){
|
|
1629
|
-
clearTimeout(t);
|
|
1630
|
-
t = setTimeout(function(){
|
|
1631
|
-
var idx = Math.round(track.scrollLeft / track.clientWidth);
|
|
1632
|
-
if (idx !== cur){ cur = idx; dots.forEach(function(d, k){ d.style.background = k === cur ? 'var(--accent)' : 'transparent'; }); }
|
|
1633
|
-
}, 80);
|
|
1634
|
-
});
|
|
1635
|
-
go(0);
|
|
1636
|
-
})();
|
|
971
|
+
const meta = document.querySelector('meta[name="theme-color"]');
|
|
972
|
+
if (meta) meta.setAttribute('content', t==='light' ? '#eef2f7' : '#0a0d14');
|
|
973
|
+
try { localStorage.setItem('am-theme', t); } catch(e){}
|
|
974
|
+
}
|
|
975
|
+
/* 需求:默认浅色。仅在用户显式切换过之后才记住选择 */
|
|
976
|
+
setTheme((()=>{ try{ return localStorage.getItem('am-theme'); }catch(e){ return null; } })() || 'light');
|
|
977
|
+
document.getElementById('theme-toggle').onclick = ()=>setTheme(root.getAttribute('data-theme')==='dark' ? 'light' : 'dark');
|
|
1637
978
|
|
|
1638
|
-
|
|
1639
|
-
|
|
1640
|
-
|
|
1641
|
-
|
|
979
|
+
/* ══════ 移动菜单 ══════ */
|
|
980
|
+
const mt = document.getElementById('menu-toggle'), mm = document.getElementById('mobile-menu');
|
|
981
|
+
mt.onclick = ()=>{ mm.classList.toggle('hidden'); };
|
|
982
|
+
mm.querySelectorAll('a').forEach(a=>a.addEventListener('click',()=>mm.classList.add('hidden')));
|
|
1642
983
|
|
|
1643
|
-
|
|
1644
|
-
|
|
1645
|
-
|
|
1646
|
-
|
|
1647
|
-
|
|
1648
|
-
|
|
1649
|
-
|
|
1650
|
-
if (navigator.clipboard && navigator.clipboard.writeText){
|
|
1651
|
-
navigator.clipboard.writeText(t).catch(function(){});
|
|
1652
|
-
} else {
|
|
1653
|
-
var ta = document.createElement('textarea');
|
|
1654
|
-
ta.value = t; ta.style.position='fixed'; ta.style.opacity='0';
|
|
1655
|
-
document.body.appendChild(ta); ta.select();
|
|
1656
|
-
try { document.execCommand('copy'); } catch (e) {}
|
|
1657
|
-
document.body.removeChild(ta);
|
|
1658
|
-
}
|
|
1659
|
-
}
|
|
1660
|
-
document.querySelectorAll('.copy-btn').forEach(function(btn){
|
|
1661
|
-
btn.addEventListener('click', function(){
|
|
1662
|
-
var t = btn.getAttribute('data-copy');
|
|
1663
|
-
if (t === 'prompt-ai') { t = document.getElementById('prompt-ai').textContent; }
|
|
1664
|
-
copyText(t);
|
|
1665
|
-
flashCopied(btn);
|
|
1666
|
-
});
|
|
984
|
+
/* ══════ 滚动入场 ══════ */
|
|
985
|
+
const ro = new IntersectionObserver(es=>{ es.forEach(x=>{ if(x.isIntersecting){ x.target.classList.add('visible'); ro.unobserve(x.target); } }); },{ threshold:0.1, rootMargin:'0px 0px -50px 0px' });
|
|
986
|
+
document.querySelectorAll('.reveal').forEach(e=>ro.observe(e));
|
|
987
|
+
/* 兜底:内容永远不该因为「观察器没触发」而消失。视口内仍未 visible 的强制放行。 */
|
|
988
|
+
function revealFallback(){
|
|
989
|
+
document.querySelectorAll('.reveal:not(.visible)').forEach(e=>{
|
|
990
|
+
if (e.getBoundingClientRect().top < window.innerHeight) e.classList.add('visible');
|
|
1667
991
|
});
|
|
1668
|
-
|
|
1669
|
-
|
|
1670
|
-
|
|
1671
|
-
|
|
1672
|
-
|
|
1673
|
-
|
|
1674
|
-
|
|
992
|
+
}
|
|
993
|
+
setTimeout(revealFallback, 900);
|
|
994
|
+
window.addEventListener('load', ()=>setTimeout(revealFallback, 300));
|
|
995
|
+
window.addEventListener('scroll', ()=>{ clearTimeout(window.__rfT); window.__rfT = setTimeout(revealFallback, 260); }, { passive:true });
|
|
996
|
+
|
|
997
|
+
/* ══════ 数字滚动 ══════ */
|
|
998
|
+
(function(){
|
|
999
|
+
const el = document.getElementById('stat-tools'); if (!el) return;
|
|
1000
|
+
const target = 17; let cur = 0;
|
|
1001
|
+
const ob = new IntersectionObserver(es=>{ es.forEach(x=>{
|
|
1002
|
+
if (!x.isIntersecting) return;
|
|
1003
|
+
ob.unobserve(el);
|
|
1004
|
+
const step = ()=>{ cur += 1; el.textContent = cur; if (cur < target) setTimeout(step, 60); };
|
|
1005
|
+
step();
|
|
1006
|
+
}); },{ threshold:0.5 });
|
|
1007
|
+
ob.observe(el);
|
|
1008
|
+
})();
|
|
1009
|
+
|
|
1010
|
+
/* ══════ 粒子背景 ══════ */
|
|
1011
|
+
class HeroBG{
|
|
1012
|
+
constructor(c){
|
|
1013
|
+
this.c = c; this.ctx = c.getContext('2d'); this.d = [];
|
|
1014
|
+
this.resize(); window.addEventListener('resize',()=>this.resize());
|
|
1015
|
+
this.init(); this.animate();
|
|
1016
|
+
}
|
|
1017
|
+
resize(){
|
|
1018
|
+
const d = Math.min(devicePixelRatio||1, 2);
|
|
1019
|
+
this.c.width = this.c.offsetWidth*d; this.c.height = this.c.offsetHeight*d;
|
|
1020
|
+
this.ctx.setTransform(1,0,0,1,0,0); this.ctx.scale(d,d);
|
|
1021
|
+
this.w = this.c.offsetWidth; this.h = this.c.offsetHeight;
|
|
1022
|
+
}
|
|
1023
|
+
init(){
|
|
1024
|
+
this.d = [];
|
|
1025
|
+
const n = Math.min(46, Math.floor(this.w/28));
|
|
1026
|
+
for (let i=0;i<n;i++) this.d.push({ x:Math.random()*this.w, y:Math.random()*this.h, vx:(Math.random()-0.5)*0.18, vy:(Math.random()-0.5)*0.18, r:Math.random()*1.3+0.3, a:Math.random()*0.3+0.12, p:Math.random()*6.28 });
|
|
1027
|
+
}
|
|
1028
|
+
animate(){
|
|
1029
|
+
if (this._pause || document.hidden){ requestAnimationFrame(()=>this.animate()); return; }
|
|
1030
|
+
this.ctx.clearRect(0,0,this.w,this.h);
|
|
1031
|
+
const t = Date.now()*0.001;
|
|
1032
|
+
const ac = getComputedStyle(root).getPropertyValue('--accent').trim();
|
|
1033
|
+
let r=37,g=99,b=235;
|
|
1034
|
+
if (ac.startsWith('#') && ac.length===7){ r=parseInt(ac.slice(1,3),16); g=parseInt(ac.slice(3,5),16); b=parseInt(ac.slice(5,7),16); }
|
|
1035
|
+
this.d.forEach(d=>{
|
|
1036
|
+
d.x+=d.vx; d.y+=d.vy;
|
|
1037
|
+
if(d.x<0)d.x=this.w; if(d.x>this.w)d.x=0; if(d.y<0)d.y=this.h; if(d.y>this.h)d.y=0;
|
|
1038
|
+
const p = 0.6+0.4*Math.sin(t*1.5+d.p);
|
|
1039
|
+
this.ctx.beginPath(); this.ctx.arc(d.x,d.y,Math.max(0.1,d.r),0,6.28);
|
|
1040
|
+
this.ctx.fillStyle = `rgba(${r},${g},${b},${d.a*p})`; this.ctx.fill();
|
|
1041
|
+
});
|
|
1042
|
+
for (let i=0;i<this.d.length;i++) for (let j=i+1;j<this.d.length;j++){
|
|
1043
|
+
const dx=this.d[i].x-this.d[j].x, dy=this.d[i].y-this.d[j].y, dist=Math.sqrt(dx*dx+dy*dy);
|
|
1044
|
+
if (dist<110){
|
|
1045
|
+
this.ctx.beginPath(); this.ctx.moveTo(this.d[i].x,this.d[i].y); this.ctx.lineTo(this.d[j].x,this.d[j].y);
|
|
1046
|
+
this.ctx.strokeStyle = `rgba(${r},${g},${b},${(1-dist/110)*0.07})`; this.ctx.lineWidth = 0.5; this.ctx.stroke();
|
|
1047
|
+
}
|
|
1675
1048
|
}
|
|
1049
|
+
requestAnimationFrame(()=>this.animate());
|
|
1050
|
+
}
|
|
1051
|
+
}
|
|
1052
|
+
const heroCanvas = document.getElementById('hero-canvas');
|
|
1053
|
+
if (heroCanvas){
|
|
1054
|
+
window.__heroInst = new HeroBG(heroCanvas);
|
|
1055
|
+
new IntersectionObserver(es=>{ es.forEach(x=>{ window.__heroInst._pause = !x.isIntersecting; }); },{ threshold:0.02 }).observe(heroCanvas);
|
|
1056
|
+
}
|
|
1057
|
+
|
|
1058
|
+
/* ══════ 磁吸按钮 ══════ */
|
|
1059
|
+
document.querySelectorAll('.magnetic').forEach(e=>{
|
|
1060
|
+
if (!window.matchMedia('(hover: hover) and (pointer: fine)').matches) return;
|
|
1061
|
+
e.addEventListener('mousemove', ev=>{
|
|
1062
|
+
const r = e.getBoundingClientRect();
|
|
1063
|
+
e.style.transform = `translate(${(ev.clientX-r.left-r.width/2)*0.12}px,${(ev.clientY-r.top-r.height/2)*0.12}px)`;
|
|
1676
1064
|
});
|
|
1065
|
+
e.addEventListener('mouseleave', ()=>e.style.transform = 'translate(0,0)');
|
|
1066
|
+
});
|
|
1677
1067
|
|
|
1678
|
-
|
|
1679
|
-
|
|
1680
|
-
|
|
1681
|
-
|
|
1682
|
-
|
|
1683
|
-
|
|
1684
|
-
|
|
1685
|
-
|
|
1686
|
-
|
|
1687
|
-
|
|
1688
|
-
|
|
1689
|
-
|
|
1690
|
-
|
|
1068
|
+
/* ══════ 复制 ══════ */
|
|
1069
|
+
function flash(btn, ok){
|
|
1070
|
+
const old = btn.innerHTML;
|
|
1071
|
+
btn.textContent = ok ? (root.dataset.lang==='zh' ? '已复制' : 'Copied') : '失败';
|
|
1072
|
+
btn.style.borderColor = 'var(--accent)'; btn.style.color = 'var(--accent)';
|
|
1073
|
+
setTimeout(()=>{ btn.innerHTML = old; btn.style.borderColor=''; btn.style.color=''; }, 1200);
|
|
1074
|
+
}
|
|
1075
|
+
function copyText(t, btn){
|
|
1076
|
+
if (navigator.clipboard && navigator.clipboard.writeText){
|
|
1077
|
+
navigator.clipboard.writeText(t).then(()=>flash(btn,true)).catch(()=>flash(btn,false));
|
|
1078
|
+
} else {
|
|
1079
|
+
const ta = document.createElement('textarea'); ta.value = t; ta.style.position='fixed'; ta.style.opacity='0';
|
|
1080
|
+
document.body.appendChild(ta); ta.select();
|
|
1081
|
+
try { document.execCommand('copy'); flash(btn,true); } catch(e){ flash(btn,false); }
|
|
1082
|
+
document.body.removeChild(ta);
|
|
1083
|
+
}
|
|
1084
|
+
}
|
|
1085
|
+
document.querySelectorAll('.copy-cmd').forEach(b=>b.addEventListener('click', e=>{
|
|
1086
|
+
e.preventDefault(); copyText(b.getAttribute('data-copy'), b);
|
|
1087
|
+
}));
|
|
1088
|
+
document.querySelectorAll('.copy-el').forEach(b=>b.addEventListener('click', ()=>{
|
|
1089
|
+
const el = document.getElementById(b.getAttribute('data-target'));
|
|
1090
|
+
copyText(el ? el.textContent : '', b);
|
|
1091
|
+
}));
|
|
1691
1092
|
|
|
1692
|
-
|
|
1693
|
-
|
|
1694
|
-
|
|
1695
|
-
|
|
1696
|
-
|
|
1697
|
-
|
|
1698
|
-
|
|
1699
|
-
|
|
1700
|
-
|
|
1701
|
-
|
|
1702
|
-
|
|
1703
|
-
|
|
1704
|
-
|
|
1705
|
-
|
|
1706
|
-
|
|
1707
|
-
|
|
1708
|
-
|
|
1709
|
-
|
|
1093
|
+
/* ══════ 宣传图轮播 ══════ */
|
|
1094
|
+
(function(){
|
|
1095
|
+
const track = document.getElementById('promo-track'); if (!track) return;
|
|
1096
|
+
const frames = track.querySelectorAll('img');
|
|
1097
|
+
const total = frames.length;
|
|
1098
|
+
const dots = document.getElementById('promo-dots');
|
|
1099
|
+
const idx = document.getElementById('promo-idx');
|
|
1100
|
+
let cur = 0, timer = null;
|
|
1101
|
+
for (let i=0;i<total;i++){
|
|
1102
|
+
const b = document.createElement('button');
|
|
1103
|
+
b.setAttribute('aria-label', 'frame '+(i+1));
|
|
1104
|
+
b.style.cssText = 'width:8px;height:8px;border-radius:50%;border:1px solid var(--border-strong);background:transparent;cursor:pointer;transition:all .25s';
|
|
1105
|
+
b.addEventListener('click', ()=>go(i));
|
|
1106
|
+
dots.appendChild(b);
|
|
1107
|
+
}
|
|
1108
|
+
function paint(){
|
|
1109
|
+
frames.forEach((f,i)=>f.style.opacity = i===cur ? '1' : '0.35');
|
|
1110
|
+
Array.from(dots.children).forEach((d,i)=>{ d.style.background = i===cur ? 'var(--accent)' : 'transparent'; d.style.borderColor = i===cur ? 'var(--accent)' : 'var(--border-strong)'; });
|
|
1111
|
+
if (idx) idx.textContent = String(cur+1);
|
|
1112
|
+
}
|
|
1113
|
+
function go(i){
|
|
1114
|
+
cur = (i+total) % total;
|
|
1115
|
+
track.style.transform = `translateX(-${cur*100}%)`;
|
|
1116
|
+
paint();
|
|
1117
|
+
rest();
|
|
1118
|
+
}
|
|
1119
|
+
function rest(){ clearInterval(timer); timer = setInterval(()=>go(cur+1), 5200); }
|
|
1120
|
+
document.getElementById('promo-prev').onclick = ()=>go(cur-1);
|
|
1121
|
+
document.getElementById('promo-next').onclick = ()=>go(cur+1);
|
|
1122
|
+
track.parentElement.addEventListener('mouseenter', ()=>clearInterval(timer));
|
|
1123
|
+
track.parentElement.addEventListener('mouseleave', rest);
|
|
1124
|
+
go(0);
|
|
1125
|
+
})();
|
|
1126
|
+
|
|
1127
|
+
/* ══════ 演示 Tab ══════ */
|
|
1128
|
+
document.querySelectorAll('.demo-tab').forEach(t=>{
|
|
1129
|
+
t.addEventListener('click', ()=>{
|
|
1130
|
+
document.querySelectorAll('.demo-tab').forEach(x=>x.classList.remove('active'));
|
|
1131
|
+
document.querySelectorAll('.demo-panel').forEach(x=>x.classList.remove('active'));
|
|
1132
|
+
t.classList.add('active');
|
|
1133
|
+
const p = document.querySelector(`.demo-panel[data-panel="${t.dataset.demo}"]`);
|
|
1134
|
+
if (p) p.classList.add('active');
|
|
1135
|
+
});
|
|
1136
|
+
});
|
|
1710
1137
|
|
|
1711
|
-
|
|
1712
|
-
|
|
1713
|
-
|
|
1714
|
-
|
|
1715
|
-
|
|
1716
|
-
|
|
1717
|
-
|
|
1718
|
-
|
|
1719
|
-
|
|
1720
|
-
|
|
1721
|
-
|
|
1722
|
-
|
|
1723
|
-
|
|
1724
|
-
|
|
1725
|
-
|
|
1726
|
-
|
|
1727
|
-
|
|
1728
|
-
|
|
1729
|
-
|
|
1730
|
-
|
|
1731
|
-
|
|
1732
|
-
|
|
1733
|
-
|
|
1138
|
+
/* ══════ 演示 1:主动召回 ══════ */
|
|
1139
|
+
(function(){
|
|
1140
|
+
const QUERIES = [
|
|
1141
|
+
{
|
|
1142
|
+
zh:'「帮我把部署脚本改一下」', en:'"help me fix the deploy script"',
|
|
1143
|
+
cands:[
|
|
1144
|
+
{ s:0.94, zh:'部署脚本在 tools/deploy.sh,改完先跑 --dry 再正式执行', en:'Deploy script lives at tools/deploy.sh — run --dry before the real run', src:'项目笔记' },
|
|
1145
|
+
{ s:0.71, zh:'上次直接改了 .sh 没跑 dry,把线上配置覆盖了', en:'Last time editing .sh without dry overwrote the live config', src:'每日日志' },
|
|
1146
|
+
{ s:0.63, zh:'服务器清单:10.0.0.3(测试)/ 10.0.0.7(正式)', en:'Server list: 10.0.0.3 (test) / 10.0.0.7 (prod)', src:'用户级记忆' },
|
|
1147
|
+
{ s:0.41, zh:'用户偏好:脚本一律同时给 Windows / POSIX 两版', en:'Preference: always ship both Windows and POSIX script variants', src:'用户级记忆' }
|
|
1148
|
+
]
|
|
1149
|
+
},
|
|
1150
|
+
{
|
|
1151
|
+
zh:'「上次那个坑又踩了」', en:'"I hit that same pitfall again"',
|
|
1152
|
+
cands:[
|
|
1153
|
+
{ s:0.91, zh:'路径取证正则默认排除反斜杠:匹配 D:\\ 会失败并误报未匹配', en:'Path regexes must allow backslashes: matching D:\\ otherwise fails silently', src:'用户级记忆' },
|
|
1154
|
+
{ s:0.78, zh:'锚点块替换:替换文本必须逐行回抄锚点原文的全部声明', en:'Anchor-block patches must copy back every declaration from the original', src:'项目笔记' },
|
|
1155
|
+
{ s:0.66, zh:'「半修」状态:同一语义在多处各写一份判据,只改部分会像新 bug', en:'"Half-fix": one semantic judged in several places — fixing some looks like a new bug', src:'每日反思' },
|
|
1156
|
+
{ s:0.38, zh:'备份命名规范:.bak-YYYYMMDD-HHMMSS-{reason}', en:'Backup naming: .bak-YYYYMMDD-HHMMSS-{reason}', src:'项目笔记' }
|
|
1157
|
+
]
|
|
1158
|
+
},
|
|
1159
|
+
{
|
|
1160
|
+
zh:'「为什么最后选了它?」', en:'"why did we end up choosing it?"',
|
|
1161
|
+
cands:[
|
|
1162
|
+
{ s:0.89, zh:'BGE-M3 int8:R@5 0.925,与 fp32 差 0.000,快 6×', en:'BGE-M3 int8: R@5 0.925, Δ0.000 vs fp32, 6× faster', src:'设计文献' },
|
|
1163
|
+
{ s:0.74, zh:'三级算力:词法 0GB 保底永远可用,失败自动逐级回退', en:'Three tiers: lexical 0GB floor always available, automatic tier fallback', src:'项目笔记' },
|
|
1164
|
+
{ s:0.61, zh:'JS 与 Python 两套引擎相对独立、可互相替换,严禁联动', en:'JS and Python engines are independent and interchangeable — coupling forbidden', src:'用户级记忆' },
|
|
1165
|
+
{ s:0.35, zh:'备选方案:fp32 档显存占用 4×,移动端不可接受', en:'Rejected: fp32 uses 4× memory, unacceptable on mobile', src:'设计文献' }
|
|
1166
|
+
]
|
|
1734
1167
|
}
|
|
1735
|
-
|
|
1736
|
-
|
|
1168
|
+
];
|
|
1169
|
+
const log = document.getElementById('recall-log');
|
|
1170
|
+
const qs = document.getElementById('recall-queries');
|
|
1171
|
+
let qi = 0, running = false;
|
|
1172
|
+
qs.querySelectorAll('button').forEach(b=>b.addEventListener('click', ()=>{
|
|
1173
|
+
qs.querySelectorAll('button').forEach(x=>x.classList.remove('active'));
|
|
1174
|
+
b.classList.add('active'); qi = parseInt(b.dataset.q,10);
|
|
1175
|
+
}));
|
|
1176
|
+
document.getElementById('recall-run').onclick = ()=>{
|
|
1177
|
+
if (running) return; running = true;
|
|
1178
|
+
const L = root.dataset.lang === 'zh' ? 'zh' : 'en';
|
|
1179
|
+
const q = QUERIES[qi];
|
|
1180
|
+
const t0 = performance.now();
|
|
1181
|
+
log.innerHTML = '';
|
|
1182
|
+
const add = (html, delay)=>new Promise(res=>setTimeout(()=>{ log.insertAdjacentHTML('beforeend', html); log.scrollTop = log.scrollHeight; res(); }, delay));
|
|
1183
|
+
(async ()=>{
|
|
1184
|
+
await add(`<div class="keyword">[observe]</div> <span class="comment">${L==='zh'?'捕获当前轮对话上下文…':'capturing current turn context…'}</span><br><span class="string">${q[L]}</span><br><br>`, 0);
|
|
1185
|
+
await add(`<div class="keyword">[search]</div> <span class="comment">${L==='zh'?'双轨检索:词法 BM25 (0.3) + 向量 (0.7)':'dual-channel: lexical BM25 (0.3) + vector (0.7)'}</span><br>`, 420);
|
|
1186
|
+
let best = q.cands[0];
|
|
1187
|
+
for (let i=0;i<q.cands.length;i++){
|
|
1188
|
+
const c = q.cands[i];
|
|
1189
|
+
await add(`<span class="comment"> ${L==='zh'?'候选':'candidate'} ${i+1}</span> <span class="highlight">${c.s.toFixed(2)}</span> <span class="comment">[${c.src}]</span> ${c[L]}<br>`, 260);
|
|
1190
|
+
if (c.s > best.s) best = c;
|
|
1191
|
+
}
|
|
1192
|
+
const ms = (performance.now()-t0).toFixed(0);
|
|
1193
|
+
await add(`<br><div class="keyword">[fuse]</div> <span class="comment">${L==='zh'?'融合排序完成,取 top-1':'fusion ranked, taking top-1'}</span><br>`, 340);
|
|
1194
|
+
await add(`<div class="keyword">[inject]</div> <span class="string">✓ ${L==='zh'?'经固定边界注入下一拍':'injected into next turn via fixed boundary'}</span><br><span class="comment"> → ${best[L]}</span><br><br>`, 420);
|
|
1195
|
+
await add(`<span class="comment">// ${L==='zh'?'模型甚至还没开口,她已经记得':'the model has not spoken yet, and she already remembers'}</span>`, 260);
|
|
1196
|
+
document.getElementById('recall-cand').textContent = String(q.cands.length);
|
|
1197
|
+
document.getElementById('recall-top').textContent = best.s.toFixed(2);
|
|
1198
|
+
document.getElementById('recall-ms').textContent = ms + 'ms';
|
|
1199
|
+
running = false;
|
|
1200
|
+
})();
|
|
1201
|
+
};
|
|
1202
|
+
document.getElementById('recall-reset').onclick = ()=>{
|
|
1203
|
+
log.innerHTML = `<div class="comment">// ${root.dataset.lang==='zh'?'等待输入…':'awaiting input…'}</div>`;
|
|
1204
|
+
document.getElementById('recall-cand').textContent = '0';
|
|
1205
|
+
document.getElementById('recall-top').textContent = '—';
|
|
1206
|
+
document.getElementById('recall-ms').textContent = '—';
|
|
1207
|
+
};
|
|
1208
|
+
})();
|
|
1209
|
+
|
|
1210
|
+
/* ══════ 演示 2:两车道决策 ══════ */
|
|
1211
|
+
(function(){
|
|
1212
|
+
const CANDS = [
|
|
1213
|
+
{ s:0.94, echo:0, zh:'部署脚本要先跑 --dry', en:'run --dry before deploying' },
|
|
1214
|
+
{ s:0.81, echo:0, zh:'上次覆盖线上配置的教训', en:'the lesson from overwriting prod config' },
|
|
1215
|
+
{ s:0.72, echo:1, zh:'(回声:模型刚说过同一句话)', en:'(echo: the model just said this)' },
|
|
1216
|
+
{ s:0.58, echo:0, zh:'服务器清单与访问方式', en:'server list and access' },
|
|
1217
|
+
{ s:0.44, echo:0, zh:'脚本双版本偏好', en:'dual-variant script preference' },
|
|
1218
|
+
{ s:0.31, echo:0, zh:'旧版构建流程(已弃用)', en:'legacy build flow (deprecated)' }
|
|
1219
|
+
];
|
|
1220
|
+
const rows = document.getElementById('gate-rows');
|
|
1221
|
+
function render(){
|
|
1222
|
+
const th = parseFloat(document.getElementById('gate-slider').value);
|
|
1223
|
+
const ev = parseInt(document.getElementById('echo-slider').value,10);
|
|
1224
|
+
const L = root.dataset.lang === 'zh' ? 'zh' : 'en';
|
|
1225
|
+
let canary = 0, shadow = 0;
|
|
1226
|
+
rows.innerHTML = '';
|
|
1227
|
+
CANDS.forEach((c,i)=>{
|
|
1228
|
+
const blocked = (ev===1 && c.echo===1) || c.s < th;
|
|
1229
|
+
const lane = blocked ? 'shadow' : 'canary';
|
|
1230
|
+
blocked ? shadow++ : canary++;
|
|
1231
|
+
const pct = Math.round(c.s*100);
|
|
1232
|
+
rows.insertAdjacentHTML('beforeend', `
|
|
1233
|
+
<div>
|
|
1234
|
+
<div class="flex items-center justify-between mb-2">
|
|
1235
|
+
<span class="text-sm" style="color:var(--fg-dim)">${c[L]}</span>
|
|
1236
|
+
<span class="font-mono text-xs" style="color:${blocked?'var(--muted)':'var(--accent)'}">${c.s.toFixed(2)} · ${lane.toUpperCase()}${blocked && ev===1 && c.echo===1 ? ' (echo veto)' : blocked ? ' (below threshold)' : ''}</span>
|
|
1237
|
+
</div>
|
|
1238
|
+
<div class="lane-bar"><i style="width:${pct}%;background:${blocked?'var(--muted)':'var(--accent)'};opacity:${blocked?0.35:0.85}"></i></div>
|
|
1239
|
+
</div>`);
|
|
1737
1240
|
});
|
|
1738
|
-
|
|
1739
|
-
|
|
1740
|
-
|
|
1741
|
-
|
|
1742
|
-
|
|
1241
|
+
document.getElementById('gate-canary').textContent = String(canary);
|
|
1242
|
+
document.getElementById('gate-shadow').textContent = String(shadow);
|
|
1243
|
+
}
|
|
1244
|
+
const th = document.getElementById('gate-slider'), ev = document.getElementById('echo-slider');
|
|
1245
|
+
th.addEventListener('input', ()=>{ document.getElementById('gate-val').textContent = parseFloat(th.value).toFixed(2); render(); });
|
|
1246
|
+
ev.addEventListener('input', ()=>{
|
|
1247
|
+
const on = ev.value === '1';
|
|
1248
|
+
const lab = document.getElementById('echo-val');
|
|
1249
|
+
lab.textContent = on ? (root.dataset.lang==='zh'?'开':'on') : (root.dataset.lang==='zh'?'关':'off');
|
|
1250
|
+
render();
|
|
1251
|
+
});
|
|
1252
|
+
document.querySelectorAll('[data-lang-btn]').forEach(b=>b.addEventListener('click', ()=>setTimeout(render, 0)));
|
|
1253
|
+
render();
|
|
1254
|
+
})();
|
|
1255
|
+
|
|
1256
|
+
/* ══════ 演示 3:技能固化 ══════ */
|
|
1257
|
+
(function(){
|
|
1258
|
+
const STAGES = [
|
|
1259
|
+
{ k:'observed', zh:'观测到重复模式', en:'repeated pattern observed', need:1 },
|
|
1260
|
+
{ k:'candidate', zh:'成为候选技能', en:'promoted to candidate', need:2 },
|
|
1261
|
+
{ k:'validated', zh:'跨会话验证通过', en:'validated across sessions', need:4 },
|
|
1262
|
+
{ k:'active', zh:'已激活 · 自动挂载清单', en:'active · checklist auto-attaches', need:6 }
|
|
1263
|
+
];
|
|
1264
|
+
const box = document.getElementById('skill-stages');
|
|
1265
|
+
let n = 0;
|
|
1266
|
+
function render(){
|
|
1267
|
+
const L = root.dataset.lang === 'zh' ? 'zh' : 'en';
|
|
1268
|
+
let stage = STAGES[0];
|
|
1269
|
+
for (const s of STAGES) if (n >= s.need) stage = s;
|
|
1270
|
+
box.innerHTML = '';
|
|
1271
|
+
STAGES.forEach(s=>{
|
|
1272
|
+
const done = n >= s.need;
|
|
1273
|
+
const isNow = s.k === stage.k;
|
|
1274
|
+
box.insertAdjacentHTML('beforeend', `
|
|
1275
|
+
<div class="hit-row ${done?'win':''}">
|
|
1276
|
+
<span class="score">${done?'✓':'·'}</span>
|
|
1277
|
+
<div class="txt">
|
|
1278
|
+
<div style="color:var(--fg);font-weight:600;font-size:13.5px">${s[L]}</div>
|
|
1279
|
+
<div class="font-mono" style="font-size:10.5px;color:var(--muted);margin-top:2px">${s.k.toUpperCase()} · need ${s.need} ${L==='zh'?'次观测':'observations'}${isNow?' ← '+ (L==='zh'?'当前':'now') : ''}</div>
|
|
1280
|
+
</div>
|
|
1281
|
+
</div>`);
|
|
1282
|
+
});
|
|
1283
|
+
document.getElementById('skill-obs').textContent = String(n);
|
|
1284
|
+
document.getElementById('skill-stage').textContent = n === 0 ? '—' : stage.k.toUpperCase();
|
|
1285
|
+
}
|
|
1286
|
+
document.getElementById('skill-run').onclick = ()=>{ if (n < 6) n += 1; render(); };
|
|
1287
|
+
document.querySelectorAll('[data-lang-btn]').forEach(b=>b.addEventListener('click', ()=>setTimeout(render, 0)));
|
|
1288
|
+
render();
|
|
1289
|
+
})();
|
|
1290
|
+
|
|
1291
|
+
/* 语言切换后刷新动态文案 */
|
|
1292
|
+
document.querySelectorAll('[data-lang-btn]').forEach(b=>b.addEventListener('click', ()=>{
|
|
1293
|
+
const t = document.getElementById('echo-val');
|
|
1294
|
+
if (t){ const on = document.getElementById('echo-slider').value === '1';
|
|
1295
|
+
t.textContent = on ? (root.dataset.lang==='zh'?'开':'on') : (root.dataset.lang==='zh'?'关':'off'); }
|
|
1296
|
+
}));
|
|
1743
1297
|
</script>
|
|
1744
1298
|
</body>
|
|
1745
1299
|
</html>
|