tide-commander 0.52.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (140) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +364 -0
  3. package/dist/assets/characters/Textures/colormap.png +0 -0
  4. package/dist/assets/characters/character-female-a.glb +0 -0
  5. package/dist/assets/characters/character-female-b.glb +0 -0
  6. package/dist/assets/characters/character-female-c.glb +0 -0
  7. package/dist/assets/characters/character-female-d.glb +0 -0
  8. package/dist/assets/characters/character-female-e.glb +0 -0
  9. package/dist/assets/characters/character-female-f.glb +0 -0
  10. package/dist/assets/characters/character-male-a-processed.gltf +11862 -0
  11. package/dist/assets/characters/character-male-a.glb +0 -0
  12. package/dist/assets/characters/character-male-b.glb +0 -0
  13. package/dist/assets/characters/character-male-c.glb +0 -0
  14. package/dist/assets/characters/character-male-d.glb +0 -0
  15. package/dist/assets/characters/character-male-e.glb +0 -0
  16. package/dist/assets/characters/character-male-f.glb +0 -0
  17. package/dist/assets/icons/icon-192.png +0 -0
  18. package/dist/assets/icons/icon-512.png +0 -0
  19. package/dist/assets/landing-Cc0MDBAK.css +1 -0
  20. package/dist/assets/main-BIpLsrUu.css +1 -0
  21. package/dist/assets/main-DMTRw3br.js +276 -0
  22. package/dist/assets/textures/concrete_floor_worn_001_diff_1k.jpg +0 -0
  23. package/dist/assets/textures/logo-blanco.png +0 -0
  24. package/dist/assets/vendor-react-uS-d4TUT.js +17 -0
  25. package/dist/assets/vendor-three-4iQNXcoo.js +3828 -0
  26. package/dist/assets/web-BZdi2lG9.js +1 -0
  27. package/dist/assets/web-yHsOO1Qb.js +1 -0
  28. package/dist/index.html +38 -0
  29. package/dist/manifest.json +39 -0
  30. package/dist/src/packages/landing/index.html +463 -0
  31. package/dist/src/packages/server/app.js +87 -0
  32. package/dist/src/packages/server/auth/index.js +121 -0
  33. package/dist/src/packages/server/claude/backend.js +578 -0
  34. package/dist/src/packages/server/claude/index.js +8 -0
  35. package/dist/src/packages/server/claude/runner/internal-events.js +22 -0
  36. package/dist/src/packages/server/claude/runner/process-lifecycle.js +208 -0
  37. package/dist/src/packages/server/claude/runner/recovery-store.js +72 -0
  38. package/dist/src/packages/server/claude/runner/resource-monitor.js +51 -0
  39. package/dist/src/packages/server/claude/runner/restart-policy.js +69 -0
  40. package/dist/src/packages/server/claude/runner/stdout-pipeline.js +153 -0
  41. package/dist/src/packages/server/claude/runner/watchdog.js +114 -0
  42. package/dist/src/packages/server/claude/runner.js +310 -0
  43. package/dist/src/packages/server/claude/session-loader.js +898 -0
  44. package/dist/src/packages/server/claude/types.js +5 -0
  45. package/dist/src/packages/server/cli.js +113 -0
  46. package/dist/src/packages/server/codex/backend.js +119 -0
  47. package/dist/src/packages/server/codex/index.js +2 -0
  48. package/dist/src/packages/server/codex/json-event-parser.js +612 -0
  49. package/dist/src/packages/server/data/builtin-skills/bitbucket-pr.js +298 -0
  50. package/dist/src/packages/server/data/builtin-skills/full-notifications.js +49 -0
  51. package/dist/src/packages/server/data/builtin-skills/git-captain.js +304 -0
  52. package/dist/src/packages/server/data/builtin-skills/index.js +61 -0
  53. package/dist/src/packages/server/data/builtin-skills/pm2-logs.js +354 -0
  54. package/dist/src/packages/server/data/builtin-skills/send-message-to-agent.js +51 -0
  55. package/dist/src/packages/server/data/builtin-skills/server-logs.js +124 -0
  56. package/dist/src/packages/server/data/builtin-skills/streaming-exec.js +94 -0
  57. package/dist/src/packages/server/data/builtin-skills/types.js +4 -0
  58. package/dist/src/packages/server/data/builtin-skills.js +6 -0
  59. package/dist/src/packages/server/data/index.js +890 -0
  60. package/dist/src/packages/server/data/snapshots.js +371 -0
  61. package/dist/src/packages/server/index.js +96 -0
  62. package/dist/src/packages/server/prompts/tide-commander.js +13 -0
  63. package/dist/src/packages/server/routes/agents.js +406 -0
  64. package/dist/src/packages/server/routes/config.js +347 -0
  65. package/dist/src/packages/server/routes/custom-models.js +170 -0
  66. package/dist/src/packages/server/routes/exec.js +269 -0
  67. package/dist/src/packages/server/routes/files.js +995 -0
  68. package/dist/src/packages/server/routes/index.js +38 -0
  69. package/dist/src/packages/server/routes/notifications.js +81 -0
  70. package/dist/src/packages/server/routes/permissions.js +115 -0
  71. package/dist/src/packages/server/routes/snapshots.js +224 -0
  72. package/dist/src/packages/server/routes/stt.js +99 -0
  73. package/dist/src/packages/server/routes/tts.js +166 -0
  74. package/dist/src/packages/server/routes/voice-assistant.js +310 -0
  75. package/dist/src/packages/server/runtime/claude-runtime-provider.js +10 -0
  76. package/dist/src/packages/server/runtime/codex-runtime-provider.js +11 -0
  77. package/dist/src/packages/server/runtime/index.js +2 -0
  78. package/dist/src/packages/server/runtime/types.js +6 -0
  79. package/dist/src/packages/server/services/agent-lifecycle-service.js +82 -0
  80. package/dist/src/packages/server/services/agent-service.js +410 -0
  81. package/dist/src/packages/server/services/boss-message-service.js +430 -0
  82. package/dist/src/packages/server/services/boss-service.js +553 -0
  83. package/dist/src/packages/server/services/building-service.js +867 -0
  84. package/dist/src/packages/server/services/claude-service.js +5 -0
  85. package/dist/src/packages/server/services/custom-class-service.js +323 -0
  86. package/dist/src/packages/server/services/database-service.js +914 -0
  87. package/dist/src/packages/server/services/docker-service.js +865 -0
  88. package/dist/src/packages/server/services/fileTracker.js +242 -0
  89. package/dist/src/packages/server/services/index.js +21 -0
  90. package/dist/src/packages/server/services/permission-service.js +258 -0
  91. package/dist/src/packages/server/services/pm2-service.js +435 -0
  92. package/dist/src/packages/server/services/runtime-command-execution.js +168 -0
  93. package/dist/src/packages/server/services/runtime-events.js +357 -0
  94. package/dist/src/packages/server/services/runtime-service.js +308 -0
  95. package/dist/src/packages/server/services/runtime-status-sync.js +104 -0
  96. package/dist/src/packages/server/services/runtime-subagents.js +50 -0
  97. package/dist/src/packages/server/services/runtime-watchdog.js +74 -0
  98. package/dist/src/packages/server/services/secrets-service.js +206 -0
  99. package/dist/src/packages/server/services/skill-service.js +508 -0
  100. package/dist/src/packages/server/services/subordinate-context-service.js +223 -0
  101. package/dist/src/packages/server/services/supervisor-claude.js +132 -0
  102. package/dist/src/packages/server/services/supervisor-prompts.js +80 -0
  103. package/dist/src/packages/server/services/supervisor-service.js +659 -0
  104. package/dist/src/packages/server/services/work-plan-service.js +476 -0
  105. package/dist/src/packages/server/setup.js +86 -0
  106. package/dist/src/packages/server/utils/index.js +4 -0
  107. package/dist/src/packages/server/utils/logger.js +302 -0
  108. package/dist/src/packages/server/utils/string.js +39 -0
  109. package/dist/src/packages/server/utils/tool-formatting.js +139 -0
  110. package/dist/src/packages/server/utils/unicode.js +46 -0
  111. package/dist/src/packages/server/websocket/handler.js +290 -0
  112. package/dist/src/packages/server/websocket/handlers/agent-handler.js +515 -0
  113. package/dist/src/packages/server/websocket/handlers/boss-handler.js +116 -0
  114. package/dist/src/packages/server/websocket/handlers/boss-response-handler.js +250 -0
  115. package/dist/src/packages/server/websocket/handlers/building-handler.js +298 -0
  116. package/dist/src/packages/server/websocket/handlers/command-handler.js +217 -0
  117. package/dist/src/packages/server/websocket/handlers/custom-class-handler.js +68 -0
  118. package/dist/src/packages/server/websocket/handlers/database-handler.js +223 -0
  119. package/dist/src/packages/server/websocket/handlers/notification-handler.js +25 -0
  120. package/dist/src/packages/server/websocket/handlers/permission-handler.js +21 -0
  121. package/dist/src/packages/server/websocket/handlers/secrets-handler.js +61 -0
  122. package/dist/src/packages/server/websocket/handlers/skill-handler.js +148 -0
  123. package/dist/src/packages/server/websocket/handlers/supervisor-handler.js +44 -0
  124. package/dist/src/packages/server/websocket/handlers/sync-handler.js +19 -0
  125. package/dist/src/packages/server/websocket/handlers/types.js +4 -0
  126. package/dist/src/packages/server/websocket/listeners/boss-listeners.js +21 -0
  127. package/dist/src/packages/server/websocket/listeners/index.js +32 -0
  128. package/dist/src/packages/server/websocket/listeners/permission-listeners.js +19 -0
  129. package/dist/src/packages/server/websocket/listeners/runtime-listeners.js +196 -0
  130. package/dist/src/packages/server/websocket/listeners/skill-listeners.js +51 -0
  131. package/dist/src/packages/server/websocket/listeners/supervisor-listeners.js +37 -0
  132. package/dist/src/packages/shared/agent-types.js +54 -0
  133. package/dist/src/packages/shared/building-types.js +43 -0
  134. package/dist/src/packages/shared/common-types.js +1 -0
  135. package/dist/src/packages/shared/database-types.js +8 -0
  136. package/dist/src/packages/shared/types/snapshot.js +7 -0
  137. package/dist/src/packages/shared/types.js +12 -0
  138. package/dist/src/packages/shared/websocket-messages.js +1 -0
  139. package/dist/sw.js +37 -0
  140. package/package.json +90 -0
@@ -0,0 +1,5 @@
1
+ /**
2
+ * Compatibility shim.
3
+ * Runtime implementation moved to runtime-service.ts.
4
+ */
5
+ export * from './runtime-service.js';
@@ -0,0 +1,323 @@
1
+ /**
2
+ * Custom Agent Class Service
3
+ * Manages user-defined agent classes with associated default skills
4
+ */
5
+ import { EventEmitter } from 'events';
6
+ import * as fs from 'fs';
7
+ import * as path from 'path';
8
+ import * as os from 'os';
9
+ import { loadCustomAgentClasses, saveCustomAgentClasses } from '../data/index.js';
10
+ import { createLogger, generateSlug } from '../utils/index.js';
11
+ const log = createLogger('CustomClassService');
12
+ // In-memory store
13
+ let customClasses = new Map();
14
+ // Event emitter for broadcasting changes
15
+ export const customClassEvents = new EventEmitter();
16
+ // Directory for storing instruction markdown files
17
+ const INSTRUCTIONS_DIR = path.join(os.homedir(), '.tide-commander', 'class-instructions');
18
+ // Directory for storing custom model files
19
+ const CUSTOM_MODELS_DIR = path.join(os.homedir(), '.tide-commander', 'custom-models');
20
+ /**
21
+ * Ensure the instructions directory exists
22
+ */
23
+ function ensureInstructionsDir() {
24
+ if (!fs.existsSync(INSTRUCTIONS_DIR)) {
25
+ fs.mkdirSync(INSTRUCTIONS_DIR, { recursive: true });
26
+ log.log(`Created instructions directory: ${INSTRUCTIONS_DIR}`);
27
+ }
28
+ }
29
+ /**
30
+ * Ensure the custom models directory exists
31
+ */
32
+ function ensureCustomModelsDir() {
33
+ if (!fs.existsSync(CUSTOM_MODELS_DIR)) {
34
+ fs.mkdirSync(CUSTOM_MODELS_DIR, { recursive: true });
35
+ log.log(`Created custom models directory: ${CUSTOM_MODELS_DIR}`);
36
+ }
37
+ }
38
+ /**
39
+ * Get the file path for a class's custom model
40
+ */
41
+ function getCustomModelFilePath(classId) {
42
+ return path.join(CUSTOM_MODELS_DIR, `${classId}.glb`);
43
+ }
44
+ /**
45
+ * Save a custom model file to disk
46
+ * @param classId The class ID
47
+ * @param modelData Buffer containing the GLB file data
48
+ * @returns The relative path to the saved model
49
+ */
50
+ export function saveCustomModel(classId, modelData) {
51
+ ensureCustomModelsDir();
52
+ const filePath = getCustomModelFilePath(classId);
53
+ fs.writeFileSync(filePath, modelData);
54
+ log.log(`Saved custom model for class ${classId} to ${filePath} (${modelData.length} bytes)`);
55
+ return `${classId}.glb`;
56
+ }
57
+ /**
58
+ * Delete custom model file for a class
59
+ */
60
+ function deleteCustomModelFile(classId) {
61
+ const filePath = getCustomModelFilePath(classId);
62
+ if (fs.existsSync(filePath)) {
63
+ fs.unlinkSync(filePath);
64
+ log.log(`Deleted custom model file for class ${classId}`);
65
+ }
66
+ }
67
+ /**
68
+ * Check if a custom model exists for a class
69
+ */
70
+ export function hasCustomModel(classId) {
71
+ return fs.existsSync(getCustomModelFilePath(classId));
72
+ }
73
+ /**
74
+ * Get the full path to a custom model file
75
+ * Returns undefined if the model doesn't exist
76
+ */
77
+ export function getCustomModelPath(classId) {
78
+ const filePath = getCustomModelFilePath(classId);
79
+ if (fs.existsSync(filePath)) {
80
+ return filePath;
81
+ }
82
+ return undefined;
83
+ }
84
+ /**
85
+ * Get the custom models directory path (for serving files)
86
+ */
87
+ export function getCustomModelsDirectory() {
88
+ ensureCustomModelsDir();
89
+ return CUSTOM_MODELS_DIR;
90
+ }
91
+ /**
92
+ * Get the file path for a class's instruction markdown
93
+ */
94
+ function getInstructionsFilePath(classId) {
95
+ return path.join(INSTRUCTIONS_DIR, `${classId}.md`);
96
+ }
97
+ /**
98
+ * Save instructions to a markdown file on disk
99
+ */
100
+ function saveInstructionsFile(classId, instructions) {
101
+ ensureInstructionsDir();
102
+ const filePath = getInstructionsFilePath(classId);
103
+ if (instructions && instructions.trim()) {
104
+ fs.writeFileSync(filePath, instructions, 'utf-8');
105
+ log.log(`Saved instructions for class ${classId} to ${filePath} (${instructions.length} chars)`);
106
+ }
107
+ else {
108
+ // Remove file if instructions are empty
109
+ if (fs.existsSync(filePath)) {
110
+ fs.unlinkSync(filePath);
111
+ log.log(`Removed instructions file for class ${classId}`);
112
+ }
113
+ }
114
+ }
115
+ /**
116
+ * Delete instructions file for a class
117
+ */
118
+ function deleteInstructionsFile(classId) {
119
+ const filePath = getInstructionsFilePath(classId);
120
+ if (fs.existsSync(filePath)) {
121
+ fs.unlinkSync(filePath);
122
+ log.log(`Deleted instructions file for class ${classId}`);
123
+ }
124
+ }
125
+ /**
126
+ * Initialize the custom class service - load from disk
127
+ */
128
+ export function initCustomClasses() {
129
+ ensureInstructionsDir();
130
+ ensureCustomModelsDir();
131
+ const loaded = loadCustomAgentClasses();
132
+ customClasses = new Map(loaded.map(c => [c.id, c]));
133
+ log.log(`Initialized with ${customClasses.size} custom agent classes`);
134
+ // Sync instructions files with stored data
135
+ for (const customClass of customClasses.values()) {
136
+ if (customClass.instructions) {
137
+ saveInstructionsFile(customClass.id, customClass.instructions);
138
+ }
139
+ }
140
+ }
141
+ /**
142
+ * Persist custom classes to disk
143
+ */
144
+ function persistClasses() {
145
+ saveCustomAgentClasses(Array.from(customClasses.values()));
146
+ }
147
+ /**
148
+ * Get all custom agent classes
149
+ */
150
+ export function getAllCustomClasses() {
151
+ return Array.from(customClasses.values());
152
+ }
153
+ /**
154
+ * Get a custom agent class by ID
155
+ */
156
+ export function getCustomClass(id) {
157
+ return customClasses.get(id);
158
+ }
159
+ /**
160
+ * Create a new custom agent class
161
+ */
162
+ export function createCustomClass(data) {
163
+ const now = Date.now();
164
+ const id = generateSlug(data.name) || `class-${now}`;
165
+ // Ensure unique ID
166
+ let uniqueId = id;
167
+ let counter = 1;
168
+ while (customClasses.has(uniqueId)) {
169
+ uniqueId = `${id}-${counter++}`;
170
+ }
171
+ const customClass = {
172
+ ...data,
173
+ id: uniqueId,
174
+ createdAt: now,
175
+ updatedAt: now,
176
+ };
177
+ customClasses.set(uniqueId, customClass);
178
+ persistClasses();
179
+ // Save instructions to disk as markdown file
180
+ if (customClass.instructions) {
181
+ saveInstructionsFile(uniqueId, customClass.instructions);
182
+ }
183
+ log.log(`Created custom class: ${customClass.name} (${uniqueId})`);
184
+ customClassEvents.emit('created', customClass);
185
+ return customClass;
186
+ }
187
+ /**
188
+ * Update a custom agent class
189
+ */
190
+ export function updateCustomClass(id, updates) {
191
+ const existing = customClasses.get(id);
192
+ if (!existing) {
193
+ log.warn(`Custom class not found: ${id}`);
194
+ return null;
195
+ }
196
+ const updated = {
197
+ ...existing,
198
+ ...updates,
199
+ id, // Prevent ID changes
200
+ createdAt: existing.createdAt, // Preserve creation time
201
+ updatedAt: Date.now(),
202
+ };
203
+ customClasses.set(id, updated);
204
+ persistClasses();
205
+ // Update instructions file on disk
206
+ saveInstructionsFile(id, updated.instructions);
207
+ log.log(`Updated custom class: ${updated.name} (${id})`);
208
+ customClassEvents.emit('updated', updated);
209
+ return updated;
210
+ }
211
+ /**
212
+ * Delete a custom agent class
213
+ */
214
+ export function deleteCustomClass(id) {
215
+ if (!customClasses.has(id)) {
216
+ log.warn(`Custom class not found: ${id}`);
217
+ return false;
218
+ }
219
+ customClasses.delete(id);
220
+ persistClasses();
221
+ // Delete instructions file
222
+ deleteInstructionsFile(id);
223
+ // Delete custom model file if exists
224
+ deleteCustomModelFile(id);
225
+ log.log(`Deleted custom class: ${id}`);
226
+ customClassEvents.emit('deleted', id);
227
+ return true;
228
+ }
229
+ /**
230
+ * Check if a class ID is a custom class
231
+ */
232
+ export function isCustomClass(classId) {
233
+ return customClasses.has(classId);
234
+ }
235
+ /**
236
+ * Get the visual model file for a custom agent class
237
+ * Returns the model file (e.g., 'character-male-a.glb') or undefined if not a custom class
238
+ */
239
+ export function getClassModelFile(classId) {
240
+ const customClass = customClasses.get(classId);
241
+ if (customClass) {
242
+ return customClass.model || 'character-male-a.glb';
243
+ }
244
+ return undefined;
245
+ }
246
+ /**
247
+ * Get class info (works for both custom and built-in)
248
+ */
249
+ export function getClassInfo(classId) {
250
+ const customClass = customClasses.get(classId);
251
+ if (customClass) {
252
+ return {
253
+ icon: customClass.icon,
254
+ color: customClass.color,
255
+ description: customClass.description,
256
+ };
257
+ }
258
+ return null; // Built-in classes handled elsewhere
259
+ }
260
+ /**
261
+ * Get default skill IDs for a custom class
262
+ */
263
+ export function getClassDefaultSkillIds(classId) {
264
+ const customClass = customClasses.get(classId);
265
+ return customClass?.defaultSkillIds || [];
266
+ }
267
+ /**
268
+ * Get instructions (CLAUDE.md content) for a custom class
269
+ * Returns undefined if class doesn't exist or has no instructions
270
+ */
271
+ export function getClassInstructions(classId) {
272
+ const customClass = customClasses.get(classId);
273
+ return customClass?.instructions;
274
+ }
275
+ /**
276
+ * Get the path to the instructions markdown file for a class
277
+ * Returns undefined if class doesn't exist or has no instructions
278
+ */
279
+ export function getClassInstructionsPath(classId) {
280
+ const customClass = customClasses.get(classId);
281
+ if (customClass?.instructions) {
282
+ return getInstructionsFilePath(classId);
283
+ }
284
+ return undefined;
285
+ }
286
+ /**
287
+ * Build a custom agent definition for the --agents flag
288
+ * Returns undefined if class doesn't have instructions
289
+ */
290
+ export function buildCustomAgentConfig(classId) {
291
+ const customClass = customClasses.get(classId);
292
+ if (!customClass?.instructions) {
293
+ return undefined;
294
+ }
295
+ return {
296
+ name: classId,
297
+ definition: {
298
+ description: customClass.description || `Custom agent class: ${customClass.name}`,
299
+ prompt: customClass.instructions,
300
+ },
301
+ };
302
+ }
303
+ // Export as a service object for consistency
304
+ export const customClassService = {
305
+ initCustomClasses,
306
+ getAllCustomClasses,
307
+ getCustomClass,
308
+ createCustomClass,
309
+ updateCustomClass,
310
+ deleteCustomClass,
311
+ isCustomClass,
312
+ getClassModelFile,
313
+ getClassInfo,
314
+ getClassDefaultSkillIds,
315
+ getClassInstructions,
316
+ getClassInstructionsPath,
317
+ buildCustomAgentConfig,
318
+ // Custom model functions
319
+ saveCustomModel,
320
+ hasCustomModel,
321
+ getCustomModelPath,
322
+ getCustomModelsDirectory,
323
+ };