create-merlin-brain 3.22.0 → 4.0.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/README.md +38 -4
- package/bin/merlin-ask.cjs +111 -0
- package/bin/merlin-cli.cjs +22 -0
- package/bin/runtime-adapters.cjs +709 -28
- package/dist/server/api/client.d.ts +2 -0
- package/dist/server/api/client.d.ts.map +1 -1
- package/dist/server/api/client.js +4 -0
- package/dist/server/api/client.js.map +1 -1
- package/dist/server/server.d.ts.map +1 -1
- package/dist/server/server.js +56 -4
- package/dist/server/server.js.map +1 -1
- package/dist/server/tools/auto-mode.d.ts +9 -0
- package/dist/server/tools/auto-mode.d.ts.map +1 -0
- package/dist/server/tools/auto-mode.js +231 -0
- package/dist/server/tools/auto-mode.js.map +1 -0
- package/dist/server/tools/computer-use.d.ts +8 -0
- package/dist/server/tools/computer-use.d.ts.map +1 -0
- package/dist/server/tools/computer-use.js +355 -0
- package/dist/server/tools/computer-use.js.map +1 -0
- package/dist/server/tools/dream.d.ts +9 -0
- package/dist/server/tools/dream.d.ts.map +1 -0
- package/dist/server/tools/dream.js +246 -0
- package/dist/server/tools/dream.js.map +1 -0
- package/dist/server/tools/help.d.ts +3 -0
- package/dist/server/tools/help.d.ts.map +1 -0
- package/dist/server/tools/help.js +110 -0
- package/dist/server/tools/help.js.map +1 -0
- package/dist/server/tools/hud.d.ts +13 -0
- package/dist/server/tools/hud.d.ts.map +1 -0
- package/dist/server/tools/hud.js +295 -0
- package/dist/server/tools/hud.js.map +1 -0
- package/dist/server/tools/index.d.ts +5 -0
- package/dist/server/tools/index.d.ts.map +1 -1
- package/dist/server/tools/index.js +5 -0
- package/dist/server/tools/index.js.map +1 -1
- package/dist/server/tools/provider-ask.d.ts +10 -0
- package/dist/server/tools/provider-ask.d.ts.map +1 -0
- package/dist/server/tools/provider-ask.js +234 -0
- package/dist/server/tools/provider-ask.js.map +1 -0
- package/dist/server/tools/rate-limit.d.ts +8 -0
- package/dist/server/tools/rate-limit.d.ts.map +1 -0
- package/dist/server/tools/rate-limit.js +184 -0
- package/dist/server/tools/rate-limit.js.map +1 -0
- package/dist/server/tools/skills.d.ts +16 -0
- package/dist/server/tools/skills.d.ts.map +1 -0
- package/dist/server/tools/skills.js +326 -0
- package/dist/server/tools/skills.js.map +1 -0
- package/dist/server/tools/team-workers.d.ts +7 -0
- package/dist/server/tools/team-workers.d.ts.map +1 -0
- package/dist/server/tools/team-workers.js +271 -0
- package/dist/server/tools/team-workers.js.map +1 -0
- package/dist/server/utils/merlin-manifest.d.ts +6 -1
- package/dist/server/utils/merlin-manifest.d.ts.map +1 -1
- package/dist/server/utils/merlin-manifest.js +34 -1
- package/dist/server/utils/merlin-manifest.js.map +1 -1
- package/files/CLAUDE.md +22 -0
- package/files/hooks/rate-limit-watch.sh +120 -0
- package/files/hooks/statusline.sh +148 -0
- package/files/merlin/skills/SKILLS-INDEX.md +82 -0
- package/files/merlin/skills/automation/payments.md +14 -0
- package/files/merlin/skills/automation/webhooks.md +14 -0
- package/files/merlin/skills/coding/accessibility.md +14 -0
- package/files/merlin/skills/coding/api-design.md +14 -0
- package/files/merlin/skills/coding/debug-mode.md +14 -0
- package/files/merlin/skills/coding/focus-mode.md +14 -0
- package/files/merlin/skills/coding/loop.md +14 -0
- package/files/merlin/skills/coding/performance.md +14 -0
- package/files/merlin/skills/coding/react-patterns.md +51 -0
- package/files/merlin/skills/coding/security-hardening.md +56 -0
- package/files/merlin/skills/coding/verify.md +14 -0
- package/files/merlin/skills/communication/dispatcher.md +40 -0
- package/files/merlin/skills/communication/email-gmail.md +31 -0
- package/files/merlin/skills/communication/telegram.md +50 -0
- package/files/merlin/skills/communication/whatsapp.md +47 -0
- package/files/merlin/skills/data/google-sheets.md +14 -0
- package/files/merlin/skills/design/animation.md +14 -0
- package/files/merlin/skills/devops/docker-containers.md +14 -0
- package/files/merlin/skills/research/brainstorm.md +14 -0
- package/files/merlin/skills/testing/tdd-workflow.md +58 -0
- package/package.json +4 -2
|
@@ -0,0 +1,271 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Team Workers Tools — Spawn parallel AI CLI workers in tmux panes.
|
|
3
|
+
* Job state persisted to ~/.merlin/state/team/ for status/cleanup queries.
|
|
4
|
+
*/
|
|
5
|
+
import { z } from 'zod';
|
|
6
|
+
import { execFile } from 'child_process';
|
|
7
|
+
import { existsSync, readFileSync, writeFileSync, mkdirSync, readdirSync, unlinkSync } from 'fs';
|
|
8
|
+
import { homedir } from 'os';
|
|
9
|
+
import { join } from 'path';
|
|
10
|
+
import { promisify } from 'util';
|
|
11
|
+
const execFileAsync = promisify(execFile);
|
|
12
|
+
const TEAM_STATE_DIR = join(homedir(), '.merlin', 'state', 'team');
|
|
13
|
+
// ── Internal helpers ──────────────────────────────────────────────────────
|
|
14
|
+
async function isTmuxAvailable() {
|
|
15
|
+
try {
|
|
16
|
+
await execFileAsync('which', ['tmux']);
|
|
17
|
+
return true;
|
|
18
|
+
}
|
|
19
|
+
catch {
|
|
20
|
+
return false;
|
|
21
|
+
}
|
|
22
|
+
}
|
|
23
|
+
function generateJobId() {
|
|
24
|
+
return `merlin-${Date.now()}-${Math.random().toString(36).slice(2, 8)}`;
|
|
25
|
+
}
|
|
26
|
+
async function ensureTmuxSession(session) {
|
|
27
|
+
try {
|
|
28
|
+
await execFileAsync('tmux', ['has-session', '-t', session]);
|
|
29
|
+
return true;
|
|
30
|
+
}
|
|
31
|
+
catch {
|
|
32
|
+
try {
|
|
33
|
+
await execFileAsync('tmux', ['new-session', '-d', '-s', session]);
|
|
34
|
+
return true;
|
|
35
|
+
}
|
|
36
|
+
catch {
|
|
37
|
+
return false;
|
|
38
|
+
}
|
|
39
|
+
}
|
|
40
|
+
}
|
|
41
|
+
/** Split a new pane in the session, send command, return pane ID. */
|
|
42
|
+
async function createTmuxPane(session, command) {
|
|
43
|
+
await execFileAsync('tmux', ['split-window', '-d', '-t', session]);
|
|
44
|
+
const { stdout } = await execFileAsync('tmux', [
|
|
45
|
+
'list-panes', '-t', session, '-F', '#{session_name}:#{window_index}.#{pane_index}',
|
|
46
|
+
]);
|
|
47
|
+
const panes = stdout.trim().split('\n').filter(Boolean);
|
|
48
|
+
if (panes.length === 0)
|
|
49
|
+
throw new Error('No panes found after split-window');
|
|
50
|
+
const paneId = panes[panes.length - 1];
|
|
51
|
+
await execFileAsync('tmux', ['send-keys', '-t', paneId, command, 'Enter']);
|
|
52
|
+
return paneId;
|
|
53
|
+
}
|
|
54
|
+
async function capturePaneOutput(paneId, lines = 50) {
|
|
55
|
+
try {
|
|
56
|
+
const { stdout } = await execFileAsync('tmux', [
|
|
57
|
+
'capture-pane', '-t', paneId, '-p', '-J', '-S', String(-lines),
|
|
58
|
+
]);
|
|
59
|
+
return stdout;
|
|
60
|
+
}
|
|
61
|
+
catch {
|
|
62
|
+
return '(pane output unavailable)';
|
|
63
|
+
}
|
|
64
|
+
}
|
|
65
|
+
async function isPaneAlive(paneId) {
|
|
66
|
+
try {
|
|
67
|
+
await execFileAsync('tmux', ['list-panes', '-t', paneId]);
|
|
68
|
+
return true;
|
|
69
|
+
}
|
|
70
|
+
catch {
|
|
71
|
+
return false;
|
|
72
|
+
}
|
|
73
|
+
}
|
|
74
|
+
/** Build provider CLI command. Escapes task string for send-keys shell boundary. */
|
|
75
|
+
function buildProviderCommand(provider, task, agent) {
|
|
76
|
+
const t = task.replace(/\\/g, '\\\\').replace(/"/g, '\\"');
|
|
77
|
+
switch (provider) {
|
|
78
|
+
case 'claude': return `claude ${agent ? `--agent ${agent} ` : ''}-p "${t}" --output-format text`;
|
|
79
|
+
case 'codex': return `codex exec "${t}"`;
|
|
80
|
+
case 'gemini': return `gemini -p "${t}"`;
|
|
81
|
+
}
|
|
82
|
+
}
|
|
83
|
+
// ── State helpers ─────────────────────────────────────────────────────────
|
|
84
|
+
function ensureStateDir() {
|
|
85
|
+
if (!existsSync(TEAM_STATE_DIR))
|
|
86
|
+
mkdirSync(TEAM_STATE_DIR, { recursive: true });
|
|
87
|
+
}
|
|
88
|
+
function stateFilePath(teamName) {
|
|
89
|
+
return join(TEAM_STATE_DIR, `${teamName}.json`);
|
|
90
|
+
}
|
|
91
|
+
function saveJobState(state) {
|
|
92
|
+
ensureStateDir();
|
|
93
|
+
writeFileSync(stateFilePath(state.teamName), JSON.stringify(state, null, 2), 'utf-8');
|
|
94
|
+
}
|
|
95
|
+
function loadJobState(teamName) {
|
|
96
|
+
try {
|
|
97
|
+
const p = stateFilePath(teamName);
|
|
98
|
+
if (!existsSync(p))
|
|
99
|
+
return null;
|
|
100
|
+
return JSON.parse(readFileSync(p, 'utf-8'));
|
|
101
|
+
}
|
|
102
|
+
catch {
|
|
103
|
+
return null;
|
|
104
|
+
}
|
|
105
|
+
}
|
|
106
|
+
function listAllJobs() {
|
|
107
|
+
try {
|
|
108
|
+
ensureStateDir();
|
|
109
|
+
return readdirSync(TEAM_STATE_DIR)
|
|
110
|
+
.filter(f => f.endsWith('.json'))
|
|
111
|
+
.flatMap(f => {
|
|
112
|
+
try {
|
|
113
|
+
return [JSON.parse(readFileSync(join(TEAM_STATE_DIR, f), 'utf-8'))];
|
|
114
|
+
}
|
|
115
|
+
catch {
|
|
116
|
+
return [];
|
|
117
|
+
}
|
|
118
|
+
});
|
|
119
|
+
}
|
|
120
|
+
catch {
|
|
121
|
+
return [];
|
|
122
|
+
}
|
|
123
|
+
}
|
|
124
|
+
function resolveJobs(teamName, jobId) {
|
|
125
|
+
if (teamName) {
|
|
126
|
+
const j = loadJobState(teamName);
|
|
127
|
+
return j ? [j] : [];
|
|
128
|
+
}
|
|
129
|
+
if (jobId) {
|
|
130
|
+
const j = listAllJobs().find(x => x.jobId === jobId);
|
|
131
|
+
return j ? [j] : [];
|
|
132
|
+
}
|
|
133
|
+
return listAllJobs();
|
|
134
|
+
}
|
|
135
|
+
// ── Tool registration ─────────────────────────────────────────────────────
|
|
136
|
+
export function registerTeamWorkerTools(ctx) {
|
|
137
|
+
const { server } = ctx;
|
|
138
|
+
server.tool('merlin_spawn_workers', 'Spawn parallel AI CLI workers in tmux panes for burst execution. Each worker gets its own ' +
|
|
139
|
+
'tmux pane running a claude/codex/gemini CLI instance. Use for maximum parallelism on ' +
|
|
140
|
+
'independent tasks. Persists job state for status queries and cleanup. ' +
|
|
141
|
+
'Requires tmux. Returns jobId and per-worker pane assignments.', {
|
|
142
|
+
workers: z.array(z.object({
|
|
143
|
+
provider: z.enum(['claude', 'codex', 'gemini']).default('claude'),
|
|
144
|
+
task: z.string().describe('Task or prompt for this worker'),
|
|
145
|
+
agent: z.string().optional().describe('For claude: agent name (e.g. implementation-dev)'),
|
|
146
|
+
})).min(1).describe('Workers to spawn'),
|
|
147
|
+
teamName: z.string().optional().default('merlin-team').describe('Logical team name for state tracking'),
|
|
148
|
+
sessionName: z.string().optional().describe('tmux session name — defaults to teamName'),
|
|
149
|
+
}, async ({ workers, teamName, sessionName }) => {
|
|
150
|
+
const resolvedTeam = teamName ?? 'merlin-team';
|
|
151
|
+
const tmuxSession = sessionName ?? resolvedTeam;
|
|
152
|
+
if (!(await isTmuxAvailable())) {
|
|
153
|
+
return {
|
|
154
|
+
content: [{ type: 'text',
|
|
155
|
+
text: 'tmux not found. Install: macOS `brew install tmux` / Linux `apt install tmux`' }],
|
|
156
|
+
isError: true,
|
|
157
|
+
};
|
|
158
|
+
}
|
|
159
|
+
if (!(await ensureTmuxSession(tmuxSession))) {
|
|
160
|
+
return {
|
|
161
|
+
content: [{ type: 'text', text: `Failed to create tmux session "${tmuxSession}".` }],
|
|
162
|
+
isError: true,
|
|
163
|
+
};
|
|
164
|
+
}
|
|
165
|
+
const jobId = generateJobId();
|
|
166
|
+
const workerStates = [];
|
|
167
|
+
const errors = [];
|
|
168
|
+
for (const w of workers) {
|
|
169
|
+
try {
|
|
170
|
+
const paneId = await createTmuxPane(tmuxSession, buildProviderCommand(w.provider, w.task, w.agent));
|
|
171
|
+
workerStates.push({ paneId, provider: w.provider, task: w.task, agent: w.agent, status: 'running' });
|
|
172
|
+
}
|
|
173
|
+
catch (err) {
|
|
174
|
+
errors.push(`${w.provider} / ${w.task.slice(0, 40)}: ${err instanceof Error ? err.message : String(err)}`);
|
|
175
|
+
}
|
|
176
|
+
}
|
|
177
|
+
saveJobState({ jobId, teamName: resolvedTeam, tmuxSession, workers: workerStates, startedAt: new Date().toISOString() });
|
|
178
|
+
const lines = [
|
|
179
|
+
`Team spawned — jobId: ${jobId}`,
|
|
180
|
+
`tmux session: ${tmuxSession}`,
|
|
181
|
+
`workers started: ${workerStates.length} / ${workers.length}`,
|
|
182
|
+
'',
|
|
183
|
+
'Workers:',
|
|
184
|
+
...workerStates.map((w, i) => ` [${i + 1}] pane=${w.paneId} provider=${w.provider}${w.agent ? ` agent=${w.agent}` : ''} task="${w.task.slice(0, 60)}"`),
|
|
185
|
+
...(errors.length ? ['', 'Errors:', ...errors.map(e => ` ! ${e}`)] : []),
|
|
186
|
+
'',
|
|
187
|
+
`Status: merlin_team_status(teamName="${resolvedTeam}")`,
|
|
188
|
+
`Attach: tmux attach-session -t ${tmuxSession}`,
|
|
189
|
+
`Cleanup: merlin_team_cleanup(teamName="${resolvedTeam}")`,
|
|
190
|
+
];
|
|
191
|
+
return { content: [{ type: 'text', text: lines.join('\n') }] };
|
|
192
|
+
});
|
|
193
|
+
server.tool('merlin_team_status', 'Check status of running tmux team workers. Shows pane liveness and captures recent terminal ' +
|
|
194
|
+
'output per worker. Provide teamName or jobId to target a specific job; omit both for all jobs.', {
|
|
195
|
+
teamName: z.string().optional().describe('Team name used at spawn time'),
|
|
196
|
+
jobId: z.string().optional().describe('Specific job ID'),
|
|
197
|
+
}, async ({ teamName, jobId }) => {
|
|
198
|
+
const jobs = resolveJobs(teamName, jobId);
|
|
199
|
+
if (jobs.length === 0) {
|
|
200
|
+
return { content: [{ type: 'text', text: 'No team jobs found. Use merlin_spawn_workers first.' }] };
|
|
201
|
+
}
|
|
202
|
+
const sections = [];
|
|
203
|
+
for (const job of jobs) {
|
|
204
|
+
sections.push(`Job: ${job.jobId} team: ${job.teamName} session: ${job.tmuxSession}`);
|
|
205
|
+
sections.push(`Started: ${job.startedAt}`, '');
|
|
206
|
+
for (const [i, worker] of job.workers.entries()) {
|
|
207
|
+
const alive = await isPaneAlive(worker.paneId);
|
|
208
|
+
sections.push(`Worker ${i + 1}: pane=${worker.paneId} status=${alive ? 'running' : 'completed/dead'}`);
|
|
209
|
+
sections.push(` provider=${worker.provider}${worker.agent ? ` agent=${worker.agent}` : ''}`);
|
|
210
|
+
sections.push(` task="${worker.task.slice(0, 80)}"`);
|
|
211
|
+
const out = (await capturePaneOutput(worker.paneId, 50)).trim();
|
|
212
|
+
if (out) {
|
|
213
|
+
sections.push(' --- recent output ---');
|
|
214
|
+
out.split('\n').slice(-20).forEach(l => sections.push(` ${l}`));
|
|
215
|
+
sections.push(' ---');
|
|
216
|
+
}
|
|
217
|
+
sections.push('');
|
|
218
|
+
}
|
|
219
|
+
}
|
|
220
|
+
return { content: [{ type: 'text', text: sections.join('\n') }] };
|
|
221
|
+
});
|
|
222
|
+
server.tool('merlin_team_cleanup', 'Clean up tmux team workers — kills panes and removes persisted job state. ' +
|
|
223
|
+
'Optionally kills the entire tmux session. Omit teamName/jobId to clean up all jobs.', {
|
|
224
|
+
teamName: z.string().optional().describe('Team name used at spawn time'),
|
|
225
|
+
jobId: z.string().optional().describe('Specific job ID'),
|
|
226
|
+
killSession: z.boolean().optional().default(false).describe('Kill the entire tmux session instead of individual panes'),
|
|
227
|
+
}, async ({ teamName, jobId, killSession }) => {
|
|
228
|
+
const jobs = resolveJobs(teamName, jobId);
|
|
229
|
+
if (jobs.length === 0) {
|
|
230
|
+
return { content: [{ type: 'text', text: 'No team jobs found. Nothing to clean up.' }] };
|
|
231
|
+
}
|
|
232
|
+
const report = [];
|
|
233
|
+
for (const job of jobs) {
|
|
234
|
+
report.push(`Cleaning job: ${job.jobId} team: ${job.teamName}`);
|
|
235
|
+
if (killSession) {
|
|
236
|
+
try {
|
|
237
|
+
await execFileAsync('tmux', ['kill-session', '-t', job.tmuxSession]);
|
|
238
|
+
report.push(` session "${job.tmuxSession}" killed`);
|
|
239
|
+
}
|
|
240
|
+
catch {
|
|
241
|
+
report.push(` session "${job.tmuxSession}" already gone`);
|
|
242
|
+
}
|
|
243
|
+
}
|
|
244
|
+
else {
|
|
245
|
+
for (const w of job.workers) {
|
|
246
|
+
try {
|
|
247
|
+
await execFileAsync('tmux', ['kill-pane', '-t', w.paneId]);
|
|
248
|
+
report.push(` pane ${w.paneId} killed`);
|
|
249
|
+
}
|
|
250
|
+
catch {
|
|
251
|
+
report.push(` pane ${w.paneId} already gone`);
|
|
252
|
+
}
|
|
253
|
+
}
|
|
254
|
+
}
|
|
255
|
+
try {
|
|
256
|
+
const p = stateFilePath(job.teamName);
|
|
257
|
+
if (existsSync(p)) {
|
|
258
|
+
unlinkSync(p);
|
|
259
|
+
report.push(' state file removed');
|
|
260
|
+
}
|
|
261
|
+
}
|
|
262
|
+
catch {
|
|
263
|
+
report.push(' warning: could not remove state file');
|
|
264
|
+
}
|
|
265
|
+
report.push('');
|
|
266
|
+
}
|
|
267
|
+
report.push('Cleanup complete.');
|
|
268
|
+
return { content: [{ type: 'text', text: report.join('\n') }] };
|
|
269
|
+
});
|
|
270
|
+
}
|
|
271
|
+
//# sourceMappingURL=team-workers.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"team-workers.js","sourceRoot":"","sources":["../../../src/server/tools/team-workers.ts"],"names":[],"mappings":"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"}
|
|
@@ -7,7 +7,7 @@
|
|
|
7
7
|
*
|
|
8
8
|
* Discovery chain:
|
|
9
9
|
* 1. .merlin.json (local file, 0 tokens, any agent)
|
|
10
|
-
* 2. CLAUDE.md
|
|
10
|
+
* 2. Instruction file comment (CLAUDE.md / AGENTS.md / GEMINI.md)
|
|
11
11
|
* 3. git remote → API lookup (network call, MCP required)
|
|
12
12
|
*/
|
|
13
13
|
/** Filename for the manifest */
|
|
@@ -26,6 +26,8 @@ export declare const MERLIN_MCP_SERVER = "merlin-mcp-server";
|
|
|
26
26
|
export declare const MERLIN_DEFAULT_CAPABILITIES: readonly ["context", "search", "conventions", "files", "ask"];
|
|
27
27
|
/** CLAUDE.md comment marker for Sight URL injection */
|
|
28
28
|
export declare const CLAUDEMD_SIGHT_MARKER = "MERLIN_SIGHT";
|
|
29
|
+
export declare const AGENTSMD_SIGHT_MARKER = "MERLIN_SIGHT";
|
|
30
|
+
export declare const GEMINIMD_SIGHT_MARKER = "MERLIN_SIGHT";
|
|
29
31
|
/** MCP configuration for the manifest */
|
|
30
32
|
export interface MerlinManifestMcp {
|
|
31
33
|
/** npm install command (e.g., "npx create-merlin-brain") */
|
|
@@ -95,4 +97,7 @@ export declare function buildManifest(sightId: string, repoUrl: string): MerlinM
|
|
|
95
97
|
* @returns true if injected, false if already present or no CLAUDE.md
|
|
96
98
|
*/
|
|
97
99
|
export declare function injectSightIntoClaudeMd(repoRoot: string, sightUrl: string): boolean;
|
|
100
|
+
export declare function injectSightIntoAgentsMd(repoRoot: string, sightUrl: string): boolean;
|
|
101
|
+
export declare function injectSightIntoGeminiMd(repoRoot: string, sightUrl: string): boolean;
|
|
102
|
+
export declare function injectSightIntoInstructionFiles(repoRoot: string, sightUrl: string): boolean;
|
|
98
103
|
//# sourceMappingURL=merlin-manifest.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"merlin-manifest.d.ts","sourceRoot":"","sources":["../../../src/server/utils/merlin-manifest.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;GAWG;AAKH,gCAAgC;AAChC,eAAO,MAAM,wBAAwB,iBAAiB,CAAC;AAEvD,0DAA0D;AAC1D,eAAO,MAAM,iBAAiB,gDAAgD,CAAC;AAE/E,0BAA0B;AAC1B,eAAO,MAAM,kBAAkB,gCAAgC,CAAC;AAEhE,qEAAqE;AACrE,eAAO,MAAM,eAAe,2CAA2C,CAAC;AAExE,0BAA0B;AAC1B,eAAO,MAAM,kBAAkB,4BAA4B,CAAC;AAE5D,sBAAsB;AACtB,eAAO,MAAM,iBAAiB,sBAAsB,CAAC;AAErD,gCAAgC;AAChC,eAAO,MAAM,2BAA2B,+DAM9B,CAAC;AAEX,uDAAuD;AACvD,eAAO,MAAM,qBAAqB,iBAAiB,CAAC;AAEpD,yCAAyC;AACzC,MAAM,WAAW,iBAAiB;IAChC,4DAA4D;IAC5D,OAAO,EAAE,MAAM,CAAC;IAChB,kDAAkD;IAClD,MAAM,EAAE,MAAM,CAAC;CAChB;AAED,uCAAuC;AACvC,MAAM,WAAW,cAAc;IAC7B,qCAAqC;IACrC,OAAO,EAAE,MAAM,CAAC;IAChB,0EAA0E;IAC1E,KAAK,EAAE,MAAM,CAAC;IACd,4DAA4D;IAC5D,IAAI,EAAE,MAAM,CAAC;IACb,iDAAiD;IACjD,GAAG,EAAE,iBAAiB,CAAC;IACvB,kGAAkG;IAClG,GAAG,EAAE,MAAM,CAAC;IACZ,oCAAoC;IACpC,YAAY,EAAE,MAAM,EAAE,CAAC;IACvB,8BAA8B;IAC9B,OAAO,EAAE,MAAM,CAAC;CACjB;AAED;;;;;;;;;GASG;AACH,wBAAgB,cAAc,CAAC,QAAQ,EAAE,MAAM,GAAG,MAAM,GAAG,IAAI,CAQ9D;AAED;;;;;;GAMG;AACH,wBAAgB,kBAAkB,CAAC,QAAQ,EAAE,MAAM,GAAG,cAAc,GAAG,IAAI,CAqC1E;AAED;;;;;;GAMG;AACH,wBAAgB,mBAAmB,CAAC,QAAQ,EAAE,MAAM,EAAE,QAAQ,EAAE,cAAc,GAAG,IAAI,CAKpF;AAED;;;;;;;GAOG;AACH,wBAAgB,aAAa,CAAC,OAAO,EAAE,MAAM,EAAE,OAAO,EAAE,MAAM,GAAG,cAAc,CAkB9E;AAED;;;;;;;GAOG;AACH,wBAAgB,uBAAuB,CAAC,QAAQ,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM,GAAG,OAAO,CAyBnF"}
|
|
1
|
+
{"version":3,"file":"merlin-manifest.d.ts","sourceRoot":"","sources":["../../../src/server/utils/merlin-manifest.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;GAWG;AAKH,gCAAgC;AAChC,eAAO,MAAM,wBAAwB,iBAAiB,CAAC;AAEvD,0DAA0D;AAC1D,eAAO,MAAM,iBAAiB,gDAAgD,CAAC;AAE/E,0BAA0B;AAC1B,eAAO,MAAM,kBAAkB,gCAAgC,CAAC;AAEhE,qEAAqE;AACrE,eAAO,MAAM,eAAe,2CAA2C,CAAC;AAExE,0BAA0B;AAC1B,eAAO,MAAM,kBAAkB,4BAA4B,CAAC;AAE5D,sBAAsB;AACtB,eAAO,MAAM,iBAAiB,sBAAsB,CAAC;AAErD,gCAAgC;AAChC,eAAO,MAAM,2BAA2B,+DAM9B,CAAC;AAEX,uDAAuD;AACvD,eAAO,MAAM,qBAAqB,iBAAiB,CAAC;AACpD,eAAO,MAAM,qBAAqB,iBAAiB,CAAC;AACpD,eAAO,MAAM,qBAAqB,iBAAiB,CAAC;AAEpD,yCAAyC;AACzC,MAAM,WAAW,iBAAiB;IAChC,4DAA4D;IAC5D,OAAO,EAAE,MAAM,CAAC;IAChB,kDAAkD;IAClD,MAAM,EAAE,MAAM,CAAC;CAChB;AAED,uCAAuC;AACvC,MAAM,WAAW,cAAc;IAC7B,qCAAqC;IACrC,OAAO,EAAE,MAAM,CAAC;IAChB,0EAA0E;IAC1E,KAAK,EAAE,MAAM,CAAC;IACd,4DAA4D;IAC5D,IAAI,EAAE,MAAM,CAAC;IACb,iDAAiD;IACjD,GAAG,EAAE,iBAAiB,CAAC;IACvB,kGAAkG;IAClG,GAAG,EAAE,MAAM,CAAC;IACZ,oCAAoC;IACpC,YAAY,EAAE,MAAM,EAAE,CAAC;IACvB,8BAA8B;IAC9B,OAAO,EAAE,MAAM,CAAC;CACjB;AAED;;;;;;;;;GASG;AACH,wBAAgB,cAAc,CAAC,QAAQ,EAAE,MAAM,GAAG,MAAM,GAAG,IAAI,CAQ9D;AAED;;;;;;GAMG;AACH,wBAAgB,kBAAkB,CAAC,QAAQ,EAAE,MAAM,GAAG,cAAc,GAAG,IAAI,CAqC1E;AAED;;;;;;GAMG;AACH,wBAAgB,mBAAmB,CAAC,QAAQ,EAAE,MAAM,EAAE,QAAQ,EAAE,cAAc,GAAG,IAAI,CAKpF;AAED;;;;;;;GAOG;AACH,wBAAgB,aAAa,CAAC,OAAO,EAAE,MAAM,EAAE,OAAO,EAAE,MAAM,GAAG,cAAc,CAkB9E;AAED;;;;;;;GAOG;AACH,wBAAgB,uBAAuB,CAAC,QAAQ,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM,GAAG,OAAO,CAyBnF;AAqBD,wBAAgB,uBAAuB,CAAC,QAAQ,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM,GAAG,OAAO,CAEnF;AAED,wBAAgB,uBAAuB,CAAC,QAAQ,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM,GAAG,OAAO,CAEnF;AAED,wBAAgB,+BAA+B,CAAC,QAAQ,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM,GAAG,OAAO,CAQ3F"}
|
|
@@ -7,7 +7,7 @@
|
|
|
7
7
|
*
|
|
8
8
|
* Discovery chain:
|
|
9
9
|
* 1. .merlin.json (local file, 0 tokens, any agent)
|
|
10
|
-
* 2. CLAUDE.md
|
|
10
|
+
* 2. Instruction file comment (CLAUDE.md / AGENTS.md / GEMINI.md)
|
|
11
11
|
* 3. git remote → API lookup (network call, MCP required)
|
|
12
12
|
*/
|
|
13
13
|
import { existsSync, readFileSync, writeFileSync } from 'fs';
|
|
@@ -34,6 +34,8 @@ export const MERLIN_DEFAULT_CAPABILITIES = [
|
|
|
34
34
|
];
|
|
35
35
|
/** CLAUDE.md comment marker for Sight URL injection */
|
|
36
36
|
export const CLAUDEMD_SIGHT_MARKER = 'MERLIN_SIGHT';
|
|
37
|
+
export const AGENTSMD_SIGHT_MARKER = 'MERLIN_SIGHT';
|
|
38
|
+
export const GEMINIMD_SIGHT_MARKER = 'MERLIN_SIGHT';
|
|
37
39
|
/**
|
|
38
40
|
* Extract the UUID sight ID from a Merlin Sights URL.
|
|
39
41
|
*
|
|
@@ -161,4 +163,35 @@ export function injectSightIntoClaudeMd(repoRoot, sightUrl) {
|
|
|
161
163
|
return false;
|
|
162
164
|
}
|
|
163
165
|
}
|
|
166
|
+
function injectSightMarker(filePath, markerPrefix, sightUrl) {
|
|
167
|
+
if (!existsSync(filePath)) {
|
|
168
|
+
return false;
|
|
169
|
+
}
|
|
170
|
+
try {
|
|
171
|
+
const content = readFileSync(filePath, 'utf-8');
|
|
172
|
+
if (content.includes(markerPrefix)) {
|
|
173
|
+
return false;
|
|
174
|
+
}
|
|
175
|
+
writeFileSync(filePath, `${markerPrefix}: ${sightUrl}\n${content}`, 'utf-8');
|
|
176
|
+
console.error(`[merlin-manifest] Injected Sight URL into ${filePath}`);
|
|
177
|
+
return true;
|
|
178
|
+
}
|
|
179
|
+
catch {
|
|
180
|
+
return false;
|
|
181
|
+
}
|
|
182
|
+
}
|
|
183
|
+
export function injectSightIntoAgentsMd(repoRoot, sightUrl) {
|
|
184
|
+
return injectSightMarker(join(repoRoot, 'AGENTS.md'), '# MERLIN_SIGHT', sightUrl);
|
|
185
|
+
}
|
|
186
|
+
export function injectSightIntoGeminiMd(repoRoot, sightUrl) {
|
|
187
|
+
return injectSightMarker(join(repoRoot, 'GEMINI.md'), '# MERLIN_SIGHT', sightUrl);
|
|
188
|
+
}
|
|
189
|
+
export function injectSightIntoInstructionFiles(repoRoot, sightUrl) {
|
|
190
|
+
const results = [
|
|
191
|
+
injectSightIntoClaudeMd(repoRoot, sightUrl),
|
|
192
|
+
injectSightIntoAgentsMd(repoRoot, sightUrl),
|
|
193
|
+
injectSightIntoGeminiMd(repoRoot, sightUrl),
|
|
194
|
+
];
|
|
195
|
+
return results.some(Boolean);
|
|
196
|
+
}
|
|
164
197
|
//# sourceMappingURL=merlin-manifest.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"merlin-manifest.js","sourceRoot":"","sources":["../../../src/server/utils/merlin-manifest.ts"],"names":[],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"merlin-manifest.js","sourceRoot":"","sources":["../../../src/server/utils/merlin-manifest.ts"],"names":[],"mappings":"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"}
|
package/files/CLAUDE.md
CHANGED
|
@@ -65,3 +65,25 @@ When user corrects you → `merlin_save_behavior`. When user says "always/never/
|
|
|
65
65
|
- Never kill user processes (Xcode, VS Code, browsers) without explicit confirmation.
|
|
66
66
|
- Never claim "done" without actually building/compiling/testing.
|
|
67
67
|
- Badge on EVERY action — if the user can't see `⟡🔮 MERLIN ›`, you're not doing your job.
|
|
68
|
+
|
|
69
|
+
## New Capabilities (March 2026)
|
|
70
|
+
|
|
71
|
+
### Auto Mode — `merlin loop yolo`
|
|
72
|
+
Enable autonomous tool approval. Call `merlin_auto_mode(action: "enable", level: "yolo")` for full autonomy or `level: "safe"` for read-only mode. Disable with `merlin_auto_mode(action: "disable")`.
|
|
73
|
+
- "loop yolo" / "auto mode" / "go autonomous" → `merlin_auto_mode(action: "enable", level: "yolo")`
|
|
74
|
+
|
|
75
|
+
### AutoDream — Memory Consolidation
|
|
76
|
+
Keep memory files clean and organized. Call `merlin_dream(action: "enable")` to turn on auto-dream, or `action: "consolidate"` to manually review and clean up memory.
|
|
77
|
+
- "dream" / "consolidate memory" / "clean up memory" → `merlin_dream(action: "consolidate")`
|
|
78
|
+
|
|
79
|
+
### Computer Use — Desktop Control
|
|
80
|
+
Take over and control desktop apps. Call `merlin_computer_use(action: "launch", app: "AppName")` to open an app, or `merlin_screenshot()` to capture the screen.
|
|
81
|
+
- "take over [app]" / "open [app]" / "control [app]" → `merlin_computer_use(action: "launch", app: "[app]")`
|
|
82
|
+
- "screenshot" / "what's on screen" → `merlin_screenshot()`
|
|
83
|
+
|
|
84
|
+
### Self-Evolving Skills — The Brain Gets Smarter
|
|
85
|
+
Skills are prompt injections that enhance your capabilities. They live at `~/.claude/merlin/skills/`.
|
|
86
|
+
- **Before any task**: Call `merlin_find_skill("what you need")` to discover relevant skills. Load 1-3 by reading their .md files.
|
|
87
|
+
- **After any task**: Call `merlin_track_skill(skillId, success)` to record whether the skill helped.
|
|
88
|
+
- **When a skill is wrong or missing**: Call `merlin_evolve_skill(...)` to improve it or create a new one. The improvement syncs to all users.
|
|
89
|
+
- Skills auto-improve over time. High success rate skills get recommended more. Failed skills get flagged for evolution.
|
|
@@ -0,0 +1,120 @@
|
|
|
1
|
+
#!/usr/bin/env bash
|
|
2
|
+
#
|
|
3
|
+
# Merlin Hook: PostToolUse — Rate-Limit Watcher
|
|
4
|
+
# Detects rate-limit signals in tool output and writes state to ~/.merlin/state/rate-limit.json.
|
|
5
|
+
# Sends a desktop notification on first detection (fire-and-forget).
|
|
6
|
+
#
|
|
7
|
+
# Always exits 0 — advisory only, never blocks.
|
|
8
|
+
#
|
|
9
|
+
set -euo pipefail
|
|
10
|
+
trap 'echo "{}"; exit 0' ERR
|
|
11
|
+
|
|
12
|
+
STATE_DIR="${HOME}/.merlin/state"
|
|
13
|
+
STATE_FILE="${STATE_DIR}/rate-limit.json"
|
|
14
|
+
|
|
15
|
+
# ── Ensure state directory exists ────────────────────────────────────────────
|
|
16
|
+
mkdir -p "${STATE_DIR}"
|
|
17
|
+
|
|
18
|
+
# ── Read stdin event ──────────────────────────────────────────────────────────
|
|
19
|
+
input=$(cat)
|
|
20
|
+
|
|
21
|
+
# ── Extract tool_result (jq with grep/sed fallback) ──────────────────────────
|
|
22
|
+
if command -v jq >/dev/null 2>&1; then
|
|
23
|
+
tool_result=$(echo "${input}" | jq -r '.tool_result // ""')
|
|
24
|
+
else
|
|
25
|
+
tool_result=$(echo "${input}" | grep -o '"tool_result":"[^"]*"' | cut -d'"' -f4 || true)
|
|
26
|
+
fi
|
|
27
|
+
|
|
28
|
+
# Lowercase for case-insensitive matching
|
|
29
|
+
tool_result_lower=$(echo "${tool_result}" | tr '[:upper:]' '[:lower:]')
|
|
30
|
+
|
|
31
|
+
# ── Rate-limit pattern matching ───────────────────────────────────────────────
|
|
32
|
+
is_rate_limited=false
|
|
33
|
+
trigger_label=""
|
|
34
|
+
|
|
35
|
+
if echo "${tool_result_lower}" | grep -qE 'rate.?limit|429|too many requests|quota exceeded|overloaded'; then
|
|
36
|
+
is_rate_limited=true
|
|
37
|
+
|
|
38
|
+
if echo "${tool_result_lower}" | grep -q '429'; then
|
|
39
|
+
trigger_label="429 response"
|
|
40
|
+
elif echo "${tool_result_lower}" | grep -q 'quota exceeded'; then
|
|
41
|
+
trigger_label="quota exceeded"
|
|
42
|
+
elif echo "${tool_result_lower}" | grep -q 'overloaded'; then
|
|
43
|
+
trigger_label="overloaded"
|
|
44
|
+
elif echo "${tool_result_lower}" | grep -q 'too many requests'; then
|
|
45
|
+
trigger_label="too many requests"
|
|
46
|
+
else
|
|
47
|
+
trigger_label="rate limit"
|
|
48
|
+
fi
|
|
49
|
+
fi
|
|
50
|
+
|
|
51
|
+
NOW=$(date -u +"%Y-%m-%dT%H:%M:%SZ")
|
|
52
|
+
|
|
53
|
+
# ── Compute estimated reset time (5 min from now) ────────────────────────────
|
|
54
|
+
# macOS date -v; Linux date -d fallback
|
|
55
|
+
if date -v+5M >/dev/null 2>&1; then
|
|
56
|
+
RESET_AT=$(date -u -v+5M +"%Y-%m-%dT%H:%M:%SZ")
|
|
57
|
+
else
|
|
58
|
+
RESET_AT=$(date -u -d "+5 minutes" +"%Y-%m-%dT%H:%M:%SZ" 2>/dev/null || echo "${NOW}")
|
|
59
|
+
fi
|
|
60
|
+
|
|
61
|
+
# ── If rate-limited: write blocked state ─────────────────────────────────────
|
|
62
|
+
if [ "${is_rate_limited}" = "true" ]; then
|
|
63
|
+
# Only notify on new detection (when previous state wasn't already blocked)
|
|
64
|
+
prev_status=""
|
|
65
|
+
if [ -f "${STATE_FILE}" ]; then
|
|
66
|
+
if command -v jq >/dev/null 2>&1; then
|
|
67
|
+
prev_status=$(jq -r '.status // ""' "${STATE_FILE}" 2>/dev/null || true)
|
|
68
|
+
else
|
|
69
|
+
prev_status=$(grep -o '"status":"[^"]*"' "${STATE_FILE}" | cut -d'"' -f4 || true)
|
|
70
|
+
fi
|
|
71
|
+
fi
|
|
72
|
+
|
|
73
|
+
cat > "${STATE_FILE}" <<EOF
|
|
74
|
+
{
|
|
75
|
+
"status": "blocked",
|
|
76
|
+
"detectedAt": "${NOW}",
|
|
77
|
+
"trigger": "${trigger_label}",
|
|
78
|
+
"estimatedResetAt": "${RESET_AT}"
|
|
79
|
+
}
|
|
80
|
+
EOF
|
|
81
|
+
|
|
82
|
+
# Desktop notification only on transition to blocked (macOS)
|
|
83
|
+
if [ "${prev_status}" != "blocked" ] && command -v osascript >/dev/null 2>&1; then
|
|
84
|
+
osascript -e 'display notification "Rate limit detected — will auto-resume" with title "⟡🔮 Merlin"' &
|
|
85
|
+
fi
|
|
86
|
+
|
|
87
|
+
echo "{}"
|
|
88
|
+
exit 0
|
|
89
|
+
fi
|
|
90
|
+
|
|
91
|
+
# ── If not rate-limited: check if we should clear a previous blocked state ───
|
|
92
|
+
if [ -f "${STATE_FILE}" ]; then
|
|
93
|
+
if command -v jq >/dev/null 2>&1; then
|
|
94
|
+
prev_status=$(jq -r '.status // ""' "${STATE_FILE}" 2>/dev/null || true)
|
|
95
|
+
detected_at=$(jq -r '.detectedAt // ""' "${STATE_FILE}" 2>/dev/null || true)
|
|
96
|
+
else
|
|
97
|
+
prev_status=$(grep -o '"status":"[^"]*"' "${STATE_FILE}" | cut -d'"' -f4 || true)
|
|
98
|
+
detected_at=$(grep -o '"detectedAt":"[^"]*"' "${STATE_FILE}" | cut -d'"' -f4 || true)
|
|
99
|
+
fi
|
|
100
|
+
|
|
101
|
+
if [ "${prev_status}" = "blocked" ] && [ -n "${detected_at}" ]; then
|
|
102
|
+
# Calculate elapsed seconds using python3 (available on macOS/Linux)
|
|
103
|
+
elapsed=$(python3 -c "
|
|
104
|
+
import datetime
|
|
105
|
+
try:
|
|
106
|
+
d = datetime.datetime.fromisoformat('${detected_at}'.replace('Z','+00:00'))
|
|
107
|
+
print(int((datetime.datetime.now(datetime.timezone.utc) - d).total_seconds()))
|
|
108
|
+
except Exception:
|
|
109
|
+
print(0)
|
|
110
|
+
" 2>/dev/null || echo "0")
|
|
111
|
+
|
|
112
|
+
# Clear blocked state only after 2+ minutes have elapsed
|
|
113
|
+
if [ "${elapsed}" -ge 120 ] 2>/dev/null; then
|
|
114
|
+
printf '{\n "status": "ok",\n "clearedAt": "%s"\n}\n' "${NOW}" > "${STATE_FILE}"
|
|
115
|
+
fi
|
|
116
|
+
fi
|
|
117
|
+
fi
|
|
118
|
+
|
|
119
|
+
echo "{}"
|
|
120
|
+
exit 0
|