@massa-ai/claude-plugin 1.25.0 → 1.26.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/.claude-plugin/plugin.json +1 -1
- package/agent-profiles/balanced/massa-ai-architecture-specialist.md +63 -0
- package/agent-profiles/balanced/massa-ai-audit-specialist.md +79 -0
- package/agent-profiles/balanced/massa-ai-builder.md +65 -0
- package/agent-profiles/balanced/massa-ai-context-curator.md +65 -0
- package/agent-profiles/balanced/massa-ai-documentation-agent.md +63 -0
- package/agent-profiles/balanced/massa-ai-furps-analyst.md +69 -0
- package/agent-profiles/balanced/massa-ai-investigator.md +66 -0
- package/agent-profiles/balanced/massa-ai-judge.md +100 -0
- package/agent-profiles/balanced/massa-ai-meta-judge.md +87 -0
- package/agent-profiles/balanced/massa-ai-mobile-specialist.md +80 -0
- package/agent-profiles/balanced/massa-ai-navigator.md +73 -0
- package/agent-profiles/balanced/massa-ai-plan-critic.md +88 -0
- package/agent-profiles/balanced/massa-ai-planner.md +63 -0
- package/agent-profiles/balanced/massa-ai-requirements-analyst.md +62 -0
- package/agent-profiles/balanced/massa-ai-reviewer.md +64 -0
- package/agent-profiles/balanced/massa-ai-test-engineer.md +64 -0
- package/agent-profiles/balanced/massa-ai-verification-agent.md +63 -0
- package/agent-profiles/cheap/massa-ai-architecture-specialist.md +63 -0
- package/agent-profiles/cheap/massa-ai-audit-specialist.md +79 -0
- package/agent-profiles/cheap/massa-ai-builder.md +65 -0
- package/agent-profiles/cheap/massa-ai-context-curator.md +65 -0
- package/agent-profiles/cheap/massa-ai-documentation-agent.md +63 -0
- package/agent-profiles/cheap/massa-ai-furps-analyst.md +69 -0
- package/agent-profiles/cheap/massa-ai-investigator.md +66 -0
- package/agent-profiles/cheap/massa-ai-judge.md +100 -0
- package/agent-profiles/cheap/massa-ai-meta-judge.md +87 -0
- package/agent-profiles/cheap/massa-ai-mobile-specialist.md +80 -0
- package/agent-profiles/cheap/massa-ai-navigator.md +73 -0
- package/agent-profiles/cheap/massa-ai-plan-critic.md +88 -0
- package/agent-profiles/cheap/massa-ai-planner.md +63 -0
- package/agent-profiles/cheap/massa-ai-requirements-analyst.md +62 -0
- package/agent-profiles/cheap/massa-ai-reviewer.md +64 -0
- package/agent-profiles/cheap/massa-ai-test-engineer.md +64 -0
- package/agent-profiles/cheap/massa-ai-verification-agent.md +63 -0
- package/agent-profiles/heavy/massa-ai-architecture-specialist.md +63 -0
- package/agent-profiles/heavy/massa-ai-audit-specialist.md +79 -0
- package/agent-profiles/heavy/massa-ai-builder.md +65 -0
- package/agent-profiles/heavy/massa-ai-context-curator.md +65 -0
- package/agent-profiles/heavy/massa-ai-documentation-agent.md +63 -0
- package/agent-profiles/heavy/massa-ai-furps-analyst.md +69 -0
- package/agent-profiles/heavy/massa-ai-investigator.md +66 -0
- package/agent-profiles/heavy/massa-ai-judge.md +100 -0
- package/agent-profiles/heavy/massa-ai-meta-judge.md +87 -0
- package/agent-profiles/heavy/massa-ai-mobile-specialist.md +80 -0
- package/agent-profiles/heavy/massa-ai-navigator.md +73 -0
- package/agent-profiles/heavy/massa-ai-plan-critic.md +88 -0
- package/agent-profiles/heavy/massa-ai-planner.md +63 -0
- package/agent-profiles/heavy/massa-ai-requirements-analyst.md +62 -0
- package/agent-profiles/heavy/massa-ai-reviewer.md +64 -0
- package/agent-profiles/heavy/massa-ai-test-engineer.md +64 -0
- package/agent-profiles/heavy/massa-ai-verification-agent.md +63 -0
- package/agent-profiles/home/massa-ai-architecture-specialist.md +63 -0
- package/agent-profiles/home/massa-ai-audit-specialist.md +79 -0
- package/agent-profiles/home/massa-ai-builder.md +65 -0
- package/agent-profiles/home/massa-ai-context-curator.md +65 -0
- package/agent-profiles/home/massa-ai-documentation-agent.md +63 -0
- package/agent-profiles/home/massa-ai-furps-analyst.md +69 -0
- package/agent-profiles/home/massa-ai-investigator.md +66 -0
- package/agent-profiles/home/massa-ai-judge.md +100 -0
- package/agent-profiles/home/massa-ai-meta-judge.md +87 -0
- package/agent-profiles/home/massa-ai-mobile-specialist.md +80 -0
- package/agent-profiles/home/massa-ai-navigator.md +73 -0
- package/agent-profiles/home/massa-ai-plan-critic.md +88 -0
- package/agent-profiles/home/massa-ai-planner.md +63 -0
- package/agent-profiles/home/massa-ai-requirements-analyst.md +62 -0
- package/agent-profiles/home/massa-ai-reviewer.md +64 -0
- package/agent-profiles/home/massa-ai-test-engineer.md +64 -0
- package/agent-profiles/home/massa-ai-verification-agent.md +63 -0
- package/agent-profiles/work/massa-ai-architecture-specialist.md +63 -0
- package/agent-profiles/work/massa-ai-audit-specialist.md +79 -0
- package/agent-profiles/work/massa-ai-builder.md +65 -0
- package/agent-profiles/work/massa-ai-context-curator.md +65 -0
- package/agent-profiles/work/massa-ai-documentation-agent.md +63 -0
- package/agent-profiles/work/massa-ai-furps-analyst.md +69 -0
- package/agent-profiles/work/massa-ai-investigator.md +66 -0
- package/agent-profiles/work/massa-ai-judge.md +100 -0
- package/agent-profiles/work/massa-ai-meta-judge.md +87 -0
- package/agent-profiles/work/massa-ai-mobile-specialist.md +80 -0
- package/agent-profiles/work/massa-ai-navigator.md +73 -0
- package/agent-profiles/work/massa-ai-plan-critic.md +88 -0
- package/agent-profiles/work/massa-ai-planner.md +63 -0
- package/agent-profiles/work/massa-ai-requirements-analyst.md +62 -0
- package/agent-profiles/work/massa-ai-reviewer.md +64 -0
- package/agent-profiles/work/massa-ai-test-engineer.md +64 -0
- package/agent-profiles/work/massa-ai-verification-agent.md +63 -0
- package/install.sh +103 -8
- package/package.json +2 -1
- package/skills/profile/SKILL.md +39 -0
package/install.sh
CHANGED
|
@@ -84,6 +84,15 @@ HOOK_BIN="$SCRIPT_DIR/hooks/massa-ai-hook.ts"
|
|
|
84
84
|
# for --project, so this resolves from $HOME, never from $SCOPE.
|
|
85
85
|
PLUGIN_REGISTRY="$HOME/.claude/plugins/installed_plugins.json"
|
|
86
86
|
|
|
87
|
+
# Model-profile variant tree (T8, design Component 3 / MPS-04). Source is the
|
|
88
|
+
# bundle's per-profile agent-profiles/<p>/ (sibling of agents/, A5); dest is
|
|
89
|
+
# the engine's own host path table (packages/shared/src/profile-switch/
|
|
90
|
+
# hosts.ts): $TARGET/massa-ai/agent-profiles/<p>/. File-route only — the
|
|
91
|
+
# marketplace route serves agents in place and switching is refused there
|
|
92
|
+
# regardless (Component 2 topology rules), so there is nothing to install to.
|
|
93
|
+
VARIANTS_SRC="$SCRIPT_DIR/agent-profiles"
|
|
94
|
+
VARIANTS_DEST="$TARGET/massa-ai/agent-profiles"
|
|
95
|
+
|
|
87
96
|
# The 5 Claude Code events → binary subcommands. The matcher-group entry shape:
|
|
88
97
|
# { "hooks": [{ "type": "command", "command": "bun run \"<HOOK_BIN>\" <sub>" }],
|
|
89
98
|
# "_massaAiOwned": true }
|
|
@@ -293,10 +302,22 @@ if (typeof data.platforms !== "object" || data.platforms === null || Array.isArr
|
|
|
293
302
|
data.version = 2;
|
|
294
303
|
const prev = data.platforms[host];
|
|
295
304
|
data.platforms[host] = { root, skillsOwner: "plugin", skills: ["massa-ai", "persona-router"] };
|
|
296
|
-
// The whole-record replace must not drop
|
|
297
|
-
//
|
|
298
|
-
|
|
299
|
-
|
|
305
|
+
// The whole-record replace must not drop fields a previous successful install
|
|
306
|
+
// wrote (R2) — re-attach them. modelProfile (T10, MPS-03 round-trip
|
|
307
|
+
// obligation) is engine-owned; installRoute is installer-owned but written by
|
|
308
|
+
// a LATER step of this same install (record_plugin_version) — both must
|
|
309
|
+
// survive this earlier whole-record replace or a switched profile / recorded
|
|
310
|
+
// route silently vanishes on the next skills-bundling pass.
|
|
311
|
+
if (prev && typeof prev === "object" && !Array.isArray(prev)) {
|
|
312
|
+
if (prev.plugin && typeof prev.plugin === "object") {
|
|
313
|
+
data.platforms[host].plugin = prev.plugin;
|
|
314
|
+
}
|
|
315
|
+
if (prev.modelProfile && typeof prev.modelProfile === "object") {
|
|
316
|
+
data.platforms[host].modelProfile = prev.modelProfile;
|
|
317
|
+
}
|
|
318
|
+
if (typeof prev.installRoute === "string") {
|
|
319
|
+
data.platforms[host].installRoute = prev.installRoute;
|
|
320
|
+
}
|
|
300
321
|
}
|
|
301
322
|
fs.mkdirSync(path.dirname(file), { recursive: true });
|
|
302
323
|
fs.writeFileSync(file, JSON.stringify(data, null, 2) + "\n");
|
|
@@ -372,18 +393,24 @@ record_plugin_version() {
|
|
|
372
393
|
return 0
|
|
373
394
|
fi
|
|
374
395
|
|
|
375
|
-
local version installed_at
|
|
396
|
+
local version installed_at route
|
|
376
397
|
version="$(sed -n 's/.*"version"[[:space:]]*:[[:space:]]*"\([^"]*\)".*/\1/p' "$SCRIPT_DIR/package.json" | head -n 1)"
|
|
377
398
|
installed_at="$(date -u +%Y-%m-%dT%H:%M:%SZ)"
|
|
399
|
+
# installRoute (T8, design F1): installer-owned, engine-read-only. The
|
|
400
|
+
# marketplace route (register_claude_plugin succeeded) serves agents in
|
|
401
|
+
# place from the bundle; the file route copies them into $TARGET/agents.
|
|
402
|
+
# Written on EVERY install path — an absent field is what makes the switch
|
|
403
|
+
# engine refuse loud rather than guess (hosts.ts detectRoute).
|
|
404
|
+
if [[ "$PLUGIN_ROUTE" -eq 1 ]]; then route="marketplace"; else route="file"; fi
|
|
378
405
|
|
|
379
406
|
# Tolerant of a corrupt/missing state file (rewrites a minimal valid one —
|
|
380
407
|
# AC-8). A record-write failure warns but never fails the install: the next
|
|
381
408
|
# run treats the host as unknown-version and reinstalls.
|
|
382
|
-
"$runner" - "$HARNESS_STATE_FILE" "$HARNESS_HOST" "$TARGET" "$version" "$installed_at" <<'NODE' || \
|
|
409
|
+
"$runner" - "$HARNESS_STATE_FILE" "$HARNESS_HOST" "$TARGET" "$version" "$installed_at" "$route" <<'NODE' || \
|
|
383
410
|
echo " ⚠ could not record the plugin version — next run will reinstall (unknown version)" >&2
|
|
384
411
|
const fs = require("fs");
|
|
385
412
|
const path = require("path");
|
|
386
|
-
const [, , file, host, root, version, installedAt] = process.argv;
|
|
413
|
+
const [, , file, host, root, version, installedAt, installRoute] = process.argv;
|
|
387
414
|
let data = { version: 2, platforms: {} };
|
|
388
415
|
try {
|
|
389
416
|
const existing = JSON.parse(fs.readFileSync(file, "utf8"));
|
|
@@ -400,12 +427,54 @@ const rec =
|
|
|
400
427
|
? data.platforms[host]
|
|
401
428
|
: { root, skillsOwner: "plugin", skills: [] };
|
|
402
429
|
rec.plugin = { version, installedAt };
|
|
430
|
+
// installRoute is installer-owned (like plugin above); modelProfile is NEVER
|
|
431
|
+
// written here — the switch engine (packages/shared/src/profile-switch/) is
|
|
432
|
+
// its sole writer, and this installer only ever reads it (see
|
|
433
|
+
// apply_recorded_profile below).
|
|
434
|
+
rec.installRoute = installRoute;
|
|
403
435
|
data.platforms[host] = rec;
|
|
404
436
|
fs.mkdirSync(path.dirname(file), { recursive: true });
|
|
405
437
|
fs.writeFileSync(file, JSON.stringify(data, null, 2) + "\n");
|
|
406
438
|
NODE
|
|
407
439
|
}
|
|
408
440
|
|
|
441
|
+
# ── Model-profile variant tree + recorded-profile re-apply (T8, MPS-04) ─────
|
|
442
|
+
# Read-side only: this installer never writes platforms[host].modelProfile —
|
|
443
|
+
# see the comment above record_plugin_version's NODE block. It only (a)
|
|
444
|
+
# refreshes the on-disk variant tree so an offline switch has files to copy
|
|
445
|
+
# from, and (b) re-applies a previously recorded profile's active agent set on
|
|
446
|
+
# install/upgrade, so a plugin upgrade never silently reverts a switched
|
|
447
|
+
# profile back to the shipped default.
|
|
448
|
+
install_variant_tree() {
|
|
449
|
+
[[ -d "$VARIANTS_SRC" ]] || return 0
|
|
450
|
+
rm -rf "$VARIANTS_DEST"
|
|
451
|
+
mkdir -p "$VARIANTS_DEST"
|
|
452
|
+
cp -R "$VARIANTS_SRC/." "$VARIANTS_DEST/"
|
|
453
|
+
vecho " + model-profile variant tree refreshed at $VARIANTS_DEST"
|
|
454
|
+
}
|
|
455
|
+
|
|
456
|
+
# Prints the recorded profile name (platforms[claude].modelProfile.profile),
|
|
457
|
+
# or an empty string when unset/unreadable. Never throws — a corrupt or
|
|
458
|
+
# missing state file just means "no recorded profile", not an install failure.
|
|
459
|
+
recorded_profile() {
|
|
460
|
+
local runner="$1"
|
|
461
|
+
"$runner" - "$HARNESS_STATE_FILE" "$HARNESS_HOST" <<'NODE'
|
|
462
|
+
const fs = require("fs");
|
|
463
|
+
const [, , file, host] = process.argv;
|
|
464
|
+
try {
|
|
465
|
+
const data = JSON.parse(fs.readFileSync(file, "utf8"));
|
|
466
|
+
const rec = data && data.platforms && data.platforms[host];
|
|
467
|
+
const profile =
|
|
468
|
+
rec && rec.modelProfile && typeof rec.modelProfile.profile === "string"
|
|
469
|
+
? rec.modelProfile.profile
|
|
470
|
+
: "";
|
|
471
|
+
process.stdout.write(profile);
|
|
472
|
+
} catch {
|
|
473
|
+
process.stdout.write("");
|
|
474
|
+
}
|
|
475
|
+
NODE
|
|
476
|
+
}
|
|
477
|
+
|
|
409
478
|
# ── Plugin-registry registration (delegated to the claude CLI) ──────────────
|
|
410
479
|
# The CLI owns the registry format, so it is the only supported way to make the
|
|
411
480
|
# plugin appear in /plugin. Every failure path returns non-zero and the caller
|
|
@@ -541,7 +610,31 @@ else
|
|
|
541
610
|
|
|
542
611
|
# Subagent specialists (generated from skills/agents/*/SKILL.md, navigator
|
|
543
612
|
# included). The massa-ai- name prefix is the ownership marker used by uninstall.
|
|
544
|
-
|
|
613
|
+
#
|
|
614
|
+
# Model-profile re-apply (T8, MPS-04): if a switch previously recorded a
|
|
615
|
+
# profile for this host, and the bundle ships that profile's variant, the
|
|
616
|
+
# ACTIVE set comes from agent-profiles/<profile>/ instead of the shipped
|
|
617
|
+
# default — an upgrade must never silently revert a switched profile.
|
|
618
|
+
# Recorded-but-missing-from-bundle is a loud fallback to the default, never
|
|
619
|
+
# a silent one.
|
|
620
|
+
ACTIVE_AGENTS_SRC="$SCRIPT_DIR/agents"
|
|
621
|
+
json_runner=""
|
|
622
|
+
if command -v node &>/dev/null; then json_runner="node"
|
|
623
|
+
elif command -v bun &>/dev/null; then json_runner="bun"
|
|
624
|
+
fi
|
|
625
|
+
if [[ -n "$json_runner" ]]; then
|
|
626
|
+
RECORDED_PROFILE="$(recorded_profile "$json_runner")"
|
|
627
|
+
if [[ -n "$RECORDED_PROFILE" ]]; then
|
|
628
|
+
if [[ -d "$VARIANTS_SRC/$RECORDED_PROFILE" ]]; then
|
|
629
|
+
ACTIVE_AGENTS_SRC="$VARIANTS_SRC/$RECORDED_PROFILE"
|
|
630
|
+
echo " ↷ re-applying recorded model profile '$RECORDED_PROFILE'"
|
|
631
|
+
else
|
|
632
|
+
echo " ⚠ recorded model profile '$RECORDED_PROFILE' is not in this bundle — falling back to the default profile" >&2
|
|
633
|
+
fi
|
|
634
|
+
fi
|
|
635
|
+
fi
|
|
636
|
+
|
|
637
|
+
for src in "$ACTIVE_AGENTS_SRC/"massa-ai-*.md; do
|
|
545
638
|
[[ -f "$src" ]] || continue
|
|
546
639
|
name="$(basename "$src")"
|
|
547
640
|
cp "$src" "$TARGET/agents/$name"
|
|
@@ -549,6 +642,8 @@ else
|
|
|
549
642
|
specialist_count=$((specialist_count + 1))
|
|
550
643
|
done
|
|
551
644
|
vecho " + ${specialist_count} subagent specialists (generated from skills/agents/*/SKILL.md)"
|
|
645
|
+
|
|
646
|
+
install_variant_tree
|
|
552
647
|
fi
|
|
553
648
|
|
|
554
649
|
# Skills bundling (PDO-08, 09): install massa-ai/persona-router into the
|
package/package.json
CHANGED
|
@@ -1,9 +1,10 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@massa-ai/claude-plugin",
|
|
3
|
-
"version": "1.
|
|
3
|
+
"version": "1.26.0",
|
|
4
4
|
"description": "massa-ai plugin for Claude Code — semantic code search, durable memory, symbol graph, and context compression",
|
|
5
5
|
"files": [
|
|
6
6
|
"agents",
|
|
7
|
+
"agent-profiles",
|
|
7
8
|
"commands",
|
|
8
9
|
"hooks",
|
|
9
10
|
"!hooks/__tests__",
|
|
@@ -0,0 +1,39 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: profile
|
|
3
|
+
description: Switch the installed massa-ai agents to a registry model profile (e.g. "work", "cheap", "home") or report the currently active profile per host. Use when the user asks to change/switch the model profile, asks which models the agents currently use, or asks to preview a profile switch. Do NOT use for editing the model registry itself (a registry edit is a massa-ai repository change, not a runtime switch) and do NOT claim the new profile is active before the user restarts the host session.
|
|
4
|
+
license: MIT
|
|
5
|
+
metadata:
|
|
6
|
+
author: Luiz Massa
|
|
7
|
+
version: 1.0.0
|
|
8
|
+
---
|
|
9
|
+
|
|
10
|
+
# Profile Switch Skill
|
|
11
|
+
|
|
12
|
+
## Mission
|
|
13
|
+
Drive the one massa-ai model-profile switch engine and relay its report — never a second implementation.
|
|
14
|
+
|
|
15
|
+
## When To Use
|
|
16
|
+
- The user asks to switch, change, or set the model profile (by name, e.g. "work", "cheap", "home", "balanced").
|
|
17
|
+
- The user asks what profile is currently active, or which profiles are shipped.
|
|
18
|
+
- The user asks to preview a switch without applying it.
|
|
19
|
+
|
|
20
|
+
## How To Drive It
|
|
21
|
+
There is exactly one switch implementation (`@massa-ai/shared`'s switch engine); every front — this skill, the MCP tools, and both `massa-ai-config` CLIs — calls the same engine and returns the same per-host report shape. Prefer whichever front is already available in the session:
|
|
22
|
+
|
|
23
|
+
- **MCP tools** (preferred when the massa-ai MCP server is connected): call `profile_list` to report shipped profiles + per-host active profile + bundle version, and `profile_set` to switch (`{profile, host?, dryRun?}`).
|
|
24
|
+
- **CLI fallback**: `massa-ai-config profile list` / `massa-ai-config profile show` / `massa-ai-config profile set <name> [--host <h>] [--dry-run]`.
|
|
25
|
+
|
|
26
|
+
Default to a dry run first when the user has not explicitly asked to apply the switch immediately — `dryRun: true` (MCP) or `--dry-run` (CLI) previews the per-host plan and changes nothing.
|
|
27
|
+
|
|
28
|
+
## Relaying The Result
|
|
29
|
+
Always relay the per-host outcome and the restart notice verbatim in substance, not just "done":
|
|
30
|
+
|
|
31
|
+
- Report each host as switched / skipped (with its reason) / unsupported (with its reason) / failed (with its reason). Cursor is always reported skipped — every tier resolves to inherit, so switching it is a no-op by design, not an error.
|
|
32
|
+
- When at least one host switched (non-dry-run), state explicitly that a session restart of that host is required before the new models take effect — hosts load agent definitions at session start; there is no live in-session switch.
|
|
33
|
+
- On a dry run, say so and that no files changed.
|
|
34
|
+
- On a fully failed request (e.g. unknown profile name), relay the named error and the list of profiles the report says are actually available — never guess a profile name.
|
|
35
|
+
|
|
36
|
+
## Restrictions
|
|
37
|
+
- Never invent a profile name; only use names the engine's own report lists as shipped/available.
|
|
38
|
+
- Never claim a profile switch is "live" before the affected host's session restarts.
|
|
39
|
+
- Never edit the model-profile registry (`skills/model-profiles.json`) to satisfy a switch request — that is a build-time registry change owned by a different workflow, not a runtime switch.
|