@hongmaple0820/scale-engine 0.50.1 → 0.50.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (50) hide show
  1. package/README.en.md +2 -2
  2. package/README.md +2 -2
  3. package/dist/api/http.js +3 -1
  4. package/dist/api/http.js.map +1 -1
  5. package/dist/cli/cortexCommands.d.ts +16 -0
  6. package/dist/cli/cortexCommands.js +47 -4
  7. package/dist/cli/cortexCommands.js.map +1 -1
  8. package/dist/cortex/InstinctStore.d.ts +13 -1
  9. package/dist/cortex/InstinctStore.js +90 -11
  10. package/dist/cortex/InstinctStore.js.map +1 -1
  11. package/dist/cortex/SessionInjector.js +39 -2
  12. package/dist/cortex/SessionInjector.js.map +1 -1
  13. package/dist/dashboard/DashboardServer.d.ts +158 -0
  14. package/dist/dashboard/DashboardServer.js +753 -13
  15. package/dist/dashboard/DashboardServer.js.map +1 -1
  16. package/dist/dashboard/spa/assets/index-VYBCLBje.js +11 -0
  17. package/dist/dashboard/spa/assets/index-VhwY_ac1.css +1 -0
  18. package/dist/dashboard/spa/assets/naive-ui-BQy2AJkt.js +3340 -0
  19. package/dist/dashboard/spa/assets/vendor-BPU6aOYA.js +3 -0
  20. package/dist/dashboard/spa/assets/vue-CQQMb5Wi.js +17 -0
  21. package/dist/dashboard/spa/index.html +15 -462
  22. package/dist/memory/MemoryFabric.d.ts +13 -1
  23. package/dist/memory/MemoryFabric.js +60 -0
  24. package/dist/memory/MemoryFabric.js.map +1 -1
  25. package/dist/version.d.ts +1 -1
  26. package/dist/version.js +1 -1
  27. package/docs/workflow/ASSESSMENT_INDEX.md +326 -0
  28. package/docs/workflow/COMPARATIVE_ANALYSIS.md +422 -0
  29. package/docs/workflow/EXECUTIVE_SUMMARY.md +310 -0
  30. package/docs/workflow/IMPROVEMENT_CHECKLIST.md +518 -0
  31. package/docs/workflow/IMPROVEMENT_ROADMAP.md +707 -0
  32. package/docs/workflow/README.md +8 -0
  33. package/package.json +6 -2
  34. package/dist/dashboard/spa/app.js +0 -515
  35. package/dist/dashboard/spa/components/DataTable.js +0 -53
  36. package/dist/dashboard/spa/components/EventStream.js +0 -66
  37. package/dist/dashboard/spa/components/LoadingState.js +0 -39
  38. package/dist/dashboard/spa/components/MetricCard.js +0 -30
  39. package/dist/dashboard/spa/components/Panel.js +0 -27
  40. package/dist/dashboard/spa/components/StatusBadge.js +0 -51
  41. package/dist/dashboard/spa/i18n.js +0 -767
  42. package/dist/dashboard/spa/pages/costs.js +0 -522
  43. package/dist/dashboard/spa/pages/documents.js +0 -540
  44. package/dist/dashboard/spa/pages/knowledge.js +0 -457
  45. package/dist/dashboard/spa/pages/monitoring.js +0 -361
  46. package/dist/dashboard/spa/pages/overview.js +0 -301
  47. package/dist/dashboard/spa/pages/topology-renderers.js +0 -251
  48. package/dist/dashboard/spa/pages/topology.js +0 -370
  49. package/dist/dashboard/spa/pages/workflow-renderers.js +0 -239
  50. package/dist/dashboard/spa/pages/workflow.js +0 -217
@@ -1,457 +0,0 @@
1
- /**
2
- * Knowledge Page - Memory Brain nodes, provider status, and explicit recall.
3
- */
4
- ;(() => {
5
- 'use strict'
6
-
7
- const { copyText, downloadText, fetchJSON, formatTime, runtimeLabel, t, $, dom } = window.Dashboard
8
- const { autoRefreshControl, dataNote, dataTable, el, emptyState, metricCard, panel, renderText } = dom
9
- let lastReport = null
10
- let lastQuery = ''
11
- let localStatusFilter = ''
12
- let reviewMessage = ''
13
-
14
- async function renderKnowledge() {
15
- const app = $('#app')
16
- const search = el('input', {
17
- id: 'knowledge-search',
18
- type: 'text',
19
- className: 'search-box',
20
- placeholder: t('knowledge.searchPlaceholder'),
21
- style: { flex: '1', maxWidth: '460px' },
22
- })
23
- const recall = el('button', { id: 'knowledge-recall', className: 'topo-btn', text: t('knowledge.recall') })
24
- const refresh = el('button', { id: 'knowledge-refresh', className: 'topo-btn', text: t('common.refresh') })
25
- const copyButton = el('button', { id: 'knowledge-copy-json', className: 'topo-btn', text: t('common.copyJson') })
26
- const exportButton = el('button', { id: 'knowledge-export', className: 'topo-btn', text: t('knowledge.exportAll') })
27
- const localFilter = el('select', {
28
- id: 'knowledge-local-filter',
29
- className: 'search-box',
30
- title: t('knowledge.localFilter'),
31
- style: { width: '180px' },
32
- }, [
33
- el('option', { value: '', text: t('knowledge.allStatuses') }),
34
- ])
35
-
36
- app.replaceChildren(
37
- el('div', { className: 'page-toolbar' }, [
38
- search,
39
- recall,
40
- refresh,
41
- copyButton,
42
- exportButton,
43
- autoRefreshControl(() => loadKnowledge(search.value.trim())),
44
- el('label', { className: 'field-label' }, [
45
- el('span', { text: t('knowledge.localFilter') }),
46
- localFilter,
47
- ]),
48
- ]),
49
- el('div', { id: 'knowledge-data-note' }),
50
- el('div', { className: 'metric-grid', id: 'knowledge-summary' }),
51
- panel(t('knowledge.operations'), 'knowledge-operations'),
52
- panel(t('knowledge.reviewQueue'), 'knowledge-review'),
53
- el('div', { className: 'grid-2', style: { marginTop: '16px' } }, [
54
- panel(t('knowledge.providers'), 'knowledge-providers'),
55
- panel(t('knowledge.recallResults'), 'knowledge-recall-results'),
56
- ]),
57
- panel(t('knowledge.localMemory'), 'knowledge-local', { className: 'mt-3' }),
58
- panel(t('knowledge.warnings'), 'knowledge-warnings', { className: 'mt-3' }),
59
- )
60
-
61
- const load = () => loadKnowledge(search.value.trim())
62
- recall.addEventListener('click', load)
63
- refresh.addEventListener('click', () => loadKnowledge(''))
64
- copyButton.addEventListener('click', () => copyKnowledgeSection('all', copyButton))
65
- exportButton.addEventListener('click', exportKnowledge)
66
- localFilter.addEventListener('change', () => {
67
- localStatusFilter = localFilter.value
68
- renderLocal(lastReport?.local)
69
- })
70
- search.addEventListener('keydown', event => {
71
- if (event.key === 'Enter') load()
72
- })
73
-
74
- await loadKnowledge('')
75
- }
76
-
77
- async function loadKnowledge(query) {
78
- const params = new URLSearchParams({ limit: '20' })
79
- if (query) {
80
- params.set('query', query)
81
- params.set('recall', '1')
82
- }
83
- const report = await fetchJSON(`/api/knowledge?${params.toString()}`)
84
- const localContainer = $('#knowledge-local')
85
- if (!report) {
86
- if (localContainer) renderText(localContainer, t('knowledge.failedToLoad'))
87
- return
88
- }
89
- if (!$('#knowledge-summary')) return
90
- lastReport = report
91
- lastQuery = query
92
- renderSummary(report)
93
- renderDataNote(report)
94
- renderOperations(report)
95
- renderReviewQueue(report)
96
- renderProviders(report.providers)
97
- renderRecall(report.recall)
98
- renderLocal(report.local)
99
- renderWarnings(report.warnings || [])
100
- }
101
-
102
- function renderDataNote(report) {
103
- const node = $('#knowledge-data-note')
104
- if (!node) return
105
- const providerCount = report.providers?.availableProviderCount ?? 0
106
- node.replaceChildren(dataNote([
107
- { strong: true, text: t('common.snapshot') },
108
- `${t('common.lastLoaded')}: ${formatTime(Date.now())}`,
109
- t('knowledge.dataHint'),
110
- `${t('knowledge.providersReady')}: ${providerCount}`,
111
- ]))
112
- }
113
-
114
- function renderSummary(report) {
115
- const summary = $('#knowledge-summary')
116
- if (!summary) return
117
- const local = report.local || { total: 0, byStatus: {} }
118
- const providers = report.providers?.providers || []
119
- const recallItems = report.recall?.items || []
120
- summary.replaceChildren(
121
- metricCard(t('knowledge.localNodes'), local.total ?? 0),
122
- metricCard(t('knowledge.activeNodes'), local.byStatus?.active ?? 0),
123
- metricCard(t('knowledge.providersReady'), providers.filter(provider => provider.available).length),
124
- metricCard(t('knowledge.recalledItems'), recallItems.length),
125
- )
126
- }
127
-
128
- function renderOperations(report) {
129
- const container = $('#knowledge-operations')
130
- if (!container) return
131
- const local = report.local || { total: 0, nodes: [] }
132
- const providers = report.providers?.providers || []
133
- const recallItems = report.recall?.items || []
134
- const actions = [
135
- actionButton(t('knowledge.copyLocal'), button => copyKnowledgeSection('local', button)),
136
- actionButton(t('knowledge.exportLocal'), () => exportKnowledgeSection('local')),
137
- actionButton(t('knowledge.copyRecall'), button => copyKnowledgeSection('recall', button)),
138
- actionButton(t('knowledge.exportRecall'), () => exportKnowledgeSection('recall')),
139
- ]
140
- const rows = [
141
- sourceRow(t('knowledge.localBrainSource'), local.available ? local.total : 0, true),
142
- sourceRow(t('knowledge.providerSource'), providers.length, true),
143
- sourceRow(t('knowledge.recallSource'), recallItems.length, true),
144
- ]
145
- container.replaceChildren(
146
- el('div', { className: 'action-row', style: { marginBottom: '12px' } }, actions),
147
- dataNote([
148
- { strong: true, text: t('knowledge.managementScope') },
149
- t('knowledge.managementScopeHint'),
150
- t('knowledge.fullProviderExportHint'),
151
- ]),
152
- dataTable([t('knowledge.source'), t('knowledge.count'), t('knowledge.exportable')], rows),
153
- )
154
- }
155
-
156
- function renderReviewQueue(report) {
157
- const container = $('#knowledge-review')
158
- if (!container) return
159
- const packet = memoryReviewPacket(report)
160
- const copy = actionButton(t('knowledge.copyReviewPacket'), button => copyText(JSON.stringify(packet, null, 2), button))
161
- const exportButton = actionButton(t('knowledge.exportReviewPacket'), () => {
162
- downloadText(`scale-memory-review-${Date.now()}.json`, JSON.stringify(packet, null, 2), 'application/json;charset=utf-8')
163
- })
164
- const summary = packet.summary
165
- const blocks = [
166
- reviewBlock(t('knowledge.candidates'), summary.candidate),
167
- reviewBlock(t('knowledge.stale'), summary.stale),
168
- reviewBlock(t('knowledge.rejected'), summary.rejected),
169
- reviewBlock(t('knowledge.missingEvidence'), summary.missingEvidence),
170
- ]
171
-
172
- const children = [
173
- el('div', { className: 'action-row', style: { marginBottom: '12px' } }, [copy, exportButton]),
174
- el('div', { id: 'knowledge-review-message', className: 'text-muted text-sm', text: reviewMessage, style: { marginBottom: '10px' } }),
175
- dataNote([{ strong: true, text: t('knowledge.reviewQueue') }, t('knowledge.reviewQueueHint')]),
176
- el('div', { className: 'review-grid' }, blocks),
177
- ]
178
-
179
- if (packet.items.length === 0) {
180
- children.push(emptyStateWithHint(t('knowledge.noReviewItems'), t('knowledge.noReviewItemsHint'), '\u25cc'))
181
- } else {
182
- children.push(el('div', { className: 'list' }, packet.items.map(item => renderReviewItem(item))))
183
- }
184
- container.replaceChildren(...children)
185
- }
186
-
187
- function reviewBlock(label, count) {
188
- return el('div', { className: 'review-item' }, [
189
- el('div', { className: 'review-count', text: count }),
190
- el('div', { className: 'review-label', text: label }),
191
- ])
192
- }
193
-
194
- function renderReviewItem(item) {
195
- const copyId = actionButton(t('common.copy'), button => copyText(item.id, button))
196
- const copyEvidence = actionButton(t('knowledge.evidence'), button => copyText((item.evidencePaths || []).join('\n'), button))
197
- const reviewActions = reviewActionsFor(item).map(action => actionButton(reviewActionLabel(action), button => reviewMemoryNode(item.id, action, button)))
198
- return el('div', { className: 'list-item' }, [
199
- el('div', { style: { display: 'flex', justifyContent: 'space-between', gap: '12px' } }, [
200
- el('strong', { text: item.title || item.id }),
201
- el('span', { className: 'status-badge', text: runtimeLabel('status', item.status) }),
202
- ]),
203
- el('p', { text: item.summary || '', style: { margin: '6px 0', lineHeight: '1.5' } }),
204
- el('div', { className: 'text-muted text-sm', text: `${item.type} · ${item.layer} · ${t('common.confidence')} ${formatScore(item.confidence)}` }),
205
- el('div', { className: 'action-row', style: { marginTop: '8px' } }, [copyId, copyEvidence, ...reviewActions]),
206
- ])
207
- }
208
-
209
- function reviewActionsFor(item) {
210
- if (item.status === 'candidate') return ['approve', 'reject']
211
- if (item.status === 'active' && item.reason === 'missing-evidence') return ['stale']
212
- if (item.status === 'stale' || item.status === 'rejected') return ['restore']
213
- return []
214
- }
215
-
216
- function reviewActionLabel(action) {
217
- if (action === 'approve') return t('knowledge.approveMemory')
218
- if (action === 'reject') return t('knowledge.rejectMemory')
219
- if (action === 'stale') return t('knowledge.markStale')
220
- return t('knowledge.restoreMemory')
221
- }
222
-
223
- async function reviewMemoryNode(id, action, button) {
224
- const message = $('#knowledge-review-message')
225
- const original = button.textContent
226
- button.disabled = true
227
- button.textContent = t('common.refreshing')
228
- try {
229
- const response = await fetch(`/api/knowledge/local/${encodeURIComponent(id)}/review`, {
230
- method: 'POST',
231
- headers: { 'Content-Type': 'application/json' },
232
- body: JSON.stringify({ action, reason: t('knowledge.reviewReason') }),
233
- })
234
- const result = await response.json().catch(() => ({}))
235
- if (!response.ok || !result.success) throw new Error(result.error || `${response.status} ${response.statusText}`)
236
- reviewMessage = t('knowledge.reviewSucceeded', { id: result.evidence?.id || '-' })
237
- if (message) message.textContent = reviewMessage
238
- await loadKnowledge(lastQuery)
239
- } catch (error) {
240
- reviewMessage = t('knowledge.reviewFailed', { error: errorMessage(error) })
241
- if (message) message.textContent = reviewMessage
242
- } finally {
243
- button.disabled = false
244
- button.textContent = original
245
- }
246
- }
247
-
248
- function memoryReviewPacket(report) {
249
- const nodes = report?.local?.nodes || []
250
- const items = nodes
251
- .filter(node => ['candidate', 'stale', 'rejected'].includes(node.status) || (node.status === 'active' && (node.evidencePaths || []).length === 0))
252
- .map(node => ({
253
- id: node.id,
254
- title: node.title,
255
- summary: node.summary,
256
- type: node.type,
257
- layer: node.layer,
258
- status: node.status,
259
- confidence: node.confidence,
260
- evidencePaths: node.evidencePaths || [],
261
- updatedAt: node.updatedAt,
262
- reason: reviewReason(node),
263
- }))
264
- return {
265
- exportedAt: new Date().toISOString(),
266
- project: report?.project ?? null,
267
- summary: {
268
- total: nodes.length,
269
- candidate: nodes.filter(node => node.status === 'candidate').length,
270
- stale: nodes.filter(node => node.status === 'stale').length,
271
- rejected: nodes.filter(node => node.status === 'rejected').length,
272
- missingEvidence: nodes.filter(node => node.status === 'active' && (node.evidencePaths || []).length === 0).length,
273
- reviewItems: items.length,
274
- },
275
- items,
276
- writePolicy: t('knowledge.managementScopeHint'),
277
- }
278
- }
279
-
280
- function reviewReason(node) {
281
- if (node.status === 'candidate') return 'candidate'
282
- if (node.status === 'stale') return 'stale'
283
- if (node.status === 'rejected') return 'rejected'
284
- if (node.status === 'active' && (node.evidencePaths || []).length === 0) return 'missing-evidence'
285
- return 'review'
286
- }
287
-
288
- function renderProviders(providersReport) {
289
- const container = $('#knowledge-providers')
290
- if (!container) return
291
- const providers = providersReport?.providers || []
292
- if (providers.length === 0) {
293
- container.replaceChildren(emptyState(t('knowledge.noProviders'), '\u25cc'))
294
- return
295
- }
296
- container.replaceChildren(el('div', { className: 'list' }, providers.map(provider => el('div', { className: 'list-item' }, [
297
- el('div', { style: { display: 'flex', justifyContent: 'space-between', gap: '12px' } }, [
298
- el('strong', { text: provider.id }),
299
- el('span', {
300
- className: provider.available ? 'status-badge passed' : 'status-badge failed',
301
- text: provider.available ? t('knowledge.available') : t('knowledge.unavailable'),
302
- }),
303
- ]),
304
- el('div', { className: 'text-muted text-sm', text: `${provider.kind || '-'} · ${provider.reason || ''}` }),
305
- ]))))
306
- }
307
-
308
- function renderRecall(recall) {
309
- const container = $('#knowledge-recall-results')
310
- if (!container) return
311
- const items = recall?.items || []
312
- if (items.length === 0) {
313
- container.replaceChildren(emptyStateWithHint(t('knowledge.noRecall'), t('knowledge.noRecallHint'), '\u2315'))
314
- return
315
- }
316
- container.replaceChildren(el('div', { className: 'list' }, items.map(item => renderKnowledgeItem({
317
- title: item.title,
318
- summary: item.summary,
319
- status: item.provider,
320
- meta: `${t('common.score')} ${formatScore(item.score)} · ${t('common.confidence')} ${formatScore(item.confidence)}`,
321
- evidencePaths: item.evidencePaths || [],
322
- }))))
323
- }
324
-
325
- function renderLocal(local) {
326
- const container = $('#knowledge-local')
327
- if (!container) return
328
- const nodes = local?.nodes || []
329
- if (!local?.available) {
330
- container.replaceChildren(emptyStateWithHint(t('knowledge.noLocalBrain'), t('knowledge.noLocalBrainHint'), '\u25cc'))
331
- return
332
- }
333
- if (nodes.length === 0) {
334
- container.replaceChildren(emptyStateWithHint(t('knowledge.noLocalNodes'), t('knowledge.noLocalNodesHint'), '\u25cc'))
335
- return
336
- }
337
- const filtered = localStatusFilter ? nodes.filter(node => node.status === localStatusFilter) : nodes
338
- updateLocalFilter(nodes)
339
- if (filtered.length === 0) {
340
- container.replaceChildren(emptyStateWithHint(t('common.noData'), t('knowledge.managementScopeHint'), '\u25cc'))
341
- return
342
- }
343
- container.replaceChildren(el('div', { className: 'list' }, filtered.map(node => renderKnowledgeItem({
344
- title: node.title,
345
- summary: node.summary,
346
- status: node.status,
347
- meta: `${node.type} · ${node.layer} · ${t('common.confidence')} ${formatScore(node.confidence)}`,
348
- evidencePaths: node.evidencePaths || [],
349
- }))))
350
- }
351
-
352
- function updateLocalFilter(nodes) {
353
- const filter = $('#knowledge-local-filter')
354
- if (!filter) return
355
- const statuses = [...new Set(nodes.map(node => node.status).filter(Boolean))].sort()
356
- const current = filter.value
357
- filter.replaceChildren(
358
- el('option', { value: '', text: t('knowledge.allStatuses') }),
359
- ...statuses.map(status => el('option', {
360
- value: status,
361
- text: runtimeLabel('status', status),
362
- attrs: { selected: status === current ? true : null },
363
- })),
364
- )
365
- filter.value = statuses.includes(current) ? current : ''
366
- localStatusFilter = filter.value
367
- }
368
-
369
- function renderWarnings(warnings) {
370
- const container = $('#knowledge-warnings')
371
- if (!container) return
372
- if (!warnings.length) {
373
- container.replaceChildren(el('div', { className: 'text-muted text-sm', text: t('knowledge.noWarnings') }))
374
- return
375
- }
376
- container.replaceChildren(el('ul', {}, warnings.map(warning => el('li', { text: warning }))))
377
- }
378
-
379
- function renderKnowledgeItem(item) {
380
- return el('div', { className: 'list-item' }, [
381
- el('div', { style: { display: 'flex', justifyContent: 'space-between', gap: '12px' } }, [
382
- el('strong', { text: item.title || '(untitled)' }),
383
- el('span', { className: 'status-badge', text: runtimeLabel('status', item.status) }),
384
- ]),
385
- el('p', { text: item.summary || '', style: { margin: '6px 0', lineHeight: '1.5' } }),
386
- el('div', { className: 'text-muted text-sm', text: item.meta || '' }),
387
- renderEvidence(item.evidencePaths),
388
- ])
389
- }
390
-
391
- function renderEvidence(paths) {
392
- if (!paths?.length) return el('div', { className: 'text-muted text-sm', text: t('knowledge.noEvidence') })
393
- return el('div', {
394
- className: 'text-muted text-sm',
395
- text: `${t('knowledge.evidence')}: ${paths.slice(0, 3).join(', ')}${paths.length > 3 ? '...' : ''}`,
396
- })
397
- }
398
-
399
- function emptyStateWithHint(message, hint, icon) {
400
- const state = emptyState(message, icon)
401
- state.appendChild(el('p', { className: 'text-muted text-sm', text: hint, style: { marginTop: '8px' } }))
402
- return state
403
- }
404
-
405
- function exportKnowledge() {
406
- const payload = knowledgePayload('all')
407
- const text = JSON.stringify(payload, null, 2)
408
- downloadText(`scale-knowledge-${Date.now()}.json`, text, 'application/json;charset=utf-8')
409
- }
410
-
411
- function exportKnowledgeSection(section) {
412
- const text = JSON.stringify(knowledgePayload(section), null, 2)
413
- downloadText(`scale-knowledge-${section}-${Date.now()}.json`, text, 'application/json;charset=utf-8')
414
- }
415
-
416
- function copyKnowledgeSection(section, button) {
417
- return copyText(JSON.stringify(knowledgePayload(section), null, 2), button)
418
- }
419
-
420
- function knowledgePayload(section) {
421
- const payload = {
422
- exportedAt: new Date().toISOString(),
423
- query: lastQuery,
424
- section,
425
- }
426
- if (section === 'local') return { ...payload, local: lastReport?.local ?? null }
427
- if (section === 'recall') return { ...payload, recall: lastReport?.recall ?? null }
428
- if (section === 'providers') return { ...payload, providers: lastReport?.providers ?? null }
429
- return { ...payload, report: lastReport }
430
- }
431
-
432
- function actionButton(text, onClick) {
433
- const button = el('button', { className: 'topo-btn', text })
434
- button.addEventListener('click', () => onClick(button))
435
- return button
436
- }
437
-
438
- function sourceRow(source, count, exportable) {
439
- return el('tr', {}, [
440
- el('td', { text: source }),
441
- el('td', { text: String(count ?? 0) }),
442
- el('td', { text: exportable ? t('common.yes') : t('common.no') }),
443
- ])
444
- }
445
-
446
- function formatScore(value) {
447
- if (typeof value !== 'number' || Number.isNaN(value)) return '-'
448
- return value.toFixed(2)
449
- }
450
-
451
- function errorMessage(error) {
452
- return error instanceof Error ? error.message : String(error || 'Unknown error')
453
- }
454
-
455
- window.DashboardPages = window.DashboardPages || {}
456
- window.DashboardPages.knowledge = renderKnowledge
457
- })()