@markus-global/cli 0.2.0
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/api-client.d.ts +31 -0
- package/dist/api-client.d.ts.map +1 -0
- package/dist/api-client.js +96 -0
- package/dist/api-client.js.map +1 -0
- package/dist/commands/agent.d.ts +3 -0
- package/dist/commands/agent.d.ts.map +1 -0
- package/dist/commands/agent.js +224 -0
- package/dist/commands/agent.js.map +1 -0
- package/dist/commands/approval.d.ts +3 -0
- package/dist/commands/approval.d.ts.map +1 -0
- package/dist/commands/approval.js +59 -0
- package/dist/commands/approval.js.map +1 -0
- package/dist/commands/audit.d.ts +3 -0
- package/dist/commands/audit.d.ts.map +1 -0
- package/dist/commands/audit.js +92 -0
- package/dist/commands/audit.js.map +1 -0
- package/dist/commands/builder.d.ts +3 -0
- package/dist/commands/builder.d.ts.map +1 -0
- package/dist/commands/builder.js +85 -0
- package/dist/commands/builder.js.map +1 -0
- package/dist/commands/deliverable.d.ts +3 -0
- package/dist/commands/deliverable.d.ts.map +1 -0
- package/dist/commands/deliverable.js +127 -0
- package/dist/commands/deliverable.js.map +1 -0
- package/dist/commands/external-agent.d.ts +3 -0
- package/dist/commands/external-agent.d.ts.map +1 -0
- package/dist/commands/external-agent.js +74 -0
- package/dist/commands/external-agent.js.map +1 -0
- package/dist/commands/gateway.d.ts +3 -0
- package/dist/commands/gateway.d.ts.map +1 -0
- package/dist/commands/gateway.js +155 -0
- package/dist/commands/gateway.js.map +1 -0
- package/dist/commands/init.d.ts +6 -0
- package/dist/commands/init.d.ts.map +1 -0
- package/dist/commands/init.js +251 -0
- package/dist/commands/init.js.map +1 -0
- package/dist/commands/key.d.ts +3 -0
- package/dist/commands/key.d.ts.map +1 -0
- package/dist/commands/key.js +68 -0
- package/dist/commands/key.js.map +1 -0
- package/dist/commands/project.d.ts +3 -0
- package/dist/commands/project.d.ts.map +1 -0
- package/dist/commands/project.js +164 -0
- package/dist/commands/project.js.map +1 -0
- package/dist/commands/report.d.ts +3 -0
- package/dist/commands/report.d.ts.map +1 -0
- package/dist/commands/report.js +69 -0
- package/dist/commands/report.js.map +1 -0
- package/dist/commands/requirement.d.ts +3 -0
- package/dist/commands/requirement.d.ts.map +1 -0
- package/dist/commands/requirement.js +197 -0
- package/dist/commands/requirement.js.map +1 -0
- package/dist/commands/review.d.ts +3 -0
- package/dist/commands/review.d.ts.map +1 -0
- package/dist/commands/review.js +71 -0
- package/dist/commands/review.js.map +1 -0
- package/dist/commands/role.d.ts +3 -0
- package/dist/commands/role.d.ts.map +1 -0
- package/dist/commands/role.js +39 -0
- package/dist/commands/role.js.map +1 -0
- package/dist/commands/settings.d.ts +3 -0
- package/dist/commands/settings.d.ts.map +1 -0
- package/dist/commands/settings.js +53 -0
- package/dist/commands/settings.js.map +1 -0
- package/dist/commands/skill.d.ts +3 -0
- package/dist/commands/skill.d.ts.map +1 -0
- package/dist/commands/skill.js +136 -0
- package/dist/commands/skill.js.map +1 -0
- package/dist/commands/start.d.ts +3 -0
- package/dist/commands/start.d.ts.map +1 -0
- package/dist/commands/start.js +628 -0
- package/dist/commands/start.js.map +1 -0
- package/dist/commands/system.d.ts +3 -0
- package/dist/commands/system.d.ts.map +1 -0
- package/dist/commands/system.js +248 -0
- package/dist/commands/system.js.map +1 -0
- package/dist/commands/task.d.ts +3 -0
- package/dist/commands/task.d.ts.map +1 -0
- package/dist/commands/task.js +510 -0
- package/dist/commands/task.js.map +1 -0
- package/dist/commands/team.d.ts +3 -0
- package/dist/commands/team.d.ts.map +1 -0
- package/dist/commands/team.js +312 -0
- package/dist/commands/team.js.map +1 -0
- package/dist/commands/template.d.ts +3 -0
- package/dist/commands/template.d.ts.map +1 -0
- package/dist/commands/template.js +77 -0
- package/dist/commands/template.js.map +1 -0
- package/dist/commands/user.d.ts +3 -0
- package/dist/commands/user.d.ts.map +1 -0
- package/dist/commands/user.js +68 -0
- package/dist/commands/user.js.map +1 -0
- package/dist/index.d.ts +3 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +96 -0
- package/dist/index.js.map +1 -0
- package/dist/markus.mjs +82359 -0
- package/dist/output.d.ts +31 -0
- package/dist/output.d.ts.map +1 -0
- package/dist/output.js +121 -0
- package/dist/output.js.map +1 -0
- package/dist/paths.d.ts +20 -0
- package/dist/paths.d.ts.map +1 -0
- package/dist/paths.js +61 -0
- package/dist/paths.js.map +1 -0
- package/dist/web-ui/assets/index-Bcc58A3R.css +1 -0
- package/dist/web-ui/assets/index-CP5PJ1Oz.js +61 -0
- package/dist/web-ui/index.html +20 -0
- package/dist/web-ui/logo.png +0 -0
- package/package.json +37 -0
- package/templates/openclaw-markus-skill/AGENTS.md +163 -0
- package/templates/openclaw-markus-skill/TOOLS.md +155 -0
- package/templates/openclaw-markus-skill/config.json5 +44 -0
- package/templates/openclaw-markus-skill/heartbeat.md +45 -0
- package/templates/roles/SHARED.md +383 -0
- package/templates/roles/agent-father/ROLE.md +42 -0
- package/templates/roles/content-writer/ROLE.md +28 -0
- package/templates/roles/developer/HEARTBEAT.md +8 -0
- package/templates/roles/developer/POLICIES.md +31 -0
- package/templates/roles/developer/ROLE.md +23 -0
- package/templates/roles/devops/ROLE.md +28 -0
- package/templates/roles/finance/ROLE.md +16 -0
- package/templates/roles/hr/ROLE.md +17 -0
- package/templates/roles/marketing/ROLE.md +16 -0
- package/templates/roles/openclaw-developer/openclaw.md +78 -0
- package/templates/roles/operations/HEARTBEAT.md +10 -0
- package/templates/roles/operations/ROLE.md +23 -0
- package/templates/roles/org-manager/HEARTBEAT.md +12 -0
- package/templates/roles/org-manager/POLICIES.md +14 -0
- package/templates/roles/org-manager/ROLE.md +102 -0
- package/templates/roles/product-manager/HEARTBEAT.md +9 -0
- package/templates/roles/product-manager/ROLE.md +37 -0
- package/templates/roles/project-manager/ROLE.md +44 -0
- package/templates/roles/qa-engineer/ROLE.md +28 -0
- package/templates/roles/research-assistant/ROLE.md +23 -0
- package/templates/roles/reviewer/HEARTBEAT.md +13 -0
- package/templates/roles/reviewer/ROLE.md +69 -0
- package/templates/roles/secretary/HEARTBEAT.md +50 -0
- package/templates/roles/secretary/ROLE.md +148 -0
- package/templates/roles/skill-architect/ROLE.md +42 -0
- package/templates/roles/support/ROLE.md +16 -0
- package/templates/roles/team-factory/ROLE.md +54 -0
- package/templates/roles/tech-writer/ROLE.md +23 -0
- package/templates/skills/agent-building/SKILL.md +140 -0
- package/templates/skills/agent-building/skill.json +13 -0
- package/templates/skills/chrome-devtools/SKILL.md +257 -0
- package/templates/skills/chrome-devtools/skill.json +21 -0
- package/templates/skills/markus-admin-cli/SKILL.md +121 -0
- package/templates/skills/markus-admin-cli/skill.json +14 -0
- package/templates/skills/markus-agent-cli/SKILL.md +67 -0
- package/templates/skills/markus-agent-cli/skill.json +14 -0
- package/templates/skills/markus-cli/SKILL.md +113 -0
- package/templates/skills/markus-cli/skill.json +14 -0
- package/templates/skills/markus-hub-connector/SKILL.md +64 -0
- package/templates/skills/markus-hub-connector/server.mjs +321 -0
- package/templates/skills/markus-hub-connector/skill.json +20 -0
- package/templates/skills/markus-project-cli/SKILL.md +161 -0
- package/templates/skills/markus-project-cli/skill.json +14 -0
- package/templates/skills/markus-skill-cli/SKILL.md +57 -0
- package/templates/skills/markus-skill-cli/skill.json +14 -0
- package/templates/skills/markus-team-cli/SKILL.md +52 -0
- package/templates/skills/markus-team-cli/skill.json +14 -0
- package/templates/skills/self-evolution/SKILL.md +207 -0
- package/templates/skills/self-evolution/skill.json +14 -0
- package/templates/skills/skill-building/SKILL.md +172 -0
- package/templates/skills/skill-building/skill.json +13 -0
- package/templates/skills/team-building/SKILL.md +159 -0
- package/templates/skills/team-building/skill.json +13 -0
- package/templates/teams/content-team/ANNOUNCEMENT.md +10 -0
- package/templates/teams/content-team/NORMS.md +20 -0
- package/templates/teams/content-team/team.json +18 -0
- package/templates/teams/dev-squad/ANNOUNCEMENT.md +11 -0
- package/templates/teams/dev-squad/NORMS.md +22 -0
- package/templates/teams/dev-squad/team.json +19 -0
- package/templates/teams/startup-team/ANNOUNCEMENT.md +11 -0
- package/templates/teams/startup-team/NORMS.md +21 -0
- package/templates/teams/startup-team/team.json +20 -0
|
@@ -0,0 +1,321 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
|
|
3
|
+
// Self-contained MCP server for Markus Hub operations.
|
|
4
|
+
// Reads hub URL from ~/.markus/markus.json, token from ~/.markus/hub-token.
|
|
5
|
+
// Protocol: JSON-RPC 2.0 over stdio (MCP 2024-11-05).
|
|
6
|
+
|
|
7
|
+
import { readFileSync, writeFileSync, mkdirSync, readdirSync, existsSync } from 'node:fs';
|
|
8
|
+
import { join } from 'node:path';
|
|
9
|
+
import { homedir } from 'node:os';
|
|
10
|
+
import { createInterface } from 'node:readline';
|
|
11
|
+
|
|
12
|
+
const MARKUS_DIR = join(homedir(), '.markus');
|
|
13
|
+
const CONFIG_PATH = join(MARKUS_DIR, 'markus.json');
|
|
14
|
+
const TOKEN_PATH = join(MARKUS_DIR, 'hub-token');
|
|
15
|
+
const ARTIFACTS_DIR = join(MARKUS_DIR, 'builder-artifacts');
|
|
16
|
+
const DEFAULT_HUB_URL = 'https://markus.global';
|
|
17
|
+
|
|
18
|
+
function getHubUrl() {
|
|
19
|
+
try {
|
|
20
|
+
const cfg = JSON.parse(readFileSync(CONFIG_PATH, 'utf-8'));
|
|
21
|
+
return cfg?.hub?.url || DEFAULT_HUB_URL;
|
|
22
|
+
} catch {
|
|
23
|
+
return DEFAULT_HUB_URL;
|
|
24
|
+
}
|
|
25
|
+
}
|
|
26
|
+
|
|
27
|
+
function getHubToken() {
|
|
28
|
+
try {
|
|
29
|
+
return readFileSync(TOKEN_PATH, 'utf-8').trim() || null;
|
|
30
|
+
} catch {
|
|
31
|
+
return null;
|
|
32
|
+
}
|
|
33
|
+
}
|
|
34
|
+
|
|
35
|
+
async function hubFetch(path, opts = {}) {
|
|
36
|
+
const hubUrl = getHubUrl();
|
|
37
|
+
const token = getHubToken();
|
|
38
|
+
const headers = { 'Content-Type': 'application/json', ...opts.headers };
|
|
39
|
+
if (token) headers['Authorization'] = `Bearer ${token}`;
|
|
40
|
+
const url = `${hubUrl}/api${path}`;
|
|
41
|
+
const res = await fetch(url, { ...opts, headers });
|
|
42
|
+
if (!res.ok) {
|
|
43
|
+
const text = await res.text().catch(() => '');
|
|
44
|
+
throw new Error(`Hub API ${res.status}: ${text || res.statusText}`);
|
|
45
|
+
}
|
|
46
|
+
return res.json();
|
|
47
|
+
}
|
|
48
|
+
|
|
49
|
+
// --------------- Tool implementations ---------------
|
|
50
|
+
|
|
51
|
+
async function hubSearch(args) {
|
|
52
|
+
const params = new URLSearchParams();
|
|
53
|
+
if (args.query) params.set('q', args.query);
|
|
54
|
+
if (args.type) params.set('type', args.type);
|
|
55
|
+
if (args.category) params.set('category', args.category);
|
|
56
|
+
if (args.sort) params.set('sort', args.sort);
|
|
57
|
+
if (args.page) params.set('page', String(args.page));
|
|
58
|
+
if (args.limit) params.set('limit', String(args.limit || 20));
|
|
59
|
+
const qs = params.toString();
|
|
60
|
+
const data = await hubFetch(`/items${qs ? `?${qs}` : ''}`);
|
|
61
|
+
const items = (data.items || []).map(i => ({
|
|
62
|
+
id: i.id, name: i.name, type: i.itemType,
|
|
63
|
+
description: i.description, author: i.author?.username,
|
|
64
|
+
downloads: i.downloadCount, version: i.version,
|
|
65
|
+
}));
|
|
66
|
+
return JSON.stringify({ total: data.total, items }, null, 2);
|
|
67
|
+
}
|
|
68
|
+
|
|
69
|
+
async function hubDownload(args) {
|
|
70
|
+
const token = getHubToken();
|
|
71
|
+
if (!token) return JSON.stringify({ error: 'Not authenticated. User must login to Markus Hub first (via the web UI).' });
|
|
72
|
+
|
|
73
|
+
const data = await hubFetch(`/items/${args.id}/download`, { method: 'POST' });
|
|
74
|
+
const itemType = data.itemType || 'skill';
|
|
75
|
+
const name = data.name || args.id;
|
|
76
|
+
const typeDir = `${itemType}s`;
|
|
77
|
+
const targetDir = join(ARTIFACTS_DIR, typeDir, name);
|
|
78
|
+
mkdirSync(targetDir, { recursive: true });
|
|
79
|
+
|
|
80
|
+
if (data.config) {
|
|
81
|
+
writeFileSync(join(targetDir, `${itemType}.json`), JSON.stringify(data.config, null, 2), 'utf-8');
|
|
82
|
+
}
|
|
83
|
+
if (data.files) {
|
|
84
|
+
for (const [filename, content] of Object.entries(data.files)) {
|
|
85
|
+
const filePath = join(targetDir, filename);
|
|
86
|
+
mkdirSync(join(filePath, '..'), { recursive: true });
|
|
87
|
+
writeFileSync(filePath, content, 'utf-8');
|
|
88
|
+
}
|
|
89
|
+
}
|
|
90
|
+
|
|
91
|
+
const fileList = [];
|
|
92
|
+
try {
|
|
93
|
+
const walk = (dir, prefix = '') => {
|
|
94
|
+
for (const e of readdirSync(dir, { withFileTypes: true })) {
|
|
95
|
+
if (e.isDirectory()) walk(join(dir, e.name), `${prefix}${e.name}/`);
|
|
96
|
+
else fileList.push(`${prefix}${e.name}`);
|
|
97
|
+
}
|
|
98
|
+
};
|
|
99
|
+
walk(targetDir);
|
|
100
|
+
} catch { /* ignore */ }
|
|
101
|
+
|
|
102
|
+
return JSON.stringify({
|
|
103
|
+
downloaded: name,
|
|
104
|
+
type: itemType,
|
|
105
|
+
path: targetDir,
|
|
106
|
+
files: fileList,
|
|
107
|
+
note: 'Downloaded to builder-artifacts. User can install it from the Builder page.',
|
|
108
|
+
}, null, 2);
|
|
109
|
+
}
|
|
110
|
+
|
|
111
|
+
async function hubPublish(args) {
|
|
112
|
+
const token = getHubToken();
|
|
113
|
+
if (!token) return JSON.stringify({ error: 'Not authenticated. User must login to Markus Hub first (via the web UI).' });
|
|
114
|
+
|
|
115
|
+
let payload;
|
|
116
|
+
if (args.directory) {
|
|
117
|
+
payload = buildPayloadFromDir(args.directory);
|
|
118
|
+
if (payload.error) return JSON.stringify(payload);
|
|
119
|
+
} else {
|
|
120
|
+
payload = {
|
|
121
|
+
itemType: args.type || 'skill',
|
|
122
|
+
name: args.name,
|
|
123
|
+
description: args.description,
|
|
124
|
+
category: args.category,
|
|
125
|
+
tags: args.tags,
|
|
126
|
+
config: args.config,
|
|
127
|
+
files: args.files,
|
|
128
|
+
readme: args.readme,
|
|
129
|
+
};
|
|
130
|
+
}
|
|
131
|
+
|
|
132
|
+
const data = await hubFetch('/items', { method: 'POST', body: JSON.stringify(payload) });
|
|
133
|
+
return JSON.stringify({
|
|
134
|
+
id: data.id, name: data.name, slug: data.slug,
|
|
135
|
+
updated: data.updated || false,
|
|
136
|
+
url: `${getHubUrl()}/packages/${data.slug || data.id}`,
|
|
137
|
+
}, null, 2);
|
|
138
|
+
}
|
|
139
|
+
|
|
140
|
+
function buildPayloadFromDir(dir) {
|
|
141
|
+
const resolved = dir.startsWith('~') ? join(homedir(), dir.slice(1)) : dir;
|
|
142
|
+
if (!existsSync(resolved)) return { error: `Directory not found: ${resolved}` };
|
|
143
|
+
|
|
144
|
+
const manifestNames = ['skill.json', 'agent.json', 'team.json'];
|
|
145
|
+
let manifestFile = null;
|
|
146
|
+
let itemType = 'skill';
|
|
147
|
+
for (const mf of manifestNames) {
|
|
148
|
+
if (existsSync(join(resolved, mf))) {
|
|
149
|
+
manifestFile = mf;
|
|
150
|
+
itemType = mf.replace('.json', '');
|
|
151
|
+
break;
|
|
152
|
+
}
|
|
153
|
+
}
|
|
154
|
+
if (!manifestFile) return { error: `No manifest (skill.json/agent.json/team.json) found in ${resolved}` };
|
|
155
|
+
|
|
156
|
+
let config;
|
|
157
|
+
try { config = JSON.parse(readFileSync(join(resolved, manifestFile), 'utf-8')); }
|
|
158
|
+
catch { return { error: `Invalid JSON in ${manifestFile}` }; }
|
|
159
|
+
|
|
160
|
+
const files = {};
|
|
161
|
+
const walk = (d, prefix = '') => {
|
|
162
|
+
for (const e of readdirSync(d, { withFileTypes: true })) {
|
|
163
|
+
const rel = `${prefix}${e.name}`;
|
|
164
|
+
if (e.name === manifestFile && !prefix) continue;
|
|
165
|
+
if (e.name === 'node_modules' || e.name === '.git') continue;
|
|
166
|
+
if (e.isDirectory()) walk(join(d, e.name), `${rel}/`);
|
|
167
|
+
else {
|
|
168
|
+
try { files[rel] = readFileSync(join(d, e.name), 'utf-8'); }
|
|
169
|
+
catch { /* skip binary files */ }
|
|
170
|
+
}
|
|
171
|
+
}
|
|
172
|
+
};
|
|
173
|
+
walk(resolved);
|
|
174
|
+
|
|
175
|
+
let readme;
|
|
176
|
+
if (files['README.md']) { readme = files['README.md']; delete files['README.md']; }
|
|
177
|
+
|
|
178
|
+
return {
|
|
179
|
+
itemType, name: config.name, description: config.description,
|
|
180
|
+
category: config.category, tags: config.tags, config, files, readme,
|
|
181
|
+
};
|
|
182
|
+
}
|
|
183
|
+
|
|
184
|
+
async function hubMyItems() {
|
|
185
|
+
const token = getHubToken();
|
|
186
|
+
if (!token) return JSON.stringify({ error: 'Not authenticated. User must login to Markus Hub first (via the web UI).' });
|
|
187
|
+
|
|
188
|
+
const data = await hubFetch('/items/mine');
|
|
189
|
+
const items = (data.items || []).map(i => ({
|
|
190
|
+
id: i.id, name: i.name, type: i.itemType,
|
|
191
|
+
description: i.description, version: i.version,
|
|
192
|
+
updatedAt: i.updatedAt,
|
|
193
|
+
}));
|
|
194
|
+
return JSON.stringify({ count: items.length, items }, null, 2);
|
|
195
|
+
}
|
|
196
|
+
|
|
197
|
+
// --------------- MCP protocol ---------------
|
|
198
|
+
|
|
199
|
+
const TOOLS = [
|
|
200
|
+
{
|
|
201
|
+
name: 'hub_search',
|
|
202
|
+
description: 'Search Markus Hub for agents, teams, or skills by keyword, type, or category',
|
|
203
|
+
inputSchema: {
|
|
204
|
+
type: 'object',
|
|
205
|
+
properties: {
|
|
206
|
+
query: { type: 'string', description: 'Search keyword' },
|
|
207
|
+
type: { type: 'string', enum: ['agent', 'team', 'skill'], description: 'Filter by package type' },
|
|
208
|
+
category: { type: 'string', description: 'Filter by category' },
|
|
209
|
+
sort: { type: 'string', enum: ['downloads', 'recent', 'name'], description: 'Sort order' },
|
|
210
|
+
page: { type: 'number', description: 'Page number (1-based)' },
|
|
211
|
+
limit: { type: 'number', description: 'Results per page (default 20)' },
|
|
212
|
+
},
|
|
213
|
+
},
|
|
214
|
+
},
|
|
215
|
+
{
|
|
216
|
+
name: 'hub_download',
|
|
217
|
+
description: 'Download a package from Markus Hub to local builder-artifacts directory. Requires Hub login.',
|
|
218
|
+
inputSchema: {
|
|
219
|
+
type: 'object',
|
|
220
|
+
properties: {
|
|
221
|
+
id: { type: 'string', description: 'Hub item ID (from search results)' },
|
|
222
|
+
},
|
|
223
|
+
required: ['id'],
|
|
224
|
+
},
|
|
225
|
+
},
|
|
226
|
+
{
|
|
227
|
+
name: 'hub_publish',
|
|
228
|
+
description: 'Publish a local builder artifact to Markus Hub. Requires Hub login. Provide either a directory path or explicit fields.',
|
|
229
|
+
inputSchema: {
|
|
230
|
+
type: 'object',
|
|
231
|
+
properties: {
|
|
232
|
+
directory: { type: 'string', description: 'Path to artifact directory (reads manifest + files automatically)' },
|
|
233
|
+
type: { type: 'string', enum: ['agent', 'team', 'skill'], description: 'Package type (when not using directory)' },
|
|
234
|
+
name: { type: 'string', description: 'Package name (when not using directory)' },
|
|
235
|
+
description: { type: 'string', description: 'Package description (when not using directory)' },
|
|
236
|
+
category: { type: 'string' },
|
|
237
|
+
tags: { type: 'array', items: { type: 'string' } },
|
|
238
|
+
config: { type: 'object', description: 'Manifest JSON (when not using directory)' },
|
|
239
|
+
files: { type: 'object', description: 'Map of filename→content (when not using directory)' },
|
|
240
|
+
readme: { type: 'string', description: 'README content (when not using directory)' },
|
|
241
|
+
},
|
|
242
|
+
},
|
|
243
|
+
},
|
|
244
|
+
{
|
|
245
|
+
name: 'hub_my_items',
|
|
246
|
+
description: 'List all items the current user has published on Markus Hub. Requires Hub login.',
|
|
247
|
+
inputSchema: {
|
|
248
|
+
type: 'object',
|
|
249
|
+
properties: {},
|
|
250
|
+
},
|
|
251
|
+
},
|
|
252
|
+
];
|
|
253
|
+
|
|
254
|
+
const TOOL_MAP = {
|
|
255
|
+
hub_search: hubSearch,
|
|
256
|
+
hub_download: hubDownload,
|
|
257
|
+
hub_publish: hubPublish,
|
|
258
|
+
hub_my_items: hubMyItems,
|
|
259
|
+
};
|
|
260
|
+
|
|
261
|
+
function respond(id, result) {
|
|
262
|
+
process.stdout.write(JSON.stringify({ jsonrpc: '2.0', id, result }) + '\n');
|
|
263
|
+
}
|
|
264
|
+
|
|
265
|
+
function respondError(id, code, message) {
|
|
266
|
+
process.stdout.write(JSON.stringify({ jsonrpc: '2.0', id, error: { code, message } }) + '\n');
|
|
267
|
+
}
|
|
268
|
+
|
|
269
|
+
const rl = createInterface({ input: process.stdin, terminal: false });
|
|
270
|
+
|
|
271
|
+
rl.on('line', async (line) => {
|
|
272
|
+
const trimmed = line.trim();
|
|
273
|
+
if (!trimmed) return;
|
|
274
|
+
|
|
275
|
+
let msg;
|
|
276
|
+
try { msg = JSON.parse(trimmed); } catch { return; }
|
|
277
|
+
|
|
278
|
+
const { id, method, params } = msg;
|
|
279
|
+
|
|
280
|
+
if (!method) return; // response to something we sent — ignore
|
|
281
|
+
|
|
282
|
+
// Notifications (no id) — just acknowledge silently
|
|
283
|
+
if (id === undefined || id === null) return;
|
|
284
|
+
|
|
285
|
+
switch (method) {
|
|
286
|
+
case 'initialize':
|
|
287
|
+
respond(id, {
|
|
288
|
+
protocolVersion: '2024-11-05',
|
|
289
|
+
capabilities: { tools: {} },
|
|
290
|
+
serverInfo: { name: 'markus-hub', version: '1.0.0' },
|
|
291
|
+
});
|
|
292
|
+
break;
|
|
293
|
+
|
|
294
|
+
case 'tools/list':
|
|
295
|
+
respond(id, { tools: TOOLS });
|
|
296
|
+
break;
|
|
297
|
+
|
|
298
|
+
case 'tools/call': {
|
|
299
|
+
const toolName = params?.name;
|
|
300
|
+
const toolArgs = params?.arguments || {};
|
|
301
|
+
const handler = TOOL_MAP[toolName];
|
|
302
|
+
if (!handler) {
|
|
303
|
+
respondError(id, -32601, `Unknown tool: ${toolName}`);
|
|
304
|
+
break;
|
|
305
|
+
}
|
|
306
|
+
try {
|
|
307
|
+
const text = await handler(toolArgs);
|
|
308
|
+
respond(id, { content: [{ type: 'text', text }] });
|
|
309
|
+
} catch (err) {
|
|
310
|
+
respond(id, { content: [{ type: 'text', text: `Error: ${err.message}` }], isError: true });
|
|
311
|
+
}
|
|
312
|
+
break;
|
|
313
|
+
}
|
|
314
|
+
|
|
315
|
+
default:
|
|
316
|
+
respondError(id, -32601, `Method not found: ${method}`);
|
|
317
|
+
}
|
|
318
|
+
});
|
|
319
|
+
|
|
320
|
+
// Keep process alive
|
|
321
|
+
process.stdin.resume();
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
{
|
|
2
|
+
"type": "skill",
|
|
3
|
+
"name": "markus-hub-connector",
|
|
4
|
+
"displayName": "Markus Hub Connector",
|
|
5
|
+
"version": "1.0.0",
|
|
6
|
+
"description": "Search, download, and publish agents/teams/skills on Markus Hub community marketplace",
|
|
7
|
+
"author": "markus",
|
|
8
|
+
"category": "productivity",
|
|
9
|
+
"tags": ["hub", "marketplace", "community", "share"],
|
|
10
|
+
"skill": {
|
|
11
|
+
"skillFile": "SKILL.md",
|
|
12
|
+
"requiredPermissions": ["network"],
|
|
13
|
+
"mcpServers": {
|
|
14
|
+
"markus-hub": {
|
|
15
|
+
"command": "node",
|
|
16
|
+
"args": ["${SKILL_DIR}/server.mjs"]
|
|
17
|
+
}
|
|
18
|
+
}
|
|
19
|
+
}
|
|
20
|
+
}
|
|
@@ -0,0 +1,161 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: markus-project-cli
|
|
3
|
+
description: Manage projects, tasks, requirements, deliverables, reports, reviews, and approvals via markus CLI.
|
|
4
|
+
---
|
|
5
|
+
|
|
6
|
+
# Project & Task Management via CLI
|
|
7
|
+
|
|
8
|
+
Operate projects, tasks, requirements, deliverables, reports, reviews, and approvals through `shell_execute` with `markus` commands. Always use `--json` for parseable output.
|
|
9
|
+
|
|
10
|
+
## Projects
|
|
11
|
+
|
|
12
|
+
```bash
|
|
13
|
+
markus project list --json
|
|
14
|
+
markus project get proj_xxx --json
|
|
15
|
+
markus project create --name "Web App v2" --org-id default --description "Next version"
|
|
16
|
+
markus project update proj_xxx --description "Updated scope"
|
|
17
|
+
markus project delete proj_xxx
|
|
18
|
+
```
|
|
19
|
+
|
|
20
|
+
| Command | Key Options |
|
|
21
|
+
|---------|-------------|
|
|
22
|
+
| `project list` | `--org <id>` |
|
|
23
|
+
| `project get <id>` | |
|
|
24
|
+
| `project create` | `--name` (required) `--org` `--description` `--repositories` `--team-ids` |
|
|
25
|
+
| `project update <id>` | `--name` `--description` `--status` `--repositories` `--team-ids` |
|
|
26
|
+
| `project delete <id>` | |
|
|
27
|
+
|
|
28
|
+
## Tasks (nested under project)
|
|
29
|
+
|
|
30
|
+
```bash
|
|
31
|
+
markus project task list --status in_progress --json
|
|
32
|
+
markus project task create --title "Implement login page" --priority high --assignee agt_xxx --project-id proj_xxx
|
|
33
|
+
markus project task run tsk_xxx
|
|
34
|
+
markus project task get tsk_xxx --json
|
|
35
|
+
markus project task approve tsk_xxx
|
|
36
|
+
markus project task accept tsk_xxx
|
|
37
|
+
markus project task revision tsk_xxx --reason "Tests are missing"
|
|
38
|
+
```
|
|
39
|
+
|
|
40
|
+
### CRUD
|
|
41
|
+
|
|
42
|
+
| Command | Options |
|
|
43
|
+
|---------|---------|
|
|
44
|
+
| `project task list` | `--status` `--agent-id` `--project-id` `--requirement-id` `--org-id` `--limit` |
|
|
45
|
+
| `project task get <id>` | |
|
|
46
|
+
| `project task create` | `--title` (required) `--description` `--priority` `--assignee` `--reviewer` `--project-id` `--blocked-by` `--type` |
|
|
47
|
+
| `project task update <id>` | `--title` `--description` `--priority` `--status` `--assignee` `--reviewer` `--project-id` `--blocked-by` |
|
|
48
|
+
| `project task dashboard` | `--org-id` |
|
|
49
|
+
| `project task board` | `--org-id` `--project-id` |
|
|
50
|
+
|
|
51
|
+
### Lifecycle Actions
|
|
52
|
+
|
|
53
|
+
| Command | Options |
|
|
54
|
+
|---------|---------|
|
|
55
|
+
| `project task approve <id>` | |
|
|
56
|
+
| `project task reject <id>` | |
|
|
57
|
+
| `project task run <id>` | |
|
|
58
|
+
| `project task pause <id>` | |
|
|
59
|
+
| `project task resume <id>` | |
|
|
60
|
+
| `project task retry <id>` | |
|
|
61
|
+
| `project task cancel <id>` | `--cascade` |
|
|
62
|
+
| `project task accept <id>` | |
|
|
63
|
+
| `project task revision <id>` | `--reason` |
|
|
64
|
+
| `project task archive <id>` | |
|
|
65
|
+
|
|
66
|
+
### Subtasks & Comments
|
|
67
|
+
|
|
68
|
+
| Command | Options |
|
|
69
|
+
|---------|---------|
|
|
70
|
+
| `project task subtasks <id>` | |
|
|
71
|
+
| `project task subtask-add <id>` | `--title` (required) |
|
|
72
|
+
| `project task comment <id>` | `--content` (required) `--author-id` `--author-name` |
|
|
73
|
+
| `project task logs <id>` | |
|
|
74
|
+
|
|
75
|
+
### Task State Flow
|
|
76
|
+
|
|
77
|
+
```
|
|
78
|
+
pending → pending_approval → assigned → in_progress → review → accepted → completed → archived
|
|
79
|
+
```
|
|
80
|
+
|
|
81
|
+
## Requirements (nested under project)
|
|
82
|
+
|
|
83
|
+
```bash
|
|
84
|
+
markus project requirement list --project proj_xxx --json
|
|
85
|
+
markus project requirement create --title "User auth" --project proj_xxx --priority high
|
|
86
|
+
markus project requirement approve req_xxx
|
|
87
|
+
markus project requirement reject req_xxx --reason "Out of scope"
|
|
88
|
+
```
|
|
89
|
+
|
|
90
|
+
| Command | Key Options |
|
|
91
|
+
|---------|-------------|
|
|
92
|
+
| `project requirement list` | `--org` `--status` `--project` `--source` |
|
|
93
|
+
| `project requirement get <id>` | |
|
|
94
|
+
| `project requirement create` | `--title` (required) `--description` `--priority` `--project` `--org` `--tags` |
|
|
95
|
+
| `project requirement update <id>` | `--title` `--description` `--priority` `--tags` |
|
|
96
|
+
| `project requirement approve <id>` | |
|
|
97
|
+
| `project requirement reject <id>` | `--reason` |
|
|
98
|
+
| `project requirement delete <id>` | |
|
|
99
|
+
|
|
100
|
+
### Requirement State Flow
|
|
101
|
+
|
|
102
|
+
```
|
|
103
|
+
draft → pending_review → approved → in_progress → completed
|
|
104
|
+
→ rejected / cancelled
|
|
105
|
+
```
|
|
106
|
+
|
|
107
|
+
## Deliverables (nested under project)
|
|
108
|
+
|
|
109
|
+
```bash
|
|
110
|
+
markus project deliverable list --project-id proj_xxx --json
|
|
111
|
+
markus project deliverable create --title "API Design Doc" --type knowledge --project-id proj_xxx
|
|
112
|
+
markus project deliverable update dlv_xxx --status verified
|
|
113
|
+
markus project deliverable delete dlv_xxx
|
|
114
|
+
```
|
|
115
|
+
|
|
116
|
+
| Command | Key Options |
|
|
117
|
+
|---------|-------------|
|
|
118
|
+
| `project deliverable list` | `--query` `--project` `--agent` `--task` `--type` `--status` `--limit` `--offset` |
|
|
119
|
+
| `project deliverable create` | `--title` (required) `--type` `--summary` `--reference` `--tags` `--task` `--agent` `--project` |
|
|
120
|
+
| `project deliverable update <id>` | `--title` `--summary` `--reference` `--tags` `--status` `--type` |
|
|
121
|
+
| `project deliverable delete <id>` | |
|
|
122
|
+
|
|
123
|
+
## Reports & Usage (nested under project)
|
|
124
|
+
|
|
125
|
+
```bash
|
|
126
|
+
markus project report generate --period weekly --scope org
|
|
127
|
+
markus project report usage --json
|
|
128
|
+
```
|
|
129
|
+
|
|
130
|
+
| Command | Key Options |
|
|
131
|
+
|---------|-------------|
|
|
132
|
+
| `project report generate` | `--period` (required: daily/weekly/monthly) `--scope` `--org` `--project` |
|
|
133
|
+
| `project report list` | `--scope` `--scope-id` `--type` |
|
|
134
|
+
| `project report get <id>` | |
|
|
135
|
+
| `project report usage` | `--org` |
|
|
136
|
+
|
|
137
|
+
## Code Reviews (nested under project)
|
|
138
|
+
|
|
139
|
+
```bash
|
|
140
|
+
markus project review run --task-id tsk_xxx --agent-id agt_xxx --description "PR review"
|
|
141
|
+
markus project review list --task-id tsk_xxx --json
|
|
142
|
+
markus project review get rev_xxx --json
|
|
143
|
+
```
|
|
144
|
+
|
|
145
|
+
| Command | Key Options |
|
|
146
|
+
|---------|-------------|
|
|
147
|
+
| `project review run` | `--task` (required) `--agent` (required) `--description` `--changed-files` |
|
|
148
|
+
| `project review list` | `--task` `--limit` |
|
|
149
|
+
| `project review get <id>` | |
|
|
150
|
+
|
|
151
|
+
## Approvals (nested under project)
|
|
152
|
+
|
|
153
|
+
```bash
|
|
154
|
+
markus project approval list --task-id tsk_xxx --json
|
|
155
|
+
markus project approval process apv_xxx --action approve
|
|
156
|
+
```
|
|
157
|
+
|
|
158
|
+
| Command | Key Options |
|
|
159
|
+
|---------|-------------|
|
|
160
|
+
| `project approval list` | `--task` `--status` |
|
|
161
|
+
| `project approval process <id>` | `--action` (approve/reject) `--reason` |
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
{
|
|
2
|
+
"type": "skill",
|
|
3
|
+
"name": "markus-project-cli",
|
|
4
|
+
"displayName": "Markus Project CLI",
|
|
5
|
+
"version": "1.0.0",
|
|
6
|
+
"description": "Manage projects, requirements, deliverables, reports, and code reviews via markus CLI.",
|
|
7
|
+
"author": "markus",
|
|
8
|
+
"category": "platform",
|
|
9
|
+
"tags": ["cli", "projects", "requirements", "deliverables", "reports"],
|
|
10
|
+
"skill": {
|
|
11
|
+
"skillFile": "SKILL.md",
|
|
12
|
+
"alwaysOn": false
|
|
13
|
+
}
|
|
14
|
+
}
|
|
@@ -0,0 +1,57 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: markus-skill-cli
|
|
3
|
+
description: Manage skills via markus CLI — list, install, uninstall, search, scaffold.
|
|
4
|
+
---
|
|
5
|
+
|
|
6
|
+
# Skill Management via CLI
|
|
7
|
+
|
|
8
|
+
Operate the skill registry through `shell_execute` with `markus skill` commands. Always use `--json` for parseable output.
|
|
9
|
+
|
|
10
|
+
## Quick examples
|
|
11
|
+
|
|
12
|
+
```bash
|
|
13
|
+
# List installed skills
|
|
14
|
+
markus skill list --json
|
|
15
|
+
|
|
16
|
+
# List built-in template skills
|
|
17
|
+
markus skill builtin --json
|
|
18
|
+
|
|
19
|
+
# Search remote registries
|
|
20
|
+
markus skill search --query "browser automation" --json
|
|
21
|
+
|
|
22
|
+
# Install a skill
|
|
23
|
+
markus skill install --name chrome-devtools --source builtin
|
|
24
|
+
|
|
25
|
+
# Uninstall a skill
|
|
26
|
+
markus skill uninstall chrome-devtools
|
|
27
|
+
|
|
28
|
+
# Scaffold a new custom skill
|
|
29
|
+
markus skill init --name my-skill
|
|
30
|
+
```
|
|
31
|
+
|
|
32
|
+
## Command Reference
|
|
33
|
+
|
|
34
|
+
| Command | Key Options |
|
|
35
|
+
|---------|-------------|
|
|
36
|
+
| `skill list` | |
|
|
37
|
+
| `skill builtin` | |
|
|
38
|
+
| `skill search` | `--query` |
|
|
39
|
+
| `skill install` | `--name` (required) `--source` |
|
|
40
|
+
| `skill uninstall <name>` | |
|
|
41
|
+
| `skill init` | `--name` `--dir` |
|
|
42
|
+
|
|
43
|
+
## Skill types
|
|
44
|
+
|
|
45
|
+
- **Built-in**: Ship with Markus (e.g. `chrome-devtools`, `self-evolution`)
|
|
46
|
+
- **Custom**: User-created, stored locally
|
|
47
|
+
- **Registry**: Discovered via `skill search`, installed from remote sources
|
|
48
|
+
|
|
49
|
+
## Scaffold structure
|
|
50
|
+
|
|
51
|
+
`markus skill init --name my-skill` creates:
|
|
52
|
+
|
|
53
|
+
```
|
|
54
|
+
my-skill/
|
|
55
|
+
skill.json # Metadata (name, version, category, tags)
|
|
56
|
+
SKILL.md # Instructions for the agent
|
|
57
|
+
```
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
{
|
|
2
|
+
"type": "skill",
|
|
3
|
+
"name": "markus-skill-cli",
|
|
4
|
+
"displayName": "Markus Skill CLI",
|
|
5
|
+
"version": "1.0.0",
|
|
6
|
+
"description": "Manage skills via markus CLI — list, install, uninstall, search, scaffold.",
|
|
7
|
+
"author": "markus",
|
|
8
|
+
"category": "platform",
|
|
9
|
+
"tags": ["cli", "skills", "registry"],
|
|
10
|
+
"skill": {
|
|
11
|
+
"skillFile": "SKILL.md",
|
|
12
|
+
"alwaysOn": false
|
|
13
|
+
}
|
|
14
|
+
}
|
|
@@ -0,0 +1,52 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: markus-team-cli
|
|
3
|
+
description: Manage teams via markus CLI — create, members, lifecycle, export.
|
|
4
|
+
---
|
|
5
|
+
|
|
6
|
+
# Team Management via CLI
|
|
7
|
+
|
|
8
|
+
Operate teams through `shell_execute` with `markus team` commands. Always use `--json` for parseable output.
|
|
9
|
+
|
|
10
|
+
## Quick examples
|
|
11
|
+
|
|
12
|
+
```bash
|
|
13
|
+
# List teams
|
|
14
|
+
markus team list --json
|
|
15
|
+
|
|
16
|
+
# Create a team
|
|
17
|
+
markus team create --name "Backend Team" --org default
|
|
18
|
+
|
|
19
|
+
# Add/remove members
|
|
20
|
+
markus team add-member team_xxx --member agt_xxx --type agent
|
|
21
|
+
markus team remove-member team_xxx agt_xxx
|
|
22
|
+
|
|
23
|
+
# Team lifecycle
|
|
24
|
+
markus team start team_xxx
|
|
25
|
+
markus team stop team_xxx
|
|
26
|
+
markus team pause team_xxx --reason "Maintenance"
|
|
27
|
+
markus team resume team_xxx
|
|
28
|
+
|
|
29
|
+
# Team status
|
|
30
|
+
markus team status team_xxx --json
|
|
31
|
+
|
|
32
|
+
# Export team config
|
|
33
|
+
markus team export team_xxx --json
|
|
34
|
+
```
|
|
35
|
+
|
|
36
|
+
## Command Reference
|
|
37
|
+
|
|
38
|
+
| Command | Key Options |
|
|
39
|
+
|---------|-------------|
|
|
40
|
+
| `team list` | `--org` |
|
|
41
|
+
| `team get <id>` | |
|
|
42
|
+
| `team create` | `--name` (required) `--org` `--description` |
|
|
43
|
+
| `team update <id>` | `--name` `--description` `--manager-id` `--manager-type` |
|
|
44
|
+
| `team delete <id>` | `--delete-members` `--purge-files` |
|
|
45
|
+
| `team add-member <id>` | `--member` (required) `--type` (agent/human) |
|
|
46
|
+
| `team remove-member <id> <memberId>` | |
|
|
47
|
+
| `team start <id>` | |
|
|
48
|
+
| `team stop <id>` | |
|
|
49
|
+
| `team pause <id>` | `--reason` |
|
|
50
|
+
| `team resume <id>` | |
|
|
51
|
+
| `team status <id>` | |
|
|
52
|
+
| `team export <id>` | |
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
{
|
|
2
|
+
"type": "skill",
|
|
3
|
+
"name": "markus-team-cli",
|
|
4
|
+
"displayName": "Markus Team CLI",
|
|
5
|
+
"version": "1.0.0",
|
|
6
|
+
"description": "Manage teams via markus CLI — create, members, lifecycle, export.",
|
|
7
|
+
"author": "markus",
|
|
8
|
+
"category": "platform",
|
|
9
|
+
"tags": ["cli", "teams", "management"],
|
|
10
|
+
"skill": {
|
|
11
|
+
"skillFile": "SKILL.md",
|
|
12
|
+
"alwaysOn": false
|
|
13
|
+
}
|
|
14
|
+
}
|