Compare commits

..
6 Commits
Author SHA1 Message Date
StanPonomarev b0adf2ab18 Merge pull request 'chore: bump deps (oc 2.0.27)' (#26) from chore/opencode-2-0-27 into main
Release / release (push) Successful in 10s
Reviewed-on: #26
2026-10-12 09:49:50 +02:00
StanPonomarev 64b2f96601 chore: bump deps (oc 2.0.27)
CI / verify (pull_request) Successful in 10s
2026-10-12 09:48:45 +02:00
StanPonomarev d1c944f262 Merge pull request 'Chore: reorg files' (#25) from chore/file_reorg into main
Release / release (push) Successful in 10s
Reviewed-on: #25
2026-10-10 15:17:35 +02:00
StanPonomarev 513d51f702 stricter checks
CI / verify (pull_request) Successful in 12s
2026-10-10 15:16:53 +02:00
StanPonomarev ced43fbb11 chore: reorg files 2026-10-10 15:00:15 +02:00
StanPonomarev c853cca9cf Merge pull request 'Feat/remove optchat add planning prompt' (#24) from feat/remove_optchat_add_planning_prompt into main
Reviewed-on: #24
2026-10-10 14:55:51 +02:00
42 changed files with 1140 additions and 631 deletions
+62
View File
@@ -0,0 +1,62 @@
/** @type {import('dependency-cruiser').IConfiguration} */
module.exports = {
forbidden: [
{
name: "no-circular",
severity: "error",
from: {},
to: { circular: true },
},
{
name: "no-orphans",
severity: "error",
from: { orphan: true, pathNot: ["\\.d\\.ts$"] },
to: {},
},
{
name: "not-to-unresolvable",
severity: "error",
from: {},
to: { couldNotResolve: true, pathNot: ["^bun:"] },
},
{
name: "quota-is-standalone",
comment: "Quota ships independently of Agents and Multi-work.",
severity: "error",
from: { path: "^src/quota/" },
to: { path: "^src/(agents|multi-work)/" },
},
{
name: "agents-is-standalone",
comment: "Agents must load without Quota or Multi-work.",
severity: "error",
from: { path: "^src/agents/" },
to: { path: "^src/(quota|multi-work)/" },
},
{
name: "multi-work-not-to-quota",
comment: "Multi-work may build on Agents but not on Quota.",
severity: "error",
from: { path: "^src/multi-work/" },
to: { path: "^src/quota/" },
},
{
name: "src-not-to-scripts-or-tests",
severity: "error",
from: { path: "^src/" },
to: { path: "^(scripts|tests)/" },
},
],
options: {
doNotFollow: { path: "node_modules" },
tsConfig: { fileName: "tsconfig.json" },
tsPreCompilationDeps: true,
// TypeScript 7 has no compiler API yet; swc parses TS/TSX for the cruise.
parser: "swc",
enhancedResolveOptions: {
exportsFields: ["exports"],
conditionNames: ["import", "types", "bun", "default"],
extensions: [".ts", ".tsx", ".js", ".d.ts"],
},
},
};
+1 -4
View File
@@ -22,8 +22,5 @@ jobs:
- name: Verify and build - name: Verify and build
run: | run: |
bun install --frozen-lockfile bun install --frozen-lockfile
bun run check bun run verify
bun run lint
bun run format:check
bun run test
bun run build bun run build
+1 -4
View File
@@ -28,10 +28,7 @@ jobs:
- name: Verify and build - name: Verify and build
run: | run: |
bun install --frozen-lockfile bun install --frozen-lockfile
bun run check bun run verify
bun run lint
bun run format:check
bun run test
bun run build bun run build
- name: Pack distributable - name: Pack distributable
run: | run: |
+8
View File
@@ -0,0 +1,8 @@
{
"path": ["src", "scripts", "tests"],
"format": ["typescript", "tsx"],
"threshold": 1,
"minTokens": 50,
"reporters": ["console"],
"gitignore": true
}
+1 -1
View File
@@ -16,7 +16,7 @@
".roo/**", ".roo/**",
".windsurf/**", ".windsurf/**",
"tools/oxlint/anti-slop/**", "tools/oxlint/anti-slop/**",
"src/anti-overengineering.md", "src/skills/anti-overengineering.md",
"node_modules/**", "node_modules/**",
"dist/**", "dist/**",
"coverage/**", "coverage/**",
+77 -2
View File
@@ -24,6 +24,34 @@
} }
], ],
"rules": { "rules": {
"typescript/no-explicit-any": "error",
"typescript/ban-ts-comment": "error",
"typescript/no-non-null-assertion": "error",
"max-lines": [
"error",
{
"max": 600,
"skipBlankLines": true,
"skipComments": true
}
],
"max-lines-per-function": "off",
"complexity": ["error", 20],
"max-depth": ["error", 4],
"max-params": ["error", 5],
"typescript/no-floating-promises": "error",
"typescript/no-misused-promises": "error",
"typescript/no-unsafe-argument": "error",
"typescript/no-unsafe-assignment": "error",
"typescript/no-unsafe-call": "error",
"typescript/no-unsafe-member-access": "error",
"typescript/no-unsafe-return": "error",
"typescript/no-unsafe-enum-comparison": "error",
"typescript/no-unsafe-unary-minus": "error",
"typescript/no-unsafe-type-assertion": "error",
"typescript/no-unnecessary-condition": "error",
"typescript/strict-boolean-expressions": "error",
"typescript/switch-exhaustiveness-check": "error",
"anti-slop/no-chained-type-assertions": "error", "anti-slop/no-chained-type-assertions": "error",
"anti-slop/no-conditional-empty-object-spread": "error", "anti-slop/no-conditional-empty-object-spread": "error",
"anti-slop/no-known-value-widening": "error", "anti-slop/no-known-value-widening": "error",
@@ -38,6 +66,53 @@
"anti-slop/no-unknown-type-aliases": "error", "anti-slop/no-unknown-type-aliases": "error",
"anti-slop/no-unsafe-dictionary-type": "error", "anti-slop/no-unsafe-dictionary-type": "error",
"anti-slop/no-widen-then-assert": "error", "anti-slop/no-widen-then-assert": "error",
"anti-slop/require-safety-comment-for-type-assertion": "error" "anti-slop/require-safety-comment-for-type-assertion": "error",
} "typescript/prefer-readonly-parameter-types": "off",
"eslint/require-await": "off",
"eslint/no-await-in-loop": "off",
"import/max-dependencies": [
"error",
{
"max": 15
}
],
"typescript/require-await": "off",
"typescript/consistent-return": "off",
"eslint/no-underscore-dangle": "off",
"unicorn/prefer-top-level-await": "off",
"unicorn/no-useless-undefined": [
"error",
{
"checkArguments": false,
"checkArrowFunctionBody": false
}
],
"oxc/no-map-spread": "off",
"eslint/no-useless-return": "off"
},
"plugins": ["typescript", "unicorn", "oxc", "import", "promise"],
"categories": {
"correctness": "error",
"suspicious": "error",
"pedantic": "error",
"perf": "error"
},
"overrides": [
{
"files": ["tests/**"],
"rules": {
"typescript/no-unsafe-type-assertion": "off",
"typescript/await-thenable": "off",
"typescript/no-confusing-void-expression": "off"
}
},
{
"files": ["**/*.tsx", "tests/tui.test.ts"],
"rules": {
"typescript/no-unsafe-return": "off",
"typescript/no-unsafe-assignment": "off",
"typescript/no-unsafe-member-access": "off"
}
}
]
} }
+1 -1
View File
@@ -2,7 +2,7 @@
## Installation ## Installation
Requires OpenCode 2.0.22, Bun 1.4.2+, Bash, curl, jq and `sha256sum` on Linux/WSL. Requires OpenCode 2.0.27, Bun 1.4.2+, Bash, curl, jq and `sha256sum` on Linux/WSL.
```sh ```sh
curl -fsSL https://git.krtss.de/StanPonomarev/stanp-opencode/raw/branch/main/install.sh | bash -s -- --plugins agents,multi-work,quota curl -fsSL https://git.krtss.de/StanPonomarev/stanp-opencode/raw/branch/main/install.sh | bash -s -- --plugins agents,multi-work,quota
+325 -130
View File
@@ -5,24 +5,29 @@
"": { "": {
"name": "stanp-opencode", "name": "stanp-opencode",
"dependencies": { "dependencies": {
"effect": "4.0.0-rc.112", "effect": "4.0.1",
"zod": "4.6.5", "zod": "4.6.5",
}, },
"devDependencies": { "devDependencies": {
"@opencode/client": "2.0.22", "@opencode/client": "2.0.27",
"@opencode/plugin": "2.0.22", "@opencode/plugin": "2.0.27",
"@opencode/schema": "2.0.22", "@opencode/schema": "2.0.27",
"@opentui/core": "0.5.14", "@opentui/core": "0.6.1",
"@opentui/solid": "0.5.14", "@opentui/solid": "0.6.1",
"@oxlint/plugins": "1.86.0", "@oxlint/plugins": "1.87.0",
"@swc/core": "1.16.18",
"@types/bun": "1.4.2", "@types/bun": "1.4.2",
"oxfmt": "0.71.0", "dependency-cruiser": "18.6.0",
"oxlint": "1.86.0", "jscpd": "5.4.1",
"knip": "6.41.0",
"oxfmt": "0.72.0",
"oxlint": "1.87.0",
"oxlint-tsgolint": "7.0.2004",
"solid-js": "1.9.15", "solid-js": "1.9.15",
"typescript": "7.0.2", "typescript": "7.0.2",
}, },
"peerDependencies": { "peerDependencies": {
"@opencode/plugin": "2.0.22", "@opencode/plugin": "2.0.27",
"@opentui/core": ">=0.5.14", "@opentui/core": ">=0.5.14",
"@opentui/solid": ">=0.5.14", "@opentui/solid": ">=0.5.14",
"solid-js": ">=1.9.0", "solid-js": ">=1.9.0",
@@ -32,8 +37,6 @@
"packages": { "packages": {
"@ai-sdk/provider": ["@ai-sdk/provider@3.0.8", "", { "dependencies": { "json-schema": "^0.4.0" } }, "sha512-oGMAgGoQdBXbZqNG0Ze56CHjDZ1IDYOwGYxYjO5KLSlz5HiNQ9udIXsPZ61VWaHGZ5XW/jyjmr6t2xz2jGVwbQ=="], "@ai-sdk/provider": ["@ai-sdk/provider@3.0.8", "", { "dependencies": { "json-schema": "^0.4.0" } }, "sha512-oGMAgGoQdBXbZqNG0Ze56CHjDZ1IDYOwGYxYjO5KLSlz5HiNQ9udIXsPZ61VWaHGZ5XW/jyjmr6t2xz2jGVwbQ=="],
"@ampproject/remapping": ["@ampproject/remapping@2.3.0", "", { "dependencies": { "@jridgewell/gen-mapping": "^0.3.5", "@jridgewell/trace-mapping": "^0.3.24" } }, "sha512-30iZtAPgz+LTIYoeivqYo853f02jBYSd5uGnGpkFV0M3xOt9aN73erkgYAmZU43x4VfqcnLxW9Kpg3R5LC4YYw=="],
"@aws-crypto/crc32": ["@aws-crypto/crc32@5.2.0", "", { "dependencies": { "@aws-crypto/util": "^5.2.0", "@aws-sdk/types": "^3.222.0", "tslib": "^2.6.2" } }, "sha512-nLbCWqQNgUiwwtFsen1AdzAtvuLRsQS8rYgMuxCrdKf9kOssamGLuPwyTY9wyYblNr9+1XM8v6zoDTPPSIeANg=="], "@aws-crypto/crc32": ["@aws-crypto/crc32@5.2.0", "", { "dependencies": { "@aws-crypto/util": "^5.2.0", "@aws-sdk/types": "^3.222.0", "tslib": "^2.6.2" } }, "sha512-nLbCWqQNgUiwwtFsen1AdzAtvuLRsQS8rYgMuxCrdKf9kOssamGLuPwyTY9wyYblNr9+1XM8v6zoDTPPSIeANg=="],
"@aws-crypto/sha256-browser": ["@aws-crypto/sha256-browser@5.2.0", "", { "dependencies": { "@aws-crypto/sha256-js": "^5.2.0", "@aws-crypto/supports-web-crypto": "^5.2.0", "@aws-crypto/util": "^5.2.0", "@aws-sdk/types": "^3.222.0", "@aws-sdk/util-locate-window": "^3.0.0", "@smithy/util-utf8": "^2.0.0", "tslib": "^2.6.2" } }, "sha512-AXfN/lGotSQwu6HNcEsIASo7kWXZ5HYWvfOmSNKDsEqC4OashTp8alTmaz+F7TC2L083SFv5RdB+qU3Vs1kZqw=="], "@aws-crypto/sha256-browser": ["@aws-crypto/sha256-browser@5.2.0", "", { "dependencies": { "@aws-crypto/sha256-js": "^5.2.0", "@aws-crypto/supports-web-crypto": "^5.2.0", "@aws-crypto/util": "^5.2.0", "@aws-sdk/types": "^3.222.0", "@aws-sdk/util-locate-window": "^3.0.0", "@smithy/util-utf8": "^2.0.0", "tslib": "^2.6.2" } }, "sha512-AXfN/lGotSQwu6HNcEsIASo7kWXZ5HYWvfOmSNKDsEqC4OashTp8alTmaz+F7TC2L083SFv5RdB+qU3Vs1kZqw=="],
@@ -86,7 +89,7 @@
"@babel/compat-data": ["@babel/compat-data@7.29.7", "", {}, "sha512-locTkQyKvwIEgBzVrn8693ebc97F2U8ZHjbXwDXJ5Fn2TCpNwTlKcaKLkdHop5c/icOFE7qt7Q9JC5hnKNa6Gg=="], "@babel/compat-data": ["@babel/compat-data@7.29.7", "", {}, "sha512-locTkQyKvwIEgBzVrn8693ebc97F2U8ZHjbXwDXJ5Fn2TCpNwTlKcaKLkdHop5c/icOFE7qt7Q9JC5hnKNa6Gg=="],
"@babel/core": ["@babel/core@7.28.0", "", { "dependencies": { "@ampproject/remapping": "^2.2.0", "@babel/code-frame": "^7.27.1", "@babel/generator": "^7.28.0", "@babel/helper-compilation-targets": "^7.27.2", "@babel/helper-module-transforms": "^7.27.3", "@babel/helpers": "^7.27.6", "@babel/parser": "^7.28.0", "@babel/template": "^7.27.2", "@babel/traverse": "^7.28.0", "@babel/types": "^7.28.0", "convert-source-map": "^2.0.0", "debug": "^4.1.0", "gensync": "^1.0.0-beta.2", "json5": "^2.2.3", "semver": "^6.3.1" } }, "sha512-UlLAnTPrFdNGoFtbSXwcGFQBtQZJCNjaN6hQNP3UPvuNXT1i82N26KL3dZeIpNalWywr9IuQuncaAfUaS1g6sQ=="], "@babel/core": ["@babel/core@7.29.7", "", { "dependencies": { "@babel/code-frame": "^7.29.7", "@babel/generator": "^7.29.7", "@babel/helper-compilation-targets": "^7.29.7", "@babel/helper-module-transforms": "^7.29.7", "@babel/helpers": "^7.29.7", "@babel/parser": "^7.29.7", "@babel/template": "^7.29.7", "@babel/traverse": "^7.29.7", "@babel/types": "^7.29.7", "@jridgewell/remapping": "^2.3.5", "convert-source-map": "^2.0.0", "debug": "^4.1.0", "gensync": "^1.0.0-beta.2", "json5": "^2.2.3", "semver": "^6.3.1" } }, "sha512-RgHBCvtjbOK2gXSNBNIkNoEc9qoVEtau3hj8gEqKQuL3HZAibKarWFEI3Lfm6EYKkLalOh8eSrj9b+ch9H/VBA=="],
"@babel/generator": ["@babel/generator@7.29.8", "", { "dependencies": { "@babel/parser": "^7.29.8", "@babel/types": "^7.29.8", "@jridgewell/gen-mapping": "^0.3.12", "@jridgewell/trace-mapping": "^0.3.28", "jsesc": "^3.0.2" } }, "sha512-gZbepsdh3WDtgZKWL+vTPh71LSBrm/Y4/QDZBVCcYfmeTEEuoOYwlSy+G1StfJg+/Zy550u/3TATbm7qDbbMtg=="], "@babel/generator": ["@babel/generator@7.29.8", "", { "dependencies": { "@babel/parser": "^7.29.8", "@babel/types": "^7.29.8", "@jridgewell/gen-mapping": "^0.3.12", "@jridgewell/trace-mapping": "^0.3.28", "jsesc": "^3.0.2" } }, "sha512-gZbepsdh3WDtgZKWL+vTPh71LSBrm/Y4/QDZBVCcYfmeTEEuoOYwlSy+G1StfJg+/Zy550u/3TATbm7qDbbMtg=="],
@@ -138,11 +141,17 @@
"@babel/types": ["@babel/types@7.29.8", "", { "dependencies": { "@babel/helper-string-parser": "^7.29.7", "@babel/helper-validator-identifier": "^7.29.7" } }, "sha512-Vj1jF3cPfxg7OAfoI7QnVKLoILlm2JF9pnVHrX8qx7AHMiYWT+NDAA7jChlNgRS4WTLc/fD1lXLmPixluj+3Gg=="], "@babel/types": ["@babel/types@7.29.8", "", { "dependencies": { "@babel/helper-string-parser": "^7.29.7", "@babel/helper-validator-identifier": "^7.29.7" } }, "sha512-Vj1jF3cPfxg7OAfoI7QnVKLoILlm2JF9pnVHrX8qx7AHMiYWT+NDAA7jChlNgRS4WTLc/fD1lXLmPixluj+3Gg=="],
"@effect/opentelemetry": ["@effect/opentelemetry@4.0.0-rc.112", "", { "peerDependencies": { "@opentelemetry/api": ">=1.9.0 <2.0.0", "@opentelemetry/api-logs": ">=0.203.0 <0.300.0", "@opentelemetry/resources": ">=2.0.0 <3.0.0", "@opentelemetry/sdk-logs": ">=0.203.0 <0.300.0", "@opentelemetry/sdk-metrics": ">=2.0.0 <3.0.0", "@opentelemetry/sdk-trace-base": ">=2.0.0 <3.0.0", "@opentelemetry/sdk-trace-node": ">=2.0.0 <3.0.0", "@opentelemetry/sdk-trace-web": ">=2.0.0 <3.0.0", "@opentelemetry/semantic-conventions": ">=1.33.0 <2.0.0", "effect": "^4.0.0-rc.112" }, "optionalPeers": ["@opentelemetry/api", "@opentelemetry/api-logs", "@opentelemetry/resources", "@opentelemetry/sdk-logs", "@opentelemetry/sdk-metrics", "@opentelemetry/sdk-trace-base", "@opentelemetry/sdk-trace-node", "@opentelemetry/sdk-trace-web"] }, "sha512-OTRv1DxTHUmnakgJ6XVM8wVgF1KgZH4UXnOemwSLUwUjXO+RCikzF8oR/rlVmOGq81KtQzj1URM4M4nchlQOuQ=="], "@effect/opentelemetry": ["@effect/opentelemetry@4.0.1", "", { "peerDependencies": { "@opentelemetry/api": ">=1.9.0 <2.0.0", "@opentelemetry/api-logs": ">=0.203.0 <0.300.0", "@opentelemetry/resources": ">=2.0.0 <3.0.0", "@opentelemetry/sdk-logs": ">=0.203.0 <0.300.0", "@opentelemetry/sdk-metrics": ">=2.0.0 <3.0.0", "@opentelemetry/sdk-trace-base": ">=2.0.0 <3.0.0", "@opentelemetry/sdk-trace-node": ">=2.0.0 <3.0.0", "@opentelemetry/sdk-trace-web": ">=2.0.0 <3.0.0", "@opentelemetry/semantic-conventions": ">=1.33.0 <2.0.0", "effect": "^4.0.1" }, "optionalPeers": ["@opentelemetry/api", "@opentelemetry/api-logs", "@opentelemetry/resources", "@opentelemetry/sdk-logs", "@opentelemetry/sdk-metrics", "@opentelemetry/sdk-trace-base", "@opentelemetry/sdk-trace-node", "@opentelemetry/sdk-trace-web"] }, "sha512-MZ7M1a1dxMqTqeNwIGSECjO7RrReEgeEwHo8BnbOqP+8IfVpdiJi/iPCmkFVWlAxanMl4qhsq69e0Hkul9t+bA=="],
"@effect/platform-node": ["@effect/platform-node@4.0.0-rc.112", "", { "dependencies": { "@effect/platform-node-shared": "^4.0.0-rc.112", "mime": "^4.1.0", "undici": "^8.10.0" }, "peerDependencies": { "effect": "^4.0.0-rc.112", "redis": ">=5.0.0 <7.0.0" } }, "sha512-/BMAcdNGQQskLmI0Zoa95KfTZkr9HV9N4NSxaSrusG6GeW6Ulp9KvZ+Rlaiw8lnOt43CXjFLdfll5/k5rxL4hQ=="], "@effect/platform-node": ["@effect/platform-node@4.0.1", "", { "dependencies": { "@effect/platform-node-shared": "^4.0.1", "undici": "^8.11.2" }, "peerDependencies": { "effect": "^4.0.1", "redis": ">=5.0.0 <7.0.0" } }, "sha512-FT0Fu5LO0/XP9zBpj0HqrtJNLluK4StNKqf6TSulUsjp8FPBsDVXGJiDuyoN5J2yVMT7tgvhxSwaDcObWVRIaQ=="],
"@effect/platform-node-shared": ["@effect/platform-node-shared@4.0.0-rc.112", "", { "dependencies": { "@types/ws": "^8.18.1", "ws": "^8.21.3" }, "peerDependencies": { "effect": "^4.0.0-rc.112" } }, "sha512-ttjz0xKamFN7vL8pNDYVwddJLjZvqKePc05djlz2VcdaKbLsnYbtMnL1rbOfHgEnIUSHGh7FkjaN4DM1Ov81sQ=="], "@effect/platform-node-shared": ["@effect/platform-node-shared@4.0.1", "", { "dependencies": { "@types/ws": "^8.18.1", "ws": "^8.22.0" }, "peerDependencies": { "effect": "^4.0.1" } }, "sha512-VanaejudEhKJ4mpmqnEzdncVUhN6sGSO9ZDND54mRxAlZxj+4dYAWjDTYAy9o4tJo9aALeP2U8cVcOFzEdSeLg=="],
"@emnapi/core": ["@emnapi/core@1.11.2", "", { "dependencies": { "@emnapi/wasi-threads": "1.2.2", "tslib": "^2.4.0" } }, "sha512-TC8MkTuZUtcTSiFeuC0ksCh9QIJ5+F21MvZ4Wn4ORfYaFJ/0dsiudv5tVkejgwZlwQ39jL9WWDe2lz8x0WglOA=="],
"@emnapi/runtime": ["@emnapi/runtime@1.11.2", "", { "dependencies": { "tslib": "^2.4.0" } }, "sha512-kyOl3X0DuTiT1h2ft8r2fYO8JYtU9a9Xis/zBSiGArNaagCOWx90N1k2wxp18czFDH+OgcWGb5ZP/XMt3dcyPA=="],
"@emnapi/wasi-threads": ["@emnapi/wasi-threads@1.2.2", "", { "dependencies": { "tslib": "^2.4.0" } }, "sha512-c95qOXkHdydNKhscBTebqEC1CVAZpyqOfVfBzQ1qgzyl3gfeldUjIggDbIZgDKsHLgnsM+igH7TJ/eAasaVuMA=="],
"@gar/promise-retry": ["@gar/promise-retry@1.0.3", "", {}, "sha512-GmzA9ckNokPypTg10pgpeHNQe7ph+iIKKmhKu3Ob9ANkswreCx7R3cKmY781K8QK3AqVL3xVh9A42JvIAbkkSA=="], "@gar/promise-retry": ["@gar/promise-retry@1.0.3", "", {}, "sha512-GmzA9ckNokPypTg10pgpeHNQe7ph+iIKKmhKu3Ob9ANkswreCx7R3cKmY781K8QK3AqVL3xVh9A42JvIAbkkSA=="],
@@ -154,23 +163,15 @@
"@jridgewell/gen-mapping": ["@jridgewell/gen-mapping@0.3.13", "", { "dependencies": { "@jridgewell/sourcemap-codec": "^1.5.0", "@jridgewell/trace-mapping": "^0.3.24" } }, "sha512-2kkt/7niJ6MgEPxF0bYdQ6etZaA+fQvDcLKckhy1yIQOzaoKjBBjSj63/aLVjYE3qhRt5dvM+uUyfCg6UKCBbA=="], "@jridgewell/gen-mapping": ["@jridgewell/gen-mapping@0.3.13", "", { "dependencies": { "@jridgewell/sourcemap-codec": "^1.5.0", "@jridgewell/trace-mapping": "^0.3.24" } }, "sha512-2kkt/7niJ6MgEPxF0bYdQ6etZaA+fQvDcLKckhy1yIQOzaoKjBBjSj63/aLVjYE3qhRt5dvM+uUyfCg6UKCBbA=="],
"@jridgewell/remapping": ["@jridgewell/remapping@2.3.5", "", { "dependencies": { "@jridgewell/gen-mapping": "^0.3.5", "@jridgewell/trace-mapping": "^0.3.24" } }, "sha512-LI9u/+laYG4Ds1TDKSJW2YPrIlcVYOwi2fUC6xB43lueCjgxV4lffOCZCtYFiH6TNOX+tQKXx97T4IKHbhyHEQ=="],
"@jridgewell/resolve-uri": ["@jridgewell/resolve-uri@3.1.2", "", {}, "sha512-bRISgCIjP20/tbWSPWMEi54QVPRZExkuD9lJL+UIxUKtwVJA8wW1Trb1jMs1RFXo1CBTNZ/5hpC9QvmKWdopKw=="], "@jridgewell/resolve-uri": ["@jridgewell/resolve-uri@3.1.2", "", {}, "sha512-bRISgCIjP20/tbWSPWMEi54QVPRZExkuD9lJL+UIxUKtwVJA8wW1Trb1jMs1RFXo1CBTNZ/5hpC9QvmKWdopKw=="],
"@jridgewell/sourcemap-codec": ["@jridgewell/sourcemap-codec@1.6.0", "", {}, "sha512-T7jf+5zgsZHwNJ4lvQ7/aezbyk0nNX+zJVWpmHA7VYsEx7a7qr5Rg5IbtJFqkgze5Y2sruq1RUY8Q837Od7iFw=="], "@jridgewell/sourcemap-codec": ["@jridgewell/sourcemap-codec@1.6.0", "", {}, "sha512-T7jf+5zgsZHwNJ4lvQ7/aezbyk0nNX+zJVWpmHA7VYsEx7a7qr5Rg5IbtJFqkgze5Y2sruq1RUY8Q837Od7iFw=="],
"@jridgewell/trace-mapping": ["@jridgewell/trace-mapping@0.3.31", "", { "dependencies": { "@jridgewell/resolve-uri": "^3.1.0", "@jridgewell/sourcemap-codec": "^1.4.14" } }, "sha512-zzNR+SdQSDJzc8joaeP8QQoCQr8NuYx2dIIytl1QeBEZHJ9uW6hebsrYgbz8hJwUQao3TWCMtmfV8Nu1twOLAw=="], "@jridgewell/trace-mapping": ["@jridgewell/trace-mapping@0.3.31", "", { "dependencies": { "@jridgewell/resolve-uri": "^3.1.0", "@jridgewell/sourcemap-codec": "^1.4.14" } }, "sha512-zzNR+SdQSDJzc8joaeP8QQoCQr8NuYx2dIIytl1QeBEZHJ9uW6hebsrYgbz8hJwUQao3TWCMtmfV8Nu1twOLAw=="],
"@msgpackr-extract/msgpackr-extract-darwin-arm64": ["@msgpackr-extract/msgpackr-extract-darwin-arm64@3.0.4", "", { "os": "darwin", "cpu": "arm64" }, "sha512-LCkGo6JDfaBhgST7UpPWgNgLINpcpabaHfyz5OBx75nUYxBsaEPxjnyNjWpeb/xBup/682QnBfRBy2/LvPutZQ=="], "@napi-rs/wasm-runtime": ["@napi-rs/wasm-runtime@1.2.5", "", { "dependencies": { "@tybys/wasm-util": "^0.10.3" }, "peerDependencies": { "@emnapi/core": "^1.7.1 || ^2.0.0-alpha.4", "@emnapi/runtime": "^1.7.1 || ^2.0.0-alpha.4" } }, "sha512-HshSvXzmBxNzqejd3k/KemgQ3hdREUYFRRrgxOZ+gPljDIsO2SDZrVZMd4Z/HsxudQbE62OVyVFE8z9BCurfjA=="],
"@msgpackr-extract/msgpackr-extract-darwin-x64": ["@msgpackr-extract/msgpackr-extract-darwin-x64@3.0.4", "", { "os": "darwin", "cpu": "x64" }, "sha512-zExlW9zUJKZH/tOtVMttwjKa4Xm/3KcNjnE3dPN92uCktwavMxpgCA3MoJK/DOnTWsQgo224OaST27/mPNAf+w=="],
"@msgpackr-extract/msgpackr-extract-linux-arm": ["@msgpackr-extract/msgpackr-extract-linux-arm@3.0.4", "", { "os": "linux", "cpu": "arm" }, "sha512-Tg3yX65f5GbtXLkrYEHE5oibZG9epyYWas7FogTTEJeDEF9JlXJzKgXaNhT3UXlTOeA+AfZpYZYZ0uPj7Cfquw=="],
"@msgpackr-extract/msgpackr-extract-linux-arm64": ["@msgpackr-extract/msgpackr-extract-linux-arm64@3.0.4", "", { "os": "linux", "cpu": "arm64" }, "sha512-dgX0P/9wGPJeHFBG+ZmhgE6bmtMt7NP5CRBGyyktpopdk/mW4POnrpQsSLtKI1dwpc+pPLuXHDh6vvskyQE/sw=="],
"@msgpackr-extract/msgpackr-extract-linux-x64": ["@msgpackr-extract/msgpackr-extract-linux-x64@3.0.4", "", { "os": "linux", "cpu": "x64" }, "sha512-8TNXMEjJc3QEy7R/x1INhgiU+XakDAFUzBhaz7+Rbrs8NH5UQeHQxxmzsSBJGyV6I1jW79undiQm8tOI+D+8FQ=="],
"@msgpackr-extract/msgpackr-extract-win32-x64": ["@msgpackr-extract/msgpackr-extract-win32-x64@3.0.4", "", { "os": "win32", "cpu": "x64" }, "sha512-CmCXPQrkbwExx3j946/PtHWHbYJiCRBRDl4BlkRQcJB/YOwQxJRTpoo7aTsortjgoJ1x7opzTSxn7C+ASSLVjQ=="],
"@npmcli/agent": ["@npmcli/agent@4.0.2", "", { "dependencies": { "agent-base": "^7.1.0", "http-proxy-agent": "^7.0.0", "https-proxy-agent": "^7.0.1", "lru-cache": "^11.2.1", "socks-proxy-agent": "^8.0.3" } }, "sha512-EUEuWAxnL07Sp5/iC/1X6Xj+XThUvnbei9zfRWZdEXa7lss9RTHMhAHBeg+MZ5To9s/gGaSI+UwZTPdYMvKSeg=="], "@npmcli/agent": ["@npmcli/agent@4.0.2", "", { "dependencies": { "agent-base": "^7.1.0", "http-proxy-agent": "^7.0.0", "https-proxy-agent": "^7.0.1", "lru-cache": "^11.2.1", "socks-proxy-agent": "^8.0.3" } }, "sha512-EUEuWAxnL07Sp5/iC/1X6Xj+XThUvnbei9zfRWZdEXa7lss9RTHMhAHBeg+MZ5To9s/gGaSI+UwZTPdYMvKSeg=="],
@@ -202,17 +203,17 @@
"@npmcli/run-script": ["@npmcli/run-script@10.0.4", "", { "dependencies": { "@npmcli/node-gyp": "^5.0.0", "@npmcli/package-json": "^7.0.0", "@npmcli/promise-spawn": "^9.0.0", "node-gyp": "^12.1.0", "proc-log": "^6.0.0" } }, "sha512-mGUWr1uMnf0le2TwfOZY4SFxZGXGfm4Jtay/nwAa2FLNAKXUoUwaGwBMNH36UHPtinWfTSJ3nqFQr0091CxVGg=="], "@npmcli/run-script": ["@npmcli/run-script@10.0.4", "", { "dependencies": { "@npmcli/node-gyp": "^5.0.0", "@npmcli/package-json": "^7.0.0", "@npmcli/promise-spawn": "^9.0.0", "node-gyp": "^12.1.0", "proc-log": "^6.0.0" } }, "sha512-mGUWr1uMnf0le2TwfOZY4SFxZGXGfm4Jtay/nwAa2FLNAKXUoUwaGwBMNH36UHPtinWfTSJ3nqFQr0091CxVGg=="],
"@opencode/ai": ["@opencode/ai@2.0.22", "", { "dependencies": { "@aws-sdk/credential-providers": "3.1057.0", "@opencode/schema": "2.0.22", "@smithy/eventstream-codec": "4.2.14", "@smithy/util-utf8": "4.2.2", "aws4fetch": "1.0.20", "effect": "4.0.0-rc.112", "google-auth-library": "10.5.0" } }, "sha512-wdD2ut4G/areDkA9bYizYiho6C1sRQ6mPqMSji93XzadavbkIcbhU/VyodOmExtZtOg2IjheJCUVCpDXQ8n8FA=="], "@opencode/ai": ["@opencode/ai@2.0.27", "", { "dependencies": { "@aws-sdk/credential-providers": "3.1057.0", "@opencode/schema": "2.0.27", "@smithy/eventstream-codec": "4.2.14", "@smithy/util-utf8": "4.2.2", "aws4fetch": "1.0.20", "effect": "4.0.1", "google-auth-library": "10.5.0" } }, "sha512-RiVtSBo1veffbDnrWo++04XdlcSEzqCAxo1TWDtG/5fZSjWLuiII6OT6Fo/N8ScU/awy9X3omfvun1aq4Lfttw=="],
"@opencode/client": ["@opencode/client@2.0.22", "", { "dependencies": { "@opencode/protocol": "2.0.22", "@opencode/schema": "2.0.22" }, "peerDependencies": { "effect": "4.0.0-rc.112", "solid-js": ">=1.9.0" }, "optionalPeers": ["effect", "solid-js"] }, "sha512-FJKugH301QHlV/rGL8TvgL3ly+toVlww+TP+YdVTKQWytQvjLoUdYtvvm+Iq5k6pN6Ki3ybE/08E8Cg+e6Opbg=="], "@opencode/client": ["@opencode/client@2.0.27", "", { "dependencies": { "@opencode/protocol": "2.0.27", "@opencode/schema": "2.0.27" }, "peerDependencies": { "effect": "4.0.1", "solid-js": ">=1.9.0" }, "optionalPeers": ["effect", "solid-js"] }, "sha512-RqJodg+QsUgqqJVo+b2PGk2w96l7424nM4BijUSb49Iep9IyUfjDH3zfii4OGfCsmZkNCYK83Mgk9e9EeRA1iQ=="],
"@opencode/plugin": ["@opencode/plugin@2.0.22", "", { "dependencies": { "@ai-sdk/provider": "3.0.8", "@opencode/ai": "2.0.22", "@opencode/client": "2.0.22", "@opencode/protocol": "2.0.22", "@opencode/schema": "2.0.22", "@opencode/util": "2.0.22", "@standard-schema/spec": "1.1.0", "effect": "4.0.0-rc.112", "zod": "4.1.8" }, "peerDependencies": { "@opencode/theme": "2.0.22", "@opentui/core": ">=0.5.14", "@opentui/solid": ">=0.5.14", "solid-js": ">=1.9.0" }, "optionalPeers": ["@opencode/theme", "@opentui/core", "@opentui/solid", "solid-js"] }, "sha512-EJyr+qA+I41rfJqE2zfyKL2qNez+wE8QkNwXf5TddEKIPmL8FUvYMVT5lLhbnXyOGTDxsEc0/8bX7ErQfX5/Rg=="], "@opencode/plugin": ["@opencode/plugin@2.0.27", "", { "dependencies": { "@ai-sdk/provider": "3.0.8", "@opencode/ai": "2.0.27", "@opencode/client": "2.0.27", "@opencode/protocol": "2.0.27", "@opencode/schema": "2.0.27", "@opencode/util": "2.0.27", "effect": "4.0.1" }, "peerDependencies": { "@opencode/theme": "2.0.27", "@opentui/core": ">=0.5.17", "@opentui/solid": ">=0.5.17", "solid-js": ">=1.9.0" }, "optionalPeers": ["@opencode/theme", "@opentui/core", "@opentui/solid", "solid-js"] }, "sha512-TlK5PhHDCIieQEt/zjPlb/5BYbsyQnMSjXWhqL3rYjobKIauUNxdG+UCSCaLyQPhS9ab5zThg9v9tF6xiSyFyw=="],
"@opencode/protocol": ["@opencode/protocol@2.0.22", "", { "dependencies": { "@opencode/schema": "2.0.22", "effect": "4.0.0-rc.112" } }, "sha512-Ws3DKQW/rlBDwNz2cPE9+nGwbw7pgnZ+5bzgoHWCWxgTZmxdFulmLP05lxR+PPwMklUwzOGoUXFIzODPZ27WfA=="], "@opencode/protocol": ["@opencode/protocol@2.0.27", "", { "dependencies": { "@opencode/schema": "2.0.27", "effect": "4.0.1" } }, "sha512-t1j+m5T3TBusHaL58t6gSSQQEFoi+qjVyQ0Eta/4mLeZLJDqSV8BNN6N93GFpV2MJ1iBpGmrH0C02n2Q+nDHfw=="],
"@opencode/schema": ["@opencode/schema@2.0.22", "", { "dependencies": { "@standard-schema/spec": "1.1.0", "effect": "4.0.0-rc.112" } }, "sha512-PTqTrx3QHhlRL5ypfoMnSzXDU8XB2+vtKX8QKwIHP7B1F1yw90LN0XTmGP82k9rYoEcERq0TLuL+ykAsYJXJdA=="], "@opencode/schema": ["@opencode/schema@2.0.27", "", { "dependencies": { "@standard-schema/spec": "1.1.0", "effect": "4.0.1" } }, "sha512-BxGuiIFo503tW6UYxoBrrgjyczEvPiU3fDn45FxUHtmZgBC8kFE+ldI56ab8kV0Lu5C94ZKOniRb2bWqDu4tAg=="],
"@opencode/util": ["@opencode/util@2.0.22", "", { "dependencies": { "@effect/opentelemetry": "4.0.0-rc.112", "@effect/platform-node": "4.0.0-rc.112", "@effect/platform-node-shared": "4.0.0-rc.112", "@npmcli/arborist": "9.4.0", "@npmcli/config": "10.8.1", "@opentelemetry/api": "1.9.0", "@opentelemetry/api-logs": "0.219.0", "@opentelemetry/context-async-hooks": "2.8.0", "@opentelemetry/exporter-trace-otlp-http": "0.219.0", "@opentelemetry/resources": "2.8.0", "@opentelemetry/sdk-logs": "0.219.0", "@opentelemetry/sdk-metrics": "2.8.0", "@opentelemetry/sdk-trace-base": "2.8.0", "@opentelemetry/sdk-trace-node": "2.8.0", "cross-spawn": "7.0.6", "effect": "4.0.0-rc.112", "glob": "13.0.5", "mime-types": "3.0.2", "minimatch": "10.2.5", "npm-package-arg": "13.0.2", "open": "11.0.4", "pacote": "21.5.1" } }, "sha512-nipMu7ZAM9gCOKwH06eqAUVgATR+5XbqXEKSN+ECYLgm9PStsmxraxDN93gJLV3bYzpR+9Ow0Be/s0ZYKUxPKg=="], "@opencode/util": ["@opencode/util@2.0.27", "", { "dependencies": { "@effect/opentelemetry": "4.0.1", "@effect/platform-node": "4.0.1", "@effect/platform-node-shared": "4.0.1", "@npmcli/arborist": "9.4.0", "@npmcli/config": "10.8.1", "@opentelemetry/api": "1.9.0", "@opentelemetry/api-logs": "0.219.0", "@opentelemetry/context-async-hooks": "2.8.0", "@opentelemetry/exporter-trace-otlp-http": "0.219.0", "@opentelemetry/resources": "2.8.0", "@opentelemetry/sdk-logs": "0.219.0", "@opentelemetry/sdk-metrics": "2.8.0", "@opentelemetry/sdk-trace-base": "2.8.0", "@opentelemetry/sdk-trace-node": "2.8.0", "cross-spawn": "7.0.6", "effect": "4.0.1", "glob": "13.0.5", "mime-types": "3.0.2", "minimatch": "10.2.5", "npm-package-arg": "13.0.2", "open": "11.0.4", "pacote": "21.5.1" } }, "sha512-2TIEAJsX4UsyV9CHSk+/6jHWrEllgomgD0WQ8Ne+SN4xlmN9cGUvZo/Jgk0XrZZXSmADDOIER2HLcaI0tAr22A=="],
"@opentelemetry/api": ["@opentelemetry/api@1.9.0", "", {}, "sha512-3giAOQvZiH5F9bMlMiv8+GSPMeqg0dbaeo58/0SlA9sxSqZhnUtxzX9/2FzyhS9sWQf5S0GJE0AKBrFqjpeYcg=="], "@opentelemetry/api": ["@opentelemetry/api@1.9.0", "", {}, "sha512-3giAOQvZiH5F9bMlMiv8+GSPMeqg0dbaeo58/0SlA9sxSqZhnUtxzX9/2FzyhS9sWQf5S0GJE0AKBrFqjpeYcg=="],
@@ -240,103 +241,193 @@
"@opentelemetry/semantic-conventions": ["@opentelemetry/semantic-conventions@1.43.0", "", {}, "sha512-eSYWTm620tTk45EKSedaUL8MFYI8hW164hIXsgIHyxu3VobUB3fFCu5t0hQby6OoWRPsG1KkKUG2M5UadiLiVg=="], "@opentelemetry/semantic-conventions": ["@opentelemetry/semantic-conventions@1.43.0", "", {}, "sha512-eSYWTm620tTk45EKSedaUL8MFYI8hW164hIXsgIHyxu3VobUB3fFCu5t0hQby6OoWRPsG1KkKUG2M5UadiLiVg=="],
"@opentui/core": ["@opentui/core@0.5.14", "", { "dependencies": { "bun-ffi-structs": "0.3.1", "diff": "9.0.0", "marked": "17.0.1", "string-width": "7.2.0", "strip-ansi": "7.1.2" }, "optionalDependencies": { "@opentui/core-darwin-arm64": "0.5.14", "@opentui/core-darwin-x64": "0.5.14", "@opentui/core-linux-arm64": "0.5.14", "@opentui/core-linux-arm64-musl": "0.5.14", "@opentui/core-linux-x64": "0.5.14", "@opentui/core-linux-x64-musl": "0.5.14", "@opentui/core-win32-arm64": "0.5.14", "@opentui/core-win32-x64": "0.5.14" }, "peerDependencies": { "web-tree-sitter": "0.25.10" } }, "sha512-tfQ+PWQyeBnYloB3diEcPqbILv14xemH5jjAEICfPuyNDtGBqrjhUtThrhbvFRuPMcj6IEeXrAk6VE8e91h0kg=="], "@opentui/core": ["@opentui/core@0.6.1", "", { "dependencies": { "bun-ffi-structs": "0.3.1", "diff": "9.0.0", "marked": "17.0.1", "string-width": "7.2.0" }, "optionalDependencies": { "@opentui/core-darwin-arm64": "0.6.1", "@opentui/core-darwin-x64": "0.6.1", "@opentui/core-linux-arm64": "0.6.1", "@opentui/core-linux-arm64-musl": "0.6.1", "@opentui/core-linux-x64": "0.6.1", "@opentui/core-linux-x64-musl": "0.6.1", "@opentui/core-win32-arm64": "0.6.1", "@opentui/core-win32-x64": "0.6.1" }, "peerDependencies": { "web-tree-sitter": "0.25.10" } }, "sha512-zDb6HyzprBp9AJRk/zRx9jRPKsyd3zEJNN3WUOrTqFzjf+PIytW9+s77tONM5Pb57QoLvnTVeM6evFzXV831ww=="],
"@opentui/core-darwin-arm64": ["@opentui/core-darwin-arm64@0.5.14", "", { "os": "darwin", "cpu": "arm64" }, "sha512-wWmw41wRMBoI0lN9mgyzGRwYujwwfNkBP6jYM99k4Bx2XkeSZ3sCeu5bwX9vEJPYqjiBShbDhc0NnVSP7NwzVg=="], "@opentui/core-darwin-arm64": ["@opentui/core-darwin-arm64@0.6.1", "", { "os": "darwin", "cpu": "arm64" }, "sha512-yU5TdLeacaIZi+cwD12fbfqwgcFQHzJ9xAdZHlWodIZAMXqhZJuOuI9o406I6axiSYyl7NTA9dOPJBkcc6UHXQ=="],
"@opentui/core-darwin-x64": ["@opentui/core-darwin-x64@0.5.14", "", { "os": "darwin", "cpu": "x64" }, "sha512-7smHKDH8IhUaBsgYuAClMl2mHWu+yjpMrtdw3wEvBVtCzKMrHi/TJ5PtydO+IfUzR3BXpVubdbR1irD8BTcR/w=="], "@opentui/core-darwin-x64": ["@opentui/core-darwin-x64@0.6.1", "", { "os": "darwin", "cpu": "x64" }, "sha512-1ZX1W9amrGxq3yvZqgV/ejaBqb7rj/4UjTQ8Fm8oekDz+birTpxtTj2CBU1vP63OkNxwIL1TlPdlw2McVLOdhA=="],
"@opentui/core-linux-arm64": ["@opentui/core-linux-arm64@0.5.14", "", { "os": "linux", "cpu": "arm64" }, "sha512-xH1hP+NaLySEJeZkl21NlkZBMddMfQ1jU8NeX1AEBc2GNBOvDXU4Ud/xw87SrAvU1xG9K7/9C4oy4AmIMEpVGg=="], "@opentui/core-linux-arm64": ["@opentui/core-linux-arm64@0.6.1", "", { "os": "linux", "cpu": "arm64" }, "sha512-KUkwDY8ZyNtr49G04iMgK9IDfOTzHk/J5DWXdvdzwqUpBuBZYSBDh8OLxSEx8f/bpDFhO/PFLQKo0XPlDtiKOw=="],
"@opentui/core-linux-arm64-musl": ["@opentui/core-linux-arm64-musl@0.5.14", "", { "os": "linux", "cpu": "arm64" }, "sha512-mnBBAuTb92NiRLAjOD755tS8/tNQemDztbg9tMvoCT90G52FtVrRb31Ge6OrYqfm0c9DkZGhEBOhunsId/4zSA=="], "@opentui/core-linux-arm64-musl": ["@opentui/core-linux-arm64-musl@0.6.1", "", { "os": "linux", "cpu": "arm64" }, "sha512-kIyHCHFdceIuteA9QX0bnGA2TNggQRk+t2xqo80TI4NDbcBZL4AHnUn0HcPh53PlHRNZjFf6IhwY+EEiultq1Q=="],
"@opentui/core-linux-x64": ["@opentui/core-linux-x64@0.5.14", "", { "os": "linux", "cpu": "x64" }, "sha512-Hkk4kaDGMcn9bmJFJPW3/QOGGbPuWe3sCFV/CkiVb4+bCvcTm7EXQr4QTAA63BYy2dKE5bUFUi1zZlyeMkWpnA=="], "@opentui/core-linux-x64": ["@opentui/core-linux-x64@0.6.1", "", { "os": "linux", "cpu": "x64" }, "sha512-fwpZ3iCfKmvFb98m05LuGEZRklnT8h0A03pnYv95b52lixTpXbkmQfh0iw7PHHYOOS3cfDxK7sPqleQO7FAhgQ=="],
"@opentui/core-linux-x64-musl": ["@opentui/core-linux-x64-musl@0.5.14", "", { "os": "linux", "cpu": "x64" }, "sha512-ngJ+U2grOGEteeQvZdAJNqn09M+At5mfWInauK5aS427bea1yLo+e6hor/CRmbn9SxEEF+SwoyekaOrLPWyU7w=="], "@opentui/core-linux-x64-musl": ["@opentui/core-linux-x64-musl@0.6.1", "", { "os": "linux", "cpu": "x64" }, "sha512-DsrOEM+i8un4NoeI21iM1p4oK390mFHBXPr4JQHwYekTGXNTtk+fCLdy1TDvciijFjb0phaVq4ISoGhO3ewzHA=="],
"@opentui/core-win32-arm64": ["@opentui/core-win32-arm64@0.5.14", "", { "os": "win32", "cpu": "arm64" }, "sha512-T9kNqKXg2jysmTsyyZ1A8LBQotFBM+iPjzyRslxyexqrs8a1UcmxbApEo+COtxQuqukMTbvwyqEdAT8vcmxEkQ=="], "@opentui/core-win32-arm64": ["@opentui/core-win32-arm64@0.6.1", "", { "os": "win32", "cpu": "arm64" }, "sha512-m/4fLjCxNzyzTuLAK0yKj85EwS44nl+5p1lG5IEKB7GNi0DeGIonEXEu7kb902OPWlUxGwDOFX2RIwou0UvjGQ=="],
"@opentui/core-win32-x64": ["@opentui/core-win32-x64@0.5.14", "", { "os": "win32", "cpu": "x64" }, "sha512-mqKSkab8VdMLSmMdocna7+BTyMoIutkVXOV9lfmPrBO2g7Np5c6c4SJ4QIVZqPvast11XyT0/7FfXOYLKAS72w=="], "@opentui/core-win32-x64": ["@opentui/core-win32-x64@0.6.1", "", { "os": "win32", "cpu": "x64" }, "sha512-2A0ksCH9V3CLrLEhR5EuFg5dMUrDK8LnO6ci8n/FMoZ9KbCd5Mj+i0f7hHRK6Q54LZtZOHU5aGXZhcRK1YH7rA=="],
"@opentui/solid": ["@opentui/solid@0.5.14", "", { "dependencies": { "@babel/core": "7.28.0", "@babel/preset-typescript": "7.27.1", "@opentui/core": "0.5.14", "babel-plugin-module-resolver": "5.0.2", "babel-preset-solid": "1.9.12", "entities": "7.0.1", "s-js": "^0.4.9" }, "peerDependencies": { "solid-js": "1.9.12" } }, "sha512-bBRl34mZ0wFGhjHX6y1VNiZmJ3DSm2DVPm0PNSVDpvq9qxRHuywEPTCn/Lgte0C9450tgf11cDqcE3pR9cZwVA=="], "@opentui/solid": ["@opentui/solid@0.6.1", "", { "dependencies": { "@babel/core": "7.29.7", "@babel/preset-typescript": "7.27.1", "@opentui/core": "0.6.1", "babel-plugin-module-resolver": "5.0.2", "babel-preset-solid": "1.9.12", "entities": "7.0.1", "s-js": "^0.4.9" }, "peerDependencies": { "solid-js": "1.9.12" } }, "sha512-pdVwX80KjBY3fI0khiZEKRBWqZKCTzoIrMvf59vus/0bHal/pKTkOHTMOu5vsZ1NH2QvMjecDxwmXyn4SwqtSA=="],
"@oxfmt/binding-android-arm-eabi": ["@oxfmt/binding-android-arm-eabi@0.71.0", "", { "os": "android", "cpu": "arm" }, "sha512-l31EyBfB4egJeFua11aQFEUE9nnDtfpWCadqQovm0WL30t/yUHtdFl/5HyFXvd5xT8Ewh3U4TI9f30GowrQ1fw=="], "@oxc-parser/binding-android-arm-eabi": ["@oxc-parser/binding-android-arm-eabi@0.153.0", "", { "os": "android", "cpu": "arm" }, "sha512-BcWu25dMwMjHpaDCEidmpAi7rGg1qZoihJeUUH9bD55pVZ0z4Wa5CQgqSTo0R41H81oozisQKW3WqvAN2m77IQ=="],
"@oxfmt/binding-android-arm64": ["@oxfmt/binding-android-arm64@0.71.0", "", { "os": "android", "cpu": "arm64" }, "sha512-E8q39SUZzSXQ08oZoFoTkxRADkdBNgL6De4qgZYr2O4JCunwqrZwAyCebxIF3yVHBafHM30WUkhTkDi+jNYZOw=="], "@oxc-parser/binding-android-arm64": ["@oxc-parser/binding-android-arm64@0.153.0", "", { "os": "android", "cpu": "arm64" }, "sha512-9l5rdp2DhRqVriBHsNpu5cEf+hizZ4B58rt93HzyQEBUgZiC6qe2oFpaAAnXGCxHGnQExI1s7S2G0QhFacUZ6w=="],
"@oxfmt/binding-darwin-arm64": ["@oxfmt/binding-darwin-arm64@0.71.0", "", { "os": "darwin", "cpu": "arm64" }, "sha512-pTteTrN88DicrmJ3DocBmpNDa6Umfh0iveEG8rnAlDFQpclmtDS7hnIvZbIEV9mDO0Ot1U0sjtoJQ1itd/ZMhQ=="], "@oxc-parser/binding-darwin-arm64": ["@oxc-parser/binding-darwin-arm64@0.153.0", "", { "os": "darwin", "cpu": "arm64" }, "sha512-EcpsyRXHhENDpekpG4QNaSZj2F/BAz4Gh4o89zZwNss86R8KyRSQ6sXbAj74Xyeb4z3j/yBZZ6joQZhraIWyfw=="],
"@oxfmt/binding-darwin-x64": ["@oxfmt/binding-darwin-x64@0.71.0", "", { "os": "darwin", "cpu": "x64" }, "sha512-G5melRC3IiNEgXlNKJhSExJYQGAQIppHFp2cl/wFrqQcEwmc4k4TkrHaFTR29SDudjoW5AZq5cXPGJDqtlH/Yg=="], "@oxc-parser/binding-darwin-x64": ["@oxc-parser/binding-darwin-x64@0.153.0", "", { "os": "darwin", "cpu": "x64" }, "sha512-hlj80HUQy07/2lYp6rmxH+3u+H2ik3rjLR52CUdPApxmZCNxASDUf/+ykTzAHS/fehftmVMATKvPaWmuLHuasg=="],
"@oxfmt/binding-freebsd-x64": ["@oxfmt/binding-freebsd-x64@0.71.0", "", { "os": "freebsd", "cpu": "x64" }, "sha512-Hb1P5yKb9aiH2VSbm3Ml37mKjzqpunYet9krw/YK7V5JsAUJDQlju3Yk/dEqQvJD/usBvpi01Vbk9ZDNo0a8Cw=="], "@oxc-parser/binding-freebsd-x64": ["@oxc-parser/binding-freebsd-x64@0.153.0", "", { "os": "freebsd", "cpu": "x64" }, "sha512-fWRcv2pMSh1qtez46MOu8vuUJ5fiaQZPHSphbWulbL7SHBMKfRgZl2PzjXZYQJbq7NEXyXbgIuIuUm+/Rmkv8w=="],
"@oxfmt/binding-linux-arm-gnueabihf": ["@oxfmt/binding-linux-arm-gnueabihf@0.71.0", "", { "os": "linux", "cpu": "arm" }, "sha512-r7n4JEO+rkp0kaP3ia+0hv6FzK3PQIHqaF0jxGuhjJ4JHVX9ZVRbgpDVDW+OloyuJsRWpWFDKIHe8gfl1p/4mQ=="], "@oxc-parser/binding-linux-arm-gnueabihf": ["@oxc-parser/binding-linux-arm-gnueabihf@0.153.0", "", { "os": "linux", "cpu": "arm" }, "sha512-paZeUK1GXShl/bOJQET1/8AQxayFeuN4SIWAkgTRxE7ZQwv9uYSB2n0648smygP22N7jcI3zxAm0Z+ALNiIKxg=="],
"@oxfmt/binding-linux-arm-musleabihf": ["@oxfmt/binding-linux-arm-musleabihf@0.71.0", "", { "os": "linux", "cpu": "arm" }, "sha512-EEynTF4nakgqDhVCmd3cHQCmTcw0BM8ea6eHigTdtZ3yxdsBNv+dYkt+OpDDZx1n/jzjI7J+Ht7IgkqFWuJUxQ=="], "@oxc-parser/binding-linux-arm-musleabihf": ["@oxc-parser/binding-linux-arm-musleabihf@0.153.0", "", { "os": "linux", "cpu": "arm" }, "sha512-qFPp5NwMf4K1C0O+DCVGmcbOaYyYAq98Rvv9p4VSfb777iUwlJCqMUxf6QG9N5f5ls4TEX6LitOZHi+6GL6rYQ=="],
"@oxfmt/binding-linux-arm64-gnu": ["@oxfmt/binding-linux-arm64-gnu@0.71.0", "", { "os": "linux", "cpu": "arm64" }, "sha512-7VgJIrywCwR/G6YMv+HqsccUt8Z4q4mbM2xR+Ry/6AeMk4pCmZ9aO4Srd3mmrvVu8PsCZGP7oHEHSXWTmyloaQ=="], "@oxc-parser/binding-linux-arm64-gnu": ["@oxc-parser/binding-linux-arm64-gnu@0.153.0", "", { "os": "linux", "cpu": "arm64" }, "sha512-oufEhZCX7saeo27Logra8cvBR1jQ/yw2zUI2hHmWw3qA/XYqEW31FOvLQBv7DWN32NjVdlcaP11WBBZTJo4k9g=="],
"@oxfmt/binding-linux-arm64-musl": ["@oxfmt/binding-linux-arm64-musl@0.71.0", "", { "os": "linux", "cpu": "arm64" }, "sha512-AOCaminv/+fhinUXKvtPZT4POhNYmN9GfvaJdgJa1AbvuzClWGwDIXfJg8eu3sYaVL2B68jNvmS7LZGAYa0z3A=="], "@oxc-parser/binding-linux-arm64-musl": ["@oxc-parser/binding-linux-arm64-musl@0.153.0", "", { "os": "linux", "cpu": "arm64" }, "sha512-zXYzuAqng85h6+LI3iRm0zeMLX1/K2z41ZAMWxVRgt0D10VvZUaV5q+TEB46KDhoKBpdexoTLC6QoB/EiP2oqQ=="],
"@oxfmt/binding-linux-ppc64-gnu": ["@oxfmt/binding-linux-ppc64-gnu@0.71.0", "", { "os": "linux", "cpu": "ppc64" }, "sha512-0SHxuaa4QRLM7jfsd8wc6L7KdLg+FR6/ah9k1eAvcrK/Sni7oxchMvsjwUsyakVAta+wBVDkjJTr7/RFU0uUGA=="], "@oxc-parser/binding-linux-ppc64-gnu": ["@oxc-parser/binding-linux-ppc64-gnu@0.153.0", "", { "os": "linux", "cpu": "ppc64" }, "sha512-J7+NLwLEzdkKM9cKyPHH/AjXXstWOs98KYgLrPPnO4N9MO8EZRBfPNnBcS3S67uMOBkRpUmCl2FhRnWdQ5CbBA=="],
"@oxfmt/binding-linux-riscv64-gnu": ["@oxfmt/binding-linux-riscv64-gnu@0.71.0", "", { "os": "linux", "cpu": "none" }, "sha512-UNKj1+rPorTK6uSlQzpN96vDNbHbL/63zcpznweo0ImQdkDdtQCS7G3puxX++2cESPKT2B56Y6DICUmFTJde5A=="], "@oxc-parser/binding-linux-riscv64-gnu": ["@oxc-parser/binding-linux-riscv64-gnu@0.153.0", "", { "os": "linux", "cpu": "none" }, "sha512-sD0K11GQTLWylln54nPMMTtgmBbQrR5It/vMpZpy/fogiw8O2AvIE+9LuWUXddrWk9zvFIHGRcSgFn4IHOfoYg=="],
"@oxfmt/binding-linux-riscv64-musl": ["@oxfmt/binding-linux-riscv64-musl@0.71.0", "", { "os": "linux", "cpu": "none" }, "sha512-5cVXKj7a0mWu7GU6/bZgNyv+KtLgM5S9cnT26Os2/abj8pK/bklHsbdYEHGLLniGjNYkyzwem8mZciPCaDtilw=="], "@oxc-parser/binding-linux-riscv64-musl": ["@oxc-parser/binding-linux-riscv64-musl@0.153.0", "", { "os": "linux", "cpu": "none" }, "sha512-7L66uql2BhvSz51LwfExjOdn6et/ydTiQxl23VApdKzJhTc3TczA1Qt6VR/UcvlQrL2ZbytIJb447vh7p5wmUw=="],
"@oxfmt/binding-linux-s390x-gnu": ["@oxfmt/binding-linux-s390x-gnu@0.71.0", "", { "os": "linux", "cpu": "s390x" }, "sha512-lNpcMuZvyU1V/CY5h19hac03m4E4PLSYRckcxZOynSPojI4Mwt6nEu9wT/gVf0bclH3xGEWjwqApnSTgjkd2oA=="], "@oxc-parser/binding-linux-s390x-gnu": ["@oxc-parser/binding-linux-s390x-gnu@0.153.0", "", { "os": "linux", "cpu": "s390x" }, "sha512-hXV3T7mNyrPR19rbPYkglkQJtoM/UNo/xwbZeeqdAxEg8PXgb4LXXuxPpGgI4bzRRCWwLUxdDSS58xIyC2u1TA=="],
"@oxfmt/binding-linux-x64-gnu": ["@oxfmt/binding-linux-x64-gnu@0.71.0", "", { "os": "linux", "cpu": "x64" }, "sha512-5/Z6pUewQpknXqC4/ykK6Zc6RiteAnPem1Ci7K1RZLVF6w6MMjwHjR4vsjijW4Czidgv7HKeVglGjElADliT9w=="], "@oxc-parser/binding-linux-x64-gnu": ["@oxc-parser/binding-linux-x64-gnu@0.153.0", "", { "os": "linux", "cpu": "x64" }, "sha512-Da8Vqs1xdtoDYtEjmozD7wGgJeLBQkMbR0WUBECOSxodyX5DXy8ySlvJWbukyO2Q0+TM9EK+4LT6tbq0jCg4hQ=="],
"@oxfmt/binding-linux-x64-musl": ["@oxfmt/binding-linux-x64-musl@0.71.0", "", { "os": "linux", "cpu": "x64" }, "sha512-uVdG2N/4GEbOeljpQ+xv+NeEwJWJGj0WaxSiSYnoiqIYy3RWrWd3rGUmxWXP1A8+ferNvvwFoDAtvgsDUvBuSw=="], "@oxc-parser/binding-linux-x64-musl": ["@oxc-parser/binding-linux-x64-musl@0.153.0", "", { "os": "linux", "cpu": "x64" }, "sha512-zGAPxNTIIw6X5WyTRscIFE/oDjpdNtrrl32ing6NOXdGjzRucadnxBilexLdeYQ9YxixF93GujpXyQ0jw7ddSg=="],
"@oxfmt/binding-openharmony-arm64": ["@oxfmt/binding-openharmony-arm64@0.71.0", "", { "os": "none", "cpu": "arm64" }, "sha512-1LwEZmSDRFKeBaGd/Hgj2xI3SmgGFpF4YtgkSx0sTYdTiZfHWbcFvRIBjL1YiDNdQd9Khda3Ij8CoqBULjskDg=="], "@oxc-parser/binding-openharmony-arm64": ["@oxc-parser/binding-openharmony-arm64@0.153.0", "", { "os": "none", "cpu": "arm64" }, "sha512-GoHzpqP5XyPIp9DHokoEdCp+K4UPl/h1neFj1uXnUB3pJYyOQ7NOhFVOttNUgCGcj2eywAvu5cRivTOSq4S10g=="],
"@oxfmt/binding-win32-arm64-msvc": ["@oxfmt/binding-win32-arm64-msvc@0.71.0", "", { "os": "win32", "cpu": "arm64" }, "sha512-5tplmkeMXmza3PUptJQy25wCPJbIAg5g5r7zs+DI+7eEYOqbY+7roMdSH2zbDvv1Pb4oTDJ6NWYx9IRxBxXwhQ=="], "@oxc-parser/binding-win32-arm64-msvc": ["@oxc-parser/binding-win32-arm64-msvc@0.153.0", "", { "os": "win32", "cpu": "arm64" }, "sha512-xGcy12tO9k7zFbeyQzEuilfWfQpyRq23/fLPfN3wjSWuWv58k46fQT1hsO1KFNykZuVGW9xSJE/z592TmAoSDA=="],
"@oxfmt/binding-win32-ia32-msvc": ["@oxfmt/binding-win32-ia32-msvc@0.71.0", "", { "os": "win32", "cpu": "ia32" }, "sha512-T2LWgh3Vx4PYDjtcqRRGDyCsVxeF/VE5xTpUQiCm65bNLwMpRnJYj6Hlkf6qRM3+jxCIOqHD1kVHNQCCiAVMNQ=="], "@oxc-parser/binding-win32-ia32-msvc": ["@oxc-parser/binding-win32-ia32-msvc@0.153.0", "", { "os": "win32", "cpu": "ia32" }, "sha512-o1ykUjWncvXX6N5a4KebgLjtD8zRui+f1llMhSGoSC9oP2KOqapRpdwmZ3NcNG0axFouwVKmhGBjd+IhA8BksA=="],
"@oxfmt/binding-win32-x64-msvc": ["@oxfmt/binding-win32-x64-msvc@0.71.0", "", { "os": "win32", "cpu": "x64" }, "sha512-L06SVp7Hu1EQTkh3+PHnKK26dxVbEpOG2InMwCooTE4MA437b5FgfTleCCiGn4ykISHnHU6UHaIg7SiMO7rBHA=="], "@oxc-parser/binding-win32-x64-msvc": ["@oxc-parser/binding-win32-x64-msvc@0.153.0", "", { "os": "win32", "cpu": "x64" }, "sha512-gxQz7G96Up136fd+2zWrP+o6FYGs9NO4Dyv55IoeJFJUDwLFHcLYY11hhA5wQKs0HoM57Q8esQ3nEVhnCdsjAQ=="],
"@oxlint/binding-android-arm-eabi": ["@oxlint/binding-android-arm-eabi@1.86.0", "", { "os": "android", "cpu": "arm" }, "sha512-63Ozq6yQn79B2UxjSZ9huJmI+3/ZPI7hxAe6TyFh9oQL447KnIMoffOdtog+h4KILbQr61ZRvFPW5gYbAUgpgQ=="], "@oxc-project/types": ["@oxc-project/types@0.153.0", "", {}, "sha512-jSNrRIyvPVLL5E1z/tS5zLAprosGz/FuI1PWwEOz59j3E4TTTzSpqKb/RDGqJhhW0QHYISGXxq582wGx6T11Tw=="],
"@oxlint/binding-android-arm64": ["@oxlint/binding-android-arm64@1.86.0", "", { "os": "android", "cpu": "arm64" }, "sha512-JdLGp44phbf/0Du236Dt06yfK6Qw8xhTFeDvHJdjk167r59OfP5+BL31mgMYVnswS8e+j6tFuccSY0QDC/lgCw=="], "@oxc-resolver/binding-android-arm-eabi": ["@oxc-resolver/binding-android-arm-eabi@11.24.2", "", { "os": "android", "cpu": "arm" }, "sha512-y09e0L0SRI2OA2tUIrjBgoV3eH5hvUKXNkJqXmNo5V2WxIjyC7I7aJfRLMEVpA8yi95f90gFDvO0VMgrDw+vwA=="],
"@oxlint/binding-darwin-arm64": ["@oxlint/binding-darwin-arm64@1.86.0", "", { "os": "darwin", "cpu": "arm64" }, "sha512-h+vkOr4ik6KLFCXdtNVEj9xfnXfNUpPoF95QjORdhiSpLqQePzcN81kGHjAgsw1/G7WBWK5KsFKbI2UK8EyzMA=="], "@oxc-resolver/binding-android-arm64": ["@oxc-resolver/binding-android-arm64@11.24.2", "", { "os": "android", "cpu": "arm64" }, "sha512-cl4icWaZFnLdg8m6qtnh5rBMuGbxc/ptStFHLeCNwr+2cZjkjNwQu/jYRS0CHlnPecOJMpuS5M6/BH+0J/YkEg=="],
"@oxlint/binding-darwin-x64": ["@oxlint/binding-darwin-x64@1.86.0", "", { "os": "darwin", "cpu": "x64" }, "sha512-wbglRuH5eKsp68keTOOeKDHU1astWSRYFsh2bwKQTAPb44rD6kVgzYI1ZrAJRTc6/7PH55ZXFCQx0rQXrj0UdA=="], "@oxc-resolver/binding-darwin-arm64": ["@oxc-resolver/binding-darwin-arm64@11.24.2", "", { "os": "darwin", "cpu": "arm64" }, "sha512-At29QEMF6HajbQvgY8K6OXnHD1x9rad74xBEfmCB6ZqCGsdq75aK7tOYcTbOanMy8qdIBrfL3SMr3p/lfSlb9w=="],
"@oxlint/binding-freebsd-x64": ["@oxlint/binding-freebsd-x64@1.86.0", "", { "os": "freebsd", "cpu": "x64" }, "sha512-yTQ7QSOlNfQsrfbeVweTiegQJLKPjUKgXp/JpGiFzza6Hp29S9LAoH77TM3L0RjK39iQRZB5lk5iq2t241Mfag=="], "@oxc-resolver/binding-darwin-x64": ["@oxc-resolver/binding-darwin-x64@11.24.2", "", { "os": "darwin", "cpu": "x64" }, "sha512-A5Kqr1EUj4oIL5CF4WRssq/o5P0Y11cwoFouMRmQ7YnC/A8V93nv1nb7aSU8HwcgmXropjLNkVTl4MN87cu28Q=="],
"@oxlint/binding-linux-arm-gnueabihf": ["@oxlint/binding-linux-arm-gnueabihf@1.86.0", "", { "os": "linux", "cpu": "arm" }, "sha512-QYJGy0E2Tv8GAayyBIeHFTwQb8u+zrvrOYrifuDGZDr9ad5XsDhiMScpZymhS9fwWjqrgG2ZUwT4vpY0ISqp4Q=="], "@oxc-resolver/binding-freebsd-x64": ["@oxc-resolver/binding-freebsd-x64@11.24.2", "", { "os": "freebsd", "cpu": "x64" }, "sha512-R5xkRBRRz7ceH/P5Jrc6G7FmdUdgpLYyESFAUDVTNQ9K0sGPxcp4ljiwEwEqsvNcQ4sYbMRrWcHHBCu7ksAJVw=="],
"@oxlint/binding-linux-arm-musleabihf": ["@oxlint/binding-linux-arm-musleabihf@1.86.0", "", { "os": "linux", "cpu": "arm" }, "sha512-oQo83CafLT8p3qh0AGkN0tSUIh5Hm63mfDsoqUmBQUBnSZLNBAbyRaAftfGY5a0cKZ34dG6jAtMYgcY5kZqt5g=="], "@oxc-resolver/binding-linux-arm-gnueabihf": ["@oxc-resolver/binding-linux-arm-gnueabihf@11.24.2", "", { "os": "linux", "cpu": "arm" }, "sha512-k/RuYL4L/R58IBn3wT5ma3Wh4k62bp1eYCFRWCmMsasUOqL+H6sW0VGFadEzKWXFFlz+2uIMoeMk9ySSZJHgbg=="],
"@oxlint/binding-linux-arm64-gnu": ["@oxlint/binding-linux-arm64-gnu@1.86.0", "", { "os": "linux", "cpu": "arm64" }, "sha512-EM6wy5c2UM12qPb7iDJDBAZvHyfEJGH6iosFgaFiaRZpirz99//EHcUyD2KAskz07x1TULuiAtsojf4nvWWksw=="], "@oxc-resolver/binding-linux-arm-musleabihf": ["@oxc-resolver/binding-linux-arm-musleabihf@11.24.2", "", { "os": "linux", "cpu": "arm" }, "sha512-bnHAak3ujYfH5pKk4NieFNbvYvernfoQDgwLddbZ3OtMYrem87/qjlA+u+aKG0oZcqSLGCful/6/CEA+aeAgaA=="],
"@oxlint/binding-linux-arm64-musl": ["@oxlint/binding-linux-arm64-musl@1.86.0", "", { "os": "linux", "cpu": "arm64" }, "sha512-vCiUQb9ZNzZalxYRU4mlZwUqT5f+c7Sk9DwUOplWHtik3Dl4r3DVnUB5tBeRuTAUe6MUVCTylNW7TkkN8J1oTw=="], "@oxc-resolver/binding-linux-arm64-gnu": ["@oxc-resolver/binding-linux-arm64-gnu@11.24.2", "", { "os": "linux", "cpu": "arm64" }, "sha512-vDT3KHgzYp47gmtNOqL2VNhCyl5Zv643eyxm//A68J8DeUGXrvD1pZFiaT4jSfe+RInfnn1R2yVHye4enx6RnA=="],
"@oxlint/binding-linux-ppc64-gnu": ["@oxlint/binding-linux-ppc64-gnu@1.86.0", "", { "os": "linux", "cpu": "ppc64" }, "sha512-T0AzE89yjTYmOhB/hb6i+rWTpe2mYt+xiguBhs9DEPIJTZ1H8OYqsE4VxJHHw2Wlq8Mztwvp2P8NV87ZOuhPRw=="], "@oxc-resolver/binding-linux-arm64-musl": ["@oxc-resolver/binding-linux-arm64-musl@11.24.2", "", { "os": "linux", "cpu": "arm64" }, "sha512-+kMlQvbzfyEYtu5FcjE4p+ttBLpKW4d/AsAsuE69BxV6V4twZJeIQZFfD8gh/wqglY0MkPSezWXQH0jBV13MUw=="],
"@oxlint/binding-linux-riscv64-gnu": ["@oxlint/binding-linux-riscv64-gnu@1.86.0", "", { "os": "linux", "cpu": "none" }, "sha512-s49r0K2f5Oc7fJoMUO1WkdhYK5Ob79uYRwWQ/XNoGysaOq3RUGmGUbHSuXiyydTTA+P9xEdDEnnlZVXiaSJhlw=="], "@oxc-resolver/binding-linux-ppc64-gnu": ["@oxc-resolver/binding-linux-ppc64-gnu@11.24.2", "", { "os": "linux", "cpu": "ppc64" }, "sha512-shjfMhmZ3gq9fv/w7bi3PnZlgOPG+2QAOFf0BJF0EgBSIGZ6PMLN2zbGEblTUYB/NKVDRyYhE2ff3dJ1QqNPkA=="],
"@oxlint/binding-linux-riscv64-musl": ["@oxlint/binding-linux-riscv64-musl@1.86.0", "", { "os": "linux", "cpu": "none" }, "sha512-JIa2tYR8ayb3nvcMSZzn4O/xTy13S7MHllu7cBD+B5qDQXXSRy/Vwk1aNpiTjZmBJGwKCHOy/NvnY5Xcwg27uQ=="], "@oxc-resolver/binding-linux-riscv64-gnu": ["@oxc-resolver/binding-linux-riscv64-gnu@11.24.2", "", { "os": "linux", "cpu": "none" }, "sha512-zGelwFR5oRo+b69k8Lrzun86DyUHzfKN6cnjbR9l7Z7NIRznOE/2ZvPa1IUKqAL2PzAXOdwkfVqNvO1H2RlpAw=="],
"@oxlint/binding-linux-s390x-gnu": ["@oxlint/binding-linux-s390x-gnu@1.86.0", "", { "os": "linux", "cpu": "s390x" }, "sha512-XwXMyBsAuWZkhZU74UNcfQKr1CJJAKnS80dZzOnjl6A4fKcf91IjFgidegQugMHA5SN8ulwDXEDV1yPntjXgQQ=="], "@oxc-resolver/binding-linux-riscv64-musl": ["@oxc-resolver/binding-linux-riscv64-musl@11.24.2", "", { "os": "linux", "cpu": "none" }, "sha512-qxZ1SWCXJY0eyhAlP6Lmo9F2Nrtx7EkYj9oCgL8apDPCwXwCEDA2U697bbT81JIc2IrVjxO4KX6WU2N+oN9Z4w=="],
"@oxlint/binding-linux-x64-gnu": ["@oxlint/binding-linux-x64-gnu@1.86.0", "", { "os": "linux", "cpu": "x64" }, "sha512-C1WjukSyMnr66b+w1/tV8RFVv6d9v0MzDf4p9IxVXknqgmTHBgZh1pccN1eHzFr0b9Tbb3OXoPsAAdAuHAQfeA=="], "@oxc-resolver/binding-linux-s390x-gnu": ["@oxc-resolver/binding-linux-s390x-gnu@11.24.2", "", { "os": "linux", "cpu": "s390x" }, "sha512-sGCecF3cx2DFlH4t/z7ApnOnXqN48p5p5mlHDEnHTAukQa2P+qMVE4CwyWE9W+q/m3QJ7kKfGrIjax31f44oFQ=="],
"@oxlint/binding-linux-x64-musl": ["@oxlint/binding-linux-x64-musl@1.86.0", "", { "os": "linux", "cpu": "x64" }, "sha512-ap6KLmvC38c6MdYzsIh25cXQupqYvjd37tMNftzrX1DCtkX1Gcf2B+S2B17dD4lKa5c5gJog7DQJyDo82PBKyw=="], "@oxc-resolver/binding-linux-x64-gnu": ["@oxc-resolver/binding-linux-x64-gnu@11.24.2", "", { "os": "linux", "cpu": "x64" }, "sha512-k/VlMMcSzMlahb3/fENM4rTlsJ0s3fFROA0KXPBmKggqmTSaE383sl8F3KCOXPLmVsYfW6hCitMhXCEtNeZxxg=="],
"@oxlint/binding-openharmony-arm64": ["@oxlint/binding-openharmony-arm64@1.86.0", "", { "os": "none", "cpu": "arm64" }, "sha512-996Q9w/2GLwNyy5Djs39Jt09aFlr4b7TPhoj7dvo5FHmcyiF68nPz73HNc5UAYKIYeK+M9JzPQ4Wg1r1dXvP6A=="], "@oxc-resolver/binding-linux-x64-musl": ["@oxc-resolver/binding-linux-x64-musl@11.24.2", "", { "os": "linux", "cpu": "x64" }, "sha512-8hbnZyNi97b/8wapYaIF9+t9GmZKBW2vunaOc3h9HGJptH7b7XpvZqOTBSm/MpTjr7H497BlgOaSfLUdhmy2bw=="],
"@oxlint/binding-win32-arm64-msvc": ["@oxlint/binding-win32-arm64-msvc@1.86.0", "", { "os": "win32", "cpu": "arm64" }, "sha512-9uTCHYTknNkug5+46ViSoUMuOuGWK61D87QnblU6CXaWKJC630Z7dbls61vdHxya/cR2ycQZ6Mm6ckgF6Cag5g=="], "@oxc-resolver/binding-openharmony-arm64": ["@oxc-resolver/binding-openharmony-arm64@11.24.2", "", { "os": "none", "cpu": "arm64" }, "sha512-MvyGik3a6pVgZ0t/kWlbmFxFLmXQJwgLsY2eYFHLpy0wGwRbfzeIGgDwQ3kXqE30z+kSXennRkCrT7TUvkptNg=="],
"@oxlint/binding-win32-ia32-msvc": ["@oxlint/binding-win32-ia32-msvc@1.86.0", "", { "os": "win32", "cpu": "ia32" }, "sha512-a47ga7EKVfMU8rO0i1m3mGwfNRj3FhQyt1d/ukO/E9u1HHF3KpR3tyb3VhuJBGEVPF8uR4exSyHUyx7xbE+uxw=="], "@oxc-resolver/binding-wasm32-wasi": ["@oxc-resolver/binding-wasm32-wasi@11.24.2", "", { "dependencies": { "@emnapi/core": "1.11.2", "@emnapi/runtime": "1.11.2", "@napi-rs/wasm-runtime": "^1.1.6" }, "cpu": "none" }, "sha512-vHcssMPwO08RTvj/c0iOBz90attxyG3wQJ0dTcyEQK43LRpcdLWZlV5feBhv6Isn6ahbQIzHbCgfa81+RiML0Q=="],
"@oxlint/binding-win32-x64-msvc": ["@oxlint/binding-win32-x64-msvc@1.86.0", "", { "os": "win32", "cpu": "x64" }, "sha512-az4dzifCRzES1crwu6pDFXzJTIanrdxXFL9TbiJWrx9LKcuacbR83aPvxDA1LKLNswi/RoqitC7Afcflhu3zBQ=="], "@oxc-resolver/binding-win32-arm64-msvc": ["@oxc-resolver/binding-win32-arm64-msvc@11.24.2", "", { "os": "win32", "cpu": "arm64" }, "sha512-uokJqro2iBqkFvJdKQLP7d8/BUmFwESQFVmIJUQKj1Xn1a/LysJoe1vmeECLF5b3jsV8CAL5sEMJXX6SdK9Nhg=="],
"@oxlint/plugins": ["@oxlint/plugins@1.86.0", "", {}, "sha512-JeAiaaRMyUiUEQHQ7zBsJn1aEdbLyt1HJsOs4XKIIlATNxcvWRrRxneZA+RF4G03cQobq3IhTqSfyLhOFv03qA=="], "@oxc-resolver/binding-win32-x64-msvc": ["@oxc-resolver/binding-win32-x64-msvc@11.24.2", "", { "os": "win32", "cpu": "x64" }, "sha512-UqGPmo56KDfLlfXFAFIrNflHT8tFxWGEivWg3Zeyp4Uy2NlKN1FGPr6/BxcLGG3+kZ6Wp14g5Uj+n71boqZfiw=="],
"@oxfmt/binding-android-arm-eabi": ["@oxfmt/binding-android-arm-eabi@0.72.0", "", { "os": "android", "cpu": "arm" }, "sha512-u4U1uaDOVBuorGNC/07NLm48nECHOiJJka002YGML16Md2DRvf38RGBt01lH60EOGvNlFVmbLoksQedNBoZHKw=="],
"@oxfmt/binding-android-arm64": ["@oxfmt/binding-android-arm64@0.72.0", "", { "os": "android", "cpu": "arm64" }, "sha512-GCnM+Ae2mWOKC+92y3FOb6eZJeVnBAVz82e3lITUUg+kxukYKzBNAvJ/hhHIfa2A0md55SYYhdWPddSSy3KPVA=="],
"@oxfmt/binding-darwin-arm64": ["@oxfmt/binding-darwin-arm64@0.72.0", "", { "os": "darwin", "cpu": "arm64" }, "sha512-LjQ8tlevdtwraFlWC6AnQ1Forzde0clRmnsP3QmK+ydSElDt/J+5Jc+m+//Ly1G97aP7WCNUw110QMIUw2K7xA=="],
"@oxfmt/binding-darwin-x64": ["@oxfmt/binding-darwin-x64@0.72.0", "", { "os": "darwin", "cpu": "x64" }, "sha512-+ZbcxhB1C34RQR5IldSyY6Z/yalJIxHXhP36PGE4sEq0f/lgL5jCLmOKoDeVm8dqd9gFGDsd1bNWHSGCAwdSkw=="],
"@oxfmt/binding-freebsd-x64": ["@oxfmt/binding-freebsd-x64@0.72.0", "", { "os": "freebsd", "cpu": "x64" }, "sha512-yGPhA8sePEBFV9iGcprhyOk3Bz3fZshswMH3DpYIPZFLT1DG5LjiZ0j6AJQpSueaL6bUK0av1K+5+fe+ldy5EQ=="],
"@oxfmt/binding-linux-arm-gnueabihf": ["@oxfmt/binding-linux-arm-gnueabihf@0.72.0", "", { "os": "linux", "cpu": "arm" }, "sha512-/g5axuqFMcAtoQrFLR5EJEMDjR5Ea4GuzpdDmMpPWAgrF1DmL4kD1NPNVlpXEOxpFJnD6lPvLKYj1lzdlrfifA=="],
"@oxfmt/binding-linux-arm-musleabihf": ["@oxfmt/binding-linux-arm-musleabihf@0.72.0", "", { "os": "linux", "cpu": "arm" }, "sha512-InVitdHbS09PM+w+WinIiyX37rC9R3L7lUP9mKy9uKTEDSUFaLjWsLoreRIxKivnv7Ndqc6Trvi+K+b6ZzhiJg=="],
"@oxfmt/binding-linux-arm64-gnu": ["@oxfmt/binding-linux-arm64-gnu@0.72.0", "", { "os": "linux", "cpu": "arm64" }, "sha512-WKjlyRAxpPjXoqeuwFBim5LscgvY+RNEiZ971C9JlRQZONhJTsXDki/oHFYQE+fzzRpzXh3owZvOdT3kNL2g+g=="],
"@oxfmt/binding-linux-arm64-musl": ["@oxfmt/binding-linux-arm64-musl@0.72.0", "", { "os": "linux", "cpu": "arm64" }, "sha512-poafnbsPpJhR+5Mbwpf8CscugTyiRAzjTOxRVn8ra3X2jnURs2xL5Du2xl5g2iW85lICMglpmLf8jDjZEbNgzQ=="],
"@oxfmt/binding-linux-ppc64-gnu": ["@oxfmt/binding-linux-ppc64-gnu@0.72.0", "", { "os": "linux", "cpu": "ppc64" }, "sha512-zNUi0gKRsO7S3IfPzsTbnm88OedPuX32hmZFWZRWHvWJlAoZRwVbeO6Nb3hng4vDgL7qUKp4TGqzPz1mhsycYg=="],
"@oxfmt/binding-linux-riscv64-gnu": ["@oxfmt/binding-linux-riscv64-gnu@0.72.0", "", { "os": "linux", "cpu": "none" }, "sha512-qTY7z/iyF/rWI2HWwWMevXqZW5PZUOofUy2afK7v6rseXnpld3yjgyIk6pCux3DqWQ0lB+f5atvLJNBwzLvFsw=="],
"@oxfmt/binding-linux-riscv64-musl": ["@oxfmt/binding-linux-riscv64-musl@0.72.0", "", { "os": "linux", "cpu": "none" }, "sha512-w18qfo8vEMD6EKEHtzTvjc6jH8yCyXIT1Bn7PFWJd0PpZyzH/VQDx4xvjCh0LGz6GRzqiezbisTdG9AoXtpkZQ=="],
"@oxfmt/binding-linux-s390x-gnu": ["@oxfmt/binding-linux-s390x-gnu@0.72.0", "", { "os": "linux", "cpu": "s390x" }, "sha512-grW8HwEir+vK7fCcq1ZgL3NHQCfZ1PidiERE9Hbf+24xGys+DoDaoqTht4ccfn0PcBwbViLkwkda/KNpJu2KRQ=="],
"@oxfmt/binding-linux-x64-gnu": ["@oxfmt/binding-linux-x64-gnu@0.72.0", "", { "os": "linux", "cpu": "x64" }, "sha512-wQJRQfWBRIn88Pkr449EUViwRayrYUScg7ty+Ihiem21mQ9BUA6S9e/4RAgyNk9lMag0KBouyKskjq61rOC0WQ=="],
"@oxfmt/binding-linux-x64-musl": ["@oxfmt/binding-linux-x64-musl@0.72.0", "", { "os": "linux", "cpu": "x64" }, "sha512-T1B0uQzafxuGPjjaPrZJ497nxoi1BiI65JfsYc56nNpmev3msfb/iaTmH2kQuNFqa8PKxpMlf3GhWrWBvBPORQ=="],
"@oxfmt/binding-openharmony-arm64": ["@oxfmt/binding-openharmony-arm64@0.72.0", "", { "os": "none", "cpu": "arm64" }, "sha512-OKxxgTurl7+hypVplO8QRAbbQlwEs0j1Y6FZv+ZN2qNbdxQk2muMlzuJNBGTCWwxQ0rkkOD1uK/DW1fvzoUSJA=="],
"@oxfmt/binding-win32-arm64-msvc": ["@oxfmt/binding-win32-arm64-msvc@0.72.0", "", { "os": "win32", "cpu": "arm64" }, "sha512-L78TKzURqvjuZOCo88ixMbPXf/RP7u31Y0cmjJ/KEmrHmfYhmhEvsDaTYPiyTRne64jUgCbADfY0YeoQk4/Xyw=="],
"@oxfmt/binding-win32-ia32-msvc": ["@oxfmt/binding-win32-ia32-msvc@0.72.0", "", { "os": "win32", "cpu": "ia32" }, "sha512-gQtFW+Ii8BWgtJTAD17TY/WsdNS5gUfAPov8iI1jeq4r9lRRYImmxPL08UU00/RLaCfBJwh2UgINnDY0iOiZ+A=="],
"@oxfmt/binding-win32-x64-msvc": ["@oxfmt/binding-win32-x64-msvc@0.72.0", "", { "os": "win32", "cpu": "x64" }, "sha512-uhooIN+DCzWX5uH7mQkSVCsODqsGluGJ4n3ch4+mITtWKpESMDjUJUSDBAVFuYQDwqY2McPDKdKJbM0oZVW/Qw=="],
"@oxlint-tsgolint/darwin-arm64": ["@oxlint-tsgolint/darwin-arm64@7.0.2004", "", { "os": "darwin", "cpu": "arm64" }, "sha512-uJk3ttju7Lz+Nv8WG4CsLyewoL1qf/Ny8S8OksJ7Bm/F14Tc9gMfW6arM1PCc57IzH/X/I79YsCWTgxX1FKibQ=="],
"@oxlint-tsgolint/darwin-x64": ["@oxlint-tsgolint/darwin-x64@7.0.2004", "", { "os": "darwin", "cpu": "x64" }, "sha512-0BFfHTzDxNDFPcu0UZAXT6CyCJHAXM0dZveyDb4KEHa2qF/DSnOKOrmvK/wFuFol9kvijbGM9JfuOsor+zWXRw=="],
"@oxlint-tsgolint/linux-arm64": ["@oxlint-tsgolint/linux-arm64@7.0.2004", "", { "os": "linux", "cpu": "arm64" }, "sha512-TAehQc+qdRXyDN3nl/r/3/oPrBVrbtrDeGMkFyG6mf+XphpoJ2lAMVFLclyvrVZCw02RbKROjyw8h72XwQQHcw=="],
"@oxlint-tsgolint/linux-x64": ["@oxlint-tsgolint/linux-x64@7.0.2004", "", { "os": "linux", "cpu": "x64" }, "sha512-LPunZvm6ZbWPfHMAyfZf9ci3HHvNEzLejO8zdqO3GoVGoSEHqqufHUD7+OgeatVSaJP7uXDJ2HaNOHIoH7go4Q=="],
"@oxlint-tsgolint/win32-arm64": ["@oxlint-tsgolint/win32-arm64@7.0.2004", "", { "os": "win32", "cpu": "arm64" }, "sha512-FVWplzDImWhiuawnIZVETaQecv4GWom6Jv4Fx2xj7hhXXDZ5okEgiw1gTCImHTIQsi2ycC5oSxVwrn69bMh7iw=="],
"@oxlint-tsgolint/win32-x64": ["@oxlint-tsgolint/win32-x64@7.0.2004", "", { "os": "win32", "cpu": "x64" }, "sha512-7PsxuUx11Ry9DYTWcljTzRbmZY9B6O9fFFfZV+aodQEMy6pfRT3fhoQRv9PtGN/89z1pPz3nFKrsFm6WqNtX7w=="],
"@oxlint/binding-android-arm-eabi": ["@oxlint/binding-android-arm-eabi@1.87.0", "", { "os": "android", "cpu": "arm" }, "sha512-22tVIHlB9898OYsBKmYB6He1MCSqdTmK1BVWuSNUTVrpS0KWNege+U9uEYqGJ+KatQag0r/oU44i3OOs46z7HQ=="],
"@oxlint/binding-android-arm64": ["@oxlint/binding-android-arm64@1.87.0", "", { "os": "android", "cpu": "arm64" }, "sha512-JfZQ3MWf74n8ov0DojZpkOduIubYJvZL5tbTMMhDutsal6u1xH1QuNpN+lK+EQwF8AeAfgwTR2fgh5U2br27XA=="],
"@oxlint/binding-darwin-arm64": ["@oxlint/binding-darwin-arm64@1.87.0", "", { "os": "darwin", "cpu": "arm64" }, "sha512-rkx6Xvvw93z2GImVOyvbZwAZcoY0Z6MJW177XNsSB+i/CBsH7ANyelTp01VZyIkM3iSXtqKVb4+ptBgPHap5pQ=="],
"@oxlint/binding-darwin-x64": ["@oxlint/binding-darwin-x64@1.87.0", "", { "os": "darwin", "cpu": "x64" }, "sha512-cw5nYw7L/pQ2SgGBgOcg/Qo89llQre3vIc/kuBLhSICzu1r5s8L76H3ug6AIFsD98WpROj8/z5JVzkf4daxHaQ=="],
"@oxlint/binding-freebsd-x64": ["@oxlint/binding-freebsd-x64@1.87.0", "", { "os": "freebsd", "cpu": "x64" }, "sha512-x/SuznE6loRZK9gz9AS4ZmzNzSu+5KdeoCS+sVHhnrE8HM6AD8UyTjwldQTTqlXGvkwHASgB0NiTNOc3o3PdAg=="],
"@oxlint/binding-linux-arm-gnueabihf": ["@oxlint/binding-linux-arm-gnueabihf@1.87.0", "", { "os": "linux", "cpu": "arm" }, "sha512-+JEDmCAXiiFmKhAjZhgAOwaHWY6WENOQ5QA+lFuY59tgsUCDOTRi46B+lENK6CWvtxsXpwkZXNOgpjAQcpIpnA=="],
"@oxlint/binding-linux-arm-musleabihf": ["@oxlint/binding-linux-arm-musleabihf@1.87.0", "", { "os": "linux", "cpu": "arm" }, "sha512-/uC9XqXLAC9AHFLNycwmSQEvKqGrOCgU+uXALI7gNW0DG81TJ/3T2eHnKdRvcb5R1gFEfjxDwI4e4zIa29rICQ=="],
"@oxlint/binding-linux-arm64-gnu": ["@oxlint/binding-linux-arm64-gnu@1.87.0", "", { "os": "linux", "cpu": "arm64" }, "sha512-FTRYPsBy/M728vnUv7l+KAwSAa3Qi4BQbhVvy7NYuMTZ0sUa/OWsbMx79HVFw6u/5KWcaYayDsoOiv7xbevzDg=="],
"@oxlint/binding-linux-arm64-musl": ["@oxlint/binding-linux-arm64-musl@1.87.0", "", { "os": "linux", "cpu": "arm64" }, "sha512-6sC+N7IY0h1egd8SrYUGNN7CUyKJZ4bIZakKa7V7hfinf4jfi8Kq4+klJvFp5DqXcwMn44I5MeBwmJluO1odFg=="],
"@oxlint/binding-linux-ppc64-gnu": ["@oxlint/binding-linux-ppc64-gnu@1.87.0", "", { "os": "linux", "cpu": "ppc64" }, "sha512-d5Mnn+ICbhoJPi37Ccjy+86T5qfH2+mSTrTMBXNPfB+wqSWOayBBLLIrCXdUy1YssluCVdGkl+DO9w5r5ODmUA=="],
"@oxlint/binding-linux-riscv64-gnu": ["@oxlint/binding-linux-riscv64-gnu@1.87.0", "", { "os": "linux", "cpu": "none" }, "sha512-sf5YWuUo1Dx9loqWCgF8P278MycfcD4JHjDC/LV5j11L3Lqa4PFiwCjD6B8kP4AjsgZZkLn3xbpJEtZBaccs4Q=="],
"@oxlint/binding-linux-riscv64-musl": ["@oxlint/binding-linux-riscv64-musl@1.87.0", "", { "os": "linux", "cpu": "none" }, "sha512-+aCraYbmK3uU3P0rFojjeaK9pGY6JvBDXh/0CM+gPyWKmNmXmnFe0qj4qj02U4ibFpbd9Pa9CmDvIdjJUd29rA=="],
"@oxlint/binding-linux-s390x-gnu": ["@oxlint/binding-linux-s390x-gnu@1.87.0", "", { "os": "linux", "cpu": "s390x" }, "sha512-7rzbZQIljo6VLWVPqUyLa2P/WV3VFsJB4M52R4NCUJn1A50yjtUsHxiMHFL9opEKGFIiTbZ3VQzmtcJOPUq4NQ=="],
"@oxlint/binding-linux-x64-gnu": ["@oxlint/binding-linux-x64-gnu@1.87.0", "", { "os": "linux", "cpu": "x64" }, "sha512-Dry46Fa+AXE/xt9J/YriujU1pU9mzfNWHGQwtOYibAFH8HLrKWCi93AhIGnuUMiwn2JbuBkRyz51f50Ly4r4ow=="],
"@oxlint/binding-linux-x64-musl": ["@oxlint/binding-linux-x64-musl@1.87.0", "", { "os": "linux", "cpu": "x64" }, "sha512-f/HMZez74gJvnRpGz+b5sdGyWrEgRLmFTXg9sNoqjPWogGxYHUhXKTKyMiYsu9rUGR2ciYqL3fk+Ua4JhMJbRA=="],
"@oxlint/binding-openharmony-arm64": ["@oxlint/binding-openharmony-arm64@1.87.0", "", { "os": "none", "cpu": "arm64" }, "sha512-lEC6ZfPZm/07JlB7FsOWX9o1RiHlXiBW594LSUGuXmekC8LZmvUPP9XzE2WZcNxJi5cHA/Fw56o02c3JxgMA5g=="],
"@oxlint/binding-win32-arm64-msvc": ["@oxlint/binding-win32-arm64-msvc@1.87.0", "", { "os": "win32", "cpu": "arm64" }, "sha512-afBWKOD36dUiA9AenaiWpCg8xfyUVPYznyAAVXu413brK4RA5UI/Xoc4yfeGIT8G1a44MV+JR7hioryerBDzGQ=="],
"@oxlint/binding-win32-ia32-msvc": ["@oxlint/binding-win32-ia32-msvc@1.87.0", "", { "os": "win32", "cpu": "ia32" }, "sha512-daptNsEOuru4/nJTxV4DBHNJ5GepzmaBVQf+jjgKQGi9NRlZKik+RFq4hUL7ewsF1pwjKM+SkYaMbF82UwFGnw=="],
"@oxlint/binding-win32-x64-msvc": ["@oxlint/binding-win32-x64-msvc@1.87.0", "", { "os": "win32", "cpu": "x64" }, "sha512-k+m/EShyXE29J/r1fjk0HlAzhN5JhIvj044oSJkXTEkCLrWZQgXb/3r4q5LTw/eaKW/4GuMXG2xmiJs3s5rPNw=="],
"@oxlint/plugins": ["@oxlint/plugins@1.87.0", "", {}, "sha512-OtSZ6NxNkS7bkVy7zk9zGnajz2hVIu0uRPP/dJvJesGRaXtimpA4lpxap7FaIJndG2UIoKhnBU4DxyDQIWv6yg=="],
"@pkgjs/parseargs": ["@pkgjs/parseargs@0.11.0", "", {}, "sha512-+1VkjdD0QBLPodGrJUeqarH8VAIvQODIbwh9XpP5Syisf7YoQgsJKPNFoqqLQlu+VQ/tVSshMR6loPMn8U+dPg=="], "@pkgjs/parseargs": ["@pkgjs/parseargs@0.11.0", "", {}, "sha512-+1VkjdD0QBLPodGrJUeqarH8VAIvQODIbwh9XpP5Syisf7YoQgsJKPNFoqqLQlu+VQ/tVSshMR6loPMn8U+dPg=="],
@@ -386,10 +477,42 @@
"@standard-schema/spec": ["@standard-schema/spec@1.1.0", "", {}, "sha512-l2aFy5jALhniG5HgqrD6jXLi/rUWrKvqN/qJx6yoJsgKhblVd+iqqU4RCXavm/jPityDo5TCvKMnpjKnOriy0w=="], "@standard-schema/spec": ["@standard-schema/spec@1.1.0", "", {}, "sha512-l2aFy5jALhniG5HgqrD6jXLi/rUWrKvqN/qJx6yoJsgKhblVd+iqqU4RCXavm/jPityDo5TCvKMnpjKnOriy0w=="],
"@swc/core": ["@swc/core@1.16.18", "", { "dependencies": { "@swc/counter": "^0.1.3", "@swc/types": "^0.1.28" }, "optionalDependencies": { "@swc/core-darwin-arm64": "1.16.18", "@swc/core-darwin-x64": "1.16.18", "@swc/core-linux-arm-gnueabihf": "1.16.18", "@swc/core-linux-arm64-gnu": "1.16.18", "@swc/core-linux-arm64-musl": "1.16.18", "@swc/core-linux-ppc64-gnu": "1.16.18", "@swc/core-linux-s390x-gnu": "1.16.18", "@swc/core-linux-x64-gnu": "1.16.18", "@swc/core-linux-x64-musl": "1.16.18", "@swc/core-win32-arm64-msvc": "1.16.18", "@swc/core-win32-ia32-msvc": "1.16.18", "@swc/core-win32-x64-msvc": "1.16.18" }, "peerDependencies": { "@swc/helpers": ">=0.5.17" }, "optionalPeers": ["@swc/helpers"] }, "sha512-0cYQLkpcwUngg55TDwpwrrVOU+B6zh1NFbp+oS7dVFhmYkzaARelwugo/bzPJh1FrcnppmF+KTqioCGwyqbcEw=="],
"@swc/core-darwin-arm64": ["@swc/core-darwin-arm64@1.16.18", "", { "os": "darwin", "cpu": "arm64" }, "sha512-ozgiCHyFDCwfXzTnaLR+i8WxEyt06GTudn9rPh08vj+u3Z8vMvt5Pi8T+BikyNXm7y++h6UMdqsnJuWrV+tk2A=="],
"@swc/core-darwin-x64": ["@swc/core-darwin-x64@1.16.18", "", { "os": "darwin", "cpu": "x64" }, "sha512-tuwxXi+sjxxTAi7GP3NeQXQxOf4SXSiFxKAMYLBdoy7JqGYby6uSDXojcFoLOhSp7oiNGstnaFXxfbP0Hpro9w=="],
"@swc/core-linux-arm-gnueabihf": ["@swc/core-linux-arm-gnueabihf@1.16.18", "", { "os": "linux", "cpu": "arm" }, "sha512-SMdhmY1P9Kveh0MRj6vqQF98bsjnDa0lBBvkd/lcpxmjj5QHJOQAU0N3g6h7GPWpBMs3h2g3lHu/QTDn+uMsXg=="],
"@swc/core-linux-arm64-gnu": ["@swc/core-linux-arm64-gnu@1.16.18", "", { "os": "linux", "cpu": "arm64" }, "sha512-ep/mQyhblQYZ6tkfq0IJspcVSFl5jdywks3kejanrbB31uuujRD/QWOoGNp2L3lLRdAdQvgl/M3pA7g3hSuQug=="],
"@swc/core-linux-arm64-musl": ["@swc/core-linux-arm64-musl@1.16.18", "", { "os": "linux", "cpu": "arm64" }, "sha512-pkzGVxrAQu5+febW1a/Aiph3YJk0UiJKXoWbxnDVEIOZWkk5aETHTuyVsOQ3kOgn2dzNMvJVeqcoEQdH+ntqWQ=="],
"@swc/core-linux-ppc64-gnu": ["@swc/core-linux-ppc64-gnu@1.16.18", "", { "os": "linux", "cpu": "ppc64" }, "sha512-v9kiu4as1pJyQ8ESFTtMNydZ99m86QXLfAtm+XiKPKS93pXL80BCaXokAs9ebioGkIXgmwfbzUCdUC62H3JWkw=="],
"@swc/core-linux-s390x-gnu": ["@swc/core-linux-s390x-gnu@1.16.18", "", { "os": "linux", "cpu": "s390x" }, "sha512-vU7TKRJ26i86YQr4QY/5bdcH72KzkBbSSUfPlErW6d6KOR47BcVGlYZFTcMMYlmd3CVSXFHW18tBSila66YfoA=="],
"@swc/core-linux-x64-gnu": ["@swc/core-linux-x64-gnu@1.16.18", "", { "os": "linux", "cpu": "x64" }, "sha512-Ml6kbe0BoVJkSgmYPAEUudGcu84jaQeqDN8xeMumbwNpT0vlmm7241Ddp9XKCjQABvjomnXF0OiNOAfjBhNDNw=="],
"@swc/core-linux-x64-musl": ["@swc/core-linux-x64-musl@1.16.18", "", { "os": "linux", "cpu": "x64" }, "sha512-TGU24+QmmS8y/hg0BLKgOU3W5TCcQC9bgGl8AB0R61gTNQdWdcmCehRLAJwlZfxtAml66xMJ6PWrX8NKrABOsA=="],
"@swc/core-win32-arm64-msvc": ["@swc/core-win32-arm64-msvc@1.16.18", "", { "os": "win32", "cpu": "arm64" }, "sha512-S53hm7Amc3YV8t2BUT6R7J+zSnwiGarG+GnxMca4W0uMkxBZ3Gl6jBwEgb6YqrYjf2DzOuRfauztqptCO76a/w=="],
"@swc/core-win32-ia32-msvc": ["@swc/core-win32-ia32-msvc@1.16.18", "", { "os": "win32", "cpu": "ia32" }, "sha512-+6/10+OJmU12zWkrPVG0QeQEr8VsWeF8gyXrOfHZMIfMOfz8/ULXVZPhV9GhGMKSWake1xEJj2IYCiFRS/xMpQ=="],
"@swc/core-win32-x64-msvc": ["@swc/core-win32-x64-msvc@1.16.18", "", { "os": "win32", "cpu": "x64" }, "sha512-7LsVrIICAZWSajXT6DwO7PYSTnW9maamOCyQylaOh13Viptrgi/7hl9fP75SiHe+kscaJahGXcorgt4MOOh/1w=="],
"@swc/counter": ["@swc/counter@0.1.3", "", {}, "sha512-e2BR4lsJkkRlKZ/qCHPw9ZaSxc0MVUd7gtbtaB7aMvHeJVYe8sOB8DBZkP2DtISHGSku9sCK6T6cnY0CtXrOCQ=="],
"@swc/types": ["@swc/types@0.1.28", "", { "dependencies": { "@swc/counter": "^0.1.3" } }, "sha512-V6Mnml8v09QALx6K0elJ7o9K/MkVDtW3t6L+7Ou/JcWtb3xwId2AH4FeOceySd2JaO87IMw4+6vSZxLm34LPbw=="],
"@tufjs/canonical-json": ["@tufjs/canonical-json@2.0.0", "", {}, "sha512-yVtV8zsdo8qFHe+/3kw81dSLyF7D576A5cCFCi4X7B39tWT7SekaEFUnvnWJHz+9qO7qJTah1JbrDjWKqFtdWA=="], "@tufjs/canonical-json": ["@tufjs/canonical-json@2.0.0", "", {}, "sha512-yVtV8zsdo8qFHe+/3kw81dSLyF7D576A5cCFCi4X7B39tWT7SekaEFUnvnWJHz+9qO7qJTah1JbrDjWKqFtdWA=="],
"@tufjs/models": ["@tufjs/models@4.1.0", "", { "dependencies": { "@tufjs/canonical-json": "2.0.0", "minimatch": "^10.1.1" } }, "sha512-Y8cK9aggNRsqJVaKUlEYs4s7CvQ1b1ta2DVPyAimb0I2qhzjNk+A+mxvll/klL0RlfuIUei8BF7YWiua4kQqww=="], "@tufjs/models": ["@tufjs/models@4.1.0", "", { "dependencies": { "@tufjs/canonical-json": "2.0.0", "minimatch": "^10.1.1" } }, "sha512-Y8cK9aggNRsqJVaKUlEYs4s7CvQ1b1ta2DVPyAimb0I2qhzjNk+A+mxvll/klL0RlfuIUei8BF7YWiua4kQqww=="],
"@tybys/wasm-util": ["@tybys/wasm-util@0.10.4", "", { "dependencies": { "tslib": "^2.4.0" } }, "sha512-W3c4gRigFS0T/Ma4qIYF3GDAc5AQdHb1yL5znJT1Zv1YaD9Kitx656wBjvr19qbiosmZT8lWDM5BEMynUqX65A=="],
"@types/bun": ["@types/bun@1.4.2", "", { "dependencies": { "bun-types": "1.4.2" } }, "sha512-GimotNn7+ZV0uVArItBbriZsR1oNf0+WTzPkdcFrzShI7k2norL0uzEaJT8T33dWr7O/c9ZDuAFQrctKCi72oQ=="], "@types/bun": ["@types/bun@1.4.2", "", { "dependencies": { "bun-types": "1.4.2" } }, "sha512-GimotNn7+ZV0uVArItBbriZsR1oNf0+WTzPkdcFrzShI7k2norL0uzEaJT8T33dWr7O/c9ZDuAFQrctKCi72oQ=="],
"@types/node": ["@types/node@26.5.0", "", { "dependencies": { "undici-types": "~8.9.0" } }, "sha512-dVSGpriSoCgz8WnDNTuSSuSv1PC/ALXihO4ulRZt7Md8k9mlbdin3lGOcDE8SnWOgf513ByWlXd7BK4azmyg/A=="], "@types/node": ["@types/node@26.5.0", "", { "dependencies": { "undici-types": "~8.9.0" } }, "sha512-dVSGpriSoCgz8WnDNTuSSuSv1PC/ALXihO4ulRZt7Md8k9mlbdin3lGOcDE8SnWOgf513ByWlXd7BK4azmyg/A=="],
@@ -438,11 +561,21 @@
"abbrev": ["abbrev@4.0.0", "", {}, "sha512-a1wflyaL0tHtJSmLSOVybYhy22vRih4eduhhrkcjgrWGnRfrZtovJ2FRjxuTtkkj47O/baf0R86QU5OuYpz8fA=="], "abbrev": ["abbrev@4.0.0", "", {}, "sha512-a1wflyaL0tHtJSmLSOVybYhy22vRih4eduhhrkcjgrWGnRfrZtovJ2FRjxuTtkkj47O/baf0R86QU5OuYpz8fA=="],
"acorn": ["acorn@8.19.0", "", { "bin": { "acorn": "bin/acorn" } }, "sha512-oJlA3XiRm7Cyk6qFD2Jn8ak9B7jSy0qy00ADO3+8dpT0LSjFihQYv4C02LFCSYJV3Q37xYwwRy5m+IpIiUzqWw=="],
"acorn-jsx": ["acorn-jsx@5.3.2", "", { "peerDependencies": { "acorn": "^6.0.0 || ^7.0.0 || ^8.0.0" } }, "sha512-rq9s+JNhf0IChjtDXxllJ7g41oZk5SlXtp0LHwyA5cejwn7vKmKp4pPri6YEePv2PU65sAsegbXtIinmDFDXgQ=="],
"acorn-jsx-walk": ["acorn-jsx-walk@2.0.0", "", {}, "sha512-uuo6iJj4D4ygkdzd6jPtcxs8vZgDX9YFIkqczGImoypX2fQ4dVImmu3UzA4ynixCIMTrEOWW+95M2HuBaCEOVA=="],
"acorn-loose": ["acorn-loose@8.5.2", "", { "dependencies": { "acorn": "^8.15.0" } }, "sha512-PPvV6g8UGMGgjrMu+n/f9E/tCSkNQ2Y97eFvuVdJfG11+xdIeDcLyNdC8SHcrHbRqkfwLASdplyR6B6sKM1U4A=="],
"acorn-walk": ["acorn-walk@8.3.5", "", { "dependencies": { "acorn": "^8.11.0" } }, "sha512-HEHNfbars9v4pgpW6SO1KSPkfoS0xVOM/9UzkJltjlsHZmJasxg8aXkuZa7SMf8vKGIBhpUsPluQSqhJFCqebw=="],
"agent-base": ["agent-base@7.1.4", "", {}, "sha512-MnA+YT8fwfJPgBx3m60MNqakm30XOkyIoH1y6huTQvC0PwZG7ki8NacLBcrPbNoo8vEZy7Jpuk7+jMO+CUovTQ=="], "agent-base": ["agent-base@7.1.4", "", {}, "sha512-MnA+YT8fwfJPgBx3m60MNqakm30XOkyIoH1y6huTQvC0PwZG7ki8NacLBcrPbNoo8vEZy7Jpuk7+jMO+CUovTQ=="],
"ansi-regex": ["ansi-regex@6.3.0", "", {}, "sha512-WpDfL7NO6j7tH88IDBNVdUJxDh9nmCteAVW9dsep846XdwF4naCBK+/tGLX3KJgcpgMRXCFlTM2hKGoK9FsdrQ=="], "ansi-regex": ["ansi-regex@6.3.0", "", {}, "sha512-WpDfL7NO6j7tH88IDBNVdUJxDh9nmCteAVW9dsep846XdwF4naCBK+/tGLX3KJgcpgMRXCFlTM2hKGoK9FsdrQ=="],
"ansi-styles": ["ansi-styles@6.2.3", "", {}, "sha512-4Dj6M28JB+oAH8kFkTLUo+a2jwOFkuqb3yucU0CANcRRUbxS0cP0nZYCGjcc3BNXwRIsUVmDGgzawme7zvJHvg=="], "ansi-styles": ["ansi-styles@4.3.0", "", { "dependencies": { "color-convert": "^2.0.1" } }, "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg=="],
"aws4fetch": ["aws4fetch@1.0.20", "", {}, "sha512-/djoAN709iY65ETD6LKCtyyEI04XIBP5xVvfmNxsEP0uJB5tyaGBztSryRr4HqMStr9R06PisQE7m9zDTXKu6g=="], "aws4fetch": ["aws4fetch@1.0.20", "", {}, "sha512-/djoAN709iY65ETD6LKCtyyEI04XIBP5xVvfmNxsEP0uJB5tyaGBztSryRr4HqMStr9R06PisQE7m9zDTXKu6g=="],
@@ -480,6 +613,8 @@
"caniuse-lite": ["caniuse-lite@1.0.30001810", "", {}, "sha512-TITQPUkaz+aVk5GL6NhOdwk1aEaNTSDPsGFWrTuhKGtjTF70jL/Oht2W4c6rXUe5fu7Ie19VIahAXHIIiWWNeg=="], "caniuse-lite": ["caniuse-lite@1.0.30001810", "", {}, "sha512-TITQPUkaz+aVk5GL6NhOdwk1aEaNTSDPsGFWrTuhKGtjTF70jL/Oht2W4c6rXUe5fu7Ie19VIahAXHIIiWWNeg=="],
"chalk": ["chalk@4.1.2", "", { "dependencies": { "ansi-styles": "^4.1.0", "supports-color": "^7.1.0" } }, "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA=="],
"chownr": ["chownr@3.0.0", "", {}, "sha512-+IxzY9BZOQd/XuYPRmrvEVjF/nqj5kgT4kEq7VofrDoM1MxoRjEWkrCC3EtLi59TVawxTAn+orJwFQcrqEN1+g=="], "chownr": ["chownr@3.0.0", "", {}, "sha512-+IxzY9BZOQd/XuYPRmrvEVjF/nqj5kgT4kEq7VofrDoM1MxoRjEWkrCC3EtLi59TVawxTAn+orJwFQcrqEN1+g=="],
"ci-info": ["ci-info@4.4.0", "", {}, "sha512-77PSwercCZU2Fc4sX94eF8k8Pxte6JAwL4/ICZLFjJLqegs7kCuAsqqj/70NQF6TvDpgFjkubQB2FW2ZZddvQg=="], "ci-info": ["ci-info@4.4.0", "", {}, "sha512-77PSwercCZU2Fc4sX94eF8k8Pxte6JAwL4/ICZLFjJLqegs7kCuAsqqj/70NQF6TvDpgFjkubQB2FW2ZZddvQg=="],
@@ -492,6 +627,8 @@
"color-name": ["color-name@1.1.4", "", {}, "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA=="], "color-name": ["color-name@1.1.4", "", {}, "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA=="],
"commander": ["commander@15.0.0", "", {}, "sha512-z67u4ZhzCL/Tydu1lJARtEZYWbWaN7oYLHbsuzocr6y4N6WZAagG3RQ4FW61V1/0+jImpj293XfrcYnd1qxtPg=="],
"common-ancestor-path": ["common-ancestor-path@2.0.0", "", {}, "sha512-dnN3ibLeoRf2HNC+OlCiNc5d2zxbLJXOtiZUudNFSXZrNSydxcCsSpRzXwfu7BBWCIfHPw+xTayeBvJCP/D8Ng=="], "common-ancestor-path": ["common-ancestor-path@2.0.0", "", {}, "sha512-dnN3ibLeoRf2HNC+OlCiNc5d2zxbLJXOtiZUudNFSXZrNSydxcCsSpRzXwfu7BBWCIfHPw+xTayeBvJCP/D8Ng=="],
"content-type": ["content-type@2.1.0", "", {}, "sha512-mj7UPXE0jaqaOsukNZRUEfEi2AcL7C/vwmwcHV0O97eO1E1pxBZuyjlZrx5seTaNBg1U6+o35wpa35Qfcc+7ag=="], "content-type": ["content-type@2.1.0", "", {}, "sha512-mj7UPXE0jaqaOsukNZRUEfEi2AcL7C/vwmwcHV0O97eO1E1pxBZuyjlZrx5seTaNBg1U6+o35wpa35Qfcc+7ag=="],
@@ -514,7 +651,7 @@
"define-lazy-prop": ["define-lazy-prop@3.0.0", "", {}, "sha512-N+MeXYoqr3pOgn8xfyRPREN7gHakLYjhsHhWGT3fWAiL4IkAt0iDw14QiiEm2bE30c5XX5q0FtAA3CK5f9/BUg=="], "define-lazy-prop": ["define-lazy-prop@3.0.0", "", {}, "sha512-N+MeXYoqr3pOgn8xfyRPREN7gHakLYjhsHhWGT3fWAiL4IkAt0iDw14QiiEm2bE30c5XX5q0FtAA3CK5f9/BUg=="],
"detect-libc": ["detect-libc@2.1.2", "", {}, "sha512-Btj2BOOO83o3WyH59e8MgXsxEQVcarkUOpEYrubB0urwnN10yQ364rsiByU11nZlqWYZm05i/of7io4mzihBtQ=="], "dependency-cruiser": ["dependency-cruiser@18.6.0", "", { "dependencies": { "acorn": "8.19.0", "acorn-jsx": "5.3.2", "acorn-jsx-walk": "2.0.0", "acorn-loose": "8.5.2", "acorn-walk": "8.3.5", "commander": "15.0.0", "enhanced-resolve": "5.26.0", "ignore": "7.0.12", "interpret": "3.1.1", "is-installed-globally": "1.0.1", "json5": "2.2.3", "picomatch": "4.0.7", "prompts": "2.4.2", "rechoir": "0.8.0", "safe-regex": "2.1.1", "semver": "7.8.5", "tsconfig-paths-webpack-plugin": "4.2.0", "watskeburt": "6.0.0" }, "bin": { "depcruise": "bin/dependency-cruiser.mjs", "depcruise-fmt": "bin/depcruise-fmt.mjs", "dependency-cruise": "bin/dependency-cruiser.mjs", "depcruise-baseline": "bin/depcruise-baseline.mjs", "dependency-cruiser": "bin/dependency-cruiser.mjs", "depcruise-wrap-stream-in-html": "bin/wrap-stream-in-html.mjs" } }, "sha512-It7NW5AmCDBCLMq7I91Nfu8VRKzrIE6S+M/FMQzALDceJ0B1PWRHo77q9YJg/HwyBBEWHVtOuTptIQki+xecOw=="],
"diff": ["diff@9.0.0", "", {}, "sha512-svtcdpS8CgJyqAjEQIXdb3OjhFVVYjzGAPO8WGCmRbrml64SPw/jJD4GoE98aR7r25A0XcgrK3F02yw9R/vhQw=="], "diff": ["diff@9.0.0", "", {}, "sha512-svtcdpS8CgJyqAjEQIXdb3OjhFVVYjzGAPO8WGCmRbrml64SPw/jJD4GoE98aR7r25A0XcgrK3F02yw9R/vhQw=="],
@@ -522,12 +659,14 @@
"ecdsa-sig-formatter": ["ecdsa-sig-formatter@1.0.11", "", { "dependencies": { "safe-buffer": "^5.0.1" } }, "sha512-nagl3RYrbNv6kQkeJIpt6NJZy8twLB/2vtz6yN9Z4vRKHN4/QZJIEbqohALSgwKdnksuY3k5Addp5lg8sVoVcQ=="], "ecdsa-sig-formatter": ["ecdsa-sig-formatter@1.0.11", "", { "dependencies": { "safe-buffer": "^5.0.1" } }, "sha512-nagl3RYrbNv6kQkeJIpt6NJZy8twLB/2vtz6yN9Z4vRKHN4/QZJIEbqohALSgwKdnksuY3k5Addp5lg8sVoVcQ=="],
"effect": ["effect@4.0.0-rc.112", "", { "dependencies": { "fast-check": "^4.9.0", "msgpackr": "^2.0.5" } }, "sha512-wXxwuh1Ywnv4cPRM3Wfa0vDwuOHnZ1TsTgHJkG9XgzND6inhBH9n1vBxhg3iIXOia/OrpmvVmd3lrD4vq6bF3A=="], "effect": ["effect@4.0.1", "", {}, "sha512-b1VlQG9g8fwxE5QnIZuPoOP/0MsqHJSRKxUijjoM80E5q95FXrX5yWtY5XI8G+GJsBQAVSDbLS458z9a++uVvw=="],
"electron-to-chromium": ["electron-to-chromium@1.5.427", "", {}, "sha512-n14zb3FdsChZ2BNobqNHAJMcP3ifFv4paox2LvCrfVAQcqGiSURgbJl+PfMpHVCNFkStnNc+RRVtPBTVW5PDgw=="], "electron-to-chromium": ["electron-to-chromium@1.5.427", "", {}, "sha512-n14zb3FdsChZ2BNobqNHAJMcP3ifFv4paox2LvCrfVAQcqGiSURgbJl+PfMpHVCNFkStnNc+RRVtPBTVW5PDgw=="],
"emoji-regex": ["emoji-regex@10.6.0", "", {}, "sha512-toUI84YS5YmxW219erniWD0CIVOo46xGKColeNQRgOzDorgBi1v4D71/OFzgD9GO2UGKIv1C3Sp8DAn0+j5w7A=="], "emoji-regex": ["emoji-regex@10.6.0", "", {}, "sha512-toUI84YS5YmxW219erniWD0CIVOo46xGKColeNQRgOzDorgBi1v4D71/OFzgD9GO2UGKIv1C3Sp8DAn0+j5w7A=="],
"enhanced-resolve": ["enhanced-resolve@5.26.0", "", { "dependencies": { "graceful-fs": "^4.2.4", "tapable": "^2.3.3" } }, "sha512-9vhedylFonb2YGogzUKX6+Ja72gOJbN1QHAqdrvqLwhdl/QWbKopzoUC9EbQNVsAns/bx/4uyqalrQAoy1IByw=="],
"entities": ["entities@7.0.1", "", {}, "sha512-TWrgLOFUQTH994YUyl1yT4uyavY5nNB5muff+RtWaqNVCAK408b5ZnnbNAUEWLTCpum9w6arT70i1XdQ4UeOPA=="], "entities": ["entities@7.0.1", "", {}, "sha512-TWrgLOFUQTH994YUyl1yT4uyavY5nNB5muff+RtWaqNVCAK408b5ZnnbNAUEWLTCpum9w6arT70i1XdQ4UeOPA=="],
"env-paths": ["env-paths@2.2.1", "", {}, "sha512-+h1lkLKhZMTYjog1VEpJNG7NZJWcuc2DDk/qsqSTRRCOXiLjeQ1d1/udrUGhqMxUgAlwKNZ0cf2uqan5GLuS2A=="], "env-paths": ["env-paths@2.2.1", "", {}, "sha512-+h1lkLKhZMTYjog1VEpJNG7NZJWcuc2DDk/qsqSTRRCOXiLjeQ1d1/udrUGhqMxUgAlwKNZ0cf2uqan5GLuS2A=="],
@@ -540,7 +679,7 @@
"extend": ["extend@3.0.2", "", {}, "sha512-fjquC59cD7CyW6urNXK0FBufkZcoiGG80wTuPujX590cB5Ttln20E2UB4S/WARVqhXffZl2LNgS+gQdPIIim/g=="], "extend": ["extend@3.0.2", "", {}, "sha512-fjquC59cD7CyW6urNXK0FBufkZcoiGG80wTuPujX590cB5Ttln20E2UB4S/WARVqhXffZl2LNgS+gQdPIIim/g=="],
"fast-check": ["fast-check@4.9.0", "", { "dependencies": { "pure-rand": "^8.0.0" } }, "sha512-7ms6T7SybUev/PQITciI0yLM2pOSFy5zpG8Ty7tQofcVaQUvrMXp6CBwqF6fThLCLOrfBtuHAtwq6Yu4XPCllg=="], "fd-package-json": ["fd-package-json@2.0.0", "", { "dependencies": { "walk-up-path": "^4.0.0" } }, "sha512-jKmm9YtsNXN789RS/0mSzOC1NUq9mkVd65vbSSVsKdjGvYXBuE4oWe2QOEoFeRmJg+lPuZxpmrfFclNhoRMneQ=="],
"fdir": ["fdir@6.5.0", "", { "peerDependencies": { "picomatch": "^3 || ^4" }, "optionalPeers": ["picomatch"] }, "sha512-tIbYtZbucOs0BRGqPJkshJUYdL+SDH7dVM8gjy+ERp3WAUjLEFJE+02kanyHtwjWOnwrKYBiwAmM0p4kLJAnXg=="], "fdir": ["fdir@6.5.0", "", { "peerDependencies": { "picomatch": "^3 || ^4" }, "optionalPeers": ["picomatch"] }, "sha512-tIbYtZbucOs0BRGqPJkshJUYdL+SDH7dVM8gjy+ERp3WAUjLEFJE+02kanyHtwjWOnwrKYBiwAmM0p4kLJAnXg=="],
@@ -552,6 +691,8 @@
"foreground-child": ["foreground-child@3.3.1", "", { "dependencies": { "cross-spawn": "^7.0.6", "signal-exit": "^4.0.1" } }, "sha512-gIXjKqtFuWEgzFRJA9WCQeSJLZDjgJUOMCMzxtvFq/37KojM1BFGufqsCy0r4qSQmYLsZYMeyRqzIWOMup03sw=="], "foreground-child": ["foreground-child@3.3.1", "", { "dependencies": { "cross-spawn": "^7.0.6", "signal-exit": "^4.0.1" } }, "sha512-gIXjKqtFuWEgzFRJA9WCQeSJLZDjgJUOMCMzxtvFq/37KojM1BFGufqsCy0r4qSQmYLsZYMeyRqzIWOMup03sw=="],
"formatly": ["formatly@0.11.4", "", { "dependencies": { "fd-package-json": "^2.0.0", "package-manager-detector": "^1.8.0" }, "bin": { "formatly": "bin/index.mjs" } }, "sha512-TeCC10lP8KCgoX+Fe5lryILIT0/Dy+nP0OSVnsuB5CwXoLuOdqxCYlPFF1inR8S/zTy1ec7TjhS2TeRKWzzImA=="],
"formdata-polyfill": ["formdata-polyfill@4.0.10", "", { "dependencies": { "fetch-blob": "^3.1.2" } }, "sha512-buewHzMvYL29jdeQTVILecSaZKnt/RJWjoZCF5OW60Z67/GmSLBkOFM7qh1PI3zFNtJbaZL5eQu1vLfazOwj4g=="], "formdata-polyfill": ["formdata-polyfill@4.0.10", "", { "dependencies": { "fetch-blob": "^3.1.2" } }, "sha512-buewHzMvYL29jdeQTVILecSaZKnt/RJWjoZCF5OW60Z67/GmSLBkOFM7qh1PI3zFNtJbaZL5eQu1vLfazOwj4g=="],
"fs-minipass": ["fs-minipass@3.0.3", "", { "dependencies": { "minipass": "^7.0.3" } }, "sha512-XUBA9XClHbnJWSfBzjkm6RvPsyg3sryZt06BEQoXcF7EK/xpGaQYJgQKDJSUH5SGZ76Y7pFx1QBnXz09rU5Fbw=="], "fs-minipass": ["fs-minipass@3.0.3", "", { "dependencies": { "minipass": "^7.0.3" } }, "sha512-XUBA9XClHbnJWSfBzjkm6RvPsyg3sryZt06BEQoXcF7EK/xpGaQYJgQKDJSUH5SGZ76Y7pFx1QBnXz09rU5Fbw=="],
@@ -568,8 +709,12 @@
"get-east-asian-width": ["get-east-asian-width@1.6.0", "", {}, "sha512-QRbvDIbx6YklUe6RxeTeleMR0yv3cYH6PsPZHcnVn7xv7zO1BHN8r0XETu8n6Ye3Q+ahtSarc3WgtNWmehIBfA=="], "get-east-asian-width": ["get-east-asian-width@1.6.0", "", {}, "sha512-QRbvDIbx6YklUe6RxeTeleMR0yv3cYH6PsPZHcnVn7xv7zO1BHN8r0XETu8n6Ye3Q+ahtSarc3WgtNWmehIBfA=="],
"get-tsconfig": ["get-tsconfig@4.14.3", "", { "dependencies": { "resolve-pkg-maps": "^1.0.0" } }, "sha512-++QEw4DIY7WGoukz+/+A/8dGYPT9l9yIadnmSgZ8Rjr3YVSVDipQSO9CdnJo9ePqFqUUqh+wk9uIaoiAwsiPkA=="],
"glob": ["glob@13.0.5", "", { "dependencies": { "minimatch": "^10.2.1", "minipass": "^7.1.2", "path-scurry": "^2.0.0" } }, "sha512-BzXxZg24Ibra1pbQ/zE7Kys4Ua1ks7Bn6pKLkVPZ9FZe4JQS6/Q7ef3LG1H+k7lUf5l4T3PLSyYyYJVYUvfgTw=="], "glob": ["glob@13.0.5", "", { "dependencies": { "minimatch": "^10.2.1", "minipass": "^7.1.2", "path-scurry": "^2.0.0" } }, "sha512-BzXxZg24Ibra1pbQ/zE7Kys4Ua1ks7Bn6pKLkVPZ9FZe4JQS6/Q7ef3LG1H+k7lUf5l4T3PLSyYyYJVYUvfgTw=="],
"global-directory": ["global-directory@4.0.1", "", { "dependencies": { "ini": "4.1.1" } }, "sha512-wHTUcDUoZ1H5/0iVqEudYW4/kAlN5cZ3j/bXn0Dpbizl9iaUVeWSHqiOjsgk6OW2bkLclbBjzewBz6weQ1zA2Q=="],
"google-auth-library": ["google-auth-library@10.5.0", "", { "dependencies": { "base64-js": "^1.3.0", "ecdsa-sig-formatter": "^1.0.11", "gaxios": "^7.0.0", "gcp-metadata": "^8.0.0", "google-logging-utils": "^1.0.0", "gtoken": "^8.0.0", "jws": "^4.0.0" } }, "sha512-7ABviyMOlX5hIVD60YOfHw4/CxOfBhyduaYB+wbFWCWoni4N7SLcV46hrVRktuBbZjFC9ONyqamZITN7q3n32w=="], "google-auth-library": ["google-auth-library@10.5.0", "", { "dependencies": { "base64-js": "^1.3.0", "ecdsa-sig-formatter": "^1.0.11", "gaxios": "^7.0.0", "gcp-metadata": "^8.0.0", "google-logging-utils": "^1.0.0", "gtoken": "^8.0.0", "jws": "^4.0.0" } }, "sha512-7ABviyMOlX5hIVD60YOfHw4/CxOfBhyduaYB+wbFWCWoni4N7SLcV46hrVRktuBbZjFC9ONyqamZITN7q3n32w=="],
"google-logging-utils": ["google-logging-utils@1.2.0", "", {}, "sha512-WE9av4wKDZgRjBwgVUabocx8T6/7o3Ca1Fat46FXDhXVAFibzNadedcOXrdgd1Kzmk8tsk/9ZH89Wyf/SqeZ3A=="], "google-logging-utils": ["google-logging-utils@1.2.0", "", {}, "sha512-WE9av4wKDZgRjBwgVUabocx8T6/7o3Ca1Fat46FXDhXVAFibzNadedcOXrdgd1Kzmk8tsk/9ZH89Wyf/SqeZ3A=="],
@@ -578,6 +723,8 @@
"gtoken": ["gtoken@8.0.0", "", { "dependencies": { "gaxios": "^7.0.0", "jws": "^4.0.0" } }, "sha512-+CqsMbHPiSTdtSO14O51eMNlrp9N79gmeqmXeouJOhfucAedHw9noVe/n5uJk3tbKE6a+6ZCQg3RPhVhHByAIw=="], "gtoken": ["gtoken@8.0.0", "", { "dependencies": { "gaxios": "^7.0.0", "jws": "^4.0.0" } }, "sha512-+CqsMbHPiSTdtSO14O51eMNlrp9N79gmeqmXeouJOhfucAedHw9noVe/n5uJk3tbKE6a+6ZCQg3RPhVhHByAIw=="],
"has-flag": ["has-flag@4.0.0", "", {}, "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ=="],
"hasown": ["hasown@2.0.4", "", { "dependencies": { "function-bind": "^1.1.2" } }, "sha512-T2UbfbBEF32wiepXIsMlTW9+dDYC6wMh/t/vYA4tuOMKqWz/n3vr1NFSxQiyP+zk2mXsoMA/i/7qV6LKut1t1A=="], "hasown": ["hasown@2.0.4", "", { "dependencies": { "function-bind": "^1.1.2" } }, "sha512-T2UbfbBEF32wiepXIsMlTW9+dDYC6wMh/t/vYA4tuOMKqWz/n3vr1NFSxQiyP+zk2mXsoMA/i/7qV6LKut1t1A=="],
"hosted-git-info": ["hosted-git-info@9.0.3", "", { "dependencies": { "lru-cache": "^11.1.0" } }, "sha512-Hc+ghLoSt6QaYZUv0WBiIvmMDZuZZ7oaDvdH8MbfOO4lOsxdXLEvuC6ePoGs9H1X9oCLyq6+NVN0MKqD+ydxyg=="], "hosted-git-info": ["hosted-git-info@9.0.3", "", { "dependencies": { "lru-cache": "^11.1.0" } }, "sha512-Hc+ghLoSt6QaYZUv0WBiIvmMDZuZZ7oaDvdH8MbfOO4lOsxdXLEvuC6ePoGs9H1X9oCLyq6+NVN0MKqD+ydxyg=="],
@@ -592,10 +739,14 @@
"iconv-lite": ["iconv-lite@0.7.3", "", { "dependencies": { "safer-buffer": ">= 2.1.2 < 3.0.0" } }, "sha512-IKXpvIzjnC9XTAUbVBcMfGS0EPaIXtW6v+zr+RRp+hqULEpo0owZax6wyRwPOJbWbzjYspQwusTsfVr0ifh4uQ=="], "iconv-lite": ["iconv-lite@0.7.3", "", { "dependencies": { "safer-buffer": ">= 2.1.2 < 3.0.0" } }, "sha512-IKXpvIzjnC9XTAUbVBcMfGS0EPaIXtW6v+zr+RRp+hqULEpo0owZax6wyRwPOJbWbzjYspQwusTsfVr0ifh4uQ=="],
"ignore": ["ignore@7.0.12", "", {}, "sha512-/8UvqAPU9DGTI9k4mxtf49U37Isfwr8Uts96+SBHIkFxPJnHS0Ew4f00sM4Scd8V8EjM0jUNtVDdv1kPdt35lg=="],
"ignore-walk": ["ignore-walk@8.0.0", "", { "dependencies": { "minimatch": "^10.0.3" } }, "sha512-FCeMZT4NiRQGh+YkeKMtWrOmBgWjHjMJ26WQWrRQyoyzqevdaGSakUaJW5xQYmjLlUVk2qUnCjYVBax9EKKg8A=="], "ignore-walk": ["ignore-walk@8.0.0", "", { "dependencies": { "minimatch": "^10.0.3" } }, "sha512-FCeMZT4NiRQGh+YkeKMtWrOmBgWjHjMJ26WQWrRQyoyzqevdaGSakUaJW5xQYmjLlUVk2qUnCjYVBax9EKKg8A=="],
"ini": ["ini@6.0.0", "", {}, "sha512-IBTdIkzZNOpqm7q3dRqJvMaldXjDHWkEDfrwGEQTs5eaQMWV+djAhR+wahyNNMAa+qpbDUhBMVt4ZKNwpPm7xQ=="], "ini": ["ini@6.0.0", "", {}, "sha512-IBTdIkzZNOpqm7q3dRqJvMaldXjDHWkEDfrwGEQTs5eaQMWV+djAhR+wahyNNMAa+qpbDUhBMVt4ZKNwpPm7xQ=="],
"interpret": ["interpret@3.1.1", "", {}, "sha512-6xwYfHbajpoF0xLW+iwLkhwgvLoZDfjYfoFNu8ftMoXINzwuymNLd9u/KmwtdT2GbR+/Cz66otEGEVVUHX9QLQ=="],
"ip-address": ["ip-address@10.7.0", "", {}, "sha512-BGFsyJd5mpXp3rK6jIdADLNgpJUK1jnjzvYF8lK+VyDab9JAmqN0YOKDdP17HlgKb2+ehPgDc8EtnRLbGCAMhA=="], "ip-address": ["ip-address@10.7.0", "", {}, "sha512-BGFsyJd5mpXp3rK6jIdADLNgpJUK1jnjzvYF8lK+VyDab9JAmqN0YOKDdP17HlgKb2+ehPgDc8EtnRLbGCAMhA=="],
"is-core-module": ["is-core-module@2.16.2", "", { "dependencies": { "hasown": "^2.0.3" } }, "sha512-evOr8xfXKxE6qSR0hSXL2r3sd7ALj8+7jQEUvPYcm5sgZFdJ+AYzT6yNmJenvIYQBgIGwfwz08sL8zoL7yq2BA=="], "is-core-module": ["is-core-module@2.16.2", "", { "dependencies": { "hasown": "^2.0.3" } }, "sha512-evOr8xfXKxE6qSR0hSXL2r3sd7ALj8+7jQEUvPYcm5sgZFdJ+AYzT6yNmJenvIYQBgIGwfwz08sL8zoL7yq2BA=="],
@@ -608,14 +759,38 @@
"is-inside-container": ["is-inside-container@1.0.0", "", { "dependencies": { "is-docker": "^3.0.0" }, "bin": { "is-inside-container": "cli.js" } }, "sha512-KIYLCCJghfHZxqjYBE7rEy0OBuTd5xCHS7tHVgvCLkx7StIoaxwNW3hCALgEUjFfeRk+MG/Qxmp/vtETEF3tRA=="], "is-inside-container": ["is-inside-container@1.0.0", "", { "dependencies": { "is-docker": "^3.0.0" }, "bin": { "is-inside-container": "cli.js" } }, "sha512-KIYLCCJghfHZxqjYBE7rEy0OBuTd5xCHS7tHVgvCLkx7StIoaxwNW3hCALgEUjFfeRk+MG/Qxmp/vtETEF3tRA=="],
"is-installed-globally": ["is-installed-globally@1.0.1", "", { "dependencies": { "global-directory": "^4.0.1", "is-path-inside": "^4.0.0" } }, "sha512-li88H4QGRoNMX27jEmY8nR515oJVspAgC/WFMlhHfFV8RJ4QyGpHhXnwAe9gH5RIgKmdYRUmrOhQobcgEjIdSw=="],
"is-path-inside": ["is-path-inside@4.0.0", "", {}, "sha512-lJJV/5dYS+RcL8uQdBDW9c9uWFLLBNRyFhnAKXw5tVqLlKZ4RMGZKv+YQ/IA3OhD+RpbJa1LLFM1FQPGyIXvOA=="],
"is-wsl": ["is-wsl@3.1.1", "", { "dependencies": { "is-inside-container": "^1.0.0" } }, "sha512-e6rvdUCiQCAuumZslxRJWR/Doq4VpPR82kqclvcS0efgt430SlGIk05vdCN58+VrzgtIcfNODjozVielycD4Sw=="], "is-wsl": ["is-wsl@3.1.1", "", { "dependencies": { "is-inside-container": "^1.0.0" } }, "sha512-e6rvdUCiQCAuumZslxRJWR/Doq4VpPR82kqclvcS0efgt430SlGIk05vdCN58+VrzgtIcfNODjozVielycD4Sw=="],
"isexe": ["isexe@2.0.0", "", {}, "sha512-RHxMLp9lnKHGHRng9QFhRCMbYAcVpn69smSGcq3f36xjgVVWThj4qqLbTLlq7Ssj8B+fIQ1EuCEGI2lKsyQeIw=="], "isexe": ["isexe@2.0.0", "", {}, "sha512-RHxMLp9lnKHGHRng9QFhRCMbYAcVpn69smSGcq3f36xjgVVWThj4qqLbTLlq7Ssj8B+fIQ1EuCEGI2lKsyQeIw=="],
"jackspeak": ["jackspeak@3.4.3", "", { "dependencies": { "@isaacs/cliui": "^8.0.2" }, "optionalDependencies": { "@pkgjs/parseargs": "^0.11.0" } }, "sha512-OGlZQpz2yfahA/Rd1Y8Cd9SIEsqvXkLVoSw/cgwhnhFMDbsQFeZYoJJ7bIZBS9BcamUW96asq/npPWugM+RQBw=="], "jackspeak": ["jackspeak@3.4.3", "", { "dependencies": { "@isaacs/cliui": "^8.0.2" }, "optionalDependencies": { "@pkgjs/parseargs": "^0.11.0" } }, "sha512-OGlZQpz2yfahA/Rd1Y8Cd9SIEsqvXkLVoSw/cgwhnhFMDbsQFeZYoJJ7bIZBS9BcamUW96asq/npPWugM+RQBw=="],
"jiti": ["jiti@2.7.0", "", { "bin": { "jiti": "lib/jiti-cli.mjs" } }, "sha512-AC/7JofJvZGrrneWNaEnJeOLUx+JlGt7tNa0wZiRPT4MY1wmfKjt2+6O2p2uz2+skll8OZZmJMNqeke7kKbNgQ=="],
"js-tokens": ["js-tokens@4.0.0", "", {}, "sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ=="], "js-tokens": ["js-tokens@4.0.0", "", {}, "sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ=="],
"jscpd": ["jscpd@5.4.1", "", { "optionalDependencies": { "jscpd-darwin-arm64": "5.4.1", "jscpd-darwin-x64": "5.4.1", "jscpd-linux-arm64-gnu": "5.4.1", "jscpd-linux-arm64-musl": "5.4.1", "jscpd-linux-x64-gnu": "5.4.1", "jscpd-linux-x64-musl": "5.4.1", "jscpd-windows-arm64-msvc": "5.4.1", "jscpd-windows-x64-msvc": "5.4.1" }, "bin": { "jscpd": "run-jscpd.js" } }, "sha512-afUt+LSQMmzSPYrWZlNGTwj8X4tmwVJbMNmr92qxPf4uUF/naLwG7SQyMPEZtrHqGgzGxmAzNjiwlVdjls2MyQ=="],
"jscpd-darwin-arm64": ["jscpd-darwin-arm64@5.4.1", "", { "os": "darwin", "cpu": "arm64" }, "sha512-LXHVeH60C9BsozcVIMPmXWvj97KqFKbCJYmYG4hDwfwIwS1kz+uF7yiObckP6h2xo12pD88nI4XjWTB5frjZUw=="],
"jscpd-darwin-x64": ["jscpd-darwin-x64@5.4.1", "", { "os": "darwin", "cpu": "x64" }, "sha512-Gqck4tcMZjv4IvYHU2Vcikb885zTADo5T/YfEqeu1i5W5tfFpLdViiTYrh5wbrW+uxBqC33gHpG1hy0xbGYknQ=="],
"jscpd-linux-arm64-gnu": ["jscpd-linux-arm64-gnu@5.4.1", "", { "os": "linux", "cpu": "arm64" }, "sha512-XUYZJZVxSY7JIBEoyOOMTgvJwmymkns4wG55tu6I/vRKXnS5QtaTESQfRLt6xj1+62aflAvr01FAhPAy+du6tA=="],
"jscpd-linux-arm64-musl": ["jscpd-linux-arm64-musl@5.4.1", "", { "os": "linux", "cpu": "arm64" }, "sha512-h2sH8Bk++yBxWqq2QAy4fvPzXkw1vecDSyOmzLwPfnRQoQ2Q/EWxCNOrgJSb+SNMLWoHLLzfqx8m9wt2GG6a8w=="],
"jscpd-linux-x64-gnu": ["jscpd-linux-x64-gnu@5.4.1", "", { "os": "linux", "cpu": "x64" }, "sha512-UiC4YoGAVVLy6hPVz8A6cndo7W5br4FAO2hADnFeinhBPnXPu0QFh1q/s/8B3ldeQHQkpYd/l5cjqNBMrbm78w=="],
"jscpd-linux-x64-musl": ["jscpd-linux-x64-musl@5.4.1", "", { "os": "linux", "cpu": "x64" }, "sha512-toAafl5roqfFotPrDJNMY9noNVZ9dReBqcO/nT5pJ8+7aq+opbscaLUcV4+8jxTq5btUD6CiO72+Fu+TyUZv3Q=="],
"jscpd-windows-arm64-msvc": ["jscpd-windows-arm64-msvc@5.4.1", "", { "os": "win32", "cpu": "arm64" }, "sha512-JLMga/NIwv/OPurPsXA2/d5OdWfdwrsBk2D4NhyKnrV/uNjo1BIi2zXztzDyTQVKMK/TEK6GPgLD143GG1fZ0A=="],
"jscpd-windows-x64-msvc": ["jscpd-windows-x64-msvc@5.4.1", "", { "os": "win32", "cpu": "x64" }, "sha512-sN57Y9YP3ijrqc1IsWDceOFHUwbukg9/mU2NSDHTryKKc5CUvWz+o9GId8uKTiJIhkKfR/Ce5GKkCepTwB6kaw=="],
"jsesc": ["jsesc@3.1.0", "", { "bin": { "jsesc": "bin/jsesc" } }, "sha512-/sM3dO2FOzXjKQhJuo0Q173wf2KOo8t4I8vHy6lF9poUp7bKT0/NHE8fPX23PwfhnykfqnC2xRxOnVw5XuGIaA=="], "jsesc": ["jsesc@3.1.0", "", { "bin": { "jsesc": "bin/jsesc" } }, "sha512-/sM3dO2FOzXjKQhJuo0Q173wf2KOo8t4I8vHy6lF9poUp7bKT0/NHE8fPX23PwfhnykfqnC2xRxOnVw5XuGIaA=="],
"json-bigint": ["json-bigint@1.0.0", "", { "dependencies": { "bignumber.js": "^9.0.0" } }, "sha512-SiPv/8VpZuWbvLSMtTDU8hEfrZWg/mH/nV/b4o0CYbSxu1UIQPLdwKOCIyLQX+VIPO5vrLX3i8qtqFyhdPSUSQ=="], "json-bigint": ["json-bigint@1.0.0", "", { "dependencies": { "bignumber.js": "^9.0.0" } }, "sha512-SiPv/8VpZuWbvLSMtTDU8hEfrZWg/mH/nV/b4o0CYbSxu1UIQPLdwKOCIyLQX+VIPO5vrLX3i8qtqFyhdPSUSQ=="],
@@ -638,6 +813,10 @@
"jws": ["jws@4.0.1", "", { "dependencies": { "jwa": "^2.0.1", "safe-buffer": "^5.0.1" } }, "sha512-EKI/M/yqPncGUUh44xz0PxSidXFr/+r0pA70+gIYhjv+et7yxM+s29Y+VGDkovRofQem0fs7Uvf4+YmAdyRduA=="], "jws": ["jws@4.0.1", "", { "dependencies": { "jwa": "^2.0.1", "safe-buffer": "^5.0.1" } }, "sha512-EKI/M/yqPncGUUh44xz0PxSidXFr/+r0pA70+gIYhjv+et7yxM+s29Y+VGDkovRofQem0fs7Uvf4+YmAdyRduA=="],
"kleur": ["kleur@3.0.3", "", {}, "sha512-eTIzlVOSUR+JxdDFepEYcBMtZ9Qqdef+rnzWdRZuMbOywu5tO2w2N7rqjoANZ5k9vywhL6Br1VRjUIgTQx4E8w=="],
"knip": ["knip@6.41.0", "", { "dependencies": { "formatly": "^0.11.4", "get-tsconfig": "4.14.3", "jiti": "^2.7.0", "oxc-parser": "^0.153.0", "oxc-resolver": "11.24.2", "picomatch": "^4.0.7", "smol-toml": "^1.9.0", "strip-json-comments": "5.0.3", "tinyglobby": "^0.2.17", "unbash": "^5.0.0", "yaml": "^2.9.1", "zod": "^4.6.5" }, "bin": { "knip": "bin/knip.js", "knip-bun": "bin/knip-bun.js" } }, "sha512-DrhQlIuV6xScd5Q+WTF1znd1w41QzxFGCtAHXCajsH/ndGMotHoNYbdXbuFtzW3mIOmniHtZ7zCtvnQkUmJtQQ=="],
"locate-path": ["locate-path@3.0.0", "", { "dependencies": { "p-locate": "^3.0.0", "path-exists": "^3.0.0" } }, "sha512-7AO748wWnIhNqAuaty2ZWHkQHRSNfPVIsPIfwEOWO22AmaoVrWavlOcMR5nzTLNYvp36X220/maaRsrec1G65A=="], "locate-path": ["locate-path@3.0.0", "", { "dependencies": { "p-locate": "^3.0.0", "path-exists": "^3.0.0" } }, "sha512-7AO748wWnIhNqAuaty2ZWHkQHRSNfPVIsPIfwEOWO22AmaoVrWavlOcMR5nzTLNYvp36X220/maaRsrec1G65A=="],
"lru-cache": ["lru-cache@11.5.2", "", {}, "sha512-4pfM1Ff0x50o0tQwb5ucw/RzNyD0/YJME6IVcStalZuMWxdt3sR3huStTtxz4PUmvZfRguvDejasvQ2kifR11g=="], "lru-cache": ["lru-cache@11.5.2", "", {}, "sha512-4pfM1Ff0x50o0tQwb5ucw/RzNyD0/YJME6IVcStalZuMWxdt3sR3huStTtxz4PUmvZfRguvDejasvQ2kifR11g=="],
@@ -646,14 +825,14 @@
"marked": ["marked@17.0.1", "", { "bin": { "marked": "bin/marked.js" } }, "sha512-boeBdiS0ghpWcSwoNm/jJBwdpFaMnZWRzjA6SkUMYb40SVaN1x7mmfGKp0jvexGcx+7y2La5zRZsYFZI6Qpypg=="], "marked": ["marked@17.0.1", "", { "bin": { "marked": "bin/marked.js" } }, "sha512-boeBdiS0ghpWcSwoNm/jJBwdpFaMnZWRzjA6SkUMYb40SVaN1x7mmfGKp0jvexGcx+7y2La5zRZsYFZI6Qpypg=="],
"mime": ["mime@4.1.0", "", { "bin": { "mime": "bin/cli.js" } }, "sha512-X5ju04+cAzsojXKes0B/S4tcYtFAJ6tTMuSPBEn9CPGlrWr8Fiw7qYeLT0XyH80HSoAoqWCaz+MWKh22P7G1cw=="],
"mime-db": ["mime-db@1.54.0", "", {}, "sha512-aU5EJuIN2WDemCcAp2vFBfp/m4EAhWJnUNSSw0ixs7/kXbd6Pg64EmwJkNdFhB8aWt1sH2CTXrLxo/iAGV3oPQ=="], "mime-db": ["mime-db@1.54.0", "", {}, "sha512-aU5EJuIN2WDemCcAp2vFBfp/m4EAhWJnUNSSw0ixs7/kXbd6Pg64EmwJkNdFhB8aWt1sH2CTXrLxo/iAGV3oPQ=="],
"mime-types": ["mime-types@3.0.2", "", { "dependencies": { "mime-db": "^1.54.0" } }, "sha512-Lbgzdk0h4juoQ9fCKXW4by0UJqj+nOOrI9MJ1sSj4nI8aI2eo1qmvQEie4VD1glsS250n15LsWsYtCugiStS5A=="], "mime-types": ["mime-types@3.0.2", "", { "dependencies": { "mime-db": "^1.54.0" } }, "sha512-Lbgzdk0h4juoQ9fCKXW4by0UJqj+nOOrI9MJ1sSj4nI8aI2eo1qmvQEie4VD1glsS250n15LsWsYtCugiStS5A=="],
"minimatch": ["minimatch@10.2.5", "", { "dependencies": { "brace-expansion": "^5.0.5" } }, "sha512-MULkVLfKGYDFYejP07QOurDLLQpcjk7Fw+7jXS2R2czRQzR56yHRveU5NDJEOviH+hETZKSkIk5c+T23GjFUMg=="], "minimatch": ["minimatch@10.2.5", "", { "dependencies": { "brace-expansion": "^5.0.5" } }, "sha512-MULkVLfKGYDFYejP07QOurDLLQpcjk7Fw+7jXS2R2czRQzR56yHRveU5NDJEOviH+hETZKSkIk5c+T23GjFUMg=="],
"minimist": ["minimist@1.2.8", "", {}, "sha512-2yyAR8qBkN3YuheJanUpWC5U3bb5osDywNB8RzDVlDwDHbocAJveqqj1u8+SVD7jkWT4yvsHCpWqqWqAxb0zCA=="],
"minipass": ["minipass@7.1.3", "", {}, "sha512-tEBHqDnIoM/1rXME1zgka9g6Q2lcoCkxHLuc7ODJ5BxbP5d4c2Z5cGgtXAku59200Cx7diuHTOYfSBD8n6mm8A=="], "minipass": ["minipass@7.1.3", "", {}, "sha512-tEBHqDnIoM/1rXME1zgka9g6Q2lcoCkxHLuc7ODJ5BxbP5d4c2Z5cGgtXAku59200Cx7diuHTOYfSBD8n6mm8A=="],
"minipass-collect": ["minipass-collect@2.0.1", "", { "dependencies": { "minipass": "^7.0.3" } }, "sha512-D7V8PO9oaz7PWGLbCACuI1qEOsq7UKfLotx/C0Aet43fCUB/wfQ7DYeq2oR/svFJGYDHPr38SHATeaj/ZoKHKw=="], "minipass-collect": ["minipass-collect@2.0.1", "", { "dependencies": { "minipass": "^7.0.3" } }, "sha512-D7V8PO9oaz7PWGLbCACuI1qEOsq7UKfLotx/C0Aet43fCUB/wfQ7DYeq2oR/svFJGYDHPr38SHATeaj/ZoKHKw=="],
@@ -670,10 +849,6 @@
"ms": ["ms@2.1.3", "", {}, "sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA=="], "ms": ["ms@2.1.3", "", {}, "sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA=="],
"msgpackr": ["msgpackr@2.1.0", "", { "optionalDependencies": { "msgpackr-extract": "^3.0.4" } }, "sha512-p/pBCVO63CsvvpkomUnNNag6+n38rULuDA6HHe70o2gtC8ODI52foF/4ko2qQcp6OiErJXTmrZeXmsGGHsIQNQ=="],
"msgpackr-extract": ["msgpackr-extract@3.0.4", "", { "dependencies": { "node-gyp-build-optional-packages": "5.2.2" }, "optionalDependencies": { "@msgpackr-extract/msgpackr-extract-darwin-arm64": "3.0.4", "@msgpackr-extract/msgpackr-extract-darwin-x64": "3.0.4", "@msgpackr-extract/msgpackr-extract-linux-arm": "3.0.4", "@msgpackr-extract/msgpackr-extract-linux-arm64": "3.0.4", "@msgpackr-extract/msgpackr-extract-linux-x64": "3.0.4", "@msgpackr-extract/msgpackr-extract-win32-x64": "3.0.4" }, "bin": { "download-msgpackr-prebuilds": "bin/download-prebuilds.js" } }, "sha512-4kmO/MdyUIkLIvTPr8VHLil4AtoKIoniWPIEk5+CDy0xnWC84azhSFmuJ7PxZdsYtiP5kEeQsORAVIeMgxT+Hw=="],
"negotiator": ["negotiator@1.1.0", "", { "dependencies": { "content-type": "^2.1.0" } }, "sha512-NMPBRMJgiQHjbd8phG3Vebdx4kZ1H121rbl5IkMqeOsahptB9BKo/d7oJ3zTXqTgagn2bWlNSXkh0QUGM31RYg=="], "negotiator": ["negotiator@1.1.0", "", { "dependencies": { "content-type": "^2.1.0" } }, "sha512-NMPBRMJgiQHjbd8phG3Vebdx4kZ1H121rbl5IkMqeOsahptB9BKo/d7oJ3zTXqTgagn2bWlNSXkh0QUGM31RYg=="],
"node-domexception": ["node-domexception@1.0.0", "", {}, "sha512-/jKZoMpw0F8GRwl4/eLROPA3cfcXtLApP0QzLmUT/HuPCZWyB7IY9ZrMeKw2O/nFIqPQB3PVM9aYm0F312AXDQ=="], "node-domexception": ["node-domexception@1.0.0", "", {}, "sha512-/jKZoMpw0F8GRwl4/eLROPA3cfcXtLApP0QzLmUT/HuPCZWyB7IY9ZrMeKw2O/nFIqPQB3PVM9aYm0F312AXDQ=="],
@@ -682,8 +857,6 @@
"node-gyp": ["node-gyp@12.4.0", "", { "dependencies": { "env-paths": "^2.2.0", "exponential-backoff": "^3.1.1", "graceful-fs": "^4.2.6", "nopt": "^9.0.0", "proc-log": "^6.0.0", "semver": "^7.3.5", "tar": "^7.5.4", "tinyglobby": "^0.2.12", "undici": "^6.25.0", "which": "^6.0.0" }, "bin": { "node-gyp": "bin/node-gyp.js" } }, "sha512-OMcPNvqTCFUnNaBlmdgq+lfNqY7gTiSmNRDjY3uAXRyudeKZEZxu3CLtjMQrx4zZxCX2b/mpNqTtwuCJgXhHkw=="], "node-gyp": ["node-gyp@12.4.0", "", { "dependencies": { "env-paths": "^2.2.0", "exponential-backoff": "^3.1.1", "graceful-fs": "^4.2.6", "nopt": "^9.0.0", "proc-log": "^6.0.0", "semver": "^7.3.5", "tar": "^7.5.4", "tinyglobby": "^0.2.12", "undici": "^6.25.0", "which": "^6.0.0" }, "bin": { "node-gyp": "bin/node-gyp.js" } }, "sha512-OMcPNvqTCFUnNaBlmdgq+lfNqY7gTiSmNRDjY3uAXRyudeKZEZxu3CLtjMQrx4zZxCX2b/mpNqTtwuCJgXhHkw=="],
"node-gyp-build-optional-packages": ["node-gyp-build-optional-packages@5.2.2", "", { "dependencies": { "detect-libc": "^2.0.1" }, "bin": { "node-gyp-build-optional-packages": "bin.js", "node-gyp-build-optional-packages-optional": "optional.js", "node-gyp-build-optional-packages-test": "build-test.js" } }, "sha512-s+w+rBWnpTMwSFbaE0UXsRlg7hU4FjekKU4eyAih5T8nJuNZT1nNsskXpxmeqSK9UzkBl6UgRlnKc8hz8IEqOw=="],
"node-releases": ["node-releases@2.0.55", "", {}, "sha512-mIrE/Cw9y+9Au6dS5vDKDhQza9YvG6w+ZrS6X+ZzA7yFW/soAeaups4Qzn1bL6g5FVy8WtP79+0j82oPIbqRjQ=="], "node-releases": ["node-releases@2.0.55", "", {}, "sha512-mIrE/Cw9y+9Au6dS5vDKDhQza9YvG6w+ZrS6X+ZzA7yFW/soAeaups4Qzn1bL6g5FVy8WtP79+0j82oPIbqRjQ=="],
"nopt": ["nopt@9.0.0", "", { "dependencies": { "abbrev": "^4.0.0" }, "bin": { "nopt": "bin/nopt.js" } }, "sha512-Zhq3a+yFKrYwSBluL4H9XP3m3y5uvQkB/09CwDruCiRmR/UJYnn9W4R48ry0uGC70aeTPKLynBtscP9efFFcPw=="], "nopt": ["nopt@9.0.0", "", { "dependencies": { "abbrev": "^4.0.0" }, "bin": { "nopt": "bin/nopt.js" } }, "sha512-Zhq3a+yFKrYwSBluL4H9XP3m3y5uvQkB/09CwDruCiRmR/UJYnn9W4R48ry0uGC70aeTPKLynBtscP9efFFcPw=="],
@@ -704,9 +877,15 @@
"open": ["open@11.0.4", "", { "dependencies": { "default-browser": "^5.5.1", "define-lazy-prop": "^3.0.0", "is-in-ssh": "^1.0.0", "is-inside-container": "^1.0.0", "powershell-utils": "^0.2.1", "wsl-utils": "^1.0.0" } }, "sha512-++Zlftm0kVLPmzC06t6epuWmcRMDbI4z5P3NNX979WA/k23+NtSOynEGzsVfZwguKw2mi5umVgnBlJQMwRz4Pg=="], "open": ["open@11.0.4", "", { "dependencies": { "default-browser": "^5.5.1", "define-lazy-prop": "^3.0.0", "is-in-ssh": "^1.0.0", "is-inside-container": "^1.0.0", "powershell-utils": "^0.2.1", "wsl-utils": "^1.0.0" } }, "sha512-++Zlftm0kVLPmzC06t6epuWmcRMDbI4z5P3NNX979WA/k23+NtSOynEGzsVfZwguKw2mi5umVgnBlJQMwRz4Pg=="],
"oxfmt": ["oxfmt@0.71.0", "", { "dependencies": { "tinypool": "2.2.0" }, "optionalDependencies": { "@oxfmt/binding-android-arm-eabi": "0.71.0", "@oxfmt/binding-android-arm64": "0.71.0", "@oxfmt/binding-darwin-arm64": "0.71.0", "@oxfmt/binding-darwin-x64": "0.71.0", "@oxfmt/binding-freebsd-x64": "0.71.0", "@oxfmt/binding-linux-arm-gnueabihf": "0.71.0", "@oxfmt/binding-linux-arm-musleabihf": "0.71.0", "@oxfmt/binding-linux-arm64-gnu": "0.71.0", "@oxfmt/binding-linux-arm64-musl": "0.71.0", "@oxfmt/binding-linux-ppc64-gnu": "0.71.0", "@oxfmt/binding-linux-riscv64-gnu": "0.71.0", "@oxfmt/binding-linux-riscv64-musl": "0.71.0", "@oxfmt/binding-linux-s390x-gnu": "0.71.0", "@oxfmt/binding-linux-x64-gnu": "0.71.0", "@oxfmt/binding-linux-x64-musl": "0.71.0", "@oxfmt/binding-openharmony-arm64": "0.71.0", "@oxfmt/binding-win32-arm64-msvc": "0.71.0", "@oxfmt/binding-win32-ia32-msvc": "0.71.0", "@oxfmt/binding-win32-x64-msvc": "0.71.0" }, "peerDependencies": { "svelte": "^5.0.0", "vite-plus": "*" }, "optionalPeers": ["svelte", "vite-plus"], "bin": { "oxfmt": "bin/oxfmt" } }, "sha512-lUPUl0d/+Io5pDrsPXWs6rB4N/bpB78oj9CTDpnbulfDz+0r3XXcHPlQ7kRPJ2GjIT4nX+/mcqunOeP9BvsEtg=="], "oxc-parser": ["oxc-parser@0.153.0", "", { "dependencies": { "@oxc-project/types": "^0.153.0" }, "optionalDependencies": { "@oxc-parser/binding-android-arm-eabi": "0.153.0", "@oxc-parser/binding-android-arm64": "0.153.0", "@oxc-parser/binding-darwin-arm64": "0.153.0", "@oxc-parser/binding-darwin-x64": "0.153.0", "@oxc-parser/binding-freebsd-x64": "0.153.0", "@oxc-parser/binding-linux-arm-gnueabihf": "0.153.0", "@oxc-parser/binding-linux-arm-musleabihf": "0.153.0", "@oxc-parser/binding-linux-arm64-gnu": "0.153.0", "@oxc-parser/binding-linux-arm64-musl": "0.153.0", "@oxc-parser/binding-linux-ppc64-gnu": "0.153.0", "@oxc-parser/binding-linux-riscv64-gnu": "0.153.0", "@oxc-parser/binding-linux-riscv64-musl": "0.153.0", "@oxc-parser/binding-linux-s390x-gnu": "0.153.0", "@oxc-parser/binding-linux-x64-gnu": "0.153.0", "@oxc-parser/binding-linux-x64-musl": "0.153.0", "@oxc-parser/binding-openharmony-arm64": "0.153.0", "@oxc-parser/binding-win32-arm64-msvc": "0.153.0", "@oxc-parser/binding-win32-ia32-msvc": "0.153.0", "@oxc-parser/binding-win32-x64-msvc": "0.153.0" } }, "sha512-cEnpyyV1OJRXv++SFNw0z8i+2o/cr88rVLaOYJafELDoHM5yHvCAbwGRLvxuany6SNLcbblSMUyZaGzH+quSYg=="],
"oxlint": ["oxlint@1.86.0", "", { "optionalDependencies": { "@oxlint/binding-android-arm-eabi": "1.86.0", "@oxlint/binding-android-arm64": "1.86.0", "@oxlint/binding-darwin-arm64": "1.86.0", "@oxlint/binding-darwin-x64": "1.86.0", "@oxlint/binding-freebsd-x64": "1.86.0", "@oxlint/binding-linux-arm-gnueabihf": "1.86.0", "@oxlint/binding-linux-arm-musleabihf": "1.86.0", "@oxlint/binding-linux-arm64-gnu": "1.86.0", "@oxlint/binding-linux-arm64-musl": "1.86.0", "@oxlint/binding-linux-ppc64-gnu": "1.86.0", "@oxlint/binding-linux-riscv64-gnu": "1.86.0", "@oxlint/binding-linux-riscv64-musl": "1.86.0", "@oxlint/binding-linux-s390x-gnu": "1.86.0", "@oxlint/binding-linux-x64-gnu": "1.86.0", "@oxlint/binding-linux-x64-musl": "1.86.0", "@oxlint/binding-openharmony-arm64": "1.86.0", "@oxlint/binding-win32-arm64-msvc": "1.86.0", "@oxlint/binding-win32-ia32-msvc": "1.86.0", "@oxlint/binding-win32-x64-msvc": "1.86.0" }, "peerDependencies": { "oxlint-tsgolint": ">=7.0.2003", "vite-plus": "*" }, "optionalPeers": ["oxlint-tsgolint", "vite-plus"], "bin": { "oxlint": "bin/oxlint" } }, "sha512-og0lhgvZfgGF//gOOmZXvtr+GmBbAGEnbEhv/QUg7UW2Wi4wHMnJbnMD+zuHgPdJxdklfgpPupdlAaAySyxrZg=="], "oxc-resolver": ["oxc-resolver@11.24.2", "", { "optionalDependencies": { "@oxc-resolver/binding-android-arm-eabi": "11.24.2", "@oxc-resolver/binding-android-arm64": "11.24.2", "@oxc-resolver/binding-darwin-arm64": "11.24.2", "@oxc-resolver/binding-darwin-x64": "11.24.2", "@oxc-resolver/binding-freebsd-x64": "11.24.2", "@oxc-resolver/binding-linux-arm-gnueabihf": "11.24.2", "@oxc-resolver/binding-linux-arm-musleabihf": "11.24.2", "@oxc-resolver/binding-linux-arm64-gnu": "11.24.2", "@oxc-resolver/binding-linux-arm64-musl": "11.24.2", "@oxc-resolver/binding-linux-ppc64-gnu": "11.24.2", "@oxc-resolver/binding-linux-riscv64-gnu": "11.24.2", "@oxc-resolver/binding-linux-riscv64-musl": "11.24.2", "@oxc-resolver/binding-linux-s390x-gnu": "11.24.2", "@oxc-resolver/binding-linux-x64-gnu": "11.24.2", "@oxc-resolver/binding-linux-x64-musl": "11.24.2", "@oxc-resolver/binding-openharmony-arm64": "11.24.2", "@oxc-resolver/binding-wasm32-wasi": "11.24.2", "@oxc-resolver/binding-win32-arm64-msvc": "11.24.2", "@oxc-resolver/binding-win32-x64-msvc": "11.24.2" } }, "sha512-FY91FiDBj7ls5MsFS9jN3tjz2o0/zsdSsymlakySaBwVJZorHhkWyICLZMKxlu1R9vYo+sd3z1jwb4J8x7bNDw=="],
"oxfmt": ["oxfmt@0.72.0", "", { "dependencies": { "tinypool": "2.2.0" }, "optionalDependencies": { "@oxfmt/binding-android-arm-eabi": "0.72.0", "@oxfmt/binding-android-arm64": "0.72.0", "@oxfmt/binding-darwin-arm64": "0.72.0", "@oxfmt/binding-darwin-x64": "0.72.0", "@oxfmt/binding-freebsd-x64": "0.72.0", "@oxfmt/binding-linux-arm-gnueabihf": "0.72.0", "@oxfmt/binding-linux-arm-musleabihf": "0.72.0", "@oxfmt/binding-linux-arm64-gnu": "0.72.0", "@oxfmt/binding-linux-arm64-musl": "0.72.0", "@oxfmt/binding-linux-ppc64-gnu": "0.72.0", "@oxfmt/binding-linux-riscv64-gnu": "0.72.0", "@oxfmt/binding-linux-riscv64-musl": "0.72.0", "@oxfmt/binding-linux-s390x-gnu": "0.72.0", "@oxfmt/binding-linux-x64-gnu": "0.72.0", "@oxfmt/binding-linux-x64-musl": "0.72.0", "@oxfmt/binding-openharmony-arm64": "0.72.0", "@oxfmt/binding-win32-arm64-msvc": "0.72.0", "@oxfmt/binding-win32-ia32-msvc": "0.72.0", "@oxfmt/binding-win32-x64-msvc": "0.72.0" }, "peerDependencies": { "svelte": "^5.0.0", "vite-plus": "*" }, "optionalPeers": ["svelte", "vite-plus"], "bin": { "oxfmt": "bin/oxfmt" } }, "sha512-16OQeL0uhPZbfmT9S9WWM0Nv9+BmVi8Ra1uTYaSKj/qSCs6FB30KOhz9JoNYw6thT+K5bVxsk/tSEOu497i34g=="],
"oxlint": ["oxlint@1.87.0", "", { "optionalDependencies": { "@oxlint/binding-android-arm-eabi": "1.87.0", "@oxlint/binding-android-arm64": "1.87.0", "@oxlint/binding-darwin-arm64": "1.87.0", "@oxlint/binding-darwin-x64": "1.87.0", "@oxlint/binding-freebsd-x64": "1.87.0", "@oxlint/binding-linux-arm-gnueabihf": "1.87.0", "@oxlint/binding-linux-arm-musleabihf": "1.87.0", "@oxlint/binding-linux-arm64-gnu": "1.87.0", "@oxlint/binding-linux-arm64-musl": "1.87.0", "@oxlint/binding-linux-ppc64-gnu": "1.87.0", "@oxlint/binding-linux-riscv64-gnu": "1.87.0", "@oxlint/binding-linux-riscv64-musl": "1.87.0", "@oxlint/binding-linux-s390x-gnu": "1.87.0", "@oxlint/binding-linux-x64-gnu": "1.87.0", "@oxlint/binding-linux-x64-musl": "1.87.0", "@oxlint/binding-openharmony-arm64": "1.87.0", "@oxlint/binding-win32-arm64-msvc": "1.87.0", "@oxlint/binding-win32-ia32-msvc": "1.87.0", "@oxlint/binding-win32-x64-msvc": "1.87.0" }, "peerDependencies": { "oxlint-tsgolint": ">=7.0.2003", "vite-plus": "*" }, "optionalPeers": ["oxlint-tsgolint", "vite-plus"], "bin": { "oxlint": "bin/oxlint" } }, "sha512-drxVlaW7Oqq7wSy1CN25znRu00aRq8n57Q2wniJRxCmtYVz07ufCm7EVDPQFZURrTgQIjzKrVEHAD/HcvJXObg=="],
"oxlint-tsgolint": ["oxlint-tsgolint@7.0.2004", "", { "optionalDependencies": { "@oxlint-tsgolint/darwin-arm64": "7.0.2004", "@oxlint-tsgolint/darwin-x64": "7.0.2004", "@oxlint-tsgolint/linux-arm64": "7.0.2004", "@oxlint-tsgolint/linux-x64": "7.0.2004", "@oxlint-tsgolint/win32-arm64": "7.0.2004", "@oxlint-tsgolint/win32-x64": "7.0.2004" }, "bin": { "tsgolint": "./bin/tsgolint.js" } }, "sha512-vQ9WDF3fiZJvRdSDosNOflerOCOpwol6vWzVDxW76RcU19cjTh7engvkHLvmv+tzedR8fAiJUVUGr6IVZdkzXQ=="],
"p-limit": ["p-limit@2.3.0", "", { "dependencies": { "p-try": "^2.0.0" } }, "sha512-//88mFWSJx8lxCzwdAABTJL2MyWB12+eIY7MDL2SqLmAkeKU9qxRvWuSyTjm3FUmpBEMuFfckAIqEaVGUDxb6w=="], "p-limit": ["p-limit@2.3.0", "", { "dependencies": { "p-try": "^2.0.0" } }, "sha512-//88mFWSJx8lxCzwdAABTJL2MyWB12+eIY7MDL2SqLmAkeKU9qxRvWuSyTjm3FUmpBEMuFfckAIqEaVGUDxb6w=="],
@@ -718,6 +897,8 @@
"package-json-from-dist": ["package-json-from-dist@1.0.1", "", {}, "sha512-UEZIS3/by4OC8vL3P2dTXRETpebLI2NiI5vIrjaD/5UtrkFX/tNbwjTSRAGC/+7CAo2pIcBaRgWmcBBHcsaCIw=="], "package-json-from-dist": ["package-json-from-dist@1.0.1", "", {}, "sha512-UEZIS3/by4OC8vL3P2dTXRETpebLI2NiI5vIrjaD/5UtrkFX/tNbwjTSRAGC/+7CAo2pIcBaRgWmcBBHcsaCIw=="],
"package-manager-detector": ["package-manager-detector@1.9.0", "", {}, "sha512-zAMfbta9nPA8AKkA4WdmNAT8R8s6Dk0/xwPsqNnRidMFcLo1YkLuPDTgs2f64XdzS8vbLNnoJ+uUIkgbz7oRHA=="],
"pacote": ["pacote@21.5.1", "", { "dependencies": { "@gar/promise-retry": "^1.0.0", "@npmcli/git": "^7.0.0", "@npmcli/installed-package-contents": "^4.0.0", "@npmcli/package-json": "^7.0.0", "@npmcli/promise-spawn": "^9.0.0", "@npmcli/run-script": "^10.0.0", "cacache": "^20.0.0", "fs-minipass": "^3.0.0", "minipass": "^7.0.2", "npm-package-arg": "^13.0.0", "npm-packlist": "^10.0.1", "npm-pick-manifest": "^11.0.1", "npm-registry-fetch": "^19.0.0", "proc-log": "^6.0.0", "sigstore": "^4.0.0", "ssri": "^13.0.0", "tar": "^7.4.3" }, "bin": { "pacote": "bin/index.js" } }, "sha512-KvcJ9iy3crysCsgqc4+PknH/w6jkrp8JN36mpZBPwNaDRwTfMZD37YzRazNstiZUOhuF5pno9f78n9mEJBavwg=="], "pacote": ["pacote@21.5.1", "", { "dependencies": { "@gar/promise-retry": "^1.0.0", "@npmcli/git": "^7.0.0", "@npmcli/installed-package-contents": "^4.0.0", "@npmcli/package-json": "^7.0.0", "@npmcli/promise-spawn": "^9.0.0", "@npmcli/run-script": "^10.0.0", "cacache": "^20.0.0", "fs-minipass": "^3.0.0", "minipass": "^7.0.2", "npm-package-arg": "^13.0.0", "npm-packlist": "^10.0.1", "npm-pick-manifest": "^11.0.1", "npm-registry-fetch": "^19.0.0", "proc-log": "^6.0.0", "sigstore": "^4.0.0", "ssri": "^13.0.0", "tar": "^7.4.3" }, "bin": { "pacote": "bin/index.js" } }, "sha512-KvcJ9iy3crysCsgqc4+PknH/w6jkrp8JN36mpZBPwNaDRwTfMZD37YzRazNstiZUOhuF5pno9f78n9mEJBavwg=="],
"parse-conflict-json": ["parse-conflict-json@5.0.1", "", { "dependencies": { "json-parse-even-better-errors": "^5.0.0", "just-diff": "^6.0.0", "just-diff-apply": "^5.2.0" } }, "sha512-ZHEmNKMq1wyJXNwLxyHnluPfRAFSIliBvbK/UiOceROt4Xh9Pz0fq49NytIaeaCUf5VR86hwQ/34FCcNU5/LKQ=="], "parse-conflict-json": ["parse-conflict-json@5.0.1", "", { "dependencies": { "json-parse-even-better-errors": "^5.0.0", "just-diff": "^6.0.0", "just-diff-apply": "^5.2.0" } }, "sha512-ZHEmNKMq1wyJXNwLxyHnluPfRAFSIliBvbK/UiOceROt4Xh9Pz0fq49NytIaeaCUf5VR86hwQ/34FCcNU5/LKQ=="],
@@ -750,16 +931,22 @@
"promise-call-limit": ["promise-call-limit@3.0.2", "", {}, "sha512-mRPQO2T1QQVw11E7+UdCJu7S61eJVWknzml9sC1heAdj1jxl0fWMBypIt9ZOcLFf8FkG995ZD7RnVk7HH72fZw=="], "promise-call-limit": ["promise-call-limit@3.0.2", "", {}, "sha512-mRPQO2T1QQVw11E7+UdCJu7S61eJVWknzml9sC1heAdj1jxl0fWMBypIt9ZOcLFf8FkG995ZD7RnVk7HH72fZw=="],
"pure-rand": ["pure-rand@8.4.2", "", {}, "sha512-vvuOGgcuPJAirlHvuQw1TrOiw7ptaIXXmIbNuiNOY6lNGJJH49PQ1Kj4nd783nPdQhQdicgOjVI2yI/9BD6/Ng=="], "prompts": ["prompts@2.4.2", "", { "dependencies": { "kleur": "^3.0.3", "sisteransi": "^1.0.5" } }, "sha512-NxNv/kLguCA7p3jE8oL2aEBsrJWgAakBpgmgK6lpPWV+WuOmY6r2/zbAVnP+T8bQlA0nzHXSJSJW0Hq7ylaD2Q=="],
"read-cmd-shim": ["read-cmd-shim@6.0.0", "", {}, "sha512-1zM5HuOfagXCBWMN83fuFI/x+T/UhZ7k+KIzhrHXcQoeX5+7gmaDYjELQHmmzIodumBHeByBJT4QYS7ufAgs7A=="], "read-cmd-shim": ["read-cmd-shim@6.0.0", "", {}, "sha512-1zM5HuOfagXCBWMN83fuFI/x+T/UhZ7k+KIzhrHXcQoeX5+7gmaDYjELQHmmzIodumBHeByBJT4QYS7ufAgs7A=="],
"rechoir": ["rechoir@0.8.0", "", { "dependencies": { "resolve": "^1.20.0" } }, "sha512-/vxpCXddiX8NGfGO/mTafwjq4aFa/71pvamip0++IQk3zG8cbCj0fifNPrjjF1XMXUne91jL9OoxmdykoEtifQ=="],
"redis": ["redis@6.2.1", "", { "dependencies": { "@redis/bloom": "6.2.1", "@redis/client": "6.2.1", "@redis/json": "6.2.1", "@redis/search": "6.2.1", "@redis/time-series": "6.2.1" } }, "sha512-Z9VHtgYs48PiQC77X9O2Er8Hj4T+5BtFjT91/vi5Is1D04N72cA946ZslM1ImJw8ZctFBZWAVjM7S5wJNeHMpg=="], "redis": ["redis@6.2.1", "", { "dependencies": { "@redis/bloom": "6.2.1", "@redis/client": "6.2.1", "@redis/json": "6.2.1", "@redis/search": "6.2.1", "@redis/time-series": "6.2.1" } }, "sha512-Z9VHtgYs48PiQC77X9O2Er8Hj4T+5BtFjT91/vi5Is1D04N72cA946ZslM1ImJw8ZctFBZWAVjM7S5wJNeHMpg=="],
"regexp-tree": ["regexp-tree@0.1.27", "", { "bin": { "regexp-tree": "bin/regexp-tree" } }, "sha512-iETxpjK6YoRWJG5o6hXLwvjYAoW+FEZn9os0PD/b6AP6xQwsa/Y7lCVgIixBbUPMfhu+i2LtdeAqVTgGlQarfA=="],
"reselect": ["reselect@4.1.8", "", {}, "sha512-ab9EmR80F/zQTMNeneUr4cv+jSwPJgIlvEmVwLerwrWVbpLlBuls9XHzIeTFy4cegU2NHBp3va0LKOzU5qFEYQ=="], "reselect": ["reselect@4.1.8", "", {}, "sha512-ab9EmR80F/zQTMNeneUr4cv+jSwPJgIlvEmVwLerwrWVbpLlBuls9XHzIeTFy4cegU2NHBp3va0LKOzU5qFEYQ=="],
"resolve": ["resolve@1.22.12", "", { "dependencies": { "es-errors": "^1.3.0", "is-core-module": "^2.16.1", "path-parse": "^1.0.7", "supports-preserve-symlinks-flag": "^1.0.0" }, "bin": { "resolve": "bin/resolve" } }, "sha512-TyeJ1zif53BPfHootBGwPRYT1RUt6oGWsaQr8UyZW/eAm9bKoijtvruSDEmZHm92CwS9nj7/fWttqPCgzep8CA=="], "resolve": ["resolve@1.22.12", "", { "dependencies": { "es-errors": "^1.3.0", "is-core-module": "^2.16.1", "path-parse": "^1.0.7", "supports-preserve-symlinks-flag": "^1.0.0" }, "bin": { "resolve": "bin/resolve" } }, "sha512-TyeJ1zif53BPfHootBGwPRYT1RUt6oGWsaQr8UyZW/eAm9bKoijtvruSDEmZHm92CwS9nj7/fWttqPCgzep8CA=="],
"resolve-pkg-maps": ["resolve-pkg-maps@1.0.0", "", {}, "sha512-seS2Tj26TBVOC2NIc2rOe2y2ZO7efxITtLZcGSOnHHNOQ7CkiUBfw0Iw2ck6xkIhPwLhKNLS8BO+hEpngQlqzw=="],
"rimraf": ["rimraf@5.0.10", "", { "dependencies": { "glob": "^10.3.7" }, "bin": { "rimraf": "dist/esm/bin.mjs" } }, "sha512-l0OE8wL34P4nJH/H2ffoaniAokM2qSmrtXHmlpvYr5AVVX8msAyW0l8NVJFDxlSK4u3Uh/f41cQheDVdnYijwQ=="], "rimraf": ["rimraf@5.0.10", "", { "dependencies": { "glob": "^10.3.7" }, "bin": { "rimraf": "dist/esm/bin.mjs" } }, "sha512-l0OE8wL34P4nJH/H2ffoaniAokM2qSmrtXHmlpvYr5AVVX8msAyW0l8NVJFDxlSK4u3Uh/f41cQheDVdnYijwQ=="],
"run-applescript": ["run-applescript@7.1.0", "", {}, "sha512-DPe5pVFaAsinSaV6QjQ6gdiedWDcRCbUuiQfQa2wmWV7+xC9bGulGI8+TdRmoFkAPaBXk8CrAbnlY2ISniJ47Q=="], "run-applescript": ["run-applescript@7.1.0", "", {}, "sha512-DPe5pVFaAsinSaV6QjQ6gdiedWDcRCbUuiQfQa2wmWV7+xC9bGulGI8+TdRmoFkAPaBXk8CrAbnlY2ISniJ47Q=="],
@@ -768,9 +955,11 @@
"safe-buffer": ["safe-buffer@5.2.1", "", {}, "sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ=="], "safe-buffer": ["safe-buffer@5.2.1", "", {}, "sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ=="],
"safe-regex": ["safe-regex@2.1.1", "", { "dependencies": { "regexp-tree": "~0.1.1" } }, "sha512-rx+x8AMzKb5Q5lQ95Zoi6ZbJqwCLkqi3XuJXp5P3rT8OEc6sZCJG5AE5dU3lsgRr/F4Bs31jSlVN+j5KrsGu9A=="],
"safer-buffer": ["safer-buffer@2.1.2", "", {}, "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg=="], "safer-buffer": ["safer-buffer@2.1.2", "", {}, "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg=="],
"semver": ["semver@6.3.1", "", { "bin": { "semver": "bin/semver.js" } }, "sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA=="], "semver": ["semver@7.8.5", "", { "bin": { "semver": "bin/semver.js" } }, "sha512-Y7/KDsb8LjooZpwaqGyulO6DQlksgCncchHGk+sZIY4SBvUocMBEFH5Ur1fI4dV+Jvl0w6cjvucaIi40puRioA=="],
"seroval": ["seroval@1.5.6", "", {}, "sha512-rVQVWjjSvlINzaQPZH5JFqsqEsIWdTxY3iJZCnTL/5gQbXIRooVZKI60tVCkOVfzcRPejboxO2t0P89dg5mQaA=="], "seroval": ["seroval@1.5.6", "", {}, "sha512-rVQVWjjSvlINzaQPZH5JFqsqEsIWdTxY3iJZCnTL/5gQbXIRooVZKI60tVCkOVfzcRPejboxO2t0P89dg5mQaA=="],
@@ -784,8 +973,12 @@
"sigstore": ["sigstore@4.1.1", "", { "dependencies": { "@sigstore/bundle": "^4.0.0", "@sigstore/core": "^3.2.1", "@sigstore/protobuf-specs": "^0.5.0", "@sigstore/sign": "^4.1.1", "@sigstore/tuf": "^4.0.2", "@sigstore/verify": "^3.1.1" } }, "sha512-endqECJkfhozrXMK5ngu/UAA0xVcVEFdnHJCElGaExypjW+HK5i6zu3NteLoaX/iFbRUbC3+DjttQs0GARr+5w=="], "sigstore": ["sigstore@4.1.1", "", { "dependencies": { "@sigstore/bundle": "^4.0.0", "@sigstore/core": "^3.2.1", "@sigstore/protobuf-specs": "^0.5.0", "@sigstore/sign": "^4.1.1", "@sigstore/tuf": "^4.0.2", "@sigstore/verify": "^3.1.1" } }, "sha512-endqECJkfhozrXMK5ngu/UAA0xVcVEFdnHJCElGaExypjW+HK5i6zu3NteLoaX/iFbRUbC3+DjttQs0GARr+5w=="],
"sisteransi": ["sisteransi@1.0.5", "", {}, "sha512-bLGGlR1QxBcynn2d5YmDX4MGjlZvy2MRBDRNHLJ8VI6l6+9FUiyTFNJ0IveOSP0bcXgVDPRcfGqA0pjaqUpfVg=="],
"smart-buffer": ["smart-buffer@4.2.0", "", {}, "sha512-94hK0Hh8rPqQl2xXc3HsaBoOXKV20MToPkcXvwbISWLEs+64sBq5kFgn2kJDHb1Pry9yrP0dxrCI9RRci7RXKg=="], "smart-buffer": ["smart-buffer@4.2.0", "", {}, "sha512-94hK0Hh8rPqQl2xXc3HsaBoOXKV20MToPkcXvwbISWLEs+64sBq5kFgn2kJDHb1Pry9yrP0dxrCI9RRci7RXKg=="],
"smol-toml": ["smol-toml@1.9.1", "", {}, "sha512-j7WyPdf0CJoutMzMoPLF/bVXHtKZIT9Rb4eGeEbWw8X2t5oirjPgpL+OpaENZrILYaXqYwnVH+qgUwVbl+pUJQ=="],
"socks": ["socks@2.8.10", "", { "dependencies": { "ip-address": "^10.1.1", "smart-buffer": "^4.2.0" } }, "sha512-e0VyvkVTwVYViNovRkZ9aodhxVlyoMn7eJhVUPxZ+eK9P/7CBkxvvsBOHqFPEH416726W8tLXXXjKwqgTErrCQ=="], "socks": ["socks@2.8.10", "", { "dependencies": { "ip-address": "^10.1.1", "smart-buffer": "^4.2.0" } }, "sha512-e0VyvkVTwVYViNovRkZ9aodhxVlyoMn7eJhVUPxZ+eK9P/7CBkxvvsBOHqFPEH416726W8tLXXXjKwqgTErrCQ=="],
"socks-proxy-agent": ["socks-proxy-agent@8.0.5", "", { "dependencies": { "agent-base": "^7.1.2", "debug": "^4.3.4", "socks": "^2.8.3" } }, "sha512-HehCEsotFqbPW9sJ8WVYB6UbmIMv7kUUORIF2Nncq4VQvBfNBLibW9YZR5dlYCSUhwcD628pRllm7n+E+YTzJw=="], "socks-proxy-agent": ["socks-proxy-agent@8.0.5", "", { "dependencies": { "agent-base": "^7.1.2", "debug": "^4.3.4", "socks": "^2.8.3" } }, "sha512-HehCEsotFqbPW9sJ8WVYB6UbmIMv7kUUORIF2Nncq4VQvBfNBLibW9YZR5dlYCSUhwcD628pRllm7n+E+YTzJw=="],
@@ -804,12 +997,20 @@
"string-width-cjs": ["string-width@4.2.3", "", { "dependencies": { "emoji-regex": "^8.0.0", "is-fullwidth-code-point": "^3.0.0", "strip-ansi": "^6.0.1" } }, "sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g=="], "string-width-cjs": ["string-width@4.2.3", "", { "dependencies": { "emoji-regex": "^8.0.0", "is-fullwidth-code-point": "^3.0.0", "strip-ansi": "^6.0.1" } }, "sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g=="],
"strip-ansi": ["strip-ansi@7.1.2", "", { "dependencies": { "ansi-regex": "^6.0.1" } }, "sha512-gmBGslpoQJtgnMAvOVqGZpEz9dyoKTCzy2nfz/n8aIFhN/jCE/rCmcxabB6jOOHV+0WNnylOxaxBQPSvcWklhA=="], "strip-ansi": ["strip-ansi@7.2.0", "", { "dependencies": { "ansi-regex": "^6.2.2" } }, "sha512-yDPMNjp4WyfYBkHnjIRLfca1i6KMyGCtsVgoKe/z1+6vukgaENdgGBZt+ZmKPc4gavvEZ5OgHfHdrazhgNyG7w=="],
"strip-ansi-cjs": ["strip-ansi@6.0.1", "", { "dependencies": { "ansi-regex": "^5.0.1" } }, "sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A=="], "strip-ansi-cjs": ["strip-ansi@6.0.1", "", { "dependencies": { "ansi-regex": "^5.0.1" } }, "sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A=="],
"strip-bom": ["strip-bom@3.0.0", "", {}, "sha512-vavAMRXOgBVNF6nyEEmL3DBK19iRpDcoIwW+swQ+CbGiu7lju6t+JklA1MHweoWtadgt4ISVUsXLyDq34ddcwA=="],
"strip-json-comments": ["strip-json-comments@5.0.3", "", {}, "sha512-1tB5mhVo7U+ETBKNf92xT4hrQa3pm0MZ0PQvuDnWgAAGHDsfp4lPSpiS6psrSiet87wyGPh9ft6wmhOMQ0hDiw=="],
"supports-color": ["supports-color@7.2.0", "", { "dependencies": { "has-flag": "^4.0.0" } }, "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw=="],
"supports-preserve-symlinks-flag": ["supports-preserve-symlinks-flag@1.0.0", "", {}, "sha512-ot0WnXS9fgdkgIcePe6RHNk1WA8+muPa6cSjeR3V8K27q9BB1rTE3R1p7Hv0z1ZyAc8s6Vvv8DIyWf681MAt0w=="], "supports-preserve-symlinks-flag": ["supports-preserve-symlinks-flag@1.0.0", "", {}, "sha512-ot0WnXS9fgdkgIcePe6RHNk1WA8+muPa6cSjeR3V8K27q9BB1rTE3R1p7Hv0z1ZyAc8s6Vvv8DIyWf681MAt0w=="],
"tapable": ["tapable@2.3.3", "", {}, "sha512-uxc/zpqFg6x7C8vOE7lh6Lbda8eEL9zmVm/PLeTPBRhh1xCgdWaQ+J1CUieGpIfm2HdtsUpRv+HshiasBMcc6A=="],
"tar": ["tar@7.5.22", "", { "dependencies": { "@isaacs/fs-minipass": "^4.0.0", "chownr": "^3.0.0", "minipass": "^7.1.2", "minizlib": "^3.1.0", "yallist": "^5.0.0" } }, "sha512-MFO/QzvtAOmJbkhOaCTvbGcFN9L9b+JunIsDwaKljSOdcLMea3NJ1k9Usz/rjdfSXTq4dfzfeS7W4p4YOAAHeA=="], "tar": ["tar@7.5.22", "", { "dependencies": { "@isaacs/fs-minipass": "^4.0.0", "chownr": "^3.0.0", "minipass": "^7.1.2", "minizlib": "^3.1.0", "yallist": "^5.0.0" } }, "sha512-MFO/QzvtAOmJbkhOaCTvbGcFN9L9b+JunIsDwaKljSOdcLMea3NJ1k9Usz/rjdfSXTq4dfzfeS7W4p4YOAAHeA=="],
"tinyglobby": ["tinyglobby@0.2.17", "", { "dependencies": { "fdir": "^6.5.0", "picomatch": "^4.0.4" } }, "sha512-wXR/dYpcqKmfWpEdZjiKJOwCNFndD0DMnrW/cYjVGttEkBfVgcLFHoNrlj47mjOVic9yyNu65alsgF4NQyTa2g=="], "tinyglobby": ["tinyglobby@0.2.17", "", { "dependencies": { "fdir": "^6.5.0", "picomatch": "^4.0.4" } }, "sha512-wXR/dYpcqKmfWpEdZjiKJOwCNFndD0DMnrW/cYjVGttEkBfVgcLFHoNrlj47mjOVic9yyNu65alsgF4NQyTa2g=="],
@@ -818,13 +1019,19 @@
"treeverse": ["treeverse@3.0.0", "", {}, "sha512-gcANaAnd2QDZFmHFEOF4k7uc1J/6a6z3DJMd/QwEyxLoKGiptJRwid582r7QIsFlFMIZ3SnxfS52S4hm2DHkuQ=="], "treeverse": ["treeverse@3.0.0", "", {}, "sha512-gcANaAnd2QDZFmHFEOF4k7uc1J/6a6z3DJMd/QwEyxLoKGiptJRwid582r7QIsFlFMIZ3SnxfS52S4hm2DHkuQ=="],
"tsconfig-paths": ["tsconfig-paths@4.2.0", "", { "dependencies": { "json5": "^2.2.2", "minimist": "^1.2.6", "strip-bom": "^3.0.0" } }, "sha512-NoZ4roiN7LnbKn9QqE1amc9DJfzvZXxF4xDavcOWt1BPkdx+m+0gJuPM+S0vCe7zTJMYUP0R8pO2XMr+Y8oLIg=="],
"tsconfig-paths-webpack-plugin": ["tsconfig-paths-webpack-plugin@4.2.0", "", { "dependencies": { "chalk": "^4.1.0", "enhanced-resolve": "^5.7.0", "tapable": "^2.2.1", "tsconfig-paths": "^4.1.2" } }, "sha512-zbem3rfRS8BgeNK50Zz5SIQgXzLafiHjOwUAvk/38/o1jHn/V5QAgVUcz884or7WYcPaH3N2CIfUc2u0ul7UcA=="],
"tslib": ["tslib@2.8.1", "", {}, "sha512-oJFu94HQb+KVduSUQL7wnpmqnfmLsOA/nAh6b6EH0wCEoK0/mPeXU6c3wKDV83MkOuHPRHtSXKKU99IBazS/2w=="], "tslib": ["tslib@2.8.1", "", {}, "sha512-oJFu94HQb+KVduSUQL7wnpmqnfmLsOA/nAh6b6EH0wCEoK0/mPeXU6c3wKDV83MkOuHPRHtSXKKU99IBazS/2w=="],
"tuf-js": ["tuf-js@4.1.0", "", { "dependencies": { "@tufjs/models": "4.1.0", "debug": "^4.4.3", "make-fetch-happen": "^15.0.1" } }, "sha512-50QV99kCKH5P/Vs4E2Gzp7BopNV+KzTXqWeaxrfu5IQJBOULRsTIS9seSsOVT8ZnGXzCyx55nYWAi4qJzpZKEQ=="], "tuf-js": ["tuf-js@4.1.0", "", { "dependencies": { "@tufjs/models": "4.1.0", "debug": "^4.4.3", "make-fetch-happen": "^15.0.1" } }, "sha512-50QV99kCKH5P/Vs4E2Gzp7BopNV+KzTXqWeaxrfu5IQJBOULRsTIS9seSsOVT8ZnGXzCyx55nYWAi4qJzpZKEQ=="],
"typescript": ["typescript@7.0.2", "", { "optionalDependencies": { "@typescript/typescript-aix-ppc64": "7.0.2", "@typescript/typescript-darwin-arm64": "7.0.2", "@typescript/typescript-darwin-x64": "7.0.2", "@typescript/typescript-freebsd-arm64": "7.0.2", "@typescript/typescript-freebsd-x64": "7.0.2", "@typescript/typescript-linux-arm": "7.0.2", "@typescript/typescript-linux-arm64": "7.0.2", "@typescript/typescript-linux-loong64": "7.0.2", "@typescript/typescript-linux-mips64el": "7.0.2", "@typescript/typescript-linux-ppc64": "7.0.2", "@typescript/typescript-linux-riscv64": "7.0.2", "@typescript/typescript-linux-s390x": "7.0.2", "@typescript/typescript-linux-x64": "7.0.2", "@typescript/typescript-netbsd-arm64": "7.0.2", "@typescript/typescript-netbsd-x64": "7.0.2", "@typescript/typescript-openbsd-arm64": "7.0.2", "@typescript/typescript-openbsd-x64": "7.0.2", "@typescript/typescript-sunos-x64": "7.0.2", "@typescript/typescript-win32-arm64": "7.0.2", "@typescript/typescript-win32-x64": "7.0.2" }, "bin": { "tsc": "bin/tsc" } }, "sha512-8FYau96o3NKOhbjKi/qNvG/W5jhzxkbdm5sj9AbZ/5T5sWqn3hJgLfGx27sRKZWTvyzCP8dLRBTf5tBTSRVUNA=="], "typescript": ["typescript@7.0.2", "", { "optionalDependencies": { "@typescript/typescript-aix-ppc64": "7.0.2", "@typescript/typescript-darwin-arm64": "7.0.2", "@typescript/typescript-darwin-x64": "7.0.2", "@typescript/typescript-freebsd-arm64": "7.0.2", "@typescript/typescript-freebsd-x64": "7.0.2", "@typescript/typescript-linux-arm": "7.0.2", "@typescript/typescript-linux-arm64": "7.0.2", "@typescript/typescript-linux-loong64": "7.0.2", "@typescript/typescript-linux-mips64el": "7.0.2", "@typescript/typescript-linux-ppc64": "7.0.2", "@typescript/typescript-linux-riscv64": "7.0.2", "@typescript/typescript-linux-s390x": "7.0.2", "@typescript/typescript-linux-x64": "7.0.2", "@typescript/typescript-netbsd-arm64": "7.0.2", "@typescript/typescript-netbsd-x64": "7.0.2", "@typescript/typescript-openbsd-arm64": "7.0.2", "@typescript/typescript-openbsd-x64": "7.0.2", "@typescript/typescript-sunos-x64": "7.0.2", "@typescript/typescript-win32-arm64": "7.0.2", "@typescript/typescript-win32-x64": "7.0.2" }, "bin": { "tsc": "bin/tsc" } }, "sha512-8FYau96o3NKOhbjKi/qNvG/W5jhzxkbdm5sj9AbZ/5T5sWqn3hJgLfGx27sRKZWTvyzCP8dLRBTf5tBTSRVUNA=="],
"undici": ["undici@8.10.2", "", {}, "sha512-/y4/bH9YNU5hi9NIrpOuvGXFcxrj3CMrV+/AYpowAYTpHn8gX/XPFjNy766FPoYY0miQhdW977JFWKGNhBdwyQ=="], "unbash": ["unbash@5.0.0", "", {}, "sha512-RYNm/ISFtflWpIcXTPHHLJZ0mqzInav+L9ke9PcL+hHsSf9+Fd/syPb614Mlqs/O3AYgjnvxDOFl0a+zVqi1/w=="],
"undici": ["undici@8.11.2", "", {}, "sha512-u4UB2/IrKdU6lFxumHmmo1a3fCQO5tzQllRorfoRS63txhrB7xTpSn1PftwC4qEHkOaqP95fCWW4lJzwErwzhQ=="],
"undici-types": ["undici-types@8.9.0", "", {}, "sha512-KTDyRTYX8sWmKXAikPHHSyc63CRPETMctyjKFupcC6OBLXT3xsN0e9aF7m+mIXutFWpUXuedtowG7iLOzp0kQg=="], "undici-types": ["undici-types@8.9.0", "", {}, "sha512-KTDyRTYX8sWmKXAikPHHSyc63CRPETMctyjKFupcC6OBLXT3xsN0e9aF7m+mIXutFWpUXuedtowG7iLOzp0kQg=="],
@@ -836,6 +1043,8 @@
"walk-up-path": ["walk-up-path@4.0.0", "", {}, "sha512-3hu+tD8YzSLGuFYtPRb48vdhKMi0KQV5sn+uWr8+7dMEq/2G/dtLrdDinkLjqq5TIbIBjYJ4Ax/n3YiaW7QM8A=="], "walk-up-path": ["walk-up-path@4.0.0", "", {}, "sha512-3hu+tD8YzSLGuFYtPRb48vdhKMi0KQV5sn+uWr8+7dMEq/2G/dtLrdDinkLjqq5TIbIBjYJ4Ax/n3YiaW7QM8A=="],
"watskeburt": ["watskeburt@6.0.0", "", { "bin": { "watskeburt": "dist/run-cli.js" } }, "sha512-jfiuDABaxSkC71T6oZ3vCS99roYkSHm/+As+G0Dz8taAHQb+SJBvLEm5RlsgG71XdfAj3rv7eudUBTgwcQUPlQ=="],
"web-streams-polyfill": ["web-streams-polyfill@3.3.3", "", {}, "sha512-d2JWLCivmZYTSIoge9MsgFCZrt571BikcWGYkjC1khllbTeDlGqZ2D8vD8E/lJa8WGWbb7Plm8/XJYV7IJHZZw=="], "web-streams-polyfill": ["web-streams-polyfill@3.3.3", "", {}, "sha512-d2JWLCivmZYTSIoge9MsgFCZrt571BikcWGYkjC1khllbTeDlGqZ2D8vD8E/lJa8WGWbb7Plm8/XJYV7IJHZZw=="],
"web-tree-sitter": ["web-tree-sitter@0.25.10", "", { "peerDependencies": { "@types/emscripten": "^1.40.0" }, "optionalPeers": ["@types/emscripten"] }, "sha512-Y09sF44/13XvgVKgO2cNDw5rGk6s26MgoZPXLESvMXeefBf7i6/73eFurre0IsTW6E14Y0ArIzhUMmjoc7xyzA=="], "web-tree-sitter": ["web-tree-sitter@0.25.10", "", { "peerDependencies": { "@types/emscripten": "^1.40.0" }, "optionalPeers": ["@types/emscripten"] }, "sha512-Y09sF44/13XvgVKgO2cNDw5rGk6s26MgoZPXLESvMXeefBf7i6/73eFurre0IsTW6E14Y0ArIzhUMmjoc7xyzA=="],
@@ -848,41 +1057,37 @@
"write-file-atomic": ["write-file-atomic@7.0.1", "", { "dependencies": { "signal-exit": "^4.0.1" } }, "sha512-OTIk8iR8/aCRWBqvxrzxR0hgxWpnYBblY1S5hDWBQfk/VFmJwzmJgQFN3WsoUKHISv2eAwe+PpbUzyL1CKTLXg=="], "write-file-atomic": ["write-file-atomic@7.0.1", "", { "dependencies": { "signal-exit": "^4.0.1" } }, "sha512-OTIk8iR8/aCRWBqvxrzxR0hgxWpnYBblY1S5hDWBQfk/VFmJwzmJgQFN3WsoUKHISv2eAwe+PpbUzyL1CKTLXg=="],
"ws": ["ws@8.21.3", "", { "peerDependencies": { "bufferutil": "^4.0.1", "utf-8-validate": ">=5.0.2" }, "optionalPeers": ["bufferutil", "utf-8-validate"] }, "sha512-201TZ/kPWxoPr/OKWjquZR1SWKXcvxdH+e1xrx89b3YbmzLMFCLfnaG1HFIgWzJOEWZ7MvpK++odZufgYR50Rw=="], "ws": ["ws@8.22.0", "", { "peerDependencies": { "bufferutil": "^4.0.1", "utf-8-validate": ">=5.0.2" }, "optionalPeers": ["bufferutil", "utf-8-validate"] }, "sha512-Ydggc987+RO0AnWtZ/7Wq9FtNvcrL1b/RO0ud9mWjUPgDrsAAwQSF51sm2hm1XofbU/4jkpGEsLFsZZxU+1DOg=="],
"wsl-utils": ["wsl-utils@1.0.1", "", { "dependencies": { "is-wsl": "^3.1.0", "powershell-utils": "^0.2.0" } }, "sha512-c16PKLIRxBYpR3jSWsdS7SFp0COm5SOQdiFjY818dYFHJbMGuLBszpF07LBWmOS1uzrHa9VGdynsEgoeKy0oOQ=="], "wsl-utils": ["wsl-utils@1.0.1", "", { "dependencies": { "is-wsl": "^3.1.0", "powershell-utils": "^0.2.0" } }, "sha512-c16PKLIRxBYpR3jSWsdS7SFp0COm5SOQdiFjY818dYFHJbMGuLBszpF07LBWmOS1uzrHa9VGdynsEgoeKy0oOQ=="],
"yallist": ["yallist@5.0.0", "", {}, "sha512-YgvUTfwqyc7UXVMrB+SImsVYSmTS8X/tSrtdNZMImM+n7+QTriRXyXim0mBrTXNeqzVF0KWGgHPeiyViFFrNDw=="], "yallist": ["yallist@5.0.0", "", {}, "sha512-YgvUTfwqyc7UXVMrB+SImsVYSmTS8X/tSrtdNZMImM+n7+QTriRXyXim0mBrTXNeqzVF0KWGgHPeiyViFFrNDw=="],
"yaml": ["yaml@2.9.1", "", { "bin": { "yaml": "bin.mjs" } }, "sha512-3NxN8+78OdzbT7C/WjGsyfPAtJaN3FNDsWxv7Y7mcDsT/oOmgW8BpyQQFFBnvZE3j9Y2Sdz1ULFLezL7Eb2yFw=="],
"zod": ["zod@4.6.5", "", {}, "sha512-v5l/aFXZQeai4awLbOpSoHecE9UiMrnfx75tEXLjNonXVARxQ5mOeipTjROUchszUNCqnE+hqAMujRsRHsut2Q=="], "zod": ["zod@4.6.5", "", {}, "sha512-v5l/aFXZQeai4awLbOpSoHecE9UiMrnfx75tEXLjNonXVARxQ5mOeipTjROUchszUNCqnE+hqAMujRsRHsut2Q=="],
"@aws-crypto/sha256-browser/@smithy/util-utf8": ["@smithy/util-utf8@2.3.0", "", { "dependencies": { "@smithy/util-buffer-from": "^2.2.0", "tslib": "^2.6.2" } }, "sha512-R8Rdn8Hy72KKcebgLiv8jQcQkXoLMOGGv5uI1/k0l+snqkOzQ1R0ChUBCxWMlBsFMekWjq0wRudIweFs7sKT5A=="], "@aws-crypto/sha256-browser/@smithy/util-utf8": ["@smithy/util-utf8@2.3.0", "", { "dependencies": { "@smithy/util-buffer-from": "^2.2.0", "tslib": "^2.6.2" } }, "sha512-R8Rdn8Hy72KKcebgLiv8jQcQkXoLMOGGv5uI1/k0l+snqkOzQ1R0ChUBCxWMlBsFMekWjq0wRudIweFs7sKT5A=="],
"@aws-crypto/util/@smithy/util-utf8": ["@smithy/util-utf8@2.3.0", "", { "dependencies": { "@smithy/util-buffer-from": "^2.2.0", "tslib": "^2.6.2" } }, "sha512-R8Rdn8Hy72KKcebgLiv8jQcQkXoLMOGGv5uI1/k0l+snqkOzQ1R0ChUBCxWMlBsFMekWjq0wRudIweFs7sKT5A=="], "@aws-crypto/util/@smithy/util-utf8": ["@smithy/util-utf8@2.3.0", "", { "dependencies": { "@smithy/util-buffer-from": "^2.2.0", "tslib": "^2.6.2" } }, "sha512-R8Rdn8Hy72KKcebgLiv8jQcQkXoLMOGGv5uI1/k0l+snqkOzQ1R0ChUBCxWMlBsFMekWjq0wRudIweFs7sKT5A=="],
"@babel/core/semver": ["semver@6.3.1", "", { "bin": { "semver": "bin/semver.js" } }, "sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA=="],
"@babel/helper-compilation-targets/lru-cache": ["lru-cache@5.1.1", "", { "dependencies": { "yallist": "^3.0.2" } }, "sha512-KpNARQA3Iwv+jTA0utUVVbrh+Jlrr1Fv0e56GGzAFOXN7dk/FviaDW8LHmK52DlcH4WP2n6gI8vN1aesBFgo9w=="], "@babel/helper-compilation-targets/lru-cache": ["lru-cache@5.1.1", "", { "dependencies": { "yallist": "^3.0.2" } }, "sha512-KpNARQA3Iwv+jTA0utUVVbrh+Jlrr1Fv0e56GGzAFOXN7dk/FviaDW8LHmK52DlcH4WP2n6gI8vN1aesBFgo9w=="],
"@babel/helper-compilation-targets/semver": ["semver@6.3.1", "", { "bin": { "semver": "bin/semver.js" } }, "sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA=="],
"@babel/helper-create-class-features-plugin/semver": ["semver@6.3.1", "", { "bin": { "semver": "bin/semver.js" } }, "sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA=="],
"@isaacs/cliui/string-width": ["string-width@5.1.2", "", { "dependencies": { "eastasianwidth": "^0.2.0", "emoji-regex": "^9.2.2", "strip-ansi": "^7.0.1" } }, "sha512-HnLOCR3vjcY8beoNLtcjZ5/nxn2afmME6lhrDrebokqMap+XbeW8n9TXpPDOqdGK5qcI3oT0GKTW6wC7EMiVqA=="], "@isaacs/cliui/string-width": ["string-width@5.1.2", "", { "dependencies": { "eastasianwidth": "^0.2.0", "emoji-regex": "^9.2.2", "strip-ansi": "^7.0.1" } }, "sha512-HnLOCR3vjcY8beoNLtcjZ5/nxn2afmME6lhrDrebokqMap+XbeW8n9TXpPDOqdGK5qcI3oT0GKTW6wC7EMiVqA=="],
"@isaacs/cliui/strip-ansi": ["strip-ansi@7.2.0", "", { "dependencies": { "ansi-regex": "^6.2.2" } }, "sha512-yDPMNjp4WyfYBkHnjIRLfca1i6KMyGCtsVgoKe/z1+6vukgaENdgGBZt+ZmKPc4gavvEZ5OgHfHdrazhgNyG7w=="],
"@npmcli/arborist/semver": ["semver@7.8.5", "", { "bin": { "semver": "bin/semver.js" } }, "sha512-Y7/KDsb8LjooZpwaqGyulO6DQlksgCncchHGk+sZIY4SBvUocMBEFH5Ur1fI4dV+Jvl0w6cjvucaIi40puRioA=="],
"@npmcli/config/semver": ["semver@7.8.5", "", { "bin": { "semver": "bin/semver.js" } }, "sha512-Y7/KDsb8LjooZpwaqGyulO6DQlksgCncchHGk+sZIY4SBvUocMBEFH5Ur1fI4dV+Jvl0w6cjvucaIi40puRioA=="],
"@npmcli/fs/semver": ["semver@7.8.5", "", { "bin": { "semver": "bin/semver.js" } }, "sha512-Y7/KDsb8LjooZpwaqGyulO6DQlksgCncchHGk+sZIY4SBvUocMBEFH5Ur1fI4dV+Jvl0w6cjvucaIi40puRioA=="],
"@npmcli/git/semver": ["semver@7.8.5", "", { "bin": { "semver": "bin/semver.js" } }, "sha512-Y7/KDsb8LjooZpwaqGyulO6DQlksgCncchHGk+sZIY4SBvUocMBEFH5Ur1fI4dV+Jvl0w6cjvucaIi40puRioA=="],
"@npmcli/git/which": ["which@6.0.1", "", { "dependencies": { "isexe": "^4.0.0" }, "bin": { "node-which": "bin/which.js" } }, "sha512-oGLe46MIrCRqX7ytPUf66EAYvdeMIZYn3WaocqqKZAxrBpkqHfL/qvTyJ/bTk5+AqHCjXmrv3CEWgy368zhRUg=="], "@npmcli/git/which": ["which@6.0.1", "", { "dependencies": { "isexe": "^4.0.0" }, "bin": { "node-which": "bin/which.js" } }, "sha512-oGLe46MIrCRqX7ytPUf66EAYvdeMIZYn3WaocqqKZAxrBpkqHfL/qvTyJ/bTk5+AqHCjXmrv3CEWgy368zhRUg=="],
"@npmcli/metavuln-calculator/semver": ["semver@7.8.5", "", { "bin": { "semver": "bin/semver.js" } }, "sha512-Y7/KDsb8LjooZpwaqGyulO6DQlksgCncchHGk+sZIY4SBvUocMBEFH5Ur1fI4dV+Jvl0w6cjvucaIi40puRioA=="],
"@npmcli/package-json/semver": ["semver@7.8.5", "", { "bin": { "semver": "bin/semver.js" } }, "sha512-Y7/KDsb8LjooZpwaqGyulO6DQlksgCncchHGk+sZIY4SBvUocMBEFH5Ur1fI4dV+Jvl0w6cjvucaIi40puRioA=="],
"@npmcli/promise-spawn/which": ["which@6.0.1", "", { "dependencies": { "isexe": "^4.0.0" }, "bin": { "node-which": "bin/which.js" } }, "sha512-oGLe46MIrCRqX7ytPUf66EAYvdeMIZYn3WaocqqKZAxrBpkqHfL/qvTyJ/bTk5+AqHCjXmrv3CEWgy368zhRUg=="], "@npmcli/promise-spawn/which": ["which@6.0.1", "", { "dependencies": { "isexe": "^4.0.0" }, "bin": { "node-which": "bin/which.js" } }, "sha512-oGLe46MIrCRqX7ytPUf66EAYvdeMIZYn3WaocqqKZAxrBpkqHfL/qvTyJ/bTk5+AqHCjXmrv3CEWgy368zhRUg=="],
"@opencode/plugin/zod": ["zod@4.1.8", "", {}, "sha512-5R1P+WwQqmmMIEACyzSvo4JXHY5WiAFHRMg+zBZKgKS+Q1viRa0C1hmUKtHltoIFKtIdki3pRxkmpP74jnNYHQ=="], "acorn-loose/acorn": ["acorn@8.18.0", "", { "bin": { "acorn": "bin/acorn" } }, "sha512-lGq+9yr1/GuAWaVYIHRjvvySG5/4VfKIvC8EWxStPdcDh/Ka7FG3twP6v4d5BkravUilhIAsG4Qj83t02LWUPQ=="],
"acorn-walk/acorn": ["acorn@8.18.0", "", { "bin": { "acorn": "bin/acorn" } }, "sha512-lGq+9yr1/GuAWaVYIHRjvvySG5/4VfKIvC8EWxStPdcDh/Ka7FG3twP6v4d5BkravUilhIAsG4Qj83t02LWUPQ=="],
"babel-plugin-jsx-dom-expressions/@babel/helper-module-imports": ["@babel/helper-module-imports@7.18.6", "", { "dependencies": { "@babel/types": "^7.18.6" } }, "sha512-0NFvs3VkuSYbFi1x2Vd6tKrywq+z/cLeYC/RJNFrIX/30Bf5aiGYbtvGXolEktzJH8o5E5KJ3tT+nkxuuZFVlA=="], "babel-plugin-jsx-dom-expressions/@babel/helper-module-imports": ["@babel/helper-module-imports@7.18.6", "", { "dependencies": { "@babel/types": "^7.18.6" } }, "sha512-0NFvs3VkuSYbFi1x2Vd6tKrywq+z/cLeYC/RJNFrIX/30Bf5aiGYbtvGXolEktzJH8o5E5KJ3tT+nkxuuZFVlA=="],
@@ -892,40 +1097,30 @@
"gcp-metadata/google-logging-utils": ["google-logging-utils@1.1.3", "", {}, "sha512-eAmLkjDjAFCVXg7A1unxHsLf961m6y17QFqXqAXGj/gVkKFrEICfStRfwUlGNfeCEjNRa32JEWOUTlYXPyyKvA=="], "gcp-metadata/google-logging-utils": ["google-logging-utils@1.1.3", "", {}, "sha512-eAmLkjDjAFCVXg7A1unxHsLf961m6y17QFqXqAXGj/gVkKFrEICfStRfwUlGNfeCEjNRa32JEWOUTlYXPyyKvA=="],
"global-directory/ini": ["ini@4.1.1", "", {}, "sha512-QQnnxNyfvmHFIsj7gkPcYymR8Jdw/o7mp5ZFihxn6h8Ci6fh3Dx4E1gPjpQEpIuPo9XVNY/ZUwh4BPMjGyL01g=="],
"minipass-flush/minipass": ["minipass@3.3.6", "", { "dependencies": { "yallist": "^4.0.0" } }, "sha512-DxiNidxSEK+tHG6zOIklvNOwm3hvCrbUrdtzY74U6HKTJxvIDfOUL5W5P2Ghd3DTkhhKPYGqeNUIh5qcM4YBfw=="], "minipass-flush/minipass": ["minipass@3.3.6", "", { "dependencies": { "yallist": "^4.0.0" } }, "sha512-DxiNidxSEK+tHG6zOIklvNOwm3hvCrbUrdtzY74U6HKTJxvIDfOUL5W5P2Ghd3DTkhhKPYGqeNUIh5qcM4YBfw=="],
"minipass-pipeline/minipass": ["minipass@3.3.6", "", { "dependencies": { "yallist": "^4.0.0" } }, "sha512-DxiNidxSEK+tHG6zOIklvNOwm3hvCrbUrdtzY74U6HKTJxvIDfOUL5W5P2Ghd3DTkhhKPYGqeNUIh5qcM4YBfw=="], "minipass-pipeline/minipass": ["minipass@3.3.6", "", { "dependencies": { "yallist": "^4.0.0" } }, "sha512-DxiNidxSEK+tHG6zOIklvNOwm3hvCrbUrdtzY74U6HKTJxvIDfOUL5W5P2Ghd3DTkhhKPYGqeNUIh5qcM4YBfw=="],
"node-gyp/semver": ["semver@7.8.5", "", { "bin": { "semver": "bin/semver.js" } }, "sha512-Y7/KDsb8LjooZpwaqGyulO6DQlksgCncchHGk+sZIY4SBvUocMBEFH5Ur1fI4dV+Jvl0w6cjvucaIi40puRioA=="],
"node-gyp/undici": ["undici@6.28.1", "", {}, "sha512-zWpdTVD54H48CIybL0rWQ3ukpb9d23wM7eH5RtfdmeP70cWHNjtfo7P4vZX+5CoDcO53J4Pu5uXp7lNfjc6DRA=="], "node-gyp/undici": ["undici@6.28.1", "", {}, "sha512-zWpdTVD54H48CIybL0rWQ3ukpb9d23wM7eH5RtfdmeP70cWHNjtfo7P4vZX+5CoDcO53J4Pu5uXp7lNfjc6DRA=="],
"node-gyp/which": ["which@6.0.1", "", { "dependencies": { "isexe": "^4.0.0" }, "bin": { "node-which": "bin/which.js" } }, "sha512-oGLe46MIrCRqX7ytPUf66EAYvdeMIZYn3WaocqqKZAxrBpkqHfL/qvTyJ/bTk5+AqHCjXmrv3CEWgy368zhRUg=="], "node-gyp/which": ["which@6.0.1", "", { "dependencies": { "isexe": "^4.0.0" }, "bin": { "node-which": "bin/which.js" } }, "sha512-oGLe46MIrCRqX7ytPUf66EAYvdeMIZYn3WaocqqKZAxrBpkqHfL/qvTyJ/bTk5+AqHCjXmrv3CEWgy368zhRUg=="],
"npm-install-checks/semver": ["semver@7.8.5", "", { "bin": { "semver": "bin/semver.js" } }, "sha512-Y7/KDsb8LjooZpwaqGyulO6DQlksgCncchHGk+sZIY4SBvUocMBEFH5Ur1fI4dV+Jvl0w6cjvucaIi40puRioA=="],
"npm-package-arg/semver": ["semver@7.8.5", "", { "bin": { "semver": "bin/semver.js" } }, "sha512-Y7/KDsb8LjooZpwaqGyulO6DQlksgCncchHGk+sZIY4SBvUocMBEFH5Ur1fI4dV+Jvl0w6cjvucaIi40puRioA=="],
"npm-pick-manifest/semver": ["semver@7.8.5", "", { "bin": { "semver": "bin/semver.js" } }, "sha512-Y7/KDsb8LjooZpwaqGyulO6DQlksgCncchHGk+sZIY4SBvUocMBEFH5Ur1fI4dV+Jvl0w6cjvucaIi40puRioA=="],
"parse5/entities": ["entities@6.0.1", "", {}, "sha512-aN97NXWF6AWBTahfVOIrB/NShkzi5H7F9r1s9mD3cDj4Ko5f2qhhVoYMibXF7GlLveb/D2ioWay8lxI97Ven3g=="], "parse5/entities": ["entities@6.0.1", "", {}, "sha512-aN97NXWF6AWBTahfVOIrB/NShkzi5H7F9r1s9mD3cDj4Ko5f2qhhVoYMibXF7GlLveb/D2ioWay8lxI97Ven3g=="],
"rimraf/glob": ["glob@10.5.0", "", { "dependencies": { "foreground-child": "^3.1.0", "jackspeak": "^3.1.2", "minimatch": "^9.0.4", "minipass": "^7.1.2", "package-json-from-dist": "^1.0.0", "path-scurry": "^1.11.1" }, "bin": { "glob": "dist/esm/bin.mjs" } }, "sha512-DfXN8DfhJ7NH3Oe7cFmu3NCu1wKbkReJ8TorzSAFbSKrlNaQSKfIzqYqVY8zlbs2NLBbWpRiU52GX2PbaBVNkg=="], "rimraf/glob": ["glob@10.5.0", "", { "dependencies": { "foreground-child": "^3.1.0", "jackspeak": "^3.1.2", "minimatch": "^9.0.4", "minipass": "^7.1.2", "package-json-from-dist": "^1.0.0", "path-scurry": "^1.11.1" }, "bin": { "glob": "dist/esm/bin.mjs" } }, "sha512-DfXN8DfhJ7NH3Oe7cFmu3NCu1wKbkReJ8TorzSAFbSKrlNaQSKfIzqYqVY8zlbs2NLBbWpRiU52GX2PbaBVNkg=="],
"string-width/strip-ansi": ["strip-ansi@7.2.0", "", { "dependencies": { "ansi-regex": "^6.2.2" } }, "sha512-yDPMNjp4WyfYBkHnjIRLfca1i6KMyGCtsVgoKe/z1+6vukgaENdgGBZt+ZmKPc4gavvEZ5OgHfHdrazhgNyG7w=="],
"string-width-cjs/emoji-regex": ["emoji-regex@8.0.0", "", {}, "sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A=="], "string-width-cjs/emoji-regex": ["emoji-regex@8.0.0", "", {}, "sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A=="],
"string-width-cjs/strip-ansi": ["strip-ansi@6.0.1", "", { "dependencies": { "ansi-regex": "^5.0.1" } }, "sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A=="], "string-width-cjs/strip-ansi": ["strip-ansi@6.0.1", "", { "dependencies": { "ansi-regex": "^5.0.1" } }, "sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A=="],
"strip-ansi-cjs/ansi-regex": ["ansi-regex@5.0.1", "", {}, "sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ=="], "strip-ansi-cjs/ansi-regex": ["ansi-regex@5.0.1", "", {}, "sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ=="],
"wrap-ansi/ansi-styles": ["ansi-styles@6.2.3", "", {}, "sha512-4Dj6M28JB+oAH8kFkTLUo+a2jwOFkuqb3yucU0CANcRRUbxS0cP0nZYCGjcc3BNXwRIsUVmDGgzawme7zvJHvg=="],
"wrap-ansi/string-width": ["string-width@5.1.2", "", { "dependencies": { "eastasianwidth": "^0.2.0", "emoji-regex": "^9.2.2", "strip-ansi": "^7.0.1" } }, "sha512-HnLOCR3vjcY8beoNLtcjZ5/nxn2afmME6lhrDrebokqMap+XbeW8n9TXpPDOqdGK5qcI3oT0GKTW6wC7EMiVqA=="], "wrap-ansi/string-width": ["string-width@5.1.2", "", { "dependencies": { "eastasianwidth": "^0.2.0", "emoji-regex": "^9.2.2", "strip-ansi": "^7.0.1" } }, "sha512-HnLOCR3vjcY8beoNLtcjZ5/nxn2afmME6lhrDrebokqMap+XbeW8n9TXpPDOqdGK5qcI3oT0GKTW6wC7EMiVqA=="],
"wrap-ansi/strip-ansi": ["strip-ansi@7.2.0", "", { "dependencies": { "ansi-regex": "^6.2.2" } }, "sha512-yDPMNjp4WyfYBkHnjIRLfca1i6KMyGCtsVgoKe/z1+6vukgaENdgGBZt+ZmKPc4gavvEZ5OgHfHdrazhgNyG7w=="],
"wrap-ansi-cjs/ansi-styles": ["ansi-styles@4.3.0", "", { "dependencies": { "color-convert": "^2.0.1" } }, "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg=="],
"wrap-ansi-cjs/string-width": ["string-width@4.2.3", "", { "dependencies": { "emoji-regex": "^8.0.0", "is-fullwidth-code-point": "^3.0.0", "strip-ansi": "^6.0.1" } }, "sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g=="], "wrap-ansi-cjs/string-width": ["string-width@4.2.3", "", { "dependencies": { "emoji-regex": "^8.0.0", "is-fullwidth-code-point": "^3.0.0", "strip-ansi": "^6.0.1" } }, "sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g=="],
"wrap-ansi-cjs/strip-ansi": ["strip-ansi@6.0.1", "", { "dependencies": { "ansi-regex": "^5.0.1" } }, "sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A=="], "wrap-ansi-cjs/strip-ansi": ["strip-ansi@6.0.1", "", { "dependencies": { "ansi-regex": "^5.0.1" } }, "sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A=="],
+8 -7
View File
@@ -39,9 +39,10 @@ Load **Agents before Multi-work**, at both root and destination locations. Multi
Upgrading from the old `stanp-opencode` monolith is a clean break: existing bindings cannot resume, and quota tracking resets. Start new delegated sessions. Existing worktrees, workspaces, and old host storage remain untouched. New bindings persist normally under the new identity. Upgrading from the old `stanp-opencode` monolith is a clean break: existing bindings cannot resume, and quota tracking resets. Start new delegated sessions. Existing worktrees, workspaces, and old host storage remain untouched. New bindings persist normally under the new identity.
Use OpenCode **2.0.22**, the version this integration targets. The package Use OpenCode **2.0.27**, the version this integration targets. The package
retains Effect `4.0.0-rc.112` because OpenCode 2.0.22's client requires that pins Effect `4.0.1` because OpenCode 2.0.27's client requires that exact peer
exact peer version. Solid `1.9.15` matches the host's override and shared runtime; version, and the bundled copy must match the host's Effect internals (a mismatched
copy fails activation when registering scoped finalizers). Solid `1.9.15` matches the host's override and shared runtime;
OpenTUI Solid's exact `1.9.12` peer warning is expected. OpenTUI Solid's exact `1.9.12` peer warning is expected.
At both the root and destination locations, configure: At both the root and destination locations, configure:
@@ -143,7 +144,7 @@ The plugin composes the original **Effect executor** in place, preserving the
foreground results, background job handling, and completion notifications. It does foreground results, background job handling, and completion notifications. It does
not create substitute top-level sessions or a separate job scheduler. not create substitute top-level sessions or a separate job scheduler.
OpenCode 2.0.22 awaits a child-ID progress callback after child creation and before OpenCode 2.0.27 awaits a child-ID progress callback after child creation and before
prompting. The wrapper uses that boundary to create the worktree, move the explicit prompting. The wrapper uses that boundary to create the worktree, move the explicit
child ID, and confirm its actual session location before allowing the task prompt. child ID, and confirm its actual session location before allowing the task prompt.
A move-request acknowledgement alone is insufficient. Confirmation is bounded to A move-request acknowledgement alone is insufficient. Confirmation is bounded to
@@ -173,15 +174,15 @@ load Agents through the real Promise adapter followed by Multi-work, apply confi
both plugin transforms, replay twice, and test separate location registries sharing both plugin transforms, replay twice, and test separate location registries sharing
disk-backed bindings across plugin scope restarts. Their executor is simulated. disk-backed bindings across plugin scope restarts. Their executor is simulated.
An opt-in integration check runs the **real OpenCode 2.0.22 server and native An opt-in integration check runs the **real OpenCode 2.0.27 server and native
subagent executor**: subagent executor**:
```sh ```sh
OPENCODE_2022=/absolute/path/to/2.0.22/opencode bun scripts/test-multi-work-host.ts OPENCODE_2027=/absolute/path/to/2.0.27/opencode bun scripts/test-multi-work-host.ts
``` ```
It requires the exact-version binary (for Linux x64, published as It requires the exact-version binary (for Linux x64, published as
`@opencode/cli-linux-x64@2.0.22`), uses fresh HOME/XDG/config/database paths under `@opencode/cli-linux-x64@2.0.27`), uses fresh HOME/XDG/config/database paths under
the system temporary directory (or `TMPDIR`), and starts only loopback services. the system temporary directory (or `TMPDIR`), and starts only loopback services.
Herdr is a fake CLI performing real Git worktree operations in the fixture repository; the model is a deterministic Herdr is a fake CLI performing real Git worktree operations in the fixture repository; the model is a deterministic
HTTP endpoint. Fixture resources and logs are cleaned up after the host check. HTTP endpoint. Fixture resources and logs are cleaned up after the host check.
+15
View File
@@ -0,0 +1,15 @@
{
"$schema": "https://unpkg.com/knip@6/schema.json",
"entry": [
"src/agents/agents.ts",
"src/multi-work/multi-work.ts",
"src/quota/quota-plugin.ts",
"src/quota/quota-rpc.ts",
"src/quota/tui.tsx",
"scripts/*.ts",
"tests/**/*.test.ts",
"tests/fixtures/*.ts"
],
"project": ["src/**/*.{ts,tsx}", "scripts/**/*.ts", "tests/**/*.ts"],
"ignoreDependencies": ["@swc/core"]
}
+27 -18
View File
@@ -5,27 +5,27 @@
"type": "module", "type": "module",
"exports": { "exports": {
"./agents": { "./agents": {
"types": "./dist/agents.d.ts", "types": "./dist/agents/agents.d.ts",
"import": "./dist/agents.js" "import": "./dist/agents.js"
}, },
"./multi-work": { "./multi-work": {
"types": "./dist/multi-work.d.ts", "types": "./dist/multi-work/multi-work.d.ts",
"import": "./dist/multi-work.js" "import": "./dist/multi-work.js"
}, },
"./quota": { "./quota": {
"types": "./dist/quota-plugin.d.ts", "types": "./dist/quota/quota-plugin.d.ts",
"import": "./dist/quota-plugin.js" "import": "./dist/quota-plugin.js"
}, },
"./tui": { "./tui": {
"types": "./dist/tui.d.ts", "types": "./dist/quota/tui.d.ts",
"import": "./dist/tui.js" "import": "./dist/tui.js"
}, },
"./quota/tui": { "./quota/tui": {
"types": "./dist/tui.d.ts", "types": "./dist/quota/tui.d.ts",
"import": "./dist/tui.js" "import": "./dist/tui.js"
}, },
"./quota-rpc": { "./quota-rpc": {
"types": "./dist/quota-rpc.d.ts", "types": "./dist/quota/quota-rpc.d.ts",
"import": "./dist/quota-rpc.js" "import": "./dist/quota-rpc.js"
} }
}, },
@@ -39,33 +39,42 @@
}, },
"scripts": { "scripts": {
"check": "tsc --noEmit", "check": "tsc --noEmit",
"lint": "oxlint --deny-warnings .", "lint": "oxlint --type-aware --deny-warnings .",
"format": "oxfmt --write .", "format": "oxfmt --write .",
"format:check": "oxfmt --check .", "format:check": "oxfmt --check .",
"test": "bun test --conditions=browser", "test": "bun test --conditions=browser",
"build": "bun scripts/build.ts && tsc --project tsconfig.build.json --emitDeclarationOnly" "build": "bun scripts/build.ts && tsc --project tsconfig.build.json --emitDeclarationOnly",
"knip": "knip",
"duplicates": "jscpd",
"deps": "depcruise src scripts tests",
"verify": "bun run lint && bun run check && bun run knip && bun run duplicates && bun run deps && bun run format:check && bun run test"
}, },
"devDependencies": { "devDependencies": {
"@opencode/client": "2.0.22", "@opencode/client": "2.0.27",
"@opencode/plugin": "2.0.22", "@opencode/plugin": "2.0.27",
"@opencode/schema": "2.0.22", "@opencode/schema": "2.0.27",
"@opentui/core": "0.5.14", "@opentui/core": "0.6.1",
"@opentui/solid": "0.5.14", "@opentui/solid": "0.6.1",
"@oxlint/plugins": "1.86.0", "@oxlint/plugins": "1.87.0",
"@swc/core": "1.16.18",
"@types/bun": "1.4.2", "@types/bun": "1.4.2",
"oxfmt": "0.71.0", "dependency-cruiser": "18.6.0",
"oxlint": "1.86.0", "jscpd": "5.4.1",
"knip": "6.41.0",
"oxfmt": "0.72.0",
"oxlint": "1.87.0",
"oxlint-tsgolint": "7.0.2004",
"solid-js": "1.9.15", "solid-js": "1.9.15",
"typescript": "7.0.2" "typescript": "7.0.2"
}, },
"peerDependencies": { "peerDependencies": {
"@opencode/plugin": "2.0.22", "@opencode/plugin": "2.0.27",
"@opentui/core": ">=0.5.14", "@opentui/core": ">=0.5.14",
"@opentui/solid": ">=0.5.14", "@opentui/solid": ">=0.5.14",
"solid-js": ">=1.9.0" "solid-js": ">=1.9.0"
}, },
"dependencies": { "dependencies": {
"effect": "4.0.0-rc.112", "effect": "4.0.1",
"zod": "4.6.5" "zod": "4.6.5"
} }
} }
+8 -5
View File
@@ -7,24 +7,27 @@ export async function build() {
const results = await Promise.all([ const results = await Promise.all([
Bun.build({ Bun.build({
entrypoints: [ entrypoints: [
"src/agents.ts", "src/agents/agents.ts",
"src/multi-work.ts", "src/multi-work/multi-work.ts",
"src/quota-plugin.ts", "src/quota/quota-plugin.ts",
"src/quota-rpc.ts", "src/quota/quota-rpc.ts",
], ],
outdir: "dist", outdir: "dist",
naming: "[name].[ext]",
target: "bun", target: "bun",
format: "esm", format: "esm",
}), }),
Bun.build({ Bun.build({
entrypoints: ["scripts/install.ts"], entrypoints: ["scripts/install.ts"],
outdir: "dist", outdir: "dist",
naming: "[name].[ext]",
target: "bun", target: "bun",
format: "esm", format: "esm",
}), }),
Bun.build({ Bun.build({
entrypoints: ["src/tui.tsx"], entrypoints: ["src/quota/tui.tsx"],
outdir: "dist", outdir: "dist",
naming: "[name].[ext]",
target: "bun", target: "bun",
format: "esm", format: "esm",
external: ["@opencode/plugin/tui", "@opentui/solid", "solid-js"], external: ["@opencode/plugin/tui", "@opentui/solid", "solid-js"],
+118 -105
View File
@@ -50,11 +50,118 @@ const nativePlugin = z.union([
z.object({ id: z.string(), effect: z.function() }), z.object({ id: z.string(), effect: z.function() }),
]); ]);
type DirectoryExports = { ".": string; "./tui"?: string }; type DirectoryExports = { ".": string; "./tui"?: string };
type Name = (typeof names)[number];
async function prompt(retained: Name[]) {
const input = createInterface({ input: process.stdin, output: process.stdout });
try {
const defaults = retained.length > 0 ? retained : names;
const chosen = (
(
await input.question(`Plugins (agents,multi-work,quota) [${defaults.join(",")}]: `)
).trim() || defaults.join(",")
).split(",");
if (
chosen.includes("multi-work") &&
!chosen.includes("agents") &&
/^(y|yes)?$/iu.test(
(await input.question("Multi-work requires Agents. Add Agents? [Y/n]: ")).trim(),
)
)
chosen.push("agents");
return chosen;
} finally {
input.close();
}
}
async function choose(retained: Name[], selection?: string) {
if (selection !== undefined) return selection.split(",");
if (process.stdin.isTTY) return prompt(retained);
if (retained.length === 0)
throw new Error(
"Noninteractive installation requires --plugins agents,multi-work,quota (or a valid subset)",
);
return [...retained];
}
async function stage(source: string, staged: string, name: Name) {
const file = name === "quota" ? "quota-plugin" : name;
const entrypoint = join(source, "dist", `${file}.js`);
const { default: plugin } = z.object({ default: nativePlugin }).parse(await import(entrypoint));
if (plugin.id !== `stanp-opencode.${name}`)
throw new Error(`Invalid native OpenCode plugin: ${name}`);
const directory = join(staged, name);
await mkdir(directory);
await copyFile(entrypoint, join(directory, "index.js"));
const exports: DirectoryExports = { ".": "./index.js" };
if (name === "quota") {
const tui = join(source, "dist", "tui.js");
if (
!new Bun.Transpiler({ loader: "js" })
.scan(await Bun.file(tui).text())
.exports.includes("default")
)
throw new Error("Quota lacks its TUI entrypoint");
await copyFile(tui, join(directory, "tui.js"));
exports["./tui"] = "./tui.js";
}
await Bun.write(
join(directory, "package.json"),
JSON.stringify({
name: `stanp-opencode-${name}`,
type: "module",
main: "./index.js",
exports,
}),
);
}
async function activate(
source: string,
config: string,
selected: Name[],
updated: z.infer<typeof configSchema>,
) {
const configFile = join(config, "opencode.json");
const parent = join(config, "plugins");
await mkdir(parent, { recursive: true });
const staged = join(parent, `.stanp-opencode.new.${process.pid}`);
const backup = join(parent, `.stanp-opencode.old.${process.pid}`);
const target = join(parent, "stanp-opencode");
const configStage = join(config, `.stanp-opencode.config.${process.pid}`);
let saved = false;
let activated = false;
try {
await mkdir(staged);
for (const name of selected) await stage(source, staged, name);
await Bun.write(configStage, JSON.stringify(updated, null, 4) + "\n");
try {
await rename(target, backup);
saved = true;
} catch (error) {
if (!(error instanceof Error && "code" in error && error.code === "ENOENT"))
throw error;
}
await rename(staged, target);
activated = true;
await rename(configStage, configFile);
} catch (error) {
if (activated) await rm(target, { recursive: true, force: true });
if (saved) await rename(backup, target);
throw error;
} finally {
await rm(staged, { recursive: true, force: true });
await rm(configStage, { force: true });
}
if (saved) await rm(backup, { recursive: true, force: true });
await rm(join(parent, "stanp-opencode.js"), { force: true });
}
export async function install(source: string, config: string, selection?: string) { export async function install(source: string, config: string, selection?: string) {
const absoluteBase = join(config, "plugins", "stanp-opencode"); const absoluteBase = join(config, "plugins", "stanp-opencode");
const monolith = (target: string) => const monolith = (target: string) =>
target === base || target === absoluteBase || /^stanp-opencode(?:@[^/]+)?$/.test(target); target === base || target === absoluteBase || /^stanp-opencode(?:@[^/]+)?$/u.test(target);
const owned = new Set( const owned = new Set(
names.flatMap((name) => [ names.flatMap((name) => [
`${base}/${name}`, `${base}/${name}`,
@@ -82,39 +189,7 @@ export async function install(source: string, config: string, selection?: string
entry.package === `stanp-opencode/${name}`, entry.package === `stanp-opencode/${name}`,
), ),
); );
let chosen: string[]; const chosen = await choose(retained, selection);
if (selection !== undefined) chosen = selection.split(",");
else if (process.stdin.isTTY) {
const input = createInterface({ input: process.stdin, output: process.stdout });
try {
const defaults = retained.length ? retained : names;
chosen = (
(
await input.question(
`Plugins (agents,multi-work,quota) [${defaults.join(",")}]: `,
)
).trim() || defaults.join(",")
).split(",");
if (chosen.includes("multi-work") && !chosen.includes("agents")) {
if (
/^(y|yes)?$/i.test(
(
await input.question("Multi-work requires Agents. Add Agents? [Y/n]: ")
).trim(),
)
)
chosen.push("agents");
}
} finally {
input.close();
}
} else {
if (!retained.length)
throw new Error(
"Noninteractive installation requires --plugins agents,multi-work,quota (or a valid subset)",
);
chosen = [...retained];
}
if ( if (
!z.array(z.enum(names)).min(1).safeParse(chosen).success || !z.array(z.enum(names)).min(1).safeParse(chosen).success ||
new Set(chosen).size !== chosen.length new Set(chosen).size !== chosen.length
@@ -131,17 +206,16 @@ export async function install(source: string, config: string, selection?: string
entry.package === `stanp-opencode/${name}` || entry.package === `stanp-opencode/${name}` ||
(name === "agents" && monolith(entry.package)), (name === "agents" && monolith(entry.package)),
); );
const options: NonNullable<Entry["options"]> = {}; const options: NonNullable<Entry["options"]> = { ...prior?.options };
Object.assign(options, prior?.options); delete options["playwright"];
delete options.playwright;
fill(options, skeleton(name)); fill(options, skeleton(name));
const entry = entrySchema.parse({ ...prior, package: `${base}/${name}` }); const entry = entrySchema.parse({ ...prior, package: `${base}/${name}` });
delete entry.options; delete entry.options;
if (Object.keys(options).length) entry.options = options; if (Object.keys(options).length > 0) entry.options = options;
return entry; return entry;
}); });
const first = configured.findIndex((entry) => isOwned(entry.package)); const first = configured.findIndex((entry) => isOwned(entry.package));
const next = entries.filter((_entry, index) => !isOwned(configured[index]!.package)); const next = entries.filter((_entry, index) => !isOwned(configured[index]?.package ?? ""));
next.splice(first < 0 ? next.length : first, 0, ...registrations); next.splice(first < 0 ? next.length : first, 0, ...registrations);
const updated: z.infer<typeof configSchema> = { const updated: z.infer<typeof configSchema> = {
...current, ...current,
@@ -149,75 +223,13 @@ export async function install(source: string, config: string, selection?: string
plugins: next, plugins: next,
}; };
// Coordinate delegates to workers from Multi-work children, so routing needs depth >= 2. // Coordinate delegates to workers from Multi-work children, so routing needs depth >= 2.
const experimental = experimentalSchema.safeParse(current.experimental ?? {}); const experimental = experimentalSchema.safeParse(current["experimental"] ?? {});
if (selected.includes("agents") && experimental.success) if (selected.includes("agents") && experimental.success)
updated.experimental = { updated["experimental"] = {
...experimental.data, ...experimental.data,
subagent_depth: Math.max(experimental.data.subagent_depth ?? 0, 2), subagent_depth: Math.max(experimental.data.subagent_depth ?? 0, 2),
}; };
const parent = join(config, "plugins"); await activate(source, config, selected, updated);
await mkdir(parent, { recursive: true });
const staged = join(parent, `.stanp-opencode.new.${process.pid}`);
const backup = join(parent, `.stanp-opencode.old.${process.pid}`);
const target = join(parent, "stanp-opencode");
const configStage = join(config, `.stanp-opencode.config.${process.pid}`);
let saved = false;
let activated = false;
try {
await mkdir(staged);
for (const name of selected) {
const file = name === "quota" ? "quota-plugin" : name;
const entrypoint = join(source, "dist", `${file}.js`);
const { default: definition } = await import(entrypoint);
const plugin = nativePlugin.parse(definition);
if (plugin.id !== `stanp-opencode.${name}`)
throw new Error(`Invalid native OpenCode plugin: ${name}`);
const directory = join(staged, name);
await mkdir(directory);
await copyFile(entrypoint, join(directory, "index.js"));
const exports: DirectoryExports = { ".": "./index.js" };
if (name === "quota") {
const tui = join(source, "dist", "tui.js");
if (
!new Bun.Transpiler({ loader: "js" })
.scan(await Bun.file(tui).text())
.exports.includes("default")
)
throw new Error("Quota lacks its TUI entrypoint");
await copyFile(tui, join(directory, "tui.js"));
exports["./tui"] = "./tui.js";
}
await Bun.write(
join(directory, "package.json"),
JSON.stringify({
name: `stanp-opencode-${name}`,
type: "module",
main: "./index.js",
exports,
}),
);
}
await Bun.write(configStage, JSON.stringify(updated, null, 4) + "\n");
try {
await rename(target, backup);
saved = true;
} catch (error) {
if (!(error instanceof Error && "code" in error && error.code === "ENOENT"))
throw error;
}
await rename(staged, target);
activated = true;
await rename(configStage, configFile);
} catch (error) {
if (activated) await rm(target, { recursive: true, force: true });
if (saved) await rename(backup, target);
throw error;
} finally {
await rm(staged, { recursive: true, force: true });
await rm(configStage, { force: true });
}
if (saved) await rm(backup, { recursive: true, force: true });
await rm(join(parent, "stanp-opencode.js"), { force: true });
console.log(`Installed ${selected.join(", ")}. Restart OpenCode.`); console.log(`Installed ${selected.join(", ")}. Restart OpenCode.`);
if (oldMonolith) if (oldMonolith)
console.log( console.log(
@@ -227,6 +239,7 @@ export async function install(source: string, config: string, selection?: string
if (import.meta.main) { if (import.meta.main) {
const [source, config, selection] = process.argv.slice(2); const [source, config, selection] = process.argv.slice(2);
if (!source || !config) throw new Error("Expected package directory and config directory"); if (source === undefined || source === "" || config === undefined || config === "")
throw new Error("Expected package directory and config directory");
await install(source, config, selection); await install(source, config, selection);
} }
+53 -42
View File
@@ -1,26 +1,27 @@
// Opt-in real-host check: OPENCODE_2022=/absolute/path/to/2.0.22/opencode bun scripts/test-multi-work-host.ts // Opt-in real-host check: OPENCODE_2027=/absolute/path/to/2.0.27/opencode bun scripts/test-multi-work-host.ts
// Only fake Herdr/model servers and fresh temporary repositories/databases are used. // Only fake Herdr/model servers and fresh temporary repositories/databases are used.
import { mkdir, mkdtemp, writeFile, chmod, readFile, rm } from "node:fs/promises"; import { mkdir, mkdtemp, writeFile, chmod, readFile, rm } from "node:fs/promises";
import { tmpdir } from "node:os"; import { tmpdir } from "node:os";
import { join, resolve } from "node:path"; import { join, resolve } from "node:path";
import { createServer } from "node:net"; import { createServer } from "node:net";
import { OpenCode } from "@opencode/client"; import { OpenCode } from "@opencode/client";
import { command } from "../src/herdr.js"; import { command } from "../src/multi-work/herdr.js";
import { z } from "zod"; import { z } from "zod";
const binary = process.env.OPENCODE_2022; const binary = process.env["OPENCODE_2027"];
if (!binary) throw new Error("Set OPENCODE_2022 to an isolated OpenCode 2.0.22 binary"); if (binary === undefined || binary === "")
throw new Error("Set OPENCODE_2027 to an isolated OpenCode 2.0.27 binary");
const temp = await mkdtemp(join(tmpdir(), "native-multi-work-")); const temp = await mkdtemp(join(tmpdir(), "native-multi-work-"));
try { try {
const root = join(temp, "root"), const root = join(temp, "root");
destination = join(temp, "child"), const destination = join(temp, "child");
bin = join(temp, "bin"), const bin = join(temp, "bin");
config = join(temp, "config"); const config = join(temp, "config");
const herdrCreation = join(temp, "herdr-creation.txt"); const herdrCreation = join(temp, "herdr-creation.txt");
for (const path of [root, bin, config, join(temp, "plugin")]) await mkdir(path); for (const path of [root, bin, config, join(temp, "plugin")]) await mkdir(path);
const signal = AbortSignal.timeout(120_000); const signal = AbortSignal.timeout(120_000);
if ((await command([binary, "--version"], temp, signal)) !== "opencode v2.0.22") if ((await command([binary, "--version"], temp, signal)) !== "opencode v2.0.27")
throw new Error("Exact 2.0.22 binary required"); throw new Error("Exact 2.0.27 binary required");
await command(["git", "init", "-b", "main"], root, signal); await command(["git", "init", "-b", "main"], root, signal);
await command( await command(
[ [
@@ -82,7 +83,7 @@ try {
target: "bun", target: "bun",
format: "esm", format: "esm",
}); });
if (!built.success) throw new Error(String(built.logs)); if (!built.success) throw new Error(built.logs.map((log) => log.message).join(","));
} }
await writeFile( await writeFile(
join(config, "opencode.json"), join(config, "opencode.json"),
@@ -134,12 +135,18 @@ try {
}, },
}); });
const socket = createServer(); const socket = createServer();
await new Promise<void>((done) => socket.listen(0, "127.0.0.1", done)); await new Promise<void>((done) => {
socket.listen(0, "127.0.0.1", done);
});
const { port } = z.object({ port: z.number() }).parse(socket.address()); const { port } = z.object({ port: z.number() }).parse(socket.address());
await new Promise<void>((done) => socket.close(() => done())); await new Promise<void>((done) => {
socket.close(() => {
done();
});
});
// Do not inherit user credentials, discovery URLs, Herdr identity, or config overrides. // Do not inherit user credentials, discovery URLs, Herdr identity, or config overrides.
const env = { const env = {
PATH: `${bin}:${process.env.PATH}`, PATH: `${bin}:${process.env["PATH"]}`,
HOME: join(temp, "home"), HOME: join(temp, "home"),
XDG_CONFIG_HOME: config, XDG_CONFIG_HOME: config,
XDG_DATA_HOME: join(temp, "data"), XDG_DATA_HOME: join(temp, "data"),
@@ -160,13 +167,13 @@ try {
let server = start(); let server = start();
const headers = { authorization: "" }; const headers = { authorization: "" };
const client = OpenCode.make({ baseUrl: `http://127.0.0.1:${port}`, headers }); const client = OpenCode.make({ baseUrl: `http://127.0.0.1:${port}`, headers });
async function ready() { const ready = async () => {
for (let attempt = 0; attempt < 200; attempt++) { for (let attempt = 0; attempt < 200; attempt++) {
try { try {
const password = (await readFile(join(temp, "server.log"), "utf8")).match( const password = (await readFile(join(temp, "server.log"), "utf8")).match(
/server password (\S+)/, /server password (\S+)/u,
)?.[1]; )?.[1];
if (password) if (password !== undefined)
headers.authorization = `Basic ${Buffer.from(`opencode:${password}`).toString("base64")}`; headers.authorization = `Basic ${Buffer.from(`opencode:${password}`).toString("base64")}`;
await client.server.info(); await client.server.info();
return; return;
@@ -177,7 +184,7 @@ try {
throw new Error( throw new Error(
`Host did not start: ${await readFile(join(temp, "server-errors.log"), "utf8")}`, `Host did not start: ${await readFile(join(temp, "server-errors.log"), "utf8")}`,
); );
} };
try { try {
await ready(); await ready();
const location = { directory: root }; const location = { directory: root };
@@ -228,7 +235,7 @@ try {
(await readFile(env.FIXTURE_TRACE, "utf8")) (await readFile(env.FIXTURE_TRACE, "utf8"))
.trim() .trim()
.split("\n") .split("\n")
.map((line) => JSON.parse(line)), .map((line) => z.json().parse(JSON.parse(line))),
); );
if ( if (
!admission.some((entry) => entry.id === child.id && entry.directory === destination) || !admission.some((entry) => entry.id === child.id && entry.directory === destination) ||
@@ -305,21 +312,21 @@ try {
pending.then(() => { pending.then(() => {
throw new Error("Foreground unexpectedly finished before cancellation"); throw new Error("Foreground unexpectedly finished before cancellation");
}), }),
new Promise<never>((_resolve, reject) => new Promise<never>((_resolve, reject) => {
deadline.addEventListener( deadline.addEventListener(
"abort", "abort",
() => reject(new Error("Model was not reached")), () => {
{ reject(new Error("Model was not reached"));
once: true,
}, },
), { once: true },
), );
}),
]); ]);
cancel.abort(); cancel.abort();
let rejected = false; const rejected = await pending.then(
await pending.catch(() => { () => false,
rejected = true; () => true,
}); );
if (!rejected) throw new Error("Cancelled RPC did not reject"); if (!rejected) throw new Error("Cancelled RPC did not reject");
for (let attempt = 0; attempt < 100; attempt++) { for (let attempt = 0; attempt < 100; attempt++) {
if ((await client.session.get({ sessionID: child.id })).outcome === "interrupted") if ((await client.session.get({ sessionID: child.id })).outcome === "interrupted")
@@ -329,6 +336,18 @@ try {
} }
releaseModel.resolve(); releaseModel.resolve();
holdModel = false; holdModel = false;
const multiWorkFailed = async () => {
for (let attempt = 0; attempt < 100; attempt++) {
const { data } = await client.plugin.list({ location });
const multi = data.find((plugin) => plugin.id === "stanp-opencode.multi-work");
if (multi?.state.status === "failed") return;
if (attempt === 99 || multi?.state.status === "active")
throw new Error(
`Missing or late Agents did not fail Multi-work activation: ${JSON.stringify(data)}`,
);
await Bun.sleep(100);
}
};
for (const plugins of [ for (const plugins of [
[{ package: join(temp, "plugin", "multi-work") }], [{ package: join(temp, "plugin", "multi-work") }],
[ [
@@ -344,27 +363,19 @@ try {
); );
server = start(); server = start();
await ready(); await ready();
for (let attempt = 0; attempt < 100; attempt++) { await multiWorkFailed();
const { data } = await client.plugin.list({ location });
const multi = data.find((plugin) => plugin.id === "stanp-opencode.multi-work");
if (multi?.state.status === "failed") break;
if (attempt === 99 || multi?.state.status === "active")
throw new Error(
`Missing or late Agents did not fail Multi-work activation: ${JSON.stringify(data)}`,
);
await Bun.sleep(100);
}
} }
server.kill(); server.kill();
await server.exited; await server.exited;
const quotaBuild = await Bun.build({ const quotaBuild = await Bun.build({
entrypoints: [resolve("src/quota-plugin.ts")], entrypoints: [resolve("src/quota/quota-plugin.ts")],
outdir: join(temp, "plugin", "quota"), outdir: join(temp, "plugin", "quota"),
naming: "index.js", naming: "index.js",
target: "bun", target: "bun",
format: "esm", format: "esm",
}); });
if (!quotaBuild.success) throw new Error(String(quotaBuild.logs)); if (!quotaBuild.success)
throw new Error(quotaBuild.logs.map((log) => log.message).join(","));
await writeFile( await writeFile(
join(config, "opencode.json"), join(config, "opencode.json"),
JSON.stringify({ JSON.stringify({
@@ -409,7 +420,7 @@ try {
releaseModel.resolve(); releaseModel.resolve();
server.kill(); server.kill();
await server.exited; await server.exited;
model.stop(true); void model.stop(true);
} }
} finally { } finally {
await rm(temp, { recursive: true, force: true }); await rm(temp, { recursive: true, force: true });
+64 -64
View File
@@ -1,4 +1,5 @@
import { Agent, Model, Plugin, Provider } from "@opencode/plugin"; import { Agent, Model, Plugin, Provider } from "@opencode/plugin";
import type { DeepMutable } from "@opencode/plugin/promise/types";
import type { ModelInfo } from "@opencode/client"; import type { ModelInfo } from "@opencode/client";
import { z } from "zod"; import { z } from "zod";
import { settings, workerNames } from "./config.js"; import { settings, workerNames } from "./config.js";
@@ -7,18 +8,38 @@ import { discover, modelKey } from "./provider.js";
import { descriptions, routingGuide } from "./routing.js"; import { descriptions, routingGuide } from "./routing.js";
import { Skill } from "@opencode/schema/skill"; import { Skill } from "@opencode/schema/skill";
import { AbsolutePath } from "@opencode/schema/schema"; import { AbsolutePath } from "@opencode/schema/schema";
import { fileURLToPath } from "node:url"; import antiOverengineering from "../skills/anti-overengineering.md" with { type: "text" };
import antiOverengineering from "./anti-overengineering.md" with { type: "text" }; import taskPlanning from "../skills/task-planning.md" with { type: "text" };
import taskPlanning from "./task-planning.md" with { type: "text" };
import { AgentsRpc } from "./agents-rpc.js"; import { AgentsRpc } from "./agents-rpc.js";
import { matches } from "./wildcard.js";
// Permission actions use wildcards, not filesystem globs. // Assignments use "" as unset.
function matches(value: string, pattern: string) { function assigned(value: string | undefined): value is string {
const escaped = pattern return value !== undefined && value !== "";
.replace(/[.+^${}()|[\]\\]/g, "\\$&") }
.replace(/\*/g, ".*")
.replace(/\?/g, "."); /** Points the agent at the available model, using the variant or a reasoning-effort fallback. */
return new RegExp(`^${escaped}$`, "s").test(value); function useModel(
agent: DeepMutable<Agent.Info>,
assignment: ReturnType<typeof model>,
available: ModelInfo,
) {
const hasVariant =
assignment.variant !== undefined &&
available.variants.some(({ id }) => id === assignment.variant);
agent.model = {
providerID: Provider.ID.make(available.providerID),
id: Model.ID.make(available.id),
};
if (hasVariant) agent.model.variant = Model.VariantID.make(assignment.variant);
agent.request = {
settings:
hasVariant || assignment.variant === undefined
? {}
: { reasoningEffort: assignment.variant },
headers: {},
body: {},
};
} }
const reading = [ const reading = [
@@ -40,12 +61,12 @@ export default Plugin.define({
id: "stanp-opencode.agents", id: "stanp-opencode.agents",
async setup(context) { async setup(context) {
const { agents } = settings.parse(context.options); const { agents } = settings.parse(context.options);
if (!workerNames.some((name) => agents?.[name])) return; if (!workerNames.some((name) => assigned(agents?.[name]))) return;
const assignments: Partial<Record<(typeof workerNames)[number], ReturnType<typeof model>>> = const assignments: Partial<Record<(typeof workerNames)[number], ReturnType<typeof model>>> =
{}; {};
for (const name of workerNames) { for (const name of workerNames) {
const reference = agents?.[name]; const reference = agents?.[name];
if (reference) assignments[name] = model(reference, `agents ${name}`); if (assigned(reference)) assignments[name] = model(reference, `agents ${name}`);
else if (!name.startsWith("deep-")) throw new Error(`agents ${name} is required`); else if (!name.startsWith("deep-")) throw new Error(`agents ${name} is required`);
} }
let models = new Map<string, ModelInfo>(); let models = new Map<string, ModelInfo>();
@@ -106,13 +127,14 @@ export default Plugin.define({
["task-planning", taskPlanning], ["task-planning", taskPlanning],
] as const) { ] as const) {
if (editor.get(name)) continue; if (editor.get(name)) continue;
const description = content.match(/^description: "?(.+?)"?$/m)?.[1]; const description = content.match(/^description: "?(.+?)"?$/mu)?.[1];
if (!description) throw new Error(`${name} skill has no description`); if (description === undefined || description === "")
throw new Error(`${name} skill has no description`);
editor.add({ editor.add({
id: Skill.ID.make(name), id: Skill.ID.make(name),
name: Skill.Name.make(name), name: Skill.Name.make(name),
description, description,
path: AbsolutePath.make(fileURLToPath(import.meta.url)), path: AbsolutePath.make(import.meta.filename),
content, content,
}); });
} }
@@ -123,22 +145,20 @@ export default Plugin.define({
.list() .list()
.map((tool) => tool.id) .map((tool) => tool.id)
.filter((id) => id.startsWith("codegraph_")) .filter((id) => id.startsWith("codegraph_"))
.sort(); .toSorted();
if (JSON.stringify(next) === JSON.stringify(codegraphTools)) return; if (JSON.stringify(next) === JSON.stringify(codegraphTools)) return;
codegraphTools = next; codegraphTools = next;
if (agentTransformReady) if (agentTransformReady)
queueMicrotask(() => { queueMicrotask(() => {
void context.agent void context.agent.reload().catch((error) => {
.reload() console.error("stanp-opencode agent reload failed", error);
.catch((error) => });
console.error("stanp-opencode agent reload failed", error),
);
}); });
}); });
const availableFor = (assignment: { providerID: string; id: string }) =>
models.get(modelKey(assignment.providerID, assignment.id));
await context.agent.transform((editor) => { await context.agent.transform((editor) => {
const availableFor = (assignment: { providerID: string; id: string }) =>
models.get(modelKey(assignment.providerID, assignment.id));
const deepLo = assignments["deep-lo"]; const deepLo = assignments["deep-lo"];
const deep = const deep =
deepLo !== undefined && deepLo !== undefined &&
@@ -154,59 +174,37 @@ export default Plugin.define({
active.clear(); active.clear();
for (const name of workers) active.add(name); for (const name of workers) active.add(name);
if (workers.length === 0 || coordinate === undefined) return; if (workers.length === 0 || coordinate === undefined) return;
for (const name of workers) { const configureWorker = (
const assignment = assignments[name]!; name: (typeof workerNames)[number],
const available = availableFor(assignment)!; assignment: ReturnType<typeof model>,
available: ModelInfo,
) => {
editor.update(name, (agent) => { editor.update(name, (agent) => {
const hasVariant =
assignment.variant !== undefined &&
available.variants.some(({ id }) => id === assignment.variant);
agent.name = Agent.Name.make(name); agent.name = Agent.Name.make(name);
agent.mode = "subagent"; agent.mode = "subagent";
agent.hidden = false; agent.hidden = false;
agent.description = descriptions[name]; agent.description = descriptions[name];
agent.model = { useModel(agent, assignment, available);
providerID: Provider.ID.make(available.providerID),
id: Model.ID.make(available.id),
};
if (hasVariant) agent.model.variant = Model.VariantID.make(assignment.variant!);
agent.request = {
settings:
hasVariant || assignment.variant === undefined
? {}
: { reasoningEffort: assignment.variant },
headers: {},
body: {},
};
agent.permissions = [ agent.permissions = [
...structuredClone(inherited), ...structuredClone(inherited),
{ action: "subagent", resource: "*", effect: "deny" }, { action: "subagent", resource: "*", effect: "deny" },
]; ];
}); });
};
for (const name of workers) {
const assignment = assignments[name];
const available = assignment && availableFor(assignment);
if (assignment && available) configureWorker(name, assignment, available);
} }
const available = availableFor(coordinate);
if (!available) return;
editor.update("coordinate", (agent) => { editor.update("coordinate", (agent) => {
const available = availableFor(coordinate)!;
const hasVariant =
coordinate.variant !== undefined &&
available.variants.some(({ id }) => id === coordinate.variant);
agent.name = Agent.Name.make("coordinate"); agent.name = Agent.Name.make("coordinate");
agent.mode = "primary"; agent.mode = "primary";
agent.hidden = false; agent.hidden = false;
agent.description = agent.description =
"Read, plan, and coordinate specialist workers; never implement directly."; "Read, plan, and coordinate specialist workers; never implement directly.";
agent.model = { useModel(agent, coordinate, available);
providerID: Provider.ID.make(available.providerID),
id: Model.ID.make(available.id),
};
if (hasVariant) agent.model.variant = Model.VariantID.make(coordinate.variant!);
agent.request = {
settings:
hasVariant || coordinate.variant === undefined
? {}
: { reasoningEffort: coordinate.variant },
headers: {},
body: {},
};
agent.system = routingGuide(deep); agent.system = routingGuide(deep);
agent.permissions = [ agent.permissions = [
{ action: "*", resource: "*", effect: "deny" }, { action: "*", resource: "*", effect: "deny" },
@@ -242,18 +240,20 @@ export default Plugin.define({
} }
await context.session.hook("context", (event) => { await context.session.hook("context", (event) => {
if (workerNames.some((name) => name === event.agent)) { if (workerNames.some((name) => name === event.agent)) {
delete event.tools.subagent; delete event.tools["subagent"];
return; return;
} }
const tool = event.tools.subagent; const tool = event.tools["subagent"];
if (event.agent === "coordinate" && workers.length === 0) { if (event.agent === "coordinate" && workers.length === 0) {
delete event.tools.subagent; delete event.tools["subagent"];
return; return;
} }
if (event.agent !== "coordinate" || !tool) return; if (event.agent !== "coordinate" || !tool) return;
tool.description = `Delegate a self-contained assignment to one of these workers:\n${workers.map((name) => `- ${name}: ${descriptions[name]}`).join("\n")}`; tool.description = `Delegate a self-contained assignment to one of these workers:\n${workers.map((name) => `- ${name}: ${descriptions[name]}`).join("\n")}`;
// The executable definition remains native; constrain only this request's schema. // The executable definition remains native; constrain only this request's schema.
const properties = z.record(z.string(), z.unknown()).parse(tool.input.properties ?? {}); const properties = z
.record(z.string(), z.unknown())
.parse(tool.input["properties"] ?? {});
tool.input = { tool.input = {
...tool.input, ...tool.input,
properties: { ...properties, agent: { type: "string", enum: workers } }, properties: { ...properties, agent: { type: "string", enum: workers } },
@@ -273,7 +273,7 @@ export default Plugin.define({
// Commands can create child sessions without going through the subagent tool. // Commands can create child sessions without going through the subagent tool.
await context.session.hook("prompt", async (event) => { await context.session.hook("prompt", async (event) => {
const child = await context.session.get({ sessionID: event.sessionID }); const child = await context.session.get({ sessionID: event.sessionID });
if (!child.parentID) return; if (child.parentID === undefined || child.parentID === "") return;
const parent = await context.session.get({ sessionID: child.parentID }); const parent = await context.session.get({ sessionID: child.parentID });
if (child.agent === "coordinate" && parent.agent !== "multi-work") if (child.agent === "coordinate" && parent.agent !== "multi-work")
throw new Error("coordinate cannot run as a subagent without Multi-work"); throw new Error("coordinate cannot run as a subagent without Multi-work");
+3 -1
View File
@@ -5,5 +5,7 @@ export function model(reference: string, name: string) {
if (slash <= 0) throw new Error(`${name} must be provider/model[#variant]: ${reference}`); if (slash <= 0) throw new Error(`${name} must be provider/model[#variant]: ${reference}`);
const providerID = path.slice(0, slash); const providerID = path.slice(0, slash);
const id = path.slice(slash + 1); const id = path.slice(slash + 1);
return variant ? { providerID, id, variant } : { providerID, id }; return variant !== undefined && variant !== ""
? { providerID, id, variant }
: { providerID, id };
} }
+8
View File
@@ -0,0 +1,8 @@
// Permission actions use wildcards, not filesystem globs.
export function matches(value: string, pattern: string) {
const escaped = pattern
.replaceAll(/[.+^${}()|[\]\\]/gu, "\\$&")
.replaceAll("*", ".*")
.replaceAll("?", ".");
return new RegExp(`^${escaped}$`, "su").test(value);
}
+5 -3
View File
@@ -3,13 +3,15 @@ import { realpath } from "node:fs/promises";
import { z } from "zod"; import { z } from "zod";
export async function command(args: string[], cwd: string, signal: AbortSignal) { export async function command(args: string[], cwd: string, signal: AbortSignal) {
const [file, ...rest] = args;
if (file === undefined) throw new Error("Missing command");
return new Promise<string>((resolve, reject) => { return new Promise<string>((resolve, reject) => {
execFile( execFile(
args[0]!, file,
args.slice(1), rest,
{ cwd, signal, timeout: 30_000, maxBuffer: 2_000_000 }, { cwd, signal, timeout: 30_000, maxBuffer: 2_000_000 },
(error, stdout, stderr) => { (error, stdout, stderr) => {
if (error) reject(new Error(`${args[0]} failed: ${stderr || error.message}`)); if (error) reject(new Error(`${file} failed: ${stderr || error.message}`));
else resolve(stdout.trim()); else resolve(stdout.trim());
}, },
); );
@@ -4,12 +4,13 @@ import { Session } from "@opencode/schema/session";
import { AbsolutePath } from "@opencode/schema/schema"; import { AbsolutePath } from "@opencode/schema/schema";
import type { Context } from "@opencode/plugin/effect/plugin"; import type { Context } from "@opencode/plugin/effect/plugin";
import { Plugin } from "@opencode/plugin/effect"; import { Plugin } from "@opencode/plugin/effect";
import { AgentsRpc } from "./agents-rpc.js"; import { AgentsRpc } from "../agents/agents-rpc.js";
import { Cause, Effect, Schedule, Stream } from "effect"; import { Cause, Effect, Schedule, Stream } from "effect";
import { z } from "zod"; import { z } from "zod";
import { randomUUID } from "node:crypto"; import { randomUUID } from "node:crypto";
import { Herdr, rootSchema } from "./herdr.js"; import { Herdr, rootSchema } from "./herdr.js";
import { multiWorkGuide } from "./routing.js"; import { multiWorkGuide } from "../agents/routing.js";
import { matches } from "../agents/wildcard.js";
export const bindingSchema = z export const bindingSchema = z
.object({ .object({
@@ -62,14 +63,8 @@ const readTools = new Set([
export const childProtocol = export const childProtocol =
"Bound child sessions use stanp-opencode multi-work protocol 1 and must remain in their assigned worktree."; "Bound child sessions use stanp-opencode multi-work protocol 1 and must remain in their assigned worktree.";
function matches(value: string, pattern: string) { function present(value: string | undefined): value is string {
return new RegExp( return value !== undefined && value !== "";
`^${pattern
.replace(/[.+^${}()|[\]\\]/g, "\\$&")
.replace(/\*/g, ".*")
.replace(/\?/g, ".")}$`,
"s",
).test(value);
} }
export const installMultiWork = ( export const installMultiWork = (
@@ -158,6 +153,20 @@ export const installMultiWork = (
return binding; return binding;
}); });
const verifyLocalChild = (
sessionID: Session.ID,
parent: { id: string; location: { directory: string } },
) =>
Effect.gen(function* () {
const child = yield* context.session.get({ sessionID });
if (
child.parentID !== parent.id ||
child.agent !== "fast-lo" ||
child.location.directory !== parent.location.directory
)
throw new Error("Local fast-lo child binding changed");
});
// Commands can create children without going through the subagent tool. // Commands can create children without going through the subagent tool.
yield* context.session.hook("prompt", (event) => yield* context.session.hook("prompt", (event) =>
Effect.gen(function* () { Effect.gen(function* () {
@@ -192,12 +201,12 @@ export const installMultiWork = (
if (event.agent === "coordinate" && session.parentID) if (event.agent === "coordinate" && session.parentID)
yield* validate(event.sessionID); yield* validate(event.sessionID);
if (event.agent !== "multi-work") { if (event.agent !== "multi-work") {
const tool = event.tools.subagent; const tool = event.tools["subagent"];
if (tool) { if (tool) {
const properties = z const properties = z
.record(z.string(), z.unknown()) .record(z.string(), z.unknown())
.parse(tool.input.properties ?? {}); .parse(tool.input["properties"] ?? {});
delete properties.worktree; delete properties["worktree"];
tool.input = { ...tool.input, properties }; tool.input = { ...tool.input, properties };
} }
return; return;
@@ -211,13 +220,13 @@ export const installMultiWork = (
); );
if (!root) if (!root)
throw new Error("multi-work requires a live, unambiguous Herdr root checkout"); throw new Error("multi-work requires a live, unambiguous Herdr root checkout");
const tool = event.tools.subagent; const tool = event.tools["subagent"];
if (tool) { if (tool) {
tool.input = z.toJSONSchema(inputSchema); tool.input = z.toJSONSchema(inputSchema);
const properties = z const properties = z
.record(z.string(), z.unknown()) .record(z.string(), z.unknown())
.parse(tool.input.properties); .parse(tool.input["properties"]);
tool.input.properties = { tool.input["properties"] = {
...properties, ...properties,
agent: { type: "string", enum: ["fast-lo", "coordinate"] }, agent: { type: "string", enum: ["fast-lo", "coordinate"] },
}; };
@@ -238,7 +247,7 @@ export const installMultiWork = (
if (input.agent === "multi-work") if (input.agent === "multi-work")
throw new Error("multi-work is primary only"); throw new Error("multi-work is primary only");
if ( if (
input.sessionID && present(input.sessionID) &&
(yield* context.storage.get(bindingKey(input.sessionID))) !== (yield* context.storage.get(bindingKey(input.sessionID))) !==
undefined && undefined &&
(call.agent !== "multi-work" || input.agent !== "coordinate") (call.agent !== "multi-work" || input.agent !== "coordinate")
@@ -261,22 +270,13 @@ export const installMultiWork = (
); );
if (input.agent === "fast-lo") { if (input.agent === "fast-lo") {
if (input.worktree) throw new Error("fast-lo is local retrieval only"); if (input.worktree) throw new Error("fast-lo is local retrieval only");
if (input.sessionID) { if (present(input.sessionID))
const child = yield* context.session.get({ yield* verifyLocalChild(Session.ID.make(input.sessionID), parent);
sessionID: Session.ID.make(input.sessionID),
});
if (
child.parentID !== parent.id ||
child.agent !== "fast-lo" ||
child.location.directory !== parent.location.directory
)
throw new Error("Local fast-lo child binding changed");
}
return yield* native.execute(input, call); return yield* native.execute(input, call);
} }
if (input.agent !== "coordinate") if (input.agent !== "coordinate")
throw new Error("multi-work delegates only to fast-lo or coordinate"); throw new Error("multi-work delegates only to fast-lo or coordinate");
if (input.sessionID && input.worktree !== undefined) if (present(input.sessionID) && input.worktree !== undefined)
throw new Error( throw new Error(
"Coordinate resumes require only sessionID; worktree is create-only", "Coordinate resumes require only sessionID; worktree is create-only",
); );
@@ -287,7 +287,7 @@ export const installMultiWork = (
return yield* Effect.gen(function* () { return yield* Effect.gen(function* () {
let initialized = false; let initialized = false;
let placement: z.infer<typeof bindingSchema> | undefined; let placement: z.infer<typeof bindingSchema> | undefined;
if (input.sessionID) { if (present(input.sessionID)) {
const binding = yield* validate(Session.ID.make(input.sessionID)); const binding = yield* validate(Session.ID.make(input.sessionID));
if (binding.owner !== call.sessionID) if (binding.owner !== call.sessionID)
throw new Error("Cannot resume another parent's binding"); throw new Error("Cannot resume another parent's binding");
@@ -336,7 +336,7 @@ export const installMultiWork = (
} }
const { worktree, ...args } = input; const { worktree, ...args } = input;
const callKey = `multi-work-call:${call.sessionID}:${call.id}`; const callKey = `multi-work-call:${call.sessionID}:${call.id}`;
if (!input.sessionID) { if (!present(input.sessionID)) {
const previous = yield* context.storage.get(callKey); const previous = yield* context.storage.get(callKey);
if (previous !== undefined) if (previous !== undefined)
throw new Error( throw new Error(
@@ -347,10 +347,10 @@ export const installMultiWork = (
...call, ...call,
progress: (metadata) => progress: (metadata) =>
Effect.gen(function* () { Effect.gen(function* () {
// Native 2.0.22 awaits this update after creation and before prompt admission. // Native 2.0.27 awaits this update after creation and before prompt admission.
yield* call.progress(metadata); yield* call.progress(metadata);
if (initialized) return; if (initialized) return;
const id = z.string().parse(metadata.sessionID); const id = z.string().parse(metadata["sessionID"]);
if (busy.has(id)) if (busy.has(id))
throw new Error( throw new Error(
"This child is already being delegated", "This child is already being delegated",
@@ -433,7 +433,7 @@ export const installMultiWork = (
coordinator?.mode === "all" && coordinator?.mode === "all" &&
coordinator.system?.includes( coordinator.system?.includes(
childProtocol, childProtocol,
) && ) === true &&
[ [
"coordinate", "coordinate",
"fast-lo", "fast-lo",
@@ -503,7 +503,7 @@ export const installMultiWork = (
Effect.ensuring( Effect.ensuring(
Effect.sync(() => { Effect.sync(() => {
busy.delete(lock); busy.delete(lock);
if (childLock) busy.delete(childLock); if (present(childLock)) busy.delete(childLock);
}), }),
), ),
); );
@@ -11,11 +11,15 @@ const TIMEOUT_MS = 5_000;
const RETRY_MS = 2_000; const RETRY_MS = 2_000;
const RETRIES = 4; const RETRIES = 4;
const WEEK = 604_800; const WEEK = 604_800;
const jsonValue = z.json();
type QuotaFetch = (input: string | URL | Request, init?: RequestInit) => Promise<Response>; type QuotaFetch = (input: string | URL | Request, init?: RequestInit) => Promise<Response>;
export function claudeCredentialsPath() { function claudeCredentialsPath() {
return join(process.env.CLAUDE_CONFIG_DIR ?? join(homedir(), ".claude"), ".credentials.json"); return join(
process.env["CLAUDE_CONFIG_DIR"] ?? join(homedir(), ".claude"),
".credentials.json",
);
} }
const credentials = z.object({ const credentials = z.object({
@@ -27,7 +31,7 @@ const credentials = z.object({
}); });
const usageWindow = z const usageWindow = z
.object({ utilization: z.number().finite(), resets_at: z.string().nullish() }) .object({ utilization: z.number(), resets_at: z.string().nullish() })
.nullish(); .nullish();
const usagePayload = z.object({ const usagePayload = z.object({
five_hour: usageWindow, five_hour: usageWindow,
@@ -38,7 +42,7 @@ const usagePayload = z.object({
.array( .array(
z.object({ z.object({
kind: z.string(), kind: z.string(),
percent: z.number().finite(), percent: z.number(),
resets_at: z.string().nullish(), resets_at: z.string().nullish(),
scope: z scope: z
.object({ .object({
@@ -63,7 +67,7 @@ function window(
label, label,
seconds, seconds,
used: Math.max(0, Math.min(100, used)), used: Math.max(0, Math.min(100, used)),
resetsAt: resetsAt ? Date.parse(resetsAt) : Number.NaN, resetsAt: resetsAt === null || resetsAt === undefined ? Number.NaN : Date.parse(resetsAt),
}; };
} }
@@ -173,31 +177,14 @@ export class ClaudeQuotaTracker {
const credential = parsed.data.claudeAiOauth; const credential = parsed.data.claudeAiOauth;
if (this.disposed) return true; if (this.disposed) return true;
if (credential.expiresAt <= Date.now()) return false; if (credential.expiresAt <= Date.now()) return false;
const controller = new AbortController(); const response = await this.fetchUsage(credential.accessToken);
this.controller = controller;
const timeout = setTimeout(() => controller.abort(), TIMEOUT_MS);
let response: Response;
try {
response = await this.fetcher(USAGE_URL, {
headers: {
Authorization: `Bearer ${credential.accessToken}`,
"anthropic-beta": "oauth-2025-04-20",
Accept: "application/json",
},
signal: controller.signal,
});
} finally {
clearTimeout(timeout);
if (this.controller === controller) this.controller = undefined;
}
if (!response.ok) return false; if (!response.ok) return false;
// SAFETY: Response.json yields JSON values; usagePayload validates fields used. const payload = jsonValue.parse(await response.json());
const payload = (await response.json()) as Schema.Json;
const snapshot = normalizeClaudeQuota( const snapshot = normalizeClaudeQuota(
payload, payload,
credential.subscriptionType ?? "unknown", credential.subscriptionType ?? "unknown",
); );
if (this.disposed) return true; if (this.isDisposed()) return true;
if (!snapshot) return false; if (!snapshot) return false;
this.latest = snapshot; this.latest = snapshot;
} catch { } catch {
@@ -207,6 +194,32 @@ export class ClaudeQuotaTracker {
return true; return true;
} }
private async fetchUsage(accessToken: string) {
const controller = new AbortController();
this.controller = controller;
const timeout = setTimeout(() => {
controller.abort();
}, TIMEOUT_MS);
try {
return await this.fetcher(USAGE_URL, {
headers: {
Authorization: `Bearer ${accessToken}`,
"anthropic-beta": "oauth-2025-04-20",
Accept: "application/json",
},
signal: controller.signal,
});
} finally {
clearTimeout(timeout);
if (this.controller === controller) this.controller = undefined;
}
}
/** Reads the flag through a call so checks after `await` are not narrowed away. */
private isDisposed() {
return this.disposed;
}
status(): QuotaStatus | undefined { status(): QuotaStatus | undefined {
if (!this.latest) return; if (!this.latest) return;
return { return {
@@ -40,7 +40,7 @@ export default Plugin.define({
await quota.authChanged(); await quota.authChanged();
} else if ( } else if (
event.type === "credential.switched" && event.type === "credential.switched" &&
String(event.data.integrationID) === "openai" event.data.integrationID === "openai"
) { ) {
await quota.authChanged(true); await quota.authChanged(true);
} }
+69 -45
View File
@@ -8,24 +8,30 @@ const USAGE_URL = "https://chatgpt.com/backend-api/wham/usage";
const POLL_MS = 60_000; const POLL_MS = 60_000;
const TIMEOUT_MS = 5_000; const TIMEOUT_MS = 5_000;
const STORAGE_KEY = "chatgpt-quota"; const STORAGE_KEY = "chatgpt-quota";
const jsonValue = z.json();
function compactLimitIdentity(value: string) { function compactLimitIdentity(value: string) {
return value.toLowerCase().replace(/[^a-z0-9]+/g, ""); return value.toLowerCase().replaceAll(/[^a-z0-9]+/gu, "");
} }
function isSparkLimit(meteredFeature?: string, limitName?: string | null) { function isSparkLimit(meteredFeature?: string, limitName?: string | null) {
return ( return (
(meteredFeature !== undefined && (meteredFeature !== undefined &&
compactLimitIdentity(meteredFeature) === "codexbengalfox") || compactLimitIdentity(meteredFeature) === "codexbengalfox") ||
(limitName != null && compactLimitIdentity(limitName) === "gpt53codexspark") (limitName !== null &&
limitName !== undefined &&
compactLimitIdentity(limitName) === "gpt53codexspark")
); );
} }
function hasReserveToken(value: string) {
return /(^|[^a-z0-9])reserve($|[^a-z0-9])/iu.test(value);
}
function isReserveLimit(meteredFeature?: string, limitName?: string | null) { function isReserveLimit(meteredFeature?: string, limitName?: string | null) {
const hasReserveToken = (value: string) => /(^|[^a-z0-9])reserve($|[^a-z0-9])/i.test(value);
return ( return (
(meteredFeature !== undefined && hasReserveToken(meteredFeature)) || (meteredFeature !== undefined && hasReserveToken(meteredFeature)) ||
(limitName != null && hasReserveToken(limitName)) (limitName !== null && limitName !== undefined && hasReserveToken(limitName))
); );
} }
@@ -81,7 +87,10 @@ function withoutExcludedState(state: StoredState): StoredState {
const windows = state.latest?.windows.filter((window) => !isExcludedWindow(window)); const windows = state.latest?.windows.filter((window) => !isExcludedWindow(window));
return { return {
...state, ...state,
latest: state.latest && windows?.length ? { ...state.latest, windows } : undefined, latest:
state.latest && windows !== undefined && windows.length > 0
? { ...state.latest, windows }
: undefined,
}; };
} }
@@ -89,9 +98,9 @@ type QuotaContext = Pick<Plugin.Context, "integration" | "storage">;
type QuotaFetch = (input: string | URL | Request, init?: RequestInit) => Promise<Response>; type QuotaFetch = (input: string | URL | Request, init?: RequestInit) => Promise<Response>;
const quotaWindow = z.object({ const quotaWindow = z.object({
limit_window_seconds: z.number().finite().positive(), limit_window_seconds: z.number().positive(),
used_percent: z.number().finite(), used_percent: z.number(),
reset_at: z.number().finite(), reset_at: z.number(),
}); });
const additionalRateLimitIdentity = z.object({ const additionalRateLimitIdentity = z.object({
limit_name: z.string().optional(), limit_name: z.string().optional(),
@@ -187,7 +196,7 @@ export function normalizeQuota(
function accountID(credential: Credential.OAuth) { function accountID(credential: Credential.OAuth) {
const metadataID = z const metadataID = z
.string() .string()
.safeParse(credential.metadata?.accountID ?? credential.metadata?.accountId); .safeParse(credential.metadata?.["accountID"] ?? credential.metadata?.["accountId"]);
if (metadataID.success) return metadataID.data; if (metadataID.success) return metadataID.data;
const parts = credential.access.split("."); const parts = credential.access.split(".");
if (parts.length !== 3) return; if (parts.length !== 3) return;
@@ -200,7 +209,7 @@ function accountID(credential: Credential.OAuth) {
.optional(), .optional(),
organizations: z.array(z.object({ id: z.string() })).optional(), organizations: z.array(z.object({ id: z.string() })).optional(),
}) })
.safeParse(JSON.parse(Buffer.from(parts[1]!, "base64url").toString())); .safeParse(JSON.parse(Buffer.from(parts[1] ?? "", "base64url").toString()));
if (!claims.success) return; if (!claims.success) return;
return ( return (
claims.data.chatgpt_account_id ?? claims.data.chatgpt_account_id ??
@@ -250,23 +259,30 @@ export class QuotaTracker {
return; return;
} }
const id = accountID(credential); const id = accountID(credential);
const account = id const account =
? await fingerprint(`account:${id}`) id !== undefined && id !== ""
: (this.state?.account ?? (await fingerprint(`credential:${credential.refresh}`))); ? await fingerprint(`account:${id}`)
: (this.state?.account ?? (await fingerprint(`credential:${credential.refresh}`)));
if (generation !== this.generation) return; if (generation !== this.generation) return;
if (this.state?.account !== account) { if (this.state?.account !== account) await this.load(account, generation);
const value = await this.context.storage.get(STORAGE_KEY);
const parsed = storedState.safeParse(value);
if (generation !== this.generation) return;
const stored = parsed.success ? parsed.data : undefined;
if (generation !== this.generation) return;
this.state = stored?.account === account ? withoutExcludedState(stored) : { account };
}
if (generation !== this.generation) return; if (generation !== this.generation) return;
if (!this.timer) this.timer = setInterval(() => void this.refresh(), this.pollMs); this.timer ??= setInterval(() => void this.refresh(), this.pollMs);
return credential; return credential;
} }
private async load(account: string, generation: number) {
const value = await this.context.storage.get(STORAGE_KEY);
const parsed = storedState.safeParse(value);
if (generation !== this.generation) return;
const stored = parsed.success ? parsed.data : undefined;
this.state = stored?.account === account ? withoutExcludedState(stored) : { account };
}
/** Reads state through a call so checks after `await` are not narrowed away. */
private current(): StoredState | undefined {
return this.state;
}
private async clear() { private async clear() {
this.state = undefined; this.state = undefined;
if (this.timer) clearInterval(this.timer); if (this.timer) clearInterval(this.timer);
@@ -297,32 +313,20 @@ export class QuotaTracker {
try { try {
const credential = await this.resolveCredential(generation); const credential = await this.resolveCredential(generation);
if (!credential || !this.state || generation !== this.generation) return; if (!credential || !this.state || generation !== this.generation) return;
const controller = new AbortController(); const response = await this.fetchUsage(credential);
this.controller = controller;
const timeout = setTimeout(() => controller.abort(), TIMEOUT_MS);
let response: Response;
try {
const headers = new Headers({
Authorization: `Bearer ${credential.access}`,
Accept: "application/json",
});
const id = accountID(credential);
if (id) headers.set("ChatGPT-Account-Id", id);
response = await this.fetcher(USAGE_URL, { headers, signal: controller.signal });
} finally {
clearTimeout(timeout);
if (this.controller === controller) this.controller = undefined;
}
if (!response.ok || generation !== this.generation) return; if (!response.ok || generation !== this.generation) return;
// SAFETY: JSON.parse semantics from Response.json produce only JSON values; const payload = jsonValue.parse(await response.json());
// quotaPayload validates all fields used below. if (generation !== this.generation || !this.current()) return;
const payload = (await response.json()) as Schema.Json;
if (generation !== this.generation || !this.state) return;
const parsed = quotaPayload.safeParse(payload); const parsed = quotaPayload.safeParse(payload);
if (parsed.success && parsed.data.account_id) { if (
parsed.success &&
parsed.data.account_id !== undefined &&
parsed.data.account_id !== ""
) {
const account = await fingerprint(`account:${parsed.data.account_id}`); const account = await fingerprint(`account:${parsed.data.account_id}`);
if (generation !== this.generation || !this.state) return; const state = this.current();
if (account !== this.state.account) this.state = { account }; if (generation !== this.generation || !state) return;
if (account !== state.account) this.state = { account };
} }
const snapshot = normalizeQuota(payload); const snapshot = normalizeQuota(payload);
if (!snapshot) return; if (!snapshot) return;
@@ -335,6 +339,26 @@ export class QuotaTracker {
} }
} }
private async fetchUsage(credential: Credential.OAuth) {
const controller = new AbortController();
this.controller = controller;
const timeout = setTimeout(() => {
controller.abort();
}, TIMEOUT_MS);
try {
const headers = new Headers({
Authorization: `Bearer ${credential.access}`,
Accept: "application/json",
});
const id = accountID(credential);
if (id !== undefined && id !== "") headers.set("ChatGPT-Account-Id", id);
return await this.fetcher(USAGE_URL, { headers, signal: controller.signal });
} finally {
clearTimeout(timeout);
if (this.controller === controller) this.controller = undefined;
}
}
private apply(snapshot: QuotaSnapshot) { private apply(snapshot: QuotaSnapshot) {
if (!this.state) return; if (!this.state) return;
this.state.latest = snapshot; this.state.latest = snapshot;
+26 -25
View File
@@ -34,9 +34,10 @@ function resetTiming(resetsAt: number, now: number) {
} }
export function formatQuotaWindow(window: QuotaWindow & { remaining: number }, now = Date.now()) { export function formatQuotaWindow(window: QuotaWindow & { remaining: number }, now = Date.now()) {
const label = window.label const label =
? `${window.label} ${duration(window.seconds)}` window.label !== null && window.label !== ""
: duration(window.seconds); ? `${window.label} ${duration(window.seconds)}`
: duration(window.seconds);
return `${label}: ${percent(window.remaining)}% · ${resetTiming(window.resetsAt, now)}`; return `${label}: ${percent(window.remaining)}% · ${resetTiming(window.resetsAt, now)}`;
} }
@@ -60,6 +61,26 @@ export default Plugin.define({
setRevision((value) => value + 1); setRevision((value) => value + 1);
}); });
const Section = (section: { title: string; status: QuotaStatus | null }) => (
<Show when={section.status}>
{(status: () => QuotaStatus) => (
<>
<text fg={context.theme.text.default}>
<b>
{section.title} quota ({status().plan})
</b>
</text>
<For each={status().windows}>
{(window) => (
<text fg={context.theme.text.muted}>
{formatQuotaWindow(window)}
</text>
)}
</For>
</>
)}
</Show>
);
const Slot = (props: { instance: string; centered?: boolean; visible?: () => boolean }) => { const Slot = (props: { instance: string; centered?: boolean; visible?: () => boolean }) => {
const [statuses] = createResource( const [statuses] = createResource(
() => (props.visible?.() === false ? false : `${props.instance}:${revision()}`), () => (props.visible?.() === false ? false : `${props.instance}:${revision()}`),
@@ -71,30 +92,10 @@ export default Plugin.define({
return chatgpt || claude ? { chatgpt, claude } : null; return chatgpt || claude ? { chatgpt, claude } : null;
}, },
); );
const Section = (section: { title: string; status: QuotaStatus | null }) => (
<Show when={section.status}>
{(status: () => QuotaStatus) => (
<>
<text fg={context.theme.text.default}>
<b>
{section.title} quota ({status().plan})
</b>
</text>
<For each={status().windows}>
{(window) => (
<text fg={context.theme.text.muted}>
{formatQuotaWindow(window)}
</text>
)}
</For>
</>
)}
</Show>
);
const Content = () => ( const Content = () => (
<box flexDirection="column"> <box flexDirection="column">
<Section title="ChatGPT" status={statuses()!.chatgpt} /> <Section title="ChatGPT" status={statuses()?.chatgpt ?? null} />
<Section title="Claude" status={statuses()!.claude} /> <Section title="Claude" status={statuses()?.claude ?? null} />
</box> </box>
); );
return ( return (
+11 -6
View File
@@ -2,7 +2,7 @@ import { afterEach, beforeEach, expect, test } from "bun:test";
import { mkdtemp, rm, writeFile } from "node:fs/promises"; import { mkdtemp, rm, writeFile } from "node:fs/promises";
import { tmpdir } from "node:os"; import { tmpdir } from "node:os";
import { join } from "node:path"; import { join } from "node:path";
import { ClaudeQuotaTracker, normalizeClaudeQuota } from "../src/claude-quota.js"; import { ClaudeQuotaTracker, normalizeClaudeQuota } from "../src/quota/claude-quota.js";
const payload = { const payload = {
five_hour: { utilization: 12.5, resets_at: "2026-10-07T12:00:00+00:00" }, five_hour: { utilization: 12.5, resets_at: "2026-10-07T12:00:00+00:00" },
@@ -97,7 +97,10 @@ test("reads credentials file and sends OAuth usage request", async () => {
changed++; changed++;
}, },
async (input, init) => { async (input, init) => {
calls.push({ url: String(input), headers: new Headers(init?.headers) }); calls.push({
url: input instanceof Request ? input.url : String(input),
headers: new Headers(init?.headers),
});
return Response.json(payload); return Response.json(payload);
}, },
60_000, 60_000,
@@ -105,10 +108,12 @@ test("reads credentials file and sends OAuth usage request", async () => {
); );
await tracker.init(); await tracker.init();
expect(calls).toHaveLength(1); expect(calls).toHaveLength(1);
expect(calls[0]!.url).toBe("https://api.anthropic.com/api/oauth/usage"); const [call] = calls;
expect(calls[0]!.headers.get("authorization")).toBe("Bearer token-123"); if (!call) throw new Error("Missing usage request");
expect(calls[0]!.headers.get("anthropic-beta")).toBe("oauth-2025-04-20"); expect(call.url).toBe("https://api.anthropic.com/api/oauth/usage");
expect(calls[0]!.headers.get("accept")).toBe("application/json"); expect(call.headers.get("authorization")).toBe("Bearer token-123");
expect(call.headers.get("anthropic-beta")).toBe("oauth-2025-04-20");
expect(call.headers.get("accept")).toBe("application/json");
expect(tracker.status()?.plan).toBe("max"); expect(tracker.status()?.plan).toBe("max");
expect(tracker.status()?.windows[0]?.remaining).toBe(87.5); expect(tracker.status()?.windows[0]?.remaining).toBe(87.5);
expect(changed).toBe(1); expect(changed).toBe(1);
+19 -7
View File
@@ -1,7 +1,7 @@
import { Plugin, Model, Provider } from "@opencode/plugin/effect"; import { Plugin, Model, Provider } from "@opencode/plugin/effect";
import { fromPromise } from "@opencode/plugin/promise/adapter"; import { fromPromise } from "@opencode/plugin/promise/adapter";
import { Effect } from "effect"; import { Effect } from "effect";
import agents from "../../src/agents.js"; import agents from "../../src/agents/agents.js";
export default Plugin.define({ export default Plugin.define({
id: agents.id, id: agents.id,
@@ -10,18 +10,30 @@ export default Plugin.define({
const providerID = Provider.ID.make("fixture"); const providerID = Provider.ID.make("fixture");
yield* context.provider.transform((editor) => yield* context.provider.transform((editor) =>
editor.add({ editor.add({
info: { // Copy own fields like the former spread; the editor accepts plain info.
...Provider.Info.empty(providerID), info: Object.assign({}, Provider.Info.empty(providerID), {
name: "Isolated fixture", name: "Isolated fixture",
activation: "enabled", activation: "enabled" as const,
package: "@opencode/ai/providers/openai-compatible", package: "@opencode/ai/providers/openai-compatible",
settings: { baseURL: process.env.FIXTURE_MODEL_URL! }, settings: { baseURL: process.env["FIXTURE_MODEL_URL"] ?? "" },
}, }),
models: ["gpt-6-luna", "gpt-6.1-sol", "gpt-6-astra"].map((id) => models: ["gpt-6-luna", "gpt-6.1-sol", "gpt-6-astra"].map((id) =>
Model.Info.default(providerID, Model.ID.make(id)), Model.Info.default(providerID, Model.ID.make(id)),
), ),
}), }),
); );
yield* fromPromise(agents).effect({ ...context, options: { provider: "fixture" } }); yield* fromPromise(agents).effect({
...context,
options: {
agents: {
"fast-lo": "fixture/gpt-6-luna",
"fast-hi": "fixture/gpt-6-luna",
"good-lo": "fixture/gpt-6.1-sol",
"good-hi": "fixture/gpt-6.1-sol",
"deep-lo": "fixture/gpt-6-astra",
"deep-hi": "fixture/gpt-6-astra",
},
},
});
}), }),
}); });
+3 -3
View File
@@ -6,7 +6,7 @@ import { Tool } from "@opencode/schema/tool";
import { Cause, Effect } from "effect"; import { Cause, Effect } from "effect";
import { z } from "zod"; import { z } from "zod";
import { appendFile } from "node:fs/promises"; import { appendFile } from "node:fs/promises";
import multiWork from "../../src/multi-work.js"; import multiWork from "../../src/multi-work/multi-work.js";
const probe = Rpc.define({ const probe = Rpc.define({
id: "multi-work-test", id: "multi-work-test",
@@ -37,7 +37,7 @@ export default Plugin.define({
const child = yield* context.session.get({ sessionID: event.sessionID }); const child = yield* context.session.get({ sessionID: event.sessionID });
yield* Effect.promise(() => yield* Effect.promise(() =>
appendFile( appendFile(
process.env.FIXTURE_TRACE!, process.env["FIXTURE_TRACE"] ?? "",
JSON.stringify({ JSON.stringify({
id: child.id, id: child.id,
parent: child.parentID, parent: child.parentID,
@@ -59,7 +59,7 @@ export default Plugin.define({
description: "native host proof", description: "native host proof",
prompt: "Reply with FIXTURE_COMPLETE", prompt: "Reply with FIXTURE_COMPLETE",
background: input.background, background: input.background,
...(input.child ...(input.child !== undefined && input.child !== ""
? { sessionID: input.child } ? { sessionID: input.child }
: { : {
worktree: { worktree: {
+9 -8
View File
@@ -2,7 +2,7 @@ import { afterEach, expect, test } from "bun:test";
import { mkdir, mkdtemp, rm } from "node:fs/promises"; import { mkdir, mkdtemp, rm } from "node:fs/promises";
import { tmpdir } from "node:os"; import { tmpdir } from "node:os";
import { join } from "node:path"; import { join } from "node:path";
import { command, Herdr } from "../src/herdr.js"; import { command, Herdr } from "../src/multi-work/herdr.js";
const directories: string[] = []; const directories: string[] = [];
afterEach(async () => { afterEach(async () => {
@@ -45,9 +45,9 @@ async function fixture() {
let childWorkspaceIDOverride: string | undefined; let childWorkspaceIDOverride: string | undefined;
let childPathOverride: string | undefined; let childPathOverride: string | undefined;
let repoOverride: string | undefined; let repoOverride: string | undefined;
const run = async (args: string[], cwd: string, signal: AbortSignal) => { const run = async (args: string[], cwd: string, abort: AbortSignal) => {
calls.push(args); calls.push(args);
if (args[0] !== "herdr") return command(args, cwd, signal); if (args[0] !== "herdr") return command(args, cwd, abort);
if (args[1] === "workspace") if (args[1] === "workspace")
return JSON.stringify({ return JSON.stringify({
result: { result: {
@@ -57,7 +57,7 @@ async function fixture() {
}, },
}); });
if (args[2] === "list") { if (args[2] === "list") {
const id = args[4]!; const id = args[4] ?? "";
const path = id === "w2" ? destination : root; const path = id === "w2" ? destination : root;
const sourceWorkspaceID = sourceWorkspaceIDOverride ?? (id === "w2" ? "w1" : id); const sourceWorkspaceID = sourceWorkspaceIDOverride ?? (id === "w2" ? "w1" : id);
const sourcePath = sourcePathOverride ?? root; const sourcePath = sourcePathOverride ?? root;
@@ -93,10 +93,10 @@ async function fixture() {
expect(args[2]).toBe("create"); expect(args[2]).toBe("create");
expect(args.slice(3, 5)).toEqual(["--cwd", root]); expect(args.slice(3, 5)).toEqual(["--cwd", root]);
expect(args.at(-1)).toBe("--no-focus"); expect(args.at(-1)).toBe("--no-focus");
branch = args[args.indexOf("--branch") + 1]!; branch = args[args.indexOf("--branch") + 1] ?? "";
const labelIndex = args.indexOf("--label"); const labelIndex = args.indexOf("--label");
label = labelIndex === -1 ? undefined : args[labelIndex + 1]; label = labelIndex === -1 ? undefined : args[labelIndex + 1];
const base = args[args.indexOf("--base") + 1]!; const base = args[args.indexOf("--base") + 1] ?? "";
// Real Git worktree behavior, but only in an isolated temporary repository. // Real Git worktree behavior, but only in an isolated temporary repository.
await command(["git", "worktree", "add", "-b", branch, destination, base], root, signal); await command(["git", "worktree", "add", "-b", branch, destination, base], root, signal);
return JSON.stringify({ return JSON.stringify({
@@ -144,14 +144,15 @@ test("create verifies a linked workspace whose inventory source remains the pare
const f = await fixture(); const f = await fixture();
const root = await f.herdr.root(f.root, f.signal); const root = await f.herdr.root(f.root, f.signal);
expect(root?.workspaceID).toBe("w1"); expect(root?.workspaceID).toBe("w1");
const destination = await f.herdr.create(root!, "other", "multi-work/fixture", f.signal); if (!root) throw new Error("Missing Herdr root");
const destination = await f.herdr.create(root, "other", "multi-work/fixture", f.signal);
expect(destination.directory).toBe(f.destination); expect(destination.directory).toBe(f.destination);
expect(destination.branch).toStartWith("multi-work/"); expect(destination.branch).toStartWith("multi-work/");
expect(await command(["git", "branch", "--show-current"], f.root, f.signal)).toBe("main"); expect(await command(["git", "branch", "--show-current"], f.root, f.signal)).toBe("main");
await f.herdr.verify( await f.herdr.verify(
destination.directory, destination.directory,
destination.workspaceID, destination.workspaceID,
root!, root,
destination.branch, destination.branch,
f.signal, f.signal,
); );
+51 -27
View File
@@ -3,6 +3,7 @@ import { chmod, mkdir, mkdtemp, readFile, readdir, rm, writeFile } from "node:fs
import { tmpdir } from "node:os"; import { tmpdir } from "node:os";
import { dirname, join } from "node:path"; import { dirname, join } from "node:path";
import { createHash } from "node:crypto"; import { createHash } from "node:crypto";
import { z } from "zod";
import { install } from "../scripts/install.js"; import { install } from "../scripts/install.js";
const directories: string[] = []; const directories: string[] = [];
@@ -34,6 +35,15 @@ const empty = {
"deep-hi": "", "deep-hi": "",
}, },
}; };
const pluginEntry = z
.object({ package: z.string(), options: z.record(z.string(), z.json()).optional() })
.loose();
const configFile = z
.object({ plugins: z.array(z.json()), experimental: z.json().optional() })
.loose();
const manifestFile = z.object({ exports: z.record(z.string(), z.json()) }).loose();
const entries = (plugins: z.infer<typeof configFile>["plugins"]) =>
z.array(pluginEntry).parse(plugins);
const helper = new URL("../scripts/install.ts", import.meta.url); const helper = new URL("../scripts/install.ts", import.meta.url);
async function run( async function run(
command: string[], command: string[],
@@ -50,8 +60,8 @@ async function run(
timeout: 30_000, timeout: 30_000,
}); });
if (input !== undefined && process.stdin) { if (input !== undefined && process.stdin) {
process.stdin.write(input); void process.stdin.write(input);
process.stdin.end(); void process.stdin.end();
} }
const [exitCode, stdout, stderr] = await Promise.all([ const [exitCode, stdout, stderr] = await Promise.all([
process.exited, process.exited,
@@ -83,7 +93,9 @@ async function fixture() {
format: "esm", format: "esm",
}); });
expect(built.success).toBe(true); expect(built.success).toBe(true);
await Bun.write(join(source, "dist", "install.js"), built.outputs[0]!); const [output] = built.outputs;
if (output === undefined) throw new Error("Missing installer build output");
await Bun.write(join(source, "dist", "install.js"), output);
await writeFile(join(source, "package.json"), '{"type":"module"}'); await writeFile(join(source, "package.json"), '{"type":"module"}');
await writeFile( await writeFile(
join(config, "opencode.json"), join(config, "opencode.json"),
@@ -96,7 +108,7 @@ async function fixture() {
return { directory, source, config }; return { directory, source, config };
} }
async function contents(config: string) { async function contents(config: string) {
return JSON.parse(await readFile(join(config, "opencode.json"), "utf8")); return configFile.parse(JSON.parse(await readFile(join(config, "opencode.json"), "utf8")));
} }
for (const selection of ["quota", "agents,multi-work,quota"]) { for (const selection of ["quota", "agents,multi-work,quota"]) {
@@ -106,14 +118,16 @@ for (const selection of ["quota", "agents,multi-work,quota"]) {
const result = await contents(f.config); const result = await contents(f.config);
expect(result).toMatchObject(unrelated); expect(result).toMatchObject(unrelated);
expect(result.experimental === undefined).toBe(selection === "quota"); expect(result.experimental === undefined).toBe(selection === "quota");
expect(result.plugins.map((entry: { package: string }) => entry.package)).toEqual([ expect(entries(result.plugins).map((entry) => entry.package)).toEqual([
"before", "before",
...selection.split(",").map((name) => `./plugins/stanp-opencode/${name}`), ...selection.split(",").map((name) => `./plugins/stanp-opencode/${name}`),
]); ]);
const target = join(f.config, "plugins", "stanp-opencode"); const target = join(f.config, "plugins", "stanp-opencode");
expect((await readdir(target)).sort()).toEqual(selection.split(",").sort()); expect((await readdir(target)).toSorted()).toEqual(selection.split(",").toSorted());
for (const name of selection.split(",")) { for (const name of selection.split(",")) {
const manifest = await Bun.file(join(target, name, "package.json")).json(); const manifest = manifestFile.parse(
await Bun.file(join(target, name, "package.json")).json(),
);
expect(manifest.exports["./tui"] !== undefined).toBe(name === "quota"); expect(manifest.exports["./tui"] !== undefined).toBe(name === "quota");
expect(await Bun.file(join(target, name, "tui.js")).exists()).toBe(name === "quota"); expect(await Bun.file(join(target, name, "tui.js")).exists()).toBe(name === "quota");
} }
@@ -127,18 +141,23 @@ test("upgrades retain selection and options; explicit selection replaces only ow
const f = await fixture(); const f = await fixture();
await install(f.source, f.config, "agents,quota"); await install(f.source, f.config, "agents,quota");
const current = await contents(f.config); const current = await contents(f.config);
current.plugins[1].options = { const [before, agents, quota] = entries(current.plugins);
agents: { ...empty.agents, "fast-lo": "openai/gpt-6-luna#low" }, if (!before || !agents || !quota) throw new Error("Missing installed plugins");
}; const after = { package: "after", options: { untouched: 1 } };
current.plugins.push({ package: "after", options: { untouched: 1 } }); const plugins = [
await writeFile(join(f.config, "opencode.json"), JSON.stringify(current)); before,
{ ...agents, options: { agents: { ...empty.agents, "fast-lo": "openai/gpt-6-luna#low" } } },
quota,
after,
];
await writeFile(join(f.config, "opencode.json"), JSON.stringify({ ...current, plugins }));
await install(f.source, f.config); await install(f.source, f.config);
expect((await contents(f.config)).plugins).toEqual(current.plugins); expect(entries((await contents(f.config)).plugins)).toEqual(plugins);
await install(f.source, f.config, "quota"); await install(f.source, f.config, "quota");
expect((await contents(f.config)).plugins).toEqual([ expect(entries((await contents(f.config)).plugins)).toEqual([
current.plugins[0], before,
{ package: "./plugins/stanp-opencode/quota" }, { package: "./plugins/stanp-opencode/quota" },
current.plugins[3], after,
]); ]);
}); });
@@ -152,14 +171,17 @@ test("installer writes empty option skeletons and subagent_depth, fills only mis
{ package: "./plugins/stanp-opencode/quota" }, { package: "./plugins/stanp-opencode/quota" },
]); ]);
expect(fresh.experimental).toEqual({ subagent_depth: 2 }); expect(fresh.experimental).toEqual({ subagent_depth: 2 });
fresh.plugins[1].options = { const [before, agents, ...rest] = entries(fresh.plugins);
agents: { "fast-lo": "openai/gpt-6-luna#low" }, if (!before || !agents) throw new Error("Missing installed plugins");
extra: 1, const plugins = [
}; before,
await writeFile(join(f.config, "opencode.json"), JSON.stringify(fresh)); { ...agents, options: { agents: { "fast-lo": "openai/gpt-6-luna#low" }, extra: 1 } },
...rest,
];
await writeFile(join(f.config, "opencode.json"), JSON.stringify({ ...fresh, plugins }));
await install(f.source, f.config); await install(f.source, f.config);
const filled = await contents(f.config); const filled = await contents(f.config);
expect(filled.plugins[1].options).toEqual({ expect(entries(filled.plugins)[1]?.options).toEqual({
agents: { ...empty.agents, "fast-lo": "openai/gpt-6-luna#low" }, agents: { ...empty.agents, "fast-lo": "openai/gpt-6-luna#low" },
extra: 1, extra: 1,
}); });
@@ -169,7 +191,7 @@ test("installer writes empty option skeletons and subagent_depth, fills only mis
for (const [depth, expected] of [ for (const [depth, expected] of [
[1, 2], [1, 2],
[3, 3], [3, 3],
]) { ] as const) {
await writeFile( await writeFile(
join(f.config, "opencode.json"), join(f.config, "opencode.json"),
JSON.stringify({ JSON.stringify({
@@ -214,12 +236,14 @@ test("replaces the legacy monolith without duplicates and retains Agents options
await writeFile(join(f.config, "plugins", "stanp-opencode.js"), "legacy"); await writeFile(join(f.config, "plugins", "stanp-opencode.js"), "legacy");
await install(f.source, f.config); await install(f.source, f.config);
const result = await contents(f.config); const result = await contents(f.config);
expect(result.plugins.map((entry: { package: string }) => entry.package)).toEqual([ expect(entries(result.plugins).map((entry) => entry.package)).toEqual([
"before", "before",
...names.map((name) => `./plugins/stanp-opencode/${name}`), ...names.map((name) => `./plugins/stanp-opencode/${name}`),
"after", "after",
]); ]);
expect(result.plugins[1].options.agents["fast-lo"]).toBe("openai/gpt-6-luna#low"); expect(result.plugins[1]).toMatchObject({
options: { agents: { "fast-lo": "openai/gpt-6-luna#low" } },
});
expect(await Bun.file(join(f.config, "plugins", "stanp-opencode.js")).exists()).toBe(false); expect(await Bun.file(join(f.config, "plugins", "stanp-opencode.js")).exists()).toBe(false);
expect(result).toMatchObject(unrelated); expect(result).toMatchObject(unrelated);
}); });
@@ -283,7 +307,7 @@ test("local shell installer builds its checkout and upgrades mixed entries witho
await chmod(join(bin, "bun"), 0o755); await chmod(join(bin, "bun"), 0o755);
const env = { const env = {
...Bun.env, ...Bun.env,
PATH: `${bin}:${dirname(process.execPath)}:${Bun.env.PATH}`, PATH: `${bin}:${dirname(process.execPath)}:${Bun.env["PATH"]}`,
REAL_BUN: process.execPath, REAL_BUN: process.execPath,
CALLS: join(f.directory, "calls"), CALLS: join(f.directory, "calls"),
OPENCODE_CONFIG_DIR: f.config, OPENCODE_CONFIG_DIR: f.config,
@@ -357,7 +381,7 @@ for (const validChecksum of [true, false])
f.directory, f.directory,
{ {
...Bun.env, ...Bun.env,
PATH: `${bin}:${dirname(process.execPath)}:${Bun.env.PATH}`, PATH: `${bin}:${dirname(process.execPath)}:${Bun.env["PATH"]}`,
ARCHIVE: archive, ARCHIVE: archive,
CHECKSUM: checksum, CHECKSUM: checksum,
RELEASE: release, RELEASE: release,
+31 -22
View File
@@ -9,8 +9,8 @@ import type { ToolEditor, ToolHooks } from "@opencode/plugin/effect/tool";
import type { AgentEditor } from "@opencode/plugin/effect/agent"; import type { AgentEditor } from "@opencode/plugin/effect/agent";
import type { SessionContext } from "@opencode/plugin/effect/session"; import type { SessionContext } from "@opencode/plugin/effect/session";
import { z } from "zod"; import { z } from "zod";
import { Herdr, type HerdrRoot } from "../src/herdr.js"; import { Herdr, type HerdrRoot } from "../src/multi-work/herdr.js";
import { bindingKey, bindingSchema, installMultiWork } from "../src/multi-work.js"; import { bindingKey, bindingSchema, installMultiWork } from "../src/multi-work/multi-work.js";
class FixtureHerdr extends Herdr { class FixtureHerdr extends Herdr {
eligible = true; eligible = true;
@@ -70,6 +70,19 @@ interface FixtureSession {
permissions: Agent.Info["permissions"]; permissions: Agent.Info["permissions"];
} }
const defaultInput = {
agent: "coordinate",
description: "test",
prompt: "work",
worktree: { base: "main" },
};
function required<T>(map: Map<string, T>, key: string) {
const value = map.get(key);
if (value === undefined) throw new Error(`Missing fixture entry ${key}`);
return value;
}
function fixture() { function fixture() {
const herdr = new FixtureHerdr(); const herdr = new FixtureHerdr();
const storage = new Map<string, Parameters<Context["storage"]["set"]>[1]>(); const storage = new Map<string, Parameters<Context["storage"]["set"]>[1]>();
@@ -112,7 +125,7 @@ function fixture() {
}) })
.parse(raw); .parse(raw);
const id = Session.ID.make(input.sessionID ?? `ses_child${++serial}`); const id = Session.ID.make(input.sessionID ?? `ses_child${++serial}`);
if (!input.sessionID) if (input.sessionID === undefined || input.sessionID === "")
sessions.set(id, { sessions.set(id, {
...parent, ...parent,
id, id,
@@ -122,7 +135,7 @@ function fixture() {
}); });
order.push("create"); order.push("create");
yield* call.progress({ sessionID: id, status: "running" }); yield* call.progress({ sessionID: id, status: "running" });
order.push(`prompt:${sessions.get(id)!.location.directory}`); order.push(`prompt:${required(sessions, id).location.directory}`);
prompts++; prompts++;
entered.resolve(); entered.resolve();
if (hold) if (hold)
@@ -135,7 +148,10 @@ function fixture() {
); );
return { return {
content: "native result", content: "native result",
metadata: { sessionID: id, status: input.background ? "running" : "completed" }, metadata: {
sessionID: id,
status: input.background === true ? "running" : "completed",
},
}; };
}), }),
}; };
@@ -144,7 +160,7 @@ function fixture() {
[]; [];
const hooks: ((event: SessionContext) => Effect.Effect<void>)[] = []; const hooks: ((event: SessionContext) => Effect.Effect<void>)[] = [];
let prompt!: (event: Pick<SessionContext, "sessionID">) => Effect.Effect<void>; let prompt!: (event: Pick<SessionContext, "sessionID">) => Effect.Effect<void>;
let transform!: (editor: AgentEditor) => void; let transform: ((editor: AgentEditor) => void) | undefined;
const registration = Effect.succeed({ dispose: Effect.void }); const registration = Effect.succeed({ dispose: Effect.void });
const editAgents = (): AgentEditor => ({ const editAgents = (): AgentEditor => ({
get: (id) => agents.get(id), get: (id) => agents.get(id),
@@ -185,16 +201,16 @@ function fixture() {
}), }),
}, },
agent: { agent: {
transform: (callback: typeof transform) => transform: (callback: (editor: AgentEditor) => void) =>
Effect.sync(() => { Effect.sync(() => {
transform = callback; transform = callback;
callback(editAgents()); callback(editAgents());
}).pipe(Effect.andThen(registration)), }).pipe(Effect.andThen(registration)),
reload: () => reload: () =>
Effect.sync(() => { Effect.sync(() => {
if (transform) transform(editAgents()); transform?.(editAgents());
}), }),
get: () => Effect.succeed({ data: agents.get("multi-work")! }), get: () => Effect.succeed({ data: required(agents, "multi-work") }),
list: () => list: () =>
Effect.sync(() => { Effect.sync(() => {
agentReads++; agentReads++;
@@ -204,14 +220,15 @@ function fixture() {
}, },
session: { session: {
get: ({ sessionID }: { sessionID: string }) => get: ({ sessionID }: { sessionID: string }) =>
Effect.sync(() => sessions.get(sessionID)!), Effect.sync(() => required(sessions, sessionID)),
move: ({ sessionID, directory }: { sessionID: string; directory: string }) => move: ({ sessionID, directory }: { sessionID: string; directory: string }) =>
Effect.sync(() => { Effect.sync(() => {
order.push("move-request"); order.push("move-request");
if (!delayMove) { if (!delayMove) {
sessions.get(sessionID)!.location.directory = directory; required(sessions, sessionID).location.directory = directory;
order.push("moved"); order.push("moved");
if (crossProject) sessions.get(sessionID)!.projectID = "another-project"; if (crossProject)
required(sessions, sessionID).projectID = "another-project";
} }
entered.resolve(); entered.resolve();
}), }),
@@ -272,15 +289,7 @@ function fixture() {
Agent.Info.default(Agent.ID.make("build")).permissions, Agent.Info.default(Agent.ID.make("build")).permissions,
herdr, herdr,
), ),
invoke: ( invoke: (input = defaultInput, caller = call) => tool.execute(input, caller),
input = {
agent: "coordinate",
description: "test",
prompt: "work",
worktree: { base: "main" },
},
caller = call,
) => tool.execute(input, caller),
execute: (input: z.infer<typeof request>, caller = call) => tool.execute(input, caller), execute: (input: z.infer<typeof request>, caller = call) => tool.execute(input, caller),
hold() { hold() {
hold = true; hold = true;
@@ -381,7 +390,7 @@ test("root-local resume rejects location, binding, and live-root changes", async
prompt: "work", prompt: "work",
}); });
if (tamper === "session") if (tamper === "session")
f.sessions.get("ses_child1")!.location.directory = "/other"; required(f.sessions, "ses_child1").location.directory = "/other";
else if (tamper === "live-root") f.herdr.rootWorkspaceID = "foreign"; else if (tamper === "live-root") f.herdr.rootWorkspaceID = "foreign";
else { else {
const binding = bindingSchema.parse( const binding = bindingSchema.parse(
+22 -4
View File
@@ -3,9 +3,19 @@ import { mkdir, mkdtemp, rm } from "node:fs/promises";
import { tmpdir } from "node:os"; import { tmpdir } from "node:os";
import { join } from "node:path"; import { join } from "node:path";
import { Host } from "@opencode/plugin/host"; import { Host } from "@opencode/plugin/host";
import { z } from "zod";
import { build } from "../scripts/build.js"; import { build } from "../scripts/build.js";
import { install } from "../scripts/install.js"; import { install } from "../scripts/install.js";
test("bundled Effect matches the host's exact Effect version", async () => {
const manifest = z.object({ dependencies: z.record(z.string(), z.string()) });
const own = manifest.parse(await Bun.file("package.json").json());
const host = z
.object({ peerDependencies: z.object({ effect: z.string() }) })
.parse(await Bun.file("node_modules/@opencode/client/package.json").json());
expect(own.dependencies["effect"]).toBe(host.peerDependencies.effect);
});
test("packed package has independent native plugins and quota-only TUI discovery", async () => { test("packed package has independent native plugins and quota-only TUI discovery", async () => {
const directory = await mkdtemp(join(tmpdir(), "plugin-package-")); const directory = await mkdtemp(join(tmpdir(), "plugin-package-"));
try { try {
@@ -23,13 +33,19 @@ test("packed package has independent native plugins and quota-only TUI discovery
}); });
expect(await unpack.exited).toBe(0); expect(await unpack.exited).toBe(0);
const source = join(directory, "package"); const source = join(directory, "package");
const manifest = await Bun.file(join(source, "package.json")).json(); const manifest = z
.object({ exports: z.record(z.string(), z.object({ import: z.string() }).loose()) })
.loose()
.parse(await Bun.file(join(source, "package.json")).json());
const entrypoint = (name: string) =>
join(source, z.string().parse(manifest.exports[name]?.import));
expect(manifest.exports["."]).toBeUndefined(); expect(manifest.exports["."]).toBeUndefined();
expect(await Bun.file(join(source, "index.js")).exists()).toBe(false); expect(await Bun.file(join(source, "index.js")).exists()).toBe(false);
expect(await Bun.file(join(source, "dist", "index.js")).exists()).toBe(false); expect(await Bun.file(join(source, "dist", "index.js")).exists()).toBe(false);
for (const name of ["agents", "multi-work", "quota"]) { for (const name of ["agents", "multi-work", "quota"]) {
const entrypoint = join(source, manifest.exports[`./${name}`].import); const { default: plugin } = z
const { default: plugin } = await import(entrypoint); .object({ default: z.object({ id: z.string() }).loose() })
.parse(await import(entrypoint(`./${name}`)));
expect(plugin.id).toBe(`stanp-opencode.${name}`); expect(plugin.id).toBe(`stanp-opencode.${name}`);
} }
const config = join(directory, "config"); const config = join(directory, "config");
@@ -42,7 +58,9 @@ test("packed package has independent native plugins and quota-only TUI discovery
expect(entries.server).toBeDefined(); expect(entries.server).toBeDefined();
expect(entries.tui !== undefined).toBe(name === "quota"); expect(entries.tui !== undefined).toBe(name === "quota");
} }
const { QuotaRpc } = await import(join(source, manifest.exports["./quota-rpc"].import)); const { QuotaRpc } = z
.object({ QuotaRpc: z.object({ id: z.string() }).loose() })
.parse(await import(entrypoint("./quota-rpc")));
expect(QuotaRpc.id).toBe("stanp-opencode.quota"); expect(QuotaRpc.id).toBe("stanp-opencode.quota");
} finally { } finally {
await rm(directory, { recursive: true, force: true }); await rm(directory, { recursive: true, force: true });
+27 -25
View File
@@ -7,10 +7,10 @@ import type { SkillEditor } from "@opencode/plugin/promise/skill";
import type { DeepMutable } from "@opencode/plugin/promise/types"; import type { DeepMutable } from "@opencode/plugin/promise/types";
import type { Skill } from "@opencode/schema/skill"; import type { Skill } from "@opencode/schema/skill";
import type { ModelInfo } from "@opencode/client"; import type { ModelInfo } from "@opencode/client";
import plugin from "../src/agents.js"; import plugin from "../src/agents/agents.js";
import { model } from "../src/model.js"; import { model } from "../src/agents/model.js";
import { z } from "zod"; import { z } from "zod";
import { AgentsRpc } from "../src/agents-rpc.js"; import { AgentsRpc } from "../src/agents/agents-rpc.js";
const cleanups: Plugin.Cleanup[] = []; const cleanups: Plugin.Cleanup[] = [];
afterEach(async () => { afterEach(async () => {
@@ -31,24 +31,29 @@ const agents = {
"deep-lo": "test/gpt-6-astra#low", "deep-lo": "test/gpt-6-astra#low",
"deep-hi": "test/gpt-6-astra#high", "deep-hi": "test/gpt-6-astra#high",
}; };
const defaultOptions = { agents };
const defaultLocation = { directory: "/fixture" };
async function flush() {
await Bun.sleep(10);
}
async function host( async function host(
catalog: ModelInfo[] = models, catalog: ModelInfo[] = models,
options: Plugin.Context["options"] = { agents }, options: Plugin.Context["options"] = defaultOptions,
existingSkill?: Skill.Info, existingSkill?: Skill.Info,
) { ) {
const agents = new Map<string, DeepMutable<Agent.Info>>(); const registry = new Map<string, DeepMutable<Agent.Info>>();
let build: DeepMutable<Agent.Info> = Agent.Info.default(Agent.ID.make("build")); let build: DeepMutable<Agent.Info> = Agent.Info.default(Agent.ID.make("build"));
const skills = new Map<string, Skill.Info>( const skills = new Map<string, Skill.Info>(
existingSkill ? [[existingSkill.id, existingSkill]] : [], existingSkill ? [[existingSkill.id, existingSkill]] : [],
); );
let transform: (editor: AgentEditor) => void; let transform: ((editor: AgentEditor) => void) | undefined;
let contextHook: (event: Pick<SessionContext, "agent" | "tools">) => Promise<void> | void; let contextHook: (event: Pick<SessionContext, "agent" | "tools">) => Promise<void> | void;
let promptHook: (event: { sessionID: string }) => Promise<void> | void; let promptHook: (event: { sessionID: string }) => Promise<void> | void;
let before: (event: { tool: string; agent: string; input: unknown }) => Promise<void> | void; let before: (event: { tool: string; agent: string; input: unknown }) => Promise<void> | void;
let parent = "build"; let parent = "build";
let child = "fast-lo"; let child = "fast-lo";
let tools: string[] = []; let tools: string[] = [];
let toolTransform: (editor: ToolEditor) => void; let toolTransform: ((editor: ToolEditor) => void) | undefined;
let permissions: () => Promise<Agent.Info["permissions"]>; let permissions: () => Promise<Agent.Info["permissions"]>;
let controller: ReadableStreamDefaultController<unknown>; let controller: ReadableStreamDefaultController<unknown>;
const stream = new ReadableStream({ const stream = new ReadableStream({
@@ -58,20 +63,20 @@ async function host(
}); });
const registration = { async dispose() {} }; const registration = { async dispose() {} };
const replay = () => { const replay = () => {
agents.clear(); registry.clear();
agents.set("build", structuredClone(build)); registry.set("build", structuredClone(build));
transform?.({ transform?.({
get: (id) => agents.get(id), get: (id) => registry.get(id),
list: () => [...agents.values()], list: () => [...registry.values()],
default() {}, default() {},
remove: (id) => { remove: (id) => {
agents.delete(id); registry.delete(id);
}, },
update(id, update) { update(id, update) {
const draft = const draft =
agents.get(id) ?? structuredClone(Agent.Info.default(Agent.ID.make(id))); registry.get(id) ?? structuredClone(Agent.Info.default(Agent.ID.make(id)));
update(draft); update(draft);
agents.set(id, draft); registry.set(id, draft);
}, },
}); });
}; };
@@ -110,7 +115,7 @@ async function host(
}, },
agent: { agent: {
async list() { async list() {
return { data: [...agents.values()] }; return { data: [...registry.values()] };
}, },
async reload() { async reload() {
replay(); replay();
@@ -182,11 +187,8 @@ async function host(
replay(); replay();
const cleanup = await setup(context); const cleanup = await setup(context);
if (cleanup) cleanups.push(cleanup); if (cleanup) cleanups.push(cleanup);
const flush = async () => {
await Bun.sleep(10);
};
return { return {
agents, agents: registry,
skills, skills,
permissions: () => permissions(), permissions: () => permissions(),
async configure(rules: Agent.Info["permissions"]) { async configure(rules: Agent.Info["permissions"]) {
@@ -195,7 +197,7 @@ async function host(
controller.enqueue({ type: "agent.updated" }); controller.enqueue({ type: "agent.updated" });
await flush(); await flush();
}, },
async models(next: ModelInfo[], location = { directory: "/fixture" }) { async models(next: ModelInfo[], location = defaultLocation) {
catalog = next; catalog = next;
controller.enqueue({ type: "model.updated", location }); controller.enqueue({ type: "model.updated", location });
await flush(); await flush();
@@ -205,10 +207,10 @@ async function host(
replayTools(); replayTools();
await flush(); await flush();
}, },
async delegate(agent: string, target: string) { delegate: async (agent: string, target: string) => {
await before({ tool: "subagent", agent, input: { agent: target } }); await before({ tool: "subagent", agent, input: { agent: target } });
}, },
async command(owner: string, target: string) { command: async (owner: string, target: string) => {
parent = owner; parent = owner;
child = target; child = target;
await promptHook({ sessionID: "child" }); await promptHook({ sessionID: "child" });
@@ -231,7 +233,7 @@ async function host(
test("worker availability, deep fallback, and model refresh remain provider aware", async () => { test("worker availability, deep fallback, and model refresh remain provider aware", async () => {
const h = await host(); const h = await host();
expect([...h.skills.keys()].sort()).toEqual(["anti-overengineering", "task-planning"]); expect([...h.skills.keys()].toSorted()).toEqual(["anti-overengineering", "task-planning"]);
expect(String(h.agents.get("coordinate")?.model?.id)).toBe("gpt-6-astra"); expect(String(h.agents.get("coordinate")?.model?.id)).toBe("gpt-6-astra");
await h.models(models.slice(0, 2)); await h.models(models.slice(0, 2));
expect(String(h.agents.get("coordinate")?.model?.id)).toBe("gpt-6.1-sol"); expect(String(h.agents.get("coordinate")?.model?.id)).toBe("gpt-6.1-sol");
@@ -256,7 +258,7 @@ test("assignments are provider-qualified with optional deep pair and variant; pa
const shallow = Object.fromEntries( const shallow = Object.fromEntries(
Object.entries(agents).filter(([name]) => !name.startsWith("deep-")), Object.entries(agents).filter(([name]) => !name.startsWith("deep-")),
); );
const duplicate = models.map((model) => ({ ...model, providerID: Provider.ID.make("other") })); const duplicate = models.map((entry) => ({ ...entry, providerID: Provider.ID.make("other") }));
const h = await host([...duplicate, ...models], { agents: shallow }); const h = await host([...duplicate, ...models], { agents: shallow });
expect(String(h.agents.get("coordinate")?.model?.providerID)).toBe("test"); expect(String(h.agents.get("coordinate")?.model?.providerID)).toBe("test");
expect(String(h.agents.get("coordinate")?.model?.id)).toBe("gpt-6.1-sol"); expect(String(h.agents.get("coordinate")?.model?.id)).toBe("gpt-6.1-sol");
@@ -295,6 +297,6 @@ test("native tool and command paths retain core delegation restrictions", async
expect( expect(
z z
.object({ agent: z.object({ type: z.string(), enum: z.array(z.string()) }) }) .object({ agent: z.object({ type: z.string(), enum: z.array(z.string()) }) })
.parse((await h.request("coordinate")).subagent?.input.properties).agent, .parse((await h.request("coordinate"))["subagent"]?.input["properties"]).agent,
).toEqual({ type: "string", enum: ["fast-lo", "fast-hi", "good-lo", "good-hi"] }); ).toEqual({ type: "string", enum: ["fast-lo", "fast-hi", "good-lo", "good-hi"] });
}); });
+4 -6
View File
@@ -1,7 +1,7 @@
import { expect, test } from "bun:test"; import { expect, test } from "bun:test";
import type { Plugin } from "@opencode/plugin"; import type { Plugin } from "@opencode/plugin";
import quota from "../src/quota-plugin.js"; import quota from "../src/quota/quota-plugin.js";
import { QuotaRpc } from "../src/quota-rpc.js"; import { QuotaRpc } from "../src/quota/quota-rpc.js";
test("Quota loads independently and retains its RPC ID and nullable status", async () => { test("Quota loads independently and retains its RPC ID and nullable status", async () => {
let controller: ReadableStreamDefaultController<unknown>; let controller: ReadableStreamDefaultController<unknown>;
@@ -18,9 +18,7 @@ test("Quota loads independently and retains its RPC ID and nullable status", asy
location: { directory: "/fixture" }, location: { directory: "/fixture" },
integration: { integration: {
connection: { connection: {
async active() { async active() {},
return undefined;
},
}, },
}, },
event: { event: {
@@ -56,7 +54,7 @@ test("Quota loads independently and retains its RPC ID and nullable status", asy
) => ReturnType<typeof quota.setup>; ) => ReturnType<typeof quota.setup>;
const cleanup = await setup(context); const cleanup = await setup(context);
expect(quota.id).toBe("stanp-opencode.quota"); expect(quota.id).toBe("stanp-opencode.quota");
expect(await status!()).toBeNull(); expect(await status?.()).toBeNull();
expect(modelHook).toBe(true); expect(modelHook).toBe(true);
if (cleanup) await cleanup(); if (cleanup) await cleanup();
expect(disposed).toBe(true); expect(disposed).toBe(true);
+3 -3
View File
@@ -1,6 +1,6 @@
import { expect, test } from "bun:test"; import { expect, test } from "bun:test";
import type { Schema } from "effect"; import type { Schema } from "effect";
import { normalizeQuota, QuotaTracker } from "../src/quota.js"; import { normalizeQuota, QuotaTracker } from "../src/quota/quota.js";
const plus = { const plus = {
plan_type: "plus", plan_type: "plus",
@@ -186,8 +186,8 @@ function fixture(
changes: () => changes, changes: () => changes,
headers, headers,
stored, stored,
switch(credential: typeof current) { switch(next: typeof current) {
current = credential; current = next;
}, },
logout: () => { logout: () => {
current = undefined; current = undefined;
+2 -2
View File
@@ -4,7 +4,7 @@ import type { Route, SlotMap } from "@opencode/plugin/tui/context";
import { testRender, type JSX } from "@opentui/solid"; import { testRender, type JSX } from "@opentui/solid";
import { createSignal } from "solid-js"; import { createSignal } from "solid-js";
import { build } from "../scripts/build.js"; import { build } from "../scripts/build.js";
import type { QuotaStatus } from "../src/quota.js"; import type { QuotaStatus } from "../src/quota/quota.js";
type SidebarSlotRender = (input: { readonly sessionID: string }) => JSX.Element; type SidebarSlotRender = (input: { readonly sessionID: string }) => JSX.Element;
type HomeSlotRender = (input: SlotMap["prompt.footer"]) => JSX.Element; type HomeSlotRender = (input: SlotMap["prompt.footer"]) => JSX.Element;
@@ -27,7 +27,7 @@ const status = (plan: string, remaining: number): QuotaStatus => ({
test("built quota slot stays reactive across pending, empty, failure, update, and session states", async () => { test("built quota slot stays reactive across pending, empty, failure, update, and session states", async () => {
await build(); await build();
// Resolve the built bundle at runtime; tsc runs before build creates dist/tui.js. // Resolve the built bundle at runtime; tsc runs before build creates dist/tui.js.
const tui: typeof import("../src/tui.js") = await import( const tui: typeof import("../src/quota/tui.js") = await import(
new URL("../dist/tui.js", import.meta.url).href new URL("../dist/tui.js", import.meta.url).href
); );
const { default: plugin } = tui; const { default: plugin } = tui;
+4
View File
@@ -9,6 +9,10 @@
"noUncheckedIndexedAccess": true, "noUncheckedIndexedAccess": true,
"exactOptionalPropertyTypes": true, "exactOptionalPropertyTypes": true,
"noFallthroughCasesInSwitch": true, "noFallthroughCasesInSwitch": true,
"noImplicitOverride": true,
"noImplicitReturns": true,
"noPropertyAccessFromIndexSignature": true,
"allowUnreachableCode": false,
"noUnusedLocals": true, "noUnusedLocals": true,
"noUnusedParameters": true, "noUnusedParameters": true,
"verbatimModuleSyntax": true, "verbatimModuleSyntax": true,