poe-code 3.0.99-beta.1 → 3.0.100
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/dist/cli/commands/login.js +2 -4
- package/dist/cli/commands/login.js.map +1 -1
- package/dist/cli/container.js +9 -9
- package/dist/cli/container.js.map +1 -1
- package/dist/cli/oauth-login.js +1 -1
- package/dist/cli/oauth-login.js.map +1 -1
- package/dist/index.js +552 -652
- package/dist/index.js.map +4 -4
- package/dist/providers/claude-code.js +1 -1
- package/dist/providers/claude-code.js.map +1 -1
- package/dist/providers/codex.js +1 -1
- package/dist/providers/codex.js.map +1 -1
- package/dist/providers/kimi.js +1 -1
- package/dist/providers/kimi.js.map +1 -1
- package/dist/providers/opencode.js +1 -1
- package/dist/providers/opencode.js.map +1 -1
- package/dist/providers/poe-agent.js +95 -253
- package/dist/providers/poe-agent.js.map +4 -4
- package/dist/sdk/container.js +9 -9
- package/dist/sdk/container.js.map +1 -1
- package/dist/sdk/credentials.d.ts +1 -1
- package/dist/sdk/credentials.js +11 -4
- package/dist/sdk/credentials.js.map +1 -1
- package/package.json +3 -2
package/dist/index.js
CHANGED
|
@@ -31,7 +31,7 @@ var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__ge
|
|
|
31
31
|
mod
|
|
32
32
|
));
|
|
33
33
|
|
|
34
|
-
// packages/
|
|
34
|
+
// packages/auth-store/src/encrypted-file-store.ts
|
|
35
35
|
import { createCipheriv, createDecipheriv, randomBytes, scrypt } from "node:crypto";
|
|
36
36
|
import { promises as fs } from "node:fs";
|
|
37
37
|
import { homedir, hostname, userInfo } from "node:os";
|
|
@@ -42,11 +42,11 @@ function defaultMachineIdentity() {
|
|
|
42
42
|
username: userInfo().username
|
|
43
43
|
};
|
|
44
44
|
}
|
|
45
|
-
async function deriveEncryptionKey(getMachineIdentity) {
|
|
45
|
+
async function deriveEncryptionKey(getMachineIdentity, salt) {
|
|
46
46
|
const machineIdentity = await getMachineIdentity();
|
|
47
47
|
const secret = `${machineIdentity.hostname}:${machineIdentity.username}`;
|
|
48
48
|
return await new Promise((resolve, reject) => {
|
|
49
|
-
scrypt(secret,
|
|
49
|
+
scrypt(secret, salt, ENCRYPTION_KEY_BYTES, (error2, derivedKey) => {
|
|
50
50
|
if (error2) {
|
|
51
51
|
reject(error2);
|
|
52
52
|
return;
|
|
@@ -85,34 +85,35 @@ function isNotFoundError(error2) {
|
|
|
85
85
|
error2 && typeof error2 === "object" && "code" in error2 && error2.code === "ENOENT"
|
|
86
86
|
);
|
|
87
87
|
}
|
|
88
|
-
var ENCRYPTION_ALGORITHM, ENCRYPTION_VERSION, ENCRYPTION_KEY_BYTES, ENCRYPTION_IV_BYTES, ENCRYPTION_AUTH_TAG_BYTES,
|
|
89
|
-
var
|
|
90
|
-
"packages/
|
|
88
|
+
var ENCRYPTION_ALGORITHM, ENCRYPTION_VERSION, ENCRYPTION_KEY_BYTES, ENCRYPTION_IV_BYTES, ENCRYPTION_AUTH_TAG_BYTES, ENCRYPTION_FILE_MODE, EncryptedFileStore;
|
|
89
|
+
var init_encrypted_file_store = __esm({
|
|
90
|
+
"packages/auth-store/src/encrypted-file-store.ts"() {
|
|
91
91
|
"use strict";
|
|
92
92
|
ENCRYPTION_ALGORITHM = "aes-256-gcm";
|
|
93
93
|
ENCRYPTION_VERSION = 1;
|
|
94
94
|
ENCRYPTION_KEY_BYTES = 32;
|
|
95
95
|
ENCRYPTION_IV_BYTES = 12;
|
|
96
96
|
ENCRYPTION_AUTH_TAG_BYTES = 16;
|
|
97
|
-
ENCRYPTION_SALT = "poe-code:encrypted-file-auth-store:v1";
|
|
98
97
|
ENCRYPTION_FILE_MODE = 384;
|
|
99
|
-
|
|
98
|
+
EncryptedFileStore = class {
|
|
100
99
|
fs;
|
|
101
100
|
filePath;
|
|
101
|
+
salt;
|
|
102
102
|
getMachineIdentity;
|
|
103
103
|
getRandomBytes;
|
|
104
104
|
keyPromise = null;
|
|
105
|
-
constructor(input
|
|
105
|
+
constructor(input) {
|
|
106
106
|
this.fs = input.fs ?? fs;
|
|
107
|
+
this.salt = input.salt;
|
|
107
108
|
this.filePath = input.filePath ?? path.join(
|
|
108
109
|
(input.getHomeDirectory ?? homedir)(),
|
|
109
|
-
".
|
|
110
|
-
"credentials.enc"
|
|
110
|
+
input.defaultDirectory ?? ".auth-store",
|
|
111
|
+
input.defaultFileName ?? "credentials.enc"
|
|
111
112
|
);
|
|
112
113
|
this.getMachineIdentity = input.getMachineIdentity ?? defaultMachineIdentity;
|
|
113
114
|
this.getRandomBytes = input.getRandomBytes ?? randomBytes;
|
|
114
115
|
}
|
|
115
|
-
async
|
|
116
|
+
async get() {
|
|
116
117
|
let rawDocument;
|
|
117
118
|
try {
|
|
118
119
|
rawDocument = await this.fs.readFile(this.filePath, "utf8");
|
|
@@ -142,12 +143,12 @@ var init_encrypted_file_auth_store = __esm({
|
|
|
142
143
|
return null;
|
|
143
144
|
}
|
|
144
145
|
}
|
|
145
|
-
async
|
|
146
|
+
async set(value) {
|
|
146
147
|
const key = await this.getEncryptionKey();
|
|
147
148
|
const iv = this.getRandomBytes(ENCRYPTION_IV_BYTES);
|
|
148
149
|
const cipher = createCipheriv(ENCRYPTION_ALGORITHM, key, iv);
|
|
149
150
|
const ciphertext = Buffer.concat([
|
|
150
|
-
cipher.update(
|
|
151
|
+
cipher.update(value, "utf8"),
|
|
151
152
|
cipher.final()
|
|
152
153
|
]);
|
|
153
154
|
const authTag = cipher.getAuthTag();
|
|
@@ -163,7 +164,7 @@ var init_encrypted_file_auth_store = __esm({
|
|
|
163
164
|
});
|
|
164
165
|
await this.fs.chmod(this.filePath, ENCRYPTION_FILE_MODE);
|
|
165
166
|
}
|
|
166
|
-
async
|
|
167
|
+
async delete() {
|
|
167
168
|
try {
|
|
168
169
|
await this.fs.unlink(this.filePath);
|
|
169
170
|
} catch (error2) {
|
|
@@ -174,7 +175,7 @@ var init_encrypted_file_auth_store = __esm({
|
|
|
174
175
|
}
|
|
175
176
|
getEncryptionKey() {
|
|
176
177
|
if (!this.keyPromise) {
|
|
177
|
-
this.keyPromise = deriveEncryptionKey(this.getMachineIdentity);
|
|
178
|
+
this.keyPromise = deriveEncryptionKey(this.getMachineIdentity, this.salt);
|
|
178
179
|
}
|
|
179
180
|
return this.keyPromise;
|
|
180
181
|
}
|
|
@@ -182,7 +183,7 @@ var init_encrypted_file_auth_store = __esm({
|
|
|
182
183
|
}
|
|
183
184
|
});
|
|
184
185
|
|
|
185
|
-
// packages/
|
|
186
|
+
// packages/auth-store/src/keychain-store.ts
|
|
186
187
|
import { spawn } from "node:child_process";
|
|
187
188
|
function runSecurityCommand(command, args) {
|
|
188
189
|
return new Promise((resolve) => {
|
|
@@ -242,27 +243,25 @@ function createSecurityCliFailure(operation, result) {
|
|
|
242
243
|
}
|
|
243
244
|
return new Error(`Failed to ${operation}: security exited with code ${result.exitCode}`);
|
|
244
245
|
}
|
|
245
|
-
var SECURITY_CLI,
|
|
246
|
-
var
|
|
247
|
-
"packages/
|
|
246
|
+
var SECURITY_CLI, KEYCHAIN_ITEM_NOT_FOUND_EXIT_CODE, KeychainStore;
|
|
247
|
+
var init_keychain_store = __esm({
|
|
248
|
+
"packages/auth-store/src/keychain-store.ts"() {
|
|
248
249
|
"use strict";
|
|
249
250
|
SECURITY_CLI = "security";
|
|
250
|
-
KEYCHAIN_SERVICE = "poe-code";
|
|
251
|
-
KEYCHAIN_ACCOUNT = "api-key";
|
|
252
251
|
KEYCHAIN_ITEM_NOT_FOUND_EXIT_CODE = 44;
|
|
253
|
-
|
|
252
|
+
KeychainStore = class {
|
|
254
253
|
runCommand;
|
|
255
254
|
service;
|
|
256
255
|
account;
|
|
257
|
-
constructor(input
|
|
256
|
+
constructor(input) {
|
|
258
257
|
this.runCommand = input.runCommand ?? runSecurityCommand;
|
|
259
|
-
this.service = input.service
|
|
260
|
-
this.account = input.account
|
|
258
|
+
this.service = input.service;
|
|
259
|
+
this.account = input.account;
|
|
261
260
|
}
|
|
262
|
-
async
|
|
261
|
+
async get() {
|
|
263
262
|
const result = await this.executeSecurityCommand(
|
|
264
263
|
["find-generic-password", "-s", this.service, "-a", this.account, "-w"],
|
|
265
|
-
"read
|
|
264
|
+
"read secret from macOS Keychain"
|
|
266
265
|
);
|
|
267
266
|
if (result.exitCode === 0) {
|
|
268
267
|
return stripTrailingLineBreak(result.stdout);
|
|
@@ -270,9 +269,9 @@ var init_keychain_auth_store = __esm({
|
|
|
270
269
|
if (isKeychainEntryNotFound(result)) {
|
|
271
270
|
return null;
|
|
272
271
|
}
|
|
273
|
-
throw createSecurityCliFailure("read
|
|
272
|
+
throw createSecurityCliFailure("read secret from macOS Keychain", result);
|
|
274
273
|
}
|
|
275
|
-
async
|
|
274
|
+
async set(value) {
|
|
276
275
|
const result = await this.executeSecurityCommand(
|
|
277
276
|
[
|
|
278
277
|
"add-generic-password",
|
|
@@ -281,24 +280,24 @@ var init_keychain_auth_store = __esm({
|
|
|
281
280
|
"-a",
|
|
282
281
|
this.account,
|
|
283
282
|
"-w",
|
|
284
|
-
|
|
283
|
+
value,
|
|
285
284
|
"-U"
|
|
286
285
|
],
|
|
287
|
-
"store
|
|
286
|
+
"store secret in macOS Keychain"
|
|
288
287
|
);
|
|
289
288
|
if (result.exitCode !== 0) {
|
|
290
|
-
throw createSecurityCliFailure("store
|
|
289
|
+
throw createSecurityCliFailure("store secret in macOS Keychain", result);
|
|
291
290
|
}
|
|
292
291
|
}
|
|
293
|
-
async
|
|
292
|
+
async delete() {
|
|
294
293
|
const result = await this.executeSecurityCommand(
|
|
295
294
|
["delete-generic-password", "-s", this.service, "-a", this.account],
|
|
296
|
-
"delete
|
|
295
|
+
"delete secret from macOS Keychain"
|
|
297
296
|
);
|
|
298
297
|
if (result.exitCode === 0 || isKeychainEntryNotFound(result)) {
|
|
299
298
|
return;
|
|
300
299
|
}
|
|
301
|
-
throw createSecurityCliFailure("delete
|
|
300
|
+
throw createSecurityCliFailure("delete secret from macOS Keychain", result);
|
|
302
301
|
}
|
|
303
302
|
async executeSecurityCommand(args, operation) {
|
|
304
303
|
try {
|
|
@@ -312,382 +311,58 @@ var init_keychain_auth_store = __esm({
|
|
|
312
311
|
}
|
|
313
312
|
});
|
|
314
313
|
|
|
315
|
-
// packages/
|
|
316
|
-
|
|
317
|
-
import { homedir as homedir2 } from "node:os";
|
|
318
|
-
import path2 from "node:path";
|
|
319
|
-
function createAuthStore(input = {}) {
|
|
314
|
+
// packages/auth-store/src/create-secret-store.ts
|
|
315
|
+
function createSecretStore(input) {
|
|
320
316
|
const backend = resolveBackend(input);
|
|
321
317
|
const platform = input.platform ?? process.platform;
|
|
322
318
|
if (backend === "keychain" && platform !== MACOS_PLATFORM) {
|
|
323
319
|
throw new Error(
|
|
324
|
-
`
|
|
320
|
+
`Keychain backend is only supported on macOS. Current platform: ${platform}`
|
|
325
321
|
);
|
|
326
322
|
}
|
|
327
|
-
const store =
|
|
328
|
-
return {
|
|
329
|
-
backend,
|
|
330
|
-
store: enableLegacyCredentialsMigration(store, input)
|
|
331
|
-
};
|
|
323
|
+
const store = storeFactories[backend](input);
|
|
324
|
+
return { backend, store };
|
|
332
325
|
}
|
|
333
326
|
function resolveBackend(input) {
|
|
334
|
-
const
|
|
327
|
+
const envVar = input.backendEnvVar ?? DEFAULT_BACKEND_ENV_VAR;
|
|
328
|
+
const configuredBackend = input.backend ?? input.env?.[envVar] ?? process.env[envVar];
|
|
335
329
|
if (configuredBackend === "keychain") {
|
|
336
330
|
return "keychain";
|
|
337
331
|
}
|
|
338
332
|
return "file";
|
|
339
333
|
}
|
|
340
|
-
|
|
341
|
-
|
|
342
|
-
|
|
343
|
-
let hasCheckedLegacyCredentials = false;
|
|
344
|
-
let legacyMigrationPromise = null;
|
|
345
|
-
store.getApiKey = async () => {
|
|
346
|
-
const storedApiKey = await readApiKeyFromStore();
|
|
347
|
-
if (isNonEmptyString(storedApiKey)) {
|
|
348
|
-
return storedApiKey;
|
|
349
|
-
}
|
|
350
|
-
if (hasCheckedLegacyCredentials) {
|
|
351
|
-
return null;
|
|
352
|
-
}
|
|
353
|
-
if (!legacyMigrationPromise) {
|
|
354
|
-
legacyMigrationPromise = migrateLegacyApiKey(store, migrationContext).finally(() => {
|
|
355
|
-
hasCheckedLegacyCredentials = true;
|
|
356
|
-
legacyMigrationPromise = null;
|
|
357
|
-
});
|
|
358
|
-
}
|
|
359
|
-
return legacyMigrationPromise;
|
|
360
|
-
};
|
|
361
|
-
return store;
|
|
362
|
-
}
|
|
363
|
-
async function migrateLegacyApiKey(store, migrationContext) {
|
|
364
|
-
const legacyCredentials = await loadLegacyCredentials(
|
|
365
|
-
migrationContext.fs,
|
|
366
|
-
migrationContext.filePath
|
|
367
|
-
);
|
|
368
|
-
if (!legacyCredentials || !isNonEmptyString(legacyCredentials.apiKey)) {
|
|
369
|
-
return null;
|
|
370
|
-
}
|
|
371
|
-
const plaintextApiKey = legacyCredentials.apiKey;
|
|
372
|
-
try {
|
|
373
|
-
await store.setApiKey(plaintextApiKey);
|
|
374
|
-
delete legacyCredentials.apiKey;
|
|
375
|
-
await saveLegacyCredentials(
|
|
376
|
-
migrationContext.fs,
|
|
377
|
-
migrationContext.filePath,
|
|
378
|
-
legacyCredentials
|
|
379
|
-
);
|
|
380
|
-
} catch (error2) {
|
|
381
|
-
migrationContext.logWarning(
|
|
382
|
-
`Failed to migrate plaintext API key from ${migrationContext.filePath}.`,
|
|
383
|
-
error2
|
|
384
|
-
);
|
|
385
|
-
}
|
|
386
|
-
return plaintextApiKey;
|
|
387
|
-
}
|
|
388
|
-
function createLegacyMigrationContext(input) {
|
|
389
|
-
const legacyCredentialsInput = input.legacyCredentials;
|
|
390
|
-
const getHomeDirectory = legacyCredentialsInput?.getHomeDirectory ?? homedir2;
|
|
391
|
-
return {
|
|
392
|
-
fs: legacyCredentialsInput?.fs ?? input.fileStore?.fs ?? nodeFs,
|
|
393
|
-
filePath: legacyCredentialsInput?.filePath ?? path2.join(
|
|
394
|
-
getHomeDirectory(),
|
|
395
|
-
LEGACY_CREDENTIALS_RELATIVE_PATH
|
|
396
|
-
),
|
|
397
|
-
logWarning: legacyCredentialsInput?.logWarning ?? defaultMigrationWarning
|
|
398
|
-
};
|
|
399
|
-
}
|
|
400
|
-
async function loadLegacyCredentials(fs3, filePath) {
|
|
401
|
-
let raw;
|
|
402
|
-
try {
|
|
403
|
-
raw = await fs3.readFile(filePath, "utf8");
|
|
404
|
-
} catch (error2) {
|
|
405
|
-
if (isNotFoundError2(error2)) {
|
|
406
|
-
return null;
|
|
407
|
-
}
|
|
408
|
-
return null;
|
|
409
|
-
}
|
|
410
|
-
try {
|
|
411
|
-
const parsed = JSON.parse(raw);
|
|
412
|
-
if (!isRecord2(parsed)) {
|
|
413
|
-
return null;
|
|
414
|
-
}
|
|
415
|
-
return parsed;
|
|
416
|
-
} catch {
|
|
417
|
-
return null;
|
|
418
|
-
}
|
|
419
|
-
}
|
|
420
|
-
async function saveLegacyCredentials(fs3, filePath, document) {
|
|
421
|
-
await fs3.mkdir(path2.dirname(filePath), { recursive: true });
|
|
422
|
-
await fs3.writeFile(filePath, `${JSON.stringify(document, null, 2)}
|
|
423
|
-
`, {
|
|
424
|
-
encoding: "utf8"
|
|
425
|
-
});
|
|
426
|
-
}
|
|
427
|
-
function defaultMigrationWarning(message, error2) {
|
|
428
|
-
const details = toErrorDetails(error2);
|
|
429
|
-
if (details.length > 0) {
|
|
430
|
-
console.warn(`${message} ${details}`);
|
|
431
|
-
return;
|
|
432
|
-
}
|
|
433
|
-
console.warn(message);
|
|
434
|
-
}
|
|
435
|
-
function toErrorDetails(error2) {
|
|
436
|
-
if (error2 instanceof Error) {
|
|
437
|
-
return error2.message;
|
|
438
|
-
}
|
|
439
|
-
return typeof error2 === "string" ? error2 : "";
|
|
440
|
-
}
|
|
441
|
-
function isNonEmptyString(value) {
|
|
442
|
-
return typeof value === "string" && value.length > 0;
|
|
443
|
-
}
|
|
444
|
-
function isRecord2(value) {
|
|
445
|
-
return Boolean(value && typeof value === "object" && !Array.isArray(value));
|
|
446
|
-
}
|
|
447
|
-
function isNotFoundError2(error2) {
|
|
448
|
-
return Boolean(
|
|
449
|
-
error2 && typeof error2 === "object" && "code" in error2 && error2.code === "ENOENT"
|
|
450
|
-
);
|
|
451
|
-
}
|
|
452
|
-
var AUTH_BACKEND_ENV_VAR, MACOS_PLATFORM, LEGACY_CREDENTIALS_RELATIVE_PATH, authStoreFactories;
|
|
453
|
-
var init_create_auth_store = __esm({
|
|
454
|
-
"packages/poe-auth/src/create-auth-store.ts"() {
|
|
334
|
+
var DEFAULT_BACKEND_ENV_VAR, MACOS_PLATFORM, storeFactories;
|
|
335
|
+
var init_create_secret_store = __esm({
|
|
336
|
+
"packages/auth-store/src/create-secret-store.ts"() {
|
|
455
337
|
"use strict";
|
|
456
|
-
|
|
457
|
-
|
|
458
|
-
|
|
338
|
+
init_encrypted_file_store();
|
|
339
|
+
init_keychain_store();
|
|
340
|
+
DEFAULT_BACKEND_ENV_VAR = "AUTH_BACKEND";
|
|
459
341
|
MACOS_PLATFORM = "darwin";
|
|
460
|
-
|
|
461
|
-
|
|
462
|
-
|
|
463
|
-
|
|
464
|
-
|
|
465
|
-
|
|
466
|
-
}
|
|
467
|
-
|
|
468
|
-
|
|
469
|
-
|
|
470
|
-
|
|
471
|
-
|
|
472
|
-
init_create_auth_store();
|
|
473
|
-
}
|
|
474
|
-
});
|
|
475
|
-
|
|
476
|
-
// packages/poe-auth/src/get-token.ts
|
|
477
|
-
var init_get_token = __esm({
|
|
478
|
-
"packages/poe-auth/src/get-token.ts"() {
|
|
479
|
-
"use strict";
|
|
480
|
-
init_create_auth_store();
|
|
481
|
-
}
|
|
482
|
-
});
|
|
483
|
-
|
|
484
|
-
// packages/poe-auth/src/api-key-validation.ts
|
|
485
|
-
var init_api_key_validation = __esm({
|
|
486
|
-
"packages/poe-auth/src/api-key-validation.ts"() {
|
|
487
|
-
"use strict";
|
|
488
|
-
}
|
|
489
|
-
});
|
|
490
|
-
|
|
491
|
-
// packages/poe-auth/src/oauth-client.ts
|
|
492
|
-
import http from "node:http";
|
|
493
|
-
import crypto from "node:crypto";
|
|
494
|
-
function createOAuthClient(config2) {
|
|
495
|
-
const fetchFn = config2.fetch ?? globalThis.fetch;
|
|
496
|
-
return {
|
|
497
|
-
authorize: () => startAuthorization(config2, fetchFn)
|
|
498
|
-
};
|
|
499
|
-
}
|
|
500
|
-
function generateCodeVerifier() {
|
|
501
|
-
return crypto.randomBytes(32).toString("base64url");
|
|
502
|
-
}
|
|
503
|
-
function generateCodeChallenge(verifier) {
|
|
504
|
-
return crypto.createHash("sha256").update(verifier).digest("base64url");
|
|
505
|
-
}
|
|
506
|
-
async function startAuthorization(config2, fetchFn) {
|
|
507
|
-
const codeVerifier = generateCodeVerifier();
|
|
508
|
-
const codeChallenge = generateCodeChallenge(codeVerifier);
|
|
509
|
-
const server = config2.createServer ? config2.createServer() : http.createServer();
|
|
510
|
-
const port = await startServer(server);
|
|
511
|
-
const redirectUri = `http://127.0.0.1:${port}/callback`;
|
|
512
|
-
const authorizationUrl = buildAuthorizationUrl({
|
|
513
|
-
endpoint: config2.authorizationEndpoint,
|
|
514
|
-
clientId: config2.clientId,
|
|
515
|
-
redirectUri,
|
|
516
|
-
codeChallenge
|
|
517
|
-
});
|
|
518
|
-
const waitForResult = async () => {
|
|
519
|
-
try {
|
|
520
|
-
const code = await waitForAuthorizationCode(server, config2, authorizationUrl);
|
|
521
|
-
return await exchangeCodeForApiKey({
|
|
522
|
-
tokenEndpoint: config2.tokenEndpoint,
|
|
523
|
-
code,
|
|
524
|
-
codeVerifier,
|
|
525
|
-
clientId: config2.clientId,
|
|
526
|
-
redirectUri,
|
|
527
|
-
fetchFn
|
|
528
|
-
});
|
|
529
|
-
} finally {
|
|
530
|
-
server.closeAllConnections?.();
|
|
531
|
-
server.close();
|
|
532
|
-
}
|
|
533
|
-
};
|
|
534
|
-
return { authorizationUrl, waitForResult };
|
|
535
|
-
}
|
|
536
|
-
function startServer(server) {
|
|
537
|
-
return new Promise((resolve) => {
|
|
538
|
-
server.listen(0, "127.0.0.1", () => {
|
|
539
|
-
const address = server.address();
|
|
540
|
-
resolve(address.port);
|
|
541
|
-
});
|
|
542
|
-
});
|
|
543
|
-
}
|
|
544
|
-
function buildAuthorizationUrl(params) {
|
|
545
|
-
const url2 = new URL(params.endpoint);
|
|
546
|
-
url2.searchParams.set("response_type", "code");
|
|
547
|
-
url2.searchParams.set("client_id", params.clientId);
|
|
548
|
-
url2.searchParams.set("scope", "apikey:create");
|
|
549
|
-
url2.searchParams.set("code_challenge", params.codeChallenge);
|
|
550
|
-
url2.searchParams.set("code_challenge_method", "S256");
|
|
551
|
-
url2.searchParams.set("redirect_uri", params.redirectUri);
|
|
552
|
-
return url2.toString();
|
|
553
|
-
}
|
|
554
|
-
function waitForAuthorizationCode(server, config2, authorizationUrl) {
|
|
555
|
-
return new Promise((resolve, reject) => {
|
|
556
|
-
let settled = false;
|
|
557
|
-
const settle = (fn) => {
|
|
558
|
-
if (!settled) {
|
|
559
|
-
settled = true;
|
|
560
|
-
fn();
|
|
342
|
+
storeFactories = {
|
|
343
|
+
file: (input) => {
|
|
344
|
+
if (!input.fileStore) {
|
|
345
|
+
throw new Error("fileStore configuration is required for file backend");
|
|
346
|
+
}
|
|
347
|
+
return new EncryptedFileStore(input.fileStore);
|
|
348
|
+
},
|
|
349
|
+
keychain: (input) => {
|
|
350
|
+
if (!input.keychainStore) {
|
|
351
|
+
throw new Error("keychainStore configuration is required for keychain backend");
|
|
352
|
+
}
|
|
353
|
+
return new KeychainStore(input.keychainStore);
|
|
561
354
|
}
|
|
562
355
|
};
|
|
563
|
-
server.on("request", (req, res) => {
|
|
564
|
-
const url2 = new URL(req.url, `http://127.0.0.1`);
|
|
565
|
-
if (url2.pathname !== "/callback") {
|
|
566
|
-
res.writeHead(404);
|
|
567
|
-
res.end("Not found");
|
|
568
|
-
return;
|
|
569
|
-
}
|
|
570
|
-
const error2 = url2.searchParams.get("error");
|
|
571
|
-
if (error2) {
|
|
572
|
-
const description = url2.searchParams.get("error_description") ?? error2;
|
|
573
|
-
res.writeHead(400);
|
|
574
|
-
res.end(`Authorization failed: ${description}`);
|
|
575
|
-
settle(() => reject(new Error(`OAuth authorization failed: ${error2} \u2014 ${description}`)));
|
|
576
|
-
return;
|
|
577
|
-
}
|
|
578
|
-
const code = url2.searchParams.get("code");
|
|
579
|
-
if (!code) {
|
|
580
|
-
res.writeHead(400);
|
|
581
|
-
res.end("Missing authorization code");
|
|
582
|
-
settle(() => reject(new Error("OAuth callback missing authorization code")));
|
|
583
|
-
return;
|
|
584
|
-
}
|
|
585
|
-
res.writeHead(200, { "Content-Type": "text/html" });
|
|
586
|
-
res.end(buildSuccessPage());
|
|
587
|
-
settle(() => resolve(code));
|
|
588
|
-
});
|
|
589
|
-
if (config2.readLine) {
|
|
590
|
-
config2.readLine().then((input) => {
|
|
591
|
-
const code = extractCodeFromInput(input);
|
|
592
|
-
if (code) {
|
|
593
|
-
settle(() => resolve(code));
|
|
594
|
-
}
|
|
595
|
-
}).catch(() => {
|
|
596
|
-
});
|
|
597
|
-
}
|
|
598
|
-
if (config2.openBrowser) {
|
|
599
|
-
config2.openBrowser(authorizationUrl).catch(
|
|
600
|
-
(err) => settle(() => reject(err))
|
|
601
|
-
);
|
|
602
|
-
}
|
|
603
|
-
});
|
|
604
|
-
}
|
|
605
|
-
function extractCodeFromInput(input) {
|
|
606
|
-
const trimmed = input.replace(/[\r\n]/g, "").trim();
|
|
607
|
-
if (trimmed.length === 0) {
|
|
608
|
-
return null;
|
|
609
|
-
}
|
|
610
|
-
try {
|
|
611
|
-
const url2 = new URL(trimmed);
|
|
612
|
-
return url2.searchParams.get("code");
|
|
613
|
-
} catch {
|
|
614
|
-
return trimmed;
|
|
615
|
-
}
|
|
616
|
-
}
|
|
617
|
-
async function exchangeCodeForApiKey(params) {
|
|
618
|
-
const body = new URLSearchParams({
|
|
619
|
-
grant_type: "authorization_code",
|
|
620
|
-
code: params.code,
|
|
621
|
-
code_verifier: params.codeVerifier,
|
|
622
|
-
client_id: params.clientId,
|
|
623
|
-
redirect_uri: params.redirectUri
|
|
624
|
-
});
|
|
625
|
-
const response = await params.fetchFn(params.tokenEndpoint, {
|
|
626
|
-
method: "POST",
|
|
627
|
-
headers: { "Content-Type": "application/x-www-form-urlencoded" },
|
|
628
|
-
body: body.toString()
|
|
629
|
-
});
|
|
630
|
-
if (!response.ok) {
|
|
631
|
-
const text4 = await response.text();
|
|
632
|
-
throw new Error(`Token exchange failed (${response.status}): ${text4}`);
|
|
633
|
-
}
|
|
634
|
-
const data = await response.json();
|
|
635
|
-
if (typeof data.api_key !== "string" || data.api_key.length === 0) {
|
|
636
|
-
throw new Error("Token response missing api_key field");
|
|
637
|
-
}
|
|
638
|
-
return {
|
|
639
|
-
apiKey: data.api_key,
|
|
640
|
-
expiresIn: typeof data.api_key_expires_in === "number" ? data.api_key_expires_in : null
|
|
641
|
-
};
|
|
642
|
-
}
|
|
643
|
-
function buildSuccessPage() {
|
|
644
|
-
return [
|
|
645
|
-
"<!DOCTYPE html>",
|
|
646
|
-
"<html><head><meta charset=utf-8><title>Connected to Poe</title></head>",
|
|
647
|
-
'<body style="font-family:system-ui,sans-serif;display:flex;align-items:center;justify-content:center;min-height:100vh;margin:0">',
|
|
648
|
-
'<div style="text-align:center">',
|
|
649
|
-
"<h1>Connected to Poe</h1>",
|
|
650
|
-
'<p style="color:#666">You can close this tab and return to your terminal.</p>',
|
|
651
|
-
"</div></body></html>"
|
|
652
|
-
].join("");
|
|
653
|
-
}
|
|
654
|
-
var init_oauth_client = __esm({
|
|
655
|
-
"packages/poe-auth/src/oauth-client.ts"() {
|
|
656
|
-
"use strict";
|
|
657
|
-
}
|
|
658
|
-
});
|
|
659
|
-
|
|
660
|
-
// packages/poe-auth/src/login.ts
|
|
661
|
-
var init_login = __esm({
|
|
662
|
-
"packages/poe-auth/src/login.ts"() {
|
|
663
|
-
"use strict";
|
|
664
|
-
init_api_key_validation();
|
|
665
|
-
init_create_auth_store();
|
|
666
|
-
init_oauth_client();
|
|
667
|
-
}
|
|
668
|
-
});
|
|
669
|
-
|
|
670
|
-
// packages/poe-auth/src/logout.ts
|
|
671
|
-
var init_logout = __esm({
|
|
672
|
-
"packages/poe-auth/src/logout.ts"() {
|
|
673
|
-
"use strict";
|
|
674
|
-
init_create_auth_store();
|
|
675
356
|
}
|
|
676
357
|
});
|
|
677
358
|
|
|
678
|
-
// packages/
|
|
359
|
+
// packages/auth-store/src/index.ts
|
|
679
360
|
var init_src = __esm({
|
|
680
|
-
"packages/
|
|
361
|
+
"packages/auth-store/src/index.ts"() {
|
|
681
362
|
"use strict";
|
|
682
|
-
|
|
683
|
-
|
|
684
|
-
|
|
685
|
-
init_api_key_validation();
|
|
686
|
-
init_login();
|
|
687
|
-
init_logout();
|
|
688
|
-
init_oauth_client();
|
|
689
|
-
init_encrypted_file_auth_store();
|
|
690
|
-
init_keychain_auth_store();
|
|
363
|
+
init_create_secret_store();
|
|
364
|
+
init_encrypted_file_store();
|
|
365
|
+
init_keychain_store();
|
|
691
366
|
}
|
|
692
367
|
});
|
|
693
368
|
|
|
@@ -697,8 +372,15 @@ async function getPoeApiKey() {
|
|
|
697
372
|
if (typeof envKey === "string" && envKey.trim().length > 0) {
|
|
698
373
|
return envKey.trim();
|
|
699
374
|
}
|
|
700
|
-
const { store } =
|
|
701
|
-
|
|
375
|
+
const { store } = createSecretStore({
|
|
376
|
+
backendEnvVar: "POE_AUTH_BACKEND",
|
|
377
|
+
fileStore: {
|
|
378
|
+
salt: "poe-code:encrypted-file-auth-store:v1",
|
|
379
|
+
defaultDirectory: ".poe-code",
|
|
380
|
+
defaultFileName: "credentials.enc"
|
|
381
|
+
}
|
|
382
|
+
});
|
|
383
|
+
const storedKey = await store.get();
|
|
702
384
|
if (typeof storedKey === "string" && storedKey.trim().length > 0) {
|
|
703
385
|
return storedKey.trim();
|
|
704
386
|
}
|
|
@@ -1032,16 +714,16 @@ function getConfigFormat(pathOrFormat) {
|
|
|
1032
714
|
}
|
|
1033
715
|
return formatRegistry[formatName];
|
|
1034
716
|
}
|
|
1035
|
-
function detectFormat(
|
|
1036
|
-
const ext = getExtension(
|
|
717
|
+
function detectFormat(path24) {
|
|
718
|
+
const ext = getExtension(path24);
|
|
1037
719
|
return extensionMap[ext];
|
|
1038
720
|
}
|
|
1039
|
-
function getExtension(
|
|
1040
|
-
const lastDot =
|
|
721
|
+
function getExtension(path24) {
|
|
722
|
+
const lastDot = path24.lastIndexOf(".");
|
|
1041
723
|
if (lastDot === -1) {
|
|
1042
724
|
return "";
|
|
1043
725
|
}
|
|
1044
|
-
return
|
|
726
|
+
return path24.slice(lastDot).toLowerCase();
|
|
1045
727
|
}
|
|
1046
728
|
var formatRegistry, extensionMap;
|
|
1047
729
|
var init_formats = __esm({
|
|
@@ -1063,7 +745,7 @@ var init_formats = __esm({
|
|
|
1063
745
|
});
|
|
1064
746
|
|
|
1065
747
|
// packages/config-mutations/src/execution/path-utils.ts
|
|
1066
|
-
import
|
|
748
|
+
import path2 from "node:path";
|
|
1067
749
|
function expandHome(targetPath, homeDir) {
|
|
1068
750
|
if (!targetPath?.startsWith("~")) {
|
|
1069
751
|
return targetPath;
|
|
@@ -1080,7 +762,7 @@ function expandHome(targetPath, homeDir) {
|
|
|
1080
762
|
remainder = remainder.slice(1);
|
|
1081
763
|
}
|
|
1082
764
|
}
|
|
1083
|
-
return remainder.length === 0 ? homeDir :
|
|
765
|
+
return remainder.length === 0 ? homeDir : path2.join(homeDir, remainder);
|
|
1084
766
|
}
|
|
1085
767
|
function validateHomePath(targetPath) {
|
|
1086
768
|
if (typeof targetPath !== "string" || targetPath.length === 0) {
|
|
@@ -1098,12 +780,12 @@ function resolvePath(rawPath, homeDir, pathMapper) {
|
|
|
1098
780
|
if (!pathMapper) {
|
|
1099
781
|
return expanded;
|
|
1100
782
|
}
|
|
1101
|
-
const rawDirectory =
|
|
783
|
+
const rawDirectory = path2.dirname(expanded);
|
|
1102
784
|
const mappedDirectory = pathMapper.mapTargetDirectory({
|
|
1103
785
|
targetDirectory: rawDirectory
|
|
1104
786
|
});
|
|
1105
|
-
const filename =
|
|
1106
|
-
return filename.length === 0 ? mappedDirectory :
|
|
787
|
+
const filename = path2.basename(expanded);
|
|
788
|
+
return filename.length === 0 ? mappedDirectory : path2.join(mappedDirectory, filename);
|
|
1107
789
|
}
|
|
1108
790
|
var init_path_utils = __esm({
|
|
1109
791
|
"packages/config-mutations/src/execution/path-utils.ts"() {
|
|
@@ -1768,38 +1450,38 @@ import { createTwoFilesPatch } from "diff";
|
|
|
1768
1450
|
import chalk from "chalk";
|
|
1769
1451
|
function createDryRunFileSystem(base, recorder) {
|
|
1770
1452
|
const proxy = {
|
|
1771
|
-
async readFile(
|
|
1453
|
+
async readFile(path24, encoding) {
|
|
1772
1454
|
if (encoding) {
|
|
1773
|
-
return base.readFile(
|
|
1455
|
+
return base.readFile(path24, encoding);
|
|
1774
1456
|
}
|
|
1775
|
-
return base.readFile(
|
|
1457
|
+
return base.readFile(path24);
|
|
1776
1458
|
},
|
|
1777
|
-
async writeFile(
|
|
1778
|
-
const previousContent = await tryReadText(base,
|
|
1459
|
+
async writeFile(path24, data, options) {
|
|
1460
|
+
const previousContent = await tryReadText(base, path24);
|
|
1779
1461
|
const nextContent = formatData(data, options?.encoding);
|
|
1780
1462
|
recorder.record({
|
|
1781
1463
|
type: "writeFile",
|
|
1782
|
-
path:
|
|
1464
|
+
path: path24,
|
|
1783
1465
|
nextContent,
|
|
1784
1466
|
previousContent
|
|
1785
1467
|
});
|
|
1786
1468
|
},
|
|
1787
|
-
async mkdir(
|
|
1788
|
-
recorder.record({ type: "mkdir", path:
|
|
1469
|
+
async mkdir(path24, options) {
|
|
1470
|
+
recorder.record({ type: "mkdir", path: path24, options });
|
|
1789
1471
|
},
|
|
1790
|
-
async stat(
|
|
1791
|
-
return base.stat(
|
|
1472
|
+
async stat(path24) {
|
|
1473
|
+
return base.stat(path24);
|
|
1792
1474
|
},
|
|
1793
|
-
async unlink(
|
|
1794
|
-
recorder.record({ type: "unlink", path:
|
|
1475
|
+
async unlink(path24) {
|
|
1476
|
+
recorder.record({ type: "unlink", path: path24 });
|
|
1795
1477
|
},
|
|
1796
|
-
async readdir(
|
|
1797
|
-
return base.readdir(
|
|
1478
|
+
async readdir(path24) {
|
|
1479
|
+
return base.readdir(path24);
|
|
1798
1480
|
}
|
|
1799
1481
|
};
|
|
1800
1482
|
if (typeof base.rm === "function") {
|
|
1801
|
-
proxy.rm = async (
|
|
1802
|
-
recorder.record({ type: "rm", path:
|
|
1483
|
+
proxy.rm = async (path24, options) => {
|
|
1484
|
+
recorder.record({ type: "rm", path: path24, options });
|
|
1803
1485
|
};
|
|
1804
1486
|
}
|
|
1805
1487
|
if (typeof base.copyFile === "function") {
|
|
@@ -1889,8 +1571,8 @@ function describeWriteChange(previous, next) {
|
|
|
1889
1571
|
}
|
|
1890
1572
|
return "update";
|
|
1891
1573
|
}
|
|
1892
|
-
function renderWriteCommand(
|
|
1893
|
-
const command = `cat > ${
|
|
1574
|
+
function renderWriteCommand(path24, change) {
|
|
1575
|
+
const command = `cat > ${path24}`;
|
|
1894
1576
|
if (change === "create") {
|
|
1895
1577
|
return renderOperationCommand(command, chalk.green, "# create");
|
|
1896
1578
|
}
|
|
@@ -2052,9 +1734,9 @@ function redactTomlLine(line) {
|
|
|
2052
1734
|
}
|
|
2053
1735
|
return line;
|
|
2054
1736
|
}
|
|
2055
|
-
async function tryReadText(base,
|
|
1737
|
+
async function tryReadText(base, path24) {
|
|
2056
1738
|
try {
|
|
2057
|
-
return await base.readFile(
|
|
1739
|
+
return await base.readFile(path24, "utf8");
|
|
2058
1740
|
} catch (error2) {
|
|
2059
1741
|
if (isNotFound(error2)) {
|
|
2060
1742
|
return null;
|
|
@@ -2236,7 +1918,7 @@ var init_context = __esm({
|
|
|
2236
1918
|
});
|
|
2237
1919
|
|
|
2238
1920
|
// src/cli/isolated-env.ts
|
|
2239
|
-
import
|
|
1921
|
+
import path3 from "node:path";
|
|
2240
1922
|
async function resolveIsolatedEnvDetails(env, isolated, providerName, readApiKey) {
|
|
2241
1923
|
if (!providerName) {
|
|
2242
1924
|
throw new Error("resolveIsolatedEnvDetails requires providerName.");
|
|
@@ -2258,7 +1940,7 @@ function resolveIsolatedTargetDirectory(input) {
|
|
|
2258
1940
|
const expanded = expandHomeShortcut(input.env, input.targetDirectory);
|
|
2259
1941
|
const baseDir = resolveIsolatedBaseDir(input.env, input.providerName);
|
|
2260
1942
|
const homeDir = input.env.homeDir;
|
|
2261
|
-
const homeDirWithSep = `${homeDir}${
|
|
1943
|
+
const homeDirWithSep = `${homeDir}${path3.sep}`;
|
|
2262
1944
|
if (expanded !== homeDir && !expanded.startsWith(homeDirWithSep)) {
|
|
2263
1945
|
throw new Error(
|
|
2264
1946
|
`Isolated config targets must live under the user's home directory (received "${input.targetDirectory}").`
|
|
@@ -2273,7 +1955,7 @@ function resolveIsolatedTargetDirectory(input) {
|
|
|
2273
1955
|
if (!expanded.startsWith(homeDirWithSep)) {
|
|
2274
1956
|
return expanded;
|
|
2275
1957
|
}
|
|
2276
|
-
const mapped =
|
|
1958
|
+
const mapped = path3.join(baseDir, expanded.slice(homeDirWithSep.length));
|
|
2277
1959
|
return stripAgentHome(mapped, baseDir, input.isolated.agentBinary);
|
|
2278
1960
|
}
|
|
2279
1961
|
function resolveIsolatedBaseDir(env, providerName) {
|
|
@@ -2322,9 +2004,9 @@ async function resolveIsolatedEnvValue(env, baseDir, value, readApiKey) {
|
|
|
2322
2004
|
function resolveIsolatedEnvPath(env, baseDir, value) {
|
|
2323
2005
|
switch (value.kind) {
|
|
2324
2006
|
case "isolatedDir":
|
|
2325
|
-
return value.relativePath ?
|
|
2007
|
+
return value.relativePath ? path3.join(baseDir, value.relativePath) : baseDir;
|
|
2326
2008
|
case "isolatedFile":
|
|
2327
|
-
return
|
|
2009
|
+
return path3.join(baseDir, value.relativePath);
|
|
2328
2010
|
}
|
|
2329
2011
|
}
|
|
2330
2012
|
function isEnvVarReference(value) {
|
|
@@ -2366,10 +2048,10 @@ async function applyIsolatedEnvRepairs(input) {
|
|
|
2366
2048
|
if (repair.kind !== "chmod") {
|
|
2367
2049
|
continue;
|
|
2368
2050
|
}
|
|
2369
|
-
if (
|
|
2051
|
+
if (path3.isAbsolute(repair.relativePath)) {
|
|
2370
2052
|
continue;
|
|
2371
2053
|
}
|
|
2372
|
-
const repairPath =
|
|
2054
|
+
const repairPath = path3.join(baseDir, repair.relativePath);
|
|
2373
2055
|
try {
|
|
2374
2056
|
await input.fs.chmod(repairPath, repair.mode);
|
|
2375
2057
|
} catch (error2) {
|
|
@@ -2420,13 +2102,13 @@ async function resolveCliSettingValue(value, env, readApiKey) {
|
|
|
2420
2102
|
}
|
|
2421
2103
|
function stripAgentHome(mapped, baseDir, agentBinary) {
|
|
2422
2104
|
const agentDir = `.${agentBinary}`;
|
|
2423
|
-
const prefix =
|
|
2105
|
+
const prefix = path3.join(baseDir, agentDir);
|
|
2424
2106
|
if (mapped === prefix) {
|
|
2425
2107
|
return baseDir;
|
|
2426
2108
|
}
|
|
2427
|
-
const withSep = `${prefix}${
|
|
2109
|
+
const withSep = `${prefix}${path3.sep}`;
|
|
2428
2110
|
if (mapped.startsWith(withSep)) {
|
|
2429
|
-
return
|
|
2111
|
+
return path3.join(baseDir, mapped.slice(withSep.length));
|
|
2430
2112
|
}
|
|
2431
2113
|
return mapped;
|
|
2432
2114
|
}
|
|
@@ -2437,11 +2119,11 @@ function expandHomeShortcut(env, input) {
|
|
|
2437
2119
|
if (input === "~") {
|
|
2438
2120
|
return env.homeDir;
|
|
2439
2121
|
}
|
|
2440
|
-
if (input.startsWith("~/") || input.startsWith(`~${
|
|
2441
|
-
return
|
|
2122
|
+
if (input.startsWith("~/") || input.startsWith(`~${path3.sep}`)) {
|
|
2123
|
+
return path3.join(env.homeDir, input.slice(2));
|
|
2442
2124
|
}
|
|
2443
|
-
if (input.startsWith("~./") || input.startsWith(`~.${
|
|
2444
|
-
return
|
|
2125
|
+
if (input.startsWith("~./") || input.startsWith(`~.${path3.sep}`)) {
|
|
2126
|
+
return path3.join(env.homeDir, `.${input.slice(3)}`);
|
|
2445
2127
|
}
|
|
2446
2128
|
return input;
|
|
2447
2129
|
}
|
|
@@ -3946,13 +3628,13 @@ function truncate2(text4, maxLength) {
|
|
|
3946
3628
|
if (maxLength <= 3) return text4.slice(0, maxLength);
|
|
3947
3629
|
return `${text4.slice(0, maxLength - 3)}...`;
|
|
3948
3630
|
}
|
|
3949
|
-
function
|
|
3631
|
+
function isNonEmptyString(value) {
|
|
3950
3632
|
return typeof value === "string" && value.length > 0;
|
|
3951
3633
|
}
|
|
3952
3634
|
function extractThreadId(value) {
|
|
3953
3635
|
if (!value || typeof value !== "object") return;
|
|
3954
3636
|
const obj = value;
|
|
3955
|
-
const maybeThreadId =
|
|
3637
|
+
const maybeThreadId = isNonEmptyString(obj.thread_id) && obj.thread_id || isNonEmptyString(obj.threadId) && obj.threadId || isNonEmptyString(obj.threadID) && obj.threadID || isNonEmptyString(obj.session_id) && obj.session_id || isNonEmptyString(obj.sessionId) && obj.sessionId || isNonEmptyString(obj.sessionID) && obj.sessionID;
|
|
3956
3638
|
return maybeThreadId || void 0;
|
|
3957
3639
|
}
|
|
3958
3640
|
var init_utils = __esm({
|
|
@@ -3998,7 +3680,7 @@ async function* adaptClaude(lines) {
|
|
|
3998
3680
|
continue;
|
|
3999
3681
|
}
|
|
4000
3682
|
const eventType = event.type;
|
|
4001
|
-
if (!
|
|
3683
|
+
if (!isNonEmptyString(eventType)) continue;
|
|
4002
3684
|
if (!emittedSessionStart) {
|
|
4003
3685
|
const threadId = extractThreadId(event);
|
|
4004
3686
|
emittedSessionStart = true;
|
|
@@ -4021,16 +3703,16 @@ async function* adaptClaude(lines) {
|
|
|
4021
3703
|
const item = block;
|
|
4022
3704
|
if (!item || typeof item !== "object") continue;
|
|
4023
3705
|
const blockType = item.type;
|
|
4024
|
-
if (!
|
|
3706
|
+
if (!isNonEmptyString(blockType)) continue;
|
|
4025
3707
|
if (eventType === "assistant") {
|
|
4026
|
-
if (blockType === "text" &&
|
|
3708
|
+
if (blockType === "text" && isNonEmptyString(item.text)) {
|
|
4027
3709
|
yield {
|
|
4028
3710
|
event: "agent_message",
|
|
4029
3711
|
text: item.text
|
|
4030
3712
|
};
|
|
4031
3713
|
continue;
|
|
4032
3714
|
}
|
|
4033
|
-
if (blockType === "tool_use" &&
|
|
3715
|
+
if (blockType === "tool_use" && isNonEmptyString(item.id) && isNonEmptyString(item.name)) {
|
|
4034
3716
|
const kind = TOOL_KIND_MAP[item.name] ?? "other";
|
|
4035
3717
|
toolKindsById.set(item.id, kind);
|
|
4036
3718
|
yield {
|
|
@@ -4044,25 +3726,25 @@ async function* adaptClaude(lines) {
|
|
|
4044
3726
|
continue;
|
|
4045
3727
|
}
|
|
4046
3728
|
if (eventType === "user") {
|
|
4047
|
-
if (!
|
|
3729
|
+
if (!isNonEmptyString(item.tool_use_id)) continue;
|
|
4048
3730
|
if (blockType !== "tool_result") continue;
|
|
4049
3731
|
const kind = toolKindsById.get(item.tool_use_id);
|
|
4050
3732
|
toolKindsById.delete(item.tool_use_id);
|
|
4051
|
-
let
|
|
3733
|
+
let path24;
|
|
4052
3734
|
if (typeof item.content === "string") {
|
|
4053
|
-
|
|
3735
|
+
path24 = item.content;
|
|
4054
3736
|
} else {
|
|
4055
3737
|
try {
|
|
4056
|
-
|
|
3738
|
+
path24 = JSON.stringify(item.content);
|
|
4057
3739
|
} catch {
|
|
4058
|
-
|
|
3740
|
+
path24 = String(item.content);
|
|
4059
3741
|
}
|
|
4060
3742
|
}
|
|
4061
3743
|
yield {
|
|
4062
3744
|
event: "tool_complete",
|
|
4063
3745
|
id: item.tool_use_id,
|
|
4064
3746
|
kind,
|
|
4065
|
-
path:
|
|
3747
|
+
path: path24
|
|
4066
3748
|
};
|
|
4067
3749
|
}
|
|
4068
3750
|
}
|
|
@@ -4116,7 +3798,7 @@ async function* adaptCodex(lines) {
|
|
|
4116
3798
|
continue;
|
|
4117
3799
|
}
|
|
4118
3800
|
const eventType = event.type;
|
|
4119
|
-
if (!
|
|
3801
|
+
if (!isNonEmptyString(eventType)) continue;
|
|
4120
3802
|
if (eventType === "thread.started") {
|
|
4121
3803
|
const maybeThreadId = extractThreadId(event);
|
|
4122
3804
|
yield { event: "session_start", threadId: maybeThreadId };
|
|
@@ -4140,23 +3822,23 @@ async function* adaptCodex(lines) {
|
|
|
4140
3822
|
const item = event.item ?? null;
|
|
4141
3823
|
if (!item || typeof item !== "object") continue;
|
|
4142
3824
|
const itemType = item.type;
|
|
4143
|
-
if (!
|
|
3825
|
+
if (!isNonEmptyString(itemType)) continue;
|
|
4144
3826
|
if (eventType === "item.started") {
|
|
4145
|
-
if (!
|
|
3827
|
+
if (!isNonEmptyString(item.id)) continue;
|
|
4146
3828
|
let kind;
|
|
4147
3829
|
let title;
|
|
4148
3830
|
if (itemType === "command_execution") {
|
|
4149
3831
|
kind = "exec";
|
|
4150
|
-
title = truncate2(
|
|
3832
|
+
title = truncate2(isNonEmptyString(item.command) ? item.command : "", 80);
|
|
4151
3833
|
} else if (itemType === "file_edit") {
|
|
4152
3834
|
kind = "edit";
|
|
4153
|
-
title =
|
|
3835
|
+
title = isNonEmptyString(item.path) ? item.path : "";
|
|
4154
3836
|
} else if (itemType === "thinking") {
|
|
4155
3837
|
kind = "think";
|
|
4156
3838
|
title = "thinking...";
|
|
4157
3839
|
} else if (itemType === "mcp_tool_call") {
|
|
4158
|
-
const server =
|
|
4159
|
-
const tool =
|
|
3840
|
+
const server = isNonEmptyString(item.server) ? item.server : "unknown";
|
|
3841
|
+
const tool = isNonEmptyString(item.tool) ? item.tool : "unknown";
|
|
4160
3842
|
kind = "other";
|
|
4161
3843
|
title = `${server}.${tool}`;
|
|
4162
3844
|
}
|
|
@@ -4169,25 +3851,25 @@ async function* adaptCodex(lines) {
|
|
|
4169
3851
|
}
|
|
4170
3852
|
if (eventType === "item.completed") {
|
|
4171
3853
|
if (itemType === "agent_message") {
|
|
4172
|
-
if (!
|
|
3854
|
+
if (!isNonEmptyString(item.text)) continue;
|
|
4173
3855
|
yield { event: "agent_message", text: item.text };
|
|
4174
3856
|
continue;
|
|
4175
3857
|
}
|
|
4176
3858
|
if (itemType === "reasoning") {
|
|
4177
|
-
const text4 =
|
|
3859
|
+
const text4 = isNonEmptyString(item.text) ? item.text : isNonEmptyString(item.content) ? item.content : isNonEmptyString(item.summary) ? item.summary : void 0;
|
|
4178
3860
|
if (!text4) continue;
|
|
4179
3861
|
yield { event: "reasoning", text: text4 };
|
|
4180
3862
|
continue;
|
|
4181
3863
|
}
|
|
4182
|
-
if (!
|
|
3864
|
+
if (!isNonEmptyString(item.id)) continue;
|
|
4183
3865
|
if (itemType === "command_execution" || itemType === "file_edit" || itemType === "mcp_tool_call") {
|
|
4184
3866
|
const kindFromStart = toolKindById.get(item.id);
|
|
4185
3867
|
const kind = kindFromStart ?? (itemType === "command_execution" ? "exec" : itemType === "file_edit" ? "edit" : "other");
|
|
4186
|
-
const titleFromEvent =
|
|
4187
|
-
const
|
|
3868
|
+
const titleFromEvent = isNonEmptyString(item.path) ? item.path : itemType === "mcp_tool_call" ? `${isNonEmptyString(item.server) ? item.server : "unknown"}.${isNonEmptyString(item.tool) ? item.tool : "unknown"}` : void 0;
|
|
3869
|
+
const path24 = titleFromEvent ?? toolTitleById.get(item.id) ?? "";
|
|
4188
3870
|
toolTitleById.delete(item.id);
|
|
4189
3871
|
toolKindById.delete(item.id);
|
|
4190
|
-
yield { event: "tool_complete", id: item.id, kind, path:
|
|
3872
|
+
yield { event: "tool_complete", id: item.id, kind, path: path24 };
|
|
4191
3873
|
}
|
|
4192
3874
|
}
|
|
4193
3875
|
}
|
|
@@ -4226,9 +3908,9 @@ async function* adaptKimi(lines) {
|
|
|
4226
3908
|
}
|
|
4227
3909
|
}
|
|
4228
3910
|
const role = event.role;
|
|
4229
|
-
if (!
|
|
3911
|
+
if (!isNonEmptyString(role) || role !== "assistant") continue;
|
|
4230
3912
|
const content = event.content;
|
|
4231
|
-
if (!
|
|
3913
|
+
if (!isNonEmptyString(content)) continue;
|
|
4232
3914
|
yield { event: "agent_message", text: content };
|
|
4233
3915
|
}
|
|
4234
3916
|
}
|
|
@@ -4257,7 +3939,7 @@ async function* adaptNative(lines) {
|
|
|
4257
3939
|
continue;
|
|
4258
3940
|
}
|
|
4259
3941
|
const maybeEventType = event?.event;
|
|
4260
|
-
if (!
|
|
3942
|
+
if (!isNonEmptyString(maybeEventType)) {
|
|
4261
3943
|
yield {
|
|
4262
3944
|
event: "error",
|
|
4263
3945
|
message: `[adaptNative] Line missing string "event" field: ${truncate2(line, 200)}`
|
|
@@ -4316,23 +3998,23 @@ async function* adaptOpenCode(lines) {
|
|
|
4316
3998
|
}
|
|
4317
3999
|
if (!event || typeof event !== "object") continue;
|
|
4318
4000
|
const sessionID = extractThreadId(event);
|
|
4319
|
-
if (!emittedSessionStart &&
|
|
4001
|
+
if (!emittedSessionStart && isNonEmptyString(sessionID)) {
|
|
4320
4002
|
emittedSessionStart = true;
|
|
4321
4003
|
yield { event: "session_start", threadId: sessionID };
|
|
4322
4004
|
}
|
|
4323
4005
|
const eventType = event.type;
|
|
4324
|
-
if (!
|
|
4006
|
+
if (!isNonEmptyString(eventType)) continue;
|
|
4325
4007
|
if (eventType === "text") {
|
|
4326
4008
|
const part = event.part ?? null;
|
|
4327
4009
|
if (!part || typeof part !== "object") continue;
|
|
4328
|
-
if (!
|
|
4010
|
+
if (!isNonEmptyString(part.text)) continue;
|
|
4329
4011
|
yield { event: "agent_message", text: part.text };
|
|
4330
4012
|
continue;
|
|
4331
4013
|
}
|
|
4332
4014
|
if (eventType === "tool_use") {
|
|
4333
4015
|
const part = event.part ?? null;
|
|
4334
4016
|
if (!part || typeof part !== "object") continue;
|
|
4335
|
-
if (!
|
|
4017
|
+
if (!isNonEmptyString(part.callID) || !isNonEmptyString(part.tool)) continue;
|
|
4336
4018
|
const state = part.state ?? null;
|
|
4337
4019
|
if (!state || typeof state !== "object") continue;
|
|
4338
4020
|
const kind = guessToolKind(part.tool);
|
|
@@ -4344,7 +4026,7 @@ async function* adaptOpenCode(lines) {
|
|
|
4344
4026
|
const maybeInput = state.input;
|
|
4345
4027
|
if (kind === "exec" && maybeInput && typeof maybeInput === "object") {
|
|
4346
4028
|
const command = maybeInput.command;
|
|
4347
|
-
if (
|
|
4029
|
+
if (isNonEmptyString(command)) {
|
|
4348
4030
|
title = truncate2(command, 80);
|
|
4349
4031
|
}
|
|
4350
4032
|
}
|
|
@@ -4629,7 +4311,7 @@ function updateSessionFromEvent(ctx, event, toolCallsById) {
|
|
|
4629
4311
|
}
|
|
4630
4312
|
const id = readString(event.id);
|
|
4631
4313
|
const kind = readString(event.kind);
|
|
4632
|
-
const
|
|
4314
|
+
const path24 = readString(event.path);
|
|
4633
4315
|
let toolCall = id ? toolCallsById.get(id) : void 0;
|
|
4634
4316
|
if (!toolCall) {
|
|
4635
4317
|
toolCall = {};
|
|
@@ -4644,8 +4326,8 @@ function updateSessionFromEvent(ctx, event, toolCallsById) {
|
|
|
4644
4326
|
if (kind) {
|
|
4645
4327
|
toolCall.kind = kind;
|
|
4646
4328
|
}
|
|
4647
|
-
if (
|
|
4648
|
-
toolCall.path =
|
|
4329
|
+
if (path24) {
|
|
4330
|
+
toolCall.path = path24;
|
|
4649
4331
|
}
|
|
4650
4332
|
}
|
|
4651
4333
|
var sessionCapture;
|
|
@@ -4731,8 +4413,8 @@ var init_usage_capture = __esm({
|
|
|
4731
4413
|
});
|
|
4732
4414
|
|
|
4733
4415
|
// packages/agent-spawn/src/acp/middlewares/spawn-log.ts
|
|
4734
|
-
import
|
|
4735
|
-
import { homedir as
|
|
4416
|
+
import path4 from "node:path";
|
|
4417
|
+
import { homedir as homedir2 } from "node:os";
|
|
4736
4418
|
import { mkdir, open } from "node:fs/promises";
|
|
4737
4419
|
function pad(value, width) {
|
|
4738
4420
|
return String(value).padStart(width, "0");
|
|
@@ -4765,11 +4447,11 @@ function resolveStartedAt(value) {
|
|
|
4765
4447
|
return value;
|
|
4766
4448
|
}
|
|
4767
4449
|
function resolveLogFilePath(ctx) {
|
|
4768
|
-
const baseDir = ctx.logDir ??
|
|
4450
|
+
const baseDir = ctx.logDir ?? path4.join(homedir2(), ".poe-code", "spawn-logs");
|
|
4769
4451
|
const startedAt = resolveStartedAt(ctx.startedAt);
|
|
4770
4452
|
const { day, time: time3, milliseconds } = formatTimestamp(startedAt);
|
|
4771
4453
|
const fileName = `${day}-${time3}-${milliseconds}-${normalizeAgent(ctx.agent)}.jsonl`;
|
|
4772
|
-
return
|
|
4454
|
+
return path4.join(baseDir, fileName);
|
|
4773
4455
|
}
|
|
4774
4456
|
async function writePreloadedEvents(writer, events) {
|
|
4775
4457
|
for (const event of events) {
|
|
@@ -4787,7 +4469,7 @@ var init_spawn_log = __esm({
|
|
|
4787
4469
|
logDirPath;
|
|
4788
4470
|
constructor(ctx) {
|
|
4789
4471
|
this.logFilePath = resolveLogFilePath(ctx);
|
|
4790
|
-
this.logDirPath =
|
|
4472
|
+
this.logDirPath = path4.dirname(this.logFilePath);
|
|
4791
4473
|
}
|
|
4792
4474
|
async writeEvent(event) {
|
|
4793
4475
|
if (this.isDisabled) {
|
|
@@ -4872,7 +4554,7 @@ var init_src5 = __esm({
|
|
|
4872
4554
|
});
|
|
4873
4555
|
|
|
4874
4556
|
// src/cli/commands/shared.ts
|
|
4875
|
-
import
|
|
4557
|
+
import path5 from "node:path";
|
|
4876
4558
|
function resolveCommandFlags(program) {
|
|
4877
4559
|
const opts = program.optsWithGlobals();
|
|
4878
4560
|
return {
|
|
@@ -4945,7 +4627,7 @@ function buildResumeCommand(canonicalService, threadId, cwd) {
|
|
|
4945
4627
|
if (!binaryName) {
|
|
4946
4628
|
return void 0;
|
|
4947
4629
|
}
|
|
4948
|
-
const resumeCwd =
|
|
4630
|
+
const resumeCwd = path5.resolve(cwd);
|
|
4949
4631
|
const args = spawnConfig.resumeCommand(threadId, resumeCwd);
|
|
4950
4632
|
const agentCommand = [binaryName, ...args.map(shlexQuote)].join(" ");
|
|
4951
4633
|
const needsCdPrefix = !args.includes(resumeCwd);
|
|
@@ -5042,7 +4724,7 @@ var init_shared = __esm({
|
|
|
5042
4724
|
});
|
|
5043
4725
|
|
|
5044
4726
|
// src/sdk/spawn-core.ts
|
|
5045
|
-
import
|
|
4727
|
+
import path6 from "node:path";
|
|
5046
4728
|
import chalk10 from "chalk";
|
|
5047
4729
|
async function spawnCore(container, service, options, flags = { dryRun: false, verbose: false }) {
|
|
5048
4730
|
const cwdOverride = resolveSpawnWorkingDirectory(
|
|
@@ -5141,10 +4823,10 @@ function resolveSpawnWorkingDirectory(baseDir, candidate) {
|
|
|
5141
4823
|
if (!candidate || candidate.trim().length === 0) {
|
|
5142
4824
|
return void 0;
|
|
5143
4825
|
}
|
|
5144
|
-
if (
|
|
4826
|
+
if (path6.isAbsolute(candidate)) {
|
|
5145
4827
|
return candidate;
|
|
5146
4828
|
}
|
|
5147
|
-
return
|
|
4829
|
+
return path6.resolve(baseDir, candidate);
|
|
5148
4830
|
}
|
|
5149
4831
|
var init_spawn_core = __esm({
|
|
5150
4832
|
"src/sdk/spawn-core.ts"() {
|
|
@@ -5154,14 +4836,14 @@ var init_spawn_core = __esm({
|
|
|
5154
4836
|
});
|
|
5155
4837
|
|
|
5156
4838
|
// src/cli/environment.ts
|
|
5157
|
-
import
|
|
4839
|
+
import path7 from "node:path";
|
|
5158
4840
|
function createCliEnvironment(init) {
|
|
5159
4841
|
const platform = init.platform ?? process.platform;
|
|
5160
4842
|
const variables = init.variables ?? process.env;
|
|
5161
4843
|
const configPath = resolveConfigPath(init.homeDir);
|
|
5162
4844
|
const logDir = resolveLogDir(init.homeDir);
|
|
5163
4845
|
const { poeApiBaseUrl, poeBaseUrl } = resolvePoeBaseUrls(variables);
|
|
5164
|
-
const resolveHomePath = (...segments) =>
|
|
4846
|
+
const resolveHomePath = (...segments) => path7.join(init.homeDir, ...segments);
|
|
5165
4847
|
const getVariable = (name) => variables[name];
|
|
5166
4848
|
return {
|
|
5167
4849
|
cwd: init.cwd,
|
|
@@ -5177,10 +4859,10 @@ function createCliEnvironment(init) {
|
|
|
5177
4859
|
};
|
|
5178
4860
|
}
|
|
5179
4861
|
function resolveConfigPath(homeDir) {
|
|
5180
|
-
return
|
|
4862
|
+
return path7.join(homeDir, ".poe-code", "config.json");
|
|
5181
4863
|
}
|
|
5182
4864
|
function resolveLogDir(homeDir) {
|
|
5183
|
-
return
|
|
4865
|
+
return path7.join(homeDir, ".poe-code", "logs");
|
|
5184
4866
|
}
|
|
5185
4867
|
function resolvePoeBaseUrls(variables) {
|
|
5186
4868
|
const raw = variables.POE_BASE_URL;
|
|
@@ -5404,7 +5086,7 @@ var init_prompts2 = __esm({
|
|
|
5404
5086
|
});
|
|
5405
5087
|
|
|
5406
5088
|
// src/cli/options.ts
|
|
5407
|
-
function
|
|
5089
|
+
function stripBracketedPaste(value) {
|
|
5408
5090
|
return value.replace(/\x1b\[200~/g, "").replace(/\x1b\[201~/g, "").replace(/undefinedndefined$/, "").replace(/undefined$/, "").replace(/ndefined$/, "");
|
|
5409
5091
|
}
|
|
5410
5092
|
function isAlphanumericWithSeparators(value) {
|
|
@@ -5423,7 +5105,7 @@ function isAlphanumericWithSeparators(value) {
|
|
|
5423
5105
|
function hasMinimumApiKeyLength(value) {
|
|
5424
5106
|
return value.length >= MIN_API_KEY_LENGTH;
|
|
5425
5107
|
}
|
|
5426
|
-
function
|
|
5108
|
+
function isValidApiKeyFormat(key) {
|
|
5427
5109
|
if (key.length === 0) return false;
|
|
5428
5110
|
if (key.startsWith("sk-poe-")) {
|
|
5429
5111
|
const hash2 = key.slice(7);
|
|
@@ -5447,7 +5129,7 @@ function createOptionResolvers(init) {
|
|
|
5447
5129
|
return result;
|
|
5448
5130
|
};
|
|
5449
5131
|
const normalizeApiKey2 = (value) => {
|
|
5450
|
-
const sanitized =
|
|
5132
|
+
const sanitized = stripBracketedPaste(value);
|
|
5451
5133
|
const trimmed = sanitized.trim();
|
|
5452
5134
|
if (trimmed.length === 0) {
|
|
5453
5135
|
throw new Error("POE API key cannot be empty.");
|
|
@@ -5455,7 +5137,7 @@ function createOptionResolvers(init) {
|
|
|
5455
5137
|
return trimmed;
|
|
5456
5138
|
};
|
|
5457
5139
|
const confirmKeyFormat = async (apiKey, assumeYes) => {
|
|
5458
|
-
if (
|
|
5140
|
+
if (isValidApiKeyFormat(apiKey)) return true;
|
|
5459
5141
|
if (assumeYes) return false;
|
|
5460
5142
|
return await init.confirm(
|
|
5461
5143
|
"Key doesn't match expected API key format. Use it anyway?"
|
|
@@ -5614,7 +5296,7 @@ function isSilentError(error2) {
|
|
|
5614
5296
|
}
|
|
5615
5297
|
return error2.name === "SilentError" || error2.name === "OperationCancelledError";
|
|
5616
5298
|
}
|
|
5617
|
-
var CliError, SilentError, ApiError, ValidationError, OperationCancelledError;
|
|
5299
|
+
var CliError, SilentError, ApiError, ValidationError, AuthenticationError, OperationCancelledError;
|
|
5618
5300
|
var init_errors = __esm({
|
|
5619
5301
|
"src/cli/errors.ts"() {
|
|
5620
5302
|
"use strict";
|
|
@@ -5654,6 +5336,11 @@ var init_errors = __esm({
|
|
|
5654
5336
|
super(message, context, { isUserError: true });
|
|
5655
5337
|
}
|
|
5656
5338
|
};
|
|
5339
|
+
AuthenticationError = class extends CliError {
|
|
5340
|
+
constructor(message, context) {
|
|
5341
|
+
super(message, context, { isUserError: true });
|
|
5342
|
+
}
|
|
5343
|
+
};
|
|
5657
5344
|
OperationCancelledError = class extends SilentError {
|
|
5658
5345
|
constructor(message = "Operation cancelled.") {
|
|
5659
5346
|
super(message, { isUserError: true });
|
|
@@ -5868,7 +5555,7 @@ var init_logger2 = __esm({
|
|
|
5868
5555
|
});
|
|
5869
5556
|
|
|
5870
5557
|
// src/cli/error-logger.ts
|
|
5871
|
-
import
|
|
5558
|
+
import path8 from "node:path";
|
|
5872
5559
|
var DEFAULT_MAX_SIZE, DEFAULT_MAX_BACKUPS, ErrorLogger;
|
|
5873
5560
|
var init_error_logger = __esm({
|
|
5874
5561
|
"src/cli/error-logger.ts"() {
|
|
@@ -5885,7 +5572,7 @@ var init_error_logger = __esm({
|
|
|
5885
5572
|
fileLoggingAvailable;
|
|
5886
5573
|
constructor(options) {
|
|
5887
5574
|
this.fs = options.fs;
|
|
5888
|
-
this.logFilePath =
|
|
5575
|
+
this.logFilePath = path8.join(options.logDir, "errors.log");
|
|
5889
5576
|
this.logToStderr = options.logToStderr ?? true;
|
|
5890
5577
|
this.maxSize = options.maxSize ?? DEFAULT_MAX_SIZE;
|
|
5891
5578
|
this.maxBackups = options.maxBackups ?? DEFAULT_MAX_BACKUPS;
|
|
@@ -6004,7 +5691,7 @@ ${entry.stack}`);
|
|
|
6004
5691
|
return `${this.logFilePath}.${index}`;
|
|
6005
5692
|
}
|
|
6006
5693
|
ensureLogDirectory() {
|
|
6007
|
-
const directory =
|
|
5694
|
+
const directory = path8.dirname(this.logFilePath);
|
|
6008
5695
|
try {
|
|
6009
5696
|
if (!this.fs.existsSync(directory)) {
|
|
6010
5697
|
this.fs.mkdirSync(directory, { recursive: true });
|
|
@@ -6022,7 +5709,7 @@ ${entry.stack}`);
|
|
|
6022
5709
|
});
|
|
6023
5710
|
|
|
6024
5711
|
// src/providers/index.ts
|
|
6025
|
-
import
|
|
5712
|
+
import path9 from "node:path";
|
|
6026
5713
|
import { readdir } from "node:fs/promises";
|
|
6027
5714
|
import { fileURLToPath, pathToFileURL } from "node:url";
|
|
6028
5715
|
function isProviderModule(filename) {
|
|
@@ -6049,7 +5736,7 @@ async function loadProviders() {
|
|
|
6049
5736
|
for (const entry of entries) {
|
|
6050
5737
|
if (!entry.isFile()) continue;
|
|
6051
5738
|
if (!isProviderModule(entry.name)) continue;
|
|
6052
|
-
const moduleUrl = pathToFileURL(
|
|
5739
|
+
const moduleUrl = pathToFileURL(path9.join(currentDir, entry.name)).href;
|
|
6053
5740
|
const moduleExports = await import(moduleUrl);
|
|
6054
5741
|
if (!moduleExports.provider) {
|
|
6055
5742
|
throw new Error(`Provider module "${entry.name}" must export "provider".`);
|
|
@@ -6065,8 +5752,8 @@ var moduleDir, currentDir, defaultProviders;
|
|
|
6065
5752
|
var init_providers = __esm({
|
|
6066
5753
|
async "src/providers/index.ts"() {
|
|
6067
5754
|
"use strict";
|
|
6068
|
-
moduleDir =
|
|
6069
|
-
currentDir =
|
|
5755
|
+
moduleDir = path9.dirname(fileURLToPath(import.meta.url));
|
|
5756
|
+
currentDir = path9.basename(moduleDir) === "providers" ? moduleDir : path9.join(moduleDir, "providers");
|
|
6070
5757
|
defaultProviders = await loadProviders();
|
|
6071
5758
|
}
|
|
6072
5759
|
});
|
|
@@ -6408,21 +6095,21 @@ function createSdkContainer(options) {
|
|
|
6408
6095
|
});
|
|
6409
6096
|
loggerFactory.setErrorLogger(errorLogger);
|
|
6410
6097
|
const asyncFs = {
|
|
6411
|
-
readFile: ((
|
|
6098
|
+
readFile: ((path24, encoding) => {
|
|
6412
6099
|
if (encoding) {
|
|
6413
|
-
return fs2.readFile(
|
|
6100
|
+
return fs2.readFile(path24, encoding);
|
|
6414
6101
|
}
|
|
6415
|
-
return fs2.readFile(
|
|
6102
|
+
return fs2.readFile(path24);
|
|
6416
6103
|
}),
|
|
6417
|
-
writeFile: (
|
|
6418
|
-
mkdir: (
|
|
6104
|
+
writeFile: (path24, data, opts) => fs2.writeFile(path24, data, opts),
|
|
6105
|
+
mkdir: (path24, opts) => fs2.mkdir(path24, opts).then(() => {
|
|
6419
6106
|
}),
|
|
6420
|
-
stat: (
|
|
6421
|
-
rm: (
|
|
6422
|
-
unlink: (
|
|
6423
|
-
readdir: (
|
|
6107
|
+
stat: (path24) => fs2.stat(path24),
|
|
6108
|
+
rm: (path24, opts) => fs2.rm(path24, opts),
|
|
6109
|
+
unlink: (path24) => fs2.unlink(path24),
|
|
6110
|
+
readdir: (path24) => fs2.readdir(path24),
|
|
6424
6111
|
copyFile: (src, dest) => fs2.copyFile(src, dest),
|
|
6425
|
-
chmod: (
|
|
6112
|
+
chmod: (path24, mode) => fs2.chmod(path24, mode)
|
|
6426
6113
|
};
|
|
6427
6114
|
const contextFactory = createCommandContextFactory({ fs: asyncFs });
|
|
6428
6115
|
const authFs = {
|
|
@@ -6432,21 +6119,21 @@ function createSdkContainer(options) {
|
|
|
6432
6119
|
unlink: (filePath) => fs2.unlink(filePath),
|
|
6433
6120
|
chmod: (filePath, mode) => fs2.chmod(filePath, mode)
|
|
6434
6121
|
};
|
|
6435
|
-
const { store: authStore } =
|
|
6122
|
+
const { store: authStore } = createSecretStore({
|
|
6123
|
+
backendEnvVar: "POE_AUTH_BACKEND",
|
|
6436
6124
|
env: variables,
|
|
6437
6125
|
platform: process.platform,
|
|
6438
6126
|
fileStore: {
|
|
6439
6127
|
fs: authFs,
|
|
6440
|
-
|
|
6441
|
-
|
|
6442
|
-
|
|
6443
|
-
fs: authFs,
|
|
6128
|
+
salt: "poe-code:encrypted-file-auth-store:v1",
|
|
6129
|
+
defaultDirectory: ".poe-code",
|
|
6130
|
+
defaultFileName: "credentials.enc",
|
|
6444
6131
|
getHomeDirectory: () => homeDir
|
|
6445
6132
|
}
|
|
6446
6133
|
});
|
|
6447
|
-
const readApiKey = authStore.
|
|
6448
|
-
const writeApiKey = authStore.
|
|
6449
|
-
const deleteApiKey = authStore.
|
|
6134
|
+
const readApiKey = authStore.get.bind(authStore);
|
|
6135
|
+
const writeApiKey = authStore.set.bind(authStore);
|
|
6136
|
+
const deleteApiKey = authStore.delete.bind(authStore);
|
|
6450
6137
|
const noopPrompts = async () => {
|
|
6451
6138
|
throw new Error("SDK does not support interactive prompts");
|
|
6452
6139
|
};
|
|
@@ -7124,8 +6811,8 @@ function resourceNotFound(resource) {
|
|
|
7124
6811
|
`Resource not found: ${resource}`
|
|
7125
6812
|
);
|
|
7126
6813
|
}
|
|
7127
|
-
function assertAbsolutePath(
|
|
7128
|
-
if (!isAbsolute(
|
|
6814
|
+
function assertAbsolutePath(path24) {
|
|
6815
|
+
if (!isAbsolute(path24)) {
|
|
7129
6816
|
throw invalidParams('"path" must be an absolute path');
|
|
7130
6817
|
}
|
|
7131
6818
|
}
|
|
@@ -7723,7 +7410,7 @@ var init_stream_helpers = __esm({
|
|
|
7723
7410
|
|
|
7724
7411
|
// packages/poe-acp-client/src/run-report.ts
|
|
7725
7412
|
import * as fsPromises from "node:fs/promises";
|
|
7726
|
-
import { homedir as
|
|
7413
|
+
import { homedir as homedir4 } from "node:os";
|
|
7727
7414
|
import { join } from "node:path";
|
|
7728
7415
|
async function generateRunReportFromSessionUpdateStream(stream, options = {}) {
|
|
7729
7416
|
const now = options.now ?? (() => /* @__PURE__ */ new Date());
|
|
@@ -7977,7 +7664,7 @@ var require_requirements_txt = __commonJS({
|
|
|
7977
7664
|
// src/templates/codex/config.toml.hbs
|
|
7978
7665
|
var require_config_toml = __commonJS({
|
|
7979
7666
|
"src/templates/codex/config.toml.hbs"(exports, module) {
|
|
7980
|
-
module.exports = 'model_provider = "poe"\n\n[profiles."{{{profileName}}}"]\nmodel = "{{{model}}}"\nmodel_provider = "poe"\nmodel_reasoning_effort = "{{reasoningEffort}}"\nmodel_verbosity = "medium"\n\n[model_providers.poe]\nname = "poe"\nbase_url = "{{{baseUrl}}}"\nwire_api = "responses"\nexperimental_bearer_token = "{{apiKey}}"\n';
|
|
7667
|
+
module.exports = 'model_provider = "poe"\n\n[profiles."{{{profileName}}}"]\nmodel = "{{{model}}}"\nmodel_provider = "poe"\nmodel_reasoning_effort = "{{reasoningEffort}}"\nmodel_verbosity = "medium"\n\n[model_providers.poe]\nname = "poe"\nbase_url = "{{{baseUrl}}}"\nwire_api = "responses"\nexperimental_bearer_token = "{{apiKey}}"\nrequires_openai_auth = false\nsupports_websockets = false\n';
|
|
7981
7668
|
}
|
|
7982
7669
|
});
|
|
7983
7670
|
|
|
@@ -8886,7 +8573,7 @@ var init_acp_core = __esm({
|
|
|
8886
8573
|
});
|
|
8887
8574
|
|
|
8888
8575
|
// packages/poe-agent/src/plugins/plugin-args.ts
|
|
8889
|
-
import
|
|
8576
|
+
import path10 from "node:path";
|
|
8890
8577
|
function isObjectRecord3(value) {
|
|
8891
8578
|
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
8892
8579
|
}
|
|
@@ -8917,13 +8604,13 @@ function getOptionalString(args, key) {
|
|
|
8917
8604
|
return value;
|
|
8918
8605
|
}
|
|
8919
8606
|
function resolveAllowedPath(cwd, allowedPaths, inputPath) {
|
|
8920
|
-
const resolvedPath =
|
|
8607
|
+
const resolvedPath = path10.resolve(cwd, inputPath);
|
|
8921
8608
|
const isAllowed = allowedPaths.some((allowedPath) => {
|
|
8922
8609
|
if (allowedPath === resolvedPath) {
|
|
8923
8610
|
return true;
|
|
8924
8611
|
}
|
|
8925
|
-
const rel =
|
|
8926
|
-
return rel.length > 0 && !rel.startsWith("..") && !
|
|
8612
|
+
const rel = path10.relative(allowedPath, resolvedPath);
|
|
8613
|
+
return rel.length > 0 && !rel.startsWith("..") && !path10.isAbsolute(rel);
|
|
8927
8614
|
});
|
|
8928
8615
|
if (!isAllowed) {
|
|
8929
8616
|
throw new Error(`Path is outside allowed paths: ${inputPath}`);
|
|
@@ -8938,7 +8625,7 @@ var init_plugin_args = __esm({
|
|
|
8938
8625
|
|
|
8939
8626
|
// packages/poe-agent/src/plugins/poe-agent-plugin-files.ts
|
|
8940
8627
|
import fsPromises2 from "node:fs/promises";
|
|
8941
|
-
import
|
|
8628
|
+
import path11 from "node:path";
|
|
8942
8629
|
async function fileExists(fs3, filePath) {
|
|
8943
8630
|
try {
|
|
8944
8631
|
await fs3.readFile(filePath, "utf8");
|
|
@@ -8962,9 +8649,9 @@ var init_poe_agent_plugin_files = __esm({
|
|
|
8962
8649
|
"use strict";
|
|
8963
8650
|
init_plugin_args();
|
|
8964
8651
|
filesPlugin = (options = {}) => {
|
|
8965
|
-
const cwd =
|
|
8652
|
+
const cwd = path11.resolve(options.cwd ?? process.cwd());
|
|
8966
8653
|
const allowedPaths = (options.allowedPaths ?? [cwd]).map(
|
|
8967
|
-
(allowedPath) =>
|
|
8654
|
+
(allowedPath) => path11.resolve(cwd, allowedPath)
|
|
8968
8655
|
);
|
|
8969
8656
|
const fs3 = options.fs ?? fsPromises2;
|
|
8970
8657
|
const readFileTool = {
|
|
@@ -9018,7 +8705,7 @@ var init_poe_agent_plugin_files = __esm({
|
|
|
9018
8705
|
async call(args) {
|
|
9019
8706
|
const command = getRequiredString(args, "command");
|
|
9020
8707
|
const filePath = resolveAllowedPath(cwd, allowedPaths, getRequiredString(args, "path"));
|
|
9021
|
-
const displayedPath =
|
|
8708
|
+
const displayedPath = path11.relative(cwd, filePath) || path11.basename(filePath);
|
|
9022
8709
|
if (command === "str_replace") {
|
|
9023
8710
|
const oldStr = getRequiredString(args, "old_str", true);
|
|
9024
8711
|
const newStr = getRequiredString(args, "new_str", true);
|
|
@@ -9038,7 +8725,7 @@ var init_poe_agent_plugin_files = __esm({
|
|
|
9038
8725
|
if (await fileExists(fs3, filePath)) {
|
|
9039
8726
|
throw new Error("File already exists \u2014 use str_replace to edit");
|
|
9040
8727
|
}
|
|
9041
|
-
await fs3.mkdir(
|
|
8728
|
+
await fs3.mkdir(path11.dirname(filePath), { recursive: true });
|
|
9042
8729
|
await fs3.writeFile(filePath, fileText, "utf8");
|
|
9043
8730
|
return `Created file: ${displayedPath}`;
|
|
9044
8731
|
}
|
|
@@ -9079,7 +8766,7 @@ var init_poe_agent_plugin_files = __esm({
|
|
|
9079
8766
|
|
|
9080
8767
|
// packages/poe-agent/src/plugins/poe-agent-plugin-shell.ts
|
|
9081
8768
|
import { exec as execCallback } from "node:child_process";
|
|
9082
|
-
import
|
|
8769
|
+
import path12 from "node:path";
|
|
9083
8770
|
import { promisify } from "node:util";
|
|
9084
8771
|
async function defaultRunCommand(command, cwd) {
|
|
9085
8772
|
try {
|
|
@@ -9112,9 +8799,9 @@ var init_poe_agent_plugin_shell = __esm({
|
|
|
9112
8799
|
init_plugin_args();
|
|
9113
8800
|
exec = promisify(execCallback);
|
|
9114
8801
|
shellPlugin = (options = {}) => {
|
|
9115
|
-
const cwd =
|
|
8802
|
+
const cwd = path12.resolve(options.cwd ?? process.cwd());
|
|
9116
8803
|
const allowedPaths = (options.allowedPaths ?? [cwd]).map(
|
|
9117
|
-
(allowedPath) =>
|
|
8804
|
+
(allowedPath) => path12.resolve(cwd, allowedPath)
|
|
9118
8805
|
);
|
|
9119
8806
|
const runCommand2 = options.runCommand ?? defaultRunCommand;
|
|
9120
8807
|
const runCommandTool = {
|
|
@@ -11441,8 +11128,15 @@ async function resolveApiKey(explicitApiKey) {
|
|
|
11441
11128
|
if (normalizedExplicitApiKey) {
|
|
11442
11129
|
return normalizedExplicitApiKey;
|
|
11443
11130
|
}
|
|
11444
|
-
const { store } =
|
|
11445
|
-
|
|
11131
|
+
const { store } = createSecretStore({
|
|
11132
|
+
backendEnvVar: "POE_AUTH_BACKEND",
|
|
11133
|
+
fileStore: {
|
|
11134
|
+
salt: "poe-code:encrypted-file-auth-store:v1",
|
|
11135
|
+
defaultDirectory: ".poe-code",
|
|
11136
|
+
defaultFileName: "credentials.enc"
|
|
11137
|
+
}
|
|
11138
|
+
});
|
|
11139
|
+
const storedApiKey = normalizeNonEmptyString(await store.get());
|
|
11446
11140
|
if (storedApiKey) {
|
|
11447
11141
|
return storedApiKey;
|
|
11448
11142
|
}
|
|
@@ -12451,7 +12145,7 @@ var init_spawn3 = __esm({
|
|
|
12451
12145
|
});
|
|
12452
12146
|
|
|
12453
12147
|
// packages/pipeline/src/utils.ts
|
|
12454
|
-
function
|
|
12148
|
+
function isRecord2(value) {
|
|
12455
12149
|
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
12456
12150
|
}
|
|
12457
12151
|
function isNotFound2(error2) {
|
|
@@ -12485,7 +12179,7 @@ var init_utils2 = __esm({
|
|
|
12485
12179
|
});
|
|
12486
12180
|
|
|
12487
12181
|
// packages/pipeline/src/config/loader.ts
|
|
12488
|
-
import
|
|
12182
|
+
import path13 from "node:path";
|
|
12489
12183
|
import { parse as parse4 } from "yaml";
|
|
12490
12184
|
function asStepMode(value) {
|
|
12491
12185
|
if (value === void 0 || value === null) {
|
|
@@ -12509,19 +12203,19 @@ function parseStepConfigDocument(filePath, content) {
|
|
|
12509
12203
|
if (document === null || document === void 0) {
|
|
12510
12204
|
return {};
|
|
12511
12205
|
}
|
|
12512
|
-
if (!
|
|
12206
|
+
if (!isRecord2(document)) {
|
|
12513
12207
|
throw new Error(`Invalid pipeline step config in "${filePath}": expected a top-level object.`);
|
|
12514
12208
|
}
|
|
12515
12209
|
const stepsValue = document.steps;
|
|
12516
12210
|
if (stepsValue === void 0 || stepsValue === null) {
|
|
12517
12211
|
return {};
|
|
12518
12212
|
}
|
|
12519
|
-
if (!
|
|
12213
|
+
if (!isRecord2(stepsValue)) {
|
|
12520
12214
|
throw new Error(`Invalid pipeline step config in "${filePath}": "steps" must be an object.`);
|
|
12521
12215
|
}
|
|
12522
12216
|
const steps = {};
|
|
12523
12217
|
for (const [stepName, value] of Object.entries(stepsValue)) {
|
|
12524
|
-
if (!
|
|
12218
|
+
if (!isRecord2(value)) {
|
|
12525
12219
|
throw new Error(`Invalid step "${stepName}" in "${filePath}": expected an object.`);
|
|
12526
12220
|
}
|
|
12527
12221
|
const instruction = value.instruction;
|
|
@@ -12543,7 +12237,7 @@ function parseConfigDocument(filePath, content) {
|
|
|
12543
12237
|
if (document === null || document === void 0) {
|
|
12544
12238
|
return {};
|
|
12545
12239
|
}
|
|
12546
|
-
if (!
|
|
12240
|
+
if (!isRecord2(document)) {
|
|
12547
12241
|
throw new Error(`Invalid pipeline config in "${filePath}": expected a top-level object.`);
|
|
12548
12242
|
}
|
|
12549
12243
|
const planPath = document.planPath;
|
|
@@ -12569,8 +12263,8 @@ async function loadStepsFile(fs3, filePath) {
|
|
|
12569
12263
|
return parseStepConfigDocument(filePath, content);
|
|
12570
12264
|
}
|
|
12571
12265
|
async function loadPipelineConfig(options) {
|
|
12572
|
-
const globalPath =
|
|
12573
|
-
const projectPath =
|
|
12266
|
+
const globalPath = path13.join(options.homeDir, ".poe-code", "pipeline", "config.yaml");
|
|
12267
|
+
const projectPath = path13.join(options.cwd, ".poe-code", "pipeline", "config.yaml");
|
|
12574
12268
|
const [globalConfig2, projectConfig] = await Promise.all([
|
|
12575
12269
|
loadConfigFile(options.fs, globalPath),
|
|
12576
12270
|
loadConfigFile(options.fs, projectPath)
|
|
@@ -12581,8 +12275,8 @@ async function loadPipelineConfig(options) {
|
|
|
12581
12275
|
};
|
|
12582
12276
|
}
|
|
12583
12277
|
async function loadResolvedSteps(options) {
|
|
12584
|
-
const globalPath =
|
|
12585
|
-
const projectPath =
|
|
12278
|
+
const globalPath = path13.join(options.homeDir, ".poe-code", "pipeline", "steps.yaml");
|
|
12279
|
+
const projectPath = path13.join(options.cwd, ".poe-code", "pipeline", "steps.yaml");
|
|
12586
12280
|
const [globalSteps, projectSteps] = await Promise.all([
|
|
12587
12281
|
loadStepsFile(options.fs, globalPath),
|
|
12588
12282
|
loadStepsFile(options.fs, projectPath)
|
|
@@ -12621,7 +12315,7 @@ function parseTaskStatus(value, availableSteps, taskId) {
|
|
|
12621
12315
|
if (typeof value === "string") {
|
|
12622
12316
|
return normalizeStatus(value, "task status");
|
|
12623
12317
|
}
|
|
12624
|
-
if (!
|
|
12318
|
+
if (!isRecord2(value)) {
|
|
12625
12319
|
throw new Error(`Invalid status for task "${taskId}": expected a string or step-status map.`);
|
|
12626
12320
|
}
|
|
12627
12321
|
const statusMap = {};
|
|
@@ -12641,7 +12335,7 @@ function parsePlan(yamlContent, options = {}) {
|
|
|
12641
12335
|
const message = error2 instanceof Error ? error2.message : String(error2);
|
|
12642
12336
|
throw new Error(`Invalid plan YAML: ${message}`);
|
|
12643
12337
|
}
|
|
12644
|
-
if (!
|
|
12338
|
+
if (!isRecord2(document)) {
|
|
12645
12339
|
throw new Error("Invalid plan YAML: expected a top-level object.");
|
|
12646
12340
|
}
|
|
12647
12341
|
const tasksValue = document.tasks;
|
|
@@ -12650,7 +12344,7 @@ function parsePlan(yamlContent, options = {}) {
|
|
|
12650
12344
|
}
|
|
12651
12345
|
const ids = /* @__PURE__ */ new Set();
|
|
12652
12346
|
const tasks = tasksValue.map((value, index) => {
|
|
12653
|
-
if (!
|
|
12347
|
+
if (!isRecord2(value)) {
|
|
12654
12348
|
throw new Error(`Invalid tasks[${index}]: expected an object.`);
|
|
12655
12349
|
}
|
|
12656
12350
|
const id = asRequiredString(value.id, `tasks[${index}].id`);
|
|
@@ -12675,7 +12369,7 @@ var init_parser = __esm({
|
|
|
12675
12369
|
});
|
|
12676
12370
|
|
|
12677
12371
|
// packages/pipeline/src/plan/discovery.ts
|
|
12678
|
-
import
|
|
12372
|
+
import path14 from "node:path";
|
|
12679
12373
|
import * as fsPromises3 from "node:fs/promises";
|
|
12680
12374
|
function createDefaultFs() {
|
|
12681
12375
|
return {
|
|
@@ -12711,7 +12405,7 @@ function countCompletedTasks(planPath, content) {
|
|
|
12711
12405
|
};
|
|
12712
12406
|
}
|
|
12713
12407
|
async function ensurePlanExists(fs3, cwd, planPath) {
|
|
12714
|
-
const absolutePath =
|
|
12408
|
+
const absolutePath = path14.isAbsolute(planPath) ? planPath : path14.resolve(cwd, planPath);
|
|
12715
12409
|
try {
|
|
12716
12410
|
const stat6 = await fs3.stat(absolutePath);
|
|
12717
12411
|
if (!stat6.isFile()) {
|
|
@@ -12739,20 +12433,20 @@ async function scanPlansDir(fs3, plansDir, displayPrefix) {
|
|
|
12739
12433
|
if (!isPlanCandidateFile(entry)) {
|
|
12740
12434
|
continue;
|
|
12741
12435
|
}
|
|
12742
|
-
const absolutePath =
|
|
12436
|
+
const absolutePath = path14.join(plansDir, entry);
|
|
12743
12437
|
const stat6 = await fs3.stat(absolutePath);
|
|
12744
12438
|
if (!stat6.isFile()) {
|
|
12745
12439
|
continue;
|
|
12746
12440
|
}
|
|
12747
|
-
const displayPath =
|
|
12441
|
+
const displayPath = path14.join(displayPrefix, entry);
|
|
12748
12442
|
const content = await fs3.readFile(absolutePath, "utf8");
|
|
12749
12443
|
candidates.push(countCompletedTasks(displayPath, content));
|
|
12750
12444
|
}
|
|
12751
12445
|
return candidates;
|
|
12752
12446
|
}
|
|
12753
12447
|
async function listPlanCandidates(fs3, cwd, homeDir) {
|
|
12754
|
-
const projectDir =
|
|
12755
|
-
const globalDir =
|
|
12448
|
+
const projectDir = path14.join(cwd, ".poe-code", "pipeline", "plans");
|
|
12449
|
+
const globalDir = path14.join(homeDir, ".poe-code", "pipeline", "plans");
|
|
12756
12450
|
const [projectCandidates, globalCandidates] = await Promise.all([
|
|
12757
12451
|
scanPlansDir(fs3, projectDir, ".poe-code/pipeline/plans"),
|
|
12758
12452
|
scanPlansDir(fs3, globalDir, "~/.poe-code/pipeline/plans")
|
|
@@ -12763,9 +12457,9 @@ async function listPlanCandidates(fs3, cwd, homeDir) {
|
|
|
12763
12457
|
}
|
|
12764
12458
|
function resolveAbsolutePlanPath(planPath, cwd, homeDir) {
|
|
12765
12459
|
if (planPath.startsWith("~/")) {
|
|
12766
|
-
return
|
|
12460
|
+
return path14.join(homeDir, planPath.slice(2));
|
|
12767
12461
|
}
|
|
12768
|
-
return
|
|
12462
|
+
return path14.isAbsolute(planPath) ? planPath : path14.resolve(cwd, planPath);
|
|
12769
12463
|
}
|
|
12770
12464
|
async function resolvePlanPath(options) {
|
|
12771
12465
|
const fs3 = options.fs ?? createDefaultFs();
|
|
@@ -13008,7 +12702,7 @@ var init_lock = __esm({
|
|
|
13008
12702
|
});
|
|
13009
12703
|
|
|
13010
12704
|
// packages/pipeline/src/run/pipeline.ts
|
|
13011
|
-
import
|
|
12705
|
+
import path15 from "node:path";
|
|
13012
12706
|
import * as fsPromises5 from "node:fs/promises";
|
|
13013
12707
|
function createDefaultFs3() {
|
|
13014
12708
|
return {
|
|
@@ -13044,9 +12738,9 @@ function resolveMode(stepName, steps) {
|
|
|
13044
12738
|
return step.mode;
|
|
13045
12739
|
}
|
|
13046
12740
|
async function archivePlan(fs3, absolutePlanPath) {
|
|
13047
|
-
const dir =
|
|
13048
|
-
const archiveDir =
|
|
13049
|
-
const archivePath =
|
|
12741
|
+
const dir = path15.dirname(absolutePlanPath);
|
|
12742
|
+
const archiveDir = path15.join(dir, "archive");
|
|
12743
|
+
const archivePath = path15.join(archiveDir, path15.basename(absolutePlanPath));
|
|
13050
12744
|
await fs3.mkdir(archiveDir, { recursive: true });
|
|
13051
12745
|
await fs3.rename(absolutePlanPath, archivePath);
|
|
13052
12746
|
}
|
|
@@ -13383,13 +13077,13 @@ async function readErrorBody(response) {
|
|
|
13383
13077
|
}
|
|
13384
13078
|
}
|
|
13385
13079
|
function extractTextContent(data) {
|
|
13386
|
-
if (!
|
|
13080
|
+
if (!isRecord3(data)) return void 0;
|
|
13387
13081
|
const choices = data.choices;
|
|
13388
13082
|
if (!Array.isArray(choices) || choices.length === 0) return void 0;
|
|
13389
13083
|
const first = choices[0];
|
|
13390
|
-
if (!
|
|
13084
|
+
if (!isRecord3(first)) return void 0;
|
|
13391
13085
|
const message = first.message;
|
|
13392
|
-
if (!
|
|
13086
|
+
if (!isRecord3(message)) return void 0;
|
|
13393
13087
|
return typeof message.content === "string" ? message.content : void 0;
|
|
13394
13088
|
}
|
|
13395
13089
|
function extractMediaFromCompletion(data) {
|
|
@@ -13397,14 +13091,14 @@ function extractMediaFromCompletion(data) {
|
|
|
13397
13091
|
if (!content) return {};
|
|
13398
13092
|
try {
|
|
13399
13093
|
const parsed = JSON.parse(content);
|
|
13400
|
-
if (
|
|
13094
|
+
if (isRecord3(parsed) && typeof parsed.url === "string") {
|
|
13401
13095
|
return {
|
|
13402
13096
|
url: parsed.url,
|
|
13403
13097
|
mimeType: typeof parsed.mimeType === "string" ? parsed.mimeType : void 0,
|
|
13404
13098
|
data: typeof parsed.data === "string" ? parsed.data : void 0
|
|
13405
13099
|
};
|
|
13406
13100
|
}
|
|
13407
|
-
if (
|
|
13101
|
+
if (isRecord3(parsed) && typeof parsed.data === "string") {
|
|
13408
13102
|
return {
|
|
13409
13103
|
data: parsed.data,
|
|
13410
13104
|
mimeType: typeof parsed.mimeType === "string" ? parsed.mimeType : void 0
|
|
@@ -13438,7 +13132,7 @@ function isValidUrl(value) {
|
|
|
13438
13132
|
return false;
|
|
13439
13133
|
}
|
|
13440
13134
|
}
|
|
13441
|
-
function
|
|
13135
|
+
function isRecord3(value) {
|
|
13442
13136
|
return Boolean(value && typeof value === "object" && !Array.isArray(value));
|
|
13443
13137
|
}
|
|
13444
13138
|
var init_llm_client = __esm({
|
|
@@ -13478,6 +13172,213 @@ var init_client_instance = __esm({
|
|
|
13478
13172
|
}
|
|
13479
13173
|
});
|
|
13480
13174
|
|
|
13175
|
+
// packages/poe-oauth/src/check-auth.ts
|
|
13176
|
+
var init_check_auth = __esm({
|
|
13177
|
+
"packages/poe-oauth/src/check-auth.ts"() {
|
|
13178
|
+
"use strict";
|
|
13179
|
+
}
|
|
13180
|
+
});
|
|
13181
|
+
|
|
13182
|
+
// packages/poe-oauth/src/api-key-validation.ts
|
|
13183
|
+
var init_api_key_validation = __esm({
|
|
13184
|
+
"packages/poe-oauth/src/api-key-validation.ts"() {
|
|
13185
|
+
"use strict";
|
|
13186
|
+
}
|
|
13187
|
+
});
|
|
13188
|
+
|
|
13189
|
+
// packages/poe-oauth/src/oauth-client.ts
|
|
13190
|
+
import http from "node:http";
|
|
13191
|
+
import crypto from "node:crypto";
|
|
13192
|
+
function createOAuthClient(config2) {
|
|
13193
|
+
const fetchFn = config2.fetch ?? globalThis.fetch;
|
|
13194
|
+
return {
|
|
13195
|
+
authorize: () => startAuthorization(config2, fetchFn)
|
|
13196
|
+
};
|
|
13197
|
+
}
|
|
13198
|
+
function generateCodeVerifier() {
|
|
13199
|
+
return crypto.randomBytes(32).toString("base64url");
|
|
13200
|
+
}
|
|
13201
|
+
function generateCodeChallenge(verifier) {
|
|
13202
|
+
return crypto.createHash("sha256").update(verifier).digest("base64url");
|
|
13203
|
+
}
|
|
13204
|
+
async function startAuthorization(config2, fetchFn) {
|
|
13205
|
+
const codeVerifier = generateCodeVerifier();
|
|
13206
|
+
const codeChallenge = generateCodeChallenge(codeVerifier);
|
|
13207
|
+
const server = config2.createServer ? config2.createServer() : http.createServer();
|
|
13208
|
+
const port = await startServer(server);
|
|
13209
|
+
const redirectUri = `http://127.0.0.1:${port}/callback`;
|
|
13210
|
+
const authorizationUrl = buildAuthorizationUrl({
|
|
13211
|
+
endpoint: config2.authorizationEndpoint,
|
|
13212
|
+
clientId: config2.clientId,
|
|
13213
|
+
redirectUri,
|
|
13214
|
+
codeChallenge
|
|
13215
|
+
});
|
|
13216
|
+
const waitForResult = async () => {
|
|
13217
|
+
try {
|
|
13218
|
+
const code = await waitForAuthorizationCode(server, config2, authorizationUrl);
|
|
13219
|
+
return await exchangeCodeForApiKey({
|
|
13220
|
+
tokenEndpoint: config2.tokenEndpoint,
|
|
13221
|
+
code,
|
|
13222
|
+
codeVerifier,
|
|
13223
|
+
clientId: config2.clientId,
|
|
13224
|
+
redirectUri,
|
|
13225
|
+
fetchFn
|
|
13226
|
+
});
|
|
13227
|
+
} finally {
|
|
13228
|
+
server.closeAllConnections?.();
|
|
13229
|
+
server.close();
|
|
13230
|
+
}
|
|
13231
|
+
};
|
|
13232
|
+
return { authorizationUrl, waitForResult };
|
|
13233
|
+
}
|
|
13234
|
+
function startServer(server) {
|
|
13235
|
+
return new Promise((resolve) => {
|
|
13236
|
+
server.listen(0, "127.0.0.1", () => {
|
|
13237
|
+
const address = server.address();
|
|
13238
|
+
resolve(address.port);
|
|
13239
|
+
});
|
|
13240
|
+
});
|
|
13241
|
+
}
|
|
13242
|
+
function buildAuthorizationUrl(params) {
|
|
13243
|
+
const url2 = new URL(params.endpoint);
|
|
13244
|
+
url2.searchParams.set("response_type", "code");
|
|
13245
|
+
url2.searchParams.set("client_id", params.clientId);
|
|
13246
|
+
url2.searchParams.set("scope", "apikey:create");
|
|
13247
|
+
url2.searchParams.set("code_challenge", params.codeChallenge);
|
|
13248
|
+
url2.searchParams.set("code_challenge_method", "S256");
|
|
13249
|
+
url2.searchParams.set("redirect_uri", params.redirectUri);
|
|
13250
|
+
return url2.toString();
|
|
13251
|
+
}
|
|
13252
|
+
function waitForAuthorizationCode(server, config2, authorizationUrl) {
|
|
13253
|
+
return new Promise((resolve, reject) => {
|
|
13254
|
+
let settled = false;
|
|
13255
|
+
const settle = (fn) => {
|
|
13256
|
+
if (!settled) {
|
|
13257
|
+
settled = true;
|
|
13258
|
+
fn();
|
|
13259
|
+
}
|
|
13260
|
+
};
|
|
13261
|
+
server.on("request", (req, res) => {
|
|
13262
|
+
const url2 = new URL(req.url, `http://127.0.0.1`);
|
|
13263
|
+
if (url2.pathname !== "/callback") {
|
|
13264
|
+
res.writeHead(404);
|
|
13265
|
+
res.end("Not found");
|
|
13266
|
+
return;
|
|
13267
|
+
}
|
|
13268
|
+
const error2 = url2.searchParams.get("error");
|
|
13269
|
+
if (error2) {
|
|
13270
|
+
const description = url2.searchParams.get("error_description") ?? error2;
|
|
13271
|
+
res.writeHead(400);
|
|
13272
|
+
res.end(`Authorization failed: ${description}`);
|
|
13273
|
+
settle(() => reject(new Error(`OAuth authorization failed: ${error2} \u2014 ${description}`)));
|
|
13274
|
+
return;
|
|
13275
|
+
}
|
|
13276
|
+
const code = url2.searchParams.get("code");
|
|
13277
|
+
if (!code) {
|
|
13278
|
+
res.writeHead(400);
|
|
13279
|
+
res.end("Missing authorization code");
|
|
13280
|
+
settle(() => reject(new Error("OAuth callback missing authorization code")));
|
|
13281
|
+
return;
|
|
13282
|
+
}
|
|
13283
|
+
res.writeHead(200, { "Content-Type": "text/html" });
|
|
13284
|
+
res.end(buildSuccessPage());
|
|
13285
|
+
settle(() => resolve(code));
|
|
13286
|
+
});
|
|
13287
|
+
if (config2.readLine) {
|
|
13288
|
+
config2.readLine().then((input) => {
|
|
13289
|
+
const code = extractCodeFromInput(input);
|
|
13290
|
+
if (code) {
|
|
13291
|
+
settle(() => resolve(code));
|
|
13292
|
+
}
|
|
13293
|
+
}).catch(() => {
|
|
13294
|
+
});
|
|
13295
|
+
}
|
|
13296
|
+
if (config2.openBrowser) {
|
|
13297
|
+
config2.openBrowser(authorizationUrl).catch(
|
|
13298
|
+
(err) => settle(() => reject(err))
|
|
13299
|
+
);
|
|
13300
|
+
}
|
|
13301
|
+
});
|
|
13302
|
+
}
|
|
13303
|
+
function extractCodeFromInput(input) {
|
|
13304
|
+
const trimmed = input.replace(/[\r\n]/g, "").trim();
|
|
13305
|
+
if (trimmed.length === 0) {
|
|
13306
|
+
return null;
|
|
13307
|
+
}
|
|
13308
|
+
try {
|
|
13309
|
+
const url2 = new URL(trimmed);
|
|
13310
|
+
return url2.searchParams.get("code");
|
|
13311
|
+
} catch {
|
|
13312
|
+
return trimmed;
|
|
13313
|
+
}
|
|
13314
|
+
}
|
|
13315
|
+
async function exchangeCodeForApiKey(params) {
|
|
13316
|
+
const body = new URLSearchParams({
|
|
13317
|
+
grant_type: "authorization_code",
|
|
13318
|
+
code: params.code,
|
|
13319
|
+
code_verifier: params.codeVerifier,
|
|
13320
|
+
client_id: params.clientId,
|
|
13321
|
+
redirect_uri: params.redirectUri
|
|
13322
|
+
});
|
|
13323
|
+
const response = await params.fetchFn(params.tokenEndpoint, {
|
|
13324
|
+
method: "POST",
|
|
13325
|
+
headers: { "Content-Type": "application/x-www-form-urlencoded" },
|
|
13326
|
+
body: body.toString()
|
|
13327
|
+
});
|
|
13328
|
+
if (!response.ok) {
|
|
13329
|
+
const text4 = await response.text();
|
|
13330
|
+
const description = parseErrorDescription(text4);
|
|
13331
|
+
throw new Error(description ?? `Token exchange failed (${response.status}): ${text4}`);
|
|
13332
|
+
}
|
|
13333
|
+
const data = await response.json();
|
|
13334
|
+
if (typeof data.api_key !== "string" || data.api_key.length === 0) {
|
|
13335
|
+
throw new Error("Token response missing api_key field");
|
|
13336
|
+
}
|
|
13337
|
+
return {
|
|
13338
|
+
apiKey: data.api_key,
|
|
13339
|
+
expiresIn: typeof data.api_key_expires_in === "number" ? data.api_key_expires_in : null
|
|
13340
|
+
};
|
|
13341
|
+
}
|
|
13342
|
+
function parseErrorDescription(text4) {
|
|
13343
|
+
try {
|
|
13344
|
+
const data = JSON.parse(text4);
|
|
13345
|
+
if (typeof data.error_description === "string") {
|
|
13346
|
+
return data.error_description;
|
|
13347
|
+
}
|
|
13348
|
+
if (typeof data.error === "string") {
|
|
13349
|
+
return data.error;
|
|
13350
|
+
}
|
|
13351
|
+
} catch {
|
|
13352
|
+
}
|
|
13353
|
+
return null;
|
|
13354
|
+
}
|
|
13355
|
+
function buildSuccessPage() {
|
|
13356
|
+
return [
|
|
13357
|
+
"<!DOCTYPE html>",
|
|
13358
|
+
"<html><head><meta charset=utf-8><title>Connected to Poe</title></head>",
|
|
13359
|
+
'<body style="font-family:system-ui,sans-serif;display:flex;align-items:center;justify-content:center;min-height:100vh;margin:0">',
|
|
13360
|
+
'<div style="text-align:center">',
|
|
13361
|
+
"<h1>Connected to Poe</h1>",
|
|
13362
|
+
'<p style="color:#666">You can close this tab and return to your terminal.</p>',
|
|
13363
|
+
"</div></body></html>"
|
|
13364
|
+
].join("");
|
|
13365
|
+
}
|
|
13366
|
+
var init_oauth_client = __esm({
|
|
13367
|
+
"packages/poe-oauth/src/oauth-client.ts"() {
|
|
13368
|
+
"use strict";
|
|
13369
|
+
}
|
|
13370
|
+
});
|
|
13371
|
+
|
|
13372
|
+
// packages/poe-oauth/src/index.ts
|
|
13373
|
+
var init_src10 = __esm({
|
|
13374
|
+
"packages/poe-oauth/src/index.ts"() {
|
|
13375
|
+
"use strict";
|
|
13376
|
+
init_check_auth();
|
|
13377
|
+
init_api_key_validation();
|
|
13378
|
+
init_oauth_client();
|
|
13379
|
+
}
|
|
13380
|
+
});
|
|
13381
|
+
|
|
13481
13382
|
// src/cli/oauth-login.ts
|
|
13482
13383
|
import { exec as exec2 } from "node:child_process";
|
|
13483
13384
|
import readline from "node:readline";
|
|
@@ -13522,7 +13423,7 @@ function openInBrowser(url2) {
|
|
|
13522
13423
|
var init_oauth_login = __esm({
|
|
13523
13424
|
"src/cli/oauth-login.ts"() {
|
|
13524
13425
|
"use strict";
|
|
13525
|
-
|
|
13426
|
+
init_src10();
|
|
13526
13427
|
init_src4();
|
|
13527
13428
|
}
|
|
13528
13429
|
});
|
|
@@ -13569,21 +13470,21 @@ function createCliContainer(dependencies) {
|
|
|
13569
13470
|
unlink: (filePath) => dependencies.fs.unlink(filePath),
|
|
13570
13471
|
chmod: (filePath, mode) => dependencies.fs.chmod ? dependencies.fs.chmod(filePath, mode) : Promise.resolve()
|
|
13571
13472
|
};
|
|
13572
|
-
const { store: authStore } =
|
|
13473
|
+
const { store: authStore } = createSecretStore({
|
|
13474
|
+
backendEnvVar: "POE_AUTH_BACKEND",
|
|
13573
13475
|
env: dependencies.env.variables,
|
|
13574
13476
|
platform: dependencies.env.platform,
|
|
13575
13477
|
fileStore: {
|
|
13576
13478
|
fs: authFs,
|
|
13577
|
-
|
|
13578
|
-
|
|
13579
|
-
|
|
13580
|
-
fs: authFs,
|
|
13479
|
+
salt: "poe-code:encrypted-file-auth-store:v1",
|
|
13480
|
+
defaultDirectory: ".poe-code",
|
|
13481
|
+
defaultFileName: "credentials.enc",
|
|
13581
13482
|
getHomeDirectory: () => dependencies.env.homeDir
|
|
13582
13483
|
}
|
|
13583
13484
|
});
|
|
13584
|
-
const readApiKey = authStore.
|
|
13585
|
-
const writeApiKey = authStore.
|
|
13586
|
-
const deleteApiKey = authStore.
|
|
13485
|
+
const readApiKey = authStore.get.bind(authStore);
|
|
13486
|
+
const writeApiKey = authStore.set.bind(authStore);
|
|
13487
|
+
const deleteApiKey = authStore.delete.bind(authStore);
|
|
13587
13488
|
const oauthEnabled = (dependencies.env.variables ?? process.env).POE_CODE_OAUTH_LOGIN !== "0";
|
|
13588
13489
|
const options = createOptionResolvers({
|
|
13589
13490
|
prompts: dependencies.prompts,
|
|
@@ -13653,7 +13554,7 @@ var init_container2 = __esm({
|
|
|
13653
13554
|
});
|
|
13654
13555
|
|
|
13655
13556
|
// src/services/config.ts
|
|
13656
|
-
import
|
|
13557
|
+
import path17 from "node:path";
|
|
13657
13558
|
async function deleteConfig(options) {
|
|
13658
13559
|
const { fs: fs3, filePath } = options;
|
|
13659
13560
|
try {
|
|
@@ -13723,7 +13624,7 @@ async function readConfigDocument(fs3, filePath) {
|
|
|
13723
13624
|
}
|
|
13724
13625
|
}
|
|
13725
13626
|
async function migrateLegacyCredentialsFile(fs3, configPath) {
|
|
13726
|
-
const legacyPath =
|
|
13627
|
+
const legacyPath = path17.join(path17.dirname(configPath), "credentials.json");
|
|
13727
13628
|
try {
|
|
13728
13629
|
const raw = await fs3.readFile(legacyPath, "utf8");
|
|
13729
13630
|
const document = await parseConfigDocument2(fs3, legacyPath, raw);
|
|
@@ -13747,7 +13648,7 @@ async function parseConfigDocument2(fs3, filePath, raw) {
|
|
|
13747
13648
|
}
|
|
13748
13649
|
}
|
|
13749
13650
|
function normalizeConfigDocument(value) {
|
|
13750
|
-
if (!
|
|
13651
|
+
if (!isRecord4(value)) {
|
|
13751
13652
|
return {};
|
|
13752
13653
|
}
|
|
13753
13654
|
const document = {};
|
|
@@ -13761,12 +13662,12 @@ function normalizeConfigDocument(value) {
|
|
|
13761
13662
|
return document;
|
|
13762
13663
|
}
|
|
13763
13664
|
function normalizeConfiguredServices(value) {
|
|
13764
|
-
if (!
|
|
13665
|
+
if (!isRecord4(value)) {
|
|
13765
13666
|
return {};
|
|
13766
13667
|
}
|
|
13767
13668
|
const entries = {};
|
|
13768
13669
|
for (const [key, entry] of Object.entries(value)) {
|
|
13769
|
-
if (!
|
|
13670
|
+
if (!isRecord4(entry)) {
|
|
13770
13671
|
continue;
|
|
13771
13672
|
}
|
|
13772
13673
|
const normalized = normalizeConfiguredServiceMetadata({
|
|
@@ -13777,7 +13678,7 @@ function normalizeConfiguredServices(value) {
|
|
|
13777
13678
|
return entries;
|
|
13778
13679
|
}
|
|
13779
13680
|
async function writeConfigDocument(fs3, filePath, document) {
|
|
13780
|
-
await fs3.mkdir(
|
|
13681
|
+
await fs3.mkdir(path17.dirname(filePath), { recursive: true });
|
|
13781
13682
|
const payload = {};
|
|
13782
13683
|
if (document.apiKey) {
|
|
13783
13684
|
payload.apiKey = document.apiKey;
|
|
@@ -13797,11 +13698,11 @@ async function recoverInvalidConfig(fs3, filePath, content) {
|
|
|
13797
13698
|
}
|
|
13798
13699
|
function createInvalidBackupPath(filePath) {
|
|
13799
13700
|
const timestamp = (/* @__PURE__ */ new Date()).toISOString().replace(/[:.]/g, "-");
|
|
13800
|
-
const dir =
|
|
13801
|
-
const base =
|
|
13802
|
-
return
|
|
13701
|
+
const dir = path17.dirname(filePath);
|
|
13702
|
+
const base = path17.basename(filePath);
|
|
13703
|
+
return path17.join(dir, `${base}.invalid-${timestamp}.json`);
|
|
13803
13704
|
}
|
|
13804
|
-
function
|
|
13705
|
+
function isRecord4(value) {
|
|
13805
13706
|
return Boolean(value && typeof value === "object" && !Array.isArray(value));
|
|
13806
13707
|
}
|
|
13807
13708
|
var EMPTY_DOCUMENT;
|
|
@@ -14061,7 +13962,7 @@ var init_agent2 = __esm({
|
|
|
14061
13962
|
});
|
|
14062
13963
|
|
|
14063
13964
|
// src/cli/commands/spawn.ts
|
|
14064
|
-
import
|
|
13965
|
+
import path18 from "node:path";
|
|
14065
13966
|
function registerSpawnCommand(program, container, options = {}) {
|
|
14066
13967
|
const spawnServices = container.registry.list().filter((service) => typeof service.spawn === "function" || getSpawnConfig(service.name)).map((service) => service.name);
|
|
14067
13968
|
const extraServices = options.extraServices ?? [];
|
|
@@ -14272,10 +14173,10 @@ function resolveSpawnWorkingDirectory2(baseDir, candidate) {
|
|
|
14272
14173
|
if (!candidate || candidate.trim().length === 0) {
|
|
14273
14174
|
return void 0;
|
|
14274
14175
|
}
|
|
14275
|
-
if (
|
|
14176
|
+
if (path18.isAbsolute(candidate)) {
|
|
14276
14177
|
return candidate;
|
|
14277
14178
|
}
|
|
14278
|
-
return
|
|
14179
|
+
return path18.resolve(baseDir, candidate);
|
|
14279
14180
|
}
|
|
14280
14181
|
function parseMcpSpawnConfig2(input) {
|
|
14281
14182
|
if (!input) {
|
|
@@ -14395,7 +14296,7 @@ var init_spawn4 = __esm({
|
|
|
14395
14296
|
});
|
|
14396
14297
|
|
|
14397
14298
|
// src/sdk/research.ts
|
|
14398
|
-
import
|
|
14299
|
+
import path19 from "node:path";
|
|
14399
14300
|
async function research(container, options) {
|
|
14400
14301
|
const logger2 = options.logger;
|
|
14401
14302
|
const source = await resolveSource({
|
|
@@ -14430,7 +14331,7 @@ async function research(container, options) {
|
|
|
14430
14331
|
markdown: markdownOutput
|
|
14431
14332
|
});
|
|
14432
14333
|
outputPath = buildOutputPath(container.env.homeDir, options.prompt);
|
|
14433
|
-
await ensureDirectory2(container.fs,
|
|
14334
|
+
await ensureDirectory2(container.fs, path19.dirname(outputPath));
|
|
14434
14335
|
await container.fs.writeFile(outputPath, document, {
|
|
14435
14336
|
encoding: "utf8"
|
|
14436
14337
|
});
|
|
@@ -14505,7 +14406,7 @@ function buildResearchDocument(input) {
|
|
|
14505
14406
|
}
|
|
14506
14407
|
function buildClonePath(homeDir, github) {
|
|
14507
14408
|
const slug = extractRepoSlug(github);
|
|
14508
|
-
return
|
|
14409
|
+
return path19.join(homeDir, ".poe-code", "repos", slug);
|
|
14509
14410
|
}
|
|
14510
14411
|
function extractRepoSlug(value) {
|
|
14511
14412
|
const trimmed = value.trim();
|
|
@@ -14543,7 +14444,7 @@ function extractRepoSlug(value) {
|
|
|
14543
14444
|
function buildOutputPath(homeDir, prompt, now = /* @__PURE__ */ new Date()) {
|
|
14544
14445
|
const timestamp = formatTimestamp2(now);
|
|
14545
14446
|
const slug = buildSlug(prompt);
|
|
14546
|
-
return
|
|
14447
|
+
return path19.join(
|
|
14547
14448
|
homeDir,
|
|
14548
14449
|
".poe-code",
|
|
14549
14450
|
"research",
|
|
@@ -14564,7 +14465,7 @@ async function resolveSource(input) {
|
|
|
14564
14465
|
if (options.github) {
|
|
14565
14466
|
const cloneUrl = resolveGithubCloneUrl(options.github);
|
|
14566
14467
|
const clonePath = buildClonePath(container.env.homeDir, options.github);
|
|
14567
|
-
await ensureDirectory2(container.fs,
|
|
14468
|
+
await ensureDirectory2(container.fs, path19.dirname(clonePath));
|
|
14568
14469
|
const exists = await pathExists2(container.fs, clonePath);
|
|
14569
14470
|
if (!exists) {
|
|
14570
14471
|
const cloneResult = await container.commandRunner(
|
|
@@ -14662,10 +14563,10 @@ function formatYamlString(value) {
|
|
|
14662
14563
|
return JSON.stringify(value);
|
|
14663
14564
|
}
|
|
14664
14565
|
function resolvePath2(baseDir, candidate) {
|
|
14665
|
-
if (
|
|
14566
|
+
if (path19.isAbsolute(candidate)) {
|
|
14666
14567
|
return candidate;
|
|
14667
14568
|
}
|
|
14668
|
-
return
|
|
14569
|
+
return path19.resolve(baseDir, candidate);
|
|
14669
14570
|
}
|
|
14670
14571
|
function teeAcpStream(events) {
|
|
14671
14572
|
const chunks = [];
|
|
@@ -14725,7 +14626,7 @@ async function removePathFallback(fs3, target) {
|
|
|
14725
14626
|
if (stats && typeof stats.isDirectory === "function" && stats.isDirectory()) {
|
|
14726
14627
|
const entries = await fs3.readdir(target);
|
|
14727
14628
|
for (const entry of entries) {
|
|
14728
|
-
await removePathFallback(fs3,
|
|
14629
|
+
await removePathFallback(fs3, path19.join(target, entry));
|
|
14729
14630
|
}
|
|
14730
14631
|
}
|
|
14731
14632
|
try {
|
|
@@ -15064,10 +14965,7 @@ async function executeLogin(program, container, options) {
|
|
|
15064
14965
|
resources.context.finalize();
|
|
15065
14966
|
} catch (error2) {
|
|
15066
14967
|
if (error2 instanceof Error) {
|
|
15067
|
-
|
|
15068
|
-
operation: "login",
|
|
15069
|
-
configPath: container.env.configPath
|
|
15070
|
-
});
|
|
14968
|
+
throw new AuthenticationError(error2.message);
|
|
15071
14969
|
}
|
|
15072
14970
|
throw error2;
|
|
15073
14971
|
}
|
|
@@ -15120,10 +15018,11 @@ async function reconfigureServices(input) {
|
|
|
15120
15018
|
});
|
|
15121
15019
|
}
|
|
15122
15020
|
}
|
|
15123
|
-
var
|
|
15021
|
+
var init_login = __esm({
|
|
15124
15022
|
"src/cli/commands/login.ts"() {
|
|
15125
15023
|
"use strict";
|
|
15126
15024
|
init_shared();
|
|
15025
|
+
init_errors();
|
|
15127
15026
|
init_config2();
|
|
15128
15027
|
init_mutation_events();
|
|
15129
15028
|
}
|
|
@@ -15300,7 +15199,7 @@ async function executeLogout(program, container) {
|
|
|
15300
15199
|
});
|
|
15301
15200
|
resources.context.finalize();
|
|
15302
15201
|
}
|
|
15303
|
-
var
|
|
15202
|
+
var init_logout = __esm({
|
|
15304
15203
|
"src/cli/commands/logout.ts"() {
|
|
15305
15204
|
"use strict";
|
|
15306
15205
|
init_config2();
|
|
@@ -15405,8 +15304,8 @@ var init_auth = __esm({
|
|
|
15405
15304
|
init_errors();
|
|
15406
15305
|
init_config2();
|
|
15407
15306
|
init_shared();
|
|
15408
|
-
|
|
15409
|
-
|
|
15307
|
+
init_login();
|
|
15308
|
+
init_logout();
|
|
15410
15309
|
}
|
|
15411
15310
|
});
|
|
15412
15311
|
|
|
@@ -15606,7 +15505,7 @@ var init_media_download = __esm({
|
|
|
15606
15505
|
});
|
|
15607
15506
|
|
|
15608
15507
|
// src/cli/commands/generate.ts
|
|
15609
|
-
import
|
|
15508
|
+
import path20 from "node:path";
|
|
15610
15509
|
function registerGenerateCommand(program, container) {
|
|
15611
15510
|
const generate2 = program.command("generate").description("Generate content via Poe API").option("--model <model>", `Model identifier (default: ${DEFAULT_TEXT_MODEL})`).option(
|
|
15612
15511
|
"--param <key=value>",
|
|
@@ -15872,11 +15771,11 @@ function getDefaultMimeType(type) {
|
|
|
15872
15771
|
return defaults[type];
|
|
15873
15772
|
}
|
|
15874
15773
|
function resolveOutputPath(filename, cwd) {
|
|
15875
|
-
if (
|
|
15774
|
+
if (path20.isAbsolute(filename)) {
|
|
15876
15775
|
return { path: filename, label: filename };
|
|
15877
15776
|
}
|
|
15878
15777
|
return {
|
|
15879
|
-
path:
|
|
15778
|
+
path: path20.join(cwd, filename),
|
|
15880
15779
|
label: `./${filename}`
|
|
15881
15780
|
};
|
|
15882
15781
|
}
|
|
@@ -16980,8 +16879,8 @@ var init_parseUtil = __esm({
|
|
|
16980
16879
|
init_errors3();
|
|
16981
16880
|
init_en();
|
|
16982
16881
|
makeIssue = (params) => {
|
|
16983
|
-
const { data, path:
|
|
16984
|
-
const fullPath = [...
|
|
16882
|
+
const { data, path: path24, errorMaps, issueData } = params;
|
|
16883
|
+
const fullPath = [...path24, ...issueData.path || []];
|
|
16985
16884
|
const fullIssue = {
|
|
16986
16885
|
...issueData,
|
|
16987
16886
|
path: fullPath
|
|
@@ -17261,11 +17160,11 @@ var init_types4 = __esm({
|
|
|
17261
17160
|
init_parseUtil();
|
|
17262
17161
|
init_util();
|
|
17263
17162
|
ParseInputLazyPath = class {
|
|
17264
|
-
constructor(parent, value,
|
|
17163
|
+
constructor(parent, value, path24, key) {
|
|
17265
17164
|
this._cachedPath = [];
|
|
17266
17165
|
this.parent = parent;
|
|
17267
17166
|
this.data = value;
|
|
17268
|
-
this._path =
|
|
17167
|
+
this._path = path24;
|
|
17269
17168
|
this._key = key;
|
|
17270
17169
|
}
|
|
17271
17170
|
get path() {
|
|
@@ -20769,10 +20668,10 @@ function mergeDefs(...defs) {
|
|
|
20769
20668
|
function cloneDef(schema) {
|
|
20770
20669
|
return mergeDefs(schema._zod.def);
|
|
20771
20670
|
}
|
|
20772
|
-
function getElementAtPath(obj,
|
|
20773
|
-
if (!
|
|
20671
|
+
function getElementAtPath(obj, path24) {
|
|
20672
|
+
if (!path24)
|
|
20774
20673
|
return obj;
|
|
20775
|
-
return
|
|
20674
|
+
return path24.reduce((acc, key) => acc?.[key], obj);
|
|
20776
20675
|
}
|
|
20777
20676
|
function promiseAllObject(promisesObj) {
|
|
20778
20677
|
const keys = Object.keys(promisesObj);
|
|
@@ -21084,11 +20983,11 @@ function aborted(x, startIndex = 0) {
|
|
|
21084
20983
|
}
|
|
21085
20984
|
return false;
|
|
21086
20985
|
}
|
|
21087
|
-
function prefixIssues(
|
|
20986
|
+
function prefixIssues(path24, issues) {
|
|
21088
20987
|
return issues.map((iss) => {
|
|
21089
20988
|
var _a2;
|
|
21090
20989
|
(_a2 = iss).path ?? (_a2.path = []);
|
|
21091
|
-
iss.path.unshift(
|
|
20990
|
+
iss.path.unshift(path24);
|
|
21092
20991
|
return iss;
|
|
21093
20992
|
});
|
|
21094
20993
|
}
|
|
@@ -33249,8 +33148,8 @@ var require_utils = __commonJS({
|
|
|
33249
33148
|
}
|
|
33250
33149
|
return ind;
|
|
33251
33150
|
}
|
|
33252
|
-
function removeDotSegments(
|
|
33253
|
-
let input =
|
|
33151
|
+
function removeDotSegments(path24) {
|
|
33152
|
+
let input = path24;
|
|
33254
33153
|
const output = [];
|
|
33255
33154
|
let nextSlash = -1;
|
|
33256
33155
|
let len = 0;
|
|
@@ -33449,8 +33348,8 @@ var require_schemes = __commonJS({
|
|
|
33449
33348
|
wsComponent.secure = void 0;
|
|
33450
33349
|
}
|
|
33451
33350
|
if (wsComponent.resourceName) {
|
|
33452
|
-
const [
|
|
33453
|
-
wsComponent.path =
|
|
33351
|
+
const [path24, query] = wsComponent.resourceName.split("?");
|
|
33352
|
+
wsComponent.path = path24 && path24 !== "/" ? path24 : void 0;
|
|
33454
33353
|
wsComponent.query = query;
|
|
33455
33354
|
wsComponent.resourceName = void 0;
|
|
33456
33355
|
}
|
|
@@ -36683,7 +36582,7 @@ var init_content = __esm({
|
|
|
36683
36582
|
});
|
|
36684
36583
|
|
|
36685
36584
|
// packages/tiny-stdio-mcp-server/src/index.ts
|
|
36686
|
-
var
|
|
36585
|
+
var init_src11 = __esm({
|
|
36687
36586
|
"packages/tiny-stdio-mcp-server/src/index.ts"() {
|
|
36688
36587
|
"use strict";
|
|
36689
36588
|
init_server();
|
|
@@ -36987,7 +36886,7 @@ var generateTextSchema, generateImageSchema, generateVideoSchema, generateAudioS
|
|
|
36987
36886
|
var init_mcp_server = __esm({
|
|
36988
36887
|
"src/cli/mcp-server.ts"() {
|
|
36989
36888
|
"use strict";
|
|
36990
|
-
|
|
36889
|
+
init_src11();
|
|
36991
36890
|
init_client_instance();
|
|
36992
36891
|
init_constants();
|
|
36993
36892
|
generateTextSchema = defineSchema({
|
|
@@ -37393,9 +37292,9 @@ var init_shapes = __esm({
|
|
|
37393
37292
|
});
|
|
37394
37293
|
|
|
37395
37294
|
// packages/agent-mcp-config/src/apply.ts
|
|
37396
|
-
import
|
|
37295
|
+
import path21 from "node:path";
|
|
37397
37296
|
function getConfigDirectory(configPath) {
|
|
37398
|
-
return
|
|
37297
|
+
return path21.dirname(configPath);
|
|
37399
37298
|
}
|
|
37400
37299
|
function isConfigObject5(value) {
|
|
37401
37300
|
return Boolean(value) && typeof value === "object" && !Array.isArray(value);
|
|
@@ -37497,7 +37396,7 @@ var init_apply = __esm({
|
|
|
37497
37396
|
});
|
|
37498
37397
|
|
|
37499
37398
|
// packages/agent-mcp-config/src/index.ts
|
|
37500
|
-
var
|
|
37399
|
+
var init_src12 = __esm({
|
|
37501
37400
|
"packages/agent-mcp-config/src/index.ts"() {
|
|
37502
37401
|
"use strict";
|
|
37503
37402
|
init_configs2();
|
|
@@ -37677,7 +37576,7 @@ var init_mcp2 = __esm({
|
|
|
37677
37576
|
init_shared();
|
|
37678
37577
|
init_mcp_output_format();
|
|
37679
37578
|
init_command_not_found();
|
|
37680
|
-
|
|
37579
|
+
init_src12();
|
|
37681
37580
|
init_execution_context();
|
|
37682
37581
|
DEFAULT_MCP_AGENT = "claude-code";
|
|
37683
37582
|
}
|
|
@@ -37685,7 +37584,7 @@ var init_mcp2 = __esm({
|
|
|
37685
37584
|
|
|
37686
37585
|
// packages/agent-skill-config/src/configs.ts
|
|
37687
37586
|
import os2 from "node:os";
|
|
37688
|
-
import
|
|
37587
|
+
import path22 from "node:path";
|
|
37689
37588
|
function resolveAgentSupport2(input, registry2 = agentSkillConfigs) {
|
|
37690
37589
|
const resolvedId = resolveAgentId(input);
|
|
37691
37590
|
if (!resolvedId) {
|
|
@@ -37877,7 +37776,7 @@ var init_apply2 = __esm({
|
|
|
37877
37776
|
});
|
|
37878
37777
|
|
|
37879
37778
|
// packages/agent-skill-config/src/index.ts
|
|
37880
|
-
var
|
|
37779
|
+
var init_src13 = __esm({
|
|
37881
37780
|
"packages/agent-skill-config/src/index.ts"() {
|
|
37882
37781
|
"use strict";
|
|
37883
37782
|
init_configs3();
|
|
@@ -38102,7 +38001,7 @@ var init_skill = __esm({
|
|
|
38102
38001
|
"src/cli/commands/skill.ts"() {
|
|
38103
38002
|
"use strict";
|
|
38104
38003
|
init_src4();
|
|
38105
|
-
|
|
38004
|
+
init_src13();
|
|
38106
38005
|
init_shared();
|
|
38107
38006
|
init_command_not_found();
|
|
38108
38007
|
DEFAULT_SKILL_AGENT = "claude-code";
|
|
@@ -38696,7 +38595,7 @@ var init_models = __esm({
|
|
|
38696
38595
|
});
|
|
38697
38596
|
|
|
38698
38597
|
// src/cli/commands/pipeline.ts
|
|
38699
|
-
import
|
|
38598
|
+
import path23 from "node:path";
|
|
38700
38599
|
import { readFile as readFile6, stat as stat5 } from "node:fs/promises";
|
|
38701
38600
|
import { fileURLToPath as fileURLToPath4 } from "node:url";
|
|
38702
38601
|
function formatDuration(ms) {
|
|
@@ -38728,11 +38627,11 @@ function resolveMaxRuns(value) {
|
|
|
38728
38627
|
return parsed;
|
|
38729
38628
|
}
|
|
38730
38629
|
function resolvePipelinePaths(scope, cwd, homeDir) {
|
|
38731
|
-
const rootPath = scope === "global" ?
|
|
38630
|
+
const rootPath = scope === "global" ? path23.join(homeDir, ".poe-code", "pipeline") : path23.join(cwd, ".poe-code", "pipeline");
|
|
38732
38631
|
const displayRoot = scope === "global" ? "~/.poe-code/pipeline" : ".poe-code/pipeline";
|
|
38733
38632
|
return {
|
|
38734
|
-
plansPath:
|
|
38735
|
-
stepsPath:
|
|
38633
|
+
plansPath: path23.join(rootPath, "plans"),
|
|
38634
|
+
stepsPath: path23.join(rootPath, "steps.yaml"),
|
|
38736
38635
|
displayPlansPath: `${displayRoot}/plans`,
|
|
38737
38636
|
displayStepsPath: `${displayRoot}/steps.yaml`
|
|
38738
38637
|
};
|
|
@@ -38743,16 +38642,16 @@ async function loadPipelineTemplates() {
|
|
|
38743
38642
|
}
|
|
38744
38643
|
const packageRoot = await findPackageRoot(fileURLToPath4(import.meta.url));
|
|
38745
38644
|
const templateRoots = [
|
|
38746
|
-
|
|
38747
|
-
|
|
38645
|
+
path23.join(packageRoot, "src", "templates", "pipeline"),
|
|
38646
|
+
path23.join(packageRoot, "dist", "templates", "pipeline")
|
|
38748
38647
|
];
|
|
38749
38648
|
for (const templateRoot of templateRoots) {
|
|
38750
38649
|
if (!await pathExistsOnDisk(templateRoot)) {
|
|
38751
38650
|
continue;
|
|
38752
38651
|
}
|
|
38753
38652
|
const [skillPlan, steps] = await Promise.all([
|
|
38754
|
-
readFile6(
|
|
38755
|
-
readFile6(
|
|
38653
|
+
readFile6(path23.join(templateRoot, "SKILL_plan.md"), "utf8"),
|
|
38654
|
+
readFile6(path23.join(templateRoot, "steps.yaml.hbs"), "utf8")
|
|
38756
38655
|
]);
|
|
38757
38656
|
pipelineTemplatesCache = { skillPlan, steps };
|
|
38758
38657
|
return pipelineTemplatesCache;
|
|
@@ -38771,12 +38670,12 @@ async function pathExistsOnDisk(targetPath) {
|
|
|
38771
38670
|
}
|
|
38772
38671
|
}
|
|
38773
38672
|
async function findPackageRoot(entryFilePath) {
|
|
38774
|
-
let currentPath =
|
|
38673
|
+
let currentPath = path23.dirname(entryFilePath);
|
|
38775
38674
|
while (true) {
|
|
38776
|
-
if (await pathExistsOnDisk(
|
|
38675
|
+
if (await pathExistsOnDisk(path23.join(currentPath, "package.json"))) {
|
|
38777
38676
|
return currentPath;
|
|
38778
38677
|
}
|
|
38779
|
-
const parentPath =
|
|
38678
|
+
const parentPath = path23.dirname(currentPath);
|
|
38780
38679
|
if (parentPath === currentPath) {
|
|
38781
38680
|
throw new Error("Unable to locate package root for Pipeline templates.");
|
|
38782
38681
|
}
|
|
@@ -39054,7 +38953,7 @@ function registerPipelineCommand(program, container) {
|
|
|
39054
38953
|
`Would ${stepsExists ? "overwrite" : "create"}: ${pipelinePaths.displayStepsPath}`
|
|
39055
38954
|
);
|
|
39056
38955
|
} else {
|
|
39057
|
-
await container.fs.mkdir(
|
|
38956
|
+
await container.fs.mkdir(path23.dirname(pipelinePaths.stepsPath), {
|
|
39058
38957
|
recursive: true
|
|
39059
38958
|
});
|
|
39060
38959
|
await container.fs.writeFile(pipelinePaths.stepsPath, templates.steps, {
|
|
@@ -39079,7 +38978,7 @@ var init_pipeline4 = __esm({
|
|
|
39079
38978
|
"use strict";
|
|
39080
38979
|
init_src4();
|
|
39081
38980
|
init_src3();
|
|
39082
|
-
|
|
38981
|
+
init_src13();
|
|
39083
38982
|
init_errors();
|
|
39084
38983
|
init_shared();
|
|
39085
38984
|
await init_pipeline2();
|
|
@@ -39096,7 +38995,7 @@ var init_package = __esm({
|
|
|
39096
38995
|
"package.json"() {
|
|
39097
38996
|
package_default = {
|
|
39098
38997
|
name: "poe-code",
|
|
39099
|
-
version: "3.0.
|
|
38998
|
+
version: "3.0.100",
|
|
39100
38999
|
description: "CLI tool to configure Poe API for developer workflows.",
|
|
39101
39000
|
type: "module",
|
|
39102
39001
|
main: "./dist/index.js",
|
|
@@ -39180,7 +39079,8 @@ var init_package = __esm({
|
|
|
39180
39079
|
devDependencies: {
|
|
39181
39080
|
"@eslint/js": "^9.0.0",
|
|
39182
39081
|
"@modelcontextprotocol/sdk": "^1.26.0",
|
|
39183
|
-
"
|
|
39082
|
+
"auth-store": "*",
|
|
39083
|
+
"poe-oauth": "*",
|
|
39184
39084
|
"@poe-code/agent-spawn": "*",
|
|
39185
39085
|
"@poe-code/config-mutations": "*",
|
|
39186
39086
|
"@poe-code/design-system": "*",
|
|
@@ -39518,8 +39418,8 @@ var init_program = __esm({
|
|
|
39518
39418
|
await init_spawn4();
|
|
39519
39419
|
await init_research2();
|
|
39520
39420
|
init_wrap();
|
|
39521
|
-
|
|
39522
|
-
|
|
39421
|
+
init_login();
|
|
39422
|
+
init_logout();
|
|
39523
39423
|
init_auth();
|
|
39524
39424
|
init_install();
|
|
39525
39425
|
init_unconfigure();
|
|
@@ -39622,16 +39522,16 @@ __export(bootstrap_exports, {
|
|
|
39622
39522
|
createCliMain: () => createCliMain,
|
|
39623
39523
|
isCliInvocation: () => isCliInvocation
|
|
39624
39524
|
});
|
|
39625
|
-
import * as
|
|
39525
|
+
import * as nodeFs from "node:fs/promises";
|
|
39626
39526
|
import * as nodeFsSync3 from "node:fs";
|
|
39627
39527
|
import { realpathSync } from "node:fs";
|
|
39628
|
-
import { homedir as
|
|
39528
|
+
import { homedir as homedir5 } from "node:os";
|
|
39629
39529
|
import { pathToFileURL as pathToFileURL2 } from "node:url";
|
|
39630
39530
|
import { join as join2 } from "node:path";
|
|
39631
39531
|
import chalk13 from "chalk";
|
|
39632
39532
|
function createCliMain(programFactory) {
|
|
39633
39533
|
return async function runCli() {
|
|
39634
|
-
const homeDir =
|
|
39534
|
+
const homeDir = homedir5();
|
|
39635
39535
|
const logDir = join2(homeDir, ".poe-code", "logs");
|
|
39636
39536
|
const promptRunner = createPromptRunner();
|
|
39637
39537
|
const shouldLogToStderr = process.env.POE_CODE_STDERR_LOGS === "1" || process.env.POE_CODE_STDERR_LOGS === "true";
|
|
@@ -39697,7 +39597,7 @@ var init_bootstrap = __esm({
|
|
|
39697
39597
|
init_error_logger();
|
|
39698
39598
|
init_errors();
|
|
39699
39599
|
init_prompt_runner();
|
|
39700
|
-
fsAdapter =
|
|
39600
|
+
fsAdapter = nodeFs;
|
|
39701
39601
|
}
|
|
39702
39602
|
});
|
|
39703
39603
|
|
|
@@ -39812,7 +39712,7 @@ init_src5();
|
|
|
39812
39712
|
init_src4();
|
|
39813
39713
|
init_constants();
|
|
39814
39714
|
init_errors();
|
|
39815
|
-
import
|
|
39715
|
+
import path16 from "node:path";
|
|
39816
39716
|
import { Command } from "commander";
|
|
39817
39717
|
function parseMcpSpawnConfig(input) {
|
|
39818
39718
|
if (!input) {
|
|
@@ -39883,10 +39783,10 @@ function resolveWorkingDirectory(baseDir, candidate) {
|
|
|
39883
39783
|
if (!candidate || candidate.trim().length === 0) {
|
|
39884
39784
|
return void 0;
|
|
39885
39785
|
}
|
|
39886
|
-
if (
|
|
39786
|
+
if (path16.isAbsolute(candidate)) {
|
|
39887
39787
|
return candidate;
|
|
39888
39788
|
}
|
|
39889
|
-
return
|
|
39789
|
+
return path16.resolve(baseDir, candidate);
|
|
39890
39790
|
}
|
|
39891
39791
|
function createPoeAgentProgram() {
|
|
39892
39792
|
const program = new Command();
|