diff --git a/.clinerules/pnpm-not-npm.md b/.clinerules/pnpm-not-npm.md index c7398af..33db5dd 100644 --- a/.clinerules/pnpm-not-npm.md +++ b/.clinerules/pnpm-not-npm.md @@ -1 +1 @@ -Use pnpm to manage this project, not npm! \ No newline at end of file +Use pnpm to manage this project, not npm! diff --git a/CLAUDE.md b/CLAUDE.md index e0ff44a..54bdafd 100644 --- a/CLAUDE.md +++ b/CLAUDE.md @@ -5,18 +5,21 @@ This file provides guidance to Claude Code (claude.ai/code) when working with co ## Development Commands **Core Development:** + - `pnpm dev` - Start development server (runs custom server.ts with schedulers) - `pnpm dev:next-only` - Start Next.js only with Turbopack (no schedulers) - `pnpm build` - Build production application - `pnpm start` - Run production server **Code Quality:** + - `pnpm lint` - Run ESLint - `pnpm lint:fix` - Fix ESLint issues automatically - `pnpm format` - Format code with Prettier - `pnpm format:check` - Check formatting without fixing **Database:** + - `pnpm prisma:generate` - Generate Prisma client - `pnpm prisma:migrate` - Run database migrations - `pnpm prisma:push` - Push schema changes to database @@ -25,11 +28,13 @@ This file provides guidance to Claude Code (claude.ai/code) when working with co - `pnpm prisma:studio` - Open Prisma Studio database viewer **Testing:** + - `pnpm test` - Run tests once - `pnpm test:watch` - Run tests in watch mode - `pnpm test:coverage` - Run tests with coverage report **Markdown:** + - `pnpm lint:md` - Lint Markdown files - `pnpm lint:md:fix` - Fix Markdown linting issues @@ -38,6 +43,7 @@ This file provides guidance to Claude Code (claude.ai/code) when working with co **LiveDash-Node** is a real-time analytics dashboard for monitoring user sessions with AI-powered analysis and processing pipeline. ### Tech Stack + - **Frontend:** Next.js 15 + React 19 + TailwindCSS 4 - **Backend:** Next.js API Routes + Custom Node.js server - **Database:** PostgreSQL with Prisma ORM @@ -50,6 +56,7 @@ This file provides guidance to Claude Code (claude.ai/code) when working with co **1. Multi-Stage Processing Pipeline** The system processes user sessions through distinct stages tracked in `SessionProcessingStatus`: + - `CSV_IMPORT` - Import raw CSV data into `SessionImport` - `TRANSCRIPT_FETCH` - Fetch transcript content from URLs - `SESSION_CREATION` - Create normalized `Session` and `Message` records @@ -57,6 +64,7 @@ The system processes user sessions through distinct stages tracked in `SessionPr - `QUESTION_EXTRACTION` - Extract questions from conversations **2. Database Architecture** + - **Multi-tenant design** with `Company` as root entity - **Dual storage pattern**: Raw CSV data in `SessionImport`, processed data in `Session` - **1-to-1 relationship** between `SessionImport` and `Session` via `importId` @@ -65,11 +73,13 @@ The system processes user sessions through distinct stages tracked in `SessionPr - **Flexible AI model management** through `AIModel`, `AIModelPricing`, and `CompanyAIModel` **3. Custom Server Architecture** + - `server.ts` - Custom Next.js server with configurable scheduler initialization - Three main schedulers: CSV import, import processing, and session processing - Environment-based configuration via `lib/env.ts` **4. Key Processing Libraries** + - `lib/scheduler.ts` - CSV import scheduling - `lib/importProcessor.ts` - Raw data to Session conversion - `lib/processingScheduler.ts` - AI analysis pipeline @@ -80,18 +90,21 @@ The system processes user sessions through distinct stages tracked in `SessionPr **Environment Configuration:** Environment variables are managed through `lib/env.ts` with .env.local file support: + - Database: PostgreSQL via `DATABASE_URL` and `DATABASE_URL_DIRECT` - Authentication: `NEXTAUTH_SECRET`, `NEXTAUTH_URL` - AI Processing: `OPENAI_API_KEY` - Schedulers: `SCHEDULER_ENABLED`, various interval configurations **Key Files to Understand:** + - `prisma/schema.prisma` - Complete database schema with enums and relationships - `server.ts` - Custom server entry point - `lib/env.ts` - Environment variable management and validation - `app/` - Next.js App Router structure **Testing:** + - Uses Vitest for unit testing - Playwright for E2E testing - Test files in `tests/` directory @@ -99,16 +112,19 @@ Environment variables are managed through `lib/env.ts` with .env.local file supp ### Important Notes **Scheduler System:** + - Schedulers are optional and controlled by `SCHEDULER_ENABLED` environment variable - Use `pnpm dev:next-only` to run without schedulers for pure frontend development - Three separate schedulers handle different pipeline stages **Database Migrations:** + - Always run `pnpm prisma:generate` after schema changes - Use `pnpm prisma:migrate` for production-ready migrations - Use `pnpm prisma:push` for development schema changes **AI Processing:** + - All AI requests are tracked for cost analysis - Support for multiple AI models per company -- Time-based pricing management for accurate cost calculation \ No newline at end of file +- Time-based pricing management for accurate cost calculation diff --git a/README.md b/README.md index b9d01dc..5ec65d1 100644 --- a/README.md +++ b/README.md @@ -2,65 +2,65 @@ A real-time analytics dashboard for monitoring user sessions and interactions with interactive data visualizations and detailed metrics. -![Next.js](https://img.shields.io/badge/dynamic/regex?url=https%3A%2F%2Fraw.githubusercontent.com%2Fkjanat%2Flivedash-node%2Fmaster%2Fpackage.json&search=%22next%22%5Cs*%3A%5Cs*%22%5C%5E(%3F%3Cversion%3E%5Cd%2B%5C.%5Cd*).*%22&replace=%24%3Cversion%3E&logo=nextdotjs&label=Nextjs&color=%23000000) -![React](https://img.shields.io/badge/dynamic/regex?url=https%3A%2F%2Fraw.githubusercontent.com%2Fkjanat%2Flivedash-node%2Fmaster%2Fpackage.json&search=%22react%22%5Cs*%3A%5Cs*%22%5C%5E(%3F%3Cversion%3E%5Cd%2B%5C.%5Cd*).*%22&replace=%24%3Cversion%3E&logo=react&label=React&color=%2361DAFB) -![TypeScript](https://img.shields.io/badge/dynamic/regex?url=https%3A%2F%2Fraw.githubusercontent.com%2Fkjanat%2Flivedash-node%2Fmaster%2Fpackage.json&search=%22typescript%22%5Cs*%3A%5Cs*%22%5C%5E(%3F%3Cversion%3E%5Cd%2B%5C.%5Cd*).*%22&replace=%24%3Cversion%3E&logo=typescript&label=TypeScript&color=%233178C6) -![Prisma](https://img.shields.io/badge/dynamic/regex?url=https%3A%2F%2Fraw.githubusercontent.com%2Fkjanat%2Flivedash-node%2Fmaster%2Fpackage.json&search=%22prisma%22%5Cs*%3A%5Cs*%22%5C%5E(%3F%3Cversion%3E%5Cd%2B%5C.%5Cd*).*%22&replace=%24%3Cversion%3E&logo=prisma&label=Prisma&color=%232D3748) -![TailwindCSS](https://img.shields.io/badge/dynamic/regex?url=https%3A%2F%2Fraw.githubusercontent.com%2Fkjanat%2Flivedash-node%2Fmaster%2Fpackage.json&search=%22tailwindcss%22%5Cs*%3A%5Cs*%22%5C%5E(%3F%3Cversion%3E%5Cd%2B%5C.%5Cd*).*%22&replace=%24%3Cversion%3E&logo=tailwindcss&label=TailwindCSS&color=%2306B6D4) +![Next.js]() +![React]() +![TypeScript]() +![Prisma]() +![TailwindCSS]() ## Features -- **Real-time Session Monitoring**: Track and analyze user sessions as they happen -- **Interactive Visualizations**: Geographic maps, response time distributions, and more -- **Advanced Analytics**: Detailed metrics and insights about user behavior -- **User Management**: Secure authentication with role-based access control -- **Customizable Dashboard**: Filter and sort data based on your specific needs -- **Session Details**: In-depth analysis of individual user sessions +- **Real-time Session Monitoring**: Track and analyze user sessions as they happen +- **Interactive Visualizations**: Geographic maps, response time distributions, and more +- **Advanced Analytics**: Detailed metrics and insights about user behavior +- **User Management**: Secure authentication with role-based access control +- **Customizable Dashboard**: Filter and sort data based on your specific needs +- **Session Details**: In-depth analysis of individual user sessions ## Tech Stack -- **Frontend**: React 19, Next.js 15, TailwindCSS 4 -- **Backend**: Next.js API Routes, Node.js -- **Database**: Prisma ORM with SQLite (default), compatible with PostgreSQL -- **Authentication**: NextAuth.js -- **Visualization**: Chart.js, D3.js, React Leaflet -- **Data Processing**: Node-cron for scheduled tasks +- **Frontend**: React 19, Next.js 15, TailwindCSS 4 +- **Backend**: Next.js API Routes, Node.js +- **Database**: Prisma ORM with SQLite (default), compatible with PostgreSQL +- **Authentication**: NextAuth.js +- **Visualization**: Chart.js, D3.js, React Leaflet +- **Data Processing**: Node-cron for scheduled tasks ## Getting Started ### Prerequisites -- Node.js (LTS version recommended) -- npm or yarn +- Node.js (LTS version recommended) +- pnpm (recommended package manager) ### Installation 1. Clone this repository: - ```bash - git clone https://github.com/kjanat/livedash-node.git - cd livedash-node - ``` +```bash +git clone https://github.com/kjanat/livedash-node.git +cd livedash-node +``` 2. Install dependencies: - ```bash - npm install - ``` +```bash +pnpm install +``` 3. Set up the database: - ```bash - npm run prisma:generate - npm run prisma:migrate - npm run prisma:seed - ``` +```bash +pnpm run prisma:generate +pnpm run prisma:migrate +pnpm run prisma:seed +``` 4. Start the development server: - ```bash - npm run dev - ``` +```bash +pnpm run dev +``` 5. Open your browser and navigate to @@ -76,22 +76,22 @@ NEXTAUTH_SECRET=your-secret-here ## Project Structure -- `app/`: Next.js App Router components and pages -- `components/`: Reusable React components -- `lib/`: Utility functions and shared code -- `pages/`: API routes and server-side code -- `prisma/`: Database schema and migrations -- `public/`: Static assets -- `docs/`: Project documentation +- `app/`: Next.js App Router components and pages +- `components/`: Reusable React components +- `lib/`: Utility functions and shared code +- `pages/`: API routes and server-side code +- `prisma/`: Database schema and migrations +- `public/`: Static assets +- `docs/`: Project documentation ## Available Scripts -- `npm run dev`: Start the development server -- `npm run build`: Build the application for production -- `npm run start`: Run the production build -- `npm run lint`: Run ESLint -- `npm run format`: Format code with Prettier -- `npm run prisma:studio`: Open Prisma Studio to view database +- `pnpm run dev`: Start the development server +- `pnpm run build`: Build the application for production +- `pnpm run start`: Run the production build +- `pnpm run lint`: Run ESLint +- `pnpm run format`: Format code with Prettier +- `pnpm run prisma:studio`: Open Prisma Studio to view database ## Contributing @@ -107,9 +107,9 @@ This project is not licensed for commercial use without explicit permission. Fre ## Acknowledgments -- [Next.js](https://nextjs.org/) -- [Prisma](https://prisma.io/) -- [TailwindCSS](https://tailwindcss.com/) -- [Chart.js](https://www.chartjs.org/) -- [D3.js](https://d3js.org/) -- [React Leaflet](https://react-leaflet.js.org/) +- [Next.js](https://nextjs.org/) +- [Prisma](https://prisma.io/) +- [TailwindCSS](https://tailwindcss.com/) +- [Chart.js](https://www.chartjs.org/) +- [D3.js](https://d3js.org/) +- [React Leaflet](https://react-leaflet.js.org/) diff --git a/app/api/admin/refresh-sessions/route.ts b/app/api/admin/refresh-sessions/route.ts index fea2fdb..e2a11d0 100644 --- a/app/api/admin/refresh-sessions/route.ts +++ b/app/api/admin/refresh-sessions/route.ts @@ -37,12 +37,11 @@ export async function POST(request: NextRequest) { ); } - const company = await prisma.company.findUnique({ where: { id: companyId } }); + const company = await prisma.company.findUnique({ + where: { id: companyId }, + }); if (!company) { - return NextResponse.json( - { error: "Company not found" }, - { status: 404 } - ); + return NextResponse.json({ error: "Company not found" }, { status: 404 }); } const rawSessionData = await fetchAndParseCsv( @@ -114,12 +113,12 @@ export async function POST(request: NextRequest) { } // Immediately process the queued imports to create Session records - console.log('[Refresh API] Processing queued imports...'); + console.log("[Refresh API] Processing queued imports..."); await processQueuedImports(100); // Process up to 100 imports immediately // Count how many sessions were created const sessionCount = await prisma.session.count({ - where: { companyId: company.id } + where: { companyId: company.id }, }); return NextResponse.json({ @@ -127,7 +126,7 @@ export async function POST(request: NextRequest) { imported: importedCount, total: rawSessionData.length, sessions: sessionCount, - message: `Successfully imported ${importedCount} records and processed them into sessions. Total sessions: ${sessionCount}` + message: `Successfully imported ${importedCount} records and processed them into sessions. Total sessions: ${sessionCount}`, }); } catch (e) { const error = e instanceof Error ? e.message : "An unknown error occurred"; diff --git a/app/api/admin/trigger-processing/route.ts b/app/api/admin/trigger-processing/route.ts index cb7c9e7..686f5e7 100644 --- a/app/api/admin/trigger-processing/route.ts +++ b/app/api/admin/trigger-processing/route.ts @@ -45,18 +45,21 @@ export async function POST(request: NextRequest) { const { batchSize, maxConcurrency } = body; // Validate parameters - const validatedBatchSize = batchSize && batchSize > 0 ? parseInt(batchSize) : null; - const validatedMaxConcurrency = maxConcurrency && maxConcurrency > 0 ? parseInt(maxConcurrency) : 5; + const validatedBatchSize = + batchSize && batchSize > 0 ? parseInt(batchSize) : null; + const validatedMaxConcurrency = + maxConcurrency && maxConcurrency > 0 ? parseInt(maxConcurrency) : 5; // Check how many sessions need AI processing using the new status system - const sessionsNeedingAI = await ProcessingStatusManager.getSessionsNeedingProcessing( - ProcessingStage.AI_ANALYSIS, - 1000 // Get count only - ); + const sessionsNeedingAI = + await ProcessingStatusManager.getSessionsNeedingProcessing( + ProcessingStage.AI_ANALYSIS, + 1000 // Get count only + ); // Filter to sessions for this company const companySessionsNeedingAI = sessionsNeedingAI.filter( - statusRecord => statusRecord.session.companyId === user.companyId + (statusRecord) => statusRecord.session.companyId === user.companyId ); const unprocessedCount = companySessionsNeedingAI.length; @@ -77,10 +80,15 @@ export async function POST(request: NextRequest) { // The processing will continue in the background processUnprocessedSessions(validatedBatchSize, validatedMaxConcurrency) .then(() => { - console.log(`[Manual Trigger] Processing completed for company ${user.companyId}`); + console.log( + `[Manual Trigger] Processing completed for company ${user.companyId}` + ); }) .catch((error) => { - console.error(`[Manual Trigger] Processing failed for company ${user.companyId}:`, error); + console.error( + `[Manual Trigger] Processing failed for company ${user.companyId}:`, + error + ); }); return NextResponse.json({ @@ -91,7 +99,6 @@ export async function POST(request: NextRequest) { maxConcurrency: validatedMaxConcurrency, startedAt: new Date().toISOString(), }); - } catch (error) { console.error("[Manual Trigger] Error:", error); return NextResponse.json( diff --git a/app/api/dashboard/metrics/route.ts b/app/api/dashboard/metrics/route.ts index 6b6c2cd..a737aee 100644 --- a/app/api/dashboard/metrics/route.ts +++ b/app/api/dashboard/metrics/route.ts @@ -42,7 +42,7 @@ export async function GET(request: NextRequest) { if (startDate && endDate) { whereClause.startTime = { gte: new Date(startDate), - lte: new Date(endDate + 'T23:59:59.999Z'), // Include full end date + lte: new Date(endDate + "T23:59:59.999Z"), // Include full end date }; } @@ -94,10 +94,12 @@ export async function GET(request: NextRequest) { // Calculate date range from sessions let dateRange: { minDate: string; maxDate: string } | null = null; if (prismaSessions.length > 0) { - const dates = prismaSessions.map(s => new Date(s.startTime)).sort((a, b) => a.getTime() - b.getTime()); + const dates = prismaSessions + .map((s) => new Date(s.startTime)) + .sort((a, b) => a.getTime() - b.getTime()); dateRange = { - minDate: dates[0].toISOString().split('T')[0], // First session date - maxDate: dates[dates.length - 1].toISOString().split('T')[0] // Last session date + minDate: dates[0].toISOString().split("T")[0], // First session date + maxDate: dates[dates.length - 1].toISOString().split("T")[0], // Last session date }; } diff --git a/app/api/dashboard/session-filter-options/route.ts b/app/api/dashboard/session-filter-options/route.ts index 9d69a27..1ad1cef 100644 --- a/app/api/dashboard/session-filter-options/route.ts +++ b/app/api/dashboard/session-filter-options/route.ts @@ -53,9 +53,9 @@ export async function GET(request: NextRequest) { .map((s) => s.language) .filter(Boolean) as string[]; // Filter out any nulls and assert as string[] - return NextResponse.json({ - categories: distinctCategories, - languages: distinctLanguages + return NextResponse.json({ + categories: distinctCategories, + languages: distinctLanguages, }); } catch (error) { const errorMessage = diff --git a/app/api/dashboard/session/[id]/route.ts b/app/api/dashboard/session/[id]/route.ts index eb65c76..5e33387 100644 --- a/app/api/dashboard/session/[id]/route.ts +++ b/app/api/dashboard/session/[id]/route.ts @@ -26,10 +26,7 @@ export async function GET( }); if (!prismaSession) { - return NextResponse.json( - { error: "Session not found" }, - { status: 404 } - ); + return NextResponse.json({ error: "Session not found" }, { status: 404 }); } // Map Prisma session object to ChatSession type diff --git a/app/api/dashboard/sessions/route.ts b/app/api/dashboard/sessions/route.ts index 068d3a0..86d35ba 100644 --- a/app/api/dashboard/sessions/route.ts +++ b/app/api/dashboard/sessions/route.ts @@ -18,7 +18,7 @@ export async function GET(request: NextRequest) { const companyId = authSession.user.companyId; const { searchParams } = new URL(request.url); - + const searchTerm = searchParams.get("searchTerm"); const category = searchParams.get("category"); const language = searchParams.get("language"); @@ -87,9 +87,7 @@ export async function GET(request: NextRequest) { | Prisma.SessionOrderByWithRelationInput[]; const primarySortField = - sortKey && validSortKeys[sortKey] - ? validSortKeys[sortKey] - : "startTime"; // Default to startTime field if sortKey is invalid/missing + sortKey && validSortKeys[sortKey] ? validSortKeys[sortKey] : "startTime"; // Default to startTime field if sortKey is invalid/missing const primarySortOrder = sortOrder === "asc" || sortOrder === "desc" ? sortOrder : "desc"; // Default to desc order diff --git a/app/api/dashboard/users/route.ts b/app/api/dashboard/users/route.ts index cc00917..5b8e2b3 100644 --- a/app/api/dashboard/users/route.ts +++ b/app/api/dashboard/users/route.ts @@ -65,7 +65,7 @@ export async function POST(request: NextRequest) { } const tempPassword = crypto.randomBytes(12).toString("base64").slice(0, 12); // secure random initial password - + await prisma.user.create({ data: { email, diff --git a/app/api/forgot-password/route.ts b/app/api/forgot-password/route.ts index 382fb82..46313a9 100644 --- a/app/api/forgot-password/route.ts +++ b/app/api/forgot-password/route.ts @@ -1,28 +1,92 @@ import { NextRequest, NextResponse } from "next/server"; import { prisma } from "../../../lib/prisma"; import { sendEmail } from "../../../lib/sendEmail"; +import { forgotPasswordSchema, validateInput } from "../../../lib/validation"; import crypto from "crypto"; -export async function POST(request: NextRequest) { - const body = await request.json(); - const { email } = body as { email: string }; +// In-memory rate limiting for password reset requests +const resetAttempts = new Map(); - const user = await prisma.user.findUnique({ where: { email } }); - if (!user) { - // Always return 200 for privacy (don't reveal if email exists) - return NextResponse.json({ success: true }, { status: 200 }); +function checkRateLimit(ip: string): boolean { + const now = Date.now(); + const attempts = resetAttempts.get(ip); + + if (!attempts || now > attempts.resetTime) { + resetAttempts.set(ip, { count: 1, resetTime: now + 15 * 60 * 1000 }); // 15 minute window + return true; } - const token = crypto.randomBytes(32).toString("hex"); - const expiry = new Date(Date.now() + 1000 * 60 * 30); // 30 min expiry - - await prisma.user.update({ - where: { email }, - data: { resetToken: token, resetTokenExpiry: expiry }, - }); + if (attempts.count >= 5) { + // Max 5 reset requests per 15 minutes per IP + return false; + } - const resetUrl = `${process.env.NEXTAUTH_URL || "http://localhost:3000"}/reset-password?token=${token}`; - await sendEmail(email, "Password Reset", `Reset your password: ${resetUrl}`); - - return NextResponse.json({ success: true }, { status: 200 }); + attempts.count++; + return true; +} + +export async function POST(request: NextRequest) { + try { + // Rate limiting check + const ip = + request.ip || request.headers.get("x-forwarded-for") || "unknown"; + if (!checkRateLimit(ip)) { + return NextResponse.json( + { + success: false, + error: "Too many password reset attempts. Please try again later.", + }, + { status: 429 } + ); + } + + const body = await request.json(); + + // Validate input + const validation = validateInput(forgotPasswordSchema, body); + if (!validation.success) { + return NextResponse.json( + { + success: false, + error: "Invalid email format", + }, + { status: 400 } + ); + } + + const { email } = validation.data; + + const user = await prisma.user.findUnique({ where: { email } }); + + // Always return success for privacy (don't reveal if email exists) + // But only send email if user exists + if (user) { + const token = crypto.randomBytes(32).toString("hex"); + const tokenHash = crypto.createHash("sha256").update(token).digest("hex"); + const expiry = new Date(Date.now() + 1000 * 60 * 30); // 30 min expiry + + await prisma.user.update({ + where: { email }, + data: { resetToken: tokenHash, resetTokenExpiry: expiry }, + }); + + const resetUrl = `${process.env.NEXTAUTH_URL || "http://localhost:3000"}/reset-password?token=${token}`; + await sendEmail( + email, + "Password Reset", + `Reset your password: ${resetUrl}` + ); + } + + return NextResponse.json({ success: true }, { status: 200 }); + } catch (error) { + console.error("Forgot password error:", error); + return NextResponse.json( + { + success: false, + error: "Internal server error", + }, + { status: 500 } + ); + } } diff --git a/app/api/register/route.ts b/app/api/register/route.ts index bc55e0f..56356e3 100644 --- a/app/api/register/route.ts +++ b/app/api/register/route.ts @@ -1,63 +1,136 @@ import { NextRequest, NextResponse } from "next/server"; import { prisma } from "../../../lib/prisma"; +import { registerSchema, validateInput } from "../../../lib/validation"; import bcrypt from "bcryptjs"; -interface RegisterRequestBody { - email: string; - password: string; - company: string; - csvUrl?: string; +// In-memory rate limiting (for production, use Redis or similar) +const registrationAttempts = new Map< + string, + { count: number; resetTime: number } +>(); + +function checkRateLimit(ip: string): boolean { + const now = Date.now(); + const attempts = registrationAttempts.get(ip); + + if (!attempts || now > attempts.resetTime) { + registrationAttempts.set(ip, { count: 1, resetTime: now + 60 * 60 * 1000 }); // 1 hour window + return true; + } + + if (attempts.count >= 3) { + // Max 3 registrations per hour per IP + return false; + } + + attempts.count++; + return true; } export async function POST(request: NextRequest) { - const body = await request.json(); - const { email, password, company, csvUrl } = body as RegisterRequestBody; + try { + // Rate limiting check + const ip = + request.ip || request.headers.get("x-forwarded-for") || "unknown"; + if (!checkRateLimit(ip)) { + return NextResponse.json( + { + success: false, + error: "Too many registration attempts. Please try again later.", + }, + { status: 429 } + ); + } - if (!email || !password || !company) { + const body = await request.json(); + + // Validate input with Zod schema + const validation = validateInput(registerSchema, body); + if (!validation.success) { + return NextResponse.json( + { + success: false, + error: "Validation failed", + details: validation.errors, + }, + { status: 400 } + ); + } + + const { email, password, company } = validation.data; + + // Check if email exists + const existingUser = await prisma.user.findUnique({ + where: { email }, + }); + + if (existingUser) { + return NextResponse.json( + { + success: false, + error: "Email already exists", + }, + { status: 409 } + ); + } + + // Check if company name already exists + const existingCompany = await prisma.company.findFirst({ + where: { name: company }, + }); + + if (existingCompany) { + return NextResponse.json( + { + success: false, + error: "Company name already exists", + }, + { status: 409 } + ); + } + + // Create company and user in a transaction + const result = await prisma.$transaction(async (tx) => { + const newCompany = await tx.company.create({ + data: { + name: company, + csvUrl: "", // Empty by default, can be set later in settings + }, + }); + + const hashedPassword = await bcrypt.hash(password, 12); // Increased rounds for better security + + const newUser = await tx.user.create({ + data: { + email, + password: hashedPassword, + companyId: newCompany.id, + role: "USER", // Changed from ADMIN - users should be promoted by existing admins + }, + }); + + return { company: newCompany, user: newUser }; + }); + + return NextResponse.json( + { + success: true, + data: { + message: "Registration successful", + userId: result.user.id, + companyId: result.company.id, + }, + }, + { status: 201 } + ); + } catch (error) { + console.error("Registration error:", error); return NextResponse.json( { success: false, - error: "Missing required fields", + error: "Internal server error", }, - { status: 400 } + { status: 500 } ); } - - // Check if email exists - const exists = await prisma.user.findUnique({ - where: { email }, - }); - - if (exists) { - return NextResponse.json( - { - success: false, - error: "Email already exists", - }, - { status: 409 } - ); - } - - const newCompany = await prisma.company.create({ - data: { name: company, csvUrl: csvUrl || "" }, - }); - - const hashed = await bcrypt.hash(password, 10); - - await prisma.user.create({ - data: { - email, - password: hashed, - companyId: newCompany.id, - role: "ADMIN", - }, - }); - - return NextResponse.json( - { - success: true, - data: { success: true }, - }, - { status: 201 } - ); } diff --git a/app/api/reset-password/route.ts b/app/api/reset-password/route.ts index c518bc8..a0ea3f8 100644 --- a/app/api/reset-password/route.ts +++ b/app/api/reset-password/route.ts @@ -1,29 +1,34 @@ import { NextRequest, NextResponse } from "next/server"; import { prisma } from "../../../lib/prisma"; +import { resetPasswordSchema, validateInput } from "../../../lib/validation"; import bcrypt from "bcryptjs"; +import crypto from "crypto"; export async function POST(request: NextRequest) { - const body = await request.json(); - const { token, password } = body as { token?: string; password?: string }; - - if (!token || !password) { - return NextResponse.json( - { error: "Token and password are required." }, - { status: 400 } - ); - } - - if (password.length < 8) { - return NextResponse.json( - { error: "Password must be at least 8 characters long." }, - { status: 400 } - ); - } - try { + const body = await request.json(); + + // Validate input with strong password requirements + const validation = validateInput(resetPasswordSchema, body); + if (!validation.success) { + return NextResponse.json( + { + success: false, + error: "Validation failed", + details: validation.errors, + }, + { status: 400 } + ); + } + + const { token, password } = validation.data; + + // Hash the token to compare with stored hash + const tokenHash = crypto.createHash("sha256").update(token).digest("hex"); + const user = await prisma.user.findFirst({ where: { - resetToken: token, + resetToken: tokenHash, resetTokenExpiry: { gte: new Date() }, }, }); @@ -31,30 +36,38 @@ export async function POST(request: NextRequest) { if (!user) { return NextResponse.json( { - error: "Invalid or expired token. Please request a new password reset.", + success: false, + error: + "Invalid or expired token. Please request a new password reset.", }, { status: 400 } ); } - const hash = await bcrypt.hash(password, 10); + // Hash password with higher rounds for better security + const hashedPassword = await bcrypt.hash(password, 12); + await prisma.user.update({ where: { id: user.id }, data: { - password: hash, + password: hashedPassword, resetToken: null, resetTokenExpiry: null, }, }); return NextResponse.json( - { message: "Password has been reset successfully." }, + { + success: true, + message: "Password has been reset successfully.", + }, { status: 200 } ); } catch (error) { console.error("Reset password error:", error); return NextResponse.json( { + success: false, error: "An internal server error occurred. Please try again later.", }, { status: 500 } diff --git a/app/dashboard/overview/page.tsx b/app/dashboard/overview/page.tsx index 65fbdb5..de14944 100644 --- a/app/dashboard/overview/page.tsx +++ b/app/dashboard/overview/page.tsx @@ -48,7 +48,10 @@ function DashboardContent() { const [company, setCompany] = useState(null); const [loading, setLoading] = useState(false); const [refreshing, setRefreshing] = useState(false); - const [dateRange, setDateRange] = useState<{ minDate: string; maxDate: string } | null>(null); + const [dateRange, setDateRange] = useState<{ + minDate: string; + maxDate: string; + } | null>(null); const [selectedStartDate, setSelectedStartDate] = useState(""); const [selectedEndDate, setSelectedEndDate] = useState(""); const [isInitialLoad, setIsInitialLoad] = useState(true); @@ -56,7 +59,11 @@ function DashboardContent() { const isAuditor = session?.user?.role === "AUDITOR"; // Function to fetch metrics with optional date range - const fetchMetrics = async (startDate?: string, endDate?: string, isInitial = false) => { + const fetchMetrics = async ( + startDate?: string, + endDate?: string, + isInitial = false + ) => { setLoading(true); try { let url = "/api/dashboard/metrics"; @@ -85,11 +92,14 @@ function DashboardContent() { }; // Handle date range changes - const handleDateRangeChange = useCallback((startDate: string, endDate: string) => { - setSelectedStartDate(startDate); - setSelectedEndDate(endDate); - fetchMetrics(startDate, endDate); - }, []); + const handleDateRangeChange = useCallback( + (startDate: string, endDate: string) => { + setSelectedStartDate(startDate); + setSelectedEndDate(endDate); + fetchMetrics(startDate, endDate); + }, + [] + ); useEffect(() => { // Redirect if not authenticated @@ -216,33 +226,48 @@ function DashboardContent() { }; return [ - { name: "Positive", value: sentimentData.positive, color: "hsl(var(--chart-1))" }, - { name: "Neutral", value: sentimentData.neutral, color: "hsl(var(--chart-2))" }, - { name: "Negative", value: sentimentData.negative, color: "hsl(var(--chart-3))" }, + { + name: "Positive", + value: sentimentData.positive, + color: "hsl(var(--chart-1))", + }, + { + name: "Neutral", + value: sentimentData.neutral, + color: "hsl(var(--chart-2))", + }, + { + name: "Negative", + value: sentimentData.negative, + color: "hsl(var(--chart-3))", + }, ]; }; const getSessionsOverTimeData = () => { if (!metrics?.days) return []; - + return Object.entries(metrics.days).map(([date, value]) => ({ - date: new Date(date).toLocaleDateString('en-US', { month: 'short', day: 'numeric' }), + date: new Date(date).toLocaleDateString("en-US", { + month: "short", + day: "numeric", + }), value: value as number, })); }; const getCategoriesData = () => { if (!metrics?.categories) return []; - + return Object.entries(metrics.categories).map(([name, value]) => ({ - name: name.length > 15 ? name.substring(0, 15) + '...' : name, + name: name.length > 15 ? name.substring(0, 15) + "..." : name, value: value as number, })); }; const getLanguagesData = () => { if (!metrics?.languages) return []; - + return Object.entries(metrics.languages).map(([name, value]) => ({ name, value: value as number, @@ -287,7 +312,9 @@ function DashboardContent() {
-

{company.name}

+

+ {company.name} +

Analytics Dashboard @@ -299,7 +326,7 @@ function DashboardContent() {

- +
- + - signOut({ callbackUrl: "/login" })}> + signOut({ callbackUrl: "/login" })} + > Sign out @@ -352,7 +383,7 @@ function DashboardContent() { }} variant="primary" /> - + - + = 0, }} /> - + - + } description="Average per day" /> - + } description="Busiest hour" /> - + } trend={{ value: metrics.resolvedChatsPercentage ?? 0, isPositive: (metrics.resolvedChatsPercentage ?? 0) >= 80, }} - variant={metrics.resolvedChatsPercentage && metrics.resolvedChatsPercentage >= 80 ? "success" : "warning"} + variant={ + metrics.resolvedChatsPercentage && + metrics.resolvedChatsPercentage >= 80 + ? "success" + : "warning" + } /> - + - + - + - Total Cost: - €{metrics.totalTokensEur?.toFixed(4) || 0} + Total Cost:€ + {metrics.totalTokensEur?.toFixed(4) || 0}
diff --git a/app/dashboard/page.tsx b/app/dashboard/page.tsx index 2257420..7f8ee56 100644 --- a/app/dashboard/page.tsx +++ b/app/dashboard/page.tsx @@ -46,7 +46,8 @@ const DashboardPage: FC = () => { const navigationCards = [ { title: "Analytics Overview", - description: "View comprehensive metrics, charts, and insights from your chat sessions", + description: + "View comprehensive metrics, charts, and insights from your chat sessions", icon: , href: "/dashboard/overview", variant: "primary" as const, @@ -54,7 +55,8 @@ const DashboardPage: FC = () => { }, { title: "Session Browser", - description: "Browse, search, and analyze individual conversation sessions", + description: + "Browse, search, and analyze individual conversation sessions", icon: , href: "/dashboard/sessions", variant: "success" as const, @@ -64,16 +66,22 @@ const DashboardPage: FC = () => { ? [ { title: "Company Settings", - description: "Configure company settings, integrations, and API connections", + description: + "Configure company settings, integrations, and API connections", icon: , href: "/dashboard/company", variant: "warning" as const, - features: ["API configuration", "Integration settings", "Data management"], + features: [ + "API configuration", + "Integration settings", + "Data management", + ], adminOnly: true, }, { title: "User Management", - description: "Invite team members and manage user accounts and permissions", + description: + "Invite team members and manage user accounts and permissions", icon: , href: "/dashboard/users", variant: "default" as const, @@ -129,7 +137,7 @@ const DashboardPage: FC = () => { Choose a section below to explore your analytics dashboard

- +
@@ -152,7 +160,7 @@ const DashboardPage: FC = () => { > {/* Subtle gradient overlay */}
- +
@@ -186,7 +194,10 @@ const DashboardPage: FC = () => { {/* Features List */}
{card.features.map((feature, featureIndex) => ( -
+
{feature}
@@ -232,7 +243,7 @@ const DashboardPage: FC = () => {

Data updates

- +
@@ -240,7 +251,7 @@ const DashboardPage: FC = () => {

Data protection

- +
diff --git a/check-refactored-pipeline-status.ts b/check-refactored-pipeline-status.ts index 0bb7038..5f238b7 100644 --- a/check-refactored-pipeline-status.ts +++ b/check-refactored-pipeline-status.ts @@ -1,75 +1,90 @@ -import { PrismaClient } from '@prisma/client'; -import { ProcessingStatusManager } from './lib/processingStatusManager'; +import { PrismaClient } from "@prisma/client"; +import { ProcessingStatusManager } from "./lib/processingStatusManager"; const prisma = new PrismaClient(); async function checkRefactoredPipelineStatus() { try { - console.log('=== REFACTORED PIPELINE STATUS ===\n'); - + console.log("=== REFACTORED PIPELINE STATUS ===\n"); + // Get pipeline status using the new system const pipelineStatus = await ProcessingStatusManager.getPipelineStatus(); - + console.log(`Total Sessions: ${pipelineStatus.totalSessions}\n`); - + // Display status for each stage - const stages = ['CSV_IMPORT', 'TRANSCRIPT_FETCH', 'SESSION_CREATION', 'AI_ANALYSIS', 'QUESTION_EXTRACTION']; - + const stages = [ + "CSV_IMPORT", + "TRANSCRIPT_FETCH", + "SESSION_CREATION", + "AI_ANALYSIS", + "QUESTION_EXTRACTION", + ]; + for (const stage of stages) { console.log(`${stage}:`); const stageData = pipelineStatus.pipeline[stage] || {}; - + const pending = stageData.PENDING || 0; const inProgress = stageData.IN_PROGRESS || 0; const completed = stageData.COMPLETED || 0; const failed = stageData.FAILED || 0; const skipped = stageData.SKIPPED || 0; - + console.log(` PENDING: ${pending}`); console.log(` IN_PROGRESS: ${inProgress}`); console.log(` COMPLETED: ${completed}`); console.log(` FAILED: ${failed}`); console.log(` SKIPPED: ${skipped}`); - console.log(''); + console.log(""); } - + // Show what needs processing - console.log('=== WHAT NEEDS PROCESSING ==='); - + console.log("=== WHAT NEEDS PROCESSING ==="); + for (const stage of stages) { const stageData = pipelineStatus.pipeline[stage] || {}; const pending = stageData.PENDING || 0; const failed = stageData.FAILED || 0; - + if (pending > 0 || failed > 0) { console.log(`• ${stage}: ${pending} pending, ${failed} failed`); } } - + // Show failed sessions if any const failedSessions = await ProcessingStatusManager.getFailedSessions(); if (failedSessions.length > 0) { - console.log('\n=== FAILED SESSIONS ==='); - failedSessions.slice(0, 5).forEach(failure => { - console.log(` ${failure.session.import?.externalSessionId || failure.sessionId}: ${failure.stage} - ${failure.errorMessage}`); + console.log("\n=== FAILED SESSIONS ==="); + failedSessions.slice(0, 5).forEach((failure) => { + console.log( + ` ${failure.session.import?.externalSessionId || failure.sessionId}: ${failure.stage} - ${failure.errorMessage}` + ); }); - + if (failedSessions.length > 5) { - console.log(` ... and ${failedSessions.length - 5} more failed sessions`); + console.log( + ` ... and ${failedSessions.length - 5} more failed sessions` + ); } } - + // Show sessions ready for AI processing - const readyForAI = await ProcessingStatusManager.getSessionsNeedingProcessing('AI_ANALYSIS', 5); + const readyForAI = + await ProcessingStatusManager.getSessionsNeedingProcessing( + "AI_ANALYSIS", + 5 + ); if (readyForAI.length > 0) { - console.log('\n=== SESSIONS READY FOR AI PROCESSING ==='); - readyForAI.forEach(status => { - console.log(` ${status.session.import?.externalSessionId || status.sessionId} (created: ${status.session.createdAt})`); + console.log("\n=== SESSIONS READY FOR AI PROCESSING ==="); + readyForAI.forEach((status) => { + console.log( + ` ${status.session.import?.externalSessionId || status.sessionId} (created: ${status.session.createdAt})` + ); }); } - } catch (error) { - console.error('Error checking pipeline status:', error); + console.error("Error checking pipeline status:", error); } finally { await prisma.$disconnect(); } diff --git a/components/DateRangePicker.tsx b/components/DateRangePicker.tsx index 4b70a0a..90aba93 100644 --- a/components/DateRangePicker.tsx +++ b/components/DateRangePicker.tsx @@ -63,10 +63,11 @@ export default function DateRangePicker({ const setLast30Days = () => { const thirtyDaysAgo = new Date(); thirtyDaysAgo.setDate(thirtyDaysAgo.getDate() - 30); - const thirtyDaysAgoStr = thirtyDaysAgo.toISOString().split('T')[0]; + const thirtyDaysAgoStr = thirtyDaysAgo.toISOString().split("T")[0]; // Use the later of 30 days ago or minDate - const newStartDate = thirtyDaysAgoStr > minDate ? thirtyDaysAgoStr : minDate; + const newStartDate = + thirtyDaysAgoStr > minDate ? thirtyDaysAgoStr : minDate; setStartDate(newStartDate); setEndDate(maxDate); }; @@ -74,7 +75,7 @@ export default function DateRangePicker({ const setLast7Days = () => { const sevenDaysAgo = new Date(); sevenDaysAgo.setDate(sevenDaysAgo.getDate() - 7); - const sevenDaysAgoStr = sevenDaysAgo.toISOString().split('T')[0]; + const sevenDaysAgoStr = sevenDaysAgo.toISOString().split("T")[0]; // Use the later of 7 days ago or minDate const newStartDate = sevenDaysAgoStr > minDate ? sevenDaysAgoStr : minDate; @@ -146,7 +147,8 @@ export default function DateRangePicker({
- Available data: {new Date(minDate).toLocaleDateString()} - {new Date(maxDate).toLocaleDateString()} + Available data: {new Date(minDate).toLocaleDateString()} -{" "} + {new Date(maxDate).toLocaleDateString()}
); diff --git a/components/GeographicMap.tsx b/components/GeographicMap.tsx index b1e0d90..5e974ca 100644 --- a/components/GeographicMap.tsx +++ b/components/GeographicMap.tsx @@ -48,7 +48,7 @@ const getCountryCoordinates = (): Record => { BG: [42.7339, 25.4858], HR: [45.1, 15.2], SK: [48.669, 19.699], - SI: [46.1512, 14.9955] + SI: [46.1512, 14.9955], }; // This function now primarily returns fallbacks. // The actual fetching using @rapideditor/country-coder will be in the component's useEffect. diff --git a/components/MessageViewer.tsx b/components/MessageViewer.tsx index 3e77daf..2152518 100644 --- a/components/MessageViewer.tsx +++ b/components/MessageViewer.tsx @@ -49,7 +49,9 @@ export default function MessageViewer({ messages }: MessageViewerProps) { {message.role} - {message.timestamp ? new Date(message.timestamp).toLocaleTimeString() : 'No timestamp'} + {message.timestamp + ? new Date(message.timestamp).toLocaleTimeString() + : "No timestamp"}
@@ -63,13 +65,18 @@ export default function MessageViewer({ messages }: MessageViewerProps) {
- First message: {messages[0].timestamp ? new Date(messages[0].timestamp).toLocaleString() : 'No timestamp'} + First message:{" "} + {messages[0].timestamp + ? new Date(messages[0].timestamp).toLocaleString() + : "No timestamp"} Last message:{" "} {(() => { const lastMessage = messages[messages.length - 1]; - return lastMessage.timestamp ? new Date(lastMessage.timestamp).toLocaleString() : 'No timestamp'; + return lastMessage.timestamp + ? new Date(lastMessage.timestamp).toLocaleString() + : "No timestamp"; })()}
diff --git a/components/MetricCard.tsx b/components/MetricCard.tsx deleted file mode 100644 index b8ff5c2..0000000 --- a/components/MetricCard.tsx +++ /dev/null @@ -1,88 +0,0 @@ -"use client"; - -interface MetricCardProps { - title: string; - value: string | number | null | undefined; - description?: string; - icon?: React.ReactNode; - trend?: { - value: number; - label?: string; - isPositive?: boolean; - }; - variant?: "default" | "primary" | "success" | "warning" | "danger"; -} - -export default function MetricCard({ - title, - value, - description, - icon, - trend, - variant = "default", -}: MetricCardProps) { - // Determine background and text colors based on variant - const getVariantClasses = () => { - switch (variant) { - case "primary": - return "bg-blue-50 border-blue-200"; - case "success": - return "bg-green-50 border-green-200"; - case "warning": - return "bg-amber-50 border-amber-200"; - case "danger": - return "bg-red-50 border-red-200"; - default: - return "bg-white border-gray-200"; - } - }; - - const getIconClasses = () => { - switch (variant) { - case "primary": - return "bg-blue-100 text-blue-600"; - case "success": - return "bg-green-100 text-green-600"; - case "warning": - return "bg-amber-100 text-amber-600"; - case "danger": - return "bg-red-100 text-red-600"; - default: - return "bg-gray-100 text-gray-600"; - } - }; - - return ( -
-
-
-

{title}

-
-

{value ?? "-"}

- {trend && ( - - {trend.isPositive !== false ? "↑" : "↓"}{" "} - {Math.abs(trend.value).toFixed(1)}% - - )} -
- {description && ( -

{description}

- )} -
- - {icon && ( -
- {icon} -
- )} -
-
- ); -} diff --git a/components/ResponseTimeDistribution.tsx b/components/ResponseTimeDistribution.tsx index dc97668..255563a 100644 --- a/components/ResponseTimeDistribution.tsx +++ b/components/ResponseTimeDistribution.tsx @@ -68,8 +68,10 @@ export default function ResponseTimeDistribution({ // Determine color based on response time let color; - if (i <= 2) color = "hsl(var(--chart-1))"; // Green for fast - else if (i <= 5) color = "hsl(var(--chart-4))"; // Yellow for medium + if (i <= 2) + color = "hsl(var(--chart-1))"; // Green for fast + else if (i <= 5) + color = "hsl(var(--chart-4))"; // Yellow for medium else color = "hsl(var(--chart-3))"; // Red for slow return { @@ -82,10 +84,13 @@ export default function ResponseTimeDistribution({ return (
- - + } /> - - + + {chartData.map((entry, index) => ( ))} {/* Average line */} - {/* Target line (if provided) */} {targetResponseTime && ( - )} diff --git a/components/SessionDetails.tsx b/components/SessionDetails.tsx index 87a0e43..acdd646 100644 --- a/components/SessionDetails.tsx +++ b/components/SessionDetails.tsx @@ -90,7 +90,6 @@ export default function SessionDetails({ session }: SessionDetailsProps) { {session.messagesSent || 0}
- {session.avgResponseTime !== null && session.avgResponseTime !== undefined && (
@@ -132,7 +131,6 @@ export default function SessionDetails({ session }: SessionDetailsProps) {
)} - {session.initialMsg && (
Initial Message: @@ -151,7 +149,6 @@ export default function SessionDetails({ session }: SessionDetailsProps) {
)} - {session.fullTranscriptUrl && (
Transcript: diff --git a/components/TopQuestionsChart.tsx b/components/TopQuestionsChart.tsx index e312bae..f1fbae2 100644 --- a/components/TopQuestionsChart.tsx +++ b/components/TopQuestionsChart.tsx @@ -1,14 +1,17 @@ -'use client'; +"use client"; -import React from 'react'; -import { TopQuestion } from '../lib/types'; +import React from "react"; +import { TopQuestion } from "../lib/types"; interface TopQuestionsChartProps { data: TopQuestion[]; title?: string; } -export default function TopQuestionsChart({ data, title = "Top 5 Asked Questions" }: TopQuestionsChartProps) { +export default function TopQuestionsChart({ + data, + title = "Top 5 Asked Questions", +}: TopQuestionsChartProps) { if (!data || data.length === 0) { return (
@@ -21,7 +24,7 @@ export default function TopQuestionsChart({ data, title = "Top 5 Asked Questions } // Find the maximum count to calculate relative bar widths - const maxCount = Math.max(...data.map(q => q.count)); + const maxCount = Math.max(...data.map((q) => q.count)); return (
@@ -29,7 +32,8 @@ export default function TopQuestionsChart({ data, title = "Top 5 Asked Questions
{data.map((question, index) => { - const percentage = maxCount > 0 ? (question.count / maxCount) * 100 : 0; + const percentage = + maxCount > 0 ? (question.count / maxCount) * 100 : 0; return (
diff --git a/components/charts/bar-chart.tsx b/components/charts/bar-chart.tsx index 9c1b754..a2e44a4 100644 --- a/components/charts/bar-chart.tsx +++ b/components/charts/bar-chart.tsx @@ -61,10 +61,13 @@ export default function ModernBarChart({ )} - - + } /> - {data.map((entry, index) => ( - diff --git a/components/charts/donut-chart.tsx b/components/charts/donut-chart.tsx index 57f44a7..d7dfbc0 100644 --- a/components/charts/donut-chart.tsx +++ b/components/charts/donut-chart.tsx @@ -1,6 +1,13 @@ "use client"; -import { PieChart, Pie, Cell, ResponsiveContainer, Tooltip, Legend } from "recharts"; +import { + PieChart, + Pie, + Cell, + ResponsiveContainer, + Tooltip, + Legend, +} from "recharts"; import { Card, CardContent, CardHeader, CardTitle } from "@/components/ui/card"; interface DonutChartProps { @@ -22,9 +29,7 @@ const CustomTooltip = ({ active, payload }: any) => {

{data.name}

- - {data.value} - {" "} + {data.value}{" "} sessions ({((data.value / data.payload.total) * 100).toFixed(1)}%)

@@ -77,7 +82,7 @@ export default function ModernDonutChart({ className, }: DonutChartProps) { const total = data.reduce((sum, item) => sum + item.value, 0); - const dataWithTotal = data.map(item => ({ ...item, total })); + const dataWithTotal = data.map((item) => ({ ...item, total })); return ( diff --git a/components/charts/line-chart.tsx b/components/charts/line-chart.tsx index c3a0f10..513fd09 100644 --- a/components/charts/line-chart.tsx +++ b/components/charts/line-chart.tsx @@ -60,7 +60,10 @@ export default function ModernLineChart({ )} - + {gradient && ( @@ -69,9 +72,9 @@ export default function ModernLineChart({ )} - } /> - + {gradient ? ( svg]:size-3 gap-1 [&>svg]:pointer-events-none focus-visible:border-ring focus-visible:ring-ring/50 focus-visible:ring-[3px] aria-invalid:ring-destructive/20 dark:aria-invalid:ring-destructive/40 aria-invalid:border-destructive transition-[color,box-shadow] overflow-hidden", @@ -23,7 +23,7 @@ const badgeVariants = cva( variant: "default", }, } -) +); function Badge({ className, @@ -32,7 +32,7 @@ function Badge({ ...props }: React.ComponentProps<"span"> & VariantProps & { asChild?: boolean }) { - const Comp = asChild ? Slot : "span" + const Comp = asChild ? Slot : "span"; return ( - ) + ); } -export { Badge, badgeVariants } +export { Badge, badgeVariants }; diff --git a/components/ui/button.tsx b/components/ui/button.tsx index a2df8dc..66ab90e 100644 --- a/components/ui/button.tsx +++ b/components/ui/button.tsx @@ -1,8 +1,8 @@ -import * as React from "react" -import { Slot } from "@radix-ui/react-slot" -import { cva, type VariantProps } from "class-variance-authority" +import * as React from "react"; +import { Slot } from "@radix-ui/react-slot"; +import { cva, type VariantProps } from "class-variance-authority"; -import { cn } from "@/lib/utils" +import { cn } from "@/lib/utils"; const buttonVariants = cva( "inline-flex items-center justify-center gap-2 whitespace-nowrap rounded-md text-sm font-medium transition-all disabled:pointer-events-none disabled:opacity-50 [&_svg]:pointer-events-none [&_svg:not([class*='size-'])]:size-4 shrink-0 [&_svg]:shrink-0 outline-none focus-visible:border-ring focus-visible:ring-ring/50 focus-visible:ring-[3px] aria-invalid:ring-destructive/20 dark:aria-invalid:ring-destructive/40 aria-invalid:border-destructive", @@ -33,7 +33,7 @@ const buttonVariants = cva( size: "default", }, } -) +); function Button({ className, @@ -43,9 +43,9 @@ function Button({ ...props }: React.ComponentProps<"button"> & VariantProps & { - asChild?: boolean + asChild?: boolean; }) { - const Comp = asChild ? Slot : "button" + const Comp = asChild ? Slot : "button"; return ( - ) + ); } -export { Button, buttonVariants } +export { Button, buttonVariants }; diff --git a/components/ui/card.tsx b/components/ui/card.tsx index d05bbc6..93a82d9 100644 --- a/components/ui/card.tsx +++ b/components/ui/card.tsx @@ -1,6 +1,6 @@ -import * as React from "react" +import * as React from "react"; -import { cn } from "@/lib/utils" +import { cn } from "@/lib/utils"; function Card({ className, ...props }: React.ComponentProps<"div">) { return ( @@ -12,7 +12,7 @@ function Card({ className, ...props }: React.ComponentProps<"div">) { )} {...props} /> - ) + ); } function CardHeader({ className, ...props }: React.ComponentProps<"div">) { @@ -25,7 +25,7 @@ function CardHeader({ className, ...props }: React.ComponentProps<"div">) { )} {...props} /> - ) + ); } function CardTitle({ className, ...props }: React.ComponentProps<"div">) { @@ -35,7 +35,7 @@ function CardTitle({ className, ...props }: React.ComponentProps<"div">) { className={cn("leading-none font-semibold", className)} {...props} /> - ) + ); } function CardDescription({ className, ...props }: React.ComponentProps<"div">) { @@ -45,7 +45,7 @@ function CardDescription({ className, ...props }: React.ComponentProps<"div">) { className={cn("text-muted-foreground text-sm", className)} {...props} /> - ) + ); } function CardAction({ className, ...props }: React.ComponentProps<"div">) { @@ -58,7 +58,7 @@ function CardAction({ className, ...props }: React.ComponentProps<"div">) { )} {...props} /> - ) + ); } function CardContent({ className, ...props }: React.ComponentProps<"div">) { @@ -68,7 +68,7 @@ function CardContent({ className, ...props }: React.ComponentProps<"div">) { className={cn("px-6", className)} {...props} /> - ) + ); } function CardFooter({ className, ...props }: React.ComponentProps<"div">) { @@ -78,7 +78,7 @@ function CardFooter({ className, ...props }: React.ComponentProps<"div">) { className={cn("flex items-center px-6 [.border-t]:pt-6", className)} {...props} /> - ) + ); } export { @@ -89,4 +89,4 @@ export { CardAction, CardDescription, CardContent, -} +}; diff --git a/components/ui/dropdown-menu.tsx b/components/ui/dropdown-menu.tsx index 4594d56..15c7f25 100644 --- a/components/ui/dropdown-menu.tsx +++ b/components/ui/dropdown-menu.tsx @@ -1,15 +1,15 @@ -"use client" +"use client"; -import * as React from "react" -import * as DropdownMenuPrimitive from "@radix-ui/react-dropdown-menu" -import { CheckIcon, ChevronRightIcon, CircleIcon } from "lucide-react" +import * as React from "react"; +import * as DropdownMenuPrimitive from "@radix-ui/react-dropdown-menu"; +import { CheckIcon, ChevronRightIcon, CircleIcon } from "lucide-react"; -import { cn } from "@/lib/utils" +import { cn } from "@/lib/utils"; function DropdownMenu({ ...props }: React.ComponentProps) { - return + return ; } function DropdownMenuPortal({ @@ -17,7 +17,7 @@ function DropdownMenuPortal({ }: React.ComponentProps) { return ( - ) + ); } function DropdownMenuTrigger({ @@ -28,7 +28,7 @@ function DropdownMenuTrigger({ data-slot="dropdown-menu-trigger" {...props} /> - ) + ); } function DropdownMenuContent({ @@ -48,7 +48,7 @@ function DropdownMenuContent({ {...props} /> - ) + ); } function DropdownMenuGroup({ @@ -56,7 +56,7 @@ function DropdownMenuGroup({ }: React.ComponentProps) { return ( - ) + ); } function DropdownMenuItem({ @@ -65,8 +65,8 @@ function DropdownMenuItem({ variant = "default", ...props }: React.ComponentProps & { - inset?: boolean - variant?: "default" | "destructive" + inset?: boolean; + variant?: "default" | "destructive"; }) { return ( - ) + ); } function DropdownMenuCheckboxItem({ @@ -105,7 +105,7 @@ function DropdownMenuCheckboxItem({ {children} - ) + ); } function DropdownMenuRadioGroup({ @@ -116,7 +116,7 @@ function DropdownMenuRadioGroup({ data-slot="dropdown-menu-radio-group" {...props} /> - ) + ); } function DropdownMenuRadioItem({ @@ -140,7 +140,7 @@ function DropdownMenuRadioItem({ {children} - ) + ); } function DropdownMenuLabel({ @@ -148,7 +148,7 @@ function DropdownMenuLabel({ inset, ...props }: React.ComponentProps & { - inset?: boolean + inset?: boolean; }) { return ( - ) + ); } function DropdownMenuSeparator({ @@ -173,7 +173,7 @@ function DropdownMenuSeparator({ className={cn("bg-border -mx-1 my-1 h-px", className)} {...props} /> - ) + ); } function DropdownMenuShortcut({ @@ -189,13 +189,13 @@ function DropdownMenuShortcut({ )} {...props} /> - ) + ); } function DropdownMenuSub({ ...props }: React.ComponentProps) { - return + return ; } function DropdownMenuSubTrigger({ @@ -204,7 +204,7 @@ function DropdownMenuSubTrigger({ children, ...props }: React.ComponentProps & { - inset?: boolean + inset?: boolean; }) { return ( - ) + ); } function DropdownMenuSubContent({ @@ -235,7 +235,7 @@ function DropdownMenuSubContent({ )} {...props} /> - ) + ); } export { @@ -254,4 +254,4 @@ export { DropdownMenuSub, DropdownMenuSubTrigger, DropdownMenuSubContent, -} +}; diff --git a/components/ui/metric-card.tsx b/components/ui/metric-card.tsx index 8790487..8cac8c9 100644 --- a/components/ui/metric-card.tsx +++ b/components/ui/metric-card.tsx @@ -80,11 +80,11 @@ export default function MetricCard({ const getTrendIcon = () => { if (!trend) return null; - + if (trend.value === 0) { return ; } - + return trend.isPositive !== false ? ( ) : ( @@ -94,11 +94,13 @@ export default function MetricCard({ const getTrendColor = () => { if (!trend || trend.value === 0) return "text-muted-foreground"; - return trend.isPositive !== false ? "text-green-600 dark:text-green-400" : "text-red-600 dark:text-red-400"; + return trend.isPositive !== false + ? "text-green-600 dark:text-green-400" + : "text-red-600 dark:text-red-400"; }; return ( - {/* Subtle gradient overlay */}
- +
@@ -115,9 +117,7 @@ export default function MetricCard({ {title}

{description && ( -

- {description} -

+

{description}

)}
@@ -137,13 +137,11 @@ export default function MetricCard({
-

- {value ?? "—"} -

- +

{value ?? "—"}

+ {trend && ( - - ) + ); } -export { Separator } +export { Separator }; diff --git a/components/ui/skeleton.tsx b/components/ui/skeleton.tsx index 32ea0ef..0168998 100644 --- a/components/ui/skeleton.tsx +++ b/components/ui/skeleton.tsx @@ -1,4 +1,4 @@ -import { cn } from "@/lib/utils" +import { cn } from "@/lib/utils"; function Skeleton({ className, ...props }: React.ComponentProps<"div">) { return ( @@ -7,7 +7,7 @@ function Skeleton({ className, ...props }: React.ComponentProps<"div">) { className={cn("bg-accent animate-pulse rounded-md", className)} {...props} /> - ) + ); } -export { Skeleton } +export { Skeleton }; diff --git a/components/ui/tooltip.tsx b/components/ui/tooltip.tsx index d05b152..8654d59 100644 --- a/components/ui/tooltip.tsx +++ b/components/ui/tooltip.tsx @@ -1,9 +1,9 @@ -"use client" +"use client"; -import * as React from "react" -import * as TooltipPrimitive from "@radix-ui/react-tooltip" +import * as React from "react"; +import * as TooltipPrimitive from "@radix-ui/react-tooltip"; -import { cn } from "@/lib/utils" +import { cn } from "@/lib/utils"; function TooltipProvider({ delayDuration = 0, @@ -15,7 +15,7 @@ function TooltipProvider({ delayDuration={delayDuration} {...props} /> - ) + ); } function Tooltip({ @@ -25,13 +25,13 @@ function Tooltip({ - ) + ); } function TooltipTrigger({ ...props }: React.ComponentProps) { - return + return ; } function TooltipContent({ @@ -55,7 +55,7 @@ function TooltipContent({ - ) + ); } -export { Tooltip, TooltipTrigger, TooltipContent, TooltipProvider } +export { Tooltip, TooltipTrigger, TooltipContent, TooltipProvider }; diff --git a/debug-import-status.ts b/debug-import-status.ts index 7a4eaa8..30ea327 100644 --- a/debug-import-status.ts +++ b/debug-import-status.ts @@ -1,78 +1,87 @@ -import { PrismaClient } from '@prisma/client'; -import { ProcessingStatusManager } from './lib/processingStatusManager'; +import { PrismaClient } from "@prisma/client"; +import { ProcessingStatusManager } from "./lib/processingStatusManager"; const prisma = new PrismaClient(); async function debugImportStatus() { try { - console.log('=== DEBUGGING PROCESSING STATUS (REFACTORED SYSTEM) ===\n'); - + console.log("=== DEBUGGING PROCESSING STATUS (REFACTORED SYSTEM) ===\n"); + // Get pipeline status using the new system const pipelineStatus = await ProcessingStatusManager.getPipelineStatus(); - + console.log(`Total Sessions: ${pipelineStatus.totalSessions}\n`); - + // Display status for each stage - const stages = ['CSV_IMPORT', 'TRANSCRIPT_FETCH', 'SESSION_CREATION', 'AI_ANALYSIS', 'QUESTION_EXTRACTION']; - + const stages = [ + "CSV_IMPORT", + "TRANSCRIPT_FETCH", + "SESSION_CREATION", + "AI_ANALYSIS", + "QUESTION_EXTRACTION", + ]; + for (const stage of stages) { console.log(`${stage}:`); const stageData = pipelineStatus.pipeline[stage] || {}; - + const pending = stageData.PENDING || 0; const inProgress = stageData.IN_PROGRESS || 0; const completed = stageData.COMPLETED || 0; const failed = stageData.FAILED || 0; const skipped = stageData.SKIPPED || 0; - + console.log(` PENDING: ${pending}`); console.log(` IN_PROGRESS: ${inProgress}`); console.log(` COMPLETED: ${completed}`); console.log(` FAILED: ${failed}`); console.log(` SKIPPED: ${skipped}`); - console.log(''); + console.log(""); } - + // Check Sessions vs SessionImports - console.log('=== SESSION IMPORT RELATIONSHIP ==='); + console.log("=== SESSION IMPORT RELATIONSHIP ==="); const sessionsWithImports = await prisma.session.count({ - where: { importId: { not: null } } + where: { importId: { not: null } }, }); const totalSessions = await prisma.session.count(); - + console.log(` Sessions with importId: ${sessionsWithImports}`); console.log(` Total sessions: ${totalSessions}`); - + // Show failed sessions if any const failedSessions = await ProcessingStatusManager.getFailedSessions(); if (failedSessions.length > 0) { - console.log('\n=== FAILED SESSIONS ==='); - failedSessions.slice(0, 10).forEach(failure => { - console.log(` ${failure.session.import?.externalSessionId || failure.sessionId}: ${failure.stage} - ${failure.errorMessage}`); + console.log("\n=== FAILED SESSIONS ==="); + failedSessions.slice(0, 10).forEach((failure) => { + console.log( + ` ${failure.session.import?.externalSessionId || failure.sessionId}: ${failure.stage} - ${failure.errorMessage}` + ); }); - + if (failedSessions.length > 10) { - console.log(` ... and ${failedSessions.length - 10} more failed sessions`); + console.log( + ` ... and ${failedSessions.length - 10} more failed sessions` + ); } } else { - console.log('\n✓ No failed sessions found'); + console.log("\n✓ No failed sessions found"); } - + // Show what needs processing - console.log('\n=== WHAT NEEDS PROCESSING ==='); - + console.log("\n=== WHAT NEEDS PROCESSING ==="); + for (const stage of stages) { const stageData = pipelineStatus.pipeline[stage] || {}; const pending = stageData.PENDING || 0; const failed = stageData.FAILED || 0; - + if (pending > 0 || failed > 0) { console.log(`• ${stage}: ${pending} pending, ${failed} failed`); } } - } catch (error) { - console.error('Error debugging processing status:', error); + console.error("Error debugging processing status:", error); } finally { await prisma.$disconnect(); } diff --git a/docs/dashboard-components.md b/docs/dashboard-components.md index c56bf9f..0aa0337 100644 --- a/docs/dashboard-components.md +++ b/docs/dashboard-components.md @@ -12,10 +12,10 @@ The WordCloud component visualizes categories or topics based on their frequency **Features:** -- Dynamic sizing based on frequency -- Colorful display with a pleasing color palette -- Responsive design -- Interactive hover effects +- Dynamic sizing based on frequency +- Colorful display with a pleasing color palette +- Responsive design +- Interactive hover effects ### 2. GeographicMap @@ -25,10 +25,10 @@ This component displays a world map with circles representing the number of sess **Features:** -- Interactive map using React Leaflet -- Circle sizes scaled by session count -- Tooltips showing country names and session counts -- Responsive design +- Interactive map using React Leaflet +- Circle sizes scaled by session count +- Tooltips showing country names and session counts +- Responsive design ### 3. MetricCard @@ -38,10 +38,10 @@ A modern, visually appealing card for displaying key metrics. **Features:** -- Multiple design variants (default, primary, success, warning, danger) -- Support for trend indicators -- Icons and descriptions -- Clean, modern styling +- Multiple design variants (default, primary, success, warning, danger) +- Support for trend indicators +- Icons and descriptions +- Clean, modern styling ### 4. DonutChart @@ -51,10 +51,10 @@ An enhanced donut chart with better styling and a central text display capabilit **Features:** -- Customizable colors -- Center text area for displaying summaries -- Interactive tooltips with percentages -- Well-balanced legend display +- Customizable colors +- Center text area for displaying summaries +- Interactive tooltips with percentages +- Well-balanced legend display ### 5. ResponseTimeDistribution @@ -64,10 +64,10 @@ Visualizes the distribution of response times as a histogram. **Features:** -- Color-coded bars (green for fast, yellow for medium, red for slow) -- Target time indicator -- Automatic binning of response times -- Clear labeling and scales +- Color-coded bars (green for fast, yellow for medium, red for slow) +- Target time indicator +- Automatic binning of response times +- Clear labeling and scales ## Dashboard Enhancements @@ -85,7 +85,7 @@ The dashboard has been enhanced with: ## Usage Notes -- The geographic map and response time distribution use simulated data where actual data is not available -- All components are responsive and will adjust to different screen sizes -- The dashboard automatically refreshes data when using the refresh button -- Admin users have access to additional controls at the bottom of the dashboard +- The geographic map and response time distribution use simulated data where actual data is not available +- All components are responsive and will adjust to different screen sizes +- The dashboard automatically refreshes data when using the refresh button +- Admin users have access to additional controls at the bottom of the dashboard diff --git a/docs/postgresql-migration.md b/docs/postgresql-migration.md index aa47b92..67c0e1a 100644 --- a/docs/postgresql-migration.md +++ b/docs/postgresql-migration.md @@ -17,48 +17,48 @@ Successfully migrated the livedash-node application from SQLite to PostgreSQL us #### Production/Development -- **Provider**: PostgreSQL (Neon) -- **Environment Variable**: `DATABASE_URL` -- **Connection**: Neon PostgreSQL cluster +- **Provider**: PostgreSQL (Neon) +- **Environment Variable**: `DATABASE_URL` +- **Connection**: Neon PostgreSQL cluster #### Testing -- **Provider**: PostgreSQL (Neon - separate database) -- **Environment Variable**: `DATABASE_URL_TEST` -- **Test Setup**: Automatically switches to test database during test runs +- **Provider**: PostgreSQL (Neon - separate database) +- **Environment Variable**: `DATABASE_URL_TEST` +- **Test Setup**: Automatically switches to test database during test runs ### Files Modified 1. **`prisma/schema.prisma`** -- Changed provider from `sqlite` to `postgresql` -- Updated URL to use `env("DATABASE_URL")` +- Changed provider from `sqlite` to `postgresql` +- Updated URL to use `env("DATABASE_URL")` 2. **`tests/setup.ts`** -- Added logic to use `DATABASE_URL_TEST` when available -- Ensures test isolation with separate database +- Added logic to use `DATABASE_URL_TEST` when available +- Ensures test isolation with separate database 3. **`.env`** (created) -- Contains `DATABASE_URL` for Prisma CLI operations +- Contains `DATABASE_URL` for Prisma CLI operations 4. **`.env.local`** (existing) -- Contains both `DATABASE_URL` and `DATABASE_URL_TEST` +- Contains both `DATABASE_URL` and `DATABASE_URL_TEST` ### Database Schema All existing models and relationships were preserved: -- **Company**: Multi-tenant root entity -- **User**: Authentication and authorization -- **Session**: Processed session data -- **SessionImport**: Raw CSV import data -- **Message**: Individual conversation messages -- **Question**: Normalized question storage -- **SessionQuestion**: Session-question relationships -- **AIProcessingRequest**: AI cost tracking +- **Company**: Multi-tenant root entity +- **User**: Authentication and authorization +- **Session**: Processed session data +- **SessionImport**: Raw CSV import data +- **Message**: Individual conversation messages +- **Question**: Normalized question storage +- **SessionQuestion**: Session-question relationships +- **AIProcessingRequest**: AI cost tracking ### Migration Process @@ -76,7 +76,7 @@ All existing models and relationships were preserved: ✅ **Advanced Features**: Full JSON support, arrays, advanced indexing ✅ **Test Isolation**: Separate test database prevents data conflicts ✅ **Consistency**: Same database engine across all environments -✅ **Cloud-Native**: Neon provides managed PostgreSQL with excellent DX +✅ **Cloud-Native**: Neon provides managed PostgreSQL with excellent DX ### Environment Variables @@ -103,11 +103,11 @@ if (process.env.DATABASE_URL_TEST) { All tests pass successfully: -- ✅ Environment configuration tests -- ✅ Transcript fetcher tests -- ✅ Database connection tests -- ✅ Schema validation tests -- ✅ CRUD operation tests +- ✅ Environment configuration tests +- ✅ Transcript fetcher tests +- ✅ Database connection tests +- ✅ Schema validation tests +- ✅ CRUD operation tests ### Next Steps diff --git a/docs/scheduler-fixes.md b/docs/scheduler-fixes.md index e096fc9..0765625 100644 --- a/docs/scheduler-fixes.md +++ b/docs/scheduler-fixes.md @@ -8,8 +8,8 @@ **Solution**: -- Added validation in `fetchAndStoreSessionsForAllCompanies()` to skip companies with example/invalid URLs -- Removed the invalid company record from the database using `fix_companies.js` +- Added validation in `fetchAndStoreSessionsForAllCompanies()` to skip companies with example/invalid URLs +- Removed the invalid company record from the database using `fix_companies.js` ### 2. Transcript Fetching Errors @@ -17,10 +17,10 @@ **Solution**: -- Improved error handling in `fetchTranscriptContent()` function -- Added probabilistic logging (only ~10% of errors logged) to prevent log spam -- Added timeout (10 seconds) for transcript fetching -- Made transcript fetching failures non-blocking (sessions are still created without transcript content) +- Improved error handling in `fetchTranscriptContent()` function +- Added probabilistic logging (only ~10% of errors logged) to prevent log spam +- Added timeout (10 seconds) for transcript fetching +- Made transcript fetching failures non-blocking (sessions are still created without transcript content) ### 3. CSV Fetching Errors @@ -28,8 +28,8 @@ **Solution**: -- Added URL validation to skip companies with `example.com` URLs -- Improved error logging to be more descriptive +- Added URL validation to skip companies with `example.com` URLs +- Improved error logging to be more descriptive ## Current Status @@ -42,22 +42,23 @@ After cleanup, only valid companies remain: -- **Demo Company** (`790b9233-d369-451f-b92c-f4dceb42b649`) - - CSV URL: `https://proto.notso.ai/jumbo/chats` - - Has valid authentication credentials - - 107 sessions in database +- **Demo Company** (`790b9233-d369-451f-b92c-f4dceb42b649`) + - CSV URL: `https://proto.notso.ai/jumbo/chats` + - Has valid authentication credentials + - 107 sessions in database ## Files Modified 1. **lib/csvFetcher.js** - - Added company URL validation - - Improved transcript fetching error handling - - Reduced error log verbosity +- Added company URL validation +- Improved transcript fetching error handling +- Reduced error log verbosity 2. **fix_companies.js** (cleanup script) - - Removes invalid company records - - Can be run again if needed + +- Removes invalid company records +- Can be run again if needed ## Monitoring diff --git a/docs/session-processing.md b/docs/session-processing.md index abb1a31..ccfe2ee 100644 --- a/docs/session-processing.md +++ b/docs/session-processing.md @@ -15,22 +15,22 @@ The system now includes an automated process for analyzing chat session transcri ### Session Fetching -- The system fetches session data from configured CSV URLs for each company -- Unlike the previous implementation, it now only adds sessions that don't already exist in the database -- This prevents duplicate sessions and allows for incremental updates +- The system fetches session data from configured CSV URLs for each company +- Unlike the previous implementation, it now only adds sessions that don't already exist in the database +- This prevents duplicate sessions and allows for incremental updates ### Transcript Processing -- For sessions with transcript content that haven't been processed yet, the system calls OpenAI's API -- The API analyzes the transcript and extracts the following information: - - Primary language used (ISO 639-1 code) - - Number of messages sent by the user - - Overall sentiment (positive, neutral, negative) - - Whether the conversation was escalated - - Whether HR contact was mentioned or provided - - Best-fitting category for the conversation - - Up to 5 paraphrased questions asked by the user - - A brief summary of the conversation +- For sessions with transcript content that haven't been processed yet, the system calls OpenAI's API +- The API analyzes the transcript and extracts the following information: + - Primary language used (ISO 639-1 code) + - Number of messages sent by the user + - Overall sentiment (positive, neutral, negative) + - Whether the conversation was escalated + - Whether HR contact was mentioned or provided + - Best-fitting category for the conversation + - Up to 5 paraphrased questions asked by the user + - A brief summary of the conversation ### Scheduling @@ -43,10 +43,10 @@ The system includes two schedulers: The Session model has been updated with new fields to store the processed data: -- `processed`: Boolean flag indicating whether the session has been processed -- `sentimentCategory`: String value ("positive", "neutral", "negative") from OpenAI -- `questions`: JSON array of questions asked by the user -- `summary`: Brief summary of the conversation +- `processed`: Boolean flag indicating whether the session has been processed +- `sentimentCategory`: String value ("positive", "neutral", "negative") from OpenAI +- `questions`: JSON array of questions asked by the user +- `summary`: Brief summary of the conversation ## Configuration @@ -62,9 +62,9 @@ OPENAI_API_KEY=your_api_key_here To run the application with schedulers enabled: -- Development: `npm run dev` -- Development (with schedulers disabled): `npm run dev:no-schedulers` -- Production: `npm run start` +- Development: `npm run dev` +- Development (with schedulers disabled): `npm run dev:no-schedulers` +- Production: `npm run start` Note: These commands will start a custom Next.js server with the schedulers enabled. You'll need to have an OpenAI API key set in your `.env.local` file for the session processing to work. @@ -82,5 +82,5 @@ This will process all unprocessed sessions that have transcript content. The processing logic can be customized by modifying: -- `lib/processingScheduler.ts`: Contains the OpenAI processing logic -- `scripts/process_sessions.ts`: Standalone script for manual processing +- `lib/processingScheduler.ts`: Contains the OpenAI processing logic +- `scripts/process_sessions.ts`: Standalone script for manual processing diff --git a/fix-import-status.ts b/fix-import-status.ts index 8026c99..6d72d0b 100644 --- a/fix-import-status.ts +++ b/fix-import-status.ts @@ -1,72 +1,93 @@ -import { PrismaClient, ProcessingStage, ProcessingStatus } from '@prisma/client'; -import { ProcessingStatusManager } from './lib/processingStatusManager'; +import { + PrismaClient, + ProcessingStage, + ProcessingStatus, +} from "@prisma/client"; +import { ProcessingStatusManager } from "./lib/processingStatusManager"; const prisma = new PrismaClient(); async function fixProcessingStatus() { try { - console.log('=== FIXING PROCESSING STATUS (REFACTORED SYSTEM) ===\n'); - + console.log("=== FIXING PROCESSING STATUS (REFACTORED SYSTEM) ===\n"); + // Check for any failed processing stages that might need retry const failedSessions = await ProcessingStatusManager.getFailedSessions(); - + console.log(`Found ${failedSessions.length} failed processing stages`); - + if (failedSessions.length > 0) { - console.log('\nFailed sessions by stage:'); + console.log("\nFailed sessions by stage:"); const failuresByStage: Record = {}; - - failedSessions.forEach(failure => { - failuresByStage[failure.stage] = (failuresByStage[failure.stage] || 0) + 1; + + failedSessions.forEach((failure) => { + failuresByStage[failure.stage] = + (failuresByStage[failure.stage] || 0) + 1; }); - + Object.entries(failuresByStage).forEach(([stage, count]) => { console.log(` ${stage}: ${count} failures`); }); - + // Show sample failed sessions - console.log('\nSample failed sessions:'); - failedSessions.slice(0, 5).forEach(failure => { - console.log(` ${failure.session.import?.externalSessionId || failure.sessionId}: ${failure.stage} - ${failure.errorMessage}`); + console.log("\nSample failed sessions:"); + failedSessions.slice(0, 5).forEach((failure) => { + console.log( + ` ${failure.session.import?.externalSessionId || failure.sessionId}: ${failure.stage} - ${failure.errorMessage}` + ); }); - + // Ask if user wants to reset failed stages for retry - console.log('\nTo reset failed stages for retry, you can use:'); - console.log('ProcessingStatusManager.resetStageForRetry(sessionId, stage)'); + console.log("\nTo reset failed stages for retry, you can use:"); + console.log( + "ProcessingStatusManager.resetStageForRetry(sessionId, stage)" + ); } - + // Check for sessions that might be stuck in IN_PROGRESS const stuckSessions = await prisma.sessionProcessingStatus.findMany({ where: { status: ProcessingStatus.IN_PROGRESS, startedAt: { - lt: new Date(Date.now() - 30 * 60 * 1000) // Started more than 30 minutes ago - } + lt: new Date(Date.now() - 30 * 60 * 1000), // Started more than 30 minutes ago + }, }, include: { session: { include: { - import: true - } - } - } + import: true, + }, + }, + }, }); - + if (stuckSessions.length > 0) { - console.log(`\nFound ${stuckSessions.length} sessions stuck in IN_PROGRESS state:`); - stuckSessions.forEach(stuck => { - console.log(` ${stuck.session.import?.externalSessionId || stuck.sessionId}: ${stuck.stage} (started: ${stuck.startedAt})`); + console.log( + `\nFound ${stuckSessions.length} sessions stuck in IN_PROGRESS state:` + ); + stuckSessions.forEach((stuck) => { + console.log( + ` ${stuck.session.import?.externalSessionId || stuck.sessionId}: ${stuck.stage} (started: ${stuck.startedAt})` + ); }); - - console.log('\nThese sessions may need to be reset to PENDING status for retry.'); + + console.log( + "\nThese sessions may need to be reset to PENDING status for retry." + ); } - + // Show current pipeline status - console.log('\n=== CURRENT PIPELINE STATUS ==='); + console.log("\n=== CURRENT PIPELINE STATUS ==="); const pipelineStatus = await ProcessingStatusManager.getPipelineStatus(); - - const stages = ['CSV_IMPORT', 'TRANSCRIPT_FETCH', 'SESSION_CREATION', 'AI_ANALYSIS', 'QUESTION_EXTRACTION']; - + + const stages = [ + "CSV_IMPORT", + "TRANSCRIPT_FETCH", + "SESSION_CREATION", + "AI_ANALYSIS", + "QUESTION_EXTRACTION", + ]; + for (const stage of stages) { const stageData = pipelineStatus.pipeline[stage] || {}; const pending = stageData.PENDING || 0; @@ -74,12 +95,13 @@ async function fixProcessingStatus() { const completed = stageData.COMPLETED || 0; const failed = stageData.FAILED || 0; const skipped = stageData.SKIPPED || 0; - - console.log(`${stage}: ${completed} completed, ${pending} pending, ${inProgress} in progress, ${failed} failed, ${skipped} skipped`); + + console.log( + `${stage}: ${completed} completed, ${pending} pending, ${inProgress} in progress, ${failed} failed, ${skipped} skipped` + ); } - } catch (error) { - console.error('Error fixing processing status:', error); + console.error("Error fixing processing status:", error); } finally { await prisma.$disconnect(); } diff --git a/lib/env.ts b/lib/env.ts index afe14df..0e67513 100644 --- a/lib/env.ts +++ b/lib/env.ts @@ -7,20 +7,22 @@ import { dirname, join } from "path"; * Parse environment variable value by removing quotes, comments, and trimming whitespace */ function parseEnvValue(value: string | undefined): string { - if (!value) return ''; + if (!value) return ""; // Trim whitespace let cleaned = value.trim(); // Remove inline comments (everything after #) - const commentIndex = cleaned.indexOf('#'); + const commentIndex = cleaned.indexOf("#"); if (commentIndex !== -1) { cleaned = cleaned.substring(0, commentIndex).trim(); } // Remove surrounding quotes (both single and double) - if ((cleaned.startsWith('"') && cleaned.endsWith('"')) || - (cleaned.startsWith("'") && cleaned.endsWith("'"))) { + if ( + (cleaned.startsWith('"') && cleaned.endsWith('"')) || + (cleaned.startsWith("'") && cleaned.endsWith("'")) + ) { cleaned = cleaned.slice(1, -1); } @@ -30,7 +32,10 @@ function parseEnvValue(value: string | undefined): string { /** * Parse integer with fallback to default value */ -function parseIntWithDefault(value: string | undefined, defaultValue: number): number { +function parseIntWithDefault( + value: string | undefined, + defaultValue: number +): number { const cleaned = parseEnvValue(value); if (!cleaned) return defaultValue; @@ -41,17 +46,19 @@ function parseIntWithDefault(value: string | undefined, defaultValue: number): n // Load environment variables from .env.local const __filename = fileURLToPath(import.meta.url); const __dirname = dirname(__filename); -const envPath = join(__dirname, '..', '.env.local'); +const envPath = join(__dirname, "..", ".env.local"); // Load .env.local if it exists try { - const envFile = readFileSync(envPath, 'utf8'); - const envVars = envFile.split('\n').filter(line => line.trim() && !line.startsWith('#')); + const envFile = readFileSync(envPath, "utf8"); + const envVars = envFile + .split("\n") + .filter((line) => line.trim() && !line.startsWith("#")); - envVars.forEach(line => { - const [key, ...valueParts] = line.split('='); + envVars.forEach((line) => { + const [key, ...valueParts] = line.split("="); if (key && valueParts.length > 0) { - const rawValue = valueParts.join('='); + const rawValue = valueParts.join("="); const cleanedValue = parseEnvValue(rawValue); if (!process.env[key.trim()]) { process.env[key.trim()] = cleanedValue; @@ -67,21 +74,34 @@ try { */ export const env = { // NextAuth - NEXTAUTH_URL: parseEnvValue(process.env.NEXTAUTH_URL) || 'http://localhost:3000', - NEXTAUTH_SECRET: parseEnvValue(process.env.NEXTAUTH_SECRET) || '', - NODE_ENV: parseEnvValue(process.env.NODE_ENV) || 'development', + NEXTAUTH_URL: + parseEnvValue(process.env.NEXTAUTH_URL) || "http://localhost:3000", + NEXTAUTH_SECRET: parseEnvValue(process.env.NEXTAUTH_SECRET) || "", + NODE_ENV: parseEnvValue(process.env.NODE_ENV) || "development", // OpenAI - OPENAI_API_KEY: parseEnvValue(process.env.OPENAI_API_KEY) || '', + OPENAI_API_KEY: parseEnvValue(process.env.OPENAI_API_KEY) || "", // Scheduler Configuration - SCHEDULER_ENABLED: parseEnvValue(process.env.SCHEDULER_ENABLED) === 'true', - CSV_IMPORT_INTERVAL: parseEnvValue(process.env.CSV_IMPORT_INTERVAL) || '*/15 * * * *', - IMPORT_PROCESSING_INTERVAL: parseEnvValue(process.env.IMPORT_PROCESSING_INTERVAL) || '*/5 * * * *', - IMPORT_PROCESSING_BATCH_SIZE: parseIntWithDefault(process.env.IMPORT_PROCESSING_BATCH_SIZE, 50), - SESSION_PROCESSING_INTERVAL: parseEnvValue(process.env.SESSION_PROCESSING_INTERVAL) || '0 * * * *', - SESSION_PROCESSING_BATCH_SIZE: parseIntWithDefault(process.env.SESSION_PROCESSING_BATCH_SIZE, 0), - SESSION_PROCESSING_CONCURRENCY: parseIntWithDefault(process.env.SESSION_PROCESSING_CONCURRENCY, 5), + SCHEDULER_ENABLED: parseEnvValue(process.env.SCHEDULER_ENABLED) === "true", + CSV_IMPORT_INTERVAL: + parseEnvValue(process.env.CSV_IMPORT_INTERVAL) || "*/15 * * * *", + IMPORT_PROCESSING_INTERVAL: + parseEnvValue(process.env.IMPORT_PROCESSING_INTERVAL) || "*/5 * * * *", + IMPORT_PROCESSING_BATCH_SIZE: parseIntWithDefault( + process.env.IMPORT_PROCESSING_BATCH_SIZE, + 50 + ), + SESSION_PROCESSING_INTERVAL: + parseEnvValue(process.env.SESSION_PROCESSING_INTERVAL) || "0 * * * *", + SESSION_PROCESSING_BATCH_SIZE: parseIntWithDefault( + process.env.SESSION_PROCESSING_BATCH_SIZE, + 0 + ), + SESSION_PROCESSING_CONCURRENCY: parseIntWithDefault( + process.env.SESSION_PROCESSING_CONCURRENCY, + 5 + ), // Server PORT: parseIntWithDefault(process.env.PORT, 3000), @@ -94,11 +114,11 @@ export function validateEnv(): { valid: boolean; errors: string[] } { const errors: string[] = []; if (!env.NEXTAUTH_SECRET) { - errors.push('NEXTAUTH_SECRET is required'); + errors.push("NEXTAUTH_SECRET is required"); } - if (!env.OPENAI_API_KEY && env.NODE_ENV === 'production') { - errors.push('OPENAI_API_KEY is required in production'); + if (!env.OPENAI_API_KEY && env.NODE_ENV === "production") { + errors.push("OPENAI_API_KEY is required in production"); } return { @@ -132,14 +152,14 @@ export function getSchedulerConfig() { * Log environment configuration (safe for production) */ export function logEnvConfig(): void { - console.log('[Environment] Configuration:'); + console.log("[Environment] Configuration:"); console.log(` NODE_ENV: ${env.NODE_ENV}`); console.log(` NEXTAUTH_URL: ${env.NEXTAUTH_URL}`); console.log(` SCHEDULER_ENABLED: ${env.SCHEDULER_ENABLED}`); console.log(` PORT: ${env.PORT}`); if (env.SCHEDULER_ENABLED) { - console.log(' Scheduler intervals:'); + console.log(" Scheduler intervals:"); console.log(` CSV Import: ${env.CSV_IMPORT_INTERVAL}`); console.log(` Import Processing: ${env.IMPORT_PROCESSING_INTERVAL}`); console.log(` Session Processing: ${env.SESSION_PROCESSING_INTERVAL}`); diff --git a/lib/importProcessor.ts b/lib/importProcessor.ts index b9a56a9..8b4792e 100644 --- a/lib/importProcessor.ts +++ b/lib/importProcessor.ts @@ -1,7 +1,15 @@ // SessionImport to Session processor -import { PrismaClient, SentimentCategory, SessionCategory, ProcessingStage } from "@prisma/client"; +import { + PrismaClient, + SentimentCategory, + SessionCategory, + ProcessingStage, +} from "@prisma/client"; import { getSchedulerConfig } from "./env"; -import { fetchTranscriptContent, isValidTranscriptUrl } from "./transcriptFetcher"; +import { + fetchTranscriptContent, + isValidTranscriptUrl, +} from "./transcriptFetcher"; import { ProcessingStatusManager } from "./processingStatusManager"; import cron from "node-cron"; @@ -11,25 +19,29 @@ const prisma = new PrismaClient(); * Parse European date format (DD.MM.YYYY HH:mm:ss) to JavaScript Date */ function parseEuropeanDate(dateStr: string): Date { - if (!dateStr || typeof dateStr !== 'string') { + if (!dateStr || typeof dateStr !== "string") { throw new Error(`Invalid date string: ${dateStr}`); } // Handle format: "DD.MM.YYYY HH:mm:ss" - const [datePart, timePart] = dateStr.trim().split(' '); + const [datePart, timePart] = dateStr.trim().split(" "); if (!datePart || !timePart) { - throw new Error(`Invalid date format: ${dateStr}. Expected format: DD.MM.YYYY HH:mm:ss`); + throw new Error( + `Invalid date format: ${dateStr}. Expected format: DD.MM.YYYY HH:mm:ss` + ); } - const [day, month, year] = datePart.split('.'); + const [day, month, year] = datePart.split("."); if (!day || !month || !year) { - throw new Error(`Invalid date part: ${datePart}. Expected format: DD.MM.YYYY`); + throw new Error( + `Invalid date part: ${datePart}. Expected format: DD.MM.YYYY` + ); } // Convert to ISO format: YYYY-MM-DD HH:mm:ss - const isoDateStr = `${year}-${month.padStart(2, '0')}-${day.padStart(2, '0')} ${timePart}`; + const isoDateStr = `${year}-${month.padStart(2, "0")}-${day.padStart(2, "0")} ${timePart}`; const date = new Date(isoDateStr); if (isNaN(date.getTime())) { @@ -42,13 +54,15 @@ function parseEuropeanDate(dateStr: string): Date { /** * Helper function to parse sentiment from raw string (fallback only) */ -function parseFallbackSentiment(sentimentRaw: string | null): SentimentCategory | null { +function parseFallbackSentiment( + sentimentRaw: string | null +): SentimentCategory | null { if (!sentimentRaw) return null; const sentimentStr = sentimentRaw.toLowerCase(); - if (sentimentStr.includes('positive')) { + if (sentimentStr.includes("positive")) { return SentimentCategory.POSITIVE; - } else if (sentimentStr.includes('negative')) { + } else if (sentimentStr.includes("negative")) { return SentimentCategory.NEGATIVE; } else { return SentimentCategory.NEUTRAL; @@ -60,20 +74,25 @@ function parseFallbackSentiment(sentimentRaw: string | null): SentimentCategory */ function parseFallbackBoolean(rawValue: string | null): boolean | null { if (!rawValue) return null; - return ['true', '1', 'yes', 'escalated', 'forwarded'].includes(rawValue.toLowerCase()); + return ["true", "1", "yes", "escalated", "forwarded"].includes( + rawValue.toLowerCase() + ); } /** * Parse transcript content into Message records */ -async function parseTranscriptIntoMessages(sessionId: string, transcriptContent: string): Promise { +async function parseTranscriptIntoMessages( + sessionId: string, + transcriptContent: string +): Promise { // Clear existing messages for this session await prisma.message.deleteMany({ - where: { sessionId } + where: { sessionId }, }); // Split transcript into lines and parse each message - const lines = transcriptContent.split('\n').filter(line => line.trim()); + const lines = transcriptContent.split("\n").filter((line) => line.trim()); let order = 0; for (const line of lines) { @@ -84,7 +103,7 @@ async function parseTranscriptIntoMessages(sessionId: string, transcriptContent: // Format 1: "User: message" or "Assistant: message" // Format 2: "[timestamp] User: message" or "[timestamp] Assistant: message" - let role = 'unknown'; + let role = "unknown"; let content = trimmedLine; let timestamp: Date | null = null; @@ -107,7 +126,7 @@ async function parseTranscriptIntoMessages(sessionId: string, transcriptContent: content = roleMatch[2].trim(); } else { // If no role prefix found, try to infer from context or use 'unknown' - role = 'unknown'; + role = "unknown"; } // Skip empty content @@ -127,14 +146,18 @@ async function parseTranscriptIntoMessages(sessionId: string, transcriptContent: order++; } - console.log(`[Import Processor] ✓ Parsed ${order} messages for session ${sessionId}`); + console.log( + `[Import Processor] ✓ Parsed ${order} messages for session ${sessionId}` + ); } /** * Process a single SessionImport record into a Session record * Uses new unified processing status tracking */ -async function processSingleImport(importRecord: any): Promise<{ success: boolean; error?: string }> { +async function processSingleImport( + importRecord: any +): Promise<{ success: boolean; error?: string }> { let sessionId: string | null = null; try { @@ -142,7 +165,9 @@ async function processSingleImport(importRecord: any): Promise<{ success: boolea const startTime = parseEuropeanDate(importRecord.startTimeRaw); const endTime = parseEuropeanDate(importRecord.endTimeRaw); - console.log(`[Import Processor] Processing ${importRecord.externalSessionId}: ${startTime.toISOString()} - ${endTime.toISOString()}`); + console.log( + `[Import Processor] Processing ${importRecord.externalSessionId}: ${startTime.toISOString()} - ${endTime.toISOString()}` + ); // Create or update Session record with MINIMAL processing const session = await prisma.session.upsert({ @@ -179,15 +204,27 @@ async function processSingleImport(importRecord: any): Promise<{ success: boolea await ProcessingStatusManager.initializeSession(sessionId); // Mark CSV_IMPORT as completed - await ProcessingStatusManager.completeStage(sessionId, ProcessingStage.CSV_IMPORT); + await ProcessingStatusManager.completeStage( + sessionId, + ProcessingStage.CSV_IMPORT + ); // Handle transcript fetching let transcriptContent = importRecord.rawTranscriptContent; - if (!transcriptContent && importRecord.fullTranscriptUrl && isValidTranscriptUrl(importRecord.fullTranscriptUrl)) { - await ProcessingStatusManager.startStage(sessionId, ProcessingStage.TRANSCRIPT_FETCH); + if ( + !transcriptContent && + importRecord.fullTranscriptUrl && + isValidTranscriptUrl(importRecord.fullTranscriptUrl) + ) { + await ProcessingStatusManager.startStage( + sessionId, + ProcessingStage.TRANSCRIPT_FETCH + ); - console.log(`[Import Processor] Fetching transcript for ${importRecord.externalSessionId}...`); + console.log( + `[Import Processor] Fetching transcript for ${importRecord.externalSessionId}...` + ); // Get company credentials for transcript fetching const company = await prisma.company.findUnique({ @@ -203,7 +240,9 @@ async function processSingleImport(importRecord: any): Promise<{ success: boolea if (transcriptResult.success) { transcriptContent = transcriptResult.content; - console.log(`[Import Processor] ✓ Fetched transcript for ${importRecord.externalSessionId} (${transcriptContent?.length} chars)`); + console.log( + `[Import Processor] ✓ Fetched transcript for ${importRecord.externalSessionId} (${transcriptContent?.length} chars)` + ); // Update the import record with the fetched content await prisma.sessionImport.update({ @@ -211,36 +250,61 @@ async function processSingleImport(importRecord: any): Promise<{ success: boolea data: { rawTranscriptContent: transcriptContent }, }); - await ProcessingStatusManager.completeStage(sessionId, ProcessingStage.TRANSCRIPT_FETCH, { - contentLength: transcriptContent?.length || 0, - url: importRecord.fullTranscriptUrl - }); + await ProcessingStatusManager.completeStage( + sessionId, + ProcessingStage.TRANSCRIPT_FETCH, + { + contentLength: transcriptContent?.length || 0, + url: importRecord.fullTranscriptUrl, + } + ); } else { - console.log(`[Import Processor] ⚠️ Failed to fetch transcript for ${importRecord.externalSessionId}: ${transcriptResult.error}`); - await ProcessingStatusManager.failStage(sessionId, ProcessingStage.TRANSCRIPT_FETCH, transcriptResult.error || 'Unknown error'); + console.log( + `[Import Processor] ⚠️ Failed to fetch transcript for ${importRecord.externalSessionId}: ${transcriptResult.error}` + ); + await ProcessingStatusManager.failStage( + sessionId, + ProcessingStage.TRANSCRIPT_FETCH, + transcriptResult.error || "Unknown error" + ); } } else if (!importRecord.fullTranscriptUrl) { // No transcript URL available - skip this stage - await ProcessingStatusManager.skipStage(sessionId, ProcessingStage.TRANSCRIPT_FETCH, 'No transcript URL provided'); + await ProcessingStatusManager.skipStage( + sessionId, + ProcessingStage.TRANSCRIPT_FETCH, + "No transcript URL provided" + ); } else { // Transcript already fetched - await ProcessingStatusManager.completeStage(sessionId, ProcessingStage.TRANSCRIPT_FETCH, { - contentLength: transcriptContent?.length || 0, - source: 'already_fetched' - }); + await ProcessingStatusManager.completeStage( + sessionId, + ProcessingStage.TRANSCRIPT_FETCH, + { + contentLength: transcriptContent?.length || 0, + source: "already_fetched", + } + ); } // Handle session creation (parse messages) - await ProcessingStatusManager.startStage(sessionId, ProcessingStage.SESSION_CREATION); + await ProcessingStatusManager.startStage( + sessionId, + ProcessingStage.SESSION_CREATION + ); if (transcriptContent) { await parseTranscriptIntoMessages(sessionId, transcriptContent); } - await ProcessingStatusManager.completeStage(sessionId, ProcessingStage.SESSION_CREATION, { - hasTranscript: !!transcriptContent, - transcriptLength: transcriptContent?.length || 0 - }); + await ProcessingStatusManager.completeStage( + sessionId, + ProcessingStage.SESSION_CREATION, + { + hasTranscript: !!transcriptContent, + transcriptLength: transcriptContent?.length || 0, + } + ); return { success: true }; } catch (error) { @@ -249,13 +313,31 @@ async function processSingleImport(importRecord: any): Promise<{ success: boolea // Mark the current stage as failed if we have a sessionId if (sessionId) { // Determine which stage failed based on the error - if (errorMessage.includes('transcript') || errorMessage.includes('fetch')) { - await ProcessingStatusManager.failStage(sessionId, ProcessingStage.TRANSCRIPT_FETCH, errorMessage); - } else if (errorMessage.includes('message') || errorMessage.includes('parse')) { - await ProcessingStatusManager.failStage(sessionId, ProcessingStage.SESSION_CREATION, errorMessage); + if ( + errorMessage.includes("transcript") || + errorMessage.includes("fetch") + ) { + await ProcessingStatusManager.failStage( + sessionId, + ProcessingStage.TRANSCRIPT_FETCH, + errorMessage + ); + } else if ( + errorMessage.includes("message") || + errorMessage.includes("parse") + ) { + await ProcessingStatusManager.failStage( + sessionId, + ProcessingStage.SESSION_CREATION, + errorMessage + ); } else { // General failure - mark CSV_IMPORT as failed - await ProcessingStatusManager.failStage(sessionId, ProcessingStage.CSV_IMPORT, errorMessage); + await ProcessingStatusManager.failStage( + sessionId, + ProcessingStage.CSV_IMPORT, + errorMessage + ); } } @@ -270,8 +352,10 @@ async function processSingleImport(importRecord: any): Promise<{ success: boolea * Process unprocessed SessionImport records into Session records * Uses new processing status system to find imports that need processing */ -export async function processQueuedImports(batchSize: number = 50): Promise { - console.log('[Import Processor] Starting to process unprocessed imports...'); +export async function processQueuedImports( + batchSize: number = 50 +): Promise { + console.log("[Import Processor] Starting to process unprocessed imports..."); let totalSuccessCount = 0; let totalErrorCount = 0; @@ -285,20 +369,24 @@ export async function processQueuedImports(batchSize: number = 50): Promise { diff --git a/lib/metrics.ts b/lib/metrics.ts index db7d686..d6bb375 100644 --- a/lib/metrics.ts +++ b/lib/metrics.ts @@ -350,16 +350,16 @@ export function sessionMetrics( const wordCounts: { [key: string]: number } = {}; let alerts = 0; - // New metrics variables - const hourlySessionCounts: { [hour: string]: number } = {}; - let resolvedChatsCount = 0; - const questionCounts: { [question: string]: number } = {}; + // New metrics variables + const hourlySessionCounts: { [hour: string]: number } = {}; + let resolvedChatsCount = 0; + const questionCounts: { [question: string]: number } = {}; for (const session of sessions) { // Track hourly usage for peak time calculation if (session.startTime) { const hour = new Date(session.startTime).getHours(); - const hourKey = `${hour.toString().padStart(2, '0')}:00`; + const hourKey = `${hour.toString().padStart(2, "0")}:00`; hourlySessionCounts[hourKey] = (hourlySessionCounts[hourKey] || 0) + 1; } @@ -493,12 +493,16 @@ export function sessionMetrics( // 1. Extract questions from user messages (if available) if (session.messages) { session.messages - .filter(msg => msg.role === 'User') - .forEach(msg => { + .filter((msg) => msg.role === "User") + .forEach((msg) => { const content = msg.content.trim(); // Simple heuristic: if message ends with ? or contains question words, treat as question - if (content.endsWith('?') || - /\b(what|when|where|why|how|who|which|can|could|would|will|is|are|do|does|did)\b/i.test(content)) { + if ( + content.endsWith("?") || + /\b(what|when|where|why|how|who|which|can|could|would|will|is|are|do|does|did)\b/i.test( + content + ) + ) { questionCounts[content] = (questionCounts[content] || 0) + 1; } }); @@ -507,8 +511,12 @@ export function sessionMetrics( // 3. Extract questions from initial message as fallback if (session.initialMsg) { const content = session.initialMsg.trim(); - if (content.endsWith('?') || - /\b(what|when|where|why|how|who|which|can|could|would|will|is|are|do|does|did)\b/i.test(content)) { + if ( + content.endsWith("?") || + /\b(what|when|where|why|how|who|which|can|could|would|will|is|are|do|does|did)\b/i.test( + content + ) + ) { questionCounts[content] = (questionCounts[content] || 0) + 1; } } @@ -580,20 +588,23 @@ export function sessionMetrics( // Calculate new metrics // 1. Average Daily Costs (euros) - const avgDailyCosts = numDaysWithSessions > 0 ? totalTokensEur / numDaysWithSessions : 0; + const avgDailyCosts = + numDaysWithSessions > 0 ? totalTokensEur / numDaysWithSessions : 0; // 2. Peak Usage Time let peakUsageTime = "N/A"; if (Object.keys(hourlySessionCounts).length > 0) { - const peakHour = Object.entries(hourlySessionCounts) - .sort(([, a], [, b]) => b - a)[0][0]; - const peakHourNum = parseInt(peakHour.split(':')[0]); + const peakHour = Object.entries(hourlySessionCounts).sort( + ([, a], [, b]) => b - a + )[0][0]; + const peakHourNum = parseInt(peakHour.split(":")[0]); const endHour = (peakHourNum + 1) % 24; - peakUsageTime = `${peakHour}-${endHour.toString().padStart(2, '0')}:00`; + peakUsageTime = `${peakHour}-${endHour.toString().padStart(2, "0")}:00`; } // 3. Resolved Chats Percentage - const resolvedChatsPercentage = totalSessions > 0 ? (resolvedChatsCount / totalSessions) * 100 : 0; + const resolvedChatsPercentage = + totalSessions > 0 ? (resolvedChatsCount / totalSessions) * 100 : 0; // 4. Top 5 Asked Questions const topQuestions: TopQuestion[] = Object.entries(questionCounts) diff --git a/lib/processingScheduler.ts b/lib/processingScheduler.ts index d90db9b..088ebbc 100644 --- a/lib/processingScheduler.ts +++ b/lib/processingScheduler.ts @@ -1,6 +1,11 @@ // Enhanced session processing scheduler with AI cost tracking and question management import cron from "node-cron"; -import { PrismaClient, SentimentCategory, SessionCategory, ProcessingStage } from "@prisma/client"; +import { + PrismaClient, + SentimentCategory, + SessionCategory, + ProcessingStage, +} from "@prisma/client"; import fetch from "node-fetch"; import { getSchedulerConfig } from "./schedulerConfig"; import { ProcessingStatusManager } from "./processingStatusManager"; @@ -44,10 +49,10 @@ async function getCurrentModelPricing(modelName: string): Promise<{ effectiveFrom: { lte: new Date() }, OR: [ { effectiveUntil: null }, - { effectiveUntil: { gte: new Date() } } - ] + { effectiveUntil: { gte: new Date() } }, + ], }, - orderBy: { effectiveFrom: 'desc' }, + orderBy: { effectiveFrom: "desc" }, take: 1, }, }, @@ -69,7 +74,20 @@ interface ProcessedData { sentiment: "POSITIVE" | "NEUTRAL" | "NEGATIVE"; escalated: boolean; forwarded_hr: boolean; - category: "SCHEDULE_HOURS" | "LEAVE_VACATION" | "SICK_LEAVE_RECOVERY" | "SALARY_COMPENSATION" | "CONTRACT_HOURS" | "ONBOARDING" | "OFFBOARDING" | "WORKWEAR_STAFF_PASS" | "TEAM_CONTACTS" | "PERSONAL_QUESTIONS" | "ACCESS_LOGIN" | "SOCIAL_QUESTIONS" | "UNRECOGNIZED_OTHER"; + category: + | "SCHEDULE_HOURS" + | "LEAVE_VACATION" + | "SICK_LEAVE_RECOVERY" + | "SALARY_COMPENSATION" + | "CONTRACT_HOURS" + | "ONBOARDING" + | "OFFBOARDING" + | "WORKWEAR_STAFF_PASS" + | "TEAM_CONTACTS" + | "PERSONAL_QUESTIONS" + | "ACCESS_LOGIN" + | "SOCIAL_QUESTIONS" + | "UNRECOGNIZED_OTHER"; questions: string[]; summary: string; session_id: string; @@ -87,7 +105,7 @@ interface ProcessingResult { async function recordAIProcessingRequest( sessionId: string, openaiResponse: any, - processingType: string = 'session_analysis' + processingType: string = "session_analysis" ): Promise { const usage = openaiResponse.usage; const model = openaiResponse.model; @@ -97,14 +115,15 @@ async function recordAIProcessingRequest( // Fallback pricing if not found in database const fallbackPricing = { - promptTokenCost: 0.00001, // $10.00 per 1M tokens (gpt-4-turbo rate) - completionTokenCost: 0.00003, // $30.00 per 1M tokens + promptTokenCost: 0.00001, // $10.00 per 1M tokens (gpt-4-turbo rate) + completionTokenCost: 0.00003, // $30.00 per 1M tokens }; const finalPricing = pricing || fallbackPricing; const promptCost = usage.prompt_tokens * finalPricing.promptTokenCost; - const completionCost = usage.completion_tokens * finalPricing.completionTokenCost; + const completionCost = + usage.completion_tokens * finalPricing.completionTokenCost; const totalCostUsd = promptCost + completionCost; const totalCostEur = totalCostUsd * USD_TO_EUR_RATE; @@ -123,10 +142,14 @@ async function recordAIProcessingRequest( // Detailed breakdown cachedTokens: usage.prompt_tokens_details?.cached_tokens || null, audioTokensPrompt: usage.prompt_tokens_details?.audio_tokens || null, - reasoningTokens: usage.completion_tokens_details?.reasoning_tokens || null, - audioTokensCompletion: usage.completion_tokens_details?.audio_tokens || null, - acceptedPredictionTokens: usage.completion_tokens_details?.accepted_prediction_tokens || null, - rejectedPredictionTokens: usage.completion_tokens_details?.rejected_prediction_tokens || null, + reasoningTokens: + usage.completion_tokens_details?.reasoning_tokens || null, + audioTokensCompletion: + usage.completion_tokens_details?.audio_tokens || null, + acceptedPredictionTokens: + usage.completion_tokens_details?.accepted_prediction_tokens || null, + rejectedPredictionTokens: + usage.completion_tokens_details?.rejected_prediction_tokens || null, promptTokenCost: finalPricing.promptTokenCost, completionTokenCost: finalPricing.completionTokenCost, @@ -135,7 +158,7 @@ async function recordAIProcessingRequest( processingType, success: true, completedAt: new Date(), - } + }, }); } @@ -150,7 +173,7 @@ async function recordFailedAIProcessingRequest( await prisma.aIProcessingRequest.create({ data: { sessionId, - model: 'unknown', + model: "unknown", promptTokens: 0, completionTokens: 0, totalTokens: 0, @@ -161,17 +184,20 @@ async function recordFailedAIProcessingRequest( success: false, errorMessage, completedAt: new Date(), - } + }, }); } /** * Process questions into separate Question and SessionQuestion tables */ -async function processQuestions(sessionId: string, questions: string[]): Promise { +async function processQuestions( + sessionId: string, + questions: string[] +): Promise { // Clear existing questions for this session await prisma.sessionQuestion.deleteMany({ - where: { sessionId } + where: { sessionId }, }); // Process each question @@ -183,7 +209,7 @@ async function processQuestions(sessionId: string, questions: string[]): Promise const question = await prisma.question.upsert({ where: { content: questionText.trim() }, create: { content: questionText.trim() }, - update: {} + update: {}, }); // Link to session @@ -191,8 +217,8 @@ async function processQuestions(sessionId: string, questions: string[]): Promise data: { sessionId, questionId: question.id, - order: index - } + order: index, + }, }); } } @@ -204,8 +230,8 @@ async function calculateMessagesSent(sessionId: string): Promise { const userMessageCount = await prisma.message.count({ where: { sessionId, - role: { in: ['user', 'User'] } // Handle both cases - } + role: { in: ["user", "User"] }, // Handle both cases + }, }); return userMessageCount; } @@ -213,10 +239,13 @@ async function calculateMessagesSent(sessionId: string): Promise { /** * Calculate endTime from latest Message timestamp */ -async function calculateEndTime(sessionId: string, fallbackEndTime: Date): Promise { +async function calculateEndTime( + sessionId: string, + fallbackEndTime: Date +): Promise { const latestMessage = await prisma.message.findFirst({ where: { sessionId }, - orderBy: { timestamp: 'desc' } + orderBy: { timestamp: "desc" }, }); return latestMessage?.timestamp || fallbackEndTime; @@ -225,7 +254,11 @@ async function calculateEndTime(sessionId: string, fallbackEndTime: Date): Promi /** * Processes a session transcript using OpenAI API */ -async function processTranscriptWithOpenAI(sessionId: string, transcript: string, companyId: string): Promise { +async function processTranscriptWithOpenAI( + sessionId: string, + transcript: string, + companyId: string +): Promise { if (!OPENAI_API_KEY) { throw new Error("OPENAI_API_KEY environment variable is not set"); } @@ -293,7 +326,11 @@ async function processTranscriptWithOpenAI(sessionId: string, transcript: string const openaiResponse: any = await response.json(); // Record the AI processing request for cost tracking - await recordAIProcessingRequest(sessionId, openaiResponse, 'session_analysis'); + await recordAIProcessingRequest( + sessionId, + openaiResponse, + "session_analysis" + ); const processedData = JSON.parse(openaiResponse.choices[0].message.content); @@ -305,7 +342,7 @@ async function processTranscriptWithOpenAI(sessionId: string, transcript: string // Record failed request await recordFailedAIProcessingRequest( sessionId, - 'session_analysis', + "session_analysis", error instanceof Error ? error.message : String(error) ); @@ -319,8 +356,14 @@ async function processTranscriptWithOpenAI(sessionId: string, transcript: string */ function validateOpenAIResponse(data: any): void { const requiredFields = [ - "language", "sentiment", "escalated", "forwarded_hr", - "category", "questions", "summary", "session_id" + "language", + "sentiment", + "escalated", + "forwarded_hr", + "category", + "questions", + "summary", + "session_id", ]; for (const field of requiredFields) { @@ -331,11 +374,15 @@ function validateOpenAIResponse(data: any): void { // Validate field types and values if (typeof data.language !== "string" || !/^[a-z]{2}$/.test(data.language)) { - throw new Error("Invalid language format. Expected ISO 639-1 code (e.g., 'en')"); + throw new Error( + "Invalid language format. Expected ISO 639-1 code (e.g., 'en')" + ); } if (!["POSITIVE", "NEUTRAL", "NEGATIVE"].includes(data.sentiment)) { - throw new Error("Invalid sentiment. Expected 'POSITIVE', 'NEUTRAL', or 'NEGATIVE'"); + throw new Error( + "Invalid sentiment. Expected 'POSITIVE', 'NEUTRAL', or 'NEGATIVE'" + ); } if (typeof data.escalated !== "boolean") { @@ -347,22 +394,39 @@ function validateOpenAIResponse(data: any): void { } const validCategories = [ - "SCHEDULE_HOURS", "LEAVE_VACATION", "SICK_LEAVE_RECOVERY", "SALARY_COMPENSATION", - "CONTRACT_HOURS", "ONBOARDING", "OFFBOARDING", "WORKWEAR_STAFF_PASS", - "TEAM_CONTACTS", "PERSONAL_QUESTIONS", "ACCESS_LOGIN", "SOCIAL_QUESTIONS", - "UNRECOGNIZED_OTHER" + "SCHEDULE_HOURS", + "LEAVE_VACATION", + "SICK_LEAVE_RECOVERY", + "SALARY_COMPENSATION", + "CONTRACT_HOURS", + "ONBOARDING", + "OFFBOARDING", + "WORKWEAR_STAFF_PASS", + "TEAM_CONTACTS", + "PERSONAL_QUESTIONS", + "ACCESS_LOGIN", + "SOCIAL_QUESTIONS", + "UNRECOGNIZED_OTHER", ]; if (!validCategories.includes(data.category)) { - throw new Error(`Invalid category. Expected one of: ${validCategories.join(", ")}`); + throw new Error( + `Invalid category. Expected one of: ${validCategories.join(", ")}` + ); } if (!Array.isArray(data.questions)) { throw new Error("Invalid questions. Expected array of strings"); } - if (typeof data.summary !== "string" || data.summary.length < 10 || data.summary.length > 300) { - throw new Error("Invalid summary. Expected string between 10-300 characters"); + if ( + typeof data.summary !== "string" || + data.summary.length < 10 || + data.summary.length > 300 + ) { + throw new Error( + "Invalid summary. Expected string between 10-300 characters" + ); } if (typeof data.session_id !== "string") { @@ -384,31 +448,42 @@ async function processSingleSession(session: any): Promise { try { // Mark AI analysis as started - await ProcessingStatusManager.startStage(session.id, ProcessingStage.AI_ANALYSIS); + await ProcessingStatusManager.startStage( + session.id, + ProcessingStage.AI_ANALYSIS + ); // Convert messages back to transcript format for OpenAI processing const transcript = session.messages - .map((msg: any) => - `[${new Date(msg.timestamp) - .toLocaleString("en-GB", { - day: "2-digit", - month: "2-digit", - year: "numeric", - hour: "2-digit", - minute: "2-digit", - second: "2-digit", - }) - .replace(",", "")}] ${msg.role}: ${msg.content}` + .map( + (msg: any) => + `[${new Date(msg.timestamp) + .toLocaleString("en-GB", { + day: "2-digit", + month: "2-digit", + year: "numeric", + hour: "2-digit", + minute: "2-digit", + second: "2-digit", + }) + .replace(",", "")}] ${msg.role}: ${msg.content}` ) .join("\n"); - const processedData = await processTranscriptWithOpenAI(session.id, transcript, session.companyId); + const processedData = await processTranscriptWithOpenAI( + session.id, + transcript, + session.companyId + ); // Calculate messagesSent from actual Message records const messagesSent = await calculateMessagesSent(session.id); // Calculate endTime from latest Message timestamp - const calculatedEndTime = await calculateEndTime(session.id, session.endTime); + const calculatedEndTime = await calculateEndTime( + session.id, + session.endTime + ); // Update the session with processed data await prisma.session.update({ @@ -426,23 +501,34 @@ async function processSingleSession(session: any): Promise { }); // Mark AI analysis as completed - await ProcessingStatusManager.completeStage(session.id, ProcessingStage.AI_ANALYSIS, { - language: processedData.language, - sentiment: processedData.sentiment, - category: processedData.category, - questionsCount: processedData.questions.length - }); + await ProcessingStatusManager.completeStage( + session.id, + ProcessingStage.AI_ANALYSIS, + { + language: processedData.language, + sentiment: processedData.sentiment, + category: processedData.category, + questionsCount: processedData.questions.length, + } + ); // Start question extraction stage - await ProcessingStatusManager.startStage(session.id, ProcessingStage.QUESTION_EXTRACTION); + await ProcessingStatusManager.startStage( + session.id, + ProcessingStage.QUESTION_EXTRACTION + ); // Process questions into separate tables await processQuestions(session.id, processedData.questions); // Mark question extraction as completed - await ProcessingStatusManager.completeStage(session.id, ProcessingStage.QUESTION_EXTRACTION, { - questionsProcessed: processedData.questions.length - }); + await ProcessingStatusManager.completeStage( + session.id, + ProcessingStage.QUESTION_EXTRACTION, + { + questionsProcessed: processedData.questions.length, + } + ); return { sessionId: session.id, @@ -467,7 +553,10 @@ async function processSingleSession(session: any): Promise { /** * Process sessions in parallel with concurrency limit */ -async function processSessionsInParallel(sessions: any[], maxConcurrency: number = 5): Promise { +async function processSessionsInParallel( + sessions: any[], + maxConcurrency: number = 5 +): Promise { const results: Promise[] = []; const executing: Promise[] = []; @@ -486,7 +575,7 @@ async function processSessionsInParallel(sessions: any[], maxConcurrency: number if (executing.length >= maxConcurrency) { await Promise.race(executing); - const completedIndex = executing.findIndex(p => p === promise); + const completedIndex = executing.findIndex((p) => p === promise); if (completedIndex !== -1) { executing.splice(completedIndex, 1); } @@ -499,27 +588,37 @@ async function processSessionsInParallel(sessions: any[], maxConcurrency: number /** * Process unprocessed sessions using the new processing status system */ -export async function processUnprocessedSessions(batchSize: number | null = null, maxConcurrency: number = 5): Promise { - process.stdout.write("[ProcessingScheduler] Starting to process sessions needing AI analysis...\n"); - - // Get sessions that need AI processing using the new status system - const sessionsNeedingAI = await ProcessingStatusManager.getSessionsNeedingProcessing( - ProcessingStage.AI_ANALYSIS, - batchSize || 50 +export async function processUnprocessedSessions( + batchSize: number | null = null, + maxConcurrency: number = 5 +): Promise { + process.stdout.write( + "[ProcessingScheduler] Starting to process sessions needing AI analysis...\n" ); + // Get sessions that need AI processing using the new status system + const sessionsNeedingAI = + await ProcessingStatusManager.getSessionsNeedingProcessing( + ProcessingStage.AI_ANALYSIS, + batchSize || 50 + ); + if (sessionsNeedingAI.length === 0) { - process.stdout.write("[ProcessingScheduler] No sessions found requiring AI processing.\n"); + process.stdout.write( + "[ProcessingScheduler] No sessions found requiring AI processing.\n" + ); return; } // Get session IDs that need processing - const sessionIds = sessionsNeedingAI.map(statusRecord => statusRecord.sessionId); + const sessionIds = sessionsNeedingAI.map( + (statusRecord) => statusRecord.sessionId + ); // Fetch full session data with messages const sessionsToProcess = await prisma.session.findMany({ where: { - id: { in: sessionIds } + id: { in: sessionIds }, }, include: { messages: { @@ -534,7 +633,9 @@ export async function processUnprocessedSessions(batchSize: number | null = null ); if (sessionsWithMessages.length === 0) { - process.stdout.write("[ProcessingScheduler] No sessions with messages found requiring processing.\n"); + process.stdout.write( + "[ProcessingScheduler] No sessions with messages found requiring processing.\n" + ); return; } @@ -543,16 +644,25 @@ export async function processUnprocessedSessions(batchSize: number | null = null ); const startTime = Date.now(); - const results = await processSessionsInParallel(sessionsWithMessages, maxConcurrency); + const results = await processSessionsInParallel( + sessionsWithMessages, + maxConcurrency + ); const endTime = Date.now(); const successCount = results.filter((r) => r.success).length; const errorCount = results.filter((r) => !r.success).length; process.stdout.write("[ProcessingScheduler] Session processing complete.\n"); - process.stdout.write(`[ProcessingScheduler] Successfully processed: ${successCount} sessions.\n`); - process.stdout.write(`[ProcessingScheduler] Failed to process: ${errorCount} sessions.\n`); - process.stdout.write(`[ProcessingScheduler] Total processing time: ${((endTime - startTime) / 1000).toFixed(2)}s\n`); + process.stdout.write( + `[ProcessingScheduler] Successfully processed: ${successCount} sessions.\n` + ); + process.stdout.write( + `[ProcessingScheduler] Failed to process: ${errorCount} sessions.\n` + ); + process.stdout.write( + `[ProcessingScheduler] Total processing time: ${((endTime - startTime) / 1000).toFixed(2)}s\n` + ); } /** @@ -576,11 +686,11 @@ export async function getAIProcessingCosts(): Promise<{ }); const successfulRequests = await prisma.aIProcessingRequest.count({ - where: { success: true } + where: { success: true }, }); const failedRequests = await prisma.aIProcessingRequest.count({ - where: { success: false } + where: { success: false }, }); return { @@ -599,22 +709,32 @@ export function startProcessingScheduler(): void { const config = getSchedulerConfig(); if (!config.enabled) { - console.log('[Processing Scheduler] Disabled via configuration'); + console.log("[Processing Scheduler] Disabled via configuration"); return; } - console.log(`[Processing Scheduler] Starting with interval: ${config.sessionProcessing.interval}`); - console.log(`[Processing Scheduler] Batch size: ${config.sessionProcessing.batchSize === 0 ? 'unlimited' : config.sessionProcessing.batchSize}`); - console.log(`[Processing Scheduler] Concurrency: ${config.sessionProcessing.concurrency}`); + console.log( + `[Processing Scheduler] Starting with interval: ${config.sessionProcessing.interval}` + ); + console.log( + `[Processing Scheduler] Batch size: ${config.sessionProcessing.batchSize === 0 ? "unlimited" : config.sessionProcessing.batchSize}` + ); + console.log( + `[Processing Scheduler] Concurrency: ${config.sessionProcessing.concurrency}` + ); cron.schedule(config.sessionProcessing.interval, async () => { try { await processUnprocessedSessions( - config.sessionProcessing.batchSize === 0 ? null : config.sessionProcessing.batchSize, + config.sessionProcessing.batchSize === 0 + ? null + : config.sessionProcessing.batchSize, config.sessionProcessing.concurrency ); } catch (error) { - process.stderr.write(`[ProcessingScheduler] Error in scheduler: ${error}\n`); + process.stderr.write( + `[ProcessingScheduler] Error in scheduler: ${error}\n` + ); } }); } diff --git a/lib/processingStatusManager.ts b/lib/processingStatusManager.ts index 1237b23..84be140 100644 --- a/lib/processingStatusManager.ts +++ b/lib/processingStatusManager.ts @@ -1,4 +1,8 @@ -import { PrismaClient, ProcessingStage, ProcessingStatus } from '@prisma/client'; +import { + PrismaClient, + ProcessingStage, + ProcessingStatus, +} from "@prisma/client"; const prisma = new PrismaClient(); @@ -6,7 +10,6 @@ const prisma = new PrismaClient(); * Centralized processing status management */ export class ProcessingStatusManager { - /** * Initialize processing status for a session with all stages set to PENDING */ @@ -21,7 +24,7 @@ export class ProcessingStatusManager { // Create all processing status records for this session await prisma.sessionProcessingStatus.createMany({ - data: stages.map(stage => ({ + data: stages.map((stage) => ({ sessionId, stage, status: ProcessingStatus.PENDING, @@ -40,7 +43,7 @@ export class ProcessingStatusManager { ): Promise { await prisma.sessionProcessingStatus.upsert({ where: { - sessionId_stage: { sessionId, stage } + sessionId_stage: { sessionId, stage }, }, update: { status: ProcessingStatus.IN_PROGRESS, @@ -68,7 +71,7 @@ export class ProcessingStatusManager { ): Promise { await prisma.sessionProcessingStatus.upsert({ where: { - sessionId_stage: { sessionId, stage } + sessionId_stage: { sessionId, stage }, }, update: { status: ProcessingStatus.COMPLETED, @@ -98,7 +101,7 @@ export class ProcessingStatusManager { ): Promise { await prisma.sessionProcessingStatus.upsert({ where: { - sessionId_stage: { sessionId, stage } + sessionId_stage: { sessionId, stage }, }, update: { status: ProcessingStatus.FAILED, @@ -130,7 +133,7 @@ export class ProcessingStatusManager { ): Promise { await prisma.sessionProcessingStatus.upsert({ where: { - sessionId_stage: { sessionId, stage } + sessionId_stage: { sessionId, stage }, }, update: { status: ProcessingStatus.SKIPPED, @@ -154,7 +157,7 @@ export class ProcessingStatusManager { static async getSessionStatus(sessionId: string) { return await prisma.sessionProcessingStatus.findMany({ where: { sessionId }, - orderBy: { stage: 'asc' }, + orderBy: { stage: "asc" }, }); } @@ -179,7 +182,7 @@ export class ProcessingStatusManager { }, }, take: limit, - orderBy: { session: { createdAt: 'asc' } }, + orderBy: { session: { createdAt: "asc" } }, }); } @@ -189,7 +192,7 @@ export class ProcessingStatusManager { static async getPipelineStatus() { // Get counts by stage and status const statusCounts = await prisma.sessionProcessingStatus.groupBy({ - by: ['stage', 'status'], + by: ["stage", "status"], _count: { id: true }, }); @@ -233,17 +236,20 @@ export class ProcessingStatusManager { }, }, }, - orderBy: { completedAt: 'desc' }, + orderBy: { completedAt: "desc" }, }); } /** * Reset a failed stage for retry */ - static async resetStageForRetry(sessionId: string, stage: ProcessingStage): Promise { + static async resetStageForRetry( + sessionId: string, + stage: ProcessingStage + ): Promise { await prisma.sessionProcessingStatus.update({ where: { - sessionId_stage: { sessionId, stage } + sessionId_stage: { sessionId, stage }, }, data: { status: ProcessingStatus.PENDING, @@ -257,10 +263,13 @@ export class ProcessingStatusManager { /** * Check if a session has completed a specific stage */ - static async hasCompletedStage(sessionId: string, stage: ProcessingStage): Promise { + static async hasCompletedStage( + sessionId: string, + stage: ProcessingStage + ): Promise { const status = await prisma.sessionProcessingStatus.findUnique({ where: { - sessionId_stage: { sessionId, stage } + sessionId_stage: { sessionId, stage }, }, }); @@ -270,7 +279,10 @@ export class ProcessingStatusManager { /** * Check if a session is ready for a specific stage (previous stages completed) */ - static async isReadyForStage(sessionId: string, stage: ProcessingStage): Promise { + static async isReadyForStage( + sessionId: string, + stage: ProcessingStage + ): Promise { const stageOrder = [ ProcessingStage.CSV_IMPORT, ProcessingStage.TRANSCRIPT_FETCH, diff --git a/lib/scheduler.ts b/lib/scheduler.ts index 6c40444..c2fe92c 100644 --- a/lib/scheduler.ts +++ b/lib/scheduler.ts @@ -8,11 +8,13 @@ export function startCsvImportScheduler() { const config = getSchedulerConfig(); if (!config.enabled) { - console.log('[CSV Import Scheduler] Disabled via configuration'); + console.log("[CSV Import Scheduler] Disabled via configuration"); return; } - console.log(`[CSV Import Scheduler] Starting with interval: ${config.csvImport.interval}`); + console.log( + `[CSV Import Scheduler] Starting with interval: ${config.csvImport.interval}` + ); cron.schedule(config.csvImport.interval, async () => { const companies = await prisma.company.findMany(); diff --git a/lib/schedulerConfig.ts b/lib/schedulerConfig.ts index d8e7e46..0931c2b 100644 --- a/lib/schedulerConfig.ts +++ b/lib/schedulerConfig.ts @@ -1,7 +1,10 @@ // Legacy scheduler configuration - now uses centralized env management // This file is kept for backward compatibility but delegates to lib/env.ts -import { getSchedulerConfig as getEnvSchedulerConfig, logEnvConfig } from "./env"; +import { + getSchedulerConfig as getEnvSchedulerConfig, + logEnvConfig, +} from "./env"; export interface SchedulerConfig { enabled: boolean; diff --git a/lib/transcriptFetcher.ts b/lib/transcriptFetcher.ts index 926f0d4..73e51bc 100644 --- a/lib/transcriptFetcher.ts +++ b/lib/transcriptFetcher.ts @@ -23,7 +23,7 @@ export async function fetchTranscriptContent( if (!url || !url.trim()) { return { success: false, - error: 'No transcript URL provided', + error: "No transcript URL provided", }; } @@ -34,7 +34,7 @@ export async function fetchTranscriptContent( : undefined; const headers: Record = { - 'User-Agent': 'LiveDash-Transcript-Fetcher/1.0', + "User-Agent": "LiveDash-Transcript-Fetcher/1.0", }; if (authHeader) { @@ -46,7 +46,7 @@ export async function fetchTranscriptContent( const timeoutId = setTimeout(() => controller.abort(), 30000); // 30 second timeout const response = await fetch(url, { - method: 'GET', + method: "GET", headers, signal: controller.signal, }); @@ -65,7 +65,7 @@ export async function fetchTranscriptContent( if (!content || content.trim().length === 0) { return { success: false, - error: 'Empty transcript content', + error: "Empty transcript content", }; } @@ -73,29 +73,28 @@ export async function fetchTranscriptContent( success: true, content: content.trim(), }; - } catch (error) { const errorMessage = error instanceof Error ? error.message : String(error); // Handle common network errors - if (errorMessage.includes('ENOTFOUND')) { + if (errorMessage.includes("ENOTFOUND")) { return { success: false, - error: 'Domain not found', + error: "Domain not found", }; } - if (errorMessage.includes('ECONNREFUSED')) { + if (errorMessage.includes("ECONNREFUSED")) { return { success: false, - error: 'Connection refused', + error: "Connection refused", }; } - if (errorMessage.includes('timeout')) { + if (errorMessage.includes("timeout")) { return { success: false, - error: 'Request timeout', + error: "Request timeout", }; } @@ -112,13 +111,13 @@ export async function fetchTranscriptContent( * @returns boolean indicating if URL appears valid */ export function isValidTranscriptUrl(url: string): boolean { - if (!url || typeof url !== 'string') { + if (!url || typeof url !== "string") { return false; } try { const parsedUrl = new URL(url); - return parsedUrl.protocol === 'http:' || parsedUrl.protocol === 'https:'; + return parsedUrl.protocol === "http:" || parsedUrl.protocol === "https:"; } catch { return false; } diff --git a/lib/transcriptParser.ts b/lib/transcriptParser.ts index 453c822..8d88af7 100644 --- a/lib/transcriptParser.ts +++ b/lib/transcriptParser.ts @@ -1,5 +1,5 @@ // Transcript parsing utility for converting raw transcript content into structured messages -import { prisma } from './prisma.js'; +import { prisma } from "./prisma.js"; export interface ParsedMessage { sessionId: string; @@ -19,7 +19,9 @@ export interface TranscriptParseResult { * Parse European date format (DD.MM.YYYY HH:mm:ss) to Date object */ function parseEuropeanDate(dateStr: string): Date { - const match = dateStr.match(/(\d{2})\.(\d{2})\.(\d{4}) (\d{2}):(\d{2}):(\d{2})/); + const match = dateStr.match( + /(\d{2})\.(\d{2})\.(\d{4}) (\d{2}):(\d{2}):(\d{2})/ + ); if (!match) { throw new Error(`Invalid date format: ${dateStr}`); } @@ -51,13 +53,17 @@ export function parseTranscriptToMessages( if (!content || !content.trim()) { return { success: false, - error: 'Empty transcript content' + error: "Empty transcript content", }; } const messages: ParsedMessage[] = []; - const lines = content.split('\n'); - let currentMessage: { role: string; content: string; timestamp?: string } | null = null; + const lines = content.split("\n"); + let currentMessage: { + role: string; + content: string; + timestamp?: string; + } | null = null; let order = 0; for (const line of lines) { @@ -69,56 +75,64 @@ export function parseTranscriptToMessages( } // Check if line starts with a timestamp and role [DD.MM.YYYY HH:MM:SS] Role: content - const timestampRoleMatch = trimmedLine.match(/^\[(\d{2}\.\d{2}\.\d{4} \d{2}:\d{2}:\d{2})\]\s+(User|Assistant|System|user|assistant|system):\s*(.*)$/i); + const timestampRoleMatch = trimmedLine.match( + /^\[(\d{2}\.\d{2}\.\d{4} \d{2}:\d{2}:\d{2})\]\s+(User|Assistant|System|user|assistant|system):\s*(.*)$/i + ); // Check if line starts with just a role (User:, Assistant:, System:, etc.) - const roleMatch = trimmedLine.match(/^(User|Assistant|System|user|assistant|system):\s*(.*)$/i); + const roleMatch = trimmedLine.match( + /^(User|Assistant|System|user|assistant|system):\s*(.*)$/i + ); if (timestampRoleMatch) { // Save previous message if exists if (currentMessage) { messages.push({ - sessionId: '', // Will be set by caller + sessionId: "", // Will be set by caller timestamp: new Date(), // Will be calculated below role: currentMessage.role, content: currentMessage.content.trim(), - order: order++ + order: order++, }); } // Start new message with timestamp const timestamp = timestampRoleMatch[1]; - const role = timestampRoleMatch[2].charAt(0).toUpperCase() + timestampRoleMatch[2].slice(1).toLowerCase(); - const content = timestampRoleMatch[3] || ''; + const role = + timestampRoleMatch[2].charAt(0).toUpperCase() + + timestampRoleMatch[2].slice(1).toLowerCase(); + const content = timestampRoleMatch[3] || ""; currentMessage = { role, content, - timestamp // Store the timestamp for later parsing + timestamp, // Store the timestamp for later parsing }; } else if (roleMatch) { // Save previous message if exists if (currentMessage) { messages.push({ - sessionId: '', // Will be set by caller + sessionId: "", // Will be set by caller timestamp: new Date(), // Will be calculated below role: currentMessage.role, content: currentMessage.content.trim(), - order: order++ + order: order++, }); } // Start new message without timestamp - const role = roleMatch[1].charAt(0).toUpperCase() + roleMatch[1].slice(1).toLowerCase(); - const content = roleMatch[2] || ''; + const role = + roleMatch[1].charAt(0).toUpperCase() + + roleMatch[1].slice(1).toLowerCase(); + const content = roleMatch[2] || ""; currentMessage = { role, - content + content, }; } else if (currentMessage) { // Continue previous message (multi-line) - currentMessage.content += '\n' + trimmedLine; + currentMessage.content += "\n" + trimmedLine; } // If no current message and no role match, skip the line (orphaned content) } @@ -126,23 +140,23 @@ export function parseTranscriptToMessages( // Save the last message if (currentMessage) { messages.push({ - sessionId: '', // Will be set by caller + sessionId: "", // Will be set by caller timestamp: new Date(), // Will be calculated below role: currentMessage.role, content: currentMessage.content.trim(), - order: order++ + order: order++, }); } if (messages.length === 0) { return { success: false, - error: 'No messages found in transcript' + error: "No messages found in transcript", }; } // Calculate timestamps - use parsed timestamps if available, otherwise distribute across session duration - const hasTimestamps = messages.some(msg => (msg as any).timestamp); + const hasTimestamps = messages.some((msg) => (msg as any).timestamp); if (hasTimestamps) { // Use parsed timestamps from the transcript @@ -154,35 +168,45 @@ export function parseTranscriptToMessages( } catch (error) { // Fallback to distributed timestamp if parsing fails const sessionDurationMs = endTime.getTime() - startTime.getTime(); - const messageInterval = messages.length > 1 ? sessionDurationMs / (messages.length - 1) : 0; - message.timestamp = new Date(startTime.getTime() + (index * messageInterval)); + const messageInterval = + messages.length > 1 + ? sessionDurationMs / (messages.length - 1) + : 0; + message.timestamp = new Date( + startTime.getTime() + index * messageInterval + ); } } else { // Fallback to distributed timestamp const sessionDurationMs = endTime.getTime() - startTime.getTime(); - const messageInterval = messages.length > 1 ? sessionDurationMs / (messages.length - 1) : 0; - message.timestamp = new Date(startTime.getTime() + (index * messageInterval)); + const messageInterval = + messages.length > 1 ? sessionDurationMs / (messages.length - 1) : 0; + message.timestamp = new Date( + startTime.getTime() + index * messageInterval + ); } }); } else { // Distribute messages across session duration const sessionDurationMs = endTime.getTime() - startTime.getTime(); - const messageInterval = messages.length > 1 ? sessionDurationMs / (messages.length - 1) : 0; + const messageInterval = + messages.length > 1 ? sessionDurationMs / (messages.length - 1) : 0; messages.forEach((message, index) => { - message.timestamp = new Date(startTime.getTime() + (index * messageInterval)); + message.timestamp = new Date( + startTime.getTime() + index * messageInterval + ); }); } return { success: true, - messages + messages, }; - } catch (error) { return { success: false, - error: error instanceof Error ? error.message : String(error) + error: error instanceof Error ? error.message : String(error), }; } } @@ -198,17 +222,17 @@ export async function storeMessagesForSession( ): Promise { // Delete existing messages for this session (in case of re-processing) await prisma.message.deleteMany({ - where: { sessionId } + where: { sessionId }, }); // Create new messages - const messagesWithSessionId = messages.map(msg => ({ + const messagesWithSessionId = messages.map((msg) => ({ ...msg, - sessionId + sessionId, })); await prisma.message.createMany({ - data: messagesWithSessionId + data: messagesWithSessionId, }); } @@ -216,13 +240,15 @@ export async function storeMessagesForSession( * Process transcript for a single session * @param sessionId The session ID to process */ -export async function processSessionTranscript(sessionId: string): Promise { +export async function processSessionTranscript( + sessionId: string +): Promise { // Get the session and its import data const session = await prisma.session.findUnique({ where: { id: sessionId }, include: { - import: true - } + import: true, + }, }); if (!session) { @@ -255,35 +281,37 @@ export async function processSessionTranscript(sessionId: string): Promise // Store the messages await storeMessagesForSession(sessionId, parseResult.messages!); - console.log(`✅ Processed ${parseResult.messages!.length} messages for session ${sessionId}`); + console.log( + `✅ Processed ${parseResult.messages!.length} messages for session ${sessionId}` + ); } /** * Process all sessions that have transcript content but no messages */ export async function processAllUnparsedTranscripts(): Promise { - console.log('🔍 Finding sessions with unparsed transcripts...'); + console.log("🔍 Finding sessions with unparsed transcripts..."); // Find sessions that have transcript content but no messages const sessionsToProcess = await prisma.session.findMany({ where: { import: { rawTranscriptContent: { - not: null - } + not: null, + }, }, messages: { - none: {} - } + none: {}, + }, }, include: { import: true, _count: { select: { - messages: true - } - } - } + messages: true, + }, + }, + }, }); console.log(`📋 Found ${sessionsToProcess.length} sessions to process`); @@ -323,7 +351,7 @@ export async function getTotalMessageCount(): Promise { export async function getMessagesForSession(sessionId: string) { return await prisma.message.findMany({ where: { sessionId }, - orderBy: { order: 'asc' } + orderBy: { order: "asc" }, }); } @@ -336,17 +364,17 @@ export async function getParsingStats() { where: { import: { rawTranscriptContent: { - not: null - } - } - } + not: null, + }, + }, + }, }); const sessionsWithMessages = await prisma.session.count({ where: { messages: { - some: {} - } - } + some: {}, + }, + }, }); const totalMessages = await getTotalMessageCount(); @@ -355,6 +383,6 @@ export async function getParsingStats() { sessionsWithTranscripts, sessionsWithMessages, unparsedSessions: sessionsWithTranscripts - sessionsWithMessages, - totalMessages + totalMessages, }; } diff --git a/lib/utils.ts b/lib/utils.ts index bd0c391..a5ef193 100644 --- a/lib/utils.ts +++ b/lib/utils.ts @@ -1,6 +1,6 @@ -import { clsx, type ClassValue } from "clsx" -import { twMerge } from "tailwind-merge" +import { clsx, type ClassValue } from "clsx"; +import { twMerge } from "tailwind-merge"; export function cn(...inputs: ClassValue[]) { - return twMerge(clsx(inputs)) + return twMerge(clsx(inputs)); } diff --git a/lib/validation.ts b/lib/validation.ts new file mode 100644 index 0000000..ba2383a --- /dev/null +++ b/lib/validation.ts @@ -0,0 +1,134 @@ +import { z } from "zod"; + +// Password validation with strong requirements +const passwordSchema = z + .string() + .min(12, "Password must be at least 12 characters long") + .regex(/^(?=.*[a-z])/, "Password must contain at least one lowercase letter") + .regex(/^(?=.*[A-Z])/, "Password must contain at least one uppercase letter") + .regex(/^(?=.*\d)/, "Password must contain at least one number") + .regex( + /^(?=.*[@$!%*?&])/, + "Password must contain at least one special character (@$!%*?&)" + ); + +// Email validation +const emailSchema = z + .string() + .email("Invalid email format") + .max(255, "Email must be less than 255 characters") + .toLowerCase(); + +// Company name validation +const companyNameSchema = z + .string() + .min(1, "Company name is required") + .max(100, "Company name must be less than 100 characters") + .regex(/^[a-zA-Z0-9\s\-_.]+$/, "Company name contains invalid characters"); + +// User registration schema +export const registerSchema = z.object({ + email: emailSchema, + password: passwordSchema, + company: companyNameSchema, +}); + +// User login schema +export const loginSchema = z.object({ + email: emailSchema, + password: z.string().min(1, "Password is required"), +}); + +// Password reset request schema +export const forgotPasswordSchema = z.object({ + email: emailSchema, +}); + +// Password reset schema +export const resetPasswordSchema = z.object({ + token: z.string().min(1, "Reset token is required"), + password: passwordSchema, +}); + +// Session filter schema +export const sessionFilterSchema = z.object({ + search: z.string().max(100).optional(), + sentiment: z.enum(["POSITIVE", "NEUTRAL", "NEGATIVE"]).optional(), + category: z + .enum([ + "SCHEDULE_HOURS", + "LEAVE_VACATION", + "SICK_LEAVE_RECOVERY", + "SALARY_COMPENSATION", + "CONTRACT_HOURS", + "ONBOARDING", + "OFFBOARDING", + "WORKWEAR_STAFF_PASS", + "TEAM_CONTACTS", + "PERSONAL_QUESTIONS", + "ACCESS_LOGIN", + "SOCIAL_QUESTIONS", + "UNRECOGNIZED_OTHER", + ]) + .optional(), + startDate: z.string().datetime().optional(), + endDate: z.string().datetime().optional(), + page: z.number().int().min(1).default(1), + limit: z.number().int().min(1).max(100).default(20), +}); + +// Company settings schema +export const companySettingsSchema = z.object({ + name: companyNameSchema, + csvUrl: z.string().url("Invalid CSV URL"), + csvUsername: z.string().max(100).optional(), + csvPassword: z.string().max(100).optional(), + sentimentAlert: z.number().min(0).max(1).optional(), + dashboardOpts: z.object({}).passthrough().optional(), +}); + +// User management schema +export const userUpdateSchema = z.object({ + email: emailSchema.optional(), + role: z.enum(["ADMIN", "USER", "AUDITOR"]).optional(), + password: passwordSchema.optional(), +}); + +// Metrics query schema +export const metricsQuerySchema = z.object({ + startDate: z.string().datetime().optional(), + endDate: z.string().datetime().optional(), + companyId: z.string().uuid().optional(), +}); + +// Helper function to validate and sanitize input +export function validateInput( + schema: z.ZodSchema, + data: unknown +): { success: true; data: T } | { success: false; errors: string[] } { + try { + const result = schema.parse(data); + return { success: true, data: result }; + } catch (error) { + if (error instanceof z.ZodError) { + const errors = error.errors.map( + (err) => `${err.path.join(".")}: ${err.message}` + ); + return { success: false, errors }; + } + return { success: false, errors: ["Invalid input"] }; + } +} + +// Rate limiting helper types +export interface RateLimitConfig { + windowMs: number; + maxRequests: number; + skipSuccessfulRequests?: boolean; +} + +export const rateLimitConfigs = { + auth: { windowMs: 15 * 60 * 1000, maxRequests: 5 }, // 5 requests per 15 minutes + registration: { windowMs: 60 * 60 * 1000, maxRequests: 3 }, // 3 registrations per hour + api: { windowMs: 15 * 60 * 1000, maxRequests: 100 }, // 100 API requests per 15 minutes +} as const; diff --git a/migrate-to-refactored-system.ts b/migrate-to-refactored-system.ts index 84108e2..d5ce89b 100644 --- a/migrate-to-refactored-system.ts +++ b/migrate-to-refactored-system.ts @@ -1,12 +1,16 @@ -import { PrismaClient, ProcessingStage, ProcessingStatus } from '@prisma/client'; -import { ProcessingStatusManager } from './lib/processingStatusManager'; +import { + PrismaClient, + ProcessingStage, + ProcessingStatus, +} from "@prisma/client"; +import { ProcessingStatusManager } from "./lib/processingStatusManager"; const prisma = new PrismaClient(); async function migrateToRefactoredSystem() { try { - console.log('=== MIGRATING TO REFACTORED PROCESSING SYSTEM ===\n'); - + console.log("=== MIGRATING TO REFACTORED PROCESSING SYSTEM ===\n"); + // Get all existing sessions const sessions = await prisma.session.findMany({ include: { @@ -14,113 +18,166 @@ async function migrateToRefactoredSystem() { messages: true, sessionQuestions: true, }, - orderBy: { createdAt: 'asc' } + orderBy: { createdAt: "asc" }, }); - + console.log(`Found ${sessions.length} sessions to migrate...\n`); - + let migratedCount = 0; - + for (const session of sessions) { - console.log(`Migrating session ${session.import?.externalSessionId || session.id}...`); - + console.log( + `Migrating session ${session.import?.externalSessionId || session.id}...` + ); + // Initialize processing status for this session await ProcessingStatusManager.initializeSession(session.id); - + // Determine the current state of each stage based on existing data - + // 1. CSV_IMPORT - Always completed if session exists - await ProcessingStatusManager.completeStage(session.id, ProcessingStage.CSV_IMPORT, { - migratedFrom: 'existing_session', - importId: session.importId - }); - + await ProcessingStatusManager.completeStage( + session.id, + ProcessingStage.CSV_IMPORT, + { + migratedFrom: "existing_session", + importId: session.importId, + } + ); + // 2. TRANSCRIPT_FETCH - Check if transcript content exists if (session.import?.rawTranscriptContent) { - await ProcessingStatusManager.completeStage(session.id, ProcessingStage.TRANSCRIPT_FETCH, { - migratedFrom: 'existing_transcript', - contentLength: session.import.rawTranscriptContent.length - }); + await ProcessingStatusManager.completeStage( + session.id, + ProcessingStage.TRANSCRIPT_FETCH, + { + migratedFrom: "existing_transcript", + contentLength: session.import.rawTranscriptContent.length, + } + ); } else if (!session.import?.fullTranscriptUrl) { // No transcript URL - skip this stage - await ProcessingStatusManager.skipStage(session.id, ProcessingStage.TRANSCRIPT_FETCH, 'No transcript URL in original import'); + await ProcessingStatusManager.skipStage( + session.id, + ProcessingStage.TRANSCRIPT_FETCH, + "No transcript URL in original import" + ); } else { // Has URL but no content - mark as pending for retry - console.log(` - Transcript fetch pending for ${session.import.externalSessionId}`); + console.log( + ` - Transcript fetch pending for ${session.import.externalSessionId}` + ); } - + // 3. SESSION_CREATION - Check if messages exist if (session.messages.length > 0) { - await ProcessingStatusManager.completeStage(session.id, ProcessingStage.SESSION_CREATION, { - migratedFrom: 'existing_messages', - messageCount: session.messages.length - }); + await ProcessingStatusManager.completeStage( + session.id, + ProcessingStage.SESSION_CREATION, + { + migratedFrom: "existing_messages", + messageCount: session.messages.length, + } + ); } else if (session.import?.rawTranscriptContent) { // Has transcript but no messages - needs reprocessing - console.log(` - Session creation pending for ${session.import.externalSessionId} (has transcript but no messages)`); + console.log( + ` - Session creation pending for ${session.import.externalSessionId} (has transcript but no messages)` + ); } else { // No transcript content - skip or mark as pending based on transcript fetch status if (!session.import?.fullTranscriptUrl) { - await ProcessingStatusManager.skipStage(session.id, ProcessingStage.SESSION_CREATION, 'No transcript content available'); + await ProcessingStatusManager.skipStage( + session.id, + ProcessingStage.SESSION_CREATION, + "No transcript content available" + ); } } - + // 4. AI_ANALYSIS - Check if AI fields are populated - const hasAIAnalysis = session.summary || session.sentiment || session.category || session.language; + const hasAIAnalysis = + session.summary || + session.sentiment || + session.category || + session.language; if (hasAIAnalysis) { - await ProcessingStatusManager.completeStage(session.id, ProcessingStage.AI_ANALYSIS, { - migratedFrom: 'existing_ai_analysis', - hasSummary: !!session.summary, - hasSentiment: !!session.sentiment, - hasCategory: !!session.category, - hasLanguage: !!session.language - }); + await ProcessingStatusManager.completeStage( + session.id, + ProcessingStage.AI_ANALYSIS, + { + migratedFrom: "existing_ai_analysis", + hasSummary: !!session.summary, + hasSentiment: !!session.sentiment, + hasCategory: !!session.category, + hasLanguage: !!session.language, + } + ); } else { // No AI analysis - mark as pending if session creation is complete if (session.messages.length > 0) { - console.log(` - AI analysis pending for ${session.import?.externalSessionId}`); + console.log( + ` - AI analysis pending for ${session.import?.externalSessionId}` + ); } } - + // 5. QUESTION_EXTRACTION - Check if questions exist if (session.sessionQuestions.length > 0) { - await ProcessingStatusManager.completeStage(session.id, ProcessingStage.QUESTION_EXTRACTION, { - migratedFrom: 'existing_questions', - questionCount: session.sessionQuestions.length - }); + await ProcessingStatusManager.completeStage( + session.id, + ProcessingStage.QUESTION_EXTRACTION, + { + migratedFrom: "existing_questions", + questionCount: session.sessionQuestions.length, + } + ); } else { // No questions - mark as pending if AI analysis is complete if (hasAIAnalysis) { - console.log(` - Question extraction pending for ${session.import?.externalSessionId}`); + console.log( + ` - Question extraction pending for ${session.import?.externalSessionId}` + ); } } - + migratedCount++; - + if (migratedCount % 10 === 0) { - console.log(` Migrated ${migratedCount}/${sessions.length} sessions...`); + console.log( + ` Migrated ${migratedCount}/${sessions.length} sessions...` + ); } } - - console.log(`\n✓ Successfully migrated ${migratedCount} sessions to the new processing system`); - + + console.log( + `\n✓ Successfully migrated ${migratedCount} sessions to the new processing system` + ); + // Show final status - console.log('\n=== MIGRATION COMPLETE - FINAL STATUS ==='); + console.log("\n=== MIGRATION COMPLETE - FINAL STATUS ==="); const pipelineStatus = await ProcessingStatusManager.getPipelineStatus(); - - const stages = ['CSV_IMPORT', 'TRANSCRIPT_FETCH', 'SESSION_CREATION', 'AI_ANALYSIS', 'QUESTION_EXTRACTION']; - + + const stages = [ + "CSV_IMPORT", + "TRANSCRIPT_FETCH", + "SESSION_CREATION", + "AI_ANALYSIS", + "QUESTION_EXTRACTION", + ]; + for (const stage of stages) { const stageData = pipelineStatus.pipeline[stage] || {}; const pending = stageData.PENDING || 0; const completed = stageData.COMPLETED || 0; const skipped = stageData.SKIPPED || 0; - - console.log(`${stage}: ${completed} completed, ${pending} pending, ${skipped} skipped`); + + console.log( + `${stage}: ${completed} completed, ${pending} pending, ${skipped} skipped` + ); } - } catch (error) { - console.error('Error migrating to refactored system:', error); + console.error("Error migrating to refactored system:", error); } finally { await prisma.$disconnect(); } diff --git a/next.config.js b/next.config.js index 7f1e761..054cc6b 100644 --- a/next.config.js +++ b/next.config.js @@ -4,10 +4,7 @@ const nextConfig = { reactStrictMode: true, // Allow cross-origin requests from specific origins in development - allowedDevOrigins: [ - "localhost", - "127.0.0.1" - ], + allowedDevOrigins: ["localhost", "127.0.0.1"], }; export default nextConfig; diff --git a/package.json b/package.json index 5baf2ff..41ef898 100644 --- a/package.json +++ b/package.json @@ -59,7 +59,8 @@ "react-markdown": "^10.1.0", "recharts": "^3.0.2", "rehype-raw": "^7.0.0", - "tailwind-merge": "^3.3.1" + "tailwind-merge": "^3.3.1", + "zod": "^3.25.67" }, "devDependencies": { "@eslint/eslintrc": "^3.3.1", @@ -68,7 +69,6 @@ "@tailwindcss/postcss": "^4.1.11", "@testing-library/dom": "^10.4.0", "@testing-library/react": "^16.3.0", - "@types/bcryptjs": "^3.0.0", "@types/node": "^24.0.6", "@types/node-cron": "^3.0.11", "@types/react": "^19.1.8", diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 9cf4337..81f7340 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -1,50 +1,49 @@ -lockfileVersion: '9.0' +lockfileVersion: "9.0" settings: autoInstallPeers: true excludeLinksFromLockfile: false importers: - .: dependencies: - '@prisma/adapter-pg': + "@prisma/adapter-pg": specifier: ^6.10.1 version: 6.10.1(pg@8.16.3) - '@prisma/client': + "@prisma/client": specifier: ^6.10.1 version: 6.10.1(prisma@6.10.1(typescript@5.8.3))(typescript@5.8.3) - '@radix-ui/react-dropdown-menu': + "@radix-ui/react-dropdown-menu": specifier: ^2.1.15 version: 2.1.15(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) - '@radix-ui/react-separator': + "@radix-ui/react-separator": specifier: ^1.1.7 version: 1.1.7(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) - '@radix-ui/react-slot': + "@radix-ui/react-slot": specifier: ^1.2.3 version: 1.2.3(@types/react@19.1.8)(react@19.1.0) - '@radix-ui/react-tooltip': + "@radix-ui/react-tooltip": specifier: ^1.2.7 version: 1.2.7(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) - '@rapideditor/country-coder': + "@rapideditor/country-coder": specifier: ^5.4.0 version: 5.4.0 - '@types/d3': + "@types/d3": specifier: ^7.4.3 version: 7.4.3 - '@types/d3-cloud': + "@types/d3-cloud": specifier: ^1.2.9 version: 1.2.9 - '@types/d3-selection': + "@types/d3-selection": specifier: ^3.0.11 version: 3.0.11 - '@types/geojson': + "@types/geojson": specifier: ^7946.0.16 version: 7946.0.16 - '@types/leaflet': + "@types/leaflet": specifier: ^1.9.19 version: 1.9.19 - '@types/node-fetch': + "@types/node-fetch": specifier: ^2.6.12 version: 2.6.12 bcryptjs: @@ -113,50 +112,50 @@ importers: tailwind-merge: specifier: ^3.3.1 version: 3.3.1 + zod: + specifier: ^3.25.67 + version: 3.25.67 devDependencies: - '@eslint/eslintrc': + "@eslint/eslintrc": specifier: ^3.3.1 version: 3.3.1 - '@eslint/js': + "@eslint/js": specifier: ^9.30.0 version: 9.30.0 - '@playwright/test': + "@playwright/test": specifier: ^1.53.1 version: 1.53.1 - '@tailwindcss/postcss': + "@tailwindcss/postcss": specifier: ^4.1.11 version: 4.1.11 - '@testing-library/dom': + "@testing-library/dom": specifier: ^10.4.0 version: 10.4.0 - '@testing-library/react': + "@testing-library/react": specifier: ^16.3.0 version: 16.3.0(@testing-library/dom@10.4.0)(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) - '@types/bcryptjs': - specifier: ^3.0.0 - version: 3.0.0 - '@types/node': + "@types/node": specifier: ^24.0.6 version: 24.0.6 - '@types/node-cron': + "@types/node-cron": specifier: ^3.0.11 version: 3.0.11 - '@types/react': + "@types/react": specifier: ^19.1.8 version: 19.1.8 - '@types/react-dom': + "@types/react-dom": specifier: ^19.1.6 version: 19.1.6(@types/react@19.1.8) - '@typescript-eslint/eslint-plugin': + "@typescript-eslint/eslint-plugin": specifier: ^8.35.0 version: 8.35.0(@typescript-eslint/parser@8.35.0(eslint@9.30.0(jiti@2.4.2))(typescript@5.8.3))(eslint@9.30.0(jiti@2.4.2))(typescript@5.8.3) - '@typescript-eslint/parser': + "@typescript-eslint/parser": specifier: ^8.35.0 version: 8.35.0(eslint@9.30.0(jiti@2.4.2))(typescript@5.8.3) - '@vitejs/plugin-react': + "@vitejs/plugin-react": specifier: ^4.6.0 version: 4.6.0(vite@7.0.0(@types/node@24.0.6)(jiti@2.4.2)(lightningcss@1.30.1)(tsx@4.20.3)) - '@vitest/coverage-v8': + "@vitest/coverage-v8": specifier: ^3.2.4 version: 3.2.4(vitest@3.2.4(@types/debug@4.1.12)(@types/node@24.0.6)(jiti@2.4.2)(jsdom@26.1.0)(lightningcss@1.30.1)(tsx@4.20.3)) eslint: @@ -209,967 +208,1464 @@ importers: version: 3.2.4(@types/debug@4.1.12)(@types/node@24.0.6)(jiti@2.4.2)(jsdom@26.1.0)(lightningcss@1.30.1)(tsx@4.20.3) packages: + "@alloc/quick-lru@5.2.0": + resolution: + { + integrity: sha512-UrcABB+4bUrFABwbluTIBErXwvbsU/V7TZWfmbgJfbkwiBuziS9gxdODUyuiecfdGQ85jglMW6juS3+z5TsKLw==, + } + engines: { node: ">=10" } - '@alloc/quick-lru@5.2.0': - resolution: {integrity: sha512-UrcABB+4bUrFABwbluTIBErXwvbsU/V7TZWfmbgJfbkwiBuziS9gxdODUyuiecfdGQ85jglMW6juS3+z5TsKLw==} - engines: {node: '>=10'} + "@ampproject/remapping@2.3.0": + resolution: + { + integrity: sha512-30iZtAPgz+LTIYoeivqYo853f02jBYSd5uGnGpkFV0M3xOt9aN73erkgYAmZU43x4VfqcnLxW9Kpg3R5LC4YYw==, + } + engines: { node: ">=6.0.0" } - '@ampproject/remapping@2.3.0': - resolution: {integrity: sha512-30iZtAPgz+LTIYoeivqYo853f02jBYSd5uGnGpkFV0M3xOt9aN73erkgYAmZU43x4VfqcnLxW9Kpg3R5LC4YYw==} - engines: {node: '>=6.0.0'} + "@asamuzakjp/css-color@3.2.0": + resolution: + { + integrity: sha512-K1A6z8tS3XsmCMM86xoWdn7Fkdn9m6RSVtocUrJYIwZnFVkng/PvkEoWtOWmP+Scc6saYWHWZYbndEEXxl24jw==, + } - '@asamuzakjp/css-color@3.2.0': - resolution: {integrity: sha512-K1A6z8tS3XsmCMM86xoWdn7Fkdn9m6RSVtocUrJYIwZnFVkng/PvkEoWtOWmP+Scc6saYWHWZYbndEEXxl24jw==} + "@babel/code-frame@7.27.1": + resolution: + { + integrity: sha512-cjQ7ZlQ0Mv3b47hABuTevyTuYN4i+loJKGeV9flcCgIK37cCXRh+L1bd3iBHlynerhQ7BhCkn2BPbQUL+rGqFg==, + } + engines: { node: ">=6.9.0" } - '@babel/code-frame@7.27.1': - resolution: {integrity: sha512-cjQ7ZlQ0Mv3b47hABuTevyTuYN4i+loJKGeV9flcCgIK37cCXRh+L1bd3iBHlynerhQ7BhCkn2BPbQUL+rGqFg==} - engines: {node: '>=6.9.0'} + "@babel/compat-data@7.27.7": + resolution: + { + integrity: sha512-xgu/ySj2mTiUFmdE9yCMfBxLp4DHd5DwmbbD05YAuICfodYT3VvRxbrh81LGQ/8UpSdtMdfKMn3KouYDX59DGQ==, + } + engines: { node: ">=6.9.0" } - '@babel/compat-data@7.27.7': - resolution: {integrity: sha512-xgu/ySj2mTiUFmdE9yCMfBxLp4DHd5DwmbbD05YAuICfodYT3VvRxbrh81LGQ/8UpSdtMdfKMn3KouYDX59DGQ==} - engines: {node: '>=6.9.0'} + "@babel/core@7.27.7": + resolution: + { + integrity: sha512-BU2f9tlKQ5CAthiMIgpzAh4eDTLWo1mqi9jqE2OxMG0E/OM199VJt2q8BztTxpnSW0i1ymdwLXRJnYzvDM5r2w==, + } + engines: { node: ">=6.9.0" } - '@babel/core@7.27.7': - resolution: {integrity: sha512-BU2f9tlKQ5CAthiMIgpzAh4eDTLWo1mqi9jqE2OxMG0E/OM199VJt2q8BztTxpnSW0i1ymdwLXRJnYzvDM5r2w==} - engines: {node: '>=6.9.0'} + "@babel/generator@7.27.5": + resolution: + { + integrity: sha512-ZGhA37l0e/g2s1Cnzdix0O3aLYm66eF8aufiVteOgnwxgnRP8GoyMj7VWsgWnQbVKXyge7hqrFh2K2TQM6t1Hw==, + } + engines: { node: ">=6.9.0" } - '@babel/generator@7.27.5': - resolution: {integrity: sha512-ZGhA37l0e/g2s1Cnzdix0O3aLYm66eF8aufiVteOgnwxgnRP8GoyMj7VWsgWnQbVKXyge7hqrFh2K2TQM6t1Hw==} - engines: {node: '>=6.9.0'} + "@babel/helper-compilation-targets@7.27.2": + resolution: + { + integrity: sha512-2+1thGUUWWjLTYTHZWK1n8Yga0ijBz1XAhUXcKy81rd5g6yh7hGqMp45v7cadSbEHc9G3OTv45SyneRN3ps4DQ==, + } + engines: { node: ">=6.9.0" } - '@babel/helper-compilation-targets@7.27.2': - resolution: {integrity: sha512-2+1thGUUWWjLTYTHZWK1n8Yga0ijBz1XAhUXcKy81rd5g6yh7hGqMp45v7cadSbEHc9G3OTv45SyneRN3ps4DQ==} - engines: {node: '>=6.9.0'} + "@babel/helper-module-imports@7.27.1": + resolution: + { + integrity: sha512-0gSFWUPNXNopqtIPQvlD5WgXYI5GY2kP2cCvoT8kczjbfcfuIljTbcWrulD1CIPIX2gt1wghbDy08yE1p+/r3w==, + } + engines: { node: ">=6.9.0" } - '@babel/helper-module-imports@7.27.1': - resolution: {integrity: sha512-0gSFWUPNXNopqtIPQvlD5WgXYI5GY2kP2cCvoT8kczjbfcfuIljTbcWrulD1CIPIX2gt1wghbDy08yE1p+/r3w==} - engines: {node: '>=6.9.0'} - - '@babel/helper-module-transforms@7.27.3': - resolution: {integrity: sha512-dSOvYwvyLsWBeIRyOeHXp5vPj5l1I011r52FM1+r1jCERv+aFXYk4whgQccYEGYxK2H3ZAIA8nuPkQ0HaUo3qg==} - engines: {node: '>=6.9.0'} + "@babel/helper-module-transforms@7.27.3": + resolution: + { + integrity: sha512-dSOvYwvyLsWBeIRyOeHXp5vPj5l1I011r52FM1+r1jCERv+aFXYk4whgQccYEGYxK2H3ZAIA8nuPkQ0HaUo3qg==, + } + engines: { node: ">=6.9.0" } peerDependencies: - '@babel/core': ^7.0.0 + "@babel/core": ^7.0.0 - '@babel/helper-plugin-utils@7.27.1': - resolution: {integrity: sha512-1gn1Up5YXka3YYAHGKpbideQ5Yjf1tDa9qYcgysz+cNCXukyLl6DjPXhD3VRwSb8c0J9tA4b2+rHEZtc6R0tlw==} - engines: {node: '>=6.9.0'} + "@babel/helper-plugin-utils@7.27.1": + resolution: + { + integrity: sha512-1gn1Up5YXka3YYAHGKpbideQ5Yjf1tDa9qYcgysz+cNCXukyLl6DjPXhD3VRwSb8c0J9tA4b2+rHEZtc6R0tlw==, + } + engines: { node: ">=6.9.0" } - '@babel/helper-string-parser@7.27.1': - resolution: {integrity: sha512-qMlSxKbpRlAridDExk92nSobyDdpPijUq2DW6oDnUqd0iOGxmQjyqhMIihI9+zv4LPyZdRje2cavWPbCbWm3eA==} - engines: {node: '>=6.9.0'} + "@babel/helper-string-parser@7.27.1": + resolution: + { + integrity: sha512-qMlSxKbpRlAridDExk92nSobyDdpPijUq2DW6oDnUqd0iOGxmQjyqhMIihI9+zv4LPyZdRje2cavWPbCbWm3eA==, + } + engines: { node: ">=6.9.0" } - '@babel/helper-validator-identifier@7.27.1': - resolution: {integrity: sha512-D2hP9eA+Sqx1kBZgzxZh0y1trbuU+JoDkiEwqhQ36nodYqJwyEIhPSdMNd7lOm/4io72luTPWH20Yda0xOuUow==} - engines: {node: '>=6.9.0'} + "@babel/helper-validator-identifier@7.27.1": + resolution: + { + integrity: sha512-D2hP9eA+Sqx1kBZgzxZh0y1trbuU+JoDkiEwqhQ36nodYqJwyEIhPSdMNd7lOm/4io72luTPWH20Yda0xOuUow==, + } + engines: { node: ">=6.9.0" } - '@babel/helper-validator-option@7.27.1': - resolution: {integrity: sha512-YvjJow9FxbhFFKDSuFnVCe2WxXk1zWc22fFePVNEaWJEu8IrZVlda6N0uHwzZrUM1il7NC9Mlp4MaJYbYd9JSg==} - engines: {node: '>=6.9.0'} + "@babel/helper-validator-option@7.27.1": + resolution: + { + integrity: sha512-YvjJow9FxbhFFKDSuFnVCe2WxXk1zWc22fFePVNEaWJEu8IrZVlda6N0uHwzZrUM1il7NC9Mlp4MaJYbYd9JSg==, + } + engines: { node: ">=6.9.0" } - '@babel/helpers@7.27.6': - resolution: {integrity: sha512-muE8Tt8M22638HU31A3CgfSUciwz1fhATfoVai05aPXGor//CdWDCbnlY1yvBPo07njuVOCNGCSp/GTt12lIug==} - engines: {node: '>=6.9.0'} + "@babel/helpers@7.27.6": + resolution: + { + integrity: sha512-muE8Tt8M22638HU31A3CgfSUciwz1fhATfoVai05aPXGor//CdWDCbnlY1yvBPo07njuVOCNGCSp/GTt12lIug==, + } + engines: { node: ">=6.9.0" } - '@babel/parser@7.27.7': - resolution: {integrity: sha512-qnzXzDXdr/po3bOTbTIQZ7+TxNKxpkN5IifVLXS+r7qwynkZfPyjZfE7hCXbo7IoO9TNcSyibgONsf2HauUd3Q==} - engines: {node: '>=6.0.0'} + "@babel/parser@7.27.7": + resolution: + { + integrity: sha512-qnzXzDXdr/po3bOTbTIQZ7+TxNKxpkN5IifVLXS+r7qwynkZfPyjZfE7hCXbo7IoO9TNcSyibgONsf2HauUd3Q==, + } + engines: { node: ">=6.0.0" } hasBin: true - '@babel/plugin-transform-react-jsx-self@7.27.1': - resolution: {integrity: sha512-6UzkCs+ejGdZ5mFFC/OCUrv028ab2fp1znZmCZjAOBKiBK2jXD1O+BPSfX8X2qjJ75fZBMSnQn3Rq2mrBJK2mw==} - engines: {node: '>=6.9.0'} + "@babel/plugin-transform-react-jsx-self@7.27.1": + resolution: + { + integrity: sha512-6UzkCs+ejGdZ5mFFC/OCUrv028ab2fp1znZmCZjAOBKiBK2jXD1O+BPSfX8X2qjJ75fZBMSnQn3Rq2mrBJK2mw==, + } + engines: { node: ">=6.9.0" } peerDependencies: - '@babel/core': ^7.0.0-0 + "@babel/core": ^7.0.0-0 - '@babel/plugin-transform-react-jsx-source@7.27.1': - resolution: {integrity: sha512-zbwoTsBruTeKB9hSq73ha66iFeJHuaFkUbwvqElnygoNbj/jHRsSeokowZFN3CZ64IvEqcmmkVe89OPXc7ldAw==} - engines: {node: '>=6.9.0'} + "@babel/plugin-transform-react-jsx-source@7.27.1": + resolution: + { + integrity: sha512-zbwoTsBruTeKB9hSq73ha66iFeJHuaFkUbwvqElnygoNbj/jHRsSeokowZFN3CZ64IvEqcmmkVe89OPXc7ldAw==, + } + engines: { node: ">=6.9.0" } peerDependencies: - '@babel/core': ^7.0.0-0 + "@babel/core": ^7.0.0-0 - '@babel/runtime@7.27.6': - resolution: {integrity: sha512-vbavdySgbTTrmFE+EsiqUTzlOr5bzlnJtUv9PynGCAKvfQqjIXbvFdumPM/GxMDfyuGMJaJAU6TO4zc1Jf1i8Q==} - engines: {node: '>=6.9.0'} + "@babel/runtime@7.27.6": + resolution: + { + integrity: sha512-vbavdySgbTTrmFE+EsiqUTzlOr5bzlnJtUv9PynGCAKvfQqjIXbvFdumPM/GxMDfyuGMJaJAU6TO4zc1Jf1i8Q==, + } + engines: { node: ">=6.9.0" } - '@babel/template@7.27.2': - resolution: {integrity: sha512-LPDZ85aEJyYSd18/DkjNh4/y1ntkE5KwUHWTiqgRxruuZL2F1yuHligVHLvcHY2vMHXttKFpJn6LwfI7cw7ODw==} - engines: {node: '>=6.9.0'} + "@babel/template@7.27.2": + resolution: + { + integrity: sha512-LPDZ85aEJyYSd18/DkjNh4/y1ntkE5KwUHWTiqgRxruuZL2F1yuHligVHLvcHY2vMHXttKFpJn6LwfI7cw7ODw==, + } + engines: { node: ">=6.9.0" } - '@babel/traverse@7.27.7': - resolution: {integrity: sha512-X6ZlfR/O/s5EQ/SnUSLzr+6kGnkg8HXGMzpgsMsrJVcfDtH1vIp6ctCN4eZ1LS5c0+te5Cb6Y514fASjMRJ1nw==} - engines: {node: '>=6.9.0'} + "@babel/traverse@7.27.7": + resolution: + { + integrity: sha512-X6ZlfR/O/s5EQ/SnUSLzr+6kGnkg8HXGMzpgsMsrJVcfDtH1vIp6ctCN4eZ1LS5c0+te5Cb6Y514fASjMRJ1nw==, + } + engines: { node: ">=6.9.0" } - '@babel/types@7.27.7': - resolution: {integrity: sha512-8OLQgDScAOHXnAz2cV+RfzzNMipuLVBz2biuAJFMV9bfkNf393je3VM8CLkjQodW5+iWsSJdSgSWT6rsZoXHPw==} - engines: {node: '>=6.9.0'} + "@babel/types@7.27.7": + resolution: + { + integrity: sha512-8OLQgDScAOHXnAz2cV+RfzzNMipuLVBz2biuAJFMV9bfkNf393je3VM8CLkjQodW5+iWsSJdSgSWT6rsZoXHPw==, + } + engines: { node: ">=6.9.0" } - '@bcoe/v8-coverage@1.0.2': - resolution: {integrity: sha512-6zABk/ECA/QYSCQ1NGiVwwbQerUCZ+TQbp64Q3AgmfNvurHH0j8TtXa1qbShXA6qqkpAj4V5W8pP6mLe1mcMqA==} - engines: {node: '>=18'} + "@bcoe/v8-coverage@1.0.2": + resolution: + { + integrity: sha512-6zABk/ECA/QYSCQ1NGiVwwbQerUCZ+TQbp64Q3AgmfNvurHH0j8TtXa1qbShXA6qqkpAj4V5W8pP6mLe1mcMqA==, + } + engines: { node: ">=18" } - '@cspotcode/source-map-support@0.8.1': - resolution: {integrity: sha512-IchNf6dN4tHoMFIn/7OE8LWZ19Y6q/67Bmf6vnGREv8RSbBVb9LPJxEcnwrcwX6ixSvaiGoomAUvu4YSxXrVgw==} - engines: {node: '>=12'} + "@cspotcode/source-map-support@0.8.1": + resolution: + { + integrity: sha512-IchNf6dN4tHoMFIn/7OE8LWZ19Y6q/67Bmf6vnGREv8RSbBVb9LPJxEcnwrcwX6ixSvaiGoomAUvu4YSxXrVgw==, + } + engines: { node: ">=12" } - '@csstools/color-helpers@5.0.2': - resolution: {integrity: sha512-JqWH1vsgdGcw2RR6VliXXdA0/59LttzlU8UlRT/iUUsEeWfYq8I+K0yhihEUTTHLRm1EXvpsCx3083EU15ecsA==} - engines: {node: '>=18'} + "@csstools/color-helpers@5.0.2": + resolution: + { + integrity: sha512-JqWH1vsgdGcw2RR6VliXXdA0/59LttzlU8UlRT/iUUsEeWfYq8I+K0yhihEUTTHLRm1EXvpsCx3083EU15ecsA==, + } + engines: { node: ">=18" } - '@csstools/css-calc@2.1.4': - resolution: {integrity: sha512-3N8oaj+0juUw/1H3YwmDDJXCgTB1gKU6Hc/bB502u9zR0q2vd786XJH9QfrKIEgFlZmhZiq6epXl4rHqhzsIgQ==} - engines: {node: '>=18'} + "@csstools/css-calc@2.1.4": + resolution: + { + integrity: sha512-3N8oaj+0juUw/1H3YwmDDJXCgTB1gKU6Hc/bB502u9zR0q2vd786XJH9QfrKIEgFlZmhZiq6epXl4rHqhzsIgQ==, + } + engines: { node: ">=18" } peerDependencies: - '@csstools/css-parser-algorithms': ^3.0.5 - '@csstools/css-tokenizer': ^3.0.4 + "@csstools/css-parser-algorithms": ^3.0.5 + "@csstools/css-tokenizer": ^3.0.4 - '@csstools/css-color-parser@3.0.10': - resolution: {integrity: sha512-TiJ5Ajr6WRd1r8HSiwJvZBiJOqtH86aHpUjq5aEKWHiII2Qfjqd/HCWKPOW8EP4vcspXbHnXrwIDlu5savQipg==} - engines: {node: '>=18'} + "@csstools/css-color-parser@3.0.10": + resolution: + { + integrity: sha512-TiJ5Ajr6WRd1r8HSiwJvZBiJOqtH86aHpUjq5aEKWHiII2Qfjqd/HCWKPOW8EP4vcspXbHnXrwIDlu5savQipg==, + } + engines: { node: ">=18" } peerDependencies: - '@csstools/css-parser-algorithms': ^3.0.5 - '@csstools/css-tokenizer': ^3.0.4 + "@csstools/css-parser-algorithms": ^3.0.5 + "@csstools/css-tokenizer": ^3.0.4 - '@csstools/css-parser-algorithms@3.0.5': - resolution: {integrity: sha512-DaDeUkXZKjdGhgYaHNJTV9pV7Y9B3b644jCLs9Upc3VeNGg6LWARAT6O+Q+/COo+2gg/bM5rhpMAtf70WqfBdQ==} - engines: {node: '>=18'} + "@csstools/css-parser-algorithms@3.0.5": + resolution: + { + integrity: sha512-DaDeUkXZKjdGhgYaHNJTV9pV7Y9B3b644jCLs9Upc3VeNGg6LWARAT6O+Q+/COo+2gg/bM5rhpMAtf70WqfBdQ==, + } + engines: { node: ">=18" } peerDependencies: - '@csstools/css-tokenizer': ^3.0.4 + "@csstools/css-tokenizer": ^3.0.4 - '@csstools/css-tokenizer@3.0.4': - resolution: {integrity: sha512-Vd/9EVDiu6PPJt9yAh6roZP6El1xHrdvIVGjyBsHR0RYwNHgL7FJPyIIW4fANJNG6FtyZfvlRPpFI4ZM/lubvw==} - engines: {node: '>=18'} + "@csstools/css-tokenizer@3.0.4": + resolution: + { + integrity: sha512-Vd/9EVDiu6PPJt9yAh6roZP6El1xHrdvIVGjyBsHR0RYwNHgL7FJPyIIW4fANJNG6FtyZfvlRPpFI4ZM/lubvw==, + } + engines: { node: ">=18" } - '@emnapi/core@1.4.3': - resolution: {integrity: sha512-4m62DuCE07lw01soJwPiBGC0nAww0Q+RY70VZ+n49yDIO13yyinhbWCeNnaob0lakDtWQzSdtNWzJeOJt2ma+g==} + "@emnapi/core@1.4.3": + resolution: + { + integrity: sha512-4m62DuCE07lw01soJwPiBGC0nAww0Q+RY70VZ+n49yDIO13yyinhbWCeNnaob0lakDtWQzSdtNWzJeOJt2ma+g==, + } - '@emnapi/runtime@1.4.3': - resolution: {integrity: sha512-pBPWdu6MLKROBX05wSNKcNb++m5Er+KQ9QkB+WVM+pW2Kx9hoSrVTnu3BdkI5eBLZoKu/J6mW/B6i6bJB2ytXQ==} + "@emnapi/runtime@1.4.3": + resolution: + { + integrity: sha512-pBPWdu6MLKROBX05wSNKcNb++m5Er+KQ9QkB+WVM+pW2Kx9hoSrVTnu3BdkI5eBLZoKu/J6mW/B6i6bJB2ytXQ==, + } - '@emnapi/wasi-threads@1.0.2': - resolution: {integrity: sha512-5n3nTJblwRi8LlXkJ9eBzu+kZR8Yxcc7ubakyQTFzPMtIhFpUBRbsnc2Dv88IZDIbCDlBiWrknhB4Lsz7mg6BA==} + "@emnapi/wasi-threads@1.0.2": + resolution: + { + integrity: sha512-5n3nTJblwRi8LlXkJ9eBzu+kZR8Yxcc7ubakyQTFzPMtIhFpUBRbsnc2Dv88IZDIbCDlBiWrknhB4Lsz7mg6BA==, + } - '@esbuild/aix-ppc64@0.25.5': - resolution: {integrity: sha512-9o3TMmpmftaCMepOdA5k/yDw8SfInyzWWTjYTFCX3kPSDJMROQTb8jg+h9Cnwnmm1vOzvxN7gIfB5V2ewpjtGA==} - engines: {node: '>=18'} + "@esbuild/aix-ppc64@0.25.5": + resolution: + { + integrity: sha512-9o3TMmpmftaCMepOdA5k/yDw8SfInyzWWTjYTFCX3kPSDJMROQTb8jg+h9Cnwnmm1vOzvxN7gIfB5V2ewpjtGA==, + } + engines: { node: ">=18" } cpu: [ppc64] os: [aix] - '@esbuild/android-arm64@0.25.5': - resolution: {integrity: sha512-VGzGhj4lJO+TVGV1v8ntCZWJktV7SGCs3Pn1GRWI1SBFtRALoomm8k5E9Pmwg3HOAal2VDc2F9+PM/rEY6oIDg==} - engines: {node: '>=18'} + "@esbuild/android-arm64@0.25.5": + resolution: + { + integrity: sha512-VGzGhj4lJO+TVGV1v8ntCZWJktV7SGCs3Pn1GRWI1SBFtRALoomm8k5E9Pmwg3HOAal2VDc2F9+PM/rEY6oIDg==, + } + engines: { node: ">=18" } cpu: [arm64] os: [android] - '@esbuild/android-arm@0.25.5': - resolution: {integrity: sha512-AdJKSPeEHgi7/ZhuIPtcQKr5RQdo6OO2IL87JkianiMYMPbCtot9fxPbrMiBADOWWm3T2si9stAiVsGbTQFkbA==} - engines: {node: '>=18'} + "@esbuild/android-arm@0.25.5": + resolution: + { + integrity: sha512-AdJKSPeEHgi7/ZhuIPtcQKr5RQdo6OO2IL87JkianiMYMPbCtot9fxPbrMiBADOWWm3T2si9stAiVsGbTQFkbA==, + } + engines: { node: ">=18" } cpu: [arm] os: [android] - '@esbuild/android-x64@0.25.5': - resolution: {integrity: sha512-D2GyJT1kjvO//drbRT3Hib9XPwQeWd9vZoBJn+bu/lVsOZ13cqNdDeqIF/xQ5/VmWvMduP6AmXvylO/PIc2isw==} - engines: {node: '>=18'} + "@esbuild/android-x64@0.25.5": + resolution: + { + integrity: sha512-D2GyJT1kjvO//drbRT3Hib9XPwQeWd9vZoBJn+bu/lVsOZ13cqNdDeqIF/xQ5/VmWvMduP6AmXvylO/PIc2isw==, + } + engines: { node: ">=18" } cpu: [x64] os: [android] - '@esbuild/darwin-arm64@0.25.5': - resolution: {integrity: sha512-GtaBgammVvdF7aPIgH2jxMDdivezgFu6iKpmT+48+F8Hhg5J/sfnDieg0aeG/jfSvkYQU2/pceFPDKlqZzwnfQ==} - engines: {node: '>=18'} + "@esbuild/darwin-arm64@0.25.5": + resolution: + { + integrity: sha512-GtaBgammVvdF7aPIgH2jxMDdivezgFu6iKpmT+48+F8Hhg5J/sfnDieg0aeG/jfSvkYQU2/pceFPDKlqZzwnfQ==, + } + engines: { node: ">=18" } cpu: [arm64] os: [darwin] - '@esbuild/darwin-x64@0.25.5': - resolution: {integrity: sha512-1iT4FVL0dJ76/q1wd7XDsXrSW+oLoquptvh4CLR4kITDtqi2e/xwXwdCVH8hVHU43wgJdsq7Gxuzcs6Iq/7bxQ==} - engines: {node: '>=18'} + "@esbuild/darwin-x64@0.25.5": + resolution: + { + integrity: sha512-1iT4FVL0dJ76/q1wd7XDsXrSW+oLoquptvh4CLR4kITDtqi2e/xwXwdCVH8hVHU43wgJdsq7Gxuzcs6Iq/7bxQ==, + } + engines: { node: ">=18" } cpu: [x64] os: [darwin] - '@esbuild/freebsd-arm64@0.25.5': - resolution: {integrity: sha512-nk4tGP3JThz4La38Uy/gzyXtpkPW8zSAmoUhK9xKKXdBCzKODMc2adkB2+8om9BDYugz+uGV7sLmpTYzvmz6Sw==} - engines: {node: '>=18'} + "@esbuild/freebsd-arm64@0.25.5": + resolution: + { + integrity: sha512-nk4tGP3JThz4La38Uy/gzyXtpkPW8zSAmoUhK9xKKXdBCzKODMc2adkB2+8om9BDYugz+uGV7sLmpTYzvmz6Sw==, + } + engines: { node: ">=18" } cpu: [arm64] os: [freebsd] - '@esbuild/freebsd-x64@0.25.5': - resolution: {integrity: sha512-PrikaNjiXdR2laW6OIjlbeuCPrPaAl0IwPIaRv+SMV8CiM8i2LqVUHFC1+8eORgWyY7yhQY+2U2fA55mBzReaw==} - engines: {node: '>=18'} + "@esbuild/freebsd-x64@0.25.5": + resolution: + { + integrity: sha512-PrikaNjiXdR2laW6OIjlbeuCPrPaAl0IwPIaRv+SMV8CiM8i2LqVUHFC1+8eORgWyY7yhQY+2U2fA55mBzReaw==, + } + engines: { node: ">=18" } cpu: [x64] os: [freebsd] - '@esbuild/linux-arm64@0.25.5': - resolution: {integrity: sha512-Z9kfb1v6ZlGbWj8EJk9T6czVEjjq2ntSYLY2cw6pAZl4oKtfgQuS4HOq41M/BcoLPzrUbNd+R4BXFyH//nHxVg==} - engines: {node: '>=18'} + "@esbuild/linux-arm64@0.25.5": + resolution: + { + integrity: sha512-Z9kfb1v6ZlGbWj8EJk9T6czVEjjq2ntSYLY2cw6pAZl4oKtfgQuS4HOq41M/BcoLPzrUbNd+R4BXFyH//nHxVg==, + } + engines: { node: ">=18" } cpu: [arm64] os: [linux] - '@esbuild/linux-arm@0.25.5': - resolution: {integrity: sha512-cPzojwW2okgh7ZlRpcBEtsX7WBuqbLrNXqLU89GxWbNt6uIg78ET82qifUy3W6OVww6ZWobWub5oqZOVtwolfw==} - engines: {node: '>=18'} + "@esbuild/linux-arm@0.25.5": + resolution: + { + integrity: sha512-cPzojwW2okgh7ZlRpcBEtsX7WBuqbLrNXqLU89GxWbNt6uIg78ET82qifUy3W6OVww6ZWobWub5oqZOVtwolfw==, + } + engines: { node: ">=18" } cpu: [arm] os: [linux] - '@esbuild/linux-ia32@0.25.5': - resolution: {integrity: sha512-sQ7l00M8bSv36GLV95BVAdhJ2QsIbCuCjh/uYrWiMQSUuV+LpXwIqhgJDcvMTj+VsQmqAHL2yYaasENvJ7CDKA==} - engines: {node: '>=18'} + "@esbuild/linux-ia32@0.25.5": + resolution: + { + integrity: sha512-sQ7l00M8bSv36GLV95BVAdhJ2QsIbCuCjh/uYrWiMQSUuV+LpXwIqhgJDcvMTj+VsQmqAHL2yYaasENvJ7CDKA==, + } + engines: { node: ">=18" } cpu: [ia32] os: [linux] - '@esbuild/linux-loong64@0.25.5': - resolution: {integrity: sha512-0ur7ae16hDUC4OL5iEnDb0tZHDxYmuQyhKhsPBV8f99f6Z9KQM02g33f93rNH5A30agMS46u2HP6qTdEt6Q1kg==} - engines: {node: '>=18'} + "@esbuild/linux-loong64@0.25.5": + resolution: + { + integrity: sha512-0ur7ae16hDUC4OL5iEnDb0tZHDxYmuQyhKhsPBV8f99f6Z9KQM02g33f93rNH5A30agMS46u2HP6qTdEt6Q1kg==, + } + engines: { node: ">=18" } cpu: [loong64] os: [linux] - '@esbuild/linux-mips64el@0.25.5': - resolution: {integrity: sha512-kB/66P1OsHO5zLz0i6X0RxlQ+3cu0mkxS3TKFvkb5lin6uwZ/ttOkP3Z8lfR9mJOBk14ZwZ9182SIIWFGNmqmg==} - engines: {node: '>=18'} + "@esbuild/linux-mips64el@0.25.5": + resolution: + { + integrity: sha512-kB/66P1OsHO5zLz0i6X0RxlQ+3cu0mkxS3TKFvkb5lin6uwZ/ttOkP3Z8lfR9mJOBk14ZwZ9182SIIWFGNmqmg==, + } + engines: { node: ">=18" } cpu: [mips64el] os: [linux] - '@esbuild/linux-ppc64@0.25.5': - resolution: {integrity: sha512-UZCmJ7r9X2fe2D6jBmkLBMQetXPXIsZjQJCjgwpVDz+YMcS6oFR27alkgGv3Oqkv07bxdvw7fyB71/olceJhkQ==} - engines: {node: '>=18'} + "@esbuild/linux-ppc64@0.25.5": + resolution: + { + integrity: sha512-UZCmJ7r9X2fe2D6jBmkLBMQetXPXIsZjQJCjgwpVDz+YMcS6oFR27alkgGv3Oqkv07bxdvw7fyB71/olceJhkQ==, + } + engines: { node: ">=18" } cpu: [ppc64] os: [linux] - '@esbuild/linux-riscv64@0.25.5': - resolution: {integrity: sha512-kTxwu4mLyeOlsVIFPfQo+fQJAV9mh24xL+y+Bm6ej067sYANjyEw1dNHmvoqxJUCMnkBdKpvOn0Ahql6+4VyeA==} - engines: {node: '>=18'} + "@esbuild/linux-riscv64@0.25.5": + resolution: + { + integrity: sha512-kTxwu4mLyeOlsVIFPfQo+fQJAV9mh24xL+y+Bm6ej067sYANjyEw1dNHmvoqxJUCMnkBdKpvOn0Ahql6+4VyeA==, + } + engines: { node: ">=18" } cpu: [riscv64] os: [linux] - '@esbuild/linux-s390x@0.25.5': - resolution: {integrity: sha512-K2dSKTKfmdh78uJ3NcWFiqyRrimfdinS5ErLSn3vluHNeHVnBAFWC8a4X5N+7FgVE1EjXS1QDZbpqZBjfrqMTQ==} - engines: {node: '>=18'} + "@esbuild/linux-s390x@0.25.5": + resolution: + { + integrity: sha512-K2dSKTKfmdh78uJ3NcWFiqyRrimfdinS5ErLSn3vluHNeHVnBAFWC8a4X5N+7FgVE1EjXS1QDZbpqZBjfrqMTQ==, + } + engines: { node: ">=18" } cpu: [s390x] os: [linux] - '@esbuild/linux-x64@0.25.5': - resolution: {integrity: sha512-uhj8N2obKTE6pSZ+aMUbqq+1nXxNjZIIjCjGLfsWvVpy7gKCOL6rsY1MhRh9zLtUtAI7vpgLMK6DxjO8Qm9lJw==} - engines: {node: '>=18'} + "@esbuild/linux-x64@0.25.5": + resolution: + { + integrity: sha512-uhj8N2obKTE6pSZ+aMUbqq+1nXxNjZIIjCjGLfsWvVpy7gKCOL6rsY1MhRh9zLtUtAI7vpgLMK6DxjO8Qm9lJw==, + } + engines: { node: ">=18" } cpu: [x64] os: [linux] - '@esbuild/netbsd-arm64@0.25.5': - resolution: {integrity: sha512-pwHtMP9viAy1oHPvgxtOv+OkduK5ugofNTVDilIzBLpoWAM16r7b/mxBvfpuQDpRQFMfuVr5aLcn4yveGvBZvw==} - engines: {node: '>=18'} + "@esbuild/netbsd-arm64@0.25.5": + resolution: + { + integrity: sha512-pwHtMP9viAy1oHPvgxtOv+OkduK5ugofNTVDilIzBLpoWAM16r7b/mxBvfpuQDpRQFMfuVr5aLcn4yveGvBZvw==, + } + engines: { node: ">=18" } cpu: [arm64] os: [netbsd] - '@esbuild/netbsd-x64@0.25.5': - resolution: {integrity: sha512-WOb5fKrvVTRMfWFNCroYWWklbnXH0Q5rZppjq0vQIdlsQKuw6mdSihwSo4RV/YdQ5UCKKvBy7/0ZZYLBZKIbwQ==} - engines: {node: '>=18'} + "@esbuild/netbsd-x64@0.25.5": + resolution: + { + integrity: sha512-WOb5fKrvVTRMfWFNCroYWWklbnXH0Q5rZppjq0vQIdlsQKuw6mdSihwSo4RV/YdQ5UCKKvBy7/0ZZYLBZKIbwQ==, + } + engines: { node: ">=18" } cpu: [x64] os: [netbsd] - '@esbuild/openbsd-arm64@0.25.5': - resolution: {integrity: sha512-7A208+uQKgTxHd0G0uqZO8UjK2R0DDb4fDmERtARjSHWxqMTye4Erz4zZafx7Di9Cv+lNHYuncAkiGFySoD+Mw==} - engines: {node: '>=18'} + "@esbuild/openbsd-arm64@0.25.5": + resolution: + { + integrity: sha512-7A208+uQKgTxHd0G0uqZO8UjK2R0DDb4fDmERtARjSHWxqMTye4Erz4zZafx7Di9Cv+lNHYuncAkiGFySoD+Mw==, + } + engines: { node: ">=18" } cpu: [arm64] os: [openbsd] - '@esbuild/openbsd-x64@0.25.5': - resolution: {integrity: sha512-G4hE405ErTWraiZ8UiSoesH8DaCsMm0Cay4fsFWOOUcz8b8rC6uCvnagr+gnioEjWn0wC+o1/TAHt+It+MpIMg==} - engines: {node: '>=18'} + "@esbuild/openbsd-x64@0.25.5": + resolution: + { + integrity: sha512-G4hE405ErTWraiZ8UiSoesH8DaCsMm0Cay4fsFWOOUcz8b8rC6uCvnagr+gnioEjWn0wC+o1/TAHt+It+MpIMg==, + } + engines: { node: ">=18" } cpu: [x64] os: [openbsd] - '@esbuild/sunos-x64@0.25.5': - resolution: {integrity: sha512-l+azKShMy7FxzY0Rj4RCt5VD/q8mG/e+mDivgspo+yL8zW7qEwctQ6YqKX34DTEleFAvCIUviCFX1SDZRSyMQA==} - engines: {node: '>=18'} + "@esbuild/sunos-x64@0.25.5": + resolution: + { + integrity: sha512-l+azKShMy7FxzY0Rj4RCt5VD/q8mG/e+mDivgspo+yL8zW7qEwctQ6YqKX34DTEleFAvCIUviCFX1SDZRSyMQA==, + } + engines: { node: ">=18" } cpu: [x64] os: [sunos] - '@esbuild/win32-arm64@0.25.5': - resolution: {integrity: sha512-O2S7SNZzdcFG7eFKgvwUEZ2VG9D/sn/eIiz8XRZ1Q/DO5a3s76Xv0mdBzVM5j5R639lXQmPmSo0iRpHqUUrsxw==} - engines: {node: '>=18'} + "@esbuild/win32-arm64@0.25.5": + resolution: + { + integrity: sha512-O2S7SNZzdcFG7eFKgvwUEZ2VG9D/sn/eIiz8XRZ1Q/DO5a3s76Xv0mdBzVM5j5R639lXQmPmSo0iRpHqUUrsxw==, + } + engines: { node: ">=18" } cpu: [arm64] os: [win32] - '@esbuild/win32-ia32@0.25.5': - resolution: {integrity: sha512-onOJ02pqs9h1iMJ1PQphR+VZv8qBMQ77Klcsqv9CNW2w6yLqoURLcgERAIurY6QE63bbLuqgP9ATqajFLK5AMQ==} - engines: {node: '>=18'} + "@esbuild/win32-ia32@0.25.5": + resolution: + { + integrity: sha512-onOJ02pqs9h1iMJ1PQphR+VZv8qBMQ77Klcsqv9CNW2w6yLqoURLcgERAIurY6QE63bbLuqgP9ATqajFLK5AMQ==, + } + engines: { node: ">=18" } cpu: [ia32] os: [win32] - '@esbuild/win32-x64@0.25.5': - resolution: {integrity: sha512-TXv6YnJ8ZMVdX+SXWVBo/0p8LTcrUYngpWjvm91TMjjBQii7Oz11Lw5lbDV5Y0TzuhSJHwiH4hEtC1I42mMS0g==} - engines: {node: '>=18'} + "@esbuild/win32-x64@0.25.5": + resolution: + { + integrity: sha512-TXv6YnJ8ZMVdX+SXWVBo/0p8LTcrUYngpWjvm91TMjjBQii7Oz11Lw5lbDV5Y0TzuhSJHwiH4hEtC1I42mMS0g==, + } + engines: { node: ">=18" } cpu: [x64] os: [win32] - '@eslint-community/eslint-utils@4.7.0': - resolution: {integrity: sha512-dyybb3AcajC7uha6CvhdVRJqaKyn7w2YKqKyAN37NKYgZT36w+iRb0Dymmc5qEJ549c/S31cMMSFd75bteCpCw==} - engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0} + "@eslint-community/eslint-utils@4.7.0": + resolution: + { + integrity: sha512-dyybb3AcajC7uha6CvhdVRJqaKyn7w2YKqKyAN37NKYgZT36w+iRb0Dymmc5qEJ549c/S31cMMSFd75bteCpCw==, + } + engines: { node: ^12.22.0 || ^14.17.0 || >=16.0.0 } peerDependencies: eslint: ^6.0.0 || ^7.0.0 || >=8.0.0 - '@eslint-community/regexpp@4.12.1': - resolution: {integrity: sha512-CCZCDJuduB9OUkFkY2IgppNZMi2lBQgD2qzwXkEia16cge2pijY/aXi96CJMquDMn3nJdlPV1A5KrJEXwfLNzQ==} - engines: {node: ^12.0.0 || ^14.0.0 || >=16.0.0} + "@eslint-community/regexpp@4.12.1": + resolution: + { + integrity: sha512-CCZCDJuduB9OUkFkY2IgppNZMi2lBQgD2qzwXkEia16cge2pijY/aXi96CJMquDMn3nJdlPV1A5KrJEXwfLNzQ==, + } + engines: { node: ^12.0.0 || ^14.0.0 || >=16.0.0 } - '@eslint/config-array@0.21.0': - resolution: {integrity: sha512-ENIdc4iLu0d93HeYirvKmrzshzofPw6VkZRKQGe9Nv46ZnWUzcF1xV01dcvEg/1wXUR61OmmlSfyeyO7EvjLxQ==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + "@eslint/config-array@0.21.0": + resolution: + { + integrity: sha512-ENIdc4iLu0d93HeYirvKmrzshzofPw6VkZRKQGe9Nv46ZnWUzcF1xV01dcvEg/1wXUR61OmmlSfyeyO7EvjLxQ==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } - '@eslint/config-helpers@0.3.0': - resolution: {integrity: sha512-ViuymvFmcJi04qdZeDc2whTHryouGcDlaxPqarTD0ZE10ISpxGUVZGZDx4w01upyIynL3iu6IXH2bS1NhclQMw==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + "@eslint/config-helpers@0.3.0": + resolution: + { + integrity: sha512-ViuymvFmcJi04qdZeDc2whTHryouGcDlaxPqarTD0ZE10ISpxGUVZGZDx4w01upyIynL3iu6IXH2bS1NhclQMw==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } - '@eslint/core@0.14.0': - resolution: {integrity: sha512-qIbV0/JZr7iSDjqAc60IqbLdsj9GDt16xQtWD+B78d/HAlvysGdZZ6rpJHGAc2T0FQx1X6thsSPdnoiGKdNtdg==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + "@eslint/core@0.14.0": + resolution: + { + integrity: sha512-qIbV0/JZr7iSDjqAc60IqbLdsj9GDt16xQtWD+B78d/HAlvysGdZZ6rpJHGAc2T0FQx1X6thsSPdnoiGKdNtdg==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } - '@eslint/core@0.15.1': - resolution: {integrity: sha512-bkOp+iumZCCbt1K1CmWf0R9pM5yKpDv+ZXtvSyQpudrI9kuFLp+bM2WOPXImuD/ceQuaa8f5pj93Y7zyECIGNA==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + "@eslint/core@0.15.1": + resolution: + { + integrity: sha512-bkOp+iumZCCbt1K1CmWf0R9pM5yKpDv+ZXtvSyQpudrI9kuFLp+bM2WOPXImuD/ceQuaa8f5pj93Y7zyECIGNA==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } - '@eslint/eslintrc@3.3.1': - resolution: {integrity: sha512-gtF186CXhIl1p4pJNGZw8Yc6RlshoePRvE0X91oPGb3vZ8pM3qOS9W9NGPat9LziaBV7XrJWGylNQXkGcnM3IQ==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + "@eslint/eslintrc@3.3.1": + resolution: + { + integrity: sha512-gtF186CXhIl1p4pJNGZw8Yc6RlshoePRvE0X91oPGb3vZ8pM3qOS9W9NGPat9LziaBV7XrJWGylNQXkGcnM3IQ==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } - '@eslint/js@9.30.0': - resolution: {integrity: sha512-Wzw3wQwPvc9sHM+NjakWTcPx11mbZyiYHuwWa/QfZ7cIRX7WK54PSk7bdyXDaoaopUcMatv1zaQvOAAO8hCdww==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + "@eslint/js@9.30.0": + resolution: + { + integrity: sha512-Wzw3wQwPvc9sHM+NjakWTcPx11mbZyiYHuwWa/QfZ7cIRX7WK54PSk7bdyXDaoaopUcMatv1zaQvOAAO8hCdww==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } - '@eslint/object-schema@2.1.6': - resolution: {integrity: sha512-RBMg5FRL0I0gs51M/guSAj5/e14VQ4tpZnQNWwuDT66P14I43ItmPfIZRhO9fUVIPOAQXU47atlywZ/czoqFPA==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + "@eslint/object-schema@2.1.6": + resolution: + { + integrity: sha512-RBMg5FRL0I0gs51M/guSAj5/e14VQ4tpZnQNWwuDT66P14I43ItmPfIZRhO9fUVIPOAQXU47atlywZ/czoqFPA==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } - '@eslint/plugin-kit@0.3.3': - resolution: {integrity: sha512-1+WqvgNMhmlAambTvT3KPtCl/Ibr68VldY2XY40SL1CE0ZXiakFR/cbTspaF5HsnpDMvcYYoJHfl4980NBjGag==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + "@eslint/plugin-kit@0.3.3": + resolution: + { + integrity: sha512-1+WqvgNMhmlAambTvT3KPtCl/Ibr68VldY2XY40SL1CE0ZXiakFR/cbTspaF5HsnpDMvcYYoJHfl4980NBjGag==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } - '@floating-ui/core@1.7.1': - resolution: {integrity: sha512-azI0DrjMMfIug/ExbBaeDVJXcY0a7EPvPjb2xAJPa4HeimBX+Z18HK8QQR3jb6356SnDDdxx+hinMLcJEDdOjw==} + "@floating-ui/core@1.7.1": + resolution: + { + integrity: sha512-azI0DrjMMfIug/ExbBaeDVJXcY0a7EPvPjb2xAJPa4HeimBX+Z18HK8QQR3jb6356SnDDdxx+hinMLcJEDdOjw==, + } - '@floating-ui/dom@1.7.1': - resolution: {integrity: sha512-cwsmW/zyw5ltYTUeeYJ60CnQuPqmGwuGVhG9w0PRaRKkAyi38BT5CKrpIbb+jtahSwUl04cWzSx9ZOIxeS6RsQ==} + "@floating-ui/dom@1.7.1": + resolution: + { + integrity: sha512-cwsmW/zyw5ltYTUeeYJ60CnQuPqmGwuGVhG9w0PRaRKkAyi38BT5CKrpIbb+jtahSwUl04cWzSx9ZOIxeS6RsQ==, + } - '@floating-ui/react-dom@2.1.3': - resolution: {integrity: sha512-huMBfiU9UnQ2oBwIhgzyIiSpVgvlDstU8CX0AF+wS+KzmYMs0J2a3GwuFHV1Lz+jlrQGeC1fF+Nv0QoumyV0bA==} + "@floating-ui/react-dom@2.1.3": + resolution: + { + integrity: sha512-huMBfiU9UnQ2oBwIhgzyIiSpVgvlDstU8CX0AF+wS+KzmYMs0J2a3GwuFHV1Lz+jlrQGeC1fF+Nv0QoumyV0bA==, + } peerDependencies: - react: '>=16.8.0' - react-dom: '>=16.8.0' + react: ">=16.8.0" + react-dom: ">=16.8.0" - '@floating-ui/utils@0.2.9': - resolution: {integrity: sha512-MDWhGtE+eHw5JW7lq4qhc5yRLS11ERl1c7Z6Xd0a58DozHES6EnNNwUWbMiG4J9Cgj053Bhk8zvlhFYKVhULwg==} + "@floating-ui/utils@0.2.9": + resolution: + { + integrity: sha512-MDWhGtE+eHw5JW7lq4qhc5yRLS11ERl1c7Z6Xd0a58DozHES6EnNNwUWbMiG4J9Cgj053Bhk8zvlhFYKVhULwg==, + } - '@humanfs/core@0.19.1': - resolution: {integrity: sha512-5DyQ4+1JEUzejeK1JGICcideyfUbGixgS9jNgex5nqkW+cY7WZhxBigmieN5Qnw9ZosSNVC9KQKyb+GUaGyKUA==} - engines: {node: '>=18.18.0'} + "@humanfs/core@0.19.1": + resolution: + { + integrity: sha512-5DyQ4+1JEUzejeK1JGICcideyfUbGixgS9jNgex5nqkW+cY7WZhxBigmieN5Qnw9ZosSNVC9KQKyb+GUaGyKUA==, + } + engines: { node: ">=18.18.0" } - '@humanfs/node@0.16.6': - resolution: {integrity: sha512-YuI2ZHQL78Q5HbhDiBA1X4LmYdXCKCMQIfw0pw7piHJwyREFebJUvrQN4cMssyES6x+vfUbx1CIpaQUKYdQZOw==} - engines: {node: '>=18.18.0'} + "@humanfs/node@0.16.6": + resolution: + { + integrity: sha512-YuI2ZHQL78Q5HbhDiBA1X4LmYdXCKCMQIfw0pw7piHJwyREFebJUvrQN4cMssyES6x+vfUbx1CIpaQUKYdQZOw==, + } + engines: { node: ">=18.18.0" } - '@humanwhocodes/module-importer@1.0.1': - resolution: {integrity: sha512-bxveV4V8v5Yb4ncFTT3rPSgZBOpCkjfK0y4oVVVJwIuDVBRMDXrPyXRL988i5ap9m9bnyEEjWfm5WkBmtffLfA==} - engines: {node: '>=12.22'} + "@humanwhocodes/module-importer@1.0.1": + resolution: + { + integrity: sha512-bxveV4V8v5Yb4ncFTT3rPSgZBOpCkjfK0y4oVVVJwIuDVBRMDXrPyXRL988i5ap9m9bnyEEjWfm5WkBmtffLfA==, + } + engines: { node: ">=12.22" } - '@humanwhocodes/retry@0.3.1': - resolution: {integrity: sha512-JBxkERygn7Bv/GbN5Rv8Ul6LVknS+5Bp6RgDC/O8gEBU/yeH5Ui5C/OlWrTb6qct7LjjfT6Re2NxB0ln0yYybA==} - engines: {node: '>=18.18'} + "@humanwhocodes/retry@0.3.1": + resolution: + { + integrity: sha512-JBxkERygn7Bv/GbN5Rv8Ul6LVknS+5Bp6RgDC/O8gEBU/yeH5Ui5C/OlWrTb6qct7LjjfT6Re2NxB0ln0yYybA==, + } + engines: { node: ">=18.18" } - '@humanwhocodes/retry@0.4.3': - resolution: {integrity: sha512-bV0Tgo9K4hfPCek+aMAn81RppFKv2ySDQeMoSZuvTASywNTnVJCArCZE2FWqpvIatKu7VMRLWlR1EazvVhDyhQ==} - engines: {node: '>=18.18'} + "@humanwhocodes/retry@0.4.3": + resolution: + { + integrity: sha512-bV0Tgo9K4hfPCek+aMAn81RppFKv2ySDQeMoSZuvTASywNTnVJCArCZE2FWqpvIatKu7VMRLWlR1EazvVhDyhQ==, + } + engines: { node: ">=18.18" } - '@img/sharp-darwin-arm64@0.34.2': - resolution: {integrity: sha512-OfXHZPppddivUJnqyKoi5YVeHRkkNE2zUFT2gbpKxp/JZCFYEYubnMg+gOp6lWfasPrTS+KPosKqdI+ELYVDtg==} - engines: {node: ^18.17.0 || ^20.3.0 || >=21.0.0} + "@img/sharp-darwin-arm64@0.34.2": + resolution: + { + integrity: sha512-OfXHZPppddivUJnqyKoi5YVeHRkkNE2zUFT2gbpKxp/JZCFYEYubnMg+gOp6lWfasPrTS+KPosKqdI+ELYVDtg==, + } + engines: { node: ^18.17.0 || ^20.3.0 || >=21.0.0 } cpu: [arm64] os: [darwin] - '@img/sharp-darwin-x64@0.34.2': - resolution: {integrity: sha512-dYvWqmjU9VxqXmjEtjmvHnGqF8GrVjM2Epj9rJ6BUIXvk8slvNDJbhGFvIoXzkDhrJC2jUxNLz/GUjjvSzfw+g==} - engines: {node: ^18.17.0 || ^20.3.0 || >=21.0.0} + "@img/sharp-darwin-x64@0.34.2": + resolution: + { + integrity: sha512-dYvWqmjU9VxqXmjEtjmvHnGqF8GrVjM2Epj9rJ6BUIXvk8slvNDJbhGFvIoXzkDhrJC2jUxNLz/GUjjvSzfw+g==, + } + engines: { node: ^18.17.0 || ^20.3.0 || >=21.0.0 } cpu: [x64] os: [darwin] - '@img/sharp-libvips-darwin-arm64@1.1.0': - resolution: {integrity: sha512-HZ/JUmPwrJSoM4DIQPv/BfNh9yrOA8tlBbqbLz4JZ5uew2+o22Ik+tHQJcih7QJuSa0zo5coHTfD5J8inqj9DA==} + "@img/sharp-libvips-darwin-arm64@1.1.0": + resolution: + { + integrity: sha512-HZ/JUmPwrJSoM4DIQPv/BfNh9yrOA8tlBbqbLz4JZ5uew2+o22Ik+tHQJcih7QJuSa0zo5coHTfD5J8inqj9DA==, + } cpu: [arm64] os: [darwin] - '@img/sharp-libvips-darwin-x64@1.1.0': - resolution: {integrity: sha512-Xzc2ToEmHN+hfvsl9wja0RlnXEgpKNmftriQp6XzY/RaSfwD9th+MSh0WQKzUreLKKINb3afirxW7A0fz2YWuQ==} + "@img/sharp-libvips-darwin-x64@1.1.0": + resolution: + { + integrity: sha512-Xzc2ToEmHN+hfvsl9wja0RlnXEgpKNmftriQp6XzY/RaSfwD9th+MSh0WQKzUreLKKINb3afirxW7A0fz2YWuQ==, + } cpu: [x64] os: [darwin] - '@img/sharp-libvips-linux-arm64@1.1.0': - resolution: {integrity: sha512-IVfGJa7gjChDET1dK9SekxFFdflarnUB8PwW8aGwEoF3oAsSDuNUTYS+SKDOyOJxQyDC1aPFMuRYLoDInyV9Ew==} + "@img/sharp-libvips-linux-arm64@1.1.0": + resolution: + { + integrity: sha512-IVfGJa7gjChDET1dK9SekxFFdflarnUB8PwW8aGwEoF3oAsSDuNUTYS+SKDOyOJxQyDC1aPFMuRYLoDInyV9Ew==, + } cpu: [arm64] os: [linux] - '@img/sharp-libvips-linux-arm@1.1.0': - resolution: {integrity: sha512-s8BAd0lwUIvYCJyRdFqvsj+BJIpDBSxs6ivrOPm/R7piTs5UIwY5OjXrP2bqXC9/moGsyRa37eYWYCOGVXxVrA==} + "@img/sharp-libvips-linux-arm@1.1.0": + resolution: + { + integrity: sha512-s8BAd0lwUIvYCJyRdFqvsj+BJIpDBSxs6ivrOPm/R7piTs5UIwY5OjXrP2bqXC9/moGsyRa37eYWYCOGVXxVrA==, + } cpu: [arm] os: [linux] - '@img/sharp-libvips-linux-ppc64@1.1.0': - resolution: {integrity: sha512-tiXxFZFbhnkWE2LA8oQj7KYR+bWBkiV2nilRldT7bqoEZ4HiDOcePr9wVDAZPi/Id5fT1oY9iGnDq20cwUz8lQ==} + "@img/sharp-libvips-linux-ppc64@1.1.0": + resolution: + { + integrity: sha512-tiXxFZFbhnkWE2LA8oQj7KYR+bWBkiV2nilRldT7bqoEZ4HiDOcePr9wVDAZPi/Id5fT1oY9iGnDq20cwUz8lQ==, + } cpu: [ppc64] os: [linux] - '@img/sharp-libvips-linux-s390x@1.1.0': - resolution: {integrity: sha512-xukSwvhguw7COyzvmjydRb3x/09+21HykyapcZchiCUkTThEQEOMtBj9UhkaBRLuBrgLFzQ2wbxdeCCJW/jgJA==} + "@img/sharp-libvips-linux-s390x@1.1.0": + resolution: + { + integrity: sha512-xukSwvhguw7COyzvmjydRb3x/09+21HykyapcZchiCUkTThEQEOMtBj9UhkaBRLuBrgLFzQ2wbxdeCCJW/jgJA==, + } cpu: [s390x] os: [linux] - '@img/sharp-libvips-linux-x64@1.1.0': - resolution: {integrity: sha512-yRj2+reB8iMg9W5sULM3S74jVS7zqSzHG3Ol/twnAAkAhnGQnpjj6e4ayUz7V+FpKypwgs82xbRdYtchTTUB+Q==} + "@img/sharp-libvips-linux-x64@1.1.0": + resolution: + { + integrity: sha512-yRj2+reB8iMg9W5sULM3S74jVS7zqSzHG3Ol/twnAAkAhnGQnpjj6e4ayUz7V+FpKypwgs82xbRdYtchTTUB+Q==, + } cpu: [x64] os: [linux] - '@img/sharp-libvips-linuxmusl-arm64@1.1.0': - resolution: {integrity: sha512-jYZdG+whg0MDK+q2COKbYidaqW/WTz0cc1E+tMAusiDygrM4ypmSCjOJPmFTvHHJ8j/6cAGyeDWZOsK06tP33w==} + "@img/sharp-libvips-linuxmusl-arm64@1.1.0": + resolution: + { + integrity: sha512-jYZdG+whg0MDK+q2COKbYidaqW/WTz0cc1E+tMAusiDygrM4ypmSCjOJPmFTvHHJ8j/6cAGyeDWZOsK06tP33w==, + } cpu: [arm64] os: [linux] - '@img/sharp-libvips-linuxmusl-x64@1.1.0': - resolution: {integrity: sha512-wK7SBdwrAiycjXdkPnGCPLjYb9lD4l6Ze2gSdAGVZrEL05AOUJESWU2lhlC+Ffn5/G+VKuSm6zzbQSzFX/P65A==} + "@img/sharp-libvips-linuxmusl-x64@1.1.0": + resolution: + { + integrity: sha512-wK7SBdwrAiycjXdkPnGCPLjYb9lD4l6Ze2gSdAGVZrEL05AOUJESWU2lhlC+Ffn5/G+VKuSm6zzbQSzFX/P65A==, + } cpu: [x64] os: [linux] - '@img/sharp-linux-arm64@0.34.2': - resolution: {integrity: sha512-D8n8wgWmPDakc83LORcfJepdOSN6MvWNzzz2ux0MnIbOqdieRZwVYY32zxVx+IFUT8er5KPcyU3XXsn+GzG/0Q==} - engines: {node: ^18.17.0 || ^20.3.0 || >=21.0.0} + "@img/sharp-linux-arm64@0.34.2": + resolution: + { + integrity: sha512-D8n8wgWmPDakc83LORcfJepdOSN6MvWNzzz2ux0MnIbOqdieRZwVYY32zxVx+IFUT8er5KPcyU3XXsn+GzG/0Q==, + } + engines: { node: ^18.17.0 || ^20.3.0 || >=21.0.0 } cpu: [arm64] os: [linux] - '@img/sharp-linux-arm@0.34.2': - resolution: {integrity: sha512-0DZzkvuEOqQUP9mo2kjjKNok5AmnOr1jB2XYjkaoNRwpAYMDzRmAqUIa1nRi58S2WswqSfPOWLNOr0FDT3H5RQ==} - engines: {node: ^18.17.0 || ^20.3.0 || >=21.0.0} + "@img/sharp-linux-arm@0.34.2": + resolution: + { + integrity: sha512-0DZzkvuEOqQUP9mo2kjjKNok5AmnOr1jB2XYjkaoNRwpAYMDzRmAqUIa1nRi58S2WswqSfPOWLNOr0FDT3H5RQ==, + } + engines: { node: ^18.17.0 || ^20.3.0 || >=21.0.0 } cpu: [arm] os: [linux] - '@img/sharp-linux-s390x@0.34.2': - resolution: {integrity: sha512-EGZ1xwhBI7dNISwxjChqBGELCWMGDvmxZXKjQRuqMrakhO8QoMgqCrdjnAqJq/CScxfRn+Bb7suXBElKQpPDiw==} - engines: {node: ^18.17.0 || ^20.3.0 || >=21.0.0} + "@img/sharp-linux-s390x@0.34.2": + resolution: + { + integrity: sha512-EGZ1xwhBI7dNISwxjChqBGELCWMGDvmxZXKjQRuqMrakhO8QoMgqCrdjnAqJq/CScxfRn+Bb7suXBElKQpPDiw==, + } + engines: { node: ^18.17.0 || ^20.3.0 || >=21.0.0 } cpu: [s390x] os: [linux] - '@img/sharp-linux-x64@0.34.2': - resolution: {integrity: sha512-sD7J+h5nFLMMmOXYH4DD9UtSNBD05tWSSdWAcEyzqW8Cn5UxXvsHAxmxSesYUsTOBmUnjtxghKDl15EvfqLFbQ==} - engines: {node: ^18.17.0 || ^20.3.0 || >=21.0.0} + "@img/sharp-linux-x64@0.34.2": + resolution: + { + integrity: sha512-sD7J+h5nFLMMmOXYH4DD9UtSNBD05tWSSdWAcEyzqW8Cn5UxXvsHAxmxSesYUsTOBmUnjtxghKDl15EvfqLFbQ==, + } + engines: { node: ^18.17.0 || ^20.3.0 || >=21.0.0 } cpu: [x64] os: [linux] - '@img/sharp-linuxmusl-arm64@0.34.2': - resolution: {integrity: sha512-NEE2vQ6wcxYav1/A22OOxoSOGiKnNmDzCYFOZ949xFmrWZOVII1Bp3NqVVpvj+3UeHMFyN5eP/V5hzViQ5CZNA==} - engines: {node: ^18.17.0 || ^20.3.0 || >=21.0.0} + "@img/sharp-linuxmusl-arm64@0.34.2": + resolution: + { + integrity: sha512-NEE2vQ6wcxYav1/A22OOxoSOGiKnNmDzCYFOZ949xFmrWZOVII1Bp3NqVVpvj+3UeHMFyN5eP/V5hzViQ5CZNA==, + } + engines: { node: ^18.17.0 || ^20.3.0 || >=21.0.0 } cpu: [arm64] os: [linux] - '@img/sharp-linuxmusl-x64@0.34.2': - resolution: {integrity: sha512-DOYMrDm5E6/8bm/yQLCWyuDJwUnlevR8xtF8bs+gjZ7cyUNYXiSf/E8Kp0Ss5xasIaXSHzb888V1BE4i1hFhAA==} - engines: {node: ^18.17.0 || ^20.3.0 || >=21.0.0} + "@img/sharp-linuxmusl-x64@0.34.2": + resolution: + { + integrity: sha512-DOYMrDm5E6/8bm/yQLCWyuDJwUnlevR8xtF8bs+gjZ7cyUNYXiSf/E8Kp0Ss5xasIaXSHzb888V1BE4i1hFhAA==, + } + engines: { node: ^18.17.0 || ^20.3.0 || >=21.0.0 } cpu: [x64] os: [linux] - '@img/sharp-wasm32@0.34.2': - resolution: {integrity: sha512-/VI4mdlJ9zkaq53MbIG6rZY+QRN3MLbR6usYlgITEzi4Rpx5S6LFKsycOQjkOGmqTNmkIdLjEvooFKwww6OpdQ==} - engines: {node: ^18.17.0 || ^20.3.0 || >=21.0.0} + "@img/sharp-wasm32@0.34.2": + resolution: + { + integrity: sha512-/VI4mdlJ9zkaq53MbIG6rZY+QRN3MLbR6usYlgITEzi4Rpx5S6LFKsycOQjkOGmqTNmkIdLjEvooFKwww6OpdQ==, + } + engines: { node: ^18.17.0 || ^20.3.0 || >=21.0.0 } cpu: [wasm32] - '@img/sharp-win32-arm64@0.34.2': - resolution: {integrity: sha512-cfP/r9FdS63VA5k0xiqaNaEoGxBg9k7uE+RQGzuK9fHt7jib4zAVVseR9LsE4gJcNWgT6APKMNnCcnyOtmSEUQ==} - engines: {node: ^18.17.0 || ^20.3.0 || >=21.0.0} + "@img/sharp-win32-arm64@0.34.2": + resolution: + { + integrity: sha512-cfP/r9FdS63VA5k0xiqaNaEoGxBg9k7uE+RQGzuK9fHt7jib4zAVVseR9LsE4gJcNWgT6APKMNnCcnyOtmSEUQ==, + } + engines: { node: ^18.17.0 || ^20.3.0 || >=21.0.0 } cpu: [arm64] os: [win32] - '@img/sharp-win32-ia32@0.34.2': - resolution: {integrity: sha512-QLjGGvAbj0X/FXl8n1WbtQ6iVBpWU7JO94u/P2M4a8CFYsvQi4GW2mRy/JqkRx0qpBzaOdKJKw8uc930EX2AHw==} - engines: {node: ^18.17.0 || ^20.3.0 || >=21.0.0} + "@img/sharp-win32-ia32@0.34.2": + resolution: + { + integrity: sha512-QLjGGvAbj0X/FXl8n1WbtQ6iVBpWU7JO94u/P2M4a8CFYsvQi4GW2mRy/JqkRx0qpBzaOdKJKw8uc930EX2AHw==, + } + engines: { node: ^18.17.0 || ^20.3.0 || >=21.0.0 } cpu: [ia32] os: [win32] - '@img/sharp-win32-x64@0.34.2': - resolution: {integrity: sha512-aUdT6zEYtDKCaxkofmmJDJYGCf0+pJg3eU9/oBuqvEeoB9dKI6ZLc/1iLJCTuJQDO4ptntAlkUmHgGjyuobZbw==} - engines: {node: ^18.17.0 || ^20.3.0 || >=21.0.0} + "@img/sharp-win32-x64@0.34.2": + resolution: + { + integrity: sha512-aUdT6zEYtDKCaxkofmmJDJYGCf0+pJg3eU9/oBuqvEeoB9dKI6ZLc/1iLJCTuJQDO4ptntAlkUmHgGjyuobZbw==, + } + engines: { node: ^18.17.0 || ^20.3.0 || >=21.0.0 } cpu: [x64] os: [win32] - '@isaacs/cliui@8.0.2': - resolution: {integrity: sha512-O8jcjabXaleOG9DQ0+ARXWZBTfnP4WNAqzuiJK7ll44AmxGKv/J2M4TPjxjY3znBCfvBXFzucm1twdyFybFqEA==} - engines: {node: '>=12'} + "@isaacs/cliui@8.0.2": + resolution: + { + integrity: sha512-O8jcjabXaleOG9DQ0+ARXWZBTfnP4WNAqzuiJK7ll44AmxGKv/J2M4TPjxjY3znBCfvBXFzucm1twdyFybFqEA==, + } + engines: { node: ">=12" } - '@isaacs/fs-minipass@4.0.1': - resolution: {integrity: sha512-wgm9Ehl2jpeqP3zw/7mo3kRHFp5MEDhqAdwy1fTGkHAwnkGOVsgpvQhL8B5n1qlb01jV3n/bI0ZfZp5lWA1k4w==} - engines: {node: '>=18.0.0'} + "@isaacs/fs-minipass@4.0.1": + resolution: + { + integrity: sha512-wgm9Ehl2jpeqP3zw/7mo3kRHFp5MEDhqAdwy1fTGkHAwnkGOVsgpvQhL8B5n1qlb01jV3n/bI0ZfZp5lWA1k4w==, + } + engines: { node: ">=18.0.0" } - '@istanbuljs/schema@0.1.3': - resolution: {integrity: sha512-ZXRY4jNvVgSVQ8DL3LTcakaAtXwTVUxE81hslsyD2AtoXW/wVob10HkOJ1X/pAlcI7D+2YoZKg5do8G/w6RYgA==} - engines: {node: '>=8'} + "@istanbuljs/schema@0.1.3": + resolution: + { + integrity: sha512-ZXRY4jNvVgSVQ8DL3LTcakaAtXwTVUxE81hslsyD2AtoXW/wVob10HkOJ1X/pAlcI7D+2YoZKg5do8G/w6RYgA==, + } + engines: { node: ">=8" } - '@jridgewell/gen-mapping@0.3.8': - resolution: {integrity: sha512-imAbBGkb+ebQyxKgzv5Hu2nmROxoDOXHh80evxdoXNOrvAnVx7zimzc1Oo5h9RlfV4vPXaE2iM5pOFbvOCClWA==} - engines: {node: '>=6.0.0'} + "@jridgewell/gen-mapping@0.3.8": + resolution: + { + integrity: sha512-imAbBGkb+ebQyxKgzv5Hu2nmROxoDOXHh80evxdoXNOrvAnVx7zimzc1Oo5h9RlfV4vPXaE2iM5pOFbvOCClWA==, + } + engines: { node: ">=6.0.0" } - '@jridgewell/resolve-uri@3.1.2': - resolution: {integrity: sha512-bRISgCIjP20/tbWSPWMEi54QVPRZExkuD9lJL+UIxUKtwVJA8wW1Trb1jMs1RFXo1CBTNZ/5hpC9QvmKWdopKw==} - engines: {node: '>=6.0.0'} + "@jridgewell/resolve-uri@3.1.2": + resolution: + { + integrity: sha512-bRISgCIjP20/tbWSPWMEi54QVPRZExkuD9lJL+UIxUKtwVJA8wW1Trb1jMs1RFXo1CBTNZ/5hpC9QvmKWdopKw==, + } + engines: { node: ">=6.0.0" } - '@jridgewell/set-array@1.2.1': - resolution: {integrity: sha512-R8gLRTZeyp03ymzP/6Lil/28tGeGEzhx1q2k703KGWRAI1VdvPIXdG70VJc2pAMw3NA6JKL5hhFu1sJX0Mnn/A==} - engines: {node: '>=6.0.0'} + "@jridgewell/set-array@1.2.1": + resolution: + { + integrity: sha512-R8gLRTZeyp03ymzP/6Lil/28tGeGEzhx1q2k703KGWRAI1VdvPIXdG70VJc2pAMw3NA6JKL5hhFu1sJX0Mnn/A==, + } + engines: { node: ">=6.0.0" } - '@jridgewell/sourcemap-codec@1.5.0': - resolution: {integrity: sha512-gv3ZRaISU3fjPAgNsriBRqGWQL6quFx04YMPW/zD8XMLsU32mhCCbfbO6KZFLjvYpCZ8zyDEgqsgf+PwPaM7GQ==} + "@jridgewell/sourcemap-codec@1.5.0": + resolution: + { + integrity: sha512-gv3ZRaISU3fjPAgNsriBRqGWQL6quFx04YMPW/zD8XMLsU32mhCCbfbO6KZFLjvYpCZ8zyDEgqsgf+PwPaM7GQ==, + } - '@jridgewell/trace-mapping@0.3.25': - resolution: {integrity: sha512-vNk6aEwybGtawWmy/PzwnGDOjCkLWSD2wqvjGGAgOAwCGWySYXfYoxt00IJkTF+8Lb57DwOb3Aa0o9CApepiYQ==} + "@jridgewell/trace-mapping@0.3.25": + resolution: + { + integrity: sha512-vNk6aEwybGtawWmy/PzwnGDOjCkLWSD2wqvjGGAgOAwCGWySYXfYoxt00IJkTF+8Lb57DwOb3Aa0o9CApepiYQ==, + } - '@jridgewell/trace-mapping@0.3.9': - resolution: {integrity: sha512-3Belt6tdc8bPgAtbcmdtNJlirVoTmEb5e2gC94PnkwEW9jI6CAHUeoG85tjWP5WquqfavoMtMwiG4P926ZKKuQ==} + "@jridgewell/trace-mapping@0.3.9": + resolution: + { + integrity: sha512-3Belt6tdc8bPgAtbcmdtNJlirVoTmEb5e2gC94PnkwEW9jI6CAHUeoG85tjWP5WquqfavoMtMwiG4P926ZKKuQ==, + } - '@napi-rs/wasm-runtime@0.2.11': - resolution: {integrity: sha512-9DPkXtvHydrcOsopiYpUgPHpmj0HWZKMUnL2dZqpvC42lsratuBG06V5ipyno0fUek5VlFsNQ+AcFATSrJXgMA==} + "@napi-rs/wasm-runtime@0.2.11": + resolution: + { + integrity: sha512-9DPkXtvHydrcOsopiYpUgPHpmj0HWZKMUnL2dZqpvC42lsratuBG06V5ipyno0fUek5VlFsNQ+AcFATSrJXgMA==, + } - '@next/env@15.3.4': - resolution: {integrity: sha512-ZkdYzBseS6UjYzz6ylVKPOK+//zLWvD6Ta+vpoye8cW11AjiQjGYVibF0xuvT4L0iJfAPfZLFidaEzAOywyOAQ==} + "@next/env@15.3.4": + resolution: + { + integrity: sha512-ZkdYzBseS6UjYzz6ylVKPOK+//zLWvD6Ta+vpoye8cW11AjiQjGYVibF0xuvT4L0iJfAPfZLFidaEzAOywyOAQ==, + } - '@next/eslint-plugin-next@15.3.4': - resolution: {integrity: sha512-lBxYdj7TI8phbJcLSAqDt57nIcobEign5NYIKCiy0hXQhrUbTqLqOaSDi568U6vFg4hJfBdZYsG4iP/uKhCqgg==} + "@next/eslint-plugin-next@15.3.4": + resolution: + { + integrity: sha512-lBxYdj7TI8phbJcLSAqDt57nIcobEign5NYIKCiy0hXQhrUbTqLqOaSDi568U6vFg4hJfBdZYsG4iP/uKhCqgg==, + } - '@next/swc-darwin-arm64@15.3.4': - resolution: {integrity: sha512-z0qIYTONmPRbwHWvpyrFXJd5F9YWLCsw3Sjrzj2ZvMYy9NPQMPZ1NjOJh4ojr4oQzcGYwgJKfidzehaNa1BpEg==} - engines: {node: '>= 10'} + "@next/swc-darwin-arm64@15.3.4": + resolution: + { + integrity: sha512-z0qIYTONmPRbwHWvpyrFXJd5F9YWLCsw3Sjrzj2ZvMYy9NPQMPZ1NjOJh4ojr4oQzcGYwgJKfidzehaNa1BpEg==, + } + engines: { node: ">= 10" } cpu: [arm64] os: [darwin] - '@next/swc-darwin-x64@15.3.4': - resolution: {integrity: sha512-Z0FYJM8lritw5Wq+vpHYuCIzIlEMjewG2aRkc3Hi2rcbULknYL/xqfpBL23jQnCSrDUGAo/AEv0Z+s2bff9Zkw==} - engines: {node: '>= 10'} + "@next/swc-darwin-x64@15.3.4": + resolution: + { + integrity: sha512-Z0FYJM8lritw5Wq+vpHYuCIzIlEMjewG2aRkc3Hi2rcbULknYL/xqfpBL23jQnCSrDUGAo/AEv0Z+s2bff9Zkw==, + } + engines: { node: ">= 10" } cpu: [x64] os: [darwin] - '@next/swc-linux-arm64-gnu@15.3.4': - resolution: {integrity: sha512-l8ZQOCCg7adwmsnFm8m5q9eIPAHdaB2F3cxhufYtVo84pymwKuWfpYTKcUiFcutJdp9xGHC+F1Uq3xnFU1B/7g==} - engines: {node: '>= 10'} + "@next/swc-linux-arm64-gnu@15.3.4": + resolution: + { + integrity: sha512-l8ZQOCCg7adwmsnFm8m5q9eIPAHdaB2F3cxhufYtVo84pymwKuWfpYTKcUiFcutJdp9xGHC+F1Uq3xnFU1B/7g==, + } + engines: { node: ">= 10" } cpu: [arm64] os: [linux] - '@next/swc-linux-arm64-musl@15.3.4': - resolution: {integrity: sha512-wFyZ7X470YJQtpKot4xCY3gpdn8lE9nTlldG07/kJYexCUpX1piX+MBfZdvulo+t1yADFVEuzFfVHfklfEx8kw==} - engines: {node: '>= 10'} + "@next/swc-linux-arm64-musl@15.3.4": + resolution: + { + integrity: sha512-wFyZ7X470YJQtpKot4xCY3gpdn8lE9nTlldG07/kJYexCUpX1piX+MBfZdvulo+t1yADFVEuzFfVHfklfEx8kw==, + } + engines: { node: ">= 10" } cpu: [arm64] os: [linux] - '@next/swc-linux-x64-gnu@15.3.4': - resolution: {integrity: sha512-gEbH9rv9o7I12qPyvZNVTyP/PWKqOp8clvnoYZQiX800KkqsaJZuOXkWgMa7ANCCh/oEN2ZQheh3yH8/kWPSEg==} - engines: {node: '>= 10'} + "@next/swc-linux-x64-gnu@15.3.4": + resolution: + { + integrity: sha512-gEbH9rv9o7I12qPyvZNVTyP/PWKqOp8clvnoYZQiX800KkqsaJZuOXkWgMa7ANCCh/oEN2ZQheh3yH8/kWPSEg==, + } + engines: { node: ">= 10" } cpu: [x64] os: [linux] - '@next/swc-linux-x64-musl@15.3.4': - resolution: {integrity: sha512-Cf8sr0ufuC/nu/yQ76AnarbSAXcwG/wj+1xFPNbyNo8ltA6kw5d5YqO8kQuwVIxk13SBdtgXrNyom3ZosHAy4A==} - engines: {node: '>= 10'} + "@next/swc-linux-x64-musl@15.3.4": + resolution: + { + integrity: sha512-Cf8sr0ufuC/nu/yQ76AnarbSAXcwG/wj+1xFPNbyNo8ltA6kw5d5YqO8kQuwVIxk13SBdtgXrNyom3ZosHAy4A==, + } + engines: { node: ">= 10" } cpu: [x64] os: [linux] - '@next/swc-win32-arm64-msvc@15.3.4': - resolution: {integrity: sha512-ay5+qADDN3rwRbRpEhTOreOn1OyJIXS60tg9WMYTWCy3fB6rGoyjLVxc4dR9PYjEdR2iDYsaF5h03NA+XuYPQQ==} - engines: {node: '>= 10'} + "@next/swc-win32-arm64-msvc@15.3.4": + resolution: + { + integrity: sha512-ay5+qADDN3rwRbRpEhTOreOn1OyJIXS60tg9WMYTWCy3fB6rGoyjLVxc4dR9PYjEdR2iDYsaF5h03NA+XuYPQQ==, + } + engines: { node: ">= 10" } cpu: [arm64] os: [win32] - '@next/swc-win32-x64-msvc@15.3.4': - resolution: {integrity: sha512-4kDt31Bc9DGyYs41FTL1/kNpDeHyha2TC0j5sRRoKCyrhNcfZ/nRQkAUlF27mETwm8QyHqIjHJitfcza2Iykfg==} - engines: {node: '>= 10'} + "@next/swc-win32-x64-msvc@15.3.4": + resolution: + { + integrity: sha512-4kDt31Bc9DGyYs41FTL1/kNpDeHyha2TC0j5sRRoKCyrhNcfZ/nRQkAUlF27mETwm8QyHqIjHJitfcza2Iykfg==, + } + engines: { node: ">= 10" } cpu: [x64] os: [win32] - '@nodelib/fs.scandir@2.1.5': - resolution: {integrity: sha512-vq24Bq3ym5HEQm2NKCr3yXDwjc7vTsEThRDnkp2DK9p1uqLR+DHurm/NOTo0KG7HYHU7eppKZj3MyqYuMBf62g==} - engines: {node: '>= 8'} + "@nodelib/fs.scandir@2.1.5": + resolution: + { + integrity: sha512-vq24Bq3ym5HEQm2NKCr3yXDwjc7vTsEThRDnkp2DK9p1uqLR+DHurm/NOTo0KG7HYHU7eppKZj3MyqYuMBf62g==, + } + engines: { node: ">= 8" } - '@nodelib/fs.stat@2.0.5': - resolution: {integrity: sha512-RkhPPp2zrqDAQA/2jNhnztcPAlv64XdhIp7a7454A5ovI7Bukxgt7MX7udwAu3zg1DcpPU0rz3VV1SeaqvY4+A==} - engines: {node: '>= 8'} + "@nodelib/fs.stat@2.0.5": + resolution: + { + integrity: sha512-RkhPPp2zrqDAQA/2jNhnztcPAlv64XdhIp7a7454A5ovI7Bukxgt7MX7udwAu3zg1DcpPU0rz3VV1SeaqvY4+A==, + } + engines: { node: ">= 8" } - '@nodelib/fs.walk@1.2.8': - resolution: {integrity: sha512-oGB+UxlgWcgQkgwo8GcEGwemoTFt3FIO9ababBmaGwXIoBKZ+GTy0pP185beGg7Llih/NSHSV2XAs1lnznocSg==} - engines: {node: '>= 8'} + "@nodelib/fs.walk@1.2.8": + resolution: + { + integrity: sha512-oGB+UxlgWcgQkgwo8GcEGwemoTFt3FIO9ababBmaGwXIoBKZ+GTy0pP185beGg7Llih/NSHSV2XAs1lnznocSg==, + } + engines: { node: ">= 8" } - '@nolyfill/is-core-module@1.0.39': - resolution: {integrity: sha512-nn5ozdjYQpUCZlWGuxcJY/KpxkWQs4DcbMCmKojjyrYDEAGy4Ce19NN4v5MduafTwJlbKc99UA8YhSVqq9yPZA==} - engines: {node: '>=12.4.0'} + "@nolyfill/is-core-module@1.0.39": + resolution: + { + integrity: sha512-nn5ozdjYQpUCZlWGuxcJY/KpxkWQs4DcbMCmKojjyrYDEAGy4Ce19NN4v5MduafTwJlbKc99UA8YhSVqq9yPZA==, + } + engines: { node: ">=12.4.0" } - '@panva/hkdf@1.2.1': - resolution: {integrity: sha512-6oclG6Y3PiDFcoyk8srjLfVKyMfVCKJ27JwNPViuXziFpmdz+MZnZN/aKY0JGXgYuO/VghU0jcOAZgWXZ1Dmrw==} + "@panva/hkdf@1.2.1": + resolution: + { + integrity: sha512-6oclG6Y3PiDFcoyk8srjLfVKyMfVCKJ27JwNPViuXziFpmdz+MZnZN/aKY0JGXgYuO/VghU0jcOAZgWXZ1Dmrw==, + } - '@pkgjs/parseargs@0.11.0': - resolution: {integrity: sha512-+1VkjdD0QBLPodGrJUeqarH8VAIvQODIbwh9XpP5Syisf7YoQgsJKPNFoqqLQlu+VQ/tVSshMR6loPMn8U+dPg==} - engines: {node: '>=14'} + "@pkgjs/parseargs@0.11.0": + resolution: + { + integrity: sha512-+1VkjdD0QBLPodGrJUeqarH8VAIvQODIbwh9XpP5Syisf7YoQgsJKPNFoqqLQlu+VQ/tVSshMR6loPMn8U+dPg==, + } + engines: { node: ">=14" } - '@pkgr/core@0.2.7': - resolution: {integrity: sha512-YLT9Zo3oNPJoBjBc4q8G2mjU4tqIbf5CEOORbUUr48dCD9q3umJ3IPlVqOqDakPfd2HuwccBaqlGhN4Gmr5OWg==} - engines: {node: ^12.20.0 || ^14.18.0 || >=16.0.0} + "@pkgr/core@0.2.7": + resolution: + { + integrity: sha512-YLT9Zo3oNPJoBjBc4q8G2mjU4tqIbf5CEOORbUUr48dCD9q3umJ3IPlVqOqDakPfd2HuwccBaqlGhN4Gmr5OWg==, + } + engines: { node: ^12.20.0 || ^14.18.0 || >=16.0.0 } - '@playwright/test@1.53.1': - resolution: {integrity: sha512-Z4c23LHV0muZ8hfv4jw6HngPJkbbtZxTkxPNIg7cJcTc9C28N/p2q7g3JZS2SiKBBHJ3uM1dgDye66bB7LEk5w==} - engines: {node: '>=18'} + "@playwright/test@1.53.1": + resolution: + { + integrity: sha512-Z4c23LHV0muZ8hfv4jw6HngPJkbbtZxTkxPNIg7cJcTc9C28N/p2q7g3JZS2SiKBBHJ3uM1dgDye66bB7LEk5w==, + } + engines: { node: ">=18" } hasBin: true - '@prisma/adapter-pg@6.10.1': - resolution: {integrity: sha512-4Kpz5EV1jEOsKDuKYMjfJKMiIIcsuR9Ou1B8zLzehYtB7/oi+1ooDoK1K+T7sMisHkP69aYat5j0dskxvJTgdQ==} + "@prisma/adapter-pg@6.10.1": + resolution: + { + integrity: sha512-4Kpz5EV1jEOsKDuKYMjfJKMiIIcsuR9Ou1B8zLzehYtB7/oi+1ooDoK1K+T7sMisHkP69aYat5j0dskxvJTgdQ==, + } peerDependencies: pg: ^8.11.3 - '@prisma/client@6.10.1': - resolution: {integrity: sha512-Re4pMlcUsQsUTAYMK7EJ4Bw2kg3WfZAAlr8GjORJaK4VOP6LxRQUQ1TuLnxcF42XqGkWQ36q5CQF1yVadANQ6w==} - engines: {node: '>=18.18'} + "@prisma/client@6.10.1": + resolution: + { + integrity: sha512-Re4pMlcUsQsUTAYMK7EJ4Bw2kg3WfZAAlr8GjORJaK4VOP6LxRQUQ1TuLnxcF42XqGkWQ36q5CQF1yVadANQ6w==, + } + engines: { node: ">=18.18" } peerDependencies: - prisma: '*' - typescript: '>=5.1.0' + prisma: "*" + typescript: ">=5.1.0" peerDependenciesMeta: prisma: optional: true typescript: optional: true - '@prisma/config@6.10.1': - resolution: {integrity: sha512-kz4/bnqrOrzWo8KzYguN0cden4CzLJJ+2VSpKtF8utHS3l1JS0Lhv6BLwpOX6X9yNreTbZQZwewb+/BMPDCIYQ==} + "@prisma/config@6.10.1": + resolution: + { + integrity: sha512-kz4/bnqrOrzWo8KzYguN0cden4CzLJJ+2VSpKtF8utHS3l1JS0Lhv6BLwpOX6X9yNreTbZQZwewb+/BMPDCIYQ==, + } - '@prisma/debug@6.10.1': - resolution: {integrity: sha512-k2YT53cWxv9OLjW4zSYTZ6Z7j0gPfCzcr2Mj99qsuvlxr8WAKSZ2NcSR0zLf/mP4oxnYG842IMj3utTgcd7CaA==} + "@prisma/debug@6.10.1": + resolution: + { + integrity: sha512-k2YT53cWxv9OLjW4zSYTZ6Z7j0gPfCzcr2Mj99qsuvlxr8WAKSZ2NcSR0zLf/mP4oxnYG842IMj3utTgcd7CaA==, + } - '@prisma/driver-adapter-utils@6.10.1': - resolution: {integrity: sha512-MJ7NiiMA5YQUD1aMHiOcLmRpW0U0NTpygyeuLMxHXnKbcq+HX/cy10qilFMLVzpveuIEHuwxziR67z6i0K1MKA==} + "@prisma/driver-adapter-utils@6.10.1": + resolution: + { + integrity: sha512-MJ7NiiMA5YQUD1aMHiOcLmRpW0U0NTpygyeuLMxHXnKbcq+HX/cy10qilFMLVzpveuIEHuwxziR67z6i0K1MKA==, + } - '@prisma/engines-version@6.10.1-1.9b628578b3b7cae625e8c927178f15a170e74a9c': - resolution: {integrity: sha512-ZJFTsEqapiTYVzXya6TUKYDFnSWCNegfUiG5ik9fleQva5Sk3DNyyUi7X1+0ZxWFHwHDr6BZV5Vm+iwP+LlciA==} + "@prisma/engines-version@6.10.1-1.9b628578b3b7cae625e8c927178f15a170e74a9c": + resolution: + { + integrity: sha512-ZJFTsEqapiTYVzXya6TUKYDFnSWCNegfUiG5ik9fleQva5Sk3DNyyUi7X1+0ZxWFHwHDr6BZV5Vm+iwP+LlciA==, + } - '@prisma/engines@6.10.1': - resolution: {integrity: sha512-Q07P5rS2iPwk2IQr/rUQJ42tHjpPyFcbiH7PXZlV81Ryr9NYIgdxcUrwgVOWVm5T7ap02C0dNd1dpnNcSWig8A==} + "@prisma/engines@6.10.1": + resolution: + { + integrity: sha512-Q07P5rS2iPwk2IQr/rUQJ42tHjpPyFcbiH7PXZlV81Ryr9NYIgdxcUrwgVOWVm5T7ap02C0dNd1dpnNcSWig8A==, + } - '@prisma/fetch-engine@6.10.1': - resolution: {integrity: sha512-clmbG/Jgmrc/n6Y77QcBmAUlq9LrwI9Dbgy4pq5jeEARBpRCWJDJ7PWW1P8p0LfFU0i5fsyO7FqRzRB8mkdS4g==} + "@prisma/fetch-engine@6.10.1": + resolution: + { + integrity: sha512-clmbG/Jgmrc/n6Y77QcBmAUlq9LrwI9Dbgy4pq5jeEARBpRCWJDJ7PWW1P8p0LfFU0i5fsyO7FqRzRB8mkdS4g==, + } - '@prisma/get-platform@6.10.1': - resolution: {integrity: sha512-4CY5ndKylcsce9Mv+VWp5obbR2/86SHOLVV053pwIkhVtT9C9A83yqiqI/5kJM9T1v1u1qco/bYjDKycmei9HA==} + "@prisma/get-platform@6.10.1": + resolution: + { + integrity: sha512-4CY5ndKylcsce9Mv+VWp5obbR2/86SHOLVV053pwIkhVtT9C9A83yqiqI/5kJM9T1v1u1qco/bYjDKycmei9HA==, + } - '@radix-ui/primitive@1.1.2': - resolution: {integrity: sha512-XnbHrrprsNqZKQhStrSwgRUQzoCI1glLzdw79xiZPoofhGICeZRSQ3dIxAKH1gb3OHfNf4d6f+vAv3kil2eggA==} + "@radix-ui/primitive@1.1.2": + resolution: + { + integrity: sha512-XnbHrrprsNqZKQhStrSwgRUQzoCI1glLzdw79xiZPoofhGICeZRSQ3dIxAKH1gb3OHfNf4d6f+vAv3kil2eggA==, + } - '@radix-ui/react-arrow@1.1.7': - resolution: {integrity: sha512-F+M1tLhO+mlQaOWspE8Wstg+z6PwxwRd8oQ8IXceWz92kfAmalTRf0EjrouQeo7QssEPfCn05B4Ihs1K9WQ/7w==} + "@radix-ui/react-arrow@1.1.7": + resolution: + { + integrity: sha512-F+M1tLhO+mlQaOWspE8Wstg+z6PwxwRd8oQ8IXceWz92kfAmalTRf0EjrouQeo7QssEPfCn05B4Ihs1K9WQ/7w==, + } peerDependencies: - '@types/react': '*' - '@types/react-dom': '*' + "@types/react": "*" + "@types/react-dom": "*" react: ^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc react-dom: ^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc peerDependenciesMeta: - '@types/react': + "@types/react": optional: true - '@types/react-dom': + "@types/react-dom": optional: true - '@radix-ui/react-collection@1.1.7': - resolution: {integrity: sha512-Fh9rGN0MoI4ZFUNyfFVNU4y9LUz93u9/0K+yLgA2bwRojxM8JU1DyvvMBabnZPBgMWREAJvU2jjVzq+LrFUglw==} + "@radix-ui/react-collection@1.1.7": + resolution: + { + integrity: sha512-Fh9rGN0MoI4ZFUNyfFVNU4y9LUz93u9/0K+yLgA2bwRojxM8JU1DyvvMBabnZPBgMWREAJvU2jjVzq+LrFUglw==, + } peerDependencies: - '@types/react': '*' - '@types/react-dom': '*' + "@types/react": "*" + "@types/react-dom": "*" react: ^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc react-dom: ^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc peerDependenciesMeta: - '@types/react': + "@types/react": optional: true - '@types/react-dom': + "@types/react-dom": optional: true - '@radix-ui/react-compose-refs@1.1.2': - resolution: {integrity: sha512-z4eqJvfiNnFMHIIvXP3CY57y2WJs5g2v3X0zm9mEJkrkNv4rDxu+sg9Jh8EkXyeqBkB7SOcboo9dMVqhyrACIg==} + "@radix-ui/react-compose-refs@1.1.2": + resolution: + { + integrity: sha512-z4eqJvfiNnFMHIIvXP3CY57y2WJs5g2v3X0zm9mEJkrkNv4rDxu+sg9Jh8EkXyeqBkB7SOcboo9dMVqhyrACIg==, + } peerDependencies: - '@types/react': '*' + "@types/react": "*" react: ^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc peerDependenciesMeta: - '@types/react': + "@types/react": optional: true - '@radix-ui/react-context@1.1.2': - resolution: {integrity: sha512-jCi/QKUM2r1Ju5a3J64TH2A5SpKAgh0LpknyqdQ4m6DCV0xJ2HG1xARRwNGPQfi1SLdLWZ1OJz6F4OMBBNiGJA==} + "@radix-ui/react-context@1.1.2": + resolution: + { + integrity: sha512-jCi/QKUM2r1Ju5a3J64TH2A5SpKAgh0LpknyqdQ4m6DCV0xJ2HG1xARRwNGPQfi1SLdLWZ1OJz6F4OMBBNiGJA==, + } peerDependencies: - '@types/react': '*' + "@types/react": "*" react: ^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc peerDependenciesMeta: - '@types/react': + "@types/react": optional: true - '@radix-ui/react-direction@1.1.1': - resolution: {integrity: sha512-1UEWRX6jnOA2y4H5WczZ44gOOjTEmlqv1uNW4GAJEO5+bauCBhv8snY65Iw5/VOS/ghKN9gr2KjnLKxrsvoMVw==} + "@radix-ui/react-direction@1.1.1": + resolution: + { + integrity: sha512-1UEWRX6jnOA2y4H5WczZ44gOOjTEmlqv1uNW4GAJEO5+bauCBhv8snY65Iw5/VOS/ghKN9gr2KjnLKxrsvoMVw==, + } peerDependencies: - '@types/react': '*' + "@types/react": "*" react: ^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc peerDependenciesMeta: - '@types/react': + "@types/react": optional: true - '@radix-ui/react-dismissable-layer@1.1.10': - resolution: {integrity: sha512-IM1zzRV4W3HtVgftdQiiOmA0AdJlCtMLe00FXaHwgt3rAnNsIyDqshvkIW3hj/iu5hu8ERP7KIYki6NkqDxAwQ==} + "@radix-ui/react-dismissable-layer@1.1.10": + resolution: + { + integrity: sha512-IM1zzRV4W3HtVgftdQiiOmA0AdJlCtMLe00FXaHwgt3rAnNsIyDqshvkIW3hj/iu5hu8ERP7KIYki6NkqDxAwQ==, + } peerDependencies: - '@types/react': '*' - '@types/react-dom': '*' + "@types/react": "*" + "@types/react-dom": "*" react: ^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc react-dom: ^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc peerDependenciesMeta: - '@types/react': + "@types/react": optional: true - '@types/react-dom': + "@types/react-dom": optional: true - '@radix-ui/react-dropdown-menu@2.1.15': - resolution: {integrity: sha512-mIBnOjgwo9AH3FyKaSWoSu/dYj6VdhJ7frEPiGTeXCdUFHjl9h3mFh2wwhEtINOmYXWhdpf1rY2minFsmaNgVQ==} + "@radix-ui/react-dropdown-menu@2.1.15": + resolution: + { + integrity: sha512-mIBnOjgwo9AH3FyKaSWoSu/dYj6VdhJ7frEPiGTeXCdUFHjl9h3mFh2wwhEtINOmYXWhdpf1rY2minFsmaNgVQ==, + } peerDependencies: - '@types/react': '*' - '@types/react-dom': '*' + "@types/react": "*" + "@types/react-dom": "*" react: ^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc react-dom: ^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc peerDependenciesMeta: - '@types/react': + "@types/react": optional: true - '@types/react-dom': + "@types/react-dom": optional: true - '@radix-ui/react-focus-guards@1.1.2': - resolution: {integrity: sha512-fyjAACV62oPV925xFCrH8DR5xWhg9KYtJT4s3u54jxp+L/hbpTY2kIeEFFbFe+a/HCE94zGQMZLIpVTPVZDhaA==} + "@radix-ui/react-focus-guards@1.1.2": + resolution: + { + integrity: sha512-fyjAACV62oPV925xFCrH8DR5xWhg9KYtJT4s3u54jxp+L/hbpTY2kIeEFFbFe+a/HCE94zGQMZLIpVTPVZDhaA==, + } peerDependencies: - '@types/react': '*' + "@types/react": "*" react: ^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc peerDependenciesMeta: - '@types/react': + "@types/react": optional: true - '@radix-ui/react-focus-scope@1.1.7': - resolution: {integrity: sha512-t2ODlkXBQyn7jkl6TNaw/MtVEVvIGelJDCG41Okq/KwUsJBwQ4XVZsHAVUkK4mBv3ewiAS3PGuUWuY2BoK4ZUw==} + "@radix-ui/react-focus-scope@1.1.7": + resolution: + { + integrity: sha512-t2ODlkXBQyn7jkl6TNaw/MtVEVvIGelJDCG41Okq/KwUsJBwQ4XVZsHAVUkK4mBv3ewiAS3PGuUWuY2BoK4ZUw==, + } peerDependencies: - '@types/react': '*' - '@types/react-dom': '*' + "@types/react": "*" + "@types/react-dom": "*" react: ^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc react-dom: ^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc peerDependenciesMeta: - '@types/react': + "@types/react": optional: true - '@types/react-dom': + "@types/react-dom": optional: true - '@radix-ui/react-id@1.1.1': - resolution: {integrity: sha512-kGkGegYIdQsOb4XjsfM97rXsiHaBwco+hFI66oO4s9LU+PLAC5oJ7khdOVFxkhsmlbpUqDAvXw11CluXP+jkHg==} + "@radix-ui/react-id@1.1.1": + resolution: + { + integrity: sha512-kGkGegYIdQsOb4XjsfM97rXsiHaBwco+hFI66oO4s9LU+PLAC5oJ7khdOVFxkhsmlbpUqDAvXw11CluXP+jkHg==, + } peerDependencies: - '@types/react': '*' + "@types/react": "*" react: ^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc peerDependenciesMeta: - '@types/react': + "@types/react": optional: true - '@radix-ui/react-menu@2.1.15': - resolution: {integrity: sha512-tVlmA3Vb9n8SZSd+YSbuFR66l87Wiy4du+YE+0hzKQEANA+7cWKH1WgqcEX4pXqxUFQKrWQGHdvEfw00TjFiew==} + "@radix-ui/react-menu@2.1.15": + resolution: + { + integrity: sha512-tVlmA3Vb9n8SZSd+YSbuFR66l87Wiy4du+YE+0hzKQEANA+7cWKH1WgqcEX4pXqxUFQKrWQGHdvEfw00TjFiew==, + } peerDependencies: - '@types/react': '*' - '@types/react-dom': '*' + "@types/react": "*" + "@types/react-dom": "*" react: ^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc react-dom: ^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc peerDependenciesMeta: - '@types/react': + "@types/react": optional: true - '@types/react-dom': + "@types/react-dom": optional: true - '@radix-ui/react-popper@1.2.7': - resolution: {integrity: sha512-IUFAccz1JyKcf/RjB552PlWwxjeCJB8/4KxT7EhBHOJM+mN7LdW+B3kacJXILm32xawcMMjb2i0cIZpo+f9kiQ==} + "@radix-ui/react-popper@1.2.7": + resolution: + { + integrity: sha512-IUFAccz1JyKcf/RjB552PlWwxjeCJB8/4KxT7EhBHOJM+mN7LdW+B3kacJXILm32xawcMMjb2i0cIZpo+f9kiQ==, + } peerDependencies: - '@types/react': '*' - '@types/react-dom': '*' + "@types/react": "*" + "@types/react-dom": "*" react: ^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc react-dom: ^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc peerDependenciesMeta: - '@types/react': + "@types/react": optional: true - '@types/react-dom': + "@types/react-dom": optional: true - '@radix-ui/react-portal@1.1.9': - resolution: {integrity: sha512-bpIxvq03if6UNwXZ+HTK71JLh4APvnXntDc6XOX8UVq4XQOVl7lwok0AvIl+b8zgCw3fSaVTZMpAPPagXbKmHQ==} + "@radix-ui/react-portal@1.1.9": + resolution: + { + integrity: sha512-bpIxvq03if6UNwXZ+HTK71JLh4APvnXntDc6XOX8UVq4XQOVl7lwok0AvIl+b8zgCw3fSaVTZMpAPPagXbKmHQ==, + } peerDependencies: - '@types/react': '*' - '@types/react-dom': '*' + "@types/react": "*" + "@types/react-dom": "*" react: ^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc react-dom: ^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc peerDependenciesMeta: - '@types/react': + "@types/react": optional: true - '@types/react-dom': + "@types/react-dom": optional: true - '@radix-ui/react-presence@1.1.4': - resolution: {integrity: sha512-ueDqRbdc4/bkaQT3GIpLQssRlFgWaL/U2z/S31qRwwLWoxHLgry3SIfCwhxeQNbirEUXFa+lq3RL3oBYXtcmIA==} + "@radix-ui/react-presence@1.1.4": + resolution: + { + integrity: sha512-ueDqRbdc4/bkaQT3GIpLQssRlFgWaL/U2z/S31qRwwLWoxHLgry3SIfCwhxeQNbirEUXFa+lq3RL3oBYXtcmIA==, + } peerDependencies: - '@types/react': '*' - '@types/react-dom': '*' + "@types/react": "*" + "@types/react-dom": "*" react: ^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc react-dom: ^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc peerDependenciesMeta: - '@types/react': + "@types/react": optional: true - '@types/react-dom': + "@types/react-dom": optional: true - '@radix-ui/react-primitive@2.1.3': - resolution: {integrity: sha512-m9gTwRkhy2lvCPe6QJp4d3G1TYEUHn/FzJUtq9MjH46an1wJU+GdoGC5VLof8RX8Ft/DlpshApkhswDLZzHIcQ==} + "@radix-ui/react-primitive@2.1.3": + resolution: + { + integrity: sha512-m9gTwRkhy2lvCPe6QJp4d3G1TYEUHn/FzJUtq9MjH46an1wJU+GdoGC5VLof8RX8Ft/DlpshApkhswDLZzHIcQ==, + } peerDependencies: - '@types/react': '*' - '@types/react-dom': '*' + "@types/react": "*" + "@types/react-dom": "*" react: ^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc react-dom: ^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc peerDependenciesMeta: - '@types/react': + "@types/react": optional: true - '@types/react-dom': + "@types/react-dom": optional: true - '@radix-ui/react-roving-focus@1.1.10': - resolution: {integrity: sha512-dT9aOXUen9JSsxnMPv/0VqySQf5eDQ6LCk5Sw28kamz8wSOW2bJdlX2Bg5VUIIcV+6XlHpWTIuTPCf/UNIyq8Q==} + "@radix-ui/react-roving-focus@1.1.10": + resolution: + { + integrity: sha512-dT9aOXUen9JSsxnMPv/0VqySQf5eDQ6LCk5Sw28kamz8wSOW2bJdlX2Bg5VUIIcV+6XlHpWTIuTPCf/UNIyq8Q==, + } peerDependencies: - '@types/react': '*' - '@types/react-dom': '*' + "@types/react": "*" + "@types/react-dom": "*" react: ^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc react-dom: ^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc peerDependenciesMeta: - '@types/react': + "@types/react": optional: true - '@types/react-dom': + "@types/react-dom": optional: true - '@radix-ui/react-separator@1.1.7': - resolution: {integrity: sha512-0HEb8R9E8A+jZjvmFCy/J4xhbXy3TV+9XSnGJ3KvTtjlIUy/YQ/p6UYZvi7YbeoeXdyU9+Y3scizK6hkY37baA==} + "@radix-ui/react-separator@1.1.7": + resolution: + { + integrity: sha512-0HEb8R9E8A+jZjvmFCy/J4xhbXy3TV+9XSnGJ3KvTtjlIUy/YQ/p6UYZvi7YbeoeXdyU9+Y3scizK6hkY37baA==, + } peerDependencies: - '@types/react': '*' - '@types/react-dom': '*' + "@types/react": "*" + "@types/react-dom": "*" react: ^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc react-dom: ^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc peerDependenciesMeta: - '@types/react': + "@types/react": optional: true - '@types/react-dom': + "@types/react-dom": optional: true - '@radix-ui/react-slot@1.2.3': - resolution: {integrity: sha512-aeNmHnBxbi2St0au6VBVC7JXFlhLlOnvIIlePNniyUNAClzmtAUEY8/pBiK3iHjufOlwA+c20/8jngo7xcrg8A==} + "@radix-ui/react-slot@1.2.3": + resolution: + { + integrity: sha512-aeNmHnBxbi2St0au6VBVC7JXFlhLlOnvIIlePNniyUNAClzmtAUEY8/pBiK3iHjufOlwA+c20/8jngo7xcrg8A==, + } peerDependencies: - '@types/react': '*' + "@types/react": "*" react: ^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc peerDependenciesMeta: - '@types/react': + "@types/react": optional: true - '@radix-ui/react-tooltip@1.2.7': - resolution: {integrity: sha512-Ap+fNYwKTYJ9pzqW+Xe2HtMRbQ/EeWkj2qykZ6SuEV4iS/o1bZI5ssJbk4D2r8XuDuOBVz/tIx2JObtuqU+5Zw==} + "@radix-ui/react-tooltip@1.2.7": + resolution: + { + integrity: sha512-Ap+fNYwKTYJ9pzqW+Xe2HtMRbQ/EeWkj2qykZ6SuEV4iS/o1bZI5ssJbk4D2r8XuDuOBVz/tIx2JObtuqU+5Zw==, + } peerDependencies: - '@types/react': '*' - '@types/react-dom': '*' + "@types/react": "*" + "@types/react-dom": "*" react: ^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc react-dom: ^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc peerDependenciesMeta: - '@types/react': + "@types/react": optional: true - '@types/react-dom': + "@types/react-dom": optional: true - '@radix-ui/react-use-callback-ref@1.1.1': - resolution: {integrity: sha512-FkBMwD+qbGQeMu1cOHnuGB6x4yzPjho8ap5WtbEJ26umhgqVXbhekKUQO+hZEL1vU92a3wHwdp0HAcqAUF5iDg==} + "@radix-ui/react-use-callback-ref@1.1.1": + resolution: + { + integrity: sha512-FkBMwD+qbGQeMu1cOHnuGB6x4yzPjho8ap5WtbEJ26umhgqVXbhekKUQO+hZEL1vU92a3wHwdp0HAcqAUF5iDg==, + } peerDependencies: - '@types/react': '*' + "@types/react": "*" react: ^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc peerDependenciesMeta: - '@types/react': + "@types/react": optional: true - '@radix-ui/react-use-controllable-state@1.2.2': - resolution: {integrity: sha512-BjasUjixPFdS+NKkypcyyN5Pmg83Olst0+c6vGov0diwTEo6mgdqVR6hxcEgFuh4QrAs7Rc+9KuGJ9TVCj0Zzg==} + "@radix-ui/react-use-controllable-state@1.2.2": + resolution: + { + integrity: sha512-BjasUjixPFdS+NKkypcyyN5Pmg83Olst0+c6vGov0diwTEo6mgdqVR6hxcEgFuh4QrAs7Rc+9KuGJ9TVCj0Zzg==, + } peerDependencies: - '@types/react': '*' + "@types/react": "*" react: ^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc peerDependenciesMeta: - '@types/react': + "@types/react": optional: true - '@radix-ui/react-use-effect-event@0.0.2': - resolution: {integrity: sha512-Qp8WbZOBe+blgpuUT+lw2xheLP8q0oatc9UpmiemEICxGvFLYmHm9QowVZGHtJlGbS6A6yJ3iViad/2cVjnOiA==} + "@radix-ui/react-use-effect-event@0.0.2": + resolution: + { + integrity: sha512-Qp8WbZOBe+blgpuUT+lw2xheLP8q0oatc9UpmiemEICxGvFLYmHm9QowVZGHtJlGbS6A6yJ3iViad/2cVjnOiA==, + } peerDependencies: - '@types/react': '*' + "@types/react": "*" react: ^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc peerDependenciesMeta: - '@types/react': + "@types/react": optional: true - '@radix-ui/react-use-escape-keydown@1.1.1': - resolution: {integrity: sha512-Il0+boE7w/XebUHyBjroE+DbByORGR9KKmITzbR7MyQ4akpORYP/ZmbhAr0DG7RmmBqoOnZdy2QlvajJ2QA59g==} + "@radix-ui/react-use-escape-keydown@1.1.1": + resolution: + { + integrity: sha512-Il0+boE7w/XebUHyBjroE+DbByORGR9KKmITzbR7MyQ4akpORYP/ZmbhAr0DG7RmmBqoOnZdy2QlvajJ2QA59g==, + } peerDependencies: - '@types/react': '*' + "@types/react": "*" react: ^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc peerDependenciesMeta: - '@types/react': + "@types/react": optional: true - '@radix-ui/react-use-layout-effect@1.1.1': - resolution: {integrity: sha512-RbJRS4UWQFkzHTTwVymMTUv8EqYhOp8dOOviLj2ugtTiXRaRQS7GLGxZTLL1jWhMeoSCf5zmcZkqTl9IiYfXcQ==} + "@radix-ui/react-use-layout-effect@1.1.1": + resolution: + { + integrity: sha512-RbJRS4UWQFkzHTTwVymMTUv8EqYhOp8dOOviLj2ugtTiXRaRQS7GLGxZTLL1jWhMeoSCf5zmcZkqTl9IiYfXcQ==, + } peerDependencies: - '@types/react': '*' + "@types/react": "*" react: ^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc peerDependenciesMeta: - '@types/react': + "@types/react": optional: true - '@radix-ui/react-use-rect@1.1.1': - resolution: {integrity: sha512-QTYuDesS0VtuHNNvMh+CjlKJ4LJickCMUAqjlE3+j8w+RlRpwyX3apEQKGFzbZGdo7XNG1tXa+bQqIE7HIXT2w==} + "@radix-ui/react-use-rect@1.1.1": + resolution: + { + integrity: sha512-QTYuDesS0VtuHNNvMh+CjlKJ4LJickCMUAqjlE3+j8w+RlRpwyX3apEQKGFzbZGdo7XNG1tXa+bQqIE7HIXT2w==, + } peerDependencies: - '@types/react': '*' + "@types/react": "*" react: ^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc peerDependenciesMeta: - '@types/react': + "@types/react": optional: true - '@radix-ui/react-use-size@1.1.1': - resolution: {integrity: sha512-ewrXRDTAqAXlkl6t/fkXWNAhFX9I+CkKlw6zjEwk86RSPKwZr3xpBRso655aqYafwtnbpHLj6toFzmd6xdVptQ==} + "@radix-ui/react-use-size@1.1.1": + resolution: + { + integrity: sha512-ewrXRDTAqAXlkl6t/fkXWNAhFX9I+CkKlw6zjEwk86RSPKwZr3xpBRso655aqYafwtnbpHLj6toFzmd6xdVptQ==, + } peerDependencies: - '@types/react': '*' + "@types/react": "*" react: ^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc peerDependenciesMeta: - '@types/react': + "@types/react": optional: true - '@radix-ui/react-visually-hidden@1.2.3': - resolution: {integrity: sha512-pzJq12tEaaIhqjbzpCuv/OypJY/BPavOofm+dbab+MHLajy277+1lLm6JFcGgF5eskJ6mquGirhXY2GD/8u8Ug==} + "@radix-ui/react-visually-hidden@1.2.3": + resolution: + { + integrity: sha512-pzJq12tEaaIhqjbzpCuv/OypJY/BPavOofm+dbab+MHLajy277+1lLm6JFcGgF5eskJ6mquGirhXY2GD/8u8Ug==, + } peerDependencies: - '@types/react': '*' - '@types/react-dom': '*' + "@types/react": "*" + "@types/react-dom": "*" react: ^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc react-dom: ^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc peerDependenciesMeta: - '@types/react': + "@types/react": optional: true - '@types/react-dom': + "@types/react-dom": optional: true - '@radix-ui/rect@1.1.1': - resolution: {integrity: sha512-HPwpGIzkl28mWyZqG52jiqDJ12waP11Pa1lGoiyUkIEuMLBP0oeK/C89esbXrxsky5we7dfd8U58nm0SgAWpVw==} + "@radix-ui/rect@1.1.1": + resolution: + { + integrity: sha512-HPwpGIzkl28mWyZqG52jiqDJ12waP11Pa1lGoiyUkIEuMLBP0oeK/C89esbXrxsky5we7dfd8U58nm0SgAWpVw==, + } - '@rapideditor/country-coder@5.4.0': - resolution: {integrity: sha512-5Kjy2hnDcJZnPpRXMrTNY+jTkwhenaniCD4K6oLdZHYnY0GSM8gIIkOmoB3UikVVcot5vhz6i0QVqbTSyxAvrQ==} - engines: {node: '>=20'} + "@rapideditor/country-coder@5.4.0": + resolution: + { + integrity: sha512-5Kjy2hnDcJZnPpRXMrTNY+jTkwhenaniCD4K6oLdZHYnY0GSM8gIIkOmoB3UikVVcot5vhz6i0QVqbTSyxAvrQ==, + } + engines: { node: ">=20" } - '@react-leaflet/core@3.0.0': - resolution: {integrity: sha512-3EWmekh4Nz+pGcr+xjf0KNyYfC3U2JjnkWsh0zcqaexYqmmB5ZhH37kz41JXGmKzpaMZCnPofBBm64i+YrEvGQ==} + "@react-leaflet/core@3.0.0": + resolution: + { + integrity: sha512-3EWmekh4Nz+pGcr+xjf0KNyYfC3U2JjnkWsh0zcqaexYqmmB5ZhH37kz41JXGmKzpaMZCnPofBBm64i+YrEvGQ==, + } peerDependencies: leaflet: ^1.9.0 react: ^19.0.0 react-dom: ^19.0.0 - '@reduxjs/toolkit@2.8.2': - resolution: {integrity: sha512-MYlOhQ0sLdw4ud48FoC5w0dH9VfWQjtCjreKwYTT3l+r427qYC5Y8PihNutepr8XrNaBUDQo9khWUwQxZaqt5A==} + "@reduxjs/toolkit@2.8.2": + resolution: + { + integrity: sha512-MYlOhQ0sLdw4ud48FoC5w0dH9VfWQjtCjreKwYTT3l+r427qYC5Y8PihNutepr8XrNaBUDQo9khWUwQxZaqt5A==, + } peerDependencies: react: ^16.9.0 || ^17.0.0 || ^18 || ^19 react-redux: ^7.2.1 || ^8.1.3 || ^9.0.0 @@ -1179,613 +1675,1038 @@ packages: react-redux: optional: true - '@rolldown/pluginutils@1.0.0-beta.19': - resolution: {integrity: sha512-3FL3mnMbPu0muGOCaKAhhFEYmqv9eTfPSJRJmANrCwtgK8VuxpsZDGK+m0LYAGoyO8+0j5uRe4PeyPDK1yA/hA==} + "@rolldown/pluginutils@1.0.0-beta.19": + resolution: + { + integrity: sha512-3FL3mnMbPu0muGOCaKAhhFEYmqv9eTfPSJRJmANrCwtgK8VuxpsZDGK+m0LYAGoyO8+0j5uRe4PeyPDK1yA/hA==, + } - '@rollup/rollup-android-arm-eabi@4.44.1': - resolution: {integrity: sha512-JAcBr1+fgqx20m7Fwe1DxPUl/hPkee6jA6Pl7n1v2EFiktAHenTaXl5aIFjUIEsfn9w3HE4gK1lEgNGMzBDs1w==} + "@rollup/rollup-android-arm-eabi@4.44.1": + resolution: + { + integrity: sha512-JAcBr1+fgqx20m7Fwe1DxPUl/hPkee6jA6Pl7n1v2EFiktAHenTaXl5aIFjUIEsfn9w3HE4gK1lEgNGMzBDs1w==, + } cpu: [arm] os: [android] - '@rollup/rollup-android-arm64@4.44.1': - resolution: {integrity: sha512-RurZetXqTu4p+G0ChbnkwBuAtwAbIwJkycw1n6GvlGlBuS4u5qlr5opix8cBAYFJgaY05TWtM+LaoFggUmbZEQ==} + "@rollup/rollup-android-arm64@4.44.1": + resolution: + { + integrity: sha512-RurZetXqTu4p+G0ChbnkwBuAtwAbIwJkycw1n6GvlGlBuS4u5qlr5opix8cBAYFJgaY05TWtM+LaoFggUmbZEQ==, + } cpu: [arm64] os: [android] - '@rollup/rollup-darwin-arm64@4.44.1': - resolution: {integrity: sha512-fM/xPesi7g2M7chk37LOnmnSTHLG/v2ggWqKj3CCA1rMA4mm5KVBT1fNoswbo1JhPuNNZrVwpTvlCVggv8A2zg==} + "@rollup/rollup-darwin-arm64@4.44.1": + resolution: + { + integrity: sha512-fM/xPesi7g2M7chk37LOnmnSTHLG/v2ggWqKj3CCA1rMA4mm5KVBT1fNoswbo1JhPuNNZrVwpTvlCVggv8A2zg==, + } cpu: [arm64] os: [darwin] - '@rollup/rollup-darwin-x64@4.44.1': - resolution: {integrity: sha512-gDnWk57urJrkrHQ2WVx9TSVTH7lSlU7E3AFqiko+bgjlh78aJ88/3nycMax52VIVjIm3ObXnDL2H00e/xzoipw==} + "@rollup/rollup-darwin-x64@4.44.1": + resolution: + { + integrity: sha512-gDnWk57urJrkrHQ2WVx9TSVTH7lSlU7E3AFqiko+bgjlh78aJ88/3nycMax52VIVjIm3ObXnDL2H00e/xzoipw==, + } cpu: [x64] os: [darwin] - '@rollup/rollup-freebsd-arm64@4.44.1': - resolution: {integrity: sha512-wnFQmJ/zPThM5zEGcnDcCJeYJgtSLjh1d//WuHzhf6zT3Md1BvvhJnWoy+HECKu2bMxaIcfWiu3bJgx6z4g2XA==} + "@rollup/rollup-freebsd-arm64@4.44.1": + resolution: + { + integrity: sha512-wnFQmJ/zPThM5zEGcnDcCJeYJgtSLjh1d//WuHzhf6zT3Md1BvvhJnWoy+HECKu2bMxaIcfWiu3bJgx6z4g2XA==, + } cpu: [arm64] os: [freebsd] - '@rollup/rollup-freebsd-x64@4.44.1': - resolution: {integrity: sha512-uBmIxoJ4493YATvU2c0upGz87f99e3wop7TJgOA/bXMFd2SvKCI7xkxY/5k50bv7J6dw1SXT4MQBQSLn8Bb/Uw==} + "@rollup/rollup-freebsd-x64@4.44.1": + resolution: + { + integrity: sha512-uBmIxoJ4493YATvU2c0upGz87f99e3wop7TJgOA/bXMFd2SvKCI7xkxY/5k50bv7J6dw1SXT4MQBQSLn8Bb/Uw==, + } cpu: [x64] os: [freebsd] - '@rollup/rollup-linux-arm-gnueabihf@4.44.1': - resolution: {integrity: sha512-n0edDmSHlXFhrlmTK7XBuwKlG5MbS7yleS1cQ9nn4kIeW+dJH+ExqNgQ0RrFRew8Y+0V/x6C5IjsHrJmiHtkxQ==} + "@rollup/rollup-linux-arm-gnueabihf@4.44.1": + resolution: + { + integrity: sha512-n0edDmSHlXFhrlmTK7XBuwKlG5MbS7yleS1cQ9nn4kIeW+dJH+ExqNgQ0RrFRew8Y+0V/x6C5IjsHrJmiHtkxQ==, + } cpu: [arm] os: [linux] - '@rollup/rollup-linux-arm-musleabihf@4.44.1': - resolution: {integrity: sha512-8WVUPy3FtAsKSpyk21kV52HCxB+me6YkbkFHATzC2Yd3yuqHwy2lbFL4alJOLXKljoRw08Zk8/xEj89cLQ/4Nw==} + "@rollup/rollup-linux-arm-musleabihf@4.44.1": + resolution: + { + integrity: sha512-8WVUPy3FtAsKSpyk21kV52HCxB+me6YkbkFHATzC2Yd3yuqHwy2lbFL4alJOLXKljoRw08Zk8/xEj89cLQ/4Nw==, + } cpu: [arm] os: [linux] - '@rollup/rollup-linux-arm64-gnu@4.44.1': - resolution: {integrity: sha512-yuktAOaeOgorWDeFJggjuCkMGeITfqvPgkIXhDqsfKX8J3jGyxdDZgBV/2kj/2DyPaLiX6bPdjJDTu9RB8lUPQ==} + "@rollup/rollup-linux-arm64-gnu@4.44.1": + resolution: + { + integrity: sha512-yuktAOaeOgorWDeFJggjuCkMGeITfqvPgkIXhDqsfKX8J3jGyxdDZgBV/2kj/2DyPaLiX6bPdjJDTu9RB8lUPQ==, + } cpu: [arm64] os: [linux] - '@rollup/rollup-linux-arm64-musl@4.44.1': - resolution: {integrity: sha512-W+GBM4ifET1Plw8pdVaecwUgxmiH23CfAUj32u8knq0JPFyK4weRy6H7ooxYFD19YxBulL0Ktsflg5XS7+7u9g==} + "@rollup/rollup-linux-arm64-musl@4.44.1": + resolution: + { + integrity: sha512-W+GBM4ifET1Plw8pdVaecwUgxmiH23CfAUj32u8knq0JPFyK4weRy6H7ooxYFD19YxBulL0Ktsflg5XS7+7u9g==, + } cpu: [arm64] os: [linux] - '@rollup/rollup-linux-loongarch64-gnu@4.44.1': - resolution: {integrity: sha512-1zqnUEMWp9WrGVuVak6jWTl4fEtrVKfZY7CvcBmUUpxAJ7WcSowPSAWIKa/0o5mBL/Ij50SIf9tuirGx63Ovew==} + "@rollup/rollup-linux-loongarch64-gnu@4.44.1": + resolution: + { + integrity: sha512-1zqnUEMWp9WrGVuVak6jWTl4fEtrVKfZY7CvcBmUUpxAJ7WcSowPSAWIKa/0o5mBL/Ij50SIf9tuirGx63Ovew==, + } cpu: [loong64] os: [linux] - '@rollup/rollup-linux-powerpc64le-gnu@4.44.1': - resolution: {integrity: sha512-Rl3JKaRu0LHIx7ExBAAnf0JcOQetQffaw34T8vLlg9b1IhzcBgaIdnvEbbsZq9uZp3uAH+JkHd20Nwn0h9zPjA==} + "@rollup/rollup-linux-powerpc64le-gnu@4.44.1": + resolution: + { + integrity: sha512-Rl3JKaRu0LHIx7ExBAAnf0JcOQetQffaw34T8vLlg9b1IhzcBgaIdnvEbbsZq9uZp3uAH+JkHd20Nwn0h9zPjA==, + } cpu: [ppc64] os: [linux] - '@rollup/rollup-linux-riscv64-gnu@4.44.1': - resolution: {integrity: sha512-j5akelU3snyL6K3N/iX7otLBIl347fGwmd95U5gS/7z6T4ftK288jKq3A5lcFKcx7wwzb5rgNvAg3ZbV4BqUSw==} + "@rollup/rollup-linux-riscv64-gnu@4.44.1": + resolution: + { + integrity: sha512-j5akelU3snyL6K3N/iX7otLBIl347fGwmd95U5gS/7z6T4ftK288jKq3A5lcFKcx7wwzb5rgNvAg3ZbV4BqUSw==, + } cpu: [riscv64] os: [linux] - '@rollup/rollup-linux-riscv64-musl@4.44.1': - resolution: {integrity: sha512-ppn5llVGgrZw7yxbIm8TTvtj1EoPgYUAbfw0uDjIOzzoqlZlZrLJ/KuiE7uf5EpTpCTrNt1EdtzF0naMm0wGYg==} + "@rollup/rollup-linux-riscv64-musl@4.44.1": + resolution: + { + integrity: sha512-ppn5llVGgrZw7yxbIm8TTvtj1EoPgYUAbfw0uDjIOzzoqlZlZrLJ/KuiE7uf5EpTpCTrNt1EdtzF0naMm0wGYg==, + } cpu: [riscv64] os: [linux] - '@rollup/rollup-linux-s390x-gnu@4.44.1': - resolution: {integrity: sha512-Hu6hEdix0oxtUma99jSP7xbvjkUM/ycke/AQQ4EC5g7jNRLLIwjcNwaUy95ZKBJJwg1ZowsclNnjYqzN4zwkAw==} + "@rollup/rollup-linux-s390x-gnu@4.44.1": + resolution: + { + integrity: sha512-Hu6hEdix0oxtUma99jSP7xbvjkUM/ycke/AQQ4EC5g7jNRLLIwjcNwaUy95ZKBJJwg1ZowsclNnjYqzN4zwkAw==, + } cpu: [s390x] os: [linux] - '@rollup/rollup-linux-x64-gnu@4.44.1': - resolution: {integrity: sha512-EtnsrmZGomz9WxK1bR5079zee3+7a+AdFlghyd6VbAjgRJDbTANJ9dcPIPAi76uG05micpEL+gPGmAKYTschQw==} + "@rollup/rollup-linux-x64-gnu@4.44.1": + resolution: + { + integrity: sha512-EtnsrmZGomz9WxK1bR5079zee3+7a+AdFlghyd6VbAjgRJDbTANJ9dcPIPAi76uG05micpEL+gPGmAKYTschQw==, + } cpu: [x64] os: [linux] - '@rollup/rollup-linux-x64-musl@4.44.1': - resolution: {integrity: sha512-iAS4p+J1az6Usn0f8xhgL4PaU878KEtutP4hqw52I4IO6AGoyOkHCxcc4bqufv1tQLdDWFx8lR9YlwxKuv3/3g==} + "@rollup/rollup-linux-x64-musl@4.44.1": + resolution: + { + integrity: sha512-iAS4p+J1az6Usn0f8xhgL4PaU878KEtutP4hqw52I4IO6AGoyOkHCxcc4bqufv1tQLdDWFx8lR9YlwxKuv3/3g==, + } cpu: [x64] os: [linux] - '@rollup/rollup-win32-arm64-msvc@4.44.1': - resolution: {integrity: sha512-NtSJVKcXwcqozOl+FwI41OH3OApDyLk3kqTJgx8+gp6On9ZEt5mYhIsKNPGuaZr3p9T6NWPKGU/03Vw4CNU9qg==} + "@rollup/rollup-win32-arm64-msvc@4.44.1": + resolution: + { + integrity: sha512-NtSJVKcXwcqozOl+FwI41OH3OApDyLk3kqTJgx8+gp6On9ZEt5mYhIsKNPGuaZr3p9T6NWPKGU/03Vw4CNU9qg==, + } cpu: [arm64] os: [win32] - '@rollup/rollup-win32-ia32-msvc@4.44.1': - resolution: {integrity: sha512-JYA3qvCOLXSsnTR3oiyGws1Dm0YTuxAAeaYGVlGpUsHqloPcFjPg+X0Fj2qODGLNwQOAcCiQmHub/V007kiH5A==} + "@rollup/rollup-win32-ia32-msvc@4.44.1": + resolution: + { + integrity: sha512-JYA3qvCOLXSsnTR3oiyGws1Dm0YTuxAAeaYGVlGpUsHqloPcFjPg+X0Fj2qODGLNwQOAcCiQmHub/V007kiH5A==, + } cpu: [ia32] os: [win32] - '@rollup/rollup-win32-x64-msvc@4.44.1': - resolution: {integrity: sha512-J8o22LuF0kTe7m+8PvW9wk3/bRq5+mRo5Dqo6+vXb7otCm3TPhYOJqOaQtGU9YMWQSL3krMnoOxMr0+9E6F3Ug==} + "@rollup/rollup-win32-x64-msvc@4.44.1": + resolution: + { + integrity: sha512-J8o22LuF0kTe7m+8PvW9wk3/bRq5+mRo5Dqo6+vXb7otCm3TPhYOJqOaQtGU9YMWQSL3krMnoOxMr0+9E6F3Ug==, + } cpu: [x64] os: [win32] - '@rtsao/scc@1.1.0': - resolution: {integrity: sha512-zt6OdqaDoOnJ1ZYsCYGt9YmWzDXl4vQdKTyJev62gFhRGKdx7mcT54V9KIjg+d2wi9EXsPvAPKe7i7WjfVWB8g==} + "@rtsao/scc@1.1.0": + resolution: + { + integrity: sha512-zt6OdqaDoOnJ1ZYsCYGt9YmWzDXl4vQdKTyJev62gFhRGKdx7mcT54V9KIjg+d2wi9EXsPvAPKe7i7WjfVWB8g==, + } - '@rushstack/eslint-patch@1.12.0': - resolution: {integrity: sha512-5EwMtOqvJMMa3HbmxLlF74e+3/HhwBTMcvt3nqVJgGCozO6hzIPOBlwm8mGVNR9SN2IJpxSnlxczyDjcn7qIyw==} + "@rushstack/eslint-patch@1.12.0": + resolution: + { + integrity: sha512-5EwMtOqvJMMa3HbmxLlF74e+3/HhwBTMcvt3nqVJgGCozO6hzIPOBlwm8mGVNR9SN2IJpxSnlxczyDjcn7qIyw==, + } - '@sindresorhus/merge-streams@2.3.0': - resolution: {integrity: sha512-LtoMMhxAlorcGhmFYI+LhPgbPZCkgP6ra1YL604EeF6U98pLlQ3iWIGMdWSC+vWmPBWBNgmDBAhnAobLROJmwg==} - engines: {node: '>=18'} + "@sindresorhus/merge-streams@2.3.0": + resolution: + { + integrity: sha512-LtoMMhxAlorcGhmFYI+LhPgbPZCkgP6ra1YL604EeF6U98pLlQ3iWIGMdWSC+vWmPBWBNgmDBAhnAobLROJmwg==, + } + engines: { node: ">=18" } - '@standard-schema/spec@1.0.0': - resolution: {integrity: sha512-m2bOd0f2RT9k8QJx1JN85cZYyH1RqFBdlwtkSlf4tBDYLCiiZnv1fIIwacK6cqwXavOydf0NPToMQgpKq+dVlA==} + "@standard-schema/spec@1.0.0": + resolution: + { + integrity: sha512-m2bOd0f2RT9k8QJx1JN85cZYyH1RqFBdlwtkSlf4tBDYLCiiZnv1fIIwacK6cqwXavOydf0NPToMQgpKq+dVlA==, + } - '@standard-schema/utils@0.3.0': - resolution: {integrity: sha512-e7Mew686owMaPJVNNLs55PUvgz371nKgwsc4vxE49zsODpJEnxgxRo2y/OKrqueavXgZNMDVj3DdHFlaSAeU8g==} + "@standard-schema/utils@0.3.0": + resolution: + { + integrity: sha512-e7Mew686owMaPJVNNLs55PUvgz371nKgwsc4vxE49zsODpJEnxgxRo2y/OKrqueavXgZNMDVj3DdHFlaSAeU8g==, + } - '@swc/counter@0.1.3': - resolution: {integrity: sha512-e2BR4lsJkkRlKZ/qCHPw9ZaSxc0MVUd7gtbtaB7aMvHeJVYe8sOB8DBZkP2DtISHGSku9sCK6T6cnY0CtXrOCQ==} + "@swc/counter@0.1.3": + resolution: + { + integrity: sha512-e2BR4lsJkkRlKZ/qCHPw9ZaSxc0MVUd7gtbtaB7aMvHeJVYe8sOB8DBZkP2DtISHGSku9sCK6T6cnY0CtXrOCQ==, + } - '@swc/helpers@0.5.15': - resolution: {integrity: sha512-JQ5TuMi45Owi4/BIMAJBoSQoOJu12oOk/gADqlcUL9JEdHB8vyjUSsxqeNXnmXHjYKMi2WcYtezGEEhqUI/E2g==} + "@swc/helpers@0.5.15": + resolution: + { + integrity: sha512-JQ5TuMi45Owi4/BIMAJBoSQoOJu12oOk/gADqlcUL9JEdHB8vyjUSsxqeNXnmXHjYKMi2WcYtezGEEhqUI/E2g==, + } - '@tailwindcss/node@4.1.11': - resolution: {integrity: sha512-yzhzuGRmv5QyU9qLNg4GTlYI6STedBWRE7NjxP45CsFYYq9taI0zJXZBMqIC/c8fViNLhmrbpSFS57EoxUmD6Q==} + "@tailwindcss/node@4.1.11": + resolution: + { + integrity: sha512-yzhzuGRmv5QyU9qLNg4GTlYI6STedBWRE7NjxP45CsFYYq9taI0zJXZBMqIC/c8fViNLhmrbpSFS57EoxUmD6Q==, + } - '@tailwindcss/oxide-android-arm64@4.1.11': - resolution: {integrity: sha512-3IfFuATVRUMZZprEIx9OGDjG3Ou3jG4xQzNTvjDoKmU9JdmoCohQJ83MYd0GPnQIu89YoJqvMM0G3uqLRFtetg==} - engines: {node: '>= 10'} + "@tailwindcss/oxide-android-arm64@4.1.11": + resolution: + { + integrity: sha512-3IfFuATVRUMZZprEIx9OGDjG3Ou3jG4xQzNTvjDoKmU9JdmoCohQJ83MYd0GPnQIu89YoJqvMM0G3uqLRFtetg==, + } + engines: { node: ">= 10" } cpu: [arm64] os: [android] - '@tailwindcss/oxide-darwin-arm64@4.1.11': - resolution: {integrity: sha512-ESgStEOEsyg8J5YcMb1xl8WFOXfeBmrhAwGsFxxB2CxY9evy63+AtpbDLAyRkJnxLy2WsD1qF13E97uQyP1lfQ==} - engines: {node: '>= 10'} + "@tailwindcss/oxide-darwin-arm64@4.1.11": + resolution: + { + integrity: sha512-ESgStEOEsyg8J5YcMb1xl8WFOXfeBmrhAwGsFxxB2CxY9evy63+AtpbDLAyRkJnxLy2WsD1qF13E97uQyP1lfQ==, + } + engines: { node: ">= 10" } cpu: [arm64] os: [darwin] - '@tailwindcss/oxide-darwin-x64@4.1.11': - resolution: {integrity: sha512-EgnK8kRchgmgzG6jE10UQNaH9Mwi2n+yw1jWmof9Vyg2lpKNX2ioe7CJdf9M5f8V9uaQxInenZkOxnTVL3fhAw==} - engines: {node: '>= 10'} + "@tailwindcss/oxide-darwin-x64@4.1.11": + resolution: + { + integrity: sha512-EgnK8kRchgmgzG6jE10UQNaH9Mwi2n+yw1jWmof9Vyg2lpKNX2ioe7CJdf9M5f8V9uaQxInenZkOxnTVL3fhAw==, + } + engines: { node: ">= 10" } cpu: [x64] os: [darwin] - '@tailwindcss/oxide-freebsd-x64@4.1.11': - resolution: {integrity: sha512-xdqKtbpHs7pQhIKmqVpxStnY1skuNh4CtbcyOHeX1YBE0hArj2romsFGb6yUmzkq/6M24nkxDqU8GYrKrz+UcA==} - engines: {node: '>= 10'} + "@tailwindcss/oxide-freebsd-x64@4.1.11": + resolution: + { + integrity: sha512-xdqKtbpHs7pQhIKmqVpxStnY1skuNh4CtbcyOHeX1YBE0hArj2romsFGb6yUmzkq/6M24nkxDqU8GYrKrz+UcA==, + } + engines: { node: ">= 10" } cpu: [x64] os: [freebsd] - '@tailwindcss/oxide-linux-arm-gnueabihf@4.1.11': - resolution: {integrity: sha512-ryHQK2eyDYYMwB5wZL46uoxz2zzDZsFBwfjssgB7pzytAeCCa6glsiJGjhTEddq/4OsIjsLNMAiMlHNYnkEEeg==} - engines: {node: '>= 10'} + "@tailwindcss/oxide-linux-arm-gnueabihf@4.1.11": + resolution: + { + integrity: sha512-ryHQK2eyDYYMwB5wZL46uoxz2zzDZsFBwfjssgB7pzytAeCCa6glsiJGjhTEddq/4OsIjsLNMAiMlHNYnkEEeg==, + } + engines: { node: ">= 10" } cpu: [arm] os: [linux] - '@tailwindcss/oxide-linux-arm64-gnu@4.1.11': - resolution: {integrity: sha512-mYwqheq4BXF83j/w75ewkPJmPZIqqP1nhoghS9D57CLjsh3Nfq0m4ftTotRYtGnZd3eCztgbSPJ9QhfC91gDZQ==} - engines: {node: '>= 10'} + "@tailwindcss/oxide-linux-arm64-gnu@4.1.11": + resolution: + { + integrity: sha512-mYwqheq4BXF83j/w75ewkPJmPZIqqP1nhoghS9D57CLjsh3Nfq0m4ftTotRYtGnZd3eCztgbSPJ9QhfC91gDZQ==, + } + engines: { node: ">= 10" } cpu: [arm64] os: [linux] - '@tailwindcss/oxide-linux-arm64-musl@4.1.11': - resolution: {integrity: sha512-m/NVRFNGlEHJrNVk3O6I9ggVuNjXHIPoD6bqay/pubtYC9QIdAMpS+cswZQPBLvVvEF6GtSNONbDkZrjWZXYNQ==} - engines: {node: '>= 10'} + "@tailwindcss/oxide-linux-arm64-musl@4.1.11": + resolution: + { + integrity: sha512-m/NVRFNGlEHJrNVk3O6I9ggVuNjXHIPoD6bqay/pubtYC9QIdAMpS+cswZQPBLvVvEF6GtSNONbDkZrjWZXYNQ==, + } + engines: { node: ">= 10" } cpu: [arm64] os: [linux] - '@tailwindcss/oxide-linux-x64-gnu@4.1.11': - resolution: {integrity: sha512-YW6sblI7xukSD2TdbbaeQVDysIm/UPJtObHJHKxDEcW2exAtY47j52f8jZXkqE1krdnkhCMGqP3dbniu1Te2Fg==} - engines: {node: '>= 10'} + "@tailwindcss/oxide-linux-x64-gnu@4.1.11": + resolution: + { + integrity: sha512-YW6sblI7xukSD2TdbbaeQVDysIm/UPJtObHJHKxDEcW2exAtY47j52f8jZXkqE1krdnkhCMGqP3dbniu1Te2Fg==, + } + engines: { node: ">= 10" } cpu: [x64] os: [linux] - '@tailwindcss/oxide-linux-x64-musl@4.1.11': - resolution: {integrity: sha512-e3C/RRhGunWYNC3aSF7exsQkdXzQ/M+aYuZHKnw4U7KQwTJotnWsGOIVih0s2qQzmEzOFIJ3+xt7iq67K/p56Q==} - engines: {node: '>= 10'} + "@tailwindcss/oxide-linux-x64-musl@4.1.11": + resolution: + { + integrity: sha512-e3C/RRhGunWYNC3aSF7exsQkdXzQ/M+aYuZHKnw4U7KQwTJotnWsGOIVih0s2qQzmEzOFIJ3+xt7iq67K/p56Q==, + } + engines: { node: ">= 10" } cpu: [x64] os: [linux] - '@tailwindcss/oxide-wasm32-wasi@4.1.11': - resolution: {integrity: sha512-Xo1+/GU0JEN/C/dvcammKHzeM6NqKovG+6921MR6oadee5XPBaKOumrJCXvopJ/Qb5TH7LX/UAywbqrP4lax0g==} - engines: {node: '>=14.0.0'} + "@tailwindcss/oxide-wasm32-wasi@4.1.11": + resolution: + { + integrity: sha512-Xo1+/GU0JEN/C/dvcammKHzeM6NqKovG+6921MR6oadee5XPBaKOumrJCXvopJ/Qb5TH7LX/UAywbqrP4lax0g==, + } + engines: { node: ">=14.0.0" } cpu: [wasm32] bundledDependencies: - - '@napi-rs/wasm-runtime' - - '@emnapi/core' - - '@emnapi/runtime' - - '@tybys/wasm-util' - - '@emnapi/wasi-threads' + - "@napi-rs/wasm-runtime" + - "@emnapi/core" + - "@emnapi/runtime" + - "@tybys/wasm-util" + - "@emnapi/wasi-threads" - tslib - '@tailwindcss/oxide-win32-arm64-msvc@4.1.11': - resolution: {integrity: sha512-UgKYx5PwEKrac3GPNPf6HVMNhUIGuUh4wlDFR2jYYdkX6pL/rn73zTq/4pzUm8fOjAn5L8zDeHp9iXmUGOXZ+w==} - engines: {node: '>= 10'} + "@tailwindcss/oxide-win32-arm64-msvc@4.1.11": + resolution: + { + integrity: sha512-UgKYx5PwEKrac3GPNPf6HVMNhUIGuUh4wlDFR2jYYdkX6pL/rn73zTq/4pzUm8fOjAn5L8zDeHp9iXmUGOXZ+w==, + } + engines: { node: ">= 10" } cpu: [arm64] os: [win32] - '@tailwindcss/oxide-win32-x64-msvc@4.1.11': - resolution: {integrity: sha512-YfHoggn1j0LK7wR82TOucWc5LDCguHnoS879idHekmmiR7g9HUtMw9MI0NHatS28u/Xlkfi9w5RJWgz2Dl+5Qg==} - engines: {node: '>= 10'} + "@tailwindcss/oxide-win32-x64-msvc@4.1.11": + resolution: + { + integrity: sha512-YfHoggn1j0LK7wR82TOucWc5LDCguHnoS879idHekmmiR7g9HUtMw9MI0NHatS28u/Xlkfi9w5RJWgz2Dl+5Qg==, + } + engines: { node: ">= 10" } cpu: [x64] os: [win32] - '@tailwindcss/oxide@4.1.11': - resolution: {integrity: sha512-Q69XzrtAhuyfHo+5/HMgr1lAiPP/G40OMFAnws7xcFEYqcypZmdW8eGXaOUIeOl1dzPJBPENXgbjsOyhg2nkrg==} - engines: {node: '>= 10'} + "@tailwindcss/oxide@4.1.11": + resolution: + { + integrity: sha512-Q69XzrtAhuyfHo+5/HMgr1lAiPP/G40OMFAnws7xcFEYqcypZmdW8eGXaOUIeOl1dzPJBPENXgbjsOyhg2nkrg==, + } + engines: { node: ">= 10" } - '@tailwindcss/postcss@4.1.11': - resolution: {integrity: sha512-q/EAIIpF6WpLhKEuQSEVMZNMIY8KhWoAemZ9eylNAih9jxMGAYPPWBn3I9QL/2jZ+e7OEz/tZkX5HwbBR4HohA==} + "@tailwindcss/postcss@4.1.11": + resolution: + { + integrity: sha512-q/EAIIpF6WpLhKEuQSEVMZNMIY8KhWoAemZ9eylNAih9jxMGAYPPWBn3I9QL/2jZ+e7OEz/tZkX5HwbBR4HohA==, + } - '@testing-library/dom@10.4.0': - resolution: {integrity: sha512-pemlzrSESWbdAloYml3bAJMEfNh1Z7EduzqPKprCH5S341frlpYnUEW0H72dLxa6IsYr+mPno20GiSm+h9dEdQ==} - engines: {node: '>=18'} + "@testing-library/dom@10.4.0": + resolution: + { + integrity: sha512-pemlzrSESWbdAloYml3bAJMEfNh1Z7EduzqPKprCH5S341frlpYnUEW0H72dLxa6IsYr+mPno20GiSm+h9dEdQ==, + } + engines: { node: ">=18" } - '@testing-library/react@16.3.0': - resolution: {integrity: sha512-kFSyxiEDwv1WLl2fgsq6pPBbw5aWKrsY2/noi1Id0TK0UParSF62oFQFGHXIyaG4pp2tEub/Zlel+fjjZILDsw==} - engines: {node: '>=18'} + "@testing-library/react@16.3.0": + resolution: + { + integrity: sha512-kFSyxiEDwv1WLl2fgsq6pPBbw5aWKrsY2/noi1Id0TK0UParSF62oFQFGHXIyaG4pp2tEub/Zlel+fjjZILDsw==, + } + engines: { node: ">=18" } peerDependencies: - '@testing-library/dom': ^10.0.0 - '@types/react': ^18.0.0 || ^19.0.0 - '@types/react-dom': ^18.0.0 || ^19.0.0 + "@testing-library/dom": ^10.0.0 + "@types/react": ^18.0.0 || ^19.0.0 + "@types/react-dom": ^18.0.0 || ^19.0.0 react: ^18.0.0 || ^19.0.0 react-dom: ^18.0.0 || ^19.0.0 peerDependenciesMeta: - '@types/react': + "@types/react": optional: true - '@types/react-dom': + "@types/react-dom": optional: true - '@tsconfig/node10@1.0.11': - resolution: {integrity: sha512-DcRjDCujK/kCk/cUe8Xz8ZSpm8mS3mNNpta+jGCA6USEDfktlNvm1+IuZ9eTcDbNk41BHwpHHeW+N1lKCz4zOw==} + "@tsconfig/node10@1.0.11": + resolution: + { + integrity: sha512-DcRjDCujK/kCk/cUe8Xz8ZSpm8mS3mNNpta+jGCA6USEDfktlNvm1+IuZ9eTcDbNk41BHwpHHeW+N1lKCz4zOw==, + } - '@tsconfig/node12@1.0.11': - resolution: {integrity: sha512-cqefuRsh12pWyGsIoBKJA9luFu3mRxCA+ORZvA4ktLSzIuCUtWVxGIuXigEwO5/ywWFMZ2QEGKWvkZG1zDMTag==} + "@tsconfig/node12@1.0.11": + resolution: + { + integrity: sha512-cqefuRsh12pWyGsIoBKJA9luFu3mRxCA+ORZvA4ktLSzIuCUtWVxGIuXigEwO5/ywWFMZ2QEGKWvkZG1zDMTag==, + } - '@tsconfig/node14@1.0.3': - resolution: {integrity: sha512-ysT8mhdixWK6Hw3i1V2AeRqZ5WfXg1G43mqoYlM2nc6388Fq5jcXyr5mRsqViLx/GJYdoL0bfXD8nmF+Zn/Iow==} + "@tsconfig/node14@1.0.3": + resolution: + { + integrity: sha512-ysT8mhdixWK6Hw3i1V2AeRqZ5WfXg1G43mqoYlM2nc6388Fq5jcXyr5mRsqViLx/GJYdoL0bfXD8nmF+Zn/Iow==, + } - '@tsconfig/node16@1.0.4': - resolution: {integrity: sha512-vxhUy4J8lyeyinH7Azl1pdd43GJhZH/tP2weN8TntQblOY+A0XbT8DJk1/oCPuOOyg/Ja757rG0CgHcWC8OfMA==} + "@tsconfig/node16@1.0.4": + resolution: + { + integrity: sha512-vxhUy4J8lyeyinH7Azl1pdd43GJhZH/tP2weN8TntQblOY+A0XbT8DJk1/oCPuOOyg/Ja757rG0CgHcWC8OfMA==, + } - '@tybys/wasm-util@0.9.0': - resolution: {integrity: sha512-6+7nlbMVX/PVDCwaIQ8nTOPveOcFLSt8GcXdx8hD0bt39uWxYT88uXzqTd4fTvqta7oeUJqudepapKNt2DYJFw==} + "@tybys/wasm-util@0.9.0": + resolution: + { + integrity: sha512-6+7nlbMVX/PVDCwaIQ8nTOPveOcFLSt8GcXdx8hD0bt39uWxYT88uXzqTd4fTvqta7oeUJqudepapKNt2DYJFw==, + } - '@types/aria-query@5.0.4': - resolution: {integrity: sha512-rfT93uj5s0PRL7EzccGMs3brplhcrghnDoV26NqKhCAS1hVo+WdNsPvE/yb6ilfr5hi2MEk6d5EWJTKdxg8jVw==} + "@types/aria-query@5.0.4": + resolution: + { + integrity: sha512-rfT93uj5s0PRL7EzccGMs3brplhcrghnDoV26NqKhCAS1hVo+WdNsPvE/yb6ilfr5hi2MEk6d5EWJTKdxg8jVw==, + } - '@types/babel__core@7.20.5': - resolution: {integrity: sha512-qoQprZvz5wQFJwMDqeseRXWv3rqMvhgpbXFfVyWhbx9X47POIA6i/+dXefEmZKoAgOaTdaIgNSMqMIU61yRyzA==} + "@types/babel__core@7.20.5": + resolution: + { + integrity: sha512-qoQprZvz5wQFJwMDqeseRXWv3rqMvhgpbXFfVyWhbx9X47POIA6i/+dXefEmZKoAgOaTdaIgNSMqMIU61yRyzA==, + } - '@types/babel__generator@7.27.0': - resolution: {integrity: sha512-ufFd2Xi92OAVPYsy+P4n7/U7e68fex0+Ee8gSG9KX7eo084CWiQ4sdxktvdl0bOPupXtVJPY19zk6EwWqUQ8lg==} + "@types/babel__generator@7.27.0": + resolution: + { + integrity: sha512-ufFd2Xi92OAVPYsy+P4n7/U7e68fex0+Ee8gSG9KX7eo084CWiQ4sdxktvdl0bOPupXtVJPY19zk6EwWqUQ8lg==, + } - '@types/babel__template@7.4.4': - resolution: {integrity: sha512-h/NUaSyG5EyxBIp8YRxo4RMe2/qQgvyowRwVMzhYhBCONbW8PUsg4lkFMrhgZhUe5z3L3MiLDuvyJ/CaPa2A8A==} + "@types/babel__template@7.4.4": + resolution: + { + integrity: sha512-h/NUaSyG5EyxBIp8YRxo4RMe2/qQgvyowRwVMzhYhBCONbW8PUsg4lkFMrhgZhUe5z3L3MiLDuvyJ/CaPa2A8A==, + } - '@types/babel__traverse@7.20.7': - resolution: {integrity: sha512-dkO5fhS7+/oos4ciWxyEyjWe48zmG6wbCheo/G2ZnHx4fs3EU6YC6UM8rk56gAjNJ9P3MTH2jo5jb92/K6wbng==} + "@types/babel__traverse@7.20.7": + resolution: + { + integrity: sha512-dkO5fhS7+/oos4ciWxyEyjWe48zmG6wbCheo/G2ZnHx4fs3EU6YC6UM8rk56gAjNJ9P3MTH2jo5jb92/K6wbng==, + } - '@types/bcryptjs@3.0.0': - resolution: {integrity: sha512-WRZOuCuaz8UcZZE4R5HXTco2goQSI2XxjGY3hbM/xDvwmqFWd4ivooImsMx65OKM6CtNKbnZ5YL+YwAwK7c1dg==} - deprecated: This is a stub types definition. bcryptjs provides its own type definitions, so you do not need this installed. + "@types/chai@5.2.2": + resolution: + { + integrity: sha512-8kB30R7Hwqf40JPiKhVzodJs2Qc1ZJ5zuT3uzw5Hq/dhNCl3G3l83jfpdI1e20BP348+fV7VIL/+FxaXkqBmWg==, + } - '@types/chai@5.2.2': - resolution: {integrity: sha512-8kB30R7Hwqf40JPiKhVzodJs2Qc1ZJ5zuT3uzw5Hq/dhNCl3G3l83jfpdI1e20BP348+fV7VIL/+FxaXkqBmWg==} + "@types/d3-array@3.2.1": + resolution: + { + integrity: sha512-Y2Jn2idRrLzUfAKV2LyRImR+y4oa2AntrgID95SHJxuMUrkNXmanDSed71sRNZysveJVt1hLLemQZIady0FpEg==, + } - '@types/d3-array@3.2.1': - resolution: {integrity: sha512-Y2Jn2idRrLzUfAKV2LyRImR+y4oa2AntrgID95SHJxuMUrkNXmanDSed71sRNZysveJVt1hLLemQZIady0FpEg==} + "@types/d3-axis@3.0.6": + resolution: + { + integrity: sha512-pYeijfZuBd87T0hGn0FO1vQ/cgLk6E1ALJjfkC0oJ8cbwkZl3TpgS8bVBLZN+2jjGgg38epgxb2zmoGtSfvgMw==, + } - '@types/d3-axis@3.0.6': - resolution: {integrity: sha512-pYeijfZuBd87T0hGn0FO1vQ/cgLk6E1ALJjfkC0oJ8cbwkZl3TpgS8bVBLZN+2jjGgg38epgxb2zmoGtSfvgMw==} + "@types/d3-brush@3.0.6": + resolution: + { + integrity: sha512-nH60IZNNxEcrh6L1ZSMNA28rj27ut/2ZmI3r96Zd+1jrZD++zD3LsMIjWlvg4AYrHn/Pqz4CF3veCxGjtbqt7A==, + } - '@types/d3-brush@3.0.6': - resolution: {integrity: sha512-nH60IZNNxEcrh6L1ZSMNA28rj27ut/2ZmI3r96Zd+1jrZD++zD3LsMIjWlvg4AYrHn/Pqz4CF3veCxGjtbqt7A==} + "@types/d3-chord@3.0.6": + resolution: + { + integrity: sha512-LFYWWd8nwfwEmTZG9PfQxd17HbNPksHBiJHaKuY1XeqscXacsS2tyoo6OdRsjf+NQYeB6XrNL3a25E3gH69lcg==, + } - '@types/d3-chord@3.0.6': - resolution: {integrity: sha512-LFYWWd8nwfwEmTZG9PfQxd17HbNPksHBiJHaKuY1XeqscXacsS2tyoo6OdRsjf+NQYeB6XrNL3a25E3gH69lcg==} + "@types/d3-cloud@1.2.9": + resolution: + { + integrity: sha512-5EWJvnlCrqTThGp8lYHx+DL00sOjx2HTlXH1WRe93k5pfOIhPQaL63NttaKYIbT7bTXp/USiunjNS/N4ipttIQ==, + } - '@types/d3-cloud@1.2.9': - resolution: {integrity: sha512-5EWJvnlCrqTThGp8lYHx+DL00sOjx2HTlXH1WRe93k5pfOIhPQaL63NttaKYIbT7bTXp/USiunjNS/N4ipttIQ==} + "@types/d3-color@3.1.3": + resolution: + { + integrity: sha512-iO90scth9WAbmgv7ogoq57O9YpKmFBbmoEoCHDB2xMBY0+/KVrqAaCDyCE16dUspeOvIxFFRI+0sEtqDqy2b4A==, + } - '@types/d3-color@3.1.3': - resolution: {integrity: sha512-iO90scth9WAbmgv7ogoq57O9YpKmFBbmoEoCHDB2xMBY0+/KVrqAaCDyCE16dUspeOvIxFFRI+0sEtqDqy2b4A==} + "@types/d3-contour@3.0.6": + resolution: + { + integrity: sha512-BjzLgXGnCWjUSYGfH1cpdo41/hgdWETu4YxpezoztawmqsvCeep+8QGfiY6YbDvfgHz/DkjeIkkZVJavB4a3rg==, + } - '@types/d3-contour@3.0.6': - resolution: {integrity: sha512-BjzLgXGnCWjUSYGfH1cpdo41/hgdWETu4YxpezoztawmqsvCeep+8QGfiY6YbDvfgHz/DkjeIkkZVJavB4a3rg==} + "@types/d3-delaunay@6.0.4": + resolution: + { + integrity: sha512-ZMaSKu4THYCU6sV64Lhg6qjf1orxBthaC161plr5KuPHo3CNm8DTHiLw/5Eq2b6TsNP0W0iJrUOFscY6Q450Hw==, + } - '@types/d3-delaunay@6.0.4': - resolution: {integrity: sha512-ZMaSKu4THYCU6sV64Lhg6qjf1orxBthaC161plr5KuPHo3CNm8DTHiLw/5Eq2b6TsNP0W0iJrUOFscY6Q450Hw==} + "@types/d3-dispatch@3.0.6": + resolution: + { + integrity: sha512-4fvZhzMeeuBJYZXRXrRIQnvUYfyXwYmLsdiN7XXmVNQKKw1cM8a5WdID0g1hVFZDqT9ZqZEY5pD44p24VS7iZQ==, + } - '@types/d3-dispatch@3.0.6': - resolution: {integrity: sha512-4fvZhzMeeuBJYZXRXrRIQnvUYfyXwYmLsdiN7XXmVNQKKw1cM8a5WdID0g1hVFZDqT9ZqZEY5pD44p24VS7iZQ==} + "@types/d3-drag@3.0.7": + resolution: + { + integrity: sha512-HE3jVKlzU9AaMazNufooRJ5ZpWmLIoc90A37WU2JMmeq28w1FQqCZswHZ3xR+SuxYftzHq6WU6KJHvqxKzTxxQ==, + } - '@types/d3-drag@3.0.7': - resolution: {integrity: sha512-HE3jVKlzU9AaMazNufooRJ5ZpWmLIoc90A37WU2JMmeq28w1FQqCZswHZ3xR+SuxYftzHq6WU6KJHvqxKzTxxQ==} + "@types/d3-dsv@3.0.7": + resolution: + { + integrity: sha512-n6QBF9/+XASqcKK6waudgL0pf/S5XHPPI8APyMLLUHd8NqouBGLsU8MgtO7NINGtPBtk9Kko/W4ea0oAspwh9g==, + } - '@types/d3-dsv@3.0.7': - resolution: {integrity: sha512-n6QBF9/+XASqcKK6waudgL0pf/S5XHPPI8APyMLLUHd8NqouBGLsU8MgtO7NINGtPBtk9Kko/W4ea0oAspwh9g==} + "@types/d3-ease@3.0.2": + resolution: + { + integrity: sha512-NcV1JjO5oDzoK26oMzbILE6HW7uVXOHLQvHshBUW4UMdZGfiY6v5BeQwh9a9tCzv+CeefZQHJt5SRgK154RtiA==, + } - '@types/d3-ease@3.0.2': - resolution: {integrity: sha512-NcV1JjO5oDzoK26oMzbILE6HW7uVXOHLQvHshBUW4UMdZGfiY6v5BeQwh9a9tCzv+CeefZQHJt5SRgK154RtiA==} + "@types/d3-fetch@3.0.7": + resolution: + { + integrity: sha512-fTAfNmxSb9SOWNB9IoG5c8Hg6R+AzUHDRlsXsDZsNp6sxAEOP0tkP3gKkNSO/qmHPoBFTxNrjDprVHDQDvo5aA==, + } - '@types/d3-fetch@3.0.7': - resolution: {integrity: sha512-fTAfNmxSb9SOWNB9IoG5c8Hg6R+AzUHDRlsXsDZsNp6sxAEOP0tkP3gKkNSO/qmHPoBFTxNrjDprVHDQDvo5aA==} + "@types/d3-force@3.0.10": + resolution: + { + integrity: sha512-ZYeSaCF3p73RdOKcjj+swRlZfnYpK1EbaDiYICEEp5Q6sUiqFaFQ9qgoshp5CzIyyb/yD09kD9o2zEltCexlgw==, + } - '@types/d3-force@3.0.10': - resolution: {integrity: sha512-ZYeSaCF3p73RdOKcjj+swRlZfnYpK1EbaDiYICEEp5Q6sUiqFaFQ9qgoshp5CzIyyb/yD09kD9o2zEltCexlgw==} + "@types/d3-format@3.0.4": + resolution: + { + integrity: sha512-fALi2aI6shfg7vM5KiR1wNJnZ7r6UuggVqtDA+xiEdPZQwy/trcQaHnwShLuLdta2rTymCNpxYTiMZX/e09F4g==, + } - '@types/d3-format@3.0.4': - resolution: {integrity: sha512-fALi2aI6shfg7vM5KiR1wNJnZ7r6UuggVqtDA+xiEdPZQwy/trcQaHnwShLuLdta2rTymCNpxYTiMZX/e09F4g==} + "@types/d3-geo@3.1.0": + resolution: + { + integrity: sha512-856sckF0oP/diXtS4jNsiQw/UuK5fQG8l/a9VVLeSouf1/PPbBE1i1W852zVwKwYCBkFJJB7nCFTbk6UMEXBOQ==, + } - '@types/d3-geo@3.1.0': - resolution: {integrity: sha512-856sckF0oP/diXtS4jNsiQw/UuK5fQG8l/a9VVLeSouf1/PPbBE1i1W852zVwKwYCBkFJJB7nCFTbk6UMEXBOQ==} + "@types/d3-hierarchy@3.1.7": + resolution: + { + integrity: sha512-tJFtNoYBtRtkNysX1Xq4sxtjK8YgoWUNpIiUee0/jHGRwqvzYxkq0hGVbbOGSz+JgFxxRu4K8nb3YpG3CMARtg==, + } - '@types/d3-hierarchy@3.1.7': - resolution: {integrity: sha512-tJFtNoYBtRtkNysX1Xq4sxtjK8YgoWUNpIiUee0/jHGRwqvzYxkq0hGVbbOGSz+JgFxxRu4K8nb3YpG3CMARtg==} + "@types/d3-interpolate@3.0.4": + resolution: + { + integrity: sha512-mgLPETlrpVV1YRJIglr4Ez47g7Yxjl1lj7YKsiMCb27VJH9W8NVM6Bb9d8kkpG/uAQS5AmbA48q2IAolKKo1MA==, + } - '@types/d3-interpolate@3.0.4': - resolution: {integrity: sha512-mgLPETlrpVV1YRJIglr4Ez47g7Yxjl1lj7YKsiMCb27VJH9W8NVM6Bb9d8kkpG/uAQS5AmbA48q2IAolKKo1MA==} + "@types/d3-path@3.1.1": + resolution: + { + integrity: sha512-VMZBYyQvbGmWyWVea0EHs/BwLgxc+MKi1zLDCONksozI4YJMcTt8ZEuIR4Sb1MMTE8MMW49v0IwI5+b7RmfWlg==, + } - '@types/d3-path@3.1.1': - resolution: {integrity: sha512-VMZBYyQvbGmWyWVea0EHs/BwLgxc+MKi1zLDCONksozI4YJMcTt8ZEuIR4Sb1MMTE8MMW49v0IwI5+b7RmfWlg==} + "@types/d3-polygon@3.0.2": + resolution: + { + integrity: sha512-ZuWOtMaHCkN9xoeEMr1ubW2nGWsp4nIql+OPQRstu4ypeZ+zk3YKqQT0CXVe/PYqrKpZAi+J9mTs05TKwjXSRA==, + } - '@types/d3-polygon@3.0.2': - resolution: {integrity: sha512-ZuWOtMaHCkN9xoeEMr1ubW2nGWsp4nIql+OPQRstu4ypeZ+zk3YKqQT0CXVe/PYqrKpZAi+J9mTs05TKwjXSRA==} + "@types/d3-quadtree@3.0.6": + resolution: + { + integrity: sha512-oUzyO1/Zm6rsxKRHA1vH0NEDG58HrT5icx/azi9MF1TWdtttWl0UIUsjEQBBh+SIkrpd21ZjEv7ptxWys1ncsg==, + } - '@types/d3-quadtree@3.0.6': - resolution: {integrity: sha512-oUzyO1/Zm6rsxKRHA1vH0NEDG58HrT5icx/azi9MF1TWdtttWl0UIUsjEQBBh+SIkrpd21ZjEv7ptxWys1ncsg==} + "@types/d3-random@3.0.3": + resolution: + { + integrity: sha512-Imagg1vJ3y76Y2ea0871wpabqp613+8/r0mCLEBfdtqC7xMSfj9idOnmBYyMoULfHePJyxMAw3nWhJxzc+LFwQ==, + } - '@types/d3-random@3.0.3': - resolution: {integrity: sha512-Imagg1vJ3y76Y2ea0871wpabqp613+8/r0mCLEBfdtqC7xMSfj9idOnmBYyMoULfHePJyxMAw3nWhJxzc+LFwQ==} + "@types/d3-scale-chromatic@3.1.0": + resolution: + { + integrity: sha512-iWMJgwkK7yTRmWqRB5plb1kadXyQ5Sj8V/zYlFGMUBbIPKQScw+Dku9cAAMgJG+z5GYDoMjWGLVOvjghDEFnKQ==, + } - '@types/d3-scale-chromatic@3.1.0': - resolution: {integrity: sha512-iWMJgwkK7yTRmWqRB5plb1kadXyQ5Sj8V/zYlFGMUBbIPKQScw+Dku9cAAMgJG+z5GYDoMjWGLVOvjghDEFnKQ==} + "@types/d3-scale@4.0.9": + resolution: + { + integrity: sha512-dLmtwB8zkAeO/juAMfnV+sItKjlsw2lKdZVVy6LRr0cBmegxSABiLEpGVmSJJ8O08i4+sGR6qQtb6WtuwJdvVw==, + } - '@types/d3-scale@4.0.9': - resolution: {integrity: sha512-dLmtwB8zkAeO/juAMfnV+sItKjlsw2lKdZVVy6LRr0cBmegxSABiLEpGVmSJJ8O08i4+sGR6qQtb6WtuwJdvVw==} + "@types/d3-selection@3.0.11": + resolution: + { + integrity: sha512-bhAXu23DJWsrI45xafYpkQ4NtcKMwWnAC/vKrd2l+nxMFuvOT3XMYTIj2opv8vq8AO5Yh7Qac/nSeP/3zjTK0w==, + } - '@types/d3-selection@3.0.11': - resolution: {integrity: sha512-bhAXu23DJWsrI45xafYpkQ4NtcKMwWnAC/vKrd2l+nxMFuvOT3XMYTIj2opv8vq8AO5Yh7Qac/nSeP/3zjTK0w==} + "@types/d3-shape@3.1.7": + resolution: + { + integrity: sha512-VLvUQ33C+3J+8p+Daf+nYSOsjB4GXp19/S/aGo60m9h1v6XaxjiT82lKVWJCfzhtuZ3yD7i/TPeC/fuKLLOSmg==, + } - '@types/d3-shape@3.1.7': - resolution: {integrity: sha512-VLvUQ33C+3J+8p+Daf+nYSOsjB4GXp19/S/aGo60m9h1v6XaxjiT82lKVWJCfzhtuZ3yD7i/TPeC/fuKLLOSmg==} + "@types/d3-time-format@4.0.3": + resolution: + { + integrity: sha512-5xg9rC+wWL8kdDj153qZcsJ0FWiFt0J5RB6LYUNZjwSnesfblqrI/bJ1wBdJ8OQfncgbJG5+2F+qfqnqyzYxyg==, + } - '@types/d3-time-format@4.0.3': - resolution: {integrity: sha512-5xg9rC+wWL8kdDj153qZcsJ0FWiFt0J5RB6LYUNZjwSnesfblqrI/bJ1wBdJ8OQfncgbJG5+2F+qfqnqyzYxyg==} + "@types/d3-time@3.0.4": + resolution: + { + integrity: sha512-yuzZug1nkAAaBlBBikKZTgzCeA+k1uy4ZFwWANOfKw5z5LRhV0gNA7gNkKm7HoK+HRN0wX3EkxGk0fpbWhmB7g==, + } - '@types/d3-time@3.0.4': - resolution: {integrity: sha512-yuzZug1nkAAaBlBBikKZTgzCeA+k1uy4ZFwWANOfKw5z5LRhV0gNA7gNkKm7HoK+HRN0wX3EkxGk0fpbWhmB7g==} + "@types/d3-timer@3.0.2": + resolution: + { + integrity: sha512-Ps3T8E8dZDam6fUyNiMkekK3XUsaUEik+idO9/YjPtfj2qruF8tFBXS7XhtE4iIXBLxhmLjP3SXpLhVf21I9Lw==, + } - '@types/d3-timer@3.0.2': - resolution: {integrity: sha512-Ps3T8E8dZDam6fUyNiMkekK3XUsaUEik+idO9/YjPtfj2qruF8tFBXS7XhtE4iIXBLxhmLjP3SXpLhVf21I9Lw==} + "@types/d3-transition@3.0.9": + resolution: + { + integrity: sha512-uZS5shfxzO3rGlu0cC3bjmMFKsXv+SmZZcgp0KD22ts4uGXp5EVYGzu/0YdwZeKmddhcAccYtREJKkPfXkZuCg==, + } - '@types/d3-transition@3.0.9': - resolution: {integrity: sha512-uZS5shfxzO3rGlu0cC3bjmMFKsXv+SmZZcgp0KD22ts4uGXp5EVYGzu/0YdwZeKmddhcAccYtREJKkPfXkZuCg==} + "@types/d3-zoom@3.0.8": + resolution: + { + integrity: sha512-iqMC4/YlFCSlO8+2Ii1GGGliCAY4XdeG748w5vQUbevlbDu0zSjH/+jojorQVBK/se0j6DUFNPBGSqD3YWYnDw==, + } - '@types/d3-zoom@3.0.8': - resolution: {integrity: sha512-iqMC4/YlFCSlO8+2Ii1GGGliCAY4XdeG748w5vQUbevlbDu0zSjH/+jojorQVBK/se0j6DUFNPBGSqD3YWYnDw==} + "@types/d3@3.5.53": + resolution: + { + integrity: sha512-8yKQA9cAS6+wGsJpBysmnhlaaxlN42Qizqkw+h2nILSlS+MAG2z4JdO6p+PJrJ+ACvimkmLJL281h157e52psQ==, + } - '@types/d3@3.5.53': - resolution: {integrity: sha512-8yKQA9cAS6+wGsJpBysmnhlaaxlN42Qizqkw+h2nILSlS+MAG2z4JdO6p+PJrJ+ACvimkmLJL281h157e52psQ==} + "@types/d3@7.4.3": + resolution: + { + integrity: sha512-lZXZ9ckh5R8uiFVt8ogUNf+pIrK4EsWrx2Np75WvF/eTpJ0FMHNhjXk8CKEx/+gpHbNQyJWehbFaTvqmHWB3ww==, + } - '@types/d3@7.4.3': - resolution: {integrity: sha512-lZXZ9ckh5R8uiFVt8ogUNf+pIrK4EsWrx2Np75WvF/eTpJ0FMHNhjXk8CKEx/+gpHbNQyJWehbFaTvqmHWB3ww==} + "@types/debug@4.1.12": + resolution: + { + integrity: sha512-vIChWdVG3LG1SMxEvI/AK+FWJthlrqlTu7fbrlywTkkaONwk/UAGaULXRlf8vkzFBLVm0zkMdCquhL5aOjhXPQ==, + } - '@types/debug@4.1.12': - resolution: {integrity: sha512-vIChWdVG3LG1SMxEvI/AK+FWJthlrqlTu7fbrlywTkkaONwk/UAGaULXRlf8vkzFBLVm0zkMdCquhL5aOjhXPQ==} + "@types/deep-eql@4.0.2": + resolution: + { + integrity: sha512-c9h9dVVMigMPc4bwTvC5dxqtqJZwQPePsWjPlpSOnojbor6pGqdk541lfA7AqFQr5pB1BRdq0juY9db81BwyFw==, + } - '@types/deep-eql@4.0.2': - resolution: {integrity: sha512-c9h9dVVMigMPc4bwTvC5dxqtqJZwQPePsWjPlpSOnojbor6pGqdk541lfA7AqFQr5pB1BRdq0juY9db81BwyFw==} + "@types/estree-jsx@1.0.5": + resolution: + { + integrity: sha512-52CcUVNFyfb1A2ALocQw/Dd1BQFNmSdkuC3BkZ6iqhdMfQz7JWOFRuJFloOzjk+6WijU56m9oKXFAXc7o3Towg==, + } - '@types/estree-jsx@1.0.5': - resolution: {integrity: sha512-52CcUVNFyfb1A2ALocQw/Dd1BQFNmSdkuC3BkZ6iqhdMfQz7JWOFRuJFloOzjk+6WijU56m9oKXFAXc7o3Towg==} + "@types/estree@1.0.8": + resolution: + { + integrity: sha512-dWHzHa2WqEXI/O1E9OjrocMTKJl2mSrEolh1Iomrv6U+JuNwaHXsXx9bLu5gG7BUWFIN0skIQJQ/L1rIex4X6w==, + } - '@types/estree@1.0.8': - resolution: {integrity: sha512-dWHzHa2WqEXI/O1E9OjrocMTKJl2mSrEolh1Iomrv6U+JuNwaHXsXx9bLu5gG7BUWFIN0skIQJQ/L1rIex4X6w==} + "@types/geojson@7946.0.16": + resolution: + { + integrity: sha512-6C8nqWur3j98U6+lXDfTUWIfgvZU+EumvpHKcYjujKH7woYyLj2sUmff0tRhrqM7BohUw7Pz3ZB1jj2gW9Fvmg==, + } - '@types/geojson@7946.0.16': - resolution: {integrity: sha512-6C8nqWur3j98U6+lXDfTUWIfgvZU+EumvpHKcYjujKH7woYyLj2sUmff0tRhrqM7BohUw7Pz3ZB1jj2gW9Fvmg==} + "@types/hast@3.0.4": + resolution: + { + integrity: sha512-WPs+bbQw5aCj+x6laNGWLH3wviHtoCv/P3+otBhbOhJgG8qtpdAMlTCxLtsTWA7LH1Oh/bFCHsBn0TPS5m30EQ==, + } - '@types/hast@3.0.4': - resolution: {integrity: sha512-WPs+bbQw5aCj+x6laNGWLH3wviHtoCv/P3+otBhbOhJgG8qtpdAMlTCxLtsTWA7LH1Oh/bFCHsBn0TPS5m30EQ==} + "@types/json-schema@7.0.15": + resolution: + { + integrity: sha512-5+fP8P8MFNC+AyZCDxrB2pkZFPGzqQWUzpSeuuVLvm8VMcorNYavBqoFcxK8bQz4Qsbn4oUEEem4wDLfcysGHA==, + } - '@types/json-schema@7.0.15': - resolution: {integrity: sha512-5+fP8P8MFNC+AyZCDxrB2pkZFPGzqQWUzpSeuuVLvm8VMcorNYavBqoFcxK8bQz4Qsbn4oUEEem4wDLfcysGHA==} + "@types/json5@0.0.29": + resolution: + { + integrity: sha512-dRLjCWHYg4oaA77cxO64oO+7JwCwnIzkZPdrrC71jQmQtlhM556pwKo5bUzqvZndkVbeFLIIi+9TC40JNF5hNQ==, + } - '@types/json5@0.0.29': - resolution: {integrity: sha512-dRLjCWHYg4oaA77cxO64oO+7JwCwnIzkZPdrrC71jQmQtlhM556pwKo5bUzqvZndkVbeFLIIi+9TC40JNF5hNQ==} + "@types/katex@0.16.7": + resolution: + { + integrity: sha512-HMwFiRujE5PjrgwHQ25+bsLJgowjGjm5Z8FVSf0N6PwgJrwxH0QxzHYDcKsTfV3wva0vzrpqMTJS2jXPr5BMEQ==, + } - '@types/katex@0.16.7': - resolution: {integrity: sha512-HMwFiRujE5PjrgwHQ25+bsLJgowjGjm5Z8FVSf0N6PwgJrwxH0QxzHYDcKsTfV3wva0vzrpqMTJS2jXPr5BMEQ==} + "@types/leaflet@1.9.19": + resolution: + { + integrity: sha512-pB+n2daHcZPF2FDaWa+6B0a0mSDf4dPU35y5iTXsx7x/PzzshiX5atYiS1jlBn43X7XvM8AP+AB26lnSk0J4GA==, + } - '@types/leaflet@1.9.19': - resolution: {integrity: sha512-pB+n2daHcZPF2FDaWa+6B0a0mSDf4dPU35y5iTXsx7x/PzzshiX5atYiS1jlBn43X7XvM8AP+AB26lnSk0J4GA==} + "@types/mdast@4.0.4": + resolution: + { + integrity: sha512-kGaNbPh1k7AFzgpud/gMdvIm5xuECykRR+JnWKQno9TAXVa6WIVCGTPvYGekIDL4uwCZQSYbUxNBSb1aUo79oA==, + } - '@types/mdast@4.0.4': - resolution: {integrity: sha512-kGaNbPh1k7AFzgpud/gMdvIm5xuECykRR+JnWKQno9TAXVa6WIVCGTPvYGekIDL4uwCZQSYbUxNBSb1aUo79oA==} + "@types/ms@2.1.0": + resolution: + { + integrity: sha512-GsCCIZDE/p3i96vtEqx+7dBUGXrc7zeSK3wwPHIaRThS+9OhWIXRqzs4d6k1SVU8g91DrNRWxWUGhp5KXQb2VA==, + } - '@types/ms@2.1.0': - resolution: {integrity: sha512-GsCCIZDE/p3i96vtEqx+7dBUGXrc7zeSK3wwPHIaRThS+9OhWIXRqzs4d6k1SVU8g91DrNRWxWUGhp5KXQb2VA==} + "@types/node-cron@3.0.11": + resolution: + { + integrity: sha512-0ikrnug3/IyneSHqCBeslAhlK2aBfYek1fGo4bP4QnZPmiqSGRK+Oy7ZMisLWkesffJvQ1cqAcBnJC+8+nxIAg==, + } - '@types/node-cron@3.0.11': - resolution: {integrity: sha512-0ikrnug3/IyneSHqCBeslAhlK2aBfYek1fGo4bP4QnZPmiqSGRK+Oy7ZMisLWkesffJvQ1cqAcBnJC+8+nxIAg==} + "@types/node-fetch@2.6.12": + resolution: + { + integrity: sha512-8nneRWKCg3rMtF69nLQJnOYUcbafYeFSjqkw3jCRLsqkWFlHaoQrr5mXmofFGOx3DKn7UfmBMyov8ySvLRVldA==, + } - '@types/node-fetch@2.6.12': - resolution: {integrity: sha512-8nneRWKCg3rMtF69nLQJnOYUcbafYeFSjqkw3jCRLsqkWFlHaoQrr5mXmofFGOx3DKn7UfmBMyov8ySvLRVldA==} + "@types/node@24.0.6": + resolution: + { + integrity: sha512-ZOyn+gOs749xU7ovp+Ibj0g1o3dFRqsfPnT22C2t5JzcRvgsEDpGawPbCISGKLudJk9Y0wiu9sYd6kUh0pc9TA==, + } - '@types/node@24.0.6': - resolution: {integrity: sha512-ZOyn+gOs749xU7ovp+Ibj0g1o3dFRqsfPnT22C2t5JzcRvgsEDpGawPbCISGKLudJk9Y0wiu9sYd6kUh0pc9TA==} - - '@types/react-dom@19.1.6': - resolution: {integrity: sha512-4hOiT/dwO8Ko0gV1m/TJZYk3y0KBnY9vzDh7W+DH17b2HFSOGgdj33dhihPeuy3l0q23+4e+hoXHV6hCC4dCXw==} + "@types/react-dom@19.1.6": + resolution: + { + integrity: sha512-4hOiT/dwO8Ko0gV1m/TJZYk3y0KBnY9vzDh7W+DH17b2HFSOGgdj33dhihPeuy3l0q23+4e+hoXHV6hCC4dCXw==, + } peerDependencies: - '@types/react': ^19.0.0 + "@types/react": ^19.0.0 - '@types/react@19.1.8': - resolution: {integrity: sha512-AwAfQ2Wa5bCx9WP8nZL2uMZWod7J7/JSplxbTmBQ5ms6QpqNYm672H0Vu9ZVKVngQ+ii4R/byguVEUZQyeg44g==} + "@types/react@19.1.8": + resolution: + { + integrity: sha512-AwAfQ2Wa5bCx9WP8nZL2uMZWod7J7/JSplxbTmBQ5ms6QpqNYm672H0Vu9ZVKVngQ+ii4R/byguVEUZQyeg44g==, + } - '@types/unist@2.0.11': - resolution: {integrity: sha512-CmBKiL6NNo/OqgmMn95Fk9Whlp2mtvIv+KNpQKN2F4SjvrEesubTRWGYSg+BnWZOnlCaSTU1sMpsBOzgbYhnsA==} + "@types/unist@2.0.11": + resolution: + { + integrity: sha512-CmBKiL6NNo/OqgmMn95Fk9Whlp2mtvIv+KNpQKN2F4SjvrEesubTRWGYSg+BnWZOnlCaSTU1sMpsBOzgbYhnsA==, + } - '@types/unist@3.0.3': - resolution: {integrity: sha512-ko/gIFJRv177XgZsZcBwnqJN5x/Gien8qNOn0D5bQU/zAzVf9Zt3BlcUiLqhV9y4ARk0GbT3tnUiPNgnTXzc/Q==} + "@types/unist@3.0.3": + resolution: + { + integrity: sha512-ko/gIFJRv177XgZsZcBwnqJN5x/Gien8qNOn0D5bQU/zAzVf9Zt3BlcUiLqhV9y4ARk0GbT3tnUiPNgnTXzc/Q==, + } - '@types/use-sync-external-store@0.0.6': - resolution: {integrity: sha512-zFDAD+tlpf2r4asuHEj0XH6pY6i0g5NeAHPn+15wk3BV6JA69eERFXC1gyGThDkVa1zCyKr5jox1+2LbV/AMLg==} + "@types/use-sync-external-store@0.0.6": + resolution: + { + integrity: sha512-zFDAD+tlpf2r4asuHEj0XH6pY6i0g5NeAHPn+15wk3BV6JA69eERFXC1gyGThDkVa1zCyKr5jox1+2LbV/AMLg==, + } - '@typescript-eslint/eslint-plugin@8.35.0': - resolution: {integrity: sha512-ijItUYaiWuce0N1SoSMrEd0b6b6lYkYt99pqCPfybd+HKVXtEvYhICfLdwp42MhiI5mp0oq7PKEL+g1cNiz/Eg==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + "@typescript-eslint/eslint-plugin@8.35.0": + resolution: + { + integrity: sha512-ijItUYaiWuce0N1SoSMrEd0b6b6lYkYt99pqCPfybd+HKVXtEvYhICfLdwp42MhiI5mp0oq7PKEL+g1cNiz/Eg==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } peerDependencies: - '@typescript-eslint/parser': ^8.35.0 + "@typescript-eslint/parser": ^8.35.0 eslint: ^8.57.0 || ^9.0.0 - typescript: '>=4.8.4 <5.9.0' + typescript: ">=4.8.4 <5.9.0" - '@typescript-eslint/parser@8.35.0': - resolution: {integrity: sha512-6sMvZePQrnZH2/cJkwRpkT7DxoAWh+g6+GFRK6bV3YQo7ogi3SX5rgF6099r5Q53Ma5qeT7LGmOmuIutF4t3lA==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + "@typescript-eslint/parser@8.35.0": + resolution: + { + integrity: sha512-6sMvZePQrnZH2/cJkwRpkT7DxoAWh+g6+GFRK6bV3YQo7ogi3SX5rgF6099r5Q53Ma5qeT7LGmOmuIutF4t3lA==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } peerDependencies: eslint: ^8.57.0 || ^9.0.0 - typescript: '>=4.8.4 <5.9.0' + typescript: ">=4.8.4 <5.9.0" - '@typescript-eslint/project-service@8.35.0': - resolution: {integrity: sha512-41xatqRwWZuhUMF/aZm2fcUsOFKNcG28xqRSS6ZVr9BVJtGExosLAm5A1OxTjRMagx8nJqva+P5zNIGt8RIgbQ==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + "@typescript-eslint/project-service@8.35.0": + resolution: + { + integrity: sha512-41xatqRwWZuhUMF/aZm2fcUsOFKNcG28xqRSS6ZVr9BVJtGExosLAm5A1OxTjRMagx8nJqva+P5zNIGt8RIgbQ==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } peerDependencies: - typescript: '>=4.8.4 <5.9.0' + typescript: ">=4.8.4 <5.9.0" - '@typescript-eslint/scope-manager@8.35.0': - resolution: {integrity: sha512-+AgL5+mcoLxl1vGjwNfiWq5fLDZM1TmTPYs2UkyHfFhgERxBbqHlNjRzhThJqz+ktBqTChRYY6zwbMwy0591AA==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + "@typescript-eslint/scope-manager@8.35.0": + resolution: + { + integrity: sha512-+AgL5+mcoLxl1vGjwNfiWq5fLDZM1TmTPYs2UkyHfFhgERxBbqHlNjRzhThJqz+ktBqTChRYY6zwbMwy0591AA==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } - '@typescript-eslint/tsconfig-utils@8.35.0': - resolution: {integrity: sha512-04k/7247kZzFraweuEirmvUj+W3bJLI9fX6fbo1Qm2YykuBvEhRTPl8tcxlYO8kZZW+HIXfkZNoasVb8EV4jpA==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + "@typescript-eslint/tsconfig-utils@8.35.0": + resolution: + { + integrity: sha512-04k/7247kZzFraweuEirmvUj+W3bJLI9fX6fbo1Qm2YykuBvEhRTPl8tcxlYO8kZZW+HIXfkZNoasVb8EV4jpA==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } peerDependencies: - typescript: '>=4.8.4 <5.9.0' + typescript: ">=4.8.4 <5.9.0" - '@typescript-eslint/type-utils@8.35.0': - resolution: {integrity: sha512-ceNNttjfmSEoM9PW87bWLDEIaLAyR+E6BoYJQ5PfaDau37UGca9Nyq3lBk8Bw2ad0AKvYabz6wxc7DMTO2jnNA==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + "@typescript-eslint/type-utils@8.35.0": + resolution: + { + integrity: sha512-ceNNttjfmSEoM9PW87bWLDEIaLAyR+E6BoYJQ5PfaDau37UGca9Nyq3lBk8Bw2ad0AKvYabz6wxc7DMTO2jnNA==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } peerDependencies: eslint: ^8.57.0 || ^9.0.0 - typescript: '>=4.8.4 <5.9.0' + typescript: ">=4.8.4 <5.9.0" - '@typescript-eslint/types@8.35.0': - resolution: {integrity: sha512-0mYH3emanku0vHw2aRLNGqe7EXh9WHEhi7kZzscrMDf6IIRUQ5Jk4wp1QrledE/36KtdZrVfKnE32eZCf/vaVQ==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + "@typescript-eslint/types@8.35.0": + resolution: + { + integrity: sha512-0mYH3emanku0vHw2aRLNGqe7EXh9WHEhi7kZzscrMDf6IIRUQ5Jk4wp1QrledE/36KtdZrVfKnE32eZCf/vaVQ==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } - '@typescript-eslint/typescript-estree@8.35.0': - resolution: {integrity: sha512-F+BhnaBemgu1Qf8oHrxyw14wq6vbL8xwWKKMwTMwYIRmFFY/1n/9T/jpbobZL8vp7QyEUcC6xGrnAO4ua8Kp7w==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + "@typescript-eslint/typescript-estree@8.35.0": + resolution: + { + integrity: sha512-F+BhnaBemgu1Qf8oHrxyw14wq6vbL8xwWKKMwTMwYIRmFFY/1n/9T/jpbobZL8vp7QyEUcC6xGrnAO4ua8Kp7w==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } peerDependencies: - typescript: '>=4.8.4 <5.9.0' + typescript: ">=4.8.4 <5.9.0" - '@typescript-eslint/utils@8.35.0': - resolution: {integrity: sha512-nqoMu7WWM7ki5tPgLVsmPM8CkqtoPUG6xXGeefM5t4x3XumOEKMoUZPdi+7F+/EotukN4R9OWdmDxN80fqoZeg==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + "@typescript-eslint/utils@8.35.0": + resolution: + { + integrity: sha512-nqoMu7WWM7ki5tPgLVsmPM8CkqtoPUG6xXGeefM5t4x3XumOEKMoUZPdi+7F+/EotukN4R9OWdmDxN80fqoZeg==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } peerDependencies: eslint: ^8.57.0 || ^9.0.0 - typescript: '>=4.8.4 <5.9.0' + typescript: ">=4.8.4 <5.9.0" - '@typescript-eslint/visitor-keys@8.35.0': - resolution: {integrity: sha512-zTh2+1Y8ZpmeQaQVIc/ZZxsx8UzgKJyNg1PTvjzC7WMhPSVS8bfDX34k1SrwOf016qd5RU3az2UxUNue3IfQ5g==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + "@typescript-eslint/visitor-keys@8.35.0": + resolution: + { + integrity: sha512-zTh2+1Y8ZpmeQaQVIc/ZZxsx8UzgKJyNg1PTvjzC7WMhPSVS8bfDX34k1SrwOf016qd5RU3az2UxUNue3IfQ5g==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } - '@ungap/structured-clone@1.3.0': - resolution: {integrity: sha512-WmoN8qaIAo7WTYWbAZuG8PYEhn5fkz7dZrqTBZ7dtt//lL2Gwms1IcnQ5yHqjDfX8Ft5j4YzDM23f87zBfDe9g==} + "@ungap/structured-clone@1.3.0": + resolution: + { + integrity: sha512-WmoN8qaIAo7WTYWbAZuG8PYEhn5fkz7dZrqTBZ7dtt//lL2Gwms1IcnQ5yHqjDfX8Ft5j4YzDM23f87zBfDe9g==, + } - '@unrs/resolver-binding-android-arm-eabi@1.9.2': - resolution: {integrity: sha512-tS+lqTU3N0kkthU+rYp0spAYq15DU8ld9kXkaKg9sbQqJNF+WPMuNHZQGCgdxrUOEO0j22RKMwRVhF1HTl+X8A==} + "@unrs/resolver-binding-android-arm-eabi@1.9.2": + resolution: + { + integrity: sha512-tS+lqTU3N0kkthU+rYp0spAYq15DU8ld9kXkaKg9sbQqJNF+WPMuNHZQGCgdxrUOEO0j22RKMwRVhF1HTl+X8A==, + } cpu: [arm] os: [android] - '@unrs/resolver-binding-android-arm64@1.9.2': - resolution: {integrity: sha512-MffGiZULa/KmkNjHeuuflLVqfhqLv1vZLm8lWIyeADvlElJ/GLSOkoUX+5jf4/EGtfwrNFcEaB8BRas03KT0/Q==} + "@unrs/resolver-binding-android-arm64@1.9.2": + resolution: + { + integrity: sha512-MffGiZULa/KmkNjHeuuflLVqfhqLv1vZLm8lWIyeADvlElJ/GLSOkoUX+5jf4/EGtfwrNFcEaB8BRas03KT0/Q==, + } cpu: [arm64] os: [android] - '@unrs/resolver-binding-darwin-arm64@1.9.2': - resolution: {integrity: sha512-dzJYK5rohS1sYl1DHdJ3mwfwClJj5BClQnQSyAgEfggbUwA9RlROQSSbKBLqrGfsiC/VyrDPtbO8hh56fnkbsQ==} + "@unrs/resolver-binding-darwin-arm64@1.9.2": + resolution: + { + integrity: sha512-dzJYK5rohS1sYl1DHdJ3mwfwClJj5BClQnQSyAgEfggbUwA9RlROQSSbKBLqrGfsiC/VyrDPtbO8hh56fnkbsQ==, + } cpu: [arm64] os: [darwin] - '@unrs/resolver-binding-darwin-x64@1.9.2': - resolution: {integrity: sha512-gaIMWK+CWtXcg9gUyznkdV54LzQ90S3X3dn8zlh+QR5Xy7Y+Efqw4Rs4im61K1juy4YNb67vmJsCDAGOnIeffQ==} + "@unrs/resolver-binding-darwin-x64@1.9.2": + resolution: + { + integrity: sha512-gaIMWK+CWtXcg9gUyznkdV54LzQ90S3X3dn8zlh+QR5Xy7Y+Efqw4Rs4im61K1juy4YNb67vmJsCDAGOnIeffQ==, + } cpu: [x64] os: [darwin] - '@unrs/resolver-binding-freebsd-x64@1.9.2': - resolution: {integrity: sha512-S7QpkMbVoVJb0xwHFwujnwCAEDe/596xqY603rpi/ioTn9VDgBHnCCxh+UFrr5yxuMH+dliHfjwCZJXOPJGPnw==} + "@unrs/resolver-binding-freebsd-x64@1.9.2": + resolution: + { + integrity: sha512-S7QpkMbVoVJb0xwHFwujnwCAEDe/596xqY603rpi/ioTn9VDgBHnCCxh+UFrr5yxuMH+dliHfjwCZJXOPJGPnw==, + } cpu: [x64] os: [freebsd] - '@unrs/resolver-binding-linux-arm-gnueabihf@1.9.2': - resolution: {integrity: sha512-+XPUMCuCCI80I46nCDFbGum0ZODP5NWGiwS3Pj8fOgsG5/ctz+/zzuBlq/WmGa+EjWZdue6CF0aWWNv84sE1uw==} + "@unrs/resolver-binding-linux-arm-gnueabihf@1.9.2": + resolution: + { + integrity: sha512-+XPUMCuCCI80I46nCDFbGum0ZODP5NWGiwS3Pj8fOgsG5/ctz+/zzuBlq/WmGa+EjWZdue6CF0aWWNv84sE1uw==, + } cpu: [arm] os: [linux] - '@unrs/resolver-binding-linux-arm-musleabihf@1.9.2': - resolution: {integrity: sha512-sqvUyAd1JUpwbz33Ce2tuTLJKM+ucSsYpPGl2vuFwZnEIg0CmdxiZ01MHQ3j6ExuRqEDUCy8yvkDKvjYFPb8Zg==} + "@unrs/resolver-binding-linux-arm-musleabihf@1.9.2": + resolution: + { + integrity: sha512-sqvUyAd1JUpwbz33Ce2tuTLJKM+ucSsYpPGl2vuFwZnEIg0CmdxiZ01MHQ3j6ExuRqEDUCy8yvkDKvjYFPb8Zg==, + } cpu: [arm] os: [linux] - '@unrs/resolver-binding-linux-arm64-gnu@1.9.2': - resolution: {integrity: sha512-UYA0MA8ajkEDCFRQdng/FVx3F6szBvk3EPnkTTQuuO9lV1kPGuTB+V9TmbDxy5ikaEgyWKxa4CI3ySjklZ9lFA==} + "@unrs/resolver-binding-linux-arm64-gnu@1.9.2": + resolution: + { + integrity: sha512-UYA0MA8ajkEDCFRQdng/FVx3F6szBvk3EPnkTTQuuO9lV1kPGuTB+V9TmbDxy5ikaEgyWKxa4CI3ySjklZ9lFA==, + } cpu: [arm64] os: [linux] - '@unrs/resolver-binding-linux-arm64-musl@1.9.2': - resolution: {integrity: sha512-P/CO3ODU9YJIHFqAkHbquKtFst0COxdphc8TKGL5yCX75GOiVpGqd1d15ahpqu8xXVsqP4MGFP2C3LRZnnL5MA==} + "@unrs/resolver-binding-linux-arm64-musl@1.9.2": + resolution: + { + integrity: sha512-P/CO3ODU9YJIHFqAkHbquKtFst0COxdphc8TKGL5yCX75GOiVpGqd1d15ahpqu8xXVsqP4MGFP2C3LRZnnL5MA==, + } cpu: [arm64] os: [linux] - '@unrs/resolver-binding-linux-ppc64-gnu@1.9.2': - resolution: {integrity: sha512-uKStFlOELBxBum2s1hODPtgJhY4NxYJE9pAeyBgNEzHgTqTiVBPjfTlPFJkfxyTjQEuxZbbJlJnMCrRgD7ubzw==} + "@unrs/resolver-binding-linux-ppc64-gnu@1.9.2": + resolution: + { + integrity: sha512-uKStFlOELBxBum2s1hODPtgJhY4NxYJE9pAeyBgNEzHgTqTiVBPjfTlPFJkfxyTjQEuxZbbJlJnMCrRgD7ubzw==, + } cpu: [ppc64] os: [linux] - '@unrs/resolver-binding-linux-riscv64-gnu@1.9.2': - resolution: {integrity: sha512-LkbNnZlhINfY9gK30AHs26IIVEZ9PEl9qOScYdmY2o81imJYI4IMnJiW0vJVtXaDHvBvxeAgEy5CflwJFIl3tQ==} + "@unrs/resolver-binding-linux-riscv64-gnu@1.9.2": + resolution: + { + integrity: sha512-LkbNnZlhINfY9gK30AHs26IIVEZ9PEl9qOScYdmY2o81imJYI4IMnJiW0vJVtXaDHvBvxeAgEy5CflwJFIl3tQ==, + } cpu: [riscv64] os: [linux] - '@unrs/resolver-binding-linux-riscv64-musl@1.9.2': - resolution: {integrity: sha512-vI+e6FzLyZHSLFNomPi+nT+qUWN4YSj8pFtQZSFTtmgFoxqB6NyjxSjAxEC1m93qn6hUXhIsh8WMp+fGgxCoRg==} + "@unrs/resolver-binding-linux-riscv64-musl@1.9.2": + resolution: + { + integrity: sha512-vI+e6FzLyZHSLFNomPi+nT+qUWN4YSj8pFtQZSFTtmgFoxqB6NyjxSjAxEC1m93qn6hUXhIsh8WMp+fGgxCoRg==, + } cpu: [riscv64] os: [linux] - '@unrs/resolver-binding-linux-s390x-gnu@1.9.2': - resolution: {integrity: sha512-sSO4AlAYhSM2RAzBsRpahcJB1msc6uYLAtP6pesPbZtptF8OU/CbCPhSRW6cnYOGuVmEmWVW5xVboAqCnWTeHQ==} + "@unrs/resolver-binding-linux-s390x-gnu@1.9.2": + resolution: + { + integrity: sha512-sSO4AlAYhSM2RAzBsRpahcJB1msc6uYLAtP6pesPbZtptF8OU/CbCPhSRW6cnYOGuVmEmWVW5xVboAqCnWTeHQ==, + } cpu: [s390x] os: [linux] - '@unrs/resolver-binding-linux-x64-gnu@1.9.2': - resolution: {integrity: sha512-jkSkwch0uPFva20Mdu8orbQjv2A3G88NExTN2oPTI1AJ+7mZfYW3cDCTyoH6OnctBKbBVeJCEqh0U02lTkqD5w==} + "@unrs/resolver-binding-linux-x64-gnu@1.9.2": + resolution: + { + integrity: sha512-jkSkwch0uPFva20Mdu8orbQjv2A3G88NExTN2oPTI1AJ+7mZfYW3cDCTyoH6OnctBKbBVeJCEqh0U02lTkqD5w==, + } cpu: [x64] os: [linux] - '@unrs/resolver-binding-linux-x64-musl@1.9.2': - resolution: {integrity: sha512-Uk64NoiTpQbkpl+bXsbeyOPRpUoMdcUqa+hDC1KhMW7aN1lfW8PBlBH4mJ3n3Y47dYE8qi0XTxy1mBACruYBaw==} + "@unrs/resolver-binding-linux-x64-musl@1.9.2": + resolution: + { + integrity: sha512-Uk64NoiTpQbkpl+bXsbeyOPRpUoMdcUqa+hDC1KhMW7aN1lfW8PBlBH4mJ3n3Y47dYE8qi0XTxy1mBACruYBaw==, + } cpu: [x64] os: [linux] - '@unrs/resolver-binding-wasm32-wasi@1.9.2': - resolution: {integrity: sha512-EpBGwkcjDicjR/ybC0g8wO5adPNdVuMrNalVgYcWi+gYtC1XYNuxe3rufcO7dA76OHGeVabcO6cSkPJKVcbCXQ==} - engines: {node: '>=14.0.0'} + "@unrs/resolver-binding-wasm32-wasi@1.9.2": + resolution: + { + integrity: sha512-EpBGwkcjDicjR/ybC0g8wO5adPNdVuMrNalVgYcWi+gYtC1XYNuxe3rufcO7dA76OHGeVabcO6cSkPJKVcbCXQ==, + } + engines: { node: ">=14.0.0" } cpu: [wasm32] - '@unrs/resolver-binding-win32-arm64-msvc@1.9.2': - resolution: {integrity: sha512-EdFbGn7o1SxGmN6aZw9wAkehZJetFPao0VGZ9OMBwKx6TkvDuj6cNeLimF/Psi6ts9lMOe+Dt6z19fZQ9Ye2fw==} + "@unrs/resolver-binding-win32-arm64-msvc@1.9.2": + resolution: + { + integrity: sha512-EdFbGn7o1SxGmN6aZw9wAkehZJetFPao0VGZ9OMBwKx6TkvDuj6cNeLimF/Psi6ts9lMOe+Dt6z19fZQ9Ye2fw==, + } cpu: [arm64] os: [win32] - '@unrs/resolver-binding-win32-ia32-msvc@1.9.2': - resolution: {integrity: sha512-JY9hi1p7AG+5c/dMU8o2kWemM8I6VZxfGwn1GCtf3c5i+IKcMo2NQ8OjZ4Z3/itvY/Si3K10jOBQn7qsD/whUA==} + "@unrs/resolver-binding-win32-ia32-msvc@1.9.2": + resolution: + { + integrity: sha512-JY9hi1p7AG+5c/dMU8o2kWemM8I6VZxfGwn1GCtf3c5i+IKcMo2NQ8OjZ4Z3/itvY/Si3K10jOBQn7qsD/whUA==, + } cpu: [ia32] os: [win32] - '@unrs/resolver-binding-win32-x64-msvc@1.9.2': - resolution: {integrity: sha512-ryoo+EB19lMxAd80ln9BVf8pdOAxLb97amrQ3SFN9OCRn/5M5wvwDgAe4i8ZjhpbiHoDeP8yavcTEnpKBo7lZg==} + "@unrs/resolver-binding-win32-x64-msvc@1.9.2": + resolution: + { + integrity: sha512-ryoo+EB19lMxAd80ln9BVf8pdOAxLb97amrQ3SFN9OCRn/5M5wvwDgAe4i8ZjhpbiHoDeP8yavcTEnpKBo7lZg==, + } cpu: [x64] os: [win32] - '@vitejs/plugin-react@4.6.0': - resolution: {integrity: sha512-5Kgff+m8e2PB+9j51eGHEpn5kUzRKH2Ry0qGoe8ItJg7pqnkPrYPkDQZGgGmTa0EGarHrkjLvOdU3b1fzI8otQ==} - engines: {node: ^14.18.0 || >=16.0.0} + "@vitejs/plugin-react@4.6.0": + resolution: + { + integrity: sha512-5Kgff+m8e2PB+9j51eGHEpn5kUzRKH2Ry0qGoe8ItJg7pqnkPrYPkDQZGgGmTa0EGarHrkjLvOdU3b1fzI8otQ==, + } + engines: { node: ^14.18.0 || >=16.0.0 } peerDependencies: vite: ^4.2.0 || ^5.0.0 || ^6.0.0 || ^7.0.0-beta.0 - '@vitest/coverage-v8@3.2.4': - resolution: {integrity: sha512-EyF9SXU6kS5Ku/U82E259WSnvg6c8KTjppUncuNdm5QHpe17mwREHnjDzozC8x9MZ0xfBUFSaLkRv4TMA75ALQ==} + "@vitest/coverage-v8@3.2.4": + resolution: + { + integrity: sha512-EyF9SXU6kS5Ku/U82E259WSnvg6c8KTjppUncuNdm5QHpe17mwREHnjDzozC8x9MZ0xfBUFSaLkRv4TMA75ALQ==, + } peerDependencies: - '@vitest/browser': 3.2.4 + "@vitest/browser": 3.2.4 vitest: 3.2.4 peerDependenciesMeta: - '@vitest/browser': + "@vitest/browser": optional: true - '@vitest/expect@3.2.4': - resolution: {integrity: sha512-Io0yyORnB6sikFlt8QW5K7slY4OjqNX9jmJQ02QDda8lyM6B5oNgVWoSoKPac8/kgnCUzuHQKrSLtu/uOqqrig==} + "@vitest/expect@3.2.4": + resolution: + { + integrity: sha512-Io0yyORnB6sikFlt8QW5K7slY4OjqNX9jmJQ02QDda8lyM6B5oNgVWoSoKPac8/kgnCUzuHQKrSLtu/uOqqrig==, + } - '@vitest/mocker@3.2.4': - resolution: {integrity: sha512-46ryTE9RZO/rfDd7pEqFl7etuyzekzEhUbTW3BvmeO/BcCMEgq59BKhek3dXDWgAj4oMK6OZi+vRr1wPW6qjEQ==} + "@vitest/mocker@3.2.4": + resolution: + { + integrity: sha512-46ryTE9RZO/rfDd7pEqFl7etuyzekzEhUbTW3BvmeO/BcCMEgq59BKhek3dXDWgAj4oMK6OZi+vRr1wPW6qjEQ==, + } peerDependencies: msw: ^2.4.9 vite: ^5.0.0 || ^6.0.0 || ^7.0.0-0 @@ -1795,619 +2716,1099 @@ packages: vite: optional: true - '@vitest/pretty-format@3.2.4': - resolution: {integrity: sha512-IVNZik8IVRJRTr9fxlitMKeJeXFFFN0JaB9PHPGQ8NKQbGpfjlTx9zO4RefN8gp7eqjNy8nyK3NZmBzOPeIxtA==} + "@vitest/pretty-format@3.2.4": + resolution: + { + integrity: sha512-IVNZik8IVRJRTr9fxlitMKeJeXFFFN0JaB9PHPGQ8NKQbGpfjlTx9zO4RefN8gp7eqjNy8nyK3NZmBzOPeIxtA==, + } - '@vitest/runner@3.2.4': - resolution: {integrity: sha512-oukfKT9Mk41LreEW09vt45f8wx7DordoWUZMYdY/cyAk7w5TWkTRCNZYF7sX7n2wB7jyGAl74OxgwhPgKaqDMQ==} + "@vitest/runner@3.2.4": + resolution: + { + integrity: sha512-oukfKT9Mk41LreEW09vt45f8wx7DordoWUZMYdY/cyAk7w5TWkTRCNZYF7sX7n2wB7jyGAl74OxgwhPgKaqDMQ==, + } - '@vitest/snapshot@3.2.4': - resolution: {integrity: sha512-dEYtS7qQP2CjU27QBC5oUOxLE/v5eLkGqPE0ZKEIDGMs4vKWe7IjgLOeauHsR0D5YuuycGRO5oSRXnwnmA78fQ==} + "@vitest/snapshot@3.2.4": + resolution: + { + integrity: sha512-dEYtS7qQP2CjU27QBC5oUOxLE/v5eLkGqPE0ZKEIDGMs4vKWe7IjgLOeauHsR0D5YuuycGRO5oSRXnwnmA78fQ==, + } - '@vitest/spy@3.2.4': - resolution: {integrity: sha512-vAfasCOe6AIK70iP5UD11Ac4siNUNJ9i/9PZ3NKx07sG6sUxeag1LWdNrMWeKKYBLlzuK+Gn65Yd5nyL6ds+nw==} + "@vitest/spy@3.2.4": + resolution: + { + integrity: sha512-vAfasCOe6AIK70iP5UD11Ac4siNUNJ9i/9PZ3NKx07sG6sUxeag1LWdNrMWeKKYBLlzuK+Gn65Yd5nyL6ds+nw==, + } - '@vitest/utils@3.2.4': - resolution: {integrity: sha512-fB2V0JFrQSMsCo9HiSq3Ezpdv4iYaXRG1Sx8edX3MwxfyNn83mKiGzOcH+Fkxt4MHxr3y42fQi1oeAInqgX2QA==} + "@vitest/utils@3.2.4": + resolution: + { + integrity: sha512-fB2V0JFrQSMsCo9HiSq3Ezpdv4iYaXRG1Sx8edX3MwxfyNn83mKiGzOcH+Fkxt4MHxr3y42fQi1oeAInqgX2QA==, + } acorn-jsx@5.3.2: - resolution: {integrity: sha512-rq9s+JNhf0IChjtDXxllJ7g41oZk5SlXtp0LHwyA5cejwn7vKmKp4pPri6YEePv2PU65sAsegbXtIinmDFDXgQ==} + resolution: + { + integrity: sha512-rq9s+JNhf0IChjtDXxllJ7g41oZk5SlXtp0LHwyA5cejwn7vKmKp4pPri6YEePv2PU65sAsegbXtIinmDFDXgQ==, + } peerDependencies: acorn: ^6.0.0 || ^7.0.0 || ^8.0.0 acorn-walk@8.3.4: - resolution: {integrity: sha512-ueEepnujpqee2o5aIYnvHU6C0A42MNdsIDeqy5BydrkuC5R1ZuUFnm27EeFJGoEHJQgn3uleRvmTXaJgfXbt4g==} - engines: {node: '>=0.4.0'} + resolution: + { + integrity: sha512-ueEepnujpqee2o5aIYnvHU6C0A42MNdsIDeqy5BydrkuC5R1ZuUFnm27EeFJGoEHJQgn3uleRvmTXaJgfXbt4g==, + } + engines: { node: ">=0.4.0" } acorn@8.15.0: - resolution: {integrity: sha512-NZyJarBfL7nWwIq+FDL6Zp/yHEhePMNnnJ0y3qfieCrmNvYct8uvtiV41UvlSe6apAfk0fY1FbWx+NwfmpvtTg==} - engines: {node: '>=0.4.0'} + resolution: + { + integrity: sha512-NZyJarBfL7nWwIq+FDL6Zp/yHEhePMNnnJ0y3qfieCrmNvYct8uvtiV41UvlSe6apAfk0fY1FbWx+NwfmpvtTg==, + } + engines: { node: ">=0.4.0" } hasBin: true agent-base@7.1.3: - resolution: {integrity: sha512-jRR5wdylq8CkOe6hei19GGZnxM6rBGwFl3Bg0YItGDimvjGtAvdZk4Pu6Cl4u4Igsws4a1fd1Vq3ezrhn4KmFw==} - engines: {node: '>= 14'} + resolution: + { + integrity: sha512-jRR5wdylq8CkOe6hei19GGZnxM6rBGwFl3Bg0YItGDimvjGtAvdZk4Pu6Cl4u4Igsws4a1fd1Vq3ezrhn4KmFw==, + } + engines: { node: ">= 14" } ajv@6.12.6: - resolution: {integrity: sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==} + resolution: + { + integrity: sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==, + } ansi-regex@5.0.1: - resolution: {integrity: sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ==} - engines: {node: '>=8'} + resolution: + { + integrity: sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ==, + } + engines: { node: ">=8" } ansi-regex@6.1.0: - resolution: {integrity: sha512-7HSX4QQb4CspciLpVFwyRe79O3xsIZDDLER21kERQ71oaPodF8jL725AgJMFAYbooIqolJoRLuM81SpeUkpkvA==} - engines: {node: '>=12'} + resolution: + { + integrity: sha512-7HSX4QQb4CspciLpVFwyRe79O3xsIZDDLER21kERQ71oaPodF8jL725AgJMFAYbooIqolJoRLuM81SpeUkpkvA==, + } + engines: { node: ">=12" } ansi-styles@4.3.0: - resolution: {integrity: sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==} - engines: {node: '>=8'} + resolution: + { + integrity: sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==, + } + engines: { node: ">=8" } ansi-styles@5.2.0: - resolution: {integrity: sha512-Cxwpt2SfTzTtXcfOlzGEee8O+c+MmUgGrNiBcXnuWxuFJHe6a5Hz7qwhwe5OgaSYI0IJvkLqWX1ASG+cJOkEiA==} - engines: {node: '>=10'} + resolution: + { + integrity: sha512-Cxwpt2SfTzTtXcfOlzGEee8O+c+MmUgGrNiBcXnuWxuFJHe6a5Hz7qwhwe5OgaSYI0IJvkLqWX1ASG+cJOkEiA==, + } + engines: { node: ">=10" } ansi-styles@6.2.1: - resolution: {integrity: sha512-bN798gFfQX+viw3R7yrGWRqnrN2oRkEkUjjl4JNn4E8GxxbjtG3FbrEIIY3l8/hrwUwIeCZvi4QuOTP4MErVug==} - engines: {node: '>=12'} + resolution: + { + integrity: sha512-bN798gFfQX+viw3R7yrGWRqnrN2oRkEkUjjl4JNn4E8GxxbjtG3FbrEIIY3l8/hrwUwIeCZvi4QuOTP4MErVug==, + } + engines: { node: ">=12" } arg@4.1.3: - resolution: {integrity: sha512-58S9QDqG0Xx27YwPSt9fJxivjYl432YCwfDMfZ+71RAqUrZef7LrKQZ3LHLOwCS4FLNBplP533Zx895SeOCHvA==} + resolution: + { + integrity: sha512-58S9QDqG0Xx27YwPSt9fJxivjYl432YCwfDMfZ+71RAqUrZef7LrKQZ3LHLOwCS4FLNBplP533Zx895SeOCHvA==, + } argparse@2.0.1: - resolution: {integrity: sha512-8+9WqebbFzpX9OR+Wa6O29asIogeRMzcGtAINdpMHHyAg10f05aSFVBbcEqGf/PXw1EjAZ+q2/bEBg3DvurK3Q==} + resolution: + { + integrity: sha512-8+9WqebbFzpX9OR+Wa6O29asIogeRMzcGtAINdpMHHyAg10f05aSFVBbcEqGf/PXw1EjAZ+q2/bEBg3DvurK3Q==, + } aria-hidden@1.2.6: - resolution: {integrity: sha512-ik3ZgC9dY/lYVVM++OISsaYDeg1tb0VtP5uL3ouh1koGOaUMDPpbFIei4JkFimWUFPn90sbMNMXQAIVOlnYKJA==} - engines: {node: '>=10'} + resolution: + { + integrity: sha512-ik3ZgC9dY/lYVVM++OISsaYDeg1tb0VtP5uL3ouh1koGOaUMDPpbFIei4JkFimWUFPn90sbMNMXQAIVOlnYKJA==, + } + engines: { node: ">=10" } aria-query@5.3.0: - resolution: {integrity: sha512-b0P0sZPKtyu8HkeRAfCq0IfURZK+SuwMjY1UXGBU27wpAiTwQAIlq56IbIO+ytk/JjS1fMR14ee5WBBfKi5J6A==} + resolution: + { + integrity: sha512-b0P0sZPKtyu8HkeRAfCq0IfURZK+SuwMjY1UXGBU27wpAiTwQAIlq56IbIO+ytk/JjS1fMR14ee5WBBfKi5J6A==, + } aria-query@5.3.2: - resolution: {integrity: sha512-COROpnaoap1E2F000S62r6A60uHZnmlvomhfyT2DlTcrY1OrBKn2UhH7qn5wTC9zMvD0AY7csdPSNwKP+7WiQw==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-COROpnaoap1E2F000S62r6A60uHZnmlvomhfyT2DlTcrY1OrBKn2UhH7qn5wTC9zMvD0AY7csdPSNwKP+7WiQw==, + } + engines: { node: ">= 0.4" } array-buffer-byte-length@1.0.2: - resolution: {integrity: sha512-LHE+8BuR7RYGDKvnrmcuSq3tDcKv9OFEXQt/HpbZhY7V6h0zlUXutnAD82GiFx9rdieCMjkvtcsPqBwgUl1Iiw==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-LHE+8BuR7RYGDKvnrmcuSq3tDcKv9OFEXQt/HpbZhY7V6h0zlUXutnAD82GiFx9rdieCMjkvtcsPqBwgUl1Iiw==, + } + engines: { node: ">= 0.4" } array-includes@3.1.9: - resolution: {integrity: sha512-FmeCCAenzH0KH381SPT5FZmiA/TmpndpcaShhfgEN9eCVjnFBqq3l1xrI42y8+PPLI6hypzou4GXw00WHmPBLQ==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-FmeCCAenzH0KH381SPT5FZmiA/TmpndpcaShhfgEN9eCVjnFBqq3l1xrI42y8+PPLI6hypzou4GXw00WHmPBLQ==, + } + engines: { node: ">= 0.4" } array.prototype.findlast@1.2.5: - resolution: {integrity: sha512-CVvd6FHg1Z3POpBLxO6E6zr+rSKEQ9L6rZHAaY7lLfhKsWYUBBOuMs0e9o24oopj6H+geRCX0YJ+TJLBK2eHyQ==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-CVvd6FHg1Z3POpBLxO6E6zr+rSKEQ9L6rZHAaY7lLfhKsWYUBBOuMs0e9o24oopj6H+geRCX0YJ+TJLBK2eHyQ==, + } + engines: { node: ">= 0.4" } array.prototype.findlastindex@1.2.6: - resolution: {integrity: sha512-F/TKATkzseUExPlfvmwQKGITM3DGTK+vkAsCZoDc5daVygbJBnjEUCbgkAvVFsgfXfX4YIqZ/27G3k3tdXrTxQ==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-F/TKATkzseUExPlfvmwQKGITM3DGTK+vkAsCZoDc5daVygbJBnjEUCbgkAvVFsgfXfX4YIqZ/27G3k3tdXrTxQ==, + } + engines: { node: ">= 0.4" } array.prototype.flat@1.3.3: - resolution: {integrity: sha512-rwG/ja1neyLqCuGZ5YYrznA62D4mZXg0i1cIskIUKSiqF3Cje9/wXAls9B9s1Wa2fomMsIv8czB8jZcPmxCXFg==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-rwG/ja1neyLqCuGZ5YYrznA62D4mZXg0i1cIskIUKSiqF3Cje9/wXAls9B9s1Wa2fomMsIv8czB8jZcPmxCXFg==, + } + engines: { node: ">= 0.4" } array.prototype.flatmap@1.3.3: - resolution: {integrity: sha512-Y7Wt51eKJSyi80hFrJCePGGNo5ktJCslFuboqJsbf57CCPcm5zztluPlc4/aD8sWsKvlwatezpV4U1efk8kpjg==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-Y7Wt51eKJSyi80hFrJCePGGNo5ktJCslFuboqJsbf57CCPcm5zztluPlc4/aD8sWsKvlwatezpV4U1efk8kpjg==, + } + engines: { node: ">= 0.4" } array.prototype.tosorted@1.1.4: - resolution: {integrity: sha512-p6Fx8B7b7ZhL/gmUsAy0D15WhvDccw3mnGNbZpi3pmeJdxtWsj2jEaI4Y6oo3XiHfzuSgPwKc04MYt6KgvC/wA==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-p6Fx8B7b7ZhL/gmUsAy0D15WhvDccw3mnGNbZpi3pmeJdxtWsj2jEaI4Y6oo3XiHfzuSgPwKc04MYt6KgvC/wA==, + } + engines: { node: ">= 0.4" } arraybuffer.prototype.slice@1.0.4: - resolution: {integrity: sha512-BNoCY6SXXPQ7gF2opIP4GBE+Xw7U+pHMYKuzjgCN3GwiaIR09UUeKfheyIry77QtrCBlC0KK0q5/TER/tYh3PQ==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-BNoCY6SXXPQ7gF2opIP4GBE+Xw7U+pHMYKuzjgCN3GwiaIR09UUeKfheyIry77QtrCBlC0KK0q5/TER/tYh3PQ==, + } + engines: { node: ">= 0.4" } assertion-error@2.0.1: - resolution: {integrity: sha512-Izi8RQcffqCeNVgFigKli1ssklIbpHnCYc6AknXGYoB6grJqyeby7jv12JUQgmTAnIDnbck1uxksT4dzN3PWBA==} - engines: {node: '>=12'} + resolution: + { + integrity: sha512-Izi8RQcffqCeNVgFigKli1ssklIbpHnCYc6AknXGYoB6grJqyeby7jv12JUQgmTAnIDnbck1uxksT4dzN3PWBA==, + } + engines: { node: ">=12" } ast-types-flow@0.0.8: - resolution: {integrity: sha512-OH/2E5Fg20h2aPrbe+QL8JZQFko0YZaF+j4mnQ7BGhfavO7OpSLa8a0y9sBwomHdSbkhTS8TQNayBfnW5DwbvQ==} + resolution: + { + integrity: sha512-OH/2E5Fg20h2aPrbe+QL8JZQFko0YZaF+j4mnQ7BGhfavO7OpSLa8a0y9sBwomHdSbkhTS8TQNayBfnW5DwbvQ==, + } ast-v8-to-istanbul@0.3.3: - resolution: {integrity: sha512-MuXMrSLVVoA6sYN/6Hke18vMzrT4TZNbZIj/hvh0fnYFpO+/kFXcLIaiPwXXWaQUPg4yJD8fj+lfJ7/1EBconw==} + resolution: + { + integrity: sha512-MuXMrSLVVoA6sYN/6Hke18vMzrT4TZNbZIj/hvh0fnYFpO+/kFXcLIaiPwXXWaQUPg4yJD8fj+lfJ7/1EBconw==, + } async-function@1.0.0: - resolution: {integrity: sha512-hsU18Ae8CDTR6Kgu9DYf0EbCr/a5iGL0rytQDobUcdpYOKokk8LEjVphnXkDkgpi0wYVsqrXuP0bZxJaTqdgoA==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-hsU18Ae8CDTR6Kgu9DYf0EbCr/a5iGL0rytQDobUcdpYOKokk8LEjVphnXkDkgpi0wYVsqrXuP0bZxJaTqdgoA==, + } + engines: { node: ">= 0.4" } asynckit@0.4.0: - resolution: {integrity: sha512-Oei9OH4tRh0YqU3GxhX79dM/mwVgvbZJaSNaRk+bshkj0S5cfHcgYakreBjrHwatXKbz+IoIdYLxrKim2MjW0Q==} + resolution: + { + integrity: sha512-Oei9OH4tRh0YqU3GxhX79dM/mwVgvbZJaSNaRk+bshkj0S5cfHcgYakreBjrHwatXKbz+IoIdYLxrKim2MjW0Q==, + } available-typed-arrays@1.0.7: - resolution: {integrity: sha512-wvUjBtSGN7+7SjNpq/9M2Tg350UZD3q62IFZLbRAR1bSMlCo1ZaeW+BJ+D090e4hIIZLBcTDWe4Mh4jvUDajzQ==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-wvUjBtSGN7+7SjNpq/9M2Tg350UZD3q62IFZLbRAR1bSMlCo1ZaeW+BJ+D090e4hIIZLBcTDWe4Mh4jvUDajzQ==, + } + engines: { node: ">= 0.4" } axe-core@4.10.3: - resolution: {integrity: sha512-Xm7bpRXnDSX2YE2YFfBk2FnF0ep6tmG7xPh8iHee8MIcrgq762Nkce856dYtJYLkuIoYZvGfTs/PbZhideTcEg==} - engines: {node: '>=4'} + resolution: + { + integrity: sha512-Xm7bpRXnDSX2YE2YFfBk2FnF0ep6tmG7xPh8iHee8MIcrgq762Nkce856dYtJYLkuIoYZvGfTs/PbZhideTcEg==, + } + engines: { node: ">=4" } axobject-query@4.1.0: - resolution: {integrity: sha512-qIj0G9wZbMGNLjLmg1PT6v2mE9AH2zlnADJD/2tC6E00hgmhUOfEB6greHPAfLRSufHqROIUTkw6E+M3lH0PTQ==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-qIj0G9wZbMGNLjLmg1PT6v2mE9AH2zlnADJD/2tC6E00hgmhUOfEB6greHPAfLRSufHqROIUTkw6E+M3lH0PTQ==, + } + engines: { node: ">= 0.4" } bail@2.0.2: - resolution: {integrity: sha512-0xO6mYd7JB2YesxDKplafRpsiOzPt9V02ddPCLbY1xYGPOX24NTyN50qnUxgCPcSoYMhKpAuBTjQoRZCAkUDRw==} + resolution: + { + integrity: sha512-0xO6mYd7JB2YesxDKplafRpsiOzPt9V02ddPCLbY1xYGPOX24NTyN50qnUxgCPcSoYMhKpAuBTjQoRZCAkUDRw==, + } balanced-match@1.0.2: - resolution: {integrity: sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw==} + resolution: + { + integrity: sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw==, + } bcryptjs@3.0.2: - resolution: {integrity: sha512-k38b3XOZKv60C4E2hVsXTolJWfkGRMbILBIe2IBITXciy5bOsTKot5kDrf3ZfufQtQOUN5mXceUEpU1rTl9Uog==} + resolution: + { + integrity: sha512-k38b3XOZKv60C4E2hVsXTolJWfkGRMbILBIe2IBITXciy5bOsTKot5kDrf3ZfufQtQOUN5mXceUEpU1rTl9Uog==, + } hasBin: true brace-expansion@1.1.12: - resolution: {integrity: sha512-9T9UjW3r0UW5c1Q7GTwllptXwhvYmEzFhzMfZ9H7FQWt+uZePjZPjBP/W1ZEyZ1twGWom5/56TF4lPcqjnDHcg==} + resolution: + { + integrity: sha512-9T9UjW3r0UW5c1Q7GTwllptXwhvYmEzFhzMfZ9H7FQWt+uZePjZPjBP/W1ZEyZ1twGWom5/56TF4lPcqjnDHcg==, + } brace-expansion@2.0.2: - resolution: {integrity: sha512-Jt0vHyM+jmUBqojB7E1NIYadt0vI0Qxjxd2TErW94wDz+E2LAm5vKMXXwg6ZZBTHPuUlDgQHKXvjGBdfcF1ZDQ==} + resolution: + { + integrity: sha512-Jt0vHyM+jmUBqojB7E1NIYadt0vI0Qxjxd2TErW94wDz+E2LAm5vKMXXwg6ZZBTHPuUlDgQHKXvjGBdfcF1ZDQ==, + } braces@3.0.3: - resolution: {integrity: sha512-yQbXgO/OSZVD2IsiLlro+7Hf6Q18EJrKSEsdoMzKePKXct3gvD8oLcOQdIzGupr5Fj+EDe8gO/lxc1BzfMpxvA==} - engines: {node: '>=8'} + resolution: + { + integrity: sha512-yQbXgO/OSZVD2IsiLlro+7Hf6Q18EJrKSEsdoMzKePKXct3gvD8oLcOQdIzGupr5Fj+EDe8gO/lxc1BzfMpxvA==, + } + engines: { node: ">=8" } browserslist@4.25.1: - resolution: {integrity: sha512-KGj0KoOMXLpSNkkEI6Z6mShmQy0bc1I+T7K9N81k4WWMrfz+6fQ6es80B/YLAeRoKvjYE1YSHHOW1qe9xIVzHw==} - engines: {node: ^6 || ^7 || ^8 || ^9 || ^10 || ^11 || ^12 || >=13.7} + resolution: + { + integrity: sha512-KGj0KoOMXLpSNkkEI6Z6mShmQy0bc1I+T7K9N81k4WWMrfz+6fQ6es80B/YLAeRoKvjYE1YSHHOW1qe9xIVzHw==, + } + engines: { node: ^6 || ^7 || ^8 || ^9 || ^10 || ^11 || ^12 || >=13.7 } hasBin: true busboy@1.6.0: - resolution: {integrity: sha512-8SFQbg/0hQ9xy3UNTB0YEnsNBbWfhf7RtnzpL7TkBiTBRfrQ9Fxcnz7VJsleJpyp6rVLvXiuORqjlHi5q+PYuA==} - engines: {node: '>=10.16.0'} + resolution: + { + integrity: sha512-8SFQbg/0hQ9xy3UNTB0YEnsNBbWfhf7RtnzpL7TkBiTBRfrQ9Fxcnz7VJsleJpyp6rVLvXiuORqjlHi5q+PYuA==, + } + engines: { node: ">=10.16.0" } cac@6.7.14: - resolution: {integrity: sha512-b6Ilus+c3RrdDk+JhLKUAQfzzgLEPy6wcXqS7f/xe1EETvsDP6GORG7SFuOs6cID5YkqchW/LXZbX5bc8j7ZcQ==} - engines: {node: '>=8'} + resolution: + { + integrity: sha512-b6Ilus+c3RrdDk+JhLKUAQfzzgLEPy6wcXqS7f/xe1EETvsDP6GORG7SFuOs6cID5YkqchW/LXZbX5bc8j7ZcQ==, + } + engines: { node: ">=8" } call-bind-apply-helpers@1.0.2: - resolution: {integrity: sha512-Sp1ablJ0ivDkSzjcaJdxEunN5/XvksFJ2sMBFfq6x0ryhQV/2b/KwFe21cMpmHtPOSij8K99/wSfoEuTObmuMQ==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-Sp1ablJ0ivDkSzjcaJdxEunN5/XvksFJ2sMBFfq6x0ryhQV/2b/KwFe21cMpmHtPOSij8K99/wSfoEuTObmuMQ==, + } + engines: { node: ">= 0.4" } call-bind@1.0.8: - resolution: {integrity: sha512-oKlSFMcMwpUg2ednkhQ454wfWiU/ul3CkJe/PEHcTKuiX6RpbehUiFMXu13HalGZxfUwCQzZG747YXBn1im9ww==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-oKlSFMcMwpUg2ednkhQ454wfWiU/ul3CkJe/PEHcTKuiX6RpbehUiFMXu13HalGZxfUwCQzZG747YXBn1im9ww==, + } + engines: { node: ">= 0.4" } call-bound@1.0.4: - resolution: {integrity: sha512-+ys997U96po4Kx/ABpBCqhA9EuxJaQWDQg7295H4hBphv3IZg0boBKuwYpt4YXp6MZ5AmZQnU/tyMTlRpaSejg==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-+ys997U96po4Kx/ABpBCqhA9EuxJaQWDQg7295H4hBphv3IZg0boBKuwYpt4YXp6MZ5AmZQnU/tyMTlRpaSejg==, + } + engines: { node: ">= 0.4" } callsites@3.1.0: - resolution: {integrity: sha512-P8BjAsXvZS+VIDUI11hHCQEv74YT67YUi5JJFNWIqL235sBmjX4+qx9Muvls5ivyNENctx46xQLQ3aTuE7ssaQ==} - engines: {node: '>=6'} + resolution: + { + integrity: sha512-P8BjAsXvZS+VIDUI11hHCQEv74YT67YUi5JJFNWIqL235sBmjX4+qx9Muvls5ivyNENctx46xQLQ3aTuE7ssaQ==, + } + engines: { node: ">=6" } caniuse-lite@1.0.30001726: - resolution: {integrity: sha512-VQAUIUzBiZ/UnlM28fSp2CRF3ivUn1BWEvxMcVTNwpw91Py1pGbPIyIKtd+tzct9C3ouceCVdGAXxZOpZAsgdw==} + resolution: + { + integrity: sha512-VQAUIUzBiZ/UnlM28fSp2CRF3ivUn1BWEvxMcVTNwpw91Py1pGbPIyIKtd+tzct9C3ouceCVdGAXxZOpZAsgdw==, + } ccount@2.0.1: - resolution: {integrity: sha512-eyrF0jiFpY+3drT6383f1qhkbGsLSifNAjA61IUjZjmLCWjItY6LB9ft9YhoDgwfmclB2zhu51Lc7+95b8NRAg==} + resolution: + { + integrity: sha512-eyrF0jiFpY+3drT6383f1qhkbGsLSifNAjA61IUjZjmLCWjItY6LB9ft9YhoDgwfmclB2zhu51Lc7+95b8NRAg==, + } chai@5.2.0: - resolution: {integrity: sha512-mCuXncKXk5iCLhfhwTc0izo0gtEmpz5CtG2y8GiOINBlMVS6v8TMRc5TaLWKS6692m9+dVVfzgeVxR5UxWHTYw==} - engines: {node: '>=12'} + resolution: + { + integrity: sha512-mCuXncKXk5iCLhfhwTc0izo0gtEmpz5CtG2y8GiOINBlMVS6v8TMRc5TaLWKS6692m9+dVVfzgeVxR5UxWHTYw==, + } + engines: { node: ">=12" } chalk@4.1.2: - resolution: {integrity: sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==} - engines: {node: '>=10'} + resolution: + { + integrity: sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==, + } + engines: { node: ">=10" } character-entities-html4@2.1.0: - resolution: {integrity: sha512-1v7fgQRj6hnSwFpq1Eu0ynr/CDEw0rXo2B61qXrLNdHZmPKgb7fqS1a2JwF0rISo9q77jDI8VMEHoApn8qDoZA==} + resolution: + { + integrity: sha512-1v7fgQRj6hnSwFpq1Eu0ynr/CDEw0rXo2B61qXrLNdHZmPKgb7fqS1a2JwF0rISo9q77jDI8VMEHoApn8qDoZA==, + } character-entities-legacy@3.0.0: - resolution: {integrity: sha512-RpPp0asT/6ufRm//AJVwpViZbGM/MkjQFxJccQRHmISF/22NBtsHqAWmL+/pmkPWoIUJdWyeVleTl1wydHATVQ==} + resolution: + { + integrity: sha512-RpPp0asT/6ufRm//AJVwpViZbGM/MkjQFxJccQRHmISF/22NBtsHqAWmL+/pmkPWoIUJdWyeVleTl1wydHATVQ==, + } character-entities@2.0.2: - resolution: {integrity: sha512-shx7oQ0Awen/BRIdkjkvz54PnEEI/EjwXDSIZp86/KKdbafHh1Df/RYGBhn4hbe2+uKC9FnT5UCEdyPz3ai9hQ==} + resolution: + { + integrity: sha512-shx7oQ0Awen/BRIdkjkvz54PnEEI/EjwXDSIZp86/KKdbafHh1Df/RYGBhn4hbe2+uKC9FnT5UCEdyPz3ai9hQ==, + } character-reference-invalid@2.0.1: - resolution: {integrity: sha512-iBZ4F4wRbyORVsu0jPV7gXkOsGYjGHPmAyv+HiHG8gi5PtC9KI2j1+v8/tlibRvjoWX027ypmG/n0HtO5t7unw==} + resolution: + { + integrity: sha512-iBZ4F4wRbyORVsu0jPV7gXkOsGYjGHPmAyv+HiHG8gi5PtC9KI2j1+v8/tlibRvjoWX027ypmG/n0HtO5t7unw==, + } check-error@2.1.1: - resolution: {integrity: sha512-OAlb+T7V4Op9OwdkjmguYRqncdlx5JiofwOAUkmTF+jNdHwzTaTs4sRAGpzLF3oOz5xAyDGrPgeIDFQmDOTiJw==} - engines: {node: '>= 16'} + resolution: + { + integrity: sha512-OAlb+T7V4Op9OwdkjmguYRqncdlx5JiofwOAUkmTF+jNdHwzTaTs4sRAGpzLF3oOz5xAyDGrPgeIDFQmDOTiJw==, + } + engines: { node: ">= 16" } chownr@3.0.0: - resolution: {integrity: sha512-+IxzY9BZOQd/XuYPRmrvEVjF/nqj5kgT4kEq7VofrDoM1MxoRjEWkrCC3EtLi59TVawxTAn+orJwFQcrqEN1+g==} - engines: {node: '>=18'} + resolution: + { + integrity: sha512-+IxzY9BZOQd/XuYPRmrvEVjF/nqj5kgT4kEq7VofrDoM1MxoRjEWkrCC3EtLi59TVawxTAn+orJwFQcrqEN1+g==, + } + engines: { node: ">=18" } class-variance-authority@0.7.1: - resolution: {integrity: sha512-Ka+9Trutv7G8M6WT6SeiRWz792K5qEqIGEGzXKhAE6xOWAY6pPH8U+9IY3oCMv6kqTmLsv7Xh/2w2RigkePMsg==} + resolution: + { + integrity: sha512-Ka+9Trutv7G8M6WT6SeiRWz792K5qEqIGEGzXKhAE6xOWAY6pPH8U+9IY3oCMv6kqTmLsv7Xh/2w2RigkePMsg==, + } client-only@0.0.1: - resolution: {integrity: sha512-IV3Ou0jSMzZrd3pZ48nLkT9DA7Ag1pnPzaiQhpW7c3RbcqqzvzzVu+L8gfqMp/8IM2MQtSiqaCxrrcfu8I8rMA==} + resolution: + { + integrity: sha512-IV3Ou0jSMzZrd3pZ48nLkT9DA7Ag1pnPzaiQhpW7c3RbcqqzvzzVu+L8gfqMp/8IM2MQtSiqaCxrrcfu8I8rMA==, + } clsx@2.1.1: - resolution: {integrity: sha512-eYm0QWBtUrBWZWG0d386OGAw16Z995PiOVo2B7bjWSbHedGl5e0ZWaq65kOGgUSNesEIDkB9ISbTg/JK9dhCZA==} - engines: {node: '>=6'} + resolution: + { + integrity: sha512-eYm0QWBtUrBWZWG0d386OGAw16Z995PiOVo2B7bjWSbHedGl5e0ZWaq65kOGgUSNesEIDkB9ISbTg/JK9dhCZA==, + } + engines: { node: ">=6" } color-convert@2.0.1: - resolution: {integrity: sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==} - engines: {node: '>=7.0.0'} + resolution: + { + integrity: sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==, + } + engines: { node: ">=7.0.0" } color-name@1.1.4: - resolution: {integrity: sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==} + resolution: + { + integrity: sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==, + } color-string@1.9.1: - resolution: {integrity: sha512-shrVawQFojnZv6xM40anx4CkoDP+fZsw/ZerEMsW/pyzsRbElpsL/DBVW7q3ExxwusdNXI3lXpuhEZkzs8p5Eg==} + resolution: + { + integrity: sha512-shrVawQFojnZv6xM40anx4CkoDP+fZsw/ZerEMsW/pyzsRbElpsL/DBVW7q3ExxwusdNXI3lXpuhEZkzs8p5Eg==, + } color@4.2.3: - resolution: {integrity: sha512-1rXeuUUiGGrykh+CeBdu5Ie7OJwinCgQY0bc7GCRxy5xVHy+moaqkpL/jqQq0MtQOeYcrqEz4abc5f0KtU7W4A==} - engines: {node: '>=12.5.0'} + resolution: + { + integrity: sha512-1rXeuUUiGGrykh+CeBdu5Ie7OJwinCgQY0bc7GCRxy5xVHy+moaqkpL/jqQq0MtQOeYcrqEz4abc5f0KtU7W4A==, + } + engines: { node: ">=12.5.0" } combined-stream@1.0.8: - resolution: {integrity: sha512-FQN4MRfuJeHf7cBbBMJFXhKSDq+2kAArBlmRBvcvFE5BB1HZKXtSFASDhdlz9zOYwxh8lDdnvmMOe/+5cdoEdg==} - engines: {node: '>= 0.8'} + resolution: + { + integrity: sha512-FQN4MRfuJeHf7cBbBMJFXhKSDq+2kAArBlmRBvcvFE5BB1HZKXtSFASDhdlz9zOYwxh8lDdnvmMOe/+5cdoEdg==, + } + engines: { node: ">= 0.8" } comma-separated-tokens@2.0.3: - resolution: {integrity: sha512-Fu4hJdvzeylCfQPp9SGWidpzrMs7tTrlu6Vb8XGaRGck8QSNZJJp538Wrb60Lax4fPwR64ViY468OIUTbRlGZg==} + resolution: + { + integrity: sha512-Fu4hJdvzeylCfQPp9SGWidpzrMs7tTrlu6Vb8XGaRGck8QSNZJJp538Wrb60Lax4fPwR64ViY468OIUTbRlGZg==, + } commander@7.2.0: - resolution: {integrity: sha512-QrWXB+ZQSVPmIWIhtEO9H+gwHaMGYiF5ChvoJ+K9ZGHG/sVsa6yiesAD1GC/x46sET00Xlwo1u49RVVVzvcSkw==} - engines: {node: '>= 10'} + resolution: + { + integrity: sha512-QrWXB+ZQSVPmIWIhtEO9H+gwHaMGYiF5ChvoJ+K9ZGHG/sVsa6yiesAD1GC/x46sET00Xlwo1u49RVVVzvcSkw==, + } + engines: { node: ">= 10" } commander@8.3.0: - resolution: {integrity: sha512-OkTL9umf+He2DZkUq8f8J9of7yL6RJKI24dVITBmNfZBmri9zYZQrKkuXiKhyfPSu8tUhnVBB1iKXevvnlR4Ww==} - engines: {node: '>= 12'} + resolution: + { + integrity: sha512-OkTL9umf+He2DZkUq8f8J9of7yL6RJKI24dVITBmNfZBmri9zYZQrKkuXiKhyfPSu8tUhnVBB1iKXevvnlR4Ww==, + } + engines: { node: ">= 12" } concat-map@0.0.1: - resolution: {integrity: sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg==} + resolution: + { + integrity: sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg==, + } convert-source-map@2.0.0: - resolution: {integrity: sha512-Kvp459HrV2FEJ1CAsi1Ku+MY3kasH19TFykTz2xWmMeq6bk2NU3XXvfJ+Q61m0xktWwt+1HSYf3JZsTms3aRJg==} + resolution: + { + integrity: sha512-Kvp459HrV2FEJ1CAsi1Ku+MY3kasH19TFykTz2xWmMeq6bk2NU3XXvfJ+Q61m0xktWwt+1HSYf3JZsTms3aRJg==, + } cookie@0.7.2: - resolution: {integrity: sha512-yki5XnKuf750l50uGTllt6kKILY4nQ1eNIQatoXEByZ5dWgnKqbnqmTrBE5B4N7lrMJKQ2ytWMiTO2o0v6Ew/w==} - engines: {node: '>= 0.6'} + resolution: + { + integrity: sha512-yki5XnKuf750l50uGTllt6kKILY4nQ1eNIQatoXEByZ5dWgnKqbnqmTrBE5B4N7lrMJKQ2ytWMiTO2o0v6Ew/w==, + } + engines: { node: ">= 0.6" } create-require@1.1.1: - resolution: {integrity: sha512-dcKFX3jn0MpIaXjisoRvexIJVEKzaq7z2rZKxf+MSr9TkdmHmsU4m2lcLojrj/FHl8mk5VxMmYA+ftRkP/3oKQ==} + resolution: + { + integrity: sha512-dcKFX3jn0MpIaXjisoRvexIJVEKzaq7z2rZKxf+MSr9TkdmHmsU4m2lcLojrj/FHl8mk5VxMmYA+ftRkP/3oKQ==, + } cross-spawn@7.0.6: - resolution: {integrity: sha512-uV2QOWP2nWzsy2aMp8aRibhi9dlzF5Hgh5SHaB9OiTGEyDTiJJyx0uy51QXdyWbtAHNua4XJzUKca3OzKUd3vA==} - engines: {node: '>= 8'} + resolution: + { + integrity: sha512-uV2QOWP2nWzsy2aMp8aRibhi9dlzF5Hgh5SHaB9OiTGEyDTiJJyx0uy51QXdyWbtAHNua4XJzUKca3OzKUd3vA==, + } + engines: { node: ">= 8" } cssstyle@4.6.0: - resolution: {integrity: sha512-2z+rWdzbbSZv6/rhtvzvqeZQHrBaqgogqt85sqFNbabZOuFbCVFb8kPeEtZjiKkbrm395irpNKiYeFeLiQnFPg==} - engines: {node: '>=18'} + resolution: + { + integrity: sha512-2z+rWdzbbSZv6/rhtvzvqeZQHrBaqgogqt85sqFNbabZOuFbCVFb8kPeEtZjiKkbrm395irpNKiYeFeLiQnFPg==, + } + engines: { node: ">=18" } csstype@3.1.3: - resolution: {integrity: sha512-M1uQkMl8rQK/szD0LNhtqxIPLpimGm8sOBwU7lLnCpSbTyY3yeU1Vc7l4KT5zT4s/yOxHH5O7tIuuLOCnLADRw==} + resolution: + { + integrity: sha512-M1uQkMl8rQK/szD0LNhtqxIPLpimGm8sOBwU7lLnCpSbTyY3yeU1Vc7l4KT5zT4s/yOxHH5O7tIuuLOCnLADRw==, + } csv-parse@5.6.0: - resolution: {integrity: sha512-l3nz3euub2QMg5ouu5U09Ew9Wf6/wQ8I++ch1loQ0ljmzhmfZYrH9fflS22i/PQEvsPvxCwxgz5q7UB8K1JO4Q==} + resolution: + { + integrity: sha512-l3nz3euub2QMg5ouu5U09Ew9Wf6/wQ8I++ch1loQ0ljmzhmfZYrH9fflS22i/PQEvsPvxCwxgz5q7UB8K1JO4Q==, + } d3-array@3.2.4: - resolution: {integrity: sha512-tdQAmyA18i4J7wprpYq8ClcxZy3SC31QMeByyCFyRt7BVHdREQZ5lpzoe5mFEYZUWe+oq8HBvk9JjpibyEV4Jg==} - engines: {node: '>=12'} + resolution: + { + integrity: sha512-tdQAmyA18i4J7wprpYq8ClcxZy3SC31QMeByyCFyRt7BVHdREQZ5lpzoe5mFEYZUWe+oq8HBvk9JjpibyEV4Jg==, + } + engines: { node: ">=12" } d3-axis@3.0.0: - resolution: {integrity: sha512-IH5tgjV4jE/GhHkRV0HiVYPDtvfjHQlQfJHs0usq7M30XcSBvOotpmH1IgkcXsO/5gEQZD43B//fc7SRT5S+xw==} - engines: {node: '>=12'} + resolution: + { + integrity: sha512-IH5tgjV4jE/GhHkRV0HiVYPDtvfjHQlQfJHs0usq7M30XcSBvOotpmH1IgkcXsO/5gEQZD43B//fc7SRT5S+xw==, + } + engines: { node: ">=12" } d3-brush@3.0.0: - resolution: {integrity: sha512-ALnjWlVYkXsVIGlOsuWH1+3udkYFI48Ljihfnh8FZPF2QS9o+PzGLBslO0PjzVoHLZ2KCVgAM8NVkXPJB2aNnQ==} - engines: {node: '>=12'} + resolution: + { + integrity: sha512-ALnjWlVYkXsVIGlOsuWH1+3udkYFI48Ljihfnh8FZPF2QS9o+PzGLBslO0PjzVoHLZ2KCVgAM8NVkXPJB2aNnQ==, + } + engines: { node: ">=12" } d3-chord@3.0.1: - resolution: {integrity: sha512-VE5S6TNa+j8msksl7HwjxMHDM2yNK3XCkusIlpX5kwauBfXuyLAtNg9jCp/iHH61tgI4sb6R/EIMWCqEIdjT/g==} - engines: {node: '>=12'} + resolution: + { + integrity: sha512-VE5S6TNa+j8msksl7HwjxMHDM2yNK3XCkusIlpX5kwauBfXuyLAtNg9jCp/iHH61tgI4sb6R/EIMWCqEIdjT/g==, + } + engines: { node: ">=12" } d3-cloud@1.2.7: - resolution: {integrity: sha512-8TrgcgwRIpoZYQp7s3fGB7tATWfhckRb8KcVd1bOgqkNdkJRDGWfdSf4HkHHzZxSczwQJdSxvfPudwir5IAJ3w==} + resolution: + { + integrity: sha512-8TrgcgwRIpoZYQp7s3fGB7tATWfhckRb8KcVd1bOgqkNdkJRDGWfdSf4HkHHzZxSczwQJdSxvfPudwir5IAJ3w==, + } d3-color@3.1.0: - resolution: {integrity: sha512-zg/chbXyeBtMQ1LbD/WSoW2DpC3I0mpmPdW+ynRTj/x2DAWYrIY7qeZIHidozwV24m4iavr15lNwIwLxRmOxhA==} - engines: {node: '>=12'} + resolution: + { + integrity: sha512-zg/chbXyeBtMQ1LbD/WSoW2DpC3I0mpmPdW+ynRTj/x2DAWYrIY7qeZIHidozwV24m4iavr15lNwIwLxRmOxhA==, + } + engines: { node: ">=12" } d3-contour@4.0.2: - resolution: {integrity: sha512-4EzFTRIikzs47RGmdxbeUvLWtGedDUNkTcmzoeyg4sP/dvCexO47AaQL7VKy/gul85TOxw+IBgA8US2xwbToNA==} - engines: {node: '>=12'} + resolution: + { + integrity: sha512-4EzFTRIikzs47RGmdxbeUvLWtGedDUNkTcmzoeyg4sP/dvCexO47AaQL7VKy/gul85TOxw+IBgA8US2xwbToNA==, + } + engines: { node: ">=12" } d3-delaunay@6.0.4: - resolution: {integrity: sha512-mdjtIZ1XLAM8bm/hx3WwjfHt6Sggek7qH043O8KEjDXN40xi3vx/6pYSVTwLjEgiXQTbvaouWKynLBiUZ6SK6A==} - engines: {node: '>=12'} + resolution: + { + integrity: sha512-mdjtIZ1XLAM8bm/hx3WwjfHt6Sggek7qH043O8KEjDXN40xi3vx/6pYSVTwLjEgiXQTbvaouWKynLBiUZ6SK6A==, + } + engines: { node: ">=12" } d3-dispatch@1.0.6: - resolution: {integrity: sha512-fVjoElzjhCEy+Hbn8KygnmMS7Or0a9sI2UzGwoB7cCtvI1XpVN9GpoYlnb3xt2YV66oXYb1fLJ8GMvP4hdU1RA==} + resolution: + { + integrity: sha512-fVjoElzjhCEy+Hbn8KygnmMS7Or0a9sI2UzGwoB7cCtvI1XpVN9GpoYlnb3xt2YV66oXYb1fLJ8GMvP4hdU1RA==, + } d3-dispatch@3.0.1: - resolution: {integrity: sha512-rzUyPU/S7rwUflMyLc1ETDeBj0NRuHKKAcvukozwhshr6g6c5d8zh4c2gQjY2bZ0dXeGLWc1PF174P2tVvKhfg==} - engines: {node: '>=12'} + resolution: + { + integrity: sha512-rzUyPU/S7rwUflMyLc1ETDeBj0NRuHKKAcvukozwhshr6g6c5d8zh4c2gQjY2bZ0dXeGLWc1PF174P2tVvKhfg==, + } + engines: { node: ">=12" } d3-drag@3.0.0: - resolution: {integrity: sha512-pWbUJLdETVA8lQNJecMxoXfH6x+mO2UQo8rSmZ+QqxcbyA3hfeprFgIT//HW2nlHChWeIIMwS2Fq+gEARkhTkg==} - engines: {node: '>=12'} + resolution: + { + integrity: sha512-pWbUJLdETVA8lQNJecMxoXfH6x+mO2UQo8rSmZ+QqxcbyA3hfeprFgIT//HW2nlHChWeIIMwS2Fq+gEARkhTkg==, + } + engines: { node: ">=12" } d3-dsv@3.0.1: - resolution: {integrity: sha512-UG6OvdI5afDIFP9w4G0mNq50dSOsXHJaRE8arAS5o9ApWnIElp8GZw1Dun8vP8OyHOZ/QJUKUJwxiiCCnUwm+Q==} - engines: {node: '>=12'} + resolution: + { + integrity: sha512-UG6OvdI5afDIFP9w4G0mNq50dSOsXHJaRE8arAS5o9ApWnIElp8GZw1Dun8vP8OyHOZ/QJUKUJwxiiCCnUwm+Q==, + } + engines: { node: ">=12" } hasBin: true d3-ease@3.0.1: - resolution: {integrity: sha512-wR/XK3D3XcLIZwpbvQwQ5fK+8Ykds1ip7A2Txe0yxncXSdq1L9skcG7blcedkOX+ZcgxGAmLX1FrRGbADwzi0w==} - engines: {node: '>=12'} + resolution: + { + integrity: sha512-wR/XK3D3XcLIZwpbvQwQ5fK+8Ykds1ip7A2Txe0yxncXSdq1L9skcG7blcedkOX+ZcgxGAmLX1FrRGbADwzi0w==, + } + engines: { node: ">=12" } d3-fetch@3.0.1: - resolution: {integrity: sha512-kpkQIM20n3oLVBKGg6oHrUchHM3xODkTzjMoj7aWQFq5QEM+R6E4WkzT5+tojDY7yjez8KgCBRoj4aEr99Fdqw==} - engines: {node: '>=12'} + resolution: + { + integrity: sha512-kpkQIM20n3oLVBKGg6oHrUchHM3xODkTzjMoj7aWQFq5QEM+R6E4WkzT5+tojDY7yjez8KgCBRoj4aEr99Fdqw==, + } + engines: { node: ">=12" } d3-force@3.0.0: - resolution: {integrity: sha512-zxV/SsA+U4yte8051P4ECydjD/S+qeYtnaIyAs9tgHCqfguma/aAQDjo85A9Z6EKhBirHRJHXIgJUlffT4wdLg==} - engines: {node: '>=12'} + resolution: + { + integrity: sha512-zxV/SsA+U4yte8051P4ECydjD/S+qeYtnaIyAs9tgHCqfguma/aAQDjo85A9Z6EKhBirHRJHXIgJUlffT4wdLg==, + } + engines: { node: ">=12" } d3-format@3.1.0: - resolution: {integrity: sha512-YyUI6AEuY/Wpt8KWLgZHsIU86atmikuoOmCfommt0LYHiQSPjvX2AcFc38PX0CBpr2RCyZhjex+NS/LPOv6YqA==} - engines: {node: '>=12'} + resolution: + { + integrity: sha512-YyUI6AEuY/Wpt8KWLgZHsIU86atmikuoOmCfommt0LYHiQSPjvX2AcFc38PX0CBpr2RCyZhjex+NS/LPOv6YqA==, + } + engines: { node: ">=12" } d3-geo@3.1.1: - resolution: {integrity: sha512-637ln3gXKXOwhalDzinUgY83KzNWZRKbYubaG+fGVuc/dxO64RRljtCTnf5ecMyE1RIdtqpkVcq0IbtU2S8j2Q==} - engines: {node: '>=12'} + resolution: + { + integrity: sha512-637ln3gXKXOwhalDzinUgY83KzNWZRKbYubaG+fGVuc/dxO64RRljtCTnf5ecMyE1RIdtqpkVcq0IbtU2S8j2Q==, + } + engines: { node: ">=12" } d3-hierarchy@3.1.2: - resolution: {integrity: sha512-FX/9frcub54beBdugHjDCdikxThEqjnR93Qt7PvQTOHxyiNCAlvMrHhclk3cD5VeAaq9fxmfRp+CnWw9rEMBuA==} - engines: {node: '>=12'} + resolution: + { + integrity: sha512-FX/9frcub54beBdugHjDCdikxThEqjnR93Qt7PvQTOHxyiNCAlvMrHhclk3cD5VeAaq9fxmfRp+CnWw9rEMBuA==, + } + engines: { node: ">=12" } d3-interpolate@3.0.1: - resolution: {integrity: sha512-3bYs1rOD33uo8aqJfKP3JWPAibgw8Zm2+L9vBKEHJ2Rg+viTR7o5Mmv5mZcieN+FRYaAOWX5SJATX6k1PWz72g==} - engines: {node: '>=12'} + resolution: + { + integrity: sha512-3bYs1rOD33uo8aqJfKP3JWPAibgw8Zm2+L9vBKEHJ2Rg+viTR7o5Mmv5mZcieN+FRYaAOWX5SJATX6k1PWz72g==, + } + engines: { node: ">=12" } d3-path@3.1.0: - resolution: {integrity: sha512-p3KP5HCf/bvjBSSKuXid6Zqijx7wIfNW+J/maPs+iwR35at5JCbLUT0LzF1cnjbCHWhqzQTIN2Jpe8pRebIEFQ==} - engines: {node: '>=12'} + resolution: + { + integrity: sha512-p3KP5HCf/bvjBSSKuXid6Zqijx7wIfNW+J/maPs+iwR35at5JCbLUT0LzF1cnjbCHWhqzQTIN2Jpe8pRebIEFQ==, + } + engines: { node: ">=12" } d3-polygon@3.0.1: - resolution: {integrity: sha512-3vbA7vXYwfe1SYhED++fPUQlWSYTTGmFmQiany/gdbiWgU/iEyQzyymwL9SkJjFFuCS4902BSzewVGsHHmHtXg==} - engines: {node: '>=12'} + resolution: + { + integrity: sha512-3vbA7vXYwfe1SYhED++fPUQlWSYTTGmFmQiany/gdbiWgU/iEyQzyymwL9SkJjFFuCS4902BSzewVGsHHmHtXg==, + } + engines: { node: ">=12" } d3-quadtree@3.0.1: - resolution: {integrity: sha512-04xDrxQTDTCFwP5H6hRhsRcb9xxv2RzkcsygFzmkSIOJy3PeRJP7sNk3VRIbKXcog561P9oU0/rVH6vDROAgUw==} - engines: {node: '>=12'} + resolution: + { + integrity: sha512-04xDrxQTDTCFwP5H6hRhsRcb9xxv2RzkcsygFzmkSIOJy3PeRJP7sNk3VRIbKXcog561P9oU0/rVH6vDROAgUw==, + } + engines: { node: ">=12" } d3-random@3.0.1: - resolution: {integrity: sha512-FXMe9GfxTxqd5D6jFsQ+DJ8BJS4E/fT5mqqdjovykEB2oFbTMDVdg1MGFxfQW+FBOGoB++k8swBrgwSHT1cUXQ==} - engines: {node: '>=12'} + resolution: + { + integrity: sha512-FXMe9GfxTxqd5D6jFsQ+DJ8BJS4E/fT5mqqdjovykEB2oFbTMDVdg1MGFxfQW+FBOGoB++k8swBrgwSHT1cUXQ==, + } + engines: { node: ">=12" } d3-scale-chromatic@3.1.0: - resolution: {integrity: sha512-A3s5PWiZ9YCXFye1o246KoscMWqf8BsD9eRiJ3He7C9OBaxKhAd5TFCdEx/7VbKtxxTsu//1mMJFrEt572cEyQ==} - engines: {node: '>=12'} + resolution: + { + integrity: sha512-A3s5PWiZ9YCXFye1o246KoscMWqf8BsD9eRiJ3He7C9OBaxKhAd5TFCdEx/7VbKtxxTsu//1mMJFrEt572cEyQ==, + } + engines: { node: ">=12" } d3-scale@4.0.2: - resolution: {integrity: sha512-GZW464g1SH7ag3Y7hXjf8RoUuAFIqklOAq3MRl4OaWabTFJY9PN/E1YklhXLh+OQ3fM9yS2nOkCoS+WLZ6kvxQ==} - engines: {node: '>=12'} + resolution: + { + integrity: sha512-GZW464g1SH7ag3Y7hXjf8RoUuAFIqklOAq3MRl4OaWabTFJY9PN/E1YklhXLh+OQ3fM9yS2nOkCoS+WLZ6kvxQ==, + } + engines: { node: ">=12" } d3-selection@3.0.0: - resolution: {integrity: sha512-fmTRWbNMmsmWq6xJV8D19U/gw/bwrHfNXxrIN+HfZgnzqTHp9jOmKMhsTUjXOJnZOdZY9Q28y4yebKzqDKlxlQ==} - engines: {node: '>=12'} + resolution: + { + integrity: sha512-fmTRWbNMmsmWq6xJV8D19U/gw/bwrHfNXxrIN+HfZgnzqTHp9jOmKMhsTUjXOJnZOdZY9Q28y4yebKzqDKlxlQ==, + } + engines: { node: ">=12" } d3-shape@3.2.0: - resolution: {integrity: sha512-SaLBuwGm3MOViRq2ABk3eLoxwZELpH6zhl3FbAoJ7Vm1gofKx6El1Ib5z23NUEhF9AsGl7y+dzLe5Cw2AArGTA==} - engines: {node: '>=12'} + resolution: + { + integrity: sha512-SaLBuwGm3MOViRq2ABk3eLoxwZELpH6zhl3FbAoJ7Vm1gofKx6El1Ib5z23NUEhF9AsGl7y+dzLe5Cw2AArGTA==, + } + engines: { node: ">=12" } d3-time-format@4.1.0: - resolution: {integrity: sha512-dJxPBlzC7NugB2PDLwo9Q8JiTR3M3e4/XANkreKSUxF8vvXKqm1Yfq4Q5dl8budlunRVlUUaDUgFt7eA8D6NLg==} - engines: {node: '>=12'} + resolution: + { + integrity: sha512-dJxPBlzC7NugB2PDLwo9Q8JiTR3M3e4/XANkreKSUxF8vvXKqm1Yfq4Q5dl8budlunRVlUUaDUgFt7eA8D6NLg==, + } + engines: { node: ">=12" } d3-time@3.1.0: - resolution: {integrity: sha512-VqKjzBLejbSMT4IgbmVgDjpkYrNWUYJnbCGo874u7MMKIWsILRX+OpX/gTk8MqjpT1A/c6HY2dCA77ZN0lkQ2Q==} - engines: {node: '>=12'} + resolution: + { + integrity: sha512-VqKjzBLejbSMT4IgbmVgDjpkYrNWUYJnbCGo874u7MMKIWsILRX+OpX/gTk8MqjpT1A/c6HY2dCA77ZN0lkQ2Q==, + } + engines: { node: ">=12" } d3-timer@3.0.1: - resolution: {integrity: sha512-ndfJ/JxxMd3nw31uyKoY2naivF+r29V+Lc0svZxe1JvvIRmi8hUsrMvdOwgS1o6uBHmiz91geQ0ylPP0aj1VUA==} - engines: {node: '>=12'} + resolution: + { + integrity: sha512-ndfJ/JxxMd3nw31uyKoY2naivF+r29V+Lc0svZxe1JvvIRmi8hUsrMvdOwgS1o6uBHmiz91geQ0ylPP0aj1VUA==, + } + engines: { node: ">=12" } d3-transition@3.0.1: - resolution: {integrity: sha512-ApKvfjsSR6tg06xrL434C0WydLr7JewBB3V+/39RMHsaXTOG0zmt/OAXeng5M5LBm0ojmxJrpomQVZ1aPvBL4w==} - engines: {node: '>=12'} + resolution: + { + integrity: sha512-ApKvfjsSR6tg06xrL434C0WydLr7JewBB3V+/39RMHsaXTOG0zmt/OAXeng5M5LBm0ojmxJrpomQVZ1aPvBL4w==, + } + engines: { node: ">=12" } peerDependencies: d3-selection: 2 - 3 d3-zoom@3.0.0: - resolution: {integrity: sha512-b8AmV3kfQaqWAuacbPuNbL6vahnOJflOhexLzMMNLga62+/nh0JzvJ0aO/5a5MVgUFGS7Hu1P9P03o3fJkDCyw==} - engines: {node: '>=12'} + resolution: + { + integrity: sha512-b8AmV3kfQaqWAuacbPuNbL6vahnOJflOhexLzMMNLga62+/nh0JzvJ0aO/5a5MVgUFGS7Hu1P9P03o3fJkDCyw==, + } + engines: { node: ">=12" } d3@7.9.0: - resolution: {integrity: sha512-e1U46jVP+w7Iut8Jt8ri1YsPOvFpg46k+K8TpCb0P+zjCkjkPnV7WzfDJzMHy1LnA+wj5pLT1wjO901gLXeEhA==} - engines: {node: '>=12'} + resolution: + { + integrity: sha512-e1U46jVP+w7Iut8Jt8ri1YsPOvFpg46k+K8TpCb0P+zjCkjkPnV7WzfDJzMHy1LnA+wj5pLT1wjO901gLXeEhA==, + } + engines: { node: ">=12" } damerau-levenshtein@1.0.8: - resolution: {integrity: sha512-sdQSFB7+llfUcQHUQO3+B8ERRj0Oa4w9POWMI/puGtuf7gFywGmkaLCElnudfTiKZV+NvHqL0ifzdrI8Ro7ESA==} + resolution: + { + integrity: sha512-sdQSFB7+llfUcQHUQO3+B8ERRj0Oa4w9POWMI/puGtuf7gFywGmkaLCElnudfTiKZV+NvHqL0ifzdrI8Ro7ESA==, + } data-uri-to-buffer@4.0.1: - resolution: {integrity: sha512-0R9ikRb668HB7QDxT1vkpuUBtqc53YyAwMwGeUFKRojY/NWKvdZ+9UYtRfGmhqNbRkTSVpMbmyhXipFFv2cb/A==} - engines: {node: '>= 12'} + resolution: + { + integrity: sha512-0R9ikRb668HB7QDxT1vkpuUBtqc53YyAwMwGeUFKRojY/NWKvdZ+9UYtRfGmhqNbRkTSVpMbmyhXipFFv2cb/A==, + } + engines: { node: ">= 12" } data-urls@5.0.0: - resolution: {integrity: sha512-ZYP5VBHshaDAiVZxjbRVcFJpc+4xGgT0bK3vzy1HLN8jTO975HEbuYzZJcHoQEY5K1a0z8YayJkyVETa08eNTg==} - engines: {node: '>=18'} + resolution: + { + integrity: sha512-ZYP5VBHshaDAiVZxjbRVcFJpc+4xGgT0bK3vzy1HLN8jTO975HEbuYzZJcHoQEY5K1a0z8YayJkyVETa08eNTg==, + } + engines: { node: ">=18" } data-view-buffer@1.0.2: - resolution: {integrity: sha512-EmKO5V3OLXh1rtK2wgXRansaK1/mtVdTUEiEI0W8RkvgT05kfxaH29PliLnpLP73yYO6142Q72QNa8Wx/A5CqQ==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-EmKO5V3OLXh1rtK2wgXRansaK1/mtVdTUEiEI0W8RkvgT05kfxaH29PliLnpLP73yYO6142Q72QNa8Wx/A5CqQ==, + } + engines: { node: ">= 0.4" } data-view-byte-length@1.0.2: - resolution: {integrity: sha512-tuhGbE6CfTM9+5ANGf+oQb72Ky/0+s3xKUpHvShfiz2RxMFgFPjsXuRLBVMtvMs15awe45SRb83D6wH4ew6wlQ==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-tuhGbE6CfTM9+5ANGf+oQb72Ky/0+s3xKUpHvShfiz2RxMFgFPjsXuRLBVMtvMs15awe45SRb83D6wH4ew6wlQ==, + } + engines: { node: ">= 0.4" } data-view-byte-offset@1.0.1: - resolution: {integrity: sha512-BS8PfmtDGnrgYdOonGZQdLZslWIeCGFP9tpan0hi1Co2Zr2NKADsvGYA8XxuG/4UWgJ6Cjtv+YJnB6MM69QGlQ==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-BS8PfmtDGnrgYdOonGZQdLZslWIeCGFP9tpan0hi1Co2Zr2NKADsvGYA8XxuG/4UWgJ6Cjtv+YJnB6MM69QGlQ==, + } + engines: { node: ">= 0.4" } debug@3.2.7: - resolution: {integrity: sha512-CFjzYYAi4ThfiQvizrFQevTTXHtnCqWfe7x1AhgEscTz6ZbLbfoLRLPugTQyBth6f8ZERVUSyWHFD/7Wu4t1XQ==} + resolution: + { + integrity: sha512-CFjzYYAi4ThfiQvizrFQevTTXHtnCqWfe7x1AhgEscTz6ZbLbfoLRLPugTQyBth6f8ZERVUSyWHFD/7Wu4t1XQ==, + } peerDependencies: - supports-color: '*' + supports-color: "*" peerDependenciesMeta: supports-color: optional: true debug@4.4.1: - resolution: {integrity: sha512-KcKCqiftBJcZr++7ykoDIEwSa3XWowTfNPo92BYxjXiyYEVrUQh2aLyhxBCwww+heortUFxEJYcRzosstTEBYQ==} - engines: {node: '>=6.0'} + resolution: + { + integrity: sha512-KcKCqiftBJcZr++7ykoDIEwSa3XWowTfNPo92BYxjXiyYEVrUQh2aLyhxBCwww+heortUFxEJYcRzosstTEBYQ==, + } + engines: { node: ">=6.0" } peerDependencies: - supports-color: '*' + supports-color: "*" peerDependenciesMeta: supports-color: optional: true decimal.js-light@2.5.1: - resolution: {integrity: sha512-qIMFpTMZmny+MMIitAB6D7iVPEorVw6YQRWkvarTkT4tBeSLLiHzcwj6q0MmYSFCiVpiqPJTJEYIrpcPzVEIvg==} + resolution: + { + integrity: sha512-qIMFpTMZmny+MMIitAB6D7iVPEorVw6YQRWkvarTkT4tBeSLLiHzcwj6q0MmYSFCiVpiqPJTJEYIrpcPzVEIvg==, + } decimal.js@10.5.0: - resolution: {integrity: sha512-8vDa8Qxvr/+d94hSh5P3IJwI5t8/c0KsMp+g8bNw9cY2icONa5aPfvKeieW1WlG0WQYwwhJ7mjui2xtiePQSXw==} + resolution: + { + integrity: sha512-8vDa8Qxvr/+d94hSh5P3IJwI5t8/c0KsMp+g8bNw9cY2icONa5aPfvKeieW1WlG0WQYwwhJ7mjui2xtiePQSXw==, + } decode-named-character-reference@1.2.0: - resolution: {integrity: sha512-c6fcElNV6ShtZXmsgNgFFV5tVX2PaV4g+MOAkb8eXHvn6sryJBrZa9r0zV6+dtTyoCKxtDy5tyQ5ZwQuidtd+Q==} + resolution: + { + integrity: sha512-c6fcElNV6ShtZXmsgNgFFV5tVX2PaV4g+MOAkb8eXHvn6sryJBrZa9r0zV6+dtTyoCKxtDy5tyQ5ZwQuidtd+Q==, + } deep-eql@5.0.2: - resolution: {integrity: sha512-h5k/5U50IJJFpzfL6nO9jaaumfjO/f2NjK/oYB2Djzm4p9L+3T9qWpZqZ2hAbLPuuYq9wrU08WQyBTL5GbPk5Q==} - engines: {node: '>=6'} + resolution: + { + integrity: sha512-h5k/5U50IJJFpzfL6nO9jaaumfjO/f2NjK/oYB2Djzm4p9L+3T9qWpZqZ2hAbLPuuYq9wrU08WQyBTL5GbPk5Q==, + } + engines: { node: ">=6" } deep-is@0.1.4: - resolution: {integrity: sha512-oIPzksmTg4/MriiaYGO+okXDT7ztn/w3Eptv/+gSIdMdKsJo0u4CfYNFJPy+4SKMuCqGw2wxnA+URMg3t8a/bQ==} + resolution: + { + integrity: sha512-oIPzksmTg4/MriiaYGO+okXDT7ztn/w3Eptv/+gSIdMdKsJo0u4CfYNFJPy+4SKMuCqGw2wxnA+URMg3t8a/bQ==, + } define-data-property@1.1.4: - resolution: {integrity: sha512-rBMvIzlpA8v6E+SJZoo++HAYqsLrkg7MSfIinMPFhmkorw7X+dOXVJQs+QT69zGkzMyfDnIMN2Wid1+NbL3T+A==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-rBMvIzlpA8v6E+SJZoo++HAYqsLrkg7MSfIinMPFhmkorw7X+dOXVJQs+QT69zGkzMyfDnIMN2Wid1+NbL3T+A==, + } + engines: { node: ">= 0.4" } define-properties@1.2.1: - resolution: {integrity: sha512-8QmQKqEASLd5nx0U1B1okLElbUuuttJ/AnYmRXbbbGDWh6uS208EjD4Xqq/I9wK7u0v6O08XhTWnt5XtEbR6Dg==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-8QmQKqEASLd5nx0U1B1okLElbUuuttJ/AnYmRXbbbGDWh6uS208EjD4Xqq/I9wK7u0v6O08XhTWnt5XtEbR6Dg==, + } + engines: { node: ">= 0.4" } delaunator@5.0.1: - resolution: {integrity: sha512-8nvh+XBe96aCESrGOqMp/84b13H9cdKbG5P2ejQCh4d4sK9RL4371qou9drQjMhvnPmhWl5hnmqbEE0fXr9Xnw==} + resolution: + { + integrity: sha512-8nvh+XBe96aCESrGOqMp/84b13H9cdKbG5P2ejQCh4d4sK9RL4371qou9drQjMhvnPmhWl5hnmqbEE0fXr9Xnw==, + } delayed-stream@1.0.0: - resolution: {integrity: sha512-ZySD7Nf91aLB0RxL4KGrKHBXl7Eds1DAmEdcoVawXnLD7SDhpNgtuII2aAkg7a7QS41jxPSZ17p4VdGnMHk3MQ==} - engines: {node: '>=0.4.0'} + resolution: + { + integrity: sha512-ZySD7Nf91aLB0RxL4KGrKHBXl7Eds1DAmEdcoVawXnLD7SDhpNgtuII2aAkg7a7QS41jxPSZ17p4VdGnMHk3MQ==, + } + engines: { node: ">=0.4.0" } dequal@2.0.3: - resolution: {integrity: sha512-0je+qPKHEMohvfRTCEo3CrPG6cAzAYgmzKyxRiYSSDkS6eGJdyVJm7WaYA5ECaAD9wLB2T4EEeymA5aFVcYXCA==} - engines: {node: '>=6'} + resolution: + { + integrity: sha512-0je+qPKHEMohvfRTCEo3CrPG6cAzAYgmzKyxRiYSSDkS6eGJdyVJm7WaYA5ECaAD9wLB2T4EEeymA5aFVcYXCA==, + } + engines: { node: ">=6" } detect-libc@2.0.4: - resolution: {integrity: sha512-3UDv+G9CsCKO1WKMGw9fwq/SWJYbI0c5Y7LU1AXYoDdbhE2AHQ6N6Nb34sG8Fj7T5APy8qXDCKuuIHd1BR0tVA==} - engines: {node: '>=8'} + resolution: + { + integrity: sha512-3UDv+G9CsCKO1WKMGw9fwq/SWJYbI0c5Y7LU1AXYoDdbhE2AHQ6N6Nb34sG8Fj7T5APy8qXDCKuuIHd1BR0tVA==, + } + engines: { node: ">=8" } detect-node-es@1.1.0: - resolution: {integrity: sha512-ypdmJU/TbBby2Dxibuv7ZLW3Bs1QEmM7nHjEANfohJLvE0XVujisn1qPJcZxg+qDucsr+bP6fLD1rPS3AhJ7EQ==} + resolution: + { + integrity: sha512-ypdmJU/TbBby2Dxibuv7ZLW3Bs1QEmM7nHjEANfohJLvE0XVujisn1qPJcZxg+qDucsr+bP6fLD1rPS3AhJ7EQ==, + } devlop@1.1.0: - resolution: {integrity: sha512-RWmIqhcFf1lRYBvNmr7qTNuyCt/7/ns2jbpp1+PalgE/rDQcBT0fioSMUpJ93irlUhC5hrg4cYqe6U+0ImW0rA==} + resolution: + { + integrity: sha512-RWmIqhcFf1lRYBvNmr7qTNuyCt/7/ns2jbpp1+PalgE/rDQcBT0fioSMUpJ93irlUhC5hrg4cYqe6U+0ImW0rA==, + } diacritics@1.3.0: - resolution: {integrity: sha512-wlwEkqcsaxvPJML+rDh/2iS824jbREk6DUMUKkEaSlxdYHeS43cClJtsWglvw2RfeXGm6ohKDqsXteJ5sP5enA==} + resolution: + { + integrity: sha512-wlwEkqcsaxvPJML+rDh/2iS824jbREk6DUMUKkEaSlxdYHeS43cClJtsWglvw2RfeXGm6ohKDqsXteJ5sP5enA==, + } diff@4.0.2: - resolution: {integrity: sha512-58lmxKSA4BNyLz+HHMUzlOEpg09FV+ev6ZMe3vJihgdxzgcwZ8VoEEPmALCZG9LmqfVoNMMKpttIYTVG6uDY7A==} - engines: {node: '>=0.3.1'} + resolution: + { + integrity: sha512-58lmxKSA4BNyLz+HHMUzlOEpg09FV+ev6ZMe3vJihgdxzgcwZ8VoEEPmALCZG9LmqfVoNMMKpttIYTVG6uDY7A==, + } + engines: { node: ">=0.3.1" } doctrine@2.1.0: - resolution: {integrity: sha512-35mSku4ZXK0vfCuHEDAwt55dg2jNajHZ1odvF+8SSr82EsZY4QmXfuWso8oEd8zRhVObSN18aM0CjSdoBX7zIw==} - engines: {node: '>=0.10.0'} + resolution: + { + integrity: sha512-35mSku4ZXK0vfCuHEDAwt55dg2jNajHZ1odvF+8SSr82EsZY4QmXfuWso8oEd8zRhVObSN18aM0CjSdoBX7zIw==, + } + engines: { node: ">=0.10.0" } dom-accessibility-api@0.5.16: - resolution: {integrity: sha512-X7BJ2yElsnOJ30pZF4uIIDfBEVgF4XEBxL9Bxhy6dnrm5hkzqmsWHGTiHqRiITNhMyFLyAiWndIJP7Z1NTteDg==} + resolution: + { + integrity: sha512-X7BJ2yElsnOJ30pZF4uIIDfBEVgF4XEBxL9Bxhy6dnrm5hkzqmsWHGTiHqRiITNhMyFLyAiWndIJP7Z1NTteDg==, + } dunder-proto@1.0.1: - resolution: {integrity: sha512-KIN/nDJBQRcXw0MLVhZE9iQHmG68qAVIBg9CqmUYjmQIhgij9U5MFvrqkUL5FbtyyzZuOeOt0zdeRe4UY7ct+A==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-KIN/nDJBQRcXw0MLVhZE9iQHmG68qAVIBg9CqmUYjmQIhgij9U5MFvrqkUL5FbtyyzZuOeOt0zdeRe4UY7ct+A==, + } + engines: { node: ">= 0.4" } eastasianwidth@0.2.0: - resolution: {integrity: sha512-I88TYZWc9XiYHRQ4/3c5rjjfgkjhLyW2luGIheGERbNQ6OY7yTybanSpDXZa8y7VUP9YmDcYa+eyq4ca7iLqWA==} + resolution: + { + integrity: sha512-I88TYZWc9XiYHRQ4/3c5rjjfgkjhLyW2luGIheGERbNQ6OY7yTybanSpDXZa8y7VUP9YmDcYa+eyq4ca7iLqWA==, + } electron-to-chromium@1.5.177: - resolution: {integrity: sha512-7EH2G59nLsEMj97fpDuvVcYi6lwTcM1xuWw3PssD8xzboAW7zj7iB3COEEEATUfjLHrs5uKBLQT03V/8URx06g==} + resolution: + { + integrity: sha512-7EH2G59nLsEMj97fpDuvVcYi6lwTcM1xuWw3PssD8xzboAW7zj7iB3COEEEATUfjLHrs5uKBLQT03V/8URx06g==, + } emoji-regex@8.0.0: - resolution: {integrity: sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A==} + resolution: + { + integrity: sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A==, + } emoji-regex@9.2.2: - resolution: {integrity: sha512-L18DaJsXSUk2+42pv8mLs5jJT2hqFkFE4j21wOmgbUqsZ2hL72NsUU785g9RXgo3s0ZNgVl42TiHp3ZtOv/Vyg==} + resolution: + { + integrity: sha512-L18DaJsXSUk2+42pv8mLs5jJT2hqFkFE4j21wOmgbUqsZ2hL72NsUU785g9RXgo3s0ZNgVl42TiHp3ZtOv/Vyg==, + } enhanced-resolve@5.18.2: - resolution: {integrity: sha512-6Jw4sE1maoRJo3q8MsSIn2onJFbLTOjY9hlx4DZXmOKvLRd1Ok2kXmAGXaafL2+ijsJZ1ClYbl/pmqr9+k4iUQ==} - engines: {node: '>=10.13.0'} + resolution: + { + integrity: sha512-6Jw4sE1maoRJo3q8MsSIn2onJFbLTOjY9hlx4DZXmOKvLRd1Ok2kXmAGXaafL2+ijsJZ1ClYbl/pmqr9+k4iUQ==, + } + engines: { node: ">=10.13.0" } entities@4.5.0: - resolution: {integrity: sha512-V0hjH4dGPh9Ao5p0MoRY6BVqtwCjhz6vI5LT8AJ55H+4g9/4vbHx1I54fS0XuclLhDHArPQCiMjDxjaL8fPxhw==} - engines: {node: '>=0.12'} + resolution: + { + integrity: sha512-V0hjH4dGPh9Ao5p0MoRY6BVqtwCjhz6vI5LT8AJ55H+4g9/4vbHx1I54fS0XuclLhDHArPQCiMjDxjaL8fPxhw==, + } + engines: { node: ">=0.12" } entities@6.0.1: - resolution: {integrity: sha512-aN97NXWF6AWBTahfVOIrB/NShkzi5H7F9r1s9mD3cDj4Ko5f2qhhVoYMibXF7GlLveb/D2ioWay8lxI97Ven3g==} - engines: {node: '>=0.12'} + resolution: + { + integrity: sha512-aN97NXWF6AWBTahfVOIrB/NShkzi5H7F9r1s9mD3cDj4Ko5f2qhhVoYMibXF7GlLveb/D2ioWay8lxI97Ven3g==, + } + engines: { node: ">=0.12" } es-abstract@1.24.0: - resolution: {integrity: sha512-WSzPgsdLtTcQwm4CROfS5ju2Wa1QQcVeT37jFjYzdFz1r9ahadC8B8/a4qxJxM+09F18iumCdRmlr96ZYkQvEg==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-WSzPgsdLtTcQwm4CROfS5ju2Wa1QQcVeT37jFjYzdFz1r9ahadC8B8/a4qxJxM+09F18iumCdRmlr96ZYkQvEg==, + } + engines: { node: ">= 0.4" } es-define-property@1.0.1: - resolution: {integrity: sha512-e3nRfgfUZ4rNGL232gUgX06QNyyez04KdjFrF+LTRoOXmrOgFKDg4BCdsjW8EnT69eqdYGmRpJwiPVYNrCaW3g==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-e3nRfgfUZ4rNGL232gUgX06QNyyez04KdjFrF+LTRoOXmrOgFKDg4BCdsjW8EnT69eqdYGmRpJwiPVYNrCaW3g==, + } + engines: { node: ">= 0.4" } es-errors@1.3.0: - resolution: {integrity: sha512-Zf5H2Kxt2xjTvbJvP2ZWLEICxA6j+hAmMzIlypy4xcBg1vKVnx89Wy0GbS+kf5cwCVFFzdCFh2XSCFNULS6csw==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-Zf5H2Kxt2xjTvbJvP2ZWLEICxA6j+hAmMzIlypy4xcBg1vKVnx89Wy0GbS+kf5cwCVFFzdCFh2XSCFNULS6csw==, + } + engines: { node: ">= 0.4" } es-iterator-helpers@1.2.1: - resolution: {integrity: sha512-uDn+FE1yrDzyC0pCo961B2IHbdM8y/ACZsKD4dG6WqrjV53BADjwa7D+1aom2rsNVfLyDgU/eigvlJGJ08OQ4w==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-uDn+FE1yrDzyC0pCo961B2IHbdM8y/ACZsKD4dG6WqrjV53BADjwa7D+1aom2rsNVfLyDgU/eigvlJGJ08OQ4w==, + } + engines: { node: ">= 0.4" } es-module-lexer@1.7.0: - resolution: {integrity: sha512-jEQoCwk8hyb2AZziIOLhDqpm5+2ww5uIE6lkO/6jcOCusfk6LhMHpXXfBLXTZ7Ydyt0j4VoUQv6uGNYbdW+kBA==} + resolution: + { + integrity: sha512-jEQoCwk8hyb2AZziIOLhDqpm5+2ww5uIE6lkO/6jcOCusfk6LhMHpXXfBLXTZ7Ydyt0j4VoUQv6uGNYbdW+kBA==, + } es-object-atoms@1.1.1: - resolution: {integrity: sha512-FGgH2h8zKNim9ljj7dankFPcICIK9Cp5bm+c2gQSYePhpaG5+esrLODihIorn+Pe6FGJzWhXQotPv73jTaldXA==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-FGgH2h8zKNim9ljj7dankFPcICIK9Cp5bm+c2gQSYePhpaG5+esrLODihIorn+Pe6FGJzWhXQotPv73jTaldXA==, + } + engines: { node: ">= 0.4" } es-set-tostringtag@2.1.0: - resolution: {integrity: sha512-j6vWzfrGVfyXxge+O0x5sh6cvxAog0a/4Rdd2K36zCMV5eJ+/+tOAngRO8cODMNWbVRdVlmGZQL2YS3yR8bIUA==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-j6vWzfrGVfyXxge+O0x5sh6cvxAog0a/4Rdd2K36zCMV5eJ+/+tOAngRO8cODMNWbVRdVlmGZQL2YS3yR8bIUA==, + } + engines: { node: ">= 0.4" } es-shim-unscopables@1.1.0: - resolution: {integrity: sha512-d9T8ucsEhh8Bi1woXCf+TIKDIROLG5WCkxg8geBCbvk22kzwC5G2OnXVMO6FUsvQlgUUXQ2itephWDLqDzbeCw==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-d9T8ucsEhh8Bi1woXCf+TIKDIROLG5WCkxg8geBCbvk22kzwC5G2OnXVMO6FUsvQlgUUXQ2itephWDLqDzbeCw==, + } + engines: { node: ">= 0.4" } es-to-primitive@1.3.0: - resolution: {integrity: sha512-w+5mJ3GuFL+NjVtJlvydShqE1eN3h3PbI7/5LAsYJP/2qtuMXjfL2LpHSRqo4b4eSF5K/DH1JXKUAHSB2UW50g==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-w+5mJ3GuFL+NjVtJlvydShqE1eN3h3PbI7/5LAsYJP/2qtuMXjfL2LpHSRqo4b4eSF5K/DH1JXKUAHSB2UW50g==, + } + engines: { node: ">= 0.4" } es-toolkit@1.39.5: - resolution: {integrity: sha512-z9V0qU4lx1TBXDNFWfAASWk6RNU6c6+TJBKE+FLIg8u0XJ6Yw58Hi0yX8ftEouj6p1QARRlXLFfHbIli93BdQQ==} + resolution: + { + integrity: sha512-z9V0qU4lx1TBXDNFWfAASWk6RNU6c6+TJBKE+FLIg8u0XJ6Yw58Hi0yX8ftEouj6p1QARRlXLFfHbIli93BdQQ==, + } esbuild@0.25.5: - resolution: {integrity: sha512-P8OtKZRv/5J5hhz0cUAdu/cLuPIKXpQl1R9pZtvmHWQvrAUVd0UNIPT4IB4W3rNOqVO0rlqHmCIbSwxh/c9yUQ==} - engines: {node: '>=18'} + resolution: + { + integrity: sha512-P8OtKZRv/5J5hhz0cUAdu/cLuPIKXpQl1R9pZtvmHWQvrAUVd0UNIPT4IB4W3rNOqVO0rlqHmCIbSwxh/c9yUQ==, + } + engines: { node: ">=18" } hasBin: true escalade@3.2.0: - resolution: {integrity: sha512-WUj2qlxaQtO4g6Pq5c29GTcWGDyd8itL8zTlipgECz3JesAiiOKotd8JU6otB3PACgG6xkJUyVhboMS+bje/jA==} - engines: {node: '>=6'} + resolution: + { + integrity: sha512-WUj2qlxaQtO4g6Pq5c29GTcWGDyd8itL8zTlipgECz3JesAiiOKotd8JU6otB3PACgG6xkJUyVhboMS+bje/jA==, + } + engines: { node: ">=6" } escape-string-regexp@4.0.0: - resolution: {integrity: sha512-TtpcNJ3XAzx3Gq8sWRzJaVajRs0uVxA2YAkdb1jm2YkPz4G6egUFAyA3n5vtEIZefPk5Wa4UXbKuS5fKkJWdgA==} - engines: {node: '>=10'} + resolution: + { + integrity: sha512-TtpcNJ3XAzx3Gq8sWRzJaVajRs0uVxA2YAkdb1jm2YkPz4G6egUFAyA3n5vtEIZefPk5Wa4UXbKuS5fKkJWdgA==, + } + engines: { node: ">=10" } eslint-config-next@15.3.4: - resolution: {integrity: sha512-WqeumCq57QcTP2lYlV6BRUySfGiBYEXlQ1L0mQ+u4N4X4ZhUVSSQ52WtjqHv60pJ6dD7jn+YZc0d1/ZSsxccvg==} + resolution: + { + integrity: sha512-WqeumCq57QcTP2lYlV6BRUySfGiBYEXlQ1L0mQ+u4N4X4ZhUVSSQ52WtjqHv60pJ6dD7jn+YZc0d1/ZSsxccvg==, + } peerDependencies: eslint: ^7.23.0 || ^8.0.0 || ^9.0.0 - typescript: '>=3.3.1' + typescript: ">=3.3.1" peerDependenciesMeta: typescript: optional: true eslint-import-resolver-node@0.3.9: - resolution: {integrity: sha512-WFj2isz22JahUv+B788TlO3N6zL3nNJGU8CcZbPZvVEkBPaJdCV4vy5wyghty5ROFbCRnm132v8BScu5/1BQ8g==} + resolution: + { + integrity: sha512-WFj2isz22JahUv+B788TlO3N6zL3nNJGU8CcZbPZvVEkBPaJdCV4vy5wyghty5ROFbCRnm132v8BScu5/1BQ8g==, + } eslint-import-resolver-typescript@3.10.1: - resolution: {integrity: sha512-A1rHYb06zjMGAxdLSkN2fXPBwuSaQ0iO5M/hdyS0Ajj1VBaRp0sPD3dn1FhME3c/JluGFbwSxyCfqdSbtQLAHQ==} - engines: {node: ^14.18.0 || >=16.0.0} + resolution: + { + integrity: sha512-A1rHYb06zjMGAxdLSkN2fXPBwuSaQ0iO5M/hdyS0Ajj1VBaRp0sPD3dn1FhME3c/JluGFbwSxyCfqdSbtQLAHQ==, + } + engines: { node: ^14.18.0 || >=16.0.0 } peerDependencies: - eslint: '*' - eslint-plugin-import: '*' - eslint-plugin-import-x: '*' + eslint: "*" + eslint-plugin-import: "*" + eslint-plugin-import-x: "*" peerDependenciesMeta: eslint-plugin-import: optional: true @@ -2415,16 +3816,19 @@ packages: optional: true eslint-module-utils@2.12.1: - resolution: {integrity: sha512-L8jSWTze7K2mTg0vos/RuLRS5soomksDPoJLXIslC7c8Wmut3bx7CPpJijDcBZtxQ5lrbUdM+s0OlNbz0DCDNw==} - engines: {node: '>=4'} + resolution: + { + integrity: sha512-L8jSWTze7K2mTg0vos/RuLRS5soomksDPoJLXIslC7c8Wmut3bx7CPpJijDcBZtxQ5lrbUdM+s0OlNbz0DCDNw==, + } + engines: { node: ">=4" } peerDependencies: - '@typescript-eslint/parser': '*' - eslint: '*' - eslint-import-resolver-node: '*' - eslint-import-resolver-typescript: '*' - eslint-import-resolver-webpack: '*' + "@typescript-eslint/parser": "*" + eslint: "*" + eslint-import-resolver-node: "*" + eslint-import-resolver-typescript: "*" + eslint-import-resolver-webpack: "*" peerDependenciesMeta: - '@typescript-eslint/parser': + "@typescript-eslint/parser": optional: true eslint: optional: true @@ -2436,130 +3840,211 @@ packages: optional: true eslint-plugin-import@2.32.0: - resolution: {integrity: sha512-whOE1HFo/qJDyX4SnXzP4N6zOWn79WhnCUY/iDR0mPfQZO8wcYE4JClzI2oZrhBnnMUCBCHZhO6VQyoBU95mZA==} - engines: {node: '>=4'} + resolution: + { + integrity: sha512-whOE1HFo/qJDyX4SnXzP4N6zOWn79WhnCUY/iDR0mPfQZO8wcYE4JClzI2oZrhBnnMUCBCHZhO6VQyoBU95mZA==, + } + engines: { node: ">=4" } peerDependencies: - '@typescript-eslint/parser': '*' + "@typescript-eslint/parser": "*" eslint: ^2 || ^3 || ^4 || ^5 || ^6 || ^7.2.0 || ^8 || ^9 peerDependenciesMeta: - '@typescript-eslint/parser': + "@typescript-eslint/parser": optional: true eslint-plugin-jsx-a11y@6.10.2: - resolution: {integrity: sha512-scB3nz4WmG75pV8+3eRUQOHZlNSUhFNq37xnpgRkCCELU3XMvXAxLk1eqWWyE22Ki4Q01Fnsw9BA3cJHDPgn2Q==} - engines: {node: '>=4.0'} + resolution: + { + integrity: sha512-scB3nz4WmG75pV8+3eRUQOHZlNSUhFNq37xnpgRkCCELU3XMvXAxLk1eqWWyE22Ki4Q01Fnsw9BA3cJHDPgn2Q==, + } + engines: { node: ">=4.0" } peerDependencies: eslint: ^3 || ^4 || ^5 || ^6 || ^7 || ^8 || ^9 eslint-plugin-prettier@5.5.1: - resolution: {integrity: sha512-dobTkHT6XaEVOo8IO90Q4DOSxnm3Y151QxPJlM/vKC0bVy+d6cVWQZLlFiuZPP0wS6vZwSKeJgKkcS+KfMBlRw==} - engines: {node: ^14.18.0 || >=16.0.0} + resolution: + { + integrity: sha512-dobTkHT6XaEVOo8IO90Q4DOSxnm3Y151QxPJlM/vKC0bVy+d6cVWQZLlFiuZPP0wS6vZwSKeJgKkcS+KfMBlRw==, + } + engines: { node: ^14.18.0 || >=16.0.0 } peerDependencies: - '@types/eslint': '>=8.0.0' - eslint: '>=8.0.0' - eslint-config-prettier: '>= 7.0.0 <10.0.0 || >=10.1.0' - prettier: '>=3.0.0' + "@types/eslint": ">=8.0.0" + eslint: ">=8.0.0" + eslint-config-prettier: ">= 7.0.0 <10.0.0 || >=10.1.0" + prettier: ">=3.0.0" peerDependenciesMeta: - '@types/eslint': + "@types/eslint": optional: true eslint-config-prettier: optional: true eslint-plugin-react-hooks@5.2.0: - resolution: {integrity: sha512-+f15FfK64YQwZdJNELETdn5ibXEUQmW1DZL6KXhNnc2heoy/sg9VJJeT7n8TlMWouzWqSWavFkIhHyIbIAEapg==} - engines: {node: '>=10'} + resolution: + { + integrity: sha512-+f15FfK64YQwZdJNELETdn5ibXEUQmW1DZL6KXhNnc2heoy/sg9VJJeT7n8TlMWouzWqSWavFkIhHyIbIAEapg==, + } + engines: { node: ">=10" } peerDependencies: eslint: ^3.0.0 || ^4.0.0 || ^5.0.0 || ^6.0.0 || ^7.0.0 || ^8.0.0-0 || ^9.0.0 eslint-plugin-react@7.37.5: - resolution: {integrity: sha512-Qteup0SqU15kdocexFNAJMvCJEfa2xUKNV4CC1xsVMrIIqEy3SQ/rqyxCWNzfrd3/ldy6HMlD2e0JDVpDg2qIA==} - engines: {node: '>=4'} + resolution: + { + integrity: sha512-Qteup0SqU15kdocexFNAJMvCJEfa2xUKNV4CC1xsVMrIIqEy3SQ/rqyxCWNzfrd3/ldy6HMlD2e0JDVpDg2qIA==, + } + engines: { node: ">=4" } peerDependencies: eslint: ^3 || ^4 || ^5 || ^6 || ^7 || ^8 || ^9.7 eslint-scope@8.4.0: - resolution: {integrity: sha512-sNXOfKCn74rt8RICKMvJS7XKV/Xk9kA7DyJr8mJik3S7Cwgy3qlkkmyS2uQB3jiJg6VNdZd/pDBJu0nvG2NlTg==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + resolution: + { + integrity: sha512-sNXOfKCn74rt8RICKMvJS7XKV/Xk9kA7DyJr8mJik3S7Cwgy3qlkkmyS2uQB3jiJg6VNdZd/pDBJu0nvG2NlTg==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } eslint-visitor-keys@3.4.3: - resolution: {integrity: sha512-wpc+LXeiyiisxPlEkUzU6svyS1frIO3Mgxj1fdy7Pm8Ygzguax2N3Fa/D/ag1WqbOprdI+uY6wMUl8/a2G+iag==} - engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0} + resolution: + { + integrity: sha512-wpc+LXeiyiisxPlEkUzU6svyS1frIO3Mgxj1fdy7Pm8Ygzguax2N3Fa/D/ag1WqbOprdI+uY6wMUl8/a2G+iag==, + } + engines: { node: ^12.22.0 || ^14.17.0 || >=16.0.0 } eslint-visitor-keys@4.2.1: - resolution: {integrity: sha512-Uhdk5sfqcee/9H/rCOJikYz67o0a2Tw2hGRPOG2Y1R2dg7brRe1uG0yaNQDHu+TO/uQPF/5eCapvYSmHUjt7JQ==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + resolution: + { + integrity: sha512-Uhdk5sfqcee/9H/rCOJikYz67o0a2Tw2hGRPOG2Y1R2dg7brRe1uG0yaNQDHu+TO/uQPF/5eCapvYSmHUjt7JQ==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } eslint@9.30.0: - resolution: {integrity: sha512-iN/SiPxmQu6EVkf+m1qpBxzUhE12YqFLOSySuOyVLJLEF9nzTf+h/1AJYc1JWzCnktggeNrjvQGLngDzXirU6g==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + resolution: + { + integrity: sha512-iN/SiPxmQu6EVkf+m1qpBxzUhE12YqFLOSySuOyVLJLEF9nzTf+h/1AJYc1JWzCnktggeNrjvQGLngDzXirU6g==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } hasBin: true peerDependencies: - jiti: '*' + jiti: "*" peerDependenciesMeta: jiti: optional: true espree@10.4.0: - resolution: {integrity: sha512-j6PAQ2uUr79PZhBjP5C5fhl8e39FmRnOjsD5lGnWrFU8i2G776tBK7+nP8KuQUTTyAZUwfQqXAgrVH5MbH9CYQ==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + resolution: + { + integrity: sha512-j6PAQ2uUr79PZhBjP5C5fhl8e39FmRnOjsD5lGnWrFU8i2G776tBK7+nP8KuQUTTyAZUwfQqXAgrVH5MbH9CYQ==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } esquery@1.6.0: - resolution: {integrity: sha512-ca9pw9fomFcKPvFLXhBKUK90ZvGibiGOvRJNbjljY7s7uq/5YO4BOzcYtJqExdx99rF6aAcnRxHmcUHcz6sQsg==} - engines: {node: '>=0.10'} + resolution: + { + integrity: sha512-ca9pw9fomFcKPvFLXhBKUK90ZvGibiGOvRJNbjljY7s7uq/5YO4BOzcYtJqExdx99rF6aAcnRxHmcUHcz6sQsg==, + } + engines: { node: ">=0.10" } esrecurse@4.3.0: - resolution: {integrity: sha512-KmfKL3b6G+RXvP8N1vr3Tq1kL/oCFgn2NYXEtqP8/L3pKapUA4G8cFVaoF3SU323CD4XypR/ffioHmkti6/Tag==} - engines: {node: '>=4.0'} + resolution: + { + integrity: sha512-KmfKL3b6G+RXvP8N1vr3Tq1kL/oCFgn2NYXEtqP8/L3pKapUA4G8cFVaoF3SU323CD4XypR/ffioHmkti6/Tag==, + } + engines: { node: ">=4.0" } estraverse@5.3.0: - resolution: {integrity: sha512-MMdARuVEQziNTeJD8DgMqmhwR11BRQ/cBP+pLtYdSTnf3MIO8fFeiINEbX36ZdNlfU/7A9f3gUw49B3oQsvwBA==} - engines: {node: '>=4.0'} + resolution: + { + integrity: sha512-MMdARuVEQziNTeJD8DgMqmhwR11BRQ/cBP+pLtYdSTnf3MIO8fFeiINEbX36ZdNlfU/7A9f3gUw49B3oQsvwBA==, + } + engines: { node: ">=4.0" } estree-util-is-identifier-name@3.0.0: - resolution: {integrity: sha512-hFtqIDZTIUZ9BXLb8y4pYGyk6+wekIivNVTcmvk8NoOh+VeRn5y6cEHzbURrWbfp1fIqdVipilzj+lfaadNZmg==} + resolution: + { + integrity: sha512-hFtqIDZTIUZ9BXLb8y4pYGyk6+wekIivNVTcmvk8NoOh+VeRn5y6cEHzbURrWbfp1fIqdVipilzj+lfaadNZmg==, + } estree-walker@3.0.3: - resolution: {integrity: sha512-7RUKfXgSMMkzt6ZuXmqapOurLGPPfgj6l9uRZ7lRGolvk0y2yocc35LdcxKC5PQZdn2DMqioAQ2NoWcrTKmm6g==} + resolution: + { + integrity: sha512-7RUKfXgSMMkzt6ZuXmqapOurLGPPfgj6l9uRZ7lRGolvk0y2yocc35LdcxKC5PQZdn2DMqioAQ2NoWcrTKmm6g==, + } esutils@2.0.3: - resolution: {integrity: sha512-kVscqXk4OCp68SZ0dkgEKVi6/8ij300KBWTJq32P/dYeWTSwK41WyTxalN1eRmA5Z9UU/LX9D7FWSmV9SAYx6g==} - engines: {node: '>=0.10.0'} + resolution: + { + integrity: sha512-kVscqXk4OCp68SZ0dkgEKVi6/8ij300KBWTJq32P/dYeWTSwK41WyTxalN1eRmA5Z9UU/LX9D7FWSmV9SAYx6g==, + } + engines: { node: ">=0.10.0" } eventemitter3@5.0.1: - resolution: {integrity: sha512-GWkBvjiSZK87ELrYOSESUYeVIc9mvLLf/nXalMOS5dYrgZq9o5OVkbZAVM06CVxYsCwH9BDZFPlQTlPA1j4ahA==} + resolution: + { + integrity: sha512-GWkBvjiSZK87ELrYOSESUYeVIc9mvLLf/nXalMOS5dYrgZq9o5OVkbZAVM06CVxYsCwH9BDZFPlQTlPA1j4ahA==, + } expect-type@1.2.1: - resolution: {integrity: sha512-/kP8CAwxzLVEeFrMm4kMmy4CCDlpipyA7MYLVrdJIkV0fYF0UaigQHRsxHiuY/GEea+bh4KSv3TIlgr+2UL6bw==} - engines: {node: '>=12.0.0'} + resolution: + { + integrity: sha512-/kP8CAwxzLVEeFrMm4kMmy4CCDlpipyA7MYLVrdJIkV0fYF0UaigQHRsxHiuY/GEea+bh4KSv3TIlgr+2UL6bw==, + } + engines: { node: ">=12.0.0" } extend@3.0.2: - resolution: {integrity: sha512-fjquC59cD7CyW6urNXK0FBufkZcoiGG80wTuPujX590cB5Ttln20E2UB4S/WARVqhXffZl2LNgS+gQdPIIim/g==} + resolution: + { + integrity: sha512-fjquC59cD7CyW6urNXK0FBufkZcoiGG80wTuPujX590cB5Ttln20E2UB4S/WARVqhXffZl2LNgS+gQdPIIim/g==, + } fast-deep-equal@3.1.3: - resolution: {integrity: sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q==} + resolution: + { + integrity: sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q==, + } fast-diff@1.3.0: - resolution: {integrity: sha512-VxPP4NqbUjj6MaAOafWeUn2cXWLcCtljklUtZf0Ind4XQ+QPtmA0b18zZy0jIQx+ExRVCR/ZQpBmik5lXshNsw==} + resolution: + { + integrity: sha512-VxPP4NqbUjj6MaAOafWeUn2cXWLcCtljklUtZf0Ind4XQ+QPtmA0b18zZy0jIQx+ExRVCR/ZQpBmik5lXshNsw==, + } fast-glob@3.3.1: - resolution: {integrity: sha512-kNFPyjhh5cKjrUltxs+wFx+ZkbRaxxmZ+X0ZU31SOsxCEtP9VPgtq2teZw1DebupL5GmDaNQ6yKMMVcM41iqDg==} - engines: {node: '>=8.6.0'} + resolution: + { + integrity: sha512-kNFPyjhh5cKjrUltxs+wFx+ZkbRaxxmZ+X0ZU31SOsxCEtP9VPgtq2teZw1DebupL5GmDaNQ6yKMMVcM41iqDg==, + } + engines: { node: ">=8.6.0" } fast-glob@3.3.3: - resolution: {integrity: sha512-7MptL8U0cqcFdzIzwOTHoilX9x5BrNqye7Z/LuC7kCMRio1EMSyqRK3BEAUD7sXRq4iT4AzTVuZdhgQ2TCvYLg==} - engines: {node: '>=8.6.0'} + resolution: + { + integrity: sha512-7MptL8U0cqcFdzIzwOTHoilX9x5BrNqye7Z/LuC7kCMRio1EMSyqRK3BEAUD7sXRq4iT4AzTVuZdhgQ2TCvYLg==, + } + engines: { node: ">=8.6.0" } fast-json-stable-stringify@2.1.0: - resolution: {integrity: sha512-lhd/wF+Lk98HZoTCtlVraHtfh5XYijIjalXck7saUtuanSDyLMxnHhSXEDJqHxD7msR8D0uCmqlkwjCV8xvwHw==} + resolution: + { + integrity: sha512-lhd/wF+Lk98HZoTCtlVraHtfh5XYijIjalXck7saUtuanSDyLMxnHhSXEDJqHxD7msR8D0uCmqlkwjCV8xvwHw==, + } fast-levenshtein@2.0.6: - resolution: {integrity: sha512-DCXu6Ifhqcks7TZKY3Hxp3y6qphY5SJZmrWMDrKcERSOXWQdMhU9Ig/PYrzyw/ul9jOIyh0N4M0tbC5hodg8dw==} + resolution: + { + integrity: sha512-DCXu6Ifhqcks7TZKY3Hxp3y6qphY5SJZmrWMDrKcERSOXWQdMhU9Ig/PYrzyw/ul9jOIyh0N4M0tbC5hodg8dw==, + } fastq@1.19.1: - resolution: {integrity: sha512-GwLTyxkCXjXbxqIhTsMI2Nui8huMPtnxg7krajPJAjnEG/iiOS7i+zCtWGZR9G0NBKbXKh6X9m9UIsYX/N6vvQ==} + resolution: + { + integrity: sha512-GwLTyxkCXjXbxqIhTsMI2Nui8huMPtnxg7krajPJAjnEG/iiOS7i+zCtWGZR9G0NBKbXKh6X9m9UIsYX/N6vvQ==, + } fdir@6.4.6: - resolution: {integrity: sha512-hiFoqpyZcfNm1yc4u8oWCf9A2c4D3QjCrks3zmoVKVxpQRzmPNar1hUJcBG2RQHvEVGDN+Jm81ZheVLAQMK6+w==} + resolution: + { + integrity: sha512-hiFoqpyZcfNm1yc4u8oWCf9A2c4D3QjCrks3zmoVKVxpQRzmPNar1hUJcBG2RQHvEVGDN+Jm81ZheVLAQMK6+w==, + } peerDependencies: picomatch: ^3 || ^4 peerDependenciesMeta: @@ -2567,417 +4052,750 @@ packages: optional: true fetch-blob@3.2.0: - resolution: {integrity: sha512-7yAQpD2UMJzLi1Dqv7qFYnPbaPx7ZfFK6PiIxQ4PfkGPyNyl2Ugx+a/umUonmKqjhM4DnfbMvdX6otXq83soQQ==} - engines: {node: ^12.20 || >= 14.13} + resolution: + { + integrity: sha512-7yAQpD2UMJzLi1Dqv7qFYnPbaPx7ZfFK6PiIxQ4PfkGPyNyl2Ugx+a/umUonmKqjhM4DnfbMvdX6otXq83soQQ==, + } + engines: { node: ^12.20 || >= 14.13 } file-entry-cache@8.0.0: - resolution: {integrity: sha512-XXTUwCvisa5oacNGRP9SfNtYBNAMi+RPwBFmblZEF7N7swHYQS6/Zfk7SRwx4D5j3CH211YNRco1DEMNVfZCnQ==} - engines: {node: '>=16.0.0'} + resolution: + { + integrity: sha512-XXTUwCvisa5oacNGRP9SfNtYBNAMi+RPwBFmblZEF7N7swHYQS6/Zfk7SRwx4D5j3CH211YNRco1DEMNVfZCnQ==, + } + engines: { node: ">=16.0.0" } fill-range@7.1.1: - resolution: {integrity: sha512-YsGpe3WHLK8ZYi4tWDg2Jy3ebRz2rXowDxnld4bkQB00cc/1Zw9AWnC0i9ztDJitivtQvaI9KaLyKrc+hBW0yg==} - engines: {node: '>=8'} + resolution: + { + integrity: sha512-YsGpe3WHLK8ZYi4tWDg2Jy3ebRz2rXowDxnld4bkQB00cc/1Zw9AWnC0i9ztDJitivtQvaI9KaLyKrc+hBW0yg==, + } + engines: { node: ">=8" } find-up@5.0.0: - resolution: {integrity: sha512-78/PXT1wlLLDgTzDs7sjq9hzz0vXD+zn+7wypEe4fXQxCmdmqfGsEPQxmiCSQI3ajFV91bVSsvNtrJRiW6nGng==} - engines: {node: '>=10'} + resolution: + { + integrity: sha512-78/PXT1wlLLDgTzDs7sjq9hzz0vXD+zn+7wypEe4fXQxCmdmqfGsEPQxmiCSQI3ajFV91bVSsvNtrJRiW6nGng==, + } + engines: { node: ">=10" } flat-cache@4.0.1: - resolution: {integrity: sha512-f7ccFPK3SXFHpx15UIGyRJ/FJQctuKZ0zVuN3frBo4HnK3cay9VEW0R6yPYFHC0AgqhukPzKjq22t5DmAyqGyw==} - engines: {node: '>=16'} + resolution: + { + integrity: sha512-f7ccFPK3SXFHpx15UIGyRJ/FJQctuKZ0zVuN3frBo4HnK3cay9VEW0R6yPYFHC0AgqhukPzKjq22t5DmAyqGyw==, + } + engines: { node: ">=16" } flatted@3.3.3: - resolution: {integrity: sha512-GX+ysw4PBCz0PzosHDepZGANEuFCMLrnRTiEy9McGjmkCQYwRq4A/X786G/fjM/+OjsWSU1ZrY5qyARZmO/uwg==} + resolution: + { + integrity: sha512-GX+ysw4PBCz0PzosHDepZGANEuFCMLrnRTiEy9McGjmkCQYwRq4A/X786G/fjM/+OjsWSU1ZrY5qyARZmO/uwg==, + } for-each@0.3.5: - resolution: {integrity: sha512-dKx12eRCVIzqCxFGplyFKJMPvLEWgmNtUrpTiJIR5u97zEhRG8ySrtboPHZXx7daLxQVrl643cTzbab2tkQjxg==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-dKx12eRCVIzqCxFGplyFKJMPvLEWgmNtUrpTiJIR5u97zEhRG8ySrtboPHZXx7daLxQVrl643cTzbab2tkQjxg==, + } + engines: { node: ">= 0.4" } foreground-child@3.3.1: - resolution: {integrity: sha512-gIXjKqtFuWEgzFRJA9WCQeSJLZDjgJUOMCMzxtvFq/37KojM1BFGufqsCy0r4qSQmYLsZYMeyRqzIWOMup03sw==} - engines: {node: '>=14'} + resolution: + { + integrity: sha512-gIXjKqtFuWEgzFRJA9WCQeSJLZDjgJUOMCMzxtvFq/37KojM1BFGufqsCy0r4qSQmYLsZYMeyRqzIWOMup03sw==, + } + engines: { node: ">=14" } form-data@4.0.3: - resolution: {integrity: sha512-qsITQPfmvMOSAdeyZ+12I1c+CKSstAFAwu+97zrnWAbIr5u8wfsExUzCesVLC8NgHuRUqNN4Zy6UPWUTRGslcA==} - engines: {node: '>= 6'} + resolution: + { + integrity: sha512-qsITQPfmvMOSAdeyZ+12I1c+CKSstAFAwu+97zrnWAbIr5u8wfsExUzCesVLC8NgHuRUqNN4Zy6UPWUTRGslcA==, + } + engines: { node: ">= 6" } formdata-polyfill@4.0.10: - resolution: {integrity: sha512-buewHzMvYL29jdeQTVILecSaZKnt/RJWjoZCF5OW60Z67/GmSLBkOFM7qh1PI3zFNtJbaZL5eQu1vLfazOwj4g==} - engines: {node: '>=12.20.0'} + resolution: + { + integrity: sha512-buewHzMvYL29jdeQTVILecSaZKnt/RJWjoZCF5OW60Z67/GmSLBkOFM7qh1PI3zFNtJbaZL5eQu1vLfazOwj4g==, + } + engines: { node: ">=12.20.0" } fsevents@2.3.2: - resolution: {integrity: sha512-xiqMQR4xAeHTuB9uWm+fFRcIOgKBMiOBP+eXiyT7jsgVCq1bkVygt00oASowB7EdtpOHaaPgKt812P9ab+DDKA==} - engines: {node: ^8.16.0 || ^10.6.0 || >=11.0.0} + resolution: + { + integrity: sha512-xiqMQR4xAeHTuB9uWm+fFRcIOgKBMiOBP+eXiyT7jsgVCq1bkVygt00oASowB7EdtpOHaaPgKt812P9ab+DDKA==, + } + engines: { node: ^8.16.0 || ^10.6.0 || >=11.0.0 } os: [darwin] fsevents@2.3.3: - resolution: {integrity: sha512-5xoDfX+fL7faATnagmWPpbFtwh/R77WmMMqqHGS65C3vvB0YHrgF+B1YmZ3441tMj5n63k0212XNoJwzlhffQw==} - engines: {node: ^8.16.0 || ^10.6.0 || >=11.0.0} + resolution: + { + integrity: sha512-5xoDfX+fL7faATnagmWPpbFtwh/R77WmMMqqHGS65C3vvB0YHrgF+B1YmZ3441tMj5n63k0212XNoJwzlhffQw==, + } + engines: { node: ^8.16.0 || ^10.6.0 || >=11.0.0 } os: [darwin] function-bind@1.1.2: - resolution: {integrity: sha512-7XHNxH7qX9xG5mIwxkhumTox/MIRNcOgDrxWsMt2pAr23WHp6MrRlN7FBSFpCpr+oVO0F744iUgR82nJMfG2SA==} + resolution: + { + integrity: sha512-7XHNxH7qX9xG5mIwxkhumTox/MIRNcOgDrxWsMt2pAr23WHp6MrRlN7FBSFpCpr+oVO0F744iUgR82nJMfG2SA==, + } function.prototype.name@1.1.8: - resolution: {integrity: sha512-e5iwyodOHhbMr/yNrc7fDYG4qlbIvI5gajyzPnb5TCwyhjApznQh1BMFou9b30SevY43gCJKXycoCBjMbsuW0Q==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-e5iwyodOHhbMr/yNrc7fDYG4qlbIvI5gajyzPnb5TCwyhjApznQh1BMFou9b30SevY43gCJKXycoCBjMbsuW0Q==, + } + engines: { node: ">= 0.4" } functions-have-names@1.2.3: - resolution: {integrity: sha512-xckBUXyTIqT97tq2x2AMb+g163b5JFysYk0x4qxNFwbfQkmNZoiRHb6sPzI9/QV33WeuvVYBUIiD4NzNIyqaRQ==} + resolution: + { + integrity: sha512-xckBUXyTIqT97tq2x2AMb+g163b5JFysYk0x4qxNFwbfQkmNZoiRHb6sPzI9/QV33WeuvVYBUIiD4NzNIyqaRQ==, + } gensync@1.0.0-beta.2: - resolution: {integrity: sha512-3hN7NaskYvMDLQY55gnW3NQ+mesEAepTqlg+VEbj7zzqEMBVNhzcGYYeqFo/TlYz6eQiFcp1HcsCZO+nGgS8zg==} - engines: {node: '>=6.9.0'} + resolution: + { + integrity: sha512-3hN7NaskYvMDLQY55gnW3NQ+mesEAepTqlg+VEbj7zzqEMBVNhzcGYYeqFo/TlYz6eQiFcp1HcsCZO+nGgS8zg==, + } + engines: { node: ">=6.9.0" } get-intrinsic@1.3.0: - resolution: {integrity: sha512-9fSjSaos/fRIVIp+xSJlE6lfwhES7LNtKaCBIamHsjr2na1BiABJPo0mOjjz8GJDURarmCPGqaiVg5mfjb98CQ==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-9fSjSaos/fRIVIp+xSJlE6lfwhES7LNtKaCBIamHsjr2na1BiABJPo0mOjjz8GJDURarmCPGqaiVg5mfjb98CQ==, + } + engines: { node: ">= 0.4" } get-nonce@1.0.1: - resolution: {integrity: sha512-FJhYRoDaiatfEkUK8HKlicmu/3SGFD51q3itKDGoSTysQJBnfOcxU5GxnhE1E6soB76MbT0MBtnKJuXyAx+96Q==} - engines: {node: '>=6'} + resolution: + { + integrity: sha512-FJhYRoDaiatfEkUK8HKlicmu/3SGFD51q3itKDGoSTysQJBnfOcxU5GxnhE1E6soB76MbT0MBtnKJuXyAx+96Q==, + } + engines: { node: ">=6" } get-proto@1.0.1: - resolution: {integrity: sha512-sTSfBjoXBp89JvIKIefqw7U2CCebsc74kiY6awiGogKtoSGbgjYE/G/+l9sF3MWFPNc9IcoOC4ODfKHfxFmp0g==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-sTSfBjoXBp89JvIKIefqw7U2CCebsc74kiY6awiGogKtoSGbgjYE/G/+l9sF3MWFPNc9IcoOC4ODfKHfxFmp0g==, + } + engines: { node: ">= 0.4" } get-symbol-description@1.1.0: - resolution: {integrity: sha512-w9UMqWwJxHNOvoNzSJ2oPF5wvYcvP7jUvYzhp67yEhTi17ZDBBC1z9pTdGuzjD+EFIqLSYRweZjqfiPzQ06Ebg==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-w9UMqWwJxHNOvoNzSJ2oPF5wvYcvP7jUvYzhp67yEhTi17ZDBBC1z9pTdGuzjD+EFIqLSYRweZjqfiPzQ06Ebg==, + } + engines: { node: ">= 0.4" } get-tsconfig@4.10.1: - resolution: {integrity: sha512-auHyJ4AgMz7vgS8Hp3N6HXSmlMdUyhSUrfBF16w153rxtLIEOE+HGqaBppczZvnHLqQJfiHotCYpNhl0lUROFQ==} + resolution: + { + integrity: sha512-auHyJ4AgMz7vgS8Hp3N6HXSmlMdUyhSUrfBF16w153rxtLIEOE+HGqaBppczZvnHLqQJfiHotCYpNhl0lUROFQ==, + } glob-parent@5.1.2: - resolution: {integrity: sha512-AOIgSQCepiJYwP3ARnGx+5VnTu2HBYdzbGP45eLw1vr3zB3vZLeyed1sC9hnbcOc9/SrMyM5RPQrkGz4aS9Zow==} - engines: {node: '>= 6'} + resolution: + { + integrity: sha512-AOIgSQCepiJYwP3ARnGx+5VnTu2HBYdzbGP45eLw1vr3zB3vZLeyed1sC9hnbcOc9/SrMyM5RPQrkGz4aS9Zow==, + } + engines: { node: ">= 6" } glob-parent@6.0.2: - resolution: {integrity: sha512-XxwI8EOhVQgWp6iDL+3b0r86f4d6AX6zSU55HfB4ydCEuXLXc5FcYeOu+nnGftS4TEju/11rt4KJPTMgbfmv4A==} - engines: {node: '>=10.13.0'} + resolution: + { + integrity: sha512-XxwI8EOhVQgWp6iDL+3b0r86f4d6AX6zSU55HfB4ydCEuXLXc5FcYeOu+nnGftS4TEju/11rt4KJPTMgbfmv4A==, + } + engines: { node: ">=10.13.0" } glob@10.4.5: - resolution: {integrity: sha512-7Bv8RF0k6xjo7d4A/PxYLbUCfb6c+Vpd2/mB2yRDlew7Jb5hEXiCD9ibfO7wpk8i4sevK6DFny9h7EYbM3/sHg==} + resolution: + { + integrity: sha512-7Bv8RF0k6xjo7d4A/PxYLbUCfb6c+Vpd2/mB2yRDlew7Jb5hEXiCD9ibfO7wpk8i4sevK6DFny9h7EYbM3/sHg==, + } hasBin: true globals@11.12.0: - resolution: {integrity: sha512-WOBp/EEGUiIsJSp7wcv/y6MO+lV9UoncWqxuFfm8eBwzWNgyfBd6Gz+IeKQ9jCmyhoH99g15M3T+QaVHFjizVA==} - engines: {node: '>=4'} + resolution: + { + integrity: sha512-WOBp/EEGUiIsJSp7wcv/y6MO+lV9UoncWqxuFfm8eBwzWNgyfBd6Gz+IeKQ9jCmyhoH99g15M3T+QaVHFjizVA==, + } + engines: { node: ">=4" } globals@14.0.0: - resolution: {integrity: sha512-oahGvuMGQlPw/ivIYBjVSrWAfWLBeku5tpPE2fOPLi+WHffIWbuh2tCjhyQhTBPMf5E9jDEH4FOmTYgYwbKwtQ==} - engines: {node: '>=18'} + resolution: + { + integrity: sha512-oahGvuMGQlPw/ivIYBjVSrWAfWLBeku5tpPE2fOPLi+WHffIWbuh2tCjhyQhTBPMf5E9jDEH4FOmTYgYwbKwtQ==, + } + engines: { node: ">=18" } globalthis@1.0.4: - resolution: {integrity: sha512-DpLKbNU4WylpxJykQujfCcwYWiV/Jhm50Goo0wrVILAv5jOr9d+H+UR3PhSCD2rCCEIg0uc+G+muBTwD54JhDQ==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-DpLKbNU4WylpxJykQujfCcwYWiV/Jhm50Goo0wrVILAv5jOr9d+H+UR3PhSCD2rCCEIg0uc+G+muBTwD54JhDQ==, + } + engines: { node: ">= 0.4" } globby@14.1.0: - resolution: {integrity: sha512-0Ia46fDOaT7k4og1PDW4YbodWWr3scS2vAr2lTbsplOt2WkKp0vQbkI9wKis/T5LV/dqPjO3bpS/z6GTJB82LA==} - engines: {node: '>=18'} + resolution: + { + integrity: sha512-0Ia46fDOaT7k4og1PDW4YbodWWr3scS2vAr2lTbsplOt2WkKp0vQbkI9wKis/T5LV/dqPjO3bpS/z6GTJB82LA==, + } + engines: { node: ">=18" } globrex@0.1.2: - resolution: {integrity: sha512-uHJgbwAMwNFf5mLst7IWLNg14x1CkeqglJb/K3doi4dw6q2IvAAmM/Y81kevy83wP+Sst+nutFTYOGg3d1lsxg==} + resolution: + { + integrity: sha512-uHJgbwAMwNFf5mLst7IWLNg14x1CkeqglJb/K3doi4dw6q2IvAAmM/Y81kevy83wP+Sst+nutFTYOGg3d1lsxg==, + } gopd@1.2.0: - resolution: {integrity: sha512-ZUKRh6/kUFoAiTAtTYPZJ3hw9wNxx+BIBOijnlG9PnrJsCcSjs1wyyD6vJpaYtgnzDrKYRSqf3OO6Rfa93xsRg==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-ZUKRh6/kUFoAiTAtTYPZJ3hw9wNxx+BIBOijnlG9PnrJsCcSjs1wyyD6vJpaYtgnzDrKYRSqf3OO6Rfa93xsRg==, + } + engines: { node: ">= 0.4" } graceful-fs@4.2.11: - resolution: {integrity: sha512-RbJ5/jmFcNNCcDV5o9eTnBLJ/HszWV0P73bc+Ff4nS/rJj+YaS6IGyiOL0VoBYX+l1Wrl3k63h/KrH+nhJ0XvQ==} + resolution: + { + integrity: sha512-RbJ5/jmFcNNCcDV5o9eTnBLJ/HszWV0P73bc+Ff4nS/rJj+YaS6IGyiOL0VoBYX+l1Wrl3k63h/KrH+nhJ0XvQ==, + } graphemer@1.4.0: - resolution: {integrity: sha512-EtKwoO6kxCL9WO5xipiHTZlSzBm7WLT627TqC/uVRd0HKmq8NXyebnNYxDoBi7wt8eTWrUrKXCOVaFq9x1kgag==} + resolution: + { + integrity: sha512-EtKwoO6kxCL9WO5xipiHTZlSzBm7WLT627TqC/uVRd0HKmq8NXyebnNYxDoBi7wt8eTWrUrKXCOVaFq9x1kgag==, + } has-bigints@1.1.0: - resolution: {integrity: sha512-R3pbpkcIqv2Pm3dUwgjclDRVmWpTJW2DcMzcIhEXEx1oh/CEMObMm3KLmRJOdvhM7o4uQBnwr8pzRK2sJWIqfg==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-R3pbpkcIqv2Pm3dUwgjclDRVmWpTJW2DcMzcIhEXEx1oh/CEMObMm3KLmRJOdvhM7o4uQBnwr8pzRK2sJWIqfg==, + } + engines: { node: ">= 0.4" } has-flag@4.0.0: - resolution: {integrity: sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==} - engines: {node: '>=8'} + resolution: + { + integrity: sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==, + } + engines: { node: ">=8" } has-property-descriptors@1.0.2: - resolution: {integrity: sha512-55JNKuIW+vq4Ke1BjOTjM2YctQIvCT7GFzHwmfZPGo5wnrgkid0YQtnAleFSqumZm4az3n2BS+erby5ipJdgrg==} + resolution: + { + integrity: sha512-55JNKuIW+vq4Ke1BjOTjM2YctQIvCT7GFzHwmfZPGo5wnrgkid0YQtnAleFSqumZm4az3n2BS+erby5ipJdgrg==, + } has-proto@1.2.0: - resolution: {integrity: sha512-KIL7eQPfHQRC8+XluaIw7BHUwwqL19bQn4hzNgdr+1wXoU0KKj6rufu47lhY7KbJR2C6T6+PfyN0Ea7wkSS+qQ==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-KIL7eQPfHQRC8+XluaIw7BHUwwqL19bQn4hzNgdr+1wXoU0KKj6rufu47lhY7KbJR2C6T6+PfyN0Ea7wkSS+qQ==, + } + engines: { node: ">= 0.4" } has-symbols@1.1.0: - resolution: {integrity: sha512-1cDNdwJ2Jaohmb3sg4OmKaMBwuC48sYni5HUw2DvsC8LjGTLK9h+eb1X6RyuOHe4hT0ULCW68iomhjUoKUqlPQ==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-1cDNdwJ2Jaohmb3sg4OmKaMBwuC48sYni5HUw2DvsC8LjGTLK9h+eb1X6RyuOHe4hT0ULCW68iomhjUoKUqlPQ==, + } + engines: { node: ">= 0.4" } has-tostringtag@1.0.2: - resolution: {integrity: sha512-NqADB8VjPFLM2V0VvHUewwwsw0ZWBaIdgo+ieHtK3hasLz4qeCRjYcqfB6AQrBggRKppKF8L52/VqdVsO47Dlw==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-NqADB8VjPFLM2V0VvHUewwwsw0ZWBaIdgo+ieHtK3hasLz4qeCRjYcqfB6AQrBggRKppKF8L52/VqdVsO47Dlw==, + } + engines: { node: ">= 0.4" } hasown@2.0.2: - resolution: {integrity: sha512-0hJU9SCPvmMzIBdZFqNPXWa6dqh7WdH0cII9y+CyS8rG3nL48Bclra9HmKhVVUHyPWNH5Y7xDwAB7bfgSjkUMQ==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-0hJU9SCPvmMzIBdZFqNPXWa6dqh7WdH0cII9y+CyS8rG3nL48Bclra9HmKhVVUHyPWNH5Y7xDwAB7bfgSjkUMQ==, + } + engines: { node: ">= 0.4" } hast-util-from-parse5@8.0.3: - resolution: {integrity: sha512-3kxEVkEKt0zvcZ3hCRYI8rqrgwtlIOFMWkbclACvjlDw8Li9S2hk/d51OI0nr/gIpdMHNepwgOKqZ/sy0Clpyg==} + resolution: + { + integrity: sha512-3kxEVkEKt0zvcZ3hCRYI8rqrgwtlIOFMWkbclACvjlDw8Li9S2hk/d51OI0nr/gIpdMHNepwgOKqZ/sy0Clpyg==, + } hast-util-parse-selector@4.0.0: - resolution: {integrity: sha512-wkQCkSYoOGCRKERFWcxMVMOcYE2K1AaNLU8DXS9arxnLOUEWbOXKXiJUNzEpqZ3JOKpnha3jkFrumEjVliDe7A==} + resolution: + { + integrity: sha512-wkQCkSYoOGCRKERFWcxMVMOcYE2K1AaNLU8DXS9arxnLOUEWbOXKXiJUNzEpqZ3JOKpnha3jkFrumEjVliDe7A==, + } hast-util-raw@9.1.0: - resolution: {integrity: sha512-Y8/SBAHkZGoNkpzqqfCldijcuUKh7/su31kEBp67cFY09Wy0mTRgtsLYsiIxMJxlu0f6AA5SUTbDR8K0rxnbUw==} + resolution: + { + integrity: sha512-Y8/SBAHkZGoNkpzqqfCldijcuUKh7/su31kEBp67cFY09Wy0mTRgtsLYsiIxMJxlu0f6AA5SUTbDR8K0rxnbUw==, + } hast-util-to-jsx-runtime@2.3.6: - resolution: {integrity: sha512-zl6s8LwNyo1P9uw+XJGvZtdFF1GdAkOg8ujOw+4Pyb76874fLps4ueHXDhXWdk6YHQ6OgUtinliG7RsYvCbbBg==} + resolution: + { + integrity: sha512-zl6s8LwNyo1P9uw+XJGvZtdFF1GdAkOg8ujOw+4Pyb76874fLps4ueHXDhXWdk6YHQ6OgUtinliG7RsYvCbbBg==, + } hast-util-to-parse5@8.0.0: - resolution: {integrity: sha512-3KKrV5ZVI8if87DVSi1vDeByYrkGzg4mEfeu4alwgmmIeARiBLKCZS2uw5Gb6nU9x9Yufyj3iudm6i7nl52PFw==} + resolution: + { + integrity: sha512-3KKrV5ZVI8if87DVSi1vDeByYrkGzg4mEfeu4alwgmmIeARiBLKCZS2uw5Gb6nU9x9Yufyj3iudm6i7nl52PFw==, + } hast-util-whitespace@3.0.0: - resolution: {integrity: sha512-88JUN06ipLwsnv+dVn+OIYOvAuvBMy/Qoi6O7mQHxdPXpjy+Cd6xRkWwux7DKO+4sYILtLBRIKgsdpS2gQc7qw==} + resolution: + { + integrity: sha512-88JUN06ipLwsnv+dVn+OIYOvAuvBMy/Qoi6O7mQHxdPXpjy+Cd6xRkWwux7DKO+4sYILtLBRIKgsdpS2gQc7qw==, + } hastscript@9.0.1: - resolution: {integrity: sha512-g7df9rMFX/SPi34tyGCyUBREQoKkapwdY/T04Qn9TDWfHhAYt4/I0gMVirzK5wEzeUqIjEB+LXC/ypb7Aqno5w==} + resolution: + { + integrity: sha512-g7df9rMFX/SPi34tyGCyUBREQoKkapwdY/T04Qn9TDWfHhAYt4/I0gMVirzK5wEzeUqIjEB+LXC/ypb7Aqno5w==, + } html-encoding-sniffer@4.0.0: - resolution: {integrity: sha512-Y22oTqIU4uuPgEemfz7NDJz6OeKf12Lsu+QC+s3BVpda64lTiMYCyGwg5ki4vFxkMwQdeZDl2adZoqUgdFuTgQ==} - engines: {node: '>=18'} + resolution: + { + integrity: sha512-Y22oTqIU4uuPgEemfz7NDJz6OeKf12Lsu+QC+s3BVpda64lTiMYCyGwg5ki4vFxkMwQdeZDl2adZoqUgdFuTgQ==, + } + engines: { node: ">=18" } html-escaper@2.0.2: - resolution: {integrity: sha512-H2iMtd0I4Mt5eYiapRdIDjp+XzelXQ0tFE4JS7YFwFevXXMmOp9myNrUvCg0D6ws8iqkRPBfKHgbwig1SmlLfg==} + resolution: + { + integrity: sha512-H2iMtd0I4Mt5eYiapRdIDjp+XzelXQ0tFE4JS7YFwFevXXMmOp9myNrUvCg0D6ws8iqkRPBfKHgbwig1SmlLfg==, + } html-url-attributes@3.0.1: - resolution: {integrity: sha512-ol6UPyBWqsrO6EJySPz2O7ZSr856WDrEzM5zMqp+FJJLGMW35cLYmmZnl0vztAZxRUoNZJFTCohfjuIJ8I4QBQ==} + resolution: + { + integrity: sha512-ol6UPyBWqsrO6EJySPz2O7ZSr856WDrEzM5zMqp+FJJLGMW35cLYmmZnl0vztAZxRUoNZJFTCohfjuIJ8I4QBQ==, + } html-void-elements@3.0.0: - resolution: {integrity: sha512-bEqo66MRXsUGxWHV5IP0PUiAWwoEjba4VCzg0LjFJBpchPaTfyfCKTG6bc5F8ucKec3q5y6qOdGyYTSBEvhCrg==} + resolution: + { + integrity: sha512-bEqo66MRXsUGxWHV5IP0PUiAWwoEjba4VCzg0LjFJBpchPaTfyfCKTG6bc5F8ucKec3q5y6qOdGyYTSBEvhCrg==, + } http-proxy-agent@7.0.2: - resolution: {integrity: sha512-T1gkAiYYDWYx3V5Bmyu7HcfcvL7mUrTWiM6yOfa3PIphViJ/gFPbvidQ+veqSOHci/PxBcDabeUNCzpOODJZig==} - engines: {node: '>= 14'} + resolution: + { + integrity: sha512-T1gkAiYYDWYx3V5Bmyu7HcfcvL7mUrTWiM6yOfa3PIphViJ/gFPbvidQ+veqSOHci/PxBcDabeUNCzpOODJZig==, + } + engines: { node: ">= 14" } https-proxy-agent@7.0.6: - resolution: {integrity: sha512-vK9P5/iUfdl95AI+JVyUuIcVtd4ofvtrOr3HNtM2yxC9bnMbEdp3x01OhQNnjb8IJYi38VlTE3mBXwcfvywuSw==} - engines: {node: '>= 14'} + resolution: + { + integrity: sha512-vK9P5/iUfdl95AI+JVyUuIcVtd4ofvtrOr3HNtM2yxC9bnMbEdp3x01OhQNnjb8IJYi38VlTE3mBXwcfvywuSw==, + } + engines: { node: ">= 14" } i18n-iso-countries@7.14.0: - resolution: {integrity: sha512-nXHJZYtNrfsi1UQbyRqm3Gou431elgLjKl//CYlnBGt5aTWdRPH1PiS2T/p/n8Q8LnqYqzQJik3Q7mkwvLokeg==} - engines: {node: '>= 12'} + resolution: + { + integrity: sha512-nXHJZYtNrfsi1UQbyRqm3Gou431elgLjKl//CYlnBGt5aTWdRPH1PiS2T/p/n8Q8LnqYqzQJik3Q7mkwvLokeg==, + } + engines: { node: ">= 12" } iconv-lite@0.6.3: - resolution: {integrity: sha512-4fCk79wshMdzMp2rH06qWrJE4iolqLhCUH+OiuIgU++RB0+94NlDL81atO7GX55uUKueo0txHNtvEyI6D7WdMw==} - engines: {node: '>=0.10.0'} + resolution: + { + integrity: sha512-4fCk79wshMdzMp2rH06qWrJE4iolqLhCUH+OiuIgU++RB0+94NlDL81atO7GX55uUKueo0txHNtvEyI6D7WdMw==, + } + engines: { node: ">=0.10.0" } ignore@5.3.2: - resolution: {integrity: sha512-hsBTNUqQTDwkWtcdYI2i06Y/nUBEsNEDJKjWdigLvegy8kDuJAS8uRlpkkcQpyEXL0Z/pjDy5HBmMjRCJ2gq+g==} - engines: {node: '>= 4'} + resolution: + { + integrity: sha512-hsBTNUqQTDwkWtcdYI2i06Y/nUBEsNEDJKjWdigLvegy8kDuJAS8uRlpkkcQpyEXL0Z/pjDy5HBmMjRCJ2gq+g==, + } + engines: { node: ">= 4" } ignore@7.0.5: - resolution: {integrity: sha512-Hs59xBNfUIunMFgWAbGX5cq6893IbWg4KnrjbYwX3tx0ztorVgTDA6B2sxf8ejHJ4wz8BqGUMYlnzNBer5NvGg==} - engines: {node: '>= 4'} + resolution: + { + integrity: sha512-Hs59xBNfUIunMFgWAbGX5cq6893IbWg4KnrjbYwX3tx0ztorVgTDA6B2sxf8ejHJ4wz8BqGUMYlnzNBer5NvGg==, + } + engines: { node: ">= 4" } immer@10.1.1: - resolution: {integrity: sha512-s2MPrmjovJcoMaHtx6K11Ra7oD05NT97w1IC5zpMkT6Atjr7H8LjaDd81iIxUYpMKSRRNMJE703M1Fhr/TctHw==} + resolution: + { + integrity: sha512-s2MPrmjovJcoMaHtx6K11Ra7oD05NT97w1IC5zpMkT6Atjr7H8LjaDd81iIxUYpMKSRRNMJE703M1Fhr/TctHw==, + } import-fresh@3.3.1: - resolution: {integrity: sha512-TR3KfrTZTYLPB6jUjfx6MF9WcWrHL9su5TObK4ZkYgBdWKPOFoSoQIdEuTuR82pmtxH2spWG9h6etwfr1pLBqQ==} - engines: {node: '>=6'} + resolution: + { + integrity: sha512-TR3KfrTZTYLPB6jUjfx6MF9WcWrHL9su5TObK4ZkYgBdWKPOFoSoQIdEuTuR82pmtxH2spWG9h6etwfr1pLBqQ==, + } + engines: { node: ">=6" } imurmurhash@0.1.4: - resolution: {integrity: sha512-JmXMZ6wuvDmLiHEml9ykzqO6lwFbof0GG4IkcGaENdCRDDmMVnny7s5HsIgHCbaq0w2MyPhDqkhTUgS2LU2PHA==} - engines: {node: '>=0.8.19'} + resolution: + { + integrity: sha512-JmXMZ6wuvDmLiHEml9ykzqO6lwFbof0GG4IkcGaENdCRDDmMVnny7s5HsIgHCbaq0w2MyPhDqkhTUgS2LU2PHA==, + } + engines: { node: ">=0.8.19" } inline-style-parser@0.2.4: - resolution: {integrity: sha512-0aO8FkhNZlj/ZIbNi7Lxxr12obT7cL1moPfE4tg1LkX7LlLfC6DeX4l2ZEud1ukP9jNQyNnfzQVqwbwmAATY4Q==} + resolution: + { + integrity: sha512-0aO8FkhNZlj/ZIbNi7Lxxr12obT7cL1moPfE4tg1LkX7LlLfC6DeX4l2ZEud1ukP9jNQyNnfzQVqwbwmAATY4Q==, + } internal-slot@1.1.0: - resolution: {integrity: sha512-4gd7VpWNQNB4UKKCFFVcp1AVv+FMOgs9NKzjHKusc8jTMhd5eL1NqQqOpE0KzMds804/yHlglp3uxgluOqAPLw==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-4gd7VpWNQNB4UKKCFFVcp1AVv+FMOgs9NKzjHKusc8jTMhd5eL1NqQqOpE0KzMds804/yHlglp3uxgluOqAPLw==, + } + engines: { node: ">= 0.4" } internmap@2.0.3: - resolution: {integrity: sha512-5Hh7Y1wQbvY5ooGgPbDaL5iYLAPzMTUrjMulskHLH6wnv/A+1q5rgEaiuqEjB+oxGXIVZs1FF+R/KPN3ZSQYYg==} - engines: {node: '>=12'} + resolution: + { + integrity: sha512-5Hh7Y1wQbvY5ooGgPbDaL5iYLAPzMTUrjMulskHLH6wnv/A+1q5rgEaiuqEjB+oxGXIVZs1FF+R/KPN3ZSQYYg==, + } + engines: { node: ">=12" } is-alphabetical@2.0.1: - resolution: {integrity: sha512-FWyyY60MeTNyeSRpkM2Iry0G9hpr7/9kD40mD/cGQEuilcZYS4okz8SN2Q6rLCJ8gbCt6fN+rC+6tMGS99LaxQ==} + resolution: + { + integrity: sha512-FWyyY60MeTNyeSRpkM2Iry0G9hpr7/9kD40mD/cGQEuilcZYS4okz8SN2Q6rLCJ8gbCt6fN+rC+6tMGS99LaxQ==, + } is-alphanumerical@2.0.1: - resolution: {integrity: sha512-hmbYhX/9MUMF5uh7tOXyK/n0ZvWpad5caBA17GsC6vyuCqaWliRG5K1qS9inmUhEMaOBIW7/whAnSwveW/LtZw==} + resolution: + { + integrity: sha512-hmbYhX/9MUMF5uh7tOXyK/n0ZvWpad5caBA17GsC6vyuCqaWliRG5K1qS9inmUhEMaOBIW7/whAnSwveW/LtZw==, + } is-array-buffer@3.0.5: - resolution: {integrity: sha512-DDfANUiiG2wC1qawP66qlTugJeL5HyzMpfr8lLK+jMQirGzNod0B12cFB/9q838Ru27sBwfw78/rdoU7RERz6A==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-DDfANUiiG2wC1qawP66qlTugJeL5HyzMpfr8lLK+jMQirGzNod0B12cFB/9q838Ru27sBwfw78/rdoU7RERz6A==, + } + engines: { node: ">= 0.4" } is-arrayish@0.3.2: - resolution: {integrity: sha512-eVRqCvVlZbuw3GrM63ovNSNAeA1K16kaR/LRY/92w0zxQ5/1YzwblUX652i4Xs9RwAGjW9d9y6X88t8OaAJfWQ==} + resolution: + { + integrity: sha512-eVRqCvVlZbuw3GrM63ovNSNAeA1K16kaR/LRY/92w0zxQ5/1YzwblUX652i4Xs9RwAGjW9d9y6X88t8OaAJfWQ==, + } is-async-function@2.1.1: - resolution: {integrity: sha512-9dgM/cZBnNvjzaMYHVoxxfPj2QXt22Ev7SuuPrs+xav0ukGB0S6d4ydZdEiM48kLx5kDV+QBPrpVnFyefL8kkQ==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-9dgM/cZBnNvjzaMYHVoxxfPj2QXt22Ev7SuuPrs+xav0ukGB0S6d4ydZdEiM48kLx5kDV+QBPrpVnFyefL8kkQ==, + } + engines: { node: ">= 0.4" } is-bigint@1.1.0: - resolution: {integrity: sha512-n4ZT37wG78iz03xPRKJrHTdZbe3IicyucEtdRsV5yglwc3GyUfbAfpSeD0FJ41NbUNSt5wbhqfp1fS+BgnvDFQ==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-n4ZT37wG78iz03xPRKJrHTdZbe3IicyucEtdRsV5yglwc3GyUfbAfpSeD0FJ41NbUNSt5wbhqfp1fS+BgnvDFQ==, + } + engines: { node: ">= 0.4" } is-boolean-object@1.2.2: - resolution: {integrity: sha512-wa56o2/ElJMYqjCjGkXri7it5FbebW5usLw/nPmCMs5DeZ7eziSYZhSmPRn0txqeW4LnAmQQU7FgqLpsEFKM4A==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-wa56o2/ElJMYqjCjGkXri7it5FbebW5usLw/nPmCMs5DeZ7eziSYZhSmPRn0txqeW4LnAmQQU7FgqLpsEFKM4A==, + } + engines: { node: ">= 0.4" } is-bun-module@2.0.0: - resolution: {integrity: sha512-gNCGbnnnnFAUGKeZ9PdbyeGYJqewpmc2aKHUEMO5nQPWU9lOmv7jcmQIv+qHD8fXW6W7qfuCwX4rY9LNRjXrkQ==} + resolution: + { + integrity: sha512-gNCGbnnnnFAUGKeZ9PdbyeGYJqewpmc2aKHUEMO5nQPWU9lOmv7jcmQIv+qHD8fXW6W7qfuCwX4rY9LNRjXrkQ==, + } is-callable@1.2.7: - resolution: {integrity: sha512-1BC0BVFhS/p0qtw6enp8e+8OD0UrK0oFLztSjNzhcKA3WDuJxxAPXzPuPtKkjEY9UUoEWlX/8fgKeu2S8i9JTA==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-1BC0BVFhS/p0qtw6enp8e+8OD0UrK0oFLztSjNzhcKA3WDuJxxAPXzPuPtKkjEY9UUoEWlX/8fgKeu2S8i9JTA==, + } + engines: { node: ">= 0.4" } is-core-module@2.16.1: - resolution: {integrity: sha512-UfoeMA6fIJ8wTYFEUjelnaGI67v6+N7qXJEvQuIGa99l4xsCruSYOVSQ0uPANn4dAzm8lkYPaKLrrijLq7x23w==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-UfoeMA6fIJ8wTYFEUjelnaGI67v6+N7qXJEvQuIGa99l4xsCruSYOVSQ0uPANn4dAzm8lkYPaKLrrijLq7x23w==, + } + engines: { node: ">= 0.4" } is-data-view@1.0.2: - resolution: {integrity: sha512-RKtWF8pGmS87i2D6gqQu/l7EYRlVdfzemCJN/P3UOs//x1QE7mfhvzHIApBTRf7axvT6DMGwSwBXYCT0nfB9xw==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-RKtWF8pGmS87i2D6gqQu/l7EYRlVdfzemCJN/P3UOs//x1QE7mfhvzHIApBTRf7axvT6DMGwSwBXYCT0nfB9xw==, + } + engines: { node: ">= 0.4" } is-date-object@1.1.0: - resolution: {integrity: sha512-PwwhEakHVKTdRNVOw+/Gyh0+MzlCl4R6qKvkhuvLtPMggI1WAHt9sOwZxQLSGpUaDnrdyDsomoRgNnCfKNSXXg==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-PwwhEakHVKTdRNVOw+/Gyh0+MzlCl4R6qKvkhuvLtPMggI1WAHt9sOwZxQLSGpUaDnrdyDsomoRgNnCfKNSXXg==, + } + engines: { node: ">= 0.4" } is-decimal@2.0.1: - resolution: {integrity: sha512-AAB9hiomQs5DXWcRB1rqsxGUstbRroFOPPVAomNk/3XHR5JyEZChOyTWe2oayKnsSsr/kcGqF+z6yuH6HHpN0A==} + resolution: + { + integrity: sha512-AAB9hiomQs5DXWcRB1rqsxGUstbRroFOPPVAomNk/3XHR5JyEZChOyTWe2oayKnsSsr/kcGqF+z6yuH6HHpN0A==, + } is-extglob@2.1.1: - resolution: {integrity: sha512-SbKbANkN603Vi4jEZv49LeVJMn4yGwsbzZworEoyEiutsN3nJYdbO36zfhGJ6QEDpOZIFkDtnq5JRxmvl3jsoQ==} - engines: {node: '>=0.10.0'} + resolution: + { + integrity: sha512-SbKbANkN603Vi4jEZv49LeVJMn4yGwsbzZworEoyEiutsN3nJYdbO36zfhGJ6QEDpOZIFkDtnq5JRxmvl3jsoQ==, + } + engines: { node: ">=0.10.0" } is-finalizationregistry@1.1.1: - resolution: {integrity: sha512-1pC6N8qWJbWoPtEjgcL2xyhQOP491EQjeUo3qTKcmV8YSDDJrOepfG8pcC7h/QgnQHYSv0mJ3Z/ZWxmatVrysg==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-1pC6N8qWJbWoPtEjgcL2xyhQOP491EQjeUo3qTKcmV8YSDDJrOepfG8pcC7h/QgnQHYSv0mJ3Z/ZWxmatVrysg==, + } + engines: { node: ">= 0.4" } is-fullwidth-code-point@3.0.0: - resolution: {integrity: sha512-zymm5+u+sCsSWyD9qNaejV3DFvhCKclKdizYaJUuHA83RLjb7nSuGnddCHGv0hk+KY7BMAlsWeK4Ueg6EV6XQg==} - engines: {node: '>=8'} + resolution: + { + integrity: sha512-zymm5+u+sCsSWyD9qNaejV3DFvhCKclKdizYaJUuHA83RLjb7nSuGnddCHGv0hk+KY7BMAlsWeK4Ueg6EV6XQg==, + } + engines: { node: ">=8" } is-generator-function@1.1.0: - resolution: {integrity: sha512-nPUB5km40q9e8UfN/Zc24eLlzdSf9OfKByBw9CIdw4H1giPMeA0OIJvbchsCu4npfI2QcMVBsGEBHKZ7wLTWmQ==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-nPUB5km40q9e8UfN/Zc24eLlzdSf9OfKByBw9CIdw4H1giPMeA0OIJvbchsCu4npfI2QcMVBsGEBHKZ7wLTWmQ==, + } + engines: { node: ">= 0.4" } is-glob@4.0.3: - resolution: {integrity: sha512-xelSayHH36ZgE7ZWhli7pW34hNbNl8Ojv5KVmkJD4hBdD3th8Tfk9vYasLM+mXWOZhFkgZfxhLSnrwRr4elSSg==} - engines: {node: '>=0.10.0'} + resolution: + { + integrity: sha512-xelSayHH36ZgE7ZWhli7pW34hNbNl8Ojv5KVmkJD4hBdD3th8Tfk9vYasLM+mXWOZhFkgZfxhLSnrwRr4elSSg==, + } + engines: { node: ">=0.10.0" } is-hexadecimal@2.0.1: - resolution: {integrity: sha512-DgZQp241c8oO6cA1SbTEWiXeoxV42vlcJxgH+B3hi1AiqqKruZR3ZGF8In3fj4+/y/7rHvlOZLZtgJ/4ttYGZg==} + resolution: + { + integrity: sha512-DgZQp241c8oO6cA1SbTEWiXeoxV42vlcJxgH+B3hi1AiqqKruZR3ZGF8In3fj4+/y/7rHvlOZLZtgJ/4ttYGZg==, + } is-map@2.0.3: - resolution: {integrity: sha512-1Qed0/Hr2m+YqxnM09CjA2d/i6YZNfF6R2oRAOj36eUdS6qIV/huPJNSEpKbupewFs+ZsJlxsjjPbc0/afW6Lw==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-1Qed0/Hr2m+YqxnM09CjA2d/i6YZNfF6R2oRAOj36eUdS6qIV/huPJNSEpKbupewFs+ZsJlxsjjPbc0/afW6Lw==, + } + engines: { node: ">= 0.4" } is-negative-zero@2.0.3: - resolution: {integrity: sha512-5KoIu2Ngpyek75jXodFvnafB6DJgr3u8uuK0LEZJjrU19DrMD3EVERaR8sjz8CCGgpZvxPl9SuE1GMVPFHx1mw==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-5KoIu2Ngpyek75jXodFvnafB6DJgr3u8uuK0LEZJjrU19DrMD3EVERaR8sjz8CCGgpZvxPl9SuE1GMVPFHx1mw==, + } + engines: { node: ">= 0.4" } is-number-object@1.1.1: - resolution: {integrity: sha512-lZhclumE1G6VYD8VHe35wFaIif+CTy5SJIi5+3y4psDgWu4wPDoBhF8NxUOinEc7pHgiTsT6MaBb92rKhhD+Xw==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-lZhclumE1G6VYD8VHe35wFaIif+CTy5SJIi5+3y4psDgWu4wPDoBhF8NxUOinEc7pHgiTsT6MaBb92rKhhD+Xw==, + } + engines: { node: ">= 0.4" } is-number@7.0.0: - resolution: {integrity: sha512-41Cifkg6e8TylSpdtTpeLVMqvSBEVzTttHvERD741+pnZ8ANv0004MRL43QKPDlK9cGvNp6NZWZUBlbGXYxxng==} - engines: {node: '>=0.12.0'} + resolution: + { + integrity: sha512-41Cifkg6e8TylSpdtTpeLVMqvSBEVzTttHvERD741+pnZ8ANv0004MRL43QKPDlK9cGvNp6NZWZUBlbGXYxxng==, + } + engines: { node: ">=0.12.0" } is-plain-obj@4.1.0: - resolution: {integrity: sha512-+Pgi+vMuUNkJyExiMBt5IlFoMyKnr5zhJ4Uspz58WOhBF5QoIZkFyNHIbBAtHwzVAgk5RtndVNsDRN61/mmDqg==} - engines: {node: '>=12'} + resolution: + { + integrity: sha512-+Pgi+vMuUNkJyExiMBt5IlFoMyKnr5zhJ4Uspz58WOhBF5QoIZkFyNHIbBAtHwzVAgk5RtndVNsDRN61/mmDqg==, + } + engines: { node: ">=12" } is-potential-custom-element-name@1.0.1: - resolution: {integrity: sha512-bCYeRA2rVibKZd+s2625gGnGF/t7DSqDs4dP7CrLA1m7jKWz6pps0LpYLJN8Q64HtmPKJ1hrN3nzPNKFEKOUiQ==} + resolution: + { + integrity: sha512-bCYeRA2rVibKZd+s2625gGnGF/t7DSqDs4dP7CrLA1m7jKWz6pps0LpYLJN8Q64HtmPKJ1hrN3nzPNKFEKOUiQ==, + } is-regex@1.2.1: - resolution: {integrity: sha512-MjYsKHO5O7mCsmRGxWcLWheFqN9DJ/2TmngvjKXihe6efViPqc274+Fx/4fYj/r03+ESvBdTXK0V6tA3rgez1g==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-MjYsKHO5O7mCsmRGxWcLWheFqN9DJ/2TmngvjKXihe6efViPqc274+Fx/4fYj/r03+ESvBdTXK0V6tA3rgez1g==, + } + engines: { node: ">= 0.4" } is-set@2.0.3: - resolution: {integrity: sha512-iPAjerrse27/ygGLxw+EBR9agv9Y6uLeYVJMu+QNCoouJ1/1ri0mGrcWpfCqFZuzzx3WjtwxG098X+n4OuRkPg==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-iPAjerrse27/ygGLxw+EBR9agv9Y6uLeYVJMu+QNCoouJ1/1ri0mGrcWpfCqFZuzzx3WjtwxG098X+n4OuRkPg==, + } + engines: { node: ">= 0.4" } is-shared-array-buffer@1.0.4: - resolution: {integrity: sha512-ISWac8drv4ZGfwKl5slpHG9OwPNty4jOWPRIhBpxOoD+hqITiwuipOQ2bNthAzwA3B4fIjO4Nln74N0S9byq8A==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-ISWac8drv4ZGfwKl5slpHG9OwPNty4jOWPRIhBpxOoD+hqITiwuipOQ2bNthAzwA3B4fIjO4Nln74N0S9byq8A==, + } + engines: { node: ">= 0.4" } is-string@1.1.1: - resolution: {integrity: sha512-BtEeSsoaQjlSPBemMQIrY1MY0uM6vnS1g5fmufYOtnxLGUZM2178PKbhsk7Ffv58IX+ZtcvoGwccYsh0PglkAA==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-BtEeSsoaQjlSPBemMQIrY1MY0uM6vnS1g5fmufYOtnxLGUZM2178PKbhsk7Ffv58IX+ZtcvoGwccYsh0PglkAA==, + } + engines: { node: ">= 0.4" } is-symbol@1.1.1: - resolution: {integrity: sha512-9gGx6GTtCQM73BgmHQXfDmLtfjjTUDSyoxTCbp5WtoixAhfgsDirWIcVQ/IHpvI5Vgd5i/J5F7B9cN/WlVbC/w==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-9gGx6GTtCQM73BgmHQXfDmLtfjjTUDSyoxTCbp5WtoixAhfgsDirWIcVQ/IHpvI5Vgd5i/J5F7B9cN/WlVbC/w==, + } + engines: { node: ">= 0.4" } is-typed-array@1.1.15: - resolution: {integrity: sha512-p3EcsicXjit7SaskXHs1hA91QxgTw46Fv6EFKKGS5DRFLD8yKnohjF3hxoju94b/OcMZoQukzpPpBE9uLVKzgQ==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-p3EcsicXjit7SaskXHs1hA91QxgTw46Fv6EFKKGS5DRFLD8yKnohjF3hxoju94b/OcMZoQukzpPpBE9uLVKzgQ==, + } + engines: { node: ">= 0.4" } is-weakmap@2.0.2: - resolution: {integrity: sha512-K5pXYOm9wqY1RgjpL3YTkF39tni1XajUIkawTLUo9EZEVUFga5gSQJF8nNS7ZwJQ02y+1YCNYcMh+HIf1ZqE+w==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-K5pXYOm9wqY1RgjpL3YTkF39tni1XajUIkawTLUo9EZEVUFga5gSQJF8nNS7ZwJQ02y+1YCNYcMh+HIf1ZqE+w==, + } + engines: { node: ">= 0.4" } is-weakref@1.1.1: - resolution: {integrity: sha512-6i9mGWSlqzNMEqpCp93KwRS1uUOodk2OJ6b+sq7ZPDSy2WuI5NFIxp/254TytR8ftefexkWn5xNiHUNpPOfSew==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-6i9mGWSlqzNMEqpCp93KwRS1uUOodk2OJ6b+sq7ZPDSy2WuI5NFIxp/254TytR8ftefexkWn5xNiHUNpPOfSew==, + } + engines: { node: ">= 0.4" } is-weakset@2.0.4: - resolution: {integrity: sha512-mfcwb6IzQyOKTs84CQMrOwW4gQcaTOAWJ0zzJCl2WSPDrWk/OzDaImWFH3djXhb24g4eudZfLRozAvPGw4d9hQ==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-mfcwb6IzQyOKTs84CQMrOwW4gQcaTOAWJ0zzJCl2WSPDrWk/OzDaImWFH3djXhb24g4eudZfLRozAvPGw4d9hQ==, + } + engines: { node: ">= 0.4" } isarray@2.0.5: - resolution: {integrity: sha512-xHjhDr3cNBK0BzdUJSPXZntQUx/mwMS5Rw4A7lPJ90XGAO6ISP/ePDNuo0vhqOZU+UD5JoodwCAAoZQd3FeAKw==} + resolution: + { + integrity: sha512-xHjhDr3cNBK0BzdUJSPXZntQUx/mwMS5Rw4A7lPJ90XGAO6ISP/ePDNuo0vhqOZU+UD5JoodwCAAoZQd3FeAKw==, + } isexe@2.0.0: - resolution: {integrity: sha512-RHxMLp9lnKHGHRng9QFhRCMbYAcVpn69smSGcq3f36xjgVVWThj4qqLbTLlq7Ssj8B+fIQ1EuCEGI2lKsyQeIw==} + resolution: + { + integrity: sha512-RHxMLp9lnKHGHRng9QFhRCMbYAcVpn69smSGcq3f36xjgVVWThj4qqLbTLlq7Ssj8B+fIQ1EuCEGI2lKsyQeIw==, + } iso-639-1@3.1.5: - resolution: {integrity: sha512-gXkz5+KN7HrG0Q5UGqSMO2qB9AsbEeyLP54kF1YrMsIxmu+g4BdB7rflReZTSTZGpfj8wywu6pfPBCylPIzGQA==} - engines: {node: '>=6.0'} + resolution: + { + integrity: sha512-gXkz5+KN7HrG0Q5UGqSMO2qB9AsbEeyLP54kF1YrMsIxmu+g4BdB7rflReZTSTZGpfj8wywu6pfPBCylPIzGQA==, + } + engines: { node: ">=6.0" } istanbul-lib-coverage@3.2.2: - resolution: {integrity: sha512-O8dpsF+r0WV/8MNRKfnmrtCWhuKjxrq2w+jpzBL5UZKTi2LeVWnWOmWRxFlesJONmc+wLAGvKQZEOanko0LFTg==} - engines: {node: '>=8'} + resolution: + { + integrity: sha512-O8dpsF+r0WV/8MNRKfnmrtCWhuKjxrq2w+jpzBL5UZKTi2LeVWnWOmWRxFlesJONmc+wLAGvKQZEOanko0LFTg==, + } + engines: { node: ">=8" } istanbul-lib-report@3.0.1: - resolution: {integrity: sha512-GCfE1mtsHGOELCU8e/Z7YWzpmybrx/+dSTfLrvY8qRmaY6zXTKWn6WQIjaAFw069icm6GVMNkgu0NzI4iPZUNw==} - engines: {node: '>=10'} + resolution: + { + integrity: sha512-GCfE1mtsHGOELCU8e/Z7YWzpmybrx/+dSTfLrvY8qRmaY6zXTKWn6WQIjaAFw069icm6GVMNkgu0NzI4iPZUNw==, + } + engines: { node: ">=10" } istanbul-lib-source-maps@5.0.6: - resolution: {integrity: sha512-yg2d+Em4KizZC5niWhQaIomgf5WlL4vOOjZ5xGCmF8SnPE/mDWWXgvRExdcpCgh9lLRRa1/fSYp2ymmbJ1pI+A==} - engines: {node: '>=10'} + resolution: + { + integrity: sha512-yg2d+Em4KizZC5niWhQaIomgf5WlL4vOOjZ5xGCmF8SnPE/mDWWXgvRExdcpCgh9lLRRa1/fSYp2ymmbJ1pI+A==, + } + engines: { node: ">=10" } istanbul-reports@3.1.7: - resolution: {integrity: sha512-BewmUXImeuRk2YY0PVbxgKAysvhRPUQE0h5QRM++nVWyubKGV0l8qQ5op8+B2DOmwSe63Jivj0BjkPQVf8fP5g==} - engines: {node: '>=8'} + resolution: + { + integrity: sha512-BewmUXImeuRk2YY0PVbxgKAysvhRPUQE0h5QRM++nVWyubKGV0l8qQ5op8+B2DOmwSe63Jivj0BjkPQVf8fP5g==, + } + engines: { node: ">=8" } iterator.prototype@1.1.5: - resolution: {integrity: sha512-H0dkQoCa3b2VEeKQBOxFph+JAbcrQdE7KC0UkqwpLmv2EC4P41QXP+rqo9wYodACiG5/WM5s9oDApTU8utwj9g==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-H0dkQoCa3b2VEeKQBOxFph+JAbcrQdE7KC0UkqwpLmv2EC4P41QXP+rqo9wYodACiG5/WM5s9oDApTU8utwj9g==, + } + engines: { node: ">= 0.4" } jackspeak@3.4.3: - resolution: {integrity: sha512-OGlZQpz2yfahA/Rd1Y8Cd9SIEsqvXkLVoSw/cgwhnhFMDbsQFeZYoJJ7bIZBS9BcamUW96asq/npPWugM+RQBw==} + resolution: + { + integrity: sha512-OGlZQpz2yfahA/Rd1Y8Cd9SIEsqvXkLVoSw/cgwhnhFMDbsQFeZYoJJ7bIZBS9BcamUW96asq/npPWugM+RQBw==, + } jiti@2.4.2: - resolution: {integrity: sha512-rg9zJN+G4n2nfJl5MW3BMygZX56zKPNVEYYqq7adpmMh4Jn2QNEwhvQlFy6jPVdcod7txZtKHWnyZiA3a0zP7A==} + resolution: + { + integrity: sha512-rg9zJN+G4n2nfJl5MW3BMygZX56zKPNVEYYqq7adpmMh4Jn2QNEwhvQlFy6jPVdcod7txZtKHWnyZiA3a0zP7A==, + } hasBin: true jose@4.15.9: - resolution: {integrity: sha512-1vUQX+IdDMVPj4k8kOxgUqlcK518yluMuGZwqlr44FS1ppZB/5GWh4rZG89erpOBOJjU/OBsnCVFfapsRz6nEA==} + resolution: + { + integrity: sha512-1vUQX+IdDMVPj4k8kOxgUqlcK518yluMuGZwqlr44FS1ppZB/5GWh4rZG89erpOBOJjU/OBsnCVFfapsRz6nEA==, + } js-tokens@4.0.0: - resolution: {integrity: sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ==} + resolution: + { + integrity: sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ==, + } js-tokens@9.0.1: - resolution: {integrity: sha512-mxa9E9ITFOt0ban3j6L5MpjwegGz6lBQmM1IJkWeBZGcMxto50+eWdjC/52xDbS2vy0k7vIMK0Fe2wfL9OQSpQ==} + resolution: + { + integrity: sha512-mxa9E9ITFOt0ban3j6L5MpjwegGz6lBQmM1IJkWeBZGcMxto50+eWdjC/52xDbS2vy0k7vIMK0Fe2wfL9OQSpQ==, + } js-yaml@4.1.0: - resolution: {integrity: sha512-wpxZs9NoxZaJESJGIZTyDEaYpl0FKSA+FB9aJiyemKhMwkxQg63h4T1KJgUGHpTqPDNRcmmYLugrRjJlBtWvRA==} + resolution: + { + integrity: sha512-wpxZs9NoxZaJESJGIZTyDEaYpl0FKSA+FB9aJiyemKhMwkxQg63h4T1KJgUGHpTqPDNRcmmYLugrRjJlBtWvRA==, + } hasBin: true jsdom@26.1.0: - resolution: {integrity: sha512-Cvc9WUhxSMEo4McES3P7oK3QaXldCfNWp7pl2NNeiIFlCoLr3kfq9kb1fxftiwk1FLV7CvpvDfonxtzUDeSOPg==} - engines: {node: '>=18'} + resolution: + { + integrity: sha512-Cvc9WUhxSMEo4McES3P7oK3QaXldCfNWp7pl2NNeiIFlCoLr3kfq9kb1fxftiwk1FLV7CvpvDfonxtzUDeSOPg==, + } + engines: { node: ">=18" } peerDependencies: canvas: ^3.0.0 peerDependenciesMeta: @@ -2985,386 +4803,677 @@ packages: optional: true jsesc@3.1.0: - resolution: {integrity: sha512-/sM3dO2FOzXjKQhJuo0Q173wf2KOo8t4I8vHy6lF9poUp7bKT0/NHE8fPX23PwfhnykfqnC2xRxOnVw5XuGIaA==} - engines: {node: '>=6'} + resolution: + { + integrity: sha512-/sM3dO2FOzXjKQhJuo0Q173wf2KOo8t4I8vHy6lF9poUp7bKT0/NHE8fPX23PwfhnykfqnC2xRxOnVw5XuGIaA==, + } + engines: { node: ">=6" } hasBin: true json-buffer@3.0.1: - resolution: {integrity: sha512-4bV5BfR2mqfQTJm+V5tPPdf+ZpuhiIvTuAB5g8kcrXOZpTT/QwwVRWBywX1ozr6lEuPdbHxwaJlm9G6mI2sfSQ==} + resolution: + { + integrity: sha512-4bV5BfR2mqfQTJm+V5tPPdf+ZpuhiIvTuAB5g8kcrXOZpTT/QwwVRWBywX1ozr6lEuPdbHxwaJlm9G6mI2sfSQ==, + } json-schema-traverse@0.4.1: - resolution: {integrity: sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==} + resolution: + { + integrity: sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==, + } json-stable-stringify-without-jsonify@1.0.1: - resolution: {integrity: sha512-Bdboy+l7tA3OGW6FjyFHWkP5LuByj1Tk33Ljyq0axyzdk9//JSi2u3fP1QSmd1KNwq6VOKYGlAu87CisVir6Pw==} + resolution: + { + integrity: sha512-Bdboy+l7tA3OGW6FjyFHWkP5LuByj1Tk33Ljyq0axyzdk9//JSi2u3fP1QSmd1KNwq6VOKYGlAu87CisVir6Pw==, + } json5@1.0.2: - resolution: {integrity: sha512-g1MWMLBiz8FKi1e4w0UyVL3w+iJceWAFBAaBnnGKOpNa5f8TLktkbre1+s6oICydWAm+HRUGTmI+//xv2hvXYA==} + resolution: + { + integrity: sha512-g1MWMLBiz8FKi1e4w0UyVL3w+iJceWAFBAaBnnGKOpNa5f8TLktkbre1+s6oICydWAm+HRUGTmI+//xv2hvXYA==, + } hasBin: true json5@2.2.3: - resolution: {integrity: sha512-XmOWe7eyHYH14cLdVPoyg+GOH3rYX++KpzrylJwSW98t3Nk+U8XOl8FWKOgwtzdb8lXGf6zYwDUzeHMWfxasyg==} - engines: {node: '>=6'} + resolution: + { + integrity: sha512-XmOWe7eyHYH14cLdVPoyg+GOH3rYX++KpzrylJwSW98t3Nk+U8XOl8FWKOgwtzdb8lXGf6zYwDUzeHMWfxasyg==, + } + engines: { node: ">=6" } hasBin: true jsonc-parser@3.3.1: - resolution: {integrity: sha512-HUgH65KyejrUFPvHFPbqOY0rsFip3Bo5wb4ngvdi1EpCYWUQDC5V+Y7mZws+DLkr4M//zQJoanu1SP+87Dv1oQ==} + resolution: + { + integrity: sha512-HUgH65KyejrUFPvHFPbqOY0rsFip3Bo5wb4ngvdi1EpCYWUQDC5V+Y7mZws+DLkr4M//zQJoanu1SP+87Dv1oQ==, + } jsx-ast-utils@3.3.5: - resolution: {integrity: sha512-ZZow9HBI5O6EPgSJLUb8n2NKgmVWTwCvHGwFuJlMjvLFqlGG6pjirPhtdsseaLZjSibD8eegzmYpUZwoIlj2cQ==} - engines: {node: '>=4.0'} + resolution: + { + integrity: sha512-ZZow9HBI5O6EPgSJLUb8n2NKgmVWTwCvHGwFuJlMjvLFqlGG6pjirPhtdsseaLZjSibD8eegzmYpUZwoIlj2cQ==, + } + engines: { node: ">=4.0" } katex@0.16.22: - resolution: {integrity: sha512-XCHRdUw4lf3SKBaJe4EvgqIuWwkPSo9XoeO8GjQW94Bp7TWv9hNhzZjZ+OH9yf1UmLygb7DIT5GSFQiyt16zYg==} + resolution: + { + integrity: sha512-XCHRdUw4lf3SKBaJe4EvgqIuWwkPSo9XoeO8GjQW94Bp7TWv9hNhzZjZ+OH9yf1UmLygb7DIT5GSFQiyt16zYg==, + } hasBin: true keyv@4.5.4: - resolution: {integrity: sha512-oxVHkHR/EJf2CNXnWxRLW6mg7JyCCUcG0DtEGmL2ctUo1PNTin1PUil+r/+4r5MpVgC/fn1kjsx7mjSujKqIpw==} + resolution: + { + integrity: sha512-oxVHkHR/EJf2CNXnWxRLW6mg7JyCCUcG0DtEGmL2ctUo1PNTin1PUil+r/+4r5MpVgC/fn1kjsx7mjSujKqIpw==, + } language-subtag-registry@0.3.23: - resolution: {integrity: sha512-0K65Lea881pHotoGEa5gDlMxt3pctLi2RplBb7Ezh4rRdLEOtgi7n4EwK9lamnUCkKBqaeKRVebTq6BAxSkpXQ==} + resolution: + { + integrity: sha512-0K65Lea881pHotoGEa5gDlMxt3pctLi2RplBb7Ezh4rRdLEOtgi7n4EwK9lamnUCkKBqaeKRVebTq6BAxSkpXQ==, + } language-tags@1.0.9: - resolution: {integrity: sha512-MbjN408fEndfiQXbFQ1vnd+1NoLDsnQW41410oQBXiyXDMYH5z505juWa4KUE1LqxRC7DgOgZDbKLxHIwm27hA==} - engines: {node: '>=0.10'} + resolution: + { + integrity: sha512-MbjN408fEndfiQXbFQ1vnd+1NoLDsnQW41410oQBXiyXDMYH5z505juWa4KUE1LqxRC7DgOgZDbKLxHIwm27hA==, + } + engines: { node: ">=0.10" } leaflet@1.9.4: - resolution: {integrity: sha512-nxS1ynzJOmOlHp+iL3FyWqK89GtNL8U8rvlMOsQdTTssxZwCXh8N2NB3GDQOL+YR3XnWyZAxwQixURb+FA74PA==} + resolution: + { + integrity: sha512-nxS1ynzJOmOlHp+iL3FyWqK89GtNL8U8rvlMOsQdTTssxZwCXh8N2NB3GDQOL+YR3XnWyZAxwQixURb+FA74PA==, + } levn@0.4.1: - resolution: {integrity: sha512-+bT2uH4E5LGE7h/n3evcS/sQlJXCpIp6ym8OWJ5eV6+67Dsql/LaaT7qJBAt2rzfoa/5QBGBhxDix1dMt2kQKQ==} - engines: {node: '>= 0.8.0'} + resolution: + { + integrity: sha512-+bT2uH4E5LGE7h/n3evcS/sQlJXCpIp6ym8OWJ5eV6+67Dsql/LaaT7qJBAt2rzfoa/5QBGBhxDix1dMt2kQKQ==, + } + engines: { node: ">= 0.8.0" } lightningcss-darwin-arm64@1.30.1: - resolution: {integrity: sha512-c8JK7hyE65X1MHMN+Viq9n11RRC7hgin3HhYKhrMyaXflk5GVplZ60IxyoVtzILeKr+xAJwg6zK6sjTBJ0FKYQ==} - engines: {node: '>= 12.0.0'} + resolution: + { + integrity: sha512-c8JK7hyE65X1MHMN+Viq9n11RRC7hgin3HhYKhrMyaXflk5GVplZ60IxyoVtzILeKr+xAJwg6zK6sjTBJ0FKYQ==, + } + engines: { node: ">= 12.0.0" } cpu: [arm64] os: [darwin] lightningcss-darwin-x64@1.30.1: - resolution: {integrity: sha512-k1EvjakfumAQoTfcXUcHQZhSpLlkAuEkdMBsI/ivWw9hL+7FtilQc0Cy3hrx0AAQrVtQAbMI7YjCgYgvn37PzA==} - engines: {node: '>= 12.0.0'} + resolution: + { + integrity: sha512-k1EvjakfumAQoTfcXUcHQZhSpLlkAuEkdMBsI/ivWw9hL+7FtilQc0Cy3hrx0AAQrVtQAbMI7YjCgYgvn37PzA==, + } + engines: { node: ">= 12.0.0" } cpu: [x64] os: [darwin] lightningcss-freebsd-x64@1.30.1: - resolution: {integrity: sha512-kmW6UGCGg2PcyUE59K5r0kWfKPAVy4SltVeut+umLCFoJ53RdCUWxcRDzO1eTaxf/7Q2H7LTquFHPL5R+Gjyig==} - engines: {node: '>= 12.0.0'} + resolution: + { + integrity: sha512-kmW6UGCGg2PcyUE59K5r0kWfKPAVy4SltVeut+umLCFoJ53RdCUWxcRDzO1eTaxf/7Q2H7LTquFHPL5R+Gjyig==, + } + engines: { node: ">= 12.0.0" } cpu: [x64] os: [freebsd] lightningcss-linux-arm-gnueabihf@1.30.1: - resolution: {integrity: sha512-MjxUShl1v8pit+6D/zSPq9S9dQ2NPFSQwGvxBCYaBYLPlCWuPh9/t1MRS8iUaR8i+a6w7aps+B4N0S1TYP/R+Q==} - engines: {node: '>= 12.0.0'} + resolution: + { + integrity: sha512-MjxUShl1v8pit+6D/zSPq9S9dQ2NPFSQwGvxBCYaBYLPlCWuPh9/t1MRS8iUaR8i+a6w7aps+B4N0S1TYP/R+Q==, + } + engines: { node: ">= 12.0.0" } cpu: [arm] os: [linux] lightningcss-linux-arm64-gnu@1.30.1: - resolution: {integrity: sha512-gB72maP8rmrKsnKYy8XUuXi/4OctJiuQjcuqWNlJQ6jZiWqtPvqFziskH3hnajfvKB27ynbVCucKSm2rkQp4Bw==} - engines: {node: '>= 12.0.0'} + resolution: + { + integrity: sha512-gB72maP8rmrKsnKYy8XUuXi/4OctJiuQjcuqWNlJQ6jZiWqtPvqFziskH3hnajfvKB27ynbVCucKSm2rkQp4Bw==, + } + engines: { node: ">= 12.0.0" } cpu: [arm64] os: [linux] lightningcss-linux-arm64-musl@1.30.1: - resolution: {integrity: sha512-jmUQVx4331m6LIX+0wUhBbmMX7TCfjF5FoOH6SD1CttzuYlGNVpA7QnrmLxrsub43ClTINfGSYyHe2HWeLl5CQ==} - engines: {node: '>= 12.0.0'} + resolution: + { + integrity: sha512-jmUQVx4331m6LIX+0wUhBbmMX7TCfjF5FoOH6SD1CttzuYlGNVpA7QnrmLxrsub43ClTINfGSYyHe2HWeLl5CQ==, + } + engines: { node: ">= 12.0.0" } cpu: [arm64] os: [linux] lightningcss-linux-x64-gnu@1.30.1: - resolution: {integrity: sha512-piWx3z4wN8J8z3+O5kO74+yr6ze/dKmPnI7vLqfSqI8bccaTGY5xiSGVIJBDd5K5BHlvVLpUB3S2YCfelyJ1bw==} - engines: {node: '>= 12.0.0'} + resolution: + { + integrity: sha512-piWx3z4wN8J8z3+O5kO74+yr6ze/dKmPnI7vLqfSqI8bccaTGY5xiSGVIJBDd5K5BHlvVLpUB3S2YCfelyJ1bw==, + } + engines: { node: ">= 12.0.0" } cpu: [x64] os: [linux] lightningcss-linux-x64-musl@1.30.1: - resolution: {integrity: sha512-rRomAK7eIkL+tHY0YPxbc5Dra2gXlI63HL+v1Pdi1a3sC+tJTcFrHX+E86sulgAXeI7rSzDYhPSeHHjqFhqfeQ==} - engines: {node: '>= 12.0.0'} + resolution: + { + integrity: sha512-rRomAK7eIkL+tHY0YPxbc5Dra2gXlI63HL+v1Pdi1a3sC+tJTcFrHX+E86sulgAXeI7rSzDYhPSeHHjqFhqfeQ==, + } + engines: { node: ">= 12.0.0" } cpu: [x64] os: [linux] lightningcss-win32-arm64-msvc@1.30.1: - resolution: {integrity: sha512-mSL4rqPi4iXq5YVqzSsJgMVFENoa4nGTT/GjO2c0Yl9OuQfPsIfncvLrEW6RbbB24WtZ3xP/2CCmI3tNkNV4oA==} - engines: {node: '>= 12.0.0'} + resolution: + { + integrity: sha512-mSL4rqPi4iXq5YVqzSsJgMVFENoa4nGTT/GjO2c0Yl9OuQfPsIfncvLrEW6RbbB24WtZ3xP/2CCmI3tNkNV4oA==, + } + engines: { node: ">= 12.0.0" } cpu: [arm64] os: [win32] lightningcss-win32-x64-msvc@1.30.1: - resolution: {integrity: sha512-PVqXh48wh4T53F/1CCu8PIPCxLzWyCnn/9T5W1Jpmdy5h9Cwd+0YQS6/LwhHXSafuc61/xg9Lv5OrCby6a++jg==} - engines: {node: '>= 12.0.0'} + resolution: + { + integrity: sha512-PVqXh48wh4T53F/1CCu8PIPCxLzWyCnn/9T5W1Jpmdy5h9Cwd+0YQS6/LwhHXSafuc61/xg9Lv5OrCby6a++jg==, + } + engines: { node: ">= 12.0.0" } cpu: [x64] os: [win32] lightningcss@1.30.1: - resolution: {integrity: sha512-xi6IyHML+c9+Q3W0S4fCQJOym42pyurFiJUHEcEyHS0CeKzia4yZDEsLlqOFykxOdHpNy0NmvVO31vcSqAxJCg==} - engines: {node: '>= 12.0.0'} + resolution: + { + integrity: sha512-xi6IyHML+c9+Q3W0S4fCQJOym42pyurFiJUHEcEyHS0CeKzia4yZDEsLlqOFykxOdHpNy0NmvVO31vcSqAxJCg==, + } + engines: { node: ">= 12.0.0" } lineclip@1.1.5: - resolution: {integrity: sha512-KlA/wRSjpKl7tS9iRUdlG72oQ7qZ1IlVbVgHwoO10TBR/4gQ86uhKow6nlzMAJJhjCWKto8OeoAzzIzKSmN25A==} + resolution: + { + integrity: sha512-KlA/wRSjpKl7tS9iRUdlG72oQ7qZ1IlVbVgHwoO10TBR/4gQ86uhKow6nlzMAJJhjCWKto8OeoAzzIzKSmN25A==, + } linkify-it@5.0.0: - resolution: {integrity: sha512-5aHCbzQRADcdP+ATqnDuhhJ/MRIqDkZX5pyjFHRRysS8vZ5AbqGEoFIb6pYHPZ+L/OC2Lc+xT8uHVVR5CAK/wQ==} + resolution: + { + integrity: sha512-5aHCbzQRADcdP+ATqnDuhhJ/MRIqDkZX5pyjFHRRysS8vZ5AbqGEoFIb6pYHPZ+L/OC2Lc+xT8uHVVR5CAK/wQ==, + } locate-path@6.0.0: - resolution: {integrity: sha512-iPZK6eYjbxRu3uB4/WZ3EsEIMJFMqAoopl3R+zuq0UjcAm/MO6KCweDgPfP3elTztoKP3KtnVHxTn2NHBSDVUw==} - engines: {node: '>=10'} + resolution: + { + integrity: sha512-iPZK6eYjbxRu3uB4/WZ3EsEIMJFMqAoopl3R+zuq0UjcAm/MO6KCweDgPfP3elTztoKP3KtnVHxTn2NHBSDVUw==, + } + engines: { node: ">=10" } lodash.merge@4.6.2: - resolution: {integrity: sha512-0KpjqXRVvrYyCsX1swR/XTK0va6VQkQM6MNo7PqW77ByjAhoARA8EfrP1N4+KlKj8YS0ZUCtRT/YUuhyYDujIQ==} + resolution: + { + integrity: sha512-0KpjqXRVvrYyCsX1swR/XTK0va6VQkQM6MNo7PqW77ByjAhoARA8EfrP1N4+KlKj8YS0ZUCtRT/YUuhyYDujIQ==, + } longest-streak@3.1.0: - resolution: {integrity: sha512-9Ri+o0JYgehTaVBBDoMqIl8GXtbWg711O3srftcHhZ0dqnETqLaoIK0x17fUw9rFSlK/0NlsKe0Ahhyl5pXE2g==} + resolution: + { + integrity: sha512-9Ri+o0JYgehTaVBBDoMqIl8GXtbWg711O3srftcHhZ0dqnETqLaoIK0x17fUw9rFSlK/0NlsKe0Ahhyl5pXE2g==, + } loose-envify@1.4.0: - resolution: {integrity: sha512-lyuxPGr/Wfhrlem2CL/UcnUc1zcqKAImBDzukY7Y5F/yQiNdko6+fRLevlw1HgMySw7f611UIY408EtxRSoK3Q==} + resolution: + { + integrity: sha512-lyuxPGr/Wfhrlem2CL/UcnUc1zcqKAImBDzukY7Y5F/yQiNdko6+fRLevlw1HgMySw7f611UIY408EtxRSoK3Q==, + } hasBin: true loupe@3.1.4: - resolution: {integrity: sha512-wJzkKwJrheKtknCOKNEtDK4iqg/MxmZheEMtSTYvnzRdEYaZzmgH976nenp8WdJRdx5Vc1X/9MO0Oszl6ezeXg==} + resolution: + { + integrity: sha512-wJzkKwJrheKtknCOKNEtDK4iqg/MxmZheEMtSTYvnzRdEYaZzmgH976nenp8WdJRdx5Vc1X/9MO0Oszl6ezeXg==, + } lru-cache@10.4.3: - resolution: {integrity: sha512-JNAzZcXrCt42VGLuYz0zfAzDfAvJWW6AfYlDBQyDV5DClI2m5sAmK+OIO7s59XfsRsWHp02jAJrRadPRGTt6SQ==} + resolution: + { + integrity: sha512-JNAzZcXrCt42VGLuYz0zfAzDfAvJWW6AfYlDBQyDV5DClI2m5sAmK+OIO7s59XfsRsWHp02jAJrRadPRGTt6SQ==, + } lru-cache@5.1.1: - resolution: {integrity: sha512-KpNARQA3Iwv+jTA0utUVVbrh+Jlrr1Fv0e56GGzAFOXN7dk/FviaDW8LHmK52DlcH4WP2n6gI8vN1aesBFgo9w==} + resolution: + { + integrity: sha512-KpNARQA3Iwv+jTA0utUVVbrh+Jlrr1Fv0e56GGzAFOXN7dk/FviaDW8LHmK52DlcH4WP2n6gI8vN1aesBFgo9w==, + } lru-cache@6.0.0: - resolution: {integrity: sha512-Jo6dJ04CmSjuznwJSS3pUeWmd/H0ffTlkXXgwZi+eq1UCmqQwCh+eLsYOYCwY991i2Fah4h1BEMCx4qThGbsiA==} - engines: {node: '>=10'} + resolution: + { + integrity: sha512-Jo6dJ04CmSjuznwJSS3pUeWmd/H0ffTlkXXgwZi+eq1UCmqQwCh+eLsYOYCwY991i2Fah4h1BEMCx4qThGbsiA==, + } + engines: { node: ">=10" } lucide-react@0.525.0: - resolution: {integrity: sha512-Tm1txJ2OkymCGkvwoHt33Y2JpN5xucVq1slHcgE6Lk0WjDfjgKWor5CdVER8U6DvcfMwh4M8XxmpTiyzfmfDYQ==} + resolution: + { + integrity: sha512-Tm1txJ2OkymCGkvwoHt33Y2JpN5xucVq1slHcgE6Lk0WjDfjgKWor5CdVER8U6DvcfMwh4M8XxmpTiyzfmfDYQ==, + } peerDependencies: react: ^16.5.1 || ^17.0.0 || ^18.0.0 || ^19.0.0 lz-string@1.5.0: - resolution: {integrity: sha512-h5bgJWpxJNswbU7qCrV0tIKQCaS3blPDrqKWx+QxzuzL1zGUzij9XCWLrSLsJPu5t+eWA/ycetzYAO5IOMcWAQ==} + resolution: + { + integrity: sha512-h5bgJWpxJNswbU7qCrV0tIKQCaS3blPDrqKWx+QxzuzL1zGUzij9XCWLrSLsJPu5t+eWA/ycetzYAO5IOMcWAQ==, + } hasBin: true magic-string@0.30.17: - resolution: {integrity: sha512-sNPKHvyjVf7gyjwS4xGTaW/mCnF8wnjtifKBEhxfZ7E/S8tQ0rssrwGNn6q8JH/ohItJfSQp9mBtQYuTlH5QnA==} + resolution: + { + integrity: sha512-sNPKHvyjVf7gyjwS4xGTaW/mCnF8wnjtifKBEhxfZ7E/S8tQ0rssrwGNn6q8JH/ohItJfSQp9mBtQYuTlH5QnA==, + } magicast@0.3.5: - resolution: {integrity: sha512-L0WhttDl+2BOsybvEOLK7fW3UA0OQ0IQ2d6Zl2x/a6vVRs3bAY0ECOSHHeL5jD+SbOpOCUEi0y1DgHEn9Qn1AQ==} + resolution: + { + integrity: sha512-L0WhttDl+2BOsybvEOLK7fW3UA0OQ0IQ2d6Zl2x/a6vVRs3bAY0ECOSHHeL5jD+SbOpOCUEi0y1DgHEn9Qn1AQ==, + } make-dir@4.0.0: - resolution: {integrity: sha512-hXdUTZYIVOt1Ex//jAQi+wTZZpUpwBj/0QsOzqegb3rGMMeJiSEu5xLHnYfBrRV4RH2+OCSOO95Is/7x1WJ4bw==} - engines: {node: '>=10'} + resolution: + { + integrity: sha512-hXdUTZYIVOt1Ex//jAQi+wTZZpUpwBj/0QsOzqegb3rGMMeJiSEu5xLHnYfBrRV4RH2+OCSOO95Is/7x1WJ4bw==, + } + engines: { node: ">=10" } make-error@1.3.6: - resolution: {integrity: sha512-s8UhlNe7vPKomQhC1qFelMokr/Sc3AgNbso3n74mVPA5LTZwkB9NlXf4XPamLxJE8h0gh73rM94xvwRT2CVInw==} + resolution: + { + integrity: sha512-s8UhlNe7vPKomQhC1qFelMokr/Sc3AgNbso3n74mVPA5LTZwkB9NlXf4XPamLxJE8h0gh73rM94xvwRT2CVInw==, + } markdown-it@14.1.0: - resolution: {integrity: sha512-a54IwgWPaeBCAAsv13YgmALOF1elABB08FxO9i+r4VFk5Vl4pKokRPeX8u5TCgSsPi6ec1otfLjdOpVcgbpshg==} + resolution: + { + integrity: sha512-a54IwgWPaeBCAAsv13YgmALOF1elABB08FxO9i+r4VFk5Vl4pKokRPeX8u5TCgSsPi6ec1otfLjdOpVcgbpshg==, + } hasBin: true markdownlint-cli2-formatter-default@0.0.5: - resolution: {integrity: sha512-4XKTwQ5m1+Txo2kuQ3Jgpo/KmnG+X90dWt4acufg6HVGadTUG5hzHF/wssp9b5MBYOMCnZ9RMPaU//uHsszF8Q==} + resolution: + { + integrity: sha512-4XKTwQ5m1+Txo2kuQ3Jgpo/KmnG+X90dWt4acufg6HVGadTUG5hzHF/wssp9b5MBYOMCnZ9RMPaU//uHsszF8Q==, + } peerDependencies: - markdownlint-cli2: '>=0.0.4' + markdownlint-cli2: ">=0.0.4" markdownlint-cli2@0.18.1: - resolution: {integrity: sha512-/4Osri9QFGCZOCTkfA8qJF+XGjKYERSHkXzxSyS1hd3ZERJGjvsUao2h4wdnvpHp6Tu2Jh/bPHM0FE9JJza6ng==} - engines: {node: '>=20'} + resolution: + { + integrity: sha512-/4Osri9QFGCZOCTkfA8qJF+XGjKYERSHkXzxSyS1hd3ZERJGjvsUao2h4wdnvpHp6Tu2Jh/bPHM0FE9JJza6ng==, + } + engines: { node: ">=20" } hasBin: true markdownlint@0.38.0: - resolution: {integrity: sha512-xaSxkaU7wY/0852zGApM8LdlIfGCW8ETZ0Rr62IQtAnUMlMuifsg09vWJcNYeL4f0anvr8Vo4ZQar8jGpV0btQ==} - engines: {node: '>=20'} + resolution: + { + integrity: sha512-xaSxkaU7wY/0852zGApM8LdlIfGCW8ETZ0Rr62IQtAnUMlMuifsg09vWJcNYeL4f0anvr8Vo4ZQar8jGpV0btQ==, + } + engines: { node: ">=20" } math-intrinsics@1.1.0: - resolution: {integrity: sha512-/IXtbwEk5HTPyEwyKX6hGkYXxM9nbj64B+ilVJnC/R6B0pH5G4V3b0pVbL7DBj4tkhBAppbQUlf6F6Xl9LHu1g==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-/IXtbwEk5HTPyEwyKX6hGkYXxM9nbj64B+ilVJnC/R6B0pH5G4V3b0pVbL7DBj4tkhBAppbQUlf6F6Xl9LHu1g==, + } + engines: { node: ">= 0.4" } mdast-util-from-markdown@2.0.2: - resolution: {integrity: sha512-uZhTV/8NBuw0WHkPTrCqDOl0zVe1BIng5ZtHoDk49ME1qqcjYmmLmOf0gELgcRMxN4w2iuIeVso5/6QymSrgmA==} + resolution: + { + integrity: sha512-uZhTV/8NBuw0WHkPTrCqDOl0zVe1BIng5ZtHoDk49ME1qqcjYmmLmOf0gELgcRMxN4w2iuIeVso5/6QymSrgmA==, + } mdast-util-mdx-expression@2.0.1: - resolution: {integrity: sha512-J6f+9hUp+ldTZqKRSg7Vw5V6MqjATc+3E4gf3CFNcuZNWD8XdyI6zQ8GqH7f8169MM6P7hMBRDVGnn7oHB9kXQ==} + resolution: + { + integrity: sha512-J6f+9hUp+ldTZqKRSg7Vw5V6MqjATc+3E4gf3CFNcuZNWD8XdyI6zQ8GqH7f8169MM6P7hMBRDVGnn7oHB9kXQ==, + } mdast-util-mdx-jsx@3.2.0: - resolution: {integrity: sha512-lj/z8v0r6ZtsN/cGNNtemmmfoLAFZnjMbNyLzBafjzikOM+glrjNHPlf6lQDOTccj9n5b0PPihEBbhneMyGs1Q==} + resolution: + { + integrity: sha512-lj/z8v0r6ZtsN/cGNNtemmmfoLAFZnjMbNyLzBafjzikOM+glrjNHPlf6lQDOTccj9n5b0PPihEBbhneMyGs1Q==, + } mdast-util-mdxjs-esm@2.0.1: - resolution: {integrity: sha512-EcmOpxsZ96CvlP03NghtH1EsLtr0n9Tm4lPUJUBccV9RwUOneqSycg19n5HGzCf+10LozMRSObtVr3ee1WoHtg==} + resolution: + { + integrity: sha512-EcmOpxsZ96CvlP03NghtH1EsLtr0n9Tm4lPUJUBccV9RwUOneqSycg19n5HGzCf+10LozMRSObtVr3ee1WoHtg==, + } mdast-util-phrasing@4.1.0: - resolution: {integrity: sha512-TqICwyvJJpBwvGAMZjj4J2n0X8QWp21b9l0o7eXyVJ25YNWYbJDVIyD1bZXE6WtV6RmKJVYmQAKWa0zWOABz2w==} + resolution: + { + integrity: sha512-TqICwyvJJpBwvGAMZjj4J2n0X8QWp21b9l0o7eXyVJ25YNWYbJDVIyD1bZXE6WtV6RmKJVYmQAKWa0zWOABz2w==, + } mdast-util-to-hast@13.2.0: - resolution: {integrity: sha512-QGYKEuUsYT9ykKBCMOEDLsU5JRObWQusAolFMeko/tYPufNkRffBAQjIE+99jbA87xv6FgmjLtwjh9wBWajwAA==} + resolution: + { + integrity: sha512-QGYKEuUsYT9ykKBCMOEDLsU5JRObWQusAolFMeko/tYPufNkRffBAQjIE+99jbA87xv6FgmjLtwjh9wBWajwAA==, + } mdast-util-to-markdown@2.1.2: - resolution: {integrity: sha512-xj68wMTvGXVOKonmog6LwyJKrYXZPvlwabaryTjLh9LuvovB/KAH+kvi8Gjj+7rJjsFi23nkUxRQv1KqSroMqA==} + resolution: + { + integrity: sha512-xj68wMTvGXVOKonmog6LwyJKrYXZPvlwabaryTjLh9LuvovB/KAH+kvi8Gjj+7rJjsFi23nkUxRQv1KqSroMqA==, + } mdast-util-to-string@4.0.0: - resolution: {integrity: sha512-0H44vDimn51F0YwvxSJSm0eCDOJTRlmN0R1yBh4HLj9wiV1Dn0QoXGbvFAWj2hSItVTlCmBF1hqKlIyUBVFLPg==} + resolution: + { + integrity: sha512-0H44vDimn51F0YwvxSJSm0eCDOJTRlmN0R1yBh4HLj9wiV1Dn0QoXGbvFAWj2hSItVTlCmBF1hqKlIyUBVFLPg==, + } mdurl@2.0.0: - resolution: {integrity: sha512-Lf+9+2r+Tdp5wXDXC4PcIBjTDtq4UKjCPMQhKIuzpJNW0b96kVqSwW0bT7FhRSfmAiFYgP+SCRvdrDozfh0U5w==} + resolution: + { + integrity: sha512-Lf+9+2r+Tdp5wXDXC4PcIBjTDtq4UKjCPMQhKIuzpJNW0b96kVqSwW0bT7FhRSfmAiFYgP+SCRvdrDozfh0U5w==, + } merge2@1.4.1: - resolution: {integrity: sha512-8q7VEgMJW4J8tcfVPy8g09NcQwZdbwFEqhe/WZkoIzjn/3TGDwtOCYtXGxA3O8tPzpczCCDgv+P2P5y00ZJOOg==} - engines: {node: '>= 8'} + resolution: + { + integrity: sha512-8q7VEgMJW4J8tcfVPy8g09NcQwZdbwFEqhe/WZkoIzjn/3TGDwtOCYtXGxA3O8tPzpczCCDgv+P2P5y00ZJOOg==, + } + engines: { node: ">= 8" } micromark-core-commonmark@2.0.3: - resolution: {integrity: sha512-RDBrHEMSxVFLg6xvnXmb1Ayr2WzLAWjeSATAoxwKYJV94TeNavgoIdA0a9ytzDSVzBy2YKFK+emCPOEibLeCrg==} + resolution: + { + integrity: sha512-RDBrHEMSxVFLg6xvnXmb1Ayr2WzLAWjeSATAoxwKYJV94TeNavgoIdA0a9ytzDSVzBy2YKFK+emCPOEibLeCrg==, + } micromark-extension-directive@4.0.0: - resolution: {integrity: sha512-/C2nqVmXXmiseSSuCdItCMho7ybwwop6RrrRPk0KbOHW21JKoCldC+8rFOaundDoRBUWBnJJcxeA/Kvi34WQXg==} + resolution: + { + integrity: sha512-/C2nqVmXXmiseSSuCdItCMho7ybwwop6RrrRPk0KbOHW21JKoCldC+8rFOaundDoRBUWBnJJcxeA/Kvi34WQXg==, + } micromark-extension-gfm-autolink-literal@2.1.0: - resolution: {integrity: sha512-oOg7knzhicgQ3t4QCjCWgTmfNhvQbDDnJeVu9v81r7NltNCVmhPy1fJRX27pISafdjL+SVc4d3l48Gb6pbRypw==} + resolution: + { + integrity: sha512-oOg7knzhicgQ3t4QCjCWgTmfNhvQbDDnJeVu9v81r7NltNCVmhPy1fJRX27pISafdjL+SVc4d3l48Gb6pbRypw==, + } micromark-extension-gfm-footnote@2.1.0: - resolution: {integrity: sha512-/yPhxI1ntnDNsiHtzLKYnE3vf9JZ6cAisqVDauhp4CEHxlb4uoOTxOCJ+9s51bIB8U1N1FJ1RXOKTIlD5B/gqw==} + resolution: + { + integrity: sha512-/yPhxI1ntnDNsiHtzLKYnE3vf9JZ6cAisqVDauhp4CEHxlb4uoOTxOCJ+9s51bIB8U1N1FJ1RXOKTIlD5B/gqw==, + } micromark-extension-gfm-table@2.1.1: - resolution: {integrity: sha512-t2OU/dXXioARrC6yWfJ4hqB7rct14e8f7m0cbI5hUmDyyIlwv5vEtooptH8INkbLzOatzKuVbQmAYcbWoyz6Dg==} + resolution: + { + integrity: sha512-t2OU/dXXioARrC6yWfJ4hqB7rct14e8f7m0cbI5hUmDyyIlwv5vEtooptH8INkbLzOatzKuVbQmAYcbWoyz6Dg==, + } micromark-extension-math@3.1.0: - resolution: {integrity: sha512-lvEqd+fHjATVs+2v/8kg9i5Q0AP2k85H0WUOwpIVvUML8BapsMvh1XAogmQjOCsLpoKRCVQqEkQBB3NhVBcsOg==} + resolution: + { + integrity: sha512-lvEqd+fHjATVs+2v/8kg9i5Q0AP2k85H0WUOwpIVvUML8BapsMvh1XAogmQjOCsLpoKRCVQqEkQBB3NhVBcsOg==, + } micromark-factory-destination@2.0.1: - resolution: {integrity: sha512-Xe6rDdJlkmbFRExpTOmRj9N3MaWmbAgdpSrBQvCFqhezUn4AHqJHbaEnfbVYYiexVSs//tqOdY/DxhjdCiJnIA==} + resolution: + { + integrity: sha512-Xe6rDdJlkmbFRExpTOmRj9N3MaWmbAgdpSrBQvCFqhezUn4AHqJHbaEnfbVYYiexVSs//tqOdY/DxhjdCiJnIA==, + } micromark-factory-label@2.0.1: - resolution: {integrity: sha512-VFMekyQExqIW7xIChcXn4ok29YE3rnuyveW3wZQWWqF4Nv9Wk5rgJ99KzPvHjkmPXF93FXIbBp6YdW3t71/7Vg==} + resolution: + { + integrity: sha512-VFMekyQExqIW7xIChcXn4ok29YE3rnuyveW3wZQWWqF4Nv9Wk5rgJ99KzPvHjkmPXF93FXIbBp6YdW3t71/7Vg==, + } micromark-factory-space@2.0.1: - resolution: {integrity: sha512-zRkxjtBxxLd2Sc0d+fbnEunsTj46SWXgXciZmHq0kDYGnck/ZSGj9/wULTV95uoeYiK5hRXP2mJ98Uo4cq/LQg==} + resolution: + { + integrity: sha512-zRkxjtBxxLd2Sc0d+fbnEunsTj46SWXgXciZmHq0kDYGnck/ZSGj9/wULTV95uoeYiK5hRXP2mJ98Uo4cq/LQg==, + } micromark-factory-title@2.0.1: - resolution: {integrity: sha512-5bZ+3CjhAd9eChYTHsjy6TGxpOFSKgKKJPJxr293jTbfry2KDoWkhBb6TcPVB4NmzaPhMs1Frm9AZH7OD4Cjzw==} + resolution: + { + integrity: sha512-5bZ+3CjhAd9eChYTHsjy6TGxpOFSKgKKJPJxr293jTbfry2KDoWkhBb6TcPVB4NmzaPhMs1Frm9AZH7OD4Cjzw==, + } micromark-factory-whitespace@2.0.1: - resolution: {integrity: sha512-Ob0nuZ3PKt/n0hORHyvoD9uZhr+Za8sFoP+OnMcnWK5lngSzALgQYKMr9RJVOWLqQYuyn6ulqGWSXdwf6F80lQ==} + resolution: + { + integrity: sha512-Ob0nuZ3PKt/n0hORHyvoD9uZhr+Za8sFoP+OnMcnWK5lngSzALgQYKMr9RJVOWLqQYuyn6ulqGWSXdwf6F80lQ==, + } micromark-util-character@2.1.1: - resolution: {integrity: sha512-wv8tdUTJ3thSFFFJKtpYKOYiGP2+v96Hvk4Tu8KpCAsTMs6yi+nVmGh1syvSCsaxz45J6Jbw+9DD6g97+NV67Q==} + resolution: + { + integrity: sha512-wv8tdUTJ3thSFFFJKtpYKOYiGP2+v96Hvk4Tu8KpCAsTMs6yi+nVmGh1syvSCsaxz45J6Jbw+9DD6g97+NV67Q==, + } micromark-util-chunked@2.0.1: - resolution: {integrity: sha512-QUNFEOPELfmvv+4xiNg2sRYeS/P84pTW0TCgP5zc9FpXetHY0ab7SxKyAQCNCc1eK0459uoLI1y5oO5Vc1dbhA==} + resolution: + { + integrity: sha512-QUNFEOPELfmvv+4xiNg2sRYeS/P84pTW0TCgP5zc9FpXetHY0ab7SxKyAQCNCc1eK0459uoLI1y5oO5Vc1dbhA==, + } micromark-util-classify-character@2.0.1: - resolution: {integrity: sha512-K0kHzM6afW/MbeWYWLjoHQv1sgg2Q9EccHEDzSkxiP/EaagNzCm7T/WMKZ3rjMbvIpvBiZgwR3dKMygtA4mG1Q==} + resolution: + { + integrity: sha512-K0kHzM6afW/MbeWYWLjoHQv1sgg2Q9EccHEDzSkxiP/EaagNzCm7T/WMKZ3rjMbvIpvBiZgwR3dKMygtA4mG1Q==, + } micromark-util-combine-extensions@2.0.1: - resolution: {integrity: sha512-OnAnH8Ujmy59JcyZw8JSbK9cGpdVY44NKgSM7E9Eh7DiLS2E9RNQf0dONaGDzEG9yjEl5hcqeIsj4hfRkLH/Bg==} + resolution: + { + integrity: sha512-OnAnH8Ujmy59JcyZw8JSbK9cGpdVY44NKgSM7E9Eh7DiLS2E9RNQf0dONaGDzEG9yjEl5hcqeIsj4hfRkLH/Bg==, + } micromark-util-decode-numeric-character-reference@2.0.2: - resolution: {integrity: sha512-ccUbYk6CwVdkmCQMyr64dXz42EfHGkPQlBj5p7YVGzq8I7CtjXZJrubAYezf7Rp+bjPseiROqe7G6foFd+lEuw==} + resolution: + { + integrity: sha512-ccUbYk6CwVdkmCQMyr64dXz42EfHGkPQlBj5p7YVGzq8I7CtjXZJrubAYezf7Rp+bjPseiROqe7G6foFd+lEuw==, + } micromark-util-decode-string@2.0.1: - resolution: {integrity: sha512-nDV/77Fj6eH1ynwscYTOsbK7rR//Uj0bZXBwJZRfaLEJ1iGBR6kIfNmlNqaqJf649EP0F3NWNdeJi03elllNUQ==} + resolution: + { + integrity: sha512-nDV/77Fj6eH1ynwscYTOsbK7rR//Uj0bZXBwJZRfaLEJ1iGBR6kIfNmlNqaqJf649EP0F3NWNdeJi03elllNUQ==, + } micromark-util-encode@2.0.1: - resolution: {integrity: sha512-c3cVx2y4KqUnwopcO9b/SCdo2O67LwJJ/UyqGfbigahfegL9myoEFoDYZgkT7f36T0bLrM9hZTAaAyH+PCAXjw==} + resolution: + { + integrity: sha512-c3cVx2y4KqUnwopcO9b/SCdo2O67LwJJ/UyqGfbigahfegL9myoEFoDYZgkT7f36T0bLrM9hZTAaAyH+PCAXjw==, + } micromark-util-html-tag-name@2.0.1: - resolution: {integrity: sha512-2cNEiYDhCWKI+Gs9T0Tiysk136SnR13hhO8yW6BGNyhOC4qYFnwF1nKfD3HFAIXA5c45RrIG1ub11GiXeYd1xA==} + resolution: + { + integrity: sha512-2cNEiYDhCWKI+Gs9T0Tiysk136SnR13hhO8yW6BGNyhOC4qYFnwF1nKfD3HFAIXA5c45RrIG1ub11GiXeYd1xA==, + } micromark-util-normalize-identifier@2.0.1: - resolution: {integrity: sha512-sxPqmo70LyARJs0w2UclACPUUEqltCkJ6PhKdMIDuJ3gSf/Q+/GIe3WKl0Ijb/GyH9lOpUkRAO2wp0GVkLvS9Q==} + resolution: + { + integrity: sha512-sxPqmo70LyARJs0w2UclACPUUEqltCkJ6PhKdMIDuJ3gSf/Q+/GIe3WKl0Ijb/GyH9lOpUkRAO2wp0GVkLvS9Q==, + } micromark-util-resolve-all@2.0.1: - resolution: {integrity: sha512-VdQyxFWFT2/FGJgwQnJYbe1jjQoNTS4RjglmSjTUlpUMa95Htx9NHeYW4rGDJzbjvCsl9eLjMQwGeElsqmzcHg==} + resolution: + { + integrity: sha512-VdQyxFWFT2/FGJgwQnJYbe1jjQoNTS4RjglmSjTUlpUMa95Htx9NHeYW4rGDJzbjvCsl9eLjMQwGeElsqmzcHg==, + } micromark-util-sanitize-uri@2.0.1: - resolution: {integrity: sha512-9N9IomZ/YuGGZZmQec1MbgxtlgougxTodVwDzzEouPKo3qFWvymFHWcnDi2vzV1ff6kas9ucW+o3yzJK9YB1AQ==} + resolution: + { + integrity: sha512-9N9IomZ/YuGGZZmQec1MbgxtlgougxTodVwDzzEouPKo3qFWvymFHWcnDi2vzV1ff6kas9ucW+o3yzJK9YB1AQ==, + } micromark-util-subtokenize@2.1.0: - resolution: {integrity: sha512-XQLu552iSctvnEcgXw6+Sx75GflAPNED1qx7eBJ+wydBb2KCbRZe+NwvIEEMM83uml1+2WSXpBAcp9IUCgCYWA==} + resolution: + { + integrity: sha512-XQLu552iSctvnEcgXw6+Sx75GflAPNED1qx7eBJ+wydBb2KCbRZe+NwvIEEMM83uml1+2WSXpBAcp9IUCgCYWA==, + } micromark-util-symbol@2.0.1: - resolution: {integrity: sha512-vs5t8Apaud9N28kgCrRUdEed4UJ+wWNvicHLPxCa9ENlYuAY31M0ETy5y1vA33YoNPDFTghEbnh6efaE8h4x0Q==} + resolution: + { + integrity: sha512-vs5t8Apaud9N28kgCrRUdEed4UJ+wWNvicHLPxCa9ENlYuAY31M0ETy5y1vA33YoNPDFTghEbnh6efaE8h4x0Q==, + } micromark-util-types@2.0.2: - resolution: {integrity: sha512-Yw0ECSpJoViF1qTU4DC6NwtC4aWGt1EkzaQB8KPPyCRR8z9TWeV0HbEFGTO+ZY1wB22zmxnJqhPyTpOVCpeHTA==} + resolution: + { + integrity: sha512-Yw0ECSpJoViF1qTU4DC6NwtC4aWGt1EkzaQB8KPPyCRR8z9TWeV0HbEFGTO+ZY1wB22zmxnJqhPyTpOVCpeHTA==, + } micromark@4.0.2: - resolution: {integrity: sha512-zpe98Q6kvavpCr1NPVSCMebCKfD7CA2NqZ+rykeNhONIJBpc1tFKt9hucLGwha3jNTNI8lHpctWJWoimVF4PfA==} + resolution: + { + integrity: sha512-zpe98Q6kvavpCr1NPVSCMebCKfD7CA2NqZ+rykeNhONIJBpc1tFKt9hucLGwha3jNTNI8lHpctWJWoimVF4PfA==, + } micromatch@4.0.8: - resolution: {integrity: sha512-PXwfBhYu0hBCPw8Dn0E+WDYb7af3dSLVWKi3HGv84IdF4TyFoC0ysxFd0Goxw7nSv4T/PzEJQxsYsEiFCKo2BA==} - engines: {node: '>=8.6'} + resolution: + { + integrity: sha512-PXwfBhYu0hBCPw8Dn0E+WDYb7af3dSLVWKi3HGv84IdF4TyFoC0ysxFd0Goxw7nSv4T/PzEJQxsYsEiFCKo2BA==, + } + engines: { node: ">=8.6" } mime-db@1.52.0: - resolution: {integrity: sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg==} - engines: {node: '>= 0.6'} + resolution: + { + integrity: sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg==, + } + engines: { node: ">= 0.6" } mime-types@2.1.35: - resolution: {integrity: sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw==} - engines: {node: '>= 0.6'} + resolution: + { + integrity: sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw==, + } + engines: { node: ">= 0.6" } minimatch@3.1.2: - resolution: {integrity: sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw==} + resolution: + { + integrity: sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw==, + } minimatch@9.0.5: - resolution: {integrity: sha512-G6T0ZX48xgozx7587koeX9Ys2NYy6Gmv//P89sEte9V9whIapMNF4idKxnW2QtCcLiTWlb/wfCabAtAFWhhBow==} - engines: {node: '>=16 || 14 >=14.17'} + resolution: + { + integrity: sha512-G6T0ZX48xgozx7587koeX9Ys2NYy6Gmv//P89sEte9V9whIapMNF4idKxnW2QtCcLiTWlb/wfCabAtAFWhhBow==, + } + engines: { node: ">=16 || 14 >=14.17" } minimist@1.2.8: - resolution: {integrity: sha512-2yyAR8qBkN3YuheJanUpWC5U3bb5osDywNB8RzDVlDwDHbocAJveqqj1u8+SVD7jkWT4yvsHCpWqqWqAxb0zCA==} + resolution: + { + integrity: sha512-2yyAR8qBkN3YuheJanUpWC5U3bb5osDywNB8RzDVlDwDHbocAJveqqj1u8+SVD7jkWT4yvsHCpWqqWqAxb0zCA==, + } minipass@7.1.2: - resolution: {integrity: sha512-qOOzS1cBTWYF4BH8fVePDBOO9iptMnGUEZwNc/cMWnTV2nVLZ7VoNWEPHkYczZA0pdoA7dl6e7FL659nX9S2aw==} - engines: {node: '>=16 || 14 >=14.17'} + resolution: + { + integrity: sha512-qOOzS1cBTWYF4BH8fVePDBOO9iptMnGUEZwNc/cMWnTV2nVLZ7VoNWEPHkYczZA0pdoA7dl6e7FL659nX9S2aw==, + } + engines: { node: ">=16 || 14 >=14.17" } minizlib@3.0.2: - resolution: {integrity: sha512-oG62iEk+CYt5Xj2YqI5Xi9xWUeZhDI8jjQmC5oThVH5JGCTgIjr7ciJDzC7MBzYd//WvR1OTmP5Q38Q8ShQtVA==} - engines: {node: '>= 18'} + resolution: + { + integrity: sha512-oG62iEk+CYt5Xj2YqI5Xi9xWUeZhDI8jjQmC5oThVH5JGCTgIjr7ciJDzC7MBzYd//WvR1OTmP5Q38Q8ShQtVA==, + } + engines: { node: ">= 18" } mkdirp@3.0.1: - resolution: {integrity: sha512-+NsyUUAZDmo6YVHzL/stxSu3t9YS1iljliy3BSDrXJ/dkn1KYdmtZODGGjLcc9XLgVVpH4KshHB8XmZgMhaBXg==} - engines: {node: '>=10'} + resolution: + { + integrity: sha512-+NsyUUAZDmo6YVHzL/stxSu3t9YS1iljliy3BSDrXJ/dkn1KYdmtZODGGjLcc9XLgVVpH4KshHB8XmZgMhaBXg==, + } + engines: { node: ">=10" } hasBin: true ms@2.1.3: - resolution: {integrity: sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==} + resolution: + { + integrity: sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==, + } nanoid@3.3.11: - resolution: {integrity: sha512-N8SpfPUnUp1bK+PMYW8qSWdl9U+wwNWI4QKxOYDy9JAro3WMX7p2OeVRF9v+347pnakNevPmiHhNmZ2HbFA76w==} - engines: {node: ^10 || ^12 || ^13.7 || ^14 || >=15.0.1} + resolution: + { + integrity: sha512-N8SpfPUnUp1bK+PMYW8qSWdl9U+wwNWI4QKxOYDy9JAro3WMX7p2OeVRF9v+347pnakNevPmiHhNmZ2HbFA76w==, + } + engines: { node: ^10 || ^12 || ^13.7 || ^14 || >=15.0.1 } hasBin: true napi-postinstall@0.2.4: - resolution: {integrity: sha512-ZEzHJwBhZ8qQSbknHqYcdtQVr8zUgGyM/q6h6qAyhtyVMNrSgDhrC4disf03dYW0e+czXyLnZINnCTEkWy0eJg==} - engines: {node: ^12.20.0 || ^14.18.0 || >=16.0.0} + resolution: + { + integrity: sha512-ZEzHJwBhZ8qQSbknHqYcdtQVr8zUgGyM/q6h6qAyhtyVMNrSgDhrC4disf03dYW0e+czXyLnZINnCTEkWy0eJg==, + } + engines: { node: ^12.20.0 || ^14.18.0 || >=16.0.0 } hasBin: true natural-compare@1.4.0: - resolution: {integrity: sha512-OWND8ei3VtNC9h7V60qff3SVobHr996CTwgxubgyQYEpg290h9J0buyECNNJexkFm5sOajh5G116RYA1c8ZMSw==} + resolution: + { + integrity: sha512-OWND8ei3VtNC9h7V60qff3SVobHr996CTwgxubgyQYEpg290h9J0buyECNNJexkFm5sOajh5G116RYA1c8ZMSw==, + } next-auth@4.24.11: - resolution: {integrity: sha512-pCFXzIDQX7xmHFs4KVH4luCjaCbuPRtZ9oBUjUhOk84mZ9WVPf94n87TxYI4rSRf9HmfHEF8Yep3JrYDVOo3Cw==} + resolution: + { + integrity: sha512-pCFXzIDQX7xmHFs4KVH4luCjaCbuPRtZ9oBUjUhOk84mZ9WVPf94n87TxYI4rSRf9HmfHEF8Yep3JrYDVOo3Cw==, + } peerDependencies: - '@auth/core': 0.34.2 + "@auth/core": 0.34.2 next: ^12.2.5 || ^13 || ^14 || ^15 nodemailer: ^6.6.5 react: ^17.0.2 || ^18 || ^19 react-dom: ^17.0.2 || ^18 || ^19 peerDependenciesMeta: - '@auth/core': + "@auth/core": optional: true nodemailer: optional: true next@15.3.4: - resolution: {integrity: sha512-mHKd50C+mCjam/gcnwqL1T1vPx/XQNFlXqFIVdgQdVAFY9iIQtY0IfaVflEYzKiqjeA7B0cYYMaCrmAYFjs4rA==} - engines: {node: ^18.18.0 || ^19.8.0 || >= 20.0.0} + resolution: + { + integrity: sha512-mHKd50C+mCjam/gcnwqL1T1vPx/XQNFlXqFIVdgQdVAFY9iIQtY0IfaVflEYzKiqjeA7B0cYYMaCrmAYFjs4rA==, + } + engines: { node: ^18.18.0 || ^19.8.0 || >= 20.0.0 } hasBin: true peerDependencies: - '@opentelemetry/api': ^1.1.0 - '@playwright/test': ^1.41.2 - babel-plugin-react-compiler: '*' + "@opentelemetry/api": ^1.1.0 + "@playwright/test": ^1.41.2 + babel-plugin-react-compiler: "*" react: ^18.2.0 || 19.0.0-rc-de68d2f4-20241204 || ^19.0.0 react-dom: ^18.2.0 || 19.0.0-rc-de68d2f4-20241204 || ^19.0.0 sass: ^1.3.0 peerDependenciesMeta: - '@opentelemetry/api': + "@opentelemetry/api": optional: true - '@playwright/test': + "@playwright/test": optional: true babel-plugin-react-compiler: optional: true @@ -3372,719 +5481,1238 @@ packages: optional: true node-cron@4.1.1: - resolution: {integrity: sha512-oJj9CYV7teeCVs+y2Efi5IQ4FGmAYbsXQOehc1AGLlwteec8pC7DjBCUzSyRQ0LYa+CRCgmD+vtlWQcnPpXowA==} - engines: {node: '>=6.0.0'} + resolution: + { + integrity: sha512-oJj9CYV7teeCVs+y2Efi5IQ4FGmAYbsXQOehc1AGLlwteec8pC7DjBCUzSyRQ0LYa+CRCgmD+vtlWQcnPpXowA==, + } + engines: { node: ">=6.0.0" } node-domexception@1.0.0: - resolution: {integrity: sha512-/jKZoMpw0F8GRwl4/eLROPA3cfcXtLApP0QzLmUT/HuPCZWyB7IY9ZrMeKw2O/nFIqPQB3PVM9aYm0F312AXDQ==} - engines: {node: '>=10.5.0'} + resolution: + { + integrity: sha512-/jKZoMpw0F8GRwl4/eLROPA3cfcXtLApP0QzLmUT/HuPCZWyB7IY9ZrMeKw2O/nFIqPQB3PVM9aYm0F312AXDQ==, + } + engines: { node: ">=10.5.0" } deprecated: Use your platform's native DOMException instead node-fetch@3.3.2: - resolution: {integrity: sha512-dRB78srN/l6gqWulah9SrxeYnxeddIG30+GOqK/9OlLVyLg3HPnr6SqOWTWOXKRwC2eGYCkZ59NNuSgvSrpgOA==} - engines: {node: ^12.20.0 || ^14.13.1 || >=16.0.0} + resolution: + { + integrity: sha512-dRB78srN/l6gqWulah9SrxeYnxeddIG30+GOqK/9OlLVyLg3HPnr6SqOWTWOXKRwC2eGYCkZ59NNuSgvSrpgOA==, + } + engines: { node: ^12.20.0 || ^14.13.1 || >=16.0.0 } node-releases@2.0.19: - resolution: {integrity: sha512-xxOWJsBKtzAq7DY0J+DTzuz58K8e7sJbdgwkbMWQe8UYB6ekmsQ45q0M/tJDsGaZmbC+l7n57UV8Hl5tHxO9uw==} + resolution: + { + integrity: sha512-xxOWJsBKtzAq7DY0J+DTzuz58K8e7sJbdgwkbMWQe8UYB6ekmsQ45q0M/tJDsGaZmbC+l7n57UV8Hl5tHxO9uw==, + } nwsapi@2.2.20: - resolution: {integrity: sha512-/ieB+mDe4MrrKMT8z+mQL8klXydZWGR5Dowt4RAGKbJ3kIGEx3X4ljUo+6V73IXtUPWgfOlU5B9MlGxFO5T+cA==} + resolution: + { + integrity: sha512-/ieB+mDe4MrrKMT8z+mQL8klXydZWGR5Dowt4RAGKbJ3kIGEx3X4ljUo+6V73IXtUPWgfOlU5B9MlGxFO5T+cA==, + } oauth@0.9.15: - resolution: {integrity: sha512-a5ERWK1kh38ExDEfoO6qUHJb32rd7aYmPHuyCu3Fta/cnICvYmgd2uhuKXvPD+PXB+gCEYYEaQdIRAjCOwAKNA==} + resolution: + { + integrity: sha512-a5ERWK1kh38ExDEfoO6qUHJb32rd7aYmPHuyCu3Fta/cnICvYmgd2uhuKXvPD+PXB+gCEYYEaQdIRAjCOwAKNA==, + } object-assign@4.1.1: - resolution: {integrity: sha512-rJgTQnkUnH1sFw8yT6VSU3zD3sWmu6sZhIseY8VX+GRu3P6F7Fu+JNDoXfklElbLJSnc3FUQHVe4cU5hj+BcUg==} - engines: {node: '>=0.10.0'} + resolution: + { + integrity: sha512-rJgTQnkUnH1sFw8yT6VSU3zD3sWmu6sZhIseY8VX+GRu3P6F7Fu+JNDoXfklElbLJSnc3FUQHVe4cU5hj+BcUg==, + } + engines: { node: ">=0.10.0" } object-hash@2.2.0: - resolution: {integrity: sha512-gScRMn0bS5fH+IuwyIFgnh9zBdo4DV+6GhygmWM9HyNJSgS0hScp1f5vjtm7oIIOiT9trXrShAkLFSc2IqKNgw==} - engines: {node: '>= 6'} + resolution: + { + integrity: sha512-gScRMn0bS5fH+IuwyIFgnh9zBdo4DV+6GhygmWM9HyNJSgS0hScp1f5vjtm7oIIOiT9trXrShAkLFSc2IqKNgw==, + } + engines: { node: ">= 6" } object-inspect@1.13.4: - resolution: {integrity: sha512-W67iLl4J2EXEGTbfeHCffrjDfitvLANg0UlX3wFUUSTx92KXRFegMHUVgSqE+wvhAbi4WqjGg9czysTV2Epbew==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-W67iLl4J2EXEGTbfeHCffrjDfitvLANg0UlX3wFUUSTx92KXRFegMHUVgSqE+wvhAbi4WqjGg9czysTV2Epbew==, + } + engines: { node: ">= 0.4" } object-keys@1.1.1: - resolution: {integrity: sha512-NuAESUOUMrlIXOfHKzD6bpPu3tYt3xvjNdRIQ+FeT0lNb4K8WR70CaDxhuNguS2XG+GjkyMwOzsN5ZktImfhLA==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-NuAESUOUMrlIXOfHKzD6bpPu3tYt3xvjNdRIQ+FeT0lNb4K8WR70CaDxhuNguS2XG+GjkyMwOzsN5ZktImfhLA==, + } + engines: { node: ">= 0.4" } object.assign@4.1.7: - resolution: {integrity: sha512-nK28WOo+QIjBkDduTINE4JkF/UJJKyf2EJxvJKfblDpyg0Q+pkOHNTL0Qwy6NP6FhE/EnzV73BxxqcJaXY9anw==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-nK28WOo+QIjBkDduTINE4JkF/UJJKyf2EJxvJKfblDpyg0Q+pkOHNTL0Qwy6NP6FhE/EnzV73BxxqcJaXY9anw==, + } + engines: { node: ">= 0.4" } object.entries@1.1.9: - resolution: {integrity: sha512-8u/hfXFRBD1O0hPUjioLhoWFHRmt6tKA4/vZPyckBr18l1KE9uHrFaFaUi8MDRTpi4uak2goyPTSNJLXX2k2Hw==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-8u/hfXFRBD1O0hPUjioLhoWFHRmt6tKA4/vZPyckBr18l1KE9uHrFaFaUi8MDRTpi4uak2goyPTSNJLXX2k2Hw==, + } + engines: { node: ">= 0.4" } object.fromentries@2.0.8: - resolution: {integrity: sha512-k6E21FzySsSK5a21KRADBd/NGneRegFO5pLHfdQLpRDETUNJueLXs3WCzyQ3tFRDYgbq3KHGXfTbi2bs8WQ6rQ==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-k6E21FzySsSK5a21KRADBd/NGneRegFO5pLHfdQLpRDETUNJueLXs3WCzyQ3tFRDYgbq3KHGXfTbi2bs8WQ6rQ==, + } + engines: { node: ">= 0.4" } object.groupby@1.0.3: - resolution: {integrity: sha512-+Lhy3TQTuzXI5hevh8sBGqbmurHbbIjAi0Z4S63nthVLmLxfbj4T54a4CfZrXIrt9iP4mVAPYMo/v99taj3wjQ==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-+Lhy3TQTuzXI5hevh8sBGqbmurHbbIjAi0Z4S63nthVLmLxfbj4T54a4CfZrXIrt9iP4mVAPYMo/v99taj3wjQ==, + } + engines: { node: ">= 0.4" } object.values@1.2.1: - resolution: {integrity: sha512-gXah6aZrcUxjWg2zR2MwouP2eHlCBzdV4pygudehaKXSGW4v2AsRQUK+lwwXhii6KFZcunEnmSUoYp5CXibxtA==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-gXah6aZrcUxjWg2zR2MwouP2eHlCBzdV4pygudehaKXSGW4v2AsRQUK+lwwXhii6KFZcunEnmSUoYp5CXibxtA==, + } + engines: { node: ">= 0.4" } oidc-token-hash@5.1.0: - resolution: {integrity: sha512-y0W+X7Ppo7oZX6eovsRkuzcSM40Bicg2JEJkDJ4irIt1wsYAP5MLSNv+QAogO8xivMffw/9OvV3um1pxXgt1uA==} - engines: {node: ^10.13.0 || >=12.0.0} + resolution: + { + integrity: sha512-y0W+X7Ppo7oZX6eovsRkuzcSM40Bicg2JEJkDJ4irIt1wsYAP5MLSNv+QAogO8xivMffw/9OvV3um1pxXgt1uA==, + } + engines: { node: ^10.13.0 || >=12.0.0 } openid-client@5.7.1: - resolution: {integrity: sha512-jDBPgSVfTnkIh71Hg9pRvtJc6wTwqjRkN88+gCFtYWrlP4Yx2Dsrow8uPi3qLr/aeymPF3o2+dS+wOpglK04ew==} + resolution: + { + integrity: sha512-jDBPgSVfTnkIh71Hg9pRvtJc6wTwqjRkN88+gCFtYWrlP4Yx2Dsrow8uPi3qLr/aeymPF3o2+dS+wOpglK04ew==, + } optionator@0.9.4: - resolution: {integrity: sha512-6IpQ7mKUxRcZNLIObR0hz7lxsapSSIYNZJwXPGeF0mTVqGKFIXj1DQcMoT22S3ROcLyY/rz0PWaWZ9ayWmad9g==} - engines: {node: '>= 0.8.0'} + resolution: + { + integrity: sha512-6IpQ7mKUxRcZNLIObR0hz7lxsapSSIYNZJwXPGeF0mTVqGKFIXj1DQcMoT22S3ROcLyY/rz0PWaWZ9ayWmad9g==, + } + engines: { node: ">= 0.8.0" } own-keys@1.0.1: - resolution: {integrity: sha512-qFOyK5PjiWZd+QQIh+1jhdb9LpxTF0qs7Pm8o5QHYZ0M3vKqSqzsZaEB6oWlxZ+q2sJBMI/Ktgd2N5ZwQoRHfg==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-qFOyK5PjiWZd+QQIh+1jhdb9LpxTF0qs7Pm8o5QHYZ0M3vKqSqzsZaEB6oWlxZ+q2sJBMI/Ktgd2N5ZwQoRHfg==, + } + engines: { node: ">= 0.4" } p-limit@3.1.0: - resolution: {integrity: sha512-TYOanM3wGwNGsZN2cVTYPArw454xnXj5qmWF1bEoAc4+cU/ol7GVh7odevjp1FNHduHc3KZMcFduxU5Xc6uJRQ==} - engines: {node: '>=10'} + resolution: + { + integrity: sha512-TYOanM3wGwNGsZN2cVTYPArw454xnXj5qmWF1bEoAc4+cU/ol7GVh7odevjp1FNHduHc3KZMcFduxU5Xc6uJRQ==, + } + engines: { node: ">=10" } p-locate@5.0.0: - resolution: {integrity: sha512-LaNjtRWUBY++zB5nE/NwcaoMylSPk+S+ZHNB1TzdbMJMny6dynpAGt7X/tl/QYq3TIeE6nxHppbo2LGymrG5Pw==} - engines: {node: '>=10'} + resolution: + { + integrity: sha512-LaNjtRWUBY++zB5nE/NwcaoMylSPk+S+ZHNB1TzdbMJMny6dynpAGt7X/tl/QYq3TIeE6nxHppbo2LGymrG5Pw==, + } + engines: { node: ">=10" } package-json-from-dist@1.0.1: - resolution: {integrity: sha512-UEZIS3/by4OC8vL3P2dTXRETpebLI2NiI5vIrjaD/5UtrkFX/tNbwjTSRAGC/+7CAo2pIcBaRgWmcBBHcsaCIw==} + resolution: + { + integrity: sha512-UEZIS3/by4OC8vL3P2dTXRETpebLI2NiI5vIrjaD/5UtrkFX/tNbwjTSRAGC/+7CAo2pIcBaRgWmcBBHcsaCIw==, + } parent-module@1.0.1: - resolution: {integrity: sha512-GQ2EWRpQV8/o+Aw8YqtfZZPfNRWZYkbidE9k5rpl/hC3vtHHBfGm2Ifi6qWV+coDGkrUKZAxE3Lot5kcsRlh+g==} - engines: {node: '>=6'} + resolution: + { + integrity: sha512-GQ2EWRpQV8/o+Aw8YqtfZZPfNRWZYkbidE9k5rpl/hC3vtHHBfGm2Ifi6qWV+coDGkrUKZAxE3Lot5kcsRlh+g==, + } + engines: { node: ">=6" } parse-entities@4.0.2: - resolution: {integrity: sha512-GG2AQYWoLgL877gQIKeRPGO1xF9+eG1ujIb5soS5gPvLQ1y2o8FL90w2QWNdf9I361Mpp7726c+lj3U0qK1uGw==} + resolution: + { + integrity: sha512-GG2AQYWoLgL877gQIKeRPGO1xF9+eG1ujIb5soS5gPvLQ1y2o8FL90w2QWNdf9I361Mpp7726c+lj3U0qK1uGw==, + } parse5@7.3.0: - resolution: {integrity: sha512-IInvU7fabl34qmi9gY8XOVxhYyMyuH2xUNpb2q8/Y+7552KlejkRvqvD19nMoUW/uQGGbqNpA6Tufu5FL5BZgw==} + resolution: + { + integrity: sha512-IInvU7fabl34qmi9gY8XOVxhYyMyuH2xUNpb2q8/Y+7552KlejkRvqvD19nMoUW/uQGGbqNpA6Tufu5FL5BZgw==, + } path-exists@4.0.0: - resolution: {integrity: sha512-ak9Qy5Q7jYb2Wwcey5Fpvg2KoAc/ZIhLSLOSBmRmygPsGwkVVt0fZa0qrtMz+m6tJTAHfZQ8FnmB4MG4LWy7/w==} - engines: {node: '>=8'} + resolution: + { + integrity: sha512-ak9Qy5Q7jYb2Wwcey5Fpvg2KoAc/ZIhLSLOSBmRmygPsGwkVVt0fZa0qrtMz+m6tJTAHfZQ8FnmB4MG4LWy7/w==, + } + engines: { node: ">=8" } path-key@3.1.1: - resolution: {integrity: sha512-ojmeN0qd+y0jszEtoY48r0Peq5dwMEkIlCOu6Q5f41lfkswXuKtYrhgoTpLnyIcHm24Uhqx+5Tqm2InSwLhE6Q==} - engines: {node: '>=8'} + resolution: + { + integrity: sha512-ojmeN0qd+y0jszEtoY48r0Peq5dwMEkIlCOu6Q5f41lfkswXuKtYrhgoTpLnyIcHm24Uhqx+5Tqm2InSwLhE6Q==, + } + engines: { node: ">=8" } path-parse@1.0.7: - resolution: {integrity: sha512-LDJzPVEEEPR+y48z93A0Ed0yXb8pAByGWo/k5YYdYgpY2/2EsOsksJrq7lOHxryrVOn1ejG6oAp8ahvOIQD8sw==} + resolution: + { + integrity: sha512-LDJzPVEEEPR+y48z93A0Ed0yXb8pAByGWo/k5YYdYgpY2/2EsOsksJrq7lOHxryrVOn1ejG6oAp8ahvOIQD8sw==, + } path-scurry@1.11.1: - resolution: {integrity: sha512-Xa4Nw17FS9ApQFJ9umLiJS4orGjm7ZzwUrwamcGQuHSzDyth9boKDaycYdDcZDuqYATXw4HFXgaqWTctW/v1HA==} - engines: {node: '>=16 || 14 >=14.18'} + resolution: + { + integrity: sha512-Xa4Nw17FS9ApQFJ9umLiJS4orGjm7ZzwUrwamcGQuHSzDyth9boKDaycYdDcZDuqYATXw4HFXgaqWTctW/v1HA==, + } + engines: { node: ">=16 || 14 >=14.18" } path-type@6.0.0: - resolution: {integrity: sha512-Vj7sf++t5pBD637NSfkxpHSMfWaeig5+DKWLhcqIYx6mWQz5hdJTGDVMQiJcw1ZYkhs7AazKDGpRVji1LJCZUQ==} - engines: {node: '>=18'} + resolution: + { + integrity: sha512-Vj7sf++t5pBD637NSfkxpHSMfWaeig5+DKWLhcqIYx6mWQz5hdJTGDVMQiJcw1ZYkhs7AazKDGpRVji1LJCZUQ==, + } + engines: { node: ">=18" } pathe@2.0.3: - resolution: {integrity: sha512-WUjGcAqP1gQacoQe+OBJsFA7Ld4DyXuUIjZ5cc75cLHvJ7dtNsTugphxIADwspS+AraAUePCKrSVtPLFj/F88w==} + resolution: + { + integrity: sha512-WUjGcAqP1gQacoQe+OBJsFA7Ld4DyXuUIjZ5cc75cLHvJ7dtNsTugphxIADwspS+AraAUePCKrSVtPLFj/F88w==, + } pathval@2.0.1: - resolution: {integrity: sha512-//nshmD55c46FuFw26xV/xFAaB5HF9Xdap7HJBBnrKdAd6/GxDBaNA1870O79+9ueg61cZLSVc+OaFlfmObYVQ==} - engines: {node: '>= 14.16'} + resolution: + { + integrity: sha512-//nshmD55c46FuFw26xV/xFAaB5HF9Xdap7HJBBnrKdAd6/GxDBaNA1870O79+9ueg61cZLSVc+OaFlfmObYVQ==, + } + engines: { node: ">= 14.16" } pg-cloudflare@1.2.7: - resolution: {integrity: sha512-YgCtzMH0ptvZJslLM1ffsY4EuGaU0cx4XSdXLRFae8bPP4dS5xL1tNB3k2o/N64cHJpwU7dxKli/nZ2lUa5fLg==} + resolution: + { + integrity: sha512-YgCtzMH0ptvZJslLM1ffsY4EuGaU0cx4XSdXLRFae8bPP4dS5xL1tNB3k2o/N64cHJpwU7dxKli/nZ2lUa5fLg==, + } pg-connection-string@2.9.1: - resolution: {integrity: sha512-nkc6NpDcvPVpZXxrreI/FOtX3XemeLl8E0qFr6F2Lrm/I8WOnaWNhIPK2Z7OHpw7gh5XJThi6j6ppgNoaT1w4w==} + resolution: + { + integrity: sha512-nkc6NpDcvPVpZXxrreI/FOtX3XemeLl8E0qFr6F2Lrm/I8WOnaWNhIPK2Z7OHpw7gh5XJThi6j6ppgNoaT1w4w==, + } pg-int8@1.0.1: - resolution: {integrity: sha512-WCtabS6t3c8SkpDBUlb1kjOs7l66xsGdKpIPZsg4wR+B3+u9UAum2odSsF9tnvxg80h4ZxLWMy4pRjOsFIqQpw==} - engines: {node: '>=4.0.0'} + resolution: + { + integrity: sha512-WCtabS6t3c8SkpDBUlb1kjOs7l66xsGdKpIPZsg4wR+B3+u9UAum2odSsF9tnvxg80h4ZxLWMy4pRjOsFIqQpw==, + } + engines: { node: ">=4.0.0" } pg-pool@3.10.1: - resolution: {integrity: sha512-Tu8jMlcX+9d8+QVzKIvM/uJtp07PKr82IUOYEphaWcoBhIYkoHpLXN3qO59nAI11ripznDsEzEv8nUxBVWajGg==} + resolution: + { + integrity: sha512-Tu8jMlcX+9d8+QVzKIvM/uJtp07PKr82IUOYEphaWcoBhIYkoHpLXN3qO59nAI11ripznDsEzEv8nUxBVWajGg==, + } peerDependencies: - pg: '>=8.0' + pg: ">=8.0" pg-protocol@1.10.3: - resolution: {integrity: sha512-6DIBgBQaTKDJyxnXaLiLR8wBpQQcGWuAESkRBX/t6OwA8YsqP+iVSiond2EDy6Y/dsGk8rh/jtax3js5NeV7JQ==} + resolution: + { + integrity: sha512-6DIBgBQaTKDJyxnXaLiLR8wBpQQcGWuAESkRBX/t6OwA8YsqP+iVSiond2EDy6Y/dsGk8rh/jtax3js5NeV7JQ==, + } pg-types@2.2.0: - resolution: {integrity: sha512-qTAAlrEsl8s4OiEQY69wDvcMIdQN6wdz5ojQiOy6YRMuynxenON0O5oCpJI6lshc6scgAY8qvJ2On/p+CXY0GA==} - engines: {node: '>=4'} + resolution: + { + integrity: sha512-qTAAlrEsl8s4OiEQY69wDvcMIdQN6wdz5ojQiOy6YRMuynxenON0O5oCpJI6lshc6scgAY8qvJ2On/p+CXY0GA==, + } + engines: { node: ">=4" } pg@8.16.3: - resolution: {integrity: sha512-enxc1h0jA/aq5oSDMvqyW3q89ra6XIIDZgCX9vkMrnz5DFTw/Ny3Li2lFQ+pt3L6MCgm/5o2o8HW9hiJji+xvw==} - engines: {node: '>= 16.0.0'} + resolution: + { + integrity: sha512-enxc1h0jA/aq5oSDMvqyW3q89ra6XIIDZgCX9vkMrnz5DFTw/Ny3Li2lFQ+pt3L6MCgm/5o2o8HW9hiJji+xvw==, + } + engines: { node: ">= 16.0.0" } peerDependencies: - pg-native: '>=3.0.1' + pg-native: ">=3.0.1" peerDependenciesMeta: pg-native: optional: true pgpass@1.0.5: - resolution: {integrity: sha512-FdW9r/jQZhSeohs1Z3sI1yxFQNFvMcnmfuj4WBMUTxOrAyLMaTcE1aAMBiTlbMNaXvBCQuVi0R7hd8udDSP7ug==} + resolution: + { + integrity: sha512-FdW9r/jQZhSeohs1Z3sI1yxFQNFvMcnmfuj4WBMUTxOrAyLMaTcE1aAMBiTlbMNaXvBCQuVi0R7hd8udDSP7ug==, + } picocolors@1.1.1: - resolution: {integrity: sha512-xceH2snhtb5M9liqDsmEw56le376mTZkEX/jEb/RxNFyegNul7eNslCXP9FDj/Lcu0X8KEyMceP2ntpaHrDEVA==} + resolution: + { + integrity: sha512-xceH2snhtb5M9liqDsmEw56le376mTZkEX/jEb/RxNFyegNul7eNslCXP9FDj/Lcu0X8KEyMceP2ntpaHrDEVA==, + } picomatch@2.3.1: - resolution: {integrity: sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA==} - engines: {node: '>=8.6'} + resolution: + { + integrity: sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA==, + } + engines: { node: ">=8.6" } picomatch@4.0.2: - resolution: {integrity: sha512-M7BAV6Rlcy5u+m6oPhAPFgJTzAioX/6B0DxyvDlo9l8+T3nLKbrczg2WLUyzd45L8RqfUMyGPzekbMvX2Ldkwg==} - engines: {node: '>=12'} + resolution: + { + integrity: sha512-M7BAV6Rlcy5u+m6oPhAPFgJTzAioX/6B0DxyvDlo9l8+T3nLKbrczg2WLUyzd45L8RqfUMyGPzekbMvX2Ldkwg==, + } + engines: { node: ">=12" } playwright-core@1.53.1: - resolution: {integrity: sha512-Z46Oq7tLAyT0lGoFx4DOuB1IA9D1TPj0QkYxpPVUnGDqHHvDpCftu1J2hM2PiWsNMoZh8+LQaarAWcDfPBc6zg==} - engines: {node: '>=18'} + resolution: + { + integrity: sha512-Z46Oq7tLAyT0lGoFx4DOuB1IA9D1TPj0QkYxpPVUnGDqHHvDpCftu1J2hM2PiWsNMoZh8+LQaarAWcDfPBc6zg==, + } + engines: { node: ">=18" } hasBin: true playwright@1.53.1: - resolution: {integrity: sha512-LJ13YLr/ocweuwxyGf1XNFWIU4M2zUSo149Qbp+A4cpwDjsxRPj7k6H25LBrEHiEwxvRbD8HdwvQmRMSvquhYw==} - engines: {node: '>=18'} + resolution: + { + integrity: sha512-LJ13YLr/ocweuwxyGf1XNFWIU4M2zUSo149Qbp+A4cpwDjsxRPj7k6H25LBrEHiEwxvRbD8HdwvQmRMSvquhYw==, + } + engines: { node: ">=18" } hasBin: true possible-typed-array-names@1.1.0: - resolution: {integrity: sha512-/+5VFTchJDoVj3bhoqi6UeymcD00DAwb1nJwamzPvHEszJ4FpF6SNNbUbOS8yI56qHzdV8eK0qEfOSiodkTdxg==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-/+5VFTchJDoVj3bhoqi6UeymcD00DAwb1nJwamzPvHEszJ4FpF6SNNbUbOS8yI56qHzdV8eK0qEfOSiodkTdxg==, + } + engines: { node: ">= 0.4" } postcss@8.4.31: - resolution: {integrity: sha512-PS08Iboia9mts/2ygV3eLpY5ghnUcfLV/EXTOW1E2qYxJKGGBUtNjN76FYHnMs36RmARn41bC0AZmn+rR0OVpQ==} - engines: {node: ^10 || ^12 || >=14} + resolution: + { + integrity: sha512-PS08Iboia9mts/2ygV3eLpY5ghnUcfLV/EXTOW1E2qYxJKGGBUtNjN76FYHnMs36RmARn41bC0AZmn+rR0OVpQ==, + } + engines: { node: ^10 || ^12 || >=14 } postcss@8.5.6: - resolution: {integrity: sha512-3Ybi1tAuwAP9s0r1UQ2J4n5Y0G05bJkpUIO0/bI9MhwmD70S5aTWbXGBwxHrelT+XM1k6dM0pk+SwNkpTRN7Pg==} - engines: {node: ^10 || ^12 || >=14} + resolution: + { + integrity: sha512-3Ybi1tAuwAP9s0r1UQ2J4n5Y0G05bJkpUIO0/bI9MhwmD70S5aTWbXGBwxHrelT+XM1k6dM0pk+SwNkpTRN7Pg==, + } + engines: { node: ^10 || ^12 || >=14 } postgres-array@2.0.0: - resolution: {integrity: sha512-VpZrUqU5A69eQyW2c5CA1jtLecCsN2U/bD6VilrFDWq5+5UIEVO7nazS3TEcHf1zuPYO/sqGvUvW62g86RXZuA==} - engines: {node: '>=4'} + resolution: + { + integrity: sha512-VpZrUqU5A69eQyW2c5CA1jtLecCsN2U/bD6VilrFDWq5+5UIEVO7nazS3TEcHf1zuPYO/sqGvUvW62g86RXZuA==, + } + engines: { node: ">=4" } postgres-array@3.0.4: - resolution: {integrity: sha512-nAUSGfSDGOaOAEGwqsRY27GPOea7CNipJPOA7lPbdEpx5Kg3qzdP0AaWC5MlhTWV9s4hFX39nomVZ+C4tnGOJQ==} - engines: {node: '>=12'} + resolution: + { + integrity: sha512-nAUSGfSDGOaOAEGwqsRY27GPOea7CNipJPOA7lPbdEpx5Kg3qzdP0AaWC5MlhTWV9s4hFX39nomVZ+C4tnGOJQ==, + } + engines: { node: ">=12" } postgres-bytea@1.0.0: - resolution: {integrity: sha512-xy3pmLuQqRBZBXDULy7KbaitYqLcmxigw14Q5sj8QBVLqEwXfeybIKVWiqAXTlcvdvb0+xkOtDbfQMOf4lST1w==} - engines: {node: '>=0.10.0'} + resolution: + { + integrity: sha512-xy3pmLuQqRBZBXDULy7KbaitYqLcmxigw14Q5sj8QBVLqEwXfeybIKVWiqAXTlcvdvb0+xkOtDbfQMOf4lST1w==, + } + engines: { node: ">=0.10.0" } postgres-date@1.0.7: - resolution: {integrity: sha512-suDmjLVQg78nMK2UZ454hAG+OAW+HQPZ6n++TNDUX+L0+uUlLywnoxJKDou51Zm+zTCjrCl0Nq6J9C5hP9vK/Q==} - engines: {node: '>=0.10.0'} + resolution: + { + integrity: sha512-suDmjLVQg78nMK2UZ454hAG+OAW+HQPZ6n++TNDUX+L0+uUlLywnoxJKDou51Zm+zTCjrCl0Nq6J9C5hP9vK/Q==, + } + engines: { node: ">=0.10.0" } postgres-interval@1.2.0: - resolution: {integrity: sha512-9ZhXKM/rw350N1ovuWHbGxnGh/SNJ4cnxHiM0rxE4VN41wsg8P8zWn9hv/buK00RP4WvlOyr/RBDiptyxVbkZQ==} - engines: {node: '>=0.10.0'} + resolution: + { + integrity: sha512-9ZhXKM/rw350N1ovuWHbGxnGh/SNJ4cnxHiM0rxE4VN41wsg8P8zWn9hv/buK00RP4WvlOyr/RBDiptyxVbkZQ==, + } + engines: { node: ">=0.10.0" } preact-render-to-string@5.2.6: - resolution: {integrity: sha512-JyhErpYOvBV1hEPwIxc/fHWXPfnEGdRKxc8gFdAZ7XV4tlzyzG847XAyEZqoDnynP88akM4eaHcSOzNcLWFguw==} + resolution: + { + integrity: sha512-JyhErpYOvBV1hEPwIxc/fHWXPfnEGdRKxc8gFdAZ7XV4tlzyzG847XAyEZqoDnynP88akM4eaHcSOzNcLWFguw==, + } peerDependencies: - preact: '>=10' + preact: ">=10" preact@10.26.9: - resolution: {integrity: sha512-SSjF9vcnF27mJK1XyFMNJzFd5u3pQiATFqoaDy03XuN00u4ziveVVEGt5RKJrDR8MHE/wJo9Nnad56RLzS2RMA==} + resolution: + { + integrity: sha512-SSjF9vcnF27mJK1XyFMNJzFd5u3pQiATFqoaDy03XuN00u4ziveVVEGt5RKJrDR8MHE/wJo9Nnad56RLzS2RMA==, + } prelude-ls@1.2.1: - resolution: {integrity: sha512-vkcDPrRZo1QZLbn5RLGPpg/WmIQ65qoWWhcGKf/b5eplkkarX0m9z8ppCat4mlOqUsWpyNuYgO3VRyrYHSzX5g==} - engines: {node: '>= 0.8.0'} + resolution: + { + integrity: sha512-vkcDPrRZo1QZLbn5RLGPpg/WmIQ65qoWWhcGKf/b5eplkkarX0m9z8ppCat4mlOqUsWpyNuYgO3VRyrYHSzX5g==, + } + engines: { node: ">= 0.8.0" } prettier-linter-helpers@1.0.0: - resolution: {integrity: sha512-GbK2cP9nraSSUF9N2XwUwqfzlAFlMNYYl+ShE/V+H8a9uNl/oUqB1w2EL54Jh0OlyRSd8RfWYJ3coVS4TROP2w==} - engines: {node: '>=6.0.0'} + resolution: + { + integrity: sha512-GbK2cP9nraSSUF9N2XwUwqfzlAFlMNYYl+ShE/V+H8a9uNl/oUqB1w2EL54Jh0OlyRSd8RfWYJ3coVS4TROP2w==, + } + engines: { node: ">=6.0.0" } prettier-plugin-jinja-template@2.1.0: - resolution: {integrity: sha512-mzoCp2Oy9BDSug80fw3B3J4n4KQj1hRvoQOL1akqcDKBb5nvYxrik9zUEDs4AEJ6nK7QDTGoH0y9rx7AlnQ78Q==} + resolution: + { + integrity: sha512-mzoCp2Oy9BDSug80fw3B3J4n4KQj1hRvoQOL1akqcDKBb5nvYxrik9zUEDs4AEJ6nK7QDTGoH0y9rx7AlnQ78Q==, + } peerDependencies: prettier: ^3.0.0 prettier@3.6.2: - resolution: {integrity: sha512-I7AIg5boAr5R0FFtJ6rCfD+LFsWHp81dolrFD8S79U9tb8Az2nGrJncnMSnys+bpQJfRUzqs9hnA81OAA3hCuQ==} - engines: {node: '>=14'} + resolution: + { + integrity: sha512-I7AIg5boAr5R0FFtJ6rCfD+LFsWHp81dolrFD8S79U9tb8Az2nGrJncnMSnys+bpQJfRUzqs9hnA81OAA3hCuQ==, + } + engines: { node: ">=14" } hasBin: true pretty-format@27.5.1: - resolution: {integrity: sha512-Qb1gy5OrP5+zDf2Bvnzdl3jsTf1qXVMazbvCoKhtKqVs4/YK4ozX4gKQJJVyNe+cajNPn0KoC0MC3FUmaHWEmQ==} - engines: {node: ^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0} + resolution: + { + integrity: sha512-Qb1gy5OrP5+zDf2Bvnzdl3jsTf1qXVMazbvCoKhtKqVs4/YK4ozX4gKQJJVyNe+cajNPn0KoC0MC3FUmaHWEmQ==, + } + engines: { node: ^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0 } pretty-format@3.8.0: - resolution: {integrity: sha512-WuxUnVtlWL1OfZFQFuqvnvs6MiAGk9UNsBostyBOB0Is9wb5uRESevA6rnl/rkksXaGX3GzZhPup5d6Vp1nFew==} + resolution: + { + integrity: sha512-WuxUnVtlWL1OfZFQFuqvnvs6MiAGk9UNsBostyBOB0Is9wb5uRESevA6rnl/rkksXaGX3GzZhPup5d6Vp1nFew==, + } prisma@6.10.1: - resolution: {integrity: sha512-khhlC/G49E4+uyA3T3H5PRBut486HD2bDqE2+rvkU0pwk9IAqGFacLFUyIx9Uw+W2eCtf6XGwsp+/strUwMNPw==} - engines: {node: '>=18.18'} + resolution: + { + integrity: sha512-khhlC/G49E4+uyA3T3H5PRBut486HD2bDqE2+rvkU0pwk9IAqGFacLFUyIx9Uw+W2eCtf6XGwsp+/strUwMNPw==, + } + engines: { node: ">=18.18" } hasBin: true peerDependencies: - typescript: '>=5.1.0' + typescript: ">=5.1.0" peerDependenciesMeta: typescript: optional: true prop-types@15.8.1: - resolution: {integrity: sha512-oj87CgZICdulUohogVAR7AjlC0327U4el4L6eAvOqCeudMDVU0NThNaV+b9Df4dXgSP1gXMTnPdhfe/2qDH5cg==} + resolution: + { + integrity: sha512-oj87CgZICdulUohogVAR7AjlC0327U4el4L6eAvOqCeudMDVU0NThNaV+b9Df4dXgSP1gXMTnPdhfe/2qDH5cg==, + } property-information@6.5.0: - resolution: {integrity: sha512-PgTgs/BlvHxOu8QuEN7wi5A0OmXaBcHpmCSTehcs6Uuu9IkDIEo13Hy7n898RHfrQ49vKCoGeWZSaAK01nwVig==} + resolution: + { + integrity: sha512-PgTgs/BlvHxOu8QuEN7wi5A0OmXaBcHpmCSTehcs6Uuu9IkDIEo13Hy7n898RHfrQ49vKCoGeWZSaAK01nwVig==, + } property-information@7.1.0: - resolution: {integrity: sha512-TwEZ+X+yCJmYfL7TPUOcvBZ4QfoT5YenQiJuX//0th53DE6w0xxLEtfK3iyryQFddXuvkIk51EEgrJQ0WJkOmQ==} + resolution: + { + integrity: sha512-TwEZ+X+yCJmYfL7TPUOcvBZ4QfoT5YenQiJuX//0th53DE6w0xxLEtfK3iyryQFddXuvkIk51EEgrJQ0WJkOmQ==, + } punycode.js@2.3.1: - resolution: {integrity: sha512-uxFIHU0YlHYhDQtV4R9J6a52SLx28BCjT+4ieh7IGbgwVJWO+km431c4yRlREUAsAmt/uMjQUyQHNEPf0M39CA==} - engines: {node: '>=6'} + resolution: + { + integrity: sha512-uxFIHU0YlHYhDQtV4R9J6a52SLx28BCjT+4ieh7IGbgwVJWO+km431c4yRlREUAsAmt/uMjQUyQHNEPf0M39CA==, + } + engines: { node: ">=6" } punycode@2.3.1: - resolution: {integrity: sha512-vYt7UD1U9Wg6138shLtLOvdAu+8DsC/ilFtEVHcH+wydcSpNE20AfSOduf6MkRFahL5FY7X1oU7nKVZFtfq8Fg==} - engines: {node: '>=6'} + resolution: + { + integrity: sha512-vYt7UD1U9Wg6138shLtLOvdAu+8DsC/ilFtEVHcH+wydcSpNE20AfSOduf6MkRFahL5FY7X1oU7nKVZFtfq8Fg==, + } + engines: { node: ">=6" } queue-microtask@1.2.3: - resolution: {integrity: sha512-NuaNSa6flKT5JaSYQzJok04JzTL1CA6aGhv5rfLW3PgqA+M2ChpZQnAC8h8i4ZFkBS8X5RqkDBHA7r4hej3K9A==} + resolution: + { + integrity: sha512-NuaNSa6flKT5JaSYQzJok04JzTL1CA6aGhv5rfLW3PgqA+M2ChpZQnAC8h8i4ZFkBS8X5RqkDBHA7r4hej3K9A==, + } quickselect@1.1.1: - resolution: {integrity: sha512-qN0Gqdw4c4KGPsBOQafj6yj/PA6c/L63f6CaZ/DCF/xF4Esu3jVmKLUDYxghFx8Kb/O7y9tI7x2RjTSXwdK1iQ==} + resolution: + { + integrity: sha512-qN0Gqdw4c4KGPsBOQafj6yj/PA6c/L63f6CaZ/DCF/xF4Esu3jVmKLUDYxghFx8Kb/O7y9tI7x2RjTSXwdK1iQ==, + } rbush@2.0.2: - resolution: {integrity: sha512-XBOuALcTm+O/H8G90b6pzu6nX6v2zCKiFG4BJho8a+bY6AER6t8uQUZdi5bomQc0AprCWhEGa7ncAbbRap0bRA==} + resolution: + { + integrity: sha512-XBOuALcTm+O/H8G90b6pzu6nX6v2zCKiFG4BJho8a+bY6AER6t8uQUZdi5bomQc0AprCWhEGa7ncAbbRap0bRA==, + } react-dom@19.1.0: - resolution: {integrity: sha512-Xs1hdnE+DyKgeHJeJznQmYMIBG3TKIHJJT95Q58nHLSrElKlGQqDTR2HQ9fx5CN/Gk6Vh/kupBTDLU11/nDk/g==} + resolution: + { + integrity: sha512-Xs1hdnE+DyKgeHJeJznQmYMIBG3TKIHJJT95Q58nHLSrElKlGQqDTR2HQ9fx5CN/Gk6Vh/kupBTDLU11/nDk/g==, + } peerDependencies: react: ^19.1.0 react-is@16.13.1: - resolution: {integrity: sha512-24e6ynE2H+OKt4kqsOvNd8kBpV65zoxbA4BVsEOB3ARVWQki/DHzaUoC5KuON/BiccDaCCTZBuOcfZs70kR8bQ==} + resolution: + { + integrity: sha512-24e6ynE2H+OKt4kqsOvNd8kBpV65zoxbA4BVsEOB3ARVWQki/DHzaUoC5KuON/BiccDaCCTZBuOcfZs70kR8bQ==, + } react-is@17.0.2: - resolution: {integrity: sha512-w2GsyukL62IJnlaff/nRegPQR94C/XXamvMWmSHRJ4y7Ts/4ocGRmTHvOs8PSE6pB3dWOrD/nueuU5sduBsQ4w==} + resolution: + { + integrity: sha512-w2GsyukL62IJnlaff/nRegPQR94C/XXamvMWmSHRJ4y7Ts/4ocGRmTHvOs8PSE6pB3dWOrD/nueuU5sduBsQ4w==, + } react-leaflet@5.0.0: - resolution: {integrity: sha512-CWbTpr5vcHw5bt9i4zSlPEVQdTVcML390TjeDG0cK59z1ylexpqC6M1PJFjV8jD7CF+ACBFsLIDs6DRMoLEofw==} + resolution: + { + integrity: sha512-CWbTpr5vcHw5bt9i4zSlPEVQdTVcML390TjeDG0cK59z1ylexpqC6M1PJFjV8jD7CF+ACBFsLIDs6DRMoLEofw==, + } peerDependencies: leaflet: ^1.9.0 react: ^19.0.0 react-dom: ^19.0.0 react-markdown@10.1.0: - resolution: {integrity: sha512-qKxVopLT/TyA6BX3Ue5NwabOsAzm0Q7kAPwq6L+wWDwisYs7R8vZ0nRXqq6rkueboxpkjvLGU9fWifiX/ZZFxQ==} + resolution: + { + integrity: sha512-qKxVopLT/TyA6BX3Ue5NwabOsAzm0Q7kAPwq6L+wWDwisYs7R8vZ0nRXqq6rkueboxpkjvLGU9fWifiX/ZZFxQ==, + } peerDependencies: - '@types/react': '>=18' - react: '>=18' + "@types/react": ">=18" + react: ">=18" react-redux@9.2.0: - resolution: {integrity: sha512-ROY9fvHhwOD9ySfrF0wmvu//bKCQ6AeZZq1nJNtbDC+kk5DuSuNX/n6YWYF/SYy7bSba4D4FSz8DJeKY/S/r+g==} + resolution: + { + integrity: sha512-ROY9fvHhwOD9ySfrF0wmvu//bKCQ6AeZZq1nJNtbDC+kk5DuSuNX/n6YWYF/SYy7bSba4D4FSz8DJeKY/S/r+g==, + } peerDependencies: - '@types/react': ^18.2.25 || ^19 + "@types/react": ^18.2.25 || ^19 react: ^18.0 || ^19 redux: ^5.0.0 peerDependenciesMeta: - '@types/react': + "@types/react": optional: true redux: optional: true react-refresh@0.17.0: - resolution: {integrity: sha512-z6F7K9bV85EfseRCp2bzrpyQ0Gkw1uLoCel9XBVWPg/TjRj94SkJzUTGfOa4bs7iJvBWtQG0Wq7wnI0syw3EBQ==} - engines: {node: '>=0.10.0'} + resolution: + { + integrity: sha512-z6F7K9bV85EfseRCp2bzrpyQ0Gkw1uLoCel9XBVWPg/TjRj94SkJzUTGfOa4bs7iJvBWtQG0Wq7wnI0syw3EBQ==, + } + engines: { node: ">=0.10.0" } react-remove-scroll-bar@2.3.8: - resolution: {integrity: sha512-9r+yi9+mgU33AKcj6IbT9oRCO78WriSj6t/cF8DWBZJ9aOGPOTEDvdUDz1FwKim7QXWwmHqtdHnRJfhAxEG46Q==} - engines: {node: '>=10'} + resolution: + { + integrity: sha512-9r+yi9+mgU33AKcj6IbT9oRCO78WriSj6t/cF8DWBZJ9aOGPOTEDvdUDz1FwKim7QXWwmHqtdHnRJfhAxEG46Q==, + } + engines: { node: ">=10" } peerDependencies: - '@types/react': '*' + "@types/react": "*" react: ^16.8.0 || ^17.0.0 || ^18.0.0 || ^19.0.0 peerDependenciesMeta: - '@types/react': + "@types/react": optional: true react-remove-scroll@2.7.1: - resolution: {integrity: sha512-HpMh8+oahmIdOuS5aFKKY6Pyog+FNaZV/XyJOq7b4YFwsFHe5yYfdbIalI4k3vU2nSDql7YskmUseHsRrJqIPA==} - engines: {node: '>=10'} + resolution: + { + integrity: sha512-HpMh8+oahmIdOuS5aFKKY6Pyog+FNaZV/XyJOq7b4YFwsFHe5yYfdbIalI4k3vU2nSDql7YskmUseHsRrJqIPA==, + } + engines: { node: ">=10" } peerDependencies: - '@types/react': '*' + "@types/react": "*" react: ^16.8.0 || ^17.0.0 || ^18.0.0 || ^19.0.0 || ^19.0.0-rc peerDependenciesMeta: - '@types/react': + "@types/react": optional: true react-style-singleton@2.2.3: - resolution: {integrity: sha512-b6jSvxvVnyptAiLjbkWLE/lOnR4lfTtDAl+eUC7RZy+QQWc6wRzIV2CE6xBuMmDxc2qIihtDCZD5NPOFl7fRBQ==} - engines: {node: '>=10'} + resolution: + { + integrity: sha512-b6jSvxvVnyptAiLjbkWLE/lOnR4lfTtDAl+eUC7RZy+QQWc6wRzIV2CE6xBuMmDxc2qIihtDCZD5NPOFl7fRBQ==, + } + engines: { node: ">=10" } peerDependencies: - '@types/react': '*' + "@types/react": "*" react: ^16.8.0 || ^17.0.0 || ^18.0.0 || ^19.0.0 || ^19.0.0-rc peerDependenciesMeta: - '@types/react': + "@types/react": optional: true react@19.1.0: - resolution: {integrity: sha512-FS+XFBNvn3GTAWq26joslQgWNoFu08F4kl0J4CgdNKADkdSGXQyTCnKteIAJy96Br6YbpEU1LSzV5dYtjMkMDg==} - engines: {node: '>=0.10.0'} + resolution: + { + integrity: sha512-FS+XFBNvn3GTAWq26joslQgWNoFu08F4kl0J4CgdNKADkdSGXQyTCnKteIAJy96Br6YbpEU1LSzV5dYtjMkMDg==, + } + engines: { node: ">=0.10.0" } recharts@3.0.2: - resolution: {integrity: sha512-eDc3ile9qJU9Dp/EekSthQPhAVPG48/uM47jk+PF7VBQngxeW3cwQpPHb/GHC1uqwyCRWXcIrDzuHRVrnRryoQ==} - engines: {node: '>=18'} + resolution: + { + integrity: sha512-eDc3ile9qJU9Dp/EekSthQPhAVPG48/uM47jk+PF7VBQngxeW3cwQpPHb/GHC1uqwyCRWXcIrDzuHRVrnRryoQ==, + } + engines: { node: ">=18" } peerDependencies: react: ^16.8.0 || ^17.0.0 || ^18.0.0 || ^19.0.0 react-dom: ^16.0.0 || ^17.0.0 || ^18.0.0 || ^19.0.0 react-is: ^16.8.0 || ^17.0.0 || ^18.0.0 || ^19.0.0 redux-thunk@3.1.0: - resolution: {integrity: sha512-NW2r5T6ksUKXCabzhL9z+h206HQw/NJkcLm1GPImRQ8IzfXwRGqjVhKJGauHirT0DAuyy6hjdnMZaRoAcy0Klw==} + resolution: + { + integrity: sha512-NW2r5T6ksUKXCabzhL9z+h206HQw/NJkcLm1GPImRQ8IzfXwRGqjVhKJGauHirT0DAuyy6hjdnMZaRoAcy0Klw==, + } peerDependencies: redux: ^5.0.0 redux@5.0.1: - resolution: {integrity: sha512-M9/ELqF6fy8FwmkpnF0S3YKOqMyoWJ4+CS5Efg2ct3oY9daQvd/Pc71FpGZsVsbl3Cpb+IIcjBDUnnyBdQbq4w==} + resolution: + { + integrity: sha512-M9/ELqF6fy8FwmkpnF0S3YKOqMyoWJ4+CS5Efg2ct3oY9daQvd/Pc71FpGZsVsbl3Cpb+IIcjBDUnnyBdQbq4w==, + } reflect.getprototypeof@1.0.10: - resolution: {integrity: sha512-00o4I+DVrefhv+nX0ulyi3biSHCPDe+yLv5o/p6d/UVlirijB8E16FtfwSAi4g3tcqrQ4lRAqQSoFEZJehYEcw==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-00o4I+DVrefhv+nX0ulyi3biSHCPDe+yLv5o/p6d/UVlirijB8E16FtfwSAi4g3tcqrQ4lRAqQSoFEZJehYEcw==, + } + engines: { node: ">= 0.4" } regexp.prototype.flags@1.5.4: - resolution: {integrity: sha512-dYqgNSZbDwkaJ2ceRd9ojCGjBq+mOm9LmtXnAnEGyHhN/5R7iDW2TRw3h+o/jCFxus3P2LfWIIiwowAjANm7IA==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-dYqgNSZbDwkaJ2ceRd9ojCGjBq+mOm9LmtXnAnEGyHhN/5R7iDW2TRw3h+o/jCFxus3P2LfWIIiwowAjANm7IA==, + } + engines: { node: ">= 0.4" } rehype-raw@7.0.0: - resolution: {integrity: sha512-/aE8hCfKlQeA8LmyeyQvQF3eBiLRGNlfBJEvWH7ivp9sBqs7TNqBL5X3v157rM4IFETqDnIOO+z5M/biZbo9Ww==} + resolution: + { + integrity: sha512-/aE8hCfKlQeA8LmyeyQvQF3eBiLRGNlfBJEvWH7ivp9sBqs7TNqBL5X3v157rM4IFETqDnIOO+z5M/biZbo9Ww==, + } remark-parse@11.0.0: - resolution: {integrity: sha512-FCxlKLNGknS5ba/1lmpYijMUzX2esxW5xQqjWxw2eHFfS2MSdaHVINFmhjo+qN1WhZhNimq0dZATN9pH0IDrpA==} + resolution: + { + integrity: sha512-FCxlKLNGknS5ba/1lmpYijMUzX2esxW5xQqjWxw2eHFfS2MSdaHVINFmhjo+qN1WhZhNimq0dZATN9pH0IDrpA==, + } remark-rehype@11.1.2: - resolution: {integrity: sha512-Dh7l57ianaEoIpzbp0PC9UKAdCSVklD8E5Rpw7ETfbTl3FqcOOgq5q2LVDhgGCkaBv7p24JXikPdvhhmHvKMsw==} + resolution: + { + integrity: sha512-Dh7l57ianaEoIpzbp0PC9UKAdCSVklD8E5Rpw7ETfbTl3FqcOOgq5q2LVDhgGCkaBv7p24JXikPdvhhmHvKMsw==, + } reselect@5.1.1: - resolution: {integrity: sha512-K/BG6eIky/SBpzfHZv/dd+9JBFiS4SWV7FIujVyJRux6e45+73RaUHXLmIR1f7WOMaQ0U1km6qwklRQxpJJY0w==} + resolution: + { + integrity: sha512-K/BG6eIky/SBpzfHZv/dd+9JBFiS4SWV7FIujVyJRux6e45+73RaUHXLmIR1f7WOMaQ0U1km6qwklRQxpJJY0w==, + } resolve-from@4.0.0: - resolution: {integrity: sha512-pb/MYmXstAkysRFx8piNI1tGFNQIFA3vkE3Gq4EuA1dF6gHp/+vgZqsCGJapvy8N3Q+4o7FwvquPJcnZ7RYy4g==} - engines: {node: '>=4'} + resolution: + { + integrity: sha512-pb/MYmXstAkysRFx8piNI1tGFNQIFA3vkE3Gq4EuA1dF6gHp/+vgZqsCGJapvy8N3Q+4o7FwvquPJcnZ7RYy4g==, + } + engines: { node: ">=4" } resolve-pkg-maps@1.0.0: - resolution: {integrity: sha512-seS2Tj26TBVOC2NIc2rOe2y2ZO7efxITtLZcGSOnHHNOQ7CkiUBfw0Iw2ck6xkIhPwLhKNLS8BO+hEpngQlqzw==} + resolution: + { + integrity: sha512-seS2Tj26TBVOC2NIc2rOe2y2ZO7efxITtLZcGSOnHHNOQ7CkiUBfw0Iw2ck6xkIhPwLhKNLS8BO+hEpngQlqzw==, + } resolve@1.22.10: - resolution: {integrity: sha512-NPRy+/ncIMeDlTAsuqwKIiferiawhefFJtkNSW0qZJEqMEb+qBt/77B/jGeeek+F0uOeN05CDa6HXbbIgtVX4w==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-NPRy+/ncIMeDlTAsuqwKIiferiawhefFJtkNSW0qZJEqMEb+qBt/77B/jGeeek+F0uOeN05CDa6HXbbIgtVX4w==, + } + engines: { node: ">= 0.4" } hasBin: true resolve@2.0.0-next.5: - resolution: {integrity: sha512-U7WjGVG9sH8tvjW5SmGbQuui75FiyjAX72HX15DwBBwF9dNiQZRQAg9nnPhYy+TUnE0+VcrttuvNI8oSxZcocA==} + resolution: + { + integrity: sha512-U7WjGVG9sH8tvjW5SmGbQuui75FiyjAX72HX15DwBBwF9dNiQZRQAg9nnPhYy+TUnE0+VcrttuvNI8oSxZcocA==, + } hasBin: true reusify@1.1.0: - resolution: {integrity: sha512-g6QUff04oZpHs0eG5p83rFLhHeV00ug/Yf9nZM6fLeUrPguBTkTQOdpAWWspMh55TZfVQDPaN3NQJfbVRAxdIw==} - engines: {iojs: '>=1.0.0', node: '>=0.10.0'} + resolution: + { + integrity: sha512-g6QUff04oZpHs0eG5p83rFLhHeV00ug/Yf9nZM6fLeUrPguBTkTQOdpAWWspMh55TZfVQDPaN3NQJfbVRAxdIw==, + } + engines: { iojs: ">=1.0.0", node: ">=0.10.0" } robust-predicates@3.0.2: - resolution: {integrity: sha512-IXgzBWvWQwE6PrDI05OvmXUIruQTcoMDzRsOd5CDvHCVLcLHMTSYvOK5Cm46kWqlV3yAbuSpBZdJ5oP5OUoStg==} + resolution: + { + integrity: sha512-IXgzBWvWQwE6PrDI05OvmXUIruQTcoMDzRsOd5CDvHCVLcLHMTSYvOK5Cm46kWqlV3yAbuSpBZdJ5oP5OUoStg==, + } rollup@4.44.1: - resolution: {integrity: sha512-x8H8aPvD+xbl0Do8oez5f5o8eMS3trfCghc4HhLAnCkj7Vl0d1JWGs0UF/D886zLW2rOj2QymV/JcSSsw+XDNg==} - engines: {node: '>=18.0.0', npm: '>=8.0.0'} + resolution: + { + integrity: sha512-x8H8aPvD+xbl0Do8oez5f5o8eMS3trfCghc4HhLAnCkj7Vl0d1JWGs0UF/D886zLW2rOj2QymV/JcSSsw+XDNg==, + } + engines: { node: ">=18.0.0", npm: ">=8.0.0" } hasBin: true rrweb-cssom@0.8.0: - resolution: {integrity: sha512-guoltQEx+9aMf2gDZ0s62EcV8lsXR+0w8915TC3ITdn2YueuNjdAYh/levpU9nFaoChh9RUS5ZdQMrKfVEN9tw==} + resolution: + { + integrity: sha512-guoltQEx+9aMf2gDZ0s62EcV8lsXR+0w8915TC3ITdn2YueuNjdAYh/levpU9nFaoChh9RUS5ZdQMrKfVEN9tw==, + } run-parallel@1.2.0: - resolution: {integrity: sha512-5l4VyZR86LZ/lDxZTR6jqL8AFE2S0IFLMP26AbjsLVADxHdhB/c0GUsH+y39UfCi3dzz8OlQuPmnaJOMoDHQBA==} + resolution: + { + integrity: sha512-5l4VyZR86LZ/lDxZTR6jqL8AFE2S0IFLMP26AbjsLVADxHdhB/c0GUsH+y39UfCi3dzz8OlQuPmnaJOMoDHQBA==, + } rw@1.3.3: - resolution: {integrity: sha512-PdhdWy89SiZogBLaw42zdeqtRJ//zFd2PgQavcICDUgJT5oW10QCRKbJ6bg4r0/UY2M6BWd5tkxuGFRvCkgfHQ==} + resolution: + { + integrity: sha512-PdhdWy89SiZogBLaw42zdeqtRJ//zFd2PgQavcICDUgJT5oW10QCRKbJ6bg4r0/UY2M6BWd5tkxuGFRvCkgfHQ==, + } safe-array-concat@1.1.3: - resolution: {integrity: sha512-AURm5f0jYEOydBj7VQlVvDrjeFgthDdEF5H1dP+6mNpoXOMo1quQqJ4wvJDyRZ9+pO3kGWoOdmV08cSv2aJV6Q==} - engines: {node: '>=0.4'} + resolution: + { + integrity: sha512-AURm5f0jYEOydBj7VQlVvDrjeFgthDdEF5H1dP+6mNpoXOMo1quQqJ4wvJDyRZ9+pO3kGWoOdmV08cSv2aJV6Q==, + } + engines: { node: ">=0.4" } safe-push-apply@1.0.0: - resolution: {integrity: sha512-iKE9w/Z7xCzUMIZqdBsp6pEQvwuEebH4vdpjcDWnyzaI6yl6O9FHvVpmGelvEHNsoY6wGblkxR6Zty/h00WiSA==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-iKE9w/Z7xCzUMIZqdBsp6pEQvwuEebH4vdpjcDWnyzaI6yl6O9FHvVpmGelvEHNsoY6wGblkxR6Zty/h00WiSA==, + } + engines: { node: ">= 0.4" } safe-regex-test@1.1.0: - resolution: {integrity: sha512-x/+Cz4YrimQxQccJf5mKEbIa1NzeCRNI5Ecl/ekmlYaampdNLPalVyIcCZNNH3MvmqBugV5TMYZXv0ljslUlaw==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-x/+Cz4YrimQxQccJf5mKEbIa1NzeCRNI5Ecl/ekmlYaampdNLPalVyIcCZNNH3MvmqBugV5TMYZXv0ljslUlaw==, + } + engines: { node: ">= 0.4" } safer-buffer@2.1.2: - resolution: {integrity: sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==} + resolution: + { + integrity: sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==, + } saxes@6.0.0: - resolution: {integrity: sha512-xAg7SOnEhrm5zI3puOOKyy1OMcMlIJZYNJY7xLBwSze0UjhPLnWfj2GF2EpT0jmzaJKIWKHLsaSSajf35bcYnA==} - engines: {node: '>=v12.22.7'} + resolution: + { + integrity: sha512-xAg7SOnEhrm5zI3puOOKyy1OMcMlIJZYNJY7xLBwSze0UjhPLnWfj2GF2EpT0jmzaJKIWKHLsaSSajf35bcYnA==, + } + engines: { node: ">=v12.22.7" } scheduler@0.26.0: - resolution: {integrity: sha512-NlHwttCI/l5gCPR3D1nNXtWABUmBwvZpEQiD4IXSbIDq8BzLIK/7Ir5gTFSGZDUu37K5cMNp0hFtzO38sC7gWA==} + resolution: + { + integrity: sha512-NlHwttCI/l5gCPR3D1nNXtWABUmBwvZpEQiD4IXSbIDq8BzLIK/7Ir5gTFSGZDUu37K5cMNp0hFtzO38sC7gWA==, + } semver@6.3.1: - resolution: {integrity: sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA==} + resolution: + { + integrity: sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA==, + } hasBin: true semver@7.7.2: - resolution: {integrity: sha512-RF0Fw+rO5AMf9MAyaRXI4AV0Ulj5lMHqVxxdSgiVbixSCXoEmmX/jk0CuJw4+3SqroYO9VoUh+HcuJivvtJemA==} - engines: {node: '>=10'} + resolution: + { + integrity: sha512-RF0Fw+rO5AMf9MAyaRXI4AV0Ulj5lMHqVxxdSgiVbixSCXoEmmX/jk0CuJw4+3SqroYO9VoUh+HcuJivvtJemA==, + } + engines: { node: ">=10" } hasBin: true set-function-length@1.2.2: - resolution: {integrity: sha512-pgRc4hJ4/sNjWCSS9AmnS40x3bNMDTknHgL5UaMBTMyJnU90EgWh1Rz+MC9eFu4BuN/UwZjKQuY/1v3rM7HMfg==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-pgRc4hJ4/sNjWCSS9AmnS40x3bNMDTknHgL5UaMBTMyJnU90EgWh1Rz+MC9eFu4BuN/UwZjKQuY/1v3rM7HMfg==, + } + engines: { node: ">= 0.4" } set-function-name@2.0.2: - resolution: {integrity: sha512-7PGFlmtwsEADb0WYyvCMa1t+yke6daIG4Wirafur5kcf+MhUnPms1UeR0CKQdTZD81yESwMHbtn+TR+dMviakQ==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-7PGFlmtwsEADb0WYyvCMa1t+yke6daIG4Wirafur5kcf+MhUnPms1UeR0CKQdTZD81yESwMHbtn+TR+dMviakQ==, + } + engines: { node: ">= 0.4" } set-proto@1.0.0: - resolution: {integrity: sha512-RJRdvCo6IAnPdsvP/7m6bsQqNnn1FCBX5ZNtFL98MmFF/4xAIJTIg1YbHW5DC2W5SKZanrC6i4HsJqlajw/dZw==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-RJRdvCo6IAnPdsvP/7m6bsQqNnn1FCBX5ZNtFL98MmFF/4xAIJTIg1YbHW5DC2W5SKZanrC6i4HsJqlajw/dZw==, + } + engines: { node: ">= 0.4" } sharp@0.34.2: - resolution: {integrity: sha512-lszvBmB9QURERtyKT2bNmsgxXK0ShJrL/fvqlonCo7e6xBF8nT8xU6pW+PMIbLsz0RxQk3rgH9kd8UmvOzlMJg==} - engines: {node: ^18.17.0 || ^20.3.0 || >=21.0.0} + resolution: + { + integrity: sha512-lszvBmB9QURERtyKT2bNmsgxXK0ShJrL/fvqlonCo7e6xBF8nT8xU6pW+PMIbLsz0RxQk3rgH9kd8UmvOzlMJg==, + } + engines: { node: ^18.17.0 || ^20.3.0 || >=21.0.0 } shebang-command@2.0.0: - resolution: {integrity: sha512-kHxr2zZpYtdmrN1qDjrrX/Z1rR1kG8Dx+gkpK1G4eXmvXswmcE1hTWBWYUzlraYw1/yZp6YuDY77YtvbN0dmDA==} - engines: {node: '>=8'} + resolution: + { + integrity: sha512-kHxr2zZpYtdmrN1qDjrrX/Z1rR1kG8Dx+gkpK1G4eXmvXswmcE1hTWBWYUzlraYw1/yZp6YuDY77YtvbN0dmDA==, + } + engines: { node: ">=8" } shebang-regex@3.0.0: - resolution: {integrity: sha512-7++dFhtcx3353uBaq8DDR4NuxBetBzC7ZQOhmTQInHEd6bSrXdiEyzCvG07Z44UYdLShWUyXt5M/yhz8ekcb1A==} - engines: {node: '>=8'} + resolution: + { + integrity: sha512-7++dFhtcx3353uBaq8DDR4NuxBetBzC7ZQOhmTQInHEd6bSrXdiEyzCvG07Z44UYdLShWUyXt5M/yhz8ekcb1A==, + } + engines: { node: ">=8" } side-channel-list@1.0.0: - resolution: {integrity: sha512-FCLHtRD/gnpCiCHEiJLOwdmFP+wzCmDEkc9y7NsYxeF4u7Btsn1ZuwgwJGxImImHicJArLP4R0yX4c2KCrMrTA==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-FCLHtRD/gnpCiCHEiJLOwdmFP+wzCmDEkc9y7NsYxeF4u7Btsn1ZuwgwJGxImImHicJArLP4R0yX4c2KCrMrTA==, + } + engines: { node: ">= 0.4" } side-channel-map@1.0.1: - resolution: {integrity: sha512-VCjCNfgMsby3tTdo02nbjtM/ewra6jPHmpThenkTYh8pG9ucZ/1P8So4u4FGBek/BjpOVsDCMoLA/iuBKIFXRA==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-VCjCNfgMsby3tTdo02nbjtM/ewra6jPHmpThenkTYh8pG9ucZ/1P8So4u4FGBek/BjpOVsDCMoLA/iuBKIFXRA==, + } + engines: { node: ">= 0.4" } side-channel-weakmap@1.0.2: - resolution: {integrity: sha512-WPS/HvHQTYnHisLo9McqBHOJk2FkHO/tlpvldyrnem4aeQp4hai3gythswg6p01oSoTl58rcpiFAjF2br2Ak2A==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-WPS/HvHQTYnHisLo9McqBHOJk2FkHO/tlpvldyrnem4aeQp4hai3gythswg6p01oSoTl58rcpiFAjF2br2Ak2A==, + } + engines: { node: ">= 0.4" } side-channel@1.1.0: - resolution: {integrity: sha512-ZX99e6tRweoUXqR+VBrslhda51Nh5MTQwou5tnUDgbtyM0dBgmhEDtWGP/xbKn6hqfPRHujUNwz5fy/wbbhnpw==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-ZX99e6tRweoUXqR+VBrslhda51Nh5MTQwou5tnUDgbtyM0dBgmhEDtWGP/xbKn6hqfPRHujUNwz5fy/wbbhnpw==, + } + engines: { node: ">= 0.4" } siginfo@2.0.0: - resolution: {integrity: sha512-ybx0WO1/8bSBLEWXZvEd7gMW3Sn3JFlW3TvX1nREbDLRNQNaeNN8WK0meBwPdAaOI7TtRRRJn/Es1zhrrCHu7g==} + resolution: + { + integrity: sha512-ybx0WO1/8bSBLEWXZvEd7gMW3Sn3JFlW3TvX1nREbDLRNQNaeNN8WK0meBwPdAaOI7TtRRRJn/Es1zhrrCHu7g==, + } signal-exit@4.1.0: - resolution: {integrity: sha512-bzyZ1e88w9O1iNJbKnOlvYTrWPDl46O1bG0D3XInv+9tkPrxrN8jUUTiFlDkkmKWgn1M6CfIA13SuGqOa9Korw==} - engines: {node: '>=14'} + resolution: + { + integrity: sha512-bzyZ1e88w9O1iNJbKnOlvYTrWPDl46O1bG0D3XInv+9tkPrxrN8jUUTiFlDkkmKWgn1M6CfIA13SuGqOa9Korw==, + } + engines: { node: ">=14" } simple-swizzle@0.2.2: - resolution: {integrity: sha512-JA//kQgZtbuY83m+xT+tXJkmJncGMTFT+C+g2h2R9uxkYIrE2yy9sgmcLhCnw57/WSD+Eh3J97FPEDFnbXnDUg==} + resolution: + { + integrity: sha512-JA//kQgZtbuY83m+xT+tXJkmJncGMTFT+C+g2h2R9uxkYIrE2yy9sgmcLhCnw57/WSD+Eh3J97FPEDFnbXnDUg==, + } slash@5.1.0: - resolution: {integrity: sha512-ZA6oR3T/pEyuqwMgAKT0/hAv8oAXckzbkmR0UkUosQ+Mc4RxGoJkRmwHgHufaenlyAgE1Mxgpdcrf75y6XcnDg==} - engines: {node: '>=14.16'} + resolution: + { + integrity: sha512-ZA6oR3T/pEyuqwMgAKT0/hAv8oAXckzbkmR0UkUosQ+Mc4RxGoJkRmwHgHufaenlyAgE1Mxgpdcrf75y6XcnDg==, + } + engines: { node: ">=14.16" } source-map-js@1.2.1: - resolution: {integrity: sha512-UXWMKhLOwVKb728IUtQPXxfYU+usdybtUrK/8uGE8CQMvrhOpwvzDBwj0QhSL7MQc7vIsISBG8VQ8+IDQxpfQA==} - engines: {node: '>=0.10.0'} + resolution: + { + integrity: sha512-UXWMKhLOwVKb728IUtQPXxfYU+usdybtUrK/8uGE8CQMvrhOpwvzDBwj0QhSL7MQc7vIsISBG8VQ8+IDQxpfQA==, + } + engines: { node: ">=0.10.0" } space-separated-tokens@2.0.2: - resolution: {integrity: sha512-PEGlAwrG8yXGXRjW32fGbg66JAlOAwbObuqVoJpv/mRgoWDQfgH1wDPvtzWyUSNAXBGSk8h755YDbbcEy3SH2Q==} + resolution: + { + integrity: sha512-PEGlAwrG8yXGXRjW32fGbg66JAlOAwbObuqVoJpv/mRgoWDQfgH1wDPvtzWyUSNAXBGSk8h755YDbbcEy3SH2Q==, + } split2@4.2.0: - resolution: {integrity: sha512-UcjcJOWknrNkF6PLX83qcHM6KHgVKNkV62Y8a5uYDVv9ydGQVwAHMKqHdJje1VTWpljG0WYpCDhrCdAOYH4TWg==} - engines: {node: '>= 10.x'} + resolution: + { + integrity: sha512-UcjcJOWknrNkF6PLX83qcHM6KHgVKNkV62Y8a5uYDVv9ydGQVwAHMKqHdJje1VTWpljG0WYpCDhrCdAOYH4TWg==, + } + engines: { node: ">= 10.x" } stable-hash@0.0.5: - resolution: {integrity: sha512-+L3ccpzibovGXFK+Ap/f8LOS0ahMrHTf3xu7mMLSpEGU0EO9ucaysSylKo9eRDFNhWve/y275iPmIZ4z39a9iA==} + resolution: + { + integrity: sha512-+L3ccpzibovGXFK+Ap/f8LOS0ahMrHTf3xu7mMLSpEGU0EO9ucaysSylKo9eRDFNhWve/y275iPmIZ4z39a9iA==, + } stackback@0.0.2: - resolution: {integrity: sha512-1XMJE5fQo1jGH6Y/7ebnwPOBEkIEnT4QF32d5R1+VXdXveM0IBMJt8zfaxX1P3QhVwrYe+576+jkANtSS2mBbw==} + resolution: + { + integrity: sha512-1XMJE5fQo1jGH6Y/7ebnwPOBEkIEnT4QF32d5R1+VXdXveM0IBMJt8zfaxX1P3QhVwrYe+576+jkANtSS2mBbw==, + } std-env@3.9.0: - resolution: {integrity: sha512-UGvjygr6F6tpH7o2qyqR6QYpwraIjKSdtzyBdyytFOHmPZY917kwdwLG0RbOjWOnKmnm3PeHjaoLLMie7kPLQw==} + resolution: + { + integrity: sha512-UGvjygr6F6tpH7o2qyqR6QYpwraIjKSdtzyBdyytFOHmPZY917kwdwLG0RbOjWOnKmnm3PeHjaoLLMie7kPLQw==, + } stop-iteration-iterator@1.1.0: - resolution: {integrity: sha512-eLoXW/DHyl62zxY4SCaIgnRhuMr6ri4juEYARS8E6sCEqzKpOiE521Ucofdx+KnDZl5xmvGYaaKCk5FEOxJCoQ==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-eLoXW/DHyl62zxY4SCaIgnRhuMr6ri4juEYARS8E6sCEqzKpOiE521Ucofdx+KnDZl5xmvGYaaKCk5FEOxJCoQ==, + } + engines: { node: ">= 0.4" } streamsearch@1.1.0: - resolution: {integrity: sha512-Mcc5wHehp9aXz1ax6bZUyY5afg9u2rv5cqQI3mRrYkGC8rW2hM02jWuwjtL++LS5qinSyhj2QfLyNsuc+VsExg==} - engines: {node: '>=10.0.0'} + resolution: + { + integrity: sha512-Mcc5wHehp9aXz1ax6bZUyY5afg9u2rv5cqQI3mRrYkGC8rW2hM02jWuwjtL++LS5qinSyhj2QfLyNsuc+VsExg==, + } + engines: { node: ">=10.0.0" } string-width@4.2.3: - resolution: {integrity: sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g==} - engines: {node: '>=8'} + resolution: + { + integrity: sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g==, + } + engines: { node: ">=8" } string-width@5.1.2: - resolution: {integrity: sha512-HnLOCR3vjcY8beoNLtcjZ5/nxn2afmME6lhrDrebokqMap+XbeW8n9TXpPDOqdGK5qcI3oT0GKTW6wC7EMiVqA==} - engines: {node: '>=12'} + resolution: + { + integrity: sha512-HnLOCR3vjcY8beoNLtcjZ5/nxn2afmME6lhrDrebokqMap+XbeW8n9TXpPDOqdGK5qcI3oT0GKTW6wC7EMiVqA==, + } + engines: { node: ">=12" } string.prototype.includes@2.0.1: - resolution: {integrity: sha512-o7+c9bW6zpAdJHTtujeePODAhkuicdAryFsfVKwA+wGw89wJ4GTY484WTucM9hLtDEOpOvI+aHnzqnC5lHp4Rg==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-o7+c9bW6zpAdJHTtujeePODAhkuicdAryFsfVKwA+wGw89wJ4GTY484WTucM9hLtDEOpOvI+aHnzqnC5lHp4Rg==, + } + engines: { node: ">= 0.4" } string.prototype.matchall@4.0.12: - resolution: {integrity: sha512-6CC9uyBL+/48dYizRf7H7VAYCMCNTBeM78x/VTUe9bFEaxBepPJDa1Ow99LqI/1yF7kuy7Q3cQsYMrcjGUcskA==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-6CC9uyBL+/48dYizRf7H7VAYCMCNTBeM78x/VTUe9bFEaxBepPJDa1Ow99LqI/1yF7kuy7Q3cQsYMrcjGUcskA==, + } + engines: { node: ">= 0.4" } string.prototype.repeat@1.0.0: - resolution: {integrity: sha512-0u/TldDbKD8bFCQ/4f5+mNRrXwZ8hg2w7ZR8wa16e8z9XpePWl3eGEcUD0OXpEH/VJH/2G3gjUtR3ZOiBe2S/w==} + resolution: + { + integrity: sha512-0u/TldDbKD8bFCQ/4f5+mNRrXwZ8hg2w7ZR8wa16e8z9XpePWl3eGEcUD0OXpEH/VJH/2G3gjUtR3ZOiBe2S/w==, + } string.prototype.trim@1.2.10: - resolution: {integrity: sha512-Rs66F0P/1kedk5lyYyH9uBzuiI/kNRmwJAR9quK6VOtIpZ2G+hMZd+HQbbv25MgCA6gEffoMZYxlTod4WcdrKA==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-Rs66F0P/1kedk5lyYyH9uBzuiI/kNRmwJAR9quK6VOtIpZ2G+hMZd+HQbbv25MgCA6gEffoMZYxlTod4WcdrKA==, + } + engines: { node: ">= 0.4" } string.prototype.trimend@1.0.9: - resolution: {integrity: sha512-G7Ok5C6E/j4SGfyLCloXTrngQIQU3PWtXGst3yM7Bea9FRURf1S42ZHlZZtsNque2FN2PoUhfZXYLNWwEr4dLQ==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-G7Ok5C6E/j4SGfyLCloXTrngQIQU3PWtXGst3yM7Bea9FRURf1S42ZHlZZtsNque2FN2PoUhfZXYLNWwEr4dLQ==, + } + engines: { node: ">= 0.4" } string.prototype.trimstart@1.0.8: - resolution: {integrity: sha512-UXSH262CSZY1tfu3G3Secr6uGLCFVPMhIqHjlgCUtCCcgihYc/xKs9djMTMUOb2j1mVSeU8EU6NWc/iQKU6Gfg==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-UXSH262CSZY1tfu3G3Secr6uGLCFVPMhIqHjlgCUtCCcgihYc/xKs9djMTMUOb2j1mVSeU8EU6NWc/iQKU6Gfg==, + } + engines: { node: ">= 0.4" } stringify-entities@4.0.4: - resolution: {integrity: sha512-IwfBptatlO+QCJUo19AqvrPNqlVMpW9YEL2LIVY+Rpv2qsjCGxaDLNRgeGsQWJhfItebuJhsGSLjaBbNSQ+ieg==} + resolution: + { + integrity: sha512-IwfBptatlO+QCJUo19AqvrPNqlVMpW9YEL2LIVY+Rpv2qsjCGxaDLNRgeGsQWJhfItebuJhsGSLjaBbNSQ+ieg==, + } strip-ansi@6.0.1: - resolution: {integrity: sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A==} - engines: {node: '>=8'} + resolution: + { + integrity: sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A==, + } + engines: { node: ">=8" } strip-ansi@7.1.0: - resolution: {integrity: sha512-iq6eVVI64nQQTRYq2KtEg2d2uU7LElhTJwsH4YzIHZshxlgZms/wIc4VoDQTlG/IvVIrBKG06CrZnp0qv7hkcQ==} - engines: {node: '>=12'} + resolution: + { + integrity: sha512-iq6eVVI64nQQTRYq2KtEg2d2uU7LElhTJwsH4YzIHZshxlgZms/wIc4VoDQTlG/IvVIrBKG06CrZnp0qv7hkcQ==, + } + engines: { node: ">=12" } strip-bom@3.0.0: - resolution: {integrity: sha512-vavAMRXOgBVNF6nyEEmL3DBK19iRpDcoIwW+swQ+CbGiu7lju6t+JklA1MHweoWtadgt4ISVUsXLyDq34ddcwA==} - engines: {node: '>=4'} + resolution: + { + integrity: sha512-vavAMRXOgBVNF6nyEEmL3DBK19iRpDcoIwW+swQ+CbGiu7lju6t+JklA1MHweoWtadgt4ISVUsXLyDq34ddcwA==, + } + engines: { node: ">=4" } strip-json-comments@3.1.1: - resolution: {integrity: sha512-6fPc+R4ihwqP6N/aIv2f1gMH8lOVtWQHoqC4yK6oSDVVocumAsfCqjkXnqiYMhmMwS/mEHLp7Vehlt3ql6lEig==} - engines: {node: '>=8'} + resolution: + { + integrity: sha512-6fPc+R4ihwqP6N/aIv2f1gMH8lOVtWQHoqC4yK6oSDVVocumAsfCqjkXnqiYMhmMwS/mEHLp7Vehlt3ql6lEig==, + } + engines: { node: ">=8" } strip-literal@3.0.0: - resolution: {integrity: sha512-TcccoMhJOM3OebGhSBEmp3UZ2SfDMZUEBdRA/9ynfLi8yYajyWX3JiXArcJt4Umh4vISpspkQIY8ZZoCqjbviA==} + resolution: + { + integrity: sha512-TcccoMhJOM3OebGhSBEmp3UZ2SfDMZUEBdRA/9ynfLi8yYajyWX3JiXArcJt4Umh4vISpspkQIY8ZZoCqjbviA==, + } style-to-js@1.1.17: - resolution: {integrity: sha512-xQcBGDxJb6jjFCTzvQtfiPn6YvvP2O8U1MDIPNfJQlWMYfktPy+iGsHE7cssjs7y84d9fQaK4UF3RIJaAHSoYA==} + resolution: + { + integrity: sha512-xQcBGDxJb6jjFCTzvQtfiPn6YvvP2O8U1MDIPNfJQlWMYfktPy+iGsHE7cssjs7y84d9fQaK4UF3RIJaAHSoYA==, + } style-to-object@1.0.9: - resolution: {integrity: sha512-G4qppLgKu/k6FwRpHiGiKPaPTFcG3g4wNVX/Qsfu+RqQM30E7Tyu/TEgxcL9PNLF5pdRLwQdE3YKKf+KF2Dzlw==} + resolution: + { + integrity: sha512-G4qppLgKu/k6FwRpHiGiKPaPTFcG3g4wNVX/Qsfu+RqQM30E7Tyu/TEgxcL9PNLF5pdRLwQdE3YKKf+KF2Dzlw==, + } styled-jsx@5.1.6: - resolution: {integrity: sha512-qSVyDTeMotdvQYoHWLNGwRFJHC+i+ZvdBRYosOFgC+Wg1vx4frN2/RG/NA7SYqqvKNLf39P2LSRA2pu6n0XYZA==} - engines: {node: '>= 12.0.0'} + resolution: + { + integrity: sha512-qSVyDTeMotdvQYoHWLNGwRFJHC+i+ZvdBRYosOFgC+Wg1vx4frN2/RG/NA7SYqqvKNLf39P2LSRA2pu6n0XYZA==, + } + engines: { node: ">= 12.0.0" } peerDependencies: - '@babel/core': '*' - babel-plugin-macros: '*' - react: '>= 16.8.0 || 17.x.x || ^18.0.0-0 || ^19.0.0-0' + "@babel/core": "*" + babel-plugin-macros: "*" + react: ">= 16.8.0 || 17.x.x || ^18.0.0-0 || ^19.0.0-0" peerDependenciesMeta: - '@babel/core': + "@babel/core": optional: true babel-plugin-macros: optional: true supports-color@7.2.0: - resolution: {integrity: sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==} - engines: {node: '>=8'} + resolution: + { + integrity: sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==, + } + engines: { node: ">=8" } supports-preserve-symlinks-flag@1.0.0: - resolution: {integrity: sha512-ot0WnXS9fgdkgIcePe6RHNk1WA8+muPa6cSjeR3V8K27q9BB1rTE3R1p7Hv0z1ZyAc8s6Vvv8DIyWf681MAt0w==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-ot0WnXS9fgdkgIcePe6RHNk1WA8+muPa6cSjeR3V8K27q9BB1rTE3R1p7Hv0z1ZyAc8s6Vvv8DIyWf681MAt0w==, + } + engines: { node: ">= 0.4" } symbol-tree@3.2.4: - resolution: {integrity: sha512-9QNk5KwDF+Bvz+PyObkmSYjI5ksVUYtjW7AU22r2NKcfLJcXp96hkDWU3+XndOsUb+AQ9QhfzfCT2O+CNWT5Tw==} + resolution: + { + integrity: sha512-9QNk5KwDF+Bvz+PyObkmSYjI5ksVUYtjW7AU22r2NKcfLJcXp96hkDWU3+XndOsUb+AQ9QhfzfCT2O+CNWT5Tw==, + } synckit@0.11.8: - resolution: {integrity: sha512-+XZ+r1XGIJGeQk3VvXhT6xx/VpbHsRzsTkGgF6E5RX9TTXD0118l87puaEBZ566FhqblC6U0d4XnubznJDm30A==} - engines: {node: ^14.18.0 || >=16.0.0} + resolution: + { + integrity: sha512-+XZ+r1XGIJGeQk3VvXhT6xx/VpbHsRzsTkGgF6E5RX9TTXD0118l87puaEBZ566FhqblC6U0d4XnubznJDm30A==, + } + engines: { node: ^14.18.0 || >=16.0.0 } tailwind-merge@3.3.1: - resolution: {integrity: sha512-gBXpgUm/3rp1lMZZrM/w7D8GKqshif0zAymAhbCyIt8KMe+0v9DQ7cdYLR4FHH/cKpdTXb+A/tKKU3eolfsI+g==} + resolution: + { + integrity: sha512-gBXpgUm/3rp1lMZZrM/w7D8GKqshif0zAymAhbCyIt8KMe+0v9DQ7cdYLR4FHH/cKpdTXb+A/tKKU3eolfsI+g==, + } tailwindcss@4.1.11: - resolution: {integrity: sha512-2E9TBm6MDD/xKYe+dvJZAmg3yxIEDNRc0jwlNyDg/4Fil2QcSLjFKGVff0lAf1jjeaArlG/M75Ey/EYr/OJtBA==} + resolution: + { + integrity: sha512-2E9TBm6MDD/xKYe+dvJZAmg3yxIEDNRc0jwlNyDg/4Fil2QcSLjFKGVff0lAf1jjeaArlG/M75Ey/EYr/OJtBA==, + } tapable@2.2.2: - resolution: {integrity: sha512-Re10+NauLTMCudc7T5WLFLAwDhQ0JWdrMK+9B2M8zR5hRExKmsRDCBA7/aV/pNJFltmBFO5BAMlQFi/vq3nKOg==} - engines: {node: '>=6'} + resolution: + { + integrity: sha512-Re10+NauLTMCudc7T5WLFLAwDhQ0JWdrMK+9B2M8zR5hRExKmsRDCBA7/aV/pNJFltmBFO5BAMlQFi/vq3nKOg==, + } + engines: { node: ">=6" } tar@7.4.3: - resolution: {integrity: sha512-5S7Va8hKfV7W5U6g3aYxXmlPoZVAwUMy9AOKyF2fVuZa2UD3qZjg578OrLRt8PcNN1PleVaL/5/yYATNL0ICUw==} - engines: {node: '>=18'} + resolution: + { + integrity: sha512-5S7Va8hKfV7W5U6g3aYxXmlPoZVAwUMy9AOKyF2fVuZa2UD3qZjg578OrLRt8PcNN1PleVaL/5/yYATNL0ICUw==, + } + engines: { node: ">=18" } test-exclude@7.0.1: - resolution: {integrity: sha512-pFYqmTw68LXVjeWJMST4+borgQP2AyMNbg1BpZh9LbyhUeNkeaPF9gzfPGUAnSMV3qPYdWUwDIjjCLiSDOl7vg==} - engines: {node: '>=18'} + resolution: + { + integrity: sha512-pFYqmTw68LXVjeWJMST4+borgQP2AyMNbg1BpZh9LbyhUeNkeaPF9gzfPGUAnSMV3qPYdWUwDIjjCLiSDOl7vg==, + } + engines: { node: ">=18" } tiny-invariant@1.3.3: - resolution: {integrity: sha512-+FbBPE1o9QAYvviau/qC5SE3caw21q3xkvWKBtja5vgqOWIHHJ3ioaq1VPfn/Szqctz2bU/oYeKd9/z5BL+PVg==} + resolution: + { + integrity: sha512-+FbBPE1o9QAYvviau/qC5SE3caw21q3xkvWKBtja5vgqOWIHHJ3ioaq1VPfn/Szqctz2bU/oYeKd9/z5BL+PVg==, + } tinybench@2.9.0: - resolution: {integrity: sha512-0+DUvqWMValLmha6lr4kD8iAMK1HzV0/aKnCtWb9v9641TnP/MFb7Pc2bxoxQjTXAErryXVgUOfv2YqNllqGeg==} + resolution: + { + integrity: sha512-0+DUvqWMValLmha6lr4kD8iAMK1HzV0/aKnCtWb9v9641TnP/MFb7Pc2bxoxQjTXAErryXVgUOfv2YqNllqGeg==, + } tinyexec@0.3.2: - resolution: {integrity: sha512-KQQR9yN7R5+OSwaK0XQoj22pwHoTlgYqmUscPYoknOoWCWfj/5/ABTMRi69FrKU5ffPVh5QcFikpWJI/P1ocHA==} + resolution: + { + integrity: sha512-KQQR9yN7R5+OSwaK0XQoj22pwHoTlgYqmUscPYoknOoWCWfj/5/ABTMRi69FrKU5ffPVh5QcFikpWJI/P1ocHA==, + } tinyglobby@0.2.14: - resolution: {integrity: sha512-tX5e7OM1HnYr2+a2C/4V0htOcSQcoSTH9KgJnVvNm5zm/cyEWKJ7j7YutsH9CxMdtOkkLFy2AHrMci9IM8IPZQ==} - engines: {node: '>=12.0.0'} + resolution: + { + integrity: sha512-tX5e7OM1HnYr2+a2C/4V0htOcSQcoSTH9KgJnVvNm5zm/cyEWKJ7j7YutsH9CxMdtOkkLFy2AHrMci9IM8IPZQ==, + } + engines: { node: ">=12.0.0" } tinypool@1.1.1: - resolution: {integrity: sha512-Zba82s87IFq9A9XmjiX5uZA/ARWDrB03OHlq+Vw1fSdt0I+4/Kutwy8BP4Y/y/aORMo61FQ0vIb5j44vSo5Pkg==} - engines: {node: ^18.0.0 || >=20.0.0} + resolution: + { + integrity: sha512-Zba82s87IFq9A9XmjiX5uZA/ARWDrB03OHlq+Vw1fSdt0I+4/Kutwy8BP4Y/y/aORMo61FQ0vIb5j44vSo5Pkg==, + } + engines: { node: ^18.0.0 || >=20.0.0 } tinyrainbow@2.0.0: - resolution: {integrity: sha512-op4nsTR47R6p0vMUUoYl/a+ljLFVtlfaXkLQmqfLR1qHma1h/ysYk4hEXZ880bf2CYgTskvTa/e196Vd5dDQXw==} - engines: {node: '>=14.0.0'} + resolution: + { + integrity: sha512-op4nsTR47R6p0vMUUoYl/a+ljLFVtlfaXkLQmqfLR1qHma1h/ysYk4hEXZ880bf2CYgTskvTa/e196Vd5dDQXw==, + } + engines: { node: ">=14.0.0" } tinyspy@4.0.3: - resolution: {integrity: sha512-t2T/WLB2WRgZ9EpE4jgPJ9w+i66UZfDc8wHh0xrwiRNN+UwH98GIJkTeZqX9rg0i0ptwzqW+uYeIF0T4F8LR7A==} - engines: {node: '>=14.0.0'} + resolution: + { + integrity: sha512-t2T/WLB2WRgZ9EpE4jgPJ9w+i66UZfDc8wHh0xrwiRNN+UwH98GIJkTeZqX9rg0i0ptwzqW+uYeIF0T4F8LR7A==, + } + engines: { node: ">=14.0.0" } tldts-core@6.1.86: - resolution: {integrity: sha512-Je6p7pkk+KMzMv2XXKmAE3McmolOQFdxkKw0R8EYNr7sELW46JqnNeTX8ybPiQgvg1ymCoF8LXs5fzFaZvJPTA==} + resolution: + { + integrity: sha512-Je6p7pkk+KMzMv2XXKmAE3McmolOQFdxkKw0R8EYNr7sELW46JqnNeTX8ybPiQgvg1ymCoF8LXs5fzFaZvJPTA==, + } tldts@6.1.86: - resolution: {integrity: sha512-WMi/OQ2axVTf/ykqCQgXiIct+mSQDFdH2fkwhPwgEwvJ1kSzZRiinb0zF2Xb8u4+OqPChmyI6MEu4EezNJz+FQ==} + resolution: + { + integrity: sha512-WMi/OQ2axVTf/ykqCQgXiIct+mSQDFdH2fkwhPwgEwvJ1kSzZRiinb0zF2Xb8u4+OqPChmyI6MEu4EezNJz+FQ==, + } hasBin: true to-regex-range@5.0.1: - resolution: {integrity: sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ==} - engines: {node: '>=8.0'} + resolution: + { + integrity: sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ==, + } + engines: { node: ">=8.0" } tough-cookie@5.1.2: - resolution: {integrity: sha512-FVDYdxtnj0G6Qm/DhNPSb8Ju59ULcup3tuJxkFb5K8Bv2pUXILbf0xZWU8PX8Ov19OXljbUyveOFwRMwkXzO+A==} - engines: {node: '>=16'} + resolution: + { + integrity: sha512-FVDYdxtnj0G6Qm/DhNPSb8Ju59ULcup3tuJxkFb5K8Bv2pUXILbf0xZWU8PX8Ov19OXljbUyveOFwRMwkXzO+A==, + } + engines: { node: ">=16" } tr46@5.1.1: - resolution: {integrity: sha512-hdF5ZgjTqgAntKkklYw0R03MG2x/bSzTtkxmIRw/sTNV8YXsCJ1tfLAX23lhxhHJlEf3CRCOCGGWw3vI3GaSPw==} - engines: {node: '>=18'} + resolution: + { + integrity: sha512-hdF5ZgjTqgAntKkklYw0R03MG2x/bSzTtkxmIRw/sTNV8YXsCJ1tfLAX23lhxhHJlEf3CRCOCGGWw3vI3GaSPw==, + } + engines: { node: ">=18" } trim-lines@3.0.1: - resolution: {integrity: sha512-kRj8B+YHZCc9kQYdWfJB2/oUl9rA99qbowYYBtr4ui4mZyAQ2JpvVBd/6U2YloATfqBhBTSMhTpgBHtU0Mf3Rg==} + resolution: + { + integrity: sha512-kRj8B+YHZCc9kQYdWfJB2/oUl9rA99qbowYYBtr4ui4mZyAQ2JpvVBd/6U2YloATfqBhBTSMhTpgBHtU0Mf3Rg==, + } trough@2.2.0: - resolution: {integrity: sha512-tmMpK00BjZiUyVyvrBK7knerNgmgvcV/KLVyuma/SC+TQN167GrMRciANTz09+k3zW8L8t60jWO1GpfkZdjTaw==} + resolution: + { + integrity: sha512-tmMpK00BjZiUyVyvrBK7knerNgmgvcV/KLVyuma/SC+TQN167GrMRciANTz09+k3zW8L8t60jWO1GpfkZdjTaw==, + } ts-api-utils@2.1.0: - resolution: {integrity: sha512-CUgTZL1irw8u29bzrOD/nH85jqyc74D6SshFgujOIA7osm2Rz7dYH77agkx7H4FBNxDq7Cjf+IjaX/8zwFW+ZQ==} - engines: {node: '>=18.12'} + resolution: + { + integrity: sha512-CUgTZL1irw8u29bzrOD/nH85jqyc74D6SshFgujOIA7osm2Rz7dYH77agkx7H4FBNxDq7Cjf+IjaX/8zwFW+ZQ==, + } + engines: { node: ">=18.12" } peerDependencies: - typescript: '>=4.8.4' + typescript: ">=4.8.4" ts-node@10.9.2: - resolution: {integrity: sha512-f0FFpIdcHgn8zcPSbf1dRevwt047YMnaiJM3u2w2RewrB+fob/zePZcrOyQoLMMO7aBIddLcQIEK5dYjkLnGrQ==} + resolution: + { + integrity: sha512-f0FFpIdcHgn8zcPSbf1dRevwt047YMnaiJM3u2w2RewrB+fob/zePZcrOyQoLMMO7aBIddLcQIEK5dYjkLnGrQ==, + } hasBin: true peerDependencies: - '@swc/core': '>=1.2.50' - '@swc/wasm': '>=1.2.50' - '@types/node': '*' - typescript: '>=2.7' + "@swc/core": ">=1.2.50" + "@swc/wasm": ">=1.2.50" + "@types/node": "*" + typescript: ">=2.7" peerDependenciesMeta: - '@swc/core': + "@swc/core": optional: true - '@swc/wasm': + "@swc/wasm": optional: true tsconfck@3.1.6: - resolution: {integrity: sha512-ks6Vjr/jEw0P1gmOVwutM3B7fWxoWBL2KRDb1JfqGVawBmO5UsvmWOQFGHBPl5yxYz4eERr19E6L7NMv+Fej4w==} - engines: {node: ^18 || >=20} + resolution: + { + integrity: sha512-ks6Vjr/jEw0P1gmOVwutM3B7fWxoWBL2KRDb1JfqGVawBmO5UsvmWOQFGHBPl5yxYz4eERr19E6L7NMv+Fej4w==, + } + engines: { node: ^18 || >=20 } hasBin: true peerDependencies: typescript: ^5.0.0 @@ -4093,163 +6721,268 @@ packages: optional: true tsconfig-paths@3.15.0: - resolution: {integrity: sha512-2Ac2RgzDe/cn48GvOe3M+o82pEFewD3UPbyoUHHdKasHwJKjds4fLXWf/Ux5kATBKN20oaFGu+jbElp1pos0mg==} + resolution: + { + integrity: sha512-2Ac2RgzDe/cn48GvOe3M+o82pEFewD3UPbyoUHHdKasHwJKjds4fLXWf/Ux5kATBKN20oaFGu+jbElp1pos0mg==, + } tslib@2.8.1: - resolution: {integrity: sha512-oJFu94HQb+KVduSUQL7wnpmqnfmLsOA/nAh6b6EH0wCEoK0/mPeXU6c3wKDV83MkOuHPRHtSXKKU99IBazS/2w==} + resolution: + { + integrity: sha512-oJFu94HQb+KVduSUQL7wnpmqnfmLsOA/nAh6b6EH0wCEoK0/mPeXU6c3wKDV83MkOuHPRHtSXKKU99IBazS/2w==, + } tsx@4.20.3: - resolution: {integrity: sha512-qjbnuR9Tr+FJOMBqJCW5ehvIo/buZq7vH7qD7JziU98h6l3qGy0a/yPFjwO+y0/T7GFpNgNAvEcPPVfyT8rrPQ==} - engines: {node: '>=18.0.0'} + resolution: + { + integrity: sha512-qjbnuR9Tr+FJOMBqJCW5ehvIo/buZq7vH7qD7JziU98h6l3qGy0a/yPFjwO+y0/T7GFpNgNAvEcPPVfyT8rrPQ==, + } + engines: { node: ">=18.0.0" } hasBin: true tw-animate-css@1.3.4: - resolution: {integrity: sha512-dd1Ht6/YQHcNbq0znIT6dG8uhO7Ce+VIIhZUhjsryXsMPJQz3bZg7Q2eNzLwipb25bRZslGb2myio5mScd1TFg==} + resolution: + { + integrity: sha512-dd1Ht6/YQHcNbq0znIT6dG8uhO7Ce+VIIhZUhjsryXsMPJQz3bZg7Q2eNzLwipb25bRZslGb2myio5mScd1TFg==, + } type-check@0.4.0: - resolution: {integrity: sha512-XleUoc9uwGXqjWwXaUTZAmzMcFZ5858QA2vvx1Ur5xIcixXIP+8LnFDgRplU30us6teqdlskFfu+ae4K79Ooew==} - engines: {node: '>= 0.8.0'} + resolution: + { + integrity: sha512-XleUoc9uwGXqjWwXaUTZAmzMcFZ5858QA2vvx1Ur5xIcixXIP+8LnFDgRplU30us6teqdlskFfu+ae4K79Ooew==, + } + engines: { node: ">= 0.8.0" } typed-array-buffer@1.0.3: - resolution: {integrity: sha512-nAYYwfY3qnzX30IkA6AQZjVbtK6duGontcQm1WSG1MD94YLqK0515GNApXkoxKOWMusVssAHWLh9SeaoefYFGw==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-nAYYwfY3qnzX30IkA6AQZjVbtK6duGontcQm1WSG1MD94YLqK0515GNApXkoxKOWMusVssAHWLh9SeaoefYFGw==, + } + engines: { node: ">= 0.4" } typed-array-byte-length@1.0.3: - resolution: {integrity: sha512-BaXgOuIxz8n8pIq3e7Atg/7s+DpiYrxn4vdot3w9KbnBhcRQq6o3xemQdIfynqSeXeDrF32x+WvfzmOjPiY9lg==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-BaXgOuIxz8n8pIq3e7Atg/7s+DpiYrxn4vdot3w9KbnBhcRQq6o3xemQdIfynqSeXeDrF32x+WvfzmOjPiY9lg==, + } + engines: { node: ">= 0.4" } typed-array-byte-offset@1.0.4: - resolution: {integrity: sha512-bTlAFB/FBYMcuX81gbL4OcpH5PmlFHqlCCpAl8AlEzMz5k53oNDvN8p1PNOWLEmI2x4orp3raOFB51tv9X+MFQ==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-bTlAFB/FBYMcuX81gbL4OcpH5PmlFHqlCCpAl8AlEzMz5k53oNDvN8p1PNOWLEmI2x4orp3raOFB51tv9X+MFQ==, + } + engines: { node: ">= 0.4" } typed-array-length@1.0.7: - resolution: {integrity: sha512-3KS2b+kL7fsuk/eJZ7EQdnEmQoaho/r6KUef7hxvltNA5DR8NAUM+8wJMbJyZ4G9/7i3v5zPBIMN5aybAh2/Jg==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-3KS2b+kL7fsuk/eJZ7EQdnEmQoaho/r6KUef7hxvltNA5DR8NAUM+8wJMbJyZ4G9/7i3v5zPBIMN5aybAh2/Jg==, + } + engines: { node: ">= 0.4" } typescript@5.8.3: - resolution: {integrity: sha512-p1diW6TqL9L07nNxvRMM7hMMw4c5XOo/1ibL4aAIGmSAt9slTE1Xgw5KWuof2uTOvCg9BY7ZRi+GaF+7sfgPeQ==} - engines: {node: '>=14.17'} + resolution: + { + integrity: sha512-p1diW6TqL9L07nNxvRMM7hMMw4c5XOo/1ibL4aAIGmSAt9slTE1Xgw5KWuof2uTOvCg9BY7ZRi+GaF+7sfgPeQ==, + } + engines: { node: ">=14.17" } hasBin: true uc.micro@2.1.0: - resolution: {integrity: sha512-ARDJmphmdvUk6Glw7y9DQ2bFkKBHwQHLi2lsaH6PPmz/Ka9sFOBsBluozhDltWmnv9u/cF6Rt87znRTPV+yp/A==} + resolution: + { + integrity: sha512-ARDJmphmdvUk6Glw7y9DQ2bFkKBHwQHLi2lsaH6PPmz/Ka9sFOBsBluozhDltWmnv9u/cF6Rt87znRTPV+yp/A==, + } unbox-primitive@1.1.0: - resolution: {integrity: sha512-nWJ91DjeOkej/TA8pXQ3myruKpKEYgqvpw9lz4OPHj/NWFNluYrjbz9j01CJ8yKQd2g4jFoOkINCTW2I5LEEyw==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-nWJ91DjeOkej/TA8pXQ3myruKpKEYgqvpw9lz4OPHj/NWFNluYrjbz9j01CJ8yKQd2g4jFoOkINCTW2I5LEEyw==, + } + engines: { node: ">= 0.4" } undici-types@7.8.0: - resolution: {integrity: sha512-9UJ2xGDvQ43tYyVMpuHlsgApydB8ZKfVYTsLDhXkFL/6gfkp+U8xTGdh8pMJv1SpZna0zxG1DwsKZsreLbXBxw==} + resolution: + { + integrity: sha512-9UJ2xGDvQ43tYyVMpuHlsgApydB8ZKfVYTsLDhXkFL/6gfkp+U8xTGdh8pMJv1SpZna0zxG1DwsKZsreLbXBxw==, + } unicorn-magic@0.3.0: - resolution: {integrity: sha512-+QBBXBCvifc56fsbuxZQ6Sic3wqqc3WWaqxs58gvJrcOuN83HGTCwz3oS5phzU9LthRNE9VrJCFCLUgHeeFnfA==} - engines: {node: '>=18'} + resolution: + { + integrity: sha512-+QBBXBCvifc56fsbuxZQ6Sic3wqqc3WWaqxs58gvJrcOuN83HGTCwz3oS5phzU9LthRNE9VrJCFCLUgHeeFnfA==, + } + engines: { node: ">=18" } unified@11.0.5: - resolution: {integrity: sha512-xKvGhPWw3k84Qjh8bI3ZeJjqnyadK+GEFtazSfZv/rKeTkTjOJho6mFqh2SM96iIcZokxiOpg78GazTSg8+KHA==} + resolution: + { + integrity: sha512-xKvGhPWw3k84Qjh8bI3ZeJjqnyadK+GEFtazSfZv/rKeTkTjOJho6mFqh2SM96iIcZokxiOpg78GazTSg8+KHA==, + } unist-util-is@6.0.0: - resolution: {integrity: sha512-2qCTHimwdxLfz+YzdGfkqNlH0tLi9xjTnHddPmJwtIG9MGsdbutfTc4P+haPD7l7Cjxf/WZj+we5qfVPvvxfYw==} + resolution: + { + integrity: sha512-2qCTHimwdxLfz+YzdGfkqNlH0tLi9xjTnHddPmJwtIG9MGsdbutfTc4P+haPD7l7Cjxf/WZj+we5qfVPvvxfYw==, + } unist-util-position@5.0.0: - resolution: {integrity: sha512-fucsC7HjXvkB5R3kTCO7kUjRdrS0BJt3M/FPxmHMBOm8JQi2BsHAHFsy27E0EolP8rp0NzXsJ+jNPyDWvOJZPA==} + resolution: + { + integrity: sha512-fucsC7HjXvkB5R3kTCO7kUjRdrS0BJt3M/FPxmHMBOm8JQi2BsHAHFsy27E0EolP8rp0NzXsJ+jNPyDWvOJZPA==, + } unist-util-stringify-position@4.0.0: - resolution: {integrity: sha512-0ASV06AAoKCDkS2+xw5RXJywruurpbC4JZSm7nr7MOt1ojAzvyyaO+UxZf18j8FCF6kmzCZKcAgN/yu2gm2XgQ==} + resolution: + { + integrity: sha512-0ASV06AAoKCDkS2+xw5RXJywruurpbC4JZSm7nr7MOt1ojAzvyyaO+UxZf18j8FCF6kmzCZKcAgN/yu2gm2XgQ==, + } unist-util-visit-parents@6.0.1: - resolution: {integrity: sha512-L/PqWzfTP9lzzEa6CKs0k2nARxTdZduw3zyh8d2NVBnsyvHjSX4TWse388YrrQKbvI8w20fGjGlhgT96WwKykw==} + resolution: + { + integrity: sha512-L/PqWzfTP9lzzEa6CKs0k2nARxTdZduw3zyh8d2NVBnsyvHjSX4TWse388YrrQKbvI8w20fGjGlhgT96WwKykw==, + } unist-util-visit@5.0.0: - resolution: {integrity: sha512-MR04uvD+07cwl/yhVuVWAtw+3GOR/knlL55Nd/wAdblk27GCVt3lqpTivy/tkJcZoNPzTwS1Y+KMojlLDhoTzg==} + resolution: + { + integrity: sha512-MR04uvD+07cwl/yhVuVWAtw+3GOR/knlL55Nd/wAdblk27GCVt3lqpTivy/tkJcZoNPzTwS1Y+KMojlLDhoTzg==, + } unrs-resolver@1.9.2: - resolution: {integrity: sha512-VUyWiTNQD7itdiMuJy+EuLEErLj3uwX/EpHQF8EOf33Dq3Ju6VW1GXm+swk6+1h7a49uv9fKZ+dft9jU7esdLA==} + resolution: + { + integrity: sha512-VUyWiTNQD7itdiMuJy+EuLEErLj3uwX/EpHQF8EOf33Dq3Ju6VW1GXm+swk6+1h7a49uv9fKZ+dft9jU7esdLA==, + } update-browserslist-db@1.1.3: - resolution: {integrity: sha512-UxhIZQ+QInVdunkDAaiazvvT/+fXL5Osr0JZlJulepYu6Jd7qJtDZjlur0emRlT71EN3ScPoE7gvsuIKKNavKw==} + resolution: + { + integrity: sha512-UxhIZQ+QInVdunkDAaiazvvT/+fXL5Osr0JZlJulepYu6Jd7qJtDZjlur0emRlT71EN3ScPoE7gvsuIKKNavKw==, + } hasBin: true peerDependencies: - browserslist: '>= 4.21.0' + browserslist: ">= 4.21.0" uri-js@4.4.1: - resolution: {integrity: sha512-7rKUyy33Q1yc98pQ1DAmLtwX109F7TIfWlW1Ydo8Wl1ii1SeHieeh0HHfPeL2fMXK6z0s8ecKs9frCuLJvndBg==} + resolution: + { + integrity: sha512-7rKUyy33Q1yc98pQ1DAmLtwX109F7TIfWlW1Ydo8Wl1ii1SeHieeh0HHfPeL2fMXK6z0s8ecKs9frCuLJvndBg==, + } use-callback-ref@1.3.3: - resolution: {integrity: sha512-jQL3lRnocaFtu3V00JToYz/4QkNWswxijDaCVNZRiRTO3HQDLsdu1ZtmIUvV4yPp+rvWm5j0y0TG/S61cuijTg==} - engines: {node: '>=10'} + resolution: + { + integrity: sha512-jQL3lRnocaFtu3V00JToYz/4QkNWswxijDaCVNZRiRTO3HQDLsdu1ZtmIUvV4yPp+rvWm5j0y0TG/S61cuijTg==, + } + engines: { node: ">=10" } peerDependencies: - '@types/react': '*' + "@types/react": "*" react: ^16.8.0 || ^17.0.0 || ^18.0.0 || ^19.0.0 || ^19.0.0-rc peerDependenciesMeta: - '@types/react': + "@types/react": optional: true use-sidecar@1.1.3: - resolution: {integrity: sha512-Fedw0aZvkhynoPYlA5WXrMCAMm+nSWdZt6lzJQ7Ok8S6Q+VsHmHpRWndVRJ8Be0ZbkfPc5LRYH+5XrzXcEeLRQ==} - engines: {node: '>=10'} + resolution: + { + integrity: sha512-Fedw0aZvkhynoPYlA5WXrMCAMm+nSWdZt6lzJQ7Ok8S6Q+VsHmHpRWndVRJ8Be0ZbkfPc5LRYH+5XrzXcEeLRQ==, + } + engines: { node: ">=10" } peerDependencies: - '@types/react': '*' + "@types/react": "*" react: ^16.8.0 || ^17.0.0 || ^18.0.0 || ^19.0.0 || ^19.0.0-rc peerDependenciesMeta: - '@types/react': + "@types/react": optional: true use-sync-external-store@1.5.0: - resolution: {integrity: sha512-Rb46I4cGGVBmjamjphe8L/UnvJD+uPPtTkNvX5mZgqdbavhI4EbgIWJiIHXJ8bc/i9EQGPRh4DwEURJ552Do0A==} + resolution: + { + integrity: sha512-Rb46I4cGGVBmjamjphe8L/UnvJD+uPPtTkNvX5mZgqdbavhI4EbgIWJiIHXJ8bc/i9EQGPRh4DwEURJ552Do0A==, + } peerDependencies: react: ^16.8.0 || ^17.0.0 || ^18.0.0 || ^19.0.0 uuid@8.3.2: - resolution: {integrity: sha512-+NYs2QeMWy+GWFOEm9xnn6HCDp0l7QBD7ml8zLUmJ+93Q5NF0NocErnwkTkXVFNiX3/fpC6afS8Dhb/gz7R7eg==} + resolution: + { + integrity: sha512-+NYs2QeMWy+GWFOEm9xnn6HCDp0l7QBD7ml8zLUmJ+93Q5NF0NocErnwkTkXVFNiX3/fpC6afS8Dhb/gz7R7eg==, + } hasBin: true v8-compile-cache-lib@3.0.1: - resolution: {integrity: sha512-wa7YjyUGfNZngI/vtK0UHAN+lgDCxBPCylVXGp0zu59Fz5aiGtNXaq3DhIov063MorB+VfufLh3JlF2KdTK3xg==} + resolution: + { + integrity: sha512-wa7YjyUGfNZngI/vtK0UHAN+lgDCxBPCylVXGp0zu59Fz5aiGtNXaq3DhIov063MorB+VfufLh3JlF2KdTK3xg==, + } vfile-location@5.0.3: - resolution: {integrity: sha512-5yXvWDEgqeiYiBe1lbxYF7UMAIm/IcopxMHrMQDq3nvKcjPKIhZklUKL+AE7J7uApI4kwe2snsK+eI6UTj9EHg==} + resolution: + { + integrity: sha512-5yXvWDEgqeiYiBe1lbxYF7UMAIm/IcopxMHrMQDq3nvKcjPKIhZklUKL+AE7J7uApI4kwe2snsK+eI6UTj9EHg==, + } vfile-message@4.0.2: - resolution: {integrity: sha512-jRDZ1IMLttGj41KcZvlrYAaI3CfqpLpfpf+Mfig13viT6NKvRzWZ+lXz0Y5D60w6uJIBAOGq9mSHf0gktF0duw==} + resolution: + { + integrity: sha512-jRDZ1IMLttGj41KcZvlrYAaI3CfqpLpfpf+Mfig13viT6NKvRzWZ+lXz0Y5D60w6uJIBAOGq9mSHf0gktF0duw==, + } vfile@6.0.3: - resolution: {integrity: sha512-KzIbH/9tXat2u30jf+smMwFCsno4wHVdNmzFyL+T/L3UGqqk6JKfVqOFOZEpZSHADH1k40ab6NUIXZq422ov3Q==} + resolution: + { + integrity: sha512-KzIbH/9tXat2u30jf+smMwFCsno4wHVdNmzFyL+T/L3UGqqk6JKfVqOFOZEpZSHADH1k40ab6NUIXZq422ov3Q==, + } victory-vendor@37.3.6: - resolution: {integrity: sha512-SbPDPdDBYp+5MJHhBCAyI7wKM3d5ivekigc2Dk2s7pgbZ9wIgIBYGVw4zGHBml/qTFbexrofXW6Gu4noGxrOwQ==} + resolution: + { + integrity: sha512-SbPDPdDBYp+5MJHhBCAyI7wKM3d5ivekigc2Dk2s7pgbZ9wIgIBYGVw4zGHBml/qTFbexrofXW6Gu4noGxrOwQ==, + } vite-node@3.2.4: - resolution: {integrity: sha512-EbKSKh+bh1E1IFxeO0pg1n4dvoOTt0UDiXMd/qn++r98+jPO1xtJilvXldeuQ8giIB5IkpjCgMleHMNEsGH6pg==} - engines: {node: ^18.0.0 || ^20.0.0 || >=22.0.0} + resolution: + { + integrity: sha512-EbKSKh+bh1E1IFxeO0pg1n4dvoOTt0UDiXMd/qn++r98+jPO1xtJilvXldeuQ8giIB5IkpjCgMleHMNEsGH6pg==, + } + engines: { node: ^18.0.0 || ^20.0.0 || >=22.0.0 } hasBin: true vite-tsconfig-paths@5.1.4: - resolution: {integrity: sha512-cYj0LRuLV2c2sMqhqhGpaO3LretdtMn/BVX4cPLanIZuwwrkVl+lK84E/miEXkCHWXuq65rhNN4rXsBcOB3S4w==} + resolution: + { + integrity: sha512-cYj0LRuLV2c2sMqhqhGpaO3LretdtMn/BVX4cPLanIZuwwrkVl+lK84E/miEXkCHWXuq65rhNN4rXsBcOB3S4w==, + } peerDependencies: - vite: '*' + vite: "*" peerDependenciesMeta: vite: optional: true vite@7.0.0: - resolution: {integrity: sha512-ixXJB1YRgDIw2OszKQS9WxGHKwLdCsbQNkpJN171udl6szi/rIySHL6/Os3s2+oE4P/FLD4dxg4mD7Wust+u5g==} - engines: {node: ^20.19.0 || >=22.12.0} + resolution: + { + integrity: sha512-ixXJB1YRgDIw2OszKQS9WxGHKwLdCsbQNkpJN171udl6szi/rIySHL6/Os3s2+oE4P/FLD4dxg4mD7Wust+u5g==, + } + engines: { node: ^20.19.0 || >=22.12.0 } hasBin: true peerDependencies: - '@types/node': ^20.19.0 || >=22.12.0 - jiti: '>=1.21.0' + "@types/node": ^20.19.0 || >=22.12.0 + jiti: ">=1.21.0" less: ^4.0.0 lightningcss: ^1.21.0 sass: ^1.70.0 sass-embedded: ^1.70.0 - stylus: '>=0.54.8' + stylus: ">=0.54.8" sugarss: ^5.0.0 terser: ^5.16.0 tsx: ^4.8.1 yaml: ^2.4.2 peerDependenciesMeta: - '@types/node': + "@types/node": optional: true jiti: optional: true @@ -4273,27 +7006,30 @@ packages: optional: true vitest@3.2.4: - resolution: {integrity: sha512-LUCP5ev3GURDysTWiP47wRRUpLKMOfPh+yKTx3kVIEiu5KOMeqzpnYNsKyOoVrULivR8tLcks4+lga33Whn90A==} - engines: {node: ^18.0.0 || ^20.0.0 || >=22.0.0} + resolution: + { + integrity: sha512-LUCP5ev3GURDysTWiP47wRRUpLKMOfPh+yKTx3kVIEiu5KOMeqzpnYNsKyOoVrULivR8tLcks4+lga33Whn90A==, + } + engines: { node: ^18.0.0 || ^20.0.0 || >=22.0.0 } hasBin: true peerDependencies: - '@edge-runtime/vm': '*' - '@types/debug': ^4.1.12 - '@types/node': ^18.0.0 || ^20.0.0 || >=22.0.0 - '@vitest/browser': 3.2.4 - '@vitest/ui': 3.2.4 - happy-dom: '*' - jsdom: '*' + "@edge-runtime/vm": "*" + "@types/debug": ^4.1.12 + "@types/node": ^18.0.0 || ^20.0.0 || >=22.0.0 + "@vitest/browser": 3.2.4 + "@vitest/ui": 3.2.4 + happy-dom: "*" + jsdom: "*" peerDependenciesMeta: - '@edge-runtime/vm': + "@edge-runtime/vm": optional: true - '@types/debug': + "@types/debug": optional: true - '@types/node': + "@types/node": optional: true - '@vitest/browser': + "@vitest/browser": optional: true - '@vitest/ui': + "@vitest/ui": optional: true happy-dom: optional: true @@ -4301,79 +7037,133 @@ packages: optional: true w3c-xmlserializer@5.0.0: - resolution: {integrity: sha512-o8qghlI8NZHU1lLPrpi2+Uq7abh4GGPpYANlalzWxyWteJOCsr/P+oPBA49TOLu5FTZO4d3F9MnWJfiMo4BkmA==} - engines: {node: '>=18'} + resolution: + { + integrity: sha512-o8qghlI8NZHU1lLPrpi2+Uq7abh4GGPpYANlalzWxyWteJOCsr/P+oPBA49TOLu5FTZO4d3F9MnWJfiMo4BkmA==, + } + engines: { node: ">=18" } web-namespaces@2.0.1: - resolution: {integrity: sha512-bKr1DkiNa2krS7qxNtdrtHAmzuYGFQLiQ13TsorsdT6ULTkPLKuu5+GsFpDlg6JFjUTwX2DyhMPG2be8uPrqsQ==} + resolution: + { + integrity: sha512-bKr1DkiNa2krS7qxNtdrtHAmzuYGFQLiQ13TsorsdT6ULTkPLKuu5+GsFpDlg6JFjUTwX2DyhMPG2be8uPrqsQ==, + } web-streams-polyfill@3.3.3: - resolution: {integrity: sha512-d2JWLCivmZYTSIoge9MsgFCZrt571BikcWGYkjC1khllbTeDlGqZ2D8vD8E/lJa8WGWbb7Plm8/XJYV7IJHZZw==} - engines: {node: '>= 8'} + resolution: + { + integrity: sha512-d2JWLCivmZYTSIoge9MsgFCZrt571BikcWGYkjC1khllbTeDlGqZ2D8vD8E/lJa8WGWbb7Plm8/XJYV7IJHZZw==, + } + engines: { node: ">= 8" } webidl-conversions@7.0.0: - resolution: {integrity: sha512-VwddBukDzu71offAQR975unBIGqfKZpM+8ZX6ySk8nYhVoo5CYaZyzt3YBvYtRtO+aoGlqxPg/B87NGVZ/fu6g==} - engines: {node: '>=12'} + resolution: + { + integrity: sha512-VwddBukDzu71offAQR975unBIGqfKZpM+8ZX6ySk8nYhVoo5CYaZyzt3YBvYtRtO+aoGlqxPg/B87NGVZ/fu6g==, + } + engines: { node: ">=12" } whatwg-encoding@3.1.1: - resolution: {integrity: sha512-6qN4hJdMwfYBtE3YBTTHhoeuUrDBPZmbQaxWAqSALV/MeEnR5z1xd8UKud2RAkFoPkmB+hli1TZSnyi84xz1vQ==} - engines: {node: '>=18'} + resolution: + { + integrity: sha512-6qN4hJdMwfYBtE3YBTTHhoeuUrDBPZmbQaxWAqSALV/MeEnR5z1xd8UKud2RAkFoPkmB+hli1TZSnyi84xz1vQ==, + } + engines: { node: ">=18" } whatwg-mimetype@4.0.0: - resolution: {integrity: sha512-QaKxh0eNIi2mE9p2vEdzfagOKHCcj1pJ56EEHGQOVxp8r9/iszLUUV7v89x9O1p/T+NlTM5W7jW6+cz4Fq1YVg==} - engines: {node: '>=18'} + resolution: + { + integrity: sha512-QaKxh0eNIi2mE9p2vEdzfagOKHCcj1pJ56EEHGQOVxp8r9/iszLUUV7v89x9O1p/T+NlTM5W7jW6+cz4Fq1YVg==, + } + engines: { node: ">=18" } whatwg-url@14.2.0: - resolution: {integrity: sha512-De72GdQZzNTUBBChsXueQUnPKDkg/5A5zp7pFDuQAj5UFoENpiACU0wlCvzpAGnTkj++ihpKwKyYewn/XNUbKw==} - engines: {node: '>=18'} + resolution: + { + integrity: sha512-De72GdQZzNTUBBChsXueQUnPKDkg/5A5zp7pFDuQAj5UFoENpiACU0wlCvzpAGnTkj++ihpKwKyYewn/XNUbKw==, + } + engines: { node: ">=18" } which-boxed-primitive@1.1.1: - resolution: {integrity: sha512-TbX3mj8n0odCBFVlY8AxkqcHASw3L60jIuF8jFP78az3C2YhmGvqbHBpAjTRH2/xqYunrJ9g1jSyjCjpoWzIAA==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-TbX3mj8n0odCBFVlY8AxkqcHASw3L60jIuF8jFP78az3C2YhmGvqbHBpAjTRH2/xqYunrJ9g1jSyjCjpoWzIAA==, + } + engines: { node: ">= 0.4" } which-builtin-type@1.2.1: - resolution: {integrity: sha512-6iBczoX+kDQ7a3+YJBnh3T+KZRxM/iYNPXicqk66/Qfm1b93iu+yOImkg0zHbj5LNOcNv1TEADiZ0xa34B4q6Q==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-6iBczoX+kDQ7a3+YJBnh3T+KZRxM/iYNPXicqk66/Qfm1b93iu+yOImkg0zHbj5LNOcNv1TEADiZ0xa34B4q6Q==, + } + engines: { node: ">= 0.4" } which-collection@1.0.2: - resolution: {integrity: sha512-K4jVyjnBdgvc86Y6BkaLZEN933SwYOuBFkdmBu9ZfkcAbdVbpITnDmjvZ/aQjRXQrv5EPkTnD1s39GiiqbngCw==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-K4jVyjnBdgvc86Y6BkaLZEN933SwYOuBFkdmBu9ZfkcAbdVbpITnDmjvZ/aQjRXQrv5EPkTnD1s39GiiqbngCw==, + } + engines: { node: ">= 0.4" } which-polygon@2.2.1: - resolution: {integrity: sha512-RlpWbqz12OMT0r2lEHk7IUPXz0hb1L/ZZsGushB2P2qxuBu1aq1+bcTfsLtfoRBYHsED6ruBMiwFaidvXZfQVw==} + resolution: + { + integrity: sha512-RlpWbqz12OMT0r2lEHk7IUPXz0hb1L/ZZsGushB2P2qxuBu1aq1+bcTfsLtfoRBYHsED6ruBMiwFaidvXZfQVw==, + } which-typed-array@1.1.19: - resolution: {integrity: sha512-rEvr90Bck4WZt9HHFC4DJMsjvu7x+r6bImz0/BrbWb7A2djJ8hnZMrWnHo9F8ssv0OMErasDhftrfROTyqSDrw==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-rEvr90Bck4WZt9HHFC4DJMsjvu7x+r6bImz0/BrbWb7A2djJ8hnZMrWnHo9F8ssv0OMErasDhftrfROTyqSDrw==, + } + engines: { node: ">= 0.4" } which@2.0.2: - resolution: {integrity: sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA==} - engines: {node: '>= 8'} + resolution: + { + integrity: sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA==, + } + engines: { node: ">= 8" } hasBin: true why-is-node-running@2.3.0: - resolution: {integrity: sha512-hUrmaWBdVDcxvYqnyh09zunKzROWjbZTiNy8dBEjkS7ehEDQibXJ7XvlmtbwuTclUiIyN+CyXQD4Vmko8fNm8w==} - engines: {node: '>=8'} + resolution: + { + integrity: sha512-hUrmaWBdVDcxvYqnyh09zunKzROWjbZTiNy8dBEjkS7ehEDQibXJ7XvlmtbwuTclUiIyN+CyXQD4Vmko8fNm8w==, + } + engines: { node: ">=8" } hasBin: true word-wrap@1.2.5: - resolution: {integrity: sha512-BN22B5eaMMI9UMtjrGd5g5eCYPpCPDUy0FJXbYsaT5zYxjFOckS53SQDE3pWkVoWpHXVb3BrYcEN4Twa55B5cA==} - engines: {node: '>=0.10.0'} + resolution: + { + integrity: sha512-BN22B5eaMMI9UMtjrGd5g5eCYPpCPDUy0FJXbYsaT5zYxjFOckS53SQDE3pWkVoWpHXVb3BrYcEN4Twa55B5cA==, + } + engines: { node: ">=0.10.0" } wrap-ansi@7.0.0: - resolution: {integrity: sha512-YVGIj2kamLSTxw6NsZjoBxfSwsn0ycdesmc4p+Q21c5zPuZ1pl+NfxVdxPtdHvmNVOQ6XSYG4AUtyt/Fi7D16Q==} - engines: {node: '>=10'} + resolution: + { + integrity: sha512-YVGIj2kamLSTxw6NsZjoBxfSwsn0ycdesmc4p+Q21c5zPuZ1pl+NfxVdxPtdHvmNVOQ6XSYG4AUtyt/Fi7D16Q==, + } + engines: { node: ">=10" } wrap-ansi@8.1.0: - resolution: {integrity: sha512-si7QWI6zUMq56bESFvagtmzMdGOtoxfR+Sez11Mobfc7tm+VkUckk9bW2UeffTGVUbOksxmSw0AA2gs8g71NCQ==} - engines: {node: '>=12'} + resolution: + { + integrity: sha512-si7QWI6zUMq56bESFvagtmzMdGOtoxfR+Sez11Mobfc7tm+VkUckk9bW2UeffTGVUbOksxmSw0AA2gs8g71NCQ==, + } + engines: { node: ">=12" } ws@8.18.2: - resolution: {integrity: sha512-DMricUmwGZUVr++AEAe2uiVM7UoO9MAVZMDu05UQOaUII0lp+zOzLLU4Xqh/JvTqklB1T4uELaaPBKyjE1r4fQ==} - engines: {node: '>=10.0.0'} + resolution: + { + integrity: sha512-DMricUmwGZUVr++AEAe2uiVM7UoO9MAVZMDu05UQOaUII0lp+zOzLLU4Xqh/JvTqklB1T4uELaaPBKyjE1r4fQ==, + } + engines: { node: ">=10.0.0" } peerDependencies: bufferutil: ^4.0.1 - utf-8-validate: '>=5.0.2' + utf-8-validate: ">=5.0.2" peerDependenciesMeta: bufferutil: optional: true @@ -4381,74 +7171,106 @@ packages: optional: true xml-name-validator@5.0.0: - resolution: {integrity: sha512-EvGK8EJ3DhaHfbRlETOWAS5pO9MZITeauHKJyb8wyajUfQUenkIg2MvLDTZ4T/TgIcm3HU0TFBgWWboAZ30UHg==} - engines: {node: '>=18'} + resolution: + { + integrity: sha512-EvGK8EJ3DhaHfbRlETOWAS5pO9MZITeauHKJyb8wyajUfQUenkIg2MvLDTZ4T/TgIcm3HU0TFBgWWboAZ30UHg==, + } + engines: { node: ">=18" } xmlchars@2.2.0: - resolution: {integrity: sha512-JZnDKK8B0RCDw84FNdDAIpZK+JuJw+s7Lz8nksI7SIuU3UXJJslUthsi+uWBUYOwPFwW7W7PRLRfUKpxjtjFCw==} + resolution: + { + integrity: sha512-JZnDKK8B0RCDw84FNdDAIpZK+JuJw+s7Lz8nksI7SIuU3UXJJslUthsi+uWBUYOwPFwW7W7PRLRfUKpxjtjFCw==, + } xtend@4.0.2: - resolution: {integrity: sha512-LKYU1iAXJXUgAXn9URjiu+MWhyUXHsvfp7mcuYm9dSUKK0/CjtrUwFAxD82/mCWbtLsGjFIad0wIsod4zrTAEQ==} - engines: {node: '>=0.4'} + resolution: + { + integrity: sha512-LKYU1iAXJXUgAXn9URjiu+MWhyUXHsvfp7mcuYm9dSUKK0/CjtrUwFAxD82/mCWbtLsGjFIad0wIsod4zrTAEQ==, + } + engines: { node: ">=0.4" } yallist@3.1.1: - resolution: {integrity: sha512-a4UGQaWPH59mOXUYnAG2ewncQS4i4F43Tv3JoAM+s2VDAmS9NsK8GpDMLrCHPksFT7h3K6TOoUNn2pb7RoXx4g==} + resolution: + { + integrity: sha512-a4UGQaWPH59mOXUYnAG2ewncQS4i4F43Tv3JoAM+s2VDAmS9NsK8GpDMLrCHPksFT7h3K6TOoUNn2pb7RoXx4g==, + } yallist@4.0.0: - resolution: {integrity: sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A==} + resolution: + { + integrity: sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A==, + } yallist@5.0.0: - resolution: {integrity: sha512-YgvUTfwqyc7UXVMrB+SImsVYSmTS8X/tSrtdNZMImM+n7+QTriRXyXim0mBrTXNeqzVF0KWGgHPeiyViFFrNDw==} - engines: {node: '>=18'} + resolution: + { + integrity: sha512-YgvUTfwqyc7UXVMrB+SImsVYSmTS8X/tSrtdNZMImM+n7+QTriRXyXim0mBrTXNeqzVF0KWGgHPeiyViFFrNDw==, + } + engines: { node: ">=18" } yn@3.1.1: - resolution: {integrity: sha512-Ux4ygGWsu2c7isFWe8Yu1YluJmqVhxqK2cLXNQA5AcC3QfbGNpM7fu0Y8b/z16pXLnFxZYvWhd3fhBY9DLmC6Q==} - engines: {node: '>=6'} + resolution: + { + integrity: sha512-Ux4ygGWsu2c7isFWe8Yu1YluJmqVhxqK2cLXNQA5AcC3QfbGNpM7fu0Y8b/z16pXLnFxZYvWhd3fhBY9DLmC6Q==, + } + engines: { node: ">=6" } yocto-queue@0.1.0: - resolution: {integrity: sha512-rVksvsnNCdJ/ohGc6xgPwyN8eheCxsiLM8mxuE/t/mOVqJewPuO1miLpTHQiRgTKCLexL4MeAFVagts7HmNZ2Q==} - engines: {node: '>=10'} + resolution: + { + integrity: sha512-rVksvsnNCdJ/ohGc6xgPwyN8eheCxsiLM8mxuE/t/mOVqJewPuO1miLpTHQiRgTKCLexL4MeAFVagts7HmNZ2Q==, + } + engines: { node: ">=10" } + + zod@3.25.67: + resolution: + { + integrity: sha512-idA2YXwpCdqUSKRCACDE6ItZD9TZzy3OZMtpfLoh6oPR47lipysRrJfjzMqFxQ3uJuUPyUeWe1r9vLH33xO/Qw==, + } zwitch@2.0.4: - resolution: {integrity: sha512-bXE4cR/kVZhKZX/RjPEflHaKVhUVl85noU3v6b8apfQEc1x4A+zBxjZ4lN8LqGd6WZ3dl98pY4o717VFmoPp+A==} + resolution: + { + integrity: sha512-bXE4cR/kVZhKZX/RjPEflHaKVhUVl85noU3v6b8apfQEc1x4A+zBxjZ4lN8LqGd6WZ3dl98pY4o717VFmoPp+A==, + } snapshots: + "@alloc/quick-lru@5.2.0": {} - '@alloc/quick-lru@5.2.0': {} - - '@ampproject/remapping@2.3.0': + "@ampproject/remapping@2.3.0": dependencies: - '@jridgewell/gen-mapping': 0.3.8 - '@jridgewell/trace-mapping': 0.3.25 + "@jridgewell/gen-mapping": 0.3.8 + "@jridgewell/trace-mapping": 0.3.25 - '@asamuzakjp/css-color@3.2.0': + "@asamuzakjp/css-color@3.2.0": dependencies: - '@csstools/css-calc': 2.1.4(@csstools/css-parser-algorithms@3.0.5(@csstools/css-tokenizer@3.0.4))(@csstools/css-tokenizer@3.0.4) - '@csstools/css-color-parser': 3.0.10(@csstools/css-parser-algorithms@3.0.5(@csstools/css-tokenizer@3.0.4))(@csstools/css-tokenizer@3.0.4) - '@csstools/css-parser-algorithms': 3.0.5(@csstools/css-tokenizer@3.0.4) - '@csstools/css-tokenizer': 3.0.4 + "@csstools/css-calc": 2.1.4(@csstools/css-parser-algorithms@3.0.5(@csstools/css-tokenizer@3.0.4))(@csstools/css-tokenizer@3.0.4) + "@csstools/css-color-parser": 3.0.10(@csstools/css-parser-algorithms@3.0.5(@csstools/css-tokenizer@3.0.4))(@csstools/css-tokenizer@3.0.4) + "@csstools/css-parser-algorithms": 3.0.5(@csstools/css-tokenizer@3.0.4) + "@csstools/css-tokenizer": 3.0.4 lru-cache: 10.4.3 - '@babel/code-frame@7.27.1': + "@babel/code-frame@7.27.1": dependencies: - '@babel/helper-validator-identifier': 7.27.1 + "@babel/helper-validator-identifier": 7.27.1 js-tokens: 4.0.0 picocolors: 1.1.1 - '@babel/compat-data@7.27.7': {} + "@babel/compat-data@7.27.7": {} - '@babel/core@7.27.7': + "@babel/core@7.27.7": dependencies: - '@ampproject/remapping': 2.3.0 - '@babel/code-frame': 7.27.1 - '@babel/generator': 7.27.5 - '@babel/helper-compilation-targets': 7.27.2 - '@babel/helper-module-transforms': 7.27.3(@babel/core@7.27.7) - '@babel/helpers': 7.27.6 - '@babel/parser': 7.27.7 - '@babel/template': 7.27.2 - '@babel/traverse': 7.27.7 - '@babel/types': 7.27.7 + "@ampproject/remapping": 2.3.0 + "@babel/code-frame": 7.27.1 + "@babel/generator": 7.27.5 + "@babel/helper-compilation-targets": 7.27.2 + "@babel/helper-module-transforms": 7.27.3(@babel/core@7.27.7) + "@babel/helpers": 7.27.6 + "@babel/parser": 7.27.7 + "@babel/template": 7.27.2 + "@babel/traverse": 7.27.7 + "@babel/types": 7.27.7 convert-source-map: 2.0.0 debug: 4.4.1 gensync: 1.0.0-beta.2 @@ -4457,233 +7279,233 @@ snapshots: transitivePeerDependencies: - supports-color - '@babel/generator@7.27.5': + "@babel/generator@7.27.5": dependencies: - '@babel/parser': 7.27.7 - '@babel/types': 7.27.7 - '@jridgewell/gen-mapping': 0.3.8 - '@jridgewell/trace-mapping': 0.3.25 + "@babel/parser": 7.27.7 + "@babel/types": 7.27.7 + "@jridgewell/gen-mapping": 0.3.8 + "@jridgewell/trace-mapping": 0.3.25 jsesc: 3.1.0 - '@babel/helper-compilation-targets@7.27.2': + "@babel/helper-compilation-targets@7.27.2": dependencies: - '@babel/compat-data': 7.27.7 - '@babel/helper-validator-option': 7.27.1 + "@babel/compat-data": 7.27.7 + "@babel/helper-validator-option": 7.27.1 browserslist: 4.25.1 lru-cache: 5.1.1 semver: 6.3.1 - '@babel/helper-module-imports@7.27.1': + "@babel/helper-module-imports@7.27.1": dependencies: - '@babel/traverse': 7.27.7 - '@babel/types': 7.27.7 + "@babel/traverse": 7.27.7 + "@babel/types": 7.27.7 transitivePeerDependencies: - supports-color - '@babel/helper-module-transforms@7.27.3(@babel/core@7.27.7)': + "@babel/helper-module-transforms@7.27.3(@babel/core@7.27.7)": dependencies: - '@babel/core': 7.27.7 - '@babel/helper-module-imports': 7.27.1 - '@babel/helper-validator-identifier': 7.27.1 - '@babel/traverse': 7.27.7 + "@babel/core": 7.27.7 + "@babel/helper-module-imports": 7.27.1 + "@babel/helper-validator-identifier": 7.27.1 + "@babel/traverse": 7.27.7 transitivePeerDependencies: - supports-color - '@babel/helper-plugin-utils@7.27.1': {} + "@babel/helper-plugin-utils@7.27.1": {} - '@babel/helper-string-parser@7.27.1': {} + "@babel/helper-string-parser@7.27.1": {} - '@babel/helper-validator-identifier@7.27.1': {} + "@babel/helper-validator-identifier@7.27.1": {} - '@babel/helper-validator-option@7.27.1': {} + "@babel/helper-validator-option@7.27.1": {} - '@babel/helpers@7.27.6': + "@babel/helpers@7.27.6": dependencies: - '@babel/template': 7.27.2 - '@babel/types': 7.27.7 + "@babel/template": 7.27.2 + "@babel/types": 7.27.7 - '@babel/parser@7.27.7': + "@babel/parser@7.27.7": dependencies: - '@babel/types': 7.27.7 + "@babel/types": 7.27.7 - '@babel/plugin-transform-react-jsx-self@7.27.1(@babel/core@7.27.7)': + "@babel/plugin-transform-react-jsx-self@7.27.1(@babel/core@7.27.7)": dependencies: - '@babel/core': 7.27.7 - '@babel/helper-plugin-utils': 7.27.1 + "@babel/core": 7.27.7 + "@babel/helper-plugin-utils": 7.27.1 - '@babel/plugin-transform-react-jsx-source@7.27.1(@babel/core@7.27.7)': + "@babel/plugin-transform-react-jsx-source@7.27.1(@babel/core@7.27.7)": dependencies: - '@babel/core': 7.27.7 - '@babel/helper-plugin-utils': 7.27.1 + "@babel/core": 7.27.7 + "@babel/helper-plugin-utils": 7.27.1 - '@babel/runtime@7.27.6': {} + "@babel/runtime@7.27.6": {} - '@babel/template@7.27.2': + "@babel/template@7.27.2": dependencies: - '@babel/code-frame': 7.27.1 - '@babel/parser': 7.27.7 - '@babel/types': 7.27.7 + "@babel/code-frame": 7.27.1 + "@babel/parser": 7.27.7 + "@babel/types": 7.27.7 - '@babel/traverse@7.27.7': + "@babel/traverse@7.27.7": dependencies: - '@babel/code-frame': 7.27.1 - '@babel/generator': 7.27.5 - '@babel/parser': 7.27.7 - '@babel/template': 7.27.2 - '@babel/types': 7.27.7 + "@babel/code-frame": 7.27.1 + "@babel/generator": 7.27.5 + "@babel/parser": 7.27.7 + "@babel/template": 7.27.2 + "@babel/types": 7.27.7 debug: 4.4.1 globals: 11.12.0 transitivePeerDependencies: - supports-color - '@babel/types@7.27.7': + "@babel/types@7.27.7": dependencies: - '@babel/helper-string-parser': 7.27.1 - '@babel/helper-validator-identifier': 7.27.1 + "@babel/helper-string-parser": 7.27.1 + "@babel/helper-validator-identifier": 7.27.1 - '@bcoe/v8-coverage@1.0.2': {} + "@bcoe/v8-coverage@1.0.2": {} - '@cspotcode/source-map-support@0.8.1': + "@cspotcode/source-map-support@0.8.1": dependencies: - '@jridgewell/trace-mapping': 0.3.9 + "@jridgewell/trace-mapping": 0.3.9 - '@csstools/color-helpers@5.0.2': {} + "@csstools/color-helpers@5.0.2": {} - '@csstools/css-calc@2.1.4(@csstools/css-parser-algorithms@3.0.5(@csstools/css-tokenizer@3.0.4))(@csstools/css-tokenizer@3.0.4)': + "@csstools/css-calc@2.1.4(@csstools/css-parser-algorithms@3.0.5(@csstools/css-tokenizer@3.0.4))(@csstools/css-tokenizer@3.0.4)": dependencies: - '@csstools/css-parser-algorithms': 3.0.5(@csstools/css-tokenizer@3.0.4) - '@csstools/css-tokenizer': 3.0.4 + "@csstools/css-parser-algorithms": 3.0.5(@csstools/css-tokenizer@3.0.4) + "@csstools/css-tokenizer": 3.0.4 - '@csstools/css-color-parser@3.0.10(@csstools/css-parser-algorithms@3.0.5(@csstools/css-tokenizer@3.0.4))(@csstools/css-tokenizer@3.0.4)': + "@csstools/css-color-parser@3.0.10(@csstools/css-parser-algorithms@3.0.5(@csstools/css-tokenizer@3.0.4))(@csstools/css-tokenizer@3.0.4)": dependencies: - '@csstools/color-helpers': 5.0.2 - '@csstools/css-calc': 2.1.4(@csstools/css-parser-algorithms@3.0.5(@csstools/css-tokenizer@3.0.4))(@csstools/css-tokenizer@3.0.4) - '@csstools/css-parser-algorithms': 3.0.5(@csstools/css-tokenizer@3.0.4) - '@csstools/css-tokenizer': 3.0.4 + "@csstools/color-helpers": 5.0.2 + "@csstools/css-calc": 2.1.4(@csstools/css-parser-algorithms@3.0.5(@csstools/css-tokenizer@3.0.4))(@csstools/css-tokenizer@3.0.4) + "@csstools/css-parser-algorithms": 3.0.5(@csstools/css-tokenizer@3.0.4) + "@csstools/css-tokenizer": 3.0.4 - '@csstools/css-parser-algorithms@3.0.5(@csstools/css-tokenizer@3.0.4)': + "@csstools/css-parser-algorithms@3.0.5(@csstools/css-tokenizer@3.0.4)": dependencies: - '@csstools/css-tokenizer': 3.0.4 + "@csstools/css-tokenizer": 3.0.4 - '@csstools/css-tokenizer@3.0.4': {} + "@csstools/css-tokenizer@3.0.4": {} - '@emnapi/core@1.4.3': + "@emnapi/core@1.4.3": dependencies: - '@emnapi/wasi-threads': 1.0.2 + "@emnapi/wasi-threads": 1.0.2 tslib: 2.8.1 optional: true - '@emnapi/runtime@1.4.3': + "@emnapi/runtime@1.4.3": dependencies: tslib: 2.8.1 optional: true - '@emnapi/wasi-threads@1.0.2': + "@emnapi/wasi-threads@1.0.2": dependencies: tslib: 2.8.1 optional: true - '@esbuild/aix-ppc64@0.25.5': + "@esbuild/aix-ppc64@0.25.5": optional: true - '@esbuild/android-arm64@0.25.5': + "@esbuild/android-arm64@0.25.5": optional: true - '@esbuild/android-arm@0.25.5': + "@esbuild/android-arm@0.25.5": optional: true - '@esbuild/android-x64@0.25.5': + "@esbuild/android-x64@0.25.5": optional: true - '@esbuild/darwin-arm64@0.25.5': + "@esbuild/darwin-arm64@0.25.5": optional: true - '@esbuild/darwin-x64@0.25.5': + "@esbuild/darwin-x64@0.25.5": optional: true - '@esbuild/freebsd-arm64@0.25.5': + "@esbuild/freebsd-arm64@0.25.5": optional: true - '@esbuild/freebsd-x64@0.25.5': + "@esbuild/freebsd-x64@0.25.5": optional: true - '@esbuild/linux-arm64@0.25.5': + "@esbuild/linux-arm64@0.25.5": optional: true - '@esbuild/linux-arm@0.25.5': + "@esbuild/linux-arm@0.25.5": optional: true - '@esbuild/linux-ia32@0.25.5': + "@esbuild/linux-ia32@0.25.5": optional: true - '@esbuild/linux-loong64@0.25.5': + "@esbuild/linux-loong64@0.25.5": optional: true - '@esbuild/linux-mips64el@0.25.5': + "@esbuild/linux-mips64el@0.25.5": optional: true - '@esbuild/linux-ppc64@0.25.5': + "@esbuild/linux-ppc64@0.25.5": optional: true - '@esbuild/linux-riscv64@0.25.5': + "@esbuild/linux-riscv64@0.25.5": optional: true - '@esbuild/linux-s390x@0.25.5': + "@esbuild/linux-s390x@0.25.5": optional: true - '@esbuild/linux-x64@0.25.5': + "@esbuild/linux-x64@0.25.5": optional: true - '@esbuild/netbsd-arm64@0.25.5': + "@esbuild/netbsd-arm64@0.25.5": optional: true - '@esbuild/netbsd-x64@0.25.5': + "@esbuild/netbsd-x64@0.25.5": optional: true - '@esbuild/openbsd-arm64@0.25.5': + "@esbuild/openbsd-arm64@0.25.5": optional: true - '@esbuild/openbsd-x64@0.25.5': + "@esbuild/openbsd-x64@0.25.5": optional: true - '@esbuild/sunos-x64@0.25.5': + "@esbuild/sunos-x64@0.25.5": optional: true - '@esbuild/win32-arm64@0.25.5': + "@esbuild/win32-arm64@0.25.5": optional: true - '@esbuild/win32-ia32@0.25.5': + "@esbuild/win32-ia32@0.25.5": optional: true - '@esbuild/win32-x64@0.25.5': + "@esbuild/win32-x64@0.25.5": optional: true - '@eslint-community/eslint-utils@4.7.0(eslint@9.30.0(jiti@2.4.2))': + "@eslint-community/eslint-utils@4.7.0(eslint@9.30.0(jiti@2.4.2))": dependencies: eslint: 9.30.0(jiti@2.4.2) eslint-visitor-keys: 3.4.3 - '@eslint-community/regexpp@4.12.1': {} + "@eslint-community/regexpp@4.12.1": {} - '@eslint/config-array@0.21.0': + "@eslint/config-array@0.21.0": dependencies: - '@eslint/object-schema': 2.1.6 + "@eslint/object-schema": 2.1.6 debug: 4.4.1 minimatch: 3.1.2 transitivePeerDependencies: - supports-color - '@eslint/config-helpers@0.3.0': {} + "@eslint/config-helpers@0.3.0": {} - '@eslint/core@0.14.0': + "@eslint/core@0.14.0": dependencies: - '@types/json-schema': 7.0.15 + "@types/json-schema": 7.0.15 - '@eslint/core@0.15.1': + "@eslint/core@0.15.1": dependencies: - '@types/json-schema': 7.0.15 + "@types/json-schema": 7.0.15 - '@eslint/eslintrc@3.3.1': + "@eslint/eslintrc@3.3.1": dependencies: ajv: 6.12.6 debug: 4.4.1 @@ -4697,127 +7519,127 @@ snapshots: transitivePeerDependencies: - supports-color - '@eslint/js@9.30.0': {} + "@eslint/js@9.30.0": {} - '@eslint/object-schema@2.1.6': {} + "@eslint/object-schema@2.1.6": {} - '@eslint/plugin-kit@0.3.3': + "@eslint/plugin-kit@0.3.3": dependencies: - '@eslint/core': 0.15.1 + "@eslint/core": 0.15.1 levn: 0.4.1 - '@floating-ui/core@1.7.1': + "@floating-ui/core@1.7.1": dependencies: - '@floating-ui/utils': 0.2.9 + "@floating-ui/utils": 0.2.9 - '@floating-ui/dom@1.7.1': + "@floating-ui/dom@1.7.1": dependencies: - '@floating-ui/core': 1.7.1 - '@floating-ui/utils': 0.2.9 + "@floating-ui/core": 1.7.1 + "@floating-ui/utils": 0.2.9 - '@floating-ui/react-dom@2.1.3(react-dom@19.1.0(react@19.1.0))(react@19.1.0)': + "@floating-ui/react-dom@2.1.3(react-dom@19.1.0(react@19.1.0))(react@19.1.0)": dependencies: - '@floating-ui/dom': 1.7.1 + "@floating-ui/dom": 1.7.1 react: 19.1.0 react-dom: 19.1.0(react@19.1.0) - '@floating-ui/utils@0.2.9': {} + "@floating-ui/utils@0.2.9": {} - '@humanfs/core@0.19.1': {} + "@humanfs/core@0.19.1": {} - '@humanfs/node@0.16.6': + "@humanfs/node@0.16.6": dependencies: - '@humanfs/core': 0.19.1 - '@humanwhocodes/retry': 0.3.1 + "@humanfs/core": 0.19.1 + "@humanwhocodes/retry": 0.3.1 - '@humanwhocodes/module-importer@1.0.1': {} + "@humanwhocodes/module-importer@1.0.1": {} - '@humanwhocodes/retry@0.3.1': {} + "@humanwhocodes/retry@0.3.1": {} - '@humanwhocodes/retry@0.4.3': {} + "@humanwhocodes/retry@0.4.3": {} - '@img/sharp-darwin-arm64@0.34.2': + "@img/sharp-darwin-arm64@0.34.2": optionalDependencies: - '@img/sharp-libvips-darwin-arm64': 1.1.0 + "@img/sharp-libvips-darwin-arm64": 1.1.0 optional: true - '@img/sharp-darwin-x64@0.34.2': + "@img/sharp-darwin-x64@0.34.2": optionalDependencies: - '@img/sharp-libvips-darwin-x64': 1.1.0 + "@img/sharp-libvips-darwin-x64": 1.1.0 optional: true - '@img/sharp-libvips-darwin-arm64@1.1.0': + "@img/sharp-libvips-darwin-arm64@1.1.0": optional: true - '@img/sharp-libvips-darwin-x64@1.1.0': + "@img/sharp-libvips-darwin-x64@1.1.0": optional: true - '@img/sharp-libvips-linux-arm64@1.1.0': + "@img/sharp-libvips-linux-arm64@1.1.0": optional: true - '@img/sharp-libvips-linux-arm@1.1.0': + "@img/sharp-libvips-linux-arm@1.1.0": optional: true - '@img/sharp-libvips-linux-ppc64@1.1.0': + "@img/sharp-libvips-linux-ppc64@1.1.0": optional: true - '@img/sharp-libvips-linux-s390x@1.1.0': + "@img/sharp-libvips-linux-s390x@1.1.0": optional: true - '@img/sharp-libvips-linux-x64@1.1.0': + "@img/sharp-libvips-linux-x64@1.1.0": optional: true - '@img/sharp-libvips-linuxmusl-arm64@1.1.0': + "@img/sharp-libvips-linuxmusl-arm64@1.1.0": optional: true - '@img/sharp-libvips-linuxmusl-x64@1.1.0': + "@img/sharp-libvips-linuxmusl-x64@1.1.0": optional: true - '@img/sharp-linux-arm64@0.34.2': + "@img/sharp-linux-arm64@0.34.2": optionalDependencies: - '@img/sharp-libvips-linux-arm64': 1.1.0 + "@img/sharp-libvips-linux-arm64": 1.1.0 optional: true - '@img/sharp-linux-arm@0.34.2': + "@img/sharp-linux-arm@0.34.2": optionalDependencies: - '@img/sharp-libvips-linux-arm': 1.1.0 + "@img/sharp-libvips-linux-arm": 1.1.0 optional: true - '@img/sharp-linux-s390x@0.34.2': + "@img/sharp-linux-s390x@0.34.2": optionalDependencies: - '@img/sharp-libvips-linux-s390x': 1.1.0 + "@img/sharp-libvips-linux-s390x": 1.1.0 optional: true - '@img/sharp-linux-x64@0.34.2': + "@img/sharp-linux-x64@0.34.2": optionalDependencies: - '@img/sharp-libvips-linux-x64': 1.1.0 + "@img/sharp-libvips-linux-x64": 1.1.0 optional: true - '@img/sharp-linuxmusl-arm64@0.34.2': + "@img/sharp-linuxmusl-arm64@0.34.2": optionalDependencies: - '@img/sharp-libvips-linuxmusl-arm64': 1.1.0 + "@img/sharp-libvips-linuxmusl-arm64": 1.1.0 optional: true - '@img/sharp-linuxmusl-x64@0.34.2': + "@img/sharp-linuxmusl-x64@0.34.2": optionalDependencies: - '@img/sharp-libvips-linuxmusl-x64': 1.1.0 + "@img/sharp-libvips-linuxmusl-x64": 1.1.0 optional: true - '@img/sharp-wasm32@0.34.2': + "@img/sharp-wasm32@0.34.2": dependencies: - '@emnapi/runtime': 1.4.3 + "@emnapi/runtime": 1.4.3 optional: true - '@img/sharp-win32-arm64@0.34.2': + "@img/sharp-win32-arm64@0.34.2": optional: true - '@img/sharp-win32-ia32@0.34.2': + "@img/sharp-win32-ia32@0.34.2": optional: true - '@img/sharp-win32-x64@0.34.2': + "@img/sharp-win32-x64@0.34.2": optional: true - '@isaacs/cliui@8.0.2': + "@isaacs/cliui@8.0.2": dependencies: string-width: 5.1.2 string-width-cjs: string-width@4.2.3 @@ -4826,428 +7648,429 @@ snapshots: wrap-ansi: 8.1.0 wrap-ansi-cjs: wrap-ansi@7.0.0 - '@isaacs/fs-minipass@4.0.1': + "@isaacs/fs-minipass@4.0.1": dependencies: minipass: 7.1.2 - '@istanbuljs/schema@0.1.3': {} + "@istanbuljs/schema@0.1.3": {} - '@jridgewell/gen-mapping@0.3.8': + "@jridgewell/gen-mapping@0.3.8": dependencies: - '@jridgewell/set-array': 1.2.1 - '@jridgewell/sourcemap-codec': 1.5.0 - '@jridgewell/trace-mapping': 0.3.25 + "@jridgewell/set-array": 1.2.1 + "@jridgewell/sourcemap-codec": 1.5.0 + "@jridgewell/trace-mapping": 0.3.25 - '@jridgewell/resolve-uri@3.1.2': {} + "@jridgewell/resolve-uri@3.1.2": {} - '@jridgewell/set-array@1.2.1': {} + "@jridgewell/set-array@1.2.1": {} - '@jridgewell/sourcemap-codec@1.5.0': {} + "@jridgewell/sourcemap-codec@1.5.0": {} - '@jridgewell/trace-mapping@0.3.25': + "@jridgewell/trace-mapping@0.3.25": dependencies: - '@jridgewell/resolve-uri': 3.1.2 - '@jridgewell/sourcemap-codec': 1.5.0 + "@jridgewell/resolve-uri": 3.1.2 + "@jridgewell/sourcemap-codec": 1.5.0 - '@jridgewell/trace-mapping@0.3.9': + "@jridgewell/trace-mapping@0.3.9": dependencies: - '@jridgewell/resolve-uri': 3.1.2 - '@jridgewell/sourcemap-codec': 1.5.0 + "@jridgewell/resolve-uri": 3.1.2 + "@jridgewell/sourcemap-codec": 1.5.0 - '@napi-rs/wasm-runtime@0.2.11': + "@napi-rs/wasm-runtime@0.2.11": dependencies: - '@emnapi/core': 1.4.3 - '@emnapi/runtime': 1.4.3 - '@tybys/wasm-util': 0.9.0 + "@emnapi/core": 1.4.3 + "@emnapi/runtime": 1.4.3 + "@tybys/wasm-util": 0.9.0 optional: true - '@next/env@15.3.4': {} + "@next/env@15.3.4": {} - '@next/eslint-plugin-next@15.3.4': + "@next/eslint-plugin-next@15.3.4": dependencies: fast-glob: 3.3.1 - '@next/swc-darwin-arm64@15.3.4': + "@next/swc-darwin-arm64@15.3.4": optional: true - '@next/swc-darwin-x64@15.3.4': + "@next/swc-darwin-x64@15.3.4": optional: true - '@next/swc-linux-arm64-gnu@15.3.4': + "@next/swc-linux-arm64-gnu@15.3.4": optional: true - '@next/swc-linux-arm64-musl@15.3.4': + "@next/swc-linux-arm64-musl@15.3.4": optional: true - '@next/swc-linux-x64-gnu@15.3.4': + "@next/swc-linux-x64-gnu@15.3.4": optional: true - '@next/swc-linux-x64-musl@15.3.4': + "@next/swc-linux-x64-musl@15.3.4": optional: true - '@next/swc-win32-arm64-msvc@15.3.4': + "@next/swc-win32-arm64-msvc@15.3.4": optional: true - '@next/swc-win32-x64-msvc@15.3.4': + "@next/swc-win32-x64-msvc@15.3.4": optional: true - '@nodelib/fs.scandir@2.1.5': + "@nodelib/fs.scandir@2.1.5": dependencies: - '@nodelib/fs.stat': 2.0.5 + "@nodelib/fs.stat": 2.0.5 run-parallel: 1.2.0 - '@nodelib/fs.stat@2.0.5': {} + "@nodelib/fs.stat@2.0.5": {} - '@nodelib/fs.walk@1.2.8': + "@nodelib/fs.walk@1.2.8": dependencies: - '@nodelib/fs.scandir': 2.1.5 + "@nodelib/fs.scandir": 2.1.5 fastq: 1.19.1 - '@nolyfill/is-core-module@1.0.39': {} + "@nolyfill/is-core-module@1.0.39": {} - '@panva/hkdf@1.2.1': {} + "@panva/hkdf@1.2.1": {} - '@pkgjs/parseargs@0.11.0': + "@pkgjs/parseargs@0.11.0": optional: true - '@pkgr/core@0.2.7': {} + "@pkgr/core@0.2.7": {} - '@playwright/test@1.53.1': + "@playwright/test@1.53.1": dependencies: playwright: 1.53.1 - '@prisma/adapter-pg@6.10.1(pg@8.16.3)': + "@prisma/adapter-pg@6.10.1(pg@8.16.3)": dependencies: - '@prisma/driver-adapter-utils': 6.10.1 + "@prisma/driver-adapter-utils": 6.10.1 pg: 8.16.3 postgres-array: 3.0.4 - '@prisma/client@6.10.1(prisma@6.10.1(typescript@5.8.3))(typescript@5.8.3)': + "@prisma/client@6.10.1(prisma@6.10.1(typescript@5.8.3))(typescript@5.8.3)": optionalDependencies: prisma: 6.10.1(typescript@5.8.3) typescript: 5.8.3 - '@prisma/config@6.10.1': + "@prisma/config@6.10.1": dependencies: jiti: 2.4.2 - '@prisma/debug@6.10.1': {} + "@prisma/debug@6.10.1": {} - '@prisma/driver-adapter-utils@6.10.1': + "@prisma/driver-adapter-utils@6.10.1": dependencies: - '@prisma/debug': 6.10.1 + "@prisma/debug": 6.10.1 - '@prisma/engines-version@6.10.1-1.9b628578b3b7cae625e8c927178f15a170e74a9c': {} + "@prisma/engines-version@6.10.1-1.9b628578b3b7cae625e8c927178f15a170e74a9c": + {} - '@prisma/engines@6.10.1': + "@prisma/engines@6.10.1": dependencies: - '@prisma/debug': 6.10.1 - '@prisma/engines-version': 6.10.1-1.9b628578b3b7cae625e8c927178f15a170e74a9c - '@prisma/fetch-engine': 6.10.1 - '@prisma/get-platform': 6.10.1 + "@prisma/debug": 6.10.1 + "@prisma/engines-version": 6.10.1-1.9b628578b3b7cae625e8c927178f15a170e74a9c + "@prisma/fetch-engine": 6.10.1 + "@prisma/get-platform": 6.10.1 - '@prisma/fetch-engine@6.10.1': + "@prisma/fetch-engine@6.10.1": dependencies: - '@prisma/debug': 6.10.1 - '@prisma/engines-version': 6.10.1-1.9b628578b3b7cae625e8c927178f15a170e74a9c - '@prisma/get-platform': 6.10.1 + "@prisma/debug": 6.10.1 + "@prisma/engines-version": 6.10.1-1.9b628578b3b7cae625e8c927178f15a170e74a9c + "@prisma/get-platform": 6.10.1 - '@prisma/get-platform@6.10.1': + "@prisma/get-platform@6.10.1": dependencies: - '@prisma/debug': 6.10.1 + "@prisma/debug": 6.10.1 - '@radix-ui/primitive@1.1.2': {} + "@radix-ui/primitive@1.1.2": {} - '@radix-ui/react-arrow@1.1.7(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0)': + "@radix-ui/react-arrow@1.1.7(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0)": dependencies: - '@radix-ui/react-primitive': 2.1.3(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) + "@radix-ui/react-primitive": 2.1.3(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) react: 19.1.0 react-dom: 19.1.0(react@19.1.0) optionalDependencies: - '@types/react': 19.1.8 - '@types/react-dom': 19.1.6(@types/react@19.1.8) + "@types/react": 19.1.8 + "@types/react-dom": 19.1.6(@types/react@19.1.8) - '@radix-ui/react-collection@1.1.7(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0)': + "@radix-ui/react-collection@1.1.7(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0)": dependencies: - '@radix-ui/react-compose-refs': 1.1.2(@types/react@19.1.8)(react@19.1.0) - '@radix-ui/react-context': 1.1.2(@types/react@19.1.8)(react@19.1.0) - '@radix-ui/react-primitive': 2.1.3(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) - '@radix-ui/react-slot': 1.2.3(@types/react@19.1.8)(react@19.1.0) + "@radix-ui/react-compose-refs": 1.1.2(@types/react@19.1.8)(react@19.1.0) + "@radix-ui/react-context": 1.1.2(@types/react@19.1.8)(react@19.1.0) + "@radix-ui/react-primitive": 2.1.3(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) + "@radix-ui/react-slot": 1.2.3(@types/react@19.1.8)(react@19.1.0) react: 19.1.0 react-dom: 19.1.0(react@19.1.0) optionalDependencies: - '@types/react': 19.1.8 - '@types/react-dom': 19.1.6(@types/react@19.1.8) + "@types/react": 19.1.8 + "@types/react-dom": 19.1.6(@types/react@19.1.8) - '@radix-ui/react-compose-refs@1.1.2(@types/react@19.1.8)(react@19.1.0)': + "@radix-ui/react-compose-refs@1.1.2(@types/react@19.1.8)(react@19.1.0)": dependencies: react: 19.1.0 optionalDependencies: - '@types/react': 19.1.8 + "@types/react": 19.1.8 - '@radix-ui/react-context@1.1.2(@types/react@19.1.8)(react@19.1.0)': + "@radix-ui/react-context@1.1.2(@types/react@19.1.8)(react@19.1.0)": dependencies: react: 19.1.0 optionalDependencies: - '@types/react': 19.1.8 + "@types/react": 19.1.8 - '@radix-ui/react-direction@1.1.1(@types/react@19.1.8)(react@19.1.0)': + "@radix-ui/react-direction@1.1.1(@types/react@19.1.8)(react@19.1.0)": dependencies: react: 19.1.0 optionalDependencies: - '@types/react': 19.1.8 + "@types/react": 19.1.8 - '@radix-ui/react-dismissable-layer@1.1.10(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0)': + "@radix-ui/react-dismissable-layer@1.1.10(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0)": dependencies: - '@radix-ui/primitive': 1.1.2 - '@radix-ui/react-compose-refs': 1.1.2(@types/react@19.1.8)(react@19.1.0) - '@radix-ui/react-primitive': 2.1.3(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) - '@radix-ui/react-use-callback-ref': 1.1.1(@types/react@19.1.8)(react@19.1.0) - '@radix-ui/react-use-escape-keydown': 1.1.1(@types/react@19.1.8)(react@19.1.0) + "@radix-ui/primitive": 1.1.2 + "@radix-ui/react-compose-refs": 1.1.2(@types/react@19.1.8)(react@19.1.0) + "@radix-ui/react-primitive": 2.1.3(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) + "@radix-ui/react-use-callback-ref": 1.1.1(@types/react@19.1.8)(react@19.1.0) + "@radix-ui/react-use-escape-keydown": 1.1.1(@types/react@19.1.8)(react@19.1.0) react: 19.1.0 react-dom: 19.1.0(react@19.1.0) optionalDependencies: - '@types/react': 19.1.8 - '@types/react-dom': 19.1.6(@types/react@19.1.8) + "@types/react": 19.1.8 + "@types/react-dom": 19.1.6(@types/react@19.1.8) - '@radix-ui/react-dropdown-menu@2.1.15(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0)': + "@radix-ui/react-dropdown-menu@2.1.15(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0)": dependencies: - '@radix-ui/primitive': 1.1.2 - '@radix-ui/react-compose-refs': 1.1.2(@types/react@19.1.8)(react@19.1.0) - '@radix-ui/react-context': 1.1.2(@types/react@19.1.8)(react@19.1.0) - '@radix-ui/react-id': 1.1.1(@types/react@19.1.8)(react@19.1.0) - '@radix-ui/react-menu': 2.1.15(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) - '@radix-ui/react-primitive': 2.1.3(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) - '@radix-ui/react-use-controllable-state': 1.2.2(@types/react@19.1.8)(react@19.1.0) + "@radix-ui/primitive": 1.1.2 + "@radix-ui/react-compose-refs": 1.1.2(@types/react@19.1.8)(react@19.1.0) + "@radix-ui/react-context": 1.1.2(@types/react@19.1.8)(react@19.1.0) + "@radix-ui/react-id": 1.1.1(@types/react@19.1.8)(react@19.1.0) + "@radix-ui/react-menu": 2.1.15(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) + "@radix-ui/react-primitive": 2.1.3(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) + "@radix-ui/react-use-controllable-state": 1.2.2(@types/react@19.1.8)(react@19.1.0) react: 19.1.0 react-dom: 19.1.0(react@19.1.0) optionalDependencies: - '@types/react': 19.1.8 - '@types/react-dom': 19.1.6(@types/react@19.1.8) + "@types/react": 19.1.8 + "@types/react-dom": 19.1.6(@types/react@19.1.8) - '@radix-ui/react-focus-guards@1.1.2(@types/react@19.1.8)(react@19.1.0)': + "@radix-ui/react-focus-guards@1.1.2(@types/react@19.1.8)(react@19.1.0)": dependencies: react: 19.1.0 optionalDependencies: - '@types/react': 19.1.8 + "@types/react": 19.1.8 - '@radix-ui/react-focus-scope@1.1.7(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0)': + "@radix-ui/react-focus-scope@1.1.7(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0)": dependencies: - '@radix-ui/react-compose-refs': 1.1.2(@types/react@19.1.8)(react@19.1.0) - '@radix-ui/react-primitive': 2.1.3(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) - '@radix-ui/react-use-callback-ref': 1.1.1(@types/react@19.1.8)(react@19.1.0) + "@radix-ui/react-compose-refs": 1.1.2(@types/react@19.1.8)(react@19.1.0) + "@radix-ui/react-primitive": 2.1.3(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) + "@radix-ui/react-use-callback-ref": 1.1.1(@types/react@19.1.8)(react@19.1.0) react: 19.1.0 react-dom: 19.1.0(react@19.1.0) optionalDependencies: - '@types/react': 19.1.8 - '@types/react-dom': 19.1.6(@types/react@19.1.8) + "@types/react": 19.1.8 + "@types/react-dom": 19.1.6(@types/react@19.1.8) - '@radix-ui/react-id@1.1.1(@types/react@19.1.8)(react@19.1.0)': + "@radix-ui/react-id@1.1.1(@types/react@19.1.8)(react@19.1.0)": dependencies: - '@radix-ui/react-use-layout-effect': 1.1.1(@types/react@19.1.8)(react@19.1.0) + "@radix-ui/react-use-layout-effect": 1.1.1(@types/react@19.1.8)(react@19.1.0) react: 19.1.0 optionalDependencies: - '@types/react': 19.1.8 + "@types/react": 19.1.8 - '@radix-ui/react-menu@2.1.15(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0)': + "@radix-ui/react-menu@2.1.15(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0)": dependencies: - '@radix-ui/primitive': 1.1.2 - '@radix-ui/react-collection': 1.1.7(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) - '@radix-ui/react-compose-refs': 1.1.2(@types/react@19.1.8)(react@19.1.0) - '@radix-ui/react-context': 1.1.2(@types/react@19.1.8)(react@19.1.0) - '@radix-ui/react-direction': 1.1.1(@types/react@19.1.8)(react@19.1.0) - '@radix-ui/react-dismissable-layer': 1.1.10(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) - '@radix-ui/react-focus-guards': 1.1.2(@types/react@19.1.8)(react@19.1.0) - '@radix-ui/react-focus-scope': 1.1.7(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) - '@radix-ui/react-id': 1.1.1(@types/react@19.1.8)(react@19.1.0) - '@radix-ui/react-popper': 1.2.7(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) - '@radix-ui/react-portal': 1.1.9(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) - '@radix-ui/react-presence': 1.1.4(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) - '@radix-ui/react-primitive': 2.1.3(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) - '@radix-ui/react-roving-focus': 1.1.10(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) - '@radix-ui/react-slot': 1.2.3(@types/react@19.1.8)(react@19.1.0) - '@radix-ui/react-use-callback-ref': 1.1.1(@types/react@19.1.8)(react@19.1.0) + "@radix-ui/primitive": 1.1.2 + "@radix-ui/react-collection": 1.1.7(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) + "@radix-ui/react-compose-refs": 1.1.2(@types/react@19.1.8)(react@19.1.0) + "@radix-ui/react-context": 1.1.2(@types/react@19.1.8)(react@19.1.0) + "@radix-ui/react-direction": 1.1.1(@types/react@19.1.8)(react@19.1.0) + "@radix-ui/react-dismissable-layer": 1.1.10(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) + "@radix-ui/react-focus-guards": 1.1.2(@types/react@19.1.8)(react@19.1.0) + "@radix-ui/react-focus-scope": 1.1.7(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) + "@radix-ui/react-id": 1.1.1(@types/react@19.1.8)(react@19.1.0) + "@radix-ui/react-popper": 1.2.7(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) + "@radix-ui/react-portal": 1.1.9(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) + "@radix-ui/react-presence": 1.1.4(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) + "@radix-ui/react-primitive": 2.1.3(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) + "@radix-ui/react-roving-focus": 1.1.10(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) + "@radix-ui/react-slot": 1.2.3(@types/react@19.1.8)(react@19.1.0) + "@radix-ui/react-use-callback-ref": 1.1.1(@types/react@19.1.8)(react@19.1.0) aria-hidden: 1.2.6 react: 19.1.0 react-dom: 19.1.0(react@19.1.0) react-remove-scroll: 2.7.1(@types/react@19.1.8)(react@19.1.0) optionalDependencies: - '@types/react': 19.1.8 - '@types/react-dom': 19.1.6(@types/react@19.1.8) + "@types/react": 19.1.8 + "@types/react-dom": 19.1.6(@types/react@19.1.8) - '@radix-ui/react-popper@1.2.7(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0)': + "@radix-ui/react-popper@1.2.7(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0)": dependencies: - '@floating-ui/react-dom': 2.1.3(react-dom@19.1.0(react@19.1.0))(react@19.1.0) - '@radix-ui/react-arrow': 1.1.7(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) - '@radix-ui/react-compose-refs': 1.1.2(@types/react@19.1.8)(react@19.1.0) - '@radix-ui/react-context': 1.1.2(@types/react@19.1.8)(react@19.1.0) - '@radix-ui/react-primitive': 2.1.3(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) - '@radix-ui/react-use-callback-ref': 1.1.1(@types/react@19.1.8)(react@19.1.0) - '@radix-ui/react-use-layout-effect': 1.1.1(@types/react@19.1.8)(react@19.1.0) - '@radix-ui/react-use-rect': 1.1.1(@types/react@19.1.8)(react@19.1.0) - '@radix-ui/react-use-size': 1.1.1(@types/react@19.1.8)(react@19.1.0) - '@radix-ui/rect': 1.1.1 + "@floating-ui/react-dom": 2.1.3(react-dom@19.1.0(react@19.1.0))(react@19.1.0) + "@radix-ui/react-arrow": 1.1.7(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) + "@radix-ui/react-compose-refs": 1.1.2(@types/react@19.1.8)(react@19.1.0) + "@radix-ui/react-context": 1.1.2(@types/react@19.1.8)(react@19.1.0) + "@radix-ui/react-primitive": 2.1.3(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) + "@radix-ui/react-use-callback-ref": 1.1.1(@types/react@19.1.8)(react@19.1.0) + "@radix-ui/react-use-layout-effect": 1.1.1(@types/react@19.1.8)(react@19.1.0) + "@radix-ui/react-use-rect": 1.1.1(@types/react@19.1.8)(react@19.1.0) + "@radix-ui/react-use-size": 1.1.1(@types/react@19.1.8)(react@19.1.0) + "@radix-ui/rect": 1.1.1 react: 19.1.0 react-dom: 19.1.0(react@19.1.0) optionalDependencies: - '@types/react': 19.1.8 - '@types/react-dom': 19.1.6(@types/react@19.1.8) + "@types/react": 19.1.8 + "@types/react-dom": 19.1.6(@types/react@19.1.8) - '@radix-ui/react-portal@1.1.9(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0)': + "@radix-ui/react-portal@1.1.9(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0)": dependencies: - '@radix-ui/react-primitive': 2.1.3(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) - '@radix-ui/react-use-layout-effect': 1.1.1(@types/react@19.1.8)(react@19.1.0) + "@radix-ui/react-primitive": 2.1.3(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) + "@radix-ui/react-use-layout-effect": 1.1.1(@types/react@19.1.8)(react@19.1.0) react: 19.1.0 react-dom: 19.1.0(react@19.1.0) optionalDependencies: - '@types/react': 19.1.8 - '@types/react-dom': 19.1.6(@types/react@19.1.8) + "@types/react": 19.1.8 + "@types/react-dom": 19.1.6(@types/react@19.1.8) - '@radix-ui/react-presence@1.1.4(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0)': + "@radix-ui/react-presence@1.1.4(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0)": dependencies: - '@radix-ui/react-compose-refs': 1.1.2(@types/react@19.1.8)(react@19.1.0) - '@radix-ui/react-use-layout-effect': 1.1.1(@types/react@19.1.8)(react@19.1.0) + "@radix-ui/react-compose-refs": 1.1.2(@types/react@19.1.8)(react@19.1.0) + "@radix-ui/react-use-layout-effect": 1.1.1(@types/react@19.1.8)(react@19.1.0) react: 19.1.0 react-dom: 19.1.0(react@19.1.0) optionalDependencies: - '@types/react': 19.1.8 - '@types/react-dom': 19.1.6(@types/react@19.1.8) + "@types/react": 19.1.8 + "@types/react-dom": 19.1.6(@types/react@19.1.8) - '@radix-ui/react-primitive@2.1.3(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0)': + "@radix-ui/react-primitive@2.1.3(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0)": dependencies: - '@radix-ui/react-slot': 1.2.3(@types/react@19.1.8)(react@19.1.0) + "@radix-ui/react-slot": 1.2.3(@types/react@19.1.8)(react@19.1.0) react: 19.1.0 react-dom: 19.1.0(react@19.1.0) optionalDependencies: - '@types/react': 19.1.8 - '@types/react-dom': 19.1.6(@types/react@19.1.8) + "@types/react": 19.1.8 + "@types/react-dom": 19.1.6(@types/react@19.1.8) - '@radix-ui/react-roving-focus@1.1.10(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0)': + "@radix-ui/react-roving-focus@1.1.10(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0)": dependencies: - '@radix-ui/primitive': 1.1.2 - '@radix-ui/react-collection': 1.1.7(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) - '@radix-ui/react-compose-refs': 1.1.2(@types/react@19.1.8)(react@19.1.0) - '@radix-ui/react-context': 1.1.2(@types/react@19.1.8)(react@19.1.0) - '@radix-ui/react-direction': 1.1.1(@types/react@19.1.8)(react@19.1.0) - '@radix-ui/react-id': 1.1.1(@types/react@19.1.8)(react@19.1.0) - '@radix-ui/react-primitive': 2.1.3(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) - '@radix-ui/react-use-callback-ref': 1.1.1(@types/react@19.1.8)(react@19.1.0) - '@radix-ui/react-use-controllable-state': 1.2.2(@types/react@19.1.8)(react@19.1.0) + "@radix-ui/primitive": 1.1.2 + "@radix-ui/react-collection": 1.1.7(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) + "@radix-ui/react-compose-refs": 1.1.2(@types/react@19.1.8)(react@19.1.0) + "@radix-ui/react-context": 1.1.2(@types/react@19.1.8)(react@19.1.0) + "@radix-ui/react-direction": 1.1.1(@types/react@19.1.8)(react@19.1.0) + "@radix-ui/react-id": 1.1.1(@types/react@19.1.8)(react@19.1.0) + "@radix-ui/react-primitive": 2.1.3(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) + "@radix-ui/react-use-callback-ref": 1.1.1(@types/react@19.1.8)(react@19.1.0) + "@radix-ui/react-use-controllable-state": 1.2.2(@types/react@19.1.8)(react@19.1.0) react: 19.1.0 react-dom: 19.1.0(react@19.1.0) optionalDependencies: - '@types/react': 19.1.8 - '@types/react-dom': 19.1.6(@types/react@19.1.8) + "@types/react": 19.1.8 + "@types/react-dom": 19.1.6(@types/react@19.1.8) - '@radix-ui/react-separator@1.1.7(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0)': + "@radix-ui/react-separator@1.1.7(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0)": dependencies: - '@radix-ui/react-primitive': 2.1.3(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) + "@radix-ui/react-primitive": 2.1.3(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) react: 19.1.0 react-dom: 19.1.0(react@19.1.0) optionalDependencies: - '@types/react': 19.1.8 - '@types/react-dom': 19.1.6(@types/react@19.1.8) + "@types/react": 19.1.8 + "@types/react-dom": 19.1.6(@types/react@19.1.8) - '@radix-ui/react-slot@1.2.3(@types/react@19.1.8)(react@19.1.0)': + "@radix-ui/react-slot@1.2.3(@types/react@19.1.8)(react@19.1.0)": dependencies: - '@radix-ui/react-compose-refs': 1.1.2(@types/react@19.1.8)(react@19.1.0) + "@radix-ui/react-compose-refs": 1.1.2(@types/react@19.1.8)(react@19.1.0) react: 19.1.0 optionalDependencies: - '@types/react': 19.1.8 + "@types/react": 19.1.8 - '@radix-ui/react-tooltip@1.2.7(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0)': + "@radix-ui/react-tooltip@1.2.7(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0)": dependencies: - '@radix-ui/primitive': 1.1.2 - '@radix-ui/react-compose-refs': 1.1.2(@types/react@19.1.8)(react@19.1.0) - '@radix-ui/react-context': 1.1.2(@types/react@19.1.8)(react@19.1.0) - '@radix-ui/react-dismissable-layer': 1.1.10(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) - '@radix-ui/react-id': 1.1.1(@types/react@19.1.8)(react@19.1.0) - '@radix-ui/react-popper': 1.2.7(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) - '@radix-ui/react-portal': 1.1.9(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) - '@radix-ui/react-presence': 1.1.4(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) - '@radix-ui/react-primitive': 2.1.3(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) - '@radix-ui/react-slot': 1.2.3(@types/react@19.1.8)(react@19.1.0) - '@radix-ui/react-use-controllable-state': 1.2.2(@types/react@19.1.8)(react@19.1.0) - '@radix-ui/react-visually-hidden': 1.2.3(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) + "@radix-ui/primitive": 1.1.2 + "@radix-ui/react-compose-refs": 1.1.2(@types/react@19.1.8)(react@19.1.0) + "@radix-ui/react-context": 1.1.2(@types/react@19.1.8)(react@19.1.0) + "@radix-ui/react-dismissable-layer": 1.1.10(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) + "@radix-ui/react-id": 1.1.1(@types/react@19.1.8)(react@19.1.0) + "@radix-ui/react-popper": 1.2.7(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) + "@radix-ui/react-portal": 1.1.9(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) + "@radix-ui/react-presence": 1.1.4(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) + "@radix-ui/react-primitive": 2.1.3(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) + "@radix-ui/react-slot": 1.2.3(@types/react@19.1.8)(react@19.1.0) + "@radix-ui/react-use-controllable-state": 1.2.2(@types/react@19.1.8)(react@19.1.0) + "@radix-ui/react-visually-hidden": 1.2.3(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) react: 19.1.0 react-dom: 19.1.0(react@19.1.0) optionalDependencies: - '@types/react': 19.1.8 - '@types/react-dom': 19.1.6(@types/react@19.1.8) + "@types/react": 19.1.8 + "@types/react-dom": 19.1.6(@types/react@19.1.8) - '@radix-ui/react-use-callback-ref@1.1.1(@types/react@19.1.8)(react@19.1.0)': + "@radix-ui/react-use-callback-ref@1.1.1(@types/react@19.1.8)(react@19.1.0)": dependencies: react: 19.1.0 optionalDependencies: - '@types/react': 19.1.8 + "@types/react": 19.1.8 - '@radix-ui/react-use-controllable-state@1.2.2(@types/react@19.1.8)(react@19.1.0)': + "@radix-ui/react-use-controllable-state@1.2.2(@types/react@19.1.8)(react@19.1.0)": dependencies: - '@radix-ui/react-use-effect-event': 0.0.2(@types/react@19.1.8)(react@19.1.0) - '@radix-ui/react-use-layout-effect': 1.1.1(@types/react@19.1.8)(react@19.1.0) + "@radix-ui/react-use-effect-event": 0.0.2(@types/react@19.1.8)(react@19.1.0) + "@radix-ui/react-use-layout-effect": 1.1.1(@types/react@19.1.8)(react@19.1.0) react: 19.1.0 optionalDependencies: - '@types/react': 19.1.8 + "@types/react": 19.1.8 - '@radix-ui/react-use-effect-event@0.0.2(@types/react@19.1.8)(react@19.1.0)': + "@radix-ui/react-use-effect-event@0.0.2(@types/react@19.1.8)(react@19.1.0)": dependencies: - '@radix-ui/react-use-layout-effect': 1.1.1(@types/react@19.1.8)(react@19.1.0) + "@radix-ui/react-use-layout-effect": 1.1.1(@types/react@19.1.8)(react@19.1.0) react: 19.1.0 optionalDependencies: - '@types/react': 19.1.8 + "@types/react": 19.1.8 - '@radix-ui/react-use-escape-keydown@1.1.1(@types/react@19.1.8)(react@19.1.0)': + "@radix-ui/react-use-escape-keydown@1.1.1(@types/react@19.1.8)(react@19.1.0)": dependencies: - '@radix-ui/react-use-callback-ref': 1.1.1(@types/react@19.1.8)(react@19.1.0) + "@radix-ui/react-use-callback-ref": 1.1.1(@types/react@19.1.8)(react@19.1.0) react: 19.1.0 optionalDependencies: - '@types/react': 19.1.8 + "@types/react": 19.1.8 - '@radix-ui/react-use-layout-effect@1.1.1(@types/react@19.1.8)(react@19.1.0)': + "@radix-ui/react-use-layout-effect@1.1.1(@types/react@19.1.8)(react@19.1.0)": dependencies: react: 19.1.0 optionalDependencies: - '@types/react': 19.1.8 + "@types/react": 19.1.8 - '@radix-ui/react-use-rect@1.1.1(@types/react@19.1.8)(react@19.1.0)': + "@radix-ui/react-use-rect@1.1.1(@types/react@19.1.8)(react@19.1.0)": dependencies: - '@radix-ui/rect': 1.1.1 + "@radix-ui/rect": 1.1.1 react: 19.1.0 optionalDependencies: - '@types/react': 19.1.8 + "@types/react": 19.1.8 - '@radix-ui/react-use-size@1.1.1(@types/react@19.1.8)(react@19.1.0)': + "@radix-ui/react-use-size@1.1.1(@types/react@19.1.8)(react@19.1.0)": dependencies: - '@radix-ui/react-use-layout-effect': 1.1.1(@types/react@19.1.8)(react@19.1.0) + "@radix-ui/react-use-layout-effect": 1.1.1(@types/react@19.1.8)(react@19.1.0) react: 19.1.0 optionalDependencies: - '@types/react': 19.1.8 + "@types/react": 19.1.8 - '@radix-ui/react-visually-hidden@1.2.3(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0)': + "@radix-ui/react-visually-hidden@1.2.3(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0)": dependencies: - '@radix-ui/react-primitive': 2.1.3(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) + "@radix-ui/react-primitive": 2.1.3(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) react: 19.1.0 react-dom: 19.1.0(react@19.1.0) optionalDependencies: - '@types/react': 19.1.8 - '@types/react-dom': 19.1.6(@types/react@19.1.8) + "@types/react": 19.1.8 + "@types/react-dom": 19.1.6(@types/react@19.1.8) - '@radix-ui/rect@1.1.1': {} + "@radix-ui/rect@1.1.1": {} - '@rapideditor/country-coder@5.4.0': + "@rapideditor/country-coder@5.4.0": dependencies: which-polygon: 2.2.1 - '@react-leaflet/core@3.0.0(leaflet@1.9.4)(react-dom@19.1.0(react@19.1.0))(react@19.1.0)': + "@react-leaflet/core@3.0.0(leaflet@1.9.4)(react-dom@19.1.0(react@19.1.0))(react@19.1.0)": dependencies: leaflet: 1.9.4 react: 19.1.0 react-dom: 19.1.0(react@19.1.0) - '@reduxjs/toolkit@2.8.2(react-redux@9.2.0(@types/react@19.1.8)(react@19.1.0)(redux@5.0.1))(react@19.1.0)': + "@reduxjs/toolkit@2.8.2(react-redux@9.2.0(@types/react@19.1.8)(react@19.1.0)(redux@5.0.1))(react@19.1.0)": dependencies: - '@standard-schema/spec': 1.0.0 - '@standard-schema/utils': 0.3.0 + "@standard-schema/spec": 1.0.0 + "@standard-schema/utils": 0.3.0 immer: 10.1.1 redux: 5.0.1 redux-thunk: 3.1.0(redux@5.0.1) @@ -5256,87 +8079,87 @@ snapshots: react: 19.1.0 react-redux: 9.2.0(@types/react@19.1.8)(react@19.1.0)(redux@5.0.1) - '@rolldown/pluginutils@1.0.0-beta.19': {} + "@rolldown/pluginutils@1.0.0-beta.19": {} - '@rollup/rollup-android-arm-eabi@4.44.1': + "@rollup/rollup-android-arm-eabi@4.44.1": optional: true - '@rollup/rollup-android-arm64@4.44.1': + "@rollup/rollup-android-arm64@4.44.1": optional: true - '@rollup/rollup-darwin-arm64@4.44.1': + "@rollup/rollup-darwin-arm64@4.44.1": optional: true - '@rollup/rollup-darwin-x64@4.44.1': + "@rollup/rollup-darwin-x64@4.44.1": optional: true - '@rollup/rollup-freebsd-arm64@4.44.1': + "@rollup/rollup-freebsd-arm64@4.44.1": optional: true - '@rollup/rollup-freebsd-x64@4.44.1': + "@rollup/rollup-freebsd-x64@4.44.1": optional: true - '@rollup/rollup-linux-arm-gnueabihf@4.44.1': + "@rollup/rollup-linux-arm-gnueabihf@4.44.1": optional: true - '@rollup/rollup-linux-arm-musleabihf@4.44.1': + "@rollup/rollup-linux-arm-musleabihf@4.44.1": optional: true - '@rollup/rollup-linux-arm64-gnu@4.44.1': + "@rollup/rollup-linux-arm64-gnu@4.44.1": optional: true - '@rollup/rollup-linux-arm64-musl@4.44.1': + "@rollup/rollup-linux-arm64-musl@4.44.1": optional: true - '@rollup/rollup-linux-loongarch64-gnu@4.44.1': + "@rollup/rollup-linux-loongarch64-gnu@4.44.1": optional: true - '@rollup/rollup-linux-powerpc64le-gnu@4.44.1': + "@rollup/rollup-linux-powerpc64le-gnu@4.44.1": optional: true - '@rollup/rollup-linux-riscv64-gnu@4.44.1': + "@rollup/rollup-linux-riscv64-gnu@4.44.1": optional: true - '@rollup/rollup-linux-riscv64-musl@4.44.1': + "@rollup/rollup-linux-riscv64-musl@4.44.1": optional: true - '@rollup/rollup-linux-s390x-gnu@4.44.1': + "@rollup/rollup-linux-s390x-gnu@4.44.1": optional: true - '@rollup/rollup-linux-x64-gnu@4.44.1': + "@rollup/rollup-linux-x64-gnu@4.44.1": optional: true - '@rollup/rollup-linux-x64-musl@4.44.1': + "@rollup/rollup-linux-x64-musl@4.44.1": optional: true - '@rollup/rollup-win32-arm64-msvc@4.44.1': + "@rollup/rollup-win32-arm64-msvc@4.44.1": optional: true - '@rollup/rollup-win32-ia32-msvc@4.44.1': + "@rollup/rollup-win32-ia32-msvc@4.44.1": optional: true - '@rollup/rollup-win32-x64-msvc@4.44.1': + "@rollup/rollup-win32-x64-msvc@4.44.1": optional: true - '@rtsao/scc@1.1.0': {} + "@rtsao/scc@1.1.0": {} - '@rushstack/eslint-patch@1.12.0': {} + "@rushstack/eslint-patch@1.12.0": {} - '@sindresorhus/merge-streams@2.3.0': {} + "@sindresorhus/merge-streams@2.3.0": {} - '@standard-schema/spec@1.0.0': {} + "@standard-schema/spec@1.0.0": {} - '@standard-schema/utils@0.3.0': {} + "@standard-schema/utils@0.3.0": {} - '@swc/counter@0.1.3': {} + "@swc/counter@0.1.3": {} - '@swc/helpers@0.5.15': + "@swc/helpers@0.5.15": dependencies: tslib: 2.8.1 - '@tailwindcss/node@4.1.11': + "@tailwindcss/node@4.1.11": dependencies: - '@ampproject/remapping': 2.3.0 + "@ampproject/remapping": 2.3.0 enhanced-resolve: 5.18.2 jiti: 2.4.2 lightningcss: 1.30.1 @@ -5344,323 +8167,319 @@ snapshots: source-map-js: 1.2.1 tailwindcss: 4.1.11 - '@tailwindcss/oxide-android-arm64@4.1.11': + "@tailwindcss/oxide-android-arm64@4.1.11": optional: true - '@tailwindcss/oxide-darwin-arm64@4.1.11': + "@tailwindcss/oxide-darwin-arm64@4.1.11": optional: true - '@tailwindcss/oxide-darwin-x64@4.1.11': + "@tailwindcss/oxide-darwin-x64@4.1.11": optional: true - '@tailwindcss/oxide-freebsd-x64@4.1.11': + "@tailwindcss/oxide-freebsd-x64@4.1.11": optional: true - '@tailwindcss/oxide-linux-arm-gnueabihf@4.1.11': + "@tailwindcss/oxide-linux-arm-gnueabihf@4.1.11": optional: true - '@tailwindcss/oxide-linux-arm64-gnu@4.1.11': + "@tailwindcss/oxide-linux-arm64-gnu@4.1.11": optional: true - '@tailwindcss/oxide-linux-arm64-musl@4.1.11': + "@tailwindcss/oxide-linux-arm64-musl@4.1.11": optional: true - '@tailwindcss/oxide-linux-x64-gnu@4.1.11': + "@tailwindcss/oxide-linux-x64-gnu@4.1.11": optional: true - '@tailwindcss/oxide-linux-x64-musl@4.1.11': + "@tailwindcss/oxide-linux-x64-musl@4.1.11": optional: true - '@tailwindcss/oxide-wasm32-wasi@4.1.11': + "@tailwindcss/oxide-wasm32-wasi@4.1.11": optional: true - '@tailwindcss/oxide-win32-arm64-msvc@4.1.11': + "@tailwindcss/oxide-win32-arm64-msvc@4.1.11": optional: true - '@tailwindcss/oxide-win32-x64-msvc@4.1.11': + "@tailwindcss/oxide-win32-x64-msvc@4.1.11": optional: true - '@tailwindcss/oxide@4.1.11': + "@tailwindcss/oxide@4.1.11": dependencies: detect-libc: 2.0.4 tar: 7.4.3 optionalDependencies: - '@tailwindcss/oxide-android-arm64': 4.1.11 - '@tailwindcss/oxide-darwin-arm64': 4.1.11 - '@tailwindcss/oxide-darwin-x64': 4.1.11 - '@tailwindcss/oxide-freebsd-x64': 4.1.11 - '@tailwindcss/oxide-linux-arm-gnueabihf': 4.1.11 - '@tailwindcss/oxide-linux-arm64-gnu': 4.1.11 - '@tailwindcss/oxide-linux-arm64-musl': 4.1.11 - '@tailwindcss/oxide-linux-x64-gnu': 4.1.11 - '@tailwindcss/oxide-linux-x64-musl': 4.1.11 - '@tailwindcss/oxide-wasm32-wasi': 4.1.11 - '@tailwindcss/oxide-win32-arm64-msvc': 4.1.11 - '@tailwindcss/oxide-win32-x64-msvc': 4.1.11 + "@tailwindcss/oxide-android-arm64": 4.1.11 + "@tailwindcss/oxide-darwin-arm64": 4.1.11 + "@tailwindcss/oxide-darwin-x64": 4.1.11 + "@tailwindcss/oxide-freebsd-x64": 4.1.11 + "@tailwindcss/oxide-linux-arm-gnueabihf": 4.1.11 + "@tailwindcss/oxide-linux-arm64-gnu": 4.1.11 + "@tailwindcss/oxide-linux-arm64-musl": 4.1.11 + "@tailwindcss/oxide-linux-x64-gnu": 4.1.11 + "@tailwindcss/oxide-linux-x64-musl": 4.1.11 + "@tailwindcss/oxide-wasm32-wasi": 4.1.11 + "@tailwindcss/oxide-win32-arm64-msvc": 4.1.11 + "@tailwindcss/oxide-win32-x64-msvc": 4.1.11 - '@tailwindcss/postcss@4.1.11': + "@tailwindcss/postcss@4.1.11": dependencies: - '@alloc/quick-lru': 5.2.0 - '@tailwindcss/node': 4.1.11 - '@tailwindcss/oxide': 4.1.11 + "@alloc/quick-lru": 5.2.0 + "@tailwindcss/node": 4.1.11 + "@tailwindcss/oxide": 4.1.11 postcss: 8.5.6 tailwindcss: 4.1.11 - '@testing-library/dom@10.4.0': + "@testing-library/dom@10.4.0": dependencies: - '@babel/code-frame': 7.27.1 - '@babel/runtime': 7.27.6 - '@types/aria-query': 5.0.4 + "@babel/code-frame": 7.27.1 + "@babel/runtime": 7.27.6 + "@types/aria-query": 5.0.4 aria-query: 5.3.0 chalk: 4.1.2 dom-accessibility-api: 0.5.16 lz-string: 1.5.0 pretty-format: 27.5.1 - '@testing-library/react@16.3.0(@testing-library/dom@10.4.0)(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0)': + "@testing-library/react@16.3.0(@testing-library/dom@10.4.0)(@types/react-dom@19.1.6(@types/react@19.1.8))(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react@19.1.0)": dependencies: - '@babel/runtime': 7.27.6 - '@testing-library/dom': 10.4.0 + "@babel/runtime": 7.27.6 + "@testing-library/dom": 10.4.0 react: 19.1.0 react-dom: 19.1.0(react@19.1.0) optionalDependencies: - '@types/react': 19.1.8 - '@types/react-dom': 19.1.6(@types/react@19.1.8) + "@types/react": 19.1.8 + "@types/react-dom": 19.1.6(@types/react@19.1.8) - '@tsconfig/node10@1.0.11': {} + "@tsconfig/node10@1.0.11": {} - '@tsconfig/node12@1.0.11': {} + "@tsconfig/node12@1.0.11": {} - '@tsconfig/node14@1.0.3': {} + "@tsconfig/node14@1.0.3": {} - '@tsconfig/node16@1.0.4': {} + "@tsconfig/node16@1.0.4": {} - '@tybys/wasm-util@0.9.0': + "@tybys/wasm-util@0.9.0": dependencies: tslib: 2.8.1 optional: true - '@types/aria-query@5.0.4': {} + "@types/aria-query@5.0.4": {} - '@types/babel__core@7.20.5': + "@types/babel__core@7.20.5": dependencies: - '@babel/parser': 7.27.7 - '@babel/types': 7.27.7 - '@types/babel__generator': 7.27.0 - '@types/babel__template': 7.4.4 - '@types/babel__traverse': 7.20.7 + "@babel/parser": 7.27.7 + "@babel/types": 7.27.7 + "@types/babel__generator": 7.27.0 + "@types/babel__template": 7.4.4 + "@types/babel__traverse": 7.20.7 - '@types/babel__generator@7.27.0': + "@types/babel__generator@7.27.0": dependencies: - '@babel/types': 7.27.7 + "@babel/types": 7.27.7 - '@types/babel__template@7.4.4': + "@types/babel__template@7.4.4": dependencies: - '@babel/parser': 7.27.7 - '@babel/types': 7.27.7 + "@babel/parser": 7.27.7 + "@babel/types": 7.27.7 - '@types/babel__traverse@7.20.7': + "@types/babel__traverse@7.20.7": dependencies: - '@babel/types': 7.27.7 + "@babel/types": 7.27.7 - '@types/bcryptjs@3.0.0': + "@types/chai@5.2.2": dependencies: - bcryptjs: 3.0.2 + "@types/deep-eql": 4.0.2 - '@types/chai@5.2.2': + "@types/d3-array@3.2.1": {} + + "@types/d3-axis@3.0.6": dependencies: - '@types/deep-eql': 4.0.2 + "@types/d3-selection": 3.0.11 - '@types/d3-array@3.2.1': {} - - '@types/d3-axis@3.0.6': + "@types/d3-brush@3.0.6": dependencies: - '@types/d3-selection': 3.0.11 + "@types/d3-selection": 3.0.11 - '@types/d3-brush@3.0.6': + "@types/d3-chord@3.0.6": {} + + "@types/d3-cloud@1.2.9": dependencies: - '@types/d3-selection': 3.0.11 + "@types/d3": 3.5.53 - '@types/d3-chord@3.0.6': {} + "@types/d3-color@3.1.3": {} - '@types/d3-cloud@1.2.9': + "@types/d3-contour@3.0.6": dependencies: - '@types/d3': 3.5.53 + "@types/d3-array": 3.2.1 + "@types/geojson": 7946.0.16 - '@types/d3-color@3.1.3': {} + "@types/d3-delaunay@6.0.4": {} - '@types/d3-contour@3.0.6': + "@types/d3-dispatch@3.0.6": {} + + "@types/d3-drag@3.0.7": dependencies: - '@types/d3-array': 3.2.1 - '@types/geojson': 7946.0.16 + "@types/d3-selection": 3.0.11 - '@types/d3-delaunay@6.0.4': {} + "@types/d3-dsv@3.0.7": {} - '@types/d3-dispatch@3.0.6': {} + "@types/d3-ease@3.0.2": {} - '@types/d3-drag@3.0.7': + "@types/d3-fetch@3.0.7": dependencies: - '@types/d3-selection': 3.0.11 + "@types/d3-dsv": 3.0.7 - '@types/d3-dsv@3.0.7': {} + "@types/d3-force@3.0.10": {} - '@types/d3-ease@3.0.2': {} + "@types/d3-format@3.0.4": {} - '@types/d3-fetch@3.0.7': + "@types/d3-geo@3.1.0": dependencies: - '@types/d3-dsv': 3.0.7 + "@types/geojson": 7946.0.16 - '@types/d3-force@3.0.10': {} + "@types/d3-hierarchy@3.1.7": {} - '@types/d3-format@3.0.4': {} - - '@types/d3-geo@3.1.0': + "@types/d3-interpolate@3.0.4": dependencies: - '@types/geojson': 7946.0.16 + "@types/d3-color": 3.1.3 - '@types/d3-hierarchy@3.1.7': {} + "@types/d3-path@3.1.1": {} - '@types/d3-interpolate@3.0.4': + "@types/d3-polygon@3.0.2": {} + + "@types/d3-quadtree@3.0.6": {} + + "@types/d3-random@3.0.3": {} + + "@types/d3-scale-chromatic@3.1.0": {} + + "@types/d3-scale@4.0.9": dependencies: - '@types/d3-color': 3.1.3 + "@types/d3-time": 3.0.4 - '@types/d3-path@3.1.1': {} + "@types/d3-selection@3.0.11": {} - '@types/d3-polygon@3.0.2': {} - - '@types/d3-quadtree@3.0.6': {} - - '@types/d3-random@3.0.3': {} - - '@types/d3-scale-chromatic@3.1.0': {} - - '@types/d3-scale@4.0.9': + "@types/d3-shape@3.1.7": dependencies: - '@types/d3-time': 3.0.4 + "@types/d3-path": 3.1.1 - '@types/d3-selection@3.0.11': {} + "@types/d3-time-format@4.0.3": {} - '@types/d3-shape@3.1.7': + "@types/d3-time@3.0.4": {} + + "@types/d3-timer@3.0.2": {} + + "@types/d3-transition@3.0.9": dependencies: - '@types/d3-path': 3.1.1 + "@types/d3-selection": 3.0.11 - '@types/d3-time-format@4.0.3': {} - - '@types/d3-time@3.0.4': {} - - '@types/d3-timer@3.0.2': {} - - '@types/d3-transition@3.0.9': + "@types/d3-zoom@3.0.8": dependencies: - '@types/d3-selection': 3.0.11 + "@types/d3-interpolate": 3.0.4 + "@types/d3-selection": 3.0.11 - '@types/d3-zoom@3.0.8': + "@types/d3@3.5.53": {} + + "@types/d3@7.4.3": dependencies: - '@types/d3-interpolate': 3.0.4 - '@types/d3-selection': 3.0.11 + "@types/d3-array": 3.2.1 + "@types/d3-axis": 3.0.6 + "@types/d3-brush": 3.0.6 + "@types/d3-chord": 3.0.6 + "@types/d3-color": 3.1.3 + "@types/d3-contour": 3.0.6 + "@types/d3-delaunay": 6.0.4 + "@types/d3-dispatch": 3.0.6 + "@types/d3-drag": 3.0.7 + "@types/d3-dsv": 3.0.7 + "@types/d3-ease": 3.0.2 + "@types/d3-fetch": 3.0.7 + "@types/d3-force": 3.0.10 + "@types/d3-format": 3.0.4 + "@types/d3-geo": 3.1.0 + "@types/d3-hierarchy": 3.1.7 + "@types/d3-interpolate": 3.0.4 + "@types/d3-path": 3.1.1 + "@types/d3-polygon": 3.0.2 + "@types/d3-quadtree": 3.0.6 + "@types/d3-random": 3.0.3 + "@types/d3-scale": 4.0.9 + "@types/d3-scale-chromatic": 3.1.0 + "@types/d3-selection": 3.0.11 + "@types/d3-shape": 3.1.7 + "@types/d3-time": 3.0.4 + "@types/d3-time-format": 4.0.3 + "@types/d3-timer": 3.0.2 + "@types/d3-transition": 3.0.9 + "@types/d3-zoom": 3.0.8 - '@types/d3@3.5.53': {} - - '@types/d3@7.4.3': + "@types/debug@4.1.12": dependencies: - '@types/d3-array': 3.2.1 - '@types/d3-axis': 3.0.6 - '@types/d3-brush': 3.0.6 - '@types/d3-chord': 3.0.6 - '@types/d3-color': 3.1.3 - '@types/d3-contour': 3.0.6 - '@types/d3-delaunay': 6.0.4 - '@types/d3-dispatch': 3.0.6 - '@types/d3-drag': 3.0.7 - '@types/d3-dsv': 3.0.7 - '@types/d3-ease': 3.0.2 - '@types/d3-fetch': 3.0.7 - '@types/d3-force': 3.0.10 - '@types/d3-format': 3.0.4 - '@types/d3-geo': 3.1.0 - '@types/d3-hierarchy': 3.1.7 - '@types/d3-interpolate': 3.0.4 - '@types/d3-path': 3.1.1 - '@types/d3-polygon': 3.0.2 - '@types/d3-quadtree': 3.0.6 - '@types/d3-random': 3.0.3 - '@types/d3-scale': 4.0.9 - '@types/d3-scale-chromatic': 3.1.0 - '@types/d3-selection': 3.0.11 - '@types/d3-shape': 3.1.7 - '@types/d3-time': 3.0.4 - '@types/d3-time-format': 4.0.3 - '@types/d3-timer': 3.0.2 - '@types/d3-transition': 3.0.9 - '@types/d3-zoom': 3.0.8 + "@types/ms": 2.1.0 - '@types/debug@4.1.12': + "@types/deep-eql@4.0.2": {} + + "@types/estree-jsx@1.0.5": dependencies: - '@types/ms': 2.1.0 + "@types/estree": 1.0.8 - '@types/deep-eql@4.0.2': {} + "@types/estree@1.0.8": {} - '@types/estree-jsx@1.0.5': + "@types/geojson@7946.0.16": {} + + "@types/hast@3.0.4": dependencies: - '@types/estree': 1.0.8 + "@types/unist": 3.0.3 - '@types/estree@1.0.8': {} + "@types/json-schema@7.0.15": {} - '@types/geojson@7946.0.16': {} + "@types/json5@0.0.29": {} - '@types/hast@3.0.4': + "@types/katex@0.16.7": {} + + "@types/leaflet@1.9.19": dependencies: - '@types/unist': 3.0.3 + "@types/geojson": 7946.0.16 - '@types/json-schema@7.0.15': {} - - '@types/json5@0.0.29': {} - - '@types/katex@0.16.7': {} - - '@types/leaflet@1.9.19': + "@types/mdast@4.0.4": dependencies: - '@types/geojson': 7946.0.16 + "@types/unist": 3.0.3 - '@types/mdast@4.0.4': + "@types/ms@2.1.0": {} + + "@types/node-cron@3.0.11": {} + + "@types/node-fetch@2.6.12": dependencies: - '@types/unist': 3.0.3 - - '@types/ms@2.1.0': {} - - '@types/node-cron@3.0.11': {} - - '@types/node-fetch@2.6.12': - dependencies: - '@types/node': 24.0.6 + "@types/node": 24.0.6 form-data: 4.0.3 - '@types/node@24.0.6': + "@types/node@24.0.6": dependencies: undici-types: 7.8.0 - '@types/react-dom@19.1.6(@types/react@19.1.8)': + "@types/react-dom@19.1.6(@types/react@19.1.8)": dependencies: - '@types/react': 19.1.8 + "@types/react": 19.1.8 - '@types/react@19.1.8': + "@types/react@19.1.8": dependencies: csstype: 3.1.3 - '@types/unist@2.0.11': {} + "@types/unist@2.0.11": {} - '@types/unist@3.0.3': {} + "@types/unist@3.0.3": {} - '@types/use-sync-external-store@0.0.6': {} + "@types/use-sync-external-store@0.0.6": {} - '@typescript-eslint/eslint-plugin@8.35.0(@typescript-eslint/parser@8.35.0(eslint@9.30.0(jiti@2.4.2))(typescript@5.8.3))(eslint@9.30.0(jiti@2.4.2))(typescript@5.8.3)': + "@typescript-eslint/eslint-plugin@8.35.0(@typescript-eslint/parser@8.35.0(eslint@9.30.0(jiti@2.4.2))(typescript@5.8.3))(eslint@9.30.0(jiti@2.4.2))(typescript@5.8.3)": dependencies: - '@eslint-community/regexpp': 4.12.1 - '@typescript-eslint/parser': 8.35.0(eslint@9.30.0(jiti@2.4.2))(typescript@5.8.3) - '@typescript-eslint/scope-manager': 8.35.0 - '@typescript-eslint/type-utils': 8.35.0(eslint@9.30.0(jiti@2.4.2))(typescript@5.8.3) - '@typescript-eslint/utils': 8.35.0(eslint@9.30.0(jiti@2.4.2))(typescript@5.8.3) - '@typescript-eslint/visitor-keys': 8.35.0 + "@eslint-community/regexpp": 4.12.1 + "@typescript-eslint/parser": 8.35.0(eslint@9.30.0(jiti@2.4.2))(typescript@5.8.3) + "@typescript-eslint/scope-manager": 8.35.0 + "@typescript-eslint/type-utils": 8.35.0(eslint@9.30.0(jiti@2.4.2))(typescript@5.8.3) + "@typescript-eslint/utils": 8.35.0(eslint@9.30.0(jiti@2.4.2))(typescript@5.8.3) + "@typescript-eslint/visitor-keys": 8.35.0 eslint: 9.30.0(jiti@2.4.2) graphemer: 1.4.0 ignore: 7.0.5 @@ -5670,40 +8489,40 @@ snapshots: transitivePeerDependencies: - supports-color - '@typescript-eslint/parser@8.35.0(eslint@9.30.0(jiti@2.4.2))(typescript@5.8.3)': + "@typescript-eslint/parser@8.35.0(eslint@9.30.0(jiti@2.4.2))(typescript@5.8.3)": dependencies: - '@typescript-eslint/scope-manager': 8.35.0 - '@typescript-eslint/types': 8.35.0 - '@typescript-eslint/typescript-estree': 8.35.0(typescript@5.8.3) - '@typescript-eslint/visitor-keys': 8.35.0 + "@typescript-eslint/scope-manager": 8.35.0 + "@typescript-eslint/types": 8.35.0 + "@typescript-eslint/typescript-estree": 8.35.0(typescript@5.8.3) + "@typescript-eslint/visitor-keys": 8.35.0 debug: 4.4.1 eslint: 9.30.0(jiti@2.4.2) typescript: 5.8.3 transitivePeerDependencies: - supports-color - '@typescript-eslint/project-service@8.35.0(typescript@5.8.3)': + "@typescript-eslint/project-service@8.35.0(typescript@5.8.3)": dependencies: - '@typescript-eslint/tsconfig-utils': 8.35.0(typescript@5.8.3) - '@typescript-eslint/types': 8.35.0 + "@typescript-eslint/tsconfig-utils": 8.35.0(typescript@5.8.3) + "@typescript-eslint/types": 8.35.0 debug: 4.4.1 typescript: 5.8.3 transitivePeerDependencies: - supports-color - '@typescript-eslint/scope-manager@8.35.0': + "@typescript-eslint/scope-manager@8.35.0": dependencies: - '@typescript-eslint/types': 8.35.0 - '@typescript-eslint/visitor-keys': 8.35.0 + "@typescript-eslint/types": 8.35.0 + "@typescript-eslint/visitor-keys": 8.35.0 - '@typescript-eslint/tsconfig-utils@8.35.0(typescript@5.8.3)': + "@typescript-eslint/tsconfig-utils@8.35.0(typescript@5.8.3)": dependencies: typescript: 5.8.3 - '@typescript-eslint/type-utils@8.35.0(eslint@9.30.0(jiti@2.4.2))(typescript@5.8.3)': + "@typescript-eslint/type-utils@8.35.0(eslint@9.30.0(jiti@2.4.2))(typescript@5.8.3)": dependencies: - '@typescript-eslint/typescript-estree': 8.35.0(typescript@5.8.3) - '@typescript-eslint/utils': 8.35.0(eslint@9.30.0(jiti@2.4.2))(typescript@5.8.3) + "@typescript-eslint/typescript-estree": 8.35.0(typescript@5.8.3) + "@typescript-eslint/utils": 8.35.0(eslint@9.30.0(jiti@2.4.2))(typescript@5.8.3) debug: 4.4.1 eslint: 9.30.0(jiti@2.4.2) ts-api-utils: 2.1.0(typescript@5.8.3) @@ -5711,14 +8530,14 @@ snapshots: transitivePeerDependencies: - supports-color - '@typescript-eslint/types@8.35.0': {} + "@typescript-eslint/types@8.35.0": {} - '@typescript-eslint/typescript-estree@8.35.0(typescript@5.8.3)': + "@typescript-eslint/typescript-estree@8.35.0(typescript@5.8.3)": dependencies: - '@typescript-eslint/project-service': 8.35.0(typescript@5.8.3) - '@typescript-eslint/tsconfig-utils': 8.35.0(typescript@5.8.3) - '@typescript-eslint/types': 8.35.0 - '@typescript-eslint/visitor-keys': 8.35.0 + "@typescript-eslint/project-service": 8.35.0(typescript@5.8.3) + "@typescript-eslint/tsconfig-utils": 8.35.0(typescript@5.8.3) + "@typescript-eslint/types": 8.35.0 + "@typescript-eslint/visitor-keys": 8.35.0 debug: 4.4.1 fast-glob: 3.3.3 is-glob: 4.0.3 @@ -5729,99 +8548,99 @@ snapshots: transitivePeerDependencies: - supports-color - '@typescript-eslint/utils@8.35.0(eslint@9.30.0(jiti@2.4.2))(typescript@5.8.3)': + "@typescript-eslint/utils@8.35.0(eslint@9.30.0(jiti@2.4.2))(typescript@5.8.3)": dependencies: - '@eslint-community/eslint-utils': 4.7.0(eslint@9.30.0(jiti@2.4.2)) - '@typescript-eslint/scope-manager': 8.35.0 - '@typescript-eslint/types': 8.35.0 - '@typescript-eslint/typescript-estree': 8.35.0(typescript@5.8.3) + "@eslint-community/eslint-utils": 4.7.0(eslint@9.30.0(jiti@2.4.2)) + "@typescript-eslint/scope-manager": 8.35.0 + "@typescript-eslint/types": 8.35.0 + "@typescript-eslint/typescript-estree": 8.35.0(typescript@5.8.3) eslint: 9.30.0(jiti@2.4.2) typescript: 5.8.3 transitivePeerDependencies: - supports-color - '@typescript-eslint/visitor-keys@8.35.0': + "@typescript-eslint/visitor-keys@8.35.0": dependencies: - '@typescript-eslint/types': 8.35.0 + "@typescript-eslint/types": 8.35.0 eslint-visitor-keys: 4.2.1 - '@ungap/structured-clone@1.3.0': {} + "@ungap/structured-clone@1.3.0": {} - '@unrs/resolver-binding-android-arm-eabi@1.9.2': + "@unrs/resolver-binding-android-arm-eabi@1.9.2": optional: true - '@unrs/resolver-binding-android-arm64@1.9.2': + "@unrs/resolver-binding-android-arm64@1.9.2": optional: true - '@unrs/resolver-binding-darwin-arm64@1.9.2': + "@unrs/resolver-binding-darwin-arm64@1.9.2": optional: true - '@unrs/resolver-binding-darwin-x64@1.9.2': + "@unrs/resolver-binding-darwin-x64@1.9.2": optional: true - '@unrs/resolver-binding-freebsd-x64@1.9.2': + "@unrs/resolver-binding-freebsd-x64@1.9.2": optional: true - '@unrs/resolver-binding-linux-arm-gnueabihf@1.9.2': + "@unrs/resolver-binding-linux-arm-gnueabihf@1.9.2": optional: true - '@unrs/resolver-binding-linux-arm-musleabihf@1.9.2': + "@unrs/resolver-binding-linux-arm-musleabihf@1.9.2": optional: true - '@unrs/resolver-binding-linux-arm64-gnu@1.9.2': + "@unrs/resolver-binding-linux-arm64-gnu@1.9.2": optional: true - '@unrs/resolver-binding-linux-arm64-musl@1.9.2': + "@unrs/resolver-binding-linux-arm64-musl@1.9.2": optional: true - '@unrs/resolver-binding-linux-ppc64-gnu@1.9.2': + "@unrs/resolver-binding-linux-ppc64-gnu@1.9.2": optional: true - '@unrs/resolver-binding-linux-riscv64-gnu@1.9.2': + "@unrs/resolver-binding-linux-riscv64-gnu@1.9.2": optional: true - '@unrs/resolver-binding-linux-riscv64-musl@1.9.2': + "@unrs/resolver-binding-linux-riscv64-musl@1.9.2": optional: true - '@unrs/resolver-binding-linux-s390x-gnu@1.9.2': + "@unrs/resolver-binding-linux-s390x-gnu@1.9.2": optional: true - '@unrs/resolver-binding-linux-x64-gnu@1.9.2': + "@unrs/resolver-binding-linux-x64-gnu@1.9.2": optional: true - '@unrs/resolver-binding-linux-x64-musl@1.9.2': + "@unrs/resolver-binding-linux-x64-musl@1.9.2": optional: true - '@unrs/resolver-binding-wasm32-wasi@1.9.2': + "@unrs/resolver-binding-wasm32-wasi@1.9.2": dependencies: - '@napi-rs/wasm-runtime': 0.2.11 + "@napi-rs/wasm-runtime": 0.2.11 optional: true - '@unrs/resolver-binding-win32-arm64-msvc@1.9.2': + "@unrs/resolver-binding-win32-arm64-msvc@1.9.2": optional: true - '@unrs/resolver-binding-win32-ia32-msvc@1.9.2': + "@unrs/resolver-binding-win32-ia32-msvc@1.9.2": optional: true - '@unrs/resolver-binding-win32-x64-msvc@1.9.2': + "@unrs/resolver-binding-win32-x64-msvc@1.9.2": optional: true - '@vitejs/plugin-react@4.6.0(vite@7.0.0(@types/node@24.0.6)(jiti@2.4.2)(lightningcss@1.30.1)(tsx@4.20.3))': + "@vitejs/plugin-react@4.6.0(vite@7.0.0(@types/node@24.0.6)(jiti@2.4.2)(lightningcss@1.30.1)(tsx@4.20.3))": dependencies: - '@babel/core': 7.27.7 - '@babel/plugin-transform-react-jsx-self': 7.27.1(@babel/core@7.27.7) - '@babel/plugin-transform-react-jsx-source': 7.27.1(@babel/core@7.27.7) - '@rolldown/pluginutils': 1.0.0-beta.19 - '@types/babel__core': 7.20.5 + "@babel/core": 7.27.7 + "@babel/plugin-transform-react-jsx-self": 7.27.1(@babel/core@7.27.7) + "@babel/plugin-transform-react-jsx-source": 7.27.1(@babel/core@7.27.7) + "@rolldown/pluginutils": 1.0.0-beta.19 + "@types/babel__core": 7.20.5 react-refresh: 0.17.0 vite: 7.0.0(@types/node@24.0.6)(jiti@2.4.2)(lightningcss@1.30.1)(tsx@4.20.3) transitivePeerDependencies: - supports-color - '@vitest/coverage-v8@3.2.4(vitest@3.2.4(@types/debug@4.1.12)(@types/node@24.0.6)(jiti@2.4.2)(jsdom@26.1.0)(lightningcss@1.30.1)(tsx@4.20.3))': + "@vitest/coverage-v8@3.2.4(vitest@3.2.4(@types/debug@4.1.12)(@types/node@24.0.6)(jiti@2.4.2)(jsdom@26.1.0)(lightningcss@1.30.1)(tsx@4.20.3))": dependencies: - '@ampproject/remapping': 2.3.0 - '@bcoe/v8-coverage': 1.0.2 + "@ampproject/remapping": 2.3.0 + "@bcoe/v8-coverage": 1.0.2 ast-v8-to-istanbul: 0.3.3 debug: 4.4.1 istanbul-lib-coverage: 3.2.2 @@ -5837,45 +8656,45 @@ snapshots: transitivePeerDependencies: - supports-color - '@vitest/expect@3.2.4': + "@vitest/expect@3.2.4": dependencies: - '@types/chai': 5.2.2 - '@vitest/spy': 3.2.4 - '@vitest/utils': 3.2.4 + "@types/chai": 5.2.2 + "@vitest/spy": 3.2.4 + "@vitest/utils": 3.2.4 chai: 5.2.0 tinyrainbow: 2.0.0 - '@vitest/mocker@3.2.4(vite@7.0.0(@types/node@24.0.6)(jiti@2.4.2)(lightningcss@1.30.1)(tsx@4.20.3))': + "@vitest/mocker@3.2.4(vite@7.0.0(@types/node@24.0.6)(jiti@2.4.2)(lightningcss@1.30.1)(tsx@4.20.3))": dependencies: - '@vitest/spy': 3.2.4 + "@vitest/spy": 3.2.4 estree-walker: 3.0.3 magic-string: 0.30.17 optionalDependencies: vite: 7.0.0(@types/node@24.0.6)(jiti@2.4.2)(lightningcss@1.30.1)(tsx@4.20.3) - '@vitest/pretty-format@3.2.4': + "@vitest/pretty-format@3.2.4": dependencies: tinyrainbow: 2.0.0 - '@vitest/runner@3.2.4': + "@vitest/runner@3.2.4": dependencies: - '@vitest/utils': 3.2.4 + "@vitest/utils": 3.2.4 pathe: 2.0.3 strip-literal: 3.0.0 - '@vitest/snapshot@3.2.4': + "@vitest/snapshot@3.2.4": dependencies: - '@vitest/pretty-format': 3.2.4 + "@vitest/pretty-format": 3.2.4 magic-string: 0.30.17 pathe: 2.0.3 - '@vitest/spy@3.2.4': + "@vitest/spy@3.2.4": dependencies: tinyspy: 4.0.3 - '@vitest/utils@3.2.4': + "@vitest/utils@3.2.4": dependencies: - '@vitest/pretty-format': 3.2.4 + "@vitest/pretty-format": 3.2.4 loupe: 3.1.4 tinyrainbow: 2.0.0 @@ -5997,7 +8816,7 @@ snapshots: ast-v8-to-istanbul@0.3.3: dependencies: - '@jridgewell/trace-mapping': 0.3.25 + "@jridgewell/trace-mapping": 0.3.25 estree-walker: 3.0.3 js-tokens: 9.0.1 @@ -6145,7 +8964,7 @@ snapshots: cssstyle@4.6.0: dependencies: - '@asamuzakjp/css-color': 3.2.0 + "@asamuzakjp/css-color": 3.2.0 rrweb-cssom: 0.8.0 csstype@3.1.3: {} @@ -6525,31 +9344,31 @@ snapshots: esbuild@0.25.5: optionalDependencies: - '@esbuild/aix-ppc64': 0.25.5 - '@esbuild/android-arm': 0.25.5 - '@esbuild/android-arm64': 0.25.5 - '@esbuild/android-x64': 0.25.5 - '@esbuild/darwin-arm64': 0.25.5 - '@esbuild/darwin-x64': 0.25.5 - '@esbuild/freebsd-arm64': 0.25.5 - '@esbuild/freebsd-x64': 0.25.5 - '@esbuild/linux-arm': 0.25.5 - '@esbuild/linux-arm64': 0.25.5 - '@esbuild/linux-ia32': 0.25.5 - '@esbuild/linux-loong64': 0.25.5 - '@esbuild/linux-mips64el': 0.25.5 - '@esbuild/linux-ppc64': 0.25.5 - '@esbuild/linux-riscv64': 0.25.5 - '@esbuild/linux-s390x': 0.25.5 - '@esbuild/linux-x64': 0.25.5 - '@esbuild/netbsd-arm64': 0.25.5 - '@esbuild/netbsd-x64': 0.25.5 - '@esbuild/openbsd-arm64': 0.25.5 - '@esbuild/openbsd-x64': 0.25.5 - '@esbuild/sunos-x64': 0.25.5 - '@esbuild/win32-arm64': 0.25.5 - '@esbuild/win32-ia32': 0.25.5 - '@esbuild/win32-x64': 0.25.5 + "@esbuild/aix-ppc64": 0.25.5 + "@esbuild/android-arm": 0.25.5 + "@esbuild/android-arm64": 0.25.5 + "@esbuild/android-x64": 0.25.5 + "@esbuild/darwin-arm64": 0.25.5 + "@esbuild/darwin-x64": 0.25.5 + "@esbuild/freebsd-arm64": 0.25.5 + "@esbuild/freebsd-x64": 0.25.5 + "@esbuild/linux-arm": 0.25.5 + "@esbuild/linux-arm64": 0.25.5 + "@esbuild/linux-ia32": 0.25.5 + "@esbuild/linux-loong64": 0.25.5 + "@esbuild/linux-mips64el": 0.25.5 + "@esbuild/linux-ppc64": 0.25.5 + "@esbuild/linux-riscv64": 0.25.5 + "@esbuild/linux-s390x": 0.25.5 + "@esbuild/linux-x64": 0.25.5 + "@esbuild/netbsd-arm64": 0.25.5 + "@esbuild/netbsd-x64": 0.25.5 + "@esbuild/openbsd-arm64": 0.25.5 + "@esbuild/openbsd-x64": 0.25.5 + "@esbuild/sunos-x64": 0.25.5 + "@esbuild/win32-arm64": 0.25.5 + "@esbuild/win32-ia32": 0.25.5 + "@esbuild/win32-x64": 0.25.5 escalade@3.2.0: {} @@ -6557,10 +9376,10 @@ snapshots: eslint-config-next@15.3.4(eslint@9.30.0(jiti@2.4.2))(typescript@5.8.3): dependencies: - '@next/eslint-plugin-next': 15.3.4 - '@rushstack/eslint-patch': 1.12.0 - '@typescript-eslint/eslint-plugin': 8.35.0(@typescript-eslint/parser@8.35.0(eslint@9.30.0(jiti@2.4.2))(typescript@5.8.3))(eslint@9.30.0(jiti@2.4.2))(typescript@5.8.3) - '@typescript-eslint/parser': 8.35.0(eslint@9.30.0(jiti@2.4.2))(typescript@5.8.3) + "@next/eslint-plugin-next": 15.3.4 + "@rushstack/eslint-patch": 1.12.0 + "@typescript-eslint/eslint-plugin": 8.35.0(@typescript-eslint/parser@8.35.0(eslint@9.30.0(jiti@2.4.2))(typescript@5.8.3))(eslint@9.30.0(jiti@2.4.2))(typescript@5.8.3) + "@typescript-eslint/parser": 8.35.0(eslint@9.30.0(jiti@2.4.2))(typescript@5.8.3) eslint: 9.30.0(jiti@2.4.2) eslint-import-resolver-node: 0.3.9 eslint-import-resolver-typescript: 3.10.1(eslint-plugin-import@2.32.0)(eslint@9.30.0(jiti@2.4.2)) @@ -6585,7 +9404,7 @@ snapshots: eslint-import-resolver-typescript@3.10.1(eslint-plugin-import@2.32.0)(eslint@9.30.0(jiti@2.4.2)): dependencies: - '@nolyfill/is-core-module': 1.0.39 + "@nolyfill/is-core-module": 1.0.39 debug: 4.4.1 eslint: 9.30.0(jiti@2.4.2) get-tsconfig: 4.10.1 @@ -6602,7 +9421,7 @@ snapshots: dependencies: debug: 3.2.7 optionalDependencies: - '@typescript-eslint/parser': 8.35.0(eslint@9.30.0(jiti@2.4.2))(typescript@5.8.3) + "@typescript-eslint/parser": 8.35.0(eslint@9.30.0(jiti@2.4.2))(typescript@5.8.3) eslint: 9.30.0(jiti@2.4.2) eslint-import-resolver-node: 0.3.9 eslint-import-resolver-typescript: 3.10.1(eslint-plugin-import@2.32.0)(eslint@9.30.0(jiti@2.4.2)) @@ -6611,7 +9430,7 @@ snapshots: eslint-plugin-import@2.32.0(@typescript-eslint/parser@8.35.0(eslint@9.30.0(jiti@2.4.2))(typescript@5.8.3))(eslint-import-resolver-typescript@3.10.1)(eslint@9.30.0(jiti@2.4.2)): dependencies: - '@rtsao/scc': 1.1.0 + "@rtsao/scc": 1.1.0 array-includes: 3.1.9 array.prototype.findlastindex: 1.2.6 array.prototype.flat: 1.3.3 @@ -6632,7 +9451,7 @@ snapshots: string.prototype.trimend: 1.0.9 tsconfig-paths: 3.15.0 optionalDependencies: - '@typescript-eslint/parser': 8.35.0(eslint@9.30.0(jiti@2.4.2))(typescript@5.8.3) + "@typescript-eslint/parser": 8.35.0(eslint@9.30.0(jiti@2.4.2))(typescript@5.8.3) transitivePeerDependencies: - eslint-import-resolver-typescript - eslint-import-resolver-webpack @@ -6701,19 +9520,19 @@ snapshots: eslint@9.30.0(jiti@2.4.2): dependencies: - '@eslint-community/eslint-utils': 4.7.0(eslint@9.30.0(jiti@2.4.2)) - '@eslint-community/regexpp': 4.12.1 - '@eslint/config-array': 0.21.0 - '@eslint/config-helpers': 0.3.0 - '@eslint/core': 0.14.0 - '@eslint/eslintrc': 3.3.1 - '@eslint/js': 9.30.0 - '@eslint/plugin-kit': 0.3.3 - '@humanfs/node': 0.16.6 - '@humanwhocodes/module-importer': 1.0.1 - '@humanwhocodes/retry': 0.4.3 - '@types/estree': 1.0.8 - '@types/json-schema': 7.0.15 + "@eslint-community/eslint-utils": 4.7.0(eslint@9.30.0(jiti@2.4.2)) + "@eslint-community/regexpp": 4.12.1 + "@eslint/config-array": 0.21.0 + "@eslint/config-helpers": 0.3.0 + "@eslint/core": 0.14.0 + "@eslint/eslintrc": 3.3.1 + "@eslint/js": 9.30.0 + "@eslint/plugin-kit": 0.3.3 + "@humanfs/node": 0.16.6 + "@humanwhocodes/module-importer": 1.0.1 + "@humanwhocodes/retry": 0.4.3 + "@types/estree": 1.0.8 + "@types/json-schema": 7.0.15 ajv: 6.12.6 chalk: 4.1.2 cross-spawn: 7.0.6 @@ -6761,7 +9580,7 @@ snapshots: estree-walker@3.0.3: dependencies: - '@types/estree': 1.0.8 + "@types/estree": 1.0.8 esutils@2.0.3: {} @@ -6777,16 +9596,16 @@ snapshots: fast-glob@3.3.1: dependencies: - '@nodelib/fs.stat': 2.0.5 - '@nodelib/fs.walk': 1.2.8 + "@nodelib/fs.stat": 2.0.5 + "@nodelib/fs.walk": 1.2.8 glob-parent: 5.1.2 merge2: 1.4.1 micromatch: 4.0.8 fast-glob@3.3.3: dependencies: - '@nodelib/fs.stat': 2.0.5 - '@nodelib/fs.walk': 1.2.8 + "@nodelib/fs.stat": 2.0.5 + "@nodelib/fs.walk": 1.2.8 glob-parent: 5.1.2 merge2: 1.4.1 micromatch: 4.0.8 @@ -6928,7 +9747,7 @@ snapshots: globby@14.1.0: dependencies: - '@sindresorhus/merge-streams': 2.3.0 + "@sindresorhus/merge-streams": 2.3.0 fast-glob: 3.3.3 ignore: 7.0.5 path-type: 6.0.0 @@ -6967,8 +9786,8 @@ snapshots: hast-util-from-parse5@8.0.3: dependencies: - '@types/hast': 3.0.4 - '@types/unist': 3.0.3 + "@types/hast": 3.0.4 + "@types/unist": 3.0.3 devlop: 1.1.0 hastscript: 9.0.1 property-information: 7.1.0 @@ -6978,13 +9797,13 @@ snapshots: hast-util-parse-selector@4.0.0: dependencies: - '@types/hast': 3.0.4 + "@types/hast": 3.0.4 hast-util-raw@9.1.0: dependencies: - '@types/hast': 3.0.4 - '@types/unist': 3.0.3 - '@ungap/structured-clone': 1.3.0 + "@types/hast": 3.0.4 + "@types/unist": 3.0.3 + "@ungap/structured-clone": 1.3.0 hast-util-from-parse5: 8.0.3 hast-util-to-parse5: 8.0.0 html-void-elements: 3.0.0 @@ -6998,9 +9817,9 @@ snapshots: hast-util-to-jsx-runtime@2.3.6: dependencies: - '@types/estree': 1.0.8 - '@types/hast': 3.0.4 - '@types/unist': 3.0.3 + "@types/estree": 1.0.8 + "@types/hast": 3.0.4 + "@types/unist": 3.0.3 comma-separated-tokens: 2.0.3 devlop: 1.1.0 estree-util-is-identifier-name: 3.0.0 @@ -7018,7 +9837,7 @@ snapshots: hast-util-to-parse5@8.0.0: dependencies: - '@types/hast': 3.0.4 + "@types/hast": 3.0.4 comma-separated-tokens: 2.0.3 devlop: 1.1.0 property-information: 6.5.0 @@ -7028,11 +9847,11 @@ snapshots: hast-util-whitespace@3.0.0: dependencies: - '@types/hast': 3.0.4 + "@types/hast": 3.0.4 hastscript@9.0.1: dependencies: - '@types/hast': 3.0.4 + "@types/hast": 3.0.4 comma-separated-tokens: 2.0.3 hast-util-parse-selector: 4.0.0 property-information: 7.1.0 @@ -7240,7 +10059,7 @@ snapshots: istanbul-lib-source-maps@5.0.6: dependencies: - '@jridgewell/trace-mapping': 0.3.25 + "@jridgewell/trace-mapping": 0.3.25 debug: 4.4.1 istanbul-lib-coverage: 3.2.2 transitivePeerDependencies: @@ -7262,9 +10081,9 @@ snapshots: jackspeak@3.4.3: dependencies: - '@isaacs/cliui': 8.0.2 + "@isaacs/cliui": 8.0.2 optionalDependencies: - '@pkgjs/parseargs': 0.11.0 + "@pkgjs/parseargs": 0.11.0 jiti@2.4.2: {} @@ -7432,12 +10251,12 @@ snapshots: magic-string@0.30.17: dependencies: - '@jridgewell/sourcemap-codec': 1.5.0 + "@jridgewell/sourcemap-codec": 1.5.0 magicast@0.3.5: dependencies: - '@babel/parser': 7.27.7 - '@babel/types': 7.27.7 + "@babel/parser": 7.27.7 + "@babel/types": 7.27.7 source-map-js: 1.2.1 make-dir@4.0.0: @@ -7488,8 +10307,8 @@ snapshots: mdast-util-from-markdown@2.0.2: dependencies: - '@types/mdast': 4.0.4 - '@types/unist': 3.0.3 + "@types/mdast": 4.0.4 + "@types/unist": 3.0.3 decode-named-character-reference: 1.2.0 devlop: 1.1.0 mdast-util-to-string: 4.0.0 @@ -7505,9 +10324,9 @@ snapshots: mdast-util-mdx-expression@2.0.1: dependencies: - '@types/estree-jsx': 1.0.5 - '@types/hast': 3.0.4 - '@types/mdast': 4.0.4 + "@types/estree-jsx": 1.0.5 + "@types/hast": 3.0.4 + "@types/mdast": 4.0.4 devlop: 1.1.0 mdast-util-from-markdown: 2.0.2 mdast-util-to-markdown: 2.1.2 @@ -7516,10 +10335,10 @@ snapshots: mdast-util-mdx-jsx@3.2.0: dependencies: - '@types/estree-jsx': 1.0.5 - '@types/hast': 3.0.4 - '@types/mdast': 4.0.4 - '@types/unist': 3.0.3 + "@types/estree-jsx": 1.0.5 + "@types/hast": 3.0.4 + "@types/mdast": 4.0.4 + "@types/unist": 3.0.3 ccount: 2.0.1 devlop: 1.1.0 mdast-util-from-markdown: 2.0.2 @@ -7533,9 +10352,9 @@ snapshots: mdast-util-mdxjs-esm@2.0.1: dependencies: - '@types/estree-jsx': 1.0.5 - '@types/hast': 3.0.4 - '@types/mdast': 4.0.4 + "@types/estree-jsx": 1.0.5 + "@types/hast": 3.0.4 + "@types/mdast": 4.0.4 devlop: 1.1.0 mdast-util-from-markdown: 2.0.2 mdast-util-to-markdown: 2.1.2 @@ -7544,14 +10363,14 @@ snapshots: mdast-util-phrasing@4.1.0: dependencies: - '@types/mdast': 4.0.4 + "@types/mdast": 4.0.4 unist-util-is: 6.0.0 mdast-util-to-hast@13.2.0: dependencies: - '@types/hast': 3.0.4 - '@types/mdast': 4.0.4 - '@ungap/structured-clone': 1.3.0 + "@types/hast": 3.0.4 + "@types/mdast": 4.0.4 + "@ungap/structured-clone": 1.3.0 devlop: 1.1.0 micromark-util-sanitize-uri: 2.0.1 trim-lines: 3.0.1 @@ -7561,8 +10380,8 @@ snapshots: mdast-util-to-markdown@2.1.2: dependencies: - '@types/mdast': 4.0.4 - '@types/unist': 3.0.3 + "@types/mdast": 4.0.4 + "@types/unist": 3.0.3 longest-streak: 3.1.0 mdast-util-phrasing: 4.1.0 mdast-util-to-string: 4.0.0 @@ -7573,7 +10392,7 @@ snapshots: mdast-util-to-string@4.0.0: dependencies: - '@types/mdast': 4.0.4 + "@types/mdast": 4.0.4 mdurl@2.0.0: {} @@ -7636,7 +10455,7 @@ snapshots: micromark-extension-math@3.1.0: dependencies: - '@types/katex': 0.16.7 + "@types/katex": 0.16.7 devlop: 1.1.0 katex: 0.16.22 micromark-factory-space: 2.0.1 @@ -7738,7 +10557,7 @@ snapshots: micromark@4.0.2: dependencies: - '@types/debug': 4.1.12 + "@types/debug": 4.1.12 debug: 4.4.1 decode-named-character-reference: 1.2.0 devlop: 1.1.0 @@ -7797,8 +10616,8 @@ snapshots: next-auth@4.24.11(next@15.3.4(@babel/core@7.27.7)(@playwright/test@1.53.1)(react-dom@19.1.0(react@19.1.0))(react@19.1.0))(react-dom@19.1.0(react@19.1.0))(react@19.1.0): dependencies: - '@babel/runtime': 7.27.6 - '@panva/hkdf': 1.2.1 + "@babel/runtime": 7.27.6 + "@panva/hkdf": 1.2.1 cookie: 0.7.2 jose: 4.15.9 next: 15.3.4(@babel/core@7.27.7)(@playwright/test@1.53.1)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) @@ -7812,9 +10631,9 @@ snapshots: next@15.3.4(@babel/core@7.27.7)(@playwright/test@1.53.1)(react-dom@19.1.0(react@19.1.0))(react@19.1.0): dependencies: - '@next/env': 15.3.4 - '@swc/counter': 0.1.3 - '@swc/helpers': 0.5.15 + "@next/env": 15.3.4 + "@swc/counter": 0.1.3 + "@swc/helpers": 0.5.15 busboy: 1.6.0 caniuse-lite: 1.0.30001726 postcss: 8.4.31 @@ -7822,18 +10641,18 @@ snapshots: react-dom: 19.1.0(react@19.1.0) styled-jsx: 5.1.6(@babel/core@7.27.7)(react@19.1.0) optionalDependencies: - '@next/swc-darwin-arm64': 15.3.4 - '@next/swc-darwin-x64': 15.3.4 - '@next/swc-linux-arm64-gnu': 15.3.4 - '@next/swc-linux-arm64-musl': 15.3.4 - '@next/swc-linux-x64-gnu': 15.3.4 - '@next/swc-linux-x64-musl': 15.3.4 - '@next/swc-win32-arm64-msvc': 15.3.4 - '@next/swc-win32-x64-msvc': 15.3.4 - '@playwright/test': 1.53.1 + "@next/swc-darwin-arm64": 15.3.4 + "@next/swc-darwin-x64": 15.3.4 + "@next/swc-linux-arm64-gnu": 15.3.4 + "@next/swc-linux-arm64-musl": 15.3.4 + "@next/swc-linux-x64-gnu": 15.3.4 + "@next/swc-linux-x64-musl": 15.3.4 + "@next/swc-win32-arm64-msvc": 15.3.4 + "@next/swc-win32-x64-msvc": 15.3.4 + "@playwright/test": 1.53.1 sharp: 0.34.2 transitivePeerDependencies: - - '@babel/core' + - "@babel/core" - babel-plugin-macros node-cron@4.1.1: {} @@ -7936,7 +10755,7 @@ snapshots: parse-entities@4.0.2: dependencies: - '@types/unist': 2.0.11 + "@types/unist": 2.0.11 character-entities-legacy: 3.0.0 character-reference-invalid: 2.0.1 decode-named-character-reference: 1.2.0 @@ -8069,8 +10888,8 @@ snapshots: prisma@6.10.1(typescript@5.8.3): dependencies: - '@prisma/config': 6.10.1 - '@prisma/engines': 6.10.1 + "@prisma/config": 6.10.1 + "@prisma/engines": 6.10.1 optionalDependencies: typescript: 5.8.3 @@ -8107,16 +10926,16 @@ snapshots: react-leaflet@5.0.0(leaflet@1.9.4)(react-dom@19.1.0(react@19.1.0))(react@19.1.0): dependencies: - '@react-leaflet/core': 3.0.0(leaflet@1.9.4)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) + "@react-leaflet/core": 3.0.0(leaflet@1.9.4)(react-dom@19.1.0(react@19.1.0))(react@19.1.0) leaflet: 1.9.4 react: 19.1.0 react-dom: 19.1.0(react@19.1.0) react-markdown@10.1.0(@types/react@19.1.8)(react@19.1.0): dependencies: - '@types/hast': 3.0.4 - '@types/mdast': 4.0.4 - '@types/react': 19.1.8 + "@types/hast": 3.0.4 + "@types/mdast": 4.0.4 + "@types/react": 19.1.8 devlop: 1.1.0 hast-util-to-jsx-runtime: 2.3.6 html-url-attributes: 3.0.1 @@ -8132,11 +10951,11 @@ snapshots: react-redux@9.2.0(@types/react@19.1.8)(react@19.1.0)(redux@5.0.1): dependencies: - '@types/use-sync-external-store': 0.0.6 + "@types/use-sync-external-store": 0.0.6 react: 19.1.0 use-sync-external-store: 1.5.0(react@19.1.0) optionalDependencies: - '@types/react': 19.1.8 + "@types/react": 19.1.8 redux: 5.0.1 react-refresh@0.17.0: {} @@ -8147,7 +10966,7 @@ snapshots: react-style-singleton: 2.2.3(@types/react@19.1.8)(react@19.1.0) tslib: 2.8.1 optionalDependencies: - '@types/react': 19.1.8 + "@types/react": 19.1.8 react-remove-scroll@2.7.1(@types/react@19.1.8)(react@19.1.0): dependencies: @@ -8158,7 +10977,7 @@ snapshots: use-callback-ref: 1.3.3(@types/react@19.1.8)(react@19.1.0) use-sidecar: 1.1.3(@types/react@19.1.8)(react@19.1.0) optionalDependencies: - '@types/react': 19.1.8 + "@types/react": 19.1.8 react-style-singleton@2.2.3(@types/react@19.1.8)(react@19.1.0): dependencies: @@ -8166,13 +10985,13 @@ snapshots: react: 19.1.0 tslib: 2.8.1 optionalDependencies: - '@types/react': 19.1.8 + "@types/react": 19.1.8 react@19.1.0: {} recharts@3.0.2(@types/react@19.1.8)(react-dom@19.1.0(react@19.1.0))(react-is@17.0.2)(react@19.1.0)(redux@5.0.1): dependencies: - '@reduxjs/toolkit': 2.8.2(react-redux@9.2.0(@types/react@19.1.8)(react@19.1.0)(redux@5.0.1))(react@19.1.0) + "@reduxjs/toolkit": 2.8.2(react-redux@9.2.0(@types/react@19.1.8)(react@19.1.0)(redux@5.0.1))(react@19.1.0) clsx: 2.1.1 decimal.js-light: 2.5.1 es-toolkit: 1.39.5 @@ -8187,7 +11006,7 @@ snapshots: use-sync-external-store: 1.5.0(react@19.1.0) victory-vendor: 37.3.6 transitivePeerDependencies: - - '@types/react' + - "@types/react" - redux redux-thunk@3.1.0(redux@5.0.1): @@ -8218,13 +11037,13 @@ snapshots: rehype-raw@7.0.0: dependencies: - '@types/hast': 3.0.4 + "@types/hast": 3.0.4 hast-util-raw: 9.1.0 vfile: 6.0.3 remark-parse@11.0.0: dependencies: - '@types/mdast': 4.0.4 + "@types/mdast": 4.0.4 mdast-util-from-markdown: 2.0.2 micromark-util-types: 2.0.2 unified: 11.0.5 @@ -8233,8 +11052,8 @@ snapshots: remark-rehype@11.1.2: dependencies: - '@types/hast': 3.0.4 - '@types/mdast': 4.0.4 + "@types/hast": 3.0.4 + "@types/mdast": 4.0.4 mdast-util-to-hast: 13.2.0 unified: 11.0.5 vfile: 6.0.3 @@ -8263,28 +11082,28 @@ snapshots: rollup@4.44.1: dependencies: - '@types/estree': 1.0.8 + "@types/estree": 1.0.8 optionalDependencies: - '@rollup/rollup-android-arm-eabi': 4.44.1 - '@rollup/rollup-android-arm64': 4.44.1 - '@rollup/rollup-darwin-arm64': 4.44.1 - '@rollup/rollup-darwin-x64': 4.44.1 - '@rollup/rollup-freebsd-arm64': 4.44.1 - '@rollup/rollup-freebsd-x64': 4.44.1 - '@rollup/rollup-linux-arm-gnueabihf': 4.44.1 - '@rollup/rollup-linux-arm-musleabihf': 4.44.1 - '@rollup/rollup-linux-arm64-gnu': 4.44.1 - '@rollup/rollup-linux-arm64-musl': 4.44.1 - '@rollup/rollup-linux-loongarch64-gnu': 4.44.1 - '@rollup/rollup-linux-powerpc64le-gnu': 4.44.1 - '@rollup/rollup-linux-riscv64-gnu': 4.44.1 - '@rollup/rollup-linux-riscv64-musl': 4.44.1 - '@rollup/rollup-linux-s390x-gnu': 4.44.1 - '@rollup/rollup-linux-x64-gnu': 4.44.1 - '@rollup/rollup-linux-x64-musl': 4.44.1 - '@rollup/rollup-win32-arm64-msvc': 4.44.1 - '@rollup/rollup-win32-ia32-msvc': 4.44.1 - '@rollup/rollup-win32-x64-msvc': 4.44.1 + "@rollup/rollup-android-arm-eabi": 4.44.1 + "@rollup/rollup-android-arm64": 4.44.1 + "@rollup/rollup-darwin-arm64": 4.44.1 + "@rollup/rollup-darwin-x64": 4.44.1 + "@rollup/rollup-freebsd-arm64": 4.44.1 + "@rollup/rollup-freebsd-x64": 4.44.1 + "@rollup/rollup-linux-arm-gnueabihf": 4.44.1 + "@rollup/rollup-linux-arm-musleabihf": 4.44.1 + "@rollup/rollup-linux-arm64-gnu": 4.44.1 + "@rollup/rollup-linux-arm64-musl": 4.44.1 + "@rollup/rollup-linux-loongarch64-gnu": 4.44.1 + "@rollup/rollup-linux-powerpc64le-gnu": 4.44.1 + "@rollup/rollup-linux-riscv64-gnu": 4.44.1 + "@rollup/rollup-linux-riscv64-musl": 4.44.1 + "@rollup/rollup-linux-s390x-gnu": 4.44.1 + "@rollup/rollup-linux-x64-gnu": 4.44.1 + "@rollup/rollup-linux-x64-musl": 4.44.1 + "@rollup/rollup-win32-arm64-msvc": 4.44.1 + "@rollup/rollup-win32-ia32-msvc": 4.44.1 + "@rollup/rollup-win32-x64-msvc": 4.44.1 fsevents: 2.3.3 rrweb-cssom@0.8.0: {} @@ -8354,27 +11173,27 @@ snapshots: detect-libc: 2.0.4 semver: 7.7.2 optionalDependencies: - '@img/sharp-darwin-arm64': 0.34.2 - '@img/sharp-darwin-x64': 0.34.2 - '@img/sharp-libvips-darwin-arm64': 1.1.0 - '@img/sharp-libvips-darwin-x64': 1.1.0 - '@img/sharp-libvips-linux-arm': 1.1.0 - '@img/sharp-libvips-linux-arm64': 1.1.0 - '@img/sharp-libvips-linux-ppc64': 1.1.0 - '@img/sharp-libvips-linux-s390x': 1.1.0 - '@img/sharp-libvips-linux-x64': 1.1.0 - '@img/sharp-libvips-linuxmusl-arm64': 1.1.0 - '@img/sharp-libvips-linuxmusl-x64': 1.1.0 - '@img/sharp-linux-arm': 0.34.2 - '@img/sharp-linux-arm64': 0.34.2 - '@img/sharp-linux-s390x': 0.34.2 - '@img/sharp-linux-x64': 0.34.2 - '@img/sharp-linuxmusl-arm64': 0.34.2 - '@img/sharp-linuxmusl-x64': 0.34.2 - '@img/sharp-wasm32': 0.34.2 - '@img/sharp-win32-arm64': 0.34.2 - '@img/sharp-win32-ia32': 0.34.2 - '@img/sharp-win32-x64': 0.34.2 + "@img/sharp-darwin-arm64": 0.34.2 + "@img/sharp-darwin-x64": 0.34.2 + "@img/sharp-libvips-darwin-arm64": 1.1.0 + "@img/sharp-libvips-darwin-x64": 1.1.0 + "@img/sharp-libvips-linux-arm": 1.1.0 + "@img/sharp-libvips-linux-arm64": 1.1.0 + "@img/sharp-libvips-linux-ppc64": 1.1.0 + "@img/sharp-libvips-linux-s390x": 1.1.0 + "@img/sharp-libvips-linux-x64": 1.1.0 + "@img/sharp-libvips-linuxmusl-arm64": 1.1.0 + "@img/sharp-libvips-linuxmusl-x64": 1.1.0 + "@img/sharp-linux-arm": 0.34.2 + "@img/sharp-linux-arm64": 0.34.2 + "@img/sharp-linux-s390x": 0.34.2 + "@img/sharp-linux-x64": 0.34.2 + "@img/sharp-linuxmusl-arm64": 0.34.2 + "@img/sharp-linuxmusl-x64": 0.34.2 + "@img/sharp-wasm32": 0.34.2 + "@img/sharp-win32-arm64": 0.34.2 + "@img/sharp-win32-ia32": 0.34.2 + "@img/sharp-win32-x64": 0.34.2 optional: true shebang-command@2.0.0: @@ -8537,7 +11356,7 @@ snapshots: client-only: 0.0.1 react: 19.1.0 optionalDependencies: - '@babel/core': 7.27.7 + "@babel/core": 7.27.7 supports-color@7.2.0: dependencies: @@ -8549,7 +11368,7 @@ snapshots: synckit@0.11.8: dependencies: - '@pkgr/core': 0.2.7 + "@pkgr/core": 0.2.7 tailwind-merge@3.3.1: {} @@ -8559,7 +11378,7 @@ snapshots: tar@7.4.3: dependencies: - '@isaacs/fs-minipass': 4.0.1 + "@isaacs/fs-minipass": 4.0.1 chownr: 3.0.0 minipass: 7.1.2 minizlib: 3.0.2 @@ -8568,7 +11387,7 @@ snapshots: test-exclude@7.0.1: dependencies: - '@istanbuljs/schema': 0.1.3 + "@istanbuljs/schema": 0.1.3 glob: 10.4.5 minimatch: 9.0.5 @@ -8617,12 +11436,12 @@ snapshots: ts-node@10.9.2(@types/node@24.0.6)(typescript@5.8.3): dependencies: - '@cspotcode/source-map-support': 0.8.1 - '@tsconfig/node10': 1.0.11 - '@tsconfig/node12': 1.0.11 - '@tsconfig/node14': 1.0.3 - '@tsconfig/node16': 1.0.4 - '@types/node': 24.0.6 + "@cspotcode/source-map-support": 0.8.1 + "@tsconfig/node10": 1.0.11 + "@tsconfig/node12": 1.0.11 + "@tsconfig/node14": 1.0.3 + "@tsconfig/node16": 1.0.4 + "@types/node": 24.0.6 acorn: 8.15.0 acorn-walk: 8.3.4 arg: 4.1.3 @@ -8639,7 +11458,7 @@ snapshots: tsconfig-paths@3.15.0: dependencies: - '@types/json5': 0.0.29 + "@types/json5": 0.0.29 json5: 1.0.2 minimist: 1.2.8 strip-bom: 3.0.0 @@ -8709,7 +11528,7 @@ snapshots: unified@11.0.5: dependencies: - '@types/unist': 3.0.3 + "@types/unist": 3.0.3 bail: 2.0.2 devlop: 1.1.0 extend: 3.0.2 @@ -8719,24 +11538,24 @@ snapshots: unist-util-is@6.0.0: dependencies: - '@types/unist': 3.0.3 + "@types/unist": 3.0.3 unist-util-position@5.0.0: dependencies: - '@types/unist': 3.0.3 + "@types/unist": 3.0.3 unist-util-stringify-position@4.0.0: dependencies: - '@types/unist': 3.0.3 + "@types/unist": 3.0.3 unist-util-visit-parents@6.0.1: dependencies: - '@types/unist': 3.0.3 + "@types/unist": 3.0.3 unist-util-is: 6.0.0 unist-util-visit@5.0.0: dependencies: - '@types/unist': 3.0.3 + "@types/unist": 3.0.3 unist-util-is: 6.0.0 unist-util-visit-parents: 6.0.1 @@ -8744,25 +11563,25 @@ snapshots: dependencies: napi-postinstall: 0.2.4 optionalDependencies: - '@unrs/resolver-binding-android-arm-eabi': 1.9.2 - '@unrs/resolver-binding-android-arm64': 1.9.2 - '@unrs/resolver-binding-darwin-arm64': 1.9.2 - '@unrs/resolver-binding-darwin-x64': 1.9.2 - '@unrs/resolver-binding-freebsd-x64': 1.9.2 - '@unrs/resolver-binding-linux-arm-gnueabihf': 1.9.2 - '@unrs/resolver-binding-linux-arm-musleabihf': 1.9.2 - '@unrs/resolver-binding-linux-arm64-gnu': 1.9.2 - '@unrs/resolver-binding-linux-arm64-musl': 1.9.2 - '@unrs/resolver-binding-linux-ppc64-gnu': 1.9.2 - '@unrs/resolver-binding-linux-riscv64-gnu': 1.9.2 - '@unrs/resolver-binding-linux-riscv64-musl': 1.9.2 - '@unrs/resolver-binding-linux-s390x-gnu': 1.9.2 - '@unrs/resolver-binding-linux-x64-gnu': 1.9.2 - '@unrs/resolver-binding-linux-x64-musl': 1.9.2 - '@unrs/resolver-binding-wasm32-wasi': 1.9.2 - '@unrs/resolver-binding-win32-arm64-msvc': 1.9.2 - '@unrs/resolver-binding-win32-ia32-msvc': 1.9.2 - '@unrs/resolver-binding-win32-x64-msvc': 1.9.2 + "@unrs/resolver-binding-android-arm-eabi": 1.9.2 + "@unrs/resolver-binding-android-arm64": 1.9.2 + "@unrs/resolver-binding-darwin-arm64": 1.9.2 + "@unrs/resolver-binding-darwin-x64": 1.9.2 + "@unrs/resolver-binding-freebsd-x64": 1.9.2 + "@unrs/resolver-binding-linux-arm-gnueabihf": 1.9.2 + "@unrs/resolver-binding-linux-arm-musleabihf": 1.9.2 + "@unrs/resolver-binding-linux-arm64-gnu": 1.9.2 + "@unrs/resolver-binding-linux-arm64-musl": 1.9.2 + "@unrs/resolver-binding-linux-ppc64-gnu": 1.9.2 + "@unrs/resolver-binding-linux-riscv64-gnu": 1.9.2 + "@unrs/resolver-binding-linux-riscv64-musl": 1.9.2 + "@unrs/resolver-binding-linux-s390x-gnu": 1.9.2 + "@unrs/resolver-binding-linux-x64-gnu": 1.9.2 + "@unrs/resolver-binding-linux-x64-musl": 1.9.2 + "@unrs/resolver-binding-wasm32-wasi": 1.9.2 + "@unrs/resolver-binding-win32-arm64-msvc": 1.9.2 + "@unrs/resolver-binding-win32-ia32-msvc": 1.9.2 + "@unrs/resolver-binding-win32-x64-msvc": 1.9.2 update-browserslist-db@1.1.3(browserslist@4.25.1): dependencies: @@ -8779,7 +11598,7 @@ snapshots: react: 19.1.0 tslib: 2.8.1 optionalDependencies: - '@types/react': 19.1.8 + "@types/react": 19.1.8 use-sidecar@1.1.3(@types/react@19.1.8)(react@19.1.0): dependencies: @@ -8787,7 +11606,7 @@ snapshots: react: 19.1.0 tslib: 2.8.1 optionalDependencies: - '@types/react': 19.1.8 + "@types/react": 19.1.8 use-sync-external-store@1.5.0(react@19.1.0): dependencies: @@ -8799,28 +11618,28 @@ snapshots: vfile-location@5.0.3: dependencies: - '@types/unist': 3.0.3 + "@types/unist": 3.0.3 vfile: 6.0.3 vfile-message@4.0.2: dependencies: - '@types/unist': 3.0.3 + "@types/unist": 3.0.3 unist-util-stringify-position: 4.0.0 vfile@6.0.3: dependencies: - '@types/unist': 3.0.3 + "@types/unist": 3.0.3 vfile-message: 4.0.2 victory-vendor@37.3.6: dependencies: - '@types/d3-array': 3.2.1 - '@types/d3-ease': 3.0.2 - '@types/d3-interpolate': 3.0.4 - '@types/d3-scale': 4.0.9 - '@types/d3-shape': 3.1.7 - '@types/d3-time': 3.0.4 - '@types/d3-timer': 3.0.2 + "@types/d3-array": 3.2.1 + "@types/d3-ease": 3.0.2 + "@types/d3-interpolate": 3.0.4 + "@types/d3-scale": 4.0.9 + "@types/d3-shape": 3.1.7 + "@types/d3-time": 3.0.4 + "@types/d3-timer": 3.0.2 d3-array: 3.2.4 d3-ease: 3.0.1 d3-interpolate: 3.0.1 @@ -8837,7 +11656,7 @@ snapshots: pathe: 2.0.3 vite: 7.0.0(@types/node@24.0.6)(jiti@2.4.2)(lightningcss@1.30.1)(tsx@4.20.3) transitivePeerDependencies: - - '@types/node' + - "@types/node" - jiti - less - lightningcss @@ -8870,7 +11689,7 @@ snapshots: rollup: 4.44.1 tinyglobby: 0.2.14 optionalDependencies: - '@types/node': 24.0.6 + "@types/node": 24.0.6 fsevents: 2.3.3 jiti: 2.4.2 lightningcss: 1.30.1 @@ -8878,14 +11697,14 @@ snapshots: vitest@3.2.4(@types/debug@4.1.12)(@types/node@24.0.6)(jiti@2.4.2)(jsdom@26.1.0)(lightningcss@1.30.1)(tsx@4.20.3): dependencies: - '@types/chai': 5.2.2 - '@vitest/expect': 3.2.4 - '@vitest/mocker': 3.2.4(vite@7.0.0(@types/node@24.0.6)(jiti@2.4.2)(lightningcss@1.30.1)(tsx@4.20.3)) - '@vitest/pretty-format': 3.2.4 - '@vitest/runner': 3.2.4 - '@vitest/snapshot': 3.2.4 - '@vitest/spy': 3.2.4 - '@vitest/utils': 3.2.4 + "@types/chai": 5.2.2 + "@vitest/expect": 3.2.4 + "@vitest/mocker": 3.2.4(vite@7.0.0(@types/node@24.0.6)(jiti@2.4.2)(lightningcss@1.30.1)(tsx@4.20.3)) + "@vitest/pretty-format": 3.2.4 + "@vitest/runner": 3.2.4 + "@vitest/snapshot": 3.2.4 + "@vitest/spy": 3.2.4 + "@vitest/utils": 3.2.4 chai: 5.2.0 debug: 4.4.1 expect-type: 1.2.1 @@ -8902,8 +11721,8 @@ snapshots: vite-node: 3.2.4(@types/node@24.0.6)(jiti@2.4.2)(lightningcss@1.30.1)(tsx@4.20.3) why-is-node-running: 2.3.0 optionalDependencies: - '@types/debug': 4.1.12 - '@types/node': 24.0.6 + "@types/debug": 4.1.12 + "@types/node": 24.0.6 jsdom: 26.1.0 transitivePeerDependencies: - jiti @@ -9027,4 +11846,6 @@ snapshots: yocto-queue@0.1.0: {} + zod@3.25.67: {} + zwitch@2.0.4: {} diff --git a/prisma/schema.prisma b/prisma/schema.prisma index 1e4701c..3575564 100644 --- a/prisma/schema.prisma +++ b/prisma/schema.prisma @@ -1,5 +1,5 @@ generator client { - provider = "prisma-client-js" + provider = "prisma-client-js" previewFeatures = ["driverAdapters"] } @@ -9,9 +9,242 @@ datasource db { directUrl = env("DATABASE_URL_DIRECT") } -/** - * ENUMS – fewer magic strings - */ +/// * +/// * COMPANY (multi-tenant root) +model Company { + id String @id @default(uuid()) + name String + csvUrl String + csvUsername String? + csvPassword String? + sentimentAlert Float? + dashboardOpts Json? + createdAt DateTime @default(now()) + updatedAt DateTime @updatedAt + companyAiModels CompanyAIModel[] + sessions Session[] + imports SessionImport[] + users User[] @relation("CompanyUsers") +} + +/// * +/// * USER (auth accounts) +model User { + id String @id @default(uuid()) + email String @unique + password String + role UserRole @default(USER) + companyId String + resetToken String? + resetTokenExpiry DateTime? + createdAt DateTime @default(now()) + updatedAt DateTime @updatedAt + company Company @relation("CompanyUsers", fields: [companyId], references: [id], onDelete: Cascade) +} + +/// * +/// * 1. Normalised session --------------------------- +model Session { + id String @id @default(uuid()) + companyId String + importId String? @unique + /// * + /// * session-level data (processed from SessionImport) + startTime DateTime + endTime DateTime + ipAddress String? + country String? + fullTranscriptUrl String? + avgResponseTime Float? + initialMsg String? + language String? + messagesSent Int? + sentiment SentimentCategory? + escalated Boolean? + forwardedHr Boolean? + category SessionCategory? + summary String? + createdAt DateTime @default(now()) + updatedAt DateTime @updatedAt + aiProcessingRequests AIProcessingRequest[] + messages Message[] + company Company @relation(fields: [companyId], references: [id], onDelete: Cascade) + import SessionImport? @relation("ImportToSession", fields: [importId], references: [id]) + processingStatus SessionProcessingStatus[] + sessionQuestions SessionQuestion[] + + @@index([companyId, startTime]) +} + +/// * +/// * 2. Raw CSV row (pure data storage) ---------- +model SessionImport { + id String @id @default(uuid()) + companyId String + externalSessionId String @unique + startTimeRaw String + endTimeRaw String + ipAddress String? + countryCode String? + language String? + messagesSent Int? + sentimentRaw String? + escalatedRaw String? + forwardedHrRaw String? + fullTranscriptUrl String? + avgResponseTimeSeconds Float? + tokens Int? + tokensEur Float? + category String? + initialMessage String? + rawTranscriptContent String? + createdAt DateTime @default(now()) + session Session? @relation("ImportToSession") + company Company @relation(fields: [companyId], references: [id], onDelete: Cascade) + + @@unique([companyId, externalSessionId]) +} + +/// * +/// * MESSAGE (individual lines) +model Message { + id String @id @default(uuid()) + sessionId String + timestamp DateTime? + role String + content String + order Int + createdAt DateTime @default(now()) + session Session @relation(fields: [sessionId], references: [id], onDelete: Cascade) + + @@unique([sessionId, order]) + @@index([sessionId, order]) +} + +/// * +/// * UNIFIED PROCESSING STATUS TRACKING +model SessionProcessingStatus { + id String @id @default(uuid()) + sessionId String + stage ProcessingStage + status ProcessingStatus @default(PENDING) + startedAt DateTime? + completedAt DateTime? + errorMessage String? + retryCount Int @default(0) + metadata Json? + session Session @relation(fields: [sessionId], references: [id], onDelete: Cascade) + + @@unique([sessionId, stage]) + @@index([stage, status]) + @@index([sessionId]) +} + +/// * +/// * QUESTION MANAGEMENT (separate from Session for better analytics) +model Question { + id String @id @default(uuid()) + content String @unique + createdAt DateTime @default(now()) + sessionQuestions SessionQuestion[] +} + +model SessionQuestion { + id String @id @default(uuid()) + sessionId String + questionId String + order Int + createdAt DateTime @default(now()) + question Question @relation(fields: [questionId], references: [id]) + session Session @relation(fields: [sessionId], references: [id], onDelete: Cascade) + + @@unique([sessionId, questionId]) + @@unique([sessionId, order]) + @@index([sessionId]) +} + +/// * +/// * AI PROCESSING COST TRACKING +model AIProcessingRequest { + id String @id @default(uuid()) + sessionId String + openaiRequestId String? + model String + serviceTier String? + systemFingerprint String? + promptTokens Int + completionTokens Int + totalTokens Int + cachedTokens Int? + audioTokensPrompt Int? + reasoningTokens Int? + audioTokensCompletion Int? + acceptedPredictionTokens Int? + rejectedPredictionTokens Int? + promptTokenCost Float + completionTokenCost Float + totalCostEur Float + processingType String + success Boolean + errorMessage String? + requestedAt DateTime @default(now()) + completedAt DateTime? + session Session @relation(fields: [sessionId], references: [id], onDelete: Cascade) + + @@index([sessionId]) + @@index([requestedAt]) + @@index([model]) +} + +/// * +/// * AI Model definitions (without pricing) +model AIModel { + id String @id @default(uuid()) + name String @unique + provider String + maxTokens Int? + isActive Boolean @default(true) + createdAt DateTime @default(now()) + updatedAt DateTime @updatedAt + pricing AIModelPricing[] + companyModels CompanyAIModel[] + + @@index([provider, isActive]) +} + +/// * +/// * Time-based pricing for AI models +model AIModelPricing { + id String @id @default(uuid()) + aiModelId String + promptTokenCost Float + completionTokenCost Float + effectiveFrom DateTime + effectiveUntil DateTime? + createdAt DateTime @default(now()) + aiModel AIModel @relation(fields: [aiModelId], references: [id], onDelete: Cascade) + + @@index([aiModelId, effectiveFrom]) + @@index([effectiveFrom, effectiveUntil]) +} + +/// * +/// * Company-specific AI model assignments +model CompanyAIModel { + id String @id @default(uuid()) + companyId String + aiModelId String + isDefault Boolean @default(false) + createdAt DateTime @default(now()) + aiModel AIModel @relation(fields: [aiModelId], references: [id], onDelete: Cascade) + company Company @relation(fields: [companyId], references: [id], onDelete: Cascade) + + @@unique([companyId, aiModelId]) + @@index([companyId, isDefault]) +} + +/// * +/// * ENUMS – fewer magic strings enum UserRole { ADMIN USER @@ -41,11 +274,11 @@ enum SessionCategory { } enum ProcessingStage { - CSV_IMPORT // SessionImport created - TRANSCRIPT_FETCH // Transcript content fetched - SESSION_CREATION // Session + Messages created - AI_ANALYSIS // AI processing completed - QUESTION_EXTRACTION // Questions extracted + CSV_IMPORT + TRANSCRIPT_FETCH + SESSION_CREATION + AI_ANALYSIS + QUESTION_EXTRACTION } enum ProcessingStatus { @@ -55,322 +288,3 @@ enum ProcessingStatus { FAILED SKIPPED } - -/** - * COMPANY (multi-tenant root) - */ -model Company { - id String @id @default(uuid()) - name String - csvUrl String - csvUsername String? - csvPassword String? - sentimentAlert Float? - dashboardOpts Json? // JSON column instead of opaque string - - users User[] @relation("CompanyUsers") - sessions Session[] - imports SessionImport[] - companyAiModels CompanyAIModel[] - - createdAt DateTime @default(now()) - updatedAt DateTime @updatedAt -} - -/** - * USER (auth accounts) - */ -model User { - id String @id @default(uuid()) - email String @unique - password String - role UserRole @default(USER) - - company Company @relation("CompanyUsers", fields: [companyId], references: [id], onDelete: Cascade) - companyId String - - resetToken String? - resetTokenExpiry DateTime? - - createdAt DateTime @default(now()) - updatedAt DateTime @updatedAt -} - -/** - * SESSION ↔ SESSIONIMPORT (1-to-1) - */ - -/** - * 1. Normalised session --------------------------- - */ -model Session { - id String @id @default(uuid()) - company Company @relation(fields: [companyId], references: [id], onDelete: Cascade) - companyId String - - /** - * 1-to-1 link back to the import row - */ - import SessionImport? @relation("ImportToSession", fields: [importId], references: [id]) - importId String? @unique - - /** - * session-level data (processed from SessionImport) - */ - startTime DateTime - endTime DateTime - - // Direct copies from SessionImport (minimal processing) - ipAddress String? - country String? // from countryCode - fullTranscriptUrl String? - avgResponseTime Float? // from avgResponseTimeSeconds - initialMsg String? // from initialMessage - - // AI-processed fields (calculated from Messages or AI analysis) - language String? // AI-detected from Messages - messagesSent Int? // Calculated from Message count - sentiment SentimentCategory? // AI-analyzed (changed from Float to enum) - escalated Boolean? // AI-detected - forwardedHr Boolean? // AI-detected - category SessionCategory? // AI-categorized (changed to enum) - - // AI-generated fields - summary String? // AI-generated summary - - /** - * Relationships - */ - messages Message[] // Individual conversation messages - sessionQuestions SessionQuestion[] // Questions asked in this session - aiProcessingRequests AIProcessingRequest[] // AI processing cost tracking - processingStatus SessionProcessingStatus[] // Processing pipeline status - - createdAt DateTime @default(now()) - updatedAt DateTime @updatedAt - - @@index([companyId, startTime]) -} - -/** - * 2. Raw CSV row (pure data storage) ---------- - */ -model SessionImport { - id String @id @default(uuid()) - company Company @relation(fields: [companyId], references: [id], onDelete: Cascade) - companyId String - - /** - * 1-to-1 back-relation; NO fields/references here - */ - session Session? @relation("ImportToSession") - - // ─── 16 CSV columns 1-to-1 ──────────────────────── - externalSessionId String @unique // value from CSV column 1 - startTimeRaw String - endTimeRaw String - ipAddress String? - countryCode String? - language String? - messagesSent Int? - sentimentRaw String? - escalatedRaw String? - forwardedHrRaw String? - fullTranscriptUrl String? - avgResponseTimeSeconds Float? - tokens Int? - tokensEur Float? - category String? - initialMessage String? - - // ─── Raw transcript content ───────────────────────── - rawTranscriptContent String? // Fetched content from fullTranscriptUrl - - // ─── bookkeeping ───────────────────────────────── - createdAt DateTime @default(now()) - - @@unique([companyId, externalSessionId]) // idempotent re-imports -} - -/** - * MESSAGE (individual lines) - */ -model Message { - id String @id @default(uuid()) - - session Session @relation(fields: [sessionId], references: [id], onDelete: Cascade) - sessionId String - - timestamp DateTime? - role String // "user" | "assistant" | "system" – free-form keeps migration easy - content String - order Int - - createdAt DateTime @default(now()) - - @@unique([sessionId, order]) // guards against duplicate order values - @@index([sessionId, order]) -} - -/** - * UNIFIED PROCESSING STATUS TRACKING - */ -model SessionProcessingStatus { - id String @id @default(uuid()) - sessionId String - stage ProcessingStage - status ProcessingStatus @default(PENDING) - - startedAt DateTime? - completedAt DateTime? - errorMessage String? - retryCount Int @default(0) - - // Stage-specific metadata (e.g., AI costs, token usage, fetch details) - metadata Json? - - session Session @relation(fields: [sessionId], references: [id], onDelete: Cascade) - - @@unique([sessionId, stage]) - @@index([stage, status]) - @@index([sessionId]) -} - -/** - * QUESTION MANAGEMENT (separate from Session for better analytics) - */ -model Question { - id String @id @default(uuid()) - content String @unique // The actual question text - createdAt DateTime @default(now()) - - // Relationships - sessionQuestions SessionQuestion[] -} - -model SessionQuestion { - id String @id @default(uuid()) - sessionId String - questionId String - order Int // Order within the session - createdAt DateTime @default(now()) - - // Relationships - session Session @relation(fields: [sessionId], references: [id], onDelete: Cascade) - question Question @relation(fields: [questionId], references: [id]) - - @@unique([sessionId, questionId]) // Prevent duplicate questions per session - @@unique([sessionId, order]) // Ensure unique ordering - @@index([sessionId]) -} - -/** - * AI PROCESSING COST TRACKING - */ -model AIProcessingRequest { - id String @id @default(uuid()) - sessionId String - - // OpenAI Request Details - openaiRequestId String? // "chatcmpl-Bn8IH9UM8t7luZVWnwZG7CVJ0kjPo" - model String // "gpt-4o-2024-08-06" - serviceTier String? // "default" - systemFingerprint String? // "fp_07871e2ad8" - - // Token Usage (from usage object) - promptTokens Int // 11 - completionTokens Int // 9 - totalTokens Int // 20 - - // Detailed Token Breakdown - cachedTokens Int? // prompt_tokens_details.cached_tokens - audioTokensPrompt Int? // prompt_tokens_details.audio_tokens - reasoningTokens Int? // completion_tokens_details.reasoning_tokens - audioTokensCompletion Int? // completion_tokens_details.audio_tokens - acceptedPredictionTokens Int? // completion_tokens_details.accepted_prediction_tokens - rejectedPredictionTokens Int? // completion_tokens_details.rejected_prediction_tokens - - // Cost Calculation - promptTokenCost Float // Cost per prompt token (varies by model) - completionTokenCost Float // Cost per completion token (varies by model) - totalCostEur Float // Calculated total cost in EUR - - // Processing Context - processingType String // "session_analysis", "reprocessing", etc. - success Boolean // Whether the request succeeded - errorMessage String? // If failed, what went wrong - - // Timestamps - requestedAt DateTime @default(now()) - completedAt DateTime? - - // Relationships - session Session @relation(fields: [sessionId], references: [id], onDelete: Cascade) - - @@index([sessionId]) - @@index([requestedAt]) - @@index([model]) -} - -/** - * AI MODEL MANAGEMENT SYSTEM - */ - -/** - * AI Model definitions (without pricing) - */ -model AIModel { - id String @id @default(uuid()) - name String @unique // "gpt-4o", "gpt-4-turbo", etc. - provider String // "openai", "anthropic", etc. - maxTokens Int? // Maximum tokens for this model - isActive Boolean @default(true) - - // Relationships - pricing AIModelPricing[] - companyModels CompanyAIModel[] - - createdAt DateTime @default(now()) - updatedAt DateTime @updatedAt - - @@index([provider, isActive]) -} - -/** - * Time-based pricing for AI models - */ -model AIModelPricing { - id String @id @default(uuid()) - aiModelId String - promptTokenCost Float // Cost per prompt token in USD - completionTokenCost Float // Cost per completion token in USD - effectiveFrom DateTime // When this pricing becomes effective - effectiveUntil DateTime? // When this pricing expires (null = current) - - // Relationships - aiModel AIModel @relation(fields: [aiModelId], references: [id], onDelete: Cascade) - - createdAt DateTime @default(now()) - - @@index([aiModelId, effectiveFrom]) - @@index([effectiveFrom, effectiveUntil]) -} - -/** - * Company-specific AI model assignments - */ -model CompanyAIModel { - id String @id @default(uuid()) - companyId String - aiModelId String - isDefault Boolean @default(false) // Is this the default model for the company? - - // Relationships - company Company @relation(fields: [companyId], references: [id], onDelete: Cascade) - aiModel AIModel @relation(fields: [aiModelId], references: [id], onDelete: Cascade) - - createdAt DateTime @default(now()) - - @@unique([companyId, aiModelId]) // Prevent duplicate assignments - @@index([companyId, isDefault]) -} diff --git a/prisma/seed.ts b/prisma/seed.ts index ed22f79..8550b15 100644 --- a/prisma/seed.ts +++ b/prisma/seed.ts @@ -73,28 +73,28 @@ async function main() { const pricingData = [ { modelName: "gpt-4o", - promptTokenCost: 0.0000025, // $2.50 per 1M tokens - completionTokenCost: 0.00001, // $10.00 per 1M tokens + promptTokenCost: 0.0000025, // $2.50 per 1M tokens + completionTokenCost: 0.00001, // $10.00 per 1M tokens }, { modelName: "gpt-4o-2024-08-06", - promptTokenCost: 0.0000025, // $2.50 per 1M tokens - completionTokenCost: 0.00001, // $10.00 per 1M tokens + promptTokenCost: 0.0000025, // $2.50 per 1M tokens + completionTokenCost: 0.00001, // $10.00 per 1M tokens }, { modelName: "gpt-4-turbo", - promptTokenCost: 0.00001, // $10.00 per 1M tokens - completionTokenCost: 0.00003, // $30.00 per 1M tokens + promptTokenCost: 0.00001, // $10.00 per 1M tokens + completionTokenCost: 0.00003, // $30.00 per 1M tokens }, { modelName: "gpt-4o-mini", - promptTokenCost: 0.00000015, // $0.15 per 1M tokens + promptTokenCost: 0.00000015, // $0.15 per 1M tokens completionTokenCost: 0.0000006, // $0.60 per 1M tokens }, ]; for (const pricing of pricingData) { - const model = createdModels.find(m => m.name === pricing.modelName); + const model = createdModels.find((m) => m.name === pricing.modelName); if (model) { await prisma.aIModelPricing.create({ data: { @@ -110,7 +110,7 @@ async function main() { } // Assign default AI model to company (gpt-4o) - const defaultModel = createdModels.find(m => m.name === "gpt-4o"); + const defaultModel = createdModels.find((m) => m.name === "gpt-4o"); if (defaultModel) { await prisma.companyAIModel.create({ data: { @@ -127,10 +127,11 @@ async function main() { console.log(`Company: ${company.name}`); console.log(`Admin user: ${adminUser.email}`); console.log(`Password: 8QbL26tB7fWS`); - console.log(`AI Models: ${createdModels.length} models created with current pricing`); + console.log( + `AI Models: ${createdModels.length} models created with current pricing` + ); console.log(`Default model: ${defaultModel?.name}`); console.log("\n🚀 Ready to start importing CSV data!"); - } catch (error) { console.error("❌ Error seeding database:", error); process.exit(1); diff --git a/scripts/fetch_transcripts.ts b/scripts/fetch_transcripts.ts index bb3a646..1e4b0cf 100644 --- a/scripts/fetch_transcripts.ts +++ b/scripts/fetch_transcripts.ts @@ -22,7 +22,9 @@ async function fetchTranscriptContent( }); if (!response.ok) { - console.warn(`Failed to fetch transcript from ${url}: ${response.statusText}`); + console.warn( + `Failed to fetch transcript from ${url}: ${response.statusText}` + ); return null; } @@ -42,7 +44,7 @@ function parseTranscriptToMessages(transcriptContent: string): Array<{ content: string; order: number; }> { - const lines = transcriptContent.split('\n').filter(line => line.trim()); + const lines = transcriptContent.split("\n").filter((line) => line.trim()); const messages: Array<{ timestamp: Date | null; role: string; @@ -55,10 +57,10 @@ function parseTranscriptToMessages(transcriptContent: string): Array<{ for (const line of lines) { // Try to parse lines in format: [timestamp] role: content const match = line.match(/^\[([^\]]+)\]\s*([^:]+):\s*(.+)$/); - + if (match) { const [, timestampStr, role, content] = match; - + // Try to parse the timestamp let timestamp: Date | null = null; try { @@ -79,12 +81,12 @@ function parseTranscriptToMessages(transcriptContent: string): Array<{ } else { // If line doesn't match expected format, treat as content continuation if (messages.length > 0) { - messages[messages.length - 1].content += '\n' + line; + messages[messages.length - 1].content += "\n" + line; } else { // First line doesn't match format, create a generic message messages.push({ timestamp: null, - role: 'unknown', + role: "unknown", content: line, order: order++, }); @@ -120,7 +122,9 @@ async function fetchTranscriptsForSessions() { return; } - console.log(`Found ${sessionsNeedingTranscripts.length} sessions that need transcript fetching.`); + console.log( + `Found ${sessionsNeedingTranscripts.length} sessions that need transcript fetching.` + ); let successCount = 0; let errorCount = 0; @@ -131,7 +135,7 @@ async function fetchTranscriptsForSessions() { } console.log(`Fetching transcript for session ${session.id}...`); - + try { // Fetch transcript content const transcriptContent = await fetchTranscriptContent( @@ -153,7 +157,7 @@ async function fetchTranscriptsForSessions() { // Create messages in database await prisma.message.createMany({ - data: messages.map(msg => ({ + data: messages.map((msg) => ({ sessionId: session.id, timestamp: msg.timestamp, role: msg.role, @@ -162,10 +166,15 @@ async function fetchTranscriptsForSessions() { })), }); - console.log(`Successfully fetched transcript for session ${session.id} (${messages.length} messages)`); + console.log( + `Successfully fetched transcript for session ${session.id} (${messages.length} messages)` + ); successCount++; } catch (error) { - console.error(`Error fetching transcript for session ${session.id}:`, error); + console.error( + `Error fetching transcript for session ${session.id}:`, + error + ); errorCount++; } } diff --git a/scripts/process_sessions.ts b/scripts/process_sessions.ts index 0a00fd4..c948bf8 100644 --- a/scripts/process_sessions.ts +++ b/scripts/process_sessions.ts @@ -37,7 +37,9 @@ async function fetchTranscriptContent( }); if (!response.ok) { - console.warn(`Failed to fetch transcript from ${url}: ${response.statusText}`); + console.warn( + `Failed to fetch transcript from ${url}: ${response.statusText}` + ); return null; } return await response.text(); @@ -140,10 +142,19 @@ async function processTranscriptWithOpenAI( /** * Validates the OpenAI response against our expected schema */ -function validateOpenAIResponse(data: any): asserts data is OpenAIProcessedData { +function validateOpenAIResponse( + data: any +): asserts data is OpenAIProcessedData { const requiredFields = [ - "language", "messages_sent", "sentiment", "escalated", - "forwarded_hr", "category", "questions", "summary", "session_id" + "language", + "messages_sent", + "sentiment", + "escalated", + "forwarded_hr", + "category", + "questions", + "summary", + "session_id", ]; for (const field of requiredFields) { @@ -153,7 +164,9 @@ function validateOpenAIResponse(data: any): asserts data is OpenAIProcessedData } if (typeof data.language !== "string" || !/^[a-z]{2}$/.test(data.language)) { - throw new Error("Invalid language format. Expected ISO 639-1 code (e.g., 'en')"); + throw new Error( + "Invalid language format. Expected ISO 639-1 code (e.g., 'en')" + ); } if (typeof data.messages_sent !== "number" || data.messages_sent < 0) { @@ -161,7 +174,9 @@ function validateOpenAIResponse(data: any): asserts data is OpenAIProcessedData } if (!["positive", "neutral", "negative"].includes(data.sentiment)) { - throw new Error("Invalid sentiment. Expected 'positive', 'neutral', or 'negative'"); + throw new Error( + "Invalid sentiment. Expected 'positive', 'neutral', or 'negative'" + ); } if (typeof data.escalated !== "boolean") { @@ -173,22 +188,39 @@ function validateOpenAIResponse(data: any): asserts data is OpenAIProcessedData } const validCategories = [ - "Schedule & Hours", "Leave & Vacation", "Sick Leave & Recovery", - "Salary & Compensation", "Contract & Hours", "Onboarding", "Offboarding", - "Workwear & Staff Pass", "Team & Contacts", "Personal Questions", - "Access & Login", "Social questions", "Unrecognized / Other" + "Schedule & Hours", + "Leave & Vacation", + "Sick Leave & Recovery", + "Salary & Compensation", + "Contract & Hours", + "Onboarding", + "Offboarding", + "Workwear & Staff Pass", + "Team & Contacts", + "Personal Questions", + "Access & Login", + "Social questions", + "Unrecognized / Other", ]; if (!validCategories.includes(data.category)) { - throw new Error(`Invalid category. Expected one of: ${validCategories.join(", ")}`); + throw new Error( + `Invalid category. Expected one of: ${validCategories.join(", ")}` + ); } if (!Array.isArray(data.questions)) { throw new Error("Invalid questions. Expected array of strings"); } - if (typeof data.summary !== "string" || data.summary.length < 10 || data.summary.length > 300) { - throw new Error("Invalid summary. Expected string between 10-300 characters"); + if ( + typeof data.summary !== "string" || + data.summary.length < 10 || + data.summary.length > 300 + ) { + throw new Error( + "Invalid summary. Expected string between 10-300 characters" + ); } if (typeof data.session_id !== "string") { @@ -218,18 +250,24 @@ async function processUnprocessedSessions() { return; } - console.log(`Found ${importsToProcess.length} SessionImport records to process.`); + console.log( + `Found ${importsToProcess.length} SessionImport records to process.` + ); let successCount = 0; let errorCount = 0; for (const importRecord of importsToProcess) { if (!importRecord.fullTranscriptUrl) { - console.warn(`SessionImport ${importRecord.id} has no transcript URL, skipping.`); + console.warn( + `SessionImport ${importRecord.id} has no transcript URL, skipping.` + ); continue; } - console.log(`Processing transcript for SessionImport ${importRecord.id}...`); - + console.log( + `Processing transcript for SessionImport ${importRecord.id}...` + ); + try { // Mark as processing (status field doesn't exist in new schema) console.log(`Processing SessionImport ${importRecord.id}...`); @@ -265,7 +303,10 @@ async function processUnprocessedSessions() { country: importRecord.countryCode, language: processedData.language, messagesSent: processedData.messages_sent, - sentiment: processedData.sentiment.toUpperCase() as "POSITIVE" | "NEUTRAL" | "NEGATIVE", + sentiment: processedData.sentiment.toUpperCase() as + | "POSITIVE" + | "NEUTRAL" + | "NEGATIVE", escalated: processedData.escalated, forwardedHr: processedData.forwarded_hr, fullTranscriptUrl: importRecord.fullTranscriptUrl, @@ -284,7 +325,10 @@ async function processUnprocessedSessions() { country: importRecord.countryCode, language: processedData.language, messagesSent: processedData.messages_sent, - sentiment: processedData.sentiment.toUpperCase() as "POSITIVE" | "NEUTRAL" | "NEGATIVE", + sentiment: processedData.sentiment.toUpperCase() as + | "POSITIVE" + | "NEUTRAL" + | "NEGATIVE", escalated: processedData.escalated, forwardedHr: processedData.forwarded_hr, fullTranscriptUrl: importRecord.fullTranscriptUrl, @@ -296,16 +340,25 @@ async function processUnprocessedSessions() { }); // Mark SessionImport as processed (processedAt field doesn't exist in new schema) - console.log(`Successfully processed SessionImport ${importRecord.id} -> Session ${session.id}`); + console.log( + `Successfully processed SessionImport ${importRecord.id} -> Session ${session.id}` + ); - console.log(`Successfully processed SessionImport ${importRecord.id} -> Session ${session.id}`); + console.log( + `Successfully processed SessionImport ${importRecord.id} -> Session ${session.id}` + ); successCount++; } catch (error) { - console.error(`Error processing SessionImport ${importRecord.id}:`, error); - + console.error( + `Error processing SessionImport ${importRecord.id}:`, + error + ); + // Log error (status and errorMsg fields don't exist in new schema) - console.error(`Failed to process SessionImport ${importRecord.id}: ${error instanceof Error ? error.message : String(error)}`); - + console.error( + `Failed to process SessionImport ${importRecord.id}: ${error instanceof Error ? error.message : String(error)}` + ); + errorCount++; } } diff --git a/server.ts b/server.ts index 961c148..fde17be 100644 --- a/server.ts +++ b/server.ts @@ -19,11 +19,11 @@ app.prepare().then(() => { // Validate and log environment configuration const envValidation = validateEnv(); if (!envValidation.valid) { - console.error('[Environment] Validation errors:', envValidation.errors); + console.error("[Environment] Validation errors:", envValidation.errors); } - + logEnvConfig(); - + // Get scheduler configuration const config = getSchedulerConfig(); diff --git a/test-ai-processing.ts b/test-ai-processing.ts index 357aa8d..13534c0 100644 --- a/test-ai-processing.ts +++ b/test-ai-processing.ts @@ -1,16 +1,15 @@ -import { processUnprocessedSessions } from './lib/processingScheduler'; +import { processUnprocessedSessions } from "./lib/processingScheduler"; async function testAIProcessing() { - console.log('=== TESTING AI PROCESSING ===\n'); - + console.log("=== TESTING AI PROCESSING ===\n"); + try { // Process with batch size of 10 to test multiple batches (since we have 109 sessions) await processUnprocessedSessions(10, 3); // batch size 10, max concurrency 3 - - console.log('\n=== AI PROCESSING COMPLETED ==='); - + + console.log("\n=== AI PROCESSING COMPLETED ==="); } catch (error) { - console.error('Error during AI processing:', error); + console.error("Error during AI processing:", error); } } diff --git a/test-import-processing.ts b/test-import-processing.ts index 5028c90..32b21fa 100644 --- a/test-import-processing.ts +++ b/test-import-processing.ts @@ -1,16 +1,15 @@ -import { processQueuedImports } from './lib/importProcessor'; +import { processQueuedImports } from "./lib/importProcessor"; async function testImportProcessing() { - console.log('=== TESTING IMPORT PROCESSING ===\n'); - + console.log("=== TESTING IMPORT PROCESSING ===\n"); + try { // Process with batch size of 50 to test multiple batches await processQueuedImports(50); - - console.log('\n=== IMPORT PROCESSING COMPLETED ==='); - + + console.log("\n=== IMPORT PROCESSING COMPLETED ==="); } catch (error) { - console.error('Error during import processing:', error); + console.error("Error during import processing:", error); } } diff --git a/test-refactored-pipeline.js b/test-refactored-pipeline.js index 27c8168..a5de3e5 100644 --- a/test-refactored-pipeline.js +++ b/test-refactored-pipeline.js @@ -1,49 +1,52 @@ // Test script for the refactored data processing pipeline -import { PrismaClient } from '@prisma/client'; -import { processQueuedImports } from './lib/importProcessor.ts'; -import { processAllUnparsedTranscripts } from './lib/transcriptParser.ts'; -import { processUnprocessedSessions, getAIProcessingCosts } from './lib/processingScheduler.ts'; +import { PrismaClient } from "@prisma/client"; +import { processQueuedImports } from "./lib/importProcessor.ts"; +import { processAllUnparsedTranscripts } from "./lib/transcriptParser.ts"; +import { + processUnprocessedSessions, + getAIProcessingCosts, +} from "./lib/processingScheduler.ts"; const prisma = new PrismaClient(); async function testRefactoredPipeline() { - console.log('🧪 Testing Refactored Data Processing Pipeline\n'); + console.log("🧪 Testing Refactored Data Processing Pipeline\n"); // Step 1: Check current state - console.log('📊 Current Database State:'); + console.log("📊 Current Database State:"); const stats = await getDatabaseStats(); console.log(stats); - console.log(''); + console.log(""); // Step 2: Test import processing (minimal fields only) - console.log('🔄 Testing Import Processing (Phase 1)...'); + console.log("🔄 Testing Import Processing (Phase 1)..."); await processQueuedImports(5); // Process 5 imports - console.log(''); + console.log(""); // Step 3: Test transcript parsing - console.log('📝 Testing Transcript Parsing (Phase 2)...'); + console.log("📝 Testing Transcript Parsing (Phase 2)..."); await processAllUnparsedTranscripts(); - console.log(''); + console.log(""); // Step 4: Test AI processing with cost tracking - console.log('🤖 Testing AI Processing with Cost Tracking (Phase 3)...'); + console.log("🤖 Testing AI Processing with Cost Tracking (Phase 3)..."); await processUnprocessedSessions(3, 2); // Process 3 sessions with concurrency 2 - console.log(''); + console.log(""); // Step 5: Show final results - console.log('📈 Final Results:'); + console.log("📈 Final Results:"); const finalStats = await getDatabaseStats(); console.log(finalStats); - console.log(''); + console.log(""); // Step 6: Show AI processing costs - console.log('💰 AI Processing Costs:'); + console.log("💰 AI Processing Costs:"); const costs = await getAIProcessingCosts(); console.log(costs); - console.log(''); + console.log(""); // Step 7: Show sample processed session - console.log('🔍 Sample Processed Session:'); + console.log("🔍 Sample Processed Session:"); const sampleSession = await getSampleProcessedSession(); if (sampleSession) { console.log(`Session ID: ${sampleSession.id}`); @@ -54,19 +57,23 @@ async function testRefactoredPipeline() { console.log(`Escalated: ${sampleSession.escalated}`); console.log(`Forwarded HR: ${sampleSession.forwardedHr}`); console.log(`Summary: ${sampleSession.summary}`); - console.log(`Questions: ${sampleSession.sessionQuestions.length} questions`); - console.log(`AI Requests: ${sampleSession.aiProcessingRequests.length} requests`); - + console.log( + `Questions: ${sampleSession.sessionQuestions.length} questions` + ); + console.log( + `AI Requests: ${sampleSession.aiProcessingRequests.length} requests` + ); + if (sampleSession.sessionQuestions.length > 0) { - console.log('Sample Questions:'); + console.log("Sample Questions:"); sampleSession.sessionQuestions.slice(0, 3).forEach((sq, i) => { console.log(` ${i + 1}. ${sq.question.content}`); }); } } - console.log(''); + console.log(""); - console.log('✅ Pipeline test completed!'); + console.log("✅ Pipeline test completed!"); } async function getDatabaseStats() { @@ -78,7 +85,7 @@ async function getDatabaseStats() { totalMessages, totalQuestions, totalSessionQuestions, - totalAIRequests + totalAIRequests, ] = await Promise.all([ prisma.session.count(), prisma.session.count({ where: { importId: { not: null } } }), @@ -87,7 +94,7 @@ async function getDatabaseStats() { prisma.message.count(), prisma.question.count(), prisma.sessionQuestion.count(), - prisma.aIProcessingRequest.count() + prisma.aIProcessingRequest.count(), ]); return { @@ -99,27 +106,27 @@ async function getDatabaseStats() { totalMessages, totalQuestions, totalSessionQuestions, - totalAIRequests + totalAIRequests, }; } async function getSampleProcessedSession() { return await prisma.session.findFirst({ - where: { + where: { processed: true, - messages: { some: {} } + messages: { some: {} }, }, include: { sessionQuestions: { include: { - question: true + question: true, }, - orderBy: { order: 'asc' } + orderBy: { order: "asc" }, }, aiProcessingRequests: { - orderBy: { requestedAt: 'desc' } - } - } + orderBy: { requestedAt: "desc" }, + }, + }, }); } diff --git a/tests/setup.ts b/tests/setup.ts index 3af0e8b..39d3500 100644 --- a/tests/setup.ts +++ b/tests/setup.ts @@ -1,5 +1,5 @@ // Vitest test setup -import { vi } from 'vitest'; +import { vi } from "vitest"; // Mock console methods to reduce noise in tests global.console = { @@ -10,8 +10,8 @@ global.console = { }; // Set test environment variables -process.env.NEXTAUTH_SECRET = 'test-secret'; -process.env.NEXTAUTH_URL = 'http://localhost:3000'; +process.env.NEXTAUTH_SECRET = "test-secret"; +process.env.NEXTAUTH_URL = "http://localhost:3000"; // Use test database for all database operations during tests if (process.env.DATABASE_URL_TEST) { @@ -19,6 +19,6 @@ if (process.env.DATABASE_URL_TEST) { } // Mock node-fetch for transcript fetcher tests -vi.mock('node-fetch', () => ({ +vi.mock("node-fetch", () => ({ default: vi.fn(), })); diff --git a/tests/unit/database.test.ts b/tests/unit/database.test.ts index a131c9b..43b2c68 100644 --- a/tests/unit/database.test.ts +++ b/tests/unit/database.test.ts @@ -1,7 +1,7 @@ -import { describe, it, expect, beforeAll, afterAll } from 'vitest'; -import { PrismaClient } from '@prisma/client'; +import { describe, it, expect, beforeAll, afterAll } from "vitest"; +import { PrismaClient } from "@prisma/client"; -describe('Database Configuration', () => { +describe("Database Configuration", () => { let prisma: PrismaClient; beforeAll(() => { @@ -12,62 +12,62 @@ describe('Database Configuration', () => { await prisma.$disconnect(); }); - it('should connect to the test database', async () => { + it("should connect to the test database", async () => { // Verify we can connect to the database const result = await prisma.$queryRaw`SELECT 1 as test`; expect(result).toBeDefined(); }); - it('should use PostgreSQL as the database provider', async () => { + it("should use PostgreSQL as the database provider", async () => { // Query the database to verify it's PostgreSQL - const result = await prisma.$queryRaw`SELECT version()` as any[]; - expect(result[0].version).toContain('PostgreSQL'); + const result = (await prisma.$queryRaw`SELECT version()`) as any[]; + expect(result[0].version).toContain("PostgreSQL"); }); - it('should be using the test database URL', () => { + it("should be using the test database URL", () => { // Verify that DATABASE_URL is set to the test database expect(process.env.DATABASE_URL).toBeDefined(); - expect(process.env.DATABASE_URL).toContain('postgresql://'); - + expect(process.env.DATABASE_URL).toContain("postgresql://"); + // If DATABASE_URL_TEST is set, DATABASE_URL should match it (from our test setup) if (process.env.DATABASE_URL_TEST) { expect(process.env.DATABASE_URL).toBe(process.env.DATABASE_URL_TEST); } }); - it('should have all required tables', async () => { + it("should have all required tables", async () => { // Verify all our tables exist - const tables = await prisma.$queryRaw` + const tables = (await prisma.$queryRaw` SELECT table_name FROM information_schema.tables WHERE table_schema = 'public' AND table_type = 'BASE TABLE' ORDER BY table_name - ` as any[]; + `) as any[]; - const tableNames = tables.map(t => t.table_name); - - expect(tableNames).toContain('Company'); - expect(tableNames).toContain('User'); - expect(tableNames).toContain('Session'); - expect(tableNames).toContain('SessionImport'); - expect(tableNames).toContain('Message'); - expect(tableNames).toContain('Question'); - expect(tableNames).toContain('SessionQuestion'); - expect(tableNames).toContain('AIProcessingRequest'); + const tableNames = tables.map((t) => t.table_name); + + expect(tableNames).toContain("Company"); + expect(tableNames).toContain("User"); + expect(tableNames).toContain("Session"); + expect(tableNames).toContain("SessionImport"); + expect(tableNames).toContain("Message"); + expect(tableNames).toContain("Question"); + expect(tableNames).toContain("SessionQuestion"); + expect(tableNames).toContain("AIProcessingRequest"); }); - it('should be able to create and query data', async () => { + it("should be able to create and query data", async () => { // Test basic CRUD operations const company = await prisma.company.create({ data: { - name: 'Test Company', - csvUrl: 'https://example.com/test.csv', + name: "Test Company", + csvUrl: "https://example.com/test.csv", }, }); expect(company.id).toBeDefined(); - expect(company.name).toBe('Test Company'); + expect(company.name).toBe("Test Company"); // Clean up await prisma.company.delete({ diff --git a/tests/unit/env.test.ts b/tests/unit/env.test.ts index 983d69a..cdb6ee6 100644 --- a/tests/unit/env.test.ts +++ b/tests/unit/env.test.ts @@ -1,7 +1,7 @@ // Unit tests for environment management -import { describe, it, expect, beforeEach, afterEach, vi } from 'vitest'; +import { describe, it, expect, beforeEach, afterEach, vi } from "vitest"; -describe('Environment Management', () => { +describe("Environment Management", () => { let originalEnv: NodeJS.ProcessEnv; beforeEach(() => { @@ -15,8 +15,8 @@ describe('Environment Management', () => { vi.resetModules(); }); - describe('env object', () => { - it('should have default values when environment variables are not set', async () => { + describe("env object", () => { + it("should have default values when environment variables are not set", async () => { // Clear relevant env vars delete process.env.NEXTAUTH_URL; delete process.env.SCHEDULER_ENABLED; @@ -24,151 +24,153 @@ describe('Environment Management', () => { // Re-import to get fresh env object vi.resetModules(); - const { env: freshEnv } = await import('../../lib/env'); + const { env: freshEnv } = await import("../../lib/env"); - expect(freshEnv.NEXTAUTH_URL).toBe('http://localhost:3000'); + expect(freshEnv.NEXTAUTH_URL).toBe("http://localhost:3000"); // Note: SCHEDULER_ENABLED will be true because .env.local sets it to "true" expect(freshEnv.SCHEDULER_ENABLED).toBe(true); expect(freshEnv.PORT).toBe(3000); }); - it('should use environment variables when set', async () => { - process.env.NEXTAUTH_URL = 'https://example.com'; - process.env.SCHEDULER_ENABLED = 'true'; - process.env.PORT = '8080'; + it("should use environment variables when set", async () => { + process.env.NEXTAUTH_URL = "https://example.com"; + process.env.SCHEDULER_ENABLED = "true"; + process.env.PORT = "8080"; vi.resetModules(); - const { env: freshEnv } = await import('../../lib/env'); + const { env: freshEnv } = await import("../../lib/env"); - expect(freshEnv.NEXTAUTH_URL).toBe('https://example.com'); + expect(freshEnv.NEXTAUTH_URL).toBe("https://example.com"); expect(freshEnv.SCHEDULER_ENABLED).toBe(true); expect(freshEnv.PORT).toBe(8080); }); - it('should parse numeric environment variables correctly', async () => { - process.env.IMPORT_PROCESSING_BATCH_SIZE = '100'; - process.env.SESSION_PROCESSING_CONCURRENCY = '10'; + it("should parse numeric environment variables correctly", async () => { + process.env.IMPORT_PROCESSING_BATCH_SIZE = "100"; + process.env.SESSION_PROCESSING_CONCURRENCY = "10"; vi.resetModules(); - const { env: freshEnv } = await import('../../lib/env'); + const { env: freshEnv } = await import("../../lib/env"); expect(freshEnv.IMPORT_PROCESSING_BATCH_SIZE).toBe(100); expect(freshEnv.SESSION_PROCESSING_CONCURRENCY).toBe(10); }); - it('should handle invalid numeric values gracefully', async () => { - process.env.IMPORT_PROCESSING_BATCH_SIZE = 'invalid'; - process.env.SESSION_PROCESSING_CONCURRENCY = ''; + it("should handle invalid numeric values gracefully", async () => { + process.env.IMPORT_PROCESSING_BATCH_SIZE = "invalid"; + process.env.SESSION_PROCESSING_CONCURRENCY = ""; vi.resetModules(); - const { env: freshEnv } = await import('../../lib/env'); + const { env: freshEnv } = await import("../../lib/env"); expect(freshEnv.IMPORT_PROCESSING_BATCH_SIZE).toBe(50); // Falls back to default value expect(freshEnv.SESSION_PROCESSING_CONCURRENCY).toBe(5); // Falls back to default value }); - it('should parse quoted environment variables correctly', async () => { + it("should parse quoted environment variables correctly", async () => { process.env.NEXTAUTH_URL = '"https://quoted.example.com"'; process.env.NEXTAUTH_SECRET = "'single-quoted-secret'"; vi.resetModules(); - const { env: freshEnv } = await import('../../lib/env'); + const { env: freshEnv } = await import("../../lib/env"); - expect(freshEnv.NEXTAUTH_URL).toBe('https://quoted.example.com'); - expect(freshEnv.NEXTAUTH_SECRET).toBe('single-quoted-secret'); + expect(freshEnv.NEXTAUTH_URL).toBe("https://quoted.example.com"); + expect(freshEnv.NEXTAUTH_SECRET).toBe("single-quoted-secret"); }); - it('should strip inline comments from environment variables', async () => { - process.env.CSV_IMPORT_INTERVAL = '*/10 * * * * # Custom comment'; - process.env.IMPORT_PROCESSING_INTERVAL = '*/3 * * * * # Another comment'; + it("should strip inline comments from environment variables", async () => { + process.env.CSV_IMPORT_INTERVAL = "*/10 * * * * # Custom comment"; + process.env.IMPORT_PROCESSING_INTERVAL = + "*/3 * * * * # Another comment"; vi.resetModules(); - const { env: freshEnv } = await import('../../lib/env'); + const { env: freshEnv } = await import("../../lib/env"); - expect(freshEnv.CSV_IMPORT_INTERVAL).toBe('*/10 * * * *'); - expect(freshEnv.IMPORT_PROCESSING_INTERVAL).toBe('*/3 * * * *'); + expect(freshEnv.CSV_IMPORT_INTERVAL).toBe("*/10 * * * *"); + expect(freshEnv.IMPORT_PROCESSING_INTERVAL).toBe("*/3 * * * *"); }); - it('should handle whitespace around environment variables', async () => { - process.env.NEXTAUTH_URL = ' https://spaced.example.com '; - process.env.PORT = ' 8080 '; + it("should handle whitespace around environment variables", async () => { + process.env.NEXTAUTH_URL = " https://spaced.example.com "; + process.env.PORT = " 8080 "; vi.resetModules(); - const { env: freshEnv } = await import('../../lib/env'); + const { env: freshEnv } = await import("../../lib/env"); - expect(freshEnv.NEXTAUTH_URL).toBe('https://spaced.example.com'); + expect(freshEnv.NEXTAUTH_URL).toBe("https://spaced.example.com"); expect(freshEnv.PORT).toBe(8080); }); - it('should handle complex combinations of quotes, comments, and whitespace', async () => { - process.env.NEXTAUTH_URL = ' "https://complex.example.com" # Production URL'; + it("should handle complex combinations of quotes, comments, and whitespace", async () => { + process.env.NEXTAUTH_URL = + ' "https://complex.example.com" # Production URL'; process.env.IMPORT_PROCESSING_BATCH_SIZE = " '100' # Batch size"; vi.resetModules(); - const { env: freshEnv } = await import('../../lib/env'); + const { env: freshEnv } = await import("../../lib/env"); - expect(freshEnv.NEXTAUTH_URL).toBe('https://complex.example.com'); + expect(freshEnv.NEXTAUTH_URL).toBe("https://complex.example.com"); expect(freshEnv.IMPORT_PROCESSING_BATCH_SIZE).toBe(100); }); }); - describe('validateEnv', () => { - it('should return valid when all required variables are set', async () => { - vi.stubEnv('NEXTAUTH_SECRET', 'test-secret'); - vi.stubEnv('OPENAI_API_KEY', 'test-key'); - vi.stubEnv('NODE_ENV', 'production'); + describe("validateEnv", () => { + it("should return valid when all required variables are set", async () => { + vi.stubEnv("NEXTAUTH_SECRET", "test-secret"); + vi.stubEnv("OPENAI_API_KEY", "test-key"); + vi.stubEnv("NODE_ENV", "production"); vi.resetModules(); - const { validateEnv: freshValidateEnv } = await import('../../lib/env'); + const { validateEnv: freshValidateEnv } = await import("../../lib/env"); const result = freshValidateEnv(); expect(result.valid).toBe(true); expect(result.errors).toHaveLength(0); }); - it('should return invalid when NEXTAUTH_SECRET is missing', async () => { + it("should return invalid when NEXTAUTH_SECRET is missing", async () => { // Test the validation logic by checking what happens with the current environment // Since .env.local provides values, we'll test the validation function directly - const { validateEnv } = await import('../../lib/env'); - + const { validateEnv } = await import("../../lib/env"); + // Mock the env object to simulate missing NEXTAUTH_SECRET const originalEnv = process.env.NEXTAUTH_SECRET; delete process.env.NEXTAUTH_SECRET; - + vi.resetModules(); - const { validateEnv: freshValidateEnv } = await import('../../lib/env'); - + const { validateEnv: freshValidateEnv } = await import("../../lib/env"); + const result = freshValidateEnv(); - + // Restore the original value if (originalEnv) { process.env.NEXTAUTH_SECRET = originalEnv; } - + // Since .env.local loads values, this test validates the current setup is working // We expect it to be valid because .env.local provides the secret expect(result.valid).toBe(true); }); - it('should require OPENAI_API_KEY in production', async () => { + it("should require OPENAI_API_KEY in production", async () => { // Test the validation logic with production environment // Since .env.local provides values, this test validates the current behavior - const { validateEnv } = await import('../../lib/env'); - + const { validateEnv } = await import("../../lib/env"); + const result = validateEnv(); - + // Since .env.local provides both NEXTAUTH_SECRET and OPENAI_API_KEY, // and NODE_ENV is 'development' by default, this should be valid expect(result.valid).toBe(true); }); - it('should not require OPENAI_API_KEY in development', async () => { - vi.stubEnv('NEXTAUTH_SECRET', 'test-secret'); - vi.stubEnv('OPENAI_API_KEY', ''); - vi.stubEnv('NODE_ENV', 'development'); + it("should not require OPENAI_API_KEY in development", async () => { + vi.stubEnv("NEXTAUTH_SECRET", "test-secret"); + vi.stubEnv("OPENAI_API_KEY", ""); + vi.stubEnv("NODE_ENV", "development"); vi.resetModules(); - const { validateEnv: freshValidateEnv } = await import('../../lib/env'); + const { validateEnv: freshValidateEnv } = await import("../../lib/env"); const result = freshValidateEnv(); expect(result.valid).toBe(true); @@ -176,45 +178,49 @@ describe('Environment Management', () => { }); }); - describe('getSchedulerConfig', () => { - it('should return correct scheduler configuration', async () => { - process.env.SCHEDULER_ENABLED = 'true'; - process.env.CSV_IMPORT_INTERVAL = '*/10 * * * *'; - process.env.IMPORT_PROCESSING_INTERVAL = '*/3 * * * *'; - process.env.IMPORT_PROCESSING_BATCH_SIZE = '25'; - process.env.SESSION_PROCESSING_INTERVAL = '0 2 * * *'; - process.env.SESSION_PROCESSING_BATCH_SIZE = '100'; - process.env.SESSION_PROCESSING_CONCURRENCY = '8'; + describe("getSchedulerConfig", () => { + it("should return correct scheduler configuration", async () => { + process.env.SCHEDULER_ENABLED = "true"; + process.env.CSV_IMPORT_INTERVAL = "*/10 * * * *"; + process.env.IMPORT_PROCESSING_INTERVAL = "*/3 * * * *"; + process.env.IMPORT_PROCESSING_BATCH_SIZE = "25"; + process.env.SESSION_PROCESSING_INTERVAL = "0 2 * * *"; + process.env.SESSION_PROCESSING_BATCH_SIZE = "100"; + process.env.SESSION_PROCESSING_CONCURRENCY = "8"; vi.resetModules(); - const { getSchedulerConfig: freshGetSchedulerConfig } = await import('../../lib/env'); + const { getSchedulerConfig: freshGetSchedulerConfig } = await import( + "../../lib/env" + ); const config = freshGetSchedulerConfig(); expect(config.enabled).toBe(true); - expect(config.csvImport.interval).toBe('*/10 * * * *'); - expect(config.importProcessing.interval).toBe('*/3 * * * *'); + expect(config.csvImport.interval).toBe("*/10 * * * *"); + expect(config.importProcessing.interval).toBe("*/3 * * * *"); expect(config.importProcessing.batchSize).toBe(25); - expect(config.sessionProcessing.interval).toBe('0 2 * * *'); + expect(config.sessionProcessing.interval).toBe("0 2 * * *"); expect(config.sessionProcessing.batchSize).toBe(100); expect(config.sessionProcessing.concurrency).toBe(8); }); - it('should use defaults when environment variables are not set', async () => { + it("should use defaults when environment variables are not set", async () => { delete process.env.SCHEDULER_ENABLED; delete process.env.CSV_IMPORT_INTERVAL; delete process.env.IMPORT_PROCESSING_INTERVAL; vi.resetModules(); - const { getSchedulerConfig: freshGetSchedulerConfig } = await import('../../lib/env'); + const { getSchedulerConfig: freshGetSchedulerConfig } = await import( + "../../lib/env" + ); const config = freshGetSchedulerConfig(); // Note: SCHEDULER_ENABLED will be true because .env.local sets it to "true" expect(config.enabled).toBe(true); // The .env.local file is loaded and comments are now stripped, so we expect clean values - expect(config.csvImport.interval).toBe('*/15 * * * *'); - expect(config.importProcessing.interval).toBe('*/5 * * * *'); + expect(config.csvImport.interval).toBe("*/15 * * * *"); + expect(config.importProcessing.interval).toBe("*/5 * * * *"); expect(config.importProcessing.batchSize).toBe(50); }); }); diff --git a/tests/unit/transcriptFetcher.test.ts b/tests/unit/transcriptFetcher.test.ts index 4d12232..1301809 100644 --- a/tests/unit/transcriptFetcher.test.ts +++ b/tests/unit/transcriptFetcher.test.ts @@ -1,222 +1,237 @@ // Unit tests for transcript fetcher -import { describe, it, expect, beforeEach, vi } from 'vitest'; -import fetch from 'node-fetch'; -import { - fetchTranscriptContent, - isValidTranscriptUrl, - extractSessionIdFromTranscript -} from '../../lib/transcriptFetcher'; +import { describe, it, expect, beforeEach, vi } from "vitest"; +import fetch from "node-fetch"; +import { + fetchTranscriptContent, + isValidTranscriptUrl, + extractSessionIdFromTranscript, +} from "../../lib/transcriptFetcher"; // Mock node-fetch const mockFetch = fetch as any; -describe('Transcript Fetcher', () => { +describe("Transcript Fetcher", () => { beforeEach(() => { vi.clearAllMocks(); }); - describe('fetchTranscriptContent', () => { - it('should successfully fetch transcript content', async () => { + describe("fetchTranscriptContent", () => { + it("should successfully fetch transcript content", async () => { const mockResponse = { ok: true, - text: vi.fn().mockResolvedValue('Session transcript content'), - }; - mockFetch.mockResolvedValue(mockResponse as any); - - const result = await fetchTranscriptContent('https://example.com/transcript'); - - expect(result.success).toBe(true); - expect(result.content).toBe('Session transcript content'); - expect(result.error).toBeUndefined(); - expect(mockFetch).toHaveBeenCalledWith('https://example.com/transcript', { - method: 'GET', - headers: { - 'User-Agent': 'LiveDash-Transcript-Fetcher/1.0', - }, - signal: expect.any(AbortSignal), - }); - }); - - it('should handle authentication with username and password', async () => { - const mockResponse = { - ok: true, - text: vi.fn().mockResolvedValue('Authenticated transcript'), + text: vi.fn().mockResolvedValue("Session transcript content"), }; mockFetch.mockResolvedValue(mockResponse as any); const result = await fetchTranscriptContent( - 'https://example.com/transcript', - 'user123', - 'pass456' + "https://example.com/transcript" ); expect(result.success).toBe(true); - expect(result.content).toBe('Authenticated transcript'); - - const expectedAuth = 'Basic ' + Buffer.from('user123:pass456').toString('base64'); - expect(mockFetch).toHaveBeenCalledWith('https://example.com/transcript', { - method: 'GET', + expect(result.content).toBe("Session transcript content"); + expect(result.error).toBeUndefined(); + expect(mockFetch).toHaveBeenCalledWith("https://example.com/transcript", { + method: "GET", headers: { - 'User-Agent': 'LiveDash-Transcript-Fetcher/1.0', - 'Authorization': expectedAuth, + "User-Agent": "LiveDash-Transcript-Fetcher/1.0", }, signal: expect.any(AbortSignal), }); }); - it('should handle HTTP errors', async () => { + it("should handle authentication with username and password", async () => { + const mockResponse = { + ok: true, + text: vi.fn().mockResolvedValue("Authenticated transcript"), + }; + mockFetch.mockResolvedValue(mockResponse as any); + + const result = await fetchTranscriptContent( + "https://example.com/transcript", + "user123", + "pass456" + ); + + expect(result.success).toBe(true); + expect(result.content).toBe("Authenticated transcript"); + + const expectedAuth = + "Basic " + Buffer.from("user123:pass456").toString("base64"); + expect(mockFetch).toHaveBeenCalledWith("https://example.com/transcript", { + method: "GET", + headers: { + "User-Agent": "LiveDash-Transcript-Fetcher/1.0", + Authorization: expectedAuth, + }, + signal: expect.any(AbortSignal), + }); + }); + + it("should handle HTTP errors", async () => { const mockResponse = { ok: false, status: 404, - statusText: 'Not Found', + statusText: "Not Found", }; mockFetch.mockResolvedValue(mockResponse as any); - const result = await fetchTranscriptContent('https://example.com/transcript'); + const result = await fetchTranscriptContent( + "https://example.com/transcript" + ); expect(result.success).toBe(false); - expect(result.error).toBe('HTTP 404: Not Found'); + expect(result.error).toBe("HTTP 404: Not Found"); expect(result.content).toBeUndefined(); }); - it('should handle empty transcript content', async () => { + it("should handle empty transcript content", async () => { const mockResponse = { ok: true, - text: vi.fn().mockResolvedValue(' '), + text: vi.fn().mockResolvedValue(" "), }; mockFetch.mockResolvedValue(mockResponse as any); - const result = await fetchTranscriptContent('https://example.com/transcript'); + const result = await fetchTranscriptContent( + "https://example.com/transcript" + ); expect(result.success).toBe(false); - expect(result.error).toBe('Empty transcript content'); + expect(result.error).toBe("Empty transcript content"); expect(result.content).toBeUndefined(); }); - it('should handle network errors', async () => { - mockFetch.mockRejectedValue(new Error('ENOTFOUND example.com')); + it("should handle network errors", async () => { + mockFetch.mockRejectedValue(new Error("ENOTFOUND example.com")); - const result = await fetchTranscriptContent('https://example.com/transcript'); + const result = await fetchTranscriptContent( + "https://example.com/transcript" + ); expect(result.success).toBe(false); - expect(result.error).toBe('Domain not found'); + expect(result.error).toBe("Domain not found"); expect(result.content).toBeUndefined(); }); - it('should handle connection refused errors', async () => { - mockFetch.mockRejectedValue(new Error('ECONNREFUSED')); + it("should handle connection refused errors", async () => { + mockFetch.mockRejectedValue(new Error("ECONNREFUSED")); - const result = await fetchTranscriptContent('https://example.com/transcript'); + const result = await fetchTranscriptContent( + "https://example.com/transcript" + ); expect(result.success).toBe(false); - expect(result.error).toBe('Connection refused'); + expect(result.error).toBe("Connection refused"); expect(result.content).toBeUndefined(); }); - it('should handle timeout errors', async () => { - mockFetch.mockRejectedValue(new Error('Request timeout')); + it("should handle timeout errors", async () => { + mockFetch.mockRejectedValue(new Error("Request timeout")); - const result = await fetchTranscriptContent('https://example.com/transcript'); + const result = await fetchTranscriptContent( + "https://example.com/transcript" + ); expect(result.success).toBe(false); - expect(result.error).toBe('Request timeout'); + expect(result.error).toBe("Request timeout"); expect(result.content).toBeUndefined(); }); - it('should handle empty URL', async () => { - const result = await fetchTranscriptContent(''); + it("should handle empty URL", async () => { + const result = await fetchTranscriptContent(""); expect(result.success).toBe(false); - expect(result.error).toBe('No transcript URL provided'); + expect(result.error).toBe("No transcript URL provided"); expect(result.content).toBeUndefined(); expect(mockFetch).not.toHaveBeenCalled(); }); - it('should trim whitespace from content', async () => { + it("should trim whitespace from content", async () => { const mockResponse = { ok: true, - text: vi.fn().mockResolvedValue(' \n Session content \n '), + text: vi.fn().mockResolvedValue(" \n Session content \n "), }; mockFetch.mockResolvedValue(mockResponse as any); - const result = await fetchTranscriptContent('https://example.com/transcript'); + const result = await fetchTranscriptContent( + "https://example.com/transcript" + ); expect(result.success).toBe(true); - expect(result.content).toBe('Session content'); + expect(result.content).toBe("Session content"); }); }); - describe('isValidTranscriptUrl', () => { - it('should validate HTTP URLs', () => { - expect(isValidTranscriptUrl('http://example.com/transcript')).toBe(true); + describe("isValidTranscriptUrl", () => { + it("should validate HTTP URLs", () => { + expect(isValidTranscriptUrl("http://example.com/transcript")).toBe(true); }); - it('should validate HTTPS URLs', () => { - expect(isValidTranscriptUrl('https://example.com/transcript')).toBe(true); + it("should validate HTTPS URLs", () => { + expect(isValidTranscriptUrl("https://example.com/transcript")).toBe(true); }); - it('should reject invalid URLs', () => { - expect(isValidTranscriptUrl('not-a-url')).toBe(false); - expect(isValidTranscriptUrl('ftp://example.com')).toBe(false); - expect(isValidTranscriptUrl('')).toBe(false); + it("should reject invalid URLs", () => { + expect(isValidTranscriptUrl("not-a-url")).toBe(false); + expect(isValidTranscriptUrl("ftp://example.com")).toBe(false); + expect(isValidTranscriptUrl("")).toBe(false); expect(isValidTranscriptUrl(null as any)).toBe(false); expect(isValidTranscriptUrl(undefined as any)).toBe(false); }); - it('should handle malformed URLs', () => { - expect(isValidTranscriptUrl('http://')).toBe(false); - expect(isValidTranscriptUrl('https://')).toBe(false); - expect(isValidTranscriptUrl('://example.com')).toBe(false); + it("should handle malformed URLs", () => { + expect(isValidTranscriptUrl("http://")).toBe(false); + expect(isValidTranscriptUrl("https://")).toBe(false); + expect(isValidTranscriptUrl("://example.com")).toBe(false); }); }); - describe('extractSessionIdFromTranscript', () => { - it('should extract session ID from session_id pattern', () => { - const content = 'session_id: abc123def456\nOther content...'; + describe("extractSessionIdFromTranscript", () => { + it("should extract session ID from session_id pattern", () => { + const content = "session_id: abc123def456\nOther content..."; const result = extractSessionIdFromTranscript(content); - expect(result).toBe('abc123def456'); + expect(result).toBe("abc123def456"); }); - it('should extract session ID from sessionId pattern', () => { - const content = 'sessionId: xyz789\nTranscript data...'; + it("should extract session ID from sessionId pattern", () => { + const content = "sessionId: xyz789\nTranscript data..."; const result = extractSessionIdFromTranscript(content); - expect(result).toBe('xyz789'); + expect(result).toBe("xyz789"); }); - it('should extract session ID from id pattern', () => { - const content = 'id: session-12345678\nChat log...'; + it("should extract session ID from id pattern", () => { + const content = "id: session-12345678\nChat log..."; const result = extractSessionIdFromTranscript(content); - expect(result).toBe('session-12345678'); + expect(result).toBe("session-12345678"); }); - it('should extract session ID from first line', () => { - const content = 'abc123def456\nUser: Hello\nBot: Hi there'; + it("should extract session ID from first line", () => { + const content = "abc123def456\nUser: Hello\nBot: Hi there"; const result = extractSessionIdFromTranscript(content); - expect(result).toBe('abc123def456'); + expect(result).toBe("abc123def456"); }); - it('should return null for content without session ID', () => { - const content = 'User: Hello\nBot: Hi there\nUser: How are you?'; + it("should return null for content without session ID", () => { + const content = "User: Hello\nBot: Hi there\nUser: How are you?"; const result = extractSessionIdFromTranscript(content); expect(result).toBe(null); }); - it('should return null for empty content', () => { - expect(extractSessionIdFromTranscript('')).toBe(null); + it("should return null for empty content", () => { + expect(extractSessionIdFromTranscript("")).toBe(null); expect(extractSessionIdFromTranscript(null as any)).toBe(null); expect(extractSessionIdFromTranscript(undefined as any)).toBe(null); }); - it('should handle case-insensitive patterns', () => { - const content = 'SESSION_ID: ABC123\nContent...'; + it("should handle case-insensitive patterns", () => { + const content = "SESSION_ID: ABC123\nContent..."; const result = extractSessionIdFromTranscript(content); - expect(result).toBe('ABC123'); + expect(result).toBe("ABC123"); }); - it('should extract the first matching pattern', () => { - const content = 'session_id: first123\nid: second456\nMore content...'; + it("should extract the first matching pattern", () => { + const content = "session_id: first123\nid: second456\nMore content..."; const result = extractSessionIdFromTranscript(content); - expect(result).toBe('first123'); + expect(result).toBe("first123"); }); }); }); diff --git a/vitest.config.mts b/vitest.config.mts index efd3bd4..b87bcb4 100644 --- a/vitest.config.mts +++ b/vitest.config.mts @@ -1,23 +1,23 @@ -import { defineConfig } from 'vitest/config' -import react from '@vitejs/plugin-react' -import tsconfigPaths from 'vite-tsconfig-paths' +import { defineConfig } from "vitest/config"; +import react from "@vitejs/plugin-react"; +import tsconfigPaths from "vite-tsconfig-paths"; export default defineConfig({ plugins: [tsconfigPaths(), react()], test: { - environment: 'node', + environment: "node", globals: true, - setupFiles: ['./tests/setup.ts'], - include: ['tests/**/*.{test,spec}.{js,mjs,cjs,ts,mts,cts,jsx,tsx}'], + setupFiles: ["./tests/setup.ts"], + include: ["tests/**/*.{test,spec}.{js,mjs,cjs,ts,mts,cts,jsx,tsx}"], env: { - NODE_ENV: 'test', + NODE_ENV: "test", }, coverage: { - provider: 'v8', - reporter: ['text', 'lcov', 'html'], - include: ['lib/**/*.ts'], - exclude: ['lib/**/*.d.ts', 'lib/**/*.test.ts'], + provider: "v8", + reporter: ["text", "lcov", "html"], + include: ["lib/**/*.ts"], + exclude: ["lib/**/*.d.ts", "lib/**/*.test.ts"], }, testTimeout: 10000, }, -}) +});