From cc1a803bdb448da1ed48c85aa8fb3d8d0213274b Mon Sep 17 00:00:00 2001 From: zuiidea Date: Tue, 14 Apr 2026 22:27:04 +0800 Subject: [PATCH 01/16] chore(create): scaffold create-antd-admin package Made-with: Cursor --- packages/create/package.json | 35 ++ packages/create/tsconfig.json | 15 + pnpm-lock.yaml | 1019 ++++++++++++++++++++++++++++++++- 3 files changed, 1042 insertions(+), 27 deletions(-) create mode 100644 packages/create/package.json create mode 100644 packages/create/tsconfig.json diff --git a/packages/create/package.json b/packages/create/package.json new file mode 100644 index 0000000..7869850 --- /dev/null +++ b/packages/create/package.json @@ -0,0 +1,35 @@ +{ + "name": "create-antd-admin", + "version": "6.0.0", + "description": "Create an Antd Admin app from official examples", + "license": "MIT", + "type": "module", + "bin": { + "create-antd-admin": "./dist/cli.js" + }, + "files": [ + "dist" + ], + "scripts": { + "build": "tsup && node ./scripts/write-examples-json.mjs", + "dev": "tsup --watch", + "check-types": "tsc --noEmit", + "test": "vitest run", + "test:watch": "vitest" + }, + "engines": { + "node": ">=20" + }, + "dependencies": { + "@inquirer/prompts": "^7.10.1", + "commander": "^14.0.0", + "giget": "^3.2.0", + "picocolors": "^1.0.1" + }, + "devDependencies": { + "@types/node": "^22.10.0", + "tsup": "^8.3.5", + "typescript": "~5.9.3", + "vitest": "^3.0.5" + } +} diff --git a/packages/create/tsconfig.json b/packages/create/tsconfig.json new file mode 100644 index 0000000..3527578 --- /dev/null +++ b/packages/create/tsconfig.json @@ -0,0 +1,15 @@ +{ + "compilerOptions": { + "target": "ES2022", + "module": "ESNext", + "moduleResolution": "Bundler", + "strict": true, + "skipLibCheck": true, + "noEmit": true, + "types": ["node"], + "resolveJsonModule": true, + "rootDir": ".", + "verbatimModuleSyntax": true + }, + "include": ["src/**/*.ts", "tsup.config.ts", "vitest.config.ts"] +} diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 062273d..e7c17d4 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -143,6 +143,34 @@ importers: specifier: latest version: 0.1.16(@voidzero-dev/vite-plus-core@0.1.16)(typescript@5.9.3) + packages/create: + dependencies: + '@inquirer/prompts': + specifier: ^7.10.1 + version: 7.10.1(@types/node@22.19.17) + commander: + specifier: ^14.0.0 + version: 14.0.3 + giget: + specifier: ^3.2.0 + version: 3.2.0 + picocolors: + specifier: ^1.0.1 + version: 1.1.1 + devDependencies: + '@types/node': + specifier: ^22.10.0 + version: 22.19.17 + tsup: + specifier: ^8.3.5 + version: 8.5.1(typescript@5.9.3) + typescript: + specifier: ~5.9.3 + version: 5.9.3 + vitest: + specifier: ^3.0.5 + version: 3.2.4(@types/node@22.19.17) + packages: /@ant-design/colors@8.0.1: @@ -921,9 +949,25 @@ packages: /@inquirer/ansi@1.0.2: resolution: {integrity: sha512-S8qNSZiYzFd0wAcyG5AXCvUHC5Sr7xpZ9wZ2py9XR88jUz8wooStVx5M6dRzczbBWjic9NP7+rY0Xi7qqK/aMQ==} engines: {node: '>=18'} - dev: true - /@inquirer/confirm@5.1.21: + /@inquirer/checkbox@4.3.2(@types/node@22.19.17): + resolution: {integrity: sha512-VXukHf0RR1doGe6Sm4F0Em7SWYLTHSsbGfJdS9Ja2bX5/D5uwVOEjr07cncLROdBvmnvCATYEWlHqYmXv2IlQA==} + engines: {node: '>=18'} + peerDependencies: + '@types/node': '>=18' + peerDependenciesMeta: + '@types/node': + optional: true + dependencies: + '@inquirer/ansi': 1.0.2 + '@inquirer/core': 10.3.2(@types/node@22.19.17) + '@inquirer/figures': 1.0.15 + '@inquirer/type': 3.0.10(@types/node@22.19.17) + '@types/node': 22.19.17 + yoctocolors-cjs: 2.1.3 + dev: false + + /@inquirer/confirm@5.1.21(@types/node@22.19.17): resolution: {integrity: sha512-KR8edRkIsUayMXV+o3Gv+q4jlhENF9nMYUZs9PA2HzrXeHI8M5uDag70U7RJn9yyiMZSbtF5/UexBtAVtZGSbQ==} engines: {node: '>=18'} peerDependencies: @@ -932,11 +976,11 @@ packages: '@types/node': optional: true dependencies: - '@inquirer/core': 10.3.2 - '@inquirer/type': 3.0.10 - dev: true + '@inquirer/core': 10.3.2(@types/node@22.19.17) + '@inquirer/type': 3.0.10(@types/node@22.19.17) + '@types/node': 22.19.17 - /@inquirer/core@10.3.2: + /@inquirer/core@10.3.2(@types/node@22.19.17): resolution: {integrity: sha512-43RTuEbfP8MbKzedNqBrlhhNKVwoK//vUFNW3Q3vZ88BLcrs4kYpGg+B2mm5p2K/HfygoCxuKwJJiv8PbGmE0A==} engines: {node: '>=18'} peerDependencies: @@ -947,20 +991,176 @@ packages: dependencies: '@inquirer/ansi': 1.0.2 '@inquirer/figures': 1.0.15 - '@inquirer/type': 3.0.10 + '@inquirer/type': 3.0.10(@types/node@22.19.17) + '@types/node': 22.19.17 cli-width: 4.1.0 mute-stream: 2.0.0 signal-exit: 4.1.0 wrap-ansi: 6.2.0 yoctocolors-cjs: 2.1.3 - dev: true + + /@inquirer/editor@4.2.23(@types/node@22.19.17): + resolution: {integrity: sha512-aLSROkEwirotxZ1pBaP8tugXRFCxW94gwrQLxXfrZsKkfjOYC1aRvAZuhpJOb5cu4IBTJdsCigUlf2iCOu4ZDQ==} + engines: {node: '>=18'} + peerDependencies: + '@types/node': '>=18' + peerDependenciesMeta: + '@types/node': + optional: true + dependencies: + '@inquirer/core': 10.3.2(@types/node@22.19.17) + '@inquirer/external-editor': 1.0.3(@types/node@22.19.17) + '@inquirer/type': 3.0.10(@types/node@22.19.17) + '@types/node': 22.19.17 + dev: false + + /@inquirer/expand@4.0.23(@types/node@22.19.17): + resolution: {integrity: sha512-nRzdOyFYnpeYTTR2qFwEVmIWypzdAx/sIkCMeTNTcflFOovfqUk+HcFhQQVBftAh9gmGrpFj6QcGEqrDMDOiew==} + engines: {node: '>=18'} + peerDependencies: + '@types/node': '>=18' + peerDependenciesMeta: + '@types/node': + optional: true + dependencies: + '@inquirer/core': 10.3.2(@types/node@22.19.17) + '@inquirer/type': 3.0.10(@types/node@22.19.17) + '@types/node': 22.19.17 + yoctocolors-cjs: 2.1.3 + dev: false + + /@inquirer/external-editor@1.0.3(@types/node@22.19.17): + resolution: {integrity: sha512-RWbSrDiYmO4LbejWY7ttpxczuwQyZLBUyygsA9Nsv95hpzUWwnNTVQmAq3xuh7vNwCp07UTmE5i11XAEExx4RA==} + engines: {node: '>=18'} + peerDependencies: + '@types/node': '>=18' + peerDependenciesMeta: + '@types/node': + optional: true + dependencies: + '@types/node': 22.19.17 + chardet: 2.1.1 + iconv-lite: 0.7.2 + dev: false /@inquirer/figures@1.0.15: resolution: {integrity: sha512-t2IEY+unGHOzAaVM5Xx6DEWKeXlDDcNPeDyUpsRc6CUhBfU3VQOEl+Vssh7VNp1dR8MdUJBWhuObjXCsVpjN5g==} engines: {node: '>=18'} - dev: true - /@inquirer/type@3.0.10: + /@inquirer/input@4.3.1(@types/node@22.19.17): + resolution: {integrity: sha512-kN0pAM4yPrLjJ1XJBjDxyfDduXOuQHrBB8aLDMueuwUGn+vNpF7Gq7TvyVxx8u4SHlFFj4trmj+a2cbpG4Jn1g==} + engines: {node: '>=18'} + peerDependencies: + '@types/node': '>=18' + peerDependenciesMeta: + '@types/node': + optional: true + dependencies: + '@inquirer/core': 10.3.2(@types/node@22.19.17) + '@inquirer/type': 3.0.10(@types/node@22.19.17) + '@types/node': 22.19.17 + dev: false + + /@inquirer/number@3.0.23(@types/node@22.19.17): + resolution: {integrity: sha512-5Smv0OK7K0KUzUfYUXDXQc9jrf8OHo4ktlEayFlelCjwMXz0299Y8OrI+lj7i4gCBY15UObk76q0QtxjzFcFcg==} + engines: {node: '>=18'} + peerDependencies: + '@types/node': '>=18' + peerDependenciesMeta: + '@types/node': + optional: true + dependencies: + '@inquirer/core': 10.3.2(@types/node@22.19.17) + '@inquirer/type': 3.0.10(@types/node@22.19.17) + '@types/node': 22.19.17 + dev: false + + /@inquirer/password@4.0.23(@types/node@22.19.17): + resolution: {integrity: sha512-zREJHjhT5vJBMZX/IUbyI9zVtVfOLiTO66MrF/3GFZYZ7T4YILW5MSkEYHceSii/KtRk+4i3RE7E1CUXA2jHcA==} + engines: {node: '>=18'} + peerDependencies: + '@types/node': '>=18' + peerDependenciesMeta: + '@types/node': + optional: true + dependencies: + '@inquirer/ansi': 1.0.2 + '@inquirer/core': 10.3.2(@types/node@22.19.17) + '@inquirer/type': 3.0.10(@types/node@22.19.17) + '@types/node': 22.19.17 + dev: false + + /@inquirer/prompts@7.10.1(@types/node@22.19.17): + resolution: {integrity: sha512-Dx/y9bCQcXLI5ooQ5KyvA4FTgeo2jYj/7plWfV5Ak5wDPKQZgudKez2ixyfz7tKXzcJciTxqLeK7R9HItwiByg==} + engines: {node: '>=18'} + peerDependencies: + '@types/node': '>=18' + peerDependenciesMeta: + '@types/node': + optional: true + dependencies: + '@inquirer/checkbox': 4.3.2(@types/node@22.19.17) + '@inquirer/confirm': 5.1.21(@types/node@22.19.17) + '@inquirer/editor': 4.2.23(@types/node@22.19.17) + '@inquirer/expand': 4.0.23(@types/node@22.19.17) + '@inquirer/input': 4.3.1(@types/node@22.19.17) + '@inquirer/number': 3.0.23(@types/node@22.19.17) + '@inquirer/password': 4.0.23(@types/node@22.19.17) + '@inquirer/rawlist': 4.1.11(@types/node@22.19.17) + '@inquirer/search': 3.2.2(@types/node@22.19.17) + '@inquirer/select': 4.4.2(@types/node@22.19.17) + '@types/node': 22.19.17 + dev: false + + /@inquirer/rawlist@4.1.11(@types/node@22.19.17): + resolution: {integrity: sha512-+LLQB8XGr3I5LZN/GuAHo+GpDJegQwuPARLChlMICNdwW7OwV2izlCSCxN6cqpL0sMXmbKbFcItJgdQq5EBXTw==} + engines: {node: '>=18'} + peerDependencies: + '@types/node': '>=18' + peerDependenciesMeta: + '@types/node': + optional: true + dependencies: + '@inquirer/core': 10.3.2(@types/node@22.19.17) + '@inquirer/type': 3.0.10(@types/node@22.19.17) + '@types/node': 22.19.17 + yoctocolors-cjs: 2.1.3 + dev: false + + /@inquirer/search@3.2.2(@types/node@22.19.17): + resolution: {integrity: sha512-p2bvRfENXCZdWF/U2BXvnSI9h+tuA8iNqtUKb9UWbmLYCRQxd8WkvwWvYn+3NgYaNwdUkHytJMGG4MMLucI1kA==} + engines: {node: '>=18'} + peerDependencies: + '@types/node': '>=18' + peerDependenciesMeta: + '@types/node': + optional: true + dependencies: + '@inquirer/core': 10.3.2(@types/node@22.19.17) + '@inquirer/figures': 1.0.15 + '@inquirer/type': 3.0.10(@types/node@22.19.17) + '@types/node': 22.19.17 + yoctocolors-cjs: 2.1.3 + dev: false + + /@inquirer/select@4.4.2(@types/node@22.19.17): + resolution: {integrity: sha512-l4xMuJo55MAe+N7Qr4rX90vypFwCajSakx59qe/tMaC1aEHWLyw68wF4o0A4SLAY4E0nd+Vt+EyskeDIqu1M6w==} + engines: {node: '>=18'} + peerDependencies: + '@types/node': '>=18' + peerDependenciesMeta: + '@types/node': + optional: true + dependencies: + '@inquirer/ansi': 1.0.2 + '@inquirer/core': 10.3.2(@types/node@22.19.17) + '@inquirer/figures': 1.0.15 + '@inquirer/type': 3.0.10(@types/node@22.19.17) + '@types/node': 22.19.17 + yoctocolors-cjs: 2.1.3 + dev: false + + /@inquirer/type@3.0.10(@types/node@22.19.17): resolution: {integrity: sha512-BvziSRxfz5Ov8ch0z/n3oijRSEcEsHnhggm4xFZe93DHcUCTlutlq9Ox4SVENAfcRD22UQq7T/atg9Wr3k09eA==} engines: {node: '>=18'} peerDependencies: @@ -968,7 +1168,8 @@ packages: peerDependenciesMeta: '@types/node': optional: true - dev: true + dependencies: + '@types/node': 22.19.17 /@isaacs/cliui@9.0.0: resolution: {integrity: sha512-AokJm4tuBHillT+FpMtxQ60n8ObyXBatq7jD2/JA9dxbDDokKQm8KMht5ibGzLVU9IJDIKK4TPKgMHEYMn3lMg==} @@ -988,7 +1189,7 @@ packages: '@jest/schemas': 29.6.3 '@types/istanbul-lib-coverage': 2.0.6 '@types/istanbul-reports': 3.0.4 - '@types/node': 25.6.0 + '@types/node': 22.19.17 '@types/yargs': 17.0.35 chalk: 4.1.2 @@ -2227,6 +2428,206 @@ packages: resolution: {integrity: sha512-qujRfC8sFVInYSPPMLQByRh7zhwkGFS4+tyMQ83srV1qrxL4g8E2tyxVVyxd0+8QeBM1mIk9KbWxkegRr76XzA==} dev: true + /@rollup/rollup-android-arm-eabi@4.60.1: + resolution: {integrity: sha512-d6FinEBLdIiK+1uACUttJKfgZREXrF0Qc2SmLII7W2AD8FfiZ9Wjd+rD/iRuf5s5dWrr1GgwXCvPqOuDquOowA==} + cpu: [arm] + os: [android] + requiresBuild: true + dev: true + optional: true + + /@rollup/rollup-android-arm64@4.60.1: + resolution: {integrity: sha512-YjG/EwIDvvYI1YvYbHvDz/BYHtkY4ygUIXHnTdLhG+hKIQFBiosfWiACWortsKPKU/+dUwQQCKQM3qrDe8c9BA==} + cpu: [arm64] + os: [android] + requiresBuild: true + dev: true + optional: true + + /@rollup/rollup-darwin-arm64@4.60.1: + resolution: {integrity: sha512-mjCpF7GmkRtSJwon+Rq1N8+pI+8l7w5g9Z3vWj4T7abguC4Czwi3Yu/pFaLvA3TTeMVjnu3ctigusqWUfjZzvw==} + cpu: [arm64] + os: [darwin] + requiresBuild: true + dev: true + optional: true + + /@rollup/rollup-darwin-x64@4.60.1: + resolution: {integrity: sha512-haZ7hJ1JT4e9hqkoT9R/19XW2QKqjfJVv+i5AGg57S+nLk9lQnJ1F/eZloRO3o9Scy9CM3wQ9l+dkXtcBgN5Ew==} + cpu: [x64] + os: [darwin] + requiresBuild: true + dev: true + optional: true + + /@rollup/rollup-freebsd-arm64@4.60.1: + resolution: {integrity: sha512-czw90wpQq3ZsAVBlinZjAYTKduOjTywlG7fEeWKUA7oCmpA8xdTkxZZlwNJKWqILlq0wehoZcJYfBvOyhPTQ6w==} + cpu: [arm64] + os: [freebsd] + requiresBuild: true + dev: true + optional: true + + /@rollup/rollup-freebsd-x64@4.60.1: + resolution: {integrity: sha512-KVB2rqsxTHuBtfOeySEyzEOB7ltlB/ux38iu2rBQzkjbwRVlkhAGIEDiiYnO2kFOkJp+Z7pUXKyrRRFuFUKt+g==} + cpu: [x64] + os: [freebsd] + requiresBuild: true + dev: true + optional: true + + /@rollup/rollup-linux-arm-gnueabihf@4.60.1: + resolution: {integrity: sha512-L+34Qqil+v5uC0zEubW7uByo78WOCIrBvci69E7sFASRl0X7b/MB6Cqd1lky/CtcSVTydWa2WZwFuWexjS5o6g==} + cpu: [arm] + os: [linux] + requiresBuild: true + dev: true + optional: true + + /@rollup/rollup-linux-arm-musleabihf@4.60.1: + resolution: {integrity: sha512-n83O8rt4v34hgFzlkb1ycniJh7IR5RCIqt6mz1VRJD6pmhRi0CXdmfnLu9dIUS6buzh60IvACM842Ffb3xd6Gg==} + cpu: [arm] + os: [linux] + requiresBuild: true + dev: true + optional: true + + /@rollup/rollup-linux-arm64-gnu@4.60.1: + resolution: {integrity: sha512-Nql7sTeAzhTAja3QXeAI48+/+GjBJ+QmAH13snn0AJSNL50JsDqotyudHyMbO2RbJkskbMbFJfIJKWA6R1LCJQ==} + cpu: [arm64] + os: [linux] + requiresBuild: true + dev: true + optional: true + + /@rollup/rollup-linux-arm64-musl@4.60.1: + resolution: {integrity: sha512-+pUymDhd0ys9GcKZPPWlFiZ67sTWV5UU6zOJat02M1+PiuSGDziyRuI/pPue3hoUwm2uGfxdL+trT6Z9rxnlMA==} + cpu: [arm64] + os: [linux] + requiresBuild: true + dev: true + optional: true + + /@rollup/rollup-linux-loong64-gnu@4.60.1: + resolution: {integrity: sha512-VSvgvQeIcsEvY4bKDHEDWcpW4Yw7BtlKG1GUT4FzBUlEKQK0rWHYBqQt6Fm2taXS+1bXvJT6kICu5ZwqKCnvlQ==} + cpu: [loong64] + os: [linux] + requiresBuild: true + dev: true + optional: true + + /@rollup/rollup-linux-loong64-musl@4.60.1: + resolution: {integrity: sha512-4LqhUomJqwe641gsPp6xLfhqWMbQV04KtPp7/dIp0nzPxAkNY1AbwL5W0MQpcalLYk07vaW9Kp1PBhdpZYYcEw==} + cpu: [loong64] + os: [linux] + requiresBuild: true + dev: true + optional: true + + /@rollup/rollup-linux-ppc64-gnu@4.60.1: + resolution: {integrity: sha512-tLQQ9aPvkBxOc/EUT6j3pyeMD6Hb8QF2BTBnCQWP/uu1lhc9AIrIjKnLYMEroIz/JvtGYgI9dF3AxHZNaEH0rw==} + cpu: [ppc64] + os: [linux] + requiresBuild: true + dev: true + optional: true + + /@rollup/rollup-linux-ppc64-musl@4.60.1: + resolution: {integrity: sha512-RMxFhJwc9fSXP6PqmAz4cbv3kAyvD1etJFjTx4ONqFP9DkTkXsAMU4v3Vyc5BgzC+anz7nS/9tp4obsKfqkDHg==} + cpu: [ppc64] + os: [linux] + requiresBuild: true + dev: true + optional: true + + /@rollup/rollup-linux-riscv64-gnu@4.60.1: + resolution: {integrity: sha512-QKgFl+Yc1eEk6MmOBfRHYF6lTxiiiV3/z/BRrbSiW2I7AFTXoBFvdMEyglohPj//2mZS4hDOqeB0H1ACh3sBbg==} + cpu: [riscv64] + os: [linux] + requiresBuild: true + dev: true + optional: true + + /@rollup/rollup-linux-riscv64-musl@4.60.1: + resolution: {integrity: sha512-RAjXjP/8c6ZtzatZcA1RaQr6O1TRhzC+adn8YZDnChliZHviqIjmvFwHcxi4JKPSDAt6Uhf/7vqcBzQJy0PDJg==} + cpu: [riscv64] + os: [linux] + requiresBuild: true + dev: true + optional: true + + /@rollup/rollup-linux-s390x-gnu@4.60.1: + resolution: {integrity: sha512-wcuocpaOlaL1COBYiA89O6yfjlp3RwKDeTIA0hM7OpmhR1Bjo9j31G1uQVpDlTvwxGn2nQs65fBFL5UFd76FcQ==} + cpu: [s390x] + os: [linux] + requiresBuild: true + dev: true + optional: true + + /@rollup/rollup-linux-x64-gnu@4.60.1: + resolution: {integrity: sha512-77PpsFQUCOiZR9+LQEFg9GClyfkNXj1MP6wRnzYs0EeWbPcHs02AXu4xuUbM1zhwn3wqaizle3AEYg5aeoohhg==} + cpu: [x64] + os: [linux] + requiresBuild: true + dev: true + optional: true + + /@rollup/rollup-linux-x64-musl@4.60.1: + resolution: {integrity: sha512-5cIATbk5vynAjqqmyBjlciMJl1+R/CwX9oLk/EyiFXDWd95KpHdrOJT//rnUl4cUcskrd0jCCw3wpZnhIHdD9w==} + cpu: [x64] + os: [linux] + requiresBuild: true + dev: true + optional: true + + /@rollup/rollup-openbsd-x64@4.60.1: + resolution: {integrity: sha512-cl0w09WsCi17mcmWqqglez9Gk8isgeWvoUZ3WiJFYSR3zjBQc2J5/ihSjpl+VLjPqjQ/1hJRcqBfLjssREQILw==} + cpu: [x64] + os: [openbsd] + requiresBuild: true + dev: true + optional: true + + /@rollup/rollup-openharmony-arm64@4.60.1: + resolution: {integrity: sha512-4Cv23ZrONRbNtbZa37mLSueXUCtN7MXccChtKpUnQNgF010rjrjfHx3QxkS2PI7LqGT5xXyYs1a7LbzAwT0iCA==} + cpu: [arm64] + os: [openharmony] + requiresBuild: true + dev: true + optional: true + + /@rollup/rollup-win32-arm64-msvc@4.60.1: + resolution: {integrity: sha512-i1okWYkA4FJICtr7KpYzFpRTHgy5jdDbZiWfvny21iIKky5YExiDXP+zbXzm3dUcFpkEeYNHgQ5fuG236JPq0g==} + cpu: [arm64] + os: [win32] + requiresBuild: true + dev: true + optional: true + + /@rollup/rollup-win32-ia32-msvc@4.60.1: + resolution: {integrity: sha512-u09m3CuwLzShA0EYKMNiFgcjjzwqtUMLmuCJLeZWjjOYA3IT2Di09KaxGBTP9xVztWyIWjVdsB2E9goMjZvTQg==} + cpu: [ia32] + os: [win32] + requiresBuild: true + dev: true + optional: true + + /@rollup/rollup-win32-x64-gnu@4.60.1: + resolution: {integrity: sha512-k+600V9Zl1CM7eZxJgMyTUzmrmhB/0XZnF4pRypKAlAgxmedUA+1v9R+XOFv56W4SlHEzfeMtzujLJD22Uz5zg==} + cpu: [x64] + os: [win32] + requiresBuild: true + dev: true + optional: true + + /@rollup/rollup-win32-x64-msvc@4.60.1: + resolution: {integrity: sha512-lWMnixq/QzxyhTV6NjQJ4SFo1J6PvOX8vUx5Wb4bBPsEb+8xZ89Bz6kOXpfXj9ak9AHTQVQzlgzBEc1SyM27xQ==} + cpu: [x64] + os: [win32] + requiresBuild: true + dev: true + optional: true + /@sinclair/typebox@0.27.10: resolution: {integrity: sha512-MTBk/3jGLNB2tVxv6uLlFh1iu64iYOQ2PbdOSK3NW8JZsmlaOh2q6sdtKowBhfw8QFLmYNzTW4/oK4uATIi6ZA==} @@ -2573,6 +2974,10 @@ packages: resolution: {integrity: sha512-c9h9dVVMigMPc4bwTvC5dxqtqJZwQPePsWjPlpSOnojbor6pGqdk541lfA7AqFQr5pB1BRdq0juY9db81BwyFw==} dev: true + /@types/estree@1.0.8: + resolution: {integrity: sha512-dWHzHa2WqEXI/O1E9OjrocMTKJl2mSrEolh1Iomrv6U+JuNwaHXsXx9bLu5gG7BUWFIN0skIQJQ/L1rIex4X6w==} + dev: true + /@types/istanbul-lib-coverage@2.0.6: resolution: {integrity: sha512-2QF/t/auWm0lsy8XtKVPG19v3sSOQlJe/YHZgfjb/KBBHOGSV+J2q/S671rcq9uTBrLAXmZpqJiaQbMT+zNU1w==} @@ -2586,10 +2991,10 @@ packages: dependencies: '@types/istanbul-lib-report': 3.0.3 - /@types/node@25.6.0: - resolution: {integrity: sha512-+qIYRKdNYJwY3vRCZMdJbPLJAtGjQBudzZzdzwQYkEPQd+PJGixUL5QfvCLDaULoLv+RhT3LDkwEfKaAkgSmNQ==} + /@types/node@22.19.17: + resolution: {integrity: sha512-wGdMcf+vPYM6jikpS/qhg6WiqSV/OhG+jeeHT/KlVqxYfD40iYJf9/AE1uQxVWFvU7MipKRkRv8NSHiCGgPr8Q==} dependencies: - undici-types: 7.19.2 + undici-types: 6.21.0 /@types/react-dom@19.2.3(@types/react@19.2.14): resolution: {integrity: sha512-jp2L/eY6fn+KgVVQAOqYItbF0VY/YApe5Mz2F0aykSO8gx31bYCZyvSeYxCHKvzHG5eZjc+zyaS5BrBWya2+kQ==} @@ -2633,6 +3038,69 @@ packages: - '@swc/helpers' dev: true + /@vitest/expect@3.2.4: + resolution: {integrity: sha512-Io0yyORnB6sikFlt8QW5K7slY4OjqNX9jmJQ02QDda8lyM6B5oNgVWoSoKPac8/kgnCUzuHQKrSLtu/uOqqrig==} + dependencies: + '@types/chai': 5.2.3 + '@vitest/spy': 3.2.4 + '@vitest/utils': 3.2.4 + chai: 5.3.3 + tinyrainbow: 2.0.0 + dev: true + + /@vitest/mocker@3.2.4(vite@7.3.2): + resolution: {integrity: sha512-46ryTE9RZO/rfDd7pEqFl7etuyzekzEhUbTW3BvmeO/BcCMEgq59BKhek3dXDWgAj4oMK6OZi+vRr1wPW6qjEQ==} + peerDependencies: + msw: ^2.4.9 + vite: ^5.0.0 || ^6.0.0 || ^7.0.0-0 + peerDependenciesMeta: + msw: + optional: true + vite: + optional: true + dependencies: + '@vitest/spy': 3.2.4 + estree-walker: 3.0.3 + magic-string: 0.30.21 + vite: 7.3.2(@types/node@22.19.17) + dev: true + + /@vitest/pretty-format@3.2.4: + resolution: {integrity: sha512-IVNZik8IVRJRTr9fxlitMKeJeXFFFN0JaB9PHPGQ8NKQbGpfjlTx9zO4RefN8gp7eqjNy8nyK3NZmBzOPeIxtA==} + dependencies: + tinyrainbow: 2.0.0 + dev: true + + /@vitest/runner@3.2.4: + resolution: {integrity: sha512-oukfKT9Mk41LreEW09vt45f8wx7DordoWUZMYdY/cyAk7w5TWkTRCNZYF7sX7n2wB7jyGAl74OxgwhPgKaqDMQ==} + dependencies: + '@vitest/utils': 3.2.4 + pathe: 2.0.3 + strip-literal: 3.1.0 + dev: true + + /@vitest/snapshot@3.2.4: + resolution: {integrity: sha512-dEYtS7qQP2CjU27QBC5oUOxLE/v5eLkGqPE0ZKEIDGMs4vKWe7IjgLOeauHsR0D5YuuycGRO5oSRXnwnmA78fQ==} + dependencies: + '@vitest/pretty-format': 3.2.4 + magic-string: 0.30.21 + pathe: 2.0.3 + dev: true + + /@vitest/spy@3.2.4: + resolution: {integrity: sha512-vAfasCOe6AIK70iP5UD11Ac4siNUNJ9i/9PZ3NKx07sG6sUxeag1LWdNrMWeKKYBLlzuK+Gn65Yd5nyL6ds+nw==} + dependencies: + tinyspy: 4.0.4 + dev: true + + /@vitest/utils@3.2.4: + resolution: {integrity: sha512-fB2V0JFrQSMsCo9HiSq3Ezpdv4iYaXRG1Sx8edX3MwxfyNn83mKiGzOcH+Fkxt4MHxr3y42fQi1oeAInqgX2QA==} + dependencies: + '@vitest/pretty-format': 3.2.4 + loupe: 3.2.1 + tinyrainbow: 2.0.0 + dev: true + /@voidzero-dev/vite-plus-core@0.1.16(typescript@5.9.3): resolution: {integrity: sha512-fOyf14CXjcXqANFs2fCXEX+0Tn9ZjmqfFV+qTnARwIF1Kzl8WquO4XtvlDgs/fTQ91H4AyoNUgkvWdKS+C4xYA==} engines: {node: ^20.19.0 || >=22.12.0} @@ -2861,7 +3329,6 @@ packages: /ansi-regex@5.0.1: resolution: {integrity: sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ==} engines: {node: '>=8'} - dev: true /ansi-styles@4.3.0: resolution: {integrity: sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==} @@ -2940,6 +3407,10 @@ packages: - moment dev: false + /any-promise@1.3.0: + resolution: {integrity: sha512-7UvmKalWRt1wgjL1RrGxoSJW/0QZFIegpeGvZG9kjp8vrRu55XTHbwnqq2GpXm9uLbcuhxm3IqX9OB4MZR1b2A==} + dev: true + /anymatch@3.1.3: resolution: {integrity: sha512-KMReFUr0B4t+D+OBkjR3KYqvocp2XaSzO55UcB6mgQMd3KbcE+mWTyvVV7D/zsdEbNnV6acZUutkiHQXvTr1Rw==} engines: {node: '>= 8'} @@ -3037,6 +3508,21 @@ packages: ieee754: 1.2.1 dev: true + /bundle-require@5.1.0(esbuild@0.27.7): + resolution: {integrity: sha512-3WrrOuZiyaaZPWiEt4G3+IffISVC9HYlWueJEBWED4ZH4aIAC2PnkdnuRrR94M+w6yGWn4AglWtJtBI8YqvgoA==} + engines: {node: ^12.20.0 || ^14.13.1 || >=16.0.0} + peerDependencies: + esbuild: '>=0.18' + dependencies: + esbuild: 0.27.7 + load-tsconfig: 0.2.5 + dev: true + + /cac@6.7.14: + resolution: {integrity: sha512-b6Ilus+c3RrdDk+JhLKUAQfzzgLEPy6wcXqS7f/xe1EETvsDP6GORG7SFuOs6cID5YkqchW/LXZbX5bc8j7ZcQ==} + engines: {node: '>=8'} + dev: true + /callsites@3.1.0: resolution: {integrity: sha512-P8BjAsXvZS+VIDUI11hHCQEv74YT67YUi5JJFNWIqL235sBmjX4+qx9Muvls5ivyNENctx46xQLQ3aTuE7ssaQ==} engines: {node: '>=6'} @@ -3048,6 +3534,17 @@ packages: /caniuse-lite@1.0.30001788: resolution: {integrity: sha512-6q8HFp+lOQtcf7wBK+uEenxymVWkGKkjFpCvw5W25cmMwEDU45p1xQFBQv8JDlMMry7eNxyBaR+qxgmTUZkIRQ==} + /chai@5.3.3: + resolution: {integrity: sha512-4zNhdJD/iOjSH0A05ea+Ke6MU5mmpQcbQsSOkgdaUMJ9zTlDTD/GYlwohmIE2u0gaxHYiVHEn1Fw9mZ/ktJWgw==} + engines: {node: '>=18'} + dependencies: + assertion-error: 2.0.1 + check-error: 2.1.3 + deep-eql: 5.0.2 + loupe: 3.2.1 + pathval: 2.0.1 + dev: true + /chalk@4.1.2: resolution: {integrity: sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==} engines: {node: '>=10'} @@ -3055,6 +3552,15 @@ packages: ansi-styles: 4.3.0 supports-color: 7.2.0 + /chardet@2.1.1: + resolution: {integrity: sha512-PsezH1rqdV9VvyNhxxOW32/d75r01NY7TQCmOqomRo15ZSOKbpTFVsfjghxo6JloQUCGnH4k1LGu0R4yCLlWQQ==} + dev: false + + /check-error@2.1.3: + resolution: {integrity: sha512-PAJdDJusoxnwm1VwW07VWwUN1sl7smmC3OKggvndJFadxxDRyFJBX/ggnu/KE4kQAB7a3Dp8f/YXC1FlUprWmA==} + engines: {node: '>= 16'} + dev: true + /chokidar@3.5.1: resolution: {integrity: sha512-9+s+Od+W0VJJzawDma/gvBNQqkTiqYTWLuZoyAsivsI4AaWTCzHG06/TMjsf1cYe9Cb97UCEhjz7HvnPk2p/tw==} engines: {node: '>= 8.10.0'} @@ -3085,6 +3591,13 @@ packages: fsevents: 2.3.3 dev: true + /chokidar@4.0.3: + resolution: {integrity: sha512-Qgzu8kfBvo+cA4962jnP1KkS6Dop5NS6g7R5LFYJr4b8Ub94PPQXUksCw9PvXoeXPRRddRNC5C1JQUR2SMGtnA==} + engines: {node: '>= 14.16.0'} + dependencies: + readdirp: 4.1.2 + dev: true + /cli-cursor@3.1.0: resolution: {integrity: sha512-I/zHAwsKf9FqGoXM4WWRACob9+SNukZTd94DWF57E4toouRulbCxcUh6RKUEOQlYTHJnzkPMySvPNaaSLNfLZw==} engines: {node: '>=8'} @@ -3107,7 +3620,6 @@ packages: /cli-width@4.1.0: resolution: {integrity: sha512-ouuZd4/dm2Sw5Gmqy6bGyNNNe1qt9RpmxveLSO7KcgsTnU7RXfsw+/bukWGo1abgBiMAic068rclZsO4IWmmxQ==} engines: {node: '>= 12'} - dev: true /cliui@8.0.1: resolution: {integrity: sha512-BSeNnyus75C4//NQ9gQt1/csTXyo/8Sb+afLAkzAptFuMsod9HFokGNudZpi/oQV73hnVK+sR+5PVRMd+Dr7YQ==} @@ -3147,6 +3659,16 @@ packages: engines: {node: '>=14'} dev: true + /commander@14.0.3: + resolution: {integrity: sha512-H+y0Jo/T1RZ9qPP4Eh1pkcQcLRglraJaSLoyOtHxu6AapkjWVCy2Sit1QQ4x3Dng8qDlSsZEet7g5Pq06MvTgw==} + engines: {node: '>=20'} + dev: false + + /commander@4.1.1: + resolution: {integrity: sha512-NOKm8xhkzAjzFx8B2v5OAHT+u5pRQc2UCa2Vq9jYL/31o2wi9mxBA7LIFs3sV5VSC49z6pEhfbMULvShKj26WA==} + engines: {node: '>= 6'} + dev: true + /compute-scroll-into-view@3.1.1: resolution: {integrity: sha512-VRhuHOLoKYOy4UbilLbUzbYg93XLjv2PncJC50EuTWPA3gaja1UjBsUP/D/9/juV3vQFr6XBEzn9KCAHdUvOHw==} dev: false @@ -3155,6 +3677,15 @@ packages: resolution: {integrity: sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg==} dev: true + /confbox@0.1.8: + resolution: {integrity: sha512-RMtmw0iFkeR4YV+fUOSucriAQNb9g8zFR52MWCtl+cCZOFRNL6zeB395vPzFhEjjn4fMxXudmELnl/KF/WrK6w==} + dev: true + + /consola@3.4.2: + resolution: {integrity: sha512-5IKcdX0nnYavi6G7TtOhwkYzyjfJlatbjMjuLSfE2kYT5pMDOilZ4OvMhi637CcDICTmz3wARPoyhqyX1Y+XvA==} + engines: {node: ^14.18.0 || >=16.10.0} + dev: true + /convert-source-map@2.0.0: resolution: {integrity: sha512-Kvp459HrV2FEJ1CAsi1Ku+MY3kasH19TFykTz2xWmMeq6bk2NU3XXvfJ+Q61m0xktWwt+1HSYf3JZsTms3aRJg==} @@ -3212,6 +3743,11 @@ packages: dependencies: ms: 2.1.3 + /deep-eql@5.0.2: + resolution: {integrity: sha512-h5k/5U50IJJFpzfL6nO9jaaumfjO/f2NjK/oYB2Djzm4p9L+3T9qWpZqZ2hAbLPuuYq9wrU08WQyBTL5GbPk5Q==} + engines: {node: '>=6'} + dev: true + /deep-is@0.1.4: resolution: {integrity: sha512-oIPzksmTg4/MriiaYGO+okXDT7ztn/w3Eptv/+gSIdMdKsJo0u4CfYNFJPy+4SKMuCqGw2wxnA+URMg3t8a/bQ==} dev: true @@ -3244,7 +3780,6 @@ packages: /emoji-regex@8.0.0: resolution: {integrity: sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A==} - dev: true /error-ex@1.3.4: resolution: {integrity: sha512-sqQamAnR14VgCr1A618A3sGrygcpK+HEbenA/HiEAkkUwcZIIB/tgWqHFxWgOyDh4nB4JCRimh79dR5Ywc9MDQ==} @@ -3428,11 +3963,22 @@ packages: engines: {node: '>=4.0'} dev: true + /estree-walker@3.0.3: + resolution: {integrity: sha512-7RUKfXgSMMkzt6ZuXmqapOurLGPPfgj6l9uRZ7lRGolvk0y2yocc35LdcxKC5PQZdn2DMqioAQ2NoWcrTKmm6g==} + dependencies: + '@types/estree': 1.0.8 + dev: true + /esutils@2.0.3: resolution: {integrity: sha512-kVscqXk4OCp68SZ0dkgEKVi6/8ij300KBWTJq32P/dYeWTSwK41WyTxalN1eRmA5Z9UU/LX9D7FWSmV9SAYx6g==} engines: {node: '>=0.10.0'} dev: true + /expect-type@1.3.0: + resolution: {integrity: sha512-knvyeauYhqjOYvQ66MznSMs83wmHrCycNEN6Ao+2AeYEfxUIkuiVxdEa1qlGEPK+We3n0THiDciYSsCcgW/DoA==} + engines: {node: '>=12.0.0'} + dev: true + /fast-deep-equal@3.1.3: resolution: {integrity: sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q==} dev: true @@ -3485,6 +4031,14 @@ packages: path-exists: 4.0.0 dev: true + /fix-dts-default-cjs-exports@1.0.1: + resolution: {integrity: sha512-pVIECanWFC61Hzl2+oOCtoJ3F17kglZC/6N94eRWycFgBH35hHx0Li604ZIzhseh97mf2p0cv7vVrOZGoqhlEg==} + dependencies: + magic-string: 0.30.21 + mlly: 1.8.2 + rollup: 4.60.1 + dev: true + /flat-cache@3.2.0: resolution: {integrity: sha512-CYcENa+FtcUKLmhhqyctpclsq7QF38pKjZHsGNiSQF5r4FtoKDWabFDl3hzaEQMvT1LHEysw5twgLvpYYb4vbw==} engines: {node: ^10.12.0 || >=12.0.0} @@ -3541,6 +4095,11 @@ packages: resolve-pkg-maps: 1.0.0 dev: true + /giget@3.2.0: + resolution: {integrity: sha512-GvHTWcykIR/fP8cj8dMpuMMkvaeJfPvYnhq0oW+chSeIr+ldX21ifU2Ms6KBoyKZQZmVaUAAhQ2EZ68KJF8a7A==} + hasBin: true + dev: false + /glob-parent@5.1.2: resolution: {integrity: sha512-AOIgSQCepiJYwP3ARnGx+5VnTu2HBYdzbGP45eLw1vr3zB3vZLeyed1sC9hnbcOc9/SrMyM5RPQrkGz4aS9Zow==} engines: {node: '>= 6'} @@ -3605,6 +4164,13 @@ packages: resolution: {integrity: sha512-IScLbePpkvO846sIwOtOTDjutRMWdXdJmXdMvk6gCBHxFO8d+QKOQedyZSxFTTFYRSmlgSTDtXqqq4pcenBXLQ==} dev: true + /iconv-lite@0.7.2: + resolution: {integrity: sha512-im9DjEDQ55s9fL4EYzOAv0yMqmMBSZp6G0VvFyTMPKWxiSBHUj9NW/qqLmXUwXrrM7AvqSlTCfvqRb0cM8yYqw==} + engines: {node: '>=0.10.0'} + dependencies: + safer-buffer: 2.1.2 + dev: false + /ieee754@1.2.1: resolution: {integrity: sha512-dcyqhDvX1C46lXZcVqCpK+FtMRQVdIMN6/Df5js2zouUsqG7I6sFxitIC+7KYK29KdXOLHdu9zL4sFnoVQnqaA==} dev: true @@ -3656,7 +4222,6 @@ packages: /is-fullwidth-code-point@3.0.0: resolution: {integrity: sha512-zymm5+u+sCsSWyD9qNaejV3DFvhCKclKdizYaJUuHA83RLjb7nSuGnddCHGv0hk+KY7BMAlsWeK4Ueg6EV6XQg==} engines: {node: '>=8'} - dev: true /is-glob@4.0.3: resolution: {integrity: sha512-xelSayHH36ZgE7ZWhli7pW34hNbNl8Ojv5KVmkJD4hBdD3th8Tfk9vYasLM+mXWOZhFkgZfxhLSnrwRr4elSSg==} @@ -3732,12 +4297,21 @@ packages: resolution: {integrity: sha512-ekilCSN1jwRvIbgeg/57YFh8qQDNbwDb9xT/qu2DAHbFFZUicIl4ygVaAvzveMhMVr3LnpSKTNnwt8PoOfmKhQ==} hasBin: true + /joycon@3.1.1: + resolution: {integrity: sha512-34wB/Y7MW7bzjKRjUKTa46I2Z7eV62Rkhva+KkopW7Qvv/OSWBqvkSY7vusOPrNuZcUG3tApvdVgNB8POj3SPw==} + engines: {node: '>=10'} + dev: true + /js-sha256@0.10.1: resolution: {integrity: sha512-5obBtsz9301ULlsgggLg542s/jqtddfOpV5KJc4hajc9JV8GeY2gZHSVpYBn4nWqAUTJ9v+xwtbJ1mIBgIH5Vw==} /js-tokens@4.0.0: resolution: {integrity: sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ==} + /js-tokens@9.0.1: + resolution: {integrity: sha512-mxa9E9ITFOt0ban3j6L5MpjwegGz6lBQmM1IJkWeBZGcMxto50+eWdjC/52xDbS2vy0k7vIMK0Fe2wfL9OQSpQ==} + dev: true + /js-yaml@4.1.1: resolution: {integrity: sha512-qQKT4zQxXl8lLwBtHMWwaTcGfFOZviOJet3Oy/xmGk2gZH677CJM9EvtfdSkgWcATZhj/55JZ0rmy3myCT5lsA==} hasBin: true @@ -3911,9 +4485,19 @@ packages: lightningcss-win32-x64-msvc: 1.32.0 dev: true + /lilconfig@3.1.3: + resolution: {integrity: sha512-/vlFKAoH5Cgt3Ie+JLhRbwOsCQePABiU3tJ1egGvyQ+33R/vcwM2Zl2QR/LzjsBeItPt3oSVXapn+m4nQDvpzw==} + engines: {node: '>=14'} + dev: true + /lines-and-columns@1.2.4: resolution: {integrity: sha512-7ylylesZQ/PV29jhEDl3Ufjo6ZX7gCqJr5F7PKrqc93v7fzSymt1BpwEU8nAUXs8qzzvqhbjhK5QZg6Mt/HkBg==} + /load-tsconfig@0.2.5: + resolution: {integrity: sha512-IXO6OCs9yg8tMKzfPZ1YmheJbZCiEsnBdcB03l0OcfK9prKnJb96siuHCr5Fl37/yo9DnKU+TLpxzTUspw9shg==} + engines: {node: ^12.20.0 || ^14.13.1 || >=16.0.0} + dev: true + /locate-path@6.0.0: resolution: {integrity: sha512-iPZK6eYjbxRu3uB4/WZ3EsEIMJFMqAoopl3R+zuq0UjcAm/MO6KCweDgPfP3elTztoKP3KtnVHxTn2NHBSDVUw==} engines: {node: '>=10'} @@ -3933,6 +4517,10 @@ packages: is-unicode-supported: 0.1.0 dev: true + /loupe@3.2.1: + resolution: {integrity: sha512-CdzqowRJCeLU72bHvWqwRBBlLcMEtIvGrlvef74kMnV2AolS9Y8xUv1I0U/MNAWMhBlKIoyuEgoJ0t/bbwHbLQ==} + dev: true + /lru-cache@11.3.5: resolution: {integrity: sha512-NxVFwLAnrd9i7KUBxC4DrUhmgjzOs+1Qm50D3oF1/oL+r1NpZ4gA7xvG0/zJ8evR7zIKn4vLf7qTNduWFtCrRw==} engines: {node: 20 || >=22} @@ -3988,6 +4576,15 @@ packages: engines: {node: '>=16 || 14 >=14.17'} dev: true + /mlly@1.8.2: + resolution: {integrity: sha512-d+ObxMQFmbt10sretNDytwt85VrbkhhUA/JBGm1MPaWJ65Cl4wOgLaB1NYvJSZ0Ef03MMEU/0xpPMXUIQ29UfA==} + dependencies: + acorn: 8.16.0 + pathe: 2.0.3 + pkg-types: 1.3.1 + ufo: 1.6.3 + dev: true + /moo@0.5.3: resolution: {integrity: sha512-m2fmM2dDm7GZQsY7KK2cme8agi+AAljILjQnof7p1ZMDe6dQ4bdnSMx0cPppudoeNv5hEFQirN6u+O4fDE0IWA==} @@ -4010,7 +4607,7 @@ packages: typescript: optional: true dependencies: - '@inquirer/confirm': 5.1.21 + '@inquirer/confirm': 5.1.21(@types/node@22.19.17) '@mswjs/interceptors': 0.41.3 '@open-draft/deferred-promise': 2.2.0 '@types/statuses': 2.0.6 @@ -4036,6 +4633,13 @@ packages: /mute-stream@2.0.0: resolution: {integrity: sha512-WWdIxpyjEn+FhQJQQv9aQAYlHoNVdzIzUySNV1gHUPDSdZJ3yZn7pAAbQcV7B56Mvu881q9FZV+0Vx2xC44VWA==} engines: {node: ^18.17.0 || >=20.5.0} + + /mz@2.7.0: + resolution: {integrity: sha512-z81GNO7nnYMEhrGh9LeymoE4+Yr0Wn5McHIZMK5cfQCl+NDX08sCZgUc9/6MHni9IWuFLm1Z3HTCXu2z9fN62Q==} + dependencies: + any-promise: 1.3.0 + object-assign: 4.1.1 + thenify-all: 1.6.0 dev: true /nanoid@3.3.11: @@ -4056,6 +4660,11 @@ packages: engines: {node: '>=0.10.0'} dev: true + /object-assign@4.1.1: + resolution: {integrity: sha512-rJgTQnkUnH1sFw8yT6VSU3zD3sWmu6sZhIseY8VX+GRu3P6F7Fu+JNDoXfklElbLJSnc3FUQHVe4cU5hj+BcUg==} + engines: {node: '>=0.10.0'} + dev: true + /observable-fns@0.6.1: resolution: {integrity: sha512-9gRK4+sRWzeN6AOewNBTLXir7Zl/i3GB6Yl26gK4flxz8BXVpD3kt8amREmWNb0mxYOGDotvE5a4N+PtGGKdkg==} dev: true @@ -4249,6 +4858,11 @@ packages: resolution: {integrity: sha512-WUjGcAqP1gQacoQe+OBJsFA7Ld4DyXuUIjZ5cc75cLHvJ7dtNsTugphxIADwspS+AraAUePCKrSVtPLFj/F88w==} dev: true + /pathval@2.0.1: + resolution: {integrity: sha512-//nshmD55c46FuFw26xV/xFAaB5HF9Xdap7HJBBnrKdAd6/GxDBaNA1870O79+9ueg61cZLSVc+OaFlfmObYVQ==} + engines: {node: '>= 14.16'} + dev: true + /picocolors@1.1.1: resolution: {integrity: sha512-xceH2snhtb5M9liqDsmEw56le376mTZkEX/jEb/RxNFyegNul7eNslCXP9FDj/Lcu0X8KEyMceP2ntpaHrDEVA==} @@ -4262,6 +4876,11 @@ packages: engines: {node: '>=12'} dev: true + /pirates@4.0.7: + resolution: {integrity: sha512-TfySrs/5nm8fQJDcBDuUng3VOUKsd7S+zqvbOTiGXHfxX4wK31ard+hoNuvkicM/2YFzlpDgABOevKSsB4G/FA==} + engines: {node: '>= 6'} + dev: true + /pixelmatch@7.1.0: resolution: {integrity: sha512-1wrVzJ2STrpmONHKBy228LM1b84msXDUoAzVEl0R8Mz4Ce6EPr+IVtxm8+yvrqLYMHswREkjYFaMxnyGnaY3Ng==} hasBin: true @@ -4269,6 +4888,14 @@ packages: pngjs: 7.0.0 dev: true + /pkg-types@1.3.1: + resolution: {integrity: sha512-/Jm5M4RvtBFVkKWRu2BLUTNP8/M2a+UwuAX+ae4770q1qVGtfjG+WTCupoZixokjmHiry8uI+dlY8KXYV5HVVQ==} + dependencies: + confbox: 0.1.8 + mlly: 1.8.2 + pathe: 2.0.3 + dev: true + /playwright-core@1.59.1: resolution: {integrity: sha512-HBV/RJg81z5BiiZ9yPzIiClYV/QMsDCKUyogwH9p3MCP6IYjUFu/MActgYAvK0oWyV9NlwM3GLBjADyWgydVyg==} engines: {node: '>=18'} @@ -4294,6 +4921,27 @@ packages: resolution: {integrity: sha512-r6Q21sKsY1AjTVVjOuU02VYKVNQGJNQHjTIvs4dEbeuuYfxgYk/DGD2mqqq4RDaVkwdSq0VEtmQUOPe/wH8X3g==} dev: true + /postcss-load-config@6.0.1: + resolution: {integrity: sha512-oPtTM4oerL+UXmx+93ytZVN82RrlY/wPUV8IeDxFrzIjXOLF1pN+EmKPLbubvKHT2HC20xXsCAH2Z+CKV6Oz/g==} + engines: {node: '>= 18'} + peerDependencies: + jiti: '>=1.21.0' + postcss: '>=8.0.9' + tsx: ^4.8.1 + yaml: ^2.4.2 + peerDependenciesMeta: + jiti: + optional: true + postcss: + optional: true + tsx: + optional: true + yaml: + optional: true + dependencies: + lilconfig: 3.1.3 + dev: true + /postcss@8.5.9: resolution: {integrity: sha512-7a70Nsot+EMX9fFU3064K/kdHWZqGVY+BADLyXc8Dfv+mTLLVl6JzJpPaCZ2kQL9gIJvKXSLMHhqdRRjwQeFtw==} engines: {node: ^10 || ^12 || >=14} @@ -4377,6 +5025,11 @@ packages: picomatch: 2.3.2 dev: true + /readdirp@4.1.2: + resolution: {integrity: sha512-GDhwkLfywWL2s6vEjyhri+eXmfH6j1L7JE27WhqLeYzoh/A3DBaYGEj2H/HFZCn/kMfim73FXxEJTw06WtxQwg==} + engines: {node: '>= 14.18.0'} + dev: true + /require-directory@2.1.1: resolution: {integrity: sha512-fGxEI7+wsG9xrvdjsrlmL22OMTTiHRwAMroiEeMgq8gzoLC/PQr7RsRDSTLUg/bZAZtF+TVIkHc6/4RIKrui+Q==} engines: {node: '>=0.10.0'} @@ -4386,6 +5039,11 @@ packages: resolution: {integrity: sha512-pb/MYmXstAkysRFx8piNI1tGFNQIFA3vkE3Gq4EuA1dF6gHp/+vgZqsCGJapvy8N3Q+4o7FwvquPJcnZ7RYy4g==} engines: {node: '>=4'} + /resolve-from@5.0.0: + resolution: {integrity: sha512-qYg9KP24dD5qka9J47d0aVky0N+b4fTU89LN9iDnjB5waksiC49rvMB0PrUJQGoTmH50XPiqOvAjDfaijGxYZw==} + engines: {node: '>=8'} + dev: true + /resolve-pkg-maps@1.0.0: resolution: {integrity: sha512-seS2Tj26TBVOC2NIc2rOe2y2ZO7efxITtLZcGSOnHHNOQ7CkiUBfw0Iw2ck6xkIhPwLhKNLS8BO+hEpngQlqzw==} dev: true @@ -4415,6 +5073,41 @@ packages: glob: 7.2.3 dev: true + /rollup@4.60.1: + resolution: {integrity: sha512-VmtB2rFU/GroZ4oL8+ZqXgSA38O6GR8KSIvWmEFv63pQ0G6KaBH9s07PO8XTXP4vI+3UJUEypOfjkGfmSBBR0w==} + engines: {node: '>=18.0.0', npm: '>=8.0.0'} + hasBin: true + dependencies: + '@types/estree': 1.0.8 + optionalDependencies: + '@rollup/rollup-android-arm-eabi': 4.60.1 + '@rollup/rollup-android-arm64': 4.60.1 + '@rollup/rollup-darwin-arm64': 4.60.1 + '@rollup/rollup-darwin-x64': 4.60.1 + '@rollup/rollup-freebsd-arm64': 4.60.1 + '@rollup/rollup-freebsd-x64': 4.60.1 + '@rollup/rollup-linux-arm-gnueabihf': 4.60.1 + '@rollup/rollup-linux-arm-musleabihf': 4.60.1 + '@rollup/rollup-linux-arm64-gnu': 4.60.1 + '@rollup/rollup-linux-arm64-musl': 4.60.1 + '@rollup/rollup-linux-loong64-gnu': 4.60.1 + '@rollup/rollup-linux-loong64-musl': 4.60.1 + '@rollup/rollup-linux-ppc64-gnu': 4.60.1 + '@rollup/rollup-linux-ppc64-musl': 4.60.1 + '@rollup/rollup-linux-riscv64-gnu': 4.60.1 + '@rollup/rollup-linux-riscv64-musl': 4.60.1 + '@rollup/rollup-linux-s390x-gnu': 4.60.1 + '@rollup/rollup-linux-x64-gnu': 4.60.1 + '@rollup/rollup-linux-x64-musl': 4.60.1 + '@rollup/rollup-openbsd-x64': 4.60.1 + '@rollup/rollup-openharmony-arm64': 4.60.1 + '@rollup/rollup-win32-arm64-msvc': 4.60.1 + '@rollup/rollup-win32-ia32-msvc': 4.60.1 + '@rollup/rollup-win32-x64-gnu': 4.60.1 + '@rollup/rollup-win32-x64-msvc': 4.60.1 + fsevents: 2.3.3 + dev: true + /run-parallel@1.2.0: resolution: {integrity: sha512-5l4VyZR86LZ/lDxZTR6jqL8AFE2S0IFLMP26AbjsLVADxHdhB/c0GUsH+y39UfCi3dzz8OlQuPmnaJOMoDHQBA==} dependencies: @@ -4425,6 +5118,10 @@ packages: resolution: {integrity: sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ==} dev: true + /safer-buffer@2.1.2: + resolution: {integrity: sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==} + dev: false + /scheduler@0.27.0: resolution: {integrity: sha512-eNv+WrVbKu1f3vbYJT/xtiF5syA5HPIMtf9IgY/nKg0sWqzAUEvqY/xm7OcZc/qafLx/iO9FgOmeSAp4v5ti/Q==} @@ -4462,6 +5159,10 @@ packages: engines: {node: '>=8'} dev: true + /siginfo@2.0.0: + resolution: {integrity: sha512-ybx0WO1/8bSBLEWXZvEd7gMW3Sn3JFlW3TvX1nREbDLRNQNaeNN8WK0meBwPdAaOI7TtRRRJn/Es1zhrrCHu7g==} + dev: true + /signal-exit@3.0.7: resolution: {integrity: sha512-wnD2ZE+l+SPC/uoS0vXeE9L1+0wuaMqKlfz9AMUo38JsyLSBWSFcHR1Rri62LZc12vLr1gb3jl7iwQhgwpAbGQ==} dev: true @@ -4469,7 +5170,6 @@ packages: /signal-exit@4.1.0: resolution: {integrity: sha512-bzyZ1e88w9O1iNJbKnOlvYTrWPDl46O1bG0D3XInv+9tkPrxrN8jUUTiFlDkkmKWgn1M6CfIA13SuGqOa9Korw==} engines: {node: '>=14'} - dev: true /sirv@3.0.2: resolution: {integrity: sha512-2wcC/oGxHis/BoHkkPwldgiPSYcpZK3JU28WoMVv55yHJgcZ8rlXvuG9iZggz+sU1d4bRgIGASwyWqjxu3FM0g==} @@ -4490,11 +5190,19 @@ packages: engines: {node: '>= 12'} dev: true + /stackback@0.0.2: + resolution: {integrity: sha512-1XMJE5fQo1jGH6Y/7ebnwPOBEkIEnT4QF32d5R1+VXdXveM0IBMJt8zfaxX1P3QhVwrYe+576+jkANtSS2mBbw==} + dev: true + /statuses@2.0.2: resolution: {integrity: sha512-DvEy55V3DB7uknRo+4iOGT5fP1slR8wQohVdknigZPMpMstaKJQWhwiYBACJE3Ul2pTnATihhBYnRhZQHGBiRw==} engines: {node: '>= 0.8'} dev: true + /std-env@3.10.0: + resolution: {integrity: sha512-5GS12FdOZNliM5mAOxFRg7Ir0pWz8MdpYm6AY6VPkGpbA7ZzmbzNcBJQ0GPvvyWgcY7QAhCgf9Uy89I03faLkg==} + dev: true + /std-env@4.0.0: resolution: {integrity: sha512-zUMPtQ/HBY3/50VbpkupYHbRroTRZJPRLvreamgErJVys0ceuzMkD44J/QjqhHjOzK42GQ3QZIeFG1OYfOtKqQ==} dev: true @@ -4514,7 +5222,6 @@ packages: emoji-regex: 8.0.0 is-fullwidth-code-point: 3.0.0 strip-ansi: 6.0.1 - dev: true /string_decoder@1.3.0: resolution: {integrity: sha512-hkRX8U1WjJFd8LsDJ2yQ/wWWxaopEsABU1XfkM8A+j0+85JAGppt16cr1Whg6KIbb4okU6Mql6BOj+uup/wKeA==} @@ -4527,17 +5234,36 @@ packages: engines: {node: '>=8'} dependencies: ansi-regex: 5.0.1 - dev: true /strip-json-comments@3.1.1: resolution: {integrity: sha512-6fPc+R4ihwqP6N/aIv2f1gMH8lOVtWQHoqC4yK6oSDVVocumAsfCqjkXnqiYMhmMwS/mEHLp7Vehlt3ql6lEig==} engines: {node: '>=8'} dev: true + /strip-literal@3.1.0: + resolution: {integrity: sha512-8r3mkIM/2+PpjHoOtiAW8Rg3jJLHaV7xPwG+YRGrv6FP0wwk/toTpATxWYOW0BKdWwl82VT2tFYi5DlROa0Mxg==} + dependencies: + js-tokens: 9.0.1 + dev: true + /stylis@4.3.6: resolution: {integrity: sha512-yQ3rwFWRfwNUY7H5vpU0wfdkNSnvnJinhF9830Swlaxl03zsOjCfmX0ugac+3LtK0lYSgwL/KXc8oYL3mG4YFQ==} dev: false + /sucrase@3.35.1: + resolution: {integrity: sha512-DhuTmvZWux4H1UOnWMB3sk0sbaCVOoQZjv8u1rDoTV0HTdGem9hkAZtl4JZy8P2z4Bg0nT+YMeOFyVr4zcG5Tw==} + engines: {node: '>=16 || 14 >=14.17'} + hasBin: true + dependencies: + '@jridgewell/gen-mapping': 0.3.13 + commander: 4.1.1 + lines-and-columns: 1.2.4 + mz: 2.7.0 + pirates: 4.0.7 + tinyglobby: 0.2.16 + ts-interface-checker: 0.1.13 + dev: true + /supports-color@7.2.0: resolution: {integrity: sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==} engines: {node: '>=8'} @@ -4553,6 +5279,19 @@ packages: resolution: {integrity: sha512-N+8UisAXDGk8PFXP4HAzVR9nbfmVJ3zYLAWiTIoqC5v5isinhr+r5uaO8+7r3BMfuNIufIsA7RdpVgacC2cSpw==} dev: true + /thenify-all@1.6.0: + resolution: {integrity: sha512-RNxQH/qI8/t3thXJDwcstUO4zeqo64+Uy/+sNVRBx4Xn2OX+OZ9oP+iJnNFqplFra2ZUVeKCSa2oVWi3T4uVmA==} + engines: {node: '>=0.8'} + dependencies: + thenify: 3.3.1 + dev: true + + /thenify@3.3.1: + resolution: {integrity: sha512-RVZSIV5IG10Hk3enotrhvz0T9em6cyHBLkH/YAZuKqd8hRkKhSfCGIcP2KUY0EPxndzANBmNllzWPwak+bheSw==} + dependencies: + any-promise: 1.3.0 + dev: true + /threads@1.7.0: resolution: {integrity: sha512-Mx5NBSHX3sQYR6iI9VYbgHKBLisyB+xROCBGjjWm1O9wb9vfLxdaGtmT/KCjUqMsSNW6nERzCW3T6H43LqjDZQ==} dependencies: @@ -4583,6 +5322,10 @@ packages: resolution: {integrity: sha512-0+DUvqWMValLmha6lr4kD8iAMK1HzV0/aKnCtWb9v9641TnP/MFb7Pc2bxoxQjTXAErryXVgUOfv2YqNllqGeg==} dev: true + /tinyexec@0.3.2: + resolution: {integrity: sha512-KQQR9yN7R5+OSwaK0XQoj22pwHoTlgYqmUscPYoknOoWCWfj/5/ABTMRi69FrKU5ffPVh5QcFikpWJI/P1ocHA==} + dev: true + /tinyexec@1.1.1: resolution: {integrity: sha512-VKS/ZaQhhkKFMANmAOhhXVoIfBXblQxGX1myCQ2faQrfmobMftXeJPcZGp0gS07ocvGJWDLZGyOZDadDBqYIJg==} engines: {node: '>=18'} @@ -4596,11 +5339,26 @@ packages: picomatch: 4.0.4 dev: true + /tinypool@1.1.1: + resolution: {integrity: sha512-Zba82s87IFq9A9XmjiX5uZA/ARWDrB03OHlq+Vw1fSdt0I+4/Kutwy8BP4Y/y/aORMo61FQ0vIb5j44vSo5Pkg==} + engines: {node: ^18.0.0 || >=20.0.0} + dev: true + /tinypool@2.1.0: resolution: {integrity: sha512-Pugqs6M0m7Lv1I7FtxN4aoyToKg1C4tu+/381vH35y8oENM/Ai7f7C4StcoK4/+BSw9ebcS8jRiVrORFKCALLw==} engines: {node: ^20.0.0 || >=22.0.0} dev: true + /tinyrainbow@2.0.0: + resolution: {integrity: sha512-op4nsTR47R6p0vMUUoYl/a+ljLFVtlfaXkLQmqfLR1qHma1h/ysYk4hEXZ880bf2CYgTskvTa/e196Vd5dDQXw==} + engines: {node: '>=14.0.0'} + dev: true + + /tinyspy@4.0.4: + resolution: {integrity: sha512-azl+t0z7pw/z958Gy9svOTuzqIk6xq+NSheJzn5MMWtWTFywIacg2wUlzKFGtt3cthx0r2SxMK0yzJOR0IES7Q==} + engines: {node: '>=14.0.0'} + dev: true + /tldts-core@7.0.28: resolution: {integrity: sha512-7W5Efjhsc3chVdFhqtaU0KtK32J37Zcr9RKtID54nG+tIpcY79CQK/veYPODxtD/LJ4Lue66jvrQzIX2Z2/pUQ==} dev: true @@ -4631,6 +5389,59 @@ packages: tldts: 7.0.28 dev: true + /tree-kill@1.2.2: + resolution: {integrity: sha512-L0Orpi8qGpRG//Nd+H90vFB+3iHnue1zSSGmNOOCh1GLJ7rUKVwV2HvijphGQS2UmhUZewS9VgvxYIdgr+fG1A==} + hasBin: true + dev: true + + /ts-interface-checker@0.1.13: + resolution: {integrity: sha512-Y/arvbn+rrz3JCKl9C4kVNfTfSm2/mEp5FSz5EsZSANGPSlQrpRI5M4PKF+mJnE52jOO90PnPSc3Ur3bTQw0gA==} + dev: true + + /tsup@8.5.1(typescript@5.9.3): + resolution: {integrity: sha512-xtgkqwdhpKWr3tKPmCkvYmS9xnQK3m3XgxZHwSUjvfTjp7YfXe5tT3GgWi0F2N+ZSMsOeWeZFh7ZZFg5iPhing==} + engines: {node: '>=18'} + hasBin: true + peerDependencies: + '@microsoft/api-extractor': ^7.36.0 + '@swc/core': ^1 + postcss: ^8.4.12 + typescript: '>=4.5.0' + peerDependenciesMeta: + '@microsoft/api-extractor': + optional: true + '@swc/core': + optional: true + postcss: + optional: true + typescript: + optional: true + dependencies: + bundle-require: 5.1.0(esbuild@0.27.7) + cac: 6.7.14 + chokidar: 4.0.3 + consola: 3.4.2 + debug: 4.4.3 + esbuild: 0.27.7 + fix-dts-default-cjs-exports: 1.0.1 + joycon: 3.1.1 + picocolors: 1.1.1 + postcss-load-config: 6.0.1 + resolve-from: 5.0.0 + rollup: 4.60.1 + source-map: 0.7.6 + sucrase: 3.35.1 + tinyexec: 0.3.2 + tinyglobby: 0.2.16 + tree-kill: 1.2.2 + typescript: 5.9.3 + transitivePeerDependencies: + - jiti + - supports-color + - tsx + - yaml + dev: true + /tsx@4.21.0: resolution: {integrity: sha512-5C1sg4USs1lfG0GFb2RLXsdpXqBSEhAaA/0kPL01wxzpMqLILNxIxIOKiILz+cdg/pLnOUxFYOR5yhHU666wbw==} engines: {node: '>=18.0.0'} @@ -4678,8 +5489,12 @@ packages: engines: {node: '>=14.17'} hasBin: true - /undici-types@7.19.2: - resolution: {integrity: sha512-qYVnV5OEm2AW8cJMCpdV20CDyaN3g0AjDlOGf1OW4iaDEx8MwdtChUp4zu4H0VP3nDRF/8RKWH+IPp9uW0YGZg==} + /ufo@1.6.3: + resolution: {integrity: sha512-yDJTmhydvl5lJzBmy/hyOAA0d+aqCBuwl818haVdYCRrWV84o7YyeVm4QlVHStqNrrJSTb6jKuFAVqAFsr+K3Q==} + dev: true + + /undici-types@6.21.0: + resolution: {integrity: sha512-iwDZqg0QAGrg9Rav5H4n0M64c3mkR59cJ6wQp+7C4nI0gsmExaedaYLNO44eT4AtBBwjbTiGPMlt2Md0T9H9JQ==} /unplugin@2.3.11: resolution: {integrity: sha512-5uKD0nqiYVzlmCRs01Fhs2BdkEgBS3SAVP6ndrBsuK42iC2+JHyxM05Rm9G8+5mkmRtzMZGY8Ct5+mliZxU/Ww==} @@ -4722,6 +5537,31 @@ packages: resolution: {integrity: sha512-EPD5q1uXyFxJpCrLnCc1nHnq3gOa6DZBocAIiI2TaSCA7VCJ1UJDMagCzIkXNsUYfD1daK//LTEQ8xiIbrHtcw==} dev: true + /vite-node@3.2.4(@types/node@22.19.17): + resolution: {integrity: sha512-EbKSKh+bh1E1IFxeO0pg1n4dvoOTt0UDiXMd/qn++r98+jPO1xtJilvXldeuQ8giIB5IkpjCgMleHMNEsGH6pg==} + engines: {node: ^18.0.0 || ^20.0.0 || >=22.0.0} + hasBin: true + dependencies: + cac: 6.7.14 + debug: 4.4.3 + es-module-lexer: 1.7.0 + pathe: 2.0.3 + vite: 7.3.2(@types/node@22.19.17) + transitivePeerDependencies: + - '@types/node' + - jiti + - less + - lightningcss + - sass + - sass-embedded + - stylus + - sugarss + - supports-color + - terser + - tsx + - yaml + dev: true + /vite-plus@0.1.16(@voidzero-dev/vite-plus-core@0.1.16)(typescript@5.9.3): resolution: {integrity: sha512-sgYHc5zWLSDInaHb/abvEA7UOwh7sUWuyNt+Slphj55jPvzodT8Dqw115xyKwDARTuRFSpm1eo/t58qZ8/NylQ==} engines: {node: ^20.19.0 || >=22.12.0} @@ -4771,6 +5611,124 @@ packages: - yaml dev: true + /vite@7.3.2(@types/node@22.19.17): + resolution: {integrity: sha512-Bby3NOsna2jsjfLVOHKes8sGwgl4TT0E6vvpYgnAYDIF/tie7MRaFthmKuHx1NSXjiTueXH3do80FMQgvEktRg==} + engines: {node: ^20.19.0 || >=22.12.0} + hasBin: true + peerDependencies: + '@types/node': ^20.19.0 || >=22.12.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' + sugarss: ^5.0.0 + terser: ^5.16.0 + tsx: ^4.8.1 + yaml: ^2.4.2 + peerDependenciesMeta: + '@types/node': + optional: true + jiti: + optional: true + less: + optional: true + lightningcss: + optional: true + sass: + optional: true + sass-embedded: + optional: true + stylus: + optional: true + sugarss: + optional: true + terser: + optional: true + tsx: + optional: true + yaml: + optional: true + dependencies: + '@types/node': 22.19.17 + esbuild: 0.27.7 + fdir: 6.5.0(picomatch@4.0.4) + picomatch: 4.0.4 + postcss: 8.5.9 + rollup: 4.60.1 + tinyglobby: 0.2.16 + optionalDependencies: + fsevents: 2.3.3 + dev: true + + /vitest@3.2.4(@types/node@22.19.17): + resolution: {integrity: sha512-LUCP5ev3GURDysTWiP47wRRUpLKMOfPh+yKTx3kVIEiu5KOMeqzpnYNsKyOoVrULivR8tLcks4+lga33Whn90A==} + engines: {node: ^18.0.0 || ^20.0.0 || >=22.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.4 + '@vitest/ui': 3.2.4 + happy-dom: '*' + jsdom: '*' + peerDependenciesMeta: + '@edge-runtime/vm': + optional: true + '@types/debug': + optional: true + '@types/node': + optional: true + '@vitest/browser': + optional: true + '@vitest/ui': + optional: true + happy-dom: + optional: true + jsdom: + optional: true + dependencies: + '@types/chai': 5.2.3 + '@types/node': 22.19.17 + '@vitest/expect': 3.2.4 + '@vitest/mocker': 3.2.4(vite@7.3.2) + '@vitest/pretty-format': 3.2.4 + '@vitest/runner': 3.2.4 + '@vitest/snapshot': 3.2.4 + '@vitest/spy': 3.2.4 + '@vitest/utils': 3.2.4 + chai: 5.3.3 + debug: 4.4.3 + expect-type: 1.3.0 + magic-string: 0.30.21 + pathe: 2.0.3 + picomatch: 4.0.4 + std-env: 3.10.0 + tinybench: 2.9.0 + tinyexec: 0.3.2 + tinyglobby: 0.2.16 + tinypool: 1.1.1 + tinyrainbow: 2.0.0 + vite: 7.3.2(@types/node@22.19.17) + vite-node: 3.2.4(@types/node@22.19.17) + why-is-node-running: 2.3.0 + transitivePeerDependencies: + - jiti + - less + - lightningcss + - msw + - sass + - sass-embedded + - stylus + - sugarss + - supports-color + - terser + - tsx + - yaml + dev: true + /wcwidth@1.0.1: resolution: {integrity: sha512-XHPEwS0q6TaxcvG85+8EYkbiCux2XtWG2mkc47Ng2A77BQu9+DqIOJldST4HgPkuea7dvKSj5VgX3P1d4rW8Tg==} dependencies: @@ -4789,6 +5747,15 @@ packages: isexe: 2.0.0 dev: true + /why-is-node-running@2.3.0: + resolution: {integrity: sha512-hUrmaWBdVDcxvYqnyh09zunKzROWjbZTiNy8dBEjkS7ehEDQibXJ7XvlmtbwuTclUiIyN+CyXQD4Vmko8fNm8w==} + engines: {node: '>=8'} + hasBin: true + dependencies: + siginfo: 2.0.0 + stackback: 0.0.2 + dev: true + /word-wrap@1.2.5: resolution: {integrity: sha512-BN22B5eaMMI9UMtjrGd5g5eCYPpCPDUy0FJXbYsaT5zYxjFOckS53SQDE3pWkVoWpHXVb3BrYcEN4Twa55B5cA==} engines: {node: '>=0.10.0'} @@ -4801,7 +5768,6 @@ packages: ansi-styles: 4.3.0 string-width: 4.2.3 strip-ansi: 6.0.1 - dev: true /wrap-ansi@7.0.0: resolution: {integrity: sha512-YVGIj2kamLSTxw6NsZjoBxfSwsn0ycdesmc4p+Q21c5zPuZ1pl+NfxVdxPtdHvmNVOQ6XSYG4AUtyt/Fi7D16Q==} @@ -4863,7 +5829,6 @@ packages: /yoctocolors-cjs@2.1.3: resolution: {integrity: sha512-U/PBtDf35ff0D8X8D0jfdzHYEPFxAI7jJlxZXwCSez5M3190m+QobIfh+sWDWSHMCWWJN2AWamkegn6vr6YBTw==} engines: {node: '>=18'} - dev: true /zod@3.25.76: resolution: {integrity: sha512-gzUt/qt81nXsFGKIFcC3YnfEAx5NkunCfnDlvuBSSFS02bcXu4Lmea0AFIUwbLWxWPx3d9p8S5QoaujKcNQxcQ==} From 02150a61a7ba2ca2af764c4441845904c0ec813a Mon Sep 17 00:00:00 2001 From: zuiidea Date: Tue, 14 Apr 2026 22:28:11 +0800 Subject: [PATCH 02/16] build(create): tsup bundle and postbuild examples manifest Made-with: Cursor --- packages/create/package.json | 1 + .../create/scripts/write-examples-json.mjs | 20 +++++++++++++++++++ packages/create/src/cli.ts | 2 ++ packages/create/tsup.config.ts | 14 +++++++++++++ 4 files changed, 37 insertions(+) create mode 100644 packages/create/scripts/write-examples-json.mjs create mode 100644 packages/create/src/cli.ts create mode 100644 packages/create/tsup.config.ts diff --git a/packages/create/package.json b/packages/create/package.json index 7869850..b5751e0 100644 --- a/packages/create/package.json +++ b/packages/create/package.json @@ -11,6 +11,7 @@ "dist" ], "scripts": { + "prepublishOnly": "pnpm run build", "build": "tsup && node ./scripts/write-examples-json.mjs", "dev": "tsup --watch", "check-types": "tsc --noEmit", diff --git a/packages/create/scripts/write-examples-json.mjs b/packages/create/scripts/write-examples-json.mjs new file mode 100644 index 0000000..d878170 --- /dev/null +++ b/packages/create/scripts/write-examples-json.mjs @@ -0,0 +1,20 @@ +import fs from "node:fs"; +import path from "node:path"; +import { fileURLToPath } from "node:url"; + +const __dirname = path.dirname(fileURLToPath(import.meta.url)); +const repoRoot = path.resolve(__dirname, "../../.."); +const appsDir = path.join(repoRoot, "apps"); +const outFile = path.resolve(__dirname, "../dist/examples.json"); + +const exclude = new Set(["docs"]); +const names = fs + .readdirSync(appsDir, { withFileTypes: true }) + .filter((d) => d.isDirectory()) + .map((d) => d.name) + .filter((name) => !exclude.has(name)) + .sort(); + +fs.mkdirSync(path.dirname(outFile), { recursive: true }); +fs.writeFileSync(outFile, JSON.stringify({ examples: names }, null, 2)); +console.log(`write-examples-json: wrote ${outFile}`, names); diff --git a/packages/create/src/cli.ts b/packages/create/src/cli.ts new file mode 100644 index 0000000..b0bb886 --- /dev/null +++ b/packages/create/src/cli.ts @@ -0,0 +1,2 @@ +#!/usr/bin/env node +console.log("create-antd-admin stub"); diff --git a/packages/create/tsup.config.ts b/packages/create/tsup.config.ts new file mode 100644 index 0000000..6302dc3 --- /dev/null +++ b/packages/create/tsup.config.ts @@ -0,0 +1,14 @@ +import { defineConfig } from "tsup"; + +export default defineConfig({ + entry: ["src/cli.ts"], + format: ["esm"], + platform: "node", + target: "node20", + outDir: "dist", + clean: true, + banner: { + js: "#!/usr/bin/env node", + }, + shims: false, +}); From 9b8fd96a7a8f0a3d64490c9a11c73cee511eb1d2 Mon Sep 17 00:00:00 2001 From: zuiidea Date: Tue, 14 Apr 2026 22:28:36 +0800 Subject: [PATCH 03/16] docs(specs): fix write-examples-json repoRoot depth for scripts/ Made-with: Cursor --- docs/specs/2026-04-14-create-antd-admin-plan.md | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/docs/specs/2026-04-14-create-antd-admin-plan.md b/docs/specs/2026-04-14-create-antd-admin-plan.md index 8bba89f..3f2f499 100644 --- a/docs/specs/2026-04-14-create-antd-admin-plan.md +++ b/docs/specs/2026-04-14-create-antd-admin-plan.md @@ -171,7 +171,8 @@ import path from "node:path"; import { fileURLToPath } from "node:url"; const __dirname = path.dirname(fileURLToPath(import.meta.url)); -const repoRoot = path.resolve(__dirname, "../.."); +/** From `packages/create/scripts/`, three levels up = monorepo root. */ +const repoRoot = path.resolve(__dirname, "../../.."); const appsDir = path.join(repoRoot, "apps"); const outFile = path.resolve(__dirname, "../dist/examples.json"); From 578f7f5082ca2027f1f44555abb484aa01126cfb Mon Sep 17 00:00:00 2001 From: zuiidea Date: Tue, 14 Apr 2026 22:29:10 +0800 Subject: [PATCH 04/16] feat(create): add constants, CliError, and git ref resolver Made-with: Cursor --- packages/create/src/constants.ts | 11 +++++++++++ packages/create/src/errors.ts | 14 ++++++++++++++ packages/create/src/resolve-ref.ts | 26 ++++++++++++++++++++++++++ 3 files changed, 51 insertions(+) create mode 100644 packages/create/src/constants.ts create mode 100644 packages/create/src/errors.ts create mode 100644 packages/create/src/resolve-ref.ts diff --git a/packages/create/src/constants.ts b/packages/create/src/constants.ts new file mode 100644 index 0000000..d447338 --- /dev/null +++ b/packages/create/src/constants.ts @@ -0,0 +1,11 @@ +export const DEFAULT_GITHUB_REPO = "zuiidea/antd-admin"; + +/** Override full repo slug `owner/name` */ +export const ENV_REPO = "CREATE_ANTD_ADMIN_REPO"; + +/** Override ref: branch name, tag, or commit sha */ +export const ENV_REF = "CREATE_ANTD_ADMIN_REF"; + +export const EXIT_SUCCESS = 0; +export const EXIT_ERROR = 1; +export const EXIT_SIGINT = 130; diff --git a/packages/create/src/errors.ts b/packages/create/src/errors.ts new file mode 100644 index 0000000..229a6a2 --- /dev/null +++ b/packages/create/src/errors.ts @@ -0,0 +1,14 @@ +export class CliError extends Error { + constructor( + message: string, + public readonly code: + | "INVALID_INPUT" + | "DOWNLOAD_FAILED" + | "TRANSFORM_FAILED" + | "INSTALL_FAILED", + public readonly exitCode = 1 + ) { + super(message); + this.name = "CliError"; + } +} diff --git a/packages/create/src/resolve-ref.ts b/packages/create/src/resolve-ref.ts new file mode 100644 index 0000000..b9db75f --- /dev/null +++ b/packages/create/src/resolve-ref.ts @@ -0,0 +1,26 @@ +import fs from "node:fs"; +import path from "node:path"; +import { fileURLToPath } from "node:url"; +import { ENV_REF } from "./constants.js"; + +/** + * Priority: CREATE_ANTD_ADMIN_REF env → read sibling package.json version as `v${version}` → `main` on failure. + * When bundled to dist/cli.js, ../package.json is packages/create/package.json. + */ +export function resolveGitRef(): string { + const env = process.env[ENV_REF]?.trim(); + if (env) return env; + + try { + const pkgPath = path.join( + path.dirname(fileURLToPath(import.meta.url)), + "..", + "package.json" + ); + const raw = fs.readFileSync(pkgPath, "utf8"); + const { version } = JSON.parse(raw) as { version: string }; + return `v${version}`; + } catch { + return "main"; + } +} From 0185201cbddd720afc8f96fee76f12763de31136 Mon Sep 17 00:00:00 2001 From: zuiidea Date: Tue, 14 Apr 2026 22:29:50 +0800 Subject: [PATCH 05/16] feat(create): load examples manifest from dist/examples.json Made-with: Cursor --- packages/create/src/examples.ts | 35 +++++++++++++++++++++++++++++++++ 1 file changed, 35 insertions(+) create mode 100644 packages/create/src/examples.ts diff --git a/packages/create/src/examples.ts b/packages/create/src/examples.ts new file mode 100644 index 0000000..919e7ab --- /dev/null +++ b/packages/create/src/examples.ts @@ -0,0 +1,35 @@ +import fs from "node:fs"; +import path from "node:path"; +import { fileURLToPath } from "node:url"; +import { CliError } from "./errors.js"; + +export type ExamplesManifest = { examples: string[] }; + +export function loadExamplesManifest(): string[] { + const manifestPath = path.join( + path.dirname(fileURLToPath(import.meta.url)), + "examples.json" + ); + if (!fs.existsSync(manifestPath)) { + throw new CliError( + `Missing ${manifestPath}. Run pnpm run build in packages/create.`, + "INVALID_INPUT" + ); + } + const data = JSON.parse( + fs.readFileSync(manifestPath, "utf8") + ) as ExamplesManifest; + if (!Array.isArray(data.examples) || data.examples.length === 0) { + throw new CliError("Invalid examples.json", "INVALID_INPUT"); + } + return data.examples; +} + +export function assertValidExample(name: string, list: string[]): void { + if (!list.includes(name)) { + throw new CliError( + `Unknown example "${name}". Valid: ${list.join(", ")}`, + "INVALID_INPUT" + ); + } +} From 831aef8a7bcf63d00fe335e06012ded2b3ecfa30 Mon Sep 17 00:00:00 2001 From: zuiidea Date: Tue, 14 Apr 2026 22:30:41 +0800 Subject: [PATCH 06/16] test(create): vitest and package name normalization Made-with: Cursor --- .../src/utils/normalize-package-name.test.ts | 12 +++++++++ .../src/utils/normalize-package-name.ts | 26 +++++++++++++++++++ packages/create/vitest.config.ts | 8 ++++++ 3 files changed, 46 insertions(+) create mode 100644 packages/create/src/utils/normalize-package-name.test.ts create mode 100644 packages/create/src/utils/normalize-package-name.ts create mode 100644 packages/create/vitest.config.ts diff --git a/packages/create/src/utils/normalize-package-name.test.ts b/packages/create/src/utils/normalize-package-name.test.ts new file mode 100644 index 0000000..0008ea6 --- /dev/null +++ b/packages/create/src/utils/normalize-package-name.test.ts @@ -0,0 +1,12 @@ +import { describe, expect, it } from "vitest"; +import { normalizePackageName } from "./normalize-package-name.js"; + +describe("normalizePackageName", () => { + it("lowercases and replaces spaces", () => { + expect(normalizePackageName("My App")).toBe("my-app"); + }); + + it("rejects leading dot", () => { + expect(() => normalizePackageName(".bad")).toThrow(/cannot start/); + }); +}); diff --git a/packages/create/src/utils/normalize-package-name.ts b/packages/create/src/utils/normalize-package-name.ts new file mode 100644 index 0000000..e99ddc0 --- /dev/null +++ b/packages/create/src/utils/normalize-package-name.ts @@ -0,0 +1,26 @@ +import { CliError } from "../errors.js"; + +/** + * npm package name rules (simplified): lowercase, URL-safe, no leading dot, segments 1-214. + */ +export function normalizePackageName(input: string): string { + const trimmed = input.trim().toLowerCase(); + if (!trimmed) { + throw new CliError("Project name cannot be empty", "INVALID_INPUT"); + } + if (trimmed.startsWith(".") || trimmed.startsWith("_")) { + throw new CliError( + "Project name cannot start with . or _", + "INVALID_INPUT" + ); + } + const safe = trimmed + .replace(/\s+/g, "-") + .replace(/[^a-z0-9-._~]/g, "-") + .replace(/-+/g, "-") + .replace(/^-+|-+$/g, ""); + if (!safe || safe.length > 214) { + throw new CliError("Project name is invalid or too long", "INVALID_INPUT"); + } + return safe; +} diff --git a/packages/create/vitest.config.ts b/packages/create/vitest.config.ts new file mode 100644 index 0000000..c1433e6 --- /dev/null +++ b/packages/create/vitest.config.ts @@ -0,0 +1,8 @@ +import { defineConfig } from "vitest/config"; + +export default defineConfig({ + test: { + environment: "node", + include: ["src/**/*.test.ts"], + }, +}); From 26b002e80a7e20041edb866ef5585fc4f7575d51 Mon Sep 17 00:00:00 2001 From: zuiidea Date: Tue, 14 Apr 2026 22:31:24 +0800 Subject: [PATCH 07/16] feat(create): resolve giget source for examples and URLs Made-with: Cursor --- .../create/src/resolve-example-source.test.ts | 20 ++++++++++ packages/create/src/resolve-example-source.ts | 39 +++++++++++++++++++ 2 files changed, 59 insertions(+) create mode 100644 packages/create/src/resolve-example-source.test.ts create mode 100644 packages/create/src/resolve-example-source.ts diff --git a/packages/create/src/resolve-example-source.test.ts b/packages/create/src/resolve-example-source.test.ts new file mode 100644 index 0000000..8a33bb6 --- /dev/null +++ b/packages/create/src/resolve-example-source.test.ts @@ -0,0 +1,20 @@ +import { describe, expect, it, vi, beforeEach, afterEach } from "vitest"; +import { resolveExampleSource } from "./resolve-example-source.js"; + +describe("resolveExampleSource", () => { + afterEach(() => { + vi.unstubAllEnvs(); + }); + + it("resolves short example with default repo and env ref", () => { + vi.stubEnv("CREATE_ANTD_ADMIN_REF", "main"); + const r = resolveExampleSource({ example: "basic" }); + expect(r.gigetSource).toBe("github:zuiidea/antd-admin/apps/basic#main"); + }); + + it("passes through https URL", () => { + const url = "https://api.github.com/repos/zuiidea/antd-admin/tarball/main"; + const r = resolveExampleSource({ example: url }); + expect(r.gigetSource).toBe(url); + }); +}); diff --git a/packages/create/src/resolve-example-source.ts b/packages/create/src/resolve-example-source.ts new file mode 100644 index 0000000..66aae24 --- /dev/null +++ b/packages/create/src/resolve-example-source.ts @@ -0,0 +1,39 @@ +import { DEFAULT_GITHUB_REPO, ENV_REPO } from "./constants.js"; +import { CliError } from "./errors.js"; +import { resolveGitRef } from "./resolve-ref.js"; + +export type ResolvedExampleSource = { gigetSource: string; displayName: string }; + +function defaultRepo(): string { + return process.env[ENV_REPO]?.trim() || DEFAULT_GITHUB_REPO; +} + +export function resolveExampleSource(input: { + example?: string; + examplePath?: string; +}): ResolvedExampleSource { + const example = input.example?.trim(); + if (!example) { + throw new CliError("example is required", "INVALID_INPUT"); + } + const { examplePath } = input; + const ref = resolveGitRef(); + + if (/^https?:\/\//i.test(example)) { + return { gigetSource: example, displayName: example }; + } + + const repo = defaultRepo(); + + if (!example.includes("/")) { + const sub = examplePath + ? `apps/${example}/${examplePath}`.replace(/\/+/g, "/") + : `apps/${example}`; + const gigetSource = `github:${repo}/${sub}#${ref}`; + return { gigetSource, displayName: example }; + } + + const pathPart = examplePath ? `${example}/${examplePath}` : example; + const gigetSource = `github:${pathPart}#${ref}`; + return { gigetSource, displayName: pathPart }; +} From 6031d691ea8ac709e49cc70a9b24c5d1a54d7c6a Mon Sep 17 00:00:00 2001 From: zuiidea Date: Tue, 14 Apr 2026 22:32:16 +0800 Subject: [PATCH 08/16] feat(create): download templates with giget Made-with: Cursor --- packages/create/src/download.ts | 24 ++++++++++++++++++++++++ 1 file changed, 24 insertions(+) create mode 100644 packages/create/src/download.ts diff --git a/packages/create/src/download.ts b/packages/create/src/download.ts new file mode 100644 index 0000000..613bf95 --- /dev/null +++ b/packages/create/src/download.ts @@ -0,0 +1,24 @@ +import os from "node:os"; +import path from "node:path"; +import { randomUUID } from "node:crypto"; +import { downloadTemplate } from "giget"; +import { CliError } from "./errors.js"; + +export async function downloadExampleToTemp( + gigetSource: string +): Promise { + const dir = path.join(os.tmpdir(), `create-antd-admin-${randomUUID()}`); + try { + const { dir: outDir } = await downloadTemplate(gigetSource, { + dir, + forceClean: true, + }); + return outDir; + } catch (e) { + const msg = e instanceof Error ? e.message : String(e); + throw new CliError( + `Failed to download template.\nSource: ${gigetSource}\n${msg}`, + "DOWNLOAD_FAILED" + ); + } +} From db696409d35b85708828da1eff4fc53a594e61ca Mon Sep 17 00:00:00 2001 From: zuiidea Date: Tue, 14 Apr 2026 22:32:21 +0800 Subject: [PATCH 09/16] feat(create): reject non-empty target directories Made-with: Cursor --- packages/create/src/paths.ts | 17 +++++++++++++++++ 1 file changed, 17 insertions(+) create mode 100644 packages/create/src/paths.ts diff --git a/packages/create/src/paths.ts b/packages/create/src/paths.ts new file mode 100644 index 0000000..64e8176 --- /dev/null +++ b/packages/create/src/paths.ts @@ -0,0 +1,17 @@ +import fs from "node:fs"; +import path from "node:path"; +import { CliError } from "./errors.js"; + +export function resolveTargetRoot(cwd: string, dir: string): string { + const abs = path.resolve(cwd, dir); + if (fs.existsSync(abs)) { + const entries = fs.readdirSync(abs); + if (entries.length > 0) { + throw new CliError( + `Target directory is not empty: ${abs}`, + "INVALID_INPUT" + ); + } + } + return abs; +} From 3e630785bb4dba96cefd8b6c49a51da7ccf4b86e Mon Sep 17 00:00:00 2001 From: zuiidea Date: Tue, 14 Apr 2026 22:32:59 +0800 Subject: [PATCH 10/16] feat(create): detect package managers and run install Made-with: Cursor --- packages/create/src/install.ts | 22 ++++++++++++++++ packages/create/src/package-manager.ts | 35 ++++++++++++++++++++++++++ 2 files changed, 57 insertions(+) create mode 100644 packages/create/src/install.ts create mode 100644 packages/create/src/package-manager.ts diff --git a/packages/create/src/install.ts b/packages/create/src/install.ts new file mode 100644 index 0000000..3ba4af6 --- /dev/null +++ b/packages/create/src/install.ts @@ -0,0 +1,22 @@ +import { spawnSync } from "node:child_process"; +import type { PackageManagerName } from "./package-manager.js"; +import { spawnInstall } from "./package-manager.js"; +import { CliError } from "./errors.js"; + +export function installDependencies( + cwd: string, + manager: PackageManagerName +): void { + const { cmd, args } = spawnInstall(manager); + const res = spawnSync(cmd, args, { + cwd, + stdio: "inherit", + env: { ...process.env, CI: "1" }, + }); + if (res.error || res.status !== 0) { + throw new CliError( + `${cmd} ${args.join(" ")} failed in ${cwd}`, + "INSTALL_FAILED" + ); + } +} diff --git a/packages/create/src/package-manager.ts b/packages/create/src/package-manager.ts new file mode 100644 index 0000000..ecc374f --- /dev/null +++ b/packages/create/src/package-manager.ts @@ -0,0 +1,35 @@ +import { spawnSync } from "node:child_process"; + +export type PackageManagerName = "npm" | "pnpm" | "yarn" | "bun"; + +const ORDER: PackageManagerName[] = ["pnpm", "npm", "yarn", "bun"]; + +export function isManagerAvailable(name: PackageManagerName): boolean { + const result = spawnSync(name, ["--version"], { stdio: "ignore" }); + return result.status === 0; +} + +export function detectAvailableManagers(): PackageManagerName[] { + return ORDER.filter(isManagerAvailable); +} + +/** Install argv; cwd is applied by install.ts via spawnSync `cwd` option. */ +export function spawnInstall(name: PackageManagerName): { + cmd: string; + args: string[]; +} { + switch (name) { + case "pnpm": + return { cmd: "pnpm", args: ["install"] }; + case "npm": + return { cmd: "npm", args: ["install"] }; + case "yarn": + return { cmd: "yarn", args: ["install"] }; + case "bun": + return { cmd: "bun", args: ["install"] }; + default: { + const _: never = name; + throw new Error(`unsupported manager ${_}`); + } + } +} From 56943a3a95c22aa50e2d3e1646a1ee5539382ae4 Mon Sep 17 00:00:00 2001 From: zuiidea Date: Tue, 14 Apr 2026 22:33:01 +0800 Subject: [PATCH 11/16] feat(create): optional git init and initial commit Made-with: Cursor --- packages/create/src/git.ts | 22 ++++++++++++++++++++++ 1 file changed, 22 insertions(+) create mode 100644 packages/create/src/git.ts diff --git a/packages/create/src/git.ts b/packages/create/src/git.ts new file mode 100644 index 0000000..87c76f6 --- /dev/null +++ b/packages/create/src/git.ts @@ -0,0 +1,22 @@ +import { spawnSync } from "node:child_process"; +import fs from "node:fs"; +import path from "node:path"; + +export function tryGitInit(root: string, enabled: boolean): boolean { + if (!enabled) { + const gitDir = path.join(root, ".git"); + if (fs.existsSync(gitDir)) { + fs.rmSync(gitDir, { recursive: true, force: true }); + } + return false; + } + const init = spawnSync("git", ["init"], { cwd: root, stdio: "ignore" }); + if (init.status !== 0) return false; + spawnSync("git", ["add", "-A"], { cwd: root, stdio: "ignore" }); + spawnSync( + "git", + ["commit", "-m", "chore: initial commit from create-antd-admin"], + { cwd: root, stdio: "ignore" } + ); + return true; +} From 9eb67a091f13228e316bef19b96222a5e40e743e Mon Sep 17 00:00:00 2001 From: zuiidea Date: Tue, 14 Apr 2026 22:33:05 +0800 Subject: [PATCH 12/16] feat(create): transform package.json name Made-with: Cursor --- .../create/src/transforms/package-json-name.ts | 17 +++++++++++++++++ .../create/src/transforms/run-transforms.ts | 10 ++++++++++ 2 files changed, 27 insertions(+) create mode 100644 packages/create/src/transforms/package-json-name.ts create mode 100644 packages/create/src/transforms/run-transforms.ts diff --git a/packages/create/src/transforms/package-json-name.ts b/packages/create/src/transforms/package-json-name.ts new file mode 100644 index 0000000..2cb2551 --- /dev/null +++ b/packages/create/src/transforms/package-json-name.ts @@ -0,0 +1,17 @@ +import fs from "node:fs"; +import path from "node:path"; +import { CliError } from "../errors.js"; + +export function transformPackageJsonName( + projectRoot: string, + name: string +): void { + const pkgPath = path.join(projectRoot, "package.json"); + if (!fs.existsSync(pkgPath)) { + throw new CliError(`No package.json at ${pkgPath}`, "TRANSFORM_FAILED"); + } + const raw = fs.readFileSync(pkgPath, "utf8"); + const json = JSON.parse(raw) as { name?: string }; + json.name = name; + fs.writeFileSync(pkgPath, JSON.stringify(json, null, 2) + "\n"); +} diff --git a/packages/create/src/transforms/run-transforms.ts b/packages/create/src/transforms/run-transforms.ts new file mode 100644 index 0000000..bef0169 --- /dev/null +++ b/packages/create/src/transforms/run-transforms.ts @@ -0,0 +1,10 @@ +import { transformPackageJsonName } from "./package-json-name.js"; + +export async function runTransforms(opts: { + projectRoot: string; + packageName: string; + skip: boolean; +}): Promise { + if (opts.skip) return; + transformPackageJsonName(opts.projectRoot, opts.packageName); +} From a26e7f717ec9a88151783b64633929aa5ccc83a3 Mon Sep 17 00:00:00 2001 From: zuiidea Date: Tue, 14 Apr 2026 22:33:56 +0800 Subject: [PATCH 13/16] feat(create): interactive prompts for example, dir, name, pm Made-with: Cursor --- packages/create/src/prompts.ts | 61 ++++++++++++++++++++++++++++++++++ packages/create/src/types.ts | 17 ++++++++++ 2 files changed, 78 insertions(+) create mode 100644 packages/create/src/prompts.ts create mode 100644 packages/create/src/types.ts diff --git a/packages/create/src/prompts.ts b/packages/create/src/prompts.ts new file mode 100644 index 0000000..cca5a83 --- /dev/null +++ b/packages/create/src/prompts.ts @@ -0,0 +1,61 @@ +import { confirm, input, select } from "@inquirer/prompts"; +import type { PackageManagerName } from "./package-manager.js"; +import { CliError } from "./errors.js"; +import { normalizePackageName } from "./utils/normalize-package-name.js"; + +export async function promptExample(examples: string[]): Promise { + return select({ + message: "Which example do you want?", + choices: examples.map((value) => ({ name: value, value })), + }); +} + +export async function promptTargetDir(): Promise { + const raw = await input({ + message: + "Project directory (relative path, or '.' for current directory)?", + default: "my-antd-admin", + }); + const dir = (raw.trim() || "my-antd-admin").replace(/\\/g, "/"); + if (dir === ".") { + const ok = await confirm({ + message: "Scaffold into the current directory?", + default: false, + }); + if (!ok) { + throw new CliError("Aborted.", "INVALID_INPUT"); + } + } + return dir; +} + +export async function promptPackageName(defaultName: string): Promise { + const raw = await input({ + message: "npm package name for package.json?", + default: defaultName, + validate: (value) => { + try { + normalizePackageName(value); + return true; + } catch (e) { + return e instanceof Error ? e.message : String(e); + } + }, + }); + return normalizePackageName(raw); +} + +export async function promptPackageManager( + available: PackageManagerName[] +): Promise { + if (available.length === 0) { + throw new CliError( + "No supported package manager found in PATH (pnpm, npm, yarn, bun).", + "INVALID_INPUT" + ); + } + return select({ + message: "Which package manager do you want to use?", + choices: available.map((value) => ({ name: value, value })), + }); +} diff --git a/packages/create/src/types.ts b/packages/create/src/types.ts new file mode 100644 index 0000000..7df15e3 --- /dev/null +++ b/packages/create/src/types.ts @@ -0,0 +1,17 @@ +import type { PackageManagerName } from "./package-manager.js"; + +export type CreateCliOptions = { + packageManager?: PackageManagerName; + skipInstall: boolean; + skipTransforms: boolean; + example?: string; + examplePath?: string; + git: boolean; +}; + +export type CreateContext = { + example: string; + targetDir: string; + packageName: string; + packageManager: PackageManagerName; +}; From c872f80e55c7f3c778266713f73b6d3aefe99b96 Mon Sep 17 00:00:00 2001 From: zuiidea Date: Tue, 14 Apr 2026 22:36:11 +0800 Subject: [PATCH 14/16] feat(create): wire CLI entry and create command pipeline Made-with: Cursor --- packages/create/src/cli.ts | 79 +++++++++++++++++++- packages/create/src/commands/create.ts | 99 ++++++++++++++++++++++++++ 2 files changed, 176 insertions(+), 2 deletions(-) create mode 100644 packages/create/src/commands/create.ts diff --git a/packages/create/src/cli.ts b/packages/create/src/cli.ts index b0bb886..251d817 100644 --- a/packages/create/src/cli.ts +++ b/packages/create/src/cli.ts @@ -1,2 +1,77 @@ -#!/usr/bin/env node -console.log("create-antd-admin stub"); +import { readFileSync } from "node:fs"; +import path from "node:path"; +import { fileURLToPath } from "node:url"; +import { Command, Option } from "commander"; +import pc from "picocolors"; +import { runCreate } from "./commands/create.js"; +import { EXIT_ERROR, EXIT_SIGINT } from "./constants.js"; +import { CliError } from "./errors.js"; + +const pkg = JSON.parse( + readFileSync( + path.join(path.dirname(fileURLToPath(import.meta.url)), "../package.json"), + "utf8" + ) +) as { version: string }; + +const program = new Command(); + +program + .name("create-antd-admin") + .description("Create an Antd Admin app from official examples") + .version(pkg.version, "-v, --version") + .argument("[project-directory]", "Directory for the new project") + .option("-e, --example ", "Example name or template URL") + .option("--example-path ", "Path inside repo when URL is ambiguous") + .addOption( + new Option("-m, --package-manager ", "Package manager").choices([ + "npm", + "yarn", + "pnpm", + "bun", + ]) + ) + .option("--skip-install", "Skip installing dependencies", false) + .option("--skip-transforms", "Skip code transforms", false) + .option("--no-git", "Skip git repository initialization") + .action( + async ( + projectDirectory: string | undefined, + cmdOpts: { + example?: string; + examplePath?: string; + packageManager?: "npm" | "yarn" | "pnpm" | "bun"; + skipInstall?: boolean; + skipTransforms?: boolean; + git?: boolean; + } + ) => { + try { + await runCreate({ + projectDirectory, + example: cmdOpts.example, + examplePath: cmdOpts.examplePath, + packageManager: cmdOpts.packageManager, + skipInstall: Boolean(cmdOpts.skipInstall), + skipTransforms: Boolean(cmdOpts.skipTransforms), + git: cmdOpts.git !== false, + }); + } catch (e) { + if (e instanceof CliError) { + console.error(pc.red(e.message)); + process.exit(e.exitCode); + } + console.error(e); + process.exit(EXIT_ERROR); + } + } + ); + +process.on("SIGINT", () => { + process.exit(EXIT_SIGINT); +}); + +program.parseAsync(process.argv).catch((e) => { + console.error(e); + process.exit(EXIT_ERROR); +}); diff --git a/packages/create/src/commands/create.ts b/packages/create/src/commands/create.ts new file mode 100644 index 0000000..cdc529d --- /dev/null +++ b/packages/create/src/commands/create.ts @@ -0,0 +1,99 @@ +import fsSync from "node:fs"; +import path from "node:path"; +import pc from "picocolors"; +import { assertValidExample, loadExamplesManifest } from "../examples.js"; +import { downloadExampleToTemp } from "../download.js"; +import { installDependencies } from "../install.js"; +import { + detectAvailableManagers, + type PackageManagerName, +} from "../package-manager.js"; +import { resolveTargetRoot } from "../paths.js"; +import { + promptExample, + promptPackageManager, + promptPackageName, + promptTargetDir, +} from "../prompts.js"; +import { resolveExampleSource } from "../resolve-example-source.js"; +import { tryGitInit } from "../git.js"; +import { runTransforms } from "../transforms/run-transforms.js"; + +export async function runCreate( + opts: Omit & { + projectDirectory?: string; + git?: boolean; + } +): Promise { + const cwd = process.cwd(); + const manifest = loadExamplesManifest(); + + const exampleTrim = opts.example?.trim(); + const example = exampleTrim + ? exampleTrim + : await promptExample(manifest); + + if (!/^https?:\/\//i.test(example)) { + assertValidExample(example, manifest); + } + + const projectDirRaw = opts.projectDirectory?.trim(); + const projectDir = projectDirRaw + ? projectDirRaw + : await promptTargetDir(); + + const targetRoot = resolveTargetRoot(cwd, projectDir); + fsSync.mkdirSync(targetRoot, { recursive: true }); + + const defaultPkgName = + projectDir === "." + ? (() => { + const normalized = path + .basename(cwd) + .toLowerCase() + .replace(/[^a-z0-9]+/g, "-") + .replace(/^-+|-+$/g, ""); + return normalized || "antd-admin-app"; + })() + : path.basename(targetRoot); + + const packageName = await promptPackageName(defaultPkgName); + + const packageManager: PackageManagerName = + opts.packageManager ?? + (await promptPackageManager(detectAvailableManagers())); + + if (opts.skipTransforms && opts.packageManager) { + console.warn( + pc.yellow( + "--skip-transforms was used with an explicit package manager; package.json name may not be updated before install." + ) + ); + } + + const { gigetSource } = resolveExampleSource({ + example, + examplePath: opts.examplePath, + }); + + const tmp = await downloadExampleToTemp(gigetSource); + try { + fsSync.cpSync(tmp, targetRoot, { recursive: true, dereference: true }); + } finally { + fsSync.rmSync(tmp, { recursive: true, force: true }); + } + + await runTransforms({ + projectRoot: targetRoot, + packageName, + skip: opts.skipTransforms, + }); + + if (!opts.skipInstall) { + installDependencies(targetRoot, packageManager); + } + + tryGitInit(targetRoot, opts.git !== false); + + console.log(pc.green(`Success! Project created at ${targetRoot}`)); +} From 3579246c24de98b9e7f55bc25b5e51ac4f9103ea Mon Sep 17 00:00:00 2001 From: zuiidea Date: Tue, 14 Apr 2026 22:36:56 +0800 Subject: [PATCH 15/16] docs: document create-antd-admin dlx usage; verify turbo build Made-with: Cursor --- README.md | 2 ++ 1 file changed, 2 insertions(+) diff --git a/README.md b/README.md index 2e3f5ba..e1a67f3 100644 --- a/README.md +++ b/README.md @@ -49,6 +49,8 @@ Balanced admin monorepo: MSW mocks, minimal RBAC, full CRUD, and Playwright E2E ## Templates +`pnpm dlx create-antd-admin@latest` + | Directory | Use when | | -------------------- | -------- | | [`apps/with-lingui`](./apps/with-lingui/) | You want **LinguiJS** (en + zh), `.po` extract/compile, and a language switcher — this is the fuller reference stack. | From ca3cc71054334ca3f9c8683a2e30790165426c48 Mon Sep 17 00:00:00 2001 From: zuiidea Date: Tue, 14 Apr 2026 22:37:01 +0800 Subject: [PATCH 16/16] test(create): integration test for transforms without network Made-with: Cursor --- .../create/fixtures/minimal-app/package.json | 5 ++++ .../src/integration/create-pipeline.test.ts | 26 +++++++++++++++++++ 2 files changed, 31 insertions(+) create mode 100644 packages/create/fixtures/minimal-app/package.json create mode 100644 packages/create/src/integration/create-pipeline.test.ts diff --git a/packages/create/fixtures/minimal-app/package.json b/packages/create/fixtures/minimal-app/package.json new file mode 100644 index 0000000..5e4a02c --- /dev/null +++ b/packages/create/fixtures/minimal-app/package.json @@ -0,0 +1,5 @@ +{ + "name": "template-placeholder", + "version": "0.0.0", + "private": true +} diff --git a/packages/create/src/integration/create-pipeline.test.ts b/packages/create/src/integration/create-pipeline.test.ts new file mode 100644 index 0000000..d5b095f --- /dev/null +++ b/packages/create/src/integration/create-pipeline.test.ts @@ -0,0 +1,26 @@ +import fs from "node:fs"; +import os from "node:os"; +import path from "node:path"; +import { fileURLToPath } from "node:url"; +import { describe, expect, it } from "vitest"; +import { runTransforms } from "../transforms/run-transforms.js"; + +describe("create pipeline transforms", () => { + it("renames package.json", async () => { + const tmp = fs.mkdtempSync(path.join(os.tmpdir(), "cad-")); + const fixture = path.join( + path.dirname(fileURLToPath(import.meta.url)), + "../../fixtures/minimal-app" + ); + fs.cpSync(fixture, tmp, { recursive: true }); + await runTransforms({ + projectRoot: tmp, + packageName: "my-fine-app", + skip: false, + }); + const pkg = JSON.parse( + fs.readFileSync(path.join(tmp, "package.json"), "utf8") + ); + expect(pkg.name).toBe("my-fine-app"); + }); +});