trace.ai-cli 1.1.0 → 1.1.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.
@@ -1,8 +1,526 @@
1
1
  const fetch = require('node-fetch');
2
2
  const { encryptData, decryptData } = require('../utils/encryption');
3
+ const { getSystemInfo, formatBytes } = require('./systemInfoService');
4
+
5
+ /**
6
+ * Use AI to determine what system information is being requested
7
+ * @param {string} prompt - The user's prompt
8
+ * @param {Object} basicInfo - Basic system information for context
9
+ * @returns {Object} Object containing the determined query
10
+ */
11
+ async function determineSystemInfoQuery(prompt, basicInfo) {
12
+ try {
13
+ // Create a prompt for the AI to analyze the user's query
14
+ const analysisPrompt = `Analyze the user's query: "${prompt}" and determine which system information they need.`;
15
+
16
+ // Use the AI to analyze the query
17
+ const models = ['kimi', 'mvrk', 'gma3'];
18
+
19
+ const modelRequests = models.map(model =>
20
+ fetch('https://traceai.dukeindustries7.workers.dev/', {
21
+ method: 'POST',
22
+ headers: { 'Content-Type': 'application/json' },
23
+ body: encryptData({
24
+ a: model,
25
+ q: analysisPrompt,
26
+ r: [],
27
+ i: [],
28
+ c: JSON.stringify(basicInfo)
29
+ })
30
+ })
31
+ .then(res => res.text())
32
+ .then(text => {
33
+ try {
34
+ return decryptData(text);
35
+ } catch (e) {
36
+ console.error('Error decrypting data:', e.message);
37
+ return { text: null };
38
+ }
39
+ })
40
+ .catch(err => {
41
+ console.error('Error in model request:', err.message);
42
+ return { text: null };
43
+ })
44
+ );
45
+
46
+ const responses = await Promise.all(modelRequests);
47
+ // Ensure we have valid responses and filter out any null or undefined values
48
+ const validResponses = responses.filter(r => r && typeof r === 'object');
49
+ const responseTexts = validResponses
50
+ .filter(r => r.text && typeof r.text === 'string') // Ensure text exists and is a string
51
+ .map(r => r.text);
52
+
53
+ // Combine the responses to get the most accurate determination
54
+ let categories = new Set();
55
+
56
+ // Check if we have any valid responses
57
+ if (responseTexts && responseTexts.length > 0) {
58
+ for (const text of responseTexts) {
59
+ if (text && typeof text === 'string') {
60
+ const words = text.toLowerCase().trim().split(/\s+/);
61
+ for (const word of words) {
62
+ if (word && ['basic', 'cpu', 'memory', 'disk', 'network', 'process', 'environment', 'all'].includes(word)) {
63
+ categories.add(word);
64
+ }
65
+ }
66
+ }
67
+ }
68
+ } else {
69
+ // No valid responses, default to basic
70
+ console.log('No valid AI responses for system info query, defaulting to basic');
71
+ categories.add('basic');
72
+ }
73
+
74
+ // If 'all' is included, just return that
75
+ if (categories.has('all')) {
76
+ return { query: 'all' };
77
+ }
78
+
79
+ // If no categories were determined, default to basic
80
+ if (categories.size === 0) {
81
+ categories.add('basic');
82
+ }
83
+
84
+ // Convert the set to a space-separated string
85
+ const query = Array.from(categories).join(' ');
86
+
87
+ return { query };
88
+ } catch (error) {
89
+ console.error('❌ Error determining system info query:', error.message);
90
+ // Default to basic info if there's an error
91
+ return { query: 'basic' };
92
+ }
93
+ }
94
+
95
+ /**
96
+ * Check if a prompt is related to system information
97
+ * @param {string} prompt - The user's prompt
98
+ * @returns {boolean} True if the prompt is related to system information
99
+ */
100
+ function isSystemInfoQuery(prompt) {
101
+ // Always return true for /system commands - we'll let the AI determine relevance
102
+ return true;
103
+ }
104
+
105
+ /**
106
+ * Format system information into a readable response
107
+ * @param {Object} sysInfo - System information object
108
+ * @param {string} prompt - The original prompt
109
+ * @returns {string} Formatted response
110
+ */
111
+ function formatSystemInfoResponse(sysInfo, prompt) {
112
+ let response = `Here's the system information you requested:\n\n`;
113
+
114
+ // Check if we have any system information
115
+ const hasInfo = Object.keys(sysInfo).length > 0;
116
+
117
+ if (!hasInfo) {
118
+ response = `I couldn't find specific system information for your query: "${prompt}"\n\n`;
119
+ response += `You can ask about:\n`;
120
+ response += `- Basic system information (platform, architecture, hostname, manufacturer, model)\n`;
121
+ response += `- CPU information (model, cores, speed, load, temperature, manufacturer)\n`;
122
+ response += `- Memory information (total, used, free, active, available, swap)\n`;
123
+ response += `- Disk information (size, used, available, file systems, block devices)\n`;
124
+ response += `- Network information (interfaces, IP addresses, connections, wifi, latency)\n`;
125
+ response += `- Process information (running processes, services, resource usage)\n`;
126
+ response += `- Environment variables (PATH, SHELL, user info, etc.)\n\n`;
127
+ response += `Try queries like:\n`;
128
+ response += `- "What's my IP address?" (network)\n`;
129
+ response += `- "How much disk space do I have?" (disk)\n`;
130
+ response += `- "What's my CPU usage?" (cpu)\n`;
131
+ response += `- "Show me all system information" (all)\n\n`;
132
+ return response;
133
+ }
134
+
135
+ if (sysInfo.basic) {
136
+ const basic = sysInfo.basic;
137
+ response += `📱 **System Overview**\n`;
138
+ response += `- Platform: ${basic.platform} (${basic.type} ${basic.release})\n`;
139
+ response += `- Architecture: ${basic.arch}\n`;
140
+ response += `- Hostname: ${basic.hostname}\n`;
141
+ response += `- Uptime: ${Math.floor(basic.uptime / 3600)} hours ${Math.floor((basic.uptime % 3600) / 60)} minutes\n`;
142
+
143
+ // Add enhanced system information if available
144
+ if (basic.manufacturer) response += `- Manufacturer: ${basic.manufacturer}\n`;
145
+ if (basic.model) response += `- Model: ${basic.model}\n`;
146
+ if (basic.version) response += `- Version: ${basic.version}\n`;
147
+ if (basic.serial) response += `- Serial Number: ${basic.serial}\n`;
148
+ if (basic.uuid) response += `- UUID: ${basic.uuid}\n`;
149
+ if (basic.sku) response += `- SKU: ${basic.sku}\n`;
150
+ if (basic.virtual) response += `- Virtualization: ${basic.virtual ? 'Yes' : 'No'}\n`;
151
+ if (basic.distro) response += `- Distribution: ${basic.distro}\n`;
152
+ if (basic.codename) response += `- Codename: ${basic.codename}\n`;
153
+ if (basic.kernel) response += `- Kernel: ${basic.kernel}\n`;
154
+
155
+ response += `\n`;
156
+ }
157
+
158
+ if (sysInfo.cpu) {
159
+ const cpu = sysInfo.cpu;
160
+ response += `💻 **CPU Information**\n`;
161
+ response += `- Model: ${cpu.model}\n`;
162
+ response += `- Cores: ${cpu.cores}\n`;
163
+ response += `- Speed: ${cpu.speed} MHz\n`;
164
+ response += `- Load Average: ${cpu.loadAvg.map(load => load.toFixed(2)).join(', ')}\n`;
165
+
166
+ // Add enhanced CPU information if available
167
+ if (cpu.manufacturer) response += `- Manufacturer: ${cpu.manufacturer}\n`;
168
+ if (cpu.brand) response += `- Brand: ${cpu.brand}\n`;
169
+ if (cpu.physicalCores) response += `- Physical Cores: ${cpu.physicalCores}\n`;
170
+ if (cpu.processors) response += `- Processors: ${cpu.processors}\n`;
171
+ if (cpu.socket) response += `- Socket: ${cpu.socket}\n`;
172
+ if (cpu.vendor) response += `- Vendor: ${cpu.vendor}\n`;
173
+ if (cpu.family) response += `- Family: ${cpu.family}\n`;
174
+ if (cpu.stepping) response += `- Stepping: ${cpu.stepping}\n`;
175
+ if (cpu.virtualization) response += `- Virtualization: ${cpu.virtualization}\n`;
176
+ if (cpu.cache) {
177
+ response += `- Cache:\n`;
178
+ Object.entries(cpu.cache).forEach(([level, size]) => {
179
+ response += ` - ${level}: ${size}\n`;
180
+ });
181
+ }
182
+ if (cpu.temperature) response += `- Temperature: ${cpu.temperature}°C\n`;
183
+ if (cpu.currentLoad) response += `- Current Load: ${cpu.currentLoad.toFixed(2)}%\n`;
184
+ if (cpu.currentLoadUser) response += `- User Load: ${cpu.currentLoadUser.toFixed(2)}%\n`;
185
+ if (cpu.currentLoadSystem) response += `- System Load: ${cpu.currentLoadSystem.toFixed(2)}%\n`;
186
+
187
+ response += `\n`;
188
+ }
189
+
190
+ if (sysInfo.memory) {
191
+ const memory = sysInfo.memory;
192
+ response += `🧠 **Memory Information**\n`;
193
+ response += `- Total: ${memory.total}\n`;
194
+ response += `- Used: ${memory.used} (${memory.usagePercent})\n`;
195
+ response += `- Free: ${memory.free}\n`;
196
+
197
+ // Add enhanced memory information if available
198
+ if (memory.active) response += `- Active: ${memory.active}\n`;
199
+ if (memory.available) response += `- Available: ${memory.available}\n`;
200
+ if (memory.buffers) response += `- Buffers: ${memory.buffers}\n`;
201
+ if (memory.cached) response += `- Cached: ${memory.cached}\n`;
202
+ if (memory.slab) response += `- Slab: ${memory.slab}\n`;
203
+ if (memory.swapTotal) response += `- Swap Total: ${memory.swapTotal}\n`;
204
+ if (memory.swapUsed) response += `- Swap Used: ${memory.swapUsed}\n`;
205
+ if (memory.swapFree) response += `- Swap Free: ${memory.swapFree}\n`;
206
+
207
+ // Add memory layout information if available
208
+ if (memory.layout && Array.isArray(memory.layout) && memory.layout.length > 0) {
209
+ response += `- Memory Modules:\n`;
210
+ memory.layout.forEach((module, index) => {
211
+ response += ` - Module ${index + 1}:\n`;
212
+ if (module.size) response += ` - Size: ${formatBytes(module.size)}\n`;
213
+ if (module.bank) response += ` - Bank: ${module.bank}\n`;
214
+ if (module.type) response += ` - Type: ${module.type}\n`;
215
+ if (module.clockSpeed) response += ` - Clock Speed: ${module.clockSpeed} MHz\n`;
216
+ if (module.formFactor) response += ` - Form Factor: ${module.formFactor}\n`;
217
+ if (module.manufacturer) response += ` - Manufacturer: ${module.manufacturer}\n`;
218
+ if (module.partNum) response += ` - Part Number: ${module.partNum}\n`;
219
+ if (module.serialNum) response += ` - Serial Number: ${module.serialNum}\n`;
220
+ if (module.voltageConfigured) response += ` - Voltage: ${module.voltageConfigured} V\n`;
221
+ });
222
+ }
223
+
224
+ response += `\n`;
225
+ }
226
+
227
+ if (sysInfo.disk) {
228
+ response += `💾 **Disk Information**\n`;
229
+
230
+ // Handle enhanced disk information
231
+ if (sysInfo.disk.fsSize && Array.isArray(sysInfo.disk.fsSize)) {
232
+ response += `- File Systems:\n`;
233
+ sysInfo.disk.fsSize.forEach(fs => {
234
+ response += ` - ${fs.fs} (${fs.type}):\n`;
235
+ response += ` - Mount: ${fs.mount}\n`;
236
+ response += ` - Size: ${fs.size ? formatBytes(fs.size) : 'N/A'}\n`;
237
+ response += ` - Used: ${fs.used ? formatBytes(fs.used) : 'N/A'} (${fs.use ? fs.use.toFixed(1) + '%' : 'N/A'})\n`;
238
+ response += ` - Available: ${fs.available ? formatBytes(fs.available) : 'N/A'}\n`;
239
+ });
240
+ } else if (Array.isArray(sysInfo.disk)) {
241
+ // Windows format (legacy)
242
+ sysInfo.disk.forEach(disk => {
243
+ response += `- Drive ${disk.drive}:\n`;
244
+ response += ` - Size: ${disk.size}\n`;
245
+ response += ` - Used: ${disk.used} (${disk.usagePercent})\n`;
246
+ response += ` - Free: ${disk.free}\n`;
247
+ });
248
+ } else if (sysInfo.disk.error) {
249
+ response += `- Error retrieving disk information: ${sysInfo.disk.error}\n`;
250
+ } else if (sysInfo.disk.filesystem) {
251
+ // Unix format (legacy)
252
+ response += `- Filesystem: ${sysInfo.disk.filesystem}\n`;
253
+ response += `- Size: ${sysInfo.disk.size}\n`;
254
+ response += `- Used: ${sysInfo.disk.used} (${sysInfo.disk.usagePercent})\n`;
255
+ response += `- Available: ${sysInfo.disk.available}\n`;
256
+ response += `- Mounted on: ${sysInfo.disk.mountedOn}\n`;
257
+ }
258
+
259
+ // Add block devices information if available
260
+ if (sysInfo.disk.blockDevices && Array.isArray(sysInfo.disk.blockDevices)) {
261
+ response += `- Block Devices:\n`;
262
+ sysInfo.disk.blockDevices.forEach(device => {
263
+ response += ` - ${device.name}:\n`;
264
+ if (device.type) response += ` - Type: ${device.type}\n`;
265
+ if (device.size) response += ` - Size: ${formatBytes(device.size)}\n`;
266
+ if (device.physical) response += ` - Physical: ${device.physical}\n`;
267
+ if (device.uuid) response += ` - UUID: ${device.uuid}\n`;
268
+ if (device.label) response += ` - Label: ${device.label}\n`;
269
+ if (device.model) response += ` - Model: ${device.model}\n`;
270
+ if (device.serial) response += ` - Serial: ${device.serial}\n`;
271
+ if (device.removable !== undefined) response += ` - Removable: ${device.removable ? 'Yes' : 'No'}\n`;
272
+ if (device.protocol) response += ` - Protocol: ${device.protocol}\n`;
273
+ });
274
+ }
275
+
276
+ // Add disk layout information if available
277
+ if (sysInfo.disk.diskLayout && Array.isArray(sysInfo.disk.diskLayout)) {
278
+ response += `- Disk Layout:\n`;
279
+ sysInfo.disk.diskLayout.forEach(disk => {
280
+ response += ` - ${disk.device}:\n`;
281
+ if (disk.type) response += ` - Type: ${disk.type}\n`;
282
+ if (disk.name) response += ` - Name: ${disk.name}\n`;
283
+ if (disk.vendor) response += ` - Vendor: ${disk.vendor}\n`;
284
+ if (disk.size) response += ` - Size: ${formatBytes(disk.size)}\n`;
285
+ if (disk.bytesPerSector) response += ` - Bytes Per Sector: ${disk.bytesPerSector}\n`;
286
+ if (disk.totalCylinders) response += ` - Total Cylinders: ${disk.totalCylinders}\n`;
287
+ if (disk.totalHeads) response += ` - Total Heads: ${disk.totalHeads}\n`;
288
+ if (disk.totalSectors) response += ` - Total Sectors: ${disk.totalSectors}\n`;
289
+ if (disk.totalTracks) response += ` - Total Tracks: ${disk.totalTracks}\n`;
290
+ if (disk.tracksPerCylinder) response += ` - Tracks Per Cylinder: ${disk.tracksPerCylinder}\n`;
291
+ if (disk.sectorsPerTrack) response += ` - Sectors Per Track: ${disk.sectorsPerTrack}\n`;
292
+ if (disk.firmwareRevision) response += ` - Firmware Revision: ${disk.firmwareRevision}\n`;
293
+ if (disk.serialNum) response += ` - Serial Number: ${disk.serialNum}\n`;
294
+ if (disk.interfaceType) response += ` - Interface Type: ${disk.interfaceType}\n`;
295
+ });
296
+ }
297
+
298
+ response += `\n`;
299
+ }
300
+
301
+ if (sysInfo.network) {
302
+ response += `🌐 **Network Information**\n`;
303
+
304
+ // Handle enhanced network interfaces information
305
+ if (sysInfo.network.interfaces && Array.isArray(sysInfo.network.interfaces)) {
306
+ response += `- Interfaces:\n`;
307
+ sysInfo.network.interfaces.forEach(iface => {
308
+ if (!iface.internal) { // Only show external interfaces
309
+ response += ` - ${iface.iface}:\n`;
310
+ if (iface.ifaceName) response += ` - Name: ${iface.ifaceName}\n`;
311
+ if (iface.ip4) response += ` - IPv4: ${iface.ip4}\n`;
312
+ if (iface.ip6) response += ` - IPv6: ${iface.ip6}\n`;
313
+ if (iface.mac) response += ` - MAC: ${iface.mac}\n`;
314
+ if (iface.speed) response += ` - Speed: ${iface.speed} Mbps\n`;
315
+ if (iface.type) response += ` - Type: ${iface.type}\n`;
316
+ if (iface.operstate) response += ` - State: ${iface.operstate}\n`;
317
+ if (iface.carrier !== undefined) response += ` - Carrier: ${iface.carrier ? 'Yes' : 'No'}\n`;
318
+ if (iface.mtu) response += ` - MTU: ${iface.mtu}\n`;
319
+ if (iface.dhcp !== undefined) response += ` - DHCP: ${iface.dhcp ? 'Yes' : 'No'}\n`;
320
+ }
321
+ });
322
+ } else if (Array.isArray(sysInfo.network)) {
323
+ // Legacy format
324
+ sysInfo.network.forEach(net => {
325
+ if (!net.internal) { // Only show external interfaces
326
+ response += `- Interface: ${net.interface}\n`;
327
+ response += ` - IP Address: ${net.address}\n`;
328
+ response += ` - Netmask: ${net.netmask}\n`;
329
+ response += ` - MAC: ${net.mac}\n`;
330
+ }
331
+ });
332
+ }
333
+
334
+ // Add network stats if available
335
+ if (sysInfo.network.stats && Array.isArray(sysInfo.network.stats)) {
336
+ response += `- Network Stats:\n`;
337
+ sysInfo.network.stats.forEach(stat => {
338
+ if (!stat.iface.includes('lo')) { // Skip loopback
339
+ response += ` - ${stat.iface}:\n`;
340
+ if (stat.rx_bytes) response += ` - Received: ${formatBytes(stat.rx_bytes)}\n`;
341
+ if (stat.tx_bytes) response += ` - Sent: ${formatBytes(stat.tx_bytes)}\n`;
342
+ if (stat.rx_errors) response += ` - Receive Errors: ${stat.rx_errors}\n`;
343
+ if (stat.tx_errors) response += ` - Send Errors: ${stat.tx_errors}\n`;
344
+ if (stat.rx_dropped) response += ` - Receive Dropped: ${stat.rx_dropped}\n`;
345
+ if (stat.tx_dropped) response += ` - Send Dropped: ${stat.tx_dropped}\n`;
346
+ }
347
+ });
348
+ }
349
+
350
+ // Add connection information if available
351
+ if (sysInfo.network.connections && sysInfo.network.connections.length > 0) {
352
+ const connections = sysInfo.network.connections;
353
+ const totalConnections = connections.length;
354
+ const establishedCount = connections.filter(conn => conn.state === 'ESTABLISHED').length;
355
+ const listeningCount = connections.filter(conn => conn.state === 'LISTEN').length;
356
+
357
+ response += `- Connections:\n`;
358
+ response += ` - Total: ${totalConnections}\n`;
359
+ response += ` - Established: ${establishedCount}\n`;
360
+ response += ` - Listening: ${listeningCount}\n`;
361
+
362
+ // Show top 5 connections
363
+ if (totalConnections > 0) {
364
+ response += ` - Top 5 Connections:\n`;
365
+ connections.slice(0, 5).forEach(conn => {
366
+ response += ` - ${conn.protocol} ${conn.localAddress}:${conn.localPort} -> ${conn.peerAddress}:${conn.peerPort} (${conn.state})\n`;
367
+ });
368
+ }
369
+ }
370
+
371
+ // Add wifi networks if available
372
+ if (sysInfo.network.wifiNetworks && Array.isArray(sysInfo.network.wifiNetworks)) {
373
+ response += `- WiFi Networks:\n`;
374
+ sysInfo.network.wifiNetworks.forEach(network => {
375
+ response += ` - ${network.ssid}:\n`;
376
+ if (network.bssid) response += ` - BSSID: ${network.bssid}\n`;
377
+ if (network.mode) response += ` - Mode: ${network.mode}\n`;
378
+ if (network.channel) response += ` - Channel: ${network.channel}\n`;
379
+ if (network.frequency) response += ` - Frequency: ${network.frequency} MHz\n`;
380
+ if (network.signalLevel) response += ` - Signal Level: ${network.signalLevel} dBm\n`;
381
+ if (network.quality) response += ` - Quality: ${network.quality}/100\n`;
382
+ if (network.security) response += ` - Security: ${network.security.join(', ')}\n`;
383
+ });
384
+ }
385
+
386
+ // Add internet connectivity information if available
387
+ if (sysInfo.network.internetLatency !== undefined) {
388
+ response += `- Internet Connectivity:\n`;
389
+ response += ` - Latency: ${sysInfo.network.internetLatency.toFixed(2)} ms\n`;
390
+ }
391
+
392
+ // Add public IP if available
393
+ if (sysInfo.network.publicIp) {
394
+ response += `- Public IP: ${sysInfo.network.publicIp}\n`;
395
+ }
396
+
397
+ response += `\n`;
398
+ }
399
+
400
+ if (sysInfo.environment) {
401
+ response += `🔧 **Environment Variables**\n`;
402
+
403
+ // Add user information if available
404
+ if (sysInfo.environment.user) {
405
+ const user = sysInfo.environment.user;
406
+ response += `- User Information:\n`;
407
+ if (user.username) response += ` - Username: ${user.username}\n`;
408
+ if (user.uid) response += ` - UID: ${user.uid}\n`;
409
+ if (user.gid) response += ` - GID: ${user.gid}\n`;
410
+ if (user.shell) response += ` - Shell: ${user.shell}\n`;
411
+ if (user.homedir) response += ` - Home Directory: ${user.homedir}\n`;
412
+ }
413
+
414
+ // Add shell history if available
415
+ if (sysInfo.environment.shell && sysInfo.environment.shell.length > 0) {
416
+ response += `- Recent Shell Commands:\n`;
417
+ sysInfo.environment.shell.slice(0, 5).forEach((cmd, index) => {
418
+ response += ` - ${index + 1}: ${cmd}\n`;
419
+ });
420
+ }
421
+
422
+ // Add environment variables
423
+ if (sysInfo.environment.variables) {
424
+ response += `- Environment Variables:\n`;
425
+ for (const [key, value] of Object.entries(sysInfo.environment.variables)) {
426
+ response += ` - ${key}: ${value}\n`;
427
+ }
428
+ } else {
429
+ // Legacy format
430
+ for (const [key, value] of Object.entries(sysInfo.environment)) {
431
+ if (typeof value === 'string') {
432
+ response += `- ${key}: ${value}\n`;
433
+ }
434
+ }
435
+ }
436
+
437
+ response += `\n`;
438
+ }
439
+
440
+ if (sysInfo.process) {
441
+ response += `⚙️ **Process Information**\n`;
442
+
443
+ // Add current process information
444
+ if (sysInfo.process.current) {
445
+ const current = sysInfo.process.current;
446
+ response += `- Current Process:\n`;
447
+ if (current.pid) response += ` - PID: ${current.pid}\n`;
448
+ if (current.ppid) response += ` - Parent PID: ${current.ppid}\n`;
449
+ if (current.name) response += ` - Name: ${current.name}\n`;
450
+ if (current.cpu) response += ` - CPU Usage: ${current.cpu.toFixed(2)}%\n`;
451
+ if (current.memory) response += ` - Memory Usage: ${formatBytes(current.memory)}\n`;
452
+ if (current.started) response += ` - Started: ${new Date(current.started).toLocaleString()}\n`;
453
+ if (current.state) response += ` - State: ${current.state}\n`;
454
+ if (current.path) response += ` - Path: ${current.path}\n`;
455
+ if (current.command) response += ` - Command: ${current.command}\n`;
456
+ if (current.params) response += ` - Parameters: ${current.params.join(' ')}\n`;
457
+ } else {
458
+ // Legacy format
459
+ response += `- PID: ${sysInfo.process.pid}\n`;
460
+ response += `- Node.js Version: ${sysInfo.process.version}\n`;
461
+ response += `- Current Directory: ${sysInfo.process.cwd}\n`;
462
+ response += `- Memory Usage: ${Math.round(sysInfo.process.memoryUsage.rss / (1024 * 1024))} MB\n`;
463
+ }
464
+
465
+ // Add process summary if available
466
+ if (sysInfo.process.summary) {
467
+ const summary = sysInfo.process.summary;
468
+ response += `- Process Summary:\n`;
469
+ if (summary.total) response += ` - Total: ${summary.total}\n`;
470
+ if (summary.running) response += ` - Running: ${summary.running}\n`;
471
+ if (summary.blocked) response += ` - Blocked: ${summary.blocked}\n`;
472
+ if (summary.sleeping) response += ` - Sleeping: ${summary.sleeping}\n`;
473
+ if (summary.unknown) response += ` - Unknown: ${summary.unknown}\n`;
474
+ }
475
+
476
+ // Add top processes if available
477
+ if (sysInfo.process.list && Array.isArray(sysInfo.process.list)) {
478
+ response += `- Top Processes (by CPU):\n`;
479
+ sysInfo.process.list.slice(0, 10).forEach((proc, index) => {
480
+ response += ` - ${index + 1}: ${proc.name} (PID: ${proc.pid})\n`;
481
+ response += ` - CPU: ${proc.cpu.toFixed(2)}%, Memory: ${formatBytes(proc.mem)}\n`;
482
+ });
483
+ }
484
+
485
+ // Add services if available
486
+ if (sysInfo.process.services && Array.isArray(sysInfo.process.services)) {
487
+ response += `- System Services:\n`;
488
+ sysInfo.process.services.slice(0, 10).forEach((service, index) => {
489
+ response += ` - ${index + 1}: ${service.name} (${service.running ? 'Running' : 'Stopped'})\n`;
490
+ if (service.pids && service.pids.length > 0) {
491
+ response += ` - PIDs: ${service.pids.join(', ')}\n`;
492
+ }
493
+ if (service.startmode) response += ` - Start Mode: ${service.startmode}\n`;
494
+ });
495
+ }
496
+
497
+ response += `\n`;
498
+ }
499
+
500
+ return response;
501
+ }
3
502
 
4
503
  async function processWithAI(prompt, context = '') {
5
504
  try {
505
+ // Check if the prompt is related to system information
506
+ if (isSystemInfoQuery(prompt)) {
507
+ try {
508
+ // First get basic system info to provide context
509
+ const basicInfo = await getSystemInfo('basic');
510
+
511
+ // Use AI to determine what system information is being requested
512
+ const aiResponse = await determineSystemInfoQuery(prompt, basicInfo);
513
+
514
+ // Get the specific system information based on AI's determination
515
+ const systemInfo = await getSystemInfo(aiResponse.query);
516
+ return formatSystemInfoResponse(systemInfo, prompt);
517
+ } catch (sysError) {
518
+ console.error('❌ System info error:', sysError.message);
519
+ // If system info fails, fall back to AI processing
520
+ }
521
+ }
522
+
523
+ // Regular AI processing
6
524
  const models = ['kimi', 'mvrk', 'gma3', 'dsv3', 'qw32b', 'ms24b', 'll70b', 'qw3', 'mp4', 'nlm3'];
7
525
 
8
526
  const modelRequests = models.map(model =>
@@ -46,5 +564,8 @@ async function processWithAI(prompt, context = '') {
46
564
  }
47
565
 
48
566
  module.exports = {
49
- processWithAI
567
+ processWithAI,
568
+ determineSystemInfoQuery,
569
+ isSystemInfoQuery,
570
+ formatSystemInfoResponse
50
571
  };