Private photo sharing app my wife and I
0

Configure Feed

Select the types of activity you want to include in your feed.

init

author
Anirudh Oppiliappan
date (Jul 19, 2026, 11:19 AM +0300) commit e1d156a3
+12510
+15
.dev.vars.example
··· 1 + # Copy to .dev.vars for local development. Never commit .dev.vars. 2 + 3 + # Google OAuth web client (for Anita's login) — console.cloud.google.com → Credentials 4 + GOOGLE_OAUTH_CLIENT_ID=xxx.apps.googleusercontent.com 5 + GOOGLE_OAUTH_CLIENT_SECRET=GOCSPX-xxx 6 + 7 + # Google Maps Platform key with Places API (New) + Geocoding API enabled 8 + GOOGLE_MAPS_API_KEY=AIzaxxx 9 + 10 + # Any long random string; gates the one-time passkey enrollment page (/setup) 11 + SETUP_SECRET=pick-a-long-random-string 12 + 13 + # Local-only convenience: enables password login on localhost as either user. 14 + # NEVER set this as a production secret (it's also hostname-gated, but still). 15 + DEV_PASSWORD=dev
+9
.gitignore
··· 1 + node_modules/ 2 + .direnv/ 3 + dist/ 4 + .wrangler/ 5 + .dev.vars 6 + worker-configuration.d.ts 7 + *.tsbuildinfo 8 + .DS_Store 9 + .setup-secret.local
+67
README.md
··· 1 + # aniverse 2 + 3 + A private, Instagram-style photo feed for exactly two people — Anirudh and Anita. Multi-photo posts with captions, locations per photo or per post (Google Places autocomplete, pre-filled from EXIF GPS), comments, emoji reactions (double-tap to ❤️), switchable themes (Pastel / Warm / Brutalist / Noir, in the avatar menu), full-res originals kept forever. 4 + 5 + **Stack:** one Cloudflare Worker serving a React SPA (Vite) + Hono JSON API · D1 (data) · R2 (photo originals + cached variants) · Images binding (resizing) · Google login (Anita) · passkeys (Anirudh) · installable PWA. 6 + 7 + ## Local development 8 + 9 + ```sh 10 + nix develop # node 22 + resvg (or use direnv: `direnv allow`) 11 + npm install 12 + cp .dev.vars.example .dev.vars # defaults work; Google keys optional locally 13 + npm run db:migrate:local 14 + npm run dev 15 + ``` 16 + 17 + Then: 18 + 19 + - **Easiest login:** with `DEV_PASSWORD=dev` in `.dev.vars`, the login page grows a "local dev" box — type the password and enter as either Anirudh or Anita. (Only rendered when the endpoint is enabled, and the endpoint only works on localhost.) 20 + - **Passkey login:** visit `http://localhost:5173/setup?key=dev-setup-secret` once to enroll, after that use "Sign in with passkey" on `/login`. 21 + - **Google login:** needs real OAuth credentials in `.dev.vars` (add `http://localhost:5173/api/auth/google/callback` as an authorized redirect URI on the client). 22 + - **Location autocomplete:** needs `GOOGLE_MAPS_API_KEY` in `.dev.vars`; without it the app works, the pickers just say "search unavailable". 23 + 24 + ## Deploying (one-time checklist) 25 + 26 + 1. **Cloudflare resources** 27 + ```sh 28 + npx wrangler login 29 + npx wrangler d1 create aniverse # paste database_id into wrangler.jsonc 30 + npx wrangler r2 bucket create aniverse-photos 31 + npm run db:migrate:remote 32 + ``` 33 + 2. **Fix the allowlist** — in `wrangler.jsonc`, replace `CHANGE_ME_anita@gmail.com` with Anita's real Google email. 34 + 3. **Google Cloud console** (console.cloud.google.com, one project for both): 35 + - *OAuth consent screen*: External, stay in **Testing** mode, add both of your emails as test users (no verification needed for 2 users). 36 + - *Credentials → OAuth client (Web)*: authorized redirect URI `https://YOUR_DOMAIN/api/auth/google/callback`. Copy client ID + secret. 37 + - *Enable APIs*: **Places API (New)** and **Geocoding API**. Create an **API key** restricted to those two. (Requires a billing account; usage at 2-person scale sits inside the free tier.) 38 + 4. **Secrets** 39 + ```sh 40 + npx wrangler secret put GOOGLE_OAUTH_CLIENT_ID 41 + npx wrangler secret put GOOGLE_OAUTH_CLIENT_SECRET 42 + npx wrangler secret put GOOGLE_MAPS_API_KEY 43 + npx wrangler secret put SETUP_SECRET # any long random string 44 + ``` 45 + 5. **Deploy** 46 + ```sh 47 + npm run deploy 48 + ``` 49 + 6. **Domain first, then passkeys.** Passkeys are cryptographically bound to the hostname — decide the final domain (custom domain or the workers.dev URL) **before** enrolling. Then visit `https://YOUR_DOMAIN/setup?key=<SETUP_SECRET>` on each of Anirudh's devices (Face ID / Touch ID). Anita just taps "Continue with Google". 50 + 7. **Phones:** open the site in Safari → Share → **Add to Home Screen**. It runs standalone like an app (the future native iOS app will reuse this same `/api`). 51 + 52 + ## Costs 53 + 54 + Everything runs on Cloudflare's free tier: R2 has no egress fees, image transformations are cached back into R2 so each photo variant is generated exactly once (well inside the 5,000/month free transformations), and static assets are free. The only external dependency is Google Maps Platform (billing account required, but per-SKU free tiers cover this usage). 55 + 56 + ## Local-first 57 + 58 + - The TanStack Query cache persists to localStorage, so the app paints the last-seen feed instantly on launch and revalidates in the background. 59 + - A service worker (production builds only — `npm run build && npx vite preview` to test) precaches the app shell, caches photos cache-first (they're immutable per URL), and falls back to the cached feed when offline. An "offline — showing saved memories" chip appears when disconnected. 60 + - Deleting a post is optimistic: it vanishes immediately and reappears if the server call fails. 61 + 62 + ## Notes 63 + 64 + - The whole app is private: every `/api/*` and `/img/*` route requires a session; only allowlisted emails can ever create one. 65 + - Originals are stored untouched in R2 under `originals/<photoId>` (grab one at `/img/<photoId>/original`); feed/thumb/full variants are lazily generated webp. 66 + - Post timestamps are unix **milliseconds** in the DB (cursor tie-breaking); the API returns seconds. 67 + - EXIF orientation is handled: display dimensions are stored orientation-corrected, production Cloudflare Images auto-orients pixels, and the sharp-based local simulator (which doesn't) gets an explicit rotation compensation that only activates on localhost.
+61
flake.lock
··· 1 + { 2 + "nodes": { 3 + "flake-utils": { 4 + "inputs": { 5 + "systems": "systems" 6 + }, 7 + "locked": { 8 + "lastModified": 1731533236, 9 + "narHash": "sha256-l0KFg5HjrsfsO/JpG+r7fRrqm12kzFHyUHqHCVpMMbI=", 10 + "owner": "numtide", 11 + "repo": "flake-utils", 12 + "rev": "11707dc2f618dd54ca8739b309ec4fc024de578b", 13 + "type": "github" 14 + }, 15 + "original": { 16 + "owner": "numtide", 17 + "repo": "flake-utils", 18 + "type": "github" 19 + } 20 + }, 21 + "nixpkgs": { 22 + "locked": { 23 + "lastModified": 1784364478, 24 + "narHash": "sha256-CdItYNdYUlm7NxqMVyQKqT2IxTwvapiPuRLWOyHTrbY=", 25 + "owner": "NixOS", 26 + "repo": "nixpkgs", 27 + "rev": "20535e48e12c86043b577b8518234ff5dbb26957", 28 + "type": "github" 29 + }, 30 + "original": { 31 + "owner": "NixOS", 32 + "ref": "nixpkgs-unstable", 33 + "repo": "nixpkgs", 34 + "type": "github" 35 + } 36 + }, 37 + "root": { 38 + "inputs": { 39 + "flake-utils": "flake-utils", 40 + "nixpkgs": "nixpkgs" 41 + } 42 + }, 43 + "systems": { 44 + "locked": { 45 + "lastModified": 1681028828, 46 + "narHash": "sha256-Vy1rq5AaRuLzOxct8nz4T6wlgyUR7zLU309k9mBC768=", 47 + "owner": "nix-systems", 48 + "repo": "default", 49 + "rev": "da67096a3b9bf56a91d16901293e51ba5b49a27e", 50 + "type": "github" 51 + }, 52 + "original": { 53 + "owner": "nix-systems", 54 + "repo": "default", 55 + "type": "github" 56 + } 57 + } 58 + }, 59 + "root": "root", 60 + "version": 7 61 + }
+22
flake.nix
··· 1 + { 2 + description = "aniverse — private photo sharing for two"; 3 + 4 + inputs = { 5 + nixpkgs.url = "github:NixOS/nixpkgs/nixpkgs-unstable"; 6 + flake-utils.url = "github:numtide/flake-utils"; 7 + }; 8 + 9 + outputs = { self, nixpkgs, flake-utils }: 10 + flake-utils.lib.eachDefaultSystem (system: 11 + let 12 + pkgs = nixpkgs.legacyPackages.${system}; 13 + in 14 + { 15 + devShells.default = pkgs.mkShell { 16 + packages = with pkgs; [ 17 + nodejs_22 18 + resvg # icon.svg -> apple-touch-icon.png 19 + ]; 20 + }; 21 + }); 22 + }
+23
index.html
··· 1 + <!doctype html> 2 + <html lang="en"> 3 + <head> 4 + <meta charset="UTF-8" /> 5 + <meta name="viewport" content="width=device-width, initial-scale=1.0, viewport-fit=cover" /> 6 + <title>Aniverse</title> 7 + <link rel="icon" href="/icon.svg" type="image/svg+xml" /> 8 + <link rel="manifest" href="/manifest.webmanifest" /> 9 + <link rel="apple-touch-icon" href="/apple-touch-icon.png" /> 10 + <meta name="apple-mobile-web-app-capable" content="yes" /> 11 + <meta name="apple-mobile-web-app-status-bar-style" content="default" /> 12 + <meta name="theme-color" content="#f7f4f8" media="(prefers-color-scheme: light)" /> 13 + <meta name="theme-color" content="#191621" media="(prefers-color-scheme: dark)" /> 14 + <script> 15 + // Apply the saved theme before first paint to avoid a style flash. 16 + document.documentElement.dataset.style = localStorage.getItem("aniverse-style") || "pastel"; 17 + </script> 18 + </head> 19 + <body> 20 + <div id="root"></div> 21 + <script type="module" src="/src/web/main.tsx"></script> 22 + </body> 23 + </html>
+72
migrations/0001_init.sql
··· 1 + -- Migration number: 0001 init 2 + CREATE TABLE users ( 3 + id TEXT PRIMARY KEY, 4 + email TEXT NOT NULL UNIQUE, 5 + name TEXT NOT NULL, 6 + avatar_url TEXT, 7 + google_sub TEXT UNIQUE, 8 + created_at INTEGER NOT NULL DEFAULT (unixepoch()) 9 + ); 10 + 11 + CREATE TABLE webauthn_credentials ( 12 + id TEXT PRIMARY KEY, -- credential id, base64url 13 + user_id TEXT NOT NULL REFERENCES users(id), 14 + public_key TEXT NOT NULL, -- base64url-encoded COSE public key 15 + counter INTEGER NOT NULL DEFAULT 0, 16 + transports TEXT, -- JSON array 17 + created_at INTEGER NOT NULL DEFAULT (unixepoch()) 18 + ); 19 + 20 + CREATE TABLE webauthn_challenges ( 21 + id TEXT PRIMARY KEY, 22 + challenge TEXT NOT NULL, 23 + kind TEXT NOT NULL CHECK (kind IN ('register', 'auth')), 24 + user_id TEXT, 25 + expires_at INTEGER NOT NULL 26 + ); 27 + 28 + CREATE TABLE sessions ( 29 + token_hash TEXT PRIMARY KEY, -- sha256 hex of the bearer token 30 + user_id TEXT NOT NULL REFERENCES users(id), 31 + created_at INTEGER NOT NULL DEFAULT (unixepoch()), 32 + expires_at INTEGER NOT NULL 33 + ); 34 + CREATE INDEX idx_sessions_expires ON sessions(expires_at); 35 + 36 + CREATE TABLE locations ( 37 + id TEXT PRIMARY KEY, 38 + google_place_id TEXT NOT NULL UNIQUE, 39 + name TEXT NOT NULL, 40 + address TEXT, 41 + lat REAL, 42 + lng REAL, 43 + created_at INTEGER NOT NULL DEFAULT (unixepoch()) 44 + ); 45 + 46 + CREATE TABLE posts ( 47 + id TEXT PRIMARY KEY, 48 + author_id TEXT NOT NULL REFERENCES users(id), 49 + caption TEXT NOT NULL DEFAULT '', 50 + location_id TEXT REFERENCES locations(id), 51 + -- unix MILLISECONDS (cursor tie-breaking); other tables use seconds 52 + created_at INTEGER NOT NULL DEFAULT (CAST(unixepoch('subsec') * 1000 AS INTEGER)) 53 + ); 54 + CREATE INDEX idx_posts_feed ON posts(created_at DESC, id DESC); 55 + 56 + CREATE TABLE photos ( 57 + id TEXT PRIMARY KEY, 58 + post_id TEXT REFERENCES posts(id), -- NULL until attached to a post 59 + uploader_id TEXT NOT NULL REFERENCES users(id), 60 + position INTEGER NOT NULL DEFAULT 0, 61 + r2_key TEXT NOT NULL, 62 + filename TEXT, 63 + mime TEXT NOT NULL, 64 + width INTEGER, 65 + height INTEGER, 66 + taken_at INTEGER, 67 + gps_lat REAL, 68 + gps_lng REAL, 69 + location_id TEXT REFERENCES locations(id), -- per-photo location (overrides post's) 70 + created_at INTEGER NOT NULL DEFAULT (unixepoch()) 71 + ); 72 + CREATE INDEX idx_photos_post ON photos(post_id, position);
+3
migrations/0002_photo_orientation.sql
··· 1 + -- Migration number: 0002 photo orientation 2 + -- EXIF orientation (1-8); needed to fix portrait photos and aspect ratios. 3 + ALTER TABLE photos ADD COLUMN orientation INTEGER NOT NULL DEFAULT 1;
+17
migrations/0003_comments_reactions.sql
··· 1 + -- Migration number: 0003 comments and reactions 2 + CREATE TABLE comments ( 3 + id TEXT PRIMARY KEY, 4 + post_id TEXT NOT NULL REFERENCES posts(id), 5 + author_id TEXT NOT NULL REFERENCES users(id), 6 + body TEXT NOT NULL, 7 + created_at INTEGER NOT NULL DEFAULT (unixepoch()) 8 + ); 9 + CREATE INDEX idx_comments_post ON comments(post_id, created_at); 10 + 11 + CREATE TABLE reactions ( 12 + post_id TEXT NOT NULL REFERENCES posts(id), 13 + user_id TEXT NOT NULL REFERENCES users(id), 14 + emoji TEXT NOT NULL, 15 + created_at INTEGER NOT NULL DEFAULT (unixepoch()), 16 + PRIMARY KEY (post_id, user_id, emoji) 17 + );
+8920
package-lock.json
··· 1 + { 2 + "name": "aniverse", 3 + "lockfileVersion": 3, 4 + "requires": true, 5 + "packages": { 6 + "": { 7 + "name": "aniverse", 8 + "dependencies": { 9 + "@simplewebauthn/browser": "^13.3.0", 10 + "@simplewebauthn/server": "^13.3.2", 11 + "@tanstack/query-sync-storage-persister": "^5.101.2", 12 + "@tanstack/react-query": "^5.101.2", 13 + "@tanstack/react-query-persist-client": "^5.101.2", 14 + "arctic": "^3.7.0", 15 + "exifr": "^7.1.3", 16 + "hono": "^4.12.30", 17 + "react": "^19.2.7", 18 + "react-dom": "^19.2.7", 19 + "react-router-dom": "^7.18.1" 20 + }, 21 + "devDependencies": { 22 + "@cloudflare/vite-plugin": "^1.45.1", 23 + "@tailwindcss/vite": "^4.3.3", 24 + "@types/react": "^19.2.17", 25 + "@types/react-dom": "^19.2.3", 26 + "@vitejs/plugin-react": "^6.0.3", 27 + "tailwindcss": "^4.3.3", 28 + "typescript": "^7.0.2", 29 + "vite": "^8.1.5", 30 + "vite-plugin-pwa": "^1.3.0", 31 + "wrangler": "^4.112.0" 32 + } 33 + }, 34 + "node_modules/@apideck/better-ajv-errors": { 35 + "version": "0.3.7", 36 + "resolved": "https://registry.npmjs.org/@apideck/better-ajv-errors/-/better-ajv-errors-0.3.7.tgz", 37 + "integrity": "sha512-TajUJwGWbDwkCx/CZi7tRE8PVB7simCvKJfHUsSdvps+aTM/PDPP4gkLmKnc+x3CE//y9i/nj74GqdL/hwk7Iw==", 38 + "dev": true, 39 + "license": "MIT", 40 + "dependencies": { 41 + "jsonpointer": "^5.0.1", 42 + "leven": "^3.1.0" 43 + }, 44 + "engines": { 45 + "node": ">=10" 46 + }, 47 + "peerDependencies": { 48 + "ajv": ">=8" 49 + } 50 + }, 51 + "node_modules/@babel/code-frame": { 52 + "version": "7.29.7", 53 + "resolved": "https://registry.npmjs.org/@babel/code-frame/-/code-frame-7.29.7.tgz", 54 + "integrity": "sha512-Aup7aUOfpbAUg2ROOJN6Iw5f9DMBlzu0mIkm/malLQFN/YQgO48wCj0Kxa3sEHJvPVFg7siR+qRInwXd2qhQKw==", 55 + "dev": true, 56 + "license": "MIT", 57 + "dependencies": { 58 + "@babel/helper-validator-identifier": "^7.29.7", 59 + "js-tokens": "^4.0.0", 60 + "picocolors": "^1.1.1" 61 + }, 62 + "engines": { 63 + "node": ">=6.9.0" 64 + } 65 + }, 66 + "node_modules/@babel/compat-data": { 67 + "version": "7.29.7", 68 + "resolved": "https://registry.npmjs.org/@babel/compat-data/-/compat-data-7.29.7.tgz", 69 + "integrity": "sha512-locTkQyKvwIEgBzVrn8693ebc97F2U8ZHjbXwDXJ5Fn2TCpNwTlKcaKLkdHop5c/icOFE7qt7Q9JC5hnKNa6Gg==", 70 + "dev": true, 71 + "license": "MIT", 72 + "engines": { 73 + "node": ">=6.9.0" 74 + } 75 + }, 76 + "node_modules/@babel/core": { 77 + "version": "7.29.7", 78 + "resolved": "https://registry.npmjs.org/@babel/core/-/core-7.29.7.tgz", 79 + "integrity": "sha512-RgHBCvtjbOK2gXSNBNIkNoEc9qoVEtau3hj8gEqKQuL3HZAibKarWFEI3Lfm6EYKkLalOh8eSrj9b+ch9H/VBA==", 80 + "dev": true, 81 + "license": "MIT", 82 + "dependencies": { 83 + "@babel/code-frame": "^7.29.7", 84 + "@babel/generator": "^7.29.7", 85 + "@babel/helper-compilation-targets": "^7.29.7", 86 + "@babel/helper-module-transforms": "^7.29.7", 87 + "@babel/helpers": "^7.29.7", 88 + "@babel/parser": "^7.29.7", 89 + "@babel/template": "^7.29.7", 90 + "@babel/traverse": "^7.29.7", 91 + "@babel/types": "^7.29.7", 92 + "@jridgewell/remapping": "^2.3.5", 93 + "convert-source-map": "^2.0.0", 94 + "debug": "^4.1.0", 95 + "gensync": "^1.0.0-beta.2", 96 + "json5": "^2.2.3", 97 + "semver": "^6.3.1" 98 + }, 99 + "engines": { 100 + "node": ">=6.9.0" 101 + }, 102 + "funding": { 103 + "type": "opencollective", 104 + "url": "https://opencollective.com/babel" 105 + } 106 + }, 107 + "node_modules/@babel/core/node_modules/semver": { 108 + "version": "6.3.1", 109 + "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.1.tgz", 110 + "integrity": "sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA==", 111 + "dev": true, 112 + "license": "ISC", 113 + "bin": { 114 + "semver": "bin/semver.js" 115 + } 116 + }, 117 + "node_modules/@babel/generator": { 118 + "version": "7.29.7", 119 + "resolved": "https://registry.npmjs.org/@babel/generator/-/generator-7.29.7.tgz", 120 + "integrity": "sha512-DkXD5OJQaAQIdZ1bt3UZdEnHAn9Imd3IVBdX03UFe+ony9Ojw5pzr9YVKGDY1jt+Gcn/FnGkNf8r+Vj5NOJWtQ==", 121 + "dev": true, 122 + "license": "MIT", 123 + "dependencies": { 124 + "@babel/parser": "^7.29.7", 125 + "@babel/types": "^7.29.7", 126 + "@jridgewell/gen-mapping": "^0.3.12", 127 + "@jridgewell/trace-mapping": "^0.3.28", 128 + "jsesc": "^3.0.2" 129 + }, 130 + "engines": { 131 + "node": ">=6.9.0" 132 + } 133 + }, 134 + "node_modules/@babel/helper-annotate-as-pure": { 135 + "version": "7.29.7", 136 + "resolved": "https://registry.npmjs.org/@babel/helper-annotate-as-pure/-/helper-annotate-as-pure-7.29.7.tgz", 137 + "integrity": "sha512-OoK6239jHPuSQOoS0kfTVKn0b/rVTk0seKq4Gd2UMLtmOVLjDC0ki3e+c90Trqv2gMfvJFqkiljrr568+qddiw==", 138 + "dev": true, 139 + "license": "MIT", 140 + "dependencies": { 141 + "@babel/types": "^7.29.7" 142 + }, 143 + "engines": { 144 + "node": ">=6.9.0" 145 + } 146 + }, 147 + "node_modules/@babel/helper-compilation-targets": { 148 + "version": "7.29.7", 149 + "resolved": "https://registry.npmjs.org/@babel/helper-compilation-targets/-/helper-compilation-targets-7.29.7.tgz", 150 + "integrity": "sha512-wem6WaBj4NaVYVdNhLPPVacES6ZJ+KBBfSkTMD3YZxbP3rm3Di85tJU5ljaUNhaOynt+Aj0xruhYuzQBt8n71g==", 151 + "dev": true, 152 + "license": "MIT", 153 + "dependencies": { 154 + "@babel/compat-data": "^7.29.7", 155 + "@babel/helper-validator-option": "^7.29.7", 156 + "browserslist": "^4.24.0", 157 + "lru-cache": "^5.1.1", 158 + "semver": "^6.3.1" 159 + }, 160 + "engines": { 161 + "node": ">=6.9.0" 162 + } 163 + }, 164 + "node_modules/@babel/helper-compilation-targets/node_modules/semver": { 165 + "version": "6.3.1", 166 + "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.1.tgz", 167 + "integrity": "sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA==", 168 + "dev": true, 169 + "license": "ISC", 170 + "bin": { 171 + "semver": "bin/semver.js" 172 + } 173 + }, 174 + "node_modules/@babel/helper-create-class-features-plugin": { 175 + "version": "7.29.7", 176 + "resolved": "https://registry.npmjs.org/@babel/helper-create-class-features-plugin/-/helper-create-class-features-plugin-7.29.7.tgz", 177 + "integrity": "sha512-IY3ZD9Tmooqr3TUhc3DUWxiuo8xx1DWLhd5M7hQ+ZWJamqM2BbalrBJb2MisSLoYorOj75U03qULCxQTY9r3hg==", 178 + "dev": true, 179 + "license": "MIT", 180 + "dependencies": { 181 + "@babel/helper-annotate-as-pure": "^7.29.7", 182 + "@babel/helper-member-expression-to-functions": "^7.29.7", 183 + "@babel/helper-optimise-call-expression": "^7.29.7", 184 + "@babel/helper-replace-supers": "^7.29.7", 185 + "@babel/helper-skip-transparent-expression-wrappers": "^7.29.7", 186 + "@babel/traverse": "^7.29.7", 187 + "semver": "^6.3.1" 188 + }, 189 + "engines": { 190 + "node": ">=6.9.0" 191 + }, 192 + "peerDependencies": { 193 + "@babel/core": "^7.0.0" 194 + } 195 + }, 196 + "node_modules/@babel/helper-create-class-features-plugin/node_modules/semver": { 197 + "version": "6.3.1", 198 + "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.1.tgz", 199 + "integrity": "sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA==", 200 + "dev": true, 201 + "license": "ISC", 202 + "bin": { 203 + "semver": "bin/semver.js" 204 + } 205 + }, 206 + "node_modules/@babel/helper-create-regexp-features-plugin": { 207 + "version": "7.29.7", 208 + "resolved": "https://registry.npmjs.org/@babel/helper-create-regexp-features-plugin/-/helper-create-regexp-features-plugin-7.29.7.tgz", 209 + "integrity": "sha512-907Uymvqgg1dwUA+7IGwFAOSYzQOuzPXKNJ1yxzwPffzkYFg2q2eHi1fIOs6sXkG9NbIUMunnUlkYsfRFNvomg==", 210 + "dev": true, 211 + "license": "MIT", 212 + "dependencies": { 213 + "@babel/helper-annotate-as-pure": "^7.29.7", 214 + "regexpu-core": "^6.3.1", 215 + "semver": "^6.3.1" 216 + }, 217 + "engines": { 218 + "node": ">=6.9.0" 219 + }, 220 + "peerDependencies": { 221 + "@babel/core": "^7.0.0" 222 + } 223 + }, 224 + "node_modules/@babel/helper-create-regexp-features-plugin/node_modules/semver": { 225 + "version": "6.3.1", 226 + "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.1.tgz", 227 + "integrity": "sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA==", 228 + "dev": true, 229 + "license": "ISC", 230 + "bin": { 231 + "semver": "bin/semver.js" 232 + } 233 + }, 234 + "node_modules/@babel/helper-define-polyfill-provider": { 235 + "version": "0.6.8", 236 + "resolved": "https://registry.npmjs.org/@babel/helper-define-polyfill-provider/-/helper-define-polyfill-provider-0.6.8.tgz", 237 + "integrity": "sha512-47UwBLPpQi1NoWzLuHNjRoHlYXMwIJoBf7MFou6viC/sIHWYygpvr0B6IAyh5sBdA2nr2LPIRww8lfaUVQINBA==", 238 + "dev": true, 239 + "license": "MIT", 240 + "dependencies": { 241 + "@babel/helper-compilation-targets": "^7.28.6", 242 + "@babel/helper-plugin-utils": "^7.28.6", 243 + "debug": "^4.4.3", 244 + "lodash.debounce": "^4.0.8", 245 + "resolve": "^1.22.11" 246 + }, 247 + "peerDependencies": { 248 + "@babel/core": "^7.4.0 || ^8.0.0-0 <8.0.0" 249 + } 250 + }, 251 + "node_modules/@babel/helper-globals": { 252 + "version": "7.29.7", 253 + "resolved": "https://registry.npmjs.org/@babel/helper-globals/-/helper-globals-7.29.7.tgz", 254 + "integrity": "sha512-3nQVUAtvkKH9zahfWgw96Jc/uFOmjACE1kQz82E2lqWmHBgjzbNlsC22nuQTfahmWeQtTq5nQ/4Nnd2A1wj4zA==", 255 + "dev": true, 256 + "license": "MIT", 257 + "engines": { 258 + "node": ">=6.9.0" 259 + } 260 + }, 261 + "node_modules/@babel/helper-member-expression-to-functions": { 262 + "version": "7.29.7", 263 + "resolved": "https://registry.npmjs.org/@babel/helper-member-expression-to-functions/-/helper-member-expression-to-functions-7.29.7.tgz", 264 + "integrity": "sha512-j+7JYmk1JYDtACIGj0QJqqWZjoUpMoEikQGADMaHgCMCSDqd2+P32rfcibUNrGOMWrlzK1WJBdxrB3JJQZwWtg==", 265 + "dev": true, 266 + "license": "MIT", 267 + "dependencies": { 268 + "@babel/traverse": "^7.29.7", 269 + "@babel/types": "^7.29.7" 270 + }, 271 + "engines": { 272 + "node": ">=6.9.0" 273 + } 274 + }, 275 + "node_modules/@babel/helper-module-imports": { 276 + "version": "7.29.7", 277 + "resolved": "https://registry.npmjs.org/@babel/helper-module-imports/-/helper-module-imports-7.29.7.tgz", 278 + "integrity": "sha512-ejHwrQQYcm9xnTivShn2IDOlIzInN34AXskvq9QicvCtEzq1Vzclu/tKF8Jq1Cg8JG2GL6/EmjgsCT7lXepE3g==", 279 + "dev": true, 280 + "license": "MIT", 281 + "dependencies": { 282 + "@babel/traverse": "^7.29.7", 283 + "@babel/types": "^7.29.7" 284 + }, 285 + "engines": { 286 + "node": ">=6.9.0" 287 + } 288 + }, 289 + "node_modules/@babel/helper-module-transforms": { 290 + "version": "7.29.7", 291 + "resolved": "https://registry.npmjs.org/@babel/helper-module-transforms/-/helper-module-transforms-7.29.7.tgz", 292 + "integrity": "sha512-UPUVSyXbOh627KiCIGQSgwWzGeBKLkaJ9PJEdrngIwMSzxLR4jS4+f1f1jb7VzBbg8nFLaYotvVPFCTqdrmTAg==", 293 + "dev": true, 294 + "license": "MIT", 295 + "dependencies": { 296 + "@babel/helper-module-imports": "^7.29.7", 297 + "@babel/helper-validator-identifier": "^7.29.7", 298 + "@babel/traverse": "^7.29.7" 299 + }, 300 + "engines": { 301 + "node": ">=6.9.0" 302 + }, 303 + "peerDependencies": { 304 + "@babel/core": "^7.0.0" 305 + } 306 + }, 307 + "node_modules/@babel/helper-optimise-call-expression": { 308 + "version": "7.29.7", 309 + "resolved": "https://registry.npmjs.org/@babel/helper-optimise-call-expression/-/helper-optimise-call-expression-7.29.7.tgz", 310 + "integrity": "sha512-+kmGVjcT9RGYzoDwdwEqEvGgKe3BYq+O1iGzjFubaNgZHwYHP6lsF2Yghf4kEuv9BV7tYDZ913aBW9am6YKong==", 311 + "dev": true, 312 + "license": "MIT", 313 + "dependencies": { 314 + "@babel/types": "^7.29.7" 315 + }, 316 + "engines": { 317 + "node": ">=6.9.0" 318 + } 319 + }, 320 + "node_modules/@babel/helper-plugin-utils": { 321 + "version": "7.29.7", 322 + "resolved": "https://registry.npmjs.org/@babel/helper-plugin-utils/-/helper-plugin-utils-7.29.7.tgz", 323 + "integrity": "sha512-G7sHYigPY17oO5SYWnfD/0MTBwVR781S/JI643e/JhUYgVgWE/61SoW3NH9KWUKyKq5LVh3npif99Wkt6j86Jw==", 324 + "dev": true, 325 + "license": "MIT", 326 + "engines": { 327 + "node": ">=6.9.0" 328 + } 329 + }, 330 + "node_modules/@babel/helper-remap-async-to-generator": { 331 + "version": "7.29.7", 332 + "resolved": "https://registry.npmjs.org/@babel/helper-remap-async-to-generator/-/helper-remap-async-to-generator-7.29.7.tgz", 333 + "integrity": "sha512-16AMiW26DbXWBbr3B8wNozKM0ydMLB892vaOaJW/fPJdnT8vJk5sdkQcU/isqUxyCE0cEoa8wZOcbgDuC4b6Og==", 334 + "dev": true, 335 + "license": "MIT", 336 + "dependencies": { 337 + "@babel/helper-annotate-as-pure": "^7.29.7", 338 + "@babel/helper-wrap-function": "^7.29.7", 339 + "@babel/traverse": "^7.29.7" 340 + }, 341 + "engines": { 342 + "node": ">=6.9.0" 343 + }, 344 + "peerDependencies": { 345 + "@babel/core": "^7.0.0" 346 + } 347 + }, 348 + "node_modules/@babel/helper-replace-supers": { 349 + "version": "7.29.7", 350 + "resolved": "https://registry.npmjs.org/@babel/helper-replace-supers/-/helper-replace-supers-7.29.7.tgz", 351 + "integrity": "sha512-atfGXWSeCiF4DnKZIfmJfQRkSw9b9gNNXR1kqKjbhG4pGYCOnkp8OcTB8E3NXjBu8NpheSnOeNKz8KT7UNFTmQ==", 352 + "dev": true, 353 + "license": "MIT", 354 + "dependencies": { 355 + "@babel/helper-member-expression-to-functions": "^7.29.7", 356 + "@babel/helper-optimise-call-expression": "^7.29.7", 357 + "@babel/traverse": "^7.29.7" 358 + }, 359 + "engines": { 360 + "node": ">=6.9.0" 361 + }, 362 + "peerDependencies": { 363 + "@babel/core": "^7.0.0" 364 + } 365 + }, 366 + "node_modules/@babel/helper-skip-transparent-expression-wrappers": { 367 + "version": "7.29.7", 368 + "resolved": "https://registry.npmjs.org/@babel/helper-skip-transparent-expression-wrappers/-/helper-skip-transparent-expression-wrappers-7.29.7.tgz", 369 + "integrity": "sha512-brcMGQaVzIeUb+6/bs1Av0f8YuNNjKY2JyvfRCsFuFsdKccEQ5Ges2y74D74NZ1Rz8lKJ9ksJkfqwQFJ/iNEyQ==", 370 + "dev": true, 371 + "license": "MIT", 372 + "dependencies": { 373 + "@babel/traverse": "^7.29.7", 374 + "@babel/types": "^7.29.7" 375 + }, 376 + "engines": { 377 + "node": ">=6.9.0" 378 + } 379 + }, 380 + "node_modules/@babel/helper-string-parser": { 381 + "version": "7.29.7", 382 + "resolved": "https://registry.npmjs.org/@babel/helper-string-parser/-/helper-string-parser-7.29.7.tgz", 383 + "integrity": "sha512-Pb5ijPrZ89GDH8223L4UP8i6QApWxs04RbPQJTeWDV0/keR2E36MeKnyr6LYmUUvqRRI+Iv87SuF1W6ErINzYw==", 384 + "dev": true, 385 + "license": "MIT", 386 + "engines": { 387 + "node": ">=6.9.0" 388 + } 389 + }, 390 + "node_modules/@babel/helper-validator-identifier": { 391 + "version": "7.29.7", 392 + "resolved": "https://registry.npmjs.org/@babel/helper-validator-identifier/-/helper-validator-identifier-7.29.7.tgz", 393 + "integrity": "sha512-qehxGkRj55h/ff8EMaJ+cYhyaKlHIxqYDn682wQD7RNp9UujOQsHog2uS0r2vzr4pW+sXf90NeeayjcNaX3fFg==", 394 + "dev": true, 395 + "license": "MIT", 396 + "engines": { 397 + "node": ">=6.9.0" 398 + } 399 + }, 400 + "node_modules/@babel/helper-validator-option": { 401 + "version": "7.29.7", 402 + "resolved": "https://registry.npmjs.org/@babel/helper-validator-option/-/helper-validator-option-7.29.7.tgz", 403 + "integrity": "sha512-N9ZErrD+yW5geCDtBqnOoxmR8+tNKiGuxKlDpuJxfsqpa2dFcexaziGAE/qoHLiDDreVNMupxGmSoNlyvsA3gw==", 404 + "dev": true, 405 + "license": "MIT", 406 + "engines": { 407 + "node": ">=6.9.0" 408 + } 409 + }, 410 + "node_modules/@babel/helper-wrap-function": { 411 + "version": "7.29.7", 412 + "resolved": "https://registry.npmjs.org/@babel/helper-wrap-function/-/helper-wrap-function-7.29.7.tgz", 413 + "integrity": "sha512-iES0Skag9ERIF68aXadpO6dbXa03mNWK3sEqJaMnLNs/eC3l0lkImdfoy6Y09/SfkpawdAB4RjQ7PVA7TcVGdw==", 414 + "dev": true, 415 + "license": "MIT", 416 + "dependencies": { 417 + "@babel/template": "^7.29.7", 418 + "@babel/traverse": "^7.29.7", 419 + "@babel/types": "^7.29.7" 420 + }, 421 + "engines": { 422 + "node": ">=6.9.0" 423 + } 424 + }, 425 + "node_modules/@babel/helpers": { 426 + "version": "7.29.7", 427 + "resolved": "https://registry.npmjs.org/@babel/helpers/-/helpers-7.29.7.tgz", 428 + "integrity": "sha512-1k2lAGRMfHTcwuNYcCNUmaUffmQv8KWMfh2iJUUeRlwlwH4FdNG7mfPI10NPfLHJFThE4Tyr4mv7kTNZOiPuBg==", 429 + "dev": true, 430 + "license": "MIT", 431 + "dependencies": { 432 + "@babel/template": "^7.29.7", 433 + "@babel/types": "^7.29.7" 434 + }, 435 + "engines": { 436 + "node": ">=6.9.0" 437 + } 438 + }, 439 + "node_modules/@babel/parser": { 440 + "version": "7.29.7", 441 + "resolved": "https://registry.npmjs.org/@babel/parser/-/parser-7.29.7.tgz", 442 + "integrity": "sha512-hnORnjP/1P/zFEndoeX+n+t1RwWRJiJpM/jO7FW32Kn9r5+sJB2JWOdYo4L6k78j15eCwY3Gm/7364B1EMwtNg==", 443 + "dev": true, 444 + "license": "MIT", 445 + "dependencies": { 446 + "@babel/types": "^7.29.7" 447 + }, 448 + "bin": { 449 + "parser": "bin/babel-parser.js" 450 + }, 451 + "engines": { 452 + "node": ">=6.0.0" 453 + } 454 + }, 455 + "node_modules/@babel/plugin-bugfix-firefox-class-in-computed-class-key": { 456 + "version": "7.29.7", 457 + "resolved": "https://registry.npmjs.org/@babel/plugin-bugfix-firefox-class-in-computed-class-key/-/plugin-bugfix-firefox-class-in-computed-class-key-7.29.7.tgz", 458 + "integrity": "sha512-j8SrR0zLZrRsC09DlszEx8FpMiwukKffYXMK0d5LmOglO7vGG6sz/BR/20yHqWH+Lnn31JTt2PE3hIWNgM2J6w==", 459 + "dev": true, 460 + "license": "MIT", 461 + "dependencies": { 462 + "@babel/helper-plugin-utils": "^7.29.7", 463 + "@babel/traverse": "^7.29.7" 464 + }, 465 + "engines": { 466 + "node": ">=6.9.0" 467 + }, 468 + "peerDependencies": { 469 + "@babel/core": "^7.0.0" 470 + } 471 + }, 472 + "node_modules/@babel/plugin-bugfix-safari-class-field-initializer-scope": { 473 + "version": "7.29.7", 474 + "resolved": "https://registry.npmjs.org/@babel/plugin-bugfix-safari-class-field-initializer-scope/-/plugin-bugfix-safari-class-field-initializer-scope-7.29.7.tgz", 475 + "integrity": "sha512-r8j8escF+U2FUHo0KOhPUdMzUO+jp9fInva6+ACVAF3Y97Ev+5iNZwiqTghmzNeWwDkOPlYuTcfb1vDaoZKmAQ==", 476 + "dev": true, 477 + "license": "MIT", 478 + "dependencies": { 479 + "@babel/helper-plugin-utils": "^7.29.7" 480 + }, 481 + "engines": { 482 + "node": ">=6.9.0" 483 + }, 484 + "peerDependencies": { 485 + "@babel/core": "^7.0.0" 486 + } 487 + }, 488 + "node_modules/@babel/plugin-bugfix-safari-id-destructuring-collision-in-function-expression": { 489 + "version": "7.29.7", 490 + "resolved": "https://registry.npmjs.org/@babel/plugin-bugfix-safari-id-destructuring-collision-in-function-expression/-/plugin-bugfix-safari-id-destructuring-collision-in-function-expression-7.29.7.tgz", 491 + "integrity": "sha512-GE1TFSiuFeGsCxmYXZl8HwoPrVlwe4rHPFE8weieGKZqnDORK+Ar3vgWMgW+AOxQ6/2TgLSKx9p6W7O4rC6qgQ==", 492 + "dev": true, 493 + "license": "MIT", 494 + "dependencies": { 495 + "@babel/helper-plugin-utils": "^7.29.7" 496 + }, 497 + "engines": { 498 + "node": ">=6.9.0" 499 + }, 500 + "peerDependencies": { 501 + "@babel/core": "^7.0.0" 502 + } 503 + }, 504 + "node_modules/@babel/plugin-bugfix-safari-rest-destructuring-rhs-array": { 505 + "version": "7.29.7", 506 + "resolved": "https://registry.npmjs.org/@babel/plugin-bugfix-safari-rest-destructuring-rhs-array/-/plugin-bugfix-safari-rest-destructuring-rhs-array-7.29.7.tgz", 507 + "integrity": "sha512-oBNVCvnO5tND+xSopWvV8WNGfpTfgP4Zr/YXXSj8zfmcPktp5Ku/aZlsIowgSD4fjmgHn6sGmB9APVsU5zOdhA==", 508 + "dev": true, 509 + "license": "MIT", 510 + "dependencies": { 511 + "@babel/helper-plugin-utils": "^7.29.7", 512 + "@babel/helper-skip-transparent-expression-wrappers": "^7.29.7" 513 + }, 514 + "engines": { 515 + "node": ">=6.9.0" 516 + }, 517 + "peerDependencies": { 518 + "@babel/core": "^7.0.0" 519 + } 520 + }, 521 + "node_modules/@babel/plugin-bugfix-v8-spread-parameters-in-optional-chaining": { 522 + "version": "7.29.7", 523 + "resolved": "https://registry.npmjs.org/@babel/plugin-bugfix-v8-spread-parameters-in-optional-chaining/-/plugin-bugfix-v8-spread-parameters-in-optional-chaining-7.29.7.tgz", 524 + "integrity": "sha512-QQt9qKHZ2sg/kivaLr7lnQr8HVrQDdBNSfCsTjiDxRuX/K5ORyKq+Bu8Xr0cDE3Dfkv0cw28Ve0EKyKMvulkOw==", 525 + "dev": true, 526 + "license": "MIT", 527 + "dependencies": { 528 + "@babel/helper-plugin-utils": "^7.29.7", 529 + "@babel/helper-skip-transparent-expression-wrappers": "^7.29.7", 530 + "@babel/plugin-transform-optional-chaining": "^7.29.7" 531 + }, 532 + "engines": { 533 + "node": ">=6.9.0" 534 + }, 535 + "peerDependencies": { 536 + "@babel/core": "^7.13.0" 537 + } 538 + }, 539 + "node_modules/@babel/plugin-bugfix-v8-static-class-fields-redefine-readonly": { 540 + "version": "7.29.7", 541 + "resolved": "https://registry.npmjs.org/@babel/plugin-bugfix-v8-static-class-fields-redefine-readonly/-/plugin-bugfix-v8-static-class-fields-redefine-readonly-7.29.7.tgz", 542 + "integrity": "sha512-pn6QacGLgvCcwc+syUhKE/qSjV2D1IHDB84RNxWYSt1mW3K/SCtjinZ2p0cETJxAWBjPy3K/1lHwG5BjjPxNlw==", 543 + "dev": true, 544 + "license": "MIT", 545 + "dependencies": { 546 + "@babel/helper-plugin-utils": "^7.29.7", 547 + "@babel/traverse": "^7.29.7" 548 + }, 549 + "engines": { 550 + "node": ">=6.9.0" 551 + }, 552 + "peerDependencies": { 553 + "@babel/core": "^7.0.0" 554 + } 555 + }, 556 + "node_modules/@babel/plugin-proposal-private-property-in-object": { 557 + "version": "7.21.0-placeholder-for-preset-env.2", 558 + "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-private-property-in-object/-/plugin-proposal-private-property-in-object-7.21.0-placeholder-for-preset-env.2.tgz", 559 + "integrity": "sha512-SOSkfJDddaM7mak6cPEpswyTRnuRltl429hMraQEglW+OkovnCzsiszTmsrlY//qLFjCpQDFRvjdm2wA5pPm9w==", 560 + "dev": true, 561 + "license": "MIT", 562 + "engines": { 563 + "node": ">=6.9.0" 564 + }, 565 + "peerDependencies": { 566 + "@babel/core": "^7.0.0-0" 567 + } 568 + }, 569 + "node_modules/@babel/plugin-syntax-import-assertions": { 570 + "version": "7.29.7", 571 + "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-import-assertions/-/plugin-syntax-import-assertions-7.29.7.tgz", 572 + "integrity": "sha512-/An1OCBN93thpBAGyfsK2pcf0jvju1SAtKkL2Ny++B5Sy6sqgzXDQH1cZxWbF96Wuk+bn41MDA9bLd4VVAw6rw==", 573 + "dev": true, 574 + "license": "MIT", 575 + "dependencies": { 576 + "@babel/helper-plugin-utils": "^7.29.7" 577 + }, 578 + "engines": { 579 + "node": ">=6.9.0" 580 + }, 581 + "peerDependencies": { 582 + "@babel/core": "^7.0.0-0" 583 + } 584 + }, 585 + "node_modules/@babel/plugin-syntax-import-attributes": { 586 + "version": "7.29.7", 587 + "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-import-attributes/-/plugin-syntax-import-attributes-7.29.7.tgz", 588 + "integrity": "sha512-zGYcYfq/WmZ4V+kBIXQon9dSSc8ircGZqw9ZaNhhGj9nZkeBu1jHLBDQqYYi5WA9uawvA2sIMbry2nCFhf5Djg==", 589 + "dev": true, 590 + "license": "MIT", 591 + "dependencies": { 592 + "@babel/helper-plugin-utils": "^7.29.7" 593 + }, 594 + "engines": { 595 + "node": ">=6.9.0" 596 + }, 597 + "peerDependencies": { 598 + "@babel/core": "^7.0.0-0" 599 + } 600 + }, 601 + "node_modules/@babel/plugin-syntax-unicode-sets-regex": { 602 + "version": "7.18.6", 603 + "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-unicode-sets-regex/-/plugin-syntax-unicode-sets-regex-7.18.6.tgz", 604 + "integrity": "sha512-727YkEAPwSIQTv5im8QHz3upqp92JTWhidIC81Tdx4VJYIte/VndKf1qKrfnnhPLiPghStWfvC/iFaMCQu7Nqg==", 605 + "dev": true, 606 + "license": "MIT", 607 + "dependencies": { 608 + "@babel/helper-create-regexp-features-plugin": "^7.18.6", 609 + "@babel/helper-plugin-utils": "^7.18.6" 610 + }, 611 + "engines": { 612 + "node": ">=6.9.0" 613 + }, 614 + "peerDependencies": { 615 + "@babel/core": "^7.0.0" 616 + } 617 + }, 618 + "node_modules/@babel/plugin-transform-arrow-functions": { 619 + "version": "7.29.7", 620 + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-arrow-functions/-/plugin-transform-arrow-functions-7.29.7.tgz", 621 + "integrity": "sha512-N7zArUXWzAMzm+/N0uPBeVB3Fam5lMxtUwMmDK5f/IBBS7a7p1qeUoxd/6CckXoxUdgsntq1Dh8xNW06maZbDQ==", 622 + "dev": true, 623 + "license": "MIT", 624 + "dependencies": { 625 + "@babel/helper-plugin-utils": "^7.29.7" 626 + }, 627 + "engines": { 628 + "node": ">=6.9.0" 629 + }, 630 + "peerDependencies": { 631 + "@babel/core": "^7.0.0-0" 632 + } 633 + }, 634 + "node_modules/@babel/plugin-transform-async-generator-functions": { 635 + "version": "7.29.7", 636 + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-async-generator-functions/-/plugin-transform-async-generator-functions-7.29.7.tgz", 637 + "integrity": "sha512-d98gXZkgswvkyohMBABkhm3GeXhYj8psWfwQ2C7gtfrKGTykQa/iOIi+JJhwMjPlZ6Vm2XN+DCf3Es1EoG4ZLA==", 638 + "dev": true, 639 + "license": "MIT", 640 + "dependencies": { 641 + "@babel/helper-plugin-utils": "^7.29.7", 642 + "@babel/helper-remap-async-to-generator": "^7.29.7", 643 + "@babel/traverse": "^7.29.7" 644 + }, 645 + "engines": { 646 + "node": ">=6.9.0" 647 + }, 648 + "peerDependencies": { 649 + "@babel/core": "^7.0.0-0" 650 + } 651 + }, 652 + "node_modules/@babel/plugin-transform-async-to-generator": { 653 + "version": "7.29.7", 654 + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-async-to-generator/-/plugin-transform-async-to-generator-7.29.7.tgz", 655 + "integrity": "sha512-pcUb2SS+RMo9TWVBwKGI5ShtoG7R+zBsFmCKDa6fe8c+hPr3XJlZgoE5j6i8W7gDjhyvy+85vmYexanvXh3d1w==", 656 + "dev": true, 657 + "license": "MIT", 658 + "dependencies": { 659 + "@babel/helper-module-imports": "^7.29.7", 660 + "@babel/helper-plugin-utils": "^7.29.7", 661 + "@babel/helper-remap-async-to-generator": "^7.29.7" 662 + }, 663 + "engines": { 664 + "node": ">=6.9.0" 665 + }, 666 + "peerDependencies": { 667 + "@babel/core": "^7.0.0-0" 668 + } 669 + }, 670 + "node_modules/@babel/plugin-transform-block-scoped-functions": { 671 + "version": "7.29.7", 672 + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-block-scoped-functions/-/plugin-transform-block-scoped-functions-7.29.7.tgz", 673 + "integrity": "sha512-cUSmjh72N+rN4PrkFlN1dJwNCwjVp5d38/CQrEsFggkD10UiFlBFgdH3tv5dNsLuHY+3S8db2xCHjhZcv5WgvA==", 674 + "dev": true, 675 + "license": "MIT", 676 + "dependencies": { 677 + "@babel/helper-plugin-utils": "^7.29.7" 678 + }, 679 + "engines": { 680 + "node": ">=6.9.0" 681 + }, 682 + "peerDependencies": { 683 + "@babel/core": "^7.0.0-0" 684 + } 685 + }, 686 + "node_modules/@babel/plugin-transform-block-scoping": { 687 + "version": "7.29.7", 688 + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-block-scoping/-/plugin-transform-block-scoping-7.29.7.tgz", 689 + "integrity": "sha512-ONyr4+AZhKh8yKWInVxU9AXA9EbsyeLcL6V0dJy6M2/62vuvpGm29zzuymbTpdc451GEpDIdAyPLP3r+P61yKQ==", 690 + "dev": true, 691 + "license": "MIT", 692 + "dependencies": { 693 + "@babel/helper-plugin-utils": "^7.29.7" 694 + }, 695 + "engines": { 696 + "node": ">=6.9.0" 697 + }, 698 + "peerDependencies": { 699 + "@babel/core": "^7.0.0-0" 700 + } 701 + }, 702 + "node_modules/@babel/plugin-transform-class-properties": { 703 + "version": "7.29.7", 704 + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-class-properties/-/plugin-transform-class-properties-7.29.7.tgz", 705 + "integrity": "sha512-GtcpjFvanPfzNQi3eTitsCqtRRmmqzpy/A+yhTR1HaZo1Ly3EA8ZXxlPyHdR8/IuRMYc3E4wdGBewB2QKQjAaA==", 706 + "dev": true, 707 + "license": "MIT", 708 + "dependencies": { 709 + "@babel/helper-create-class-features-plugin": "^7.29.7", 710 + "@babel/helper-plugin-utils": "^7.29.7" 711 + }, 712 + "engines": { 713 + "node": ">=6.9.0" 714 + }, 715 + "peerDependencies": { 716 + "@babel/core": "^7.0.0-0" 717 + } 718 + }, 719 + "node_modules/@babel/plugin-transform-class-static-block": { 720 + "version": "7.29.7", 721 + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-class-static-block/-/plugin-transform-class-static-block-7.29.7.tgz", 722 + "integrity": "sha512-kibJgmEdX2iMwsHY2tSZNDgj8PwIlCQz7FK9KuGKO8zsuoUwSEhoNnNVp/emKWrbY4HeO6kkXfdMqRKKKXBm2A==", 723 + "dev": true, 724 + "license": "MIT", 725 + "dependencies": { 726 + "@babel/helper-create-class-features-plugin": "^7.29.7", 727 + "@babel/helper-plugin-utils": "^7.29.7" 728 + }, 729 + "engines": { 730 + "node": ">=6.9.0" 731 + }, 732 + "peerDependencies": { 733 + "@babel/core": "^7.12.0" 734 + } 735 + }, 736 + "node_modules/@babel/plugin-transform-classes": { 737 + "version": "7.29.7", 738 + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-classes/-/plugin-transform-classes-7.29.7.tgz", 739 + "integrity": "sha512-qV0OGGBVacduzQHE649JyCneOFI/maT+YKsO+K4Yi3xv2wTPNjM/W2o2gdzMwEAZz7fXNTHAe0NcSg30bIN69g==", 740 + "dev": true, 741 + "license": "MIT", 742 + "dependencies": { 743 + "@babel/helper-annotate-as-pure": "^7.29.7", 744 + "@babel/helper-compilation-targets": "^7.29.7", 745 + "@babel/helper-globals": "^7.29.7", 746 + "@babel/helper-plugin-utils": "^7.29.7", 747 + "@babel/helper-replace-supers": "^7.29.7", 748 + "@babel/traverse": "^7.29.7" 749 + }, 750 + "engines": { 751 + "node": ">=6.9.0" 752 + }, 753 + "peerDependencies": { 754 + "@babel/core": "^7.0.0-0" 755 + } 756 + }, 757 + "node_modules/@babel/plugin-transform-computed-properties": { 758 + "version": "7.29.7", 759 + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-computed-properties/-/plugin-transform-computed-properties-7.29.7.tgz", 760 + "integrity": "sha512-RK7/IyU5phpuCdBAuig5VkzG/EnbDaui5SQGdU9BFrHdV+mV4cUjLMQ9lJDjLNtWHsqtiefpGZUXQP2BiTYMsA==", 761 + "dev": true, 762 + "license": "MIT", 763 + "dependencies": { 764 + "@babel/helper-plugin-utils": "^7.29.7", 765 + "@babel/template": "^7.29.7" 766 + }, 767 + "engines": { 768 + "node": ">=6.9.0" 769 + }, 770 + "peerDependencies": { 771 + "@babel/core": "^7.0.0-0" 772 + } 773 + }, 774 + "node_modules/@babel/plugin-transform-destructuring": { 775 + "version": "7.29.7", 776 + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-destructuring/-/plugin-transform-destructuring-7.29.7.tgz", 777 + "integrity": "sha512-iPX8aD6H9zV5s7ZsqTdNocPN/MGQ5sSMnElKrktxjJRMnB2jN/1p2+R7GkfD6CAYoVFqy5A4XnSIUeGgJzIWpg==", 778 + "dev": true, 779 + "license": "MIT", 780 + "dependencies": { 781 + "@babel/helper-plugin-utils": "^7.29.7", 782 + "@babel/traverse": "^7.29.7" 783 + }, 784 + "engines": { 785 + "node": ">=6.9.0" 786 + }, 787 + "peerDependencies": { 788 + "@babel/core": "^7.0.0-0" 789 + } 790 + }, 791 + "node_modules/@babel/plugin-transform-dotall-regex": { 792 + "version": "7.29.7", 793 + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-dotall-regex/-/plugin-transform-dotall-regex-7.29.7.tgz", 794 + "integrity": "sha512-3qc18hsD2RdZiyJNDNc7HQpv6xbncwh8FYtxNFFzclSyh/trPD9KkVR9BDECUjDLvb7yJVF15GfYUuC+LMkkiQ==", 795 + "dev": true, 796 + "license": "MIT", 797 + "dependencies": { 798 + "@babel/helper-create-regexp-features-plugin": "^7.29.7", 799 + "@babel/helper-plugin-utils": "^7.29.7" 800 + }, 801 + "engines": { 802 + "node": ">=6.9.0" 803 + }, 804 + "peerDependencies": { 805 + "@babel/core": "^7.0.0-0" 806 + } 807 + }, 808 + "node_modules/@babel/plugin-transform-duplicate-keys": { 809 + "version": "7.29.7", 810 + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-duplicate-keys/-/plugin-transform-duplicate-keys-7.29.7.tgz", 811 + "integrity": "sha512-6IvRRriEMqnBwD6chtxdLpMYCHWEzN+oL5cyQtjykya19UgzbmKhxmhZgKC/LHxS2nYr9Q/qYPZ5Lr6jOL9+yQ==", 812 + "dev": true, 813 + "license": "MIT", 814 + "dependencies": { 815 + "@babel/helper-plugin-utils": "^7.29.7" 816 + }, 817 + "engines": { 818 + "node": ">=6.9.0" 819 + }, 820 + "peerDependencies": { 821 + "@babel/core": "^7.0.0-0" 822 + } 823 + }, 824 + "node_modules/@babel/plugin-transform-duplicate-named-capturing-groups-regex": { 825 + "version": "7.29.7", 826 + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-duplicate-named-capturing-groups-regex/-/plugin-transform-duplicate-named-capturing-groups-regex-7.29.7.tgz", 827 + "integrity": "sha512-2wiIyo2BjtgU7HufSeDnL9L2O7zr8jmhFKuSr65VpRkUiRKRNpb0mdlk56+XPPKoIrfHqzbMuglDvZun0RISsA==", 828 + "dev": true, 829 + "license": "MIT", 830 + "dependencies": { 831 + "@babel/helper-create-regexp-features-plugin": "^7.29.7", 832 + "@babel/helper-plugin-utils": "^7.29.7" 833 + }, 834 + "engines": { 835 + "node": ">=6.9.0" 836 + }, 837 + "peerDependencies": { 838 + "@babel/core": "^7.0.0" 839 + } 840 + }, 841 + "node_modules/@babel/plugin-transform-dynamic-import": { 842 + "version": "7.29.7", 843 + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-dynamic-import/-/plugin-transform-dynamic-import-7.29.7.tgz", 844 + "integrity": "sha512-giOlEm/EFjfjr+te9NsdjkUo2v4f8rS/SXPumRVHAtbNcyNlvtREkU1dZzaIDclNpnaVhlCqRdFKhJBjBikzLg==", 845 + "dev": true, 846 + "license": "MIT", 847 + "dependencies": { 848 + "@babel/helper-plugin-utils": "^7.29.7" 849 + }, 850 + "engines": { 851 + "node": ">=6.9.0" 852 + }, 853 + "peerDependencies": { 854 + "@babel/core": "^7.0.0-0" 855 + } 856 + }, 857 + "node_modules/@babel/plugin-transform-explicit-resource-management": { 858 + "version": "7.29.7", 859 + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-explicit-resource-management/-/plugin-transform-explicit-resource-management-7.29.7.tgz", 860 + "integrity": "sha512-Rstj7coNz8sE+7Ju7ihpHLI564lsK5pUpNNlvptCIC/16E/S5hbl6n3kESPKdNRmqEWlpn5xpS5Q2dvXBsySLw==", 861 + "dev": true, 862 + "license": "MIT", 863 + "dependencies": { 864 + "@babel/helper-plugin-utils": "^7.29.7", 865 + "@babel/plugin-transform-destructuring": "^7.29.7" 866 + }, 867 + "engines": { 868 + "node": ">=6.9.0" 869 + }, 870 + "peerDependencies": { 871 + "@babel/core": "^7.0.0-0" 872 + } 873 + }, 874 + "node_modules/@babel/plugin-transform-exponentiation-operator": { 875 + "version": "7.29.7", 876 + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-exponentiation-operator/-/plugin-transform-exponentiation-operator-7.29.7.tgz", 877 + "integrity": "sha512-zFpMOTLZBdW5LfObqcSbL6kefg4R4eLdmvS0wbN9M6D5Mym/sKm9toOoWyVOa+xDjvCnuWcHls2YonXwHvH3CQ==", 878 + "dev": true, 879 + "license": "MIT", 880 + "dependencies": { 881 + "@babel/helper-plugin-utils": "^7.29.7" 882 + }, 883 + "engines": { 884 + "node": ">=6.9.0" 885 + }, 886 + "peerDependencies": { 887 + "@babel/core": "^7.0.0-0" 888 + } 889 + }, 890 + "node_modules/@babel/plugin-transform-export-namespace-from": { 891 + "version": "7.29.7", 892 + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-export-namespace-from/-/plugin-transform-export-namespace-from-7.29.7.tgz", 893 + "integrity": "sha512-24B2nOy2TeJSMheqwPD4DDQOV/elLSIlKxjZt4i05H5AgdPdWR3n18HnNrcJ+j76WJd9gbwb9jPjNYUy6RautA==", 894 + "dev": true, 895 + "license": "MIT", 896 + "dependencies": { 897 + "@babel/helper-plugin-utils": "^7.29.7" 898 + }, 899 + "engines": { 900 + "node": ">=6.9.0" 901 + }, 902 + "peerDependencies": { 903 + "@babel/core": "^7.0.0-0" 904 + } 905 + }, 906 + "node_modules/@babel/plugin-transform-for-of": { 907 + "version": "7.29.7", 908 + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-for-of/-/plugin-transform-for-of-7.29.7.tgz", 909 + "integrity": "sha512-zeSIHh0+E1Um1WJRXCFlHQYu2ieJNdivLLjlBEp+dIBu3S51n+SZZmIXjxnItw6pz56Cn+KvK68BIBVsxq2JiQ==", 910 + "dev": true, 911 + "license": "MIT", 912 + "dependencies": { 913 + "@babel/helper-plugin-utils": "^7.29.7", 914 + "@babel/helper-skip-transparent-expression-wrappers": "^7.29.7" 915 + }, 916 + "engines": { 917 + "node": ">=6.9.0" 918 + }, 919 + "peerDependencies": { 920 + "@babel/core": "^7.0.0-0" 921 + } 922 + }, 923 + "node_modules/@babel/plugin-transform-function-name": { 924 + "version": "7.29.7", 925 + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-function-name/-/plugin-transform-function-name-7.29.7.tgz", 926 + "integrity": "sha512-otRWaHXE6fbAGkePvaj/kvs3HsqXfPhlnzwSOlnFgbqCPMd975dW+4wZ00WFBt+/YlBGcJwNrARQTOJOb4ZrIg==", 927 + "dev": true, 928 + "license": "MIT", 929 + "dependencies": { 930 + "@babel/helper-compilation-targets": "^7.29.7", 931 + "@babel/helper-plugin-utils": "^7.29.7", 932 + "@babel/traverse": "^7.29.7" 933 + }, 934 + "engines": { 935 + "node": ">=6.9.0" 936 + }, 937 + "peerDependencies": { 938 + "@babel/core": "^7.0.0-0" 939 + } 940 + }, 941 + "node_modules/@babel/plugin-transform-json-strings": { 942 + "version": "7.29.7", 943 + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-json-strings/-/plugin-transform-json-strings-7.29.7.tgz", 944 + "integrity": "sha512-RRnE2+eon1rJAq8MnoF1b5kTpY1vU88twHcvcKMrsqP/jxIRqDVs9iJB5fqPuqyeFAW0wJo4MlUIPpQCq/aRsg==", 945 + "dev": true, 946 + "license": "MIT", 947 + "dependencies": { 948 + "@babel/helper-plugin-utils": "^7.29.7" 949 + }, 950 + "engines": { 951 + "node": ">=6.9.0" 952 + }, 953 + "peerDependencies": { 954 + "@babel/core": "^7.0.0-0" 955 + } 956 + }, 957 + "node_modules/@babel/plugin-transform-literals": { 958 + "version": "7.29.7", 959 + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-literals/-/plugin-transform-literals-7.29.7.tgz", 960 + "integrity": "sha512-DZ/oLP21ZuWx1vKqnoNv6/tvEK48AQOBRai40CX9dTjGluvT/YZCyY3rryDtyUqCEoyNroy5KKPwX2iQCiRvyw==", 961 + "dev": true, 962 + "license": "MIT", 963 + "dependencies": { 964 + "@babel/helper-plugin-utils": "^7.29.7" 965 + }, 966 + "engines": { 967 + "node": ">=6.9.0" 968 + }, 969 + "peerDependencies": { 970 + "@babel/core": "^7.0.0-0" 971 + } 972 + }, 973 + "node_modules/@babel/plugin-transform-logical-assignment-operators": { 974 + "version": "7.29.7", 975 + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-logical-assignment-operators/-/plugin-transform-logical-assignment-operators-7.29.7.tgz", 976 + "integrity": "sha512-A0H91hh6W8MFRkp5TqJmMr39jzGD1A1E1Ysiv2O06Sfbhkapm+XyIzxWCEh5kqwOZ1/8QZ0dY3SeQ7XBqfJd5Q==", 977 + "dev": true, 978 + "license": "MIT", 979 + "dependencies": { 980 + "@babel/helper-plugin-utils": "^7.29.7" 981 + }, 982 + "engines": { 983 + "node": ">=6.9.0" 984 + }, 985 + "peerDependencies": { 986 + "@babel/core": "^7.0.0-0" 987 + } 988 + }, 989 + "node_modules/@babel/plugin-transform-member-expression-literals": { 990 + "version": "7.29.7", 991 + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-member-expression-literals/-/plugin-transform-member-expression-literals-7.29.7.tgz", 992 + "integrity": "sha512-hl1kwFZCCiDyfH25Xmco9jTrkPgnS9pmOzSG7W5I4SaGbLeqKv417hcU2RKmaxoPEgsoJh7ZPOrnPGq99bHoUg==", 993 + "dev": true, 994 + "license": "MIT", 995 + "dependencies": { 996 + "@babel/helper-plugin-utils": "^7.29.7" 997 + }, 998 + "engines": { 999 + "node": ">=6.9.0" 1000 + }, 1001 + "peerDependencies": { 1002 + "@babel/core": "^7.0.0-0" 1003 + } 1004 + }, 1005 + "node_modules/@babel/plugin-transform-modules-amd": { 1006 + "version": "7.29.7", 1007 + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-modules-amd/-/plugin-transform-modules-amd-7.29.7.tgz", 1008 + "integrity": "sha512-fxtQoH3m5ywUSIfaH0FGCzWu4McsYon5bD3K4XnskC7f+OyQMj7rsOMi4NvvmJ83WwBAg4UCe+ov4VZlqEvyew==", 1009 + "dev": true, 1010 + "license": "MIT", 1011 + "dependencies": { 1012 + "@babel/helper-module-transforms": "^7.29.7", 1013 + "@babel/helper-plugin-utils": "^7.29.7" 1014 + }, 1015 + "engines": { 1016 + "node": ">=6.9.0" 1017 + }, 1018 + "peerDependencies": { 1019 + "@babel/core": "^7.0.0-0" 1020 + } 1021 + }, 1022 + "node_modules/@babel/plugin-transform-modules-commonjs": { 1023 + "version": "7.29.7", 1024 + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-modules-commonjs/-/plugin-transform-modules-commonjs-7.29.7.tgz", 1025 + "integrity": "sha512-j0vCldybPC5b5dwCQOJ21uKtHzt7hxLygJTg9eF1ScfaikEDNfzn94XoW5Fi+seBR0nCyL23xaBFFkq7dTM8XQ==", 1026 + "dev": true, 1027 + "license": "MIT", 1028 + "dependencies": { 1029 + "@babel/helper-module-transforms": "^7.29.7", 1030 + "@babel/helper-plugin-utils": "^7.29.7" 1031 + }, 1032 + "engines": { 1033 + "node": ">=6.9.0" 1034 + }, 1035 + "peerDependencies": { 1036 + "@babel/core": "^7.0.0-0" 1037 + } 1038 + }, 1039 + "node_modules/@babel/plugin-transform-modules-systemjs": { 1040 + "version": "7.29.7", 1041 + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-modules-systemjs/-/plugin-transform-modules-systemjs-7.29.7.tgz", 1042 + "integrity": "sha512-TM2ZcQLoG2/y4HODiStCo10DibYhWhGWAwVv+EQKmG/7GFl0N+AAmUiXOMKM+aiJ9XBJ9AHVZBvTzMnJ2sM3cQ==", 1043 + "dev": true, 1044 + "license": "MIT", 1045 + "dependencies": { 1046 + "@babel/helper-module-transforms": "^7.29.7", 1047 + "@babel/helper-plugin-utils": "^7.29.7", 1048 + "@babel/helper-validator-identifier": "^7.29.7", 1049 + "@babel/traverse": "^7.29.7" 1050 + }, 1051 + "engines": { 1052 + "node": ">=6.9.0" 1053 + }, 1054 + "peerDependencies": { 1055 + "@babel/core": "^7.0.0-0" 1056 + } 1057 + }, 1058 + "node_modules/@babel/plugin-transform-modules-umd": { 1059 + "version": "7.29.7", 1060 + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-modules-umd/-/plugin-transform-modules-umd-7.29.7.tgz", 1061 + "integrity": "sha512-B4UkaTK3QpgCwJnrxKfMPKdo92CN7OKXAlpAAnM3UPu0Q0lCCk57ylA9AJbRy2v8dDKOPAAWcoR6CMyeoHwRCA==", 1062 + "dev": true, 1063 + "license": "MIT", 1064 + "dependencies": { 1065 + "@babel/helper-module-transforms": "^7.29.7", 1066 + "@babel/helper-plugin-utils": "^7.29.7" 1067 + }, 1068 + "engines": { 1069 + "node": ">=6.9.0" 1070 + }, 1071 + "peerDependencies": { 1072 + "@babel/core": "^7.0.0-0" 1073 + } 1074 + }, 1075 + "node_modules/@babel/plugin-transform-named-capturing-groups-regex": { 1076 + "version": "7.29.7", 1077 + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-named-capturing-groups-regex/-/plugin-transform-named-capturing-groups-regex-7.29.7.tgz", 1078 + "integrity": "sha512-vuFoLwr4qnv2xbZ16SQd6uPcH5FNrLHhk/Jzo++0XJFcaDsr4gjJVg6j398oMHiC+83k/GiBzviwF5KBJkPUtQ==", 1079 + "dev": true, 1080 + "license": "MIT", 1081 + "dependencies": { 1082 + "@babel/helper-create-regexp-features-plugin": "^7.29.7", 1083 + "@babel/helper-plugin-utils": "^7.29.7" 1084 + }, 1085 + "engines": { 1086 + "node": ">=6.9.0" 1087 + }, 1088 + "peerDependencies": { 1089 + "@babel/core": "^7.0.0" 1090 + } 1091 + }, 1092 + "node_modules/@babel/plugin-transform-new-target": { 1093 + "version": "7.29.7", 1094 + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-new-target/-/plugin-transform-new-target-7.29.7.tgz", 1095 + "integrity": "sha512-fEo41GmsOUhOBlw8ioo6zvjX5Xc2Lqkzlyfqbpsk3eB6TReV18uhxZ0esfEokVbY2+PVJAQHNKxER6lGrzNd3A==", 1096 + "dev": true, 1097 + "license": "MIT", 1098 + "dependencies": { 1099 + "@babel/helper-plugin-utils": "^7.29.7" 1100 + }, 1101 + "engines": { 1102 + "node": ">=6.9.0" 1103 + }, 1104 + "peerDependencies": { 1105 + "@babel/core": "^7.0.0-0" 1106 + } 1107 + }, 1108 + "node_modules/@babel/plugin-transform-nullish-coalescing-operator": { 1109 + "version": "7.29.7", 1110 + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-nullish-coalescing-operator/-/plugin-transform-nullish-coalescing-operator-7.29.7.tgz", 1111 + "integrity": "sha512-idmp1dFaekP9GbcMvG24Kvw2BfhFZjHnNJCkV4WuIY4PskJzwI3f1N5OdgYke38T7rftO6ERulFRn2cFeZwRkg==", 1112 + "dev": true, 1113 + "license": "MIT", 1114 + "dependencies": { 1115 + "@babel/helper-plugin-utils": "^7.29.7" 1116 + }, 1117 + "engines": { 1118 + "node": ">=6.9.0" 1119 + }, 1120 + "peerDependencies": { 1121 + "@babel/core": "^7.0.0-0" 1122 + } 1123 + }, 1124 + "node_modules/@babel/plugin-transform-numeric-separator": { 1125 + "version": "7.29.7", 1126 + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-numeric-separator/-/plugin-transform-numeric-separator-7.29.7.tgz", 1127 + "integrity": "sha512-zR7fv/z14OjgHl4AgRtkDBvBMhIzCxqV/qN/2BCRC7LjFwvuzjYe7gDWxC4Wl/SNsLM6SE1IWvRPYMgSJaUvNw==", 1128 + "dev": true, 1129 + "license": "MIT", 1130 + "dependencies": { 1131 + "@babel/helper-plugin-utils": "^7.29.7" 1132 + }, 1133 + "engines": { 1134 + "node": ">=6.9.0" 1135 + }, 1136 + "peerDependencies": { 1137 + "@babel/core": "^7.0.0-0" 1138 + } 1139 + }, 1140 + "node_modules/@babel/plugin-transform-object-rest-spread": { 1141 + "version": "7.29.7", 1142 + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-object-rest-spread/-/plugin-transform-object-rest-spread-7.29.7.tgz", 1143 + "integrity": "sha512-Ld98jn4c0smUywL57m7SgsHq3OpThOa6LqZJif3G6jYOovPleoFhVrBJ1WegRApSFB2wu4+RelAj9AC9G08Z4A==", 1144 + "dev": true, 1145 + "license": "MIT", 1146 + "dependencies": { 1147 + "@babel/helper-compilation-targets": "^7.29.7", 1148 + "@babel/helper-plugin-utils": "^7.29.7", 1149 + "@babel/plugin-transform-destructuring": "^7.29.7", 1150 + "@babel/plugin-transform-parameters": "^7.29.7", 1151 + "@babel/traverse": "^7.29.7" 1152 + }, 1153 + "engines": { 1154 + "node": ">=6.9.0" 1155 + }, 1156 + "peerDependencies": { 1157 + "@babel/core": "^7.0.0-0" 1158 + } 1159 + }, 1160 + "node_modules/@babel/plugin-transform-object-super": { 1161 + "version": "7.29.7", 1162 + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-object-super/-/plugin-transform-object-super-7.29.7.tgz", 1163 + "integrity": "sha512-Ea/diGcw0twB5IlZPO5sgET6fJsLJqPABqTuFWIR+iMPGPZJkATEIWx0wa+aEQ5UY1CBQyP/gkAiLEqn1vBiQA==", 1164 + "dev": true, 1165 + "license": "MIT", 1166 + "dependencies": { 1167 + "@babel/helper-plugin-utils": "^7.29.7", 1168 + "@babel/helper-replace-supers": "^7.29.7" 1169 + }, 1170 + "engines": { 1171 + "node": ">=6.9.0" 1172 + }, 1173 + "peerDependencies": { 1174 + "@babel/core": "^7.0.0-0" 1175 + } 1176 + }, 1177 + "node_modules/@babel/plugin-transform-optional-catch-binding": { 1178 + "version": "7.29.7", 1179 + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-optional-catch-binding/-/plugin-transform-optional-catch-binding-7.29.7.tgz", 1180 + "integrity": "sha512-sLsyndxK2VwX6yNUOakMb7Sh553ZTe/vVM1XJ+9Z5aW1ytsc8xOIwmyk05NNjN60vkc5/KqoTH6hB4V41LJhng==", 1181 + "dev": true, 1182 + "license": "MIT", 1183 + "dependencies": { 1184 + "@babel/helper-plugin-utils": "^7.29.7" 1185 + }, 1186 + "engines": { 1187 + "node": ">=6.9.0" 1188 + }, 1189 + "peerDependencies": { 1190 + "@babel/core": "^7.0.0-0" 1191 + } 1192 + }, 1193 + "node_modules/@babel/plugin-transform-optional-chaining": { 1194 + "version": "7.29.7", 1195 + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-optional-chaining/-/plugin-transform-optional-chaining-7.29.7.tgz", 1196 + "integrity": "sha512-6GM1dhvK3gNODkXcEcMCOLEDCLSoZ/sBbro2Ax8HURyasQ4NshagQixkRFdh5niI6E4gmA/jYI/4aT7rRos3ZQ==", 1197 + "dev": true, 1198 + "license": "MIT", 1199 + "dependencies": { 1200 + "@babel/helper-plugin-utils": "^7.29.7", 1201 + "@babel/helper-skip-transparent-expression-wrappers": "^7.29.7" 1202 + }, 1203 + "engines": { 1204 + "node": ">=6.9.0" 1205 + }, 1206 + "peerDependencies": { 1207 + "@babel/core": "^7.0.0-0" 1208 + } 1209 + }, 1210 + "node_modules/@babel/plugin-transform-parameters": { 1211 + "version": "7.29.7", 1212 + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-parameters/-/plugin-transform-parameters-7.29.7.tgz", 1213 + "integrity": "sha512-ZDOBqV/qLYJI0YElr8DcENEyARsFQeESqWXH6gZlghYXuPPjvweuDhP4VyEi4BlUBlLRFZVjxoZDMjxhLW766g==", 1214 + "dev": true, 1215 + "license": "MIT", 1216 + "dependencies": { 1217 + "@babel/helper-plugin-utils": "^7.29.7" 1218 + }, 1219 + "engines": { 1220 + "node": ">=6.9.0" 1221 + }, 1222 + "peerDependencies": { 1223 + "@babel/core": "^7.0.0-0" 1224 + } 1225 + }, 1226 + "node_modules/@babel/plugin-transform-private-methods": { 1227 + "version": "7.29.7", 1228 + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-private-methods/-/plugin-transform-private-methods-7.29.7.tgz", 1229 + "integrity": "sha512-/6Rz4DK1ETDEM/bWHsPHcaEe7ZaT1EqSXjtSP/L0DijOYuaUhiRiOKcwpZ8P7zR4xXEHc2ITdiCgBm9Tpyv9ug==", 1230 + "dev": true, 1231 + "license": "MIT", 1232 + "dependencies": { 1233 + "@babel/helper-create-class-features-plugin": "^7.29.7", 1234 + "@babel/helper-plugin-utils": "^7.29.7" 1235 + }, 1236 + "engines": { 1237 + "node": ">=6.9.0" 1238 + }, 1239 + "peerDependencies": { 1240 + "@babel/core": "^7.0.0-0" 1241 + } 1242 + }, 1243 + "node_modules/@babel/plugin-transform-private-property-in-object": { 1244 + "version": "7.29.7", 1245 + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-private-property-in-object/-/plugin-transform-private-property-in-object-7.29.7.tgz", 1246 + "integrity": "sha512-+BNo06dnrzdNNqCm1X6YUaVv0DKk8Q+JYcoZfOkLhYWNCXzlwTSRq8zGWayT1csjcpNXV9CQTBRRbmTLZac5cA==", 1247 + "dev": true, 1248 + "license": "MIT", 1249 + "dependencies": { 1250 + "@babel/helper-annotate-as-pure": "^7.29.7", 1251 + "@babel/helper-create-class-features-plugin": "^7.29.7", 1252 + "@babel/helper-plugin-utils": "^7.29.7" 1253 + }, 1254 + "engines": { 1255 + "node": ">=6.9.0" 1256 + }, 1257 + "peerDependencies": { 1258 + "@babel/core": "^7.0.0-0" 1259 + } 1260 + }, 1261 + "node_modules/@babel/plugin-transform-property-literals": { 1262 + "version": "7.29.7", 1263 + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-property-literals/-/plugin-transform-property-literals-7.29.7.tgz", 1264 + "integrity": "sha512-bOMRLQuI0A5ZqHq3OWJ89/rXpJ/NJrbVhXiP4zwPGMs6kpcVsuTUNjwoE30K0Qm3mf48a/TnRYYD6vPNqcg6jA==", 1265 + "dev": true, 1266 + "license": "MIT", 1267 + "dependencies": { 1268 + "@babel/helper-plugin-utils": "^7.29.7" 1269 + }, 1270 + "engines": { 1271 + "node": ">=6.9.0" 1272 + }, 1273 + "peerDependencies": { 1274 + "@babel/core": "^7.0.0-0" 1275 + } 1276 + }, 1277 + "node_modules/@babel/plugin-transform-regenerator": { 1278 + "version": "7.29.7", 1279 + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-regenerator/-/plugin-transform-regenerator-7.29.7.tgz", 1280 + "integrity": "sha512-rNNFV0DBAJp988xW2DOntfDoYn1eR8GGF5AT5vYc+rjyfaQkM242c9tZUHHPe7KYaiJizXPWhQTzzdbXySyhBw==", 1281 + "dev": true, 1282 + "license": "MIT", 1283 + "dependencies": { 1284 + "@babel/helper-plugin-utils": "^7.29.7" 1285 + }, 1286 + "engines": { 1287 + "node": ">=6.9.0" 1288 + }, 1289 + "peerDependencies": { 1290 + "@babel/core": "^7.0.0-0" 1291 + } 1292 + }, 1293 + "node_modules/@babel/plugin-transform-regexp-modifiers": { 1294 + "version": "7.29.7", 1295 + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-regexp-modifiers/-/plugin-transform-regexp-modifiers-7.29.7.tgz", 1296 + "integrity": "sha512-mB5Fs0VWrJ42ZCmc8114v60qetdaUVNkj9PmSZRmanCZM3S9hm0CFRLjRmYIsuXav14l2jvZ+4T8iiCGnhj3nQ==", 1297 + "dev": true, 1298 + "license": "MIT", 1299 + "dependencies": { 1300 + "@babel/helper-create-regexp-features-plugin": "^7.29.7", 1301 + "@babel/helper-plugin-utils": "^7.29.7" 1302 + }, 1303 + "engines": { 1304 + "node": ">=6.9.0" 1305 + }, 1306 + "peerDependencies": { 1307 + "@babel/core": "^7.0.0" 1308 + } 1309 + }, 1310 + "node_modules/@babel/plugin-transform-reserved-words": { 1311 + "version": "7.29.7", 1312 + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-reserved-words/-/plugin-transform-reserved-words-7.29.7.tgz", 1313 + "integrity": "sha512-5+YhdpVgmfSmwZyLMftfaiffLRMHjzIRHFHHLdibcSyJm2pasMrKHrO3Ptrt2DRshjvpgjEJJ1zVW14WPq/6QA==", 1314 + "dev": true, 1315 + "license": "MIT", 1316 + "dependencies": { 1317 + "@babel/helper-plugin-utils": "^7.29.7" 1318 + }, 1319 + "engines": { 1320 + "node": ">=6.9.0" 1321 + }, 1322 + "peerDependencies": { 1323 + "@babel/core": "^7.0.0-0" 1324 + } 1325 + }, 1326 + "node_modules/@babel/plugin-transform-shorthand-properties": { 1327 + "version": "7.29.7", 1328 + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-shorthand-properties/-/plugin-transform-shorthand-properties-7.29.7.tgz", 1329 + "integrity": "sha512-I+WYbGBAiCn7nA6xBrlgPH+MB7HWb4u8pv5S0Pv7OtwNvIFvCCb24YlttKEeUFVurfBCEaOTnuhlqsb7f0Z5Dg==", 1330 + "dev": true, 1331 + "license": "MIT", 1332 + "dependencies": { 1333 + "@babel/helper-plugin-utils": "^7.29.7" 1334 + }, 1335 + "engines": { 1336 + "node": ">=6.9.0" 1337 + }, 1338 + "peerDependencies": { 1339 + "@babel/core": "^7.0.0-0" 1340 + } 1341 + }, 1342 + "node_modules/@babel/plugin-transform-spread": { 1343 + "version": "7.29.7", 1344 + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-spread/-/plugin-transform-spread-7.29.7.tgz", 1345 + "integrity": "sha512-/u5K1QWada7tbYNqTjMh96718g9NTwh9tfPJMsSmVsQwGT447FskV+KcfeXkXq2GWki4EM/MuTdmBec+hOuVTQ==", 1346 + "dev": true, 1347 + "license": "MIT", 1348 + "dependencies": { 1349 + "@babel/helper-plugin-utils": "^7.29.7", 1350 + "@babel/helper-skip-transparent-expression-wrappers": "^7.29.7" 1351 + }, 1352 + "engines": { 1353 + "node": ">=6.9.0" 1354 + }, 1355 + "peerDependencies": { 1356 + "@babel/core": "^7.0.0-0" 1357 + } 1358 + }, 1359 + "node_modules/@babel/plugin-transform-sticky-regex": { 1360 + "version": "7.29.7", 1361 + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-sticky-regex/-/plugin-transform-sticky-regex-7.29.7.tgz", 1362 + "integrity": "sha512-BCHzNYJGe9l7EpwwDBN/ztlL2NYFFq8hp9ddjtUEM9f2O7S7kKV/lL6Fwo7IF7NSkYhPK2vO+86nIGltA90MsA==", 1363 + "dev": true, 1364 + "license": "MIT", 1365 + "dependencies": { 1366 + "@babel/helper-plugin-utils": "^7.29.7" 1367 + }, 1368 + "engines": { 1369 + "node": ">=6.9.0" 1370 + }, 1371 + "peerDependencies": { 1372 + "@babel/core": "^7.0.0-0" 1373 + } 1374 + }, 1375 + "node_modules/@babel/plugin-transform-template-literals": { 1376 + "version": "7.29.7", 1377 + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-template-literals/-/plugin-transform-template-literals-7.29.7.tgz", 1378 + "integrity": "sha512-NCSEJ4sLFU2gqAub45HYh4fus2yQ36rr6ei6vpU7NdoJqCpxvEG8E6eJpscGyXP3VHD2Ny+fSXr04k1hoUrFqA==", 1379 + "dev": true, 1380 + "license": "MIT", 1381 + "dependencies": { 1382 + "@babel/helper-plugin-utils": "^7.29.7" 1383 + }, 1384 + "engines": { 1385 + "node": ">=6.9.0" 1386 + }, 1387 + "peerDependencies": { 1388 + "@babel/core": "^7.0.0-0" 1389 + } 1390 + }, 1391 + "node_modules/@babel/plugin-transform-typeof-symbol": { 1392 + "version": "7.29.7", 1393 + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-typeof-symbol/-/plugin-transform-typeof-symbol-7.29.7.tgz", 1394 + "integrity": "sha512-223mNGoTkBiTEWFoK+Q6Go3tueMRclO8vxxxxquNCYuNI4jWOofFKJRRDu6SDrB8Sgo1UEGW9T4GAQ8ZyRso1A==", 1395 + "dev": true, 1396 + "license": "MIT", 1397 + "dependencies": { 1398 + "@babel/helper-plugin-utils": "^7.29.7" 1399 + }, 1400 + "engines": { 1401 + "node": ">=6.9.0" 1402 + }, 1403 + "peerDependencies": { 1404 + "@babel/core": "^7.0.0-0" 1405 + } 1406 + }, 1407 + "node_modules/@babel/plugin-transform-unicode-escapes": { 1408 + "version": "7.29.7", 1409 + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-unicode-escapes/-/plugin-transform-unicode-escapes-7.29.7.tgz", 1410 + "integrity": "sha512-jCfXxSjf94lf4E0hKE0AByxF6F3/pVFqRdUUNkDJhsY0m1ZKjnN6ZYyMeHNpzflxb/0q5b7t3p+BE+SLF1WOtA==", 1411 + "dev": true, 1412 + "license": "MIT", 1413 + "dependencies": { 1414 + "@babel/helper-plugin-utils": "^7.29.7" 1415 + }, 1416 + "engines": { 1417 + "node": ">=6.9.0" 1418 + }, 1419 + "peerDependencies": { 1420 + "@babel/core": "^7.0.0-0" 1421 + } 1422 + }, 1423 + "node_modules/@babel/plugin-transform-unicode-property-regex": { 1424 + "version": "7.29.7", 1425 + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-unicode-property-regex/-/plugin-transform-unicode-property-regex-7.29.7.tgz", 1426 + "integrity": "sha512-OgZ+zoAJgZLUCunsTRQ5LAjOywDv5zzZ2/hQ5aMw1pGXyY2rtE8/chXYUmu3AlVHKpm10KEdG9aMwbI/K76ZGw==", 1427 + "dev": true, 1428 + "license": "MIT", 1429 + "dependencies": { 1430 + "@babel/helper-create-regexp-features-plugin": "^7.29.7", 1431 + "@babel/helper-plugin-utils": "^7.29.7" 1432 + }, 1433 + "engines": { 1434 + "node": ">=6.9.0" 1435 + }, 1436 + "peerDependencies": { 1437 + "@babel/core": "^7.0.0-0" 1438 + } 1439 + }, 1440 + "node_modules/@babel/plugin-transform-unicode-regex": { 1441 + "version": "7.29.7", 1442 + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-unicode-regex/-/plugin-transform-unicode-regex-7.29.7.tgz", 1443 + "integrity": "sha512-7D/x/23/d/3VqZ0QA+LGbZMlGwZjztBygSWWWsfTPoQ1oQ6Q1P6Mr3d0kk42XabyUVw+fha3LqdRsFqeKqvCyA==", 1444 + "dev": true, 1445 + "license": "MIT", 1446 + "dependencies": { 1447 + "@babel/helper-create-regexp-features-plugin": "^7.29.7", 1448 + "@babel/helper-plugin-utils": "^7.29.7" 1449 + }, 1450 + "engines": { 1451 + "node": ">=6.9.0" 1452 + }, 1453 + "peerDependencies": { 1454 + "@babel/core": "^7.0.0-0" 1455 + } 1456 + }, 1457 + "node_modules/@babel/plugin-transform-unicode-sets-regex": { 1458 + "version": "7.29.7", 1459 + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-unicode-sets-regex/-/plugin-transform-unicode-sets-regex-7.29.7.tgz", 1460 + "integrity": "sha512-BLOhLht9DOJwIxlmp91wHvkXv1lguuHS3/FwUO8HL1H0u8s4hR1gASVFyilu9iGtcTRYqjTZmlsFFeQletntEg==", 1461 + "dev": true, 1462 + "license": "MIT", 1463 + "dependencies": { 1464 + "@babel/helper-create-regexp-features-plugin": "^7.29.7", 1465 + "@babel/helper-plugin-utils": "^7.29.7" 1466 + }, 1467 + "engines": { 1468 + "node": ">=6.9.0" 1469 + }, 1470 + "peerDependencies": { 1471 + "@babel/core": "^7.0.0" 1472 + } 1473 + }, 1474 + "node_modules/@babel/preset-env": { 1475 + "version": "7.29.7", 1476 + "resolved": "https://registry.npmjs.org/@babel/preset-env/-/preset-env-7.29.7.tgz", 1477 + "integrity": "sha512-GYzX36n1nsciIb0uyH0GHwxwtNwPQIcpxSeiVLDtG/B7jB5xXgchnmL1f/jCX5o+pwnaDBtO60ONSJhEBJfxYA==", 1478 + "dev": true, 1479 + "license": "MIT", 1480 + "dependencies": { 1481 + "@babel/compat-data": "^7.29.7", 1482 + "@babel/helper-compilation-targets": "^7.29.7", 1483 + "@babel/helper-plugin-utils": "^7.29.7", 1484 + "@babel/helper-validator-option": "^7.29.7", 1485 + "@babel/plugin-bugfix-firefox-class-in-computed-class-key": "^7.29.7", 1486 + "@babel/plugin-bugfix-safari-class-field-initializer-scope": "^7.29.7", 1487 + "@babel/plugin-bugfix-safari-id-destructuring-collision-in-function-expression": "^7.29.7", 1488 + "@babel/plugin-bugfix-safari-rest-destructuring-rhs-array": "^7.29.7", 1489 + "@babel/plugin-bugfix-v8-spread-parameters-in-optional-chaining": "^7.29.7", 1490 + "@babel/plugin-bugfix-v8-static-class-fields-redefine-readonly": "^7.29.7", 1491 + "@babel/plugin-proposal-private-property-in-object": "7.21.0-placeholder-for-preset-env.2", 1492 + "@babel/plugin-syntax-import-assertions": "^7.29.7", 1493 + "@babel/plugin-syntax-import-attributes": "^7.29.7", 1494 + "@babel/plugin-syntax-unicode-sets-regex": "^7.18.6", 1495 + "@babel/plugin-transform-arrow-functions": "^7.29.7", 1496 + "@babel/plugin-transform-async-generator-functions": "^7.29.7", 1497 + "@babel/plugin-transform-async-to-generator": "^7.29.7", 1498 + "@babel/plugin-transform-block-scoped-functions": "^7.29.7", 1499 + "@babel/plugin-transform-block-scoping": "^7.29.7", 1500 + "@babel/plugin-transform-class-properties": "^7.29.7", 1501 + "@babel/plugin-transform-class-static-block": "^7.29.7", 1502 + "@babel/plugin-transform-classes": "^7.29.7", 1503 + "@babel/plugin-transform-computed-properties": "^7.29.7", 1504 + "@babel/plugin-transform-destructuring": "^7.29.7", 1505 + "@babel/plugin-transform-dotall-regex": "^7.29.7", 1506 + "@babel/plugin-transform-duplicate-keys": "^7.29.7", 1507 + "@babel/plugin-transform-duplicate-named-capturing-groups-regex": "^7.29.7", 1508 + "@babel/plugin-transform-dynamic-import": "^7.29.7", 1509 + "@babel/plugin-transform-explicit-resource-management": "^7.29.7", 1510 + "@babel/plugin-transform-exponentiation-operator": "^7.29.7", 1511 + "@babel/plugin-transform-export-namespace-from": "^7.29.7", 1512 + "@babel/plugin-transform-for-of": "^7.29.7", 1513 + "@babel/plugin-transform-function-name": "^7.29.7", 1514 + "@babel/plugin-transform-json-strings": "^7.29.7", 1515 + "@babel/plugin-transform-literals": "^7.29.7", 1516 + "@babel/plugin-transform-logical-assignment-operators": "^7.29.7", 1517 + "@babel/plugin-transform-member-expression-literals": "^7.29.7", 1518 + "@babel/plugin-transform-modules-amd": "^7.29.7", 1519 + "@babel/plugin-transform-modules-commonjs": "^7.29.7", 1520 + "@babel/plugin-transform-modules-systemjs": "^7.29.7", 1521 + "@babel/plugin-transform-modules-umd": "^7.29.7", 1522 + "@babel/plugin-transform-named-capturing-groups-regex": "^7.29.7", 1523 + "@babel/plugin-transform-new-target": "^7.29.7", 1524 + "@babel/plugin-transform-nullish-coalescing-operator": "^7.29.7", 1525 + "@babel/plugin-transform-numeric-separator": "^7.29.7", 1526 + "@babel/plugin-transform-object-rest-spread": "^7.29.7", 1527 + "@babel/plugin-transform-object-super": "^7.29.7", 1528 + "@babel/plugin-transform-optional-catch-binding": "^7.29.7", 1529 + "@babel/plugin-transform-optional-chaining": "^7.29.7", 1530 + "@babel/plugin-transform-parameters": "^7.29.7", 1531 + "@babel/plugin-transform-private-methods": "^7.29.7", 1532 + "@babel/plugin-transform-private-property-in-object": "^7.29.7", 1533 + "@babel/plugin-transform-property-literals": "^7.29.7", 1534 + "@babel/plugin-transform-regenerator": "^7.29.7", 1535 + "@babel/plugin-transform-regexp-modifiers": "^7.29.7", 1536 + "@babel/plugin-transform-reserved-words": "^7.29.7", 1537 + "@babel/plugin-transform-shorthand-properties": "^7.29.7", 1538 + "@babel/plugin-transform-spread": "^7.29.7", 1539 + "@babel/plugin-transform-sticky-regex": "^7.29.7", 1540 + "@babel/plugin-transform-template-literals": "^7.29.7", 1541 + "@babel/plugin-transform-typeof-symbol": "^7.29.7", 1542 + "@babel/plugin-transform-unicode-escapes": "^7.29.7", 1543 + "@babel/plugin-transform-unicode-property-regex": "^7.29.7", 1544 + "@babel/plugin-transform-unicode-regex": "^7.29.7", 1545 + "@babel/plugin-transform-unicode-sets-regex": "^7.29.7", 1546 + "@babel/preset-modules": "0.1.6-no-external-plugins", 1547 + "babel-plugin-polyfill-corejs2": "^0.4.15", 1548 + "babel-plugin-polyfill-corejs3": "^0.14.0", 1549 + "babel-plugin-polyfill-regenerator": "^0.6.6", 1550 + "core-js-compat": "^3.48.0", 1551 + "semver": "^6.3.1" 1552 + }, 1553 + "engines": { 1554 + "node": ">=6.9.0" 1555 + }, 1556 + "peerDependencies": { 1557 + "@babel/core": "^7.0.0-0" 1558 + } 1559 + }, 1560 + "node_modules/@babel/preset-env/node_modules/semver": { 1561 + "version": "6.3.1", 1562 + "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.1.tgz", 1563 + "integrity": "sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA==", 1564 + "dev": true, 1565 + "license": "ISC", 1566 + "bin": { 1567 + "semver": "bin/semver.js" 1568 + } 1569 + }, 1570 + "node_modules/@babel/preset-modules": { 1571 + "version": "0.1.6-no-external-plugins", 1572 + "resolved": "https://registry.npmjs.org/@babel/preset-modules/-/preset-modules-0.1.6-no-external-plugins.tgz", 1573 + "integrity": "sha512-HrcgcIESLm9aIR842yhJ5RWan/gebQUJ6E/E5+rf0y9o6oj7w0Br+sWuL6kEQ/o/AdfvR1Je9jG18/gnpwjEyA==", 1574 + "dev": true, 1575 + "license": "MIT", 1576 + "dependencies": { 1577 + "@babel/helper-plugin-utils": "^7.0.0", 1578 + "@babel/types": "^7.4.4", 1579 + "esutils": "^2.0.2" 1580 + }, 1581 + "peerDependencies": { 1582 + "@babel/core": "^7.0.0-0 || ^8.0.0-0 <8.0.0" 1583 + } 1584 + }, 1585 + "node_modules/@babel/runtime": { 1586 + "version": "7.29.7", 1587 + "resolved": "https://registry.npmjs.org/@babel/runtime/-/runtime-7.29.7.tgz", 1588 + "integrity": "sha512-Nq8OhGWiZIZGV6hLHoyAKLLcJihP/xFeBMGJoUrxTX2psI8dCifzLhZISFb+VWS3wFMRDmCGw5R+dOySCqPLhw==", 1589 + "dev": true, 1590 + "license": "MIT", 1591 + "engines": { 1592 + "node": ">=6.9.0" 1593 + } 1594 + }, 1595 + "node_modules/@babel/template": { 1596 + "version": "7.29.7", 1597 + "resolved": "https://registry.npmjs.org/@babel/template/-/template-7.29.7.tgz", 1598 + "integrity": "sha512-puq+Gf35oI24FeN11LkoUQFqv9uwNeWpxXZi/Ji3rRIoKAzKnxRaZ+Gkj0vKS9ZCiTESfng1N9LyOyXvo+m+Gg==", 1599 + "dev": true, 1600 + "license": "MIT", 1601 + "dependencies": { 1602 + "@babel/code-frame": "^7.29.7", 1603 + "@babel/parser": "^7.29.7", 1604 + "@babel/types": "^7.29.7" 1605 + }, 1606 + "engines": { 1607 + "node": ">=6.9.0" 1608 + } 1609 + }, 1610 + "node_modules/@babel/traverse": { 1611 + "version": "7.29.7", 1612 + "resolved": "https://registry.npmjs.org/@babel/traverse/-/traverse-7.29.7.tgz", 1613 + "integrity": "sha512-EhlfNQtZ+NK22w5BM61ciuiq1m58ed33Wr1Xan//ZRTy6hgjnwyCffRYwzsGXdASJSUJ1guZILsErh1eQcl+zw==", 1614 + "dev": true, 1615 + "license": "MIT", 1616 + "dependencies": { 1617 + "@babel/code-frame": "^7.29.7", 1618 + "@babel/generator": "^7.29.7", 1619 + "@babel/helper-globals": "^7.29.7", 1620 + "@babel/parser": "^7.29.7", 1621 + "@babel/template": "^7.29.7", 1622 + "@babel/types": "^7.29.7", 1623 + "debug": "^4.3.1" 1624 + }, 1625 + "engines": { 1626 + "node": ">=6.9.0" 1627 + } 1628 + }, 1629 + "node_modules/@babel/types": { 1630 + "version": "7.29.7", 1631 + "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.29.7.tgz", 1632 + "integrity": "sha512-4zBIxpPzowiZpusoFkyGVwakdRJUyuH5PxQ/PrqghfdFWWasvnCdPfQXHrenDai+gyLARulZjZowCOj6fjT4pA==", 1633 + "dev": true, 1634 + "license": "MIT", 1635 + "dependencies": { 1636 + "@babel/helper-string-parser": "^7.29.7", 1637 + "@babel/helper-validator-identifier": "^7.29.7" 1638 + }, 1639 + "engines": { 1640 + "node": ">=6.9.0" 1641 + } 1642 + }, 1643 + "node_modules/@cloudflare/kv-asset-handler": { 1644 + "version": "0.5.0", 1645 + "resolved": "https://registry.npmjs.org/@cloudflare/kv-asset-handler/-/kv-asset-handler-0.5.0.tgz", 1646 + "integrity": "sha512-jxQYkj8dSIzc0cD6cMMNdOc1UVjqSqu8BZdor5s8cGjW2I8BjODt/kWPVdY+u9zj3ms75Q5qaZgnxUad83+eAg==", 1647 + "dev": true, 1648 + "license": "MIT OR Apache-2.0", 1649 + "engines": { 1650 + "node": ">=22.0.0" 1651 + } 1652 + }, 1653 + "node_modules/@cloudflare/unenv-preset": { 1654 + "version": "2.16.1", 1655 + "resolved": "https://registry.npmjs.org/@cloudflare/unenv-preset/-/unenv-preset-2.16.1.tgz", 1656 + "integrity": "sha512-ECxObrMfyTl5bhQf/lZCXwo5G6xX9IAUo+nDMKK4SZ8m4Jvvxp52vilxyySSWh2YTZz8+HQ07qGH/2rEom1vDw==", 1657 + "dev": true, 1658 + "license": "MIT OR Apache-2.0", 1659 + "peerDependencies": { 1660 + "unenv": "2.0.0-rc.24", 1661 + "workerd": ">1.20260305.0 <2.0.0-0" 1662 + }, 1663 + "peerDependenciesMeta": { 1664 + "workerd": { 1665 + "optional": true 1666 + } 1667 + } 1668 + }, 1669 + "node_modules/@cloudflare/vite-plugin": { 1670 + "version": "1.45.1", 1671 + "resolved": "https://registry.npmjs.org/@cloudflare/vite-plugin/-/vite-plugin-1.45.1.tgz", 1672 + "integrity": "sha512-C+iDpO9pVH7IqrjdYtUV+obcTAdpiNk0OSinGEZZyd2ZWyGVjGk7iJ2p3xpMBpZuTa1I4hfAECNp0yN/8f3PIQ==", 1673 + "dev": true, 1674 + "license": "MIT", 1675 + "dependencies": { 1676 + "@cloudflare/unenv-preset": "2.16.1", 1677 + "miniflare": "4.20260714.0", 1678 + "unenv": "2.0.0-rc.24", 1679 + "workerd": "1.20260714.1", 1680 + "wrangler": "4.112.0", 1681 + "ws": "8.21.0" 1682 + }, 1683 + "bin": { 1684 + "cf-vite": "bin/cf-vite" 1685 + }, 1686 + "peerDependencies": { 1687 + "vite": "^6.1.0 || ^7.0.0 || ^8.0.0", 1688 + "wrangler": "^4.112.0" 1689 + } 1690 + }, 1691 + "node_modules/@cloudflare/workerd-darwin-64": { 1692 + "version": "1.20260714.1", 1693 + "resolved": "https://registry.npmjs.org/@cloudflare/workerd-darwin-64/-/workerd-darwin-64-1.20260714.1.tgz", 1694 + "integrity": "sha512-ZWXqAN8G7Cx9hMRQuk+59ziJhR3j1F4iO+Qs8aHdfKZ3Dq5Yi/57xvkJTgCGBnW1YU/L78r8f6HEy51bwbTpNw==", 1695 + "cpu": [ 1696 + "x64" 1697 + ], 1698 + "dev": true, 1699 + "license": "Apache-2.0", 1700 + "optional": true, 1701 + "os": [ 1702 + "darwin" 1703 + ], 1704 + "engines": { 1705 + "node": ">=16" 1706 + } 1707 + }, 1708 + "node_modules/@cloudflare/workerd-darwin-arm64": { 1709 + "version": "1.20260714.1", 1710 + "resolved": "https://registry.npmjs.org/@cloudflare/workerd-darwin-arm64/-/workerd-darwin-arm64-1.20260714.1.tgz", 1711 + "integrity": "sha512-tueWxWC3wyCbMG6zRAxsMXX0YLgrRWbiAPYFQ2uJ7dUH8G+5E7UTWaQS9B1HdJ0bpKFW1NWxhs1o2noKVFSUYg==", 1712 + "cpu": [ 1713 + "arm64" 1714 + ], 1715 + "dev": true, 1716 + "license": "Apache-2.0", 1717 + "optional": true, 1718 + "os": [ 1719 + "darwin" 1720 + ], 1721 + "engines": { 1722 + "node": ">=16" 1723 + } 1724 + }, 1725 + "node_modules/@cloudflare/workerd-linux-64": { 1726 + "version": "1.20260714.1", 1727 + "resolved": "https://registry.npmjs.org/@cloudflare/workerd-linux-64/-/workerd-linux-64-1.20260714.1.tgz", 1728 + "integrity": "sha512-1VChTZRb0l0F7R4e1G5RtLKV4oFi6x+rQgxh2+yu887j3l/3TLgatuv1L8/5zhc9gKEhATTxOh0e52Rtd9dDWQ==", 1729 + "cpu": [ 1730 + "x64" 1731 + ], 1732 + "dev": true, 1733 + "license": "Apache-2.0", 1734 + "optional": true, 1735 + "os": [ 1736 + "linux" 1737 + ], 1738 + "engines": { 1739 + "node": ">=16" 1740 + } 1741 + }, 1742 + "node_modules/@cloudflare/workerd-linux-arm64": { 1743 + "version": "1.20260714.1", 1744 + "resolved": "https://registry.npmjs.org/@cloudflare/workerd-linux-arm64/-/workerd-linux-arm64-1.20260714.1.tgz", 1745 + "integrity": "sha512-rMm3G+NirG2UdgHIRDdF1asNC6FqgIzZzkRG+VDhhDGcVxAQwvrMT1E38BivEvHr3G04MB4AfhcOczX0+GtRkQ==", 1746 + "cpu": [ 1747 + "arm64" 1748 + ], 1749 + "dev": true, 1750 + "license": "Apache-2.0", 1751 + "optional": true, 1752 + "os": [ 1753 + "linux" 1754 + ], 1755 + "engines": { 1756 + "node": ">=16" 1757 + } 1758 + }, 1759 + "node_modules/@cloudflare/workerd-windows-64": { 1760 + "version": "1.20260714.1", 1761 + "resolved": "https://registry.npmjs.org/@cloudflare/workerd-windows-64/-/workerd-windows-64-1.20260714.1.tgz", 1762 + "integrity": "sha512-cGqnU3Hg2YZS/k3SAqrMp1DjpdsyFde72tWltdl6ZT9+SFz/Zrk/8gyTU1TcxC4YApXeNVH5TyU5cOGPgUJ0pg==", 1763 + "cpu": [ 1764 + "x64" 1765 + ], 1766 + "dev": true, 1767 + "license": "Apache-2.0", 1768 + "optional": true, 1769 + "os": [ 1770 + "win32" 1771 + ], 1772 + "engines": { 1773 + "node": ">=16" 1774 + } 1775 + }, 1776 + "node_modules/@cspotcode/source-map-support": { 1777 + "version": "0.8.1", 1778 + "resolved": "https://registry.npmjs.org/@cspotcode/source-map-support/-/source-map-support-0.8.1.tgz", 1779 + "integrity": "sha512-IchNf6dN4tHoMFIn/7OE8LWZ19Y6q/67Bmf6vnGREv8RSbBVb9LPJxEcnwrcwX6ixSvaiGoomAUvu4YSxXrVgw==", 1780 + "dev": true, 1781 + "license": "MIT", 1782 + "dependencies": { 1783 + "@jridgewell/trace-mapping": "0.3.9" 1784 + }, 1785 + "engines": { 1786 + "node": ">=12" 1787 + } 1788 + }, 1789 + "node_modules/@cspotcode/source-map-support/node_modules/@jridgewell/trace-mapping": { 1790 + "version": "0.3.9", 1791 + "resolved": "https://registry.npmjs.org/@jridgewell/trace-mapping/-/trace-mapping-0.3.9.tgz", 1792 + "integrity": "sha512-3Belt6tdc8bPgAtbcmdtNJlirVoTmEb5e2gC94PnkwEW9jI6CAHUeoG85tjWP5WquqfavoMtMwiG4P926ZKKuQ==", 1793 + "dev": true, 1794 + "license": "MIT", 1795 + "dependencies": { 1796 + "@jridgewell/resolve-uri": "^3.0.3", 1797 + "@jridgewell/sourcemap-codec": "^1.4.10" 1798 + } 1799 + }, 1800 + "node_modules/@emnapi/core": { 1801 + "version": "1.11.1", 1802 + "resolved": "https://registry.npmjs.org/@emnapi/core/-/core-1.11.1.tgz", 1803 + "integrity": "sha512-RSvbQmHzdKzNsLYa/wHrbc3KN4sYLKAdPZxqiM2HATqv/SBk2/ENSHpvXGaLOMcsAyz0poEGqkmmKYG3OWiJEQ==", 1804 + "dev": true, 1805 + "license": "MIT", 1806 + "optional": true, 1807 + "dependencies": { 1808 + "@emnapi/wasi-threads": "1.2.2", 1809 + "tslib": "^2.4.0" 1810 + } 1811 + }, 1812 + "node_modules/@emnapi/runtime": { 1813 + "version": "1.11.2", 1814 + "resolved": "https://registry.npmjs.org/@emnapi/runtime/-/runtime-1.11.2.tgz", 1815 + "integrity": "sha512-kyOl3X0DuTiT1h2ft8r2fYO8JYtU9a9Xis/zBSiGArNaagCOWx90N1k2wxp18czFDH+OgcWGb5ZP/XMt3dcyPA==", 1816 + "dev": true, 1817 + "license": "MIT", 1818 + "optional": true, 1819 + "dependencies": { 1820 + "tslib": "^2.4.0" 1821 + } 1822 + }, 1823 + "node_modules/@emnapi/wasi-threads": { 1824 + "version": "1.2.2", 1825 + "resolved": "https://registry.npmjs.org/@emnapi/wasi-threads/-/wasi-threads-1.2.2.tgz", 1826 + "integrity": "sha512-c95qOXkHdydNKhscBTebqEC1CVAZpyqOfVfBzQ1qgzyl3gfeldUjIggDbIZgDKsHLgnsM+igH7TJ/eAasaVuMA==", 1827 + "dev": true, 1828 + "license": "MIT", 1829 + "optional": true, 1830 + "dependencies": { 1831 + "tslib": "^2.4.0" 1832 + } 1833 + }, 1834 + "node_modules/@esbuild/aix-ppc64": { 1835 + "version": "0.28.1", 1836 + "resolved": "https://registry.npmjs.org/@esbuild/aix-ppc64/-/aix-ppc64-0.28.1.tgz", 1837 + "integrity": "sha512-Svl7tq8k/08+p6CXPpRjQ1fKX+1odH/BQbb48fV6fj3CWHhsoIOoY87w1oHXm0qEpkIK3ZfVgp0hed3XBXzXMQ==", 1838 + "cpu": [ 1839 + "ppc64" 1840 + ], 1841 + "dev": true, 1842 + "license": "MIT", 1843 + "optional": true, 1844 + "os": [ 1845 + "aix" 1846 + ], 1847 + "engines": { 1848 + "node": ">=18" 1849 + } 1850 + }, 1851 + "node_modules/@esbuild/android-arm": { 1852 + "version": "0.28.1", 1853 + "resolved": "https://registry.npmjs.org/@esbuild/android-arm/-/android-arm-0.28.1.tgz", 1854 + "integrity": "sha512-0k2F129Xdio1TdJfzJ8sy1Q47vUD2NnwdhiAf7drUN1EBTfPf4hsFCtmMgu/6m8JSzsBrlmVjudMBQqOfG8usQ==", 1855 + "cpu": [ 1856 + "arm" 1857 + ], 1858 + "dev": true, 1859 + "license": "MIT", 1860 + "optional": true, 1861 + "os": [ 1862 + "android" 1863 + ], 1864 + "engines": { 1865 + "node": ">=18" 1866 + } 1867 + }, 1868 + "node_modules/@esbuild/android-arm64": { 1869 + "version": "0.28.1", 1870 + "resolved": "https://registry.npmjs.org/@esbuild/android-arm64/-/android-arm64-0.28.1.tgz", 1871 + "integrity": "sha512-34EGEbCIAgosYz6goLcopX6Mo7NyGv9tfwEM2/7Ce2VcVRk568iSvniGWcUXIy7wEDR1wzolcxcriFVrWYcwBg==", 1872 + "cpu": [ 1873 + "arm64" 1874 + ], 1875 + "dev": true, 1876 + "license": "MIT", 1877 + "optional": true, 1878 + "os": [ 1879 + "android" 1880 + ], 1881 + "engines": { 1882 + "node": ">=18" 1883 + } 1884 + }, 1885 + "node_modules/@esbuild/android-x64": { 1886 + "version": "0.28.1", 1887 + "resolved": "https://registry.npmjs.org/@esbuild/android-x64/-/android-x64-0.28.1.tgz", 1888 + "integrity": "sha512-dbwY7ltSMDWsRatcRpCnES4F+im88OCUgGZjy52shC7GqHRE/cYlxNbB4Z4UpJswpcc4Qxd2oE/ufM0p61IKng==", 1889 + "cpu": [ 1890 + "x64" 1891 + ], 1892 + "dev": true, 1893 + "license": "MIT", 1894 + "optional": true, 1895 + "os": [ 1896 + "android" 1897 + ], 1898 + "engines": { 1899 + "node": ">=18" 1900 + } 1901 + }, 1902 + "node_modules/@esbuild/darwin-arm64": { 1903 + "version": "0.28.1", 1904 + "resolved": "https://registry.npmjs.org/@esbuild/darwin-arm64/-/darwin-arm64-0.28.1.tgz", 1905 + "integrity": "sha512-TZbWkQY7kvTAXbXUT7uVACR5cMHsDiSz9z7ZKAX/RTq/WJEk3QyRr0wZpNhBDX+/0CtdqUIJlOiodQcta6tY3Q==", 1906 + "cpu": [ 1907 + "arm64" 1908 + ], 1909 + "dev": true, 1910 + "license": "MIT", 1911 + "optional": true, 1912 + "os": [ 1913 + "darwin" 1914 + ], 1915 + "engines": { 1916 + "node": ">=18" 1917 + } 1918 + }, 1919 + "node_modules/@esbuild/darwin-x64": { 1920 + "version": "0.28.1", 1921 + "resolved": "https://registry.npmjs.org/@esbuild/darwin-x64/-/darwin-x64-0.28.1.tgz", 1922 + "integrity": "sha512-zfdzgK9ACBNZLI/CyHTOx81SyNbM6YXn7rxSgX97VjyiPl9W1i4Ka4fgKECEoFCKGpvBj5qArWIGgQjOwkgskQ==", 1923 + "cpu": [ 1924 + "x64" 1925 + ], 1926 + "dev": true, 1927 + "license": "MIT", 1928 + "optional": true, 1929 + "os": [ 1930 + "darwin" 1931 + ], 1932 + "engines": { 1933 + "node": ">=18" 1934 + } 1935 + }, 1936 + "node_modules/@esbuild/freebsd-arm64": { 1937 + "version": "0.28.1", 1938 + "resolved": "https://registry.npmjs.org/@esbuild/freebsd-arm64/-/freebsd-arm64-0.28.1.tgz", 1939 + "integrity": "sha512-wG2EA8ENdEI0qhkSZMjfqrdY+ziCYCPMmtZjjIwOmXFjmyzEHn+UUxk5of+SYsjtfs3VpnlC7QLzSI5hY/rOAw==", 1940 + "cpu": [ 1941 + "arm64" 1942 + ], 1943 + "dev": true, 1944 + "license": "MIT", 1945 + "optional": true, 1946 + "os": [ 1947 + "freebsd" 1948 + ], 1949 + "engines": { 1950 + "node": ">=18" 1951 + } 1952 + }, 1953 + "node_modules/@esbuild/freebsd-x64": { 1954 + "version": "0.28.1", 1955 + "resolved": "https://registry.npmjs.org/@esbuild/freebsd-x64/-/freebsd-x64-0.28.1.tgz", 1956 + "integrity": "sha512-i7dZ9vQgnvSCzi/rYCXNgtF/U+eKZNJBzu3eTQbRgHnM7tNSizLOkRFAl3qzVc/Op/u5YkHHa4pf/3DOYHthLQ==", 1957 + "cpu": [ 1958 + "x64" 1959 + ], 1960 + "dev": true, 1961 + "license": "MIT", 1962 + "optional": true, 1963 + "os": [ 1964 + "freebsd" 1965 + ], 1966 + "engines": { 1967 + "node": ">=18" 1968 + } 1969 + }, 1970 + "node_modules/@esbuild/linux-arm": { 1971 + "version": "0.28.1", 1972 + "resolved": "https://registry.npmjs.org/@esbuild/linux-arm/-/linux-arm-0.28.1.tgz", 1973 + "integrity": "sha512-qVXBOHQS+d5Y722GwJzJUtOLlX7km3CraOaGormF1pDtPd2C/l1SHRPgjLunLGe51Sh5YYWKMFDyV4SxgMQYTQ==", 1974 + "cpu": [ 1975 + "arm" 1976 + ], 1977 + "dev": true, 1978 + "license": "MIT", 1979 + "optional": true, 1980 + "os": [ 1981 + "linux" 1982 + ], 1983 + "engines": { 1984 + "node": ">=18" 1985 + } 1986 + }, 1987 + "node_modules/@esbuild/linux-arm64": { 1988 + "version": "0.28.1", 1989 + "resolved": "https://registry.npmjs.org/@esbuild/linux-arm64/-/linux-arm64-0.28.1.tgz", 1990 + "integrity": "sha512-yHs+0uc8+nvEAfAfxrWQKK5peSNzBc4PegcMO0EJ2hT71uA7vB8Ihg2e77R2P7SG5uYjPbHlLLmve4LLLRCf0g==", 1991 + "cpu": [ 1992 + "arm64" 1993 + ], 1994 + "dev": true, 1995 + "license": "MIT", 1996 + "optional": true, 1997 + "os": [ 1998 + "linux" 1999 + ], 2000 + "engines": { 2001 + "node": ">=18" 2002 + } 2003 + }, 2004 + "node_modules/@esbuild/linux-ia32": { 2005 + "version": "0.28.1", 2006 + "resolved": "https://registry.npmjs.org/@esbuild/linux-ia32/-/linux-ia32-0.28.1.tgz", 2007 + "integrity": "sha512-d1z4ZuP0ajrfz/FhGT4vv278rX8KnPPJx8i5+AtK7TYbx9Le9F1hyzurZpkEyjkGa9dUGhQow4C1NmeGvqxN2w==", 2008 + "cpu": [ 2009 + "ia32" 2010 + ], 2011 + "dev": true, 2012 + "license": "MIT", 2013 + "optional": true, 2014 + "os": [ 2015 + "linux" 2016 + ], 2017 + "engines": { 2018 + "node": ">=18" 2019 + } 2020 + }, 2021 + "node_modules/@esbuild/linux-loong64": { 2022 + "version": "0.28.1", 2023 + "resolved": "https://registry.npmjs.org/@esbuild/linux-loong64/-/linux-loong64-0.28.1.tgz", 2024 + "integrity": "sha512-M5sRjUVZrkm1OAPR3dlOYzNmN+loZKGVi1VUQGrwuqLcbR6qeAz+famMhjASeH3YVKvZz+zT1jlh/keC3Rj/lg==", 2025 + "cpu": [ 2026 + "loong64" 2027 + ], 2028 + "dev": true, 2029 + "license": "MIT", 2030 + "optional": true, 2031 + "os": [ 2032 + "linux" 2033 + ], 2034 + "engines": { 2035 + "node": ">=18" 2036 + } 2037 + }, 2038 + "node_modules/@esbuild/linux-mips64el": { 2039 + "version": "0.28.1", 2040 + "resolved": "https://registry.npmjs.org/@esbuild/linux-mips64el/-/linux-mips64el-0.28.1.tgz", 2041 + "integrity": "sha512-mRObBZeHh2OxcBFPWE/FjylkRgZdYuiTR3vaTozquCGOH14iP9oN4x4Ge81CoIDYQrXmIxpFumJBu5MtZpnQJQ==", 2042 + "cpu": [ 2043 + "mips64el" 2044 + ], 2045 + "dev": true, 2046 + "license": "MIT", 2047 + "optional": true, 2048 + "os": [ 2049 + "linux" 2050 + ], 2051 + "engines": { 2052 + "node": ">=18" 2053 + } 2054 + }, 2055 + "node_modules/@esbuild/linux-ppc64": { 2056 + "version": "0.28.1", 2057 + "resolved": "https://registry.npmjs.org/@esbuild/linux-ppc64/-/linux-ppc64-0.28.1.tgz", 2058 + "integrity": "sha512-slScBsMAb3GFDcdrCgLwZtPYRoH2H/youv10QiZyRjmsP48fznoveWytSgCI/R0ZcUgpc0ZhIUEx6LHts8yrfQ==", 2059 + "cpu": [ 2060 + "ppc64" 2061 + ], 2062 + "dev": true, 2063 + "license": "MIT", 2064 + "optional": true, 2065 + "os": [ 2066 + "linux" 2067 + ], 2068 + "engines": { 2069 + "node": ">=18" 2070 + } 2071 + }, 2072 + "node_modules/@esbuild/linux-riscv64": { 2073 + "version": "0.28.1", 2074 + "resolved": "https://registry.npmjs.org/@esbuild/linux-riscv64/-/linux-riscv64-0.28.1.tgz", 2075 + "integrity": "sha512-kw0owk1o0GFETUJyW0jc0G4Yzs0BHZn0JDZ8JRT088vjJYX777BAs1fDGxAC+q831qOs2DTC96mNsG2opdfyyQ==", 2076 + "cpu": [ 2077 + "riscv64" 2078 + ], 2079 + "dev": true, 2080 + "license": "MIT", 2081 + "optional": true, 2082 + "os": [ 2083 + "linux" 2084 + ], 2085 + "engines": { 2086 + "node": ">=18" 2087 + } 2088 + }, 2089 + "node_modules/@esbuild/linux-s390x": { 2090 + "version": "0.28.1", 2091 + "resolved": "https://registry.npmjs.org/@esbuild/linux-s390x/-/linux-s390x-0.28.1.tgz", 2092 + "integrity": "sha512-/lAIjX8aYFRByhh6L5rYtPEDRqa9de/4V/juOXcta5frjvzXO4/sqEtyytse0g3zZFuWu5cDN0MkLz2qRDD2Ag==", 2093 + "cpu": [ 2094 + "s390x" 2095 + ], 2096 + "dev": true, 2097 + "license": "MIT", 2098 + "optional": true, 2099 + "os": [ 2100 + "linux" 2101 + ], 2102 + "engines": { 2103 + "node": ">=18" 2104 + } 2105 + }, 2106 + "node_modules/@esbuild/linux-x64": { 2107 + "version": "0.28.1", 2108 + "resolved": "https://registry.npmjs.org/@esbuild/linux-x64/-/linux-x64-0.28.1.tgz", 2109 + "integrity": "sha512-u/anNYF2mmVOEDwLtnQ1wOr3EZ9sTNGLWrsYGYwHWzGA3Si84IOkHXlbWTD1NB+9/1lcnweYKO54uhxZydNzfA==", 2110 + "cpu": [ 2111 + "x64" 2112 + ], 2113 + "dev": true, 2114 + "license": "MIT", 2115 + "optional": true, 2116 + "os": [ 2117 + "linux" 2118 + ], 2119 + "engines": { 2120 + "node": ">=18" 2121 + } 2122 + }, 2123 + "node_modules/@esbuild/netbsd-arm64": { 2124 + "version": "0.28.1", 2125 + "resolved": "https://registry.npmjs.org/@esbuild/netbsd-arm64/-/netbsd-arm64-0.28.1.tgz", 2126 + "integrity": "sha512-oks0DYbLwWMmaakTsCb+zL4E+aHRVLom9IJZOAthMQEPiQmydXHkziYEsGYRx0uNV/IjEKGAV941JzH02pflqw==", 2127 + "cpu": [ 2128 + "arm64" 2129 + ], 2130 + "dev": true, 2131 + "license": "MIT", 2132 + "optional": true, 2133 + "os": [ 2134 + "netbsd" 2135 + ], 2136 + "engines": { 2137 + "node": ">=18" 2138 + } 2139 + }, 2140 + "node_modules/@esbuild/netbsd-x64": { 2141 + "version": "0.28.1", 2142 + "resolved": "https://registry.npmjs.org/@esbuild/netbsd-x64/-/netbsd-x64-0.28.1.tgz", 2143 + "integrity": "sha512-aeL6lAnN89Hz43Mlh1G8ARasbuoYvSITDEx0tHh5b7jJnHcssqgjy9Yx430GDpmCa6OyrKoS0aNRjKundRizGg==", 2144 + "cpu": [ 2145 + "x64" 2146 + ], 2147 + "dev": true, 2148 + "license": "MIT", 2149 + "optional": true, 2150 + "os": [ 2151 + "netbsd" 2152 + ], 2153 + "engines": { 2154 + "node": ">=18" 2155 + } 2156 + }, 2157 + "node_modules/@esbuild/openbsd-arm64": { 2158 + "version": "0.28.1", 2159 + "resolved": "https://registry.npmjs.org/@esbuild/openbsd-arm64/-/openbsd-arm64-0.28.1.tgz", 2160 + "integrity": "sha512-MEFJe5C3R8pwXdZ5Y21oo6m7ePiS0d9pWucn99O/wvyJZChoIQKrQDxKrGeW8F5+T0okTHesAmDeiHDTIq0V/Q==", 2161 + "cpu": [ 2162 + "arm64" 2163 + ], 2164 + "dev": true, 2165 + "license": "MIT", 2166 + "optional": true, 2167 + "os": [ 2168 + "openbsd" 2169 + ], 2170 + "engines": { 2171 + "node": ">=18" 2172 + } 2173 + }, 2174 + "node_modules/@esbuild/openbsd-x64": { 2175 + "version": "0.28.1", 2176 + "resolved": "https://registry.npmjs.org/@esbuild/openbsd-x64/-/openbsd-x64-0.28.1.tgz", 2177 + "integrity": "sha512-i/ZLIOafE0Z8cI/XANJAixoJL/uRAoS2xOA3rb0xN+KK0K177cMAsQYkzHtBrtMXAKuAc7HGgcWiZ/sRC1Nxgw==", 2178 + "cpu": [ 2179 + "x64" 2180 + ], 2181 + "dev": true, 2182 + "license": "MIT", 2183 + "optional": true, 2184 + "os": [ 2185 + "openbsd" 2186 + ], 2187 + "engines": { 2188 + "node": ">=18" 2189 + } 2190 + }, 2191 + "node_modules/@esbuild/openharmony-arm64": { 2192 + "version": "0.28.1", 2193 + "resolved": "https://registry.npmjs.org/@esbuild/openharmony-arm64/-/openharmony-arm64-0.28.1.tgz", 2194 + "integrity": "sha512-ge+Z7EXFNt2BO1oAMsVpiQ8EwndV9i1xXerAeTIK7AtPs3bKFXQM7nlRxDSIUIMeueR1CNXxqztLzdNeReKBJg==", 2195 + "cpu": [ 2196 + "arm64" 2197 + ], 2198 + "dev": true, 2199 + "license": "MIT", 2200 + "optional": true, 2201 + "os": [ 2202 + "openharmony" 2203 + ], 2204 + "engines": { 2205 + "node": ">=18" 2206 + } 2207 + }, 2208 + "node_modules/@esbuild/sunos-x64": { 2209 + "version": "0.28.1", 2210 + "resolved": "https://registry.npmjs.org/@esbuild/sunos-x64/-/sunos-x64-0.28.1.tgz", 2211 + "integrity": "sha512-BEjgtECkL3vY+SaSQ6nzVfiALUeFxpawyp8Jmf5PtYhf1Ug40N1h/hxlhts+f1FvSvarEigdxS3BlSMI2PJLcQ==", 2212 + "cpu": [ 2213 + "x64" 2214 + ], 2215 + "dev": true, 2216 + "license": "MIT", 2217 + "optional": true, 2218 + "os": [ 2219 + "sunos" 2220 + ], 2221 + "engines": { 2222 + "node": ">=18" 2223 + } 2224 + }, 2225 + "node_modules/@esbuild/win32-arm64": { 2226 + "version": "0.28.1", 2227 + "resolved": "https://registry.npmjs.org/@esbuild/win32-arm64/-/win32-arm64-0.28.1.tgz", 2228 + "integrity": "sha512-lCv9eK/H6ZJWbE7bh2nw54CZ9M2nupBxJcTsdk/QQnWkdSjKGuxmmH8/GWrlT1eMmZfn4dGcCjRte397WqfQXA==", 2229 + "cpu": [ 2230 + "arm64" 2231 + ], 2232 + "dev": true, 2233 + "license": "MIT", 2234 + "optional": true, 2235 + "os": [ 2236 + "win32" 2237 + ], 2238 + "engines": { 2239 + "node": ">=18" 2240 + } 2241 + }, 2242 + "node_modules/@esbuild/win32-ia32": { 2243 + "version": "0.28.1", 2244 + "resolved": "https://registry.npmjs.org/@esbuild/win32-ia32/-/win32-ia32-0.28.1.tgz", 2245 + "integrity": "sha512-zvb/mB2bSCoJOpoCBgYKKpX6YM6mJBlBUVUtVj41DlZJVEB6/0CKlRYxP5wWl1C1ILiCoAU5wZZ4q1P3qeS6Eg==", 2246 + "cpu": [ 2247 + "ia32" 2248 + ], 2249 + "dev": true, 2250 + "license": "MIT", 2251 + "optional": true, 2252 + "os": [ 2253 + "win32" 2254 + ], 2255 + "engines": { 2256 + "node": ">=18" 2257 + } 2258 + }, 2259 + "node_modules/@esbuild/win32-x64": { 2260 + "version": "0.28.1", 2261 + "resolved": "https://registry.npmjs.org/@esbuild/win32-x64/-/win32-x64-0.28.1.tgz", 2262 + "integrity": "sha512-bm4Mowrv+GXMlpWX++EcXw/iLyd1o3+bJkC2DkWXYVvgZCqD/bSj9ctZeAMC3cIxgjRVR2Dufaiu4YPxr5gW1A==", 2263 + "cpu": [ 2264 + "x64" 2265 + ], 2266 + "dev": true, 2267 + "license": "MIT", 2268 + "optional": true, 2269 + "os": [ 2270 + "win32" 2271 + ], 2272 + "engines": { 2273 + "node": ">=18" 2274 + } 2275 + }, 2276 + "node_modules/@hexagon/base64": { 2277 + "version": "1.1.28", 2278 + "resolved": "https://registry.npmjs.org/@hexagon/base64/-/base64-1.1.28.tgz", 2279 + "integrity": "sha512-lhqDEAvWixy3bZ+UOYbPwUbBkwBq5C1LAJ/xPC8Oi+lL54oyakv/npbA0aU2hgCsx/1NUd4IBvV03+aUBWxerw==", 2280 + "license": "MIT" 2281 + }, 2282 + "node_modules/@img/colour": { 2283 + "version": "1.1.0", 2284 + "resolved": "https://registry.npmjs.org/@img/colour/-/colour-1.1.0.tgz", 2285 + "integrity": "sha512-Td76q7j57o/tLVdgS746cYARfSyxk8iEfRxewL9h4OMzYhbW4TAcppl0mT4eyqXddh6L/jwoM75mo7ixa/pCeQ==", 2286 + "dev": true, 2287 + "license": "MIT", 2288 + "engines": { 2289 + "node": ">=18" 2290 + } 2291 + }, 2292 + "node_modules/@img/sharp-darwin-arm64": { 2293 + "version": "0.34.5", 2294 + "resolved": "https://registry.npmjs.org/@img/sharp-darwin-arm64/-/sharp-darwin-arm64-0.34.5.tgz", 2295 + "integrity": "sha512-imtQ3WMJXbMY4fxb/Ndp6HBTNVtWCUI0WdobyheGf5+ad6xX8VIDO8u2xE4qc/fr08CKG/7dDseFtn6M6g/r3w==", 2296 + "cpu": [ 2297 + "arm64" 2298 + ], 2299 + "dev": true, 2300 + "license": "Apache-2.0", 2301 + "optional": true, 2302 + "os": [ 2303 + "darwin" 2304 + ], 2305 + "engines": { 2306 + "node": "^18.17.0 || ^20.3.0 || >=21.0.0" 2307 + }, 2308 + "funding": { 2309 + "url": "https://opencollective.com/libvips" 2310 + }, 2311 + "optionalDependencies": { 2312 + "@img/sharp-libvips-darwin-arm64": "1.2.4" 2313 + } 2314 + }, 2315 + "node_modules/@img/sharp-darwin-x64": { 2316 + "version": "0.34.5", 2317 + "resolved": "https://registry.npmjs.org/@img/sharp-darwin-x64/-/sharp-darwin-x64-0.34.5.tgz", 2318 + "integrity": "sha512-YNEFAF/4KQ/PeW0N+r+aVVsoIY0/qxxikF2SWdp+NRkmMB7y9LBZAVqQ4yhGCm/H3H270OSykqmQMKLBhBJDEw==", 2319 + "cpu": [ 2320 + "x64" 2321 + ], 2322 + "dev": true, 2323 + "license": "Apache-2.0", 2324 + "optional": true, 2325 + "os": [ 2326 + "darwin" 2327 + ], 2328 + "engines": { 2329 + "node": "^18.17.0 || ^20.3.0 || >=21.0.0" 2330 + }, 2331 + "funding": { 2332 + "url": "https://opencollective.com/libvips" 2333 + }, 2334 + "optionalDependencies": { 2335 + "@img/sharp-libvips-darwin-x64": "1.2.4" 2336 + } 2337 + }, 2338 + "node_modules/@img/sharp-libvips-darwin-arm64": { 2339 + "version": "1.2.4", 2340 + "resolved": "https://registry.npmjs.org/@img/sharp-libvips-darwin-arm64/-/sharp-libvips-darwin-arm64-1.2.4.tgz", 2341 + "integrity": "sha512-zqjjo7RatFfFoP0MkQ51jfuFZBnVE2pRiaydKJ1G/rHZvnsrHAOcQALIi9sA5co5xenQdTugCvtb1cuf78Vf4g==", 2342 + "cpu": [ 2343 + "arm64" 2344 + ], 2345 + "dev": true, 2346 + "license": "LGPL-3.0-or-later", 2347 + "optional": true, 2348 + "os": [ 2349 + "darwin" 2350 + ], 2351 + "funding": { 2352 + "url": "https://opencollective.com/libvips" 2353 + } 2354 + }, 2355 + "node_modules/@img/sharp-libvips-darwin-x64": { 2356 + "version": "1.2.4", 2357 + "resolved": "https://registry.npmjs.org/@img/sharp-libvips-darwin-x64/-/sharp-libvips-darwin-x64-1.2.4.tgz", 2358 + "integrity": "sha512-1IOd5xfVhlGwX+zXv2N93k0yMONvUlANylbJw1eTah8K/Jtpi15KC+WSiaX/nBmbm2HxRM1gZ0nSdjSsrZbGKg==", 2359 + "cpu": [ 2360 + "x64" 2361 + ], 2362 + "dev": true, 2363 + "license": "LGPL-3.0-or-later", 2364 + "optional": true, 2365 + "os": [ 2366 + "darwin" 2367 + ], 2368 + "funding": { 2369 + "url": "https://opencollective.com/libvips" 2370 + } 2371 + }, 2372 + "node_modules/@img/sharp-libvips-linux-arm": { 2373 + "version": "1.2.4", 2374 + "resolved": "https://registry.npmjs.org/@img/sharp-libvips-linux-arm/-/sharp-libvips-linux-arm-1.2.4.tgz", 2375 + "integrity": "sha512-bFI7xcKFELdiNCVov8e44Ia4u2byA+l3XtsAj+Q8tfCwO6BQ8iDojYdvoPMqsKDkuoOo+X6HZA0s0q11ANMQ8A==", 2376 + "cpu": [ 2377 + "arm" 2378 + ], 2379 + "dev": true, 2380 + "license": "LGPL-3.0-or-later", 2381 + "optional": true, 2382 + "os": [ 2383 + "linux" 2384 + ], 2385 + "funding": { 2386 + "url": "https://opencollective.com/libvips" 2387 + } 2388 + }, 2389 + "node_modules/@img/sharp-libvips-linux-arm64": { 2390 + "version": "1.2.4", 2391 + "resolved": "https://registry.npmjs.org/@img/sharp-libvips-linux-arm64/-/sharp-libvips-linux-arm64-1.2.4.tgz", 2392 + "integrity": "sha512-excjX8DfsIcJ10x1Kzr4RcWe1edC9PquDRRPx3YVCvQv+U5p7Yin2s32ftzikXojb1PIFc/9Mt28/y+iRklkrw==", 2393 + "cpu": [ 2394 + "arm64" 2395 + ], 2396 + "dev": true, 2397 + "license": "LGPL-3.0-or-later", 2398 + "optional": true, 2399 + "os": [ 2400 + "linux" 2401 + ], 2402 + "funding": { 2403 + "url": "https://opencollective.com/libvips" 2404 + } 2405 + }, 2406 + "node_modules/@img/sharp-libvips-linux-ppc64": { 2407 + "version": "1.2.4", 2408 + "resolved": "https://registry.npmjs.org/@img/sharp-libvips-linux-ppc64/-/sharp-libvips-linux-ppc64-1.2.4.tgz", 2409 + "integrity": "sha512-FMuvGijLDYG6lW+b/UvyilUWu5Ayu+3r2d1S8notiGCIyYU/76eig1UfMmkZ7vwgOrzKzlQbFSuQfgm7GYUPpA==", 2410 + "cpu": [ 2411 + "ppc64" 2412 + ], 2413 + "dev": true, 2414 + "license": "LGPL-3.0-or-later", 2415 + "optional": true, 2416 + "os": [ 2417 + "linux" 2418 + ], 2419 + "funding": { 2420 + "url": "https://opencollective.com/libvips" 2421 + } 2422 + }, 2423 + "node_modules/@img/sharp-libvips-linux-riscv64": { 2424 + "version": "1.2.4", 2425 + "resolved": "https://registry.npmjs.org/@img/sharp-libvips-linux-riscv64/-/sharp-libvips-linux-riscv64-1.2.4.tgz", 2426 + "integrity": "sha512-oVDbcR4zUC0ce82teubSm+x6ETixtKZBh/qbREIOcI3cULzDyb18Sr/Wcyx7NRQeQzOiHTNbZFF1UwPS2scyGA==", 2427 + "cpu": [ 2428 + "riscv64" 2429 + ], 2430 + "dev": true, 2431 + "license": "LGPL-3.0-or-later", 2432 + "optional": true, 2433 + "os": [ 2434 + "linux" 2435 + ], 2436 + "funding": { 2437 + "url": "https://opencollective.com/libvips" 2438 + } 2439 + }, 2440 + "node_modules/@img/sharp-libvips-linux-s390x": { 2441 + "version": "1.2.4", 2442 + "resolved": "https://registry.npmjs.org/@img/sharp-libvips-linux-s390x/-/sharp-libvips-linux-s390x-1.2.4.tgz", 2443 + "integrity": "sha512-qmp9VrzgPgMoGZyPvrQHqk02uyjA0/QrTO26Tqk6l4ZV0MPWIW6LTkqOIov+J1yEu7MbFQaDpwdwJKhbJvuRxQ==", 2444 + "cpu": [ 2445 + "s390x" 2446 + ], 2447 + "dev": true, 2448 + "license": "LGPL-3.0-or-later", 2449 + "optional": true, 2450 + "os": [ 2451 + "linux" 2452 + ], 2453 + "funding": { 2454 + "url": "https://opencollective.com/libvips" 2455 + } 2456 + }, 2457 + "node_modules/@img/sharp-libvips-linux-x64": { 2458 + "version": "1.2.4", 2459 + "resolved": "https://registry.npmjs.org/@img/sharp-libvips-linux-x64/-/sharp-libvips-linux-x64-1.2.4.tgz", 2460 + "integrity": "sha512-tJxiiLsmHc9Ax1bz3oaOYBURTXGIRDODBqhveVHonrHJ9/+k89qbLl0bcJns+e4t4rvaNBxaEZsFtSfAdquPrw==", 2461 + "cpu": [ 2462 + "x64" 2463 + ], 2464 + "dev": true, 2465 + "license": "LGPL-3.0-or-later", 2466 + "optional": true, 2467 + "os": [ 2468 + "linux" 2469 + ], 2470 + "funding": { 2471 + "url": "https://opencollective.com/libvips" 2472 + } 2473 + }, 2474 + "node_modules/@img/sharp-libvips-linuxmusl-arm64": { 2475 + "version": "1.2.4", 2476 + "resolved": "https://registry.npmjs.org/@img/sharp-libvips-linuxmusl-arm64/-/sharp-libvips-linuxmusl-arm64-1.2.4.tgz", 2477 + "integrity": "sha512-FVQHuwx1IIuNow9QAbYUzJ+En8KcVm9Lk5+uGUQJHaZmMECZmOlix9HnH7n1TRkXMS0pGxIJokIVB9SuqZGGXw==", 2478 + "cpu": [ 2479 + "arm64" 2480 + ], 2481 + "dev": true, 2482 + "license": "LGPL-3.0-or-later", 2483 + "optional": true, 2484 + "os": [ 2485 + "linux" 2486 + ], 2487 + "funding": { 2488 + "url": "https://opencollective.com/libvips" 2489 + } 2490 + }, 2491 + "node_modules/@img/sharp-libvips-linuxmusl-x64": { 2492 + "version": "1.2.4", 2493 + "resolved": "https://registry.npmjs.org/@img/sharp-libvips-linuxmusl-x64/-/sharp-libvips-linuxmusl-x64-1.2.4.tgz", 2494 + "integrity": "sha512-+LpyBk7L44ZIXwz/VYfglaX/okxezESc6UxDSoyo2Ks6Jxc4Y7sGjpgU9s4PMgqgjj1gZCylTieNamqA1MF7Dg==", 2495 + "cpu": [ 2496 + "x64" 2497 + ], 2498 + "dev": true, 2499 + "license": "LGPL-3.0-or-later", 2500 + "optional": true, 2501 + "os": [ 2502 + "linux" 2503 + ], 2504 + "funding": { 2505 + "url": "https://opencollective.com/libvips" 2506 + } 2507 + }, 2508 + "node_modules/@img/sharp-linux-arm": { 2509 + "version": "0.34.5", 2510 + "resolved": "https://registry.npmjs.org/@img/sharp-linux-arm/-/sharp-linux-arm-0.34.5.tgz", 2511 + "integrity": "sha512-9dLqsvwtg1uuXBGZKsxem9595+ujv0sJ6Vi8wcTANSFpwV/GONat5eCkzQo/1O6zRIkh0m/8+5BjrRr7jDUSZw==", 2512 + "cpu": [ 2513 + "arm" 2514 + ], 2515 + "dev": true, 2516 + "license": "Apache-2.0", 2517 + "optional": true, 2518 + "os": [ 2519 + "linux" 2520 + ], 2521 + "engines": { 2522 + "node": "^18.17.0 || ^20.3.0 || >=21.0.0" 2523 + }, 2524 + "funding": { 2525 + "url": "https://opencollective.com/libvips" 2526 + }, 2527 + "optionalDependencies": { 2528 + "@img/sharp-libvips-linux-arm": "1.2.4" 2529 + } 2530 + }, 2531 + "node_modules/@img/sharp-linux-arm64": { 2532 + "version": "0.34.5", 2533 + "resolved": "https://registry.npmjs.org/@img/sharp-linux-arm64/-/sharp-linux-arm64-0.34.5.tgz", 2534 + "integrity": "sha512-bKQzaJRY/bkPOXyKx5EVup7qkaojECG6NLYswgktOZjaXecSAeCWiZwwiFf3/Y+O1HrauiE3FVsGxFg8c24rZg==", 2535 + "cpu": [ 2536 + "arm64" 2537 + ], 2538 + "dev": true, 2539 + "license": "Apache-2.0", 2540 + "optional": true, 2541 + "os": [ 2542 + "linux" 2543 + ], 2544 + "engines": { 2545 + "node": "^18.17.0 || ^20.3.0 || >=21.0.0" 2546 + }, 2547 + "funding": { 2548 + "url": "https://opencollective.com/libvips" 2549 + }, 2550 + "optionalDependencies": { 2551 + "@img/sharp-libvips-linux-arm64": "1.2.4" 2552 + } 2553 + }, 2554 + "node_modules/@img/sharp-linux-ppc64": { 2555 + "version": "0.34.5", 2556 + "resolved": "https://registry.npmjs.org/@img/sharp-linux-ppc64/-/sharp-linux-ppc64-0.34.5.tgz", 2557 + "integrity": "sha512-7zznwNaqW6YtsfrGGDA6BRkISKAAE1Jo0QdpNYXNMHu2+0dTrPflTLNkpc8l7MUP5M16ZJcUvysVWWrMefZquA==", 2558 + "cpu": [ 2559 + "ppc64" 2560 + ], 2561 + "dev": true, 2562 + "license": "Apache-2.0", 2563 + "optional": true, 2564 + "os": [ 2565 + "linux" 2566 + ], 2567 + "engines": { 2568 + "node": "^18.17.0 || ^20.3.0 || >=21.0.0" 2569 + }, 2570 + "funding": { 2571 + "url": "https://opencollective.com/libvips" 2572 + }, 2573 + "optionalDependencies": { 2574 + "@img/sharp-libvips-linux-ppc64": "1.2.4" 2575 + } 2576 + }, 2577 + "node_modules/@img/sharp-linux-riscv64": { 2578 + "version": "0.34.5", 2579 + "resolved": "https://registry.npmjs.org/@img/sharp-linux-riscv64/-/sharp-linux-riscv64-0.34.5.tgz", 2580 + "integrity": "sha512-51gJuLPTKa7piYPaVs8GmByo7/U7/7TZOq+cnXJIHZKavIRHAP77e3N2HEl3dgiqdD/w0yUfiJnII77PuDDFdw==", 2581 + "cpu": [ 2582 + "riscv64" 2583 + ], 2584 + "dev": true, 2585 + "license": "Apache-2.0", 2586 + "optional": true, 2587 + "os": [ 2588 + "linux" 2589 + ], 2590 + "engines": { 2591 + "node": "^18.17.0 || ^20.3.0 || >=21.0.0" 2592 + }, 2593 + "funding": { 2594 + "url": "https://opencollective.com/libvips" 2595 + }, 2596 + "optionalDependencies": { 2597 + "@img/sharp-libvips-linux-riscv64": "1.2.4" 2598 + } 2599 + }, 2600 + "node_modules/@img/sharp-linux-s390x": { 2601 + "version": "0.34.5", 2602 + "resolved": "https://registry.npmjs.org/@img/sharp-linux-s390x/-/sharp-linux-s390x-0.34.5.tgz", 2603 + "integrity": "sha512-nQtCk0PdKfho3eC5MrbQoigJ2gd1CgddUMkabUj+rBevs8tZ2cULOx46E7oyX+04WGfABgIwmMC0VqieTiR4jg==", 2604 + "cpu": [ 2605 + "s390x" 2606 + ], 2607 + "dev": true, 2608 + "license": "Apache-2.0", 2609 + "optional": true, 2610 + "os": [ 2611 + "linux" 2612 + ], 2613 + "engines": { 2614 + "node": "^18.17.0 || ^20.3.0 || >=21.0.0" 2615 + }, 2616 + "funding": { 2617 + "url": "https://opencollective.com/libvips" 2618 + }, 2619 + "optionalDependencies": { 2620 + "@img/sharp-libvips-linux-s390x": "1.2.4" 2621 + } 2622 + }, 2623 + "node_modules/@img/sharp-linux-x64": { 2624 + "version": "0.34.5", 2625 + "resolved": "https://registry.npmjs.org/@img/sharp-linux-x64/-/sharp-linux-x64-0.34.5.tgz", 2626 + "integrity": "sha512-MEzd8HPKxVxVenwAa+JRPwEC7QFjoPWuS5NZnBt6B3pu7EG2Ge0id1oLHZpPJdn3OQK+BQDiw9zStiHBTJQQQQ==", 2627 + "cpu": [ 2628 + "x64" 2629 + ], 2630 + "dev": true, 2631 + "license": "Apache-2.0", 2632 + "optional": true, 2633 + "os": [ 2634 + "linux" 2635 + ], 2636 + "engines": { 2637 + "node": "^18.17.0 || ^20.3.0 || >=21.0.0" 2638 + }, 2639 + "funding": { 2640 + "url": "https://opencollective.com/libvips" 2641 + }, 2642 + "optionalDependencies": { 2643 + "@img/sharp-libvips-linux-x64": "1.2.4" 2644 + } 2645 + }, 2646 + "node_modules/@img/sharp-linuxmusl-arm64": { 2647 + "version": "0.34.5", 2648 + "resolved": "https://registry.npmjs.org/@img/sharp-linuxmusl-arm64/-/sharp-linuxmusl-arm64-0.34.5.tgz", 2649 + "integrity": "sha512-fprJR6GtRsMt6Kyfq44IsChVZeGN97gTD331weR1ex1c1rypDEABN6Tm2xa1wE6lYb5DdEnk03NZPqA7Id21yg==", 2650 + "cpu": [ 2651 + "arm64" 2652 + ], 2653 + "dev": true, 2654 + "license": "Apache-2.0", 2655 + "optional": true, 2656 + "os": [ 2657 + "linux" 2658 + ], 2659 + "engines": { 2660 + "node": "^18.17.0 || ^20.3.0 || >=21.0.0" 2661 + }, 2662 + "funding": { 2663 + "url": "https://opencollective.com/libvips" 2664 + }, 2665 + "optionalDependencies": { 2666 + "@img/sharp-libvips-linuxmusl-arm64": "1.2.4" 2667 + } 2668 + }, 2669 + "node_modules/@img/sharp-linuxmusl-x64": { 2670 + "version": "0.34.5", 2671 + "resolved": "https://registry.npmjs.org/@img/sharp-linuxmusl-x64/-/sharp-linuxmusl-x64-0.34.5.tgz", 2672 + "integrity": "sha512-Jg8wNT1MUzIvhBFxViqrEhWDGzqymo3sV7z7ZsaWbZNDLXRJZoRGrjulp60YYtV4wfY8VIKcWidjojlLcWrd8Q==", 2673 + "cpu": [ 2674 + "x64" 2675 + ], 2676 + "dev": true, 2677 + "license": "Apache-2.0", 2678 + "optional": true, 2679 + "os": [ 2680 + "linux" 2681 + ], 2682 + "engines": { 2683 + "node": "^18.17.0 || ^20.3.0 || >=21.0.0" 2684 + }, 2685 + "funding": { 2686 + "url": "https://opencollective.com/libvips" 2687 + }, 2688 + "optionalDependencies": { 2689 + "@img/sharp-libvips-linuxmusl-x64": "1.2.4" 2690 + } 2691 + }, 2692 + "node_modules/@img/sharp-wasm32": { 2693 + "version": "0.34.5", 2694 + "resolved": "https://registry.npmjs.org/@img/sharp-wasm32/-/sharp-wasm32-0.34.5.tgz", 2695 + "integrity": "sha512-OdWTEiVkY2PHwqkbBI8frFxQQFekHaSSkUIJkwzclWZe64O1X4UlUjqqqLaPbUpMOQk6FBu/HtlGXNblIs0huw==", 2696 + "cpu": [ 2697 + "wasm32" 2698 + ], 2699 + "dev": true, 2700 + "license": "Apache-2.0 AND LGPL-3.0-or-later AND MIT", 2701 + "optional": true, 2702 + "dependencies": { 2703 + "@emnapi/runtime": "^1.7.0" 2704 + }, 2705 + "engines": { 2706 + "node": "^18.17.0 || ^20.3.0 || >=21.0.0" 2707 + }, 2708 + "funding": { 2709 + "url": "https://opencollective.com/libvips" 2710 + } 2711 + }, 2712 + "node_modules/@img/sharp-win32-arm64": { 2713 + "version": "0.34.5", 2714 + "resolved": "https://registry.npmjs.org/@img/sharp-win32-arm64/-/sharp-win32-arm64-0.34.5.tgz", 2715 + "integrity": "sha512-WQ3AgWCWYSb2yt+IG8mnC6Jdk9Whs7O0gxphblsLvdhSpSTtmu69ZG1Gkb6NuvxsNACwiPV6cNSZNzt0KPsw7g==", 2716 + "cpu": [ 2717 + "arm64" 2718 + ], 2719 + "dev": true, 2720 + "license": "Apache-2.0 AND LGPL-3.0-or-later", 2721 + "optional": true, 2722 + "os": [ 2723 + "win32" 2724 + ], 2725 + "engines": { 2726 + "node": "^18.17.0 || ^20.3.0 || >=21.0.0" 2727 + }, 2728 + "funding": { 2729 + "url": "https://opencollective.com/libvips" 2730 + } 2731 + }, 2732 + "node_modules/@img/sharp-win32-ia32": { 2733 + "version": "0.34.5", 2734 + "resolved": "https://registry.npmjs.org/@img/sharp-win32-ia32/-/sharp-win32-ia32-0.34.5.tgz", 2735 + "integrity": "sha512-FV9m/7NmeCmSHDD5j4+4pNI8Cp3aW+JvLoXcTUo0IqyjSfAZJ8dIUmijx1qaJsIiU+Hosw6xM5KijAWRJCSgNg==", 2736 + "cpu": [ 2737 + "ia32" 2738 + ], 2739 + "dev": true, 2740 + "license": "Apache-2.0 AND LGPL-3.0-or-later", 2741 + "optional": true, 2742 + "os": [ 2743 + "win32" 2744 + ], 2745 + "engines": { 2746 + "node": "^18.17.0 || ^20.3.0 || >=21.0.0" 2747 + }, 2748 + "funding": { 2749 + "url": "https://opencollective.com/libvips" 2750 + } 2751 + }, 2752 + "node_modules/@img/sharp-win32-x64": { 2753 + "version": "0.34.5", 2754 + "resolved": "https://registry.npmjs.org/@img/sharp-win32-x64/-/sharp-win32-x64-0.34.5.tgz", 2755 + "integrity": "sha512-+29YMsqY2/9eFEiW93eqWnuLcWcufowXewwSNIT6UwZdUUCrM3oFjMWH/Z6/TMmb4hlFenmfAVbpWeup2jryCw==", 2756 + "cpu": [ 2757 + "x64" 2758 + ], 2759 + "dev": true, 2760 + "license": "Apache-2.0 AND LGPL-3.0-or-later", 2761 + "optional": true, 2762 + "os": [ 2763 + "win32" 2764 + ], 2765 + "engines": { 2766 + "node": "^18.17.0 || ^20.3.0 || >=21.0.0" 2767 + }, 2768 + "funding": { 2769 + "url": "https://opencollective.com/libvips" 2770 + } 2771 + }, 2772 + "node_modules/@isaacs/cliui": { 2773 + "version": "9.0.0", 2774 + "resolved": "https://registry.npmjs.org/@isaacs/cliui/-/cliui-9.0.0.tgz", 2775 + "integrity": "sha512-AokJm4tuBHillT+FpMtxQ60n8ObyXBatq7jD2/JA9dxbDDokKQm8KMht5ibGzLVU9IJDIKK4TPKgMHEYMn3lMg==", 2776 + "dev": true, 2777 + "license": "BlueOak-1.0.0", 2778 + "engines": { 2779 + "node": ">=18" 2780 + } 2781 + }, 2782 + "node_modules/@jridgewell/gen-mapping": { 2783 + "version": "0.3.13", 2784 + "resolved": "https://registry.npmjs.org/@jridgewell/gen-mapping/-/gen-mapping-0.3.13.tgz", 2785 + "integrity": "sha512-2kkt/7niJ6MgEPxF0bYdQ6etZaA+fQvDcLKckhy1yIQOzaoKjBBjSj63/aLVjYE3qhRt5dvM+uUyfCg6UKCBbA==", 2786 + "dev": true, 2787 + "license": "MIT", 2788 + "dependencies": { 2789 + "@jridgewell/sourcemap-codec": "^1.5.0", 2790 + "@jridgewell/trace-mapping": "^0.3.24" 2791 + } 2792 + }, 2793 + "node_modules/@jridgewell/remapping": { 2794 + "version": "2.3.5", 2795 + "resolved": "https://registry.npmjs.org/@jridgewell/remapping/-/remapping-2.3.5.tgz", 2796 + "integrity": "sha512-LI9u/+laYG4Ds1TDKSJW2YPrIlcVYOwi2fUC6xB43lueCjgxV4lffOCZCtYFiH6TNOX+tQKXx97T4IKHbhyHEQ==", 2797 + "dev": true, 2798 + "license": "MIT", 2799 + "dependencies": { 2800 + "@jridgewell/gen-mapping": "^0.3.5", 2801 + "@jridgewell/trace-mapping": "^0.3.24" 2802 + } 2803 + }, 2804 + "node_modules/@jridgewell/resolve-uri": { 2805 + "version": "3.1.2", 2806 + "resolved": "https://registry.npmjs.org/@jridgewell/resolve-uri/-/resolve-uri-3.1.2.tgz", 2807 + "integrity": "sha512-bRISgCIjP20/tbWSPWMEi54QVPRZExkuD9lJL+UIxUKtwVJA8wW1Trb1jMs1RFXo1CBTNZ/5hpC9QvmKWdopKw==", 2808 + "dev": true, 2809 + "license": "MIT", 2810 + "engines": { 2811 + "node": ">=6.0.0" 2812 + } 2813 + }, 2814 + "node_modules/@jridgewell/source-map": { 2815 + "version": "0.3.11", 2816 + "resolved": "https://registry.npmjs.org/@jridgewell/source-map/-/source-map-0.3.11.tgz", 2817 + "integrity": "sha512-ZMp1V8ZFcPG5dIWnQLr3NSI1MiCU7UETdS/A0G8V/XWHvJv3ZsFqutJn1Y5RPmAPX6F3BiE397OqveU/9NCuIA==", 2818 + "dev": true, 2819 + "license": "MIT", 2820 + "dependencies": { 2821 + "@jridgewell/gen-mapping": "^0.3.5", 2822 + "@jridgewell/trace-mapping": "^0.3.25" 2823 + } 2824 + }, 2825 + "node_modules/@jridgewell/sourcemap-codec": { 2826 + "version": "1.5.5", 2827 + "resolved": "https://registry.npmjs.org/@jridgewell/sourcemap-codec/-/sourcemap-codec-1.5.5.tgz", 2828 + "integrity": "sha512-cYQ9310grqxueWbl+WuIUIaiUaDcj7WOq5fVhEljNVgRfOUhY9fy2zTvfoqWsnebh8Sl70VScFbICvJnLKB0Og==", 2829 + "dev": true, 2830 + "license": "MIT" 2831 + }, 2832 + "node_modules/@jridgewell/trace-mapping": { 2833 + "version": "0.3.31", 2834 + "resolved": "https://registry.npmjs.org/@jridgewell/trace-mapping/-/trace-mapping-0.3.31.tgz", 2835 + "integrity": "sha512-zzNR+SdQSDJzc8joaeP8QQoCQr8NuYx2dIIytl1QeBEZHJ9uW6hebsrYgbz8hJwUQao3TWCMtmfV8Nu1twOLAw==", 2836 + "dev": true, 2837 + "license": "MIT", 2838 + "dependencies": { 2839 + "@jridgewell/resolve-uri": "^3.1.0", 2840 + "@jridgewell/sourcemap-codec": "^1.4.14" 2841 + } 2842 + }, 2843 + "node_modules/@levischuck/tiny-cbor": { 2844 + "version": "0.2.11", 2845 + "resolved": "https://registry.npmjs.org/@levischuck/tiny-cbor/-/tiny-cbor-0.2.11.tgz", 2846 + "integrity": "sha512-llBRm4dT4Z89aRsm6u2oEZ8tfwL/2l6BwpZ7JcyieouniDECM5AqNgr/y08zalEIvW3RSK4upYyybDcmjXqAow==", 2847 + "license": "MIT" 2848 + }, 2849 + "node_modules/@napi-rs/wasm-runtime": { 2850 + "version": "1.1.6", 2851 + "resolved": "https://registry.npmjs.org/@napi-rs/wasm-runtime/-/wasm-runtime-1.1.6.tgz", 2852 + "integrity": "sha512-ZLv/JdUfkvOy9eCnnBaGfiO+XimbjebAeO+MRQqD/B+FR1tnRN0tpKSJHRbE8sFfS6aqsXZ67TQjfwfsxULVbg==", 2853 + "dev": true, 2854 + "license": "MIT", 2855 + "optional": true, 2856 + "dependencies": { 2857 + "@tybys/wasm-util": "^0.10.3" 2858 + }, 2859 + "funding": { 2860 + "type": "github", 2861 + "url": "https://github.com/sponsors/Brooooooklyn" 2862 + }, 2863 + "peerDependencies": { 2864 + "@emnapi/core": "^1.7.1", 2865 + "@emnapi/runtime": "^1.7.1" 2866 + } 2867 + }, 2868 + "node_modules/@oslojs/asn1": { 2869 + "version": "1.0.0", 2870 + "resolved": "https://registry.npmjs.org/@oslojs/asn1/-/asn1-1.0.0.tgz", 2871 + "integrity": "sha512-zw/wn0sj0j0QKbIXfIlnEcTviaCzYOY3V5rAyjR6YtOByFtJiT574+8p9Wlach0lZH9fddD4yb9laEAIl4vXQA==", 2872 + "license": "MIT", 2873 + "dependencies": { 2874 + "@oslojs/binary": "1.0.0" 2875 + } 2876 + }, 2877 + "node_modules/@oslojs/binary": { 2878 + "version": "1.0.0", 2879 + "resolved": "https://registry.npmjs.org/@oslojs/binary/-/binary-1.0.0.tgz", 2880 + "integrity": "sha512-9RCU6OwXU6p67H4NODbuxv2S3eenuQ4/WFLrsq+K/k682xrznH5EVWA7N4VFk9VYVcbFtKqur5YQQZc0ySGhsQ==", 2881 + "license": "MIT" 2882 + }, 2883 + "node_modules/@oslojs/crypto": { 2884 + "version": "1.0.1", 2885 + "resolved": "https://registry.npmjs.org/@oslojs/crypto/-/crypto-1.0.1.tgz", 2886 + "integrity": "sha512-7n08G8nWjAr/Yu3vu9zzrd0L9XnrJfpMioQcvCMxBIiF5orECHe5/3J0jmXRVvgfqMm/+4oxlQ+Sq39COYLcNQ==", 2887 + "license": "MIT", 2888 + "dependencies": { 2889 + "@oslojs/asn1": "1.0.0", 2890 + "@oslojs/binary": "1.0.0" 2891 + } 2892 + }, 2893 + "node_modules/@oslojs/encoding": { 2894 + "version": "1.1.0", 2895 + "resolved": "https://registry.npmjs.org/@oslojs/encoding/-/encoding-1.1.0.tgz", 2896 + "integrity": "sha512-70wQhgYmndg4GCPxPPxPGevRKqTIJ2Nh4OkiMWmDAVYsTQ+Ta7Sq+rPevXyXGdzr30/qZBnyOalCszoMxlyldQ==", 2897 + "license": "MIT" 2898 + }, 2899 + "node_modules/@oslojs/jwt": { 2900 + "version": "0.2.0", 2901 + "resolved": "https://registry.npmjs.org/@oslojs/jwt/-/jwt-0.2.0.tgz", 2902 + "integrity": "sha512-bLE7BtHrURedCn4Mco3ma9L4Y1GR2SMBuIvjWr7rmQ4/W/4Jy70TIAgZ+0nIlk0xHz1vNP8x8DCns45Sb2XRbg==", 2903 + "license": "MIT", 2904 + "dependencies": { 2905 + "@oslojs/encoding": "0.4.1" 2906 + } 2907 + }, 2908 + "node_modules/@oslojs/jwt/node_modules/@oslojs/encoding": { 2909 + "version": "0.4.1", 2910 + "resolved": "https://registry.npmjs.org/@oslojs/encoding/-/encoding-0.4.1.tgz", 2911 + "integrity": "sha512-hkjo6MuIK/kQR5CrGNdAPZhS01ZCXuWDRJ187zh6qqF2+yMHZpD9fAYpX8q2bOO6Ryhl3XpCT6kUX76N8hhm4Q==", 2912 + "license": "MIT" 2913 + }, 2914 + "node_modules/@oxc-project/types": { 2915 + "version": "0.139.0", 2916 + "resolved": "https://registry.npmjs.org/@oxc-project/types/-/types-0.139.0.tgz", 2917 + "integrity": "sha512-r9gHphtCs+1M7J0pw6Sn/hh/Wpa/iQrOOkrNAlVLF/gHq+/CJmHIWKKUUhdWjcD6CIa8idarspCsASiXCXvFUw==", 2918 + "dev": true, 2919 + "license": "MIT", 2920 + "funding": { 2921 + "url": "https://github.com/sponsors/Boshen" 2922 + } 2923 + }, 2924 + "node_modules/@peculiar/asn1-android": { 2925 + "version": "2.8.0", 2926 + "resolved": "https://registry.npmjs.org/@peculiar/asn1-android/-/asn1-android-2.8.0.tgz", 2927 + "integrity": "sha512-skLbS+IOGv1lUgDqtChr8xvtvEr3HMse/JGBaL2r1J1o/n7a8wqOrovMtlRq/UXLhxvmLaONP67hwtshgzwfzA==", 2928 + "license": "MIT", 2929 + "dependencies": { 2930 + "@peculiar/asn1-schema": "^2.8.0", 2931 + "asn1js": "^3.0.10", 2932 + "tslib": "^2.8.1" 2933 + } 2934 + }, 2935 + "node_modules/@peculiar/asn1-cms": { 2936 + "version": "2.8.0", 2937 + "resolved": "https://registry.npmjs.org/@peculiar/asn1-cms/-/asn1-cms-2.8.0.tgz", 2938 + "integrity": "sha512-NgekZOrSJFSBFLFoLfwePguAWAx7z1+f2TEsWFUMyiqqfntZ4+S/S5hzqME3q4pCA0iOsFKdwiQ35dwY24eVqA==", 2939 + "license": "MIT", 2940 + "dependencies": { 2941 + "@peculiar/asn1-schema": "^2.8.0", 2942 + "@peculiar/asn1-x509": "^2.8.0", 2943 + "@peculiar/asn1-x509-attr": "^2.8.0", 2944 + "asn1js": "^3.0.10", 2945 + "tslib": "^2.8.1" 2946 + } 2947 + }, 2948 + "node_modules/@peculiar/asn1-csr": { 2949 + "version": "2.8.0", 2950 + "resolved": "https://registry.npmjs.org/@peculiar/asn1-csr/-/asn1-csr-2.8.0.tgz", 2951 + "integrity": "sha512-akbF8+uvleHs8sejNPQxwmVFuInAg6FMNHOwMILXfP518YfFJwdR3jr6oNUPOaEJfuEhn/vkNOCIT6ASUd4mbg==", 2952 + "license": "MIT", 2953 + "dependencies": { 2954 + "@peculiar/asn1-schema": "^2.8.0", 2955 + "@peculiar/asn1-x509": "^2.8.0", 2956 + "asn1js": "^3.0.10", 2957 + "tslib": "^2.8.1" 2958 + } 2959 + }, 2960 + "node_modules/@peculiar/asn1-ecc": { 2961 + "version": "2.8.0", 2962 + "resolved": "https://registry.npmjs.org/@peculiar/asn1-ecc/-/asn1-ecc-2.8.0.tgz", 2963 + "integrity": "sha512-ohwlk+u9Rv2NOAY1c6MfHj45ATVF8R1DUN/WCgABiRtLi2ZftlZWZX7KvpAbU8v9xPcmoILfELeEABj/rn18AQ==", 2964 + "license": "MIT", 2965 + "dependencies": { 2966 + "@peculiar/asn1-schema": "^2.8.0", 2967 + "@peculiar/asn1-x509": "^2.8.0", 2968 + "asn1js": "^3.0.10", 2969 + "tslib": "^2.8.1" 2970 + } 2971 + }, 2972 + "node_modules/@peculiar/asn1-pfx": { 2973 + "version": "2.8.0", 2974 + "resolved": "https://registry.npmjs.org/@peculiar/asn1-pfx/-/asn1-pfx-2.8.0.tgz", 2975 + "integrity": "sha512-5yof1ytoB++RQtaFbqSUJ8pxDJtZT6vbVqZ8XoJ61ph7UjNVvfFwAilnCodqkNsAodpy13gDhoxZXw00pghnyg==", 2976 + "license": "MIT", 2977 + "dependencies": { 2978 + "@peculiar/asn1-cms": "^2.8.0", 2979 + "@peculiar/asn1-pkcs8": "^2.8.0", 2980 + "@peculiar/asn1-rsa": "^2.8.0", 2981 + "@peculiar/asn1-schema": "^2.8.0", 2982 + "asn1js": "^3.0.10", 2983 + "tslib": "^2.8.1" 2984 + } 2985 + }, 2986 + "node_modules/@peculiar/asn1-pkcs8": { 2987 + "version": "2.8.0", 2988 + "resolved": "https://registry.npmjs.org/@peculiar/asn1-pkcs8/-/asn1-pkcs8-2.8.0.tgz", 2989 + "integrity": "sha512-qAKXtLpBEw9LqhKpjw3ajZSXlBur+ipW+y2ivVBQAG6F6qRx94yO+1ZR4mvw+YaCfKSaOzLeYEzsPaBp4SJELA==", 2990 + "license": "MIT", 2991 + "dependencies": { 2992 + "@peculiar/asn1-schema": "^2.8.0", 2993 + "@peculiar/asn1-x509": "^2.8.0", 2994 + "asn1js": "^3.0.10", 2995 + "tslib": "^2.8.1" 2996 + } 2997 + }, 2998 + "node_modules/@peculiar/asn1-pkcs9": { 2999 + "version": "2.8.0", 3000 + "resolved": "https://registry.npmjs.org/@peculiar/asn1-pkcs9/-/asn1-pkcs9-2.8.0.tgz", 3001 + "integrity": "sha512-b5nDWCnkV60+cQ141D6sVVwK9nz64R5n3zSVnklGd+ECdkW2Ol3U1a6yYFlalpSOaD557yuJB64A+q42jG7lUQ==", 3002 + "license": "MIT", 3003 + "dependencies": { 3004 + "@peculiar/asn1-cms": "^2.8.0", 3005 + "@peculiar/asn1-pfx": "^2.8.0", 3006 + "@peculiar/asn1-pkcs8": "^2.8.0", 3007 + "@peculiar/asn1-schema": "^2.8.0", 3008 + "@peculiar/asn1-x509": "^2.8.0", 3009 + "@peculiar/asn1-x509-attr": "^2.8.0", 3010 + "asn1js": "^3.0.10", 3011 + "tslib": "^2.8.1" 3012 + } 3013 + }, 3014 + "node_modules/@peculiar/asn1-rsa": { 3015 + "version": "2.8.0", 3016 + "resolved": "https://registry.npmjs.org/@peculiar/asn1-rsa/-/asn1-rsa-2.8.0.tgz", 3017 + "integrity": "sha512-zHEUlCqB2mk7x2lxDwHHJy7hWZOPdGHVlsmITWKB5/PbQo61atbu9PJ/0r9dQNMwFzbKPXZ8uK8/91eUhRznSg==", 3018 + "license": "MIT", 3019 + "dependencies": { 3020 + "@peculiar/asn1-schema": "^2.8.0", 3021 + "@peculiar/asn1-x509": "^2.8.0", 3022 + "asn1js": "^3.0.10", 3023 + "tslib": "^2.8.1" 3024 + } 3025 + }, 3026 + "node_modules/@peculiar/asn1-schema": { 3027 + "version": "2.8.0", 3028 + "resolved": "https://registry.npmjs.org/@peculiar/asn1-schema/-/asn1-schema-2.8.0.tgz", 3029 + "integrity": "sha512-7YT0U/ze0tF2QOBbE15gKZwy5tvgGyLRiRHLzhlbOpf7BT032oBSd0haZqXn5W6l26WLlu3dyxzjM+2638/z2Q==", 3030 + "license": "MIT", 3031 + "dependencies": { 3032 + "@peculiar/utils": "^2.0.2", 3033 + "asn1js": "^3.0.10", 3034 + "tslib": "^2.8.1" 3035 + } 3036 + }, 3037 + "node_modules/@peculiar/asn1-x509": { 3038 + "version": "2.8.0", 3039 + "resolved": "https://registry.npmjs.org/@peculiar/asn1-x509/-/asn1-x509-2.8.0.tgz", 3040 + "integrity": "sha512-N0CMuhWUzsWEVq6F1q9X6+VKUnWzSW+cSVg+aPaGGwDdbFoFWTYgin5MHwXgpWd6y9COMBxnfy/Qc+Xc7F0Zwg==", 3041 + "license": "MIT", 3042 + "dependencies": { 3043 + "@peculiar/asn1-schema": "^2.8.0", 3044 + "@peculiar/utils": "^2.0.2", 3045 + "asn1js": "^3.0.10", 3046 + "tslib": "^2.8.1" 3047 + } 3048 + }, 3049 + "node_modules/@peculiar/asn1-x509-attr": { 3050 + "version": "2.8.0", 3051 + "resolved": "https://registry.npmjs.org/@peculiar/asn1-x509-attr/-/asn1-x509-attr-2.8.0.tgz", 3052 + "integrity": "sha512-tHjkfS/qhMnmrlB2J9NhflQlQ7In3khO3CfmVrriOlpTeErY9ZIKOso1hQ5JQiyrJ7ShvqVPk7E5fQmbclkSKA==", 3053 + "license": "MIT", 3054 + "dependencies": { 3055 + "@peculiar/asn1-schema": "^2.8.0", 3056 + "@peculiar/asn1-x509": "^2.8.0", 3057 + "asn1js": "^3.0.10", 3058 + "tslib": "^2.8.1" 3059 + } 3060 + }, 3061 + "node_modules/@peculiar/utils": { 3062 + "version": "2.0.3", 3063 + "resolved": "https://registry.npmjs.org/@peculiar/utils/-/utils-2.0.3.tgz", 3064 + "integrity": "sha512-+oL3HPFRIZ1St2K50lWCXiioIgSoxzz7R1J3uF6neO2yl1sgmpgY6XXJH4BdpoDkMWznQTeYF6oWNDZLCdQ4eQ==", 3065 + "license": "MIT", 3066 + "dependencies": { 3067 + "tslib": "^2.8.1" 3068 + } 3069 + }, 3070 + "node_modules/@peculiar/x509": { 3071 + "version": "1.14.3", 3072 + "resolved": "https://registry.npmjs.org/@peculiar/x509/-/x509-1.14.3.tgz", 3073 + "integrity": "sha512-C2Xj8FZ0uHWeCXXqX5B4/gVFQmtSkiuOolzAgutjTfseNOHT3pUjljDZsTSxXFGgio54bCzVFqmEOUrIVk8RDA==", 3074 + "license": "MIT", 3075 + "dependencies": { 3076 + "@peculiar/asn1-cms": "^2.6.0", 3077 + "@peculiar/asn1-csr": "^2.6.0", 3078 + "@peculiar/asn1-ecc": "^2.6.0", 3079 + "@peculiar/asn1-pkcs9": "^2.6.0", 3080 + "@peculiar/asn1-rsa": "^2.6.0", 3081 + "@peculiar/asn1-schema": "^2.6.0", 3082 + "@peculiar/asn1-x509": "^2.6.0", 3083 + "pvtsutils": "^1.3.6", 3084 + "reflect-metadata": "^0.2.2", 3085 + "tslib": "^2.8.1", 3086 + "tsyringe": "^4.10.0" 3087 + }, 3088 + "engines": { 3089 + "node": ">=20.0.0" 3090 + } 3091 + }, 3092 + "node_modules/@poppinss/colors": { 3093 + "version": "4.1.6", 3094 + "resolved": "https://registry.npmjs.org/@poppinss/colors/-/colors-4.1.6.tgz", 3095 + "integrity": "sha512-H9xkIdFswbS8n1d6vmRd8+c10t2Qe+rZITbbDHHkQixH5+2x1FDGmi/0K+WgWiqQFKPSlIYB7jlH6Kpfn6Fleg==", 3096 + "dev": true, 3097 + "license": "MIT", 3098 + "dependencies": { 3099 + "kleur": "^4.1.5" 3100 + } 3101 + }, 3102 + "node_modules/@poppinss/dumper": { 3103 + "version": "0.6.5", 3104 + "resolved": "https://registry.npmjs.org/@poppinss/dumper/-/dumper-0.6.5.tgz", 3105 + "integrity": "sha512-NBdYIb90J7LfOI32dOewKI1r7wnkiH6m920puQ3qHUeZkxNkQiFnXVWoE6YtFSv6QOiPPf7ys6i+HWWecDz7sw==", 3106 + "dev": true, 3107 + "license": "MIT", 3108 + "dependencies": { 3109 + "@poppinss/colors": "^4.1.5", 3110 + "@sindresorhus/is": "^7.0.2", 3111 + "supports-color": "^10.0.0" 3112 + } 3113 + }, 3114 + "node_modules/@poppinss/exception": { 3115 + "version": "1.2.3", 3116 + "resolved": "https://registry.npmjs.org/@poppinss/exception/-/exception-1.2.3.tgz", 3117 + "integrity": "sha512-dCED+QRChTVatE9ibtoaxc+WkdzOSjYTKi/+uacHWIsfodVfpsueo3+DKpgU5Px8qXjgmXkSvhXvSCz3fnP9lw==", 3118 + "dev": true, 3119 + "license": "MIT" 3120 + }, 3121 + "node_modules/@rolldown/binding-android-arm64": { 3122 + "version": "1.1.5", 3123 + "resolved": "https://registry.npmjs.org/@rolldown/binding-android-arm64/-/binding-android-arm64-1.1.5.tgz", 3124 + "integrity": "sha512-lZg8fqIv2v7FF237bwMgzGZEJvGL79/s5knJ/i6FmsGF4XXlzccZ4jb+TrFIxtSSxFtIpdsgrPZeMk1I9AFcyQ==", 3125 + "cpu": [ 3126 + "arm64" 3127 + ], 3128 + "dev": true, 3129 + "license": "MIT", 3130 + "optional": true, 3131 + "os": [ 3132 + "android" 3133 + ], 3134 + "engines": { 3135 + "node": "^20.19.0 || >=22.12.0" 3136 + } 3137 + }, 3138 + "node_modules/@rolldown/binding-darwin-arm64": { 3139 + "version": "1.1.5", 3140 + "resolved": "https://registry.npmjs.org/@rolldown/binding-darwin-arm64/-/binding-darwin-arm64-1.1.5.tgz", 3141 + "integrity": "sha512-51Bnx9pNiMRKSUNtBfySkNJ9vMU9Hh3I1ozDd6gyPPYzaXCfnptUcEZxXGYFn+ul2dtcMUiqGR1Yai2K10uoTw==", 3142 + "cpu": [ 3143 + "arm64" 3144 + ], 3145 + "dev": true, 3146 + "license": "MIT", 3147 + "optional": true, 3148 + "os": [ 3149 + "darwin" 3150 + ], 3151 + "engines": { 3152 + "node": "^20.19.0 || >=22.12.0" 3153 + } 3154 + }, 3155 + "node_modules/@rolldown/binding-darwin-x64": { 3156 + "version": "1.1.5", 3157 + "resolved": "https://registry.npmjs.org/@rolldown/binding-darwin-x64/-/binding-darwin-x64-1.1.5.tgz", 3158 + "integrity": "sha512-Tm+gbfC0aHu1tBA/JvKQh32S0K6YgCHkiAF4/W6xX0K0RmNuc94VeK419dJoE65R5aRxmo+noZQSWrAMF6yb6g==", 3159 + "cpu": [ 3160 + "x64" 3161 + ], 3162 + "dev": true, 3163 + "license": "MIT", 3164 + "optional": true, 3165 + "os": [ 3166 + "darwin" 3167 + ], 3168 + "engines": { 3169 + "node": "^20.19.0 || >=22.12.0" 3170 + } 3171 + }, 3172 + "node_modules/@rolldown/binding-freebsd-x64": { 3173 + "version": "1.1.5", 3174 + "resolved": "https://registry.npmjs.org/@rolldown/binding-freebsd-x64/-/binding-freebsd-x64-1.1.5.tgz", 3175 + "integrity": "sha512-JMzDKCCXq93YccG5gz3hvOs1oXRKAf0XYpfOS88e+wZrC8Iugj6j68867vrYZkvpDDpKn/KoKORThmchMpF6TA==", 3176 + "cpu": [ 3177 + "x64" 3178 + ], 3179 + "dev": true, 3180 + "license": "MIT", 3181 + "optional": true, 3182 + "os": [ 3183 + "freebsd" 3184 + ], 3185 + "engines": { 3186 + "node": "^20.19.0 || >=22.12.0" 3187 + } 3188 + }, 3189 + "node_modules/@rolldown/binding-linux-arm-gnueabihf": { 3190 + "version": "1.1.5", 3191 + "resolved": "https://registry.npmjs.org/@rolldown/binding-linux-arm-gnueabihf/-/binding-linux-arm-gnueabihf-1.1.5.tgz", 3192 + "integrity": "sha512-uML21j2K5TfPGutKxub+M+nLjZIrWjXQ5Grx4lCe/nimTj9B4L63zHpjXLl4y0L3mcm2htEQIb06oCG/szerNw==", 3193 + "cpu": [ 3194 + "arm" 3195 + ], 3196 + "dev": true, 3197 + "license": "MIT", 3198 + "optional": true, 3199 + "os": [ 3200 + "linux" 3201 + ], 3202 + "engines": { 3203 + "node": "^20.19.0 || >=22.12.0" 3204 + } 3205 + }, 3206 + "node_modules/@rolldown/binding-linux-arm64-gnu": { 3207 + "version": "1.1.5", 3208 + "resolved": "https://registry.npmjs.org/@rolldown/binding-linux-arm64-gnu/-/binding-linux-arm64-gnu-1.1.5.tgz", 3209 + "integrity": "sha512-navSiuTMogvnQoZoM/v+l3ZWo50/NTwSHSzheABx/RCnmUPaKwq9qSo4Br2OYRs21+Fz8uFqITZM3H4opOB0/Q==", 3210 + "cpu": [ 3211 + "arm64" 3212 + ], 3213 + "dev": true, 3214 + "license": "MIT", 3215 + "optional": true, 3216 + "os": [ 3217 + "linux" 3218 + ], 3219 + "engines": { 3220 + "node": "^20.19.0 || >=22.12.0" 3221 + } 3222 + }, 3223 + "node_modules/@rolldown/binding-linux-arm64-musl": { 3224 + "version": "1.1.5", 3225 + "resolved": "https://registry.npmjs.org/@rolldown/binding-linux-arm64-musl/-/binding-linux-arm64-musl-1.1.5.tgz", 3226 + "integrity": "sha512-lAryqH7IteztmCXQXk0etKj4wBQ7Gx5S6LjKhsgp9zb8I5bsuvU/2llH1hDQcjsFeqIsovMVN339/8pUDDBXxA==", 3227 + "cpu": [ 3228 + "arm64" 3229 + ], 3230 + "dev": true, 3231 + "license": "MIT", 3232 + "optional": true, 3233 + "os": [ 3234 + "linux" 3235 + ], 3236 + "engines": { 3237 + "node": "^20.19.0 || >=22.12.0" 3238 + } 3239 + }, 3240 + "node_modules/@rolldown/binding-linux-ppc64-gnu": { 3241 + "version": "1.1.5", 3242 + "resolved": "https://registry.npmjs.org/@rolldown/binding-linux-ppc64-gnu/-/binding-linux-ppc64-gnu-1.1.5.tgz", 3243 + "integrity": "sha512-fsK/sNBnxzBlL4O1JNrZakVQxPspqpED5dLtNsZS9oOKmtSpdNIzxH2kkol5HYTWJN47sE20ztMJPxfZ89qGOg==", 3244 + "cpu": [ 3245 + "ppc64" 3246 + ], 3247 + "dev": true, 3248 + "license": "MIT", 3249 + "optional": true, 3250 + "os": [ 3251 + "linux" 3252 + ], 3253 + "engines": { 3254 + "node": "^20.19.0 || >=22.12.0" 3255 + } 3256 + }, 3257 + "node_modules/@rolldown/binding-linux-s390x-gnu": { 3258 + "version": "1.1.5", 3259 + "resolved": "https://registry.npmjs.org/@rolldown/binding-linux-s390x-gnu/-/binding-linux-s390x-gnu-1.1.5.tgz", 3260 + "integrity": "sha512-gLYb4BIadlfTOYT5gO503n8zQjXflgzpD0FcyKh0Mzx3rqCZKnHoJWV9xe1KXUJ5lx2JfcSHr/mhzS0PC/McAA==", 3261 + "cpu": [ 3262 + "s390x" 3263 + ], 3264 + "dev": true, 3265 + "license": "MIT", 3266 + "optional": true, 3267 + "os": [ 3268 + "linux" 3269 + ], 3270 + "engines": { 3271 + "node": "^20.19.0 || >=22.12.0" 3272 + } 3273 + }, 3274 + "node_modules/@rolldown/binding-linux-x64-gnu": { 3275 + "version": "1.1.5", 3276 + "resolved": "https://registry.npmjs.org/@rolldown/binding-linux-x64-gnu/-/binding-linux-x64-gnu-1.1.5.tgz", 3277 + "integrity": "sha512-FjcpEKUyJygHgs1o50VYNvkt5+7Le/VEdYt0AkRpkL33MnyQfwr8l5mXwMmfmTbyMPr5vJLC+8/Gd9gXnwU1QQ==", 3278 + "cpu": [ 3279 + "x64" 3280 + ], 3281 + "dev": true, 3282 + "license": "MIT", 3283 + "optional": true, 3284 + "os": [ 3285 + "linux" 3286 + ], 3287 + "engines": { 3288 + "node": "^20.19.0 || >=22.12.0" 3289 + } 3290 + }, 3291 + "node_modules/@rolldown/binding-linux-x64-musl": { 3292 + "version": "1.1.5", 3293 + "resolved": "https://registry.npmjs.org/@rolldown/binding-linux-x64-musl/-/binding-linux-x64-musl-1.1.5.tgz", 3294 + "integrity": "sha512-Me+PfPI2TMeOQk0gYWfLQZtTktrmzbr8cDboqX83XKc7UrgAi55gF+2dUkWdxd19n55Essp2yeca+O9N5rBxHg==", 3295 + "cpu": [ 3296 + "x64" 3297 + ], 3298 + "dev": true, 3299 + "license": "MIT", 3300 + "optional": true, 3301 + "os": [ 3302 + "linux" 3303 + ], 3304 + "engines": { 3305 + "node": "^20.19.0 || >=22.12.0" 3306 + } 3307 + }, 3308 + "node_modules/@rolldown/binding-openharmony-arm64": { 3309 + "version": "1.1.5", 3310 + "resolved": "https://registry.npmjs.org/@rolldown/binding-openharmony-arm64/-/binding-openharmony-arm64-1.1.5.tgz", 3311 + "integrity": "sha512-yc5WrLzXks6zCQfn9Oxr8pORKyl/pF+QjHmW/Qx3qu0oyrrNC+y2JLTU1E2rcWYAmzlnqngWXHQjy51VzW70Vw==", 3312 + "cpu": [ 3313 + "arm64" 3314 + ], 3315 + "dev": true, 3316 + "license": "MIT", 3317 + "optional": true, 3318 + "os": [ 3319 + "openharmony" 3320 + ], 3321 + "engines": { 3322 + "node": "^20.19.0 || >=22.12.0" 3323 + } 3324 + }, 3325 + "node_modules/@rolldown/binding-wasm32-wasi": { 3326 + "version": "1.1.5", 3327 + "resolved": "https://registry.npmjs.org/@rolldown/binding-wasm32-wasi/-/binding-wasm32-wasi-1.1.5.tgz", 3328 + "integrity": "sha512-VbQGPX2b4r48TAMIM2cjgluIM1HYutm4pcTEJsle7iEP7sB1dFqtPLBVbdLAZCxy1txCcPxf4QFf4v8uvltPqA==", 3329 + "cpu": [ 3330 + "wasm32" 3331 + ], 3332 + "dev": true, 3333 + "license": "MIT", 3334 + "optional": true, 3335 + "dependencies": { 3336 + "@emnapi/core": "1.11.1", 3337 + "@emnapi/runtime": "1.11.1", 3338 + "@napi-rs/wasm-runtime": "^1.1.6" 3339 + }, 3340 + "engines": { 3341 + "node": "^20.19.0 || >=22.12.0" 3342 + } 3343 + }, 3344 + "node_modules/@rolldown/binding-wasm32-wasi/node_modules/@emnapi/runtime": { 3345 + "version": "1.11.1", 3346 + "resolved": "https://registry.npmjs.org/@emnapi/runtime/-/runtime-1.11.1.tgz", 3347 + "integrity": "sha512-vgj7R3y3Wgx24IQaGPA/R6YFXLHVMOZ0uVEyIQPaWs+rd1AzfEMXlAC22FYwO1XkKR6NPsq7mUandH8oIRdZFw==", 3348 + "dev": true, 3349 + "license": "MIT", 3350 + "optional": true, 3351 + "dependencies": { 3352 + "tslib": "^2.4.0" 3353 + } 3354 + }, 3355 + "node_modules/@rolldown/binding-win32-arm64-msvc": { 3356 + "version": "1.1.5", 3357 + "resolved": "https://registry.npmjs.org/@rolldown/binding-win32-arm64-msvc/-/binding-win32-arm64-msvc-1.1.5.tgz", 3358 + "integrity": "sha512-gHv82k63z4qpV5+Q1y/12KrK0ltWBukVDI8nZcbT7Tt/ZlOIVwppazneq0F93oDxTo3IgAMEDIoQh3E2n6mVsw==", 3359 + "cpu": [ 3360 + "arm64" 3361 + ], 3362 + "dev": true, 3363 + "license": "MIT", 3364 + "optional": true, 3365 + "os": [ 3366 + "win32" 3367 + ], 3368 + "engines": { 3369 + "node": "^20.19.0 || >=22.12.0" 3370 + } 3371 + }, 3372 + "node_modules/@rolldown/binding-win32-x64-msvc": { 3373 + "version": "1.1.5", 3374 + "resolved": "https://registry.npmjs.org/@rolldown/binding-win32-x64-msvc/-/binding-win32-x64-msvc-1.1.5.tgz", 3375 + "integrity": "sha512-tTZuDBPw85tEN5PQi1pnEBzDy0Z49HtScLAbD5t6hyeU92A95pRWaSMw1GZZi/RwgSgUIl0xrSlXIT/9QzvYSA==", 3376 + "cpu": [ 3377 + "x64" 3378 + ], 3379 + "dev": true, 3380 + "license": "MIT", 3381 + "optional": true, 3382 + "os": [ 3383 + "win32" 3384 + ], 3385 + "engines": { 3386 + "node": "^20.19.0 || >=22.12.0" 3387 + } 3388 + }, 3389 + "node_modules/@rolldown/pluginutils": { 3390 + "version": "1.0.1", 3391 + "resolved": "https://registry.npmjs.org/@rolldown/pluginutils/-/pluginutils-1.0.1.tgz", 3392 + "integrity": "sha512-2j9bGt5Jh8hj+vPtgzPtl72j0yRxHAyumoo6TNfAjsLB04UtpSvPbPcDcBMxz7n+9CYB0c1GxQFxYRg2jimqGw==", 3393 + "dev": true, 3394 + "license": "MIT" 3395 + }, 3396 + "node_modules/@rollup/plugin-babel": { 3397 + "version": "6.1.0", 3398 + "resolved": "https://registry.npmjs.org/@rollup/plugin-babel/-/plugin-babel-6.1.0.tgz", 3399 + "integrity": "sha512-dFZNuFD2YRcoomP4oYf+DvQNSUA9ih+A3vUqopQx5EdtPGo3WBnQcI/S8pwpz91UsGfL0HsMSOlaMld8HrbubA==", 3400 + "dev": true, 3401 + "license": "MIT", 3402 + "dependencies": { 3403 + "@babel/helper-module-imports": "^7.18.6", 3404 + "@rollup/pluginutils": "^5.0.1" 3405 + }, 3406 + "engines": { 3407 + "node": ">=14.0.0" 3408 + }, 3409 + "peerDependencies": { 3410 + "@babel/core": "^7.0.0", 3411 + "@types/babel__core": "^7.1.9", 3412 + "rollup": "^1.20.0||^2.0.0||^3.0.0||^4.0.0" 3413 + }, 3414 + "peerDependenciesMeta": { 3415 + "@types/babel__core": { 3416 + "optional": true 3417 + }, 3418 + "rollup": { 3419 + "optional": true 3420 + } 3421 + } 3422 + }, 3423 + "node_modules/@rollup/plugin-node-resolve": { 3424 + "version": "16.0.3", 3425 + "resolved": "https://registry.npmjs.org/@rollup/plugin-node-resolve/-/plugin-node-resolve-16.0.3.tgz", 3426 + "integrity": "sha512-lUYM3UBGuM93CnMPG1YocWu7X802BrNF3jW2zny5gQyLQgRFJhV1Sq0Zi74+dh/6NBx1DxFC4b4GXg9wUCG5Qg==", 3427 + "dev": true, 3428 + "license": "MIT", 3429 + "dependencies": { 3430 + "@rollup/pluginutils": "^5.0.1", 3431 + "@types/resolve": "1.20.2", 3432 + "deepmerge": "^4.2.2", 3433 + "is-module": "^1.0.0", 3434 + "resolve": "^1.22.1" 3435 + }, 3436 + "engines": { 3437 + "node": ">=14.0.0" 3438 + }, 3439 + "peerDependencies": { 3440 + "rollup": "^2.78.0||^3.0.0||^4.0.0" 3441 + }, 3442 + "peerDependenciesMeta": { 3443 + "rollup": { 3444 + "optional": true 3445 + } 3446 + } 3447 + }, 3448 + "node_modules/@rollup/plugin-replace": { 3449 + "version": "6.0.3", 3450 + "resolved": "https://registry.npmjs.org/@rollup/plugin-replace/-/plugin-replace-6.0.3.tgz", 3451 + "integrity": "sha512-J4RZarRvQAm5IF0/LwUUg+obsm+xZhYnbMXmXROyoSE1ATJe3oXSb9L5MMppdxP2ylNSjv6zFBwKYjcKMucVfA==", 3452 + "dev": true, 3453 + "license": "MIT", 3454 + "dependencies": { 3455 + "@rollup/pluginutils": "^5.0.1", 3456 + "magic-string": "^0.30.3" 3457 + }, 3458 + "engines": { 3459 + "node": ">=14.0.0" 3460 + }, 3461 + "peerDependencies": { 3462 + "rollup": "^1.20.0||^2.0.0||^3.0.0||^4.0.0" 3463 + }, 3464 + "peerDependenciesMeta": { 3465 + "rollup": { 3466 + "optional": true 3467 + } 3468 + } 3469 + }, 3470 + "node_modules/@rollup/plugin-terser": { 3471 + "version": "1.0.0", 3472 + "resolved": "https://registry.npmjs.org/@rollup/plugin-terser/-/plugin-terser-1.0.0.tgz", 3473 + "integrity": "sha512-FnCxhTBx6bMOYQrar6C8h3scPt8/JwIzw3+AJ2K++6guogH5fYaIFia+zZuhqv0eo1RN7W1Pz630SyvLbDjhtQ==", 3474 + "dev": true, 3475 + "license": "MIT", 3476 + "dependencies": { 3477 + "serialize-javascript": "^7.0.3", 3478 + "smob": "^1.0.0", 3479 + "terser": "^5.17.4" 3480 + }, 3481 + "engines": { 3482 + "node": ">=20.0.0" 3483 + }, 3484 + "peerDependencies": { 3485 + "rollup": "^2.0.0||^3.0.0||^4.0.0" 3486 + }, 3487 + "peerDependenciesMeta": { 3488 + "rollup": { 3489 + "optional": true 3490 + } 3491 + } 3492 + }, 3493 + "node_modules/@rollup/pluginutils": { 3494 + "version": "5.4.0", 3495 + "resolved": "https://registry.npmjs.org/@rollup/pluginutils/-/pluginutils-5.4.0.tgz", 3496 + "integrity": "sha512-MfPp06CjRLfXQ3wY0R8vJDYBy/MvVcc9OulEfR0B8Iv9ko+GCNaRZ+EpJYFl27LhKsZK0o420sYCRHCjfCgeUg==", 3497 + "dev": true, 3498 + "license": "MIT", 3499 + "dependencies": { 3500 + "@types/estree": "^1.0.0", 3501 + "estree-walker": "^2.0.2", 3502 + "picomatch": "^4.0.2" 3503 + }, 3504 + "engines": { 3505 + "node": ">=14.0.0" 3506 + }, 3507 + "peerDependencies": { 3508 + "rollup": "^1.20.0||^2.0.0||^3.0.0||^4.0.0" 3509 + }, 3510 + "peerDependenciesMeta": { 3511 + "rollup": { 3512 + "optional": true 3513 + } 3514 + } 3515 + }, 3516 + "node_modules/@rollup/rollup-android-arm-eabi": { 3517 + "version": "4.62.2", 3518 + "resolved": "https://registry.npmjs.org/@rollup/rollup-android-arm-eabi/-/rollup-android-arm-eabi-4.62.2.tgz", 3519 + "integrity": "sha512-6o7ZLZK+BeenkZCFNDXqpbjw9bD6nuWonvS/lwQJp7NoVVxm6p3qE7qQ5jGuBjiFsgvqjD8mZAU5oWxTmbOeOg==", 3520 + "cpu": [ 3521 + "arm" 3522 + ], 3523 + "dev": true, 3524 + "license": "MIT", 3525 + "optional": true, 3526 + "os": [ 3527 + "android" 3528 + ] 3529 + }, 3530 + "node_modules/@rollup/rollup-android-arm64": { 3531 + "version": "4.62.2", 3532 + "resolved": "https://registry.npmjs.org/@rollup/rollup-android-arm64/-/rollup-android-arm64-4.62.2.tgz", 3533 + "integrity": "sha512-BaH7BllCACHoH1LguOU56UItGfUWjujlO65kS9LAodViaN4bwIKd7oeW/ZHJ/4ljr/7MIiENnNy3HJ0zXv8Zkw==", 3534 + "cpu": [ 3535 + "arm64" 3536 + ], 3537 + "dev": true, 3538 + "license": "MIT", 3539 + "optional": true, 3540 + "os": [ 3541 + "android" 3542 + ] 3543 + }, 3544 + "node_modules/@rollup/rollup-darwin-arm64": { 3545 + "version": "4.62.2", 3546 + "resolved": "https://registry.npmjs.org/@rollup/rollup-darwin-arm64/-/rollup-darwin-arm64-4.62.2.tgz", 3547 + "integrity": "sha512-v39RCCvj4He82I9sFmk+M1VZ0PLM9sfsLVikjfx2hYBNALhrrOR2D3JjQA6AhlaSOgcR+RzrKY7e1+bT6SUO/A==", 3548 + "cpu": [ 3549 + "arm64" 3550 + ], 3551 + "dev": true, 3552 + "license": "MIT", 3553 + "optional": true, 3554 + "os": [ 3555 + "darwin" 3556 + ] 3557 + }, 3558 + "node_modules/@rollup/rollup-darwin-x64": { 3559 + "version": "4.62.2", 3560 + "resolved": "https://registry.npmjs.org/@rollup/rollup-darwin-x64/-/rollup-darwin-x64-4.62.2.tgz", 3561 + "integrity": "sha512-yl0y2vq3S3lHeuXhEdss6TWfKW8vkujImO12tn4ZkG/4oghr09LvdYm2RElVjokTQiUvDUGXLGsYeLqUMCKpGA==", 3562 + "cpu": [ 3563 + "x64" 3564 + ], 3565 + "dev": true, 3566 + "license": "MIT", 3567 + "optional": true, 3568 + "os": [ 3569 + "darwin" 3570 + ] 3571 + }, 3572 + "node_modules/@rollup/rollup-freebsd-arm64": { 3573 + "version": "4.62.2", 3574 + "resolved": "https://registry.npmjs.org/@rollup/rollup-freebsd-arm64/-/rollup-freebsd-arm64-4.62.2.tgz", 3575 + "integrity": "sha512-tT4pvt4qXD+vEoezupCWi+a1F0vvDiksiHc+PxRlYTOH1I6/X4id9jPxTP+Fg+545euaFT1jJVs4CEdHZAU1vw==", 3576 + "cpu": [ 3577 + "arm64" 3578 + ], 3579 + "dev": true, 3580 + "license": "MIT", 3581 + "optional": true, 3582 + "os": [ 3583 + "freebsd" 3584 + ] 3585 + }, 3586 + "node_modules/@rollup/rollup-freebsd-x64": { 3587 + "version": "4.62.2", 3588 + "resolved": "https://registry.npmjs.org/@rollup/rollup-freebsd-x64/-/rollup-freebsd-x64-4.62.2.tgz", 3589 + "integrity": "sha512-6nU5F2wCW+qvCBhTn1pdIU3bzsIoF7EUwsCDRxilWGprQR6yd508YnH9+OKFCwpfS8pjZqDUmnCAr7exax0XCg==", 3590 + "cpu": [ 3591 + "x64" 3592 + ], 3593 + "dev": true, 3594 + "license": "MIT", 3595 + "optional": true, 3596 + "os": [ 3597 + "freebsd" 3598 + ] 3599 + }, 3600 + "node_modules/@rollup/rollup-linux-arm-gnueabihf": { 3601 + "version": "4.62.2", 3602 + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm-gnueabihf/-/rollup-linux-arm-gnueabihf-4.62.2.tgz", 3603 + "integrity": "sha512-n1GJHPOvpIfhi3TmrCeh6S6URt9BFCt0KQE3qvexyGCTAKpR4Lg+eWvNZEqu7epxwus/8ElT3hacYEucm49SZg==", 3604 + "cpu": [ 3605 + "arm" 3606 + ], 3607 + "dev": true, 3608 + "license": "MIT", 3609 + "optional": true, 3610 + "os": [ 3611 + "linux" 3612 + ] 3613 + }, 3614 + "node_modules/@rollup/rollup-linux-arm-musleabihf": { 3615 + "version": "4.62.2", 3616 + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm-musleabihf/-/rollup-linux-arm-musleabihf-4.62.2.tgz", 3617 + "integrity": "sha512-JqgflS8wEB+UXV/vS1RpRbifGBeN4D5lz8D8oOFbFZw4vedvdOgCFAjfBmIMdW3yL10XpQQ0Ambepw6MXrhOnA==", 3618 + "cpu": [ 3619 + "arm" 3620 + ], 3621 + "dev": true, 3622 + "license": "MIT", 3623 + "optional": true, 3624 + "os": [ 3625 + "linux" 3626 + ] 3627 + }, 3628 + "node_modules/@rollup/rollup-linux-arm64-gnu": { 3629 + "version": "4.62.2", 3630 + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm64-gnu/-/rollup-linux-arm64-gnu-4.62.2.tgz", 3631 + "integrity": "sha512-wnFJkogWvN4jm/hQRF2UBaeUmk20j5+DmHvoyWii2b8HJDyvz1MF2OU/6ynXt2KR63rbZLWkFpoytpdc/yBuSA==", 3632 + "cpu": [ 3633 + "arm64" 3634 + ], 3635 + "dev": true, 3636 + "license": "MIT", 3637 + "optional": true, 3638 + "os": [ 3639 + "linux" 3640 + ] 3641 + }, 3642 + "node_modules/@rollup/rollup-linux-arm64-musl": { 3643 + "version": "4.62.2", 3644 + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm64-musl/-/rollup-linux-arm64-musl-4.62.2.tgz", 3645 + "integrity": "sha512-HVu2bp0zhvJ8xHEV9+UUs7S90VadmBSY3LcIMvozbPo4AuMGDWlz3ymHLHZPX4hR67TKTt8Qp5PJ5RBg/i+RMQ==", 3646 + "cpu": [ 3647 + "arm64" 3648 + ], 3649 + "dev": true, 3650 + "license": "MIT", 3651 + "optional": true, 3652 + "os": [ 3653 + "linux" 3654 + ] 3655 + }, 3656 + "node_modules/@rollup/rollup-linux-loong64-gnu": { 3657 + "version": "4.62.2", 3658 + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-loong64-gnu/-/rollup-linux-loong64-gnu-4.62.2.tgz", 3659 + "integrity": "sha512-mQqqAV8QaoSgr9I2fKDLY2BAVvmKjWoGiu/cSYQonsLvtqwEn1E4QYfnCOcp5zoEqNhsDYin1s6jx/VJmrxlZg==", 3660 + "cpu": [ 3661 + "loong64" 3662 + ], 3663 + "dev": true, 3664 + "license": "MIT", 3665 + "optional": true, 3666 + "os": [ 3667 + "linux" 3668 + ] 3669 + }, 3670 + "node_modules/@rollup/rollup-linux-loong64-musl": { 3671 + "version": "4.62.2", 3672 + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-loong64-musl/-/rollup-linux-loong64-musl-4.62.2.tgz", 3673 + "integrity": "sha512-IxKLoxCQ2IWi6bT2akyDUBGsOImDKB+sPp4EsTmwFQ/fMwpCKm8uLSSgP/Kx/QYUgKis6SEZ5/Nlhup0DIA0PQ==", 3674 + "cpu": [ 3675 + "loong64" 3676 + ], 3677 + "dev": true, 3678 + "license": "MIT", 3679 + "optional": true, 3680 + "os": [ 3681 + "linux" 3682 + ] 3683 + }, 3684 + "node_modules/@rollup/rollup-linux-ppc64-gnu": { 3685 + "version": "4.62.2", 3686 + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-ppc64-gnu/-/rollup-linux-ppc64-gnu-4.62.2.tgz", 3687 + "integrity": "sha512-Mk5ha2RQSgyFfmYYLkBpPnUk8D8FriBxesO1u9O75X0mHgXL1UQcH5Itl2lurWL2tj0RxV9b9tJgipac0hRY9A==", 3688 + "cpu": [ 3689 + "ppc64" 3690 + ], 3691 + "dev": true, 3692 + "license": "MIT", 3693 + "optional": true, 3694 + "os": [ 3695 + "linux" 3696 + ] 3697 + }, 3698 + "node_modules/@rollup/rollup-linux-ppc64-musl": { 3699 + "version": "4.62.2", 3700 + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-ppc64-musl/-/rollup-linux-ppc64-musl-4.62.2.tgz", 3701 + "integrity": "sha512-CjvEnqJL/0/TQ3TXX3OPIJ/kmBellrWd4heXUmHeJlTnmwjKpSJzoehLaL6Xk0ZnMHBu9dZuFADNOrtjF4v+2w==", 3702 + "cpu": [ 3703 + "ppc64" 3704 + ], 3705 + "dev": true, 3706 + "license": "MIT", 3707 + "optional": true, 3708 + "os": [ 3709 + "linux" 3710 + ] 3711 + }, 3712 + "node_modules/@rollup/rollup-linux-riscv64-gnu": { 3713 + "version": "4.62.2", 3714 + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-riscv64-gnu/-/rollup-linux-riscv64-gnu-4.62.2.tgz", 3715 + "integrity": "sha512-1SiZbzwdkaDURsew/tSOrooKiYy7EQGT6m8ufavAi9NEyQb/6VuIxFXAL1fqa4iZe3g4NbNk4P7J32z2tw5Mgg==", 3716 + "cpu": [ 3717 + "riscv64" 3718 + ], 3719 + "dev": true, 3720 + "license": "MIT", 3721 + "optional": true, 3722 + "os": [ 3723 + "linux" 3724 + ] 3725 + }, 3726 + "node_modules/@rollup/rollup-linux-riscv64-musl": { 3727 + "version": "4.62.2", 3728 + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-riscv64-musl/-/rollup-linux-riscv64-musl-4.62.2.tgz", 3729 + "integrity": "sha512-nQts12zJ3NQRoE6uYljOH89v7szzLDvG2JD/vsX+vGXU8w/At1GowTZ5/7qeFQ8m7L55rpR8Okugnuo5bgjy2Q==", 3730 + "cpu": [ 3731 + "riscv64" 3732 + ], 3733 + "dev": true, 3734 + "license": "MIT", 3735 + "optional": true, 3736 + "os": [ 3737 + "linux" 3738 + ] 3739 + }, 3740 + "node_modules/@rollup/rollup-linux-s390x-gnu": { 3741 + "version": "4.62.2", 3742 + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-s390x-gnu/-/rollup-linux-s390x-gnu-4.62.2.tgz", 3743 + "integrity": "sha512-E9/ll019jhPIJgpzfZoIkBGhcz+kKNgVWYRY0zr9srBdPPFVpvOKW8VaJKUbeK+eZXyQF9ltME+Kk6affeaPgg==", 3744 + "cpu": [ 3745 + "s390x" 3746 + ], 3747 + "dev": true, 3748 + "license": "MIT", 3749 + "optional": true, 3750 + "os": [ 3751 + "linux" 3752 + ] 3753 + }, 3754 + "node_modules/@rollup/rollup-linux-x64-gnu": { 3755 + "version": "4.62.2", 3756 + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-x64-gnu/-/rollup-linux-x64-gnu-4.62.2.tgz", 3757 + "integrity": "sha512-5BqxR/pshjey51iliyzTD5Xi3EN0aLmQ2lZ3lvefVV9c82BvrLo2/6OT55iifpWBufs6kdwWbuOKS841DrmK9A==", 3758 + "cpu": [ 3759 + "x64" 3760 + ], 3761 + "dev": true, 3762 + "license": "MIT", 3763 + "optional": true, 3764 + "os": [ 3765 + "linux" 3766 + ] 3767 + }, 3768 + "node_modules/@rollup/rollup-linux-x64-musl": { 3769 + "version": "4.62.2", 3770 + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-x64-musl/-/rollup-linux-x64-musl-4.62.2.tgz", 3771 + "integrity": "sha512-uNN83XxQrRAh/w0/pmAfibcwyb6YWt4gP+dpnQKPVJshAloQ785ii8CT8ZCIxkGg9opVsvAlGhFitSm6D1Jjpg==", 3772 + "cpu": [ 3773 + "x64" 3774 + ], 3775 + "dev": true, 3776 + "license": "MIT", 3777 + "optional": true, 3778 + "os": [ 3779 + "linux" 3780 + ] 3781 + }, 3782 + "node_modules/@rollup/rollup-openbsd-x64": { 3783 + "version": "4.62.2", 3784 + "resolved": "https://registry.npmjs.org/@rollup/rollup-openbsd-x64/-/rollup-openbsd-x64-4.62.2.tgz", 3785 + "integrity": "sha512-srjEIxSH3LRnJN6THczDHWQplqEMFiAJrTab0msUryh9kwNpkICf3Ea6q6MN/2cZwRFUNx5w+h6Hpi4QuHS6Zg==", 3786 + "cpu": [ 3787 + "x64" 3788 + ], 3789 + "dev": true, 3790 + "license": "MIT", 3791 + "optional": true, 3792 + "os": [ 3793 + "openbsd" 3794 + ] 3795 + }, 3796 + "node_modules/@rollup/rollup-openharmony-arm64": { 3797 + "version": "4.62.2", 3798 + "resolved": "https://registry.npmjs.org/@rollup/rollup-openharmony-arm64/-/rollup-openharmony-arm64-4.62.2.tgz", 3799 + "integrity": "sha512-8hOJnxgbyObnCm5AlRA3A931xX19xq80RjVTKgJOvEKWqJruP/Uf12IbAOaDjjEXYRewwHLfmF0YRIdK3OwKWA==", 3800 + "cpu": [ 3801 + "arm64" 3802 + ], 3803 + "dev": true, 3804 + "license": "MIT", 3805 + "optional": true, 3806 + "os": [ 3807 + "openharmony" 3808 + ] 3809 + }, 3810 + "node_modules/@rollup/rollup-win32-arm64-msvc": { 3811 + "version": "4.62.2", 3812 + "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-arm64-msvc/-/rollup-win32-arm64-msvc-4.62.2.tgz", 3813 + "integrity": "sha512-mmF4AY1i0hG/bLWUctUq59gtmgaSIRa3cu/A3JFRp/sCNEme2bgDEiDS22P9FbnJB8NJNF4jPJiSP5RHQpUTDg==", 3814 + "cpu": [ 3815 + "arm64" 3816 + ], 3817 + "dev": true, 3818 + "license": "MIT", 3819 + "optional": true, 3820 + "os": [ 3821 + "win32" 3822 + ] 3823 + }, 3824 + "node_modules/@rollup/rollup-win32-ia32-msvc": { 3825 + "version": "4.62.2", 3826 + "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-ia32-msvc/-/rollup-win32-ia32-msvc-4.62.2.tgz", 3827 + "integrity": "sha512-DZgkknc6jhHrk46V25vbAM0zZkyP0nSDkJB8/dRkLTxv470dOmWDqGoEJl/9A0dFfS7yE3REOwNDxpHwSLSt0Q==", 3828 + "cpu": [ 3829 + "ia32" 3830 + ], 3831 + "dev": true, 3832 + "license": "MIT", 3833 + "optional": true, 3834 + "os": [ 3835 + "win32" 3836 + ] 3837 + }, 3838 + "node_modules/@rollup/rollup-win32-x64-gnu": { 3839 + "version": "4.62.2", 3840 + "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-x64-gnu/-/rollup-win32-x64-gnu-4.62.2.tgz", 3841 + "integrity": "sha512-T6xr6ucWSFto+VGajA8YH26LdpHRuP4YLHEKAtCWvJDOlnmWcDZVCI2Jmjr+IFHDlt2zRaTAKE4tfjTaWLgJBg==", 3842 + "cpu": [ 3843 + "x64" 3844 + ], 3845 + "dev": true, 3846 + "license": "MIT", 3847 + "optional": true, 3848 + "os": [ 3849 + "win32" 3850 + ] 3851 + }, 3852 + "node_modules/@rollup/rollup-win32-x64-msvc": { 3853 + "version": "4.62.2", 3854 + "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-x64-msvc/-/rollup-win32-x64-msvc-4.62.2.tgz", 3855 + "integrity": "sha512-BfzEnDJOt9T8M989/lA37EcJgat01wLRnoi5dQf3QzOH7jzpqTAzdDbVfRljVr5r+jzKqpbHeyOfAaXxAd0PAA==", 3856 + "cpu": [ 3857 + "x64" 3858 + ], 3859 + "dev": true, 3860 + "license": "MIT", 3861 + "optional": true, 3862 + "os": [ 3863 + "win32" 3864 + ] 3865 + }, 3866 + "node_modules/@simplewebauthn/browser": { 3867 + "version": "13.3.0", 3868 + "resolved": "https://registry.npmjs.org/@simplewebauthn/browser/-/browser-13.3.0.tgz", 3869 + "integrity": "sha512-BE/UWv6FOToAdVk0EokzkqQQDOWtNydYlY6+OrmiZ5SCNmb41VehttboTetUM3T/fr6EAFYVXjz4My2wg230rQ==", 3870 + "license": "MIT" 3871 + }, 3872 + "node_modules/@simplewebauthn/server": { 3873 + "version": "13.3.2", 3874 + "resolved": "https://registry.npmjs.org/@simplewebauthn/server/-/server-13.3.2.tgz", 3875 + "integrity": "sha512-KEDhfcGP1PAKRVSDjA3npTQFqS2b/srm+ipoNBNHdkzrHAlaRQUTE+a5f4ywsx6thxAw1NU2rYcLEY1949RGbQ==", 3876 + "license": "MIT", 3877 + "dependencies": { 3878 + "@hexagon/base64": "^1.1.27", 3879 + "@levischuck/tiny-cbor": "^0.2.2", 3880 + "@peculiar/asn1-android": "^2.6.0", 3881 + "@peculiar/asn1-ecc": "^2.6.1", 3882 + "@peculiar/asn1-rsa": "^2.6.1", 3883 + "@peculiar/asn1-schema": "^2.6.0", 3884 + "@peculiar/asn1-x509": "^2.6.1", 3885 + "@peculiar/x509": "^1.14.3" 3886 + }, 3887 + "engines": { 3888 + "node": ">=20.0.0" 3889 + } 3890 + }, 3891 + "node_modules/@sindresorhus/is": { 3892 + "version": "7.2.0", 3893 + "resolved": "https://registry.npmjs.org/@sindresorhus/is/-/is-7.2.0.tgz", 3894 + "integrity": "sha512-P1Cz1dWaFfR4IR+U13mqqiGsLFf1KbayybWwdd2vfctdV6hDpUkgCY0nKOLLTMSoRd/jJNjtbqzf13K8DCCXQw==", 3895 + "dev": true, 3896 + "license": "MIT", 3897 + "engines": { 3898 + "node": ">=18" 3899 + }, 3900 + "funding": { 3901 + "url": "https://github.com/sindresorhus/is?sponsor=1" 3902 + } 3903 + }, 3904 + "node_modules/@speed-highlight/core": { 3905 + "version": "1.2.17", 3906 + "resolved": "https://registry.npmjs.org/@speed-highlight/core/-/core-1.2.17.tgz", 3907 + "integrity": "sha512-Z92FwKpCtfaW1V0jTU/fh3QzYEZN8wDwrzRIBoADCJfn4mJCNcJN/XegifX7BDrQ8/h9Xh/JnbyMchL0FqXrkg==", 3908 + "dev": true, 3909 + "license": "CC0-1.0" 3910 + }, 3911 + "node_modules/@tailwindcss/node": { 3912 + "version": "4.3.3", 3913 + "resolved": "https://registry.npmjs.org/@tailwindcss/node/-/node-4.3.3.tgz", 3914 + "integrity": "sha512-/T8IKEsf9VTU6tLjgC7+sv2mOPtQxzE2jMw7u4Tt40Tx+QSZxpzh95/H6cMKoja9XuW7iMdLJYBB0o9G1CaAgg==", 3915 + "dev": true, 3916 + "license": "MIT", 3917 + "dependencies": { 3918 + "@jridgewell/remapping": "^2.3.5", 3919 + "enhanced-resolve": "^5.24.1", 3920 + "jiti": "^2.7.0", 3921 + "lightningcss": "1.32.0", 3922 + "magic-string": "^0.30.21", 3923 + "source-map-js": "^1.2.1", 3924 + "tailwindcss": "4.3.3" 3925 + } 3926 + }, 3927 + "node_modules/@tailwindcss/oxide": { 3928 + "version": "4.3.3", 3929 + "resolved": "https://registry.npmjs.org/@tailwindcss/oxide/-/oxide-4.3.3.tgz", 3930 + "integrity": "sha512-krXjAikiaFSPaK/FkAQT5UTx3VormQaiZ5hBFlJZ9UFQGB/rwg1MZIhHAG9smMQRTdyJxP6Qt5MwMtdyU5FWrA==", 3931 + "dev": true, 3932 + "license": "MIT", 3933 + "engines": { 3934 + "node": ">= 20" 3935 + }, 3936 + "optionalDependencies": { 3937 + "@tailwindcss/oxide-android-arm64": "4.3.3", 3938 + "@tailwindcss/oxide-darwin-arm64": "4.3.3", 3939 + "@tailwindcss/oxide-darwin-x64": "4.3.3", 3940 + "@tailwindcss/oxide-freebsd-x64": "4.3.3", 3941 + "@tailwindcss/oxide-linux-arm-gnueabihf": "4.3.3", 3942 + "@tailwindcss/oxide-linux-arm64-gnu": "4.3.3", 3943 + "@tailwindcss/oxide-linux-arm64-musl": "4.3.3", 3944 + "@tailwindcss/oxide-linux-x64-gnu": "4.3.3", 3945 + "@tailwindcss/oxide-linux-x64-musl": "4.3.3", 3946 + "@tailwindcss/oxide-wasm32-wasi": "4.3.3", 3947 + "@tailwindcss/oxide-win32-arm64-msvc": "4.3.3", 3948 + "@tailwindcss/oxide-win32-x64-msvc": "4.3.3" 3949 + } 3950 + }, 3951 + "node_modules/@tailwindcss/oxide-android-arm64": { 3952 + "version": "4.3.3", 3953 + "resolved": "https://registry.npmjs.org/@tailwindcss/oxide-android-arm64/-/oxide-android-arm64-4.3.3.tgz", 3954 + "integrity": "sha512-Y85A2gmPSkl5Ve5qR86GL4HT509cFqQh1aes9p3sSkyTPwt0Pppf3GkwGe4JPACcRYjgJIEhQgM6dBClnr0NYw==", 3955 + "cpu": [ 3956 + "arm64" 3957 + ], 3958 + "dev": true, 3959 + "license": "MIT", 3960 + "optional": true, 3961 + "os": [ 3962 + "android" 3963 + ], 3964 + "engines": { 3965 + "node": ">= 20" 3966 + } 3967 + }, 3968 + "node_modules/@tailwindcss/oxide-darwin-arm64": { 3969 + "version": "4.3.3", 3970 + "resolved": "https://registry.npmjs.org/@tailwindcss/oxide-darwin-arm64/-/oxide-darwin-arm64-4.3.3.tgz", 3971 + "integrity": "sha512-BiaWatpBcERQFDlOjRDpIVXuFK5PJez5SA4JMg6VYZdBYU+qKfV/vqjcIs+IYmtitf1xYQZTwXvU/8y4lfZUGw==", 3972 + "cpu": [ 3973 + "arm64" 3974 + ], 3975 + "dev": true, 3976 + "license": "MIT", 3977 + "optional": true, 3978 + "os": [ 3979 + "darwin" 3980 + ], 3981 + "engines": { 3982 + "node": ">= 20" 3983 + } 3984 + }, 3985 + "node_modules/@tailwindcss/oxide-darwin-x64": { 3986 + "version": "4.3.3", 3987 + "resolved": "https://registry.npmjs.org/@tailwindcss/oxide-darwin-x64/-/oxide-darwin-x64-4.3.3.tgz", 3988 + "integrity": "sha512-fAeUqfV5ndhxRwai8cXGzdLvul9utWOmeTkv69unv4ZXixjn61Z+p9lCWdwOwA3TYboG3BwdVuN/RDjhBRl0mw==", 3989 + "cpu": [ 3990 + "x64" 3991 + ], 3992 + "dev": true, 3993 + "license": "MIT", 3994 + "optional": true, 3995 + "os": [ 3996 + "darwin" 3997 + ], 3998 + "engines": { 3999 + "node": ">= 20" 4000 + } 4001 + }, 4002 + "node_modules/@tailwindcss/oxide-freebsd-x64": { 4003 + "version": "4.3.3", 4004 + "resolved": "https://registry.npmjs.org/@tailwindcss/oxide-freebsd-x64/-/oxide-freebsd-x64-4.3.3.tgz", 4005 + "integrity": "sha512-iyf5bV6+wnAlflVeEy7R25dupxTNECZN5QMI0qNT6eT+EgaGdZcKhGkr5SdoaWiLJ3spLqIY9VCeSGrwmtg4kw==", 4006 + "cpu": [ 4007 + "x64" 4008 + ], 4009 + "dev": true, 4010 + "license": "MIT", 4011 + "optional": true, 4012 + "os": [ 4013 + "freebsd" 4014 + ], 4015 + "engines": { 4016 + "node": ">= 20" 4017 + } 4018 + }, 4019 + "node_modules/@tailwindcss/oxide-linux-arm-gnueabihf": { 4020 + "version": "4.3.3", 4021 + "resolved": "https://registry.npmjs.org/@tailwindcss/oxide-linux-arm-gnueabihf/-/oxide-linux-arm-gnueabihf-4.3.3.tgz", 4022 + "integrity": "sha512-aAYUprJAJQWWbRrPvtjdroZ56Md+JM8pMiopS6xGEwDfLhqj+2ver2p4nU4Mb3CRqcMmNBjo8KkUgcxhkzVQGQ==", 4023 + "cpu": [ 4024 + "arm" 4025 + ], 4026 + "dev": true, 4027 + "license": "MIT", 4028 + "optional": true, 4029 + "os": [ 4030 + "linux" 4031 + ], 4032 + "engines": { 4033 + "node": ">= 20" 4034 + } 4035 + }, 4036 + "node_modules/@tailwindcss/oxide-linux-arm64-gnu": { 4037 + "version": "4.3.3", 4038 + "resolved": "https://registry.npmjs.org/@tailwindcss/oxide-linux-arm64-gnu/-/oxide-linux-arm64-gnu-4.3.3.tgz", 4039 + "integrity": "sha512-nDxldcEENOxZRzC2uu9jrutZdAAQtb+8WWDCSnWL1zvBk1+FN+x6MtDViPB5AJMfttVCUhehGWus3XBPgatM/w==", 4040 + "cpu": [ 4041 + "arm64" 4042 + ], 4043 + "dev": true, 4044 + "license": "MIT", 4045 + "optional": true, 4046 + "os": [ 4047 + "linux" 4048 + ], 4049 + "engines": { 4050 + "node": ">= 20" 4051 + } 4052 + }, 4053 + "node_modules/@tailwindcss/oxide-linux-arm64-musl": { 4054 + "version": "4.3.3", 4055 + "resolved": "https://registry.npmjs.org/@tailwindcss/oxide-linux-arm64-musl/-/oxide-linux-arm64-musl-4.3.3.tgz", 4056 + "integrity": "sha512-Md44bD6veX/PC5iyF8cDVnw4HBIANZepRZZ7a8DQOvkfo5WUBwcp6iAuCUz23u+4SUkhJlD3eL7hNdW8ezd/kA==", 4057 + "cpu": [ 4058 + "arm64" 4059 + ], 4060 + "dev": true, 4061 + "license": "MIT", 4062 + "optional": true, 4063 + "os": [ 4064 + "linux" 4065 + ], 4066 + "engines": { 4067 + "node": ">= 20" 4068 + } 4069 + }, 4070 + "node_modules/@tailwindcss/oxide-linux-x64-gnu": { 4071 + "version": "4.3.3", 4072 + "resolved": "https://registry.npmjs.org/@tailwindcss/oxide-linux-x64-gnu/-/oxide-linux-x64-gnu-4.3.3.tgz", 4073 + "integrity": "sha512-tx7us1muwOKAKWao2v/GaafFeQboE6aj88vC6ziN2NCGcRm8gWUhwjzg+YdVB1e4boAtdtma4L43onunI6NS4w==", 4074 + "cpu": [ 4075 + "x64" 4076 + ], 4077 + "dev": true, 4078 + "license": "MIT", 4079 + "optional": true, 4080 + "os": [ 4081 + "linux" 4082 + ], 4083 + "engines": { 4084 + "node": ">= 20" 4085 + } 4086 + }, 4087 + "node_modules/@tailwindcss/oxide-linux-x64-musl": { 4088 + "version": "4.3.3", 4089 + "resolved": "https://registry.npmjs.org/@tailwindcss/oxide-linux-x64-musl/-/oxide-linux-x64-musl-4.3.3.tgz", 4090 + "integrity": "sha512-SJxX60smvHgasZoBy11dX6YRjXJFovwWBoedhbQPOBzgFWBHGB+TVPWB9BxzR7TTxU8FQZAI2AyiNCMzFm8Img==", 4091 + "cpu": [ 4092 + "x64" 4093 + ], 4094 + "dev": true, 4095 + "license": "MIT", 4096 + "optional": true, 4097 + "os": [ 4098 + "linux" 4099 + ], 4100 + "engines": { 4101 + "node": ">= 20" 4102 + } 4103 + }, 4104 + "node_modules/@tailwindcss/oxide-wasm32-wasi": { 4105 + "version": "4.3.3", 4106 + "resolved": "https://registry.npmjs.org/@tailwindcss/oxide-wasm32-wasi/-/oxide-wasm32-wasi-4.3.3.tgz", 4107 + "integrity": "sha512-jx1+rPhY/5Ympkktd656HBWEBLxP7dH06losBLjjf5vgCODXvi9KhtftWcMIwTFIDqBr7cRnQkdLnAG+IOlGvQ==", 4108 + "bundleDependencies": [ 4109 + "@napi-rs/wasm-runtime", 4110 + "@emnapi/core", 4111 + "@emnapi/runtime", 4112 + "@tybys/wasm-util", 4113 + "@emnapi/wasi-threads", 4114 + "tslib" 4115 + ], 4116 + "cpu": [ 4117 + "wasm32" 4118 + ], 4119 + "dev": true, 4120 + "license": "MIT", 4121 + "optional": true, 4122 + "dependencies": { 4123 + "@emnapi/core": "^1.11.1", 4124 + "@emnapi/runtime": "^1.11.1", 4125 + "@emnapi/wasi-threads": "^1.2.2", 4126 + "@napi-rs/wasm-runtime": "^1.1.4", 4127 + "@tybys/wasm-util": "^0.10.2", 4128 + "tslib": "^2.8.1" 4129 + }, 4130 + "engines": { 4131 + "node": ">=14.0.0" 4132 + } 4133 + }, 4134 + "node_modules/@tailwindcss/oxide-win32-arm64-msvc": { 4135 + "version": "4.3.3", 4136 + "resolved": "https://registry.npmjs.org/@tailwindcss/oxide-win32-arm64-msvc/-/oxide-win32-arm64-msvc-4.3.3.tgz", 4137 + "integrity": "sha512-3rc292Ca2ceK6Ulcc/bAVnTs/3nDtoPhyEKlgPv+yQJQi/JS/AMJlqzxvlDacL1nekbrcf6bTqp/jV4qgnPxNQ==", 4138 + "cpu": [ 4139 + "arm64" 4140 + ], 4141 + "dev": true, 4142 + "license": "MIT", 4143 + "optional": true, 4144 + "os": [ 4145 + "win32" 4146 + ], 4147 + "engines": { 4148 + "node": ">= 20" 4149 + } 4150 + }, 4151 + "node_modules/@tailwindcss/oxide-win32-x64-msvc": { 4152 + "version": "4.3.3", 4153 + "resolved": "https://registry.npmjs.org/@tailwindcss/oxide-win32-x64-msvc/-/oxide-win32-x64-msvc-4.3.3.tgz", 4154 + "integrity": "sha512-yJ0pwIVc/nYeGoV02WtsN8KYyLQv7kyI2wDnkezyJlGGjkd4QLwDGAwl47YpPJeuI0M0ObaXGSPjvWDPeTPggw==", 4155 + "cpu": [ 4156 + "x64" 4157 + ], 4158 + "dev": true, 4159 + "license": "MIT", 4160 + "optional": true, 4161 + "os": [ 4162 + "win32" 4163 + ], 4164 + "engines": { 4165 + "node": ">= 20" 4166 + } 4167 + }, 4168 + "node_modules/@tailwindcss/vite": { 4169 + "version": "4.3.3", 4170 + "resolved": "https://registry.npmjs.org/@tailwindcss/vite/-/vite-4.3.3.tgz", 4171 + "integrity": "sha512-yYU8cogLeSh/ms2jh8Fj7jaba/EWa7Ja6GoUqYZaraEuCI5YS6ms6ObZgjjedm+jm6XZjdNRWBpPP6Z86oOxcw==", 4172 + "dev": true, 4173 + "license": "MIT", 4174 + "dependencies": { 4175 + "@tailwindcss/node": "4.3.3", 4176 + "@tailwindcss/oxide": "4.3.3", 4177 + "tailwindcss": "4.3.3" 4178 + }, 4179 + "peerDependencies": { 4180 + "vite": "^5.2.0 || ^6 || ^7 || ^8" 4181 + } 4182 + }, 4183 + "node_modules/@tanstack/query-core": { 4184 + "version": "5.101.2", 4185 + "resolved": "https://registry.npmjs.org/@tanstack/query-core/-/query-core-5.101.2.tgz", 4186 + "integrity": "sha512-hH5MLoJhF7KaIGd7q3xTXGXvslI+GYlM1Z/35aSHHWaCJWB7XvTSHYuV3eM7tw+aE0mT/xMro4M4Q9rCGHT0lw==", 4187 + "license": "MIT", 4188 + "funding": { 4189 + "type": "github", 4190 + "url": "https://github.com/sponsors/tannerlinsley" 4191 + } 4192 + }, 4193 + "node_modules/@tanstack/query-persist-client-core": { 4194 + "version": "5.101.2", 4195 + "resolved": "https://registry.npmjs.org/@tanstack/query-persist-client-core/-/query-persist-client-core-5.101.2.tgz", 4196 + "integrity": "sha512-rgMsbvBVpSPDUsprC9FYxojdG0Q1LH6yq1i3DXz2aps4VEqv2l4Msj3YDqIifU3xkl/DrYe9YWntZAJLrM6xTg==", 4197 + "license": "MIT", 4198 + "dependencies": { 4199 + "@tanstack/query-core": "5.101.2" 4200 + }, 4201 + "funding": { 4202 + "type": "github", 4203 + "url": "https://github.com/sponsors/tannerlinsley" 4204 + } 4205 + }, 4206 + "node_modules/@tanstack/query-sync-storage-persister": { 4207 + "version": "5.101.2", 4208 + "resolved": "https://registry.npmjs.org/@tanstack/query-sync-storage-persister/-/query-sync-storage-persister-5.101.2.tgz", 4209 + "integrity": "sha512-hRyLEJvkUWtfCUA3Lf5vD1CrXbHHK4pZNM/iNd7JM5GgC4CWzGIHkVkeg8zC2LV11KceKObKgjNuMSg3b6NOjA==", 4210 + "license": "MIT", 4211 + "dependencies": { 4212 + "@tanstack/query-core": "5.101.2", 4213 + "@tanstack/query-persist-client-core": "5.101.2" 4214 + }, 4215 + "funding": { 4216 + "type": "github", 4217 + "url": "https://github.com/sponsors/tannerlinsley" 4218 + } 4219 + }, 4220 + "node_modules/@tanstack/react-query": { 4221 + "version": "5.101.2", 4222 + "resolved": "https://registry.npmjs.org/@tanstack/react-query/-/react-query-5.101.2.tgz", 4223 + "integrity": "sha512-seDkr6kzGzX1okaaTtZPtgA688CDPlXUz1C6xSg0ESqn04Vuc8tlrYms1s3de+znBqhPVxFRfpAfUf+6XvfPWg==", 4224 + "license": "MIT", 4225 + "dependencies": { 4226 + "@tanstack/query-core": "5.101.2" 4227 + }, 4228 + "funding": { 4229 + "type": "github", 4230 + "url": "https://github.com/sponsors/tannerlinsley" 4231 + }, 4232 + "peerDependencies": { 4233 + "react": "^18 || ^19" 4234 + } 4235 + }, 4236 + "node_modules/@tanstack/react-query-persist-client": { 4237 + "version": "5.101.2", 4238 + "resolved": "https://registry.npmjs.org/@tanstack/react-query-persist-client/-/react-query-persist-client-5.101.2.tgz", 4239 + "integrity": "sha512-19UpaRtf0lvB2QAJ2MoixxtGf3osMOd508g99EsttUj4+3eLs+ulnNgYjB7AkQMHrRlcbVXqpVNqWkB4a7g8Zw==", 4240 + "license": "MIT", 4241 + "dependencies": { 4242 + "@tanstack/query-persist-client-core": "5.101.2" 4243 + }, 4244 + "funding": { 4245 + "type": "github", 4246 + "url": "https://github.com/sponsors/tannerlinsley" 4247 + }, 4248 + "peerDependencies": { 4249 + "@tanstack/react-query": "^5.101.2", 4250 + "react": "^18 || ^19" 4251 + } 4252 + }, 4253 + "node_modules/@trickfilm400/rollup-plugin-off-main-thread": { 4254 + "version": "3.0.0-pre1", 4255 + "resolved": "https://registry.npmjs.org/@trickfilm400/rollup-plugin-off-main-thread/-/rollup-plugin-off-main-thread-3.0.0-pre1.tgz", 4256 + "integrity": "sha512-/67zpWDBLV+oYAEL682s1ktXL0HgqX76f6gaVGkGnVZlBbm1zd0v4Bz8MFF2GGhoX9rvfq3KSQHubFHwa6w6/Q==", 4257 + "dev": true, 4258 + "license": "Apache-2.0", 4259 + "dependencies": { 4260 + "ejs": "^3.1.10", 4261 + "json5": "^2.2.3", 4262 + "magic-string": "^0.30.21", 4263 + "string.prototype.matchall": "^4.0.12" 4264 + }, 4265 + "engines": { 4266 + "node": ">=12" 4267 + } 4268 + }, 4269 + "node_modules/@tybys/wasm-util": { 4270 + "version": "0.10.3", 4271 + "resolved": "https://registry.npmjs.org/@tybys/wasm-util/-/wasm-util-0.10.3.tgz", 4272 + "integrity": "sha512-F3fo1MYrRJYL3zER0OUOmkutjr1Vp23m7OsSgp7nq4SP6OqX6C/56XFIPAl5bt3zaBRjmW7SGz3u/6LwFpYcOg==", 4273 + "dev": true, 4274 + "license": "MIT", 4275 + "optional": true, 4276 + "dependencies": { 4277 + "tslib": "^2.4.0" 4278 + } 4279 + }, 4280 + "node_modules/@types/estree": { 4281 + "version": "1.0.9", 4282 + "resolved": "https://registry.npmjs.org/@types/estree/-/estree-1.0.9.tgz", 4283 + "integrity": "sha512-GhdPgy1el4/ImP05X05Uw4cw2/M93BCUmnEvWZNStlCzEKME4Fkk+YpoA5OiHNQmoS7Cafb8Xa3Pya8m1Qrzeg==", 4284 + "dev": true, 4285 + "license": "MIT" 4286 + }, 4287 + "node_modules/@types/react": { 4288 + "version": "19.2.17", 4289 + "resolved": "https://registry.npmjs.org/@types/react/-/react-19.2.17.tgz", 4290 + "integrity": "sha512-MXfmqaVPEVgkBT/aY0aGCkRWWtByiYQXo3xdQ8r5RzuFrPiRn8Gar2tQdXSUQ2GKV3bkXckek89V8wQBY2Q/Aw==", 4291 + "dev": true, 4292 + "license": "MIT", 4293 + "dependencies": { 4294 + "csstype": "^3.2.2" 4295 + } 4296 + }, 4297 + "node_modules/@types/react-dom": { 4298 + "version": "19.2.3", 4299 + "resolved": "https://registry.npmjs.org/@types/react-dom/-/react-dom-19.2.3.tgz", 4300 + "integrity": "sha512-jp2L/eY6fn+KgVVQAOqYItbF0VY/YApe5Mz2F0aykSO8gx31bYCZyvSeYxCHKvzHG5eZjc+zyaS5BrBWya2+kQ==", 4301 + "dev": true, 4302 + "license": "MIT", 4303 + "peerDependencies": { 4304 + "@types/react": "^19.2.0" 4305 + } 4306 + }, 4307 + "node_modules/@types/resolve": { 4308 + "version": "1.20.2", 4309 + "resolved": "https://registry.npmjs.org/@types/resolve/-/resolve-1.20.2.tgz", 4310 + "integrity": "sha512-60BCwRFOZCQhDncwQdxxeOEEkbc5dIMccYLwbxsS4TUNeVECQ/pBJ0j09mrHOl/JJvpRPGwO9SvE4nR2Nb/a4Q==", 4311 + "dev": true, 4312 + "license": "MIT" 4313 + }, 4314 + "node_modules/@types/trusted-types": { 4315 + "version": "2.0.7", 4316 + "resolved": "https://registry.npmjs.org/@types/trusted-types/-/trusted-types-2.0.7.tgz", 4317 + "integrity": "sha512-ScaPdn1dQczgbl0QFTeTOmVHFULt394XJgOQNoyVhZ6r2vLnMLJfBPd53SB52T/3G36VI1/g2MZaX0cwDuXsfw==", 4318 + "dev": true, 4319 + "license": "MIT" 4320 + }, 4321 + "node_modules/@typescript/typescript-aix-ppc64": { 4322 + "version": "7.0.2", 4323 + "resolved": "https://registry.npmjs.org/@typescript/typescript-aix-ppc64/-/typescript-aix-ppc64-7.0.2.tgz", 4324 + "integrity": "sha512-MTKKkWB7p/0E9xi1d1tHtZ5PiLkGEMIq88pK2CubZjOsLtYTLqhgIgi6zepFa+9GHZ6h05NMCkQxGKiPXMxXtQ==", 4325 + "cpu": [ 4326 + "ppc64" 4327 + ], 4328 + "dev": true, 4329 + "license": "Apache-2.0", 4330 + "optional": true, 4331 + "os": [ 4332 + "aix" 4333 + ], 4334 + "engines": { 4335 + "node": ">=16.20.0" 4336 + } 4337 + }, 4338 + "node_modules/@typescript/typescript-darwin-arm64": { 4339 + "version": "7.0.2", 4340 + "resolved": "https://registry.npmjs.org/@typescript/typescript-darwin-arm64/-/typescript-darwin-arm64-7.0.2.tgz", 4341 + "integrity": "sha512-gowzar9MwS/aRWp6f3a4KUqzRjAZjOsmGNCM6LcTgXum+dBfgsBVMN+AgvOCCbguXyick6LJhpBszxMebJ8syA==", 4342 + "cpu": [ 4343 + "arm64" 4344 + ], 4345 + "dev": true, 4346 + "license": "Apache-2.0", 4347 + "optional": true, 4348 + "os": [ 4349 + "darwin" 4350 + ], 4351 + "engines": { 4352 + "node": ">=16.20.0" 4353 + } 4354 + }, 4355 + "node_modules/@typescript/typescript-darwin-x64": { 4356 + "version": "7.0.2", 4357 + "resolved": "https://registry.npmjs.org/@typescript/typescript-darwin-x64/-/typescript-darwin-x64-7.0.2.tgz", 4358 + "integrity": "sha512-SZ9xZInqApNlNGc9s0W1VSsktYSOe9cFqNOIqmN1Gs8SmkjKZYFt017G4VwPxASInODuAdbTW7sXiFUf893RgA==", 4359 + "cpu": [ 4360 + "x64" 4361 + ], 4362 + "dev": true, 4363 + "license": "Apache-2.0", 4364 + "optional": true, 4365 + "os": [ 4366 + "darwin" 4367 + ], 4368 + "engines": { 4369 + "node": ">=16.20.0" 4370 + } 4371 + }, 4372 + "node_modules/@typescript/typescript-freebsd-arm64": { 4373 + "version": "7.0.2", 4374 + "resolved": "https://registry.npmjs.org/@typescript/typescript-freebsd-arm64/-/typescript-freebsd-arm64-7.0.2.tgz", 4375 + "integrity": "sha512-W5NH4y/J0plIIS5b2xvTEkU7JFxyqdMAOgf+Ilhl0vHQXKO5dZoxd+C/jEtq56c4F3wk71RB4BMRQ2XdI+bwYQ==", 4376 + "cpu": [ 4377 + "arm64" 4378 + ], 4379 + "dev": true, 4380 + "license": "Apache-2.0", 4381 + "optional": true, 4382 + "os": [ 4383 + "freebsd" 4384 + ], 4385 + "engines": { 4386 + "node": ">=16.20.0" 4387 + } 4388 + }, 4389 + "node_modules/@typescript/typescript-freebsd-x64": { 4390 + "version": "7.0.2", 4391 + "resolved": "https://registry.npmjs.org/@typescript/typescript-freebsd-x64/-/typescript-freebsd-x64-7.0.2.tgz", 4392 + "integrity": "sha512-UMGDx5sTpzNw3WiPebH7l90IWfJggEd+egHt/q6p7/Cm3zqoV7VxkGXt+3DxPIw8CcmvAB0j3sVVfbhX+M4Tpw==", 4393 + "cpu": [ 4394 + "x64" 4395 + ], 4396 + "dev": true, 4397 + "license": "Apache-2.0", 4398 + "optional": true, 4399 + "os": [ 4400 + "freebsd" 4401 + ], 4402 + "engines": { 4403 + "node": ">=16.20.0" 4404 + } 4405 + }, 4406 + "node_modules/@typescript/typescript-linux-arm": { 4407 + "version": "7.0.2", 4408 + "resolved": "https://registry.npmjs.org/@typescript/typescript-linux-arm/-/typescript-linux-arm-7.0.2.tgz", 4409 + "integrity": "sha512-gffT3xPz9sR7j/YJExkyPntrI0P2EP9XbOyWzth2/Gs0RstK+90RBcO0ncXoXy/beYll1SXw846Nf2zdnEz0QQ==", 4410 + "cpu": [ 4411 + "arm" 4412 + ], 4413 + "dev": true, 4414 + "license": "Apache-2.0", 4415 + "optional": true, 4416 + "os": [ 4417 + "linux" 4418 + ], 4419 + "engines": { 4420 + "node": ">=16.20.0" 4421 + } 4422 + }, 4423 + "node_modules/@typescript/typescript-linux-arm64": { 4424 + "version": "7.0.2", 4425 + "resolved": "https://registry.npmjs.org/@typescript/typescript-linux-arm64/-/typescript-linux-arm64-7.0.2.tgz", 4426 + "integrity": "sha512-Qh4eU4/y3yDjnfjjyPYihMj5/ODIlmt+Bzu17OI+fiSRDW57QmU5SiN63exPRNJPKUzcc1INa1NXdrJ+MqHjUQ==", 4427 + "cpu": [ 4428 + "arm64" 4429 + ], 4430 + "dev": true, 4431 + "license": "Apache-2.0", 4432 + "optional": true, 4433 + "os": [ 4434 + "linux" 4435 + ], 4436 + "engines": { 4437 + "node": ">=16.20.0" 4438 + } 4439 + }, 4440 + "node_modules/@typescript/typescript-linux-loong64": { 4441 + "version": "7.0.2", 4442 + "resolved": "https://registry.npmjs.org/@typescript/typescript-linux-loong64/-/typescript-linux-loong64-7.0.2.tgz", 4443 + "integrity": "sha512-uEHck9i8hoAzXPiYRib1O7miOnz23SxIeVl6F4LXox+qov1K35jHcEW6VHKvZI+pyvl7fZEP4MCU5LYvIq1GuQ==", 4444 + "cpu": [ 4445 + "loong64" 4446 + ], 4447 + "dev": true, 4448 + "license": "Apache-2.0", 4449 + "optional": true, 4450 + "os": [ 4451 + "linux" 4452 + ], 4453 + "engines": { 4454 + "node": ">=16.20.0" 4455 + } 4456 + }, 4457 + "node_modules/@typescript/typescript-linux-mips64el": { 4458 + "version": "7.0.2", 4459 + "resolved": "https://registry.npmjs.org/@typescript/typescript-linux-mips64el/-/typescript-linux-mips64el-7.0.2.tgz", 4460 + "integrity": "sha512-R4KvAMnE43W5Qeqb0Ly56O3mWMWIAgsMyz36DCaycd5nbg/9kzm0liw3JocfRqyJY0KPmzFjbswozXyW0DnIYA==", 4461 + "cpu": [ 4462 + "mips64el" 4463 + ], 4464 + "dev": true, 4465 + "license": "Apache-2.0", 4466 + "optional": true, 4467 + "os": [ 4468 + "linux" 4469 + ], 4470 + "engines": { 4471 + "node": ">=16.20.0" 4472 + } 4473 + }, 4474 + "node_modules/@typescript/typescript-linux-ppc64": { 4475 + "version": "7.0.2", 4476 + "resolved": "https://registry.npmjs.org/@typescript/typescript-linux-ppc64/-/typescript-linux-ppc64-7.0.2.tgz", 4477 + "integrity": "sha512-DORx5b3sd/4S7eayxm4FQv+A7CrkUIGRaHiwI8oiHTAI1fAPWhF4J0vAlkC8biAlHSVVwxMQ3tjZ2/DVbnQiiA==", 4478 + "cpu": [ 4479 + "ppc64" 4480 + ], 4481 + "dev": true, 4482 + "license": "Apache-2.0", 4483 + "optional": true, 4484 + "os": [ 4485 + "linux" 4486 + ], 4487 + "engines": { 4488 + "node": ">=16.20.0" 4489 + } 4490 + }, 4491 + "node_modules/@typescript/typescript-linux-riscv64": { 4492 + "version": "7.0.2", 4493 + "resolved": "https://registry.npmjs.org/@typescript/typescript-linux-riscv64/-/typescript-linux-riscv64-7.0.2.tgz", 4494 + "integrity": "sha512-wf0jqEDOjrPRnKwYRyyJDRo11KMbvMFrU+q4zqKyChODBzvlkbhNQfKvLxQCcwTpdDaXSHZTVuh0JoCrKCUMHQ==", 4495 + "cpu": [ 4496 + "riscv64" 4497 + ], 4498 + "dev": true, 4499 + "license": "Apache-2.0", 4500 + "optional": true, 4501 + "os": [ 4502 + "linux" 4503 + ], 4504 + "engines": { 4505 + "node": ">=16.20.0" 4506 + } 4507 + }, 4508 + "node_modules/@typescript/typescript-linux-s390x": { 4509 + "version": "7.0.2", 4510 + "resolved": "https://registry.npmjs.org/@typescript/typescript-linux-s390x/-/typescript-linux-s390x-7.0.2.tgz", 4511 + "integrity": "sha512-IkwJc3L7yhytWd/ewjyxNDfOmswCm9GWMJT/ue/dU4aZNbwZeYAetq42VyLmsmSjvoX7z74X6ZaYCtzAr0EuGw==", 4512 + "cpu": [ 4513 + "s390x" 4514 + ], 4515 + "dev": true, 4516 + "license": "Apache-2.0", 4517 + "optional": true, 4518 + "os": [ 4519 + "linux" 4520 + ], 4521 + "engines": { 4522 + "node": ">=16.20.0" 4523 + } 4524 + }, 4525 + "node_modules/@typescript/typescript-linux-x64": { 4526 + "version": "7.0.2", 4527 + "resolved": "https://registry.npmjs.org/@typescript/typescript-linux-x64/-/typescript-linux-x64-7.0.2.tgz", 4528 + "integrity": "sha512-EYdf2cNg7rgCWJnxCdJ+F3V39O8ihb37eHAu1LK8oAFizgTQbPOK7zHHXbPt8rX24COqODXeI3sIf0fCXG7H/A==", 4529 + "cpu": [ 4530 + "x64" 4531 + ], 4532 + "dev": true, 4533 + "license": "Apache-2.0", 4534 + "optional": true, 4535 + "os": [ 4536 + "linux" 4537 + ], 4538 + "engines": { 4539 + "node": ">=16.20.0" 4540 + } 4541 + }, 4542 + "node_modules/@typescript/typescript-netbsd-arm64": { 4543 + "version": "7.0.2", 4544 + "resolved": "https://registry.npmjs.org/@typescript/typescript-netbsd-arm64/-/typescript-netbsd-arm64-7.0.2.tgz", 4545 + "integrity": "sha512-+polYF4MF04aPpO5FTkHran9yUQDSXqy5GiSDKpsll5jy3l3+g9QLhpf39T+ePtefhXLOGrLl0QIjkQP6VnelA==", 4546 + "cpu": [ 4547 + "arm64" 4548 + ], 4549 + "dev": true, 4550 + "license": "Apache-2.0", 4551 + "optional": true, 4552 + "os": [ 4553 + "netbsd" 4554 + ], 4555 + "engines": { 4556 + "node": ">=16.20.0" 4557 + } 4558 + }, 4559 + "node_modules/@typescript/typescript-netbsd-x64": { 4560 + "version": "7.0.2", 4561 + "resolved": "https://registry.npmjs.org/@typescript/typescript-netbsd-x64/-/typescript-netbsd-x64-7.0.2.tgz", 4562 + "integrity": "sha512-8YIT0EHM/3dq10ZOVF/A7pc/YSMtbcecct4rWtexrnSCHOPcpC2KTLXfTCR6vDpnSiY12heNb1GiN/wu+T/FyA==", 4563 + "cpu": [ 4564 + "x64" 4565 + ], 4566 + "dev": true, 4567 + "license": "Apache-2.0", 4568 + "optional": true, 4569 + "os": [ 4570 + "netbsd" 4571 + ], 4572 + "engines": { 4573 + "node": ">=16.20.0" 4574 + } 4575 + }, 4576 + "node_modules/@typescript/typescript-openbsd-arm64": { 4577 + "version": "7.0.2", 4578 + "resolved": "https://registry.npmjs.org/@typescript/typescript-openbsd-arm64/-/typescript-openbsd-arm64-7.0.2.tgz", 4579 + "integrity": "sha512-APT8+ClYnuYm1u9+kgGXoMj2VzWzcymwh2gNSQVySHfkRDGOTVkoWLjCmOQSaO+PoqQ57B0flRp9SA+7GnnkzQ==", 4580 + "cpu": [ 4581 + "arm64" 4582 + ], 4583 + "dev": true, 4584 + "license": "Apache-2.0", 4585 + "optional": true, 4586 + "os": [ 4587 + "openbsd" 4588 + ], 4589 + "engines": { 4590 + "node": ">=16.20.0" 4591 + } 4592 + }, 4593 + "node_modules/@typescript/typescript-openbsd-x64": { 4594 + "version": "7.0.2", 4595 + "resolved": "https://registry.npmjs.org/@typescript/typescript-openbsd-x64/-/typescript-openbsd-x64-7.0.2.tgz", 4596 + "integrity": "sha512-yX7s+Q0Dln0Dt9tEzZsAjXXR/+ytBM7AlglaqyeMPxQszJ1JhlJdZ6jLA+IzldHtflX81em7lDao1xXu+aRRkg==", 4597 + "cpu": [ 4598 + "x64" 4599 + ], 4600 + "dev": true, 4601 + "license": "Apache-2.0", 4602 + "optional": true, 4603 + "os": [ 4604 + "openbsd" 4605 + ], 4606 + "engines": { 4607 + "node": ">=16.20.0" 4608 + } 4609 + }, 4610 + "node_modules/@typescript/typescript-sunos-x64": { 4611 + "version": "7.0.2", 4612 + "resolved": "https://registry.npmjs.org/@typescript/typescript-sunos-x64/-/typescript-sunos-x64-7.0.2.tgz", 4613 + "integrity": "sha512-dLJDGaLZ1D4HPQn62u1n8mBDkJREwMsAkCdkwd4Ieqw+x3TUyTsqY0YiBCtE6H6OzzgGk3iuZ3vFWRS+E8/d1g==", 4614 + "cpu": [ 4615 + "x64" 4616 + ], 4617 + "dev": true, 4618 + "license": "Apache-2.0", 4619 + "optional": true, 4620 + "os": [ 4621 + "sunos" 4622 + ], 4623 + "engines": { 4624 + "node": ">=16.20.0" 4625 + } 4626 + }, 4627 + "node_modules/@typescript/typescript-win32-arm64": { 4628 + "version": "7.0.2", 4629 + "resolved": "https://registry.npmjs.org/@typescript/typescript-win32-arm64/-/typescript-win32-arm64-7.0.2.tgz", 4630 + "integrity": "sha512-Gyl1Vy6OsWesLzmq+EP0Fb7b4Nid5232AvcA2SFcdYreldpNtYFFofPjnt62y9hQy7VTaZp65ICJjuAQRaVcIQ==", 4631 + "cpu": [ 4632 + "arm64" 4633 + ], 4634 + "dev": true, 4635 + "license": "Apache-2.0", 4636 + "optional": true, 4637 + "os": [ 4638 + "win32" 4639 + ], 4640 + "engines": { 4641 + "node": ">=16.20.0" 4642 + } 4643 + }, 4644 + "node_modules/@typescript/typescript-win32-x64": { 4645 + "version": "7.0.2", 4646 + "resolved": "https://registry.npmjs.org/@typescript/typescript-win32-x64/-/typescript-win32-x64-7.0.2.tgz", 4647 + "integrity": "sha512-0BQ3HkAHHlKLSp1qRvf3SUhGpGsDuhB/jgFw75guyqbxJqEaS0Cw/VFO8i2nHglJUzQCRtMMR/IBAKE3ETMC4g==", 4648 + "cpu": [ 4649 + "x64" 4650 + ], 4651 + "dev": true, 4652 + "license": "Apache-2.0", 4653 + "optional": true, 4654 + "os": [ 4655 + "win32" 4656 + ], 4657 + "engines": { 4658 + "node": ">=16.20.0" 4659 + } 4660 + }, 4661 + "node_modules/@vitejs/plugin-react": { 4662 + "version": "6.0.3", 4663 + "resolved": "https://registry.npmjs.org/@vitejs/plugin-react/-/plugin-react-6.0.3.tgz", 4664 + "integrity": "sha512-vmFvco5/QuC2f9Oj+wTk0+9XeDFkHxSamwZKYc7MxYwKICfvUvlMhqKI0VuICPltGqh1neqBKDvO4kes1ya8vg==", 4665 + "dev": true, 4666 + "license": "MIT", 4667 + "dependencies": { 4668 + "@rolldown/pluginutils": "^1.0.1" 4669 + }, 4670 + "engines": { 4671 + "node": "^20.19.0 || >=22.12.0" 4672 + }, 4673 + "peerDependencies": { 4674 + "@rolldown/plugin-babel": "^0.1.7 || ^0.2.0", 4675 + "babel-plugin-react-compiler": "^1.0.0", 4676 + "vite": "^8.0.0" 4677 + }, 4678 + "peerDependenciesMeta": { 4679 + "@rolldown/plugin-babel": { 4680 + "optional": true 4681 + }, 4682 + "babel-plugin-react-compiler": { 4683 + "optional": true 4684 + } 4685 + } 4686 + }, 4687 + "node_modules/acorn": { 4688 + "version": "8.17.0", 4689 + "resolved": "https://registry.npmjs.org/acorn/-/acorn-8.17.0.tgz", 4690 + "integrity": "sha512-xRQbDb9BnwDafYNn6Vwl839DYVjqXYb1XVGtWAZ1kcDc6iwAL4hg3B1dZlRiuENFeO2H53gFG3in621AdERVAg==", 4691 + "dev": true, 4692 + "license": "MIT", 4693 + "bin": { 4694 + "acorn": "bin/acorn" 4695 + }, 4696 + "engines": { 4697 + "node": ">=0.4.0" 4698 + } 4699 + }, 4700 + "node_modules/ajv": { 4701 + "version": "8.20.0", 4702 + "resolved": "https://registry.npmjs.org/ajv/-/ajv-8.20.0.tgz", 4703 + "integrity": "sha512-Thbli+OlOj+iMPYFBVBfJ3OmCAnaSyNn4M1vz9T6Gka5Jt9ba/HIR56joy65tY6kx/FCF5VXNB819Y7/GUrBGA==", 4704 + "dev": true, 4705 + "license": "MIT", 4706 + "dependencies": { 4707 + "fast-deep-equal": "^3.1.3", 4708 + "fast-uri": "^3.0.1", 4709 + "json-schema-traverse": "^1.0.0", 4710 + "require-from-string": "^2.0.2" 4711 + }, 4712 + "funding": { 4713 + "type": "github", 4714 + "url": "https://github.com/sponsors/epoberezkin" 4715 + } 4716 + }, 4717 + "node_modules/arctic": { 4718 + "version": "3.7.0", 4719 + "resolved": "https://registry.npmjs.org/arctic/-/arctic-3.7.0.tgz", 4720 + "integrity": "sha512-ZMQ+f6VazDgUJOd+qNV+H7GohNSYal1mVjm5kEaZfE2Ifb7Ss70w+Q7xpJC87qZDkMZIXYf0pTIYZA0OPasSbw==", 4721 + "license": "MIT", 4722 + "dependencies": { 4723 + "@oslojs/crypto": "1.0.1", 4724 + "@oslojs/encoding": "1.1.0", 4725 + "@oslojs/jwt": "0.2.0" 4726 + } 4727 + }, 4728 + "node_modules/array-buffer-byte-length": { 4729 + "version": "1.0.2", 4730 + "resolved": "https://registry.npmjs.org/array-buffer-byte-length/-/array-buffer-byte-length-1.0.2.tgz", 4731 + "integrity": "sha512-LHE+8BuR7RYGDKvnrmcuSq3tDcKv9OFEXQt/HpbZhY7V6h0zlUXutnAD82GiFx9rdieCMjkvtcsPqBwgUl1Iiw==", 4732 + "dev": true, 4733 + "license": "MIT", 4734 + "dependencies": { 4735 + "call-bound": "^1.0.3", 4736 + "is-array-buffer": "^3.0.5" 4737 + }, 4738 + "engines": { 4739 + "node": ">= 0.4" 4740 + }, 4741 + "funding": { 4742 + "url": "https://github.com/sponsors/ljharb" 4743 + } 4744 + }, 4745 + "node_modules/arraybuffer.prototype.slice": { 4746 + "version": "1.0.4", 4747 + "resolved": "https://registry.npmjs.org/arraybuffer.prototype.slice/-/arraybuffer.prototype.slice-1.0.4.tgz", 4748 + "integrity": "sha512-BNoCY6SXXPQ7gF2opIP4GBE+Xw7U+pHMYKuzjgCN3GwiaIR09UUeKfheyIry77QtrCBlC0KK0q5/TER/tYh3PQ==", 4749 + "dev": true, 4750 + "license": "MIT", 4751 + "dependencies": { 4752 + "array-buffer-byte-length": "^1.0.1", 4753 + "call-bind": "^1.0.8", 4754 + "define-properties": "^1.2.1", 4755 + "es-abstract": "^1.23.5", 4756 + "es-errors": "^1.3.0", 4757 + "get-intrinsic": "^1.2.6", 4758 + "is-array-buffer": "^3.0.4" 4759 + }, 4760 + "engines": { 4761 + "node": ">= 0.4" 4762 + }, 4763 + "funding": { 4764 + "url": "https://github.com/sponsors/ljharb" 4765 + } 4766 + }, 4767 + "node_modules/asn1js": { 4768 + "version": "3.0.10", 4769 + "resolved": "https://registry.npmjs.org/asn1js/-/asn1js-3.0.10.tgz", 4770 + "integrity": "sha512-S2s3aOytiKdFRdulw2qPE51MzjzVOisppcVv7jVFR+Kw0kxwvFrDcYA0h7Ndqbmj0HkMIXYWaoj7fli8kgx1eg==", 4771 + "license": "BSD-3-Clause", 4772 + "dependencies": { 4773 + "pvtsutils": "^1.3.6", 4774 + "pvutils": "^1.1.5", 4775 + "tslib": "^2.8.1" 4776 + }, 4777 + "engines": { 4778 + "node": ">=12.0.0" 4779 + } 4780 + }, 4781 + "node_modules/async": { 4782 + "version": "3.2.6", 4783 + "resolved": "https://registry.npmjs.org/async/-/async-3.2.6.tgz", 4784 + "integrity": "sha512-htCUDlxyyCLMgaM3xXg0C0LW2xqfuQ6p05pCEIsXuyQ+a1koYKTuBMzRNwmybfLgvJDMd0r1LTn4+E0Ti6C2AA==", 4785 + "dev": true, 4786 + "license": "MIT" 4787 + }, 4788 + "node_modules/async-function": { 4789 + "version": "1.0.0", 4790 + "resolved": "https://registry.npmjs.org/async-function/-/async-function-1.0.0.tgz", 4791 + "integrity": "sha512-hsU18Ae8CDTR6Kgu9DYf0EbCr/a5iGL0rytQDobUcdpYOKokk8LEjVphnXkDkgpi0wYVsqrXuP0bZxJaTqdgoA==", 4792 + "dev": true, 4793 + "license": "MIT", 4794 + "engines": { 4795 + "node": ">= 0.4" 4796 + } 4797 + }, 4798 + "node_modules/at-least-node": { 4799 + "version": "1.0.0", 4800 + "resolved": "https://registry.npmjs.org/at-least-node/-/at-least-node-1.0.0.tgz", 4801 + "integrity": "sha512-+q/t7Ekv1EDY2l6Gda6LLiX14rU9TV20Wa3ofeQmwPFZbOMo9DXrLbOjFaaclkXKWidIaopwAObQDqwWtGUjqg==", 4802 + "dev": true, 4803 + "license": "ISC", 4804 + "engines": { 4805 + "node": ">= 4.0.0" 4806 + } 4807 + }, 4808 + "node_modules/available-typed-arrays": { 4809 + "version": "1.0.7", 4810 + "resolved": "https://registry.npmjs.org/available-typed-arrays/-/available-typed-arrays-1.0.7.tgz", 4811 + "integrity": "sha512-wvUjBtSGN7+7SjNpq/9M2Tg350UZD3q62IFZLbRAR1bSMlCo1ZaeW+BJ+D090e4hIIZLBcTDWe4Mh4jvUDajzQ==", 4812 + "dev": true, 4813 + "license": "MIT", 4814 + "dependencies": { 4815 + "possible-typed-array-names": "^1.0.0" 4816 + }, 4817 + "engines": { 4818 + "node": ">= 0.4" 4819 + }, 4820 + "funding": { 4821 + "url": "https://github.com/sponsors/ljharb" 4822 + } 4823 + }, 4824 + "node_modules/babel-plugin-polyfill-corejs2": { 4825 + "version": "0.4.17", 4826 + "resolved": "https://registry.npmjs.org/babel-plugin-polyfill-corejs2/-/babel-plugin-polyfill-corejs2-0.4.17.tgz", 4827 + "integrity": "sha512-aTyf30K/rqAsNwN76zYrdtx8obu0E4KoUME29B1xj+B3WxgvWkp943vYQ+z8Mv3lw9xHXMHpvSPOBxzAkIa94w==", 4828 + "dev": true, 4829 + "license": "MIT", 4830 + "dependencies": { 4831 + "@babel/compat-data": "^7.28.6", 4832 + "@babel/helper-define-polyfill-provider": "^0.6.8", 4833 + "semver": "^6.3.1" 4834 + }, 4835 + "peerDependencies": { 4836 + "@babel/core": "^7.4.0 || ^8.0.0-0 <8.0.0" 4837 + } 4838 + }, 4839 + "node_modules/babel-plugin-polyfill-corejs2/node_modules/semver": { 4840 + "version": "6.3.1", 4841 + "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.1.tgz", 4842 + "integrity": "sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA==", 4843 + "dev": true, 4844 + "license": "ISC", 4845 + "bin": { 4846 + "semver": "bin/semver.js" 4847 + } 4848 + }, 4849 + "node_modules/babel-plugin-polyfill-corejs3": { 4850 + "version": "0.14.2", 4851 + "resolved": "https://registry.npmjs.org/babel-plugin-polyfill-corejs3/-/babel-plugin-polyfill-corejs3-0.14.2.tgz", 4852 + "integrity": "sha512-coWpDLJ410R781Npmn/SIBZEsAetR4xVi0SxLMXPaMO4lSf1MwnkGYMtkFxew0Dn8B3/CpbpYxN0JCgg8mn67g==", 4853 + "dev": true, 4854 + "license": "MIT", 4855 + "dependencies": { 4856 + "@babel/helper-define-polyfill-provider": "^0.6.8", 4857 + "core-js-compat": "^3.48.0" 4858 + }, 4859 + "peerDependencies": { 4860 + "@babel/core": "^7.4.0 || ^8.0.0-0 <8.0.0" 4861 + } 4862 + }, 4863 + "node_modules/babel-plugin-polyfill-regenerator": { 4864 + "version": "0.6.8", 4865 + "resolved": "https://registry.npmjs.org/babel-plugin-polyfill-regenerator/-/babel-plugin-polyfill-regenerator-0.6.8.tgz", 4866 + "integrity": "sha512-M762rNHfSF1EV3SLtnCJXFoQbbIIz0OyRwnCmV0KPC7qosSfCO0QLTSuJX3ayAebubhE6oYBAYPrBA5ljowaZg==", 4867 + "dev": true, 4868 + "license": "MIT", 4869 + "dependencies": { 4870 + "@babel/helper-define-polyfill-provider": "^0.6.8" 4871 + }, 4872 + "peerDependencies": { 4873 + "@babel/core": "^7.4.0 || ^8.0.0-0 <8.0.0" 4874 + } 4875 + }, 4876 + "node_modules/balanced-match": { 4877 + "version": "4.0.4", 4878 + "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-4.0.4.tgz", 4879 + "integrity": "sha512-BLrgEcRTwX2o6gGxGOCNyMvGSp35YofuYzw9h1IMTRmKqttAZZVU67bdb9Pr2vUHA8+j3i2tJfjO6C6+4myGTA==", 4880 + "dev": true, 4881 + "license": "MIT", 4882 + "engines": { 4883 + "node": "18 || 20 || >=22" 4884 + } 4885 + }, 4886 + "node_modules/baseline-browser-mapping": { 4887 + "version": "2.10.43", 4888 + "resolved": "https://registry.npmjs.org/baseline-browser-mapping/-/baseline-browser-mapping-2.10.43.tgz", 4889 + "integrity": "sha512-AjYpR78kDWAY3Efj+cDTFH9t9SCoL7OoTp1BOb0mQV7S+6CiLwnWM3FyxhJtdPufDFKzmCSFoUncKjWgJEZTCQ==", 4890 + "dev": true, 4891 + "license": "Apache-2.0", 4892 + "bin": { 4893 + "baseline-browser-mapping": "dist/cli.cjs" 4894 + }, 4895 + "engines": { 4896 + "node": ">=6.0.0" 4897 + } 4898 + }, 4899 + "node_modules/blake3-wasm": { 4900 + "version": "2.1.5", 4901 + "resolved": "https://registry.npmjs.org/blake3-wasm/-/blake3-wasm-2.1.5.tgz", 4902 + "integrity": "sha512-F1+K8EbfOZE49dtoPtmxUQrpXaBIl3ICvasLh+nJta0xkz+9kF/7uet9fLnwKqhDrmj6g+6K3Tw9yQPUg2ka5g==", 4903 + "dev": true, 4904 + "license": "MIT" 4905 + }, 4906 + "node_modules/brace-expansion": { 4907 + "version": "5.0.7", 4908 + "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-5.0.7.tgz", 4909 + "integrity": "sha512-7oFy703dxfY3/NLxC1fh2SUCQ0H9rmAY+5EpDVfXjUTTs+HEwR2nYaqLv+GWcTsumwxPfiz6CzCNkwXwBUwqCA==", 4910 + "dev": true, 4911 + "license": "MIT", 4912 + "dependencies": { 4913 + "balanced-match": "^4.0.2" 4914 + }, 4915 + "engines": { 4916 + "node": "18 || 20 || >=22" 4917 + } 4918 + }, 4919 + "node_modules/browserslist": { 4920 + "version": "4.28.6", 4921 + "resolved": "https://registry.npmjs.org/browserslist/-/browserslist-4.28.6.tgz", 4922 + "integrity": "sha512-FQBYNK15VMslhLHpA7+n+n1GOlF1kId2xcCg7/j95f24AOF6VDYMNH4mFxF7KuaTdv627faazpOAjFzMrfJOUw==", 4923 + "dev": true, 4924 + "funding": [ 4925 + { 4926 + "type": "opencollective", 4927 + "url": "https://opencollective.com/browserslist" 4928 + }, 4929 + { 4930 + "type": "tidelift", 4931 + "url": "https://tidelift.com/funding/github/npm/browserslist" 4932 + }, 4933 + { 4934 + "type": "github", 4935 + "url": "https://github.com/sponsors/ai" 4936 + } 4937 + ], 4938 + "license": "MIT", 4939 + "dependencies": { 4940 + "baseline-browser-mapping": "^2.10.42", 4941 + "caniuse-lite": "^1.0.30001803", 4942 + "electron-to-chromium": "^1.5.389", 4943 + "node-releases": "^2.0.51", 4944 + "update-browserslist-db": "^1.2.3" 4945 + }, 4946 + "bin": { 4947 + "browserslist": "cli.js" 4948 + }, 4949 + "engines": { 4950 + "node": "^6 || ^7 || ^8 || ^9 || ^10 || ^11 || ^12 || >=13.7" 4951 + } 4952 + }, 4953 + "node_modules/buffer-from": { 4954 + "version": "1.1.2", 4955 + "resolved": "https://registry.npmjs.org/buffer-from/-/buffer-from-1.1.2.tgz", 4956 + "integrity": "sha512-E+XQCRwSbaaiChtv6k6Dwgc+bx+Bs6vuKJHHl5kox/BaKbhiXzqQOwK4cO22yElGp2OCmjwVhT3HmxgyPGnJfQ==", 4957 + "dev": true, 4958 + "license": "MIT" 4959 + }, 4960 + "node_modules/call-bind": { 4961 + "version": "1.0.9", 4962 + "resolved": "https://registry.npmjs.org/call-bind/-/call-bind-1.0.9.tgz", 4963 + "integrity": "sha512-a/hy+pNsFUTR+Iz8TCJvXudKVLAnz/DyeSUo10I5yvFDQJBFU2s9uqQpoSrJlroHUKoKqzg+epxyP9lqFdzfBQ==", 4964 + "dev": true, 4965 + "license": "MIT", 4966 + "dependencies": { 4967 + "call-bind-apply-helpers": "^1.0.2", 4968 + "es-define-property": "^1.0.1", 4969 + "get-intrinsic": "^1.3.0", 4970 + "set-function-length": "^1.2.2" 4971 + }, 4972 + "engines": { 4973 + "node": ">= 0.4" 4974 + }, 4975 + "funding": { 4976 + "url": "https://github.com/sponsors/ljharb" 4977 + } 4978 + }, 4979 + "node_modules/call-bind-apply-helpers": { 4980 + "version": "1.0.2", 4981 + "resolved": "https://registry.npmjs.org/call-bind-apply-helpers/-/call-bind-apply-helpers-1.0.2.tgz", 4982 + "integrity": "sha512-Sp1ablJ0ivDkSzjcaJdxEunN5/XvksFJ2sMBFfq6x0ryhQV/2b/KwFe21cMpmHtPOSij8K99/wSfoEuTObmuMQ==", 4983 + "dev": true, 4984 + "license": "MIT", 4985 + "dependencies": { 4986 + "es-errors": "^1.3.0", 4987 + "function-bind": "^1.1.2" 4988 + }, 4989 + "engines": { 4990 + "node": ">= 0.4" 4991 + } 4992 + }, 4993 + "node_modules/call-bound": { 4994 + "version": "1.0.4", 4995 + "resolved": "https://registry.npmjs.org/call-bound/-/call-bound-1.0.4.tgz", 4996 + "integrity": "sha512-+ys997U96po4Kx/ABpBCqhA9EuxJaQWDQg7295H4hBphv3IZg0boBKuwYpt4YXp6MZ5AmZQnU/tyMTlRpaSejg==", 4997 + "dev": true, 4998 + "license": "MIT", 4999 + "dependencies": { 5000 + "call-bind-apply-helpers": "^1.0.2", 5001 + "get-intrinsic": "^1.3.0" 5002 + }, 5003 + "engines": { 5004 + "node": ">= 0.4" 5005 + }, 5006 + "funding": { 5007 + "url": "https://github.com/sponsors/ljharb" 5008 + } 5009 + }, 5010 + "node_modules/caniuse-lite": { 5011 + "version": "1.0.30001806", 5012 + "resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001806.tgz", 5013 + "integrity": "sha512-72Cuvd95zbSYPKq6Fhg8eDJRlzgWDf7/mtoZv6Qe/DYNCEBdNxoA3+rZAU2ZhGCpZlns3EssFavaZomckT5Uuw==", 5014 + "dev": true, 5015 + "funding": [ 5016 + { 5017 + "type": "opencollective", 5018 + "url": "https://opencollective.com/browserslist" 5019 + }, 5020 + { 5021 + "type": "tidelift", 5022 + "url": "https://tidelift.com/funding/github/npm/caniuse-lite" 5023 + }, 5024 + { 5025 + "type": "github", 5026 + "url": "https://github.com/sponsors/ai" 5027 + } 5028 + ], 5029 + "license": "CC-BY-4.0" 5030 + }, 5031 + "node_modules/commander": { 5032 + "version": "2.20.3", 5033 + "resolved": "https://registry.npmjs.org/commander/-/commander-2.20.3.tgz", 5034 + "integrity": "sha512-GpVkmM8vF2vQUkj2LvZmD35JxeJOLCwJ9cUkugyk2nuhbv3+mJvpLYYt+0+USMxE+oj+ey/lJEnhZw75x/OMcQ==", 5035 + "dev": true, 5036 + "license": "MIT" 5037 + }, 5038 + "node_modules/common-tags": { 5039 + "version": "1.8.2", 5040 + "resolved": "https://registry.npmjs.org/common-tags/-/common-tags-1.8.2.tgz", 5041 + "integrity": "sha512-gk/Z852D2Wtb//0I+kRFNKKE9dIIVirjoqPoA1wJU+XePVXZfGeBpk45+A1rKO4Q43prqWBNY/MiIeRLbPWUaA==", 5042 + "dev": true, 5043 + "license": "MIT", 5044 + "engines": { 5045 + "node": ">=4.0.0" 5046 + } 5047 + }, 5048 + "node_modules/convert-source-map": { 5049 + "version": "2.0.0", 5050 + "resolved": "https://registry.npmjs.org/convert-source-map/-/convert-source-map-2.0.0.tgz", 5051 + "integrity": "sha512-Kvp459HrV2FEJ1CAsi1Ku+MY3kasH19TFykTz2xWmMeq6bk2NU3XXvfJ+Q61m0xktWwt+1HSYf3JZsTms3aRJg==", 5052 + "dev": true, 5053 + "license": "MIT" 5054 + }, 5055 + "node_modules/cookie": { 5056 + "version": "1.1.1", 5057 + "resolved": "https://registry.npmjs.org/cookie/-/cookie-1.1.1.tgz", 5058 + "integrity": "sha512-ei8Aos7ja0weRpFzJnEA9UHJ/7XQmqglbRwnf2ATjcB9Wq874VKH9kfjjirM6UhU2/E5fFYadylyhFldcqSidQ==", 5059 + "license": "MIT", 5060 + "engines": { 5061 + "node": ">=18" 5062 + }, 5063 + "funding": { 5064 + "type": "opencollective", 5065 + "url": "https://opencollective.com/express" 5066 + } 5067 + }, 5068 + "node_modules/core-js-compat": { 5069 + "version": "3.49.0", 5070 + "resolved": "https://registry.npmjs.org/core-js-compat/-/core-js-compat-3.49.0.tgz", 5071 + "integrity": "sha512-VQXt1jr9cBz03b331DFDCCP90b3fanciLkgiOoy8SBHy06gNf+vQ1A3WFLqG7I8TipYIKeYK9wxd0tUrvHcOZA==", 5072 + "dev": true, 5073 + "license": "MIT", 5074 + "dependencies": { 5075 + "browserslist": "^4.28.1" 5076 + }, 5077 + "funding": { 5078 + "type": "opencollective", 5079 + "url": "https://opencollective.com/core-js" 5080 + } 5081 + }, 5082 + "node_modules/cross-spawn": { 5083 + "version": "7.0.6", 5084 + "resolved": "https://registry.npmjs.org/cross-spawn/-/cross-spawn-7.0.6.tgz", 5085 + "integrity": "sha512-uV2QOWP2nWzsy2aMp8aRibhi9dlzF5Hgh5SHaB9OiTGEyDTiJJyx0uy51QXdyWbtAHNua4XJzUKca3OzKUd3vA==", 5086 + "dev": true, 5087 + "license": "MIT", 5088 + "dependencies": { 5089 + "path-key": "^3.1.0", 5090 + "shebang-command": "^2.0.0", 5091 + "which": "^2.0.1" 5092 + }, 5093 + "engines": { 5094 + "node": ">= 8" 5095 + } 5096 + }, 5097 + "node_modules/crypto-random-string": { 5098 + "version": "2.0.0", 5099 + "resolved": "https://registry.npmjs.org/crypto-random-string/-/crypto-random-string-2.0.0.tgz", 5100 + "integrity": "sha512-v1plID3y9r/lPhviJ1wrXpLeyUIGAZ2SHNYTEapm7/8A9nLPoyvVp3RK/EPFqn5kEznyWgYZNsRtYYIWbuG8KA==", 5101 + "dev": true, 5102 + "license": "MIT", 5103 + "engines": { 5104 + "node": ">=8" 5105 + } 5106 + }, 5107 + "node_modules/csstype": { 5108 + "version": "3.2.3", 5109 + "resolved": "https://registry.npmjs.org/csstype/-/csstype-3.2.3.tgz", 5110 + "integrity": "sha512-z1HGKcYy2xA8AGQfwrn0PAy+PB7X/GSj3UVJW9qKyn43xWa+gl5nXmU4qqLMRzWVLFC8KusUX8T/0kCiOYpAIQ==", 5111 + "dev": true, 5112 + "license": "MIT" 5113 + }, 5114 + "node_modules/data-view-buffer": { 5115 + "version": "1.0.2", 5116 + "resolved": "https://registry.npmjs.org/data-view-buffer/-/data-view-buffer-1.0.2.tgz", 5117 + "integrity": "sha512-EmKO5V3OLXh1rtK2wgXRansaK1/mtVdTUEiEI0W8RkvgT05kfxaH29PliLnpLP73yYO6142Q72QNa8Wx/A5CqQ==", 5118 + "dev": true, 5119 + "license": "MIT", 5120 + "dependencies": { 5121 + "call-bound": "^1.0.3", 5122 + "es-errors": "^1.3.0", 5123 + "is-data-view": "^1.0.2" 5124 + }, 5125 + "engines": { 5126 + "node": ">= 0.4" 5127 + }, 5128 + "funding": { 5129 + "url": "https://github.com/sponsors/ljharb" 5130 + } 5131 + }, 5132 + "node_modules/data-view-byte-length": { 5133 + "version": "1.0.2", 5134 + "resolved": "https://registry.npmjs.org/data-view-byte-length/-/data-view-byte-length-1.0.2.tgz", 5135 + "integrity": "sha512-tuhGbE6CfTM9+5ANGf+oQb72Ky/0+s3xKUpHvShfiz2RxMFgFPjsXuRLBVMtvMs15awe45SRb83D6wH4ew6wlQ==", 5136 + "dev": true, 5137 + "license": "MIT", 5138 + "dependencies": { 5139 + "call-bound": "^1.0.3", 5140 + "es-errors": "^1.3.0", 5141 + "is-data-view": "^1.0.2" 5142 + }, 5143 + "engines": { 5144 + "node": ">= 0.4" 5145 + }, 5146 + "funding": { 5147 + "url": "https://github.com/sponsors/inspect-js" 5148 + } 5149 + }, 5150 + "node_modules/data-view-byte-offset": { 5151 + "version": "1.0.1", 5152 + "resolved": "https://registry.npmjs.org/data-view-byte-offset/-/data-view-byte-offset-1.0.1.tgz", 5153 + "integrity": "sha512-BS8PfmtDGnrgYdOonGZQdLZslWIeCGFP9tpan0hi1Co2Zr2NKADsvGYA8XxuG/4UWgJ6Cjtv+YJnB6MM69QGlQ==", 5154 + "dev": true, 5155 + "license": "MIT", 5156 + "dependencies": { 5157 + "call-bound": "^1.0.2", 5158 + "es-errors": "^1.3.0", 5159 + "is-data-view": "^1.0.1" 5160 + }, 5161 + "engines": { 5162 + "node": ">= 0.4" 5163 + }, 5164 + "funding": { 5165 + "url": "https://github.com/sponsors/ljharb" 5166 + } 5167 + }, 5168 + "node_modules/debug": { 5169 + "version": "4.4.3", 5170 + "resolved": "https://registry.npmjs.org/debug/-/debug-4.4.3.tgz", 5171 + "integrity": "sha512-RGwwWnwQvkVfavKVt22FGLw+xYSdzARwm0ru6DhTVA3umU5hZc28V3kO4stgYryrTlLpuvgI9GiijltAjNbcqA==", 5172 + "dev": true, 5173 + "license": "MIT", 5174 + "dependencies": { 5175 + "ms": "^2.1.3" 5176 + }, 5177 + "engines": { 5178 + "node": ">=6.0" 5179 + }, 5180 + "peerDependenciesMeta": { 5181 + "supports-color": { 5182 + "optional": true 5183 + } 5184 + } 5185 + }, 5186 + "node_modules/deepmerge": { 5187 + "version": "4.3.1", 5188 + "resolved": "https://registry.npmjs.org/deepmerge/-/deepmerge-4.3.1.tgz", 5189 + "integrity": "sha512-3sUqbMEc77XqpdNO7FRyRog+eW3ph+GYCbj+rK+uYyRMuwsVy0rMiVtPn+QJlKFvWP/1PYpapqYn0Me2knFn+A==", 5190 + "dev": true, 5191 + "license": "MIT", 5192 + "engines": { 5193 + "node": ">=0.10.0" 5194 + } 5195 + }, 5196 + "node_modules/define-data-property": { 5197 + "version": "1.1.4", 5198 + "resolved": "https://registry.npmjs.org/define-data-property/-/define-data-property-1.1.4.tgz", 5199 + "integrity": "sha512-rBMvIzlpA8v6E+SJZoo++HAYqsLrkg7MSfIinMPFhmkorw7X+dOXVJQs+QT69zGkzMyfDnIMN2Wid1+NbL3T+A==", 5200 + "dev": true, 5201 + "license": "MIT", 5202 + "dependencies": { 5203 + "es-define-property": "^1.0.0", 5204 + "es-errors": "^1.3.0", 5205 + "gopd": "^1.0.1" 5206 + }, 5207 + "engines": { 5208 + "node": ">= 0.4" 5209 + }, 5210 + "funding": { 5211 + "url": "https://github.com/sponsors/ljharb" 5212 + } 5213 + }, 5214 + "node_modules/define-properties": { 5215 + "version": "1.2.1", 5216 + "resolved": "https://registry.npmjs.org/define-properties/-/define-properties-1.2.1.tgz", 5217 + "integrity": "sha512-8QmQKqEASLd5nx0U1B1okLElbUuuttJ/AnYmRXbbbGDWh6uS208EjD4Xqq/I9wK7u0v6O08XhTWnt5XtEbR6Dg==", 5218 + "dev": true, 5219 + "license": "MIT", 5220 + "dependencies": { 5221 + "define-data-property": "^1.0.1", 5222 + "has-property-descriptors": "^1.0.0", 5223 + "object-keys": "^1.1.1" 5224 + }, 5225 + "engines": { 5226 + "node": ">= 0.4" 5227 + }, 5228 + "funding": { 5229 + "url": "https://github.com/sponsors/ljharb" 5230 + } 5231 + }, 5232 + "node_modules/detect-libc": { 5233 + "version": "2.1.2", 5234 + "resolved": "https://registry.npmjs.org/detect-libc/-/detect-libc-2.1.2.tgz", 5235 + "integrity": "sha512-Btj2BOOO83o3WyH59e8MgXsxEQVcarkUOpEYrubB0urwnN10yQ364rsiByU11nZlqWYZm05i/of7io4mzihBtQ==", 5236 + "dev": true, 5237 + "license": "Apache-2.0", 5238 + "engines": { 5239 + "node": ">=8" 5240 + } 5241 + }, 5242 + "node_modules/dunder-proto": { 5243 + "version": "1.0.1", 5244 + "resolved": "https://registry.npmjs.org/dunder-proto/-/dunder-proto-1.0.1.tgz", 5245 + "integrity": "sha512-KIN/nDJBQRcXw0MLVhZE9iQHmG68qAVIBg9CqmUYjmQIhgij9U5MFvrqkUL5FbtyyzZuOeOt0zdeRe4UY7ct+A==", 5246 + "dev": true, 5247 + "license": "MIT", 5248 + "dependencies": { 5249 + "call-bind-apply-helpers": "^1.0.1", 5250 + "es-errors": "^1.3.0", 5251 + "gopd": "^1.2.0" 5252 + }, 5253 + "engines": { 5254 + "node": ">= 0.4" 5255 + } 5256 + }, 5257 + "node_modules/ejs": { 5258 + "version": "3.1.10", 5259 + "resolved": "https://registry.npmjs.org/ejs/-/ejs-3.1.10.tgz", 5260 + "integrity": "sha512-UeJmFfOrAQS8OJWPZ4qtgHyWExa088/MtK5UEyoJGFH67cDEXkZSviOiKRCZ4Xij0zxI3JECgYs3oKx+AizQBA==", 5261 + "dev": true, 5262 + "license": "Apache-2.0", 5263 + "dependencies": { 5264 + "jake": "^10.8.5" 5265 + }, 5266 + "bin": { 5267 + "ejs": "bin/cli.js" 5268 + }, 5269 + "engines": { 5270 + "node": ">=0.10.0" 5271 + } 5272 + }, 5273 + "node_modules/electron-to-chromium": { 5274 + "version": "1.5.393", 5275 + "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.5.393.tgz", 5276 + "integrity": "sha512-kiDJdIUawuEIcp9XoICKp1iTYDEbgguIPq526N1Q7jIQDeQ3CqoMx71025PI/7E48Ddtw2HuWsVjY7afEgNxmg==", 5277 + "dev": true, 5278 + "license": "ISC" 5279 + }, 5280 + "node_modules/enhanced-resolve": { 5281 + "version": "5.24.2", 5282 + "resolved": "https://registry.npmjs.org/enhanced-resolve/-/enhanced-resolve-5.24.2.tgz", 5283 + "integrity": "sha512-rpsZEGT1jFuve6QlpyRp9ckQ+kN61hvF9BzCPyMdaKTm8UJce96KBn3sorXOFXlzjPrs3Vc4T1NsSroZ3PxlFw==", 5284 + "dev": true, 5285 + "license": "MIT", 5286 + "dependencies": { 5287 + "graceful-fs": "^4.2.4", 5288 + "tapable": "^2.3.3" 5289 + }, 5290 + "engines": { 5291 + "node": ">=10.13.0" 5292 + } 5293 + }, 5294 + "node_modules/error-stack-parser-es": { 5295 + "version": "1.0.5", 5296 + "resolved": "https://registry.npmjs.org/error-stack-parser-es/-/error-stack-parser-es-1.0.5.tgz", 5297 + "integrity": "sha512-5qucVt2XcuGMcEGgWI7i+yZpmpByQ8J1lHhcL7PwqCwu9FPP3VUXzT4ltHe5i2z9dePwEHcDVOAfSnHsOlCXRA==", 5298 + "dev": true, 5299 + "license": "MIT", 5300 + "funding": { 5301 + "url": "https://github.com/sponsors/antfu" 5302 + } 5303 + }, 5304 + "node_modules/es-abstract": { 5305 + "version": "1.24.2", 5306 + "resolved": "https://registry.npmjs.org/es-abstract/-/es-abstract-1.24.2.tgz", 5307 + "integrity": "sha512-2FpH9Q5i2RRwyEP1AylXe6nYLR5OhaJTZwmlcP0dL/+JCbgg7yyEo/sEK6HeGZRf3dFpWwThaRHVApXSkW3xeg==", 5308 + "dev": true, 5309 + "license": "MIT", 5310 + "dependencies": { 5311 + "array-buffer-byte-length": "^1.0.2", 5312 + "arraybuffer.prototype.slice": "^1.0.4", 5313 + "available-typed-arrays": "^1.0.7", 5314 + "call-bind": "^1.0.8", 5315 + "call-bound": "^1.0.4", 5316 + "data-view-buffer": "^1.0.2", 5317 + "data-view-byte-length": "^1.0.2", 5318 + "data-view-byte-offset": "^1.0.1", 5319 + "es-define-property": "^1.0.1", 5320 + "es-errors": "^1.3.0", 5321 + "es-object-atoms": "^1.1.1", 5322 + "es-set-tostringtag": "^2.1.0", 5323 + "es-to-primitive": "^1.3.0", 5324 + "function.prototype.name": "^1.1.8", 5325 + "get-intrinsic": "^1.3.0", 5326 + "get-proto": "^1.0.1", 5327 + "get-symbol-description": "^1.1.0", 5328 + "globalthis": "^1.0.4", 5329 + "gopd": "^1.2.0", 5330 + "has-property-descriptors": "^1.0.2", 5331 + "has-proto": "^1.2.0", 5332 + "has-symbols": "^1.1.0", 5333 + "hasown": "^2.0.2", 5334 + "internal-slot": "^1.1.0", 5335 + "is-array-buffer": "^3.0.5", 5336 + "is-callable": "^1.2.7", 5337 + "is-data-view": "^1.0.2", 5338 + "is-negative-zero": "^2.0.3", 5339 + "is-regex": "^1.2.1", 5340 + "is-set": "^2.0.3", 5341 + "is-shared-array-buffer": "^1.0.4", 5342 + "is-string": "^1.1.1", 5343 + "is-typed-array": "^1.1.15", 5344 + "is-weakref": "^1.1.1", 5345 + "math-intrinsics": "^1.1.0", 5346 + "object-inspect": "^1.13.4", 5347 + "object-keys": "^1.1.1", 5348 + "object.assign": "^4.1.7", 5349 + "own-keys": "^1.0.1", 5350 + "regexp.prototype.flags": "^1.5.4", 5351 + "safe-array-concat": "^1.1.3", 5352 + "safe-push-apply": "^1.0.0", 5353 + "safe-regex-test": "^1.1.0", 5354 + "set-proto": "^1.0.0", 5355 + "stop-iteration-iterator": "^1.1.0", 5356 + "string.prototype.trim": "^1.2.10", 5357 + "string.prototype.trimend": "^1.0.9", 5358 + "string.prototype.trimstart": "^1.0.8", 5359 + "typed-array-buffer": "^1.0.3", 5360 + "typed-array-byte-length": "^1.0.3", 5361 + "typed-array-byte-offset": "^1.0.4", 5362 + "typed-array-length": "^1.0.7", 5363 + "unbox-primitive": "^1.1.0", 5364 + "which-typed-array": "^1.1.19" 5365 + }, 5366 + "engines": { 5367 + "node": ">= 0.4" 5368 + }, 5369 + "funding": { 5370 + "url": "https://github.com/sponsors/ljharb" 5371 + } 5372 + }, 5373 + "node_modules/es-abstract-get": { 5374 + "version": "1.0.0", 5375 + "resolved": "https://registry.npmjs.org/es-abstract-get/-/es-abstract-get-1.0.0.tgz", 5376 + "integrity": "sha512-6PMWXpdhshVvFp+FoWYs1EvG1Nj0tvk0dZM+XcK0xMEM1czRVcP6ohqPWHy6qPagSpC8j4+p89WXlT+xXJs/fg==", 5377 + "dev": true, 5378 + "license": "MIT", 5379 + "dependencies": { 5380 + "es-errors": "^1.3.0", 5381 + "es-object-atoms": "^1.1.2", 5382 + "is-callable": "^1.2.7", 5383 + "object-inspect": "^1.13.4" 5384 + }, 5385 + "engines": { 5386 + "node": ">= 0.4" 5387 + }, 5388 + "funding": { 5389 + "url": "https://github.com/sponsors/ljharb" 5390 + } 5391 + }, 5392 + "node_modules/es-define-property": { 5393 + "version": "1.0.1", 5394 + "resolved": "https://registry.npmjs.org/es-define-property/-/es-define-property-1.0.1.tgz", 5395 + "integrity": "sha512-e3nRfgfUZ4rNGL232gUgX06QNyyez04KdjFrF+LTRoOXmrOgFKDg4BCdsjW8EnT69eqdYGmRpJwiPVYNrCaW3g==", 5396 + "dev": true, 5397 + "license": "MIT", 5398 + "engines": { 5399 + "node": ">= 0.4" 5400 + } 5401 + }, 5402 + "node_modules/es-errors": { 5403 + "version": "1.3.0", 5404 + "resolved": "https://registry.npmjs.org/es-errors/-/es-errors-1.3.0.tgz", 5405 + "integrity": "sha512-Zf5H2Kxt2xjTvbJvP2ZWLEICxA6j+hAmMzIlypy4xcBg1vKVnx89Wy0GbS+kf5cwCVFFzdCFh2XSCFNULS6csw==", 5406 + "dev": true, 5407 + "license": "MIT", 5408 + "engines": { 5409 + "node": ">= 0.4" 5410 + } 5411 + }, 5412 + "node_modules/es-object-atoms": { 5413 + "version": "1.1.2", 5414 + "resolved": "https://registry.npmjs.org/es-object-atoms/-/es-object-atoms-1.1.2.tgz", 5415 + "integrity": "sha512-HWcBoN6NileqtSydK2FqHbS/LoDd2pqrnQHLyJzBj4kOp/ky2MWMN694xOfkK8/SnUsW2DH7EfyVlydKCsm1Zw==", 5416 + "dev": true, 5417 + "license": "MIT", 5418 + "dependencies": { 5419 + "es-errors": "^1.3.0" 5420 + }, 5421 + "engines": { 5422 + "node": ">= 0.4" 5423 + } 5424 + }, 5425 + "node_modules/es-set-tostringtag": { 5426 + "version": "2.1.0", 5427 + "resolved": "https://registry.npmjs.org/es-set-tostringtag/-/es-set-tostringtag-2.1.0.tgz", 5428 + "integrity": "sha512-j6vWzfrGVfyXxge+O0x5sh6cvxAog0a/4Rdd2K36zCMV5eJ+/+tOAngRO8cODMNWbVRdVlmGZQL2YS3yR8bIUA==", 5429 + "dev": true, 5430 + "license": "MIT", 5431 + "dependencies": { 5432 + "es-errors": "^1.3.0", 5433 + "get-intrinsic": "^1.2.6", 5434 + "has-tostringtag": "^1.0.2", 5435 + "hasown": "^2.0.2" 5436 + }, 5437 + "engines": { 5438 + "node": ">= 0.4" 5439 + } 5440 + }, 5441 + "node_modules/es-to-primitive": { 5442 + "version": "1.3.4", 5443 + "resolved": "https://registry.npmjs.org/es-to-primitive/-/es-to-primitive-1.3.4.tgz", 5444 + "integrity": "sha512-yPDz7wqpg1/mmHLmS3tcfTfbw5f1eryXvyghYBffGdERwe+mV7ZcWzTR8LR17Kvqt3qfPurjlonmnq3MKXIOXw==", 5445 + "dev": true, 5446 + "license": "MIT", 5447 + "dependencies": { 5448 + "es-abstract-get": "^1.0.0", 5449 + "es-define-property": "^1.0.1", 5450 + "es-errors": "^1.3.0", 5451 + "is-callable": "^1.2.7", 5452 + "is-date-object": "^1.1.0", 5453 + "is-symbol": "^1.1.1" 5454 + }, 5455 + "engines": { 5456 + "node": ">= 0.4" 5457 + }, 5458 + "funding": { 5459 + "url": "https://github.com/sponsors/ljharb" 5460 + } 5461 + }, 5462 + "node_modules/esbuild": { 5463 + "version": "0.28.1", 5464 + "resolved": "https://registry.npmjs.org/esbuild/-/esbuild-0.28.1.tgz", 5465 + "integrity": "sha512-HrJrvZv5ayxBzPfwphOoNzkzOIIlifzk0KJrGK2c8R4+LKpMtpYLQeUdjnwjWv/LZlkH2laZk+4w78pi99D4Vw==", 5466 + "dev": true, 5467 + "hasInstallScript": true, 5468 + "license": "MIT", 5469 + "bin": { 5470 + "esbuild": "bin/esbuild" 5471 + }, 5472 + "engines": { 5473 + "node": ">=18" 5474 + }, 5475 + "optionalDependencies": { 5476 + "@esbuild/aix-ppc64": "0.28.1", 5477 + "@esbuild/android-arm": "0.28.1", 5478 + "@esbuild/android-arm64": "0.28.1", 5479 + "@esbuild/android-x64": "0.28.1", 5480 + "@esbuild/darwin-arm64": "0.28.1", 5481 + "@esbuild/darwin-x64": "0.28.1", 5482 + "@esbuild/freebsd-arm64": "0.28.1", 5483 + "@esbuild/freebsd-x64": "0.28.1", 5484 + "@esbuild/linux-arm": "0.28.1", 5485 + "@esbuild/linux-arm64": "0.28.1", 5486 + "@esbuild/linux-ia32": "0.28.1", 5487 + "@esbuild/linux-loong64": "0.28.1", 5488 + "@esbuild/linux-mips64el": "0.28.1", 5489 + "@esbuild/linux-ppc64": "0.28.1", 5490 + "@esbuild/linux-riscv64": "0.28.1", 5491 + "@esbuild/linux-s390x": "0.28.1", 5492 + "@esbuild/linux-x64": "0.28.1", 5493 + "@esbuild/netbsd-arm64": "0.28.1", 5494 + "@esbuild/netbsd-x64": "0.28.1", 5495 + "@esbuild/openbsd-arm64": "0.28.1", 5496 + "@esbuild/openbsd-x64": "0.28.1", 5497 + "@esbuild/openharmony-arm64": "0.28.1", 5498 + "@esbuild/sunos-x64": "0.28.1", 5499 + "@esbuild/win32-arm64": "0.28.1", 5500 + "@esbuild/win32-ia32": "0.28.1", 5501 + "@esbuild/win32-x64": "0.28.1" 5502 + } 5503 + }, 5504 + "node_modules/escalade": { 5505 + "version": "3.2.0", 5506 + "resolved": "https://registry.npmjs.org/escalade/-/escalade-3.2.0.tgz", 5507 + "integrity": "sha512-WUj2qlxaQtO4g6Pq5c29GTcWGDyd8itL8zTlipgECz3JesAiiOKotd8JU6otB3PACgG6xkJUyVhboMS+bje/jA==", 5508 + "dev": true, 5509 + "license": "MIT", 5510 + "engines": { 5511 + "node": ">=6" 5512 + } 5513 + }, 5514 + "node_modules/estree-walker": { 5515 + "version": "2.0.2", 5516 + "resolved": "https://registry.npmjs.org/estree-walker/-/estree-walker-2.0.2.tgz", 5517 + "integrity": "sha512-Rfkk/Mp/DL7JVje3u18FxFujQlTNR2q6QfMSMB7AvCBx91NGj/ba3kCfza0f6dVDbw7YlRf/nDrn7pQrCCyQ/w==", 5518 + "dev": true, 5519 + "license": "MIT" 5520 + }, 5521 + "node_modules/esutils": { 5522 + "version": "2.0.3", 5523 + "resolved": "https://registry.npmjs.org/esutils/-/esutils-2.0.3.tgz", 5524 + "integrity": "sha512-kVscqXk4OCp68SZ0dkgEKVi6/8ij300KBWTJq32P/dYeWTSwK41WyTxalN1eRmA5Z9UU/LX9D7FWSmV9SAYx6g==", 5525 + "dev": true, 5526 + "license": "BSD-2-Clause", 5527 + "engines": { 5528 + "node": ">=0.10.0" 5529 + } 5530 + }, 5531 + "node_modules/eta": { 5532 + "version": "4.6.0", 5533 + "resolved": "https://registry.npmjs.org/eta/-/eta-4.6.0.tgz", 5534 + "integrity": "sha512-lW6is4T1NFOYnmqGZIfvixqj7A7sSvScF+DN8EK6K58xI5MZ5UvYe0GjopxOXQtZvUn4eDdVuZ8XSoYWTMEKwA==", 5535 + "dev": true, 5536 + "license": "MIT", 5537 + "engines": { 5538 + "node": ">=20" 5539 + }, 5540 + "funding": { 5541 + "url": "https://github.com/bgub/eta?sponsor=1" 5542 + } 5543 + }, 5544 + "node_modules/exifr": { 5545 + "version": "7.1.3", 5546 + "resolved": "https://registry.npmjs.org/exifr/-/exifr-7.1.3.tgz", 5547 + "integrity": "sha512-g/aje2noHivrRSLbAUtBPWFbxKdKhgj/xr1vATDdUXPOFYJlQ62Ft0oy+72V6XLIpDJfHs6gXLbBLAolqOXYRw==", 5548 + "license": "MIT" 5549 + }, 5550 + "node_modules/fast-deep-equal": { 5551 + "version": "3.1.3", 5552 + "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-3.1.3.tgz", 5553 + "integrity": "sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q==", 5554 + "dev": true, 5555 + "license": "MIT" 5556 + }, 5557 + "node_modules/fast-json-stable-stringify": { 5558 + "version": "2.1.0", 5559 + "resolved": "https://registry.npmjs.org/fast-json-stable-stringify/-/fast-json-stable-stringify-2.1.0.tgz", 5560 + "integrity": "sha512-lhd/wF+Lk98HZoTCtlVraHtfh5XYijIjalXck7saUtuanSDyLMxnHhSXEDJqHxD7msR8D0uCmqlkwjCV8xvwHw==", 5561 + "dev": true, 5562 + "license": "MIT" 5563 + }, 5564 + "node_modules/fast-uri": { 5565 + "version": "3.1.3", 5566 + "resolved": "https://registry.npmjs.org/fast-uri/-/fast-uri-3.1.3.tgz", 5567 + "integrity": "sha512-i70LwGWUduXqzicKXWshooq+sWL1K3WUU5rKZNG/0i3a1OSoX3HqhH5WbWwTmqWfor4urUakGPiRQcleRZTwOg==", 5568 + "dev": true, 5569 + "funding": [ 5570 + { 5571 + "type": "github", 5572 + "url": "https://github.com/sponsors/fastify" 5573 + }, 5574 + { 5575 + "type": "opencollective", 5576 + "url": "https://opencollective.com/fastify" 5577 + } 5578 + ], 5579 + "license": "BSD-3-Clause" 5580 + }, 5581 + "node_modules/fdir": { 5582 + "version": "6.5.0", 5583 + "resolved": "https://registry.npmjs.org/fdir/-/fdir-6.5.0.tgz", 5584 + "integrity": "sha512-tIbYtZbucOs0BRGqPJkshJUYdL+SDH7dVM8gjy+ERp3WAUjLEFJE+02kanyHtwjWOnwrKYBiwAmM0p4kLJAnXg==", 5585 + "dev": true, 5586 + "license": "MIT", 5587 + "engines": { 5588 + "node": ">=12.0.0" 5589 + }, 5590 + "peerDependencies": { 5591 + "picomatch": "^3 || ^4" 5592 + }, 5593 + "peerDependenciesMeta": { 5594 + "picomatch": { 5595 + "optional": true 5596 + } 5597 + } 5598 + }, 5599 + "node_modules/filelist": { 5600 + "version": "1.0.6", 5601 + "resolved": "https://registry.npmjs.org/filelist/-/filelist-1.0.6.tgz", 5602 + "integrity": "sha512-5giy2PkLYY1cP39p17Ech+2xlpTRL9HLspOfEgm0L6CwBXBTgsK5ou0JtzYuepxkaQ/tvhCFIJ5uXo0OrM2DxA==", 5603 + "dev": true, 5604 + "license": "Apache-2.0", 5605 + "dependencies": { 5606 + "minimatch": "^5.0.1" 5607 + } 5608 + }, 5609 + "node_modules/filelist/node_modules/balanced-match": { 5610 + "version": "1.0.2", 5611 + "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.2.tgz", 5612 + "integrity": "sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw==", 5613 + "dev": true, 5614 + "license": "MIT" 5615 + }, 5616 + "node_modules/filelist/node_modules/brace-expansion": { 5617 + "version": "2.1.2", 5618 + "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-2.1.2.tgz", 5619 + "integrity": "sha512-w5JZcKgdhDOgOwm8H+KgbosopHMuGcl6qbulwjtz3SM7I7P3yW1eAjzMPLrIE+NQ9vjgANKHWeMHnrT0OXW1oA==", 5620 + "dev": true, 5621 + "license": "MIT", 5622 + "dependencies": { 5623 + "balanced-match": "^1.0.0" 5624 + } 5625 + }, 5626 + "node_modules/filelist/node_modules/minimatch": { 5627 + "version": "5.1.9", 5628 + "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-5.1.9.tgz", 5629 + "integrity": "sha512-7o1wEA2RyMP7Iu7GNba9vc0RWWGACJOCZBJX2GJWip0ikV+wcOsgVuY9uE8CPiyQhkGFSlhuSkZPavN7u1c2Fw==", 5630 + "dev": true, 5631 + "license": "ISC", 5632 + "dependencies": { 5633 + "brace-expansion": "^2.0.1" 5634 + }, 5635 + "engines": { 5636 + "node": ">=10" 5637 + } 5638 + }, 5639 + "node_modules/for-each": { 5640 + "version": "0.3.5", 5641 + "resolved": "https://registry.npmjs.org/for-each/-/for-each-0.3.5.tgz", 5642 + "integrity": "sha512-dKx12eRCVIzqCxFGplyFKJMPvLEWgmNtUrpTiJIR5u97zEhRG8ySrtboPHZXx7daLxQVrl643cTzbab2tkQjxg==", 5643 + "dev": true, 5644 + "license": "MIT", 5645 + "dependencies": { 5646 + "is-callable": "^1.2.7" 5647 + }, 5648 + "engines": { 5649 + "node": ">= 0.4" 5650 + }, 5651 + "funding": { 5652 + "url": "https://github.com/sponsors/ljharb" 5653 + } 5654 + }, 5655 + "node_modules/foreground-child": { 5656 + "version": "3.3.1", 5657 + "resolved": "https://registry.npmjs.org/foreground-child/-/foreground-child-3.3.1.tgz", 5658 + "integrity": "sha512-gIXjKqtFuWEgzFRJA9WCQeSJLZDjgJUOMCMzxtvFq/37KojM1BFGufqsCy0r4qSQmYLsZYMeyRqzIWOMup03sw==", 5659 + "dev": true, 5660 + "license": "ISC", 5661 + "dependencies": { 5662 + "cross-spawn": "^7.0.6", 5663 + "signal-exit": "^4.0.1" 5664 + }, 5665 + "engines": { 5666 + "node": ">=14" 5667 + }, 5668 + "funding": { 5669 + "url": "https://github.com/sponsors/isaacs" 5670 + } 5671 + }, 5672 + "node_modules/fs-extra": { 5673 + "version": "9.1.0", 5674 + "resolved": "https://registry.npmjs.org/fs-extra/-/fs-extra-9.1.0.tgz", 5675 + "integrity": "sha512-hcg3ZmepS30/7BSFqRvoo3DOMQu7IjqxO5nCDt+zM9XWjb33Wg7ziNT+Qvqbuc3+gWpzO02JubVyk2G4Zvo1OQ==", 5676 + "dev": true, 5677 + "license": "MIT", 5678 + "dependencies": { 5679 + "at-least-node": "^1.0.0", 5680 + "graceful-fs": "^4.2.0", 5681 + "jsonfile": "^6.0.1", 5682 + "universalify": "^2.0.0" 5683 + }, 5684 + "engines": { 5685 + "node": ">=10" 5686 + } 5687 + }, 5688 + "node_modules/fsevents": { 5689 + "version": "2.3.3", 5690 + "resolved": "https://registry.npmjs.org/fsevents/-/fsevents-2.3.3.tgz", 5691 + "integrity": "sha512-5xoDfX+fL7faATnagmWPpbFtwh/R77WmMMqqHGS65C3vvB0YHrgF+B1YmZ3441tMj5n63k0212XNoJwzlhffQw==", 5692 + "dev": true, 5693 + "hasInstallScript": true, 5694 + "license": "MIT", 5695 + "optional": true, 5696 + "os": [ 5697 + "darwin" 5698 + ], 5699 + "engines": { 5700 + "node": "^8.16.0 || ^10.6.0 || >=11.0.0" 5701 + } 5702 + }, 5703 + "node_modules/function-bind": { 5704 + "version": "1.1.2", 5705 + "resolved": "https://registry.npmjs.org/function-bind/-/function-bind-1.1.2.tgz", 5706 + "integrity": "sha512-7XHNxH7qX9xG5mIwxkhumTox/MIRNcOgDrxWsMt2pAr23WHp6MrRlN7FBSFpCpr+oVO0F744iUgR82nJMfG2SA==", 5707 + "dev": true, 5708 + "license": "MIT", 5709 + "funding": { 5710 + "url": "https://github.com/sponsors/ljharb" 5711 + } 5712 + }, 5713 + "node_modules/function.prototype.name": { 5714 + "version": "1.2.0", 5715 + "resolved": "https://registry.npmjs.org/function.prototype.name/-/function.prototype.name-1.2.0.tgz", 5716 + "integrity": "sha512-jObKIik1P2QjPHP5nz5BaOtUlfgS0fWo8IUByNXkM+o+02sJOi94em77GwJKQSJ3gfPHdgzLNrHc1uokV4P/ew==", 5717 + "dev": true, 5718 + "license": "MIT", 5719 + "dependencies": { 5720 + "call-bind": "^1.0.9", 5721 + "call-bound": "^1.0.4", 5722 + "es-define-property": "^1.0.1", 5723 + "es-errors": "^1.3.0", 5724 + "functions-have-names": "^1.2.3", 5725 + "has-property-descriptors": "^1.0.2", 5726 + "hasown": "^2.0.4", 5727 + "is-callable": "^1.2.7", 5728 + "is-document.all": "^1.0.0" 5729 + }, 5730 + "engines": { 5731 + "node": ">= 0.4" 5732 + }, 5733 + "funding": { 5734 + "url": "https://github.com/sponsors/ljharb" 5735 + } 5736 + }, 5737 + "node_modules/functions-have-names": { 5738 + "version": "1.2.3", 5739 + "resolved": "https://registry.npmjs.org/functions-have-names/-/functions-have-names-1.2.3.tgz", 5740 + "integrity": "sha512-xckBUXyTIqT97tq2x2AMb+g163b5JFysYk0x4qxNFwbfQkmNZoiRHb6sPzI9/QV33WeuvVYBUIiD4NzNIyqaRQ==", 5741 + "dev": true, 5742 + "license": "MIT", 5743 + "funding": { 5744 + "url": "https://github.com/sponsors/ljharb" 5745 + } 5746 + }, 5747 + "node_modules/generator-function": { 5748 + "version": "2.0.1", 5749 + "resolved": "https://registry.npmjs.org/generator-function/-/generator-function-2.0.1.tgz", 5750 + "integrity": "sha512-SFdFmIJi+ybC0vjlHN0ZGVGHc3lgE0DxPAT0djjVg+kjOnSqclqmj0KQ7ykTOLP6YxoqOvuAODGdcHJn+43q3g==", 5751 + "dev": true, 5752 + "license": "MIT", 5753 + "engines": { 5754 + "node": ">= 0.4" 5755 + } 5756 + }, 5757 + "node_modules/gensync": { 5758 + "version": "1.0.0-beta.2", 5759 + "resolved": "https://registry.npmjs.org/gensync/-/gensync-1.0.0-beta.2.tgz", 5760 + "integrity": "sha512-3hN7NaskYvMDLQY55gnW3NQ+mesEAepTqlg+VEbj7zzqEMBVNhzcGYYeqFo/TlYz6eQiFcp1HcsCZO+nGgS8zg==", 5761 + "dev": true, 5762 + "license": "MIT", 5763 + "engines": { 5764 + "node": ">=6.9.0" 5765 + } 5766 + }, 5767 + "node_modules/get-intrinsic": { 5768 + "version": "1.3.0", 5769 + "resolved": "https://registry.npmjs.org/get-intrinsic/-/get-intrinsic-1.3.0.tgz", 5770 + "integrity": "sha512-9fSjSaos/fRIVIp+xSJlE6lfwhES7LNtKaCBIamHsjr2na1BiABJPo0mOjjz8GJDURarmCPGqaiVg5mfjb98CQ==", 5771 + "dev": true, 5772 + "license": "MIT", 5773 + "dependencies": { 5774 + "call-bind-apply-helpers": "^1.0.2", 5775 + "es-define-property": "^1.0.1", 5776 + "es-errors": "^1.3.0", 5777 + "es-object-atoms": "^1.1.1", 5778 + "function-bind": "^1.1.2", 5779 + "get-proto": "^1.0.1", 5780 + "gopd": "^1.2.0", 5781 + "has-symbols": "^1.1.0", 5782 + "hasown": "^2.0.2", 5783 + "math-intrinsics": "^1.1.0" 5784 + }, 5785 + "engines": { 5786 + "node": ">= 0.4" 5787 + }, 5788 + "funding": { 5789 + "url": "https://github.com/sponsors/ljharb" 5790 + } 5791 + }, 5792 + "node_modules/get-own-enumerable-property-symbols": { 5793 + "version": "3.0.2", 5794 + "resolved": "https://registry.npmjs.org/get-own-enumerable-property-symbols/-/get-own-enumerable-property-symbols-3.0.2.tgz", 5795 + "integrity": "sha512-I0UBV/XOz1XkIJHEUDMZAbzCThU/H8DxmSfmdGcKPnVhu2VfFqr34jr9777IyaTYvxjedWhqVIilEDsCdP5G6g==", 5796 + "dev": true, 5797 + "license": "ISC" 5798 + }, 5799 + "node_modules/get-proto": { 5800 + "version": "1.0.1", 5801 + "resolved": "https://registry.npmjs.org/get-proto/-/get-proto-1.0.1.tgz", 5802 + "integrity": "sha512-sTSfBjoXBp89JvIKIefqw7U2CCebsc74kiY6awiGogKtoSGbgjYE/G/+l9sF3MWFPNc9IcoOC4ODfKHfxFmp0g==", 5803 + "dev": true, 5804 + "license": "MIT", 5805 + "dependencies": { 5806 + "dunder-proto": "^1.0.1", 5807 + "es-object-atoms": "^1.0.0" 5808 + }, 5809 + "engines": { 5810 + "node": ">= 0.4" 5811 + } 5812 + }, 5813 + "node_modules/get-symbol-description": { 5814 + "version": "1.1.0", 5815 + "resolved": "https://registry.npmjs.org/get-symbol-description/-/get-symbol-description-1.1.0.tgz", 5816 + "integrity": "sha512-w9UMqWwJxHNOvoNzSJ2oPF5wvYcvP7jUvYzhp67yEhTi17ZDBBC1z9pTdGuzjD+EFIqLSYRweZjqfiPzQ06Ebg==", 5817 + "dev": true, 5818 + "license": "MIT", 5819 + "dependencies": { 5820 + "call-bound": "^1.0.3", 5821 + "es-errors": "^1.3.0", 5822 + "get-intrinsic": "^1.2.6" 5823 + }, 5824 + "engines": { 5825 + "node": ">= 0.4" 5826 + }, 5827 + "funding": { 5828 + "url": "https://github.com/sponsors/ljharb" 5829 + } 5830 + }, 5831 + "node_modules/glob": { 5832 + "version": "11.1.0", 5833 + "resolved": "https://registry.npmjs.org/glob/-/glob-11.1.0.tgz", 5834 + "integrity": "sha512-vuNwKSaKiqm7g0THUBu2x7ckSs3XJLXE+2ssL7/MfTGPLLcrJQ/4Uq1CjPTtO5cCIiRxqvN6Twy1qOwhL0Xjcw==", 5835 + "deprecated": "Old versions of glob are not supported, and contain widely publicized security vulnerabilities, which have been fixed in the current version. Please update. Support for old versions may be purchased (at exorbitant rates) by contacting i@izs.me", 5836 + "dev": true, 5837 + "license": "BlueOak-1.0.0", 5838 + "dependencies": { 5839 + "foreground-child": "^3.3.1", 5840 + "jackspeak": "^4.1.1", 5841 + "minimatch": "^10.1.1", 5842 + "minipass": "^7.1.2", 5843 + "package-json-from-dist": "^1.0.0", 5844 + "path-scurry": "^2.0.0" 5845 + }, 5846 + "bin": { 5847 + "glob": "dist/esm/bin.mjs" 5848 + }, 5849 + "engines": { 5850 + "node": "20 || >=22" 5851 + }, 5852 + "funding": { 5853 + "url": "https://github.com/sponsors/isaacs" 5854 + } 5855 + }, 5856 + "node_modules/globalthis": { 5857 + "version": "1.0.4", 5858 + "resolved": "https://registry.npmjs.org/globalthis/-/globalthis-1.0.4.tgz", 5859 + "integrity": "sha512-DpLKbNU4WylpxJykQujfCcwYWiV/Jhm50Goo0wrVILAv5jOr9d+H+UR3PhSCD2rCCEIg0uc+G+muBTwD54JhDQ==", 5860 + "dev": true, 5861 + "license": "MIT", 5862 + "dependencies": { 5863 + "define-properties": "^1.2.1", 5864 + "gopd": "^1.0.1" 5865 + }, 5866 + "engines": { 5867 + "node": ">= 0.4" 5868 + }, 5869 + "funding": { 5870 + "url": "https://github.com/sponsors/ljharb" 5871 + } 5872 + }, 5873 + "node_modules/gopd": { 5874 + "version": "1.2.0", 5875 + "resolved": "https://registry.npmjs.org/gopd/-/gopd-1.2.0.tgz", 5876 + "integrity": "sha512-ZUKRh6/kUFoAiTAtTYPZJ3hw9wNxx+BIBOijnlG9PnrJsCcSjs1wyyD6vJpaYtgnzDrKYRSqf3OO6Rfa93xsRg==", 5877 + "dev": true, 5878 + "license": "MIT", 5879 + "engines": { 5880 + "node": ">= 0.4" 5881 + }, 5882 + "funding": { 5883 + "url": "https://github.com/sponsors/ljharb" 5884 + } 5885 + }, 5886 + "node_modules/graceful-fs": { 5887 + "version": "4.2.11", 5888 + "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.2.11.tgz", 5889 + "integrity": "sha512-RbJ5/jmFcNNCcDV5o9eTnBLJ/HszWV0P73bc+Ff4nS/rJj+YaS6IGyiOL0VoBYX+l1Wrl3k63h/KrH+nhJ0XvQ==", 5890 + "dev": true, 5891 + "license": "ISC" 5892 + }, 5893 + "node_modules/has-bigints": { 5894 + "version": "1.1.0", 5895 + "resolved": "https://registry.npmjs.org/has-bigints/-/has-bigints-1.1.0.tgz", 5896 + "integrity": "sha512-R3pbpkcIqv2Pm3dUwgjclDRVmWpTJW2DcMzcIhEXEx1oh/CEMObMm3KLmRJOdvhM7o4uQBnwr8pzRK2sJWIqfg==", 5897 + "dev": true, 5898 + "license": "MIT", 5899 + "engines": { 5900 + "node": ">= 0.4" 5901 + }, 5902 + "funding": { 5903 + "url": "https://github.com/sponsors/ljharb" 5904 + } 5905 + }, 5906 + "node_modules/has-property-descriptors": { 5907 + "version": "1.0.2", 5908 + "resolved": "https://registry.npmjs.org/has-property-descriptors/-/has-property-descriptors-1.0.2.tgz", 5909 + "integrity": "sha512-55JNKuIW+vq4Ke1BjOTjM2YctQIvCT7GFzHwmfZPGo5wnrgkid0YQtnAleFSqumZm4az3n2BS+erby5ipJdgrg==", 5910 + "dev": true, 5911 + "license": "MIT", 5912 + "dependencies": { 5913 + "es-define-property": "^1.0.0" 5914 + }, 5915 + "funding": { 5916 + "url": "https://github.com/sponsors/ljharb" 5917 + } 5918 + }, 5919 + "node_modules/has-proto": { 5920 + "version": "1.2.0", 5921 + "resolved": "https://registry.npmjs.org/has-proto/-/has-proto-1.2.0.tgz", 5922 + "integrity": "sha512-KIL7eQPfHQRC8+XluaIw7BHUwwqL19bQn4hzNgdr+1wXoU0KKj6rufu47lhY7KbJR2C6T6+PfyN0Ea7wkSS+qQ==", 5923 + "dev": true, 5924 + "license": "MIT", 5925 + "dependencies": { 5926 + "dunder-proto": "^1.0.0" 5927 + }, 5928 + "engines": { 5929 + "node": ">= 0.4" 5930 + }, 5931 + "funding": { 5932 + "url": "https://github.com/sponsors/ljharb" 5933 + } 5934 + }, 5935 + "node_modules/has-symbols": { 5936 + "version": "1.1.0", 5937 + "resolved": "https://registry.npmjs.org/has-symbols/-/has-symbols-1.1.0.tgz", 5938 + "integrity": "sha512-1cDNdwJ2Jaohmb3sg4OmKaMBwuC48sYni5HUw2DvsC8LjGTLK9h+eb1X6RyuOHe4hT0ULCW68iomhjUoKUqlPQ==", 5939 + "dev": true, 5940 + "license": "MIT", 5941 + "engines": { 5942 + "node": ">= 0.4" 5943 + }, 5944 + "funding": { 5945 + "url": "https://github.com/sponsors/ljharb" 5946 + } 5947 + }, 5948 + "node_modules/has-tostringtag": { 5949 + "version": "1.0.2", 5950 + "resolved": "https://registry.npmjs.org/has-tostringtag/-/has-tostringtag-1.0.2.tgz", 5951 + "integrity": "sha512-NqADB8VjPFLM2V0VvHUewwwsw0ZWBaIdgo+ieHtK3hasLz4qeCRjYcqfB6AQrBggRKppKF8L52/VqdVsO47Dlw==", 5952 + "dev": true, 5953 + "license": "MIT", 5954 + "dependencies": { 5955 + "has-symbols": "^1.0.3" 5956 + }, 5957 + "engines": { 5958 + "node": ">= 0.4" 5959 + }, 5960 + "funding": { 5961 + "url": "https://github.com/sponsors/ljharb" 5962 + } 5963 + }, 5964 + "node_modules/hasown": { 5965 + "version": "2.0.4", 5966 + "resolved": "https://registry.npmjs.org/hasown/-/hasown-2.0.4.tgz", 5967 + "integrity": "sha512-T2UbfbBEF32wiepXIsMlTW9+dDYC6wMh/t/vYA4tuOMKqWz/n3vr1NFSxQiyP+zk2mXsoMA/i/7qV6LKut1t1A==", 5968 + "dev": true, 5969 + "license": "MIT", 5970 + "dependencies": { 5971 + "function-bind": "^1.1.2" 5972 + }, 5973 + "engines": { 5974 + "node": ">= 0.4" 5975 + } 5976 + }, 5977 + "node_modules/hono": { 5978 + "version": "4.12.30", 5979 + "resolved": "https://registry.npmjs.org/hono/-/hono-4.12.30.tgz", 5980 + "integrity": "sha512-emn+JoJjrN9YTpRDS5it/UI2SO9BAE37T6I3d963RxcZ81G9A4pr2SZTEiiaiKbzx+NKRg5BZ89fCL7gCJCUog==", 5981 + "license": "MIT", 5982 + "engines": { 5983 + "node": ">=16.9.0" 5984 + } 5985 + }, 5986 + "node_modules/idb": { 5987 + "version": "7.1.1", 5988 + "resolved": "https://registry.npmjs.org/idb/-/idb-7.1.1.tgz", 5989 + "integrity": "sha512-gchesWBzyvGHRO9W8tzUWFDycow5gwjvFKfyV9FF32Y7F50yZMp7mP+T2mJIWFx49zicqyC4uefHM17o6xKIVQ==", 5990 + "dev": true, 5991 + "license": "ISC" 5992 + }, 5993 + "node_modules/internal-slot": { 5994 + "version": "1.1.0", 5995 + "resolved": "https://registry.npmjs.org/internal-slot/-/internal-slot-1.1.0.tgz", 5996 + "integrity": "sha512-4gd7VpWNQNB4UKKCFFVcp1AVv+FMOgs9NKzjHKusc8jTMhd5eL1NqQqOpE0KzMds804/yHlglp3uxgluOqAPLw==", 5997 + "dev": true, 5998 + "license": "MIT", 5999 + "dependencies": { 6000 + "es-errors": "^1.3.0", 6001 + "hasown": "^2.0.2", 6002 + "side-channel": "^1.1.0" 6003 + }, 6004 + "engines": { 6005 + "node": ">= 0.4" 6006 + } 6007 + }, 6008 + "node_modules/is-array-buffer": { 6009 + "version": "3.0.5", 6010 + "resolved": "https://registry.npmjs.org/is-array-buffer/-/is-array-buffer-3.0.5.tgz", 6011 + "integrity": "sha512-DDfANUiiG2wC1qawP66qlTugJeL5HyzMpfr8lLK+jMQirGzNod0B12cFB/9q838Ru27sBwfw78/rdoU7RERz6A==", 6012 + "dev": true, 6013 + "license": "MIT", 6014 + "dependencies": { 6015 + "call-bind": "^1.0.8", 6016 + "call-bound": "^1.0.3", 6017 + "get-intrinsic": "^1.2.6" 6018 + }, 6019 + "engines": { 6020 + "node": ">= 0.4" 6021 + }, 6022 + "funding": { 6023 + "url": "https://github.com/sponsors/ljharb" 6024 + } 6025 + }, 6026 + "node_modules/is-async-function": { 6027 + "version": "2.1.1", 6028 + "resolved": "https://registry.npmjs.org/is-async-function/-/is-async-function-2.1.1.tgz", 6029 + "integrity": "sha512-9dgM/cZBnNvjzaMYHVoxxfPj2QXt22Ev7SuuPrs+xav0ukGB0S6d4ydZdEiM48kLx5kDV+QBPrpVnFyefL8kkQ==", 6030 + "dev": true, 6031 + "license": "MIT", 6032 + "dependencies": { 6033 + "async-function": "^1.0.0", 6034 + "call-bound": "^1.0.3", 6035 + "get-proto": "^1.0.1", 6036 + "has-tostringtag": "^1.0.2", 6037 + "safe-regex-test": "^1.1.0" 6038 + }, 6039 + "engines": { 6040 + "node": ">= 0.4" 6041 + }, 6042 + "funding": { 6043 + "url": "https://github.com/sponsors/ljharb" 6044 + } 6045 + }, 6046 + "node_modules/is-bigint": { 6047 + "version": "1.1.0", 6048 + "resolved": "https://registry.npmjs.org/is-bigint/-/is-bigint-1.1.0.tgz", 6049 + "integrity": "sha512-n4ZT37wG78iz03xPRKJrHTdZbe3IicyucEtdRsV5yglwc3GyUfbAfpSeD0FJ41NbUNSt5wbhqfp1fS+BgnvDFQ==", 6050 + "dev": true, 6051 + "license": "MIT", 6052 + "dependencies": { 6053 + "has-bigints": "^1.0.2" 6054 + }, 6055 + "engines": { 6056 + "node": ">= 0.4" 6057 + }, 6058 + "funding": { 6059 + "url": "https://github.com/sponsors/ljharb" 6060 + } 6061 + }, 6062 + "node_modules/is-boolean-object": { 6063 + "version": "1.2.2", 6064 + "resolved": "https://registry.npmjs.org/is-boolean-object/-/is-boolean-object-1.2.2.tgz", 6065 + "integrity": "sha512-wa56o2/ElJMYqjCjGkXri7it5FbebW5usLw/nPmCMs5DeZ7eziSYZhSmPRn0txqeW4LnAmQQU7FgqLpsEFKM4A==", 6066 + "dev": true, 6067 + "license": "MIT", 6068 + "dependencies": { 6069 + "call-bound": "^1.0.3", 6070 + "has-tostringtag": "^1.0.2" 6071 + }, 6072 + "engines": { 6073 + "node": ">= 0.4" 6074 + }, 6075 + "funding": { 6076 + "url": "https://github.com/sponsors/ljharb" 6077 + } 6078 + }, 6079 + "node_modules/is-callable": { 6080 + "version": "1.2.7", 6081 + "resolved": "https://registry.npmjs.org/is-callable/-/is-callable-1.2.7.tgz", 6082 + "integrity": "sha512-1BC0BVFhS/p0qtw6enp8e+8OD0UrK0oFLztSjNzhcKA3WDuJxxAPXzPuPtKkjEY9UUoEWlX/8fgKeu2S8i9JTA==", 6083 + "dev": true, 6084 + "license": "MIT", 6085 + "engines": { 6086 + "node": ">= 0.4" 6087 + }, 6088 + "funding": { 6089 + "url": "https://github.com/sponsors/ljharb" 6090 + } 6091 + }, 6092 + "node_modules/is-core-module": { 6093 + "version": "2.16.2", 6094 + "resolved": "https://registry.npmjs.org/is-core-module/-/is-core-module-2.16.2.tgz", 6095 + "integrity": "sha512-evOr8xfXKxE6qSR0hSXL2r3sd7ALj8+7jQEUvPYcm5sgZFdJ+AYzT6yNmJenvIYQBgIGwfwz08sL8zoL7yq2BA==", 6096 + "dev": true, 6097 + "license": "MIT", 6098 + "dependencies": { 6099 + "hasown": "^2.0.3" 6100 + }, 6101 + "engines": { 6102 + "node": ">= 0.4" 6103 + }, 6104 + "funding": { 6105 + "url": "https://github.com/sponsors/ljharb" 6106 + } 6107 + }, 6108 + "node_modules/is-data-view": { 6109 + "version": "1.0.2", 6110 + "resolved": "https://registry.npmjs.org/is-data-view/-/is-data-view-1.0.2.tgz", 6111 + "integrity": "sha512-RKtWF8pGmS87i2D6gqQu/l7EYRlVdfzemCJN/P3UOs//x1QE7mfhvzHIApBTRf7axvT6DMGwSwBXYCT0nfB9xw==", 6112 + "dev": true, 6113 + "license": "MIT", 6114 + "dependencies": { 6115 + "call-bound": "^1.0.2", 6116 + "get-intrinsic": "^1.2.6", 6117 + "is-typed-array": "^1.1.13" 6118 + }, 6119 + "engines": { 6120 + "node": ">= 0.4" 6121 + }, 6122 + "funding": { 6123 + "url": "https://github.com/sponsors/ljharb" 6124 + } 6125 + }, 6126 + "node_modules/is-date-object": { 6127 + "version": "1.1.0", 6128 + "resolved": "https://registry.npmjs.org/is-date-object/-/is-date-object-1.1.0.tgz", 6129 + "integrity": "sha512-PwwhEakHVKTdRNVOw+/Gyh0+MzlCl4R6qKvkhuvLtPMggI1WAHt9sOwZxQLSGpUaDnrdyDsomoRgNnCfKNSXXg==", 6130 + "dev": true, 6131 + "license": "MIT", 6132 + "dependencies": { 6133 + "call-bound": "^1.0.2", 6134 + "has-tostringtag": "^1.0.2" 6135 + }, 6136 + "engines": { 6137 + "node": ">= 0.4" 6138 + }, 6139 + "funding": { 6140 + "url": "https://github.com/sponsors/ljharb" 6141 + } 6142 + }, 6143 + "node_modules/is-document.all": { 6144 + "version": "1.0.0", 6145 + "resolved": "https://registry.npmjs.org/is-document.all/-/is-document.all-1.0.0.tgz", 6146 + "integrity": "sha512-+XSoyS05OdBbhFuELhgTCpFNHkpBOJqtsZfUFFpe5QTw+9Sjbh8zitxhQkYAo6wV7e1Vb8cAPvpCk9jGam/82g==", 6147 + "dev": true, 6148 + "license": "MIT", 6149 + "dependencies": { 6150 + "call-bound": "^1.0.4" 6151 + }, 6152 + "engines": { 6153 + "node": ">= 0.4" 6154 + }, 6155 + "funding": { 6156 + "url": "https://github.com/sponsors/ljharb" 6157 + } 6158 + }, 6159 + "node_modules/is-finalizationregistry": { 6160 + "version": "1.1.1", 6161 + "resolved": "https://registry.npmjs.org/is-finalizationregistry/-/is-finalizationregistry-1.1.1.tgz", 6162 + "integrity": "sha512-1pC6N8qWJbWoPtEjgcL2xyhQOP491EQjeUo3qTKcmV8YSDDJrOepfG8pcC7h/QgnQHYSv0mJ3Z/ZWxmatVrysg==", 6163 + "dev": true, 6164 + "license": "MIT", 6165 + "dependencies": { 6166 + "call-bound": "^1.0.3" 6167 + }, 6168 + "engines": { 6169 + "node": ">= 0.4" 6170 + }, 6171 + "funding": { 6172 + "url": "https://github.com/sponsors/ljharb" 6173 + } 6174 + }, 6175 + "node_modules/is-generator-function": { 6176 + "version": "1.1.2", 6177 + "resolved": "https://registry.npmjs.org/is-generator-function/-/is-generator-function-1.1.2.tgz", 6178 + "integrity": "sha512-upqt1SkGkODW9tsGNG5mtXTXtECizwtS2kA161M+gJPc1xdb/Ax629af6YrTwcOeQHbewrPNlE5Dx7kzvXTizA==", 6179 + "dev": true, 6180 + "license": "MIT", 6181 + "dependencies": { 6182 + "call-bound": "^1.0.4", 6183 + "generator-function": "^2.0.0", 6184 + "get-proto": "^1.0.1", 6185 + "has-tostringtag": "^1.0.2", 6186 + "safe-regex-test": "^1.1.0" 6187 + }, 6188 + "engines": { 6189 + "node": ">= 0.4" 6190 + }, 6191 + "funding": { 6192 + "url": "https://github.com/sponsors/ljharb" 6193 + } 6194 + }, 6195 + "node_modules/is-map": { 6196 + "version": "2.0.3", 6197 + "resolved": "https://registry.npmjs.org/is-map/-/is-map-2.0.3.tgz", 6198 + "integrity": "sha512-1Qed0/Hr2m+YqxnM09CjA2d/i6YZNfF6R2oRAOj36eUdS6qIV/huPJNSEpKbupewFs+ZsJlxsjjPbc0/afW6Lw==", 6199 + "dev": true, 6200 + "license": "MIT", 6201 + "engines": { 6202 + "node": ">= 0.4" 6203 + }, 6204 + "funding": { 6205 + "url": "https://github.com/sponsors/ljharb" 6206 + } 6207 + }, 6208 + "node_modules/is-module": { 6209 + "version": "1.0.0", 6210 + "resolved": "https://registry.npmjs.org/is-module/-/is-module-1.0.0.tgz", 6211 + "integrity": "sha512-51ypPSPCoTEIN9dy5Oy+h4pShgJmPCygKfyRCISBI+JoWT/2oJvK8QPxmwv7b/p239jXrm9M1mlQbyKJ5A152g==", 6212 + "dev": true, 6213 + "license": "MIT" 6214 + }, 6215 + "node_modules/is-negative-zero": { 6216 + "version": "2.0.3", 6217 + "resolved": "https://registry.npmjs.org/is-negative-zero/-/is-negative-zero-2.0.3.tgz", 6218 + "integrity": "sha512-5KoIu2Ngpyek75jXodFvnafB6DJgr3u8uuK0LEZJjrU19DrMD3EVERaR8sjz8CCGgpZvxPl9SuE1GMVPFHx1mw==", 6219 + "dev": true, 6220 + "license": "MIT", 6221 + "engines": { 6222 + "node": ">= 0.4" 6223 + }, 6224 + "funding": { 6225 + "url": "https://github.com/sponsors/ljharb" 6226 + } 6227 + }, 6228 + "node_modules/is-number-object": { 6229 + "version": "1.1.1", 6230 + "resolved": "https://registry.npmjs.org/is-number-object/-/is-number-object-1.1.1.tgz", 6231 + "integrity": "sha512-lZhclumE1G6VYD8VHe35wFaIif+CTy5SJIi5+3y4psDgWu4wPDoBhF8NxUOinEc7pHgiTsT6MaBb92rKhhD+Xw==", 6232 + "dev": true, 6233 + "license": "MIT", 6234 + "dependencies": { 6235 + "call-bound": "^1.0.3", 6236 + "has-tostringtag": "^1.0.2" 6237 + }, 6238 + "engines": { 6239 + "node": ">= 0.4" 6240 + }, 6241 + "funding": { 6242 + "url": "https://github.com/sponsors/ljharb" 6243 + } 6244 + }, 6245 + "node_modules/is-obj": { 6246 + "version": "1.0.1", 6247 + "resolved": "https://registry.npmjs.org/is-obj/-/is-obj-1.0.1.tgz", 6248 + "integrity": "sha512-l4RyHgRqGN4Y3+9JHVrNqO+tN0rV5My76uW5/nuO4K1b6vw5G8d/cmFjP9tRfEsdhZNt0IFdZuK/c2Vr4Nb+Qg==", 6249 + "dev": true, 6250 + "license": "MIT", 6251 + "engines": { 6252 + "node": ">=0.10.0" 6253 + } 6254 + }, 6255 + "node_modules/is-regex": { 6256 + "version": "1.2.1", 6257 + "resolved": "https://registry.npmjs.org/is-regex/-/is-regex-1.2.1.tgz", 6258 + "integrity": "sha512-MjYsKHO5O7mCsmRGxWcLWheFqN9DJ/2TmngvjKXihe6efViPqc274+Fx/4fYj/r03+ESvBdTXK0V6tA3rgez1g==", 6259 + "dev": true, 6260 + "license": "MIT", 6261 + "dependencies": { 6262 + "call-bound": "^1.0.2", 6263 + "gopd": "^1.2.0", 6264 + "has-tostringtag": "^1.0.2", 6265 + "hasown": "^2.0.2" 6266 + }, 6267 + "engines": { 6268 + "node": ">= 0.4" 6269 + }, 6270 + "funding": { 6271 + "url": "https://github.com/sponsors/ljharb" 6272 + } 6273 + }, 6274 + "node_modules/is-regexp": { 6275 + "version": "1.0.0", 6276 + "resolved": "https://registry.npmjs.org/is-regexp/-/is-regexp-1.0.0.tgz", 6277 + "integrity": "sha512-7zjFAPO4/gwyQAAgRRmqeEeyIICSdmCqa3tsVHMdBzaXXRiqopZL4Cyghg/XulGWrtABTpbnYYzzIRffLkP4oA==", 6278 + "dev": true, 6279 + "license": "MIT", 6280 + "engines": { 6281 + "node": ">=0.10.0" 6282 + } 6283 + }, 6284 + "node_modules/is-set": { 6285 + "version": "2.0.3", 6286 + "resolved": "https://registry.npmjs.org/is-set/-/is-set-2.0.3.tgz", 6287 + "integrity": "sha512-iPAjerrse27/ygGLxw+EBR9agv9Y6uLeYVJMu+QNCoouJ1/1ri0mGrcWpfCqFZuzzx3WjtwxG098X+n4OuRkPg==", 6288 + "dev": true, 6289 + "license": "MIT", 6290 + "engines": { 6291 + "node": ">= 0.4" 6292 + }, 6293 + "funding": { 6294 + "url": "https://github.com/sponsors/ljharb" 6295 + } 6296 + }, 6297 + "node_modules/is-shared-array-buffer": { 6298 + "version": "1.0.4", 6299 + "resolved": "https://registry.npmjs.org/is-shared-array-buffer/-/is-shared-array-buffer-1.0.4.tgz", 6300 + "integrity": "sha512-ISWac8drv4ZGfwKl5slpHG9OwPNty4jOWPRIhBpxOoD+hqITiwuipOQ2bNthAzwA3B4fIjO4Nln74N0S9byq8A==", 6301 + "dev": true, 6302 + "license": "MIT", 6303 + "dependencies": { 6304 + "call-bound": "^1.0.3" 6305 + }, 6306 + "engines": { 6307 + "node": ">= 0.4" 6308 + }, 6309 + "funding": { 6310 + "url": "https://github.com/sponsors/ljharb" 6311 + } 6312 + }, 6313 + "node_modules/is-stream": { 6314 + "version": "2.0.1", 6315 + "resolved": "https://registry.npmjs.org/is-stream/-/is-stream-2.0.1.tgz", 6316 + "integrity": "sha512-hFoiJiTl63nn+kstHGBtewWSKnQLpyb155KHheA1l39uvtO9nWIop1p3udqPcUd/xbF1VLMO4n7OI6p7RbngDg==", 6317 + "dev": true, 6318 + "license": "MIT", 6319 + "engines": { 6320 + "node": ">=8" 6321 + }, 6322 + "funding": { 6323 + "url": "https://github.com/sponsors/sindresorhus" 6324 + } 6325 + }, 6326 + "node_modules/is-string": { 6327 + "version": "1.1.1", 6328 + "resolved": "https://registry.npmjs.org/is-string/-/is-string-1.1.1.tgz", 6329 + "integrity": "sha512-BtEeSsoaQjlSPBemMQIrY1MY0uM6vnS1g5fmufYOtnxLGUZM2178PKbhsk7Ffv58IX+ZtcvoGwccYsh0PglkAA==", 6330 + "dev": true, 6331 + "license": "MIT", 6332 + "dependencies": { 6333 + "call-bound": "^1.0.3", 6334 + "has-tostringtag": "^1.0.2" 6335 + }, 6336 + "engines": { 6337 + "node": ">= 0.4" 6338 + }, 6339 + "funding": { 6340 + "url": "https://github.com/sponsors/ljharb" 6341 + } 6342 + }, 6343 + "node_modules/is-symbol": { 6344 + "version": "1.1.1", 6345 + "resolved": "https://registry.npmjs.org/is-symbol/-/is-symbol-1.1.1.tgz", 6346 + "integrity": "sha512-9gGx6GTtCQM73BgmHQXfDmLtfjjTUDSyoxTCbp5WtoixAhfgsDirWIcVQ/IHpvI5Vgd5i/J5F7B9cN/WlVbC/w==", 6347 + "dev": true, 6348 + "license": "MIT", 6349 + "dependencies": { 6350 + "call-bound": "^1.0.2", 6351 + "has-symbols": "^1.1.0", 6352 + "safe-regex-test": "^1.1.0" 6353 + }, 6354 + "engines": { 6355 + "node": ">= 0.4" 6356 + }, 6357 + "funding": { 6358 + "url": "https://github.com/sponsors/ljharb" 6359 + } 6360 + }, 6361 + "node_modules/is-typed-array": { 6362 + "version": "1.1.15", 6363 + "resolved": "https://registry.npmjs.org/is-typed-array/-/is-typed-array-1.1.15.tgz", 6364 + "integrity": "sha512-p3EcsicXjit7SaskXHs1hA91QxgTw46Fv6EFKKGS5DRFLD8yKnohjF3hxoju94b/OcMZoQukzpPpBE9uLVKzgQ==", 6365 + "dev": true, 6366 + "license": "MIT", 6367 + "dependencies": { 6368 + "which-typed-array": "^1.1.16" 6369 + }, 6370 + "engines": { 6371 + "node": ">= 0.4" 6372 + }, 6373 + "funding": { 6374 + "url": "https://github.com/sponsors/ljharb" 6375 + } 6376 + }, 6377 + "node_modules/is-weakmap": { 6378 + "version": "2.0.2", 6379 + "resolved": "https://registry.npmjs.org/is-weakmap/-/is-weakmap-2.0.2.tgz", 6380 + "integrity": "sha512-K5pXYOm9wqY1RgjpL3YTkF39tni1XajUIkawTLUo9EZEVUFga5gSQJF8nNS7ZwJQ02y+1YCNYcMh+HIf1ZqE+w==", 6381 + "dev": true, 6382 + "license": "MIT", 6383 + "engines": { 6384 + "node": ">= 0.4" 6385 + }, 6386 + "funding": { 6387 + "url": "https://github.com/sponsors/ljharb" 6388 + } 6389 + }, 6390 + "node_modules/is-weakref": { 6391 + "version": "1.1.1", 6392 + "resolved": "https://registry.npmjs.org/is-weakref/-/is-weakref-1.1.1.tgz", 6393 + "integrity": "sha512-6i9mGWSlqzNMEqpCp93KwRS1uUOodk2OJ6b+sq7ZPDSy2WuI5NFIxp/254TytR8ftefexkWn5xNiHUNpPOfSew==", 6394 + "dev": true, 6395 + "license": "MIT", 6396 + "dependencies": { 6397 + "call-bound": "^1.0.3" 6398 + }, 6399 + "engines": { 6400 + "node": ">= 0.4" 6401 + }, 6402 + "funding": { 6403 + "url": "https://github.com/sponsors/ljharb" 6404 + } 6405 + }, 6406 + "node_modules/is-weakset": { 6407 + "version": "2.0.4", 6408 + "resolved": "https://registry.npmjs.org/is-weakset/-/is-weakset-2.0.4.tgz", 6409 + "integrity": "sha512-mfcwb6IzQyOKTs84CQMrOwW4gQcaTOAWJ0zzJCl2WSPDrWk/OzDaImWFH3djXhb24g4eudZfLRozAvPGw4d9hQ==", 6410 + "dev": true, 6411 + "license": "MIT", 6412 + "dependencies": { 6413 + "call-bound": "^1.0.3", 6414 + "get-intrinsic": "^1.2.6" 6415 + }, 6416 + "engines": { 6417 + "node": ">= 0.4" 6418 + }, 6419 + "funding": { 6420 + "url": "https://github.com/sponsors/ljharb" 6421 + } 6422 + }, 6423 + "node_modules/isarray": { 6424 + "version": "2.0.5", 6425 + "resolved": "https://registry.npmjs.org/isarray/-/isarray-2.0.5.tgz", 6426 + "integrity": "sha512-xHjhDr3cNBK0BzdUJSPXZntQUx/mwMS5Rw4A7lPJ90XGAO6ISP/ePDNuo0vhqOZU+UD5JoodwCAAoZQd3FeAKw==", 6427 + "dev": true, 6428 + "license": "MIT" 6429 + }, 6430 + "node_modules/isexe": { 6431 + "version": "2.0.0", 6432 + "resolved": "https://registry.npmjs.org/isexe/-/isexe-2.0.0.tgz", 6433 + "integrity": "sha512-RHxMLp9lnKHGHRng9QFhRCMbYAcVpn69smSGcq3f36xjgVVWThj4qqLbTLlq7Ssj8B+fIQ1EuCEGI2lKsyQeIw==", 6434 + "dev": true, 6435 + "license": "ISC" 6436 + }, 6437 + "node_modules/jackspeak": { 6438 + "version": "4.2.3", 6439 + "resolved": "https://registry.npmjs.org/jackspeak/-/jackspeak-4.2.3.tgz", 6440 + "integrity": "sha512-ykkVRwrYvFm1nb2AJfKKYPr0emF6IiXDYUaFx4Zn9ZuIH7MrzEZ3sD5RlqGXNRpHtvUHJyOnCEFxOlNDtGo7wg==", 6441 + "dev": true, 6442 + "license": "BlueOak-1.0.0", 6443 + "dependencies": { 6444 + "@isaacs/cliui": "^9.0.0" 6445 + }, 6446 + "engines": { 6447 + "node": "20 || >=22" 6448 + }, 6449 + "funding": { 6450 + "url": "https://github.com/sponsors/isaacs" 6451 + } 6452 + }, 6453 + "node_modules/jake": { 6454 + "version": "10.9.4", 6455 + "resolved": "https://registry.npmjs.org/jake/-/jake-10.9.4.tgz", 6456 + "integrity": "sha512-wpHYzhxiVQL+IV05BLE2Xn34zW1S223hvjtqk0+gsPrwd/8JNLXJgZZM/iPFsYc1xyphF+6M6EvdE5E9MBGkDA==", 6457 + "dev": true, 6458 + "license": "Apache-2.0", 6459 + "dependencies": { 6460 + "async": "^3.2.6", 6461 + "filelist": "^1.0.4", 6462 + "picocolors": "^1.1.1" 6463 + }, 6464 + "bin": { 6465 + "jake": "bin/cli.js" 6466 + }, 6467 + "engines": { 6468 + "node": ">=10" 6469 + } 6470 + }, 6471 + "node_modules/jiti": { 6472 + "version": "2.7.0", 6473 + "resolved": "https://registry.npmjs.org/jiti/-/jiti-2.7.0.tgz", 6474 + "integrity": "sha512-AC/7JofJvZGrrneWNaEnJeOLUx+JlGt7tNa0wZiRPT4MY1wmfKjt2+6O2p2uz2+skll8OZZmJMNqeke7kKbNgQ==", 6475 + "dev": true, 6476 + "license": "MIT", 6477 + "bin": { 6478 + "jiti": "lib/jiti-cli.mjs" 6479 + } 6480 + }, 6481 + "node_modules/js-tokens": { 6482 + "version": "4.0.0", 6483 + "resolved": "https://registry.npmjs.org/js-tokens/-/js-tokens-4.0.0.tgz", 6484 + "integrity": "sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ==", 6485 + "dev": true, 6486 + "license": "MIT" 6487 + }, 6488 + "node_modules/jsesc": { 6489 + "version": "3.1.0", 6490 + "resolved": "https://registry.npmjs.org/jsesc/-/jsesc-3.1.0.tgz", 6491 + "integrity": "sha512-/sM3dO2FOzXjKQhJuo0Q173wf2KOo8t4I8vHy6lF9poUp7bKT0/NHE8fPX23PwfhnykfqnC2xRxOnVw5XuGIaA==", 6492 + "dev": true, 6493 + "license": "MIT", 6494 + "bin": { 6495 + "jsesc": "bin/jsesc" 6496 + }, 6497 + "engines": { 6498 + "node": ">=6" 6499 + } 6500 + }, 6501 + "node_modules/json-schema-traverse": { 6502 + "version": "1.0.0", 6503 + "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-1.0.0.tgz", 6504 + "integrity": "sha512-NM8/P9n3XjXhIZn1lLhkFaACTOURQXjWhV4BA/RnOv8xvgqtqpAX9IO4mRQxSx1Rlo4tqzeqb0sOlruaOy3dug==", 6505 + "dev": true, 6506 + "license": "MIT" 6507 + }, 6508 + "node_modules/json5": { 6509 + "version": "2.2.3", 6510 + "resolved": "https://registry.npmjs.org/json5/-/json5-2.2.3.tgz", 6511 + "integrity": "sha512-XmOWe7eyHYH14cLdVPoyg+GOH3rYX++KpzrylJwSW98t3Nk+U8XOl8FWKOgwtzdb8lXGf6zYwDUzeHMWfxasyg==", 6512 + "dev": true, 6513 + "license": "MIT", 6514 + "bin": { 6515 + "json5": "lib/cli.js" 6516 + }, 6517 + "engines": { 6518 + "node": ">=6" 6519 + } 6520 + }, 6521 + "node_modules/jsonfile": { 6522 + "version": "6.2.1", 6523 + "resolved": "https://registry.npmjs.org/jsonfile/-/jsonfile-6.2.1.tgz", 6524 + "integrity": "sha512-zwOTdL3rFQ/lRdBnntKVOX6k5cKJwEc1HdilT71BWEu7J41gXIB2MRp+vxduPSwZJPWBxEzv4yH1wYLJGUHX4Q==", 6525 + "dev": true, 6526 + "license": "MIT", 6527 + "dependencies": { 6528 + "universalify": "^2.0.0" 6529 + }, 6530 + "optionalDependencies": { 6531 + "graceful-fs": "^4.1.6" 6532 + } 6533 + }, 6534 + "node_modules/jsonpointer": { 6535 + "version": "5.0.1", 6536 + "resolved": "https://registry.npmjs.org/jsonpointer/-/jsonpointer-5.0.1.tgz", 6537 + "integrity": "sha512-p/nXbhSEcu3pZRdkW1OfJhpsVtW1gd4Wa1fnQc9YLiTfAjn0312eMKimbdIQzuZl9aa9xUGaRlP9T/CJE/ditQ==", 6538 + "dev": true, 6539 + "license": "MIT", 6540 + "engines": { 6541 + "node": ">=0.10.0" 6542 + } 6543 + }, 6544 + "node_modules/kleur": { 6545 + "version": "4.1.5", 6546 + "resolved": "https://registry.npmjs.org/kleur/-/kleur-4.1.5.tgz", 6547 + "integrity": "sha512-o+NO+8WrRiQEE4/7nwRJhN1HWpVmJm511pBHUxPLtp0BUISzlBplORYSmTclCnJvQq2tKu/sgl3xVpkc7ZWuQQ==", 6548 + "dev": true, 6549 + "license": "MIT", 6550 + "engines": { 6551 + "node": ">=6" 6552 + } 6553 + }, 6554 + "node_modules/leven": { 6555 + "version": "3.1.0", 6556 + "resolved": "https://registry.npmjs.org/leven/-/leven-3.1.0.tgz", 6557 + "integrity": "sha512-qsda+H8jTaUaN/x5vzW2rzc+8Rw4TAQ/4KjB46IwK5VH+IlVeeeje/EoZRpiXvIqjFgK84QffqPztGI3VBLG1A==", 6558 + "dev": true, 6559 + "license": "MIT", 6560 + "engines": { 6561 + "node": ">=6" 6562 + } 6563 + }, 6564 + "node_modules/lightningcss": { 6565 + "version": "1.32.0", 6566 + "resolved": "https://registry.npmjs.org/lightningcss/-/lightningcss-1.32.0.tgz", 6567 + "integrity": "sha512-NXYBzinNrblfraPGyrbPoD19C1h9lfI/1mzgWYvXUTe414Gz/X1FD2XBZSZM7rRTrMA8JL3OtAaGifrIKhQ5yQ==", 6568 + "dev": true, 6569 + "license": "MPL-2.0", 6570 + "dependencies": { 6571 + "detect-libc": "^2.0.3" 6572 + }, 6573 + "engines": { 6574 + "node": ">= 12.0.0" 6575 + }, 6576 + "funding": { 6577 + "type": "opencollective", 6578 + "url": "https://opencollective.com/parcel" 6579 + }, 6580 + "optionalDependencies": { 6581 + "lightningcss-android-arm64": "1.32.0", 6582 + "lightningcss-darwin-arm64": "1.32.0", 6583 + "lightningcss-darwin-x64": "1.32.0", 6584 + "lightningcss-freebsd-x64": "1.32.0", 6585 + "lightningcss-linux-arm-gnueabihf": "1.32.0", 6586 + "lightningcss-linux-arm64-gnu": "1.32.0", 6587 + "lightningcss-linux-arm64-musl": "1.32.0", 6588 + "lightningcss-linux-x64-gnu": "1.32.0", 6589 + "lightningcss-linux-x64-musl": "1.32.0", 6590 + "lightningcss-win32-arm64-msvc": "1.32.0", 6591 + "lightningcss-win32-x64-msvc": "1.32.0" 6592 + } 6593 + }, 6594 + "node_modules/lightningcss-android-arm64": { 6595 + "version": "1.32.0", 6596 + "resolved": "https://registry.npmjs.org/lightningcss-android-arm64/-/lightningcss-android-arm64-1.32.0.tgz", 6597 + "integrity": "sha512-YK7/ClTt4kAK0vo6w3X+Pnm0D2cf2vPHbhOXdoNti1Ga0al1P4TBZhwjATvjNwLEBCnKvjJc2jQgHXH0NEwlAg==", 6598 + "cpu": [ 6599 + "arm64" 6600 + ], 6601 + "dev": true, 6602 + "license": "MPL-2.0", 6603 + "optional": true, 6604 + "os": [ 6605 + "android" 6606 + ], 6607 + "engines": { 6608 + "node": ">= 12.0.0" 6609 + }, 6610 + "funding": { 6611 + "type": "opencollective", 6612 + "url": "https://opencollective.com/parcel" 6613 + } 6614 + }, 6615 + "node_modules/lightningcss-darwin-arm64": { 6616 + "version": "1.32.0", 6617 + "resolved": "https://registry.npmjs.org/lightningcss-darwin-arm64/-/lightningcss-darwin-arm64-1.32.0.tgz", 6618 + "integrity": "sha512-RzeG9Ju5bag2Bv1/lwlVJvBE3q6TtXskdZLLCyfg5pt+HLz9BqlICO7LZM7VHNTTn/5PRhHFBSjk5lc4cmscPQ==", 6619 + "cpu": [ 6620 + "arm64" 6621 + ], 6622 + "dev": true, 6623 + "license": "MPL-2.0", 6624 + "optional": true, 6625 + "os": [ 6626 + "darwin" 6627 + ], 6628 + "engines": { 6629 + "node": ">= 12.0.0" 6630 + }, 6631 + "funding": { 6632 + "type": "opencollective", 6633 + "url": "https://opencollective.com/parcel" 6634 + } 6635 + }, 6636 + "node_modules/lightningcss-darwin-x64": { 6637 + "version": "1.32.0", 6638 + "resolved": "https://registry.npmjs.org/lightningcss-darwin-x64/-/lightningcss-darwin-x64-1.32.0.tgz", 6639 + "integrity": "sha512-U+QsBp2m/s2wqpUYT/6wnlagdZbtZdndSmut/NJqlCcMLTWp5muCrID+K5UJ6jqD2BFshejCYXniPDbNh73V8w==", 6640 + "cpu": [ 6641 + "x64" 6642 + ], 6643 + "dev": true, 6644 + "license": "MPL-2.0", 6645 + "optional": true, 6646 + "os": [ 6647 + "darwin" 6648 + ], 6649 + "engines": { 6650 + "node": ">= 12.0.0" 6651 + }, 6652 + "funding": { 6653 + "type": "opencollective", 6654 + "url": "https://opencollective.com/parcel" 6655 + } 6656 + }, 6657 + "node_modules/lightningcss-freebsd-x64": { 6658 + "version": "1.32.0", 6659 + "resolved": "https://registry.npmjs.org/lightningcss-freebsd-x64/-/lightningcss-freebsd-x64-1.32.0.tgz", 6660 + "integrity": "sha512-JCTigedEksZk3tHTTthnMdVfGf61Fky8Ji2E4YjUTEQX14xiy/lTzXnu1vwiZe3bYe0q+SpsSH/CTeDXK6WHig==", 6661 + "cpu": [ 6662 + "x64" 6663 + ], 6664 + "dev": true, 6665 + "license": "MPL-2.0", 6666 + "optional": true, 6667 + "os": [ 6668 + "freebsd" 6669 + ], 6670 + "engines": { 6671 + "node": ">= 12.0.0" 6672 + }, 6673 + "funding": { 6674 + "type": "opencollective", 6675 + "url": "https://opencollective.com/parcel" 6676 + } 6677 + }, 6678 + "node_modules/lightningcss-linux-arm-gnueabihf": { 6679 + "version": "1.32.0", 6680 + "resolved": "https://registry.npmjs.org/lightningcss-linux-arm-gnueabihf/-/lightningcss-linux-arm-gnueabihf-1.32.0.tgz", 6681 + "integrity": "sha512-x6rnnpRa2GL0zQOkt6rts3YDPzduLpWvwAF6EMhXFVZXD4tPrBkEFqzGowzCsIWsPjqSK+tyNEODUBXeeVHSkw==", 6682 + "cpu": [ 6683 + "arm" 6684 + ], 6685 + "dev": true, 6686 + "license": "MPL-2.0", 6687 + "optional": true, 6688 + "os": [ 6689 + "linux" 6690 + ], 6691 + "engines": { 6692 + "node": ">= 12.0.0" 6693 + }, 6694 + "funding": { 6695 + "type": "opencollective", 6696 + "url": "https://opencollective.com/parcel" 6697 + } 6698 + }, 6699 + "node_modules/lightningcss-linux-arm64-gnu": { 6700 + "version": "1.32.0", 6701 + "resolved": "https://registry.npmjs.org/lightningcss-linux-arm64-gnu/-/lightningcss-linux-arm64-gnu-1.32.0.tgz", 6702 + "integrity": "sha512-0nnMyoyOLRJXfbMOilaSRcLH3Jw5z9HDNGfT/gwCPgaDjnx0i8w7vBzFLFR1f6CMLKF8gVbebmkUN3fa/kQJpQ==", 6703 + "cpu": [ 6704 + "arm64" 6705 + ], 6706 + "dev": true, 6707 + "license": "MPL-2.0", 6708 + "optional": true, 6709 + "os": [ 6710 + "linux" 6711 + ], 6712 + "engines": { 6713 + "node": ">= 12.0.0" 6714 + }, 6715 + "funding": { 6716 + "type": "opencollective", 6717 + "url": "https://opencollective.com/parcel" 6718 + } 6719 + }, 6720 + "node_modules/lightningcss-linux-arm64-musl": { 6721 + "version": "1.32.0", 6722 + "resolved": "https://registry.npmjs.org/lightningcss-linux-arm64-musl/-/lightningcss-linux-arm64-musl-1.32.0.tgz", 6723 + "integrity": "sha512-UpQkoenr4UJEzgVIYpI80lDFvRmPVg6oqboNHfoH4CQIfNA+HOrZ7Mo7KZP02dC6LjghPQJeBsvXhJod/wnIBg==", 6724 + "cpu": [ 6725 + "arm64" 6726 + ], 6727 + "dev": true, 6728 + "license": "MPL-2.0", 6729 + "optional": true, 6730 + "os": [ 6731 + "linux" 6732 + ], 6733 + "engines": { 6734 + "node": ">= 12.0.0" 6735 + }, 6736 + "funding": { 6737 + "type": "opencollective", 6738 + "url": "https://opencollective.com/parcel" 6739 + } 6740 + }, 6741 + "node_modules/lightningcss-linux-x64-gnu": { 6742 + "version": "1.32.0", 6743 + "resolved": "https://registry.npmjs.org/lightningcss-linux-x64-gnu/-/lightningcss-linux-x64-gnu-1.32.0.tgz", 6744 + "integrity": "sha512-V7Qr52IhZmdKPVr+Vtw8o+WLsQJYCTd8loIfpDaMRWGUZfBOYEJeyJIkqGIDMZPwPx24pUMfwSxxI8phr/MbOA==", 6745 + "cpu": [ 6746 + "x64" 6747 + ], 6748 + "dev": true, 6749 + "license": "MPL-2.0", 6750 + "optional": true, 6751 + "os": [ 6752 + "linux" 6753 + ], 6754 + "engines": { 6755 + "node": ">= 12.0.0" 6756 + }, 6757 + "funding": { 6758 + "type": "opencollective", 6759 + "url": "https://opencollective.com/parcel" 6760 + } 6761 + }, 6762 + "node_modules/lightningcss-linux-x64-musl": { 6763 + "version": "1.32.0", 6764 + "resolved": "https://registry.npmjs.org/lightningcss-linux-x64-musl/-/lightningcss-linux-x64-musl-1.32.0.tgz", 6765 + "integrity": "sha512-bYcLp+Vb0awsiXg/80uCRezCYHNg1/l3mt0gzHnWV9XP1W5sKa5/TCdGWaR/zBM2PeF/HbsQv/j2URNOiVuxWg==", 6766 + "cpu": [ 6767 + "x64" 6768 + ], 6769 + "dev": true, 6770 + "license": "MPL-2.0", 6771 + "optional": true, 6772 + "os": [ 6773 + "linux" 6774 + ], 6775 + "engines": { 6776 + "node": ">= 12.0.0" 6777 + }, 6778 + "funding": { 6779 + "type": "opencollective", 6780 + "url": "https://opencollective.com/parcel" 6781 + } 6782 + }, 6783 + "node_modules/lightningcss-win32-arm64-msvc": { 6784 + "version": "1.32.0", 6785 + "resolved": "https://registry.npmjs.org/lightningcss-win32-arm64-msvc/-/lightningcss-win32-arm64-msvc-1.32.0.tgz", 6786 + "integrity": "sha512-8SbC8BR40pS6baCM8sbtYDSwEVQd4JlFTOlaD3gWGHfThTcABnNDBda6eTZeqbofalIJhFx0qKzgHJmcPTnGdw==", 6787 + "cpu": [ 6788 + "arm64" 6789 + ], 6790 + "dev": true, 6791 + "license": "MPL-2.0", 6792 + "optional": true, 6793 + "os": [ 6794 + "win32" 6795 + ], 6796 + "engines": { 6797 + "node": ">= 12.0.0" 6798 + }, 6799 + "funding": { 6800 + "type": "opencollective", 6801 + "url": "https://opencollective.com/parcel" 6802 + } 6803 + }, 6804 + "node_modules/lightningcss-win32-x64-msvc": { 6805 + "version": "1.32.0", 6806 + "resolved": "https://registry.npmjs.org/lightningcss-win32-x64-msvc/-/lightningcss-win32-x64-msvc-1.32.0.tgz", 6807 + "integrity": "sha512-Amq9B/SoZYdDi1kFrojnoqPLxYhQ4Wo5XiL8EVJrVsB8ARoC1PWW6VGtT0WKCemjy8aC+louJnjS7U18x3b06Q==", 6808 + "cpu": [ 6809 + "x64" 6810 + ], 6811 + "dev": true, 6812 + "license": "MPL-2.0", 6813 + "optional": true, 6814 + "os": [ 6815 + "win32" 6816 + ], 6817 + "engines": { 6818 + "node": ">= 12.0.0" 6819 + }, 6820 + "funding": { 6821 + "type": "opencollective", 6822 + "url": "https://opencollective.com/parcel" 6823 + } 6824 + }, 6825 + "node_modules/lodash.debounce": { 6826 + "version": "4.0.8", 6827 + "resolved": "https://registry.npmjs.org/lodash.debounce/-/lodash.debounce-4.0.8.tgz", 6828 + "integrity": "sha512-FT1yDzDYEoYWhnSGnpE/4Kj1fLZkDFyqRb7fNt6FdYOSxlUWAtp42Eh6Wb0rGIv/m9Bgo7x4GhQbm5Ys4SG5ow==", 6829 + "dev": true, 6830 + "license": "MIT" 6831 + }, 6832 + "node_modules/lodash.sortby": { 6833 + "version": "4.7.0", 6834 + "resolved": "https://registry.npmjs.org/lodash.sortby/-/lodash.sortby-4.7.0.tgz", 6835 + "integrity": "sha512-HDWXG8isMntAyRF5vZ7xKuEvOhT4AhlRt/3czTSjvGUxjYCBVRQY48ViDHyfYz9VIoBkW4TMGQNapx+l3RUwdA==", 6836 + "dev": true, 6837 + "license": "MIT" 6838 + }, 6839 + "node_modules/lru-cache": { 6840 + "version": "5.1.1", 6841 + "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-5.1.1.tgz", 6842 + "integrity": "sha512-KpNARQA3Iwv+jTA0utUVVbrh+Jlrr1Fv0e56GGzAFOXN7dk/FviaDW8LHmK52DlcH4WP2n6gI8vN1aesBFgo9w==", 6843 + "dev": true, 6844 + "license": "ISC", 6845 + "dependencies": { 6846 + "yallist": "^3.0.2" 6847 + } 6848 + }, 6849 + "node_modules/magic-string": { 6850 + "version": "0.30.21", 6851 + "resolved": "https://registry.npmjs.org/magic-string/-/magic-string-0.30.21.tgz", 6852 + "integrity": "sha512-vd2F4YUyEXKGcLHoq+TEyCjxueSeHnFxyyjNp80yg0XV4vUhnDer/lvvlqM/arB5bXQN5K2/3oinyCRyx8T2CQ==", 6853 + "dev": true, 6854 + "license": "MIT", 6855 + "dependencies": { 6856 + "@jridgewell/sourcemap-codec": "^1.5.5" 6857 + } 6858 + }, 6859 + "node_modules/math-intrinsics": { 6860 + "version": "1.1.0", 6861 + "resolved": "https://registry.npmjs.org/math-intrinsics/-/math-intrinsics-1.1.0.tgz", 6862 + "integrity": "sha512-/IXtbwEk5HTPyEwyKX6hGkYXxM9nbj64B+ilVJnC/R6B0pH5G4V3b0pVbL7DBj4tkhBAppbQUlf6F6Xl9LHu1g==", 6863 + "dev": true, 6864 + "license": "MIT", 6865 + "engines": { 6866 + "node": ">= 0.4" 6867 + } 6868 + }, 6869 + "node_modules/miniflare": { 6870 + "version": "4.20260714.0", 6871 + "resolved": "https://registry.npmjs.org/miniflare/-/miniflare-4.20260714.0.tgz", 6872 + "integrity": "sha512-MYlTCLdWCPqvrYY2uLwOjXwmglXuiHE3TGGkbOW4BwjUPa1r07E0iuHwrNDIs/sxK21r+o90Jx58AV2KeNdJZw==", 6873 + "dev": true, 6874 + "license": "MIT", 6875 + "dependencies": { 6876 + "@cspotcode/source-map-support": "0.8.1", 6877 + "sharp": "0.34.5", 6878 + "undici": "7.28.0", 6879 + "workerd": "1.20260714.1", 6880 + "ws": "8.21.0", 6881 + "youch": "4.1.0-beta.10" 6882 + }, 6883 + "bin": { 6884 + "miniflare": "bootstrap.js" 6885 + }, 6886 + "engines": { 6887 + "node": ">=22.0.0" 6888 + } 6889 + }, 6890 + "node_modules/minimatch": { 6891 + "version": "10.2.5", 6892 + "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-10.2.5.tgz", 6893 + "integrity": "sha512-MULkVLfKGYDFYejP07QOurDLLQpcjk7Fw+7jXS2R2czRQzR56yHRveU5NDJEOviH+hETZKSkIk5c+T23GjFUMg==", 6894 + "dev": true, 6895 + "license": "BlueOak-1.0.0", 6896 + "dependencies": { 6897 + "brace-expansion": "^5.0.5" 6898 + }, 6899 + "engines": { 6900 + "node": "18 || 20 || >=22" 6901 + }, 6902 + "funding": { 6903 + "url": "https://github.com/sponsors/isaacs" 6904 + } 6905 + }, 6906 + "node_modules/minipass": { 6907 + "version": "7.1.3", 6908 + "resolved": "https://registry.npmjs.org/minipass/-/minipass-7.1.3.tgz", 6909 + "integrity": "sha512-tEBHqDnIoM/1rXME1zgka9g6Q2lcoCkxHLuc7ODJ5BxbP5d4c2Z5cGgtXAku59200Cx7diuHTOYfSBD8n6mm8A==", 6910 + "dev": true, 6911 + "license": "BlueOak-1.0.0", 6912 + "engines": { 6913 + "node": ">=16 || 14 >=14.17" 6914 + } 6915 + }, 6916 + "node_modules/ms": { 6917 + "version": "2.1.3", 6918 + "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.3.tgz", 6919 + "integrity": "sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==", 6920 + "dev": true, 6921 + "license": "MIT" 6922 + }, 6923 + "node_modules/nanoid": { 6924 + "version": "3.3.16", 6925 + "resolved": "https://registry.npmjs.org/nanoid/-/nanoid-3.3.16.tgz", 6926 + "integrity": "sha512-bzlKTyNJ7+LdGIIwy8ijFpIqEQIvafahV7eYykJ8Cvh42EdJeODoJ6gUJXpQJvej1BddH8OqTXZNE/KfbWAu8Q==", 6927 + "dev": true, 6928 + "funding": [ 6929 + { 6930 + "type": "github", 6931 + "url": "https://github.com/sponsors/ai" 6932 + } 6933 + ], 6934 + "license": "MIT", 6935 + "bin": { 6936 + "nanoid": "bin/nanoid.cjs" 6937 + }, 6938 + "engines": { 6939 + "node": "^10 || ^12 || ^13.7 || ^14 || >=15.0.1" 6940 + } 6941 + }, 6942 + "node_modules/node-releases": { 6943 + "version": "2.0.51", 6944 + "resolved": "https://registry.npmjs.org/node-releases/-/node-releases-2.0.51.tgz", 6945 + "integrity": "sha512-wRNIrw4DmVLKQlbgOMdkMx27Wrpzes2hh5Jtbi2bjPd+4wJstWIqP5A+lscnqbm0xxmT5Bpg8Lec5ItEBwx6BQ==", 6946 + "dev": true, 6947 + "license": "MIT", 6948 + "engines": { 6949 + "node": ">=18" 6950 + } 6951 + }, 6952 + "node_modules/object-inspect": { 6953 + "version": "1.13.4", 6954 + "resolved": "https://registry.npmjs.org/object-inspect/-/object-inspect-1.13.4.tgz", 6955 + "integrity": "sha512-W67iLl4J2EXEGTbfeHCffrjDfitvLANg0UlX3wFUUSTx92KXRFegMHUVgSqE+wvhAbi4WqjGg9czysTV2Epbew==", 6956 + "dev": true, 6957 + "license": "MIT", 6958 + "engines": { 6959 + "node": ">= 0.4" 6960 + }, 6961 + "funding": { 6962 + "url": "https://github.com/sponsors/ljharb" 6963 + } 6964 + }, 6965 + "node_modules/object-keys": { 6966 + "version": "1.1.1", 6967 + "resolved": "https://registry.npmjs.org/object-keys/-/object-keys-1.1.1.tgz", 6968 + "integrity": "sha512-NuAESUOUMrlIXOfHKzD6bpPu3tYt3xvjNdRIQ+FeT0lNb4K8WR70CaDxhuNguS2XG+GjkyMwOzsN5ZktImfhLA==", 6969 + "dev": true, 6970 + "license": "MIT", 6971 + "engines": { 6972 + "node": ">= 0.4" 6973 + } 6974 + }, 6975 + "node_modules/object.assign": { 6976 + "version": "4.1.7", 6977 + "resolved": "https://registry.npmjs.org/object.assign/-/object.assign-4.1.7.tgz", 6978 + "integrity": "sha512-nK28WOo+QIjBkDduTINE4JkF/UJJKyf2EJxvJKfblDpyg0Q+pkOHNTL0Qwy6NP6FhE/EnzV73BxxqcJaXY9anw==", 6979 + "dev": true, 6980 + "license": "MIT", 6981 + "dependencies": { 6982 + "call-bind": "^1.0.8", 6983 + "call-bound": "^1.0.3", 6984 + "define-properties": "^1.2.1", 6985 + "es-object-atoms": "^1.0.0", 6986 + "has-symbols": "^1.1.0", 6987 + "object-keys": "^1.1.1" 6988 + }, 6989 + "engines": { 6990 + "node": ">= 0.4" 6991 + }, 6992 + "funding": { 6993 + "url": "https://github.com/sponsors/ljharb" 6994 + } 6995 + }, 6996 + "node_modules/own-keys": { 6997 + "version": "1.0.1", 6998 + "resolved": "https://registry.npmjs.org/own-keys/-/own-keys-1.0.1.tgz", 6999 + "integrity": "sha512-qFOyK5PjiWZd+QQIh+1jhdb9LpxTF0qs7Pm8o5QHYZ0M3vKqSqzsZaEB6oWlxZ+q2sJBMI/Ktgd2N5ZwQoRHfg==", 7000 + "dev": true, 7001 + "license": "MIT", 7002 + "dependencies": { 7003 + "get-intrinsic": "^1.2.6", 7004 + "object-keys": "^1.1.1", 7005 + "safe-push-apply": "^1.0.0" 7006 + }, 7007 + "engines": { 7008 + "node": ">= 0.4" 7009 + }, 7010 + "funding": { 7011 + "url": "https://github.com/sponsors/ljharb" 7012 + } 7013 + }, 7014 + "node_modules/package-json-from-dist": { 7015 + "version": "1.0.1", 7016 + "resolved": "https://registry.npmjs.org/package-json-from-dist/-/package-json-from-dist-1.0.1.tgz", 7017 + "integrity": "sha512-UEZIS3/by4OC8vL3P2dTXRETpebLI2NiI5vIrjaD/5UtrkFX/tNbwjTSRAGC/+7CAo2pIcBaRgWmcBBHcsaCIw==", 7018 + "dev": true, 7019 + "license": "BlueOak-1.0.0" 7020 + }, 7021 + "node_modules/path-key": { 7022 + "version": "3.1.1", 7023 + "resolved": "https://registry.npmjs.org/path-key/-/path-key-3.1.1.tgz", 7024 + "integrity": "sha512-ojmeN0qd+y0jszEtoY48r0Peq5dwMEkIlCOu6Q5f41lfkswXuKtYrhgoTpLnyIcHm24Uhqx+5Tqm2InSwLhE6Q==", 7025 + "dev": true, 7026 + "license": "MIT", 7027 + "engines": { 7028 + "node": ">=8" 7029 + } 7030 + }, 7031 + "node_modules/path-parse": { 7032 + "version": "1.0.7", 7033 + "resolved": "https://registry.npmjs.org/path-parse/-/path-parse-1.0.7.tgz", 7034 + "integrity": "sha512-LDJzPVEEEPR+y48z93A0Ed0yXb8pAByGWo/k5YYdYgpY2/2EsOsksJrq7lOHxryrVOn1ejG6oAp8ahvOIQD8sw==", 7035 + "dev": true, 7036 + "license": "MIT" 7037 + }, 7038 + "node_modules/path-scurry": { 7039 + "version": "2.0.2", 7040 + "resolved": "https://registry.npmjs.org/path-scurry/-/path-scurry-2.0.2.tgz", 7041 + "integrity": "sha512-3O/iVVsJAPsOnpwWIeD+d6z/7PmqApyQePUtCndjatj/9I5LylHvt5qluFaBT3I5h3r1ejfR056c+FCv+NnNXg==", 7042 + "dev": true, 7043 + "license": "BlueOak-1.0.0", 7044 + "dependencies": { 7045 + "lru-cache": "^11.0.0", 7046 + "minipass": "^7.1.2" 7047 + }, 7048 + "engines": { 7049 + "node": "18 || 20 || >=22" 7050 + }, 7051 + "funding": { 7052 + "url": "https://github.com/sponsors/isaacs" 7053 + } 7054 + }, 7055 + "node_modules/path-scurry/node_modules/lru-cache": { 7056 + "version": "11.5.2", 7057 + "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-11.5.2.tgz", 7058 + "integrity": "sha512-4pfM1Ff0x50o0tQwb5ucw/RzNyD0/YJME6IVcStalZuMWxdt3sR3huStTtxz4PUmvZfRguvDejasvQ2kifR11g==", 7059 + "dev": true, 7060 + "license": "BlueOak-1.0.0", 7061 + "engines": { 7062 + "node": "20 || >=22" 7063 + } 7064 + }, 7065 + "node_modules/path-to-regexp": { 7066 + "version": "6.3.0", 7067 + "resolved": "https://registry.npmjs.org/path-to-regexp/-/path-to-regexp-6.3.0.tgz", 7068 + "integrity": "sha512-Yhpw4T9C6hPpgPeA28us07OJeqZ5EzQTkbfwuhsUg0c237RomFoETJgmp2sa3F/41gfLE6G5cqcYwznmeEeOlQ==", 7069 + "dev": true, 7070 + "license": "MIT" 7071 + }, 7072 + "node_modules/pathe": { 7073 + "version": "2.0.3", 7074 + "resolved": "https://registry.npmjs.org/pathe/-/pathe-2.0.3.tgz", 7075 + "integrity": "sha512-WUjGcAqP1gQacoQe+OBJsFA7Ld4DyXuUIjZ5cc75cLHvJ7dtNsTugphxIADwspS+AraAUePCKrSVtPLFj/F88w==", 7076 + "dev": true, 7077 + "license": "MIT" 7078 + }, 7079 + "node_modules/picocolors": { 7080 + "version": "1.1.1", 7081 + "resolved": "https://registry.npmjs.org/picocolors/-/picocolors-1.1.1.tgz", 7082 + "integrity": "sha512-xceH2snhtb5M9liqDsmEw56le376mTZkEX/jEb/RxNFyegNul7eNslCXP9FDj/Lcu0X8KEyMceP2ntpaHrDEVA==", 7083 + "dev": true, 7084 + "license": "ISC" 7085 + }, 7086 + "node_modules/picomatch": { 7087 + "version": "4.0.5", 7088 + "resolved": "https://registry.npmjs.org/picomatch/-/picomatch-4.0.5.tgz", 7089 + "integrity": "sha512-RvwwcruNjI1ncT5xRakeyS9Lf8lcItv34KD+aif+VH9kduAyfYBipGh12274xtenIPZ119/R9BdTBa8gAwSh0A==", 7090 + "dev": true, 7091 + "license": "MIT", 7092 + "engines": { 7093 + "node": ">=12" 7094 + }, 7095 + "funding": { 7096 + "url": "https://github.com/sponsors/jonschlinkert" 7097 + } 7098 + }, 7099 + "node_modules/possible-typed-array-names": { 7100 + "version": "1.1.0", 7101 + "resolved": "https://registry.npmjs.org/possible-typed-array-names/-/possible-typed-array-names-1.1.0.tgz", 7102 + "integrity": "sha512-/+5VFTchJDoVj3bhoqi6UeymcD00DAwb1nJwamzPvHEszJ4FpF6SNNbUbOS8yI56qHzdV8eK0qEfOSiodkTdxg==", 7103 + "dev": true, 7104 + "license": "MIT", 7105 + "engines": { 7106 + "node": ">= 0.4" 7107 + } 7108 + }, 7109 + "node_modules/postcss": { 7110 + "version": "8.5.19", 7111 + "resolved": "https://registry.npmjs.org/postcss/-/postcss-8.5.19.tgz", 7112 + "integrity": "sha512-Mz8SaolMd8nB+G13WkORcxQKHZ/NE4xXevtkJHVuG+guo9/wYKlIMTKAqGdEmYOXR2ijPjTYNHssizdaVSUNdQ==", 7113 + "dev": true, 7114 + "funding": [ 7115 + { 7116 + "type": "opencollective", 7117 + "url": "https://opencollective.com/postcss/" 7118 + }, 7119 + { 7120 + "type": "tidelift", 7121 + "url": "https://tidelift.com/funding/github/npm/postcss" 7122 + }, 7123 + { 7124 + "type": "github", 7125 + "url": "https://github.com/sponsors/ai" 7126 + } 7127 + ], 7128 + "license": "MIT", 7129 + "dependencies": { 7130 + "nanoid": "^3.3.12", 7131 + "picocolors": "^1.1.1", 7132 + "source-map-js": "^1.2.1" 7133 + }, 7134 + "engines": { 7135 + "node": "^10 || ^12 || >=14" 7136 + } 7137 + }, 7138 + "node_modules/pretty-bytes": { 7139 + "version": "6.1.1", 7140 + "resolved": "https://registry.npmjs.org/pretty-bytes/-/pretty-bytes-6.1.1.tgz", 7141 + "integrity": "sha512-mQUvGU6aUFQ+rNvTIAcZuWGRT9a6f6Yrg9bHs4ImKF+HZCEK+plBvnAZYSIQztknZF2qnzNtr6F8s0+IuptdlQ==", 7142 + "dev": true, 7143 + "license": "MIT", 7144 + "engines": { 7145 + "node": "^14.13.1 || >=16.0.0" 7146 + }, 7147 + "funding": { 7148 + "url": "https://github.com/sponsors/sindresorhus" 7149 + } 7150 + }, 7151 + "node_modules/punycode": { 7152 + "version": "2.3.1", 7153 + "resolved": "https://registry.npmjs.org/punycode/-/punycode-2.3.1.tgz", 7154 + "integrity": "sha512-vYt7UD1U9Wg6138shLtLOvdAu+8DsC/ilFtEVHcH+wydcSpNE20AfSOduf6MkRFahL5FY7X1oU7nKVZFtfq8Fg==", 7155 + "dev": true, 7156 + "license": "MIT", 7157 + "engines": { 7158 + "node": ">=6" 7159 + } 7160 + }, 7161 + "node_modules/pvtsutils": { 7162 + "version": "1.3.6", 7163 + "resolved": "https://registry.npmjs.org/pvtsutils/-/pvtsutils-1.3.6.tgz", 7164 + "integrity": "sha512-PLgQXQ6H2FWCaeRak8vvk1GW462lMxB5s3Jm673N82zI4vqtVUPuZdffdZbPDFRoU8kAhItWFtPCWiPpp4/EDg==", 7165 + "license": "MIT", 7166 + "dependencies": { 7167 + "tslib": "^2.8.1" 7168 + } 7169 + }, 7170 + "node_modules/pvutils": { 7171 + "version": "1.1.5", 7172 + "resolved": "https://registry.npmjs.org/pvutils/-/pvutils-1.1.5.tgz", 7173 + "integrity": "sha512-KTqnxsgGiQ6ZAzZCVlJH5eOjSnvlyEgx1m8bkRJfOhmGRqfo5KLvmAlACQkrjEtOQ4B7wF9TdSLIs9O90MX9xA==", 7174 + "license": "MIT", 7175 + "engines": { 7176 + "node": ">=16.0.0" 7177 + } 7178 + }, 7179 + "node_modules/react": { 7180 + "version": "19.2.7", 7181 + "resolved": "https://registry.npmjs.org/react/-/react-19.2.7.tgz", 7182 + "integrity": "sha512-HNe9WslTbXmFK8o8cmwgAeJFSBvt1bPdHCVKtaaV+WlAN36mpT4hcRpwbf3fY56ar2oIXzsBpOAiIRHAdY0OlQ==", 7183 + "license": "MIT", 7184 + "engines": { 7185 + "node": ">=0.10.0" 7186 + } 7187 + }, 7188 + "node_modules/react-dom": { 7189 + "version": "19.2.7", 7190 + "resolved": "https://registry.npmjs.org/react-dom/-/react-dom-19.2.7.tgz", 7191 + "integrity": "sha512-t0BRVXvbiE/o20Hfw669rLbMCDWtYZLvmJigy2f0MxsXF+71pxhR3xOkspmsO8h3ZlNzyibAmtCa3l4lYKk6gQ==", 7192 + "license": "MIT", 7193 + "dependencies": { 7194 + "scheduler": "^0.27.0" 7195 + }, 7196 + "peerDependencies": { 7197 + "react": "^19.2.7" 7198 + } 7199 + }, 7200 + "node_modules/react-router": { 7201 + "version": "7.18.1", 7202 + "resolved": "https://registry.npmjs.org/react-router/-/react-router-7.18.1.tgz", 7203 + "integrity": "sha512-GDLgg3i3uM0aeJO3Fm+TCS+sDQ7gu12T6x0qdTEzcwqEfleci7JwugVNIF3U//0FWKnJT7ptG+20B2jfDqnZAg==", 7204 + "license": "MIT", 7205 + "dependencies": { 7206 + "cookie": "^1.0.1", 7207 + "set-cookie-parser": "^2.6.0" 7208 + }, 7209 + "engines": { 7210 + "node": ">=20.0.0" 7211 + }, 7212 + "peerDependencies": { 7213 + "react": ">=18", 7214 + "react-dom": ">=18" 7215 + }, 7216 + "peerDependenciesMeta": { 7217 + "react-dom": { 7218 + "optional": true 7219 + } 7220 + } 7221 + }, 7222 + "node_modules/react-router-dom": { 7223 + "version": "7.18.1", 7224 + "resolved": "https://registry.npmjs.org/react-router-dom/-/react-router-dom-7.18.1.tgz", 7225 + "integrity": "sha512-KaZh+X/6UtEp28x51AUYZDMg9NGoz2ja3dNHa+ta/tk40vCzKhQ/RypCWBMLbmDr6//E24Vv5uPsrqXFozdkAg==", 7226 + "license": "MIT", 7227 + "dependencies": { 7228 + "react-router": "7.18.1" 7229 + }, 7230 + "engines": { 7231 + "node": ">=20.0.0" 7232 + }, 7233 + "peerDependencies": { 7234 + "react": ">=18", 7235 + "react-dom": ">=18" 7236 + } 7237 + }, 7238 + "node_modules/reflect-metadata": { 7239 + "version": "0.2.2", 7240 + "resolved": "https://registry.npmjs.org/reflect-metadata/-/reflect-metadata-0.2.2.tgz", 7241 + "integrity": "sha512-urBwgfrvVP/eAyXx4hluJivBKzuEbSQs9rKWCrCkbSxNv8mxPcUZKeuoF3Uy4mJl3Lwprp6yy5/39VWigZ4K6Q==", 7242 + "license": "Apache-2.0" 7243 + }, 7244 + "node_modules/reflect.getprototypeof": { 7245 + "version": "1.0.10", 7246 + "resolved": "https://registry.npmjs.org/reflect.getprototypeof/-/reflect.getprototypeof-1.0.10.tgz", 7247 + "integrity": "sha512-00o4I+DVrefhv+nX0ulyi3biSHCPDe+yLv5o/p6d/UVlirijB8E16FtfwSAi4g3tcqrQ4lRAqQSoFEZJehYEcw==", 7248 + "dev": true, 7249 + "license": "MIT", 7250 + "dependencies": { 7251 + "call-bind": "^1.0.8", 7252 + "define-properties": "^1.2.1", 7253 + "es-abstract": "^1.23.9", 7254 + "es-errors": "^1.3.0", 7255 + "es-object-atoms": "^1.0.0", 7256 + "get-intrinsic": "^1.2.7", 7257 + "get-proto": "^1.0.1", 7258 + "which-builtin-type": "^1.2.1" 7259 + }, 7260 + "engines": { 7261 + "node": ">= 0.4" 7262 + }, 7263 + "funding": { 7264 + "url": "https://github.com/sponsors/ljharb" 7265 + } 7266 + }, 7267 + "node_modules/regenerate": { 7268 + "version": "1.4.2", 7269 + "resolved": "https://registry.npmjs.org/regenerate/-/regenerate-1.4.2.tgz", 7270 + "integrity": "sha512-zrceR/XhGYU/d/opr2EKO7aRHUeiBI8qjtfHqADTwZd6Szfy16la6kqD0MIUs5z5hx6AaKa+PixpPrR289+I0A==", 7271 + "dev": true, 7272 + "license": "MIT" 7273 + }, 7274 + "node_modules/regenerate-unicode-properties": { 7275 + "version": "10.2.2", 7276 + "resolved": "https://registry.npmjs.org/regenerate-unicode-properties/-/regenerate-unicode-properties-10.2.2.tgz", 7277 + "integrity": "sha512-m03P+zhBeQd1RGnYxrGyDAPpWX/epKirLrp8e3qevZdVkKtnCrjjWczIbYc8+xd6vcTStVlqfycTx1KR4LOr0g==", 7278 + "dev": true, 7279 + "license": "MIT", 7280 + "dependencies": { 7281 + "regenerate": "^1.4.2" 7282 + }, 7283 + "engines": { 7284 + "node": ">=4" 7285 + } 7286 + }, 7287 + "node_modules/regexp.prototype.flags": { 7288 + "version": "1.5.4", 7289 + "resolved": "https://registry.npmjs.org/regexp.prototype.flags/-/regexp.prototype.flags-1.5.4.tgz", 7290 + "integrity": "sha512-dYqgNSZbDwkaJ2ceRd9ojCGjBq+mOm9LmtXnAnEGyHhN/5R7iDW2TRw3h+o/jCFxus3P2LfWIIiwowAjANm7IA==", 7291 + "dev": true, 7292 + "license": "MIT", 7293 + "dependencies": { 7294 + "call-bind": "^1.0.8", 7295 + "define-properties": "^1.2.1", 7296 + "es-errors": "^1.3.0", 7297 + "get-proto": "^1.0.1", 7298 + "gopd": "^1.2.0", 7299 + "set-function-name": "^2.0.2" 7300 + }, 7301 + "engines": { 7302 + "node": ">= 0.4" 7303 + }, 7304 + "funding": { 7305 + "url": "https://github.com/sponsors/ljharb" 7306 + } 7307 + }, 7308 + "node_modules/regexpu-core": { 7309 + "version": "6.4.0", 7310 + "resolved": "https://registry.npmjs.org/regexpu-core/-/regexpu-core-6.4.0.tgz", 7311 + "integrity": "sha512-0ghuzq67LI9bLXpOX/ISfve/Mq33a4aFRzoQYhnnok1JOFpmE/A2TBGkNVenOGEeSBCjIiWcc6MVOG5HEQv0sA==", 7312 + "dev": true, 7313 + "license": "MIT", 7314 + "dependencies": { 7315 + "regenerate": "^1.4.2", 7316 + "regenerate-unicode-properties": "^10.2.2", 7317 + "regjsgen": "^0.8.0", 7318 + "regjsparser": "^0.13.0", 7319 + "unicode-match-property-ecmascript": "^2.0.0", 7320 + "unicode-match-property-value-ecmascript": "^2.2.1" 7321 + }, 7322 + "engines": { 7323 + "node": ">=4" 7324 + } 7325 + }, 7326 + "node_modules/regjsgen": { 7327 + "version": "0.8.0", 7328 + "resolved": "https://registry.npmjs.org/regjsgen/-/regjsgen-0.8.0.tgz", 7329 + "integrity": "sha512-RvwtGe3d7LvWiDQXeQw8p5asZUmfU1G/l6WbUXeHta7Y2PEIvBTwH6E2EfmYUK8pxcxEdEmaomqyp0vZZ7C+3Q==", 7330 + "dev": true, 7331 + "license": "MIT" 7332 + }, 7333 + "node_modules/regjsparser": { 7334 + "version": "0.13.2", 7335 + "resolved": "https://registry.npmjs.org/regjsparser/-/regjsparser-0.13.2.tgz", 7336 + "integrity": "sha512-NgRBy2Nx/bE+9F27nVHnqcN5HjyLmecqsqx2PJHu3/IEtADD4WuxuXIVExD5PoSDFVrl78dOonfcOe5O+5nbzQ==", 7337 + "dev": true, 7338 + "license": "BSD-2-Clause", 7339 + "dependencies": { 7340 + "jsesc": "~3.1.0" 7341 + }, 7342 + "bin": { 7343 + "regjsparser": "bin/parser" 7344 + } 7345 + }, 7346 + "node_modules/require-from-string": { 7347 + "version": "2.0.2", 7348 + "resolved": "https://registry.npmjs.org/require-from-string/-/require-from-string-2.0.2.tgz", 7349 + "integrity": "sha512-Xf0nWe6RseziFMu+Ap9biiUbmplq6S9/p+7w7YXP/JBHhrUDDUhwa+vANyubuqfZWTveU//DYVGsDG7RKL/vEw==", 7350 + "dev": true, 7351 + "license": "MIT", 7352 + "engines": { 7353 + "node": ">=0.10.0" 7354 + } 7355 + }, 7356 + "node_modules/resolve": { 7357 + "version": "1.22.12", 7358 + "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.22.12.tgz", 7359 + "integrity": "sha512-TyeJ1zif53BPfHootBGwPRYT1RUt6oGWsaQr8UyZW/eAm9bKoijtvruSDEmZHm92CwS9nj7/fWttqPCgzep8CA==", 7360 + "dev": true, 7361 + "license": "MIT", 7362 + "dependencies": { 7363 + "es-errors": "^1.3.0", 7364 + "is-core-module": "^2.16.1", 7365 + "path-parse": "^1.0.7", 7366 + "supports-preserve-symlinks-flag": "^1.0.0" 7367 + }, 7368 + "bin": { 7369 + "resolve": "bin/resolve" 7370 + }, 7371 + "engines": { 7372 + "node": ">= 0.4" 7373 + }, 7374 + "funding": { 7375 + "url": "https://github.com/sponsors/ljharb" 7376 + } 7377 + }, 7378 + "node_modules/rolldown": { 7379 + "version": "1.1.5", 7380 + "resolved": "https://registry.npmjs.org/rolldown/-/rolldown-1.1.5.tgz", 7381 + "integrity": "sha512-t9z29cJjXf/vxQ8dyhCSpt6H6aSwHTk8cT5I3iy6SMXuFpk5mB6PL6XfC8PCwrPTx93udwKUm9HRteAlTGBLiA==", 7382 + "dev": true, 7383 + "license": "MIT", 7384 + "dependencies": { 7385 + "@oxc-project/types": "=0.139.0", 7386 + "@rolldown/pluginutils": "^1.0.0" 7387 + }, 7388 + "bin": { 7389 + "rolldown": "bin/cli.mjs" 7390 + }, 7391 + "engines": { 7392 + "node": "^20.19.0 || >=22.12.0" 7393 + }, 7394 + "optionalDependencies": { 7395 + "@rolldown/binding-android-arm64": "1.1.5", 7396 + "@rolldown/binding-darwin-arm64": "1.1.5", 7397 + "@rolldown/binding-darwin-x64": "1.1.5", 7398 + "@rolldown/binding-freebsd-x64": "1.1.5", 7399 + "@rolldown/binding-linux-arm-gnueabihf": "1.1.5", 7400 + "@rolldown/binding-linux-arm64-gnu": "1.1.5", 7401 + "@rolldown/binding-linux-arm64-musl": "1.1.5", 7402 + "@rolldown/binding-linux-ppc64-gnu": "1.1.5", 7403 + "@rolldown/binding-linux-s390x-gnu": "1.1.5", 7404 + "@rolldown/binding-linux-x64-gnu": "1.1.5", 7405 + "@rolldown/binding-linux-x64-musl": "1.1.5", 7406 + "@rolldown/binding-openharmony-arm64": "1.1.5", 7407 + "@rolldown/binding-wasm32-wasi": "1.1.5", 7408 + "@rolldown/binding-win32-arm64-msvc": "1.1.5", 7409 + "@rolldown/binding-win32-x64-msvc": "1.1.5" 7410 + } 7411 + }, 7412 + "node_modules/rollup": { 7413 + "version": "4.62.2", 7414 + "resolved": "https://registry.npmjs.org/rollup/-/rollup-4.62.2.tgz", 7415 + "integrity": "sha512-RFnrW4lhXA3s3eqHDZvN654g8OTjzRfqpIRJYczCGB6HzphckVAi/Qh4tbPUbRuDi7s1Llv8g/NspLkttY3gTA==", 7416 + "dev": true, 7417 + "license": "MIT", 7418 + "dependencies": { 7419 + "@types/estree": "1.0.9" 7420 + }, 7421 + "bin": { 7422 + "rollup": "dist/bin/rollup" 7423 + }, 7424 + "engines": { 7425 + "node": ">=18.0.0", 7426 + "npm": ">=8.0.0" 7427 + }, 7428 + "optionalDependencies": { 7429 + "@rollup/rollup-android-arm-eabi": "4.62.2", 7430 + "@rollup/rollup-android-arm64": "4.62.2", 7431 + "@rollup/rollup-darwin-arm64": "4.62.2", 7432 + "@rollup/rollup-darwin-x64": "4.62.2", 7433 + "@rollup/rollup-freebsd-arm64": "4.62.2", 7434 + "@rollup/rollup-freebsd-x64": "4.62.2", 7435 + "@rollup/rollup-linux-arm-gnueabihf": "4.62.2", 7436 + "@rollup/rollup-linux-arm-musleabihf": "4.62.2", 7437 + "@rollup/rollup-linux-arm64-gnu": "4.62.2", 7438 + "@rollup/rollup-linux-arm64-musl": "4.62.2", 7439 + "@rollup/rollup-linux-loong64-gnu": "4.62.2", 7440 + "@rollup/rollup-linux-loong64-musl": "4.62.2", 7441 + "@rollup/rollup-linux-ppc64-gnu": "4.62.2", 7442 + "@rollup/rollup-linux-ppc64-musl": "4.62.2", 7443 + "@rollup/rollup-linux-riscv64-gnu": "4.62.2", 7444 + "@rollup/rollup-linux-riscv64-musl": "4.62.2", 7445 + "@rollup/rollup-linux-s390x-gnu": "4.62.2", 7446 + "@rollup/rollup-linux-x64-gnu": "4.62.2", 7447 + "@rollup/rollup-linux-x64-musl": "4.62.2", 7448 + "@rollup/rollup-openbsd-x64": "4.62.2", 7449 + "@rollup/rollup-openharmony-arm64": "4.62.2", 7450 + "@rollup/rollup-win32-arm64-msvc": "4.62.2", 7451 + "@rollup/rollup-win32-ia32-msvc": "4.62.2", 7452 + "@rollup/rollup-win32-x64-gnu": "4.62.2", 7453 + "@rollup/rollup-win32-x64-msvc": "4.62.2", 7454 + "fsevents": "~2.3.2" 7455 + } 7456 + }, 7457 + "node_modules/safe-array-concat": { 7458 + "version": "1.1.4", 7459 + "resolved": "https://registry.npmjs.org/safe-array-concat/-/safe-array-concat-1.1.4.tgz", 7460 + "integrity": "sha512-wtZlHyOje6OZTGqAoaDKxFkgRtkF9CnHAVnCHKfuj200wAgL+bSJhdsCD2l0Qx/2ekEXjPWcyKkfGb5CPboslg==", 7461 + "dev": true, 7462 + "license": "MIT", 7463 + "dependencies": { 7464 + "call-bind": "^1.0.9", 7465 + "call-bound": "^1.0.4", 7466 + "get-intrinsic": "^1.3.0", 7467 + "has-symbols": "^1.1.0", 7468 + "isarray": "^2.0.5" 7469 + }, 7470 + "engines": { 7471 + "node": ">=0.4" 7472 + }, 7473 + "funding": { 7474 + "url": "https://github.com/sponsors/ljharb" 7475 + } 7476 + }, 7477 + "node_modules/safe-push-apply": { 7478 + "version": "1.0.0", 7479 + "resolved": "https://registry.npmjs.org/safe-push-apply/-/safe-push-apply-1.0.0.tgz", 7480 + "integrity": "sha512-iKE9w/Z7xCzUMIZqdBsp6pEQvwuEebH4vdpjcDWnyzaI6yl6O9FHvVpmGelvEHNsoY6wGblkxR6Zty/h00WiSA==", 7481 + "dev": true, 7482 + "license": "MIT", 7483 + "dependencies": { 7484 + "es-errors": "^1.3.0", 7485 + "isarray": "^2.0.5" 7486 + }, 7487 + "engines": { 7488 + "node": ">= 0.4" 7489 + }, 7490 + "funding": { 7491 + "url": "https://github.com/sponsors/ljharb" 7492 + } 7493 + }, 7494 + "node_modules/safe-regex-test": { 7495 + "version": "1.1.0", 7496 + "resolved": "https://registry.npmjs.org/safe-regex-test/-/safe-regex-test-1.1.0.tgz", 7497 + "integrity": "sha512-x/+Cz4YrimQxQccJf5mKEbIa1NzeCRNI5Ecl/ekmlYaampdNLPalVyIcCZNNH3MvmqBugV5TMYZXv0ljslUlaw==", 7498 + "dev": true, 7499 + "license": "MIT", 7500 + "dependencies": { 7501 + "call-bound": "^1.0.2", 7502 + "es-errors": "^1.3.0", 7503 + "is-regex": "^1.2.1" 7504 + }, 7505 + "engines": { 7506 + "node": ">= 0.4" 7507 + }, 7508 + "funding": { 7509 + "url": "https://github.com/sponsors/ljharb" 7510 + } 7511 + }, 7512 + "node_modules/scheduler": { 7513 + "version": "0.27.0", 7514 + "resolved": "https://registry.npmjs.org/scheduler/-/scheduler-0.27.0.tgz", 7515 + "integrity": "sha512-eNv+WrVbKu1f3vbYJT/xtiF5syA5HPIMtf9IgY/nKg0sWqzAUEvqY/xm7OcZc/qafLx/iO9FgOmeSAp4v5ti/Q==", 7516 + "license": "MIT" 7517 + }, 7518 + "node_modules/semver": { 7519 + "version": "7.8.5", 7520 + "resolved": "https://registry.npmjs.org/semver/-/semver-7.8.5.tgz", 7521 + "integrity": "sha512-Y7/KDsb8LjooZpwaqGyulO6DQlksgCncchHGk+sZIY4SBvUocMBEFH5Ur1fI4dV+Jvl0w6cjvucaIi40puRioA==", 7522 + "dev": true, 7523 + "license": "ISC", 7524 + "bin": { 7525 + "semver": "bin/semver.js" 7526 + }, 7527 + "engines": { 7528 + "node": ">=10" 7529 + } 7530 + }, 7531 + "node_modules/serialize-javascript": { 7532 + "version": "7.0.7", 7533 + "resolved": "https://registry.npmjs.org/serialize-javascript/-/serialize-javascript-7.0.7.tgz", 7534 + "integrity": "sha512-YAy8Od6KV+uuwUuU50np8fGB/Aues6Y0nAhA9y/hId74PlKUcme4pXcBD46NWKr1Q4osN/iseZ17YqO1XfmI8g==", 7535 + "dev": true, 7536 + "license": "BSD-3-Clause", 7537 + "engines": { 7538 + "node": ">=20.0.0" 7539 + } 7540 + }, 7541 + "node_modules/set-cookie-parser": { 7542 + "version": "2.7.2", 7543 + "resolved": "https://registry.npmjs.org/set-cookie-parser/-/set-cookie-parser-2.7.2.tgz", 7544 + "integrity": "sha512-oeM1lpU/UvhTxw+g3cIfxXHyJRc/uidd3yK1P242gzHds0udQBYzs3y8j4gCCW+ZJ7ad0yctld8RYO+bdurlvw==", 7545 + "license": "MIT" 7546 + }, 7547 + "node_modules/set-function-length": { 7548 + "version": "1.2.2", 7549 + "resolved": "https://registry.npmjs.org/set-function-length/-/set-function-length-1.2.2.tgz", 7550 + "integrity": "sha512-pgRc4hJ4/sNjWCSS9AmnS40x3bNMDTknHgL5UaMBTMyJnU90EgWh1Rz+MC9eFu4BuN/UwZjKQuY/1v3rM7HMfg==", 7551 + "dev": true, 7552 + "license": "MIT", 7553 + "dependencies": { 7554 + "define-data-property": "^1.1.4", 7555 + "es-errors": "^1.3.0", 7556 + "function-bind": "^1.1.2", 7557 + "get-intrinsic": "^1.2.4", 7558 + "gopd": "^1.0.1", 7559 + "has-property-descriptors": "^1.0.2" 7560 + }, 7561 + "engines": { 7562 + "node": ">= 0.4" 7563 + } 7564 + }, 7565 + "node_modules/set-function-name": { 7566 + "version": "2.0.2", 7567 + "resolved": "https://registry.npmjs.org/set-function-name/-/set-function-name-2.0.2.tgz", 7568 + "integrity": "sha512-7PGFlmtwsEADb0WYyvCMa1t+yke6daIG4Wirafur5kcf+MhUnPms1UeR0CKQdTZD81yESwMHbtn+TR+dMviakQ==", 7569 + "dev": true, 7570 + "license": "MIT", 7571 + "dependencies": { 7572 + "define-data-property": "^1.1.4", 7573 + "es-errors": "^1.3.0", 7574 + "functions-have-names": "^1.2.3", 7575 + "has-property-descriptors": "^1.0.2" 7576 + }, 7577 + "engines": { 7578 + "node": ">= 0.4" 7579 + } 7580 + }, 7581 + "node_modules/set-proto": { 7582 + "version": "1.0.0", 7583 + "resolved": "https://registry.npmjs.org/set-proto/-/set-proto-1.0.0.tgz", 7584 + "integrity": "sha512-RJRdvCo6IAnPdsvP/7m6bsQqNnn1FCBX5ZNtFL98MmFF/4xAIJTIg1YbHW5DC2W5SKZanrC6i4HsJqlajw/dZw==", 7585 + "dev": true, 7586 + "license": "MIT", 7587 + "dependencies": { 7588 + "dunder-proto": "^1.0.1", 7589 + "es-errors": "^1.3.0", 7590 + "es-object-atoms": "^1.0.0" 7591 + }, 7592 + "engines": { 7593 + "node": ">= 0.4" 7594 + } 7595 + }, 7596 + "node_modules/sharp": { 7597 + "version": "0.34.5", 7598 + "resolved": "https://registry.npmjs.org/sharp/-/sharp-0.34.5.tgz", 7599 + "integrity": "sha512-Ou9I5Ft9WNcCbXrU9cMgPBcCK8LiwLqcbywW3t4oDV37n1pzpuNLsYiAV8eODnjbtQlSDwZ2cUEeQz4E54Hltg==", 7600 + "dev": true, 7601 + "hasInstallScript": true, 7602 + "license": "Apache-2.0", 7603 + "dependencies": { 7604 + "@img/colour": "^1.0.0", 7605 + "detect-libc": "^2.1.2", 7606 + "semver": "^7.7.3" 7607 + }, 7608 + "engines": { 7609 + "node": "^18.17.0 || ^20.3.0 || >=21.0.0" 7610 + }, 7611 + "funding": { 7612 + "url": "https://opencollective.com/libvips" 7613 + }, 7614 + "optionalDependencies": { 7615 + "@img/sharp-darwin-arm64": "0.34.5", 7616 + "@img/sharp-darwin-x64": "0.34.5", 7617 + "@img/sharp-libvips-darwin-arm64": "1.2.4", 7618 + "@img/sharp-libvips-darwin-x64": "1.2.4", 7619 + "@img/sharp-libvips-linux-arm": "1.2.4", 7620 + "@img/sharp-libvips-linux-arm64": "1.2.4", 7621 + "@img/sharp-libvips-linux-ppc64": "1.2.4", 7622 + "@img/sharp-libvips-linux-riscv64": "1.2.4", 7623 + "@img/sharp-libvips-linux-s390x": "1.2.4", 7624 + "@img/sharp-libvips-linux-x64": "1.2.4", 7625 + "@img/sharp-libvips-linuxmusl-arm64": "1.2.4", 7626 + "@img/sharp-libvips-linuxmusl-x64": "1.2.4", 7627 + "@img/sharp-linux-arm": "0.34.5", 7628 + "@img/sharp-linux-arm64": "0.34.5", 7629 + "@img/sharp-linux-ppc64": "0.34.5", 7630 + "@img/sharp-linux-riscv64": "0.34.5", 7631 + "@img/sharp-linux-s390x": "0.34.5", 7632 + "@img/sharp-linux-x64": "0.34.5", 7633 + "@img/sharp-linuxmusl-arm64": "0.34.5", 7634 + "@img/sharp-linuxmusl-x64": "0.34.5", 7635 + "@img/sharp-wasm32": "0.34.5", 7636 + "@img/sharp-win32-arm64": "0.34.5", 7637 + "@img/sharp-win32-ia32": "0.34.5", 7638 + "@img/sharp-win32-x64": "0.34.5" 7639 + } 7640 + }, 7641 + "node_modules/shebang-command": { 7642 + "version": "2.0.0", 7643 + "resolved": "https://registry.npmjs.org/shebang-command/-/shebang-command-2.0.0.tgz", 7644 + "integrity": "sha512-kHxr2zZpYtdmrN1qDjrrX/Z1rR1kG8Dx+gkpK1G4eXmvXswmcE1hTWBWYUzlraYw1/yZp6YuDY77YtvbN0dmDA==", 7645 + "dev": true, 7646 + "license": "MIT", 7647 + "dependencies": { 7648 + "shebang-regex": "^3.0.0" 7649 + }, 7650 + "engines": { 7651 + "node": ">=8" 7652 + } 7653 + }, 7654 + "node_modules/shebang-regex": { 7655 + "version": "3.0.0", 7656 + "resolved": "https://registry.npmjs.org/shebang-regex/-/shebang-regex-3.0.0.tgz", 7657 + "integrity": "sha512-7++dFhtcx3353uBaq8DDR4NuxBetBzC7ZQOhmTQInHEd6bSrXdiEyzCvG07Z44UYdLShWUyXt5M/yhz8ekcb1A==", 7658 + "dev": true, 7659 + "license": "MIT", 7660 + "engines": { 7661 + "node": ">=8" 7662 + } 7663 + }, 7664 + "node_modules/side-channel": { 7665 + "version": "1.1.1", 7666 + "resolved": "https://registry.npmjs.org/side-channel/-/side-channel-1.1.1.tgz", 7667 + "integrity": "sha512-6x6dK6zJdpTzF4sQeNYxwtvBzf6Eg4GtlesS94HOvTudUeyK2WXAaIfmDgsyslYrRBeFIlsi54AYsFGUuhmvrQ==", 7668 + "dev": true, 7669 + "license": "MIT", 7670 + "dependencies": { 7671 + "es-errors": "^1.3.0", 7672 + "object-inspect": "^1.13.4", 7673 + "side-channel-list": "^1.0.1", 7674 + "side-channel-map": "^1.0.1", 7675 + "side-channel-weakmap": "^1.0.2" 7676 + }, 7677 + "engines": { 7678 + "node": ">= 0.4" 7679 + }, 7680 + "funding": { 7681 + "url": "https://github.com/sponsors/ljharb" 7682 + } 7683 + }, 7684 + "node_modules/side-channel-list": { 7685 + "version": "1.0.1", 7686 + "resolved": "https://registry.npmjs.org/side-channel-list/-/side-channel-list-1.0.1.tgz", 7687 + "integrity": "sha512-mjn/0bi/oUURjc5Xl7IaWi/OJJJumuoJFQJfDDyO46+hBWsfaVM65TBHq2eoZBhzl9EchxOijpkbRC8SVBQU0w==", 7688 + "dev": true, 7689 + "license": "MIT", 7690 + "dependencies": { 7691 + "es-errors": "^1.3.0", 7692 + "object-inspect": "^1.13.4" 7693 + }, 7694 + "engines": { 7695 + "node": ">= 0.4" 7696 + }, 7697 + "funding": { 7698 + "url": "https://github.com/sponsors/ljharb" 7699 + } 7700 + }, 7701 + "node_modules/side-channel-map": { 7702 + "version": "1.0.1", 7703 + "resolved": "https://registry.npmjs.org/side-channel-map/-/side-channel-map-1.0.1.tgz", 7704 + "integrity": "sha512-VCjCNfgMsby3tTdo02nbjtM/ewra6jPHmpThenkTYh8pG9ucZ/1P8So4u4FGBek/BjpOVsDCMoLA/iuBKIFXRA==", 7705 + "dev": true, 7706 + "license": "MIT", 7707 + "dependencies": { 7708 + "call-bound": "^1.0.2", 7709 + "es-errors": "^1.3.0", 7710 + "get-intrinsic": "^1.2.5", 7711 + "object-inspect": "^1.13.3" 7712 + }, 7713 + "engines": { 7714 + "node": ">= 0.4" 7715 + }, 7716 + "funding": { 7717 + "url": "https://github.com/sponsors/ljharb" 7718 + } 7719 + }, 7720 + "node_modules/side-channel-weakmap": { 7721 + "version": "1.0.2", 7722 + "resolved": "https://registry.npmjs.org/side-channel-weakmap/-/side-channel-weakmap-1.0.2.tgz", 7723 + "integrity": "sha512-WPS/HvHQTYnHisLo9McqBHOJk2FkHO/tlpvldyrnem4aeQp4hai3gythswg6p01oSoTl58rcpiFAjF2br2Ak2A==", 7724 + "dev": true, 7725 + "license": "MIT", 7726 + "dependencies": { 7727 + "call-bound": "^1.0.2", 7728 + "es-errors": "^1.3.0", 7729 + "get-intrinsic": "^1.2.5", 7730 + "object-inspect": "^1.13.3", 7731 + "side-channel-map": "^1.0.1" 7732 + }, 7733 + "engines": { 7734 + "node": ">= 0.4" 7735 + }, 7736 + "funding": { 7737 + "url": "https://github.com/sponsors/ljharb" 7738 + } 7739 + }, 7740 + "node_modules/signal-exit": { 7741 + "version": "4.1.0", 7742 + "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-4.1.0.tgz", 7743 + "integrity": "sha512-bzyZ1e88w9O1iNJbKnOlvYTrWPDl46O1bG0D3XInv+9tkPrxrN8jUUTiFlDkkmKWgn1M6CfIA13SuGqOa9Korw==", 7744 + "dev": true, 7745 + "license": "ISC", 7746 + "engines": { 7747 + "node": ">=14" 7748 + }, 7749 + "funding": { 7750 + "url": "https://github.com/sponsors/isaacs" 7751 + } 7752 + }, 7753 + "node_modules/smob": { 7754 + "version": "1.6.2", 7755 + "resolved": "https://registry.npmjs.org/smob/-/smob-1.6.2.tgz", 7756 + "integrity": "sha512-RQsvleCbF8cVHEv+xuDGaA4pOizFqJ0GgjtMSRo6oP8pnN7WsigHgVGey6aILRBKv4W2YOMHLqbKdnB6hpB9fw==", 7757 + "dev": true, 7758 + "license": "MIT", 7759 + "engines": { 7760 + "node": ">=20.0.0" 7761 + } 7762 + }, 7763 + "node_modules/source-map": { 7764 + "version": "0.8.0-beta.0", 7765 + "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.8.0-beta.0.tgz", 7766 + "integrity": "sha512-2ymg6oRBpebeZi9UUNsgQ89bhx01TcTkmNTGnNO88imTmbSgy4nfujrgVEFKWpMTEGA11EDkTt7mqObTPdigIA==", 7767 + "deprecated": "The work that was done in this beta branch won't be included in future versions", 7768 + "dev": true, 7769 + "license": "BSD-3-Clause", 7770 + "dependencies": { 7771 + "whatwg-url": "^7.0.0" 7772 + }, 7773 + "engines": { 7774 + "node": ">= 8" 7775 + } 7776 + }, 7777 + "node_modules/source-map-js": { 7778 + "version": "1.2.1", 7779 + "resolved": "https://registry.npmjs.org/source-map-js/-/source-map-js-1.2.1.tgz", 7780 + "integrity": "sha512-UXWMKhLOwVKb728IUtQPXxfYU+usdybtUrK/8uGE8CQMvrhOpwvzDBwj0QhSL7MQc7vIsISBG8VQ8+IDQxpfQA==", 7781 + "dev": true, 7782 + "license": "BSD-3-Clause", 7783 + "engines": { 7784 + "node": ">=0.10.0" 7785 + } 7786 + }, 7787 + "node_modules/source-map-support": { 7788 + "version": "0.5.21", 7789 + "resolved": "https://registry.npmjs.org/source-map-support/-/source-map-support-0.5.21.tgz", 7790 + "integrity": "sha512-uBHU3L3czsIyYXKX88fdrGovxdSCoTGDRZ6SYXtSRxLZUzHg5P/66Ht6uoUlHu9EZod+inXhKo3qQgwXUT/y1w==", 7791 + "dev": true, 7792 + "license": "MIT", 7793 + "dependencies": { 7794 + "buffer-from": "^1.0.0", 7795 + "source-map": "^0.6.0" 7796 + } 7797 + }, 7798 + "node_modules/source-map-support/node_modules/source-map": { 7799 + "version": "0.6.1", 7800 + "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", 7801 + "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==", 7802 + "dev": true, 7803 + "license": "BSD-3-Clause", 7804 + "engines": { 7805 + "node": ">=0.10.0" 7806 + } 7807 + }, 7808 + "node_modules/stop-iteration-iterator": { 7809 + "version": "1.1.0", 7810 + "resolved": "https://registry.npmjs.org/stop-iteration-iterator/-/stop-iteration-iterator-1.1.0.tgz", 7811 + "integrity": "sha512-eLoXW/DHyl62zxY4SCaIgnRhuMr6ri4juEYARS8E6sCEqzKpOiE521Ucofdx+KnDZl5xmvGYaaKCk5FEOxJCoQ==", 7812 + "dev": true, 7813 + "license": "MIT", 7814 + "dependencies": { 7815 + "es-errors": "^1.3.0", 7816 + "internal-slot": "^1.1.0" 7817 + }, 7818 + "engines": { 7819 + "node": ">= 0.4" 7820 + } 7821 + }, 7822 + "node_modules/string.prototype.matchall": { 7823 + "version": "4.0.12", 7824 + "resolved": "https://registry.npmjs.org/string.prototype.matchall/-/string.prototype.matchall-4.0.12.tgz", 7825 + "integrity": "sha512-6CC9uyBL+/48dYizRf7H7VAYCMCNTBeM78x/VTUe9bFEaxBepPJDa1Ow99LqI/1yF7kuy7Q3cQsYMrcjGUcskA==", 7826 + "dev": true, 7827 + "license": "MIT", 7828 + "dependencies": { 7829 + "call-bind": "^1.0.8", 7830 + "call-bound": "^1.0.3", 7831 + "define-properties": "^1.2.1", 7832 + "es-abstract": "^1.23.6", 7833 + "es-errors": "^1.3.0", 7834 + "es-object-atoms": "^1.0.0", 7835 + "get-intrinsic": "^1.2.6", 7836 + "gopd": "^1.2.0", 7837 + "has-symbols": "^1.1.0", 7838 + "internal-slot": "^1.1.0", 7839 + "regexp.prototype.flags": "^1.5.3", 7840 + "set-function-name": "^2.0.2", 7841 + "side-channel": "^1.1.0" 7842 + }, 7843 + "engines": { 7844 + "node": ">= 0.4" 7845 + }, 7846 + "funding": { 7847 + "url": "https://github.com/sponsors/ljharb" 7848 + } 7849 + }, 7850 + "node_modules/string.prototype.trim": { 7851 + "version": "1.2.11", 7852 + "resolved": "https://registry.npmjs.org/string.prototype.trim/-/string.prototype.trim-1.2.11.tgz", 7853 + "integrity": "sha512-PwvK7BU+CMTJGYQCTZb5RWXIML92lftJLhQz1tBzgKiqGxJaMlBAa48POXaNAC2s4y8jr3EFqrkF9+44neS46w==", 7854 + "dev": true, 7855 + "license": "MIT", 7856 + "dependencies": { 7857 + "call-bind": "^1.0.9", 7858 + "call-bound": "^1.0.4", 7859 + "define-data-property": "^1.1.4", 7860 + "define-properties": "^1.2.1", 7861 + "es-abstract": "^1.24.2", 7862 + "es-object-atoms": "^1.1.2", 7863 + "has-property-descriptors": "^1.0.2", 7864 + "safe-regex-test": "^1.1.0" 7865 + }, 7866 + "engines": { 7867 + "node": ">= 0.4" 7868 + }, 7869 + "funding": { 7870 + "url": "https://github.com/sponsors/ljharb" 7871 + } 7872 + }, 7873 + "node_modules/string.prototype.trimend": { 7874 + "version": "1.0.10", 7875 + "resolved": "https://registry.npmjs.org/string.prototype.trimend/-/string.prototype.trimend-1.0.10.tgz", 7876 + "integrity": "sha512-2+3aDAOmPTmuFwjDnmJG2ctEkQKVki7vOSqaxkv42Mowj1V6PnvuwFCRrR5lChUux1TBskPjfkeTOhqczDMxTw==", 7877 + "dev": true, 7878 + "license": "MIT", 7879 + "dependencies": { 7880 + "call-bind": "^1.0.9", 7881 + "call-bound": "^1.0.4", 7882 + "define-properties": "^1.2.1", 7883 + "es-object-atoms": "^1.1.2" 7884 + }, 7885 + "engines": { 7886 + "node": ">= 0.4" 7887 + }, 7888 + "funding": { 7889 + "url": "https://github.com/sponsors/ljharb" 7890 + } 7891 + }, 7892 + "node_modules/string.prototype.trimstart": { 7893 + "version": "1.0.8", 7894 + "resolved": "https://registry.npmjs.org/string.prototype.trimstart/-/string.prototype.trimstart-1.0.8.tgz", 7895 + "integrity": "sha512-UXSH262CSZY1tfu3G3Secr6uGLCFVPMhIqHjlgCUtCCcgihYc/xKs9djMTMUOb2j1mVSeU8EU6NWc/iQKU6Gfg==", 7896 + "dev": true, 7897 + "license": "MIT", 7898 + "dependencies": { 7899 + "call-bind": "^1.0.7", 7900 + "define-properties": "^1.2.1", 7901 + "es-object-atoms": "^1.0.0" 7902 + }, 7903 + "engines": { 7904 + "node": ">= 0.4" 7905 + }, 7906 + "funding": { 7907 + "url": "https://github.com/sponsors/ljharb" 7908 + } 7909 + }, 7910 + "node_modules/stringify-object": { 7911 + "version": "3.3.0", 7912 + "resolved": "https://registry.npmjs.org/stringify-object/-/stringify-object-3.3.0.tgz", 7913 + "integrity": "sha512-rHqiFh1elqCQ9WPLIC8I0Q/g/wj5J1eMkyoiD6eoQApWHP0FtlK7rqnhmabL5VUY9JQCcqwwvlOaSuutekgyrw==", 7914 + "dev": true, 7915 + "license": "BSD-2-Clause", 7916 + "dependencies": { 7917 + "get-own-enumerable-property-symbols": "^3.0.0", 7918 + "is-obj": "^1.0.1", 7919 + "is-regexp": "^1.0.0" 7920 + }, 7921 + "engines": { 7922 + "node": ">=4" 7923 + } 7924 + }, 7925 + "node_modules/strip-comments": { 7926 + "version": "2.0.1", 7927 + "resolved": "https://registry.npmjs.org/strip-comments/-/strip-comments-2.0.1.tgz", 7928 + "integrity": "sha512-ZprKx+bBLXv067WTCALv8SSz5l2+XhpYCsVtSqlMnkAXMWDq+/ekVbl1ghqP9rUHTzv6sm/DwCOiYutU/yp1fw==", 7929 + "dev": true, 7930 + "license": "MIT", 7931 + "engines": { 7932 + "node": ">=10" 7933 + } 7934 + }, 7935 + "node_modules/supports-color": { 7936 + "version": "10.2.2", 7937 + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-10.2.2.tgz", 7938 + "integrity": "sha512-SS+jx45GF1QjgEXQx4NJZV9ImqmO2NPz5FNsIHrsDjh2YsHnawpan7SNQ1o8NuhrbHZy9AZhIoCUiCeaW/C80g==", 7939 + "dev": true, 7940 + "license": "MIT", 7941 + "engines": { 7942 + "node": ">=18" 7943 + }, 7944 + "funding": { 7945 + "url": "https://github.com/chalk/supports-color?sponsor=1" 7946 + } 7947 + }, 7948 + "node_modules/supports-preserve-symlinks-flag": { 7949 + "version": "1.0.0", 7950 + "resolved": "https://registry.npmjs.org/supports-preserve-symlinks-flag/-/supports-preserve-symlinks-flag-1.0.0.tgz", 7951 + "integrity": "sha512-ot0WnXS9fgdkgIcePe6RHNk1WA8+muPa6cSjeR3V8K27q9BB1rTE3R1p7Hv0z1ZyAc8s6Vvv8DIyWf681MAt0w==", 7952 + "dev": true, 7953 + "license": "MIT", 7954 + "engines": { 7955 + "node": ">= 0.4" 7956 + }, 7957 + "funding": { 7958 + "url": "https://github.com/sponsors/ljharb" 7959 + } 7960 + }, 7961 + "node_modules/tailwindcss": { 7962 + "version": "4.3.3", 7963 + "resolved": "https://registry.npmjs.org/tailwindcss/-/tailwindcss-4.3.3.tgz", 7964 + "integrity": "sha512-gOhV3P7ufE62QDGg1zVaTgCR+EtPv92k2nIhVcVKcLmxT1sUBsQGhnZj175j+MqRt4zLF7ic+sCYjfhxMxj7YQ==", 7965 + "dev": true, 7966 + "license": "MIT" 7967 + }, 7968 + "node_modules/tapable": { 7969 + "version": "2.3.3", 7970 + "resolved": "https://registry.npmjs.org/tapable/-/tapable-2.3.3.tgz", 7971 + "integrity": "sha512-uxc/zpqFg6x7C8vOE7lh6Lbda8eEL9zmVm/PLeTPBRhh1xCgdWaQ+J1CUieGpIfm2HdtsUpRv+HshiasBMcc6A==", 7972 + "dev": true, 7973 + "license": "MIT", 7974 + "engines": { 7975 + "node": ">=6" 7976 + }, 7977 + "funding": { 7978 + "type": "opencollective", 7979 + "url": "https://opencollective.com/webpack" 7980 + } 7981 + }, 7982 + "node_modules/temp-dir": { 7983 + "version": "2.0.0", 7984 + "resolved": "https://registry.npmjs.org/temp-dir/-/temp-dir-2.0.0.tgz", 7985 + "integrity": "sha512-aoBAniQmmwtcKp/7BzsH8Cxzv8OL736p7v1ihGb5e9DJ9kTwGWHrQrVB5+lfVDzfGrdRzXch+ig7LHaY1JTOrg==", 7986 + "dev": true, 7987 + "license": "MIT", 7988 + "engines": { 7989 + "node": ">=8" 7990 + } 7991 + }, 7992 + "node_modules/tempy": { 7993 + "version": "0.6.0", 7994 + "resolved": "https://registry.npmjs.org/tempy/-/tempy-0.6.0.tgz", 7995 + "integrity": "sha512-G13vtMYPT/J8A4X2SjdtBTphZlrp1gKv6hZiOjw14RCWg6GbHuQBGtjlx75xLbYV/wEc0D7G5K4rxKP/cXk8Bw==", 7996 + "dev": true, 7997 + "license": "MIT", 7998 + "dependencies": { 7999 + "is-stream": "^2.0.0", 8000 + "temp-dir": "^2.0.0", 8001 + "type-fest": "^0.16.0", 8002 + "unique-string": "^2.0.0" 8003 + }, 8004 + "engines": { 8005 + "node": ">=10" 8006 + }, 8007 + "funding": { 8008 + "url": "https://github.com/sponsors/sindresorhus" 8009 + } 8010 + }, 8011 + "node_modules/terser": { 8012 + "version": "5.49.0", 8013 + "resolved": "https://registry.npmjs.org/terser/-/terser-5.49.0.tgz", 8014 + "integrity": "sha512-SNiDnXyHSrxVcIOtVbULzcTmniUiwcV7Nwdyj1twVubeTmbjoa8p69KKDpfkdoOavuM4/GRm1+ykI8qqnavHoA==", 8015 + "dev": true, 8016 + "license": "BSD-2-Clause", 8017 + "dependencies": { 8018 + "@jridgewell/source-map": "^0.3.3", 8019 + "acorn": "^8.15.0", 8020 + "commander": "^2.20.0", 8021 + "source-map-support": "~0.5.20" 8022 + }, 8023 + "bin": { 8024 + "terser": "bin/terser" 8025 + }, 8026 + "engines": { 8027 + "node": ">=10" 8028 + } 8029 + }, 8030 + "node_modules/tinyglobby": { 8031 + "version": "0.2.17", 8032 + "resolved": "https://registry.npmjs.org/tinyglobby/-/tinyglobby-0.2.17.tgz", 8033 + "integrity": "sha512-wXR/dYpcqKmfWpEdZjiKJOwCNFndD0DMnrW/cYjVGttEkBfVgcLFHoNrlj47mjOVic9yyNu65alsgF4NQyTa2g==", 8034 + "dev": true, 8035 + "license": "MIT", 8036 + "dependencies": { 8037 + "fdir": "^6.5.0", 8038 + "picomatch": "^4.0.4" 8039 + }, 8040 + "engines": { 8041 + "node": ">=12.0.0" 8042 + }, 8043 + "funding": { 8044 + "url": "https://github.com/sponsors/SuperchupuDev" 8045 + } 8046 + }, 8047 + "node_modules/tr46": { 8048 + "version": "1.0.1", 8049 + "resolved": "https://registry.npmjs.org/tr46/-/tr46-1.0.1.tgz", 8050 + "integrity": "sha512-dTpowEjclQ7Kgx5SdBkqRzVhERQXov8/l9Ft9dVM9fmg0W0KQSVaXX9T4i6twCPNtYiZM53lpSSUAwJbFPOHxA==", 8051 + "dev": true, 8052 + "license": "MIT", 8053 + "dependencies": { 8054 + "punycode": "^2.1.0" 8055 + } 8056 + }, 8057 + "node_modules/tslib": { 8058 + "version": "2.8.1", 8059 + "resolved": "https://registry.npmjs.org/tslib/-/tslib-2.8.1.tgz", 8060 + "integrity": "sha512-oJFu94HQb+KVduSUQL7wnpmqnfmLsOA/nAh6b6EH0wCEoK0/mPeXU6c3wKDV83MkOuHPRHtSXKKU99IBazS/2w==", 8061 + "license": "0BSD" 8062 + }, 8063 + "node_modules/tsyringe": { 8064 + "version": "4.10.0", 8065 + "resolved": "https://registry.npmjs.org/tsyringe/-/tsyringe-4.10.0.tgz", 8066 + "integrity": "sha512-axr3IdNuVIxnaK5XGEUFTu3YmAQ6lllgrvqfEoR16g/HGnYY/6We4oWENtAnzK6/LpJ2ur9PAb80RBt7/U4ugw==", 8067 + "license": "MIT", 8068 + "dependencies": { 8069 + "tslib": "^1.9.3" 8070 + }, 8071 + "engines": { 8072 + "node": ">= 6.0.0" 8073 + } 8074 + }, 8075 + "node_modules/tsyringe/node_modules/tslib": { 8076 + "version": "1.14.1", 8077 + "resolved": "https://registry.npmjs.org/tslib/-/tslib-1.14.1.tgz", 8078 + "integrity": "sha512-Xni35NKzjgMrwevysHTCArtLDpPvye8zV/0E4EyYn43P7/7qvQwPh9BGkHewbMulVntbigmcT7rdX3BNo9wRJg==", 8079 + "license": "0BSD" 8080 + }, 8081 + "node_modules/type-fest": { 8082 + "version": "0.16.0", 8083 + "resolved": "https://registry.npmjs.org/type-fest/-/type-fest-0.16.0.tgz", 8084 + "integrity": "sha512-eaBzG6MxNzEn9kiwvtre90cXaNLkmadMWa1zQMs3XORCXNbsH/OewwbxC5ia9dCxIxnTAsSxXJaa/p5y8DlvJg==", 8085 + "dev": true, 8086 + "license": "(MIT OR CC0-1.0)", 8087 + "engines": { 8088 + "node": ">=10" 8089 + }, 8090 + "funding": { 8091 + "url": "https://github.com/sponsors/sindresorhus" 8092 + } 8093 + }, 8094 + "node_modules/typed-array-buffer": { 8095 + "version": "1.0.3", 8096 + "resolved": "https://registry.npmjs.org/typed-array-buffer/-/typed-array-buffer-1.0.3.tgz", 8097 + "integrity": "sha512-nAYYwfY3qnzX30IkA6AQZjVbtK6duGontcQm1WSG1MD94YLqK0515GNApXkoxKOWMusVssAHWLh9SeaoefYFGw==", 8098 + "dev": true, 8099 + "license": "MIT", 8100 + "dependencies": { 8101 + "call-bound": "^1.0.3", 8102 + "es-errors": "^1.3.0", 8103 + "is-typed-array": "^1.1.14" 8104 + }, 8105 + "engines": { 8106 + "node": ">= 0.4" 8107 + } 8108 + }, 8109 + "node_modules/typed-array-byte-length": { 8110 + "version": "1.0.3", 8111 + "resolved": "https://registry.npmjs.org/typed-array-byte-length/-/typed-array-byte-length-1.0.3.tgz", 8112 + "integrity": "sha512-BaXgOuIxz8n8pIq3e7Atg/7s+DpiYrxn4vdot3w9KbnBhcRQq6o3xemQdIfynqSeXeDrF32x+WvfzmOjPiY9lg==", 8113 + "dev": true, 8114 + "license": "MIT", 8115 + "dependencies": { 8116 + "call-bind": "^1.0.8", 8117 + "for-each": "^0.3.3", 8118 + "gopd": "^1.2.0", 8119 + "has-proto": "^1.2.0", 8120 + "is-typed-array": "^1.1.14" 8121 + }, 8122 + "engines": { 8123 + "node": ">= 0.4" 8124 + }, 8125 + "funding": { 8126 + "url": "https://github.com/sponsors/ljharb" 8127 + } 8128 + }, 8129 + "node_modules/typed-array-byte-offset": { 8130 + "version": "1.0.4", 8131 + "resolved": "https://registry.npmjs.org/typed-array-byte-offset/-/typed-array-byte-offset-1.0.4.tgz", 8132 + "integrity": "sha512-bTlAFB/FBYMcuX81gbL4OcpH5PmlFHqlCCpAl8AlEzMz5k53oNDvN8p1PNOWLEmI2x4orp3raOFB51tv9X+MFQ==", 8133 + "dev": true, 8134 + "license": "MIT", 8135 + "dependencies": { 8136 + "available-typed-arrays": "^1.0.7", 8137 + "call-bind": "^1.0.8", 8138 + "for-each": "^0.3.3", 8139 + "gopd": "^1.2.0", 8140 + "has-proto": "^1.2.0", 8141 + "is-typed-array": "^1.1.15", 8142 + "reflect.getprototypeof": "^1.0.9" 8143 + }, 8144 + "engines": { 8145 + "node": ">= 0.4" 8146 + }, 8147 + "funding": { 8148 + "url": "https://github.com/sponsors/ljharb" 8149 + } 8150 + }, 8151 + "node_modules/typed-array-length": { 8152 + "version": "1.0.8", 8153 + "resolved": "https://registry.npmjs.org/typed-array-length/-/typed-array-length-1.0.8.tgz", 8154 + "integrity": "sha512-phPGCwqr2+Qo0fwniCE8e4pKnGu/yFb5nD5Y8bf0EEeiI5GklnACYA9GFy/DrAeRrKHXvHn+1SUsOWgJp6RO+g==", 8155 + "dev": true, 8156 + "license": "MIT", 8157 + "dependencies": { 8158 + "call-bind": "^1.0.9", 8159 + "for-each": "^0.3.5", 8160 + "gopd": "^1.2.0", 8161 + "is-typed-array": "^1.1.15", 8162 + "possible-typed-array-names": "^1.1.0", 8163 + "reflect.getprototypeof": "^1.0.10" 8164 + }, 8165 + "engines": { 8166 + "node": ">= 0.4" 8167 + }, 8168 + "funding": { 8169 + "url": "https://github.com/sponsors/ljharb" 8170 + } 8171 + }, 8172 + "node_modules/typescript": { 8173 + "version": "7.0.2", 8174 + "resolved": "https://registry.npmjs.org/typescript/-/typescript-7.0.2.tgz", 8175 + "integrity": "sha512-8FYau96o3NKOhbjKi/qNvG/W5jhzxkbdm5sj9AbZ/5T5sWqn3hJgLfGx27sRKZWTvyzCP8dLRBTf5tBTSRVUNA==", 8176 + "dev": true, 8177 + "license": "Apache-2.0", 8178 + "bin": { 8179 + "tsc": "bin/tsc" 8180 + }, 8181 + "engines": { 8182 + "node": ">=16.20.0" 8183 + }, 8184 + "optionalDependencies": { 8185 + "@typescript/typescript-aix-ppc64": "7.0.2", 8186 + "@typescript/typescript-darwin-arm64": "7.0.2", 8187 + "@typescript/typescript-darwin-x64": "7.0.2", 8188 + "@typescript/typescript-freebsd-arm64": "7.0.2", 8189 + "@typescript/typescript-freebsd-x64": "7.0.2", 8190 + "@typescript/typescript-linux-arm": "7.0.2", 8191 + "@typescript/typescript-linux-arm64": "7.0.2", 8192 + "@typescript/typescript-linux-loong64": "7.0.2", 8193 + "@typescript/typescript-linux-mips64el": "7.0.2", 8194 + "@typescript/typescript-linux-ppc64": "7.0.2", 8195 + "@typescript/typescript-linux-riscv64": "7.0.2", 8196 + "@typescript/typescript-linux-s390x": "7.0.2", 8197 + "@typescript/typescript-linux-x64": "7.0.2", 8198 + "@typescript/typescript-netbsd-arm64": "7.0.2", 8199 + "@typescript/typescript-netbsd-x64": "7.0.2", 8200 + "@typescript/typescript-openbsd-arm64": "7.0.2", 8201 + "@typescript/typescript-openbsd-x64": "7.0.2", 8202 + "@typescript/typescript-sunos-x64": "7.0.2", 8203 + "@typescript/typescript-win32-arm64": "7.0.2", 8204 + "@typescript/typescript-win32-x64": "7.0.2" 8205 + } 8206 + }, 8207 + "node_modules/unbox-primitive": { 8208 + "version": "1.1.0", 8209 + "resolved": "https://registry.npmjs.org/unbox-primitive/-/unbox-primitive-1.1.0.tgz", 8210 + "integrity": "sha512-nWJ91DjeOkej/TA8pXQ3myruKpKEYgqvpw9lz4OPHj/NWFNluYrjbz9j01CJ8yKQd2g4jFoOkINCTW2I5LEEyw==", 8211 + "dev": true, 8212 + "license": "MIT", 8213 + "dependencies": { 8214 + "call-bound": "^1.0.3", 8215 + "has-bigints": "^1.0.2", 8216 + "has-symbols": "^1.1.0", 8217 + "which-boxed-primitive": "^1.1.1" 8218 + }, 8219 + "engines": { 8220 + "node": ">= 0.4" 8221 + }, 8222 + "funding": { 8223 + "url": "https://github.com/sponsors/ljharb" 8224 + } 8225 + }, 8226 + "node_modules/undici": { 8227 + "version": "7.28.0", 8228 + "resolved": "https://registry.npmjs.org/undici/-/undici-7.28.0.tgz", 8229 + "integrity": "sha512-cRZYrTDwWznlnRiPjggAGxZXanty6M8RV1ff8Wm4LWXBp7/IG8v5DnOm74DtUBp9OONpK75YlPnIjQqX0dBDtA==", 8230 + "dev": true, 8231 + "license": "MIT", 8232 + "engines": { 8233 + "node": ">=20.18.1" 8234 + } 8235 + }, 8236 + "node_modules/unenv": { 8237 + "version": "2.0.0-rc.24", 8238 + "resolved": "https://registry.npmjs.org/unenv/-/unenv-2.0.0-rc.24.tgz", 8239 + "integrity": "sha512-i7qRCmY42zmCwnYlh9H2SvLEypEFGye5iRmEMKjcGi7zk9UquigRjFtTLz0TYqr0ZGLZhaMHl/foy1bZR+Cwlw==", 8240 + "dev": true, 8241 + "license": "MIT", 8242 + "dependencies": { 8243 + "pathe": "^2.0.3" 8244 + } 8245 + }, 8246 + "node_modules/unicode-canonical-property-names-ecmascript": { 8247 + "version": "2.0.1", 8248 + "resolved": "https://registry.npmjs.org/unicode-canonical-property-names-ecmascript/-/unicode-canonical-property-names-ecmascript-2.0.1.tgz", 8249 + "integrity": "sha512-dA8WbNeb2a6oQzAQ55YlT5vQAWGV9WXOsi3SskE3bcCdM0P4SDd+24zS/OCacdRq5BkdsRj9q3Pg6YyQoxIGqg==", 8250 + "dev": true, 8251 + "license": "MIT", 8252 + "engines": { 8253 + "node": ">=4" 8254 + } 8255 + }, 8256 + "node_modules/unicode-match-property-ecmascript": { 8257 + "version": "2.0.0", 8258 + "resolved": "https://registry.npmjs.org/unicode-match-property-ecmascript/-/unicode-match-property-ecmascript-2.0.0.tgz", 8259 + "integrity": "sha512-5kaZCrbp5mmbz5ulBkDkbY0SsPOjKqVS35VpL9ulMPfSl0J0Xsm+9Evphv9CoIZFwre7aJoa94AY6seMKGVN5Q==", 8260 + "dev": true, 8261 + "license": "MIT", 8262 + "dependencies": { 8263 + "unicode-canonical-property-names-ecmascript": "^2.0.0", 8264 + "unicode-property-aliases-ecmascript": "^2.0.0" 8265 + }, 8266 + "engines": { 8267 + "node": ">=4" 8268 + } 8269 + }, 8270 + "node_modules/unicode-match-property-value-ecmascript": { 8271 + "version": "2.2.1", 8272 + "resolved": "https://registry.npmjs.org/unicode-match-property-value-ecmascript/-/unicode-match-property-value-ecmascript-2.2.1.tgz", 8273 + "integrity": "sha512-JQ84qTuMg4nVkx8ga4A16a1epI9H6uTXAknqxkGF/aFfRLw1xC/Bp24HNLaZhHSkWd3+84t8iXnp1J0kYcZHhg==", 8274 + "dev": true, 8275 + "license": "MIT", 8276 + "engines": { 8277 + "node": ">=4" 8278 + } 8279 + }, 8280 + "node_modules/unicode-property-aliases-ecmascript": { 8281 + "version": "2.2.0", 8282 + "resolved": "https://registry.npmjs.org/unicode-property-aliases-ecmascript/-/unicode-property-aliases-ecmascript-2.2.0.tgz", 8283 + "integrity": "sha512-hpbDzxUY9BFwX+UeBnxv3Sh1q7HFxj48DTmXchNgRa46lO8uj3/1iEn3MiNUYTg1g9ctIqXCCERn8gYZhHC5lQ==", 8284 + "dev": true, 8285 + "license": "MIT", 8286 + "engines": { 8287 + "node": ">=4" 8288 + } 8289 + }, 8290 + "node_modules/unique-string": { 8291 + "version": "2.0.0", 8292 + "resolved": "https://registry.npmjs.org/unique-string/-/unique-string-2.0.0.tgz", 8293 + "integrity": "sha512-uNaeirEPvpZWSgzwsPGtU2zVSTrn/8L5q/IexZmH0eH6SA73CmAA5U4GwORTxQAZs95TAXLNqeLoPPNO5gZfWg==", 8294 + "dev": true, 8295 + "license": "MIT", 8296 + "dependencies": { 8297 + "crypto-random-string": "^2.0.0" 8298 + }, 8299 + "engines": { 8300 + "node": ">=8" 8301 + } 8302 + }, 8303 + "node_modules/universalify": { 8304 + "version": "2.0.1", 8305 + "resolved": "https://registry.npmjs.org/universalify/-/universalify-2.0.1.tgz", 8306 + "integrity": "sha512-gptHNQghINnc/vTGIk0SOFGFNXw7JVrlRUtConJRlvaw6DuX0wO5Jeko9sWrMBhh+PsYAZ7oXAiOnf/UKogyiw==", 8307 + "dev": true, 8308 + "license": "MIT", 8309 + "engines": { 8310 + "node": ">= 10.0.0" 8311 + } 8312 + }, 8313 + "node_modules/upath": { 8314 + "version": "1.2.0", 8315 + "resolved": "https://registry.npmjs.org/upath/-/upath-1.2.0.tgz", 8316 + "integrity": "sha512-aZwGpamFO61g3OlfT7OQCHqhGnW43ieH9WZeP7QxN/G/jS4jfqUkZxoryvJgVPEcrl5NL/ggHsSmLMHuH64Lhg==", 8317 + "dev": true, 8318 + "license": "MIT", 8319 + "engines": { 8320 + "node": ">=4", 8321 + "yarn": "*" 8322 + } 8323 + }, 8324 + "node_modules/update-browserslist-db": { 8325 + "version": "1.2.3", 8326 + "resolved": "https://registry.npmjs.org/update-browserslist-db/-/update-browserslist-db-1.2.3.tgz", 8327 + "integrity": "sha512-Js0m9cx+qOgDxo0eMiFGEueWztz+d4+M3rGlmKPT+T4IS/jP4ylw3Nwpu6cpTTP8R1MAC1kF4VbdLt3ARf209w==", 8328 + "dev": true, 8329 + "funding": [ 8330 + { 8331 + "type": "opencollective", 8332 + "url": "https://opencollective.com/browserslist" 8333 + }, 8334 + { 8335 + "type": "tidelift", 8336 + "url": "https://tidelift.com/funding/github/npm/browserslist" 8337 + }, 8338 + { 8339 + "type": "github", 8340 + "url": "https://github.com/sponsors/ai" 8341 + } 8342 + ], 8343 + "license": "MIT", 8344 + "dependencies": { 8345 + "escalade": "^3.2.0", 8346 + "picocolors": "^1.1.1" 8347 + }, 8348 + "bin": { 8349 + "update-browserslist-db": "cli.js" 8350 + }, 8351 + "peerDependencies": { 8352 + "browserslist": ">= 4.21.0" 8353 + } 8354 + }, 8355 + "node_modules/vite": { 8356 + "version": "8.1.5", 8357 + "resolved": "https://registry.npmjs.org/vite/-/vite-8.1.5.tgz", 8358 + "integrity": "sha512-7ULLwsCdYx/nRyrpiEwvqb5TFHrMVZyBt+rg/OAXT7rgj/z+DtTDyKFeLAdDkubDVDKD8jOsndmy7m55XcfUsw==", 8359 + "dev": true, 8360 + "license": "MIT", 8361 + "dependencies": { 8362 + "lightningcss": "^1.32.0", 8363 + "picomatch": "^4.0.5", 8364 + "postcss": "^8.5.17", 8365 + "rolldown": "~1.1.5", 8366 + "tinyglobby": "^0.2.17" 8367 + }, 8368 + "bin": { 8369 + "vite": "bin/vite.js" 8370 + }, 8371 + "engines": { 8372 + "node": "^20.19.0 || >=22.12.0" 8373 + }, 8374 + "funding": { 8375 + "url": "https://github.com/vitejs/vite?sponsor=1" 8376 + }, 8377 + "optionalDependencies": { 8378 + "fsevents": "~2.3.3" 8379 + }, 8380 + "peerDependencies": { 8381 + "@types/node": "^20.19.0 || >=22.12.0", 8382 + "@vitejs/devtools": "^0.3.0", 8383 + "esbuild": "^0.27.0 || ^0.28.0", 8384 + "jiti": ">=1.21.0", 8385 + "less": "^4.0.0", 8386 + "sass": "^1.70.0", 8387 + "sass-embedded": "^1.70.0", 8388 + "stylus": ">=0.54.8", 8389 + "sugarss": "^5.0.0", 8390 + "terser": "^5.16.0", 8391 + "tsx": "^4.8.1", 8392 + "yaml": "^2.4.2" 8393 + }, 8394 + "peerDependenciesMeta": { 8395 + "@types/node": { 8396 + "optional": true 8397 + }, 8398 + "@vitejs/devtools": { 8399 + "optional": true 8400 + }, 8401 + "esbuild": { 8402 + "optional": true 8403 + }, 8404 + "jiti": { 8405 + "optional": true 8406 + }, 8407 + "less": { 8408 + "optional": true 8409 + }, 8410 + "sass": { 8411 + "optional": true 8412 + }, 8413 + "sass-embedded": { 8414 + "optional": true 8415 + }, 8416 + "stylus": { 8417 + "optional": true 8418 + }, 8419 + "sugarss": { 8420 + "optional": true 8421 + }, 8422 + "terser": { 8423 + "optional": true 8424 + }, 8425 + "tsx": { 8426 + "optional": true 8427 + }, 8428 + "yaml": { 8429 + "optional": true 8430 + } 8431 + } 8432 + }, 8433 + "node_modules/vite-plugin-pwa": { 8434 + "version": "1.3.0", 8435 + "resolved": "https://registry.npmjs.org/vite-plugin-pwa/-/vite-plugin-pwa-1.3.0.tgz", 8436 + "integrity": "sha512-c5kMgN+ITrOtHXp8PAtk2uOIEea6XjP/unCGxOWWBzQ6qa65qj/awHg0wf+QF9E/2u9vh86LqxPwzEPNbM2r5A==", 8437 + "dev": true, 8438 + "license": "MIT", 8439 + "dependencies": { 8440 + "debug": "^4.3.6", 8441 + "pretty-bytes": "^6.1.1", 8442 + "tinyglobby": "^0.2.10", 8443 + "workbox-build": "^7.4.1", 8444 + "workbox-window": "^7.4.1" 8445 + }, 8446 + "engines": { 8447 + "node": ">=16.0.0" 8448 + }, 8449 + "funding": { 8450 + "url": "https://github.com/sponsors/antfu" 8451 + }, 8452 + "peerDependencies": { 8453 + "@vite-pwa/assets-generator": "^1.0.0", 8454 + "vite": "^3.1.0 || ^4.0.0 || ^5.0.0 || ^6.0.0 || ^7.0.0 || ^8.0.0", 8455 + "workbox-build": "^7.4.1", 8456 + "workbox-window": "^7.4.1" 8457 + }, 8458 + "peerDependenciesMeta": { 8459 + "@vite-pwa/assets-generator": { 8460 + "optional": true 8461 + } 8462 + } 8463 + }, 8464 + "node_modules/webidl-conversions": { 8465 + "version": "4.0.2", 8466 + "resolved": "https://registry.npmjs.org/webidl-conversions/-/webidl-conversions-4.0.2.tgz", 8467 + "integrity": "sha512-YQ+BmxuTgd6UXZW3+ICGfyqRyHXVlD5GtQr5+qjiNW7bF0cqrzX500HVXPBOvgXb5YnzDd+h0zqyv61KUD7+Sg==", 8468 + "dev": true, 8469 + "license": "BSD-2-Clause" 8470 + }, 8471 + "node_modules/whatwg-url": { 8472 + "version": "7.1.0", 8473 + "resolved": "https://registry.npmjs.org/whatwg-url/-/whatwg-url-7.1.0.tgz", 8474 + "integrity": "sha512-WUu7Rg1DroM7oQvGWfOiAK21n74Gg+T4elXEQYkOhtyLeWiJFoOGLXPKI/9gzIie9CtwVLm8wtw6YJdKyxSjeg==", 8475 + "dev": true, 8476 + "license": "MIT", 8477 + "dependencies": { 8478 + "lodash.sortby": "^4.7.0", 8479 + "tr46": "^1.0.1", 8480 + "webidl-conversions": "^4.0.2" 8481 + } 8482 + }, 8483 + "node_modules/which": { 8484 + "version": "2.0.2", 8485 + "resolved": "https://registry.npmjs.org/which/-/which-2.0.2.tgz", 8486 + "integrity": "sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA==", 8487 + "dev": true, 8488 + "license": "ISC", 8489 + "dependencies": { 8490 + "isexe": "^2.0.0" 8491 + }, 8492 + "bin": { 8493 + "node-which": "bin/node-which" 8494 + }, 8495 + "engines": { 8496 + "node": ">= 8" 8497 + } 8498 + }, 8499 + "node_modules/which-boxed-primitive": { 8500 + "version": "1.1.1", 8501 + "resolved": "https://registry.npmjs.org/which-boxed-primitive/-/which-boxed-primitive-1.1.1.tgz", 8502 + "integrity": "sha512-TbX3mj8n0odCBFVlY8AxkqcHASw3L60jIuF8jFP78az3C2YhmGvqbHBpAjTRH2/xqYunrJ9g1jSyjCjpoWzIAA==", 8503 + "dev": true, 8504 + "license": "MIT", 8505 + "dependencies": { 8506 + "is-bigint": "^1.1.0", 8507 + "is-boolean-object": "^1.2.1", 8508 + "is-number-object": "^1.1.1", 8509 + "is-string": "^1.1.1", 8510 + "is-symbol": "^1.1.1" 8511 + }, 8512 + "engines": { 8513 + "node": ">= 0.4" 8514 + }, 8515 + "funding": { 8516 + "url": "https://github.com/sponsors/ljharb" 8517 + } 8518 + }, 8519 + "node_modules/which-builtin-type": { 8520 + "version": "1.2.1", 8521 + "resolved": "https://registry.npmjs.org/which-builtin-type/-/which-builtin-type-1.2.1.tgz", 8522 + "integrity": "sha512-6iBczoX+kDQ7a3+YJBnh3T+KZRxM/iYNPXicqk66/Qfm1b93iu+yOImkg0zHbj5LNOcNv1TEADiZ0xa34B4q6Q==", 8523 + "dev": true, 8524 + "license": "MIT", 8525 + "dependencies": { 8526 + "call-bound": "^1.0.2", 8527 + "function.prototype.name": "^1.1.6", 8528 + "has-tostringtag": "^1.0.2", 8529 + "is-async-function": "^2.0.0", 8530 + "is-date-object": "^1.1.0", 8531 + "is-finalizationregistry": "^1.1.0", 8532 + "is-generator-function": "^1.0.10", 8533 + "is-regex": "^1.2.1", 8534 + "is-weakref": "^1.0.2", 8535 + "isarray": "^2.0.5", 8536 + "which-boxed-primitive": "^1.1.0", 8537 + "which-collection": "^1.0.2", 8538 + "which-typed-array": "^1.1.16" 8539 + }, 8540 + "engines": { 8541 + "node": ">= 0.4" 8542 + }, 8543 + "funding": { 8544 + "url": "https://github.com/sponsors/ljharb" 8545 + } 8546 + }, 8547 + "node_modules/which-collection": { 8548 + "version": "1.0.2", 8549 + "resolved": "https://registry.npmjs.org/which-collection/-/which-collection-1.0.2.tgz", 8550 + "integrity": "sha512-K4jVyjnBdgvc86Y6BkaLZEN933SwYOuBFkdmBu9ZfkcAbdVbpITnDmjvZ/aQjRXQrv5EPkTnD1s39GiiqbngCw==", 8551 + "dev": true, 8552 + "license": "MIT", 8553 + "dependencies": { 8554 + "is-map": "^2.0.3", 8555 + "is-set": "^2.0.3", 8556 + "is-weakmap": "^2.0.2", 8557 + "is-weakset": "^2.0.3" 8558 + }, 8559 + "engines": { 8560 + "node": ">= 0.4" 8561 + }, 8562 + "funding": { 8563 + "url": "https://github.com/sponsors/ljharb" 8564 + } 8565 + }, 8566 + "node_modules/which-typed-array": { 8567 + "version": "1.1.22", 8568 + "resolved": "https://registry.npmjs.org/which-typed-array/-/which-typed-array-1.1.22.tgz", 8569 + "integrity": "sha512-fvO4ExWMFsqyhG3AiPAObMuY1lxaqgYcxbc49CNdWDDECOJNgQyvsOWVwbZc+qf3rzRtxojBK+CMEv0Ld5CYpw==", 8570 + "dev": true, 8571 + "license": "MIT", 8572 + "dependencies": { 8573 + "available-typed-arrays": "^1.0.7", 8574 + "call-bind": "^1.0.9", 8575 + "call-bound": "^1.0.4", 8576 + "for-each": "^0.3.5", 8577 + "get-proto": "^1.0.1", 8578 + "gopd": "^1.2.0", 8579 + "has-tostringtag": "^1.0.2" 8580 + }, 8581 + "engines": { 8582 + "node": ">= 0.4" 8583 + }, 8584 + "funding": { 8585 + "url": "https://github.com/sponsors/ljharb" 8586 + } 8587 + }, 8588 + "node_modules/workbox-background-sync": { 8589 + "version": "7.4.1", 8590 + "resolved": "https://registry.npmjs.org/workbox-background-sync/-/workbox-background-sync-7.4.1.tgz", 8591 + "integrity": "sha512-HhT7KE8tOWDm02wRNshXUnUPofMlhenF2DBdUnDPOubhizzPeItkYTmAB6td1Z2cjYPa98vzEiPLEuzn5hN66g==", 8592 + "dev": true, 8593 + "license": "MIT", 8594 + "dependencies": { 8595 + "idb": "^7.0.1", 8596 + "workbox-core": "7.4.1" 8597 + } 8598 + }, 8599 + "node_modules/workbox-broadcast-update": { 8600 + "version": "7.4.1", 8601 + "resolved": "https://registry.npmjs.org/workbox-broadcast-update/-/workbox-broadcast-update-7.4.1.tgz", 8602 + "integrity": "sha512-uAlgslKLvbQY+suirIdnBCSYrcgBhjp81Nj4l1lj/Jmj0MJO2CJERnCJjT0GFVwmReV0N+zs78K6gqd5gr9/+A==", 8603 + "dev": true, 8604 + "license": "MIT", 8605 + "dependencies": { 8606 + "workbox-core": "7.4.1" 8607 + } 8608 + }, 8609 + "node_modules/workbox-build": { 8610 + "version": "7.4.1", 8611 + "resolved": "https://registry.npmjs.org/workbox-build/-/workbox-build-7.4.1.tgz", 8612 + "integrity": "sha512-SDhxIvEAde9Gy/5w4Yo1Jh/M49Z0qE3q0oteyE8zGq0DScxFqVBcCtIXFuLtmtxRQZCMbf0prco4VyEu3KBQuw==", 8613 + "dev": true, 8614 + "license": "MIT", 8615 + "dependencies": { 8616 + "@apideck/better-ajv-errors": "^0.3.1", 8617 + "@babel/core": "^7.24.4", 8618 + "@babel/preset-env": "^7.11.0", 8619 + "@babel/runtime": "^7.11.2", 8620 + "@rollup/plugin-babel": "^6.1.0", 8621 + "@rollup/plugin-node-resolve": "^16.0.3", 8622 + "@rollup/plugin-replace": "^6.0.3", 8623 + "@rollup/plugin-terser": "^1.0.0", 8624 + "@trickfilm400/rollup-plugin-off-main-thread": "^3.0.0-pre1", 8625 + "ajv": "^8.6.0", 8626 + "common-tags": "^1.8.0", 8627 + "eta": "^4.5.1", 8628 + "fast-json-stable-stringify": "^2.1.0", 8629 + "fs-extra": "^9.0.1", 8630 + "glob": "^11.0.1", 8631 + "pretty-bytes": "^5.3.0", 8632 + "rollup": "^4.53.3", 8633 + "source-map": "^0.8.0-beta.0", 8634 + "stringify-object": "^3.3.0", 8635 + "strip-comments": "^2.0.1", 8636 + "tempy": "^0.6.0", 8637 + "upath": "^1.2.0", 8638 + "workbox-background-sync": "7.4.1", 8639 + "workbox-broadcast-update": "7.4.1", 8640 + "workbox-cacheable-response": "7.4.1", 8641 + "workbox-core": "7.4.1", 8642 + "workbox-expiration": "7.4.1", 8643 + "workbox-google-analytics": "7.4.1", 8644 + "workbox-navigation-preload": "7.4.1", 8645 + "workbox-precaching": "7.4.1", 8646 + "workbox-range-requests": "7.4.1", 8647 + "workbox-recipes": "7.4.1", 8648 + "workbox-routing": "7.4.1", 8649 + "workbox-strategies": "7.4.1", 8650 + "workbox-streams": "7.4.1", 8651 + "workbox-sw": "7.4.1", 8652 + "workbox-window": "7.4.1" 8653 + }, 8654 + "engines": { 8655 + "node": ">=20.0.0" 8656 + } 8657 + }, 8658 + "node_modules/workbox-build/node_modules/pretty-bytes": { 8659 + "version": "5.6.0", 8660 + "resolved": "https://registry.npmjs.org/pretty-bytes/-/pretty-bytes-5.6.0.tgz", 8661 + "integrity": "sha512-FFw039TmrBqFK8ma/7OL3sDz/VytdtJr044/QUJtH0wK9lb9jLq9tJyIxUwtQJHwar2BqtiA4iCWSwo9JLkzFg==", 8662 + "dev": true, 8663 + "license": "MIT", 8664 + "engines": { 8665 + "node": ">=6" 8666 + }, 8667 + "funding": { 8668 + "url": "https://github.com/sponsors/sindresorhus" 8669 + } 8670 + }, 8671 + "node_modules/workbox-cacheable-response": { 8672 + "version": "7.4.1", 8673 + "resolved": "https://registry.npmjs.org/workbox-cacheable-response/-/workbox-cacheable-response-7.4.1.tgz", 8674 + "integrity": "sha512-8xaFoJdDc2OjrlbbL3gEeBO1WKcMwRqwLRupgqahYXu75yXajPLuwrbXMrIGZuWYXrQwk0xDjOxZ/ujCy/oJYw==", 8675 + "dev": true, 8676 + "license": "MIT", 8677 + "dependencies": { 8678 + "workbox-core": "7.4.1" 8679 + } 8680 + }, 8681 + "node_modules/workbox-core": { 8682 + "version": "7.4.1", 8683 + "resolved": "https://registry.npmjs.org/workbox-core/-/workbox-core-7.4.1.tgz", 8684 + "integrity": "sha512-DT+vu46eh/2vRsSHTY4Xmc32Z1rr9PRlQUXr1Dx30ZuXRWwOsvZgGgcwxcasubQLQmbTNYZjv44LkBAQ4tT5tQ==", 8685 + "dev": true, 8686 + "license": "MIT" 8687 + }, 8688 + "node_modules/workbox-expiration": { 8689 + "version": "7.4.1", 8690 + "resolved": "https://registry.npmjs.org/workbox-expiration/-/workbox-expiration-7.4.1.tgz", 8691 + "integrity": "sha512-lRKUF7b+OGbeXkQk1s6MHXOa3d7Xxf7Of31W6c6hCfipfIyrtdWZ89stq21AHZMaoG7VNFoHply4Ox+rU31TWg==", 8692 + "dev": true, 8693 + "license": "MIT", 8694 + "dependencies": { 8695 + "idb": "^7.0.1", 8696 + "workbox-core": "7.4.1" 8697 + } 8698 + }, 8699 + "node_modules/workbox-google-analytics": { 8700 + "version": "7.4.1", 8701 + "resolved": "https://registry.npmjs.org/workbox-google-analytics/-/workbox-google-analytics-7.4.1.tgz", 8702 + "integrity": "sha512-Mks1JwLEt++ZAkF6sS1OpSh9RtAMIsiDgRpK+codiHGIPXeaUOgi4cPc3GFadUl8V5QPeypEk8Oxgl3HlwVzHw==", 8703 + "dev": true, 8704 + "license": "MIT", 8705 + "dependencies": { 8706 + "workbox-background-sync": "7.4.1", 8707 + "workbox-core": "7.4.1", 8708 + "workbox-routing": "7.4.1", 8709 + "workbox-strategies": "7.4.1" 8710 + } 8711 + }, 8712 + "node_modules/workbox-navigation-preload": { 8713 + "version": "7.4.1", 8714 + "resolved": "https://registry.npmjs.org/workbox-navigation-preload/-/workbox-navigation-preload-7.4.1.tgz", 8715 + "integrity": "sha512-C4KVsjPcYKJOhr631AxR9XoG2rLF3QiTk5aMv36MXOjtWvm8axwNFAtKUPGsWUwLXXAMgYM1En7fsvndaXeXRQ==", 8716 + "dev": true, 8717 + "license": "MIT", 8718 + "dependencies": { 8719 + "workbox-core": "7.4.1" 8720 + } 8721 + }, 8722 + "node_modules/workbox-precaching": { 8723 + "version": "7.4.1", 8724 + "resolved": "https://registry.npmjs.org/workbox-precaching/-/workbox-precaching-7.4.1.tgz", 8725 + "integrity": "sha512-cdr/9qByww7yzEp7zg/qI4ukUrrNjQLgN+ONQRpjy/VqGQXwkgHwr00KksGJK8v0VifwDXBb8a4cWNZH71jn3Q==", 8726 + "dev": true, 8727 + "license": "MIT", 8728 + "dependencies": { 8729 + "workbox-core": "7.4.1", 8730 + "workbox-routing": "7.4.1", 8731 + "workbox-strategies": "7.4.1" 8732 + } 8733 + }, 8734 + "node_modules/workbox-range-requests": { 8735 + "version": "7.4.1", 8736 + "resolved": "https://registry.npmjs.org/workbox-range-requests/-/workbox-range-requests-7.4.1.tgz", 8737 + "integrity": "sha512-7i2oxAUE82gHdAJBCAQ04JzNOdRPqzuOzGfoUyJpFSmeqBNYGPrAH8GPoPjUQTfp+NycwrD2H68VtuF8qxv0vQ==", 8738 + "dev": true, 8739 + "license": "MIT", 8740 + "dependencies": { 8741 + "workbox-core": "7.4.1" 8742 + } 8743 + }, 8744 + "node_modules/workbox-recipes": { 8745 + "version": "7.4.1", 8746 + "resolved": "https://registry.npmjs.org/workbox-recipes/-/workbox-recipes-7.4.1.tgz", 8747 + "integrity": "sha512-gnbVfmV4/TtmQaM4x9AtuXhcdstJsep3XMVeztOrQVPT+R6+6DeBjGTCQ7fFCXm+4GEHUA5VEBTyi5+4gWGeog==", 8748 + "dev": true, 8749 + "license": "MIT", 8750 + "dependencies": { 8751 + "workbox-cacheable-response": "7.4.1", 8752 + "workbox-core": "7.4.1", 8753 + "workbox-expiration": "7.4.1", 8754 + "workbox-precaching": "7.4.1", 8755 + "workbox-routing": "7.4.1", 8756 + "workbox-strategies": "7.4.1" 8757 + } 8758 + }, 8759 + "node_modules/workbox-routing": { 8760 + "version": "7.4.1", 8761 + "resolved": "https://registry.npmjs.org/workbox-routing/-/workbox-routing-7.4.1.tgz", 8762 + "integrity": "sha512-yubJGErZOusuidAenaL5ypfhQOa7urxP/f8E0ws7FPb4039RiWXUWBAyUkmUoOL/BcQGen3h0J8872d51IYxtA==", 8763 + "dev": true, 8764 + "license": "MIT", 8765 + "dependencies": { 8766 + "workbox-core": "7.4.1" 8767 + } 8768 + }, 8769 + "node_modules/workbox-strategies": { 8770 + "version": "7.4.1", 8771 + "resolved": "https://registry.npmjs.org/workbox-strategies/-/workbox-strategies-7.4.1.tgz", 8772 + "integrity": "sha512-GZxpaw9NbmOelj7667uZ2kpk5BFpOGbO4X0qjwh5ls8XQ8C+Lha5LQchTiUzsTFSS+NlUpftYAyOVXvQUrcqOQ==", 8773 + "dev": true, 8774 + "license": "MIT", 8775 + "dependencies": { 8776 + "workbox-core": "7.4.1" 8777 + } 8778 + }, 8779 + "node_modules/workbox-streams": { 8780 + "version": "7.4.1", 8781 + "resolved": "https://registry.npmjs.org/workbox-streams/-/workbox-streams-7.4.1.tgz", 8782 + "integrity": "sha512-HWWtraKUbJknd9kgqGcpQ3G114HOPYvqs8HaJMDs2ebLNAimDkVDaWfAXE6Ybl+m8U6KsCE6pWyLYuigWmnAXw==", 8783 + "dev": true, 8784 + "license": "MIT", 8785 + "dependencies": { 8786 + "workbox-core": "7.4.1", 8787 + "workbox-routing": "7.4.1" 8788 + } 8789 + }, 8790 + "node_modules/workbox-sw": { 8791 + "version": "7.4.1", 8792 + "resolved": "https://registry.npmjs.org/workbox-sw/-/workbox-sw-7.4.1.tgz", 8793 + "integrity": "sha512-fez5f2DUlDJWTFYkCWQpY10N8gtztd849NswCbVFk0QlcSM4HT5A8x4g4ii650yem4I8tHY0R7JZahwp3ltIPw==", 8794 + "dev": true, 8795 + "license": "MIT" 8796 + }, 8797 + "node_modules/workbox-window": { 8798 + "version": "7.4.1", 8799 + "resolved": "https://registry.npmjs.org/workbox-window/-/workbox-window-7.4.1.tgz", 8800 + "integrity": "sha512-notZDH2u8VXaqyuD7xaqIfEFi6SRM4SUSd7ewe9PDsVqADuepxX2ZMY3uvuZGxzY5ZOsGC/vD3A/3smFtJt4/A==", 8801 + "dev": true, 8802 + "license": "MIT", 8803 + "dependencies": { 8804 + "@types/trusted-types": "^2.0.2", 8805 + "workbox-core": "7.4.1" 8806 + } 8807 + }, 8808 + "node_modules/workerd": { 8809 + "version": "1.20260714.1", 8810 + "resolved": "https://registry.npmjs.org/workerd/-/workerd-1.20260714.1.tgz", 8811 + "integrity": "sha512-oIbQzfdyl9UQUnG6XLegcSq0Mgt/7WKDbFOoqGgOWCS+/fhyGB460uKEgdAQQ9RHCO/ttcNCX/KiMIQzdoeu3Q==", 8812 + "dev": true, 8813 + "hasInstallScript": true, 8814 + "license": "Apache-2.0", 8815 + "bin": { 8816 + "workerd": "bin/workerd" 8817 + }, 8818 + "engines": { 8819 + "node": ">=16" 8820 + }, 8821 + "optionalDependencies": { 8822 + "@cloudflare/workerd-darwin-64": "1.20260714.1", 8823 + "@cloudflare/workerd-darwin-arm64": "1.20260714.1", 8824 + "@cloudflare/workerd-linux-64": "1.20260714.1", 8825 + "@cloudflare/workerd-linux-arm64": "1.20260714.1", 8826 + "@cloudflare/workerd-windows-64": "1.20260714.1" 8827 + } 8828 + }, 8829 + "node_modules/wrangler": { 8830 + "version": "4.112.0", 8831 + "resolved": "https://registry.npmjs.org/wrangler/-/wrangler-4.112.0.tgz", 8832 + "integrity": "sha512-5H+XUD0TySCv1LuktFHDIEOkboH2nTfQs+35L+USt3MtntjDTMVIJprLgQcL2WBjulOyjxpd1vyTiSTJVW5MjQ==", 8833 + "dev": true, 8834 + "license": "MIT OR Apache-2.0", 8835 + "dependencies": { 8836 + "@cloudflare/kv-asset-handler": "0.5.0", 8837 + "@cloudflare/unenv-preset": "2.16.1", 8838 + "blake3-wasm": "2.1.5", 8839 + "esbuild": "0.28.1", 8840 + "miniflare": "4.20260714.0", 8841 + "path-to-regexp": "6.3.0", 8842 + "unenv": "2.0.0-rc.24", 8843 + "workerd": "1.20260714.1" 8844 + }, 8845 + "bin": { 8846 + "cf-wrangler": "bin/cf-wrangler.js", 8847 + "wrangler": "bin/wrangler.js", 8848 + "wrangler2": "bin/wrangler.js" 8849 + }, 8850 + "engines": { 8851 + "node": ">=22.0.0" 8852 + }, 8853 + "optionalDependencies": { 8854 + "fsevents": "2.3.3" 8855 + }, 8856 + "peerDependencies": { 8857 + "@cloudflare/workers-types": "^5.20260714.1" 8858 + }, 8859 + "peerDependenciesMeta": { 8860 + "@cloudflare/workers-types": { 8861 + "optional": true 8862 + } 8863 + } 8864 + }, 8865 + "node_modules/ws": { 8866 + "version": "8.21.0", 8867 + "resolved": "https://registry.npmjs.org/ws/-/ws-8.21.0.tgz", 8868 + "integrity": "sha512-Vsp28b7DRcimFQvrqu2Wek3z1iYxDCWqHYB8Qsnk/S4RfaCQzPGPyBNuVjJV3cd6UiKtUtp6sNM77gWvzcCH+g==", 8869 + "dev": true, 8870 + "license": "MIT", 8871 + "engines": { 8872 + "node": ">=10.0.0" 8873 + }, 8874 + "peerDependencies": { 8875 + "bufferutil": "^4.0.1", 8876 + "utf-8-validate": ">=5.0.2" 8877 + }, 8878 + "peerDependenciesMeta": { 8879 + "bufferutil": { 8880 + "optional": true 8881 + }, 8882 + "utf-8-validate": { 8883 + "optional": true 8884 + } 8885 + } 8886 + }, 8887 + "node_modules/yallist": { 8888 + "version": "3.1.1", 8889 + "resolved": "https://registry.npmjs.org/yallist/-/yallist-3.1.1.tgz", 8890 + "integrity": "sha512-a4UGQaWPH59mOXUYnAG2ewncQS4i4F43Tv3JoAM+s2VDAmS9NsK8GpDMLrCHPksFT7h3K6TOoUNn2pb7RoXx4g==", 8891 + "dev": true, 8892 + "license": "ISC" 8893 + }, 8894 + "node_modules/youch": { 8895 + "version": "4.1.0-beta.10", 8896 + "resolved": "https://registry.npmjs.org/youch/-/youch-4.1.0-beta.10.tgz", 8897 + "integrity": "sha512-rLfVLB4FgQneDr0dv1oddCVZmKjcJ6yX6mS4pU82Mq/Dt9a3cLZQ62pDBL4AUO+uVrCvtWz3ZFUL2HFAFJ/BXQ==", 8898 + "dev": true, 8899 + "license": "MIT", 8900 + "dependencies": { 8901 + "@poppinss/colors": "^4.1.5", 8902 + "@poppinss/dumper": "^0.6.4", 8903 + "@speed-highlight/core": "^1.2.7", 8904 + "cookie": "^1.0.2", 8905 + "youch-core": "^0.3.3" 8906 + } 8907 + }, 8908 + "node_modules/youch-core": { 8909 + "version": "0.3.3", 8910 + "resolved": "https://registry.npmjs.org/youch-core/-/youch-core-0.3.3.tgz", 8911 + "integrity": "sha512-ho7XuGjLaJ2hWHoK8yFnsUGy2Y5uDpqSTq1FkHLK4/oqKtyUU1AFbOOxY4IpC9f0fTLjwYbslUz0Po5BpD1wrA==", 8912 + "dev": true, 8913 + "license": "MIT", 8914 + "dependencies": { 8915 + "@poppinss/exception": "^1.2.2", 8916 + "error-stack-parser-es": "^1.0.5" 8917 + } 8918 + } 8919 + } 8920 + }
+38
package.json
··· 1 + { 2 + "name": "aniverse", 3 + "private": true, 4 + "type": "module", 5 + "scripts": { 6 + "dev": "vite dev", 7 + "build": "tsc -b && vite build", 8 + "deploy": "npm run build && wrangler deploy --config dist/aniverse/wrangler.json", 9 + "db:migrate:local": "wrangler d1 migrations apply aniverse --local", 10 + "db:migrate:remote": "wrangler d1 migrations apply aniverse --remote", 11 + "types": "wrangler types" 12 + }, 13 + "dependencies": { 14 + "@simplewebauthn/browser": "^13.3.0", 15 + "@simplewebauthn/server": "^13.3.2", 16 + "@tanstack/query-sync-storage-persister": "^5.101.2", 17 + "@tanstack/react-query": "^5.101.2", 18 + "@tanstack/react-query-persist-client": "^5.101.2", 19 + "arctic": "^3.7.0", 20 + "exifr": "^7.1.3", 21 + "hono": "^4.12.30", 22 + "react": "^19.2.7", 23 + "react-dom": "^19.2.7", 24 + "react-router-dom": "^7.18.1" 25 + }, 26 + "devDependencies": { 27 + "@cloudflare/vite-plugin": "^1.45.1", 28 + "@tailwindcss/vite": "^4.3.3", 29 + "@types/react": "^19.2.17", 30 + "@types/react-dom": "^19.2.3", 31 + "@vitejs/plugin-react": "^6.0.3", 32 + "tailwindcss": "^4.3.3", 33 + "typescript": "^7.0.2", 34 + "vite": "^8.1.5", 35 + "vite-plugin-pwa": "^1.3.0", 36 + "wrangler": "^4.112.0" 37 + } 38 + }
public/apple-touch-icon.png

This is a binary file and will not be displayed.

+29
public/icon.svg
··· 1 + <svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 180 180"> 2 + <defs> 3 + <linearGradient id="g" x1="0" y1="0" x2="1" y2="1"> 4 + <stop offset="0" stop-color="#a98fd6"/> 5 + <stop offset="1" stop-color="#ee9fc0"/> 6 + </linearGradient> 7 + </defs> 8 + <rect width="180" height="180" rx="40" fill="url(#g)"/> 9 + 10 + <!-- tiny stars --> 11 + <path d="M134 30 L137 38 L145 41 L137 44 L134 52 L131 44 L123 41 L131 38 Z" fill="#fff8ee" opacity="0.95"/> 12 + <circle cx="44" cy="48" r="2.2" fill="#fff8ee" opacity="0.8"/> 13 + <circle cx="146" cy="136" r="2.2" fill="#fff8ee" opacity="0.7"/> 14 + 15 + <!-- orbit behind (tilted) + back moon --> 16 + <g transform="rotate(-18 90 94)"> 17 + <ellipse cx="90" cy="94" rx="64" ry="21" fill="none" stroke="#4d3757" stroke-width="5" opacity="0.9"/> 18 + <circle cx="146" cy="83.5" r="5.5" fill="#4d3757"/> 19 + </g> 20 + 21 + <!-- heart planet, upright --> 22 + <path d="M90 68 C 84 54 66 50 56 60 C 46 70 48 86 60 98 C 70 108 90 124 90 124 C 90 124 110 108 120 98 C 132 86 134 70 124 60 C 114 50 96 54 90 68 Z" fill="#fff6ec"/> 23 + 24 + <!-- front half of the orbit + front moon (tilted) --> 25 + <g transform="rotate(-18 90 94)"> 26 + <path d="M26 94 A64 21 0 0 0 154 94" fill="none" stroke="#4d3757" stroke-width="5" stroke-linecap="round"/> 27 + <circle cx="58" cy="112" r="7" fill="#fff6ec" stroke="#4d3757" stroke-width="3"/> 28 + </g> 29 + </svg>
+13
public/manifest.webmanifest
··· 1 + { 2 + "name": "Aniverse", 3 + "short_name": "Aniverse", 4 + "description": "A little universe for the two of us", 5 + "start_url": "/", 6 + "display": "standalone", 7 + "background_color": "#f7f4f8", 8 + "theme_color": "#f7f4f8", 9 + "icons": [ 10 + { "src": "/icon.svg", "sizes": "any", "type": "image/svg+xml", "purpose": "any" }, 11 + { "src": "/apple-touch-icon.png", "sizes": "180x180", "type": "image/png" } 12 + ] 13 + }
+65
src/web/App.tsx
··· 1 + import { Navigate, Route, Routes, useLocation } from "react-router-dom"; 2 + import { useQuery } from "@tanstack/react-query"; 3 + import { api, ApiError } from "./lib/api"; 4 + import type { Me } from "./lib/types"; 5 + import Login from "./pages/Login"; 6 + import Setup from "./pages/Setup"; 7 + import Feed from "./pages/Feed"; 8 + import Compose from "./pages/Compose"; 9 + 10 + export function useMe() { 11 + return useQuery<Me, ApiError>({ 12 + queryKey: ["me"], 13 + queryFn: () => api.get<Me>("/api/auth/me"), 14 + }); 15 + } 16 + 17 + function Protected({ children }: { children: React.ReactNode }) { 18 + const me = useMe(); 19 + const location = useLocation(); 20 + 21 + if (me.isLoading) { 22 + return ( 23 + <div className="flex h-full items-center justify-center"> 24 + <span className="font-display text-2xl italic text-muted">aniverse…</span> 25 + </div> 26 + ); 27 + } 28 + if (me.isError) { 29 + if (me.error.status === 401) { 30 + return <Navigate to="/login" state={{ from: location }} replace />; 31 + } 32 + return ( 33 + <div className="flex h-full items-center justify-center text-muted"> 34 + something went wrong — try refreshing 35 + </div> 36 + ); 37 + } 38 + return <>{children}</>; 39 + } 40 + 41 + export default function App() { 42 + return ( 43 + <Routes> 44 + <Route path="/login" element={<Login />} /> 45 + <Route path="/setup" element={<Setup />} /> 46 + <Route 47 + path="/" 48 + element={ 49 + <Protected> 50 + <Feed /> 51 + </Protected> 52 + } 53 + /> 54 + <Route 55 + path="/new" 56 + element={ 57 + <Protected> 58 + <Compose /> 59 + </Protected> 60 + } 61 + /> 62 + <Route path="*" element={<Navigate to="/" replace />} /> 63 + </Routes> 64 + ); 65 + }
+167
src/web/components/Carousel.tsx
··· 1 + import { useRef, useState } from "react"; 2 + import type { Photo } from "../lib/types"; 3 + 4 + /** 5 + * Blur-up: shimmer placeholder, then the image fades in once decoded. 6 + * Single tap opens the lightbox (after a short delay so a second tap can 7 + * cancel it); double tap hearts the post, Instagram-style. 8 + */ 9 + function FeedImage({ 10 + photo, 11 + onOpen, 12 + onDoubleTap, 13 + }: { 14 + photo: Photo; 15 + onOpen?: () => void; 16 + onDoubleTap?: () => void; 17 + }) { 18 + const [loaded, setLoaded] = useState(false); 19 + const lastTap = useRef(0); 20 + const pendingOpen = useRef<ReturnType<typeof setTimeout>>(undefined); 21 + 22 + function handleClick() { 23 + const now = Date.now(); 24 + if (now - lastTap.current < 280) { 25 + clearTimeout(pendingOpen.current); 26 + lastTap.current = 0; 27 + onDoubleTap?.(); 28 + } else { 29 + lastTap.current = now; 30 + clearTimeout(pendingOpen.current); 31 + pendingOpen.current = setTimeout(() => onOpen?.(), 280); 32 + } 33 + } 34 + 35 + return ( 36 + <div className={`h-full w-full ${loaded ? "" : "shimmer"}`}> 37 + <img 38 + ref={(el) => { 39 + if (el?.complete) setLoaded(true); // already in browser cache 40 + }} 41 + src={`/img/${photo.id}/feed`} 42 + alt="" 43 + loading="lazy" 44 + onLoad={() => setLoaded(true)} 45 + onClick={handleClick} 46 + className={`h-full w-full cursor-pointer object-cover transition-[opacity,transform] duration-500 ${ 47 + loaded ? "opacity-100 scale-100" : "opacity-0 scale-[1.015]" 48 + }`} 49 + draggable={false} 50 + /> 51 + </div> 52 + ); 53 + } 54 + 55 + /** Instagram-style swipeable photo strip using CSS scroll-snap. */ 56 + export default function Carousel({ 57 + photos, 58 + onOpen, 59 + onDoubleTap, 60 + }: { 61 + photos: Photo[]; 62 + onOpen?: (index: number) => void; 63 + onDoubleTap?: () => void; 64 + }) { 65 + const track = useRef<HTMLDivElement>(null); 66 + const [index, setIndex] = useState(0); 67 + const [burst, setBurst] = useState(0); 68 + 69 + function handleDoubleTap() { 70 + setBurst((b) => b + 1); 71 + onDoubleTap?.(); 72 + } 73 + 74 + // All slides share the first photo's aspect ratio (clamped to IG-ish bounds). 75 + const first = photos[0]; 76 + const ratio = 77 + first?.width && first?.height 78 + ? Math.min(Math.max(first.width / first.height, 0.8), 1.91) 79 + : 1; 80 + 81 + function onScroll() { 82 + const el = track.current; 83 + if (!el) return; 84 + setIndex(Math.round(el.scrollLeft / el.clientWidth)); 85 + } 86 + 87 + function scrollTo(i: number) { 88 + const el = track.current; 89 + if (!el) return; 90 + el.scrollTo({ left: i * el.clientWidth, behavior: "smooth" }); 91 + } 92 + 93 + return ( 94 + <div className="group relative"> 95 + <div 96 + ref={track} 97 + onScroll={onScroll} 98 + className="no-scrollbar flex snap-x snap-mandatory overflow-x-auto" 99 + style={{ aspectRatio: ratio }} 100 + > 101 + {photos.map((photo, i) => ( 102 + <div key={photo.id} className="relative h-full w-full flex-shrink-0 snap-center"> 103 + <FeedImage photo={photo} onOpen={() => onOpen?.(i)} onDoubleTap={handleDoubleTap} /> 104 + {photo.location && ( 105 + <span className="absolute bottom-2 left-2 max-w-[80%] truncate rounded-pill bg-black/55 px-2.5 py-1 text-xs text-white backdrop-blur-sm"> 106 + 📍 {photo.location.name} 107 + </span> 108 + )} 109 + </div> 110 + ))} 111 + </div> 112 + 113 + {burst > 0 && ( 114 + <div 115 + key={burst} 116 + className="pointer-events-none absolute inset-0 flex items-center justify-center" 117 + > 118 + <svg 119 + viewBox="0 0 24 24" 120 + className="anim-heart-burst h-24 w-24 fill-white drop-shadow-[0_2px_12px_rgba(0,0,0,0.35)]" 121 + > 122 + <path d="M12 21.35l-1.45-1.32C5.4 15.36 2 12.28 2 8.5 2 5.42 4.42 3 7.5 3c1.74 0 3.41.81 4.5 2.09C13.09 3.81 14.76 3 16.5 3 19.58 3 22 5.42 22 8.5c0 3.78-3.4 6.86-8.55 11.54L12 21.35z" /> 123 + </svg> 124 + </div> 125 + )} 126 + 127 + {photos.length > 1 && ( 128 + <> 129 + {/* dots */} 130 + <div className="pointer-events-none absolute bottom-2 left-1/2 flex -translate-x-1/2 gap-1.5"> 131 + {photos.map((p, i) => ( 132 + <span 133 + key={p.id} 134 + className={`h-1.5 rounded-full transition-all duration-300 ${ 135 + i === index ? "w-4 bg-white" : "w-1.5 bg-white/45" 136 + }`} 137 + /> 138 + ))} 139 + </div> 140 + {/* count badge */} 141 + <span className="absolute right-2 top-2 rounded-pill bg-black/55 px-2 py-0.5 text-xs text-white"> 142 + {index + 1}/{photos.length} 143 + </span> 144 + {/* desktop chevrons */} 145 + {index > 0 && ( 146 + <button 147 + onClick={() => scrollTo(index - 1)} 148 + aria-label="Previous photo" 149 + className="absolute left-2 top-1/2 hidden h-8 w-8 -translate-y-1/2 items-center justify-center rounded-full bg-black/45 text-white opacity-0 transition group-hover:opacity-100 sm:flex" 150 + > 151 + 152 + </button> 153 + )} 154 + {index < photos.length - 1 && ( 155 + <button 156 + onClick={() => scrollTo(index + 1)} 157 + aria-label="Next photo" 158 + className="absolute right-2 top-1/2 hidden h-8 w-8 -translate-y-1/2 items-center justify-center rounded-full bg-black/45 text-white opacity-0 transition group-hover:opacity-100 sm:flex" 159 + > 160 + 161 + </button> 162 + )} 163 + </> 164 + )} 165 + </div> 166 + ); 167 + }
+85
src/web/components/Lightbox.tsx
··· 1 + import { useEffect } from "react"; 2 + import { createPortal } from "react-dom"; 3 + import type { Photo } from "../lib/types"; 4 + 5 + export default function Lightbox({ 6 + photos, 7 + index, 8 + onClose, 9 + onNavigate, 10 + }: { 11 + photos: Photo[]; 12 + index: number; 13 + onClose: () => void; 14 + onNavigate: (index: number) => void; 15 + }) { 16 + const photo = photos[index]; 17 + 18 + useEffect(() => { 19 + function onKey(e: KeyboardEvent) { 20 + if (e.key === "Escape") onClose(); 21 + if (e.key === "ArrowLeft" && index > 0) onNavigate(index - 1); 22 + if (e.key === "ArrowRight" && index < photos.length - 1) onNavigate(index + 1); 23 + } 24 + document.addEventListener("keydown", onKey); 25 + document.body.style.overflow = "hidden"; 26 + return () => { 27 + document.removeEventListener("keydown", onKey); 28 + document.body.style.overflow = ""; 29 + }; 30 + }, [index, photos.length, onClose, onNavigate]); 31 + 32 + if (!photo) return null; 33 + 34 + return createPortal( 35 + <div className="anim-fade fixed inset-0 z-50 flex items-center justify-center bg-black/95" onClick={onClose}> 36 + <img 37 + key={photo.id} 38 + src={`/img/${photo.id}/full`} 39 + alt="" 40 + className="anim-zoom max-h-full max-w-full object-contain" 41 + onClick={(e) => e.stopPropagation()} 42 + /> 43 + 44 + <button 45 + onClick={onClose} 46 + aria-label="Close" 47 + className="press absolute right-4 top-4 flex h-10 w-10 items-center justify-center rounded-pill bg-white/10 text-xl text-white" 48 + > 49 + 50 + </button> 51 + 52 + {photo.location && ( 53 + <span className="absolute bottom-4 left-1/2 -translate-x-1/2 rounded-pill bg-white/10 px-3 py-1.5 text-sm text-white"> 54 + 📍 {photo.location.name} 55 + </span> 56 + )} 57 + 58 + {index > 0 && ( 59 + <button 60 + onClick={(e) => { 61 + e.stopPropagation(); 62 + onNavigate(index - 1); 63 + }} 64 + aria-label="Previous" 65 + className="absolute left-3 top-1/2 flex h-10 w-10 -translate-y-1/2 items-center justify-center rounded-pill bg-white/10 text-2xl text-white" 66 + > 67 + 68 + </button> 69 + )} 70 + {index < photos.length - 1 && ( 71 + <button 72 + onClick={(e) => { 73 + e.stopPropagation(); 74 + onNavigate(index + 1); 75 + }} 76 + aria-label="Next" 77 + className="absolute right-3 top-1/2 flex h-10 w-10 -translate-y-1/2 items-center justify-center rounded-pill bg-white/10 text-2xl text-white" 78 + > 79 + 80 + </button> 81 + )} 82 + </div>, 83 + document.body 84 + ); 85 + }
+120
src/web/components/LocationPicker.tsx
··· 1 + import { useEffect, useRef, useState } from "react"; 2 + import { api } from "../lib/api"; 3 + import type { Location, PlaceSuggestion } from "../lib/types"; 4 + 5 + /** 6 + * Google Places autocomplete (proxied through the Worker). 7 + * `suggestion` is an optional EXIF-GPS-derived quick pick shown before typing. 8 + */ 9 + export default function LocationPicker({ 10 + value, 11 + onChange, 12 + suggestion, 13 + placeholder = "Search for a place…", 14 + autoFocus, 15 + }: { 16 + value: Location | null; 17 + onChange: (location: Location | null) => void; 18 + suggestion?: PlaceSuggestion | null; 19 + placeholder?: string; 20 + autoFocus?: boolean; 21 + }) { 22 + const [query, setQuery] = useState(""); 23 + const [results, setResults] = useState<PlaceSuggestion[]>([]); 24 + const [busy, setBusy] = useState(false); 25 + const [error, setError] = useState<string | null>(null); 26 + const session = useRef<string>(crypto.randomUUID()); 27 + const debounce = useRef<ReturnType<typeof setTimeout>>(undefined); 28 + 29 + useEffect(() => { 30 + clearTimeout(debounce.current); 31 + const q = query.trim(); 32 + if (q.length < 2) { 33 + setResults([]); 34 + return; 35 + } 36 + debounce.current = setTimeout(async () => { 37 + try { 38 + const { suggestions } = await api.get<{ suggestions: PlaceSuggestion[] }>( 39 + `/api/places/autocomplete?q=${encodeURIComponent(q)}&session=${session.current}` 40 + ); 41 + setResults(suggestions); 42 + setError(null); 43 + } catch { 44 + setError("search unavailable"); 45 + } 46 + }, 250); 47 + return () => clearTimeout(debounce.current); 48 + }, [query]); 49 + 50 + async function select(place: PlaceSuggestion) { 51 + setBusy(true); 52 + setError(null); 53 + try { 54 + const { location } = await api.post<{ location: Location }>("/api/places/select", { 55 + placeId: place.placeId, 56 + session: session.current, 57 + }); 58 + session.current = crypto.randomUUID(); // a session ends at place selection 59 + setQuery(""); 60 + setResults([]); 61 + onChange(location); 62 + } catch { 63 + setError("couldn't fetch that place"); 64 + } finally { 65 + setBusy(false); 66 + } 67 + } 68 + 69 + if (value) { 70 + return ( 71 + <span className="anim-pop inline-flex max-w-full items-center gap-1.5 rounded-pill bg-accent-soft px-3 py-1.5 text-sm text-accent"> 72 + <span className="truncate">📍 {value.name}</span> 73 + <button onClick={() => onChange(null)} aria-label="Remove location" className="font-semibold"> 74 + 75 + </button> 76 + </span> 77 + ); 78 + } 79 + 80 + const showGpsSuggestion = suggestion && query.trim().length < 2; 81 + 82 + return ( 83 + <div className="relative"> 84 + <input 85 + value={query} 86 + onChange={(e) => setQuery(e.target.value)} 87 + placeholder={placeholder} 88 + autoFocus={autoFocus} 89 + disabled={busy} 90 + className="w-full rounded-control border border-line bg-card px-3.5 py-2.5 text-sm outline-none focus:border-accent disabled:opacity-50" 91 + /> 92 + {(results.length > 0 || showGpsSuggestion || error) && ( 93 + <div className="anim-pop absolute z-30 mt-1 max-h-64 w-full origin-top overflow-y-auto rounded-control border border-line bg-card shadow-lg"> 94 + {error && <p className="px-3.5 py-2.5 text-sm text-muted">{error}</p>} 95 + {showGpsSuggestion && ( 96 + <button 97 + onClick={() => select(suggestion)} 98 + className="block w-full border-b border-line px-3.5 py-2.5 text-left transition hover:bg-accent-soft" 99 + > 100 + <span className="text-sm">✨ {suggestion.name}</span> 101 + <span className="block truncate text-xs text-muted"> 102 + from photo location — {suggestion.address} 103 + </span> 104 + </button> 105 + )} 106 + {results.map((r) => ( 107 + <button 108 + key={r.placeId} 109 + onClick={() => select(r)} 110 + className="block w-full px-3.5 py-2.5 text-left transition hover:bg-accent-soft" 111 + > 112 + <span className="text-sm">{r.name}</span> 113 + <span className="block truncate text-xs text-muted">{r.address}</span> 114 + </button> 115 + ))} 116 + </div> 117 + )} 118 + </div> 119 + ); 120 + }
+288
src/web/components/PostCard.tsx
··· 1 + import { useState } from "react"; 2 + import { useMutation, useQueryClient } from "@tanstack/react-query"; 3 + import { api } from "../lib/api"; 4 + import type { Comment, Post } from "../lib/types"; 5 + import { timeAgo } from "../lib/exif"; 6 + import { restoreFeed, snapshotFeed, updateFeedPost } from "../lib/feedCache"; 7 + import { useMe } from "../App"; 8 + import Carousel from "./Carousel"; 9 + import Lightbox from "./Lightbox"; 10 + 11 + // Keep in sync with EMOJIS in src/worker/routes/posts.ts 12 + const EMOJIS = ["❤️", "😂", "😮", "🥹", "🔥", "👍"]; 13 + 14 + export default function PostCard({ 15 + post, 16 + myUserId, 17 + index = 0, 18 + }: { 19 + post: Post; 20 + myUserId?: string; 21 + index?: number; 22 + }) { 23 + const [lightboxIndex, setLightboxIndex] = useState<number | null>(null); 24 + const [menuOpen, setMenuOpen] = useState(false); 25 + const [paletteOpen, setPaletteOpen] = useState(false); 26 + const [commentText, setCommentText] = useState(""); 27 + const queryClient = useQueryClient(); 28 + const me = useMe(); 29 + 30 + // Stale persisted caches may predate these fields. 31 + const reactions = post.reactions ?? []; 32 + const comments = post.comments ?? []; 33 + 34 + const del = useMutation({ 35 + mutationFn: () => api.del(`/api/posts/${post.id}`), 36 + // Optimistic: the post disappears immediately, comes back on failure. 37 + onMutate: async () => { 38 + await queryClient.cancelQueries({ queryKey: ["feed"] }); 39 + const previous = snapshotFeed(queryClient); 40 + queryClient.setQueryData(["feed"], (data: ReturnType<typeof snapshotFeed>) => 41 + data 42 + ? { 43 + ...data, 44 + pages: data.pages.map((page) => ({ 45 + ...page, 46 + posts: page.posts.filter((p) => p.id !== post.id), 47 + })), 48 + } 49 + : data 50 + ); 51 + return { previous }; 52 + }, 53 + onError: (_e, _v, ctx) => restoreFeed(queryClient, ctx?.previous), 54 + onSettled: () => queryClient.invalidateQueries({ queryKey: ["feed"] }), 55 + }); 56 + 57 + const react = useMutation({ 58 + mutationFn: ({ emoji, on }: { emoji: string; on: boolean }) => 59 + api.post(`/api/posts/${post.id}/react`, { emoji, on }), 60 + onMutate: async ({ emoji, on }) => { 61 + await queryClient.cancelQueries({ queryKey: ["feed"] }); 62 + const previous = snapshotFeed(queryClient); 63 + updateFeedPost(queryClient, post.id, (p) => { 64 + const current = p.reactions ?? []; 65 + const existing = current.find((r) => r.emoji === emoji); 66 + let next; 67 + if (on) { 68 + if (existing?.mine) next = current; 69 + else if (existing) 70 + next = current.map((r) => 71 + r.emoji === emoji ? { ...r, count: r.count + 1, mine: true } : r 72 + ); 73 + else next = [...current, { emoji, count: 1, mine: true }]; 74 + } else { 75 + next = current 76 + .map((r) => (r.emoji === emoji && r.mine ? { ...r, count: r.count - 1, mine: false } : r)) 77 + .filter((r) => r.count > 0); 78 + } 79 + return { ...p, reactions: next }; 80 + }); 81 + return { previous }; 82 + }, 83 + onError: (_e, _v, ctx) => restoreFeed(queryClient, ctx?.previous), 84 + }); 85 + 86 + const addComment = useMutation({ 87 + mutationFn: (body: string) => 88 + api.post<{ comment: Comment }>(`/api/posts/${post.id}/comments`, { body }), 89 + onMutate: async (body) => { 90 + await queryClient.cancelQueries({ queryKey: ["feed"] }); 91 + const previous = snapshotFeed(queryClient); 92 + const user = me.data?.user; 93 + const temp: Comment = { 94 + id: `temp-${Date.now()}`, 95 + body, 96 + createdAt: Math.floor(Date.now() / 1000), 97 + author: { 98 + id: user?.id ?? "", 99 + name: user?.name ?? "…", 100 + avatarUrl: user?.avatarUrl ?? null, 101 + }, 102 + }; 103 + updateFeedPost(queryClient, post.id, (p) => ({ 104 + ...p, 105 + comments: [...(p.comments ?? []), temp], 106 + })); 107 + setCommentText(""); 108 + return { previous }; 109 + }, 110 + onError: (_e, _v, ctx) => restoreFeed(queryClient, ctx?.previous), 111 + onSettled: () => queryClient.invalidateQueries({ queryKey: ["feed"] }), 112 + }); 113 + 114 + const deleteComment = useMutation({ 115 + mutationFn: (commentId: string) => 116 + api.del(`/api/posts/${post.id}/comments/${commentId}`), 117 + onMutate: async (commentId) => { 118 + await queryClient.cancelQueries({ queryKey: ["feed"] }); 119 + const previous = snapshotFeed(queryClient); 120 + updateFeedPost(queryClient, post.id, (p) => ({ 121 + ...p, 122 + comments: (p.comments ?? []).filter((cm) => cm.id !== commentId), 123 + })); 124 + return { previous }; 125 + }, 126 + onError: (_e, _v, ctx) => restoreFeed(queryClient, ctx?.previous), 127 + onSettled: () => queryClient.invalidateQueries({ queryKey: ["feed"] }), 128 + }); 129 + 130 + function toggleReaction(emoji: string) { 131 + const mine = reactions.find((r) => r.emoji === emoji)?.mine ?? false; 132 + react.mutate({ emoji, on: !mine }); 133 + setPaletteOpen(false); 134 + } 135 + 136 + const mine = post.author.id === myUserId; 137 + 138 + return ( 139 + <article 140 + className="anim-rise border-y border-line bg-card sm:rounded-card sm:border sm:shadow-card" 141 + style={{ animationDelay: `${Math.min(index, 6) * 60}ms` }} 142 + > 143 + <header className="flex items-center gap-3 px-4 py-3"> 144 + <div className="flex h-9 w-9 items-center justify-center overflow-hidden rounded-full bg-accent-soft"> 145 + {post.author.avatarUrl ? ( 146 + <img src={post.author.avatarUrl} alt="" className="h-full w-full object-cover" referrerPolicy="no-referrer" /> 147 + ) : ( 148 + <span className="text-sm font-semibold text-accent">{post.author.name[0]}</span> 149 + )} 150 + </div> 151 + <div className="min-w-0 flex-1 leading-tight"> 152 + <p className="truncate text-sm font-semibold">{post.author.name}</p> 153 + {post.location && ( 154 + <p className="truncate text-xs text-muted">📍 {post.location.name}</p> 155 + )} 156 + </div> 157 + <span className="text-xs text-muted">{timeAgo(post.createdAt)}</span> 158 + {mine && ( 159 + <div className="relative"> 160 + <button 161 + onClick={() => setMenuOpen((v) => !v)} 162 + aria-label="Post options" 163 + className="press px-1 text-muted transition hover:text-ink" 164 + > 165 + 166 + </button> 167 + {menuOpen && ( 168 + <div className="anim-pop absolute right-0 z-10 mt-1 origin-top-right overflow-hidden rounded-control border border-line bg-card shadow-lg"> 169 + <button 170 + onClick={() => { 171 + setMenuOpen(false); 172 + if (confirm("Delete this post? The photos will be gone too.")) del.mutate(); 173 + }} 174 + className="block w-full px-4 py-2.5 text-left text-sm text-accent transition hover:bg-accent-soft" 175 + > 176 + Delete post 177 + </button> 178 + </div> 179 + )} 180 + </div> 181 + )} 182 + </header> 183 + 184 + <Carousel 185 + photos={post.photos} 186 + onOpen={setLightboxIndex} 187 + onDoubleTap={() => react.mutate({ emoji: "❤️", on: true })} 188 + /> 189 + 190 + {/* reactions */} 191 + <div className="flex flex-wrap items-center gap-1.5 px-4 pt-3"> 192 + {reactions.map((r) => ( 193 + <button 194 + key={r.emoji} 195 + onClick={() => toggleReaction(r.emoji)} 196 + className={`press anim-pop rounded-pill border px-2.5 py-1 text-sm ${ 197 + r.mine ? "border-accent bg-accent-soft" : "border-line bg-card" 198 + }`} 199 + > 200 + {r.emoji} 201 + {r.count > 1 && <span className="ml-1 text-xs text-muted">{r.count}</span>} 202 + </button> 203 + ))} 204 + <div className="relative"> 205 + <button 206 + onClick={() => setPaletteOpen((v) => !v)} 207 + aria-label="Add reaction" 208 + className="press flex h-7 w-7 items-center justify-center rounded-pill border border-line text-muted transition hover:border-accent hover:text-accent" 209 + > 210 + <svg viewBox="0 0 24 24" className="h-4 w-4" fill="none" stroke="currentColor" strokeWidth="2"> 211 + <circle cx="12" cy="12" r="9" /> 212 + <path d="M8.5 14a4 4 0 0 0 7 0M9 10h.01M15 10h.01" strokeLinecap="round" /> 213 + </svg> 214 + </button> 215 + {paletteOpen && ( 216 + <div className="anim-pop absolute bottom-9 left-0 z-10 flex origin-bottom-left gap-0.5 rounded-pill border border-line bg-card px-2 py-1.5 shadow-lg"> 217 + {EMOJIS.map((emoji) => ( 218 + <button 219 + key={emoji} 220 + onClick={() => toggleReaction(emoji)} 221 + className="press px-1 text-xl transition hover:scale-125" 222 + > 223 + {emoji} 224 + </button> 225 + ))} 226 + </div> 227 + )} 228 + </div> 229 + </div> 230 + 231 + {post.caption && ( 232 + <p className="px-4 pt-2.5 text-sm leading-relaxed"> 233 + <span className="font-semibold">{post.author.name}</span> {post.caption} 234 + </p> 235 + )} 236 + 237 + {/* comments */} 238 + {comments.length > 0 && ( 239 + <div className="pt-1.5"> 240 + {comments.map((cm) => ( 241 + <p key={cm.id} className="group px-4 pt-1 text-sm leading-relaxed"> 242 + <span className="font-semibold">{cm.author.name}</span> {cm.body} 243 + {cm.author.id === myUserId && !cm.id.startsWith("temp-") && ( 244 + <button 245 + onClick={() => deleteComment.mutate(cm.id)} 246 + aria-label="Delete comment" 247 + className="ml-2 text-xs text-muted opacity-0 transition group-hover:opacity-100" 248 + > 249 + 250 + </button> 251 + )} 252 + </p> 253 + ))} 254 + </div> 255 + )} 256 + 257 + <form 258 + className="mt-2.5 flex items-center gap-2 border-t border-line px-4 py-2.5" 259 + onSubmit={(e) => { 260 + e.preventDefault(); 261 + const text = commentText.trim(); 262 + if (text) addComment.mutate(text); 263 + }} 264 + > 265 + <input 266 + value={commentText} 267 + onChange={(e) => setCommentText(e.target.value)} 268 + placeholder="Add a comment…" 269 + className="min-w-0 flex-1 bg-transparent text-sm outline-none placeholder:text-muted" 270 + /> 271 + {commentText.trim() && ( 272 + <button type="submit" className="press anim-pop text-sm font-semibold text-accent"> 273 + Post 274 + </button> 275 + )} 276 + </form> 277 + 278 + {lightboxIndex !== null && ( 279 + <Lightbox 280 + photos={post.photos} 281 + index={lightboxIndex} 282 + onClose={() => setLightboxIndex(null)} 283 + onNavigate={setLightboxIndex} 284 + /> 285 + )} 286 + </article> 287 + ); 288 + }
+305
src/web/index.css
··· 1 + @import "tailwindcss"; 2 + 3 + /* ---------- themes ---------- 4 + Each theme defines the same token set; the active one is picked by 5 + <html data-style="...">, persisted in localStorage (see lib/theme.ts). */ 6 + 7 + :root { 8 + /* pastel (default), light */ 9 + --bg: #f7f4f8; 10 + --card: #ffffff; 11 + --ink: #37323e; 12 + --muted: #97909f; 13 + --line: #eae4ee; 14 + --accent: #c07da4; 15 + --accent-soft: #f7e7f0; 16 + --r-card: 10px; 17 + --r-control: 10px; 18 + --r-pill: 9999px; 19 + --sh-card: 0 1px 3px rgb(40 30 50 / 0.06); 20 + --font-d: ui-serif, Georgia, "Times New Roman", serif; 21 + --font-b: ui-sans-serif, system-ui, -apple-system, sans-serif; 22 + } 23 + @media (prefers-color-scheme: dark) { 24 + :root { 25 + --bg: #191621; 26 + --card: #221e2c; 27 + --ink: #ece7f2; 28 + --muted: #9d96ab; 29 + --line: #332d42; 30 + --accent: #dda3c7; 31 + --accent-soft: #3a2c3c; 32 + --sh-card: 0 1px 3px rgb(0 0 0 / 0.4); 33 + } 34 + } 35 + 36 + [data-style="warm"] { 37 + --bg: #faf7f2; 38 + --card: #ffffff; 39 + --ink: #211b12; 40 + --muted: #8d8578; 41 + --line: #e9e2d6; 42 + --accent: #b5453b; 43 + --accent-soft: #f3e0dc; 44 + --r-card: 14px; 45 + --r-control: 12px; 46 + --r-pill: 9999px; 47 + --sh-card: 0 1px 3px rgb(60 40 20 / 0.07); 48 + } 49 + @media (prefers-color-scheme: dark) { 50 + [data-style="warm"] { 51 + --bg: #16130f; 52 + --card: #201c16; 53 + --ink: #f0e9dd; 54 + --muted: #9a9184; 55 + --line: #312b22; 56 + --accent: #e07a6b; 57 + --accent-soft: #3a2622; 58 + --sh-card: 0 1px 3px rgb(0 0 0 / 0.4); 59 + } 60 + } 61 + 62 + [data-style="brutalist"] { 63 + --bg: #f4f4f0; 64 + --card: #ffffff; 65 + --ink: #111111; 66 + --muted: #565656; 67 + --line: #111111; 68 + --accent: #d61f00; 69 + --accent-soft: #ffee00; 70 + --r-card: 0px; 71 + --r-control: 0px; 72 + --r-pill: 0px; 73 + --sh-card: 4px 4px 0 var(--ink); 74 + --font-d: ui-monospace, "SF Mono", Menlo, monospace; 75 + --font-b: ui-sans-serif, system-ui, -apple-system, sans-serif; 76 + } 77 + @media (prefers-color-scheme: dark) { 78 + [data-style="brutalist"] { 79 + --bg: #101010; 80 + --card: #1a1a1a; 81 + --ink: #f2f2f2; 82 + --muted: #9a9a9a; 83 + --line: #f2f2f2; 84 + --accent: #ff5c33; 85 + --accent-soft: #2c2c2c; 86 + --sh-card: 4px 4px 0 var(--ink); 87 + } 88 + } 89 + 90 + /* noir is deliberately dark in both color schemes */ 91 + [data-style="noir"] { 92 + --bg: #0c0c0d; 93 + --card: #151517; 94 + --ink: #f5f5f4; 95 + --muted: #8b8b90; 96 + --line: #26262a; 97 + --accent: #e63946; 98 + --accent-soft: #2a1517; 99 + --r-card: 8px; 100 + --r-control: 8px; 101 + --r-pill: 9999px; 102 + --sh-card: 0 1px 4px rgb(0 0 0 / 0.6); 103 + --font-d: ui-serif, Georgia, "Times New Roman", serif; 104 + } 105 + 106 + @theme { 107 + /* iOS-aligned type scale: footnote 13, subheadline 15, body 17 */ 108 + --text-xs: 13px; 109 + --text-xs--line-height: 1.4; 110 + --text-sm: 15px; 111 + --text-sm--line-height: 1.45; 112 + --text-base: 17px; 113 + --text-base--line-height: 1.45; 114 + } 115 + 116 + @theme inline { 117 + --color-bg: var(--bg); 118 + --color-card: var(--card); 119 + --color-ink: var(--ink); 120 + --color-muted: var(--muted); 121 + --color-line: var(--line); 122 + --color-accent: var(--accent); 123 + --color-accent-soft: var(--accent-soft); 124 + --font-display: var(--font-d); 125 + --radius-card: var(--r-card); 126 + --radius-control: var(--r-control); 127 + --radius-pill: var(--r-pill); 128 + --shadow-card: var(--sh-card); 129 + } 130 + 131 + html, 132 + body, 133 + #root { 134 + height: 100%; 135 + } 136 + 137 + body { 138 + background: var(--bg); 139 + color: var(--ink); 140 + font-family: var(--font-b); 141 + -webkit-font-smoothing: antialiased; 142 + } 143 + 144 + /* iOS Safari auto-zooms inputs with font-size < 16px on focus. 145 + Force 16px on touch devices only; desktop keeps the compact look. */ 146 + @media (hover: none) and (pointer: coarse) { 147 + input, 148 + textarea, 149 + select { 150 + font-size: max(16px, 1em) !important; 151 + } 152 + } 153 + 154 + /* Hide scrollbars on carousels without killing scroll */ 155 + @utility no-scrollbar { 156 + scrollbar-width: none; 157 + &::-webkit-scrollbar { 158 + display: none; 159 + } 160 + } 161 + 162 + /* ---------- microinteractions ---------- */ 163 + 164 + button, 165 + a { 166 + -webkit-tap-highlight-color: transparent; 167 + } 168 + 169 + /* gentle scale on press for anything tappable */ 170 + @utility press { 171 + transition: transform 0.15s ease; 172 + &:active { 173 + transform: scale(0.95); 174 + } 175 + } 176 + 177 + @keyframes rise { 178 + from { 179 + opacity: 0; 180 + transform: translateY(14px); 181 + } 182 + to { 183 + opacity: 1; 184 + transform: none; 185 + } 186 + } 187 + @keyframes pop { 188 + from { 189 + opacity: 0; 190 + transform: scale(0.9); 191 + } 192 + to { 193 + opacity: 1; 194 + transform: scale(1); 195 + } 196 + } 197 + @keyframes zoom-in { 198 + from { 199 + opacity: 0; 200 + transform: scale(0.96); 201 + } 202 + to { 203 + opacity: 1; 204 + transform: none; 205 + } 206 + } 207 + @keyframes slide-up { 208 + from { 209 + transform: translateY(100%); 210 + } 211 + to { 212 + transform: none; 213 + } 214 + } 215 + @keyframes fade-in { 216 + from { 217 + opacity: 0; 218 + } 219 + to { 220 + opacity: 1; 221 + } 222 + } 223 + @keyframes float { 224 + 0%, 225 + 100% { 226 + transform: translateY(0); 227 + } 228 + 50% { 229 + transform: translateY(-6px); 230 + } 231 + } 232 + @keyframes shimmer { 233 + to { 234 + background-position: -200% 0; 235 + } 236 + } 237 + @keyframes heart-burst { 238 + 0% { 239 + transform: scale(0); 240 + opacity: 0; 241 + } 242 + 15% { 243 + transform: scale(1.2); 244 + opacity: 1; 245 + } 246 + 30% { 247 + transform: scale(0.95); 248 + } 249 + 45% { 250 + transform: scale(1.05); 251 + } 252 + 70% { 253 + transform: scale(1); 254 + opacity: 1; 255 + } 256 + 100% { 257 + transform: scale(1.35); 258 + opacity: 0; 259 + } 260 + } 261 + 262 + @utility anim-rise { 263 + animation: rise 0.45s cubic-bezier(0.22, 1, 0.36, 1) both; 264 + } 265 + @utility anim-pop { 266 + animation: pop 0.22s cubic-bezier(0.34, 1.56, 0.64, 1) both; 267 + } 268 + @utility anim-zoom { 269 + animation: zoom-in 0.22s ease-out both; 270 + } 271 + @utility anim-slide-up { 272 + animation: slide-up 0.3s cubic-bezier(0.22, 1, 0.36, 1) both; 273 + } 274 + @utility anim-fade { 275 + animation: fade-in 0.2s ease-out both; 276 + } 277 + @utility anim-float { 278 + animation: float 3.2s ease-in-out infinite; 279 + } 280 + @utility anim-heart-burst { 281 + animation: heart-burst 0.9s ease both; 282 + } 283 + 284 + /* loading placeholder behind images */ 285 + @utility shimmer { 286 + background: linear-gradient( 287 + 100deg, 288 + var(--line) 40%, 289 + color-mix(in srgb, var(--line), var(--card) 55%) 50%, 290 + var(--line) 60% 291 + ); 292 + background-size: 200% 100%; 293 + animation: shimmer 1.6s linear infinite; 294 + } 295 + 296 + @media (prefers-reduced-motion: reduce) { 297 + *, 298 + *::before, 299 + *::after { 300 + animation-duration: 0.01ms !important; 301 + animation-iteration-count: 1 !important; 302 + transition-duration: 0.01ms !important; 303 + scroll-behavior: auto !important; 304 + } 305 + }
+77
src/web/lib/api.ts
··· 1 + export class ApiError extends Error { 2 + status: number; 3 + constructor(status: number, message: string) { 4 + super(message); 5 + this.status = status; 6 + } 7 + } 8 + 9 + async function request<T>(path: string, init?: RequestInit): Promise<T> { 10 + const res = await fetch(path, init); 11 + if (!res.ok) { 12 + let message = res.statusText; 13 + try { 14 + const body = (await res.json()) as { error?: string }; 15 + if (body.error) message = body.error; 16 + } catch { 17 + /* not json */ 18 + } 19 + throw new ApiError(res.status, message); 20 + } 21 + return res.json() as Promise<T>; 22 + } 23 + 24 + export const api = { 25 + get: <T>(path: string) => request<T>(path), 26 + post: <T>(path: string, body?: unknown) => 27 + request<T>(path, { 28 + method: "POST", 29 + headers: { "content-type": "application/json" }, 30 + body: JSON.stringify(body ?? {}), 31 + }), 32 + del: <T>(path: string) => request<T>(path, { method: "DELETE" }), 33 + }; 34 + 35 + export interface UploadMeta { 36 + takenAt?: number; 37 + lat?: number; 38 + lng?: number; 39 + width?: number; 40 + height?: number; 41 + orientation?: number; 42 + } 43 + 44 + /** XHR so we get upload progress events. */ 45 + export function uploadPhoto( 46 + file: File, 47 + meta: UploadMeta, 48 + onProgress: (fraction: number) => void 49 + ): Promise<{ id: string; width: number | null; height: number | null }> { 50 + return new Promise((resolve, reject) => { 51 + const xhr = new XMLHttpRequest(); 52 + xhr.open("POST", "/api/uploads"); 53 + xhr.setRequestHeader("content-type", file.type || "application/octet-stream"); 54 + xhr.setRequestHeader("x-filename", encodeURIComponent(file.name)); 55 + if (meta.takenAt) xhr.setRequestHeader("x-taken-at", String(meta.takenAt)); 56 + if (meta.lat !== undefined && meta.lng !== undefined) { 57 + xhr.setRequestHeader("x-gps-lat", String(meta.lat)); 58 + xhr.setRequestHeader("x-gps-lng", String(meta.lng)); 59 + } 60 + if (meta.width) xhr.setRequestHeader("x-width", String(meta.width)); 61 + if (meta.height) xhr.setRequestHeader("x-height", String(meta.height)); 62 + if (meta.orientation) xhr.setRequestHeader("x-orientation", String(meta.orientation)); 63 + 64 + xhr.upload.onprogress = (e) => { 65 + if (e.lengthComputable) onProgress(e.loaded / e.total); 66 + }; 67 + xhr.onload = () => { 68 + if (xhr.status >= 200 && xhr.status < 300) { 69 + resolve(JSON.parse(xhr.responseText)); 70 + } else { 71 + reject(new ApiError(xhr.status, `upload failed (${xhr.status})`)); 72 + } 73 + }; 74 + xhr.onerror = () => reject(new ApiError(0, "network error during upload")); 75 + xhr.send(file); 76 + }); 77 + }
+57
src/web/lib/exif.ts
··· 1 + import exifr from "exifr"; 2 + import type { UploadMeta } from "./api"; 3 + 4 + export async function extractMeta(file: File): Promise<UploadMeta> { 5 + const meta: UploadMeta = {}; 6 + 7 + try { 8 + // translateValues keeps Orientation numeric (1-8) instead of "Rotate 90 CW" 9 + const data = await exifr.parse(file, { 10 + pick: ["DateTimeOriginal", "CreateDate", "Orientation"], 11 + translateValues: false, 12 + }); 13 + const d: unknown = data?.DateTimeOriginal ?? data?.CreateDate; 14 + if (d instanceof Date && !Number.isNaN(d.getTime())) { 15 + meta.takenAt = Math.floor(d.getTime() / 1000); 16 + } 17 + if (typeof data?.Orientation === "number" && data.Orientation >= 1 && data.Orientation <= 8) { 18 + meta.orientation = data.Orientation; 19 + } 20 + } catch { 21 + /* no exif */ 22 + } 23 + 24 + try { 25 + const gps = await exifr.gps(file); 26 + if (gps && Number.isFinite(gps.latitude) && Number.isFinite(gps.longitude)) { 27 + meta.lat = gps.latitude; 28 + meta.lng = gps.longitude; 29 + } 30 + } catch { 31 + /* no gps */ 32 + } 33 + 34 + try { 35 + const bmp = await createImageBitmap(file); 36 + meta.width = bmp.width; 37 + meta.height = bmp.height; 38 + bmp.close(); 39 + } catch { 40 + /* browser can't decode (e.g. HEIC on non-Safari) */ 41 + } 42 + 43 + return meta; 44 + } 45 + 46 + export function timeAgo(unixSeconds: number): string { 47 + const diff = Math.floor(Date.now() / 1000) - unixSeconds; 48 + if (diff < 60) return "just now"; 49 + if (diff < 3600) return `${Math.floor(diff / 60)}m ago`; 50 + if (diff < 86400) return `${Math.floor(diff / 3600)}h ago`; 51 + if (diff < 7 * 86400) return `${Math.floor(diff / 86400)}d ago`; 52 + return new Date(unixSeconds * 1000).toLocaleDateString(undefined, { 53 + month: "short", 54 + day: "numeric", 55 + year: diff > 330 * 86400 ? "numeric" : undefined, 56 + }); 57 + }
+32
src/web/lib/feedCache.ts
··· 1 + import type { InfiniteData, QueryClient } from "@tanstack/react-query"; 2 + import type { FeedPage, Post } from "./types"; 3 + 4 + /** Apply an optimistic edit to one post across all cached feed pages. */ 5 + export function updateFeedPost( 6 + queryClient: QueryClient, 7 + postId: string, 8 + fn: (post: Post) => Post 9 + ) { 10 + queryClient.setQueryData<InfiniteData<FeedPage>>(["feed"], (data) => 11 + data 12 + ? { 13 + ...data, 14 + pages: data.pages.map((page) => ({ 15 + ...page, 16 + posts: page.posts.map((p) => (p.id === postId ? fn(p) : p)), 17 + })), 18 + } 19 + : data 20 + ); 21 + } 22 + 23 + export function snapshotFeed(queryClient: QueryClient) { 24 + return queryClient.getQueryData<InfiniteData<FeedPage>>(["feed"]); 25 + } 26 + 27 + export function restoreFeed( 28 + queryClient: QueryClient, 29 + snapshot: InfiniteData<FeedPage> | undefined 30 + ) { 31 + if (snapshot) queryClient.setQueryData(["feed"], snapshot); 32 + }
+35
src/web/lib/theme.ts
··· 1 + import { useState } from "react"; 2 + 3 + export const THEMES = [ 4 + { id: "pastel", label: "Pastel" }, 5 + { id: "warm", label: "Warm" }, 6 + { id: "brutalist", label: "Brutalist" }, 7 + { id: "noir", label: "Noir" }, 8 + ] as const; 9 + 10 + export type ThemeId = (typeof THEMES)[number]["id"]; 11 + 12 + const KEY = "aniverse-style"; 13 + 14 + function syncMetaThemeColor() { 15 + // Keep the browser chrome (PWA status bar) matching the active theme. 16 + requestAnimationFrame(() => { 17 + const bg = getComputedStyle(document.documentElement).getPropertyValue("--bg").trim(); 18 + document 19 + .querySelectorAll<HTMLMetaElement>('meta[name="theme-color"]') 20 + .forEach((m) => (m.content = bg)); 21 + }); 22 + } 23 + 24 + export function useTheme() { 25 + const [theme, setThemeState] = useState<ThemeId>( 26 + () => (document.documentElement.dataset.style as ThemeId) || "pastel" 27 + ); 28 + function setTheme(id: ThemeId) { 29 + localStorage.setItem(KEY, id); 30 + document.documentElement.dataset.style = id; 31 + setThemeState(id); 32 + syncMetaThemeColor(); 33 + } 34 + return { theme, setTheme }; 35 + }
+54
src/web/lib/types.ts
··· 1 + export interface Location { 2 + id: string; 3 + name: string; 4 + address: string | null; 5 + lat: number | null; 6 + lng: number | null; 7 + } 8 + 9 + export interface Photo { 10 + id: string; 11 + width: number | null; 12 + height: number | null; 13 + takenAt: number | null; 14 + location: Location | null; 15 + } 16 + 17 + export interface Comment { 18 + id: string; 19 + body: string; 20 + createdAt: number; 21 + author: { id: string; name: string; avatarUrl: string | null }; 22 + } 23 + 24 + export interface Reaction { 25 + emoji: string; 26 + count: number; 27 + mine: boolean; 28 + } 29 + 30 + export interface Post { 31 + id: string; 32 + caption: string; 33 + createdAt: number; 34 + author: { id: string; name: string; avatarUrl: string | null }; 35 + location: Location | null; 36 + photos: Photo[]; 37 + comments: Comment[]; 38 + reactions: Reaction[]; 39 + } 40 + 41 + export interface FeedPage { 42 + posts: Post[]; 43 + nextCursor: string | null; 44 + } 45 + 46 + export interface Me { 47 + user: { id: string; email: string; name: string; avatarUrl: string | null }; 48 + } 49 + 50 + export interface PlaceSuggestion { 51 + placeId: string; 52 + name: string; 53 + address: string; 54 + }
+14
src/web/lib/useOnline.ts
··· 1 + import { useSyncExternalStore } from "react"; 2 + 3 + function subscribe(callback: () => void) { 4 + window.addEventListener("online", callback); 5 + window.addEventListener("offline", callback); 6 + return () => { 7 + window.removeEventListener("online", callback); 8 + window.removeEventListener("offline", callback); 9 + }; 10 + } 11 + 12 + export function useOnline(): boolean { 13 + return useSyncExternalStore(subscribe, () => navigator.onLine); 14 + }
+49
src/web/main.tsx
··· 1 + import { StrictMode } from "react"; 2 + import { createRoot } from "react-dom/client"; 3 + import { BrowserRouter } from "react-router-dom"; 4 + import { QueryClient } from "@tanstack/react-query"; 5 + import { PersistQueryClientProvider } from "@tanstack/react-query-persist-client"; 6 + import { createSyncStoragePersister } from "@tanstack/query-sync-storage-persister"; 7 + import { registerSW } from "virtual:pwa-register"; 8 + import { ApiError } from "./lib/api"; 9 + import App from "./App"; 10 + import "./index.css"; 11 + 12 + const WEEK = 1000 * 60 * 60 * 24 * 7; 13 + 14 + const queryClient = new QueryClient({ 15 + defaultOptions: { 16 + queries: { 17 + retry: (failureCount, error) => { 18 + if (error instanceof ApiError && error.status === 401) return false; 19 + return failureCount < 2; 20 + }, 21 + staleTime: 30_000, 22 + gcTime: WEEK, // keep data around so the persisted cache can restore it 23 + }, 24 + }, 25 + }); 26 + 27 + // Local-first: the query cache (feed, session) survives restarts, so the app 28 + // paints instantly from disk and then revalidates in the background. 29 + const persister = createSyncStoragePersister({ 30 + storage: window.localStorage, 31 + key: "aniverse-cache", 32 + }); 33 + 34 + if (import.meta.env.PROD) { 35 + registerSW({ immediate: true }); 36 + } 37 + 38 + createRoot(document.getElementById("root")!).render( 39 + <StrictMode> 40 + <PersistQueryClientProvider 41 + client={queryClient} 42 + persistOptions={{ persister, maxAge: WEEK, buster: "v2" }} 43 + > 44 + <BrowserRouter> 45 + <App /> 46 + </BrowserRouter> 47 + </PersistQueryClientProvider> 48 + </StrictMode> 49 + );
+270
src/web/pages/Compose.tsx
··· 1 + import { useRef, useState } from "react"; 2 + import { Link, useNavigate } from "react-router-dom"; 3 + import { useQueryClient } from "@tanstack/react-query"; 4 + import { api, uploadPhoto } from "../lib/api"; 5 + import { extractMeta } from "../lib/exif"; 6 + import type { Location, PlaceSuggestion } from "../lib/types"; 7 + import LocationPicker from "../components/LocationPicker"; 8 + 9 + interface Draft { 10 + key: string; 11 + file: File; 12 + preview: string; 13 + meta: Awaited<ReturnType<typeof extractMeta>>; 14 + location: Location | null; 15 + gpsSuggestion: PlaceSuggestion | null; 16 + progress: number; 17 + } 18 + 19 + export default function Compose() { 20 + const [drafts, setDrafts] = useState<Draft[]>([]); 21 + const [caption, setCaption] = useState(""); 22 + const [postLocation, setPostLocation] = useState<Location | null>(null); 23 + const [editingKey, setEditingKey] = useState<string | null>(null); 24 + const [posting, setPosting] = useState(false); 25 + const [error, setError] = useState<string | null>(null); 26 + const fileInput = useRef<HTMLInputElement>(null); 27 + const navigate = useNavigate(); 28 + const queryClient = useQueryClient(); 29 + 30 + function patchDraft(key: string, patch: Partial<Draft>) { 31 + setDrafts((ds) => ds.map((d) => (d.key === key ? { ...d, ...patch } : d))); 32 + } 33 + 34 + async function addFiles(files: FileList | null) { 35 + if (!files?.length) return; 36 + for (const file of Array.from(files)) { 37 + if (!file.type.startsWith("image/")) continue; 38 + const key = crypto.randomUUID(); 39 + const draft: Draft = { 40 + key, 41 + file, 42 + preview: URL.createObjectURL(file), 43 + meta: {}, 44 + location: null, 45 + gpsSuggestion: null, 46 + progress: 0, 47 + }; 48 + setDrafts((ds) => [...ds, draft]); 49 + 50 + const meta = await extractMeta(file); 51 + patchDraft(key, { meta }); 52 + if (meta.lat !== undefined && meta.lng !== undefined) { 53 + try { 54 + const { suggestion } = await api.get<{ suggestion: PlaceSuggestion | null }>( 55 + `/api/places/reverse?lat=${meta.lat}&lng=${meta.lng}` 56 + ); 57 + if (suggestion) patchDraft(key, { gpsSuggestion: suggestion }); 58 + } catch { 59 + /* places not configured / offline — fine */ 60 + } 61 + } 62 + } 63 + if (fileInput.current) fileInput.current.value = ""; 64 + } 65 + 66 + function move(key: string, dir: -1 | 1) { 67 + setDrafts((ds) => { 68 + const i = ds.findIndex((d) => d.key === key); 69 + const j = i + dir; 70 + if (i < 0 || j < 0 || j >= ds.length) return ds; 71 + const next = [...ds]; 72 + [next[i], next[j]] = [next[j], next[i]]; 73 + return next; 74 + }); 75 + } 76 + 77 + function remove(key: string) { 78 + setDrafts((ds) => { 79 + const target = ds.find((d) => d.key === key); 80 + if (target) URL.revokeObjectURL(target.preview); 81 + return ds.filter((d) => d.key !== key); 82 + }); 83 + } 84 + 85 + async function share() { 86 + if (!drafts.length || posting) return; 87 + setPosting(true); 88 + setError(null); 89 + try { 90 + const uploaded: { id: string; locationId?: string | null }[] = []; 91 + for (const draft of drafts) { 92 + const { id } = await uploadPhoto(draft.file, draft.meta, (fraction) => 93 + patchDraft(draft.key, { progress: fraction }) 94 + ); 95 + patchDraft(draft.key, { progress: 1 }); 96 + uploaded.push({ id, locationId: draft.location?.id ?? null }); 97 + } 98 + await api.post("/api/posts", { 99 + caption, 100 + locationId: postLocation?.id ?? null, 101 + photos: uploaded, 102 + }); 103 + await queryClient.invalidateQueries({ queryKey: ["feed"] }); 104 + drafts.forEach((d) => URL.revokeObjectURL(d.preview)); 105 + navigate("/", { replace: true }); 106 + } catch (e) { 107 + console.error(e); 108 + setError("Something went wrong while posting — try again?"); 109 + setPosting(false); 110 + } 111 + } 112 + 113 + const editing = drafts.find((d) => d.key === editingKey); 114 + 115 + return ( 116 + <div className="mx-auto flex min-h-full max-w-md flex-col"> 117 + <header className="sticky top-0 z-20 flex items-center justify-between border-b border-line bg-bg/85 px-4 py-3 backdrop-blur"> 118 + <Link to="/" aria-label="Back" className="text-2xl leading-none text-muted"> 119 + 120 + </Link> 121 + <h1 className="font-display text-xl italic">new post</h1> 122 + <button 123 + onClick={share} 124 + disabled={!drafts.length || posting} 125 + className="press rounded-pill bg-accent px-4 py-1.5 text-sm font-medium text-white transition disabled:opacity-40" 126 + > 127 + {posting ? "Sharing…" : "Share"} 128 + </button> 129 + </header> 130 + 131 + <main className="flex flex-1 flex-col gap-5 px-4 py-5 pb-16"> 132 + {/* photo strip */} 133 + <div className="flex gap-3 overflow-x-auto pb-1"> 134 + {drafts.map((draft, i) => ( 135 + <div key={draft.key} className="anim-pop w-36 flex-shrink-0"> 136 + <div className="relative overflow-hidden rounded-control border border-line"> 137 + <img src={draft.preview} alt="" className="h-44 w-36 object-cover" /> 138 + {posting && ( 139 + <div className="absolute inset-x-0 bottom-0 h-1 bg-black/20"> 140 + <div 141 + className="h-full bg-accent transition-all" 142 + style={{ width: `${Math.round(draft.progress * 100)}%` }} 143 + /> 144 + </div> 145 + )} 146 + {!posting && ( 147 + <> 148 + <button 149 + onClick={() => remove(draft.key)} 150 + aria-label="Remove photo" 151 + className="absolute right-1.5 top-1.5 flex h-6 w-6 items-center justify-center rounded-pill bg-black/55 text-xs text-white" 152 + > 153 + 154 + </button> 155 + <div className="absolute bottom-1.5 right-1.5 flex gap-1"> 156 + {i > 0 && ( 157 + <button 158 + onClick={() => move(draft.key, -1)} 159 + aria-label="Move left" 160 + className="flex h-6 w-6 items-center justify-center rounded-pill bg-black/55 text-xs text-white" 161 + > 162 + 163 + </button> 164 + )} 165 + {i < drafts.length - 1 && ( 166 + <button 167 + onClick={() => move(draft.key, 1)} 168 + aria-label="Move right" 169 + className="flex h-6 w-6 items-center justify-center rounded-pill bg-black/55 text-xs text-white" 170 + > 171 + 172 + </button> 173 + )} 174 + </div> 175 + </> 176 + )} 177 + </div> 178 + <button 179 + onClick={() => setEditingKey(draft.key)} 180 + disabled={posting} 181 + className={`mt-1.5 w-full truncate rounded-pill px-2 py-1 text-xs transition ${ 182 + draft.location 183 + ? "bg-accent-soft text-accent" 184 + : "border border-dashed border-line text-muted" 185 + }`} 186 + > 187 + {draft.location 188 + ? `📍 ${draft.location.name}` 189 + : draft.gpsSuggestion 190 + ? `✨ ${draft.gpsSuggestion.name}?` 191 + : "📍 add location"} 192 + </button> 193 + </div> 194 + ))} 195 + 196 + <button 197 + onClick={() => fileInput.current?.click()} 198 + disabled={posting} 199 + className="flex h-44 w-36 flex-shrink-0 flex-col items-center justify-center gap-2 rounded-control border-2 border-dashed border-line text-muted transition hover:border-accent hover:text-accent" 200 + > 201 + <span className="text-3xl leading-none">+</span> 202 + <span className="text-xs">{drafts.length ? "add more" : "add photos"}</span> 203 + </button> 204 + <input 205 + ref={fileInput} 206 + type="file" 207 + accept="image/*" 208 + multiple 209 + hidden 210 + onChange={(e) => addFiles(e.target.files)} 211 + /> 212 + </div> 213 + 214 + {/* caption */} 215 + <textarea 216 + value={caption} 217 + onChange={(e) => setCaption(e.target.value)} 218 + placeholder="Write a caption…" 219 + rows={3} 220 + disabled={posting} 221 + className="w-full resize-none rounded-control border border-line bg-card px-3.5 py-3 text-sm outline-none focus:border-accent" 222 + /> 223 + 224 + {/* post-level location */} 225 + <div> 226 + <p className="mb-1.5 text-xs font-medium uppercase tracking-wide text-muted"> 227 + Post location 228 + </p> 229 + <LocationPicker value={postLocation} onChange={setPostLocation} /> 230 + </div> 231 + 232 + {error && <p className="text-sm text-accent">{error}</p>} 233 + </main> 234 + 235 + {/* per-photo location sheet */} 236 + {editing && ( 237 + <div 238 + className="anim-fade fixed inset-0 z-40 flex items-start justify-center bg-black/40 px-3 pt-[8vh] sm:items-center sm:pt-0" 239 + onClick={() => setEditingKey(null)} 240 + > 241 + <div 242 + className="anim-zoom w-full max-w-md rounded-card bg-bg p-5" 243 + onClick={(e) => e.stopPropagation()} 244 + > 245 + <div className="mb-4 flex items-center gap-3"> 246 + <img src={editing.preview} alt="" className="h-12 w-12 rounded-control object-cover" /> 247 + <p className="text-sm font-medium">Where was this photo taken?</p> 248 + <button 249 + onClick={() => setEditingKey(null)} 250 + aria-label="Close" 251 + className="ml-auto text-muted" 252 + > 253 + 254 + </button> 255 + </div> 256 + <LocationPicker 257 + value={editing.location} 258 + onChange={(location) => { 259 + patchDraft(editing.key, { location }); 260 + if (location) setEditingKey(null); 261 + }} 262 + suggestion={editing.gpsSuggestion} 263 + autoFocus 264 + /> 265 + </div> 266 + </div> 267 + )} 268 + </div> 269 + ); 270 + }
+149
src/web/pages/Feed.tsx
··· 1 + import { useEffect, useRef, useState } from "react"; 2 + import { Link, useNavigate } from "react-router-dom"; 3 + import { useInfiniteQuery, useQueryClient } from "@tanstack/react-query"; 4 + import { api } from "../lib/api"; 5 + import type { FeedPage } from "../lib/types"; 6 + import { useMe } from "../App"; 7 + import { useOnline } from "../lib/useOnline"; 8 + import { THEMES, useTheme } from "../lib/theme"; 9 + import PostCard from "../components/PostCard"; 10 + 11 + export default function Feed() { 12 + const me = useMe(); 13 + const navigate = useNavigate(); 14 + const queryClient = useQueryClient(); 15 + const [menuOpen, setMenuOpen] = useState(false); 16 + const online = useOnline(); 17 + const { theme, setTheme } = useTheme(); 18 + 19 + const feed = useInfiniteQuery({ 20 + queryKey: ["feed"], 21 + queryFn: ({ pageParam }) => 22 + api.get<FeedPage>(`/api/posts/feed${pageParam ? `?cursor=${pageParam}` : ""}`), 23 + initialPageParam: "", 24 + getNextPageParam: (last) => last.nextCursor ?? undefined, 25 + }); 26 + 27 + const sentinel = useRef<HTMLDivElement>(null); 28 + useEffect(() => { 29 + const el = sentinel.current; 30 + if (!el) return; 31 + const observer = new IntersectionObserver( 32 + (entries) => { 33 + if (entries[0].isIntersecting && feed.hasNextPage && !feed.isFetchingNextPage) { 34 + feed.fetchNextPage(); 35 + } 36 + }, 37 + { rootMargin: "600px" } 38 + ); 39 + observer.observe(el); 40 + return () => observer.disconnect(); 41 + }, [feed.hasNextPage, feed.isFetchingNextPage, feed.fetchNextPage]); 42 + 43 + async function logout() { 44 + await api.post("/api/auth/logout"); 45 + queryClient.clear(); 46 + navigate("/login", { replace: true }); 47 + } 48 + 49 + const posts = feed.data?.pages.flatMap((p) => p.posts) ?? []; 50 + const user = me.data?.user; 51 + 52 + return ( 53 + <div className="mx-auto flex min-h-full max-w-md flex-col"> 54 + <header className="sticky top-0 z-20 flex items-center justify-between border-b border-line bg-bg/85 px-4 py-3 backdrop-blur"> 55 + <h1 className="font-display text-2xl italic tracking-tight">aniverse</h1> 56 + <div className="flex items-center gap-3"> 57 + <Link 58 + to="/new" 59 + aria-label="New post" 60 + className="press flex h-9 w-9 items-center justify-center rounded-pill bg-accent text-white shadow-sm transition hover:opacity-90" 61 + > 62 + <svg viewBox="0 0 24 24" className="h-5 w-5" fill="none" stroke="currentColor" strokeWidth="2"> 63 + <path d="M12 5v14M5 12h14" strokeLinecap="round" /> 64 + </svg> 65 + </Link> 66 + <div className="relative"> 67 + <button 68 + onClick={() => setMenuOpen((v) => !v)} 69 + aria-label="Account" 70 + className="press block h-9 w-9 overflow-hidden rounded-full border border-line bg-accent-soft" 71 + > 72 + {user?.avatarUrl ? ( 73 + <img src={user.avatarUrl} alt="" className="h-full w-full object-cover" referrerPolicy="no-referrer" /> 74 + ) : ( 75 + <span className="flex h-full w-full items-center justify-center text-sm font-semibold text-accent"> 76 + {user?.name?.[0] ?? "?"} 77 + </span> 78 + )} 79 + </button> 80 + {menuOpen && ( 81 + <div className="anim-pop absolute right-0 mt-2 w-44 origin-top-right overflow-hidden rounded-control border border-line bg-card shadow-lg"> 82 + <div className="border-b border-line px-4 py-2 text-sm text-muted">{user?.name}</div> 83 + <div className="px-4 pb-1 pt-2 text-[11px] font-medium uppercase tracking-wide text-muted"> 84 + Theme 85 + </div> 86 + {THEMES.map((t) => ( 87 + <button 88 + key={t.id} 89 + onClick={() => setTheme(t.id)} 90 + className="flex w-full items-center justify-between px-4 py-2 text-left text-sm transition hover:bg-accent-soft" 91 + > 92 + {t.label} 93 + {theme === t.id && <span className="text-accent">✓</span>} 94 + </button> 95 + ))} 96 + <button 97 + onClick={logout} 98 + className="mt-1 block w-full border-t border-line px-4 py-2.5 text-left text-sm transition hover:bg-accent-soft" 99 + > 100 + Sign out 101 + </button> 102 + </div> 103 + )} 104 + </div> 105 + </div> 106 + </header> 107 + 108 + <main className="flex-1 pb-16"> 109 + {!online && ( 110 + <p className="anim-pop mx-auto mt-3 w-fit rounded-pill bg-accent-soft px-3.5 py-1.5 text-center text-xs text-accent"> 111 + offline — showing saved memories 112 + </p> 113 + )} 114 + {feed.isLoading && ( 115 + <p className="py-16 text-center text-sm text-muted">loading memories…</p> 116 + )} 117 + {feed.isError && ( 118 + <p className="py-16 text-center text-sm text-accent">couldn't load the feed — pull to refresh?</p> 119 + )} 120 + {!feed.isLoading && posts.length === 0 && !feed.isError && ( 121 + <div className="anim-rise flex flex-col items-center gap-4 py-24 text-center"> 122 + <span className="anim-float text-4xl">📷</span> 123 + <p className="text-muted"> 124 + nothing here yet —<br /> 125 + post the first memory! 126 + </p> 127 + <Link 128 + to="/new" 129 + className="press rounded-pill bg-accent px-5 py-2.5 text-sm font-medium text-white shadow-sm" 130 + > 131 + New post 132 + </Link> 133 + </div> 134 + )} 135 + 136 + <div className="flex flex-col gap-6 pt-4"> 137 + {posts.map((post, i) => ( 138 + <PostCard key={post.id} post={post} myUserId={user?.id} index={i % 10} /> 139 + ))} 140 + </div> 141 + 142 + <div ref={sentinel} /> 143 + {feed.isFetchingNextPage && ( 144 + <p className="py-6 text-center text-sm text-muted">loading more…</p> 145 + )} 146 + </main> 147 + </div> 148 + ); 149 + }
+143
src/web/pages/Login.tsx
··· 1 + import { useState } from "react"; 2 + import { useNavigate, useSearchParams } from "react-router-dom"; 3 + import { useQuery, useQueryClient } from "@tanstack/react-query"; 4 + import { startAuthentication } from "@simplewebauthn/browser"; 5 + import { api } from "../lib/api"; 6 + import type { PublicKeyCredentialRequestOptionsJSON } from "@simplewebauthn/browser"; 7 + 8 + interface DevLogin { 9 + enabled: boolean; 10 + users?: { email: string; name: string }[]; 11 + } 12 + 13 + const ERRORS: Record<string, string> = { 14 + oauth_failed: "Google sign-in didn't work — try again?", 15 + not_invited: "This universe only has room for two 💫", 16 + google_not_configured: "Google sign-in isn't set up yet.", 17 + }; 18 + 19 + export default function Login() { 20 + const [params] = useSearchParams(); 21 + const [busy, setBusy] = useState(false); 22 + const [error, setError] = useState<string | null>( 23 + params.get("error") ? (ERRORS[params.get("error")!] ?? "Sign-in failed.") : null 24 + ); 25 + const [devPassword, setDevPassword] = useState(""); 26 + const navigate = useNavigate(); 27 + const queryClient = useQueryClient(); 28 + 29 + const dev = useQuery({ 30 + queryKey: ["dev-login"], 31 + queryFn: () => api.get<DevLogin>("/api/auth/dev"), 32 + staleTime: Infinity, 33 + retry: false, 34 + }); 35 + 36 + async function devLogin(email: string) { 37 + setError(null); 38 + try { 39 + await api.post("/api/auth/dev", { password: devPassword, email }); 40 + await queryClient.invalidateQueries({ queryKey: ["me"] }); 41 + navigate("/", { replace: true }); 42 + } catch { 43 + setError("Dev login failed — wrong password?"); 44 + } 45 + } 46 + 47 + async function passkeyLogin() { 48 + setBusy(true); 49 + setError(null); 50 + try { 51 + const { options, challengeId } = await api.post<{ 52 + options: PublicKeyCredentialRequestOptionsJSON; 53 + challengeId: string; 54 + }>("/api/auth/passkey/login-options"); 55 + const credential = await startAuthentication({ optionsJSON: options }); 56 + await api.post("/api/auth/passkey/login-verify", { challengeId, credential }); 57 + await queryClient.invalidateQueries({ queryKey: ["me"] }); 58 + navigate("/", { replace: true }); 59 + } catch (e) { 60 + console.error(e); 61 + setError("Passkey sign-in didn't work — try again?"); 62 + } finally { 63 + setBusy(false); 64 + } 65 + } 66 + 67 + return ( 68 + <div className="flex min-h-full flex-col items-center justify-center gap-10 px-6"> 69 + <div className="anim-rise text-center"> 70 + <h1 className="font-display text-5xl italic tracking-tight">aniverse</h1> 71 + <p className="mt-3 text-sm text-muted">a little universe for the two of us</p> 72 + </div> 73 + 74 + <div className="anim-rise flex w-full max-w-xs flex-col gap-3" style={{ animationDelay: "120ms" }}> 75 + <a 76 + href="/api/auth/google" 77 + className="press flex items-center justify-center gap-3 rounded-pill border border-line bg-card px-5 py-3 text-sm font-medium shadow-sm transition hover:shadow" 78 + > 79 + <svg viewBox="0 0 24 24" className="h-5 w-5" aria-hidden> 80 + <path 81 + fill="#4285F4" 82 + d="M23.5 12.3c0-.9-.1-1.5-.3-2.2H12v4.1h6.5c-.1 1.1-.8 2.7-2.4 3.8l-.02.15 3.5 2.7.24.02c2.2-2 3.5-5 3.5-8.6" 83 + /> 84 + <path 85 + fill="#34A853" 86 + d="M12 24c3.2 0 5.9-1.1 7.9-2.9l-3.8-2.9c-1 .7-2.4 1.2-4.1 1.2a7.2 7.2 0 0 1-6.8-5l-.14.01-3.7 2.8-.05.13A12 12 0 0 0 12 24" 87 + /> 88 + <path 89 + fill="#FBBC05" 90 + d="M5.2 14.4a7.4 7.4 0 0 1-.4-2.4c0-.8.2-1.6.4-2.4l-.01-.16-3.72-2.9-.12.06a12 12 0 0 0 0 10.8l3.85-3" 91 + /> 92 + <path 93 + fill="#EB4335" 94 + d="M12 4.6c2.3 0 3.8 1 4.7 1.8l3.4-3.3C18 1.2 15.2 0 12 0A12 12 0 0 0 1.3 6.6l3.9 3A7.2 7.2 0 0 1 12 4.6" 95 + /> 96 + </svg> 97 + Continue with Google 98 + </a> 99 + 100 + <button 101 + onClick={passkeyLogin} 102 + disabled={busy} 103 + className="press flex items-center justify-center gap-3 rounded-pill bg-ink px-5 py-3 text-sm font-medium text-bg shadow-sm transition hover:opacity-90 disabled:opacity-50" 104 + > 105 + <svg viewBox="0 0 24 24" className="h-5 w-5" fill="none" stroke="currentColor" strokeWidth="2" aria-hidden> 106 + <circle cx="8" cy="8" r="4" /> 107 + <path d="M2 21v-1a6 6 0 0 1 9-5.2" /> 108 + <circle cx="17" cy="13" r="3" /> 109 + <path d="M17 16v5l2-1.5L17 18" /> 110 + </svg> 111 + {busy ? "Waiting for passkey…" : "Sign in with passkey"} 112 + </button> 113 + 114 + {error && <p className="mt-2 text-center text-sm text-accent">{error}</p>} 115 + 116 + {dev.data?.enabled && ( 117 + <div className="mt-6 flex flex-col gap-2 rounded-control border border-dashed border-line p-3"> 118 + <p className="text-center text-xs uppercase tracking-wide text-muted">local dev</p> 119 + <input 120 + type="password" 121 + placeholder="dev password" 122 + value={devPassword} 123 + onChange={(e) => setDevPassword(e.target.value)} 124 + className="rounded-control border border-line bg-card px-3 py-2 text-sm outline-none focus:border-accent" 125 + /> 126 + <div className="flex gap-2"> 127 + {dev.data.users?.map((u) => ( 128 + <button 129 + key={u.email} 130 + onClick={() => devLogin(u.email)} 131 + disabled={!devPassword} 132 + className="flex-1 rounded-control border border-line bg-card px-3 py-2 text-sm transition hover:border-accent disabled:opacity-40" 133 + > 134 + as {u.name} 135 + </button> 136 + ))} 137 + </div> 138 + </div> 139 + )} 140 + </div> 141 + </div> 142 + ); 143 + }
+71
src/web/pages/Setup.tsx
··· 1 + import { useState } from "react"; 2 + import { useNavigate, useSearchParams } from "react-router-dom"; 3 + import { useQueryClient } from "@tanstack/react-query"; 4 + import { startRegistration } from "@simplewebauthn/browser"; 5 + import { api, ApiError } from "../lib/api"; 6 + import type { PublicKeyCredentialCreationOptionsJSON } from "@simplewebauthn/browser"; 7 + 8 + /** One-time passkey enrollment, gated by SETUP_SECRET. Visit /setup?key=... */ 9 + export default function Setup() { 10 + const [params] = useSearchParams(); 11 + const [setupKey, setSetupKey] = useState(params.get("key") ?? ""); 12 + const [email, setEmail] = useState("anirudh@oppiliappan.com"); 13 + const [busy, setBusy] = useState(false); 14 + const [error, setError] = useState<string | null>(null); 15 + const navigate = useNavigate(); 16 + const queryClient = useQueryClient(); 17 + 18 + async function enroll() { 19 + setBusy(true); 20 + setError(null); 21 + try { 22 + const { options, challengeId } = await api.post<{ 23 + options: PublicKeyCredentialCreationOptionsJSON; 24 + challengeId: string; 25 + }>("/api/auth/passkey/register-options", { setupKey, email }); 26 + const credential = await startRegistration({ optionsJSON: options }); 27 + await api.post("/api/auth/passkey/register-verify", { challengeId, credential }); 28 + await queryClient.invalidateQueries({ queryKey: ["me"] }); 29 + navigate("/", { replace: true }); 30 + } catch (e) { 31 + console.error(e); 32 + setError(e instanceof ApiError ? e.message : "Enrollment failed — try again?"); 33 + } finally { 34 + setBusy(false); 35 + } 36 + } 37 + 38 + return ( 39 + <div className="flex min-h-full flex-col items-center justify-center gap-8 px-6"> 40 + <div className="text-center"> 41 + <h1 className="font-display text-4xl italic">set up your passkey</h1> 42 + <p className="mt-2 text-sm text-muted">a one-time thing, per device</p> 43 + </div> 44 + 45 + <div className="flex w-full max-w-xs flex-col gap-3"> 46 + <input 47 + type="password" 48 + placeholder="setup secret" 49 + value={setupKey} 50 + onChange={(e) => setSetupKey(e.target.value)} 51 + className="rounded-control border border-line bg-card px-4 py-3 text-sm outline-none focus:border-accent" 52 + /> 53 + <input 54 + type="email" 55 + placeholder="your email" 56 + value={email} 57 + onChange={(e) => setEmail(e.target.value)} 58 + className="rounded-control border border-line bg-card px-4 py-3 text-sm outline-none focus:border-accent" 59 + /> 60 + <button 61 + onClick={enroll} 62 + disabled={busy || !setupKey || !email} 63 + className="rounded-pill bg-ink px-5 py-3 text-sm font-medium text-bg transition hover:opacity-90 disabled:opacity-50" 64 + > 65 + {busy ? "Creating passkey…" : "Create passkey"} 66 + </button> 67 + {error && <p className="text-center text-sm text-accent">{error}</p>} 68 + </div> 69 + </div> 70 + ); 71 + }
+2
src/web/vite-env.d.ts
··· 1 + /// <reference types="vite/client" /> 2 + /// <reference types="vite-plugin-pwa/client" />
+24
src/worker/index.ts
··· 1 + import { Hono } from "hono"; 2 + import type { AppEnv } from "./lib/session"; 3 + import { auth } from "./routes/auth"; 4 + import { uploads } from "./routes/uploads"; 5 + import { posts } from "./routes/posts"; 6 + import { places } from "./routes/places"; 7 + import { img } from "./routes/img"; 8 + 9 + const app = new Hono<AppEnv>(); 10 + 11 + app.route("/api/auth", auth); 12 + app.route("/api/uploads", uploads); 13 + app.route("/api/posts", posts); 14 + app.route("/api/places", places); 15 + app.route("/img", img); 16 + 17 + app.onError((err, c) => { 18 + console.error(err); 19 + return c.json({ error: "internal error" }, 500); 20 + }); 21 + 22 + app.notFound((c) => c.json({ error: "not found" }, 404)); 23 + 24 + export default app;
+78
src/worker/lib/session.ts
··· 1 + import type { Context, MiddlewareHandler } from "hono"; 2 + import { getCookie, setCookie, deleteCookie } from "hono/cookie"; 3 + import { now, randomToken, sha256hex } from "./util"; 4 + 5 + const COOKIE = "sid"; 6 + const TTL = 90 * 24 * 60 * 60; // 90 days 7 + const REFRESH_BELOW = 60 * 24 * 60 * 60; // refresh when less than 60 days left 8 + 9 + export interface SessionUser { 10 + id: string; 11 + email: string; 12 + name: string; 13 + avatar_url: string | null; 14 + } 15 + 16 + export type AppEnv = { 17 + Bindings: Env; 18 + Variables: { user: SessionUser }; 19 + }; 20 + 21 + function secure(c: Context): boolean { 22 + return new URL(c.req.url).protocol === "https:"; 23 + } 24 + 25 + export async function createSession(c: Context<AppEnv>, userId: string): Promise<void> { 26 + const token = randomToken(); 27 + await c.env.DB.prepare( 28 + "INSERT INTO sessions (token_hash, user_id, expires_at) VALUES (?, ?, ?)" 29 + ) 30 + .bind(await sha256hex(token), userId, now() + TTL) 31 + .run(); 32 + setCookie(c, COOKIE, token, { 33 + httpOnly: true, 34 + secure: secure(c), 35 + sameSite: "Lax", 36 + path: "/", 37 + maxAge: TTL, 38 + }); 39 + } 40 + 41 + export async function destroySession(c: Context<AppEnv>): Promise<void> { 42 + const token = getCookie(c, COOKIE); 43 + if (token) { 44 + await c.env.DB.prepare("DELETE FROM sessions WHERE token_hash = ?") 45 + .bind(await sha256hex(token)) 46 + .run(); 47 + } 48 + deleteCookie(c, COOKIE, { path: "/" }); 49 + } 50 + 51 + /** Require a valid session; sets c.var.user. Responds 401 otherwise. */ 52 + export const requireAuth: MiddlewareHandler<AppEnv> = async (c, next) => { 53 + const token = getCookie(c, COOKIE); 54 + if (!token) return c.json({ error: "unauthenticated" }, 401); 55 + 56 + const hash = await sha256hex(token); 57 + const row = await c.env.DB.prepare( 58 + `SELECT s.expires_at, u.id, u.email, u.name, u.avatar_url 59 + FROM sessions s JOIN users u ON u.id = s.user_id 60 + WHERE s.token_hash = ? AND s.expires_at > ?` 61 + ) 62 + .bind(hash, now()) 63 + .first<{ expires_at: number } & SessionUser>(); 64 + 65 + if (!row) return c.json({ error: "unauthenticated" }, 401); 66 + 67 + // Rolling expiry: bump the session when it has burned through a third of its life. 68 + if (row.expires_at - now() < REFRESH_BELOW) { 69 + c.executionCtx.waitUntil( 70 + c.env.DB.prepare("UPDATE sessions SET expires_at = ? WHERE token_hash = ?") 71 + .bind(now() + TTL, hash) 72 + .run() 73 + ); 74 + } 75 + 76 + c.set("user", { id: row.id, email: row.email, name: row.name, avatar_url: row.avatar_url }); 77 + await next(); 78 + };
+36
src/worker/lib/users.ts
··· 1 + import { uid } from "./util"; 2 + 3 + interface AllowedUser { 4 + email: string; 5 + name: string; 6 + } 7 + 8 + export function allowedUser(env: Env, email: string): AllowedUser | undefined { 9 + const list = env.ALLOWED_USERS as unknown as AllowedUser[]; 10 + return list.find((u) => u.email.toLowerCase() === email.toLowerCase()); 11 + } 12 + 13 + export interface UserRow { 14 + id: string; 15 + email: string; 16 + name: string; 17 + avatar_url: string | null; 18 + google_sub: string | null; 19 + } 20 + 21 + /** Find-or-create a user row for an allowlisted email. Returns null if not allowlisted. */ 22 + export async function ensureUser(env: Env, email: string): Promise<UserRow | null> { 23 + const allowed = allowedUser(env, email); 24 + if (!allowed) return null; 25 + 26 + const existing = await env.DB.prepare("SELECT * FROM users WHERE email = ?") 27 + .bind(allowed.email) 28 + .first<UserRow>(); 29 + if (existing) return existing; 30 + 31 + const id = uid(); 32 + await env.DB.prepare("INSERT INTO users (id, email, name) VALUES (?, ?, ?)") 33 + .bind(id, allowed.email, allowed.name) 34 + .run(); 35 + return { id, email: allowed.email, name: allowed.name, avatar_url: null, google_sub: null }; 36 + }
+34
src/worker/lib/util.ts
··· 1 + export function uid(): string { 2 + return crypto.randomUUID(); 3 + } 4 + 5 + export function b64url(bytes: Uint8Array | ArrayBuffer): string { 6 + const arr = bytes instanceof ArrayBuffer ? new Uint8Array(bytes) : bytes; 7 + let bin = ""; 8 + for (const b of arr) bin += String.fromCharCode(b); 9 + return btoa(bin).replace(/\+/g, "-").replace(/\//g, "_").replace(/=+$/, ""); 10 + } 11 + 12 + export function b64urlDecode(s: string): Uint8Array<ArrayBuffer> { 13 + const bin = atob(s.replace(/-/g, "+").replace(/_/g, "/")); 14 + const arr = new Uint8Array(bin.length); 15 + for (let i = 0; i < bin.length; i++) arr[i] = bin.charCodeAt(i); 16 + return arr; 17 + } 18 + 19 + export function utf8Bytes(s: string): Uint8Array<ArrayBuffer> { 20 + return new TextEncoder().encode(s) as Uint8Array<ArrayBuffer>; 21 + } 22 + 23 + export function randomToken(): string { 24 + return b64url(crypto.getRandomValues(new Uint8Array(32))); 25 + } 26 + 27 + export async function sha256hex(s: string): Promise<string> { 28 + const digest = await crypto.subtle.digest("SHA-256", new TextEncoder().encode(s)); 29 + return [...new Uint8Array(digest)].map((b) => b.toString(16).padStart(2, "0")).join(""); 30 + } 31 + 32 + export function now(): number { 33 + return Math.floor(Date.now() / 1000); 34 + }
+282
src/worker/routes/auth.ts
··· 1 + import { Hono } from "hono"; 2 + import { getCookie, setCookie, deleteCookie } from "hono/cookie"; 3 + import * as arctic from "arctic"; 4 + import { 5 + generateRegistrationOptions, 6 + verifyRegistrationResponse, 7 + generateAuthenticationOptions, 8 + verifyAuthenticationResponse, 9 + type RegistrationResponseJSON, 10 + type AuthenticationResponseJSON, 11 + } from "@simplewebauthn/server"; 12 + import { createSession, destroySession, requireAuth, type AppEnv } from "../lib/session"; 13 + import { allowedUser, ensureUser } from "../lib/users"; 14 + import { b64url, b64urlDecode, now, uid, utf8Bytes } from "../lib/util"; 15 + 16 + const RP_NAME = "Aniverse"; 17 + const CHALLENGE_TTL = 60 * 5; 18 + 19 + export const auth = new Hono<AppEnv>(); 20 + 21 + function origin(url: string): { origin: string; hostname: string; https: boolean } { 22 + const u = new URL(url); 23 + return { origin: u.origin, hostname: u.hostname, https: u.protocol === "https:" }; 24 + } 25 + 26 + // ---------- Google OAuth (Anita) ---------- 27 + 28 + function googleClient(c: { env: Env; req: { url: string } }): arctic.Google { 29 + return new arctic.Google( 30 + c.env.GOOGLE_OAUTH_CLIENT_ID, 31 + c.env.GOOGLE_OAUTH_CLIENT_SECRET, 32 + `${origin(c.req.url).origin}/api/auth/google/callback` 33 + ); 34 + } 35 + 36 + auth.get("/google", async (c) => { 37 + if (!c.env.GOOGLE_OAUTH_CLIENT_ID) { 38 + return c.redirect("/login?error=google_not_configured"); 39 + } 40 + const state = arctic.generateState(); 41 + const codeVerifier = arctic.generateCodeVerifier(); 42 + const url = googleClient(c).createAuthorizationURL(state, codeVerifier, [ 43 + "openid", 44 + "profile", 45 + "email", 46 + ]); 47 + const https = origin(c.req.url).https; 48 + for (const [name, value] of [ 49 + ["g_state", state], 50 + ["g_verifier", codeVerifier], 51 + ] as const) { 52 + setCookie(c, name, value, { 53 + httpOnly: true, 54 + secure: https, 55 + sameSite: "Lax", 56 + path: "/", 57 + maxAge: 600, 58 + }); 59 + } 60 + return c.redirect(url.toString()); 61 + }); 62 + 63 + auth.get("/google/callback", async (c) => { 64 + const code = c.req.query("code"); 65 + const state = c.req.query("state"); 66 + const storedState = getCookie(c, "g_state"); 67 + const verifier = getCookie(c, "g_verifier"); 68 + deleteCookie(c, "g_state", { path: "/" }); 69 + deleteCookie(c, "g_verifier", { path: "/" }); 70 + 71 + if (!code || !state || !storedState || !verifier || state !== storedState) { 72 + return c.redirect("/login?error=oauth_failed"); 73 + } 74 + 75 + let claims: { sub: string; email?: string; email_verified?: boolean; name?: string; picture?: string }; 76 + try { 77 + const tokens = await googleClient(c).validateAuthorizationCode(code, verifier); 78 + claims = arctic.decodeIdToken(tokens.idToken()) as typeof claims; 79 + } catch (e) { 80 + console.error("google oauth exchange failed", e); 81 + return c.redirect("/login?error=oauth_failed"); 82 + } 83 + 84 + if (!claims.email || claims.email_verified === false) { 85 + return c.redirect("/login?error=oauth_failed"); 86 + } 87 + const user = await ensureUser(c.env, claims.email); 88 + if (!user) { 89 + return c.redirect("/login?error=not_invited"); 90 + } 91 + 92 + await c.env.DB.prepare("UPDATE users SET google_sub = ?, avatar_url = ? WHERE id = ?") 93 + .bind(claims.sub, claims.picture ?? null, user.id) 94 + .run(); 95 + await createSession(c, user.id); 96 + return c.redirect("/"); 97 + }); 98 + 99 + // ---------- Passkeys (Anirudh) ---------- 100 + 101 + async function saveChallenge(env: Env, challenge: string, kind: "register" | "auth", userId?: string) { 102 + const id = uid(); 103 + await env.DB.prepare( 104 + "INSERT INTO webauthn_challenges (id, challenge, kind, user_id, expires_at) VALUES (?, ?, ?, ?, ?)" 105 + ) 106 + .bind(id, challenge, kind, userId ?? null, now() + CHALLENGE_TTL) 107 + .run(); 108 + return id; 109 + } 110 + 111 + async function takeChallenge(env: Env, id: string, kind: "register" | "auth") { 112 + const row = await env.DB.prepare( 113 + "SELECT challenge, user_id, expires_at FROM webauthn_challenges WHERE id = ? AND kind = ?" 114 + ) 115 + .bind(id, kind) 116 + .first<{ challenge: string; user_id: string | null; expires_at: number }>(); 117 + await env.DB.prepare("DELETE FROM webauthn_challenges WHERE id = ? OR expires_at < ?") 118 + .bind(id, now()) 119 + .run(); 120 + if (!row || row.expires_at < now()) return null; 121 + return row; 122 + } 123 + 124 + // Enrollment is gated by SETUP_SECRET — visit /setup?key=... once per device. 125 + auth.post("/passkey/register-options", async (c) => { 126 + const { setupKey, email } = await c.req.json<{ setupKey: string; email: string }>(); 127 + if (!c.env.SETUP_SECRET || setupKey !== c.env.SETUP_SECRET) { 128 + return c.json({ error: "bad setup key" }, 403); 129 + } 130 + if (!allowedUser(c.env, email)) return c.json({ error: "not_invited" }, 403); 131 + const user = await ensureUser(c.env, email); 132 + if (!user) return c.json({ error: "not_invited" }, 403); 133 + 134 + const existing = await c.env.DB.prepare( 135 + "SELECT id, transports FROM webauthn_credentials WHERE user_id = ?" 136 + ) 137 + .bind(user.id) 138 + .all<{ id: string; transports: string | null }>(); 139 + 140 + const options = await generateRegistrationOptions({ 141 + rpName: RP_NAME, 142 + rpID: origin(c.req.url).hostname, 143 + userID: utf8Bytes(user.id), 144 + userName: user.email, 145 + userDisplayName: user.name, 146 + attestationType: "none", 147 + excludeCredentials: existing.results.map((cred) => ({ 148 + id: cred.id, 149 + transports: cred.transports ? JSON.parse(cred.transports) : undefined, 150 + })), 151 + authenticatorSelection: { 152 + residentKey: "required", 153 + userVerification: "preferred", 154 + }, 155 + }); 156 + 157 + const challengeId = await saveChallenge(c.env, options.challenge, "register", user.id); 158 + return c.json({ options, challengeId }); 159 + }); 160 + 161 + auth.post("/passkey/register-verify", async (c) => { 162 + const { challengeId, credential } = await c.req.json<{ 163 + challengeId: string; 164 + credential: RegistrationResponseJSON; 165 + }>(); 166 + const stored = await takeChallenge(c.env, challengeId, "register"); 167 + if (!stored || !stored.user_id) return c.json({ error: "challenge expired" }, 400); 168 + 169 + const { origin: expectedOrigin, hostname } = origin(c.req.url); 170 + const verification = await verifyRegistrationResponse({ 171 + response: credential, 172 + expectedChallenge: stored.challenge, 173 + expectedOrigin, 174 + expectedRPID: hostname, 175 + // Matches userVerification: "preferred" — password-manager authenticators 176 + // may report the user as present but not re-verified (no biometric/PIN). 177 + requireUserVerification: false, 178 + }); 179 + if (!verification.verified || !verification.registrationInfo) { 180 + return c.json({ error: "verification failed" }, 400); 181 + } 182 + 183 + const info = verification.registrationInfo.credential; 184 + await c.env.DB.prepare( 185 + "INSERT INTO webauthn_credentials (id, user_id, public_key, counter, transports) VALUES (?, ?, ?, ?, ?)" 186 + ) 187 + .bind( 188 + info.id, 189 + stored.user_id, 190 + b64url(info.publicKey), 191 + info.counter, 192 + JSON.stringify(info.transports ?? []) 193 + ) 194 + .run(); 195 + 196 + await createSession(c, stored.user_id); 197 + return c.json({ ok: true }); 198 + }); 199 + 200 + auth.post("/passkey/login-options", async (c) => { 201 + const options = await generateAuthenticationOptions({ 202 + rpID: origin(c.req.url).hostname, 203 + userVerification: "preferred", 204 + }); 205 + const challengeId = await saveChallenge(c.env, options.challenge, "auth"); 206 + return c.json({ options, challengeId }); 207 + }); 208 + 209 + auth.post("/passkey/login-verify", async (c) => { 210 + const { challengeId, credential } = await c.req.json<{ 211 + challengeId: string; 212 + credential: AuthenticationResponseJSON; 213 + }>(); 214 + const stored = await takeChallenge(c.env, challengeId, "auth"); 215 + if (!stored) return c.json({ error: "challenge expired" }, 400); 216 + 217 + const cred = await c.env.DB.prepare("SELECT * FROM webauthn_credentials WHERE id = ?") 218 + .bind(credential.id) 219 + .first<{ id: string; user_id: string; public_key: string; counter: number; transports: string | null }>(); 220 + if (!cred) return c.json({ error: "unknown credential" }, 400); 221 + 222 + const { origin: expectedOrigin, hostname } = origin(c.req.url); 223 + const verification = await verifyAuthenticationResponse({ 224 + response: credential, 225 + expectedChallenge: stored.challenge, 226 + expectedOrigin, 227 + expectedRPID: hostname, 228 + credential: { 229 + id: cred.id, 230 + publicKey: b64urlDecode(cred.public_key), 231 + counter: cred.counter, 232 + transports: cred.transports ? JSON.parse(cred.transports) : undefined, 233 + }, 234 + requireUserVerification: false, 235 + }); 236 + if (!verification.verified) return c.json({ error: "verification failed" }, 400); 237 + 238 + await c.env.DB.prepare("UPDATE webauthn_credentials SET counter = ? WHERE id = ?") 239 + .bind(verification.authenticationInfo.newCounter, cred.id) 240 + .run(); 241 + await createSession(c, cred.user_id); 242 + return c.json({ ok: true }); 243 + }); 244 + 245 + // ---------- Dev-only password login ---------- 246 + // Active only when DEV_PASSWORD is set (.dev.vars) AND the request is to 247 + // localhost, so it is inert in production even if the var leaks there. 248 + 249 + function devLoginEnabled(c: { env: Env; req: { url: string } }): boolean { 250 + const host = origin(c.req.url).hostname; 251 + return !!c.env.DEV_PASSWORD && (host === "localhost" || host === "127.0.0.1"); 252 + } 253 + 254 + auth.get("/dev", (c) => { 255 + if (!devLoginEnabled(c)) return c.json({ enabled: false }); 256 + const users = (c.env.ALLOWED_USERS as unknown as { email: string; name: string }[]).map( 257 + (u) => ({ email: u.email, name: u.name }) 258 + ); 259 + return c.json({ enabled: true, users }); 260 + }); 261 + 262 + auth.post("/dev", async (c) => { 263 + if (!devLoginEnabled(c)) return c.json({ error: "disabled" }, 404); 264 + const { password, email } = await c.req.json<{ password: string; email: string }>(); 265 + if (password !== c.env.DEV_PASSWORD) return c.json({ error: "wrong password" }, 403); 266 + const user = await ensureUser(c.env, email); 267 + if (!user) return c.json({ error: "not_invited" }, 403); 268 + await createSession(c, user.id); 269 + return c.json({ ok: true }); 270 + }); 271 + 272 + // ---------- Session ---------- 273 + 274 + auth.get("/me", requireAuth, (c) => { 275 + const u = c.var.user; 276 + return c.json({ user: { id: u.id, email: u.email, name: u.name, avatarUrl: u.avatar_url } }); 277 + }); 278 + 279 + auth.post("/logout", async (c) => { 280 + await destroySession(c); 281 + return c.json({ ok: true }); 282 + });
+83
src/worker/routes/img.ts
··· 1 + import { Hono } from "hono"; 2 + import { requireAuth, type AppEnv } from "../lib/session"; 3 + 4 + export const img = new Hono<AppEnv>(); 5 + 6 + const VARIANTS: Record<string, { width: number; height?: number; fit: "cover" | "scale-down" }> = { 7 + thumb: { width: 512, height: 512, fit: "cover" }, 8 + feed: { width: 1280, fit: "scale-down" }, 9 + full: { width: 2560, fit: "scale-down" }, 10 + }; 11 + 12 + const CACHE = "private, max-age=31536000, immutable"; 13 + 14 + // Degrees needed to upright an image for each EXIF orientation value. 15 + // (5 and 7 also involve a mirror flip, which we ignore — vanishingly rare.) 16 + const EXIF_ROTATE: Record<number, 90 | 180 | 270> = { 3: 180, 5: 90, 6: 90, 7: 270, 8: 270 }; 17 + 18 + img.get("/:photoId/:variant", requireAuth, async (c) => { 19 + const { photoId, variant } = c.req.param(); 20 + 21 + const photo = await c.env.DB.prepare( 22 + "SELECT r2_key, mime, filename, orientation FROM photos WHERE id = ?" 23 + ) 24 + .bind(photoId) 25 + .first<{ r2_key: string; mime: string; filename: string | null; orientation: number }>(); 26 + if (!photo) return c.text("not found", 404); 27 + 28 + // Full-quality original, for downloading/archiving. 29 + if (variant === "original") { 30 + const obj = await c.env.PHOTOS.get(photo.r2_key); 31 + if (!obj) return c.text("not found", 404); 32 + const headers: Record<string, string> = { "content-type": photo.mime, "cache-control": CACHE }; 33 + if (photo.filename) headers["content-disposition"] = `inline; filename="${photo.filename}"`; 34 + return new Response(obj.body, { headers }); 35 + } 36 + 37 + const transform = VARIANTS[variant]; 38 + if (!transform) return c.text("unknown variant", 404); 39 + 40 + // Serve a previously generated variant straight from R2. 41 + const variantKey = `variants/${photoId}/${variant}.webp`; 42 + const cached = await c.env.PHOTOS.get(variantKey); 43 + if (cached) { 44 + return new Response(cached.body, { 45 + headers: { "content-type": "image/webp", "cache-control": CACHE }, 46 + }); 47 + } 48 + 49 + const original = await c.env.PHOTOS.get(photo.r2_key); 50 + if (!original) return c.text("not found", 404); 51 + 52 + try { 53 + // Production Cloudflare Images auto-orients from EXIF before transforming. 54 + // The local dev simulator (sharp-based) does not, so compensate explicitly 55 + // in local dev only — adding rotate in production would double-rotate. 56 + const hostname = new URL(c.req.url).hostname; 57 + const isLocalDev = hostname === "localhost" || hostname === "127.0.0.1"; 58 + let input = c.env.IMAGES.input(original.body); 59 + const uprightRotation = EXIF_ROTATE[photo.orientation]; 60 + if (isLocalDev && uprightRotation) { 61 + input = input.transform({ rotate: uprightRotation }); 62 + } 63 + const result = await input 64 + .transform(transform) 65 + .output({ format: "image/webp", quality: 82 }); 66 + const bytes = await new Response(result.image()).arrayBuffer(); 67 + // Persist so each variant is transformed exactly once (binding calls bill per call). 68 + c.executionCtx.waitUntil( 69 + c.env.PHOTOS.put(variantKey, bytes, { httpMetadata: { contentType: "image/webp" } }) 70 + ); 71 + return new Response(bytes, { 72 + headers: { "content-type": "image/webp", "cache-control": CACHE }, 73 + }); 74 + } catch (e) { 75 + // Transform failed (e.g. unsupported input) — serve the original as-is. 76 + console.error("image transform failed", photoId, e); 77 + const fresh = await c.env.PHOTOS.get(photo.r2_key); 78 + if (!fresh) return c.text("not found", 404); 79 + return new Response(fresh.body, { 80 + headers: { "content-type": photo.mime, "cache-control": CACHE }, 81 + }); 82 + } 83 + });
+138
src/worker/routes/places.ts
··· 1 + import { Hono } from "hono"; 2 + import { requireAuth, type AppEnv } from "../lib/session"; 3 + import { uid } from "../lib/util"; 4 + 5 + export const places = new Hono<AppEnv>(); 6 + 7 + places.use("*", requireAuth); 8 + 9 + export interface LocationRow { 10 + id: string; 11 + google_place_id: string; 12 + name: string; 13 + address: string | null; 14 + lat: number | null; 15 + lng: number | null; 16 + } 17 + 18 + // Autocomplete-as-you-type. `session` groups keystrokes + the eventual 19 + // details call into one billed Places session. 20 + places.get("/autocomplete", async (c) => { 21 + const q = c.req.query("q")?.trim(); 22 + const session = c.req.query("session"); 23 + if (!q) return c.json({ suggestions: [] }); 24 + if (!c.env.GOOGLE_MAPS_API_KEY) return c.json({ error: "places_not_configured" }, 501); 25 + 26 + const res = await fetch("https://places.googleapis.com/v1/places:autocomplete", { 27 + method: "POST", 28 + headers: { 29 + "content-type": "application/json", 30 + "X-Goog-Api-Key": c.env.GOOGLE_MAPS_API_KEY, 31 + }, 32 + body: JSON.stringify({ input: q, sessionToken: session }), 33 + }); 34 + if (!res.ok) { 35 + console.error("places autocomplete failed", res.status, await res.text()); 36 + return c.json({ error: "places_failed" }, 502); 37 + } 38 + const data = (await res.json()) as { 39 + suggestions?: { 40 + placePrediction?: { 41 + placeId: string; 42 + structuredFormat?: { 43 + mainText?: { text?: string }; 44 + secondaryText?: { text?: string }; 45 + }; 46 + text?: { text?: string }; 47 + }; 48 + }[]; 49 + }; 50 + const suggestions = (data.suggestions ?? []) 51 + .map((s) => s.placePrediction) 52 + .filter((p) => !!p) 53 + .map((p) => ({ 54 + placeId: p.placeId, 55 + name: p.structuredFormat?.mainText?.text ?? p.text?.text ?? "", 56 + address: p.structuredFormat?.secondaryText?.text ?? "", 57 + })); 58 + return c.json({ suggestions }); 59 + }); 60 + 61 + // Resolve a chosen suggestion to a cached `locations` row (fetches lat/lng once). 62 + places.post("/select", async (c) => { 63 + const { placeId, session } = await c.req.json<{ placeId: string; session?: string }>(); 64 + if (!placeId) return c.json({ error: "placeId required" }, 400); 65 + 66 + const existing = await c.env.DB.prepare("SELECT * FROM locations WHERE google_place_id = ?") 67 + .bind(placeId) 68 + .first<LocationRow>(); 69 + if (existing) return c.json({ location: existing }); 70 + 71 + if (!c.env.GOOGLE_MAPS_API_KEY) return c.json({ error: "places_not_configured" }, 501); 72 + const url = new URL(`https://places.googleapis.com/v1/places/${encodeURIComponent(placeId)}`); 73 + if (session) url.searchParams.set("sessionToken", session); 74 + const res = await fetch(url, { 75 + headers: { 76 + "X-Goog-Api-Key": c.env.GOOGLE_MAPS_API_KEY, 77 + "X-Goog-FieldMask": "id,displayName,formattedAddress,location", 78 + }, 79 + }); 80 + if (!res.ok) { 81 + console.error("place details failed", res.status, await res.text()); 82 + return c.json({ error: "places_failed" }, 502); 83 + } 84 + const place = (await res.json()) as { 85 + id: string; 86 + displayName?: { text?: string }; 87 + formattedAddress?: string; 88 + location?: { latitude?: number; longitude?: number }; 89 + }; 90 + 91 + const location: LocationRow = { 92 + id: uid(), 93 + google_place_id: place.id, 94 + name: place.displayName?.text ?? "Unknown place", 95 + address: place.formattedAddress ?? null, 96 + lat: place.location?.latitude ?? null, 97 + lng: place.location?.longitude ?? null, 98 + }; 99 + const row = await c.env.DB.prepare( 100 + `INSERT INTO locations (id, google_place_id, name, address, lat, lng) 101 + VALUES (?, ?, ?, ?, ?, ?) 102 + ON CONFLICT (google_place_id) DO UPDATE SET name = excluded.name, address = excluded.address 103 + RETURNING *` 104 + ) 105 + .bind(location.id, location.google_place_id, location.name, location.address, location.lat, location.lng) 106 + .first<LocationRow>(); 107 + return c.json({ location: row }); 108 + }); 109 + 110 + // Reverse geocode EXIF GPS into a one-tap location suggestion. 111 + places.get("/reverse", async (c) => { 112 + const lat = c.req.query("lat"); 113 + const lng = c.req.query("lng"); 114 + if (!lat || !lng) return c.json({ error: "lat/lng required" }, 400); 115 + if (!c.env.GOOGLE_MAPS_API_KEY) return c.json({ error: "places_not_configured" }, 501); 116 + 117 + const url = new URL("https://maps.googleapis.com/maps/api/geocode/json"); 118 + url.searchParams.set("latlng", `${lat},${lng}`); 119 + url.searchParams.set("key", c.env.GOOGLE_MAPS_API_KEY); 120 + url.searchParams.set( 121 + "result_type", 122 + "point_of_interest|park|premise|neighborhood|sublocality|locality" 123 + ); 124 + const res = await fetch(url); 125 + if (!res.ok) return c.json({ error: "geocode_failed" }, 502); 126 + const data = (await res.json()) as { 127 + results?: { place_id: string; formatted_address: string; address_components?: { long_name: string }[] }[]; 128 + }; 129 + const first = data.results?.[0]; 130 + if (!first) return c.json({ suggestion: null }); 131 + return c.json({ 132 + suggestion: { 133 + placeId: first.place_id, 134 + name: first.address_components?.[0]?.long_name ?? first.formatted_address, 135 + address: first.formatted_address, 136 + }, 137 + }); 138 + });
+331
src/worker/routes/posts.ts
··· 1 + import { Hono } from "hono"; 2 + import { requireAuth, type AppEnv } from "../lib/session"; 3 + import { uid } from "../lib/util"; 4 + 5 + export const posts = new Hono<AppEnv>(); 6 + 7 + posts.use("*", requireAuth); 8 + 9 + interface LocationOut { 10 + id: string; 11 + name: string; 12 + address: string | null; 13 + lat: number | null; 14 + lng: number | null; 15 + } 16 + 17 + // Keep in sync with EMOJIS in src/web/components/PostCard.tsx 18 + const EMOJIS = new Set(["❤️", "😂", "😮", "🥹", "🔥", "👍"]); 19 + 20 + interface CommentOut { 21 + id: string; 22 + body: string; 23 + createdAt: number; 24 + author: { id: string; name: string; avatarUrl: string | null }; 25 + } 26 + 27 + interface ReactionOut { 28 + emoji: string; 29 + count: number; 30 + mine: boolean; 31 + } 32 + 33 + interface PhotoOut { 34 + id: string; 35 + width: number | null; 36 + height: number | null; 37 + takenAt: number | null; 38 + location: LocationOut | null; 39 + } 40 + 41 + interface PostOut { 42 + id: string; 43 + caption: string; 44 + createdAt: number; 45 + author: { id: string; name: string; avatarUrl: string | null }; 46 + location: LocationOut | null; 47 + photos: PhotoOut[]; 48 + comments: CommentOut[]; 49 + reactions: ReactionOut[]; 50 + } 51 + 52 + const PAGE_SIZE = 10; 53 + 54 + posts.post("/", async (c) => { 55 + const body = await c.req.json<{ 56 + caption?: string; 57 + locationId?: string | null; 58 + photos: { id: string; locationId?: string | null }[]; 59 + }>(); 60 + 61 + if (!body.photos?.length) return c.json({ error: "a post needs at least one photo" }, 400); 62 + if (body.photos.length > 20) return c.json({ error: "20 photos max" }, 400); 63 + 64 + // Every photo must be an unattached upload owned by the author. 65 + const ids = body.photos.map((p) => p.id); 66 + const marks = ids.map(() => "?").join(","); 67 + const owned = await c.env.DB.prepare( 68 + `SELECT id FROM photos WHERE id IN (${marks}) AND uploader_id = ? AND post_id IS NULL` 69 + ) 70 + .bind(...ids, c.var.user.id) 71 + .all<{ id: string }>(); 72 + if (owned.results.length !== ids.length) { 73 + return c.json({ error: "unknown or already-used photo" }, 400); 74 + } 75 + 76 + const postId = uid(); 77 + const statements = [ 78 + // Millisecond precision so back-to-back posts never tie on the feed cursor. 79 + c.env.DB.prepare( 80 + "INSERT INTO posts (id, author_id, caption, location_id, created_at) VALUES (?, ?, ?, ?, ?)" 81 + ).bind(postId, c.var.user.id, body.caption?.trim() ?? "", body.locationId ?? null, Date.now()), 82 + ...body.photos.map((p, i) => 83 + c.env.DB.prepare( 84 + "UPDATE photos SET post_id = ?, position = ?, location_id = COALESCE(?, location_id) WHERE id = ?" 85 + ).bind(postId, i, p.locationId ?? null, p.id) 86 + ), 87 + ]; 88 + await c.env.DB.batch(statements); 89 + 90 + return c.json({ id: postId }, 201); 91 + }); 92 + 93 + posts.get("/feed", async (c) => { 94 + const limit = PAGE_SIZE; 95 + const cursor = c.req.query("cursor"); // "<created_at>_<id>" 96 + let where = ""; 97 + const binds: (string | number)[] = []; 98 + if (cursor) { 99 + const [ts, id] = cursor.split("_"); 100 + where = "WHERE (p.created_at, p.id) < (?, ?)"; 101 + binds.push(Number(ts), id ?? ""); 102 + } 103 + 104 + const rows = await c.env.DB.prepare( 105 + `SELECT p.id, p.caption, p.created_at, 106 + u.id AS author_id, u.name AS author_name, u.avatar_url AS author_avatar, 107 + l.id AS loc_id, l.name AS loc_name, l.address AS loc_address, l.lat AS loc_lat, l.lng AS loc_lng 108 + FROM posts p 109 + JOIN users u ON u.id = p.author_id 110 + LEFT JOIN locations l ON l.id = p.location_id 111 + ${where} 112 + ORDER BY p.created_at DESC, p.id DESC 113 + LIMIT ${limit + 1}` 114 + ) 115 + .bind(...binds) 116 + .all<{ 117 + id: string; 118 + caption: string; 119 + created_at: number; 120 + author_id: string; 121 + author_name: string; 122 + author_avatar: string | null; 123 + loc_id: string | null; 124 + loc_name: string | null; 125 + loc_address: string | null; 126 + loc_lat: number | null; 127 + loc_lng: number | null; 128 + }>(); 129 + 130 + const page = rows.results.slice(0, limit); 131 + const postIds = page.map((r) => r.id); 132 + const photosByPost = new Map<string, PhotoOut[]>(); 133 + const commentsByPost = new Map<string, CommentOut[]>(); 134 + const reactionsByPost = new Map<string, ReactionOut[]>(); 135 + if (postIds.length) { 136 + const marks = postIds.map(() => "?").join(","); 137 + 138 + const commentRows = await c.env.DB.prepare( 139 + `SELECT cm.id, cm.post_id, cm.body, cm.created_at, 140 + u.id AS author_id, u.name AS author_name, u.avatar_url AS author_avatar 141 + FROM comments cm JOIN users u ON u.id = cm.author_id 142 + WHERE cm.post_id IN (${marks}) 143 + ORDER BY cm.created_at, cm.id` 144 + ) 145 + .bind(...postIds) 146 + .all<{ 147 + id: string; 148 + post_id: string; 149 + body: string; 150 + created_at: number; 151 + author_id: string; 152 + author_name: string; 153 + author_avatar: string | null; 154 + }>(); 155 + for (const cm of commentRows.results) { 156 + const list = commentsByPost.get(cm.post_id) ?? []; 157 + list.push({ 158 + id: cm.id, 159 + body: cm.body, 160 + createdAt: cm.created_at, 161 + author: { id: cm.author_id, name: cm.author_name, avatarUrl: cm.author_avatar }, 162 + }); 163 + commentsByPost.set(cm.post_id, list); 164 + } 165 + 166 + const reactionRows = await c.env.DB.prepare( 167 + `SELECT post_id, emoji, COUNT(*) AS count, 168 + MAX(CASE WHEN user_id = ? THEN 1 ELSE 0 END) AS mine 169 + FROM reactions 170 + WHERE post_id IN (${marks}) 171 + GROUP BY post_id, emoji 172 + ORDER BY MIN(created_at)` 173 + ) 174 + .bind(c.var.user.id, ...postIds) 175 + .all<{ post_id: string; emoji: string; count: number; mine: number }>(); 176 + for (const r of reactionRows.results) { 177 + const list = reactionsByPost.get(r.post_id) ?? []; 178 + list.push({ emoji: r.emoji, count: r.count, mine: r.mine === 1 }); 179 + reactionsByPost.set(r.post_id, list); 180 + } 181 + const photoRows = await c.env.DB.prepare( 182 + `SELECT ph.id, ph.post_id, ph.width, ph.height, ph.taken_at, 183 + l.id AS loc_id, l.name AS loc_name, l.address AS loc_address, l.lat AS loc_lat, l.lng AS loc_lng 184 + FROM photos ph 185 + LEFT JOIN locations l ON l.id = ph.location_id 186 + WHERE ph.post_id IN (${marks}) 187 + ORDER BY ph.post_id, ph.position` 188 + ) 189 + .bind(...postIds) 190 + .all<{ 191 + id: string; 192 + post_id: string; 193 + width: number | null; 194 + height: number | null; 195 + taken_at: number | null; 196 + loc_id: string | null; 197 + loc_name: string | null; 198 + loc_address: string | null; 199 + loc_lat: number | null; 200 + loc_lng: number | null; 201 + }>(); 202 + for (const ph of photoRows.results) { 203 + const list = photosByPost.get(ph.post_id) ?? []; 204 + list.push({ 205 + id: ph.id, 206 + width: ph.width, 207 + height: ph.height, 208 + takenAt: ph.taken_at, 209 + location: ph.loc_id 210 + ? { id: ph.loc_id, name: ph.loc_name!, address: ph.loc_address, lat: ph.loc_lat, lng: ph.loc_lng } 211 + : null, 212 + }); 213 + photosByPost.set(ph.post_id, list); 214 + } 215 + } 216 + 217 + const out: PostOut[] = page.map((r) => ({ 218 + id: r.id, 219 + caption: r.caption, 220 + createdAt: Math.floor(r.created_at / 1000), // API speaks unix seconds 221 + 222 + author: { id: r.author_id, name: r.author_name, avatarUrl: r.author_avatar }, 223 + location: r.loc_id 224 + ? { id: r.loc_id, name: r.loc_name!, address: r.loc_address, lat: r.loc_lat, lng: r.loc_lng } 225 + : null, 226 + photos: photosByPost.get(r.id) ?? [], 227 + comments: commentsByPost.get(r.id) ?? [], 228 + reactions: reactionsByPost.get(r.id) ?? [], 229 + })); 230 + 231 + const hasMore = rows.results.length > limit; 232 + const last = page[page.length - 1]; 233 + return c.json({ 234 + posts: out, 235 + nextCursor: hasMore && last ? `${last.created_at}_${last.id}` : null, 236 + }); 237 + }); 238 + 239 + posts.post("/:id/comments", async (c) => { 240 + const postId = c.req.param("id"); 241 + const { body } = await c.req.json<{ body: string }>(); 242 + const text = body?.trim(); 243 + if (!text) return c.json({ error: "empty comment" }, 400); 244 + if (text.length > 2000) return c.json({ error: "comment too long" }, 400); 245 + 246 + const post = await c.env.DB.prepare("SELECT id FROM posts WHERE id = ?").bind(postId).first(); 247 + if (!post) return c.json({ error: "not found" }, 404); 248 + 249 + const id = uid(); 250 + const createdAt = Math.floor(Date.now() / 1000); 251 + await c.env.DB.prepare( 252 + "INSERT INTO comments (id, post_id, author_id, body, created_at) VALUES (?, ?, ?, ?, ?)" 253 + ) 254 + .bind(id, postId, c.var.user.id, text, createdAt) 255 + .run(); 256 + 257 + const u = c.var.user; 258 + const comment: CommentOut = { 259 + id, 260 + body: text, 261 + createdAt, 262 + author: { id: u.id, name: u.name, avatarUrl: u.avatar_url }, 263 + }; 264 + return c.json({ comment }, 201); 265 + }); 266 + 267 + posts.delete("/:id/comments/:commentId", async (c) => { 268 + const { commentId } = c.req.param(); 269 + const comment = await c.env.DB.prepare("SELECT author_id FROM comments WHERE id = ?") 270 + .bind(commentId) 271 + .first<{ author_id: string }>(); 272 + if (!comment) return c.json({ error: "not found" }, 404); 273 + if (comment.author_id !== c.var.user.id) return c.json({ error: "not yours" }, 403); 274 + await c.env.DB.prepare("DELETE FROM comments WHERE id = ?").bind(commentId).run(); 275 + return c.json({ ok: true }); 276 + }); 277 + 278 + // Explicit on/off (not a blind toggle) so optimistic UI can't drift. 279 + posts.post("/:id/react", async (c) => { 280 + const postId = c.req.param("id"); 281 + const { emoji, on } = await c.req.json<{ emoji: string; on: boolean }>(); 282 + if (!EMOJIS.has(emoji)) return c.json({ error: "unknown emoji" }, 400); 283 + 284 + const post = await c.env.DB.prepare("SELECT id FROM posts WHERE id = ?").bind(postId).first(); 285 + if (!post) return c.json({ error: "not found" }, 404); 286 + 287 + if (on) { 288 + await c.env.DB.prepare( 289 + "INSERT OR IGNORE INTO reactions (post_id, user_id, emoji) VALUES (?, ?, ?)" 290 + ) 291 + .bind(postId, c.var.user.id, emoji) 292 + .run(); 293 + } else { 294 + await c.env.DB.prepare( 295 + "DELETE FROM reactions WHERE post_id = ? AND user_id = ? AND emoji = ?" 296 + ) 297 + .bind(postId, c.var.user.id, emoji) 298 + .run(); 299 + } 300 + return c.json({ ok: true }); 301 + }); 302 + 303 + posts.delete("/:id", async (c) => { 304 + const id = c.req.param("id"); 305 + const post = await c.env.DB.prepare("SELECT author_id FROM posts WHERE id = ?") 306 + .bind(id) 307 + .first<{ author_id: string }>(); 308 + if (!post) return c.json({ error: "not found" }, 404); 309 + if (post.author_id !== c.var.user.id) return c.json({ error: "not yours" }, 403); 310 + 311 + const photoRows = await c.env.DB.prepare("SELECT id, r2_key FROM photos WHERE post_id = ?") 312 + .bind(id) 313 + .all<{ id: string; r2_key: string }>(); 314 + 315 + await c.env.DB.batch([ 316 + c.env.DB.prepare("DELETE FROM comments WHERE post_id = ?").bind(id), 317 + c.env.DB.prepare("DELETE FROM reactions WHERE post_id = ?").bind(id), 318 + c.env.DB.prepare("DELETE FROM photos WHERE post_id = ?").bind(id), 319 + c.env.DB.prepare("DELETE FROM posts WHERE id = ?").bind(id), 320 + ]); 321 + 322 + const keys = photoRows.results.flatMap((p) => [ 323 + p.r2_key, 324 + `variants/${p.id}/thumb.webp`, 325 + `variants/${p.id}/feed.webp`, 326 + `variants/${p.id}/full.webp`, 327 + ]); 328 + if (keys.length) c.executionCtx.waitUntil(c.env.PHOTOS.delete(keys)); 329 + 330 + return c.json({ ok: true }); 331 + });
+73
src/worker/routes/uploads.ts
··· 1 + import { Hono } from "hono"; 2 + import { requireAuth, type AppEnv } from "../lib/session"; 3 + import { uid } from "../lib/util"; 4 + 5 + export const uploads = new Hono<AppEnv>(); 6 + 7 + const MAX_BYTES = 50 * 1024 * 1024; 8 + 9 + // One photo per request, raw body. EXIF-derived metadata comes in headers 10 + // (parsed client-side); dimensions are re-derived server-side when possible. 11 + uploads.post("/", requireAuth, async (c) => { 12 + const mime = c.req.header("content-type") ?? "application/octet-stream"; 13 + if (!mime.startsWith("image/")) return c.json({ error: "not an image" }, 400); 14 + const length = Number(c.req.header("content-length") ?? 0); 15 + if (length > MAX_BYTES) return c.json({ error: "too large (50MB max)" }, 413); 16 + 17 + const rawFilename = c.req.header("x-filename"); 18 + const filename = rawFilename ? decodeURIComponent(rawFilename) : null; 19 + const takenAt = c.req.header("x-taken-at"); 20 + const gpsLat = c.req.header("x-gps-lat"); 21 + const gpsLng = c.req.header("x-gps-lng"); 22 + // Client-provided dims come from createImageBitmap and are already 23 + // orientation-corrected (display dims). 24 + let width = Number(c.req.header("x-width")) || null; 25 + let height = Number(c.req.header("x-height")) || null; 26 + const rawOrientation = Number(c.req.header("x-orientation")); 27 + const orientation = rawOrientation >= 1 && rawOrientation <= 8 ? rawOrientation : 1; 28 + 29 + const id = uid(); 30 + const key = `originals/${id}`; 31 + await c.env.PHOTOS.put(key, c.req.raw.body, { 32 + httpMetadata: { contentType: mime }, 33 + customMetadata: filename ? { filename } : undefined, 34 + }); 35 + 36 + // Authoritative dimensions from the Images binding (free .info() call). 37 + // .info() reports raw pixel dims, so swap for 90°/270° EXIF orientations 38 + // (5-8) to get display dims. 39 + try { 40 + const obj = await c.env.PHOTOS.get(key); 41 + if (obj) { 42 + const info = await c.env.IMAGES.info(obj.body); 43 + if ("width" in info) { 44 + const swap = orientation >= 5; 45 + width = swap ? info.height : info.width; 46 + height = swap ? info.width : info.height; 47 + } 48 + } 49 + } catch { 50 + // Unsupported format for the binding — fall back to client-provided dims. 51 + } 52 + 53 + await c.env.DB.prepare( 54 + `INSERT INTO photos (id, uploader_id, r2_key, filename, mime, width, height, orientation, taken_at, gps_lat, gps_lng) 55 + VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)` 56 + ) 57 + .bind( 58 + id, 59 + c.var.user.id, 60 + key, 61 + filename, 62 + mime, 63 + width, 64 + height, 65 + orientation, 66 + takenAt ? Number(takenAt) : null, 67 + gpsLat ? Number(gpsLat) : null, 68 + gpsLng ? Number(gpsLng) : null 69 + ) 70 + .run(); 71 + 72 + return c.json({ id, width, height }, 201); 73 + });
+10
src/worker/secrets.d.ts
··· 1 + // Secrets are not declared in wrangler.jsonc, so `wrangler types` can't see them. 2 + // Merged into the generated global Env via declaration merging. 3 + interface Env { 4 + GOOGLE_OAUTH_CLIENT_ID: string; 5 + GOOGLE_OAUTH_CLIENT_SECRET: string; 6 + GOOGLE_MAPS_API_KEY: string; 7 + SETUP_SECRET: string; 8 + /** Local dev only (.dev.vars) — enables password login on localhost. Never set in production. */ 9 + DEV_PASSWORD?: string; 10 + }
+22
tsconfig.app.json
··· 1 + { 2 + "compilerOptions": { 3 + "composite": true, 4 + "tsBuildInfoFile": "./node_modules/.tmp/tsconfig.app.tsbuildinfo", 5 + "target": "ES2022", 6 + "lib": ["ES2022", "DOM", "DOM.Iterable"], 7 + "module": "ESNext", 8 + "moduleResolution": "bundler", 9 + "jsx": "react-jsx", 10 + "types": [], 11 + "skipLibCheck": true, 12 + "noEmit": true, 13 + "strict": true, 14 + "noUnusedLocals": true, 15 + "noUnusedParameters": true, 16 + "noFallthroughCasesInSwitch": true, 17 + "isolatedModules": true, 18 + "moduleDetection": "force", 19 + "verbatimModuleSyntax": true 20 + }, 21 + "include": ["src/web"] 22 + }
+7
tsconfig.json
··· 1 + { 2 + "files": [], 3 + "references": [ 4 + { "path": "./tsconfig.app.json" }, 5 + { "path": "./tsconfig.worker.json" } 6 + ] 7 + }
+20
tsconfig.worker.json
··· 1 + { 2 + "compilerOptions": { 3 + "composite": true, 4 + "tsBuildInfoFile": "./node_modules/.tmp/tsconfig.worker.tsbuildinfo", 5 + "target": "ES2022", 6 + "lib": ["ES2022"], 7 + "module": "ESNext", 8 + "moduleResolution": "bundler", 9 + "types": [], 10 + "skipLibCheck": true, 11 + "noEmit": true, 12 + "strict": true, 13 + "noUnusedLocals": true, 14 + "noUnusedParameters": true, 15 + "isolatedModules": true, 16 + "moduleDetection": "force", 17 + "verbatimModuleSyntax": true 18 + }, 19 + "include": ["src/worker", "worker-configuration.d.ts"] 20 + }
+59
vite.config.ts
··· 1 + import { defineConfig } from "vite"; 2 + import react from "@vitejs/plugin-react"; 3 + import tailwindcss from "@tailwindcss/vite"; 4 + import { cloudflare } from "@cloudflare/vite-plugin"; 5 + import { VitePWA } from "vite-plugin-pwa"; 6 + 7 + export default defineConfig({ 8 + plugins: [ 9 + react(), 10 + tailwindcss(), 11 + cloudflare(), 12 + VitePWA({ 13 + registerType: "autoUpdate", 14 + injectRegister: false, // registered manually in main.tsx 15 + manifest: false, // we ship our own public/manifest.webmanifest 16 + workbox: { 17 + globPatterns: ["**/*.{js,css,html,svg,png,webmanifest}"], 18 + navigateFallback: "/index.html", 19 + navigateFallbackDenylist: [/^\/api\//, /^\/img\//], 20 + runtimeCaching: [ 21 + { 22 + // Photos are immutable per URL — serve from cache forever. 23 + urlPattern: ({ url }) => url.pathname.startsWith("/img/"), 24 + handler: "CacheFirst", 25 + options: { 26 + cacheName: "aniverse-photos", 27 + expiration: { 28 + maxEntries: 1500, 29 + maxAgeSeconds: 60 * 60 * 24 * 365, 30 + purgeOnQuotaError: true, 31 + }, 32 + cacheableResponse: { statuses: [200] }, 33 + }, 34 + }, 35 + { 36 + // Feed + session: fresh when online, cached when offline. 37 + urlPattern: ({ url }) => 38 + url.pathname.startsWith("/api/posts/feed") || url.pathname === "/api/auth/me", 39 + handler: "NetworkFirst", 40 + options: { 41 + cacheName: "aniverse-api", 42 + networkTimeoutSeconds: 4, 43 + cacheableResponse: { statuses: [200] }, 44 + }, 45 + }, 46 + { 47 + // Google avatar images 48 + urlPattern: ({ url }) => url.hostname.endsWith("googleusercontent.com"), 49 + handler: "CacheFirst", 50 + options: { 51 + cacheName: "aniverse-avatars", 52 + expiration: { maxEntries: 10, maxAgeSeconds: 60 * 60 * 24 * 30 }, 53 + }, 54 + }, 55 + ], 56 + }, 57 + }), 58 + ], 59 + });
+41
wrangler.jsonc
··· 1 + { 2 + "$schema": "node_modules/wrangler/config-schema.json", 3 + "name": "aniverse", 4 + "main": "./src/worker/index.ts", 5 + "compatibility_date": "2026-07-01", 6 + "observability": { 7 + "enabled": true 8 + }, 9 + "assets": { 10 + "not_found_handling": "single-page-application", 11 + "run_worker_first": ["/api/*", "/img/*"] 12 + }, 13 + "d1_databases": [ 14 + { 15 + "binding": "DB", 16 + "database_name": "aniverse", 17 + "database_id": "ec8b7411-3e61-4937-aa43-e8b811b8a837", 18 + "migrations_dir": "./migrations" 19 + } 20 + ], 21 + "r2_buckets": [ 22 + { 23 + "binding": "PHOTOS", 24 + "bucket_name": "aniverse-photos" 25 + } 26 + ], 27 + "images": { 28 + "binding": "IMAGES" 29 + }, 30 + "vars": { 31 + // The only two people allowed in. 32 + "ALLOWED_USERS": [ 33 + { "email": "anirudh@oppiliappan.com", "name": "Anirudh" }, 34 + { "email": "anita.loutchina@gmail.com", "name": "Anita" } 35 + ] 36 + } 37 + // Secrets (set with `wrangler secret put <NAME>`, or .dev.vars locally): 38 + // GOOGLE_OAUTH_CLIENT_ID, GOOGLE_OAUTH_CLIENT_SECRET — Google Sign-In (Anita) 39 + // GOOGLE_MAPS_API_KEY — Places autocomplete + reverse geocoding 40 + // SETUP_SECRET — one-time passkey enrollment gate 41 + }