@alpacakit/agents 0.1.0-beta.19
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/LICENSE +21 -0
- package/README.md +224 -0
- package/dist/agents/builtin.d.ts +19 -0
- package/dist/agents/builtin.d.ts.map +1 -0
- package/dist/agents/builtin.js +14 -0
- package/dist/agents/claude.d.ts +20 -0
- package/dist/agents/claude.d.ts.map +1 -0
- package/dist/agents/claude.js +480 -0
- package/dist/agents/codex.d.ts +19 -0
- package/dist/agents/codex.d.ts.map +1 -0
- package/dist/agents/codex.js +355 -0
- package/dist/agents/openai-compatible/config.d.ts +16 -0
- package/dist/agents/openai-compatible/config.d.ts.map +1 -0
- package/dist/agents/openai-compatible/config.js +160 -0
- package/dist/agents/openai-compatible/engine.d.ts +18 -0
- package/dist/agents/openai-compatible/engine.d.ts.map +1 -0
- package/dist/agents/openai-compatible/engine.js +10 -0
- package/dist/agents/openai-compatible/fetch-engine.d.ts +38 -0
- package/dist/agents/openai-compatible/fetch-engine.d.ts.map +1 -0
- package/dist/agents/openai-compatible/fetch-engine.js +216 -0
- package/dist/agents/openai-compatible/pi/engine.d.ts +32 -0
- package/dist/agents/openai-compatible/pi/engine.d.ts.map +1 -0
- package/dist/agents/openai-compatible/pi/engine.js +98 -0
- package/dist/agents/openai-compatible/pi/module.d.ts +87 -0
- package/dist/agents/openai-compatible/pi/module.d.ts.map +1 -0
- package/dist/agents/openai-compatible/pi/module.js +43 -0
- package/dist/agents/openai-compatible/pi/sandbox.d.ts +25 -0
- package/dist/agents/openai-compatible/pi/sandbox.d.ts.map +1 -0
- package/dist/agents/openai-compatible/pi/sandbox.js +69 -0
- package/dist/agents/openai-compatible/pi/session.d.ts +17 -0
- package/dist/agents/openai-compatible/pi/session.d.ts.map +1 -0
- package/dist/agents/openai-compatible/pi/session.js +354 -0
- package/dist/agents/openai-compatible/response.d.ts +19 -0
- package/dist/agents/openai-compatible/response.d.ts.map +1 -0
- package/dist/agents/openai-compatible/response.js +203 -0
- package/dist/agents/openai-compatible/types.d.ts +34 -0
- package/dist/agents/openai-compatible/types.d.ts.map +1 -0
- package/dist/agents/openai-compatible/types.js +1 -0
- package/dist/agents/openai-compatible.d.ts +12 -0
- package/dist/agents/openai-compatible.d.ts.map +1 -0
- package/dist/agents/openai-compatible.js +45 -0
- package/dist/auth/login-probe.d.ts +21 -0
- package/dist/auth/login-probe.d.ts.map +1 -0
- package/dist/auth/login-probe.js +47 -0
- package/dist/auth/login.d.ts +79 -0
- package/dist/auth/login.d.ts.map +1 -0
- package/dist/auth/login.js +9 -0
- package/dist/auth/material.d.ts +87 -0
- package/dist/auth/material.d.ts.map +1 -0
- package/dist/auth/material.js +59 -0
- package/dist/auth/profile-store.d.ts +14 -0
- package/dist/auth/profile-store.d.ts.map +1 -0
- package/dist/auth/profile-store.js +101 -0
- package/dist/auth/secrets.d.ts +14 -0
- package/dist/auth/secrets.d.ts.map +1 -0
- package/dist/auth/secrets.js +40 -0
- package/dist/codex/app-server.d.ts +30 -0
- package/dist/codex/app-server.d.ts.map +1 -0
- package/dist/codex/app-server.js +322 -0
- package/dist/codex/index.d.ts +3 -0
- package/dist/codex/index.d.ts.map +1 -0
- package/dist/codex/index.js +1 -0
- package/dist/codex/protocol.d.ts +124 -0
- package/dist/codex/protocol.d.ts.map +1 -0
- package/dist/codex/protocol.js +283 -0
- package/dist/config/agent-config-validation.d.ts +22 -0
- package/dist/config/agent-config-validation.d.ts.map +1 -0
- package/dist/config/agent-config-validation.js +31 -0
- package/dist/config/agent-configs.d.ts +37 -0
- package/dist/config/agent-configs.d.ts.map +1 -0
- package/dist/config/agent-configs.js +214 -0
- package/dist/config/compose.d.ts +10 -0
- package/dist/config/compose.d.ts.map +1 -0
- package/dist/config/compose.js +89 -0
- package/dist/config/config.d.ts +21 -0
- package/dist/config/config.d.ts.map +1 -0
- package/dist/config/config.js +33 -0
- package/dist/config/errors.d.ts +45 -0
- package/dist/config/errors.d.ts.map +1 -0
- package/dist/config/errors.js +37 -0
- package/dist/config/extension.d.ts +3 -0
- package/dist/config/extension.d.ts.map +1 -0
- package/dist/config/extension.js +1 -0
- package/dist/config/ids.d.ts +8 -0
- package/dist/config/ids.d.ts.map +1 -0
- package/dist/config/ids.js +4 -0
- package/dist/config/index.d.ts +12 -0
- package/dist/config/index.d.ts.map +1 -0
- package/dist/config/index.js +6 -0
- package/dist/config/model.d.ts +105 -0
- package/dist/config/model.d.ts.map +1 -0
- package/dist/config/model.js +1 -0
- package/dist/config/paths.d.ts +7 -0
- package/dist/config/paths.d.ts.map +1 -0
- package/dist/config/paths.js +10 -0
- package/dist/config/schema.d.ts +59 -0
- package/dist/config/schema.d.ts.map +1 -0
- package/dist/config/schema.js +83 -0
- package/dist/config/store.d.ts +34 -0
- package/dist/config/store.d.ts.map +1 -0
- package/dist/config/store.js +420 -0
- package/dist/config/support.d.ts +14 -0
- package/dist/config/support.d.ts.map +1 -0
- package/dist/config/support.js +32 -0
- package/dist/config/values.d.ts +21 -0
- package/dist/config/values.d.ts.map +1 -0
- package/dist/config/values.js +22 -0
- package/dist/config/xdg.d.ts +20 -0
- package/dist/config/xdg.d.ts.map +1 -0
- package/dist/config/xdg.js +23 -0
- package/dist/core/async-queue.d.ts +14 -0
- package/dist/core/async-queue.d.ts.map +1 -0
- package/dist/core/async-queue.js +46 -0
- package/dist/core/env.d.ts +19 -0
- package/dist/core/env.d.ts.map +1 -0
- package/dist/core/env.js +39 -0
- package/dist/core/error.d.ts +121 -0
- package/dist/core/error.d.ts.map +1 -0
- package/dist/core/error.js +88 -0
- package/dist/core/fs.d.ts +16 -0
- package/dist/core/fs.d.ts.map +1 -0
- package/dist/core/fs.js +30 -0
- package/dist/core/json.d.ts +20 -0
- package/dist/core/json.d.ts.map +1 -0
- package/dist/core/json.js +42 -0
- package/dist/core/node-ports.d.ts +9 -0
- package/dist/core/node-ports.d.ts.map +1 -0
- package/dist/core/node-ports.js +135 -0
- package/dist/core/ports.d.ts +71 -0
- package/dist/core/ports.d.ts.map +1 -0
- package/dist/core/ports.js +19 -0
- package/dist/core/redact.d.ts +8 -0
- package/dist/core/redact.d.ts.map +1 -0
- package/dist/core/redact.js +66 -0
- package/dist/core/run.d.ts +125 -0
- package/dist/core/run.d.ts.map +1 -0
- package/dist/core/run.js +27 -0
- package/dist/core/values.d.ts +12 -0
- package/dist/core/values.d.ts.map +1 -0
- package/dist/core/values.js +9 -0
- package/dist/corpus/failure-corpus.d.ts +21 -0
- package/dist/corpus/failure-corpus.d.ts.map +1 -0
- package/dist/corpus/failure-corpus.js +89 -0
- package/dist/fleet/fleet.d.ts +120 -0
- package/dist/fleet/fleet.d.ts.map +1 -0
- package/dist/fleet/fleet.js +409 -0
- package/dist/fleet/policy.d.ts +45 -0
- package/dist/fleet/policy.d.ts.map +1 -0
- package/dist/fleet/policy.js +50 -0
- package/dist/fleet/store.d.ts +28 -0
- package/dist/fleet/store.d.ts.map +1 -0
- package/dist/fleet/store.js +225 -0
- package/dist/host/capabilities.d.ts +146 -0
- package/dist/host/capabilities.d.ts.map +1 -0
- package/dist/host/capabilities.js +59 -0
- package/dist/host/context.d.ts +29 -0
- package/dist/host/context.d.ts.map +1 -0
- package/dist/host/context.js +11 -0
- package/dist/host/github-dir.d.ts +16 -0
- package/dist/host/github-dir.d.ts.map +1 -0
- package/dist/host/github-dir.js +164 -0
- package/dist/host/mcp-list.d.ts +12 -0
- package/dist/host/mcp-list.d.ts.map +1 -0
- package/dist/host/mcp-list.js +122 -0
- package/dist/host/requirement-ref.d.ts +12 -0
- package/dist/host/requirement-ref.d.ts.map +1 -0
- package/dist/host/requirement-ref.js +40 -0
- package/dist/host/run-command.d.ts +27 -0
- package/dist/host/run-command.d.ts.map +1 -0
- package/dist/host/run-command.js +66 -0
- package/dist/host/validate-spec.d.ts +10 -0
- package/dist/host/validate-spec.d.ts.map +1 -0
- package/dist/host/validate-spec.js +69 -0
- package/dist/index.d.ts +69 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +41 -0
- package/dist/kernel/classify.d.ts +44 -0
- package/dist/kernel/classify.d.ts.map +1 -0
- package/dist/kernel/classify.js +136 -0
- package/dist/kernel/cli-agent.d.ts +62 -0
- package/dist/kernel/cli-agent.d.ts.map +1 -0
- package/dist/kernel/cli-agent.js +281 -0
- package/dist/kernel/cli-login.d.ts +13 -0
- package/dist/kernel/cli-login.d.ts.map +1 -0
- package/dist/kernel/cli-login.js +199 -0
- package/dist/kernel/definition.d.ts +41 -0
- package/dist/kernel/definition.d.ts.map +1 -0
- package/dist/kernel/definition.js +13 -0
- package/dist/kernel/env-template.d.ts +17 -0
- package/dist/kernel/env-template.d.ts.map +1 -0
- package/dist/kernel/env-template.js +78 -0
- package/dist/kernel/facets.d.ts +58 -0
- package/dist/kernel/facets.d.ts.map +1 -0
- package/dist/kernel/facets.js +102 -0
- package/dist/kernel/guard.d.ts +24 -0
- package/dist/kernel/guard.d.ts.map +1 -0
- package/dist/kernel/guard.js +69 -0
- package/dist/kernel/handle.d.ts +29 -0
- package/dist/kernel/handle.d.ts.map +1 -0
- package/dist/kernel/handle.js +97 -0
- package/dist/kernel/keyed.d.ts +19 -0
- package/dist/kernel/keyed.d.ts.map +1 -0
- package/dist/kernel/keyed.js +35 -0
- package/dist/kernel/login.d.ts +20 -0
- package/dist/kernel/login.d.ts.map +1 -0
- package/dist/kernel/login.js +74 -0
- package/dist/kernel/options.d.ts +73 -0
- package/dist/kernel/options.d.ts.map +1 -0
- package/dist/kernel/options.js +41 -0
- package/dist/kernel/run.d.ts +20 -0
- package/dist/kernel/run.d.ts.map +1 -0
- package/dist/kernel/run.js +245 -0
- package/dist/kernel/runtime.d.ts +48 -0
- package/dist/kernel/runtime.d.ts.map +1 -0
- package/dist/kernel/runtime.js +108 -0
- package/dist/keyring/index.d.ts +2 -0
- package/dist/keyring/index.d.ts.map +1 -0
- package/dist/keyring/index.js +1 -0
- package/dist/keyring/resolver.d.ts +9 -0
- package/dist/keyring/resolver.d.ts.map +1 -0
- package/dist/keyring/resolver.js +62 -0
- package/dist/run-agent.d.ts +19 -0
- package/dist/run-agent.d.ts.map +1 -0
- package/dist/run-agent.js +25 -0
- package/dist/structured/extract.d.ts +27 -0
- package/dist/structured/extract.d.ts.map +1 -0
- package/dist/structured/extract.js +188 -0
- package/dist/structured/run-structured.d.ts +83 -0
- package/dist/structured/run-structured.d.ts.map +1 -0
- package/dist/structured/run-structured.js +202 -0
- package/dist/structured/standard-schema.d.ts +34 -0
- package/dist/structured/standard-schema.d.ts.map +1 -0
- package/dist/structured/standard-schema.js +6 -0
- package/dist/testing/fake-agent.d.ts +32 -0
- package/dist/testing/fake-agent.d.ts.map +1 -0
- package/dist/testing/fake-agent.js +43 -0
- package/dist/testing/fake-clock.d.ts +8 -0
- package/dist/testing/fake-clock.d.ts.map +1 -0
- package/dist/testing/fake-clock.js +44 -0
- package/dist/testing/fake-exec.d.ts +26 -0
- package/dist/testing/fake-exec.d.ts.map +1 -0
- package/dist/testing/fake-exec.js +69 -0
- package/dist/testing/fake-secrets.d.ts +3 -0
- package/dist/testing/fake-secrets.d.ts.map +1 -0
- package/dist/testing/fake-secrets.js +5 -0
- package/dist/testing/index.d.ts +10 -0
- package/dist/testing/index.d.ts.map +1 -0
- package/dist/testing/index.js +9 -0
- package/package.json +75 -0
|
@@ -0,0 +1,420 @@
|
|
|
1
|
+
import { mkdir, readFile, rename, writeFile } from "node:fs/promises";
|
|
2
|
+
import path from "node:path";
|
|
3
|
+
import { AUTH_MATERIAL_KIND } from "../auth/material.js";
|
|
4
|
+
import { fileFleetStore } from "../fleet/store.js";
|
|
5
|
+
import { AGENT_CONFIG_VALIDATION_RESULT, validateAgentConfig, } from "./agent-config-validation.js";
|
|
6
|
+
import { AGENTS_CONFIG_ERROR_CODE, AgentsConfigError } from "./errors.js";
|
|
7
|
+
import { profileId } from "./ids.js";
|
|
8
|
+
import { AGENTS_CONFIG_FILE_VERSION, agentConfigSettingsFileSchema, profilesFileSchema, } from "./schema.js";
|
|
9
|
+
import { FIELD_PATH, formatFieldPath, isErrnoCode, NODE_ERRNO_CODE, } from "./support.js";
|
|
10
|
+
import { AGENT_CONFIG_KIND, DEFAULT_AGENT_CONFIG_ID } from "./values.js";
|
|
11
|
+
const TEXT_ENCODING = "utf8";
|
|
12
|
+
const PRIVATE_DIRECTORY_MODE = 0o700;
|
|
13
|
+
const PRIVATE_FILE_MODE = 0o600;
|
|
14
|
+
const TEMP_FILE_SUFFIX = "tmp";
|
|
15
|
+
const TEMP_FILE_PATH_SEPARATOR = ".";
|
|
16
|
+
const JSON_INDENT_SPACES = 2;
|
|
17
|
+
const TRAILING_NEWLINE = "\n";
|
|
18
|
+
const FILE_PARSE_ERROR_REASON = {
|
|
19
|
+
invalidJson: "Invalid JSON.",
|
|
20
|
+
invalidFile: "Invalid file.",
|
|
21
|
+
};
|
|
22
|
+
const MUTATION_FIELD = {
|
|
23
|
+
id: "id",
|
|
24
|
+
agentConfigs: "agentConfigs",
|
|
25
|
+
profileOrder: "profileIds",
|
|
26
|
+
agentConfigOrder: "agentConfigIds",
|
|
27
|
+
agentConfigKind: "kind",
|
|
28
|
+
agentConfigPayload: "payload",
|
|
29
|
+
};
|
|
30
|
+
const MUTATION_ERROR_REASON = {
|
|
31
|
+
duplicateProfileId: (id) => `Duplicate profile id "${id}".`,
|
|
32
|
+
duplicateAgentConfigId: (id) => `Duplicate agent config id "${id}".`,
|
|
33
|
+
duplicateReorderId: (id) => `Duplicate reorder id "${id}".`,
|
|
34
|
+
missingProfileId: (id) => `Missing profile id "${id}".`,
|
|
35
|
+
missingAgentConfigId: (id) => `Missing agent config id "${id}".`,
|
|
36
|
+
incompleteProfileOrder: "Profile order must include each profile exactly once.",
|
|
37
|
+
incompleteAgentConfigOrder: "Agent config order must include each agent config exactly once.",
|
|
38
|
+
unknownAgentConfigKind: (kind) => `Unknown agent config kind "${kind}".`,
|
|
39
|
+
invalidAgentConfigPayload: (issues) => `Invalid agent config payload: ${issues.join(ERROR_ISSUE_SEPARATOR)}`,
|
|
40
|
+
};
|
|
41
|
+
const ERROR_ISSUE_SEPARATOR = "; ";
|
|
42
|
+
export const DEFAULT_AGENTS_CONFIG_AGENT_SETTINGS = {
|
|
43
|
+
ambientBuiltinAuth: { enabled: true },
|
|
44
|
+
agentConfigs: [
|
|
45
|
+
{
|
|
46
|
+
id: DEFAULT_AGENT_CONFIG_ID.codex,
|
|
47
|
+
kind: AGENT_CONFIG_KIND.codex,
|
|
48
|
+
enabled: true,
|
|
49
|
+
payload: { model: null, effort: null },
|
|
50
|
+
},
|
|
51
|
+
{
|
|
52
|
+
id: DEFAULT_AGENT_CONFIG_ID.claude,
|
|
53
|
+
kind: AGENT_CONFIG_KIND.claude,
|
|
54
|
+
enabled: true,
|
|
55
|
+
payload: { model: null, effort: null },
|
|
56
|
+
},
|
|
57
|
+
],
|
|
58
|
+
};
|
|
59
|
+
class FileProfileManager {
|
|
60
|
+
store;
|
|
61
|
+
constructor(store) {
|
|
62
|
+
this.store = store;
|
|
63
|
+
}
|
|
64
|
+
async list() {
|
|
65
|
+
return await this.store.list();
|
|
66
|
+
}
|
|
67
|
+
async addHomeDir(input) {
|
|
68
|
+
const profile = {
|
|
69
|
+
id: profileId(input.id),
|
|
70
|
+
agentId: input.agentId,
|
|
71
|
+
material: {
|
|
72
|
+
kind: AUTH_MATERIAL_KIND.homeDir,
|
|
73
|
+
path: input.path,
|
|
74
|
+
},
|
|
75
|
+
};
|
|
76
|
+
return await this.addProfile(profile);
|
|
77
|
+
}
|
|
78
|
+
async addApiKey(input) {
|
|
79
|
+
const profile = {
|
|
80
|
+
id: profileId(input.id),
|
|
81
|
+
agentId: input.agentId,
|
|
82
|
+
material: {
|
|
83
|
+
kind: AUTH_MATERIAL_KIND.apiKey,
|
|
84
|
+
secret: input.secret,
|
|
85
|
+
},
|
|
86
|
+
};
|
|
87
|
+
return await this.addProfile(profile);
|
|
88
|
+
}
|
|
89
|
+
async remove(id) {
|
|
90
|
+
const profiles = await this.store.list();
|
|
91
|
+
const profile = profiles.find((entry) => entry.id === id);
|
|
92
|
+
if (profile === undefined) {
|
|
93
|
+
return null;
|
|
94
|
+
}
|
|
95
|
+
await this.store.save(profiles.filter((entry) => entry.id !== id));
|
|
96
|
+
return profile;
|
|
97
|
+
}
|
|
98
|
+
async reorder(ids) {
|
|
99
|
+
const profiles = await this.store.list();
|
|
100
|
+
const reordered = reorderRecords({
|
|
101
|
+
ids,
|
|
102
|
+
records: profiles,
|
|
103
|
+
idOf: (profile) => profile.id,
|
|
104
|
+
field: MUTATION_FIELD.profileOrder,
|
|
105
|
+
duplicateReason: MUTATION_ERROR_REASON.duplicateReorderId,
|
|
106
|
+
missingReason: MUTATION_ERROR_REASON.missingProfileId,
|
|
107
|
+
incompleteReason: MUTATION_ERROR_REASON.incompleteProfileOrder,
|
|
108
|
+
});
|
|
109
|
+
await this.store.save(reordered);
|
|
110
|
+
return reordered;
|
|
111
|
+
}
|
|
112
|
+
async clear() {
|
|
113
|
+
await this.store.save([]);
|
|
114
|
+
}
|
|
115
|
+
async addProfile(profile) {
|
|
116
|
+
const profiles = await this.store.list();
|
|
117
|
+
if (profiles.some((entry) => entry.id === profile.id)) {
|
|
118
|
+
throw invalidInputError(MUTATION_FIELD.id, MUTATION_ERROR_REASON.duplicateProfileId(profile.id));
|
|
119
|
+
}
|
|
120
|
+
const nextProfiles = [...profiles, profile];
|
|
121
|
+
validateProfileRecords(nextProfiles);
|
|
122
|
+
await this.store.save(nextProfiles);
|
|
123
|
+
return profile;
|
|
124
|
+
}
|
|
125
|
+
}
|
|
126
|
+
class FileAgentConfigManager {
|
|
127
|
+
store;
|
|
128
|
+
agentConfigTypes;
|
|
129
|
+
constructor(store, agentConfigTypes) {
|
|
130
|
+
this.store = store;
|
|
131
|
+
this.agentConfigTypes = agentConfigTypes;
|
|
132
|
+
}
|
|
133
|
+
async list() {
|
|
134
|
+
return (await this.store.read()).agentConfigs;
|
|
135
|
+
}
|
|
136
|
+
async getSettings() {
|
|
137
|
+
return await this.store.read();
|
|
138
|
+
}
|
|
139
|
+
async add(record) {
|
|
140
|
+
const settings = await this.store.read();
|
|
141
|
+
if (settings.agentConfigs.some((agentConfig) => agentConfig.id === record.id)) {
|
|
142
|
+
throw invalidInputError(MUTATION_FIELD.id, MUTATION_ERROR_REASON.duplicateAgentConfigId(record.id));
|
|
143
|
+
}
|
|
144
|
+
validateAgentConfigMutationRecord(record, this.agentConfigTypes);
|
|
145
|
+
const nextSettings = {
|
|
146
|
+
...settings,
|
|
147
|
+
agentConfigs: [...settings.agentConfigs, record],
|
|
148
|
+
};
|
|
149
|
+
validateAgentConfigSettings(nextSettings, this.agentConfigTypes);
|
|
150
|
+
await this.store.save(nextSettings);
|
|
151
|
+
return record;
|
|
152
|
+
}
|
|
153
|
+
async update(id, patch) {
|
|
154
|
+
const settings = await this.store.read();
|
|
155
|
+
const agentConfig = settings.agentConfigs.find((entry) => entry.id === id);
|
|
156
|
+
if (agentConfig === undefined) {
|
|
157
|
+
return null;
|
|
158
|
+
}
|
|
159
|
+
const nextAgentConfig = {
|
|
160
|
+
...agentConfig,
|
|
161
|
+
...(patch.enabled === undefined ? {} : { enabled: patch.enabled }),
|
|
162
|
+
...(patch.payload === undefined ? {} : { payload: patch.payload }),
|
|
163
|
+
};
|
|
164
|
+
validateAgentConfigMutationRecord(nextAgentConfig, this.agentConfigTypes);
|
|
165
|
+
const agentConfigs = settings.agentConfigs.map((entry) => entry.id === id ? nextAgentConfig : entry);
|
|
166
|
+
const nextSettings = { ...settings, agentConfigs };
|
|
167
|
+
validateAgentConfigSettings(nextSettings, this.agentConfigTypes);
|
|
168
|
+
await this.store.save(nextSettings);
|
|
169
|
+
return nextAgentConfig;
|
|
170
|
+
}
|
|
171
|
+
async remove(id) {
|
|
172
|
+
const settings = await this.store.read();
|
|
173
|
+
const agentConfig = settings.agentConfigs.find((entry) => entry.id === id);
|
|
174
|
+
if (agentConfig === undefined) {
|
|
175
|
+
return null;
|
|
176
|
+
}
|
|
177
|
+
const nextSettings = {
|
|
178
|
+
...settings,
|
|
179
|
+
agentConfigs: settings.agentConfigs.filter((entry) => entry.id !== id),
|
|
180
|
+
};
|
|
181
|
+
validateAgentConfigSettings(nextSettings, this.agentConfigTypes);
|
|
182
|
+
await this.store.save(nextSettings);
|
|
183
|
+
return agentConfig;
|
|
184
|
+
}
|
|
185
|
+
async reorder(ids) {
|
|
186
|
+
const settings = await this.store.read();
|
|
187
|
+
const agentConfigs = reorderRecords({
|
|
188
|
+
ids,
|
|
189
|
+
records: settings.agentConfigs,
|
|
190
|
+
idOf: (agentConfig) => agentConfig.id,
|
|
191
|
+
field: MUTATION_FIELD.agentConfigOrder,
|
|
192
|
+
duplicateReason: MUTATION_ERROR_REASON.duplicateReorderId,
|
|
193
|
+
missingReason: MUTATION_ERROR_REASON.missingAgentConfigId,
|
|
194
|
+
incompleteReason: MUTATION_ERROR_REASON.incompleteAgentConfigOrder,
|
|
195
|
+
});
|
|
196
|
+
const nextSettings = { ...settings, agentConfigs };
|
|
197
|
+
validateAgentConfigSettings(nextSettings, this.agentConfigTypes);
|
|
198
|
+
await this.store.save(nextSettings);
|
|
199
|
+
return agentConfigs;
|
|
200
|
+
}
|
|
201
|
+
async setAmbientBuiltinAuth(enabled) {
|
|
202
|
+
const settings = await this.store.read();
|
|
203
|
+
const nextSettings = {
|
|
204
|
+
...settings,
|
|
205
|
+
ambientBuiltinAuth: { enabled },
|
|
206
|
+
};
|
|
207
|
+
validateAgentConfigSettings(nextSettings, this.agentConfigTypes);
|
|
208
|
+
await this.store.save(nextSettings);
|
|
209
|
+
return nextSettings;
|
|
210
|
+
}
|
|
211
|
+
}
|
|
212
|
+
class FileProfileStore {
|
|
213
|
+
filePath;
|
|
214
|
+
constructor(filePath) {
|
|
215
|
+
this.filePath = filePath;
|
|
216
|
+
}
|
|
217
|
+
async list() {
|
|
218
|
+
const raw = await readOptionalFile(this.filePath);
|
|
219
|
+
if (raw === null) {
|
|
220
|
+
return [];
|
|
221
|
+
}
|
|
222
|
+
return parseProfilesFile(this.filePath, raw).profiles;
|
|
223
|
+
}
|
|
224
|
+
async save(profiles) {
|
|
225
|
+
const file = {
|
|
226
|
+
version: AGENTS_CONFIG_FILE_VERSION,
|
|
227
|
+
profiles,
|
|
228
|
+
};
|
|
229
|
+
await writeJsonAtomically(this.filePath, file);
|
|
230
|
+
}
|
|
231
|
+
}
|
|
232
|
+
class FileAgentConfigSettingsStore {
|
|
233
|
+
filePath;
|
|
234
|
+
constructor(filePath) {
|
|
235
|
+
this.filePath = filePath;
|
|
236
|
+
}
|
|
237
|
+
async read() {
|
|
238
|
+
const raw = await readOptionalFile(this.filePath);
|
|
239
|
+
if (raw === null) {
|
|
240
|
+
return DEFAULT_AGENTS_CONFIG_AGENT_SETTINGS;
|
|
241
|
+
}
|
|
242
|
+
return parseAgentConfigSettingsFile(this.filePath, raw);
|
|
243
|
+
}
|
|
244
|
+
async save(settings) {
|
|
245
|
+
const file = {
|
|
246
|
+
version: AGENTS_CONFIG_FILE_VERSION,
|
|
247
|
+
...settings,
|
|
248
|
+
};
|
|
249
|
+
await writeJsonAtomically(this.filePath, file);
|
|
250
|
+
}
|
|
251
|
+
}
|
|
252
|
+
export function openAgentsConfigStores(paths, agentConfigTypes) {
|
|
253
|
+
const profiles = new FileProfileStore(paths.profilesFile);
|
|
254
|
+
const agentConfigs = new FileAgentConfigSettingsStore(paths.agentConfigSettingsFile);
|
|
255
|
+
return {
|
|
256
|
+
paths,
|
|
257
|
+
profiles: new FileProfileManager(profiles),
|
|
258
|
+
agentConfigs: new FileAgentConfigManager(agentConfigs, agentConfigTypes),
|
|
259
|
+
fleetStateStore: fileFleetStore(paths.fleetStateFile),
|
|
260
|
+
};
|
|
261
|
+
}
|
|
262
|
+
export async function loadConfigData(home) {
|
|
263
|
+
return {
|
|
264
|
+
paths: home.paths,
|
|
265
|
+
profiles: await home.profiles.list(),
|
|
266
|
+
agentConfigs: await home.agentConfigs.getSettings(),
|
|
267
|
+
};
|
|
268
|
+
}
|
|
269
|
+
function validateProfileRecords(profiles) {
|
|
270
|
+
const result = profilesFileSchema.safeParse({
|
|
271
|
+
version: AGENTS_CONFIG_FILE_VERSION,
|
|
272
|
+
profiles,
|
|
273
|
+
});
|
|
274
|
+
if (!result.success) {
|
|
275
|
+
throw zodIssueInvalidInputError(result.error.issues[0]);
|
|
276
|
+
}
|
|
277
|
+
}
|
|
278
|
+
function validateAgentConfigMutationRecord(record, agentConfigTypes) {
|
|
279
|
+
throwAgentConfigValidationInputError(validateAgentConfig(record, agentConfigTypes), {
|
|
280
|
+
kind: MUTATION_FIELD.agentConfigKind,
|
|
281
|
+
payload: MUTATION_FIELD.agentConfigPayload,
|
|
282
|
+
});
|
|
283
|
+
}
|
|
284
|
+
function validateAgentConfigSettings(settings, agentConfigTypes) {
|
|
285
|
+
const result = agentConfigSettingsFileSchema.safeParse({
|
|
286
|
+
version: AGENTS_CONFIG_FILE_VERSION,
|
|
287
|
+
...settings,
|
|
288
|
+
});
|
|
289
|
+
if (!result.success) {
|
|
290
|
+
throw zodIssueInvalidInputError(result.error.issues[0]);
|
|
291
|
+
}
|
|
292
|
+
validateAgentConfigSettingRows(settings, agentConfigTypes);
|
|
293
|
+
}
|
|
294
|
+
function validateAgentConfigSettingRows(settings, agentConfigTypes) {
|
|
295
|
+
for (const [index, record] of settings.agentConfigs.entries()) {
|
|
296
|
+
throwAgentConfigValidationInputError(validateAgentConfig(record, agentConfigTypes), {
|
|
297
|
+
kind: agentConfigField(index, MUTATION_FIELD.agentConfigKind),
|
|
298
|
+
payload: agentConfigField(index, MUTATION_FIELD.agentConfigPayload),
|
|
299
|
+
});
|
|
300
|
+
}
|
|
301
|
+
}
|
|
302
|
+
function throwAgentConfigValidationInputError(validation, field) {
|
|
303
|
+
if (validation.kind === AGENT_CONFIG_VALIDATION_RESULT.unknownKind) {
|
|
304
|
+
throw invalidInputError(field.kind, MUTATION_ERROR_REASON.unknownAgentConfigKind(validation.agentConfigKind));
|
|
305
|
+
}
|
|
306
|
+
if (validation.kind === AGENT_CONFIG_VALIDATION_RESULT.invalidPayload) {
|
|
307
|
+
throw invalidInputError(field.payload, MUTATION_ERROR_REASON.invalidAgentConfigPayload(validation.issues));
|
|
308
|
+
}
|
|
309
|
+
}
|
|
310
|
+
function agentConfigField(index, field) {
|
|
311
|
+
return formatFieldPath([MUTATION_FIELD.agentConfigs, index, field]);
|
|
312
|
+
}
|
|
313
|
+
function reorderRecords(input) {
|
|
314
|
+
if (input.ids.length !== input.records.length) {
|
|
315
|
+
throw invalidInputError(input.field, input.incompleteReason);
|
|
316
|
+
}
|
|
317
|
+
const recordsById = new Map(input.records.map((record) => [input.idOf(record), record]));
|
|
318
|
+
const seenIds = new Set();
|
|
319
|
+
const records = [];
|
|
320
|
+
for (const id of input.ids) {
|
|
321
|
+
if (seenIds.has(id)) {
|
|
322
|
+
throw invalidInputError(input.field, input.duplicateReason(id));
|
|
323
|
+
}
|
|
324
|
+
seenIds.add(id);
|
|
325
|
+
const record = recordsById.get(id);
|
|
326
|
+
if (record === undefined) {
|
|
327
|
+
throw invalidInputError(input.field, input.missingReason(id));
|
|
328
|
+
}
|
|
329
|
+
records.push(record);
|
|
330
|
+
}
|
|
331
|
+
return records;
|
|
332
|
+
}
|
|
333
|
+
function zodIssueInvalidInputError(issue) {
|
|
334
|
+
if (issue === undefined) {
|
|
335
|
+
return invalidInputError(FIELD_PATH.root, FILE_PARSE_ERROR_REASON.invalidFile);
|
|
336
|
+
}
|
|
337
|
+
return invalidInputError(formatFieldPath(issue.path), issue.message);
|
|
338
|
+
}
|
|
339
|
+
function invalidInputError(field, reason) {
|
|
340
|
+
return new AgentsConfigError({
|
|
341
|
+
code: AGENTS_CONFIG_ERROR_CODE.invalidInput,
|
|
342
|
+
message: `${field}: ${reason}`,
|
|
343
|
+
data: { field, reason },
|
|
344
|
+
});
|
|
345
|
+
}
|
|
346
|
+
async function readOptionalFile(filePath) {
|
|
347
|
+
try {
|
|
348
|
+
return await readFile(filePath, TEXT_ENCODING);
|
|
349
|
+
}
|
|
350
|
+
catch (error) {
|
|
351
|
+
if (isErrnoCode(error, NODE_ERRNO_CODE.missingFile)) {
|
|
352
|
+
return null;
|
|
353
|
+
}
|
|
354
|
+
throw error;
|
|
355
|
+
}
|
|
356
|
+
}
|
|
357
|
+
function parseProfilesFile(filePath, raw) {
|
|
358
|
+
return parseJsonFile(filePath, raw, profilesFileSchema);
|
|
359
|
+
}
|
|
360
|
+
function parseAgentConfigSettingsFile(filePath, raw) {
|
|
361
|
+
return parseJsonFile(filePath, raw, agentConfigSettingsFileSchema);
|
|
362
|
+
}
|
|
363
|
+
function parseJsonFile(filePath, raw, schema) {
|
|
364
|
+
let parsed;
|
|
365
|
+
try {
|
|
366
|
+
parsed = JSON.parse(raw);
|
|
367
|
+
}
|
|
368
|
+
catch (error) {
|
|
369
|
+
throw invalidFileError({
|
|
370
|
+
filePath,
|
|
371
|
+
field: FIELD_PATH.root,
|
|
372
|
+
reason: error instanceof Error
|
|
373
|
+
? error.message
|
|
374
|
+
: FILE_PARSE_ERROR_REASON.invalidJson,
|
|
375
|
+
cause: error,
|
|
376
|
+
});
|
|
377
|
+
}
|
|
378
|
+
const result = schema.safeParse(parsed);
|
|
379
|
+
if (result.success) {
|
|
380
|
+
return result.data;
|
|
381
|
+
}
|
|
382
|
+
const firstIssue = result.error.issues[0];
|
|
383
|
+
throw invalidFileError({
|
|
384
|
+
filePath,
|
|
385
|
+
field: firstIssue === undefined
|
|
386
|
+
? FIELD_PATH.root
|
|
387
|
+
: formatFieldPath(firstIssue.path),
|
|
388
|
+
reason: firstIssue?.message ?? FILE_PARSE_ERROR_REASON.invalidFile,
|
|
389
|
+
cause: result.error,
|
|
390
|
+
});
|
|
391
|
+
}
|
|
392
|
+
function invalidFileError(input) {
|
|
393
|
+
return new AgentsConfigError({
|
|
394
|
+
code: AGENTS_CONFIG_ERROR_CODE.invalidFile,
|
|
395
|
+
message: `${input.filePath}:${input.field}: ${input.reason}`,
|
|
396
|
+
data: {
|
|
397
|
+
filePath: input.filePath,
|
|
398
|
+
field: input.field,
|
|
399
|
+
reason: input.reason,
|
|
400
|
+
},
|
|
401
|
+
cause: input.cause,
|
|
402
|
+
});
|
|
403
|
+
}
|
|
404
|
+
async function writeJsonAtomically(filePath, value) {
|
|
405
|
+
await mkdir(path.dirname(filePath), {
|
|
406
|
+
recursive: true,
|
|
407
|
+
mode: PRIVATE_DIRECTORY_MODE,
|
|
408
|
+
});
|
|
409
|
+
const tempPath = [
|
|
410
|
+
filePath,
|
|
411
|
+
String(process.pid),
|
|
412
|
+
String(Date.now()),
|
|
413
|
+
TEMP_FILE_SUFFIX,
|
|
414
|
+
].join(TEMP_FILE_PATH_SEPARATOR);
|
|
415
|
+
await writeFile(tempPath, `${JSON.stringify(value, null, JSON_INDENT_SPACES)}${TRAILING_NEWLINE}`, {
|
|
416
|
+
encoding: TEXT_ENCODING,
|
|
417
|
+
mode: PRIVATE_FILE_MODE,
|
|
418
|
+
});
|
|
419
|
+
await rename(tempPath, filePath);
|
|
420
|
+
}
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
export declare const ZOD_ISSUE_CODE: {
|
|
2
|
+
readonly custom: "custom";
|
|
3
|
+
};
|
|
4
|
+
export declare const FIELD_PATH: {
|
|
5
|
+
readonly root: "$";
|
|
6
|
+
readonly separator: ".";
|
|
7
|
+
};
|
|
8
|
+
export declare const NODE_ERRNO_CODE: {
|
|
9
|
+
readonly missingFile: "ENOENT";
|
|
10
|
+
};
|
|
11
|
+
export declare function readNonBlankEnvValue(env: Readonly<Record<string, string | undefined>>, name: string): string | null;
|
|
12
|
+
export declare function formatFieldPath(pathParts: readonly PropertyKey[]): string;
|
|
13
|
+
export declare function isErrnoCode(error: unknown, code: string): boolean;
|
|
14
|
+
//# sourceMappingURL=support.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"support.d.ts","sourceRoot":"","sources":["../../src/config/support.ts"],"names":[],"mappings":"AAAA,eAAO,MAAM,cAAc;;CAEjB,CAAC;AAEX,eAAO,MAAM,UAAU;;;CAGb,CAAC;AAEX,eAAO,MAAM,eAAe;;CAElB,CAAC;AAMX,wBAAgB,oBAAoB,CAClC,GAAG,EAAE,QAAQ,CAAC,MAAM,CAAC,MAAM,EAAE,MAAM,GAAG,SAAS,CAAC,CAAC,EACjD,IAAI,EAAE,MAAM,GACX,MAAM,GAAG,IAAI,CAGf;AAMD,wBAAgB,eAAe,CAAC,SAAS,EAAE,SAAS,WAAW,EAAE,GAAG,MAAM,CAKzE;AAED,wBAAgB,WAAW,CAAC,KAAK,EAAE,OAAO,EAAE,IAAI,EAAE,MAAM,GAAG,OAAO,CAOjE"}
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
export const ZOD_ISSUE_CODE = {
|
|
2
|
+
custom: "custom",
|
|
3
|
+
};
|
|
4
|
+
export const FIELD_PATH = {
|
|
5
|
+
root: "$",
|
|
6
|
+
separator: ".",
|
|
7
|
+
};
|
|
8
|
+
export const NODE_ERRNO_CODE = {
|
|
9
|
+
missingFile: "ENOENT",
|
|
10
|
+
};
|
|
11
|
+
const NODE_ERROR_FIELD = {
|
|
12
|
+
code: "code",
|
|
13
|
+
};
|
|
14
|
+
export function readNonBlankEnvValue(env, name) {
|
|
15
|
+
const value = env[name];
|
|
16
|
+
return isNonBlankString(value) ? value : null;
|
|
17
|
+
}
|
|
18
|
+
function isNonBlankString(value) {
|
|
19
|
+
return typeof value === "string" && value.trim().length > 0;
|
|
20
|
+
}
|
|
21
|
+
export function formatFieldPath(pathParts) {
|
|
22
|
+
if (pathParts.length === 0) {
|
|
23
|
+
return FIELD_PATH.root;
|
|
24
|
+
}
|
|
25
|
+
return pathParts.map(String).join(FIELD_PATH.separator);
|
|
26
|
+
}
|
|
27
|
+
export function isErrnoCode(error, code) {
|
|
28
|
+
return (typeof error === "object" &&
|
|
29
|
+
error !== null &&
|
|
30
|
+
NODE_ERROR_FIELD.code in error &&
|
|
31
|
+
Reflect.get(error, NODE_ERROR_FIELD.code) === code);
|
|
32
|
+
}
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
export { BUILTIN_AGENT_ID } from "../agents/builtin.js";
|
|
2
|
+
export declare const AGENTS_CONFIG_FILE: {
|
|
3
|
+
readonly profiles: "auth-profiles.json";
|
|
4
|
+
readonly agentConfigSettings: "agent-settings.json";
|
|
5
|
+
readonly fleetState: "fleet-state.json";
|
|
6
|
+
};
|
|
7
|
+
export declare const AGENT_CONFIG_KIND: {
|
|
8
|
+
readonly codex: import("./ids.js").AgentConfigKind;
|
|
9
|
+
readonly claude: import("./ids.js").AgentConfigKind;
|
|
10
|
+
readonly openaiCompatible: import("./ids.js").AgentConfigKind;
|
|
11
|
+
};
|
|
12
|
+
export declare const DEFAULT_AGENT_CONFIG_ID: {
|
|
13
|
+
readonly codex: import("./ids.js").AgentConfigId;
|
|
14
|
+
readonly claude: import("./ids.js").AgentConfigId;
|
|
15
|
+
};
|
|
16
|
+
export declare const CANDIDATE_SOURCE_KIND: {
|
|
17
|
+
readonly profile: "profile";
|
|
18
|
+
readonly ambient: "ambient";
|
|
19
|
+
readonly configured: "configured";
|
|
20
|
+
};
|
|
21
|
+
//# sourceMappingURL=values.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"values.d.ts","sourceRoot":"","sources":["../../src/config/values.ts"],"names":[],"mappings":"AAGA,OAAO,EAAE,gBAAgB,EAAE,MAAM,sBAAsB,CAAC;AAExD,eAAO,MAAM,kBAAkB;;;;CAIrB,CAAC;AAEX,eAAO,MAAM,iBAAiB;;;;CAIpB,CAAC;AAEX,eAAO,MAAM,uBAAuB;;;CAG1B,CAAC;AAEX,eAAO,MAAM,qBAAqB;;;;CAIxB,CAAC"}
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
import { BUILTIN_AGENT_ID } from "../agents/builtin.js";
|
|
2
|
+
import { agentConfigId, agentConfigKind } from "./ids.js";
|
|
3
|
+
export { BUILTIN_AGENT_ID } from "../agents/builtin.js";
|
|
4
|
+
export const AGENTS_CONFIG_FILE = {
|
|
5
|
+
profiles: "auth-profiles.json",
|
|
6
|
+
agentConfigSettings: "agent-settings.json",
|
|
7
|
+
fleetState: "fleet-state.json",
|
|
8
|
+
};
|
|
9
|
+
export const AGENT_CONFIG_KIND = {
|
|
10
|
+
codex: agentConfigKind(BUILTIN_AGENT_ID.codex),
|
|
11
|
+
claude: agentConfigKind(BUILTIN_AGENT_ID.claude),
|
|
12
|
+
openaiCompatible: agentConfigKind("openai-compatible"),
|
|
13
|
+
};
|
|
14
|
+
export const DEFAULT_AGENT_CONFIG_ID = {
|
|
15
|
+
codex: agentConfigId(BUILTIN_AGENT_ID.codex),
|
|
16
|
+
claude: agentConfigId(BUILTIN_AGENT_ID.claude),
|
|
17
|
+
};
|
|
18
|
+
export const CANDIDATE_SOURCE_KIND = {
|
|
19
|
+
profile: "profile",
|
|
20
|
+
ambient: "ambient",
|
|
21
|
+
configured: "configured",
|
|
22
|
+
};
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* A convention-neutral config preset for general OSS consumers: resolve
|
|
3
|
+
* the config root from the XDG Base Directory spec
|
|
4
|
+
* (`$XDG_CONFIG_HOME/<appName>/agents`, defaulting to
|
|
5
|
+
* `<homeDir>/.config/<appName>/agents`). It owns no secret-storage
|
|
6
|
+
* policy — the app supplies its own `secretResolvers` (e.g.
|
|
7
|
+
* `keyringResolver` from `/keyring`) if it needs one. Any consumer can
|
|
8
|
+
* write its own convention module (paths + keyring) as a plain instance of
|
|
9
|
+
* this same shape; this preset is just the general default.
|
|
10
|
+
*/
|
|
11
|
+
import type { OpenAgentsConfigOptions } from "./config.js";
|
|
12
|
+
export declare const XDG_CONFIG_HOME_ENV_VAR = "XDG_CONFIG_HOME";
|
|
13
|
+
export type XdgAgentsConfigInput = {
|
|
14
|
+
readonly appName: string;
|
|
15
|
+
readonly homeDir: string;
|
|
16
|
+
readonly env: Readonly<Record<string, string | undefined>>;
|
|
17
|
+
};
|
|
18
|
+
export declare function resolveXdgAgentsConfigOptions(input: XdgAgentsConfigInput): OpenAgentsConfigOptions;
|
|
19
|
+
export declare function resolveXdgAgentsConfigRootDir(input: XdgAgentsConfigInput): string;
|
|
20
|
+
//# sourceMappingURL=xdg.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"xdg.d.ts","sourceRoot":"","sources":["../../src/config/xdg.ts"],"names":[],"mappings":"AAAA;;;;;;;;;GASG;AAGH,OAAO,KAAK,EAAE,uBAAuB,EAAE,MAAM,aAAa,CAAC;AAG3D,eAAO,MAAM,uBAAuB,oBAAoB,CAAC;AAIzD,MAAM,MAAM,oBAAoB,GAAG;IACjC,QAAQ,CAAC,OAAO,EAAE,MAAM,CAAC;IACzB,QAAQ,CAAC,OAAO,EAAE,MAAM,CAAC;IACzB,QAAQ,CAAC,GAAG,EAAE,QAAQ,CAAC,MAAM,CAAC,MAAM,EAAE,MAAM,GAAG,SAAS,CAAC,CAAC,CAAC;CAC5D,CAAC;AAEF,wBAAgB,6BAA6B,CAC3C,KAAK,EAAE,oBAAoB,GAC1B,uBAAuB,CAEzB;AAED,wBAAgB,6BAA6B,CAC3C,KAAK,EAAE,oBAAoB,GAC1B,MAAM,CAKR"}
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* A convention-neutral config preset for general OSS consumers: resolve
|
|
3
|
+
* the config root from the XDG Base Directory spec
|
|
4
|
+
* (`$XDG_CONFIG_HOME/<appName>/agents`, defaulting to
|
|
5
|
+
* `<homeDir>/.config/<appName>/agents`). It owns no secret-storage
|
|
6
|
+
* policy — the app supplies its own `secretResolvers` (e.g.
|
|
7
|
+
* `keyringResolver` from `/keyring`) if it needs one. Any consumer can
|
|
8
|
+
* write its own convention module (paths + keyring) as a plain instance of
|
|
9
|
+
* this same shape; this preset is just the general default.
|
|
10
|
+
*/
|
|
11
|
+
import path from "node:path";
|
|
12
|
+
import { readNonBlankEnvValue } from "./support.js";
|
|
13
|
+
export const XDG_CONFIG_HOME_ENV_VAR = "XDG_CONFIG_HOME";
|
|
14
|
+
const DEFAULT_XDG_CONFIG_DIRECTORY = ".config";
|
|
15
|
+
const AGENTS_CONFIG_SUBDIRECTORY = "agents";
|
|
16
|
+
export function resolveXdgAgentsConfigOptions(input) {
|
|
17
|
+
return { rootDir: resolveXdgAgentsConfigRootDir(input) };
|
|
18
|
+
}
|
|
19
|
+
export function resolveXdgAgentsConfigRootDir(input) {
|
|
20
|
+
const base = readNonBlankEnvValue(input.env, XDG_CONFIG_HOME_ENV_VAR) ??
|
|
21
|
+
path.join(input.homeDir, DEFAULT_XDG_CONFIG_DIRECTORY);
|
|
22
|
+
return path.join(base, input.appName, AGENTS_CONFIG_SUBDIRECTORY);
|
|
23
|
+
}
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Unbounded push-based async queue backing exec chunk streams and the
|
|
3
|
+
* run-handle event broadcast. Internal only.
|
|
4
|
+
*/
|
|
5
|
+
export declare class AsyncQueue<T> implements AsyncIterable<T> {
|
|
6
|
+
private readonly buffered;
|
|
7
|
+
private readonly waiters;
|
|
8
|
+
private ended;
|
|
9
|
+
push(value: T): void;
|
|
10
|
+
end(): void;
|
|
11
|
+
private next;
|
|
12
|
+
[Symbol.asyncIterator](): AsyncIterator<T>;
|
|
13
|
+
}
|
|
14
|
+
//# sourceMappingURL=async-queue.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"async-queue.d.ts","sourceRoot":"","sources":["../../src/core/async-queue.ts"],"names":[],"mappings":"AAAA;;;GAGG;AACH,qBAAa,UAAU,CAAC,CAAC,CAAE,YAAW,aAAa,CAAC,CAAC,CAAC;IACpD,OAAO,CAAC,QAAQ,CAAC,QAAQ,CAAW;IACpC,OAAO,CAAC,QAAQ,CAAC,OAAO,CAAkD;IAC1E,OAAO,CAAC,KAAK,CAAS;IAEtB,IAAI,CAAC,KAAK,EAAE,CAAC,GAAG,IAAI;IAYpB,GAAG,IAAI,IAAI;IAUX,OAAO,CAAC,IAAI;IAaZ,CAAC,MAAM,CAAC,aAAa,CAAC,IAAI,aAAa,CAAC,CAAC,CAAC;CAK3C"}
|
|
@@ -0,0 +1,46 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Unbounded push-based async queue backing exec chunk streams and the
|
|
3
|
+
* run-handle event broadcast. Internal only.
|
|
4
|
+
*/
|
|
5
|
+
export class AsyncQueue {
|
|
6
|
+
buffered = [];
|
|
7
|
+
waiters = [];
|
|
8
|
+
ended = false;
|
|
9
|
+
push(value) {
|
|
10
|
+
if (this.ended) {
|
|
11
|
+
return;
|
|
12
|
+
}
|
|
13
|
+
const waiter = this.waiters.shift();
|
|
14
|
+
if (waiter === undefined) {
|
|
15
|
+
this.buffered.push(value);
|
|
16
|
+
return;
|
|
17
|
+
}
|
|
18
|
+
waiter({ value, done: false });
|
|
19
|
+
}
|
|
20
|
+
end() {
|
|
21
|
+
if (this.ended) {
|
|
22
|
+
return;
|
|
23
|
+
}
|
|
24
|
+
this.ended = true;
|
|
25
|
+
for (const waiter of this.waiters.splice(0)) {
|
|
26
|
+
waiter({ value: undefined, done: true });
|
|
27
|
+
}
|
|
28
|
+
}
|
|
29
|
+
next() {
|
|
30
|
+
const value = this.buffered.shift();
|
|
31
|
+
if (value !== undefined) {
|
|
32
|
+
return Promise.resolve({ value, done: false });
|
|
33
|
+
}
|
|
34
|
+
if (this.ended) {
|
|
35
|
+
return Promise.resolve({ value: undefined, done: true });
|
|
36
|
+
}
|
|
37
|
+
return new Promise((resolve) => {
|
|
38
|
+
this.waiters.push(resolve);
|
|
39
|
+
});
|
|
40
|
+
}
|
|
41
|
+
[Symbol.asyncIterator]() {
|
|
42
|
+
return {
|
|
43
|
+
next: () => this.next(),
|
|
44
|
+
};
|
|
45
|
+
}
|
|
46
|
+
}
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Env mutation as data (design A8): activating one auth mechanism must be
|
|
3
|
+
* able to clear competing variables, so a patch carries both directions.
|
|
4
|
+
*/
|
|
5
|
+
export type EnvPatch = {
|
|
6
|
+
set: Record<string, string>;
|
|
7
|
+
unset: string[];
|
|
8
|
+
};
|
|
9
|
+
export declare const EMPTY_ENV_PATCH: EnvPatch;
|
|
10
|
+
export declare function applyEnvPatch(env: Record<string, string>, patch: EnvPatch): Record<string, string>;
|
|
11
|
+
export declare function mergeEnvPatches(first: EnvPatch, second: EnvPatch): EnvPatch;
|
|
12
|
+
/**
|
|
13
|
+
* Snapshot `process.env` as a defined-only `Record<string, string>` — the
|
|
14
|
+
* `baseEnv` shape `createAgentRuntime` and `runAgent` expect. Exposed so
|
|
15
|
+
* callers stop reaching for `process.env as Record<string, string>`, which
|
|
16
|
+
* lies about the `undefined` values Node keeps on the object.
|
|
17
|
+
*/
|
|
18
|
+
export declare function processEnv(): Record<string, string>;
|
|
19
|
+
//# sourceMappingURL=env.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"env.d.ts","sourceRoot":"","sources":["../../src/core/env.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAEH,MAAM,MAAM,QAAQ,GAAG;IACrB,GAAG,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;IAC5B,KAAK,EAAE,MAAM,EAAE,CAAC;CACjB,CAAC;AAGF,eAAO,MAAM,eAAe,EAAE,QAAgD,CAAC;AAI/E,wBAAgB,aAAa,CAC3B,GAAG,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,EAC3B,KAAK,EAAE,QAAQ,GACd,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CASxB;AAED,wBAAgB,eAAe,CAAC,KAAK,EAAE,QAAQ,EAAE,MAAM,EAAE,QAAQ,GAAG,QAAQ,CAK3E;AAED;;;;;GAKG;AACH,wBAAgB,UAAU,IAAI,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAQnD"}
|