@dotdrelle/wiki-manager 0.12.1 → 0.12.8
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +49 -8
- package/bin/wiki-manager +23 -12
- package/docker-compose.yml +0 -1
- package/mcp.endpoints.example.json +0 -6
- package/package.json +3 -2
- package/src/activity/activityAggregator.js +34 -3
- package/src/activity/activityAggregator.test.js +32 -0
- package/src/agent/graph.js +272 -22
- package/src/agent/graph.test.js +357 -1
- package/src/cli/wiki-manager.js +33 -2
- package/src/commands/slash.js +74 -1
- package/src/commands/slash.test.js +36 -0
- package/src/core/activity.js +4 -0
- package/src/core/activity.test.js +9 -1
- package/src/core/agentEvents.js +30 -0
- package/src/core/agentEvents.test.js +42 -1
- package/src/core/buildInfo.js +58 -0
- package/src/core/buildInfo.json +4 -0
- package/src/core/buildInfo.test.js +14 -0
- package/src/core/env.js +30 -1
- package/src/core/mcp.js +21 -1
- package/src/core/mcp.test.js +25 -0
- package/src/core/runtimeLog.js +6 -1
- package/src/core/runtimeLog.test.js +3 -1
- package/src/runtime/client.js +22 -0
- package/src/runtime/controlMessages.js +2 -2
- package/src/runtime/recoveryManager.js +54 -0
- package/src/runtime/recoveryManager.test.js +73 -0
- package/src/runtime/runner.js +49 -13
- package/src/runtime/runner.test.js +196 -0
- package/src/runtime/server.js +67 -8
- package/src/runtime/server.test.js +223 -6
- package/src/runtime/store.js +48 -3
- package/src/runtime/store.test.js +32 -0
- package/src/runtime/supervisor.js +77 -1
- package/src/shell/RightPane.tsx +124 -31
- package/src/shell/SetupWizard.tsx +13 -1
- package/src/shell/repl.js +78 -9
- package/src/shell/repl.test.js +114 -1
- package/src/shell/tui.tsx +4 -1
- package/src/shell/useAgent.ts +32 -3
- package/src/shell/useSession.ts +14 -1
- package/wiki-workspace +33 -0
package/README.md
CHANGED
|
@@ -36,6 +36,44 @@ everything — either with the mouse in a browser, or by talking to an assistant
|
|
|
36
36
|
A **workspace** = a project. Each project is isolated: its documents, settings,
|
|
37
37
|
and results never get mixed up with the others.
|
|
38
38
|
|
|
39
|
+
## Installation and command modes
|
|
40
|
+
|
|
41
|
+
The package can be installed either locally in a project or globally. The
|
|
42
|
+
command used afterwards depends on the installation mode.
|
|
43
|
+
|
|
44
|
+
### Local installation
|
|
45
|
+
|
|
46
|
+
Use a local installation when the manager should be pinned in a project's
|
|
47
|
+
`package.json`:
|
|
48
|
+
|
|
49
|
+
```bash
|
|
50
|
+
npm install @dotdrelle/wiki-manager
|
|
51
|
+
npx wiki-manager
|
|
52
|
+
npx wiki-workspace --help
|
|
53
|
+
```
|
|
54
|
+
|
|
55
|
+
`npm install` does not add `wiki-manager` or `wiki-workspace` to the shell's
|
|
56
|
+
global `PATH`. Run local executables with `npx` (or `npm exec wiki-manager` and
|
|
57
|
+
`npm exec wiki-workspace`). Bun is installed automatically as a package runtime;
|
|
58
|
+
you do not need to add `~/.bun/bin` to `PATH`.
|
|
59
|
+
|
|
60
|
+
### Global installation
|
|
61
|
+
|
|
62
|
+
Use a global installation when the commands should be available directly from
|
|
63
|
+
any directory:
|
|
64
|
+
|
|
65
|
+
```bash
|
|
66
|
+
npm install --global @dotdrelle/wiki-manager
|
|
67
|
+
wiki-manager
|
|
68
|
+
wiki-workspace --help
|
|
69
|
+
```
|
|
70
|
+
|
|
71
|
+
The global installation also installs the required Bun runtime. A separately
|
|
72
|
+
installed Bun remains supported, but is not required.
|
|
73
|
+
|
|
74
|
+
In both modes, launch the commands from the directory that should hold the
|
|
75
|
+
manager state (`workspaces/`, `.env`, and `mcp.endpoints.json`).
|
|
76
|
+
|
|
39
77
|
## Functional overview
|
|
40
78
|
|
|
41
79
|
The diagram below shows the whole picture at a glance: how **inputs** (external
|
|
@@ -54,14 +92,17 @@ chat** — all on the **shipped example**, with **no external source to
|
|
|
54
92
|
configure**. External agents (Confluence, mail…) come later, only when you plug
|
|
55
93
|
in real sources.
|
|
56
94
|
|
|
57
|
-
> **Prerequisites:** Docker running and Node ≥ 22.
|
|
95
|
+
> **Prerequisites:** Docker running and Node ≥ 22. Bun is installed with the npm
|
|
96
|
+
> package.
|
|
58
97
|
|
|
59
|
-
**1 — Install
|
|
98
|
+
**1 — Install globally, pick a home folder.**
|
|
60
99
|
The manager keeps its state (workspaces, `.env`, endpoints) in the directory
|
|
61
|
-
where you launch it, so give it a home
|
|
100
|
+
where you launch it, so give it a home. This quick start uses the global mode;
|
|
101
|
+
see [Installation and command modes](#installation-and-command-modes) for the
|
|
102
|
+
local `npm install` + `npx` mode.
|
|
62
103
|
|
|
63
104
|
```bash
|
|
64
|
-
npm
|
|
105
|
+
npm install --global @dotdrelle/wiki-manager
|
|
65
106
|
mkdir -p ~/llm-wiki && cd ~/llm-wiki # all manager state lives here
|
|
66
107
|
```
|
|
67
108
|
|
|
@@ -151,7 +192,7 @@ wiki-workspace wiki demo build # or, in the shell: /skills run pipeli
|
|
|
151
192
|
That's the whole loop. Next: the four ways to use it and how to configure the
|
|
152
193
|
external agents (CME & co.) live in [docs/usage.md](https://raw.githubusercontent.com/dotdrelle/llm-wiki-manager/main/docs/usage.md); the detailed
|
|
153
194
|
story is in [The journey](#the-journey-from-first-launch-to-first-result); and
|
|
154
|
-
installing from source is in [
|
|
195
|
+
installing from source is in [Installing from source](#installing-from-source).
|
|
155
196
|
|
|
156
197
|
## The journey: from first launch to first result
|
|
157
198
|
|
|
@@ -379,15 +420,15 @@ root `.env`; the wiki's **LLM keys** live in each workspace `.wikirc.yaml`.
|
|
|
379
420
|
See the full, field-by-field reference in
|
|
380
421
|
**[docs/configuration.md](https://raw.githubusercontent.com/dotdrelle/llm-wiki-manager/main/docs/configuration.md)**.
|
|
381
422
|
|
|
382
|
-
##
|
|
423
|
+
## Installing from source
|
|
383
424
|
|
|
384
425
|
```bash
|
|
385
426
|
corepack enable
|
|
386
427
|
pnpm install
|
|
387
428
|
```
|
|
388
429
|
|
|
389
|
-
|
|
390
|
-
the package, in the directory where the command is launched:
|
|
430
|
+
Whether installed locally, globally, or from source, `wiki-manager` keeps its
|
|
431
|
+
state outside the package, in the directory where the command is launched:
|
|
391
432
|
|
|
392
433
|
```text
|
|
393
434
|
./workspaces/ # workspace registry
|
package/bin/wiki-manager
CHANGED
|
@@ -39,7 +39,26 @@ if [[ -n "$CACERT_PATH" ]]; then
|
|
|
39
39
|
export CURL_CA_BUNDLE="$CACERT_PATH"
|
|
40
40
|
fi
|
|
41
41
|
|
|
42
|
+
SCRIPT_SOURCE="${BASH_SOURCE[0]}"
|
|
43
|
+
while [[ -L "$SCRIPT_SOURCE" ]]; do
|
|
44
|
+
SCRIPT_DIR="$(cd "$(dirname "$SCRIPT_SOURCE")" && pwd)"
|
|
45
|
+
SCRIPT_TARGET="$(readlink "$SCRIPT_SOURCE")"
|
|
46
|
+
if [[ "$SCRIPT_TARGET" = /* ]]; then
|
|
47
|
+
SCRIPT_SOURCE="$SCRIPT_TARGET"
|
|
48
|
+
else
|
|
49
|
+
SCRIPT_SOURCE="$SCRIPT_DIR/$SCRIPT_TARGET"
|
|
50
|
+
fi
|
|
51
|
+
done
|
|
52
|
+
BIN_DIR="$(cd "$(dirname "$SCRIPT_SOURCE")" && pwd)"
|
|
53
|
+
PACKAGE_DIR="$(cd "$BIN_DIR/.." && pwd)"
|
|
54
|
+
|
|
42
55
|
BUN_BIN="$(command -v bun 2>/dev/null || true)"
|
|
56
|
+
if [[ -z "$BUN_BIN" && -x "$PACKAGE_DIR/node_modules/.bin/bun" ]]; then
|
|
57
|
+
BUN_BIN="$PACKAGE_DIR/node_modules/.bin/bun"
|
|
58
|
+
fi
|
|
59
|
+
if [[ -z "$BUN_BIN" && -x "$PACKAGE_DIR/../../.bin/bun" ]]; then
|
|
60
|
+
BUN_BIN="$PACKAGE_DIR/../../.bin/bun"
|
|
61
|
+
fi
|
|
43
62
|
if [[ -z "$BUN_BIN" && -n "${BUN_INSTALL:-}" && -x "$BUN_INSTALL/bin/bun" ]]; then
|
|
44
63
|
BUN_BIN="$BUN_INSTALL/bin/bun"
|
|
45
64
|
fi
|
|
@@ -49,20 +68,12 @@ fi
|
|
|
49
68
|
if [[ -z "$BUN_BIN" ]]; then
|
|
50
69
|
printf '%s\n' \
|
|
51
70
|
'wiki-manager requires Bun >= 1.2.' \
|
|
52
|
-
'
|
|
71
|
+
'Reinstall @dotdrelle/wiki-manager or install Bun from https://bun.sh/docs/installation.' >&2
|
|
53
72
|
exit 127
|
|
54
73
|
fi
|
|
55
74
|
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
SCRIPT_TARGET="$(readlink "$SCRIPT_SOURCE")"
|
|
60
|
-
if [[ "$SCRIPT_TARGET" = /* ]]; then
|
|
61
|
-
SCRIPT_SOURCE="$SCRIPT_TARGET"
|
|
62
|
-
else
|
|
63
|
-
SCRIPT_SOURCE="$SCRIPT_DIR/$SCRIPT_TARGET"
|
|
64
|
-
fi
|
|
65
|
-
done
|
|
66
|
-
BIN_DIR="$(cd "$(dirname "$SCRIPT_SOURCE")" && pwd)"
|
|
75
|
+
if [[ ${#ARGS[@]} -eq 0 ]]; then
|
|
76
|
+
exec "$BUN_BIN" "$BIN_DIR/wiki-manager.js"
|
|
77
|
+
fi
|
|
67
78
|
|
|
68
79
|
exec "$BUN_BIN" "$BIN_DIR/wiki-manager.js" "${ARGS[@]}"
|
package/docker-compose.yml
CHANGED
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@dotdrelle/wiki-manager",
|
|
3
|
-
"version": "0.12.
|
|
3
|
+
"version": "0.12.8",
|
|
4
4
|
"description": "Agentic shell and orchestration cockpit for llm-wiki workspaces.",
|
|
5
5
|
"license": "PolyForm-Noncommercial-1.0.0",
|
|
6
6
|
"author": "dotrelle",
|
|
@@ -11,7 +11,7 @@
|
|
|
11
11
|
},
|
|
12
12
|
"scripts": {
|
|
13
13
|
"start": "bun ./bin/wiki-manager.js",
|
|
14
|
-
"test": "node --test src/agent/graph.test.js src/contracts/schemas.test.js src/core/activity.test.js src/core/agentEvents.test.js src/core/runtimeLog.test.js src/activity/activityAggregator.test.js src/graph/runGraphProjector.test.js src/core/workflow.test.js src/core/planPatch.test.js src/core/agentLoop.test.js src/core/plan.test.js src/core/mcp.test.js src/core/documentIntake.test.js src/core/dockerCompose.test.js src/core/wikiWorkspace.test.js src/core/wikirc.test.js src/core/modelFetch.test.js src/core/startupCheck.test.js src/core/queueStore.test.js src/orchestrator/agentRegistry.test.js src/orchestrator/capabilityRegistry.test.js src/orchestrator/capabilityResolver.test.js src/orchestrator/planValidator.test.js src/orchestrator/planIntegrator.test.js src/orchestrator/scheduler.test.js src/orchestrator/attemptManager.test.js src/orchestrator/resultAggregator.test.js src/orchestrator/approvalPolicy.test.js src/commands/slash.test.js src/shell/repl.test.js src/runtime/store.test.js src/runtime/controlMessages.test.js src/runtime/recoveryManager.test.js src/runtime/server.test.js src/runtime/supervisor.test.js src/runtime/runner.test.js src/runtime/runner.e2e.test.js src/runtime/donna-contract.test.js src/runtime/auth.test.js",
|
|
14
|
+
"test": "node --test src/agent/graph.test.js src/contracts/schemas.test.js src/core/activity.test.js src/core/buildInfo.test.js src/core/agentEvents.test.js src/core/runtimeLog.test.js src/activity/activityAggregator.test.js src/graph/runGraphProjector.test.js src/core/workflow.test.js src/core/planPatch.test.js src/core/agentLoop.test.js src/core/plan.test.js src/core/mcp.test.js src/core/documentIntake.test.js src/core/dockerCompose.test.js src/core/wikiWorkspace.test.js src/core/wikirc.test.js src/core/modelFetch.test.js src/core/startupCheck.test.js src/core/queueStore.test.js src/orchestrator/agentRegistry.test.js src/orchestrator/capabilityRegistry.test.js src/orchestrator/capabilityResolver.test.js src/orchestrator/planValidator.test.js src/orchestrator/planIntegrator.test.js src/orchestrator/scheduler.test.js src/orchestrator/attemptManager.test.js src/orchestrator/resultAggregator.test.js src/orchestrator/approvalPolicy.test.js src/commands/slash.test.js src/shell/repl.test.js src/runtime/store.test.js src/runtime/controlMessages.test.js src/runtime/recoveryManager.test.js src/runtime/server.test.js src/runtime/supervisor.test.js src/runtime/runner.test.js src/runtime/runner.e2e.test.js src/runtime/donna-contract.test.js src/runtime/auth.test.js",
|
|
15
15
|
"check-versions": "node scripts/check-versions.js",
|
|
16
16
|
"prepack": "node scripts/check-versions.js",
|
|
17
17
|
"prepublishOnly": "node scripts/check-versions.js",
|
|
@@ -49,6 +49,7 @@
|
|
|
49
49
|
"@langchain/langgraph": "^1.3.2",
|
|
50
50
|
"@opentui/core": "^0.3.2",
|
|
51
51
|
"@opentui/solid": "^0.3.2",
|
|
52
|
+
"bun": "^1.3.14",
|
|
52
53
|
"marked": "^15.0.12",
|
|
53
54
|
"marked-terminal": "^7.3.0",
|
|
54
55
|
"openai": "^6.42.0",
|
|
@@ -10,9 +10,18 @@ export function aggregateActivity(state = {}, events = []) {
|
|
|
10
10
|
const activities = Array.isArray(state.activities) ? state.activities : [];
|
|
11
11
|
const progress = calculateWeightedProgress(tasks, activities);
|
|
12
12
|
const groups = groupTasks(tasks);
|
|
13
|
+
const deduped = deduplicateActivities(activities);
|
|
14
|
+
// Group lines only cover activities attached to plan tasks. An activity
|
|
15
|
+
// started OUTSIDE the plan (e.g. the agent calls production_start_job
|
|
16
|
+
// directly after a minimal one-step plan) must still be visible: without
|
|
17
|
+
// this, the panel showed a done "production_status" step while the actual
|
|
18
|
+
// ingest ran invisibly at 15%.
|
|
13
19
|
const lines = groups.length > 0
|
|
14
|
-
?
|
|
15
|
-
|
|
20
|
+
? [
|
|
21
|
+
...groups.map((group) => groupLine(group, activities)),
|
|
22
|
+
...unattachedActivities(tasks, deduped).map(activityLine),
|
|
23
|
+
]
|
|
24
|
+
: deduped.map(activityLine);
|
|
16
25
|
return {
|
|
17
26
|
initialSynthesis: initialSynthesisFromState(state, events),
|
|
18
27
|
progress,
|
|
@@ -20,6 +29,21 @@ export function aggregateActivity(state = {}, events = []) {
|
|
|
20
29
|
};
|
|
21
30
|
}
|
|
22
31
|
|
|
32
|
+
function unattachedActivities(tasks, activities) {
|
|
33
|
+
const attachedKeys = new Set(tasks
|
|
34
|
+
.flatMap((task) => [task.activityKey, task.ownerActivityKey, task._activityKey])
|
|
35
|
+
.filter(Boolean)
|
|
36
|
+
.map(String));
|
|
37
|
+
const taskIds = new Set(tasks.map((task) => String(task.id ?? task.step ?? '')).filter(Boolean));
|
|
38
|
+
return activities.filter((activity) => {
|
|
39
|
+
const keys = [activity.key, activity.id].filter(Boolean).map(String);
|
|
40
|
+
if (keys.some((value) => attachedKeys.has(value))) return false;
|
|
41
|
+
const stepId = String(activity?.progress?.stepId ?? '');
|
|
42
|
+
if (stepId && taskIds.has(stepId)) return false;
|
|
43
|
+
return true;
|
|
44
|
+
});
|
|
45
|
+
}
|
|
46
|
+
|
|
23
47
|
function groupTasks(tasks) {
|
|
24
48
|
const groups = new Map();
|
|
25
49
|
for (const task of tasks) {
|
|
@@ -70,11 +94,18 @@ function groupLine(group, activities) {
|
|
|
70
94
|
status = `${done}/${total}`;
|
|
71
95
|
}
|
|
72
96
|
const agents = activeAgents > 0 ? ` - ${activeAgents} agent${activeAgents > 1 ? 's' : ''}` : '';
|
|
97
|
+
// While a task is running, expose ITS live progress as the group percent.
|
|
98
|
+
// The completion ratio (done/total tasks) said 0% while the label showed
|
|
99
|
+
// the real activity progress ("— 1 %"), so the TUI badge contradicted the
|
|
100
|
+
// text. Fall back to the task-completion ratio when nothing is running.
|
|
101
|
+
const percent = running.length > 0 && activeProgress != null
|
|
102
|
+
? Math.round(activeProgress)
|
|
103
|
+
: (total > 0 ? Math.round((done / total) * 100) : null);
|
|
73
104
|
return {
|
|
74
105
|
id: `group:${group.id}`,
|
|
75
106
|
label: `${icon} ${group.label} - ${status}${agents}`,
|
|
76
107
|
status,
|
|
77
|
-
progress: { done, total, percent
|
|
108
|
+
progress: { done, total, percent },
|
|
78
109
|
activeAgents,
|
|
79
110
|
};
|
|
80
111
|
}
|
|
@@ -58,3 +58,35 @@ test('aggregateActivity exposes initial synthesis and grouped display lines', ()
|
|
|
58
58
|
assert.ok(activity.lines.some((line) => /\[\.\.\.\] customer-data\.enrich - 63 %/.test(line.label)));
|
|
59
59
|
assert.ok(activity.lines.some((line) => /\[ \] publish - en attente/.test(line.label)));
|
|
60
60
|
});
|
|
61
|
+
|
|
62
|
+
test('aggregateActivity keeps activities not attached to any plan task visible', () => {
|
|
63
|
+
// Regression: a done one-step minimal plan (production_status) masked the
|
|
64
|
+
// actually-running ingest activity started outside the plan.
|
|
65
|
+
const state = {
|
|
66
|
+
plan: [{
|
|
67
|
+
id: 'status-check',
|
|
68
|
+
step: 1,
|
|
69
|
+
description: 'production.production_status',
|
|
70
|
+
status: 'done',
|
|
71
|
+
groupId: '1',
|
|
72
|
+
}],
|
|
73
|
+
activities: [
|
|
74
|
+
{
|
|
75
|
+
key: 'production:prod_192444',
|
|
76
|
+
id: 'prod_192444',
|
|
77
|
+
label: 'Ingest b87acaf6-Comite.md',
|
|
78
|
+
source: 'production',
|
|
79
|
+
status: 'running',
|
|
80
|
+
terminal: false,
|
|
81
|
+
progress: { percent: 15, detail: 'LLM running' },
|
|
82
|
+
},
|
|
83
|
+
],
|
|
84
|
+
};
|
|
85
|
+
|
|
86
|
+
const aggregated = aggregateActivity(state, []);
|
|
87
|
+
const labels = aggregated.lines.map((line) => line.label).join('\n');
|
|
88
|
+
assert.match(labels, /\[x\] .* done/, 'the done plan group stays visible');
|
|
89
|
+
assert.match(labels, /Ingest b87acaf6/, 'the unattached running ingest must appear');
|
|
90
|
+
const ingestLine = aggregated.lines.find((line) => /Ingest/.test(line.label));
|
|
91
|
+
assert.equal(ingestLine.status, 'running');
|
|
92
|
+
});
|