@provartesting/provardx-cli 1.5.0 → 1.5.1

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 (64) hide show
  1. package/lib/mcp/docs/PROVAR_TOOL_GUIDE.md +18 -6
  2. package/lib/mcp/prompts/guidePrompts.js +21 -11
  3. package/lib/mcp/prompts/guidePrompts.js.map +1 -1
  4. package/lib/mcp/server.d.ts +1 -0
  5. package/lib/mcp/server.js +89 -21
  6. package/lib/mcp/server.js.map +1 -1
  7. package/lib/mcp/tools/antTools.js +60 -38
  8. package/lib/mcp/tools/antTools.js.map +1 -1
  9. package/lib/mcp/tools/automationTools.js +22 -21
  10. package/lib/mcp/tools/automationTools.js.map +1 -1
  11. package/lib/mcp/tools/connectionTools.js +100 -30
  12. package/lib/mcp/tools/connectionTools.js.map +1 -1
  13. package/lib/mcp/tools/defectTools.js +12 -7
  14. package/lib/mcp/tools/defectTools.js.map +1 -1
  15. package/lib/mcp/tools/descHelper.d.ts +5 -0
  16. package/lib/mcp/tools/descHelper.js +14 -0
  17. package/lib/mcp/tools/descHelper.js.map +1 -0
  18. package/lib/mcp/tools/nitroXTools.js +72 -32
  19. package/lib/mcp/tools/nitroXTools.js.map +1 -1
  20. package/lib/mcp/tools/pageObjectGenerate.js +33 -15
  21. package/lib/mcp/tools/pageObjectGenerate.js.map +1 -1
  22. package/lib/mcp/tools/pageObjectValidate.js +11 -4
  23. package/lib/mcp/tools/pageObjectValidate.js.map +1 -1
  24. package/lib/mcp/tools/projectInspect.js +31 -5
  25. package/lib/mcp/tools/projectInspect.js.map +1 -1
  26. package/lib/mcp/tools/projectValidateFromPath.js +128 -22
  27. package/lib/mcp/tools/projectValidateFromPath.js.map +1 -1
  28. package/lib/mcp/tools/propertiesTools.js +43 -17
  29. package/lib/mcp/tools/propertiesTools.js.map +1 -1
  30. package/lib/mcp/tools/qualityHubApiTools.js +8 -7
  31. package/lib/mcp/tools/qualityHubApiTools.js.map +1 -1
  32. package/lib/mcp/tools/qualityHubTools.js +108 -37
  33. package/lib/mcp/tools/qualityHubTools.js.map +1 -1
  34. package/lib/mcp/tools/rcaTools.js +18 -13
  35. package/lib/mcp/tools/rcaTools.js.map +1 -1
  36. package/lib/mcp/tools/testCaseGenerate.js +71 -12
  37. package/lib/mcp/tools/testCaseGenerate.js.map +1 -1
  38. package/lib/mcp/tools/testCaseStepTools.js +27 -9
  39. package/lib/mcp/tools/testCaseStepTools.js.map +1 -1
  40. package/lib/mcp/tools/testCaseValidate.js +136 -57
  41. package/lib/mcp/tools/testCaseValidate.js.map +1 -1
  42. package/lib/mcp/tools/testPlanTools.js +43 -26
  43. package/lib/mcp/tools/testPlanTools.js.map +1 -1
  44. package/lib/mcp/tools/testPlanValidate.js +64 -11
  45. package/lib/mcp/tools/testPlanValidate.js.map +1 -1
  46. package/lib/mcp/tools/testSuiteValidate.js +99 -10
  47. package/lib/mcp/tools/testSuiteValidate.js.map +1 -1
  48. package/lib/mcp/utils/detailLevel.d.ts +9 -0
  49. package/lib/mcp/utils/detailLevel.js +20 -0
  50. package/lib/mcp/utils/detailLevel.js.map +1 -0
  51. package/lib/mcp/utils/fieldMask.d.ts +17 -0
  52. package/lib/mcp/utils/fieldMask.js +75 -0
  53. package/lib/mcp/utils/fieldMask.js.map +1 -0
  54. package/lib/mcp/utils/tokenMeta.d.ts +40 -0
  55. package/lib/mcp/utils/tokenMeta.js +90 -0
  56. package/lib/mcp/utils/tokenMeta.js.map +1 -0
  57. package/lib/mcp/utils/validationDiff.d.ts +57 -0
  58. package/lib/mcp/utils/validationDiff.js +191 -0
  59. package/lib/mcp/utils/validationDiff.js.map +1 -0
  60. package/lib/mcp/utils/validationScore.d.ts +15 -0
  61. package/lib/mcp/utils/validationScore.js +31 -0
  62. package/lib/mcp/utils/validationScore.js.map +1 -0
  63. package/oclif.manifest.json +1 -1
  64. package/package.json +13 -1
@@ -77,15 +77,27 @@ provar_properties_set { file_path: "<output_path>", key: "connectionName", valu
77
77
 
78
78
  ## "I want to write a new test"
79
79
 
80
+ A Provar test case is a tree (scenarios → UI screens → asserts), not a flat list of steps. The agent that calls `provar_testcase_generate` is responsible for constructing the full tree in **one** call. Splitting authoring across many tool calls causes scenario numbering drift, flat asserts, and inconsistent step types — `provar_testcase_step_edit` is for **amending** an existing test case, not for **constructing** one.
81
+
82
+ Recommended sequence:
83
+
80
84
  ```
81
- 1. provar_project_inspect { project_path } ← find coverage gaps first
82
- 2. provar_testcase_generate { project_path, name, ... }
83
- 3. provar_testcase_step_edit { test_case_path, ... } repeat per step
84
- 4. provar_testcase_validate { file_path } ← must pass before adding to plan
85
- 5. provar_testplan_add-instance { project_path, plan_name, test_case_path }
86
- 6. provar_testplan_validate { project_path, plan_name }
85
+ 1. provar_project_inspect { project_path } ← find coverage gaps first
86
+ 2. provar_qualityhub_examples_retrieve { object_or_scenario } ← ground in corpus examples for the step types you need
87
+ 3. provar_testcase_generate { test_case_name, steps: [<ALL steps>] } single call, full step tree in one payload
88
+ 4. provar_testcase_validate { file_path } ← must pass before adding to plan
89
+ 5. provar_testplan_add-instance { project_path, plan_name, test_case_path }
90
+ 6. provar_testplan_validate { project_path, plan_name }
87
91
  ```
88
92
 
93
+ Use `provar_testcase_step_edit` only when:
94
+
95
+ - Adding a single step to an existing, already-validated test case
96
+ - Fixing a step's attributes after a validation finding
97
+ - Targeted edits during debugging
98
+
99
+ Do **not** use `provar_testcase_step_edit` to construct a test case step-by-step from an empty skeleton — the LLM loses scenario context between calls and the resulting structure is unreliable.
100
+
89
101
  ---
90
102
 
91
103
  ## "I want to work with Salesforce metadata"
@@ -225,16 +225,23 @@ Required sequence — do not skip steps:
225
225
  6. provar_qualityhub_defect_create → optional, create defects for failures`,
226
226
  'author-test': `## Author a New Test Case
227
227
 
228
- 1. provar_project_inspect → find coverage gaps before writing
229
- 2. provar_automation_metadata_download → if SF metadata is stale (missing fields/objects)
230
- 3. provar_pageobject_generate if a new page object is needed
231
- 4. provar_pageobject_validate → validate before compile
232
- 5. provar_automation_compile after any page object change
233
- 6. provar_testcase_generate create the test case file
234
- 7. provar_testcase_step_edit add steps (repeat as needed)
235
- 8. provar_testcase_validate MUST pass before adding to a plan
236
- 9. provar_testplan_add-instance add to an existing plan
237
- 10. provar_testplan_validate validate the plan`,
228
+ Construct the full step tree in a single \`provar_testcase_generate\` call.
229
+ \`provar_testcase_step_edit\` is for amending an existing case, not for
230
+ building one step-by-step (that pattern drops scenarios and flattens nesting).
231
+
232
+ 1. provar_project_inspect find coverage gaps before writing
233
+ 2. provar_qualityhub_examples_retrieve ground in corpus examples for the step types you need
234
+ 3. provar_automation_metadata_download if SF metadata is stale (missing fields/objects)
235
+ 4. provar_pageobject_generate only if a new page object is needed
236
+ 5. provar_pageobject_validate validate before compile
237
+ 6. provar_automation_compile after any page object change
238
+ 7. provar_testcase_generate → single call, pass ALL steps in one payload
239
+ 8. provar_testcase_validate → MUST pass before adding to a plan
240
+ 9. provar_testplan_add-instance → add to an existing plan
241
+ 10. provar_testplan_validate → validate the plan
242
+
243
+ Use provar_testcase_step_edit only to amend an existing validated test case
244
+ (single-step add, attribute fix, debug edit) — never to construct one from scratch.`,
238
245
  'debug-failures': `## Debug Failing Tests
239
246
 
240
247
  1. provar_testrun_report_locate → find the report file
@@ -278,11 +285,14 @@ provar_pageobject_validate
278
285
  provar_nitrox_generate OR provar_nitrox_patch
279
286
  └── provar_nitrox_validate (always validate after)
280
287
 
281
- provar_testcase_generate OR provar_testcase_step_edit
288
+ provar_testcase_generate (construct full case — pass ALL steps in one call)
282
289
  └── provar_testcase_validate
283
290
  └── provar_testplan_add-instance
284
291
  └── provar_testplan_validate
285
292
 
293
+ provar_testcase_step_edit (amend an existing validated case only — never construct)
294
+ └── provar_testcase_validate
295
+
286
296
  ### Safe to run in parallel (no dependency between them)
287
297
  - provar_project_inspect + provar_connection_list
288
298
  - provar_pageobject_validate on multiple files
@@ -1 +1 @@
1
- {"version":3,"file":"guidePrompts.js","sourceRoot":"","sources":["../../../src/mcp/prompts/guidePrompts.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"guidePrompts.js","sourceRoot":"","sources":["../../../src/mcp/prompts/guidePrompts.ts"],"names":[],"mappings":"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"}
@@ -7,6 +7,7 @@ export interface ServerConfig {
7
7
  updateCommand: string | null;
8
8
  };
9
9
  }
10
+ export declare function parseActiveGroups(): Set<string> | null;
10
11
  export declare function createProvarMcpServer(config: ServerConfig): McpServer;
11
12
  /**
12
13
  * Resolve the docs directory for bundled MCP Markdown resources.
package/lib/mcp/server.js CHANGED
@@ -33,6 +33,70 @@ import { registerAllNitroXTools } from './tools/nitroXTools.js';
33
33
  import { registerAllTestCaseStepTools } from './tools/testCaseStepTools.js';
34
34
  import { registerAllConnectionTools } from './tools/connectionTools.js';
35
35
  import { registerAllPrompts } from './prompts/index.js';
36
+ import { createDepthGuardState, wrapWithDepthGuard, } from './utils/tokenMeta.js';
37
+ import { desc } from './tools/descHelper.js';
38
+ // ── Tool group registry ───────────────────────────────────────────────────────
39
+ // Groups are keyed in lowercase so they match the lowercased env var values.
40
+ const TOOL_GROUPS = {
41
+ nitrox: [registerAllNitroXTools],
42
+ automation: [registerAllAutomationTools],
43
+ qualityhub: [registerAllQualityHubTools, registerAllQualityHubApiTools, registerAllDefectTools],
44
+ validation: [
45
+ registerProjectValidateFromPath,
46
+ registerAllAntTools,
47
+ registerAllPropertiesTools,
48
+ registerTestCaseValidate,
49
+ registerTestSuiteValidate,
50
+ registerTestPlanValidate,
51
+ registerPageObjectValidate,
52
+ ],
53
+ authoring: [
54
+ registerTestCaseGenerate,
55
+ registerPageObjectGenerate,
56
+ registerAllTestCaseStepTools,
57
+ registerAllTestPlanTools,
58
+ ],
59
+ inspect: [registerProjectInspect],
60
+ connection: [registerAllConnectionTools],
61
+ rca: [registerAllRcaTools],
62
+ };
63
+ export function parseActiveGroups() {
64
+ const env = process.env['PROVAR_MCP_TOOLS'];
65
+ if (!env?.trim())
66
+ return null;
67
+ const requested = new Set(env
68
+ .split(',')
69
+ .map((g) => g.trim().toLowerCase())
70
+ .filter(Boolean));
71
+ if (requested.size === 0) {
72
+ log('warn', 'PROVAR_MCP_TOOLS was set but contained no valid group names — activating all groups', { raw: env });
73
+ return null;
74
+ }
75
+ const known = new Set(Object.keys(TOOL_GROUPS));
76
+ const matched = new Set();
77
+ const unknown = [];
78
+ for (const g of requested) {
79
+ if (known.has(g))
80
+ matched.add(g);
81
+ else
82
+ unknown.push(g);
83
+ }
84
+ if (unknown.length > 0) {
85
+ log('warn', 'PROVAR_MCP_TOOLS contains unknown group names — they will be ignored', {
86
+ raw: env,
87
+ unknown,
88
+ known: [...known],
89
+ });
90
+ }
91
+ if (matched.size === 0) {
92
+ log('warn', 'PROVAR_MCP_TOOLS matched no known group names — activating all groups', {
93
+ raw: env,
94
+ known: [...known],
95
+ });
96
+ return null;
97
+ }
98
+ return matched;
99
+ }
36
100
  export function createProvarMcpServer(config) {
37
101
  log('info', 'Creating Provar MCP server', { allowedPaths: config.allowedPaths });
38
102
  const server = new McpServer({
@@ -42,9 +106,13 @@ export function createProvarMcpServer(config) {
42
106
  // ── Sanity-check tool ────────────────────────────────────────────────────────
43
107
  server.registerTool('provardx_ping', {
44
108
  title: 'Ping MCP Server',
45
- description: 'Sanity-check tool. Echoes back a message with a timestamp. Use this to verify the MCP server is reachable before calling other tools.',
109
+ description: desc('Sanity-check tool. Echoes back a message with a timestamp. Use this to verify the MCP server is reachable before calling other tools.', 'Echo message back with timestamp; verify MCP server is reachable.'),
46
110
  inputSchema: {
47
- message: z.string().optional().default('ping').describe('Optional message to echo back'),
111
+ message: z
112
+ .string()
113
+ .optional()
114
+ .default('ping')
115
+ .describe(desc('Optional message to echo back', 'message to echo')),
48
116
  },
49
117
  }, ({ message }) => {
50
118
  const result = {
@@ -60,26 +128,20 @@ export function createProvarMcpServer(config) {
60
128
  structuredContent: result,
61
129
  };
62
130
  });
131
+ // ── Depth-guard middleware (PDX-474) ─────────────────────────────────────────
132
+ const rawLimit = parseInt(process.env['PROVAR_MCP_MAX_TOOL_DEPTH'] ?? '50', 10);
133
+ const depthLimit = Number.isNaN(rawLimit) || rawLimit <= 0 ? 50 : rawLimit;
134
+ const depthState = createDepthGuardState();
135
+ patchWithMiddleware(server, depthState, depthLimit);
63
136
  // ── Provar tools ─────────────────────────────────────────────────────────────
64
- registerProjectInspect(server, config);
65
- registerPageObjectGenerate(server, config);
66
- registerPageObjectValidate(server, config);
67
- registerTestCaseGenerate(server, config);
68
- registerTestCaseValidate(server, config);
69
- registerTestSuiteValidate(server);
70
- registerTestPlanValidate(server);
71
- registerProjectValidateFromPath(server, config);
72
- registerAllPropertiesTools(server, config);
73
- registerAllQualityHubTools(server);
74
- registerAllQualityHubApiTools(server);
75
- registerAllAutomationTools(server, config);
76
- registerAllDefectTools(server);
77
- registerAllAntTools(server, config);
78
- registerAllRcaTools(server, config);
79
- registerAllTestPlanTools(server, config);
80
- registerAllNitroXTools(server, config);
81
- registerAllTestCaseStepTools(server, config);
82
- registerAllConnectionTools(server, config);
137
+ const activeGroups = parseActiveGroups();
138
+ for (const [group, registrars] of Object.entries(TOOL_GROUPS)) {
139
+ if (activeGroups === null || activeGroups.has(group)) {
140
+ for (const register of registrars) {
141
+ register(server, config);
142
+ }
143
+ }
144
+ }
83
145
  // ── Provar prompts ───────────────────────────────────────────────────────────
84
146
  registerAllPrompts(server);
85
147
  // ── Documentation resources ──────────────────────────────────────────────────
@@ -167,6 +229,12 @@ export function createProvarMcpServer(config) {
167
229
  });
168
230
  return server;
169
231
  }
232
+ function patchWithMiddleware(server, state, limit) {
233
+ const orig = server.registerTool.bind(server);
234
+ // Cast through unknown to patch the overloaded method without triggering no-unsafe-any.
235
+ const patchable = server;
236
+ patchable.registerTool = (name, config, handler) => orig(name, config, wrapWithDepthGuard(name, handler, state, limit));
237
+ }
170
238
  /**
171
239
  * Resolve the docs directory for bundled MCP Markdown resources.
172
240
  * In compiled output (lib/mcp/) the sibling docs/ dir exists; in dev/ts-node
@@ -1 +1 @@
1
- {"version":3,"file":"server.js","sourceRoot":"","sources":["../../src/mcp/server.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"server.js","sourceRoot":"","sources":["../../src/mcp/server.ts"],"names":[],"mappings":"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"}
@@ -12,6 +12,7 @@ import { XMLParser } from 'fast-xml-parser';
12
12
  import { assertPathAllowed, PathPolicyError } from '../security/pathPolicy.js';
13
13
  import { makeError, makeRequestId } from '../schemas/common.js';
14
14
  import { log } from '../logging/logger.js';
15
+ import { desc } from './descHelper.js';
15
16
  // ── Sub-schemas ───────────────────────────────────────────────────────────────
16
17
  const FilesetSchema = z.object({
17
18
  dir: z.string().describe('Directory path (relative or absolute) for the fileset'),
@@ -56,126 +57,141 @@ const AttachmentPropertiesSchema = z.object({
56
57
  export function registerAntGenerate(server, config) {
57
58
  server.registerTool('provar_ant_generate', {
58
59
  title: 'Generate ANT Build File',
59
- description: [
60
+ description: desc([
60
61
  'Generate a Provar ANT build.xml file.',
61
62
  'Produces the standard <project> skeleton with Provar-Compile and Run-Test-Case tasks.',
62
63
  'Supports targeting tests by project folder, plan folder, or specific .testcase files via filesets.',
63
64
  'Returns XML content. Writes to disk only when dry_run=false.',
64
- ].join(' '),
65
+ ].join(' '), 'Generate a Provar ANT build.xml with Provar-Compile and Run-Test-Case tasks.'),
65
66
  inputSchema: {
66
67
  // ── Core paths ──────────────────────────────────────────────────────────
67
68
  provar_home: z
68
69
  .string()
69
- .describe('Absolute path to the Provar installation directory (e.g. "C:/Program Files/Provar/"). Used for provar.home property and ant taskdef classpaths.'),
70
+ .describe(desc('Absolute path to the Provar installation directory (e.g. "C:/Program Files/Provar/"). Used for provar.home property and ant taskdef classpaths.', 'string, absolute path to Provar installation')),
70
71
  project_path: z
71
72
  .string()
72
73
  .default('..')
73
- .describe('Path to the Provar test project root. Defaults to ".." (parent of the ANT folder).'),
74
+ .describe(desc('Path to the Provar test project root. Defaults to ".." (parent of the ANT folder).', 'string, path to project root')),
74
75
  results_path: z
75
76
  .string()
76
77
  .default('../ANT/Results')
77
- .describe('Path where test results are written. Defaults to "../ANT/Results".'),
78
+ .describe(desc('Path where test results are written. Defaults to "../ANT/Results".', 'string, path for test results')),
78
79
  project_cache_path: z
79
80
  .string()
80
81
  .optional()
81
- .describe('Path to the .provarCaches directory. Defaults to "../../.provarCaches" relative to the ANT folder.'),
82
+ .describe(desc('Path to the .provarCaches directory. Defaults to "../../.provarCaches" relative to the ANT folder.', 'string, optional; path to .provarCaches')),
82
83
  license_path: z
83
84
  .string()
84
85
  .optional()
85
- .describe('Path to the Provar .licenses directory (e.g. "${env.PROVAR_HOME}/.licenses").'),
86
+ .describe(desc('Path to the Provar .licenses directory (e.g. "${env.PROVAR_HOME}/.licenses").', 'string, optional; path to .licenses dir')),
86
87
  smtp_path: z
87
88
  .string()
88
89
  .optional()
89
- .describe('Path to the Provar .smtp directory (e.g. "${env.PROVAR_HOME}/.smtp").'),
90
+ .describe(desc('Path to the Provar .smtp directory (e.g. "${env.PROVAR_HOME}/.smtp").', 'string, optional; path to .smtp dir')),
90
91
  // ── Test selection ──────────────────────────────────────────────────────
91
92
  filesets: z
92
93
  .array(FilesetSchema)
93
94
  .min(1)
94
- .describe('One or more filesets defining which tests to run. ' +
95
+ .describe(desc('One or more filesets defining which tests to run. ' +
95
96
  'To run all tests under a folder: { dir: "../tests" }. ' +
96
97
  'To run a plan: { id: "testplan", dir: "../plans/MyPlan" }. ' +
97
- 'To run specific test cases: { dir: "../tests/Suite", includes: ["MyTest.testcase"] }.'),
98
+ 'To run specific test cases: { dir: "../tests/Suite", includes: ["MyTest.testcase"] }.', 'array, min 1; filesets defining which tests to run')),
98
99
  // ── Browser / environment ───────────────────────────────────────────────
99
100
  web_browser: z
100
101
  .enum(['Chrome', 'Chrome_Headless', 'Firefox', 'Edge', 'Edge_Legacy', 'Safari', 'IE'])
101
102
  .default('Chrome')
102
- .describe('Web browser to use for test execution.'),
103
+ .describe(desc('Web browser to use for test execution.', 'enum Chrome|Chrome_Headless|Firefox|Edge|Safari|IE')),
103
104
  web_browser_configuration: z
104
105
  .string()
105
106
  .default('Full Screen')
106
- .describe('Browser window configuration (e.g. "Full Screen").'),
107
- web_browser_provider_name: z.string().default('Desktop').describe('Browser provider name (e.g. "Desktop").'),
107
+ .describe(desc('Browser window configuration (e.g. "Full Screen").', 'string, browser window config')),
108
+ web_browser_provider_name: z
109
+ .string()
110
+ .default('Desktop')
111
+ .describe(desc('Browser provider name (e.g. "Desktop").', 'string, browser provider name')),
108
112
  web_browser_device_name: z
109
113
  .string()
110
114
  .default('Full Screen')
111
- .describe('Browser device name (e.g. "Full Screen").'),
115
+ .describe(desc('Browser device name (e.g. "Full Screen").', 'string, browser device name')),
112
116
  test_environment: z
113
117
  .string()
114
118
  .default('')
115
- .describe('Named test environment to use (must match a connection in the project). Empty string uses default.'),
119
+ .describe(desc('Named test environment to use (must match a connection in the project). Empty string uses default.', 'string, optional; named test environment')),
116
120
  // ── Cache / metadata ────────────────────────────────────────────────────
117
121
  salesforce_metadata_cache: z
118
122
  .enum(['Reuse', 'Refresh', 'Reload'])
119
123
  .default('Reuse')
120
- .describe('Salesforce metadata cache strategy: Reuse (fastest, uses cached), Refresh (re-downloads), Reload (clears and re-downloads).'),
124
+ .describe(desc('Salesforce metadata cache strategy: Reuse (fastest, uses cached), Refresh (re-downloads), Reload (clears and re-downloads).', 'enum Reuse|Refresh|Reload')),
121
125
  // ── Output / logging ────────────────────────────────────────────────────
122
126
  results_path_disposition: z
123
127
  .enum(['Increment', 'Replace', 'Reuse'])
124
128
  .default('Increment')
125
- .describe('How to handle the results folder when it already exists: Increment (new subfolder), Replace (overwrite), Reuse (append).'),
129
+ .describe(desc('How to handle the results folder when it already exists: Increment (new subfolder), Replace (overwrite), Reuse (append).', 'enum Increment|Replace|Reuse')),
126
130
  test_output_level: z
127
131
  .enum(['BASIC', 'WARNING', 'DEBUG'])
128
132
  .default('BASIC')
129
- .describe('Verbosity level for test output logs.'),
133
+ .describe(desc('Verbosity level for test output logs.', 'enum BASIC|WARNING|DEBUG')),
130
134
  plugin_output_level: z
131
135
  .enum(['BASIC', 'WARNING', 'DEBUG'])
132
136
  .default('WARNING')
133
- .describe('Verbosity level for plugin output logs.'),
137
+ .describe(desc('Verbosity level for plugin output logs.', 'enum BASIC|WARNING|DEBUG')),
134
138
  // ── Execution behaviour ─────────────────────────────────────────────────
135
139
  stop_test_run_on_error: z
136
140
  .boolean()
137
141
  .default(false)
138
- .describe('Abort the entire test run when any test case fails.'),
142
+ .describe(desc('Abort the entire test run when any test case fails.', 'bool, optional; abort on failure')),
139
143
  exclude_callable_test_cases: z
140
144
  .boolean()
141
145
  .default(true)
142
- .describe('Skip test cases marked as callable (library/helper) when true.'),
146
+ .describe(desc('Skip test cases marked as callable (library/helper) when true.', 'bool, optional; skip callable tests')),
143
147
  dont_fail_build: z
144
148
  .boolean()
145
149
  .optional()
146
- .describe('When true, the ANT build does not fail even if tests fail. Useful for CI pipelines that collect results separately.'),
147
- invoke_test_run_monitor: z.boolean().default(true).describe('Enable the Provar test run monitor.'),
150
+ .describe(desc('When true, the ANT build does not fail even if tests fail. Useful for CI pipelines that collect results separately.', 'bool, optional; skip build failure on test fail')),
151
+ invoke_test_run_monitor: z
152
+ .boolean()
153
+ .default(true)
154
+ .describe(desc('Enable the Provar test run monitor.', 'bool, optional; enable test run monitor')),
148
155
  // ── Secrets / security ──────────────────────────────────────────────────
149
156
  secrets_password: z
150
157
  .string()
151
158
  .default('${env.ProvarSecretsPassword}')
152
- .describe('Encryption key used to decrypt the Provar .secrets file (the password string itself, not a file path). Defaults to reading from the ProvarSecretsPassword environment variable.'),
159
+ .describe(desc('Encryption key used to decrypt the Provar .secrets file (the password string itself, not a file path). Defaults to reading from the ProvarSecretsPassword environment variable.', 'string, NOT a file path; encryption key for .secrets')),
153
160
  test_environment_secrets_password: z
154
161
  .string()
155
162
  .optional()
156
- .describe('Per-environment secrets password. Defaults to reading from the ProvarSecretsPassword_EnvName environment variable.'),
163
+ .describe(desc('Per-environment secrets password. Defaults to reading from the ProvarSecretsPassword_EnvName environment variable.', 'string, optional; per-environment secrets key')),
157
164
  // ── Test Cycle ──────────────────────────────────────────────────────────
158
- test_cycle_path: z.string().optional().describe('Path to a TestCycle folder (used with test cycle reporting).'),
165
+ test_cycle_path: z
166
+ .string()
167
+ .optional()
168
+ .describe(desc('Path to a TestCycle folder (used with test cycle reporting).', 'string, optional; path to TestCycle folder')),
159
169
  test_cycle_run_type: z
160
170
  .enum(['ALL', 'FAILED', 'NEW'])
161
171
  .optional()
162
- .describe('Which tests in the cycle to run (ALL, FAILED, NEW).'),
172
+ .describe(desc('Which tests in the cycle to run (ALL, FAILED, NEW).', 'enum ALL|FAILED|NEW, optional')),
163
173
  // ── Plan features ───────────────────────────────────────────────────────
164
174
  plan_features: z
165
175
  .array(PlanFeatureSchema)
166
176
  .optional()
167
- .describe('Output and notification features to enable/disable (e.g. PDF, PIECHART, EMAIL). ' +
168
- 'Only meaningful when running by test plan.'),
177
+ .describe(desc('Output and notification features to enable/disable (e.g. PDF, PIECHART, EMAIL). ' +
178
+ 'Only meaningful when running by test plan.', 'array, optional; plan output/notification features')),
169
179
  // ── Email / attachment reporting ────────────────────────────────────────
170
- email_properties: EmailPropertiesSchema.optional().describe('Email notification settings. Omit to exclude <emailProperties> from the XML.'),
171
- attachment_properties: AttachmentPropertiesSchema.optional().describe('Attachment/report content settings. Omit to exclude <attachmentProperties> from the XML.'),
180
+ email_properties: EmailPropertiesSchema.optional().describe(desc('Email notification settings. Omit to exclude <emailProperties> from the XML.', 'object, optional; email notification settings')),
181
+ attachment_properties: AttachmentPropertiesSchema.optional().describe(desc('Attachment/report content settings. Omit to exclude <attachmentProperties> from the XML.', 'object, optional; attachment/report content settings')),
172
182
  // ── File output ─────────────────────────────────────────────────────────
173
183
  output_path: z
174
184
  .string()
175
185
  .optional()
176
- .describe('Where to write the build.xml file (returned in response). Required when dry_run=false.'),
177
- overwrite: z.boolean().default(false).describe('Overwrite output_path if the file already exists.'),
178
- dry_run: z.boolean().default(true).describe('true = return XML only (default); false = write to output_path.'),
186
+ .describe(desc('Where to write the build.xml file (returned in response). Required when dry_run=false.', 'string, optional; absolute path for build.xml output')),
187
+ overwrite: z
188
+ .boolean()
189
+ .default(false)
190
+ .describe(desc('Overwrite output_path if the file already exists.', 'bool, optional; overwrite if exists')),
191
+ dry_run: z
192
+ .boolean()
193
+ .default(true)
194
+ .describe(desc('true = return XML only (default); false = write to output_path.', 'bool, optional; true=return only, false=write')),
179
195
  },
180
196
  }, (input) => {
181
197
  const requestId = makeRequestId();
@@ -234,15 +250,21 @@ export function registerAntGenerate(server, config) {
234
250
  export function registerAntValidate(server, config) {
235
251
  server.registerTool('provar_ant_validate', {
236
252
  title: 'Validate ANT Build File',
237
- description: [
253
+ description: desc([
238
254
  'Validate a Provar ANT build.xml for structural correctness.',
239
255
  'Checks XML well-formedness, required <taskdef> declarations, <Provar-Compile> step,',
240
256
  '<Run-Test-Case> with required attributes (provarHome, projectPath, resultsPath),',
241
257
  'and at least one <fileset> child. Returns is_valid, issues list, and a validity_score.',
242
- ].join(' '),
258
+ ].join(' '), 'Validate a Provar ANT build.xml for structural correctness.'),
243
259
  inputSchema: {
244
- content: z.string().optional().describe('XML content to validate directly'),
245
- file_path: z.string().optional().describe('Path to the build.xml file to validate'),
260
+ content: z
261
+ .string()
262
+ .optional()
263
+ .describe(desc('XML content to validate directly', 'string, optional; inline XML')),
264
+ file_path: z
265
+ .string()
266
+ .optional()
267
+ .describe(desc('Path to the build.xml file to validate', 'string, optional; absolute path to build.xml')),
246
268
  },
247
269
  }, ({ content, file_path }) => {
248
270
  const requestId = makeRequestId();