@blackbox_ai/blackbox-cli-core 0.0.9 → 0.8.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 (247) hide show
  1. package/README.md +22 -196
  2. package/dist/index.d.ts +2 -1
  3. package/dist/index.js +2 -1
  4. package/dist/index.js.map +1 -1
  5. package/dist/src/blackbox/blackboxOAuth2.js +17 -1
  6. package/dist/src/blackbox/blackboxOAuth2.js.map +1 -1
  7. package/dist/src/code_assist/oauth2.js +15 -3
  8. package/dist/src/code_assist/oauth2.js.map +1 -1
  9. package/dist/src/config/blackboxModels.d.ts +3 -2
  10. package/dist/src/config/blackboxModels.js +262 -33
  11. package/dist/src/config/blackboxModels.js.map +1 -1
  12. package/dist/src/config/config.d.ts +65 -0
  13. package/dist/src/config/config.js +282 -17
  14. package/dist/src/config/config.js.map +1 -1
  15. package/dist/src/config/models.d.ts +1 -1
  16. package/dist/src/config/models.js +1 -1
  17. package/dist/src/config/models.js.map +1 -1
  18. package/dist/src/config/multiAgentModels.d.ts +63 -0
  19. package/dist/src/config/multiAgentModels.js +194 -0
  20. package/dist/src/config/multiAgentModels.js.map +1 -0
  21. package/dist/src/core/client.js +8 -2
  22. package/dist/src/core/client.js.map +1 -1
  23. package/dist/src/core/contentGenerator.d.ts +1 -0
  24. package/dist/src/core/contentGenerator.js +57 -7
  25. package/dist/src/core/contentGenerator.js.map +1 -1
  26. package/dist/src/core/encryptedClientFactory.d.ts +17 -0
  27. package/dist/src/core/encryptedClientFactory.js +92 -0
  28. package/dist/src/core/encryptedClientFactory.js.map +1 -0
  29. package/dist/src/core/encryptedContentGenerator.d.ts +47 -0
  30. package/dist/src/core/encryptedContentGenerator.js +445 -0
  31. package/dist/src/core/encryptedContentGenerator.js.map +1 -0
  32. package/dist/src/core/encryptedGeminiClient.d.ts +59 -0
  33. package/dist/src/core/encryptedGeminiClient.js +177 -0
  34. package/dist/src/core/encryptedGeminiClient.js.map +1 -0
  35. package/dist/src/core/encryptedGeminiClientBridge.d.ts +107 -0
  36. package/dist/src/core/encryptedGeminiClientBridge.js +808 -0
  37. package/dist/src/core/encryptedGeminiClientBridge.js.map +1 -0
  38. package/dist/src/core/encryptedGeminiClientWrapper.d.ts +129 -0
  39. package/dist/src/core/encryptedGeminiClientWrapper.js +305 -0
  40. package/dist/src/core/encryptedGeminiClientWrapper.js.map +1 -0
  41. package/dist/src/core/encryptedTurn.d.ts +40 -0
  42. package/dist/src/core/encryptedTurn.js +114 -0
  43. package/dist/src/core/encryptedTurn.js.map +1 -0
  44. package/dist/src/core/logger.d.ts +21 -0
  45. package/dist/src/core/logger.js +110 -0
  46. package/dist/src/core/logger.js.map +1 -1
  47. package/dist/src/core/openaiContentGenerator/constants.d.ts +2 -0
  48. package/dist/src/core/openaiContentGenerator/constants.js +2 -0
  49. package/dist/src/core/openaiContentGenerator/constants.js.map +1 -1
  50. package/dist/src/core/openaiContentGenerator/converter.d.ts +16 -1
  51. package/dist/src/core/openaiContentGenerator/converter.js +135 -4
  52. package/dist/src/core/openaiContentGenerator/converter.js.map +1 -1
  53. package/dist/src/core/openaiContentGenerator/pipeline.js +6 -2
  54. package/dist/src/core/openaiContentGenerator/pipeline.js.map +1 -1
  55. package/dist/src/core/openaiContentGenerator/provider/default.js +10 -1
  56. package/dist/src/core/openaiContentGenerator/provider/default.js.map +1 -1
  57. package/dist/src/core/prompts.d.ts +17 -0
  58. package/dist/src/core/prompts.js +347 -19
  59. package/dist/src/core/prompts.js.map +1 -1
  60. package/dist/src/core/tokenLimits.d.ts +1 -0
  61. package/dist/src/core/tokenLimits.js +37 -2
  62. package/dist/src/core/tokenLimits.js.map +1 -1
  63. package/dist/src/core/tokenLimits.test.js +36 -1
  64. package/dist/src/core/tokenLimits.test.js.map +1 -1
  65. package/dist/src/encrypt/attestation.d.ts +5 -0
  66. package/dist/src/encrypt/attestation.js +100 -0
  67. package/dist/src/encrypt/attestation.js.map +1 -0
  68. package/dist/src/encrypt/client.d.ts +14 -0
  69. package/dist/src/encrypt/client.js +132 -0
  70. package/dist/src/encrypt/client.js.map +1 -0
  71. package/dist/src/encrypt/config.d.ts +22 -0
  72. package/dist/src/encrypt/config.js +43 -0
  73. package/dist/src/encrypt/config.js.map +1 -0
  74. package/dist/src/encrypt/crypto-utils.d.ts +57 -0
  75. package/dist/src/encrypt/crypto-utils.js +257 -0
  76. package/dist/src/encrypt/crypto-utils.js.map +1 -0
  77. package/dist/src/encrypt/history-manager.d.ts +43 -0
  78. package/dist/src/encrypt/history-manager.js +164 -0
  79. package/dist/src/encrypt/history-manager.js.map +1 -0
  80. package/dist/src/encrypt/minimax-template.d.ts +73 -0
  81. package/dist/src/encrypt/minimax-template.js +276 -0
  82. package/dist/src/encrypt/minimax-template.js.map +1 -0
  83. package/dist/src/encrypt/sessions.d.ts +17 -0
  84. package/dist/src/encrypt/sessions.js +221 -0
  85. package/dist/src/encrypt/sessions.js.map +1 -0
  86. package/dist/src/encrypt/streaming-client.d.ts +29 -0
  87. package/dist/src/encrypt/streaming-client.js +232 -0
  88. package/dist/src/encrypt/streaming-client.js.map +1 -0
  89. package/dist/src/encrypt/tool-formatter.d.ts +36 -0
  90. package/dist/src/encrypt/tool-formatter.js +353 -0
  91. package/dist/src/encrypt/tool-formatter.js.map +1 -0
  92. package/dist/src/encrypt/tool-parser.d.ts +93 -0
  93. package/dist/src/encrypt/tool-parser.js +567 -0
  94. package/dist/src/encrypt/tool-parser.js.map +1 -0
  95. package/dist/src/encrypt/types.d.ts +81 -0
  96. package/dist/src/encrypt/types.js +2 -0
  97. package/dist/src/encrypt/types.js.map +1 -0
  98. package/dist/src/generated/git-commit.d.ts +3 -3
  99. package/dist/src/generated/git-commit.js +3 -3
  100. package/dist/src/ide/ide-client.js +9 -19
  101. package/dist/src/ide/ide-client.js.map +1 -1
  102. package/dist/src/index.d.ts +15 -0
  103. package/dist/src/index.js +15 -0
  104. package/dist/src/index.js.map +1 -1
  105. package/dist/src/mcp/oauth-provider.js +2 -6
  106. package/dist/src/mcp/oauth-provider.js.map +1 -1
  107. package/dist/src/mcp/oauth-token-storage.d.ts +7 -0
  108. package/dist/src/mcp/oauth-token-storage.js +24 -0
  109. package/dist/src/mcp/oauth-token-storage.js.map +1 -1
  110. package/dist/src/services/EncryptedChatService.d.ts +80 -0
  111. package/dist/src/services/EncryptedChatService.js +202 -0
  112. package/dist/src/services/EncryptedChatService.js.map +1 -0
  113. package/dist/src/services/StatsHistoryService.d.ts +131 -0
  114. package/dist/src/services/StatsHistoryService.js +427 -0
  115. package/dist/src/services/StatsHistoryService.js.map +1 -0
  116. package/dist/src/services/checkpointApiService.d.ts +101 -0
  117. package/dist/src/services/checkpointApiService.js +215 -0
  118. package/dist/src/services/checkpointApiService.js.map +1 -0
  119. package/dist/src/services/environmentSanitization.d.ts +24 -0
  120. package/dist/src/services/environmentSanitization.js +152 -0
  121. package/dist/src/services/environmentSanitization.js.map +1 -0
  122. package/dist/src/telemetry/blackbox-logger/blackbox-logger.d.ts +2 -6
  123. package/dist/src/telemetry/blackbox-logger/blackbox-logger.js +29 -135
  124. package/dist/src/telemetry/blackbox-logger/blackbox-logger.js.map +1 -1
  125. package/dist/src/telemetry/blackbox-logger/blackbox-logger.test.js +1 -1
  126. package/dist/src/telemetry/blackbox-logger/blackbox-logger.test.js.map +1 -1
  127. package/dist/src/telemetry/uiTelemetry.d.ts +8 -0
  128. package/dist/src/telemetry/uiTelemetry.js +17 -0
  129. package/dist/src/telemetry/uiTelemetry.js.map +1 -1
  130. package/dist/src/tools/browser-interactive.d.ts +63 -0
  131. package/dist/src/tools/browser-interactive.js +394 -0
  132. package/dist/src/tools/browser-interactive.js.map +1 -0
  133. package/dist/src/tools/browser_use.d.ts +22 -1
  134. package/dist/src/tools/browser_use.js +403 -23
  135. package/dist/src/tools/browser_use.js.map +1 -1
  136. package/dist/src/tools/data-file-constants.d.ts +17 -0
  137. package/dist/src/tools/data-file-constants.js +30 -0
  138. package/dist/src/tools/data-file-constants.js.map +1 -0
  139. package/dist/src/tools/edit.js +44 -7
  140. package/dist/src/tools/edit.js.map +1 -1
  141. package/dist/src/tools/ls.js +40 -6
  142. package/dist/src/tools/ls.js.map +1 -1
  143. package/dist/src/tools/ls.test.js +4 -4
  144. package/dist/src/tools/ls.test.js.map +1 -1
  145. package/dist/src/tools/mcp-client-manager.d.ts +28 -2
  146. package/dist/src/tools/mcp-client-manager.js +62 -4
  147. package/dist/src/tools/mcp-client-manager.js.map +1 -1
  148. package/dist/src/tools/mcp-client.d.ts +5 -3
  149. package/dist/src/tools/mcp-client.js +39 -11
  150. package/dist/src/tools/mcp-client.js.map +1 -1
  151. package/dist/src/tools/mcp-tool.d.ts +3 -1
  152. package/dist/src/tools/mcp-tool.js +37 -9
  153. package/dist/src/tools/mcp-tool.js.map +1 -1
  154. package/dist/src/tools/memoryTool.d.ts +14 -4
  155. package/dist/src/tools/memoryTool.js +98 -39
  156. package/dist/src/tools/memoryTool.js.map +1 -1
  157. package/dist/src/tools/read-data-file.d.ts +31 -0
  158. package/dist/src/tools/read-data-file.js +469 -0
  159. package/dist/src/tools/read-data-file.js.map +1 -0
  160. package/dist/src/tools/read-file.js +64 -5
  161. package/dist/src/tools/read-file.js.map +1 -1
  162. package/dist/src/tools/read-file.test.js +40 -6
  163. package/dist/src/tools/read-file.test.js.map +1 -1
  164. package/dist/src/tools/shell.d.ts +3 -1
  165. package/dist/src/tools/shell.js +25 -4
  166. package/dist/src/tools/shell.js.map +1 -1
  167. package/dist/src/tools/skill.d.ts +34 -0
  168. package/dist/src/tools/skill.js +143 -0
  169. package/dist/src/tools/skill.js.map +1 -0
  170. package/dist/src/tools/sql_db.d.ts +101 -0
  171. package/dist/src/tools/sql_db.js +1033 -0
  172. package/dist/src/tools/sql_db.js.map +1 -0
  173. package/dist/src/tools/sql_db_configure.d.ts +18 -0
  174. package/dist/src/tools/sql_db_configure.js +96 -0
  175. package/dist/src/tools/sql_db_configure.js.map +1 -0
  176. package/dist/src/tools/taskCompletion.d.ts +29 -0
  177. package/dist/src/tools/taskCompletion.js +231 -0
  178. package/dist/src/tools/taskCompletion.js.map +1 -0
  179. package/dist/src/tools/tool-error.d.ts +3 -1
  180. package/dist/src/tools/tool-error.js +3 -0
  181. package/dist/src/tools/tool-error.js.map +1 -1
  182. package/dist/src/tools/tool-names.d.ts +8 -0
  183. package/dist/src/tools/tool-names.js +8 -0
  184. package/dist/src/tools/tool-names.js.map +1 -1
  185. package/dist/src/tools/tool-registry.d.ts +22 -0
  186. package/dist/src/tools/tool-registry.js +41 -1
  187. package/dist/src/tools/tool-registry.js.map +1 -1
  188. package/dist/src/tools/tools.d.ts +18 -2
  189. package/dist/src/tools/tools.js +3 -0
  190. package/dist/src/tools/tools.js.map +1 -1
  191. package/dist/src/tools/web-fetch.js +24 -4
  192. package/dist/src/tools/web-fetch.js.map +1 -1
  193. package/dist/src/tools/web-search.js +160 -2
  194. package/dist/src/tools/web-search.js.map +1 -1
  195. package/dist/src/tools/workspace-error-helper.d.ts +9 -0
  196. package/dist/src/tools/workspace-error-helper.js +43 -0
  197. package/dist/src/tools/workspace-error-helper.js.map +1 -0
  198. package/dist/src/tools/workspace-error-helper.test.js +85 -0
  199. package/dist/src/tools/workspace-error-helper.test.js.map +1 -0
  200. package/dist/src/tools/write-file.js +42 -7
  201. package/dist/src/tools/write-file.js.map +1 -1
  202. package/dist/src/utils/environmentContext.js +3 -1
  203. package/dist/src/utils/environmentContext.js.map +1 -1
  204. package/dist/src/utils/environmentContext.test.js +3 -2
  205. package/dist/src/utils/environmentContext.test.js.map +1 -1
  206. package/dist/src/utils/fetch.d.ts +3 -1
  207. package/dist/src/utils/fetch.js +35 -2
  208. package/dist/src/utils/fetch.js.map +1 -1
  209. package/dist/src/utils/fileUtils.js +30 -3
  210. package/dist/src/utils/fileUtils.js.map +1 -1
  211. package/dist/src/utils/filesearch/fileSearch.d.ts +2 -0
  212. package/dist/src/utils/filesearch/fileSearch.js +38 -7
  213. package/dist/src/utils/filesearch/fileSearch.js.map +1 -1
  214. package/dist/src/utils/git-worktree-utils.d.ts +56 -0
  215. package/dist/src/utils/git-worktree-utils.js +176 -0
  216. package/dist/src/utils/git-worktree-utils.js.map +1 -0
  217. package/dist/src/utils/imageCompression.d.ts +34 -0
  218. package/dist/src/utils/imageCompression.js +170 -0
  219. package/dist/src/utils/imageCompression.js.map +1 -0
  220. package/dist/src/utils/messageTruncator.d.ts +51 -0
  221. package/dist/src/utils/messageTruncator.js +346 -0
  222. package/dist/src/utils/messageTruncator.js.map +1 -0
  223. package/dist/src/utils/pathReader.js +26 -6
  224. package/dist/src/utils/pathReader.js.map +1 -1
  225. package/dist/src/utils/skill.d.ts +65 -0
  226. package/dist/src/utils/skill.js +241 -0
  227. package/dist/src/utils/skill.js.map +1 -0
  228. package/dist/src/utils/textCleaning.d.ts +51 -0
  229. package/dist/src/utils/textCleaning.js +327 -0
  230. package/dist/src/utils/textCleaning.js.map +1 -0
  231. package/dist/tsconfig.tsbuildinfo +1 -1
  232. package/package.json +16 -2
  233. package/dist/src/tools/mcp-client-manager.test.js +0 -39
  234. package/dist/src/tools/mcp-client-manager.test.js.map +0 -1
  235. package/dist/src/tools/mcp-client.test.d.ts +0 -6
  236. package/dist/src/tools/mcp-client.test.js +0 -454
  237. package/dist/src/tools/mcp-client.test.js.map +0 -1
  238. package/dist/src/tools/mcp-tool.test.d.ts +0 -6
  239. package/dist/src/tools/mcp-tool.test.js +0 -576
  240. package/dist/src/tools/mcp-tool.test.js.map +0 -1
  241. package/dist/src/tools/memoryTool.test.d.ts +0 -6
  242. package/dist/src/tools/memoryTool.test.js +0 -420
  243. package/dist/src/tools/memoryTool.test.js.map +0 -1
  244. package/dist/src/tools/tool-registry.test.d.ts +0 -6
  245. package/dist/src/tools/tool-registry.test.js +0 -332
  246. package/dist/src/tools/tool-registry.test.js.map +0 -1
  247. /package/dist/src/tools/{mcp-client-manager.test.d.ts → workspace-error-helper.test.d.ts} +0 -0
@@ -0,0 +1,241 @@
1
+ /**
2
+ * @license
3
+ * Copyright 2025 Google LLC
4
+ * SPDX-License-Identifier: Apache-2.0
5
+ */
6
+ import path from 'node:path';
7
+ import fs from 'node:fs/promises';
8
+ import yaml from 'yaml';
9
+ /**
10
+ * Get the available skills for the current environment.
11
+ * Reads the skills folder in .blackbox folder in the workspace,
12
+ * returns the name and description of the skills by reading SKILL.md file.
13
+ *
14
+ * Directory structure: <workspace>/.blackbox/skills/<skill_name>/SKILL.md
15
+ *
16
+ * Every SKILL.md consists of:
17
+ * - Frontmatter (YAML): Contains name and description fields. These are the only
18
+ * fields that Claude reads to determine when the skill gets used, thus it is
19
+ * very important to be clear and comprehensive in describing what the skill is,
20
+ * and when it should be used.
21
+ * - Body (Markdown): Instructions and guidance for using the skill. Only loaded
22
+ * AFTER the skill triggers (if at all).
23
+ *
24
+ * @param workspaceRoot - The root directory of the workspace
25
+ * @returns A formatted string of available skills for system prompt injection, or undefined if no skills found
26
+ */
27
+ export async function getAvailableSkills(workspaceRoot) {
28
+ try {
29
+ const skillsFolder = path.join(workspaceRoot, '.blackbox', 'skills');
30
+ // Check if skills folder exists
31
+ try {
32
+ await fs.access(skillsFolder);
33
+ }
34
+ catch {
35
+ // Skills folder doesn't exist, return undefined
36
+ return undefined;
37
+ }
38
+ const skillDirs = await fs.readdir(skillsFolder, { withFileTypes: true });
39
+ const skills = [];
40
+ for (const dirent of skillDirs) {
41
+ if (!dirent.isDirectory()) {
42
+ continue;
43
+ }
44
+ const skillName = dirent.name;
45
+ const skillFile = path.join(skillsFolder, skillName, 'SKILL.md');
46
+ try {
47
+ const skillContent = await fs.readFile(skillFile, 'utf8');
48
+ const metadata = extractSkillMetadata(skillContent);
49
+ if (metadata) {
50
+ skills.push({
51
+ skillName,
52
+ filePath: skillFile,
53
+ name: metadata.name || skillName,
54
+ description: metadata.description || '',
55
+ });
56
+ }
57
+ }
58
+ catch (error) {
59
+ // Skip skills with missing or invalid SKILL.md files
60
+ console.debug(`Warning: Could not read skill file for "${skillName}":`, error instanceof Error ? error.message : String(error));
61
+ continue;
62
+ }
63
+ }
64
+ if (skills.length === 0) {
65
+ return undefined;
66
+ }
67
+ // Format skills for system prompt
68
+ return skills
69
+ .map((skill) => `<skill><name>\n${skill.name}\n</name><description>\n${skill.description}\n</description></skill>`)
70
+ .join('\n');
71
+ }
72
+ catch (error) {
73
+ console.error('Error getting available skills:', error);
74
+ return undefined;
75
+ }
76
+ }
77
+ /**
78
+ * Extract YAML frontmatter metadata from a SKILL.md file
79
+ * @param content - The full content of the SKILL.md file
80
+ * @returns The parsed metadata or null if no valid frontmatter found
81
+ */
82
+ export function extractSkillMetadata(content) {
83
+ // Extract YAML frontmatter (content between --- markers at the start)
84
+ if (!content.startsWith('---')) {
85
+ return null;
86
+ }
87
+ const endOfFrontmatter = content.indexOf('---', 3);
88
+ if (endOfFrontmatter === -1) {
89
+ return null;
90
+ }
91
+ const frontmatter = content.slice(3, endOfFrontmatter).trim();
92
+ try {
93
+ const metadata = yaml.parse(frontmatter);
94
+ return {
95
+ name: metadata?.name || '',
96
+ description: metadata?.description || '',
97
+ };
98
+ }
99
+ catch (error) {
100
+ console.warn('Failed to parse YAML frontmatter:', error);
101
+ return null;
102
+ }
103
+ }
104
+ /**
105
+ * Read and return the full content of a skill (without frontmatter)
106
+ * @param workspaceRoot - The root directory of the workspace
107
+ * @param skillName - The name of the skill directory
108
+ * @returns The skill content without YAML frontmatter, or null if not found
109
+ */
110
+ export async function getSkillContent(workspaceRoot, skillName) {
111
+ try {
112
+ const skillDir = path.join(workspaceRoot, '.blackbox', 'skills', skillName);
113
+ const skillFile = path.join(skillDir, 'SKILL.md');
114
+ const fileContent = await fs.readFile(skillFile, 'utf8');
115
+ // Strip YAML frontmatter (content between --- markers at the start)
116
+ let content = fileContent;
117
+ if (fileContent.startsWith('---')) {
118
+ const endOfFrontmatter = fileContent.indexOf('---', 3);
119
+ if (endOfFrontmatter !== -1) {
120
+ content = fileContent.slice(endOfFrontmatter + 3).trim();
121
+ }
122
+ }
123
+ return {
124
+ content,
125
+ baseDir: skillDir,
126
+ };
127
+ }
128
+ catch (_error) {
129
+ return null;
130
+ }
131
+ }
132
+ /**
133
+ * Create a new skill with a template SKILL.md file
134
+ * @param workspaceRoot - The root directory of the workspace
135
+ * @param skillName - The name of the skill to create
136
+ * @returns Success status and error message if failed
137
+ */
138
+ export async function createSkill(workspaceRoot, skillName) {
139
+ // Validate skill name format (lowercase letters, numbers, and hyphens only)
140
+ const validSkillName = /^[a-z0-9-]+$/;
141
+ if (!validSkillName.test(skillName)) {
142
+ return {
143
+ success: false,
144
+ error: 'Skill names may only include lowercase letters, numbers, and hyphens.',
145
+ };
146
+ }
147
+ try {
148
+ const skillDir = path.join(workspaceRoot, '.blackbox', 'skills', skillName);
149
+ const skillFile = path.join(skillDir, 'SKILL.md');
150
+ // Check if skill already exists
151
+ try {
152
+ await fs.access(skillFile);
153
+ return {
154
+ success: false,
155
+ error: `A skill named "${skillName}" already exists.`,
156
+ };
157
+ }
158
+ catch {
159
+ // Skill doesn't exist, proceed with creation
160
+ }
161
+ // Create the skill directory
162
+ await fs.mkdir(skillDir, { recursive: true });
163
+ // Create SKILL.md with template content
164
+ const skillTemplate = `---
165
+ name: ${skillName}
166
+ description: Brief description of what this skill does and when to use it
167
+ ---
168
+
169
+ # ${skillName.split('-').map((word) => word.charAt(0).toUpperCase() + word.slice(1)).join(' ')}
170
+
171
+ ## Instructions
172
+
173
+ Provide clear, step-by-step guidance for Blackbox agents on how to use this skill effectively.
174
+
175
+ ## Examples
176
+
177
+ Show concrete examples of using this skill in different scenarios.
178
+
179
+ ## Best Practices
180
+
181
+ Document important guidelines, conventions, and best practices for this skill.
182
+ `;
183
+ await fs.writeFile(skillFile, skillTemplate, 'utf8');
184
+ return {
185
+ success: true,
186
+ skillPath: skillFile,
187
+ };
188
+ }
189
+ catch (error) {
190
+ return {
191
+ success: false,
192
+ error: error instanceof Error ? error.message : 'Failed to create skill.',
193
+ };
194
+ }
195
+ }
196
+ /**
197
+ * List all available skills in the workspace
198
+ * @param workspaceRoot - The root directory of the workspace
199
+ * @returns Array of skill information
200
+ */
201
+ export async function listSkills(workspaceRoot) {
202
+ try {
203
+ const skillsFolder = path.join(workspaceRoot, '.blackbox', 'skills');
204
+ // Check if skills folder exists
205
+ try {
206
+ await fs.access(skillsFolder);
207
+ }
208
+ catch {
209
+ return [];
210
+ }
211
+ const skillDirs = await fs.readdir(skillsFolder, { withFileTypes: true });
212
+ const skills = [];
213
+ for (const dirent of skillDirs) {
214
+ if (!dirent.isDirectory()) {
215
+ continue;
216
+ }
217
+ const skillName = dirent.name;
218
+ const skillFile = path.join(skillsFolder, skillName, 'SKILL.md');
219
+ try {
220
+ const skillContent = await fs.readFile(skillFile, 'utf8');
221
+ const metadata = extractSkillMetadata(skillContent);
222
+ skills.push({
223
+ skillName,
224
+ filePath: skillFile,
225
+ name: metadata?.name || skillName,
226
+ description: metadata?.description || 'No description available',
227
+ });
228
+ }
229
+ catch {
230
+ // Skip skills with missing or invalid SKILL.md files
231
+ continue;
232
+ }
233
+ }
234
+ return skills;
235
+ }
236
+ catch (error) {
237
+ console.error('Error listing skills:', error);
238
+ return [];
239
+ }
240
+ }
241
+ //# sourceMappingURL=skill.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"skill.js","sourceRoot":"","sources":["../../../src/utils/skill.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,51 @@
1
+ /**
2
+ * @license
3
+ * Copyright 2025 Google LLC
4
+ * SPDX-License-Identifier: Apache-2.0
5
+ */
6
+ /**
7
+ * Consolidated text cleaning utilities for encrypted content processing
8
+ * This module provides consistent newline and whitespace handling across all encrypted model processing
9
+ */
10
+ export interface TextCleaningOptions {
11
+ /** Enable debug logging for text transformations */
12
+ debug?: boolean;
13
+ /** Preserve intentional paragraph breaks (double newlines) */
14
+ preserveParagraphs?: boolean;
15
+ /** Maximum consecutive newlines to allow */
16
+ maxConsecutiveNewlines?: number;
17
+ /** Remove all leading/trailing whitespace */
18
+ trimEnds?: boolean;
19
+ }
20
+ export interface CleaningResult {
21
+ /** The cleaned text */
22
+ text: string;
23
+ /** Debug information about transformations applied */
24
+ debug?: {
25
+ originalLength: number;
26
+ finalLength: number;
27
+ transformations: string[];
28
+ };
29
+ }
30
+ /**
31
+ * Remove tool call markup from text for all supported model types
32
+ * This is the primary function for cleaning tool calls from encrypted model responses
33
+ */
34
+ export declare function removeToolCallMarkup(text: string, modelType?: string, options?: TextCleaningOptions): CleaningResult;
35
+ /**
36
+ * Clean text content for streaming responses
37
+ * This is optimized for real-time streaming where we want to be conservative
38
+ */
39
+ export declare function cleanStreamingText(text: string, options?: TextCleaningOptions): CleaningResult;
40
+ /**
41
+ * Format think content with special styling
42
+ */
43
+ export declare function formatThinkContent(thinkContent: string, options?: TextCleaningOptions): string;
44
+ /**
45
+ * Detect if text contains tool calls for any supported model type
46
+ */
47
+ export declare function containsToolCalls(text: string): boolean;
48
+ /**
49
+ * Detect model type from text content
50
+ */
51
+ export declare function detectModelType(text: string): string;
@@ -0,0 +1,327 @@
1
+ /**
2
+ * @license
3
+ * Copyright 2025 Google LLC
4
+ * SPDX-License-Identifier: Apache-2.0
5
+ */
6
+ /**
7
+ * Debug logger for text cleaning operations
8
+ */
9
+ class TextCleaningDebugger {
10
+ transformations = [];
11
+ originalText = '';
12
+ enabled = false;
13
+ constructor(enabled = false) {
14
+ this.enabled = enabled;
15
+ }
16
+ setOriginalText(text) {
17
+ this.originalText = text;
18
+ this.transformations = [];
19
+ }
20
+ logTransformation(description, beforeLength, afterLength) {
21
+ if (!this.enabled)
22
+ return;
23
+ const change = afterLength - beforeLength;
24
+ const changeStr = change === 0 ? 'no change' : change > 0 ? `+${change} chars` : `${change} chars`;
25
+ this.transformations.push(`${description}: ${changeStr}`);
26
+ }
27
+ getDebugInfo(finalText) {
28
+ return {
29
+ originalLength: this.originalText.length,
30
+ finalLength: finalText.length,
31
+ transformations: [...this.transformations]
32
+ };
33
+ }
34
+ }
35
+ /**
36
+ * Remove tool call markup from text for all supported model types
37
+ * This is the primary function for cleaning tool calls from encrypted model responses
38
+ */
39
+ export function removeToolCallMarkup(text, modelType = 'minimax', options = {}) {
40
+ const logger = new TextCleaningDebugger(true); // Force debug logging for investigation
41
+ logger.setOriginalText(text);
42
+ let cleanText = text;
43
+ // Step 1: Remove think tags first (they appear in multiple model types)
44
+ const beforeThink = cleanText.length;
45
+ cleanText = cleanText.replace(/<think>[\s\S]*?<\/think>/g, '');
46
+ logger.logTransformation('Remove think tags', beforeThink, cleanText.length);
47
+ // Step 2: Remove model-specific tool call blocks with precise whitespace handling
48
+ switch (modelType.toLowerCase()) {
49
+ case 'minimax':
50
+ cleanText = removeMiniMaxToolCalls(cleanText, logger);
51
+ break;
52
+ case 'deepseek':
53
+ cleanText = removeDeepSeekToolCalls(cleanText, logger);
54
+ break;
55
+ case 'qwen':
56
+ cleanText = removeQwenToolCalls(cleanText, logger);
57
+ break;
58
+ default:
59
+ // Default to minimax format for unknown models
60
+ cleanText = removeMiniMaxToolCalls(cleanText, logger);
61
+ break;
62
+ }
63
+ // Step 3: Remove any remaining orphaned tool markers (cleanup pass)
64
+ cleanText = removeOrphanedToolMarkers(cleanText, logger);
65
+ // Step 4: Apply final whitespace normalization
66
+ cleanText = normalizeWhitespace(cleanText, options, logger);
67
+ const result = {
68
+ text: cleanText
69
+ };
70
+ result.debug = logger.getDebugInfo(cleanText);
71
+ return result;
72
+ }
73
+ /**
74
+ * Remove MiniMax format tool calls with precise whitespace handling
75
+ */
76
+ function removeMiniMaxToolCalls(text, logger) {
77
+ let cleanText = text;
78
+ const beforeMiniMax = cleanText.length;
79
+ // Check for tool call patterns and log what we find
80
+ const hasMinimaxToolCall = cleanText.includes('<minimax:tool_call>');
81
+ const hasInvoke = cleanText.includes('<invoke');
82
+ // CRITICAL FIX: Be more conservative - only remove if we actually find tool call blocks
83
+ // Check if there are actual minimax tool call blocks before removing
84
+ if (hasMinimaxToolCall) {
85
+ cleanText = cleanText.replace(/<minimax:tool_call>[\s\S]*?<\/minimax:tool_call>/g, '');
86
+ }
87
+ // Only remove invoke blocks if they exist
88
+ if (hasInvoke) {
89
+ // Log all invoke patterns found before removal
90
+ cleanText = cleanText.replace(/<invoke\s+name="[^"]*">[\s\S]*?<\/invoke>/g, '');
91
+ }
92
+ // Very conservative whitespace cleanup - only collapse excessive newlines
93
+ cleanText = cleanText.replace(/\n\s*\n\s*\n\s*\n+/g, '\n\n'); // Only collapse 4+ newlines to 2
94
+ logger.logTransformation('Remove MiniMax tool call blocks', beforeMiniMax, cleanText.length);
95
+ return cleanText;
96
+ }
97
+ /**
98
+ * Remove DeepSeek format tool calls with precise whitespace handling
99
+ */
100
+ function removeDeepSeekToolCalls(text, logger) {
101
+ let cleanText = text;
102
+ // Remove DeepSeek format tool calls - full block format
103
+ const beforeDeepSeek = cleanText.length;
104
+ cleanText = cleanText.replace(/(\n\s*)?<|tool▁calls▁begin|>[\s\S]*?<|tool▁calls▁end|>(\s*\n)?/g, (match, before, after) => {
105
+ if (before && after)
106
+ return '\n';
107
+ if (before || after)
108
+ return before || after;
109
+ return '';
110
+ });
111
+ // Remove individual DeepSeek tool calls
112
+ cleanText = cleanText.replace(/(\n\s*)?<|tool▁call▁begin|>[a-zA-Z_][a-zA-Z0-9_]*<|tool▁sep|>[\s\S]*?<|tool▁call▁end|>(\s*\n)?/g, (match, before, after) => {
113
+ if (before && after)
114
+ return '\n';
115
+ if (before || after)
116
+ return before || after;
117
+ return '';
118
+ });
119
+ // Handle DeepSeek format without begin tokens (incomplete format)
120
+ cleanText = cleanText.replace(/(\n\s*)?[a-zA-Z_][a-zA-Z0-9_]*<|tool▁sep|>[\s\S]*?<|tool▁call▁end|><|tool▁calls▁end|>(\s*\n)?/g, (match, before, after) => {
121
+ if (before && after)
122
+ return '\n';
123
+ if (before || after)
124
+ return before || after;
125
+ return '';
126
+ });
127
+ logger.logTransformation('Remove DeepSeek tool call blocks', beforeDeepSeek, cleanText.length);
128
+ return cleanText;
129
+ }
130
+ /**
131
+ * Remove Qwen format tool calls with precise whitespace handling
132
+ */
133
+ function removeQwenToolCalls(text, logger) {
134
+ let cleanText = text;
135
+ const beforeQwen = cleanText.length;
136
+ cleanText = cleanText.replace(/(\n\s*)?<tool_call>[\s\S]*?<\/tool_call>(\s*\n)?/g, (match, before, after) => {
137
+ if (before && after)
138
+ return '\n';
139
+ if (before || after)
140
+ return before || after;
141
+ return '';
142
+ });
143
+ logger.logTransformation('Remove Qwen tool call blocks', beforeQwen, cleanText.length);
144
+ return cleanText;
145
+ }
146
+ /**
147
+ * Remove any orphaned tool markers that might remain after block removal
148
+ */
149
+ function removeOrphanedToolMarkers(text, logger) {
150
+ let cleanText = text;
151
+ const beforeOrphans = cleanText.length;
152
+ // Remove standalone end tokens that might appear at the end of responses
153
+ cleanText = cleanText.replace(/<|tool▁calls▁end|>\s*$/g, '');
154
+ cleanText = cleanText.replace(/<|tool▁call▁end|>\s*$/g, '');
155
+ cleanText = cleanText.replace(/<\/minimax:tool_call>\s*$/g, '');
156
+ cleanText = cleanText.replace(/<\/tool_call>\s*$/g, '');
157
+ // Remove pipe-delimited tool calls first
158
+ const beforePipe = cleanText.length;
159
+ // Remove pipe-delimited tool calls: <|tool_name|>content<|tool_name|> or <|tool_name|>content (without closing)
160
+ cleanText = cleanText.replace(/<\|(read_file|glob|search_files|list_files|create_file|edit_file|execute_command|browser_action|ask_followup_question|attempt_completion|new_task|retrieve_knowledge)\|>[\s\S]*?(?:<\|\1\||$)/g, '');
161
+ // Remove pipe-delimited parameter tags: <|parameter_name="value">
162
+ cleanText = cleanText.replace(/<\|\w+="[^"]*"/g, '');
163
+ // Remove bare tool calls (tool tags without wrapper)
164
+ // Remove self-closing bare tool calls: <tool_name param="value" />
165
+ cleanText = cleanText.replace(/<(read_file|glob|search_files|list_files|create_file|edit_file|execute_command|browser_action|ask_followup_question|attempt_completion|new_task|retrieve_knowledge)\s[^>]*\s*\/>/g, '');
166
+ // Remove opening/closing bare tool calls: <tool_name>content</tool_name> or <tool_name param="value">content</tool_name>
167
+ cleanText = cleanText.replace(/<(read_file|glob|search_files|list_files|create_file|edit_file|execute_command|browser_action|ask_followup_question|attempt_completion|new_task|retrieve_knowledge)([^>]*?)>[\s\S]*?<\/\1>/g, '');
168
+ logger.logTransformation('Remove pipe-delimited and bare tool calls', beforePipe, cleanText.length);
169
+ // Remove any remaining individual tool markers
170
+ const markers = [
171
+ /<minimax:tool_call>/g,
172
+ /<\/minimax:tool_call>/g,
173
+ /<invoke[^>]*>/g,
174
+ /<\/invoke>/g,
175
+ /<parameter[^>]*>/g,
176
+ /<\/parameter>/g,
177
+ /<|tool▁call▁begin|>/g,
178
+ /<|tool▁call▁end|>/g,
179
+ /<|tool▁sep|>/g,
180
+ /<|tool▁calls▁begin|>/g,
181
+ /<|tool▁calls▁end|>/g,
182
+ /<tool_call>/g,
183
+ /<\/tool_call>/g,
184
+ // Pipe-delimited markers
185
+ /<\|[^|]+\|>/g
186
+ ];
187
+ for (const marker of markers) {
188
+ cleanText = cleanText.replace(marker, '');
189
+ }
190
+ logger.logTransformation('Remove orphaned tool markers', beforeOrphans, cleanText.length);
191
+ return cleanText;
192
+ }
193
+ /**
194
+ * Normalize whitespace and newlines in text
195
+ */
196
+ function normalizeWhitespace(text, options, logger) {
197
+ let cleanText = text;
198
+ const beforeNormalization = cleanText.length;
199
+ // Step 1: Remove trailing whitespace from each line
200
+ cleanText = cleanText.replace(/[ \t]+$/gm, '');
201
+ // Step 2: Handle consecutive newlines based on options
202
+ const maxNewlines = options.maxConsecutiveNewlines ?? 2;
203
+ if (maxNewlines === 1) {
204
+ // Collapse all multiple newlines to single newlines
205
+ cleanText = cleanText.replace(/\n\s*\n/g, '\n');
206
+ }
207
+ else if (maxNewlines === 2) {
208
+ // Collapse 3+ consecutive newlines to 2 (preserve paragraph breaks)
209
+ cleanText = cleanText.replace(/\n\s*\n\s*\n+/g, '\n\n');
210
+ }
211
+ else {
212
+ // Custom limit
213
+ const regex = new RegExp(`\\n(\\s*\\n){${maxNewlines},}`, 'g');
214
+ const replacement = '\n'.repeat(maxNewlines);
215
+ cleanText = cleanText.replace(regex, replacement);
216
+ }
217
+ // Step 3: Remove excessive spaces within lines (more than 4 consecutive spaces to preserve normal spacing)
218
+ cleanText = cleanText.replace(/[ ]{5,}/g, ' ');
219
+ // Step 4: Remove completely empty lines (lines with only whitespace)
220
+ cleanText = cleanText.replace(/^\s*$\n/gm, '');
221
+ // Step 5: Trim ends if requested
222
+ if (options.trimEnds !== false) { // Default to true
223
+ cleanText = cleanText.trim();
224
+ }
225
+ logger.logTransformation('Normalize whitespace', beforeNormalization, cleanText.length);
226
+ return cleanText;
227
+ }
228
+ /**
229
+ * Clean text content for streaming responses
230
+ * This is optimized for real-time streaming where we want to be conservative
231
+ */
232
+ export function cleanStreamingText(text, options = {}) {
233
+ const logger = new TextCleaningDebugger(options.debug);
234
+ logger.setOriginalText(text);
235
+ if (!text || text.trim().length === 0) {
236
+ return { text: '' };
237
+ }
238
+ let cleanText = text;
239
+ const beforeStreaming = cleanText.length;
240
+ cleanText = cleanText.replace(/[ \t]+$/gm, '');
241
+ cleanText = cleanText.replace(/[ ]{12,}/g, ' ');
242
+ cleanText = cleanText.replace(/\n\s*\n\s*\n\s*\n\s*\n\s*\n+/g, '\n\n\n\n\n');
243
+ // Apply maxConsecutiveNewlines if specified
244
+ if (options.maxConsecutiveNewlines !== undefined) {
245
+ const maxNewlines = options.maxConsecutiveNewlines;
246
+ if (maxNewlines === 1) {
247
+ cleanText = cleanText.replace(/\n\s*\n\s*\n+/g, '\n');
248
+ }
249
+ else if (maxNewlines === 2) {
250
+ cleanText = cleanText.replace(/\n\s*\n\s*\n\s*\n+/g, '\n\n');
251
+ }
252
+ }
253
+ // Apply trimEnds if specified
254
+ if (options.trimEnds) {
255
+ cleanText = cleanText.trim();
256
+ }
257
+ logger.logTransformation('Clean streaming text', beforeStreaming, cleanText.length);
258
+ const result = {
259
+ text: cleanText
260
+ };
261
+ if (options.debug) {
262
+ result.debug = logger.getDebugInfo(cleanText);
263
+ }
264
+ return result;
265
+ }
266
+ /**
267
+ * Format think content with special styling
268
+ */
269
+ export function formatThinkContent(thinkContent, options = {}) {
270
+ const cleaned = normalizeWhitespace(thinkContent, options, new TextCleaningDebugger(false));
271
+ if (!cleaned)
272
+ return '';
273
+ // Split content into lines to handle multi-line think content properly
274
+ const lines = cleaned.split('\n');
275
+ // ANSI codes for styling
276
+ const DIM = '\x1b[2m'; // Dim/faint text
277
+ const ITALIC = '\x1b[3m'; // Italic text
278
+ const RESET = '\x1b[0m'; // Reset all formatting
279
+ // Apply styling to each line individually to ensure multi-line content works correctly
280
+ const styledLines = lines.map((line, index) => {
281
+ if (index === 0) {
282
+ // First line gets the emoji and styling
283
+ return `${DIM}${ITALIC}💭 ${line}${RESET}`;
284
+ }
285
+ else {
286
+ // Subsequent lines get styling but no emoji, with proper indentation
287
+ return `${DIM}${ITALIC} ${line}${RESET}`;
288
+ }
289
+ });
290
+ return styledLines.join('\n');
291
+ }
292
+ /**
293
+ * Detect if text contains tool calls for any supported model type
294
+ */
295
+ export function containsToolCalls(text) {
296
+ const patterns = [
297
+ // MiniMax patterns
298
+ /<minimax:tool_call>/,
299
+ /<invoke name=/,
300
+ // DeepSeek patterns
301
+ /<|tool▁calls▁begin|>/,
302
+ /<|tool▁call▁begin|>/,
303
+ /<|tool▁sep|>/,
304
+ // Qwen patterns
305
+ /<tool_call>/,
306
+ // Think patterns (common across models)
307
+ /<think>/
308
+ ];
309
+ return patterns.some(pattern => pattern.test(text));
310
+ }
311
+ /**
312
+ * Detect model type from text content
313
+ */
314
+ export function detectModelType(text) {
315
+ if (text.includes('<minimax:tool_call>') || text.includes('<invoke name=')) {
316
+ return 'minimax';
317
+ }
318
+ if (text.includes('<|tool▁calls▁begin|>') || text.includes('<|tool▁call▁begin|>')) {
319
+ return 'deepseek';
320
+ }
321
+ if (text.includes('<tool_call>')) {
322
+ return 'qwen';
323
+ }
324
+ // Default to minimax
325
+ return 'minimax';
326
+ }
327
+ //# sourceMappingURL=textCleaning.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"textCleaning.js","sourceRoot":"","sources":["../../../src/utils/textCleaning.ts"],"names":[],"mappings":"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"}