diff --git a/.changeset/add-examples.md b/.changeset/add-examples.md new file mode 100644 index 0000000..a8031a9 --- /dev/null +++ b/.changeset/add-examples.md @@ -0,0 +1,5 @@ +--- +"@ilokesto/form": patch +--- + +Add Vue/Solid/Svelte login form examples and React validation flow example \ No newline at end of file diff --git a/examples/react-validation-flow/README.md b/examples/react-validation-flow/README.md new file mode 100644 index 0000000..ef0d0fd --- /dev/null +++ b/examples/react-validation-flow/README.md @@ -0,0 +1,25 @@ +# React validation flow example + +This Vite + React + TypeScript example demonstrates sync and async validation with `validateOn: ['change', 'blur', 'submit']`. + +## What it demonstrates + +- `useForm` with inline options (no pre-created `CreateForm` instance) +- `useField` for field binding with reactive `value`, `errors`, `dirty`, and `touched` +- Async Standard Schema validators that simulate server-side checks with a delay +- `validateOn: ['change', 'blur', 'submit']` so fields validate on every keystroke, blur, and submit +- `useFormState` for form-wide state (isDirty, isValid, submitCount) +- `handleSubmit` with type-safe onValid callback + +Async validation uses a generation counter internally, so rapid typing always reflects the most recent values. Stale async results are discarded. + +## Run + +From the repository root: + +```sh +pnpm --dir examples/react-validation-flow install +pnpm --dir examples/react-validation-flow dev +``` + +The example aliases `@ilokesto/form` and `@ilokesto/form/react` to the local `src/` files, so it can run before the package is built. \ No newline at end of file diff --git a/examples/react-validation-flow/index.html b/examples/react-validation-flow/index.html new file mode 100644 index 0000000..0e36902 --- /dev/null +++ b/examples/react-validation-flow/index.html @@ -0,0 +1,12 @@ + + + + + + @ilokesto/form React validation flow example + + +
+ + + \ No newline at end of file diff --git a/examples/react-validation-flow/package.json b/examples/react-validation-flow/package.json new file mode 100644 index 0000000..166b3f3 --- /dev/null +++ b/examples/react-validation-flow/package.json @@ -0,0 +1,27 @@ +{ + "name": "@ilokesto/form-react-validation-flow-example", + "version": "0.0.0", + "private": true, + "type": "module", + "scripts": { + "dev": "vite", + "build": "tsc --noEmit && vite build", + "typecheck": "tsc --noEmit" + }, + "dependencies": { + "@ilokesto/form": "workspace:*", + "react": "^19.0.0", + "react-dom": "^19.2.6", + "typescript": "^6.0.2", + "vite": "^8.1.0" + }, + "devDependencies": { + "@babel/core": "^8.0.1", + "@rolldown/plugin-babel": "^0.2.3", + "@types/babel__core": "^7.20.5", + "@types/react": "^19.2.15", + "@types/react-dom": "^19.2.3", + "@vitejs/plugin-react": "^6.0.3", + "babel-plugin-react-compiler": "^1.0.0" + } +} \ No newline at end of file diff --git a/examples/react-validation-flow/src/App.tsx b/examples/react-validation-flow/src/App.tsx new file mode 100644 index 0000000..8933cb8 --- /dev/null +++ b/examples/react-validation-flow/src/App.tsx @@ -0,0 +1,139 @@ +import { CreateForm } from '@ilokesto/form'; +import { useForm } from '@ilokesto/form/react'; +import { useState } from 'react'; +import './styles.css'; + +type FormValues = { + username: string; + email: string; +}; + +const DELAY_MS = 400; + +function asyncCheck( + check: (value: string) => string | null, +): { + '~standard': { + version: 1; + vendor: 'example-async'; + validate: (value: unknown) => Promise<{ value: unknown } | { issues: { message: string; path: never[] }[] }>; + }; +} { + return { + '~standard': { + version: 1, + vendor: 'example-async', + async validate(value: unknown) { + await new Promise((resolve) => setTimeout(resolve, DELAY_MS)); + const message = check(typeof value === 'string' ? value : ''); + if (message) { + return { issues: [{ message, path: [] }] }; + } + return { value }; + }, + }, + }; +} + +const usernameSchema = asyncCheck((v) => { + if (v.trim().length < 3) return 'Username must be at least 3 characters'; + if (!/^[a-z]/.test(v)) return 'Username must start with a lowercase letter'; + return null; +}); + +const emailSchema = asyncCheck((v) => { + if (v.trim() === '') return 'Email is required'; + if (!/^[^\s@]+@[^\s@]+\.[^\s@]+$/.test(v)) return 'Enter a valid email address'; + return null; +}); + +function ValidationFlowExample() { + const [submitted, setSubmitted] = useState(null); + const { useField, useFormState, handleSubmit } = useForm({ + defaultValues: { username: '', email: '' }, + validateOn: ['change', 'blur', 'submit'], + }); + + const username = useField({ name: 'username', schema: usernameSchema }); + const email = useField({ name: 'email', schema: emailSchema }); + const state = useFormState(); + + return ( +
+
+

React + Vite + TypeScript

+

Validation flow example

+

+ Demonstrates validateOn: ['change', 'blur', 'submit'] with async + Standard Schema validators. Each field validates on every keystroke (change), + blur, and submit. The async schemas simulate server-side checks with a + {DELAY_MS}ms delay. +

+ +
setSubmitted(values), + )} + > + + + + +
+ isDirty: {String(state.isDirty)} + isValid: {String(state.isValid)} + submitCount: {state.submitCount} +
+ + +
+ + {submitted && ( +
+ Submitted values +
{JSON.stringify(submitted, null, 2)}
+ +
+ )} + +
{JSON.stringify({
+          values: { username: username.value, email: email.value },
+          isDirty: state.isDirty,
+          isValid: state.isValid,
+          submitCount: state.submitCount,
+          dirtyFields: state.dirtyFields,
+          touchedFields: state.touchedFields,
+        }, null, 2)}
+
+
+ ); +} + +export default ValidationFlowExample; \ No newline at end of file diff --git a/examples/react-validation-flow/src/main.tsx b/examples/react-validation-flow/src/main.tsx new file mode 100644 index 0000000..d4bd065 --- /dev/null +++ b/examples/react-validation-flow/src/main.tsx @@ -0,0 +1,10 @@ +import { StrictMode } from 'react'; +import { createRoot } from 'react-dom/client'; +import App from './App'; +import './styles.css'; + +createRoot(document.getElementById('root')!).render( + + + , +); \ No newline at end of file diff --git a/examples/react-validation-flow/src/styles.css b/examples/react-validation-flow/src/styles.css new file mode 100644 index 0000000..2ba3976 --- /dev/null +++ b/examples/react-validation-flow/src/styles.css @@ -0,0 +1,164 @@ +:root { + color: #172033; + background: #f4f7fb; + font-family: Inter, ui-sans-serif, system-ui, -apple-system, BlinkMacSystemFont, "Segoe UI", sans-serif; +} + +* { + box-sizing: border-box; +} + +body { + margin: 0; +} + +button, +input { + font: inherit; +} + +.page-shell { + display: grid; + min-height: 100vh; + place-items: center; + padding: 32px; +} + +.example-card { + width: min(100%, 560px); + padding: 32px; + border: 1px solid #dce4f0; + border-radius: 24px; + background: #ffffff; + box-shadow: 0 24px 70px rgb(23 32 51 / 12%); +} + +.eyebrow { + margin: 0 0 8px; + color: #54617a; + font-size: 0.78rem; + font-weight: 700; + letter-spacing: 0.08em; + text-transform: uppercase; +} + +h1 { + margin: 0; + font-size: clamp(2rem, 7vw, 3rem); + line-height: 1; +} + +.description { + margin: 16px 0 28px; + color: #54617a; + line-height: 1.6; +} + +.form-grid { + display: grid; + gap: 16px; +} + +label { + display: grid; + gap: 6px; + color: #2b3448; + font-weight: 700; +} + +input { + width: 100%; + border: 1px solid #c9d4e5; + border-radius: 12px; + padding: 12px 14px; + color: #172033; + background: #f9fbff; +} + +input:focus-visible { + border-color: #4f7cff; + outline: 3px solid rgb(79 124 255 / 20%); +} + +.field-hint { + color: #7a87a0; + font-size: 0.82rem; + font-weight: 400; +} + +.field-errors { + margin: 0; + padding: 0 0 0 18px; + color: #d93025; + font-size: 0.88rem; + font-weight: 600; +} + +.status-bar { + display: flex; + flex-wrap: wrap; + gap: 10px; + align-items: center; +} + +.status-pill { + border: 1px solid #dce4f0; + border-radius: 999px; + padding: 8px 12px; + color: #41506a; + background: #f9fbff; + font-size: 0.9rem; + font-weight: 700; +} + +button { + border: 0; + border-radius: 12px; + padding: 12px 16px; + color: #ffffff; + background: #345cf6; + font-weight: 800; + cursor: pointer; +} + +button:disabled { + background: #aab4c8; + cursor: not-allowed; +} + +button[type="button"] { + color: #213159; + background: #e9efff; +} + +.result-panel { + display: grid; + gap: 10px; + margin-top: 20px; + border: 1px solid #bce0c9; + border-radius: 16px; + padding: 16px; + background: #eef9f1; + color: #1a5c2e; +} + +.result-panel strong { + color: #0f3d1a; +} + +.result-panel pre { + margin: 0; + border-radius: 12px; + padding: 12px; + color: #dce7ff; + background: #172033; +} + +pre { + margin: 24px 0 0; + overflow: auto; + border-radius: 16px; + padding: 16px; + color: #dce7ff; + background: #172033; +} \ No newline at end of file diff --git a/examples/react-validation-flow/src/vite-env.d.ts b/examples/react-validation-flow/src/vite-env.d.ts new file mode 100644 index 0000000..151aa68 --- /dev/null +++ b/examples/react-validation-flow/src/vite-env.d.ts @@ -0,0 +1 @@ +/// \ No newline at end of file diff --git a/examples/react-validation-flow/tsconfig.json b/examples/react-validation-flow/tsconfig.json new file mode 100644 index 0000000..2be5387 --- /dev/null +++ b/examples/react-validation-flow/tsconfig.json @@ -0,0 +1,24 @@ +{ + "compilerOptions": { + "target": "ES2022", + "useDefineForClassFields": true, + "lib": ["DOM", "DOM.Iterable", "ES2022"], + "allowJs": false, + "skipLibCheck": true, + "esModuleInterop": true, + "allowSyntheticDefaultImports": true, + "strict": true, + "forceConsistentCasingInFileNames": true, + "module": "ESNext", + "moduleResolution": "bundler", + "resolveJsonModule": true, + "isolatedModules": true, + "noEmit": true, + "jsx": "react-jsx", + "paths": { + "@ilokesto/form": ["../../src/index.ts"], + "@ilokesto/form/react": ["../../src/react/index.ts"] + } + }, + "include": ["src", "vite.config.ts"] +} \ No newline at end of file diff --git a/examples/react-validation-flow/vite.config.ts b/examples/react-validation-flow/vite.config.ts new file mode 100644 index 0000000..602b97e --- /dev/null +++ b/examples/react-validation-flow/vite.config.ts @@ -0,0 +1,19 @@ +import { resolve } from 'node:path'; +import babel from '@rolldown/plugin-babel'; +import react, { reactCompilerPreset } from '@vitejs/plugin-react'; +import { defineConfig } from 'vite'; + +export default defineConfig({ + plugins: [ + react(), + babel({ + presets: [reactCompilerPreset()], + }), + ], + resolve: { + alias: { + '@ilokesto/form/react': resolve(__dirname, '../../src/react/index.ts'), + '@ilokesto/form': resolve(__dirname, '../../src/index.ts'), + }, + }, +}); \ No newline at end of file diff --git a/examples/solid-login-form/README.md b/examples/solid-login-form/README.md new file mode 100644 index 0000000..396c75d --- /dev/null +++ b/examples/solid-login-form/README.md @@ -0,0 +1,22 @@ +# Solid login form example + +This Vite + Solid + TypeScript example shows a simple email/password login form using the Solid adapter. + +## What it demonstrates + +- `useForm` with a pre-created `CreateForm` instance +- `useRegister` for reactive input binding via spread props +- Field-local Standard Schema validation on `blur` and `submit` +- `useFormState` for reactive form-wide state (called as `state()` signal) +- `handleSubmit` for type-safe submit callbacks + +## Run + +From the repository root: + +```sh +pnpm --dir examples/solid-login-form install +pnpm --dir examples/solid-login-form dev +``` + +The example aliases `@ilokesto/form` and `@ilokesto/form/solid` to the local `src/` files, so it can run before the package is built. \ No newline at end of file diff --git a/examples/solid-login-form/index.html b/examples/solid-login-form/index.html new file mode 100644 index 0000000..0fe1fab --- /dev/null +++ b/examples/solid-login-form/index.html @@ -0,0 +1,12 @@ + + + + + + @ilokesto/form Solid login example + + +
+ + + \ No newline at end of file diff --git a/examples/solid-login-form/package.json b/examples/solid-login-form/package.json new file mode 100644 index 0000000..e6929b8 --- /dev/null +++ b/examples/solid-login-form/package.json @@ -0,0 +1,20 @@ +{ + "name": "@ilokesto/form-solid-login-example", + "version": "0.0.0", + "private": true, + "type": "module", + "scripts": { + "dev": "vite", + "build": "vite build", + "typecheck": "tsc --noEmit" + }, + "dependencies": { + "@ilokesto/form": "workspace:*", + "solid-js": "^1.9.13" + }, + "devDependencies": { + "typescript": "^6.0.2", + "vite": "^8.1.0", + "vite-plugin-solid": "^2.11.0" + } +} \ No newline at end of file diff --git a/examples/solid-login-form/src/App.tsx b/examples/solid-login-form/src/App.tsx new file mode 100644 index 0000000..45d1436 --- /dev/null +++ b/examples/solid-login-form/src/App.tsx @@ -0,0 +1,94 @@ +import { CreateForm } from '@ilokesto/form'; +import type { Form } from '@ilokesto/form'; +import { useForm } from '@ilokesto/form/solid'; +import './styles.css'; + +type LoginValues = { + email: string; + password: string; +}; + +const emailSchema = { + '~standard': { + version: 1, + vendor: 'example', + validate(value: unknown) { + if (typeof value !== 'string' || value.trim() === '') { + return { issues: [{ message: 'Email is required', path: [] }] }; + } + if (!/^[^\s@]+@[^\s@]+\.[^\s@]+$/.test(value)) { + return { issues: [{ message: 'Enter a valid email address', path: [] }] }; + } + return { value }; + }, + }, +}; + +const passwordSchema = { + '~standard': { + version: 1, + vendor: 'example', + validate(value: unknown) { + if (typeof value !== 'string' || value.length === 0) { + return { issues: [{ message: 'Password is required', path: [] }] }; + } + if (value.length < 6) { + return { issues: [{ message: 'Password must be at least 6 characters', path: [] }] }; + } + return { value }; + }, + }, +}; + +const form: Form = new CreateForm({ + defaultValues: { email: '', password: '' }, + validateOn: ['blur', 'submit'], +}); + +export default function App() { + const { useRegister, useFormState, handleSubmit } = useForm(form); + const email = useRegister({ name: 'email', schema: emailSchema }); + const password = useRegister({ name: 'password', type: 'password', schema: passwordSchema }); + const state = useFormState(); + + const onSubmit = handleSubmit( + (values) => window.alert(JSON.stringify(values, null, 2)), + ); + + return ( +
+
+

Solid + Vite + TypeScript

+

Login form example

+

+ Email and password fields with field-local Standard Schema validation. + Uses useRegister, useFormState, and + handleSubmit from the Solid adapter. +

+ +
+ + + + + +
+ +
{JSON.stringify({
+          values: form.getValues(),
+          isDirty: state().isDirty,
+          isValid: state().isValid,
+          submitCount: state().submitCount,
+        }, null, 2)}
+
+
+ ); +} \ No newline at end of file diff --git a/examples/solid-login-form/src/main.tsx b/examples/solid-login-form/src/main.tsx new file mode 100644 index 0000000..57cde46 --- /dev/null +++ b/examples/solid-login-form/src/main.tsx @@ -0,0 +1,9 @@ +/* @refresh reload */ +import { render } from 'solid-js/web'; +import App from './App'; + +const root = document.getElementById('root'); + +if (!root) throw new Error('Root element not found'); + +render(() => , root); \ No newline at end of file diff --git a/examples/solid-login-form/src/styles.css b/examples/solid-login-form/src/styles.css new file mode 100644 index 0000000..c48d843 --- /dev/null +++ b/examples/solid-login-form/src/styles.css @@ -0,0 +1,105 @@ +:root { + color: #172033; + background: #f4f7fb; + font-family: Inter, ui-sans-serif, system-ui, -apple-system, BlinkMacSystemFont, "Segoe UI", sans-serif; +} + +* { + box-sizing: border-box; +} + +body { + margin: 0; +} + +button, +input { + font: inherit; +} + +.page-shell { + display: grid; + min-height: 100vh; + place-items: center; + padding: 32px; +} + +.example-card { + width: min(100%, 560px); + padding: 32px; + border: 1px solid #dce4f0; + border-radius: 24px; + background: #ffffff; + box-shadow: 0 24px 70px rgb(23 32 51 / 12%); +} + +.eyebrow { + margin: 0 0 8px; + color: #54617a; + font-size: 0.78rem; + font-weight: 700; + letter-spacing: 0.08em; + text-transform: uppercase; +} + +h1 { + margin: 0; + font-size: clamp(2rem, 7vw, 3rem); + line-height: 1; +} + +.description { + margin: 16px 0 28px; + color: #54617a; + line-height: 1.6; +} + +.form-grid { + display: grid; + gap: 16px; +} + +label { + display: grid; + gap: 8px; + color: #2b3448; + font-weight: 700; +} + +input { + width: 100%; + border: 1px solid #c9d4e5; + border-radius: 12px; + padding: 12px 14px; + color: #172033; + background: #f9fbff; +} + +input:focus-visible { + border-color: #4f7cff; + outline: 3px solid rgb(79 124 255 / 20%); +} + +button { + border: 0; + border-radius: 12px; + padding: 12px 16px; + color: #ffffff; + background: #345cf6; + font-weight: 800; + cursor: pointer; +} + +button:disabled { + background: #aab4c8; + cursor: not-allowed; +} + +pre { + margin: 24px 0 0; + overflow: auto; + border-radius: 16px; + padding: 16px; + color: #dce7ff; + background: #172033; +} \ No newline at end of file diff --git a/examples/solid-login-form/src/vite-env.d.ts b/examples/solid-login-form/src/vite-env.d.ts new file mode 100644 index 0000000..151aa68 --- /dev/null +++ b/examples/solid-login-form/src/vite-env.d.ts @@ -0,0 +1 @@ +/// \ No newline at end of file diff --git a/examples/solid-login-form/tsconfig.json b/examples/solid-login-form/tsconfig.json new file mode 100644 index 0000000..4c5e46c --- /dev/null +++ b/examples/solid-login-form/tsconfig.json @@ -0,0 +1,25 @@ +{ + "compilerOptions": { + "target": "ES2022", + "useDefineForClassFields": true, + "lib": ["DOM", "DOM.Iterable", "ES2022"], + "allowJs": false, + "skipLibCheck": true, + "esModuleInterop": true, + "allowSyntheticDefaultImports": true, + "strict": true, + "forceConsistentCasingInFileNames": true, + "module": "ESNext", + "moduleResolution": "bundler", + "resolveJsonModule": true, + "isolatedModules": true, + "noEmit": true, + "jsx": "preserve", + "jsxImportSource": "solid-js", + "paths": { + "@ilokesto/form": ["../../src/index.ts"], + "@ilokesto/form/solid": ["../../src/solid/index.ts"] + } + }, + "include": ["src", "vite.config.ts"] +} \ No newline at end of file diff --git a/examples/solid-login-form/vite.config.ts b/examples/solid-login-form/vite.config.ts new file mode 100644 index 0000000..13f4a3d --- /dev/null +++ b/examples/solid-login-form/vite.config.ts @@ -0,0 +1,13 @@ +import { resolve } from 'node:path'; +import solid from 'vite-plugin-solid'; +import { defineConfig } from 'vite'; + +export default defineConfig({ + plugins: [solid()], + resolve: { + alias: { + '@ilokesto/form/solid': resolve(__dirname, '../../src/solid/index.ts'), + '@ilokesto/form': resolve(__dirname, '../../src/index.ts'), + }, + }, +}); \ No newline at end of file diff --git a/examples/svelte-login-form/README.md b/examples/svelte-login-form/README.md new file mode 100644 index 0000000..dea1008 --- /dev/null +++ b/examples/svelte-login-form/README.md @@ -0,0 +1,22 @@ +# Svelte login form example + +This Vite + Svelte 5 + TypeScript example shows a simple email/password login form using the Svelte adapter. + +## What it demonstrates + +- `useForm` with a pre-created `CreateForm` instance +- `register` Svelte action for DOM binding via `use:register` +- Field-local Standard Schema validation on `blur` and `submit` +- `useFormState` as a Svelte readable store (accessed with `$state` prefix) +- `handleSubmit` for type-safe submit callbacks + +## Run + +From the repository root: + +```sh +pnpm --dir examples/svelte-login-form install +pnpm --dir examples/svelte-login-form dev +``` + +The example aliases `@ilokesto/form` and `@ilokesto/form/svelte` to the local `src/` files, so it can run before the package is built. \ No newline at end of file diff --git a/examples/svelte-login-form/index.html b/examples/svelte-login-form/index.html new file mode 100644 index 0000000..e855367 --- /dev/null +++ b/examples/svelte-login-form/index.html @@ -0,0 +1,12 @@ + + + + + + @ilokesto/form Svelte login example + + +
+ + + \ No newline at end of file diff --git a/examples/svelte-login-form/package.json b/examples/svelte-login-form/package.json new file mode 100644 index 0000000..11afc43 --- /dev/null +++ b/examples/svelte-login-form/package.json @@ -0,0 +1,22 @@ +{ + "name": "@ilokesto/form-svelte-login-example", + "version": "0.0.0", + "private": true, + "type": "module", + "scripts": { + "dev": "vite", + "build": "vite build", + "typecheck": "svelte-check --tsconfig ./tsconfig.json" + }, + "dependencies": { + "@ilokesto/form": "workspace:*", + "svelte": "^5.55.9" + }, + "devDependencies": { + "@sveltejs/vite-plugin-svelte": "^6.1.0", + "@tsconfig/svelte": "^5.0.4", + "svelte-check": "^4.2.2", + "typescript": "^6.0.2", + "vite": "^8.1.0" + } +} \ No newline at end of file diff --git a/examples/svelte-login-form/src/App.svelte b/examples/svelte-login-form/src/App.svelte new file mode 100644 index 0000000..211316b --- /dev/null +++ b/examples/svelte-login-form/src/App.svelte @@ -0,0 +1,171 @@ + + +
+
+

Svelte 5 + Vite + TypeScript

+

Login form example

+

+ Email and password fields with field-local Standard Schema validation. + Uses the register action, useFormState readable store, + and handleSubmit from the Svelte adapter. +

+ +
+ + + + + +
+ +
{JSON.stringify({ values: form.getValues(), isDirty: $state.isDirty, isValid: $state.isValid, submitCount: $state.submitCount }, null, 2)}
+
+
+ + \ No newline at end of file diff --git a/examples/svelte-login-form/src/main.ts b/examples/svelte-login-form/src/main.ts new file mode 100644 index 0000000..1d07ef0 --- /dev/null +++ b/examples/svelte-login-form/src/main.ts @@ -0,0 +1,6 @@ +import { mount } from 'svelte'; +import App from './App.svelte'; + +const app = mount(App, { target: document.getElementById('app')! }); + +export default app; \ No newline at end of file diff --git a/examples/svelte-login-form/src/vite-env.d.ts b/examples/svelte-login-form/src/vite-env.d.ts new file mode 100644 index 0000000..151aa68 --- /dev/null +++ b/examples/svelte-login-form/src/vite-env.d.ts @@ -0,0 +1 @@ +/// \ No newline at end of file diff --git a/examples/svelte-login-form/tsconfig.json b/examples/svelte-login-form/tsconfig.json new file mode 100644 index 0000000..4a66a2f --- /dev/null +++ b/examples/svelte-login-form/tsconfig.json @@ -0,0 +1,22 @@ +{ + "extends": "@tsconfig/svelte/tsconfig.json", + "compilerOptions": { + "target": "ES2022", + "lib": ["DOM", "DOM.Iterable", "ES2022"], + "module": "ESNext", + "moduleResolution": "bundler", + "strict": true, + "noEmit": true, + "skipLibCheck": true, + "esModuleInterop": true, + "allowSyntheticDefaultImports": true, + "isolatedModules": true, + "resolveJsonModule": true, + "forceConsistentCasingInFileNames": true, + "paths": { + "@ilokesto/form": ["../../src/index.ts"], + "@ilokesto/form/svelte": ["../../src/svelte/index.ts"] + } + }, + "include": ["src", "vite.config.ts"] +} \ No newline at end of file diff --git a/examples/svelte-login-form/vite.config.ts b/examples/svelte-login-form/vite.config.ts new file mode 100644 index 0000000..500ff3f --- /dev/null +++ b/examples/svelte-login-form/vite.config.ts @@ -0,0 +1,13 @@ +import { resolve } from 'node:path'; +import { svelte } from '@sveltejs/vite-plugin-svelte'; +import { defineConfig } from 'vite'; + +export default defineConfig({ + plugins: [svelte()], + resolve: { + alias: { + '@ilokesto/form/svelte': resolve(__dirname, '../../src/svelte/index.ts'), + '@ilokesto/form': resolve(__dirname, '../../src/index.ts'), + }, + }, +}); \ No newline at end of file diff --git a/examples/vue-login-form/README.md b/examples/vue-login-form/README.md new file mode 100644 index 0000000..50d3d71 --- /dev/null +++ b/examples/vue-login-form/README.md @@ -0,0 +1,22 @@ +# Vue login form example + +This Vite + Vue 3 + TypeScript example shows a simple email/password login form using the Vue adapter. + +## What it demonstrates + +- `useForm` with a pre-created `CreateForm` instance +- `useRegister` for field binding with `v-bind` spread +- Field-local Standard Schema validation on `blur` and `submit` +- `useFormState` for reactive form-wide state (isDirty, isValid, submitCount) +- `handleSubmit` for type-safe submit callbacks + +## Run + +From the repository root: + +```sh +pnpm --dir examples/vue-login-form install +pnpm --dir examples/vue-login-form dev +``` + +The example aliases `@ilokesto/form` and `@ilokesto/form/vue` to the local `src/` files, so it can run before the package is built. \ No newline at end of file diff --git a/examples/vue-login-form/index.html b/examples/vue-login-form/index.html new file mode 100644 index 0000000..f616b16 --- /dev/null +++ b/examples/vue-login-form/index.html @@ -0,0 +1,12 @@ + + + + + + @ilokesto/form Vue login example + + +
+ + + \ No newline at end of file diff --git a/examples/vue-login-form/package.json b/examples/vue-login-form/package.json new file mode 100644 index 0000000..37a3bf6 --- /dev/null +++ b/examples/vue-login-form/package.json @@ -0,0 +1,21 @@ +{ + "name": "@ilokesto/form-vue-login-example", + "version": "0.0.0", + "private": true, + "type": "module", + "scripts": { + "dev": "vite", + "build": "vue-tsc --noEmit && vite build", + "typecheck": "vue-tsc --noEmit" + }, + "dependencies": { + "@ilokesto/form": "workspace:*", + "vue": "^3.5.34" + }, + "devDependencies": { + "@vitejs/plugin-vue": "^6.0.0", + "typescript": "^6.0.2", + "vite": "^8.1.0", + "vue-tsc": "^2.2.0" + } +} \ No newline at end of file diff --git a/examples/vue-login-form/src/App.vue b/examples/vue-login-form/src/App.vue new file mode 100644 index 0000000..ffd6307 --- /dev/null +++ b/examples/vue-login-form/src/App.vue @@ -0,0 +1,137 @@ + + + + + \ No newline at end of file diff --git a/examples/vue-login-form/src/env.d.ts b/examples/vue-login-form/src/env.d.ts new file mode 100644 index 0000000..e7e95ce --- /dev/null +++ b/examples/vue-login-form/src/env.d.ts @@ -0,0 +1,7 @@ +/// + +declare module '*.vue' { + import type { DefineComponent } from 'vue'; + const component: DefineComponent; + export default component; +} \ No newline at end of file diff --git a/examples/vue-login-form/src/main.ts b/examples/vue-login-form/src/main.ts new file mode 100644 index 0000000..e6031ae --- /dev/null +++ b/examples/vue-login-form/src/main.ts @@ -0,0 +1,49 @@ +import { CreateForm } from '@ilokesto/form'; +import { createApp } from 'vue'; +import App from './App.vue'; + +type LoginValues = { + email: string; + password: string; +}; + +const emailSchema = { + '~standard': { + version: 1, + vendor: 'example', + validate(value: unknown) { + if (typeof value !== 'string' || value.trim() === '') { + return { issues: [{ message: 'Email is required', path: [] }] }; + } + if (!/^[^\s@]+@[^\s@]+\.[^\s@]+$/.test(value)) { + return { issues: [{ message: 'Enter a valid email address', path: [] }] }; + } + return { value }; + }, + }, +}; + +const passwordSchema = { + '~standard': { + version: 1, + vendor: 'example', + validate(value: unknown) { + if (typeof value !== 'string' || value.length === 0) { + return { issues: [{ message: 'Password is required', path: [] }] }; + } + if (value.length < 6) { + return { issues: [{ message: 'Password must be at least 6 characters', path: [] }] }; + } + return { value }; + }, + }, +}; + +const form = new CreateForm({ + defaultValues: { email: '', password: '' }, + validateOn: ['blur', 'submit'], +}); + +export { form, emailSchema, passwordSchema }; + +createApp(App).mount('#app'); \ No newline at end of file diff --git a/examples/vue-login-form/tsconfig.json b/examples/vue-login-form/tsconfig.json new file mode 100644 index 0000000..0cbda16 --- /dev/null +++ b/examples/vue-login-form/tsconfig.json @@ -0,0 +1,24 @@ +{ + "compilerOptions": { + "target": "ES2022", + "useDefineForClassFields": true, + "lib": ["DOM", "DOM.Iterable", "ES2022"], + "allowJs": false, + "skipLibCheck": true, + "esModuleInterop": true, + "allowSyntheticDefaultImports": true, + "strict": true, + "forceConsistentCasingInFileNames": true, + "module": "ESNext", + "moduleResolution": "bundler", + "resolveJsonModule": true, + "isolatedModules": true, + "noEmit": true, + "jsx": "preserve", + "paths": { + "@ilokesto/form": ["../../src/index.ts"], + "@ilokesto/form/vue": ["../../src/vue/index.ts"] + } + }, + "include": ["src", "vite.config.ts"] +} \ No newline at end of file diff --git a/examples/vue-login-form/vite.config.ts b/examples/vue-login-form/vite.config.ts new file mode 100644 index 0000000..f3d3773 --- /dev/null +++ b/examples/vue-login-form/vite.config.ts @@ -0,0 +1,13 @@ +import { resolve } from 'node:path'; +import vue from '@vitejs/plugin-vue'; +import { defineConfig } from 'vite'; + +export default defineConfig({ + plugins: [vue()], + resolve: { + alias: { + '@ilokesto/form/vue': resolve(__dirname, '../../src/vue/index.ts'), + '@ilokesto/form': resolve(__dirname, '../../src/index.ts'), + }, + }, +}); \ No newline at end of file diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index fdeecad..5dfe8ac 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -92,6 +92,90 @@ importers: specifier: ^1.0.0 version: 1.0.0 + examples/react-validation-flow: + dependencies: + '@ilokesto/form': + specifier: workspace:* + version: link:../.. + react: + specifier: ^19.0.0 + version: 19.2.6 + react-dom: + specifier: ^19.2.6 + version: 19.2.6(react@19.2.6) + typescript: + specifier: ^6.0.2 + version: 6.0.2 + vite: + specifier: ^8.1.0 + version: 8.1.0(@types/node@22.19.15)(esbuild@0.27.7) + devDependencies: + '@babel/core': + specifier: ^8.0.1 + version: 8.0.1 + '@rolldown/plugin-babel': + specifier: ^0.2.3 + version: 0.2.3(@babel/core@8.0.1)(@babel/runtime@7.29.2)(rolldown@1.1.3)(vite@8.1.0(@types/node@22.19.15)(esbuild@0.27.7)) + '@types/babel__core': + specifier: ^7.20.5 + version: 7.20.5 + '@types/react': + specifier: ^19.2.15 + version: 19.2.15 + '@types/react-dom': + specifier: ^19.2.3 + version: 19.2.3(@types/react@19.2.15) + '@vitejs/plugin-react': + specifier: ^6.0.3 + version: 6.0.3(@rolldown/plugin-babel@0.2.3(@babel/core@8.0.1)(@babel/runtime@7.29.2)(rolldown@1.1.3)(vite@8.1.0(@types/node@22.19.15)(esbuild@0.27.7)))(babel-plugin-react-compiler@1.0.0)(vite@8.1.0(@types/node@22.19.15)(esbuild@0.27.7)) + babel-plugin-react-compiler: + specifier: ^1.0.0 + version: 1.0.0 + + examples/solid-login-form: + dependencies: + '@ilokesto/form': + specifier: workspace:* + version: link:../.. + solid-js: + specifier: ^1.9.13 + version: 1.9.13 + devDependencies: + typescript: + specifier: ^6.0.2 + version: 6.0.2 + vite: + specifier: ^8.1.0 + version: 8.1.0(@types/node@22.19.15)(esbuild@0.27.7) + vite-plugin-solid: + specifier: ^2.11.0 + version: 2.11.13(solid-js@1.9.13)(vite@8.1.0(@types/node@22.19.15)(esbuild@0.27.7)) + + examples/svelte-login-form: + dependencies: + '@ilokesto/form': + specifier: workspace:* + version: link:../.. + svelte: + specifier: ^5.55.9 + version: 5.55.9 + devDependencies: + '@sveltejs/vite-plugin-svelte': + specifier: ^6.1.0 + version: 6.2.4(svelte@5.55.9)(vite@8.1.0(@types/node@22.19.15)(esbuild@0.27.7)) + '@tsconfig/svelte': + specifier: ^5.0.4 + version: 5.0.8 + svelte-check: + specifier: ^4.2.2 + version: 4.7.3(picomatch@4.0.4)(svelte@5.55.9)(typescript@6.0.2) + typescript: + specifier: ^6.0.2 + version: 6.0.2 + vite: + specifier: ^8.1.0 + version: 8.1.0(@types/node@22.19.15)(esbuild@0.27.7) + examples/vue-login-form: dependencies: '@ilokesto/form': @@ -128,38 +212,80 @@ packages: '@asamuzakjp/nwsapi@2.3.9': resolution: {integrity: sha512-n8GuYSrI9bF7FFZ/SjhwevlHc8xaVlb/7HmHelnc/PZXBD2ZR49NnN9sMMuDdEGPeeRQ5d0hqlSlEpgCX3Wl0Q==} - '@babel/code-frame@7.29.0': - resolution: {integrity: sha512-9NhCeYjq9+3uxgdtp20LSiJXJvN0FeCtNGpJxuMFZ1Kv3cWUNb6DOhJwUvcVCzKGR66cw4njwM6hrJLqgOwbcw==} + '@babel/code-frame@7.29.7': + resolution: {integrity: sha512-Aup7aUOfpbAUg2ROOJN6Iw5f9DMBlzu0mIkm/malLQFN/YQgO48wCj0Kxa3sEHJvPVFg7siR+qRInwXd2qhQKw==} engines: {node: '>=6.9.0'} '@babel/code-frame@8.0.0': resolution: {integrity: sha512-dYYg153EyN2Ekbqw2zAsbd6/JR+9N2SEoC7YV2GyyqMM7x9bLDTjBD6XBhSMLH0wtIVyJj03jWNriQhaN+eoCw==} engines: {node: ^22.18.0 || >=24.11.0} + '@babel/compat-data@7.29.7': + resolution: {integrity: sha512-locTkQyKvwIEgBzVrn8693ebc97F2U8ZHjbXwDXJ5Fn2TCpNwTlKcaKLkdHop5c/icOFE7qt7Q9JC5hnKNa6Gg==} + engines: {node: '>=6.9.0'} + '@babel/compat-data@8.0.0': resolution: {integrity: sha512-DOjnob/cXOUgDOozCDeq/aK2p5y8dUIVdf6tNhEV1HQRd6I8aQ4f4fbtHRVEvb6lP3BGomrKHiS8ICAASSVQSw==} engines: {node: ^22.18.0 || >=24.11.0} + '@babel/core@7.29.7': + resolution: {integrity: sha512-RgHBCvtjbOK2gXSNBNIkNoEc9qoVEtau3hj8gEqKQuL3HZAibKarWFEI3Lfm6EYKkLalOh8eSrj9b+ch9H/VBA==} + engines: {node: '>=6.9.0'} + '@babel/core@8.0.1': resolution: {integrity: sha512-5FgxM4dLQpMJHSiVATk8foW263dVHQHBVpXYiimNECVWG01f4nFyEbQixeT6Mwvg7TayREJ2gpKl3o2RoMdnqw==} engines: {node: ^22.18.0 || >=24.11.0} + '@babel/generator@7.29.7': + resolution: {integrity: sha512-DkXD5OJQaAQIdZ1bt3UZdEnHAn9Imd3IVBdX03UFe+ony9Ojw5pzr9YVKGDY1jt+Gcn/FnGkNf8r+Vj5NOJWtQ==} + 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'} + '@babel/helper-compilation-targets@8.0.0': resolution: {integrity: sha512-JwculLABZvyPvyLBpwU/E/IbH2uM3mnxNtIJpxnIfb24y1PrdVxK5Dqjle4DpgqpGRnwgC7G8IkzPdSXZrO1Ew==} engines: {node: ^22.18.0 || >=24.11.0} + '@babel/helper-globals@7.29.7': + resolution: {integrity: sha512-3nQVUAtvkKH9zahfWgw96Jc/uFOmjACE1kQz82E2lqWmHBgjzbNlsC22nuQTfahmWeQtTq5nQ/4Nnd2A1wj4zA==} + engines: {node: '>=6.9.0'} + '@babel/helper-globals@8.0.0': resolution: {integrity: sha512-lLozHOM6sWWlxNo8CYqHy4MBZeTvHXNgVPBfPOGsjPKUzHC2Az9QwB6gxdQmpwHl6GlQtbGgS+lj5887guDiLw==} engines: {node: ^22.18.0 || >=24.11.0} + '@babel/helper-module-imports@7.18.6': + resolution: {integrity: sha512-0NFvs3VkuSYbFi1x2Vd6tKrywq+z/cLeYC/RJNFrIX/30Bf5aiGYbtvGXolEktzJH8o5E5KJ3tT+nkxuuZFVlA==} + engines: {node: '>=6.9.0'} + + '@babel/helper-module-imports@7.29.7': + resolution: {integrity: sha512-ejHwrQQYcm9xnTivShn2IDOlIzInN34AXskvq9QicvCtEzq1Vzclu/tKF8Jq1Cg8JG2GL6/EmjgsCT7lXepE3g==} + engines: {node: '>=6.9.0'} + + '@babel/helper-module-transforms@7.29.7': + resolution: {integrity: sha512-UPUVSyXbOh627KiCIGQSgwWzGeBKLkaJ9PJEdrngIwMSzxLR4jS4+f1f1jb7VzBbg8nFLaYotvVPFCTqdrmTAg==} + engines: {node: '>=6.9.0'} + peerDependencies: + '@babel/core': ^7.0.0 + + '@babel/helper-plugin-utils@7.29.7': + resolution: {integrity: sha512-G7sHYigPY17oO5SYWnfD/0MTBwVR781S/JI643e/JhUYgVgWE/61SoW3NH9KWUKyKq5LVh3npif99Wkt6j86Jw==} + engines: {node: '>=6.9.0'} + '@babel/helper-string-parser@7.27.1': resolution: {integrity: sha512-qMlSxKbpRlAridDExk92nSobyDdpPijUq2DW6oDnUqd0iOGxmQjyqhMIihI9+zv4LPyZdRje2cavWPbCbWm3eA==} engines: {node: '>=6.9.0'} + '@babel/helper-string-parser@7.29.7': + 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} @@ -168,14 +294,26 @@ packages: resolution: {integrity: sha512-qSs4ifwzKJSV39ucNjsvc6WVHs6b7S03sOh2OcHF9UHfVPqWWALUsNUVzhSBiItjRZoLHx7nIarVjqKVusUZ1Q==} engines: {node: '>=6.9.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'} + '@babel/helper-validator-option@8.0.0': resolution: {integrity: sha512-U4Dybxh4WESWHt5XhBeExi4DrY0/DNK1aHpQbsrQXCUbFHuMweT0TpLEWKvaraV2Y6fS+ZXunsZ8zIuZIgvF2Q==} engines: {node: ^22.18.0 || >=24.11.0} + '@babel/helpers@7.29.7': + resolution: {integrity: sha512-1k2lAGRMfHTcwuNYcCNUmaUffmQv8KWMfh2iJUUeRlwlwH4FdNG7mfPI10NPfLHJFThE4Tyr4mv7kTNZOiPuBg==} + engines: {node: '>=6.9.0'} + '@babel/helpers@8.0.0': resolution: {integrity: sha512-wfbi91pM3py96oIiJEz7qIpyXDytgr9zQC1HEWwlGNVRAEmItuU/0a41ZUKu1sJGyhhOIpc4t5vk4PYzt8wpsg==} engines: {node: ^22.18.0 || >=24.11.0} @@ -185,19 +323,38 @@ packages: engines: {node: '>=6.0.0'} hasBin: true + '@babel/parser@7.29.7': + resolution: {integrity: sha512-hnORnjP/1P/zFEndoeX+n+t1RwWRJiJpM/jO7FW32Kn9r5+sJB2JWOdYo4L6k78j15eCwY3Gm/7364B1EMwtNg==} + 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/plugin-syntax-jsx@7.29.7': + resolution: {integrity: sha512-TSu8+mHCoEaaCDEZ0I3+6mvTBYR4PCxQwf2z9/r5Tbztv6NaLR3B9thGTTxX2WGuGHJqRiAbKPeGTJ5XWXVg6A==} + engines: {node: '>=6.9.0'} + peerDependencies: + '@babel/core': ^7.0.0-0 + '@babel/runtime@7.29.2': resolution: {integrity: sha512-JiDShH45zKHWyGe4ZNVRrCjBz8Nh9TMmZG1kh4QTK8hCBTWBi8Da+i7s1fJw7/lYpM4ccepSNfqzZ/QvABBi5g==} engines: {node: '>=6.9.0'} + '@babel/template@7.29.7': + resolution: {integrity: sha512-puq+Gf35oI24FeN11LkoUQFqv9uwNeWpxXZi/Ji3rRIoKAzKnxRaZ+Gkj0vKS9ZCiTESfng1N9LyOyXvo+m+Gg==} + engines: {node: '>=6.9.0'} + '@babel/template@8.0.0': resolution: {integrity: sha512-eAD0QW/AlbamBbw0FeGiwasbCVPq5ncW0HNVyLP3B9czqLyh4gvw+5JTSNt6le9+ziAU7mqDZsKTHf3jTb4chQ==} engines: {node: ^22.18.0 || >=24.11.0} + '@babel/traverse@7.29.7': + resolution: {integrity: sha512-EhlfNQtZ+NK22w5BM61ciuiq1m58ed33Wr1Xan//ZRTy6hgjnwyCffRYwzsGXdASJSUJ1guZILsErh1eQcl+zw==} + engines: {node: '>=6.9.0'} + '@babel/traverse@8.0.0': resolution: {integrity: sha512-bxTj/W2VclGE6CctlfQOpxg8MPDzXArRqkOBePw8EHfebcjF7fETWSS3BriEECo+UiU/Yblq+xUtSImFu7cTbw==} engines: {node: ^22.18.0 || >=24.11.0} @@ -206,6 +363,10 @@ packages: resolution: {integrity: sha512-LwdZHpScM4Qz8Xw2iKSzS+cfglZzJGvofQICy7W7v4caru4EaAmyUuO6BGrbyQ2mYV11W0U8j5mBhd14dd3B0A==} engines: {node: '>=6.9.0'} + '@babel/types@7.29.7': + resolution: {integrity: sha512-4zBIxpPzowiZpusoFkyGVwakdRJUyuH5PxQ/PrqghfdFWWasvnCdPfQXHrenDai+gyLARulZjZowCOj6fjT4pA==} + engines: {node: '>=6.9.0'} + '@babel/types@8.0.0': resolution: {integrity: sha512-K8ponJDxBwDHigkeFqaqT5wLGl4bTlwMafR8k7b5CPxr6Ww+UG9ls8Yx6Tcpboxu97eeGVEEyKcHmEyOwN1vSw==} engines: {node: ^22.18.0 || >=24.11.0} @@ -825,6 +986,25 @@ packages: peerDependencies: acorn: ^8.9.0 + '@sveltejs/load-config@0.2.0': + resolution: {integrity: sha512-1LgZ/qUqSoq+QorD83lk2hka79Px0wXNW2q5V1nZlxGhQgw1jrsIbVz5YiCeucVLo4XvFLjXukUaQjIiqowkcg==} + engines: {node: '>= 18.0.0'} + + '@sveltejs/vite-plugin-svelte-inspector@5.0.2': + resolution: {integrity: sha512-TZzRTcEtZffICSAoZGkPSl6Etsj2torOVrx6Uw0KpXxrec9Gg6jFWQ60Q3+LmNGfZSxHRCZL7vXVZIWmuV50Ig==} + engines: {node: ^20.19 || ^22.12 || >=24} + peerDependencies: + '@sveltejs/vite-plugin-svelte': ^6.0.0-next.0 + svelte: ^5.0.0 + vite: ^6.3.0 || ^7.0.0 + + '@sveltejs/vite-plugin-svelte@6.2.4': + resolution: {integrity: sha512-ou/d51QSdTyN26D7h6dSpusAKaZkAiGM55/AKYi+9AGZw7q85hElbjK3kEyzXHhLSnRISHOYzVge6x0jRZ7DXA==} + engines: {node: ^20.19 || ^22.12 || >=24} + peerDependencies: + svelte: ^5.0.0 + vite: ^6.3.0 || ^7.0.0 + '@testing-library/dom@10.4.1': resolution: {integrity: sha512-o4PXJQidqJl82ckFaXUeoAW+XysPLauYI43Abki5hABd853iMhitooc6znOnczgbTYmEP6U6/y1ZyKAIsvMKGg==} engines: {node: '>=18'} @@ -844,6 +1024,9 @@ packages: '@types/react-dom': optional: true + '@tsconfig/svelte@5.0.8': + resolution: {integrity: sha512-UkNnw1/oFEfecR8ypyHIQuWYdkPvHiwcQ78sh+ymIiYoF+uc5H1UBetbjyqT+vgGJ3qQN6nhucJviX6HesWtKQ==} + '@tybys/wasm-util@0.10.3': resolution: {integrity: sha512-F3fo1MYrRJYL3zER0OUOmkutjr1Vp23m7OsSgp7nq4SP6OqX6C/56XFIPAl5bt3zaBRjmW7SGz3u/6LwFpYcOg==} @@ -1044,9 +1227,23 @@ packages: resolution: {integrity: sha512-qIj0G9wZbMGNLjLmg1PT6v2mE9AH2zlnADJD/2tC6E00hgmhUOfEB6greHPAfLRSufHqROIUTkw6E+M3lH0PTQ==} engines: {node: '>= 0.4'} + babel-plugin-jsx-dom-expressions@0.40.7: + resolution: {integrity: sha512-/O6JWUmjv03OI9lL2ry9bUjpD5S3PclM55RRJEyCdcFZ5W2SEA/59d+l2hNsk3gI6kiWRdRPdOtqZmsQzFN1pQ==} + peerDependencies: + '@babel/core': ^7.20.12 + babel-plugin-react-compiler@1.0.0: resolution: {integrity: sha512-Ixm8tFfoKKIPYdCCKYTsqv+Fd4IJ0DQqMyEimo+pxUOMUR9cVPlwTrFt9Avu+3cb6Zp3mAzl+t1MrG2fxxKsxw==} + babel-preset-solid@1.9.12: + resolution: {integrity: sha512-LLqnuKVDlKpyBlMPcH6qEvs/wmS9a+NczppxJ3ryS/c0O5IiSFOIBQi9GzyiGDSbcJpx4Gr87jyFTos1MyEuWg==} + peerDependencies: + '@babel/core': ^7.0.0 + solid-js: ^1.9.12 + peerDependenciesMeta: + solid-js: + optional: true + balanced-match@1.0.2: resolution: {integrity: sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw==} @@ -1084,6 +1281,10 @@ packages: chardet@2.2.0: resolution: {integrity: sha512-rddelWYNPRrXq6PtNEN2S3f6t9ILzvqaN5pVgi4kqt9jHQaXIial9PznB5iSPVlQSLNaaH22ItWz3EJtQ10+OA==} + chokidar@4.0.3: + resolution: {integrity: sha512-Qgzu8kfBvo+cA4962jnP1KkS6Dop5NS6g7R5LFYJr4b8Ub94PPQXUksCw9PvXoeXPRRddRNC5C1JQUR2SMGtnA==} + engines: {node: '>= 14.16.0'} + clsx@2.1.1: resolution: {integrity: sha512-eYm0QWBtUrBWZWG0d386OGAw16Z995PiOVo2B7bjWSbHedGl5e0ZWaq65kOGgUSNesEIDkB9ISbTg/JK9dhCZA==} engines: {node: '>=6'} @@ -1125,6 +1326,10 @@ packages: decimal.js@10.6.0: resolution: {integrity: sha512-YpgQiITW3JXGntzdUmyUR1V812Hn8T1YVXhCu+wO3OpS4eU9l4YdD3qjyiKdV6mvV29zapkMeD390UVEf2lkUg==} + deepmerge@4.3.1: + resolution: {integrity: sha512-3sUqbMEc77XqpdNO7FRyRog+eW3ph+GYCbj+rK+uYyRMuwsVy0rMiVtPn+QJlKFvWP/1PYpapqYn0Me2knFn+A==} + engines: {node: '>=0.10.0'} + dequal@2.0.3: resolution: {integrity: sha512-0je+qPKHEMohvfRTCEo3CrPG6cAzAYgmzKyxRiYSSDkS6eGJdyVJm7WaYA5ECaAD9wLB2T4EEeymA5aFVcYXCA==} engines: {node: '>=6'} @@ -1158,6 +1363,10 @@ packages: resolution: {integrity: sha512-rRqJg/6gd538VHvR3PSrdRBb/1Vy2YfzHqzvbhGIQpDRKIa4FgV/54b5Q1xYSxOOwKvjXweS26E0Q+nAMwp2pQ==} engines: {node: '>=8.6'} + entities@6.0.1: + resolution: {integrity: sha512-aN97NXWF6AWBTahfVOIrB/NShkzi5H7F9r1s9mD3cDj4Ko5f2qhhVoYMibXF7GlLveb/D2ioWay8lxI97Ven3g==} + engines: {node: '>=0.12'} + entities@7.0.1: resolution: {integrity: sha512-TWrgLOFUQTH994YUyl1yT4uyavY5nNB5muff+RtWaqNVCAK408b5ZnnbNAUEWLTCpum9w6arT70i1XdQ4UeOPA==} engines: {node: '>=0.12'} @@ -1267,6 +1476,9 @@ packages: resolution: {integrity: sha512-CV9TW3Y3f8/wT0BRFc1/KAVQ3TUHiXmaAb6VW9vtiMFf7SLoMd1PdAc4W3KFOFETBJUb90KatHqlsZMWV+R9Gg==} engines: {node: ^20.19.0 || ^22.12.0 || >=24.0.0} + html-entities@2.3.3: + resolution: {integrity: sha512-DV5Ln36z34NNTDgnz0EWGBLZENelNAtkiFA4kyNOG2tDI6Mz1uSWiq1wAKdyjnJwyDiDO7Fa2SO1CTxPXL8VxA==} + http-proxy-agent@7.0.2: resolution: {integrity: sha512-T1gkAiYYDWYx3V5Bmyu7HcfcvL7mUrTWiM6yOfa3PIphViJ/gFPbvidQ+veqSOHci/PxBcDabeUNCzpOODJZig==} engines: {node: '>= 14'} @@ -1315,6 +1527,10 @@ packages: resolution: {integrity: sha512-2AT6j+gXe/1ueqbW6fLZJiIw3F8iXGJtt0yDrZaBhAZEG1raiTxKWU+IPqMCzQAXOUCKdA4UDMgacKH25XG2Cw==} engines: {node: '>=4'} + is-what@4.1.16: + resolution: {integrity: sha512-ZhMwEosbFJkA0YhFnNDgTM4ZxDRsS6HqTo7qsZM08fehyRYIYa0yHu5R6mgo1n/8MgaPBXiPimPD77baVFYg+A==} + engines: {node: '>=12.13'} + is-windows@1.0.2: resolution: {integrity: sha512-eXK1UInq2bPmjyX6e3VHIzMLobc4J94i4AWn+Hpq3OU5KkrRC96OAcR3PRJ/pGu6m8TRnBHP9dkXQVsT/COVIA==} engines: {node: '>=0.10.0'} @@ -1442,6 +1658,9 @@ packages: resolution: {integrity: sha512-5YgH9UJd7wVb9hIouI2adWpgqrrICkt070Dnj8EUY1+B4B2P9eRLPAkAAo6NICA7CEhOIeBHl46u9zSNpNu7zA==} engines: {node: 20 || >=22} + lru-cache@5.1.1: + resolution: {integrity: sha512-KpNARQA3Iwv+jTA0utUVVbrh+Jlrr1Fv0e56GGzAFOXN7dk/FviaDW8LHmK52DlcH4WP2n6gI8vN1aesBFgo9w==} + lz-string@1.5.0: resolution: {integrity: sha512-h5bgJWpxJNswbU7qCrV0tIKQCaS3blPDrqKWx+QxzuzL1zGUzij9XCWLrSLsJPu5t+eWA/ycetzYAO5IOMcWAQ==} hasBin: true @@ -1452,6 +1671,10 @@ packages: mdn-data@2.27.1: resolution: {integrity: sha512-9Yubnt3e8A0OKwxYSXyhLymGW4sCufcLG6VdiDdUGVkPhpqLxlvP5vl1983gQjJl3tqbrM731mjaZaP68AgosQ==} + merge-anything@5.1.7: + resolution: {integrity: sha512-eRtbOb1N5iyH0tkQDAoQ4Ipsp/5qSR79Dzrz8hEPxRX10RWWR/iQXdoKmBSRCThY1Fh5EhISDtpSc93fpxUniQ==} + engines: {node: '>=12.13'} + merge2@1.4.1: resolution: {integrity: sha512-8q7VEgMJW4J8tcfVPy8g09NcQwZdbwFEqhe/WZkoIzjn/3TGDwtOCYtXGxA3O8tPzpczCCDgv+P2P5y00ZJOOg==} engines: {node: '>= 8'} @@ -1512,6 +1735,9 @@ packages: package-manager-detector@0.2.11: resolution: {integrity: sha512-BEnLolu+yuz22S56CU1SUKq3XC3PkwD5wv4ikR4MfGvnRVcmzXR9DwSlW2fEamyTPyXHomBJRzgapeuBvRNzJQ==} + parse5@7.3.0: + resolution: {integrity: sha512-IInvU7fabl34qmi9gY8XOVxhYyMyuH2xUNpb2q8/Y+7552KlejkRvqvD19nMoUW/uQGGbqNpA6Tufu5FL5BZgw==} + parse5@8.0.1: resolution: {integrity: sha512-z1e/HMG90obSGeidlli3hj7cbocou0/wa5HacvI3ASx34PecNjNQeaHNo5WIZpWofN9kgkqV1q5YvXe3F0FoPw==} @@ -1587,6 +1813,10 @@ packages: resolution: {integrity: sha512-VIMnQi/Z4HT2Fxuwg5KrY174U1VdUIASQVWXXyqtNRtxSr9IYkn1rsI6Tb6HsrHCmB7gVpNwX6JxPTHcH6IoTA==} engines: {node: '>=6'} + readdirp@4.1.2: + resolution: {integrity: sha512-GDhwkLfywWL2s6vEjyhri+eXmfH6j1L7JE27WhqLeYzoh/A3DBaYGEj2H/HFZCn/kMfim73FXxEJTw06WtxQwg==} + engines: {node: '>= 14.18.0'} + require-from-string@2.0.2: resolution: {integrity: sha512-Xf0nWe6RseziFMu+Ap9biiUbmplq6S9/p+7w7YXP/JBHhrUDDUhwa+vANyubuqfZWTveU//DYVGsDG7RKL/vEw==} engines: {node: '>=0.10.0'} @@ -1612,6 +1842,10 @@ packages: run-parallel@1.2.0: resolution: {integrity: sha512-5l4VyZR86LZ/lDxZTR6jqL8AFE2S0IFLMP26AbjsLVADxHdhB/c0GUsH+y39UfCi3dzz8OlQuPmnaJOMoDHQBA==} + sade@1.8.1: + resolution: {integrity: sha512-xal3CZX1Xlo/k4ApwCFrHVACi9fBqJ7V+mwhBsuf/1IOKbBy098Fex+Wa/5QMubw09pSZ/u8EY8PWgevJsXp1A==} + engines: {node: '>=6'} + safer-buffer@2.1.2: resolution: {integrity: sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==} @@ -1622,6 +1856,10 @@ packages: scheduler@0.27.0: resolution: {integrity: sha512-eNv+WrVbKu1f3vbYJT/xtiF5syA5HPIMtf9IgY/nKg0sWqzAUEvqY/xm7OcZc/qafLx/iO9FgOmeSAp4v5ti/Q==} + semver@6.3.1: + resolution: {integrity: sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA==} + hasBin: true + semver@7.8.5: resolution: {integrity: sha512-Y7/KDsb8LjooZpwaqGyulO6DQlksgCncchHGk+sZIY4SBvUocMBEFH5Ur1fI4dV+Jvl0w6cjvucaIi40puRioA==} engines: {node: '>=10'} @@ -1659,6 +1897,11 @@ packages: solid-js@1.9.13: resolution: {integrity: sha512-6hJeJMOcEX8ktqjpDoJZEmld3ijvcvWBDtiXBm7f4332SiFN66QeAQI1REQshvyUoISsSeJ4PHDauKYbwao9JQ==} + solid-refresh@0.6.3: + resolution: {integrity: sha512-F3aPsX6hVw9ttm5LYlth8Q15x6MlI/J3Dn+o3EQyRTtTxidepSTwAYdozt01/YA+7ObcciagGEyXIopGZzQtbA==} + peerDependencies: + solid-js: ^1.3 + source-map-js@1.2.1: resolution: {integrity: sha512-UXWMKhLOwVKb728IUtQPXxfYU+usdybtUrK/8uGE8CQMvrhOpwvzDBwj0QhSL7MQc7vIsISBG8VQ8+IDQxpfQA==} engines: {node: '>=0.10.0'} @@ -1683,6 +1926,14 @@ packages: resolution: {integrity: sha512-vavAMRXOgBVNF6nyEEmL3DBK19iRpDcoIwW+swQ+CbGiu7lju6t+JklA1MHweoWtadgt4ISVUsXLyDq34ddcwA==} engines: {node: '>=4'} + svelte-check@4.7.3: + resolution: {integrity: sha512-DHdTCGX62R0fCxBEaT+USdASAnoaRBaaNczkRJl0K7o3WyoCeVUbVxo6fKqpOll/B+WMWCsiFK0eFrJSNBKZIg==} + engines: {node: '>= 18.0.0'} + hasBin: true + peerDependencies: + svelte: ^4.0.0 || ^5.0.0-next.0 + typescript: '>=5.0.0' + svelte@5.55.9: resolution: {integrity: sha512-fTjjT8cHLDwigcu2j3pv7Jq04LklXevPB8uBgyHNiTXv+RMNvVnrjS4UEYrLMkhuq1vpCodHjiW+z/95SDs/fg==} engines: {node: '>=18'} @@ -1753,6 +2004,16 @@ packages: peerDependencies: browserslist: '>= 4.21.0' + vite-plugin-solid@2.11.13: + resolution: {integrity: sha512-YaCNMzwIawUO8K16uj5jaxUJIYCstBEjkUppC5OKElBz/K2+R7Q7MWycHDgqzjBca5WWy/2ZQQ45IHexaabYew==} + peerDependencies: + '@testing-library/jest-dom': ^5.16.6 || ^5.17.0 || ^6.* + solid-js: ^1.7.2 + vite: ^3.0.0 || ^4.0.0 || ^5.0.0 || ^6.0.0 || ^7.0.0 || ^8.0.0 || ^9.0.0 + peerDependenciesMeta: + '@testing-library/jest-dom': + optional: true + vite@7.3.3: resolution: {integrity: sha512-/4XH147Ui7OGTjg3HbdWe5arnZQSbfuRzdr9Ec7TQi5I7R+ir0Rlc9GIvD4v0XZurELqA035KVXJXpR61xhiTA==} engines: {node: ^20.19.0 || >=22.12.0} @@ -1836,6 +2097,14 @@ packages: yaml: optional: true + vitefu@1.1.3: + resolution: {integrity: sha512-ub4okH7Z5KLjb6hDyjqrGXqWtWvoYdU3IGm/NorpgHncKoLTCfRIbvlhBm7r0YstIaQRYlp4yEbFqDcKSzXSSg==} + peerDependencies: + vite: ^3.0.0 || ^4.0.0 || ^5.0.0 || ^6.0.0 || ^7.0.0 || ^8.0.0 + peerDependenciesMeta: + vite: + optional: true + vitest@4.1.7: resolution: {integrity: sha512-flYyaFd2CgoCoU+0UKt3pxksgC+S02iTDN0n3LtqaMeXsI9SBcdNujc2k0DeFLzUn/0k538yNjOSdwgCqcrwJA==} engines: {node: ^20.0.0 || ^22.0.0 || >=24.0.0} @@ -1943,6 +2212,9 @@ packages: xmlchars@2.2.0: resolution: {integrity: sha512-JZnDKK8B0RCDw84FNdDAIpZK+JuJw+s7Lz8nksI7SIuU3UXJJslUthsi+uWBUYOwPFwW7W7PRLRfUKpxjtjFCw==} + yallist@3.1.1: + resolution: {integrity: sha512-a4UGQaWPH59mOXUYnAG2ewncQS4i4F43Tv3JoAM+s2VDAmS9NsK8GpDMLrCHPksFT7h3K6TOoUNn2pb7RoXx4g==} + zimmerframe@1.1.4: resolution: {integrity: sha512-B58NGBEoc8Y9MWWCQGl/gq9xBCe4IiKM0a2x7GZdQKOW5Exr8S1W24J6OgM1njK8xCRGvAJIL/MxXHf6SkmQKQ==} @@ -1968,9 +2240,9 @@ snapshots: '@asamuzakjp/nwsapi@2.3.9': {} - '@babel/code-frame@7.29.0': + '@babel/code-frame@7.29.7': dependencies: - '@babel/helper-validator-identifier': 7.28.5 + '@babel/helper-validator-identifier': 7.29.7 js-tokens: 4.0.0 picocolors: 1.1.1 @@ -1979,8 +2251,30 @@ snapshots: '@babel/helper-validator-identifier': 8.0.2 js-tokens: 10.0.0 + '@babel/compat-data@7.29.7': {} + '@babel/compat-data@8.0.0': {} + '@babel/core@7.29.7': + dependencies: + '@babel/code-frame': 7.29.7 + '@babel/generator': 7.29.7 + '@babel/helper-compilation-targets': 7.29.7 + '@babel/helper-module-transforms': 7.29.7(@babel/core@7.29.7) + '@babel/helpers': 7.29.7 + '@babel/parser': 7.29.7 + '@babel/template': 7.29.7 + '@babel/traverse': 7.29.7 + '@babel/types': 7.29.7 + '@jridgewell/remapping': 2.3.5 + convert-source-map: 2.0.0 + debug: 4.4.3 + gensync: 1.0.0-beta.2 + json5: 2.2.3 + semver: 6.3.1 + transitivePeerDependencies: + - supports-color + '@babel/core@8.0.1': dependencies: '@babel/code-frame': 8.0.0 @@ -2000,6 +2294,14 @@ snapshots: obug: 2.1.1 semver: 7.8.5 + '@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': dependencies: '@babel/parser': 8.0.0 @@ -2009,6 +2311,14 @@ snapshots: '@types/jsesc': 2.5.1 jsesc: 3.1.0 + '@babel/helper-compilation-targets@7.29.7': + dependencies: + '@babel/compat-data': 7.29.7 + '@babel/helper-validator-option': 7.29.7 + browserslist: 4.28.4 + lru-cache: 5.1.1 + semver: 6.3.1 + '@babel/helper-compilation-targets@8.0.0': dependencies: '@babel/compat-data': 8.0.0 @@ -2017,18 +2327,53 @@ snapshots: lru-cache: 11.5.0 semver: 7.8.5 + '@babel/helper-globals@7.29.7': {} + '@babel/helper-globals@8.0.0': {} + '@babel/helper-module-imports@7.18.6': + dependencies: + '@babel/types': 7.29.0 + + '@babel/helper-module-imports@7.29.7': + dependencies: + '@babel/traverse': 7.29.7 + '@babel/types': 7.29.7 + transitivePeerDependencies: + - supports-color + + '@babel/helper-module-transforms@7.29.7(@babel/core@7.29.7)': + dependencies: + '@babel/core': 7.29.7 + '@babel/helper-module-imports': 7.29.7 + '@babel/helper-validator-identifier': 7.29.7 + '@babel/traverse': 7.29.7 + transitivePeerDependencies: + - supports-color + + '@babel/helper-plugin-utils@7.29.7': {} + '@babel/helper-string-parser@7.27.1': {} + '@babel/helper-string-parser@7.29.7': {} + '@babel/helper-string-parser@8.0.0': {} '@babel/helper-validator-identifier@7.28.5': {} + '@babel/helper-validator-identifier@7.29.7': {} + '@babel/helper-validator-identifier@8.0.2': {} + '@babel/helper-validator-option@7.29.7': {} + '@babel/helper-validator-option@8.0.0': {} + '@babel/helpers@7.29.7': + dependencies: + '@babel/template': 7.29.7 + '@babel/types': 7.29.7 + '@babel/helpers@8.0.0': dependencies: '@babel/template': 8.0.0 @@ -2038,18 +2383,45 @@ snapshots: dependencies: '@babel/types': 7.29.0 + '@babel/parser@7.29.7': + dependencies: + '@babel/types': 7.29.7 + '@babel/parser@8.0.0': dependencies: '@babel/types': 8.0.0 + '@babel/plugin-syntax-jsx@7.29.7(@babel/core@7.29.7)': + dependencies: + '@babel/core': 7.29.7 + '@babel/helper-plugin-utils': 7.29.7 + '@babel/runtime@7.29.2': {} + '@babel/template@7.29.7': + dependencies: + '@babel/code-frame': 7.29.7 + '@babel/parser': 7.29.7 + '@babel/types': 7.29.7 + '@babel/template@8.0.0': dependencies: '@babel/code-frame': 8.0.0 '@babel/parser': 8.0.0 '@babel/types': 8.0.0 + '@babel/traverse@7.29.7': + dependencies: + '@babel/code-frame': 7.29.7 + '@babel/generator': 7.29.7 + '@babel/helper-globals': 7.29.7 + '@babel/parser': 7.29.7 + '@babel/template': 7.29.7 + '@babel/types': 7.29.7 + debug: 4.4.3 + transitivePeerDependencies: + - supports-color + '@babel/traverse@8.0.0': dependencies: '@babel/code-frame': 8.0.0 @@ -2065,6 +2437,11 @@ snapshots: '@babel/helper-string-parser': 7.27.1 '@babel/helper-validator-identifier': 7.28.5 + '@babel/types@7.29.7': + 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 @@ -2574,9 +2951,28 @@ snapshots: dependencies: acorn: 8.16.0 + '@sveltejs/load-config@0.2.0': {} + + '@sveltejs/vite-plugin-svelte-inspector@5.0.2(@sveltejs/vite-plugin-svelte@6.2.4(svelte@5.55.9)(vite@8.1.0(@types/node@22.19.15)(esbuild@0.27.7)))(svelte@5.55.9)(vite@8.1.0(@types/node@22.19.15)(esbuild@0.27.7))': + dependencies: + '@sveltejs/vite-plugin-svelte': 6.2.4(svelte@5.55.9)(vite@8.1.0(@types/node@22.19.15)(esbuild@0.27.7)) + obug: 2.1.1 + svelte: 5.55.9 + vite: 8.1.0(@types/node@22.19.15)(esbuild@0.27.7) + + '@sveltejs/vite-plugin-svelte@6.2.4(svelte@5.55.9)(vite@8.1.0(@types/node@22.19.15)(esbuild@0.27.7))': + dependencies: + '@sveltejs/vite-plugin-svelte-inspector': 5.0.2(@sveltejs/vite-plugin-svelte@6.2.4(svelte@5.55.9)(vite@8.1.0(@types/node@22.19.15)(esbuild@0.27.7)))(svelte@5.55.9)(vite@8.1.0(@types/node@22.19.15)(esbuild@0.27.7)) + deepmerge: 4.3.1 + magic-string: 0.30.21 + obug: 2.1.1 + svelte: 5.55.9 + vite: 8.1.0(@types/node@22.19.15)(esbuild@0.27.7) + vitefu: 1.1.3(vite@8.1.0(@types/node@22.19.15)(esbuild@0.27.7)) + '@testing-library/dom@10.4.1': dependencies: - '@babel/code-frame': 7.29.0 + '@babel/code-frame': 7.29.7 '@babel/runtime': 7.29.2 '@types/aria-query': 5.0.4 aria-query: 5.3.0 @@ -2595,6 +2991,8 @@ snapshots: '@types/react': 19.2.15 '@types/react-dom': 19.2.3(@types/react@19.2.15) + '@tsconfig/svelte@5.0.8': {} + '@tybys/wasm-util@0.10.3': dependencies: tslib: 2.8.1 @@ -2823,10 +3221,26 @@ snapshots: axobject-query@4.1.0: {} + babel-plugin-jsx-dom-expressions@0.40.7(@babel/core@7.29.7): + dependencies: + '@babel/core': 7.29.7 + '@babel/helper-module-imports': 7.18.6 + '@babel/plugin-syntax-jsx': 7.29.7(@babel/core@7.29.7) + '@babel/types': 7.29.0 + html-entities: 2.3.3 + parse5: 7.3.0 + babel-plugin-react-compiler@1.0.0: dependencies: '@babel/types': 7.29.0 + babel-preset-solid@1.9.12(@babel/core@7.29.7)(solid-js@1.9.13): + dependencies: + '@babel/core': 7.29.7 + babel-plugin-jsx-dom-expressions: 0.40.7(@babel/core@7.29.7) + optionalDependencies: + solid-js: 1.9.13 + balanced-match@1.0.2: {} baseline-browser-mapping@2.10.38: {} @@ -2861,6 +3275,10 @@ snapshots: chardet@2.2.0: {} + chokidar@4.0.3: + dependencies: + readdirp: 4.1.2 + clsx@2.1.1: {} convert-source-map@2.0.0: {} @@ -2898,6 +3316,8 @@ snapshots: decimal.js@10.6.0: {} + deepmerge@4.3.1: {} + dequal@2.0.3: {} detect-indent@6.1.0: {} @@ -2921,6 +3341,8 @@ snapshots: ansi-colors: 4.1.3 strip-ansi: 6.0.1 + entities@6.0.1: {} + entities@7.0.1: {} entities@8.0.0: {} @@ -3041,6 +3463,8 @@ snapshots: transitivePeerDependencies: - '@noble/hashes' + html-entities@2.3.3: {} + http-proxy-agent@7.0.2: dependencies: agent-base: 7.1.4 @@ -3085,6 +3509,8 @@ snapshots: dependencies: better-path-resolve: 1.0.0 + is-what@4.1.16: {} + is-windows@1.0.2: {} isexe@2.0.0: {} @@ -3197,6 +3623,10 @@ snapshots: lru-cache@11.5.0: {} + lru-cache@5.1.1: + dependencies: + yallist: 3.1.1 + lz-string@1.5.0: {} magic-string@0.30.21: @@ -3205,6 +3635,10 @@ snapshots: mdn-data@2.27.1: {} + merge-anything@5.1.7: + dependencies: + is-what: 4.1.16 + merge2@1.4.1: {} micromatch@4.0.8: @@ -3250,6 +3684,10 @@ snapshots: dependencies: quansync: 0.2.11 + parse5@7.3.0: + dependencies: + entities: 6.0.1 + parse5@8.0.1: dependencies: entities: 8.0.0 @@ -3308,6 +3746,8 @@ snapshots: pify: 4.0.1 strip-bom: 3.0.0 + readdirp@4.1.2: {} + require-from-string@2.0.2: {} resolve-from@5.0.0: {} @@ -3370,6 +3810,10 @@ snapshots: dependencies: queue-microtask: 1.2.3 + sade@1.8.1: + dependencies: + mri: 1.2.0 + safer-buffer@2.1.2: {} saxes@6.0.0: @@ -3378,6 +3822,8 @@ snapshots: scheduler@0.27.0: {} + semver@6.3.1: {} + semver@7.8.5: {} seroval-plugins@1.5.4(seroval@1.5.4): @@ -3404,6 +3850,15 @@ snapshots: seroval: 1.5.4 seroval-plugins: 1.5.4(seroval@1.5.4) + solid-refresh@0.6.3(solid-js@1.9.13): + dependencies: + '@babel/generator': 7.29.7 + '@babel/helper-module-imports': 7.29.7 + '@babel/types': 7.29.0 + solid-js: 1.9.13 + transitivePeerDependencies: + - supports-color + source-map-js@1.2.1: {} spawndamnit@3.0.1: @@ -3423,6 +3878,19 @@ snapshots: strip-bom@3.0.0: {} + svelte-check@4.7.3(picomatch@4.0.4)(svelte@5.55.9)(typescript@6.0.2): + dependencies: + '@jridgewell/trace-mapping': 0.3.31 + '@sveltejs/load-config': 0.2.0 + chokidar: 4.0.3 + fdir: 6.5.0(picomatch@4.0.4) + picocolors: 1.1.1 + sade: 1.8.1 + svelte: 5.55.9 + typescript: 6.0.2 + transitivePeerDependencies: + - picomatch + svelte@5.55.9: dependencies: '@jridgewell/remapping': 2.3.5 @@ -3497,6 +3965,19 @@ snapshots: escalade: 3.2.0 picocolors: 1.1.1 + vite-plugin-solid@2.11.13(solid-js@1.9.13)(vite@8.1.0(@types/node@22.19.15)(esbuild@0.27.7)): + dependencies: + '@babel/core': 7.29.7 + '@types/babel__core': 7.20.5 + babel-preset-solid: 1.9.12(@babel/core@7.29.7)(solid-js@1.9.13) + merge-anything: 5.1.7 + solid-js: 1.9.13 + solid-refresh: 0.6.3(solid-js@1.9.13) + vite: 8.1.0(@types/node@22.19.15)(esbuild@0.27.7) + vitefu: 1.1.3(vite@8.1.0(@types/node@22.19.15)(esbuild@0.27.7)) + transitivePeerDependencies: + - supports-color + vite@7.3.3(@types/node@22.19.15)(lightningcss@1.32.0): dependencies: esbuild: 0.27.7 @@ -3522,6 +4003,10 @@ snapshots: esbuild: 0.27.7 fsevents: 2.3.3 + vitefu@1.1.3(vite@8.1.0(@types/node@22.19.15)(esbuild@0.27.7)): + optionalDependencies: + vite: 8.1.0(@types/node@22.19.15)(esbuild@0.27.7) + vitest@4.1.7(@types/node@22.19.15)(jsdom@27.4.0)(vite@7.3.3(@types/node@22.19.15)(lightningcss@1.32.0)): dependencies: '@vitest/expect': 4.1.7 @@ -3598,4 +4083,6 @@ snapshots: xmlchars@2.2.0: {} + yallist@3.1.1: {} + zimmerframe@1.1.4: {}