@macintacos/caret 0.12.0 → 0.14.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/.claude-plugin/plugin.json +1 -1
- package/README.md +13 -0
- package/dist/cli.js +808 -225
- package/package.json +2 -1
- package/ui/dist/assets/{angular-html-DMUNxAT7.js → angular-html-C0XElF0f.js} +1 -1
- package/ui/dist/assets/{angular-ts-CjN6OxaN.js → angular-ts-BVnV1Yg5.js} +1 -1
- package/ui/dist/assets/{apl-Dw4C1Sv3.js → apl-BFyMAB9c.js} +1 -1
- package/ui/dist/assets/{astro-DzXQf-F7.js → astro-DAtaAFYq.js} +1 -1
- package/ui/dist/assets/{blade-CTMS_AXM.js → blade-BoZH76v_.js} +1 -1
- package/ui/dist/assets/{c-DBanwSNn.js → c-DyRawzd0.js} +1 -1
- package/ui/dist/assets/{chapel-BTstFNqm.js → chapel-CAaCMdek.js} +1 -1
- package/ui/dist/assets/{cobol-Ca4PWvOz.js → cobol-BjXiLsat.js} +1 -1
- package/ui/dist/assets/{coffee-a9u7Cq0q.js → coffee-DvjcTlIE.js} +1 -1
- package/ui/dist/assets/{cpp-oowRqiuJ.js → cpp-sRP7rZGr.js} +1 -1
- package/ui/dist/assets/{crystal-D7O4UX-i.js → crystal-CaRkbKnA.js} +1 -1
- package/ui/dist/assets/{css-CZVl8Px8.js → css-Igh3vvbt.js} +1 -1
- package/ui/dist/assets/{dist-CdQe3tPj.js → dist-5Bv2mYWj.js} +1 -1
- package/ui/dist/assets/{dist-DpTOg-NC.js → dist-B5Dwvt_o.js} +1 -1
- package/ui/dist/assets/{dist-BbiHto2W.js → dist-BdaKUV8X.js} +1 -1
- package/ui/dist/assets/{dist-IHT5kND0.js → dist-BkB3Dkvt.js} +1 -1
- package/ui/dist/assets/{dist-DigqW6HL.js → dist-CBxRdWpx.js} +1 -1
- package/ui/dist/assets/dist-CF48ImGm.js +1 -0
- package/ui/dist/assets/{dist-pedI8d1Q.js → dist-CF4FIhxu.js} +1 -1
- package/ui/dist/assets/dist-CGl7bSLs.js +1 -0
- package/ui/dist/assets/{dist-vKL_CWkV.js → dist-CYIXdHF6.js} +1 -1
- package/ui/dist/assets/dist-CZeI5UV9.js +1 -0
- package/ui/dist/assets/{dist-BAGkWecZ.js → dist-C_lXyw3s.js} +1 -1
- package/ui/dist/assets/dist-CiBs4R_k.js +12 -0
- package/ui/dist/assets/{dist-Bc8Y8K-M.js → dist-D4FUs8dC.js} +1 -1
- package/ui/dist/assets/{dist-DaoC_D4S.js → dist-DHAfbOzU.js} +1 -1
- package/ui/dist/assets/{dist-CikfqRw0.js → dist-D_g9f9rz.js} +1 -1
- package/ui/dist/assets/{dist-CaX-VV5u.js → dist-Dt1D8SWK.js} +1 -1
- package/ui/dist/assets/{dist-C3qTFPSx.js → dist-YE9up3VR.js} +1 -1
- package/ui/dist/assets/{dist-CWGZKcUs.js → dist-lE2sJQyW.js} +1 -1
- package/ui/dist/assets/{edge-I4NpgvYm.js → edge-CvHTOXgI.js} +1 -1
- package/ui/dist/assets/{elixir-BJknh2p7.js → elixir-CtokNUaA.js} +1 -1
- package/ui/dist/assets/{elm-CRrD_tPY.js → elm-B34p-CC5.js} +1 -1
- package/ui/dist/assets/{erb-CROtc598.js → erb-FjaGN5LV.js} +1 -1
- package/ui/dist/assets/{git-rebase-BRtkWL3M.js → git-rebase-BFUCuD7O.js} +1 -1
- package/ui/dist/assets/{glimmer-js-lqkYwHrU.js → glimmer-js-CRs6sgzF.js} +1 -1
- package/ui/dist/assets/{glimmer-ts-CB5BuR0n.js → glimmer-ts-Bkt0v-q2.js} +1 -1
- package/ui/dist/assets/{glsl-CBceQiUy.js → glsl-Ckh3d22M.js} +1 -1
- package/ui/dist/assets/{graphql-Qo62WpvI.js → graphql-IqxoIj3x.js} +1 -1
- package/ui/dist/assets/{hack-BNJdjzLU.js → hack-DG1p8zpS.js} +1 -1
- package/ui/dist/assets/{haml-BMBtqt90.js → haml-DA2jQcOV.js} +1 -1
- package/ui/dist/assets/{handlebars-CBP-BQZd.js → handlebars-CqT0epoo.js} +1 -1
- package/ui/dist/assets/{html-Df586Ko0.js → html-CoTd-Axz.js} +1 -1
- package/ui/dist/assets/{html-derivative-yN18G809.js → html-derivative-DDt5A1xL.js} +1 -1
- package/ui/dist/assets/{http-YpWiVC6m.js → http-TEp9u8BR.js} +1 -1
- package/ui/dist/assets/{hurl-BfSO2S_0.js → hurl-OLD-GtJJ.js} +1 -1
- package/ui/dist/assets/index-BucWCjoT.js +6767 -0
- package/ui/dist/assets/index-Djrj2rps.css +1 -0
- package/ui/dist/assets/{java-BqL-WKyb.js → java-DYZ_BnxQ.js} +1 -1
- package/ui/dist/assets/{javascript-C7z4qtlP.js → javascript-B4vvB79r.js} +1 -1
- package/ui/dist/assets/{jinja-Dt2LjYg4.js → jinja-BTulBbvB.js} +1 -1
- package/ui/dist/assets/{jison-RhcomYXF.js → jison-CDVJmcGj.js} +1 -1
- package/ui/dist/assets/{json-C7RFwAc6.js → json-DahQZwqh.js} +1 -1
- package/ui/dist/assets/{jsx-DzVoS5cK.js → jsx-Dzcw0XhS.js} +1 -1
- package/ui/dist/assets/{julia-C86cVJ4I.js → julia-BB_aSeOr.js} +1 -1
- package/ui/dist/assets/{just-DLVt7fko.js → just-C3IsNIar.js} +1 -1
- package/ui/dist/assets/{latex-DRxirEYd.js → latex-D7dYt9yW.js} +1 -1
- package/ui/dist/assets/{liquid-BR_Lw-Bt.js → liquid-CO9g2vFd.js} +1 -1
- package/ui/dist/assets/{lua-CHeMByWu.js → lua-D6OK3PTP.js} +1 -1
- package/ui/dist/assets/{marko-B9JYg09W.js → marko-YPWiYUQ_.js} +1 -1
- package/ui/dist/assets/{mdc-BkqLhTks.js → mdc-DoQ9fqeC.js} +1 -1
- package/ui/dist/assets/{nginx-Jer0MbpA.js → nginx-BuX_dG5x.js} +1 -1
- package/ui/dist/assets/{nim-Cy_m8HmF.js → nim-oEF2CEaX.js} +1 -1
- package/ui/dist/assets/{org-CokmGrbo.js → org-C1kwr3b8.js} +1 -1
- package/ui/dist/assets/{perl-C8zK1dLy.js → perl-CzZcVIM9.js} +1 -1
- package/ui/dist/assets/{php-CGPNoYNj.js → php-C_i1TWmy.js} +1 -1
- package/ui/dist/assets/{pug-5sES-m6u.js → pug-Oz2JZVGZ.js} +1 -1
- package/ui/dist/assets/{qml-BJN6wOEM.js → qml-DWZFG7aa.js} +1 -1
- package/ui/dist/assets/{r-Byftp3ZA.js → r-CKwXeGZ_.js} +1 -1
- package/ui/dist/assets/{razor-DpZOlAnr.js → razor-DT1mg2x6.js} +1 -1
- package/ui/dist/assets/{regexp-BvqsLg1Y.js → regexp-C2K6ptTb.js} +1 -1
- package/ui/dist/assets/{rst-9vLxmSRm.js → rst-C5gmF0mo.js} +1 -1
- package/ui/dist/assets/{ruby-B0g6MeYE.js → ruby-CrEJdgPT.js} +1 -1
- package/ui/dist/assets/{sas-ho_fqc91.js → sas-D1TGFNd_.js} +1 -1
- package/ui/dist/assets/{scss-CXllYR3p.js → scss-DBO_Sp1C.js} +1 -1
- package/ui/dist/assets/{shellscript-CS4mUnIg.js → shellscript-QIWVo1P5.js} +1 -1
- package/ui/dist/assets/{shellsession-BErKFUp0.js → shellsession-iBMCyJwd.js} +1 -1
- package/ui/dist/assets/{soy-DLadX5Sh.js → soy-NHBvJjBh.js} +1 -1
- package/ui/dist/assets/{sql-D2_tJtd9.js → sql-Yf21hpnW.js} +1 -1
- package/ui/dist/assets/{stata-DeuspBBD.js → stata-CluZWHbV.js} +1 -1
- package/ui/dist/assets/{surrealql-Dsg6kBYD.js → surrealql-Bu2dU1Qj.js} +1 -1
- package/ui/dist/assets/{svelte-BLUhg5N2.js → svelte-Owb3qG7g.js} +1 -1
- package/ui/dist/assets/{templ-DmwzJEXE.js → templ-DScnsiaP.js} +1 -1
- package/ui/dist/assets/{tex-DvJatE2t.js → tex-DvCQ8DJI.js} +1 -1
- package/ui/dist/assets/{ts-tags-DopPyAVy.js → ts-tags-Fh6nOEbM.js} +1 -1
- package/ui/dist/assets/{tsx-Df8h3iwb.js → tsx-C_2AyD6m.js} +1 -1
- package/ui/dist/assets/{twig-D-FWilfB.js → twig-DjT0rOpv.js} +1 -1
- package/ui/dist/assets/{typescript-GaY7hgCy.js → typescript-NDIZTg4J.js} +1 -1
- package/ui/dist/assets/{typst-NzoQLrPM.js → typst-DNJZJFvq.js} +1 -1
- package/ui/dist/assets/{vue-DlAEzgCu.js → vue-BTZXwXJ_.js} +1 -1
- package/ui/dist/assets/{vue-html-ZDj41605.js → vue-html-CBhLp-FO.js} +1 -1
- package/ui/dist/assets/{vue-vine-cO7C1w8g.js → vue-vine-KGJI1qvi.js} +1 -1
- package/ui/dist/assets/{xml-Cw5Gpdej.js → xml-CeV6vl7T.js} +1 -1
- package/ui/dist/assets/{xsl-BJg3bH1H.js → xsl-CibkluSG.js} +1 -1
- package/ui/dist/assets/{yaml-kOrEV2t6.js → yaml-D89KUdIt.js} +1 -1
- package/ui/dist/index.html +3 -3
- package/ui/dist/assets/dist-ByhlQ0Ut.js +0 -1
- package/ui/dist/assets/dist-DfISJt9o.js +0 -12
- package/ui/dist/assets/dist-UGYOZkY4.js +0 -1
- package/ui/dist/assets/dist-oDQCW51e.js +0 -1
- package/ui/dist/assets/index-Dml6ilmw.css +0 -1
- package/ui/dist/assets/index-DxHUxDDf.js +0 -6766
package/dist/cli.js
CHANGED
|
@@ -1994,7 +1994,7 @@ var require_thread_stream = __commonJS((exports, module) => {
|
|
|
1994
1994
|
var { version: version2 } = require_package();
|
|
1995
1995
|
var { EventEmitter } = __require("events");
|
|
1996
1996
|
var { Worker } = __require("worker_threads");
|
|
1997
|
-
var { join:
|
|
1997
|
+
var { join: join9 } = __require("path");
|
|
1998
1998
|
var { pathToFileURL } = __require("url");
|
|
1999
1999
|
var { wait } = require_wait();
|
|
2000
2000
|
var {
|
|
@@ -2044,7 +2044,7 @@ var require_thread_stream = __commonJS((exports, module) => {
|
|
|
2044
2044
|
function createWorker(stream, opts) {
|
|
2045
2045
|
const { filename, workerData } = opts;
|
|
2046
2046
|
const bundlerOverrides = "__bundlerPathsOverrides" in globalThis ? globalThis.__bundlerPathsOverrides : {};
|
|
2047
|
-
const toExecute = bundlerOverrides["thread-stream-worker"] ||
|
|
2047
|
+
const toExecute = bundlerOverrides["thread-stream-worker"] || join9(__dirname, "lib", "worker.js");
|
|
2048
2048
|
const worker = new Worker(toExecute, {
|
|
2049
2049
|
...opts.workerOpts,
|
|
2050
2050
|
name: opts.workerOpts?.name || "thread-stream",
|
|
@@ -2510,7 +2510,7 @@ var require_transport = __commonJS((exports, module) => {
|
|
|
2510
2510
|
var { createRequire } = __require("module");
|
|
2511
2511
|
var { existsSync: existsSync5 } = __require("fs");
|
|
2512
2512
|
var getCallers = require_caller();
|
|
2513
|
-
var { join:
|
|
2513
|
+
var { join: join9, isAbsolute, sep: sep3 } = __require("path");
|
|
2514
2514
|
var { fileURLToPath: fileURLToPath2 } = __require("url");
|
|
2515
2515
|
var sleep = require_atomic_sleep();
|
|
2516
2516
|
var onExit = require_on_exit_leak_free();
|
|
@@ -2663,7 +2663,7 @@ var require_transport = __commonJS((exports, module) => {
|
|
|
2663
2663
|
throw new Error("only one of target or targets can be specified");
|
|
2664
2664
|
}
|
|
2665
2665
|
if (targets) {
|
|
2666
|
-
target = bundlerOverrides["pino-worker"] ||
|
|
2666
|
+
target = bundlerOverrides["pino-worker"] || join9(__dirname, "worker.js");
|
|
2667
2667
|
options.targets = targets.filter((dest) => dest.target).map((dest) => {
|
|
2668
2668
|
return {
|
|
2669
2669
|
...dest,
|
|
@@ -2680,7 +2680,7 @@ var require_transport = __commonJS((exports, module) => {
|
|
|
2680
2680
|
});
|
|
2681
2681
|
});
|
|
2682
2682
|
} else if (pipeline) {
|
|
2683
|
-
target = bundlerOverrides["pino-worker"] ||
|
|
2683
|
+
target = bundlerOverrides["pino-worker"] || join9(__dirname, "worker.js");
|
|
2684
2684
|
options.pipelines = [pipeline.map((dest) => {
|
|
2685
2685
|
return {
|
|
2686
2686
|
...dest,
|
|
@@ -2703,12 +2703,12 @@ var require_transport = __commonJS((exports, module) => {
|
|
|
2703
2703
|
return origin;
|
|
2704
2704
|
}
|
|
2705
2705
|
if (origin === "pino/file") {
|
|
2706
|
-
return
|
|
2706
|
+
return join9(__dirname, "..", "file.js");
|
|
2707
2707
|
}
|
|
2708
2708
|
let fixTarget2;
|
|
2709
2709
|
for (const filePath of callers) {
|
|
2710
2710
|
try {
|
|
2711
|
-
const context = filePath === "node:repl" ? process.cwd() +
|
|
2711
|
+
const context = filePath === "node:repl" ? process.cwd() + sep3 : filePath;
|
|
2712
2712
|
fixTarget2 = createRequire(context).resolve(origin);
|
|
2713
2713
|
break;
|
|
2714
2714
|
} catch (err) {
|
|
@@ -3632,7 +3632,7 @@ var require_safe_stable_stringify = __commonJS((exports, module) => {
|
|
|
3632
3632
|
return circularValue;
|
|
3633
3633
|
}
|
|
3634
3634
|
let res = "";
|
|
3635
|
-
let
|
|
3635
|
+
let join9 = ",";
|
|
3636
3636
|
const originalIndentation = indentation;
|
|
3637
3637
|
if (Array.isArray(value)) {
|
|
3638
3638
|
if (value.length === 0) {
|
|
@@ -3646,7 +3646,7 @@ var require_safe_stable_stringify = __commonJS((exports, module) => {
|
|
|
3646
3646
|
indentation += spacer;
|
|
3647
3647
|
res += `
|
|
3648
3648
|
${indentation}`;
|
|
3649
|
-
|
|
3649
|
+
join9 = `,
|
|
3650
3650
|
${indentation}`;
|
|
3651
3651
|
}
|
|
3652
3652
|
const maximumValuesToStringify = Math.min(value.length, maximumBreadth);
|
|
@@ -3654,13 +3654,13 @@ ${indentation}`;
|
|
|
3654
3654
|
for (;i < maximumValuesToStringify - 1; i++) {
|
|
3655
3655
|
const tmp2 = stringifyFnReplacer(String(i), value, stack, replacer, spacer, indentation);
|
|
3656
3656
|
res += tmp2 !== undefined ? tmp2 : "null";
|
|
3657
|
-
res +=
|
|
3657
|
+
res += join9;
|
|
3658
3658
|
}
|
|
3659
3659
|
const tmp = stringifyFnReplacer(String(i), value, stack, replacer, spacer, indentation);
|
|
3660
3660
|
res += tmp !== undefined ? tmp : "null";
|
|
3661
3661
|
if (value.length - 1 > maximumBreadth) {
|
|
3662
3662
|
const removedKeys = value.length - maximumBreadth - 1;
|
|
3663
|
-
res += `${
|
|
3663
|
+
res += `${join9}"... ${getItemCount(removedKeys)} not stringified"`;
|
|
3664
3664
|
}
|
|
3665
3665
|
if (spacer !== "") {
|
|
3666
3666
|
res += `
|
|
@@ -3681,7 +3681,7 @@ ${originalIndentation}`;
|
|
|
3681
3681
|
let separator = "";
|
|
3682
3682
|
if (spacer !== "") {
|
|
3683
3683
|
indentation += spacer;
|
|
3684
|
-
|
|
3684
|
+
join9 = `,
|
|
3685
3685
|
${indentation}`;
|
|
3686
3686
|
whitespace = " ";
|
|
3687
3687
|
}
|
|
@@ -3695,13 +3695,13 @@ ${indentation}`;
|
|
|
3695
3695
|
const tmp = stringifyFnReplacer(key2, value, stack, replacer, spacer, indentation);
|
|
3696
3696
|
if (tmp !== undefined) {
|
|
3697
3697
|
res += `${separator}${strEscape(key2)}:${whitespace}${tmp}`;
|
|
3698
|
-
separator =
|
|
3698
|
+
separator = join9;
|
|
3699
3699
|
}
|
|
3700
3700
|
}
|
|
3701
3701
|
if (keyLength > maximumBreadth) {
|
|
3702
3702
|
const removedKeys = keyLength - maximumBreadth;
|
|
3703
3703
|
res += `${separator}"...":${whitespace}"${getItemCount(removedKeys)} not stringified"`;
|
|
3704
|
-
separator =
|
|
3704
|
+
separator = join9;
|
|
3705
3705
|
}
|
|
3706
3706
|
if (spacer !== "" && separator.length > 1) {
|
|
3707
3707
|
res = `
|
|
@@ -3741,7 +3741,7 @@ ${originalIndentation}`;
|
|
|
3741
3741
|
}
|
|
3742
3742
|
const originalIndentation = indentation;
|
|
3743
3743
|
let res = "";
|
|
3744
|
-
let
|
|
3744
|
+
let join9 = ",";
|
|
3745
3745
|
if (Array.isArray(value)) {
|
|
3746
3746
|
if (value.length === 0) {
|
|
3747
3747
|
return "[]";
|
|
@@ -3754,7 +3754,7 @@ ${originalIndentation}`;
|
|
|
3754
3754
|
indentation += spacer;
|
|
3755
3755
|
res += `
|
|
3756
3756
|
${indentation}`;
|
|
3757
|
-
|
|
3757
|
+
join9 = `,
|
|
3758
3758
|
${indentation}`;
|
|
3759
3759
|
}
|
|
3760
3760
|
const maximumValuesToStringify = Math.min(value.length, maximumBreadth);
|
|
@@ -3762,13 +3762,13 @@ ${indentation}`;
|
|
|
3762
3762
|
for (;i < maximumValuesToStringify - 1; i++) {
|
|
3763
3763
|
const tmp2 = stringifyArrayReplacer(String(i), value[i], stack, replacer, spacer, indentation);
|
|
3764
3764
|
res += tmp2 !== undefined ? tmp2 : "null";
|
|
3765
|
-
res +=
|
|
3765
|
+
res += join9;
|
|
3766
3766
|
}
|
|
3767
3767
|
const tmp = stringifyArrayReplacer(String(i), value[i], stack, replacer, spacer, indentation);
|
|
3768
3768
|
res += tmp !== undefined ? tmp : "null";
|
|
3769
3769
|
if (value.length - 1 > maximumBreadth) {
|
|
3770
3770
|
const removedKeys = value.length - maximumBreadth - 1;
|
|
3771
|
-
res += `${
|
|
3771
|
+
res += `${join9}"... ${getItemCount(removedKeys)} not stringified"`;
|
|
3772
3772
|
}
|
|
3773
3773
|
if (spacer !== "") {
|
|
3774
3774
|
res += `
|
|
@@ -3781,7 +3781,7 @@ ${originalIndentation}`;
|
|
|
3781
3781
|
let whitespace = "";
|
|
3782
3782
|
if (spacer !== "") {
|
|
3783
3783
|
indentation += spacer;
|
|
3784
|
-
|
|
3784
|
+
join9 = `,
|
|
3785
3785
|
${indentation}`;
|
|
3786
3786
|
whitespace = " ";
|
|
3787
3787
|
}
|
|
@@ -3790,7 +3790,7 @@ ${indentation}`;
|
|
|
3790
3790
|
const tmp = stringifyArrayReplacer(key2, value[key2], stack, replacer, spacer, indentation);
|
|
3791
3791
|
if (tmp !== undefined) {
|
|
3792
3792
|
res += `${separator}${strEscape(key2)}:${whitespace}${tmp}`;
|
|
3793
|
-
separator =
|
|
3793
|
+
separator = join9;
|
|
3794
3794
|
}
|
|
3795
3795
|
}
|
|
3796
3796
|
if (spacer !== "" && separator.length > 1) {
|
|
@@ -3847,20 +3847,20 @@ ${originalIndentation}`;
|
|
|
3847
3847
|
indentation += spacer;
|
|
3848
3848
|
let res2 = `
|
|
3849
3849
|
${indentation}`;
|
|
3850
|
-
const
|
|
3850
|
+
const join10 = `,
|
|
3851
3851
|
${indentation}`;
|
|
3852
3852
|
const maximumValuesToStringify = Math.min(value.length, maximumBreadth);
|
|
3853
3853
|
let i = 0;
|
|
3854
3854
|
for (;i < maximumValuesToStringify - 1; i++) {
|
|
3855
3855
|
const tmp2 = stringifyIndent(String(i), value[i], stack, spacer, indentation);
|
|
3856
3856
|
res2 += tmp2 !== undefined ? tmp2 : "null";
|
|
3857
|
-
res2 +=
|
|
3857
|
+
res2 += join10;
|
|
3858
3858
|
}
|
|
3859
3859
|
const tmp = stringifyIndent(String(i), value[i], stack, spacer, indentation);
|
|
3860
3860
|
res2 += tmp !== undefined ? tmp : "null";
|
|
3861
3861
|
if (value.length - 1 > maximumBreadth) {
|
|
3862
3862
|
const removedKeys = value.length - maximumBreadth - 1;
|
|
3863
|
-
res2 += `${
|
|
3863
|
+
res2 += `${join10}"... ${getItemCount(removedKeys)} not stringified"`;
|
|
3864
3864
|
}
|
|
3865
3865
|
res2 += `
|
|
3866
3866
|
${originalIndentation}`;
|
|
@@ -3876,16 +3876,16 @@ ${originalIndentation}`;
|
|
|
3876
3876
|
return '"[Object]"';
|
|
3877
3877
|
}
|
|
3878
3878
|
indentation += spacer;
|
|
3879
|
-
const
|
|
3879
|
+
const join9 = `,
|
|
3880
3880
|
${indentation}`;
|
|
3881
3881
|
let res = "";
|
|
3882
3882
|
let separator = "";
|
|
3883
3883
|
let maximumPropertiesToStringify = Math.min(keyLength, maximumBreadth);
|
|
3884
3884
|
if (isTypedArrayWithEntries(value)) {
|
|
3885
|
-
res += stringifyTypedArray(value,
|
|
3885
|
+
res += stringifyTypedArray(value, join9, maximumBreadth);
|
|
3886
3886
|
keys = keys.slice(value.length);
|
|
3887
3887
|
maximumPropertiesToStringify -= value.length;
|
|
3888
|
-
separator =
|
|
3888
|
+
separator = join9;
|
|
3889
3889
|
}
|
|
3890
3890
|
if (deterministic) {
|
|
3891
3891
|
keys = sort(keys, comparator);
|
|
@@ -3896,13 +3896,13 @@ ${indentation}`;
|
|
|
3896
3896
|
const tmp = stringifyIndent(key2, value[key2], stack, spacer, indentation);
|
|
3897
3897
|
if (tmp !== undefined) {
|
|
3898
3898
|
res += `${separator}${strEscape(key2)}: ${tmp}`;
|
|
3899
|
-
separator =
|
|
3899
|
+
separator = join9;
|
|
3900
3900
|
}
|
|
3901
3901
|
}
|
|
3902
3902
|
if (keyLength > maximumBreadth) {
|
|
3903
3903
|
const removedKeys = keyLength - maximumBreadth;
|
|
3904
3904
|
res += `${separator}"...": "${getItemCount(removedKeys)} not stringified"`;
|
|
3905
|
-
separator =
|
|
3905
|
+
separator = join9;
|
|
3906
3906
|
}
|
|
3907
3907
|
if (separator !== "") {
|
|
3908
3908
|
res = `
|
|
@@ -5804,7 +5804,7 @@ __export(exports_dist, {
|
|
|
5804
5804
|
import { styleText as styleText2, stripVTControlCharacters } from "util";
|
|
5805
5805
|
import process$1 from "process";
|
|
5806
5806
|
import { existsSync as existsSync11, lstatSync, readdirSync as readdirSync6 } from "fs";
|
|
5807
|
-
import { dirname as
|
|
5807
|
+
import { dirname as dirname9, join as join17 } from "path";
|
|
5808
5808
|
function isUnicodeSupported() {
|
|
5809
5809
|
if (process$1.platform !== "win32") {
|
|
5810
5810
|
return process$1.env.TERM !== "linux";
|
|
@@ -6515,10 +6515,10 @@ ${n3}
|
|
|
6515
6515
|
return [];
|
|
6516
6516
|
try {
|
|
6517
6517
|
let i;
|
|
6518
|
-
existsSync11(t2) ? lstatSync(t2).isDirectory() && (!e.directory || t2.endsWith("/")) ? i = t2 : i =
|
|
6518
|
+
existsSync11(t2) ? lstatSync(t2).isDirectory() && (!e.directory || t2.endsWith("/")) ? i = t2 : i = dirname9(t2) : i = dirname9(t2);
|
|
6519
6519
|
const c2 = t2.length > 1 && t2.endsWith("/") ? t2.slice(0, -1) : t2;
|
|
6520
6520
|
return readdirSync6(i).map((r2) => {
|
|
6521
|
-
const n3 =
|
|
6521
|
+
const n3 = join17(i, r2), m3 = lstatSync(n3);
|
|
6522
6522
|
return {
|
|
6523
6523
|
name: r2,
|
|
6524
6524
|
path: n3,
|
|
@@ -7066,9 +7066,18 @@ function fatalDenyLine(reason) {
|
|
|
7066
7066
|
});
|
|
7067
7067
|
}
|
|
7068
7068
|
|
|
7069
|
-
// src/adapters/claude/
|
|
7069
|
+
// src/adapters/claude/paths.ts
|
|
7070
7070
|
import { homedir } from "os";
|
|
7071
7071
|
import { join } from "path";
|
|
7072
|
+
function claudeConfigDir() {
|
|
7073
|
+
return process.env.CLAUDE_CONFIG_DIR || join(homedir(), ".claude");
|
|
7074
|
+
}
|
|
7075
|
+
function installedPluginsFile() {
|
|
7076
|
+
return join(claudeConfigDir(), "plugins", "installed_plugins.json");
|
|
7077
|
+
}
|
|
7078
|
+
function userSettingsFile() {
|
|
7079
|
+
return join(claudeConfigDir(), "settings.json");
|
|
7080
|
+
}
|
|
7072
7081
|
|
|
7073
7082
|
// src/lib/json-file.ts
|
|
7074
7083
|
import { readFileSync } from "fs";
|
|
@@ -7089,16 +7098,12 @@ async function readJsonFile(path) {
|
|
|
7089
7098
|
}
|
|
7090
7099
|
|
|
7091
7100
|
// src/adapters/claude/install.ts
|
|
7092
|
-
function claudeConfigDir() {
|
|
7093
|
-
return process.env.CLAUDE_CONFIG_DIR || join(homedir(), ".claude");
|
|
7094
|
-
}
|
|
7095
7101
|
var PLUGIN_ID = "caret@caret";
|
|
7096
7102
|
function readClaudeInstallState() {
|
|
7097
|
-
const dir = claudeConfigDir();
|
|
7098
7103
|
return {
|
|
7099
|
-
pluginVersion: readPluginVersion(
|
|
7100
|
-
pluginEnabled: readPluginEnabled(
|
|
7101
|
-
hookInUserSettings: readHookInUserSettings(
|
|
7104
|
+
pluginVersion: readPluginVersion(installedPluginsFile()),
|
|
7105
|
+
pluginEnabled: readPluginEnabled(userSettingsFile()),
|
|
7106
|
+
hookInUserSettings: readHookInUserSettings(userSettingsFile())
|
|
7102
7107
|
};
|
|
7103
7108
|
}
|
|
7104
7109
|
function readPluginVersion(path) {
|
|
@@ -7141,6 +7146,180 @@ function readHookInUserSettings(path) {
|
|
|
7141
7146
|
return false;
|
|
7142
7147
|
}
|
|
7143
7148
|
|
|
7149
|
+
// src/adapters/claude/skills.ts
|
|
7150
|
+
import { access, readdir } from "fs/promises";
|
|
7151
|
+
import { join as join3 } from "path";
|
|
7152
|
+
|
|
7153
|
+
// src/lib/skill-doc.ts
|
|
7154
|
+
import { readFile as readFile2, realpath, stat } from "fs/promises";
|
|
7155
|
+
import { join as join2, sep } from "path";
|
|
7156
|
+
var FENCE = "---";
|
|
7157
|
+
var MAX_DOC_BYTES = 1024 * 1024;
|
|
7158
|
+
var DESCRIPTION_LINE = /^description:[ \t]*(.*)$/;
|
|
7159
|
+
var BLOCK_INTRODUCER = /^([|>])[-+]?\d*$/;
|
|
7160
|
+
function blockJoiner(value) {
|
|
7161
|
+
const introducer = BLOCK_INTRODUCER.exec(value)?.[1];
|
|
7162
|
+
if (introducer === undefined)
|
|
7163
|
+
return;
|
|
7164
|
+
return introducer === "|" ? `
|
|
7165
|
+
` : " ";
|
|
7166
|
+
}
|
|
7167
|
+
async function containedFile(root, relative) {
|
|
7168
|
+
const [rootReal, real] = await Promise.all([
|
|
7169
|
+
realpath(root).catch(() => null),
|
|
7170
|
+
realpath(join2(root, relative)).catch(() => null)
|
|
7171
|
+
]);
|
|
7172
|
+
if (rootReal === null || real === null)
|
|
7173
|
+
return null;
|
|
7174
|
+
return real === rootReal || real.startsWith(rootReal + sep) ? real : null;
|
|
7175
|
+
}
|
|
7176
|
+
function frontmatterLines(content) {
|
|
7177
|
+
const lines = content.split(`
|
|
7178
|
+
`).map((line) => line.replace(/\r$/, ""));
|
|
7179
|
+
if (lines[0]?.trimEnd() !== FENCE)
|
|
7180
|
+
return null;
|
|
7181
|
+
const close = lines.findIndex((line, i) => i > 0 && line.trimEnd() === FENCE);
|
|
7182
|
+
return close === -1 ? null : lines.slice(1, close);
|
|
7183
|
+
}
|
|
7184
|
+
function unquote(value) {
|
|
7185
|
+
const quote = value[0];
|
|
7186
|
+
if ((quote === '"' || quote === "'") && value.length > 1 && value.endsWith(quote)) {
|
|
7187
|
+
return value.slice(1, -1);
|
|
7188
|
+
}
|
|
7189
|
+
return value;
|
|
7190
|
+
}
|
|
7191
|
+
function blockScalar(rest, joiner) {
|
|
7192
|
+
const taken = [];
|
|
7193
|
+
for (const line of rest) {
|
|
7194
|
+
if (line.trim() !== "" && !/^[ \t]/.test(line))
|
|
7195
|
+
break;
|
|
7196
|
+
taken.push(line.trim());
|
|
7197
|
+
}
|
|
7198
|
+
const kept = joiner === `
|
|
7199
|
+
` ? taken : taken.filter((line) => line !== "");
|
|
7200
|
+
return kept.join(joiner).trim();
|
|
7201
|
+
}
|
|
7202
|
+
function descriptionIn(block) {
|
|
7203
|
+
const at = block.findIndex((line) => DESCRIPTION_LINE.test(line));
|
|
7204
|
+
if (at === -1)
|
|
7205
|
+
return null;
|
|
7206
|
+
const value = (block[at]?.match(DESCRIPTION_LINE)?.[1] ?? "").trimEnd();
|
|
7207
|
+
const joiner = blockJoiner(value);
|
|
7208
|
+
const text = joiner === undefined ? unquote(value).trim() : blockScalar(block.slice(at + 1), joiner);
|
|
7209
|
+
return text === "" ? null : text;
|
|
7210
|
+
}
|
|
7211
|
+
async function descriptionOf(abs) {
|
|
7212
|
+
const size = await stat(abs).then((s) => s.size, () => null);
|
|
7213
|
+
if (size === null || size > MAX_DOC_BYTES)
|
|
7214
|
+
return null;
|
|
7215
|
+
let content;
|
|
7216
|
+
try {
|
|
7217
|
+
content = await readFile2(abs, "utf-8");
|
|
7218
|
+
} catch {
|
|
7219
|
+
return null;
|
|
7220
|
+
}
|
|
7221
|
+
const block = frontmatterLines(content);
|
|
7222
|
+
return block === null ? null : descriptionIn(block);
|
|
7223
|
+
}
|
|
7224
|
+
async function readDescriptionUnder(root, relative) {
|
|
7225
|
+
const abs = await containedFile(root, relative);
|
|
7226
|
+
return abs === null ? null : descriptionOf(abs);
|
|
7227
|
+
}
|
|
7228
|
+
|
|
7229
|
+
// src/adapters/claude/skills.ts
|
|
7230
|
+
var SKILL_FILE = "SKILL.md";
|
|
7231
|
+
async function skillNamesUnder(root) {
|
|
7232
|
+
let names;
|
|
7233
|
+
try {
|
|
7234
|
+
names = await readdir(root);
|
|
7235
|
+
} catch {
|
|
7236
|
+
return [];
|
|
7237
|
+
}
|
|
7238
|
+
const found = await Promise.all(names.map((name) => hasSkillFile(join3(root, name))));
|
|
7239
|
+
return names.filter((_, i) => found[i]).sort();
|
|
7240
|
+
}
|
|
7241
|
+
async function hasSkillFile(dir) {
|
|
7242
|
+
try {
|
|
7243
|
+
await access(join3(dir, SKILL_FILE));
|
|
7244
|
+
return true;
|
|
7245
|
+
} catch {
|
|
7246
|
+
return false;
|
|
7247
|
+
}
|
|
7248
|
+
}
|
|
7249
|
+
function settingsLayers(cwd) {
|
|
7250
|
+
const userDir = claudeConfigDir();
|
|
7251
|
+
return [
|
|
7252
|
+
userSettingsFile(),
|
|
7253
|
+
join3(userDir, "settings.local.json"),
|
|
7254
|
+
join3(cwd, ".claude", "settings.json"),
|
|
7255
|
+
join3(cwd, ".claude", "settings.local.json")
|
|
7256
|
+
];
|
|
7257
|
+
}
|
|
7258
|
+
var userSkillsRoot = () => join3(claudeConfigDir(), "skills");
|
|
7259
|
+
var projectSkillsRoot = (cwd) => join3(cwd, ".claude", "skills");
|
|
7260
|
+
var pluginSkillsRoot = (install) => join3(install, "skills");
|
|
7261
|
+
async function enabledPluginKeys(cwd) {
|
|
7262
|
+
const layers = await Promise.all(settingsLayers(cwd).map((path) => readJsonFile(path)));
|
|
7263
|
+
const merged = {};
|
|
7264
|
+
for (const layer of layers)
|
|
7265
|
+
Object.assign(merged, layer?.enabledPlugins ?? {});
|
|
7266
|
+
return new Set(Object.keys(merged).filter((key) => merged[key] === true));
|
|
7267
|
+
}
|
|
7268
|
+
function pickInstallPath(installs, cwd) {
|
|
7269
|
+
const usable = installs.filter((install) => typeof install.installPath === "string");
|
|
7270
|
+
const here = usable.find((install) => install.projectPath === cwd);
|
|
7271
|
+
const anywhere = usable.find((install) => install.scope === "user" || install.scope === "managed");
|
|
7272
|
+
return (here ?? anywhere ?? usable[0])?.installPath;
|
|
7273
|
+
}
|
|
7274
|
+
async function enabledPlugins(cwd) {
|
|
7275
|
+
const [registry, enabled] = await Promise.all([
|
|
7276
|
+
readJsonFile(installedPluginsFile()),
|
|
7277
|
+
enabledPluginKeys(cwd)
|
|
7278
|
+
]);
|
|
7279
|
+
const out = [];
|
|
7280
|
+
for (const [key, installs] of Object.entries(registry?.plugins ?? {})) {
|
|
7281
|
+
if (!enabled.has(key))
|
|
7282
|
+
continue;
|
|
7283
|
+
const installPath = pickInstallPath(installs ?? [], cwd);
|
|
7284
|
+
if (installPath === undefined)
|
|
7285
|
+
continue;
|
|
7286
|
+
out.push([key.split("@")[0] ?? key, installPath]);
|
|
7287
|
+
}
|
|
7288
|
+
return out.sort(([a], [b]) => a < b ? -1 : a > b ? 1 : 0);
|
|
7289
|
+
}
|
|
7290
|
+
async function readClaudeSkills(cwd) {
|
|
7291
|
+
const [user, project, plugins] = await Promise.all([
|
|
7292
|
+
skillNamesUnder(userSkillsRoot()),
|
|
7293
|
+
skillNamesUnder(projectSkillsRoot(cwd)),
|
|
7294
|
+
enabledPlugins(cwd)
|
|
7295
|
+
]);
|
|
7296
|
+
const pluginSkills = await Promise.all(plugins.map(async ([plugin, dir]) => (await skillNamesUnder(pluginSkillsRoot(dir))).map((name) => ({ name: `${plugin}:${name}`, origin: "plugin" }))));
|
|
7297
|
+
return [
|
|
7298
|
+
...user.map((name) => ({ name, origin: "user" })),
|
|
7299
|
+
...project.map((name) => ({ name, origin: "project" })),
|
|
7300
|
+
...pluginSkills.flat()
|
|
7301
|
+
];
|
|
7302
|
+
}
|
|
7303
|
+
async function skillDocLocation(cwd, skill) {
|
|
7304
|
+
const under = (root, name) => ({ root, relative: join3(name, SKILL_FILE) });
|
|
7305
|
+
if (skill.origin === "user")
|
|
7306
|
+
return under(userSkillsRoot(), skill.name);
|
|
7307
|
+
if (skill.origin === "project")
|
|
7308
|
+
return under(projectSkillsRoot(cwd), skill.name);
|
|
7309
|
+
if (skill.origin !== "plugin")
|
|
7310
|
+
return null;
|
|
7311
|
+
const at = skill.name.indexOf(":");
|
|
7312
|
+
if (at === -1)
|
|
7313
|
+
return null;
|
|
7314
|
+
const plugin = skill.name.slice(0, at);
|
|
7315
|
+
const hit = (await enabledPlugins(cwd)).find(([key]) => key === plugin);
|
|
7316
|
+
return hit === undefined ? null : under(pluginSkillsRoot(hit[1]), skill.name.slice(at + 1));
|
|
7317
|
+
}
|
|
7318
|
+
async function readClaudeSkillDescription(cwd, skill) {
|
|
7319
|
+
const at = await skillDocLocation(cwd, skill);
|
|
7320
|
+
return at === null ? null : readDescriptionUnder(at.root, at.relative);
|
|
7321
|
+
}
|
|
7322
|
+
|
|
7144
7323
|
// src/adapters/claude/index.ts
|
|
7145
7324
|
function toolInputEcho(input) {
|
|
7146
7325
|
if (!input)
|
|
@@ -7177,6 +7356,12 @@ var claudeAdapter = {
|
|
|
7177
7356
|
},
|
|
7178
7357
|
readInstallState() {
|
|
7179
7358
|
return readClaudeInstallState();
|
|
7359
|
+
},
|
|
7360
|
+
listSkills(cwd) {
|
|
7361
|
+
return readClaudeSkills(cwd);
|
|
7362
|
+
},
|
|
7363
|
+
readSkillDescription(cwd, skill) {
|
|
7364
|
+
return readClaudeSkillDescription(cwd, skill);
|
|
7180
7365
|
}
|
|
7181
7366
|
};
|
|
7182
7367
|
|
|
@@ -7214,7 +7399,7 @@ function fatalDenyLine2(reason) {
|
|
|
7214
7399
|
// src/adapters/codex/install.ts
|
|
7215
7400
|
import { readFileSync as readFileSync2 } from "fs";
|
|
7216
7401
|
import { homedir as homedir2 } from "os";
|
|
7217
|
-
import { join as
|
|
7402
|
+
import { join as join4 } from "path";
|
|
7218
7403
|
|
|
7219
7404
|
// node_modules/.bun/smol-toml@1.8.0/node_modules/smol-toml/dist/date.js
|
|
7220
7405
|
/*!
|
|
@@ -7468,7 +7653,7 @@ function skipVoid(ctx, banNewLines, banComments) {
|
|
|
7468
7653
|
skipComment(ctx);
|
|
7469
7654
|
}
|
|
7470
7655
|
}
|
|
7471
|
-
function skipUntil(ctx,
|
|
7656
|
+
function skipUntil(ctx, sep2, end) {
|
|
7472
7657
|
let ptr = ctx.p;
|
|
7473
7658
|
if (!end) {
|
|
7474
7659
|
ptr = indexOfNewline(ctx.s, ptr);
|
|
@@ -7479,7 +7664,7 @@ function skipUntil(ctx, sep, end) {
|
|
|
7479
7664
|
let c = ctx.s.charCodeAt(ctx.p);
|
|
7480
7665
|
if (c === 35) {
|
|
7481
7666
|
skipComment(ctx);
|
|
7482
|
-
} else if (c === end || c ===
|
|
7667
|
+
} else if (c === end || c === sep2) {
|
|
7483
7668
|
return;
|
|
7484
7669
|
}
|
|
7485
7670
|
}
|
|
@@ -8095,14 +8280,14 @@ function parse(toml, { maxDepth = 1000, integersAsBigInt } = {}) {
|
|
|
8095
8280
|
|
|
8096
8281
|
// src/adapters/codex/install.ts
|
|
8097
8282
|
function codexConfigDir() {
|
|
8098
|
-
return process.env.CODEX_HOME ||
|
|
8283
|
+
return process.env.CODEX_HOME || join4(homedir2(), ".codex");
|
|
8099
8284
|
}
|
|
8100
8285
|
function readCodexInstallState() {
|
|
8101
8286
|
const dir = codexConfigDir();
|
|
8102
8287
|
return {
|
|
8103
8288
|
pluginVersion: "unknown",
|
|
8104
|
-
pluginEnabled: readCodexHooksFeature(
|
|
8105
|
-
hookInUserSettings: readHookInUserSettings2(
|
|
8289
|
+
pluginEnabled: readCodexHooksFeature(join4(dir, "config.toml")),
|
|
8290
|
+
hookInUserSettings: readHookInUserSettings2(join4(dir, "hooks.json"))
|
|
8106
8291
|
};
|
|
8107
8292
|
}
|
|
8108
8293
|
function readCodexHooksFeature(path) {
|
|
@@ -8158,6 +8343,12 @@ var codexAdapter = {
|
|
|
8158
8343
|
},
|
|
8159
8344
|
readInstallState() {
|
|
8160
8345
|
return readCodexInstallState();
|
|
8346
|
+
},
|
|
8347
|
+
listSkills() {
|
|
8348
|
+
return Promise.resolve([]);
|
|
8349
|
+
},
|
|
8350
|
+
readSkillDescription() {
|
|
8351
|
+
return Promise.resolve(null);
|
|
8161
8352
|
}
|
|
8162
8353
|
};
|
|
8163
8354
|
|
|
@@ -8180,7 +8371,7 @@ function fatalDenyLine3(reason) {
|
|
|
8180
8371
|
|
|
8181
8372
|
// src/adapters/opencode/install.ts
|
|
8182
8373
|
import { existsSync as existsSync3, readFileSync as readFileSync4 } from "fs";
|
|
8183
|
-
import { join as
|
|
8374
|
+
import { join as join7 } from "path";
|
|
8184
8375
|
|
|
8185
8376
|
// node_modules/.bun/jsonc-parser@3.3.1/node_modules/jsonc-parser/lib/esm/impl/scanner.js
|
|
8186
8377
|
function createScanner(text, ignoreTrivia = false) {
|
|
@@ -8962,11 +9153,11 @@ function parseTree(text, errors = [], options = ParseOptions.DEFAULT) {
|
|
|
8962
9153
|
onValue({ type: getNodeType(value), offset, length, parent: currentParent, value });
|
|
8963
9154
|
ensurePropertyComplete(offset + length);
|
|
8964
9155
|
},
|
|
8965
|
-
onSeparator: (
|
|
9156
|
+
onSeparator: (sep2, offset, length) => {
|
|
8966
9157
|
if (currentParent.type === "property") {
|
|
8967
|
-
if (
|
|
9158
|
+
if (sep2 === ":") {
|
|
8968
9159
|
currentParent.colonOffset = offset;
|
|
8969
|
-
} else if (
|
|
9160
|
+
} else if (sep2 === ",") {
|
|
8970
9161
|
ensurePropertyComplete(offset);
|
|
8971
9162
|
}
|
|
8972
9163
|
}
|
|
@@ -9508,7 +9699,7 @@ function applyEdits(text, edits) {
|
|
|
9508
9699
|
// src/adapters/opencode/paths.ts
|
|
9509
9700
|
import { existsSync, readdirSync } from "fs";
|
|
9510
9701
|
import { homedir as homedir3 } from "os";
|
|
9511
|
-
import { basename, dirname, join as
|
|
9702
|
+
import { basename, dirname, join as join5 } from "path";
|
|
9512
9703
|
var CARET_PACKAGE = "@macintacos/caret";
|
|
9513
9704
|
function localPluginSpecifier(repoDir) {
|
|
9514
9705
|
return `file:${repoDir}`;
|
|
@@ -9530,39 +9721,42 @@ function opencodeConfigDir() {
|
|
|
9530
9721
|
if (override)
|
|
9531
9722
|
return override;
|
|
9532
9723
|
const xdg = process.env.XDG_CONFIG_HOME?.trim();
|
|
9533
|
-
return
|
|
9724
|
+
return join5(xdg || join5(homedir3(), ".config"), "opencode");
|
|
9534
9725
|
}
|
|
9535
9726
|
function resolveConfigFile(configDir) {
|
|
9536
9727
|
for (const name of CONFIG_FILENAMES) {
|
|
9537
|
-
const p =
|
|
9728
|
+
const p = join5(configDir, name);
|
|
9538
9729
|
if (existsSync(p))
|
|
9539
9730
|
return p;
|
|
9540
9731
|
}
|
|
9541
|
-
return
|
|
9732
|
+
return join5(configDir, "opencode.json");
|
|
9542
9733
|
}
|
|
9543
9734
|
function commandDir(configDir) {
|
|
9544
|
-
return
|
|
9735
|
+
return join5(configDir, COMMAND_DIRNAME);
|
|
9736
|
+
}
|
|
9737
|
+
function commandDirs(configDir) {
|
|
9738
|
+
return [commandDir(configDir), join5(configDir, LEGACY_COMMAND_DIRNAME)];
|
|
9545
9739
|
}
|
|
9546
9740
|
var LEGACY_PLUGIN_FILENAME = "caret.ts";
|
|
9547
9741
|
var LEGACY_PLUGIN_DIRNAMES = ["plugins", "plugin"];
|
|
9548
9742
|
var LEGACY_COMMAND_DIRNAME = "command";
|
|
9549
9743
|
function existingLegacyInstallFiles(configDir) {
|
|
9550
|
-
const plugins = LEGACY_PLUGIN_DIRNAMES.map((d) =>
|
|
9744
|
+
const plugins = LEGACY_PLUGIN_DIRNAMES.map((d) => join5(configDir, d, LEGACY_PLUGIN_FILENAME));
|
|
9551
9745
|
let entries;
|
|
9552
9746
|
try {
|
|
9553
|
-
entries = readdirSync(
|
|
9747
|
+
entries = readdirSync(join5(configDir, LEGACY_COMMAND_DIRNAME), { withFileTypes: true });
|
|
9554
9748
|
} catch {
|
|
9555
9749
|
entries = [];
|
|
9556
9750
|
}
|
|
9557
|
-
const commands = entries.filter((e) => !e.isDirectory() && e.name.startsWith(COMMAND_NAMESPACE)).filter((e) => e.name.endsWith(".md")).map((e) =>
|
|
9751
|
+
const commands = entries.filter((e) => !e.isDirectory() && e.name.startsWith(COMMAND_NAMESPACE)).filter((e) => e.name.endsWith(".md")).map((e) => join5(configDir, LEGACY_COMMAND_DIRNAME, e.name)).sort();
|
|
9558
9752
|
return [...plugins, ...commands].filter((p) => existsSync(p));
|
|
9559
9753
|
}
|
|
9560
9754
|
function opencodeCachePackagesDir() {
|
|
9561
9755
|
const xdg = process.env.XDG_CACHE_HOME?.trim();
|
|
9562
|
-
return
|
|
9756
|
+
return join5(xdg || join5(homedir3(), ".cache"), "opencode", "packages");
|
|
9563
9757
|
}
|
|
9564
9758
|
function opencodeCachePackageDir(pkg = CARET_PACKAGE) {
|
|
9565
|
-
return
|
|
9759
|
+
return join5(opencodeCachePackagesDir(), pkg);
|
|
9566
9760
|
}
|
|
9567
9761
|
function existingOpencodeCachePackageDirs(pkg = CARET_PACKAGE) {
|
|
9568
9762
|
const bare = opencodeCachePackageDir(pkg);
|
|
@@ -9575,12 +9769,12 @@ function existingOpencodeCachePackageDirs(pkg = CARET_PACKAGE) {
|
|
|
9575
9769
|
return [];
|
|
9576
9770
|
}
|
|
9577
9771
|
const pinned = names.filter((n) => n.startsWith(`${leaf}@`)).sort();
|
|
9578
|
-
return [...names.includes(leaf) ? [bare] : [], ...pinned.map((n) =>
|
|
9772
|
+
return [...names.includes(leaf) ? [bare] : [], ...pinned.map((n) => join5(parent, n))];
|
|
9579
9773
|
}
|
|
9580
9774
|
|
|
9581
9775
|
// src/adapters/opencode/upgrade.ts
|
|
9582
9776
|
import { existsSync as existsSync2, readFileSync as readFileSync3, rmSync } from "fs";
|
|
9583
|
-
import { join as
|
|
9777
|
+
import { join as join6 } from "path";
|
|
9584
9778
|
|
|
9585
9779
|
// src/adapters/opencode/config-plugin.ts
|
|
9586
9780
|
var FORMATTING = { insertSpaces: true, tabSize: 2 };
|
|
@@ -9647,9 +9841,7 @@ function removePluginFromConfigText(existing, pkg) {
|
|
|
9647
9841
|
return applyEdits(existing, edits);
|
|
9648
9842
|
}
|
|
9649
9843
|
|
|
9650
|
-
// src/
|
|
9651
|
-
var NPM_LATEST_URL = `https://registry.npmjs.org/${CARET_PACKAGE}/latest`;
|
|
9652
|
-
var NPM_TIMEOUT_MS = 3000;
|
|
9844
|
+
// src/lib/semver.ts
|
|
9653
9845
|
function parseVersionTriple(v) {
|
|
9654
9846
|
const m = v.trim().replace(/^v/, "").match(/^(\d+)\.(\d+)\.(\d+)/);
|
|
9655
9847
|
return m ? [Number(m[1]), Number(m[2]), Number(m[3])] : null;
|
|
@@ -9667,6 +9859,8 @@ function isNewer(latest, current) {
|
|
|
9667
9859
|
return a1 > b1;
|
|
9668
9860
|
return a2 > b2;
|
|
9669
9861
|
}
|
|
9862
|
+
|
|
9863
|
+
// src/adapters/opencode/upgrade.ts
|
|
9670
9864
|
function upgradeVerdict(input) {
|
|
9671
9865
|
const { entry, cached, published } = input;
|
|
9672
9866
|
if (published === null) {
|
|
@@ -9691,7 +9885,7 @@ function upgradeVerdict(input) {
|
|
|
9691
9885
|
function readCachedCaretVersion(dirs = existingOpencodeCachePackageDirs()) {
|
|
9692
9886
|
for (const d of dirs) {
|
|
9693
9887
|
try {
|
|
9694
|
-
const deps = JSON.parse(readFileSync3(
|
|
9888
|
+
const deps = JSON.parse(readFileSync3(join6(d, "package.json"), "utf-8")).dependencies;
|
|
9695
9889
|
const v = deps?.[CARET_PACKAGE];
|
|
9696
9890
|
if (typeof v === "string" && v.length > 0)
|
|
9697
9891
|
return v;
|
|
@@ -9709,18 +9903,6 @@ function clearCachedCaret(dirs = existingOpencodeCachePackageDirs()) {
|
|
|
9709
9903
|
}
|
|
9710
9904
|
return cleared;
|
|
9711
9905
|
}
|
|
9712
|
-
async function publishedCaretVersion(fetchImpl = fetch) {
|
|
9713
|
-
try {
|
|
9714
|
-
const res = await fetchImpl(NPM_LATEST_URL, { signal: AbortSignal.timeout(NPM_TIMEOUT_MS) });
|
|
9715
|
-
if (!res.ok)
|
|
9716
|
-
return null;
|
|
9717
|
-
const body = await res.json();
|
|
9718
|
-
const v = body?.version;
|
|
9719
|
-
return typeof v === "string" && v.length > 0 ? v : null;
|
|
9720
|
-
} catch {
|
|
9721
|
-
return null;
|
|
9722
|
-
}
|
|
9723
|
-
}
|
|
9724
9906
|
|
|
9725
9907
|
// src/adapters/opencode/install.ts
|
|
9726
9908
|
function readOpencodeInstallState() {
|
|
@@ -9738,7 +9920,7 @@ function readOpencodeInstallState() {
|
|
|
9738
9920
|
function readCaretInPluginArray(dir) {
|
|
9739
9921
|
let sawConfig = false;
|
|
9740
9922
|
for (const name of CONFIG_FILENAMES) {
|
|
9741
|
-
const path =
|
|
9923
|
+
const path = join7(dir, name);
|
|
9742
9924
|
if (!existsSync3(path))
|
|
9743
9925
|
continue;
|
|
9744
9926
|
let cfg;
|
|
@@ -9758,6 +9940,33 @@ function readCaretInPluginArray(dir) {
|
|
|
9758
9940
|
return sawConfig ? false : "unknown";
|
|
9759
9941
|
}
|
|
9760
9942
|
|
|
9943
|
+
// src/adapters/opencode/skills.ts
|
|
9944
|
+
import { readdir as readdir2 } from "fs/promises";
|
|
9945
|
+
import { sep as sep2 } from "path";
|
|
9946
|
+
async function commandNamesUnder(dir) {
|
|
9947
|
+
let entries;
|
|
9948
|
+
try {
|
|
9949
|
+
entries = await readdir2(dir, { recursive: true });
|
|
9950
|
+
} catch {
|
|
9951
|
+
return [];
|
|
9952
|
+
}
|
|
9953
|
+
return entries.filter((rel) => rel.endsWith(".md")).map((rel) => rel.slice(0, -".md".length).split(sep2).join("/"));
|
|
9954
|
+
}
|
|
9955
|
+
async function readOpencodeCommands() {
|
|
9956
|
+
const perDir = await Promise.all(commandDirs(opencodeConfigDir()).map(commandNamesUnder));
|
|
9957
|
+
const names = new Set(perDir.flat());
|
|
9958
|
+
return [...names].sort().map((name) => ({ name, origin: "command" }));
|
|
9959
|
+
}
|
|
9960
|
+
async function readOpencodeCommandDescription(name) {
|
|
9961
|
+
const relative = `${name}.md`;
|
|
9962
|
+
for (const dir of commandDirs(opencodeConfigDir())) {
|
|
9963
|
+
const abs = await containedFile(dir, relative);
|
|
9964
|
+
if (abs !== null)
|
|
9965
|
+
return descriptionOf(abs);
|
|
9966
|
+
}
|
|
9967
|
+
return null;
|
|
9968
|
+
}
|
|
9969
|
+
|
|
9761
9970
|
// src/adapters/opencode/index.ts
|
|
9762
9971
|
var opencodeAdapter = {
|
|
9763
9972
|
id: "opencode",
|
|
@@ -9784,6 +9993,12 @@ var opencodeAdapter = {
|
|
|
9784
9993
|
},
|
|
9785
9994
|
readInstallState() {
|
|
9786
9995
|
return readOpencodeInstallState();
|
|
9996
|
+
},
|
|
9997
|
+
listSkills() {
|
|
9998
|
+
return readOpencodeCommands();
|
|
9999
|
+
},
|
|
10000
|
+
readSkillDescription(_cwd, skill) {
|
|
10001
|
+
return readOpencodeCommandDescription(skill.name);
|
|
9787
10002
|
}
|
|
9788
10003
|
};
|
|
9789
10004
|
|
|
@@ -9824,7 +10039,7 @@ function fatalDeny(reason) {
|
|
|
9824
10039
|
|
|
9825
10040
|
// src/commands/daemon.ts
|
|
9826
10041
|
import { randomUUID } from "crypto";
|
|
9827
|
-
import { existsSync as existsSync7
|
|
10042
|
+
import { existsSync as existsSync7 } from "fs";
|
|
9828
10043
|
|
|
9829
10044
|
// src/config/settings.ts
|
|
9830
10045
|
import { readFileSync as readFileSync7, statSync as statSync2 } from "fs";
|
|
@@ -24208,6 +24423,9 @@ function configFile() {
|
|
|
24208
24423
|
function prefsFile() {
|
|
24209
24424
|
return `${stateDir()}/prefs.json`;
|
|
24210
24425
|
}
|
|
24426
|
+
function updateCheckFile() {
|
|
24427
|
+
return `${stateDir()}/update-check.json`;
|
|
24428
|
+
}
|
|
24211
24429
|
function logsDir() {
|
|
24212
24430
|
return `${stateDir()}/logs`;
|
|
24213
24431
|
}
|
|
@@ -24254,7 +24472,7 @@ import { createHash } from "crypto";
|
|
|
24254
24472
|
|
|
24255
24473
|
// src/ui/assets.ts
|
|
24256
24474
|
import { readdirSync as readdirSync2 } from "fs";
|
|
24257
|
-
import { dirname as dirname2, join as
|
|
24475
|
+
import { dirname as dirname2, join as join8, relative } from "path";
|
|
24258
24476
|
import { fileURLToPath } from "url";
|
|
24259
24477
|
function fromPathMap(map2) {
|
|
24260
24478
|
const paths = Object.keys(map2).sort();
|
|
@@ -24270,7 +24488,7 @@ function assetsFromDist(distDir) {
|
|
|
24270
24488
|
const map2 = {};
|
|
24271
24489
|
const walk = (dir) => {
|
|
24272
24490
|
for (const ent of readdirSync2(dir, { withFileTypes: true })) {
|
|
24273
|
-
const full =
|
|
24491
|
+
const full = join8(dir, ent.name);
|
|
24274
24492
|
if (ent.isDirectory())
|
|
24275
24493
|
walk(full);
|
|
24276
24494
|
else if (ent.isFile())
|
|
@@ -24302,13 +24520,13 @@ async function loadUiAssets() {
|
|
|
24302
24520
|
if (fromDist)
|
|
24303
24521
|
return fromDist;
|
|
24304
24522
|
}
|
|
24305
|
-
const besideDist =
|
|
24523
|
+
const besideDist = join8(dirname2(process.execPath), "ui");
|
|
24306
24524
|
return assetsFromDist(besideDist);
|
|
24307
24525
|
}
|
|
24308
24526
|
// package.json
|
|
24309
24527
|
var package_default = {
|
|
24310
24528
|
name: "@macintacos/caret",
|
|
24311
|
-
version: "0.
|
|
24529
|
+
version: "0.14.0",
|
|
24312
24530
|
license: "MIT",
|
|
24313
24531
|
type: "module",
|
|
24314
24532
|
description: "A Claude Code plugin that replaces the terminal plan-approval prompt with a local web UI for inline review, annotation, and approval.",
|
|
@@ -24344,6 +24562,7 @@ var package_default = {
|
|
|
24344
24562
|
},
|
|
24345
24563
|
devDependencies: {
|
|
24346
24564
|
"@clack/prompts": "^1.7.0",
|
|
24565
|
+
"@codemirror/autocomplete": "^6.20.3",
|
|
24347
24566
|
"@codemirror/commands": "^6.10.3",
|
|
24348
24567
|
"@codemirror/lang-markdown": "^6.5.0",
|
|
24349
24568
|
"@codemirror/language": "^6.12.3",
|
|
@@ -25013,6 +25232,53 @@ function warnInvalidEnvVars(warn) {
|
|
|
25013
25232
|
warn(`${name} invalid; using config/default`);
|
|
25014
25233
|
}
|
|
25015
25234
|
|
|
25235
|
+
// src/config/prefs.ts
|
|
25236
|
+
import { readFile as readFile3, writeFile } from "fs/promises";
|
|
25237
|
+
import { dirname as dirname4 } from "path";
|
|
25238
|
+
var DEFAULT_SET = { valid: ["default"], fallback: "default" };
|
|
25239
|
+
async function readApproveMode(file2 = prefsFile(), log = noopLogger, set2 = DEFAULT_SET) {
|
|
25240
|
+
try {
|
|
25241
|
+
const parsed = JSON.parse(await readFile3(file2, "utf-8"));
|
|
25242
|
+
if (typeof parsed.approveMode === "string" && set2.valid.includes(parsed.approveMode)) {
|
|
25243
|
+
return parsed.approveMode;
|
|
25244
|
+
}
|
|
25245
|
+
log.debug("prefs", "unrecognized approve mode; using default");
|
|
25246
|
+
return set2.fallback;
|
|
25247
|
+
} catch (err) {
|
|
25248
|
+
const absent = err?.code === "ENOENT";
|
|
25249
|
+
log.debug("prefs", absent ? "no prefs file; using default approve mode" : "prefs unreadable; using default approve mode");
|
|
25250
|
+
return set2.fallback;
|
|
25251
|
+
}
|
|
25252
|
+
}
|
|
25253
|
+
async function readUpdatesCheck(file2 = prefsFile()) {
|
|
25254
|
+
const parsed = await readJsonFile(file2);
|
|
25255
|
+
return parsed?.updates?.check !== false;
|
|
25256
|
+
}
|
|
25257
|
+
function createPrefsWriter(file2 = prefsFile()) {
|
|
25258
|
+
let tail = Promise.resolve();
|
|
25259
|
+
return {
|
|
25260
|
+
merge(patch) {
|
|
25261
|
+
const next = tail.then(async () => {
|
|
25262
|
+
ensureStateDir(dirname4(file2));
|
|
25263
|
+
const existing = await readJsonFile(file2) ?? {};
|
|
25264
|
+
await writeFile(file2, JSON.stringify({ ...existing, ...patch }, null, 2), {
|
|
25265
|
+
mode: 384
|
|
25266
|
+
});
|
|
25267
|
+
});
|
|
25268
|
+
tail = next.catch(() => {});
|
|
25269
|
+
return next;
|
|
25270
|
+
}
|
|
25271
|
+
};
|
|
25272
|
+
}
|
|
25273
|
+
async function writeApproveMode(mode, writer, log = noopLogger, set2 = DEFAULT_SET) {
|
|
25274
|
+
if (!set2.valid.includes(mode)) {
|
|
25275
|
+
log.warn("prefs", "ignoring invalid approve mode");
|
|
25276
|
+
return;
|
|
25277
|
+
}
|
|
25278
|
+
await writer.merge({ approveMode: mode });
|
|
25279
|
+
log.debug("prefs", `approve mode saved: ${mode}`);
|
|
25280
|
+
}
|
|
25281
|
+
|
|
25016
25282
|
// src/daemon/diagnostics.ts
|
|
25017
25283
|
function buildDiagnostics(deps) {
|
|
25018
25284
|
return {
|
|
@@ -25165,6 +25431,10 @@ function removeDaemonLock() {
|
|
|
25165
25431
|
unlinkSync2(daemonLock());
|
|
25166
25432
|
} catch {}
|
|
25167
25433
|
}
|
|
25434
|
+
function removeOwnDaemonLock() {
|
|
25435
|
+
if (readDaemonLock()?.pid === process.pid)
|
|
25436
|
+
removeDaemonLock();
|
|
25437
|
+
}
|
|
25168
25438
|
async function retireDaemon(baseUrl, lock, currentStateDir, kill = (pid, sig) => process.kill(pid, sig)) {
|
|
25169
25439
|
try {
|
|
25170
25440
|
const res = await fetch(`${baseUrl}/api/retire`, {
|
|
@@ -25237,34 +25507,6 @@ async function prodEnsureDeps(s) {
|
|
|
25237
25507
|
import { renameSync as renameSync3, unlinkSync as unlinkSync3, writeFileSync as writeFileSync5 } from "fs";
|
|
25238
25508
|
import { dirname as dirname6 } from "path";
|
|
25239
25509
|
|
|
25240
|
-
// src/config/prefs.ts
|
|
25241
|
-
import { readFile as readFile2, writeFile } from "fs/promises";
|
|
25242
|
-
import { dirname as dirname4 } from "path";
|
|
25243
|
-
var DEFAULT_SET = { valid: ["default"], fallback: "default" };
|
|
25244
|
-
async function readApproveMode(file2 = prefsFile(), log = noopLogger, set2 = DEFAULT_SET) {
|
|
25245
|
-
try {
|
|
25246
|
-
const parsed = JSON.parse(await readFile2(file2, "utf-8"));
|
|
25247
|
-
if (typeof parsed.approveMode === "string" && set2.valid.includes(parsed.approveMode)) {
|
|
25248
|
-
return parsed.approveMode;
|
|
25249
|
-
}
|
|
25250
|
-
log.debug("prefs", "unrecognized approve mode; using default");
|
|
25251
|
-
return set2.fallback;
|
|
25252
|
-
} catch (err) {
|
|
25253
|
-
const absent = err?.code === "ENOENT";
|
|
25254
|
-
log.debug("prefs", absent ? "no prefs file; using default approve mode" : "prefs unreadable; using default approve mode");
|
|
25255
|
-
return set2.fallback;
|
|
25256
|
-
}
|
|
25257
|
-
}
|
|
25258
|
-
async function writeApproveMode(mode, file2 = prefsFile(), log = noopLogger, set2 = DEFAULT_SET) {
|
|
25259
|
-
if (!set2.valid.includes(mode)) {
|
|
25260
|
-
log.warn("prefs", "ignoring invalid approve mode");
|
|
25261
|
-
return;
|
|
25262
|
-
}
|
|
25263
|
-
ensureStateDir(dirname4(file2));
|
|
25264
|
-
await writeFile(file2, JSON.stringify({ approveMode: mode }, null, 2), { mode: 384 });
|
|
25265
|
-
log.debug("prefs", `approve mode saved: ${mode}`);
|
|
25266
|
-
}
|
|
25267
|
-
|
|
25268
25510
|
// src/daemon/guards.ts
|
|
25269
25511
|
var LIVE_CLIENT_WINDOW_MS = 120000;
|
|
25270
25512
|
function isClientLive(lastPollAt, now, windowMs) {
|
|
@@ -25273,17 +25515,33 @@ function isClientLive(lastPollAt, now, windowMs) {
|
|
|
25273
25515
|
function isSafeMethod(method) {
|
|
25274
25516
|
return method === "GET" || method === "HEAD";
|
|
25275
25517
|
}
|
|
25276
|
-
|
|
25277
|
-
|
|
25278
|
-
|
|
25279
|
-
|
|
25280
|
-
|
|
25281
|
-
|
|
25282
|
-
|
|
25283
|
-
|
|
25284
|
-
|
|
25285
|
-
}
|
|
25518
|
+
var OWN_HOSTNAMES = new Set(["127.0.0.1", "localhost", VANITY_HOST]);
|
|
25519
|
+
function isOwnAuthority(authority, port) {
|
|
25520
|
+
try {
|
|
25521
|
+
const u = new URL(`http://${authority}`);
|
|
25522
|
+
if (u.href !== `http://${u.host}/`)
|
|
25523
|
+
return false;
|
|
25524
|
+
return OWN_HOSTNAMES.has(u.hostname) && (u.port || "80") === String(port);
|
|
25525
|
+
} catch {
|
|
25526
|
+
return false;
|
|
25286
25527
|
}
|
|
25528
|
+
}
|
|
25529
|
+
function isForeignHost(req, port) {
|
|
25530
|
+
const host = req.headers.get("host");
|
|
25531
|
+
return host === null || !isOwnAuthority(host, port);
|
|
25532
|
+
}
|
|
25533
|
+
function isOwnOrigin(origin, port) {
|
|
25534
|
+
try {
|
|
25535
|
+
const u = new URL(origin);
|
|
25536
|
+
return u.protocol === "http:" && isOwnAuthority(u.host, port);
|
|
25537
|
+
} catch {
|
|
25538
|
+
return false;
|
|
25539
|
+
}
|
|
25540
|
+
}
|
|
25541
|
+
function isCrossOrigin(req, port) {
|
|
25542
|
+
const origin = req.headers.get("origin");
|
|
25543
|
+
if (origin && !isOwnOrigin(origin, port))
|
|
25544
|
+
return true;
|
|
25287
25545
|
const site = req.headers.get("sec-fetch-site");
|
|
25288
25546
|
if (site && site !== "same-origin" && site !== "none")
|
|
25289
25547
|
return true;
|
|
@@ -25301,12 +25559,14 @@ var PlanInputSchema = exports_external.object({
|
|
|
25301
25559
|
}).catch({});
|
|
25302
25560
|
var MAX_FILE_REFS = 1000;
|
|
25303
25561
|
var FileRefsBodySchema = exports_external.object({ paths: exports_external.array(exports_external.string()).catch([]) }).catch({ paths: [] });
|
|
25562
|
+
var FileSearchBodySchema = exports_external.object({ query: exports_external.string().catch("") }).catch({ query: "" });
|
|
25304
25563
|
var BehaviorSchema = exports_external.enum(["allow", "deny"]);
|
|
25305
25564
|
var ResolveBodySchema = exports_external.object({
|
|
25306
25565
|
behavior: BehaviorSchema.catch("allow"),
|
|
25307
25566
|
feedback: exports_external.string().optional(),
|
|
25308
25567
|
acceptMode: exports_external.string().optional().catch(undefined)
|
|
25309
25568
|
}).catch({ behavior: "allow" });
|
|
25569
|
+
var PrefsPatchSchema = exports_external.object({ updates: exports_external.object({ check: exports_external.boolean() }).strict().optional() }).strict();
|
|
25310
25570
|
var LineAnnotationSchema = exports_external.object({
|
|
25311
25571
|
id: exports_external.string(),
|
|
25312
25572
|
startLine: exports_external.number().int().min(1),
|
|
@@ -25389,13 +25649,13 @@ function markPaneRead(pane, deps = {}) {
|
|
|
25389
25649
|
}
|
|
25390
25650
|
|
|
25391
25651
|
// src/plan/directory.ts
|
|
25392
|
-
import { readdir as
|
|
25393
|
-
import { join as
|
|
25652
|
+
import { readdir as readdir4 } from "fs/promises";
|
|
25653
|
+
import { join as join10, relative as relative3, sep as sep4 } from "path";
|
|
25394
25654
|
|
|
25395
25655
|
// src/plan/excerpt.ts
|
|
25396
25656
|
import { readFileSync as readFileSync8 } from "fs";
|
|
25397
|
-
import { readdir, realpath, stat } from "fs/promises";
|
|
25398
|
-
import { extname, isAbsolute, join as
|
|
25657
|
+
import { readdir as readdir3, realpath as realpath2, stat as stat2 } from "fs/promises";
|
|
25658
|
+
import { extname, isAbsolute, join as join9, relative as relative2, resolve, sep as sep3 } from "path";
|
|
25399
25659
|
var EXCERPT_HEAD_LINES = 60;
|
|
25400
25660
|
var MAX_EXCERPT_BYTES = 10 * 1024 * 1024;
|
|
25401
25661
|
var MAX_SCAN_ENTRIES = 5000;
|
|
@@ -25451,16 +25711,16 @@ function languageForPath(path) {
|
|
|
25451
25711
|
return EXT_LANGUAGE[extname(path).toLowerCase()] ?? "text";
|
|
25452
25712
|
}
|
|
25453
25713
|
function safeRealpath(path) {
|
|
25454
|
-
return
|
|
25714
|
+
return realpath2(path).catch(() => null);
|
|
25455
25715
|
}
|
|
25456
25716
|
function safeStat(path) {
|
|
25457
|
-
return
|
|
25717
|
+
return stat2(path).catch(() => null);
|
|
25458
25718
|
}
|
|
25459
25719
|
async function contained(cwdReal, abs) {
|
|
25460
25720
|
const real = await safeRealpath(abs);
|
|
25461
25721
|
if (real === null)
|
|
25462
25722
|
return null;
|
|
25463
|
-
if (real !== cwdReal && !real.startsWith(cwdReal +
|
|
25723
|
+
if (real !== cwdReal && !real.startsWith(cwdReal + sep3))
|
|
25464
25724
|
return null;
|
|
25465
25725
|
const stats = await safeStat(real);
|
|
25466
25726
|
if (stats === null)
|
|
@@ -25476,7 +25736,7 @@ async function basenameSearch(cwdReal, name) {
|
|
|
25476
25736
|
const currentDir = queue.shift();
|
|
25477
25737
|
let entries;
|
|
25478
25738
|
try {
|
|
25479
|
-
entries = await
|
|
25739
|
+
entries = await readdir3(currentDir, { withFileTypes: true });
|
|
25480
25740
|
} catch {
|
|
25481
25741
|
continue;
|
|
25482
25742
|
}
|
|
@@ -25485,9 +25745,9 @@ async function basenameSearch(cwdReal, name) {
|
|
|
25485
25745
|
return null;
|
|
25486
25746
|
if (entry.isFile()) {
|
|
25487
25747
|
if (entry.name === name)
|
|
25488
|
-
return
|
|
25748
|
+
return join9(currentDir, entry.name);
|
|
25489
25749
|
} else if (entry.isDirectory() && !SKIP_DIRS.has(entry.name) && !entry.name.startsWith(".")) {
|
|
25490
|
-
queue.push(
|
|
25750
|
+
queue.push(join9(currentDir, entry.name));
|
|
25491
25751
|
}
|
|
25492
25752
|
}
|
|
25493
25753
|
}
|
|
@@ -25599,13 +25859,13 @@ async function listDirectory(cwd, root, path) {
|
|
|
25599
25859
|
if (target === null || target.kind !== "directory")
|
|
25600
25860
|
return null;
|
|
25601
25861
|
const rel = relative3(rootHit.path, target.path);
|
|
25602
|
-
if (rel === ".." || rel.startsWith(`..${
|
|
25862
|
+
if (rel === ".." || rel.startsWith(`..${sep4}`))
|
|
25603
25863
|
return null;
|
|
25604
|
-
if (rel !== "" && rel.split(
|
|
25864
|
+
if (rel !== "" && rel.split(sep4).length > MAX_DIR_DEPTH)
|
|
25605
25865
|
return null;
|
|
25606
25866
|
let dirents;
|
|
25607
25867
|
try {
|
|
25608
|
-
dirents = await
|
|
25868
|
+
dirents = await readdir4(target.path, { withFileTypes: true });
|
|
25609
25869
|
} catch {
|
|
25610
25870
|
return null;
|
|
25611
25871
|
}
|
|
@@ -25619,7 +25879,7 @@ async function listDirectory(cwd, root, path) {
|
|
|
25619
25879
|
else if (d.isSymbolicLink())
|
|
25620
25880
|
links.push(d);
|
|
25621
25881
|
}
|
|
25622
|
-
const targets = await Promise.all(links.map((d) => resolveInCwd(cwd,
|
|
25882
|
+
const targets = await Promise.all(links.map((d) => resolveInCwd(cwd, join10(target.path, d.name))));
|
|
25623
25883
|
targets.forEach((hit, i) => {
|
|
25624
25884
|
const link = links[i];
|
|
25625
25885
|
if (hit !== null && link !== undefined)
|
|
@@ -25634,6 +25894,78 @@ async function listDirectory(cwd, root, path) {
|
|
|
25634
25894
|
};
|
|
25635
25895
|
}
|
|
25636
25896
|
|
|
25897
|
+
// src/plan/file-search.ts
|
|
25898
|
+
import { readdir as readdir5 } from "fs/promises";
|
|
25899
|
+
import { isAbsolute as isAbsolute2, join as join11 } from "path";
|
|
25900
|
+
var SEARCH_BUDGET = { dirents: 20000, results: 50 };
|
|
25901
|
+
var MAX_SEARCH_QUERY_CHARS = 128;
|
|
25902
|
+
function subsequence(haystack, needle) {
|
|
25903
|
+
let i = 0;
|
|
25904
|
+
for (let h = 0;h < haystack.length && i < needle.length; h++) {
|
|
25905
|
+
if (haystack[h] === needle[i])
|
|
25906
|
+
i++;
|
|
25907
|
+
}
|
|
25908
|
+
return i === needle.length;
|
|
25909
|
+
}
|
|
25910
|
+
function relPath(dir, name) {
|
|
25911
|
+
return dir === "" ? name : `${dir}/${name}`;
|
|
25912
|
+
}
|
|
25913
|
+
function partition(dirents, allowance) {
|
|
25914
|
+
const files = [];
|
|
25915
|
+
const dirs = [];
|
|
25916
|
+
let scanned = 0;
|
|
25917
|
+
for (const entry of dirents) {
|
|
25918
|
+
if (scanned >= allowance)
|
|
25919
|
+
return { files, dirs, scanned, cut: true };
|
|
25920
|
+
scanned++;
|
|
25921
|
+
if (entry.name === ".git")
|
|
25922
|
+
continue;
|
|
25923
|
+
if (entry.isFile())
|
|
25924
|
+
files.push(entry.name);
|
|
25925
|
+
else if (entry.isDirectory() && !SKIP_DIRS.has(entry.name) && !entry.name.startsWith(".")) {
|
|
25926
|
+
dirs.push(entry.name);
|
|
25927
|
+
}
|
|
25928
|
+
}
|
|
25929
|
+
files.sort();
|
|
25930
|
+
dirs.sort();
|
|
25931
|
+
return { files, dirs, scanned, cut: false };
|
|
25932
|
+
}
|
|
25933
|
+
async function searchFiles(cwd, query, budget = SEARCH_BUDGET) {
|
|
25934
|
+
if (cwd === "" || !isAbsolute2(cwd))
|
|
25935
|
+
return null;
|
|
25936
|
+
const cwdReal = await safeRealpath(cwd);
|
|
25937
|
+
if (cwdReal === null)
|
|
25938
|
+
return null;
|
|
25939
|
+
const needle = query.slice(0, MAX_SEARCH_QUERY_CHARS).toLowerCase();
|
|
25940
|
+
const paths = [];
|
|
25941
|
+
const queue = [""];
|
|
25942
|
+
let scanned = 0;
|
|
25943
|
+
while (queue.length > 0) {
|
|
25944
|
+
const rel = queue.shift();
|
|
25945
|
+
let dirents;
|
|
25946
|
+
try {
|
|
25947
|
+
dirents = await readdir5(join11(cwdReal, rel), { withFileTypes: true });
|
|
25948
|
+
} catch {
|
|
25949
|
+
continue;
|
|
25950
|
+
}
|
|
25951
|
+
const level = partition(dirents, budget.dirents - scanned);
|
|
25952
|
+
scanned += level.scanned;
|
|
25953
|
+
if (level.cut)
|
|
25954
|
+
return { paths, stoppedAt: "scan" };
|
|
25955
|
+
for (const name of level.files) {
|
|
25956
|
+
const path = relPath(rel, name);
|
|
25957
|
+
if (!subsequence(path.toLowerCase(), needle))
|
|
25958
|
+
continue;
|
|
25959
|
+
if (paths.length === budget.results)
|
|
25960
|
+
return { paths, stoppedAt: "results" };
|
|
25961
|
+
paths.push(path);
|
|
25962
|
+
}
|
|
25963
|
+
for (const name of level.dirs)
|
|
25964
|
+
queue.push(relPath(rel, name));
|
|
25965
|
+
}
|
|
25966
|
+
return { paths, stoppedAt: null };
|
|
25967
|
+
}
|
|
25968
|
+
|
|
25637
25969
|
// src/review/decisions.ts
|
|
25638
25970
|
function createDecisions(log = noopLogger) {
|
|
25639
25971
|
const pending = new Map;
|
|
@@ -25710,7 +26042,7 @@ import { createHash as createHash2 } from "crypto";
|
|
|
25710
26042
|
import { chmodSync as chmodSync3, existsSync as existsSync6, mkdirSync as mkdirSync2, renameSync as renameSync2, writeFileSync as writeFileSync4 } from "fs";
|
|
25711
26043
|
import { mkdtemp, rm } from "fs/promises";
|
|
25712
26044
|
import { tmpdir } from "os";
|
|
25713
|
-
import { dirname as dirname5, join as
|
|
26045
|
+
import { dirname as dirname5, join as join12 } from "path";
|
|
25714
26046
|
var RUMDL_VERSION = "0.2.54";
|
|
25715
26047
|
var ASSETS = {
|
|
25716
26048
|
"darwin-arm64": {
|
|
@@ -25753,14 +26085,14 @@ async function downloadRumdl(binPath, asset, fetchImpl = fetch) {
|
|
|
25753
26085
|
if (actual !== asset.sha256) {
|
|
25754
26086
|
throw new Error(`rumdl: checksum mismatch for ${asset.url} (expected ${asset.sha256}, got ${actual})`);
|
|
25755
26087
|
}
|
|
25756
|
-
const work = await mkdtemp(
|
|
26088
|
+
const work = await mkdtemp(join12(tmpdir(), "caret-rumdl-"));
|
|
25757
26089
|
try {
|
|
25758
|
-
const archive =
|
|
26090
|
+
const archive = join12(work, "rumdl.tar.gz");
|
|
25759
26091
|
await Bun.write(archive, bytes);
|
|
25760
26092
|
const tar = Bun.spawn(["tar", "-xzf", archive, "-C", work], { stderr: "pipe" });
|
|
25761
26093
|
if (await tar.exited !== 0)
|
|
25762
26094
|
throw new Error(`rumdl: failed to extract ${asset.url}`);
|
|
25763
|
-
const extracted =
|
|
26095
|
+
const extracted = join12(work, "rumdl");
|
|
25764
26096
|
if (!existsSync6(extracted))
|
|
25765
26097
|
throw new Error(`rumdl: binary not found in ${asset.url}`);
|
|
25766
26098
|
mkdirSync2(dirname5(binPath), { recursive: true });
|
|
@@ -25992,6 +26324,7 @@ var PLACEHOLDER_HTML = `<!doctype html><html lang="en"><head><meta charset="utf-
|
|
|
25992
26324
|
var INDEX_CACHE_CONTROL = "no-cache";
|
|
25993
26325
|
var ASSET_CACHE_CONTROL = "public, max-age=31536000, immutable";
|
|
25994
26326
|
var INDEX_PATH = "/index.html";
|
|
26327
|
+
var FILE_REF_BATCH = 64;
|
|
25995
26328
|
function resolveOptions(opts) {
|
|
25996
26329
|
return {
|
|
25997
26330
|
store: opts.store,
|
|
@@ -26008,12 +26341,16 @@ function resolveOptions(opts) {
|
|
|
26008
26341
|
instanceId: opts.instanceId,
|
|
26009
26342
|
approveVariants: opts.approveVariants,
|
|
26010
26343
|
source: opts.source,
|
|
26344
|
+
listSkills: opts.listSkills,
|
|
26345
|
+
readSkillDescription: opts.readSkillDescription,
|
|
26011
26346
|
diagnostics: opts.diagnostics,
|
|
26347
|
+
updateReport: opts.updateReport,
|
|
26348
|
+
onUpdatesEnabled: opts.onUpdatesEnabled,
|
|
26012
26349
|
markPaneRead: opts.markPaneRead ?? ((pane) => markPaneRead(pane, { log: opts.log })),
|
|
26013
26350
|
log: opts.log ?? noopLogger
|
|
26014
26351
|
};
|
|
26015
26352
|
}
|
|
26016
|
-
var ID_ROUTE_RE = /^\/api\/reviews\/([^/]+)(\/decision|\/resolve|\/draft|\/expire|\/seen|\/file-refs|\/file|\/dir)?$/;
|
|
26353
|
+
var ID_ROUTE_RE = /^\/api\/reviews\/([^/]+)(\/decision|\/resolve|\/draft|\/expire|\/seen|\/file-refs|\/file-search|\/file|\/dir|\/skills|\/skill-description)?$/;
|
|
26017
26354
|
function matchIdRoute(path) {
|
|
26018
26355
|
const m = path.match(ID_ROUTE_RE);
|
|
26019
26356
|
if (!m)
|
|
@@ -26026,6 +26363,7 @@ function createServer(opts) {
|
|
|
26026
26363
|
const { buildId, commit, stateDir: stateDir2, instanceId, approveVariants, source, lockPath } = cfg;
|
|
26027
26364
|
const { awaitDecision, resolveDecision, clearDecision, openDecisionCount } = createDecisions(log);
|
|
26028
26365
|
const approveModeSet = approveVariants && approveVariants.length > 0 ? { valid: approveVariants.map((v) => v.id), fallback: approveVariants[0]?.id ?? "default" } : { valid: ["default"], fallback: "default" };
|
|
26366
|
+
const prefsWriter = createPrefsWriter(prefsPath);
|
|
26029
26367
|
function raceDecision(id, ms) {
|
|
26030
26368
|
return new Promise((resolve2) => {
|
|
26031
26369
|
const t = setTimeout(() => resolve2(null), ms);
|
|
@@ -26094,6 +26432,11 @@ function createServer(opts) {
|
|
|
26094
26432
|
return notFound();
|
|
26095
26433
|
return Response.json(cfg.diagnostics());
|
|
26096
26434
|
}
|
|
26435
|
+
async function handleUpdate() {
|
|
26436
|
+
if (!cfg.updateReport)
|
|
26437
|
+
return notFound();
|
|
26438
|
+
return Response.json(await cfg.updateReport());
|
|
26439
|
+
}
|
|
26097
26440
|
function handleRetire() {
|
|
26098
26441
|
log.info("retire", "retire requested");
|
|
26099
26442
|
setTimeout(() => {
|
|
@@ -26167,7 +26510,23 @@ function createServer(opts) {
|
|
|
26167
26510
|
return new Response(null, { status: 204 });
|
|
26168
26511
|
}
|
|
26169
26512
|
async function handlePrefs() {
|
|
26170
|
-
|
|
26513
|
+
const body = {
|
|
26514
|
+
approveMode: await readApproveMode(prefsPath, log, approveModeSet)
|
|
26515
|
+
};
|
|
26516
|
+
return Response.json(body);
|
|
26517
|
+
}
|
|
26518
|
+
async function handleSetPrefs(req) {
|
|
26519
|
+
const parsed = PrefsPatchSchema.safeParse(await req.json().catch(() => null));
|
|
26520
|
+
if (!parsed.success) {
|
|
26521
|
+
const error51 = parsed.error.issues[0]?.message ?? "invalid prefs patch";
|
|
26522
|
+
log.warn("prefs", "prefs patch rejected", { reason: error51 });
|
|
26523
|
+
return Response.json({ error: error51 }, { status: 400 });
|
|
26524
|
+
}
|
|
26525
|
+
await prefsWriter.merge(parsed.data);
|
|
26526
|
+
log.debug("prefs", "prefs saved");
|
|
26527
|
+
if (parsed.data.updates?.check === true)
|
|
26528
|
+
cfg.onUpdatesEnabled?.();
|
|
26529
|
+
return Response.json({ ok: true });
|
|
26171
26530
|
}
|
|
26172
26531
|
function handleGetReview(id) {
|
|
26173
26532
|
const r = store.get(id);
|
|
@@ -26187,10 +26546,13 @@ function createServer(opts) {
|
|
|
26187
26546
|
if (unique.push(p) === MAX_FILE_REFS)
|
|
26188
26547
|
break;
|
|
26189
26548
|
}
|
|
26190
|
-
const entries =
|
|
26191
|
-
|
|
26192
|
-
|
|
26193
|
-
|
|
26549
|
+
const entries = [];
|
|
26550
|
+
for (let i = 0;i < unique.length; i += FILE_REF_BATCH) {
|
|
26551
|
+
entries.push(...await Promise.all(unique.slice(i, i + FILE_REF_BATCH).map(async (p) => {
|
|
26552
|
+
const hit = await resolveInCwd(r.cwd, p);
|
|
26553
|
+
return hit === null ? null : [p, hit.kind];
|
|
26554
|
+
})));
|
|
26555
|
+
}
|
|
26194
26556
|
const resolved = Object.fromEntries(entries.filter((e) => e !== null));
|
|
26195
26557
|
log.debug("request", `file-refs resolved: ${Object.keys(resolved).length}/${unique.length}`, {
|
|
26196
26558
|
reviewId: id,
|
|
@@ -26233,6 +26595,45 @@ function createServer(opts) {
|
|
|
26233
26595
|
});
|
|
26234
26596
|
return Response.json(listing);
|
|
26235
26597
|
}
|
|
26598
|
+
async function handleSkills(id) {
|
|
26599
|
+
if (!cfg.listSkills)
|
|
26600
|
+
return notFound();
|
|
26601
|
+
const r = store.get(id);
|
|
26602
|
+
if (!r)
|
|
26603
|
+
return notFound();
|
|
26604
|
+
const skills = await cfg.listSkills(r.cwd);
|
|
26605
|
+
log.debug("request", "skills listed", { reviewId: id, count: skills.length });
|
|
26606
|
+
return Response.json(skills);
|
|
26607
|
+
}
|
|
26608
|
+
async function handleSkillDescription(req, id) {
|
|
26609
|
+
if (!cfg.readSkillDescription)
|
|
26610
|
+
return notFound();
|
|
26611
|
+
const r = store.get(id);
|
|
26612
|
+
if (!r)
|
|
26613
|
+
return notFound();
|
|
26614
|
+
const params = new URL(req.url).searchParams;
|
|
26615
|
+
const description = await cfg.readSkillDescription(r.cwd, {
|
|
26616
|
+
name: params.get("name") ?? "",
|
|
26617
|
+
origin: params.get("origin") ?? ""
|
|
26618
|
+
});
|
|
26619
|
+
log.debug("request", "skill description read", { reviewId: id, found: description !== null });
|
|
26620
|
+
return Response.json({ description });
|
|
26621
|
+
}
|
|
26622
|
+
async function handleFileSearch(req, id) {
|
|
26623
|
+
const r = store.get(id);
|
|
26624
|
+
if (!r)
|
|
26625
|
+
return notFound();
|
|
26626
|
+
const { query } = await parseBody(req, FileSearchBodySchema);
|
|
26627
|
+
const result = await searchFiles(r.cwd, query);
|
|
26628
|
+
if (result === null)
|
|
26629
|
+
return notFound();
|
|
26630
|
+
log.debug("request", "file search answered", {
|
|
26631
|
+
reviewId: id,
|
|
26632
|
+
returned: result.paths.length,
|
|
26633
|
+
stoppedAt: result.stoppedAt
|
|
26634
|
+
});
|
|
26635
|
+
return Response.json(result);
|
|
26636
|
+
}
|
|
26236
26637
|
async function handleDecision(id) {
|
|
26237
26638
|
const inMem = store.get(id);
|
|
26238
26639
|
if (inMem?.decision) {
|
|
@@ -26300,7 +26701,7 @@ function createServer(opts) {
|
|
|
26300
26701
|
store.bumpEpoch(existing.sessionId);
|
|
26301
26702
|
await store.remove(id);
|
|
26302
26703
|
if (decision.acceptMode !== undefined && approveModeSet.valid.includes(decision.acceptMode)) {
|
|
26303
|
-
writeApproveMode(decision.acceptMode,
|
|
26704
|
+
writeApproveMode(decision.acceptMode, prefsWriter, log, approveModeSet).catch(() => {
|
|
26304
26705
|
log.warn("prefs", "approve mode write failed");
|
|
26305
26706
|
});
|
|
26306
26707
|
}
|
|
@@ -26340,6 +26741,8 @@ function createServer(opts) {
|
|
|
26340
26741
|
return handleHealth();
|
|
26341
26742
|
if (method === "GET" && path === "/api/diagnostics")
|
|
26342
26743
|
return handleDiagnostics();
|
|
26744
|
+
if (method === "GET" && path === "/api/update")
|
|
26745
|
+
return handleUpdate();
|
|
26343
26746
|
if (method === "POST" && path === "/api/retire")
|
|
26344
26747
|
return handleRetire();
|
|
26345
26748
|
if (method === "GET" && (path === "/" || path === INDEX_PATH))
|
|
@@ -26354,6 +26757,8 @@ function createServer(opts) {
|
|
|
26354
26757
|
return handleListReviews();
|
|
26355
26758
|
if (method === "GET" && path === "/api/prefs")
|
|
26356
26759
|
return handlePrefs();
|
|
26760
|
+
if (method === "POST" && path === "/api/prefs")
|
|
26761
|
+
return handleSetPrefs(req);
|
|
26357
26762
|
const route = matchIdRoute(path);
|
|
26358
26763
|
if (route) {
|
|
26359
26764
|
const { id, sub } = route;
|
|
@@ -26363,8 +26768,15 @@ function createServer(opts) {
|
|
|
26363
26768
|
return handleFileExcerpt(req, id);
|
|
26364
26769
|
if (method === "GET" && sub === "/dir")
|
|
26365
26770
|
return handleDirListing(req, id);
|
|
26771
|
+
if (method === "GET" && sub === "/skills")
|
|
26772
|
+
return handleSkills(id);
|
|
26773
|
+
if (method === "GET" && sub === "/skill-description") {
|
|
26774
|
+
return handleSkillDescription(req, id);
|
|
26775
|
+
}
|
|
26366
26776
|
if (method === "POST" && sub === "/file-refs")
|
|
26367
26777
|
return handleFileRefs(req, id);
|
|
26778
|
+
if (method === "POST" && sub === "/file-search")
|
|
26779
|
+
return handleFileSearch(req, id);
|
|
26368
26780
|
if (method === "GET" && sub === "/decision")
|
|
26369
26781
|
return handleDecision(id);
|
|
26370
26782
|
if (method === "PUT" && sub === "/draft")
|
|
@@ -26383,14 +26795,18 @@ function createServer(opts) {
|
|
|
26383
26795
|
}
|
|
26384
26796
|
return notFound();
|
|
26385
26797
|
}
|
|
26386
|
-
async function handle(req) {
|
|
26798
|
+
async function handle(req, self) {
|
|
26387
26799
|
inFlight++;
|
|
26388
26800
|
cancelIdle();
|
|
26389
26801
|
try {
|
|
26802
|
+
const port = self.port ?? -1;
|
|
26803
|
+
if (isForeignHost(req, port)) {
|
|
26804
|
+
return new Response("host not recognized", { status: 403 });
|
|
26805
|
+
}
|
|
26390
26806
|
const url2 = new URL(req.url);
|
|
26391
26807
|
const path = url2.pathname;
|
|
26392
26808
|
const method = req.method;
|
|
26393
|
-
if (!isSafeMethod(method) && isCrossOrigin(req)) {
|
|
26809
|
+
if (!isSafeMethod(method) && isCrossOrigin(req, port)) {
|
|
26394
26810
|
return new Response("cross-origin request blocked", { status: 403 });
|
|
26395
26811
|
}
|
|
26396
26812
|
return await dispatch(req, method, path);
|
|
@@ -26455,9 +26871,153 @@ function createServer(opts) {
|
|
|
26455
26871
|
return { port: server.port ?? 0, stop };
|
|
26456
26872
|
}
|
|
26457
26873
|
|
|
26874
|
+
// src/daemon/update-check.ts
|
|
26875
|
+
import { writeFileSync as writeFileSync6 } from "fs";
|
|
26876
|
+
import { dirname as dirname7 } from "path";
|
|
26877
|
+
var CHECK_INTERVAL_MS = 24 * 60 * 60 * 1000;
|
|
26878
|
+
var REFRESH_COMMAND = "bunx --no-cache @macintacos/caret@latest install --refresh";
|
|
26879
|
+
var REBUILD_COMMAND = "mise run build --install";
|
|
26880
|
+
var NEEDS_COMPARE = "could not compare this build against trunk";
|
|
26881
|
+
var NEVER_CHECKED = {
|
|
26882
|
+
kind: "unknown",
|
|
26883
|
+
reason: "no update check has run for this build yet"
|
|
26884
|
+
};
|
|
26885
|
+
var DISABLED = { kind: "unavailable", reason: "disabled" };
|
|
26886
|
+
function updateStatusFor(facts) {
|
|
26887
|
+
if (facts.kind === "dev")
|
|
26888
|
+
return { kind: "unavailable", reason: "dev" };
|
|
26889
|
+
if (facts.kind === "bundle") {
|
|
26890
|
+
if (facts.npmLatest === null)
|
|
26891
|
+
return unknown2("could not reach npm for the published version");
|
|
26892
|
+
return isNewer(facts.npmLatest, facts.version) ? { kind: "behind-release", available: facts.npmLatest, command: REFRESH_COMMAND } : { kind: "current" };
|
|
26893
|
+
}
|
|
26894
|
+
if (facts.release === null)
|
|
26895
|
+
return unknown2("could not reach GitHub for the newest release");
|
|
26896
|
+
if (isNewer(facts.release, facts.version)) {
|
|
26897
|
+
return { kind: "behind-release", available: facts.release, command: REFRESH_COMMAND };
|
|
26898
|
+
}
|
|
26899
|
+
if (facts.commit === "unknown")
|
|
26900
|
+
return { kind: "current" };
|
|
26901
|
+
if (facts.aheadBy === null)
|
|
26902
|
+
return unknown2(NEEDS_COMPARE);
|
|
26903
|
+
return facts.aheadBy > 0 ? { kind: "behind-commit", aheadBy: facts.aheadBy, command: REBUILD_COMMAND } : { kind: "current" };
|
|
26904
|
+
}
|
|
26905
|
+
function updateReportFor(identity, status, checkEnabled) {
|
|
26906
|
+
const devBuild = status.kind === "unavailable" && status.reason === "dev";
|
|
26907
|
+
return { ...identity, checkEnabled, status: checkEnabled || devBuild ? status : DISABLED };
|
|
26908
|
+
}
|
|
26909
|
+
function readCachedStatus(cache, version2, commit) {
|
|
26910
|
+
const rec = cache.read();
|
|
26911
|
+
if (!rec || rec.version !== version2 || rec.commit !== commit)
|
|
26912
|
+
return NEVER_CHECKED;
|
|
26913
|
+
return rec.status;
|
|
26914
|
+
}
|
|
26915
|
+
async function runUpdateCheck(deps) {
|
|
26916
|
+
if (deps.kind === "dev")
|
|
26917
|
+
return { kind: "unavailable", reason: "dev" };
|
|
26918
|
+
try {
|
|
26919
|
+
if (!await deps.enabled())
|
|
26920
|
+
return null;
|
|
26921
|
+
const now = deps.now();
|
|
26922
|
+
const prev = deps.cache.read();
|
|
26923
|
+
const sameBuild = prev?.version === deps.version && prev?.commit === deps.commit;
|
|
26924
|
+
if (prev && sameBuild && Math.abs(now - prev.checkedAt) < CHECK_INTERVAL_MS)
|
|
26925
|
+
return null;
|
|
26926
|
+
const record2 = (status2) => {
|
|
26927
|
+
deps.cache.write({ checkedAt: now, version: deps.version, commit: deps.commit, status: status2 });
|
|
26928
|
+
};
|
|
26929
|
+
record2(prev && sameBuild ? prev.status : NEVER_CHECKED);
|
|
26930
|
+
const status = await gather(deps);
|
|
26931
|
+
record2(status);
|
|
26932
|
+
deps.log.info("update", `update check: ${status.kind}`, status.kind === "unknown" ? { detail: status.reason } : undefined);
|
|
26933
|
+
return status;
|
|
26934
|
+
} catch (err) {
|
|
26935
|
+
deps.log.warn("update", "update check failed", { detail: errorMessage(err) });
|
|
26936
|
+
return unknown2("the update check failed");
|
|
26937
|
+
}
|
|
26938
|
+
}
|
|
26939
|
+
function fileUpdateCache(path) {
|
|
26940
|
+
return {
|
|
26941
|
+
read: () => asRecord(readJsonFileSync(path)),
|
|
26942
|
+
write: (entry) => {
|
|
26943
|
+
try {
|
|
26944
|
+
ensureStateDir(dirname7(path));
|
|
26945
|
+
writeFileSync6(path, JSON.stringify(entry, null, 2), { mode: 384 });
|
|
26946
|
+
} catch {}
|
|
26947
|
+
}
|
|
26948
|
+
};
|
|
26949
|
+
}
|
|
26950
|
+
async function gather(deps) {
|
|
26951
|
+
const base = { kind: deps.kind, version: deps.version, commit: deps.commit };
|
|
26952
|
+
if (deps.kind === "bundle") {
|
|
26953
|
+
return updateStatusFor({
|
|
26954
|
+
...base,
|
|
26955
|
+
npmLatest: await deps.npmLatest(),
|
|
26956
|
+
release: null,
|
|
26957
|
+
aheadBy: null
|
|
26958
|
+
});
|
|
26959
|
+
}
|
|
26960
|
+
const release = await deps.release();
|
|
26961
|
+
const first = updateStatusFor({ ...base, npmLatest: null, release, aheadBy: null });
|
|
26962
|
+
if (first.kind !== "unknown" || first.reason !== NEEDS_COMPARE)
|
|
26963
|
+
return first;
|
|
26964
|
+
const aheadBy = await deps.aheadBy(deps.commit);
|
|
26965
|
+
return updateStatusFor({ ...base, npmLatest: null, release, aheadBy });
|
|
26966
|
+
}
|
|
26967
|
+
function asRecord(value) {
|
|
26968
|
+
const r = value;
|
|
26969
|
+
if (typeof r?.checkedAt !== "number")
|
|
26970
|
+
return null;
|
|
26971
|
+
if (typeof r.version !== "string" || typeof r.commit !== "string")
|
|
26972
|
+
return null;
|
|
26973
|
+
if (typeof r.status?.kind !== "string")
|
|
26974
|
+
return null;
|
|
26975
|
+
return r;
|
|
26976
|
+
}
|
|
26977
|
+
function unknown2(reason) {
|
|
26978
|
+
return { kind: "unknown", reason };
|
|
26979
|
+
}
|
|
26980
|
+
|
|
26981
|
+
// src/lib/upstream.ts
|
|
26982
|
+
var NPM_LATEST_URL = `https://registry.npmjs.org/${package_default.name}/latest`;
|
|
26983
|
+
var LATEST_RELEASE_URL = "https://api.github.com/repos/macintacos/caret/releases/latest";
|
|
26984
|
+
var COMPARE_URL = "https://api.github.com/repos/macintacos/caret/compare";
|
|
26985
|
+
var UPSTREAM_TIMEOUT_MS = 3000;
|
|
26986
|
+
var GITHUB_HEADERS = { "user-agent": "caret" };
|
|
26987
|
+
async function readJson(url2, fetchImpl, headers) {
|
|
26988
|
+
try {
|
|
26989
|
+
const res = await fetchImpl(url2, {
|
|
26990
|
+
signal: AbortSignal.timeout(UPSTREAM_TIMEOUT_MS),
|
|
26991
|
+
...headers ? { headers } : {}
|
|
26992
|
+
});
|
|
26993
|
+
return res.ok ? await res.json() : null;
|
|
26994
|
+
} catch {
|
|
26995
|
+
return null;
|
|
26996
|
+
}
|
|
26997
|
+
}
|
|
26998
|
+
async function publishedCaretVersion(fetchImpl = fetch) {
|
|
26999
|
+
const body = await readJson(NPM_LATEST_URL, fetchImpl);
|
|
27000
|
+
const v = body?.version;
|
|
27001
|
+
return typeof v === "string" && v.length > 0 ? v : null;
|
|
27002
|
+
}
|
|
27003
|
+
async function latestReleaseTag(fetchImpl = fetch) {
|
|
27004
|
+
const body = await readJson(LATEST_RELEASE_URL, fetchImpl, GITHUB_HEADERS);
|
|
27005
|
+
const tag = body?.tag_name;
|
|
27006
|
+
if (typeof tag !== "string" || tag.length === 0)
|
|
27007
|
+
return null;
|
|
27008
|
+
const stripped = tag.replace(/^v/, "");
|
|
27009
|
+
return stripped.length > 0 ? stripped : null;
|
|
27010
|
+
}
|
|
27011
|
+
async function commitsAheadOfTrunk(commit, fetchImpl = fetch) {
|
|
27012
|
+
const url2 = `${COMPARE_URL}/${encodeURIComponent(commit)}...trunk`;
|
|
27013
|
+
const body = await readJson(url2, fetchImpl, GITHUB_HEADERS);
|
|
27014
|
+
const ahead = body?.ahead_by;
|
|
27015
|
+
return typeof ahead === "number" && Number.isFinite(ahead) ? ahead : null;
|
|
27016
|
+
}
|
|
27017
|
+
|
|
26458
27018
|
// src/review/store.ts
|
|
26459
|
-
import { readdir as
|
|
26460
|
-
import { join as
|
|
27019
|
+
import { readdir as readdir6, readFile as readFile4, writeFile as writeFile2 } from "fs/promises";
|
|
27020
|
+
import { join as join13 } from "path";
|
|
26461
27021
|
function createStore(dir, log = noopLogger) {
|
|
26462
27022
|
const reviews = new Map;
|
|
26463
27023
|
const epochs = new Map;
|
|
@@ -26466,7 +27026,7 @@ function createStore(dir, log = noopLogger) {
|
|
|
26466
27026
|
const prev = writeChains.get(review.id) ?? Promise.resolve();
|
|
26467
27027
|
const next = prev.catch(() => {}).then(async () => {
|
|
26468
27028
|
ensureStateDir(dir);
|
|
26469
|
-
await writeFile2(
|
|
27029
|
+
await writeFile2(join13(dir, `${review.id}.json`), JSON.stringify(review, null, 2), {
|
|
26470
27030
|
mode: 384
|
|
26471
27031
|
});
|
|
26472
27032
|
log.debug("store", `review persisted: ${shortId(review.id)}`, { reviewId: review.id });
|
|
@@ -26516,7 +27076,7 @@ function createStore(dir, log = noopLogger) {
|
|
|
26516
27076
|
return review;
|
|
26517
27077
|
},
|
|
26518
27078
|
async persisted(id) {
|
|
26519
|
-
return await readJsonFile(
|
|
27079
|
+
return await readJsonFile(join13(dir, `${id}.json`)) ?? undefined;
|
|
26520
27080
|
},
|
|
26521
27081
|
size() {
|
|
26522
27082
|
return reviews.size;
|
|
@@ -26533,7 +27093,7 @@ function createStore(dir, log = noopLogger) {
|
|
|
26533
27093
|
async rehydrate() {
|
|
26534
27094
|
let files;
|
|
26535
27095
|
try {
|
|
26536
|
-
files = await
|
|
27096
|
+
files = await readdir6(dir);
|
|
26537
27097
|
} catch {
|
|
26538
27098
|
log.debug("store", "no reviews dir; nothing to rehydrate");
|
|
26539
27099
|
return;
|
|
@@ -26543,7 +27103,7 @@ function createStore(dir, log = noopLogger) {
|
|
|
26543
27103
|
if (!file2.endsWith(".json"))
|
|
26544
27104
|
continue;
|
|
26545
27105
|
try {
|
|
26546
|
-
const review = JSON.parse(await
|
|
27106
|
+
const review = JSON.parse(await readFile4(join13(dir, file2), "utf-8"));
|
|
26547
27107
|
if (isUnresolved(review.status)) {
|
|
26548
27108
|
reviews.set(review.id, review);
|
|
26549
27109
|
loaded++;
|
|
@@ -26568,6 +27128,28 @@ async function runDaemon(opts) {
|
|
|
26568
27128
|
log.info("settings", existsSync7(cfg) ? `settings: reading ${cfg}` : `settings: no config at ${cfg}; using defaults`, { settings: boot });
|
|
26569
27129
|
warnInvalidEnvVars((msg) => log.warn("env", msg));
|
|
26570
27130
|
const adapter = selectAdapter();
|
|
27131
|
+
const install = buildKind();
|
|
27132
|
+
const version2 = VERSION;
|
|
27133
|
+
const commit = currentCommit();
|
|
27134
|
+
const updateCache = fileUpdateCache(updateCheckFile());
|
|
27135
|
+
let updateStatus = readCachedStatus(updateCache, version2, commit);
|
|
27136
|
+
function refreshUpdate() {
|
|
27137
|
+
runUpdateCheck({
|
|
27138
|
+
kind: install,
|
|
27139
|
+
version: version2,
|
|
27140
|
+
commit,
|
|
27141
|
+
enabled: () => readUpdatesCheck(),
|
|
27142
|
+
now: Date.now,
|
|
27143
|
+
cache: updateCache,
|
|
27144
|
+
npmLatest: publishedCaretVersion,
|
|
27145
|
+
release: latestReleaseTag,
|
|
27146
|
+
aheadBy: commitsAheadOfTrunk,
|
|
27147
|
+
log
|
|
27148
|
+
}).then((status) => {
|
|
27149
|
+
if (status)
|
|
27150
|
+
updateStatus = status;
|
|
27151
|
+
}, (err) => log.error("update", err));
|
|
27152
|
+
}
|
|
26571
27153
|
const store = createStore(reviewsDir(), log);
|
|
26572
27154
|
await store.rehydrate();
|
|
26573
27155
|
const assets = await loadUiAssets();
|
|
@@ -26575,6 +27157,19 @@ async function runDaemon(opts) {
|
|
|
26575
27157
|
log.info("ui", "no embedded ui; serving placeholder");
|
|
26576
27158
|
const ephemeral = opts.ephemeral;
|
|
26577
27159
|
let server;
|
|
27160
|
+
const shutdown = (code) => {
|
|
27161
|
+
server?.stop();
|
|
27162
|
+
process.exit(code);
|
|
27163
|
+
};
|
|
27164
|
+
process.once("SIGTERM", () => {
|
|
27165
|
+
log.info("signal", "sigterm: shutting down");
|
|
27166
|
+
shutdown(0);
|
|
27167
|
+
});
|
|
27168
|
+
process.once("SIGINT", () => {
|
|
27169
|
+
log.info("signal", "sigint: shutting down");
|
|
27170
|
+
shutdown(0);
|
|
27171
|
+
});
|
|
27172
|
+
process.once("exit", removeOwnDaemonLock);
|
|
26578
27173
|
try {
|
|
26579
27174
|
server = createServer({
|
|
26580
27175
|
store,
|
|
@@ -26584,11 +27179,13 @@ async function runDaemon(opts) {
|
|
|
26584
27179
|
assets,
|
|
26585
27180
|
lockPath: daemonLock(),
|
|
26586
27181
|
buildId: await currentBuildId(),
|
|
26587
|
-
commit
|
|
27182
|
+
commit,
|
|
26588
27183
|
stateDir: stateDir(),
|
|
26589
27184
|
instanceId: randomUUID().slice(0, 8),
|
|
26590
27185
|
approveVariants: adapter.approveVariants,
|
|
26591
27186
|
source: adapter.id,
|
|
27187
|
+
listSkills: (cwd) => adapter.listSkills(cwd),
|
|
27188
|
+
readSkillDescription: (cwd, skill) => adapter.readSkillDescription(cwd, skill),
|
|
26592
27189
|
diagnostics: () => buildDiagnostics({
|
|
26593
27190
|
now: Date.now,
|
|
26594
27191
|
startedAt,
|
|
@@ -26602,6 +27199,8 @@ async function runDaemon(opts) {
|
|
|
26602
27199
|
configExists: () => existsSync7(cfg),
|
|
26603
27200
|
envOverrides
|
|
26604
27201
|
}),
|
|
27202
|
+
updateReport: async () => updateReportFor({ install, version: version2, commit }, updateStatus, await readUpdatesCheck()),
|
|
27203
|
+
onUpdatesEnabled: refreshUpdate,
|
|
26605
27204
|
log
|
|
26606
27205
|
});
|
|
26607
27206
|
} catch (e) {
|
|
@@ -26612,29 +27211,13 @@ async function runDaemon(opts) {
|
|
|
26612
27211
|
}
|
|
26613
27212
|
throw e;
|
|
26614
27213
|
}
|
|
26615
|
-
const shutdown = (code) => {
|
|
26616
|
-
server.stop();
|
|
26617
|
-
process.exit(code);
|
|
26618
|
-
};
|
|
26619
|
-
process.once("SIGTERM", () => {
|
|
26620
|
-
log.info("signal", "sigterm: shutting down");
|
|
26621
|
-
shutdown(0);
|
|
26622
|
-
});
|
|
26623
|
-
process.once("SIGINT", () => {
|
|
26624
|
-
log.info("signal", "sigint: shutting down");
|
|
26625
|
-
shutdown(0);
|
|
26626
|
-
});
|
|
26627
27214
|
const onFatal = (label) => (err) => {
|
|
26628
27215
|
log.error(label, err);
|
|
26629
27216
|
shutdown(1);
|
|
26630
27217
|
};
|
|
26631
27218
|
process.once("uncaughtException", onFatal("uncaughtException"));
|
|
26632
27219
|
process.once("unhandledRejection", onFatal("unhandledRejection"));
|
|
26633
|
-
|
|
26634
|
-
try {
|
|
26635
|
-
unlinkSync4(daemonLock());
|
|
26636
|
-
} catch {}
|
|
26637
|
-
});
|
|
27220
|
+
refreshUpdate();
|
|
26638
27221
|
}
|
|
26639
27222
|
|
|
26640
27223
|
// src/commands/discovery.ts
|
|
@@ -26643,7 +27226,7 @@ import { release } from "os";
|
|
|
26643
27226
|
|
|
26644
27227
|
// src/discovery.ts
|
|
26645
27228
|
import { readdirSync as readdirSync4, statSync as statSync4 } from "fs";
|
|
26646
|
-
import { basename as basename3, join as
|
|
27229
|
+
import { basename as basename3, join as join14 } from "path";
|
|
26647
27230
|
var CARET_BIN = "caret-native";
|
|
26648
27231
|
async function safe(build) {
|
|
26649
27232
|
try {
|
|
@@ -26854,7 +27437,7 @@ function listReviewFiles() {
|
|
|
26854
27437
|
continue;
|
|
26855
27438
|
if (out.length >= 5000)
|
|
26856
27439
|
break;
|
|
26857
|
-
const raw = readJsonFileSync(
|
|
27440
|
+
const raw = readJsonFileSync(join14(dir, file2));
|
|
26858
27441
|
if (raw && typeof raw.id === "string" && typeof raw.status === "string") {
|
|
26859
27442
|
out.push({ id: raw.id, status: raw.status });
|
|
26860
27443
|
}
|
|
@@ -26964,31 +27547,31 @@ import {
|
|
|
26964
27547
|
rmSync as rmSync2,
|
|
26965
27548
|
statSync as statSync5,
|
|
26966
27549
|
symlinkSync,
|
|
26967
|
-
writeFileSync as
|
|
27550
|
+
writeFileSync as writeFileSync7
|
|
26968
27551
|
} from "fs";
|
|
26969
|
-
import { join as
|
|
27552
|
+
import { join as join16, resolve as resolve2 } from "path";
|
|
26970
27553
|
|
|
26971
27554
|
// src/adapters/opencode/packaging.ts
|
|
26972
27555
|
import { existsSync as existsSync9, readdirSync as readdirSync5, readFileSync as readFileSync9 } from "fs";
|
|
26973
|
-
import { dirname as
|
|
27556
|
+
import { dirname as dirname8, join as join15 } from "path";
|
|
26974
27557
|
function resolveCaretRoot() {
|
|
26975
27558
|
const candidates = [];
|
|
26976
27559
|
const script = process.argv[1];
|
|
26977
27560
|
if (script)
|
|
26978
|
-
candidates.push(
|
|
26979
|
-
candidates.push(
|
|
27561
|
+
candidates.push(join15(dirname8(script), ".."));
|
|
27562
|
+
candidates.push(join15(dirname8(process.execPath), ".."));
|
|
26980
27563
|
for (const root of candidates) {
|
|
26981
|
-
if (existsSync9(
|
|
27564
|
+
if (existsSync9(join15(root, "opencode", "caret.plugin.ts")))
|
|
26982
27565
|
return root;
|
|
26983
27566
|
}
|
|
26984
27567
|
throw new Error(`caret OpenCode packaging not found (no opencode/caret.plugin.ts under: ${candidates.join(", ") || "(none)"}). The OpenCode plugin source must ship with caret.`);
|
|
26985
27568
|
}
|
|
26986
27569
|
function loadOpencodePackaging(root = resolveCaretRoot()) {
|
|
26987
|
-
const binPath =
|
|
26988
|
-
const commandsDir =
|
|
27570
|
+
const binPath = join15(root, "bin", "caret");
|
|
27571
|
+
const commandsDir = join15(root, "opencode", "commands");
|
|
26989
27572
|
let commands = [];
|
|
26990
27573
|
try {
|
|
26991
|
-
commands = readdirSync5(commandsDir).filter((f) => f.endsWith(".md")).sort().map((f) => ({ name: f, contents: readFileSync9(
|
|
27574
|
+
commands = readdirSync5(commandsDir).filter((f) => f.endsWith(".md")).sort().map((f) => ({ name: f, contents: readFileSync9(join15(commandsDir, f), "utf-8") }));
|
|
26992
27575
|
} catch {
|
|
26993
27576
|
commands = [];
|
|
26994
27577
|
}
|
|
@@ -26997,17 +27580,17 @@ function loadOpencodePackaging(root = resolveCaretRoot()) {
|
|
|
26997
27580
|
|
|
26998
27581
|
// src/commands/install/local.ts
|
|
26999
27582
|
function devMarketplaceDir() {
|
|
27000
|
-
return
|
|
27583
|
+
return join16(stateDir(), "dev-marketplace");
|
|
27001
27584
|
}
|
|
27002
27585
|
function resolveLocalCheckout(opts = {}, deps = {}) {
|
|
27003
27586
|
const repoDir = resolve2(caretRoot(deps));
|
|
27004
|
-
if (!existsSync10(
|
|
27587
|
+
if (!existsSync10(join16(repoDir, ".claude-plugin", "marketplace.json"))) {
|
|
27005
27588
|
throw new Error(`--from-local must run from a caret checkout (no .claude-plugin/marketplace.json at ${repoDir}). A published caret installs with a plain \`caret install\`.`);
|
|
27006
27589
|
}
|
|
27007
27590
|
if (opts.requireArtifacts !== false) {
|
|
27008
27591
|
const missing = [
|
|
27009
|
-
isExecutable(
|
|
27010
|
-
isDirectory(
|
|
27592
|
+
isExecutable(join16(repoDir, "bin", "caret-native")) ? null : "bin/caret-native",
|
|
27593
|
+
isDirectory(join16(repoDir, "bin", "ui")) ? null : "bin/ui"
|
|
27011
27594
|
].filter((m) => m !== null);
|
|
27012
27595
|
if (missing.length > 0) {
|
|
27013
27596
|
throw new Error(`--from-local reuses the build artifacts bin/caret-native + bin/ui, and ${repoDir} is missing ${missing.join(" + ")} \u2014 run \`mise run build\` first.`);
|
|
@@ -27026,9 +27609,9 @@ function caretRoot(deps) {
|
|
|
27026
27609
|
}
|
|
27027
27610
|
function writeDevMarketplace(repoDir, outDir) {
|
|
27028
27611
|
rmSync2(outDir, { recursive: true, force: true });
|
|
27029
|
-
mkdirSync3(
|
|
27030
|
-
symlinkSync(resolve2(repoDir),
|
|
27031
|
-
|
|
27612
|
+
mkdirSync3(join16(outDir, ".claude-plugin"), { recursive: true });
|
|
27613
|
+
symlinkSync(resolve2(repoDir), join16(outDir, "caret"));
|
|
27614
|
+
writeFileSync7(join16(outDir, ".claude-plugin", "marketplace.json"), `${JSON.stringify({
|
|
27032
27615
|
name: "caret",
|
|
27033
27616
|
description: "Local caret dev build (generated by caret install --from-local).",
|
|
27034
27617
|
owner: { name: "macintacos" },
|
|
@@ -27039,7 +27622,7 @@ function writeDevMarketplace(repoDir, outDir) {
|
|
|
27039
27622
|
async function prewarmLocalBuild(repoDir, deps = {}) {
|
|
27040
27623
|
const spawn = deps.spawn ?? runCaptured;
|
|
27041
27624
|
try {
|
|
27042
|
-
await spawn([
|
|
27625
|
+
await spawn([join16(repoDir, "bin", "caret-native"), "prewarm"]);
|
|
27043
27626
|
} catch {}
|
|
27044
27627
|
}
|
|
27045
27628
|
function isExecutable(path) {
|
|
@@ -27313,12 +27896,12 @@ async function runInstallClaudeTarget(opts, deps = {}) {
|
|
|
27313
27896
|
}
|
|
27314
27897
|
|
|
27315
27898
|
// src/commands/install/opencode.ts
|
|
27316
|
-
import { existsSync as existsSync14, readFileSync as readFileSync10, writeFileSync as
|
|
27317
|
-
import { basename as basename4, join as
|
|
27899
|
+
import { existsSync as existsSync14, readFileSync as readFileSync10, writeFileSync as writeFileSync9 } from "fs";
|
|
27900
|
+
import { basename as basename4, join as join18 } from "path";
|
|
27318
27901
|
|
|
27319
27902
|
// src/adapters/opencode/deploy.ts
|
|
27320
|
-
import { existsSync as existsSync12, mkdirSync as mkdirSync4, rmSync as rmSync3, writeFileSync as
|
|
27321
|
-
import { dirname as
|
|
27903
|
+
import { existsSync as existsSync12, mkdirSync as mkdirSync4, rmSync as rmSync3, writeFileSync as writeFileSync8 } from "fs";
|
|
27904
|
+
import { dirname as dirname10 } from "path";
|
|
27322
27905
|
function renderPlugin(source, opts) {
|
|
27323
27906
|
return source.replaceAll("__CARET_VERSION__", () => opts.version).replaceAll("__CARET_BIN__", () => opts.binPath);
|
|
27324
27907
|
}
|
|
@@ -27326,8 +27909,8 @@ function deployFiles(files, opts) {
|
|
|
27326
27909
|
const paths = [];
|
|
27327
27910
|
for (const f2 of files) {
|
|
27328
27911
|
if (!opts.dryRun) {
|
|
27329
|
-
mkdirSync4(
|
|
27330
|
-
|
|
27912
|
+
mkdirSync4(dirname10(f2.path), { recursive: true });
|
|
27913
|
+
writeFileSync8(f2.path, f2.contents);
|
|
27331
27914
|
}
|
|
27332
27915
|
paths.push(f2.path);
|
|
27333
27916
|
}
|
|
@@ -27417,7 +28000,7 @@ async function promptUpgrade(verdict, clack) {
|
|
|
27417
28000
|
|
|
27418
28001
|
// src/commands/install/opencode.ts
|
|
27419
28002
|
function isCaretCheckout(dir) {
|
|
27420
|
-
return existsSync14(
|
|
28003
|
+
return existsSync14(join18(dir, "opencode", "caret.plugin.ts"));
|
|
27421
28004
|
}
|
|
27422
28005
|
function caretEntries(text2, isCheckout) {
|
|
27423
28006
|
return pluginEntries(text2).filter((entry) => {
|
|
@@ -27443,7 +28026,7 @@ async function runInstallOpencodeTarget(opts, deps = {}) {
|
|
|
27443
28026
|
const ui = deps.ui ?? silentUI;
|
|
27444
28027
|
const isCheckout = deps.isCheckout ?? isCaretCheckout;
|
|
27445
28028
|
const configFile2 = resolveConfigFile(dir);
|
|
27446
|
-
const commandPaths = pkg.commands.map((c3) =>
|
|
28029
|
+
const commandPaths = pkg.commands.map((c3) => join18(commandDir(dir), namespacedCommandFilename(c3.name)));
|
|
27447
28030
|
const legacy = existingLegacyInstallFiles(dir);
|
|
27448
28031
|
const specifier = opts.local ? localPluginSpecifier(opts.local.repoDir) : CARET_PACKAGE;
|
|
27449
28032
|
if (opts.dryRun) {
|
|
@@ -27466,7 +28049,7 @@ async function runInstallOpencodeTarget(opts, deps = {}) {
|
|
|
27466
28049
|
await upgradeStep(configFile2, opts, deps, ui);
|
|
27467
28050
|
await sweepLegacy(legacy, dir, ui);
|
|
27468
28051
|
const files = pkg.commands.map((c3) => ({
|
|
27469
|
-
path:
|
|
28052
|
+
path: join18(commandDir(dir), namespacedCommandFilename(c3.name)),
|
|
27470
28053
|
contents: renderPlugin(c3.contents, { version: VERSION, binPath: pkg.binPath })
|
|
27471
28054
|
}));
|
|
27472
28055
|
await ui.step("Deploying the /caret:* command files", async () => deployFiles(files, { dryRun: false }), (deployed) => `Deployed ${deployed.paths.length} command file(s) to ${dir}`);
|
|
@@ -27522,7 +28105,7 @@ function editConfig(path2, transform2) {
|
|
|
27522
28105
|
const next = transform2(existing);
|
|
27523
28106
|
if (next === null || next === existing)
|
|
27524
28107
|
return [];
|
|
27525
|
-
|
|
28108
|
+
writeFileSync9(path2, next);
|
|
27526
28109
|
return [path2];
|
|
27527
28110
|
}
|
|
27528
28111
|
|
|
@@ -27534,10 +28117,10 @@ function parseTargets(raw) {
|
|
|
27534
28117
|
error: `--target names no agent (it takes a comma-separated list of: ${INSTALL_TARGET_IDS.join(", ")}) \u2014 omit it entirely to choose interactively.`
|
|
27535
28118
|
};
|
|
27536
28119
|
}
|
|
27537
|
-
const
|
|
27538
|
-
if (
|
|
28120
|
+
const unknown3 = parts.filter((p3) => !INSTALL_TARGET_IDS.includes(p3));
|
|
28121
|
+
if (unknown3.length > 0) {
|
|
27539
28122
|
return {
|
|
27540
|
-
error: `unknown --target value(s): ${
|
|
28123
|
+
error: `unknown --target value(s): ${unknown3.join(", ")}. Valid: ${INSTALL_TARGET_IDS.join(", ")}.`
|
|
27541
28124
|
};
|
|
27542
28125
|
}
|
|
27543
28126
|
const targets = [];
|
|
@@ -30591,7 +31174,7 @@ Expecting one of '${allowedValues.join("', '")}'`);
|
|
|
30591
31174
|
});
|
|
30592
31175
|
this.runningCommand = proc;
|
|
30593
31176
|
}
|
|
30594
|
-
_dispatchSubcommand(commandName, operands,
|
|
31177
|
+
_dispatchSubcommand(commandName, operands, unknown3) {
|
|
30595
31178
|
const subCommand = this._findCommand(commandName);
|
|
30596
31179
|
if (!subCommand)
|
|
30597
31180
|
this.help({ error: true });
|
|
@@ -30600,9 +31183,9 @@ Expecting one of '${allowedValues.join("', '")}'`);
|
|
|
30600
31183
|
promiseChain = this._chainOrCallSubCommandHook(promiseChain, subCommand, "preSubcommand");
|
|
30601
31184
|
promiseChain = this._chainOrCall(promiseChain, () => {
|
|
30602
31185
|
if (subCommand._executableHandler) {
|
|
30603
|
-
this._executeSubCommand(subCommand, operands.concat(
|
|
31186
|
+
this._executeSubCommand(subCommand, operands.concat(unknown3));
|
|
30604
31187
|
} else {
|
|
30605
|
-
return subCommand._parseCommand(operands,
|
|
31188
|
+
return subCommand._parseCommand(operands, unknown3);
|
|
30606
31189
|
}
|
|
30607
31190
|
});
|
|
30608
31191
|
return promiseChain;
|
|
@@ -30699,22 +31282,22 @@ Expecting one of '${allowedValues.join("', '")}'`);
|
|
|
30699
31282
|
}
|
|
30700
31283
|
return result;
|
|
30701
31284
|
}
|
|
30702
|
-
_parseCommand(operands,
|
|
30703
|
-
const parsed = this.parseOptions(
|
|
31285
|
+
_parseCommand(operands, unknown3) {
|
|
31286
|
+
const parsed = this.parseOptions(unknown3);
|
|
30704
31287
|
this._parseOptionsEnv();
|
|
30705
31288
|
this._parseOptionsImplied();
|
|
30706
31289
|
operands = operands.concat(parsed.operands);
|
|
30707
|
-
|
|
30708
|
-
this.args = operands.concat(
|
|
31290
|
+
unknown3 = parsed.unknown;
|
|
31291
|
+
this.args = operands.concat(unknown3);
|
|
30709
31292
|
if (operands && this._findCommand(operands[0])) {
|
|
30710
|
-
return this._dispatchSubcommand(operands[0], operands.slice(1),
|
|
31293
|
+
return this._dispatchSubcommand(operands[0], operands.slice(1), unknown3);
|
|
30711
31294
|
}
|
|
30712
31295
|
if (this._getHelpCommand() && operands[0] === this._getHelpCommand().name()) {
|
|
30713
31296
|
return this._dispatchHelpCommand(operands[1]);
|
|
30714
31297
|
}
|
|
30715
31298
|
if (this._defaultCommandName) {
|
|
30716
|
-
this._outputHelpIfRequested(
|
|
30717
|
-
return this._dispatchSubcommand(this._defaultCommandName, operands,
|
|
31299
|
+
this._outputHelpIfRequested(unknown3);
|
|
31300
|
+
return this._dispatchSubcommand(this._defaultCommandName, operands, unknown3);
|
|
30718
31301
|
}
|
|
30719
31302
|
if (this.commands.length && this.args.length === 0 && !this._actionHandler && !this._defaultCommandName) {
|
|
30720
31303
|
this.help({ error: true });
|
|
@@ -30736,7 +31319,7 @@ Expecting one of '${allowedValues.join("', '")}'`);
|
|
|
30736
31319
|
promiseChain = this._chainOrCall(promiseChain, () => this._actionHandler(this.processedArgs));
|
|
30737
31320
|
if (this.parent) {
|
|
30738
31321
|
promiseChain = this._chainOrCall(promiseChain, () => {
|
|
30739
|
-
this.parent.emit(commandEvent, operands,
|
|
31322
|
+
this.parent.emit(commandEvent, operands, unknown3);
|
|
30740
31323
|
});
|
|
30741
31324
|
}
|
|
30742
31325
|
promiseChain = this._chainOrCallHooks(promiseChain, "postAction");
|
|
@@ -30745,13 +31328,13 @@ Expecting one of '${allowedValues.join("', '")}'`);
|
|
|
30745
31328
|
if (this.parent?.listenerCount(commandEvent)) {
|
|
30746
31329
|
checkForUnknownOptions();
|
|
30747
31330
|
this._processArguments();
|
|
30748
|
-
this.parent.emit(commandEvent, operands,
|
|
31331
|
+
this.parent.emit(commandEvent, operands, unknown3);
|
|
30749
31332
|
} else if (operands.length) {
|
|
30750
31333
|
if (this._findCommand("*")) {
|
|
30751
|
-
return this._dispatchSubcommand("*", operands,
|
|
31334
|
+
return this._dispatchSubcommand("*", operands, unknown3);
|
|
30752
31335
|
}
|
|
30753
31336
|
if (this.listenerCount("command:*")) {
|
|
30754
|
-
this.emit("command:*", operands,
|
|
31337
|
+
this.emit("command:*", operands, unknown3);
|
|
30755
31338
|
} else if (this.commands.length) {
|
|
30756
31339
|
this.unknownCommand();
|
|
30757
31340
|
} else {
|
|
@@ -30806,7 +31389,7 @@ Expecting one of '${allowedValues.join("', '")}'`);
|
|
|
30806
31389
|
}
|
|
30807
31390
|
parseOptions(args) {
|
|
30808
31391
|
const operands = [];
|
|
30809
|
-
const
|
|
31392
|
+
const unknown3 = [];
|
|
30810
31393
|
let dest = operands;
|
|
30811
31394
|
function maybeOption(arg) {
|
|
30812
31395
|
return arg.length > 1 && arg[0] === "-";
|
|
@@ -30823,7 +31406,7 @@ Expecting one of '${allowedValues.join("', '")}'`);
|
|
|
30823
31406
|
const arg = activeGroup ?? args[i2++];
|
|
30824
31407
|
activeGroup = null;
|
|
30825
31408
|
if (arg === "--") {
|
|
30826
|
-
if (dest ===
|
|
31409
|
+
if (dest === unknown3)
|
|
30827
31410
|
dest.push(arg);
|
|
30828
31411
|
dest.push(...args.slice(i2));
|
|
30829
31412
|
break;
|
|
@@ -30875,18 +31458,18 @@ Expecting one of '${allowedValues.join("', '")}'`);
|
|
|
30875
31458
|
}
|
|
30876
31459
|
}
|
|
30877
31460
|
if (dest === operands && maybeOption(arg) && !(this.commands.length === 0 && negativeNumberArg(arg))) {
|
|
30878
|
-
dest =
|
|
31461
|
+
dest = unknown3;
|
|
30879
31462
|
}
|
|
30880
|
-
if ((this._enablePositionalOptions || this._passThroughOptions) && operands.length === 0 &&
|
|
31463
|
+
if ((this._enablePositionalOptions || this._passThroughOptions) && operands.length === 0 && unknown3.length === 0) {
|
|
30881
31464
|
if (this._findCommand(arg)) {
|
|
30882
31465
|
operands.push(arg);
|
|
30883
|
-
|
|
31466
|
+
unknown3.push(...args.slice(i2));
|
|
30884
31467
|
break;
|
|
30885
31468
|
} else if (this._getHelpCommand() && arg === this._getHelpCommand().name()) {
|
|
30886
31469
|
operands.push(arg, ...args.slice(i2));
|
|
30887
31470
|
break;
|
|
30888
31471
|
} else if (this._defaultCommandName) {
|
|
30889
|
-
|
|
31472
|
+
unknown3.push(arg, ...args.slice(i2));
|
|
30890
31473
|
break;
|
|
30891
31474
|
}
|
|
30892
31475
|
}
|
|
@@ -30896,7 +31479,7 @@ Expecting one of '${allowedValues.join("', '")}'`);
|
|
|
30896
31479
|
}
|
|
30897
31480
|
dest.push(arg);
|
|
30898
31481
|
}
|
|
30899
|
-
return { operands, unknown:
|
|
31482
|
+
return { operands, unknown: unknown3 };
|
|
30900
31483
|
}
|
|
30901
31484
|
opts() {
|
|
30902
31485
|
if (this._storeOptionsAsProperties) {
|