orquesta-cli 0.2.75 → 0.2.76
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.
|
@@ -89,6 +89,11 @@ export declare class LLMClient {
|
|
|
89
89
|
latency?: number;
|
|
90
90
|
error?: string;
|
|
91
91
|
}[]>>;
|
|
92
|
+
static healthCheckCurrent(): Promise<{
|
|
93
|
+
healthy: boolean;
|
|
94
|
+
latency?: number;
|
|
95
|
+
error?: string;
|
|
96
|
+
}>;
|
|
92
97
|
static testConnection(baseUrl: string, apiKey: string, model: string): Promise<{
|
|
93
98
|
success: boolean;
|
|
94
99
|
latency?: number;
|
|
@@ -1213,6 +1213,52 @@ export class LLMClient {
|
|
|
1213
1213
|
}
|
|
1214
1214
|
return results;
|
|
1215
1215
|
}
|
|
1216
|
+
static async healthCheckCurrent() {
|
|
1217
|
+
const endpoint = configManager.getCurrentEndpoint();
|
|
1218
|
+
const model = configManager.getCurrentModel();
|
|
1219
|
+
if (!endpoint || !model) {
|
|
1220
|
+
return { healthy: false, error: 'No endpoint/model configured' };
|
|
1221
|
+
}
|
|
1222
|
+
const startTime = Date.now();
|
|
1223
|
+
try {
|
|
1224
|
+
const axiosInstance = axios.create({
|
|
1225
|
+
baseURL: endpoint.baseUrl,
|
|
1226
|
+
headers: {
|
|
1227
|
+
'Content-Type': 'application/json',
|
|
1228
|
+
...(endpoint.apiKey && { Authorization: `Bearer ${endpoint.apiKey}` }),
|
|
1229
|
+
},
|
|
1230
|
+
timeout: 10000,
|
|
1231
|
+
});
|
|
1232
|
+
const response = await axiosInstance.post('/chat/completions', {
|
|
1233
|
+
model: model.id,
|
|
1234
|
+
messages: [{ role: 'user', content: 'ping' }],
|
|
1235
|
+
max_tokens: 1,
|
|
1236
|
+
});
|
|
1237
|
+
const latency = Date.now() - startTime;
|
|
1238
|
+
if (response.status === 200 && response.data.choices?.[0]?.message) {
|
|
1239
|
+
return { healthy: true, latency };
|
|
1240
|
+
}
|
|
1241
|
+
return { healthy: false, latency, error: 'Invalid response' };
|
|
1242
|
+
}
|
|
1243
|
+
catch (error) {
|
|
1244
|
+
const latency = Date.now() - startTime;
|
|
1245
|
+
const axiosError = error;
|
|
1246
|
+
let errorMessage = 'Unknown error';
|
|
1247
|
+
if (axiosError.response) {
|
|
1248
|
+
errorMessage = `HTTP ${axiosError.response.status}`;
|
|
1249
|
+
}
|
|
1250
|
+
else if (axiosError.code === 'ECONNREFUSED') {
|
|
1251
|
+
errorMessage = 'Connection refused';
|
|
1252
|
+
}
|
|
1253
|
+
else if (axiosError.code === 'ETIMEDOUT' || axiosError.code === 'ECONNABORTED') {
|
|
1254
|
+
errorMessage = 'Timeout';
|
|
1255
|
+
}
|
|
1256
|
+
else if (axiosError.request) {
|
|
1257
|
+
errorMessage = 'Network error';
|
|
1258
|
+
}
|
|
1259
|
+
return { healthy: false, latency, error: errorMessage };
|
|
1260
|
+
}
|
|
1261
|
+
}
|
|
1216
1262
|
static async testConnection(baseUrl, apiKey, model) {
|
|
1217
1263
|
const startTime = Date.now();
|
|
1218
1264
|
try {
|
|
@@ -470,30 +470,24 @@ export const PlanExecuteApp = ({ llmClient: initialLlmClient, modelInfo, resumeL
|
|
|
470
470
|
logger.startTimer('app-init');
|
|
471
471
|
try {
|
|
472
472
|
setInitStep('health');
|
|
473
|
-
logger.flow('
|
|
473
|
+
logger.flow('Kicking off background health probe + docs init');
|
|
474
474
|
setHealthStatus('checking');
|
|
475
|
-
|
|
475
|
+
void (async () => {
|
|
476
476
|
if (configManager.hasEndpoints()) {
|
|
477
|
-
const
|
|
478
|
-
|
|
479
|
-
|
|
480
|
-
logger.vars({ name: 'endpointId', value: endpointId }, { name: 'healthyModels', value: modelResults.filter(r => r.healthy).length });
|
|
481
|
-
if (modelResults.some((r) => r.healthy)) {
|
|
482
|
-
hasHealthy = true;
|
|
483
|
-
}
|
|
484
|
-
}
|
|
485
|
-
logger.state('Health status', 'checking', hasHealthy ? 'healthy' : 'unhealthy');
|
|
486
|
-
setHealthStatus(hasHealthy ? 'healthy' : 'unhealthy');
|
|
487
|
-
await configManager.updateAllHealthStatus(healthResults);
|
|
477
|
+
const result = await LLMClient.healthCheckCurrent();
|
|
478
|
+
logger.state('Health status', 'checking', result.healthy ? 'healthy' : 'unhealthy');
|
|
479
|
+
setHealthStatus(result.healthy ? 'healthy' : 'unhealthy');
|
|
488
480
|
}
|
|
489
481
|
else {
|
|
490
482
|
setHealthStatus('unknown');
|
|
491
483
|
}
|
|
492
|
-
})()
|
|
493
|
-
|
|
484
|
+
})().catch((err) => {
|
|
485
|
+
logger.warn('Background health probe failed', { error: err });
|
|
486
|
+
setHealthStatus('unknown');
|
|
487
|
+
});
|
|
488
|
+
await initializeDocsDirectory().catch((err) => {
|
|
494
489
|
logger.warn('Docs directory initialization warning', { error: err });
|
|
495
490
|
});
|
|
496
|
-
await Promise.all([healthPromise, docsPromise]);
|
|
497
491
|
setInitStep('config');
|
|
498
492
|
logger.flow('Checking configuration');
|
|
499
493
|
if (!configManager.hasEndpoints()) {
|