@clawstore/clawstore 1.0.6 → 1.0.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/dist/src/cli.d.ts.map +1 -1
- package/dist/src/cli.js +3 -1
- package/dist/src/cli.js.map +1 -1
- package/dist/src/commands.d.ts.map +1 -1
- package/dist/src/commands.js +2 -1
- package/dist/src/commands.js.map +1 -1
- package/dist/src/core/agent-register.d.ts +6 -0
- package/dist/src/core/agent-register.d.ts.map +1 -0
- package/dist/src/core/agent-register.js +73 -0
- package/dist/src/core/agent-register.js.map +1 -0
- package/dist/src/core/api-health.d.ts +9 -0
- package/dist/src/core/api-health.d.ts.map +1 -0
- package/dist/src/core/api-health.js +17 -0
- package/dist/src/core/api-health.js.map +1 -0
- package/dist/src/core/diagnostics.d.ts +7 -0
- package/dist/src/core/diagnostics.d.ts.map +1 -0
- package/dist/src/core/diagnostics.js +145 -0
- package/dist/src/core/diagnostics.js.map +1 -0
- package/dist/src/core/openclaw-profile.d.ts +6 -0
- package/dist/src/core/openclaw-profile.d.ts.map +1 -0
- package/dist/src/core/openclaw-profile.js +12 -0
- package/dist/src/core/openclaw-profile.js.map +1 -0
- package/dist/src/core/skill-installer.d.ts +1 -1
- package/dist/src/core/skill-installer.d.ts.map +1 -1
- package/dist/src/core/skill-installer.js +5 -25
- package/dist/src/core/skill-installer.js.map +1 -1
- package/dist/src/core/store-client.d.ts +0 -11
- package/dist/src/core/store-client.d.ts.map +1 -1
- package/dist/src/core/store-client.js +0 -19
- package/dist/src/core/store-client.js.map +1 -1
- package/dist/src/core/workspace.d.ts +0 -18
- package/dist/src/core/workspace.d.ts.map +1 -1
- package/dist/src/core/workspace.js +4 -195
- package/dist/src/core/workspace.js.map +1 -1
- package/openclaw.plugin.json +1 -1
- package/package.json +9 -3
- package/src/cli.ts +3 -1
- package/src/commands.ts +2 -1
- package/src/core/agent-register.ts +79 -0
- package/src/core/api-health.ts +17 -0
- package/src/core/diagnostics.ts +163 -0
- package/src/core/openclaw-profile.ts +10 -0
- package/src/core/skill-installer.ts +6 -27
- package/src/core/store-client.ts +0 -21
- package/src/core/workspace.ts +3 -219
- package/dist/src/__tests__/cli-sim.test.d.ts +0 -9
- package/dist/src/__tests__/cli-sim.test.d.ts.map +0 -1
- package/dist/src/__tests__/cli-sim.test.js +0 -275
- package/dist/src/__tests__/cli-sim.test.js.map +0 -1
- package/dist/src/__tests__/e2e.test.d.ts +0 -10
- package/dist/src/__tests__/e2e.test.d.ts.map +0 -1
- package/dist/src/__tests__/e2e.test.js +0 -159
- package/dist/src/__tests__/e2e.test.js.map +0 -1
- package/src/__tests__/cli-sim.test.ts +0 -303
- package/src/__tests__/e2e.test.ts +0 -186
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"store-client.d.ts","sourceRoot":"","sources":["../../../src/core/store-client.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EACV,iBAAiB,EACjB,gBAAgB,EAEhB,eAAe,EAChB,MAAM,aAAa,CAAC;AAGrB;;;;;;GAMG;AACH,qBAAa,WAAW;IACtB,OAAO,CAAC,OAAO,CAAS;IACxB,OAAO,CAAC,SAAS,CAAuB;gBAE5B,MAAM,CAAC,EAAE,OAAO,CAAC,eAAe,CAAC;IAI7C,YAAY,CAAC,KAAK,EAAE,MAAM,GAAG,IAAI;IAIjC,OAAO,CAAC,OAAO;YAWD,OAAO;IAgBf,MAAM,CAAC,KAAK,EAAE,MAAM,EAAE,IAAI,CAAC,EAAE;QACjC,QAAQ,CAAC,EAAE,MAAM,CAAC;QAClB,IAAI,CAAC,EAAE,MAAM,CAAC;QACd,KAAK,CAAC,EAAE,MAAM,CAAC;KAChB,GAAG,OAAO,CAAC,iBAAiB,CAAC;IAWxB,cAAc,CAAC,OAAO,EAAE,MAAM,GAAG,OAAO,CAAC,gBAAgB,CAAC;IAM1D,cAAc,CAAC,OAAO,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,CAAC;IAOhD,YAAY,CAAC,SAAS,EAAE,MAAM,EAAE,QAAQ,EAAE;QAC9C,IAAI,EAAE,MAAM,CAAC;QACb,WAAW,EAAE,MAAM,CAAC;QACpB,QAAQ,EAAE,MAAM,CAAC;QACjB,KAAK,EAAE,MAAM,CAAC;QACd,QAAQ,EAAE,MAAM,CAAC;KAClB,GAAG,OAAO,CAAC;QAAE,OAAO,EAAE,MAAM,CAAC;QAAC,OAAO,EAAE,MAAM,CAAA;KAAE,CAAC;IAyB3C,KAAK,CAAC,KAAK,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM,GAAG,OAAO,CAAC;QAAE,KAAK,EAAE,MAAM,CAAC;QAAC,IAAI,EAAE;YAAE,EAAE,EAAE,MAAM,CAAC;YAAC,IAAI,EAAE,MAAM,CAAA;SAAE,CAAA;KAAE,CAAC;IAOtG,MAAM,IAAI,OAAO,CAAC;QAAE,EAAE,EAAE,MAAM,CAAC;QAAC,IAAI,EAAE,MAAM,CAAC;QAAC,KAAK,EAAE,MAAM,CAAA;KAAE,GAAG,IAAI,CAAC;IAWrE,WAAW,IAAI,OAAO,CAAC,OAAO,CAAC;CAQtC
|
|
1
|
+
{"version":3,"file":"store-client.d.ts","sourceRoot":"","sources":["../../../src/core/store-client.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EACV,iBAAiB,EACjB,gBAAgB,EAEhB,eAAe,EAChB,MAAM,aAAa,CAAC;AAGrB;;;;;;GAMG;AACH,qBAAa,WAAW;IACtB,OAAO,CAAC,OAAO,CAAS;IACxB,OAAO,CAAC,SAAS,CAAuB;gBAE5B,MAAM,CAAC,EAAE,OAAO,CAAC,eAAe,CAAC;IAI7C,YAAY,CAAC,KAAK,EAAE,MAAM,GAAG,IAAI;IAIjC,OAAO,CAAC,OAAO;YAWD,OAAO;IAgBf,MAAM,CAAC,KAAK,EAAE,MAAM,EAAE,IAAI,CAAC,EAAE;QACjC,QAAQ,CAAC,EAAE,MAAM,CAAC;QAClB,IAAI,CAAC,EAAE,MAAM,CAAC;QACd,KAAK,CAAC,EAAE,MAAM,CAAC;KAChB,GAAG,OAAO,CAAC,iBAAiB,CAAC;IAWxB,cAAc,CAAC,OAAO,EAAE,MAAM,GAAG,OAAO,CAAC,gBAAgB,CAAC;IAM1D,cAAc,CAAC,OAAO,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,CAAC;IAOhD,YAAY,CAAC,SAAS,EAAE,MAAM,EAAE,QAAQ,EAAE;QAC9C,IAAI,EAAE,MAAM,CAAC;QACb,WAAW,EAAE,MAAM,CAAC;QACpB,QAAQ,EAAE,MAAM,CAAC;QACjB,KAAK,EAAE,MAAM,CAAC;QACd,QAAQ,EAAE,MAAM,CAAC;KAClB,GAAG,OAAO,CAAC;QAAE,OAAO,EAAE,MAAM,CAAC;QAAC,OAAO,EAAE,MAAM,CAAA;KAAE,CAAC;IAyB3C,KAAK,CAAC,KAAK,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM,GAAG,OAAO,CAAC;QAAE,KAAK,EAAE,MAAM,CAAC;QAAC,IAAI,EAAE;YAAE,EAAE,EAAE,MAAM,CAAC;YAAC,IAAI,EAAE,MAAM,CAAA;SAAE,CAAA;KAAE,CAAC;IAOtG,MAAM,IAAI,OAAO,CAAC;QAAE,EAAE,EAAE,MAAM,CAAC;QAAC,IAAI,EAAE,MAAM,CAAC;QAAC,KAAK,EAAE,MAAM,CAAA;KAAE,GAAG,IAAI,CAAC;IAWrE,WAAW,IAAI,OAAO,CAAC,OAAO,CAAC;CAQtC"}
|
|
@@ -108,23 +108,4 @@ export class StoreClient {
|
|
|
108
108
|
}
|
|
109
109
|
}
|
|
110
110
|
}
|
|
111
|
-
/**
|
|
112
|
-
* GET {apiBaseUrl}/health for `clawstore doctor` diagnostics.
|
|
113
|
-
*
|
|
114
|
-
* Lives here (not workspace.ts) because OpenClaw's plugin scanner treats
|
|
115
|
-
* `process.env` + `fetch` in the same file as a possible credential-harvesting
|
|
116
|
-
* pattern; workspace.ts reads OPENCLAW_PROFILE and must not import fetch.
|
|
117
|
-
*/
|
|
118
|
-
export async function checkClawstoreApiReachable(apiBaseUrl) {
|
|
119
|
-
const base = apiBaseUrl.replace(/\/+$/, "");
|
|
120
|
-
try {
|
|
121
|
-
const res = await fetch(`${base}/health`, { signal: AbortSignal.timeout(5000) });
|
|
122
|
-
if (res.ok)
|
|
123
|
-
return { ok: true, detail: "reachable" };
|
|
124
|
-
return { ok: false, detail: `HTTP ${res.status}` };
|
|
125
|
-
}
|
|
126
|
-
catch (err) {
|
|
127
|
-
return { ok: false, detail: `unreachable (${err.message})` };
|
|
128
|
-
}
|
|
129
|
-
}
|
|
130
111
|
//# sourceMappingURL=store-client.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"store-client.js","sourceRoot":"","sources":["../../../src/core/store-client.ts"],"names":[],"mappings":"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
|
|
1
|
+
{"version":3,"file":"store-client.js","sourceRoot":"","sources":["../../../src/core/store-client.ts"],"names":[],"mappings":"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"}
|
|
@@ -1,4 +1,3 @@
|
|
|
1
|
-
import type { DiagnosticReport } from "../types.js";
|
|
2
1
|
/**
|
|
3
2
|
* Resolve the workspace directory for a given OpenClaw agent.
|
|
4
3
|
*
|
|
@@ -18,21 +17,4 @@ export declare function resolveWorkspace(agent?: string): Promise<string>;
|
|
|
18
17
|
* Clawstore. Returns agent names (e.g. ["main", "sales"]).
|
|
19
18
|
*/
|
|
20
19
|
export declare function listClawstoreAgents(): Promise<string[]>;
|
|
21
|
-
/**
|
|
22
|
-
* Run a full diagnostic for a specific OpenClaw agent.
|
|
23
|
-
*/
|
|
24
|
-
export declare function diagnose(apiBaseUrl?: string, agent?: string): Promise<DiagnosticReport>;
|
|
25
|
-
/**
|
|
26
|
-
* Check whether the given OpenClaw agent is registered in openclaw.json.
|
|
27
|
-
* If not, automatically register it via `openclaw agents add` so that
|
|
28
|
-
* `clawstore install --agent <name>` works without a prior manual step.
|
|
29
|
-
*
|
|
30
|
-
* Returns `true` if the agent was already registered or was successfully
|
|
31
|
-
* created; `false` if auto-registration failed.
|
|
32
|
-
*/
|
|
33
|
-
export declare function ensureAgentRegistered(agent: string, log?: (msg: string) => void): Promise<boolean>;
|
|
34
|
-
/**
|
|
35
|
-
* Format a diagnostic report for CLI output.
|
|
36
|
-
*/
|
|
37
|
-
export declare function formatDiagnosticReport(report: DiagnosticReport): string;
|
|
38
20
|
//# sourceMappingURL=workspace.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"workspace.d.ts","sourceRoot":"","sources":["../../../src/core/workspace.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"workspace.d.ts","sourceRoot":"","sources":["../../../src/core/workspace.ts"],"names":[],"mappings":"AAWA;;;;;;;;;;;;GAYG;AACH,wBAAsB,gBAAgB,CAAC,KAAK,CAAC,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,CAAC,CAwCtE;AAUD;;;GAGG;AACH,wBAAsB,mBAAmB,IAAI,OAAO,CAAC,MAAM,EAAE,CAAC,CAoB7D"}
|
|
@@ -1,9 +1,8 @@
|
|
|
1
|
-
import { readFile, access, readdir
|
|
2
|
-
import { exec } from "node:child_process";
|
|
1
|
+
import { readFile, access, readdir } from "node:fs/promises";
|
|
3
2
|
import { join } from "node:path";
|
|
4
3
|
import { homedir } from "node:os";
|
|
5
|
-
import { OPENCLAW_HOME, CLAWSTORE_DIR, DEFAULT_AGENT,
|
|
6
|
-
import {
|
|
4
|
+
import { OPENCLAW_HOME, CLAWSTORE_DIR, DEFAULT_AGENT, agentRegistryFile, } from "../constants.js";
|
|
5
|
+
import { readOpenclawProfileLabel } from "./openclaw-profile.js";
|
|
7
6
|
/**
|
|
8
7
|
* Resolve the workspace directory for a given OpenClaw agent.
|
|
9
8
|
*
|
|
@@ -46,7 +45,7 @@ export async function resolveWorkspace(agent) {
|
|
|
46
45
|
// config not found or invalid — fall through
|
|
47
46
|
}
|
|
48
47
|
if (target === DEFAULT_AGENT) {
|
|
49
|
-
const profile =
|
|
48
|
+
const profile = readOpenclawProfileLabel();
|
|
50
49
|
if (profile !== "default") {
|
|
51
50
|
return join(OPENCLAW_HOME, `workspace-${profile}`);
|
|
52
51
|
}
|
|
@@ -68,11 +67,9 @@ function expandHome(p) {
|
|
|
68
67
|
*/
|
|
69
68
|
export async function listClawstoreAgents() {
|
|
70
69
|
const agents = [];
|
|
71
|
-
// "main" agent uses the root-level registry file
|
|
72
70
|
if (await exists(agentRegistryFile(DEFAULT_AGENT))) {
|
|
73
71
|
agents.push(DEFAULT_AGENT);
|
|
74
72
|
}
|
|
75
|
-
// Non-main agents live under clawstore/agents/<name>/
|
|
76
73
|
const agentsDir = join(CLAWSTORE_DIR, "agents");
|
|
77
74
|
if (await exists(agentsDir)) {
|
|
78
75
|
const entries = await readdir(agentsDir, { withFileTypes: true });
|
|
@@ -95,192 +92,4 @@ async function exists(p) {
|
|
|
95
92
|
return false;
|
|
96
93
|
}
|
|
97
94
|
}
|
|
98
|
-
async function dirItemCount(p) {
|
|
99
|
-
try {
|
|
100
|
-
const entries = await readdir(p);
|
|
101
|
-
return entries.length;
|
|
102
|
-
}
|
|
103
|
-
catch {
|
|
104
|
-
return -1;
|
|
105
|
-
}
|
|
106
|
-
}
|
|
107
|
-
/**
|
|
108
|
-
* Run a full diagnostic for a specific OpenClaw agent.
|
|
109
|
-
*/
|
|
110
|
-
export async function diagnose(apiBaseUrl, agent) {
|
|
111
|
-
const target = agent ?? DEFAULT_AGENT;
|
|
112
|
-
const checks = [];
|
|
113
|
-
let allOk = true;
|
|
114
|
-
const workspace = await resolveWorkspace(target);
|
|
115
|
-
const registryFile = agentRegistryFile(target);
|
|
116
|
-
const backupDir = agentBackupDir(target);
|
|
117
|
-
if (target !== DEFAULT_AGENT) {
|
|
118
|
-
checks.push({
|
|
119
|
-
label: "Target agent",
|
|
120
|
-
status: "ok",
|
|
121
|
-
detail: target,
|
|
122
|
-
});
|
|
123
|
-
}
|
|
124
|
-
// 1. OpenClaw home
|
|
125
|
-
const homeOk = await exists(OPENCLAW_HOME);
|
|
126
|
-
checks.push({
|
|
127
|
-
label: "OpenClaw home",
|
|
128
|
-
path: OPENCLAW_HOME,
|
|
129
|
-
status: homeOk ? "ok" : "fail",
|
|
130
|
-
detail: homeOk ? undefined : "NOT FOUND",
|
|
131
|
-
});
|
|
132
|
-
if (!homeOk)
|
|
133
|
-
allOk = false;
|
|
134
|
-
// 2. Workspace
|
|
135
|
-
const wsOk = await exists(workspace);
|
|
136
|
-
checks.push({
|
|
137
|
-
label: "Workspace",
|
|
138
|
-
path: workspace,
|
|
139
|
-
status: wsOk ? "ok" : "fail",
|
|
140
|
-
detail: wsOk ? undefined : "NOT FOUND",
|
|
141
|
-
});
|
|
142
|
-
if (!wsOk)
|
|
143
|
-
allOk = false;
|
|
144
|
-
// 3. Workspace files
|
|
145
|
-
for (const f of [...REQUIRED_FILES, ...OPTIONAL_FILES]) {
|
|
146
|
-
const fp = join(workspace, f);
|
|
147
|
-
const found = await exists(fp);
|
|
148
|
-
checks.push({
|
|
149
|
-
label: `Workspace file: ${f}`,
|
|
150
|
-
path: fp,
|
|
151
|
-
status: found ? "ok" : "warn",
|
|
152
|
-
detail: found ? "found" : "missing",
|
|
153
|
-
});
|
|
154
|
-
}
|
|
155
|
-
// 4. Registry
|
|
156
|
-
const regOk = await exists(registryFile);
|
|
157
|
-
if (regOk) {
|
|
158
|
-
try {
|
|
159
|
-
const raw = await readFile(registryFile, "utf-8");
|
|
160
|
-
const reg = JSON.parse(raw);
|
|
161
|
-
const count = Object.keys(reg.agents ?? {}).length;
|
|
162
|
-
checks.push({
|
|
163
|
-
label: "Agent registry",
|
|
164
|
-
path: registryFile,
|
|
165
|
-
status: "ok",
|
|
166
|
-
detail: `${count} agent(s) registered`,
|
|
167
|
-
});
|
|
168
|
-
}
|
|
169
|
-
catch {
|
|
170
|
-
checks.push({
|
|
171
|
-
label: "Agent registry",
|
|
172
|
-
path: registryFile,
|
|
173
|
-
status: "warn",
|
|
174
|
-
detail: "exists but cannot be parsed",
|
|
175
|
-
});
|
|
176
|
-
}
|
|
177
|
-
}
|
|
178
|
-
else {
|
|
179
|
-
checks.push({
|
|
180
|
-
label: "Agent registry",
|
|
181
|
-
path: registryFile,
|
|
182
|
-
status: "ok",
|
|
183
|
-
detail: "not created yet (OK for first run)",
|
|
184
|
-
});
|
|
185
|
-
}
|
|
186
|
-
// 5. Skills directory
|
|
187
|
-
const skillsDir = join(workspace, "skills");
|
|
188
|
-
const skillCount = await dirItemCount(skillsDir);
|
|
189
|
-
checks.push({
|
|
190
|
-
label: "Skills directory",
|
|
191
|
-
path: skillsDir,
|
|
192
|
-
status: skillCount >= 0 ? "ok" : "warn",
|
|
193
|
-
detail: skillCount >= 0 ? `${skillCount} skill(s)` : "NOT FOUND",
|
|
194
|
-
});
|
|
195
|
-
// 6. Backup directory
|
|
196
|
-
const backupCount = await dirItemCount(backupDir);
|
|
197
|
-
checks.push({
|
|
198
|
-
label: "Backup directory",
|
|
199
|
-
path: backupDir,
|
|
200
|
-
status: "ok",
|
|
201
|
-
detail: backupCount >= 0 ? `${backupCount} backup(s)` : "will be created on first install",
|
|
202
|
-
});
|
|
203
|
-
// 7. Cache directory
|
|
204
|
-
const cacheCount = await dirItemCount(join(CLAWSTORE_DIR, "cache"));
|
|
205
|
-
checks.push({
|
|
206
|
-
label: "Cache directory",
|
|
207
|
-
path: join(CLAWSTORE_DIR, "cache"),
|
|
208
|
-
status: "ok",
|
|
209
|
-
detail: cacheCount >= 0 ? `${cacheCount} item(s)` : "will be created on first install",
|
|
210
|
-
});
|
|
211
|
-
// 8. API connectivity (optional) — fetch lives in store-client.ts (see comment there)
|
|
212
|
-
if (apiBaseUrl) {
|
|
213
|
-
const { ok, detail } = await checkClawstoreApiReachable(apiBaseUrl);
|
|
214
|
-
checks.push({
|
|
215
|
-
label: "Clawstore API",
|
|
216
|
-
status: ok ? "ok" : "warn",
|
|
217
|
-
detail,
|
|
218
|
-
});
|
|
219
|
-
}
|
|
220
|
-
return { checks, allOk };
|
|
221
|
-
}
|
|
222
|
-
/**
|
|
223
|
-
* Check whether the given OpenClaw agent is registered in openclaw.json.
|
|
224
|
-
* If not, automatically register it via `openclaw agents add` so that
|
|
225
|
-
* `clawstore install --agent <name>` works without a prior manual step.
|
|
226
|
-
*
|
|
227
|
-
* Returns `true` if the agent was already registered or was successfully
|
|
228
|
-
* created; `false` if auto-registration failed.
|
|
229
|
-
*/
|
|
230
|
-
export async function ensureAgentRegistered(agent, log = console.log) {
|
|
231
|
-
if (agent === DEFAULT_AGENT)
|
|
232
|
-
return true;
|
|
233
|
-
const configFile = join(OPENCLAW_HOME, "openclaw.json");
|
|
234
|
-
try {
|
|
235
|
-
const raw = await readFile(configFile, "utf-8");
|
|
236
|
-
const config = JSON.parse(raw);
|
|
237
|
-
const inMap = config?.agents?.[agent] !== undefined ||
|
|
238
|
-
config?.agents?.entries?.[agent] !== undefined;
|
|
239
|
-
const inList = Array.isArray(config?.agents?.list) &&
|
|
240
|
-
config.agents.list.some((e) => e?.id === agent);
|
|
241
|
-
if (inMap || inList)
|
|
242
|
-
return true;
|
|
243
|
-
}
|
|
244
|
-
catch {
|
|
245
|
-
// config missing or unreadable — agent is definitely not registered
|
|
246
|
-
}
|
|
247
|
-
const workspace = join(OPENCLAW_HOME, `workspace-${agent}`);
|
|
248
|
-
try {
|
|
249
|
-
await mkdir(workspace, { recursive: true });
|
|
250
|
-
}
|
|
251
|
-
catch { /* directory may already exist */ }
|
|
252
|
-
log(`\n OpenClaw agent "${agent}" is not registered. Auto-registering ...`);
|
|
253
|
-
const cmd = `openclaw agents add ${agent} --workspace "${workspace}"`;
|
|
254
|
-
return new Promise((resolve) => {
|
|
255
|
-
exec(cmd, { timeout: 15_000 }, (err, stdout, stderr) => {
|
|
256
|
-
if (err) {
|
|
257
|
-
log(` Auto-register failed: ${err.message}`);
|
|
258
|
-
if (stderr)
|
|
259
|
-
log(` ${stderr.trim()}`);
|
|
260
|
-
log(` Please run manually: ${cmd}\n`);
|
|
261
|
-
resolve(false);
|
|
262
|
-
return;
|
|
263
|
-
}
|
|
264
|
-
log(` Registered agent "${agent}" → ${workspace}`);
|
|
265
|
-
resolve(true);
|
|
266
|
-
});
|
|
267
|
-
});
|
|
268
|
-
}
|
|
269
|
-
/**
|
|
270
|
-
* Format a diagnostic report for CLI output.
|
|
271
|
-
*/
|
|
272
|
-
export function formatDiagnosticReport(report) {
|
|
273
|
-
const lines = ["\n Clawstore Doctor\n"];
|
|
274
|
-
for (const c of report.checks) {
|
|
275
|
-
const icon = c.status === "ok" ? "OK" : c.status === "warn" ? "WARN" : "FAIL";
|
|
276
|
-
const pathPart = c.path ? ` ${c.path}` : "";
|
|
277
|
-
const detailPart = c.detail ? ` (${c.detail})` : "";
|
|
278
|
-
lines.push(` ${c.label}:${pathPart} ... ${icon}${detailPart}`);
|
|
279
|
-
}
|
|
280
|
-
lines.push("");
|
|
281
|
-
lines.push(report.allOk
|
|
282
|
-
? " All checks passed.\n"
|
|
283
|
-
: " Some issues found. Run `openclaw setup` to initialize missing directories.\n");
|
|
284
|
-
return lines.join("\n");
|
|
285
|
-
}
|
|
286
95
|
//# sourceMappingURL=workspace.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"workspace.js","sourceRoot":"","sources":["../../../src/core/workspace.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,QAAQ,EAAE,MAAM,EAAE,OAAO,
|
|
1
|
+
{"version":3,"file":"workspace.js","sourceRoot":"","sources":["../../../src/core/workspace.ts"],"names":[],"mappings":"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"}
|
package/openclaw.plugin.json
CHANGED
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@clawstore/clawstore",
|
|
3
|
-
"version": "1.0.
|
|
3
|
+
"version": "1.0.8",
|
|
4
4
|
"description": "Agent marketplace plugin for OpenClaw — browse, install, manage and pack AI employee agents.",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"main": "./index.ts",
|
|
@@ -16,7 +16,8 @@
|
|
|
16
16
|
"scripts": {
|
|
17
17
|
"build": "tsc",
|
|
18
18
|
"test": "node --import tsx src/__tests__/e2e.test.ts",
|
|
19
|
-
"
|
|
19
|
+
"clean": "node -e \"try{require('fs').rmSync('dist',{recursive:true,force:true})}catch(e){if(e.code!=='ENOENT')throw e}\"",
|
|
20
|
+
"prepack": "npm run clean && npm run build",
|
|
20
21
|
"pack:release": "npm pack --pack-destination ../../dist"
|
|
21
22
|
},
|
|
22
23
|
"dependencies": {
|
|
@@ -34,7 +35,12 @@
|
|
|
34
35
|
"files": [
|
|
35
36
|
"index.ts",
|
|
36
37
|
"openclaw.plugin.json",
|
|
37
|
-
"src",
|
|
38
|
+
"src/cli.ts",
|
|
39
|
+
"src/commands.ts",
|
|
40
|
+
"src/constants.ts",
|
|
41
|
+
"src/types.ts",
|
|
42
|
+
"src/core/*.ts",
|
|
43
|
+
"src/utils/*.ts",
|
|
38
44
|
"dist",
|
|
39
45
|
"typings"
|
|
40
46
|
]
|
package/src/cli.ts
CHANGED
|
@@ -17,7 +17,9 @@ import {
|
|
|
17
17
|
|
|
18
18
|
import { installAgent, updateAgent } from "./core/package-installer.js";
|
|
19
19
|
import { packAgent, packCurrentAgent } from "./core/packager.js";
|
|
20
|
-
import {
|
|
20
|
+
import { listClawstoreAgents } from "./core/workspace.js";
|
|
21
|
+
import { diagnose, formatDiagnosticReport } from "./core/diagnostics.js";
|
|
22
|
+
import { ensureAgentRegistered } from "./core/agent-register.js";
|
|
21
23
|
import { StoreClient } from "./core/store-client.js";
|
|
22
24
|
import { DEFAULT_API_BASE_URL, DEFAULT_AGENT, STORE_DOWNLOAD_BASE_URL } from "./constants.js";
|
|
23
25
|
import {
|
package/src/commands.ts
CHANGED
|
@@ -9,7 +9,8 @@ import {
|
|
|
9
9
|
disableAgent,
|
|
10
10
|
} from "./core/agent-manager.js";
|
|
11
11
|
import { installAgent } from "./core/package-installer.js";
|
|
12
|
-
import { diagnose
|
|
12
|
+
import { diagnose } from "./core/diagnostics.js";
|
|
13
|
+
import { ensureAgentRegistered } from "./core/agent-register.js";
|
|
13
14
|
|
|
14
15
|
/**
|
|
15
16
|
* Register the `/clawstore` slash command.
|
|
@@ -0,0 +1,79 @@
|
|
|
1
|
+
import { readFile, writeFile, mkdir } from "node:fs/promises";
|
|
2
|
+
import { join, dirname } from "node:path";
|
|
3
|
+
import { OPENCLAW_HOME, DEFAULT_AGENT } from "../constants.js";
|
|
4
|
+
|
|
5
|
+
function isRegistered(config: Record<string, unknown>, agent: string): boolean {
|
|
6
|
+
const agents = config.agents as Record<string, unknown> | undefined;
|
|
7
|
+
if (!agents || typeof agents !== "object") return false;
|
|
8
|
+
if (agents[agent] !== undefined) return true;
|
|
9
|
+
const entries = agents.entries as Record<string, unknown> | undefined;
|
|
10
|
+
if (entries && typeof entries === "object" && !Array.isArray(entries) && entries[agent] !== undefined) {
|
|
11
|
+
return true;
|
|
12
|
+
}
|
|
13
|
+
const list = agents.list;
|
|
14
|
+
if (Array.isArray(list) && list.some((e: { id?: string }) => e?.id === agent)) return true;
|
|
15
|
+
return false;
|
|
16
|
+
}
|
|
17
|
+
|
|
18
|
+
/**
|
|
19
|
+
* Ensure a non-main agent exists in openclaw.json (file-only; avoids shell subprocesses for plugin safety scans).
|
|
20
|
+
* Creates workspace-{agent} and merges `agents.entries` / `agents.list` as needed.
|
|
21
|
+
*/
|
|
22
|
+
export async function ensureAgentRegistered(
|
|
23
|
+
agent: string,
|
|
24
|
+
log: (msg: string) => void = console.log,
|
|
25
|
+
): Promise<boolean> {
|
|
26
|
+
if (agent === DEFAULT_AGENT) return true;
|
|
27
|
+
|
|
28
|
+
const configFile = join(OPENCLAW_HOME, "openclaw.json");
|
|
29
|
+
let config: Record<string, unknown> = {};
|
|
30
|
+
|
|
31
|
+
try {
|
|
32
|
+
const raw = await readFile(configFile, "utf-8");
|
|
33
|
+
config = JSON.parse(raw) as Record<string, unknown>;
|
|
34
|
+
if (isRegistered(config, agent)) return true;
|
|
35
|
+
} catch {
|
|
36
|
+
// missing or invalid — rewrite below
|
|
37
|
+
}
|
|
38
|
+
|
|
39
|
+
const workspace = join(OPENCLAW_HOME, `workspace-${agent}`);
|
|
40
|
+
try {
|
|
41
|
+
await mkdir(workspace, { recursive: true });
|
|
42
|
+
} catch { /* may exist */ }
|
|
43
|
+
|
|
44
|
+
log(`\n OpenClaw agent "${agent}" is not registered. Updating ${configFile} ...`);
|
|
45
|
+
|
|
46
|
+
try {
|
|
47
|
+
const raw = await readFile(configFile, "utf-8");
|
|
48
|
+
config = JSON.parse(raw) as Record<string, unknown>;
|
|
49
|
+
} catch {
|
|
50
|
+
config = {};
|
|
51
|
+
}
|
|
52
|
+
|
|
53
|
+
if (!config.agents || typeof config.agents !== "object" || Array.isArray(config.agents)) {
|
|
54
|
+
config.agents = {};
|
|
55
|
+
}
|
|
56
|
+
const agents = config.agents as Record<string, unknown>;
|
|
57
|
+
|
|
58
|
+
const entry = { workspace };
|
|
59
|
+
|
|
60
|
+
const prevEntries =
|
|
61
|
+
agents.entries && typeof agents.entries === "object" && !Array.isArray(agents.entries)
|
|
62
|
+
? { ...(agents.entries as Record<string, { workspace: string }>) }
|
|
63
|
+
: {};
|
|
64
|
+
prevEntries[agent] = entry;
|
|
65
|
+
agents.entries = prevEntries;
|
|
66
|
+
|
|
67
|
+
if (Array.isArray(agents.list)) {
|
|
68
|
+
const list = agents.list as Array<{ id?: string; workspace?: string }>;
|
|
69
|
+
const idx = list.findIndex((e) => e?.id === agent);
|
|
70
|
+
if (idx >= 0) list[idx] = { ...list[idx], id: agent, workspace };
|
|
71
|
+
else list.push({ id: agent, workspace });
|
|
72
|
+
}
|
|
73
|
+
|
|
74
|
+
await mkdir(dirname(configFile), { recursive: true });
|
|
75
|
+
await writeFile(configFile, `${JSON.stringify(config, null, 2)}\n`, "utf-8");
|
|
76
|
+
|
|
77
|
+
log(` Registered agent "${agent}" → ${workspace}`);
|
|
78
|
+
return true;
|
|
79
|
+
}
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Clawstore API GET /health — used only by clawstore doctor.
|
|
3
|
+
* Standalone module (no process/env reads) for OpenClaw plugin static analysis.
|
|
4
|
+
*/
|
|
5
|
+
export async function checkClawstoreApiReachable(apiBaseUrl: string): Promise<{
|
|
6
|
+
ok: boolean;
|
|
7
|
+
detail: string;
|
|
8
|
+
}> {
|
|
9
|
+
const base = apiBaseUrl.replace(/\/+$/, "");
|
|
10
|
+
try {
|
|
11
|
+
const res = await fetch(`${base}/health`, { signal: AbortSignal.timeout(5000) });
|
|
12
|
+
if (res.ok) return { ok: true, detail: "reachable" };
|
|
13
|
+
return { ok: false, detail: `HTTP ${res.status}` };
|
|
14
|
+
} catch (err) {
|
|
15
|
+
return { ok: false, detail: `unreachable (${(err as Error).message})` };
|
|
16
|
+
}
|
|
17
|
+
}
|
|
@@ -0,0 +1,163 @@
|
|
|
1
|
+
import { readFile, access, readdir } from "node:fs/promises";
|
|
2
|
+
import { join } from "node:path";
|
|
3
|
+
import {
|
|
4
|
+
OPENCLAW_HOME,
|
|
5
|
+
CLAWSTORE_DIR,
|
|
6
|
+
DEFAULT_AGENT,
|
|
7
|
+
REQUIRED_FILES,
|
|
8
|
+
OPTIONAL_FILES,
|
|
9
|
+
agentRegistryFile,
|
|
10
|
+
agentBackupDir,
|
|
11
|
+
} from "../constants.js";
|
|
12
|
+
import type { DiagnosticCheck, DiagnosticReport } from "../types.js";
|
|
13
|
+
import { resolveWorkspace } from "./workspace.js";
|
|
14
|
+
import { checkClawstoreApiReachable } from "./api-health.js";
|
|
15
|
+
|
|
16
|
+
async function pathExists(p: string): Promise<boolean> {
|
|
17
|
+
try {
|
|
18
|
+
await access(p);
|
|
19
|
+
return true;
|
|
20
|
+
} catch {
|
|
21
|
+
return false;
|
|
22
|
+
}
|
|
23
|
+
}
|
|
24
|
+
|
|
25
|
+
async function dirItemCount(p: string): Promise<number> {
|
|
26
|
+
try {
|
|
27
|
+
const entries = await readdir(p);
|
|
28
|
+
return entries.length;
|
|
29
|
+
} catch {
|
|
30
|
+
return -1;
|
|
31
|
+
}
|
|
32
|
+
}
|
|
33
|
+
|
|
34
|
+
/**
|
|
35
|
+
* Run a full diagnostic for a specific OpenClaw agent.
|
|
36
|
+
*/
|
|
37
|
+
export async function diagnose(apiBaseUrl?: string, agent?: string): Promise<DiagnosticReport> {
|
|
38
|
+
const target = agent ?? DEFAULT_AGENT;
|
|
39
|
+
const checks: DiagnosticCheck[] = [];
|
|
40
|
+
let allOk = true;
|
|
41
|
+
const workspace = await resolveWorkspace(target);
|
|
42
|
+
const registryFile = agentRegistryFile(target);
|
|
43
|
+
const backupDir = agentBackupDir(target);
|
|
44
|
+
|
|
45
|
+
if (target !== DEFAULT_AGENT) {
|
|
46
|
+
checks.push({
|
|
47
|
+
label: "Target agent",
|
|
48
|
+
status: "ok",
|
|
49
|
+
detail: target,
|
|
50
|
+
});
|
|
51
|
+
}
|
|
52
|
+
|
|
53
|
+
const homeOk = await pathExists(OPENCLAW_HOME);
|
|
54
|
+
checks.push({
|
|
55
|
+
label: "OpenClaw home",
|
|
56
|
+
path: OPENCLAW_HOME,
|
|
57
|
+
status: homeOk ? "ok" : "fail",
|
|
58
|
+
detail: homeOk ? undefined : "NOT FOUND",
|
|
59
|
+
});
|
|
60
|
+
if (!homeOk) allOk = false;
|
|
61
|
+
|
|
62
|
+
const wsOk = await pathExists(workspace);
|
|
63
|
+
checks.push({
|
|
64
|
+
label: "Workspace",
|
|
65
|
+
path: workspace,
|
|
66
|
+
status: wsOk ? "ok" : "fail",
|
|
67
|
+
detail: wsOk ? undefined : "NOT FOUND",
|
|
68
|
+
});
|
|
69
|
+
if (!wsOk) allOk = false;
|
|
70
|
+
|
|
71
|
+
for (const f of [...REQUIRED_FILES, ...OPTIONAL_FILES]) {
|
|
72
|
+
const fp = join(workspace, f);
|
|
73
|
+
const found = await pathExists(fp);
|
|
74
|
+
checks.push({
|
|
75
|
+
label: `Workspace file: ${f}`,
|
|
76
|
+
path: fp,
|
|
77
|
+
status: found ? "ok" : "warn",
|
|
78
|
+
detail: found ? "found" : "missing",
|
|
79
|
+
});
|
|
80
|
+
}
|
|
81
|
+
|
|
82
|
+
const regOk = await pathExists(registryFile);
|
|
83
|
+
if (regOk) {
|
|
84
|
+
try {
|
|
85
|
+
const raw = await readFile(registryFile, "utf-8");
|
|
86
|
+
const reg = JSON.parse(raw);
|
|
87
|
+
const count = Object.keys(reg.agents ?? {}).length;
|
|
88
|
+
checks.push({
|
|
89
|
+
label: "Agent registry",
|
|
90
|
+
path: registryFile,
|
|
91
|
+
status: "ok",
|
|
92
|
+
detail: `${count} agent(s) registered`,
|
|
93
|
+
});
|
|
94
|
+
} catch {
|
|
95
|
+
checks.push({
|
|
96
|
+
label: "Agent registry",
|
|
97
|
+
path: registryFile,
|
|
98
|
+
status: "warn",
|
|
99
|
+
detail: "exists but cannot be parsed",
|
|
100
|
+
});
|
|
101
|
+
}
|
|
102
|
+
} else {
|
|
103
|
+
checks.push({
|
|
104
|
+
label: "Agent registry",
|
|
105
|
+
path: registryFile,
|
|
106
|
+
status: "ok",
|
|
107
|
+
detail: "not created yet (OK for first run)",
|
|
108
|
+
});
|
|
109
|
+
}
|
|
110
|
+
|
|
111
|
+
const skillsDir = join(workspace, "skills");
|
|
112
|
+
const skillCount = await dirItemCount(skillsDir);
|
|
113
|
+
checks.push({
|
|
114
|
+
label: "Skills directory",
|
|
115
|
+
path: skillsDir,
|
|
116
|
+
status: skillCount >= 0 ? "ok" : "warn",
|
|
117
|
+
detail: skillCount >= 0 ? `${skillCount} skill(s)` : "NOT FOUND",
|
|
118
|
+
});
|
|
119
|
+
|
|
120
|
+
const backupCount = await dirItemCount(backupDir);
|
|
121
|
+
checks.push({
|
|
122
|
+
label: "Backup directory",
|
|
123
|
+
path: backupDir,
|
|
124
|
+
status: "ok",
|
|
125
|
+
detail: backupCount >= 0 ? `${backupCount} backup(s)` : "will be created on first install",
|
|
126
|
+
});
|
|
127
|
+
|
|
128
|
+
const cacheCount = await dirItemCount(join(CLAWSTORE_DIR, "cache"));
|
|
129
|
+
checks.push({
|
|
130
|
+
label: "Cache directory",
|
|
131
|
+
path: join(CLAWSTORE_DIR, "cache"),
|
|
132
|
+
status: "ok",
|
|
133
|
+
detail: cacheCount >= 0 ? `${cacheCount} item(s)` : "will be created on first install",
|
|
134
|
+
});
|
|
135
|
+
|
|
136
|
+
if (apiBaseUrl) {
|
|
137
|
+
const { ok, detail } = await checkClawstoreApiReachable(apiBaseUrl);
|
|
138
|
+
checks.push({
|
|
139
|
+
label: "Clawstore API",
|
|
140
|
+
status: ok ? "ok" : "warn",
|
|
141
|
+
detail,
|
|
142
|
+
});
|
|
143
|
+
}
|
|
144
|
+
|
|
145
|
+
return { checks, allOk };
|
|
146
|
+
}
|
|
147
|
+
|
|
148
|
+
export function formatDiagnosticReport(report: DiagnosticReport): string {
|
|
149
|
+
const lines: string[] = ["\n Clawstore Doctor\n"];
|
|
150
|
+
for (const c of report.checks) {
|
|
151
|
+
const icon = c.status === "ok" ? "OK" : c.status === "warn" ? "WARN" : "FAIL";
|
|
152
|
+
const pathPart = c.path ? ` ${c.path}` : "";
|
|
153
|
+
const detailPart = c.detail ? ` (${c.detail})` : "";
|
|
154
|
+
lines.push(` ${c.label}:${pathPart} ... ${icon}${detailPart}`);
|
|
155
|
+
}
|
|
156
|
+
lines.push("");
|
|
157
|
+
lines.push(
|
|
158
|
+
report.allOk
|
|
159
|
+
? " All checks passed.\n"
|
|
160
|
+
: " Some issues found. Run `openclaw setup` to initialize missing directories.\n"
|
|
161
|
+
);
|
|
162
|
+
return lines.join("\n");
|
|
163
|
+
}
|