From feecf13191f849db2a1aeb8d5f8df09338e267db Mon Sep 17 00:00:00 2001 From: Chris Alexander <41589890+clalexander@users.noreply.github.com> Date: Thu, 3 Sep 2026 09:29:55 -0400 Subject: [PATCH 1/5] ci: modernize ci (#42) * Add plan * Phase 1 * Phase 2 * Phase 2 * Phase 3 * Phase 4 * Phase 5 * Closeout --- .github/dependabot.yml | 52 +- .github/pull_request_template.md | 13 +- .github/scripts/react-support.ts | 184 ++ .../scripts/update-react-major-support.mjs | 176 -- .github/scripts/update-react-major-support.ts | 81 + .github/workflows/ci.yml | 93 +- .github/workflows/dependency-release.yml | 201 +++ .github/workflows/pr-title.yml | 4 +- .github/workflows/react-major-support.yml | 122 +- .github/workflows/release.yml | 162 +- .github/workflows/verify.yml | 171 ++ CONTRIBUTING.md | 51 +- README.md | 2 + docs/README.md | 28 + docs/development/README.md | 38 + docs/development/ci.md | 99 ++ docs/development/release.md | 107 ++ .../plans/flow-stack-ci-modernization-plan.md | 1505 +++++++++++++++++ package.json | 12 +- pnpm-lock.yaml | 106 +- pnpm-workspace.yaml | 18 +- release.config.mjs | 59 +- test/tooling/react-support.test.ts | 134 ++ vitest.config.ts | 6 +- 24 files changed, 2931 insertions(+), 493 deletions(-) create mode 100644 .github/scripts/react-support.ts delete mode 100644 .github/scripts/update-react-major-support.mjs create mode 100644 .github/scripts/update-react-major-support.ts create mode 100644 .github/workflows/dependency-release.yml create mode 100644 .github/workflows/verify.yml create mode 100644 docs/README.md create mode 100644 docs/development/README.md create mode 100644 docs/development/ci.md create mode 100644 docs/development/release.md create mode 100644 docs/plans/flow-stack-ci-modernization-plan.md create mode 100644 test/tooling/react-support.test.ts diff --git a/.github/dependabot.yml b/.github/dependabot.yml index fddfd15..4a8068a 100644 --- a/.github/dependabot.yml +++ b/.github/dependabot.yml @@ -7,9 +7,15 @@ updates: interval: weekly day: monday time: '06:00' - timezone: America/Chicago - open-pull-requests-limit: 10 + timezone: America/New_York + cooldown: + default-days: 3 + semver-major-days: 7 + semver-minor-days: 3 + semver-patch-days: 2 + open-pull-requests-limit: 1 target-branch: dev + # Dependabot scopes dev-only groups as chore(deps-dev), which intentionally does not release. commit-message: prefix: chore include: scope @@ -17,26 +23,11 @@ updates: - dependencies - automated groups: - production-minor-patch-dependencies: - dependency-type: production - update-types: - - minor - - patch - exclude-patterns: - - react - - react-dom - - development-minor-patch-dependencies: - dependency-type: development - update-types: - - minor - - patch - exclude-patterns: - - react - - react-dom - - '@types/react' - - '@types/react-dom' + npm-dependencies: + patterns: + - '*' + # React major upgrades are owned by the React compatibility watcher. ignore: - dependency-name: react update-types: @@ -50,6 +41,17 @@ updates: - dependency-name: '@types/react-dom' update-types: - version-update:semver-major + # Remove once eslint-plugin-react and eslint-plugin-jsx-a11y support ESLint 10. + - dependency-name: '@eslint/js' + versions: + - '>=10.0.0' + - dependency-name: eslint + versions: + - '>=10.0.0' + # Remove once typescript-eslint supports TypeScript >=6.1.0. + - dependency-name: typescript + versions: + - '>=6.1.0' - package-ecosystem: github-actions directory: / @@ -57,8 +59,8 @@ updates: interval: weekly day: monday time: '06:30' - timezone: America/Chicago - open-pull-requests-limit: 10 + timezone: America/New_York + open-pull-requests-limit: 1 target-branch: dev commit-message: prefix: ci @@ -67,3 +69,7 @@ updates: - dependencies - github-actions - automated + groups: + github-actions: + patterns: + - '*' diff --git a/.github/pull_request_template.md b/.github/pull_request_template.md index 1fb9157..d01610b 100644 --- a/.github/pull_request_template.md +++ b/.github/pull_request_template.md @@ -2,6 +2,8 @@ Describe the change clearly and concisely. +> This repository squash merges, so the title above becomes the commit subject and drives release automation. Use a conventional title such as `fix: correct navigation index underflow`. + ## Why This Change Explain the problem being solved or the reason for the change. @@ -52,11 +54,11 @@ If this is breaking, describe the change and required migration steps. What did you do to validate this change? -- [ ] `pnpm run format` -- [ ] `pnpm run lint` -- [ ] `pnpm run typecheck` -- [ ] `pnpm run test` - [ ] `pnpm run build` +- [ ] `pnpm run typecheck` +- [ ] `pnpm test` +- [ ] `pnpm run lint` +- [ ] `pnpm run format:check` Describe any additional manual or automated testing performed. @@ -65,7 +67,8 @@ Describe any additional manual or automated testing performed. - [ ] No documentation update needed - [ ] I updated README and/or docs - [ ] I updated examples -- [ ] I updated changelog/release-related content if needed + +The changelog and package version are generated by release automation. Do not edit them here. ## Related Issues diff --git a/.github/scripts/react-support.ts b/.github/scripts/react-support.ts new file mode 100644 index 0000000..87f031b --- /dev/null +++ b/.github/scripts/react-support.ts @@ -0,0 +1,184 @@ +export interface ReactSupportPackageJson { + peerDependencies?: { + react?: string; + 'react-dom'?: string; + }; +} + +export interface ReactMajorUpdate { + candidateMajor: number; + changed: boolean; + packageJson: TPackageJson; + supportedMajors: string[]; +} + +export interface ReactSupportFileUpdate { + original: string; + path: string; + updated: string; +} + +const peerRangePattern = /^>=(\d+) <(\d+)$/; +const compatibilityPattern = /Requires React and React DOM ([^.]+)\./g; + +function getMajor(version: string): number { + const match = /^(\d+)\./.exec(version); + + if (!match) { + throw new Error(`Could not parse React major from "${version}".`); + } + + return Number.parseInt(match[1], 10); +} + +function parsePeerRange(peerRange: string): { + exclusiveMaximumMajor: number; + minimumMajor: number; +} { + const match = peerRangePattern.exec(peerRange); + + if (!match) { + throw new Error( + `Expected a contiguous React peer range like ">=18 <20", received "${peerRange}".`, + ); + } + + const minimumMajor = Number.parseInt(match[1], 10); + const exclusiveMaximumMajor = Number.parseInt(match[2], 10); + + if (exclusiveMaximumMajor <= minimumMajor) { + throw new Error( + `React peer range "${peerRange}" must include at least one major.`, + ); + } + + return { exclusiveMaximumMajor, minimumMajor }; +} + +function getMajorRange( + minimumMajor: number, + exclusiveMaximumMajor: number, +): string[] { + return Array.from( + { length: exclusiveMaximumMajor - minimumMajor }, + (_, index) => String(minimumMajor + index), + ); +} + +function formatCompatibility(majors: string[]): string { + if (majors.length === 1) { + return majors[0]; + } + + if (majors.length === 2) { + return `${majors[0]} or ${majors[1]}`; + } + + return `${majors.slice(0, -1).join(', ')}, or ${majors[majors.length - 1]}`; +} + +export function getSupportedReactMajors( + reactRange: string, + reactDomRange: string, +): string[] { + if (reactRange !== reactDomRange) { + throw new Error( + `React peer ranges must match: react is "${reactRange}" and react-dom is "${reactDomRange}".`, + ); + } + + const { exclusiveMaximumMajor, minimumMajor } = parsePeerRange(reactRange); + + return getMajorRange(minimumMajor, exclusiveMaximumMajor); +} + +export function createReactMajorUpdate< + TPackageJson extends ReactSupportPackageJson, +>( + packageJson: TPackageJson, + latestVersion: string, +): ReactMajorUpdate { + const reactRange = packageJson.peerDependencies?.react; + const reactDomRange = packageJson.peerDependencies?.['react-dom']; + + if (!reactRange || !reactDomRange) { + throw new Error( + 'package.json must define react and react-dom peer dependencies.', + ); + } + + const supportedMajors = getSupportedReactMajors(reactRange, reactDomRange); + const maximumSupportedMajor = Number.parseInt( + supportedMajors[supportedMajors.length - 1], + 10, + ); + const latestMajor = getMajor(latestVersion); + + if (latestMajor <= maximumSupportedMajor) { + return { + candidateMajor: maximumSupportedMajor, + changed: false, + packageJson, + supportedMajors, + }; + } + + const candidateMajor = maximumSupportedMajor + 1; + const minimumMajor = supportedMajors[0]; + const nextPeerRange = `>=${minimumMajor} <${candidateMajor + 1}`; + const updatedPackageJson = structuredClone(packageJson); + + if (!updatedPackageJson.peerDependencies) { + throw new Error( + 'package.json must define react and react-dom peer dependencies.', + ); + } + + updatedPackageJson.peerDependencies.react = nextPeerRange; + updatedPackageJson.peerDependencies['react-dom'] = nextPeerRange; + + return { + candidateMajor, + changed: true, + packageJson: updatedPackageJson, + supportedMajors: [...supportedMajors, String(candidateMajor)], + }; +} + +export function updateCompatibilityText( + readme: string, + supportedMajors: string[], +): string { + const matches = [...readme.matchAll(compatibilityPattern)]; + + if (matches.length !== 1) { + throw new Error( + `Expected exactly one React compatibility sentence, found ${matches.length}.`, + ); + } + + return readme.replace( + compatibilityPattern, + `Requires React and React DOM ${formatCompatibility(supportedMajors)}.`, + ); +} + +export function writeReactSupportFiles( + updates: ReactSupportFileUpdate[], + writeFile: (path: string, value: string) => void, +): void { + const completedUpdates: ReactSupportFileUpdate[] = []; + + try { + updates.forEach((update) => { + writeFile(update.path, update.updated); + completedUpdates.push(update); + }); + } catch (error) { + completedUpdates.reverse().forEach((update) => { + writeFile(update.path, update.original); + }); + + throw error; + } +} diff --git a/.github/scripts/update-react-major-support.mjs b/.github/scripts/update-react-major-support.mjs deleted file mode 100644 index 2b35842..0000000 --- a/.github/scripts/update-react-major-support.mjs +++ /dev/null @@ -1,176 +0,0 @@ -import { execFileSync } from 'node:child_process'; -import { - appendFileSync, - existsSync, - readFileSync, - writeFileSync, -} from 'node:fs'; - -const packageJsonPath = 'package.json'; -const readmePath = 'README.md'; -const workflowPaths = [ - '.github/workflows/ci.yml', - '.github/workflows/release.yml', -]; - -function setOutput(name, value) { - if (!process.env.GITHUB_OUTPUT) { - return; - } - - appendFileSync(process.env.GITHUB_OUTPUT, `${name}=${value}\n`); -} - -function readJson(path) { - return JSON.parse(readFileSync(path, 'utf8')); -} - -function writeJson(path, value) { - writeFileSync(path, `${JSON.stringify(value, null, 2)}\n`); -} - -function getLatestReactVersion() { - return execFileSync('npm', ['view', 'react', 'version'], { - encoding: 'utf8', - }).trim(); -} - -function getMajor(version) { - const major = Number.parseInt(version.split('.')[0] ?? '', 10); - - if (!Number.isInteger(major)) { - throw new Error(`Could not parse major version from "${version}".`); - } - - return major; -} - -function getMinimumPeerMajor(peerRange) { - const match = peerRange.match(/>=\s*(\d+)/); - - if (!match) { - throw new Error( - `Could not parse minimum React peer major from "${peerRange}".`, - ); - } - - return Number.parseInt(match[1], 10); -} - -function getMaximumSupportedMajor(peerRange) { - const match = peerRange.match(/<\s*(\d+)/); - - if (!match) { - throw new Error( - `Could not parse upper React peer bound from "${peerRange}".`, - ); - } - - return Number.parseInt(match[1], 10) - 1; -} - -function getMajorRange(minimumMajor, maximumMajor) { - return Array.from({ length: maximumMajor - minimumMajor + 1 }, (_, index) => - String(minimumMajor + index), - ); -} - -function formatYamlArray(values) { - return `[${values.map((value) => `'${value}'`).join(', ')}]`; -} - -function formatReadmeCompatibility(values) { - if (values.length === 1) { - return values[0]; - } - - if (values.length === 2) { - return `${values[0]} or ${values[1]}`; - } - - return `${values.slice(0, -1).join(', ')}, or ${values.at(-1)}`; -} - -function updateWorkflowReactMatrix(path, supportedMajors) { - if (!existsSync(path)) { - return; - } - - const original = readFileSync(path, 'utf8'); - const updated = original.replace( - /react:\s*\[[^\]]+\]/g, - `react: ${formatYamlArray(supportedMajors)}`, - ); - - if (updated === original) { - throw new Error(`Could not find an inline React matrix in ${path}.`); - } - - writeFileSync(path, updated); -} - -function updateReadmeCompatibility(path, supportedMajors) { - if (!existsSync(path)) { - return; - } - - const original = readFileSync(path, 'utf8'); - const compatibility = formatReadmeCompatibility(supportedMajors); - const updated = original.replace( - /Requires React and react-dom .+?\./, - `Requires React and react-dom ${compatibility}.`, - ); - - if (updated !== original) { - writeFileSync(path, updated); - } -} - -const packageJson = readJson(packageJsonPath); -const latestReactVersion = getLatestReactVersion(); -const latestReactMajor = getMajor(latestReactVersion); -const currentReactPeerRange = packageJson.peerDependencies?.react; - -if (!currentReactPeerRange) { - throw new Error('package.json is missing peerDependencies.react.'); -} - -const minimumSupportedMajor = getMinimumPeerMajor(currentReactPeerRange); -const maximumSupportedMajor = getMaximumSupportedMajor(currentReactPeerRange); - -setOutput('latest-react-version', latestReactVersion); -setOutput('latest-react-major', String(latestReactMajor)); - -if (latestReactMajor <= maximumSupportedMajor) { - setOutput('changed', 'false'); - setOutput('candidate-react-major', String(maximumSupportedMajor)); - console.log( - `React ${latestReactVersion} is already covered by ${currentReactPeerRange}.`, - ); - process.exit(0); -} - -const candidateReactMajor = maximumSupportedMajor + 1; -const supportedMajors = getMajorRange( - minimumSupportedMajor, - candidateReactMajor, -); -const nextPeerRange = `>=${minimumSupportedMajor} <${candidateReactMajor + 1}`; - -packageJson.peerDependencies.react = nextPeerRange; -packageJson.peerDependencies['react-dom'] = nextPeerRange; - -writeJson(packageJsonPath, packageJson); - -for (const workflowPath of workflowPaths) { - updateWorkflowReactMatrix(workflowPath, supportedMajors); -} - -updateReadmeCompatibility(readmePath, supportedMajors); - -setOutput('changed', 'true'); -setOutput('candidate-react-major', String(candidateReactMajor)); - -console.log( - `Prepared React ${candidateReactMajor} compatibility candidate using latest React ${latestReactVersion}.`, -); diff --git a/.github/scripts/update-react-major-support.ts b/.github/scripts/update-react-major-support.ts new file mode 100644 index 0000000..8e099ce --- /dev/null +++ b/.github/scripts/update-react-major-support.ts @@ -0,0 +1,81 @@ +import { execFileSync } from 'node:child_process'; +import { appendFileSync, readFileSync, writeFileSync } from 'node:fs'; + +import { + createReactMajorUpdate, + type ReactSupportPackageJson, + updateCompatibilityText, + writeReactSupportFiles, +} from './react-support.ts'; + +const packageJsonPath = 'package.json'; +const readmePath = 'README.md'; + +function setOutput(name: string, value: string): void { + if (!process.env.GITHUB_OUTPUT) { + return; + } + + appendFileSync(process.env.GITHUB_OUTPUT, `${name}=${value}\n`); +} + +function getLatestReactVersion(): string { + return execFileSync('npm', ['view', 'react', 'version'], { + encoding: 'utf8', + }).trim(); +} + +function parsePackageJson( + value: string, +): ReactSupportPackageJson & Record { + const parsed: unknown = JSON.parse(value); + + if (typeof parsed !== 'object' || parsed === null || Array.isArray(parsed)) { + throw new Error('package.json must contain a JSON object.'); + } + + return parsed as ReactSupportPackageJson & Record; +} + +const originalPackageJson = readFileSync(packageJsonPath, 'utf8'); +const packageJson = parsePackageJson(originalPackageJson); +const latestReactVersion = getLatestReactVersion(); +const update = createReactMajorUpdate(packageJson, latestReactVersion); + +setOutput('latest-react-version', latestReactVersion); +setOutput('candidate-react-major', String(update.candidateMajor)); +setOutput('changed', String(update.changed)); + +if (!update.changed) { + console.log( + `React ${latestReactVersion} is already covered by ${packageJson.peerDependencies?.react}.`, + ); + process.exit(0); +} + +const originalReadme = readFileSync(readmePath, 'utf8'); +const updatedPackageJson = `${JSON.stringify(update.packageJson, null, 2)}\n`; +const updatedReadme = updateCompatibilityText( + originalReadme, + update.supportedMajors, +); + +writeReactSupportFiles( + [ + { + original: originalPackageJson, + path: packageJsonPath, + updated: updatedPackageJson, + }, + { + original: originalReadme, + path: readmePath, + updated: updatedReadme, + }, + ], + (path, value) => writeFileSync(path, value), +); + +console.log( + `Prepared React ${update.candidateMajor} compatibility candidate using latest React ${latestReactVersion}.`, +); diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 5d14d57..05f71a8 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -13,10 +13,6 @@ on: - dev - 'release/**' - 'hotfix/**' - push: - branches: - - main - permissions: contents: read @@ -25,90 +21,7 @@ concurrency: cancel-in-progress: true jobs: - quality: - name: Quality + verify: + name: Verify if: ${{ github.event_name != 'pull_request' || !github.event.pull_request.draft }} - runs-on: ubuntu-latest - timeout-minutes: 20 - - steps: - - name: Checkout - uses: actions/checkout@v7 - with: - persist-credentials: false - - - name: Enable Corepack - run: corepack enable - - - name: Setup Node.js - uses: actions/setup-node@v7 - with: - node-version: 24 - cache: pnpm - cache-dependency-path: pnpm-lock.yaml - - - name: Install dependencies - run: pnpm install --frozen-lockfile - - - name: Audit dependencies - run: pnpm audit - - - name: Check formatting - run: pnpm run format:check - - - name: Lint - run: pnpm run lint - - compatibility: - name: Compatibility (Node ${{ matrix.node }}, React ${{ matrix.react }}) - if: ${{ github.event_name != 'pull_request' || !github.event.pull_request.draft }} - needs: quality - runs-on: ubuntu-latest - timeout-minutes: 20 - - strategy: - fail-fast: false - matrix: - node: - - '20' - - '22' - - '24' - react: - - '18' - - '19' - - steps: - - name: Checkout - uses: actions/checkout@v7 - with: - persist-credentials: false - - - name: Enable Corepack - run: corepack enable - - - name: Setup Node.js - uses: actions/setup-node@v7 - with: - node-version: ${{ matrix.node }} - cache: pnpm - cache-dependency-path: pnpm-lock.yaml - - - name: Install dependencies - run: pnpm install --frozen-lockfile - - - name: Install React compatibility version - run: > - pnpm add -D --save-exact - react@${{ matrix.react }} - react-dom@${{ matrix.react }} - @types/react@${{ matrix.react }} - @types/react-dom@${{ matrix.react }} - - - name: Typecheck - run: pnpm run typecheck - - - name: Build - run: pnpm run build - - - name: Test - run: pnpm test + uses: ./.github/workflows/verify.yml diff --git a/.github/workflows/dependency-release.yml b/.github/workflows/dependency-release.yml new file mode 100644 index 0000000..638b2d9 --- /dev/null +++ b/.github/workflows/dependency-release.yml @@ -0,0 +1,201 @@ +name: Dependency Release + +# Uses pull_request_target only for merged-event metadata and GitHub API calls. +# It must never check out or execute pull request code. +on: + pull_request_target: + types: + - closed + branches: + - dev + - main + +permissions: + contents: read + +jobs: + create-release-pr: + name: Open dependency release PR + if: >- + ${{ github.event.pull_request.merged == true && + github.event.pull_request.base.ref == 'dev' && + github.event.pull_request.user.login == 'dependabot[bot]' && + github.event.pull_request.head.repo.full_name == github.repository && + (startsWith(github.event.pull_request.head.ref, 'dependabot/npm_and_yarn/dev/npm-dependencies-') || + startsWith(github.event.pull_request.head.ref, 'dependabot/github_actions/dev/github-actions-')) }} + runs-on: ubuntu-latest + timeout-minutes: 10 + permissions: {} + concurrency: + group: dependency-release-branch-release/dependencies-${{ github.event.pull_request.number }} + cancel-in-progress: false + + steps: + - name: Create release automation token + id: app-token + uses: actions/create-github-app-token@v3 + with: + app-id: ${{ vars.RELEASE_AUTOMATION_APP_ID }} + private-key: ${{ secrets.RELEASE_AUTOMATION_PRIVATE_KEY }} + permission-contents: write + permission-pull-requests: write + + - name: Open draft release PR + env: + BRANCH: release/dependencies-${{ github.event.pull_request.number }} + GH_TOKEN: ${{ steps.app-token.outputs.token }} + HEAD_REF: ${{ github.event.pull_request.head.ref }} + MERGE_SHA: ${{ github.event.pull_request.merge_commit_sha }} + REPO: ${{ github.repository }} + SOURCE_PR: ${{ github.event.pull_request.html_url }} + SOURCE_TITLE: ${{ github.event.pull_request.title }} + run: | + set -euo pipefail + + case "$HEAD_REF" in + dependabot/npm_and_yarn/dev/npm-dependencies-*) + ecosystem='npm' + group='npm-dependencies' + ;; + dependabot/github_actions/dev/github-actions-*) + ecosystem='github-actions' + group='github-actions' + ;; + *) + echo "Refusing an unrecognized Dependabot group branch: $HEAD_REF" >&2 + exit 1 + ;; + esac + + # The promotion title mirrors the source scope so release classification is preserved. + case "$ecosystem ${SOURCE_TITLE%%:*}" in + 'npm chore(deps)') + release_title='chore(deps): release dependency updates' + ;; + 'npm chore(deps-dev)') + release_title='chore(deps-dev): release development dependency updates' + ;; + 'github-actions ci(deps)') + release_title='ci(deps): release github actions updates' + ;; + *) + echo "Refusing $HEAD_REF because its title scope is not valid for the $ecosystem group: $SOURCE_TITLE" >&2 + exit 1 + ;; + esac + + if [[ ! "$MERGE_SHA" =~ ^[0-9a-f]{40}$ ]]; then + echo "Refusing to promote without a resolved merge commit." >&2 + exit 1 + fi + + dev_status="$(gh api "repos/$REPO/compare/$MERGE_SHA...dev" --jq '.status')" + if [[ "$dev_status" != 'identical' && "$dev_status" != 'ahead' ]]; then + echo "Refusing to promote $MERGE_SHA because dev does not contain it ($dev_status)." >&2 + exit 1 + fi + + main_status="$(gh api "repos/$REPO/compare/main...$MERGE_SHA" --jq '.status')" + if [[ "$main_status" == 'identical' || "$main_status" == 'behind' ]]; then + echo "main already contains $MERGE_SHA; there is nothing to promote." + exit 0 + fi + + refs="$(gh api "repos/$REPO/git/matching-refs/heads/$BRANCH")" + existing_sha="$(jq -r --arg ref "refs/heads/$BRANCH" \ + '[.[] | select(.ref == $ref)][0].object.sha // empty' <<<"$refs")" + if [[ -n "$existing_sha" && "$existing_sha" != "$MERGE_SHA" ]]; then + echo "Refusing to reuse $BRANCH because it points at $existing_sha instead of $MERGE_SHA." >&2 + exit 1 + fi + + owner="${REPO%%/*}" + matching_prs="$(gh api \ + --method GET \ + "repos/$REPO/pulls" \ + -f state=open \ + -f base=main \ + -f head="$owner:$BRANCH")" + valid_pr_count="$(jq \ + --arg repo "$REPO" \ + --arg branch "$BRANCH" \ + --arg sha "$MERGE_SHA" \ + '[.[] | select(.head.repo.full_name == $repo and .head.ref == $branch and .head.sha == $sha)] | length' \ + <<<"$matching_prs")" + if [[ "$valid_pr_count" -gt 0 ]]; then + echo "A promotion PR for $BRANCH at $MERGE_SHA already exists." + exit 0 + fi + + if [[ -z "$existing_sha" ]]; then + gh api \ + --method POST \ + "repos/$REPO/git/refs" \ + -f ref="refs/heads/$BRANCH" \ + -f sha="$MERGE_SHA" \ + >/dev/null + fi + + pr_url="$(gh pr create \ + --repo "$REPO" \ + --base main \ + --head "$BRANCH" \ + --draft \ + --title "$release_title" \ + --body "Promotes \`dev\` at \`$MERGE_SHA\`, the fixed snapshot taken when the \`$ecosystem\` \`$group\` updates in $SOURCE_PR merged. + + This snapshot contains every commit on \`dev\` at that point, not only the dependency updates, and it does not follow later \`dev\` commits. Review the full diff, then mark it ready for review and merge it to release.")" + echo "Created $ecosystem promotion PR $pr_url from $BRANCH at $MERGE_SHA to main." + + delete-release-branch: + name: Delete merged dependency release branch + if: >- + ${{ github.event.pull_request.merged == true && + github.event.pull_request.base.ref == 'main' && + github.event.pull_request.head.repo.full_name == github.repository && + startsWith(github.event.pull_request.head.ref, 'release/dependencies-') }} + runs-on: ubuntu-latest + timeout-minutes: 5 + permissions: {} + concurrency: + group: dependency-release-branch-${{ github.event.pull_request.head.ref }} + cancel-in-progress: false + + steps: + - name: Create release automation token + id: app-token + uses: actions/create-github-app-token@v3 + with: + app-id: ${{ vars.RELEASE_AUTOMATION_APP_ID }} + private-key: ${{ secrets.RELEASE_AUTOMATION_PRIVATE_KEY }} + permission-contents: write + + - name: Delete release branch + env: + BRANCH: ${{ github.event.pull_request.head.ref }} + GH_TOKEN: ${{ steps.app-token.outputs.token }} + HEAD_SHA: ${{ github.event.pull_request.head.sha }} + REPO: ${{ github.repository }} + run: | + set -euo pipefail + + if [[ ! "$BRANCH" =~ ^release/dependencies-[0-9]+$ ]]; then + echo "Refusing to delete an unexpected branch: $BRANCH" >&2 + exit 1 + fi + + refs="$(gh api "repos/$REPO/git/matching-refs/heads/$BRANCH")" + current_sha="$(jq -r --arg ref "refs/heads/$BRANCH" \ + '[.[] | select(.ref == $ref)][0].object.sha // empty' <<<"$refs")" + if [[ -z "$current_sha" ]]; then + echo "Branch $BRANCH is already deleted." + exit 0 + fi + + if [[ "$current_sha" != "$HEAD_SHA" ]]; then + echo "Refusing to delete $BRANCH because it moved from $HEAD_SHA to $current_sha." >&2 + exit 1 + fi + + gh api --method DELETE "repos/$REPO/git/refs/heads/$BRANCH" + echo "Deleted $BRANCH at $HEAD_SHA after its promotion PR merged." diff --git a/.github/workflows/pr-title.yml b/.github/workflows/pr-title.yml index 18b97a3..8346f44 100644 --- a/.github/workflows/pr-title.yml +++ b/.github/workflows/pr-title.yml @@ -1,7 +1,7 @@ name: PR Title on: - pull_request_target: + pull_request: types: - opened - reopened @@ -29,7 +29,7 @@ jobs: pull-requests: read steps: - name: Validate pull request title - uses: amannn/action-semantic-pull-request@v6.1.1 + uses: amannn/action-semantic-pull-request@v6 env: GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} with: diff --git a/.github/workflows/react-major-support.yml b/.github/workflows/react-major-support.yml index dc87a17..00c89e0 100644 --- a/.github/workflows/react-major-support.yml +++ b/.github/workflows/react-major-support.yml @@ -6,8 +6,7 @@ on: - cron: '0 12 1 * *' permissions: - contents: write - pull-requests: write + contents: read concurrency: group: react-major-support-watch @@ -25,6 +24,7 @@ jobs: with: ref: dev fetch-depth: 0 + persist-credentials: false - name: Setup Node.js uses: actions/setup-node@v7 @@ -33,64 +33,114 @@ jobs: - name: Update React compatibility files id: update - run: node .github/scripts/update-react-major-support.mjs + run: node .github/scripts/update-react-major-support.ts - name: Stop if no newer React major exists if: ${{ steps.update.outputs.changed != 'true' }} run: echo "No newer React major support candidate found." - - name: Configure Git User + - name: Create release automation token + id: app-token if: ${{ steps.update.outputs.changed == 'true' }} - run: | - git config --global user.name "github-actions[bot]" - git config --global user.email "41898282+github-actions[bot]@users.noreply.github.com" + uses: actions/create-github-app-token@v3 + with: + app-id: ${{ vars.RELEASE_AUTOMATION_APP_ID }} + private-key: ${{ secrets.RELEASE_AUTOMATION_PRIVATE_KEY }} + permission-contents: write + permission-pull-requests: write - - name: Commit and push branch + - name: Create compatibility branch and pull request if: ${{ steps.update.outputs.changed == 'true' }} env: + APP_SLUG: ${{ steps.app-token.outputs.app-slug }} BRANCH: automation/react-${{ steps.update.outputs.candidate-react-major }}-compatibility CANDIDATE_REACT_MAJOR: ${{ steps.update.outputs.candidate-react-major }} + GH_TOKEN: ${{ steps.app-token.outputs.token }} + LATEST_REACT_VERSION: ${{ steps.update.outputs.latest-react-version }} + REPO: ${{ github.repository }} run: | set -euo pipefail - git checkout -B "$BRANCH" - git add package.json README.md .github/workflows/ci.yml .github/workflows/release.yml + if [[ ! "$CANDIDATE_REACT_MAJOR" =~ ^[0-9]+$ ]]; then + echo "Refusing an invalid React major: $CANDIDATE_REACT_MAJOR" >&2 + exit 1 + fi - if git diff --cached --quiet; then - echo "No changes to commit." - exit 0 + base_sha="$(git rev-parse HEAD)" + remote_dev_sha="$(gh api "repos/$REPO/git/ref/heads/dev" --jq '.object.sha')" + if [[ "$base_sha" != "$remote_dev_sha" ]]; then + echo "Refusing to create $BRANCH because dev moved from $base_sha to $remote_dev_sha." >&2 + exit 1 fi - git commit -m "feat(react): add React ${CANDIDATE_REACT_MAJOR} compatibility candidate" - git push --force-with-lease origin "$BRANCH" + git switch --create "$BRANCH" "$base_sha" + git add package.json README.md + if git diff --cached --quiet; then + echo "The updater reported a change but produced no staged compatibility files." >&2 + exit 1 + fi - - name: Open pull request - if: ${{ steps.update.outputs.changed == 'true' }} - env: - GH_TOKEN: ${{ secrets.GITHUB_TOKEN }} - REPO: ${{ github.repository }} - BRANCH: automation/react-${{ steps.update.outputs.candidate-react-major }}-compatibility - CANDIDATE_REACT_MAJOR: ${{ steps.update.outputs.candidate-react-major }} - LATEST_REACT_VERSION: ${{ steps.update.outputs.latest-react-version }} - run: | - set -euo pipefail + git \ + -c user.name="${APP_SLUG}[bot]" \ + -c user.email="${APP_SLUG}[bot]@users.noreply.github.com" \ + commit -m "feat(react): add React ${CANDIDATE_REACT_MAJOR} compatibility candidate" + + generated_sha="$(git rev-parse HEAD)" + generated_tree="$(git rev-parse HEAD^{tree})" + refs="$(gh api "repos/$REPO/git/matching-refs/heads/$BRANCH")" + existing_sha="$(jq -r --arg ref "refs/heads/$BRANCH" \ + '[.[] | select(.ref == $ref)][0].object.sha // empty' <<<"$refs")" + + if [[ -n "$existing_sha" ]]; then + existing_commit="$(gh api "repos/$REPO/git/commits/$existing_sha")" + existing_parent="$(jq -r '.parents[0].sha // empty' <<<"$existing_commit")" + existing_tree="$(jq -r '.tree.sha' <<<"$existing_commit")" + if [[ "$existing_parent" != "$base_sha" || "$existing_tree" != "$generated_tree" ]]; then + echo "Refusing to overwrite $BRANCH at unexpected commit $existing_sha." >&2 + exit 1 + fi + branch_sha="$existing_sha" + else + gh api \ + --method POST \ + "repos/$REPO/git/refs" \ + -f ref="refs/heads/$BRANCH" \ + -f sha="$base_sha" \ + >/dev/null + + git_auth="$(printf 'x-access-token:%s' "$GH_TOKEN" | base64 -w 0)" + echo "::add-mask::$git_auth" + export GIT_CONFIG_COUNT=1 + export GIT_CONFIG_KEY_0=http.https://github.com/.extraheader + export GIT_CONFIG_VALUE_0="AUTHORIZATION: basic $git_auth" + git push origin "HEAD:refs/heads/$BRANCH" + branch_sha="$generated_sha" + fi - if gh pr list \ - --repo "$REPO" \ - --base dev \ - --head "$BRANCH" \ - --state open \ - --json number \ - --jq 'length > 0' | grep -q true; then - echo "A React ${CANDIDATE_REACT_MAJOR} compatibility PR already exists." + owner="${REPO%%/*}" + matching_prs="$(gh api \ + --method GET \ + "repos/$REPO/pulls" \ + -f state=open \ + -f base=dev \ + -f head="$owner:$BRANCH")" + valid_pr_count="$(jq \ + --arg repo "$REPO" \ + --arg branch "$BRANCH" \ + --arg sha "$branch_sha" \ + '[.[] | select(.head.repo.full_name == $repo and .head.ref == $branch and .head.sha == $sha)] | length' \ + <<<"$matching_prs")" + if [[ "$valid_pr_count" -gt 0 ]]; then + echo "React compatibility PR already exists for $BRANCH at $branch_sha." exit 0 fi - gh pr create \ + pr_url="$(gh pr create \ --repo "$REPO" \ --base dev \ --head "$BRANCH" \ --title "feat(react): add React ${CANDIDATE_REACT_MAJOR} compatibility candidate" \ - --body "React ${LATEST_REACT_VERSION} is available on npm. This PR updates Flow Stack's peer dependency range and compatibility matrix to evaluate React ${CANDIDATE_REACT_MAJOR} support. + --body "React ${LATEST_REACT_VERSION} is available on npm. This PR updates Flow Stack's peer dependency range and compatibility documentation to evaluate React ${CANDIDATE_REACT_MAJOR} support. - Merge this only after the compatibility matrix passes and the public API/runtime behavior is verified." + Merge this only after the compatibility matrix passes and the public API/runtime behavior is verified.")" + echo "Created React compatibility PR $pr_url from $BRANCH at $branch_sha to dev." diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml index e548b46..12a0f6c 100644 --- a/.github/workflows/release.yml +++ b/.github/workflows/release.yml @@ -5,6 +5,12 @@ on: branches: - main workflow_dispatch: + inputs: + dry-run: + description: Evaluate the next release without publishing or repository mutation + required: true + default: true + type: boolean permissions: contents: read @@ -14,22 +20,29 @@ concurrency: cancel-in-progress: false jobs: - compatibility: - name: Compatibility (React ${{ matrix.react }}) + verify: + name: Verify + uses: ./.github/workflows/verify.yml + + release: + name: Release + if: >- + ${{ github.event_name == 'push' || + (!inputs.dry-run && github.ref == 'refs/heads/main') }} + needs: verify runs-on: ubuntu-latest - timeout-minutes: 20 + timeout-minutes: 30 + environment: npm - strategy: - fail-fast: false - matrix: - react: - - '18' - - '19' + permissions: + contents: read + id-token: write steps: - name: Checkout uses: actions/checkout@v7 with: + fetch-depth: 0 persist-credentials: false - name: Enable Corepack @@ -45,49 +58,56 @@ jobs: - name: Install dependencies run: pnpm install --frozen-lockfile - - name: Verify dependency signatures - run: pnpm audit - - - name: Install React compatibility version - run: > - pnpm add -D --save-exact - react@${{ matrix.react }} - react-dom@${{ matrix.react }} - @types/react@${{ matrix.react }} - @types/react-dom@${{ matrix.react }} - - - name: Check formatting - run: pnpm run format:check + - name: Build + run: pnpm run build - - name: Lint - run: pnpm run lint + - name: Create release automation token + id: app-token + uses: actions/create-github-app-token@v3 + with: + app-id: ${{ vars.RELEASE_AUTOMATION_APP_ID }} + private-key: ${{ secrets.RELEASE_AUTOMATION_PRIVATE_KEY }} + permission-contents: write + permission-issues: write + permission-pull-requests: write - - name: Typecheck - run: pnpm run typecheck + - name: Release + env: + GH_TOKEN: ${{ steps.app-token.outputs.token }} + GITHUB_TOKEN: ${{ steps.app-token.outputs.token }} + GIT_AUTHOR_NAME: ${{ steps.app-token.outputs.app-slug }}[bot] + GIT_AUTHOR_EMAIL: ${{ steps.app-token.outputs.app-slug }}[bot]@users.noreply.github.com + GIT_COMMITTER_NAME: ${{ steps.app-token.outputs.app-slug }}[bot] + GIT_COMMITTER_EMAIL: ${{ steps.app-token.outputs.app-slug }}[bot]@users.noreply.github.com + run: | + set -euo pipefail - - name: Test - run: pnpm test + git_auth="$(printf 'x-access-token:%s' "$GH_TOKEN" | base64 -w 0)" + echo "::add-mask::$git_auth" + export GIT_CONFIG_COUNT=1 + export GIT_CONFIG_KEY_0=http.https://github.com/.extraheader + export GIT_CONFIG_VALUE_0="AUTHORIZATION: basic $git_auth" - - name: Build - run: pnpm run build + pnpm exec semantic-release - release: - name: Release - needs: compatibility + release-dry-run: + name: Release dry run + if: >- + ${{ github.event_name == 'workflow_dispatch' && + inputs.dry-run && github.ref == 'refs/heads/main' }} + needs: verify runs-on: ubuntu-latest - timeout-minutes: 30 + timeout-minutes: 15 permissions: - contents: write - issues: write - pull-requests: write - id-token: write + contents: read steps: - name: Checkout uses: actions/checkout@v7 with: fetch-depth: 0 + persist-credentials: false - name: Enable Corepack run: corepack enable @@ -102,25 +122,19 @@ jobs: - name: Install dependencies run: pnpm install --frozen-lockfile - - name: Verify dependency signatures - run: pnpm audit - - - name: Build - run: pnpm run build - - - name: Configure Git User + - name: Evaluate release without mutation + env: + RELEASE_ANALYSIS_ONLY: 'true' run: | - git config --global user.name "github-actions[bot]" - git config --global user.email "41898282+github-actions[bot]@users.noreply.github.com" + set -euo pipefail - - name: Release - env: - GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} - GIT_AUTHOR_NAME: github-actions[bot] - GIT_AUTHOR_EMAIL: 41898282+github-actions[bot]@users.noreply.github.com - GIT_COMMITTER_NAME: github-actions[bot] - GIT_COMMITTER_EMAIL: 41898282+github-actions[bot]@users.noreply.github.com - run: pnpm exec semantic-release + dry_run_remote="$RUNNER_TEMP/flow-stack-release-dry-run.git" + git clone --bare . "$dry_run_remote" + + pnpm exec semantic-release \ + --dry-run \ + --no-ci \ + --repository-url "file://$dry_run_remote" sync-main-into-dev: name: Open sync PR to dev @@ -130,31 +144,49 @@ jobs: timeout-minutes: 10 permissions: - pull-requests: write + contents: read steps: + - name: Create release automation token + id: app-token + uses: actions/create-github-app-token@v3 + with: + app-id: ${{ vars.RELEASE_AUTOMATION_APP_ID }} + private-key: ${{ secrets.RELEASE_AUTOMATION_PRIVATE_KEY }} + permission-contents: read + permission-pull-requests: write + - name: Open back-merge PR env: - GH_TOKEN: ${{ secrets.GITHUB_TOKEN }} + GH_TOKEN: ${{ steps.app-token.outputs.token }} REPO: ${{ github.repository }} run: | set -euo pipefail - if gh pr list \ + owner="${REPO%%/*}" + main_sha="$(gh api "repos/$REPO/git/ref/heads/main" --jq '.object.sha')" + ahead_by="$(gh api "repos/$REPO/compare/dev...main" --jq '.ahead_by')" + if [[ "$ahead_by" -eq 0 ]]; then + echo "No commits need to be synchronized from main at $main_sha into dev." + exit 0 + fi + + matching_prs="$(gh pr list \ --repo "$REPO" \ --base dev \ - --head main \ + --head "$owner:main" \ --state open \ - --json number \ - --jq 'length > 0' | grep -q true; then - echo "A sync PR from main to dev already exists." + --json headRefOid,headRepository,number \ + --jq "[.[] | select(.headRepository.nameWithOwner == \"$REPO\" and .headRefOid == \"$main_sha\")]")" + if [[ "$(jq 'length' <<<"$matching_prs")" -gt 0 ]]; then + echo "A sync PR from main at $main_sha to dev already exists." exit 0 fi - gh pr create \ + pr_url="$(gh pr create \ --repo "$REPO" \ --base dev \ --head main \ --title "chore: sync main into dev" \ - --body "Automated post-release sync PR from \`main\` into \`dev\`." \ - || echo "No sync PR created. This usually means there are no changes to merge." + --body "Automated post-release sync PR from \`main\` at \`$main_sha\` into \`dev\`.")" + echo "Created sync PR $pr_url from main at $main_sha to dev." diff --git a/.github/workflows/verify.yml b/.github/workflows/verify.yml new file mode 100644 index 0000000..26f1511 --- /dev/null +++ b/.github/workflows/verify.yml @@ -0,0 +1,171 @@ +name: Verify + +on: + workflow_call: + +permissions: + contents: read + +jobs: + prepare: + name: Prepare compatibility matrix + runs-on: ubuntu-latest + timeout-minutes: 5 + outputs: + react: ${{ steps.react.outputs.matrix }} + + steps: + - name: Checkout + uses: actions/checkout@v7 + with: + persist-credentials: false + + - name: Setup Node.js + uses: actions/setup-node@v7 + with: + node-version: 24 + + - name: Prepare React matrix + id: react + run: | + matrix="$(node --input-type=module -e " + import { readFileSync } from 'node:fs'; + import { getSupportedReactMajors } from './.github/scripts/react-support.ts'; + + const packageJson = JSON.parse(readFileSync('package.json', 'utf8')); + const majors = getSupportedReactMajors( + packageJson.peerDependencies.react, + packageJson.peerDependencies['react-dom'], + ); + + process.stdout.write(JSON.stringify(majors)); + ")" + echo "matrix=$matrix" >> "$GITHUB_OUTPUT" + + quality: + name: Quality + runs-on: ubuntu-latest + timeout-minutes: 20 + + steps: + - name: Checkout + uses: actions/checkout@v7 + with: + persist-credentials: false + + - name: Enable Corepack + run: corepack enable + + - name: Setup Node.js + uses: actions/setup-node@v7 + with: + node-version: 24 + cache: pnpm + cache-dependency-path: pnpm-lock.yaml + + - name: Install dependencies + run: pnpm install --frozen-lockfile + + - name: Audit dependency vulnerabilities + run: pnpm audit + + - name: Verify dependency signatures + run: npm audit signatures + + - name: Check formatting + run: pnpm run format:check + + - name: Lint + run: pnpm run lint + + compatibility: + name: Compatibility (Node ${{ matrix.node }}, React ${{ matrix.react }}) + needs: + - prepare + - quality + runs-on: ubuntu-latest + timeout-minutes: 20 + + strategy: + fail-fast: false + matrix: + node: + - '20' + - '22' + - '24' + react: ${{ fromJSON(needs.prepare.outputs.react) }} + + steps: + - name: Checkout + uses: actions/checkout@v7 + with: + persist-credentials: false + + - name: Enable Corepack + run: corepack enable + + - name: Setup Node.js + uses: actions/setup-node@v7 + with: + node-version: ${{ matrix.node }} + cache: pnpm + cache-dependency-path: pnpm-lock.yaml + + - name: Install dependencies + run: pnpm install --frozen-lockfile + + - name: Install React compatibility version + run: > + pnpm add --workspace-root -D --save-exact + react@${{ matrix.react }} + react-dom@${{ matrix.react }} + @types/react@${{ matrix.react }} + @types/react-dom@${{ matrix.react }} + + - name: Typecheck + run: pnpm run typecheck + + - name: Build + run: pnpm run build + + - name: Test + run: pnpm test + + - name: Verify compatibility changes are ephemeral + if: ${{ always() }} + run: | + unexpected="$(git diff --name-only -- . ':(exclude)package.json' ':(exclude)pnpm-lock.yaml')" + if [[ -n "$unexpected" ]]; then + echo "Compatibility checks changed unexpected files:" >&2 + echo "$unexpected" >&2 + exit 1 + fi + + verification: + name: Verification + if: ${{ always() }} + needs: + - prepare + - quality + - compatibility + runs-on: ubuntu-latest + timeout-minutes: 5 + + steps: + - name: Require successful verification jobs + env: + PREPARE_RESULT: ${{ needs.prepare.result }} + QUALITY_RESULT: ${{ needs.quality.result }} + COMPATIBILITY_RESULT: ${{ needs.compatibility.result }} + run: | + failed=0 + for result in \ + "prepare=$PREPARE_RESULT" \ + "quality=$QUALITY_RESULT" \ + "compatibility=$COMPATIBILITY_RESULT"; do + if [[ "${result#*=}" != "success" ]]; then + echo "Required job did not succeed: $result" >&2 + failed=1 + fi + done + exit "$failed" diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md index 5f26ffc..94604b9 100644 --- a/CONTRIBUTING.md +++ b/CONTRIBUTING.md @@ -63,11 +63,11 @@ Typical commands: ```bash corepack enable pnpm install -pnpm run format -pnpm run lint -pnpm run typecheck -pnpm run test pnpm run build +pnpm run typecheck +pnpm test +pnpm run lint +pnpm run format:check ``` ## Repository Conventions @@ -88,13 +88,18 @@ We separate formatting from linting: - Prettier handles formatting. - ESLint handles code quality and rule-based issues. -Before opening a pull request, run: +Before opening a pull request, run the reporting commands, which are the same ones continuous integration runs: ```bash -pnpm run format pnpm run lint -pnpm run typecheck -pnpm run test +pnpm run format:check +``` + +To apply fixes instead of reporting them: + +```bash +pnpm run lint:fix +pnpm run format ``` ## Tests @@ -116,9 +121,11 @@ When fixing a bug, prefer adding a test that fails before the fix and passes aft Please update documentation when relevant. This includes: - `README.md` +- project documentation under [`docs/`](./docs/README.md) - API documentation - examples -- migration or release notes for notable behavior changes + +Release notes are generated from commit subjects, so no manual changelog entry is needed. A contribution is not complete if users would need new behavior explained and the documentation was left behind. @@ -134,6 +141,7 @@ A contribution is not complete if users would need new behavior explained and th A good pull request should: +- use a conventional title, because it becomes the squashed commit subject - explain what changed - explain why it changed - reference any related issue @@ -144,24 +152,29 @@ Please keep pull requests reviewable. If a change is large, break it into smalle ## Commit Guidance -Write commit messages that are clear and descriptive. A commit should communicate intent, not just activity. +This repository squash merges pull requests, so the pull request title becomes the commit subject on the target branch. Release automation reads those subjects, which makes the title part of the change rather than a label. + +Use [Conventional Commits](https://www.conventionalcommits.org/). A title is `type(optional scope): subject`, where the subject starts with a lowercase letter. Good examples: -- `Add stack transition state guards` -- `Fix navigation index underflow` -- `Document controlled container usage` +- `feat: add stack transition state guards` +- `fix: correct navigation index underflow` +- `docs: document controlled container usage` + +Allowed types are `build`, `chore`, `ci`, `docs`, `feat`, `fix`, `perf`, `refactor`, and `test`. A pull request title is validated automatically. + +Which types publish a release is documented in [release operations](./docs/development/release.md). In short, `feat` produces a minor release, `fix` and `perf` produce a patch, a `BREAKING CHANGE:` footer produces a major, and most other types publish nothing. ## Release Expectations -Releases are cut from `main`, with work integrated through `dev` first. Release branches should focus on release preparation only, such as: +Releases are automated. When a change merges to `main`, semantic-release determines the version from commit subjects, publishes to npm, writes `CHANGELOG.md`, updates the version in `package.json`, tags the commit, and creates the GitHub release. + +Because those artifacts are generated, do not edit the package version or changelog by hand in a pull request. -- version updates -- changelog updates -- final documentation adjustments -- release validation +Work still integrates through `dev` before reaching `main`, and release branches should carry only release preparation and validation. Avoid mixing new feature work into a release branch. -Avoid mixing new feature work into a release branch. +The full release path, including prerequisites, recovery, and rollback, is documented in [release operations](./docs/development/release.md). ## Hotfix Process diff --git a/README.md b/README.md index 57dcd9d..558e76f 100644 --- a/README.md +++ b/README.md @@ -97,6 +97,8 @@ Examples coming soon. In the meantime, see the [Quick start](#quick-start) above Deeper documentation (transitions, controlled mode, accessibility, headless controller) is in progress. Questions and requests are welcome on the [GitHub issues page](https://github.com/clalexander/flow-stack/issues). +Contributor and maintainer documentation lives in [`docs/`](./docs/README.md). + ## API summary **Components** diff --git a/docs/README.md b/docs/README.md new file mode 100644 index 0000000..2e1e777 --- /dev/null +++ b/docs/README.md @@ -0,0 +1,28 @@ +# Flow Stack Documentation + +This is the canonical documentation for the Flow Stack repository. It is written for maintainers and for AI agents working in this codebase. + +## Start Here + +- [Development](./development/README.md) +- [Continuous integration](./development/ci.md) +- [Release operations](./development/release.md) +- [CI modernization plan](./plans/flow-stack-ci-modernization-plan.md) + +Consumer-facing usage and the public API live in the root [README](../README.md). The contribution workflow lives in [CONTRIBUTING](../CONTRIBUTING.md). + +## For Agents + +Before making a non-trivial change: + +1. Read this index. +2. Read the relevant document under `development/`. +3. Inspect the workflows, `package.json`, and `release.config.mjs` to confirm current behavior. +4. Treat documentation as design intent and code as implementation truth. If they conflict, report the discrepancy instead of silently changing behavior. + +## Documentation Areas + +- `development/`: verification, dependency automation, and release operations. +- `plans/`: historical records of completed plans, kept for context rather than as current instructions. + +Other areas are added only when they carry real content. diff --git a/docs/development/README.md b/docs/development/README.md new file mode 100644 index 0000000..ac62ccc --- /dev/null +++ b/docs/development/README.md @@ -0,0 +1,38 @@ +# Development + +Operational documentation for building, verifying, and releasing Flow Stack. + +## Contents + +- [Continuous integration](./ci.md): workflow topology, the required checks, the compatibility matrix, supply-chain audits, and dependency automation. +- [Release operations](./release.md): release classification, prerequisites, the release path, recovery, and rollback. +- [CI modernization plan](../plans/flow-stack-ci-modernization-plan.md): the initiative record describing why the current automation exists. + +## Toolchain + +- Node: `engines.node` is `>=20.19.0`, and continuous integration verifies Node 20, 22, and 24. +- pnpm: pinned by `packageManager`. Use `corepack enable` rather than installing pnpm globally. +- `pnpm-lock.yaml` is the authoritative lockfile. An ignored `package-lock.json` may exist locally and is not used. + +## Local Quality Gates + +Run the same checks continuous integration runs, in gate order: + +```powershell +pnpm run build +pnpm run typecheck +pnpm test +pnpm run lint +pnpm run format:check +``` + +To apply fixes rather than report them: + +```powershell +pnpm run lint:fix +pnpm run format +``` + +## Dependency Updates + +`pnpm-workspace.yaml` holds compatibility pins through `updateConfig.ignoreDependencies`. That list suppresses packages only during a bare `pnpm update`; naming a package explicitly, such as `pnpm update react`, still updates it. React majors are owned by the React compatibility watcher described in [ci.md](./ci.md). diff --git a/docs/development/ci.md b/docs/development/ci.md new file mode 100644 index 0000000..f8d1ba9 --- /dev/null +++ b/docs/development/ci.md @@ -0,0 +1,99 @@ +# Continuous Integration + +Flow Stack has one authoritative verification contract. Pull requests and releases both call the same reusable workflow, so the commit that publishes to npm passes exactly the checks a reviewer saw. + +## Workflow Topology + +| Workflow | Trigger | Purpose | +| ------------------------- | ------------------------------------------------------------------------------ | ------------------------------------------------------------------ | +| `ci.yml` | Pull requests to `main`, `dev`, `release/**`, `hotfix/**`, and manual dispatch | Thin caller that runs verification for unprivileged changes | +| `verify.yml` | `workflow_call` only | Owns all quality and compatibility checks | +| `release.yml` | Push to `main`, and manual dispatch | Verifies, then publishes or performs an analysis-only dry run | +| `pr-title.yml` | `pull_request` | Validates conventional pull request titles | +| `react-major-support.yml` | Monthly schedule and manual dispatch | Proposes support for a new React major | +| `dependency-release.yml` | `pull_request_target` on closed pull requests | Promotes merged Dependabot groups and cleans up promotion branches | + +`ci.yml` skips draft pull requests. Marking a draft ready for review starts verification. + +## The Verification Contract + +`verify.yml` runs three working jobs and one aggregate: + +1. **Prepare compatibility matrix** derives the supported React majors from package metadata. +2. **Quality** installs with a frozen lockfile, audits dependencies, then checks formatting and lint. +3. **Compatibility** runs typecheck, build, and tests across every supported Node and React combination with `fail-fast: false`. +4. **Verification** is the stable aggregate. It runs with `if: always()` and succeeds only when every upstream job succeeded, so a failed, cancelled, or unexpectedly skipped job fails the check. + +`Verification` is a naming contract with branch protection. Renaming that job breaks required status checks. + +Verification has read-only repository permission, receives no secrets, and never mutates remote state. + +## Required Checks + +Branch rulesets for `main` and `dev` require: + +- `Verification` +- `Validate PR title` + +GitHub only offers checks that have reported recently. If either is missing when configuring a ruleset, run the workflows on a pull request first. + +## Compatibility Sources + +React support is declared once, in `peerDependencies.react` in `package.json`. `react-dom` must carry the same range. The matrix job parses that range, so the supported majors are never duplicated in workflow YAML. + +Node majors are explicit in the compatibility matrix because a minimum version in `engines.node` does not imply which majors to test. + +The React compatibility watcher checks npm monthly for a newer React major. When one exists, it updates `peerDependencies` and the README compatibility sentence, then opens a pull request to `dev`. It never edits workflow YAML and never changes `devDependencies`, so local development stays on the current baseline while the matrix exercises the candidate. + +## Supply-Chain Audits + +Quality runs two distinct, fail-closed controls: + +- `pnpm audit` reports known vulnerability advisories. +- `npm audit signatures` verifies registry signatures and attestations. + +These are separate concerns. Do not merge them or rename one to describe the other. + +Transitive advisories that have no direct upgrade path are pinned through `overrides` in `pnpm-workspace.yaml`. + +## Dependency Automation + +Dependabot targets `dev` and produces at most two routine pull requests: + +| Ecosystem | Group | Title scope | Open PR limit | +| ---------------- | ------------------ | ---------------------------------- | ------------- | +| npm | `npm-dependencies` | `chore(deps)` or `chore(deps-dev)` | 1 | +| `github-actions` | `github-actions` | `ci(deps)` | 1 | + +The npm group keeps Dependabot's own scope. A group containing a production dependency is `chore(deps)` and releases a patch; a development-only group is `chore(deps-dev)` and intentionally releases nothing. + +Compatibility holds live in two places and mean different things: + +- `.github/dependabot.yml` ignores React majors and specific unsupported version ranges. These entries support version bounds. +- `pnpm-workspace.yaml` lists package names under `updateConfig.ignoreDependencies`. These entries have no version granularity and apply only to a bare `pnpm update`. + +Dependabot reads `.github/dependabot.yml` from the default branch. Changes to grouping take effect only after they land there. + +### Promotion To `main` + +Merging either grouped pull request into `dev` triggers `dependency-release.yml`, which: + +1. verifies the merge commit is contained in `dev` and not already contained in `main`; +2. creates `release/dependencies-` at that exact merge commit; +3. opens a draft pull request to `main` whose title mirrors the source scope. + +The promotion branch is a fixed snapshot of `dev` at the merge commit. It contains every commit on `dev` at that point, not only the dependency updates, so review the full diff. + +An existing branch at an unexpected commit is a hard failure rather than an overwrite. After the promotion pull request merges, the branch is deleted only when its name matches `release/dependencies-` and its commit still equals the merged head. + +Security updates that GitHub cannot fold into a group use per-dependency branches. Those are intentionally not promoted automatically and require a manual promotion pull request. + +## Generated Pull Request Identity + +Automated pull requests are created with a GitHub App installation token, not the default workflow token, so they trigger normal checks. Tokens are minted immediately before the step that needs them and are never persisted by checkout. + +`dependency-release.yml` uses `pull_request_target` because it needs merged-event metadata. It never checks out or executes pull request code, and every untrusted event value is passed through the environment rather than interpolated into a shell command. + +## Local Equivalents + +Verification mirrors commands available locally. See [the development guide](./README.md) for the gate order and the fix commands. diff --git a/docs/development/release.md b/docs/development/release.md new file mode 100644 index 0000000..9fb641f --- /dev/null +++ b/docs/development/release.md @@ -0,0 +1,107 @@ +# Release Operations + +Flow Stack publishes to public npm with semantic-release. Versioning, changelog entries, tags, and GitHub releases are generated. Do not edit the version in `package.json` or write `CHANGELOG.md` entries by hand. + +## Release Model + +Releases run from `main`. Work integrates through `dev` first. + +Because pull requests are squash merged, the pull request title becomes the commit subject on `main`, and that subject determines the release. A careless title changes what ships. + +## Release Classification + +| Commit subject | Result | +| ------------------------------------------- | ------------- | +| `feat: ...` | minor release | +| `fix: ...` or `perf: ...` | patch release | +| `chore(deps): ...` | patch release | +| `chore(deps-dev): ...` | no release | +| `ci: ...` or `test: ...` | no release | +| `chore(release): ...` | no release | +| Any commit with a `BREAKING CHANGE:` footer | major release | + +Types such as `docs`, `refactor`, `style`, and `build` do not trigger a release on their own. + +## Prerequisites + +The release path depends on external configuration that lives outside this repository: + +- A GitHub App installed on this repository, exposed as the Actions variable `RELEASE_AUTOMATION_APP_ID` and the secret `RELEASE_AUTOMATION_PRIVATE_KEY`. +- A protected `npm` environment restricted to `main`, with a required reviewer and no environment secrets. +- An npm trusted publisher for this repository, workflow `release.yml`, and environment `npm`. + +No long-lived npm token exists. Publication authenticates through GitHub OIDC. If publishing fails, fix the trusted publisher configuration; do not add a token. + +Setup steps are recorded in the manual configuration runbook of the [CI modernization plan](../plans/flow-stack-ci-modernization-plan.md). + +## The Release Path + +1. A pull request merges to `main`. +2. `release.yml` runs the reusable verification workflow. Nothing else starts until `Verification` succeeds. +3. The release job requests the protected `npm` environment and waits for approval. +4. A short-lived App token is minted and passed only to semantic-release, using process-scoped Git authentication. +5. semantic-release analyzes commits and, when a release is warranted, publishes to npm with provenance, commits the version and changelog, creates the tag, and publishes the GitHub release. +6. A back-merge pull request from `main` into `dev` is opened so the release commit returns to the integration branch. + +If no commit warrants a release, the run is a successful no-op. + +The release commit is `chore(release): `, which is classified as non-releasing, so it cannot cause a second release. It does re-trigger the workflow once; that run verifies and then no-ops. + +## Dry Run + +Use **Actions → Release → Run workflow** from `main` with `dry-run` enabled. + +The dry run is mechanically incapable of publishing. It runs in a separate job with no npm environment, no OIDC permission, and no App credentials, and it points semantic-release at a local bare clone with only the analysis plugins loaded. It reports the version that would be released. + +## Back-Merge + +The post-release sync pull request opens only when `main` is ahead of `dev`. If an equivalent pull request already exists for the current `main` commit, the step is a no-op. Merge it promptly so `dev` does not drift. + +## Hotfixes + +1. Branch from `main`. +2. Open a pull request into `main` with a conventional title, usually `fix: ...`. +3. Merge after `Verification` passes and the release publishes. +4. Merge the resulting sync pull request back into `dev`. + +## Failure Recovery + +| Failure | Effect | Action | +| --------------------------------- | -------------------------------------------- | --------------------------------------------------------------------------- | +| Verification fails | Nothing is published | Fix the code and merge again | +| Advisory or signature audit fails | Release blocked before mutation | Resolve the advisory or add a reviewed override | +| App token creation fails | No mutation occurs | Check App installation, variable, and secret; do not substitute a token | +| npm OIDC failure | Publish fails with no fallback | Correct the trusted publisher or environment, then re-run | +| Publish succeeded, commit failed | npm has the version, `main` lacks the commit | Do not unpublish. Reconcile the repository, then release a corrective patch | +| Promotion branch moved | Workflow refuses to overwrite or delete | Investigate manually; the exact commit is reported in the log | + +## Rollback Policy + +Never unpublish a released version as routine rollback. Use one of: + +- a corrective patch release, or +- `npm deprecate` with a message pointing at the fixed version. + +Unpublishing breaks consumers and lockfiles. + +## App Key Rotation + +1. Generate a new private key in the App settings. +2. Replace the `RELEASE_AUTOMATION_PRIVATE_KEY` secret. +3. Confirm an automated pull request or a dry run still authenticates. +4. Delete the old key. + +Record the owner and rotation date in maintainer records, not in this repository. + +## Verifying External Configuration + +Non-secret evidence worth confirming after any change to the release path: + +- the App's installed repository and permission list; +- the Actions variable and secret names, never their values; +- the `npm` environment branch restriction and reviewer setting; +- the npm trusted publisher repository, workflow, and environment; +- required checks and bypass actors on `main` and `dev`; +- that squash merging is enabled; +- the actor and checks on the most recent generated pull request; +- the provenance attestation on the most recent published version. diff --git a/docs/plans/flow-stack-ci-modernization-plan.md b/docs/plans/flow-stack-ci-modernization-plan.md new file mode 100644 index 0000000..f044529 --- /dev/null +++ b/docs/plans/flow-stack-ci-modernization-plan.md @@ -0,0 +1,1505 @@ +# Flow Stack CI Modernization Architecture and Implementation Plan + +> Status: COMPLETE +> +> Plan version: 5.2 +> +> Revision: 23 +> +> Last updated: 2026-09-03 +> +> Repository: `clalexander/flow-stack` +> +> Branch: `ci/update` +> +> Baseline commit: `525e8d7817b205d39b33f37b938655a1a8cad775` +> +> Working tree: Clean at planning baseline +> +> Canonical location: `docs/plans/flow-stack-ci-modernization-plan.md` +> +> Current phase: None; all phases are accepted +> +> Implementation authorization: Phase 5 granted on 2026-09-03 (`Phase 4 accepted. Proceed with phase 5`) +> +> Supersedes: None + +## Purpose + +This plan governs modernization of Flow Stack's GitHub CI, dependency automation, React compatibility automation, and public npm release workflow. It adapts applicable controls from an internal reference monorepo while preserving Flow Stack's single-package semantic-release model, public npm publishing target, and Node/React compatibility promises. + +The durable outcome is a release path in which the exact commit published to npm passes one authoritative verification workflow, automated pull requests trigger normal protections, repository mutations use short-lived least-privilege credentials, and manual GitHub/npm configuration is documented and testable. + +> This is a planning document. It does not authorize implementation. + +## Intent and Goals + +### Intent + +Make Flow Stack's automation reliable, secure, understandable, and maintainable without importing monorepo- or AWS-specific machinery from that reference repository. + +### Goals + +1. Make one reusable workflow authoritative for pull-request and pre-publish verification. +2. Test every supported Node and React major before publication. +3. Remove duplicated React compatibility lists and repair React-major automation. +4. Use least-privilege, short-lived credentials for npm publishing and repository mutation. +5. Consolidate Dependabot into exactly one open grouped npm version-update PR and one open grouped GitHub Actions version-update PR, both reviewable and promotable from `dev` to `main`. +6. Keep `package.json` authoritative for the package contract without repository-specific validation wrappers. +7. Establish branch rulesets, a GitHub App, a protected release environment, and npm Trusted Publishing through explicit manual steps. +8. Keep release and recovery procedures in repository documentation. + +### Success Outcomes + +- A required `Verification` check represents all quality and compatibility jobs and cannot pass when any dependency job fails or is cancelled. +- The release job cannot publish until `Verification` succeeds for the release commit. +- React support is declared once in `package.json`; automation and matrices derive from it. +- Generated React, dependency-promotion, and back-merge pull requests trigger normal PR checks. +- Dependabot does not fan out routine updates by dependency: all eligible npm updates share one PR and all eligible GitHub Actions updates share one PR. +- No long-lived npm token is stored; npm publishing uses GitHub OIDC Trusted Publishing. +- semantic-release receives a GitHub App token only in its mutation step and checkout never persists credentials. +- `main` and `dev` are protected by stable required checks and restricted update rules. + +## Scope + +### In Scope + +- `.github/workflows/ci.yml` +- `.github/workflows/release.yml` +- `.github/workflows/pr-title.yml` +- `.github/workflows/react-major-support.yml` +- A reusable verification workflow under `.github/workflows/` +- A dependency-promotion workflow under `.github/workflows/` +- `.github/dependabot.yml` +- `.github/scripts/update-react-major-support.ts` and focused tests +- `package.json`, `pnpm-lock.yaml`, `pnpm-workspace.yaml`, and `release.config.mjs` +- Release, automation, and contributor documentation +- Manual GitHub ruleset, environment, GitHub App, and npm Trusted Publisher configuration + +### Out of Scope + +- Lerna, Nx, workspace package generation, fixed-version monorepo releases, or recursive publishing +- AWS OIDC, CodeArtifact, IAM roles, or private registry configuration +- Product source behavior or public Flow Stack APIs +- React support for a new major; this initiative only makes future evaluation reliable +- Changing the Node or React support policy currently declared by the package +- Automated dependency merging +- Renovate or another replacement for Dependabot +- Replacing semantic-release +- Unrelated dependency upgrades or repository cleanup + +### Deferred Possibilities + +- Removing committed `package.json` version and `CHANGELOG.md` updates from semantic-release. The current behavior is preserved because changing release artifacts is a separate product/repository policy decision. +- Separate GitHub Apps for release mutation and PR automation. One shared account-level App with repository-selected installations is used initially; split it if organizational policy requires tighter actor separation. +- Enforcing signed commits. This depends on contributor and bot signing policy outside this initiative. + +## Non-Negotiable Execution Protocol + +1. Implementation proceeds through strictly sequential phases. +2. Only one phase may be active at a time. +3. Starting Phase 1 requires explicit user authorization. +4. Completing a phase does not authorize the next phase. +5. After each phase, implementation stops and presents changed files, public API changes, tests, commands, evidence, deviations, and unresolved issues. +6. The next phase begins only after explicit user acceptance of the prior phase and authorization of the next. +7. Work outside the active phase allowlist is prohibited unless this plan is revised and the deviation is approved. +8. Unexpected unrelated defects are documented, not repaired. +9. The implementing agent must reread this entire document before planning the next phase, before starting each phase, and after context compaction, handoff, or resumed work. +10. This plan is updated at every phase boundary with authorization, backlog status, validation evidence, deviations, and acceptance. +11. Only tasks present in the authorized phase backlog may be executed. Newly discovered tasks require a documented plan revision before execution. +12. An implementation, design, behavior, or intent change outside approved scope must not be executed or silently incorporated. Stop, document the proposal, ask the user for direction, and wait. +13. This plan remains the canonical initiative source of truth until explicitly superseded, promoted, archived, or removed. +14. Ambiguous approval language does not authorize crossing a phase boundary. + +Unambiguous authorization examples: + +- `Authorize Phase 1.` +- `Phase 1 is accepted. Authorize Phase 2.` + +## Document Maintenance Protocol + +- Increment `Revision` for every saved plan update, implementation checkpoint, and phase closeout. +- Increment the minor plan version for additive clarification that preserves scope and architecture. +- Increment the major plan version when approved scope, target architecture, canonical semantics, or phase structure changes materially. +- Preserve requirement and task IDs. Mark removed entries `SUPERSEDED`, `OUT OF SCOPE`, or `REMOVED`; never silently delete history. +- Update the revision log, phase table, affected requirements, decisions, tasks, evidence, and acceptance state together. +- Use only the defined document statuses: `DRAFT`, `BLOCKED`, `READY FOR REVIEW`, `APPROVED`, `IN PROGRESS`, `AWAITING ACCEPTANCE`, `COMPLETE`, and `SUPERSEDED`. + +## Planning Baseline + +| Field | Value | Evidence | +| ------------------------------ | --------------------------------------------------------------------------------------- | --------------------------------------------------------------------------------- | +| Repository root | Local checkout of `clalexander/flow-stack` | Workspace inspection | +| Branch | `ci/update` | `git branch --show-current` | +| Baseline commit | `525e8d7817b205d39b33f37b938655a1a8cad775` | `git rev-parse HEAD` | +| Working tree | Clean | `git status --short` returned no entries | +| Relevant components | GitHub workflows, Dependabot, semantic-release, package metadata, release documentation | `.github/`, `package.json`, `release.config.mjs`, `CONTRIBUTING.md` | +| Existing Flow Stack plans/docs | No `/docs` tree existed at baseline | Workspace file search | +| Comparison source | Internal reference monorepo automation and release documentation | Repository inspection | +| Recent automation history | Action upgrades and dependency update commits are active on the branch | `git log -5 --oneline -- .github package.json release.config.mjs CONTRIBUTING.md` | +| Toolchain | Node 20.19+; pnpm 10; CI uses Node 20, 22, and 24 | `package.json`, `.github/workflows/ci.yml` | + +An ignored `package-lock.json` exists locally but is not authoritative. `pnpm-lock.yaml` remains the only lockfile in scope. + +## Revision Log + +| Revision | Plan Version | Date | Status | Summary | Author/Source | +| -------- | ------------ | ---------- | ------------------- | ---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | ----------------------------------------- | +| 1 | 1.0 | 2026-09-02 | READY FOR REVIEW | Initial architecture and phased implementation plan. | Initiative Architect | +| 2 | 2.0 | 2026-09-02 | READY FOR REVIEW | Replaced production/development npm PR groups with one catch-all npm group, added one catch-all GitHub Actions group, limited each ecosystem to one open PR, and aligned promotion/release semantics. | User direction | +| 3 | 2.0 | 2026-09-02 | IN PROGRESS | Recorded Phase 1 authorization and added `vitest.config.ts` to its allowlist so the planned `test/tooling` suite runs in the Node test project. | Phase 1 implementation | +| 4 | 3.0 | 2026-09-02 | IN PROGRESS | Replaced immutable action SHA pinning with maintained major-version tags such as `@v7`, accepting tag mutability and relying on grouped Dependabot review for updates. | User direction | +| 5 | 3.0 | 2026-09-02 | IN PROGRESS | Broadened Node test discovery to all `.test.ts` files outside jsdom/type-owned trees and allowed a colocated `.d.mts` boundary for importable React support tooling. | User direction and Phase 1 implementation | +| 6 | 3.0 | 2026-09-02 | IN PROGRESS | Replaced the React support `.mjs` implementation and declaration pair with directly executable TypeScript GitHub scripts under the existing Node 24 runtime policy. | User direction | +| 7 | 3.0 | 2026-09-02 | IN PROGRESS | Recorded authorization to add direct `@types/node` development declarations required to typecheck the TypeScript GitHub CLI without local hand-written Node API declarations. | User authorization | +| 8 | 3.0 | 2026-09-02 | AWAITING ACCEPTANCE | Completed the Phase 1 backlog and recorded focused, repository-wide, runtime, diagnostic, formatting, and diff validation evidence; hosted GitHub job-graph confirmation remains a PR acceptance check. | Phase 1 closeout | +| 9 | 3.0 | 2026-09-02 | IN PROGRESS | Recorded explicit Phase 1 acceptance and Phase 2 authorization; activated package and supply-chain validation tasks P2-T001 through P2-T004. | User authorization | +| 10 | 4.0 | 2026-09-02 | IN PROGRESS | Removed the monorepo-derived hard-coded package metadata and file-list validator; `package.json` remains authoritative, established analyzers interpret it, and the local script tests only packed consumers. | User direction | +| 11 | 5.0 | 2026-09-02 | IN PROGRESS | Removed package validation entirely, including its script, package commands, analyzers, packed-consumer requirements, and workflow plan; Phase 2 now covers only distinct audits and action-tag normalization. | User direction | +| 12 | 5.0 | 2026-09-02 | IN PROGRESS | Authorized patched transitive overrides for `nanoid@3.3.18` and `browserslist@4.28.8` after the new fail-closed vulnerability audit identified three high-severity advisories. | User authorization | +| 13 | 5.0 | 2026-09-02 | AWAITING ACCEPTANCE | Completed active Phase 2 audit and action-normalization tasks, remediated three high-severity transitive advisories, and recorded local validation plus the remaining GitHub-hosted workflow evidence. | Phase 2 closeout | +| 14 | 5.1 | 2026-09-02 | IN PROGRESS | Recorded Phase 2 acceptance, Phase 3 authorization, completed M-001 through M-003 prerequisites, the shared App's repository-selected installation model, and completion of unprivileged PR-title task P3-T005. | User confirmation and Phase 3 start | +| 15 | 5.1 | 2026-09-02 | IN PROGRESS | Completed the Phase 3 implementation backlog: isolated OIDC publication, ephemeral App-authenticated mutations, credential-free release analysis, checked sync/React PRs, and unprivileged title validation. | Phase 3 implementation checkpoint | +| 16 | 5.1 | 2026-09-02 | AWAITING ACCEPTANCE | Closed Phase 3 implementation with full local validation, security/correctness review repairs, confirmed App/environment/Trusted Publisher prerequisites, and explicit hosted acceptance checks. | Phase 3 closeout | +| 17 | 5.1 | 2026-09-02 | IN PROGRESS | Recorded Phase 3 acceptance and Phase 4 authorization, retained the post-release verification run instead of a skip directive, and activated dependency grouping and promotion tasks P4-T001 through P4-T004. | User authorization and Phase 4 start | +| 18 | 5.1 | 2026-09-02 | AWAITING ACCEPTANCE | Closed Phase 4 implementation, correcting Dependabot branch-name and release-scope assumptions against observed repository evidence and hardening promotion containment, concurrency, and token scope. | Phase 4 closeout | +| 19 | 5.2 | 2026-09-03 | AWAITING ACCEPTANCE | Accepted that development-only npm groups stay `chore(deps-dev)` and do not release, aligned DR-005/DEC-006/step 4.1/acceptance, recorded pnpm 10 `updateConfig` holds, and opened the Node 20 support question. | User direction | +| 20 | 5.2 | 2026-09-03 | AWAITING ACCEPTANCE | Extended the P4-T001 compatibility holds so React, React DOM, and their type packages are ignored by bare `pnpm update`, matching the Dependabot major ignores that reserve React majors for the watcher. | User direction | +| 21 | 5.2 | 2026-09-03 | IN PROGRESS | Recorded Phase 4 acceptance and Phase 5 authorization, and activated documentation, contributor-alignment, ruleset, and final-proof tasks P5-T001 through P5-T004. | User authorization and Phase 5 start | +| 22 | 5.2 | 2026-09-03 | IN PROGRESS | Completed P5-T001 and P5-T002 by adding the `docs/` knowledge base with CI and release runbooks and aligning contributor guidance with conventional squash titles and generated release artifacts. | Phase 5 implementation checkpoint | +| 23 | 5.2 | 2026-09-03 | COMPLETE | Recorded Phase 5 acceptance with P5-T003 and P5-T004 deferred, redacted local paths and third-party repository identifiers, and relocated this record to `docs/plans/`. | User direction and initiative closeout | + +## Phase Status + +| Phase | Conceptual Boundary | Status | Backlog Progress | Authorization | Acceptance | Revision | +| ----- | ------------------------------------------------------------------ | -------- | -------------------------------- | ------------------- | ------------------- | -------- | +| 1 | Canonical verification and React compatibility | COMPLETE | 5 / 5 complete | Received 2026-09-02 | Received 2026-09-02 | 9 | +| 2 | Supply-chain validation and action normalization | COMPLETE | 2 / 2 active complete; 2 removed | Received 2026-09-02 | Received 2026-09-02 | 14 | +| 3 | Credentialed release and generated-PR automation | COMPLETE | 5 / 5 complete | Received 2026-09-02 | Received 2026-09-02 | 17 | +| 4 | Dependabot grouping, promotion, and policy | COMPLETE | 4 / 4 complete | Received 2026-09-02 | Received 2026-09-03 | 21 | +| 5 | Branch enforcement, operations documentation, and end-to-end proof | COMPLETE | 2 / 4 complete; 2 deferred | Received 2026-09-03 | Received 2026-09-03 | 23 | + +## Requirement Sources + +| Source ID | Source | Authority/Scope | Relevant Material | +| --------- | --------------------------------------------- | ------------------- | ----------------------------------------------------------------------------------------- | +| SRC-000 | Initiative execution protocol | Initiative process | Phase gates, backlog control, scope control, handoff, and reread requirements | +| SRC-001 | User request | Initiative | Durable Flow Stack CI plan including manual branch protection and GitHub App setup | +| SRC-002 | Repository development and architecture rules | Repository | Maintainability, existing patterns, explicit boundaries, focused changes, full validation | +| SRC-003 | Repository security and CI rules | Workflows/scripts | Least privilege, OIDC, secret handling, trust-boundary validation | +| SRC-004 | Environment safety constraints | Local environment | No installs, machine changes, services, or destructive actions without permission | +| SRC-005 | Current Flow Stack automation | Current behavior | CI, release, React support, Dependabot, PR title checks, semantic-release | +| SRC-006 | Internal reference monorepo automation | Comparison evidence | GitHub App tokens, dependency promotion, cooldowns, package checks, release docs | +| SRC-007 | Flow Stack package and contributor contracts | Current behavior | Supported engines/peers, scripts, branching model, release classification | + +## Active Requirements + +### Functional Requirements + +| ID | Requirement | Source | Verification | Status | +| ------ | --------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | ---------------- | -------------------------------------------------------- | ------ | +| FR-001 | Pull requests to `main`, `dev`, `release/**`, and `hotfix/**` must run one authoritative verification contract. | SRC-001, SRC-005 | Trigger tests and GitHub check results | ACTIVE | +| FR-002 | A release must not start mutation or publication until the release commit passes all supported Node and React combinations. | SRC-001, SRC-005 | Release dependency graph and controlled release evidence | ACTIVE | +| FR-003 | React-major automation must update `package.json` and compatibility documentation, open a PR to `dev`, and rely on derived matrices rather than editing workflow YAML. | SRC-005 | Script tests and automation PR evidence | ACTIVE | +| FR-004 | Dependabot scheduled version updates must produce at most one open catch-all npm PR and at most one open catch-all GitHub Actions PR against `dev`, rather than one PR per dependency/action. | SRC-001 | Dependabot configuration and observed PRs | ACTIVE | +| FR-005 | Post-release synchronization from `main` to `dev` must create at most one open PR and trigger normal checks. | SRC-005, SRC-006 | Controlled release evidence | ACTIVE | +| FR-006 | PR titles must be conventional for non-draft PRs, including generated automation PRs. | SRC-005, SRC-007 | PR-title workflow checks | ACTIVE | +| FR-007 | Merging either grouped Dependabot PR into `dev` must create one reviewable draft snapshot PR to `main` at the exact merge commit. | SRC-001, SRC-006 | Event-filter tests and controlled PR evidence | ACTIVE | + +### Domain and Data Requirements + +| ID | Requirement | Source | Verification | Status | +| ------ | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | ---------------- | ------------------------------------------------- | ------ | +| DR-001 | `package.json.peerDependencies.react` is the canonical source for supported React majors; `react-dom` must have the same range. | SRC-005, SRC-007 | Matrix preparation and validator tests | ACTIVE | +| DR-002 | The supported Node matrix remains 20, 22, and 24 while `engines.node` is `>=20.19.0`; changing support requires a plan revision. | SRC-005, SRC-007 | Workflow matrix inspection and jobs | ACTIVE | +| DR-003 | Dependency-promotion branches identify the source Dependabot PR and point exactly to its merge commit. | SRC-006 | GitHub API assertions and workflow evidence | ACTIVE | +| DR-004 | `pnpm-lock.yaml` is authoritative; compatibility jobs may mutate manifests only in ephemeral runners and must not upload or commit those mutations. | SRC-004, SRC-005 | Git diff guard in workflow and repository status | ACTIVE | +| DR-005 | The npm group keeps Dependabot's conventional scope: `chore(deps)` when the group contains at least one production dependency, and `chore(deps-dev)` when it contains only development dependencies, which intentionally does not release. The GitHub Actions group uses `ci(deps)` and does not itself request an npm release. | SRC-001, SRC-005 | Dependabot PR titles and semantic-release dry run | ACTIVE | + +### Architectural Requirements + +| ID | Requirement | Source | Verification | Status | +| ------ | --------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | ---------------- | -------------------------------------------- | ------ | +| AR-001 | A reusable workflow owns quality and compatibility verification; CI and release call it instead of duplicating steps. | SRC-001, SRC-002 | Workflow graph review | ACTIVE | +| AR-002 | A final `Verification` job uses `if: always()` and fails unless every required upstream job succeeded. Branch rules depend on this stable check rather than dynamic matrix check names. | SRC-001, SRC-005 | Failure/cancellation workflow tests | ACTIVE | +| AR-003 | semantic-release remains the release engine and public npm remains the publication target. | SRC-005, SRC-007 | Release config and controlled dry run | ACTIVE | +| AR-004 | Existing committed `package.json` version and `CHANGELOG.md` release artifacts remain enabled. | SRC-005 | semantic-release dry run and release commit | ACTIVE | +| AR-005 | Workflow automation must use structured JSON parsing and pure functions for package metadata; it must not rewrite YAML matrices using regex. | SRC-002, SRC-005 | Script unit tests and code review | ACTIVE | +| AR-006 | GitHub Actions dependencies must use maintained major-version tags such as `@v7`; Dependabot continues to update them through the single grouped GitHub Actions PR. | SRC-001 | Workflow source inspection and Dependabot PR | ACTIVE | + +### Security and Operational Requirements + +| ID | Requirement | Source | Verification | Status | +| ------ | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ | ------------------------- | ------------------------------------------------------ | ------ | +| SR-001 | Checkout must set `persist-credentials: false` in every job. | SRC-003, SRC-006 | Workflow source inspection | ACTIVE | +| SR-002 | Public npm publishing must use GitHub OIDC Trusted Publishing through a protected `npm` environment; no long-lived npm token may be added. | SRC-001, SRC-003 | GitHub/npm settings and publication attestation | ACTIVE | +| SR-003 | Repository mutation and generated PRs must use a repository-installed GitHub App token with only Contents, Issues, and Pull requests permissions required by semantic-release and PR automation. | SRC-001, SRC-003, SRC-006 | App settings, workflow permissions, and audit log | ACTIVE | +| SR-004 | App authentication must be injected only into mutation steps and must not be persisted in checkout or written to repository files/logs. | SRC-003, SRC-006 | Workflow inspection and masked log review | ACTIVE | +| SR-005 | `pull_request_target` workflows must never check out or execute PR-controlled code. PR-title validation will use `pull_request` because write privileges are unnecessary. | SRC-003, SRC-005 | Trigger and permission inspection | ACTIVE | +| SR-006 | Vulnerability auditing and registry signature verification are separate fail-closed controls with accurate step names. | SRC-003, SRC-006 | CI logs for `pnpm audit` and `npm audit signatures` | ACTIVE | +| SR-007 | Automated branch creation/deletion must validate branch name and exact expected SHA and refuse unexpected existing state. | SRC-003, SRC-006 | Workflow tests and controlled run | ACTIVE | +| SR-008 | `main` and `dev` rulesets must block force pushes/deletion and require PRs plus stable CI checks; only the Release Automation App may bypass `main` for semantic-release commits. | SRC-001, SRC-003 | GitHub ruleset export/screenshots and controlled tests | ACTIVE | +| OR-001 | Release and generated-PR jobs must use concurrency groups that prevent duplicate mutation without cancelling an active release. | SRC-005 | Concurrent dispatch test or workflow graph | ACTIVE | +| OR-002 | Failure recovery must never delete published npm versions as a normal rollback; use a corrective patch or npm deprecation. | SRC-006 | Release runbook review | ACTIVE | +| OR-003 | Workflow logs must identify the source SHA/PR and outcome without printing credentials or authentication headers. | SRC-003 | Log review | ACTIVE | + +### Testing and Validation Requirements + +| ID | Requirement | Source | Verification | Status | +| ------ | --------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | ---------------- | ------------------------------- | ------- | +| TR-001 | React support parsing and update generation must have Vitest coverage for no-op, next-major, malformed range, mismatched React DOM, README replacement, and write-failure cases. | SRC-002, SRC-005 | Focused Vitest suite | ACTIVE | +| TR-002 | Verification must run format check, lint, typecheck, build, tests, vulnerability audit, and signature audit. | SRC-002, SRC-006 | Reusable workflow logs | ACTIVE | +| TR-003 | Packed-artifact consumer validation was removed because this single-package repository treats `package.json` as authoritative and does not need the copied monorepo validation pattern. | User direction | Revision 11 | REMOVED | +| TR-004 | Workflow event filters, result aggregation, branch collision handling, and dry-run paths require reviewable tests or controlled GitHub runs before enforcement. | SRC-001, SRC-003 | Test records and phase evidence | ACTIVE | +| TR-005 | Validation uses the repository's active Node/pnpm toolchain and does not install dependencies or alter the machine without explicit permission. | SRC-004 | Command record | ACTIVE | + +### Process and Handoff Requirements + +| ID | Requirement | Source | Verification | Status | +| ------ | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | ------------------------- | ----------------------------------------- | ------ | +| PR-001 | Implementation is limited to the authorized phase backlog and approved scope. Out-of-scope design or intent changes require consultation and explicit direction. | SRC-000 | Phase backlog, revision history, closeout | ACTIVE | +| PR-002 | The canonical plan must be reread in full before planning or starting each phase and after compaction, handoff, or resumed work. | SRC-000 | Phase checkpoint and closeout | ACTIVE | +| PR-003 | Manual repository or account configuration occurs only at the documented gate and requires the user; credentials are never supplied through chat. | SRC-001, SRC-003, SRC-004 | Gate evidence without secret values | ACTIVE | +| PR-004 | No dependency installation, environment alteration, service/container operation, release, branch mutation, or remote settings change occurs without explicit authorization for that action. | SRC-004 | Command and phase authorization record | ACTIVE | + +## Acceptance Criteria + +| ID | Acceptance Criterion | Requirements | Evidence | +| ------ | --------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | ------------------------------ | ----------------------------------------------- | +| AC-001 | A deliberately failing matrix cell makes the stable `Verification` check fail, blocks merge, and prevents the release job. | FR-001, FR-002, AR-001, AR-002 | Controlled PR/run | +| AC-002 | A React peer range fixture produces the expected dynamic matrix; the next-major updater changes only package metadata/docs and opens a checked PR. | FR-003, DR-001, AR-005, TR-001 | Tests and controlled dispatch | +| AC-003 | A release from `main` publishes only after verification, produces a GitHub release and committed changelog/version, and has npm provenance. | FR-002, AR-003, AR-004, SR-002 | Release logs, npm/GitHub artifacts | +| AC-004 | App-created React, dependency-promotion, and sync PRs all run `Verification` and PR-title checks. | FR-003, FR-004, FR-005, SR-003 | GitHub checks on controlled PRs | +| AC-005 | Dependabot exposes no more than one open scheduled npm update PR and one open scheduled GitHub Actions update PR; merging either creates one draft promotion PR at the exact merge SHA. | FR-004, FR-007, DR-003, SR-007 | Dependabot PR list and controlled workflow runs | +| AC-006 | Repository checkout/config/log review finds no persisted or exposed App/npm credentials. | SR-001, SR-002, SR-004 | Workflow and log review | +| AC-007 | Branch rules block direct human pushes, force pushes, deletion, and merging without required checks while allowing the App's release commit. | SR-008 | Controlled ruleset tests | +| AC-008 | Removed: packed package validation is not part of this single-package repository's CI contract. | None | User direction, revision 11 | + +## Assumptions and Constraints + +### Assumptions + +| ID | Assumption | Basis | Risk if False | Resolution | +| ------- | ----------------------------------------------------------------------------------------------------------------------------- | ----------------------------------------------------- | ------------------------------------------------------------------------- | ------------------------------------------------------------------------------------------------ | +| ASM-001 | The repository uses squash merging so the PR title becomes the release-visible commit subject. | Existing PR-title workflow and semantic-release model | Releases may be missed or misclassified | Confirm in Phase 5 manual settings; otherwise revise plan to add commit-message enforcement | +| ASM-002 | npm Trusted Publishing is available for `clalexander/flow-stack` and the public package. | Existing `id-token: write` release design | Publication cannot authenticate without a token | Verify before Phase 3; mark Phase 3 blocked if unavailable rather than adding a long-lived token | +| ASM-003 | The user can create/install a GitHub App and configure repository rulesets/environments. | User request | Generated PR checks and protected release commits cannot work as designed | Complete manual gate before Phase 3 | +| ASM-004 | GitHub Actions Ubuntu runners provide npm compatible with `npm audit signatures` for the pnpm lockfile. | Reference monorepo pattern | Signature check may not understand the lockfile | Prove in Phase 2; stop for plan revision if unsupported | +| ASM-005 | One shared Release Automation App with repository-selected installations is acceptable for release commits and generated PRs. | User direction and reference monorepo precedent | Permission surface may exceed policy | Split into repository-specific or purpose-specific Apps through a plan revision if required | + +### Constraints + +- The local toolchain and machine configuration must remain unchanged unless separately authorized. +- Workflow changes cannot prove external GitHub/npm settings locally. +- Major-version action tags are mutable upstream references. This accepted risk is mitigated by limiting actions to established publishers, least-privilege workflow permissions, and reviewing the single grouped GitHub Actions Dependabot PR. +- Branch rules cannot require newly named checks until those checks have run at least once in the repository. +- App private keys and npm/GitHub credentials must be entered directly in trusted product interfaces, never in chat or repository files. + +## Material Open Questions + +MOQ-001: Should Flow Stack continue to declare Node 20 support? Node 20 reached end of life in April 2026, so `engines.node` of `>=20.19.0` and the 20/22/24 verification matrix now cover an unsupported runtime. The field itself must stay: tsdown derives the published build target from it through `resolvePackageTarget`, so removing it would silently change emitted syntax, and Publint reports `USE_ENGINES_NODE` when it is absent because consumers may install on an unsupported runtime. Raising the minimum to Node 22 would reduce the matrix from nine cells to six, permit newer emitted syntax, and unblock pnpm 11, whose update settings are spelled `update.ignoreDeps` rather than pnpm 10's `updateConfig.ignoreDependencies`. It is a breaking change for consumers on Node 20 and would alter DR-002, the Node support policy listed under Out of Scope, `package.json`, the verification matrix, and README compatibility text. This question is recorded only. It is not authorized and must not be implemented without an explicit scope revision. + +MOQ-002: Should `engines.pnpm` remain in the published manifest? `packageManager` already pins local development, so the published range may warn consumers who install with a newer pnpm about a repository-only constraint. Confirm pnpm's dependency-engine behavior before changing it. + +No other open questions remain. The assumptions above have explicit stop conditions. Plan approval accepts preserving committed release artifacts, using one repository-scoped Release Automation App, and using an approval-protected `npm` environment. + +## Terminology + +- **Verification workflow**: reusable workflow containing all quality, package, and compatibility jobs. +- **Verification check**: stable aggregate job required by branch rules. +- **Release commit**: exact `main` commit evaluated before semantic-release mutation/publication. +- **Release Automation App**: GitHub App used for semantic-release Git/GitHub operations and generated pull requests. +- **npm update group**: the single Dependabot PR containing all eligible npm ecosystem version updates, including production and development dependencies, using `chore(deps)`. +- **GitHub Actions update group**: the single Dependabot PR containing all eligible action version updates, using `ci(deps)`. +- **Eligible update**: a version update not suppressed by an explicit compatibility ignore or cooldown. React major updates are intentionally ineligible because the React compatibility watcher owns them. +- **Promotion PR**: draft PR from a fixed `release/dependencies-` branch into `main`. +- **Trusted Publishing**: npm publication using GitHub Actions OIDC instead of a stored npm token. + +## Current-State Observations + +1. CI has a quality job and a Node 20/22/24 by React 18/19 matrix, but release independently repeats a React-only Node 24 matrix. Evidence: `.github/workflows/ci.yml`, `.github/workflows/release.yml`. +2. CI and release compatibility steps run `pnpm add -D --save-exact` at a pnpm workspace root without an explicit workspace-root flag. Evidence: both workflow files and `pnpm-workspace.yaml`. +3. The baseline React updater searches for inline YAML arrays while the workflows use block arrays, so a new React major reaches an exception after local runner mutations. Evidence: baseline `.github/scripts/update-react-major-support.mjs` and both matrices. +4. The updater's README pattern says `React and react-dom`; README says `React and React DOM`. Evidence: updater and `README.md`. +5. semantic-release publishes one public npm package, writes `package.json` and `CHANGELOG.md`, creates GitHub release artifacts, and only releases `chore(deps)`, not `chore(deps-dev)`. Evidence: `release.config.mjs`. +6. Generated React and sync PRs use `GITHUB_TOKEN`; such generated events do not reliably trigger normal downstream workflows. Evidence: React and release workflows. +7. Release checkout persists credentials while running dependencies and release plugins. Evidence: release checkout lacks `persist-credentials: false`. +8. Steps named “Verify dependency signatures” execute `pnpm audit`, which is a vulnerability advisory audit rather than signature verification. Evidence: CI/release workflows. +9. Dependabot targets `dev`, currently splits npm production and development minor/patch updates and does not group GitHub Actions updates; therefore it can open multiple routine PRs. It excludes React majors and has no cooldown or promotion path. Evidence: `.github/dependabot.yml`. +10. PR-title validation uses `pull_request_target` with read-only permissions and no checkout; it is currently constrained but does not require the target trigger. +11. `pnpm-workspace.yaml` has `minimumReleaseAgeExclude` without `minimumReleaseAge`, so the exception has no active age policy. +12. `CONTRIBUTING.md` recommends human-readable non-conventional commits and manual version/changelog work, conflicting with semantic-release behavior. + +### Documentation or Contract Discrepancies + +| ID | Documentation Says | Code/Tests Say | Planned Resolution | +| -------- | ---------------------------------------------------------- | --------------------------------------------------------------- | --------------------------------------------------------------- | +| DISC-001 | Release branches prepare versions and changelogs manually. | semantic-release writes both after merge to `main`. | Document semantic-release as authoritative in Phase 5. | +| DISC-002 | Example commits are not conventional. | Release classification requires conventional commits/PR titles. | Replace examples and document squash-merge contract in Phase 5. | +| DISC-003 | Workflow step verifies dependency signatures. | It runs vulnerability auditing only. | Run and label both controls in Phase 2. | + +## Current Architecture + +```mermaid +flowchart LR + PR[Pull request] --> CI[CI workflow] + CI --> Q[Quality] + CI --> CM[Node x React matrix] + M[Merge to main] --> CI + M --> R[Release workflow] + R --> RM[React matrix on Node 24] + RM --> SR[semantic-release] + SR --> NPM[Public npm] + SR --> RC[Version/changelog commit] + SR --> GH[GitHub Release] + SR --> SP[Sync PR via GITHUB_TOKEN] + D[Dependabot to dev] -. manual promotion .-> M + W[React watcher] --> RP[PR via GITHUB_TOKEN] +``` + +CI and release independently define verification. The main-push CI matrix and release workflow race rather than forming one gate. React support is copied across package metadata, two YAML matrices, and README. Repository mutation relies on the workflow token, and external branch/npm settings are undocumented. + +## Target Architecture + +```mermaid +flowchart LR + PR[Pull request] --> CI[CI caller] + CI --> V[Reusable verification workflow] + MP[Push to main] --> R[Release caller] + R --> V + V --> Q[Quality and audits] + V --> MX[Derived Node x React matrix] + Q --> A[Stable Verification check] + MX --> A + A -->|success| SR[semantic-release] + OIDC[GitHub OIDC] --> SR + APP[Release Automation App] --> SR + SR --> NPM[Public npm with provenance] + SR --> GH[GitHub Release and release commit] + APP --> GP[Generated PRs] + DB[Dependabot merge to dev] --> DP[Fixed-SHA promotion] + DP --> GP + RW[React watcher] --> GP + SR --> GP + GP --> PR +``` + +### Responsibilities and Boundaries + +- `verify.yml` owns verification semantics and exposes only pass/fail through `Verification`. +- `ci.yml` owns unprivileged PR/manual triggers and calls `verify.yml`. +- `release.yml` owns main-push/manual release orchestration, calls `verify.yml`, then enters the protected `npm` environment. +- `package.json` owns React peer support and repository commands. +- React tooling computes metadata/doc changes; it no longer edits workflow YAML. +- The Release Automation App owns repository mutation identity. Workflow `GITHUB_TOKEN` remains read-only by default. +- npm owns package publication; OIDC identifies only the approved repository, workflow filename, and environment. +- Dependency promotion snapshots an immutable merge SHA and never merges automatically. + +## Settled Design Decisions + +| ID | Decision | Rationale | Alternatives Rejected | Consequences | Revisit When | +| ------- | -------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | ------------------------------------------------------------------------------------------------------------------------------------ | ----------------------------------------------------------------------------------------------------------------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | ------------------------------------------------------------------------------------------------- | +| DEC-001 | Use a reusable workflow plus stable aggregate `Verification` job. | Removes drift and makes branch rules stable across dynamic matrices. | Duplicated release matrix; relying on concurrent CI. | Release waits for complete verification; one workflow controls semantics. | GitHub supports a simpler native required-workflow policy suitable for this repository. | +| DEC-002 | Derive React matrix from `peerDependencies.react`; keep Node majors explicit. | React metadata is already public package truth; Node minimum-to-major mapping is not safely inferable. | Regex editing YAML; duplicate lists. | Matrix-preparation job is required. | Peer ranges become non-contiguous or prerelease-specific. | +| DEC-003 | Preserve semantic-release, committed changelog/version, and public npm. | Avoids changing established release intent. | Lerna; AWS/CodeArtifact; removing release commits. | App requires protected-branch bypass and sync PR remains necessary. | Maintainer elects tags/releases as sole release records. | +| DEC-004 | Use one shared account-level GitHub App, installed only on selected repositories, for release mutation and generated PRs. | Reuses one automation identity across similarly managed packages while retaining repository-scoped installations and checked events. | PAT; broad `GITHUB_TOKEN`; one App per repository; two purpose-specific Apps initially. | Each repository stores the App ID/key and manages its own installation, environment, Trusted Publisher, rules, and validation; key compromise has a wider blast radius. | Organization policy requires actor separation, repository-specific keys, or narrower permissions. | +| DEC-005 | Use npm Trusted Publishing through protected environment `npm`. | Avoids long-lived npm tokens and produces provenance. | Stored `NPM_TOKEN`. | External npm/GitHub setup becomes a release prerequisite. | Trusted Publishing is unavailable for the package. | +| DEC-006 | Configure one catch-all npm group and one catch-all GitHub Actions group, each with `open-pull-requests-limit: 1`, and promote either merged group through a draft fixed-SHA PR. | Directly prevents per-dependency/action PR fan-out while preserving one review and promotion boundary per ecosystem. | Production/development npm groups; per-update PRs; one mixed cross-ecosystem PR, which Dependabot cannot produce; auto-merge. | Development-only npm updates keep `chore(deps-dev)` and intentionally do not release; groups containing a production dependency use `chore(deps)` and produce a patch. Actions use `ci(deps)` and remain non-releasing. React majors stay in the dedicated watcher. | Dependabot supports a safe cross-ecosystem group or release classification requirements change. | +| DEC-007 | Pin actions to maintained major-version tags such as `@v7`. | Keeps action references readable and aligned with the repository's preferred Dependabot update model. | Full commit SHAs; minor/patch tags. | Upstream tags are mutable; least privilege, established publishers, and grouped Dependabot review mitigate but do not eliminate that risk. | Repository policy changes to require immutable action references. | +| DEC-008 | Do not add repository-specific package validation, analyzers, packed-consumer scripts, or package commands; `package.json` is authoritative. | The copied pattern solves cross-package consistency in a monorepo, which does not apply to this repository. | Metadata mirrors, package analyzers, and packed-consumer wrappers. | Phase 2 validates supply-chain controls without maintaining a second package-contract mechanism. | The repository becomes a monorepo with package-level consistency requirements. | + +## Canonical Patterns and Contracts + +### Pattern Inventory + +| Pattern ID | Concern | Chosen Pattern | Canonical Location | Consumers | +| ---------- | -------------------- | -------------------------------------------------------- | ------------------------------------------ | ------------------------------ | +| PAT-001 | Verification reuse | Callable workflow with stable aggregate | `.github/workflows/verify.yml` | CI and release | +| PAT-002 | Compatibility source | Pure peer-range parser and JSON matrix output | `.github/scripts/react-support.ts` | Verification and React watcher | +| PAT-003 | Repository mutation | Ephemeral GitHub App token and temporary Git auth header | Release/generated PR jobs | semantic-release and `gh` | +| PAT-004 | Dependency promotion | Event predicates plus fixed merge-SHA branch | `.github/workflows/dependency-release.yml` | Dependabot merge events | + +### PAT-001: Reusable Verification Workflow + +**Ownership and boundaries** + +- Owned by `.github/workflows/verify.yml`. +- Uses read-only contents permission. +- Must not receive secrets, publish, push, create PRs, or mutate remote state. +- Compatibility dependency edits are ephemeral and followed by a git-diff assertion limited to expected manifest/lockfile files. + +Representative workflow shape: + +```yaml +name: Verify + +on: + workflow_call: + +permissions: + contents: read + +jobs: + matrix: + outputs: + react: ${{ steps.support.outputs.react }} + # Checkout, setup Node 24, then emit JSON from package.json. + + quality: + # Frozen install, audits, format, lint. + + compatibility: + needs: matrix + strategy: + fail-fast: false + matrix: + node: ['20', '22', '24'] + react: ${{ fromJSON(needs.matrix.outputs.react) }} + # Frozen install, ephemeral peer version install, typecheck, build, test. + + verification: + name: Verification + if: ${{ always() }} + needs: [matrix, quality, compatibility] + # Exit success only when every needs.*.result is success. +``` + +The aggregate job must treat `failure`, `cancelled`, and unexpected `skipped` as failure. Its name is a compatibility contract with branch rules. + +### PAT-002: React Support Contract + +The pure module must expose individually named functions and avoid executing network or filesystem work during import: + +```js +export function getSupportedReactMajors(reactRange, reactDomRange) { + // Returns string majors, for example ['18', '19'], or throws a precise error. +} + +export function createReactMajorUpdate(packageJson, latestVersion) { + // Returns { changed, candidateMajor, packageJson } without writing files. +} + +export function updateCompatibilityText(readme, supportedMajors) { + // Replaces one canonical compatibility sentence or throws. +} +``` + +The CLI adapter obtains the latest npm version, reads files, calls pure functions, writes only after all transformations succeed, and emits GitHub outputs. A malformed or mismatched peer range fails without writing any file. + +### PAT-003: Ephemeral GitHub App Authentication + +Workflow permissions remain explicit. The App token step requests only permissions needed by the job. Checkout uses `persist-credentials: false`. For semantic-release, configure a temporary process-scoped Git extra header and mask its encoded value; do not run `git config --global` for credentials. + +```yaml +- name: Create release automation token + id: app-token + uses: actions/create-github-app-token@v3 + with: + app-id: ${{ vars.RELEASE_AUTOMATION_APP_ID }} + private-key: ${{ secrets.RELEASE_AUTOMATION_PRIVATE_KEY }} + permission-contents: write + permission-issues: write + permission-pull-requests: write +``` + +The token is supplied as both `GH_TOKEN` and `GITHUB_TOKEN` only to semantic-release or the specific `gh` step. App credentials never reach verification jobs. + +### PAT-004: Fixed-SHA Dependency Promotion + +The workflow accepts only a merged PR where all conditions hold: + +- base is `dev`; +- actor is `dependabot[bot]`; +- head identifies either the configured npm group or configured GitHub Actions group; +- the title is exactly compatible with the group's conventional prefix: `chore(deps):` for npm or `ci(deps):` for GitHub Actions; +- merge commit SHA is non-empty. + +It creates `release/dependencies-` at that merge SHA only when absent. An existing branch at another SHA is a hard failure. An existing matching PR is a no-op. Deletion after merge requires matching branch syntax and exact merged head SHA. + +## Public API and Compatibility + +| Surface | Current | Target | Compatibility Strategy | Phase | +| ----------------------- | --------------------------------------------- | -------------------------------------- | ---------------------------------------- | ----- | +| Package runtime API | Existing Flow Stack exports | Unchanged | `package.json` remains authoritative | N/A | +| React peer support | `>=18 <20` duplicated in YAML/docs | Same range, package metadata canonical | Derived matrix and generated docs update | 1 | +| Node support | `>=20.19.0`; matrix 20/22/24 in CI | Unchanged; same matrix blocks release | Explicit reusable matrix | 1 | +| Workflow required check | Individual/unstable jobs | `Verification` aggregate | Run once before enabling rules | 1/5 | +| Release artifacts | npm, GitHub Release, changelog/version commit | Unchanged with provenance | GitHub App and OIDC | 3 | + +No consumer-facing API deprecation or migration is planned. + +## Canonical Semantics + +| Case ID | State/Input | Operation | Expected Result | Mutation | Error/Code | +| ------- | ----------------------------------------------------- | -------------- | -------------------------------------- | ---------------------- | ----------------------- | +| VER-001 | All verification jobs succeed | Aggregate | `Verification` succeeds | none | none | +| VER-002 | Any required job fails/cancels/skips unexpectedly | Aggregate | `Verification` fails | none | nonzero exit | +| REL-001 | Main push and verification succeeds | Release | semantic-release evaluates/publishes | release artifacts only | none | +| REL-002 | Verification fails | Release | Release job does not enter environment | none | blocked by `needs` | +| REL-003 | No releasable commits | Release | Successful no-op | none | none | +| RCT-001 | Latest React major already supported | Watcher | Successful no-op | none | `changed=false` | +| RCT-002 | Exactly next React major available | Watcher | Update peers/docs and open PR | automation branch/PR | none | +| RCT-003 | Invalid or mismatched peers | Watcher/matrix | Fail before writes | none | validation error | +| DEP-001 | Merged grouped npm Dependabot PR to `dev` | Promote | Draft fixed-SHA PR to `main` | branch and PR | none | +| DEP-002 | Merged grouped GitHub Actions Dependabot PR to `dev` | Promote | Draft fixed-SHA PR to `main` | branch and PR | none | +| DEP-003 | Promotion branch exists at expected SHA | Promote | Reuse/no-op | none | none | +| DEP-004 | Promotion branch exists at another SHA | Promote | Hard failure | none | collision error | +| DEP-005 | Merged promotion PR and branch SHA matches | Cleanup | Delete branch | branch deletion | none | +| DEP-006 | Cleanup branch name/SHA mismatch | Cleanup | Refuse deletion | none | validation error | +| DEP-007 | Dependabot PR is not one of the two configured groups | Promote | Successful no-op | none | none | +| PR-001 | Non-draft valid conventional title | Validate | Check succeeds | none | none | +| PR-002 | Invalid title | Validate | Check fails | none | action validation error | + +## Error and Failure Semantics + +| Condition | Public Behavior | Retryable | Observability | +| -------------------------------- | ----------------------------------------------------------------------- | ---------------------------------------------- | -------------------------------------- | +| Frozen lockfile mismatch | Verification fails before tests | After repository correction | Named install step | +| Advisory audit failure | Verification/release blocked | After dependency/risk resolution | `pnpm audit` output without secrets | +| Signature audit failure | Verification/release blocked | After registry/tool issue investigation | Separate signature step | +| Matrix preparation error | All compatibility/release work blocked | After peer metadata correction | Precise range validation message | +| One matrix cell fails | Aggregate fails after all cells complete | After code/dependency correction | Matrix labels identify Node/React pair | +| App token creation fails | Mutation job fails; package is not published if before semantic-release | After App settings correction | App action failure, no key output | +| npm OIDC failure | Publish fails with no token fallback | After Trusted Publisher/environment correction | npm/semantic-release error | +| Existing automation branch moved | Workflow refuses overwrite/delete | Manual investigation | Expected and actual SHA, no token | +| Sync PR already exists/no diff | Successful no-op | Not applicable | Explicit message | + +## Security, Privacy, and Trust Boundaries + +- PR code is untrusted. Verification has read-only repository permission and receives no secrets. +- PR-title validation moves to `pull_request`, requires only `contents: read` and `pull-requests: read`, and never executes checked-out PR code in a privileged context. +- Release mutation occurs only after trusted `main` verification and protected-environment approval. +- OIDC `id-token: write` exists only on the publish job. +- The shared App is installed on Flow Stack through a repository-selected installation and is not granted administration, actions, workflows, environments, secrets, or members permissions. +- Branch-ruleset bypass is limited to the Release Automation App and only where semantic-release must write to `main`. +- Automation validates GitHub event fields before branch mutation. No shell interpolation may accept unvalidated branch names. +- Secrets are held in GitHub Actions secrets; the App ID is a non-secret Actions variable. +- No plan, test fixture, log, or documentation contains a private key, token, authorization header, or real credential. + +## Data, Persistence, and Migration + +No application data changes exist. Repository-state changes are: + +1. New workflow contracts and scripts land without changing external settings. +2. The App variable/secret and npm environment are configured manually. +3. Workflows switch generated mutations to App identity. +4. New stable checks run once. +5. Branch rulesets are updated to require the stable checks. + +Rollback is performed by reverting workflow/configuration commits and restoring prior ruleset requirements. Do not delete the App or Trusted Publisher until the old workflow is restored and a release-path decision is made; otherwise rollback could strand releases. + +## Concurrency, Atomicity, and Idempotency + +- Verification may cancel obsolete PR runs, but release uses `cancel-in-progress: false`. +- Release concurrency remains scoped to the ref so only one main release mutates at a time. +- React watcher has one non-cancelling global group. +- Dependency promotion uses the source PR number for deterministic branch identity. +- Branch creation checks existing SHA before mutation; cleanup checks exact SHA before deletion. +- Generated PR lookup checks repository, base, head repository, branch, and expected SHA. +- semantic-release remains the final authority for duplicate tags/versions and no-release commits. +- Failed verification and collision cases must leave remote state unchanged. + +## Observability and Operations + +- Job names remain stable and descriptive; matrix names include Node and React majors. +- Mutation logs record source PR number, source SHA, target branch, generated branch, and resulting PR URL. +- Release logs identify baseline SHA, semantic-release outcome, npm version, tag, and GitHub Release without credentials. +- GitHub deployment history for environment `npm` provides approval and publication auditability. +- GitHub App audit logs provide mutation actor identity. +- Release runbook documents signature failures, OIDC failures, branch protection failures, partial semantic-release failures, corrective patch release, npm deprecation, and sync recovery. +- Additional hosted-runner cost is accepted for the full release matrix; reusable verification avoids duplicate main-push CI runs. + +## Testing Strategy + +| Layer | Responsibility | Location | Required Cases | +| ------------------ | --------------------------------------------------------------------- | ------------------------------------ | ----------------------------------------------------------- | +| Unit | Peer parsing and update transformations | `test/tooling/react-support.test.ts` | RCT-001 through RCT-003 plus malformed/read-write integrity | +| Workflow review | Trigger, permission, major action tag, aggregate, collision semantics | `.github/workflows/*.yml` | VER, REL, DEP, PR cases | +| GitHub integration | External event and credential behavior | Controlled draft PRs/dispatches | App events trigger checks, rules block bypass, OIDC works | +| Release acceptance | Public artifacts | npm and GitHub | provenance, version/tag/release/changelog/sync | + +### Failed-Operation Integrity + +- Unit tests snapshot the filesystem fixture before malformed update cases and assert byte-for-byte equality afterward. +- Verification failure is tested on a draft implementation PR before ruleset enforcement; release must remain skipped. +- Collision tests create or mock an unexpected branch SHA and prove no force push/deletion occurs. + +## Validation Protocol + +Current repository commands, run in quality-gate order: + +```powershell +pnpm run build +pnpm run typecheck +pnpm test +pnpm run lint +pnpm run format:check +``` + +Automatic repair commands, only when authorized: + +```powershell +pnpm run lint:fix +pnpm run format +``` + +Validation rules: + +- Focused tests run immediately after each implementation slice. +- Phase completion runs all affected checks with the active local toolchain; dependency installation is not authorized by plan approval alone. +- After `lint:fix`, inspect changes and rerun `lint`; do not restart build/typecheck/test solely for automatic lint cleanup. +- After `format`, inspect changes and rerun `format:check`; do not restart semantic gates solely for formatting. +- Rerun affected semantic gates when a repair changes behavior, types, configuration, generated artifacts, or more than formatting/lint-only concerns. +- GitHub-only behavior is validated on a controlled draft PR or manual dry run before branch enforcement. +- Release acceptance requires a controlled real release; it is separately authorized and never implied by phase authorization. + +## Manual Configuration Runbook + +These steps are performed by the user in GitHub/npm interfaces. Do not paste secrets into chat. + +### M-001: Create the Release Automation GitHub App + +Complete before Phase 3 repository changes are activated: + +1. In GitHub developer settings, create or reuse a shared package release automation GitHub App with repository-selected installations. +2. Set webhook activation off unless organizational policy requires it; no callback URL or user authorization is needed. +3. Grant repository permissions only: + - Contents: Read and write + - Issues: Read and write + - Pull requests: Read and write + - Metadata: Read-only, implicit +4. Do not grant Administration, Actions, Workflows, Environments, Secrets, Members, or organization permissions. +5. Install the App only on `clalexander/flow-stack`. +6. Generate a private key and immediately store its full PEM value as repository Actions secret `RELEASE_AUTOMATION_PRIVATE_KEY`. +7. Store the numeric App ID as repository Actions variable `RELEASE_AUTOMATION_APP_ID`. +8. Record the App owner and key-rotation date in the maintainer's secure operational records, not this repository. +9. After Phase 3 lands, run a controlled generated PR and confirm the PR actor is the App and CI starts. + +### M-002: Configure the Protected npm Environment + +Complete before enabling the Phase 3 release job: + +1. In repository Settings > Environments, create environment `npm`. +2. Restrict deployment branches/tags so only `main` can deploy. +3. Add the maintainer as required reviewer and enable prevention of self-review where the account/team arrangement supports it. +4. Do not add an `NPM_TOKEN` environment or repository secret. +5. Keep environment secrets empty unless a future approved requirement adds one. +6. Confirm the release job references `environment: npm` exactly. + +### M-003: Configure npm Trusted Publishing + +Complete before the first Phase 3 release test: + +1. Sign in to npm directly and open the `flow-stack` package publishing settings. +2. Add a GitHub Actions trusted publisher for repository owner `clalexander`, repository `flow-stack`, workflow filename `release.yml`, and environment `npm`. +3. Verify the npm package uses two-factor protection appropriate for trusted publishing and that no obsolete automation token is required by the workflow. +4. Do not provide npm credentials to the implementing agent. +5. After the first controlled release, inspect the npm version page and verify its provenance attestation identifies this repository/workflow. + +### M-004: Configure Preliminary Rulesets + +Complete after Phase 3 workflows have run successfully but before final enforcement: + +1. Enable squash merging and disable merge commits for the repository. Rebase merging may remain enabled only if maintainers preserve conventional commit subjects; squash-only is preferred. +2. Enable automatic deletion of ordinary head branches if desired, but do not rely on it for protected automation branch cleanup. +3. In Dependabot repository settings, enable grouped security updates by ecosystem where GitHub exposes that option. Security updates that GitHub schedules independently remain the only permitted exception to the two routine version-update PR streams. +4. Create or update a `dev` branch ruleset: + - Require pull requests before merging. + - Require at least one approval if the repository has an independent reviewer; otherwise document the single-maintainer exception. + - Dismiss stale approvals on new commits. + - Require conversation resolution. + - Require `Verification` and `Validate PR title` checks to pass. + - Require branches to be up to date before merging. + - Block force pushes and branch deletion. + - Require linear history. +5. Create or update a `main` branch ruleset with the same controls. +6. Add the Release Automation App as the only bypass actor for the `main` ruleset, with bypass always allowed only if required for semantic-release's release commit. Do not add GitHub Actions or the maintainer as a broad bypass actor. +7. Do not grant the App bypass on `dev`; generated sync PRs must pass normal review/checks. +8. Keep release/hotfix wildcard behavior aligned with CI triggers; do not allow direct merge to `main` without checks. +9. Test rules using a non-release branch before the controlled release. + +GitHub only allows selecting required checks that have reported recently. If `Verification` or `Validate PR title` is absent, first run the updated workflows on a draft PR, then return to the ruleset. + +### M-005: Verify External Configuration + +Record non-secret evidence in the Phase 5 closeout: + +- App installed repository and permission list +- Actions variable/secret names, not values +- `npm` environment branch restriction and reviewer setting +- npm trusted publisher repository/workflow/environment tuple +- `main` and `dev` required checks and bypass actors +- Squash merge configuration +- Dependabot grouped security-update setting and the observed one-PR-per-ecosystem routine update behavior +- First successful generated PR actor/checks +- First publication provenance URL or npm UI evidence + +## Implementation Strategy + +Five phases isolate unprivileged correctness, supply-chain auditing, privileged release changes, dependency policy, and external enforcement. This allows repository logic to be validated before credentials or branch rules can block normal development, while keeping each security boundary separately reviewable. + +## Phase 1: Canonical Verification and React Compatibility + +### Goal + +Establish a single unprivileged verification workflow and remove duplicated/broken React matrix updates. + +### Status and Gate + +- Status: AWAITING ACCEPTANCE +- Start requires: `Authorize Phase 1.` +- Exit requires: all Phase 1 criteria and explicit user acceptance +- Mandatory stop: request authorization for Phase 2 + +### Requirements Addressed + +FR-001, FR-002, FR-003, DR-001, DR-002, DR-004, AR-001, AR-002, AR-005, TR-001, TR-004 + +### Dependencies and Prerequisites + +- No external credentials or settings. +- Use existing installed dependencies; ask separately before any install/update. + +### Phase Task Backlog + +| Task ID | Task | Requirements | Detailed Step | Dependencies | Deliverable | Verification | Status | +| ------- | ------------------------------------------------------------- | ------------------------------ | ------------- | ------------ | ------------------------------------- | ------------------------------------------------- | -------- | +| P1-T001 | Extract pure React support module and CLI adapter | FR-003, DR-001, AR-005 | 1.1 | None | Pure functions plus safe writer | Focused Vitest | COMPLETE | +| P1-T002 | Add React tooling tests | TR-001 | 1.2 | P1-T001 | Semantic cases and non-mutation proof | `pnpm test -- test/tooling/react-support.test.ts` | COMPLETE | +| P1-T003 | Add reusable verification workflow and aggregate | FR-001, FR-002, AR-001, AR-002 | 1.3 | P1-T001 | `verify.yml` | Workflow diagnostics and draft PR | COMPLETE | +| P1-T004 | Convert CI/release callers and remove duplicate matrices | FR-001, FR-002 | 1.4 | P1-T003 | Thin callers | Draft PR check graph | COMPLETE | +| P1-T005 | Simplify React watcher and use major tags for touched actions | FR-003, AR-006 | 1.5 | P1-T001 | Metadata/docs-only watcher | Manual dry dispatch and source review | COMPLETE | + +### Package or Component Allowlist + +- Flow Stack GitHub workflows and scripts +- Tooling tests +- Package metadata only where required to expose scripts + +### File Allowlist + +- `.github/workflows/verify.yml` (new) +- `.github/workflows/ci.yml` +- `.github/workflows/release.yml` +- `.github/workflows/react-major-support.yml` +- `.github/scripts/update-react-major-support.ts` +- `.github/scripts/react-support.ts` (new) +- `test/tooling/react-support.test.ts` (new) +- `vitest.config.ts` only to discover all `test/**/*.test.ts` files while excluding jsdom/type-owned trees +- `package.json` only for a focused test/script entry if needed +- `pnpm-lock.yaml` only if an explicitly authorized dependency change becomes necessary +- This planning document for closeout + +### Explicit Denylist + +- Production source under `src/` +- Dependabot and dependency-promotion behavior +- GitHub App credentials or external settings +- npm publication +- Branch rulesets + +### Detailed Steps + +#### 1.1 Extract React support logic + +Move parsing/transformation into import-safe pure functions matching PAT-002. Validate identical React/React DOM ranges and the canonical contiguous range format. Perform all reads and transformations before writes; write package and README only when all transformations succeed. + +#### 1.2 Add focused tests + +Cover RCT-001 through RCT-003, malformed bounds, non-contiguous/unsupported syntax, mismatched peer ranges, README sentence absence, next-major-only advancement, and failed-operation non-mutation. + +#### 1.3 Create reusable verification + +Add `workflow_call`, read-only permissions, matrix preparation from package metadata, quality job, Node/React compatibility job, and `Verification` aggregate. + +Compatibility install must explicitly target the workspace root and avoid committing changes. Keep `fail-fast: false` and verify all combinations. Use maintained major-version action tags. + +#### 1.4 Convert callers + +Make `ci.yml` a trigger/concurrency wrapper that calls `verify.yml`. Make release call `verify.yml` and depend on its success before existing release behavior. Remove separate release compatibility steps and prevent duplicate CI on `main` pushes when release already invokes verification. + +#### 1.5 Simplify watcher + +The watcher updates package peers and README only. It must not stage workflow files. Preserve monthly/manual triggers and candidate branch naming during this phase; App identity changes in Phase 3. + +### Public API and Contract Impact + +- No package API impact. +- New stable CI contract: check name `Verification`. +- React peer range remains unchanged. + +### Migration and Rollback + +- Do not configure required checks yet. +- Rollback by reverting caller and reusable workflow changes together. + +### Phase Validation + +```powershell +pnpm test -- test/tooling/react-support.test.ts +pnpm run build +pnpm run typecheck +pnpm test +pnpm run lint +pnpm run format:check +``` + +Then open or update a draft PR and confirm every matrix cell and aggregate behavior. A temporary deliberate failure may be used only in an unmerged commit and must be removed before closeout. + +### Phase Acceptance Criteria + +- React tests cover all required cases and failed updates do not mutate fixtures. +- CI and release contain no duplicated React lists. +- Release waits for the same complete verification used by PRs. +- `Verification` fails when a dependency job fails/cancels/skips unexpectedly. +- No credentials or remote mutations were introduced. + +### Phase Closeout + +- Status: AWAITING ACCEPTANCE +- Authorization received: 2026-09-02 (`Plan accepted. Begin Phase 1`) +- Started on: 2026-09-02 +- Completed on: 2026-09-02 +- Plan revision at start: 3 +- Plan revision at closeout: 8 +- Requirements addressed: FR-001, FR-002, FR-003, DR-001, DR-002, DR-004, AR-001, AR-002, AR-005, AR-006, TR-001, TR-004 +- Backlog results: + - Completed: P1-T001, P1-T002, P1-T003, P1-T004, P1-T005 + - Removed by approved revision: None + - Remaining: None + - Tasks added during implementation: None +- Changed files: `.github/scripts/react-support.ts`, `.github/scripts/update-react-major-support.ts`, `.github/scripts/update-react-major-support.mjs` (removed), `.github/workflows/ci.yml`, `.github/workflows/react-major-support.yml`, `.github/workflows/release.yml`, `.github/workflows/verify.yml`, `test/tooling/react-support.test.ts`, `vitest.config.ts`, `package.json`, `pnpm-lock.yaml`, and this plan +- Public API changes: None +- Data or migration changes: None +- Semantic case results: RCT-001 through RCT-003 pass in 11 focused tests; VER-001 and VER-002 are implemented by an `always()` aggregate that requires explicit success from prepare, quality, and compatibility; REL-001 and REL-002 route release through the same reusable verification result. +- Validation: direct Node 24 TypeScript import PASS (`["18","19"]`); focused Vitest PASS (11 tests); test-project typecheck PASS; focused ESLint PASS; `pnpm run build` PASS; `pnpm run typecheck` PASS; `pnpm test` PASS (31 files, 263 tests, no type errors); `pnpm run lint` PASS; `pnpm run format:check` PASS; workspace diagnostics PASS; `git diff --check` PASS +- Automated repairs: Prettier applied to five touched files reported by the initial format check, followed by successful focused and full formatting validation +- Security and operational evidence: Reusable verification has read-only contents permission, callers pass no secrets, checkout does not persist credentials, release cannot run before reusable verification succeeds, and touched actions use maintained major-version tags. +- Manual configuration evidence: None required in Phase 1 +- Deviations: Revisions 4-7 record approved action-tag, broad test-discovery, TypeScript-script, and direct Node-declaration changes. +- Unresolved issues: GitHub-hosted matrix cells, aggregate failure/cancellation behavior, and React watcher dry dispatch require confirmation on the draft PR; local validation cannot execute GitHub's hosted job graph. Existing Vitest shutdown timeout warning remains after all 263 tests pass and is outside this phase's scope. +- Next action: STOP. Await explicit Phase 1 acceptance and Phase 2 authorization. + +## Phase 2: Supply-Chain Validation and Action Normalization + +### Goal + +Validate dependency authenticity/advisories and normalize GitHub Action references before release. + +### Status and Gate + +- Status: COMPLETE +- Start requires: Phase 1 accepted and `Authorize Phase 2.` +- Exit requires: all Phase 2 criteria and explicit user acceptance +- Mandatory stop: request manual prerequisites and Phase 3 authorization + +### Requirements Addressed + +SR-006, TR-002, AR-006, DEC-008 + +### Dependencies and Prerequisites + +- Phase 1 accepted. +- Explicit permission before adding development dependencies or updating the lockfile. + +### Phase Task Backlog + +| Task ID | Task | Requirements | Detailed Step | Dependencies | Deliverable | Verification | Status | +| ------- | --------------------------------------------------------- | -------------- | ------------- | ------------ | ------------------------------- | --------------------- | -------- | +| P2-T001 | Add package analyzers and packed-artifact validator | TR-002, TR-003 | 2.1 | Phase 1 | Removed by revision 11 | User direction | REMOVED | +| P2-T002 | Add package smoke tests | TR-003 | 2.2 | P2-T001 | Removed by revision 11 | User direction | REMOVED | +| P2-T003 | Add distinct vulnerability/signature audits | SR-006 | 2.3 | None | Accurately named workflow steps | Reusable workflow run | COMPLETE | +| P2-T004 | Integrate audit gates and normalize remaining action tags | TR-002, AR-006 | 2.4 | P2-T003 | Updated `verify.yml` | Full verification run | COMPLETE | + +### File Allowlist + +- `package.json` +- `pnpm-lock.yaml` +- `pnpm-workspace.yaml` only for the authorized `nanoid@3.3.18` and `browserslist@4.28.8` security overrides +- `.github/workflows/verify.yml` +- Other existing workflow files only for normalizing action references to major-version tags +- This planning document + +### Explicit Denylist + +- Runtime source changes +- Release credentials and App setup +- Dependency promotion +- Branch rulesets and remote publication + +### Detailed Steps + +#### 2.1 Package validation removed + +P2-T001 and P2-T002 were removed by revision 11. Do not add package validation scripts, analyzer dependencies, packed-consumer wrappers, or calling package scripts. `package.json` is the source of truth. + +#### 2.3 Split audits + +Run `pnpm audit` as vulnerability advisory audit and `npm audit signatures` as signature verification after frozen install. If signature verification cannot consume the pnpm lockfile, stop for plan revision; do not silently drop or relabel the control. + +#### 2.4 Integrate gates + +Extend verification quality checks with both audits and normalize every third-party action in all workflow files to a maintained major-version tag from its established publisher. + +### Public API and Contract Impact + +- No runtime API change. + +### Migration and Rollback + +- Remove audit workflow steps together if the controls are incompatible and revise the plan rather than weakening their labels or behavior. + +### Phase Validation + +```powershell +pnpm run build +pnpm run typecheck +pnpm test +pnpm run lint +pnpm run format:check +``` + +Also validate both audit steps in GitHub's clean runner environment. + +### Phase Acceptance Criteria + +- Both audit controls run and are accurately named. +- All actions use reviewed major-version tags and are covered by the grouped GitHub Actions Dependabot policy. +- Full reusable verification passes. + +### Phase Closeout + +- Status: AWAITING ACCEPTANCE +- Authorization received: 2026-09-02 (`Phase 1 accepted. Authorize Phase 2`) +- Started on: 2026-09-02 +- Completed on: 2026-09-02 +- Plan revision at start: 9 +- Plan revision at closeout: 13 +- Requirements addressed: SR-006, TR-002, AR-006, DEC-008 +- Backlog results: + - Completed: P2-T003, P2-T004 + - Removed by approved revision: P2-T001 and P2-T002 because package validation is not required for this single-package repository + - Remaining: None + - Tasks added during implementation: None +- Changed files: `.github/workflows/verify.yml`, `.github/workflows/pr-title.yml`, `pnpm-workspace.yaml`, `pnpm-lock.yaml`, and this plan +- Public API changes: None +- Data or migration changes: None +- Semantic case results: vulnerability and signature controls are distinct and fail closed; all third-party Actions use maintained major-version tags. +- Validation: `pnpm audit` PASS (no known vulnerabilities); `npm audit signatures` PASS (2,555 signed packages and 573 attestations); frozen lockfile PASS; patched `nanoid@3.3.18` and `browserslist@4.28.8` resolutions confirmed; build PASS; typecheck PASS; tests PASS (31 files, 263 tests, no type errors); lint PASS; format check PASS; workspace diagnostics PASS; `git diff --check` PASS +- Automated repairs: Prettier applied to this plan after revisions 12 and 13 +- Security and operational evidence: The initial advisory audit failed on three high-severity transitive advisories. Authorized overrides upgraded `nanoid` from 3.3.17 to 3.3.18 and `browserslist` from 4.28.4 to 4.28.8; the audit then passed. Signature verification remained successful. +- Manual configuration evidence: None required in Phase 2 +- Deviations: Revisions 10-11 removed the inapplicable package-validation pattern; revision 12 authorized transitive security remediation. +- Unresolved issues: The updated reusable workflow still requires a successful GitHub-hosted run to confirm clean-runner audit and aggregate behavior. The existing Vitest shutdown timeout warning remains after all tests pass and is outside this phase's scope. +- Next action: STOP. Await explicit Phase 2 acceptance, completion of M-001 through M-003, and Phase 3 authorization. + +## Phase 3: Credentialed Release and Generated-PR Automation + +### Goal + +Harden npm publishing and repository mutation with protected OIDC publishing and a least-privilege GitHub App. + +### Status and Gate + +- Status: COMPLETE +- Start requires: Phase 2 accepted, M-001 through M-003 complete, and `Authorize Phase 3.` +- Exit requires: dry-run/generated-PR evidence and explicit user acceptance +- Mandatory stop: request authorization for Phase 4 + +### Requirements Addressed + +FR-003, FR-005, AR-003, AR-004, SR-001 through SR-005, SR-007, OR-001, OR-003 + +### Dependencies and Prerequisites + +- GitHub App installed; variable and secret names configured. +- Protected `npm` environment configured. +- npm Trusted Publisher configured. +- No credentials shared with the implementing agent. + +### Phase Task Backlog + +| Task ID | Task | Requirements | Detailed Step | Dependencies | Deliverable | Verification | Status | +| ------- | -------------------------------------------------------- | ---------------------- | ------------- | ------------------ | ---------------------------------- | ----------------------- | -------- | +| P3-T001 | Harden release checkout/permissions/environment | SR-001, SR-002 | 3.1 | Manual M-002/M-003 | Least-privilege release job | Workflow review/dry run | COMPLETE | +| P3-T002 | Add App token and temporary semantic-release auth | SR-003, SR-004 | 3.2 | Manual M-001 | App-authenticated release mutation | Dry run/log review | COMPLETE | +| P3-T003 | Convert sync PR to App identity | FR-005, SR-003, SR-007 | 3.3 | P3-T002 | Checked sync PR | Controlled no-op/PR | COMPLETE | +| P3-T004 | Convert React PR to App identity and collision-safe refs | FR-003, SR-003, SR-007 | 3.4 | P3-T002 | Checked React PR | Controlled dispatch | COMPLETE | +| P3-T005 | Move PR title validation to unprivileged trigger | FR-006, SR-005 | 3.5 | None | `pull_request` title check | Draft PR | COMPLETE | + +### File Allowlist + +- `.github/workflows/release.yml` +- `.github/workflows/react-major-support.yml` +- `.github/workflows/pr-title.yml` +- `package.json` for explicit provenance metadata if supported/required +- `release.config.mjs` only for token/provenance behavior required by the selected semantic-release version +- This planning document + +### Explicit Denylist + +- Secret values +- AWS/CodeArtifact configuration +- Long-lived npm tokens +- Dependabot promotion +- Branch ruleset enforcement before checks are proven +- Runtime source + +### Detailed Steps + +#### 3.1 Harden release boundary + +Set checkout credential persistence false, make job permissions explicit, attach only the mutation/publish job to environment `npm`, and scope `id-token: write` to that job. Verification receives no environment or secrets. + +#### 3.2 Authenticate semantic-release + +Create the App token immediately before release. Supply it only to semantic-release using process-scoped temporary Git authentication as in PAT-003. Preserve package version/changelog commit, tag, npm publish, and GitHub Release behavior. + +Add a manual dry-run input/path that runs semantic-release dry-run without publishing or remote mutation. Dry-run behavior must be visibly distinct and cannot accidentally reach the real release step. + +#### 3.3 Harden sync PR + +Use App token, read-only workflow token defaults, duplicate PR detection, and successful no-op for no diff. The App-created PR must target `dev`, use a conventional title, and trigger checks. + +#### 3.4 Harden React PR + +Use App token and GitHub API ref creation with expected base SHA. Refuse overwrite of an existing branch at unexpected SHA. Remove `checkout -B`, force push, and workflow-file staging. + +#### 3.5 Reduce PR-title trust + +Use `pull_request` because validation needs no target-branch secrets or write operations. Preserve draft/release/hotfix policy unless Phase 5 documentation alignment requires an approved change. + +### Public API and Contract Impact + +- No package API impact. +- Release requires external App/environment/Trusted Publisher configuration. + +### Migration and Rollback + +- Keep the current release workflow commit available for revert. +- If App authentication fails, stop release; do not restore persisted credentials or PATs. +- If Trusted Publishing fails, stop and correct external configuration; do not add `NPM_TOKEN` without plan revision. + +### Phase Validation + +```powershell +pnpm run build +pnpm run typecheck +pnpm test +pnpm run lint +pnpm run format:check +``` + +External checks: + +1. Run release dry-run from the intended workflow. +2. Dispatch React watcher in a no-op state. +3. If a safe candidate fixture/branch is approved, prove an App-created PR triggers `Verification` and PR title checks. +4. Inspect logs for token/header leakage. + +### Phase Acceptance Criteria + +- Verification receives no privileged token/environment. +- Release checkout has no persisted credentials. +- App token exists only in mutation steps. +- Dry-run cannot publish or push. +- App-created PRs trigger normal checks. +- No long-lived npm token exists in repository workflow configuration. + +### Phase Closeout + +- Status: AWAITING ACCEPTANCE +- Authorization received: 2026-09-02 (`Phase 2 accepted. Proceed with phase 3`) +- Started on: 2026-09-02 +- Completed on: 2026-09-02 +- Plan revision at start: 14 +- Plan revision at closeout: 16 +- Requirements addressed: FR-003, FR-005, FR-006, AR-003, AR-004, SR-001 through SR-005, SR-007, OR-001, OR-003 +- Backlog results: + - Completed: P3-T001, P3-T002, P3-T003, P3-T004, P3-T005 + - Removed by approved revision: None + - Remaining: None + - Tasks added during implementation: None +- Changed files: `.github/workflows/release.yml`, `.github/workflows/react-major-support.yml`, `.github/workflows/pr-title.yml`, `release.config.mjs`, and this plan +- Public API changes: None +- Data or migration changes: None +- Semantic case results: release publication is bound to the verified `main` SHA and protected `npm` environment; analysis-only dry run uses a local bare remote, no credential/OIDC/environment, production release rules, and no mutating plugins; sync PR creation validates repository and current `main` SHA; React automation validates the exact `dev` base, generated tree, existing branch parent/tree, and existing PR repository/ref/SHA; PR-title validation uses `pull_request`. +- Validation: focused workflow diagnostics PASS; focused Prettier PASS; `release.config.mjs` ESLint PASS; analysis-only runtime assertion PASS (`chore(deps)` remains patch and only analyzer/notes plugins load); installed semantic-release CLI options confirmed; security and correctness reviews completed and findings repaired; `pnpm run build` PASS; `pnpm run typecheck` PASS; `pnpm test` PASS (31 files, 263 tests, no type errors); `pnpm run lint` PASS; `pnpm run format:check` PASS; workspace diagnostics PASS; major Action tag scan PASS; forbidden mutation-token/force-push/persisted-credential/privileged-trigger/skip-directive scan PASS; `git diff --check` PASS +- Automated repairs: Prettier applied to the React workflow and this plan; the malformed intermediate React YAML edit was atomically reconstructed before further implementation and passed diagnostics/formatting afterward. +- Security and operational evidence: only the real release job has `environment: npm` and `id-token: write`; verification and dry run receive no secrets or environment; checkouts do not persist credentials; App tokens are minted immediately before mutation and injected only into the relevant release/PR step; Git authentication is process scoped and masked; no `NPM_TOKEN` exists; release commits no longer suppress generated PR checks with `[skip ci]`; generated branch/PR state fails closed on unexpected SHAs. +- Manual configuration evidence: M-001 confirmed with the shared App installed on Flow Stack and Actions variable `RELEASE_AUTOMATION_APP_ID` plus secret `RELEASE_AUTOMATION_PRIVATE_KEY`; M-002 confirmed with environment `npm` restricted to `main`; M-003 confirmed with npm Trusted Publisher tuple `clalexander/flow-stack`, workflow `release.yml`, environment `npm`. No values or credentials were disclosed. +- Deviations: Revision 14 clarified that the App is a shared account-level identity installed only on selected repositories. No Phase 3 scope deviation. +- Unresolved issues: Hosted evidence remains required: dispatch the release dry run from `main`; dispatch the React watcher in its current no-op state; inspect logs for credential/header leakage; and, when a safe candidate exists, confirm an App-created PR runs `Verification` and `Validate PR title`. A controlled real release and npm provenance remain separately authorized Phase 5 evidence. The existing Vitest shutdown timeout warning remains after all tests pass. The optional direct YAML parser was unavailable because `yaml` is not a direct dependency; VS Code workflow diagnostics and Prettier parsing passed. +- Next action: STOP. Await hosted Phase 3 evidence, explicit Phase 3 acceptance, and Phase 4 authorization. + +## Phase 4: Dependabot Grouping, Promotion, and Policy + +### Goal + +Consolidate routine updates into one npm PR and one GitHub Actions PR, then promote either reviewed group through the immutable dependency-promotion pattern. + +### Status and Gate + +- Status: COMPLETE +- Start requires: Phase 3 accepted and `Authorize Phase 4.` +- Exit requires: event/filter evidence and explicit user acceptance +- Mandatory stop: request Phase 5 authorization + +### Requirements Addressed + +FR-004, FR-007, DR-003, DR-005, SR-007, OR-001, DEC-006 + +### Dependencies and Prerequisites + +- Release Automation App proven in Phase 3. +- `dev` remains Dependabot target. + +### Phase Task Backlog + +| Task ID | Task | Requirements | Detailed Step | Dependencies | Deliverable | Verification | Status | +| ------- | ---------------------------------------------------------------------------------------------- | ----------------------- | ------------- | ------------ | ---------------------------------------------- | --------------------------------- | -------- | +| P4-T001 | Add one catch-all group and one-PR limit per ecosystem, plus cooldowns and compatibility holds | FR-004, DR-005, DEC-006 | 4.1 | None | Updated policy | Config diagnostics/PR observation | COMPLETE | +| P4-T002 | Add grouped npm/Actions promotion workflow | FR-007, DR-003 | 4.2 | Phase 3 | Draft fixed-SHA PR automation | Controlled event/run | COMPLETE | +| P4-T003 | Add guarded promotion branch cleanup | SR-007 | 4.3 | P4-T002 | Exact-SHA deletion | Controlled merged test PR | COMPLETE | +| P4-T004 | Resolve pnpm release-age policy | DEC-006 | 4.4 | P4-T001 | Active policy or removed ineffective exception | Config review | COMPLETE | + +### File Allowlist + +- `.github/dependabot.yml` +- `.github/workflows/dependency-release.yml` (new) +- `pnpm-workspace.yaml` +- Documentation sections directly describing dependency policy +- This planning document + +### Explicit Denylist + +- Auto-merge +- Per-dependency or per-action Dependabot PR groups +- A cross-ecosystem npm/Actions PR, which Dependabot does not support +- Product dependencies unrelated to policy configuration +- Release engine changes +- Branch ruleset enforcement + +### Detailed Steps + +#### 4.1 Add Dependabot policy + +Replace the production/development npm groups with one group named `npm-dependencies` using `patterns: ['*']`. Include every eligible npm update type in that group and set the npm ecosystem's `open-pull-requests-limit` to `1`. Keep explicit React, React DOM, and React type major ignores because the dedicated compatibility watcher owns those upgrades. Mirror that ownership in `pnpm-workspace.yaml` through `updateConfig.ignoreDependencies`, which applies only to a bare `pnpm update`; naming a package explicitly still updates it, so adopting a new React major is never blocked. Keep the npm group's conventional commit prefix and scope so Dependabot emits `chore(deps):` when the group contains a production dependency and `chore(deps-dev):` when it contains only development dependencies. A development-only group intentionally produces no release, and the promotion workflow mirrors whichever scope Dependabot used. + +Add one GitHub Actions group named `github-actions` using `patterns: ['*']` and set that ecosystem's `open-pull-requests-limit` to `1`. Its title must remain `ci(deps):` and must not request an npm release. Dependabot cannot combine ecosystems into one PR, so these two group PRs are the complete routine update surface. + +Add cooldown defaults of 3 days, major 7, minor 3, and patch 2 as adopted from the reference monorepo. Add only compatibility ignores supported by current Flow Stack evidence; do not copy `type-fest` or monorepo-specific exceptions. Scheduled security updates that GitHub cannot combine with ordinary version updates are an explicit platform exception; enable grouped security updates per ecosystem in repository settings where available, but never split routine version updates into per-package PRs to emulate them. + +#### 4.2 Add promotion workflow + +Use `pull_request_target` only for merged-event metadata and GitHub API calls; never checkout or execute PR code. Apply PAT-004 predicates for either configured group. Use App token and fixed merge SHA. Open a draft conventional-title PR to `main` with source ecosystem/group, source PR URL, and snapshot warning. + +#### 4.3 Guard cleanup + +On merged promotion PRs, delete only names matching `^release/dependencies-[0-9]+$` and only when the current ref SHA equals the merged PR head SHA. + +#### 4.4 Resolve release-age configuration + +Either configure a real `minimumReleaseAge` consistent with the cooldown policy or remove the ineffective exclusion. This plan selects removal unless a concrete package requires an age bypass during implementation; adding a real delay changes install behavior and requires a plan revision. + +### Public API and Contract Impact + +- No package API impact. +- The single grouped npm PR contains production and development updates and gains a draft promotion PR after merge to `dev`. +- The single grouped GitHub Actions PR also gains a draft promotion PR after merge to `dev` but does not itself request an npm release. + +### Migration and Rollback + +- Introduce the `pull_request_target` workflow to the default branch before expecting events, then sync it to `dev`. +- Disable by reverting the workflow; never delete generated branches without SHA checks. + +### Phase Validation + +```powershell +pnpm run format:check +pnpm run lint +``` + +Controlled GitHub cases must cover DEP-001 through DEP-007. If creating real test PRs is undesirable, keep the workflow unenforced and Phase 4 unaccepted until equivalent evidence exists. + +### Phase Acceptance Criteria + +- Dependabot has exactly one catch-all npm group and one catch-all GitHub Actions group, with an open-PR limit of one for each ecosystem. +- Eligible minor, patch, and major updates do not escape their ecosystem group; explicit React major ignores remain under the compatibility watcher. +- Merging either grouped PR creates one draft fixed-SHA promotion PR. +- npm group titles preserve Dependabot's scope, so `chore(deps)` promotes a patch release and a development-only `chore(deps-dev)` promotes without releasing; Actions group titles are non-releasing `ci(deps)` commits. +- Existing unexpected branch state cannot be overwritten or deleted. +- App-created promotion PR runs normal checks. + +### Phase Closeout + +- Status: AWAITING ACCEPTANCE +- Authorization received: 2026-09-02 (`Phase 3 accepted. Proceed with phase 4`) +- Started on: 2026-09-02 +- Completed on: 2026-09-02 +- Plan revision at start: 17 +- Plan revision at closeout: 20 +- Requirements addressed: FR-004, FR-007, DR-003, DR-005, SR-007, OR-001, DEC-006 +- Backlog results: + - Completed: P4-T001, P4-T002, P4-T003, P4-T004 + - Removed by approved revision: None + - Remaining: None + - Tasks added during implementation: None +- Changed files: `.github/dependabot.yml`, `.github/workflows/dependency-release.yml` (new), `pnpm-workspace.yaml`, and this plan +- Public API changes: None +- Data or migration changes: None +- Semantic case results: DEP-001 and DEP-002 create one draft fixed-SHA promotion PR per ecosystem; DEP-003 reuses a branch already at the merge SHA and no-ops on a matching open PR; DEP-004 hard-fails on a moved branch; DEP-005 deletes only on exact merged-head SHA; DEP-006 refuses a moved or misnamed branch; DEP-007 no-ops because non-configured group branches never satisfy the anchored job predicate. +- Validation: focused Prettier PASS; `pnpm run format:check` PASS; `pnpm run lint` PASS; workspace diagnostics PASS; `git diff --check` PASS; observed repository refs and commit titles confirmed the corrected branch and scope assumptions; security and correctness reviews completed and blocking findings repaired +- Automated repairs: Prettier applied to this plan after the revision 17 checkpoint +- Security and operational evidence: `pull_request_target` is used only for merged-event metadata and GitHub API calls, with no checkout or execution of pull request code; every untrusted event field is passed through `env:` and never interpolated into a shell body; both jobs set `permissions: {}` so the ambient workflow token has no scopes; mutation uses ephemeral App tokens with per-job permissions; fork pull requests are excluded; the merge commit must be a 40-character SHA contained in `dev`; promotion is skipped when `main` already contains it; branch creation and deletion require exact SHA matches; promotion PRs are drafts, so nothing auto-merges. +- Manual configuration evidence: None required in Phase 4 +- Deviations: Revision 19 accepts that the npm ecosystem keeps `commit-message.prefix: chore` with `include: scope`, so Dependabot's own scope is preserved and a development-only group remains `chore(deps-dev)` and intentionally does not release; DR-005, DEC-006, step 4.1, and the Phase 4 acceptance criterion were aligned, and the promotion workflow mirrors the source scope rather than forcing `chore(deps)`. `pnpm-workspace.yaml` also gained `updateConfig.ignoreDependencies` holds for ESLint 10 and TypeScript, verified against the settings list recognized by the pinned pnpm 10 release; the pnpm 11 spelling `update.ignoreDeps` is inert on pnpm 10. Cooldown is applied to the npm ecosystem only, matching the reference monorepo precedent, because the official option reference could not be reached to confirm cooldown support for the `github-actions` ecosystem. A title whose scope is not valid for its group is a hard failure rather than a no-op; this is an invariant beyond DEP-007 and is intentionally visible. Revision 20 adds `react`, `react-dom`, `@types/react`, and `@types/react-dom` to `updateConfig.ignoreDependencies` so the watcher owns React majors for manual updates as well as Dependabot; because that list has no version granularity it also suppresses React patch bumps during a bare `pnpm update`, which the grouped Dependabot pull request still delivers. +- Unresolved issues: Hosted evidence remains required for DEP-001 through DEP-007. Confirm on the first grouped run that real branch names are `dependabot/npm_and_yarn/dev/npm-dependencies-` and `dependabot/github_actions/dev/github-actions-` and that npm titles carry the expected `chore(deps):` or `chore(deps-dev):` scope. Dependabot reads `.github/dependabot.yml` from the default branch, the promotion job is read from `dev`, and the cleanup job is read from `main`, so all three must land before events behave as designed. Confirm the Dependabot configuration reports no schema error. Existing per-dependency Dependabot pull requests predate grouping and should be closed manually. With `target-branch: dev`, GitHub may not raise security update pull requests at all; if it does, ungrouped security branches are intentionally not promoted and require manual promotion. A promotion branch is a full `dev` snapshot, so an Actions promotion can carry unrelated releasable commits; the pull request body states this. `pr-title.yml` skips `release/**` heads, so a manually edited promotion title is not validated. +- Next action: STOP. Await hosted Phase 4 evidence, explicit Phase 4 acceptance, and Phase 5 authorization. + +## Phase 5: Branch Enforcement, Documentation, and End-to-End Proof + +### Goal + +Make repository policy enforce the verified workflow contracts, document operations, and prove one complete controlled release path. + +### Status and Gate + +- Status: COMPLETE +- Start requires: Phase 4 accepted and `Authorize Phase 5.` +- A real npm release requires separate explicit authorization at the point of execution. +- Exit requires: all initiative acceptance criteria and explicit final acceptance + +### Requirements Addressed + +SR-008, OR-002, PR-003, FR-006, all acceptance criteria + +### Dependencies and Prerequisites + +- M-001 through M-003 complete and Phase 3 proven. +- Stable checks have reported in GitHub. +- User available to perform M-004 and verify M-005. + +### Phase Task Backlog + +| Task ID | Task | Requirements | Detailed Step | Dependencies | Deliverable | Verification | Status | +| ------- | ------------------------------------------------------------ | --------------- | ------------- | --------------- | ---------------------------- | ------------------------- | -------- | +| P5-T001 | Write release and CI operations documentation | OR-002, PR-003 | 5.1 | Prior phases | Durable runbooks | Documentation review | COMPLETE | +| P5-T002 | Align contributor/PR guidance | FR-006, ASM-001 | 5.2 | P5-T001 | Conventional/squash guidance | Documentation review | COMPLETE | +| P5-T003 | Configure and test branch rulesets | SR-008 | 5.3 | Stable checks | M-004 evidence | Controlled rules tests | DEFERRED | +| P5-T004 | Execute final verification and controlled release acceptance | All | 5.4 | P5-T001-P5-T003 | M-005 and final closeout | Full command/run evidence | DEFERRED | + +### File Allowlist + +- `docs/README.md` (new documentation index) +- `docs/development/README.md` (new development index) +- `docs/development/ci.md` (new) +- `docs/development/release.md` (new) +- `CONTRIBUTING.md` +- `.github/pull_request_template.md` +- `README.md` only for links/brief release compatibility corrections +- This planning document +- External GitHub/npm settings listed in M-004/M-005 + +### Explicit Denylist + +- Product source/API changes +- New release behavior beyond prior accepted phases +- Broad ruleset bypass actors +- Secret/token disclosure +- Unrelated documentation reorganization + +### Detailed Steps + +#### 5.1 Document operations + +Document workflow topology, required checks, React source of truth, audits, release classification, environment/App/Trusted Publisher prerequisites, dependency promotion, hotfixes, back-merge, partial failure recovery, patch rollback, npm deprecation, App key rotation, and external-setting verification. + +#### 5.2 Align contributor guidance + +Replace non-conventional examples, explain squash-title release semantics, remove manual version/changelog instructions, and make PR template commands check-only (`format:check`, not mutating `format`). Confirm squash-only merge setting or stop for plan revision if commit-level enforcement is needed. + +#### 5.3 Enforce branch rules + +User completes M-004. Test direct push rejection, missing-check rejection, force-push/deletion protection, App release bypass, and no App bypass on `dev`. Do not weaken rules to make a failed test pass; correct workflow identity/check naming. + +#### 5.4 Final proof + +Run all local/reusable verification, controlled generated PRs, and release dry-run. With separate explicit user authorization, perform one real release and verify npm provenance, package consumers, GitHub tag/release, changelog/version commit, and checked sync PR. + +### Public API and Contract Impact + +- No runtime API change. +- Repository contribution and release policy becomes explicit and enforced. + +### Migration and Rollback + +- Export or record prior ruleset configuration before changes. +- If enforcement blocks valid workflows, disable only the affected new required check temporarily, document the exception, and revise the plan; do not add broad bypass. +- A bad publication is corrected by patch release or deprecation, never normal deletion. + +### Phase Validation + +```powershell +pnpm run build +pnpm run typecheck +pnpm test +pnpm run lint +pnpm run format:check +``` + +GitHub/npm validation follows active AC-001 through AC-007 and M-005. + +### Phase Acceptance Criteria + +- Both branch rulesets enforce stable checks and block unsafe mutations. +- Only the App has the documented `main` bypass. +- Contributor and release documentation matches executable behavior. +- Generated PRs and release dry-run pass. +- A separately authorized release proves npm provenance and all expected artifacts. +- This plan contains final evidence and no unresolved gate. + +### Phase Closeout + +- Status: COMPLETE +- Authorization received: 2026-09-03 (`Phase 4 accepted. Proceed with phase 5`) +- Acceptance received: 2026-09-03 (`Phase 5 accepted. Mark as completed.`) +- Started on: 2026-09-03 +- Completed on: 2026-09-03 +- Plan revision at start: 21 +- Plan revision at closeout: 23 +- Requirements addressed: OR-002, PR-003, and FR-006 through documentation. SR-008 remains maintainer configuration work and was not executed. +- Backlog results: + - Completed: P5-T001, P5-T002 + - Deferred by user acceptance: P5-T003 and P5-T004 + - Remaining: None within this initiative + - Tasks added during implementation: None +- Changed files: `docs/README.md`, `docs/development/README.md`, `docs/development/ci.md`, `docs/development/release.md`, `CONTRIBUTING.md`, `.github/pull_request_template.md`, `README.md`, and this plan, which moved from `docs/development/` to `docs/plans/` +- Public API changes: None +- Data or migration changes: None +- Semantic case results: None were executed in this phase. The new documentation records the semantics proven in Phases 1 through 4. +- Validation: `pnpm run format:check` PASS; `pnpm run lint` PASS; workspace diagnostics PASS; `git diff --check` PASS; documentation cross-link check PASS; credential pattern scan of `docs/` PASS with no key material, token, or authorization header +- Automated repairs: Prettier applied to the new documentation and to this plan +- Security and operational evidence: Before publication, the local filesystem path in the planning baseline was replaced with a repository reference, and named third-party repository identifiers were generalized to an internal reference monorepo. Documented secret and variable names are identifiers only and disclose no values. +- Manual configuration evidence: None. M-004 and M-005 were not performed, so branch rulesets, required checks, bypass actors, and publication provenance are unverified. +- Deviations: P5-T003 and P5-T004 were accepted without execution. AC-003, AC-005, and AC-007 therefore carry no recorded evidence, and the Final Definition of Done is satisfied only for the automation this initiative implemented. +- Unresolved issues: No branch ruleset is configured, so no required check is enforced and the documented `main` bypass does not yet exist. Outstanding hosted evidence from Phases 3 and 4 and a controlled release are now ordinary maintenance work rather than initiative work. +- Final document disposition: Retained as a historical initiative record at `docs/plans/flow-stack-ci-modernization-plan.md`. Durable operations documentation lives under `docs/development/`. +- Next action: None. The initiative is closed. + +## Cross-Phase Dependencies + +| Dependency | Producer Phase | Consumer Phase | Contract/Gate | +| ----------------------------------------- | -------------- | -------------- | ------------------------------------- | +| Derived React matrix and stable aggregate | 1 | 2-5 | Phase 1 acceptance | +| Package and audit gates | 2 | 3-5 | Phase 2 acceptance | +| Proven App/OIDC identities | Manual + 3 | 4-5 | Phase 3 acceptance | +| Dependabot promotion | 4 | 5 | Phase 4 acceptance | +| Stable reported checks | 1-4 | 5 | Required before ruleset configuration | + +## Cross-Phase Drift Guards + +Stop and revise this plan when: + +1. A required edit is outside the active phase allowlist. +2. Current source contradicts a foundational plan assumption. +3. A shared test exposes a contract defect in an earlier accepted phase. +4. GitHub cannot express the aggregate/reusable workflow relationship as planned. +5. React peer ranges cannot be translated without weakening support semantics. +6. npm Trusted Publishing is unavailable or requires a long-lived token. +7. semantic-release cannot use App authentication while preserving current artifacts. +8. A public package API or support range must change. +9. User-authored changes overlap an in-scope file ambiguously. +10. Validation requires unrelated dependency/root configuration or machine changes. +11. Security, privacy, or operational cost exceeds approved assumptions. +12. A new foundational architectural decision is needed. +13. A required action is absent from the authorized phase backlog. +14. An out-of-scope design/behavior/intent change appears necessary. +15. Signature verification cannot validate the pnpm dependency graph. +16. Branch protection cannot distinguish the App mutation from broad bypass. +17. Repository merge policy is not squash-based and release-visible commits are not conventional. + +## Implementation Handoff Protocol + +1. Read this document in full before planning the next implementation phase. +2. Read it again before starting the authorized phase. +3. Confirm active phase, allowlist, denylist, requirements, manual prerequisites, and validation commands. +4. Confirm authorized backlog task IDs and execute only those tasks. +5. Do not rely on chat summaries as a substitute for this plan. +6. Add newly discovered in-scope work through a revision before execution; out-of-scope or intent-changing work requires explicit user direction. +7. Update this plan at every phase boundary. +8. Stop after closeout and request explicit acceptance/authorization. + +## Phase Closeout Template + +```md +### Phase N Closeout + +- Status: AWAITING ACCEPTANCE +- Authorization received: +- Started on: +- Completed on: +- Plan revision at start: +- Plan revision at closeout: +- Requirements addressed: +- Backlog results: + - Completed: + - Removed by approved revision: None / + - Remaining: None / + - Tasks added during implementation: None / +- Changed files: +- Public API changes: None /
+- Data or migration changes: None /
+- Semantic case results: +- Validation: +- Automated repairs: None / +- Security and operational evidence:
+- Manual configuration evidence: None / +- Deviations: None / +- Unresolved issues: None /
+- Next action: STOP. Await explicit acceptance and next-phase authorization. +``` + +## Final Definition of Done + +The initiative is complete only when: + +1. Every phase is explicitly accepted. +2. All active requirements and active AC-001 through AC-007 are satisfied. +3. All semantic cases pass in their required test/integration layer. +4. Full repository and GitHub quality gates pass. +5. App, environment, Trusted Publisher, and ruleset evidence is recorded without secrets. +6. npm provenance and expected release artifacts are verified through a separately authorized release. +7. Documentation reflects actual behavior and recovery paths. +8. This plan contains final evidence and no unresolved gate. +9. Final document disposition is explicitly recorded. + +Closed on 2026-09-03 by user acceptance with conditions 2, 5, and 6 unmet, because P5-T003 and P5-T004 were deferred. AC-003, AC-005, and AC-007 have no recorded evidence, and branch rulesets, hosted workflow runs, and a controlled release remain outstanding as maintenance work. + +## Plan Readiness Checklist + +- [x] User and environment requirements are consolidated with stable IDs. +- [x] Current-state claims have repository evidence. +- [x] Foundational architecture and naming are settled. +- [x] Core patterns and representative contracts are explicit. +- [x] Observable semantics and error mappings are defined. +- [x] Security, migration, compatibility, and operations are addressed. +- [x] Manual App, npm, environment, and branch-protection steps are explicit. +- [x] Phases have conceptual boundaries, task backlogs, allowlists, denylists, gates, and stops. +- [x] Every implementation action maps to a stable phase task. +- [x] Actual current validation commands are included; future commands are introduced before use. +- [x] Acceptance criteria are observable and mapped to requirements. +- [x] Drift guards and scope exclusions are explicit. +- [x] A less-capable implementation agent should not need to re-derive core design. +- [x] A full reread is required before planning or starting each phase. + +## Handoff to Implementing Agent + +- Canonical plan: `docs/plans/flow-stack-ci-modernization-plan.md` +- Authorized phase: None; the initiative is closed +- Plan version/revision: 5.2/23 +- Baseline commit: `525e8d7817b205d39b33f37b938655a1a8cad775` +- Mandatory first action: Read this plan in full before reopening any phase. +- Active phase backlog: None +- Stop condition: Reopening this initiative requires a documented revision and explicit authorization. +- Prohibited action: Do not treat P5-T003 or P5-T004 as delivered. They were accepted without execution, and the branch rulesets and controlled release they cover remain outstanding. diff --git a/package.json b/package.json index e2af8b8..6d9db6f 100644 --- a/package.json +++ b/package.json @@ -30,9 +30,14 @@ "types": "./dist/index.d.ts", "exports": { ".": { - "types": "./dist/index.d.ts", - "import": "./dist/index.js", - "require": "./dist/index.cjs" + "import": { + "types": "./dist/index.d.ts", + "default": "./dist/index.js" + }, + "require": { + "types": "./dist/index.d.cts", + "default": "./dist/index.cjs" + } }, "./package.json": "./package.json" }, @@ -68,6 +73,7 @@ "@semantic-release/git": "^10.0.1", "@testing-library/react": "^16.3.2", "@testing-library/user-event": "^14.6.1", + "@types/node": "24.0.0", "@types/react": "^18.3.31", "@types/react-dom": "^18.3.7", "@vitest/coverage-v8": "^3.2.6", diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 57c2342..3ce198e 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -8,8 +8,9 @@ overrides: brace-expansion@^1: 1.1.18 brace-expansion@^2: 2.1.4 brace-expansion@^5: 5.0.9 + browserslist: 4.28.8 js-yaml: 4.3.1 - nanoid: 3.3.17 + nanoid: 3.3.18 postcss: 8.5.23 undici: 7.29.0 @@ -32,6 +33,9 @@ importers: '@testing-library/user-event': specifier: ^14.6.1 version: 14.6.1(@testing-library/dom@10.4.1) + '@types/node': + specifier: 24.0.0 + version: 24.0.0 '@types/react': specifier: ^18.3.31 version: 18.3.31 @@ -40,7 +44,7 @@ importers: version: 18.3.7(@types/react@18.3.31) '@vitest/coverage-v8': specifier: ^3.2.6 - version: 3.2.6(vitest@3.2.6(jsdom@29.1.1)) + version: 3.2.6(vitest@3.2.6(@types/node@24.0.0)(jsdom@29.1.1)) eslint: specifier: ^9.39.4 version: 9.39.4 @@ -97,7 +101,7 @@ importers: version: 8.62.0(eslint@9.39.4)(typescript@6.0.3) vitest: specifier: ^3.2.6 - version: 3.2.6(jsdom@29.1.1) + version: 3.2.6(@types/node@24.0.0)(jsdom@29.1.1) packages: @@ -1061,6 +1065,9 @@ packages: '@types/json5@0.0.29': resolution: {integrity: sha512-dRLjCWHYg4oaA77cxO64oO+7JwCwnIzkZPdrrC71jQmQtlhM556pwKo5bUzqvZndkVbeFLIIi+9TC40JNF5hNQ==} + '@types/node@24.0.0': + resolution: {integrity: sha512-yZQa2zm87aRVcqDyH5+4Hv9KYgSdgwX1rFnGvpbzMaC7YAljmhBET93TPiTd3ObwTL+gSpIzPKg5BqVxdCvxKg==} + '@types/normalize-package-data@2.4.4': resolution: {integrity: sha512-37i+OaWTh9qeK4LSHPsyRC7NahnGotNuZvjLSgcPzblpHB3rrCJxAOgI5gCdKm7coonsaX1Of0ILiTcnZjbfxA==} @@ -1437,8 +1444,8 @@ packages: resolution: {integrity: sha512-BLrgEcRTwX2o6gGxGOCNyMvGSp35YofuYzw9h1IMTRmKqttAZZVU67bdb9Pr2vUHA8+j3i2tJfjO6C6+4myGTA==} engines: {node: 18 || 20 || >=22} - baseline-browser-mapping@2.10.38: - resolution: {integrity: sha512-31/02mVB4yuQU6adKk5SlY6m+mxDwUq5KZkyYgnLrrKl7TEm1+3PyDtDBz2kOv/wxZz41GHsvV1A/u6RmiyBvw==} + baseline-browser-mapping@2.11.20: + resolution: {integrity: sha512-H0ulySigv6icDJ1F7SjtdCD6PrhTpdYCmP0CactWy1+ekh0AFd0o1Wn5T8b+hnTmdBx19u9yhL6wvCylXMY7zw==} engines: {node: '>=6.0.0'} hasBin: true @@ -1468,8 +1475,8 @@ packages: resolution: {integrity: sha512-yQbXgO/OSZVD2IsiLlro+7Hf6Q18EJrKSEsdoMzKePKXct3gvD8oLcOQdIzGupr5Fj+EDe8gO/lxc1BzfMpxvA==} engines: {node: '>=8'} - browserslist@4.28.4: - resolution: {integrity: sha512-MTc8i/x9jBQd1iMw2CFGS+rwMa07eYjLR0CCTLDACl9xhxy+nIs3KeML/biicXtk9JrZ6dnnTatmc7ErPXIxqw==} + browserslist@4.28.8: + resolution: {integrity: sha512-V2NpofLblG64mfOtSgDhOJESZEGogzDMBv/q+W6oc4LXWP/q75eOXoOaaOu1EOadB9U4Bwx/e0yzbvwKH8zalA==} engines: {node: ^6 || ^7 || ^8 || ^9 || ^10 || ^11 || ^12 || >=13.7} hasBin: true @@ -1497,8 +1504,8 @@ packages: resolution: {integrity: sha512-P8BjAsXvZS+VIDUI11hHCQEv74YT67YUi5JJFNWIqL235sBmjX4+qx9Muvls5ivyNENctx46xQLQ3aTuE7ssaQ==} engines: {node: '>=6'} - caniuse-lite@1.0.30001799: - resolution: {integrity: sha512-hG1bReV+OUU+MOqK4t/ZWI0tZOyz3rqS9XuhOUz1cIcbwBKjOyJEJuw9ER5JuNyqxNk8u/JUVbGibBOL1yrjFw==} + caniuse-lite@1.0.30001810: + resolution: {integrity: sha512-TITQPUkaz+aVk5GL6NhOdwk1aEaNTSDPsGFWrTuhKGtjTF70jL/Oht2W4c6rXUe5fu7Ie19VIahAXHIIiWWNeg==} chai@5.3.3: resolution: {integrity: sha512-4zNhdJD/iOjSH0A05ea+Ke6MU5mmpQcbQsSOkgdaUMJ9zTlDTD/GYlwohmIE2u0gaxHYiVHEn1Fw9mZ/ktJWgw==} @@ -1725,8 +1732,8 @@ packages: eastasianwidth@0.2.0: resolution: {integrity: sha512-I88TYZWc9XiYHRQ4/3c5rjjfgkjhLyW2luGIheGERbNQ6OY7yTybanSpDXZa8y7VUP9YmDcYa+eyq4ca7iLqWA==} - electron-to-chromium@1.5.376: - resolution: {integrity: sha512-cUVA7/RvbFTEuw/i3obUwDTRIXojaxkResf+ibByPFxjc6XK3VNtcQXV0NSbAlJ0FMjcJGgftVVB4Qo184EXvA==} + electron-to-chromium@1.5.420: + resolution: {integrity: sha512-2yD6XreGusOfNV+dUcvipJEXc3n/n7fgr7996aszTG+YY5E4mqM4tOq/3uhP129cazL9YHbVWSpc79ePotWtPA==} emoji-regex@10.6.0: resolution: {integrity: sha512-toUI84YS5YmxW219erniWD0CIVOo46xGKColeNQRgOzDorgBi1v4D71/OFzgD9GO2UGKIv1C3Sp8DAn0+j5w7A==} @@ -2678,8 +2685,8 @@ packages: mz@2.7.0: resolution: {integrity: sha512-z81GNO7nnYMEhrGh9LeymoE4+Yr0Wn5McHIZMK5cfQCl+NDX08sCZgUc9/6MHni9IWuFLm1Z3HTCXu2z9fN62Q==} - nanoid@3.3.17: - resolution: {integrity: sha512-xQLf0A3HOMlgHq0n247/LRuAOYmB7dXJ/DvAxGvsSBij45XtBSmQycu+F8ODbHwns/XyFZagyL1+J0Offw1E0g==} + nanoid@3.3.18: + resolution: {integrity: sha512-DTg4MJbGMWkfi6VZFdNt2/caMbQy4Ou+Op/hJQvGEWcnVfoA1QA+xzRKAzw9jD6+GVOOeYr/mIcuDSdug6F6+w==} engines: {node: ^10 || ^12 || ^13.7 || ^14 || >=15.0.1} hasBin: true @@ -2705,8 +2712,8 @@ packages: resolution: {integrity: sha512-pyFS63ptit/P5WqUkt+UUfe+4oevH+bFeIiPPdfb0pFeYEu/1ELnJu5l+5EcTKYL5M7zaAa7S8ddywgXypqKCw==} engines: {node: '>= 0.4'} - node-releases@2.0.48: - resolution: {integrity: sha512-1uz8041X6LoI6ZSdZacM9lVY28vuzDlSKitnpbSNK0RfKoIJkX29NBPVEFXhnuSuEOA9Ww0xnPJ+ILWbGAv8DA==} + node-releases@2.0.54: + resolution: {integrity: sha512-YHs7BmmcsdAI5Ozuf8JZo6PT0mv2GIWC9vMfvUC3dp65M8hn7Ux8CPL+2oBI7juNuj9d0ndhTcznq2ODBps9cQ==} engines: {node: '>=18'} normalize-package-data@6.0.2: @@ -3585,6 +3592,9 @@ packages: unconfig-core@7.5.0: resolution: {integrity: sha512-Su3FauozOGP44ZmKdHy2oE6LPjk51M/TRRjHv2HNCWiDvfvCoxC2lno6jevMA91MYAdCdwP05QnWdWpSbncX/w==} + undici-types@7.8.0: + resolution: {integrity: sha512-9UJ2xGDvQ43tYyVMpuHlsgApydB8ZKfVYTsLDhXkFL/6gfkp+U8xTGdh8pMJv1SpZna0zxG1DwsKZsreLbXBxw==} + undici@7.29.0: resolution: {integrity: sha512-IDxfleLmmbSskfWSUATiN1nfn2rDuvnMOqb5CWR92iIfojA0Ud+ulOAAEQ57LPr9rWmsreUyf5lwyao+7GNNVw==} engines: {node: '>=20.18.1'} @@ -3629,11 +3639,11 @@ packages: synckit: optional: true - update-browserslist-db@1.2.3: - resolution: {integrity: sha512-Js0m9cx+qOgDxo0eMiFGEueWztz+d4+M3rGlmKPT+T4IS/jP4ylw3Nwpu6cpTTP8R1MAC1kF4VbdLt3ARf209w==} + update-browserslist-db@1.3.2: + resolution: {integrity: sha512-UQ+MSxlhRm1bzjhU+DcuXfjFO1FzNtqhK5+9Yvlp90ItDLk5vT932A0rFu619nf7RVS+Y/VeaUW1jaRDqZ8VJw==} hasBin: true peerDependencies: - browserslist: '>= 4.21.0' + browserslist: 4.28.8 uri-js@4.4.1: resolution: {integrity: sha512-7rKUyy33Q1yc98pQ1DAmLtwX109F7TIfWlW1Ydo8Wl1ii1SeHieeh0HHfPeL2fMXK6z0s8ecKs9frCuLJvndBg==} @@ -3928,7 +3938,7 @@ snapshots: dependencies: '@babel/compat-data': 7.29.7 '@babel/helper-validator-option': 7.29.7 - browserslist: 4.28.4 + browserslist: 4.28.8 lru-cache: 5.1.1 semver: 6.3.1 @@ -4670,6 +4680,10 @@ snapshots: '@types/json5@0.0.29': {} + '@types/node@24.0.0': + dependencies: + undici-types: 7.8.0 + '@types/normalize-package-data@2.4.4': {} '@types/prop-types@15.7.15': {} @@ -4844,7 +4858,7 @@ snapshots: '@unrs/resolver-binding-win32-x64-msvc@1.12.2': optional: true - '@vitest/coverage-v8@3.2.6(vitest@3.2.6(jsdom@29.1.1))': + '@vitest/coverage-v8@3.2.6(vitest@3.2.6(@types/node@24.0.0)(jsdom@29.1.1))': dependencies: '@ampproject/remapping': 2.3.0 '@bcoe/v8-coverage': 1.0.2 @@ -4859,7 +4873,7 @@ snapshots: std-env: 3.10.0 test-exclude: 7.0.2 tinyrainbow: 2.0.0 - vitest: 3.2.6(jsdom@29.1.1) + vitest: 3.2.6(@types/node@24.0.0)(jsdom@29.1.1) transitivePeerDependencies: - supports-color @@ -4871,13 +4885,13 @@ snapshots: chai: 5.3.3 tinyrainbow: 2.0.0 - '@vitest/mocker@3.2.6(vite@7.3.5)': + '@vitest/mocker@3.2.6(vite@7.3.5(@types/node@24.0.0))': dependencies: '@vitest/spy': 3.2.6 estree-walker: 3.0.3 magic-string: 0.30.21 optionalDependencies: - vite: 7.3.5 + vite: 7.3.5(@types/node@24.0.0) '@vitest/pretty-format@3.2.6': dependencies: @@ -5063,7 +5077,7 @@ snapshots: balanced-match@4.0.4: {} - baseline-browser-mapping@2.10.38: {} + baseline-browser-mapping@2.11.20: {} before-after-hook@4.0.0: {} @@ -5092,13 +5106,13 @@ snapshots: dependencies: fill-range: 7.1.1 - browserslist@4.28.4: + browserslist@4.28.8: dependencies: - baseline-browser-mapping: 2.10.38 - caniuse-lite: 1.0.30001799 - electron-to-chromium: 1.5.376 - node-releases: 2.0.48 - update-browserslist-db: 1.2.3(browserslist@4.28.4) + baseline-browser-mapping: 2.11.20 + caniuse-lite: 1.0.30001810 + electron-to-chromium: 1.5.420 + node-releases: 2.0.54 + update-browserslist-db: 1.3.2(browserslist@4.28.8) cac@6.7.14: {} @@ -5123,7 +5137,7 @@ snapshots: callsites@3.1.0: {} - caniuse-lite@1.0.30001799: {} + caniuse-lite@1.0.30001810: {} chai@5.3.3: dependencies: @@ -5347,7 +5361,7 @@ snapshots: eastasianwidth@0.2.0: {} - electron-to-chromium@1.5.376: {} + electron-to-chromium@1.5.420: {} emoji-regex@10.6.0: {} @@ -6463,7 +6477,7 @@ snapshots: object-assign: 4.1.1 thenify-all: 1.6.0 - nanoid@3.3.17: {} + nanoid@3.3.18: {} napi-postinstall@0.3.4: {} @@ -6487,7 +6501,7 @@ snapshots: object.entries: 1.1.9 semver: 6.3.1 - node-releases@2.0.48: {} + node-releases@2.0.54: {} normalize-package-data@6.0.2: dependencies: @@ -6702,7 +6716,7 @@ snapshots: postcss@8.5.23: dependencies: - nanoid: 3.3.17 + nanoid: 3.3.18 picocolors: 1.1.1 source-map-js: 1.2.1 @@ -7425,6 +7439,8 @@ snapshots: '@quansync/fs': 1.0.0 quansync: 1.0.0 + undici-types@7.8.0: {} + undici@7.29.0: {} unicode-emoji-modifier-base@1.0.0: {} @@ -7475,9 +7491,9 @@ snapshots: rolldown: 1.0.0-rc.17 optional: true - update-browserslist-db@1.2.3(browserslist@4.28.4): + update-browserslist-db@1.3.2(browserslist@4.28.8): dependencies: - browserslist: 4.28.4 + browserslist: 4.28.8 escalade: 3.2.0 picocolors: 1.1.1 @@ -7494,13 +7510,13 @@ snapshots: spdx-correct: 3.2.0 spdx-expression-parse: 3.0.1 - vite-node@3.2.4: + vite-node@3.2.4(@types/node@24.0.0): dependencies: cac: 6.7.14 debug: 4.4.3 es-module-lexer: 1.7.0 pathe: 2.0.3 - vite: 7.3.5 + vite: 7.3.5(@types/node@24.0.0) transitivePeerDependencies: - '@types/node' - jiti @@ -7515,7 +7531,7 @@ snapshots: - tsx - yaml - vite@7.3.5: + vite@7.3.5(@types/node@24.0.0): dependencies: esbuild: 0.27.2 fdir: 6.5.0(picomatch@4.0.4) @@ -7524,13 +7540,14 @@ snapshots: rollup: 4.62.2 tinyglobby: 0.2.17 optionalDependencies: + '@types/node': 24.0.0 fsevents: 2.3.3 - vitest@3.2.6(jsdom@29.1.1): + vitest@3.2.6(@types/node@24.0.0)(jsdom@29.1.1): dependencies: '@types/chai': 5.2.3 '@vitest/expect': 3.2.6 - '@vitest/mocker': 3.2.6(vite@7.3.5) + '@vitest/mocker': 3.2.6(vite@7.3.5(@types/node@24.0.0)) '@vitest/pretty-format': 3.2.6 '@vitest/runner': 3.2.6 '@vitest/snapshot': 3.2.6 @@ -7548,10 +7565,11 @@ snapshots: tinyglobby: 0.2.17 tinypool: 1.1.1 tinyrainbow: 2.0.0 - vite: 7.3.5 - vite-node: 3.2.4 + vite: 7.3.5(@types/node@24.0.0) + vite-node: 3.2.4(@types/node@24.0.0) why-is-node-running: 2.3.0 optionalDependencies: + '@types/node': 24.0.0 jsdom: 29.1.1 transitivePeerDependencies: - jiti diff --git a/pnpm-workspace.yaml b/pnpm-workspace.yaml index b2eb92a..04835b1 100644 --- a/pnpm-workspace.yaml +++ b/pnpm-workspace.yaml @@ -2,13 +2,23 @@ overrides: brace-expansion@^1: 1.1.18 brace-expansion@^2: 2.1.4 brace-expansion@^5: 5.0.9 + browserslist: 4.28.8 js-yaml: 4.3.1 - nanoid: 3.3.17 + nanoid: 3.3.18 postcss: 8.5.23 undici: 7.29.0 - +updateConfig: + ignoreDependencies: + # Remove once eslint-plugin-react and eslint-plugin-jsx-a11y support ESLint 10. + - '@eslint/js' + - eslint + # Remove once typescript-eslint supports TypeScript 7. + - typescript + # React majors are owned by the React compatibility watcher. + - react + - react-dom + - '@types/react' + - '@types/react-dom' allowBuilds: esbuild: true unrs-resolver: false -minimumReleaseAgeExclude: - - esbuild@0.28.1 diff --git a/release.config.mjs b/release.config.mjs index 4375048..cd9e4e0 100644 --- a/release.config.mjs +++ b/release.config.mjs @@ -1,33 +1,42 @@ /** * @type {import('semantic-release').GlobalConfig} */ +const commitAnalyzer = [ + '@semantic-release/commit-analyzer', + { + releaseRules: [ + { type: 'chore', scope: 'deps', release: 'patch' }, + { type: 'chore', scope: 'deps-dev', release: false }, + { type: 'ci', release: false }, + { type: 'test', release: false }, + { type: 'chore', scope: 'release', release: false }, + ], + }, +]; + +const analysisPlugins = [ + commitAnalyzer, + '@semantic-release/release-notes-generator', +]; + export default { branches: ['main'], tagFormat: 'v${version}', - plugins: [ - [ - '@semantic-release/commit-analyzer', - { - releaseRules: [ - { type: 'chore', scope: 'deps', release: 'patch' }, - { type: 'chore', scope: 'deps-dev', release: false }, - { type: 'ci', release: false }, - { type: 'test', release: false }, - { type: 'chore', scope: 'release', release: false }, + plugins: + process.env.RELEASE_ANALYSIS_ONLY === 'true' + ? analysisPlugins + : [ + ...analysisPlugins, + '@semantic-release/changelog', + '@semantic-release/npm', + [ + '@semantic-release/git', + { + assets: ['package.json', 'CHANGELOG.md'], + message: + 'chore(release): ${nextRelease.version}\n\n${nextRelease.notes}', + }, + ], + '@semantic-release/github', ], - }, - ], - '@semantic-release/release-notes-generator', - '@semantic-release/changelog', - '@semantic-release/npm', - [ - '@semantic-release/git', - { - assets: ['package.json', 'CHANGELOG.md'], - message: - 'chore(release): ${nextRelease.version} [skip ci]\n\n${nextRelease.notes}', - }, - ], - '@semantic-release/github', - ], }; diff --git a/test/tooling/react-support.test.ts b/test/tooling/react-support.test.ts new file mode 100644 index 0000000..bc5a206 --- /dev/null +++ b/test/tooling/react-support.test.ts @@ -0,0 +1,134 @@ +import { describe, expect, it } from 'vitest'; + +import { + createReactMajorUpdate, + getSupportedReactMajors, + updateCompatibilityText, + writeReactSupportFiles, +} from '../../.github/scripts/react-support.js'; + +const packageJson = { + name: 'flow-stack', + peerDependencies: { + react: '>=18 <20', + 'react-dom': '>=18 <20', + }, +}; + +describe('React support tooling', () => { + it('derives supported majors from matching peer ranges', () => { + expect(getSupportedReactMajors('>=18 <20', '>=18 <20')).toEqual([ + '18', + '19', + ]); + }); + + it('returns a no-op when the latest React major is already supported', () => { + expect(createReactMajorUpdate(packageJson, '19.2.0')).toEqual({ + candidateMajor: 19, + changed: false, + packageJson, + supportedMajors: ['18', '19'], + }); + }); + + it('adds only the next unsupported React major', () => { + const result = createReactMajorUpdate(packageJson, '21.0.0'); + + expect(result).toEqual({ + candidateMajor: 20, + changed: true, + packageJson: { + ...packageJson, + peerDependencies: { + react: '>=18 <21', + 'react-dom': '>=18 <21', + }, + }, + supportedMajors: ['18', '19', '20'], + }); + expect(packageJson.peerDependencies).toEqual({ + react: '>=18 <20', + 'react-dom': '>=18 <20', + }); + }); + + it.each(['>=18', '^18 || ^19', '>=20 <20'])( + 'rejects unsupported peer range %s', + (peerRange) => { + expect(() => getSupportedReactMajors(peerRange, peerRange)).toThrow(); + }, + ); + + it('rejects mismatched React and React DOM peer ranges', () => { + expect(() => getSupportedReactMajors('>=18 <20', '>=18 <19')).toThrow( + 'React peer ranges must match', + ); + }); + + it('updates the canonical README compatibility sentence', () => { + expect( + updateCompatibilityText( + 'Install it. Requires React and React DOM 18 or 19. Continue.', + ['18', '19', '20'], + ), + ).toBe('Install it. Requires React and React DOM 18, 19, or 20. Continue.'); + }); + + it('rejects a missing or ambiguous README compatibility sentence', () => { + expect(() => updateCompatibilityText('No compatibility.', ['18'])).toThrow( + 'found 0', + ); + expect(() => + updateCompatibilityText( + 'Requires React and React DOM 18. Requires React and React DOM 18.', + ['18'], + ), + ).toThrow('found 2'); + }); + + it('rejects malformed versions without mutating package metadata', () => { + const original = structuredClone(packageJson); + + expect(() => createReactMajorUpdate(packageJson, 'latest')).toThrow( + 'Could not parse React major', + ); + expect(packageJson).toEqual(original); + }); + + it('rolls back completed writes when a later write fails', () => { + const files = new Map([ + ['package.json', 'original package'], + ['README.md', 'original README'], + ]); + const writeFile = (path: string, value: string) => { + if (path === 'README.md' && value === 'updated README') { + throw new Error('write failed'); + } + + files.set(path, value); + }; + + expect(() => + writeReactSupportFiles( + [ + { + original: 'original package', + path: 'package.json', + updated: 'updated package', + }, + { + original: 'original README', + path: 'README.md', + updated: 'updated README', + }, + ], + writeFile, + ), + ).toThrow('write failed'); + expect(Object.fromEntries(files)).toEqual({ + 'README.md': 'original README', + 'package.json': 'original package', + }); + }); +}); diff --git a/vitest.config.ts b/vitest.config.ts index 41d2582..82acf9f 100644 --- a/vitest.config.ts +++ b/vitest.config.ts @@ -10,7 +10,11 @@ export default defineConfig({ test: { name: 'unit-and-integration', environment: 'node', - include: ['test/unit/**/*.test.ts', 'test/integration/**/*.test.ts'], + include: [ + 'test/unit/**/*.test.ts', + 'test/integration/**/*.test.ts', + 'test/tooling/**/*.test.ts', + ], }, }, { From 419150e6c173d2fd433338821337baabe8042342 Mon Sep 17 00:00:00 2001 From: Chris Alexander <41589890+clalexander@users.noreply.github.com> Date: Thu, 3 Sep 2026 10:02:09 -0400 Subject: [PATCH 2/5] feat!: require Node 22.12 or newer (#43) BREAKING CHANGE: Node 20 is no longer supported --- .github/workflows/verify.yml | 1 - docs/development/README.md | 4 +- docs/development/ci.md | 2 +- package.json | 5 +- pnpm-lock.yaml | 101 +++++++++++++++++++++++++++++++++++ pnpm-workspace.yaml | 4 +- 6 files changed, 108 insertions(+), 9 deletions(-) diff --git a/.github/workflows/verify.yml b/.github/workflows/verify.yml index 26f1511..8e232a0 100644 --- a/.github/workflows/verify.yml +++ b/.github/workflows/verify.yml @@ -90,7 +90,6 @@ jobs: fail-fast: false matrix: node: - - '20' - '22' - '24' react: ${{ fromJSON(needs.prepare.outputs.react) }} diff --git a/docs/development/README.md b/docs/development/README.md index ac62ccc..879a4f3 100644 --- a/docs/development/README.md +++ b/docs/development/README.md @@ -10,7 +10,7 @@ Operational documentation for building, verifying, and releasing Flow Stack. ## Toolchain -- Node: `engines.node` is `>=20.19.0`, and continuous integration verifies Node 20, 22, and 24. +- Node: `engines.node` is `>=22.12.0`, and continuous integration verifies Node 22 and 24. - pnpm: pinned by `packageManager`. Use `corepack enable` rather than installing pnpm globally. - `pnpm-lock.yaml` is the authoritative lockfile. An ignored `package-lock.json` may exist locally and is not used. @@ -35,4 +35,4 @@ pnpm run format ## Dependency Updates -`pnpm-workspace.yaml` holds compatibility pins through `updateConfig.ignoreDependencies`. That list suppresses packages only during a bare `pnpm update`; naming a package explicitly, such as `pnpm update react`, still updates it. React majors are owned by the React compatibility watcher described in [ci.md](./ci.md). +`pnpm-workspace.yaml` holds compatibility pins through `update.ignoreDeps`. That list suppresses packages only during a bare `pnpm update`; naming a package explicitly, such as `pnpm update react`, still updates it. React majors are owned by the React compatibility watcher described in [ci.md](./ci.md). diff --git a/docs/development/ci.md b/docs/development/ci.md index f8d1ba9..4e0c5ac 100644 --- a/docs/development/ci.md +++ b/docs/development/ci.md @@ -70,7 +70,7 @@ The npm group keeps Dependabot's own scope. A group containing a production depe Compatibility holds live in two places and mean different things: - `.github/dependabot.yml` ignores React majors and specific unsupported version ranges. These entries support version bounds. -- `pnpm-workspace.yaml` lists package names under `updateConfig.ignoreDependencies`. These entries have no version granularity and apply only to a bare `pnpm update`. +- `pnpm-workspace.yaml` lists package names under `update.ignoreDeps`. These entries have no version granularity and apply only to a bare `pnpm update`. Dependabot reads `.github/dependabot.yml` from the default branch. Changes to grouping take effect only after they land there. diff --git a/package.json b/package.json index 6d9db6f..ee70070 100644 --- a/package.json +++ b/package.json @@ -45,10 +45,9 @@ "dist", "CHANGELOG.md" ], - "packageManager": "pnpm@10.34.4", + "packageManager": "pnpm@12.3.1", "engines": { - "node": ">=20.19.0", - "pnpm": ">=10.0.0 <11" + "node": ">=22.12.0" }, "sideEffects": false, "scripts": { diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 3ce198e..177c271 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -1,3 +1,104 @@ +--- +lockfileVersion: '9.0' + +importers: + + .: + configDependencies: {} + packageManagerDependencies: + pnpm: + specifier: 12.3.1 + version: 12.3.1 + +packages: + + '@pnpm/exe.darwin-arm64@12.3.1': + resolution: {integrity: sha512-Yer+aZnQtgE+OOLKwbRHaAEt74WBJdH8eXpLrSWf+5vj7DkkDvhSR45HVxN3a5d430fMUyF0lmQai02T650r4g==} + cpu: [arm64] + os: [darwin] + + '@pnpm/exe.darwin-x64@12.3.1': + resolution: {integrity: sha512-XPZYf+XpxufwZS8tpQQdftsv6eUtPDA0uU5NlfXA1uMVPvXJesw5PLGWmmJZHcI4rIscn2H6FngkIcvkuZaaKQ==} + cpu: [x64] + os: [darwin] + + '@pnpm/exe.linux-arm64-musl@12.3.1': + resolution: {integrity: sha512-WjKcLeuierWGSQHjb0QeDl8avQTel8rN5jDMCI55tBJTrTBXNQsdlpgzP9uCD0GSzjPH+hjWKb+GjeMNvv5Ruw==} + cpu: [arm64] + os: [linux] + libc: [musl] + + '@pnpm/exe.linux-arm64@12.3.1': + resolution: {integrity: sha512-X0HxHlEYubFRuMPBOy+ytKsv6c11v4em/ovVVCy5KCdJVBtVGF7vF5ywlGqw7EjpGdqM39pdLTWFwH9Q77lUzQ==} + cpu: [arm64] + os: [linux] + libc: [glibc] + + '@pnpm/exe.linux-x64-musl@12.3.1': + resolution: {integrity: sha512-ZvzQI2+Ek0v+V6m30XV3ShIx5sm+ZIZoM669Z0F/RvMSpHgklqv3CBdEwAsQCZ7XBNZLMQIE7RPR2yIwxt3mnw==} + cpu: [x64] + os: [linux] + libc: [musl] + + '@pnpm/exe.linux-x64@12.3.1': + resolution: {integrity: sha512-ubvbQ2OSt7fR3kSnhtknx5xnm2H7uRi0kC32ADmzKJ1vZz337kmL30rTHoUzTG7ZcIyEhODg7R+zI1cW1ZdVDw==} + cpu: [x64] + os: [linux] + libc: [glibc] + + '@pnpm/exe.win32-arm64@12.3.1': + resolution: {integrity: sha512-e+5CjFBGWP7U7RfFlH/EQnlFaP9Uyo/Y0BDCEbitsC4if28WBur3ajAkc25rRwiEwmmEpipTSzqNsKIs9Mq72Q==} + cpu: [arm64] + os: [win32] + + '@pnpm/exe.win32-x64@12.3.1': + resolution: {integrity: sha512-5pW8NQuVF3dkNdaUCm03PeoDiC5I9h4y9Fz717KLWi5jxDKmgARmD1zDdm60F5ohRZHPrRv/jAg94a/5+VXxow==} + cpu: [x64] + os: [win32] + + pnpm@12.3.1: + resolution: {integrity: sha512-PBTBVAjRSJ01D47X+TNh0mzHBwVPaEmk7qO7dAf/T+RWS0E6HEIadzoXarEWio3xx9VI8s0Nx9NE9YxOaApbGA==} + engines: {node: '>=18.*'} + hasBin: true + +snapshots: + + '@pnpm/exe.darwin-arm64@12.3.1': + optional: true + + '@pnpm/exe.darwin-x64@12.3.1': + optional: true + + '@pnpm/exe.linux-arm64-musl@12.3.1': + optional: true + + '@pnpm/exe.linux-arm64@12.3.1': + optional: true + + '@pnpm/exe.linux-x64-musl@12.3.1': + optional: true + + '@pnpm/exe.linux-x64@12.3.1': + optional: true + + '@pnpm/exe.win32-arm64@12.3.1': + optional: true + + '@pnpm/exe.win32-x64@12.3.1': + optional: true + + pnpm@12.3.1: + optionalDependencies: + '@pnpm/exe.darwin-arm64': 12.3.1 + '@pnpm/exe.darwin-x64': 12.3.1 + '@pnpm/exe.linux-arm64': 12.3.1 + '@pnpm/exe.linux-arm64-musl': 12.3.1 + '@pnpm/exe.linux-x64': 12.3.1 + '@pnpm/exe.linux-x64-musl': 12.3.1 + '@pnpm/exe.win32-arm64': 12.3.1 + '@pnpm/exe.win32-x64': 12.3.1 + +--- lockfileVersion: '9.0' settings: diff --git a/pnpm-workspace.yaml b/pnpm-workspace.yaml index 04835b1..abcc57b 100644 --- a/pnpm-workspace.yaml +++ b/pnpm-workspace.yaml @@ -7,8 +7,8 @@ overrides: nanoid: 3.3.18 postcss: 8.5.23 undici: 7.29.0 -updateConfig: - ignoreDependencies: +update: + ignoreDeps: # Remove once eslint-plugin-react and eslint-plugin-jsx-a11y support ESLint 10. - '@eslint/js' - eslint From 5fc7f5c474526b469c6a53cfb05d0657322c7e67 Mon Sep 17 00:00:00 2001 From: Chris Alexander <41589890+clalexander@users.noreply.github.com> Date: Thu, 3 Sep 2026 10:12:10 -0400 Subject: [PATCH 3/5] build!: remove cjs support (#44) BREAKING CHANGE: Remove CommonJS support --- tsdown.config.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tsdown.config.ts b/tsdown.config.ts index 5af7ac1..6a61f54 100644 --- a/tsdown.config.ts +++ b/tsdown.config.ts @@ -3,7 +3,7 @@ import { defineConfig } from 'tsdown'; export default defineConfig({ entry: ['src/index.ts'], outDir: 'dist', - format: ['esm', 'cjs'], + format: ['esm'], dts: true, sourcemap: true, platform: 'neutral', From 2a45850706c3794507a473934893647fc7565226 Mon Sep 17 00:00:00 2001 From: Chris Alexander <41589890+clalexander@users.noreply.github.com> Date: Thu, 3 Sep 2026 12:47:31 -0400 Subject: [PATCH 4/5] tests: fix Vitest close timeout and close the test typeckeck gap (#45) --- .github/scripts/react-support.ts | 41 +++++++++++-------- package.json | 2 +- .../createNavigationStackController.test.ts | 6 +-- .../controller/navigationReducer.test.ts | 32 +++++++-------- test/unit/a11y/reducedMotion.test.ts | 4 +- .../routes/normalizeRouteRegistry.test.ts | 6 +-- test/unit/state/guards.test.ts | 30 +++++++++----- test/unit/state/history.test.ts | 20 ++++----- test/unit/state/matchers.test.ts | 3 +- tsconfig.test.json | 3 +- vitest.config.ts | 11 ----- 11 files changed, 82 insertions(+), 76 deletions(-) diff --git a/.github/scripts/react-support.ts b/.github/scripts/react-support.ts index 87f031b..6b8d945 100644 --- a/.github/scripts/react-support.ts +++ b/.github/scripts/react-support.ts @@ -22,29 +22,29 @@ const peerRangePattern = /^>=(\d+) <(\d+)$/; const compatibilityPattern = /Requires React and React DOM ([^.]+)\./g; function getMajor(version: string): number { - const match = /^(\d+)\./.exec(version); + const major = /^(\d+)\./.exec(version)?.[1]; - if (!match) { + if (major === undefined) { throw new Error(`Could not parse React major from "${version}".`); } - return Number.parseInt(match[1], 10); + return Number.parseInt(major, 10); } function parsePeerRange(peerRange: string): { exclusiveMaximumMajor: number; minimumMajor: number; } { - const match = peerRangePattern.exec(peerRange); + const [, minimum, exclusiveMaximum] = peerRangePattern.exec(peerRange) ?? []; - if (!match) { + if (minimum === undefined || exclusiveMaximum === undefined) { throw new Error( `Expected a contiguous React peer range like ">=18 <20", received "${peerRange}".`, ); } - const minimumMajor = Number.parseInt(match[1], 10); - const exclusiveMaximumMajor = Number.parseInt(match[2], 10); + const minimumMajor = Number.parseInt(minimum, 10); + const exclusiveMaximumMajor = Number.parseInt(exclusiveMaximum, 10); if (exclusiveMaximumMajor <= minimumMajor) { throw new Error( @@ -66,15 +66,21 @@ function getMajorRange( } function formatCompatibility(majors: string[]): string { - if (majors.length === 1) { - return majors[0]; + const [first, ...rest] = majors; + + if (first === undefined) { + throw new Error('Expected at least one supported React major.'); } - if (majors.length === 2) { - return `${majors[0]} or ${majors[1]}`; + const last = rest.pop(); + + if (last === undefined) { + return first; } - return `${majors.slice(0, -1).join(', ')}, or ${majors[majors.length - 1]}`; + return rest.length === 0 + ? `${first} or ${last}` + : `${[first, ...rest].join(', ')}, or ${last}`; } export function getSupportedReactMajors( @@ -108,10 +114,13 @@ export function createReactMajorUpdate< } const supportedMajors = getSupportedReactMajors(reactRange, reactDomRange); - const maximumSupportedMajor = Number.parseInt( - supportedMajors[supportedMajors.length - 1], - 10, - ); + const highestSupportedMajor = supportedMajors[supportedMajors.length - 1]; + + if (highestSupportedMajor === undefined) { + throw new Error('The React peer range produced no supported majors.'); + } + + const maximumSupportedMajor = Number.parseInt(highestSupportedMajor, 10); const latestMajor = getMajor(latestVersion); if (latestMajor <= maximumSupportedMajor) { diff --git a/package.json b/package.json index ee70070..f101e3c 100644 --- a/package.json +++ b/package.json @@ -53,7 +53,7 @@ "scripts": { "build": "tsdown", "clean": "rimraf dist", - "typecheck": "tsc --noEmit", + "typecheck": "tsc --noEmit && tsc -p tsconfig.test.json --noEmit", "format": "prettier --write .", "format:check": "prettier --check .", "lint": "eslint .", diff --git a/test/integration/controller/createNavigationStackController.test.ts b/test/integration/controller/createNavigationStackController.test.ts index 5667f8d..0fd2a81 100644 --- a/test/integration/controller/createNavigationStackController.test.ts +++ b/test/integration/controller/createNavigationStackController.test.ts @@ -16,7 +16,7 @@ describe('createNavigationStackController', () => { it('starts with the initial route', () => { const c = makeController(); expect(c.entries).toHaveLength(1); - expect(c.entries[0].routeName).toBe('Home'); + expect(c.entries[0]!.routeName).toBe('Home'); }); it('activeIndex is 0', () => { @@ -50,7 +50,7 @@ describe('createNavigationStackController', () => { const c = makeController(); c.push('Detail'); expect(c.entries).toHaveLength(2); - expect(c.entries[1].routeName).toBe('Detail'); + expect(c.entries[1]!.routeName).toBe('Detail'); expect(c.state.activeIndex).toBe(1); }); @@ -81,7 +81,7 @@ describe('createNavigationStackController', () => { const c = makeController(); c.replace('Detail'); expect(c.entries).toHaveLength(1); - expect(c.entries[0].routeName).toBe('Detail'); + expect(c.entries[0]!.routeName).toBe('Detail'); }); it('does not increase depth', () => { diff --git a/test/integration/controller/navigationReducer.test.ts b/test/integration/controller/navigationReducer.test.ts index df813bf..292975c 100644 --- a/test/integration/controller/navigationReducer.test.ts +++ b/test/integration/controller/navigationReducer.test.ts @@ -18,7 +18,7 @@ describe('navigationReducer', () => { route: 'Settings', }); expect(next.entries).toHaveLength(3); - expect(next.entries[2].routeName).toBe('Settings'); + expect(next.entries[2]!.routeName).toBe('Settings'); }); it('advances activeIndex to the new entry', () => { @@ -49,21 +49,21 @@ describe('navigationReducer', () => { route: 'Settings', }); expect(next.entries).toHaveLength(2); - expect(next.entries[1].routeName).toBe('Settings'); + expect(next.entries[1]!.routeName).toBe('Settings'); }); it('keeps the same key for the replaced entry', () => { const s = state2(); - const originalKey = s.entries[1].key; + const originalKey = s.entries[1]!.key; const next = navigationReducer(s, { type: 'replace', route: 'Settings' }); - expect(next.entries[1].key).toBe(originalKey); + expect(next.entries[1]!.key).toBe(originalKey); }); it('handles replace on empty stack', () => { const empty = activeStackState([], -1); const next = navigationReducer(empty, { type: 'replace', route: 'Home' }); expect(next.entries).toHaveLength(1); - expect(next.entries[0].routeName).toBe('Home'); + expect(next.entries[0]!.routeName).toBe('Home'); }); }); @@ -71,7 +71,7 @@ describe('navigationReducer', () => { it('removes the top entry', () => { const next = navigationReducer(state2(), { type: 'pop' }); expect(next.entries).toHaveLength(1); - expect(next.entries[0].routeName).toBe('Home'); + expect(next.entries[0]!.routeName).toBe('Home'); }); it('decrements activeIndex', () => { @@ -93,7 +93,7 @@ describe('navigationReducer', () => { ]); const next = navigationReducer(s, { type: 'pop', count: 2 }); expect(next.entries).toHaveLength(1); - expect(next.entries[0].routeName).toBe('A'); + expect(next.entries[0]!.routeName).toBe('A'); }); }); @@ -106,7 +106,7 @@ describe('navigationReducer', () => { ]); const next = navigationReducer(s, { type: 'popToRoot' }); expect(next.entries).toHaveLength(1); - expect(next.entries[0].routeName).toBe('Home'); + expect(next.entries[0]!.routeName).toBe('Home'); expect(next.activeIndex).toBe(0); }); @@ -149,8 +149,8 @@ describe('navigationReducer', () => { entries: [{ name: 'X' }, { name: 'Y' }], }); expect(next.entries).toHaveLength(2); - expect(next.entries[0].routeName).toBe('X'); - expect(next.entries[1].routeName).toBe('Y'); + expect(next.entries[0]!.routeName).toBe('X'); + expect(next.entries[1]!.routeName).toBe('Y'); }); it('sets activeIndex to last entry', () => { @@ -171,7 +171,7 @@ describe('navigationReducer', () => { type: 'setParams', params: { a: 99, b: 2 }, }); - expect(next.entries[0].params).toEqual({ a: 99, b: 2 }); + expect(next.entries[0]!.params).toEqual({ a: 99, b: 2 }); }); it('is a no-op when no active entry', () => { @@ -187,13 +187,13 @@ describe('navigationReducer', () => { describe('updateEntry', () => { it('applies the updater to the matching entry', () => { const s = state2(); - const key = s.entries[0].key; + const key = s.entries[0]!.key; const next = navigationReducer(s, { type: 'updateEntry', entryKey: key, updater: (e) => ({ ...e, params: { updated: true } }), }); - expect(next.entries[0].params).toEqual({ updated: true }); + expect(next.entries[0]!.params).toEqual({ updated: true }); }); it('returns unchanged state when key not found', () => { @@ -224,16 +224,16 @@ describe('navigationReducer', () => { describe('entry state normalization', () => { it('active entry has state "active" after push', () => { const next = navigationReducer(state2(), { type: 'push', route: 'X' }); - expect(next.entries[next.activeIndex].state).toBe('active'); + expect(next.entries[next.activeIndex]!.state).toBe('active'); }); it('previous entries have state "inactive" after push', () => { const next = navigationReducer(state2(), { type: 'push', route: 'X' }); // entries[0] (Home) was already inactive before push; normalizeEntries preserves it - expect(next.entries[0].state).toBe('inactive'); + expect(next.entries[0]!.state).toBe('inactive'); // entries[1] (Detail) was the active entry; normalizeEntries(state.entries, state.activeIndex=1) // keeps it 'active' so it remains visible during the outgoing transition - expect(next.entries[1].state).toBe('active'); + expect(next.entries[1]!.state).toBe('active'); }); }); }); diff --git a/test/unit/a11y/reducedMotion.test.ts b/test/unit/a11y/reducedMotion.test.ts index 9b761dc..2f97a73 100644 --- a/test/unit/a11y/reducedMotion.test.ts +++ b/test/unit/a11y/reducedMotion.test.ts @@ -43,14 +43,14 @@ describe('resolveReducedMotionPreference', () => { it('"system" returns false when matchMedia does not match', () => { ( - globalThis as unknown as Record void> + globalThis as unknown as { __setMatchMedia: (v: boolean) => void } ).__setMatchMedia(false); expect(resolveReducedMotionPreference('system')).toBe(false); }); it('"system" returns true when matchMedia matches', () => { ( - globalThis as unknown as Record void> + globalThis as unknown as { __setMatchMedia: (v: boolean) => void } ).__setMatchMedia(true); expect(resolveReducedMotionPreference('system')).toBe(true); }); diff --git a/test/unit/routes/normalizeRouteRegistry.test.ts b/test/unit/routes/normalizeRouteRegistry.test.ts index 8dc98ea..f50a18f 100644 --- a/test/unit/routes/normalizeRouteRegistry.test.ts +++ b/test/unit/routes/normalizeRouteRegistry.test.ts @@ -34,8 +34,8 @@ describe('normalizeRouteRegistry', () => { describe('object input', () => { it('clones the object into a normalized registry', () => { const obj = { - Home: simpleRegistry[0], - Detail: simpleRegistry[1], + Home: simpleRegistry[0]!, + Detail: simpleRegistry[1]!, }; const result = normalizeRouteRegistry(obj); expect(result['Home']).toBe(obj.Home); @@ -43,7 +43,7 @@ describe('normalizeRouteRegistry', () => { }); it('returns the same keys as the input object', () => { - const obj = { Settings: simpleRegistry[2] }; + const obj = { Settings: simpleRegistry[2]! }; const result = normalizeRouteRegistry(obj); expect(Object.keys(result)).toEqual(['Settings']); }); diff --git a/test/unit/state/guards.test.ts b/test/unit/state/guards.test.ts index 5d69e5d..17b7d05 100644 --- a/test/unit/state/guards.test.ts +++ b/test/unit/state/guards.test.ts @@ -5,7 +5,15 @@ import { runNavigationGuards } from '../../../src/state/guards'; import { makeEntry, activeStackState } from '../../fixtures/entries'; import { simpleRegistry } from '../../fixtures/routes'; -const routes = normalizeRouteRegistry(simpleRegistry); +const registry = normalizeRouteRegistry(simpleRegistry); +const homeRoute = registry['Home']; +const detailRoute = registry['Detail']; + +if (!homeRoute || !detailRoute) { + throw new Error('The simple registry must define Home and Detail routes.'); +} + +const routes = { Detail: detailRoute, Home: homeRoute }; const action = { type: 'push' as const, route: 'Detail' }; function makeState() { @@ -17,8 +25,8 @@ describe('runNavigationGuards', () => { const result = await runNavigationGuards({ action, currentState: makeState(), - currentRoute: routes['Home'], - nextRoute: routes['Detail'], + currentRoute: routes.Home, + nextRoute: routes.Detail, }); expect(result).toBe(true); }); @@ -28,7 +36,7 @@ describe('runNavigationGuards', () => { const result = await runNavigationGuards({ action, currentState: makeState(), - currentRoute: { ...routes['Home'], canLeave }, + currentRoute: { ...routes.Home, canLeave }, }); expect(result).toBe(true); expect(canLeave).toHaveBeenCalled(); @@ -39,7 +47,7 @@ describe('runNavigationGuards', () => { const result = await runNavigationGuards({ action, currentState: makeState(), - currentRoute: { ...routes['Home'], canLeave }, + currentRoute: { ...routes.Home, canLeave }, }); expect(result).toBe(false); }); @@ -49,7 +57,7 @@ describe('runNavigationGuards', () => { const result = await runNavigationGuards({ action, currentState: makeState(), - nextRoute: { ...routes['Detail'], canEnter }, + nextRoute: { ...routes.Detail, canEnter }, }); expect(result).toBe(true); }); @@ -59,7 +67,7 @@ describe('runNavigationGuards', () => { const result = await runNavigationGuards({ action, currentState: makeState(), - nextRoute: { ...routes['Detail'], canEnter }, + nextRoute: { ...routes.Detail, canEnter }, }); expect(result).toBe(false); }); @@ -70,8 +78,8 @@ describe('runNavigationGuards', () => { const result = await runNavigationGuards({ action, currentState: makeState(), - currentRoute: { ...routes['Home'], canLeave }, - nextRoute: { ...routes['Detail'], canEnter }, + currentRoute: { ...routes.Home, canLeave }, + nextRoute: { ...routes.Detail, canEnter }, }); expect(result).toBe(false); expect(canEnter).not.toHaveBeenCalled(); @@ -82,7 +90,7 @@ describe('runNavigationGuards', () => { const result = await runNavigationGuards({ action, currentState: makeState(), - nextRoute: { ...routes['Detail'], canEnter }, + nextRoute: { ...routes.Detail, canEnter }, }); expect(result).toBe(true); }); @@ -92,7 +100,7 @@ describe('runNavigationGuards', () => { const result = await runNavigationGuards({ action, currentState: makeState(), - nextRoute: { ...routes['Detail'], canEnter }, + nextRoute: { ...routes.Detail, canEnter }, }); expect(result).toBe(false); }); diff --git a/test/unit/state/history.test.ts b/test/unit/state/history.test.ts index c050e47..dc7b931 100644 --- a/test/unit/state/history.test.ts +++ b/test/unit/state/history.test.ts @@ -58,28 +58,28 @@ describe('createEntriesFromInputs', () => { ]; const entries = createEntriesFromInputs(inputs); expect(entries).toHaveLength(2); - expect(entries[0].routeName).toBe('Home'); - expect(entries[0].params).toEqual({ a: 1 }); - expect(entries[1].routeName).toBe('Detail'); + expect(entries[0]!.routeName).toBe('Home'); + expect(entries[0]!.params).toEqual({ a: 1 }); + expect(entries[1]!.routeName).toBe('Detail'); }); it('sets last entry state to active, others to inactive', () => { const inputs = [{ name: 'A' }, { name: 'B' }, { name: 'C' }]; const entries = createEntriesFromInputs(inputs); - expect(entries[0].state).toBe('inactive'); - expect(entries[1].state).toBe('inactive'); - expect(entries[2].state).toBe('active'); + expect(entries[0]!.state).toBe('inactive'); + expect(entries[1]!.state).toBe('inactive'); + expect(entries[2]!.state).toBe('active'); }); it('uses empty object when params is omitted', () => { const entries = createEntriesFromInputs([{ name: 'Home' }]); - expect(entries[0].params).toEqual({}); + expect(entries[0]!.params).toEqual({}); }); it('assigns a unique non-empty key to each entry', () => { const entries = createEntriesFromInputs([{ name: 'A' }, { name: 'B' }]); - expect(entries[0].key).toBeTruthy(); - expect(entries[1].key).toBeTruthy(); - expect(entries[0].key).not.toBe(entries[1].key); + expect(entries[0]!.key).toBeTruthy(); + expect(entries[1]!.key).toBeTruthy(); + expect(entries[0]!.key).not.toBe(entries[1]!.key); }); }); diff --git a/test/unit/state/matchers.test.ts b/test/unit/state/matchers.test.ts index 9ac73f8..a362d2d 100644 --- a/test/unit/state/matchers.test.ts +++ b/test/unit/state/matchers.test.ts @@ -1,5 +1,6 @@ import { describe, it, expect } from 'vitest'; +import type { NavigationEntry } from '../../../src/core/public'; import { matchesNavigationEntry, findNavigationEntry, @@ -7,7 +8,7 @@ import { import { makeEntry } from '../../fixtures/entries'; describe('matchesNavigationEntry', () => { - const entries = [ + const entries: [NavigationEntry, NavigationEntry] = [ makeEntry({ routeName: 'Home', key: 'key-home' }), makeEntry({ routeName: 'Detail', key: 'key-detail', id: 'detail-1' }), ]; diff --git a/tsconfig.test.json b/tsconfig.test.json index aa70cfa..1c27fa6 100644 --- a/tsconfig.test.json +++ b/tsconfig.test.json @@ -3,8 +3,7 @@ "extends": "./tsconfig.json", "compilerOptions": { "noEmit": true, - "verbatimModuleSyntax": true, - "noUncheckedIndexedAccess": false + "verbatimModuleSyntax": true }, "include": ["src", "test", "vitest.config.ts"] } diff --git a/vitest.config.ts b/vitest.config.ts index 82acf9f..2636ec3 100644 --- a/vitest.config.ts +++ b/vitest.config.ts @@ -29,17 +29,6 @@ export default defineConfig({ setupFiles: ['test/helpers/setup.ts'], }, }, - { - test: { - name: 'types', - include: ['test/types/**/*.test-d.ts'], - typecheck: { - enabled: true, - only: true, - include: ['test/types/**/*.test-d.ts'], - }, - }, - }, ], coverage: { provider: 'v8', From ddc397fc65c515c8fdd25af808a9595ce9c4be01 Mon Sep 17 00:00:00 2001 From: Chris Alexander <41589890+clalexander@users.noreply.github.com> Date: Thu, 3 Sep 2026 13:05:23 -0400 Subject: [PATCH 5/5] chore(deps): update dependencies (#46) * chore(deps): update dependencies * Fix lint errors --- package.json | 30 +- pnpm-lock.yaml | 3071 ++++++++++++------------------- test/helpers/renderStack.tsx | 17 - test/types/public-api.test-d.ts | 2 +- 4 files changed, 1217 insertions(+), 1903 deletions(-) diff --git a/package.json b/package.json index f101e3c..23a6a98 100644 --- a/package.json +++ b/package.json @@ -67,16 +67,16 @@ "react-dom": ">=18 <20" }, "devDependencies": { - "@eslint/js": "^9.39.4", - "@semantic-release/changelog": "^6.0.3", - "@semantic-release/git": "^10.0.1", - "@testing-library/react": "^16.3.2", - "@testing-library/user-event": "^14.6.1", - "@types/node": "24.0.0", + "@eslint/js": "^9.39.5", + "@semantic-release/changelog": "^7.0.0", + "@semantic-release/git": "^11.0.1", + "@testing-library/react": "^16.3.3", + "@testing-library/user-event": "^14.6.7", + "@types/node": "^26.4.1", "@types/react": "^18.3.31", "@types/react-dom": "^18.3.7", - "@vitest/coverage-v8": "^3.2.6", - "eslint": "^9.39.4", + "@vitest/coverage-v8": "^4.1.11", + "eslint": "^9.39.5", "eslint-config-prettier": "^10.1.8", "eslint-import-resolver-typescript": "^4.4.5", "eslint-plugin-import": "^2.32.0", @@ -84,17 +84,17 @@ "eslint-plugin-react": "^7.37.5", "eslint-plugin-react-hooks": "^7.1.1", "eslint-plugin-sort-exports": "^0.9.1", - "globals": "^17.6.0", - "jsdom": "^29.1.1", - "prettier": "3.9.3", + "globals": "^17.12.0", + "jsdom": "^30.0.1", + "prettier": "^3.9.6", "react": "^18.3.1", "react-dom": "^18.3.1", "rimraf": "^6.1.3", - "semantic-release": "^25.0.5", - "tsdown": "^0.22.3", + "semantic-release": "^25.0.9", + "tsdown": "^0.22.14", "typescript": "^6.0.3", - "typescript-eslint": "^8.61.1", - "vitest": "^3.2.6" + "typescript-eslint": "^8.69.0", + "vitest": "^4.1.11" }, "publishConfig": { "registry": "https://registry.npmjs.org/", diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 177c271..dd964f1 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -120,23 +120,23 @@ importers: .: devDependencies: '@eslint/js': - specifier: ^9.39.4 - version: 9.39.4 + specifier: ^9.39.5 + version: 9.39.5 '@semantic-release/changelog': - specifier: ^6.0.3 - version: 6.0.3(semantic-release@25.0.5(typescript@6.0.3)) + specifier: ^7.0.0 + version: 7.0.0(semantic-release@25.0.9(supports-color@7.2.0)(typescript@6.0.3)) '@semantic-release/git': - specifier: ^10.0.1 - version: 10.0.1(semantic-release@25.0.5(typescript@6.0.3)) + specifier: ^11.0.1 + version: 11.0.1(semantic-release@25.0.9(supports-color@7.2.0)(typescript@6.0.3))(supports-color@7.2.0) '@testing-library/react': - specifier: ^16.3.2 - version: 16.3.2(@testing-library/dom@10.4.1)(@types/react-dom@18.3.7(@types/react@18.3.31))(@types/react@18.3.31)(react-dom@18.3.1(react@18.3.1))(react@18.3.1) + specifier: ^16.3.3 + version: 16.3.3(@testing-library/dom@10.4.1)(@types/react-dom@18.3.7(@types/react@18.3.31))(@types/react@18.3.31)(react-dom@18.3.1(react@18.3.1))(react@18.3.1) '@testing-library/user-event': - specifier: ^14.6.1 - version: 14.6.1(@testing-library/dom@10.4.1) + specifier: ^14.6.7 + version: 14.6.7(@testing-library/dom@10.4.1) '@types/node': - specifier: 24.0.0 - version: 24.0.0 + specifier: ^26.4.1 + version: 26.4.1 '@types/react': specifier: ^18.3.31 version: 18.3.31 @@ -144,41 +144,41 @@ importers: specifier: ^18.3.7 version: 18.3.7(@types/react@18.3.31) '@vitest/coverage-v8': - specifier: ^3.2.6 - version: 3.2.6(vitest@3.2.6(@types/node@24.0.0)(jsdom@29.1.1)) + specifier: ^4.1.11 + version: 4.1.11(vitest@4.1.11) eslint: - specifier: ^9.39.4 - version: 9.39.4 + specifier: ^9.39.5 + version: 9.39.5(supports-color@7.2.0) eslint-config-prettier: specifier: ^10.1.8 - version: 10.1.8(eslint@9.39.4) + version: 10.1.8(eslint@9.39.5(supports-color@7.2.0)) eslint-import-resolver-typescript: specifier: ^4.4.5 - version: 4.4.5(eslint-plugin-import@2.32.0)(eslint@9.39.4) + version: 4.4.5(eslint-plugin-import@2.32.0)(eslint@9.39.5(supports-color@7.2.0))(supports-color@7.2.0) eslint-plugin-import: specifier: ^2.32.0 - version: 2.32.0(@typescript-eslint/parser@8.62.0(eslint@9.39.4)(typescript@6.0.3))(eslint-import-resolver-typescript@4.4.5)(eslint@9.39.4) + version: 2.32.0(@typescript-eslint/parser@8.69.0(eslint@9.39.5(supports-color@7.2.0))(supports-color@7.2.0)(typescript@6.0.3))(eslint-import-resolver-typescript@4.4.5)(eslint@9.39.5(supports-color@7.2.0))(supports-color@7.2.0) eslint-plugin-jsx-a11y: specifier: ^6.10.2 - version: 6.10.2(eslint@9.39.4) + version: 6.10.2(eslint@9.39.5(supports-color@7.2.0)) eslint-plugin-react: specifier: ^7.37.5 - version: 7.37.5(eslint@9.39.4) + version: 7.37.5(eslint@9.39.5(supports-color@7.2.0)) eslint-plugin-react-hooks: specifier: ^7.1.1 - version: 7.1.1(eslint@9.39.4) + version: 7.1.1(eslint@9.39.5(supports-color@7.2.0))(supports-color@7.2.0) eslint-plugin-sort-exports: specifier: ^0.9.1 - version: 0.9.1(eslint@9.39.4) + version: 0.9.1(eslint@9.39.5(supports-color@7.2.0)) globals: - specifier: ^17.6.0 - version: 17.7.0 + specifier: ^17.12.0 + version: 17.12.0 jsdom: - specifier: ^29.1.1 - version: 29.1.1 + specifier: ^30.0.1 + version: 30.0.1 prettier: - specifier: 3.9.3 - version: 3.9.3 + specifier: ^3.9.6 + version: 3.9.6 react: specifier: ^18.3.1 version: 18.3.1 @@ -189,20 +189,20 @@ importers: specifier: ^6.1.3 version: 6.1.3 semantic-release: - specifier: ^25.0.5 - version: 25.0.5(typescript@6.0.3) + specifier: ^25.0.9 + version: 25.0.9(supports-color@7.2.0)(typescript@6.0.3) tsdown: - specifier: ^0.22.3 - version: 0.22.3(typescript@6.0.3)(unrun@0.2.39) + specifier: ^0.22.14 + version: 0.22.14(typescript@6.0.3) typescript: specifier: ^6.0.3 version: 6.0.3 typescript-eslint: - specifier: ^8.61.1 - version: 8.62.0(eslint@9.39.4)(typescript@6.0.3) + specifier: ^8.69.0 + version: 8.69.0(eslint@9.39.5(supports-color@7.2.0))(supports-color@7.2.0)(typescript@6.0.3) vitest: - specifier: ^3.2.6 - version: 3.2.6(@types/node@24.0.0)(jsdom@29.1.1) + specifier: ^4.1.11 + version: 4.1.11(@types/node@26.4.1)(@vitest/coverage-v8@4.1.11)(jsdom@30.0.1)(vite@8.2.2(@types/node@26.4.1)) packages: @@ -218,24 +218,13 @@ packages: '@actions/io@3.0.2': resolution: {integrity: sha512-nRBchcMM+QK1pdjO7/idu86rbJI5YHUKCvKs0KxnSYbVe3F51UfGxuZX4Qy/fWlp6l7gWFwIkrOzN+oUK03kfw==} - '@ampproject/remapping@2.3.0': - resolution: {integrity: sha512-30iZtAPgz+LTIYoeivqYo853f02jBYSd5uGnGpkFV0M3xOt9aN73erkgYAmZU43x4VfqcnLxW9Kpg3R5LC4YYw==} - engines: {node: '>=6.0.0'} - - '@asamuzakjp/css-color@5.1.11': - resolution: {integrity: sha512-KVw6qIiCTUQhByfTd78h2yD1/00waTmm9uy/R7Ck/ctUyAPj+AEDLkQIdJW0T8+qGgj3j5bpNKK7Q3G+LedJWg==} - engines: {node: ^20.19.0 || ^22.12.0 || >=24.0.0} - - '@asamuzakjp/dom-selector@7.1.1': - resolution: {integrity: sha512-67RZDnYRc8H/8MLDgQCDE//zoqVFwajkepHZgmXrbwybzXOEwOWGPYGmALYl9J2DOLfFPPs6kKCqmbzV895hTQ==} - engines: {node: ^20.19.0 || ^22.12.0 || >=24.0.0} - - '@asamuzakjp/generational-cache@1.0.1': - resolution: {integrity: sha512-wajfB8KqzMCN2KGNFdLkReeHncd0AslUSrvHVvvYWuU8ghncRJoA50kT3zP9MVL0+9g4/67H+cdvBskj9THPzg==} - engines: {node: ^20.19.0 || ^22.12.0 || >=24.0.0} + '@asamuzakjp/css-color@6.0.7': + resolution: {integrity: sha512-vC/bk1Lz7Tn/EfU9/apOTBk80/8dyGyWMowPoV1tJ52muDGsDqt2HPT2klrFUiY60MQmQv9q8yIht15JnBgDGw==} + engines: {node: ^22.13.0 || >=24.0.0} - '@asamuzakjp/nwsapi@2.3.9': - resolution: {integrity: sha512-n8GuYSrI9bF7FFZ/SjhwevlHc8xaVlb/7HmHelnc/PZXBD2ZR49NnN9sMMuDdEGPeeRQ5d0hqlSlEpgCX3Wl0Q==} + '@asamuzakjp/dom-selector@8.3.2': + resolution: {integrity: sha512-93Z1N+BQNXysodoicpOIyNh2drHfz/CTf9nnT0FEx72GJcIiwgydD7tGAr78j41LsYn3hlRn+LdGPuBLn1Bl8Q==} + engines: {node: ^22.13.0 || >=24.0.0} '@babel/code-frame@7.29.7': resolution: {integrity: sha512-Aup7aUOfpbAUg2ROOJN6Iw5f9DMBlzu0mIkm/malLQFN/YQgO48wCj0Kxa3sEHJvPVFg7siR+qRInwXd2qhQKw==} @@ -249,14 +238,10 @@ packages: resolution: {integrity: sha512-RgHBCvtjbOK2gXSNBNIkNoEc9qoVEtau3hj8gEqKQuL3HZAibKarWFEI3Lfm6EYKkLalOh8eSrj9b+ch9H/VBA==} engines: {node: '>=6.9.0'} - '@babel/generator@7.29.7': - resolution: {integrity: sha512-DkXD5OJQaAQIdZ1bt3UZdEnHAn9Imd3IVBdX03UFe+ony9Ojw5pzr9YVKGDY1jt+Gcn/FnGkNf8r+Vj5NOJWtQ==} + '@babel/generator@7.29.8': + resolution: {integrity: sha512-gZbepsdh3WDtgZKWL+vTPh71LSBrm/Y4/QDZBVCcYfmeTEEuoOYwlSy+G1StfJg+/Zy550u/3TATbm7qDbbMtg==} engines: {node: '>=6.9.0'} - '@babel/generator@8.0.0': - resolution: {integrity: sha512-NT9NrVwJsbSV6Y2FSstWa71EETOnzrjkL5/wX3D2mYHtKM+qvqB1DvR4D0Setb/gDBsHzRICifwEWMO8CnTF6g==} - engines: {node: ^22.18.0 || >=24.11.0} - '@babel/helper-compilation-targets@7.29.7': resolution: {integrity: sha512-wem6WaBj4NaVYVdNhLPPVacES6ZJ+KBBfSkTMD3YZxbP3rm3Di85tJU5ljaUNhaOynt+Aj0xruhYuzQBt8n71g==} engines: {node: '>=6.9.0'} @@ -279,18 +264,10 @@ packages: resolution: {integrity: sha512-Pb5ijPrZ89GDH8223L4UP8i6QApWxs04RbPQJTeWDV0/keR2E36MeKnyr6LYmUUvqRRI+Iv87SuF1W6ErINzYw==} engines: {node: '>=6.9.0'} - '@babel/helper-string-parser@8.0.0': - resolution: {integrity: sha512-6mJgmFFFIIO82vvoLt9XtRC7/TkzXfts1t/SpRX4IHSzMgqoPYCWesVu1udUPUWioAE/2fcG6WuI8zrkE1gwrg==} - engines: {node: ^22.18.0 || >=24.11.0} - '@babel/helper-validator-identifier@7.29.7': resolution: {integrity: sha512-qehxGkRj55h/ff8EMaJ+cYhyaKlHIxqYDn682wQD7RNp9UujOQsHog2uS0r2vzr4pW+sXf90NeeayjcNaX3fFg==} engines: {node: '>=6.9.0'} - '@babel/helper-validator-identifier@8.0.2': - resolution: {integrity: sha512-9Fr9QeyCAyi1BR1jKZ6uYQ24EIhQUx5ReHfQU7drOE+TPOb+w11/dsqLkMOT2U29OdCT71XajrOT8xDc1C7orA==} - engines: {node: ^22.18.0 || >=24.11.0} - '@babel/helper-validator-option@7.29.7': resolution: {integrity: sha512-N9ZErrD+yW5geCDtBqnOoxmR8+tNKiGuxKlDpuJxfsqpa2dFcexaziGAE/qoHLiDDreVNMupxGmSoNlyvsA3gw==} engines: {node: '>=6.9.0'} @@ -299,16 +276,11 @@ packages: resolution: {integrity: sha512-1k2lAGRMfHTcwuNYcCNUmaUffmQv8KWMfh2iJUUeRlwlwH4FdNG7mfPI10NPfLHJFThE4Tyr4mv7kTNZOiPuBg==} engines: {node: '>=6.9.0'} - '@babel/parser@7.29.7': - resolution: {integrity: sha512-hnORnjP/1P/zFEndoeX+n+t1RwWRJiJpM/jO7FW32Kn9r5+sJB2JWOdYo4L6k78j15eCwY3Gm/7364B1EMwtNg==} + '@babel/parser@7.29.8': + resolution: {integrity: sha512-E8lTAYNB1KW+FH+VGJuZM1ioAx2E6oVlvQFRrf5P8ZZmsiJXYAD9vTFV7yyEURNzgh1dFqMZuO6tUwcARbqFCA==} engines: {node: '>=6.0.0'} hasBin: true - '@babel/parser@8.0.0': - resolution: {integrity: sha512-aLxAE+imI9bCcyaPrUDjBv3uSkWieifjLe0kuFOZF0zli0L6GCsTmsePnTr55adbIAgYz2zhN1vnFimCBUYcRQ==} - engines: {node: ^22.18.0 || >=24.11.0} - hasBin: true - '@babel/runtime@7.29.7': resolution: {integrity: sha512-Nq8OhGWiZIZGV6hLHoyAKLLcJihP/xFeBMGJoUrxTX2psI8dCifzLhZISFb+VWS3wFMRDmCGw5R+dOySCqPLhw==} engines: {node: '>=6.9.0'} @@ -317,18 +289,14 @@ packages: resolution: {integrity: sha512-puq+Gf35oI24FeN11LkoUQFqv9uwNeWpxXZi/Ji3rRIoKAzKnxRaZ+Gkj0vKS9ZCiTESfng1N9LyOyXvo+m+Gg==} engines: {node: '>=6.9.0'} - '@babel/traverse@7.29.7': - resolution: {integrity: sha512-EhlfNQtZ+NK22w5BM61ciuiq1m58ed33Wr1Xan//ZRTy6hgjnwyCffRYwzsGXdASJSUJ1guZILsErh1eQcl+zw==} + '@babel/traverse@7.29.8': + resolution: {integrity: sha512-I5z7H3bf/41ktsNVLtpN0wAa336HkqIHQ5BuPLEhTkt1jVSyZpeNKIzTgEWmlxjdg81R0IgUCcaE+Ok3NvrfZg==} engines: {node: '>=6.9.0'} - '@babel/types@7.29.7': - resolution: {integrity: sha512-4zBIxpPzowiZpusoFkyGVwakdRJUyuH5PxQ/PrqghfdFWWasvnCdPfQXHrenDai+gyLARulZjZowCOj6fjT4pA==} + '@babel/types@7.29.8': + resolution: {integrity: sha512-Vj1jF3cPfxg7OAfoI7QnVKLoILlm2JF9pnVHrX8qx7AHMiYWT+NDAA7jChlNgRS4WTLc/fD1lXLmPixluj+3Gg==} engines: {node: '>=6.9.0'} - '@babel/types@8.0.0': - resolution: {integrity: sha512-K8ponJDxBwDHigkeFqaqT5wLGl4bTlwMafR8k7b5CPxr6Ww+UG9ls8Yx6Tcpboxu97eeGVEEyKcHmEyOwN1vSw==} - engines: {node: ^22.18.0 || >=24.11.0} - '@bcoe/v8-coverage@1.0.2': resolution: {integrity: sha512-6zABk/ECA/QYSCQ1NGiVwwbQerUCZ+TQbp64Q3AgmfNvurHH0j8TtXa1qbShXA6qqkpAj4V5W8pP6mLe1mcMqA==} engines: {node: '>=18'} @@ -341,19 +309,19 @@ packages: resolution: {integrity: sha512-ooWCrlZP11i8GImSjTHYHLkvFDP48nS4+204nGb1RiX/WXYHmJA2III9/e2DWVabCESdW7hBAEzHRqUn9OUVvQ==} engines: {node: '>=0.1.90'} - '@csstools/color-helpers@6.1.0': - resolution: {integrity: sha512-064IFJdjTfUqnjpCVpMOdbr8FLQBhinbZj6yRv2An2E41O/pLEXqfFRWqGq/SxlE5PEUYTlvWsG2r8MswAVvkg==} + '@csstools/color-helpers@6.1.1': + resolution: {integrity: sha512-gLNsunvwf3mCi5u5o46/Z/JcJMnhbHSaZ69rkgPzNM3J4s8hWwpPUQB6/tt0EDFyCiWzxANlx+2LJwpYj4zS1w==} engines: {node: '>=20.19.0'} - '@csstools/css-calc@3.2.1': - resolution: {integrity: sha512-DtdHlgXh5ZkA43cwBcAm+huzgJiwx3ZTWVjBs94kwz2xKqSimDA3lBgCjphYgwgVUMWatSM0pDd8TILB1yrVVg==} + '@csstools/css-calc@3.3.0': + resolution: {integrity: sha512-c5ihYsPkdG6JCkU2zTMm4+k6r7RXuGxtWYhu5DHMIiF1FHzrfmHL5so11AoFpUv/tu61xfcmT4AmKoFfMPoqdQ==} engines: {node: '>=20.19.0'} peerDependencies: '@csstools/css-parser-algorithms': ^4.0.0 '@csstools/css-tokenizer': ^4.0.0 - '@csstools/css-color-parser@4.1.9': - resolution: {integrity: sha512-paQcIaOO53Rk5+YrBaBjm/SgrV4INImjo2BT1DtQRYr+XeTRbeAYlS+jxXp9drqvKmtFnWRJKIalDLhZZDu42A==} + '@csstools/css-color-parser@4.2.2': + resolution: {integrity: sha512-3QKjR/vxyjcSXBLgb6lP0S3MGdvwbmqSsvLPbYdVORqPDc8FX1HAJ0Spk38bxaRXgvENTA47tlhhbb5Z2e8hEg==} engines: {node: '>=20.19.0'} peerDependencies: '@csstools/css-parser-algorithms': ^4.0.0 @@ -365,8 +333,8 @@ packages: peerDependencies: '@csstools/css-tokenizer': ^4.0.0 - '@csstools/css-syntax-patches-for-csstree@1.1.6': - resolution: {integrity: sha512-TcJCWFbXLPpJYq6z7bfOyjWYJDiDg2/I4gyUC9pqPNqHFRIey0EB0q0L5cSnQDfWJg8Jd6VadakxdIez/3zkqQ==} + '@csstools/css-syntax-patches-for-csstree@1.1.12': + resolution: {integrity: sha512-3vLQK+dXxhBMR2Wx99PTCifE+vHtW2ndZWyla8yK813ev6oGhyn8Lja8jCyGAWTJ+LEYZK7EVtJxrDj8ztevJw==} peerDependencies: css-tree: ^3.2.1 peerDependenciesMeta: @@ -380,179 +348,14 @@ packages: '@emnapi/core@1.10.0': resolution: {integrity: sha512-yq6OkJ4p82CAfPl0u9mQebQHKPJkY7WrIuk205cTYnYe+k2Z8YBh11FrbRG/H6ihirqcacOgl2BIO8oyMQLeXw==} - '@emnapi/core@1.11.1': - resolution: {integrity: sha512-RSvbQmHzdKzNsLYa/wHrbc3KN4sYLKAdPZxqiM2HATqv/SBk2/ENSHpvXGaLOMcsAyz0poEGqkmmKYG3OWiJEQ==} - '@emnapi/runtime@1.10.0': resolution: {integrity: sha512-ewvYlk86xUoGI0zQRNq/mC+16R1QeDlKQy21Ki3oSYXNgLb45GV1P6A0M+/s6nyCuNDqe5VpaY84BzXGwVbwFA==} - '@emnapi/runtime@1.11.1': - resolution: {integrity: sha512-vgj7R3y3Wgx24IQaGPA/R6YFXLHVMOZ0uVEyIQPaWs+rd1AzfEMXlAC22FYwO1XkKR6NPsq7mUandH8oIRdZFw==} - '@emnapi/wasi-threads@1.2.1': resolution: {integrity: sha512-uTII7OYF+/Mes/MrcIOYp5yOtSMLBWSIoLPpcgwipoiKbli6k322tcoFsxoIIxPDqW01SQGAgko4EzZi2BNv2w==} - '@emnapi/wasi-threads@1.2.2': - resolution: {integrity: sha512-c95qOXkHdydNKhscBTebqEC1CVAZpyqOfVfBzQ1qgzyl3gfeldUjIggDbIZgDKsHLgnsM+igH7TJ/eAasaVuMA==} - - '@esbuild/aix-ppc64@0.27.2': - resolution: {integrity: sha512-GZMB+a0mOMZs4MpDbj8RJp4cw+w1WV5NYD6xzgvzUJ5Ek2jerwfO2eADyI6ExDSUED+1X8aMbegahsJi+8mgpw==} - engines: {node: '>=18'} - cpu: [ppc64] - os: [aix] - - '@esbuild/android-arm64@0.27.2': - resolution: {integrity: sha512-pvz8ZZ7ot/RBphf8fv60ljmaoydPU12VuXHImtAs0XhLLw+EXBi2BLe3OYSBslR4rryHvweW5gmkKFwTiFy6KA==} - engines: {node: '>=18'} - cpu: [arm64] - os: [android] - - '@esbuild/android-arm@0.27.2': - resolution: {integrity: sha512-DVNI8jlPa7Ujbr1yjU2PfUSRtAUZPG9I1RwW4F4xFB1Imiu2on0ADiI/c3td+KmDtVKNbi+nffGDQMfcIMkwIA==} - engines: {node: '>=18'} - cpu: [arm] - os: [android] - - '@esbuild/android-x64@0.27.2': - resolution: {integrity: sha512-z8Ank4Byh4TJJOh4wpz8g2vDy75zFL0TlZlkUkEwYXuPSgX8yzep596n6mT7905kA9uHZsf/o2OJZubl2l3M7A==} - engines: {node: '>=18'} - cpu: [x64] - os: [android] - - '@esbuild/darwin-arm64@0.27.2': - resolution: {integrity: sha512-davCD2Zc80nzDVRwXTcQP/28fiJbcOwvdolL0sOiOsbwBa72kegmVU0Wrh1MYrbuCL98Omp5dVhQFWRKR2ZAlg==} - engines: {node: '>=18'} - cpu: [arm64] - os: [darwin] - - '@esbuild/darwin-x64@0.27.2': - resolution: {integrity: sha512-ZxtijOmlQCBWGwbVmwOF/UCzuGIbUkqB1faQRf5akQmxRJ1ujusWsb3CVfk/9iZKr2L5SMU5wPBi1UWbvL+VQA==} - engines: {node: '>=18'} - cpu: [x64] - os: [darwin] - - '@esbuild/freebsd-arm64@0.27.2': - resolution: {integrity: sha512-lS/9CN+rgqQ9czogxlMcBMGd+l8Q3Nj1MFQwBZJyoEKI50XGxwuzznYdwcav6lpOGv5BqaZXqvBSiB/kJ5op+g==} - engines: {node: '>=18'} - cpu: [arm64] - os: [freebsd] - - '@esbuild/freebsd-x64@0.27.2': - resolution: {integrity: sha512-tAfqtNYb4YgPnJlEFu4c212HYjQWSO/w/h/lQaBK7RbwGIkBOuNKQI9tqWzx7Wtp7bTPaGC6MJvWI608P3wXYA==} - engines: {node: '>=18'} - cpu: [x64] - os: [freebsd] - - '@esbuild/linux-arm64@0.27.2': - resolution: {integrity: sha512-hYxN8pr66NsCCiRFkHUAsxylNOcAQaxSSkHMMjcpx0si13t1LHFphxJZUiGwojB1a/Hd5OiPIqDdXONia6bhTw==} - engines: {node: '>=18'} - cpu: [arm64] - os: [linux] - - '@esbuild/linux-arm@0.27.2': - resolution: {integrity: sha512-vWfq4GaIMP9AIe4yj1ZUW18RDhx6EPQKjwe7n8BbIecFtCQG4CfHGaHuh7fdfq+y3LIA2vGS/o9ZBGVxIDi9hw==} - engines: {node: '>=18'} - cpu: [arm] - os: [linux] - - '@esbuild/linux-ia32@0.27.2': - resolution: {integrity: sha512-MJt5BRRSScPDwG2hLelYhAAKh9imjHK5+NE/tvnRLbIqUWa+0E9N4WNMjmp/kXXPHZGqPLxggwVhz7QP8CTR8w==} - engines: {node: '>=18'} - cpu: [ia32] - os: [linux] - - '@esbuild/linux-loong64@0.27.2': - resolution: {integrity: sha512-lugyF1atnAT463aO6KPshVCJK5NgRnU4yb3FUumyVz+cGvZbontBgzeGFO1nF+dPueHD367a2ZXe1NtUkAjOtg==} - engines: {node: '>=18'} - cpu: [loong64] - os: [linux] - - '@esbuild/linux-mips64el@0.27.2': - resolution: {integrity: sha512-nlP2I6ArEBewvJ2gjrrkESEZkB5mIoaTswuqNFRv/WYd+ATtUpe9Y09RnJvgvdag7he0OWgEZWhviS1OTOKixw==} - engines: {node: '>=18'} - cpu: [mips64el] - os: [linux] - - '@esbuild/linux-ppc64@0.27.2': - resolution: {integrity: sha512-C92gnpey7tUQONqg1n6dKVbx3vphKtTHJaNG2Ok9lGwbZil6DrfyecMsp9CrmXGQJmZ7iiVXvvZH6Ml5hL6XdQ==} - engines: {node: '>=18'} - cpu: [ppc64] - os: [linux] - - '@esbuild/linux-riscv64@0.27.2': - resolution: {integrity: sha512-B5BOmojNtUyN8AXlK0QJyvjEZkWwy/FKvakkTDCziX95AowLZKR6aCDhG7LeF7uMCXEJqwa8Bejz5LTPYm8AvA==} - engines: {node: '>=18'} - cpu: [riscv64] - os: [linux] - - '@esbuild/linux-s390x@0.27.2': - resolution: {integrity: sha512-p4bm9+wsPwup5Z8f4EpfN63qNagQ47Ua2znaqGH6bqLlmJ4bx97Y9JdqxgGZ6Y8xVTixUnEkoKSHcpRlDnNr5w==} - engines: {node: '>=18'} - cpu: [s390x] - os: [linux] - - '@esbuild/linux-x64@0.27.2': - resolution: {integrity: sha512-uwp2Tip5aPmH+NRUwTcfLb+W32WXjpFejTIOWZFw/v7/KnpCDKG66u4DLcurQpiYTiYwQ9B7KOeMJvLCu/OvbA==} - engines: {node: '>=18'} - cpu: [x64] - os: [linux] - - '@esbuild/netbsd-arm64@0.27.2': - resolution: {integrity: sha512-Kj6DiBlwXrPsCRDeRvGAUb/LNrBASrfqAIok+xB0LxK8CHqxZ037viF13ugfsIpePH93mX7xfJp97cyDuTZ3cw==} - engines: {node: '>=18'} - cpu: [arm64] - os: [netbsd] - - '@esbuild/netbsd-x64@0.27.2': - resolution: {integrity: sha512-HwGDZ0VLVBY3Y+Nw0JexZy9o/nUAWq9MlV7cahpaXKW6TOzfVno3y3/M8Ga8u8Yr7GldLOov27xiCnqRZf0tCA==} - engines: {node: '>=18'} - cpu: [x64] - os: [netbsd] - - '@esbuild/openbsd-arm64@0.27.2': - resolution: {integrity: sha512-DNIHH2BPQ5551A7oSHD0CKbwIA/Ox7+78/AWkbS5QoRzaqlev2uFayfSxq68EkonB+IKjiuxBFoV8ESJy8bOHA==} - engines: {node: '>=18'} - cpu: [arm64] - os: [openbsd] - - '@esbuild/openbsd-x64@0.27.2': - resolution: {integrity: sha512-/it7w9Nb7+0KFIzjalNJVR5bOzA9Vay+yIPLVHfIQYG/j+j9VTH84aNB8ExGKPU4AzfaEvN9/V4HV+F+vo8OEg==} - engines: {node: '>=18'} - cpu: [x64] - os: [openbsd] - - '@esbuild/openharmony-arm64@0.27.2': - resolution: {integrity: sha512-LRBbCmiU51IXfeXk59csuX/aSaToeG7w48nMwA6049Y4J4+VbWALAuXcs+qcD04rHDuSCSRKdmY63sruDS5qag==} - engines: {node: '>=18'} - cpu: [arm64] - os: [openharmony] - - '@esbuild/sunos-x64@0.27.2': - resolution: {integrity: sha512-kMtx1yqJHTmqaqHPAzKCAkDaKsffmXkPHThSfRwZGyuqyIeBvf08KSsYXl+abf5HDAPMJIPnbBfXvP2ZC2TfHg==} - engines: {node: '>=18'} - cpu: [x64] - os: [sunos] - - '@esbuild/win32-arm64@0.27.2': - resolution: {integrity: sha512-Yaf78O/B3Kkh+nKABUF++bvJv5Ijoy9AN1ww904rOXZFLWVc5OLOfL56W+C8F9xn5JQZa3UX6m+IktJnIb1Jjg==} - engines: {node: '>=18'} - cpu: [arm64] - os: [win32] - - '@esbuild/win32-ia32@0.27.2': - resolution: {integrity: sha512-Iuws0kxo4yusk7sw70Xa2E2imZU5HoixzxfGCdxwBdhiDgt9vX9VUCBhqcwY7/uh//78A1hMkkROMJq9l27oLQ==} - engines: {node: '>=18'} - cpu: [ia32] - os: [win32] - - '@esbuild/win32-x64@0.27.2': - resolution: {integrity: sha512-sRdU18mcKf7F+YgheI/zGf5alZatMUTKj/jNS6l744f9u3WFu4v7twcUI9vu4mknF4Y9aDlblIie0IM+5xxaqQ==} - engines: {node: '>=18'} - cpu: [x64] - os: [win32] - - '@eslint-community/eslint-utils@4.9.1': - resolution: {integrity: sha512-phrYmNiYppR7znFEdqgfWHXR6NCkZEK7hwWDHZUjit/2/U0r6XvkDl0SYnoM51Hq7FhCGdLDT6zxCCOY1hexsQ==} + '@eslint-community/eslint-utils@4.10.1': + resolution: {integrity: sha512-cuadcxVFE8sDK6iWJbs8Sn0av2Nrh2QSGQhVlBW9AaAHqHwjWsZHT8LJ4hFGPh7ASBV2deFdM7H/DPjulmh8rg==} engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0} peerDependencies: eslint: ^6.0.0 || ^7.0.0 || >=8.0.0 @@ -573,12 +376,12 @@ packages: resolution: {integrity: sha512-yL/sLrpmtDaFEiUj1osRP4TI2MDz1AddJL+jZ7KSqvBuliN4xqYY54IfdN8qD8Toa6g1iloph1fxQNkjOxrrpQ==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} - '@eslint/eslintrc@3.3.5': - resolution: {integrity: sha512-4IlJx0X0qftVsN5E+/vGujTRIFtwuLbNsVUe7TO6zYPDR1O6nFwvwhIKEKSrl6dZchmYBITazxKoUYOjdtjlRg==} + '@eslint/eslintrc@3.3.7': + resolution: {integrity: sha512-F42g89Qd5oAWtp0k0nnSrjziAKza7w8SVT4mStc18LZMaRb4J1HQAHLCalEtDCxrTuksx7NU9qsmeLwpOfPqWw==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} - '@eslint/js@9.39.4': - resolution: {integrity: sha512-nE7DEIchvtiFTwBw4Lfbu59PG+kCofhjsKaCWzxTpt4lfRjRMqG6uMBzKXuEcyXhOHoUp9riAm7/aWYGhXZ9cw==} + '@eslint/js@9.39.5': + resolution: {integrity: sha512-QywQuszQh77pIXCsq998c8hbhSTI/azTty1Z6N53dmAudKHhy573j3yvRLsX2BSp8YpLtoCEG8E9DJe+8zUh4A==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} '@eslint/object-schema@2.1.7': @@ -618,14 +421,6 @@ packages: resolution: {integrity: sha512-bV0Tgo9K4hfPCek+aMAn81RppFKv2ySDQeMoSZuvTASywNTnVJCArCZE2FWqpvIatKu7VMRLWlR1EazvVhDyhQ==} engines: {node: '>=18.18'} - '@isaacs/cliui@8.0.2': - resolution: {integrity: sha512-O8jcjabXaleOG9DQ0+ARXWZBTfnP4WNAqzuiJK7ll44AmxGKv/J2M4TPjxjY3znBCfvBXFzucm1twdyFybFqEA==} - engines: {node: '>=12'} - - '@istanbuljs/schema@0.1.6': - resolution: {integrity: sha512-+Sg6GCR/wy1oSmQDFq4LQDAhm3ETKnorxN+y5nbLULOR3P0c14f2Wurzj3/xqPXtasLFfHd5iRFQ7AJt4KH2cw==} - engines: {node: '>=8'} - '@jridgewell/gen-mapping@0.3.13': resolution: {integrity: sha512-2kkt/7niJ6MgEPxF0bYdQ6etZaA+fQvDcLKckhy1yIQOzaoKjBBjSj63/aLVjYE3qhRt5dvM+uUyfCg6UKCBbA==} @@ -636,75 +431,81 @@ packages: resolution: {integrity: sha512-bRISgCIjP20/tbWSPWMEi54QVPRZExkuD9lJL+UIxUKtwVJA8wW1Trb1jMs1RFXo1CBTNZ/5hpC9QvmKWdopKw==} engines: {node: '>=6.0.0'} - '@jridgewell/sourcemap-codec@1.5.5': - resolution: {integrity: sha512-cYQ9310grqxueWbl+WuIUIaiUaDcj7WOq5fVhEljNVgRfOUhY9fy2zTvfoqWsnebh8Sl70VScFbICvJnLKB0Og==} + '@jridgewell/sourcemap-codec@1.6.0': + resolution: {integrity: sha512-T7jf+5zgsZHwNJ4lvQ7/aezbyk0nNX+zJVWpmHA7VYsEx7a7qr5Rg5IbtJFqkgze5Y2sruq1RUY8Q837Od7iFw==} '@jridgewell/trace-mapping@0.3.31': resolution: {integrity: sha512-zzNR+SdQSDJzc8joaeP8QQoCQr8NuYx2dIIytl1QeBEZHJ9uW6hebsrYgbz8hJwUQao3TWCMtmfV8Nu1twOLAw==} - '@napi-rs/wasm-runtime@1.1.6': - resolution: {integrity: sha512-ZLv/JdUfkvOy9eCnnBaGfiO+XimbjebAeO+MRQqD/B+FR1tnRN0tpKSJHRbE8sFfS6aqsXZ67TQjfwfsxULVbg==} + '@napi-rs/wasm-runtime@1.2.3': + resolution: {integrity: sha512-UMduMbqO5s5zF2NkNacMT/yK5Y5QiKvWr2+50bzIIxFDwVJ2h49b+oyjaCGPhJxd2/gC2x39EHv/gHVuu36x2Q==} + engines: {node: ^20.19.0 || ^22.13.0 || >=23.5.0} peerDependencies: - '@emnapi/core': ^1.7.1 - '@emnapi/runtime': ^1.7.1 + '@emnapi/core': ^1.7.1 || ^2.0.0-alpha.4 + '@emnapi/runtime': ^1.7.1 || ^2.0.0-alpha.4 '@octokit/auth-token@6.0.0': resolution: {integrity: sha512-P4YJBPdPSpWTQ1NU4XYdvHvXJJDxM6YwpS0FZHRgP7YFkdVxsWcpWGy/NVqlAA7PcPCnMacXlRm1y2PFZRWL/w==} engines: {node: '>= 20'} - '@octokit/core@7.0.6': - resolution: {integrity: sha512-DhGl4xMVFGVIyMwswXeyzdL4uXD5OGILGX5N8Y+f6W7LhC1Ze2poSNrkF/fedpVDHEEZ+PHFW0vL14I+mm8K3Q==} + '@octokit/core@7.0.8': + resolution: {integrity: sha512-L7y8eYc+AwxGr2PWI4WFt1VG4TiJ66c26BD16mXpYIlXxG0SMigM1+m4aTSlYyBr5BlQsGAlz8uDCoZN4SEMcg==} engines: {node: '>= 20'} - '@octokit/endpoint@11.0.3': - resolution: {integrity: sha512-FWFlNxghg4HrXkD3ifYbS/IdL/mDHjh9QcsNyhQjN8dplUoZbejsdpmuqdA76nxj2xoWPs7p8uX2SNr9rYu0Ag==} + '@octokit/endpoint@11.0.5': + resolution: {integrity: sha512-iXa654H3yFafF/ieHkukfbgWo2rmXD2ceD0ZOtrPhw1bc3FDch1d9N/TNs0FQ1/cIbwb7kspUX8jzIs8nzb9DQ==} engines: {node: '>= 20'} - '@octokit/graphql@9.0.3': - resolution: {integrity: sha512-grAEuupr/C1rALFnXTv6ZQhFuL1D8G5y8CN04RgrO4FIPMrtm+mcZzFG7dcBm+nq+1ppNixu+Jd78aeJOYxlGA==} + '@octokit/graphql@9.0.5': + resolution: {integrity: sha512-bt/hm03LeU6Vy7FwTrkkC9p3XGT/lBwClglMqxBSe5/q0E5CdJTXeAqEI0vlw89/LF/G6tryTIH8HirZ3prMVg==} engines: {node: '>= 20'} '@octokit/openapi-types@27.0.0': resolution: {integrity: sha512-whrdktVs1h6gtR+09+QsNk2+FO+49j6ga1c55YZudfEG+oKJVvJLQi3zkOm5JjiUXAagWK2tI2kTGKJ2Ys7MGA==} + '@octokit/openapi-types@28.0.0': + resolution: {integrity: sha512-0rFyLuyHvIj6uuZWuDslxkowFYdPXoNIkeAv4b27dzm2Tf4vGWXnPsMcxs7d65kLdMERgP3wc1AEPlqMz8e1cQ==} + + '@octokit/openapi-types@29.0.1': + resolution: {integrity: sha512-9qWOMFNxxLokERcms42rU0PTLqQmVs7g5E41TI4mCOxmpFayD1rfC7XxOL55cG9MBZLFlC31BrR37myMKardwg==} + '@octokit/plugin-paginate-rest@14.0.0': resolution: {integrity: sha512-fNVRE7ufJiAA3XUrha2omTA39M6IXIc6GIZLvlbsm8QOQCYvpq/LkMNGyFlB1d8hTDzsAXa3OKtybdMAYsV/fw==} engines: {node: '>= 20'} peerDependencies: '@octokit/core': '>=6' - '@octokit/plugin-retry@8.1.0': - resolution: {integrity: sha512-O1FZgXeiGb2sowEr/hYTr6YunGdSAFWnr2fyW39Ah85H8O33ELASQxcvOFF5LE6Tjekcyu2ms4qAzJVhSaJxTw==} + '@octokit/plugin-retry@8.1.1': + resolution: {integrity: sha512-VCVvZ/R1+u3WuiBWpNavZ0mY4aaJNAsENrpBP9aLSR2QyOpQgd7DhM5j4AW7z4MQpnJYgwBPf0XqPQoNBRdQwg==} engines: {node: '>= 20'} peerDependencies: '@octokit/core': '>=7' - '@octokit/plugin-throttling@11.0.3': - resolution: {integrity: sha512-34eE0RkFCKycLl2D2kq7W+LovheM/ex3AwZCYN8udpi6bxsyjZidb2McXs69hZhLmJlDqTSP8cH+jSRpiaijBg==} + '@octokit/plugin-throttling@11.0.5': + resolution: {integrity: sha512-LIdrkrUv+DWbKeg/49rGuFJ3SU0d3hUS+B4MhNZLepBoNUFXms8Ic9edJjrlx+zycqJHjrMRudVpVb/bAXM2Lw==} engines: {node: '>= 20'} peerDependencies: '@octokit/core': ^7.0.0 - '@octokit/request-error@7.1.0': - resolution: {integrity: sha512-KMQIfq5sOPpkQYajXHwnhjCC0slzCNScLHs9JafXc4RAJI+9f+jNDlBNaIMTvazOPLgb4BnlhGJOTbnN0wIjPw==} + '@octokit/request-error@7.1.2': + resolution: {integrity: sha512-XZRuT3xZ84D3gYErI1DZvhJ33dCWVV6uzBtWkaBB4TvA/L6eOeTZodxLFVB44bBEEo3vEx7y00UfX1tBLrtLRg==} engines: {node: '>= 20'} - '@octokit/request@10.0.10': - resolution: {integrity: sha512-KxNC2pTqqhszMNrf12ZRd4PonRgyJdsM4F/jySiddQK+DsRcfBtUvqn8t7UsyZhnRJHvX46OohDt5N3VqIWC2w==} + '@octokit/request@10.0.16': + resolution: {integrity: sha512-A0zWGjHzISIb+9ccG8s0dq7LKO5zVpJLRICjgUb+sJxEWqn8RUHB1rD3AE51+PECvXHIxqZ1VVvs4fHTSD9nUQ==} engines: {node: '>= 20'} '@octokit/types@16.0.0': resolution: {integrity: sha512-sKq+9r1Mm4efXW1FCk7hFSeJo4QKreL/tTbR0rz/qx/r1Oa2VV83LTA/H/MuCOX7uCIJmQVRKBcbmWoySjAnSg==} - '@oxc-project/types@0.127.0': - resolution: {integrity: sha512-aIYXQBo4lCbO4z0R3FHeucQHpF46l2LbMdxRvqvuRuW2OxdnSkcng5B8+K12spgLDj93rtN3+J2Vac/TIO+ciQ==} + '@octokit/types@17.0.0': + resolution: {integrity: sha512-ByP1v7YL5SMveFPP7+sj0/ZuWCOOg/Chs4NafOMpq6WNIM/hdGY0S7C0TCGDBWu1aGmOxmUIhMx3cO+IdwYZ1Q==} - '@oxc-project/types@0.137.0': - resolution: {integrity: sha512-WT+Gb24i8hmvo85AIv2oEYouEXkRlKAlT9WaCa3TfLgNCN+GhrJOGZuIlMouAh38Qe4QOx26eUOVsq70qXrywA==} + '@octokit/types@18.0.0': + resolution: {integrity: sha512-l6bAF43PNxkJp6g+W4PjoUSSkxHomXw2nOum5CTftJz1NlV3vu93NImgOYtLf6CbBUb5j+fiuzW0PPQ5JTSvZA==} - '@pkgjs/parseargs@0.11.0': - resolution: {integrity: sha512-+1VkjdD0QBLPodGrJUeqarH8VAIvQODIbwh9XpP5Syisf7YoQgsJKPNFoqqLQlu+VQ/tVSshMR6loPMn8U+dPg==} - engines: {node: '>=14'} + '@oxc-project/types@0.148.0': + resolution: {integrity: sha512-Nm4s/jB+4FpFsPhWGEC4h7rzksesmtnMXomo6rCMcg/b8zLQuOziRgkCS1fxDCXOlJB/6Q8oABOZ/OP6RIPj9A==} '@pnpm/config.env-replace@1.1.0': resolution: {integrity: sha512-htyl8TWnKL7K/ESFa1oW2UB5lVDxuF5DpM7tBi6Hu2LNL3mWkIzNLG6N4zoCUP1lCKNxWy/3iu8mS8MvToGd6w==} @@ -721,351 +522,116 @@ packages: '@quansync/fs@1.0.0': resolution: {integrity: sha512-4TJ3DFtlf1L5LDMaM6CanJ/0lckGNtJcMjQ1NAV6zDmA0tEHKZtxNKin8EgPaVX1YzljbxckyT2tJrpQKAtngQ==} - '@rolldown/binding-android-arm64@1.0.0-rc.17': - resolution: {integrity: sha512-s70pVGhw4zqGeFnXWvAzJDlvxhlRollagdCCKRgOsgUOH3N1l0LIxf83AtGzmb5SiVM4Hjl5HyarMRfdfj3DaQ==} + '@rolldown/binding-android-arm-eabi@1.2.7': + resolution: {integrity: sha512-EypzgnYCwyVY4NDHKzGmNJT5b+XaQEBniHxsMdeIQLB/tcCzZnhqrzHpZFbX9iaxx+5RiB8caATBtfvZP7zVxQ==} engines: {node: ^20.19.0 || >=22.12.0} - cpu: [arm64] + cpu: [arm] os: [android] - '@rolldown/binding-android-arm64@1.1.3': - resolution: {integrity: sha512-DT6Z3PhvioeHMvxo+xHc3KtqggrI7CCTXCmC2h/5zUlp5jVitv7XEy+9q5/7v8IolhlioawpMo8Kg0EEBy7J0g==} + '@rolldown/binding-android-arm64@1.2.7': + resolution: {integrity: sha512-l17HE9EweWaqJZhuUuNBN/FzM62xw+DECVnJyvMsxn8vJFAGLy5QfLDoYAcronkAN8VxKZHezDpulHDPx95vFw==} engines: {node: ^20.19.0 || >=22.12.0} cpu: [arm64] os: [android] - '@rolldown/binding-darwin-arm64@1.0.0-rc.17': - resolution: {integrity: sha512-4ksWc9n0mhlZpZ9PMZgTGjeOPRu8MB1Z3Tz0Mo02eWfWCHMW1zN82Qz/pL/rC+yQa+8ZnutMF0JjJe7PjwasYw==} - engines: {node: ^20.19.0 || >=22.12.0} - cpu: [arm64] - os: [darwin] - - '@rolldown/binding-darwin-arm64@1.1.3': - resolution: {integrity: sha512-0NwgwsjM7LrsuVnXMK3koTpagBNOhloc/BNjKqZjv4V5zI5r13qx69uVhRx+o5Z0yy4Hzq+lpy7TAgUG/ocvrw==} + '@rolldown/binding-darwin-arm64@1.2.7': + resolution: {integrity: sha512-8ED8ELFvHXc6OCETIn4gXObPiaR6bckM/ipXtbzlPVDRMBfEGjCKgO90F9YtfdpDatVx/ZQw7aZ1vUMf/+T3Mw==} engines: {node: ^20.19.0 || >=22.12.0} cpu: [arm64] os: [darwin] - '@rolldown/binding-darwin-x64@1.0.0-rc.17': - resolution: {integrity: sha512-SUSDOI6WwUVNcWxd02QEBjLdY1VPHvlEkw6T/8nYG322iYWCTxRb1vzk4E+mWWYehTp7ERibq54LSJGjmouOsw==} + '@rolldown/binding-darwin-x64@1.2.7': + resolution: {integrity: sha512-/WPripjtiAIZ2tWY7ddijORT0Ujg87wxWW/qcoFVCKAWVDPhtY0xr7Dj0M3GyNGz60jGwTElhro/mkF9dT7dDQ==} engines: {node: ^20.19.0 || >=22.12.0} cpu: [x64] os: [darwin] - '@rolldown/binding-darwin-x64@1.1.3': - resolution: {integrity: sha512-YtiBp4disu6V560loT6PjMdiRaWmVvDNrUunAalbiFx2ggeJwxdAsgZMcoGP17uyAsTwAj5V1niksxlHnVQ1Sw==} - engines: {node: ^20.19.0 || >=22.12.0} - cpu: [x64] - os: [darwin] - - '@rolldown/binding-freebsd-x64@1.0.0-rc.17': - resolution: {integrity: sha512-hwnz3nw9dbJ05EDO/PvcjaaewqqDy7Y1rn1UO81l8iIK1GjenME75dl16ajbvSSMfv66WXSRCYKIqfgq2KCfxw==} + '@rolldown/binding-freebsd-x64@1.2.7': + resolution: {integrity: sha512-14DI4NcqpvbICxSnGLx3PmtDaWqRP/KGSGb6C+JLLVPeZRl6dKdHba3pGsqT3vpdTqhEYIPG0MMQ8c0xYqoJxA==} engines: {node: ^20.19.0 || >=22.12.0} cpu: [x64] os: [freebsd] - '@rolldown/binding-freebsd-x64@1.1.3': - resolution: {integrity: sha512-yD3EkEdXk2LypPxnf/kSZHirarsI8gcPzc62SukhR9VJTyvV+F9Q/GxWNuCojc7sXyuVC4DxRGhdDK4X8VSsbw==} - engines: {node: ^20.19.0 || >=22.12.0} - cpu: [x64] - os: [freebsd] - - '@rolldown/binding-linux-arm-gnueabihf@1.0.0-rc.17': - resolution: {integrity: sha512-IS+W7epTcwANmFSQFrS1SivEXHtl1JtuQA9wlxrZTcNi6mx+FDOYrakGevvvTwgj2JvWiK8B29/qD9BELZPyXQ==} + '@rolldown/binding-linux-arm-gnueabihf@1.2.7': + resolution: {integrity: sha512-bxrWIRvHWQvbJwi+VIie/kDJmQxcNE6xxWwZdqF/ExVAigtHkv54WTLQPb+QsZdnFy18fg7JPfWGL0RH6vwIlQ==} engines: {node: ^20.19.0 || >=22.12.0} cpu: [arm] os: [linux] - '@rolldown/binding-linux-arm-gnueabihf@1.1.3': - resolution: {integrity: sha512-c+8vieQbsD7HNAHKIA34w0GJ9FedFFuJGD+7E6vz7Q3uqAIugL5p45fhlsj4UaAsHpcmlqugBWMhA0/j7o0sIg==} - engines: {node: ^20.19.0 || >=22.12.0} - cpu: [arm] - os: [linux] - - '@rolldown/binding-linux-arm64-gnu@1.0.0-rc.17': - resolution: {integrity: sha512-e6usGaHKW5BMNZOymS1UcEYGowQMWcgZ71Z17Sl/h2+ZziNJ1a9n3Zvcz6LdRyIW5572wBCTH/Z+bKuZouGk9Q==} - engines: {node: ^20.19.0 || >=22.12.0} - cpu: [arm64] - os: [linux] - libc: [glibc] - - '@rolldown/binding-linux-arm64-gnu@1.1.3': - resolution: {integrity: sha512-50jD0uUwLvur7Zz9LHz17kaAdTPjn5wN93hEgjvmYFRZwiR7ZJYovTd5ipyWJDAnXKvZ+wgc+/Ika6dwSF5OcA==} + '@rolldown/binding-linux-arm64-gnu@1.2.7': + resolution: {integrity: sha512-toOY2BChBZyuxU7OYX6Tn389di4IzAqPTycVcci0O7FSfBqzRB3RZn+K5Is6ANf4tmgRd/K1yZTsNTXbkXsnLg==} engines: {node: ^20.19.0 || >=22.12.0} cpu: [arm64] os: [linux] libc: [glibc] - '@rolldown/binding-linux-arm64-musl@1.0.0-rc.17': - resolution: {integrity: sha512-b/CgbwAJpmrRLp02RPfhbudf5tZnN9nsPWK82znefso832etkem8H7FSZwxrOI9djcdTP7U6YfNhbRnh7djErg==} + '@rolldown/binding-linux-arm64-musl@1.2.7': + resolution: {integrity: sha512-lAIXTH/aiLRLxsTgQvfhjo4K1ydWIp00+V0voOr9beb/9ZmkUFrSIb03dXNFRgMNvkE6oGsF10ioQ6UsI+vS5Q==} engines: {node: ^20.19.0 || >=22.12.0} cpu: [arm64] os: [linux] libc: [musl] - '@rolldown/binding-linux-arm64-musl@1.1.3': - resolution: {integrity: sha512-BO9+oPL8K9poZJBfYPsXNtYjPE5uM3qeehT3aFcW4LITOl+iSqhp0abzjR2nWBUNjIZeKXjAEWBZ64WjNoHd6w==} - engines: {node: ^20.19.0 || >=22.12.0} - cpu: [arm64] - os: [linux] - libc: [musl] - - '@rolldown/binding-linux-ppc64-gnu@1.0.0-rc.17': - resolution: {integrity: sha512-4EII1iNGRUN5WwGbF/kOh/EIkoDN9HsupgLQoXfY+D1oyJm7/F4t5PYU5n8SWZgG0FEwakyM8pGgwcBYruGTlA==} + '@rolldown/binding-linux-ppc64-gnu@1.2.7': + resolution: {integrity: sha512-kdnwS28Pkenp/mZMRwjXXXwxQ7pIsm+bF919LUK93BOyhcLsrVKdP2p9fxpiPNPAbNuch8ypQt0pm2P2LYCAGg==} engines: {node: ^20.19.0 || >=22.12.0} cpu: [ppc64] os: [linux] libc: [glibc] - '@rolldown/binding-linux-ppc64-gnu@1.1.3': - resolution: {integrity: sha512-f3VpLB1vQ0Eo6ecr/6cekLnvYMFF4YBFoVGkfkvPLq1bAkbAwHYQPZKoAmG6OJyTcxxoC+AvezGx/S1obNC0Mw==} - engines: {node: ^20.19.0 || >=22.12.0} - cpu: [ppc64] - os: [linux] - libc: [glibc] - - '@rolldown/binding-linux-s390x-gnu@1.0.0-rc.17': - resolution: {integrity: sha512-AH8oq3XqQo4IibpVXvPeLDI5pzkpYn0WiZAfT05kFzoJ6tQNzwRdDYQ45M8I/gslbodRZwW8uxLhbSBbkv96rA==} + '@rolldown/binding-linux-s390x-gnu@1.2.7': + resolution: {integrity: sha512-516OdsyLdr5E65paF3yBF55t8mfm9+gmtCsK3xI7XKXIT7EfRlHhxL8K/NR6Hu8BWSgF5+1w74lTL0+nxcc8Qw==} engines: {node: ^20.19.0 || >=22.12.0} cpu: [s390x] os: [linux] libc: [glibc] - '@rolldown/binding-linux-s390x-gnu@1.1.3': - resolution: {integrity: sha512-AmurZ26Pqx/RI9N1gzEOCklkKXl927yjfXWUUS0O7Puh8ARM/Ob8qfrD3qnWksScdw6cSrW5PSHE9DyLu7+PtA==} - engines: {node: ^20.19.0 || >=22.12.0} - cpu: [s390x] - os: [linux] - libc: [glibc] - - '@rolldown/binding-linux-x64-gnu@1.0.0-rc.17': - resolution: {integrity: sha512-cLnjV3xfo7KslbU41Z7z8BH/E1y5mzUYzAqih1d1MDaIGZRCMqTijqLv76/P7fyHuvUcfGsIpqCdddbxLLK9rA==} - engines: {node: ^20.19.0 || >=22.12.0} - cpu: [x64] - os: [linux] - libc: [glibc] - - '@rolldown/binding-linux-x64-gnu@1.1.3': - resolution: {integrity: sha512-JJpqs8bRGITDOdbkNKnlojzBabbOHrqjSvDr0IVsZObE1lBcPjxItUEY9eWIDbxaJ3cGrXPWGfGkIxFijg/URg==} + '@rolldown/binding-linux-x64-gnu@1.2.7': + resolution: {integrity: sha512-r8/z8n7GFaYRln3xmP1Cxy0HH/HLM0uBUPkEuSVEfKGDA89M0FsZRZJRSwe/tJjRx+fpH/gjorfhB8tmEbSFLA==} engines: {node: ^20.19.0 || >=22.12.0} cpu: [x64] os: [linux] libc: [glibc] - '@rolldown/binding-linux-x64-musl@1.0.0-rc.17': - resolution: {integrity: sha512-0phclDw1spsL7dUB37sIARuis2tAgomCJXAHZlpt8PXZ4Ba0dRP1e+66lsRqrfhISeN9bEGNjQs+T/Fbd7oYGw==} - engines: {node: ^20.19.0 || >=22.12.0} - cpu: [x64] - os: [linux] - libc: [musl] - - '@rolldown/binding-linux-x64-musl@1.1.3': - resolution: {integrity: sha512-rSJcdjPxzA/by/6/rYs+v+bXU7UjvnbUWz8MJb6kh6+knqB1dCrtHg0uu7C/4haqJvqdkYHQ5IGn+tCH9GLW/g==} + '@rolldown/binding-linux-x64-musl@1.2.7': + resolution: {integrity: sha512-pAsE8iiDxUg1xBqdhrTfg45AVDVpirjz00sblEYClGNNcMnDb+e8beQgqIAw6LvauX/APvgxUnwrgun/YYGBhw==} engines: {node: ^20.19.0 || >=22.12.0} cpu: [x64] os: [linux] libc: [musl] - '@rolldown/binding-openharmony-arm64@1.0.0-rc.17': - resolution: {integrity: sha512-0ag/hEgXOwgw4t8QyQvUCxvEg+V0KBcA6YuOx9g0r02MprutRF5dyljgm3EmR02O292UX7UeS6HzWHAl6KgyhA==} + '@rolldown/binding-openharmony-arm64@1.2.7': + resolution: {integrity: sha512-lTcIYmmnQQA8Or/2DatS6oSqcdLHvendjS+zLu+FwgToynWMRSmQdpM65fTANJgIS4mjbMOo5KT2lnT9SAb96w==} engines: {node: ^20.19.0 || >=22.12.0} cpu: [arm64] os: [openharmony] - '@rolldown/binding-openharmony-arm64@1.1.3': - resolution: {integrity: sha512-hQ3/PYkDJICgevvyNcVrihVeqq7k1Pp3VZ9lY+dauAYUJKO+auqApvANhvR1An9BhmqYKvW2Mu1F9u4DXSMLxQ==} - engines: {node: ^20.19.0 || >=22.12.0} - cpu: [arm64] - os: [openharmony] - - '@rolldown/binding-wasm32-wasi@1.0.0-rc.17': - resolution: {integrity: sha512-LEXei6vo0E5wTGwpkJ4KoT3OZJRnglwldt5ziLzOlc6qqb55z4tWNq2A+PFqCJuvWWdP53CVhG1Z9NtToDPJrA==} - engines: {node: ^20.19.0 || >=22.12.0} - cpu: [wasm32] - - '@rolldown/binding-wasm32-wasi@1.1.3': - resolution: {integrity: sha512-Elcv/BtML9lXrV6JuKITc/grN2kYV9gjsQpW8Jfw4ioK0TOkjBjye0nnyqQNy9STNaI20lXNaQBRrD5gSgR0Yg==} - engines: {node: ^20.19.0 || >=22.12.0} - cpu: [wasm32] - - '@rolldown/binding-win32-arm64-msvc@1.0.0-rc.17': - resolution: {integrity: sha512-gUmyzBl3SPMa6hrqFUth9sVfcLBlYsbMzBx5PlexMroZStgzGqlZ26pYG89rBb45Mnia+oil6YAIFeEWGWhoZA==} - engines: {node: ^20.19.0 || >=22.12.0} - cpu: [arm64] - os: [win32] - - '@rolldown/binding-win32-arm64-msvc@1.1.3': - resolution: {integrity: sha512-2DrEfhluH9yhiaFApmsjsjwrSYbNcY1oFTzYSP1a535jDbV98zCFanA/96TBUd0iDFcxGmw9QRExwGCXz3U+/g==} + '@rolldown/binding-win32-arm64-msvc@1.2.7': + resolution: {integrity: sha512-e3Gu3WxbNk/UqQhxqU7YIYO+9ZBvWNz3U+h/qRFosscMFzdRPbXYSaSWgSnklv2fz1TgzBTcti2z35c/7irsHw==} engines: {node: ^20.19.0 || >=22.12.0} cpu: [arm64] os: [win32] - '@rolldown/binding-win32-x64-msvc@1.0.0-rc.17': - resolution: {integrity: sha512-3hkiolcUAvPB9FLb3UZdfjVVNWherN1f/skkGWJP/fgSQhYUZpSIRr0/I8ZK9TkF3F7kxvJAk0+IcKvPHk9qQg==} + '@rolldown/binding-win32-x64-msvc@1.2.7': + resolution: {integrity: sha512-W/jg5qoRSqjsEv0+dZi4e687mcHqmVuU0P4fK6qS/xjetW2Gmc1W8j//z5nAeNcC8Ttm0hV46IjcYeuVwYhuiw==} engines: {node: ^20.19.0 || >=22.12.0} cpu: [x64] os: [win32] - '@rolldown/binding-win32-x64-msvc@1.1.3': - resolution: {integrity: sha512-OL4OMk7UPXOeVGGd3qo5zJyPIljf4AFgk5QAkPPS+OoLuOOozhuaQGC18MxVTnw/06q93gShAJzlwnSCY9YtqA==} - engines: {node: ^20.19.0 || >=22.12.0} - cpu: [x64] - os: [win32] - - '@rolldown/pluginutils@1.0.0-rc.17': - resolution: {integrity: sha512-n8iosDOt6Ig1UhJ2AYqoIhHWh/isz0xpicHTzpKBeotdVsTEcxsSA/i3EVM7gQAj0rU27OLAxCjzlj15IWY7bg==} - '@rolldown/pluginutils@1.0.1': resolution: {integrity: sha512-2j9bGt5Jh8hj+vPtgzPtl72j0yRxHAyumoo6TNfAjsLB04UtpSvPbPcDcBMxz7n+9CYB0c1GxQFxYRg2jimqGw==} - '@rollup/rollup-android-arm-eabi@4.62.2': - resolution: {integrity: sha512-6o7ZLZK+BeenkZCFNDXqpbjw9bD6nuWonvS/lwQJp7NoVVxm6p3qE7qQ5jGuBjiFsgvqjD8mZAU5oWxTmbOeOg==} - cpu: [arm] - os: [android] - - '@rollup/rollup-android-arm64@4.62.2': - resolution: {integrity: sha512-BaH7BllCACHoH1LguOU56UItGfUWjujlO65kS9LAodViaN4bwIKd7oeW/ZHJ/4ljr/7MIiENnNy3HJ0zXv8Zkw==} - cpu: [arm64] - os: [android] - - '@rollup/rollup-darwin-arm64@4.62.2': - resolution: {integrity: sha512-v39RCCvj4He82I9sFmk+M1VZ0PLM9sfsLVikjfx2hYBNALhrrOR2D3JjQA6AhlaSOgcR+RzrKY7e1+bT6SUO/A==} - cpu: [arm64] - os: [darwin] - - '@rollup/rollup-darwin-x64@4.62.2': - resolution: {integrity: sha512-yl0y2vq3S3lHeuXhEdss6TWfKW8vkujImO12tn4ZkG/4oghr09LvdYm2RElVjokTQiUvDUGXLGsYeLqUMCKpGA==} - cpu: [x64] - os: [darwin] - - '@rollup/rollup-freebsd-arm64@4.62.2': - resolution: {integrity: sha512-tT4pvt4qXD+vEoezupCWi+a1F0vvDiksiHc+PxRlYTOH1I6/X4id9jPxTP+Fg+545euaFT1jJVs4CEdHZAU1vw==} - cpu: [arm64] - os: [freebsd] - - '@rollup/rollup-freebsd-x64@4.62.2': - resolution: {integrity: sha512-6nU5F2wCW+qvCBhTn1pdIU3bzsIoF7EUwsCDRxilWGprQR6yd508YnH9+OKFCwpfS8pjZqDUmnCAr7exax0XCg==} - cpu: [x64] - os: [freebsd] - - '@rollup/rollup-linux-arm-gnueabihf@4.62.2': - resolution: {integrity: sha512-n1GJHPOvpIfhi3TmrCeh6S6URt9BFCt0KQE3qvexyGCTAKpR4Lg+eWvNZEqu7epxwus/8ElT3hacYEucm49SZg==} - cpu: [arm] - os: [linux] - libc: [glibc] - - '@rollup/rollup-linux-arm-musleabihf@4.62.2': - resolution: {integrity: sha512-JqgflS8wEB+UXV/vS1RpRbifGBeN4D5lz8D8oOFbFZw4vedvdOgCFAjfBmIMdW3yL10XpQQ0Ambepw6MXrhOnA==} - cpu: [arm] - os: [linux] - libc: [musl] - - '@rollup/rollup-linux-arm64-gnu@4.62.2': - resolution: {integrity: sha512-wnFJkogWvN4jm/hQRF2UBaeUmk20j5+DmHvoyWii2b8HJDyvz1MF2OU/6ynXt2KR63rbZLWkFpoytpdc/yBuSA==} - cpu: [arm64] - os: [linux] - libc: [glibc] - - '@rollup/rollup-linux-arm64-musl@4.62.2': - resolution: {integrity: sha512-HVu2bp0zhvJ8xHEV9+UUs7S90VadmBSY3LcIMvozbPo4AuMGDWlz3ymHLHZPX4hR67TKTt8Qp5PJ5RBg/i+RMQ==} - cpu: [arm64] - os: [linux] - libc: [musl] - - '@rollup/rollup-linux-loong64-gnu@4.62.2': - resolution: {integrity: sha512-mQqqAV8QaoSgr9I2fKDLY2BAVvmKjWoGiu/cSYQonsLvtqwEn1E4QYfnCOcp5zoEqNhsDYin1s6jx/VJmrxlZg==} - cpu: [loong64] - os: [linux] - libc: [glibc] - - '@rollup/rollup-linux-loong64-musl@4.62.2': - resolution: {integrity: sha512-IxKLoxCQ2IWi6bT2akyDUBGsOImDKB+sPp4EsTmwFQ/fMwpCKm8uLSSgP/Kx/QYUgKis6SEZ5/Nlhup0DIA0PQ==} - cpu: [loong64] - os: [linux] - libc: [musl] - - '@rollup/rollup-linux-ppc64-gnu@4.62.2': - resolution: {integrity: sha512-Mk5ha2RQSgyFfmYYLkBpPnUk8D8FriBxesO1u9O75X0mHgXL1UQcH5Itl2lurWL2tj0RxV9b9tJgipac0hRY9A==} - cpu: [ppc64] - os: [linux] - libc: [glibc] - - '@rollup/rollup-linux-ppc64-musl@4.62.2': - resolution: {integrity: sha512-CjvEnqJL/0/TQ3TXX3OPIJ/kmBellrWd4heXUmHeJlTnmwjKpSJzoehLaL6Xk0ZnMHBu9dZuFADNOrtjF4v+2w==} - cpu: [ppc64] - os: [linux] - libc: [musl] - - '@rollup/rollup-linux-riscv64-gnu@4.62.2': - resolution: {integrity: sha512-1SiZbzwdkaDURsew/tSOrooKiYy7EQGT6m8ufavAi9NEyQb/6VuIxFXAL1fqa4iZe3g4NbNk4P7J32z2tw5Mgg==} - cpu: [riscv64] - os: [linux] - libc: [glibc] - - '@rollup/rollup-linux-riscv64-musl@4.62.2': - resolution: {integrity: sha512-nQts12zJ3NQRoE6uYljOH89v7szzLDvG2JD/vsX+vGXU8w/At1GowTZ5/7qeFQ8m7L55rpR8Okugnuo5bgjy2Q==} - cpu: [riscv64] - os: [linux] - libc: [musl] - - '@rollup/rollup-linux-s390x-gnu@4.62.2': - resolution: {integrity: sha512-E9/ll019jhPIJgpzfZoIkBGhcz+kKNgVWYRY0zr9srBdPPFVpvOKW8VaJKUbeK+eZXyQF9ltME+Kk6affeaPgg==} - cpu: [s390x] - os: [linux] - libc: [glibc] - - '@rollup/rollup-linux-x64-gnu@4.62.2': - resolution: {integrity: sha512-5BqxR/pshjey51iliyzTD5Xi3EN0aLmQ2lZ3lvefVV9c82BvrLo2/6OT55iifpWBufs6kdwWbuOKS841DrmK9A==} - cpu: [x64] - os: [linux] - libc: [glibc] - - '@rollup/rollup-linux-x64-musl@4.62.2': - resolution: {integrity: sha512-uNN83XxQrRAh/w0/pmAfibcwyb6YWt4gP+dpnQKPVJshAloQ785ii8CT8ZCIxkGg9opVsvAlGhFitSm6D1Jjpg==} - cpu: [x64] - os: [linux] - libc: [musl] - - '@rollup/rollup-openbsd-x64@4.62.2': - resolution: {integrity: sha512-srjEIxSH3LRnJN6THczDHWQplqEMFiAJrTab0msUryh9kwNpkICf3Ea6q6MN/2cZwRFUNx5w+h6Hpi4QuHS6Zg==} - cpu: [x64] - os: [openbsd] - - '@rollup/rollup-openharmony-arm64@4.62.2': - resolution: {integrity: sha512-8hOJnxgbyObnCm5AlRA3A931xX19xq80RjVTKgJOvEKWqJruP/Uf12IbAOaDjjEXYRewwHLfmF0YRIdK3OwKWA==} - cpu: [arm64] - os: [openharmony] - - '@rollup/rollup-win32-arm64-msvc@4.62.2': - resolution: {integrity: sha512-mmF4AY1i0hG/bLWUctUq59gtmgaSIRa3cu/A3JFRp/sCNEme2bgDEiDS22P9FbnJB8NJNF4jPJiSP5RHQpUTDg==} - cpu: [arm64] - os: [win32] - - '@rollup/rollup-win32-ia32-msvc@4.62.2': - resolution: {integrity: sha512-DZgkknc6jhHrk46V25vbAM0zZkyP0nSDkJB8/dRkLTxv470dOmWDqGoEJl/9A0dFfS7yE3REOwNDxpHwSLSt0Q==} - cpu: [ia32] - os: [win32] - - '@rollup/rollup-win32-x64-gnu@4.62.2': - resolution: {integrity: sha512-T6xr6ucWSFto+VGajA8YH26LdpHRuP4YLHEKAtCWvJDOlnmWcDZVCI2Jmjr+IFHDlt2zRaTAKE4tfjTaWLgJBg==} - cpu: [x64] - os: [win32] - - '@rollup/rollup-win32-x64-msvc@4.62.2': - resolution: {integrity: sha512-BfzEnDJOt9T8M989/lA37EcJgat01wLRnoi5dQf3QzOH7jzpqTAzdDbVfRljVr5r+jzKqpbHeyOfAaXxAd0PAA==} - cpu: [x64] - os: [win32] - '@rtsao/scc@1.1.0': resolution: {integrity: sha512-zt6OdqaDoOnJ1ZYsCYGt9YmWzDXl4vQdKTyJev62gFhRGKdx7mcT54V9KIjg+d2wi9EXsPvAPKe7i7WjfVWB8g==} '@sec-ant/readable-stream@0.4.1': resolution: {integrity: sha512-831qok9r2t8AlxLko40y2ebgSDhenenCatLVeW/uBtnHPyhHOvG0C7TvfgecV+wHzIm5KUICgzmVpWS+IMEAeg==} - '@semantic-release/changelog@6.0.3': - resolution: {integrity: sha512-dZuR5qByyfe3Y03TpmCvAxCyTnp7r5XwtHRf/8vD9EAn4ZWbavUX8adMtXYzE86EVh0gyLA7lm5yW4IV30XUag==} - engines: {node: '>=14.17'} + '@semantic-release/changelog@7.0.0': + resolution: {integrity: sha512-TNPyag5db24o7jWjre7UwKB4EcL8oJxbRhnDQ7hmZRAYqzreAc6PgdxQuU3pppp5xQinYtiumL0iG8SSKvnlzg==} + engines: {node: ^22.22.2 || >=24.15} peerDependencies: - semantic-release: '>=18.0.0' + semantic-release: '>=20.1.0' '@semantic-release/commit-analyzer@13.0.1': resolution: {integrity: sha512-wdnBPHKkr9HhNhXOhZD5a2LNl91+hs8CC2vsAVYxtZH3y0dV3wKn+uZSN61rdJQZ8EGxzWB3inWocBHV9+u/CQ==} @@ -1073,22 +639,18 @@ packages: peerDependencies: semantic-release: '>=20.1.0' - '@semantic-release/error@3.0.0': - resolution: {integrity: sha512-5hiM4Un+tpl4cKw3lV4UgzJj+SmfNIDCLLw0TepzQxz9ZGV5ixnqkzIVF+3tp0ZHgcMKE+VNGHJjEeyFG2dcSw==} - engines: {node: '>=14.17'} - '@semantic-release/error@4.0.0': resolution: {integrity: sha512-mgdxrHTLOjOddRVYIYDo0fR3/v61GNN1YGkfbrjuIKg/uMgCd+Qzo3UAXJ+woLQQpos4pl5Esuw5A7AoNlzjUQ==} engines: {node: '>=18'} - '@semantic-release/git@10.0.1': - resolution: {integrity: sha512-eWrx5KguUcU2wUPaO6sfvZI0wPafUKAMNC18aXY4EnNcrZL86dEmpNVnC9uMpGZkmZJ9EfCVJBQx4pV4EMGT1w==} - engines: {node: '>=14.17'} + '@semantic-release/git@11.0.1': + resolution: {integrity: sha512-Zr8BUYCTZMc8V6wDKN2dpR7nJgewd9I6THL3ydLTnp3OEdTo1/4RBLNYaeRucYMsjMv+BXoCNfXA0NADj1kwhw==} + engines: {node: ^22.22.2 || >=24.15} peerDependencies: - semantic-release: '>=18.0.0' + semantic-release: '>=20.1.0' - '@semantic-release/github@12.0.8': - resolution: {integrity: sha512-tej5AAgK5X9wHRoDmYhecMXEHEkFeGOY1XsEblKxu8pIQwahzf1STYyr7iPU6Lpbg6C5I3N2w/ocXrBo+L7jhw==} + '@semantic-release/github@12.0.9': + resolution: {integrity: sha512-ODIqb0V3QqndipryEEiaBxUQCFjvv7Oese5Dt4omMGa60YRNEW0Sx3K+zri0uac2Y6S9nOlMehciWIzvvRCTGQ==} engines: {node: ^22.14.0 || >= 24.10.0} peerDependencies: semantic-release: '>=24.1.0' @@ -1117,12 +679,15 @@ packages: resolution: {integrity: sha512-tlqY9xq5ukxTUZBmoOp+m61cqwQD5pHJtFY3Mn8CA8ps6yghLH/Hw8UPdqg4OLmFW3IFlcXnQNmo/dh8HzXYIQ==} engines: {node: '>=18'} + '@standard-schema/spec@1.1.0': + resolution: {integrity: sha512-l2aFy5jALhniG5HgqrD6jXLi/rUWrKvqN/qJx6yoJsgKhblVd+iqqU4RCXavm/jPityDo5TCvKMnpjKnOriy0w==} + '@testing-library/dom@10.4.1': resolution: {integrity: sha512-o4PXJQidqJl82ckFaXUeoAW+XysPLauYI43Abki5hABd853iMhitooc6znOnczgbTYmEP6U6/y1ZyKAIsvMKGg==} engines: {node: '>=18'} - '@testing-library/react@16.3.2': - resolution: {integrity: sha512-XU5/SytQM+ykqMnAnvB2umaJNIOsLF3PVv//1Ew4CTcpz0/BRyy/af40qqrt7SjKpDdT1saBMc42CUok5gaw+g==} + '@testing-library/react@16.3.3': + resolution: {integrity: sha512-Uo193NgQbPMz6lrrhtRQQFcMC6Re/ELLFbbuVL30WDlZxlpZf9/lMHTAVxPRLw1q1iu9OJmR1c2BLiENRstdBg==} engines: {node: '>=18'} peerDependencies: '@testing-library/dom': ^10.0.0 @@ -1136,8 +701,8 @@ packages: '@types/react-dom': optional: true - '@testing-library/user-event@14.6.1': - resolution: {integrity: sha512-vq7fv0rnt+QTXgPxr5Hjc210p6YKq2kmdziLgnsZGgLJ9e6VAShx1pACLuRjd/AS/sr7phAR58OIIpf0LlmQNw==} + '@testing-library/user-event@14.6.7': + resolution: {integrity: sha512-MPCpX8bxe8zS+JmmTwLp8jd0dy1rAm60Te/SL8JrQM3qvQJcBOs1d7IefJMyZzqM3EWBrDn/LWDt1BCGu4ASfg==} engines: {node: '>=12', npm: '>=6'} peerDependencies: '@testing-library/dom': '>=7.21.4' @@ -1157,17 +722,14 @@ packages: '@types/estree@1.0.9': resolution: {integrity: sha512-GhdPgy1el4/ImP05X05Uw4cw2/M93BCUmnEvWZNStlCzEKME4Fkk+YpoA5OiHNQmoS7Cafb8Xa3Pya8m1Qrzeg==} - '@types/jsesc@2.5.1': - resolution: {integrity: sha512-9VN+6yxLOPLOav+7PwjZbxiID2bVaeq0ED4qSQmdQTdjnXJSaCVKTR58t15oqH1H5t8Ng2ZX1SabJVoN9Q34bw==} - '@types/json-schema@7.0.15': resolution: {integrity: sha512-5+fP8P8MFNC+AyZCDxrB2pkZFPGzqQWUzpSeuuVLvm8VMcorNYavBqoFcxK8bQz4Qsbn4oUEEem4wDLfcysGHA==} '@types/json5@0.0.29': resolution: {integrity: sha512-dRLjCWHYg4oaA77cxO64oO+7JwCwnIzkZPdrrC71jQmQtlhM556pwKo5bUzqvZndkVbeFLIIi+9TC40JNF5hNQ==} - '@types/node@24.0.0': - resolution: {integrity: sha512-yZQa2zm87aRVcqDyH5+4Hv9KYgSdgwX1rFnGvpbzMaC7YAljmhBET93TPiTd3ObwTL+gSpIzPKg5BqVxdCvxKg==} + '@types/node@26.4.1': + resolution: {integrity: sha512-k97ENvZWtvA6yqz5/FS6a7duDgOPEeOQOc2iKS/nY6mX6qJUKtLnWzQS+Xj6tXweyj6ZcTAK2Qecetnvi9nCLA==} '@types/normalize-package-data@2.4.4': resolution: {integrity: sha512-37i+OaWTh9qeK4LSHPsyRC7NahnGotNuZvjLSgcPzblpHB3rrCJxAOgI5gCdKm7coonsaX1Of0ILiTcnZjbfxA==} @@ -1183,63 +745,63 @@ packages: '@types/react@18.3.31': resolution: {integrity: sha512-vfEqpXTvwT91yhmwdfouStN2hSKwTvyRs8qpLfADyrq/kxDw0hZM7Wk9Ug1FELj8hIby+S/+kQCSRFF32nv2Qw==} - '@typescript-eslint/eslint-plugin@8.62.0': - resolution: {integrity: sha512-o+mpz7EYiMzXoySXiKmzlabIvTVqUuK5yLrAedRPRDA0IpPFMUV1IXt6OqljIxX/kumN6EjUYp41Hqelh6p/Dw==} + '@typescript-eslint/eslint-plugin@8.69.0': + resolution: {integrity: sha512-t5jQTKPIgVW1PE6dR6H6Qz5gm8zjMlX5/2gRaOGd9eO6V7J+tQc6iWKukEe7dY8u9HyYasQ0yfF0/FSSTEO2gA==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: - '@typescript-eslint/parser': ^8.62.0 + '@typescript-eslint/parser': ^8.69.0 eslint: ^8.57.0 || ^9.0.0 || ^10.0.0 typescript: '>=4.8.4 <6.1.0' - '@typescript-eslint/parser@8.62.0': - resolution: {integrity: sha512-dzHeT2gySzZtLDsuqxU9AkYgIsQoHAHtRBpOqM+Ofzx1Bwrd2RcCjQJ+6iQbsHOIR6NS33bF2W1k3blN1zLDrA==} + '@typescript-eslint/parser@8.69.0': + resolution: {integrity: sha512-l4b0DhWioGg6Gt2ebGlvfkFMOjRsauxtsnDRwUSRX1qHq3HdTfQHV8wW9zEXeciai6HfeaKOedQn2Zoofx3WBw==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: eslint: ^8.57.0 || ^9.0.0 || ^10.0.0 typescript: '>=4.8.4 <6.1.0' - '@typescript-eslint/project-service@8.62.0': - resolution: {integrity: sha512-wexnCqiTg7BOGtbLDftYpRWlmLq4xfoMd7BKFR6Y75sZS3QmRKLdN3yWLhmIYgqMmP/OXWpj3H8odkb5nGURCQ==} + '@typescript-eslint/project-service@8.69.0': + resolution: {integrity: sha512-yi4obFrHMmnsesWehHbkg9zMA7Jt8cXT+mKM08G999pH1yT6nqgsHx7MYm0uY1wAj8CqiBXYRJ7WAT0QdQHQXg==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: typescript: '>=4.8.4 <6.1.0' - '@typescript-eslint/scope-manager@8.62.0': - resolution: {integrity: sha512-1lX38kNxXIRb8mEc3lbq5mdHq1Pf2+U0nFU65KfT18mtPxxl0fvjuEE92mHuXPuCtElJhOrddOpyMlM3Z0umEA==} + '@typescript-eslint/scope-manager@8.69.0': + resolution: {integrity: sha512-ewfspqWvSxKSOaplqAUNbaSFO0eB6w1EtQ+esfYFRm3614Ty4uNtExkcbgd6nWsXphbqKyf9ZYdbZdv2xEoWEQ==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} - '@typescript-eslint/tsconfig-utils@8.62.0': - resolution: {integrity: sha512-y2GAdB6ykaXUvuspbYnizQc4oDDz0Tz/Yc7iWrXf9mx8vm/L/0vLHCe0tS2boG96Zy+DivnVDQ9ZUEWoHqqx1g==} + '@typescript-eslint/tsconfig-utils@8.69.0': + resolution: {integrity: sha512-xNqK7YTDZsLniQMV/4rpFR8Z5JlqeRvVjuG1YgF/mdPVH84HSD19L8CczMA0qg2RfwEV231GHH3VnToJDo4MfQ==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: typescript: '>=4.8.4 <6.1.0' - '@typescript-eslint/type-utils@8.62.0': - resolution: {integrity: sha512-+g5O3j0w2ldzC86Pv6fvbO/xhAonbJFIdf/MKQ1d30gndlsVzUOE83ldfSE15Qrl9fhFjK6AovHs5Wpp6vx86w==} + '@typescript-eslint/type-utils@8.69.0': + resolution: {integrity: sha512-ZfoJAVg3JZndQEpEl9petVlxau3lRuElc4HRMuAlLCf8to04/iHz692RUSNmXKDjEuJmIL+KZ2/BsOcBc16dsA==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: eslint: ^8.57.0 || ^9.0.0 || ^10.0.0 typescript: '>=4.8.4 <6.1.0' - '@typescript-eslint/types@8.62.0': - resolution: {integrity: sha512-KvAclkktORPvM54TgLgA4z9HIV1M8zOgw9ZVNXl9f/8dLYfXYX1wkMXP7qmabpijQRV5bHJLOmoyGQbLMaUYeg==} + '@typescript-eslint/types@8.69.0': + resolution: {integrity: sha512-K3VrubUPhlo9VDBS6QdI8YB5j7ClpqLRdefcz6PFrhnwicehBweqQ9Evhl4l+FYz0HdDmMqIiSX0aldGRYtDCA==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} - '@typescript-eslint/typescript-estree@8.62.0': - resolution: {integrity: sha512-+hVbNxtW64pIcZWDPGbyaKF7vp2IBTVY5ma1blwwksrjdsbdqqEKvJWMGbBofei4F6Dovx1M0RJgoFeNu2279A==} + '@typescript-eslint/typescript-estree@8.69.0': + resolution: {integrity: sha512-AdFkgqck3Vudb/kWnxlyafU/4aBhHrbQ9locP2N4psXTy5mOBg0SHJumnLvx7r6g1gV4DKvUFwV2nJZBoqOD8w==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: typescript: '>=4.8.4 <6.1.0' - '@typescript-eslint/utils@8.62.0': - resolution: {integrity: sha512-82r66fi9zYwZ+mTq3vKgwjbZ1PVk/DJzrXFLpG6RnBbdvH8TEGVHIs9H4d2drhkOzf0syZuD/OZvvlu6GDbP4g==} + '@typescript-eslint/utils@8.69.0': + resolution: {integrity: sha512-tUbx60BBqQa31kXF5MCsOOLL5E/WzUuxIn7YpAvq+eaUlqvk8/NXnXMBNAdLCr0icjkzem7iUA5QqWHe/hJ1aw==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: eslint: ^8.57.0 || ^9.0.0 || ^10.0.0 typescript: '>=4.8.4 <6.1.0' - '@typescript-eslint/visitor-keys@8.62.0': - resolution: {integrity: sha512-CY3uyFSRbcQv3nnSv8S0+lDftMVz6P963PoRlxrV7ew/Md564g9ut60PYzdLM5qW4jFn93GBF+Soi90ISAN+GQ==} + '@typescript-eslint/visitor-keys@8.69.0': + resolution: {integrity: sha512-+rmdgPA+EXkNgKYvHvFfhrs35utXbwaC5PGpDquSXcoXQDKUA5UjV0LmTucG/4JXkM31BTu4TilHtrN8IVBe8w==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} '@unrs/resolver-binding-android-arm-eabi@1.12.2': @@ -1362,51 +924,186 @@ packages: cpu: [x64] os: [win32] - '@vitest/coverage-v8@3.2.6': - resolution: {integrity: sha512-LsAdmUapA0qSN306d8+zOyawM0hFm2m2Hg9IwVNIKBm+qJV8cijiq2c+gxKZcB1HCfIWAy+0qEZDCUQA58A1cw==} + '@vitest/coverage-v8@4.1.11': + resolution: {integrity: sha512-8MVGEFnJIcdGjcbfKmeq8z0pZHH0JlVtoVZH9Q/qwUp6wyFnEJUBMrw9DCaj+ra3vShGmhavjalMIhPNxZAUcw==} peerDependencies: - '@vitest/browser': 3.2.6 - vitest: 3.2.6 + '@vitest/browser': 4.1.11 + vitest: 4.1.11 peerDependenciesMeta: '@vitest/browser': optional: true - '@vitest/expect@3.2.6': - resolution: {integrity: sha512-1+7q9BtaKzEmO+fmNT3kYvoNn5Y71XWAx2Q5HRim4tTVRQVRv4uJFAQ5FbK0OPUeNP/WmVCpxYxoJdvuHVjzBQ==} + '@vitest/expect@4.1.11': + resolution: {integrity: sha512-VX2x5vNJXET47KAFzwERI+KRMtTTCSWTfSMKsW7JsUsXV4psq++e3DvZpuTDOpHcxytiDs6p2nhVb2tVDiiUYw==} - '@vitest/mocker@3.2.6': - resolution: {integrity: sha512-EZOrpDbkKotFAP7wPAQV1UIyoGOk4oX7ynWhBhLB7v+meMHbQhU16oPpIYGTTe4oFlhpryGpgpcZP/sin3hYuw==} + '@vitest/mocker@4.1.11': + resolution: {integrity: sha512-2XJVD55d1o5AZous5CCGKS74g/riOj9odEt2bQpCVZeblHyHdnMeFl4jl0XjU21stf4mbjUkew2eXQZt65g5CQ==} peerDependencies: msw: ^2.4.9 - vite: ^5.0.0 || ^6.0.0 || ^7.0.0-0 + vite: ^6.0.0 || ^7.0.0 || ^8.0.0 peerDependenciesMeta: msw: optional: true vite: optional: true - '@vitest/pretty-format@3.2.6': - resolution: {integrity: sha512-lb7XXXzmm2h2ASzFnRvQpDo6onT1NmMJA3tkGTWiBFtRJ9lxGY3d3mm/Apt36gej2bkkOVLL/yTOtufDaFa/jA==} + '@vitest/pretty-format@4.1.11': + resolution: {integrity: sha512-yiZzPbGTS9Sr/JpFl8zHrcIkAofNbFV6k21vIgQN/cY/oxZeXhJv5sc/MBJ5jFKWmWs+oJHw0UXLZjmf931+Vw==} + + '@vitest/runner@4.1.11': + resolution: {integrity: sha512-LztvUgdwMNJMIkj3hQnnxiC2Xy1zNxq928W/xhjCLaNCzqTZOudjwbQf6v9IntZGPw132i2Lq2rgTRZHD3JHNw==} + + '@vitest/snapshot@4.1.11': + resolution: {integrity: sha512-pN7ikn1ON7h8ee4gIAp4AzyK+zBtJPzVbqOgu5LCEh4VaJVbPQcgYQYJIMGQPXVeJJq1fnfazis7a5pFNPahog==} + + '@vitest/spy@4.1.11': + resolution: {integrity: sha512-apNa/prQy2qCeywhnixOHPRCgGNhvg7T4Dapfl1GahLp/R+uhBm5cPyFoNVyqsNd2h1nJxL6BqqdIjiABL60YA==} - '@vitest/runner@3.2.6': - resolution: {integrity: sha512-HYcoSj1w5tcgUnzoF0HcyaAQjpA1gj9ftUJ7iSJSuipc02jW9gKkigwZbjFldAfYHA1fa8UZVRftdMY5msWM9Q==} + '@vitest/utils@4.1.11': + resolution: {integrity: sha512-zTCVGpyFsGWBhllOyKlTw/vnr6D9qxsfSDyfbyZmTyjHw5N/VuvzHpHoQjm2ZJzn4RJgx5w4r7V0er69CmLgPQ==} - '@vitest/snapshot@3.2.6': - resolution: {integrity: sha512-H+ZjNTWGpObenh0YnlBctAPnJSI20P81PL8BPzWpx54YXLLTm8hEsWawtcYLMrwvpK48hGxLLbCS+1KRXhsKhw==} + '@yuku-codegen/binding-android-arm64@0.8.7': + resolution: {integrity: sha512-C/0zV5IhgVdYhGJTwrY0v8dknxlhiKwtVJkMUaexu9/QvRmzlV4vfU3hZlUSgqc2BxQHntL1mCVbDq8j0FRFDw==} + cpu: [arm64] + os: [android] + + '@yuku-codegen/binding-darwin-arm64@0.8.7': + resolution: {integrity: sha512-/u+REDMI4a0/lsJXTM4c53/w31OGZLOReZIyg62uhgLs0kc8NHsj/nOcxTdlQjq5gi0zhdkccD9LaLTXcdzPvw==} + cpu: [arm64] + os: [darwin] + + '@yuku-codegen/binding-darwin-x64@0.8.7': + resolution: {integrity: sha512-sMMzFOwCo4WXR+/6zIBThOocSC50iIIZZdfiIDbaLvj0Ax/rWt/iavyfEAqajyvzydLyCqR/ZItdLWSRlu1umw==} + cpu: [x64] + os: [darwin] - '@vitest/spy@3.2.6': - resolution: {integrity: sha512-oq6BbH68WzcWmwtBrU9nqLeaXTR4XwJF7FSLkKEZo4i6eoXcrxjcwSuTvWBIRUTC6VC72nXYunzqgZA+IKdtxg==} + '@yuku-codegen/binding-freebsd-x64@0.8.7': + resolution: {integrity: sha512-MpdpKXix9P+Y1rKgjvcNeNtGjXeL1CmttNhYINrWls8kRpm4xM/oBGTmn6w7to8lAlwj5jm8q03dQPl5mRv4Qw==} + cpu: [x64] + os: [freebsd] - '@vitest/utils@3.2.6': - resolution: {integrity: sha512-lI23nIs4bnT3T8NIoh+vFaz5s2/DdP0Jgt2jxwgWljvwn82cLJtyi/If+fjFyoLMGIOz0U/fKvWE0d4jsNQEfg==} + '@yuku-codegen/binding-linux-arm-gnu@0.8.7': + resolution: {integrity: sha512-rr1srFLlPAmC1vtxfc9C1YLDe3iH09YjfSeeIidBqKhzx1MATjOAq4mjlRUOnhr/L27MotWIYOFKwVsd5JZFOg==} + cpu: [arm] + os: [linux] + libc: [glibc] + + '@yuku-codegen/binding-linux-arm-musl@0.8.7': + resolution: {integrity: sha512-eAufXh8qBRpiSO6ueaMDL+yyoXIGLhpUce72YbcACtZU2qhExwBIJyEtQf5kH2Ki0X2aqkSjSfog4OPtKXan3Q==} + cpu: [arm] + os: [linux] + libc: [musl] + + '@yuku-codegen/binding-linux-arm64-gnu@0.8.7': + resolution: {integrity: sha512-gw4w6wPoHObBrdIC4duVWLmJOvpdE25j5D7yrM5mACNlK4klRz/lv8hK+ssQk9EJHBgZjSaqZIJVFgqNYbfv7A==} + cpu: [arm64] + os: [linux] + libc: [glibc] + + '@yuku-codegen/binding-linux-arm64-musl@0.8.7': + resolution: {integrity: sha512-L68N6Y4XkqcIaKo3Ra88JEvBEH4AHff44A4INcrxeVWZ8CZtu2tCpfVxe3hR8qQQMcvBSQlDn24KpkCKEhVvfA==} + cpu: [arm64] + os: [linux] + libc: [musl] + + '@yuku-codegen/binding-linux-x64-gnu@0.8.7': + resolution: {integrity: sha512-dzyAbltJmf3Cqlb8HcFuYIf5Yn0fl1vTr3XJ9HiVNNvOlhqPSArOqtw9vI1p6/VTXTjrMLXlU+s+/kNHiIy/Cw==} + cpu: [x64] + os: [linux] + libc: [glibc] + + '@yuku-codegen/binding-linux-x64-musl@0.8.7': + resolution: {integrity: sha512-Otw4MH3404q0Bbvl+YTdW9aoUV5vXmUw8260bWvt1XlaoIX/ceSgI4ygheRDMfBPoHt6FDayQaO9OLVUZAgkFA==} + cpu: [x64] + os: [linux] + libc: [musl] + + '@yuku-codegen/binding-win32-arm64@0.8.7': + resolution: {integrity: sha512-qo/jyrzryiBuKEsFiuWaBCBe3tRMynQ0qFWFgOEjcCMQeZfBm+wKiVEUEFXXLc7bh8YezguAWp0Mtnhq4ARNyA==} + cpu: [arm64] + os: [win32] + + '@yuku-codegen/binding-win32-x64@0.8.7': + resolution: {integrity: sha512-D5lDsVDx6m00E6bWySlWdH72Ca4TPSaphDqB6QjU6MpuNLIJqoGoatYyq2rOmBE8Zv/kunot/o58KGL03P3eiA==} + cpu: [x64] + os: [win32] + + '@yuku-parser/binding-android-arm64@0.8.7': + resolution: {integrity: sha512-eGKYiUDX7Y0V7tDTmg+JTVnXnjMqfXXsorZ+EDf5kxwchQ3Or1HS14MzI2fw+jFhHR85fCWt+mtX33Yao73hIQ==} + cpu: [arm64] + os: [android] + + '@yuku-parser/binding-darwin-arm64@0.8.7': + resolution: {integrity: sha512-Re0RHelKLnjEURulY2/KxW+Ngb8zuNA4BRZuMwgGQNzVumT6u4U2N2hc01oeYVNVof0i7GrXE4UCNBgbpRRnjQ==} + cpu: [arm64] + os: [darwin] + + '@yuku-parser/binding-darwin-x64@0.8.7': + resolution: {integrity: sha512-Hn8DROtQkjlA1ACbPgj4a7eP9IuVOI504oiTwpkWPbpaDWD9KdmnVYCqW+1LfenNK/g7O9NhWGpXEdaCNX7lIA==} + cpu: [x64] + os: [darwin] + + '@yuku-parser/binding-freebsd-x64@0.8.7': + resolution: {integrity: sha512-bAP2OV8wRuzplX/jYxv9+vvqQT8JxyNphI8fLfXGL054Xs+4/J5u33cIm3y4rxY8rdoLmmdiJs2Tq7r7lrDRfA==} + cpu: [x64] + os: [freebsd] + + '@yuku-parser/binding-linux-arm-gnu@0.8.7': + resolution: {integrity: sha512-kTYwJQQgmZeAWdDIWabiReIZMpmfLueIj1tCmjStUtFGhR1Z0qwxonKVfUC4N7h/VhGGzLZ//7O1kgt1QKqgCg==} + cpu: [arm] + os: [linux] + libc: [glibc] + + '@yuku-parser/binding-linux-arm-musl@0.8.7': + resolution: {integrity: sha512-uL4jE8HPT2BLlxAXyD10LqgPuXa9eDa0BKpCdSANmzIJghq/2eZo3/gQNtaxPZMupWoxjYzSad9IXrwu7aYPXQ==} + cpu: [arm] + os: [linux] + libc: [musl] + + '@yuku-parser/binding-linux-arm64-gnu@0.8.7': + resolution: {integrity: sha512-3gVN4pWSKZmXiNX7cU164dR9MPvesCHnlH6nPfpK+yQsCuYphjKKplcb4SnZBrhiqmXbgb2HR0c2TS0IZUPhgA==} + cpu: [arm64] + os: [linux] + libc: [glibc] + + '@yuku-parser/binding-linux-arm64-musl@0.8.7': + resolution: {integrity: sha512-S0mwfEjoLpxzXeZw802Wa4RaELsQiPtWqG6INcy8j4GtvNFtl4LCX3eGO1XLn9pyLAISLzTRyU3zUCBUPin8lg==} + cpu: [arm64] + os: [linux] + libc: [musl] + + '@yuku-parser/binding-linux-x64-gnu@0.8.7': + resolution: {integrity: sha512-lnbWdPmerE5D1uH1G4IEZKnPzCrWCStRGrtgpSIe1RibAo5bZIjDbbbPYXmMHCEh4F+x/JaJpElh26a3r+BPbg==} + cpu: [x64] + os: [linux] + libc: [glibc] + + '@yuku-parser/binding-linux-x64-musl@0.8.7': + resolution: {integrity: sha512-769uwndMvMzUvATWbAcEvyLHKA+DzhHSCl/obBUrRdYfRo26yxui6S8y3z7uJ+Naup7UKrDxrpK7OnQkxkl9KQ==} + cpu: [x64] + os: [linux] + libc: [musl] + + '@yuku-parser/binding-win32-arm64@0.8.7': + resolution: {integrity: sha512-mEB/9PlaAkisJ6KWGz0zvywXoU6+80dTlR2LwS7s/jcXXoU6fm2+sitBZXtqu3+Q4DcDgPxM45uWMCzPs0TSRw==} + cpu: [arm64] + os: [win32] + + '@yuku-parser/binding-win32-x64@0.8.7': + resolution: {integrity: sha512-8vNB2DP0ou61nGb8tc/qfi41gfyDXz1MHr2zqL3nR+cJ6CEbiuWV/l/a/vv151gCgiZLLAyGkQGENpozdg716w==} + cpu: [x64] + os: [win32] + + '@yuku-toolchain/types@0.8.7': + resolution: {integrity: sha512-2Z53dNxAJL6UvFoIrDZvYf3zlO8s4VJK4O2hhaB4mXVwwpX/7ajtss3cmfqKvamlNLWyt9FSWs4eoYdlbxpnHA==} acorn-jsx@5.3.2: resolution: {integrity: sha512-rq9s+JNhf0IChjtDXxllJ7g41oZk5SlXtp0LHwyA5cejwn7vKmKp4pPri6YEePv2PU65sAsegbXtIinmDFDXgQ==} peerDependencies: acorn: ^6.0.0 || ^7.0.0 || ^8.0.0 - acorn@8.17.0: - resolution: {integrity: sha512-xRQbDb9BnwDafYNn6Vwl839DYVjqXYb1XVGtWAZ1kcDc6iwAL4hg3B1dZlRiuENFeO2H53gFG3in621AdERVAg==} + acorn@8.18.0: + resolution: {integrity: sha512-lGq+9yr1/GuAWaVYIHRjvvySG5/4VfKIvC8EWxStPdcDh/Ka7FG3twP6v4d5BkravUilhIAsG4Qj83t02LWUPQ==} engines: {node: '>=0.4.0'} hasBin: true @@ -1414,10 +1111,6 @@ packages: resolution: {integrity: sha512-TQf59BsZnytt8GdJKLPfUZ54g/iaUL2OWDSFCCvMOhsHduDQxO8xC4PNeyIkVcA5KwL2phPSv0douC0fgWzmnA==} engines: {node: '>= 20'} - aggregate-error@3.1.0: - resolution: {integrity: sha512-4I7Td01quW/RpocfNayFdFVk1qSuoh0E7JrbRJ16nH01HhKFQ88INq9Sd+nd72zqRySlr9BmDA8xlEJ6vJMrYA==} - engines: {node: '>=8'} - aggregate-error@5.0.0: resolution: {integrity: sha512-gOsf2YwSlleG6IjRYG2A7k0HmBMEo6qVNk9Bp/EaLgAJT5ngH6PXbqa4ItvnEwCm/velL5jAnQgsHsWnjhGmvw==} engines: {node: '>=18'} @@ -1433,8 +1126,8 @@ packages: resolution: {integrity: sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ==} engines: {node: '>=8'} - ansi-regex@6.2.2: - resolution: {integrity: sha512-Bq3SmSpyFHaWjPk8If9yc6svM8c56dB5BAtW4Qbw5jHTwwXXcTLoRMkpDJp6VL0XzlWaCHTXrkFURMYmD0sLqg==} + ansi-regex@6.3.0: + resolution: {integrity: sha512-WpDfL7NO6j7tH88IDBNVdUJxDh9nmCteAVW9dsep846XdwF4naCBK+/tGLX3KJgcpgMRXCFlTM2hKGoK9FsdrQ==} engines: {node: '>=12'} ansi-styles@3.2.1: @@ -1512,15 +1205,11 @@ packages: resolution: {integrity: sha512-Izi8RQcffqCeNVgFigKli1ssklIbpHnCYc6AknXGYoB6grJqyeby7jv12JUQgmTAnIDnbck1uxksT4dzN3PWBA==} engines: {node: '>=12'} - ast-kit@3.0.0: - resolution: {integrity: sha512-8OG92q3R35qjC/4i6BLBMg8IB+fClWu/1PEwg2Z9Rn+BuNaiEgJzpzn+pxWOdHJWDCAwu2JP0wCDTozAM4QirQ==} - engines: {node: ^22.18.0 || >=24.11.0} - ast-types-flow@0.0.8: resolution: {integrity: sha512-OH/2E5Fg20h2aPrbe+QL8JZQFko0YZaF+j4mnQ7BGhfavO7OpSLa8a0y9sBwomHdSbkhTS8TQNayBfnW5DwbvQ==} - ast-v8-to-istanbul@0.3.12: - resolution: {integrity: sha512-BRRC8VRZY2R4Z4lFIL35MwNXmwVqBityvOIwETtsCSwvjl0IdgFsy9NhdaA6j74nUdtJJlIypeRhpDam19Wq3g==} + ast-v8-to-istanbul@1.0.5: + resolution: {integrity: sha512-UPAgKJFSEGMWSDr3LX4tqnAb4f7KGT8O40Tyx8wbYmmZ/yn58lNCm8h3svs3eXgiGd5AXxz8NDOvXWvicq+rJA==} async-function@1.0.0: resolution: {integrity: sha512-hsU18Ae8CDTR6Kgu9DYf0EbCr/a5iGL0rytQDobUcdpYOKokk8LEjVphnXkDkgpi0wYVsqrXuP0bZxJaTqdgoA==} @@ -1530,8 +1219,8 @@ packages: resolution: {integrity: sha512-wvUjBtSGN7+7SjNpq/9M2Tg350UZD3q62IFZLbRAR1bSMlCo1ZaeW+BJ+D090e4hIIZLBcTDWe4Mh4jvUDajzQ==} engines: {node: '>= 0.4'} - axe-core@4.12.1: - resolution: {integrity: sha512-s7iGf5GaVMxEG0ENN9x+xTr7GFZCb1ZP/1uATUpCEK2X78nDB3RwbtFCo9pGAf9ru+VwoQ464DkaLEeRM08wJA==} + axe-core@4.13.0: + resolution: {integrity: sha512-UzGt8zg7Ny8djbYMhxl2zuEevVa7r2gJjYY5Lwr1xM7+XU2nd6CkIWFTVcCIbAP63vSz71NaVyyuSk9lHKcy0A==} engines: {node: '>=4'} axobject-query@4.1.0: @@ -1556,9 +1245,6 @@ packages: bidi-js@1.0.3: resolution: {integrity: sha512-RKshQI1R3YQ+n9YJz2QQ147P66ELpa1FQEg20Dk8oW9t2KgLbpDLLp9aGZ7y8WHSshDknG0bknqGw5/tyCs5tw==} - birpc@4.0.0: - resolution: {integrity: sha512-LShSxJP0KTmd101b6DRyGBj57LZxSDYWKitQNW/mi8GRMvZb078Uf9+pveax1DrVL89vm7mWe+TovdI/UDOuPw==} - bottleneck@2.19.5: resolution: {integrity: sha512-VHiNCbI1lKdl44tGrhNfU3lup0Tj/ZBMJB5/2ZbNXRCPuRCO7ed2mgcK4r17y+KB2EfuYuRaVlwNbAeaWGSpbw==} @@ -1581,10 +1267,6 @@ packages: engines: {node: ^6 || ^7 || ^8 || ^9 || ^10 || ^11 || ^12 || >=13.7} hasBin: true - cac@6.7.14: - resolution: {integrity: sha512-b6Ilus+c3RrdDk+JhLKUAQfzzgLEPy6wcXqS7f/xe1EETvsDP6GORG7SFuOs6cID5YkqchW/LXZbX5bc8j7ZcQ==} - engines: {node: '>=8'} - cac@7.0.0: resolution: {integrity: sha512-tixWYgm5ZoOD+3g6UTea91eow5z6AAHaho3g0V9CNSNb45gM8SmflpAc+GRd1InC4AqN/07Unrgp56Y94N9hJQ==} engines: {node: '>=20.19.0'} @@ -1608,8 +1290,8 @@ packages: caniuse-lite@1.0.30001810: resolution: {integrity: sha512-TITQPUkaz+aVk5GL6NhOdwk1aEaNTSDPsGFWrTuhKGtjTF70jL/Oht2W4c6rXUe5fu7Ie19VIahAXHIIiWWNeg==} - chai@5.3.3: - resolution: {integrity: sha512-4zNhdJD/iOjSH0A05ea+Ke6MU5mmpQcbQsSOkgdaUMJ9zTlDTD/GYlwohmIE2u0gaxHYiVHEn1Fw9mZ/ktJWgw==} + chai@6.2.2: + resolution: {integrity: sha512-NUPRluOfOiTKBKvWPtSD4PhFvWCqOi0BGStNWs57X9js7XGTprSmFoz5F0tWhR4WPjNeR9jXqdC7/UpSJTnlRg==} engines: {node: '>=18'} chalk@2.4.2: @@ -1628,14 +1310,6 @@ packages: resolution: {integrity: sha512-kWWXztvZ5SBQV+eRgKFeh8q5sLuZY2+8WUIzlxWVTg+oGwY14qylx1KbKzHd8P6ZYkAg0xyIDU9JMHhyJMZ1jw==} engines: {node: '>=10'} - check-error@2.1.3: - resolution: {integrity: sha512-PAJdDJusoxnwm1VwW07VWwUN1sl7smmC3OKggvndJFadxxDRyFJBX/ggnu/KE4kQAB7a3Dp8f/YXC1FlUprWmA==} - engines: {node: '>= 16'} - - clean-stack@2.2.0: - resolution: {integrity: sha512-4diC9HaTE+KRAMWhDhrGOECgWZxoevMc5TlkObMqNSsVU62PYzXZ/SMTjzyGAFF1YusgxGcSWTEXBhp0CPwQ1A==} - engines: {node: '>=6'} - clean-stack@5.3.0: resolution: {integrity: sha512-9ngPTOhYGQqNVSfeJkYXHmF7AGWp4/nN5D/QqNQs3Dvxd1Kk/WpjHfNujKHYUQ/5CoGyOyFNoWSPk5afzP0QVg==} engines: {node: '>=14.16'} @@ -1678,9 +1352,9 @@ packages: config-chain@1.1.13: resolution: {integrity: sha512-qj+f8APARXHrM0hraqXYb2/bOVSV4PvJQlNZ/DVj0QrmNM2q2euizkeuVckQ57J+W0mRH6Hvi+k50M4Jul2VRQ==} - content-type@2.0.0: - resolution: {integrity: sha512-j/O/d7GcZCyNl7/hwZAb606rzqkyvaDctLmckbxLzHvFBzTJHuGEdodATcP3yIRoDrLHkIATJuvzbFlp/ki2cQ==} - engines: {node: '>=18'} + content-type@3.0.0: + resolution: {integrity: sha512-AIi5H6p0xk5uknXcN3/rmhP8jgp69OfSe/JuKiQAFprJ7UGw7mwj7m4XcmDzlrnJDG+cGpphAINGdU3g3g7kDw==} + engines: {node: '>=22'} conventional-changelog-angular@8.3.1: resolution: {integrity: sha512-6gfI3otXK5Ph5DfCOI1dblr+kN3FAm5a97hYoQkqNZxOaYa5WKfXH+AnpsmS+iUH2mgVC2Cg2Qw9m5OKcmNrIg==} @@ -1773,10 +1447,6 @@ packages: decimal.js@10.6.0: resolution: {integrity: sha512-YpgQiITW3JXGntzdUmyUR1V812Hn8T1YVXhCu+wO3OpS4eU9l4YdD3qjyiKdV6mvV29zapkMeD390UVEf2lkUg==} - deep-eql@5.0.2: - resolution: {integrity: sha512-h5k/5U50IJJFpzfL6nO9jaaumfjO/f2NjK/oYB2Djzm4p9L+3T9qWpZqZ2hAbLPuuYq9wrU08WQyBTL5GbPk5Q==} - engines: {node: '>=6'} - deep-extend@0.6.0: resolution: {integrity: sha512-LOHxIOaPYdHlJRtCQfDIVZtfw/ufM8+rVj649RIHzcm/vGwQRXFt6OPqIFWsm2XEMrNIEtWR64sY1LEKD2vAOA==} engines: {node: '>=4.0.0'} @@ -1799,6 +1469,10 @@ packages: resolution: {integrity: sha512-0je+qPKHEMohvfRTCEo3CrPG6cAzAYgmzKyxRiYSSDkS6eGJdyVJm7WaYA5ECaAD9wLB2T4EEeymA5aFVcYXCA==} engines: {node: '>=6'} + detect-libc@2.1.2: + resolution: {integrity: sha512-Btj2BOOO83o3WyH59e8MgXsxEQVcarkUOpEYrubB0urwnN10yQ364rsiByU11nZlqWYZm05i/of7io4mzihBtQ==} + engines: {node: '>=8'} + dir-glob@3.0.1: resolution: {integrity: sha512-WkrWp9GR4KXfKGYzOLmTuGVi1UWFfws377n9cc55/tb6DuqyF6pcQ5AbiHEshaDpY9v6oaSr2XCDidGmMwdzIA==} engines: {node: '>=8'} @@ -1830,9 +1504,6 @@ packages: duplexer2@0.1.4: resolution: {integrity: sha512-asLFVfWWtJ90ZyOUHMqk7/S2w2guQKxUI2itj3d92ADHhxUSbCMGi1f1cBcJ7xM1To+pE/Khbwo1yuNbMEPKeA==} - eastasianwidth@0.2.0: - resolution: {integrity: sha512-I88TYZWc9XiYHRQ4/3c5rjjfgkjhLyW2luGIheGERbNQ6OY7yTybanSpDXZa8y7VUP9YmDcYa+eyq4ca7iLqWA==} - electron-to-chromium@1.5.420: resolution: {integrity: sha512-2yD6XreGusOfNV+dUcvipJEXc3n/n7fgr7996aszTG+YY5E4mqM4tOq/3uhP129cazL9YHbVWSpc79ePotWtPA==} @@ -1887,12 +1558,12 @@ packages: resolution: {integrity: sha512-Zf5H2Kxt2xjTvbJvP2ZWLEICxA6j+hAmMzIlypy4xcBg1vKVnx89Wy0GbS+kf5cwCVFFzdCFh2XSCFNULS6csw==} engines: {node: '>= 0.4'} - es-iterator-helpers@1.3.3: - resolution: {integrity: sha512-0PuBxFi+4uPanB97iDxCLWuHeYud2FALrw5HFZGtAF38UpJDbDC8frwp2cnDyae692CQ0dou60UwWfhgsa4U/g==} + es-iterator-helpers@1.4.0: + resolution: {integrity: sha512-c/A0P0oxkACDc+cKWw8evLXK83oBKgn0qPOqCYT4x9uolpCIJAcYvJC9QYKNDRPsTeGyCrQ326jrvgZWdCdK5Q==} engines: {node: '>= 0.4'} - es-module-lexer@1.7.0: - resolution: {integrity: sha512-jEQoCwk8hyb2AZziIOLhDqpm5+2ww5uIE6lkO/6jcOCusfk6LhMHpXXfBLXTZ7Ydyt0j4VoUQv6uGNYbdW+kBA==} + es-module-lexer@2.3.2: + resolution: {integrity: sha512-poHGpORABojJJucnV9KbOavETW8lBVnphkW77ER5/BQ5Fz7oXSoCNek7IH3vR5nRjdsEz926ibFYX8KtLQmdyw==} es-object-atoms@1.1.2: resolution: {integrity: sha512-HWcBoN6NileqtSydK2FqHbS/LoDd2pqrnQHLyJzBj4kOp/ky2MWMN694xOfkK8/SnUsW2DH7EfyVlydKCsm1Zw==} @@ -1906,15 +1577,10 @@ packages: resolution: {integrity: sha512-d9T8ucsEhh8Bi1woXCf+TIKDIROLG5WCkxg8geBCbvk22kzwC5G2OnXVMO6FUsvQlgUUXQ2itephWDLqDzbeCw==} engines: {node: '>= 0.4'} - es-to-primitive@1.3.1: - resolution: {integrity: sha512-CxN9N56HYfd2m/acc/NOFrZQsN9kU4eh+2kk6A707Kz1krH8tKmfrs5RnftB8WNX80T0NS7vSQsDOlg23diR2g==} + es-to-primitive@1.3.4: + resolution: {integrity: sha512-yPDz7wqpg1/mmHLmS3tcfTfbw5f1eryXvyghYBffGdERwe+mV7ZcWzTR8LR17Kvqt3qfPurjlonmnq3MKXIOXw==} engines: {node: '>= 0.4'} - esbuild@0.27.2: - resolution: {integrity: sha512-HyNQImnsOC7X9PMNaCIeAm4ISCQXs5a5YasTXVliKv4uuBo1dKrG0A+uQS8M5eXjVMnLg3WgXaKvprHlFJQffw==} - engines: {node: '>=18'} - hasBin: true - escalade@3.2.0: resolution: {integrity: sha512-WUj2qlxaQtO4g6Pq5c29GTcWGDyd8itL8zTlipgECz3JesAiiOKotd8JU6otB3PACgG6xkJUyVhboMS+bje/jA==} engines: {node: '>=6'} @@ -1962,8 +1628,8 @@ packages: eslint-plugin-import-x: optional: true - eslint-module-utils@2.13.0: - resolution: {integrity: sha512-bLohSkT6469rRs8czj0tLTD8vaeIS/whvPRJVjDr7IuoTT1k5DYDERlNycjDj/HkOlvQdYurmfZ/g3fG5bgeLQ==} + eslint-module-utils@2.14.0: + resolution: {integrity: sha512-W2WCRZ9Dqntd+2u8jJcVMV2PKulc6RdLgUUoh/yQr3uB6lo/ZOeGx11sv60/8S4QFFKNslAlWhr9u0Ef7ZW6Ig==} engines: {node: '>=4'} peerDependencies: '@typescript-eslint/parser': '*' @@ -2032,9 +1698,10 @@ packages: resolution: {integrity: sha512-tD40eHxA35h0PEIZNeIjkHoDR4YjjJp34biM0mDvplBe//mB+IHCqHDGV7pxF+7MklTvighcCPPZC7ynWyjdTA==} engines: {node: ^20.19.0 || ^22.13.0 || >=24} - eslint@9.39.4: - resolution: {integrity: sha512-XoMjdBOwe/esVgEvLmNsD3IRHkm7fbKIUGvrleloJXUZgDHig2IPWNniv+GwjyJXzuNqVjlr5+4yVUZjycJwfQ==} + eslint@9.39.5: + resolution: {integrity: sha512-DgZS62aPLXKlnxILS/AYCoRvHaZeXceIzlXPkkGGzJWSow1aEk0lbTlxUSlyjC8jcaKxAdOnTDz+o1JFSBsyjw==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + deprecated: This version is no longer supported. Please see https://eslint.org/version-support for other options. hasBin: true peerDependencies: jiti: '*' @@ -2065,9 +1732,9 @@ packages: resolution: {integrity: sha512-kVscqXk4OCp68SZ0dkgEKVi6/8ij300KBWTJq32P/dYeWTSwK41WyTxalN1eRmA5Z9UU/LX9D7FWSmV9SAYx6g==} engines: {node: '>=0.10.0'} - execa@5.1.1: - resolution: {integrity: sha512-8uSpZZocAZRBAPIEINJj3Lo9HyGitllczc27Eh5YYojjMFMn8yHMDMaUHE2Jqfq05D/wucwI4JGURyXt1vchyg==} - engines: {node: '>=10'} + execa@10.0.1: + resolution: {integrity: sha512-ge98qjkRK4IB7tL7Ju/6qmm5LHoH1eEMt5FNZrz3f4UIYhF28lggX20z3FaX1sgc67msLEn0N0BscOs29iuwyw==} + engines: {node: '>=22'} execa@8.0.1: resolution: {integrity: sha512-VyhnebXciFV2DESc+p6B+y0LjSm0krU4OgJN44qFAhBY0TJ+1V61tYD2+wHusZ6F9n5K+vl8k0sTy7PEfV4qpg==} @@ -2077,8 +1744,8 @@ packages: resolution: {integrity: sha512-9Be3ZoN4LmYR90tUoVu2te2BsbzHfhJyfEiAVfz7N5/zv+jduIfLrV2xdQXOHbaD6KgpGdO9PRPM1Y4Q9QkPkA==} engines: {node: ^18.19.0 || >=20.5.0} - expect-type@1.3.0: - resolution: {integrity: sha512-knvyeauYhqjOYvQ66MznSMs83wmHrCycNEN6Ao+2AeYEfxUIkuiVxdEa1qlGEPK+We3n0THiDciYSsCcgW/DoA==} + expect-type@1.4.0: + resolution: {integrity: sha512-KfYbmpRm0VbLjEvVa9yGwCi9GI34xvi7A/HXYWQO65CSD2u3MczUJSuwXKFIxlGsgBQizV9q5J9NHj4VG0n+pA==} engines: {node: '>=12.0.0'} fast-deep-equal@3.1.3: @@ -2135,19 +1802,15 @@ packages: resolution: {integrity: sha512-f7ccFPK3SXFHpx15UIGyRJ/FJQctuKZ0zVuN3frBo4HnK3cay9VEW0R6yPYFHC0AgqhukPzKjq22t5DmAyqGyw==} engines: {node: '>=16'} - flatted@3.4.2: - resolution: {integrity: sha512-PjDse7RzhcPkIJwy5t7KPWQSZ9cAbzQXcafsetQoD7sOJRQlGikNbx7yZp2OotDnJyrDcbyRq3Ttb18iYOqkxA==} + flatted@3.4.4: + resolution: {integrity: sha512-5+ybhBZANEJxaH3X5evAFatUxLfEHSr7n6kYJ+1Qd0mUqr4eu9gIf6GDbWHf8RJijHrjjO8G+la14SlL2SeS1Q==} for-each@0.3.5: resolution: {integrity: sha512-dKx12eRCVIzqCxFGplyFKJMPvLEWgmNtUrpTiJIR5u97zEhRG8ySrtboPHZXx7daLxQVrl643cTzbab2tkQjxg==} engines: {node: '>= 0.4'} - foreground-child@3.3.1: - resolution: {integrity: sha512-gIXjKqtFuWEgzFRJA9WCQeSJLZDjgJUOMCMzxtvFq/37KojM1BFGufqsCy0r4qSQmYLsZYMeyRqzIWOMup03sw==} - engines: {node: '>=14'} - - fs-extra@11.3.5: - resolution: {integrity: sha512-eKpRKAovdpZtR1WopLHxlBWvAgPny3c4gX1G5Jhwmmw4XJj0ifSD5qB5TOo8hmA0wlRKDAOAhEE1yVPgs6Fgcg==} + fs-extra@11.4.0: + resolution: {integrity: sha512-EQsFzMUJkCKGr1ePqlYADkIUmHW1s3ZXr5Yqy6wbGrfUCphpl2maM/kyOIRA2HpP3AaFQTZXD4ldjek+nccddA==} engines: {node: '>=14.14'} fsevents@2.3.3: @@ -2209,8 +1872,8 @@ packages: resolution: {integrity: sha512-w9UMqWwJxHNOvoNzSJ2oPF5wvYcvP7jUvYzhp67yEhTi17ZDBBC1z9pTdGuzjD+EFIqLSYRweZjqfiPzQ06Ebg==} engines: {node: '>= 0.4'} - get-tsconfig@4.14.0: - resolution: {integrity: sha512-yTb+8DXzDREzgvYmh6s9vHsSVCHeC0G3PI5bEXNBHtmshPnO+S5O7qgLEOn0I5QvMy6kpZN8K1NKGyilLb93wA==} + get-tsconfig@4.14.3: + resolution: {integrity: sha512-++QEw4DIY7WGoukz+/+A/8dGYPT9l9yIadnmSgZ8Rjr3YVSVDipQSO9CdnJo9ePqFqUUqh+wk9uIaoiAwsiPkA==} get-tsconfig@5.0.0-beta.5: resolution: {integrity: sha512-/6gFNr0N04nob252sTQxyFLi3eKFRqIg1I87YcqAMT1i6SQrSF6KujUEQrtrjMV0H/eejTCltLdDSTEMzHbnsQ==} @@ -2223,11 +1886,6 @@ packages: resolution: {integrity: sha512-XxwI8EOhVQgWp6iDL+3b0r86f4d6AX6zSU55HfB4ydCEuXLXc5FcYeOu+nnGftS4TEju/11rt4KJPTMgbfmv4A==} engines: {node: '>=10.13.0'} - glob@10.5.0: - resolution: {integrity: sha512-DfXN8DfhJ7NH3Oe7cFmu3NCu1wKbkReJ8TorzSAFbSKrlNaQSKfIzqYqVY8zlbs2NLBbWpRiU52GX2PbaBVNkg==} - deprecated: Old versions of glob are not supported, and contain widely publicized security vulnerabilities, which have been fixed in the current version. Please update. Support for old versions may be purchased (at exorbitant rates) by contacting i@izs.me - hasBin: true - glob@13.0.6: resolution: {integrity: sha512-Wjlyrolmm8uDpm/ogGyXZXb1Z+Ca2B8NbJwqBVg0axK9GbBeoS7yGV6vjXnYdGm6X53iehEuxxbyiKp8QmN4Vw==} engines: {node: 18 || 20 || >=22} @@ -2236,8 +1894,8 @@ packages: resolution: {integrity: sha512-oahGvuMGQlPw/ivIYBjVSrWAfWLBeku5tpPE2fOPLi+WHffIWbuh2tCjhyQhTBPMf5E9jDEH4FOmTYgYwbKwtQ==} engines: {node: '>=18'} - globals@17.7.0: - resolution: {integrity: sha512-Czmyns5dUsq4seFBR/Kdydhmo8y9kC79hiSkPn0YcGtNnYWnrgt0vjrSjx9tspoDGWm2CMarffRuLjM4xUz8xg==} + globals@17.12.0: + resolution: {integrity: sha512-cezEd/DTyyht9cvSSURyygXPfy04GtWO/5e6ZPvH7fCtjKz9PYOmuawphw1Ctd1f6C+5JypXfGD7ahNMXvevBA==} engines: {node: '>=18'} globalthis@1.0.4: @@ -2329,10 +1987,6 @@ packages: resolution: {integrity: sha512-ag87y7cJJ9/3+GxFr8Oy4O5faDsGRGnBGsJj/YjOSsSx/5eadKLYTMPlzuR6obgoCDDm0abAAZitXXQkMOPSpA==} engines: {node: '>= 20'} - human-signals@2.1.0: - resolution: {integrity: sha512-B4FFZ6q/T2jhhksgkbEW3HBvWIfDW85snkQgawt07S7J5QXTk6BkNV+0yAeZrM5QpMAdYlocGoljn0sJ/WQkFw==} - engines: {node: '>=10.17.0'} - human-signals@5.0.0: resolution: {integrity: sha512-AXcZb6vzzrFAUE61HnN4mpLqd/cSIwNQjtNWR0euPm6y0iqx3G4gOXaIDdtdDwZmhwe82LA6+zinmW4UBWVePQ==} engines: {node: '>=16.17.0'} @@ -2345,8 +1999,8 @@ packages: resolution: {integrity: sha512-hsBTNUqQTDwkWtcdYI2i06Y/nUBEsNEDJKjWdigLvegy8kDuJAS8uRlpkkcQpyEXL0Z/pjDy5HBmMjRCJ2gq+g==} engines: {node: '>= 4'} - ignore@7.0.5: - resolution: {integrity: sha512-Hs59xBNfUIunMFgWAbGX5cq6893IbWg4KnrjbYwX3tx0ztorVgTDA6B2sxf8ejHJ4wz8BqGUMYlnzNBer5NvGg==} + ignore@7.0.8: + resolution: {integrity: sha512-YYNsSlXBjMk92SKnkwvB5LOVSa6OznlFUGcsvrFgNJbJCd0M1XKeFVRc8ZByeCqz32FivYNHJVooLmdqrmvp/Q==} engines: {node: '>= 4'} import-fresh@3.3.1: @@ -2368,10 +2022,6 @@ packages: resolution: {integrity: sha512-JmXMZ6wuvDmLiHEml9ykzqO6lwFbof0GG4IkcGaENdCRDDmMVnny7s5HsIgHCbaq0w2MyPhDqkhTUgS2LU2PHA==} engines: {node: '>=0.8.19'} - indent-string@4.0.0: - resolution: {integrity: sha512-EdDDZu4A2OyIK7Lr/2zG+w5jmbuk1DVBnEwREQvBzspBJkCEbRa8GxU1lghYcaGJCnRWibjDXlq779X1/y5xwg==} - engines: {node: '>=8'} - indent-string@5.0.0: resolution: {integrity: sha512-m6FAo/spmsW2Ab2fU35JTYwtOKa2yAwXSwgjSv1TJzh4Mh7mC3lzAOVLBprb72XsTrgkEIsl7YrFNAiDiRhIGg==} engines: {node: '>=12'} @@ -2491,10 +2141,6 @@ packages: resolution: {integrity: sha512-ISWac8drv4ZGfwKl5slpHG9OwPNty4jOWPRIhBpxOoD+hqITiwuipOQ2bNthAzwA3B4fIjO4Nln74N0S9byq8A==} engines: {node: '>= 0.4'} - is-stream@2.0.1: - resolution: {integrity: sha512-hFoiJiTl63nn+kstHGBtewWSKnQLpyb155KHheA1l39uvtO9nWIop1p3udqPcUd/xbF1VLMO4n7OI6p7RbngDg==} - engines: {node: '>=8'} - is-stream@3.0.0: resolution: {integrity: sha512-LnQR4bZ9IADDRSkvpqMGvt/tEJWclzklNgSw48V5EAaAeDd6qGvN8ei6k5p0tvxSR171VmGyHuTiAOfxAbr8kA==} engines: {node: ^12.20.0 || ^14.13.1 || >=16.0.0} @@ -2552,10 +2198,6 @@ packages: resolution: {integrity: sha512-GCfE1mtsHGOELCU8e/Z7YWzpmybrx/+dSTfLrvY8qRmaY6zXTKWn6WQIjaAFw069icm6GVMNkgu0NzI4iPZUNw==} engines: {node: '>=10'} - istanbul-lib-source-maps@5.0.6: - resolution: {integrity: sha512-yg2d+Em4KizZC5niWhQaIomgf5WlL4vOOjZ5xGCmF8SnPE/mDWWXgvRExdcpCgh9lLRRa1/fSYp2ymmbJ1pI+A==} - engines: {node: '>=10'} - istanbul-reports@3.2.0: resolution: {integrity: sha512-HGYWWS/ehqTV3xN10i23tkPkpH46MLCIMFNCaaKNavAXTF1RkqxawEPtnjnGZ6XKSInBKkiOA5BKS+aZiY3AvA==} engines: {node: '>=8'} @@ -2564,9 +2206,6 @@ packages: resolution: {integrity: sha512-H0dkQoCa3b2VEeKQBOxFph+JAbcrQdE7KC0UkqwpLmv2EC4P41QXP+rqo9wYodACiG5/WM5s9oDApTU8utwj9g==} engines: {node: '>= 0.4'} - jackspeak@3.4.3: - resolution: {integrity: sha512-OGlZQpz2yfahA/Rd1Y8Cd9SIEsqvXkLVoSw/cgwhnhFMDbsQFeZYoJJ7bIZBS9BcamUW96asq/npPWugM+RQBw==} - java-properties@1.0.2: resolution: {integrity: sha512-qjdpeo2yKlYTH7nFdK0vbZWuTCesk4o63v5iVOlhMQPfuIZQfW/HI35SjfhA+4qpg36rnFSvUK5b1m+ckIblQQ==} engines: {node: '>= 0.6.0'} @@ -2577,18 +2216,15 @@ packages: js-tokens@4.0.0: resolution: {integrity: sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ==} - js-tokens@9.0.1: - resolution: {integrity: sha512-mxa9E9ITFOt0ban3j6L5MpjwegGz6lBQmM1IJkWeBZGcMxto50+eWdjC/52xDbS2vy0k7vIMK0Fe2wfL9OQSpQ==} - js-yaml@4.3.1: resolution: {integrity: sha512-CY6crGq313MX8GkwvB7tzgp99vjQxY1++5y10/BKN/GUfHqWaOGQMNZkBvqSzsZKWk/ijwHlWzzkLulsGHhjWQ==} hasBin: true - jsdom@29.1.1: - resolution: {integrity: sha512-ECi4Fi2f7BdJtUKTflYRTiaMxIB0O6zfR1fX0GXpUrf6flp8QIYn1UT20YQqdSOfk2dfkCwS8LAFoJDEppNK5Q==} - engines: {node: ^20.19.0 || ^22.13.0 || >=24.0.0} + jsdom@30.0.1: + resolution: {integrity: sha512-52v7mUVUfNQVYYqE1lcdaymWL0njO7lTLUog6ZvW2U5KsbiLk/GnZlVJ+qx0xfNJZ6Gn+KSpPNE52vurbxZwrA==} + engines: {node: ^22.22.2 || ^24.15.0 || >=26.0.0} peerDependencies: - canvas: ^3.0.0 + canvas: ^3.2.3 peerDependenciesMeta: canvas: optional: true @@ -2613,8 +2249,8 @@ packages: json-stable-stringify-without-jsonify@1.0.1: resolution: {integrity: sha512-Bdboy+l7tA3OGW6FjyFHWkP5LuByj1Tk33Ljyq0axyzdk9//JSi2u3fP1QSmd1KNwq6VOKYGlAu87CisVir6Pw==} - json-with-bigint@3.5.8: - resolution: {integrity: sha512-eq/4KP6K34kwa7TcFdtvnftvHCD9KvHOGGICWwMFc4dOOKF5t4iYqnfLK8otCRCRv06FXOzGGyqE8h8ElMvvdw==} + json-with-bigint@3.5.12: + resolution: {integrity: sha512-uwbF/wSSuOgC7qqlq27Xp5B6a2MHVug3t0idZdTqu0JnlFvgJuH7ju+KAk/J06C7GfhoYy2gnb9wz2INqcne7w==} json5@1.0.2: resolution: {integrity: sha512-g1MWMLBiz8FKi1e4w0UyVL3w+iJceWAFBAaBnnGKOpNa5f8TLktkbre1+s6oICydWAm+HRUGTmI+//xv2hvXYA==} @@ -2646,6 +2282,80 @@ packages: resolution: {integrity: sha512-+bT2uH4E5LGE7h/n3evcS/sQlJXCpIp6ym8OWJ5eV6+67Dsql/LaaT7qJBAt2rzfoa/5QBGBhxDix1dMt2kQKQ==} engines: {node: '>= 0.8.0'} + lightningcss-android-arm64@1.33.0: + resolution: {integrity: sha512-gEpRTalKdosp4Bb8qWtc2iOgE5SeIHlpS1up9bFq2wAyYhl1UdTObYiHe98zEM9SQvSoqQZ1IQD0JNpg3Ml5pg==} + engines: {node: '>= 12.0.0'} + cpu: [arm64] + os: [android] + + lightningcss-darwin-arm64@1.33.0: + resolution: {integrity: sha512-Sciaz8eenNTKn9b3t7+xr0ipTp9YxKQY4npwQ3mrRuL0BAVHBLyZxofhaKBAVtzmtRZ/zTyo0/to4B1uWG/Djg==} + engines: {node: '>= 12.0.0'} + cpu: [arm64] + os: [darwin] + + lightningcss-darwin-x64@1.33.0: + resolution: {integrity: sha512-Z5UPAxzrjlWNNyGy6i65cJzzvgJ5D3T6wMvs+gWpY9d7qRhANrxqAp6LhxIgZhWEw18RfJTGcRxjuLIBr+m8XQ==} + engines: {node: '>= 12.0.0'} + cpu: [x64] + os: [darwin] + + lightningcss-freebsd-x64@1.33.0: + resolution: {integrity: sha512-QQM/Ti/hQajJwCY+RiWuCZ9sdtI/XQk7nDK5vC8kkdwixezOlDgvDx7+RT+QjK6FcFT4MpsuoBnHIo/O3StRRg==} + engines: {node: '>= 12.0.0'} + cpu: [x64] + os: [freebsd] + + lightningcss-linux-arm-gnueabihf@1.33.0: + resolution: {integrity: sha512-N7FVBe6iS24MlM6R/4RBTxGhQheZGs7tiQ9U32UtF75NzP5Q7xWPRqLBCKxlRQRk3rY1jCIPLzx7WzOhuUIRLQ==} + engines: {node: '>= 12.0.0'} + cpu: [arm] + os: [linux] + + lightningcss-linux-arm64-gnu@1.33.0: + resolution: {integrity: sha512-j2v/itmy4HlNxlc6voKXYgBqNi0Ng2LShg4z7GufpEgs05P+2suBVyi9I6YHq5uoVFx9ETin3eCEhLVyXGQnKg==} + engines: {node: '>= 12.0.0'} + cpu: [arm64] + os: [linux] + libc: [glibc] + + lightningcss-linux-arm64-musl@1.33.0: + resolution: {integrity: sha512-yiO5ROMuYQgXbC60yjZU5CYSFZGKXL0HFATXt9mHJn1+zW55oCtMI9NfcVhYLMFDL7gV7oBPon/EmMMGg2OvtQ==} + engines: {node: '>= 12.0.0'} + cpu: [arm64] + os: [linux] + libc: [musl] + + lightningcss-linux-x64-gnu@1.33.0: + resolution: {integrity: sha512-ar+Ju7LmcN0Jo4FpL4hpFybwNG9/3A/Br5KW2n2jyODg3MEZXaDYADdemoNS+BDNfMgKvylJLj4S5tyRActuAg==} + engines: {node: '>= 12.0.0'} + cpu: [x64] + os: [linux] + libc: [glibc] + + lightningcss-linux-x64-musl@1.33.0: + resolution: {integrity: sha512-RYiYbkokw0trfKqqzfF55lginwEPrD3OJDfTuJzFs1MK6iFnDenaz1fqLLtX4ITG3OktJQXOeTaw1awrBAlZPw==} + engines: {node: '>= 12.0.0'} + cpu: [x64] + os: [linux] + libc: [musl] + + lightningcss-win32-arm64-msvc@1.33.0: + resolution: {integrity: sha512-1K+MPfLSFVpphzpdbfkhlWk6wBrTObBzS2T6db10PNOZgR9GoVsAWzwNyuhUYYbTp23j+4RrncfujZ4uAzXvwA==} + engines: {node: '>= 12.0.0'} + cpu: [arm64] + os: [win32] + + lightningcss-win32-x64-msvc@1.33.0: + resolution: {integrity: sha512-OlEICDx/Xl0FqSp4bry8zFnCvGpig3Gl4gCquvYwHuqJKEC1+n9NgDniFvqHGmMv1ZkqDJrDqKKSykTDX+ehuA==} + engines: {node: '>= 12.0.0'} + cpu: [x64] + os: [win32] + + lightningcss@1.33.0: + resolution: {integrity: sha512-WkUDrojuJs0xkgGf2udWxa3yGBRxPtxUkB79i6aCZLRgc7PM8fZe9TosfPDcvEpQZbuFASnHYmRLBLUbmLOIIA==} + engines: {node: '>= 12.0.0'} + lines-and-columns@1.2.4: resolution: {integrity: sha512-7ylylesZQ/PV29jhEDl3Ufjo6ZX7gCqJr5F7PKrqc93v7fzSymt1BpwEU8nAUXs8qzzvqhbjhK5QZg6Mt/HkBg==} @@ -2682,21 +2392,15 @@ packages: lodash.uniqby@4.7.0: resolution: {integrity: sha512-e/zcLx6CSbmaEgFHCA7BnoQKyCtKMxnuWrJygbwPs/AIn+IMKl66L8/s+wBUn5LRw2pZx3bUHibiV1b6aTWIww==} - lodash@4.18.1: - resolution: {integrity: sha512-dMInicTPVE8d1e5otfwmmjlxkZoUpiVLwyeTdUsi/Caj/gfzzblBcCE5sRHV/AsjuCmxWrte2TNGSYuCeCq+0Q==} - loose-envify@1.4.0: resolution: {integrity: sha512-lyuxPGr/Wfhrlem2CL/UcnUc1zcqKAImBDzukY7Y5F/yQiNdko6+fRLevlw1HgMySw7f611UIY408EtxRSoK3Q==} hasBin: true - loupe@3.2.1: - resolution: {integrity: sha512-CdzqowRJCeLU72bHvWqwRBBlLcMEtIvGrlvef74kMnV2AolS9Y8xUv1I0U/MNAWMhBlKIoyuEgoJ0t/bbwHbLQ==} - lru-cache@10.4.3: resolution: {integrity: sha512-JNAzZcXrCt42VGLuYz0zfAzDfAvJWW6AfYlDBQyDV5DClI2m5sAmK+OIO7s59XfsRsWHp02jAJrRadPRGTt6SQ==} - lru-cache@11.5.1: - resolution: {integrity: sha512-RPimw/7aMdv2oqRrxKwvZXcPfwBrn/JZ2xYcY9Hus/6LaS3VOAKVWKWgNLCFSiOm1ESXinjsDlidVU7JlnCN2A==} + lru-cache@11.5.2: + resolution: {integrity: sha512-4pfM1Ff0x50o0tQwb5ucw/RzNyD0/YJME6IVcStalZuMWxdt3sR3huStTtxz4PUmvZfRguvDejasvQ2kifR11g==} engines: {node: 20 || >=22} lru-cache@5.1.1: @@ -2709,8 +2413,8 @@ packages: magic-string@0.30.21: resolution: {integrity: sha512-vd2F4YUyEXKGcLHoq+TEyCjxueSeHnFxyyjNp80yg0XV4vUhnDer/lvvlqM/arB5bXQN5K2/3oinyCRyx8T2CQ==} - magicast@0.3.5: - resolution: {integrity: sha512-L0WhttDl+2BOsybvEOLK7fW3UA0OQ0IQ2d6Zl2x/a6vVRs3bAY0ECOSHHeL5jD+SbOpOCUEi0y1DgHEn9Qn1AQ==} + magicast@0.5.4: + resolution: {integrity: sha512-llBEhWm1SacoRwgHUoQJYtwp4PBLF4faQi5TCpIGyGs9n4y5+juI0tDgyKIfpqxckRHaHzouUEph3THklWh03w==} make-asynchronous@1.1.0: resolution: {integrity: sha512-ayF7iT+44LXdxJLTrTd3TLQpFDDvPCBxXxbv+pMUSuHA5Q8zyAfwkRP6aHHwNVFBUFWtxAHqwNJxF8vMZLAbVg==} @@ -2754,16 +2458,12 @@ packages: engines: {node: '>=16'} hasBin: true - mimic-fn@2.1.0: - resolution: {integrity: sha512-OqbOk5oEQeAZ8WXWydlu9HJjz9WVdEIvamMCcXmuqUYjTknH/sqsWvhQ3vgwKFRR1HpjvNBKQ37nbJgYzGqGcg==} - engines: {node: '>=6'} - mimic-fn@4.0.0: resolution: {integrity: sha512-vqiC06CuhBTUdZH+RYl8sFrL096vA45Ok5ISO6sE/Mr1jRbGH4Csnhi8f3wKVl7x8mO4Au7Ir9D3Oyv1VYMFJw==} engines: {node: '>=12'} - minimatch@10.2.5: - resolution: {integrity: sha512-MULkVLfKGYDFYejP07QOurDLLQpcjk7Fw+7jXS2R2czRQzR56yHRveU5NDJEOviH+hETZKSkIk5c+T23GjFUMg==} + minimatch@10.2.6: + resolution: {integrity: sha512-vpLQEs+VLCr1nU0BXS07maYoFwlDAH0gngQuuttxIwutDFEMHq2blX+8vpgxDdK3J1PwjCJiep77OitTZ4Ll1A==} engines: {node: 18 || 20 || >=22} minimatch@3.1.5: @@ -2809,8 +2509,8 @@ packages: resolution: {integrity: sha512-Z3lTE9pLaJF47NyMhd4ww1yFTAP8YhYI8SleJiHzM46Fgpm5cnNzSl9XfzFNqbaz+VlJrIj3fXQ4DeN1Rjm6cw==} engines: {node: '>=18'} - node-exports-info@1.6.0: - resolution: {integrity: sha512-pyFS63ptit/P5WqUkt+UUfe+4oevH+bFeIiPPdfb0pFeYEu/1ELnJu5l+5EcTKYL5M7zaAa7S8ddywgXypqKCw==} + node-exports-info@1.6.2: + resolution: {integrity: sha512-kXs9Go0cah0qHVV2v389IXQLdLCeE1xfFtjOAF+iobu0OIoG1pje8At2vMHyaPMiPMnG/LWP50twML21eMcAag==} engines: {node: '>= 0.4'} node-releases@2.0.54: @@ -2829,10 +2529,6 @@ packages: resolution: {integrity: sha512-ARftfC5HdUNu9jJeL8pHj8debUIHA2b91FizCoMzY4lG6dDX13jdvTK0TBe24IBDRf2HvJSzzwEPvmbkQWHRSg==} engines: {node: '>=20'} - npm-run-path@4.0.1: - resolution: {integrity: sha512-S48WzZW777zhNIrn7gxOlISNAqi9ZC/uQFnRdbeIHhZhCA6UqpkOT8T1G7BvfdgP4Er8gF4sUbaS0i7QvIfCWw==} - engines: {node: '>=8'} - npm-run-path@5.3.0: resolution: {integrity: sha512-ppwTtiJZq0O/ai0z7yfudtBpWIoxM8yE6nHi1X47eFR2EWORqfbu6CnPlNsjeN683eT0qG6H/Pyf9fCcvjnnnQ==} engines: {node: ^12.20.0 || ^14.13.1 || >=16.0.0} @@ -2841,8 +2537,8 @@ packages: resolution: {integrity: sha512-9qny7Z9DsQU8Ou39ERsPU4OZQlSTP47ShQzuKZ6PRXpYLtIFgl/DEBYEXKlvcEa+9tHVcK8CF81Y2V72qaZhWA==} engines: {node: '>=18'} - npm@11.17.0: - resolution: {integrity: sha512-PurxiZexEHDTE4SSaLI3ZrnbAGiZfeyUcQcxcP5D+hfytNAze/D1IzDuInTn9XVLIbAQUnQuSPXJx02LHjLvQw==} + npm@11.19.1: + resolution: {integrity: sha512-ztsxKxt/kkIaAs+2i0GU6I+DRmUdrNasxTZKJe9TCdSjKxlhah/4r/hl5ygMD6XAg1qZ9c2TNomR4qgOydp10g==} engines: {node: ^20.17.0 || >=22.9.0} hasBin: true bundledDependencies: @@ -2944,14 +2640,10 @@ packages: resolution: {integrity: sha512-gXah6aZrcUxjWg2zR2MwouP2eHlCBzdV4pygudehaKXSGW4v2AsRQUK+lwwXhii6KFZcunEnmSUoYp5CXibxtA==} engines: {node: '>= 0.4'} - obug@2.1.3: - resolution: {integrity: sha512-9miFgM2OFba7hB+pRgvtV84pYTBaoTHohvmIgiRt6dRIzbwEOIaNaP+dIlGs2fNFoB0SeISs0Jz5WFVRid6Xyg==} + obug@2.1.4: + resolution: {integrity: sha512-4a+OsYv9UktOJKE+l1A4OufDgdRF9PifWj+tJnHURo/P+WOxpG4GzUFL9qCalmWauao6ogiG+QvnCovwPoyAWA==} engines: {node: '>=12.20.0'} - onetime@5.1.2: - resolution: {integrity: sha512-kbpaSSGJTWdAY5KPVeMOKXSrPtr8C8C7wodJbcsd51jRnmD+GZu8Y0VoU6Dm5Z4vWr0Ig/1NKuWRKf7j5aaYSg==} - engines: {node: '>=6'} - onetime@6.0.0: resolution: {integrity: sha512-1FlR+gjXK7X+AsAHso35MnyN5KqGwJRi/31ft6x0M194ht7S+rWAvd7PHss9xSKMzE0asv1pyIHaJYq+BbacAQ==} engines: {node: '>=12'} @@ -2960,8 +2652,8 @@ packages: resolution: {integrity: sha512-6IpQ7mKUxRcZNLIObR0hz7lxsapSSIYNZJwXPGeF0mTVqGKFIXj1DQcMoT22S3ROcLyY/rz0PWaWZ9ayWmad9g==} engines: {node: '>= 0.8.0'} - own-keys@1.0.1: - resolution: {integrity: sha512-qFOyK5PjiWZd+QQIh+1jhdb9LpxTF0qs7Pm8o5QHYZ0M3vKqSqzsZaEB6oWlxZ+q2sJBMI/Ktgd2N5ZwQoRHfg==} + own-keys@1.0.2: + resolution: {integrity: sha512-19YVAg7T+WTrxggPukVq7DjTv6+PJ867TmhCvBsYwmbFCsZd344rq2Ld1p0wo8f8Qrrhgp82c6FJRqdXWtSEhg==} engines: {node: '>= 0.4'} p-each-series@3.0.0: @@ -2992,14 +2684,10 @@ packages: resolution: {integrity: sha512-LaNjtRWUBY++zB5nE/NwcaoMylSPk+S+ZHNB1TzdbMJMny6dynpAGt7X/tl/QYq3TIeE6nxHppbo2LGymrG5Pw==} engines: {node: '>=10'} - p-map@7.0.4: - resolution: {integrity: sha512-tkAQEw8ysMzmkhgw8k+1U/iPhWNhykKnSk4Rd5zLoPJCuJaGRPo6YposrZgaxHKzDHdDWWZvE/Sk7hsL2X/CpQ==} + p-map@7.0.7: + resolution: {integrity: sha512-VaWRu2i4FJNRtiRWCuuQRgfQ1B7a6+gMSrO+3j0EQi/k0ULfS9kosRxGoiqwzIjZTDI02tGfk5mXXltLg6QtfQ==} engines: {node: '>=18'} - p-reduce@2.1.0: - resolution: {integrity: sha512-2USApvnsutq8uoxZBGbbWM0JIYLiEMJ9RlaN7fAzVNb9OZN0SHjjTTfIcb667XynS5Y1VhwDJVDa72TnPzAYWw==} - engines: {node: '>=8'} - p-reduce@3.0.0: resolution: {integrity: sha512-xsrIUgI0Kn6iyDYm9StOpOeK29XM1aboGji26+QEortiFST1hGZaUQOLhtEbqHErPpGW/aSz6allwK2qcptp0Q==} engines: {node: '>=12'} @@ -3066,10 +2754,6 @@ packages: path-parse@1.0.7: resolution: {integrity: sha512-LDJzPVEEEPR+y48z93A0Ed0yXb8pAByGWo/k5YYdYgpY2/2EsOsksJrq7lOHxryrVOn1ejG6oAp8ahvOIQD8sw==} - path-scurry@1.11.1: - resolution: {integrity: sha512-Xa4Nw17FS9ApQFJ9umLiJS4orGjm7ZzwUrwamcGQuHSzDyth9boKDaycYdDcZDuqYATXw4HFXgaqWTctW/v1HA==} - engines: {node: '>=16 || 14 >=14.18'} - path-scurry@2.0.2: resolution: {integrity: sha512-3O/iVVsJAPsOnpwWIeD+d6z/7PmqApyQePUtCndjatj/9I5LylHvt5qluFaBT3I5h3r1ejfR056c+FCv+NnNXg==} engines: {node: 18 || 20 || >=22} @@ -3081,10 +2765,6 @@ packages: pathe@2.0.3: resolution: {integrity: sha512-WUjGcAqP1gQacoQe+OBJsFA7Ld4DyXuUIjZ5cc75cLHvJ7dtNsTugphxIADwspS+AraAUePCKrSVtPLFj/F88w==} - pathval@2.0.1: - resolution: {integrity: sha512-//nshmD55c46FuFw26xV/xFAaB5HF9Xdap7HJBBnrKdAd6/GxDBaNA1870O79+9ueg61cZLSVc+OaFlfmObYVQ==} - engines: {node: '>= 14.16'} - picocolors@1.1.1: resolution: {integrity: sha512-xceH2snhtb5M9liqDsmEw56le376mTZkEX/jEb/RxNFyegNul7eNslCXP9FDj/Lcu0X8KEyMceP2ntpaHrDEVA==} @@ -3092,8 +2772,8 @@ packages: resolution: {integrity: sha512-V7+vQEJ06Z+c5tSye8S+nHUfI51xoXIXjHQ99cQtKUkQqqO1kO/KCJUfZXuB47h/YBlDhah2H3hdUGXn8ie0oA==} engines: {node: '>=8.6'} - picomatch@4.0.4: - resolution: {integrity: sha512-QP88BAKvMam/3NxH6vj2o21R6MjxZUAd6nlwAS/pnGvN9IVLocLHxGYIzFhg6fUQ+5th6P4dv4eW9jX3DSIj7A==} + picomatch@4.0.7: + resolution: {integrity: sha512-qcJu88Q2IWqJsDD529JKMdwGm/dvInW4HvQnRwiH9JtihJvzGOscDtHE3x1pBKeUOTysQ8kVmLnJ2kJu7yhcGA==} engines: {node: '>=12'} pify@3.0.0: @@ -3116,8 +2796,8 @@ packages: resolution: {integrity: sha512-vkcDPrRZo1QZLbn5RLGPpg/WmIQ65qoWWhcGKf/b5eplkkarX0m9z8ppCat4mlOqUsWpyNuYgO3VRyrYHSzX5g==} engines: {node: '>= 0.8.0'} - prettier@3.9.3: - resolution: {integrity: sha512-HWmu+K+zvHNpaMfSnYeqdqrDbR16cuIXaPx8WoHaviQkDJh1/0BNtOZmHVQI5jc3wXv0H1yXc9wjvFdXh+n3hQ==} + prettier@3.9.6: + resolution: {integrity: sha512-OpN0zzVdiaiAhxpuuj5efpIS4sY9j7bY6uR5mnj5yPzGkdkjNKSJeUThPb60Jw29QuAZgA4o+/iB49kFiaBX6g==} engines: {node: '>=14'} hasBin: true @@ -3125,8 +2805,8 @@ packages: resolution: {integrity: sha512-Qb1gy5OrP5+zDf2Bvnzdl3jsTf1qXVMazbvCoKhtKqVs4/YK4ozX4gKQJJVyNe+cajNPn0KoC0MC3FUmaHWEmQ==} engines: {node: ^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0} - pretty-ms@9.3.0: - resolution: {integrity: sha512-gjVS5hOP+M3wMm5nmNOucbIrqudzs9v/57bWRHQWLYklXqoXKrVfYW2W9+glfGsqtPgpiz5WwyEEB+ksXIx3gQ==} + pretty-ms@9.3.1: + resolution: {integrity: sha512-HzMy3Geq23nVALD/M2LliU+F+M+gVNsvkQWWqeBZ8HDiCgzo6YPJ/Omrmtq24EFrIsk0a3EkQGEd7bDOo+IhGA==} engines: {node: '>=18'} process-nextick-args@2.0.1: @@ -3233,40 +2913,30 @@ packages: engines: {node: 20 || >=22} hasBin: true - rolldown-plugin-dts@0.26.0: - resolution: {integrity: sha512-e+kEPtUiDES0htk5iqkSeF4EzAV7R+vugGB44iPDuw1Kw9E+WyL1VG7PaV0IIjGHLiacztMBcMTyrr8ON9CT1Q==} + rolldown-plugin-dts@0.27.14: + resolution: {integrity: sha512-ZvuDDwoIpRK9RPxDXratCpklFO9QZZWndf/sd0VBFb4LEj0jj07UcHK9OCh7V4XiFz2Z89ziyBC2K6tJiDjrbw==} engines: {node: ^22.18.0 || >=24.11.0} peerDependencies: - '@ts-macro/tsc': ^0.3.6 - '@typescript/native-preview': '>=7.0.0-dev.20260325.1' + '@typescript/native-preview': '*' + '@volar/typescript': ~2.4.0 rolldown: ^1.0.0 - typescript: ^5.0.0 || ^6.0.0 + typescript: ^5.0.0 || ^6.0.0 || ~7.0.0 vue-tsc: ~3.2.0 || ~3.3.0 peerDependenciesMeta: - '@ts-macro/tsc': - optional: true '@typescript/native-preview': optional: true + '@volar/typescript': + optional: true typescript: optional: true vue-tsc: optional: true - rolldown@1.0.0-rc.17: - resolution: {integrity: sha512-ZrT53oAKrtA4+YtBWPQbtPOxIbVDbxT0orcYERKd63VJTF13zPcgXTvD4843L8pcsI7M6MErt8QtON6lrB9tyA==} + rolldown@1.2.7: + resolution: {integrity: sha512-g0EtLvBjTUB7jhyV0S/TCup3v/XSVl45vUIGbOGU4QPiyjTenCe4mKuFvW9fEgYmS2Fo42AUssRmNuMziXdrig==} engines: {node: ^20.19.0 || >=22.12.0} hasBin: true - rolldown@1.1.3: - resolution: {integrity: sha512-1F1eEtUBtFvcGm1HQ9TiUIUHPQG7mSAODrhIzjxoUEFuo8OcbrGLiVLkevNgj84TE4lnHvnumwFjhJO5Eu135g==} - engines: {node: ^20.19.0 || >=22.12.0} - hasBin: true - - rollup@4.62.2: - resolution: {integrity: sha512-RFnrW4lhXA3s3eqHDZvN654g8OTjzRfqpIRJYczCGB6HzphckVAi/Qh4tbPUbRuDi7s1Llv8g/NspLkttY3gTA==} - engines: {node: '>=18.0.0', npm: '>=8.0.0'} - hasBin: true - safe-array-concat@1.1.4: resolution: {integrity: sha512-wtZlHyOje6OZTGqAoaDKxFkgRtkF9CnHAVnCHKfuj200wAgL+bSJhdsCD2l0Qx/2ekEXjPWcyKkfGb5CPboslg==} engines: {node: '>=0.4'} @@ -3289,8 +2959,8 @@ packages: scheduler@0.23.2: resolution: {integrity: sha512-UOShsPwz7NrMUqhR6t0hWjFduvOzbtv7toDH1/hIrfRNIDBnnBWd0CwJTGvTpngVlmwGCdP9/Zl/tVrDqcuYzQ==} - semantic-release@25.0.5: - resolution: {integrity: sha512-mn61SUJwtM8ThrWn2WmgLVpwVJeG/hPSupua1psdMoufmwRIPyvRLkRkL0JDXkP67OntlLWUYnBnfVc8EDO3/g==} + semantic-release@25.0.9: + resolution: {integrity: sha512-bxve7csK0/Txr++CkfrmV+X1r4jqiSOw2WsSad9E2S68R+ZfLBwDn8IceM8WfiOmKQIHgsQc1cNA8Dzg7U75pg==} engines: {node: ^22.14.0 || >= 24.10.0} hasBin: true @@ -3346,9 +3016,6 @@ packages: siginfo@2.0.0: resolution: {integrity: sha512-ybx0WO1/8bSBLEWXZvEd7gMW3Sn3JFlW3TvX1nREbDLRNQNaeNN8WK0meBwPdAaOI7TtRRRJn/Es1zhrrCHu7g==} - signal-exit@3.0.7: - resolution: {integrity: sha512-wnD2ZE+l+SPC/uoS0vXeE9L1+0wuaMqKlfz9AMUo38JsyLSBWSFcHR1Rri62LZc12vLr1gb3jl7iwQhgwpAbGQ==} - signal-exit@4.1.0: resolution: {integrity: sha512-bzyZ1e88w9O1iNJbKnOlvYTrWPDl46O1bG0D3XInv+9tkPrxrN8jUUTiFlDkkmKWgn1M6CfIA13SuGqOa9Korw==} engines: {node: '>=14'} @@ -3394,8 +3061,8 @@ packages: stackback@0.0.2: resolution: {integrity: sha512-1XMJE5fQo1jGH6Y/7ebnwPOBEkIEnT4QF32d5R1+VXdXveM0IBMJt8zfaxX1P3QhVwrYe+576+jkANtSS2mBbw==} - std-env@3.10.0: - resolution: {integrity: sha512-5GS12FdOZNliM5mAOxFRg7Ir0pWz8MdpYm6AY6VPkGpbA7ZzmbzNcBJQ0GPvvyWgcY7QAhCgf9Uy89I03faLkg==} + std-env@4.2.0: + resolution: {integrity: sha512-oCUKSupKTHX53EyjDtuZQ64pjLJ6yYCtpmEw0goYxtjG9KpbRe8KAsl2tBUGU9DyMcJ0RwJ8GqJAFzMXcXW1Rw==} stop-iteration-iterator@1.1.0: resolution: {integrity: sha512-eLoXW/DHyl62zxY4SCaIgnRhuMr6ri4juEYARS8E6sCEqzKpOiE521Ucofdx+KnDZl5xmvGYaaKCk5FEOxJCoQ==} @@ -3408,20 +3075,20 @@ packages: resolution: {integrity: sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g==} engines: {node: '>=8'} - string-width@5.1.2: - resolution: {integrity: sha512-HnLOCR3vjcY8beoNLtcjZ5/nxn2afmME6lhrDrebokqMap+XbeW8n9TXpPDOqdGK5qcI3oT0GKTW6wC7EMiVqA==} - engines: {node: '>=12'} - string-width@7.2.0: resolution: {integrity: sha512-tsaTIkKW9b4N+AEj+SVA+WhJzV7/zMhcSu78mLKWSk7cXMOSHsBKFWUs0fWwq8QyK3MgJBQRX6Gbi4kYbdvGkQ==} engines: {node: '>=18'} + string-width@8.2.2: + resolution: {integrity: sha512-GaPUh5gfdrYzqeVNZvUfT23vYYxXzKYidUcnMtJg/3rxRV63EFZy3k6xfKlmfeJD0176lnUV/Usr3XcwSvFzpg==} + engines: {node: '>=20'} + string.prototype.includes@2.0.1: resolution: {integrity: sha512-o7+c9bW6zpAdJHTtujeePODAhkuicdAryFsfVKwA+wGw89wJ4GTY484WTucM9hLtDEOpOvI+aHnzqnC5lHp4Rg==} engines: {node: '>= 0.4'} - string.prototype.matchall@4.0.12: - resolution: {integrity: sha512-6CC9uyBL+/48dYizRf7H7VAYCMCNTBeM78x/VTUe9bFEaxBepPJDa1Ow99LqI/1yF7kuy7Q3cQsYMrcjGUcskA==} + string.prototype.matchall@4.1.0: + resolution: {integrity: sha512-tHNHTxInrYLCga9O9YGxWA3G9/nnzQw8UGAyqGx3Ar1pSTTzIuM4woFSq4SowkXCjJIwq5sIiQvEfRI9tCH1qQ==} engines: {node: '>= 0.4'} string.prototype.repeat@1.0.0: @@ -3454,10 +3121,6 @@ packages: resolution: {integrity: sha512-vavAMRXOgBVNF6nyEEmL3DBK19iRpDcoIwW+swQ+CbGiu7lju6t+JklA1MHweoWtadgt4ISVUsXLyDq34ddcwA==} engines: {node: '>=4'} - strip-final-newline@2.0.0: - resolution: {integrity: sha512-BrpvfNAE3dcvq7ll3xVumzjKjZQ5tI1sEUIKr3Uoks0XUl45St3FlatVqef9prk4jRDzhW6WZg+3bk93y6pLjA==} - engines: {node: '>=6'} - strip-final-newline@3.0.0: resolution: {integrity: sha512-dOESqjYr96iWYylGObzd39EuNTa5VJxyvVAEm5Jnh7KGo75V43Hk1odPQkNDyXNmUR6k+gEiDVXnjB8HJ3crXw==} engines: {node: '>=12'} @@ -3474,9 +3137,6 @@ packages: resolution: {integrity: sha512-6fPc+R4ihwqP6N/aIv2f1gMH8lOVtWQHoqC4yK6oSDVVocumAsfCqjkXnqiYMhmMwS/mEHLp7Vehlt3ql6lEig==} engines: {node: '>=8'} - strip-literal@3.1.0: - resolution: {integrity: sha512-8r3mkIM/2+PpjHoOtiAW8Rg3jJLHaV7xPwG+YRGrv6FP0wwk/toTpATxWYOW0BKdWwl82VT2tFYi5DlROa0Mxg==} - super-regex@1.1.0: resolution: {integrity: sha512-WHkws2ZflZe41zj6AolvvmaTrWds/VuyeYr9iPVv/oQeaIoVxMKaushfFWpOGDT+GuBrM/sVqF8KUCYQlSSTdQ==} engines: {node: '>=18'} @@ -3512,10 +3172,6 @@ packages: resolution: {integrity: sha512-d79HhZya5Djd7am0q+W4RTsSU+D/aJzM+4Y4AGJGuGlgM2L6sx5ZvOYTmZjqPhrDrV6xJTtRSm1JCLj6V6LHLQ==} engines: {node: '>=14.16'} - test-exclude@7.0.2: - resolution: {integrity: sha512-u9E6A+ZDYdp7a4WnarkXPZOx8Ilz46+kby6p1yZ8zsGTz9gYa6FIS7lj2oezzNKmtdyyJNNmmXDppga5GB7kSw==} - engines: {node: '>=18'} - thenify-all@1.6.0: resolution: {integrity: sha512-RNxQH/qI8/t3thXJDwcstUO4zeqo64+Uy/+sNVRBx4Xn2OX+OZ9oP+iJnNFqplFra2ZUVeKCSa2oVWi3T4uVmA==} engines: {node: '>=0.8'} @@ -3533,42 +3189,31 @@ packages: tinybench@2.9.0: resolution: {integrity: sha512-0+DUvqWMValLmha6lr4kD8iAMK1HzV0/aKnCtWb9v9641TnP/MFb7Pc2bxoxQjTXAErryXVgUOfv2YqNllqGeg==} - tinyexec@0.3.2: - resolution: {integrity: sha512-KQQR9yN7R5+OSwaK0XQoj22pwHoTlgYqmUscPYoknOoWCWfj/5/ABTMRi69FrKU5ffPVh5QcFikpWJI/P1ocHA==} - - tinyexec@1.2.4: - resolution: {integrity: sha512-SHf/r48b7vOrjve9PxJo3MN5v5yuyjHvdUcrQffT3WXMUfnGmHDVbC4k3sHJaJTgZCwpUplIaAo5ANtMyp3YHg==} + tinyexec@1.3.0: + resolution: {integrity: sha512-QKAl9m8gWWGHV8jZcPeym6j+XULi6tOf1mT83WYJ4Lk2ytW/uwAWkrP0uFsdoYMdueVJ0qs26wZ+23xeB4ibNQ==} engines: {node: '>=18'} tinyglobby@0.2.17: resolution: {integrity: sha512-wXR/dYpcqKmfWpEdZjiKJOwCNFndD0DMnrW/cYjVGttEkBfVgcLFHoNrlj47mjOVic9yyNu65alsgF4NQyTa2g==} engines: {node: '>=12.0.0'} - tinypool@1.1.1: - resolution: {integrity: sha512-Zba82s87IFq9A9XmjiX5uZA/ARWDrB03OHlq+Vw1fSdt0I+4/Kutwy8BP4Y/y/aORMo61FQ0vIb5j44vSo5Pkg==} - engines: {node: ^18.0.0 || >=20.0.0} - - tinyrainbow@2.0.0: - resolution: {integrity: sha512-op4nsTR47R6p0vMUUoYl/a+ljLFVtlfaXkLQmqfLR1qHma1h/ysYk4hEXZ880bf2CYgTskvTa/e196Vd5dDQXw==} - engines: {node: '>=14.0.0'} - - tinyspy@4.0.4: - resolution: {integrity: sha512-azl+t0z7pw/z958Gy9svOTuzqIk6xq+NSheJzn5MMWtWTFywIacg2wUlzKFGtt3cthx0r2SxMK0yzJOR0IES7Q==} + tinyrainbow@3.1.1: + resolution: {integrity: sha512-yau8yJdTt989Mm0Bd/236QnzEiPf2xLLTqUZRUJOo/3CB078LSwzei343DgtJVmfJKJE3TMINY1u42SQsP6mXw==} engines: {node: '>=14.0.0'} - tldts-core@7.4.5: - resolution: {integrity: sha512-pGrwzZDvPwKe+7NNUqAunb6rqTfynr0VOUhCMdqbu5xlvNiszsAJygRzwvpVycdzejlbpY+SWJOn+s75Og7FEA==} + tldts-core@7.4.11: + resolution: {integrity: sha512-CW3WN2rIIE/Of21mulhgnGOwoDyEFNygyIBOONSdyAuSATgMMUCpLeUlB+E8sAwA5xRV9hYPl+kyZ9citHCaKg==} - tldts@7.4.5: - resolution: {integrity: sha512-RfEzKWcq5fHUOFq7J3rl3Oz6ylKGtcHqUznzj4EcXsxLSIjJcvpbXAQtWGeJQ0xKnimR5e0Cn+cn9TssfMzm+g==} + tldts@7.4.11: + resolution: {integrity: sha512-aBiNayCfTQxuIJBm06M+xR14cYaYlDlSXZbgsnKzKNxDKUVq7KFwTjwBSsb7m9Y5xO8WfPnBc63WaYFMTGlvqw==} hasBin: true to-regex-range@5.0.1: resolution: {integrity: sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ==} engines: {node: '>=8.0'} - tough-cookie@6.0.1: - resolution: {integrity: sha512-LktZQb3IeoUWB9lqR5EWTHgW/VTITCXg4D21M+lvybRVdylLrRMnqaIONLVb5mav8vM19m44HIcGq4qASeu2Qw==} + tough-cookie@6.0.2: + resolution: {integrity: sha512-exgYmnmL/sJpR3upZfXG5PoatXQii55xAiXGXzY+sROLZ/Y+SLcp9PgJNI9Vz37HpQ74WvDcLT8eqm+kV3FzrA==} engines: {node: '>=16'} tr46@6.0.0: @@ -3592,18 +3237,18 @@ packages: tsconfig-paths@3.15.0: resolution: {integrity: sha512-2Ac2RgzDe/cn48GvOe3M+o82pEFewD3UPbyoUHHdKasHwJKjds4fLXWf/Ux5kATBKN20oaFGu+jbElp1pos0mg==} - tsdown@0.22.3: - resolution: {integrity: sha512-louqbfA8Qf//B9jTTL0FPtXTNpjCWv1VPkbcmQMph2pTpzs+LnB1tbe4tDDRVpo2BjF5SgUXaTZe45SxB8pWHg==} + tsdown@0.22.14: + resolution: {integrity: sha512-ule7Y+fsAN2iZbLDoo7C4KYljFJNJJ+fLshyn+9gozeTspVersWHxwdGB+Dm2hzA38s6muFnUTl0jK3vJm9ifQ==} engines: {node: ^22.18.0 || >=24.11.0} hasBin: true peerDependencies: '@arethetypeswrong/core': ^0.18.1 - '@tsdown/css': 0.22.3 - '@tsdown/exe': 0.22.3 + '@tsdown/css': 0.22.14 + '@tsdown/exe': 0.22.14 '@vitejs/devtools': '*' publint: ^0.3.8 tsx: '*' - typescript: ^5.0.0 || ^6.0.0 + typescript: ^5.0.0 || ^6.0.0 || ^7.0.0 unplugin-unused: ^0.5.0 unrun: '*' peerDependenciesMeta: @@ -3649,8 +3294,8 @@ packages: resolution: {integrity: sha512-TeTSQ6H5YHvpqVwBRcnLDCBnDOHWYu7IvGbHT6N8AOymcr9PJGjc1GTtiWZTYg0NCgYwvnYWEkVChQAr9bjfwA==} engines: {node: '>=16'} - type-fest@5.7.0: - resolution: {integrity: sha512-1URUxUqfHFM1c+zfSPsa3gnkO7Aq21qyH75SIduNYz4SzY964rn1X2vCMQaHSHhktiw+0kPa2iyb6PUpXqB6Vg==} + type-fest@5.9.0: + resolution: {integrity: sha512-yANm3Jr3GiJ1qgJlxGAVxTOIcEOk1rhQHamlXtnrCK7EHP4HeM9OGxtMg/W7HFdrVzw/ZWJKGVIJusVH85sLtw==} engines: {node: '>=20'} typed-array-buffer@1.0.3: @@ -3669,8 +3314,8 @@ packages: resolution: {integrity: sha512-phPGCwqr2+Qo0fwniCE8e4pKnGu/yFb5nD5Y8bf0EEeiI5GklnACYA9GFy/DrAeRrKHXvHn+1SUsOWgJp6RO+g==} engines: {node: '>= 0.4'} - typescript-eslint@8.62.0: - resolution: {integrity: sha512-8QxXi+ZACKX0kaqO4gY8kn0RSD9gFfaHDWwjqtEN48aWCBkX4MJaufWN+c3BzlrXLOxfywDL8CaoqUwcRq4j4Q==} + typescript-eslint@8.69.0: + resolution: {integrity: sha512-B3MltX0VqjUBNEe3b3sSuiRbfa6XrfHFtBiPamjT5AsW/dfq+y+bc0wyuS9DxAS1LyzCxRp2+rxzpLUvqM2BvA==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: eslint: ^8.57.0 || ^9.0.0 || ^10.0.0 @@ -3693,8 +3338,8 @@ packages: unconfig-core@7.5.0: resolution: {integrity: sha512-Su3FauozOGP44ZmKdHy2oE6LPjk51M/TRRjHv2HNCWiDvfvCoxC2lno6jevMA91MYAdCdwP05QnWdWpSbncX/w==} - undici-types@7.8.0: - resolution: {integrity: sha512-9UJ2xGDvQ43tYyVMpuHlsgApydB8ZKfVYTsLDhXkFL/6gfkp+U8xTGdh8pMJv1SpZna0zxG1DwsKZsreLbXBxw==} + undici-types@8.3.0: + resolution: {integrity: sha512-j375ScV60dom+YkPFIfTLcOiPxkN/buHz5GobjLhixFuANaNs3C9l4GmrWqejgXWJ7BbJcFYpTEUkS1Ge8bpZQ==} undici@7.29.0: resolution: {integrity: sha512-IDxfleLmmbSskfWSUATiN1nfn2rDuvnMOqb5CWR92iIfojA0Ud+ulOAAEQ57LPr9rWmsreUyf5lwyao+7GNNVw==} @@ -3730,16 +3375,6 @@ packages: unrs-resolver@1.12.2: resolution: {integrity: sha512-dmlRxBJJayXjqTwC+JtF1HhJmgf3ftQ3YejFcZrf4+KKtJv0qDsK1pjqaaVjG7wJ5NJ6UVP1OqRMQ71Z4C3rxQ==} - unrun@0.2.39: - resolution: {integrity: sha512-h9FxYVpztY/wwq+bauLOh6Y3CWu2IVeRLq5lxzneBiIU9Tn86OGp9xiQrGhnYspAmg5dzdY0Cc8+Y70kuTARCg==} - engines: {node: '>=20.19.0'} - hasBin: true - peerDependencies: - synckit: ^0.11.11 - peerDependenciesMeta: - synckit: - optional: true - update-browserslist-db@1.3.2: resolution: {integrity: sha512-UQ+MSxlhRm1bzjhU+DcuXfjFO1FzNtqhK5+9Yvlp90ItDLk5vT932A0rFu619nf7RVS+Y/VeaUW1jaRDqZ8VJw==} hasBin: true @@ -3759,20 +3394,20 @@ packages: validate-npm-package-license@3.0.4: resolution: {integrity: sha512-DpKm2Ui/xN7/HQKCtpZxoRWBhZ9Z0kqtygG8XCgNQ8ZlDnxuQmWhj566j8fN4Cu3/JmbhsDo7fcAJq4s9h27Ew==} - vite-node@3.2.4: - resolution: {integrity: sha512-EbKSKh+bh1E1IFxeO0pg1n4dvoOTt0UDiXMd/qn++r98+jPO1xtJilvXldeuQ8giIB5IkpjCgMleHMNEsGH6pg==} - engines: {node: ^18.0.0 || ^20.0.0 || >=22.0.0} - hasBin: true + verkit@0.3.2: + resolution: {integrity: sha512-zj/ob3UsvJGN0whEAKFp53REA5X66hvffVqoCtVQAakJKnKlH+/PcOfMoFwIG/o4rElqLv/ycAFlx8ZlXUorCg==} + engines: {node: '>=18.12.0'} - vite@7.3.5: - resolution: {integrity: sha512-KuOaNhcnGFN2zIPGA7wRmzF+lJA1sea7rHq17aiJ++9lzY1WWG6Jpwqwe1KNbRVPIqHmr8GLYx7jbrQcN/7/ww==} + vite@8.2.2: + resolution: {integrity: sha512-cFKLV/PRgAUlIRm5WjMjJ86jrftzpqcgH+Us+DS8mI3CDNiH30Whrz8uHL3+MOLPAgqbMBAqWdAHAphOAM+z/Q==} engines: {node: ^20.19.0 || >=22.12.0} hasBin: true peerDependencies: '@types/node': ^20.19.0 || >=22.12.0 + '@vitejs/devtools': ^0.4.0 || ^0.5.0 + esbuild: ^0.27.0 || ^0.28.0 jiti: '>=1.21.0' less: ^4.0.0 - lightningcss: ^1.21.0 sass: ^1.70.0 sass-embedded: ^1.70.0 stylus: '>=0.54.8' @@ -3783,12 +3418,14 @@ packages: peerDependenciesMeta: '@types/node': optional: true + '@vitejs/devtools': + optional: true + esbuild: + optional: true jiti: optional: true less: optional: true - lightningcss: - optional: true sass: optional: true sass-embedded: @@ -3804,26 +3441,39 @@ packages: yaml: optional: true - vitest@3.2.6: - resolution: {integrity: sha512-xejya+bT/j/+R/AGa1XOfRxLmNUlLtlwjRsFUILF+xHfzElmGcmFydy2gqqIrd62ptIEfwVMofd19uNWD9L7Nw==} - engines: {node: ^18.0.0 || ^20.0.0 || >=22.0.0} + vitest@4.1.11: + resolution: {integrity: sha512-fhACrNXUidIbGSBr5FlbuBkO7VWC1ZyLl0DO4CU2DrQoAPxX84Ysxs+HeGQpii5lZWV1Q4gBZTTu49mF+A6Edw==} + engines: {node: ^20.0.0 || ^22.0.0 || >=24.0.0} hasBin: true peerDependencies: '@edge-runtime/vm': '*' - '@types/debug': ^4.1.12 - '@types/node': ^18.0.0 || ^20.0.0 || >=22.0.0 - '@vitest/browser': 3.2.6 - '@vitest/ui': 3.2.6 + '@opentelemetry/api': ^1.9.0 + '@types/node': ^20.0.0 || ^22.0.0 || >=24.0.0 + '@vitest/browser-playwright': 4.1.11 + '@vitest/browser-preview': 4.1.11 + '@vitest/browser-webdriverio': 4.1.11 + '@vitest/coverage-istanbul': 4.1.11 + '@vitest/coverage-v8': 4.1.11 + '@vitest/ui': 4.1.11 happy-dom: '*' jsdom: '*' + vite: ^6.0.0 || ^7.0.0 || ^8.0.0 peerDependenciesMeta: '@edge-runtime/vm': optional: true - '@types/debug': + '@opentelemetry/api': optional: true '@types/node': optional: true - '@vitest/browser': + '@vitest/browser-playwright': + optional: true + '@vitest/browser-preview': + optional: true + '@vitest/browser-webdriverio': + optional: true + '@vitest/coverage-istanbul': + optional: true + '@vitest/coverage-v8': optional: true '@vitest/ui': optional: true @@ -3851,6 +3501,10 @@ packages: resolution: {integrity: sha512-1to4zXBxmXHV3IiSSEInrreIlu02vUOvrhxJJH5vcxYTBDAx51cqZiKdyTxlecdKNSjj8EcxGBxNf6Vg+945gw==} engines: {node: ^20.19.0 || ^22.12.0 || >=24.0.0} + whatwg-url@17.1.0: + resolution: {integrity: sha512-3GeworPmc2ZfEEHP7lEbUfBX/L75wdEsi0rLNhXcXxnoN5jyq0SL5gCy06SGW2cyTIZdTvWIDQNQoza++vKeaw==} + engines: {node: ^22.14.0 || >=24.0.0} + which-boxed-primitive@1.1.1: resolution: {integrity: sha512-TbX3mj8n0odCBFVlY8AxkqcHASw3L60jIuF8jFP78az3C2YhmGvqbHBpAjTRH2/xqYunrJ9g1jSyjCjpoWzIAA==} engines: {node: '>= 0.4'} @@ -3863,6 +3517,11 @@ packages: resolution: {integrity: sha512-K4jVyjnBdgvc86Y6BkaLZEN933SwYOuBFkdmBu9ZfkcAbdVbpITnDmjvZ/aQjRXQrv5EPkTnD1s39GiiqbngCw==} engines: {node: '>= 0.4'} + which-command@0.1.0: + resolution: {integrity: sha512-XZyoF5/5hZtXitIwzrU4NKK+Wtbb9aB9CezUEw2Q0wlYK8NUYQxC1rRXgNueYLtBAJwXIb+/tFVk4dozciNJMA==} + engines: {node: '>=22'} + hasBin: true + which-typed-array@1.1.22: resolution: {integrity: sha512-fvO4ExWMFsqyhG3AiPAObMuY1lxaqgYcxbc49CNdWDDECOJNgQyvsOWVwbZc+qf3rzRtxojBK+CMEv0Ld5CYpw==} engines: {node: '>= 0.4'} @@ -3888,10 +3547,6 @@ packages: resolution: {integrity: sha512-YVGIj2kamLSTxw6NsZjoBxfSwsn0ycdesmc4p+Q21c5zPuZ1pl+NfxVdxPtdHvmNVOQ6XSYG4AUtyt/Fi7D16Q==} engines: {node: '>=10'} - wrap-ansi@8.1.0: - resolution: {integrity: sha512-si7QWI6zUMq56bESFvagtmzMdGOtoxfR+Sez11Mobfc7tm+VkUckk9bW2UeffTGVUbOksxmSw0AA2gs8g71NCQ==} - engines: {node: '>=12'} - wrap-ansi@9.0.2: resolution: {integrity: sha512-42AtmgqjV+X1VpdOfyTGOYRi0/zsoLqtXQckTmqTeybT+BDIbM/Guxo7x3pE2vtpr1ok6xRqM9OpBe+Jyoqyww==} engines: {node: '>=18'} @@ -3926,26 +3581,35 @@ packages: resolution: {integrity: sha512-Nt9ZJjXTv5R8MHbqby/wXQ6Gi0Bb3TcYZkR1bzuL4yB2OxWPkXknz513gEF0GoA6tn00UpbPvERW8rzCuWCA6w==} engines: {node: '>=10'} - yargs@18.0.0: - resolution: {integrity: sha512-4UEqdc2RYGHZc7Doyqkrqiln3p9X2DZVxaGbwhn2pi7MrRagKaOcIKe8L3OxYcbhXLgLFUS3zAYuQjKBQgmuNg==} + yargs@18.1.0: + resolution: {integrity: sha512-2rAgRKu54VsHkqI0/tYkmluGXHD4KW7yZoycuqDQ15QOTnc2VVfy0nN/1eMhnQLO00A+dwtK20xuCnc1YGeUyg==} engines: {node: ^20.19.0 || ^22.12.0 || >=23} yocto-queue@0.1.0: resolution: {integrity: sha512-rVksvsnNCdJ/ohGc6xgPwyN8eheCxsiLM8mxuE/t/mOVqJewPuO1miLpTHQiRgTKCLexL4MeAFVagts7HmNZ2Q==} engines: {node: '>=10'} - yoctocolors@2.1.2: - resolution: {integrity: sha512-CzhO+pFNo8ajLM2d2IW/R93ipy99LWjtwblvC1RsoSUMZgyLbYFr221TnSNT7GjGdYui6P459mw9JH/g/zW2ug==} + yoctocolors@2.2.0: + resolution: {integrity: sha512-xYqdZFUK/VYazNl/oCDYN+3WloWQwMfZxBoiNt6qNyk+xfOdi598muWE42rNZFp1kNOiqW936q5RhUdnpqElSg==} engines: {node: '>=18'} + yuku-ast@0.8.7: + resolution: {integrity: sha512-h6+4bDfyootiMB9vckk5uKo5r5j0GHrkr17FQTDNfEsFT3DWlN9uu1HJwQwc64pgmLCI945fWM3lbTIqxjT3GQ==} + + yuku-codegen@0.8.7: + resolution: {integrity: sha512-adwDZSh8oVDzhE6Du9PwVWxcOxeV0e2EVhUuMKWfhSY4wkrDq9eqixlxFF3l/XGUV1E7UFzhpz9393MUumkyNw==} + + yuku-parser@0.8.7: + resolution: {integrity: sha512-vRD9nwt4L3aYpxNqeSC4WqLv58xrXef0Ong1Mc45CTXTIpvLafx7JO05sczmQZwdLEZvywrLOGdNC5+Rp5N1BQ==} + zod-validation-error@4.0.2: resolution: {integrity: sha512-Q6/nZLe6jxuU80qb/4uJ4t5v2VEZ44lzQjPDhYJNztRQ4wyWc6VF3D3Kb/fAuPetZQnhS3hnajCf9CsWesghLQ==} engines: {node: '>=18.0.0'} peerDependencies: zod: ^3.25.0 || ^4.0.0 - zod@4.4.3: - resolution: {integrity: sha512-ytENFjIJFl2UwYglde2jchW2Hwm4GJFLDiSXWdTrJQBIN9Fcyp7n4DhxJEiWNAJMV1/BqWfW/kkg71UDcHJyTQ==} + zod@4.5.4: + resolution: {integrity: sha512-sC95tT5iHHH9gtpj6A81kh+NEaRAUFN+qlUPDUbRfOMvNf5QCBqsb3WgvnpVtK5Y+4UfA6KqufotuTvMGiTlsA==} snapshots: @@ -3965,30 +3629,20 @@ snapshots: '@actions/io@3.0.2': {} - '@ampproject/remapping@2.3.0': - dependencies: - '@jridgewell/gen-mapping': 0.3.13 - '@jridgewell/trace-mapping': 0.3.31 - - '@asamuzakjp/css-color@5.1.11': + '@asamuzakjp/css-color@6.0.7': dependencies: - '@asamuzakjp/generational-cache': 1.0.1 - '@csstools/css-calc': 3.2.1(@csstools/css-parser-algorithms@4.0.0(@csstools/css-tokenizer@4.0.0))(@csstools/css-tokenizer@4.0.0) - '@csstools/css-color-parser': 4.1.9(@csstools/css-parser-algorithms@4.0.0(@csstools/css-tokenizer@4.0.0))(@csstools/css-tokenizer@4.0.0) + '@csstools/css-calc': 3.3.0(@csstools/css-parser-algorithms@4.0.0(@csstools/css-tokenizer@4.0.0))(@csstools/css-tokenizer@4.0.0) + '@csstools/css-color-parser': 4.2.2(@csstools/css-parser-algorithms@4.0.0(@csstools/css-tokenizer@4.0.0))(@csstools/css-tokenizer@4.0.0) '@csstools/css-parser-algorithms': 4.0.0(@csstools/css-tokenizer@4.0.0) '@csstools/css-tokenizer': 4.0.0 + lru-cache: 11.5.2 - '@asamuzakjp/dom-selector@7.1.1': + '@asamuzakjp/dom-selector@8.3.2': dependencies: - '@asamuzakjp/generational-cache': 1.0.1 - '@asamuzakjp/nwsapi': 2.3.9 bidi-js: 1.0.3 css-tree: 3.2.1 is-potential-custom-element-name: 1.0.1 - - '@asamuzakjp/generational-cache@1.0.1': {} - - '@asamuzakjp/nwsapi@2.3.9': {} + lru-cache: 11.5.2 '@babel/code-frame@7.29.7': dependencies: @@ -3998,41 +3652,32 @@ snapshots: '@babel/compat-data@7.29.7': {} - '@babel/core@7.29.7': + '@babel/core@7.29.7(supports-color@7.2.0)': dependencies: '@babel/code-frame': 7.29.7 - '@babel/generator': 7.29.7 + '@babel/generator': 7.29.8 '@babel/helper-compilation-targets': 7.29.7 - '@babel/helper-module-transforms': 7.29.7(@babel/core@7.29.7) + '@babel/helper-module-transforms': 7.29.7(@babel/core@7.29.7(supports-color@7.2.0))(supports-color@7.2.0) '@babel/helpers': 7.29.7 - '@babel/parser': 7.29.7 + '@babel/parser': 7.29.8 '@babel/template': 7.29.7 - '@babel/traverse': 7.29.7 - '@babel/types': 7.29.7 + '@babel/traverse': 7.29.8(supports-color@7.2.0) + '@babel/types': 7.29.8 '@jridgewell/remapping': 2.3.5 convert-source-map: 2.0.0 - debug: 4.4.3 + debug: 4.4.3(supports-color@7.2.0) gensync: 1.0.0-beta.2 json5: 2.2.3 semver: 6.3.1 transitivePeerDependencies: - supports-color - '@babel/generator@7.29.7': - dependencies: - '@babel/parser': 7.29.7 - '@babel/types': 7.29.7 - '@jridgewell/gen-mapping': 0.3.13 - '@jridgewell/trace-mapping': 0.3.31 - jsesc: 3.1.0 - - '@babel/generator@8.0.0': + '@babel/generator@7.29.8': dependencies: - '@babel/parser': 8.0.0 - '@babel/types': 8.0.0 + '@babel/parser': 7.29.8 + '@babel/types': 7.29.8 '@jridgewell/gen-mapping': 0.3.13 '@jridgewell/trace-mapping': 0.3.31 - '@types/jsesc': 2.5.1 jsesc: 3.1.0 '@babel/helper-compilation-targets@7.29.7': @@ -4045,75 +3690,62 @@ snapshots: '@babel/helper-globals@7.29.7': {} - '@babel/helper-module-imports@7.29.7': + '@babel/helper-module-imports@7.29.7(supports-color@7.2.0)': dependencies: - '@babel/traverse': 7.29.7 - '@babel/types': 7.29.7 + '@babel/traverse': 7.29.8(supports-color@7.2.0) + '@babel/types': 7.29.8 transitivePeerDependencies: - supports-color - '@babel/helper-module-transforms@7.29.7(@babel/core@7.29.7)': + '@babel/helper-module-transforms@7.29.7(@babel/core@7.29.7(supports-color@7.2.0))(supports-color@7.2.0)': dependencies: - '@babel/core': 7.29.7 - '@babel/helper-module-imports': 7.29.7 + '@babel/core': 7.29.7(supports-color@7.2.0) + '@babel/helper-module-imports': 7.29.7(supports-color@7.2.0) '@babel/helper-validator-identifier': 7.29.7 - '@babel/traverse': 7.29.7 + '@babel/traverse': 7.29.8(supports-color@7.2.0) transitivePeerDependencies: - supports-color '@babel/helper-string-parser@7.29.7': {} - '@babel/helper-string-parser@8.0.0': {} - '@babel/helper-validator-identifier@7.29.7': {} - '@babel/helper-validator-identifier@8.0.2': {} - '@babel/helper-validator-option@7.29.7': {} '@babel/helpers@7.29.7': dependencies: '@babel/template': 7.29.7 - '@babel/types': 7.29.7 - - '@babel/parser@7.29.7': - dependencies: - '@babel/types': 7.29.7 + '@babel/types': 7.29.8 - '@babel/parser@8.0.0': + '@babel/parser@7.29.8': dependencies: - '@babel/types': 8.0.0 + '@babel/types': 7.29.8 '@babel/runtime@7.29.7': {} '@babel/template@7.29.7': dependencies: '@babel/code-frame': 7.29.7 - '@babel/parser': 7.29.7 - '@babel/types': 7.29.7 + '@babel/parser': 7.29.8 + '@babel/types': 7.29.8 - '@babel/traverse@7.29.7': + '@babel/traverse@7.29.8(supports-color@7.2.0)': dependencies: '@babel/code-frame': 7.29.7 - '@babel/generator': 7.29.7 + '@babel/generator': 7.29.8 '@babel/helper-globals': 7.29.7 - '@babel/parser': 7.29.7 + '@babel/parser': 7.29.8 '@babel/template': 7.29.7 - '@babel/types': 7.29.7 - debug: 4.4.3 + '@babel/types': 7.29.8 + debug: 4.4.3(supports-color@7.2.0) transitivePeerDependencies: - supports-color - '@babel/types@7.29.7': + '@babel/types@7.29.8': dependencies: '@babel/helper-string-parser': 7.29.7 '@babel/helper-validator-identifier': 7.29.7 - '@babel/types@8.0.0': - dependencies: - '@babel/helper-string-parser': 8.0.0 - '@babel/helper-validator-identifier': 8.0.2 - '@bcoe/v8-coverage@1.0.2': {} '@bramus/specificity@2.4.2': @@ -4123,17 +3755,17 @@ snapshots: '@colors/colors@1.5.0': optional: true - '@csstools/color-helpers@6.1.0': {} + '@csstools/color-helpers@6.1.1': {} - '@csstools/css-calc@3.2.1(@csstools/css-parser-algorithms@4.0.0(@csstools/css-tokenizer@4.0.0))(@csstools/css-tokenizer@4.0.0)': + '@csstools/css-calc@3.3.0(@csstools/css-parser-algorithms@4.0.0(@csstools/css-tokenizer@4.0.0))(@csstools/css-tokenizer@4.0.0)': dependencies: '@csstools/css-parser-algorithms': 4.0.0(@csstools/css-tokenizer@4.0.0) '@csstools/css-tokenizer': 4.0.0 - '@csstools/css-color-parser@4.1.9(@csstools/css-parser-algorithms@4.0.0(@csstools/css-tokenizer@4.0.0))(@csstools/css-tokenizer@4.0.0)': + '@csstools/css-color-parser@4.2.2(@csstools/css-parser-algorithms@4.0.0(@csstools/css-tokenizer@4.0.0))(@csstools/css-tokenizer@4.0.0)': dependencies: - '@csstools/color-helpers': 6.1.0 - '@csstools/css-calc': 3.2.1(@csstools/css-parser-algorithms@4.0.0(@csstools/css-tokenizer@4.0.0))(@csstools/css-tokenizer@4.0.0) + '@csstools/color-helpers': 6.1.1 + '@csstools/css-calc': 3.3.0(@csstools/css-parser-algorithms@4.0.0(@csstools/css-tokenizer@4.0.0))(@csstools/css-tokenizer@4.0.0) '@csstools/css-parser-algorithms': 4.0.0(@csstools/css-tokenizer@4.0.0) '@csstools/css-tokenizer': 4.0.0 @@ -4141,7 +3773,7 @@ snapshots: dependencies: '@csstools/css-tokenizer': 4.0.0 - '@csstools/css-syntax-patches-for-csstree@1.1.6(css-tree@3.2.1)': + '@csstools/css-syntax-patches-for-csstree@1.1.12(css-tree@3.2.1)': optionalDependencies: css-tree: 3.2.1 @@ -4153,121 +3785,27 @@ snapshots: tslib: 2.8.1 optional: true - '@emnapi/core@1.11.1': - dependencies: - '@emnapi/wasi-threads': 1.2.2 - tslib: 2.8.1 - optional: true - '@emnapi/runtime@1.10.0': dependencies: tslib: 2.8.1 optional: true - '@emnapi/runtime@1.11.1': - dependencies: - tslib: 2.8.1 - optional: true - '@emnapi/wasi-threads@1.2.1': dependencies: tslib: 2.8.1 optional: true - '@emnapi/wasi-threads@1.2.2': - dependencies: - tslib: 2.8.1 - optional: true - - '@esbuild/aix-ppc64@0.27.2': - optional: true - - '@esbuild/android-arm64@0.27.2': - optional: true - - '@esbuild/android-arm@0.27.2': - optional: true - - '@esbuild/android-x64@0.27.2': - optional: true - - '@esbuild/darwin-arm64@0.27.2': - optional: true - - '@esbuild/darwin-x64@0.27.2': - optional: true - - '@esbuild/freebsd-arm64@0.27.2': - optional: true - - '@esbuild/freebsd-x64@0.27.2': - optional: true - - '@esbuild/linux-arm64@0.27.2': - optional: true - - '@esbuild/linux-arm@0.27.2': - optional: true - - '@esbuild/linux-ia32@0.27.2': - optional: true - - '@esbuild/linux-loong64@0.27.2': - optional: true - - '@esbuild/linux-mips64el@0.27.2': - optional: true - - '@esbuild/linux-ppc64@0.27.2': - optional: true - - '@esbuild/linux-riscv64@0.27.2': - optional: true - - '@esbuild/linux-s390x@0.27.2': - optional: true - - '@esbuild/linux-x64@0.27.2': - optional: true - - '@esbuild/netbsd-arm64@0.27.2': - optional: true - - '@esbuild/netbsd-x64@0.27.2': - optional: true - - '@esbuild/openbsd-arm64@0.27.2': - optional: true - - '@esbuild/openbsd-x64@0.27.2': - optional: true - - '@esbuild/openharmony-arm64@0.27.2': - optional: true - - '@esbuild/sunos-x64@0.27.2': - optional: true - - '@esbuild/win32-arm64@0.27.2': - optional: true - - '@esbuild/win32-ia32@0.27.2': - optional: true - - '@esbuild/win32-x64@0.27.2': - optional: true - - '@eslint-community/eslint-utils@4.9.1(eslint@9.39.4)': + '@eslint-community/eslint-utils@4.10.1(eslint@9.39.5(supports-color@7.2.0))': dependencies: - eslint: 9.39.4 + eslint: 9.39.5(supports-color@7.2.0) eslint-visitor-keys: 3.4.3 '@eslint-community/regexpp@4.12.2': {} - '@eslint/config-array@0.21.2': + '@eslint/config-array@0.21.2(supports-color@7.2.0)': dependencies: '@eslint/object-schema': 2.1.7 - debug: 4.4.3 + debug: 4.4.3(supports-color@7.2.0) minimatch: 3.1.5 transitivePeerDependencies: - supports-color @@ -4280,10 +3818,10 @@ snapshots: dependencies: '@types/json-schema': 7.0.15 - '@eslint/eslintrc@3.3.5': + '@eslint/eslintrc@3.3.7(supports-color@7.2.0)': dependencies: ajv: 6.15.0 - debug: 4.4.3 + debug: 4.4.3(supports-color@7.2.0) espree: 10.4.0 globals: 14.0.0 ignore: 5.3.2 @@ -4294,7 +3832,7 @@ snapshots: transitivePeerDependencies: - supports-color - '@eslint/js@9.39.4': {} + '@eslint/js@9.39.5': {} '@eslint/object-schema@2.1.7': {} @@ -4321,20 +3859,9 @@ snapshots: '@humanwhocodes/retry@0.4.3': {} - '@isaacs/cliui@8.0.2': - dependencies: - string-width: 5.1.2 - string-width-cjs: string-width@4.2.3 - strip-ansi: 7.2.0 - strip-ansi-cjs: strip-ansi@6.0.1 - wrap-ansi: 8.1.0 - wrap-ansi-cjs: wrap-ansi@7.0.0 - - '@istanbuljs/schema@0.1.6': {} - '@jridgewell/gen-mapping@0.3.13': dependencies: - '@jridgewell/sourcemap-codec': 1.5.5 + '@jridgewell/sourcemap-codec': 1.6.0 '@jridgewell/trace-mapping': 0.3.31 '@jridgewell/remapping@2.3.5': @@ -4344,350 +3871,215 @@ snapshots: '@jridgewell/resolve-uri@3.1.2': {} - '@jridgewell/sourcemap-codec@1.5.5': {} + '@jridgewell/sourcemap-codec@1.6.0': {} '@jridgewell/trace-mapping@0.3.31': dependencies: '@jridgewell/resolve-uri': 3.1.2 - '@jridgewell/sourcemap-codec': 1.5.5 + '@jridgewell/sourcemap-codec': 1.6.0 - '@napi-rs/wasm-runtime@1.1.6(@emnapi/core@1.10.0)(@emnapi/runtime@1.10.0)': + '@napi-rs/wasm-runtime@1.2.3(@emnapi/core@1.10.0)(@emnapi/runtime@1.10.0)': dependencies: '@emnapi/core': 1.10.0 '@emnapi/runtime': 1.10.0 '@tybys/wasm-util': 0.10.3 optional: true - '@napi-rs/wasm-runtime@1.1.6(@emnapi/core@1.11.1)(@emnapi/runtime@1.11.1)': - dependencies: - '@emnapi/core': 1.11.1 - '@emnapi/runtime': 1.11.1 - '@tybys/wasm-util': 0.10.3 - optional: true - '@octokit/auth-token@6.0.0': {} - '@octokit/core@7.0.6': + '@octokit/core@7.0.8': dependencies: '@octokit/auth-token': 6.0.0 - '@octokit/graphql': 9.0.3 - '@octokit/request': 10.0.10 - '@octokit/request-error': 7.1.0 - '@octokit/types': 16.0.0 + '@octokit/graphql': 9.0.5 + '@octokit/request': 10.0.16 + '@octokit/request-error': 7.1.2 + '@octokit/types': 18.0.0 before-after-hook: 4.0.0 universal-user-agent: 7.0.3 - '@octokit/endpoint@11.0.3': + '@octokit/endpoint@11.0.5': dependencies: - '@octokit/types': 16.0.0 + '@octokit/types': 18.0.0 universal-user-agent: 7.0.3 - '@octokit/graphql@9.0.3': + '@octokit/graphql@9.0.5': dependencies: - '@octokit/request': 10.0.10 - '@octokit/types': 16.0.0 + '@octokit/request': 10.0.16 + '@octokit/types': 18.0.0 universal-user-agent: 7.0.3 '@octokit/openapi-types@27.0.0': {} - '@octokit/plugin-paginate-rest@14.0.0(@octokit/core@7.0.6)': - dependencies: - '@octokit/core': 7.0.6 - '@octokit/types': 16.0.0 - - '@octokit/plugin-retry@8.1.0(@octokit/core@7.0.6)': - dependencies: - '@octokit/core': 7.0.6 - '@octokit/request-error': 7.1.0 - '@octokit/types': 16.0.0 - bottleneck: 2.19.5 - - '@octokit/plugin-throttling@11.0.3(@octokit/core@7.0.6)': - dependencies: - '@octokit/core': 7.0.6 - '@octokit/types': 16.0.0 - bottleneck: 2.19.5 - - '@octokit/request-error@7.1.0': - dependencies: - '@octokit/types': 16.0.0 - - '@octokit/request@10.0.10': - dependencies: - '@octokit/endpoint': 11.0.3 - '@octokit/request-error': 7.1.0 - '@octokit/types': 16.0.0 - content-type: 2.0.0 - json-with-bigint: 3.5.8 - universal-user-agent: 7.0.3 - - '@octokit/types@16.0.0': - dependencies: - '@octokit/openapi-types': 27.0.0 - - '@oxc-project/types@0.127.0': - optional: true - - '@oxc-project/types@0.137.0': {} - - '@pkgjs/parseargs@0.11.0': - optional: true - - '@pnpm/config.env-replace@1.1.0': {} - - '@pnpm/network.ca-file@1.0.2': - dependencies: - graceful-fs: 4.2.10 - - '@pnpm/npm-conf@3.0.3': - dependencies: - '@pnpm/config.env-replace': 1.1.0 - '@pnpm/network.ca-file': 1.0.2 - config-chain: 1.1.13 - - '@quansync/fs@1.0.0': - dependencies: - quansync: 1.0.0 - - '@rolldown/binding-android-arm64@1.0.0-rc.17': - optional: true - - '@rolldown/binding-android-arm64@1.1.3': - optional: true - - '@rolldown/binding-darwin-arm64@1.0.0-rc.17': - optional: true - - '@rolldown/binding-darwin-arm64@1.1.3': - optional: true - - '@rolldown/binding-darwin-x64@1.0.0-rc.17': - optional: true - - '@rolldown/binding-darwin-x64@1.1.3': - optional: true - - '@rolldown/binding-freebsd-x64@1.0.0-rc.17': - optional: true - - '@rolldown/binding-freebsd-x64@1.1.3': - optional: true - - '@rolldown/binding-linux-arm-gnueabihf@1.0.0-rc.17': - optional: true - - '@rolldown/binding-linux-arm-gnueabihf@1.1.3': - optional: true - - '@rolldown/binding-linux-arm64-gnu@1.0.0-rc.17': - optional: true - - '@rolldown/binding-linux-arm64-gnu@1.1.3': - optional: true - - '@rolldown/binding-linux-arm64-musl@1.0.0-rc.17': - optional: true - - '@rolldown/binding-linux-arm64-musl@1.1.3': - optional: true - - '@rolldown/binding-linux-ppc64-gnu@1.0.0-rc.17': - optional: true - - '@rolldown/binding-linux-ppc64-gnu@1.1.3': - optional: true - - '@rolldown/binding-linux-s390x-gnu@1.0.0-rc.17': - optional: true - - '@rolldown/binding-linux-s390x-gnu@1.1.3': - optional: true - - '@rolldown/binding-linux-x64-gnu@1.0.0-rc.17': - optional: true - - '@rolldown/binding-linux-x64-gnu@1.1.3': - optional: true - - '@rolldown/binding-linux-x64-musl@1.0.0-rc.17': - optional: true - - '@rolldown/binding-linux-x64-musl@1.1.3': - optional: true - - '@rolldown/binding-openharmony-arm64@1.0.0-rc.17': - optional: true - - '@rolldown/binding-openharmony-arm64@1.1.3': - optional: true + '@octokit/openapi-types@28.0.0': {} - '@rolldown/binding-wasm32-wasi@1.0.0-rc.17': - dependencies: - '@emnapi/core': 1.10.0 - '@emnapi/runtime': 1.10.0 - '@napi-rs/wasm-runtime': 1.1.6(@emnapi/core@1.10.0)(@emnapi/runtime@1.10.0) - optional: true + '@octokit/openapi-types@29.0.1': {} - '@rolldown/binding-wasm32-wasi@1.1.3': + '@octokit/plugin-paginate-rest@14.0.0(@octokit/core@7.0.8)': dependencies: - '@emnapi/core': 1.11.1 - '@emnapi/runtime': 1.11.1 - '@napi-rs/wasm-runtime': 1.1.6(@emnapi/core@1.11.1)(@emnapi/runtime@1.11.1) - optional: true - - '@rolldown/binding-win32-arm64-msvc@1.0.0-rc.17': - optional: true - - '@rolldown/binding-win32-arm64-msvc@1.1.3': - optional: true - - '@rolldown/binding-win32-x64-msvc@1.0.0-rc.17': - optional: true + '@octokit/core': 7.0.8 + '@octokit/types': 16.0.0 - '@rolldown/binding-win32-x64-msvc@1.1.3': - optional: true + '@octokit/plugin-retry@8.1.1(@octokit/core@7.0.8)': + dependencies: + '@octokit/core': 7.0.8 + '@octokit/request-error': 7.1.2 + '@octokit/types': 17.0.0 + bottleneck: 2.19.5 - '@rolldown/pluginutils@1.0.0-rc.17': - optional: true + '@octokit/plugin-throttling@11.0.5(@octokit/core@7.0.8)': + dependencies: + '@octokit/core': 7.0.8 + '@octokit/types': 17.0.0 + bottleneck: 2.19.5 - '@rolldown/pluginutils@1.0.1': {} + '@octokit/request-error@7.1.2': + dependencies: + '@octokit/types': 18.0.0 - '@rollup/rollup-android-arm-eabi@4.62.2': - optional: true + '@octokit/request@10.0.16': + dependencies: + '@octokit/endpoint': 11.0.5 + '@octokit/request-error': 7.1.2 + '@octokit/types': 18.0.0 + content-type: 3.0.0 + json-with-bigint: 3.5.12 + universal-user-agent: 7.0.3 - '@rollup/rollup-android-arm64@4.62.2': - optional: true + '@octokit/types@16.0.0': + dependencies: + '@octokit/openapi-types': 27.0.0 - '@rollup/rollup-darwin-arm64@4.62.2': - optional: true + '@octokit/types@17.0.0': + dependencies: + '@octokit/openapi-types': 28.0.0 - '@rollup/rollup-darwin-x64@4.62.2': - optional: true + '@octokit/types@18.0.0': + dependencies: + '@octokit/openapi-types': 29.0.1 - '@rollup/rollup-freebsd-arm64@4.62.2': - optional: true + '@oxc-project/types@0.148.0': {} - '@rollup/rollup-freebsd-x64@4.62.2': - optional: true + '@pnpm/config.env-replace@1.1.0': {} - '@rollup/rollup-linux-arm-gnueabihf@4.62.2': - optional: true + '@pnpm/network.ca-file@1.0.2': + dependencies: + graceful-fs: 4.2.10 - '@rollup/rollup-linux-arm-musleabihf@4.62.2': - optional: true + '@pnpm/npm-conf@3.0.3': + dependencies: + '@pnpm/config.env-replace': 1.1.0 + '@pnpm/network.ca-file': 1.0.2 + config-chain: 1.1.13 - '@rollup/rollup-linux-arm64-gnu@4.62.2': - optional: true + '@quansync/fs@1.0.0': + dependencies: + quansync: 1.0.0 - '@rollup/rollup-linux-arm64-musl@4.62.2': + '@rolldown/binding-android-arm-eabi@1.2.7': optional: true - '@rollup/rollup-linux-loong64-gnu@4.62.2': + '@rolldown/binding-android-arm64@1.2.7': optional: true - '@rollup/rollup-linux-loong64-musl@4.62.2': + '@rolldown/binding-darwin-arm64@1.2.7': optional: true - '@rollup/rollup-linux-ppc64-gnu@4.62.2': + '@rolldown/binding-darwin-x64@1.2.7': optional: true - '@rollup/rollup-linux-ppc64-musl@4.62.2': + '@rolldown/binding-freebsd-x64@1.2.7': optional: true - '@rollup/rollup-linux-riscv64-gnu@4.62.2': + '@rolldown/binding-linux-arm-gnueabihf@1.2.7': optional: true - '@rollup/rollup-linux-riscv64-musl@4.62.2': + '@rolldown/binding-linux-arm64-gnu@1.2.7': optional: true - '@rollup/rollup-linux-s390x-gnu@4.62.2': + '@rolldown/binding-linux-arm64-musl@1.2.7': optional: true - '@rollup/rollup-linux-x64-gnu@4.62.2': + '@rolldown/binding-linux-ppc64-gnu@1.2.7': optional: true - '@rollup/rollup-linux-x64-musl@4.62.2': + '@rolldown/binding-linux-s390x-gnu@1.2.7': optional: true - '@rollup/rollup-openbsd-x64@4.62.2': + '@rolldown/binding-linux-x64-gnu@1.2.7': optional: true - '@rollup/rollup-openharmony-arm64@4.62.2': + '@rolldown/binding-linux-x64-musl@1.2.7': optional: true - '@rollup/rollup-win32-arm64-msvc@4.62.2': + '@rolldown/binding-openharmony-arm64@1.2.7': optional: true - '@rollup/rollup-win32-ia32-msvc@4.62.2': + '@rolldown/binding-win32-arm64-msvc@1.2.7': optional: true - '@rollup/rollup-win32-x64-gnu@4.62.2': + '@rolldown/binding-win32-x64-msvc@1.2.7': optional: true - '@rollup/rollup-win32-x64-msvc@4.62.2': - optional: true + '@rolldown/pluginutils@1.0.1': {} '@rtsao/scc@1.1.0': {} '@sec-ant/readable-stream@0.4.1': {} - '@semantic-release/changelog@6.0.3(semantic-release@25.0.5(typescript@6.0.3))': + '@semantic-release/changelog@7.0.0(semantic-release@25.0.9(supports-color@7.2.0)(typescript@6.0.3))': dependencies: - '@semantic-release/error': 3.0.0 - aggregate-error: 3.1.0 - fs-extra: 11.3.5 - lodash: 4.18.1 - semantic-release: 25.0.5(typescript@6.0.3) + '@semantic-release/error': 4.0.0 + aggregate-error: 5.0.0 + lodash-es: 4.18.1 + semantic-release: 25.0.9(supports-color@7.2.0)(typescript@6.0.3) - '@semantic-release/commit-analyzer@13.0.1(semantic-release@25.0.5(typescript@6.0.3))': + '@semantic-release/commit-analyzer@13.0.1(semantic-release@25.0.9(supports-color@7.2.0)(typescript@6.0.3))(supports-color@7.2.0)': dependencies: conventional-changelog-angular: 8.3.1 conventional-changelog-writer: 8.4.0 conventional-commits-filter: 5.0.0 conventional-commits-parser: 6.4.0 - debug: 4.4.3 - import-from-esm: 2.0.0 + debug: 4.4.3(supports-color@7.2.0) + import-from-esm: 2.0.0(supports-color@7.2.0) lodash-es: 4.18.1 micromatch: 4.0.8 - semantic-release: 25.0.5(typescript@6.0.3) + semantic-release: 25.0.9(supports-color@7.2.0)(typescript@6.0.3) transitivePeerDependencies: - supports-color - '@semantic-release/error@3.0.0': {} - '@semantic-release/error@4.0.0': {} - '@semantic-release/git@10.0.1(semantic-release@25.0.5(typescript@6.0.3))': + '@semantic-release/git@11.0.1(semantic-release@25.0.9(supports-color@7.2.0)(typescript@6.0.3))(supports-color@7.2.0)': dependencies: - '@semantic-release/error': 3.0.0 - aggregate-error: 3.1.0 - debug: 4.4.3 + '@semantic-release/error': 4.0.0 + aggregate-error: 5.0.0 + debug: 4.4.3(supports-color@7.2.0) dir-glob: 3.0.1 - execa: 5.1.1 - lodash: 4.18.1 + execa: 10.0.1 + lodash-es: 4.18.1 micromatch: 4.0.8 - p-reduce: 2.1.0 - semantic-release: 25.0.5(typescript@6.0.3) + p-reduce: 3.0.0 + semantic-release: 25.0.9(supports-color@7.2.0)(typescript@6.0.3) transitivePeerDependencies: - supports-color - '@semantic-release/github@12.0.8(semantic-release@25.0.5(typescript@6.0.3))': + '@semantic-release/github@12.0.9(semantic-release@25.0.9(supports-color@7.2.0)(typescript@6.0.3))(supports-color@7.2.0)': dependencies: - '@octokit/core': 7.0.6 - '@octokit/plugin-paginate-rest': 14.0.0(@octokit/core@7.0.6) - '@octokit/plugin-retry': 8.1.0(@octokit/core@7.0.6) - '@octokit/plugin-throttling': 11.0.3(@octokit/core@7.0.6) + '@octokit/core': 7.0.8 + '@octokit/plugin-paginate-rest': 14.0.0(@octokit/core@7.0.8) + '@octokit/plugin-retry': 8.1.1(@octokit/core@7.0.8) + '@octokit/plugin-throttling': 11.0.5(@octokit/core@7.0.8) '@semantic-release/error': 4.0.0 aggregate-error: 5.0.0 - debug: 4.4.3 + debug: 4.4.3(supports-color@7.2.0) dir-glob: 3.0.1 - http-proxy-agent: 9.1.0 - https-proxy-agent: 9.1.0 + http-proxy-agent: 9.1.0(supports-color@7.2.0) + https-proxy-agent: 9.1.0(supports-color@7.2.0) issue-parser: 7.0.2 lodash-es: 4.18.1 mime: 4.1.0 p-filter: 4.1.0 - semantic-release: 25.0.5(typescript@6.0.3) + semantic-release: 25.0.9(supports-color@7.2.0)(typescript@6.0.3) tinyglobby: 0.2.17 undici: 7.29.0 url-join: 5.0.0 @@ -4695,36 +4087,36 @@ snapshots: - kerberos - supports-color - '@semantic-release/npm@13.1.5(semantic-release@25.0.5(typescript@6.0.3))': + '@semantic-release/npm@13.1.5(semantic-release@25.0.9(supports-color@7.2.0)(typescript@6.0.3))': dependencies: '@actions/core': 3.0.1 '@semantic-release/error': 4.0.0 aggregate-error: 5.0.0 env-ci: 11.2.0 execa: 9.6.1 - fs-extra: 11.3.5 + fs-extra: 11.4.0 lodash-es: 4.18.1 nerf-dart: 1.0.0 normalize-url: 9.0.1 - npm: 11.17.0 + npm: 11.19.1 rc: 1.2.8 read-pkg: 10.1.0 registry-auth-token: 5.1.1 - semantic-release: 25.0.5(typescript@6.0.3) + semantic-release: 25.0.9(supports-color@7.2.0)(typescript@6.0.3) semver: 7.8.5 tempy: 3.2.0 - '@semantic-release/release-notes-generator@14.1.1(semantic-release@25.0.5(typescript@6.0.3))': + '@semantic-release/release-notes-generator@14.1.1(semantic-release@25.0.9(supports-color@7.2.0)(typescript@6.0.3))(supports-color@7.2.0)': dependencies: conventional-changelog-angular: 8.3.1 conventional-changelog-writer: 8.4.0 conventional-commits-filter: 5.0.0 conventional-commits-parser: 6.4.0 - debug: 4.4.3 - import-from-esm: 2.0.0 + debug: 4.4.3(supports-color@7.2.0) + import-from-esm: 2.0.0(supports-color@7.2.0) lodash-es: 4.18.1 read-package-up: 11.0.0 - semantic-release: 25.0.5(typescript@6.0.3) + semantic-release: 25.0.9(supports-color@7.2.0)(typescript@6.0.3) transitivePeerDependencies: - supports-color @@ -4734,6 +4126,8 @@ snapshots: '@sindresorhus/merge-streams@4.0.0': {} + '@standard-schema/spec@1.1.0': {} + '@testing-library/dom@10.4.1': dependencies: '@babel/code-frame': 7.29.7 @@ -4745,7 +4139,7 @@ snapshots: picocolors: 1.1.1 pretty-format: 27.5.1 - '@testing-library/react@16.3.2(@testing-library/dom@10.4.1)(@types/react-dom@18.3.7(@types/react@18.3.31))(@types/react@18.3.31)(react-dom@18.3.1(react@18.3.1))(react@18.3.1)': + '@testing-library/react@16.3.3(@testing-library/dom@10.4.1)(@types/react-dom@18.3.7(@types/react@18.3.31))(@types/react@18.3.31)(react-dom@18.3.1(react@18.3.1))(react@18.3.1)': dependencies: '@babel/runtime': 7.29.7 '@testing-library/dom': 10.4.1 @@ -4755,7 +4149,7 @@ snapshots: '@types/react': 18.3.31 '@types/react-dom': 18.3.7(@types/react@18.3.31) - '@testing-library/user-event@14.6.1(@testing-library/dom@10.4.1)': + '@testing-library/user-event@14.6.7(@testing-library/dom@10.4.1)': dependencies: '@testing-library/dom': 10.4.1 @@ -4775,15 +4169,13 @@ snapshots: '@types/estree@1.0.9': {} - '@types/jsesc@2.5.1': {} - '@types/json-schema@7.0.15': {} '@types/json5@0.0.29': {} - '@types/node@24.0.0': + '@types/node@26.4.1': dependencies: - undici-types: 7.8.0 + undici-types: 8.3.0 '@types/normalize-package-data@2.4.4': {} @@ -4798,74 +4190,74 @@ snapshots: '@types/prop-types': 15.7.15 csstype: 3.2.3 - '@typescript-eslint/eslint-plugin@8.62.0(@typescript-eslint/parser@8.62.0(eslint@9.39.4)(typescript@6.0.3))(eslint@9.39.4)(typescript@6.0.3)': + '@typescript-eslint/eslint-plugin@8.69.0(@typescript-eslint/parser@8.69.0(eslint@9.39.5(supports-color@7.2.0))(supports-color@7.2.0)(typescript@6.0.3))(eslint@9.39.5(supports-color@7.2.0))(supports-color@7.2.0)(typescript@6.0.3)': dependencies: '@eslint-community/regexpp': 4.12.2 - '@typescript-eslint/parser': 8.62.0(eslint@9.39.4)(typescript@6.0.3) - '@typescript-eslint/scope-manager': 8.62.0 - '@typescript-eslint/type-utils': 8.62.0(eslint@9.39.4)(typescript@6.0.3) - '@typescript-eslint/utils': 8.62.0(eslint@9.39.4)(typescript@6.0.3) - '@typescript-eslint/visitor-keys': 8.62.0 - eslint: 9.39.4 - ignore: 7.0.5 + '@typescript-eslint/parser': 8.69.0(eslint@9.39.5(supports-color@7.2.0))(supports-color@7.2.0)(typescript@6.0.3) + '@typescript-eslint/scope-manager': 8.69.0 + '@typescript-eslint/type-utils': 8.69.0(eslint@9.39.5(supports-color@7.2.0))(supports-color@7.2.0)(typescript@6.0.3) + '@typescript-eslint/utils': 8.69.0(eslint@9.39.5(supports-color@7.2.0))(supports-color@7.2.0)(typescript@6.0.3) + '@typescript-eslint/visitor-keys': 8.69.0 + eslint: 9.39.5(supports-color@7.2.0) + ignore: 7.0.8 natural-compare: 1.4.0 ts-api-utils: 2.5.0(typescript@6.0.3) typescript: 6.0.3 transitivePeerDependencies: - supports-color - '@typescript-eslint/parser@8.62.0(eslint@9.39.4)(typescript@6.0.3)': + '@typescript-eslint/parser@8.69.0(eslint@9.39.5(supports-color@7.2.0))(supports-color@7.2.0)(typescript@6.0.3)': dependencies: - '@typescript-eslint/scope-manager': 8.62.0 - '@typescript-eslint/types': 8.62.0 - '@typescript-eslint/typescript-estree': 8.62.0(typescript@6.0.3) - '@typescript-eslint/visitor-keys': 8.62.0 - debug: 4.4.3 - eslint: 9.39.4 + '@typescript-eslint/scope-manager': 8.69.0 + '@typescript-eslint/types': 8.69.0 + '@typescript-eslint/typescript-estree': 8.69.0(supports-color@7.2.0)(typescript@6.0.3) + '@typescript-eslint/visitor-keys': 8.69.0 + debug: 4.4.3(supports-color@7.2.0) + eslint: 9.39.5(supports-color@7.2.0) typescript: 6.0.3 transitivePeerDependencies: - supports-color - '@typescript-eslint/project-service@8.62.0(typescript@6.0.3)': + '@typescript-eslint/project-service@8.69.0(supports-color@7.2.0)(typescript@6.0.3)': dependencies: - '@typescript-eslint/tsconfig-utils': 8.62.0(typescript@6.0.3) - '@typescript-eslint/types': 8.62.0 - debug: 4.4.3 + '@typescript-eslint/tsconfig-utils': 8.69.0(typescript@6.0.3) + '@typescript-eslint/types': 8.69.0 + debug: 4.4.3(supports-color@7.2.0) typescript: 6.0.3 transitivePeerDependencies: - supports-color - '@typescript-eslint/scope-manager@8.62.0': + '@typescript-eslint/scope-manager@8.69.0': dependencies: - '@typescript-eslint/types': 8.62.0 - '@typescript-eslint/visitor-keys': 8.62.0 + '@typescript-eslint/types': 8.69.0 + '@typescript-eslint/visitor-keys': 8.69.0 - '@typescript-eslint/tsconfig-utils@8.62.0(typescript@6.0.3)': + '@typescript-eslint/tsconfig-utils@8.69.0(typescript@6.0.3)': dependencies: typescript: 6.0.3 - '@typescript-eslint/type-utils@8.62.0(eslint@9.39.4)(typescript@6.0.3)': + '@typescript-eslint/type-utils@8.69.0(eslint@9.39.5(supports-color@7.2.0))(supports-color@7.2.0)(typescript@6.0.3)': dependencies: - '@typescript-eslint/types': 8.62.0 - '@typescript-eslint/typescript-estree': 8.62.0(typescript@6.0.3) - '@typescript-eslint/utils': 8.62.0(eslint@9.39.4)(typescript@6.0.3) - debug: 4.4.3 - eslint: 9.39.4 + '@typescript-eslint/types': 8.69.0 + '@typescript-eslint/typescript-estree': 8.69.0(supports-color@7.2.0)(typescript@6.0.3) + '@typescript-eslint/utils': 8.69.0(eslint@9.39.5(supports-color@7.2.0))(supports-color@7.2.0)(typescript@6.0.3) + debug: 4.4.3(supports-color@7.2.0) + eslint: 9.39.5(supports-color@7.2.0) ts-api-utils: 2.5.0(typescript@6.0.3) typescript: 6.0.3 transitivePeerDependencies: - supports-color - '@typescript-eslint/types@8.62.0': {} + '@typescript-eslint/types@8.69.0': {} - '@typescript-eslint/typescript-estree@8.62.0(typescript@6.0.3)': + '@typescript-eslint/typescript-estree@8.69.0(supports-color@7.2.0)(typescript@6.0.3)': dependencies: - '@typescript-eslint/project-service': 8.62.0(typescript@6.0.3) - '@typescript-eslint/tsconfig-utils': 8.62.0(typescript@6.0.3) - '@typescript-eslint/types': 8.62.0 - '@typescript-eslint/visitor-keys': 8.62.0 - debug: 4.4.3 - minimatch: 10.2.5 + '@typescript-eslint/project-service': 8.69.0(supports-color@7.2.0)(typescript@6.0.3) + '@typescript-eslint/tsconfig-utils': 8.69.0(typescript@6.0.3) + '@typescript-eslint/types': 8.69.0 + '@typescript-eslint/visitor-keys': 8.69.0 + debug: 4.4.3(supports-color@7.2.0) + minimatch: 10.2.6 semver: 7.8.5 tinyglobby: 0.2.17 ts-api-utils: 2.5.0(typescript@6.0.3) @@ -4873,20 +4265,20 @@ snapshots: transitivePeerDependencies: - supports-color - '@typescript-eslint/utils@8.62.0(eslint@9.39.4)(typescript@6.0.3)': + '@typescript-eslint/utils@8.69.0(eslint@9.39.5(supports-color@7.2.0))(supports-color@7.2.0)(typescript@6.0.3)': dependencies: - '@eslint-community/eslint-utils': 4.9.1(eslint@9.39.4) - '@typescript-eslint/scope-manager': 8.62.0 - '@typescript-eslint/types': 8.62.0 - '@typescript-eslint/typescript-estree': 8.62.0(typescript@6.0.3) - eslint: 9.39.4 + '@eslint-community/eslint-utils': 4.10.1(eslint@9.39.5(supports-color@7.2.0)) + '@typescript-eslint/scope-manager': 8.69.0 + '@typescript-eslint/types': 8.69.0 + '@typescript-eslint/typescript-estree': 8.69.0(supports-color@7.2.0)(typescript@6.0.3) + eslint: 9.39.5(supports-color@7.2.0) typescript: 6.0.3 transitivePeerDependencies: - supports-color - '@typescript-eslint/visitor-keys@8.62.0': + '@typescript-eslint/visitor-keys@8.69.0': dependencies: - '@typescript-eslint/types': 8.62.0 + '@typescript-eslint/types': 8.69.0 eslint-visitor-keys: 5.0.1 '@unrs/resolver-binding-android-arm-eabi@1.12.2': @@ -4947,7 +4339,7 @@ snapshots: dependencies: '@emnapi/core': 1.10.0 '@emnapi/runtime': 1.10.0 - '@napi-rs/wasm-runtime': 1.1.6(@emnapi/core@1.10.0)(@emnapi/runtime@1.10.0) + '@napi-rs/wasm-runtime': 1.2.3(@emnapi/core@1.10.0)(@emnapi/runtime@1.10.0) optional: true '@unrs/resolver-binding-win32-arm64-msvc@1.12.2': @@ -4959,79 +4351,142 @@ snapshots: '@unrs/resolver-binding-win32-x64-msvc@1.12.2': optional: true - '@vitest/coverage-v8@3.2.6(vitest@3.2.6(@types/node@24.0.0)(jsdom@29.1.1))': + '@vitest/coverage-v8@4.1.11(vitest@4.1.11)': dependencies: - '@ampproject/remapping': 2.3.0 '@bcoe/v8-coverage': 1.0.2 - ast-v8-to-istanbul: 0.3.12 - debug: 4.4.3 + '@vitest/utils': 4.1.11 + ast-v8-to-istanbul: 1.0.5 istanbul-lib-coverage: 3.2.2 istanbul-lib-report: 3.0.1 - istanbul-lib-source-maps: 5.0.6 istanbul-reports: 3.2.0 - magic-string: 0.30.21 - magicast: 0.3.5 - std-env: 3.10.0 - test-exclude: 7.0.2 - tinyrainbow: 2.0.0 - vitest: 3.2.6(@types/node@24.0.0)(jsdom@29.1.1) - transitivePeerDependencies: - - supports-color + magicast: 0.5.4 + obug: 2.1.4 + std-env: 4.2.0 + tinyrainbow: 3.1.1 + vitest: 4.1.11(@types/node@26.4.1)(@vitest/coverage-v8@4.1.11)(jsdom@30.0.1)(vite@8.2.2(@types/node@26.4.1)) - '@vitest/expect@3.2.6': + '@vitest/expect@4.1.11': dependencies: + '@standard-schema/spec': 1.1.0 '@types/chai': 5.2.3 - '@vitest/spy': 3.2.6 - '@vitest/utils': 3.2.6 - chai: 5.3.3 - tinyrainbow: 2.0.0 + '@vitest/spy': 4.1.11 + '@vitest/utils': 4.1.11 + chai: 6.2.2 + tinyrainbow: 3.1.1 - '@vitest/mocker@3.2.6(vite@7.3.5(@types/node@24.0.0))': + '@vitest/mocker@4.1.11(vite@8.2.2(@types/node@26.4.1))': dependencies: - '@vitest/spy': 3.2.6 + '@vitest/spy': 4.1.11 estree-walker: 3.0.3 magic-string: 0.30.21 optionalDependencies: - vite: 7.3.5(@types/node@24.0.0) + vite: 8.2.2(@types/node@26.4.1) - '@vitest/pretty-format@3.2.6': + '@vitest/pretty-format@4.1.11': dependencies: - tinyrainbow: 2.0.0 + tinyrainbow: 3.1.1 - '@vitest/runner@3.2.6': + '@vitest/runner@4.1.11': dependencies: - '@vitest/utils': 3.2.6 + '@vitest/utils': 4.1.11 pathe: 2.0.3 - strip-literal: 3.1.0 - '@vitest/snapshot@3.2.6': + '@vitest/snapshot@4.1.11': dependencies: - '@vitest/pretty-format': 3.2.6 + '@vitest/pretty-format': 4.1.11 + '@vitest/utils': 4.1.11 magic-string: 0.30.21 pathe: 2.0.3 - '@vitest/spy@3.2.6': - dependencies: - tinyspy: 4.0.4 + '@vitest/spy@4.1.11': {} - '@vitest/utils@3.2.6': + '@vitest/utils@4.1.11': dependencies: - '@vitest/pretty-format': 3.2.6 - loupe: 3.2.1 - tinyrainbow: 2.0.0 + '@vitest/pretty-format': 4.1.11 + convert-source-map: 2.0.0 + tinyrainbow: 3.1.1 - acorn-jsx@5.3.2(acorn@8.17.0): - dependencies: - acorn: 8.17.0 + '@yuku-codegen/binding-android-arm64@0.8.7': + optional: true - acorn@8.17.0: {} + '@yuku-codegen/binding-darwin-arm64@0.8.7': + optional: true - agent-base@9.0.0: {} + '@yuku-codegen/binding-darwin-x64@0.8.7': + optional: true + + '@yuku-codegen/binding-freebsd-x64@0.8.7': + optional: true + + '@yuku-codegen/binding-linux-arm-gnu@0.8.7': + optional: true + + '@yuku-codegen/binding-linux-arm-musl@0.8.7': + optional: true + + '@yuku-codegen/binding-linux-arm64-gnu@0.8.7': + optional: true + + '@yuku-codegen/binding-linux-arm64-musl@0.8.7': + optional: true + + '@yuku-codegen/binding-linux-x64-gnu@0.8.7': + optional: true + + '@yuku-codegen/binding-linux-x64-musl@0.8.7': + optional: true + + '@yuku-codegen/binding-win32-arm64@0.8.7': + optional: true + + '@yuku-codegen/binding-win32-x64@0.8.7': + optional: true + + '@yuku-parser/binding-android-arm64@0.8.7': + optional: true + + '@yuku-parser/binding-darwin-arm64@0.8.7': + optional: true + + '@yuku-parser/binding-darwin-x64@0.8.7': + optional: true + + '@yuku-parser/binding-freebsd-x64@0.8.7': + optional: true + + '@yuku-parser/binding-linux-arm-gnu@0.8.7': + optional: true + + '@yuku-parser/binding-linux-arm-musl@0.8.7': + optional: true + + '@yuku-parser/binding-linux-arm64-gnu@0.8.7': + optional: true + + '@yuku-parser/binding-linux-arm64-musl@0.8.7': + optional: true + + '@yuku-parser/binding-linux-x64-gnu@0.8.7': + optional: true + + '@yuku-parser/binding-linux-x64-musl@0.8.7': + optional: true + + '@yuku-parser/binding-win32-arm64@0.8.7': + optional: true + + '@yuku-parser/binding-win32-x64@0.8.7': + optional: true + + '@yuku-toolchain/types@0.8.7': {} - aggregate-error@3.1.0: + acorn-jsx@5.3.2(acorn@8.18.0): dependencies: - clean-stack: 2.2.0 - indent-string: 4.0.0 + acorn: 8.18.0 + + acorn@8.18.0: {} + + agent-base@9.0.0: {} aggregate-error@5.0.0: dependencies: @@ -5051,7 +4506,7 @@ snapshots: ansi-regex@5.0.1: {} - ansi-regex@6.2.2: {} + ansi-regex@6.3.0: {} ansi-styles@3.2.1: dependencies: @@ -5150,15 +4605,9 @@ snapshots: assertion-error@2.0.1: {} - ast-kit@3.0.0: - dependencies: - '@babel/parser': 8.0.0 - estree-walker: 3.0.3 - pathe: 2.0.3 - ast-types-flow@0.0.8: {} - ast-v8-to-istanbul@0.3.12: + ast-v8-to-istanbul@1.0.5: dependencies: '@jridgewell/trace-mapping': 0.3.31 estree-walker: 3.0.3 @@ -5170,7 +4619,7 @@ snapshots: dependencies: possible-typed-array-names: 1.1.0 - axe-core@4.12.1: {} + axe-core@4.13.0: {} axobject-query@4.1.0: {} @@ -5186,8 +4635,6 @@ snapshots: dependencies: require-from-string: 2.0.2 - birpc@4.0.0: {} - bottleneck@2.19.5: {} brace-expansion@1.1.18: @@ -5215,8 +4662,6 @@ snapshots: node-releases: 2.0.54 update-browserslist-db: 1.3.2(browserslist@4.28.8) - cac@6.7.14: {} - cac@7.0.0: {} call-bind-apply-helpers@1.0.2: @@ -5240,13 +4685,7 @@ snapshots: caniuse-lite@1.0.30001810: {} - chai@5.3.3: - dependencies: - assertion-error: 2.0.1 - check-error: 2.1.3 - deep-eql: 5.0.2 - loupe: 3.2.1 - pathval: 2.0.1 + chai@6.2.2: {} chalk@2.4.2: dependencies: @@ -5263,10 +4702,6 @@ snapshots: char-regex@1.0.2: {} - check-error@2.1.3: {} - - clean-stack@2.2.0: {} - clean-stack@5.3.0: dependencies: escape-string-regexp: 5.0.0 @@ -5322,7 +4757,7 @@ snapshots: ini: 1.3.8 proto-list: 1.2.4 - content-type@2.0.0: {} + content-type@3.0.0: {} conventional-changelog-angular@8.3.1: dependencies: @@ -5402,18 +4837,20 @@ snapshots: es-errors: 1.3.0 is-data-view: 1.0.2 - debug@3.2.7: + debug@3.2.7(supports-color@7.2.0): dependencies: ms: 2.1.3 + optionalDependencies: + supports-color: 7.2.0 - debug@4.4.3: + debug@4.4.3(supports-color@7.2.0): dependencies: ms: 2.1.3 + optionalDependencies: + supports-color: 7.2.0 decimal.js@10.6.0: {} - deep-eql@5.0.2: {} - deep-extend@0.6.0: {} deep-is@0.1.4: {} @@ -5434,6 +4871,8 @@ snapshots: dequal@2.0.3: {} + detect-libc@2.1.2: {} + dir-glob@3.0.1: dependencies: path-type: 4.0.0 @@ -5460,8 +4899,6 @@ snapshots: dependencies: readable-stream: 2.3.8 - eastasianwidth@0.2.0: {} - electron-to-chromium@1.5.420: {} emoji-regex@10.6.0: {} @@ -5510,7 +4947,7 @@ snapshots: es-errors: 1.3.0 es-object-atoms: 1.1.2 es-set-tostringtag: 2.1.0 - es-to-primitive: 1.3.1 + es-to-primitive: 1.3.4 function.prototype.name: 1.2.0 get-intrinsic: 1.3.0 get-proto: 1.0.1 @@ -5536,7 +4973,7 @@ snapshots: object-inspect: 1.13.4 object-keys: 1.1.1 object.assign: 4.1.7 - own-keys: 1.0.1 + own-keys: 1.0.2 regexp.prototype.flags: 1.5.4 safe-array-concat: 1.1.4 safe-push-apply: 1.0.0 @@ -5557,7 +4994,7 @@ snapshots: es-errors@1.3.0: {} - es-iterator-helpers@1.3.3: + es-iterator-helpers@1.4.0: dependencies: call-bind: 1.0.9 call-bound: 1.0.4 @@ -5576,7 +5013,7 @@ snapshots: iterator.prototype: 1.1.5 math-intrinsics: 1.1.0 - es-module-lexer@1.7.0: {} + es-module-lexer@2.3.2: {} es-object-atoms@1.1.2: dependencies: @@ -5593,43 +5030,15 @@ snapshots: dependencies: hasown: 2.0.4 - es-to-primitive@1.3.1: + es-to-primitive@1.3.4: dependencies: es-abstract-get: 1.0.0 + es-define-property: 1.0.1 es-errors: 1.3.0 is-callable: 1.2.7 is-date-object: 1.1.0 is-symbol: 1.1.1 - esbuild@0.27.2: - optionalDependencies: - '@esbuild/aix-ppc64': 0.27.2 - '@esbuild/android-arm': 0.27.2 - '@esbuild/android-arm64': 0.27.2 - '@esbuild/android-x64': 0.27.2 - '@esbuild/darwin-arm64': 0.27.2 - '@esbuild/darwin-x64': 0.27.2 - '@esbuild/freebsd-arm64': 0.27.2 - '@esbuild/freebsd-x64': 0.27.2 - '@esbuild/linux-arm': 0.27.2 - '@esbuild/linux-arm64': 0.27.2 - '@esbuild/linux-ia32': 0.27.2 - '@esbuild/linux-loong64': 0.27.2 - '@esbuild/linux-mips64el': 0.27.2 - '@esbuild/linux-ppc64': 0.27.2 - '@esbuild/linux-riscv64': 0.27.2 - '@esbuild/linux-s390x': 0.27.2 - '@esbuild/linux-x64': 0.27.2 - '@esbuild/netbsd-arm64': 0.27.2 - '@esbuild/netbsd-x64': 0.27.2 - '@esbuild/openbsd-arm64': 0.27.2 - '@esbuild/openbsd-x64': 0.27.2 - '@esbuild/openharmony-arm64': 0.27.2 - '@esbuild/sunos-x64': 0.27.2 - '@esbuild/win32-arm64': 0.27.2 - '@esbuild/win32-ia32': 0.27.2 - '@esbuild/win32-x64': 0.27.2 - escalade@3.2.0: {} escape-string-regexp@1.0.5: {} @@ -5638,63 +5047,63 @@ snapshots: escape-string-regexp@5.0.0: {} - eslint-config-prettier@10.1.8(eslint@9.39.4): + eslint-config-prettier@10.1.8(eslint@9.39.5(supports-color@7.2.0)): dependencies: - eslint: 9.39.4 + eslint: 9.39.5(supports-color@7.2.0) eslint-import-context@0.1.9(unrs-resolver@1.12.2): dependencies: - get-tsconfig: 4.14.0 + get-tsconfig: 4.14.3 stable-hash-x: 0.2.0 optionalDependencies: unrs-resolver: 1.12.2 - eslint-import-resolver-node@0.3.10: + eslint-import-resolver-node@0.3.10(supports-color@7.2.0): dependencies: - debug: 3.2.7 + debug: 3.2.7(supports-color@7.2.0) is-core-module: 2.16.2 resolve: 2.0.0-next.7 transitivePeerDependencies: - supports-color - eslint-import-resolver-typescript@4.4.5(eslint-plugin-import@2.32.0)(eslint@9.39.4): + eslint-import-resolver-typescript@4.4.5(eslint-plugin-import@2.32.0)(eslint@9.39.5(supports-color@7.2.0))(supports-color@7.2.0): dependencies: - debug: 4.4.3 - eslint: 9.39.4 + debug: 4.4.3(supports-color@7.2.0) + eslint: 9.39.5(supports-color@7.2.0) eslint-import-context: 0.1.9(unrs-resolver@1.12.2) - get-tsconfig: 4.14.0 + get-tsconfig: 4.14.3 is-bun-module: 2.0.0 stable-hash-x: 0.2.0 tinyglobby: 0.2.17 unrs-resolver: 1.12.2 optionalDependencies: - eslint-plugin-import: 2.32.0(@typescript-eslint/parser@8.62.0(eslint@9.39.4)(typescript@6.0.3))(eslint-import-resolver-typescript@4.4.5)(eslint@9.39.4) + eslint-plugin-import: 2.32.0(@typescript-eslint/parser@8.69.0(eslint@9.39.5(supports-color@7.2.0))(supports-color@7.2.0)(typescript@6.0.3))(eslint-import-resolver-typescript@4.4.5)(eslint@9.39.5(supports-color@7.2.0))(supports-color@7.2.0) transitivePeerDependencies: - supports-color - eslint-module-utils@2.13.0(@typescript-eslint/parser@8.62.0(eslint@9.39.4)(typescript@6.0.3))(eslint-import-resolver-node@0.3.10)(eslint-import-resolver-typescript@4.4.5)(eslint@9.39.4): + eslint-module-utils@2.14.0(@typescript-eslint/parser@8.69.0(eslint@9.39.5(supports-color@7.2.0))(supports-color@7.2.0)(typescript@6.0.3))(eslint-import-resolver-node@0.3.10(supports-color@7.2.0))(eslint-import-resolver-typescript@4.4.5)(eslint@9.39.5(supports-color@7.2.0))(supports-color@7.2.0): dependencies: - debug: 3.2.7 + debug: 3.2.7(supports-color@7.2.0) optionalDependencies: - '@typescript-eslint/parser': 8.62.0(eslint@9.39.4)(typescript@6.0.3) - eslint: 9.39.4 - eslint-import-resolver-node: 0.3.10 - eslint-import-resolver-typescript: 4.4.5(eslint-plugin-import@2.32.0)(eslint@9.39.4) + '@typescript-eslint/parser': 8.69.0(eslint@9.39.5(supports-color@7.2.0))(supports-color@7.2.0)(typescript@6.0.3) + eslint: 9.39.5(supports-color@7.2.0) + eslint-import-resolver-node: 0.3.10(supports-color@7.2.0) + eslint-import-resolver-typescript: 4.4.5(eslint-plugin-import@2.32.0)(eslint@9.39.5(supports-color@7.2.0))(supports-color@7.2.0) transitivePeerDependencies: - supports-color - eslint-plugin-import@2.32.0(@typescript-eslint/parser@8.62.0(eslint@9.39.4)(typescript@6.0.3))(eslint-import-resolver-typescript@4.4.5)(eslint@9.39.4): + eslint-plugin-import@2.32.0(@typescript-eslint/parser@8.69.0(eslint@9.39.5(supports-color@7.2.0))(supports-color@7.2.0)(typescript@6.0.3))(eslint-import-resolver-typescript@4.4.5)(eslint@9.39.5(supports-color@7.2.0))(supports-color@7.2.0): dependencies: '@rtsao/scc': 1.1.0 array-includes: 3.1.9 array.prototype.findlastindex: 1.2.6 array.prototype.flat: 1.3.3 array.prototype.flatmap: 1.3.3 - debug: 3.2.7 + debug: 3.2.7(supports-color@7.2.0) doctrine: 2.1.0 - eslint: 9.39.4 - eslint-import-resolver-node: 0.3.10 - eslint-module-utils: 2.13.0(@typescript-eslint/parser@8.62.0(eslint@9.39.4)(typescript@6.0.3))(eslint-import-resolver-node@0.3.10)(eslint-import-resolver-typescript@4.4.5)(eslint@9.39.4) + eslint: 9.39.5(supports-color@7.2.0) + eslint-import-resolver-node: 0.3.10(supports-color@7.2.0) + eslint-module-utils: 2.14.0(@typescript-eslint/parser@8.69.0(eslint@9.39.5(supports-color@7.2.0))(supports-color@7.2.0)(typescript@6.0.3))(eslint-import-resolver-node@0.3.10(supports-color@7.2.0))(eslint-import-resolver-typescript@4.4.5)(eslint@9.39.5(supports-color@7.2.0))(supports-color@7.2.0) hasown: 2.0.4 is-core-module: 2.16.2 is-glob: 4.0.3 @@ -5706,23 +5115,23 @@ snapshots: string.prototype.trimend: 1.0.10 tsconfig-paths: 3.15.0 optionalDependencies: - '@typescript-eslint/parser': 8.62.0(eslint@9.39.4)(typescript@6.0.3) + '@typescript-eslint/parser': 8.69.0(eslint@9.39.5(supports-color@7.2.0))(supports-color@7.2.0)(typescript@6.0.3) transitivePeerDependencies: - eslint-import-resolver-typescript - eslint-import-resolver-webpack - supports-color - eslint-plugin-jsx-a11y@6.10.2(eslint@9.39.4): + eslint-plugin-jsx-a11y@6.10.2(eslint@9.39.5(supports-color@7.2.0)): dependencies: aria-query: 5.3.2 array-includes: 3.1.9 array.prototype.flatmap: 1.3.3 ast-types-flow: 0.0.8 - axe-core: 4.12.1 + axe-core: 4.13.0 axobject-query: 4.1.0 damerau-levenshtein: 1.0.8 emoji-regex: 9.2.2 - eslint: 9.39.4 + eslint: 9.39.5(supports-color@7.2.0) hasown: 2.0.4 jsx-ast-utils: 3.3.5 language-tags: 1.0.9 @@ -5731,26 +5140,26 @@ snapshots: safe-regex-test: 1.1.0 string.prototype.includes: 2.0.1 - eslint-plugin-react-hooks@7.1.1(eslint@9.39.4): + eslint-plugin-react-hooks@7.1.1(eslint@9.39.5(supports-color@7.2.0))(supports-color@7.2.0): dependencies: - '@babel/core': 7.29.7 - '@babel/parser': 7.29.7 - eslint: 9.39.4 + '@babel/core': 7.29.7(supports-color@7.2.0) + '@babel/parser': 7.29.8 + eslint: 9.39.5(supports-color@7.2.0) hermes-parser: 0.25.1 - zod: 4.4.3 - zod-validation-error: 4.0.2(zod@4.4.3) + zod: 4.5.4 + zod-validation-error: 4.0.2(zod@4.5.4) transitivePeerDependencies: - supports-color - eslint-plugin-react@7.37.5(eslint@9.39.4): + eslint-plugin-react@7.37.5(eslint@9.39.5(supports-color@7.2.0)): dependencies: array-includes: 3.1.9 array.prototype.findlast: 1.2.5 array.prototype.flatmap: 1.3.3 array.prototype.tosorted: 1.1.4 doctrine: 2.1.0 - es-iterator-helpers: 1.3.3 - eslint: 9.39.4 + es-iterator-helpers: 1.4.0 + eslint: 9.39.5(supports-color@7.2.0) estraverse: 5.3.0 hasown: 2.0.4 jsx-ast-utils: 3.3.5 @@ -5761,12 +5170,12 @@ snapshots: prop-types: 15.8.1 resolve: 2.0.0-next.7 semver: 6.3.1 - string.prototype.matchall: 4.0.12 + string.prototype.matchall: 4.1.0 string.prototype.repeat: 1.0.0 - eslint-plugin-sort-exports@0.9.1(eslint@9.39.4): + eslint-plugin-sort-exports@0.9.1(eslint@9.39.5(supports-color@7.2.0)): dependencies: - eslint: 9.39.4 + eslint: 9.39.5(supports-color@7.2.0) minimatch: 9.0.9 eslint-scope@8.4.0: @@ -5780,15 +5189,15 @@ snapshots: eslint-visitor-keys@5.0.1: {} - eslint@9.39.4: + eslint@9.39.5(supports-color@7.2.0): dependencies: - '@eslint-community/eslint-utils': 4.9.1(eslint@9.39.4) + '@eslint-community/eslint-utils': 4.10.1(eslint@9.39.5(supports-color@7.2.0)) '@eslint-community/regexpp': 4.12.2 - '@eslint/config-array': 0.21.2 + '@eslint/config-array': 0.21.2(supports-color@7.2.0) '@eslint/config-helpers': 0.4.2 '@eslint/core': 0.17.0 - '@eslint/eslintrc': 3.3.5 - '@eslint/js': 9.39.4 + '@eslint/eslintrc': 3.3.7(supports-color@7.2.0) + '@eslint/js': 9.39.5 '@eslint/plugin-kit': 0.4.1 '@humanfs/node': 0.16.8 '@humanwhocodes/module-importer': 1.0.1 @@ -5797,7 +5206,7 @@ snapshots: ajv: 6.15.0 chalk: 4.1.2 cross-spawn: 7.0.6 - debug: 4.4.3 + debug: 4.4.3(supports-color@7.2.0) escape-string-regexp: 4.0.0 eslint-scope: 8.4.0 eslint-visitor-keys: 4.2.1 @@ -5821,8 +5230,8 @@ snapshots: espree@10.4.0: dependencies: - acorn: 8.17.0 - acorn-jsx: 5.3.2(acorn@8.17.0) + acorn: 8.18.0 + acorn-jsx: 5.3.2(acorn@8.18.0) eslint-visitor-keys: 4.2.1 esquery@1.7.0: @@ -5841,17 +5250,20 @@ snapshots: esutils@2.0.3: {} - execa@5.1.1: + execa@10.0.1: dependencies: - cross-spawn: 7.0.6 - get-stream: 6.0.1 - human-signals: 2.1.0 - is-stream: 2.0.1 - merge-stream: 2.0.0 - npm-run-path: 4.0.1 - onetime: 5.1.2 - signal-exit: 3.0.7 - strip-final-newline: 2.0.0 + '@sindresorhus/merge-streams': 4.0.0 + figures: 6.1.0 + get-stream: 9.0.1 + human-signals: 8.0.1 + is-plain-obj: 4.1.0 + is-stream: 4.0.1 + npm-run-path: 6.0.0 + pretty-ms: 9.3.1 + signal-exit: 4.1.0 + strip-final-newline: 4.0.0 + which-command: 0.1.0 + yoctocolors: 2.2.0 execa@8.0.1: dependencies: @@ -5875,12 +5287,12 @@ snapshots: is-plain-obj: 4.1.0 is-stream: 4.0.1 npm-run-path: 6.0.0 - pretty-ms: 9.3.0 + pretty-ms: 9.3.1 signal-exit: 4.1.0 strip-final-newline: 4.0.0 - yoctocolors: 2.1.2 + yoctocolors: 2.2.0 - expect-type@1.3.0: {} + expect-type@1.4.0: {} fast-deep-equal@3.1.3: {} @@ -5888,9 +5300,9 @@ snapshots: fast-levenshtein@2.0.6: {} - fdir@6.5.0(picomatch@4.0.4): + fdir@6.5.0(picomatch@4.0.7): optionalDependencies: - picomatch: 4.0.4 + picomatch: 4.0.7 figures@2.0.0: dependencies: @@ -5926,21 +5338,16 @@ snapshots: flat-cache@4.0.1: dependencies: - flatted: 3.4.2 + flatted: 3.4.4 keyv: 4.5.4 - flatted@3.4.2: {} + flatted@3.4.4: {} for-each@0.3.5: dependencies: is-callable: 1.2.7 - foreground-child@3.3.1: - dependencies: - cross-spawn: 7.0.6 - signal-exit: 4.1.0 - - fs-extra@11.3.5: + fs-extra@11.4.0: dependencies: graceful-fs: 4.2.11 jsonfile: 6.2.1 @@ -6008,7 +5415,7 @@ snapshots: es-errors: 1.3.0 get-intrinsic: 1.3.0 - get-tsconfig@4.14.0: + get-tsconfig@4.14.3: dependencies: resolve-pkg-maps: 1.0.0 @@ -6029,24 +5436,15 @@ snapshots: dependencies: is-glob: 4.0.3 - glob@10.5.0: - dependencies: - foreground-child: 3.3.1 - jackspeak: 3.4.3 - minimatch: 9.0.9 - minipass: 7.1.3 - package-json-from-dist: 1.0.1 - path-scurry: 1.11.1 - glob@13.0.6: dependencies: - minimatch: 10.2.5 + minimatch: 10.2.6 minipass: 7.1.3 path-scurry: 2.0.2 globals@14.0.0: {} - globals@17.7.0: {} + globals@17.12.0: {} globalthis@1.0.4: dependencies: @@ -6110,7 +5508,7 @@ snapshots: hosted-git-info@9.0.3: dependencies: - lru-cache: 11.5.1 + lru-cache: 11.5.2 html-encoding-sniffer@6.0.0: dependencies: @@ -6120,42 +5518,40 @@ snapshots: html-escaper@2.0.2: {} - http-proxy-agent@9.1.0: + http-proxy-agent@9.1.0(supports-color@7.2.0): dependencies: agent-base: 9.0.0 - debug: 4.4.3 + debug: 4.4.3(supports-color@7.2.0) proxy-agent-negotiate: 1.1.0 transitivePeerDependencies: - kerberos - supports-color - https-proxy-agent@9.1.0: + https-proxy-agent@9.1.0(supports-color@7.2.0): dependencies: agent-base: 9.0.0 - debug: 4.4.3 + debug: 4.4.3(supports-color@7.2.0) proxy-agent-negotiate: 1.1.0 transitivePeerDependencies: - kerberos - supports-color - human-signals@2.1.0: {} - human-signals@5.0.0: {} human-signals@8.0.1: {} ignore@5.3.2: {} - ignore@7.0.5: {} + ignore@7.0.8: {} import-fresh@3.3.1: dependencies: parent-module: 1.0.1 resolve-from: 4.0.0 - import-from-esm@2.0.0: + import-from-esm@2.0.0(supports-color@7.2.0): dependencies: - debug: 4.4.3 + debug: 4.4.3(supports-color@7.2.0) import-meta-resolve: 4.2.0 transitivePeerDependencies: - supports-color @@ -6166,8 +5562,6 @@ snapshots: imurmurhash@0.1.4: {} - indent-string@4.0.0: {} - indent-string@5.0.0: {} index-to-position@1.2.0: {} @@ -6282,8 +5676,6 @@ snapshots: dependencies: call-bound: 1.0.4 - is-stream@2.0.1: {} - is-stream@3.0.0: {} is-stream@4.0.1: {} @@ -6338,14 +5730,6 @@ snapshots: make-dir: 4.0.0 supports-color: 7.2.0 - istanbul-lib-source-maps@5.0.6: - dependencies: - '@jridgewell/trace-mapping': 0.3.31 - debug: 4.4.3 - istanbul-lib-coverage: 3.2.2 - transitivePeerDependencies: - - supports-color - istanbul-reports@3.2.0: dependencies: html-escaper: 2.0.2 @@ -6360,46 +5744,38 @@ snapshots: has-symbols: 1.1.0 set-function-name: 2.0.2 - jackspeak@3.4.3: - dependencies: - '@isaacs/cliui': 8.0.2 - optionalDependencies: - '@pkgjs/parseargs': 0.11.0 - java-properties@1.0.2: {} js-tokens@10.0.0: {} js-tokens@4.0.0: {} - js-tokens@9.0.1: {} - js-yaml@4.3.1: dependencies: argparse: 2.0.1 - jsdom@29.1.1: + jsdom@30.0.1: dependencies: - '@asamuzakjp/css-color': 5.1.11 - '@asamuzakjp/dom-selector': 7.1.1 + '@asamuzakjp/css-color': 6.0.7 + '@asamuzakjp/dom-selector': 8.3.2 '@bramus/specificity': 2.4.2 - '@csstools/css-syntax-patches-for-csstree': 1.1.6(css-tree@3.2.1) + '@csstools/css-syntax-patches-for-csstree': 1.1.12(css-tree@3.2.1) '@exodus/bytes': 1.15.1 css-tree: 3.2.1 data-urls: 7.0.0 decimal.js: 10.6.0 html-encoding-sniffer: 6.0.0 is-potential-custom-element-name: 1.0.1 - lru-cache: 11.5.1 + lru-cache: 11.5.2 parse5: 8.0.1 saxes: 6.0.0 symbol-tree: 3.2.4 - tough-cookie: 6.0.1 + tough-cookie: 6.0.2 undici: 7.29.0 w3c-xmlserializer: 5.0.0 webidl-conversions: 8.0.1 whatwg-mimetype: 5.0.0 - whatwg-url: 16.0.1 + whatwg-url: 17.1.0 xml-name-validator: 5.0.0 transitivePeerDependencies: - '@noble/hashes' @@ -6416,7 +5792,7 @@ snapshots: json-stable-stringify-without-jsonify@1.0.1: {} - json-with-bigint@3.5.8: {} + json-with-bigint@3.5.12: {} json5@1.0.2: dependencies: @@ -6452,6 +5828,55 @@ snapshots: prelude-ls: 1.2.1 type-check: 0.4.0 + lightningcss-android-arm64@1.33.0: + optional: true + + lightningcss-darwin-arm64@1.33.0: + optional: true + + lightningcss-darwin-x64@1.33.0: + optional: true + + lightningcss-freebsd-x64@1.33.0: + optional: true + + lightningcss-linux-arm-gnueabihf@1.33.0: + optional: true + + lightningcss-linux-arm64-gnu@1.33.0: + optional: true + + lightningcss-linux-arm64-musl@1.33.0: + optional: true + + lightningcss-linux-x64-gnu@1.33.0: + optional: true + + lightningcss-linux-x64-musl@1.33.0: + optional: true + + lightningcss-win32-arm64-msvc@1.33.0: + optional: true + + lightningcss-win32-x64-msvc@1.33.0: + optional: true + + lightningcss@1.33.0: + dependencies: + detect-libc: 2.1.2 + optionalDependencies: + lightningcss-android-arm64: 1.33.0 + lightningcss-darwin-arm64: 1.33.0 + lightningcss-darwin-x64: 1.33.0 + lightningcss-freebsd-x64: 1.33.0 + lightningcss-linux-arm-gnueabihf: 1.33.0 + lightningcss-linux-arm64-gnu: 1.33.0 + lightningcss-linux-arm64-musl: 1.33.0 + lightningcss-linux-x64-gnu: 1.33.0 + lightningcss-linux-x64-musl: 1.33.0 + lightningcss-win32-arm64-msvc: 1.33.0 + lightningcss-win32-x64-msvc: 1.33.0 + lines-and-columns@1.2.4: {} load-json-file@4.0.0: @@ -6484,17 +5909,13 @@ snapshots: lodash.uniqby@4.7.0: {} - lodash@4.18.1: {} - loose-envify@1.4.0: dependencies: js-tokens: 4.0.0 - loupe@3.2.1: {} - lru-cache@10.4.3: {} - lru-cache@11.5.1: {} + lru-cache@11.5.2: {} lru-cache@5.1.1: dependencies: @@ -6504,12 +5925,12 @@ snapshots: magic-string@0.30.21: dependencies: - '@jridgewell/sourcemap-codec': 1.5.5 + '@jridgewell/sourcemap-codec': 1.6.0 - magicast@0.3.5: + magicast@0.5.4: dependencies: - '@babel/parser': 7.29.7 - '@babel/types': 7.29.7 + '@babel/parser': 7.29.8 + '@babel/types': 7.29.8 source-map-js: 1.2.1 make-asynchronous@1.1.0: @@ -6525,7 +5946,7 @@ snapshots: marked-terminal@7.3.0(marked@15.0.12): dependencies: ansi-escapes: 7.3.0 - ansi-regex: 6.2.2 + ansi-regex: 6.3.0 chalk: 5.6.2 cli-highlight: 2.1.11 cli-table3: 0.6.5 @@ -6550,11 +5971,9 @@ snapshots: mime@4.1.0: {} - mimic-fn@2.1.0: {} - mimic-fn@4.0.0: {} - minimatch@10.2.5: + minimatch@10.2.6: dependencies: brace-expansion: 5.0.9 @@ -6595,7 +6014,7 @@ snapshots: emojilib: 2.4.0 skin-tone: 2.0.0 - node-exports-info@1.6.0: + node-exports-info@1.6.2: dependencies: array.prototype.flatmap: 1.3.3 es-errors: 1.3.0 @@ -6618,10 +6037,6 @@ snapshots: normalize-url@9.0.1: {} - npm-run-path@4.0.1: - dependencies: - path-key: 3.1.1 - npm-run-path@5.3.0: dependencies: path-key: 4.0.0 @@ -6631,7 +6046,7 @@ snapshots: path-key: 4.0.0 unicorn-magic: 0.3.0 - npm@11.17.0: {} + npm@11.19.1: {} object-assign@4.1.1: {} @@ -6675,11 +6090,7 @@ snapshots: define-properties: 1.2.1 es-object-atoms: 1.1.2 - obug@2.1.3: {} - - onetime@5.1.2: - dependencies: - mimic-fn: 2.1.0 + obug@2.1.4: {} onetime@6.0.0: dependencies: @@ -6694,8 +6105,9 @@ snapshots: type-check: 0.4.0 word-wrap: 1.2.5 - own-keys@1.0.1: + own-keys@1.0.2: dependencies: + call-bound: 1.0.4 get-intrinsic: 1.3.0 object-keys: 1.1.1 safe-push-apply: 1.0.0 @@ -6708,7 +6120,7 @@ snapshots: p-filter@4.1.0: dependencies: - p-map: 7.0.4 + p-map: 7.0.7 p-limit@1.3.0: dependencies: @@ -6726,9 +6138,7 @@ snapshots: dependencies: p-limit: 3.1.0 - p-map@7.0.4: {} - - p-reduce@2.1.0: {} + p-map@7.0.7: {} p-reduce@3.0.0: {} @@ -6784,27 +6194,20 @@ snapshots: path-parse@1.0.7: {} - path-scurry@1.11.1: - dependencies: - lru-cache: 10.4.3 - minipass: 7.1.3 - path-scurry@2.0.2: dependencies: - lru-cache: 11.5.1 + lru-cache: 11.5.2 minipass: 7.1.3 path-type@4.0.0: {} pathe@2.0.3: {} - pathval@2.0.1: {} - picocolors@1.1.1: {} picomatch@2.3.2: {} - picomatch@4.0.4: {} + picomatch@4.0.7: {} pify@3.0.0: {} @@ -6823,7 +6226,7 @@ snapshots: prelude-ls@1.2.1: {} - prettier@3.9.3: {} + prettier@3.9.6: {} pretty-format@27.5.1: dependencies: @@ -6831,7 +6234,7 @@ snapshots: ansi-styles: 5.2.0 react-is: 17.0.2 - pretty-ms@9.3.0: + pretty-ms@9.3.1: dependencies: parse-ms: 4.0.0 @@ -6882,14 +6285,14 @@ snapshots: dependencies: find-up-simple: 1.0.1 read-pkg: 10.1.0 - type-fest: 5.7.0 + type-fest: 5.9.0 read-pkg@10.1.0: dependencies: '@types/normalize-package-data': 2.4.4 normalize-package-data: 8.0.0 parse-json: 8.3.0 - type-fest: 5.7.0 + type-fest: 5.9.0 unicorn-magic: 0.4.0 read-pkg@9.0.1: @@ -6948,7 +6351,7 @@ snapshots: dependencies: es-errors: 1.3.0 is-core-module: 2.16.2 - node-exports-info: 1.6.0 + node-exports-info: 1.6.2 object-keys: 1.1.1 path-parse: 1.0.7 supports-preserve-symlinks-flag: 1.0.0 @@ -6958,95 +6361,40 @@ snapshots: glob: 13.0.6 package-json-from-dist: 1.0.1 - rolldown-plugin-dts@0.26.0(rolldown@1.1.3)(typescript@6.0.3): + rolldown-plugin-dts@0.27.14(rolldown@1.2.7)(typescript@6.0.3): dependencies: - '@babel/generator': 8.0.0 - '@babel/helper-validator-identifier': 8.0.2 - '@babel/parser': 8.0.0 - ast-kit: 3.0.0 - birpc: 4.0.0 dts-resolver: 3.0.0 get-tsconfig: 5.0.0-beta.5 - obug: 2.1.3 - rolldown: 1.1.3 + obug: 2.1.4 + rolldown: 1.2.7 + yuku-ast: 0.8.7 + yuku-codegen: 0.8.7 + yuku-parser: 0.8.7 optionalDependencies: typescript: 6.0.3 transitivePeerDependencies: - oxc-resolver - rolldown@1.0.0-rc.17: - dependencies: - '@oxc-project/types': 0.127.0 - '@rolldown/pluginutils': 1.0.0-rc.17 - optionalDependencies: - '@rolldown/binding-android-arm64': 1.0.0-rc.17 - '@rolldown/binding-darwin-arm64': 1.0.0-rc.17 - '@rolldown/binding-darwin-x64': 1.0.0-rc.17 - '@rolldown/binding-freebsd-x64': 1.0.0-rc.17 - '@rolldown/binding-linux-arm-gnueabihf': 1.0.0-rc.17 - '@rolldown/binding-linux-arm64-gnu': 1.0.0-rc.17 - '@rolldown/binding-linux-arm64-musl': 1.0.0-rc.17 - '@rolldown/binding-linux-ppc64-gnu': 1.0.0-rc.17 - '@rolldown/binding-linux-s390x-gnu': 1.0.0-rc.17 - '@rolldown/binding-linux-x64-gnu': 1.0.0-rc.17 - '@rolldown/binding-linux-x64-musl': 1.0.0-rc.17 - '@rolldown/binding-openharmony-arm64': 1.0.0-rc.17 - '@rolldown/binding-wasm32-wasi': 1.0.0-rc.17 - '@rolldown/binding-win32-arm64-msvc': 1.0.0-rc.17 - '@rolldown/binding-win32-x64-msvc': 1.0.0-rc.17 - optional: true - - rolldown@1.1.3: + rolldown@1.2.7: dependencies: - '@oxc-project/types': 0.137.0 + '@oxc-project/types': 0.148.0 '@rolldown/pluginutils': 1.0.1 optionalDependencies: - '@rolldown/binding-android-arm64': 1.1.3 - '@rolldown/binding-darwin-arm64': 1.1.3 - '@rolldown/binding-darwin-x64': 1.1.3 - '@rolldown/binding-freebsd-x64': 1.1.3 - '@rolldown/binding-linux-arm-gnueabihf': 1.1.3 - '@rolldown/binding-linux-arm64-gnu': 1.1.3 - '@rolldown/binding-linux-arm64-musl': 1.1.3 - '@rolldown/binding-linux-ppc64-gnu': 1.1.3 - '@rolldown/binding-linux-s390x-gnu': 1.1.3 - '@rolldown/binding-linux-x64-gnu': 1.1.3 - '@rolldown/binding-linux-x64-musl': 1.1.3 - '@rolldown/binding-openharmony-arm64': 1.1.3 - '@rolldown/binding-wasm32-wasi': 1.1.3 - '@rolldown/binding-win32-arm64-msvc': 1.1.3 - '@rolldown/binding-win32-x64-msvc': 1.1.3 - - rollup@4.62.2: - dependencies: - '@types/estree': 1.0.9 - optionalDependencies: - '@rollup/rollup-android-arm-eabi': 4.62.2 - '@rollup/rollup-android-arm64': 4.62.2 - '@rollup/rollup-darwin-arm64': 4.62.2 - '@rollup/rollup-darwin-x64': 4.62.2 - '@rollup/rollup-freebsd-arm64': 4.62.2 - '@rollup/rollup-freebsd-x64': 4.62.2 - '@rollup/rollup-linux-arm-gnueabihf': 4.62.2 - '@rollup/rollup-linux-arm-musleabihf': 4.62.2 - '@rollup/rollup-linux-arm64-gnu': 4.62.2 - '@rollup/rollup-linux-arm64-musl': 4.62.2 - '@rollup/rollup-linux-loong64-gnu': 4.62.2 - '@rollup/rollup-linux-loong64-musl': 4.62.2 - '@rollup/rollup-linux-ppc64-gnu': 4.62.2 - '@rollup/rollup-linux-ppc64-musl': 4.62.2 - '@rollup/rollup-linux-riscv64-gnu': 4.62.2 - '@rollup/rollup-linux-riscv64-musl': 4.62.2 - '@rollup/rollup-linux-s390x-gnu': 4.62.2 - '@rollup/rollup-linux-x64-gnu': 4.62.2 - '@rollup/rollup-linux-x64-musl': 4.62.2 - '@rollup/rollup-openbsd-x64': 4.62.2 - '@rollup/rollup-openharmony-arm64': 4.62.2 - '@rollup/rollup-win32-arm64-msvc': 4.62.2 - '@rollup/rollup-win32-ia32-msvc': 4.62.2 - '@rollup/rollup-win32-x64-gnu': 4.62.2 - '@rollup/rollup-win32-x64-msvc': 4.62.2 - fsevents: 2.3.3 + '@rolldown/binding-android-arm-eabi': 1.2.7 + '@rolldown/binding-android-arm64': 1.2.7 + '@rolldown/binding-darwin-arm64': 1.2.7 + '@rolldown/binding-darwin-x64': 1.2.7 + '@rolldown/binding-freebsd-x64': 1.2.7 + '@rolldown/binding-linux-arm-gnueabihf': 1.2.7 + '@rolldown/binding-linux-arm64-gnu': 1.2.7 + '@rolldown/binding-linux-arm64-musl': 1.2.7 + '@rolldown/binding-linux-ppc64-gnu': 1.2.7 + '@rolldown/binding-linux-s390x-gnu': 1.2.7 + '@rolldown/binding-linux-x64-gnu': 1.2.7 + '@rolldown/binding-linux-x64-musl': 1.2.7 + '@rolldown/binding-openharmony-arm64': 1.2.7 + '@rolldown/binding-win32-arm64-msvc': 1.2.7 + '@rolldown/binding-win32-x64-msvc': 1.2.7 safe-array-concat@1.1.4: dependencies: @@ -7077,16 +6425,16 @@ snapshots: dependencies: loose-envify: 1.4.0 - semantic-release@25.0.5(typescript@6.0.3): + semantic-release@25.0.9(supports-color@7.2.0)(typescript@6.0.3): dependencies: - '@semantic-release/commit-analyzer': 13.0.1(semantic-release@25.0.5(typescript@6.0.3)) + '@semantic-release/commit-analyzer': 13.0.1(semantic-release@25.0.9(supports-color@7.2.0)(typescript@6.0.3))(supports-color@7.2.0) '@semantic-release/error': 4.0.0 - '@semantic-release/github': 12.0.8(semantic-release@25.0.5(typescript@6.0.3)) - '@semantic-release/npm': 13.1.5(semantic-release@25.0.5(typescript@6.0.3)) - '@semantic-release/release-notes-generator': 14.1.1(semantic-release@25.0.5(typescript@6.0.3)) + '@semantic-release/github': 12.0.9(semantic-release@25.0.9(supports-color@7.2.0)(typescript@6.0.3))(supports-color@7.2.0) + '@semantic-release/npm': 13.1.5(semantic-release@25.0.9(supports-color@7.2.0)(typescript@6.0.3)) + '@semantic-release/release-notes-generator': 14.1.1(semantic-release@25.0.9(supports-color@7.2.0)(typescript@6.0.3))(supports-color@7.2.0) aggregate-error: 5.0.0 cosmiconfig: 9.0.2(typescript@6.0.3) - debug: 4.4.3 + debug: 4.4.3(supports-color@7.2.0) env-ci: 11.2.0 execa: 9.6.1 figures: 6.1.0 @@ -7095,7 +6443,7 @@ snapshots: git-log-parser: 1.2.1 hook-std: 4.0.0 hosted-git-info: 9.0.3 - import-from-esm: 2.0.0 + import-from-esm: 2.0.0(supports-color@7.2.0) lodash-es: 4.18.1 marked: 15.0.12 marked-terminal: 7.3.0(marked@15.0.12) @@ -7106,7 +6454,7 @@ snapshots: resolve-from: 5.0.0 semver: 7.8.5 signale: 1.4.0 - yargs: 18.0.0 + yargs: 18.1.0 transitivePeerDependencies: - kerberos - supports-color @@ -7176,8 +6524,6 @@ snapshots: siginfo@2.0.0: {} - signal-exit@3.0.7: {} - signal-exit@4.1.0: {} signale@1.4.0: @@ -7218,7 +6564,7 @@ snapshots: stackback@0.0.2: {} - std-env@3.10.0: {} + std-env@4.2.0: {} stop-iteration-iterator@1.1.0: dependencies: @@ -7236,15 +6582,14 @@ snapshots: is-fullwidth-code-point: 3.0.0 strip-ansi: 6.0.1 - string-width@5.1.2: + string-width@7.2.0: dependencies: - eastasianwidth: 0.2.0 - emoji-regex: 9.2.2 + emoji-regex: 10.6.0 + get-east-asian-width: 1.6.0 strip-ansi: 7.2.0 - string-width@7.2.0: + string-width@8.2.2: dependencies: - emoji-regex: 10.6.0 get-east-asian-width: 1.6.0 strip-ansi: 7.2.0 @@ -7254,7 +6599,7 @@ snapshots: define-properties: 1.2.1 es-abstract: 1.24.2 - string.prototype.matchall@4.0.12: + string.prototype.matchall@4.1.0: dependencies: call-bind: 1.0.9 call-bound: 1.0.4 @@ -7309,12 +6654,10 @@ snapshots: strip-ansi@7.2.0: dependencies: - ansi-regex: 6.2.2 + ansi-regex: 6.3.0 strip-bom@3.0.0: {} - strip-final-newline@2.0.0: {} - strip-final-newline@3.0.0: {} strip-final-newline@4.0.0: {} @@ -7323,10 +6666,6 @@ snapshots: strip-json-comments@3.1.1: {} - strip-literal@3.1.0: - dependencies: - js-tokens: 9.0.1 - super-regex@1.1.0: dependencies: function-timeout: 1.0.2 @@ -7361,12 +6700,6 @@ snapshots: type-fest: 2.19.0 unique-string: 3.0.0 - test-exclude@7.0.2: - dependencies: - '@istanbuljs/schema': 0.1.6 - glob: 10.5.0 - minimatch: 10.2.5 - thenify-all@1.6.0: dependencies: thenify: 3.3.1 @@ -7386,34 +6719,28 @@ snapshots: tinybench@2.9.0: {} - tinyexec@0.3.2: {} - - tinyexec@1.2.4: {} + tinyexec@1.3.0: {} tinyglobby@0.2.17: dependencies: - fdir: 6.5.0(picomatch@4.0.4) - picomatch: 4.0.4 - - tinypool@1.1.1: {} + fdir: 6.5.0(picomatch@4.0.7) + picomatch: 4.0.7 - tinyrainbow@2.0.0: {} + tinyrainbow@3.1.1: {} - tinyspy@4.0.4: {} + tldts-core@7.4.11: {} - tldts-core@7.4.5: {} - - tldts@7.4.5: + tldts@7.4.11: dependencies: - tldts-core: 7.4.5 + tldts-core: 7.4.11 to-regex-range@5.0.1: dependencies: is-number: 7.0.0 - tough-cookie@6.0.1: + tough-cookie@6.0.2: dependencies: - tldts: 7.4.5 + tldts: 7.4.11 tr46@6.0.0: dependencies: @@ -7434,7 +6761,7 @@ snapshots: minimist: 1.2.8 strip-bom: 3.0.0 - tsdown@0.22.3(typescript@6.0.3)(unrun@0.2.39): + tsdown@0.22.14(typescript@6.0.3): dependencies: ansis: 4.3.1 cac: 7.0.0 @@ -7442,21 +6769,20 @@ snapshots: empathic: 2.0.1 hookable: 6.1.1 import-without-cache: 0.4.0 - obug: 2.1.3 - picomatch: 4.0.4 - rolldown: 1.1.3 - rolldown-plugin-dts: 0.26.0(rolldown@1.1.3)(typescript@6.0.3) - semver: 7.8.5 - tinyexec: 1.2.4 + obug: 2.1.4 + picomatch: 4.0.7 + rolldown: 1.2.7 + rolldown-plugin-dts: 0.27.14(rolldown@1.2.7)(typescript@6.0.3) + tinyexec: 1.3.0 tinyglobby: 0.2.17 tree-kill: 1.2.2 unconfig-core: 7.5.0 + verkit: 0.3.2 optionalDependencies: typescript: 6.0.3 - unrun: 0.2.39 transitivePeerDependencies: - - '@ts-macro/tsc' - '@typescript/native-preview' + - '@volar/typescript' - oxc-resolver - vue-tsc @@ -7475,7 +6801,7 @@ snapshots: type-fest@4.41.0: {} - type-fest@5.7.0: + type-fest@5.9.0: dependencies: tagged-tag: 1.0.0 @@ -7512,13 +6838,13 @@ snapshots: possible-typed-array-names: 1.1.0 reflect.getprototypeof: 1.0.10 - typescript-eslint@8.62.0(eslint@9.39.4)(typescript@6.0.3): + typescript-eslint@8.69.0(eslint@9.39.5(supports-color@7.2.0))(supports-color@7.2.0)(typescript@6.0.3): dependencies: - '@typescript-eslint/eslint-plugin': 8.62.0(@typescript-eslint/parser@8.62.0(eslint@9.39.4)(typescript@6.0.3))(eslint@9.39.4)(typescript@6.0.3) - '@typescript-eslint/parser': 8.62.0(eslint@9.39.4)(typescript@6.0.3) - '@typescript-eslint/typescript-estree': 8.62.0(typescript@6.0.3) - '@typescript-eslint/utils': 8.62.0(eslint@9.39.4)(typescript@6.0.3) - eslint: 9.39.4 + '@typescript-eslint/eslint-plugin': 8.69.0(@typescript-eslint/parser@8.69.0(eslint@9.39.5(supports-color@7.2.0))(supports-color@7.2.0)(typescript@6.0.3))(eslint@9.39.5(supports-color@7.2.0))(supports-color@7.2.0)(typescript@6.0.3) + '@typescript-eslint/parser': 8.69.0(eslint@9.39.5(supports-color@7.2.0))(supports-color@7.2.0)(typescript@6.0.3) + '@typescript-eslint/typescript-estree': 8.69.0(supports-color@7.2.0)(typescript@6.0.3) + '@typescript-eslint/utils': 8.69.0(eslint@9.39.5(supports-color@7.2.0))(supports-color@7.2.0)(typescript@6.0.3) + eslint: 9.39.5(supports-color@7.2.0) typescript: 6.0.3 transitivePeerDependencies: - supports-color @@ -7540,7 +6866,7 @@ snapshots: '@quansync/fs': 1.0.0 quansync: 1.0.0 - undici-types@7.8.0: {} + undici-types@8.3.0: {} undici@7.29.0: {} @@ -7587,11 +6913,6 @@ snapshots: '@unrs/resolver-binding-win32-ia32-msvc': 1.12.2 '@unrs/resolver-binding-win32-x64-msvc': 1.12.2 - unrun@0.2.39: - dependencies: - rolldown: 1.0.0-rc.17 - optional: true - update-browserslist-db@1.3.2(browserslist@4.28.8): dependencies: browserslist: 4.28.8 @@ -7611,80 +6932,47 @@ snapshots: spdx-correct: 3.2.0 spdx-expression-parse: 3.0.1 - vite-node@3.2.4(@types/node@24.0.0): - dependencies: - cac: 6.7.14 - debug: 4.4.3 - es-module-lexer: 1.7.0 - pathe: 2.0.3 - vite: 7.3.5(@types/node@24.0.0) - transitivePeerDependencies: - - '@types/node' - - jiti - - less - - lightningcss - - sass - - sass-embedded - - stylus - - sugarss - - supports-color - - terser - - tsx - - yaml + verkit@0.3.2: {} - vite@7.3.5(@types/node@24.0.0): + vite@8.2.2(@types/node@26.4.1): dependencies: - esbuild: 0.27.2 - fdir: 6.5.0(picomatch@4.0.4) - picomatch: 4.0.4 + lightningcss: 1.33.0 + picomatch: 4.0.7 postcss: 8.5.23 - rollup: 4.62.2 + rolldown: 1.2.7 tinyglobby: 0.2.17 optionalDependencies: - '@types/node': 24.0.0 + '@types/node': 26.4.1 fsevents: 2.3.3 - vitest@3.2.6(@types/node@24.0.0)(jsdom@29.1.1): - dependencies: - '@types/chai': 5.2.3 - '@vitest/expect': 3.2.6 - '@vitest/mocker': 3.2.6(vite@7.3.5(@types/node@24.0.0)) - '@vitest/pretty-format': 3.2.6 - '@vitest/runner': 3.2.6 - '@vitest/snapshot': 3.2.6 - '@vitest/spy': 3.2.6 - '@vitest/utils': 3.2.6 - chai: 5.3.3 - debug: 4.4.3 - expect-type: 1.3.0 + vitest@4.1.11(@types/node@26.4.1)(@vitest/coverage-v8@4.1.11)(jsdom@30.0.1)(vite@8.2.2(@types/node@26.4.1)): + dependencies: + '@vitest/expect': 4.1.11 + '@vitest/mocker': 4.1.11(vite@8.2.2(@types/node@26.4.1)) + '@vitest/pretty-format': 4.1.11 + '@vitest/runner': 4.1.11 + '@vitest/snapshot': 4.1.11 + '@vitest/spy': 4.1.11 + '@vitest/utils': 4.1.11 + es-module-lexer: 2.3.2 + expect-type: 1.4.0 magic-string: 0.30.21 + obug: 2.1.4 pathe: 2.0.3 - picomatch: 4.0.4 - std-env: 3.10.0 + picomatch: 4.0.7 + std-env: 4.2.0 tinybench: 2.9.0 - tinyexec: 0.3.2 + tinyexec: 1.3.0 tinyglobby: 0.2.17 - tinypool: 1.1.1 - tinyrainbow: 2.0.0 - vite: 7.3.5(@types/node@24.0.0) - vite-node: 3.2.4(@types/node@24.0.0) + tinyrainbow: 3.1.1 + vite: 8.2.2(@types/node@26.4.1) why-is-node-running: 2.3.0 optionalDependencies: - '@types/node': 24.0.0 - jsdom: 29.1.1 + '@types/node': 26.4.1 + '@vitest/coverage-v8': 4.1.11(vitest@4.1.11) + jsdom: 30.0.1 transitivePeerDependencies: - - jiti - - less - - lightningcss - msw - - sass - - sass-embedded - - stylus - - sugarss - - supports-color - - terser - - tsx - - yaml w3c-xmlserializer@5.0.0: dependencies: @@ -7704,6 +6992,14 @@ snapshots: transitivePeerDependencies: - '@noble/hashes' + whatwg-url@17.1.0: + dependencies: + '@exodus/bytes': 1.15.1 + tr46: 6.0.0 + webidl-conversions: 8.0.1 + transitivePeerDependencies: + - '@noble/hashes' + which-boxed-primitive@1.1.1: dependencies: is-bigint: 1.1.0 @@ -7735,6 +7031,8 @@ snapshots: is-weakmap: 2.0.2 is-weakset: 2.0.4 + which-command@0.1.0: {} + which-typed-array@1.1.22: dependencies: available-typed-arrays: 1.0.7 @@ -7764,12 +7062,6 @@ snapshots: string-width: 4.2.3 strip-ansi: 6.0.1 - wrap-ansi@8.1.0: - dependencies: - ansi-styles: 6.2.3 - string-width: 5.1.2 - strip-ansi: 7.2.0 - wrap-ansi@9.0.2: dependencies: ansi-styles: 6.2.3 @@ -7800,21 +7092,60 @@ snapshots: y18n: 5.0.8 yargs-parser: 20.2.9 - yargs@18.0.0: + yargs@18.1.0: dependencies: cliui: 9.0.1 escalade: 3.2.0 get-caller-file: 2.0.5 - string-width: 7.2.0 + string-width: 8.2.2 y18n: 5.0.8 yargs-parser: 22.0.0 yocto-queue@0.1.0: {} - yoctocolors@2.1.2: {} + yoctocolors@2.2.0: {} - zod-validation-error@4.0.2(zod@4.4.3): + yuku-ast@0.8.7: dependencies: - zod: 4.4.3 + '@yuku-toolchain/types': 0.8.7 - zod@4.4.3: {} + yuku-codegen@0.8.7: + dependencies: + '@yuku-toolchain/types': 0.8.7 + optionalDependencies: + '@yuku-codegen/binding-android-arm64': 0.8.7 + '@yuku-codegen/binding-darwin-arm64': 0.8.7 + '@yuku-codegen/binding-darwin-x64': 0.8.7 + '@yuku-codegen/binding-freebsd-x64': 0.8.7 + '@yuku-codegen/binding-linux-arm-gnu': 0.8.7 + '@yuku-codegen/binding-linux-arm-musl': 0.8.7 + '@yuku-codegen/binding-linux-arm64-gnu': 0.8.7 + '@yuku-codegen/binding-linux-arm64-musl': 0.8.7 + '@yuku-codegen/binding-linux-x64-gnu': 0.8.7 + '@yuku-codegen/binding-linux-x64-musl': 0.8.7 + '@yuku-codegen/binding-win32-arm64': 0.8.7 + '@yuku-codegen/binding-win32-x64': 0.8.7 + + yuku-parser@0.8.7: + dependencies: + '@yuku-toolchain/types': 0.8.7 + yuku-ast: 0.8.7 + optionalDependencies: + '@yuku-parser/binding-android-arm64': 0.8.7 + '@yuku-parser/binding-darwin-arm64': 0.8.7 + '@yuku-parser/binding-darwin-x64': 0.8.7 + '@yuku-parser/binding-freebsd-x64': 0.8.7 + '@yuku-parser/binding-linux-arm-gnu': 0.8.7 + '@yuku-parser/binding-linux-arm-musl': 0.8.7 + '@yuku-parser/binding-linux-arm64-gnu': 0.8.7 + '@yuku-parser/binding-linux-arm64-musl': 0.8.7 + '@yuku-parser/binding-linux-x64-gnu': 0.8.7 + '@yuku-parser/binding-linux-x64-musl': 0.8.7 + '@yuku-parser/binding-win32-arm64': 0.8.7 + '@yuku-parser/binding-win32-x64': 0.8.7 + + zod-validation-error@4.0.2(zod@4.5.4): + dependencies: + zod: 4.5.4 + + zod@4.5.4: {} diff --git a/test/helpers/renderStack.tsx b/test/helpers/renderStack.tsx index c376692..fd9f700 100644 --- a/test/helpers/renderStack.tsx +++ b/test/helpers/renderStack.tsx @@ -1,9 +1,7 @@ import { render, act } from '@testing-library/react'; -import type { ReactElement } from 'react'; import { NavigationStackProvider } from '../../src/components/NavigationStackProvider'; import { NavigationStackViewport } from '../../src/components/NavigationStackViewport'; -import type { NavigationStackController } from '../../src/controller/NavigationStackController'; import type { NavigationStackState, NavigationStackId, @@ -24,7 +22,6 @@ export interface RenderStackOptions { export interface RenderStackResult { container: HTMLElement; - getController: () => NavigationStackController; unmount: () => void; } @@ -34,14 +31,6 @@ export function renderStack( ): RenderStackResult { const stackId = options.stackId ?? 'test-stack'; - const controllerRef: NavigationStackController | null = null; - - function ControllerCapture(): ReactElement | null { - // Capture controller via context lazily in tests rather than a ref in render - return null; - } - void ControllerCapture; - const baseProps = { id: stackId, routes, @@ -78,12 +67,6 @@ export function renderStack( return { container, - getController: () => { - if (!controllerRef) { - throw new Error('Controller not captured yet'); - } - return controllerRef; - }, unmount, }; } diff --git a/test/types/public-api.test-d.ts b/test/types/public-api.test-d.ts index 7f49c99..5a3cee0 100644 --- a/test/types/public-api.test-d.ts +++ b/test/types/public-api.test-d.ts @@ -94,7 +94,7 @@ const missingOnChange: NavigationStackProviderProps = { id: 'x', state: validState, }; -void missingOnChange; +expectTypeOf(missingOnChange).toExtend(); // --------------------------------------------------------------------------- // Uncontrolled provider — must not accept state or onStateChange