@skyramp/mcp 0.2.6 → 0.2.7

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.
Files changed (184) hide show
  1. package/build/commands/commandLibrary.d.ts +12 -0
  2. package/build/commands/recommendTestsAndExecuteCommand.d.ts +2 -0
  3. package/build/commands/testThisEndpointCommand.d.ts +2 -0
  4. package/build/index.d.ts +2 -0
  5. package/build/index.js +1 -2
  6. package/build/playwright/PlaywrightTraceService.d.ts +32 -0
  7. package/build/playwright/index.d.ts +3 -0
  8. package/build/playwright/registerPlaywrightTools.d.ts +8 -0
  9. package/build/playwright/registerPlaywrightTools.js +12 -11
  10. package/build/playwright/traceRecordingPrompt.d.ts +13 -0
  11. package/build/playwright/traceRecordingPrompt.js +3 -11
  12. package/build/prompts/code-reuse.d.ts +1 -0
  13. package/build/prompts/enhance-assertions/contractProviderAssertionsPrompt.d.ts +2 -0
  14. package/build/prompts/enhance-assertions/integrationAssertionsPrompt.d.ts +2 -0
  15. package/build/prompts/enhance-assertions/sharedAssertionRules.d.ts +15 -0
  16. package/build/prompts/enhance-assertions/uiAssertionsPrompt.d.ts +2 -0
  17. package/build/prompts/fix-error-prompt.d.ts +1 -0
  18. package/build/prompts/initialize-workspace/initializeWorkspacePrompt.d.ts +1 -0
  19. package/build/prompts/modularization/integration-test-modularization.d.ts +1 -0
  20. package/build/prompts/modularization/ui-test-modularization.d.ts +1 -0
  21. package/build/prompts/personas.d.ts +21 -0
  22. package/build/prompts/pom-aware-code-reuse.d.ts +1 -0
  23. package/build/prompts/startTraceCollectionPrompts.d.ts +2 -0
  24. package/build/prompts/test-maintenance/actionsInstructions.d.ts +35 -0
  25. package/build/prompts/test-maintenance/drift-analysis-prompt.d.ts +4 -0
  26. package/build/prompts/test-maintenance/driftAnalysisSections.d.ts +13 -0
  27. package/build/prompts/test-recommendation/analysisOutputPrompt.d.ts +84 -0
  28. package/build/prompts/test-recommendation/analysisOutputPrompt.test.d.ts +1 -0
  29. package/build/prompts/test-recommendation/analysisOutputPrompt.test.js +1 -0
  30. package/build/prompts/test-recommendation/diffExecutionPlan.d.ts +17 -0
  31. package/build/prompts/test-recommendation/diffExecutionPlan.js +7 -16
  32. package/build/prompts/test-recommendation/fullRepoCatalog.d.ts +7 -0
  33. package/build/prompts/test-recommendation/mergeEnrichedScenarios.test.d.ts +1 -0
  34. package/build/prompts/test-recommendation/mergeEnrichedScenarios.test.js +1 -0
  35. package/build/prompts/test-recommendation/promptPlan.d.ts +203 -0
  36. package/build/prompts/test-recommendation/promptPlan.test.d.ts +1 -0
  37. package/build/prompts/test-recommendation/recommendationSections.d.ts +35 -0
  38. package/build/prompts/test-recommendation/recommendationShared.d.ts +31 -0
  39. package/build/prompts/test-recommendation/registerRecommendTestsPrompt.d.ts +7 -0
  40. package/build/prompts/test-recommendation/scopeAssessment.d.ts +55 -0
  41. package/build/prompts/test-recommendation/scopeAssessment.js +2 -2
  42. package/build/prompts/test-recommendation/scopeAssessment.test.d.ts +1 -0
  43. package/build/prompts/test-recommendation/scopeAssessment.test.js +1 -0
  44. package/build/prompts/test-recommendation/test-recommendation-prompt.d.ts +6 -0
  45. package/build/prompts/test-recommendation/test-recommendation-prompt.js +4 -4
  46. package/build/prompts/test-recommendation/test-recommendation-prompt.test.d.ts +1 -0
  47. package/build/prompts/test-recommendation/test-recommendation-prompt.test.js +6 -99
  48. package/build/prompts/testbot/testbot-prompts.d.ts +11 -0
  49. package/build/prompts/testbot/testbot-prompts.js +198 -34
  50. package/build/prompts/testbot/testbot-prompts.test.d.ts +1 -0
  51. package/build/prompts/testbot/testbot-prompts.test.js +15 -73
  52. package/build/resources/analysisResources.d.ts +17 -0
  53. package/build/resources/progressResource.d.ts +2 -0
  54. package/build/resources/testbotResource.d.ts +2 -0
  55. package/build/services/AnalyticsService.d.ts +13 -0
  56. package/build/services/AnalyticsService.test.d.ts +1 -0
  57. package/build/services/AnalyticsService.test.js +86 -0
  58. package/build/services/ModularizationService.d.ts +11 -0
  59. package/build/services/ScenarioGenerationService.d.ts +37 -0
  60. package/build/services/ScenarioGenerationService.integration.test.d.ts +1 -0
  61. package/build/services/ScenarioGenerationService.integration.test.js +4 -0
  62. package/build/services/ScenarioGenerationService.test.d.ts +1 -0
  63. package/build/services/TestDiscoveryService.d.ts +128 -0
  64. package/build/services/TestDiscoveryService.test.d.ts +1 -0
  65. package/build/services/TestDiscoveryService.test.js +4 -3
  66. package/build/services/TestExecutionService.d.ts +46 -0
  67. package/build/services/TestExecutionService.test.d.ts +1 -0
  68. package/build/services/TestExecutionService.test.js +33 -25
  69. package/build/services/TestGenerationService.d.ts +56 -0
  70. package/build/services/TestGenerationService.test.d.ts +1 -0
  71. package/build/services/TestGenerationService.test.js +10 -8
  72. package/build/services/containerEnv.d.ts +14 -0
  73. package/build/tool-phase-coverage.test.d.ts +1 -0
  74. package/build/tool-phase-coverage.test.js +2 -0
  75. package/build/tool-phases.d.ts +38 -0
  76. package/build/tools/auth/loginTool.d.ts +2 -0
  77. package/build/tools/auth/logoutTool.d.ts +2 -0
  78. package/build/tools/code-refactor/codeReuseTool.d.ts +2 -0
  79. package/build/tools/code-refactor/enhanceAssertionsTool.d.ts +2 -0
  80. package/build/tools/code-refactor/modularizationTool.d.ts +2 -0
  81. package/build/tools/executeSkyrampTestTool.d.ts +2 -0
  82. package/build/tools/fixErrorTool.d.ts +2 -0
  83. package/build/tools/generate-tests/generateBatchScenarioRestTool.d.ts +45 -0
  84. package/build/tools/generate-tests/generateBatchScenarioRestTool.test.d.ts +1 -0
  85. package/build/tools/generate-tests/generateBatchScenarioRestTool.test.js +11 -9
  86. package/build/tools/generate-tests/generateContractRestTool.d.ts +31 -0
  87. package/build/tools/generate-tests/generateE2ERestTool.d.ts +13 -0
  88. package/build/tools/generate-tests/generateFuzzRestTool.d.ts +10 -0
  89. package/build/tools/generate-tests/generateIntegrationRestTool.d.ts +16 -0
  90. package/build/tools/generate-tests/generateLoadRestTool.d.ts +18 -0
  91. package/build/tools/generate-tests/generateLoadRestTool.test.d.ts +1 -0
  92. package/build/tools/generate-tests/generateMockRestTool.d.ts +64 -0
  93. package/build/tools/generate-tests/generateSmokeRestTool.d.ts +8 -0
  94. package/build/tools/generate-tests/generateUIRestTool.d.ts +14 -0
  95. package/build/tools/generate-tests/generateUIRestTool.js +1 -1
  96. package/build/tools/generate-tests/loadTestSchema.d.ts +39 -0
  97. package/build/tools/one-click/oneClickTool.d.ts +11 -0
  98. package/build/tools/submitReportTool.d.ts +384 -0
  99. package/build/tools/submitReportTool.js +144 -2
  100. package/build/tools/submitReportTool.test.d.ts +1 -0
  101. package/build/tools/submitReportTool.test.js +215 -5
  102. package/build/tools/test-management/actionsTool.d.ts +10 -0
  103. package/build/tools/test-management/analyzeChangesTool.d.ts +27 -0
  104. package/build/tools/test-management/analyzeChangesTool.js +44 -7
  105. package/build/tools/test-management/analyzeChangesTool.test.d.ts +1 -0
  106. package/build/tools/test-management/analyzeChangesTool.test.js +76 -39
  107. package/build/tools/test-management/analyzeTestHealthTool.d.ts +2 -0
  108. package/build/tools/test-management/index.d.ts +3 -0
  109. package/build/tools/test-management/index.js +0 -1
  110. package/build/tools/trace/resolveSaveStoragePath.d.ts +7 -0
  111. package/build/tools/trace/resolveSaveStoragePath.test.d.ts +1 -0
  112. package/build/tools/trace/resolveSessionPaths.d.ts +40 -0
  113. package/build/tools/trace/resolveSessionPaths.test.d.ts +1 -0
  114. package/build/tools/trace/sessionState.d.ts +2 -0
  115. package/build/tools/trace/sessionState.test.d.ts +1 -0
  116. package/build/tools/trace/startTraceCollectionTool.d.ts +2 -0
  117. package/build/tools/trace/stopTraceCollectionTool.d.ts +2 -0
  118. package/build/tools/workspace/initScanWorkspaceTool.d.ts +4 -0
  119. package/build/tools/workspace/initializeWorkspaceTool.d.ts +2 -0
  120. package/build/tools/workspace/initializeWorkspaceTool.test.d.ts +1 -0
  121. package/build/tools/workspace/initializeWorkspaceTool.test.js +134 -0
  122. package/build/types/OneClickCommands.d.ts +68 -0
  123. package/build/types/RepositoryAnalysis.d.ts +3004 -0
  124. package/build/types/TestAnalysis.d.ts +96 -0
  125. package/build/types/TestExecution.d.ts +53 -0
  126. package/build/types/TestRecommendation.d.ts +12 -0
  127. package/build/types/TestTypes.d.ts +234 -0
  128. package/build/utils/AnalysisStateManager.d.ts +182 -0
  129. package/build/utils/AnalysisStateManager.test.d.ts +1 -0
  130. package/build/utils/analyze-openapi.d.ts +1 -0
  131. package/build/utils/branchDiff.d.ts +18 -0
  132. package/build/utils/dartRouteExtractor.d.ts +45 -0
  133. package/build/utils/dartRouteExtractor.test.d.ts +1 -0
  134. package/build/utils/docker.d.ts +19 -0
  135. package/build/utils/docker.test.d.ts +1 -0
  136. package/build/utils/docker.test.js +10 -9
  137. package/build/utils/featureFlags.d.ts +37 -0
  138. package/build/utils/featureFlags.test.d.ts +1 -0
  139. package/build/utils/gitStaging.d.ts +24 -0
  140. package/build/utils/gitStaging.test.d.ts +1 -0
  141. package/build/utils/gitStaging.test.js +13 -7
  142. package/build/utils/httpDefaults.d.ts +10 -0
  143. package/build/utils/httpDefaults.test.d.ts +1 -0
  144. package/build/utils/initAgent.d.ts +36 -0
  145. package/build/utils/language-helper.d.ts +6 -0
  146. package/build/utils/logger.d.ts +11 -0
  147. package/build/utils/normalizeParams.d.ts +14 -0
  148. package/build/utils/normalizeSkyrampImports.d.ts +13 -0
  149. package/build/utils/pr-comment-parser.d.ts +31 -0
  150. package/build/utils/pr-comment-parser.test.d.ts +1 -0
  151. package/build/utils/pr-comment-parser.test.js +6 -5
  152. package/build/utils/projectMetadata.d.ts +15 -0
  153. package/build/utils/projectMetadata.test.d.ts +1 -0
  154. package/build/utils/proxy-terminal.d.ts +2 -0
  155. package/build/utils/repoScanner.d.ts +27 -0
  156. package/build/utils/repoScanner.test.d.ts +1 -0
  157. package/build/utils/routeParsers.d.ts +63 -0
  158. package/build/utils/routeParsers.test.d.ts +1 -0
  159. package/build/utils/scenarioDrafting.d.ts +71 -0
  160. package/build/utils/scenarioDrafting.test.d.ts +1 -0
  161. package/build/utils/skyrampMdContent.d.ts +5 -0
  162. package/build/utils/sourceRouteExtractor.d.ts +48 -0
  163. package/build/utils/sourceRouteExtractor.test.d.ts +1 -0
  164. package/build/utils/telemetry.d.ts +32 -0
  165. package/build/utils/telemetry.test.d.ts +1 -0
  166. package/build/utils/trace-parser.d.ts +32 -0
  167. package/build/utils/trace-parser.test.d.ts +6 -0
  168. package/build/utils/uiPageEnumerator.d.ts +146 -0
  169. package/build/utils/uiPageEnumerator.js +58 -14
  170. package/build/utils/uiPageEnumerator.test.d.ts +1 -0
  171. package/build/utils/uiPageEnumerator.test.js +223 -43
  172. package/build/utils/utils.d.ts +39 -0
  173. package/build/utils/utils.test.d.ts +1 -0
  174. package/build/utils/versions.d.ts +3 -0
  175. package/build/utils/versions.js +1 -1
  176. package/build/utils/workspaceAuth.d.ts +127 -0
  177. package/build/utils/workspaceAuth.test.d.ts +1 -0
  178. package/build/utils/workspaceAuth.test.js +25 -25
  179. package/build/workspace/index.d.ts +1 -0
  180. package/build/workspace/workspace.d.ts +390 -0
  181. package/build/workspace/workspace.test.d.ts +1 -0
  182. package/package.json +8 -3
  183. package/build/tools/test-management/uiAnalyzeChangesTool.js +0 -155
  184. package/build/tools/test-management/uiAnalyzeChangesTool.test.js +0 -147
@@ -0,0 +1,203 @@
1
+ /**
2
+ * PromptPlan — structured prompt composition with phases, steps, and sub-steps.
3
+ *
4
+ * Design goals:
5
+ * - Main steps are always non-conditional; their labels (1, 2, 3, …) are
6
+ * static string constants usable in tests without calling any function.
7
+ * - Sub-steps are sequentially numbered within their parent (1.1, 1.2, 2.1, …).
8
+ * No manually chosen suffixes — insertion or removal automatically renumbers.
9
+ * - Conditional sub-steps: when absent, remaining siblings re-number so the
10
+ * LLM never sees a gap in the step sequence.
11
+ * - Phases group steps under an optional named heading with a configurable
12
+ * rendering style.
13
+ * - preview(params) returns a structured snapshot for developer inspection:
14
+ * which steps are active, what their labels are, and why conditional ones
15
+ * are absent.
16
+ *
17
+ * Usage:
18
+ * const _plan = new PromptPlan<MyParams>()
19
+ * .addPhase("main", "Task Instructions", { headerLevel: "##", stepFormat: "hash" })
20
+ * .step("READ", "Read the files", (p) => buildReadBody(p))
21
+ * .subStep("PATHS", "Resolve paths", (p) => buildPathsBody(p))
22
+ * .step("EXTRACT", "Extract items", (p) => buildExtractBody(p))
23
+ * .subStep("TRACE", "Trace callers", (p) => buildTraceBody(p),
24
+ * { when: (p) => p.hasUnmatched, whenDesc: "unmatched backend files present" })
25
+ * .step("CALL", "Call the tool", (p) => buildCallBody(p))
26
+ * .done();
27
+ *
28
+ * // Static constants for non-conditional steps (safe to export at module level)
29
+ * export const STEP_READ = _plan.labels.READ; // "1"
30
+ * export const STEP_PATHS = _plan.labels.PATHS; // "1.1"
31
+ * export const STEP_EXTRACT = _plan.labels.EXTRACT; // "2"
32
+ * export const STEP_CALL = _plan.labels.CALL; // "3"
33
+ *
34
+ * // Dynamic accessor for the conditional sub-step
35
+ * export const getStepTrace = (p: MyParams) => _plan.labelFor("TRACE", p); // "2.1" | null
36
+ *
37
+ * // Render for the LLM
38
+ * const promptText = _plan.render(params);
39
+ *
40
+ * // Developer review
41
+ * console.log(_plan.preview(params));
42
+ */
43
+ export type StepBody<P> = (params: P) => string;
44
+ /** Step title: either a static string or a function for dynamic titles. */
45
+ export type StepTitle<P> = string | ((params: P) => string);
46
+ export type StepCondition<P> = (params: P) => boolean;
47
+ interface SubStepDef<P> {
48
+ key: string;
49
+ title: StepTitle<P>;
50
+ body: StepBody<P>;
51
+ condition?: StepCondition<P>;
52
+ conditionDesc?: string;
53
+ }
54
+ interface StepDef<P> {
55
+ key: string;
56
+ title: StepTitle<P>;
57
+ body: StepBody<P>;
58
+ subSteps: SubStepDef<P>[];
59
+ }
60
+ interface PhaseDef<P> {
61
+ key: string;
62
+ title: string;
63
+ headerLevel: "##" | "###" | "hidden";
64
+ stepFormat: "hash" | "bold";
65
+ steps: StepDef<P>[];
66
+ }
67
+ export interface SubStepPreview {
68
+ key: string;
69
+ /** Computed label if active (e.g. "2.1"), or "N.?" if conditional and absent. */
70
+ label: string;
71
+ title: string;
72
+ active: boolean;
73
+ /** Human-readable description of the condition gating this sub-step. */
74
+ conditionDesc?: string;
75
+ }
76
+ export interface StepPreview {
77
+ key: string;
78
+ label: string;
79
+ title: string;
80
+ subSteps: SubStepPreview[];
81
+ }
82
+ export interface PhasePreview {
83
+ key: string;
84
+ title: string;
85
+ steps: StepPreview[];
86
+ }
87
+ export interface PlanPreview {
88
+ phases: PhasePreview[];
89
+ /** Total steps (main + sub-steps) that are active for the given params. */
90
+ activeStepCount: number;
91
+ /** Total steps registered in the plan, including conditional ones. */
92
+ totalStepCount: number;
93
+ }
94
+ export declare class PhaseBuilder<P extends object> {
95
+ private readonly _plan;
96
+ private readonly _phase;
97
+ private _lastStep;
98
+ constructor(plan: PromptPlan<P>, phase: PhaseDef<P>);
99
+ /**
100
+ * Add a non-conditional main step.
101
+ * Main steps always appear in the rendered output and always carry a stable
102
+ * label (1, 2, 3, …) regardless of which sub-steps are active.
103
+ */
104
+ step(key: string, title: StepTitle<P>, body: StepBody<P>): this;
105
+ /**
106
+ * Add a sub-step under the most recently declared main step.
107
+ * Sub-steps are sequentially numbered within their parent (1.1, 1.2, …).
108
+ *
109
+ * When opts.when is provided the sub-step is conditional: if the condition
110
+ * returns false for the given params, the step is omitted and remaining
111
+ * siblings re-number so the LLM never sees a gap.
112
+ *
113
+ * @throws when called before any step() in this phase.
114
+ */
115
+ subStep(key: string, title: StepTitle<P>, body: StepBody<P>, opts?: {
116
+ when?: StepCondition<P>;
117
+ whenDesc?: string;
118
+ }): this;
119
+ /** Finish building this phase and return the parent PromptPlan. */
120
+ done(): PromptPlan<P>;
121
+ }
122
+ export declare class PromptPlan<P extends object> {
123
+ private readonly _phases;
124
+ private readonly _startFrom;
125
+ /** Track registered step/sub-step keys for duplicate detection. */
126
+ private readonly _registeredKeys;
127
+ /**
128
+ * @param opts.startFrom - Label of the first main step. Defaults to 1.
129
+ * Use 0 for execution-plan style (Step 0, Step 1, Step 2, …).
130
+ */
131
+ constructor(opts?: {
132
+ startFrom?: number;
133
+ });
134
+ /** @internal Register a key and throw if already taken. */
135
+ _registerKey(key: string): void;
136
+ /**
137
+ * Add a phase and return a PhaseBuilder to register its steps.
138
+ * Multiple phases share a single global main-step counter, so step labels
139
+ * increment continuously across phase boundaries.
140
+ */
141
+ addPhase(key: string, title: string, opts?: {
142
+ /** Markdown heading level for the phase header. "hidden" emits no header. */
143
+ headerLevel?: "##" | "###" | "hidden";
144
+ /**
145
+ * Step header rendering style.
146
+ * "hash" => "### Step N: Title" (analysis prompt style)
147
+ * "bold" => "**Step N — Title**" (execution plan style)
148
+ */
149
+ stepFormat?: "hash" | "bold";
150
+ }): PhaseBuilder<P>;
151
+ /**
152
+ * Static label map for all non-conditional steps (main steps and
153
+ * unconditional sub-steps). Conditional sub-steps are not present here —
154
+ * use labelFor() for those.
155
+ *
156
+ * Safe to export as module-level constants for use in tests.
157
+ *
158
+ * **Ordering constraint**: unconditional sub-steps that appear *after* a
159
+ * conditional sibling will have a stable label here only if no conditional
160
+ * siblings precede them. When a conditional sibling is active at runtime,
161
+ * labelFor() will assign a higher number than the static label here. To
162
+ * avoid this mismatch, place conditional sub-steps AFTER all unconditional
163
+ * siblings, or use labelFor() for any sub-step with a conditional predecessor.
164
+ *
165
+ * O(steps) per call — intentionally avoids a stale-cache window during plan
166
+ * construction. Plans have ~6 steps so the cost is negligible; exported
167
+ * constants are evaluated once at module-load time.
168
+ */
169
+ get labels(): Record<string, string>;
170
+ /**
171
+ * Dynamic label for any registered step given runtime params.
172
+ *
173
+ * Returns null when the step has a condition that evaluates to false.
174
+ * Throws when key is not registered in this plan.
175
+ *
176
+ * For non-conditional steps the result equals labels[key], but using
177
+ * labels is preferred for those since it avoids passing params.
178
+ */
179
+ labelFor(key: string, params: P): string | null;
180
+ /**
181
+ * Render the full prompt for the given params.
182
+ *
183
+ * - Phase headers are emitted when headerLevel is not "hidden".
184
+ * - Steps are formatted per the phase's stepFormat.
185
+ * - Conditional sub-steps absent for these params are skipped; remaining
186
+ * siblings re-number with no gaps.
187
+ * - Each section (header + body) is separated by a single blank line.
188
+ */
189
+ render(params: P): string;
190
+ /**
191
+ * Return a structured preview of all steps and their active state for the
192
+ * given params. Useful in development, tests, and debugging to verify exactly
193
+ * which steps would be emitted and what labels they carry.
194
+ *
195
+ * @example
196
+ * const pv = _plan.preview({ ...params, unmatchedFiles: [] });
197
+ * // pv.phases[0].steps[1].subSteps[0] =>
198
+ * // { key: "TRACE_CALLERS", label: "2.?", active: false,
199
+ * // conditionDesc: "non-frontend unmatched backend files present" }
200
+ */
201
+ preview(params: P): PlanPreview;
202
+ }
203
+ export {};
@@ -0,0 +1,35 @@
1
+ export declare const MAX_TESTS_TO_GENERATE = 3;
2
+ export declare const MAX_RECOMMENDATIONS = 20;
3
+ export declare const MAX_CRITICAL_TESTS = 3;
4
+ /**
5
+ * Error string emitted by skyramp_integration_test_generation when both
6
+ * an explicit authHeader and a workspace api.authType are passed simultaneously.
7
+ * Both the tool description and all prompt locations import this constant,
8
+ * so every occurrence is character-for-character identical by construction.
9
+ */
10
+ export declare const AUTH_CONFLICT_ERROR_MSG = "Auth header and auth type cannot be supported at the same time.";
11
+ export declare function buildArchitectPreamble(isDiffScope: boolean): string;
12
+ export declare function buildContextFetchingGuidance(sessionId?: string): string;
13
+ export declare function buildReasoningProtocol(): string;
14
+ export interface AuthCallParams {
15
+ authHeader: string;
16
+ authScheme?: string;
17
+ authToken?: string;
18
+ }
19
+ /**
20
+ * Returns the authScheme snippet for a given authHeader + authType combination.
21
+ *
22
+ * Delegates scheme resolution to getAuthScheme() in workspaceAuth.ts — the single
23
+ * source of truth — so this file no longer maintains its own slug→scheme table.
24
+ */
25
+ export declare function getAuthSnippets(authHeaderValue: string, authType?: string, explicitScheme?: string): {
26
+ authSchemeSnippet: string;
27
+ authTokenSnippet: string;
28
+ };
29
+ export declare const PATH_PARAM_UUID_GUIDANCE: string;
30
+ export declare function buildTestPatternGuidelines(): string;
31
+ export declare function buildTestQualityCriteria(): string;
32
+ export declare function buildGenerationRules(isUIOnlyPR: boolean): string;
33
+ export declare function buildVerificationChecklist(topN: number, maxGen: number, codeReviewStepLabel?: string): string;
34
+ export declare function buildFewShotExamples(): string;
35
+ export declare function buildToolWorkflows(authHeaderValue: string, authTypeValue?: string, explicitScheme?: string): string;
@@ -0,0 +1,31 @@
1
+ /**
2
+ * Shared dedup primitives used by both diff-mode (diffExecutionPlan.ts) and
3
+ * full-repo mode (fullRepoCatalog.ts). Extracted here to avoid circular imports.
4
+ */
5
+ import { DraftedScenario } from "../../types/RepositoryAnalysis.js";
6
+ export declare function scenarioCoverageKey(scenario: DraftedScenario): string;
7
+ /**
8
+ * Method-aware coverage key for external test dedup.
9
+ * Unlike scenarioCoverageKey (resource::testType), this includes the HTTP method
10
+ * so that e.g. an external test covering "GET /orders" doesn't block generating
11
+ * a test for "PUT /orders" — a different operation on the same resource.
12
+ */
13
+ export declare function externalDedupKey(scenario: DraftedScenario): string;
14
+ export declare function isAttackSurfaceSecurityBoundary(scenario: DraftedScenario): boolean;
15
+ export declare function isOrdinaryDirectAuthBoundary(scenario: DraftedScenario): boolean;
16
+ /**
17
+ * Build a set of coverage keys from external (non-Skyramp) tests.
18
+ * Parses `testLocations` entries tagged with `[external]` to extract the
19
+ * method-aware `METHOD::resource::testType` keys they cover.
20
+ */
21
+ export declare function buildExternalCoverageSet(testLocations: Record<string, string>): Set<string>;
22
+ export declare const TASK_UI_PRESCAN = "0";
23
+ export declare const TASK_ANALYZE_MAINTAIN = "1";
24
+ export declare const TASK_GENERATE = "2";
25
+ export declare const TASK_SUBMIT = "3";
26
+ export declare const TESTBOT_TASK1_STEP_ANALYZE = "1";
27
+ export declare const TESTBOT_TASK1_STEP_MAINTAIN = "2";
28
+ export declare const TESTBOT_TASK1_STEP_CODE_REVIEW = "3";
29
+ export declare const TESTBOT_TASK1_STEP_UI_GROUNDING = "4";
30
+ export declare const taskRef: (taskId: string) => string;
31
+ export declare const taskStepRef: (taskId: string, stepId: string) => string;
@@ -0,0 +1,7 @@
1
+ import { McpServer } from "@modelcontextprotocol/sdk/server/mcp.js";
2
+ import { DraftedScenario } from "../../types/RepositoryAnalysis.js";
3
+ export declare function mergeEnrichedScenarios(serverScenarios: DraftedScenario[], raw: string): {
4
+ scenarios: DraftedScenario[];
5
+ rejectionNotes: string[];
6
+ };
7
+ export declare function registerRecommendTestsPrompt(server: McpServer): void;
@@ -0,0 +1,55 @@
1
+ export declare function hasFlutterSdkDep(repositoryPath: string): boolean;
2
+ /**
3
+ * Returns true if the file path is a frontend file.
4
+ *
5
+ * Four tiers:
6
+ * 1. .vue / .svelte — always frontend; these file types cannot be route handlers.
7
+ * 2. .dart — always frontend IFF `hasFlutterSdkDep` is true (Flutter project).
8
+ * Sits in tier 1 because there's no server-side Dart web framework in scope
9
+ * when the Flutter SDK dep is present, so `API_DIR_PATTERN` doesn't apply.
10
+ * 3. .tsx / .jsx — frontend unless in an API/backend directory (e.g. pages/api/).
11
+ * 4. Ambiguous extensions (.ts, .js, .css, .html, …) — require a recognised
12
+ * frontend directory AND must not be in an API/backend directory.
13
+ *
14
+ * The `hasFlutterSdkDep` opt is passed in by the budget-driving caller
15
+ * (analyzeChangesTool) which has repository context.
16
+ * Pure-path callers (test-recommendation-prompt, analysisOutputPrompt,
17
+ * scopeAssessment's own buildScopeAssessmentSection) default to false —
18
+ * they don't drive the budget.
19
+ */
20
+ export declare function isFrontendFile(filePath: string, { hasFlutterSdkDep }?: {
21
+ hasFlutterSdkDep?: boolean;
22
+ }): boolean;
23
+ /**
24
+ * Returns true if the file path looks like a test file rather than UI source.
25
+ *
26
+ * Catches:
27
+ * - Skyramp-generated tests (`*_test.ts`, `*_smoke.ts`, `*_contract.ts`,
28
+ * `*_fuzz.ts`, `*_integration.ts`, `*_load.ts`, `*_e2e.ts`, `*_ui.ts`)
29
+ * - Skyramp scenario files (`scenario_*.json`)
30
+ * - Conventional Vitest/Jest/Playwright spec naming
31
+ * (`*.spec.{ts,tsx,js,jsx}`, `*.test.{ts,tsx,js,jsx}`)
32
+ * - Files inside `__tests__/` directories (Jest convention)
33
+ *
34
+ * Used by callers that want to filter test files OUT of frontend-source
35
+ * processing — `isFrontendFile` returns true for `.spec.ts` under a
36
+ * frontend directory because the rule is "tier-3 ambiguous + frontend dir,"
37
+ * but those tests aren't UI source we'd want to ground recommendations in.
38
+ */
39
+ export declare function isTestFile(filePath: string): boolean;
40
+ /**
41
+ * Builds the PR scope assessment section.
42
+ *
43
+ * When `precomputedUIPct` is provided (0 = backend-only, 100 = UI-only) the server
44
+ * has already determined the split unambiguously — skip Steps A–C and emit one line.
45
+ *
46
+ * For mixed PRs (`precomputedUIPct` is undefined, `hasFrontendChanges` is true) skip
47
+ * Steps A–C but keep Step D so the LLM can apply judgment to determine the UI%.
48
+ *
49
+ * Falls back to the full four-step assessment when no precomputed data is available.
50
+ */
51
+ export declare function buildScopeAssessmentSection(maxTotal?: number, maxGenerate?: number, isUIOnly?: boolean,
52
+ /** Server-determined UI/E2E percentage. `undefined` = mixed PR or unknown. */
53
+ precomputedUIPct?: number,
54
+ /** Whether the diff contains frontend files (true ↔ mixed PR when precomputedUIPct is undefined). */
55
+ hasFrontendChanges?: boolean): string;
@@ -109,8 +109,8 @@ function checkPubspec(pubspecPath) {
109
109
  * 4. Ambiguous extensions (.ts, .js, .css, .html, …) — require a recognised
110
110
  * frontend directory AND must not be in an API/backend directory.
111
111
  *
112
- * The `hasFlutterSdkDep` opt is passed in by the budget-driving callers
113
- * (uiAnalyzeChangesTool, analyzeChangesTool) which have repository context.
112
+ * The `hasFlutterSdkDep` opt is passed in by the budget-driving caller
113
+ * (analyzeChangesTool) which has repository context.
114
114
  * Pure-path callers (test-recommendation-prompt, analysisOutputPrompt,
115
115
  * scopeAssessment's own buildScopeAssessmentSection) default to false —
116
116
  * they don't drive the budget.
@@ -1,3 +1,4 @@
1
+ import { jest } from "@jest/globals";
1
2
  jest.mock("@skyramp/skyramp", () => ({
2
3
  WorkspaceConfigManager: { create: jest.fn() },
3
4
  }));
@@ -0,0 +1,6 @@
1
+ import { RepositoryAnalysis, AnalysisScope } from "../../types/RepositoryAnalysis.js";
2
+ import { WorkspaceAuthType } from "../../utils/workspaceAuth.js";
3
+ import { PRTestContext } from "../../utils/pr-comment-parser.js";
4
+ import { buildExternalCoverageSet, externalDedupKey } from "./recommendationShared.js";
5
+ export { buildExternalCoverageSet, externalDedupKey };
6
+ export declare function buildRecommendationPrompt(analysis: RepositoryAnalysis, analysisScope?: AnalysisScope, topN?: number, prContext?: PRTestContext, workspaceAuthHeader?: string, workspaceAuthType?: WorkspaceAuthType, workspaceAuthScheme?: string, maxGenerateOverride?: number, sessionId?: string): string;
@@ -93,10 +93,10 @@ ${isUIOnlyPR ? `\n**UI-only PR** — no backend changes. UI and E2E tests are mo
93
93
  Output should be concise and immediately actionable.`
94
94
  : `You are in **Repo mode**. Comprehensive test strategy across all endpoints.`;
95
95
  // ── UI rec authoring rules ──
96
- // Anchors every UI recommendation regardless of whether the agent ran
97
- // skyramp_ui_analyze_changes / browser_blueprint before this call. When the
98
- // agent has prior captures in its own tool-result history, those serve as
99
- // grounding; when it doesn't, recommendations fall back to source-grounded
96
+ // Anchors every UI recommendation regardless of whether the agent captured
97
+ // browser_blueprints (from the UI Blueprint Capture section this tool returns).
98
+ // When the agent has prior captures in its own tool-result history, those serve
99
+ // as grounding; when it doesn't, recommendations fall back to source-grounded
100
100
  // prose. Either way, inventing elements / leaking jargon / duplicating UI
101
101
  // tests are wrong, so the rules fire unconditionally.
102
102
  const uiRecRulesSection = `
@@ -1,10 +1,11 @@
1
- jest.mock("@skyramp/skyramp", () => ({
1
+ import { jest } from "@jest/globals";
2
+ import { TestType } from "../../types/TestTypes.js";
3
+ jest.unstable_mockModule("@skyramp/skyramp", () => ({
2
4
  WorkspaceConfigManager: { create: jest.fn() },
3
5
  }));
4
- import { TestType } from "../../types/TestTypes.js";
5
- import { buildRecommendationPrompt, buildExternalCoverageSet, externalDedupKey } from "./test-recommendation-prompt.js";
6
- import { buildExecutionPlan } from "./diffExecutionPlan.js";
7
- import { PATH_PARAM_UUID_GUIDANCE, MAX_TESTS_TO_GENERATE, buildTestQualityCriteria, buildArchitectPreamble, buildContextFetchingGuidance, buildReasoningProtocol, buildFewShotExamples, buildVerificationChecklist, } from "./recommendationSections.js";
6
+ const { buildRecommendationPrompt, buildExternalCoverageSet, externalDedupKey } = await import("./test-recommendation-prompt.js");
7
+ const { buildExecutionPlan } = await import("./diffExecutionPlan.js");
8
+ const { PATH_PARAM_UUID_GUIDANCE, MAX_TESTS_TO_GENERATE, buildTestQualityCriteria, buildArchitectPreamble, buildContextFetchingGuidance, buildReasoningProtocol, buildFewShotExamples, buildVerificationChecklist, } = await import("./recommendationSections.js");
8
9
  import { AnalysisScope } from "../../types/RepositoryAnalysis.js";
9
10
  // ---------------------------------------------------------------------------
10
11
  // Minimal fixtures
@@ -1669,100 +1670,6 @@ describe("externalDedupKey", () => {
1669
1670
  expect(externalDedupKey(scenario)).toBe("POST::orders::contract");
1670
1671
  });
1671
1672
  });
1672
- describe("UI grounding guidance (Phase C D-1.a)", () => {
1673
- const editOrderScenario = minimalScenario({
1674
- scenarioName: 'edit-order',
1675
- description: 'edit order',
1676
- category: 'new_endpoint',
1677
- priority: 'medium',
1678
- steps: [
1679
- { order: 1, method: 'PATCH', path: '/api/v1/orders/{id}', description: 'edit', interactionType: 'success', expectedStatusCode: 200 },
1680
- ],
1681
- chainingKeys: [],
1682
- });
1683
- const uiGroundingBusinessContext = {
1684
- mainPurpose: "Test API", userFlows: [], dataFlows: [], integrationPatterns: [],
1685
- draftedScenarios: [editOrderScenario],
1686
- };
1687
- const uiOnlyAnalysis = () => minimalAnalysis({
1688
- branchDiffContext: {
1689
- currentBranch: "feature", baseBranch: "main",
1690
- changedFiles: ['frontend/src/components/EditOrder.tsx'],
1691
- newEndpoints: [],
1692
- modifiedEndpoints: [],
1693
- affectedServices: [],
1694
- },
1695
- businessContext: uiGroundingBusinessContext,
1696
- });
1697
- const mixedAnalysis = () => minimalAnalysis({
1698
- branchDiffContext: {
1699
- currentBranch: "feature", baseBranch: "main",
1700
- changedFiles: ['frontend/src/components/EditOrder.tsx', 'backend/orders.py'],
1701
- newEndpoints: [{
1702
- path: '/api/v1/orders/{id}',
1703
- methods: [{ method: 'PATCH', sourceFile: 'backend/orders.py', interactionCount: 1 }],
1704
- }],
1705
- modifiedEndpoints: [],
1706
- affectedServices: [],
1707
- },
1708
- businessContext: uiGroundingBusinessContext,
1709
- });
1710
- const backendOnlyAnalysis = () => minimalAnalysis({
1711
- branchDiffContext: {
1712
- currentBranch: "feature", baseBranch: "main",
1713
- changedFiles: ['backend/orders.py'],
1714
- newEndpoints: [{
1715
- path: '/api/v1/orders',
1716
- methods: [{ method: 'POST', sourceFile: 'backend/orders.py', interactionCount: 1 }],
1717
- }],
1718
- modifiedEndpoints: [],
1719
- affectedServices: [],
1720
- },
1721
- businessContext: uiGroundingBusinessContext,
1722
- });
1723
- it("emits UI grounding block on UI-only PRs", () => {
1724
- const out = buildRecommendationPrompt(uiOnlyAnalysis(), AnalysisScope.CurrentBranchDiff, 10);
1725
- expect(out).toContain("UI recommendation grounding");
1726
- expect(out).toContain("role=<role>");
1727
- expect(out).toContain("accessibleName=");
1728
- });
1729
- it("emits UI grounding block on mixed PRs", () => {
1730
- const out = buildRecommendationPrompt(mixedAnalysis(), AnalysisScope.CurrentBranchDiff, 10);
1731
- expect(out).toContain("UI recommendation grounding");
1732
- expect(out).toContain("contextText=");
1733
- });
1734
- it("does not emit UI grounding block on backend-only PRs", () => {
1735
- const out = buildRecommendationPrompt(backendOnlyAnalysis(), AnalysisScope.CurrentBranchDiff, 10);
1736
- expect(out).not.toContain("UI recommendation grounding");
1737
- });
1738
- it("carves out non-UI entries from the grounding format", () => {
1739
- const out = buildRecommendationPrompt(mixedAnalysis(), AnalysisScope.CurrentBranchDiff, 10);
1740
- expect(out).toMatch(/Contract, integration, e2e.*existing conventions/);
1741
- });
1742
- it("includes contextText example for repeating elements", () => {
1743
- const out = buildRecommendationPrompt(uiOnlyAnalysis(), AnalysisScope.CurrentBranchDiff, 10);
1744
- expect(out).toContain('contextText=["customer@example.com"');
1745
- });
1746
- // Phase C D-1.a/7b: directive instruction strengthening + Validates coverage
1747
- // + marked fallback. Asserts the post-7b language is present.
1748
- it("uses MUST directive for tuple presence in reasoning field", () => {
1749
- const out = buildRecommendationPrompt(uiOnlyAnalysis(), AnalysisScope.CurrentBranchDiff, 10);
1750
- expect(out).toContain("MUST contain at least three of");
1751
- expect(out).toContain("not valid output for UI test types");
1752
- });
1753
- it("instructs the agent to ground the Validates line for UI entries", () => {
1754
- const out = buildRecommendationPrompt(uiOnlyAnalysis(), AnalysisScope.CurrentBranchDiff, 10);
1755
- expect(out).toContain("Validates line — applies to");
1756
- expect(out).toContain("observable behavior the test verifies");
1757
- expect(out).toContain("structural facts");
1758
- });
1759
- it("requires a [no-blueprint-data] marker on source-grounded fallback entries", () => {
1760
- const out = buildRecommendationPrompt(uiOnlyAnalysis(), AnalysisScope.CurrentBranchDiff, 10);
1761
- expect(out).toContain("[no-blueprint-data]");
1762
- expect(out).toContain("issuesFound");
1763
- expect(out).toContain("Do NOT silently produce ungrounded reasoning");
1764
- });
1765
- });
1766
1673
  // ---------------------------------------------------------------------------
1767
1674
  // Tests — UI recommendation authoring rules
1768
1675
  // ---------------------------------------------------------------------------
@@ -0,0 +1,11 @@
1
+ import { McpServer } from "@modelcontextprotocol/sdk/server/mcp.js";
2
+ import { type Service } from "../../workspace/workspace.js";
3
+ export declare function getTestbotPrompt(prTitle: string, prDescription: string, summaryOutputFile: string, repositoryPath: string, baseBranch?: string, maxRecommendations?: number, maxGenerate?: number, _maxCritical?: number, // Reserved — accepted for API compat but not yet wired into prompt
4
+ prNumber?: number, userPrompt?: string, services?: Service[], stateOutputFile?: string, uiCredentials?: string, testsRepoDir?: string): string;
5
+ /**
6
+ * Read services from .skyramp/workspace.yml. Returns empty array if
7
+ * the workspace file doesn't exist or can't be parsed.
8
+ */
9
+ export declare function readWorkspaceServices(repositoryPath: string): Promise<Service[]>;
10
+ export declare function buildWorkspaceRecoveryPrefix(repositoryPath: string): string;
11
+ export declare function registerTestbotPrompt(server: McpServer): void;