@livedesk/hub 0.1.16 → 0.1.17
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.
package/package.json
CHANGED
|
@@ -94,15 +94,6 @@ export function createAgentManager({
|
|
|
94
94
|
async deleteApiKey() {
|
|
95
95
|
return publicSettings();
|
|
96
96
|
},
|
|
97
|
-
async getModels() {
|
|
98
|
-
return [{
|
|
99
|
-
id: '',
|
|
100
|
-
name: 'Codex default',
|
|
101
|
-
protocol: 'codex-sdk',
|
|
102
|
-
available: true,
|
|
103
|
-
capabilities: { supportsReasoningLevel: true, supportsStreaming: true, supportsTools: true }
|
|
104
|
-
}];
|
|
105
|
-
},
|
|
106
97
|
async testConnection() {
|
|
107
98
|
if (!runtime) throw new AgentProviderError('codex-sdk-not-installed', 'Codex SDK is not installed.', { status: 503 });
|
|
108
99
|
statusCache = { expiresAt: 0, value: null };
|
|
@@ -4,14 +4,11 @@ import path from 'node:path';
|
|
|
4
4
|
|
|
5
5
|
export const AGENT_PROVIDER_CODEX = 'codex';
|
|
6
6
|
export const DEFAULT_AGENT_PROVIDER = AGENT_PROVIDER_CODEX;
|
|
7
|
-
export const DEFAULT_CODEX_MODEL_ID = '';
|
|
8
7
|
export const DEFAULT_AGENT_WORKSPACE = path.join(os.homedir(), '.livedesk', 'agent-workspace');
|
|
9
8
|
export const DEFAULT_AGENT_SETTINGS = Object.freeze({
|
|
10
|
-
settingsVersion:
|
|
9
|
+
settingsVersion: 4,
|
|
11
10
|
enabled: true,
|
|
12
11
|
provider: DEFAULT_AGENT_PROVIDER,
|
|
13
|
-
codexModelId: DEFAULT_CODEX_MODEL_ID,
|
|
14
|
-
codexReasoningEffort: 'medium',
|
|
15
12
|
codexSandboxMode: 'read-only',
|
|
16
13
|
codexApprovalPolicy: 'never',
|
|
17
14
|
codexWorkingDirectory: DEFAULT_AGENT_WORKSPACE,
|
|
@@ -25,20 +22,6 @@ export const DEFAULT_AGENT_SETTINGS = Object.freeze({
|
|
|
25
22
|
maxConcurrentRequests: 2
|
|
26
23
|
});
|
|
27
24
|
|
|
28
|
-
const REASONING_EFFORTS = new Set(['minimal', 'low', 'medium', 'high', 'xhigh']);
|
|
29
|
-
const SANDBOX_MODES = new Set(['read-only', 'workspace-write', 'danger-full-access']);
|
|
30
|
-
const APPROVAL_POLICIES = new Set(['never', 'on-request', 'on-failure', 'untrusted']);
|
|
31
|
-
const WEB_SEARCH_MODES = new Set(['disabled', 'cached', 'live']);
|
|
32
|
-
|
|
33
|
-
export class AgentSettingsError extends Error {
|
|
34
|
-
constructor(code, message) {
|
|
35
|
-
super(message);
|
|
36
|
-
this.name = 'AgentSettingsError';
|
|
37
|
-
this.code = code;
|
|
38
|
-
this.status = 400;
|
|
39
|
-
}
|
|
40
|
-
}
|
|
41
|
-
|
|
42
25
|
function booleanValue(value, fallback) {
|
|
43
26
|
return typeof value === 'boolean' ? value : fallback;
|
|
44
27
|
}
|
|
@@ -50,18 +33,7 @@ function numberValue(value, min, max, fallback, integer = false) {
|
|
|
50
33
|
return integer ? Math.round(clamped) : clamped;
|
|
51
34
|
}
|
|
52
35
|
|
|
53
|
-
function
|
|
54
|
-
if (typeof value !== 'string') return fallback;
|
|
55
|
-
return value.trim().slice(0, maxLength);
|
|
56
|
-
}
|
|
57
|
-
|
|
58
|
-
function enumValue(value, allowed, fallback, code) {
|
|
59
|
-
const normalized = stringValue(value, fallback, 80).toLowerCase();
|
|
60
|
-
if (!allowed.has(normalized)) throw new AgentSettingsError(code, `Invalid agent setting: ${normalized}.`);
|
|
61
|
-
return normalized;
|
|
62
|
-
}
|
|
63
|
-
|
|
64
|
-
function normalizeWorkingDirectory(value) {
|
|
36
|
+
function normalizeWorkingDirectory() {
|
|
65
37
|
// The agent runtime owns this directory. Do not allow a browser/API caller
|
|
66
38
|
// to move Codex into a user project or an arbitrary filesystem root.
|
|
67
39
|
return DEFAULT_AGENT_WORKSPACE;
|
|
@@ -70,18 +42,16 @@ function normalizeWorkingDirectory(value) {
|
|
|
70
42
|
export function normalizeAgentSettings(value = {}) {
|
|
71
43
|
const source = value && typeof value === 'object' && !Array.isArray(value) ? value : {};
|
|
72
44
|
return {
|
|
73
|
-
settingsVersion:
|
|
45
|
+
settingsVersion: 4,
|
|
74
46
|
enabled: booleanValue(source.enabled, DEFAULT_AGENT_SETTINGS.enabled),
|
|
75
47
|
// LiveDesk has one Agent runtime. Old provider values are deliberately
|
|
76
48
|
// normalized to Codex so an upgrade cannot reactivate a retired provider.
|
|
77
49
|
provider: AGENT_PROVIDER_CODEX,
|
|
78
|
-
codexModelId: stringValue(source.codexModelId, DEFAULT_AGENT_SETTINGS.codexModelId, 160),
|
|
79
|
-
codexReasoningEffort: enumValue(source.codexReasoningEffort, REASONING_EFFORTS, DEFAULT_AGENT_SETTINGS.codexReasoningEffort, 'agent-invalid-reasoning-effort'),
|
|
80
50
|
// These are safety settings, not user-controlled execution toggles. They
|
|
81
51
|
// are accepted for compatibility but always normalized to the safe floor.
|
|
82
52
|
codexSandboxMode: 'read-only',
|
|
83
53
|
codexApprovalPolicy: 'never',
|
|
84
|
-
codexWorkingDirectory: normalizeWorkingDirectory(
|
|
54
|
+
codexWorkingDirectory: normalizeWorkingDirectory(),
|
|
85
55
|
codexTaskTimeoutMs: numberValue(source.codexTaskTimeoutMs, 30000, 1800000, DEFAULT_AGENT_SETTINGS.codexTaskTimeoutMs, true),
|
|
86
56
|
codexMaxTurns: numberValue(source.codexMaxTurns, 1, 40, DEFAULT_AGENT_SETTINGS.codexMaxTurns, true),
|
|
87
57
|
codexMaxToolCalls: numberValue(source.codexMaxToolCalls, 1, 100, DEFAULT_AGENT_SETTINGS.codexMaxToolCalls, true),
|
|
@@ -66,15 +66,13 @@ function normalizeCodexError(error) {
|
|
|
66
66
|
return new AgentProviderError('codex-run-failed', message, { status: 502, retryable: true });
|
|
67
67
|
}
|
|
68
68
|
|
|
69
|
-
function codexThreadOptions(
|
|
70
|
-
return {
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
modelReasoningEffort: settings.codexReasoningEffort,
|
|
77
|
-
networkAccessEnabled: false,
|
|
69
|
+
function codexThreadOptions(workspace) {
|
|
70
|
+
return {
|
|
71
|
+
sandboxMode: 'read-only',
|
|
72
|
+
approvalPolicy: 'never',
|
|
73
|
+
workingDirectory: workspace,
|
|
74
|
+
skipGitRepoCheck: true,
|
|
75
|
+
networkAccessEnabled: false,
|
|
78
76
|
webSearchMode: 'disabled',
|
|
79
77
|
webSearchEnabled: false,
|
|
80
78
|
additionalDirectories: []
|
|
@@ -417,10 +415,10 @@ export function createCodexAgentRuntime({
|
|
|
417
415
|
const controller = new AbortController();
|
|
418
416
|
const timer = setTimeout(() => controller.abort(), Math.min(30000, settings.codexTaskTimeoutMs));
|
|
419
417
|
try {
|
|
420
|
-
const thread = codex.startThread(codexThreadOptions(
|
|
421
|
-
const turn = await thread.run('Reply with the single word READY. Do not use tools.', { signal: controller.signal });
|
|
422
|
-
if (!String(turn.finalResponse || '').trim()) throw new AgentProviderError('codex-empty-response', 'Codex returned an empty response.', { status: 502 });
|
|
423
|
-
return { ok: true,
|
|
418
|
+
const thread = codex.startThread(codexThreadOptions(workspace));
|
|
419
|
+
const turn = await thread.run('Reply with the single word READY. Do not use tools.', { signal: controller.signal });
|
|
420
|
+
if (!String(turn.finalResponse || '').trim()) throw new AgentProviderError('codex-empty-response', 'Codex returned an empty response.', { status: 502 });
|
|
421
|
+
return { ok: true, latencyMs: Date.now() - startedAt, threadId: thread.id || '' };
|
|
424
422
|
} catch (error) {
|
|
425
423
|
throw normalizeCodexError(error);
|
|
426
424
|
} finally {
|
|
@@ -531,7 +529,7 @@ export function createCodexAgentRuntime({
|
|
|
531
529
|
if (run.abortReason === 'timeout') throw codexAbortError('codex-run-timeout', 'The Codex task exceeded its timeout.');
|
|
532
530
|
throw Object.assign(new Error('The Codex task was cancelled.'), { name: 'AbortError' });
|
|
533
531
|
}
|
|
534
|
-
const threadOptions = codexThreadOptions(
|
|
532
|
+
const threadOptions = codexThreadOptions(workspace);
|
|
535
533
|
run.status = 'running';
|
|
536
534
|
run.updatedAt = new Date().toISOString();
|
|
537
535
|
for (let attempt = 0; attempt < 2; attempt += 1) {
|
package/src/server.js
CHANGED
|
@@ -2955,14 +2955,14 @@ app.delete('/api/settings/agent/api-key', async (_req, res) => {
|
|
|
2955
2955
|
}
|
|
2956
2956
|
});
|
|
2957
2957
|
|
|
2958
|
-
app.get('/api/settings/agent/models', async (_req, res) => {
|
|
2959
|
-
noStore(res);
|
|
2960
|
-
|
|
2961
|
-
|
|
2962
|
-
|
|
2963
|
-
|
|
2964
|
-
}
|
|
2965
|
-
});
|
|
2958
|
+
app.get('/api/settings/agent/models', async (_req, res) => {
|
|
2959
|
+
noStore(res);
|
|
2960
|
+
res.status(410).json({
|
|
2961
|
+
ok: false,
|
|
2962
|
+
error: 'agent-model-catalog-retired',
|
|
2963
|
+
message: 'LiveDesk uses the Codex SDK defaults and does not manage models.'
|
|
2964
|
+
});
|
|
2965
|
+
});
|
|
2966
2966
|
|
|
2967
2967
|
app.post('/api/settings/agent/test', async (_req, res) => {
|
|
2968
2968
|
noStore(res);
|