@appkit/llamacpp-cli 1.0.0 → 1.1.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 (43) hide show
  1. package/CHANGELOG.md +7 -0
  2. package/README.md +52 -14
  3. package/dist/cli.js +8 -2
  4. package/dist/cli.js.map +1 -1
  5. package/dist/commands/logs.d.ts +4 -0
  6. package/dist/commands/logs.d.ts.map +1 -1
  7. package/dist/commands/logs.js +157 -24
  8. package/dist/commands/logs.js.map +1 -1
  9. package/dist/commands/ps.d.ts.map +1 -1
  10. package/dist/commands/ps.js +11 -1
  11. package/dist/commands/ps.js.map +1 -1
  12. package/dist/commands/start.d.ts +2 -0
  13. package/dist/commands/start.d.ts.map +1 -1
  14. package/dist/commands/start.js +4 -0
  15. package/dist/commands/start.js.map +1 -1
  16. package/dist/lib/config-generator.d.ts +2 -0
  17. package/dist/lib/config-generator.d.ts.map +1 -1
  18. package/dist/lib/config-generator.js +6 -0
  19. package/dist/lib/config-generator.js.map +1 -1
  20. package/dist/lib/launchctl-manager.d.ts.map +1 -1
  21. package/dist/lib/launchctl-manager.js +22 -13
  22. package/dist/lib/launchctl-manager.js.map +1 -1
  23. package/dist/types/server-config.d.ts +2 -0
  24. package/dist/types/server-config.d.ts.map +1 -1
  25. package/dist/types/server-config.js.map +1 -1
  26. package/dist/utils/log-parser.d.ts +37 -0
  27. package/dist/utils/log-parser.d.ts.map +1 -0
  28. package/dist/utils/log-parser.js +164 -0
  29. package/dist/utils/log-parser.js.map +1 -0
  30. package/dist/utils/process-utils.d.ts +6 -0
  31. package/dist/utils/process-utils.d.ts.map +1 -1
  32. package/dist/utils/process-utils.js +35 -0
  33. package/dist/utils/process-utils.js.map +1 -1
  34. package/package.json +1 -1
  35. package/src/cli.ts +8 -2
  36. package/src/commands/logs.ts +133 -26
  37. package/src/commands/ps.ts +13 -2
  38. package/src/commands/start.ts +6 -0
  39. package/src/lib/config-generator.ts +8 -0
  40. package/src/lib/launchctl-manager.ts +22 -13
  41. package/src/types/server-config.ts +2 -0
  42. package/src/utils/log-parser.ts +184 -0
  43. package/src/utils/process-utils.ts +38 -0
@@ -42,6 +42,27 @@ class LaunchctlManager {
42
42
  * Generate plist XML content for a server
43
43
  */
44
44
  generatePlist(config) {
45
+ // Build program arguments array
46
+ const args = [
47
+ '/opt/homebrew/bin/llama-server',
48
+ '--model', config.modelPath,
49
+ '--port', config.port.toString(),
50
+ '--threads', config.threads.toString(),
51
+ '--ctx-size', config.ctxSize.toString(),
52
+ '--gpu-layers', config.gpuLayers.toString(),
53
+ ];
54
+ // Add flags
55
+ if (config.embeddings)
56
+ args.push('--embeddings');
57
+ if (config.jinja)
58
+ args.push('--jinja');
59
+ if (config.logVerbosity !== undefined) {
60
+ args.push('--log-verbosity', config.logVerbosity.toString());
61
+ }
62
+ if (config.logTimestamps)
63
+ args.push('--log-timestamps');
64
+ // Generate XML array elements
65
+ const argsXml = args.map(arg => ` <string>${arg}</string>`).join('\n');
45
66
  return `<?xml version="1.0" encoding="UTF-8"?>
46
67
  <!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN"
47
68
  "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
@@ -52,19 +73,7 @@ class LaunchctlManager {
52
73
 
53
74
  <key>ProgramArguments</key>
54
75
  <array>
55
- <string>/opt/homebrew/bin/llama-server</string>
56
- <string>--model</string>
57
- <string>${config.modelPath}</string>
58
- <string>--port</string>
59
- <string>${config.port}</string>
60
- <string>--threads</string>
61
- <string>${config.threads}</string>
62
- <string>--ctx-size</string>
63
- <string>${config.ctxSize}</string>
64
- <string>--gpu-layers</string>
65
- <string>${config.gpuLayers}</string>
66
- <string>--embeddings</string>
67
- <string>--jinja</string>
76
+ ${argsXml}
68
77
  </array>
69
78
 
70
79
  <key>RunAtLoad</key>
@@ -1 +1 @@
1
- {"version":3,"file":"launchctl-manager.js","sourceRoot":"","sources":["../../src/lib/launchctl-manager.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"launchctl-manager.js","sourceRoot":"","sources":["../../src/lib/launchctl-manager.ts"],"names":[],"mappings":"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"}
@@ -9,6 +9,8 @@ export interface ServerConfig {
9
9
  gpuLayers: number;
10
10
  embeddings: boolean;
11
11
  jinja: boolean;
12
+ logVerbosity?: number;
13
+ logTimestamps: boolean;
12
14
  status: ServerStatus;
13
15
  pid?: number;
14
16
  createdAt: string;
@@ -1 +1 @@
1
- {"version":3,"file":"server-config.d.ts","sourceRoot":"","sources":["../../src/types/server-config.ts"],"names":[],"mappings":"AAAA,MAAM,MAAM,YAAY,GAAG,SAAS,GAAG,SAAS,GAAG,SAAS,CAAC;AAE7D,MAAM,WAAW,YAAY;IAC3B,EAAE,EAAE,MAAM,CAAC;IACX,SAAS,EAAE,MAAM,CAAC;IAClB,SAAS,EAAE,MAAM,CAAC;IAClB,IAAI,EAAE,MAAM,CAAC;IAGb,OAAO,EAAE,MAAM,CAAC;IAChB,OAAO,EAAE,MAAM,CAAC;IAChB,SAAS,EAAE,MAAM,CAAC;IAClB,UAAU,EAAE,OAAO,CAAC;IACpB,KAAK,EAAE,OAAO,CAAC;IAGf,MAAM,EAAE,YAAY,CAAC;IACrB,GAAG,CAAC,EAAE,MAAM,CAAC;IACb,SAAS,EAAE,MAAM,CAAC;IAClB,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,WAAW,CAAC,EAAE,MAAM,CAAC;IAGrB,SAAS,EAAE,MAAM,CAAC;IAClB,KAAK,EAAE,MAAM,CAAC;IAGd,UAAU,EAAE,MAAM,CAAC;IACnB,UAAU,EAAE,MAAM,CAAC;CACpB;AAED;;;GAGG;AACH,wBAAgB,iBAAiB,CAAC,SAAS,EAAE,MAAM,GAAG,MAAM,CAM3D"}
1
+ {"version":3,"file":"server-config.d.ts","sourceRoot":"","sources":["../../src/types/server-config.ts"],"names":[],"mappings":"AAAA,MAAM,MAAM,YAAY,GAAG,SAAS,GAAG,SAAS,GAAG,SAAS,CAAC;AAE7D,MAAM,WAAW,YAAY;IAC3B,EAAE,EAAE,MAAM,CAAC;IACX,SAAS,EAAE,MAAM,CAAC;IAClB,SAAS,EAAE,MAAM,CAAC;IAClB,IAAI,EAAE,MAAM,CAAC;IAGb,OAAO,EAAE,MAAM,CAAC;IAChB,OAAO,EAAE,MAAM,CAAC;IAChB,SAAS,EAAE,MAAM,CAAC;IAClB,UAAU,EAAE,OAAO,CAAC;IACpB,KAAK,EAAE,OAAO,CAAC;IACf,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB,aAAa,EAAE,OAAO,CAAC;IAGvB,MAAM,EAAE,YAAY,CAAC;IACrB,GAAG,CAAC,EAAE,MAAM,CAAC;IACb,SAAS,EAAE,MAAM,CAAC;IAClB,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,WAAW,CAAC,EAAE,MAAM,CAAC;IAGrB,SAAS,EAAE,MAAM,CAAC;IAClB,KAAK,EAAE,MAAM,CAAC;IAGd,UAAU,EAAE,MAAM,CAAC;IACnB,UAAU,EAAE,MAAM,CAAC;CACpB;AAED;;;GAGG;AACH,wBAAgB,iBAAiB,CAAC,SAAS,EAAE,MAAM,GAAG,MAAM,CAM3D"}
@@ -1 +1 @@
1
- {"version":3,"file":"server-config.js","sourceRoot":"","sources":["../../src/types/server-config.ts"],"names":[],"mappings":";;AAmCA,8CAMC;AAVD;;;GAGG;AACH,SAAgB,iBAAiB,CAAC,SAAiB;IACjD,OAAO,SAAS;SACb,OAAO,CAAC,UAAU,EAAE,EAAE,CAAC,CAAW,yBAAyB;SAC3D,OAAO,CAAC,gBAAgB,EAAE,GAAG,CAAC,CAAI,wCAAwC;SAC1E,WAAW,EAAE,CAAsB,YAAY;SAC/C,OAAO,CAAC,UAAU,EAAE,EAAE,CAAC,CAAC,CAAU,yBAAyB;AAChE,CAAC"}
1
+ {"version":3,"file":"server-config.js","sourceRoot":"","sources":["../../src/types/server-config.ts"],"names":[],"mappings":";;AAqCA,8CAMC;AAVD;;;GAGG;AACH,SAAgB,iBAAiB,CAAC,SAAiB;IACjD,OAAO,SAAS;SACb,OAAO,CAAC,UAAU,EAAE,EAAE,CAAC,CAAW,yBAAyB;SAC3D,OAAO,CAAC,gBAAgB,EAAE,GAAG,CAAC,CAAI,wCAAwC;SAC1E,WAAW,EAAE,CAAsB,YAAY;SAC/C,OAAO,CAAC,UAAU,EAAE,EAAE,CAAC,CAAC,CAAU,yBAAyB;AAChE,CAAC"}
@@ -0,0 +1,37 @@
1
+ /**
2
+ * Parse and consolidate verbose llama-server logs into compact single-line format
3
+ */
4
+ export declare class LogParser {
5
+ private buffer;
6
+ private isBuffering;
7
+ /**
8
+ * Process log lines and output compact format
9
+ */
10
+ processLine(line: string, callback: (compactLine: string) => void): void;
11
+ /**
12
+ * Consolidate buffered request/response lines into single line
13
+ */
14
+ private consolidateRequest;
15
+ /**
16
+ * Extract timestamp from log line
17
+ */
18
+ private extractTimestamp;
19
+ /**
20
+ * Extract JSON from log line
21
+ */
22
+ private extractJson;
23
+ /**
24
+ * Extract first user message from request JSON
25
+ */
26
+ private extractUserMessage;
27
+ /**
28
+ * Extract response time from response JSON
29
+ */
30
+ private extractResponseTime;
31
+ /**
32
+ * Format compact log line
33
+ */
34
+ private formatCompactLine;
35
+ }
36
+ export declare const logParser: LogParser;
37
+ //# sourceMappingURL=log-parser.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"log-parser.d.ts","sourceRoot":"","sources":["../../src/utils/log-parser.ts"],"names":[],"mappings":"AAAA;;GAEG;AAcH,qBAAa,SAAS;IACpB,OAAO,CAAC,MAAM,CAAgB;IAC9B,OAAO,CAAC,WAAW,CAAS;IAE5B;;OAEG;IACH,WAAW,CAAC,IAAI,EAAE,MAAM,EAAE,QAAQ,EAAE,CAAC,WAAW,EAAE,MAAM,KAAK,IAAI,GAAG,IAAI;IAwBxE;;OAEG;IACH,OAAO,CAAC,kBAAkB;IAiD1B;;OAEG;IACH,OAAO,CAAC,gBAAgB;IAWxB;;OAEG;IACH,OAAO,CAAC,WAAW;IAYnB;;OAEG;IACH,OAAO,CAAC,kBAAkB;IAU1B;;OAEG;IACH,OAAO,CAAC,mBAAmB;IAoB3B;;OAEG;IACH,OAAO,CAAC,iBAAiB;CAa1B;AAGD,eAAO,MAAM,SAAS,WAAkB,CAAC"}
@@ -0,0 +1,164 @@
1
+ "use strict";
2
+ /**
3
+ * Parse and consolidate verbose llama-server logs into compact single-line format
4
+ */
5
+ Object.defineProperty(exports, "__esModule", { value: true });
6
+ exports.logParser = exports.LogParser = void 0;
7
+ class LogParser {
8
+ constructor() {
9
+ this.buffer = [];
10
+ this.isBuffering = false;
11
+ }
12
+ /**
13
+ * Process log lines and output compact format
14
+ */
15
+ processLine(line, callback) {
16
+ // Check if this is the start of an HTTP request log
17
+ if (line.includes('log_server_r: request: POST')) {
18
+ this.isBuffering = true;
19
+ this.buffer = [line];
20
+ return;
21
+ }
22
+ // If we're buffering, collect lines
23
+ if (this.isBuffering) {
24
+ this.buffer.push(line);
25
+ // Check if we have a complete request (found response line)
26
+ if (line.includes('log_server_r: response:')) {
27
+ const compactLine = this.consolidateRequest(this.buffer);
28
+ if (compactLine) {
29
+ callback(compactLine);
30
+ }
31
+ this.buffer = [];
32
+ this.isBuffering = false;
33
+ }
34
+ }
35
+ }
36
+ /**
37
+ * Consolidate buffered request/response lines into single line
38
+ */
39
+ consolidateRequest(lines) {
40
+ try {
41
+ // Parse first line: timestamp and request info
42
+ const firstLine = lines[0];
43
+ const timestamp = this.extractTimestamp(firstLine);
44
+ const requestMatch = firstLine.match(/request: (POST|GET|PUT|DELETE) (\/[^\s]+) ([^\s]+) (\d+)/);
45
+ if (!requestMatch)
46
+ return null;
47
+ const [, method, endpoint, ip, status] = requestMatch;
48
+ // Parse request JSON (second line)
49
+ const requestLine = lines.find((l) => l.includes('log_server_r: request:') && l.includes('{'));
50
+ if (!requestLine)
51
+ return null;
52
+ const requestJson = this.extractJson(requestLine);
53
+ if (!requestJson)
54
+ return null;
55
+ const userMessage = this.extractUserMessage(requestJson);
56
+ // Parse response JSON (last line)
57
+ const responseLine = lines.find((l) => l.includes('log_server_r: response:'));
58
+ if (!responseLine)
59
+ return null;
60
+ const responseJson = this.extractJson(responseLine);
61
+ if (!responseJson)
62
+ return null;
63
+ const tokensIn = responseJson.usage?.prompt_tokens || 0;
64
+ const tokensOut = responseJson.usage?.completion_tokens || 0;
65
+ // Extract response time from verbose timings
66
+ const responseTimeMs = this.extractResponseTime(responseJson);
67
+ // Format compact line
68
+ return this.formatCompactLine({
69
+ timestamp,
70
+ method,
71
+ endpoint,
72
+ ip,
73
+ status: parseInt(status, 10),
74
+ userMessage,
75
+ tokensIn,
76
+ tokensOut,
77
+ responseTimeMs,
78
+ });
79
+ }
80
+ catch (error) {
81
+ return null;
82
+ }
83
+ }
84
+ /**
85
+ * Extract timestamp from log line
86
+ */
87
+ extractTimestamp(line) {
88
+ // Look for timestamp format like [2025-12-09 10:13:45]
89
+ const match = line.match(/\[(\d{4}-\d{2}-\d{2} \d{2}:\d{2}:\d{2})\]/);
90
+ if (match) {
91
+ return match[1]; // Return as-is: 2025-12-09 10:13:45
92
+ }
93
+ // If no timestamp in logs, use current time in same format
94
+ const now = new Date();
95
+ return now.toISOString().substring(0, 19).replace('T', ' '); // 2025-12-09 10:13:45
96
+ }
97
+ /**
98
+ * Extract JSON from log line
99
+ */
100
+ extractJson(line) {
101
+ const jsonStart = line.indexOf('{');
102
+ if (jsonStart === -1)
103
+ return null;
104
+ try {
105
+ const jsonStr = line.substring(jsonStart);
106
+ return JSON.parse(jsonStr);
107
+ }
108
+ catch {
109
+ return null;
110
+ }
111
+ }
112
+ /**
113
+ * Extract first user message from request JSON
114
+ */
115
+ extractUserMessage(requestJson) {
116
+ const messages = requestJson.messages || [];
117
+ const userMsg = messages.find((m) => m.role === 'user');
118
+ if (!userMsg || !userMsg.content)
119
+ return '';
120
+ // Truncate to first 50 characters
121
+ const content = userMsg.content.replace(/\n/g, ' ').replace(/\s+/g, ' ').trim();
122
+ return content.length > 50 ? content.substring(0, 47) + '...' : content;
123
+ }
124
+ /**
125
+ * Extract response time from response JSON
126
+ */
127
+ extractResponseTime(responseJson) {
128
+ // Check __verbose.timings first (has total time)
129
+ const verboseTimings = responseJson.__verbose?.timings;
130
+ if (verboseTimings) {
131
+ const promptMs = verboseTimings.prompt_ms || 0;
132
+ const predictedMs = verboseTimings.predicted_ms || 0;
133
+ return Math.round(promptMs + predictedMs);
134
+ }
135
+ // Fallback to top-level timings
136
+ const timings = responseJson.timings;
137
+ if (timings) {
138
+ const promptMs = timings.prompt_ms || 0;
139
+ const predictedMs = timings.predicted_ms || 0;
140
+ return Math.round(promptMs + predictedMs);
141
+ }
142
+ return 0;
143
+ }
144
+ /**
145
+ * Format compact log line
146
+ */
147
+ formatCompactLine(entry) {
148
+ return [
149
+ entry.timestamp,
150
+ entry.method,
151
+ entry.endpoint,
152
+ entry.ip,
153
+ entry.status,
154
+ `"${entry.userMessage}"`,
155
+ entry.tokensIn,
156
+ entry.tokensOut,
157
+ entry.responseTimeMs,
158
+ ].join(' ');
159
+ }
160
+ }
161
+ exports.LogParser = LogParser;
162
+ // Export singleton instance
163
+ exports.logParser = new LogParser();
164
+ //# sourceMappingURL=log-parser.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"log-parser.js","sourceRoot":"","sources":["../../src/utils/log-parser.ts"],"names":[],"mappings":"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"}
@@ -24,4 +24,10 @@ export declare function isProcessRunning(pid: number): Promise<boolean>;
24
24
  * Check if a port is in use
25
25
  */
26
26
  export declare function isPortInUse(port: number): Promise<boolean>;
27
+ /**
28
+ * Get memory usage for a process in bytes
29
+ * Uses 'top' on macOS which includes GPU/Metal memory (more accurate for llama-server)
30
+ * Returns null if process not found or error occurs
31
+ */
32
+ export declare function getProcessMemory(pid: number): Promise<number | null>;
27
33
  //# sourceMappingURL=process-utils.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"process-utils.d.ts","sourceRoot":"","sources":["../../src/utils/process-utils.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,IAAI,EAAE,MAAM,eAAe,CAAC;AAGrC,eAAO,MAAM,SAAS,2BAAkB,CAAC;AAEzC;;;GAGG;AACH,wBAAsB,WAAW,CAAC,OAAO,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,CAAC,CAGlE;AAED;;GAEG;AACH,wBAAsB,eAAe,CAAC,OAAO,EAAE,MAAM,GAAG,OAAO,CAAC;IAAE,MAAM,EAAE,MAAM,CAAC;IAAC,MAAM,EAAE,MAAM,CAAA;CAAE,CAAC,CAMlG;AAED;;GAEG;AACH,wBAAsB,aAAa,CAAC,OAAO,EAAE,MAAM,GAAG,OAAO,CAAC,OAAO,CAAC,CAOrE;AAED;;GAEG;AACH,wBAAsB,gBAAgB,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,OAAO,CAAC,CAOpE;AAED;;GAEG;AACH,wBAAsB,WAAW,CAAC,IAAI,EAAE,MAAM,GAAG,OAAO,CAAC,OAAO,CAAC,CAOhE"}
1
+ {"version":3,"file":"process-utils.d.ts","sourceRoot":"","sources":["../../src/utils/process-utils.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,IAAI,EAAE,MAAM,eAAe,CAAC;AAGrC,eAAO,MAAM,SAAS,2BAAkB,CAAC;AAEzC;;;GAGG;AACH,wBAAsB,WAAW,CAAC,OAAO,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,CAAC,CAGlE;AAED;;GAEG;AACH,wBAAsB,eAAe,CAAC,OAAO,EAAE,MAAM,GAAG,OAAO,CAAC;IAAE,MAAM,EAAE,MAAM,CAAC;IAAC,MAAM,EAAE,MAAM,CAAA;CAAE,CAAC,CAMlG;AAED;;GAEG;AACH,wBAAsB,aAAa,CAAC,OAAO,EAAE,MAAM,GAAG,OAAO,CAAC,OAAO,CAAC,CAOrE;AAED;;GAEG;AACH,wBAAsB,gBAAgB,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,OAAO,CAAC,CAOpE;AAED;;GAEG;AACH,wBAAsB,WAAW,CAAC,IAAI,EAAE,MAAM,GAAG,OAAO,CAAC,OAAO,CAAC,CAOhE;AAED;;;;GAIG;AACH,wBAAsB,gBAAgB,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,GAAG,IAAI,CAAC,CA+B1E"}
@@ -6,6 +6,7 @@ exports.execCommandFull = execCommandFull;
6
6
  exports.commandExists = commandExists;
7
7
  exports.isProcessRunning = isProcessRunning;
8
8
  exports.isPortInUse = isPortInUse;
9
+ exports.getProcessMemory = getProcessMemory;
9
10
  const child_process_1 = require("child_process");
10
11
  const util_1 = require("util");
11
12
  exports.execAsync = (0, util_1.promisify)(child_process_1.exec);
@@ -63,4 +64,38 @@ async function isPortInUse(port) {
63
64
  return false;
64
65
  }
65
66
  }
67
+ /**
68
+ * Get memory usage for a process in bytes
69
+ * Uses 'top' on macOS which includes GPU/Metal memory (more accurate for llama-server)
70
+ * Returns null if process not found or error occurs
71
+ */
72
+ async function getProcessMemory(pid) {
73
+ try {
74
+ // Use top with -l 1 (one sample) to get memory stats
75
+ // MEM column shows resident memory including GPU memory on macOS
76
+ const output = await execCommand(`top -l 1 -pid ${pid} -stats mem`);
77
+ // Get the last non-empty line which contains the memory value
78
+ const lines = output.split('\n').filter((line) => line.trim().length > 0);
79
+ if (lines.length === 0)
80
+ return null;
81
+ const memStr = lines[lines.length - 1].trim();
82
+ // Parse memory string (e.g., "10.5G", "512M", "1024K", "10G")
83
+ const match = memStr.match(/^([\d.]+)([KMGT])$/);
84
+ if (!match)
85
+ return null;
86
+ const value = parseFloat(match[1]);
87
+ const unit = match[2];
88
+ // Convert to bytes
89
+ const multipliers = {
90
+ K: 1024,
91
+ M: 1024 * 1024,
92
+ G: 1024 * 1024 * 1024,
93
+ T: 1024 * 1024 * 1024 * 1024,
94
+ };
95
+ return Math.round(value * multipliers[unit]);
96
+ }
97
+ catch {
98
+ return null;
99
+ }
100
+ }
66
101
  //# sourceMappingURL=process-utils.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"process-utils.js","sourceRoot":"","sources":["../../src/utils/process-utils.ts"],"names":[],"mappings":";;;AASA,kCAGC;AAKD,0CAMC;AAKD,sCAOC;AAKD,4CAOC;AAKD,kCAOC;AA3DD,iDAAqC;AACrC,+BAAiC;AAEpB,QAAA,SAAS,GAAG,IAAA,gBAAS,EAAC,oBAAI,CAAC,CAAC;AAEzC;;;GAGG;AACI,KAAK,UAAU,WAAW,CAAC,OAAe;IAC/C,MAAM,EAAE,MAAM,EAAE,GAAG,MAAM,IAAA,iBAAS,EAAC,OAAO,CAAC,CAAC;IAC5C,OAAO,MAAM,CAAC,IAAI,EAAE,CAAC;AACvB,CAAC;AAED;;GAEG;AACI,KAAK,UAAU,eAAe,CAAC,OAAe;IACnD,MAAM,EAAE,MAAM,EAAE,MAAM,EAAE,GAAG,MAAM,IAAA,iBAAS,EAAC,OAAO,CAAC,CAAC;IACpD,OAAO;QACL,MAAM,EAAE,MAAM,CAAC,IAAI,EAAE;QACrB,MAAM,EAAE,MAAM,CAAC,IAAI,EAAE;KACtB,CAAC;AACJ,CAAC;AAED;;GAEG;AACI,KAAK,UAAU,aAAa,CAAC,OAAe;IACjD,IAAI,CAAC;QACH,MAAM,IAAA,iBAAS,EAAC,SAAS,OAAO,EAAE,CAAC,CAAC;QACpC,OAAO,IAAI,CAAC;IACd,CAAC;IAAC,MAAM,CAAC;QACP,OAAO,KAAK,CAAC;IACf,CAAC;AACH,CAAC;AAED;;GAEG;AACI,KAAK,UAAU,gBAAgB,CAAC,GAAW;IAChD,IAAI,CAAC;QACH,MAAM,IAAA,iBAAS,EAAC,SAAS,GAAG,EAAE,CAAC,CAAC;QAChC,OAAO,IAAI,CAAC;IACd,CAAC;IAAC,MAAM,CAAC;QACP,OAAO,KAAK,CAAC;IACf,CAAC;AACH,CAAC;AAED;;GAEG;AACI,KAAK,UAAU,WAAW,CAAC,IAAY;IAC5C,IAAI,CAAC;QACH,MAAM,IAAA,iBAAS,EAAC,cAAc,IAAI,kBAAkB,CAAC,CAAC;QACtD,OAAO,IAAI,CAAC;IACd,CAAC;IAAC,MAAM,CAAC;QACP,OAAO,KAAK,CAAC;IACf,CAAC;AACH,CAAC"}
1
+ {"version":3,"file":"process-utils.js","sourceRoot":"","sources":["../../src/utils/process-utils.ts"],"names":[],"mappings":"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"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@appkit/llamacpp-cli",
3
- "version": "1.0.0",
3
+ "version": "1.1.0",
4
4
  "description": "CLI tool to manage local llama.cpp servers on macOS",
5
5
  "main": "dist/cli.js",
6
6
  "bin": {
package/src/cli.ts CHANGED
@@ -123,6 +123,8 @@ server
123
123
  .option('-t, --threads <number>', 'Thread count (default: auto)', parseInt)
124
124
  .option('-c, --ctx-size <number>', 'Context size (default: auto)', parseInt)
125
125
  .option('-g, --gpu-layers <number>', 'GPU layers (default: 60)', parseInt)
126
+ .option('-v, --log-verbosity <level>', 'Log verbosity: 0=errors, 1=warnings, 2=info (default), 9=debug, omit for all', parseInt)
127
+ .option('--no-log-timestamps', 'Disable timestamps in log messages')
126
128
  .action(async (model: string, options) => {
127
129
  try {
128
130
  await startCommand(model, options);
@@ -177,11 +179,15 @@ server
177
179
  // View logs
178
180
  server
179
181
  .command('logs')
180
- .description('View server logs')
182
+ .description('View server logs (default: compact one-line per request)')
181
183
  .argument('<identifier>', 'Server identifier: port (9000), server ID (llama-3-2-3b), or partial model name')
182
184
  .option('-f, --follow', 'Follow log output in real-time')
183
185
  .option('-n, --lines <number>', 'Number of lines to show (default: 50)', parseInt)
184
- .option('--errors', 'Show stderr instead of stdout')
186
+ .option('--http', 'Show full HTTP JSON request/response logs')
187
+ .option('--errors', 'Show only error messages')
188
+ .option('--verbose', 'Show all messages including debug internals')
189
+ .option('--filter <pattern>', 'Custom grep pattern for filtering')
190
+ .option('--stdout', 'Show stdout instead of stderr (rarely needed)')
185
191
  .action(async (identifier: string, options) => {
186
192
  try {
187
193
  await logsCommand(identifier, options);
@@ -1,13 +1,20 @@
1
1
  import chalk from 'chalk';
2
2
  import { spawn } from 'child_process';
3
+ import * as readline from 'readline';
4
+ import * as fs from 'fs';
3
5
  import { stateManager } from '../lib/state-manager';
4
6
  import { fileExists } from '../utils/file-utils';
5
7
  import { execCommand } from '../utils/process-utils';
8
+ import { logParser } from '../utils/log-parser';
6
9
 
7
10
  interface LogsOptions {
8
11
  follow?: boolean;
9
12
  lines?: number;
10
13
  errors?: boolean;
14
+ verbose?: boolean;
15
+ http?: boolean;
16
+ stdout?: boolean;
17
+ filter?: string;
11
18
  }
12
19
 
13
20
  export async function logsCommand(identifier: string, options: LogsOptions): Promise<void> {
@@ -17,9 +24,9 @@ export async function logsCommand(identifier: string, options: LogsOptions): Pro
17
24
  throw new Error(`Server not found: ${identifier}\n\nUse: llamacpp ps`);
18
25
  }
19
26
 
20
- // Determine log file
21
- const logPath = options.errors ? server.stderrPath : server.stdoutPath;
22
- const logType = options.errors ? 'errors' : 'logs';
27
+ // Determine log file (default to stderr where verbose logs go)
28
+ const logPath = options.stdout ? server.stdoutPath : server.stderrPath;
29
+ const logType = options.stdout ? 'stdout' : 'stderr';
23
30
 
24
31
  // Check if log file exists
25
32
  if (!(await fileExists(logPath))) {
@@ -28,34 +35,134 @@ export async function logsCommand(identifier: string, options: LogsOptions): Pro
28
35
  return;
29
36
  }
30
37
 
31
- console.log(chalk.blue(`📋 ${options.errors ? 'Errors' : 'Logs'} for ${server.modelName}`));
38
+ // Determine filter pattern and mode
39
+ let filterPattern: string | null = null;
40
+ let filterDesc = '';
41
+ let useCompactMode = false;
42
+
43
+ if (options.verbose) {
44
+ // Show everything (no filter)
45
+ filterDesc = ' (all messages)';
46
+ } else if (options.errors) {
47
+ // Show only errors
48
+ filterPattern = 'error|Error|ERROR|failed|Failed|FAILED';
49
+ filterDesc = ' (errors only)';
50
+ } else if (options.http) {
51
+ // Full HTTP JSON logs
52
+ filterPattern = 'log_server_r';
53
+ filterDesc = ' (HTTP JSON)';
54
+ } else if (options.filter) {
55
+ // Custom filter
56
+ filterPattern = options.filter;
57
+ filterDesc = ` (filter: ${options.filter})`;
58
+ } else {
59
+ // Default: Compact one-liner format
60
+ filterPattern = 'log_server_r';
61
+ filterDesc = ' (compact)';
62
+ useCompactMode = true;
63
+ }
64
+
65
+ console.log(chalk.blue(`📋 Logs for ${server.modelName} (${logType}${filterDesc})`));
32
66
  console.log(chalk.dim(` ${logPath}\n`));
33
67
 
34
68
  if (options.follow) {
35
- // Follow logs in real-time
36
- const tail = spawn('tail', ['-f', logPath], {
37
- stdio: 'inherit',
38
- });
39
-
40
- // Handle Ctrl+C gracefully
41
- process.on('SIGINT', () => {
42
- tail.kill();
43
- console.log();
44
- process.exit(0);
45
- });
46
-
47
- // Wait for tail to exit
48
- tail.on('exit', () => {
49
- process.exit(0);
50
- });
69
+ // Follow logs in real-time with optional filtering
70
+ if (useCompactMode) {
71
+ // Compact mode with follow: parse lines in real-time
72
+ const tailProcess = spawn('tail', ['-f', logPath]);
73
+ const rl = readline.createInterface({
74
+ input: tailProcess.stdout,
75
+ crlfDelay: Infinity,
76
+ });
77
+
78
+ rl.on('line', (line) => {
79
+ if (line.includes('log_server_r')) {
80
+ logParser.processLine(line, (compactLine) => {
81
+ console.log(compactLine);
82
+ });
83
+ }
84
+ });
85
+
86
+ // Handle Ctrl+C gracefully
87
+ process.on('SIGINT', () => {
88
+ tailProcess.kill();
89
+ rl.close();
90
+ console.log();
91
+ process.exit(0);
92
+ });
93
+
94
+ tailProcess.on('exit', () => {
95
+ process.exit(0);
96
+ });
97
+ } else if (filterPattern) {
98
+ // Use tail piped to grep for filtering
99
+ const grepProcess = spawn('sh', ['-c', `tail -f "${logPath}" | grep --line-buffered -E "${filterPattern}"`], {
100
+ stdio: 'inherit',
101
+ });
102
+
103
+ // Handle Ctrl+C gracefully
104
+ process.on('SIGINT', () => {
105
+ grepProcess.kill();
106
+ console.log();
107
+ process.exit(0);
108
+ });
109
+
110
+ grepProcess.on('exit', () => {
111
+ process.exit(0);
112
+ });
113
+ } else {
114
+ // No filter, just tail
115
+ const tail = spawn('tail', ['-f', logPath], {
116
+ stdio: 'inherit',
117
+ });
118
+
119
+ process.on('SIGINT', () => {
120
+ tail.kill();
121
+ console.log();
122
+ process.exit(0);
123
+ });
124
+
125
+ tail.on('exit', () => {
126
+ process.exit(0);
127
+ });
128
+ }
51
129
  } else {
52
- // Show last N lines
130
+ // Show last N lines with optional filtering
53
131
  const lines = options.lines || 50;
54
- try {
55
- const output = await execCommand(`tail -n ${lines} "${logPath}"`);
56
- console.log(output);
57
- } catch (error) {
58
- throw new Error(`Failed to read logs: ${(error as Error).message}`);
132
+
133
+ if (useCompactMode) {
134
+ // Compact mode: read file and parse
135
+ try {
136
+ const command = `tail -n ${lines * 3} "${logPath}" | grep -E "log_server_r"`;
137
+ const output = await execCommand(command);
138
+ const logLines = output.split('\n').filter((l) => l.trim());
139
+
140
+ for (const line of logLines) {
141
+ logParser.processLine(line, (compactLine) => {
142
+ console.log(compactLine);
143
+ });
144
+ }
145
+ } catch (error) {
146
+ throw new Error(`Failed to read logs: ${(error as Error).message}`);
147
+ }
148
+ } else {
149
+ // Regular filtering
150
+ try {
151
+ let command: string;
152
+
153
+ if (filterPattern) {
154
+ // Use tail piped to grep
155
+ command = `tail -n ${lines} "${logPath}" | grep -E "${filterPattern}"`;
156
+ } else {
157
+ // No filter
158
+ command = `tail -n ${lines} "${logPath}"`;
159
+ }
160
+
161
+ const output = await execCommand(command);
162
+ console.log(output);
163
+ } catch (error) {
164
+ throw new Error(`Failed to read logs: ${(error as Error).message}`);
165
+ }
59
166
  }
60
167
  }
61
168
  }
@@ -2,7 +2,8 @@ import chalk from 'chalk';
2
2
  import Table from 'cli-table3';
3
3
  import { stateManager } from '../lib/state-manager';
4
4
  import { statusChecker } from '../lib/status-checker';
5
- import { formatUptime } from '../utils/format-utils';
5
+ import { formatUptime, formatBytes } from '../utils/format-utils';
6
+ import { getProcessMemory } from '../utils/process-utils';
6
7
 
7
8
  export async function psCommand(): Promise<void> {
8
9
  const servers = await stateManager.getAllServers();
@@ -18,7 +19,7 @@ export async function psCommand(): Promise<void> {
18
19
  const updated = await statusChecker.updateAllServerStatuses();
19
20
 
20
21
  const table = new Table({
21
- head: ['SERVER ID', 'MODEL', 'PORT', 'STATUS', 'PID', 'UPTIME'],
22
+ head: ['SERVER ID', 'MODEL', 'PORT', 'STATUS', 'PID', 'MEMORY', 'UPTIME'],
22
23
  });
23
24
 
24
25
  let runningCount = 0;
@@ -51,12 +52,22 @@ export async function psCommand(): Promise<void> {
51
52
  ? formatUptime(server.lastStarted)
52
53
  : '-';
53
54
 
55
+ // Get memory usage for running servers
56
+ let memoryText = '-';
57
+ if (server.status === 'running' && server.pid) {
58
+ const memoryBytes = await getProcessMemory(server.pid);
59
+ if (memoryBytes !== null) {
60
+ memoryText = formatBytes(memoryBytes);
61
+ }
62
+ }
63
+
54
64
  table.push([
55
65
  server.id,
56
66
  server.modelName,
57
67
  server.port.toString(),
58
68
  statusColor(statusText),
59
69
  server.pid?.toString() || '-',
70
+ memoryText,
60
71
  uptime,
61
72
  ]);
62
73
  }