@kkeve/suite 0.0.1 → 0.0.2

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 (152) hide show
  1. package/README.md +53 -0
  2. package/dist/bin/keve.d.ts +13 -0
  3. package/dist/bin/keve.js +164 -0
  4. package/dist/commands/auth-update.d.ts +16 -0
  5. package/dist/commands/auth-update.js +88 -0
  6. package/dist/commands/clean.d.ts +10 -0
  7. package/dist/commands/clean.js +78 -0
  8. package/dist/commands/config.d.ts +17 -0
  9. package/dist/commands/config.js +99 -0
  10. package/dist/commands/init.d.ts +15 -0
  11. package/dist/commands/init.js +292 -0
  12. package/dist/commands/report.d.ts +12 -0
  13. package/dist/commands/report.js +159 -0
  14. package/dist/commands/run.d.ts +29 -0
  15. package/dist/commands/run.js +417 -0
  16. package/dist/commands/test.d.ts +12 -0
  17. package/dist/commands/test.js +102 -0
  18. package/dist/commands/vitest.d.ts +14 -0
  19. package/dist/commands/vitest.js +166 -0
  20. package/dist/config.d.ts +109 -0
  21. package/dist/config.js +291 -0
  22. package/dist/core/action-log-writer.d.ts +47 -0
  23. package/dist/{tools/write-file.js → core/action-log-writer.js} +42 -26
  24. package/dist/core/auth.d.ts +17 -0
  25. package/dist/core/auth.js +224 -0
  26. package/dist/core/cdp-resolver.d.ts +5 -0
  27. package/dist/core/cdp-resolver.js +93 -0
  28. package/dist/core/generateReport/report.d.ts +19 -0
  29. package/dist/core/generateReport/report.js +91 -0
  30. package/dist/core/generateReport/reportData.d.ts +215 -0
  31. package/dist/core/generateReport/reportData.js +735 -0
  32. package/dist/core/global-setup.d.ts +6 -0
  33. package/dist/core/global-setup.js +113 -0
  34. package/dist/core/keve-aspect.d.ts +54 -0
  35. package/dist/core/keve-aspect.js +52 -0
  36. package/dist/core/keve-decorators.d.ts +51 -0
  37. package/dist/core/keve-decorators.js +95 -0
  38. package/dist/core/keve-registry.d.ts +38 -0
  39. package/dist/core/keve-registry.js +25 -0
  40. package/dist/core/keve-report.d.ts +27 -0
  41. package/dist/core/keve-report.js +357 -0
  42. package/dist/core/keve-test.d.ts +36 -0
  43. package/dist/core/keve-test.js +364 -0
  44. package/dist/core/learned-actions.d.ts +24 -0
  45. package/dist/core/learned-actions.js +65 -0
  46. package/dist/core/pw-config.d.ts +19 -0
  47. package/dist/core/pw-config.js +180 -0
  48. package/dist/index.d.ts +8 -23
  49. package/dist/index.js +36 -43
  50. package/dist/page-agent/agent.d.ts +129 -0
  51. package/dist/page-agent/agent.js +585 -0
  52. package/dist/page-agent/hooks.d.ts +13 -0
  53. package/dist/page-agent/hooks.js +218 -0
  54. package/dist/page-agent/tools.d.ts +29 -0
  55. package/dist/page-agent/tools.js +297 -0
  56. package/doc/README.md +124 -0
  57. package/doc/agents/keve-dev-test-agent.md +140 -0
  58. package/doc/agents/keve-test-agent.md +178 -0
  59. package/doc/asserts//346/265/213/350/257/225/345/220/204/351/230/266/346/256/265/350/257/264/346/230/216.png +0 -0
  60. package/doc/keve-agent-demo.html +370 -0
  61. package/doc/skills/keve-bddcase-gen/SKILL.md +332 -0
  62. package/doc/skills/keve-bddcase-gen/references/test-case-rules.md +91 -0
  63. package/doc/skills/keve-bddcase-gen/references/test-cases-example.md +103 -0
  64. package/doc/skills/keve-component-gen/SKILL.md +255 -0
  65. package/doc/skills/keve-component-gen/references/component-mock-strategy.md +74 -0
  66. package/doc/skills/keve-component-gen/references/component-model-template.md +98 -0
  67. package/doc/skills/keve-component-gen/references/component-test-template.md +100 -0
  68. package/doc/skills/keve-component-gen/references/vue-test-utils-guide.md +91 -0
  69. package/doc/skills/keve-e2e-gen/SKILL.md +179 -0
  70. package/doc/skills/keve-e2e-gen/references/code-analysis-guide.md +208 -0
  71. package/doc/skills/keve-e2e-gen/references/decisions.md +36 -0
  72. package/doc/skills/keve-e2e-gen/references/pom-generation-guide.md +140 -0
  73. package/doc/skills/keve-e2e-gen/references/script-generation-guide.md +236 -0
  74. package/doc/skills/keve-e2e-gen/references/test-auditor-guide.md +189 -0
  75. package/doc/skills/keve-e2e-gen/scripts/extract-components.sh +85 -0
  76. package/doc/skills/keve-e2e-gen/scripts/inject-testids.sh +95 -0
  77. package/doc/skills/keve-static-analysis/SKILL.md +362 -0
  78. package/doc/skills/keve-static-analysis/references/codegraph-analysis-guide.md +108 -0
  79. package/doc/skills/keve-static-analysis/references/git-impact-analysis.md +81 -0
  80. package/doc/skills/keve-static-analysis/references/lint-fix-guide.md +69 -0
  81. package/doc/skills/keve-static-analysis/references/runtime-risk-patterns.md +92 -0
  82. package/doc/skills/keve-static-analysis/references/security-scan-guide.md +32 -0
  83. package/doc/skills/keve-static-analysis/references/ts-error-patterns.md +98 -0
  84. package/doc/skills/keve-static-analysis/references/vue-security-guide.md +72 -0
  85. package/doc/skills/keve-test-eval/SKILL.md +78 -0
  86. package/doc/skills/keve-test-eval/references/common-fix-guide.md +166 -0
  87. package/doc/skills/keve-test-eval/references/confidence-data-guide.md +78 -0
  88. package/doc/skills/keve-test-eval/references/fix-loop-guide.md +67 -0
  89. package/doc/skills/keve-unit-gen/SKILL.md +203 -0
  90. package/doc/skills/keve-unit-gen/references/boundary-conditions.md +78 -0
  91. package/doc/skills/keve-unit-gen/references/unit-mock-strategy.md +71 -0
  92. package/doc/skills/keve-unit-gen/references/unit-test-template.md +105 -0
  93. package/package.json +47 -25
  94. package/dist/agent/factory.d.ts +0 -25
  95. package/dist/agent/factory.js +0 -99
  96. package/dist/agent/index.d.ts +0 -3
  97. package/dist/agent/index.js +0 -7
  98. package/dist/agent/loader.d.ts +0 -22
  99. package/dist/agent/loader.js +0 -117
  100. package/dist/agent/types.d.ts +0 -9
  101. package/dist/agent/types.js +0 -2
  102. package/dist/agent-loop/complete-task.d.ts +0 -28
  103. package/dist/agent-loop/complete-task.js +0 -70
  104. package/dist/agent-loop/index.d.ts +0 -16
  105. package/dist/agent-loop/index.js +0 -26
  106. package/dist/agent-loop/loop.d.ts +0 -42
  107. package/dist/agent-loop/loop.js +0 -282
  108. package/dist/agent-loop/runtime.d.ts +0 -40
  109. package/dist/agent-loop/runtime.js +0 -163
  110. package/dist/agent-loop/types.d.ts +0 -161
  111. package/dist/agent-loop/types.js +0 -105
  112. package/dist/context/index.d.ts +0 -8
  113. package/dist/context/index.js +0 -29
  114. package/dist/context/tokenCalculation.d.ts +0 -55
  115. package/dist/context/tokenCalculation.js +0 -95
  116. package/dist/context/truncation.d.ts +0 -67
  117. package/dist/context/truncation.js +0 -142
  118. package/dist/context/types.d.ts +0 -7
  119. package/dist/context/types.js +0 -27
  120. package/dist/llm/OpenAIClient.d.ts +0 -31
  121. package/dist/llm/OpenAIClient.js +0 -455
  122. package/dist/llm/constants.d.ts +0 -2
  123. package/dist/llm/constants.js +0 -6
  124. package/dist/llm/errors.d.ts +0 -25
  125. package/dist/llm/errors.js +0 -51
  126. package/dist/llm/index.d.ts +0 -49
  127. package/dist/llm/index.js +0 -158
  128. package/dist/llm/types.d.ts +0 -124
  129. package/dist/llm/types.js +0 -2
  130. package/dist/llm/utils.d.ts +0 -29
  131. package/dist/llm/utils.js +0 -284
  132. package/dist/skill/frontmatter-parser.d.ts +0 -50
  133. package/dist/skill/frontmatter-parser.js +0 -152
  134. package/dist/skill/index.d.ts +0 -12
  135. package/dist/skill/index.js +0 -17
  136. package/dist/skill/loader.d.ts +0 -96
  137. package/dist/skill/loader.js +0 -256
  138. package/dist/tools/ask-user.d.ts +0 -8
  139. package/dist/tools/ask-user.js +0 -47
  140. package/dist/tools/bash.d.ts +0 -47
  141. package/dist/tools/bash.js +0 -213
  142. package/dist/tools/edit-file.d.ts +0 -9
  143. package/dist/tools/edit-file.js +0 -76
  144. package/dist/tools/glob.d.ts +0 -8
  145. package/dist/tools/glob.js +0 -101
  146. package/dist/tools/grep.d.ts +0 -10
  147. package/dist/tools/grep.js +0 -76
  148. package/dist/tools/index.d.ts +0 -24
  149. package/dist/tools/index.js +0 -47
  150. package/dist/tools/read-files.d.ts +0 -8
  151. package/dist/tools/read-files.js +0 -81
  152. package/dist/tools/write-file.d.ts +0 -8
package/dist/llm/index.js DELETED
@@ -1,158 +0,0 @@
1
- "use strict";
2
- /**
3
- * LLM client with MacroTool support
4
- *
5
- * Key features:
6
- * - Direct fetch to OpenAI API (no LangChain dependency)
7
- * - Zod schema for tool definitions
8
- * - toolChoiceName support (force specific tool call)
9
- * - parallel_tool_calls: false (one tool per step)
10
- * - Retry with error classification
11
- * - Model-specific patches (Claude, Qwen, GPT, etc.)
12
- */
13
- Object.defineProperty(exports, "__esModule", { value: true });
14
- exports.LLM = exports.extractXMLTag = exports.parseXMLExtractionResponse = exports.InvokeErrorType = exports.InvokeError = void 0;
15
- exports.parseLLMConfig = parseLLMConfig;
16
- const OpenAIClient_1 = require("./OpenAIClient");
17
- const constants_1 = require("./constants");
18
- const errors_1 = require("./errors");
19
- Object.defineProperty(exports, "InvokeError", { enumerable: true, get: function () { return errors_1.InvokeError; } });
20
- Object.defineProperty(exports, "InvokeErrorType", { enumerable: true, get: function () { return errors_1.InvokeErrorType; } });
21
- const utils_1 = require("./utils");
22
- Object.defineProperty(exports, "parseXMLExtractionResponse", { enumerable: true, get: function () { return utils_1.parseXMLExtractionResponse; } });
23
- Object.defineProperty(exports, "extractXMLTag", { enumerable: true, get: function () { return utils_1.extractXMLTag; } });
24
- function parseLLMConfig(config) {
25
- if (!config.baseURL || !config.model) {
26
- throw new Error('[EVEAgent] LLM configuration required. Please provide: baseURL, model.');
27
- }
28
- return {
29
- baseURL: config.baseURL,
30
- model: config.model,
31
- apiKey: config.apiKey || '',
32
- temperature: config.temperature ?? constants_1.DEFAULT_TEMPERATURE,
33
- maxRetries: config.maxRetries ?? constants_1.LLM_MAX_RETRIES,
34
- disableNamedToolChoice: config.disableNamedToolChoice ?? false,
35
- customFetch: (config.customFetch ?? fetch).bind(globalThis),
36
- };
37
- }
38
- class LLM extends EventTarget {
39
- config;
40
- client;
41
- constructor(config) {
42
- super();
43
- this.config = parseLLMConfig(config);
44
- this.client = new OpenAIClient_1.OpenAIClient(this.config);
45
- }
46
- /**
47
- * Call LLM API once, invoke tool call once, return the result.
48
- * This is the core method used by gui-agent's MacroTool loop.
49
- */
50
- async invoke(messages, tools, abortSignal, options) {
51
- const signal = abortSignal || new AbortController().signal;
52
- return await withRetry(async () => {
53
- if (signal.aborted)
54
- throw new Error('AbortError');
55
- return await this.client.invoke(messages, tools, signal, options);
56
- }, {
57
- maxRetries: this.config.maxRetries,
58
- onRetry: (attempt) => {
59
- this.dispatchEvent(new CustomEvent('retry', { detail: { attempt, maxAttempts: this.config.maxRetries } }));
60
- },
61
- onError: (error) => {
62
- this.dispatchEvent(new CustomEvent('error', { detail: { error } }));
63
- },
64
- });
65
- }
66
- /**
67
- * Simple chat call — no tools, just text generation.
68
- * Used for validation and other non-tool-call LLM tasks.
69
- */
70
- async chat(messages, abortSignal) {
71
- const requestBody = {
72
- model: this.config.model,
73
- temperature: this.config.temperature,
74
- messages,
75
- };
76
- (0, utils_1.modelPatch)(requestBody);
77
- const response = await this.config.customFetch(`${this.config.baseURL}/chat/completions`, {
78
- method: 'POST',
79
- headers: {
80
- 'Content-Type': 'application/json',
81
- ...(this.config.apiKey && { Authorization: `Bearer ${this.config.apiKey}` }),
82
- },
83
- body: JSON.stringify(requestBody),
84
- signal: abortSignal,
85
- });
86
- if (!response.ok) {
87
- const errorData = await response.json().catch(() => ({}));
88
- throw new Error(`LLM chat failed: HTTP ${response.status} - ${errorData.error?.message || response.statusText}`);
89
- }
90
- const data = await response.json();
91
- const content = data.choices?.[0]?.message?.content || '';
92
- return {
93
- content,
94
- usage: {
95
- prompt_tokens: data.usage?.prompt_tokens ?? 0,
96
- completion_tokens: data.usage?.completion_tokens ?? 0,
97
- total_tokens: data.usage?.total_tokens ?? 0,
98
- },
99
- };
100
- }
101
- /**
102
- * Agent loop chat — call LLM with tools and return the full assistant message.
103
- * Unlike invoke(), this does NOT execute tools. The agent loop handles tool
104
- * execution via its own ToolRegistry after getting the response.
105
- *
106
- * Uses tool_choice: 'auto' by default (LLM can choose text or tool_calls).
107
- * Includes retry logic with exponential backoff.
108
- */
109
- async chatWithTools(messages, tools, abortSignal, options) {
110
- const signal = abortSignal || new AbortController().signal;
111
- return await withRetry(async () => {
112
- if (signal.aborted)
113
- throw new Error('AbortError');
114
- return await this.client.chat(messages, tools, signal, options);
115
- }, {
116
- maxRetries: this.config.maxRetries,
117
- onRetry: (attempt) => {
118
- this.dispatchEvent(new CustomEvent('retry', { detail: { attempt, maxAttempts: this.config.maxRetries } }));
119
- },
120
- onError: (error) => {
121
- this.dispatchEvent(new CustomEvent('error', { detail: { error } }));
122
- },
123
- });
124
- }
125
- }
126
- exports.LLM = LLM;
127
- async function withRetry(fn, settings) {
128
- let attempt = 0;
129
- let lastError = null;
130
- while (attempt <= settings.maxRetries) {
131
- if (attempt > 0) {
132
- settings.onRetry(attempt);
133
- // Exponential backoff: 1s, 2s, 4s, 8s...
134
- const delay = Math.min(1000 * Math.pow(2, attempt - 1), 30000);
135
- console.log(`[Retry] Attempt ${attempt}/${settings.maxRetries}, waiting ${delay}ms...`);
136
- await new Promise((resolve) => setTimeout(resolve, delay));
137
- }
138
- try {
139
- return await fn();
140
- }
141
- catch (error) {
142
- if (error?.rawError?.name === 'AbortError')
143
- throw error;
144
- settings.onError(error);
145
- if (error instanceof errors_1.InvokeError && !error.retryable)
146
- throw error;
147
- // Rate limit (429): use longer backoff
148
- if (error instanceof errors_1.InvokeError && error.type === 'rate_limit') {
149
- const rateLimitDelay = Math.min(5000 * attempt + 5000, 60000); // 5s, 10s, 15s...
150
- console.log(`[Retry] Rate limit hit, waiting ${rateLimitDelay}ms...`);
151
- await new Promise((resolve) => setTimeout(resolve, rateLimitDelay));
152
- }
153
- lastError = error;
154
- attempt++;
155
- }
156
- }
157
- throw lastError;
158
- }
@@ -1,124 +0,0 @@
1
- /**
2
- * Core types for LLM integration
3
- */
4
- import type * as z from 'zod/v4';
5
- /**
6
- * Content item for multimodal messages
7
- */
8
- export type ContentItem = {
9
- type: 'text';
10
- text: string;
11
- } | {
12
- type: 'image_url';
13
- image_url: {
14
- url: string;
15
- detail?: 'low' | 'high' | 'auto';
16
- };
17
- };
18
- /**
19
- * Message format - OpenAI standard
20
- */
21
- export interface Message {
22
- role: 'system' | 'user' | 'assistant' | 'tool';
23
- content?: string | ContentItem[] | null;
24
- tool_calls?: {
25
- id: string;
26
- type: 'function';
27
- function: {
28
- name: string;
29
- arguments: string;
30
- };
31
- }[];
32
- tool_call_id?: string;
33
- name?: string;
34
- }
35
- /**
36
- * Tool definition - uses Zod schema
37
- * Optional customJsonSchema: If provided, this JSON Schema is sent to the LLM
38
- * instead of converting inputSchema via zodToOpenAITool.
39
- * This allows detailed tool parameter descriptions while keeping zod validation loose.
40
- */
41
- export interface Tool<TParams = any, TResult = any> {
42
- description?: string;
43
- inputSchema: z.ZodType<TParams>;
44
- execute: (args: TParams) => Promise<TResult>;
45
- /** Custom JSON Schema sent to LLM (overrides zodToOpenAITool conversion) */
46
- customJsonSchema?: Record<string, any>;
47
- }
48
- /**
49
- * Invoke options for LLM call
50
- */
51
- export interface InvokeOptions {
52
- /**
53
- * Force LLM to call a specific tool by name.
54
- * If provided: tool_choice = { type: 'function', function: { name: toolChoiceName } }
55
- * If not provided: tool_choice = 'required'
56
- */
57
- toolChoiceName?: string;
58
- /**
59
- * Response normalization function.
60
- */
61
- normalizeResponse?: (response: any) => any;
62
- }
63
- /**
64
- * Invoke result
65
- */
66
- export interface InvokeResult<TResult = unknown> {
67
- toolCall: {
68
- name: string;
69
- args: any;
70
- };
71
- toolResult: TResult;
72
- usage: {
73
- promptTokens: number;
74
- completionTokens: number;
75
- totalTokens: number;
76
- cachedTokens?: number;
77
- reasoningTokens?: number;
78
- };
79
- rawResponse?: unknown;
80
- rawRequest?: unknown;
81
- }
82
- /**
83
- * Chat result — returns the full assistant message without executing tools.
84
- * Used by the agent loop to get the LLM's response and then process tool_calls separately.
85
- */
86
- export interface ChatResult {
87
- /** The full assistant message from the LLM response. */
88
- message: Message;
89
- /** Token usage information. */
90
- usage: {
91
- promptTokens: number;
92
- completionTokens: number;
93
- totalTokens: number;
94
- cachedTokens?: number;
95
- reasoningTokens?: number;
96
- };
97
- /** The raw API response data. */
98
- rawResponse?: unknown;
99
- }
100
- /**
101
- * LLM Client interface
102
- */
103
- export interface LLMClient {
104
- invoke(messages: Message[], tools: Record<string, Tool>, abortSignal?: AbortSignal, options?: InvokeOptions): Promise<InvokeResult>;
105
- /**
106
- * Call the LLM and return the full assistant message.
107
- * Unlike invoke(), this does NOT execute any tools — it just returns
108
- * the raw response. The caller (agent loop) processes tool_calls and
109
- * executes tools separately via its own ToolRegistry.
110
- */
111
- chat(messages: Message[], tools: Record<string, Tool>, abortSignal?: AbortSignal, options?: InvokeOptions): Promise<ChatResult>;
112
- }
113
- /**
114
- * LLM configuration
115
- */
116
- export interface LLMConfig {
117
- baseURL: string;
118
- model: string;
119
- apiKey?: string;
120
- temperature?: number;
121
- maxRetries?: number;
122
- disableNamedToolChoice?: boolean;
123
- customFetch?: typeof globalThis.fetch;
124
- }
package/dist/llm/types.js DELETED
@@ -1,2 +0,0 @@
1
- "use strict";
2
- Object.defineProperty(exports, "__esModule", { value: true });
@@ -1,29 +0,0 @@
1
- import * as z from 'zod/v4';
2
- import type { Tool } from './types';
3
- /**
4
- * Convert Zod schema to OpenAI tool format
5
- */
6
- export declare function zodToOpenAITool(name: string, tool: Tool): {
7
- type: "function";
8
- function: {
9
- name: string;
10
- description: string | undefined;
11
- parameters: z.core.ZodStandardJSONSchemaPayload<z.ZodType<any, unknown, z.core.$ZodTypeInternals<any, unknown>>>;
12
- };
13
- };
14
- /**
15
- * Patch model specific parameters
16
- */
17
- export declare function modelPatch(body: Record<string, any>): Record<string, any>;
18
- /**
19
- * Parse XML response from LLM and convert to AIDataExtractionResponse
20
- */
21
- export declare function parseXMLExtractionResponse<T>(xmlString: string): any;
22
- export declare function safeParseJson(input: string, modelFamily: any | undefined): any;
23
- /**
24
- * Extract content from an XML tag in a string
25
- * @param xmlString - The XML string to parse
26
- * @param tagName - The name of the tag to extract (case-insensitive)
27
- * @returns The trimmed content of the tag, or undefined if not found
28
- */
29
- export declare function extractXMLTag(xmlString: string, tagName: string): string | undefined;
package/dist/llm/utils.js DELETED
@@ -1,284 +0,0 @@
1
- "use strict";
2
- var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
3
- if (k2 === undefined) k2 = k;
4
- var desc = Object.getOwnPropertyDescriptor(m, k);
5
- if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
6
- desc = { enumerable: true, get: function() { return m[k]; } };
7
- }
8
- Object.defineProperty(o, k2, desc);
9
- }) : (function(o, m, k, k2) {
10
- if (k2 === undefined) k2 = k;
11
- o[k2] = m[k];
12
- }));
13
- var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
14
- Object.defineProperty(o, "default", { enumerable: true, value: v });
15
- }) : function(o, v) {
16
- o["default"] = v;
17
- });
18
- var __importStar = (this && this.__importStar) || (function () {
19
- var ownKeys = function(o) {
20
- ownKeys = Object.getOwnPropertyNames || function (o) {
21
- var ar = [];
22
- for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
23
- return ar;
24
- };
25
- return ownKeys(o);
26
- };
27
- return function (mod) {
28
- if (mod && mod.__esModule) return mod;
29
- var result = {};
30
- if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
31
- __setModuleDefault(result, mod);
32
- return result;
33
- };
34
- })();
35
- Object.defineProperty(exports, "__esModule", { value: true });
36
- exports.zodToOpenAITool = zodToOpenAITool;
37
- exports.modelPatch = modelPatch;
38
- exports.parseXMLExtractionResponse = parseXMLExtractionResponse;
39
- exports.safeParseJson = safeParseJson;
40
- exports.extractXMLTag = extractXMLTag;
41
- /**
42
- * Utility functions for LLM integration
43
- */
44
- const jsonrepair_1 = require("jsonrepair");
45
- const z = __importStar(require("zod/v4"));
46
- /**
47
- * Convert Zod schema to OpenAI tool format
48
- */
49
- function zodToOpenAITool(name, tool) {
50
- return {
51
- type: 'function',
52
- function: {
53
- name,
54
- description: tool.description,
55
- parameters: z.toJSONSchema(tool.inputSchema, { target: 'openapi-3.0' }),
56
- },
57
- };
58
- }
59
- /**
60
- * Patch model specific parameters
61
- */
62
- function modelPatch(body) {
63
- const model = body.model || '';
64
- if (!model)
65
- return body;
66
- const modelName = normalizeModelName(model);
67
- if (modelName.startsWith('qwen') || modelName.startsWith('app-')) {
68
- body.temperature = Math.max(body.temperature || 0, 1.0);
69
- body.enable_thinking = false;
70
- }
71
- if (modelName.startsWith('claude')) {
72
- body.thinking = { type: 'disabled' };
73
- if (body.tool_choice === 'required') {
74
- body.tool_choice = { type: 'any' };
75
- }
76
- else if (body.tool_choice?.function?.name) {
77
- body.tool_choice = { type: 'tool', name: body.tool_choice.function.name };
78
- }
79
- }
80
- if (modelName.startsWith('grok')) {
81
- delete body.tool_choice;
82
- body.thinking = { type: 'disabled', effort: 'minimal' };
83
- body.reasoning = { enabled: false, effort: 'low' };
84
- }
85
- if (modelName.startsWith('gpt')) {
86
- if (modelName.startsWith('gpt-52')) {
87
- body.reasoning_effort = 'none';
88
- }
89
- else if (modelName.startsWith('gpt-51')) {
90
- body.reasoning_effort = 'none';
91
- }
92
- else if (modelName.startsWith('gpt-54')) {
93
- delete body.reasoning_effort;
94
- }
95
- else if (modelName.startsWith('gpt-5-mini')) {
96
- body.reasoning_effort = 'low';
97
- body.temperature = 1;
98
- }
99
- else if (modelName.startsWith('gpt-5')) {
100
- body.reasoning_effort = 'low';
101
- }
102
- }
103
- if (modelName.startsWith('gemini')) {
104
- body.reasoning_effort = 'minimal';
105
- }
106
- if (modelName.startsWith('minimax')) {
107
- body.temperature = Math.max(body.temperature || 0, 0.01);
108
- if (body.temperature > 1)
109
- body.temperature = 1;
110
- delete body.parallel_tool_calls;
111
- }
112
- return body;
113
- }
114
- function normalizeModelName(modelName) {
115
- let normalizedName = modelName.toLowerCase();
116
- if (normalizedName.includes('/')) {
117
- normalizedName = normalizedName.split('/')[1];
118
- }
119
- normalizedName = normalizedName.replace(/_/g, '');
120
- normalizedName = normalizedName.replace(/\./g, '');
121
- return normalizedName;
122
- }
123
- /**
124
- * Parse XML response from LLM and convert to AIDataExtractionResponse
125
- */
126
- function parseXMLExtractionResponse(xmlString) {
127
- const thought = extractXMLTag(xmlString, 'thought');
128
- const dataJsonStr = extractXMLTag(xmlString, 'data-json');
129
- const errorsStr = extractXMLTag(xmlString, 'errors');
130
- let data = '';
131
- if (dataJsonStr) {
132
- try {
133
- data = safeParseJson(dataJsonStr, undefined);
134
- }
135
- catch (e) {
136
- throw new Error(`Failed to parse data-json: ${e}`);
137
- }
138
- }
139
- // Parse errors (optional)
140
- let errors;
141
- if (errorsStr) {
142
- try {
143
- const parsedErrors = safeParseJson(errorsStr, undefined);
144
- if (Array.isArray(parsedErrors)) {
145
- errors = parsedErrors;
146
- }
147
- }
148
- catch (e) {
149
- // If errors parsing fails, just ignore it
150
- }
151
- }
152
- return {
153
- ...(thought ? { thought } : {}),
154
- data: data || xmlString,
155
- ...(errors && errors.length > 0 ? { errors } : {}),
156
- };
157
- }
158
- function safeParseJson(input, modelFamily) {
159
- const cleanJsonString = extractJSONFromCodeBlock(input);
160
- // match the point
161
- if (cleanJsonString?.match(/\((\d+),(\d+)\)/)) {
162
- return cleanJsonString
163
- .match(/\((\d+),(\d+)\)/)
164
- ?.slice(1)
165
- .map(Number);
166
- }
167
- let parsed;
168
- let lastError;
169
- try {
170
- parsed = JSON.parse(cleanJsonString);
171
- return normalizeJsonObject(parsed);
172
- }
173
- catch (error) {
174
- lastError = error;
175
- }
176
- try {
177
- parsed = JSON.parse((0, jsonrepair_1.jsonrepair)(cleanJsonString));
178
- return normalizeJsonObject(parsed);
179
- }
180
- catch (error) {
181
- lastError = error;
182
- }
183
- if (modelFamily === 'doubao-vision' || isUITars(modelFamily)) {
184
- const jsonString = preprocessDoubaoBboxJson(cleanJsonString);
185
- try {
186
- parsed = JSON.parse((0, jsonrepair_1.jsonrepair)(jsonString));
187
- return normalizeJsonObject(parsed);
188
- }
189
- catch (error) {
190
- lastError = error;
191
- }
192
- }
193
- throw Error(`failed to parse LLM response into JSON. Error - ${String(lastError ?? 'unknown error')}. Response - \n ${input}`);
194
- }
195
- /**
196
- * Extract content from an XML tag in a string
197
- * @param xmlString - The XML string to parse
198
- * @param tagName - The name of the tag to extract (case-insensitive)
199
- * @returns The trimmed content of the tag, or undefined if not found
200
- */
201
- function extractXMLTag(xmlString, tagName) {
202
- const regex = new RegExp(`<${tagName}>([\\s\\S]*?)</${tagName}>`, 'i');
203
- const match = xmlString.match(regex);
204
- return match ? match[1].trim() : undefined;
205
- }
206
- function extractJSONFromCodeBlock(response) {
207
- try {
208
- // First, try to match a JSON object directly in the response
209
- const jsonMatch = response.match(/^\s*(\{[\s\S]*\})\s*$/);
210
- if (jsonMatch) {
211
- return jsonMatch[1];
212
- }
213
- // If no direct JSON object is found, try to extract JSON from a code block
214
- const codeBlockMatch = response.match(/```(?:json)?\s*(\{[\s\S]*?\})\s*```/);
215
- if (codeBlockMatch) {
216
- return codeBlockMatch[1];
217
- }
218
- // If no code block is found, try to find a JSON-like structure in the text
219
- const jsonLikeMatch = response.match(/\{[\s\S]*\}/);
220
- if (jsonLikeMatch) {
221
- return jsonLikeMatch[0];
222
- }
223
- }
224
- catch { }
225
- // If no JSON-like structure is found, return the original response
226
- return response;
227
- }
228
- /**
229
- * Normalize a parsed JSON object by trimming whitespace from:
230
- * 1. All object keys (e.g., " prompt " -> "prompt")
231
- * 2. All string values (e.g., " Tap " -> "Tap")
232
- * This handles LLM output that may include leading/trailing spaces.
233
- */
234
- function normalizeJsonObject(obj) {
235
- // Handle null and undefined
236
- if (obj === null || obj === undefined) {
237
- return obj;
238
- }
239
- // Handle arrays - recursively normalize each element
240
- if (Array.isArray(obj)) {
241
- return obj.map((item) => normalizeJsonObject(item));
242
- }
243
- // Handle objects
244
- if (typeof obj === 'object') {
245
- const normalized = {};
246
- for (const [key, value] of Object.entries(obj)) {
247
- // Trim the key to remove leading/trailing spaces
248
- const trimmedKey = key.trim();
249
- // Recursively normalize the value
250
- let normalizedValue = normalizeJsonObject(value);
251
- // Trim all string values
252
- if (typeof normalizedValue === 'string') {
253
- normalizedValue = normalizedValue.trim();
254
- }
255
- normalized[trimmedKey] = normalizedValue;
256
- }
257
- return normalized;
258
- }
259
- // Handle primitive strings
260
- if (typeof obj === 'string') {
261
- return obj.trim();
262
- }
263
- // Return other primitives as-is
264
- return obj;
265
- }
266
- function preprocessDoubaoBboxJson(input) {
267
- if (input.includes('bbox')) {
268
- // when its values like 940 445 969 490, replace all /\d+\s+\d+/g with /$1,$2/g
269
- while (/\d+\s+\d+/.test(input)) {
270
- input = input.replace(/(\d+)\s+(\d+)/g, '$1,$2');
271
- }
272
- }
273
- return input;
274
- }
275
- /**
276
- * Check if the modelFamily is a UI-TARS variant
277
- * @param modelFamily The model family to check
278
- * @returns true if modelFamily is any UI-TARS variant
279
- */
280
- function isUITars(modelFamily) {
281
- return (modelFamily === 'vlm-ui-tars' ||
282
- modelFamily === 'vlm-ui-tars-doubao' ||
283
- modelFamily === 'vlm-ui-tars-doubao-1.5');
284
- }
@@ -1,50 +0,0 @@
1
- /**
2
- * SKILL.md Frontmatter Parser
3
- *
4
- * Reference: gemini-cli skillLoader.ts (skills/skillLoader.ts L34-110)
5
- * Parses YAML frontmatter from SKILL.md files to extract name, description,
6
- * and allowed-tools. Uses the 'yaml' npm package for robust YAML parsing,
7
- * with a fallback simple parser for malformed YAML (e.g. descriptions with colons).
8
- */
9
- /**
10
- * Regex for extracting frontmatter from markdown files.
11
- * Matches ---\n<yaml content>\n--- at the start of the file.
12
- */
13
- export declare const FRONTMATTER_REGEX: RegExp;
14
- /**
15
- * Parsed frontmatter result.
16
- */
17
- export interface ParsedFrontmatter {
18
- name: string;
19
- description: string;
20
- /** Allowed tools for this skill (from frontmatter 'allowed-tools' field). */
21
- allowedTools?: string[];
22
- /** Output artifact type for Pipeline routing (e.g. 'code_knowledge', 'case_list'). */
23
- outputType?: string;
24
- /** The body content after the closing ---. */
25
- body: string;
26
- }
27
- /**
28
- * Parse frontmatter from a SKILL.md file string.
29
- *
30
- * Returns the name, description, allowedTools from the YAML frontmatter,
31
- * and the body (content after the frontmatter).
32
- *
33
- * @param content The full SKILL.md file content
34
- * @returns Parsed frontmatter and body, or null if no valid frontmatter found
35
- */
36
- export declare function parseSkillFrontmatter(content: string): ParsedFrontmatter | null;
37
- /**
38
- * Parse YAML frontmatter content using the yaml library
39
- * with a fallback to simple key-value parsing.
40
- *
41
- * Reference: gemini-cli skillLoader.ts parseFrontmatter (L41-61)
42
- *
43
- * Uses YAML.parse() (yaml v2 API) instead of the deprecated YAML.load().
44
- */
45
- export declare function parseFrontmatterYaml(yamlContent: string): {
46
- name: string;
47
- description: string;
48
- allowedTools?: string[];
49
- outputType?: string;
50
- } | null;