diff --git a/lib/search/agent.ts b/lib/search/agent.ts index 4eeeed8d..b9bd1652 100644 --- a/lib/search/agent.ts +++ b/lib/search/agent.ts @@ -67,6 +67,7 @@ export const runSearch = async ( tldr, prevMessages: lastTurn, userUniversity, + supabase, emit, progress, updateProgress, diff --git a/lib/search/general/debug.ts b/lib/search/general/debug.ts index d41eac34..6d04584c 100644 --- a/lib/search/general/debug.ts +++ b/lib/search/general/debug.ts @@ -40,3 +40,72 @@ export function extractOutputText(resp: Response): string { } return parts.join("\n").trim(); } + +type KBSearchFilters = { + uni?: string; + corpus?: "su" | "official"; + year?: number; + kb_slug?: string; +}; + +function pretty(obj: any) { + return JSON.stringify(obj, null, 2); +} + +export async function debugVectorSearch(opts: { + openai: any; // OpenAI client + vectorStoreId: string; + query: string; + topK?: number; + filters: KBSearchFilters; + label?: string; +}) { + const { openai, vectorStoreId, query, topK = 5, filters, label } = opts; + + // 1) LOG THE INPUTS (this answers your “what filters were applied?” question) + console.log( + "\n[KB VS SEARCH] " + + (label ? `${label} ` : "") + + `query=${JSON.stringify(query)} topK=${topK}\n` + + `[KB VS SEARCH] vectorStoreId=${vectorStoreId}\n` + + `[KB VS SEARCH] filters=\n${pretty(filters)}\n` + ); + + // 2) RUN THE SEARCH (adjust to your SDK call shape) + // If your code uses openai.vectorStores.search(...) or openai.responses with tool=file_search, + // keep the actual call you already have, but add logs before/after. + const res = await openai.vectorStores.search(vectorStoreId, { + query, + top_k: topK, + // If your SDK supports metadata filtering here, pass it through. + // Different SDK versions may call this 'filter' or 'filters'. Keep whatever your current code uses. + filter: filters, + }); + + // 3) LOG WHAT CAME BACK (esp. attributes) + const results = res?.data ?? res?.results ?? []; + console.log(`[KB VS SEARCH] results=${results.length}`); + + for (let i = 0; i < Math.min(results.length, topK); i++) { + const r = results[i]; + const fileId = r?.file_id ?? r?.file?.id ?? r?.id; + const attrs = r?.attributes ?? r?.file?.attributes ?? {}; + const score = r?.score ?? r?.relevance_score; + + console.log( + `\n[KB VS SEARCH] #${i + 1} file_id=${fileId} score=${score}\n` + + `[KB VS SEARCH] attrs=${pretty({ + uni: attrs.uni, + corpus: attrs.corpus, + kb_slug: attrs.kb_slug, + site: attrs.site, + year: attrs.year, + canonical_url: attrs.canonical_url, + doc_id: attrs.doc_id, + section_key: attrs.section_key, + })}` + ); + } + + return res; +} diff --git a/lib/search/general/router.ts b/lib/search/general/router.ts index 91f3b952..e7db53a7 100644 --- a/lib/search/general/router.ts +++ b/lib/search/general/router.ts @@ -21,27 +21,19 @@ import type { ResponseInput } from "openai/resources/responses/responses.mjs"; // Types // ============================================================================ -/** Supported universities with their vector store IDs */ +/** Supported universities for routing */ export const SUPPORTED_UNIVERSITIES = { unimelb: { name: "University of Melbourne", - official: process.env.OPENAI_VS_UNIMELB_OFFICIAL, - union: process.env.OPENAI_VS_UNIMELB_SU, }, monash: { name: "Monash University", - official: process.env.OPENAI_VS_MONASH_OFFICIAL, - union: process.env.OPENAI_VS_MONASH_SU, }, rmit: { name: "RMIT University", - official: process.env.OPENAI_VS_RMIT_OFFICIAL, - union: process.env.OPENAI_VS_RMIT_SU, }, uwa: { name: "University of Western Australia", - official: process.env.OPENAI_VS_UWA_OFFICIAL, - union: process.env.OPENAI_VS_UWA_SU, }, } as const; @@ -196,15 +188,3 @@ export async function routeQuery( return { route: "web", university: null, intent: "both", reason: "error" }; } } - -/** - * Get vector store IDs for a university. - */ -export function getVectorStores(slug: UniversitySlug | null): { - official?: string; - union?: string; -} { - if (!slug || !SUPPORTED_UNIVERSITIES[slug]) return {}; - const uni = SUPPORTED_UNIVERSITIES[slug]; - return { official: uni.official, union: uni.union }; -} diff --git a/lib/search/general/runGeneral.ts b/lib/search/general/runGeneral.ts index 7e01392f..29c3a4bb 100644 --- a/lib/search/general/runGeneral.ts +++ b/lib/search/general/runGeneral.ts @@ -7,12 +7,13 @@ import OpenAI from "openai"; import type { ResponseInput } from "openai/resources/responses/responses.mjs"; -import { routeQuery, getVectorStores } from "./router"; +import { routeQuery } from "./router"; import { runUniversityGeneral } from "./runUniversityGeneral"; import { runConnect3General } from "./runConnect3General"; import { countWebSearchCalls } from "./countWebSearches"; import type { SearchResponse } from "../types"; import { ProgressAction } from "@/components/search/utils"; +import { SupabaseClient } from "@supabase/supabase-js"; type RunGeneralArgs = { openai: OpenAI; @@ -20,6 +21,7 @@ type RunGeneralArgs = { tldr: string; prevMessages: ResponseInput; userUniversity?: string | null; + supabase: SupabaseClient; emit?: (event: string, data: unknown) => void; progress: ProgressAction[]; updateProgress: ( @@ -35,6 +37,7 @@ export async function runGeneral({ tldr, prevMessages, userUniversity, + supabase, emit, progress, updateProgress, @@ -86,9 +89,9 @@ export async function runGeneral({ // -------- University-specific query -------- case "university": { - const vectorStores = getVectorStores(routing.university); + const centralVectorStoreId = process.env.OPENAI_UNI_VECTOR_STORE_ID; - if (vectorStores.official || vectorStores.union) { + if (centralVectorStoreId) { progress = updateProgress( progress, { @@ -101,9 +104,9 @@ export async function runGeneral({ return runUniversityGeneral( openai, + supabase, query, routing.university!, - vectorStores, { emit, intent: routing.intent }, ); } diff --git a/lib/search/general/runUniversityGeneral.ts b/lib/search/general/runUniversityGeneral.ts index e489b6d6..b645861b 100644 --- a/lib/search/general/runUniversityGeneral.ts +++ b/lib/search/general/runUniversityGeneral.ts @@ -1,13 +1,21 @@ // lib/search/general/runUniversityGeneral.ts import OpenAI from "openai"; +import { createHash } from "crypto"; +import { SupabaseClient } from "@supabase/supabase-js"; import { countWebSearchCalls } from "./countWebSearches"; +import { debugVectorSearch } from "./debug"; import type { SearchResponse } from "../types"; import type { KBIntent } from "./router"; -type VectorStores = { - official?: string; - union?: string; -}; +const KB_YEAR = 2026; +const MAX_RESULTS = 8; +const MAX_HIT_EXCERPTS = 4; +const MAX_CHUNK_CHARS = 1200; +const MAX_CHUNKS_PER_DOC = 6; +const MAX_TOTAL_CHUNKS = MAX_RESULTS * MAX_HIT_EXCERPTS; +const MIN_RESULT_SCORE = 0.3; +const MIN_RESULTS = 6; +const MIN_DISTINCT_DOCS = 3; type RunUniversityGeneralOpts = { traceId?: string; @@ -15,48 +23,223 @@ type RunUniversityGeneralOpts = { intent?: KBIntent; }; -export async function runUniversityGeneral( - openai: OpenAI, - query: string, +type ComparisonFilter = { + type: "eq"; + key: string; + value: string | number | boolean; +}; + +type CompoundFilter = { + type: "and" | "or"; + filters: Array; +}; + +type KBDocumentFileRow = { + file_id: string | null; + kb_slug: string; + doc_id: string; + section_key: string; + canonical_url: string | null; + title: string | null; + site: string | null; + uni: string | null; + corpus: string | null; + year: number | null; +}; + +type VectorStoreHit = { + file_id: string; + score: number; + filename: string; + content: Array<{ text: string; type: "text" }>; + attributes: Record | null; +}; + +type SourceChunk = { + label: string; + snippet: string; + score: number; +}; + +type SourceContext = { + doc: KBDocumentFileRow; + fileId: string; + corpus: string; + chunks: SourceChunk[]; +}; + +function corpusLabel(corpus: string) { + if (corpus === "official") return "Official"; + if (corpus === "su") return "Student Union"; + return corpus; +} + +function kbSlugFor(uniSlug: string, corpus: string) { + return `${uniSlug}_${corpus}`; +} + +function preferredCorpusForIntent(intent: KBIntent): "official" | "su" { + return intent === "union" ? "su" : "official"; +} + +function fallbackCorpusForIntent(intent: KBIntent): "official" | "su" { + return intent === "union" ? "official" : "su"; +} + +function buildKBFilters( uniSlug: string, - vectorStores: VectorStores, - opts?: RunUniversityGeneralOpts, -): Promise { - const emit = opts?.emit; - const intent = opts?.intent ?? "both"; + year: number, + corpus?: string, +): CompoundFilter { + const filters: Array = [ + { type: "eq", key: "uni", value: uniSlug }, + { type: "eq", key: "year", value: year }, + ]; + + if (corpus) { + filters.push({ type: "eq", key: "corpus", value: corpus }); + filters.push({ + type: "eq", + key: "kb_slug", + value: kbSlugFor(uniSlug, corpus), + }); + } + + return { + type: "and", + filters, + }; +} + +function clampSnippet(text: string, maxChars: number) { + if (text.length <= maxChars) return text; + return `${text.slice(0, maxChars).trim()}...`; +} + +function cleanChunkText(text: string, title?: string | null) { + const rawLines = text.split(/\r?\n/).map((line) => line.trim()); + const filtered: string[] = []; + const sourceOrSection = /^(source|section)\s*:/i; + + for (const line of rawLines) { + if (!line) continue; + if (sourceOrSection.test(line)) continue; + filtered.push(line); + } + + const normalizedTitle = title?.trim().toLowerCase() ?? ""; + const collapsed: string[] = []; + let prev = ""; + + for (const line of filtered) { + const normalized = line.toLowerCase(); + if (collapsed.length === 0 && normalizedTitle && normalized === normalizedTitle) { + collapsed.push(line); + prev = normalized; + continue; + } + if (normalized === prev) continue; + collapsed.push(line); + prev = normalized; + } + + // Remove repeated title lines at the top (keep first if present). + if (normalizedTitle) { + let firstTitleIndex = -1; + for (let i = 0; i < collapsed.length; i++) { + if (collapsed[i].toLowerCase() === normalizedTitle) { + firstTitleIndex = i; + break; + } + } + if (firstTitleIndex > 0) { + collapsed.splice(0, firstTitleIndex); + } + while ( + collapsed.length > 1 && + collapsed[0].toLowerCase() === normalizedTitle && + collapsed[1].toLowerCase() === normalizedTitle + ) { + collapsed.splice(1, 1); + } + } + + return collapsed.join("\n").trim(); +} - // Choose store order based on intent - const storesToQuery: { id: string; source: "Official" | "Student Union" }[] = - []; +function normalizeForFingerprint(text: string) { + const rawLines = text + .split(/\r?\n/) + .map((line) => line.trim()) + .filter(Boolean); + const filtered: string[] = []; + const sourceOrSection = /^(source|section)\s*:/i; + let prev = ""; - const officialId = vectorStores.official; - const unionId = vectorStores.union; + for (const line of rawLines) { + if (sourceOrSection.test(line)) continue; + const normalized = line.toLowerCase(); + if (normalized === prev) continue; + filtered.push(normalized); + prev = normalized; + } - if (intent === "official") { - if (officialId) storesToQuery.push({ id: officialId, source: "Official" }); - if (unionId) storesToQuery.push({ id: unionId, source: "Student Union" }); // fallback - } else if (intent === "union") { - if (unionId) storesToQuery.push({ id: unionId, source: "Student Union" }); - if (officialId) storesToQuery.push({ id: officialId, source: "Official" }); // fallback + return filtered.join(" ").replace(/\s+/g, " ").trim(); +} + +function fingerprintChunk(text: string) { + const normalized = normalizeForFingerprint(text); + const head = normalized.slice(0, MAX_CHUNK_CHARS); + return createHash("sha1").update(head).digest("hex"); +} + +function formatSourceContext(source: SourceContext, index: number) { + const lines: string[] = []; + lines.push(`[Document ${index}]`); + lines.push(`title: ${source.doc.title ?? "Untitled"}`); + if (source.doc.canonical_url) lines.push(`url: ${source.doc.canonical_url}`); + lines.push(`corpus: ${corpusLabel(source.corpus)}`); + lines.push(`section: ${source.doc.section_key}`); + if (!source.chunks.length) { + lines.push("excerpts: (no chunk text available)"); } else { - // "both": prefer official first, then union - if (officialId) storesToQuery.push({ id: officialId, source: "Official" }); - if (unionId) storesToQuery.push({ id: unionId, source: "Student Union" }); + lines.push("excerpts:"); + for (const chunk of source.chunks) { + lines.push(`- ${chunk.label}: ${chunk.snippet}`); + } } + return lines.join("\n"); +} - // If no KB stores configured, go straight to web fallback - if (storesToQuery.length === 0) { - emit?.("status", { - step: "uni_web_fallback", - message: "No university KB configured, searching the web...", - }); +function toQuickLinkLabel(url: string, title?: string | null) { + if (title && title.trim()) return title.trim().slice(0, 64); + try { + const u = new URL(url); + const host = u.hostname.replace(/^www\./, ""); + const path = u.pathname === "/" ? "" : u.pathname; + return `${host}${path}`.slice(0, 64); + } catch { + return url.slice(0, 64); + } +} - const webResp = await openai.responses.create({ - model: "gpt-4o-mini", - input: [ - { - role: "system", - content: ` +async function webFallback( + openai: OpenAI, + query: string, + uniSlug: string, + emit?: (event: string, data: unknown) => void, +): Promise { + emit?.("status", { + step: "uni_web_fallback", + message: "No KB match, searching the web...", + }); + + const webResp = await openai.responses.create({ + model: "gpt-4o-mini", + input: [ + { + role: "system", + content: ` You are a university help assistant for ${uniSlug}. Use web search. Prefer official university or government sources. @@ -71,57 +254,473 @@ Rules: - Do NOT add a separate "Key Links"/"Related Links" section. - Do NOT invent URLs. `.trim(), + }, + { role: "user", content: query }, + ], + tools: [{ type: "web_search_preview" }], + }); + + emit?.( + "status", + `WEB SEARCH usage: calls=${countWebSearchCalls(webResp)} tokens=${webResp.usage?.total_tokens}`, + ); + + return { + markdown: (webResp.output_text ?? "").trim(), + }; +} + +export async function runUniversityGeneral( + openai: OpenAI, + supabase: SupabaseClient, + query: string, + uniSlug: string, + opts?: RunUniversityGeneralOpts, +): Promise { + const emit = opts?.emit; + const intent = opts?.intent ?? "both"; + const vectorStoreId = process.env.OPENAI_UNI_VECTOR_STORE_ID; + + if (!vectorStoreId) { + return webFallback(openai, query, uniSlug, emit); + } + + const preferredCorpus = preferredCorpusForIntent(intent); + const fallbackCorpus = fallbackCorpusForIntent(intent); + const kbDebug = process.env.KB_DEBUG === "1"; + + if (kbDebug) { + console.log("[runUniversityGeneral] kb_corpus_preference", { + uniSlug, + intent, + preferredCorpus, + fallbackCorpus, + year: KB_YEAR, + }); + } + + const runSearch = async (corpus?: string) => { + const filter = buildKBFilters(uniSlug, KB_YEAR, corpus); + const searchPage = await openai.vectorStores.search(vectorStoreId, { + query, + filters: filter, + max_num_results: MAX_RESULTS, + rewrite_query: true, + }); + const hits = (searchPage?.data ?? []) as VectorStoreHit[]; + const filtered = hits.filter((hit) => hit.score >= MIN_RESULT_SCORE); + return { hits, filtered }; + }; + + emit?.("status", { + step: "uni_kb_search", + message: `Searching university KB (${preferredCorpus})...`, + }); + + if (process.env.DEBUG_KB_VECTOR_SEARCH === "1") { + console.log("[runUniversityGeneral] debug_kb_vector_search", { + uniSlug, + corpus: preferredCorpus, + year: KB_YEAR, + }); + await debugVectorSearch({ + openai, + vectorStoreId, + query, + topK: 5, + filters: { + uni: uniSlug, + corpus: preferredCorpus, + year: KB_YEAR, + kb_slug: kbSlugFor(uniSlug, preferredCorpus), + }, + label: "kb-central", + }); + } + + const preferredSearch = await runSearch(preferredCorpus); + let mergedHits = preferredSearch.filtered.slice(); + + const distinctDocsPreferred = new Set( + mergedHits.map((h) => h.attributes?.doc_id).filter(Boolean), + ); + const insufficientPreferred = + mergedHits.length < MIN_RESULTS || + distinctDocsPreferred.size < MIN_DISTINCT_DOCS; + + if (kbDebug) { + console.log("[runUniversityGeneral] kb_search_pass", { + pass: "preferred", + corpus: preferredCorpus, + totalHits: preferredSearch.hits.length, + filteredHits: preferredSearch.filtered.length, + distinctDocs: distinctDocsPreferred.size, + insufficient: insufficientPreferred, + reason: insufficientPreferred + ? mergedHits.length < MIN_RESULTS + ? "min_results" + : "min_distinct_docs" + : null, + }); + } + + let usedFallback = false; + let usedNoCorpus = false; + + if (insufficientPreferred) { + emit?.("status", { + step: "uni_kb_search", + message: `KB results low, retrying (${fallbackCorpus})...`, + }); + + if (process.env.DEBUG_KB_VECTOR_SEARCH === "1") { + console.log("[runUniversityGeneral] debug_kb_vector_search", { + uniSlug, + corpus: fallbackCorpus, + year: KB_YEAR, + }); + await debugVectorSearch({ + openai, + vectorStoreId, + query, + topK: 5, + filters: { + uni: uniSlug, + corpus: fallbackCorpus, + year: KB_YEAR, + kb_slug: kbSlugFor(uniSlug, fallbackCorpus), }, - { role: "user", content: query }, - ], - tools: [{ type: "web_search_preview" }], + label: "kb-central", + }); + } + + const fallbackSearch = await runSearch(fallbackCorpus); + mergedHits = mergedHits.concat(fallbackSearch.filtered); + usedFallback = true; + + const distinctDocsAfterFallback = new Set( + mergedHits.map((h) => h.attributes?.doc_id).filter(Boolean), + ); + const insufficientAfterFallback = + mergedHits.length < MIN_RESULTS || + distinctDocsAfterFallback.size < MIN_DISTINCT_DOCS; + + if (kbDebug) { + console.log("[runUniversityGeneral] kb_search_pass", { + pass: "fallback", + corpus: fallbackCorpus, + totalHits: fallbackSearch.hits.length, + filteredHits: fallbackSearch.filtered.length, + distinctDocs: distinctDocsAfterFallback.size, + insufficient: insufficientAfterFallback, + reason: insufficientAfterFallback + ? mergedHits.length < MIN_RESULTS + ? "min_results" + : "min_distinct_docs" + : null, + }); + } + + if (insufficientAfterFallback) { + emit?.("status", { + step: "uni_kb_search", + message: "KB results low, retrying without corpus filter...", + }); + + const openSearch = await runSearch(); + mergedHits = mergedHits.concat(openSearch.filtered); + usedNoCorpus = true; + + if (kbDebug) { + const distinctDocsOpen = new Set( + mergedHits.map((h) => h.attributes?.doc_id).filter(Boolean), + ); + console.log("[runUniversityGeneral] kb_search_pass", { + pass: "no_corpus", + totalHits: openSearch.hits.length, + filteredHits: openSearch.filtered.length, + distinctDocs: distinctDocsOpen.size, + }); + } + } + } + + const hits = mergedHits; + const filteredHits = mergedHits; + + if (!filteredHits.length) { + console.warn("[runUniversityGeneral] no_vector_hits", { + uniSlug, + intent, + query, + minScore: MIN_RESULT_SCORE, + totalHits: hits.length, }); + return webFallback(openai, query, uniSlug, emit); + } - emit?.( - "status", - `WEB SEARCH usage: calls=${countWebSearchCalls(webResp)} tokens=${webResp.usage?.total_tokens}`, + if (kbDebug) { + console.log("[runUniversityGeneral] kb_corpus_fallback", { + preferredCorpus, + fallbackCorpus, + usedFallback, + usedNoCorpus, + }); + } + + const seenFileIds = new Set(); + const seenDocs = new Set(); + const dedupedHits = filteredHits.filter((hit) => { + if (!hit.file_id) return false; + if (seenFileIds.has(hit.file_id)) return false; + const docId = + typeof hit.attributes?.doc_id === "string" ? hit.attributes.doc_id : ""; + const canonical = + typeof hit.attributes?.canonical_url === "string" + ? hit.attributes.canonical_url + : ""; + const docKey = (canonical || docId).trim(); + if (docKey && seenDocs.has(docKey)) return false; + seenFileIds.add(hit.file_id); + if (docKey) seenDocs.add(docKey); + return true; + }); + + const hitByFileId = new Map(dedupedHits.map((h) => [h.file_id, h])); + const fileIds = dedupedHits.map((h) => h.file_id); + + if (fileIds.length === 0) { + console.warn("[runUniversityGeneral] no_file_ids_from_hits", { + uniSlug, + intent, + query, + }); + return webFallback(openai, query, uniSlug, emit); + } + + const { data: docFiles, error: docFilesError } = await supabase + .from("kb_document_files") + .select( + "file_id,kb_slug,doc_id,section_key,canonical_url,title,site,uni,corpus,year", + ) + .in("file_id", fileIds) + .eq("is_active", true); + + if (docFilesError) { + console.error("[runUniversityGeneral] kb_document_files lookup failed", { + error: docFilesError.message, + query, + uniSlug, + }); + return webFallback(openai, query, uniSlug, emit); + } + + const docByFileId = new Map(); + for (const row of docFiles ?? []) { + if (row.file_id) docByFileId.set(row.file_id, row as KBDocumentFileRow); + } + + const missingHits = dedupedHits.filter((h) => !docByFileId.has(h.file_id)); + await Promise.all( + missingHits.map(async (hit) => { + const attrs = hit.attributes ?? {}; + const kb_slug = typeof attrs.kb_slug === "string" ? attrs.kb_slug : ""; + const doc_id = typeof attrs.doc_id === "string" ? attrs.doc_id : ""; + const section_key = + typeof attrs.section_key === "string" ? attrs.section_key : ""; + + if (!kb_slug || !doc_id || !section_key) { + console.warn("[runUniversityGeneral] kb_document_files missing", { + file_id: hit.file_id, + attrs, + query, + }); + return; + } + + const { data: fallbackRow, error: fallbackError } = await supabase + .from("kb_document_files") + .select( + "file_id,kb_slug,doc_id,section_key,canonical_url,title,site,uni,corpus,year", + ) + .eq("kb_slug", kb_slug) + .eq("doc_id", doc_id) + .eq("section_key", section_key) + .eq("is_active", true) + .maybeSingle(); + + if (fallbackError || !fallbackRow) { + console.warn("[runUniversityGeneral] kb_document_files fallback miss", { + file_id: hit.file_id, + kb_slug, + doc_id, + section_key, + error: fallbackError?.message, + }); + return; + } + + docByFileId.set(hit.file_id, fallbackRow as KBDocumentFileRow); + }), + ); + + const seenHits = new Set(); + const orderedMatches = dedupedHits + .map((hit) => { + if (seenHits.has(hit.file_id)) return null; + seenHits.add(hit.file_id); + const doc = docByFileId.get(hit.file_id); + if (!doc) return null; + return { doc, fileId: hit.file_id }; + }) + .filter( + (row): row is { doc: KBDocumentFileRow; fileId: string } => Boolean(row), ); - return { - markdown: (webResp.output_text ?? "").trim(), + if (!orderedMatches.length) { + console.warn("[runUniversityGeneral] no_kb_document_files", { + uniSlug, + intent, + query, + }); + return webFallback(openai, query, uniSlug, emit); + } + + type ChunkCandidate = { + doc: KBDocumentFileRow; + fileId: string; + corpus: string; + label: string; + snippet: string; + score: number; + }; + + const chunkCandidates: ChunkCandidate[] = []; + for (const { doc, fileId } of orderedMatches) { + const hit = hitByFileId.get(fileId); + const content = hit?.content ?? []; + const score = hit?.score ?? 0; + const selected = content.slice(0, MAX_HIT_EXCERPTS); + + if (!selected.length) { + console.warn("[runUniversityGeneral] empty_vector_content", { + kb_slug: doc.kb_slug, + doc_id: doc.doc_id, + file_id: fileId, + }); + } + + for (const [idx, chunk] of selected.entries()) { + const cleaned = cleanChunkText(chunk.text, doc.title); + const snippet = clampSnippet(cleaned, MAX_CHUNK_CHARS); + if (!snippet) continue; + chunkCandidates.push({ + doc, + fileId, + corpus: doc.corpus ?? "unknown", + label: `vector_store_excerpt_${idx + 1}`, + snippet, + score, + }); + } + } + + chunkCandidates.sort((a, b) => b.score - a.score); + + const seenFingerprints = new Set(); + const grouped = new Map< + string, + { doc: KBDocumentFileRow; corpus: string; chunks: SourceChunk[]; topScore: number } + >(); + + let totalChunks = 0; + for (const candidate of chunkCandidates) { + if (totalChunks >= MAX_TOTAL_CHUNKS) break; + + const fingerprint = fingerprintChunk(candidate.snippet); + if (seenFingerprints.has(fingerprint)) continue; + seenFingerprints.add(fingerprint); + + const docKey = candidate.doc.canonical_url?.trim() || candidate.doc.doc_id; + const existing = grouped.get(docKey); + const chunk: SourceChunk = { + label: candidate.label, + snippet: candidate.snippet, + score: candidate.score, }; + + if (!existing) { + grouped.set(docKey, { + doc: candidate.doc, + corpus: candidate.corpus, + chunks: [chunk], + topScore: candidate.score, + }); + totalChunks += 1; + continue; + } + + if (existing.chunks.length >= MAX_CHUNKS_PER_DOC) continue; + + existing.chunks.push(chunk); + if (candidate.score > existing.topScore) { + existing.topScore = candidate.score; + } + totalChunks += 1; + } + + const sources: SourceContext[] = Array.from(grouped.values()) + .sort((a, b) => b.topScore - a.topScore) + .map((group) => ({ + doc: group.doc, + fileId: group.doc.file_id ?? "", + corpus: group.corpus, + chunks: group.chunks.sort((a, b) => b.score - a.score), + })); + + if (kbDebug) { + const perDocCounts = sources + .map((source) => ({ + doc_id: source.doc.doc_id, + title: source.doc.title ?? "Untitled", + url: source.doc.canonical_url ?? null, + chunks: source.chunks.length, + topScore: source.chunks[0]?.score ?? 0, + })) + .sort((a, b) => b.topScore - a.topScore) + .slice(0, 8); + + console.log("[runUniversityGeneral] kb_dedupe_stats", { + rawHits: hits.length, + filteredHits: filteredHits.length, + dedupedHits: dedupedHits.length, + chunkCandidates: chunkCandidates.length, + uniqueChunks: seenFingerprints.size, + totalChunksAfterCap: totalChunks, + perDocCap: MAX_CHUNKS_PER_DOC, + totalCap: MAX_TOTAL_CHUNKS, + topDocs: perDocCounts, + }); } - // Status message - const searchMsg = - storesToQuery.length === 2 - ? `Searching ${storesToQuery[0].source} then ${storesToQuery[1].source}...` - : `Searching ${storesToQuery[0].source}...`; - emit?.("status", { step: "uni_kb_search", message: searchMsg }); - - /** - * ONE LLM CALL: - * - model calls file_search tools itself (for one or two stores) - * - model produces the final answer (no retriever pass, no contextPack building) - * - * Key: you must pass BOTH vector store IDs to tools list, because a single tool call - * can only target one store. The model will choose to call one or both. - */ - const storeTooling = storesToQuery.map((s) => ({ - type: "file_search" as const, - // IMPORTANT: single store per tool call; the model can call multiple tools - vector_store_ids: [s.id], - max_num_results: 6, - })); + const contextText = sources + .map((source, idx) => formatSourceContext(source, idx + 1)) + .join("\n\n"); const system = ` You are a university help assistant for ${uniSlug}. -You MUST use file_search to retrieve relevant passages, then answer the user's question. +Use ONLY the provided KB excerpts to answer the user's question. +If the KB does not contain the answer, say what is missing and suggest what to search for next. -Grounding rules: -- Prefer [Official] information over [Student Union] if there is any conflict. -- If both sources are used, label key claims with [Official] or [Student Union]. -- If information is missing from KB, say what is missing briefly and suggest what to search for next (do not invent details). + Grounding rules: + - Prefer official information over student union if there is any conflict. + - If both sources are used, label key claims with [Official] or [Student Union]. + - When helpful, include brief quoted snippets from the KB excerpts to support key facts. Formatting rules: - For lists, use Markdown bullets with a blank line before the list. -- You MAY include inline links if they appear in retrieved content. +- You MAY include inline links if they appear in the KB excerpts. - Do NOT invent URLs. - Do NOT add a separate "Key Links"/"Related Links" section. `.trim(); @@ -136,89 +735,44 @@ Formatting rules: User question: ${query} -Source preference: -- Primary: ${storesToQuery[0].source} -${storesToQuery[1] ? `- Secondary: ${storesToQuery[1].source}` : ""} +KB excerpts: +${contextText} `.trim(), }, ], - tools: storeTooling, temperature: 0.2, }); - // (Optional) log token usage - console.log("[runUniversityGeneral] one_call", { - uniSlug, - intent, - primary: storesToQuery[0].source, - secondary: storesToQuery[1]?.source, - usage: answerResp.usage, - }); - - // If the model failed to use KB at all, do a web fallback - // (lightweight check: did any file_citation appear?) - const usedKB = (() => { - const outputs = answerResp?.output ?? []; - for (const o of outputs) { - if (o?.type !== "message") continue; - const content = Array.isArray(o?.content) ? o.content : []; - for (const c of content) { - if ("annotations" in c && Array.isArray(c.annotations)) { - if (c.annotations.some((a) => a?.type === "file_citation")) - return true; - } - } - } - return false; - })(); - - if (usedKB) { - emit?.("status", { - step: "uni_kb_answer", - message: "Answered from university KB.", - }); - return { - markdown: (answerResp.output_text ?? "").trim(), - }; - } - emit?.("status", { - step: "uni_web_fallback", - message: "No KB match, searching the web...", + step: "uni_kb_answer", + message: "Answered from university KB.", }); - const webResp = await openai.responses.create({ - model: "gpt-4o-mini", - input: [ - { - role: "system", - content: ` -You are a university help assistant for ${uniSlug}. -Use web search. Prefer official university or government sources. - -Rules: -- For lists, use Markdown bullets with a blank line before the list: - Example: - Some intro sentence: - - - Item one - - Item two -- You MAY include inline links naturally in the summary. -- Do NOT add a separate "Key Links"/"Related Links" section. -- Do NOT invent URLs. -`.trim(), - }, - { role: "user", content: query }, - ], - tools: [{ type: "web_search_preview" }], - }); - - emit?.( - "status", - `WEB SEARCH usage: calls=${countWebSearchCalls(webResp)} tokens=${webResp.usage?.total_tokens}`, - ); + const seenLinks = new Set(); + const quickLinks = sources + .map((s) => { + if (!s.doc.canonical_url) return null; + const url = s.doc.canonical_url; + if (seenLinks.has(url)) return null; + seenLinks.add(url); + return { + url, + label: toQuickLinkLabel(url, s.doc.title), + source: "kb" as const, + }; + }) + .filter( + ( + l, + ): l is { + url: string; + label: string; + source: "kb"; + } => Boolean(l), + ); return { - markdown: (webResp.output_text ?? "").trim(), + markdown: (answerResp.output_text ?? "").trim(), + quickLinks, }; } diff --git a/package-lock.json b/package-lock.json index c394ae41..bb3ac01d 100644 --- a/package-lock.json +++ b/package-lock.json @@ -4,7 +4,6 @@ "requires": true, "packages": { "": { - "name": "connect3", "dependencies": { "@dnd-kit/core": "^6.3.1", "@dnd-kit/sortable": "^10.0.0", @@ -27,12 +26,12 @@ "cmdk": "^1.1.1", "fast-average-color": "^9.5.0", "framer-motion": "^12.23.12", - "html-react-parser": "^5.2.11", + "html-react-parser": "^5.2.14", "install": "^0.13.0", "jsdom": "^27.3.0", "lucide-react": "^0.511.0", "mammoth": "^1.10.0", - "next": "15.5.9", + "next": "^15.5.11", "next-themes": "^0.4.6", "npm": "^11.5.2", "openai": "^6.16.0", @@ -73,9 +72,9 @@ } }, "node_modules/@acemir/cssom": { - "version": "0.9.30", - "resolved": "https://registry.npmjs.org/@acemir/cssom/-/cssom-0.9.30.tgz", - "integrity": "sha512-9CnlMCI0LmCIq0olalQqdWrJHPzm0/tw3gzOA9zJSgvFX7Xau3D24mAGa4BtwxwY69nsuJW6kQqqCzf/mEcQgg==", + "version": "0.9.31", + "resolved": "https://registry.npmjs.org/@acemir/cssom/-/cssom-0.9.31.tgz", + "integrity": "sha512-ZnR3GSaH+/vJ0YlHau21FjfLYjMpYVIzTD8M8vIEQvIGxeOXyXdzCI140rrCY862p/C/BbzWsjc1dgnM9mkoTA==", "license": "MIT" }, "node_modules/@alloc/quick-lru": { @@ -83,6 +82,7 @@ "resolved": "https://registry.npmjs.org/@alloc/quick-lru/-/quick-lru-5.2.0.tgz", "integrity": "sha512-UrcABB+4bUrFABwbluTIBErXwvbsU/V7TZWfmbgJfbkwiBuziS9gxdODUyuiecfdGQ85jglMW6juS3+z5TsKLw==", "dev": true, + "license": "MIT", "engines": { "node": ">=10" }, @@ -103,15 +103,6 @@ "lru-cache": "^11.2.4" } }, - "node_modules/@asamuzakjp/css-color/node_modules/lru-cache": { - "version": "11.2.4", - "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-11.2.4.tgz", - "integrity": "sha512-B5Y16Jr9LB9dHVkh6ZevG+vAbOsNOYCX+sXvFWFu7B3Iz5mijW3zdbMyhsh8ANd2mSWBYdJgnqi+mL7/LrOPYg==", - "license": "BlueOak-1.0.0", - "engines": { - "node": "20 || >=22" - } - }, "node_modules/@asamuzakjp/dom-selector": { "version": "6.7.6", "resolved": "https://registry.npmjs.org/@asamuzakjp/dom-selector/-/dom-selector-6.7.6.tgz", @@ -125,15 +116,6 @@ "lru-cache": "^11.2.4" } }, - "node_modules/@asamuzakjp/dom-selector/node_modules/lru-cache": { - "version": "11.2.4", - "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-11.2.4.tgz", - "integrity": "sha512-B5Y16Jr9LB9dHVkh6ZevG+vAbOsNOYCX+sXvFWFu7B3Iz5mijW3zdbMyhsh8ANd2mSWBYdJgnqi+mL7/LrOPYg==", - "license": "BlueOak-1.0.0", - "engines": { - "node": "20 || >=22" - } - }, "node_modules/@asamuzakjp/nwsapi": { "version": "2.3.9", "resolved": "https://registry.npmjs.org/@asamuzakjp/nwsapi/-/nwsapi-2.3.9.tgz", @@ -141,9 +123,9 @@ "license": "MIT" }, "node_modules/@babel/runtime": { - "version": "7.28.4", - "resolved": "https://registry.npmjs.org/@babel/runtime/-/runtime-7.28.4.tgz", - "integrity": "sha512-Q/N6JNWvIvPnLDvjlE1OUBLPQHH6l3CltCEsHIujp45zQUSSh8K+gHnaEX45yAT1nyngnINhvWtzN+Nb9D8RAQ==", + "version": "7.28.6", + "resolved": "https://registry.npmjs.org/@babel/runtime/-/runtime-7.28.6.tgz", + "integrity": "sha512-05WQkdpL9COIMz4LjTxGpPNCdlpyimKppYNoJ5Di5EUObifl8t4tuLuUBBZEpoLYOmfvIWrsp9fCl0HoPRVTdA==", "license": "MIT", "engines": { "node": ">=6.9.0" @@ -242,9 +224,9 @@ } }, "node_modules/@csstools/css-syntax-patches-for-csstree": { - "version": "1.0.23", - "resolved": "https://registry.npmjs.org/@csstools/css-syntax-patches-for-csstree/-/css-syntax-patches-for-csstree-1.0.23.tgz", - "integrity": "sha512-YEmgyklR6l/oKUltidNVYdjSmLSW88vMsKx0pmiS3r71s8ZZRpd8A0Yf0U+6p/RzElmMnPBv27hNWjDQMSZRtQ==", + "version": "1.0.26", + "resolved": "https://registry.npmjs.org/@csstools/css-syntax-patches-for-csstree/-/css-syntax-patches-for-csstree-1.0.26.tgz", + "integrity": "sha512-6boXK0KkzT5u5xOgF6TKB+CLq9SOpEGmkZw0g5n9/7yg85wab3UzSxB8TxhLJ31L4SGJ6BCFRw/iftTha1CJXA==", "funding": [ { "type": "github", @@ -255,10 +237,7 @@ "url": "https://opencollective.com/csstools" } ], - "license": "MIT-0", - "engines": { - "node": ">=18" - } + "license": "MIT-0" }, "node_modules/@csstools/css-tokenizer": { "version": "3.0.4", @@ -810,10 +789,11 @@ } }, "node_modules/@eslint-community/eslint-utils": { - "version": "4.7.0", - "resolved": "https://registry.npmjs.org/@eslint-community/eslint-utils/-/eslint-utils-4.7.0.tgz", - "integrity": "sha512-dyybb3AcajC7uha6CvhdVRJqaKyn7w2YKqKyAN37NKYgZT36w+iRb0Dymmc5qEJ549c/S31cMMSFd75bteCpCw==", + "version": "4.9.1", + "resolved": "https://registry.npmjs.org/@eslint-community/eslint-utils/-/eslint-utils-4.9.1.tgz", + "integrity": "sha512-phrYmNiYppR7znFEdqgfWHXR6NCkZEK7hwWDHZUjit/2/U0r6XvkDl0SYnoM51Hq7FhCGdLDT6zxCCOY1hexsQ==", "dev": true, + "license": "MIT", "dependencies": { "eslint-visitor-keys": "^3.4.3" }, @@ -832,6 +812,7 @@ "resolved": "https://registry.npmjs.org/eslint-visitor-keys/-/eslint-visitor-keys-3.4.3.tgz", "integrity": "sha512-wpc+LXeiyiisxPlEkUzU6svyS1frIO3Mgxj1fdy7Pm8Ygzguax2N3Fa/D/ag1WqbOprdI+uY6wMUl8/a2G+iag==", "dev": true, + "license": "Apache-2.0", "engines": { "node": "^12.22.0 || ^14.17.0 || >=16.0.0" }, @@ -840,21 +821,23 @@ } }, "node_modules/@eslint-community/regexpp": { - "version": "4.12.1", - "resolved": "https://registry.npmjs.org/@eslint-community/regexpp/-/regexpp-4.12.1.tgz", - "integrity": "sha512-CCZCDJuduB9OUkFkY2IgppNZMi2lBQgD2qzwXkEia16cge2pijY/aXi96CJMquDMn3nJdlPV1A5KrJEXwfLNzQ==", + "version": "4.12.2", + "resolved": "https://registry.npmjs.org/@eslint-community/regexpp/-/regexpp-4.12.2.tgz", + "integrity": "sha512-EriSTlt5OC9/7SXkRSCAhfSxxoSUgBm33OH+IkwbdpgoqsSsUg7y3uh+IICI/Qg4BBWr3U2i39RpmycbxMq4ew==", "dev": true, + "license": "MIT", "engines": { "node": "^12.0.0 || ^14.0.0 || >=16.0.0" } }, "node_modules/@eslint/config-array": { - "version": "0.21.0", - "resolved": "https://registry.npmjs.org/@eslint/config-array/-/config-array-0.21.0.tgz", - "integrity": "sha512-ENIdc4iLu0d93HeYirvKmrzshzofPw6VkZRKQGe9Nv46ZnWUzcF1xV01dcvEg/1wXUR61OmmlSfyeyO7EvjLxQ==", + "version": "0.21.1", + "resolved": "https://registry.npmjs.org/@eslint/config-array/-/config-array-0.21.1.tgz", + "integrity": "sha512-aw1gNayWpdI/jSYVgzN5pL0cfzU02GT3NBpeT/DXbx1/1x7ZKxFPd9bwrzygx/qiwIQiJ1sw/zD8qY/kRvlGHA==", "dev": true, + "license": "Apache-2.0", "dependencies": { - "@eslint/object-schema": "^2.1.6", + "@eslint/object-schema": "^2.1.7", "debug": "^4.3.1", "minimatch": "^3.1.2" }, @@ -863,19 +846,24 @@ } }, "node_modules/@eslint/config-helpers": { - "version": "0.3.1", - "resolved": "https://registry.npmjs.org/@eslint/config-helpers/-/config-helpers-0.3.1.tgz", - "integrity": "sha512-xR93k9WhrDYpXHORXpxVL5oHj3Era7wo6k/Wd8/IsQNnZUTzkGS29lyn3nAT05v6ltUuTFVCCYDEGfy2Or/sPA==", + "version": "0.4.2", + "resolved": "https://registry.npmjs.org/@eslint/config-helpers/-/config-helpers-0.4.2.tgz", + "integrity": "sha512-gBrxN88gOIf3R7ja5K9slwNayVcZgK6SOUORm2uBzTeIEfeVaIhOpCtTox3P6R7o2jLFwLFTLnC7kU/RGcYEgw==", "dev": true, + "license": "Apache-2.0", + "dependencies": { + "@eslint/core": "^0.17.0" + }, "engines": { "node": "^18.18.0 || ^20.9.0 || >=21.1.0" } }, "node_modules/@eslint/core": { - "version": "0.15.2", - "resolved": "https://registry.npmjs.org/@eslint/core/-/core-0.15.2.tgz", - "integrity": "sha512-78Md3/Rrxh83gCxoUc0EiciuOHsIITzLy53m3d9UyiW8y9Dj2D29FeETqyKA+BRK76tnTp6RXWb3pCay8Oyomg==", + "version": "0.17.0", + "resolved": "https://registry.npmjs.org/@eslint/core/-/core-0.17.0.tgz", + "integrity": "sha512-yL/sLrpmtDaFEiUj1osRP4TI2MDz1AddJL+jZ7KSqvBuliN4xqYY54IfdN8qD8Toa6g1iloph1fxQNkjOxrrpQ==", "dev": true, + "license": "Apache-2.0", "dependencies": { "@types/json-schema": "^7.0.15" }, @@ -884,10 +872,11 @@ } }, "node_modules/@eslint/eslintrc": { - "version": "3.3.1", - "resolved": "https://registry.npmjs.org/@eslint/eslintrc/-/eslintrc-3.3.1.tgz", - "integrity": "sha512-gtF186CXhIl1p4pJNGZw8Yc6RlshoePRvE0X91oPGb3vZ8pM3qOS9W9NGPat9LziaBV7XrJWGylNQXkGcnM3IQ==", + "version": "3.3.3", + "resolved": "https://registry.npmjs.org/@eslint/eslintrc/-/eslintrc-3.3.3.tgz", + "integrity": "sha512-Kr+LPIUVKz2qkx1HAMH8q1q6azbqBAsXJUxBl/ODDuVPX45Z9DfwB8tPjTi6nNZ8BuM3nbJxC5zCAg5elnBUTQ==", "dev": true, + "license": "MIT", "dependencies": { "ajv": "^6.12.4", "debug": "^4.3.2", @@ -895,7 +884,7 @@ "globals": "^14.0.0", "ignore": "^5.2.0", "import-fresh": "^3.2.1", - "js-yaml": "^4.1.0", + "js-yaml": "^4.1.1", "minimatch": "^3.1.2", "strip-json-comments": "^3.1.1" }, @@ -907,10 +896,11 @@ } }, "node_modules/@eslint/js": { - "version": "9.34.0", - "resolved": "https://registry.npmjs.org/@eslint/js/-/js-9.34.0.tgz", - "integrity": "sha512-EoyvqQnBNsV1CWaEJ559rxXL4c8V92gxirbawSmVUOWXlsRxxQXl6LmCpdUblgxgSkDIqKnhzba2SjRTI/A5Rw==", + "version": "9.39.2", + "resolved": "https://registry.npmjs.org/@eslint/js/-/js-9.39.2.tgz", + "integrity": "sha512-q1mjIoW1VX4IvSocvM/vbTiveKC4k9eLrajNEuSsmjymSDEbpGddtpfOoN7YGAqBK3NG+uqo8ia4PDTt8buCYA==", "dev": true, + "license": "MIT", "engines": { "node": "^18.18.0 || ^20.9.0 || >=21.1.0" }, @@ -919,21 +909,23 @@ } }, "node_modules/@eslint/object-schema": { - "version": "2.1.6", - "resolved": "https://registry.npmjs.org/@eslint/object-schema/-/object-schema-2.1.6.tgz", - "integrity": "sha512-RBMg5FRL0I0gs51M/guSAj5/e14VQ4tpZnQNWwuDT66P14I43ItmPfIZRhO9fUVIPOAQXU47atlywZ/czoqFPA==", + "version": "2.1.7", + "resolved": "https://registry.npmjs.org/@eslint/object-schema/-/object-schema-2.1.7.tgz", + "integrity": "sha512-VtAOaymWVfZcmZbp6E2mympDIHvyjXs/12LqWYjVw6qjrfF+VK+fyG33kChz3nnK+SU5/NeHOqrTEHS8sXO3OA==", "dev": true, + "license": "Apache-2.0", "engines": { "node": "^18.18.0 || ^20.9.0 || >=21.1.0" } }, "node_modules/@eslint/plugin-kit": { - "version": "0.3.5", - "resolved": "https://registry.npmjs.org/@eslint/plugin-kit/-/plugin-kit-0.3.5.tgz", - "integrity": "sha512-Z5kJ+wU3oA7MMIqVR9tyZRtjYPr4OC004Q4Rw7pgOKUOKkJfZ3O24nz3WYfGRpMDNmcOi3TwQOmgm7B7Tpii0w==", + "version": "0.4.1", + "resolved": "https://registry.npmjs.org/@eslint/plugin-kit/-/plugin-kit-0.4.1.tgz", + "integrity": "sha512-43/qtrDUokr7LJqoF2c3+RInu/t4zfrpYdoSDfYyhg52rwLV6TnOvdG4fXm7IkSB3wErkcmJS9iEhjVtOSEjjA==", "dev": true, + "license": "Apache-2.0", "dependencies": { - "@eslint/core": "^0.15.2", + "@eslint/core": "^0.17.0", "levn": "^0.4.1" }, "engines": { @@ -941,45 +933,48 @@ } }, "node_modules/@exodus/bytes": { - "version": "1.8.0", - "resolved": "https://registry.npmjs.org/@exodus/bytes/-/bytes-1.8.0.tgz", - "integrity": "sha512-8JPn18Bcp8Uo1T82gR8lh2guEOa5KKU/IEKvvdp0sgmi7coPBWf1Doi1EXsGZb2ehc8ym/StJCjffYV+ne7sXQ==", + "version": "1.10.0", + "resolved": "https://registry.npmjs.org/@exodus/bytes/-/bytes-1.10.0.tgz", + "integrity": "sha512-tf8YdcbirXdPnJ+Nd4UN1EXnz+IP2DI45YVEr3vvzcVTOyrApkmIB4zvOQVd3XPr7RXnfBtAx+PXImXOIU0Ajg==", "license": "MIT", "engines": { "node": "^20.19.0 || ^22.12.0 || >=24.0.0" }, "peerDependencies": { - "@exodus/crypto": "^1.0.0-rc.4" + "@noble/hashes": "^1.8.0 || ^2.0.0" }, "peerDependenciesMeta": { - "@exodus/crypto": { + "@noble/hashes": { "optional": true } } }, "node_modules/@floating-ui/core": { - "version": "1.7.3", - "resolved": "https://registry.npmjs.org/@floating-ui/core/-/core-1.7.3.tgz", - "integrity": "sha512-sGnvb5dmrJaKEZ+LDIpguvdX3bDlEllmv4/ClQ9awcmCZrlx5jQyyMWFM5kBI+EyNOCDDiKk8il0zeuX3Zlg/w==", + "version": "1.7.4", + "resolved": "https://registry.npmjs.org/@floating-ui/core/-/core-1.7.4.tgz", + "integrity": "sha512-C3HlIdsBxszvm5McXlB8PeOEWfBhcGBTZGkGlWc2U0KFY5IwG5OQEuQ8rq52DZmcHDlPLd+YFBK+cZcytwIFWg==", + "license": "MIT", "dependencies": { "@floating-ui/utils": "^0.2.10" } }, "node_modules/@floating-ui/dom": { - "version": "1.7.4", - "resolved": "https://registry.npmjs.org/@floating-ui/dom/-/dom-1.7.4.tgz", - "integrity": "sha512-OOchDgh4F2CchOX94cRVqhvy7b3AFb+/rQXyswmzmGakRfkMgoWVjfnLWkRirfLEfuD4ysVW16eXzwt3jHIzKA==", + "version": "1.7.5", + "resolved": "https://registry.npmjs.org/@floating-ui/dom/-/dom-1.7.5.tgz", + "integrity": "sha512-N0bD2kIPInNHUHehXhMke1rBGs1dwqvC9O9KYMyyjK7iXt7GAhnro7UlcuYcGdS/yYOlq0MAVgrow8IbWJwyqg==", + "license": "MIT", "dependencies": { - "@floating-ui/core": "^1.7.3", + "@floating-ui/core": "^1.7.4", "@floating-ui/utils": "^0.2.10" } }, "node_modules/@floating-ui/react-dom": { - "version": "2.1.6", - "resolved": "https://registry.npmjs.org/@floating-ui/react-dom/-/react-dom-2.1.6.tgz", - "integrity": "sha512-4JX6rEatQEvlmgU80wZyq9RT96HZJa88q8hp0pBd+LrczeDI4o6uA2M+uvxngVHo4Ihr8uibXxH6+70zhAFrVw==", + "version": "2.1.7", + "resolved": "https://registry.npmjs.org/@floating-ui/react-dom/-/react-dom-2.1.7.tgz", + "integrity": "sha512-0tLRojf/1Go2JgEVm+3Frg9A3IW8bJgKgdO0BN5RkF//ufuz2joZM63Npau2ff3J6lUVYgDSNzNkR+aH3IVfjg==", + "license": "MIT", "dependencies": { - "@floating-ui/dom": "^1.7.4" + "@floating-ui/dom": "^1.7.5" }, "peerDependencies": { "react": ">=16.8.0", @@ -989,7 +984,8 @@ "node_modules/@floating-ui/utils": { "version": "0.2.10", "resolved": "https://registry.npmjs.org/@floating-ui/utils/-/utils-0.2.10.tgz", - "integrity": "sha512-aGTxbpbg8/b5JfU1HXSrbH3wXZuLPJcNEcZQFMxLs3oSzgtVu6nFPkbbGGUvBcUjKV2YyB9Wxxabo+HEH9tcRQ==" + "integrity": "sha512-aGTxbpbg8/b5JfU1HXSrbH3wXZuLPJcNEcZQFMxLs3oSzgtVu6nFPkbbGGUvBcUjKV2YyB9Wxxabo+HEH9tcRQ==", + "license": "MIT" }, "node_modules/@google-cloud/secret-manager": { "version": "6.1.1", @@ -1039,41 +1035,31 @@ "resolved": "https://registry.npmjs.org/@humanfs/core/-/core-0.19.1.tgz", "integrity": "sha512-5DyQ4+1JEUzejeK1JGICcideyfUbGixgS9jNgex5nqkW+cY7WZhxBigmieN5Qnw9ZosSNVC9KQKyb+GUaGyKUA==", "dev": true, + "license": "Apache-2.0", "engines": { "node": ">=18.18.0" } }, "node_modules/@humanfs/node": { - "version": "0.16.6", - "resolved": "https://registry.npmjs.org/@humanfs/node/-/node-0.16.6.tgz", - "integrity": "sha512-YuI2ZHQL78Q5HbhDiBA1X4LmYdXCKCMQIfw0pw7piHJwyREFebJUvrQN4cMssyES6x+vfUbx1CIpaQUKYdQZOw==", + "version": "0.16.7", + "resolved": "https://registry.npmjs.org/@humanfs/node/-/node-0.16.7.tgz", + "integrity": "sha512-/zUx+yOsIrG4Y43Eh2peDeKCxlRt/gET6aHfaKpuq267qXdYDFViVHfMaLyygZOnl0kGWxFIgsBy8QFuTLUXEQ==", "dev": true, + "license": "Apache-2.0", "dependencies": { "@humanfs/core": "^0.19.1", - "@humanwhocodes/retry": "^0.3.0" + "@humanwhocodes/retry": "^0.4.0" }, "engines": { "node": ">=18.18.0" } }, - "node_modules/@humanfs/node/node_modules/@humanwhocodes/retry": { - "version": "0.3.1", - "resolved": "https://registry.npmjs.org/@humanwhocodes/retry/-/retry-0.3.1.tgz", - "integrity": "sha512-JBxkERygn7Bv/GbN5Rv8Ul6LVknS+5Bp6RgDC/O8gEBU/yeH5Ui5C/OlWrTb6qct7LjjfT6Re2NxB0ln0yYybA==", - "dev": true, - "engines": { - "node": ">=18.18" - }, - "funding": { - "type": "github", - "url": "https://github.com/sponsors/nzakas" - } - }, "node_modules/@humanwhocodes/module-importer": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/@humanwhocodes/module-importer/-/module-importer-1.0.1.tgz", "integrity": "sha512-bxveV4V8v5Yb4ncFTT3rPSgZBOpCkjfK0y4oVVVJwIuDVBRMDXrPyXRL988i5ap9m9bnyEEjWfm5WkBmtffLfA==", "dev": true, + "license": "Apache-2.0", "engines": { "node": ">=12.22" }, @@ -1087,6 +1073,7 @@ "resolved": "https://registry.npmjs.org/@humanwhocodes/retry/-/retry-0.4.3.tgz", "integrity": "sha512-bV0Tgo9K4hfPCek+aMAn81RppFKv2ySDQeMoSZuvTASywNTnVJCArCZE2FWqpvIatKu7VMRLWlR1EazvVhDyhQ==", "dev": true, + "license": "Apache-2.0", "engines": { "node": ">=18.18" }, @@ -1099,6 +1086,7 @@ "version": "1.0.0", "resolved": "https://registry.npmjs.org/@img/colour/-/colour-1.0.0.tgz", "integrity": "sha512-A5P/LfWGFSl6nsckYtjw9da+19jB8hkJ6ACTGcDfEJ0aE+l2n2El7dsVM7UVHZQ9s2lmYMWlrS21YLy2IR1LUw==", + "license": "MIT", "engines": { "node": ">=18" } @@ -1581,6 +1569,7 @@ "resolved": "https://registry.npmjs.org/@jridgewell/gen-mapping/-/gen-mapping-0.3.13.tgz", "integrity": "sha512-2kkt/7niJ6MgEPxF0bYdQ6etZaA+fQvDcLKckhy1yIQOzaoKjBBjSj63/aLVjYE3qhRt5dvM+uUyfCg6UKCBbA==", "dev": true, + "license": "MIT", "dependencies": { "@jridgewell/sourcemap-codec": "^1.5.0", "@jridgewell/trace-mapping": "^0.3.24" @@ -1591,6 +1580,7 @@ "resolved": "https://registry.npmjs.org/@jridgewell/resolve-uri/-/resolve-uri-3.1.2.tgz", "integrity": "sha512-bRISgCIjP20/tbWSPWMEi54QVPRZExkuD9lJL+UIxUKtwVJA8wW1Trb1jMs1RFXo1CBTNZ/5hpC9QvmKWdopKw==", "dev": true, + "license": "MIT", "engines": { "node": ">=6.0.0" } @@ -1599,13 +1589,15 @@ "version": "1.5.5", "resolved": "https://registry.npmjs.org/@jridgewell/sourcemap-codec/-/sourcemap-codec-1.5.5.tgz", "integrity": "sha512-cYQ9310grqxueWbl+WuIUIaiUaDcj7WOq5fVhEljNVgRfOUhY9fy2zTvfoqWsnebh8Sl70VScFbICvJnLKB0Og==", - "dev": true + "dev": true, + "license": "MIT" }, "node_modules/@jridgewell/trace-mapping": { - "version": "0.3.30", - "resolved": "https://registry.npmjs.org/@jridgewell/trace-mapping/-/trace-mapping-0.3.30.tgz", - "integrity": "sha512-GQ7Nw5G2lTu/BtHTKfXhKHok2WGetd4XYcVKGx00SjAk8GMwgJM3zr6zORiPGuOE+/vkc90KtTosSSvaCjKb2Q==", + "version": "0.3.31", + "resolved": "https://registry.npmjs.org/@jridgewell/trace-mapping/-/trace-mapping-0.3.31.tgz", + "integrity": "sha512-zzNR+SdQSDJzc8joaeP8QQoCQr8NuYx2dIIytl1QeBEZHJ9uW6hebsrYgbz8hJwUQao3TWCMtmfV8Nu1twOLAw==", "dev": true, + "license": "MIT", "dependencies": { "@jridgewell/resolve-uri": "^3.1.0", "@jridgewell/sourcemap-codec": "^1.4.14" @@ -1654,9 +1646,9 @@ } }, "node_modules/@next/env": { - "version": "15.5.9", - "resolved": "https://registry.npmjs.org/@next/env/-/env-15.5.9.tgz", - "integrity": "sha512-4GlTZ+EJM7WaW2HEZcyU317tIQDjkQIyENDLxYJfSWlfqguN+dHkZgyQTV/7ykvobU7yEH5gKvreNrH4B6QgIg==", + "version": "15.5.11", + "resolved": "https://registry.npmjs.org/@next/env/-/env-15.5.11.tgz", + "integrity": "sha512-g9s5SS9gC7GJCEOR3OV3zqs7C5VddqxP9X+/6BpMbdXRkqsWfFf2CJPBZNvNEtAkKTNuRgRXAgNxSAXzfLdaTg==", "license": "MIT" }, "node_modules/@next/eslint-plugin-next": { @@ -1664,6 +1656,7 @@ "resolved": "https://registry.npmjs.org/@next/eslint-plugin-next/-/eslint-plugin-next-15.3.1.tgz", "integrity": "sha512-oEs4dsfM6iyER3jTzMm4kDSbrQJq8wZw5fmT6fg2V3SMo+kgG+cShzLfEV20senZzv8VF+puNLheiGPlBGsv2A==", "dev": true, + "license": "MIT", "dependencies": { "fast-glob": "3.3.1" } @@ -1801,6 +1794,7 @@ "resolved": "https://registry.npmjs.org/@nodelib/fs.scandir/-/fs.scandir-2.1.5.tgz", "integrity": "sha512-vq24Bq3ym5HEQm2NKCr3yXDwjc7vTsEThRDnkp2DK9p1uqLR+DHurm/NOTo0KG7HYHU7eppKZj3MyqYuMBf62g==", "dev": true, + "license": "MIT", "dependencies": { "@nodelib/fs.stat": "2.0.5", "run-parallel": "^1.1.9" @@ -1814,6 +1808,7 @@ "resolved": "https://registry.npmjs.org/@nodelib/fs.stat/-/fs.stat-2.0.5.tgz", "integrity": "sha512-RkhPPp2zrqDAQA/2jNhnztcPAlv64XdhIp7a7454A5ovI7Bukxgt7MX7udwAu3zg1DcpPU0rz3VV1SeaqvY4+A==", "dev": true, + "license": "MIT", "engines": { "node": ">= 8" } @@ -1823,6 +1818,7 @@ "resolved": "https://registry.npmjs.org/@nodelib/fs.walk/-/fs.walk-1.2.8.tgz", "integrity": "sha512-oGB+UxlgWcgQkgwo8GcEGwemoTFt3FIO9ababBmaGwXIoBKZ+GTy0pP185beGg7Llih/NSHSV2XAs1lnznocSg==", "dev": true, + "license": "MIT", "dependencies": { "@nodelib/fs.scandir": "2.1.5", "fastq": "^1.6.0" @@ -1836,14 +1832,15 @@ "resolved": "https://registry.npmjs.org/@nolyfill/is-core-module/-/is-core-module-1.0.39.tgz", "integrity": "sha512-nn5ozdjYQpUCZlWGuxcJY/KpxkWQs4DcbMCmKojjyrYDEAGy4Ce19NN4v5MduafTwJlbKc99UA8YhSVqq9yPZA==", "dev": true, + "license": "MIT", "engines": { "node": ">=12.4.0" } }, "node_modules/@oxc-resolver/binding-android-arm-eabi": { - "version": "11.16.3", - "resolved": "https://registry.npmjs.org/@oxc-resolver/binding-android-arm-eabi/-/binding-android-arm-eabi-11.16.3.tgz", - "integrity": "sha512-CVyWHu6ACDqDcJxR4nmGiG8vDF4TISJHqRNzac5z/gPQycs/QrP/1pDsJBy0MD7jSw8nVq2E5WqeHQKabBG/Jg==", + "version": "11.17.0", + "resolved": "https://registry.npmjs.org/@oxc-resolver/binding-android-arm-eabi/-/binding-android-arm-eabi-11.17.0.tgz", + "integrity": "sha512-kVnY21v0GyZ/+LG6EIO48wK3mE79BUuakHUYLIqobO/Qqq4mJsjuYXMSn3JtLcKZpN1HDVit4UHpGJHef1lrlw==", "cpu": [ "arm" ], @@ -1855,9 +1852,9 @@ ] }, "node_modules/@oxc-resolver/binding-android-arm64": { - "version": "11.16.3", - "resolved": "https://registry.npmjs.org/@oxc-resolver/binding-android-arm64/-/binding-android-arm64-11.16.3.tgz", - "integrity": "sha512-tTIoB7plLeh2o6Ay7NnV5CJb6QUXdxI7Shnsp2ECrLSV81k+oVE3WXYrQSh4ltWL75i0OgU5Bj3bsuyg5SMepw==", + "version": "11.17.0", + "resolved": "https://registry.npmjs.org/@oxc-resolver/binding-android-arm64/-/binding-android-arm64-11.17.0.tgz", + "integrity": "sha512-Pf8e3XcsK9a8RHInoAtEcrwf2vp7V9bSturyUUYxw9syW6E7cGi7z9+6ADXxm+8KAevVfLA7pfBg8NXTvz/HOw==", "cpu": [ "arm64" ], @@ -1869,9 +1866,9 @@ ] }, "node_modules/@oxc-resolver/binding-darwin-arm64": { - "version": "11.16.3", - "resolved": "https://registry.npmjs.org/@oxc-resolver/binding-darwin-arm64/-/binding-darwin-arm64-11.16.3.tgz", - "integrity": "sha512-OXKVH7uwYd3Rbw1s2yJZd6/w+6b01iaokZubYhDAq4tOYArr+YCS+lr81q1hsTPPRZeIsWE+rJLulmf1qHdYZA==", + "version": "11.17.0", + "resolved": "https://registry.npmjs.org/@oxc-resolver/binding-darwin-arm64/-/binding-darwin-arm64-11.17.0.tgz", + "integrity": "sha512-lVSgKt3biecofXVr8e1hnfX0IYMd4A6VCxmvOmHsFt5Zbmt0lkO4S2ap2bvQwYDYh5ghUNamC7M2L8K6vishhQ==", "cpu": [ "arm64" ], @@ -1883,9 +1880,9 @@ ] }, "node_modules/@oxc-resolver/binding-darwin-x64": { - "version": "11.16.3", - "resolved": "https://registry.npmjs.org/@oxc-resolver/binding-darwin-x64/-/binding-darwin-x64-11.16.3.tgz", - "integrity": "sha512-WwjQ4WdnCxVYZYd3e3oY5XbV3JeLy9pPMK+eQQ2m8DtqUtbxnvPpAYC2Knv/2bS6q5JiktqOVJ2Hfia3OSo0/A==", + "version": "11.17.0", + "resolved": "https://registry.npmjs.org/@oxc-resolver/binding-darwin-x64/-/binding-darwin-x64-11.17.0.tgz", + "integrity": "sha512-+/raxVJE1bo7R4fA9Yp0wm3slaCOofTEeUzM01YqEGcRDLHB92WRGjRhagMG2wGlvqFuSiTp81DwSbBVo/g6AQ==", "cpu": [ "x64" ], @@ -1897,9 +1894,9 @@ ] }, "node_modules/@oxc-resolver/binding-freebsd-x64": { - "version": "11.16.3", - "resolved": "https://registry.npmjs.org/@oxc-resolver/binding-freebsd-x64/-/binding-freebsd-x64-11.16.3.tgz", - "integrity": "sha512-4OHKFGJBBfOnuJnelbCS4eBorI6cj54FUxcZJwEXPeoLc8yzORBoJ2w+fQbwjlQcUUZLEg92uGhKCRiUoqznjg==", + "version": "11.17.0", + "resolved": "https://registry.npmjs.org/@oxc-resolver/binding-freebsd-x64/-/binding-freebsd-x64-11.17.0.tgz", + "integrity": "sha512-x9Ks56n+n8h0TLhzA6sJXa2tGh3uvMGpBppg6PWf8oF0s5S/3p/J6k1vJJ9lIUtTmenfCQEGKnFokpRP4fLTLg==", "cpu": [ "x64" ], @@ -1911,9 +1908,9 @@ ] }, "node_modules/@oxc-resolver/binding-linux-arm-gnueabihf": { - "version": "11.16.3", - "resolved": "https://registry.npmjs.org/@oxc-resolver/binding-linux-arm-gnueabihf/-/binding-linux-arm-gnueabihf-11.16.3.tgz", - "integrity": "sha512-OM3W0NLt9u7uKwG/yZbeXABansZC0oZeDF1nKgvcZoRw4/Yak6/l4S0onBfDFeYMY94eYeAt2bl60e30lgsb5A==", + "version": "11.17.0", + "resolved": "https://registry.npmjs.org/@oxc-resolver/binding-linux-arm-gnueabihf/-/binding-linux-arm-gnueabihf-11.17.0.tgz", + "integrity": "sha512-Wf3w07Ow9kXVJrS0zmsaFHKOGhXKXE8j1tNyy+qIYDsQWQ4UQZVx5SjlDTcqBnFerlp3Z3Is0RjmVzgoLG3qkA==", "cpu": [ "arm" ], @@ -1925,9 +1922,9 @@ ] }, "node_modules/@oxc-resolver/binding-linux-arm-musleabihf": { - "version": "11.16.3", - "resolved": "https://registry.npmjs.org/@oxc-resolver/binding-linux-arm-musleabihf/-/binding-linux-arm-musleabihf-11.16.3.tgz", - "integrity": "sha512-MRs7D7i1t7ACsAdTuP81gLZES918EpBmiUyEl8fu302yQB+4L7L7z0Ui8BWnthUTQd3nAU9dXvENLK/SqRVH8A==", + "version": "11.17.0", + "resolved": "https://registry.npmjs.org/@oxc-resolver/binding-linux-arm-musleabihf/-/binding-linux-arm-musleabihf-11.17.0.tgz", + "integrity": "sha512-N0OKA1al1gQ5Gm7Fui1RWlXaHRNZlwMoBLn3TVtSXX+WbnlZoVyDqqOqFL8+pVEHhhxEA2LR8kmM0JO6FAk6dg==", "cpu": [ "arm" ], @@ -1939,9 +1936,9 @@ ] }, "node_modules/@oxc-resolver/binding-linux-arm64-gnu": { - "version": "11.16.3", - "resolved": "https://registry.npmjs.org/@oxc-resolver/binding-linux-arm64-gnu/-/binding-linux-arm64-gnu-11.16.3.tgz", - "integrity": "sha512-0eVYZxSceNqGADzhlV4ZRqkHF0fjWxRXQOB7Qwl5y1gN/XYUDvMfip+ngtzj4dM7zQT4U97hUhJ7PUKSy/JIGQ==", + "version": "11.17.0", + "resolved": "https://registry.npmjs.org/@oxc-resolver/binding-linux-arm64-gnu/-/binding-linux-arm64-gnu-11.17.0.tgz", + "integrity": "sha512-wdcQ7Niad9JpjZIGEeqKJnTvczVunqlZ/C06QzR5zOQNeLVRScQ9S5IesKWUAPsJQDizV+teQX53nTK+Z5Iy+g==", "cpu": [ "arm64" ], @@ -1953,9 +1950,9 @@ ] }, "node_modules/@oxc-resolver/binding-linux-arm64-musl": { - "version": "11.16.3", - "resolved": "https://registry.npmjs.org/@oxc-resolver/binding-linux-arm64-musl/-/binding-linux-arm64-musl-11.16.3.tgz", - "integrity": "sha512-B1BvLeZbgDdVN0FvU40l5Q7lej8310WlabCBaouk8jY7H7xbI8phtomTtk3Efmevgfy5hImaQJu6++OmcFb2NQ==", + "version": "11.17.0", + "resolved": "https://registry.npmjs.org/@oxc-resolver/binding-linux-arm64-musl/-/binding-linux-arm64-musl-11.17.0.tgz", + "integrity": "sha512-65B2/t39HQN5AEhkLsC+9yBD1iRUkKOIhfmJEJ7g6wQ9kylra7JRmNmALFjbsj0VJsoSQkpM8K07kUZuNJ9Kxw==", "cpu": [ "arm64" ], @@ -1967,9 +1964,9 @@ ] }, "node_modules/@oxc-resolver/binding-linux-ppc64-gnu": { - "version": "11.16.3", - "resolved": "https://registry.npmjs.org/@oxc-resolver/binding-linux-ppc64-gnu/-/binding-linux-ppc64-gnu-11.16.3.tgz", - "integrity": "sha512-q7khglic3Jqak7uDgA3MFnjDeI7krQT595GDZpvFq785fmFYSx8rlTkoHzmhQtUisYtl4XG7WUscwsoidFUI4w==", + "version": "11.17.0", + "resolved": "https://registry.npmjs.org/@oxc-resolver/binding-linux-ppc64-gnu/-/binding-linux-ppc64-gnu-11.17.0.tgz", + "integrity": "sha512-kExgm3TLK21dNMmcH+xiYGbc6BUWvT03PUZ2aYn8mUzGPeeORklBhg3iYcaBI3ZQHB25412X1Z6LLYNjt4aIaA==", "cpu": [ "ppc64" ], @@ -1981,9 +1978,9 @@ ] }, "node_modules/@oxc-resolver/binding-linux-riscv64-gnu": { - "version": "11.16.3", - "resolved": "https://registry.npmjs.org/@oxc-resolver/binding-linux-riscv64-gnu/-/binding-linux-riscv64-gnu-11.16.3.tgz", - "integrity": "sha512-aFRNmQNPzDgQEbw2s3c8yJYRimacSDI+u9df8rn5nSKzTVitHmbEpZqfxpwNLCKIuLSNmozHR1z1OT+oZVeYqg==", + "version": "11.17.0", + "resolved": "https://registry.npmjs.org/@oxc-resolver/binding-linux-riscv64-gnu/-/binding-linux-riscv64-gnu-11.17.0.tgz", + "integrity": "sha512-1utUJC714/ydykZQE8c7QhpEyM4SaslMfRXxN9G61KYazr6ndt85LaubK3EZCSD50vVEfF4PVwFysCSO7LN9uA==", "cpu": [ "riscv64" ], @@ -1995,9 +1992,9 @@ ] }, "node_modules/@oxc-resolver/binding-linux-riscv64-musl": { - "version": "11.16.3", - "resolved": "https://registry.npmjs.org/@oxc-resolver/binding-linux-riscv64-musl/-/binding-linux-riscv64-musl-11.16.3.tgz", - "integrity": "sha512-vZI85SvSMADcEL9G1TIrV0Rlkc1fY5Mup0DdlVC5EHPysZB4hXXHpr+h09pjlK5y+5om5foIzDRxE1baUCaWOA==", + "version": "11.17.0", + "resolved": "https://registry.npmjs.org/@oxc-resolver/binding-linux-riscv64-musl/-/binding-linux-riscv64-musl-11.17.0.tgz", + "integrity": "sha512-mayiYOl3LMmtO2CLn4I5lhanfxEo0LAqlT/EQyFbu1ZN3RS+Xa7Q3JEM0wBpVIyfO/pqFrjvC5LXw/mHNDEL7A==", "cpu": [ "riscv64" ], @@ -2009,9 +2006,9 @@ ] }, "node_modules/@oxc-resolver/binding-linux-s390x-gnu": { - "version": "11.16.3", - "resolved": "https://registry.npmjs.org/@oxc-resolver/binding-linux-s390x-gnu/-/binding-linux-s390x-gnu-11.16.3.tgz", - "integrity": "sha512-xiLBnaUlddFEzRHiHiSGEMbkg8EwZY6VD8F+3GfnFsiK3xg/4boaUV2bwXd+nUzl3UDQOMW1QcZJ4jJSb0qiJA==", + "version": "11.17.0", + "resolved": "https://registry.npmjs.org/@oxc-resolver/binding-linux-s390x-gnu/-/binding-linux-s390x-gnu-11.17.0.tgz", + "integrity": "sha512-Ow/yI+CrUHxIIhn/Y1sP/xoRKbCC3x9O1giKr3G/pjMe+TCJ5ZmfqVWU61JWwh1naC8X5Xa7uyLnbzyYqPsHfg==", "cpu": [ "s390x" ], @@ -2023,9 +2020,9 @@ ] }, "node_modules/@oxc-resolver/binding-linux-x64-gnu": { - "version": "11.16.3", - "resolved": "https://registry.npmjs.org/@oxc-resolver/binding-linux-x64-gnu/-/binding-linux-x64-gnu-11.16.3.tgz", - "integrity": "sha512-6y0b05wIazJJgwu7yU/AYGFswzQQudYJBOb/otDhiDacp1+6ye8egoxx63iVo9lSpDbipL++54AJQFlcOHCB+g==", + "version": "11.17.0", + "resolved": "https://registry.npmjs.org/@oxc-resolver/binding-linux-x64-gnu/-/binding-linux-x64-gnu-11.17.0.tgz", + "integrity": "sha512-Z4J7XlPMQOLPANyu6y3B3V417Md4LKH5bV6bhqgaG99qLHmU5LV2k9ErV14fSqoRc/GU/qOpqMdotxiJqN/YWg==", "cpu": [ "x64" ], @@ -2037,9 +2034,9 @@ ] }, "node_modules/@oxc-resolver/binding-linux-x64-musl": { - "version": "11.16.3", - "resolved": "https://registry.npmjs.org/@oxc-resolver/binding-linux-x64-musl/-/binding-linux-x64-musl-11.16.3.tgz", - "integrity": "sha512-RmMgwuMa42c9logS7Pjprf5KCp8J1a1bFiuBFtG9/+yMu0BhY2t+0VR/um7pwtkNFvIQqAVh6gDOg/PnoKRcdQ==", + "version": "11.17.0", + "resolved": "https://registry.npmjs.org/@oxc-resolver/binding-linux-x64-musl/-/binding-linux-x64-musl-11.17.0.tgz", + "integrity": "sha512-0effK+8lhzXsgsh0Ny2ngdnTPF30v6QQzVFApJ1Ctk315YgpGkghkelvrLYYgtgeFJFrzwmOJ2nDvCrUFKsS2Q==", "cpu": [ "x64" ], @@ -2051,9 +2048,9 @@ ] }, "node_modules/@oxc-resolver/binding-openharmony-arm64": { - "version": "11.16.3", - "resolved": "https://registry.npmjs.org/@oxc-resolver/binding-openharmony-arm64/-/binding-openharmony-arm64-11.16.3.tgz", - "integrity": "sha512-/7AYRkjjW7xu1nrHgWUFy99Duj4/ydOBVaHtODie9/M6fFngo+8uQDFFnzmr4q//sd/cchIerISp/8CQ5TsqIA==", + "version": "11.17.0", + "resolved": "https://registry.npmjs.org/@oxc-resolver/binding-openharmony-arm64/-/binding-openharmony-arm64-11.17.0.tgz", + "integrity": "sha512-kFB48dRUW6RovAICZaxHKdtZe+e94fSTNA2OedXokzMctoU54NPZcv0vUX5PMqyikLIKJBIlW7laQidnAzNrDA==", "cpu": [ "arm64" ], @@ -2065,9 +2062,9 @@ ] }, "node_modules/@oxc-resolver/binding-wasm32-wasi": { - "version": "11.16.3", - "resolved": "https://registry.npmjs.org/@oxc-resolver/binding-wasm32-wasi/-/binding-wasm32-wasi-11.16.3.tgz", - "integrity": "sha512-urM6aIPbi5di4BSlnpd/TWtDJgG6RD06HvLBuNM+qOYuFtY1/xPbzQ2LanBI2ycpqIoIZwsChyplALwAMdyfCQ==", + "version": "11.17.0", + "resolved": "https://registry.npmjs.org/@oxc-resolver/binding-wasm32-wasi/-/binding-wasm32-wasi-11.17.0.tgz", + "integrity": "sha512-a3elKSBLPT0OoRPxTkCIIc+4xnOELolEBkPyvdj01a6PSdSmyJ1NExWjWLaXnT6wBMblvKde5RmSwEi3j+jZpg==", "cpu": [ "wasm32" ], @@ -2082,9 +2079,9 @@ } }, "node_modules/@oxc-resolver/binding-win32-arm64-msvc": { - "version": "11.16.3", - "resolved": "https://registry.npmjs.org/@oxc-resolver/binding-win32-arm64-msvc/-/binding-win32-arm64-msvc-11.16.3.tgz", - "integrity": "sha512-QuvLqGKf7frxWHQ5TnrcY0C/hJpANsaez99Q4dAk1hen7lDTD4FBPtBzPnntLFXeaVG3PnSmnVjlv0vMILwU7Q==", + "version": "11.17.0", + "resolved": "https://registry.npmjs.org/@oxc-resolver/binding-win32-arm64-msvc/-/binding-win32-arm64-msvc-11.17.0.tgz", + "integrity": "sha512-4eszUsSDb9YVx0RtYkPWkxxtSZIOgfeiX//nG5cwRRArg178w4RCqEF1kbKPud9HPrp1rXh7gE4x911OhvTnPg==", "cpu": [ "arm64" ], @@ -2096,9 +2093,9 @@ ] }, "node_modules/@oxc-resolver/binding-win32-ia32-msvc": { - "version": "11.16.3", - "resolved": "https://registry.npmjs.org/@oxc-resolver/binding-win32-ia32-msvc/-/binding-win32-ia32-msvc-11.16.3.tgz", - "integrity": "sha512-QR/witXK6BmYTlEP8CCjC5fxeG5U9A6a50pNpC1nLnhAcJjtzFG8KcQ5etVy/XvCLiDc7fReaAWRNWtCaIhM8Q==", + "version": "11.17.0", + "resolved": "https://registry.npmjs.org/@oxc-resolver/binding-win32-ia32-msvc/-/binding-win32-ia32-msvc-11.17.0.tgz", + "integrity": "sha512-t946xTXMmR7yGH0KAe9rB055/X4EPIu93JUvjchl2cizR5QbuwkUV7vLS2BS6x6sfvDoQb6rWYnV1HCci6tBSg==", "cpu": [ "ia32" ], @@ -2110,9 +2107,9 @@ ] }, "node_modules/@oxc-resolver/binding-win32-x64-msvc": { - "version": "11.16.3", - "resolved": "https://registry.npmjs.org/@oxc-resolver/binding-win32-x64-msvc/-/binding-win32-x64-msvc-11.16.3.tgz", - "integrity": "sha512-bFuJRKOscsDAEZ/a8BezcTMAe2BQ/OBRfuMLFUuINfTR5qGVcm4a3xBIrQVepBaPxFj16SJdRjGe05vDiwZmFw==", + "version": "11.17.0", + "resolved": "https://registry.npmjs.org/@oxc-resolver/binding-win32-x64-msvc/-/binding-win32-x64-msvc-11.17.0.tgz", + "integrity": "sha512-pX6s2kMXLQg+hlqKk5UqOW09iLLxnTkvn8ohpYp2Mhsm2yzDPCx9dyOHiB/CQixLzTkLQgWWJykN4Z3UfRKW4Q==", "cpu": [ "x64" ], @@ -2127,6 +2124,7 @@ "version": "0.11.0", "resolved": "https://registry.npmjs.org/@pkgjs/parseargs/-/parseargs-0.11.0.tgz", "integrity": "sha512-+1VkjdD0QBLPodGrJUeqarH8VAIvQODIbwh9XpP5Syisf7YoQgsJKPNFoqqLQlu+VQ/tVSshMR6loPMn8U+dPg==", + "license": "MIT", "optional": true, "engines": { "node": ">=14" @@ -2199,12 +2197,14 @@ "node_modules/@radix-ui/primitive": { "version": "1.1.3", "resolved": "https://registry.npmjs.org/@radix-ui/primitive/-/primitive-1.1.3.tgz", - "integrity": "sha512-JTF99U/6XIjCBo0wqkU5sK10glYe27MRRsfwoiq5zzOEZLHU3A3KCMa5X/azekYRCJ0HlwI0crAXS/5dEHTzDg==" + "integrity": "sha512-JTF99U/6XIjCBo0wqkU5sK10glYe27MRRsfwoiq5zzOEZLHU3A3KCMa5X/azekYRCJ0HlwI0crAXS/5dEHTzDg==", + "license": "MIT" }, "node_modules/@radix-ui/react-arrow": { "version": "1.1.7", "resolved": "https://registry.npmjs.org/@radix-ui/react-arrow/-/react-arrow-1.1.7.tgz", "integrity": "sha512-F+M1tLhO+mlQaOWspE8Wstg+z6PwxwRd8oQ8IXceWz92kfAmalTRf0EjrouQeo7QssEPfCn05B4Ihs1K9WQ/7w==", + "license": "MIT", "dependencies": { "@radix-ui/react-primitive": "2.1.3" }, @@ -2227,6 +2227,7 @@ "version": "1.3.3", "resolved": "https://registry.npmjs.org/@radix-ui/react-checkbox/-/react-checkbox-1.3.3.tgz", "integrity": "sha512-wBbpv+NQftHDdG86Qc0pIyXk5IR3tM8Vd0nWLKDcX8nNn4nXFOFwsKuqw2okA/1D/mpaAkmuyndrPJTYDNZtFw==", + "license": "MIT", "dependencies": { "@radix-ui/primitive": "1.1.3", "@radix-ui/react-compose-refs": "1.1.2", @@ -2256,6 +2257,7 @@ "version": "1.1.7", "resolved": "https://registry.npmjs.org/@radix-ui/react-collection/-/react-collection-1.1.7.tgz", "integrity": "sha512-Fh9rGN0MoI4ZFUNyfFVNU4y9LUz93u9/0K+yLgA2bwRojxM8JU1DyvvMBabnZPBgMWREAJvU2jjVzq+LrFUglw==", + "license": "MIT", "dependencies": { "@radix-ui/react-compose-refs": "1.1.2", "@radix-ui/react-context": "1.1.2", @@ -2277,10 +2279,29 @@ } } }, + "node_modules/@radix-ui/react-collection/node_modules/@radix-ui/react-slot": { + "version": "1.2.3", + "resolved": "https://registry.npmjs.org/@radix-ui/react-slot/-/react-slot-1.2.3.tgz", + "integrity": "sha512-aeNmHnBxbi2St0au6VBVC7JXFlhLlOnvIIlePNniyUNAClzmtAUEY8/pBiK3iHjufOlwA+c20/8jngo7xcrg8A==", + "license": "MIT", + "dependencies": { + "@radix-ui/react-compose-refs": "1.1.2" + }, + "peerDependencies": { + "@types/react": "*", + "react": "^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc" + }, + "peerDependenciesMeta": { + "@types/react": { + "optional": true + } + } + }, "node_modules/@radix-ui/react-compose-refs": { "version": "1.1.2", "resolved": "https://registry.npmjs.org/@radix-ui/react-compose-refs/-/react-compose-refs-1.1.2.tgz", "integrity": "sha512-z4eqJvfiNnFMHIIvXP3CY57y2WJs5g2v3X0zm9mEJkrkNv4rDxu+sg9Jh8EkXyeqBkB7SOcboo9dMVqhyrACIg==", + "license": "MIT", "peerDependencies": { "@types/react": "*", "react": "^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc" @@ -2295,6 +2316,7 @@ "version": "1.1.2", "resolved": "https://registry.npmjs.org/@radix-ui/react-context/-/react-context-1.1.2.tgz", "integrity": "sha512-jCi/QKUM2r1Ju5a3J64TH2A5SpKAgh0LpknyqdQ4m6DCV0xJ2HG1xARRwNGPQfi1SLdLWZ1OJz6F4OMBBNiGJA==", + "license": "MIT", "peerDependencies": { "@types/react": "*", "react": "^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc" @@ -2341,10 +2363,29 @@ } } }, + "node_modules/@radix-ui/react-dialog/node_modules/@radix-ui/react-slot": { + "version": "1.2.3", + "resolved": "https://registry.npmjs.org/@radix-ui/react-slot/-/react-slot-1.2.3.tgz", + "integrity": "sha512-aeNmHnBxbi2St0au6VBVC7JXFlhLlOnvIIlePNniyUNAClzmtAUEY8/pBiK3iHjufOlwA+c20/8jngo7xcrg8A==", + "license": "MIT", + "dependencies": { + "@radix-ui/react-compose-refs": "1.1.2" + }, + "peerDependencies": { + "@types/react": "*", + "react": "^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc" + }, + "peerDependenciesMeta": { + "@types/react": { + "optional": true + } + } + }, "node_modules/@radix-ui/react-direction": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/@radix-ui/react-direction/-/react-direction-1.1.1.tgz", "integrity": "sha512-1UEWRX6jnOA2y4H5WczZ44gOOjTEmlqv1uNW4GAJEO5+bauCBhv8snY65Iw5/VOS/ghKN9gr2KjnLKxrsvoMVw==", + "license": "MIT", "peerDependencies": { "@types/react": "*", "react": "^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc" @@ -2359,6 +2400,7 @@ "version": "1.1.11", "resolved": "https://registry.npmjs.org/@radix-ui/react-dismissable-layer/-/react-dismissable-layer-1.1.11.tgz", "integrity": "sha512-Nqcp+t5cTB8BinFkZgXiMJniQH0PsUt2k51FUhbdfeKvc4ACcG2uQniY/8+h1Yv6Kza4Q7lD7PQV0z0oicE0Mg==", + "license": "MIT", "dependencies": { "@radix-ui/primitive": "1.1.3", "@radix-ui/react-compose-refs": "1.1.2", @@ -2385,6 +2427,7 @@ "version": "2.1.16", "resolved": "https://registry.npmjs.org/@radix-ui/react-dropdown-menu/-/react-dropdown-menu-2.1.16.tgz", "integrity": "sha512-1PLGQEynI/3OX/ftV54COn+3Sud/Mn8vALg2rWnBLnRaGtJDduNW/22XjlGgPdpcIbiQxjKtb7BkcjP00nqfJw==", + "license": "MIT", "dependencies": { "@radix-ui/primitive": "1.1.3", "@radix-ui/react-compose-refs": "1.1.2", @@ -2413,6 +2456,7 @@ "version": "1.1.3", "resolved": "https://registry.npmjs.org/@radix-ui/react-focus-guards/-/react-focus-guards-1.1.3.tgz", "integrity": "sha512-0rFg/Rj2Q62NCm62jZw0QX7a3sz6QCQU0LpZdNrJX8byRGaGVTqbrW9jAoIAHyMQqsNpeZ81YgSizOt5WXq0Pw==", + "license": "MIT", "peerDependencies": { "@types/react": "*", "react": "^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc" @@ -2427,6 +2471,7 @@ "version": "1.1.7", "resolved": "https://registry.npmjs.org/@radix-ui/react-focus-scope/-/react-focus-scope-1.1.7.tgz", "integrity": "sha512-t2ODlkXBQyn7jkl6TNaw/MtVEVvIGelJDCG41Okq/KwUsJBwQ4XVZsHAVUkK4mBv3ewiAS3PGuUWuY2BoK4ZUw==", + "license": "MIT", "dependencies": { "@radix-ui/react-compose-refs": "1.1.2", "@radix-ui/react-primitive": "2.1.3", @@ -2451,6 +2496,7 @@ "version": "1.1.1", "resolved": "https://registry.npmjs.org/@radix-ui/react-id/-/react-id-1.1.1.tgz", "integrity": "sha512-kGkGegYIdQsOb4XjsfM97rXsiHaBwco+hFI66oO4s9LU+PLAC5oJ7khdOVFxkhsmlbpUqDAvXw11CluXP+jkHg==", + "license": "MIT", "dependencies": { "@radix-ui/react-use-layout-effect": "1.1.1" }, @@ -2465,11 +2511,35 @@ } }, "node_modules/@radix-ui/react-label": { - "version": "2.1.7", - "resolved": "https://registry.npmjs.org/@radix-ui/react-label/-/react-label-2.1.7.tgz", - "integrity": "sha512-YT1GqPSL8kJn20djelMX7/cTRp/Y9w5IZHvfxQTVHrOqa2yMl7i/UfMqKRU5V7mEyKTrUVgJXhNQPVCG8PBLoQ==", + "version": "2.1.8", + "resolved": "https://registry.npmjs.org/@radix-ui/react-label/-/react-label-2.1.8.tgz", + "integrity": "sha512-FmXs37I6hSBVDlO4y764TNz1rLgKwjJMQ0EGte6F3Cb3f4bIuHB/iLa/8I9VKkmOy+gNHq8rql3j686ACVV21A==", + "license": "MIT", "dependencies": { - "@radix-ui/react-primitive": "2.1.3" + "@radix-ui/react-primitive": "2.1.4" + }, + "peerDependencies": { + "@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": { + "optional": true + }, + "@types/react-dom": { + "optional": true + } + } + }, + "node_modules/@radix-ui/react-label/node_modules/@radix-ui/react-primitive": { + "version": "2.1.4", + "resolved": "https://registry.npmjs.org/@radix-ui/react-primitive/-/react-primitive-2.1.4.tgz", + "integrity": "sha512-9hQc4+GNVtJAIEPEqlYqW5RiYdrr8ea5XQ0ZOnD6fgru+83kqT15mq2OCcbe8KnjRZl5vF3ks69AKz3kh1jrhg==", + "license": "MIT", + "dependencies": { + "@radix-ui/react-slot": "1.2.4" }, "peerDependencies": { "@types/react": "*", @@ -2490,6 +2560,7 @@ "version": "2.1.16", "resolved": "https://registry.npmjs.org/@radix-ui/react-menu/-/react-menu-2.1.16.tgz", "integrity": "sha512-72F2T+PLlphrqLcAotYPp0uJMr5SjP5SL01wfEspJbru5Zs5vQaSHb4VB3ZMJPimgHHCHG7gMOeOB9H3Hdmtxg==", + "license": "MIT", "dependencies": { "@radix-ui/primitive": "1.1.3", "@radix-ui/react-collection": "1.1.7", @@ -2525,10 +2596,29 @@ } } }, + "node_modules/@radix-ui/react-menu/node_modules/@radix-ui/react-slot": { + "version": "1.2.3", + "resolved": "https://registry.npmjs.org/@radix-ui/react-slot/-/react-slot-1.2.3.tgz", + "integrity": "sha512-aeNmHnBxbi2St0au6VBVC7JXFlhLlOnvIIlePNniyUNAClzmtAUEY8/pBiK3iHjufOlwA+c20/8jngo7xcrg8A==", + "license": "MIT", + "dependencies": { + "@radix-ui/react-compose-refs": "1.1.2" + }, + "peerDependencies": { + "@types/react": "*", + "react": "^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc" + }, + "peerDependenciesMeta": { + "@types/react": { + "optional": true + } + } + }, "node_modules/@radix-ui/react-popper": { "version": "1.2.8", "resolved": "https://registry.npmjs.org/@radix-ui/react-popper/-/react-popper-1.2.8.tgz", "integrity": "sha512-0NJQ4LFFUuWkE7Oxf0htBKS6zLkkjBH+hM1uk7Ng705ReR8m/uelduy1DBo0PyBXPKVnBA6YBlU94MBGXrSBCw==", + "license": "MIT", "dependencies": { "@floating-ui/react-dom": "^2.0.0", "@radix-ui/react-arrow": "1.1.7", @@ -2560,6 +2650,7 @@ "version": "1.1.9", "resolved": "https://registry.npmjs.org/@radix-ui/react-portal/-/react-portal-1.1.9.tgz", "integrity": "sha512-bpIxvq03if6UNwXZ+HTK71JLh4APvnXntDc6XOX8UVq4XQOVl7lwok0AvIl+b8zgCw3fSaVTZMpAPPagXbKmHQ==", + "license": "MIT", "dependencies": { "@radix-ui/react-primitive": "2.1.3", "@radix-ui/react-use-layout-effect": "1.1.1" @@ -2583,6 +2674,7 @@ "version": "1.1.5", "resolved": "https://registry.npmjs.org/@radix-ui/react-presence/-/react-presence-1.1.5.tgz", "integrity": "sha512-/jfEwNDdQVBCNvjkGit4h6pMOzq8bHkopq458dPt2lMjx+eBQUohZNG9A7DtO/O5ukSbxuaNGXMjHicgwy6rQQ==", + "license": "MIT", "dependencies": { "@radix-ui/react-compose-refs": "1.1.2", "@radix-ui/react-use-layout-effect": "1.1.1" @@ -2606,6 +2698,7 @@ "version": "2.1.3", "resolved": "https://registry.npmjs.org/@radix-ui/react-primitive/-/react-primitive-2.1.3.tgz", "integrity": "sha512-m9gTwRkhy2lvCPe6QJp4d3G1TYEUHn/FzJUtq9MjH46an1wJU+GdoGC5VLof8RX8Ft/DlpshApkhswDLZzHIcQ==", + "license": "MIT", "dependencies": { "@radix-ui/react-slot": "1.2.3" }, @@ -2624,6 +2717,24 @@ } } }, + "node_modules/@radix-ui/react-primitive/node_modules/@radix-ui/react-slot": { + "version": "1.2.3", + "resolved": "https://registry.npmjs.org/@radix-ui/react-slot/-/react-slot-1.2.3.tgz", + "integrity": "sha512-aeNmHnBxbi2St0au6VBVC7JXFlhLlOnvIIlePNniyUNAClzmtAUEY8/pBiK3iHjufOlwA+c20/8jngo7xcrg8A==", + "license": "MIT", + "dependencies": { + "@radix-ui/react-compose-refs": "1.1.2" + }, + "peerDependencies": { + "@types/react": "*", + "react": "^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc" + }, + "peerDependenciesMeta": { + "@types/react": { + "optional": true + } + } + }, "node_modules/@radix-ui/react-radio-group": { "version": "1.3.8", "resolved": "https://registry.npmjs.org/@radix-ui/react-radio-group/-/react-radio-group-1.3.8.tgz", @@ -2660,6 +2771,7 @@ "version": "1.1.11", "resolved": "https://registry.npmjs.org/@radix-ui/react-roving-focus/-/react-roving-focus-1.1.11.tgz", "integrity": "sha512-7A6S9jSgm/S+7MdtNDSb+IU859vQqJ/QAtcYQcfFC6W8RS4IxIZDldLR0xqCFZ6DCyrQLjLPsxtTNch5jVA4lA==", + "license": "MIT", "dependencies": { "@radix-ui/primitive": "1.1.3", "@radix-ui/react-collection": "1.1.7", @@ -2732,7 +2844,7 @@ } } }, - "node_modules/@radix-ui/react-separator/node_modules/@radix-ui/react-slot": { + "node_modules/@radix-ui/react-slot": { "version": "1.2.4", "resolved": "https://registry.npmjs.org/@radix-ui/react-slot/-/react-slot-1.2.4.tgz", "integrity": "sha512-Jl+bCv8HxKnlTLVrcDE8zTMJ09R9/ukw4qBs/oZClOfoQk/cOTbDn+NceXfV7j09YPVQUryJPHurafcSg6EVKA==", @@ -2750,27 +2862,11 @@ } } }, - "node_modules/@radix-ui/react-slot": { - "version": "1.2.3", - "resolved": "https://registry.npmjs.org/@radix-ui/react-slot/-/react-slot-1.2.3.tgz", - "integrity": "sha512-aeNmHnBxbi2St0au6VBVC7JXFlhLlOnvIIlePNniyUNAClzmtAUEY8/pBiK3iHjufOlwA+c20/8jngo7xcrg8A==", - "dependencies": { - "@radix-ui/react-compose-refs": "1.1.2" - }, - "peerDependencies": { - "@types/react": "*", - "react": "^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc" - }, - "peerDependenciesMeta": { - "@types/react": { - "optional": true - } - } - }, "node_modules/@radix-ui/react-tooltip": { "version": "1.2.8", "resolved": "https://registry.npmjs.org/@radix-ui/react-tooltip/-/react-tooltip-1.2.8.tgz", "integrity": "sha512-tY7sVt1yL9ozIxvmbtN5qtmH2krXcBCfjEiCgKGLqunJHvgvZG2Pcl2oQ3kbcZARb1BGEHdkLzcYGO8ynVlieg==", + "license": "MIT", "dependencies": { "@radix-ui/primitive": "1.1.3", "@radix-ui/react-compose-refs": "1.1.2", @@ -2800,10 +2896,29 @@ } } }, + "node_modules/@radix-ui/react-tooltip/node_modules/@radix-ui/react-slot": { + "version": "1.2.3", + "resolved": "https://registry.npmjs.org/@radix-ui/react-slot/-/react-slot-1.2.3.tgz", + "integrity": "sha512-aeNmHnBxbi2St0au6VBVC7JXFlhLlOnvIIlePNniyUNAClzmtAUEY8/pBiK3iHjufOlwA+c20/8jngo7xcrg8A==", + "license": "MIT", + "dependencies": { + "@radix-ui/react-compose-refs": "1.1.2" + }, + "peerDependencies": { + "@types/react": "*", + "react": "^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc" + }, + "peerDependenciesMeta": { + "@types/react": { + "optional": true + } + } + }, "node_modules/@radix-ui/react-use-callback-ref": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/@radix-ui/react-use-callback-ref/-/react-use-callback-ref-1.1.1.tgz", "integrity": "sha512-FkBMwD+qbGQeMu1cOHnuGB6x4yzPjho8ap5WtbEJ26umhgqVXbhekKUQO+hZEL1vU92a3wHwdp0HAcqAUF5iDg==", + "license": "MIT", "peerDependencies": { "@types/react": "*", "react": "^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc" @@ -2818,6 +2933,7 @@ "version": "1.2.2", "resolved": "https://registry.npmjs.org/@radix-ui/react-use-controllable-state/-/react-use-controllable-state-1.2.2.tgz", "integrity": "sha512-BjasUjixPFdS+NKkypcyyN5Pmg83Olst0+c6vGov0diwTEo6mgdqVR6hxcEgFuh4QrAs7Rc+9KuGJ9TVCj0Zzg==", + "license": "MIT", "dependencies": { "@radix-ui/react-use-effect-event": "0.0.2", "@radix-ui/react-use-layout-effect": "1.1.1" @@ -2836,6 +2952,7 @@ "version": "0.0.2", "resolved": "https://registry.npmjs.org/@radix-ui/react-use-effect-event/-/react-use-effect-event-0.0.2.tgz", "integrity": "sha512-Qp8WbZOBe+blgpuUT+lw2xheLP8q0oatc9UpmiemEICxGvFLYmHm9QowVZGHtJlGbS6A6yJ3iViad/2cVjnOiA==", + "license": "MIT", "dependencies": { "@radix-ui/react-use-layout-effect": "1.1.1" }, @@ -2853,6 +2970,7 @@ "version": "1.1.1", "resolved": "https://registry.npmjs.org/@radix-ui/react-use-escape-keydown/-/react-use-escape-keydown-1.1.1.tgz", "integrity": "sha512-Il0+boE7w/XebUHyBjroE+DbByORGR9KKmITzbR7MyQ4akpORYP/ZmbhAr0DG7RmmBqoOnZdy2QlvajJ2QA59g==", + "license": "MIT", "dependencies": { "@radix-ui/react-use-callback-ref": "1.1.1" }, @@ -2870,6 +2988,7 @@ "version": "1.1.1", "resolved": "https://registry.npmjs.org/@radix-ui/react-use-layout-effect/-/react-use-layout-effect-1.1.1.tgz", "integrity": "sha512-RbJRS4UWQFkzHTTwVymMTUv8EqYhOp8dOOviLj2ugtTiXRaRQS7GLGxZTLL1jWhMeoSCf5zmcZkqTl9IiYfXcQ==", + "license": "MIT", "peerDependencies": { "@types/react": "*", "react": "^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc" @@ -2884,6 +3003,7 @@ "version": "1.1.1", "resolved": "https://registry.npmjs.org/@radix-ui/react-use-previous/-/react-use-previous-1.1.1.tgz", "integrity": "sha512-2dHfToCj/pzca2Ck724OZ5L0EVrr3eHRNsG/b3xQJLA2hZpVCS99bLAX+hm1IHXDEnzU6by5z/5MIY794/a8NQ==", + "license": "MIT", "peerDependencies": { "@types/react": "*", "react": "^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc" @@ -2898,6 +3018,7 @@ "version": "1.1.1", "resolved": "https://registry.npmjs.org/@radix-ui/react-use-rect/-/react-use-rect-1.1.1.tgz", "integrity": "sha512-QTYuDesS0VtuHNNvMh+CjlKJ4LJickCMUAqjlE3+j8w+RlRpwyX3apEQKGFzbZGdo7XNG1tXa+bQqIE7HIXT2w==", + "license": "MIT", "dependencies": { "@radix-ui/rect": "1.1.1" }, @@ -2915,6 +3036,7 @@ "version": "1.1.1", "resolved": "https://registry.npmjs.org/@radix-ui/react-use-size/-/react-use-size-1.1.1.tgz", "integrity": "sha512-ewrXRDTAqAXlkl6t/fkXWNAhFX9I+CkKlw6zjEwk86RSPKwZr3xpBRso655aqYafwtnbpHLj6toFzmd6xdVptQ==", + "license": "MIT", "dependencies": { "@radix-ui/react-use-layout-effect": "1.1.1" }, @@ -2932,6 +3054,7 @@ "version": "1.2.3", "resolved": "https://registry.npmjs.org/@radix-ui/react-visually-hidden/-/react-visually-hidden-1.2.3.tgz", "integrity": "sha512-pzJq12tEaaIhqjbzpCuv/OypJY/BPavOofm+dbab+MHLajy277+1lLm6JFcGgF5eskJ6mquGirhXY2GD/8u8Ug==", + "license": "MIT", "dependencies": { "@radix-ui/react-primitive": "2.1.3" }, @@ -2953,103 +3076,121 @@ "node_modules/@radix-ui/rect": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/@radix-ui/rect/-/rect-1.1.1.tgz", - "integrity": "sha512-HPwpGIzkl28mWyZqG52jiqDJ12waP11Pa1lGoiyUkIEuMLBP0oeK/C89esbXrxsky5we7dfd8U58nm0SgAWpVw==" + "integrity": "sha512-HPwpGIzkl28mWyZqG52jiqDJ12waP11Pa1lGoiyUkIEuMLBP0oeK/C89esbXrxsky5we7dfd8U58nm0SgAWpVw==", + "license": "MIT" }, "node_modules/@rtsao/scc": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/@rtsao/scc/-/scc-1.1.0.tgz", "integrity": "sha512-zt6OdqaDoOnJ1ZYsCYGt9YmWzDXl4vQdKTyJev62gFhRGKdx7mcT54V9KIjg+d2wi9EXsPvAPKe7i7WjfVWB8g==", - "dev": true + "dev": true, + "license": "MIT" }, "node_modules/@rushstack/eslint-patch": { - "version": "1.12.0", - "resolved": "https://registry.npmjs.org/@rushstack/eslint-patch/-/eslint-patch-1.12.0.tgz", - "integrity": "sha512-5EwMtOqvJMMa3HbmxLlF74e+3/HhwBTMcvt3nqVJgGCozO6hzIPOBlwm8mGVNR9SN2IJpxSnlxczyDjcn7qIyw==", - "dev": true + "version": "1.15.0", + "resolved": "https://registry.npmjs.org/@rushstack/eslint-patch/-/eslint-patch-1.15.0.tgz", + "integrity": "sha512-ojSshQPKwVvSMR8yT2L/QtUkV5SXi/IfDiJ4/8d6UbTPjiHVmxZzUAzGD8Tzks1b9+qQkZa0isUOvYObedITaw==", + "dev": true, + "license": "MIT" }, "node_modules/@supabase/auth-js": { - "version": "2.71.1", - "resolved": "https://registry.npmjs.org/@supabase/auth-js/-/auth-js-2.71.1.tgz", - "integrity": "sha512-mMIQHBRc+SKpZFRB2qtupuzulaUhFYupNyxqDj5Jp/LyPvcWvjaJzZzObv6URtL/O6lPxkanASnotGtNpS3H2Q==", + "version": "2.93.3", + "resolved": "https://registry.npmjs.org/@supabase/auth-js/-/auth-js-2.93.3.tgz", + "integrity": "sha512-JdnkHZPKexVGSNONtu89RHU4bxz3X9kxx+f5ZnR5osoCIX+vs/MckwWRPZEybAEvlJXt5xjomDb3IB876QCxWQ==", + "license": "MIT", "dependencies": { - "@supabase/node-fetch": "^2.6.14" + "tslib": "2.8.1" + }, + "engines": { + "node": ">=20.0.0" } }, "node_modules/@supabase/functions-js": { - "version": "2.4.5", - "resolved": "https://registry.npmjs.org/@supabase/functions-js/-/functions-js-2.4.5.tgz", - "integrity": "sha512-v5GSqb9zbosquTo6gBwIiq7W9eQ7rE5QazsK/ezNiQXdCbY+bH8D9qEaBIkhVvX4ZRW5rP03gEfw5yw9tiq4EQ==", - "dependencies": { - "@supabase/node-fetch": "^2.6.14" - } - }, - "node_modules/@supabase/node-fetch": { - "version": "2.6.15", - "resolved": "https://registry.npmjs.org/@supabase/node-fetch/-/node-fetch-2.6.15.tgz", - "integrity": "sha512-1ibVeYUacxWYi9i0cf5efil6adJ9WRyZBLivgjs+AUpewx1F3xPi7gLgaASI2SmIQxPoCEjAsLAzKPgMJVgOUQ==", + "version": "2.93.3", + "resolved": "https://registry.npmjs.org/@supabase/functions-js/-/functions-js-2.93.3.tgz", + "integrity": "sha512-qWO0gHNDm/5jRjROv/nv9L6sYabCWS1kzorOLUv3kqCwRvEJLYZga93ppJPrZwOgoZfXmJzvpjY8fODA4HQfBw==", + "license": "MIT", "dependencies": { - "whatwg-url": "^5.0.0" + "tslib": "2.8.1" }, "engines": { - "node": "4.x || >=6.0.0" + "node": ">=20.0.0" } }, "node_modules/@supabase/postgrest-js": { - "version": "1.21.3", - "resolved": "https://registry.npmjs.org/@supabase/postgrest-js/-/postgrest-js-1.21.3.tgz", - "integrity": "sha512-rg3DmmZQKEVCreXq6Am29hMVe1CzemXyIWVYyyua69y6XubfP+DzGfLxME/1uvdgwqdoaPbtjBDpEBhqxq1ZwA==", + "version": "2.93.3", + "resolved": "https://registry.npmjs.org/@supabase/postgrest-js/-/postgrest-js-2.93.3.tgz", + "integrity": "sha512-+iJ96g94skO2e4clsRSmEXg22NUOjh9BziapsJSAvnB1grOBf/BA8vGtCHjNOA+Z6lvKXL1jwBqcL9+fS1W/Lg==", + "license": "MIT", "dependencies": { - "@supabase/node-fetch": "^2.6.14" + "tslib": "2.8.1" + }, + "engines": { + "node": ">=20.0.0" } }, "node_modules/@supabase/realtime-js": { - "version": "2.15.4", - "resolved": "https://registry.npmjs.org/@supabase/realtime-js/-/realtime-js-2.15.4.tgz", - "integrity": "sha512-e/FYIWjvQJHOCNACWehnKvg26zosju3694k0NMUNb+JGLdvHJzEa29ZVVLmawd2kvx4hdbv8mxSqfttRnH3+DA==", + "version": "2.93.3", + "resolved": "https://registry.npmjs.org/@supabase/realtime-js/-/realtime-js-2.93.3.tgz", + "integrity": "sha512-gnYpcFzwy8IkezRP4CDbT5I8jOsiOjrWrqTY1B+7jIriXsnpifmlM6RRjLBm9oD7OwPG0/WksniGPdKW67sXOA==", + "license": "MIT", "dependencies": { - "@supabase/node-fetch": "^2.6.13", "@types/phoenix": "^1.6.6", "@types/ws": "^8.18.1", + "tslib": "2.8.1", "ws": "^8.18.2" + }, + "engines": { + "node": ">=20.0.0" } }, "node_modules/@supabase/ssr": { - "version": "0.7.0", - "resolved": "https://registry.npmjs.org/@supabase/ssr/-/ssr-0.7.0.tgz", - "integrity": "sha512-G65t5EhLSJ5c8hTCcXifSL9Q/ZRXvqgXeNo+d3P56f4U1IxwTqjB64UfmfixvmMcjuxnq2yGqEWVJqUcO+AzAg==", + "version": "0.8.0", + "resolved": "https://registry.npmjs.org/@supabase/ssr/-/ssr-0.8.0.tgz", + "integrity": "sha512-/PKk8kNFSs8QvvJ2vOww1mF5/c5W8y42duYtXvkOSe+yZKRgTTZywYG2l41pjhNomqESZCpZtXuWmYjFRMV+dw==", + "license": "MIT", "dependencies": { "cookie": "^1.0.2" }, "peerDependencies": { - "@supabase/supabase-js": "^2.43.4" + "@supabase/supabase-js": "^2.76.1" } }, "node_modules/@supabase/storage-js": { - "version": "2.11.0", - "resolved": "https://registry.npmjs.org/@supabase/storage-js/-/storage-js-2.11.0.tgz", - "integrity": "sha512-Y+kx/wDgd4oasAgoAq0bsbQojwQ+ejIif8uczZ9qufRHWFLMU5cODT+ApHsSrDufqUcVKt+eyxtOXSkeh2v9ww==", + "version": "2.93.3", + "resolved": "https://registry.npmjs.org/@supabase/storage-js/-/storage-js-2.93.3.tgz", + "integrity": "sha512-cw4qXiLrx3apglDM02Tx/w/stvFlrkKocC6vCvuFAz3JtVEl1zH8MUfDQDTH59kJAQVaVdbewrMWSoBob7REnA==", + "license": "MIT", "dependencies": { - "@supabase/node-fetch": "^2.6.14" + "iceberg-js": "^0.8.1", + "tslib": "2.8.1" + }, + "engines": { + "node": ">=20.0.0" } }, "node_modules/@supabase/supabase-js": { - "version": "2.56.1", - "resolved": "https://registry.npmjs.org/@supabase/supabase-js/-/supabase-js-2.56.1.tgz", - "integrity": "sha512-cb/kS0d6G/qbcmUFItkqVrQbxQHWXzfRZuoiSDv/QiU6RbGNTn73XjjvmbBCZ4MMHs+5teihjhpEVluqbXISEg==", + "version": "2.93.3", + "resolved": "https://registry.npmjs.org/@supabase/supabase-js/-/supabase-js-2.93.3.tgz", + "integrity": "sha512-paUqEqdBI9ztr/4bbMoCgeJ6M8ZTm2fpfjSOlzarPuzYveKFM20ZfDZqUpi9CFfYagYj5Iv3m3ztUjaI9/tM1w==", + "license": "MIT", "peer": true, "dependencies": { - "@supabase/auth-js": "2.71.1", - "@supabase/functions-js": "2.4.5", - "@supabase/node-fetch": "2.6.15", - "@supabase/postgrest-js": "1.21.3", - "@supabase/realtime-js": "2.15.4", - "@supabase/storage-js": "^2.10.4" + "@supabase/auth-js": "2.93.3", + "@supabase/functions-js": "2.93.3", + "@supabase/postgrest-js": "2.93.3", + "@supabase/realtime-js": "2.93.3", + "@supabase/storage-js": "2.93.3" + }, + "engines": { + "node": ">=20.0.0" } }, "node_modules/@swc/helpers": { "version": "0.5.15", "resolved": "https://registry.npmjs.org/@swc/helpers/-/helpers-0.5.15.tgz", "integrity": "sha512-JQ5TuMi45Owi4/BIMAJBoSQoOJu12oOk/gADqlcUL9JEdHB8vyjUSsxqeNXnmXHjYKMi2WcYtezGEEhqUI/E2g==", + "license": "Apache-2.0", "dependencies": { "tslib": "^2.8.0" } @@ -3086,7 +3227,8 @@ "node_modules/@types/estree": { "version": "1.0.8", "resolved": "https://registry.npmjs.org/@types/estree/-/estree-1.0.8.tgz", - "integrity": "sha512-dWHzHa2WqEXI/O1E9OjrocMTKJl2mSrEolh1Iomrv6U+JuNwaHXsXx9bLu5gG7BUWFIN0skIQJQ/L1rIex4X6w==" + "integrity": "sha512-dWHzHa2WqEXI/O1E9OjrocMTKJl2mSrEolh1Iomrv6U+JuNwaHXsXx9bLu5gG7BUWFIN0skIQJQ/L1rIex4X6w==", + "license": "MIT" }, "node_modules/@types/estree-jsx": { "version": "1.0.5", @@ -3122,13 +3264,15 @@ "version": "7.0.15", "resolved": "https://registry.npmjs.org/@types/json-schema/-/json-schema-7.0.15.tgz", "integrity": "sha512-5+fP8P8MFNC+AyZCDxrB2pkZFPGzqQWUzpSeuuVLvm8VMcorNYavBqoFcxK8bQz4Qsbn4oUEEem4wDLfcysGHA==", - "dev": true + "dev": true, + "license": "MIT" }, "node_modules/@types/json5": { "version": "0.0.29", "resolved": "https://registry.npmjs.org/@types/json5/-/json5-0.0.29.tgz", "integrity": "sha512-dRLjCWHYg4oaA77cxO64oO+7JwCwnIzkZPdrrC71jQmQtlhM556pwKo5bUzqvZndkVbeFLIIi+9TC40JNF5hNQ==", - "dev": true + "dev": true, + "license": "MIT" }, "node_modules/@types/mdast": { "version": "4.0.4", @@ -3146,36 +3290,40 @@ "license": "MIT" }, "node_modules/@types/node": { - "version": "20.19.11", - "resolved": "https://registry.npmjs.org/@types/node/-/node-20.19.11.tgz", - "integrity": "sha512-uug3FEEGv0r+jrecvUUpbY8lLisvIjg6AAic6a2bSP5OEOLeJsDSnvhCDov7ipFFMXS3orMpzlmi0ZcuGkBbow==", + "version": "20.19.30", + "resolved": "https://registry.npmjs.org/@types/node/-/node-20.19.30.tgz", + "integrity": "sha512-WJtwWJu7UdlvzEAUm484QNg5eAoq5QR08KDNx7g45Usrs2NtOPiX8ugDqmKdXkyL03rBqU5dYNYVQetEpBHq2g==", + "license": "MIT", "peer": true, "dependencies": { "undici-types": "~6.21.0" } }, "node_modules/@types/phoenix": { - "version": "1.6.6", - "resolved": "https://registry.npmjs.org/@types/phoenix/-/phoenix-1.6.6.tgz", - "integrity": "sha512-PIzZZlEppgrpoT2QgbnDU+MMzuR6BbCjllj0bM70lWoejMeNJAxCchxnv7J3XFkI8MpygtRpzXrIlmWUBclP5A==" + "version": "1.6.7", + "resolved": "https://registry.npmjs.org/@types/phoenix/-/phoenix-1.6.7.tgz", + "integrity": "sha512-oN9ive//QSBkf19rfDv45M7eZPi0eEXylht2OLEXicu5b4KoQ1OzXIw+xDSGWxSxe1JmepRR/ZH283vsu518/Q==", + "license": "MIT" }, "node_modules/@types/react": { - "version": "19.1.12", - "resolved": "https://registry.npmjs.org/@types/react/-/react-19.1.12.tgz", - "integrity": "sha512-cMoR+FoAf/Jyq6+Df2/Z41jISvGZZ2eTlnsaJRptmZ76Caldwy1odD4xTr/gNV9VLj0AWgg/nmkevIyUfIIq5w==", + "version": "19.2.10", + "resolved": "https://registry.npmjs.org/@types/react/-/react-19.2.10.tgz", + "integrity": "sha512-WPigyYuGhgZ/cTPRXB2EwUw+XvsRA3GqHlsP4qteqrnnjDrApbS7MxcGr/hke5iUoeB7E/gQtrs9I37zAJ0Vjw==", + "license": "MIT", "peer": true, "dependencies": { - "csstype": "^3.0.2" + "csstype": "^3.2.2" } }, "node_modules/@types/react-dom": { - "version": "19.1.9", - "resolved": "https://registry.npmjs.org/@types/react-dom/-/react-dom-19.1.9.tgz", - "integrity": "sha512-qXRuZaOsAdXKFyOhRBg6Lqqc0yay13vN7KrIg4L7N4aaHN68ma9OK3NE1BoDFgFOTfM7zg+3/8+2n8rLUH3OKQ==", + "version": "19.2.3", + "resolved": "https://registry.npmjs.org/@types/react-dom/-/react-dom-19.2.3.tgz", + "integrity": "sha512-jp2L/eY6fn+KgVVQAOqYItbF0VY/YApe5Mz2F0aykSO8gx31bYCZyvSeYxCHKvzHG5eZjc+zyaS5BrBWya2+kQ==", "devOptional": true, + "license": "MIT", "peer": true, "peerDependencies": { - "@types/react": "^19.0.0" + "@types/react": "^19.2.0" } }, "node_modules/@types/tough-cookie": { @@ -3202,25 +3350,26 @@ "version": "8.18.1", "resolved": "https://registry.npmjs.org/@types/ws/-/ws-8.18.1.tgz", "integrity": "sha512-ThVF6DCVhA8kUGy+aazFQ4kXQ7E1Ty7A3ypFOe0IcJV8O/M511G99AW24irKrW56Wt44yG9+ij8FaqoBGkuBXg==", + "license": "MIT", "dependencies": { "@types/node": "*" } }, "node_modules/@typescript-eslint/eslint-plugin": { - "version": "8.41.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/eslint-plugin/-/eslint-plugin-8.41.0.tgz", - "integrity": "sha512-8fz6oa6wEKZrhXWro/S3n2eRJqlRcIa6SlDh59FXJ5Wp5XRZ8B9ixpJDcjadHq47hMx0u+HW6SNa6LjJQ6NLtw==", - "dev": true, - "dependencies": { - "@eslint-community/regexpp": "^4.10.0", - "@typescript-eslint/scope-manager": "8.41.0", - "@typescript-eslint/type-utils": "8.41.0", - "@typescript-eslint/utils": "8.41.0", - "@typescript-eslint/visitor-keys": "8.41.0", - "graphemer": "^1.4.0", - "ignore": "^7.0.0", + "version": "8.54.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/eslint-plugin/-/eslint-plugin-8.54.0.tgz", + "integrity": "sha512-hAAP5io/7csFStuOmR782YmTthKBJ9ND3WVL60hcOjvtGFb+HJxH4O5huAcmcZ9v9G8P+JETiZ/G1B8MALnWZQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "@eslint-community/regexpp": "^4.12.2", + "@typescript-eslint/scope-manager": "8.54.0", + "@typescript-eslint/type-utils": "8.54.0", + "@typescript-eslint/utils": "8.54.0", + "@typescript-eslint/visitor-keys": "8.54.0", + "ignore": "^7.0.5", "natural-compare": "^1.4.0", - "ts-api-utils": "^2.1.0" + "ts-api-utils": "^2.4.0" }, "engines": { "node": "^18.18.0 || ^20.9.0 || >=21.1.0" @@ -3230,7 +3379,7 @@ "url": "https://opencollective.com/typescript-eslint" }, "peerDependencies": { - "@typescript-eslint/parser": "^8.41.0", + "@typescript-eslint/parser": "^8.54.0", "eslint": "^8.57.0 || ^9.0.0", "typescript": ">=4.8.4 <6.0.0" } @@ -3240,22 +3389,24 @@ "resolved": "https://registry.npmjs.org/ignore/-/ignore-7.0.5.tgz", "integrity": "sha512-Hs59xBNfUIunMFgWAbGX5cq6893IbWg4KnrjbYwX3tx0ztorVgTDA6B2sxf8ejHJ4wz8BqGUMYlnzNBer5NvGg==", "dev": true, + "license": "MIT", "engines": { "node": ">= 4" } }, "node_modules/@typescript-eslint/parser": { - "version": "8.41.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/parser/-/parser-8.41.0.tgz", - "integrity": "sha512-gTtSdWX9xiMPA/7MV9STjJOOYtWwIJIYxkQxnSV1U3xcE+mnJSH3f6zI0RYP+ew66WSlZ5ed+h0VCxsvdC1jJg==", + "version": "8.54.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/parser/-/parser-8.54.0.tgz", + "integrity": "sha512-BtE0k6cjwjLZoZixN0t5AKP0kSzlGu7FctRXYuPAm//aaiZhmfq1JwdYpYr1brzEspYyFeF+8XF5j2VK6oalrA==", "dev": true, + "license": "MIT", "peer": true, "dependencies": { - "@typescript-eslint/scope-manager": "8.41.0", - "@typescript-eslint/types": "8.41.0", - "@typescript-eslint/typescript-estree": "8.41.0", - "@typescript-eslint/visitor-keys": "8.41.0", - "debug": "^4.3.4" + "@typescript-eslint/scope-manager": "8.54.0", + "@typescript-eslint/types": "8.54.0", + "@typescript-eslint/typescript-estree": "8.54.0", + "@typescript-eslint/visitor-keys": "8.54.0", + "debug": "^4.4.3" }, "engines": { "node": "^18.18.0 || ^20.9.0 || >=21.1.0" @@ -3270,14 +3421,15 @@ } }, "node_modules/@typescript-eslint/project-service": { - "version": "8.41.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/project-service/-/project-service-8.41.0.tgz", - "integrity": "sha512-b8V9SdGBQzQdjJ/IO3eDifGpDBJfvrNTp2QD9P2BeqWTGrRibgfgIlBSw6z3b6R7dPzg752tOs4u/7yCLxksSQ==", + "version": "8.54.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/project-service/-/project-service-8.54.0.tgz", + "integrity": "sha512-YPf+rvJ1s7MyiWM4uTRhE4DvBXrEV+d8oC3P9Y2eT7S+HBS0clybdMIPnhiATi9vZOYDc7OQ1L/i6ga6NFYK/g==", "dev": true, + "license": "MIT", "dependencies": { - "@typescript-eslint/tsconfig-utils": "^8.41.0", - "@typescript-eslint/types": "^8.41.0", - "debug": "^4.3.4" + "@typescript-eslint/tsconfig-utils": "^8.54.0", + "@typescript-eslint/types": "^8.54.0", + "debug": "^4.4.3" }, "engines": { "node": "^18.18.0 || ^20.9.0 || >=21.1.0" @@ -3291,13 +3443,14 @@ } }, "node_modules/@typescript-eslint/scope-manager": { - "version": "8.41.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/scope-manager/-/scope-manager-8.41.0.tgz", - "integrity": "sha512-n6m05bXn/Cd6DZDGyrpXrELCPVaTnLdPToyhBoFkLIMznRUQUEQdSp96s/pcWSQdqOhrgR1mzJ+yItK7T+WPMQ==", + "version": "8.54.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/scope-manager/-/scope-manager-8.54.0.tgz", + "integrity": "sha512-27rYVQku26j/PbHYcVfRPonmOlVI6gihHtXFbTdB5sb6qA0wdAQAbyXFVarQ5t4HRojIz64IV90YtsjQSSGlQg==", "dev": true, + "license": "MIT", "dependencies": { - "@typescript-eslint/types": "8.41.0", - "@typescript-eslint/visitor-keys": "8.41.0" + "@typescript-eslint/types": "8.54.0", + "@typescript-eslint/visitor-keys": "8.54.0" }, "engines": { "node": "^18.18.0 || ^20.9.0 || >=21.1.0" @@ -3308,10 +3461,11 @@ } }, "node_modules/@typescript-eslint/tsconfig-utils": { - "version": "8.41.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/tsconfig-utils/-/tsconfig-utils-8.41.0.tgz", - "integrity": "sha512-TDhxYFPUYRFxFhuU5hTIJk+auzM/wKvWgoNYOPcOf6i4ReYlOoYN8q1dV5kOTjNQNJgzWN3TUUQMtlLOcUgdUw==", + "version": "8.54.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/tsconfig-utils/-/tsconfig-utils-8.54.0.tgz", + "integrity": "sha512-dRgOyT2hPk/JwxNMZDsIXDgyl9axdJI3ogZ2XWhBPsnZUv+hPesa5iuhdYt2gzwA9t8RE5ytOJ6xB0moV0Ujvw==", "dev": true, + "license": "MIT", "engines": { "node": "^18.18.0 || ^20.9.0 || >=21.1.0" }, @@ -3324,16 +3478,17 @@ } }, "node_modules/@typescript-eslint/type-utils": { - "version": "8.41.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/type-utils/-/type-utils-8.41.0.tgz", - "integrity": "sha512-63qt1h91vg3KsjVVonFJWjgSK7pZHSQFKH6uwqxAH9bBrsyRhO6ONoKyXxyVBzG1lJnFAJcKAcxLS54N1ee1OQ==", + "version": "8.54.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/type-utils/-/type-utils-8.54.0.tgz", + "integrity": "sha512-hiLguxJWHjjwL6xMBwD903ciAwd7DmK30Y9Axs/etOkftC3ZNN9K44IuRD/EB08amu+Zw6W37x9RecLkOo3pMA==", "dev": true, + "license": "MIT", "dependencies": { - "@typescript-eslint/types": "8.41.0", - "@typescript-eslint/typescript-estree": "8.41.0", - "@typescript-eslint/utils": "8.41.0", - "debug": "^4.3.4", - "ts-api-utils": "^2.1.0" + "@typescript-eslint/types": "8.54.0", + "@typescript-eslint/typescript-estree": "8.54.0", + "@typescript-eslint/utils": "8.54.0", + "debug": "^4.4.3", + "ts-api-utils": "^2.4.0" }, "engines": { "node": "^18.18.0 || ^20.9.0 || >=21.1.0" @@ -3348,10 +3503,11 @@ } }, "node_modules/@typescript-eslint/types": { - "version": "8.41.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-8.41.0.tgz", - "integrity": "sha512-9EwxsWdVqh42afLbHP90n2VdHaWU/oWgbH2P0CfcNfdKL7CuKpwMQGjwev56vWu9cSKU7FWSu6r9zck6CVfnag==", + "version": "8.54.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-8.54.0.tgz", + "integrity": "sha512-PDUI9R1BVjqu7AUDsRBbKMtwmjWcn4J3le+5LpcFgWULN3LvHC5rkc9gCVxbrsrGmO1jfPybN5s6h4Jy+OnkAA==", "dev": true, + "license": "MIT", "engines": { "node": "^18.18.0 || ^20.9.0 || >=21.1.0" }, @@ -3361,21 +3517,21 @@ } }, "node_modules/@typescript-eslint/typescript-estree": { - "version": "8.41.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-8.41.0.tgz", - "integrity": "sha512-D43UwUYJmGhuwHfY7MtNKRZMmfd8+p/eNSfFe6tH5mbVDto+VQCayeAt35rOx3Cs6wxD16DQtIKw/YXxt5E0UQ==", + "version": "8.54.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-8.54.0.tgz", + "integrity": "sha512-BUwcskRaPvTk6fzVWgDPdUndLjB87KYDrN5EYGetnktoeAvPtO4ONHlAZDnj5VFnUANg0Sjm7j4usBlnoVMHwA==", "dev": true, + "license": "MIT", "dependencies": { - "@typescript-eslint/project-service": "8.41.0", - "@typescript-eslint/tsconfig-utils": "8.41.0", - "@typescript-eslint/types": "8.41.0", - "@typescript-eslint/visitor-keys": "8.41.0", - "debug": "^4.3.4", - "fast-glob": "^3.3.2", - "is-glob": "^4.0.3", - "minimatch": "^9.0.4", - "semver": "^7.6.0", - "ts-api-utils": "^2.1.0" + "@typescript-eslint/project-service": "8.54.0", + "@typescript-eslint/tsconfig-utils": "8.54.0", + "@typescript-eslint/types": "8.54.0", + "@typescript-eslint/visitor-keys": "8.54.0", + "debug": "^4.4.3", + "minimatch": "^9.0.5", + "semver": "^7.7.3", + "tinyglobby": "^0.2.15", + "ts-api-utils": "^2.4.0" }, "engines": { "node": "^18.18.0 || ^20.9.0 || >=21.1.0" @@ -3393,43 +3549,17 @@ "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-2.0.2.tgz", "integrity": "sha512-Jt0vHyM+jmUBqojB7E1NIYadt0vI0Qxjxd2TErW94wDz+E2LAm5vKMXXwg6ZZBTHPuUlDgQHKXvjGBdfcF1ZDQ==", "dev": true, + "license": "MIT", "dependencies": { "balanced-match": "^1.0.0" } }, - "node_modules/@typescript-eslint/typescript-estree/node_modules/fast-glob": { - "version": "3.3.3", - "resolved": "https://registry.npmjs.org/fast-glob/-/fast-glob-3.3.3.tgz", - "integrity": "sha512-7MptL8U0cqcFdzIzwOTHoilX9x5BrNqye7Z/LuC7kCMRio1EMSyqRK3BEAUD7sXRq4iT4AzTVuZdhgQ2TCvYLg==", - "dev": true, - "dependencies": { - "@nodelib/fs.stat": "^2.0.2", - "@nodelib/fs.walk": "^1.2.3", - "glob-parent": "^5.1.2", - "merge2": "^1.3.0", - "micromatch": "^4.0.8" - }, - "engines": { - "node": ">=8.6.0" - } - }, - "node_modules/@typescript-eslint/typescript-estree/node_modules/glob-parent": { - "version": "5.1.2", - "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-5.1.2.tgz", - "integrity": "sha512-AOIgSQCepiJYwP3ARnGx+5VnTu2HBYdzbGP45eLw1vr3zB3vZLeyed1sC9hnbcOc9/SrMyM5RPQrkGz4aS9Zow==", - "dev": true, - "dependencies": { - "is-glob": "^4.0.1" - }, - "engines": { - "node": ">= 6" - } - }, "node_modules/@typescript-eslint/typescript-estree/node_modules/minimatch": { "version": "9.0.5", "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-9.0.5.tgz", "integrity": "sha512-G6T0ZX48xgozx7587koeX9Ys2NYy6Gmv//P89sEte9V9whIapMNF4idKxnW2QtCcLiTWlb/wfCabAtAFWhhBow==", "dev": true, + "license": "ISC", "dependencies": { "brace-expansion": "^2.0.1" }, @@ -3441,15 +3571,16 @@ } }, "node_modules/@typescript-eslint/utils": { - "version": "8.41.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/utils/-/utils-8.41.0.tgz", - "integrity": "sha512-udbCVstxZ5jiPIXrdH+BZWnPatjlYwJuJkDA4Tbo3WyYLh8NvB+h/bKeSZHDOFKfphsZYJQqaFtLeXEqurQn1A==", + "version": "8.54.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/utils/-/utils-8.54.0.tgz", + "integrity": "sha512-9Cnda8GS57AQakvRyG0PTejJNlA2xhvyNtEVIMlDWOOeEyBkYWhGPnfrIAnqxLMTSTo6q8g12XVjjev5l1NvMA==", "dev": true, + "license": "MIT", "dependencies": { - "@eslint-community/eslint-utils": "^4.7.0", - "@typescript-eslint/scope-manager": "8.41.0", - "@typescript-eslint/types": "8.41.0", - "@typescript-eslint/typescript-estree": "8.41.0" + "@eslint-community/eslint-utils": "^4.9.1", + "@typescript-eslint/scope-manager": "8.54.0", + "@typescript-eslint/types": "8.54.0", + "@typescript-eslint/typescript-estree": "8.54.0" }, "engines": { "node": "^18.18.0 || ^20.9.0 || >=21.1.0" @@ -3464,12 +3595,13 @@ } }, "node_modules/@typescript-eslint/visitor-keys": { - "version": "8.41.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-8.41.0.tgz", - "integrity": "sha512-+GeGMebMCy0elMNg67LRNoVnUFPIm37iu5CmHESVx56/9Jsfdpsvbv605DQ81Pi/x11IdKUsS5nzgTYbCQU9fg==", + "version": "8.54.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-8.54.0.tgz", + "integrity": "sha512-VFlhGSl4opC0bprJiItPQ1RfUhGDIBokcPwaFH4yiBCaNPeld/9VeXbiPO1cLyorQi1G1vL+ecBk1x8o1axORA==", "dev": true, + "license": "MIT", "dependencies": { - "@typescript-eslint/types": "8.41.0", + "@typescript-eslint/types": "8.54.0", "eslint-visitor-keys": "^4.2.1" }, "engines": { @@ -3522,6 +3654,7 @@ "arm64" ], "dev": true, + "license": "MIT", "optional": true, "os": [ "darwin" @@ -3771,6 +3904,7 @@ "version": "0.8.11", "resolved": "https://registry.npmjs.org/@xmldom/xmldom/-/xmldom-0.8.11.tgz", "integrity": "sha512-cQzWCtO6C8TQiYl1ruKNn2U6Ao4o4WBBcbL61yJl84x+j5sOWWFU9X7DpND8XZG3daDppSsigMdfAIl2upQBRw==", + "license": "MIT", "engines": { "node": ">=10.0.0" } @@ -3780,6 +3914,7 @@ "resolved": "https://registry.npmjs.org/acorn/-/acorn-8.15.0.tgz", "integrity": "sha512-NZyJarBfL7nWwIq+FDL6Zp/yHEhePMNnnJ0y3qfieCrmNvYct8uvtiV41UvlSe6apAfk0fY1FbWx+NwfmpvtTg==", "dev": true, + "license": "MIT", "peer": true, "bin": { "acorn": "bin/acorn" @@ -3793,6 +3928,7 @@ "resolved": "https://registry.npmjs.org/acorn-jsx/-/acorn-jsx-5.3.2.tgz", "integrity": "sha512-rq9s+JNhf0IChjtDXxllJ7g41oZk5SlXtp0LHwyA5cejwn7vKmKp4pPri6YEePv2PU65sAsegbXtIinmDFDXgQ==", "dev": true, + "license": "MIT", "peerDependencies": { "acorn": "^6.0.0 || ^7.0.0 || ^8.0.0" } @@ -3811,6 +3947,7 @@ "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz", "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==", "dev": true, + "license": "MIT", "dependencies": { "fast-deep-equal": "^3.1.1", "fast-json-stable-stringify": "^2.0.0", @@ -3823,9 +3960,10 @@ } }, "node_modules/ansi-regex": { - "version": "6.2.0", - "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-6.2.0.tgz", - "integrity": "sha512-TKY5pyBkHyADOPYlRT9Lx6F544mPl0vS5Ew7BJ45hA08Q+t3GjbueLliBWN3sMICk6+y7HdyxSzC4bWS8baBdg==", + "version": "6.2.2", + "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-6.2.2.tgz", + "integrity": "sha512-Bq3SmSpyFHaWjPk8If9yc6svM8c56dB5BAtW4Qbw5jHTwwXXcTLoRMkpDJp6VL0XzlWaCHTXrkFURMYmD0sLqg==", + "license": "MIT", "engines": { "node": ">=12" }, @@ -3837,6 +3975,7 @@ "version": "4.3.0", "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", + "license": "MIT", "dependencies": { "color-convert": "^2.0.1" }, @@ -3851,13 +3990,15 @@ "version": "1.3.0", "resolved": "https://registry.npmjs.org/any-promise/-/any-promise-1.3.0.tgz", "integrity": "sha512-7UvmKalWRt1wgjL1RrGxoSJW/0QZFIegpeGvZG9kjp8vrRu55XTHbwnqq2GpXm9uLbcuhxm3IqX9OB4MZR1b2A==", - "dev": true + "dev": true, + "license": "MIT" }, "node_modules/anymatch": { "version": "3.1.3", "resolved": "https://registry.npmjs.org/anymatch/-/anymatch-3.1.3.tgz", "integrity": "sha512-KMReFUr0B4t+D+OBkjR3KYqvocp2XaSzO55UcB6mgQMd3KbcE+mWTyvVV7D/zsdEbNnV6acZUutkiHQXvTr1Rw==", "dev": true, + "license": "ISC", "dependencies": { "normalize-path": "^3.0.0", "picomatch": "^2.0.4" @@ -3883,18 +4024,21 @@ "version": "5.0.2", "resolved": "https://registry.npmjs.org/arg/-/arg-5.0.2.tgz", "integrity": "sha512-PYjyFOLKQ9y57JvQ6QLo8dAgNqswh8M1RMJYdQduT6xbWSgK36P/Z/v+p888pM69jMMfS8Xd8F6I1kQ/I9HUGg==", - "dev": true + "dev": true, + "license": "MIT" }, "node_modules/argparse": { "version": "2.0.1", "resolved": "https://registry.npmjs.org/argparse/-/argparse-2.0.1.tgz", "integrity": "sha512-8+9WqebbFzpX9OR+Wa6O29asIogeRMzcGtAINdpMHHyAg10f05aSFVBbcEqGf/PXw1EjAZ+q2/bEBg3DvurK3Q==", - "dev": true + "dev": true, + "license": "Python-2.0" }, "node_modules/aria-hidden": { "version": "1.2.6", "resolved": "https://registry.npmjs.org/aria-hidden/-/aria-hidden-1.2.6.tgz", "integrity": "sha512-ik3ZgC9dY/lYVVM++OISsaYDeg1tb0VtP5uL3ouh1koGOaUMDPpbFIei4JkFimWUFPn90sbMNMXQAIVOlnYKJA==", + "license": "MIT", "dependencies": { "tslib": "^2.0.0" }, @@ -3907,6 +4051,7 @@ "resolved": "https://registry.npmjs.org/aria-query/-/aria-query-5.3.2.tgz", "integrity": "sha512-COROpnaoap1E2F000S62r6A60uHZnmlvomhfyT2DlTcrY1OrBKn2UhH7qn5wTC9zMvD0AY7csdPSNwKP+7WiQw==", "dev": true, + "license": "Apache-2.0", "engines": { "node": ">= 0.4" } @@ -3916,6 +4061,7 @@ "resolved": "https://registry.npmjs.org/array-buffer-byte-length/-/array-buffer-byte-length-1.0.2.tgz", "integrity": "sha512-LHE+8BuR7RYGDKvnrmcuSq3tDcKv9OFEXQt/HpbZhY7V6h0zlUXutnAD82GiFx9rdieCMjkvtcsPqBwgUl1Iiw==", "dev": true, + "license": "MIT", "dependencies": { "call-bound": "^1.0.3", "is-array-buffer": "^3.0.5" @@ -3932,6 +4078,7 @@ "resolved": "https://registry.npmjs.org/array-includes/-/array-includes-3.1.9.tgz", "integrity": "sha512-FmeCCAenzH0KH381SPT5FZmiA/TmpndpcaShhfgEN9eCVjnFBqq3l1xrI42y8+PPLI6hypzou4GXw00WHmPBLQ==", "dev": true, + "license": "MIT", "dependencies": { "call-bind": "^1.0.8", "call-bound": "^1.0.4", @@ -3954,6 +4101,7 @@ "resolved": "https://registry.npmjs.org/array.prototype.findlast/-/array.prototype.findlast-1.2.5.tgz", "integrity": "sha512-CVvd6FHg1Z3POpBLxO6E6zr+rSKEQ9L6rZHAaY7lLfhKsWYUBBOuMs0e9o24oopj6H+geRCX0YJ+TJLBK2eHyQ==", "dev": true, + "license": "MIT", "dependencies": { "call-bind": "^1.0.7", "define-properties": "^1.2.1", @@ -3974,6 +4122,7 @@ "resolved": "https://registry.npmjs.org/array.prototype.findlastindex/-/array.prototype.findlastindex-1.2.6.tgz", "integrity": "sha512-F/TKATkzseUExPlfvmwQKGITM3DGTK+vkAsCZoDc5daVygbJBnjEUCbgkAvVFsgfXfX4YIqZ/27G3k3tdXrTxQ==", "dev": true, + "license": "MIT", "dependencies": { "call-bind": "^1.0.8", "call-bound": "^1.0.4", @@ -3995,6 +4144,7 @@ "resolved": "https://registry.npmjs.org/array.prototype.flat/-/array.prototype.flat-1.3.3.tgz", "integrity": "sha512-rwG/ja1neyLqCuGZ5YYrznA62D4mZXg0i1cIskIUKSiqF3Cje9/wXAls9B9s1Wa2fomMsIv8czB8jZcPmxCXFg==", "dev": true, + "license": "MIT", "dependencies": { "call-bind": "^1.0.8", "define-properties": "^1.2.1", @@ -4013,6 +4163,7 @@ "resolved": "https://registry.npmjs.org/array.prototype.flatmap/-/array.prototype.flatmap-1.3.3.tgz", "integrity": "sha512-Y7Wt51eKJSyi80hFrJCePGGNo5ktJCslFuboqJsbf57CCPcm5zztluPlc4/aD8sWsKvlwatezpV4U1efk8kpjg==", "dev": true, + "license": "MIT", "dependencies": { "call-bind": "^1.0.8", "define-properties": "^1.2.1", @@ -4031,6 +4182,7 @@ "resolved": "https://registry.npmjs.org/array.prototype.tosorted/-/array.prototype.tosorted-1.1.4.tgz", "integrity": "sha512-p6Fx8B7b7ZhL/gmUsAy0D15WhvDccw3mnGNbZpi3pmeJdxtWsj2jEaI4Y6oo3XiHfzuSgPwKc04MYt6KgvC/wA==", "dev": true, + "license": "MIT", "dependencies": { "call-bind": "^1.0.7", "define-properties": "^1.2.1", @@ -4047,6 +4199,7 @@ "resolved": "https://registry.npmjs.org/arraybuffer.prototype.slice/-/arraybuffer.prototype.slice-1.0.4.tgz", "integrity": "sha512-BNoCY6SXXPQ7gF2opIP4GBE+Xw7U+pHMYKuzjgCN3GwiaIR09UUeKfheyIry77QtrCBlC0KK0q5/TER/tYh3PQ==", "dev": true, + "license": "MIT", "dependencies": { "array-buffer-byte-length": "^1.0.1", "call-bind": "^1.0.8", @@ -4067,21 +4220,29 @@ "version": "0.0.8", "resolved": "https://registry.npmjs.org/ast-types-flow/-/ast-types-flow-0.0.8.tgz", "integrity": "sha512-OH/2E5Fg20h2aPrbe+QL8JZQFko0YZaF+j4mnQ7BGhfavO7OpSLa8a0y9sBwomHdSbkhTS8TQNayBfnW5DwbvQ==", - "dev": true + "dev": true, + "license": "MIT" }, "node_modules/async-function": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/async-function/-/async-function-1.0.0.tgz", "integrity": "sha512-hsU18Ae8CDTR6Kgu9DYf0EbCr/a5iGL0rytQDobUcdpYOKokk8LEjVphnXkDkgpi0wYVsqrXuP0bZxJaTqdgoA==", "dev": true, + "license": "MIT", "engines": { "node": ">= 0.4" } }, + "node_modules/asynckit": { + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/asynckit/-/asynckit-0.4.0.tgz", + "integrity": "sha512-Oei9OH4tRh0YqU3GxhX79dM/mwVgvbZJaSNaRk+bshkj0S5cfHcgYakreBjrHwatXKbz+IoIdYLxrKim2MjW0Q==", + "license": "MIT" + }, "node_modules/autoprefixer": { - "version": "10.4.21", - "resolved": "https://registry.npmjs.org/autoprefixer/-/autoprefixer-10.4.21.tgz", - "integrity": "sha512-O+A6LWV5LDHSJD3LjHYoNi4VLsj/Whi7k6zG12xTYaU4cQ8oxQGckXNX8cRHK5yOZ/ppVHe0ZBXGzSV9jXdVbQ==", + "version": "10.4.24", + "resolved": "https://registry.npmjs.org/autoprefixer/-/autoprefixer-10.4.24.tgz", + "integrity": "sha512-uHZg7N9ULTVbutaIsDRoUkoS8/h3bdsmVJYZ5l3wv8Cp/6UIIoRDm90hZ+BwxUj/hGBEzLxdHNSKuFpn8WOyZw==", "dev": true, "funding": [ { @@ -4097,11 +4258,11 @@ "url": "https://github.com/sponsors/ai" } ], + "license": "MIT", "dependencies": { - "browserslist": "^4.24.4", - "caniuse-lite": "^1.0.30001702", - "fraction.js": "^4.3.7", - "normalize-range": "^0.1.2", + "browserslist": "^4.28.1", + "caniuse-lite": "^1.0.30001766", + "fraction.js": "^5.3.4", "picocolors": "^1.1.1", "postcss-value-parser": "^4.2.0" }, @@ -4120,6 +4281,7 @@ "resolved": "https://registry.npmjs.org/available-typed-arrays/-/available-typed-arrays-1.0.7.tgz", "integrity": "sha512-wvUjBtSGN7+7SjNpq/9M2Tg350UZD3q62IFZLbRAR1bSMlCo1ZaeW+BJ+D090e4hIIZLBcTDWe4Mh4jvUDajzQ==", "dev": true, + "license": "MIT", "dependencies": { "possible-typed-array-names": "^1.0.0" }, @@ -4131,18 +4293,19 @@ } }, "node_modules/axe-core": { - "version": "4.10.3", - "resolved": "https://registry.npmjs.org/axe-core/-/axe-core-4.10.3.tgz", - "integrity": "sha512-Xm7bpRXnDSX2YE2YFfBk2FnF0ep6tmG7xPh8iHee8MIcrgq762Nkce856dYtJYLkuIoYZvGfTs/PbZhideTcEg==", + "version": "4.11.1", + "resolved": "https://registry.npmjs.org/axe-core/-/axe-core-4.11.1.tgz", + "integrity": "sha512-BASOg+YwO2C+346x3LZOeoovTIoTrRqEsqMa6fmfAV0P+U9mFr9NsyOEpiYvFjbc64NMrSswhV50WdXzdb/Z5A==", "dev": true, + "license": "MPL-2.0", "engines": { "node": ">=4" } }, "node_modules/axios": { - "version": "1.13.2", - "resolved": "https://registry.npmjs.org/axios/-/axios-1.13.2.tgz", - "integrity": "sha512-VPk9ebNqPcy5lRGuSlKx752IlDatOjT9paPlm8A7yOuW2Fbvp4X3JznJtT4f0GzGLLiWE9W8onz51SqLYwzGaA==", + "version": "1.13.4", + "resolved": "https://registry.npmjs.org/axios/-/axios-1.13.4.tgz", + "integrity": "sha512-1wVkUaAO6WyaYtCkcYCOx12ZgpGf9Zif+qXa4n+oYzK558YryKqiL6UWwd5DqiH3VRW0GYhTZQ/vlgJrCoNQlg==", "license": "MIT", "dependencies": { "follow-redirects": "^1.15.6", @@ -4155,6 +4318,7 @@ "resolved": "https://registry.npmjs.org/axobject-query/-/axobject-query-4.1.0.tgz", "integrity": "sha512-qIj0G9wZbMGNLjLmg1PT6v2mE9AH2zlnADJD/2tC6E00hgmhUOfEB6greHPAfLRSufHqROIUTkw6E+M3lH0PTQ==", "dev": true, + "license": "Apache-2.0", "engines": { "node": ">= 0.4" } @@ -4172,7 +4336,8 @@ "node_modules/balanced-match": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.2.tgz", - "integrity": "sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw==" + "integrity": "sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw==", + "license": "MIT" }, "node_modules/base64-js": { "version": "1.5.1", @@ -4191,7 +4356,18 @@ "type": "consulting", "url": "https://feross.org/support" } - ] + ], + "license": "MIT" + }, + "node_modules/baseline-browser-mapping": { + "version": "2.9.19", + "resolved": "https://registry.npmjs.org/baseline-browser-mapping/-/baseline-browser-mapping-2.9.19.tgz", + "integrity": "sha512-ipDqC8FrAl/76p2SSWKSI+H9tFwm7vYqXQrItCuiVPt26Km0jS+NzSsBWAaBusvSbQcfJG+JitdMm+wZAgTYqg==", + "dev": true, + "license": "Apache-2.0", + "bin": { + "baseline-browser-mapping": "dist/cli.js" + } }, "node_modules/bidi-js": { "version": "1.0.3", @@ -4227,7 +4403,8 @@ "node_modules/bluebird": { "version": "3.4.7", "resolved": "https://registry.npmjs.org/bluebird/-/bluebird-3.4.7.tgz", - "integrity": "sha512-iD3898SR7sWVRHbiQv+sHUtHnMvC1o3nW5rAcqnq3uOn07DSAppZYUkIGslDz6gXC7HfunPe7YVBgoEJASPcHA==" + "integrity": "sha512-iD3898SR7sWVRHbiQv+sHUtHnMvC1o3nW5rAcqnq3uOn07DSAppZYUkIGslDz6gXC7HfunPe7YVBgoEJASPcHA==", + "license": "MIT" }, "node_modules/boolbase": { "version": "1.0.0", @@ -4239,7 +4416,7 @@ "version": "1.1.12", "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.12.tgz", "integrity": "sha512-9T9UjW3r0UW5c1Q7GTwllptXwhvYmEzFhzMfZ9H7FQWt+uZePjZPjBP/W1ZEyZ1twGWom5/56TF4lPcqjnDHcg==", - "dev": true, + "license": "MIT", "dependencies": { "balanced-match": "^1.0.0", "concat-map": "0.0.1" @@ -4250,6 +4427,7 @@ "resolved": "https://registry.npmjs.org/braces/-/braces-3.0.3.tgz", "integrity": "sha512-yQbXgO/OSZVD2IsiLlro+7Hf6Q18EJrKSEsdoMzKePKXct3gvD8oLcOQdIzGupr5Fj+EDe8gO/lxc1BzfMpxvA==", "dev": true, + "license": "MIT", "dependencies": { "fill-range": "^7.1.1" }, @@ -4258,9 +4436,9 @@ } }, "node_modules/browserslist": { - "version": "4.25.4", - "resolved": "https://registry.npmjs.org/browserslist/-/browserslist-4.25.4.tgz", - "integrity": "sha512-4jYpcjabC606xJ3kw2QwGEZKX0Aw7sgQdZCvIK9dhVSPh76BKo+C+btT1RRofH7B+8iNpEbgGNVWiLki5q93yg==", + "version": "4.28.1", + "resolved": "https://registry.npmjs.org/browserslist/-/browserslist-4.28.1.tgz", + "integrity": "sha512-ZC5Bd0LgJXgwGqUknZY/vkUQ04r8NXnJZ3yYi4vDmSiZmC/pdSN0NbNRPxZpbtO4uAfDUAFffO8IZoM3Gj8IkA==", "dev": true, "funding": [ { @@ -4276,12 +4454,14 @@ "url": "https://github.com/sponsors/ai" } ], + "license": "MIT", "peer": true, "dependencies": { - "caniuse-lite": "^1.0.30001737", - "electron-to-chromium": "^1.5.211", - "node-releases": "^2.0.19", - "update-browserslist-db": "^1.1.3" + "baseline-browser-mapping": "^2.9.0", + "caniuse-lite": "^1.0.30001759", + "electron-to-chromium": "^1.5.263", + "node-releases": "^2.0.27", + "update-browserslist-db": "^1.2.0" }, "bin": { "browserslist": "cli.js" @@ -4301,6 +4481,7 @@ "resolved": "https://registry.npmjs.org/call-bind/-/call-bind-1.0.8.tgz", "integrity": "sha512-oKlSFMcMwpUg2ednkhQ454wfWiU/ul3CkJe/PEHcTKuiX6RpbehUiFMXu13HalGZxfUwCQzZG747YXBn1im9ww==", "dev": true, + "license": "MIT", "dependencies": { "call-bind-apply-helpers": "^1.0.0", "es-define-property": "^1.0.0", @@ -4318,7 +4499,7 @@ "version": "1.0.2", "resolved": "https://registry.npmjs.org/call-bind-apply-helpers/-/call-bind-apply-helpers-1.0.2.tgz", "integrity": "sha512-Sp1ablJ0ivDkSzjcaJdxEunN5/XvksFJ2sMBFfq6x0ryhQV/2b/KwFe21cMpmHtPOSij8K99/wSfoEuTObmuMQ==", - "dev": true, + "license": "MIT", "dependencies": { "es-errors": "^1.3.0", "function-bind": "^1.1.2" @@ -4332,6 +4513,7 @@ "resolved": "https://registry.npmjs.org/call-bound/-/call-bound-1.0.4.tgz", "integrity": "sha512-+ys997U96po4Kx/ABpBCqhA9EuxJaQWDQg7295H4hBphv3IZg0boBKuwYpt4YXp6MZ5AmZQnU/tyMTlRpaSejg==", "dev": true, + "license": "MIT", "dependencies": { "call-bind-apply-helpers": "^1.0.2", "get-intrinsic": "^1.3.0" @@ -4348,6 +4530,7 @@ "resolved": "https://registry.npmjs.org/callsites/-/callsites-3.1.0.tgz", "integrity": "sha512-P8BjAsXvZS+VIDUI11hHCQEv74YT67YUi5JJFNWIqL235sBmjX4+qx9Muvls5ivyNENctx46xQLQ3aTuE7ssaQ==", "dev": true, + "license": "MIT", "engines": { "node": ">=6" } @@ -4357,14 +4540,15 @@ "resolved": "https://registry.npmjs.org/camelcase-css/-/camelcase-css-2.0.1.tgz", "integrity": "sha512-QOSvevhslijgYwRx6Rv7zKdMF8lbRmx+uQGx2+vDc+KI/eBnsy9kit5aj23AgGu3pa4t9AgwbnXWqS+iOY+2aA==", "dev": true, + "license": "MIT", "engines": { "node": ">= 6" } }, "node_modules/caniuse-lite": { - "version": "1.0.30001737", - "resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001737.tgz", - "integrity": "sha512-BiloLiXtQNrY5UyF0+1nSJLXUENuhka2pzy2Fx5pGxqavdrxSCW4U6Pn/PoG3Efspi2frRbHpBV2XsrPE6EDlw==", + "version": "1.0.30001766", + "resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001766.tgz", + "integrity": "sha512-4C0lfJ0/YPjJQHagaE9x2Elb69CIqEPZeG0anQt9SIvIoOH4a4uaRl73IavyO+0qZh6MDLH//DrXThEYKHkmYA==", "funding": [ { "type": "opencollective", @@ -4378,7 +4562,8 @@ "type": "github", "url": "https://github.com/sponsors/ai" } - ] + ], + "license": "CC-BY-4.0" }, "node_modules/ccount": { "version": "2.0.1", @@ -4394,7 +4579,7 @@ "version": "4.1.2", "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", - "dev": true, + "license": "MIT", "dependencies": { "ansi-styles": "^4.1.0", "supports-color": "^7.1.0" @@ -4447,9 +4632,9 @@ } }, "node_modules/cheerio": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/cheerio/-/cheerio-1.1.2.tgz", - "integrity": "sha512-IkxPpb5rS/d1IiLbHMgfPuS0FgiWTtFIm/Nj+2woXDLTZ7fOT2eqzgYbdMlLweqlHbsZjxEChoVK+7iph7jyQg==", + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/cheerio/-/cheerio-1.2.0.tgz", + "integrity": "sha512-WDrybc/gKFpTYQutKIK6UvfcuxijIZfMfXaYm8NMsPQxSYvf+13fXUJ4rztGGbJcBQ/GF55gvrZ0Bc0bj/mqvg==", "license": "MIT", "dependencies": { "cheerio-select": "^2.1.0", @@ -4457,11 +4642,11 @@ "domhandler": "^5.0.3", "domutils": "^3.2.2", "encoding-sniffer": "^0.2.1", - "htmlparser2": "^10.0.0", + "htmlparser2": "^10.1.0", "parse5": "^7.3.0", "parse5-htmlparser2-tree-adapter": "^7.1.0", "parse5-parser-stream": "^7.1.2", - "undici": "^7.12.0", + "undici": "^7.19.0", "whatwg-mimetype": "^4.0.0" }, "engines": { @@ -4493,6 +4678,7 @@ "resolved": "https://registry.npmjs.org/chokidar/-/chokidar-3.6.0.tgz", "integrity": "sha512-7VT13fmjotKpGipCW9JEQAusEPE+Ei8nl6/g4FBAmIm0GOOLMua9NDDo/DWp0ZAxCr3cPq5ZpBqmPAQgDda2Pw==", "dev": true, + "license": "MIT", "dependencies": { "anymatch": "~3.1.2", "braces": "~3.0.2", @@ -4517,6 +4703,7 @@ "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-5.1.2.tgz", "integrity": "sha512-AOIgSQCepiJYwP3ARnGx+5VnTu2HBYdzbGP45eLw1vr3zB3vZLeyed1sC9hnbcOc9/SrMyM5RPQrkGz4aS9Zow==", "dev": true, + "license": "ISC", "dependencies": { "is-glob": "^4.0.1" }, @@ -4539,7 +4726,8 @@ "node_modules/client-only": { "version": "0.0.1", "resolved": "https://registry.npmjs.org/client-only/-/client-only-0.0.1.tgz", - "integrity": "sha512-IV3Ou0jSMzZrd3pZ48nLkT9DA7Ag1pnPzaiQhpW7c3RbcqqzvzzVu+L8gfqMp/8IM2MQtSiqaCxrrcfu8I8rMA==" + "integrity": "sha512-IV3Ou0jSMzZrd3pZ48nLkT9DA7Ag1pnPzaiQhpW7c3RbcqqzvzzVu+L8gfqMp/8IM2MQtSiqaCxrrcfu8I8rMA==", + "license": "MIT" }, "node_modules/cliui": { "version": "8.0.1", @@ -4617,6 +4805,7 @@ "version": "2.1.1", "resolved": "https://registry.npmjs.org/clsx/-/clsx-2.1.1.tgz", "integrity": "sha512-eYm0QWBtUrBWZWG0d386OGAw16Z995PiOVo2B7bjWSbHedGl5e0ZWaq65kOGgUSNesEIDkB9ISbTg/JK9dhCZA==", + "license": "MIT", "engines": { "node": ">=6" } @@ -4641,6 +4830,7 @@ "version": "2.0.1", "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", + "license": "MIT", "dependencies": { "color-name": "~1.1.4" }, @@ -4651,7 +4841,20 @@ "node_modules/color-name": { "version": "1.1.4", "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" + "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==", + "license": "MIT" + }, + "node_modules/combined-stream": { + "version": "1.0.8", + "resolved": "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.8.tgz", + "integrity": "sha512-FQN4MRfuJeHf7cBbBMJFXhKSDq+2kAArBlmRBvcvFE5BB1HZKXtSFASDhdlz9zOYwxh8lDdnvmMOe/+5cdoEdg==", + "license": "MIT", + "dependencies": { + "delayed-stream": "~1.0.0" + }, + "engines": { + "node": ">= 0.8" + } }, "node_modules/comma-separated-tokens": { "version": "2.0.3", @@ -4668,6 +4871,7 @@ "resolved": "https://registry.npmjs.org/commander/-/commander-4.1.1.tgz", "integrity": "sha512-NOKm8xhkzAjzFx8B2v5OAHT+u5pRQc2UCa2Vq9jYL/31o2wi9mxBA7LIFs3sV5VSC49z6pEhfbMULvShKj26WA==", "dev": true, + "license": "MIT", "engines": { "node": ">= 6" } @@ -4676,25 +4880,32 @@ "version": "0.0.1", "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", "integrity": "sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg==", - "dev": true + "license": "MIT" }, "node_modules/cookie": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/cookie/-/cookie-1.0.2.tgz", - "integrity": "sha512-9Kr/j4O16ISv8zBBhJoi4bXOYNTkFLOqSL3UDB0njXxCXNezjeyVrJyGOWtgfs/q2km1gwBcfH8q1yEGoMYunA==", + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/cookie/-/cookie-1.1.1.tgz", + "integrity": "sha512-ei8Aos7ja0weRpFzJnEA9UHJ/7XQmqglbRwnf2ATjcB9Wq874VKH9kfjjirM6UhU2/E5fFYadylyhFldcqSidQ==", + "license": "MIT", "engines": { "node": ">=18" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/express" } }, "node_modules/core-util-is": { "version": "1.0.3", "resolved": "https://registry.npmjs.org/core-util-is/-/core-util-is-1.0.3.tgz", - "integrity": "sha512-ZQBvi1DcpJ4GDqanjucZ2Hj3wEO5pZDS89BWbkcrvdxksJorwUDDZamX9ldFkp9aw2lmBDLgkObEA4DWNJ9FYQ==" + "integrity": "sha512-ZQBvi1DcpJ4GDqanjucZ2Hj3wEO5pZDS89BWbkcrvdxksJorwUDDZamX9ldFkp9aw2lmBDLgkObEA4DWNJ9FYQ==", + "license": "MIT" }, "node_modules/cross-spawn": { "version": "7.0.6", "resolved": "https://registry.npmjs.org/cross-spawn/-/cross-spawn-7.0.6.tgz", "integrity": "sha512-uV2QOWP2nWzsy2aMp8aRibhi9dlzF5Hgh5SHaB9OiTGEyDTiJJyx0uy51QXdyWbtAHNua4XJzUKca3OzKUd3vA==", + "license": "MIT", "dependencies": { "path-key": "^3.1.0", "shebang-command": "^2.0.0", @@ -4750,6 +4961,7 @@ "resolved": "https://registry.npmjs.org/cssesc/-/cssesc-3.0.0.tgz", "integrity": "sha512-/Tb/JcjK111nNScGob5MNtsntNM1aCNUDipB/TkwZFhyDrrE47SOx/18wF2bbjgc3ZzCSKW1T5nt5EbFoAz/Vg==", "dev": true, + "license": "MIT", "bin": { "cssesc": "bin/cssesc" }, @@ -4772,25 +4984,18 @@ "node": ">=20" } }, - "node_modules/cssstyle/node_modules/lru-cache": { - "version": "11.2.4", - "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-11.2.4.tgz", - "integrity": "sha512-B5Y16Jr9LB9dHVkh6ZevG+vAbOsNOYCX+sXvFWFu7B3Iz5mijW3zdbMyhsh8ANd2mSWBYdJgnqi+mL7/LrOPYg==", - "license": "BlueOak-1.0.0", - "engines": { - "node": "20 || >=22" - } - }, "node_modules/csstype": { - "version": "3.1.3", - "resolved": "https://registry.npmjs.org/csstype/-/csstype-3.1.3.tgz", - "integrity": "sha512-M1uQkMl8rQK/szD0LNhtqxIPLpimGm8sOBwU7lLnCpSbTyY3yeU1Vc7l4KT5zT4s/yOxHH5O7tIuuLOCnLADRw==" + "version": "3.2.3", + "resolved": "https://registry.npmjs.org/csstype/-/csstype-3.2.3.tgz", + "integrity": "sha512-z1HGKcYy2xA8AGQfwrn0PAy+PB7X/GSj3UVJW9qKyn43xWa+gl5nXmU4qqLMRzWVLFC8KusUX8T/0kCiOYpAIQ==", + "license": "MIT" }, "node_modules/damerau-levenshtein": { "version": "1.0.8", "resolved": "https://registry.npmjs.org/damerau-levenshtein/-/damerau-levenshtein-1.0.8.tgz", "integrity": "sha512-sdQSFB7+llfUcQHUQO3+B8ERRj0Oa4w9POWMI/puGtuf7gFywGmkaLCElnudfTiKZV+NvHqL0ifzdrI8Ro7ESA==", - "dev": true + "dev": true, + "license": "BSD-2-Clause" }, "node_modules/data-uri-to-buffer": { "version": "4.0.1", @@ -4802,39 +5007,23 @@ } }, "node_modules/data-urls": { - "version": "6.0.0", - "resolved": "https://registry.npmjs.org/data-urls/-/data-urls-6.0.0.tgz", - "integrity": "sha512-BnBS08aLUM+DKamupXs3w2tJJoqU+AkaE/+6vQxi/G/DPmIZFJJp9Dkb1kM03AZx8ADehDUZgsNxju3mPXZYIA==", - "license": "MIT", - "dependencies": { - "whatwg-mimetype": "^4.0.0", - "whatwg-url": "^15.0.0" - }, - "engines": { - "node": ">=20" - } - }, - "node_modules/data-urls/node_modules/tr46": { - "version": "6.0.0", - "resolved": "https://registry.npmjs.org/tr46/-/tr46-6.0.0.tgz", - "integrity": "sha512-bLVMLPtstlZ4iMQHpFHTR7GAGj2jxi8Dg0s2h2MafAE4uSWF98FC/3MomU51iQAMf8/qDUbKWf5GxuvvVcXEhw==", + "version": "6.0.1", + "resolved": "https://registry.npmjs.org/data-urls/-/data-urls-6.0.1.tgz", + "integrity": "sha512-euIQENZg6x8mj3fO6o9+fOW8MimUI4PpD/fZBhJfeioZVy9TUpM4UY7KjQNVZFlqwJ0UdzRDzkycB997HEq1BQ==", "license": "MIT", "dependencies": { - "punycode": "^2.3.1" + "whatwg-mimetype": "^5.0.0", + "whatwg-url": "^15.1.0" }, "engines": { "node": ">=20" } }, - "node_modules/data-urls/node_modules/whatwg-url": { - "version": "15.1.0", - "resolved": "https://registry.npmjs.org/whatwg-url/-/whatwg-url-15.1.0.tgz", - "integrity": "sha512-2ytDk0kiEj/yu90JOAp44PVPUkO9+jVhyf+SybKlRHSDlvOOZhdPIrr7xTH64l4WixO2cP+wQIcgujkGBPPz6g==", + "node_modules/data-urls/node_modules/whatwg-mimetype": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/whatwg-mimetype/-/whatwg-mimetype-5.0.0.tgz", + "integrity": "sha512-sXcNcHOC51uPGF0P/D4NVtrkjSU2fNsm9iog4ZvZJsL3rjoDAzXZhkm2MWt1y+PUdggKAYVoMAIYcs78wJ51Cw==", "license": "MIT", - "dependencies": { - "tr46": "^6.0.0", - "webidl-conversions": "^8.0.0" - }, "engines": { "node": ">=20" } @@ -4844,6 +5033,7 @@ "resolved": "https://registry.npmjs.org/data-view-buffer/-/data-view-buffer-1.0.2.tgz", "integrity": "sha512-EmKO5V3OLXh1rtK2wgXRansaK1/mtVdTUEiEI0W8RkvgT05kfxaH29PliLnpLP73yYO6142Q72QNa8Wx/A5CqQ==", "dev": true, + "license": "MIT", "dependencies": { "call-bound": "^1.0.3", "es-errors": "^1.3.0", @@ -4861,6 +5051,7 @@ "resolved": "https://registry.npmjs.org/data-view-byte-length/-/data-view-byte-length-1.0.2.tgz", "integrity": "sha512-tuhGbE6CfTM9+5ANGf+oQb72Ky/0+s3xKUpHvShfiz2RxMFgFPjsXuRLBVMtvMs15awe45SRb83D6wH4ew6wlQ==", "dev": true, + "license": "MIT", "dependencies": { "call-bound": "^1.0.3", "es-errors": "^1.3.0", @@ -4878,6 +5069,7 @@ "resolved": "https://registry.npmjs.org/data-view-byte-offset/-/data-view-byte-offset-1.0.1.tgz", "integrity": "sha512-BS8PfmtDGnrgYdOonGZQdLZslWIeCGFP9tpan0hi1Co2Zr2NKADsvGYA8XxuG/4UWgJ6Cjtv+YJnB6MM69QGlQ==", "dev": true, + "license": "MIT", "dependencies": { "call-bound": "^1.0.2", "es-errors": "^1.3.0", @@ -4891,9 +5083,10 @@ } }, "node_modules/debug": { - "version": "4.4.1", - "resolved": "https://registry.npmjs.org/debug/-/debug-4.4.1.tgz", - "integrity": "sha512-KcKCqiftBJcZr++7ykoDIEwSa3XWowTfNPo92BYxjXiyYEVrUQh2aLyhxBCwww+heortUFxEJYcRzosstTEBYQ==", + "version": "4.4.3", + "resolved": "https://registry.npmjs.org/debug/-/debug-4.4.3.tgz", + "integrity": "sha512-RGwwWnwQvkVfavKVt22FGLw+xYSdzARwm0ru6DhTVA3umU5hZc28V3kO4stgYryrTlLpuvgI9GiijltAjNbcqA==", + "license": "MIT", "dependencies": { "ms": "^2.1.3" }, @@ -4913,9 +5106,9 @@ "license": "MIT" }, "node_modules/decode-named-character-reference": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/decode-named-character-reference/-/decode-named-character-reference-1.2.0.tgz", - "integrity": "sha512-c6fcElNV6ShtZXmsgNgFFV5tVX2PaV4g+MOAkb8eXHvn6sryJBrZa9r0zV6+dtTyoCKxtDy5tyQ5ZwQuidtd+Q==", + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/decode-named-character-reference/-/decode-named-character-reference-1.3.0.tgz", + "integrity": "sha512-GtpQYB283KrPp6nRw50q3U9/VfOutZOe103qlN7BPP6Ad27xYnOIWv4lPzo8HCAL+mMZofJ9KEy30fq6MfaK6Q==", "license": "MIT", "dependencies": { "character-entities": "^2.0.0" @@ -4929,13 +5122,15 @@ "version": "0.1.4", "resolved": "https://registry.npmjs.org/deep-is/-/deep-is-0.1.4.tgz", "integrity": "sha512-oIPzksmTg4/MriiaYGO+okXDT7ztn/w3Eptv/+gSIdMdKsJo0u4CfYNFJPy+4SKMuCqGw2wxnA+URMg3t8a/bQ==", - "dev": true + "dev": true, + "license": "MIT" }, "node_modules/define-data-property": { "version": "1.1.4", "resolved": "https://registry.npmjs.org/define-data-property/-/define-data-property-1.1.4.tgz", "integrity": "sha512-rBMvIzlpA8v6E+SJZoo++HAYqsLrkg7MSfIinMPFhmkorw7X+dOXVJQs+QT69zGkzMyfDnIMN2Wid1+NbL3T+A==", "dev": true, + "license": "MIT", "dependencies": { "es-define-property": "^1.0.0", "es-errors": "^1.3.0", @@ -4953,6 +5148,7 @@ "resolved": "https://registry.npmjs.org/define-properties/-/define-properties-1.2.1.tgz", "integrity": "sha512-8QmQKqEASLd5nx0U1B1okLElbUuuttJ/AnYmRXbbbGDWh6uS208EjD4Xqq/I9wK7u0v6O08XhTWnt5XtEbR6Dg==", "dev": true, + "license": "MIT", "dependencies": { "define-data-property": "^1.0.1", "has-property-descriptors": "^1.0.0", @@ -4965,6 +5161,15 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/delayed-stream": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/delayed-stream/-/delayed-stream-1.0.0.tgz", + "integrity": "sha512-ZySD7Nf91aLB0RxL4KGrKHBXl7Eds1DAmEdcoVawXnLD7SDhpNgtuII2aAkg7a7QS41jxPSZ17p4VdGnMHk3MQ==", + "license": "MIT", + "engines": { + "node": ">=0.4.0" + } + }, "node_modules/dequal": { "version": "2.0.3", "resolved": "https://registry.npmjs.org/dequal/-/dequal-2.0.3.tgz", @@ -4986,7 +5191,8 @@ "node_modules/detect-node-es": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/detect-node-es/-/detect-node-es-1.1.0.tgz", - "integrity": "sha512-ypdmJU/TbBby2Dxibuv7ZLW3Bs1QEmM7nHjEANfohJLvE0XVujisn1qPJcZxg+qDucsr+bP6fLD1rPS3AhJ7EQ==" + "integrity": "sha512-ypdmJU/TbBby2Dxibuv7ZLW3Bs1QEmM7nHjEANfohJLvE0XVujisn1qPJcZxg+qDucsr+bP6fLD1rPS3AhJ7EQ==", + "license": "MIT" }, "node_modules/devlop": { "version": "1.1.0", @@ -5005,24 +5211,28 @@ "version": "1.2.2", "resolved": "https://registry.npmjs.org/didyoumean/-/didyoumean-1.2.2.tgz", "integrity": "sha512-gxtyfqMg7GKyhQmb056K7M3xszy/myH8w+B4RT+QXBQsvAOdc3XymqDDPHx1BgPgsdAA5SIifona89YtRATDzw==", - "dev": true + "dev": true, + "license": "Apache-2.0" }, "node_modules/dingbat-to-unicode": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/dingbat-to-unicode/-/dingbat-to-unicode-1.0.1.tgz", - "integrity": "sha512-98l0sW87ZT58pU4i61wa2OHwxbiYSbuxsCBozaVnYX2iCnr3bLM3fIes1/ej7h1YdOKuKt/MLs706TVnALA65w==" + "integrity": "sha512-98l0sW87ZT58pU4i61wa2OHwxbiYSbuxsCBozaVnYX2iCnr3bLM3fIes1/ej7h1YdOKuKt/MLs706TVnALA65w==", + "license": "BSD-2-Clause" }, "node_modules/dlv": { "version": "1.1.3", "resolved": "https://registry.npmjs.org/dlv/-/dlv-1.1.3.tgz", "integrity": "sha512-+HlytyjlPKnIG8XuRG8WvmBP8xs8P71y+SKKS6ZXWoEgLuePxtDoUEiH7WkdePWrQ5JBpE6aoVqfZfJUQkjXwA==", - "dev": true + "dev": true, + "license": "MIT" }, "node_modules/doctrine": { "version": "2.1.0", "resolved": "https://registry.npmjs.org/doctrine/-/doctrine-2.1.0.tgz", "integrity": "sha512-35mSku4ZXK0vfCuHEDAwt55dg2jNajHZ1odvF+8SSr82EsZY4QmXfuWso8oEd8zRhVObSN18aM0CjSdoBX7zIw==", "dev": true, + "license": "Apache-2.0", "dependencies": { "esutils": "^2.0.2" }, @@ -5044,18 +5254,6 @@ "url": "https://github.com/cheeriojs/dom-serializer?sponsor=1" } }, - "node_modules/dom-serializer/node_modules/entities": { - "version": "4.5.0", - "resolved": "https://registry.npmjs.org/entities/-/entities-4.5.0.tgz", - "integrity": "sha512-V0hjH4dGPh9Ao5p0MoRY6BVqtwCjhz6vI5LT8AJ55H+4g9/4vbHx1I54fS0XuclLhDHArPQCiMjDxjaL8fPxhw==", - "license": "BSD-2-Clause", - "engines": { - "node": ">=0.12" - }, - "funding": { - "url": "https://github.com/fb55/entities?sponsor=1" - } - }, "node_modules/domelementtype": { "version": "2.3.0", "resolved": "https://registry.npmjs.org/domelementtype/-/domelementtype-2.3.0.tgz", @@ -5114,6 +5312,7 @@ "version": "0.1.12", "resolved": "https://registry.npmjs.org/duck/-/duck-0.1.12.tgz", "integrity": "sha512-wkctla1O6VfP89gQ+J/yDesM0S7B7XLXjKGzXxMDVFg7uEn706niAtyYovKbyq1oT9YwDcly721/iUWoc8MVRg==", + "license": "BSD", "dependencies": { "underscore": "^1.13.1" } @@ -5122,7 +5321,7 @@ "version": "1.0.1", "resolved": "https://registry.npmjs.org/dunder-proto/-/dunder-proto-1.0.1.tgz", "integrity": "sha512-KIN/nDJBQRcXw0MLVhZE9iQHmG68qAVIBg9CqmUYjmQIhgij9U5MFvrqkUL5FbtyyzZuOeOt0zdeRe4UY7ct+A==", - "dev": true, + "license": "MIT", "dependencies": { "call-bind-apply-helpers": "^1.0.1", "es-errors": "^1.3.0", @@ -5144,24 +5343,11 @@ "stream-shift": "^1.0.2" } }, - "node_modules/duplexify/node_modules/readable-stream": { - "version": "3.6.2", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-3.6.2.tgz", - "integrity": "sha512-9u/sniCrY3D5WdsERHzHE4G2YCXqoG5FTHUiCC4SIbr6XcLZBY05ya9EKjYek9O5xOAwjGq+1JdGBAS7Q9ScoA==", - "license": "MIT", - "dependencies": { - "inherits": "^2.0.3", - "string_decoder": "^1.1.1", - "util-deprecate": "^1.0.1" - }, - "engines": { - "node": ">= 6" - } - }, "node_modules/eastasianwidth": { "version": "0.2.0", "resolved": "https://registry.npmjs.org/eastasianwidth/-/eastasianwidth-0.2.0.tgz", - "integrity": "sha512-I88TYZWc9XiYHRQ4/3c5rjjfgkjhLyW2luGIheGERbNQ6OY7yTybanSpDXZa8y7VUP9YmDcYa+eyq4ca7iLqWA==" + "integrity": "sha512-I88TYZWc9XiYHRQ4/3c5rjjfgkjhLyW2luGIheGERbNQ6OY7yTybanSpDXZa8y7VUP9YmDcYa+eyq4ca7iLqWA==", + "license": "MIT" }, "node_modules/ecdsa-sig-formatter": { "version": "1.0.11", @@ -5173,15 +5359,17 @@ } }, "node_modules/electron-to-chromium": { - "version": "1.5.211", - "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.5.211.tgz", - "integrity": "sha512-IGBvimJkotaLzFnwIVgW9/UD/AOJ2tByUmeOrtqBfACSbAw5b1G0XpvdaieKyc7ULmbwXVx+4e4Be8pOPBrYkw==", - "dev": true + "version": "1.5.283", + "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.5.283.tgz", + "integrity": "sha512-3vifjt1HgrGW/h76UEeny+adYApveS9dH2h3p57JYzBSXJIKUJAvtmIytDKjcSCt9xHfrNCFJ7gts6vkhuq++w==", + "dev": true, + "license": "ISC" }, "node_modules/emoji-regex": { "version": "9.2.2", "resolved": "https://registry.npmjs.org/emoji-regex/-/emoji-regex-9.2.2.tgz", - "integrity": "sha512-L18DaJsXSUk2+42pv8mLs5jJT2hqFkFE4j21wOmgbUqsZ2hL72NsUU785g9RXgo3s0ZNgVl42TiHp3ZtOv/Vyg==" + "integrity": "sha512-L18DaJsXSUk2+42pv8mLs5jJT2hqFkFE4j21wOmgbUqsZ2hL72NsUU785g9RXgo3s0ZNgVl42TiHp3ZtOv/Vyg==", + "license": "MIT" }, "node_modules/encoding-sniffer": { "version": "0.2.1", @@ -5206,9 +5394,9 @@ } }, "node_modules/entities": { - "version": "6.0.1", - "resolved": "https://registry.npmjs.org/entities/-/entities-6.0.1.tgz", - "integrity": "sha512-aN97NXWF6AWBTahfVOIrB/NShkzi5H7F9r1s9mD3cDj4Ko5f2qhhVoYMibXF7GlLveb/D2ioWay8lxI97Ven3g==", + "version": "4.5.0", + "resolved": "https://registry.npmjs.org/entities/-/entities-4.5.0.tgz", + "integrity": "sha512-V0hjH4dGPh9Ao5p0MoRY6BVqtwCjhz6vI5LT8AJ55H+4g9/4vbHx1I54fS0XuclLhDHArPQCiMjDxjaL8fPxhw==", "license": "BSD-2-Clause", "engines": { "node": ">=0.12" @@ -5218,10 +5406,11 @@ } }, "node_modules/es-abstract": { - "version": "1.24.0", - "resolved": "https://registry.npmjs.org/es-abstract/-/es-abstract-1.24.0.tgz", - "integrity": "sha512-WSzPgsdLtTcQwm4CROfS5ju2Wa1QQcVeT37jFjYzdFz1r9ahadC8B8/a4qxJxM+09F18iumCdRmlr96ZYkQvEg==", + "version": "1.24.1", + "resolved": "https://registry.npmjs.org/es-abstract/-/es-abstract-1.24.1.tgz", + "integrity": "sha512-zHXBLhP+QehSSbsS9Pt23Gg964240DPd6QCf8WpkqEXxQ7fhdZzYsocOr5u7apWonsS5EjZDmTF+/slGMyasvw==", "dev": true, + "license": "MIT", "dependencies": { "array-buffer-byte-length": "^1.0.2", "arraybuffer.prototype.slice": "^1.0.4", @@ -5289,7 +5478,7 @@ "version": "1.0.1", "resolved": "https://registry.npmjs.org/es-define-property/-/es-define-property-1.0.1.tgz", "integrity": "sha512-e3nRfgfUZ4rNGL232gUgX06QNyyez04KdjFrF+LTRoOXmrOgFKDg4BCdsjW8EnT69eqdYGmRpJwiPVYNrCaW3g==", - "dev": true, + "license": "MIT", "engines": { "node": ">= 0.4" } @@ -5298,32 +5487,33 @@ "version": "1.3.0", "resolved": "https://registry.npmjs.org/es-errors/-/es-errors-1.3.0.tgz", "integrity": "sha512-Zf5H2Kxt2xjTvbJvP2ZWLEICxA6j+hAmMzIlypy4xcBg1vKVnx89Wy0GbS+kf5cwCVFFzdCFh2XSCFNULS6csw==", - "dev": true, + "license": "MIT", "engines": { "node": ">= 0.4" } }, "node_modules/es-iterator-helpers": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/es-iterator-helpers/-/es-iterator-helpers-1.2.1.tgz", - "integrity": "sha512-uDn+FE1yrDzyC0pCo961B2IHbdM8y/ACZsKD4dG6WqrjV53BADjwa7D+1aom2rsNVfLyDgU/eigvlJGJ08OQ4w==", + "version": "1.2.2", + "resolved": "https://registry.npmjs.org/es-iterator-helpers/-/es-iterator-helpers-1.2.2.tgz", + "integrity": "sha512-BrUQ0cPTB/IwXj23HtwHjS9n7O4h9FX94b4xc5zlTHxeLgTAdzYUDyy6KdExAl9lbN5rtfe44xpjpmj9grxs5w==", "dev": true, + "license": "MIT", "dependencies": { "call-bind": "^1.0.8", - "call-bound": "^1.0.3", + "call-bound": "^1.0.4", "define-properties": "^1.2.1", - "es-abstract": "^1.23.6", + "es-abstract": "^1.24.1", "es-errors": "^1.3.0", - "es-set-tostringtag": "^2.0.3", + "es-set-tostringtag": "^2.1.0", "function-bind": "^1.1.2", - "get-intrinsic": "^1.2.6", + "get-intrinsic": "^1.3.0", "globalthis": "^1.0.4", "gopd": "^1.2.0", "has-property-descriptors": "^1.0.2", "has-proto": "^1.2.0", "has-symbols": "^1.1.0", "internal-slot": "^1.1.0", - "iterator.prototype": "^1.1.4", + "iterator.prototype": "^1.1.5", "safe-array-concat": "^1.1.3" }, "engines": { @@ -5334,7 +5524,7 @@ "version": "1.1.1", "resolved": "https://registry.npmjs.org/es-object-atoms/-/es-object-atoms-1.1.1.tgz", "integrity": "sha512-FGgH2h8zKNim9ljj7dankFPcICIK9Cp5bm+c2gQSYePhpaG5+esrLODihIorn+Pe6FGJzWhXQotPv73jTaldXA==", - "dev": true, + "license": "MIT", "dependencies": { "es-errors": "^1.3.0" }, @@ -5346,7 +5536,7 @@ "version": "2.1.0", "resolved": "https://registry.npmjs.org/es-set-tostringtag/-/es-set-tostringtag-2.1.0.tgz", "integrity": "sha512-j6vWzfrGVfyXxge+O0x5sh6cvxAog0a/4Rdd2K36zCMV5eJ+/+tOAngRO8cODMNWbVRdVlmGZQL2YS3yR8bIUA==", - "dev": true, + "license": "MIT", "dependencies": { "es-errors": "^1.3.0", "get-intrinsic": "^1.2.6", @@ -5362,6 +5552,7 @@ "resolved": "https://registry.npmjs.org/es-shim-unscopables/-/es-shim-unscopables-1.1.0.tgz", "integrity": "sha512-d9T8ucsEhh8Bi1woXCf+TIKDIROLG5WCkxg8geBCbvk22kzwC5G2OnXVMO6FUsvQlgUUXQ2itephWDLqDzbeCw==", "dev": true, + "license": "MIT", "dependencies": { "hasown": "^2.0.2" }, @@ -5374,6 +5565,7 @@ "resolved": "https://registry.npmjs.org/es-to-primitive/-/es-to-primitive-1.3.0.tgz", "integrity": "sha512-w+5mJ3GuFL+NjVtJlvydShqE1eN3h3PbI7/5LAsYJP/2qtuMXjfL2LpHSRqo4b4eSF5K/DH1JXKUAHSB2UW50g==", "dev": true, + "license": "MIT", "dependencies": { "is-callable": "^1.2.7", "is-date-object": "^1.0.5", @@ -5432,6 +5624,7 @@ "version": "3.2.0", "resolved": "https://registry.npmjs.org/escalade/-/escalade-3.2.0.tgz", "integrity": "sha512-WUj2qlxaQtO4g6Pq5c29GTcWGDyd8itL8zTlipgECz3JesAiiOKotd8JU6otB3PACgG6xkJUyVhboMS+bje/jA==", + "license": "MIT", "engines": { "node": ">=6" } @@ -5441,6 +5634,7 @@ "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-4.0.0.tgz", "integrity": "sha512-TtpcNJ3XAzx3Gq8sWRzJaVajRs0uVxA2YAkdb1jm2YkPz4G6egUFAyA3n5vtEIZefPk5Wa4UXbKuS5fKkJWdgA==", "dev": true, + "license": "MIT", "engines": { "node": ">=10" }, @@ -5449,25 +5643,25 @@ } }, "node_modules/eslint": { - "version": "9.34.0", - "resolved": "https://registry.npmjs.org/eslint/-/eslint-9.34.0.tgz", - "integrity": "sha512-RNCHRX5EwdrESy3Jc9o8ie8Bog+PeYvvSR8sDGoZxNFTvZ4dlxUB3WzQ3bQMztFrSRODGrLLj8g6OFuGY/aiQg==", + "version": "9.39.2", + "resolved": "https://registry.npmjs.org/eslint/-/eslint-9.39.2.tgz", + "integrity": "sha512-LEyamqS7W5HB3ujJyvi0HQK/dtVINZvd5mAAp9eT5S/ujByGjiZLCzPcHVzuXbpJDJF/cxwHlfceVUDZ2lnSTw==", "dev": true, + "license": "MIT", "peer": true, "dependencies": { - "@eslint-community/eslint-utils": "^4.2.0", + "@eslint-community/eslint-utils": "^4.8.0", "@eslint-community/regexpp": "^4.12.1", - "@eslint/config-array": "^0.21.0", - "@eslint/config-helpers": "^0.3.1", - "@eslint/core": "^0.15.2", + "@eslint/config-array": "^0.21.1", + "@eslint/config-helpers": "^0.4.2", + "@eslint/core": "^0.17.0", "@eslint/eslintrc": "^3.3.1", - "@eslint/js": "9.34.0", - "@eslint/plugin-kit": "^0.3.5", + "@eslint/js": "9.39.2", + "@eslint/plugin-kit": "^0.4.1", "@humanfs/node": "^0.16.6", "@humanwhocodes/module-importer": "^1.0.1", "@humanwhocodes/retry": "^0.4.2", "@types/estree": "^1.0.6", - "@types/json-schema": "^7.0.15", "ajv": "^6.12.4", "chalk": "^4.0.0", "cross-spawn": "^7.0.6", @@ -5514,6 +5708,7 @@ "resolved": "https://registry.npmjs.org/eslint-config-next/-/eslint-config-next-15.3.1.tgz", "integrity": "sha512-GnmyVd9TE/Ihe3RrvcafFhXErErtr2jS0JDeCSp3vWvy86AXwHsRBt0E3MqP/m8ACS1ivcsi5uaqjbhsG18qKw==", "dev": true, + "license": "MIT", "dependencies": { "@next/eslint-plugin-next": "15.3.1", "@rushstack/eslint-patch": "^1.10.3", @@ -5541,6 +5736,7 @@ "resolved": "https://registry.npmjs.org/eslint-import-resolver-node/-/eslint-import-resolver-node-0.3.9.tgz", "integrity": "sha512-WFj2isz22JahUv+B788TlO3N6zL3nNJGU8CcZbPZvVEkBPaJdCV4vy5wyghty5ROFbCRnm132v8BScu5/1BQ8g==", "dev": true, + "license": "MIT", "dependencies": { "debug": "^3.2.7", "is-core-module": "^2.13.0", @@ -5552,6 +5748,7 @@ "resolved": "https://registry.npmjs.org/debug/-/debug-3.2.7.tgz", "integrity": "sha512-CFjzYYAi4ThfiQvizrFQevTTXHtnCqWfe7x1AhgEscTz6ZbLbfoLRLPugTQyBth6f8ZERVUSyWHFD/7Wu4t1XQ==", "dev": true, + "license": "MIT", "dependencies": { "ms": "^2.1.1" } @@ -5561,6 +5758,7 @@ "resolved": "https://registry.npmjs.org/eslint-import-resolver-typescript/-/eslint-import-resolver-typescript-3.10.1.tgz", "integrity": "sha512-A1rHYb06zjMGAxdLSkN2fXPBwuSaQ0iO5M/hdyS0Ajj1VBaRp0sPD3dn1FhME3c/JluGFbwSxyCfqdSbtQLAHQ==", "dev": true, + "license": "ISC", "dependencies": { "@nolyfill/is-core-module": "1.0.39", "debug": "^4.4.0", @@ -5595,6 +5793,7 @@ "resolved": "https://registry.npmjs.org/eslint-module-utils/-/eslint-module-utils-2.12.1.tgz", "integrity": "sha512-L8jSWTze7K2mTg0vos/RuLRS5soomksDPoJLXIslC7c8Wmut3bx7CPpJijDcBZtxQ5lrbUdM+s0OlNbz0DCDNw==", "dev": true, + "license": "MIT", "dependencies": { "debug": "^3.2.7" }, @@ -5612,6 +5811,7 @@ "resolved": "https://registry.npmjs.org/debug/-/debug-3.2.7.tgz", "integrity": "sha512-CFjzYYAi4ThfiQvizrFQevTTXHtnCqWfe7x1AhgEscTz6ZbLbfoLRLPugTQyBth6f8ZERVUSyWHFD/7Wu4t1XQ==", "dev": true, + "license": "MIT", "dependencies": { "ms": "^2.1.1" } @@ -5621,7 +5821,7 @@ "resolved": "https://registry.npmjs.org/eslint-plugin-import/-/eslint-plugin-import-2.32.0.tgz", "integrity": "sha512-whOE1HFo/qJDyX4SnXzP4N6zOWn79WhnCUY/iDR0mPfQZO8wcYE4JClzI2oZrhBnnMUCBCHZhO6VQyoBU95mZA==", "dev": true, - "peer": true, + "license": "MIT", "dependencies": { "@rtsao/scc": "^1.1.0", "array-includes": "^3.1.9", @@ -5655,6 +5855,7 @@ "resolved": "https://registry.npmjs.org/debug/-/debug-3.2.7.tgz", "integrity": "sha512-CFjzYYAi4ThfiQvizrFQevTTXHtnCqWfe7x1AhgEscTz6ZbLbfoLRLPugTQyBth6f8ZERVUSyWHFD/7Wu4t1XQ==", "dev": true, + "license": "MIT", "dependencies": { "ms": "^2.1.1" } @@ -5664,6 +5865,7 @@ "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.1.tgz", "integrity": "sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA==", "dev": true, + "license": "ISC", "bin": { "semver": "bin/semver.js" } @@ -5673,6 +5875,7 @@ "resolved": "https://registry.npmjs.org/eslint-plugin-jsx-a11y/-/eslint-plugin-jsx-a11y-6.10.2.tgz", "integrity": "sha512-scB3nz4WmG75pV8+3eRUQOHZlNSUhFNq37xnpgRkCCELU3XMvXAxLk1eqWWyE22Ki4Q01Fnsw9BA3cJHDPgn2Q==", "dev": true, + "license": "MIT", "dependencies": { "aria-query": "^5.3.2", "array-includes": "^3.1.8", @@ -5702,6 +5905,7 @@ "resolved": "https://registry.npmjs.org/eslint-plugin-react/-/eslint-plugin-react-7.37.5.tgz", "integrity": "sha512-Qteup0SqU15kdocexFNAJMvCJEfa2xUKNV4CC1xsVMrIIqEy3SQ/rqyxCWNzfrd3/ldy6HMlD2e0JDVpDg2qIA==", "dev": true, + "license": "MIT", "dependencies": { "array-includes": "^3.1.8", "array.prototype.findlast": "^1.2.5", @@ -5734,6 +5938,7 @@ "resolved": "https://registry.npmjs.org/eslint-plugin-react-hooks/-/eslint-plugin-react-hooks-5.2.0.tgz", "integrity": "sha512-+f15FfK64YQwZdJNELETdn5ibXEUQmW1DZL6KXhNnc2heoy/sg9VJJeT7n8TlMWouzWqSWavFkIhHyIbIAEapg==", "dev": true, + "license": "MIT", "engines": { "node": ">=10" }, @@ -5746,6 +5951,7 @@ "resolved": "https://registry.npmjs.org/resolve/-/resolve-2.0.0-next.5.tgz", "integrity": "sha512-U7WjGVG9sH8tvjW5SmGbQuui75FiyjAX72HX15DwBBwF9dNiQZRQAg9nnPhYy+TUnE0+VcrttuvNI8oSxZcocA==", "dev": true, + "license": "MIT", "dependencies": { "is-core-module": "^2.13.0", "path-parse": "^1.0.7", @@ -5763,6 +5969,7 @@ "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.1.tgz", "integrity": "sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA==", "dev": true, + "license": "ISC", "bin": { "semver": "bin/semver.js" } @@ -5772,6 +5979,7 @@ "resolved": "https://registry.npmjs.org/eslint-scope/-/eslint-scope-8.4.0.tgz", "integrity": "sha512-sNXOfKCn74rt8RICKMvJS7XKV/Xk9kA7DyJr8mJik3S7Cwgy3qlkkmyS2uQB3jiJg6VNdZd/pDBJu0nvG2NlTg==", "dev": true, + "license": "BSD-2-Clause", "dependencies": { "esrecurse": "^4.3.0", "estraverse": "^5.2.0" @@ -5788,6 +5996,7 @@ "resolved": "https://registry.npmjs.org/eslint-visitor-keys/-/eslint-visitor-keys-4.2.1.tgz", "integrity": "sha512-Uhdk5sfqcee/9H/rCOJikYz67o0a2Tw2hGRPOG2Y1R2dg7brRe1uG0yaNQDHu+TO/uQPF/5eCapvYSmHUjt7JQ==", "dev": true, + "license": "Apache-2.0", "engines": { "node": "^18.18.0 || ^20.9.0 || >=21.1.0" }, @@ -5800,6 +6009,7 @@ "resolved": "https://registry.npmjs.org/espree/-/espree-10.4.0.tgz", "integrity": "sha512-j6PAQ2uUr79PZhBjP5C5fhl8e39FmRnOjsD5lGnWrFU8i2G776tBK7+nP8KuQUTTyAZUwfQqXAgrVH5MbH9CYQ==", "dev": true, + "license": "BSD-2-Clause", "dependencies": { "acorn": "^8.15.0", "acorn-jsx": "^5.3.2", @@ -5813,10 +6023,11 @@ } }, "node_modules/esquery": { - "version": "1.6.0", - "resolved": "https://registry.npmjs.org/esquery/-/esquery-1.6.0.tgz", - "integrity": "sha512-ca9pw9fomFcKPvFLXhBKUK90ZvGibiGOvRJNbjljY7s7uq/5YO4BOzcYtJqExdx99rF6aAcnRxHmcUHcz6sQsg==", + "version": "1.7.0", + "resolved": "https://registry.npmjs.org/esquery/-/esquery-1.7.0.tgz", + "integrity": "sha512-Ap6G0WQwcU/LHsvLwON1fAQX9Zp0A2Y6Y/cJBl9r/JbW90Zyg4/zbG6zzKa2OTALELarYHmKu0GhpM5EO+7T0g==", "dev": true, + "license": "BSD-3-Clause", "dependencies": { "estraverse": "^5.1.0" }, @@ -5829,6 +6040,7 @@ "resolved": "https://registry.npmjs.org/esrecurse/-/esrecurse-4.3.0.tgz", "integrity": "sha512-KmfKL3b6G+RXvP8N1vr3Tq1kL/oCFgn2NYXEtqP8/L3pKapUA4G8cFVaoF3SU323CD4XypR/ffioHmkti6/Tag==", "dev": true, + "license": "BSD-2-Clause", "dependencies": { "estraverse": "^5.2.0" }, @@ -5841,6 +6053,7 @@ "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-5.3.0.tgz", "integrity": "sha512-MMdARuVEQziNTeJD8DgMqmhwR11BRQ/cBP+pLtYdSTnf3MIO8fFeiINEbX36ZdNlfU/7A9f3gUw49B3oQsvwBA==", "dev": true, + "license": "BSD-2-Clause", "engines": { "node": ">=4.0" } @@ -5860,6 +6073,7 @@ "resolved": "https://registry.npmjs.org/esutils/-/esutils-2.0.3.tgz", "integrity": "sha512-kVscqXk4OCp68SZ0dkgEKVi6/8ij300KBWTJq32P/dYeWTSwK41WyTxalN1eRmA5Z9UU/LX9D7FWSmV9SAYx6g==", "dev": true, + "license": "BSD-2-Clause", "engines": { "node": ">=0.10.0" } @@ -5883,13 +6097,15 @@ "version": "3.1.3", "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-3.1.3.tgz", "integrity": "sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q==", - "dev": true + "dev": true, + "license": "MIT" }, "node_modules/fast-glob": { "version": "3.3.1", "resolved": "https://registry.npmjs.org/fast-glob/-/fast-glob-3.3.1.tgz", "integrity": "sha512-kNFPyjhh5cKjrUltxs+wFx+ZkbRaxxmZ+X0ZU31SOsxCEtP9VPgtq2teZw1DebupL5GmDaNQ6yKMMVcM41iqDg==", "dev": true, + "license": "MIT", "dependencies": { "@nodelib/fs.stat": "^2.0.2", "@nodelib/fs.walk": "^1.2.3", @@ -5906,6 +6122,7 @@ "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-5.1.2.tgz", "integrity": "sha512-AOIgSQCepiJYwP3ARnGx+5VnTu2HBYdzbGP45eLw1vr3zB3vZLeyed1sC9hnbcOc9/SrMyM5RPQrkGz4aS9Zow==", "dev": true, + "license": "ISC", "dependencies": { "is-glob": "^4.0.1" }, @@ -5917,19 +6134,22 @@ "version": "2.1.0", "resolved": "https://registry.npmjs.org/fast-json-stable-stringify/-/fast-json-stable-stringify-2.1.0.tgz", "integrity": "sha512-lhd/wF+Lk98HZoTCtlVraHtfh5XYijIjalXck7saUtuanSDyLMxnHhSXEDJqHxD7msR8D0uCmqlkwjCV8xvwHw==", - "dev": true + "dev": true, + "license": "MIT" }, "node_modules/fast-levenshtein": { "version": "2.0.6", "resolved": "https://registry.npmjs.org/fast-levenshtein/-/fast-levenshtein-2.0.6.tgz", "integrity": "sha512-DCXu6Ifhqcks7TZKY3Hxp3y6qphY5SJZmrWMDrKcERSOXWQdMhU9Ig/PYrzyw/ul9jOIyh0N4M0tbC5hodg8dw==", - "dev": true + "dev": true, + "license": "MIT" }, "node_modules/fastq": { - "version": "1.19.1", - "resolved": "https://registry.npmjs.org/fastq/-/fastq-1.19.1.tgz", - "integrity": "sha512-GwLTyxkCXjXbxqIhTsMI2Nui8huMPtnxg7krajPJAjnEG/iiOS7i+zCtWGZR9G0NBKbXKh6X9m9UIsYX/N6vvQ==", + "version": "1.20.1", + "resolved": "https://registry.npmjs.org/fastq/-/fastq-1.20.1.tgz", + "integrity": "sha512-GGToxJ/w1x32s/D2EKND7kTil4n8OVk/9mycTc4VDza13lOvpUZTGX3mFSCtV9ksdGBVzvsyAVLM6mHFThxXxw==", "dev": true, + "license": "ISC", "dependencies": { "reusify": "^1.0.4" } @@ -5990,6 +6210,7 @@ "resolved": "https://registry.npmjs.org/file-entry-cache/-/file-entry-cache-8.0.0.tgz", "integrity": "sha512-XXTUwCvisa5oacNGRP9SfNtYBNAMi+RPwBFmblZEF7N7swHYQS6/Zfk7SRwx4D5j3CH211YNRco1DEMNVfZCnQ==", "dev": true, + "license": "MIT", "dependencies": { "flat-cache": "^4.0.0" }, @@ -6002,6 +6223,7 @@ "resolved": "https://registry.npmjs.org/fill-range/-/fill-range-7.1.1.tgz", "integrity": "sha512-YsGpe3WHLK8ZYi4tWDg2Jy3ebRz2rXowDxnld4bkQB00cc/1Zw9AWnC0i9ztDJitivtQvaI9KaLyKrc+hBW0yg==", "dev": true, + "license": "MIT", "dependencies": { "to-regex-range": "^5.0.1" }, @@ -6014,6 +6236,7 @@ "resolved": "https://registry.npmjs.org/find-up/-/find-up-5.0.0.tgz", "integrity": "sha512-78/PXT1wlLLDgTzDs7sjq9hzz0vXD+zn+7wypEe4fXQxCmdmqfGsEPQxmiCSQI3ajFV91bVSsvNtrJRiW6nGng==", "dev": true, + "license": "MIT", "dependencies": { "locate-path": "^6.0.0", "path-exists": "^4.0.0" @@ -6030,6 +6253,7 @@ "resolved": "https://registry.npmjs.org/flat-cache/-/flat-cache-4.0.1.tgz", "integrity": "sha512-f7ccFPK3SXFHpx15UIGyRJ/FJQctuKZ0zVuN3frBo4HnK3cay9VEW0R6yPYFHC0AgqhukPzKjq22t5DmAyqGyw==", "dev": true, + "license": "MIT", "dependencies": { "flatted": "^3.2.9", "keyv": "^4.5.4" @@ -6042,7 +6266,8 @@ "version": "3.3.3", "resolved": "https://registry.npmjs.org/flatted/-/flatted-3.3.3.tgz", "integrity": "sha512-GX+ysw4PBCz0PzosHDepZGANEuFCMLrnRTiEy9McGjmkCQYwRq4A/X786G/fjM/+OjsWSU1ZrY5qyARZmO/uwg==", - "dev": true + "dev": true, + "license": "ISC" }, "node_modules/follow-redirects": { "version": "1.15.11", @@ -6069,6 +6294,7 @@ "resolved": "https://registry.npmjs.org/for-each/-/for-each-0.3.5.tgz", "integrity": "sha512-dKx12eRCVIzqCxFGplyFKJMPvLEWgmNtUrpTiJIR5u97zEhRG8ySrtboPHZXx7daLxQVrl643cTzbab2tkQjxg==", "dev": true, + "license": "MIT", "dependencies": { "is-callable": "^1.2.7" }, @@ -6099,7 +6325,17 @@ "version": "4.0.5", "resolved": "https://registry.npmjs.org/form-data/-/form-data-4.0.5.tgz", "integrity": "sha512-8RipRLol37bNs2bhoV67fiTEvdTrbMUYcFTiy3+wuuOnUog2QBHCZWXDRijWQfAkhBj2Uf5UnVaiWwA5vdd82w==", - "license": "MIT" + "license": "MIT", + "dependencies": { + "asynckit": "^0.4.0", + "combined-stream": "^1.0.8", + "es-set-tostringtag": "^2.1.0", + "hasown": "^2.0.2", + "mime-types": "^2.1.12" + }, + "engines": { + "node": ">= 6" + } }, "node_modules/formatly": { "version": "0.3.0", @@ -6130,27 +6366,27 @@ } }, "node_modules/fraction.js": { - "version": "4.3.7", - "resolved": "https://registry.npmjs.org/fraction.js/-/fraction.js-4.3.7.tgz", - "integrity": "sha512-ZsDfxO51wGAXREY55a7la9LScWpwv9RxIrYABrlvOFBlH/ShPnrtsXeuUIfXKKOVicNxQ+o8JTbJvjS4M89yew==", + "version": "5.3.4", + "resolved": "https://registry.npmjs.org/fraction.js/-/fraction.js-5.3.4.tgz", + "integrity": "sha512-1X1NTtiJphryn/uLQz3whtY6jK3fTqoE3ohKs0tT+Ujr1W59oopxmoEh7Lu5p6vBaPbgoM0bzveAW4Qi5RyWDQ==", "dev": true, "license": "MIT", "engines": { "node": "*" }, "funding": { - "type": "patreon", + "type": "github", "url": "https://github.com/sponsors/rawify" } }, "node_modules/framer-motion": { - "version": "12.27.5", - "resolved": "https://registry.npmjs.org/framer-motion/-/framer-motion-12.27.5.tgz", - "integrity": "sha512-yUFof7Y2Y2qDJxLKeA91qMazuA6QBOoLOZ0No2J5VIQuhJLWMmGwT/5qyCfpa9mNNS3C7lOR6NhlC3mLZjLw4g==", + "version": "12.29.2", + "resolved": "https://registry.npmjs.org/framer-motion/-/framer-motion-12.29.2.tgz", + "integrity": "sha512-lSNRzBJk4wuIy0emYQ/nfZ7eWhqud2umPKw2QAQki6uKhZPKm2hRQHeQoHTG9MIvfobb+A/LbEWPJU794ZUKrg==", "license": "MIT", "dependencies": { - "motion-dom": "^12.27.5", - "motion-utils": "^12.27.2", + "motion-dom": "^12.29.2", + "motion-utils": "^12.29.2", "tslib": "^2.4.0" }, "peerDependencies": { @@ -6189,7 +6425,6 @@ "version": "1.1.2", "resolved": "https://registry.npmjs.org/function-bind/-/function-bind-1.1.2.tgz", "integrity": "sha512-7XHNxH7qX9xG5mIwxkhumTox/MIRNcOgDrxWsMt2pAr23WHp6MrRlN7FBSFpCpr+oVO0F744iUgR82nJMfG2SA==", - "dev": true, "license": "MIT", "funding": { "url": "https://github.com/sponsors/ljharb" @@ -6278,7 +6513,6 @@ "version": "1.3.0", "resolved": "https://registry.npmjs.org/get-intrinsic/-/get-intrinsic-1.3.0.tgz", "integrity": "sha512-9fSjSaos/fRIVIp+xSJlE6lfwhES7LNtKaCBIamHsjr2na1BiABJPo0mOjjz8GJDURarmCPGqaiVg5mfjb98CQ==", - "dev": true, "license": "MIT", "dependencies": { "call-bind-apply-helpers": "^1.0.2", @@ -6312,7 +6546,6 @@ "version": "1.0.1", "resolved": "https://registry.npmjs.org/get-proto/-/get-proto-1.0.1.tgz", "integrity": "sha512-sTSfBjoXBp89JvIKIefqw7U2CCebsc74kiY6awiGogKtoSGbgjYE/G/+l9sF3MWFPNc9IcoOC4ODfKHfxFmp0g==", - "dev": true, "license": "MIT", "dependencies": { "dunder-proto": "^1.0.1", @@ -6341,9 +6574,9 @@ } }, "node_modules/get-tsconfig": { - "version": "4.13.0", - "resolved": "https://registry.npmjs.org/get-tsconfig/-/get-tsconfig-4.13.0.tgz", - "integrity": "sha512-1VKTZJCwBrvbd+Wn3AOgQP/2Av+TfTCOlE4AcRJE72W1ksZXbAx8PPBR9RzgTeSPzlPMHrbANMH3LbltH73wxQ==", + "version": "4.13.1", + "resolved": "https://registry.npmjs.org/get-tsconfig/-/get-tsconfig-4.13.1.tgz", + "integrity": "sha512-EoY1N2xCn44xU6750Sx7OjOIT59FkmstNc3X6y5xpz7D5cBtZRe/3pSlTkDJgqsOk3WwZPkWfonhhUJfttQo3w==", "dev": true, "license": "MIT", "dependencies": { @@ -6493,7 +6726,6 @@ "version": "1.2.0", "resolved": "https://registry.npmjs.org/gopd/-/gopd-1.2.0.tgz", "integrity": "sha512-ZUKRh6/kUFoAiTAtTYPZJ3hw9wNxx+BIBOijnlG9PnrJsCcSjs1wyyD6vJpaYtgnzDrKYRSqf3OO6Rfa93xsRg==", - "dev": true, "license": "MIT", "engines": { "node": ">= 0.4" @@ -6502,13 +6734,6 @@ "url": "https://github.com/sponsors/ljharb" } }, - "node_modules/graphemer": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/graphemer/-/graphemer-1.4.0.tgz", - "integrity": "sha512-EtKwoO6kxCL9WO5xipiHTZlSzBm7WLT627TqC/uVRd0HKmq8NXyebnNYxDoBi7wt8eTWrUrKXCOVaFq9x1kgag==", - "dev": true, - "license": "MIT" - }, "node_modules/gtoken": { "version": "8.0.0", "resolved": "https://registry.npmjs.org/gtoken/-/gtoken-8.0.0.tgz", @@ -6539,7 +6764,6 @@ "version": "4.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", - "dev": true, "license": "MIT", "engines": { "node": ">=8" @@ -6578,7 +6802,6 @@ "version": "1.1.0", "resolved": "https://registry.npmjs.org/has-symbols/-/has-symbols-1.1.0.tgz", "integrity": "sha512-1cDNdwJ2Jaohmb3sg4OmKaMBwuC48sYni5HUw2DvsC8LjGTLK9h+eb1X6RyuOHe4hT0ULCW68iomhjUoKUqlPQ==", - "dev": true, "license": "MIT", "engines": { "node": ">= 0.4" @@ -6591,7 +6814,6 @@ "version": "1.0.2", "resolved": "https://registry.npmjs.org/has-tostringtag/-/has-tostringtag-1.0.2.tgz", "integrity": "sha512-NqADB8VjPFLM2V0VvHUewwwsw0ZWBaIdgo+ieHtK3hasLz4qeCRjYcqfB6AQrBggRKppKF8L52/VqdVsO47Dlw==", - "dev": true, "license": "MIT", "dependencies": { "has-symbols": "^1.0.3" @@ -6607,7 +6829,6 @@ "version": "2.0.2", "resolved": "https://registry.npmjs.org/hasown/-/hasown-2.0.2.tgz", "integrity": "sha512-0hJU9SCPvmMzIBdZFqNPXWa6dqh7WdH0cII9y+CyS8rG3nL48Bclra9HmKhVVUHyPWNH5Y7xDwAB7bfgSjkUMQ==", - "dev": true, "license": "MIT", "dependencies": { "function-bind": "^1.1.2" @@ -6670,13 +6891,13 @@ } }, "node_modules/html-dom-parser": { - "version": "5.1.2", - "resolved": "https://registry.npmjs.org/html-dom-parser/-/html-dom-parser-5.1.2.tgz", - "integrity": "sha512-9nD3Rj3/FuQt83AgIa1Y3ruzspwFFA54AJbQnohXN+K6fL1/bhcDQJJY5Ne4L4A163ADQFVESd/0TLyNoV0mfg==", + "version": "5.1.4", + "resolved": "https://registry.npmjs.org/html-dom-parser/-/html-dom-parser-5.1.4.tgz", + "integrity": "sha512-UGjp7y8jSrDU2RdN2J9FDOo3X+WBu+LkS/I3TjjFW020ocZWjPvave+RKk1zeuY2sUWy5fh6zHgXHthzDGlFNQ==", "license": "MIT", "dependencies": { "domhandler": "5.0.3", - "htmlparser2": "10.0.0" + "htmlparser2": "10.1.0" } }, "node_modules/html-encoding-sniffer": { @@ -6692,13 +6913,13 @@ } }, "node_modules/html-react-parser": { - "version": "5.2.11", - "resolved": "https://registry.npmjs.org/html-react-parser/-/html-react-parser-5.2.11.tgz", - "integrity": "sha512-WnSQVn/D1UTj64nSz5y8MriL+MrbsZH80Ytr1oqKqs8DGZnphWY1R1pl3t7TY3rpqTSu+FHA21P80lrsmrdNBA==", + "version": "5.2.14", + "resolved": "https://registry.npmjs.org/html-react-parser/-/html-react-parser-5.2.14.tgz", + "integrity": "sha512-yiSZHuJq6LwQc450IhpLApug8bKTpHv5oVsClpVS1jEDepifXYcJu0Sw0r7pqEl89q/ZpO0nth6LEDWtz5n6qg==", "license": "MIT", "dependencies": { "domhandler": "5.0.3", - "html-dom-parser": "5.1.2", + "html-dom-parser": "5.1.4", "react-property": "2.0.2", "style-to-js": "1.1.21" }, @@ -6723,9 +6944,9 @@ } }, "node_modules/htmlparser2": { - "version": "10.0.0", - "resolved": "https://registry.npmjs.org/htmlparser2/-/htmlparser2-10.0.0.tgz", - "integrity": "sha512-TwAZM+zE5Tq3lrEHvOlvwgj1XLWQCtaaibSN11Q+gGBAS7Y1uZSWwXXRe4iF6OXnaq1riyQAPFOBtYc77Mxq0g==", + "version": "10.1.0", + "resolved": "https://registry.npmjs.org/htmlparser2/-/htmlparser2-10.1.0.tgz", + "integrity": "sha512-VTZkM9GWRAtEpveh7MSF6SjjrpNVNNVJfFup7xTY3UpFtm67foy9HDVXneLtFVt4pMz5kZtgNcvCniNFb1hlEQ==", "funding": [ "https://github.com/fb55/htmlparser2?sponsor=1", { @@ -6737,8 +6958,20 @@ "dependencies": { "domelementtype": "^2.3.0", "domhandler": "^5.0.3", - "domutils": "^3.2.1", - "entities": "^6.0.0" + "domutils": "^3.2.2", + "entities": "^7.0.1" + } + }, + "node_modules/htmlparser2/node_modules/entities": { + "version": "7.0.1", + "resolved": "https://registry.npmjs.org/entities/-/entities-7.0.1.tgz", + "integrity": "sha512-TWrgLOFUQTH994YUyl1yT4uyavY5nNB5muff+RtWaqNVCAK408b5ZnnbNAUEWLTCpum9w6arT70i1XdQ4UeOPA==", + "license": "BSD-2-Clause", + "engines": { + "node": ">=0.12" + }, + "funding": { + "url": "https://github.com/fb55/entities?sponsor=1" } }, "node_modules/http-proxy-agent": { @@ -6767,6 +7000,15 @@ "node": ">= 14" } }, + "node_modules/iceberg-js": { + "version": "0.8.1", + "resolved": "https://registry.npmjs.org/iceberg-js/-/iceberg-js-0.8.1.tgz", + "integrity": "sha512-1dhVQZXhcHje7798IVM+xoo/1ZdVfzOMIc8/rgVSijRK38EDqOJoGula9N/8ZI5RD8QTxNQtK/Gozpr+qUqRRA==", + "license": "MIT", + "engines": { + "node": ">=20.0.0" + } + }, "node_modules/iconv-lite": { "version": "0.6.3", "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.6.3.tgz", @@ -7357,9 +7599,10 @@ } }, "node_modules/isarray": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", - "integrity": "sha512-VLghIWNM6ELQzo7zwmcg0NmTVyWKYjvIeM83yjp0wRDTmUnrM678fQbcKBo6n2CJEF0szoG//ytg+TKla89ALQ==", + "version": "2.0.5", + "resolved": "https://registry.npmjs.org/isarray/-/isarray-2.0.5.tgz", + "integrity": "sha512-xHjhDr3cNBK0BzdUJSPXZntQUx/mwMS5Rw4A7lPJ90XGAO6ISP/ePDNuo0vhqOZU+UD5JoodwCAAoZQd3FeAKw==", + "dev": true, "license": "MIT" }, "node_modules/isexe": { @@ -7465,10 +7708,22 @@ "peerDependencies": { "canvas": "^3.0.0" }, - "peerDependenciesMeta": { - "canvas": { - "optional": true - } + "peerDependenciesMeta": { + "canvas": { + "optional": true + } + } + }, + "node_modules/jsdom/node_modules/entities": { + "version": "6.0.1", + "resolved": "https://registry.npmjs.org/entities/-/entities-6.0.1.tgz", + "integrity": "sha512-aN97NXWF6AWBTahfVOIrB/NShkzi5H7F9r1s9mD3cDj4Ko5f2qhhVoYMibXF7GlLveb/D2ioWay8lxI97Ven3g==", + "license": "BSD-2-Clause", + "engines": { + "node": ">=0.12" + }, + "funding": { + "url": "https://github.com/fb55/entities?sponsor=1" } }, "node_modules/jsdom/node_modules/parse5": { @@ -7483,31 +7738,6 @@ "url": "https://github.com/inikulin/parse5?sponsor=1" } }, - "node_modules/jsdom/node_modules/tr46": { - "version": "6.0.0", - "resolved": "https://registry.npmjs.org/tr46/-/tr46-6.0.0.tgz", - "integrity": "sha512-bLVMLPtstlZ4iMQHpFHTR7GAGj2jxi8Dg0s2h2MafAE4uSWF98FC/3MomU51iQAMf8/qDUbKWf5GxuvvVcXEhw==", - "license": "MIT", - "dependencies": { - "punycode": "^2.3.1" - }, - "engines": { - "node": ">=20" - } - }, - "node_modules/jsdom/node_modules/whatwg-url": { - "version": "15.1.0", - "resolved": "https://registry.npmjs.org/whatwg-url/-/whatwg-url-15.1.0.tgz", - "integrity": "sha512-2ytDk0kiEj/yu90JOAp44PVPUkO9+jVhyf+SybKlRHSDlvOOZhdPIrr7xTH64l4WixO2cP+wQIcgujkGBPPz6g==", - "license": "MIT", - "dependencies": { - "tr46": "^6.0.0", - "webidl-conversions": "^8.0.0" - }, - "engines": { - "node": ">=20" - } - }, "node_modules/json-bigint": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/json-bigint/-/json-bigint-1.0.0.tgz", @@ -7579,6 +7809,42 @@ "setimmediate": "^1.0.5" } }, + "node_modules/jszip/node_modules/isarray": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", + "integrity": "sha512-VLghIWNM6ELQzo7zwmcg0NmTVyWKYjvIeM83yjp0wRDTmUnrM678fQbcKBo6n2CJEF0szoG//ytg+TKla89ALQ==", + "license": "MIT" + }, + "node_modules/jszip/node_modules/readable-stream": { + "version": "2.3.8", + "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.8.tgz", + "integrity": "sha512-8p0AUk4XODgIewSi0l8Epjs+EVnWiK7NoDIEGU0HhE7+ZyY8D1IMY7odu5lRrFXGg71L15KG8QrPmum45RTtdA==", + "license": "MIT", + "dependencies": { + "core-util-is": "~1.0.0", + "inherits": "~2.0.3", + "isarray": "~1.0.0", + "process-nextick-args": "~2.0.0", + "safe-buffer": "~5.1.1", + "string_decoder": "~1.1.1", + "util-deprecate": "~1.0.1" + } + }, + "node_modules/jszip/node_modules/safe-buffer": { + "version": "5.1.2", + "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz", + "integrity": "sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==", + "license": "MIT" + }, + "node_modules/jszip/node_modules/string_decoder": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.1.1.tgz", + "integrity": "sha512-n/ShnvDi6FHbbVfviro+WojiFzv+s8MPMHBczVePfUpDJLwoLT0ht1l4YwBCbi8pJAveEEdnkHyPyTP/mzRfwg==", + "license": "MIT", + "dependencies": { + "safe-buffer": "~5.1.0" + } + }, "node_modules/jwa": { "version": "2.0.1", "resolved": "https://registry.npmjs.org/jwa/-/jwa-2.0.1.tgz", @@ -7696,9 +7962,9 @@ } }, "node_modules/knip/node_modules/zod": { - "version": "4.3.5", - "resolved": "https://registry.npmjs.org/zod/-/zod-4.3.5.tgz", - "integrity": "sha512-k7Nwx6vuWx1IJ9Bjuf4Zt1PEllcwe7cls3VNzm4CQ1/hgtFUK2bRNG3rvnpPUhFjmqJKAKtjV576KnUkHocg/g==", + "version": "4.3.6", + "resolved": "https://registry.npmjs.org/zod/-/zod-4.3.6.tgz", + "integrity": "sha512-rftlrkhHZOcjDwkGlnUtZZkvaPHCsDATp4pGpuOOMDaTdDDXF91wuVDJoWoPsKX/3YPQ5fHuF3STjcYyKr+Qhg==", "dev": true, "license": "MIT", "funding": { @@ -7838,10 +8104,13 @@ } }, "node_modules/lru-cache": { - "version": "10.4.3", - "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-10.4.3.tgz", - "integrity": "sha512-JNAzZcXrCt42VGLuYz0zfAzDfAvJWW6AfYlDBQyDV5DClI2m5sAmK+OIO7s59XfsRsWHp02jAJrRadPRGTt6SQ==", - "license": "ISC" + "version": "11.2.5", + "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-11.2.5.tgz", + "integrity": "sha512-vFrFJkWtJvJnD5hg+hJvVE8Lh/TcMzKnTgCWmtBipwI5yLX/iX+5UB2tfuyODF5E7k9xEzMdYgGqaSb1c0c5Yw==", + "license": "BlueOak-1.0.0", + "engines": { + "node": "20 || >=22" + } }, "node_modules/lucide-react": { "version": "0.511.0", @@ -7899,7 +8168,6 @@ "version": "1.1.0", "resolved": "https://registry.npmjs.org/math-intrinsics/-/math-intrinsics-1.1.0.tgz", "integrity": "sha512-/IXtbwEk5HTPyEwyKX6hGkYXxM9nbj64B+ilVJnC/R6B0pH5G4V3b0pVbL7DBj4tkhBAppbQUlf6F6Xl9LHu1g==", - "dev": true, "license": "MIT", "engines": { "node": ">= 0.4" @@ -8793,11 +9061,31 @@ "url": "https://github.com/sponsors/jonschlinkert" } }, + "node_modules/mime-db": { + "version": "1.52.0", + "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.52.0.tgz", + "integrity": "sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg==", + "license": "MIT", + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/mime-types": { + "version": "2.1.35", + "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.35.tgz", + "integrity": "sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw==", + "license": "MIT", + "dependencies": { + "mime-db": "1.52.0" + }, + "engines": { + "node": ">= 0.6" + } + }, "node_modules/minimatch": { "version": "3.1.2", "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.1.2.tgz", "integrity": "sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw==", - "dev": true, "license": "ISC", "dependencies": { "brace-expansion": "^1.1.7" @@ -8826,18 +9114,18 @@ } }, "node_modules/motion-dom": { - "version": "12.27.5", - "resolved": "https://registry.npmjs.org/motion-dom/-/motion-dom-12.27.5.tgz", - "integrity": "sha512-UwBv2AUOkA7/TCHr67NGjg3aRT7nbsanmmenRoR7T6IJXZp34OZB+pooGnKjMd8CqqCsF/+qwT657EkukjgmiQ==", + "version": "12.29.2", + "resolved": "https://registry.npmjs.org/motion-dom/-/motion-dom-12.29.2.tgz", + "integrity": "sha512-/k+NuycVV8pykxyiTCoFzIVLA95Nb1BFIVvfSu9L50/6K6qNeAYtkxXILy/LRutt7AzaYDc2myj0wkCVVYAPPA==", "license": "MIT", "dependencies": { - "motion-utils": "^12.27.2" + "motion-utils": "^12.29.2" } }, "node_modules/motion-utils": { - "version": "12.27.2", - "resolved": "https://registry.npmjs.org/motion-utils/-/motion-utils-12.27.2.tgz", - "integrity": "sha512-B55gcoL85Mcdt2IEStY5EEAsrMSVE2sI14xQ/uAdPL+mfQxhKKFaEag9JmfxedJOR4vZpBGoPeC/Gm13I/4g5Q==", + "version": "12.29.2", + "resolved": "https://registry.npmjs.org/motion-utils/-/motion-utils-12.29.2.tgz", + "integrity": "sha512-G3kc34H2cX2gI63RqU+cZq+zWRRPSsNIOjpdl9TN4AQwC4sgwYPl/Q/Obf/d53nOm569T0fYK+tcoSV50BWx8A==", "license": "MIT" }, "node_modules/ms": { @@ -8900,12 +9188,12 @@ "license": "MIT" }, "node_modules/next": { - "version": "15.5.9", - "resolved": "https://registry.npmjs.org/next/-/next-15.5.9.tgz", - "integrity": "sha512-agNLK89seZEtC5zUHwtut0+tNrc0Xw4FT/Dg+B/VLEo9pAcS9rtTKpek3V6kVcVwsB2YlqMaHdfZL4eLEVYuCg==", + "version": "15.5.11", + "resolved": "https://registry.npmjs.org/next/-/next-15.5.11.tgz", + "integrity": "sha512-L2KPiKmqTDpRdeVDdPjhf43g2/VPe0NCNndq7OKDCgOLWtxe1kbr/zXGIZtYY7kZEAjRf7Bj/mwUFSr+tYC2Yg==", "license": "MIT", "dependencies": { - "@next/env": "15.5.9", + "@next/env": "15.5.11", "@swc/helpers": "0.5.15", "caniuse-lite": "^1.0.30001579", "postcss": "8.4.31", @@ -9044,20 +9332,10 @@ "node": ">=0.10.0" } }, - "node_modules/normalize-range": { - "version": "0.1.2", - "resolved": "https://registry.npmjs.org/normalize-range/-/normalize-range-0.1.2.tgz", - "integrity": "sha512-bdok/XvKII3nUpklnV6P2hxtMNrCboOjAcyBuQnWEhO665FwrSNRxU+AqpsyvO6LgGYPspN+lu5CLtw4jPRKNA==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=0.10.0" - } - }, "node_modules/npm": { - "version": "11.7.0", - "resolved": "https://registry.npmjs.org/npm/-/npm-11.7.0.tgz", - "integrity": "sha512-wiCZpv/41bIobCoJ31NStIWKfAxxYyD1iYnWCtiyns8s5v3+l8y0HCP/sScuH6B5+GhIfda4HQKiqeGZwJWhFw==", + "version": "11.8.0", + "resolved": "https://registry.npmjs.org/npm/-/npm-11.8.0.tgz", + "integrity": "sha512-n19sJeW+RGKdkHo8SCc5xhSwkKhQUFfZaFzSc+EsYXLjSqIV0tl72aDYQVuzVvfrbysGwdaQsNLNy58J10EBSQ==", "bundleDependencies": [ "@isaacs/string-locale-compare", "@npmcli/arborist", @@ -9136,8 +9414,8 @@ ], "dependencies": { "@isaacs/string-locale-compare": "^1.1.0", - "@npmcli/arborist": "^9.1.9", - "@npmcli/config": "^10.4.5", + "@npmcli/arborist": "^9.1.10", + "@npmcli/config": "^10.5.0", "@npmcli/fs": "^5.0.0", "@npmcli/map-workspaces": "^5.0.3", "@npmcli/metavuln-calculator": "^9.0.3", @@ -9145,7 +9423,7 @@ "@npmcli/promise-spawn": "^9.0.1", "@npmcli/redact": "^4.0.0", "@npmcli/run-script": "^10.0.3", - "@sigstore/tuf": "^4.0.0", + "@sigstore/tuf": "^4.0.1", "abbrev": "^4.0.0", "archy": "~1.0.0", "cacache": "^20.0.3", @@ -9162,11 +9440,11 @@ "is-cidr": "^6.0.1", "json-parse-even-better-errors": "^5.0.0", "libnpmaccess": "^10.0.3", - "libnpmdiff": "^8.0.12", - "libnpmexec": "^10.1.11", - "libnpmfund": "^7.0.12", + "libnpmdiff": "^8.0.13", + "libnpmexec": "^10.1.12", + "libnpmfund": "^7.0.13", "libnpmorg": "^8.0.1", - "libnpmpack": "^9.0.12", + "libnpmpack": "^9.0.13", "libnpmpublish": "^11.1.3", "libnpmsearch": "^9.0.1", "libnpmteam": "^8.0.2", @@ -9195,11 +9473,11 @@ "spdx-expression-parse": "^4.0.0", "ssri": "^13.0.0", "supports-color": "^10.2.2", - "tar": "^7.5.2", + "tar": "^7.5.4", "text-table": "~0.2.0", "tiny-relative-date": "^2.0.2", "treeverse": "^3.0.0", - "validate-npm-package-name": "^7.0.0", + "validate-npm-package-name": "^7.0.2", "which": "^6.0.0" }, "bin": { @@ -9261,7 +9539,7 @@ } }, "node_modules/npm/node_modules/@npmcli/arborist": { - "version": "9.1.9", + "version": "9.1.10", "inBundle": true, "license": "ISC", "dependencies": { @@ -9278,7 +9556,7 @@ "@npmcli/run-script": "^10.0.0", "bin-links": "^6.0.0", "cacache": "^20.0.1", - "common-ancestor-path": "^1.0.1", + "common-ancestor-path": "^2.0.0", "hosted-git-info": "^9.0.0", "json-stringify-nice": "^1.1.4", "lru-cache": "^11.2.1", @@ -9307,7 +9585,7 @@ } }, "node_modules/npm/node_modules/@npmcli/config": { - "version": "10.4.5", + "version": "10.5.0", "inBundle": true, "license": "ISC", "dependencies": { @@ -9488,7 +9766,7 @@ } }, "node_modules/npm/node_modules/@sigstore/core": { - "version": "3.0.0", + "version": "3.1.0", "inBundle": true, "license": "Apache-2.0", "engines": { @@ -9504,48 +9782,40 @@ } }, "node_modules/npm/node_modules/@sigstore/sign": { - "version": "4.0.1", + "version": "4.1.0", "inBundle": true, "license": "Apache-2.0", "dependencies": { "@sigstore/bundle": "^4.0.0", - "@sigstore/core": "^3.0.0", + "@sigstore/core": "^3.1.0", "@sigstore/protobuf-specs": "^0.5.0", - "make-fetch-happen": "^15.0.2", - "proc-log": "^5.0.0", + "make-fetch-happen": "^15.0.3", + "proc-log": "^6.1.0", "promise-retry": "^2.0.1" }, "engines": { "node": "^20.17.0 || >=22.9.0" } }, - "node_modules/npm/node_modules/@sigstore/sign/node_modules/proc-log": { - "version": "5.0.0", - "inBundle": true, - "license": "ISC", - "engines": { - "node": "^18.17.0 || >=20.5.0" - } - }, "node_modules/npm/node_modules/@sigstore/tuf": { - "version": "4.0.0", + "version": "4.0.1", "inBundle": true, "license": "Apache-2.0", "dependencies": { "@sigstore/protobuf-specs": "^0.5.0", - "tuf-js": "^4.0.0" + "tuf-js": "^4.1.0" }, "engines": { "node": "^20.17.0 || >=22.9.0" } }, "node_modules/npm/node_modules/@sigstore/verify": { - "version": "3.0.0", + "version": "3.1.0", "inBundle": true, "license": "Apache-2.0", "dependencies": { "@sigstore/bundle": "^4.0.0", - "@sigstore/core": "^3.0.0", + "@sigstore/core": "^3.1.0", "@sigstore/protobuf-specs": "^0.5.0" }, "engines": { @@ -9561,31 +9831,17 @@ } }, "node_modules/npm/node_modules/@tufjs/models": { - "version": "4.0.0", + "version": "4.1.0", "inBundle": true, "license": "MIT", "dependencies": { "@tufjs/canonical-json": "2.0.0", - "minimatch": "^9.0.5" + "minimatch": "^10.1.1" }, "engines": { "node": "^20.17.0 || >=22.9.0" } }, - "node_modules/npm/node_modules/@tufjs/models/node_modules/minimatch": { - "version": "9.0.5", - "inBundle": true, - "license": "ISC", - "dependencies": { - "brace-expansion": "^2.0.1" - }, - "engines": { - "node": ">=16 || 14 >=14.17" - }, - "funding": { - "url": "https://github.com/sponsors/isaacs" - } - }, "node_modules/npm/node_modules/abbrev": { "version": "4.0.0", "inBundle": true, @@ -9620,11 +9876,6 @@ "inBundle": true, "license": "MIT" }, - "node_modules/npm/node_modules/balanced-match": { - "version": "1.0.2", - "inBundle": true, - "license": "MIT" - }, "node_modules/npm/node_modules/bin-links": { "version": "6.0.0", "inBundle": true, @@ -9651,14 +9902,6 @@ "url": "https://github.com/sponsors/sindresorhus" } }, - "node_modules/npm/node_modules/brace-expansion": { - "version": "2.0.2", - "inBundle": true, - "license": "MIT", - "dependencies": { - "balanced-match": "^1.0.0" - } - }, "node_modules/npm/node_modules/cacache": { "version": "20.0.3", "inBundle": true, @@ -9745,9 +9988,12 @@ } }, "node_modules/npm/node_modules/common-ancestor-path": { - "version": "1.0.1", + "version": "2.0.0", "inBundle": true, - "license": "ISC" + "license": "BlueOak-1.0.0", + "engines": { + "node": ">= 18" + } }, "node_modules/npm/node_modules/cssesc": { "version": "3.0.0", @@ -9777,7 +10023,7 @@ } }, "node_modules/npm/node_modules/diff": { - "version": "8.0.2", + "version": "8.0.3", "inBundle": true, "license": "BSD-3-Clause", "engines": { @@ -9953,7 +10199,7 @@ } }, "node_modules/npm/node_modules/ip-address": { - "version": "10.0.1", + "version": "10.1.0", "inBundle": true, "license": "MIT", "engines": { @@ -10045,11 +10291,11 @@ } }, "node_modules/npm/node_modules/libnpmdiff": { - "version": "8.0.12", + "version": "8.0.13", "inBundle": true, "license": "ISC", "dependencies": { - "@npmcli/arborist": "^9.1.9", + "@npmcli/arborist": "^9.1.10", "@npmcli/installed-package-contents": "^4.0.0", "binary-extensions": "^3.0.0", "diff": "^8.0.2", @@ -10063,11 +10309,11 @@ } }, "node_modules/npm/node_modules/libnpmexec": { - "version": "10.1.11", + "version": "10.1.12", "inBundle": true, "license": "ISC", "dependencies": { - "@npmcli/arborist": "^9.1.9", + "@npmcli/arborist": "^9.1.10", "@npmcli/package-json": "^7.0.0", "@npmcli/run-script": "^10.0.0", "ci-info": "^4.0.0", @@ -10085,11 +10331,11 @@ } }, "node_modules/npm/node_modules/libnpmfund": { - "version": "7.0.12", + "version": "7.0.13", "inBundle": true, "license": "ISC", "dependencies": { - "@npmcli/arborist": "^9.1.9" + "@npmcli/arborist": "^9.1.10" }, "engines": { "node": "^20.17.0 || >=22.9.0" @@ -10108,11 +10354,11 @@ } }, "node_modules/npm/node_modules/libnpmpack": { - "version": "9.0.12", + "version": "9.0.13", "inBundle": true, "license": "ISC", "dependencies": { - "@npmcli/arborist": "^9.1.9", + "@npmcli/arborist": "^9.1.10", "@npmcli/run-script": "^10.0.0", "npm-package-arg": "^13.0.0", "pacote": "^21.0.2" @@ -10178,9 +10424,9 @@ } }, "node_modules/npm/node_modules/lru-cache": { - "version": "11.2.2", + "version": "11.2.4", "inBundle": true, - "license": "ISC", + "license": "BlueOak-1.0.0", "engines": { "node": "20 || >=22" } @@ -10561,7 +10807,7 @@ } }, "node_modules/npm/node_modules/path-scurry": { - "version": "2.0.0", + "version": "2.0.1", "inBundle": true, "license": "BlueOak-1.0.0", "dependencies": { @@ -10576,7 +10822,7 @@ } }, "node_modules/npm/node_modules/postcss-selector-parser": { - "version": "7.1.0", + "version": "7.1.1", "inBundle": true, "license": "MIT", "dependencies": { @@ -10705,16 +10951,16 @@ } }, "node_modules/npm/node_modules/sigstore": { - "version": "4.0.0", + "version": "4.1.0", "inBundle": true, "license": "Apache-2.0", "dependencies": { "@sigstore/bundle": "^4.0.0", - "@sigstore/core": "^3.0.0", + "@sigstore/core": "^3.1.0", "@sigstore/protobuf-specs": "^0.5.0", - "@sigstore/sign": "^4.0.0", - "@sigstore/tuf": "^4.0.0", - "@sigstore/verify": "^3.0.0" + "@sigstore/sign": "^4.1.0", + "@sigstore/tuf": "^4.0.1", + "@sigstore/verify": "^3.1.0" }, "engines": { "node": "^20.17.0 || >=22.9.0" @@ -10839,7 +11085,7 @@ } }, "node_modules/npm/node_modules/tar": { - "version": "7.5.2", + "version": "7.5.4", "inBundle": true, "license": "BlueOak-1.0.0", "dependencies": { @@ -10923,13 +11169,13 @@ } }, "node_modules/npm/node_modules/tuf-js": { - "version": "4.0.0", + "version": "4.1.0", "inBundle": true, "license": "MIT", "dependencies": { - "@tufjs/models": "4.0.0", - "debug": "^4.4.1", - "make-fetch-happen": "^15.0.0" + "@tufjs/models": "4.1.0", + "debug": "^4.4.3", + "make-fetch-happen": "^15.0.1" }, "engines": { "node": "^20.17.0 || >=22.9.0" @@ -10981,7 +11227,7 @@ } }, "node_modules/npm/node_modules/validate-npm-package-name": { - "version": "7.0.0", + "version": "7.0.2", "inBundle": true, "license": "ISC", "engines": { @@ -11181,9 +11427,9 @@ } }, "node_modules/openai": { - "version": "6.16.0", - "resolved": "https://registry.npmjs.org/openai/-/openai-6.16.0.tgz", - "integrity": "sha512-fZ1uBqjFUjXzbGc35fFtYKEOxd20kd9fDpFeqWtsOZWiubY8CZ1NAlXHW3iathaFvqmNtCWMIsosCuyeI7Joxg==", + "version": "6.17.0", + "resolved": "https://registry.npmjs.org/openai/-/openai-6.17.0.tgz", + "integrity": "sha512-NHRpPEUPzAvFOAFs9+9pC6+HCw/iWsYsKCMPXH5Kw7BpMxqd8g/A07/1o7Gx2TWtCnzevVRyKMRFqyiHyAlqcA==", "license": "Apache-2.0", "bin": { "openai": "bin/cli" @@ -11244,35 +11490,35 @@ } }, "node_modules/oxc-resolver": { - "version": "11.16.3", - "resolved": "https://registry.npmjs.org/oxc-resolver/-/oxc-resolver-11.16.3.tgz", - "integrity": "sha512-goLOJH3x69VouGWGp5CgCIHyksmOZzXr36lsRmQz1APg3SPFORrvV2q7nsUHMzLVa6ZJgNwkgUSJFsbCpAWkCA==", + "version": "11.17.0", + "resolved": "https://registry.npmjs.org/oxc-resolver/-/oxc-resolver-11.17.0.tgz", + "integrity": "sha512-R5P2Tw6th+nQJdNcZGfuppBS/sM0x1EukqYffmlfX2xXLgLGCCPwu4ruEr9Sx29mrpkHgITc130Qps2JR90NdQ==", "dev": true, "license": "MIT", "funding": { "url": "https://github.com/sponsors/Boshen" }, "optionalDependencies": { - "@oxc-resolver/binding-android-arm-eabi": "11.16.3", - "@oxc-resolver/binding-android-arm64": "11.16.3", - "@oxc-resolver/binding-darwin-arm64": "11.16.3", - "@oxc-resolver/binding-darwin-x64": "11.16.3", - "@oxc-resolver/binding-freebsd-x64": "11.16.3", - "@oxc-resolver/binding-linux-arm-gnueabihf": "11.16.3", - "@oxc-resolver/binding-linux-arm-musleabihf": "11.16.3", - "@oxc-resolver/binding-linux-arm64-gnu": "11.16.3", - "@oxc-resolver/binding-linux-arm64-musl": "11.16.3", - "@oxc-resolver/binding-linux-ppc64-gnu": "11.16.3", - "@oxc-resolver/binding-linux-riscv64-gnu": "11.16.3", - "@oxc-resolver/binding-linux-riscv64-musl": "11.16.3", - "@oxc-resolver/binding-linux-s390x-gnu": "11.16.3", - "@oxc-resolver/binding-linux-x64-gnu": "11.16.3", - "@oxc-resolver/binding-linux-x64-musl": "11.16.3", - "@oxc-resolver/binding-openharmony-arm64": "11.16.3", - "@oxc-resolver/binding-wasm32-wasi": "11.16.3", - "@oxc-resolver/binding-win32-arm64-msvc": "11.16.3", - "@oxc-resolver/binding-win32-ia32-msvc": "11.16.3", - "@oxc-resolver/binding-win32-x64-msvc": "11.16.3" + "@oxc-resolver/binding-android-arm-eabi": "11.17.0", + "@oxc-resolver/binding-android-arm64": "11.17.0", + "@oxc-resolver/binding-darwin-arm64": "11.17.0", + "@oxc-resolver/binding-darwin-x64": "11.17.0", + "@oxc-resolver/binding-freebsd-x64": "11.17.0", + "@oxc-resolver/binding-linux-arm-gnueabihf": "11.17.0", + "@oxc-resolver/binding-linux-arm-musleabihf": "11.17.0", + "@oxc-resolver/binding-linux-arm64-gnu": "11.17.0", + "@oxc-resolver/binding-linux-arm64-musl": "11.17.0", + "@oxc-resolver/binding-linux-ppc64-gnu": "11.17.0", + "@oxc-resolver/binding-linux-riscv64-gnu": "11.17.0", + "@oxc-resolver/binding-linux-riscv64-musl": "11.17.0", + "@oxc-resolver/binding-linux-s390x-gnu": "11.17.0", + "@oxc-resolver/binding-linux-x64-gnu": "11.17.0", + "@oxc-resolver/binding-linux-x64-musl": "11.17.0", + "@oxc-resolver/binding-openharmony-arm64": "11.17.0", + "@oxc-resolver/binding-wasm32-wasi": "11.17.0", + "@oxc-resolver/binding-win32-arm64-msvc": "11.17.0", + "@oxc-resolver/binding-win32-ia32-msvc": "11.17.0", + "@oxc-resolver/binding-win32-x64-msvc": "11.17.0" } }, "node_modules/p-limit": { @@ -11422,6 +11668,18 @@ "url": "https://github.com/inikulin/parse5?sponsor=1" } }, + "node_modules/parse5/node_modules/entities": { + "version": "6.0.1", + "resolved": "https://registry.npmjs.org/entities/-/entities-6.0.1.tgz", + "integrity": "sha512-aN97NXWF6AWBTahfVOIrB/NShkzi5H7F9r1s9mD3cDj4Ko5f2qhhVoYMibXF7GlLveb/D2ioWay8lxI97Ven3g==", + "license": "BSD-2-Clause", + "engines": { + "node": ">=0.12" + }, + "funding": { + "url": "https://github.com/fb55/entities?sponsor=1" + } + }, "node_modules/path-exists": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-4.0.0.tgz", @@ -11473,6 +11731,12 @@ "url": "https://github.com/sponsors/isaacs" } }, + "node_modules/path-scurry/node_modules/lru-cache": { + "version": "10.4.3", + "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-10.4.3.tgz", + "integrity": "sha512-JNAzZcXrCt42VGLuYz0zfAzDfAvJWW6AfYlDBQyDV5DClI2m5sAmK+OIO7s59XfsRsWHp02jAJrRadPRGTt6SQ==", + "license": "ISC" + }, "node_modules/picocolors": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/picocolors/-/picocolors-1.1.1.tgz", @@ -11797,9 +12061,9 @@ "license": "MIT" }, "node_modules/react": { - "version": "19.2.3", - "resolved": "https://registry.npmjs.org/react/-/react-19.2.3.tgz", - "integrity": "sha512-Ku/hhYbVjOQnXDZFv2+RibmLFGwFdeeKHFcOTlrt7xplBnya5OGn/hIRDsqDiSUcfORsDC7MPxwork8jBwsIWA==", + "version": "19.2.4", + "resolved": "https://registry.npmjs.org/react/-/react-19.2.4.tgz", + "integrity": "sha512-9nfp2hYpCwOjAN+8TZFGhtWEwgvWHXqESH8qT89AT/lWklpLON22Lc8pEtnpsZz7VmawabSU0gCjnj8aC0euHQ==", "license": "MIT", "peer": true, "engines": { @@ -11807,16 +12071,16 @@ } }, "node_modules/react-dom": { - "version": "19.2.3", - "resolved": "https://registry.npmjs.org/react-dom/-/react-dom-19.2.3.tgz", - "integrity": "sha512-yELu4WmLPw5Mr/lmeEpox5rw3RETacE++JgHqQzd2dg+YbJuat3jH4ingc+WPZhxaoFzdv9y33G+F7Nl5O0GBg==", + "version": "19.2.4", + "resolved": "https://registry.npmjs.org/react-dom/-/react-dom-19.2.4.tgz", + "integrity": "sha512-AXJdLo8kgMbimY95O2aKQqsz2iWi9jMgKJhRBAxECE4IFxfcazB2LmzloIoibJI3C12IlY20+KFaLv+71bUJeQ==", "license": "MIT", "peer": true, "dependencies": { "scheduler": "^0.27.0" }, "peerDependencies": { - "react": "^19.2.3" + "react": "^19.2.4" } }, "node_modules/react-icons": { @@ -11965,26 +12229,19 @@ } }, "node_modules/readable-stream": { - "version": "2.3.8", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.8.tgz", - "integrity": "sha512-8p0AUk4XODgIewSi0l8Epjs+EVnWiK7NoDIEGU0HhE7+ZyY8D1IMY7odu5lRrFXGg71L15KG8QrPmum45RTtdA==", + "version": "3.6.2", + "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-3.6.2.tgz", + "integrity": "sha512-9u/sniCrY3D5WdsERHzHE4G2YCXqoG5FTHUiCC4SIbr6XcLZBY05ya9EKjYek9O5xOAwjGq+1JdGBAS7Q9ScoA==", "license": "MIT", "dependencies": { - "core-util-is": "~1.0.0", - "inherits": "~2.0.3", - "isarray": "~1.0.0", - "process-nextick-args": "~2.0.0", - "safe-buffer": "~5.1.1", - "string_decoder": "~1.1.1", - "util-deprecate": "~1.0.1" + "inherits": "^2.0.3", + "string_decoder": "^1.1.1", + "util-deprecate": "^1.0.1" + }, + "engines": { + "node": ">= 6" } }, - "node_modules/readable-stream/node_modules/safe-buffer": { - "version": "5.1.2", - "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz", - "integrity": "sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==", - "license": "MIT" - }, "node_modules/readdirp": { "version": "3.6.0", "resolved": "https://registry.npmjs.org/readdirp/-/readdirp-3.6.0.tgz", @@ -12290,13 +12547,6 @@ "url": "https://github.com/sponsors/ljharb" } }, - "node_modules/safe-array-concat/node_modules/isarray": { - "version": "2.0.5", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-2.0.5.tgz", - "integrity": "sha512-xHjhDr3cNBK0BzdUJSPXZntQUx/mwMS5Rw4A7lPJ90XGAO6ISP/ePDNuo0vhqOZU+UD5JoodwCAAoZQd3FeAKw==", - "dev": true, - "license": "MIT" - }, "node_modules/safe-buffer": { "version": "5.2.1", "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.2.1.tgz", @@ -12334,13 +12584,6 @@ "url": "https://github.com/sponsors/ljharb" } }, - "node_modules/safe-push-apply/node_modules/isarray": { - "version": "2.0.5", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-2.0.5.tgz", - "integrity": "sha512-xHjhDr3cNBK0BzdUJSPXZntQUx/mwMS5Rw4A7lPJ90XGAO6ISP/ePDNuo0vhqOZU+UD5JoodwCAAoZQd3FeAKw==", - "dev": true, - "license": "MIT" - }, "node_modules/safe-regex-test": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/safe-regex-test/-/safe-regex-test-1.1.0.tgz", @@ -12688,20 +12931,14 @@ "license": "MIT" }, "node_modules/string_decoder": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.1.1.tgz", - "integrity": "sha512-n/ShnvDi6FHbbVfviro+WojiFzv+s8MPMHBczVePfUpDJLwoLT0ht1l4YwBCbi8pJAveEEdnkHyPyTP/mzRfwg==", + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.3.0.tgz", + "integrity": "sha512-hkRX8U1WjJFd8LsDJ2yQ/wWWxaopEsABU1XfkM8A+j0+85JAGppt16cr1Whg6KIbb4okU6Mql6BOj+uup/wKeA==", "license": "MIT", "dependencies": { - "safe-buffer": "~5.1.0" + "safe-buffer": "~5.2.0" } }, - "node_modules/string_decoder/node_modules/safe-buffer": { - "version": "5.1.2", - "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz", - "integrity": "sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==", - "license": "MIT" - }, "node_modules/string-width": { "version": "5.1.2", "resolved": "https://registry.npmjs.org/string-width/-/string-width-5.1.2.tgz", @@ -13022,7 +13259,6 @@ "version": "7.2.0", "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", - "dev": true, "license": "MIT", "dependencies": { "has-flag": "^4.0.0" @@ -13299,10 +13535,16 @@ } }, "node_modules/tr46": { - "version": "0.0.3", - "resolved": "https://registry.npmjs.org/tr46/-/tr46-0.0.3.tgz", - "integrity": "sha512-N3WMsuqV66lT30CrXNbEjx4GEwlow3v6rr4mCcv6prnfwhS01rkgyFdjPNBYd9br7LpXV1+Emh01fHnq2Gdgrw==", - "license": "MIT" + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/tr46/-/tr46-6.0.0.tgz", + "integrity": "sha512-bLVMLPtstlZ4iMQHpFHTR7GAGj2jxi8Dg0s2h2MafAE4uSWF98FC/3MomU51iQAMf8/qDUbKWf5GxuvvVcXEhw==", + "license": "MIT", + "dependencies": { + "punycode": "^2.3.1" + }, + "engines": { + "node": ">=20" + } }, "node_modules/trim-lines": { "version": "3.0.1", @@ -13525,9 +13767,9 @@ "license": "MIT" }, "node_modules/undici": { - "version": "7.18.2", - "resolved": "https://registry.npmjs.org/undici/-/undici-7.18.2.tgz", - "integrity": "sha512-y+8YjDFzWdQlSE9N5nzKMT3g4a5UBX1HKowfdXh0uvAnTaqqwqB92Jt4UXBAeKekDs5IaDKyJFR4X1gYVCgXcw==", + "version": "7.19.2", + "resolved": "https://registry.npmjs.org/undici/-/undici-7.19.2.tgz", + "integrity": "sha512-4VQSpGEGsWzk0VYxyB/wVX/Q7qf9t5znLRgs0dzszr9w9Fej/8RVNQ+S20vdXSAyra/bJ7ZQfGv6ZMj7UEbzSg==", "license": "MIT", "engines": { "node": ">=20.18.1" @@ -13598,9 +13840,9 @@ } }, "node_modules/unist-util-visit": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/unist-util-visit/-/unist-util-visit-5.0.0.tgz", - "integrity": "sha512-MR04uvD+07cwl/yhVuVWAtw+3GOR/knlL55Nd/wAdblk27GCVt3lqpTivy/tkJcZoNPzTwS1Y+KMojlLDhoTzg==", + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/unist-util-visit/-/unist-util-visit-5.1.0.tgz", + "integrity": "sha512-m+vIdyeCOpdr/QeQCu2EzxX/ohgS8KbnPDgFni4dQsfSCtpz8UqDyY5GjRru8PDKuYn7Fq19j1CQ+nJSsGKOzg==", "license": "MIT", "dependencies": { "@types/unist": "^3.0.0", @@ -13896,21 +14138,18 @@ } }, "node_modules/whatwg-url": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/whatwg-url/-/whatwg-url-5.0.0.tgz", - "integrity": "sha512-saE57nupxk6v3HY35+jzBwYa0rKSy0XR8JSxZPwgLr7ys0IBzhGviA1/TUGJLmSVqs8pb9AnvICXEuOHLprYTw==", + "version": "15.1.0", + "resolved": "https://registry.npmjs.org/whatwg-url/-/whatwg-url-15.1.0.tgz", + "integrity": "sha512-2ytDk0kiEj/yu90JOAp44PVPUkO9+jVhyf+SybKlRHSDlvOOZhdPIrr7xTH64l4WixO2cP+wQIcgujkGBPPz6g==", "license": "MIT", "dependencies": { - "tr46": "~0.0.3", - "webidl-conversions": "^3.0.0" + "tr46": "^6.0.0", + "webidl-conversions": "^8.0.0" + }, + "engines": { + "node": ">=20" } }, - "node_modules/whatwg-url/node_modules/webidl-conversions": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/webidl-conversions/-/webidl-conversions-3.0.1.tgz", - "integrity": "sha512-2JAn3z8AR6rjK8Sm8orRC0h/bcl/DqL7tRPdGZ4I1CjdF+EaMLmYxBHyXuKL849eucPFhvBoxMsflfOb8kxaeQ==", - "license": "BSD-2-Clause" - }, "node_modules/which": { "version": "2.0.2", "resolved": "https://registry.npmjs.org/which/-/which-2.0.2.tgz", @@ -13974,13 +14213,6 @@ "url": "https://github.com/sponsors/ljharb" } }, - "node_modules/which-builtin-type/node_modules/isarray": { - "version": "2.0.5", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-2.0.5.tgz", - "integrity": "sha512-xHjhDr3cNBK0BzdUJSPXZntQUx/mwMS5Rw4A7lPJ90XGAO6ISP/ePDNuo0vhqOZU+UD5JoodwCAAoZQd3FeAKw==", - "dev": true, - "license": "MIT" - }, "node_modules/which-collection": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/which-collection/-/which-collection-1.0.2.tgz", diff --git a/package.json b/package.json index 64821752..0f46a145 100644 --- a/package.json +++ b/package.json @@ -9,13 +9,17 @@ "kb:upload:umsu": "tsx scripts/kb/upload-umsu-vector-store.ts", "kb:upload": "tsx scripts/kb/upload-kb-vs.ts", "chunk:sync": "tsx scripts/kb/sync-kb-vector-store-chunks.ts", - "rechunk": "tsx scripts/kb/rechunk-from-pages.ts" + "rechunk": "tsx scripts/kb/rechunk-from-pages.ts", + "build:vs-files": "tsx scripts/kb/build-vs-files-from-pages.ts", + "sync:central-vs-files": "tsx scripts/kb/sync-central-vector-store-vs-files.ts", + "kb:validate": "tsx scripts/kb/validate-central-kb-search.ts", + "wipe:umsu": "tsx scripts/kb/wipe-umsu-from-central.ts" }, "dependencies": { "@dnd-kit/core": "^6.3.1", "@dnd-kit/sortable": "^10.0.0", - "@mozilla/readability": "^0.6.0", "@google-cloud/secret-manager": "^6.1.1", + "@mozilla/readability": "^0.6.0", "@radix-ui/react-checkbox": "^1.3.1", "@radix-ui/react-dialog": "^1.1.15", "@radix-ui/react-dropdown-menu": "^2.1.14", @@ -33,12 +37,12 @@ "cmdk": "^1.1.1", "fast-average-color": "^9.5.0", "framer-motion": "^12.23.12", - "html-react-parser": "^5.2.11", + "html-react-parser": "^5.2.14", "install": "^0.13.0", "jsdom": "^27.3.0", "lucide-react": "^0.511.0", "mammoth": "^1.10.0", - "next": "15.5.9", + "next": "^15.5.11", "next-themes": "^0.4.6", "npm": "^11.5.2", "openai": "^6.16.0", diff --git a/scripts/kb/build-vs-files-from-pages.ts b/scripts/kb/build-vs-files-from-pages.ts new file mode 100644 index 00000000..48feda31 --- /dev/null +++ b/scripts/kb/build-vs-files-from-pages.ts @@ -0,0 +1,654 @@ +// scripts/kb/build-vs-files-from-pages.ts +// +// Build VECTOR-STORE INGESTION files from already-scraped PAGE-LEVEL markdown files. +// - Normal pages -> 1 file per page (section_key="__full__"). +// - Large pages -> split into H2 (then H3 if needed) section files and/or parts. +// +// Usage: +// tsx scripts/kb/build-vs-files-from-pages.ts [chunkMaxTokens] [largeChunkThreshold] [sectionMaxTokens] [sectionOverlapTokens] [year] +// +// Example: +// tsx scripts/kb/build-vs-files-from-pages.ts msa scripts/kb_scrapes/msa scripts/kb_scrapes/msa/vs_files 380 40 1600 0 2026 +// +// Notes: +// - Expects each page .md to have YAML frontmatter with at least canonical_url or url. +// - Skips anything under an existing "/chunks" or "/vs_files" directory by default. +// - Token counting is approximate (chars/4). +// +// Output: +// - Writes .md ingestion files to outVsDir +// - Writes manifest.json to outVsDir with per-file attributes + +import fs from "node:fs"; +import path from "node:path"; +import { globSync } from "glob"; + +import { sha1, canonicalizeUrl, normalizeTextForHash } from "./hash"; + +/* -------------------------- args -------------------------- */ + +function usageAndExit(): never { + console.error( + "Usage: tsx scripts/kb/build-vs-files-from-pages.ts [chunkMaxTokens] [largeChunkThreshold] [sectionMaxTokens] [sectionOverlapTokens] [year]\n" + + "Example: tsx scripts/kb/build-vs-files-from-pages.ts msa scripts/kb_scrapes/msa scripts/kb_scrapes/msa/vs_files 380 40 1600 0 2026" + ); + process.exit(1); +} + +const [ + , + , + kbSlug, + pagesDirArg, + outVsDirArg, + chunkMaxTokensArg, + largeChunkThresholdArg, + sectionMaxTokensArg, + sectionOverlapTokensArg, + yearArg, +] = process.argv; + +if (!kbSlug || !pagesDirArg || !outVsDirArg) usageAndExit(); + +const CHUNK_MAX_TOKENS = Number(chunkMaxTokensArg ?? "380"); // matches your chunker default +const LARGE_CHUNK_THRESHOLD = Number(largeChunkThresholdArg ?? "40"); // pages w/ > this chunks are "large" +const SECTION_MAX_TOKENS = Number(sectionMaxTokensArg ?? "1600"); // per section file / part cap +const SECTION_OVERLAP_TOKENS = Number(sectionOverlapTokensArg ?? "0"); // overlap between section parts +const YEAR = Number(yearArg ?? "2026"); + +const pagesDir = path.resolve(process.cwd(), pagesDirArg); +const outVsDir = path.resolve(process.cwd(), outVsDirArg); + +if (!fs.existsSync(pagesDir)) throw new Error(`pagesDir not found: ${pagesDir}`); +fs.mkdirSync(outVsDir, { recursive: true }); + +/* ---------------------- frontmatter ----------------------- */ + +function readFrontmatter(md: string): { fm: Record; body: string } { + const out: Record = {}; + const m = md.match(/^---\s*\n([\s\S]*?)\n---\s*\n/); + if (!m) return { fm: out, body: md }; + for (const line of m[1].split("\n")) { + const t = line.trim(); + if (!t || t.startsWith("#")) continue; + const idx = t.indexOf(":"); + if (idx === -1) continue; + const k = t.slice(0, idx).trim(); + const v = t.slice(idx + 1).trim(); + if (k) out[k] = v; + } + const body = md.slice(m[0].length); + return { fm: out, body }; +} + +function must(fm: Record, keys: string[], filePath: string): string { + for (const k of keys) { + const v = fm[k]; + if (v) return v; + } + throw new Error(`Missing required frontmatter (${keys.join(" or ")}) in ${filePath}`); +} + +function safeTrim(s: string) { + return (s ?? "").toString().trim(); +} + +function inferTitleFromFrontmatter(fm: Record, fallbackUrl: string) { + return safeTrim(fm["title"] || fm["page_title"] || fm["name"] || fallbackUrl); +} + +function inferSectionFromFrontmatter(fm: Record) { + return safeTrim(fm["section"] || fm["category"] || fm["site_section"] || "unknown"); +} + +function inferSiteFromFrontmatter(fm: Record) { + return safeTrim(fm["site"] || fm["source_site"] || fm["kb_site"] || kbSlug); +} + +/* --------------------- token estimate --------------------- */ + +function estTokens(text: string): number { + const t = text.trim(); + if (!t) return 0; + return Math.ceil(t.length / 4); +} + +/* --------------------- markdown splitting --------------------- */ + +type Section = { + headingPath: string[]; // e.g. ["Uniride | Bike Shop", "Workshop", "Basic Service"] + chunkTitle: string; // last heading + content: string; // markdown under that heading (includes heading line) +}; + +function splitByHeadings(md: string): Section[] { + const lines = md.replace(/\r\n/g, "\n").split("\n"); + + const sections: Section[] = []; + let headingPath: string[] = []; + let buf: string[] = []; + + const flush = () => { + const content = buf.join("\n").trim(); + if (content) { + const chunkTitle = headingPath.length ? headingPath[headingPath.length - 1] : ""; + sections.push({ headingPath: [...headingPath], chunkTitle, content }); + } + buf = []; + }; + + for (const line of lines) { + const m = line.match(/^(#{1,6})\s+(.*)$/); + if (m) { + flush(); + const level = m[1].length; + const title = safeTrim(m[2].replace(/\s+#*\s*$/, "")); + headingPath = headingPath.slice(0, Math.max(0, level - 1)); + headingPath.push(title || "(untitled)"); + buf.push(line); + continue; + } + buf.push(line); + } + + flush(); + + if (sections.length === 0) { + const content = md.trim(); + if (content) sections.push({ headingPath: [], chunkTitle: "", content }); + } + + return sections; +} + +function splitIntoBlocks(md: string): string[] { + const normalized = md.replace(/\r\n/g, "\n"); + const blocks = normalized + .split(/\n{2,}/) + .map((b) => b.trim()) + .filter(Boolean); + + return blocks.length ? blocks : [normalized.trim()]; +} + +function joinHeadingPath(pathParts: string[]): string { + return pathParts.map((p) => p.replace(/\s+/g, " ").trim()).filter(Boolean).join(" > "); +} + +/* --------------------- ids / hashes --------------------- */ + +function makeDocId(canonicalUrl: string) { + return sha1(canonicalUrl); +} + +function makeContentHash(content: string) { + return sha1(normalizeTextForHash(content)); +} + +/* --------------------- helpers --------------------- */ + +function slugify(s: string): string { + const t = safeTrim(s) + .toLowerCase() + .replace(/&/g, " and ") + .replace(/[^a-z0-9]+/g, "-") + .replace(/^-+|-+$/g, ""); + return t || "untitled"; +} + +function clampAttribute(s: string, maxLen: number): string { + const t = safeTrim(s); + if (t.length <= maxLen) return t; + const prefix = t.slice(0, Math.max(0, maxLen - 1 - 10)); + const h = sha1(t).slice(0, 8); + return `${prefix}|${h}`.slice(0, maxLen); +} + +function rmDirContents(dir: string) { + if (!fs.existsSync(dir)) return; + for (const f of fs.readdirSync(dir)) { + fs.rmSync(path.join(dir, f), { recursive: true, force: true }); + } +} + +function findPageMarkdownFiles(root: string) { + const all = globSync(path.join(root, "**/*.md"), { nodir: true }); + return all.filter((p) => { + const norm = p.split(path.sep).join("/"); + if (norm.includes("/chunks/")) return false; + if (norm.includes("/vs_files/")) return false; + return true; + }); +} + +function getDomain(url: string): string { + try { + const u = new URL(url); + return u.hostname.toLowerCase(); + } catch { + return ""; + } +} + +/* --------------------- uni/corpus mapping --------------------- */ + +// IMPORTANT: These are defaults. You'll likely want to expand/override. +const SU_SITE_CODES = new Set([ + "msa", // Monash Student Association + "rusu", // RMIT University Student Union + "umsu", // UoM Student Union + "uwa_guild", // UWA Student Guild + "umsu", + // add: "umsu", "rusu", "uwa_guild", etc. +]); + +function inferCorpus(site: string, canonicalUrl: string): "su" | "official" { + if (SU_SITE_CODES.has(site.toLowerCase())) return "su"; + const d = getDomain(canonicalUrl); + // heuristic: student union domains often differ; adjust as needed + if (d.includes("msa.monash.edu")) return "su"; + return "official"; +} + +function inferUni(site: string, canonicalUrl: string, kbSlugLocal: string): string { + const d = getDomain(canonicalUrl); + if (d.includes("monash")) return "monash"; + if (d.includes("unimelb")) return "unimelb"; + if (d.includes("rmit")) return "rmit"; + if (d.includes("uwa")) return "uwa"; + + // fallback: site/kbSlug hints + const s = site.toLowerCase(); + if (s === "msa") return "monash"; + const k = kbSlugLocal.toLowerCase(); + if (k.includes("monash")) return "monash"; + if (k.includes("unimelb")) return "unimelb"; + if (k.includes("rmit")) return "rmit"; + if (k.includes("uwa")) return "uwa"; + + return "unknown"; +} + +function inferKbSlugUnified(uni: string, corpus: "su" | "official"): string { + // If you already have your own kb slug convention, replace this. + return `${uni}_${corpus}`; +} + +/* --------------------- VS unit build --------------------- */ + +type VsAttributes = Record; + +type VsUnit = { + kb_slug: string; + doc_id: string; + canonical_url: string; + title: string; + section: string; + site: string; + + uni: string; + corpus: "su" | "official"; + year: number; + + section_key: string; // "__full__" or derived slug / slug__part_N + content_hash: string; + + content: string; +}; + +function buildVsBody(pageTitle: string, canonicalUrl: string, sectionLabel: string, body: string) { + // Keep a lightweight header for retrieval clarity. + return [ + `# ${pageTitle}`, + ``, + `Source: ${canonicalUrl}`, + sectionLabel ? `Section: ${sectionLabel}` : ``, + ``, + body.trim(), + ] + .filter(Boolean) + .join("\n"); +} + +function estimateChunkCountForPage(pageBody: string): number { + // Mirrors your chunk flushing logic at a high level (no overlap) + const sections = splitByHeadings(pageBody); + let count = 0; + + for (const sec of sections) { + const blocks = splitIntoBlocks(sec.content); + let accTokens = 0; + + for (const block of blocks) { + const bt = estTokens(block); + + if (bt > CHUNK_MAX_TOKENS) { + // hard-split big blocks into multiple chunk-equivalents + const slices = hardSplitByChars(block, CHUNK_MAX_TOKENS); + count += slices.length; + accTokens = 0; + continue; + } + + if (accTokens + bt > CHUNK_MAX_TOKENS) { + count += 1; + accTokens = 0; + } + + accTokens += bt; + } + + if (accTokens > 0) count += 1; + } + + return count; +} + +function hardSplitByChars(text: string, maxTokens: number): string[] { + const maxChars = maxTokens * 4; + const out: string[] = []; + let i = 0; + while (i < text.length) { + out.push(text.slice(i, i + maxChars).trim()); + i += maxChars; + } + return out.filter(Boolean); +} + +function takeLastTokensApprox(text: string, tokens: number) { + const maxChars = tokens * 4; + if (text.length <= maxChars) return text.trim(); + return text.slice(text.length - maxChars).trim(); +} + +function splitIntoPartsWithCap(md: string, maxTokens: number, overlapTokens: number): string[] { + const blocks = splitIntoBlocks(md); + const parts: string[] = []; + + let acc: string[] = []; + let accTokens = 0; + + const flush = () => { + const body = acc.join("\n\n").trim(); + if (!body) return; + parts.push(body); + + if (overlapTokens > 0) { + const joined = acc.join("\n\n"); + const overlap = takeLastTokensApprox(joined, overlapTokens); + acc = overlap ? [overlap] : []; + accTokens = estTokens(acc.join("\n\n")); + } else { + acc = []; + accTokens = 0; + } + }; + + for (const block of blocks) { + const bt = estTokens(block); + + if (bt > maxTokens) { + flush(); + // hard split huge block into slices + const slices = hardSplitByChars(block, maxTokens); + for (const s of slices) { + acc = [s]; + accTokens = estTokens(s); + flush(); + } + continue; + } + + if (accTokens + bt > maxTokens && acc.length > 0) { + flush(); + } + + acc.push(block); + accTokens += bt; + } + + flush(); + + return parts.length ? parts : [md.trim()]; +} + +function buildUnitsFromPage( + kbSlugLocal: string, + pageMeta: { canonical_url: string; title: string; section: string; site: string }, + pageBody: string +): { doc_id: string; chunkCountEstimate: number; units: VsUnit[] } { + const canonical_url = canonicalizeUrl(pageMeta.canonical_url); + const title = pageMeta.title; + const section = pageMeta.section; + const site = pageMeta.site; + + const doc_id = makeDocId(canonical_url); + + const corpus = inferCorpus(site, canonical_url); + const uni = inferUni(site, canonical_url, kbSlugLocal); + const kb_slug = inferKbSlugUnified(uni, corpus); + + const chunkCountEstimate = estimateChunkCountForPage(pageBody); + + // Normal: single unit + if (chunkCountEstimate <= LARGE_CHUNK_THRESHOLD) { + const body = buildVsBody(title, canonical_url, section, pageBody); + const content_hash = makeContentHash(body); + + const unit: VsUnit = { + kb_slug, + doc_id, + canonical_url, + title, + section, + site, + uni, + corpus, + year: YEAR, + section_key: "__full__", + content_hash, + content: body, + }; + return { doc_id, chunkCountEstimate, units: [unit] }; + } + + // Large: split into H2 sections (fallback to intro) + const sections = splitByHeadings(pageBody); + + // Group content by top-level section key. + // Convention: + // - H1 title is usually headingPath[0] + // - H2 is headingPath[1] + // If absent, group into "__intro__". + const groups = new Map(); + + for (const sec of sections) { + const h2 = sec.headingPath.length >= 2 ? sec.headingPath[1] : "__intro__"; + const key = slugify(h2); + const label = h2 === "__intro__" ? "__intro__" : h2; + + const g = groups.get(key) ?? { headingLabel: label, contents: [] }; + g.contents.push(sec.content); + groups.set(key, g); + } + + const units: VsUnit[] = []; + + for (const [key, g] of groups.entries()) { + const combined = g.contents.join("\n\n").trim(); + if (!combined) continue; + + // Cap each section into parts, if needed + const parts = splitIntoPartsWithCap(combined, SECTION_MAX_TOKENS, SECTION_OVERLAP_TOKENS); + + for (let i = 0; i < parts.length; i++) { + const partKey = parts.length === 1 ? key : `${key}__part_${i}`; + const body = buildVsBody(title, canonical_url, section, parts[i]); + const content_hash = makeContentHash(body); + + units.push({ + kb_slug, + doc_id, + canonical_url, + title, + section, + site, + uni, + corpus, + year: YEAR, + section_key: clampAttribute(partKey, 200), + content_hash, + content: body, + }); + } + } + + // If something went wrong and we produced none, fallback to full doc. + if (units.length === 0) { + const body = buildVsBody(title, canonical_url, section, pageBody); + const content_hash = makeContentHash(body); + units.push({ + kb_slug, + doc_id, + canonical_url, + title, + section, + site, + uni, + corpus, + year: YEAR, + section_key: "__full__", + content_hash, + content: body, + }); + } + + return { doc_id, chunkCountEstimate, units }; +} + +/* --------------------- output writing --------------------- */ + +function toVsFrontmatter(u: VsUnit): string { + const lines = [ + "---", + `kb_slug: ${u.kb_slug}`, + `doc_id: ${u.doc_id}`, + `canonical_url: ${u.canonical_url}`, + `title: ${clampAttribute(u.title, 200)}`, + `section: ${clampAttribute(u.section, 128)}`, + `site: ${clampAttribute(u.site, 64)}`, + `uni: ${u.uni}`, + `corpus: ${u.corpus}`, + `year: ${u.year}`, + `section_key: ${u.section_key}`, + `content_hash: ${u.content_hash}`, + "---", + "", + ]; + return lines.join("\n"); +} + +function writeVsFile(outDir: string, u: VsUnit): string { + const safeDoc = u.doc_id.replace(/[^a-zA-Z0-9_-]/g, "_"); + const safeKey = u.section_key.replace(/[^a-zA-Z0-9_-]/g, "_"); + const filename = `${u.kb_slug}__${safeDoc}__${safeKey}.md`; + const filePath = path.join(outDir, filename); + fs.writeFileSync(filePath, toVsFrontmatter(u) + u.content.trim() + "\n", "utf-8"); + return filePath; +} + +function buildAttributes(u: VsUnit): VsAttributes { + // These are the attributes you should attach onto the vector-store file. + // Keep values simple (string/number/bool). + return { + uni: u.uni, + corpus: u.corpus, + year: u.year, + kb_slug: u.kb_slug, + doc_id: u.doc_id, + site: u.site, + section_key: u.section_key, + canonical_url: u.canonical_url, // optional but useful for debugging + content_hash: u.content_hash, // useful for idempotency + }; +} + +/* -------------------------- main -------------------------- */ + +(async function main() { + const pagePaths = findPageMarkdownFiles(pagesDir); + if (pagePaths.length === 0) throw new Error(`No page .md files found under: ${pagesDir}`); + + console.log("Building VS files for:", kbSlug); + console.log("Pages dir:", pagesDir); + console.log("VS out:", outVsDir); + console.log( + `chunkMaxTokens=${CHUNK_MAX_TOKENS} largeChunkThreshold=${LARGE_CHUNK_THRESHOLD} sectionMaxTokens=${SECTION_MAX_TOKENS} sectionOverlapTokens=${SECTION_OVERLAP_TOKENS} year=${YEAR}` + ); + console.log(`Found ${pagePaths.length} page files`); + + // Clear destination directory by default (matches your chunk script behavior) + rmDirContents(outVsDir); + + const manifest: Array<{ + page_path: string; + vs_file_path: string; + attributes: VsAttributes; + }> = []; + + let pagesOk = 0; + let pagesFailed = 0; + let totalVsFiles = 0; + let totalLargePages = 0; + + for (const p of pagePaths) { + try { + const raw = fs.readFileSync(p, "utf-8"); + const { fm, body } = readFrontmatter(raw); + + const canonical_url = must(fm, ["canonical_url", "url"], p); + const title = inferTitleFromFrontmatter(fm, canonical_url); + const section = inferSectionFromFrontmatter(fm); + const site = inferSiteFromFrontmatter(fm); + + const { units, chunkCountEstimate } = buildUnitsFromPage( + kbSlug, + { canonical_url, title, section, site }, + body + ); + + if (chunkCountEstimate > LARGE_CHUNK_THRESHOLD) totalLargePages += 1; + + for (const u of units) { + const vsPath = writeVsFile(outVsDir, u); + manifest.push({ + page_path: p, + vs_file_path: vsPath, + attributes: buildAttributes(u), + }); + } + + pagesOk += 1; + totalVsFiles += units.length; + + if (pagesOk % 25 === 0) { + console.log( + `...processed ${pagesOk}/${pagePaths.length} pages (vs_files=${totalVsFiles}, large_pages=${totalLargePages})` + ); + } + } catch (e: any) { + pagesFailed += 1; + console.warn("FAILED:", p, "-", e?.message ?? e); + } + } + + const manifestPath = path.join(outVsDir, "manifest.json"); + fs.writeFileSync(manifestPath, JSON.stringify(manifest, null, 2), "utf-8"); + + console.log("\nDone."); + console.log("Pages ok:", pagesOk); + console.log("Pages failed:", pagesFailed); + console.log("Large pages:", totalLargePages); + console.log("Total VS files written:", totalVsFiles); + console.log("Manifest:", manifestPath); +})(); \ No newline at end of file diff --git a/scripts/kb/sync-central-vector-store-vs-files.ts b/scripts/kb/sync-central-vector-store-vs-files.ts new file mode 100644 index 00000000..ec4a331d --- /dev/null +++ b/scripts/kb/sync-central-vector-store-vs-files.ts @@ -0,0 +1,422 @@ +// scripts/kb/sync-central-vector-store-vs-files.ts +// +// Sync VS ingestion files (generated by build-vs-files-from-pages.ts) into a CENTRAL vector store, +// using manifest.json for attributes, and upserting kb_document_files in Supabase. +// +// Usage: +// tsx scripts/kb/sync-central-vector-store-vs-files.ts +// +// Example: +// tsx scripts/kb/sync-central-vector-store-vs-files.ts scripts/kb_scrapes/all/vs_files vs_abc123 +// +// Notes: +// - Expects /manifest.json produced by build-vs-files-from-pages.ts. +// - Uses content_hash for idempotency: if unchanged, skips upload. +// - Deletes (detaches) active rows in kb_document_files that are not present in manifest (for the kb_slugs present). +// +// Env required: +// OPENAI_API_KEY +// NEXT_PUBLIC_SUPABASE_URL +// SUPABASE_SERVICE_ROLE_KEY + +import fs from "node:fs"; +import path from "node:path"; +import crypto from "node:crypto"; +import dotenv from "dotenv"; +import OpenAI from "openai"; +import pLimit from "p-limit"; +import { createClient, SupabaseClient } from "@supabase/supabase-js"; + +dotenv.config({ path: path.resolve(process.cwd(), ".env.local") }); +dotenv.config({ path: path.resolve(process.cwd(), ".env") }); + +const CONCURRENCY = 3; + +type ManifestEntry = { + page_path: string; + vs_file_path: string; + attributes: Record; +}; + +type KBDocFileRow = { + kb_slug: string; + doc_id: string; + section_key: string; + + canonical_url: string | null; + title: string | null; + site: string | null; + + uni: string | null; + corpus: string | null; + year: number | null; + + vector_store_id: string | null; + file_id: string | null; + vector_store_file_id: string | null; + + content_hash: string | null; + last_fetched_at: string; + is_active: boolean; +}; + +function usageAndExit(): never { + console.error( + "Usage: tsx scripts/kb/sync-central-vector-store-vs-files.ts \n" + + "Example: tsx scripts/kb/sync-central-vector-store-vs-files.ts scripts/kb_scrapes/all/vs_files vs_abc123" + ); + process.exit(1); +} + +function clampAttr(s: unknown, maxLen: number): string { + const v = String(s ?? "").trim(); + if (!v) return ""; + if (v.length <= maxLen) return v; + + const hash = crypto.createHash("sha1").update(v).digest("hex").slice(0, 10); + const suffix = `...#${hash}`; + const keep = Math.max(0, maxLen - suffix.length); + const out = v.slice(0, keep) + suffix; + return out.length <= maxLen ? out : out.slice(0, maxLen); +} + +function makeSupabaseAdminClient(): SupabaseClient { + const url = process.env.NEXT_PUBLIC_SUPABASE_URL; + const serviceKey = process.env.SUPABASE_SERVICE_ROLE_KEY; + if (!url) throw new Error("Missing NEXT_PUBLIC_SUPABASE_URL"); + if (!serviceKey) throw new Error("Missing SUPABASE_SERVICE_ROLE_KEY"); + return createClient(url, serviceKey, { auth: { persistSession: false } }); +} + +async function fetchAllDocFileRows(supabase: SupabaseClient, kbSlug: string): Promise { + const rows: KBDocFileRow[] = []; + const pageSize = 1000; + let from = 0; + + while (true) { + const to = from + pageSize - 1; + const { data, error } = await supabase + .from("kb_document_files") + .select("*") + .eq("kb_slug", kbSlug) + .range(from, to); + + if (error) throw error; + if (!data || data.length === 0) break; + + rows.push(...(data as KBDocFileRow[])); + if (data.length < pageSize) break; + from += pageSize; + } + + return rows; +} + +function readManifest(vsFilesDir: string): ManifestEntry[] { + const manifestPath = path.join(vsFilesDir, "manifest.json"); + if (!fs.existsSync(manifestPath)) throw new Error(`manifest.json not found: ${manifestPath}`); + const raw = fs.readFileSync(manifestPath, "utf-8"); + const parsed = JSON.parse(raw); + if (!Array.isArray(parsed)) throw new Error("manifest.json must be an array"); + return parsed as ManifestEntry[]; +} + +function keyOf(attrs: Record): string { + const kb_slug = String(attrs.kb_slug ?? ""); + const doc_id = String(attrs.doc_id ?? ""); + const section_key = String(attrs.section_key ?? ""); + if (!kb_slug || !doc_id || !section_key) { + throw new Error(`Missing required attributes for key: kb_slug/doc_id/section_key`); + } + return `${kb_slug}:${doc_id}:${section_key}`; +} + +async function uploadAndAttach( + openai: OpenAI, + vectorStoreId: string, + filePath: string, + attributes: Record +): Promise<{ file_id: string; vector_store_file_id: string }> { + const created = await openai.files.create({ + file: fs.createReadStream(filePath), + purpose: "assistants", + }); + + const vsFile = await openai.vectorStores.files.create(vectorStoreId, { + file_id: created.id, + attributes, + }); + + return { file_id: created.id, vector_store_file_id: vsFile.id }; +} + +async function deleteVSFile( + openai: OpenAI, + vectorStoreId: string, + vectorStoreFileId: string | null | undefined +) { + if (!vectorStoreFileId) return; + try { + await openai.vectorStores.files.delete(vectorStoreFileId, { vector_store_id: vectorStoreId }); + } catch (e: any) { + console.warn(`Warning: failed to delete vector store file ${vectorStoreFileId}:`, e?.message ?? e); + } +} + +async function upsertDocFileRow( + supabase: SupabaseClient, + row: Omit +) { + const payload = { ...row, last_fetched_at: new Date().toISOString() }; + const { error } = await supabase + .from("kb_document_files") + .upsert(payload, { onConflict: "kb_slug,doc_id,section_key" }); + + if (error) throw error; +} + +async function markDocFileInactive( + supabase: SupabaseClient, + kb_slug: string, + doc_id: string, + section_key: string +) { + const { error } = await supabase + .from("kb_document_files") + .update({ is_active: false, last_fetched_at: new Date().toISOString() }) + .eq("kb_slug", kb_slug) + .eq("doc_id", doc_id) + .eq("section_key", section_key); + + if (error) throw error; +} + +function sanitizeAttributes(attrs: Record): Record { + // Keep attributes tight and within typical limits. + // NOTE: If you later decide to drop canonical_url from attributes, remove it here. + const out: Record = { + uni: String(attrs.uni ?? ""), + corpus: String(attrs.corpus ?? ""), + year: Number(attrs.year ?? 2026), + kb_slug: String(attrs.kb_slug ?? ""), + doc_id: String(attrs.doc_id ?? ""), + site: String(attrs.site ?? ""), + section_key: String(attrs.section_key ?? ""), + canonical_url: clampAttr(attrs.canonical_url ?? "", 512), + content_hash: String(attrs.content_hash ?? ""), + }; + + // Remove empties so you don’t attach noisy attributes + for (const k of Object.keys(out)) { + const v = out[k]; + if (v === "" || v === null || v === undefined || (typeof v === "number" && Number.isNaN(v))) { + delete out[k]; + } + } + return out; +} + +async function main() { + const [, , vsFilesDirArg, centralVectorStoreId] = process.argv; + if (!vsFilesDirArg || !centralVectorStoreId) usageAndExit(); + + const apiKey = process.env.OPENAI_API_KEY; + if (!apiKey) throw new Error("Missing OPENAI_API_KEY"); + + const vsFilesDir = path.resolve(process.cwd(), vsFilesDirArg); + if (!fs.existsSync(vsFilesDir)) throw new Error(`vsFilesDir not found: ${vsFilesDir}`); + + const openai = new OpenAI({ apiKey }); + const supabase = makeSupabaseAdminClient(); + + // Validate store exists + const store = await openai.vectorStores.retrieve(centralVectorStoreId); + console.log(`Using CENTRAL vector store: ${store.id} (status=${store.status})`); + + const manifest = readManifest(vsFilesDir); + console.log(`Loaded manifest entries: ${manifest.length}`); + + // Normalize paths and attributes + const desired = new Map }>(); + const kbSlugsInRun = new Set(); + + for (const entry of manifest) { + const filePathAbs = path.isAbsolute(entry.vs_file_path) + ? entry.vs_file_path + : path.resolve(process.cwd(), entry.vs_file_path); + + if (!fs.existsSync(filePathAbs)) { + throw new Error(`VS file not found: ${filePathAbs}`); + } + + const attrs = sanitizeAttributes(entry.attributes ?? {}); + const k = keyOf(attrs); + + desired.set(k, { filePath: filePathAbs, attrs }); + kbSlugsInRun.add(String(attrs.kb_slug ?? "")); + } + + // Fetch existing rows per kb_slug (only the kb_slugs present in this manifest) + const existingRows: KBDocFileRow[] = []; + for (const kbSlug of kbSlugsInRun) { + if (!kbSlug) continue; + const rows = await fetchAllDocFileRows(supabase, kbSlug); + existingRows.push(...rows); + } + + const existingByKey = new Map(existingRows.map(r => [`${r.kb_slug}:${r.doc_id}:${r.section_key}`, r])); + const activeExistingKeys = new Set(existingRows.filter(r => r.is_active).map(r => `${r.kb_slug}:${r.doc_id}:${r.section_key}`)); + + // Plan + const toAdd: Array<{ key: string; filePath: string; attrs: Record }> = []; + const toUpdate: Array<{ key: string; filePath: string; attrs: Record; existing: KBDocFileRow }> = []; + const toSkip: Array<{ key: string }> = []; + const toDelete: KBDocFileRow[] = []; + + for (const [k, v] of desired.entries()) { + const ex = existingByKey.get(k); + if (!ex) { + toAdd.push({ key: k, filePath: v.filePath, attrs: v.attrs }); + continue; + } + + const desiredHash = String(v.attrs.content_hash ?? ""); + const existingHash = String(ex.content_hash ?? ""); + + // Skip if active, same hash, and already attached to this central store + if (ex.is_active && desiredHash && desiredHash === existingHash && ex.vector_store_id === centralVectorStoreId && ex.file_id) { + toSkip.push({ key: k }); + continue; + } + + toUpdate.push({ key: k, filePath: v.filePath, attrs: v.attrs, existing: ex }); + } + + for (const k of activeExistingKeys) { + if (!desired.has(k)) { + const ex = existingByKey.get(k); + if (ex && ex.vector_store_id === centralVectorStoreId) { + toDelete.push(ex); + } + } + } + + console.log( + `\nPlan (central store=${centralVectorStoreId}):\n` + + ` Add: ${toAdd.length}\n` + + ` Update: ${toUpdate.length}\n` + + ` Delete: ${toDelete.length}\n` + + ` Skip: ${toSkip.length}\n` + ); + + const limit = pLimit(CONCURRENCY); + + // 1) Delete (detach) rows missing from manifest + await Promise.all( + toDelete.map(ex => + limit(async () => { + await deleteVSFile(openai, centralVectorStoreId, ex.vector_store_file_id); + await markDocFileInactive(supabase, ex.kb_slug, ex.doc_id, ex.section_key); + }) + ) + ); + + // 2) Update changed rows + await Promise.all( + toUpdate.map(u => + limit(async () => { + // Detach old attachment if we have it and it was attached to central store + if (u.existing.vector_store_id === centralVectorStoreId) { + await deleteVSFile(openai, centralVectorStoreId, u.existing.vector_store_file_id); + } + + const { file_id, vector_store_file_id } = await uploadAndAttach( + openai, + centralVectorStoreId, + u.filePath, + u.attrs + ); + + const kb_slug = String(u.attrs.kb_slug); + const doc_id = String(u.attrs.doc_id); + const section_key = String(u.attrs.section_key); + + await upsertDocFileRow(supabase, { + kb_slug, + doc_id, + section_key, + + canonical_url: String(u.attrs.canonical_url ?? "") || null, + title: null, + site: String(u.attrs.site ?? "") || null, + + uni: String(u.attrs.uni ?? "") || null, + corpus: String(u.attrs.corpus ?? "") || null, + year: Number(u.attrs.year ?? 2026), + + vector_store_id: centralVectorStoreId, + file_id, + vector_store_file_id, + + content_hash: String(u.attrs.content_hash ?? "") || null, + is_active: true, + } as Omit); + }) + ) + ); + + // 3) Add new rows + await Promise.all( + toAdd.map(a => + limit(async () => { + const { file_id, vector_store_file_id } = await uploadAndAttach( + openai, + centralVectorStoreId, + a.filePath, + a.attrs + ); + + const kb_slug = String(a.attrs.kb_slug); + const doc_id = String(a.attrs.doc_id); + const section_key = String(a.attrs.section_key); + + await upsertDocFileRow(supabase, { + kb_slug, + doc_id, + section_key, + + canonical_url: String(a.attrs.canonical_url ?? "") || null, + title: null, + site: String(a.attrs.site ?? "") || null, + + uni: String(a.attrs.uni ?? "") || null, + corpus: String(a.attrs.corpus ?? "") || null, + year: Number(a.attrs.year ?? 2026), + + vector_store_id: centralVectorStoreId, + file_id, + vector_store_file_id, + + content_hash: String(a.attrs.content_hash ?? "") || null, + is_active: true, + } as Omit); + }) + ) + ); + + const finalStore = await openai.vectorStores.retrieve(centralVectorStoreId); + console.log( + "\nSync complete.\nVector store:", + finalStore.id, + "status:", + finalStore.status, + "file_counts:", + finalStore.file_counts + ); + console.log(`Summary: added=${toAdd.length}, updated=${toUpdate.length}, deleted=${toDelete.length}, skipped=${toSkip.length}`); +} + +main().catch((e) => { + console.error(e); + process.exit(1); +}); \ No newline at end of file diff --git a/scripts/kb/validate-central-kb-search.ts b/scripts/kb/validate-central-kb-search.ts new file mode 100644 index 00000000..2d61c342 --- /dev/null +++ b/scripts/kb/validate-central-kb-search.ts @@ -0,0 +1,197 @@ +import path from "node:path"; +import dotenv from "dotenv"; +import OpenAI from "openai"; +import { createClient } from "@supabase/supabase-js"; + +dotenv.config({ path: path.resolve(process.cwd(), ".env.local") }); +dotenv.config({ path: path.resolve(process.cwd(), ".env") }); + +const KB_YEAR = 2026; + +type ComparisonFilter = { + type: "eq"; + key: string; + value: string | number | boolean; +}; + +type CompoundFilter = { + type: "and" | "or"; + filters: Array; +}; + +function corporaForIntent(intent: string): string[] { + if (intent === "official") return ["official"]; + if (intent === "su" || intent === "union") return ["su"]; + return ["official", "su"]; +} + +function kbSlugFor(uniSlug: string, corpus: string) { + return `${uniSlug}_${corpus}`; +} + +function buildKBFilters( + uniSlug: string, + corpora: string[], + year: number, +): CompoundFilter { + const corpusFilter: CompoundFilter | ComparisonFilter = + corpora.length === 1 + ? { type: "eq", key: "corpus", value: corpora[0] } + : { + type: "or", + filters: corpora.map((c) => ({ type: "eq", key: "corpus", value: c })), + }; + + const kbSlugFilter: CompoundFilter | ComparisonFilter = + corpora.length === 1 + ? { type: "eq", key: "kb_slug", value: kbSlugFor(uniSlug, corpora[0]) } + : { + type: "or", + filters: corpora.map((c) => ({ + type: "eq", + key: "kb_slug", + value: kbSlugFor(uniSlug, c), + })), + }; + + return { + type: "and", + filters: [ + { type: "eq", key: "uni", value: uniSlug }, + { type: "eq", key: "year", value: year }, + corpusFilter, + kbSlugFilter, + ], + }; +} + +function normalizeSlug(s: string) { + return s + .toLowerCase() + .replace(/__part_\d+$/, "") + .replace(/[^a-z0-9]+/g, "-") + .replace(/^-+|-+$/g, ""); +} + +function chunkMatchesSection( + chunk: { heading_path?: string | null; chunk_title?: string | null }, + sectionKey: string, +) { + if (!sectionKey || sectionKey === "__full__") return true; + const target = normalizeSlug(sectionKey); + if (!target) return false; + const heading = [chunk.heading_path, chunk.chunk_title] + .filter((v) => typeof v === "string") + .join(" "); + const haystack = normalizeSlug(heading); + return haystack.includes(target); +} + +async function main() { + const [, , query, uniSlug, intentArg] = process.argv; + if (!query || !uniSlug) { + console.error( + "Usage: tsx scripts/kb/validate-central-kb-search.ts [official|su|both]", + ); + process.exit(1); + } + + const intent = intentArg ?? "both"; + const vectorStoreId = process.env.OPENAI_UNI_VECTOR_STORE_ID; + if (!vectorStoreId) throw new Error("Missing OPENAI_UNI_VECTOR_STORE_ID"); + + const apiKey = process.env.OPENAI_API_KEY; + if (!apiKey) throw new Error("Missing OPENAI_API_KEY"); + + const url = process.env.NEXT_PUBLIC_SUPABASE_URL; + const serviceKey = process.env.SUPABASE_SERVICE_ROLE_KEY; + if (!url || !serviceKey) { + throw new Error("Missing Supabase service credentials"); + } + + const openai = new OpenAI({ apiKey }); + const supabase = createClient(url, serviceKey, { auth: { persistSession: false } }); + + const corpora = corporaForIntent(intent); + const filters = buildKBFilters(uniSlug, corpora, KB_YEAR); + + const searchPage = await openai.vectorStores.search(vectorStoreId, { + query, + filters, + max_num_results: 6, + rewrite_query: true, + }); + + console.log(`Vector store results: ${searchPage.data.length}`); + + const fileIds = Array.from(new Set(searchPage.data.map((h) => h.file_id))); + console.log("file_ids:", fileIds); + + const { data: docFiles, error: docError } = await supabase + .from("kb_document_files") + .select( + "file_id,kb_slug,doc_id,section_key,canonical_url,title,site,uni,corpus,year", + ) + .in("file_id", fileIds) + .eq("is_active", true); + + if (docError) throw docError; + + for (const row of docFiles ?? []) { + console.log("doc_file:", row.file_id, row.kb_slug, row.doc_id, row.section_key); + } + + if (!docFiles || docFiles.length === 0) { + console.log("No kb_document_files rows matched."); + return; + } + + const doc = docFiles[0]; + const { data: chunks, error: chunkError } = await supabase + .from("kb_chunks") + .select("*") + .eq("kb_slug", doc.kb_slug) + .eq("doc_id", doc.doc_id) + .eq("is_active", true) + .order("chunk_index", { ascending: true }); + + if (chunkError) throw chunkError; + + const sectionChunks = (chunks ?? []).filter((c) => + chunkMatchesSection( + { + heading_path: c.heading_path, + chunk_title: c.chunk_title, + }, + doc.section_key, + ), + ); + + console.log( + `chunks: ${chunks?.length ?? 0}, section-matched: ${sectionChunks.length}`, + ); + + const firstChunk = sectionChunks[0] ?? chunks?.[0]; + if (firstChunk) { + const text = + firstChunk.content || + firstChunk.chunk_content || + firstChunk.chunk_text || + firstChunk.text || + firstChunk.markdown || + ""; + if (typeof text === "string" && text.trim()) { + console.log("chunk snippet:", text.trim().slice(0, 240)); + } else { + console.log("chunk metadata:", { + heading_path: firstChunk.heading_path, + chunk_title: firstChunk.chunk_title, + }); + } + } +} + +main().catch((err) => { + console.error("Validation failed:", err); + process.exit(1); +}); diff --git a/scripts/kb/wipe-umsu-from-central.ts b/scripts/kb/wipe-umsu-from-central.ts new file mode 100644 index 00000000..e001bf3c --- /dev/null +++ b/scripts/kb/wipe-umsu-from-central.ts @@ -0,0 +1,106 @@ +import path from "node:path"; +import dotenv from "dotenv"; +import OpenAI from "openai"; +import { createClient } from "@supabase/supabase-js"; + +dotenv.config({ path: path.resolve(process.cwd(), ".env.local") }); +dotenv.config({ path: path.resolve(process.cwd(), ".env") }); + +type Row = { + kb_slug: string; + doc_id: string; + section_key: string; + vector_store_id: string | null; + vector_store_file_id: string | null; + file_id: string | null; + canonical_url: string | null; + is_active: boolean; +}; + +function supabaseAdmin() { + const url = process.env.NEXT_PUBLIC_SUPABASE_URL; + const key = process.env.SUPABASE_SERVICE_ROLE_KEY; + if (!url) throw new Error("Missing NEXT_PUBLIC_SUPABASE_URL"); + if (!key) throw new Error("Missing SUPABASE_SERVICE_ROLE_KEY"); + return createClient(url, key, { auth: { persistSession: false } }); +} + +async function main() { + const [, , centralVsId, mode] = process.argv; + if (!centralVsId) { + console.error("Usage: tsx scripts/kb/wipe-umsu-from-central.ts [delete|deactivate]"); + process.exit(1); + } + const doDelete = (mode ?? "deactivate") === "delete"; + + const apiKey = process.env.OPENAI_API_KEY; + if (!apiKey) throw new Error("Missing OPENAI_API_KEY"); + + const openai = new OpenAI({ apiKey }); + const supabase = supabaseAdmin(); + + // Pull ALL UMSU rows (active + inactive) so we can detach everything we know about + const rows: Row[] = []; + const pageSize = 1000; + let from = 0; + + while (true) { + const to = from + pageSize - 1; + const { data, error } = await supabase + .from("kb_document_files") + .select("kb_slug,doc_id,section_key,vector_store_id,vector_store_file_id,file_id,canonical_url,is_active") + .eq("site", "umsu") + .range(from, to); + + if (error) throw error; + if (!data || data.length === 0) break; + + rows.push(...(data as Row[])); + if (data.length < pageSize) break; + from += pageSize; + } + + const targets = rows.filter(r => r.vector_store_id === centralVsId); + + console.log(`Found ${rows.length} kb_document_files rows with site=umsu`); + console.log(`Of those, ${targets.length} point at central store ${centralVsId}`); + + // Detach from the central vector store + let detached = 0; + for (const r of targets) { + if (!r.vector_store_file_id) continue; + + try { + await openai.vectorStores.files.delete(r.vector_store_file_id, { vector_store_id: centralVsId }); + detached += 1; + } catch (e: any) { + console.warn("Detach failed:", r.vector_store_file_id, e?.message ?? e); + } + } + + console.log(`Detached ${detached} vector store files from ${centralVsId}`); + + // Now clean Supabase rows + if (doDelete) { + const { error } = await supabase + .from("kb_document_files") + .delete() + .eq("site", "umsu"); + if (error) throw error; + console.log("Deleted kb_document_files rows where site=umsu"); + } else { + const { error } = await supabase + .from("kb_document_files") + .update({ is_active: false, last_fetched_at: new Date().toISOString() }) + .eq("site", "umsu"); + if (error) throw error; + console.log("Deactivated kb_document_files rows where site=umsu (is_active=false)"); + } + + console.log("\nWipe complete."); +} + +main().catch((e) => { + console.error(e); + process.exit(1); +}); diff --git a/scripts/scrape/config.ts b/scripts/scrape/config.ts index 823d1730..c39fddca 100644 --- a/scripts/scrape/config.ts +++ b/scripts/scrape/config.ts @@ -18,26 +18,49 @@ export type SiteConfig = { siteId: "umsu", kbSlug: "unimelb_su", baseUrl: "https://umsu.unimelb.edu.au", - - // “Soft sitemap” seeds (you provided these) + + // Broader seeds to help discovery seeds: [ + "https://umsu.unimelb.edu.au/", + + // Keep your original seeds "https://umsu.unimelb.edu.au/support/", "https://umsu.unimelb.edu.au/buddy-up/", - "https://umsu.unimelb.edu.au/buddy-up/clubs/", "https://umsu.unimelb.edu.au/express-yourself/", "https://umsu.unimelb.edu.au/about/", + + // New: major sections on the public site + "https://umsu.unimelb.edu.au/things-to-do/", + "https://umsu.unimelb.edu.au/things-to-do/events/", + "https://umsu.unimelb.edu.au/make-a-difference/", + "https://umsu.unimelb.edu.au/international/", + "https://umsu.unimelb.edu.au/oweek/", + + // New: public sitemap as an efficient discovery hub + "https://umsu.unimelb.edu.au/sitemap/", ], - - // Restrict crawl strictly to these sections (and their children) + + // Allow crawling across additional public sections allowPrefixes: [ + // Keep original scope "https://umsu.unimelb.edu.au/support/", "https://umsu.unimelb.edu.au/buddy-up/", "https://umsu.unimelb.edu.au/express-yourself/", "https://umsu.unimelb.edu.au/about/", + + // Expanded scope + "https://umsu.unimelb.edu.au/things-to-do/", + "https://umsu.unimelb.edu.au/make-a-difference/", + "https://umsu.unimelb.edu.au/international/", + "https://umsu.unimelb.edu.au/oweek/", + + // Optional: allow the sitemap page itself (but not necessarily "everything") + "https://umsu.unimelb.edu.au/sitemap/", ], - - // Robots.txt disallows + additional practical exclusions + + // Keep your practical exclusions + add a couple more denySubstrings: [ + // existing "/photos/", "/advertclick/", "/login/", @@ -55,11 +78,24 @@ export type SiteConfig = { "tel:", "javascript:", "#", + + // extra: common non-content/static noise (adjust to your crawler logic) + ".css", + ".js", + ".png", + ".jpg", + ".jpeg", + ".gif", + ".webp", + ".svg", + "/ords/", // if any oracle/ords surfaces show up + "/api/", // if you see api endpoints being discovered ], - - maxPages: 650, // bump if you want more coverage - delayMs: 900, // polite + + maxPages: 8000, // increased because you widened scope + delayMs: 650, // keep polite (or increase to 800–1000 if you hit rate limits) }, + /* // --------------------------- // 1) Unimelb main site // robots disallows: /home-new/, /design/, /staffdev/, /_assets/, /templates*, etc.