claude-use 11.18.0 → 11.19.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/cli.cjs +200 -106
- package/dist/index.cjs +164 -70
- package/dist/index.mjs +164 -70
- package/package.json +1 -1
package/dist/index.cjs
CHANGED
|
@@ -583,25 +583,102 @@ var init_schema = __esm({
|
|
|
583
583
|
}
|
|
584
584
|
});
|
|
585
585
|
|
|
586
|
+
// src/config/unrecognisedKeys.ts
|
|
587
|
+
function isRecord(value) {
|
|
588
|
+
return typeof value === "object" && value !== null;
|
|
589
|
+
}
|
|
590
|
+
function parseIgnoringUnrecognisedKeys(schema, raw) {
|
|
591
|
+
const first = schema.safeParse(raw);
|
|
592
|
+
if (first.success) {
|
|
593
|
+
return { success: true, data: first.data, ignored: [] };
|
|
594
|
+
}
|
|
595
|
+
const unrecognised = first.error.issues.filter((issue) => issue.code === "unrecognized_keys");
|
|
596
|
+
const others = first.error.issues.filter((issue) => issue.code !== "unrecognized_keys");
|
|
597
|
+
if (others.length > 0) {
|
|
598
|
+
return { success: false, issues: others };
|
|
599
|
+
}
|
|
600
|
+
const stripped = structuredClone(raw);
|
|
601
|
+
const ignored = [];
|
|
602
|
+
for (const issue of unrecognised) {
|
|
603
|
+
let holder = stripped;
|
|
604
|
+
for (const step of issue.path) {
|
|
605
|
+
holder = isRecord(holder) ? holder[step] : void 0;
|
|
606
|
+
}
|
|
607
|
+
if (isRecord(holder)) {
|
|
608
|
+
const values = Object.fromEntries(issue.keys.map((key) => [key, holder[key]]));
|
|
609
|
+
for (const key of issue.keys) {
|
|
610
|
+
Reflect.deleteProperty(holder, key);
|
|
611
|
+
}
|
|
612
|
+
ignored.push({ path: issue.path, keys: issue.keys, values });
|
|
613
|
+
}
|
|
614
|
+
}
|
|
615
|
+
const second = schema.safeParse(stripped);
|
|
616
|
+
return second.success ? { success: true, data: second.data, ignored } : { success: false, issues: second.error.issues };
|
|
617
|
+
}
|
|
618
|
+
function describeIgnoredKeys(filePath, ignored) {
|
|
619
|
+
const places = ignored.map(({ path: path41, keys }) => `${path41.length === 0 ? "" : `${path41.map(String).join(".")}.`}${keys.join(", ")}`);
|
|
620
|
+
return `${filePath} has settings this version of agent-shim does not know and ignores: ${places.join("; ")}. A newer release may read them.`;
|
|
621
|
+
}
|
|
622
|
+
function noteIgnoredKeys(filePath, ignored) {
|
|
623
|
+
if (ignored.length === 0) {
|
|
624
|
+
ignoredByFile.delete(filePath);
|
|
625
|
+
return;
|
|
626
|
+
}
|
|
627
|
+
ignoredByFile.set(filePath, ignored);
|
|
628
|
+
const message = `agent-shim: warning: ${describeIgnoredKeys(filePath, ignored)}
|
|
629
|
+
`;
|
|
630
|
+
if (!warned.has(message)) {
|
|
631
|
+
warned.add(message);
|
|
632
|
+
process.stderr.write(message);
|
|
633
|
+
}
|
|
634
|
+
}
|
|
635
|
+
function restoreIgnoredKeys(filePath, value) {
|
|
636
|
+
const ignored = ignoredByFile.get(filePath);
|
|
637
|
+
if (ignored === void 0) {
|
|
638
|
+
return value;
|
|
639
|
+
}
|
|
640
|
+
const restored = structuredClone(value);
|
|
641
|
+
for (const { path: path41, values } of ignored) {
|
|
642
|
+
let holder = restored;
|
|
643
|
+
for (const step of path41) {
|
|
644
|
+
holder = isRecord(holder) ? holder[step] : void 0;
|
|
645
|
+
}
|
|
646
|
+
if (isRecord(holder)) {
|
|
647
|
+
for (const [key, held] of Object.entries(values)) {
|
|
648
|
+
holder[key] = held;
|
|
649
|
+
}
|
|
650
|
+
}
|
|
651
|
+
}
|
|
652
|
+
return restored;
|
|
653
|
+
}
|
|
654
|
+
var warned, ignoredByFile;
|
|
655
|
+
var init_unrecognisedKeys = __esm({
|
|
656
|
+
"src/config/unrecognisedKeys.ts"() {
|
|
657
|
+
"use strict";
|
|
658
|
+
warned = /* @__PURE__ */ new Set();
|
|
659
|
+
ignoredByFile = /* @__PURE__ */ new Map();
|
|
660
|
+
}
|
|
661
|
+
});
|
|
662
|
+
|
|
586
663
|
// src/config/load.ts
|
|
587
664
|
function createExplorer(moduleName = "agent-shim") {
|
|
588
665
|
return (0, import_cosmiconfig.cosmiconfigSync)(moduleName, { searchPlaces: [] });
|
|
589
666
|
}
|
|
590
|
-
function
|
|
667
|
+
function isRecord2(value) {
|
|
591
668
|
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
592
669
|
}
|
|
593
670
|
function captureEntryOrder(value) {
|
|
594
|
-
if (!
|
|
671
|
+
if (!isRecord2(value)) {
|
|
595
672
|
return [];
|
|
596
673
|
}
|
|
597
674
|
const entries = value.entries;
|
|
598
|
-
if (!
|
|
675
|
+
if (!isRecord2(entries)) {
|
|
599
676
|
return [];
|
|
600
677
|
}
|
|
601
678
|
return Object.keys(entries);
|
|
602
679
|
}
|
|
603
680
|
function captureRuleEntryOrders(value) {
|
|
604
|
-
if (!
|
|
681
|
+
if (!isRecord2(value)) {
|
|
605
682
|
return [];
|
|
606
683
|
}
|
|
607
684
|
const rules = value.rules;
|
|
@@ -616,7 +693,7 @@ function cosmiconfigReader(explorer = createExplorer()) {
|
|
|
616
693
|
try {
|
|
617
694
|
result = explorer.load(filepath);
|
|
618
695
|
} catch (error) {
|
|
619
|
-
const code =
|
|
696
|
+
const code = isRecord2(error) ? error.code : void 0;
|
|
620
697
|
if (code === "ENOENT") {
|
|
621
698
|
return void 0;
|
|
622
699
|
}
|
|
@@ -633,10 +710,11 @@ function loadConfigFile(filepath, schema, read = cosmiconfigReader()) {
|
|
|
633
710
|
if (raw === void 0) {
|
|
634
711
|
return void 0;
|
|
635
712
|
}
|
|
636
|
-
const parsed = schema
|
|
713
|
+
const parsed = parseIgnoringUnrecognisedKeys(schema, raw);
|
|
637
714
|
if (!parsed.success) {
|
|
638
|
-
throw new ConfigValidationError(filepath, parsed.
|
|
715
|
+
throw new ConfigValidationError(filepath, parsed.issues);
|
|
639
716
|
}
|
|
717
|
+
noteIgnoredKeys(filepath, parsed.ignored);
|
|
640
718
|
return {
|
|
641
719
|
filepath,
|
|
642
720
|
config: parsed.data,
|
|
@@ -650,6 +728,7 @@ var init_load = __esm({
|
|
|
650
728
|
"use strict";
|
|
651
729
|
import_cosmiconfig = require("cosmiconfig");
|
|
652
730
|
init_cliError();
|
|
731
|
+
init_unrecognisedKeys();
|
|
653
732
|
ConfigValidationError = class extends CliError {
|
|
654
733
|
constructor(filepath, issues) {
|
|
655
734
|
const detail = issues.map((issue) => ` ${issue.path.join(".") || "(root)"}: ${issue.message}`).join("\n");
|
|
@@ -675,10 +754,11 @@ function readJson(filePath, schema, storeFs = nodeStoreFs) {
|
|
|
675
754
|
return void 0;
|
|
676
755
|
}
|
|
677
756
|
const parsed = JSON.parse(raw);
|
|
678
|
-
const result = schema
|
|
757
|
+
const result = parseIgnoringUnrecognisedKeys(schema, parsed);
|
|
679
758
|
if (!result.success) {
|
|
680
|
-
throw new ConfigValidationError(filePath, result.
|
|
759
|
+
throw new ConfigValidationError(filePath, result.issues);
|
|
681
760
|
}
|
|
761
|
+
noteIgnoredKeys(filePath, result.ignored);
|
|
682
762
|
return result.data;
|
|
683
763
|
}
|
|
684
764
|
function writeTextAtomic(filePath, contents, storeFs = nodeStoreFs) {
|
|
@@ -694,7 +774,7 @@ function writeTextAtomic(filePath, contents, storeFs = nodeStoreFs) {
|
|
|
694
774
|
}
|
|
695
775
|
}
|
|
696
776
|
function writeJsonAtomic(filePath, data, storeFs = nodeStoreFs) {
|
|
697
|
-
writeTextAtomic(filePath, `${JSON.stringify(data, null, 2)}
|
|
777
|
+
writeTextAtomic(filePath, `${JSON.stringify(restoreIgnoredKeys(filePath, data), null, 2)}
|
|
698
778
|
`, storeFs);
|
|
699
779
|
}
|
|
700
780
|
function applyPatch(filePath, schema, patch, options = {}) {
|
|
@@ -720,6 +800,7 @@ var init_store = __esm({
|
|
|
720
800
|
import_node_path3 = __toESM(require("node:path"), 1);
|
|
721
801
|
import_node_crypto = require("node:crypto");
|
|
722
802
|
init_load();
|
|
803
|
+
init_unrecognisedKeys();
|
|
723
804
|
nodeStoreFs = {
|
|
724
805
|
readFileUtf8(filePath) {
|
|
725
806
|
try {
|
|
@@ -2839,7 +2920,7 @@ var init_package = __esm({
|
|
|
2839
2920
|
"package.json"() {
|
|
2840
2921
|
package_default = {
|
|
2841
2922
|
name: "claude-use",
|
|
2842
|
-
version: "11.
|
|
2923
|
+
version: "11.19.0",
|
|
2843
2924
|
description: "A profile manager and launcher for Claude Code that lets one person run multiple logins from one machine while controlling what gets shared between them.",
|
|
2844
2925
|
license: "MIT",
|
|
2845
2926
|
author: "Joseph Mearman <joseph@mearman.co.uk>",
|
|
@@ -6203,7 +6284,7 @@ function formatCredentialSummary(summary) {
|
|
|
6203
6284
|
function describeCredential(credential) {
|
|
6204
6285
|
return formatCredentialSummary(summariseCredential(credential));
|
|
6205
6286
|
}
|
|
6206
|
-
function
|
|
6287
|
+
function isRecord6(value) {
|
|
6207
6288
|
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
6208
6289
|
}
|
|
6209
6290
|
function unpackKeyringToken(raw) {
|
|
@@ -6215,7 +6296,7 @@ function unpackKeyringToken(raw) {
|
|
|
6215
6296
|
const base64Str = trimmed.slice(GO_KEYRING_BASE64_PREFIX.length);
|
|
6216
6297
|
const decoded = Buffer.from(base64Str, "base64").toString("utf8");
|
|
6217
6298
|
const parsed = JSON.parse(decoded);
|
|
6218
|
-
if (
|
|
6299
|
+
if (isRecord6(parsed) && isRecord6(parsed.token)) {
|
|
6219
6300
|
const accessToken = parsed.token.access_token;
|
|
6220
6301
|
if (typeof accessToken === "string" && accessToken.trim() !== "") {
|
|
6221
6302
|
return accessToken.trim();
|
|
@@ -6329,14 +6410,14 @@ function providerJsonPath(paths, name) {
|
|
|
6329
6410
|
function providerExists(paths, name) {
|
|
6330
6411
|
return import_node_fs6.default.existsSync(providerJsonPath(paths, name));
|
|
6331
6412
|
}
|
|
6332
|
-
function
|
|
6413
|
+
function isRecord7(value) {
|
|
6333
6414
|
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
6334
6415
|
}
|
|
6335
6416
|
function legacyProviderConversion(raw) {
|
|
6336
|
-
if (!
|
|
6417
|
+
if (!isRecord7(raw) || "credential" in raw) {
|
|
6337
6418
|
return void 0;
|
|
6338
6419
|
}
|
|
6339
|
-
const env =
|
|
6420
|
+
const env = isRecord7(raw.env) ? raw.env : void 0;
|
|
6340
6421
|
const legacyEnvKeys = env === void 0 ? [] : Object.keys(env).filter((key) => LEGACY_ENV_CREDENTIAL_KEYS.includes(key));
|
|
6341
6422
|
const fields = [...LEGACY_PROVIDER_FIELDS.filter((field) => field in raw), ...legacyEnvKeys.map((key) => `env.${key}`)];
|
|
6342
6423
|
if (fields.length === 0) {
|
|
@@ -6369,10 +6450,11 @@ function parseProviderFile(filePath, raw) {
|
|
|
6369
6450
|
if (conversion !== void 0) {
|
|
6370
6451
|
throw new LegacyProviderFileError(filePath, conversion);
|
|
6371
6452
|
}
|
|
6372
|
-
const parsed = ProviderSchema
|
|
6453
|
+
const parsed = parseIgnoringUnrecognisedKeys(ProviderSchema, raw);
|
|
6373
6454
|
if (!parsed.success) {
|
|
6374
|
-
throw new ConfigValidationError(filePath, parsed.
|
|
6455
|
+
throw new ConfigValidationError(filePath, parsed.issues);
|
|
6375
6456
|
}
|
|
6457
|
+
noteIgnoredKeys(filePath, parsed.ignored);
|
|
6376
6458
|
return parsed.data;
|
|
6377
6459
|
}
|
|
6378
6460
|
function readProvider(paths, name) {
|
|
@@ -6582,6 +6664,7 @@ var init_providersStore = __esm({
|
|
|
6582
6664
|
import_node_path25 = __toESM(require("node:path"), 1);
|
|
6583
6665
|
init_load();
|
|
6584
6666
|
init_store();
|
|
6667
|
+
init_unrecognisedKeys();
|
|
6585
6668
|
init_schema();
|
|
6586
6669
|
init_cliError();
|
|
6587
6670
|
init_credential();
|
|
@@ -7564,7 +7647,7 @@ function resolvePoolLaunch(params) {
|
|
|
7564
7647
|
if (stickyRead.problem !== void 0) {
|
|
7565
7648
|
log.warn(`agent-shim: ${stickyRead.problem}; ignoring the last-pick record`);
|
|
7566
7649
|
}
|
|
7567
|
-
const
|
|
7650
|
+
const warned2 = /* @__PURE__ */ new Set();
|
|
7568
7651
|
for (; ; ) {
|
|
7569
7652
|
const nowMs = params.now();
|
|
7570
7653
|
let graph;
|
|
@@ -7588,8 +7671,8 @@ function resolvePoolLaunch(params) {
|
|
|
7588
7671
|
}
|
|
7589
7672
|
for (const gone of graph.missing) {
|
|
7590
7673
|
const key = `${gone.pool}:${gone.identity}`;
|
|
7591
|
-
if (!
|
|
7592
|
-
|
|
7674
|
+
if (!warned2.has(key)) {
|
|
7675
|
+
warned2.add(key);
|
|
7593
7676
|
log.warn(`agent-shim: pool "${gone.pool}" names identity "${gone.identity}", which does not exist; skipping it`);
|
|
7594
7677
|
}
|
|
7595
7678
|
}
|
|
@@ -10304,7 +10387,7 @@ var LiveTaskSchema = import_zod5.z.strictObject({
|
|
|
10304
10387
|
observedAt: import_zod5.z.number()
|
|
10305
10388
|
});
|
|
10306
10389
|
var SYSTEM_SUBTYPES = ["task_started", "task_progress", "task_updated", "task_notification", "background_tasks_changed"];
|
|
10307
|
-
function
|
|
10390
|
+
function isRecord3(value) {
|
|
10308
10391
|
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
10309
10392
|
}
|
|
10310
10393
|
function stringField(record, field) {
|
|
@@ -10321,7 +10404,7 @@ function booleanField(record, field) {
|
|
|
10321
10404
|
}
|
|
10322
10405
|
function usageOf(record) {
|
|
10323
10406
|
const raw = record.usage;
|
|
10324
|
-
if (!
|
|
10407
|
+
if (!isRecord3(raw)) {
|
|
10325
10408
|
return void 0;
|
|
10326
10409
|
}
|
|
10327
10410
|
const totalTokens = numberField(raw, "total_tokens");
|
|
@@ -10353,7 +10436,7 @@ function bounded(book) {
|
|
|
10353
10436
|
return book;
|
|
10354
10437
|
}
|
|
10355
10438
|
function applyAgentTaskEvent(book, sessionId, payload, observedAt2) {
|
|
10356
|
-
if (!
|
|
10439
|
+
if (!isRecord3(payload) || payload.type !== "system") {
|
|
10357
10440
|
return book;
|
|
10358
10441
|
}
|
|
10359
10442
|
const subtype = payload.subtype;
|
|
@@ -10369,8 +10452,8 @@ function applyAgentTaskEvent(book, sessionId, payload, observedAt2) {
|
|
|
10369
10452
|
if (subtype === "background_tasks_changed") {
|
|
10370
10453
|
const tasks = Array.isArray(payload.tasks) ? payload.tasks : [];
|
|
10371
10454
|
for (const raw of tasks) {
|
|
10372
|
-
const taskId2 =
|
|
10373
|
-
if (
|
|
10455
|
+
const taskId2 = isRecord3(raw) ? stringField(raw, "task_id") : void 0;
|
|
10456
|
+
if (isRecord3(raw) && taskId2 !== void 0) {
|
|
10374
10457
|
upsert(taskId2, { runId: stringField(raw, "run_id"), taskType: stringField(raw, "task_type"), description: stringField(raw, "description") });
|
|
10375
10458
|
}
|
|
10376
10459
|
}
|
|
@@ -10393,7 +10476,7 @@ function applyAgentTaskEvent(book, sessionId, payload, observedAt2) {
|
|
|
10393
10476
|
} else if (subtype === "task_progress") {
|
|
10394
10477
|
upsert(taskId, { ...common, subagentType: stringField(payload, "subagent_type"), lastToolName: stringField(payload, "last_tool_name"), usage: usageOf(payload) });
|
|
10395
10478
|
} else if (subtype === "task_updated") {
|
|
10396
|
-
const patch =
|
|
10479
|
+
const patch = isRecord3(payload.patch) ? payload.patch : {};
|
|
10397
10480
|
upsert(taskId, { runId: stringField(payload, "run_id"), status: stringField(patch, "status") });
|
|
10398
10481
|
} else {
|
|
10399
10482
|
upsert(taskId, { ...common, status: stringField(payload, "status"), outputFile: stringField(payload, "output_file"), summary: stringField(payload, "summary"), usage: usageOf(payload) });
|
|
@@ -10475,7 +10558,7 @@ function sessionCreateId(body) {
|
|
|
10475
10558
|
const id = session.id;
|
|
10476
10559
|
return typeof id === "string" && id.startsWith(RC_SESSION_ID_PREFIX) ? id : void 0;
|
|
10477
10560
|
}
|
|
10478
|
-
function
|
|
10561
|
+
function isRecord4(value) {
|
|
10479
10562
|
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
10480
10563
|
}
|
|
10481
10564
|
function parseJsonObject(body) {
|
|
@@ -10485,7 +10568,7 @@ function parseJsonObject(body) {
|
|
|
10485
10568
|
} catch {
|
|
10486
10569
|
return void 0;
|
|
10487
10570
|
}
|
|
10488
|
-
return
|
|
10571
|
+
return isRecord4(parsed) ? parsed : void 0;
|
|
10489
10572
|
}
|
|
10490
10573
|
function nonEmptyString(record, field) {
|
|
10491
10574
|
const value = record === void 0 ? void 0 : record[field];
|
|
@@ -10506,11 +10589,11 @@ function payloadEventsOf(body) {
|
|
|
10506
10589
|
}
|
|
10507
10590
|
const payloads = [];
|
|
10508
10591
|
for (const event of events) {
|
|
10509
|
-
if (!
|
|
10592
|
+
if (!isRecord4(event)) {
|
|
10510
10593
|
continue;
|
|
10511
10594
|
}
|
|
10512
10595
|
const payload = event.payload;
|
|
10513
|
-
if (!
|
|
10596
|
+
if (!isRecord4(payload)) {
|
|
10514
10597
|
continue;
|
|
10515
10598
|
}
|
|
10516
10599
|
payloads.push(payload);
|
|
@@ -10525,7 +10608,7 @@ function pendingOfControlRequestPayload(payload) {
|
|
|
10525
10608
|
if (requestId === void 0) {
|
|
10526
10609
|
return void 0;
|
|
10527
10610
|
}
|
|
10528
|
-
const request4 =
|
|
10611
|
+
const request4 = isRecord4(payload.request) ? payload.request : void 0;
|
|
10529
10612
|
const subtype = nonEmptyString(request4, "subtype");
|
|
10530
10613
|
const type = subtype ?? "control_request";
|
|
10531
10614
|
let summary = "";
|
|
@@ -10542,7 +10625,7 @@ function answeredRequestIdsOfControlResponsePayload(payload) {
|
|
|
10542
10625
|
if (payload.type !== "control_response") {
|
|
10543
10626
|
return [];
|
|
10544
10627
|
}
|
|
10545
|
-
const response =
|
|
10628
|
+
const response = isRecord4(payload.response) ? payload.response : void 0;
|
|
10546
10629
|
const id = nonEmptyString(response, "request_id") ?? nonEmptyString(payload, "request_id") ?? nonEmptyString(payload, "uuid");
|
|
10547
10630
|
return id === void 0 ? [] : [id];
|
|
10548
10631
|
}
|
|
@@ -10771,7 +10854,7 @@ function createRcSessionTracker(deps) {
|
|
|
10771
10854
|
return;
|
|
10772
10855
|
}
|
|
10773
10856
|
entry.sequenceNum = entry.sequenceNum === void 0 || event.sequence_num > entry.sequenceNum ? event.sequence_num : entry.sequenceNum;
|
|
10774
|
-
if (!
|
|
10857
|
+
if (!isRecord4(event.payload)) {
|
|
10775
10858
|
return;
|
|
10776
10859
|
}
|
|
10777
10860
|
entry.liveTasks = applyAgentTaskEvent(entry.liveTasks, sessionId, event.payload, deps.now());
|
|
@@ -12194,11 +12277,11 @@ var import_node_path10 = __toESM(require("node:path"), 1);
|
|
|
12194
12277
|
function isSafeSessionId(sessionId) {
|
|
12195
12278
|
return /^[A-Za-z0-9_-]+$/.test(sessionId);
|
|
12196
12279
|
}
|
|
12197
|
-
function
|
|
12280
|
+
function isRecord5(value) {
|
|
12198
12281
|
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
12199
12282
|
}
|
|
12200
12283
|
function credentialOfJson(parsed) {
|
|
12201
|
-
if (!
|
|
12284
|
+
if (!isRecord5(parsed)) {
|
|
12202
12285
|
return void 0;
|
|
12203
12286
|
}
|
|
12204
12287
|
const { authorization, anthropicVersion, anthropicClientPlatform } = parsed;
|
|
@@ -12228,7 +12311,7 @@ function createRcCredentialStore(fs13, dir) {
|
|
|
12228
12311
|
} catch {
|
|
12229
12312
|
return void 0;
|
|
12230
12313
|
}
|
|
12231
|
-
return
|
|
12314
|
+
return isRecord5(parsed) ? parsed : void 0;
|
|
12232
12315
|
};
|
|
12233
12316
|
return {
|
|
12234
12317
|
read: (sessionId) => {
|
|
@@ -14165,6 +14248,7 @@ function parseSiwcFile(raw, filePath) {
|
|
|
14165
14248
|
|
|
14166
14249
|
// src/doctorReport.ts
|
|
14167
14250
|
init_load();
|
|
14251
|
+
init_unrecognisedKeys();
|
|
14168
14252
|
init_schema();
|
|
14169
14253
|
init_credential();
|
|
14170
14254
|
init_credentialCache();
|
|
@@ -14375,11 +14459,11 @@ function validateJson(schema, input) {
|
|
|
14375
14459
|
} catch (error) {
|
|
14376
14460
|
return { ok: false, message: `${input.path} is not valid JSON: ${error instanceof Error ? error.message : String(error)}` };
|
|
14377
14461
|
}
|
|
14378
|
-
const result = schema
|
|
14462
|
+
const result = parseIgnoringUnrecognisedKeys(schema, parsed);
|
|
14379
14463
|
if (!result.success) {
|
|
14380
|
-
return { ok: false, message: new ConfigValidationError(input.path, result.
|
|
14464
|
+
return { ok: false, message: new ConfigValidationError(input.path, result.issues).message };
|
|
14381
14465
|
}
|
|
14382
|
-
return { ok: true, data: result.data };
|
|
14466
|
+
return { ok: true, data: result.data, ...result.ignored.length === 0 ? {} : { warning: describeIgnoredKeys(input.path, result.ignored) } };
|
|
14383
14467
|
}
|
|
14384
14468
|
function tcpPortEraRecord(raw) {
|
|
14385
14469
|
let parsed;
|
|
@@ -14472,11 +14556,14 @@ function pushProvider(push, entry, cacheEnv, signIn) {
|
|
|
14472
14556
|
push("provider", "fail", new LegacyProviderFileError(entry.path, conversion).message, entry.name);
|
|
14473
14557
|
return;
|
|
14474
14558
|
}
|
|
14475
|
-
const validated3 = ProviderSchema
|
|
14559
|
+
const validated3 = parseIgnoringUnrecognisedKeys(ProviderSchema, parsed);
|
|
14476
14560
|
if (!validated3.success) {
|
|
14477
|
-
push("provider", "fail", new ConfigValidationError(entry.path, validated3.
|
|
14561
|
+
push("provider", "fail", new ConfigValidationError(entry.path, validated3.issues).message, entry.name);
|
|
14478
14562
|
return;
|
|
14479
14563
|
}
|
|
14564
|
+
if (validated3.ignored.length > 0) {
|
|
14565
|
+
push("provider", "warn", describeIgnoredKeys(entry.path, validated3.ignored), entry.name);
|
|
14566
|
+
}
|
|
14480
14567
|
const cache = cacheClause(cacheEnv, `provider ${entry.name}`, validated3.data.credential);
|
|
14481
14568
|
push("provider", cache.unreadable ? "fail" : "pass", `${entry.name} is valid (${describeProviderEndpoint(validated3.data)}, credential ${describeCredential(validated3.data.credential)})${cache.text}.`, entry.name);
|
|
14482
14569
|
if (validated3.data.env?.ENABLE_TOOL_SEARCH === void 0) {
|
|
@@ -14511,6 +14598,13 @@ function runDoctor(params) {
|
|
|
14511
14598
|
const push = (section, severity, message, subject) => {
|
|
14512
14599
|
findings.push({ section, severity, message, ...subject === void 0 ? {} : { subject } });
|
|
14513
14600
|
};
|
|
14601
|
+
const validate = (schema, input, section, subject) => {
|
|
14602
|
+
const validated3 = validateJson(schema, input);
|
|
14603
|
+
if (validated3.ok && validated3.warning !== void 0) {
|
|
14604
|
+
push(section, "warn", validated3.warning, subject);
|
|
14605
|
+
}
|
|
14606
|
+
return validated3;
|
|
14607
|
+
};
|
|
14514
14608
|
const checkPin = (section, subject, where, version) => {
|
|
14515
14609
|
const installed = params.installedClaudeVersions;
|
|
14516
14610
|
if (version === void 0 || installed === void 0 || installed.includes(version)) {
|
|
@@ -14550,7 +14644,7 @@ function runDoctor(params) {
|
|
|
14550
14644
|
pushLegacyName(push, params);
|
|
14551
14645
|
const profileSources = /* @__PURE__ */ new Map();
|
|
14552
14646
|
for (const entry of params.configProfiles) {
|
|
14553
|
-
const validated3 =
|
|
14647
|
+
const validated3 = validate(ConfigProfileSchema, entry, "config-profile", entry.name);
|
|
14554
14648
|
if (!validated3.ok) {
|
|
14555
14649
|
push("config-profile", "fail", validated3.message, entry.name);
|
|
14556
14650
|
continue;
|
|
@@ -14572,7 +14666,7 @@ function runDoctor(params) {
|
|
|
14572
14666
|
const validProfileNames = new Set(profileSources.keys());
|
|
14573
14667
|
const validIdentityNames = /* @__PURE__ */ new Set();
|
|
14574
14668
|
for (const entry of params.identities) {
|
|
14575
|
-
const validated3 =
|
|
14669
|
+
const validated3 = validate(IdentitySchema, entry, "identity", entry.name);
|
|
14576
14670
|
if (!validated3.ok) {
|
|
14577
14671
|
push("identity", "fail", validated3.message, entry.name);
|
|
14578
14672
|
continue;
|
|
@@ -14658,7 +14752,7 @@ function runDoctor(params) {
|
|
|
14658
14752
|
if (params.directoryRules.raw === void 0) {
|
|
14659
14753
|
push("directory-rules", "pass", "No directory-rules.json configured.");
|
|
14660
14754
|
} else {
|
|
14661
|
-
const validated3 =
|
|
14755
|
+
const validated3 = validate(DirectoryRulesSchema, params.directoryRules, "directory-rules");
|
|
14662
14756
|
if (!validated3.ok) {
|
|
14663
14757
|
push("directory-rules", "fail", validated3.message);
|
|
14664
14758
|
} else {
|
|
@@ -14683,7 +14777,7 @@ function runDoctor(params) {
|
|
|
14683
14777
|
if (params.globalConfig.raw === void 0) {
|
|
14684
14778
|
push("global-config", "pass", "No config.json configured.");
|
|
14685
14779
|
} else {
|
|
14686
|
-
const validated3 =
|
|
14780
|
+
const validated3 = validate(GlobalConfigSchema, params.globalConfig, "global-config");
|
|
14687
14781
|
if (!validated3.ok) {
|
|
14688
14782
|
push("global-config", "fail", validated3.message);
|
|
14689
14783
|
} else {
|
|
@@ -14703,7 +14797,7 @@ function runDoctor(params) {
|
|
|
14703
14797
|
if (params.categoriesLocal.raw === void 0) {
|
|
14704
14798
|
push("categories-local", "pass", "No categories.local.json configured.");
|
|
14705
14799
|
} else {
|
|
14706
|
-
const validated3 =
|
|
14800
|
+
const validated3 = validate(CategoryClassificationOverlaySchema, params.categoriesLocal, "categories-local");
|
|
14707
14801
|
push(
|
|
14708
14802
|
"categories-local",
|
|
14709
14803
|
validated3.ok ? "pass" : "fail",
|
|
@@ -16314,15 +16408,15 @@ function createQuotaExpiringPublisher(hub, deps) {
|
|
|
16314
16408
|
|
|
16315
16409
|
// src/frontdoor/rcLiveUsage.ts
|
|
16316
16410
|
var RC_RATE_LIMIT_EVENT_TYPE = "rate_limit_event";
|
|
16317
|
-
function
|
|
16411
|
+
function isRecord8(value) {
|
|
16318
16412
|
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
16319
16413
|
}
|
|
16320
16414
|
function rcRateLimitInfoOf(event) {
|
|
16321
16415
|
const payload = event.envelope.payload;
|
|
16322
|
-
if (!
|
|
16416
|
+
if (!isRecord8(payload) || payload.type !== RC_RATE_LIMIT_EVENT_TYPE) {
|
|
16323
16417
|
return void 0;
|
|
16324
16418
|
}
|
|
16325
|
-
if (!
|
|
16419
|
+
if (!isRecord8(payload.rate_limit_info)) {
|
|
16326
16420
|
return void 0;
|
|
16327
16421
|
}
|
|
16328
16422
|
const parsed = RcRateLimitInfoSchema.safeParse(payload.rate_limit_info);
|
|
@@ -16410,7 +16504,7 @@ function createSseParser() {
|
|
|
16410
16504
|
}
|
|
16411
16505
|
};
|
|
16412
16506
|
}
|
|
16413
|
-
function
|
|
16507
|
+
function isRecord9(value) {
|
|
16414
16508
|
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
16415
16509
|
}
|
|
16416
16510
|
function sequenceNumOf(value) {
|
|
@@ -16432,7 +16526,7 @@ function parseRcStreamEnvelope(parsed) {
|
|
|
16432
16526
|
} catch {
|
|
16433
16527
|
return void 0;
|
|
16434
16528
|
}
|
|
16435
|
-
if (!
|
|
16529
|
+
if (!isRecord9(data)) {
|
|
16436
16530
|
return void 0;
|
|
16437
16531
|
}
|
|
16438
16532
|
const eventType = data.event_type;
|
|
@@ -16673,7 +16767,7 @@ init_capability();
|
|
|
16673
16767
|
// src/frontdoor/rcSelfHostEndpoints.ts
|
|
16674
16768
|
var RC_SOURCE_WORKER = "worker";
|
|
16675
16769
|
var RC_SOURCE_CLIENT = "client";
|
|
16676
|
-
function
|
|
16770
|
+
function isRecord10(value) {
|
|
16677
16771
|
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
16678
16772
|
}
|
|
16679
16773
|
function parseJsonObject2(body) {
|
|
@@ -16683,7 +16777,7 @@ function parseJsonObject2(body) {
|
|
|
16683
16777
|
} catch {
|
|
16684
16778
|
return void 0;
|
|
16685
16779
|
}
|
|
16686
|
-
return
|
|
16780
|
+
return isRecord10(parsed) ? parsed : void 0;
|
|
16687
16781
|
}
|
|
16688
16782
|
function nonEmptyString2(record, field) {
|
|
16689
16783
|
const value = record === void 0 ? void 0 : record[field];
|
|
@@ -16757,7 +16851,7 @@ async function serveRcClientChannels(ctx, tail, method, maxBatchEvents) {
|
|
|
16757
16851
|
}
|
|
16758
16852
|
const results = [];
|
|
16759
16853
|
for (const event of events) {
|
|
16760
|
-
if (!
|
|
16854
|
+
if (!isRecord10(event) || !isRecord10(event.payload)) {
|
|
16761
16855
|
await ctx.answerJson(response, HTTP_STATUS.badRequest, { type: "error", error: { type: "invalid_request_error", message: "every event in a teleport write is an object carrying one payload object" } });
|
|
16762
16856
|
return true;
|
|
16763
16857
|
}
|
|
@@ -16857,7 +16951,7 @@ async function serveRcCompatSessions(ctx, pathname, compatPath) {
|
|
|
16857
16951
|
// src/frontdoor/rcSelfHostConversations.ts
|
|
16858
16952
|
var RC_CONVERSATIONS_PATH_PREFIX = "/v1/code/conversations";
|
|
16859
16953
|
var RC_CONVERSATION_ID_PREFIX = "conv_";
|
|
16860
|
-
function
|
|
16954
|
+
function isRecord11(value) {
|
|
16861
16955
|
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
16862
16956
|
}
|
|
16863
16957
|
function parseJsonObject3(body) {
|
|
@@ -16867,7 +16961,7 @@ function parseJsonObject3(body) {
|
|
|
16867
16961
|
} catch {
|
|
16868
16962
|
return void 0;
|
|
16869
16963
|
}
|
|
16870
|
-
return
|
|
16964
|
+
return isRecord11(parsed) ? parsed : void 0;
|
|
16871
16965
|
}
|
|
16872
16966
|
function nonEmptyString3(record, field) {
|
|
16873
16967
|
const value = record === void 0 ? void 0 : record[field];
|
|
@@ -16921,7 +17015,7 @@ async function serveRcConversations(ctx, pathname, method) {
|
|
|
16921
17015
|
}
|
|
16922
17016
|
const results = [];
|
|
16923
17017
|
for (const event of events) {
|
|
16924
|
-
if (!
|
|
17018
|
+
if (!isRecord11(event) || !isRecord11(event.payload)) {
|
|
16925
17019
|
await ctx.answerJson(response, HTTP_STATUS.badRequest, { type: "error", error: { type: "invalid_request_error", message: "every event in a write is an object carrying one payload object" } });
|
|
16926
17020
|
return;
|
|
16927
17021
|
}
|
|
@@ -16953,7 +17047,7 @@ var RC_SELF_HOST_SCOPE_LIST = ["user:profile", "user:inference", "user:sessions:
|
|
|
16953
17047
|
var RC_SELF_HOST_OAUTH_TOKEN_TTL_SECONDS = 3600;
|
|
16954
17048
|
var MS_PER_SECOND5 = 1e3;
|
|
16955
17049
|
var HTTP_SERVICE_UNAVAILABLE = 503;
|
|
16956
|
-
function
|
|
17050
|
+
function isRecord12(value) {
|
|
16957
17051
|
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
16958
17052
|
}
|
|
16959
17053
|
function parseJsonObject4(body) {
|
|
@@ -16963,7 +17057,7 @@ function parseJsonObject4(body) {
|
|
|
16963
17057
|
} catch {
|
|
16964
17058
|
return void 0;
|
|
16965
17059
|
}
|
|
16966
|
-
return
|
|
17060
|
+
return isRecord12(parsed) ? parsed : void 0;
|
|
16967
17061
|
}
|
|
16968
17062
|
function growthBookFeatures() {
|
|
16969
17063
|
return {
|
|
@@ -17317,7 +17411,7 @@ var RC_SELF_HOST_WORKER_EPOCH = 1;
|
|
|
17317
17411
|
var RC_STREAM_EVENT_NAME2 = "client_event";
|
|
17318
17412
|
var CONFLICT_REASON_HEADER2 = "x-ccr-conflict-reason";
|
|
17319
17413
|
var CONFLICT_REASON_EPOCH_STALE = "epoch_stale";
|
|
17320
|
-
function
|
|
17414
|
+
function isRecord13(value) {
|
|
17321
17415
|
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
17322
17416
|
}
|
|
17323
17417
|
function isWebSearchRefusal(value) {
|
|
@@ -17401,7 +17495,7 @@ function parseJsonObject5(body) {
|
|
|
17401
17495
|
} catch {
|
|
17402
17496
|
return void 0;
|
|
17403
17497
|
}
|
|
17404
|
-
return
|
|
17498
|
+
return isRecord13(parsed) ? parsed : void 0;
|
|
17405
17499
|
}
|
|
17406
17500
|
function mintWorkerJwt(randomToken, issuedAt) {
|
|
17407
17501
|
const encode = (value) => Buffer.from(JSON.stringify(value), "utf8").toString("base64url");
|
|
@@ -17661,7 +17755,7 @@ data: ${JSON.stringify(envelope)}
|
|
|
17661
17755
|
if (status !== void 0) {
|
|
17662
17756
|
session.workerStatus = status;
|
|
17663
17757
|
}
|
|
17664
|
-
if (
|
|
17758
|
+
if (isRecord13(body?.external_metadata)) {
|
|
17665
17759
|
session.externalMetadata = body.external_metadata;
|
|
17666
17760
|
}
|
|
17667
17761
|
await answerJson2(response, HTTP_STATUS.ok, {});
|
|
@@ -17691,7 +17785,7 @@ data: ${JSON.stringify(envelope)}
|
|
|
17691
17785
|
}
|
|
17692
17786
|
const results = [];
|
|
17693
17787
|
for (const event of events) {
|
|
17694
|
-
if (!
|
|
17788
|
+
if (!isRecord13(event) || !isRecord13(event.payload)) {
|
|
17695
17789
|
await answerJson2(response, HTTP_STATUS.badRequest, { type: "error", error: { type: "invalid_request_error", message: "every event in a batch is an object carrying one payload object" } });
|
|
17696
17790
|
return;
|
|
17697
17791
|
}
|
|
@@ -17724,7 +17818,7 @@ data: ${JSON.stringify(envelope)}
|
|
|
17724
17818
|
return;
|
|
17725
17819
|
}
|
|
17726
17820
|
for (const event of events) {
|
|
17727
|
-
if (
|
|
17821
|
+
if (isRecord13(event)) {
|
|
17728
17822
|
session.internalEvents.push({ eventId: deps.newUuid(), body: event });
|
|
17729
17823
|
}
|
|
17730
17824
|
}
|
|
@@ -17820,7 +17914,7 @@ data: ${JSON.stringify(envelope)}
|
|
|
17820
17914
|
}
|
|
17821
17915
|
const results = [];
|
|
17822
17916
|
for (const event of events) {
|
|
17823
|
-
if (!
|
|
17917
|
+
if (!isRecord13(event) || !isRecord13(event.payload)) {
|
|
17824
17918
|
await answerJson2(response, HTTP_STATUS.badRequest, { type: "error", error: { type: "invalid_request_error", message: "every event in a write is an object carrying one payload object" } });
|
|
17825
17919
|
return;
|
|
17826
17920
|
}
|
|
@@ -17957,7 +18051,7 @@ var RC_SELF_HOST_RECORD_DIR = "rc-selfhost";
|
|
|
17957
18051
|
var RC_SELF_HOST_RECORD_FILE = "credential.json";
|
|
17958
18052
|
var SELF_HOST_EMAIL = "selfhost@agent-shim.invalid";
|
|
17959
18053
|
var SELF_HOST_SUBSCRIPTION_TYPE = "max";
|
|
17960
|
-
function
|
|
18054
|
+
function isRecord14(value) {
|
|
17961
18055
|
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
17962
18056
|
}
|
|
17963
18057
|
function readJsonObject(fs13, file) {
|
|
@@ -17971,7 +18065,7 @@ function readJsonObject(fs13, file) {
|
|
|
17971
18065
|
} catch {
|
|
17972
18066
|
return void 0;
|
|
17973
18067
|
}
|
|
17974
|
-
return
|
|
18068
|
+
return isRecord14(parsed) ? parsed : void 0;
|
|
17975
18069
|
}
|
|
17976
18070
|
function readRcSelfHostRecord(fs13, frontdoorDir) {
|
|
17977
18071
|
const parsed = readJsonObject(fs13, import_node_path33.default.join(frontdoorDir, RC_SELF_HOST_RECORD_DIR, RC_SELF_HOST_RECORD_FILE));
|
|
@@ -17995,7 +18089,7 @@ function mintRcSelfHostCredential(deps) {
|
|
|
17995
18089
|
const recordFile = import_node_path33.default.join(recordDir, RC_SELF_HOST_RECORD_FILE);
|
|
17996
18090
|
const previousRecord = readRcSelfHostRecord(deps.fs, deps.frontdoorDir);
|
|
17997
18091
|
const existingCredentials = readJsonObject(deps.fs, credentialsFile);
|
|
17998
|
-
const existingOauth =
|
|
18092
|
+
const existingOauth = isRecord14(existingCredentials?.claudeAiOauth) ? existingCredentials.claudeAiOauth : void 0;
|
|
17999
18093
|
const existingToken = typeof existingOauth?.accessToken === "string" && existingOauth.accessToken !== "" ? existingOauth.accessToken : void 0;
|
|
18000
18094
|
const existingIsOwn = existingToken !== void 0 && previousRecord?.accessToken === existingToken;
|
|
18001
18095
|
if (existingToken !== void 0 && !existingIsOwn && !deps.force) {
|
|
@@ -18012,7 +18106,7 @@ function mintRcSelfHostCredential(deps) {
|
|
|
18012
18106
|
deps.fs.writeFilePrivate(credentialsFile, `${JSON.stringify({ ...existingCredentials, claudeAiOauth: { accessToken, refreshToken, expiresAt: null, scopes: [...RC_SELF_HOST_SCOPE_LIST], subscriptionType: SELF_HOST_SUBSCRIPTION_TYPE, rateLimitTier: null } }, null, 2)}
|
|
18013
18107
|
`);
|
|
18014
18108
|
const claudeJson = readJsonObject(deps.fs, claudeJsonFile) ?? {};
|
|
18015
|
-
const existingBlock = (value) =>
|
|
18109
|
+
const existingBlock = (value) => isRecord14(value) ? value : {};
|
|
18016
18110
|
deps.fs.writeFilePrivate(claudeJsonFile, `${JSON.stringify({
|
|
18017
18111
|
...claudeJson,
|
|
18018
18112
|
oauthAccount: {
|