@mushi-mushi/mcp 0.20.2 → 0.21.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 +21 -4
- package/dist/catalog.js +1 -1
- package/dist/{chunk-RVZIKP4X.js → chunk-FNDGCFSJ.js} +9 -0
- package/dist/{chunk-ZSVRLSW5.js → chunk-XSL2FPLV.js} +1 -0
- package/dist/clients.d.ts +1 -1
- package/dist/clients.js +2 -2
- package/dist/feature-groups.js +1 -1
- package/dist/index.js +313 -234
- package/dist/server.d.ts +1 -1
- package/dist/server.js +284 -223
- package/package.json +5 -3
package/dist/server.js
CHANGED
|
@@ -3,17 +3,17 @@ import {
|
|
|
3
3
|
TDD_TOOL_CATALOG,
|
|
4
4
|
TOOL_CATALOG,
|
|
5
5
|
USE_MUSHI_INTENTS
|
|
6
|
-
} from "./chunk-
|
|
6
|
+
} from "./chunk-FNDGCFSJ.js";
|
|
7
7
|
import {
|
|
8
8
|
MUSHI_SERVER_METADATA
|
|
9
9
|
} from "./chunk-EANW5YTI.js";
|
|
10
10
|
import {
|
|
11
11
|
DEPRECATED_TOOL_ALIASES,
|
|
12
12
|
toolMatchesFeatures
|
|
13
|
-
} from "./chunk-
|
|
13
|
+
} from "./chunk-XSL2FPLV.js";
|
|
14
14
|
|
|
15
15
|
// src/server.ts
|
|
16
|
-
import { McpServer } from "@modelcontextprotocol/
|
|
16
|
+
import { McpServer } from "@modelcontextprotocol/server";
|
|
17
17
|
import { z } from "zod";
|
|
18
18
|
import { createLogger } from "@mushi-mushi/core";
|
|
19
19
|
|
|
@@ -211,7 +211,7 @@ function safeStringify(value) {
|
|
|
211
211
|
|
|
212
212
|
// src/server.ts
|
|
213
213
|
installStdoutGuard();
|
|
214
|
-
var NO_ARG_INPUT = {};
|
|
214
|
+
var NO_ARG_INPUT = z.object({});
|
|
215
215
|
var DEFAULT_API_TIMEOUT_MS = 15e3;
|
|
216
216
|
var MIN_API_TIMEOUT_MS = 250;
|
|
217
217
|
var MAX_API_TIMEOUT_MS = 3e5;
|
|
@@ -485,7 +485,7 @@ function createMushiServer(config) {
|
|
|
485
485
|
title: titleOf("get_recent_reports"),
|
|
486
486
|
description: descOf("get_recent_reports"),
|
|
487
487
|
annotations: annotationsFor("get_recent_reports"),
|
|
488
|
-
inputSchema: {
|
|
488
|
+
inputSchema: z.object({
|
|
489
489
|
status: z.string().optional().describe("Filter by status: new, classified, grouped, fixing, fixed, dismissed"),
|
|
490
490
|
category: z.string().optional().describe("Filter by category: bug, slow, visual, confusing, other"),
|
|
491
491
|
severity: z.string().optional().describe("Filter by severity: critical, high, medium, low"),
|
|
@@ -493,11 +493,11 @@ function createMushiServer(config) {
|
|
|
493
493
|
project_id: z.string().optional().describe(
|
|
494
494
|
"Project UUID \u2014 defaults to the server-configured project. Useful when you have multiple projects and want to query a specific one by its ID. Get IDs by calling list_projects or get_account_overview first."
|
|
495
495
|
)
|
|
496
|
-
},
|
|
497
|
-
outputSchema: {
|
|
496
|
+
}),
|
|
497
|
+
outputSchema: z.object({
|
|
498
498
|
reports: z.array(z.unknown()),
|
|
499
499
|
total: z.number()
|
|
500
|
-
}
|
|
500
|
+
})
|
|
501
501
|
},
|
|
502
502
|
async (args) => {
|
|
503
503
|
const params = new URLSearchParams();
|
|
@@ -522,11 +522,11 @@ function createMushiServer(config) {
|
|
|
522
522
|
title: titleOf("get_report_detail"),
|
|
523
523
|
description: descOf("get_report_detail"),
|
|
524
524
|
annotations: annotationsFor("get_report_detail"),
|
|
525
|
-
inputSchema: {
|
|
525
|
+
inputSchema: z.object({
|
|
526
526
|
reportId: z.string().describe("The report UUID"),
|
|
527
527
|
project_id: z.string().optional().describe("Project UUID \u2014 required for org-scoped keys with multiple projects.")
|
|
528
|
-
},
|
|
529
|
-
outputSchema: { report: z.unknown() }
|
|
528
|
+
}),
|
|
529
|
+
outputSchema: z.object({ report: z.unknown() })
|
|
530
530
|
},
|
|
531
531
|
async (args) => {
|
|
532
532
|
const { headers } = await projectScopeHeaders(args.project_id);
|
|
@@ -549,7 +549,7 @@ function createMushiServer(config) {
|
|
|
549
549
|
title: titleOf("get_report_timeline"),
|
|
550
550
|
description: descOf("get_report_timeline"),
|
|
551
551
|
annotations: annotationsFor("get_report_timeline"),
|
|
552
|
-
inputSchema: { reportId: z.string().describe("The report UUID") }
|
|
552
|
+
inputSchema: z.object({ reportId: z.string().describe("The report UUID") })
|
|
553
553
|
},
|
|
554
554
|
async (args) => jsonText(await apiCall(`/v1/sync/reports/${args.reportId}/timeline`))
|
|
555
555
|
);
|
|
@@ -569,14 +569,14 @@ function createMushiServer(config) {
|
|
|
569
569
|
title: titleOf("search_reports"),
|
|
570
570
|
description: descOf("search_reports"),
|
|
571
571
|
annotations: annotationsFor("search_reports"),
|
|
572
|
-
inputSchema: {
|
|
572
|
+
inputSchema: z.object({
|
|
573
573
|
query: z.string().describe("Natural-language search text or component path"),
|
|
574
574
|
limit: z.number().optional().describe("Max results (default 10, max 50)"),
|
|
575
575
|
threshold: z.number().optional().describe("Similarity threshold 0..1, default 0.2")
|
|
576
|
-
},
|
|
577
|
-
outputSchema: {
|
|
576
|
+
}),
|
|
577
|
+
outputSchema: z.object({
|
|
578
578
|
results: z.array(z.unknown())
|
|
579
|
-
}
|
|
579
|
+
})
|
|
580
580
|
},
|
|
581
581
|
async (args) => {
|
|
582
582
|
const data = await apiCall("/v1/admin/reports/similarity", {
|
|
@@ -597,13 +597,13 @@ function createMushiServer(config) {
|
|
|
597
597
|
title: titleOf("get_similar_bugs"),
|
|
598
598
|
description: descOf("get_similar_bugs"),
|
|
599
599
|
annotations: annotationsFor("get_similar_bugs"),
|
|
600
|
-
inputSchema: {
|
|
600
|
+
inputSchema: z.object({
|
|
601
601
|
query: z.string().describe("Component name, page path, or bug description"),
|
|
602
602
|
limit: z.number().optional().describe("Max results (default 5, max 20)")
|
|
603
|
-
},
|
|
604
|
-
outputSchema: {
|
|
603
|
+
}),
|
|
604
|
+
outputSchema: z.object({
|
|
605
605
|
results: z.array(z.unknown())
|
|
606
|
-
}
|
|
606
|
+
})
|
|
607
607
|
},
|
|
608
608
|
async (args) => {
|
|
609
609
|
const data = await apiCall("/v1/admin/reports/similarity", {
|
|
@@ -624,18 +624,18 @@ function createMushiServer(config) {
|
|
|
624
624
|
title: titleOf("get_fix_context"),
|
|
625
625
|
description: descOf("get_fix_context"),
|
|
626
626
|
annotations: annotationsFor("get_fix_context"),
|
|
627
|
-
inputSchema: {
|
|
627
|
+
inputSchema: z.object({
|
|
628
628
|
reportId: z.string().describe("The report UUID to fix"),
|
|
629
629
|
project_id: z.string().optional().describe("Project UUID \u2014 required for org-scoped keys with multiple projects.")
|
|
630
|
-
},
|
|
631
|
-
outputSchema: {
|
|
630
|
+
}),
|
|
631
|
+
outputSchema: z.object({
|
|
632
632
|
report: z.unknown(),
|
|
633
633
|
fixPrompt: z.unknown(),
|
|
634
634
|
reproductionSteps: z.unknown(),
|
|
635
635
|
component: z.unknown(),
|
|
636
636
|
rootCause: z.unknown(),
|
|
637
637
|
bugOntologyTags: z.unknown()
|
|
638
|
-
}
|
|
638
|
+
})
|
|
639
639
|
},
|
|
640
640
|
async (args) => {
|
|
641
641
|
const { headers } = await projectScopeHeaders(args.project_id);
|
|
@@ -664,10 +664,10 @@ function createMushiServer(config) {
|
|
|
664
664
|
title: titleOf("get_fix_timeline"),
|
|
665
665
|
description: descOf("get_fix_timeline"),
|
|
666
666
|
annotations: annotationsFor("get_fix_timeline"),
|
|
667
|
-
inputSchema: {
|
|
667
|
+
inputSchema: z.object({
|
|
668
668
|
fixId: z.string().describe("fix_attempt UUID"),
|
|
669
669
|
project_id: z.string().optional().describe("Project UUID \u2014 required for org-scoped keys with multiple projects.")
|
|
670
|
-
}
|
|
670
|
+
})
|
|
671
671
|
},
|
|
672
672
|
async (args) => {
|
|
673
673
|
const { headers } = await projectScopeHeaders(args.project_id);
|
|
@@ -680,7 +680,7 @@ function createMushiServer(config) {
|
|
|
680
680
|
title: titleOf("get_blast_radius"),
|
|
681
681
|
description: descOf("get_blast_radius"),
|
|
682
682
|
annotations: annotationsFor("get_blast_radius"),
|
|
683
|
-
inputSchema: { nodeId: z.string().describe("Graph node UUID") }
|
|
683
|
+
inputSchema: z.object({ nodeId: z.string().describe("Graph node UUID") })
|
|
684
684
|
},
|
|
685
685
|
async (args) => jsonText(await apiCall(`/v1/admin/graph/blast-radius/${args.nodeId}`))
|
|
686
686
|
);
|
|
@@ -690,14 +690,14 @@ function createMushiServer(config) {
|
|
|
690
690
|
title: titleOf("get_knowledge_graph"),
|
|
691
691
|
description: descOf("get_knowledge_graph"),
|
|
692
692
|
annotations: annotationsFor("get_knowledge_graph"),
|
|
693
|
-
inputSchema: {
|
|
693
|
+
inputSchema: z.object({
|
|
694
694
|
seed: z.string().describe("Starting graph node id or human-readable label to traverse from"),
|
|
695
695
|
depth: z.number().optional().describe("BFS hops outward from seed \u2014 clamped to 4 in the handler (default 2)")
|
|
696
|
-
},
|
|
697
|
-
outputSchema: {
|
|
696
|
+
}),
|
|
697
|
+
outputSchema: z.object({
|
|
698
698
|
nodes: z.array(z.unknown()).describe("Graph nodes within the depth budget"),
|
|
699
699
|
edges: z.array(z.unknown()).describe("Edges connecting the returned nodes")
|
|
700
|
-
}
|
|
700
|
+
})
|
|
701
701
|
},
|
|
702
702
|
async (args) => {
|
|
703
703
|
const params = new URLSearchParams({
|
|
@@ -716,16 +716,16 @@ function createMushiServer(config) {
|
|
|
716
716
|
title: titleOf("get_graph_neighborhood"),
|
|
717
717
|
description: descOf("get_graph_neighborhood"),
|
|
718
718
|
annotations: annotationsFor("get_graph_neighborhood"),
|
|
719
|
-
inputSchema: {
|
|
719
|
+
inputSchema: z.object({
|
|
720
720
|
seed: z.string().describe(
|
|
721
721
|
"Starting graph node id or label to expand around (e.g. an inventory Action id or component name)"
|
|
722
722
|
),
|
|
723
723
|
depth: z.number().int().min(1).max(4).optional().describe("BFS hops to traverse outward. Default 2; clamped to a max of 4.")
|
|
724
|
-
},
|
|
725
|
-
outputSchema: {
|
|
724
|
+
}),
|
|
725
|
+
outputSchema: z.object({
|
|
726
726
|
nodes: z.array(z.unknown()).describe("Graph nodes within the depth budget"),
|
|
727
727
|
edges: z.array(z.unknown()).describe("Edges connecting the returned nodes")
|
|
728
|
-
}
|
|
728
|
+
})
|
|
729
729
|
},
|
|
730
730
|
async (args) => {
|
|
731
731
|
const params = new URLSearchParams({
|
|
@@ -744,12 +744,12 @@ function createMushiServer(config) {
|
|
|
744
744
|
title: titleOf("get_graph_node"),
|
|
745
745
|
description: descOf("get_graph_node"),
|
|
746
746
|
annotations: annotationsFor("get_graph_node"),
|
|
747
|
-
inputSchema: {
|
|
747
|
+
inputSchema: z.object({
|
|
748
748
|
nodeId: z.string().describe("The graph_nodes.id of the node to fetch (UUID).")
|
|
749
|
-
},
|
|
750
|
-
outputSchema: {
|
|
749
|
+
}),
|
|
750
|
+
outputSchema: z.object({
|
|
751
751
|
node: z.unknown().describe("Single graph_nodes row including metadata (Action nodes carry v2 status)")
|
|
752
|
-
}
|
|
752
|
+
})
|
|
753
753
|
},
|
|
754
754
|
async (args) => {
|
|
755
755
|
const data = await apiCall(`/v1/admin/graph/node/${args.nodeId}`);
|
|
@@ -762,9 +762,9 @@ function createMushiServer(config) {
|
|
|
762
762
|
title: titleOf("get_inventory"),
|
|
763
763
|
description: descOf("get_inventory"),
|
|
764
764
|
annotations: annotationsFor("get_inventory"),
|
|
765
|
-
inputSchema: {
|
|
765
|
+
inputSchema: z.object({
|
|
766
766
|
projectId: z.string().optional().describe("Project UUID \u2014 defaults to the server-configured project when omitted")
|
|
767
|
-
}
|
|
767
|
+
})
|
|
768
768
|
},
|
|
769
769
|
async (args) => {
|
|
770
770
|
const pid = args.projectId ?? projectId;
|
|
@@ -779,11 +779,11 @@ function createMushiServer(config) {
|
|
|
779
779
|
title: titleOf("diff_inventory"),
|
|
780
780
|
description: descOf("diff_inventory"),
|
|
781
781
|
annotations: annotationsFor("diff_inventory"),
|
|
782
|
-
inputSchema: {
|
|
782
|
+
inputSchema: z.object({
|
|
783
783
|
projectId: z.string().optional().describe("Project UUID \u2014 defaults to configured project"),
|
|
784
784
|
fromSha: z.string().describe("Older commit SHA (the baseline to diff from)"),
|
|
785
785
|
toSha: z.string().describe("Newer commit SHA (the candidate to diff to)")
|
|
786
|
-
}
|
|
786
|
+
})
|
|
787
787
|
},
|
|
788
788
|
async (args) => {
|
|
789
789
|
const pid = args.projectId ?? projectId;
|
|
@@ -799,15 +799,15 @@ function createMushiServer(config) {
|
|
|
799
799
|
title: titleOf("list_gate_findings"),
|
|
800
800
|
description: descOf("list_gate_findings"),
|
|
801
801
|
annotations: annotationsFor("list_gate_findings"),
|
|
802
|
-
inputSchema: {
|
|
802
|
+
inputSchema: z.object({
|
|
803
803
|
projectId: z.string().optional().describe("Project UUID \u2014 defaults to configured project"),
|
|
804
804
|
gate: z.string().optional().describe("Filter to one gate id: dead-handler | mock-leak | crawl | status-claim"),
|
|
805
805
|
severity: z.string().optional().describe("Minimum severity to include: low | medium | high | critical")
|
|
806
|
-
},
|
|
807
|
-
outputSchema: {
|
|
806
|
+
}),
|
|
807
|
+
outputSchema: z.object({
|
|
808
808
|
runs: z.array(z.unknown()).describe("Recent gate_runs rows, newest first"),
|
|
809
809
|
findings: z.array(z.unknown()).describe("gate_findings rows for those runs")
|
|
810
|
-
}
|
|
810
|
+
})
|
|
811
811
|
},
|
|
812
812
|
async (args) => {
|
|
813
813
|
const pid = args.projectId ?? projectId;
|
|
@@ -833,18 +833,20 @@ function createMushiServer(config) {
|
|
|
833
833
|
title: titleOf("suggest_fix"),
|
|
834
834
|
description: descOf("suggest_fix"),
|
|
835
835
|
annotations: annotationsFor("suggest_fix"),
|
|
836
|
-
inputSchema: {
|
|
836
|
+
inputSchema: z.object({
|
|
837
837
|
reportId: z.string().describe("Report UUID to read the Stage-2 suggested-fix slice for")
|
|
838
|
-
},
|
|
839
|
-
outputSchema: {
|
|
838
|
+
}),
|
|
839
|
+
outputSchema: z.object({
|
|
840
840
|
reportId: z.string().describe("The report this slice was read from"),
|
|
841
841
|
rootCause: z.unknown().describe("Stage-2 root-cause hint, or null if not yet classified"),
|
|
842
842
|
suggestedFix: z.unknown().describe("Stage-2 suggested fix, or null if not yet classified"),
|
|
843
843
|
reproductionSteps: z.unknown().describe("Reproduction steps recorded on the report (array; [] if none)"),
|
|
844
844
|
summary: z.unknown().describe("One-line report summary, or null"),
|
|
845
845
|
component: z.unknown().describe("Component/page the bug was attributed to, or null"),
|
|
846
|
-
note: z.string().optional().describe(
|
|
847
|
-
|
|
846
|
+
note: z.string().optional().describe(
|
|
847
|
+
"Present when no Stage-2 analysis exists \u2014 explains why and what to call instead"
|
|
848
|
+
)
|
|
849
|
+
})
|
|
848
850
|
},
|
|
849
851
|
async (args) => {
|
|
850
852
|
const report = await apiCall(`/v1/admin/reports/${args.reportId}`);
|
|
@@ -876,11 +878,11 @@ function createMushiServer(config) {
|
|
|
876
878
|
title: titleOf("run_nl_query"),
|
|
877
879
|
description: descOf("run_nl_query"),
|
|
878
880
|
annotations: annotationsFor("run_nl_query"),
|
|
879
|
-
inputSchema: {
|
|
881
|
+
inputSchema: z.object({
|
|
880
882
|
question: z.string().describe(
|
|
881
883
|
'Question in plain English, e.g. "Which components had the most critical bugs this week?"'
|
|
882
884
|
)
|
|
883
|
-
}
|
|
885
|
+
})
|
|
884
886
|
},
|
|
885
887
|
async (args) => {
|
|
886
888
|
const data = await apiCall("/v1/admin/query", {
|
|
@@ -896,14 +898,14 @@ function createMushiServer(config) {
|
|
|
896
898
|
title: titleOf("diagnose_setup"),
|
|
897
899
|
description: descOf("diagnose_setup"),
|
|
898
900
|
annotations: annotationsFor("diagnose_setup"),
|
|
899
|
-
inputSchema: {
|
|
901
|
+
inputSchema: z.object({
|
|
900
902
|
mode: z.enum(["full", "ingest", "dispatch"]).optional().describe(
|
|
901
903
|
"full (default) = ingest + dispatch; ingest = SDK pipeline only; dispatch = fix preflight only."
|
|
902
904
|
),
|
|
903
905
|
project_id: z.string().optional().describe("Project UUID for dispatch checks (defaults to configured project)."),
|
|
904
906
|
projectId: z.string().optional().describe("Alias for project_id.")
|
|
905
|
-
},
|
|
906
|
-
outputSchema: {
|
|
907
|
+
}),
|
|
908
|
+
outputSchema: z.object({
|
|
907
909
|
mode: z.string(),
|
|
908
910
|
ready: z.boolean(),
|
|
909
911
|
summary: z.string(),
|
|
@@ -911,7 +913,7 @@ function createMushiServer(config) {
|
|
|
911
913
|
ingest: z.unknown().optional(),
|
|
912
914
|
dispatch: z.unknown().optional(),
|
|
913
915
|
connection: z.unknown().optional()
|
|
914
|
-
}
|
|
916
|
+
})
|
|
915
917
|
},
|
|
916
918
|
async (args) => {
|
|
917
919
|
const mode = args.mode ?? "full";
|
|
@@ -1050,17 +1052,71 @@ function createMushiServer(config) {
|
|
|
1050
1052
|
});
|
|
1051
1053
|
}
|
|
1052
1054
|
);
|
|
1055
|
+
server.registerTool(
|
|
1056
|
+
"check_sdk_version",
|
|
1057
|
+
{
|
|
1058
|
+
title: titleOf("check_sdk_version"),
|
|
1059
|
+
description: descOf("check_sdk_version"),
|
|
1060
|
+
annotations: annotationsFor("check_sdk_version"),
|
|
1061
|
+
inputSchema: z.object({
|
|
1062
|
+
package: z.string().optional().describe(
|
|
1063
|
+
"npm package name (default @mushi-mushi/web). Examples: @mushi-mushi/web, @mushi-mushi/node, @mushi-mushi/core."
|
|
1064
|
+
),
|
|
1065
|
+
current: z.string().optional().describe("Installed version from package.json, if known (e.g. 1.27.0).")
|
|
1066
|
+
}),
|
|
1067
|
+
outputSchema: z.object({
|
|
1068
|
+
package: z.string(),
|
|
1069
|
+
latest: z.string().optional(),
|
|
1070
|
+
current: z.string().optional(),
|
|
1071
|
+
outdated: z.boolean().optional(),
|
|
1072
|
+
suggestedActions: z.array(
|
|
1073
|
+
z.object({
|
|
1074
|
+
type: z.literal("tool_call"),
|
|
1075
|
+
toolName: z.string(),
|
|
1076
|
+
arguments: z.record(z.string(), z.unknown()),
|
|
1077
|
+
reason: z.string()
|
|
1078
|
+
})
|
|
1079
|
+
).optional()
|
|
1080
|
+
})
|
|
1081
|
+
},
|
|
1082
|
+
async (args) => {
|
|
1083
|
+
const pkg = args.package?.trim() || "@mushi-mushi/web";
|
|
1084
|
+
const query = new URLSearchParams({ package: pkg }).toString();
|
|
1085
|
+
const data = await apiCall(
|
|
1086
|
+
`/v1/sdk/latest-version?${query}`
|
|
1087
|
+
);
|
|
1088
|
+
const latest = data.latest ?? data.version;
|
|
1089
|
+
const current = args.current;
|
|
1090
|
+
const outdated = current && latest ? current !== latest : void 0;
|
|
1091
|
+
return jsonResult({
|
|
1092
|
+
package: data.package ?? pkg,
|
|
1093
|
+
latest,
|
|
1094
|
+
current,
|
|
1095
|
+
outdated,
|
|
1096
|
+
...outdated ? {
|
|
1097
|
+
suggestedActions: [
|
|
1098
|
+
{
|
|
1099
|
+
type: "tool_call",
|
|
1100
|
+
toolName: "search_mushi_docs",
|
|
1101
|
+
arguments: { query: `${pkg} upgrade mushi-sdk-upgrade` },
|
|
1102
|
+
reason: "Read current upgrade notes, then apply the mushi-sdk-upgrade skill. This tool does not bump the pin."
|
|
1103
|
+
}
|
|
1104
|
+
]
|
|
1105
|
+
} : {}
|
|
1106
|
+
});
|
|
1107
|
+
}
|
|
1108
|
+
);
|
|
1053
1109
|
server.registerTool(
|
|
1054
1110
|
"search_mushi_docs",
|
|
1055
1111
|
{
|
|
1056
1112
|
title: titleOf("search_mushi_docs"),
|
|
1057
1113
|
description: descOf("search_mushi_docs"),
|
|
1058
1114
|
annotations: annotationsFor("search_mushi_docs"),
|
|
1059
|
-
inputSchema: {
|
|
1115
|
+
inputSchema: z.object({
|
|
1060
1116
|
query: z.string().describe("Keywords to search official Mushi docs (guides, MCP, inventory, QA)."),
|
|
1061
1117
|
limit: z.number().int().min(1).max(20).optional().describe("Max results (default 8).")
|
|
1062
|
-
},
|
|
1063
|
-
outputSchema: {
|
|
1118
|
+
}),
|
|
1119
|
+
outputSchema: z.object({
|
|
1064
1120
|
query: z.string(),
|
|
1065
1121
|
results: z.array(
|
|
1066
1122
|
z.object({
|
|
@@ -1070,7 +1126,7 @@ function createMushiServer(config) {
|
|
|
1070
1126
|
score: z.number()
|
|
1071
1127
|
})
|
|
1072
1128
|
)
|
|
1073
|
-
}
|
|
1129
|
+
})
|
|
1074
1130
|
},
|
|
1075
1131
|
async (args) => {
|
|
1076
1132
|
const query = args.query ?? "";
|
|
@@ -1091,11 +1147,11 @@ function createMushiServer(config) {
|
|
|
1091
1147
|
description: descOf("list_projects"),
|
|
1092
1148
|
annotations: annotationsFor("list_projects"),
|
|
1093
1149
|
inputSchema: NO_ARG_INPUT,
|
|
1094
|
-
outputSchema: {
|
|
1150
|
+
outputSchema: z.object({
|
|
1095
1151
|
projects: z.array(z.unknown()),
|
|
1096
1152
|
total: z.number().optional(),
|
|
1097
1153
|
_multi_project_hint: z.string().optional()
|
|
1098
|
-
}
|
|
1154
|
+
})
|
|
1099
1155
|
},
|
|
1100
1156
|
async () => {
|
|
1101
1157
|
const data = await apiCall("/v1/admin/mcp/projects");
|
|
@@ -1112,7 +1168,7 @@ function createMushiServer(config) {
|
|
|
1112
1168
|
description: descOf("get_account_overview"),
|
|
1113
1169
|
annotations: annotationsFor("get_account_overview"),
|
|
1114
1170
|
inputSchema: NO_ARG_INPUT,
|
|
1115
|
-
outputSchema: {
|
|
1171
|
+
outputSchema: z.object({
|
|
1116
1172
|
projects: z.array(z.unknown()),
|
|
1117
1173
|
total: z.number(),
|
|
1118
1174
|
active_project_id: z.string().nullable(),
|
|
@@ -1120,7 +1176,7 @@ function createMushiServer(config) {
|
|
|
1120
1176
|
resourceCount: z.number().optional(),
|
|
1121
1177
|
promptCount: z.number().optional(),
|
|
1122
1178
|
multi_project_hint: z.string()
|
|
1123
|
-
}
|
|
1179
|
+
})
|
|
1124
1180
|
},
|
|
1125
1181
|
async () => {
|
|
1126
1182
|
const data = await apiCall("/v1/admin/mcp/account-overview");
|
|
@@ -1142,9 +1198,9 @@ function createMushiServer(config) {
|
|
|
1142
1198
|
title: titleOf("get_project_context"),
|
|
1143
1199
|
description: descOf("get_project_context"),
|
|
1144
1200
|
annotations: annotationsFor("get_project_context"),
|
|
1145
|
-
inputSchema: {
|
|
1201
|
+
inputSchema: z.object({
|
|
1146
1202
|
project_id: z.string().optional().describe("Project UUID. Defaults to configured project.")
|
|
1147
|
-
}
|
|
1203
|
+
})
|
|
1148
1204
|
},
|
|
1149
1205
|
async (args) => {
|
|
1150
1206
|
const pid = args.project_id ?? projectId;
|
|
@@ -1166,13 +1222,13 @@ function createMushiServer(config) {
|
|
|
1166
1222
|
title: titleOf("get_pipeline_logs"),
|
|
1167
1223
|
description: descOf("get_pipeline_logs"),
|
|
1168
1224
|
annotations: annotationsFor("get_pipeline_logs"),
|
|
1169
|
-
inputSchema: {
|
|
1225
|
+
inputSchema: z.object({
|
|
1170
1226
|
project_id: z.string().optional().describe("Project UUID. Defaults to configured project."),
|
|
1171
1227
|
service: z.enum(["fix-worker", "qa-story-runner", "pipeline", "all"]).optional().describe("Pipeline service to filter (default: all)."),
|
|
1172
1228
|
since: z.string().optional().describe("ISO-8601 timestamp \u2014 return only entries after this time."),
|
|
1173
1229
|
limit: z.number().optional().describe("Max entries to return (default 50, max 200)."),
|
|
1174
1230
|
level: z.enum(["info", "warn", "error", "fatal"]).optional().describe("Minimum severity level (default: warn).")
|
|
1175
|
-
}
|
|
1231
|
+
})
|
|
1176
1232
|
},
|
|
1177
1233
|
async (args) => {
|
|
1178
1234
|
const pid = args.project_id ?? projectId;
|
|
@@ -1192,9 +1248,9 @@ function createMushiServer(config) {
|
|
|
1192
1248
|
title: titleOf("get_report_evidence"),
|
|
1193
1249
|
description: descOf("get_report_evidence"),
|
|
1194
1250
|
annotations: annotationsFor("get_report_evidence"),
|
|
1195
|
-
inputSchema: {
|
|
1251
|
+
inputSchema: z.object({
|
|
1196
1252
|
report_id: z.string().describe("Report UUID.")
|
|
1197
|
-
}
|
|
1253
|
+
})
|
|
1198
1254
|
},
|
|
1199
1255
|
async (args) => {
|
|
1200
1256
|
const [reportRes, timelineRes] = await Promise.allSettled([
|
|
@@ -1242,12 +1298,12 @@ function createMushiServer(config) {
|
|
|
1242
1298
|
title: titleOf("triage_issue"),
|
|
1243
1299
|
description: descOf("triage_issue"),
|
|
1244
1300
|
annotations: annotationsFor("triage_issue"),
|
|
1245
|
-
inputSchema: {
|
|
1301
|
+
inputSchema: z.object({
|
|
1246
1302
|
report_id: z.string().uuid().describe("Report UUID to triage."),
|
|
1247
1303
|
project_id: z.string().optional().describe("Project UUID. Defaults to configured project."),
|
|
1248
1304
|
include_logs: z.boolean().optional().describe("Include recent pipeline logs in triage packet (default: true).")
|
|
1249
|
-
},
|
|
1250
|
-
outputSchema: {
|
|
1305
|
+
}),
|
|
1306
|
+
outputSchema: z.object({
|
|
1251
1307
|
report_id: z.string(),
|
|
1252
1308
|
severity: z.unknown(),
|
|
1253
1309
|
category: z.unknown(),
|
|
@@ -1260,7 +1316,7 @@ function createMushiServer(config) {
|
|
|
1260
1316
|
recent_logs: z.unknown().nullable(),
|
|
1261
1317
|
recommended_actions: z.array(z.unknown()),
|
|
1262
1318
|
triage_summary: z.string()
|
|
1263
|
-
}
|
|
1319
|
+
})
|
|
1264
1320
|
},
|
|
1265
1321
|
async (args) => {
|
|
1266
1322
|
const { projectId: pid, headers } = await projectScopeHeaders(args.project_id);
|
|
@@ -1384,7 +1440,7 @@ function createMushiServer(config) {
|
|
|
1384
1440
|
title: titleOf("submit_fix_result"),
|
|
1385
1441
|
description: descOf("submit_fix_result"),
|
|
1386
1442
|
annotations: annotationsFor("submit_fix_result"),
|
|
1387
|
-
inputSchema: {
|
|
1443
|
+
inputSchema: z.object({
|
|
1388
1444
|
reportId: z.string().describe("Report UUID to attach this external fix attempt to"),
|
|
1389
1445
|
branch: z.string().describe("Git branch name where the fix was implemented"),
|
|
1390
1446
|
prUrl: z.string().optional().describe("GitHub pull request URL, if a PR was opened"),
|
|
@@ -1394,19 +1450,14 @@ function createMushiServer(config) {
|
|
|
1394
1450
|
idempotencyKey: z.string().uuid().optional().describe(
|
|
1395
1451
|
"Optional UUID \u2014 resend the same key to safely retry without creating duplicate fix rows. Omit it and a stable key is derived from reportId + branch + prUrl, so a retried submission carries the identical key instead of a fresh random one."
|
|
1396
1452
|
)
|
|
1397
|
-
},
|
|
1398
|
-
outputSchema: {
|
|
1453
|
+
}),
|
|
1454
|
+
outputSchema: z.object({
|
|
1399
1455
|
ok: z.boolean().describe("True when the fix_attempt row was created and marked completed"),
|
|
1400
1456
|
fixId: z.string().describe("UUID of the new fix_attempt row")
|
|
1401
|
-
}
|
|
1457
|
+
})
|
|
1402
1458
|
},
|
|
1403
1459
|
async (args) => {
|
|
1404
|
-
const idemKey = args.idempotencyKey ?? await stableUuidFrom(
|
|
1405
|
-
IDEMPOTENCY_NAMESPACE,
|
|
1406
|
-
args.reportId,
|
|
1407
|
-
args.branch,
|
|
1408
|
-
args.prUrl ?? ""
|
|
1409
|
-
);
|
|
1460
|
+
const idemKey = args.idempotencyKey ?? await stableUuidFrom(IDEMPOTENCY_NAMESPACE, args.reportId, args.branch, args.prUrl ?? "");
|
|
1410
1461
|
const created = await apiCall("/v1/admin/fixes", {
|
|
1411
1462
|
method: "POST",
|
|
1412
1463
|
headers: { "Idempotency-Key": idemKey },
|
|
@@ -1442,10 +1493,10 @@ function createMushiServer(config) {
|
|
|
1442
1493
|
title: titleOf("triage_next_steps"),
|
|
1443
1494
|
description: descOf("triage_next_steps"),
|
|
1444
1495
|
annotations: annotationsFor("triage_next_steps"),
|
|
1445
|
-
inputSchema: {
|
|
1496
|
+
inputSchema: z.object({
|
|
1446
1497
|
project_id: z.string().uuid().optional().describe("Project UUID (defaults to the configured project).")
|
|
1447
|
-
},
|
|
1448
|
-
outputSchema: {
|
|
1498
|
+
}),
|
|
1499
|
+
outputSchema: z.object({
|
|
1449
1500
|
steps: z.array(
|
|
1450
1501
|
z.object({
|
|
1451
1502
|
priority: z.number(),
|
|
@@ -1456,7 +1507,7 @@ function createMushiServer(config) {
|
|
|
1456
1507
|
})
|
|
1457
1508
|
),
|
|
1458
1509
|
summary: z.string()
|
|
1459
|
-
}
|
|
1510
|
+
})
|
|
1460
1511
|
},
|
|
1461
1512
|
async (args) => {
|
|
1462
1513
|
const pid = await resolveProjectId(args.project_id);
|
|
@@ -1491,7 +1542,9 @@ function createMushiServer(config) {
|
|
|
1491
1542
|
args: { report_id: r.id }
|
|
1492
1543
|
});
|
|
1493
1544
|
}
|
|
1494
|
-
const openUserReports = reports.filter(
|
|
1545
|
+
const openUserReports = reports.filter(
|
|
1546
|
+
(r) => (r.status === "new" || r.status === "classified") && !isCron(r) && !isBlocked(r)
|
|
1547
|
+
).sort((a, b) => {
|
|
1495
1548
|
const rank = { critical: 0, high: 1, medium: 2, low: 3 };
|
|
1496
1549
|
return (rank[String(a.severity)] ?? 4) - (rank[String(b.severity)] ?? 4);
|
|
1497
1550
|
});
|
|
@@ -1524,7 +1577,7 @@ function createMushiServer(config) {
|
|
|
1524
1577
|
title: titleOf("dispatch_fix"),
|
|
1525
1578
|
description: descOf("dispatch_fix"),
|
|
1526
1579
|
annotations: annotationsFor("dispatch_fix"),
|
|
1527
|
-
inputSchema: {
|
|
1580
|
+
inputSchema: z.object({
|
|
1528
1581
|
reportId: z.string().uuid().describe("Report UUID to fix"),
|
|
1529
1582
|
agent: z.enum(["claude_code", "codex", "rest_worker", "mcp"]).optional().describe("Override the agent adapter"),
|
|
1530
1583
|
idempotencyKey: z.string().uuid().optional().describe(
|
|
@@ -1533,19 +1586,19 @@ function createMushiServer(config) {
|
|
|
1533
1586
|
inventoryActionNodeId: z.string().uuid().optional().describe(
|
|
1534
1587
|
"Optional inventory Action node UUID for spec-traceability (\xA72.10). When provided, the fix-worker embeds the expected_outcome contract in the LLM prompt and runs validateAgainstSpec before opening the PR."
|
|
1535
1588
|
)
|
|
1536
|
-
},
|
|
1537
|
-
outputSchema: {
|
|
1589
|
+
}),
|
|
1590
|
+
outputSchema: z.object({
|
|
1538
1591
|
fixId: z.string(),
|
|
1539
1592
|
status: z.string()
|
|
1540
|
-
}
|
|
1593
|
+
})
|
|
1541
1594
|
},
|
|
1542
|
-
async (args,
|
|
1543
|
-
if (
|
|
1595
|
+
async (args, ctx) => {
|
|
1596
|
+
if (ctx?.mcpReq.notify && ctx?.mcpReq._meta?.progressToken) {
|
|
1544
1597
|
try {
|
|
1545
|
-
await
|
|
1598
|
+
await ctx.mcpReq.notify({
|
|
1546
1599
|
method: "notifications/progress",
|
|
1547
1600
|
params: {
|
|
1548
|
-
progressToken:
|
|
1601
|
+
progressToken: ctx.mcpReq._meta.progressToken,
|
|
1549
1602
|
progress: 0,
|
|
1550
1603
|
total: 100,
|
|
1551
1604
|
message: "Dispatching Mushi fix orchestrator\u2026"
|
|
@@ -1578,13 +1631,13 @@ function createMushiServer(config) {
|
|
|
1578
1631
|
title: titleOf("trigger_judge"),
|
|
1579
1632
|
description: descOf("trigger_judge"),
|
|
1580
1633
|
annotations: annotationsFor("trigger_judge"),
|
|
1581
|
-
inputSchema: {
|
|
1634
|
+
inputSchema: z.object({
|
|
1582
1635
|
limit: z.number().optional().describe("Max reports to judge in this batch (default 25, max 100)"),
|
|
1583
1636
|
projectId: z.string().optional().describe("Restrict to one project when the API key owns multiple")
|
|
1584
|
-
},
|
|
1585
|
-
outputSchema: {
|
|
1637
|
+
}),
|
|
1638
|
+
outputSchema: z.object({
|
|
1586
1639
|
dispatched: z.number().describe("Number of judge-batch jobs dispatched (one per accessible project)")
|
|
1587
|
-
}
|
|
1640
|
+
})
|
|
1588
1641
|
},
|
|
1589
1642
|
async (args) => {
|
|
1590
1643
|
const data = await apiCall("/v1/admin/judge/run", {
|
|
@@ -1603,10 +1656,10 @@ function createMushiServer(config) {
|
|
|
1603
1656
|
title: titleOf("test_gen_from_report"),
|
|
1604
1657
|
description: descOf("test_gen_from_report"),
|
|
1605
1658
|
annotations: annotationsFor("test_gen_from_report"),
|
|
1606
|
-
inputSchema: {
|
|
1659
|
+
inputSchema: z.object({
|
|
1607
1660
|
reportId: z.string().describe("Report UUID to turn into a Playwright PR"),
|
|
1608
1661
|
projectId: z.string().optional().describe("Project UUID \u2014 defaults to configured project")
|
|
1609
|
-
}
|
|
1662
|
+
})
|
|
1610
1663
|
},
|
|
1611
1664
|
async (args) => {
|
|
1612
1665
|
const pid = args.projectId ?? projectId;
|
|
@@ -1632,16 +1685,16 @@ function createMushiServer(config) {
|
|
|
1632
1685
|
title: titleOf("merge_fix"),
|
|
1633
1686
|
description: descOf("merge_fix"),
|
|
1634
1687
|
annotations: annotationsFor("merge_fix"),
|
|
1635
|
-
inputSchema: {
|
|
1688
|
+
inputSchema: z.object({
|
|
1636
1689
|
fixId: z.string().describe("Fix attempt UUID whose GitHub PR should be squash-merged"),
|
|
1637
1690
|
mergeMethod: z.enum(["squash", "merge", "rebase"]).optional().describe("GitHub merge method (default squash)")
|
|
1638
|
-
},
|
|
1639
|
-
outputSchema: {
|
|
1691
|
+
}),
|
|
1692
|
+
outputSchema: z.object({
|
|
1640
1693
|
merged: z.boolean().optional().describe("True when GitHub accepted the merge in this call"),
|
|
1641
1694
|
alreadyMerged: z.boolean().optional().describe("True when the PR was already merged (idempotent no-op)"),
|
|
1642
1695
|
reportId: z.string().describe("Report UUID linked to this fix attempt"),
|
|
1643
1696
|
reportStatus: z.string().describe("Report workflow status after merge bookkeeping")
|
|
1644
|
-
}
|
|
1697
|
+
})
|
|
1645
1698
|
},
|
|
1646
1699
|
async (args) => {
|
|
1647
1700
|
const data = await apiCall(`/v1/admin/fixes/${args.fixId}/merge`, {
|
|
@@ -1657,14 +1710,14 @@ function createMushiServer(config) {
|
|
|
1657
1710
|
title: titleOf("refresh_ci"),
|
|
1658
1711
|
description: descOf("refresh_ci"),
|
|
1659
1712
|
annotations: annotationsFor("refresh_ci"),
|
|
1660
|
-
inputSchema: {
|
|
1713
|
+
inputSchema: z.object({
|
|
1661
1714
|
fixId: z.string().describe("Fix attempt UUID whose PR check-runs should be re-polled")
|
|
1662
|
-
},
|
|
1663
|
-
outputSchema: {
|
|
1715
|
+
}),
|
|
1716
|
+
outputSchema: z.object({
|
|
1664
1717
|
check_run_status: z.string().nullable().describe("GitHub check run status after refresh"),
|
|
1665
1718
|
check_run_conclusion: z.string().nullable().describe("success | failure | neutral | null while pending"),
|
|
1666
1719
|
check_run_updated_at: z.string().nullable().describe("ISO timestamp when CI status was last persisted")
|
|
1667
|
-
}
|
|
1720
|
+
})
|
|
1668
1721
|
},
|
|
1669
1722
|
async (args) => {
|
|
1670
1723
|
const data = await apiCall(`/v1/admin/fixes/${args.fixId}/refresh-ci`, { method: "POST" });
|
|
@@ -1677,13 +1730,13 @@ function createMushiServer(config) {
|
|
|
1677
1730
|
title: titleOf("reopen_report"),
|
|
1678
1731
|
description: descOf("reopen_report"),
|
|
1679
1732
|
annotations: annotationsFor("reopen_report"),
|
|
1680
|
-
inputSchema: {
|
|
1733
|
+
inputSchema: z.object({
|
|
1681
1734
|
reportId: z.string().describe("Report UUID to move back to reopened status"),
|
|
1682
1735
|
note: z.string().optional().describe("Operator note recorded on the reopen transition")
|
|
1683
|
-
},
|
|
1684
|
-
outputSchema: {
|
|
1736
|
+
}),
|
|
1737
|
+
outputSchema: z.object({
|
|
1685
1738
|
report: z.unknown().describe("Updated report row with status=reopened")
|
|
1686
|
-
}
|
|
1739
|
+
})
|
|
1687
1740
|
},
|
|
1688
1741
|
async (args) => {
|
|
1689
1742
|
const report = await apiCall(`/v1/sync/reports/${args.reportId}`, {
|
|
@@ -1699,7 +1752,7 @@ function createMushiServer(config) {
|
|
|
1699
1752
|
title: titleOf("transition_status"),
|
|
1700
1753
|
description: descOf("transition_status"),
|
|
1701
1754
|
annotations: annotationsFor("transition_status"),
|
|
1702
|
-
inputSchema: {
|
|
1755
|
+
inputSchema: z.object({
|
|
1703
1756
|
reportId: z.string().describe("Report UUID"),
|
|
1704
1757
|
status: z.enum([
|
|
1705
1758
|
"pending",
|
|
@@ -1718,7 +1771,7 @@ function createMushiServer(config) {
|
|
|
1718
1771
|
"dismissed"
|
|
1719
1772
|
]).describe("Target status (resolved is stored as fixed)"),
|
|
1720
1773
|
reason: z.string().optional().describe("Reason for the transition (audit trail)")
|
|
1721
|
-
}
|
|
1774
|
+
})
|
|
1722
1775
|
},
|
|
1723
1776
|
async (args) => {
|
|
1724
1777
|
const data = await apiCall(`/v1/admin/reports/${args.reportId}`, {
|
|
@@ -1734,9 +1787,9 @@ function createMushiServer(config) {
|
|
|
1734
1787
|
title: titleOf("setup_repo_for_mushi"),
|
|
1735
1788
|
description: descOf("setup_repo_for_mushi"),
|
|
1736
1789
|
annotations: annotationsFor("setup_repo_for_mushi"),
|
|
1737
|
-
inputSchema: {
|
|
1790
|
+
inputSchema: z.object({
|
|
1738
1791
|
projectId: z.string().optional().describe("Project UUID \u2014 defaults to configured project")
|
|
1739
|
-
}
|
|
1792
|
+
})
|
|
1740
1793
|
},
|
|
1741
1794
|
async (args) => {
|
|
1742
1795
|
const pid = args.projectId ?? projectId;
|
|
@@ -1759,12 +1812,12 @@ function createMushiServer(config) {
|
|
|
1759
1812
|
title: titleOf("query_lessons"),
|
|
1760
1813
|
description: descOf("query_lessons"),
|
|
1761
1814
|
annotations: annotationsFor("query_lessons"),
|
|
1762
|
-
inputSchema: {
|
|
1815
|
+
inputSchema: z.object({
|
|
1763
1816
|
diff_text: z.string().describe("The PR diff, code snippet, or description of the change being made."),
|
|
1764
1817
|
max_tokens: z.number().optional().describe("Maximum tokens for returned lessons context (default 3000, max 8000)."),
|
|
1765
1818
|
top_k: z.number().optional().describe("Max number of lessons to return (default 15, max 50)."),
|
|
1766
1819
|
project_id: z.string().optional().describe("Project UUID. Defaults to configured project.")
|
|
1767
|
-
}
|
|
1820
|
+
})
|
|
1768
1821
|
},
|
|
1769
1822
|
async (args) => {
|
|
1770
1823
|
const pid = args.project_id ?? projectId;
|
|
@@ -1786,14 +1839,14 @@ function createMushiServer(config) {
|
|
|
1786
1839
|
title: titleOf("list_lessons"),
|
|
1787
1840
|
description: descOf("list_lessons"),
|
|
1788
1841
|
annotations: annotationsFor("list_lessons"),
|
|
1789
|
-
inputSchema: {
|
|
1842
|
+
inputSchema: z.object({
|
|
1790
1843
|
severity: z.enum(["info", "warn", "critical"]).optional().describe("Filter to one severity level"),
|
|
1791
1844
|
limit: z.number().optional().describe("Max lessons to return (default 50, max 200)"),
|
|
1792
1845
|
project_id: z.string().optional().describe("Project UUID \u2014 defaults to configured project")
|
|
1793
|
-
},
|
|
1794
|
-
outputSchema: {
|
|
1846
|
+
}),
|
|
1847
|
+
outputSchema: z.object({
|
|
1795
1848
|
lessons: z.array(z.unknown()).describe("Promoted lesson rows ordered by frequency")
|
|
1796
|
-
}
|
|
1849
|
+
})
|
|
1797
1850
|
},
|
|
1798
1851
|
async (args) => {
|
|
1799
1852
|
const pid = args.project_id ?? projectId;
|
|
@@ -1805,7 +1858,7 @@ function createMushiServer(config) {
|
|
|
1805
1858
|
return wrappedJsonResult({ lessons }, "lesson text");
|
|
1806
1859
|
}
|
|
1807
1860
|
);
|
|
1808
|
-
server.
|
|
1861
|
+
server.registerResource(
|
|
1809
1862
|
"project_stats",
|
|
1810
1863
|
"project://stats",
|
|
1811
1864
|
{ description: "Report counts, category breakdown, severity distribution" },
|
|
@@ -1819,7 +1872,7 @@ function createMushiServer(config) {
|
|
|
1819
1872
|
]
|
|
1820
1873
|
})
|
|
1821
1874
|
);
|
|
1822
|
-
server.
|
|
1875
|
+
server.registerResource(
|
|
1823
1876
|
"project_settings",
|
|
1824
1877
|
"project://settings",
|
|
1825
1878
|
{
|
|
@@ -1835,7 +1888,7 @@ function createMushiServer(config) {
|
|
|
1835
1888
|
]
|
|
1836
1889
|
})
|
|
1837
1890
|
);
|
|
1838
|
-
server.
|
|
1891
|
+
server.registerResource(
|
|
1839
1892
|
"project_dashboard",
|
|
1840
1893
|
"project://dashboard",
|
|
1841
1894
|
{
|
|
@@ -1857,10 +1910,10 @@ function createMushiServer(config) {
|
|
|
1857
1910
|
title: titleOf("list_top_contributors"),
|
|
1858
1911
|
description: descOf("list_top_contributors"),
|
|
1859
1912
|
annotations: annotationsFor("list_top_contributors"),
|
|
1860
|
-
inputSchema: {
|
|
1913
|
+
inputSchema: z.object({
|
|
1861
1914
|
limit: z.number().int().min(1).max(100).optional().default(10).describe("Max rows to return (default 10, max 100)"),
|
|
1862
1915
|
range: z.enum(["30d", "90d", "all"]).optional().default("30d").describe("Time window for points calculation")
|
|
1863
|
-
}
|
|
1916
|
+
})
|
|
1864
1917
|
},
|
|
1865
1918
|
async ({ limit, range }) => ({
|
|
1866
1919
|
content: [
|
|
@@ -1881,11 +1934,11 @@ function createMushiServer(config) {
|
|
|
1881
1934
|
title: titleOf("award_bonus_points"),
|
|
1882
1935
|
description: descOf("award_bonus_points"),
|
|
1883
1936
|
annotations: annotationsFor("award_bonus_points"),
|
|
1884
|
-
inputSchema: {
|
|
1937
|
+
inputSchema: z.object({
|
|
1885
1938
|
external_user_id: z.string().describe("The host-app user id as passed to Mushi.identify()"),
|
|
1886
1939
|
points: z.number().int().min(1).max(5e4).describe("Bonus points to award (max 50,000 per call)"),
|
|
1887
1940
|
reason: z.string().max(200).describe("Human-readable reason, logged to end_user_activity")
|
|
1888
|
-
}
|
|
1941
|
+
})
|
|
1889
1942
|
},
|
|
1890
1943
|
async ({ external_user_id, points, reason }) => ({
|
|
1891
1944
|
content: [
|
|
@@ -1910,11 +1963,11 @@ function createMushiServer(config) {
|
|
|
1910
1963
|
title: titleOf("set_tier"),
|
|
1911
1964
|
description: descOf("set_tier"),
|
|
1912
1965
|
annotations: annotationsFor("set_tier"),
|
|
1913
|
-
inputSchema: {
|
|
1966
|
+
inputSchema: z.object({
|
|
1914
1967
|
external_user_id: z.string().describe("The host-app user id as passed to Mushi.identify()"),
|
|
1915
1968
|
tier_slug: z.string().describe('Tier slug to assign, e.g. "champion", "contributor", "explorer"'),
|
|
1916
1969
|
reason: z.string().max(200).optional().describe("Optional reason for manual override")
|
|
1917
|
-
}
|
|
1970
|
+
})
|
|
1918
1971
|
},
|
|
1919
1972
|
async ({ external_user_id, tier_slug, reason }) => ({
|
|
1920
1973
|
content: [
|
|
@@ -1933,7 +1986,7 @@ function createMushiServer(config) {
|
|
|
1933
1986
|
]
|
|
1934
1987
|
})
|
|
1935
1988
|
);
|
|
1936
|
-
server.
|
|
1989
|
+
server.registerResource(
|
|
1937
1990
|
"privacy_status",
|
|
1938
1991
|
"privacy://status",
|
|
1939
1992
|
{
|
|
@@ -1949,7 +2002,7 @@ function createMushiServer(config) {
|
|
|
1949
2002
|
]
|
|
1950
2003
|
})
|
|
1951
2004
|
);
|
|
1952
|
-
server.
|
|
2005
|
+
server.registerResource(
|
|
1953
2006
|
"evolution_history",
|
|
1954
2007
|
"evolution://history",
|
|
1955
2008
|
{
|
|
@@ -1971,7 +2024,7 @@ function createMushiServer(config) {
|
|
|
1971
2024
|
]
|
|
1972
2025
|
})
|
|
1973
2026
|
);
|
|
1974
|
-
server.
|
|
2027
|
+
server.registerResource(
|
|
1975
2028
|
"project_integration_health",
|
|
1976
2029
|
"project://integration-health",
|
|
1977
2030
|
{
|
|
@@ -1987,7 +2040,7 @@ function createMushiServer(config) {
|
|
|
1987
2040
|
]
|
|
1988
2041
|
})
|
|
1989
2042
|
);
|
|
1990
|
-
server.
|
|
2043
|
+
server.registerResource(
|
|
1991
2044
|
"inventory_current",
|
|
1992
2045
|
"inventory://current",
|
|
1993
2046
|
{
|
|
@@ -2012,9 +2065,9 @@ function createMushiServer(config) {
|
|
|
2012
2065
|
title: titleOf("activation_status"),
|
|
2013
2066
|
description: descOf("activation_status"),
|
|
2014
2067
|
annotations: annotationsFor("activation_status"),
|
|
2015
|
-
inputSchema: {
|
|
2068
|
+
inputSchema: z.object({
|
|
2016
2069
|
project_id: z.string().optional().describe("Project UUID (defaults to the configured project).")
|
|
2017
|
-
}
|
|
2070
|
+
})
|
|
2018
2071
|
},
|
|
2019
2072
|
async (args) => {
|
|
2020
2073
|
const pid = args.project_id ?? projectId;
|
|
@@ -2022,7 +2075,7 @@ function createMushiServer(config) {
|
|
|
2022
2075
|
return jsonResult(await apiCall(`/v1/admin/activation${qs}`));
|
|
2023
2076
|
}
|
|
2024
2077
|
);
|
|
2025
|
-
server.
|
|
2078
|
+
server.registerResource(
|
|
2026
2079
|
"activation_status",
|
|
2027
2080
|
"mushi://activation",
|
|
2028
2081
|
{
|
|
@@ -2041,10 +2094,12 @@ function createMushiServer(config) {
|
|
|
2041
2094
|
};
|
|
2042
2095
|
}
|
|
2043
2096
|
);
|
|
2044
|
-
server.
|
|
2097
|
+
server.registerPrompt(
|
|
2045
2098
|
"summarize_report_for_fix",
|
|
2046
|
-
|
|
2047
|
-
|
|
2099
|
+
{
|
|
2100
|
+
description: "Turn a Mushi report into a one-line root cause, smallest file set, repro steps, and blast-radius warnings. Use before asking an agent to write the patch.",
|
|
2101
|
+
argsSchema: z.object({ reportId: z.string().describe("The report UUID to summarize") })
|
|
2102
|
+
},
|
|
2048
2103
|
({ reportId }) => ({
|
|
2049
2104
|
messages: [
|
|
2050
2105
|
{
|
|
@@ -2069,10 +2124,12 @@ Lead with the fix. Skip the preamble.`
|
|
|
2069
2124
|
]
|
|
2070
2125
|
})
|
|
2071
2126
|
);
|
|
2072
|
-
server.
|
|
2127
|
+
server.registerPrompt(
|
|
2073
2128
|
"explain_judge_result",
|
|
2074
|
-
|
|
2075
|
-
|
|
2129
|
+
{
|
|
2130
|
+
description: "Turn raw Sonnet-as-Judge scores into ship / iterate / dismiss guidance. Use after a fix attempt has been judged.",
|
|
2131
|
+
argsSchema: z.object({ fixId: z.string().describe("The fix_attempt UUID to explain") })
|
|
2132
|
+
},
|
|
2076
2133
|
({ fixId }) => ({
|
|
2077
2134
|
messages: [
|
|
2078
2135
|
{
|
|
@@ -2093,10 +2150,12 @@ No preamble, no score-by-score recap \u2014 the numbers are in the tool output.`
|
|
|
2093
2150
|
]
|
|
2094
2151
|
})
|
|
2095
2152
|
);
|
|
2096
|
-
server.
|
|
2153
|
+
server.registerPrompt(
|
|
2097
2154
|
"triage_next_steps",
|
|
2098
|
-
|
|
2099
|
-
|
|
2155
|
+
{
|
|
2156
|
+
description: 'Answer "what should I focus on right now?" \u2014 five-item markdown list drawn from the dashboard + recent classified queue.',
|
|
2157
|
+
argsSchema: z.object({})
|
|
2158
|
+
},
|
|
2100
2159
|
() => ({
|
|
2101
2160
|
messages: [
|
|
2102
2161
|
{
|
|
@@ -2116,10 +2175,12 @@ Prefer items that are bottlenecks or critical severity. Skip filler.`
|
|
|
2116
2175
|
]
|
|
2117
2176
|
})
|
|
2118
2177
|
);
|
|
2119
|
-
server.
|
|
2178
|
+
server.registerPrompt(
|
|
2120
2179
|
"mushi_setup",
|
|
2121
|
-
|
|
2122
|
-
|
|
2180
|
+
{
|
|
2181
|
+
description: "Diagnose why Mushi setup is stuck and return the single next command or console step to unblock it.",
|
|
2182
|
+
argsSchema: z.object({})
|
|
2183
|
+
},
|
|
2123
2184
|
() => ({
|
|
2124
2185
|
messages: [
|
|
2125
2186
|
{
|
|
@@ -2149,13 +2210,13 @@ Be specific. No generic advice.`
|
|
|
2149
2210
|
title: titleOf("map_user_stories", TDD_TOOL_CATALOG),
|
|
2150
2211
|
description: descOf("map_user_stories", TDD_TOOL_CATALOG),
|
|
2151
2212
|
annotations: annotationsFor("map_user_stories", TDD_TOOL_CATALOG),
|
|
2152
|
-
inputSchema: {
|
|
2213
|
+
inputSchema: z.object({
|
|
2153
2214
|
projectId: z.string().describe("Project id to map stories for"),
|
|
2154
2215
|
baseUrl: z.string().url().describe("Live app URL to crawl"),
|
|
2155
2216
|
maxPages: z.number().int().min(1).max(50).optional().describe("Max pages to crawl (default 20)"),
|
|
2156
2217
|
provider: z.enum(["firecrawl", "browserbase"]).optional().describe("Crawl provider (default: firecrawl)"),
|
|
2157
2218
|
cursorCloudRefine: z.boolean().optional().describe("Dispatch Cursor Cloud agent to refine and open a PR")
|
|
2158
|
-
}
|
|
2219
|
+
})
|
|
2159
2220
|
},
|
|
2160
2221
|
async ({ projectId: projectId2, baseUrl, maxPages, provider, cursorCloudRefine }) => {
|
|
2161
2222
|
if (!projectId2) throw new MushiApiError(400, "MISSING_PROJECT", "projectId is required");
|
|
@@ -2180,9 +2241,9 @@ Be specific. No generic advice.`
|
|
|
2180
2241
|
title: titleOf("get_map_run_status", TDD_TOOL_CATALOG),
|
|
2181
2242
|
description: descOf("get_map_run_status", TDD_TOOL_CATALOG),
|
|
2182
2243
|
annotations: annotationsFor("get_map_run_status", TDD_TOOL_CATALOG),
|
|
2183
|
-
inputSchema: {
|
|
2244
|
+
inputSchema: z.object({
|
|
2184
2245
|
projectId: z.string().describe("Project id")
|
|
2185
|
-
}
|
|
2246
|
+
})
|
|
2186
2247
|
},
|
|
2187
2248
|
async ({ projectId: projectId2 }) => {
|
|
2188
2249
|
const data = await apiCall(`/v1/admin/inventory/${projectId2}/map-runs`);
|
|
@@ -2195,7 +2256,7 @@ Be specific. No generic advice.`
|
|
|
2195
2256
|
title: titleOf("generate_tdd_from_story", TDD_TOOL_CATALOG),
|
|
2196
2257
|
description: descOf("generate_tdd_from_story", TDD_TOOL_CATALOG),
|
|
2197
2258
|
annotations: annotationsFor("generate_tdd_from_story", TDD_TOOL_CATALOG),
|
|
2198
|
-
inputSchema: {
|
|
2259
|
+
inputSchema: z.object({
|
|
2199
2260
|
projectId: z.string().describe("Project UUID that owns the inventory story"),
|
|
2200
2261
|
storyNodeId: z.string().describe(
|
|
2201
2262
|
"User story node id/slug from accepted inventory (from map_user_stories or inventory.yaml)"
|
|
@@ -2203,13 +2264,13 @@ Be specific. No generic advice.`
|
|
|
2203
2264
|
automationMode: z.enum(["auto", "review", "approve"]).optional().describe("Approval gate for the generated qa_story (default review \u2192 pending_review)"),
|
|
2204
2265
|
baseUrl: z.string().url().optional().describe("Override the live app URL the Playwright test should target"),
|
|
2205
2266
|
openPr: z.boolean().optional().describe("Open a draft GitHub PR with the generated spec (default true)")
|
|
2206
|
-
},
|
|
2207
|
-
outputSchema: {
|
|
2267
|
+
}),
|
|
2268
|
+
outputSchema: z.object({
|
|
2208
2269
|
qaStoryId: z.string().describe("UUID of the inserted qa_stories row"),
|
|
2209
2270
|
prUrl: z.string().nullable().describe("GitHub PR URL when openPr=true and GitHub is connected"),
|
|
2210
2271
|
approvalStatus: z.string().describe("pending_review | approved \u2014 follows automationMode and project defaults"),
|
|
2211
2272
|
needsHumanReview: z.boolean().describe("True when the story requires operator approval before scheduled runs")
|
|
2212
|
-
}
|
|
2273
|
+
})
|
|
2213
2274
|
},
|
|
2214
2275
|
async ({ projectId: projectId2, storyNodeId, automationMode, baseUrl, openPr }) => {
|
|
2215
2276
|
if (!projectId2) throw new MushiApiError(400, "MISSING_PROJECT", "projectId is required");
|
|
@@ -2230,9 +2291,9 @@ Be specific. No generic advice.`
|
|
|
2230
2291
|
title: titleOf("improve_qa_story", TDD_TOOL_CATALOG),
|
|
2231
2292
|
description: descOf("improve_qa_story", TDD_TOOL_CATALOG),
|
|
2232
2293
|
annotations: annotationsFor("improve_qa_story", TDD_TOOL_CATALOG),
|
|
2233
|
-
inputSchema: {
|
|
2294
|
+
inputSchema: z.object({
|
|
2234
2295
|
projectId: z.string().optional().describe("Project id (omit to run across all projects)")
|
|
2235
|
-
}
|
|
2296
|
+
})
|
|
2236
2297
|
},
|
|
2237
2298
|
async ({ projectId: projectId2 }) => {
|
|
2238
2299
|
const data = await apiCall("/v1/admin/pdca/improve-qa-stories", {
|
|
@@ -2248,10 +2309,10 @@ Be specific. No generic advice.`
|
|
|
2248
2309
|
title: titleOf("run_qa_story", TDD_TOOL_CATALOG),
|
|
2249
2310
|
description: descOf("run_qa_story", TDD_TOOL_CATALOG),
|
|
2250
2311
|
annotations: annotationsFor("run_qa_story", TDD_TOOL_CATALOG),
|
|
2251
|
-
inputSchema: {
|
|
2312
|
+
inputSchema: z.object({
|
|
2252
2313
|
projectId: z.string().describe("Project id"),
|
|
2253
2314
|
qaStoryId: z.string().describe("qa_story id to run")
|
|
2254
|
-
}
|
|
2315
|
+
})
|
|
2255
2316
|
},
|
|
2256
2317
|
async ({ projectId: projectId2, qaStoryId }) => {
|
|
2257
2318
|
const data = await apiCall(
|
|
@@ -2267,9 +2328,9 @@ Be specific. No generic advice.`
|
|
|
2267
2328
|
title: titleOf("list_byok_keys", TDD_TOOL_CATALOG),
|
|
2268
2329
|
description: descOf("list_byok_keys", TDD_TOOL_CATALOG),
|
|
2269
2330
|
annotations: annotationsFor("list_byok_keys", TDD_TOOL_CATALOG),
|
|
2270
|
-
inputSchema: {
|
|
2331
|
+
inputSchema: z.object({
|
|
2271
2332
|
projectId: z.string().describe("Project id")
|
|
2272
|
-
}
|
|
2333
|
+
})
|
|
2273
2334
|
},
|
|
2274
2335
|
async ({ projectId: projectId2 }) => {
|
|
2275
2336
|
const data = await apiCall(
|
|
@@ -2284,14 +2345,14 @@ Be specific. No generic advice.`
|
|
|
2284
2345
|
title: titleOf("add_byok_key", TDD_TOOL_CATALOG),
|
|
2285
2346
|
description: descOf("add_byok_key", TDD_TOOL_CATALOG),
|
|
2286
2347
|
annotations: annotationsFor("add_byok_key", TDD_TOOL_CATALOG),
|
|
2287
|
-
inputSchema: {
|
|
2348
|
+
inputSchema: z.object({
|
|
2288
2349
|
projectId: z.string().describe("Project id"),
|
|
2289
2350
|
provider: z.enum(["anthropic", "openai", "firecrawl", "browserbase", "cursor"]).describe("Provider slug"),
|
|
2290
2351
|
key: z.string().min(8).max(4096).describe("The API key value to add"),
|
|
2291
2352
|
label: z.string().optional().describe("Human-readable label for this key"),
|
|
2292
2353
|
priority: z.number().int().min(0).max(1e4).optional().describe("Priority for ordering (lower = higher priority)"),
|
|
2293
2354
|
baseUrl: z.string().url().max(2048).optional().describe("Allow-listed OpenAI-compatible HTTPS base URL")
|
|
2294
|
-
}
|
|
2355
|
+
})
|
|
2295
2356
|
},
|
|
2296
2357
|
async ({ projectId: projectId2, provider, key, label, priority, baseUrl }) => {
|
|
2297
2358
|
const data = await apiCall("/v1/admin/byok/keys", {
|
|
@@ -2314,10 +2375,10 @@ Be specific. No generic advice.`
|
|
|
2314
2375
|
title: titleOf("test_byok_key", TDD_TOOL_CATALOG),
|
|
2315
2376
|
description: descOf("test_byok_key", TDD_TOOL_CATALOG),
|
|
2316
2377
|
annotations: annotationsFor("test_byok_key", TDD_TOOL_CATALOG),
|
|
2317
|
-
inputSchema: {
|
|
2378
|
+
inputSchema: z.object({
|
|
2318
2379
|
projectId: z.string().describe("Project id"),
|
|
2319
2380
|
keyId: z.string().uuid().describe("Pooled BYOK key id")
|
|
2320
|
-
}
|
|
2381
|
+
})
|
|
2321
2382
|
},
|
|
2322
2383
|
async ({ keyId }) => {
|
|
2323
2384
|
const data = await apiCall(`/v1/admin/byok/keys/${encodeURIComponent(keyId)}/test`, {
|
|
@@ -2332,10 +2393,10 @@ Be specific. No generic advice.`
|
|
|
2332
2393
|
title: titleOf("remove_byok_key", TDD_TOOL_CATALOG),
|
|
2333
2394
|
description: descOf("remove_byok_key", TDD_TOOL_CATALOG),
|
|
2334
2395
|
annotations: annotationsFor("remove_byok_key", TDD_TOOL_CATALOG),
|
|
2335
|
-
inputSchema: {
|
|
2396
|
+
inputSchema: z.object({
|
|
2336
2397
|
projectId: z.string().describe("Project id"),
|
|
2337
2398
|
keyId: z.string().uuid().describe("Pooled BYOK key UUID from list_byok_keys")
|
|
2338
|
-
}
|
|
2399
|
+
})
|
|
2339
2400
|
},
|
|
2340
2401
|
async ({ keyId }) => {
|
|
2341
2402
|
const data = await apiCall(`/v1/admin/byok/keys/${encodeURIComponent(keyId)}`, {
|
|
@@ -2350,9 +2411,9 @@ Be specific. No generic advice.`
|
|
|
2350
2411
|
title: titleOf("list_pending_review_stories", TDD_TOOL_CATALOG),
|
|
2351
2412
|
description: descOf("list_pending_review_stories", TDD_TOOL_CATALOG),
|
|
2352
2413
|
annotations: annotationsFor("list_pending_review_stories", TDD_TOOL_CATALOG),
|
|
2353
|
-
inputSchema: {
|
|
2414
|
+
inputSchema: z.object({
|
|
2354
2415
|
projectId: z.string().describe("Project id")
|
|
2355
|
-
}
|
|
2416
|
+
})
|
|
2356
2417
|
},
|
|
2357
2418
|
async ({ projectId: projectId2 }) => {
|
|
2358
2419
|
const data = await apiCall(
|
|
@@ -2367,11 +2428,11 @@ Be specific. No generic advice.`
|
|
|
2367
2428
|
title: titleOf("approve_qa_story", TDD_TOOL_CATALOG),
|
|
2368
2429
|
description: descOf("approve_qa_story", TDD_TOOL_CATALOG),
|
|
2369
2430
|
annotations: annotationsFor("approve_qa_story", TDD_TOOL_CATALOG),
|
|
2370
|
-
inputSchema: {
|
|
2431
|
+
inputSchema: z.object({
|
|
2371
2432
|
projectId: z.string().describe("Project id"),
|
|
2372
2433
|
qaStoryId: z.string().describe("QA story id to approve or reject"),
|
|
2373
2434
|
status: z.enum(["approved", "rejected"]).describe("New approval status")
|
|
2374
|
-
}
|
|
2435
|
+
})
|
|
2375
2436
|
},
|
|
2376
2437
|
async ({ projectId: projectId2, qaStoryId, status }) => {
|
|
2377
2438
|
const data = await apiCall(
|
|
@@ -2387,11 +2448,11 @@ Be specific. No generic advice.`
|
|
|
2387
2448
|
title: titleOf("reply_to_reporter", TDD_TOOL_CATALOG),
|
|
2388
2449
|
description: descOf("reply_to_reporter", TDD_TOOL_CATALOG),
|
|
2389
2450
|
annotations: annotationsFor("reply_to_reporter", TDD_TOOL_CATALOG),
|
|
2390
|
-
inputSchema: {
|
|
2451
|
+
inputSchema: z.object({
|
|
2391
2452
|
reportId: z.string().describe("Report id to reply to"),
|
|
2392
2453
|
message: z.string().min(1).max(1e4).describe("Message text to send to the reporter"),
|
|
2393
2454
|
authorName: z.string().optional().describe('Display name for the admin sender (default: "Mushi Admin")')
|
|
2394
|
-
}
|
|
2455
|
+
})
|
|
2395
2456
|
},
|
|
2396
2457
|
async ({ reportId, message, authorName }) => {
|
|
2397
2458
|
const data = await apiCall(`/v1/sync/reports/${reportId}/reply`, {
|
|
@@ -2407,10 +2468,10 @@ Be specific. No generic advice.`
|
|
|
2407
2468
|
title: titleOf("list_qa_story_runs", TDD_TOOL_CATALOG),
|
|
2408
2469
|
description: descOf("list_qa_story_runs", TDD_TOOL_CATALOG),
|
|
2409
2470
|
annotations: annotationsFor("list_qa_story_runs", TDD_TOOL_CATALOG),
|
|
2410
|
-
inputSchema: {
|
|
2471
|
+
inputSchema: z.object({
|
|
2411
2472
|
storyId: z.string().describe("QA story id (uuid)"),
|
|
2412
2473
|
limit: z.number().int().min(1).max(50).optional().default(10).describe("Max runs to return (default 10)")
|
|
2413
|
-
}
|
|
2474
|
+
})
|
|
2414
2475
|
},
|
|
2415
2476
|
async ({ storyId, limit }) => {
|
|
2416
2477
|
const data = await apiCall(
|
|
@@ -2425,10 +2486,10 @@ Be specific. No generic advice.`
|
|
|
2425
2486
|
title: titleOf("get_qa_story_run", TDD_TOOL_CATALOG),
|
|
2426
2487
|
description: descOf("get_qa_story_run", TDD_TOOL_CATALOG),
|
|
2427
2488
|
annotations: annotationsFor("get_qa_story_run", TDD_TOOL_CATALOG),
|
|
2428
|
-
inputSchema: {
|
|
2489
|
+
inputSchema: z.object({
|
|
2429
2490
|
storyId: z.string().describe("QA story id (uuid)"),
|
|
2430
2491
|
runId: z.string().describe("Run id (uuid) to fetch detail for")
|
|
2431
|
-
}
|
|
2492
|
+
})
|
|
2432
2493
|
},
|
|
2433
2494
|
async ({ storyId, runId }) => {
|
|
2434
2495
|
const data = await apiCall(
|
|
@@ -2451,9 +2512,9 @@ Be specific. No generic advice.`
|
|
|
2451
2512
|
title: titleOf("test_notification_channel", TDD_TOOL_CATALOG),
|
|
2452
2513
|
description: descOf("test_notification_channel", TDD_TOOL_CATALOG),
|
|
2453
2514
|
annotations: annotationsFor("test_notification_channel", TDD_TOOL_CATALOG),
|
|
2454
|
-
inputSchema: {
|
|
2515
|
+
inputSchema: z.object({
|
|
2455
2516
|
kind: z.enum(["slack", "discord"]).describe("Notification channel kind to test")
|
|
2456
|
-
}
|
|
2517
|
+
})
|
|
2457
2518
|
},
|
|
2458
2519
|
async ({ kind }) => {
|
|
2459
2520
|
const data = await apiCall(
|
|
@@ -2469,9 +2530,9 @@ Be specific. No generic advice.`
|
|
|
2469
2530
|
title: titleOf("run_fullstack_audit"),
|
|
2470
2531
|
description: descOf("run_fullstack_audit"),
|
|
2471
2532
|
annotations: annotationsFor("run_fullstack_audit"),
|
|
2472
|
-
inputSchema: {
|
|
2533
|
+
inputSchema: z.object({
|
|
2473
2534
|
project_id: z.string().optional().describe("Project ID to audit. Defaults to the configured project.")
|
|
2474
|
-
}
|
|
2535
|
+
})
|
|
2475
2536
|
},
|
|
2476
2537
|
async ({ project_id }) => {
|
|
2477
2538
|
const pid = project_id ?? config.projectId;
|
|
@@ -2489,10 +2550,10 @@ Be specific. No generic advice.`
|
|
|
2489
2550
|
title: titleOf("get_backend_health"),
|
|
2490
2551
|
description: descOf("get_backend_health"),
|
|
2491
2552
|
annotations: annotationsFor("get_backend_health"),
|
|
2492
|
-
inputSchema: {
|
|
2553
|
+
inputSchema: z.object({
|
|
2493
2554
|
project_id: z.string().optional().describe("Project ID. Defaults to the configured project."),
|
|
2494
2555
|
include_logs: z.boolean().optional().describe("Whether to include recent backend error logs (default: true).")
|
|
2495
|
-
}
|
|
2556
|
+
})
|
|
2496
2557
|
},
|
|
2497
2558
|
async ({ project_id, include_logs = true }) => {
|
|
2498
2559
|
const pid = project_id ?? config.projectId;
|
|
@@ -2516,9 +2577,9 @@ Be specific. No generic advice.`
|
|
|
2516
2577
|
title: titleOf("get_usage"),
|
|
2517
2578
|
description: descOf("get_usage"),
|
|
2518
2579
|
annotations: annotationsFor("get_usage"),
|
|
2519
|
-
inputSchema: {
|
|
2580
|
+
inputSchema: z.object({
|
|
2520
2581
|
project_id: z.string().optional().describe("Project ID. Defaults to the configured project.")
|
|
2521
|
-
}
|
|
2582
|
+
})
|
|
2522
2583
|
},
|
|
2523
2584
|
async ({ project_id }) => {
|
|
2524
2585
|
const pid = project_id ?? config.projectId;
|
|
@@ -2533,12 +2594,12 @@ Be specific. No generic advice.`
|
|
|
2533
2594
|
title: titleOf("list_skills"),
|
|
2534
2595
|
description: descOf("list_skills"),
|
|
2535
2596
|
annotations: annotationsFor("list_skills"),
|
|
2536
|
-
inputSchema: {
|
|
2597
|
+
inputSchema: z.object({
|
|
2537
2598
|
category: z.string().optional().describe("Filter by category: workflow, debug, test, audit, enhance, \u2026"),
|
|
2538
2599
|
search: z.string().optional().describe("Free-text search across slug, title, description"),
|
|
2539
2600
|
page: z.number().optional().describe("Page number (default 1)"),
|
|
2540
2601
|
limit: z.number().optional().describe("Max results per page (default 200, max 200)")
|
|
2541
|
-
}
|
|
2602
|
+
})
|
|
2542
2603
|
},
|
|
2543
2604
|
async (args) => {
|
|
2544
2605
|
const qs = new URLSearchParams();
|
|
@@ -2557,9 +2618,9 @@ Be specific. No generic advice.`
|
|
|
2557
2618
|
title: titleOf("get_skill"),
|
|
2558
2619
|
description: descOf("get_skill"),
|
|
2559
2620
|
annotations: annotationsFor("get_skill"),
|
|
2560
|
-
inputSchema: {
|
|
2621
|
+
inputSchema: z.object({
|
|
2561
2622
|
slug: z.string().describe('Skill slug, e.g. "workflow-fix-and-ship"')
|
|
2562
|
-
}
|
|
2623
|
+
})
|
|
2563
2624
|
},
|
|
2564
2625
|
async (args) => {
|
|
2565
2626
|
const data = await apiCall(`/v1/admin/skills/${args.slug}`);
|
|
@@ -2572,14 +2633,14 @@ Be specific. No generic advice.`
|
|
|
2572
2633
|
title: titleOf("start_skill_pipeline"),
|
|
2573
2634
|
description: descOf("start_skill_pipeline"),
|
|
2574
2635
|
annotations: annotationsFor("start_skill_pipeline"),
|
|
2575
|
-
inputSchema: {
|
|
2636
|
+
inputSchema: z.object({
|
|
2576
2637
|
root_skill_slug: z.string().describe('Root skill slug to run, e.g. "workflow-fix-and-ship"'),
|
|
2577
2638
|
report_id: z.string().optional().describe("Report UUID to attach the pipeline to"),
|
|
2578
2639
|
mode: z.enum(["handoff", "cloud"]).optional().describe(
|
|
2579
2640
|
"handoff (default): get context packet for local agent. cloud: auto-dispatch via Cursor Cloud."
|
|
2580
2641
|
),
|
|
2581
2642
|
project_id: z.string().optional().describe("Project UUID. Falls back to the configured project.")
|
|
2582
|
-
}
|
|
2643
|
+
})
|
|
2583
2644
|
},
|
|
2584
2645
|
async (args) => {
|
|
2585
2646
|
const resolvedProjectId = args.project_id ?? projectId;
|
|
@@ -2597,9 +2658,9 @@ Be specific. No generic advice.`
|
|
|
2597
2658
|
title: titleOf("get_pipeline_run"),
|
|
2598
2659
|
description: descOf("get_pipeline_run"),
|
|
2599
2660
|
annotations: annotationsFor("get_pipeline_run"),
|
|
2600
|
-
inputSchema: {
|
|
2661
|
+
inputSchema: z.object({
|
|
2601
2662
|
run_id: z.string().describe("Pipeline run UUID")
|
|
2602
|
-
}
|
|
2663
|
+
})
|
|
2603
2664
|
},
|
|
2604
2665
|
async (args) => {
|
|
2605
2666
|
const data = await apiCall(`/v1/admin/skills/pipelines/${args.run_id}`);
|
|
@@ -2612,14 +2673,14 @@ Be specific. No generic advice.`
|
|
|
2612
2673
|
title: titleOf("checkin_pipeline_step"),
|
|
2613
2674
|
description: descOf("checkin_pipeline_step"),
|
|
2614
2675
|
annotations: annotationsFor("checkin_pipeline_step"),
|
|
2615
|
-
inputSchema: {
|
|
2676
|
+
inputSchema: z.object({
|
|
2616
2677
|
run_id: z.string().describe("Pipeline run UUID"),
|
|
2617
2678
|
step_index: z.number().describe("Step index (0-based)"),
|
|
2618
2679
|
status: z.enum(["running", "passed", "failed", "skipped"]).describe("Step status"),
|
|
2619
2680
|
notes: z.string().optional().describe("Optional notes or output summary"),
|
|
2620
2681
|
pr_url: z.string().optional().describe("PR URL opened during this step"),
|
|
2621
2682
|
agent_ref: z.string().optional().describe("Cursor agentId or external agent reference")
|
|
2622
|
-
}
|
|
2683
|
+
})
|
|
2623
2684
|
},
|
|
2624
2685
|
async (args) => {
|
|
2625
2686
|
const { run_id, step_index, ...body } = args;
|
|
@@ -2636,13 +2697,13 @@ Be specific. No generic advice.`
|
|
|
2636
2697
|
title: titleOf("ask_codebase", CODEBASE_TOOL_CATALOG),
|
|
2637
2698
|
description: descOf("ask_codebase", CODEBASE_TOOL_CATALOG),
|
|
2638
2699
|
annotations: annotationsFor("ask_codebase", CODEBASE_TOOL_CATALOG),
|
|
2639
|
-
inputSchema: {
|
|
2700
|
+
inputSchema: z.object({
|
|
2640
2701
|
project_id: z.string().optional().describe("Project UUID (defaults to configured project)"),
|
|
2641
2702
|
question: z.string().describe("Plain-English question about the repo"),
|
|
2642
2703
|
thread_id: z.string().optional().describe("Optional thread UUID to continue a conversation"),
|
|
2643
2704
|
file_path: z.string().optional().describe("Optional file path focus"),
|
|
2644
2705
|
symbol_name: z.string().optional().describe("Optional symbol name focus")
|
|
2645
|
-
}
|
|
2706
|
+
})
|
|
2646
2707
|
},
|
|
2647
2708
|
async (args) => {
|
|
2648
2709
|
const pid = args.project_id ?? projectId;
|
|
@@ -2670,12 +2731,12 @@ Be specific. No generic advice.`
|
|
|
2670
2731
|
title: titleOf("get_file_summary", CODEBASE_TOOL_CATALOG),
|
|
2671
2732
|
description: descOf("get_file_summary", CODEBASE_TOOL_CATALOG),
|
|
2672
2733
|
annotations: annotationsFor("get_file_summary", CODEBASE_TOOL_CATALOG),
|
|
2673
|
-
inputSchema: {
|
|
2734
|
+
inputSchema: z.object({
|
|
2674
2735
|
project_id: z.string().optional().describe("Project UUID (defaults to configured project)"),
|
|
2675
2736
|
file_path: z.string().describe("Indexed file path"),
|
|
2676
2737
|
symbol_name: z.string().optional().describe("Optional symbol name within the file"),
|
|
2677
2738
|
force: z.boolean().optional().describe("Bypass cache and regenerate")
|
|
2678
|
-
}
|
|
2739
|
+
})
|
|
2679
2740
|
},
|
|
2680
2741
|
async (args) => {
|
|
2681
2742
|
const pid = args.project_id ?? projectId;
|
|
@@ -2693,10 +2754,10 @@ Be specific. No generic advice.`
|
|
|
2693
2754
|
title: titleOf("get_codebase_tour", CODEBASE_TOOL_CATALOG),
|
|
2694
2755
|
description: descOf("get_codebase_tour", CODEBASE_TOOL_CATALOG),
|
|
2695
2756
|
annotations: annotationsFor("get_codebase_tour", CODEBASE_TOOL_CATALOG),
|
|
2696
|
-
inputSchema: {
|
|
2757
|
+
inputSchema: z.object({
|
|
2697
2758
|
project_id: z.string().optional().describe("Project UUID (defaults to configured project)"),
|
|
2698
2759
|
force: z.boolean().optional().describe("Bypass cache and regenerate")
|
|
2699
|
-
}
|
|
2760
|
+
})
|
|
2700
2761
|
},
|
|
2701
2762
|
async (args) => {
|
|
2702
2763
|
const pid = args.project_id ?? projectId;
|
|
@@ -2712,17 +2773,17 @@ Be specific. No generic advice.`
|
|
|
2712
2773
|
title: titleOf("search_codebase", CODEBASE_TOOL_CATALOG),
|
|
2713
2774
|
description: descOf("search_codebase", CODEBASE_TOOL_CATALOG),
|
|
2714
2775
|
annotations: annotationsFor("search_codebase", CODEBASE_TOOL_CATALOG),
|
|
2715
|
-
inputSchema: {
|
|
2776
|
+
inputSchema: z.object({
|
|
2716
2777
|
project_id: z.string().optional().describe("Project UUID (defaults to configured project)"),
|
|
2717
2778
|
query: z.string().describe("Plain-English search query against indexed source files"),
|
|
2718
2779
|
k: z.number().int().min(1).max(20).optional().describe("Max hits to return (default 8, max 20)"),
|
|
2719
2780
|
scope_prefix: z.string().optional().describe("Optional repo subdirectory prefix to limit search scope")
|
|
2720
|
-
},
|
|
2721
|
-
outputSchema: {
|
|
2781
|
+
}),
|
|
2782
|
+
outputSchema: z.object({
|
|
2722
2783
|
results: z.array(z.unknown()).describe("Ranked file/symbol hits with paths, line ranges, and similarity"),
|
|
2723
2784
|
query: z.string().describe("Normalized query string that was searched"),
|
|
2724
2785
|
mode: z.string().optional().describe("semantic (embeddings) or name (path/symbol match)")
|
|
2725
|
-
}
|
|
2786
|
+
})
|
|
2726
2787
|
},
|
|
2727
2788
|
async (args) => {
|
|
2728
2789
|
const pid = args.project_id ?? projectId;
|
|
@@ -2747,11 +2808,11 @@ Be specific. No generic advice.`
|
|
|
2747
2808
|
title: titleOf("get_codebase_domains", CODEBASE_TOOL_CATALOG),
|
|
2748
2809
|
description: descOf("get_codebase_domains", CODEBASE_TOOL_CATALOG),
|
|
2749
2810
|
annotations: annotationsFor("get_codebase_domains", CODEBASE_TOOL_CATALOG),
|
|
2750
|
-
inputSchema: {
|
|
2811
|
+
inputSchema: z.object({
|
|
2751
2812
|
project_id: z.string().optional().describe("Project UUID (defaults to configured project)"),
|
|
2752
2813
|
force: z.boolean().optional().describe("Bypass cache and regenerate"),
|
|
2753
2814
|
scope_prefix: z.string().optional().describe("Optional subdirectory scope prefix")
|
|
2754
|
-
}
|
|
2815
|
+
})
|
|
2755
2816
|
},
|
|
2756
2817
|
async (args) => {
|
|
2757
2818
|
const pid = args.project_id ?? projectId;
|
|
@@ -2770,20 +2831,20 @@ Be specific. No generic advice.`
|
|
|
2770
2831
|
title: titleOf("analyze_codebase_impact", CODEBASE_TOOL_CATALOG),
|
|
2771
2832
|
description: descOf("analyze_codebase_impact", CODEBASE_TOOL_CATALOG),
|
|
2772
2833
|
annotations: annotationsFor("analyze_codebase_impact", CODEBASE_TOOL_CATALOG),
|
|
2773
|
-
inputSchema: {
|
|
2834
|
+
inputSchema: z.object({
|
|
2774
2835
|
project_id: z.string().optional().describe("Project UUID (defaults to configured project)"),
|
|
2775
2836
|
paths: z.array(z.string()).optional().describe("Changed repo-relative file paths to analyze"),
|
|
2776
2837
|
source: z.enum(["last_push", "compare", "fix"]).optional().describe("Auto-resolve changed paths instead of manual paths"),
|
|
2777
2838
|
compare: z.string().optional().describe("GitHub compare range base...head when source=compare"),
|
|
2778
2839
|
fix_id: z.string().optional().describe("Fix attempt UUID \u2014 uses that PR's changed files when source=fix")
|
|
2779
|
-
},
|
|
2780
|
-
outputSchema: {
|
|
2840
|
+
}),
|
|
2841
|
+
outputSchema: z.object({
|
|
2781
2842
|
changed_paths: z.array(z.string()).describe("Resolved set of changed paths analyzed"),
|
|
2782
2843
|
source: z.string().describe("How changed_paths were resolved (manual, last_push, compare, fix, \u2026)"),
|
|
2783
2844
|
affected_file_paths: z.array(z.string()).describe("Indexed files that import or depend on changed paths"),
|
|
2784
2845
|
affected_node_ids: z.array(z.string()).describe("Codebase graph node ids impacted by the change"),
|
|
2785
2846
|
meta: z.unknown().nullable().optional().describe("Extra resolution metadata when auto-sourced")
|
|
2786
|
-
}
|
|
2847
|
+
})
|
|
2787
2848
|
},
|
|
2788
2849
|
async (args) => {
|
|
2789
2850
|
const pid = args.project_id ?? projectId;
|
|
@@ -2810,9 +2871,9 @@ Be specific. No generic advice.`
|
|
|
2810
2871
|
title: titleOf("analyze_wiki_knowledge", CODEBASE_TOOL_CATALOG),
|
|
2811
2872
|
description: descOf("analyze_wiki_knowledge", CODEBASE_TOOL_CATALOG),
|
|
2812
2873
|
annotations: annotationsFor("analyze_wiki_knowledge", CODEBASE_TOOL_CATALOG),
|
|
2813
|
-
inputSchema: {
|
|
2874
|
+
inputSchema: z.object({
|
|
2814
2875
|
project_id: z.string().optional().describe("Project UUID (defaults to configured project)")
|
|
2815
|
-
}
|
|
2876
|
+
})
|
|
2816
2877
|
},
|
|
2817
2878
|
async (args) => {
|
|
2818
2879
|
const pid = args.project_id ?? projectId;
|
|
@@ -2826,11 +2887,11 @@ Be specific. No generic advice.`
|
|
|
2826
2887
|
{
|
|
2827
2888
|
title: titleOf("use_mushi"),
|
|
2828
2889
|
description: descOf("use_mushi"),
|
|
2829
|
-
inputSchema: {
|
|
2890
|
+
inputSchema: z.object({
|
|
2830
2891
|
intent: z.string().optional().describe(
|
|
2831
2892
|
'What you are trying to accomplish with Mushi, e.g. "fix the top bug", "check project health", "run QA tests", "set up Mushi". Leave blank for a general orientation.'
|
|
2832
2893
|
)
|
|
2833
|
-
},
|
|
2894
|
+
}),
|
|
2834
2895
|
annotations: annotationsFor("use_mushi")
|
|
2835
2896
|
},
|
|
2836
2897
|
async (args) => {
|