diff --git a/electron/electron-env.d.ts b/electron/electron-env.d.ts index b7858e2..29d2585 100644 --- a/electron/electron-env.d.ts +++ b/electron/electron-env.d.ts @@ -35,6 +35,9 @@ interface Window { value: string, internal?: boolean, ) => string; + shell: { + openExternal: (url: string) => void; + }; isMonitored: (path: string) => boolean; setMonitored: (path: string, monitor: boolean) => void; getAppVersion: () => string; @@ -47,6 +50,7 @@ interface Window { setAutoUpdateEnabled: (autoUpdateEnabled: boolean) => void; codeTimeInStatusBar: () => boolean; setCodeTimeInStatusBar: (codeTimeInStatusBar: boolean) => void; + getOpenWindows: () => Promise; }; } diff --git a/electron/helpers/apps-manager.ts b/electron/helpers/apps-manager.ts index 3dfbb15..0c280f4 100644 --- a/electron/helpers/apps-manager.ts +++ b/electron/helpers/apps-manager.ts @@ -32,7 +32,9 @@ export class AppsManager { const data = fs.readFileSync(this.cacheFilePath, { encoding: "utf-8" }); const apps = z.array(appDataSchema).parse(JSON.parse(data)); return apps; - } catch (error) {} + } catch (_error) { + /* empty */ + } return []; } diff --git a/electron/helpers/config-file-reader.ts b/electron/helpers/config-file-reader.ts index 1f79b32..a7e08a7 100644 --- a/electron/helpers/config-file-reader.ts +++ b/electron/helpers/config-file-reader.ts @@ -34,7 +34,7 @@ export abstract class ConfigFileReader { try { contents = fs.readFileSync(file, { encoding: "utf-8" }); - } catch (error) { + } catch (_error) { contents = "[" + section + "]\n" + key + " = " + value; try { fs.writeFileSync(file, contents, { encoding: "utf-8" }); @@ -43,7 +43,7 @@ export abstract class ConfigFileReader { } } const lines = contents ? contents.split("\n") : []; - let output: string[] = []; + const output: string[] = []; let currentSection = ""; let found = false; for (const line of lines) { @@ -55,7 +55,7 @@ export abstract class ConfigFileReader { output.push(line); currentSection = line.slice(1, line.length - 1); } else if (currentSection === section) { - let parts = line.split("=", 2); + const parts = line.split("=", 2); if (parts.length === 2 && parts[0].trim() === key) { if (!found) { output.push(key + " = " + value); diff --git a/electron/helpers/filter-manager.ts b/electron/helpers/filter-manager.ts index 07bd4a9..779600a 100644 --- a/electron/helpers/filter-manager.ts +++ b/electron/helpers/filter-manager.ts @@ -1,4 +1,3 @@ -import { FilterType } from "../utils/constants"; import { PropertiesManager } from "./properties-manager"; export abstract class FilterManager { @@ -14,7 +13,7 @@ export abstract class FilterManager { const httpsUrl = "https://" + url; switch (PropertiesManager.filterType) { - case FilterType.denylist: + case "denylist": { for (const pattern of patterns) { if ( url.match(pattern) || @@ -26,7 +25,8 @@ export abstract class FilterManager { } } break; - case FilterType.allowlist: + } + case "allowlist": { const matchedPatternIndex = patterns.findIndex( (pattern) => url.match(pattern) || @@ -37,6 +37,7 @@ export abstract class FilterManager { return false; } break; + } } // The given address passed all filters and will be included diff --git a/electron/helpers/installed-apps/index.ts b/electron/helpers/installed-apps/index.ts index b66466c..10fbb53 100644 --- a/electron/helpers/installed-apps/index.ts +++ b/electron/helpers/installed-apps/index.ts @@ -1,3 +1,5 @@ +import path from "node:path"; + import { AppData } from "../../utils/validators"; import { allApps } from "../../watchers/apps"; import { getAppIconMac, getInstalledApps as getInstalledAppsMac } from "./mac"; @@ -39,7 +41,7 @@ export async function getApps(): Promise { let filePath: string | null = null; try { filePath = getFilePathWindows(record, app.windows.exePath); - } catch (error) { + } catch (_error) { /* empty */ } if (!filePath) { @@ -49,7 +51,7 @@ export async function getApps(): Promise { let icon: string | null = null; try { icon = await getIconFromWindows(filePath); - } catch (error) { + } catch (_error) { /* empty */ } @@ -69,6 +71,7 @@ export async function getApps(): Promise { isBrowser: app.isBrowser ?? false, isDefaultEnabled: app.isDefaultEnabled ?? false, isElectronApp: app.isElectronApp ?? false, + execName: path.parse(filePath).base, } satisfies AppData; } @@ -83,16 +86,17 @@ export async function getApps(): Promise { if (!record) { return null; } - const name = record["kMDItemDisplayName"]?.replace(".app", ""); - const path = record["_FILE_PATH"]; - if (!path || !name) { + const execName = record["kMDItemDisplayName"]; + const name = execName?.replace(".app", ""); + const filePath = record["_FILE_PATH"]; + if (!filePath || !name) { return; } - const icon = await getAppIconMac(path); + const icon = await getAppIconMac(filePath); const version = record["kMDItemVersion"] || null; return { - path, + path: filePath, icon, name, bundleId: app.mac.bundleId, @@ -101,6 +105,7 @@ export async function getApps(): Promise { isDefaultEnabled: app.isDefaultEnabled ?? false, isElectronApp: app.isElectronApp ?? false, version, + execName: path.parse(filePath).base, } satisfies AppData; } diff --git a/electron/helpers/installed-apps/mac.ts b/electron/helpers/installed-apps/mac.ts index 109b98e..e7a44e1 100644 --- a/electron/helpers/installed-apps/mac.ts +++ b/electron/helpers/installed-apps/mac.ts @@ -146,14 +146,14 @@ export async function getAppIconMac(appPath: string) { } icnsPath = path.join(appPath, "Contents/Resources", iconFileName); } - } catch (error) { + } catch (_error) { /* empty */ } if (!icnsPath) { try { icnsPath = await getFirstIcnsFileFromResourcesDir(); - } catch (error) { + } catch (_error) { /* empty */ } } diff --git a/electron/helpers/installed-apps/windows.ts b/electron/helpers/installed-apps/windows.ts index 4071b86..95567e5 100644 --- a/electron/helpers/installed-apps/windows.ts +++ b/electron/helpers/installed-apps/windows.ts @@ -2,7 +2,7 @@ import fs from "node:fs"; import path from "node:path"; import Winreg from "winreg"; -import { store } from "../../store"; +import { Store } from "../../store"; export function getFilePathWindows( appData: Record, @@ -49,7 +49,7 @@ export async function getIconFromWindows(filePath: string) { return null; } - const cachedIcon = store.get(`${filePath}-icon`); + const cachedIcon = Store.instance().get(`${filePath}-icon`); if (typeof cachedIcon === "string") { return cachedIcon; } @@ -57,7 +57,7 @@ export async function getIconFromWindows(filePath: string) { const buffer = extractIcon(filePath, "large"); const icon = "data:image/png;base64," + buffer.toString("base64"); - store.set(`${filePath}-icon`, icon); + Store.instance().set(`${filePath}-icon`, icon); return icon; } diff --git a/electron/helpers/monitored-app.ts b/electron/helpers/monitored-app.ts index 52467fd..f990ae8 100644 --- a/electron/helpers/monitored-app.ts +++ b/electron/helpers/monitored-app.ts @@ -1,16 +1,25 @@ import { WindowInfo } from "@miniben90/x-win"; -import { DomainPreferenceType } from "../utils/constants"; import { Category } from "../utils/types"; import { AppData } from "../utils/validators"; import { FilterManager } from "./filter-manager"; import { PropertiesManager } from "./properties-manager"; +export interface HeartbeatData { + entity: string; + category: Category | null; + language: string | null; + project: string | null; +} + export class MonitoredApp { - static heartbeatData(windowInfo: WindowInfo, app: AppData) { + static heartbeatData( + windowInfo: WindowInfo, + app?: AppData, + ): HeartbeatData | null { const entity = this.entity(windowInfo, app); - const category = this.category(app); - const language = this.language(app); + const category = app ? this.category(app) : null; + const language = app ? this.language(app) : null; const project = this.project(windowInfo); if (!entity) { return null; @@ -79,11 +88,11 @@ export class MonitoredApp { return null; } const patterns = [ - /github\.com\/([^\/]+\/[^\/]+)\/?.*$/, - /bitbucket\.org\/([^\/]+\/[^\/]+)\/?.*$/, - /app\.circleci\.com\/.*\/?(github|bitbucket|gitlab)\/([^\/]+\/[^\/]+)\/?.*$/, - /app\.travis-ci\.com\/(github|bitbucket|gitlab)\/([^\/]+\/[^\/]+)\/?.*$/, - /app\.travis-ci\.org\/(github|bitbucket|gitlab)\/([^\/]+\/[^\/]+)\/?.*$/, + /github\.com\/([^/]+\/[^/]+)\/?.*$/, + /bitbucket\.org\/([^/]+\/[^/]+)\/?.*$/, + /app\.circleci\.com\/.*\/?(github|bitbucket|gitlab)\/([^/]+\/[^/]+)\/?.*$/, + /app\.travis-ci\.com\/(github|bitbucket|gitlab)\/([^/]+\/[^/]+)\/?.*$/, + /app\.travis-ci\.org\/(github|bitbucket|gitlab)\/([^/]+\/[^/]+)\/?.*$/, ]; for (const pattern of patterns) { @@ -102,12 +111,10 @@ export class MonitoredApp { return null; } - static entity(windowInfo: WindowInfo, app: AppData) { - if (app.isBrowser) { + static entity(windowInfo: WindowInfo, app?: AppData) { + if (app?.isBrowser) { if (windowInfo.url && FilterManager.filterBrowsedSites(windowInfo.url)) { - if ( - PropertiesManager.domainPreference === DomainPreferenceType.domain - ) { + if (PropertiesManager.domainPreference === "domain") { return this.domainFromUrl(windowInfo.url); } return windowInfo.url; @@ -115,7 +122,7 @@ export class MonitoredApp { return null; } - switch (app.id) { + switch (app?.id) { // TODO: Unimplemented feature case "canva": return null; @@ -127,8 +134,8 @@ export class MonitoredApp { } } - static title(windowInfo: WindowInfo, app: AppData) { - switch (app.id) { + static title(windowInfo: WindowInfo, app?: AppData) { + switch (app?.id) { case "arcbrowser": case "brave": case "canva": @@ -139,7 +146,7 @@ export class MonitoredApp { case "safaripreview": case "xcode": case "microsoft_edge": - return `${app.id} should never use window title as entity`; + return `${app?.id} should never use window title as entity`; case "figma": { const title = windowInfo.title.split(" - ")[0]; if (!title || title === "Figma" || title === "Drafts") { @@ -162,7 +169,10 @@ export class MonitoredApp { return title; } default: - return windowInfo.title.split(" - ")[0]; + if (windowInfo.title) { + return windowInfo.title.split(" - ")[0]; + } + return windowInfo.info.name; } } diff --git a/electron/helpers/monitoring-manager.ts b/electron/helpers/monitoring-manager.ts index 154209a..af08d34 100644 --- a/electron/helpers/monitoring-manager.ts +++ b/electron/helpers/monitoring-manager.ts @@ -11,9 +11,6 @@ export abstract class MonitoringManager { } static isMonitored(path: string) { - if (!AppsManager.instance().getApp(path)) { - return; - } const monitoringKey = this.monitoredKey(path); const file = getDesktopWakaTimeConfigFilePath(); const monitoring = ConfigFileReader.getBool( @@ -29,9 +26,6 @@ export abstract class MonitoringManager { } static set(path: string, monitor: boolean) { - if (!AppsManager.instance().getApp(path)) { - return; - } const file = getDesktopWakaTimeConfigFilePath(); const monitoringKey = this.monitoredKey(path); ConfigFileReader.setBool(file, "monitoring", monitoringKey, monitor); diff --git a/electron/helpers/properties-manager.ts b/electron/helpers/properties-manager.ts index 868c586..6eb9455 100644 --- a/electron/helpers/properties-manager.ts +++ b/electron/helpers/properties-manager.ts @@ -1,21 +1,21 @@ +import type { DomainPreferenceType, FilterType } from "../utils/constants"; import { getDesktopWakaTimeConfigFilePath } from "../utils"; -import { DomainPreferenceType, FilterType } from "../utils/constants"; import { Logging } from "../utils/logging"; import { ConfigFileReader } from "./config-file-reader"; -enum Keys { - shouldLaunchOnLogin = "launch_on_login", - shouldLogToFile = "log_to_file", - shouldRequestA11y = "request_a11y", - shouldAutomaticallyDownloadUpdates = "should_automatically_download_updates", - hasLaunchedBefore = "has_launched_before", - domainPreference = "domain_preference", - filterType = "filter_type", - denylist = "denylist", - allowlist = "allowlist", - autoUpdateEnabled = "auto_update_enabled", - codeTimeInStatusBar = "code_time_in_status_bar", -} +const Keys = { + shouldLaunchOnLogin: "launch_on_login", + shouldLogToFile: "log_to_file", + shouldRequestA11y: "request_a11y", + shouldAutomaticallyDownloadUpdates: "should_automatically_download_updates", + hasLaunchedBefore: "has_launched_before", + domainPreference: "domain_preference", + filterType: "filter_type", + denylist: "denylist", + allowlist: "allowlist", + autoUpdateEnabled: "auto_update_enabled", + codeTimeInStatusBar: "code_time_in_status_bar", +}; export class PropertiesManager { static get autoUpdateEnabled(): boolean { @@ -209,13 +209,9 @@ export class PropertiesManager { Keys.domainPreference, ); if (value === null) { - return DomainPreferenceType.domain; + return "domain"; } - return value === DomainPreferenceType.domain - ? DomainPreferenceType.domain - : value === DomainPreferenceType.url - ? DomainPreferenceType.url - : DomainPreferenceType.domain; + return value === "domain" ? "domain" : value === "url" ? "url" : "domain"; } static set domainPreference(value: DomainPreferenceType) { ConfigFileReader.set( @@ -230,13 +226,13 @@ export class PropertiesManager { const file = getDesktopWakaTimeConfigFilePath(); const value = ConfigFileReader.get(file, "properties", Keys.filterType); if (value === null) { - return FilterType.allowlist; + return "allowlist"; } - return value === FilterType.allowlist - ? FilterType.allowlist - : value === FilterType.denylist - ? FilterType.denylist - : FilterType.denylist; + return value === "allowlist" + ? "allowlist" + : value === "denylist" + ? "denylist" + : "denylist"; } static set filterType(value: FilterType) { ConfigFileReader.set( @@ -292,9 +288,9 @@ export class PropertiesManager { static get currentFilterList() { switch (this.filterType) { - case FilterType.allowlist: + case "allowlist": return this.allowlist; - case FilterType.denylist: + case "denylist": return this.denylist; } } diff --git a/electron/main.ts b/electron/main.ts index 6227aaa..dcdf99b 100644 --- a/electron/main.ts +++ b/electron/main.ts @@ -1,4 +1,5 @@ import path from "node:path"; +import { openWindowsAsync } from "@miniben90/x-win"; import { app, BrowserWindow, @@ -9,20 +10,16 @@ import { Tray, } from "electron"; +import type { DomainPreferenceType, FilterType } from "./utils/constants"; import { AppsManager } from "./helpers/apps-manager"; import { ConfigFile } from "./helpers/config-file"; import { MonitoringManager } from "./helpers/monitoring-manager"; import { PropertiesManager } from "./helpers/properties-manager"; import { SettingsManager } from "./helpers/settings-manager"; import { getLogFilePath } from "./utils"; -import { - DeepLink, - DomainPreferenceType, - FilterType, - IpcKeys, - WAKATIME_PROTOCALL, -} from "./utils/constants"; +import { DeepLink, IpcKeys, WAKATIME_PROTOCALL } from "./utils/constants"; import { Logging } from "./utils/logging"; +import { AppData } from "./utils/validators"; import { Wakatime } from "./watchers/wakatime"; import { Watcher } from "./watchers/watcher"; @@ -224,7 +221,7 @@ function handleDeepLink(url: string) { if (!gotTheLock) { app.quit(); } else { - app.on("second-instance", (_event, commandLine, _workingDirectory) => { + app.on("second-instance", (_event, commandLine) => { const url = commandLine.pop()?.slice(0, -1); if (url) { handleDeepLink(url); @@ -358,3 +355,45 @@ ipcMain.on(IpcKeys.getAllowlist, (event) => { ipcMain.on(IpcKeys.setAllowlist, (_, value: string) => { PropertiesManager.allowlist = value; }); + +ipcMain.on(IpcKeys.shellOpenExternal, (_, url: string) => { + shell.openExternal(url); +}); + +ipcMain.on(IpcKeys.getOpenWindows, async (event) => { + const windows = await openWindowsAsync(); + event.returnValue = ( + await Promise.all( + windows + .filter( + (win, i) => + win.info.execName && + windows.findIndex((win2) => win2.info.path === win.info.path) === i, + ) + .sort((a, b) => a.info.name.localeCompare(b.info.name)) + .map(async (window) => { + const app = AppsManager.instance().apps.find( + (item) => item.path === window.info.path, + ); + + if (app) { + return null; + } + + const icon = (await window.getIconAsync()).data; + return { + id: window.info.path, + name: window.info.name, + path: window.info.path, + icon, + isBrowser: false, + isDefaultEnabled: false, + isElectronApp: false, + bundleId: null, + version: null, + execName: path.parse(window.info.path).base, + } satisfies AppData; + }), + ) + ).filter((item) => !!item); +}); diff --git a/electron/preload.ts b/electron/preload.ts index 8c17c63..655405b 100644 --- a/electron/preload.ts +++ b/electron/preload.ts @@ -22,6 +22,11 @@ contextBridge.exposeInMainWorld("ipcRenderer", { const [channel, ...omit] = args; return ipcRenderer.sendSync(channel, ...omit); }, + shell: { + openExternal: (url: string) => { + ipcRenderer.send(IpcKeys.shellOpenExternal, url); + }, + }, invoke(...args: Parameters) { const [channel, ...omit] = args; return ipcRenderer.invoke(channel, ...omit); @@ -68,4 +73,7 @@ contextBridge.exposeInMainWorld("ipcRenderer", { setShouldLogToFile(shouldLogToFile: boolean) { ipcRenderer.send(IpcKeys.setShouldLogToFile, shouldLogToFile); }, + getOpenWindows() { + return ipcRenderer.sendSync(IpcKeys.getOpenWindows); + }, }); diff --git a/electron/store.ts b/electron/store.ts index e415094..6922d76 100644 --- a/electron/store.ts +++ b/electron/store.ts @@ -1,14 +1,13 @@ -let instance: Store; - // This is just a simple in memory key value pair store to keep in memory caches. export class Store { records: Record = {}; + static _instacneCache?: Store; - constructor() { - if (instance) { - throw new Error("There can be only one stroe."); + static instance(): Store { + if (!this._instacneCache) { + this._instacneCache = new this(); } - instance = this; + return this._instacneCache; } set(key: string, value: T) { @@ -16,7 +15,7 @@ export class Store { } get(key: string) { - let value = this.records[key] as T | undefined; + const value = this.records[key] as T | undefined; return value; } @@ -28,5 +27,3 @@ export class Store { this.records[key] = undefined; } } - -export const store = Object.freeze(new Store()); diff --git a/electron/utils/constants.ts b/electron/utils/constants.ts index 5238649..4abe523 100644 --- a/electron/utils/constants.ts +++ b/electron/utils/constants.ts @@ -1,43 +1,39 @@ -export enum IpcKeys { - getApps = "get_apps", - getAppVersion = "get_app_version", - getSetting = "get_setting", - setSetting = "set_setting", - isMonitored = "is_monitored", - setMonitored = "set_monitored", - autoUpdateEnabled = "auto_update_enabled", - setAutoUpdateEnabled = "set_auto_update_enabled", - codeTimeInStatusBar = "code_time_in_status_bar", - setCodeTimeInStatusBar = "set_code_time_in_status_bar", - shouldLogToFile = "should_log_to_file", - setShouldLogToFile = "set_should_log_to_file", - shouldLaunchOnLogin = "should_launch_on_login", - setShouldLaunchOnLogin = "set_should_launch_on_login", - logFilePath = "log_file_path", - isBrowserMonitored = "is_browser_monitored", - getDomainPreference = "get_domain_preference", - setDomainPreference = "set_domain_preference", - getFilterType = "get_filter_type", - setFilterType = "set_filter_type", - getDenylist = "get_denylist", - setDenylist = "set_denylist", - getAllowlist = "get_allowlist", - setAllowlist = "set_allowlist", -} +export const IpcKeys = { + getApps: "get_apps", + getAppVersion: "get_app_version", + getSetting: "get_setting", + setSetting: "set_setting", + isMonitored: "is_monitored", + setMonitored: "set_monitored", + autoUpdateEnabled: "auto_update_enabled", + setAutoUpdateEnabled: "set_auto_update_enabled", + codeTimeInStatusBar: "code_time_in_status_bar", + setCodeTimeInStatusBar: "set_code_time_in_status_bar", + shouldLogToFile: "should_log_to_file", + setShouldLogToFile: "set_should_log_to_file", + shouldLaunchOnLogin: "should_launch_on_login", + setShouldLaunchOnLogin: "set_should_launch_on_login", + logFilePath: "log_file_path", + isBrowserMonitored: "is_browser_monitored", + getDomainPreference: "get_domain_preference", + setDomainPreference: "set_domain_preference", + getFilterType: "get_filter_type", + setFilterType: "set_filter_type", + getDenylist: "get_denylist", + setDenylist: "set_denylist", + getAllowlist: "get_allowlist", + setAllowlist: "set_allowlist", + getOpenWindows: "get_opened_windows", + shellOpenExternal: "shell_open_external", +}; -export enum FilterType { - denylist = "denylist", - allowlist = "allowlist", -} +export type FilterType = "denylist" | "allowlist"; -export enum DomainPreferenceType { - domain = "domain", - url = "url", -} +export type DomainPreferenceType = "domain" | "url"; -export enum DeepLink { - settings = "settings", - monitoredApps = "monitoredApps", -} +export const DeepLink = { + settings: "settings", + monitoredApps: "monitoredApps", +}; export const WAKATIME_PROTOCALL = "wakatime"; diff --git a/electron/utils/index.ts b/electron/utils/index.ts index e2d2b3e..c7f01b9 100644 --- a/electron/utils/index.ts +++ b/electron/utils/index.ts @@ -3,7 +3,7 @@ import fs from "node:fs"; import path from "node:path"; import { app } from "electron"; -import { DeepLink, WAKATIME_PROTOCALL } from "./constants"; +import { WAKATIME_PROTOCALL } from "./constants"; export function getResourcesFolderPath() { const userHome = app.getPath("home"); @@ -58,7 +58,7 @@ export function getCLIPath() { ); } -export function getDeepLinkUrl(link: DeepLink) { +export function getDeepLinkUrl(link: string) { return `${WAKATIME_PROTOCALL}://${link}`; } @@ -101,15 +101,15 @@ export function parseJSONObject(data: string): object | null { return null; } return obj; - } catch (e) { + } catch (_error) { try { const obj = JSON.parse(data) as unknown; if (typeof obj !== "object") { return null; } return obj; - } catch (e) { - /* ignore */ + } catch (_error) { + /* empty */ } } return null; diff --git a/electron/utils/validators.ts b/electron/utils/validators.ts index ffb6ed5..b948e27 100644 --- a/electron/utils/validators.ts +++ b/electron/utils/validators.ts @@ -1,9 +1,7 @@ import { z } from "zod"; -import { MonitoredApp } from "./types"; - export const appDataSchema = z.object({ - id: z.custom(), + id: z.string(), name: z.string(), path: z.string(), icon: z.string().nullable(), @@ -12,6 +10,7 @@ export const appDataSchema = z.object({ isBrowser: z.boolean(), isDefaultEnabled: z.boolean(), isElectronApp: z.boolean(), + execName: z.string().nullish(), }); export type AppData = z.infer; diff --git a/electron/watchers/wakatime.ts b/electron/watchers/wakatime.ts index 9dafac2..f7bba73 100644 --- a/electron/watchers/wakatime.ts +++ b/electron/watchers/wakatime.ts @@ -116,7 +116,7 @@ export class Wakatime { } async sendHeartbeat(props: { - appData: AppData; + appData?: AppData; windowInfo: WindowInfo; entity: string; entityType: EntityType; @@ -140,13 +140,13 @@ export class Wakatime { if (!this.shouldSendHeartbeat(entity, time, isWrite, category)) { return; } - if (!MonitoringManager.isMonitored(appData.path)) { + if (!MonitoringManager.isMonitored(windowInfo.info.path)) { return; } - const appName = windowInfo?.info.name ?? appData.name; - const appVersion = appData.version; - if (!appName || !appVersion) { + const appName = windowInfo.info.name ?? appData?.name; + const appVersion = appData?.version; + if (!appName) { return; } @@ -162,7 +162,7 @@ export class Wakatime { "--category", category, "--plugin", - `${appName}/${appVersion} ${getPlatfrom()}-wakatime/${app.getVersion()}`, + `${appName}${appVersion ? `/${appVersion}` : ""} ${getPlatfrom()}-wakatime/${app.getVersion()}`, ]; if (project) { @@ -179,7 +179,7 @@ export class Wakatime { Logging.instance().log(`Sending heartbeat: ${cli} ${args}`); try { - const [_, err] = await exec(cli, ...args); + const [, err] = await exec(cli, ...args); if (err) { Logging.instance().log( `Error sending heartbeat: ${err}`, diff --git a/electron/watchers/watcher.ts b/electron/watchers/watcher.ts index eb410c9..4d1cfee 100644 --- a/electron/watchers/watcher.ts +++ b/electron/watchers/watcher.ts @@ -35,9 +35,6 @@ export class Watcher { // To ensure we always retrieve the most current window information, including the updated URL and title, we use the activeWindow function instead of relying on the previously stored this.activeApp. This approach addresses the issue where switching tabs in your browser does not trigger a window change event, leading to activeApp retaining outdated URL and title information. const window = activeWindow(); const app = AppsManager.instance().getApp(window.info.path); - if (!app) { - return; - } const heartbeatData = MonitoredApp.heartbeatData(window, app); if (!heartbeatData) { return; diff --git a/eslint.config.mjs b/eslint.config.mjs index c7f3dc6..0e3862c 100644 --- a/eslint.config.mjs +++ b/eslint.config.mjs @@ -1,33 +1,63 @@ -import globals from "globals"; -import reactRefresh from "eslint-plugin-react-refresh"; +import path from "node:path"; +import { fileURLToPath } from "node:url"; +import { includeIgnoreFile } from "@eslint/compat"; +import eslint from "@eslint/js"; import tsParser from "@typescript-eslint/parser"; +import pluginReact from "eslint-plugin-react"; +import reactRefresh from "eslint-plugin-react-refresh"; +import globals from "globals"; +import tseslint from "typescript-eslint"; + +const __filename = fileURLToPath(import.meta.url); +const __dirname = path.dirname(__filename); +const gitignorePath = path.resolve(__dirname, ".gitignore"); export default [ - { - ignores: ["**/dist/*", "**/dist-electron/*", "**/dist-web/*", "**/node_modules/*"], - files: ["**/*.{ts,tsx}"], - plugins: { - "react-refresh": reactRefresh, + { + ignores: ["**/*.config.js"], + }, + includeIgnoreFile(gitignorePath), + eslint.configs.recommended, + ...tseslint.configs.recommended, + { + languageOptions: { + ecmaVersion: 2020, + sourceType: "module", + globals: { + ...globals.browser, + }, + parser: tsParser, + }, + plugins: { + react: pluginReact, + "react-refresh": reactRefresh, + }, + rules: { + "react-refresh/only-export-components": [ + "warn", + { + allowConstantExport: true, }, - languageOptions: { - ecmaVersion: 2020, - sourceType: "module", - globals: { - ...globals.browser, - }, - parser: tsParser, + ], + "no-unused-vars": "off", + "@typescript-eslint/no-unused-vars": [ + "error", + { + args: "all", + argsIgnorePattern: "^_", + caughtErrors: "all", + caughtErrorsIgnorePattern: "^_", + destructuredArrayIgnorePattern: "^_", + varsIgnorePattern: "^_", + ignoreRestSiblings: true, }, - rules: { - "react-refresh/only-export-components": ["warn", { - allowConstantExport: true, - }], - "no-unused-vars": ["error", { - vars: "all", - args: "after-used", - caughtErrors: "all", - ignoreRestSiblings: false, - reportUsedIgnorePattern: false, - }], + ], + "@typescript-eslint/no-empty-object-type": [ + "error", + { + allowInterfaces: "with-single-extends", }, + ], }, -]; \ No newline at end of file + }, +]; diff --git a/package-lock.json b/package-lock.json index 4ebab7b..40749cf 100644 --- a/package-lock.json +++ b/package-lock.json @@ -16,6 +16,7 @@ "@radix-ui/react-slot": "^1.1.0", "@radix-ui/react-switch": "^1.1.0", "@radix-ui/react-tabs": "^1.1.0", + "@tanstack/react-query": "^5.52.0", "class-variance-authority": "^0.7.0", "clsx": "^2.1.1", "date-fns": "^3.6.0", @@ -37,14 +38,16 @@ "zod": "^3.23.8" }, "devDependencies": { + "@eslint/compat": "^1.1.1", + "@eslint/js": "^9.9.1", "@ianvs/prettier-plugin-sort-imports": "^4.3.1", + "@types/eslint__js": "^8.42.3", "@types/node": "^22.4.1", "@types/plist": "^3.0.5", "@types/react": "^18.3.3", "@types/react-dom": "^18.3.0", "@types/unzipper": "^0.10.10", "@types/winreg": "^1.2.36", - "@typescript-eslint/eslint-plugin": "^8.2.0", "@typescript-eslint/parser": "^8.2.0", "@vitejs/plugin-react": "^4.3.1", "autoprefixer": "^10.4.20", @@ -58,6 +61,7 @@ "prettier-plugin-tailwindcss": "^0.6.6", "tailwindcss": "^3.4.10", "typescript": "^5.5.4", + "typescript-eslint": "^8.2.0", "vite": "^5.4.1", "vite-plugin-electron": "^0.28.7", "vite-plugin-electron-renderer": "^0.14.5", @@ -296,18 +300,18 @@ } }, "node_modules/@aws-sdk/client-s3": { - "version": "3.633.0", - "resolved": "https://registry.npmjs.org/@aws-sdk/client-s3/-/client-s3-3.633.0.tgz", - "integrity": "sha512-KPwNGlZlCRUADNTvwPJmvDvlh8N/jxjcv5e71M/mWxLXwSPdlHlRjVSBL1/CPSXUr86XRAsPL+BCRkdiytUhbg==", + "version": "3.637.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/client-s3/-/client-s3-3.637.0.tgz", + "integrity": "sha512-y6UC94fsMvhKbf0dzfnjVP1HePeGjplfcYfilZU1COIJLyTkMcUv4XcT4I407CGIrvgEafONHkiC09ygqUauNA==", "license": "Apache-2.0", "dependencies": { "@aws-crypto/sha1-browser": "5.2.0", "@aws-crypto/sha256-browser": "5.2.0", "@aws-crypto/sha256-js": "5.2.0", - "@aws-sdk/client-sso-oidc": "3.632.0", - "@aws-sdk/client-sts": "3.632.0", - "@aws-sdk/core": "3.629.0", - "@aws-sdk/credential-provider-node": "3.632.0", + "@aws-sdk/client-sso-oidc": "3.637.0", + "@aws-sdk/client-sts": "3.637.0", + "@aws-sdk/core": "3.635.0", + "@aws-sdk/credential-provider-node": "3.637.0", "@aws-sdk/middleware-bucket-endpoint": "3.620.0", "@aws-sdk/middleware-expect-continue": "3.620.0", "@aws-sdk/middleware-flexible-checksums": "3.620.0", @@ -315,18 +319,18 @@ "@aws-sdk/middleware-location-constraint": "3.609.0", "@aws-sdk/middleware-logger": "3.609.0", "@aws-sdk/middleware-recursion-detection": "3.620.0", - "@aws-sdk/middleware-sdk-s3": "3.633.0", + "@aws-sdk/middleware-sdk-s3": "3.635.0", "@aws-sdk/middleware-ssec": "3.609.0", - "@aws-sdk/middleware-user-agent": "3.632.0", + "@aws-sdk/middleware-user-agent": "3.637.0", "@aws-sdk/region-config-resolver": "3.614.0", - "@aws-sdk/signature-v4-multi-region": "3.633.0", + "@aws-sdk/signature-v4-multi-region": "3.635.0", "@aws-sdk/types": "3.609.0", - "@aws-sdk/util-endpoints": "3.632.0", + "@aws-sdk/util-endpoints": "3.637.0", "@aws-sdk/util-user-agent-browser": "3.609.0", "@aws-sdk/util-user-agent-node": "3.614.0", "@aws-sdk/xml-builder": "3.609.0", "@smithy/config-resolver": "^3.0.5", - "@smithy/core": "^2.3.2", + "@smithy/core": "^2.4.0", "@smithy/eventstream-serde-browser": "^3.0.6", "@smithy/eventstream-serde-config-resolver": "^3.0.3", "@smithy/eventstream-serde-node": "^3.0.5", @@ -338,20 +342,20 @@ "@smithy/md5-js": "^3.0.3", "@smithy/middleware-content-length": "^3.0.5", "@smithy/middleware-endpoint": "^3.1.0", - "@smithy/middleware-retry": "^3.0.14", + "@smithy/middleware-retry": "^3.0.15", "@smithy/middleware-serde": "^3.0.3", "@smithy/middleware-stack": "^3.0.3", "@smithy/node-config-provider": "^3.1.4", "@smithy/node-http-handler": "^3.1.4", "@smithy/protocol-http": "^4.1.0", - "@smithy/smithy-client": "^3.1.12", + "@smithy/smithy-client": "^3.2.0", "@smithy/types": "^3.3.0", "@smithy/url-parser": "^3.0.3", "@smithy/util-base64": "^3.0.0", "@smithy/util-body-length-browser": "^3.0.0", "@smithy/util-body-length-node": "^3.0.0", - "@smithy/util-defaults-mode-browser": "^3.0.14", - "@smithy/util-defaults-mode-node": "^3.0.14", + "@smithy/util-defaults-mode-browser": "^3.0.15", + "@smithy/util-defaults-mode-node": "^3.0.15", "@smithy/util-endpoints": "^2.0.5", "@smithy/util-middleware": "^3.0.3", "@smithy/util-retry": "^3.0.3", @@ -365,44 +369,44 @@ } }, "node_modules/@aws-sdk/client-sso": { - "version": "3.632.0", - "resolved": "https://registry.npmjs.org/@aws-sdk/client-sso/-/client-sso-3.632.0.tgz", - "integrity": "sha512-iYWHiKBz44m3chCFvtvHnvCpL2rALzyr1e6tOZV3dLlOKtQtDUlPy6OtnXDu4y+wyJCniy8ivG3+LAe4klzn1Q==", + "version": "3.637.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/client-sso/-/client-sso-3.637.0.tgz", + "integrity": "sha512-+KjLvgX5yJYROWo3TQuwBJlHCY0zz9PsLuEolmXQn0BVK1L/m9GteZHtd+rEdAoDGBpE0Xqjy1oz5+SmtsaRUw==", "license": "Apache-2.0", "dependencies": { "@aws-crypto/sha256-browser": "5.2.0", "@aws-crypto/sha256-js": "5.2.0", - "@aws-sdk/core": "3.629.0", + "@aws-sdk/core": "3.635.0", "@aws-sdk/middleware-host-header": "3.620.0", "@aws-sdk/middleware-logger": "3.609.0", "@aws-sdk/middleware-recursion-detection": "3.620.0", - "@aws-sdk/middleware-user-agent": "3.632.0", + "@aws-sdk/middleware-user-agent": "3.637.0", "@aws-sdk/region-config-resolver": "3.614.0", "@aws-sdk/types": "3.609.0", - "@aws-sdk/util-endpoints": "3.632.0", + "@aws-sdk/util-endpoints": "3.637.0", "@aws-sdk/util-user-agent-browser": "3.609.0", "@aws-sdk/util-user-agent-node": "3.614.0", "@smithy/config-resolver": "^3.0.5", - "@smithy/core": "^2.3.2", + "@smithy/core": "^2.4.0", "@smithy/fetch-http-handler": "^3.2.4", "@smithy/hash-node": "^3.0.3", "@smithy/invalid-dependency": "^3.0.3", "@smithy/middleware-content-length": "^3.0.5", "@smithy/middleware-endpoint": "^3.1.0", - "@smithy/middleware-retry": "^3.0.14", + "@smithy/middleware-retry": "^3.0.15", "@smithy/middleware-serde": "^3.0.3", "@smithy/middleware-stack": "^3.0.3", "@smithy/node-config-provider": "^3.1.4", "@smithy/node-http-handler": "^3.1.4", "@smithy/protocol-http": "^4.1.0", - "@smithy/smithy-client": "^3.1.12", + "@smithy/smithy-client": "^3.2.0", "@smithy/types": "^3.3.0", "@smithy/url-parser": "^3.0.3", "@smithy/util-base64": "^3.0.0", "@smithy/util-body-length-browser": "^3.0.0", "@smithy/util-body-length-node": "^3.0.0", - "@smithy/util-defaults-mode-browser": "^3.0.14", - "@smithy/util-defaults-mode-node": "^3.0.14", + "@smithy/util-defaults-mode-browser": "^3.0.15", + "@smithy/util-defaults-mode-node": "^3.0.15", "@smithy/util-endpoints": "^2.0.5", "@smithy/util-middleware": "^3.0.3", "@smithy/util-retry": "^3.0.3", @@ -414,45 +418,45 @@ } }, "node_modules/@aws-sdk/client-sso-oidc": { - "version": "3.632.0", - "resolved": "https://registry.npmjs.org/@aws-sdk/client-sso-oidc/-/client-sso-oidc-3.632.0.tgz", - "integrity": "sha512-Oh1fIWaoZluihOCb/zDEpRTi+6an82fgJz7fyRBugyLhEtDjmvpCQ3oKjzaOhoN+4EvXAm1ZS/ZgpvXBlIRTgw==", + "version": "3.637.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/client-sso-oidc/-/client-sso-oidc-3.637.0.tgz", + "integrity": "sha512-27bHALN6Qb6m6KZmPvRieJ/QRlj1lyac/GT2Rn5kJpre8Mpp+yxrtvp3h9PjNBty4lCeFEENfY4dGNSozBuBcw==", "license": "Apache-2.0", "dependencies": { "@aws-crypto/sha256-browser": "5.2.0", "@aws-crypto/sha256-js": "5.2.0", - "@aws-sdk/core": "3.629.0", - "@aws-sdk/credential-provider-node": "3.632.0", + "@aws-sdk/core": "3.635.0", + "@aws-sdk/credential-provider-node": "3.637.0", "@aws-sdk/middleware-host-header": "3.620.0", "@aws-sdk/middleware-logger": "3.609.0", "@aws-sdk/middleware-recursion-detection": "3.620.0", - "@aws-sdk/middleware-user-agent": "3.632.0", + "@aws-sdk/middleware-user-agent": "3.637.0", "@aws-sdk/region-config-resolver": "3.614.0", "@aws-sdk/types": "3.609.0", - "@aws-sdk/util-endpoints": "3.632.0", + "@aws-sdk/util-endpoints": "3.637.0", "@aws-sdk/util-user-agent-browser": "3.609.0", "@aws-sdk/util-user-agent-node": "3.614.0", "@smithy/config-resolver": "^3.0.5", - "@smithy/core": "^2.3.2", + "@smithy/core": "^2.4.0", "@smithy/fetch-http-handler": "^3.2.4", "@smithy/hash-node": "^3.0.3", "@smithy/invalid-dependency": "^3.0.3", "@smithy/middleware-content-length": "^3.0.5", "@smithy/middleware-endpoint": "^3.1.0", - "@smithy/middleware-retry": "^3.0.14", + "@smithy/middleware-retry": "^3.0.15", "@smithy/middleware-serde": "^3.0.3", "@smithy/middleware-stack": "^3.0.3", "@smithy/node-config-provider": "^3.1.4", "@smithy/node-http-handler": "^3.1.4", "@smithy/protocol-http": "^4.1.0", - "@smithy/smithy-client": "^3.1.12", + "@smithy/smithy-client": "^3.2.0", "@smithy/types": "^3.3.0", "@smithy/url-parser": "^3.0.3", "@smithy/util-base64": "^3.0.0", "@smithy/util-body-length-browser": "^3.0.0", "@smithy/util-body-length-node": "^3.0.0", - "@smithy/util-defaults-mode-browser": "^3.0.14", - "@smithy/util-defaults-mode-node": "^3.0.14", + "@smithy/util-defaults-mode-browser": "^3.0.15", + "@smithy/util-defaults-mode-node": "^3.0.15", "@smithy/util-endpoints": "^2.0.5", "@smithy/util-middleware": "^3.0.3", "@smithy/util-retry": "^3.0.3", @@ -463,50 +467,50 @@ "node": ">=16.0.0" }, "peerDependencies": { - "@aws-sdk/client-sts": "^3.632.0" + "@aws-sdk/client-sts": "^3.637.0" } }, "node_modules/@aws-sdk/client-sts": { - "version": "3.632.0", - "resolved": "https://registry.npmjs.org/@aws-sdk/client-sts/-/client-sts-3.632.0.tgz", - "integrity": "sha512-Ss5cBH09icpTvT+jtGGuQlRdwtO7RyE9BF4ZV/CEPATdd9whtJt4Qxdya8BUnkWR7h5HHTrQHqai3YVYjku41A==", + "version": "3.637.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/client-sts/-/client-sts-3.637.0.tgz", + "integrity": "sha512-xUi7x4qDubtA8QREtlblPuAcn91GS/09YVEY/RwU7xCY0aqGuFwgszAANlha4OUIqva8oVj2WO4gJuG+iaSnhw==", "license": "Apache-2.0", "dependencies": { "@aws-crypto/sha256-browser": "5.2.0", "@aws-crypto/sha256-js": "5.2.0", - "@aws-sdk/client-sso-oidc": "3.632.0", - "@aws-sdk/core": "3.629.0", - "@aws-sdk/credential-provider-node": "3.632.0", + "@aws-sdk/client-sso-oidc": "3.637.0", + "@aws-sdk/core": "3.635.0", + "@aws-sdk/credential-provider-node": "3.637.0", "@aws-sdk/middleware-host-header": "3.620.0", "@aws-sdk/middleware-logger": "3.609.0", "@aws-sdk/middleware-recursion-detection": "3.620.0", - "@aws-sdk/middleware-user-agent": "3.632.0", + "@aws-sdk/middleware-user-agent": "3.637.0", "@aws-sdk/region-config-resolver": "3.614.0", "@aws-sdk/types": "3.609.0", - "@aws-sdk/util-endpoints": "3.632.0", + "@aws-sdk/util-endpoints": "3.637.0", "@aws-sdk/util-user-agent-browser": "3.609.0", "@aws-sdk/util-user-agent-node": "3.614.0", "@smithy/config-resolver": "^3.0.5", - "@smithy/core": "^2.3.2", + "@smithy/core": "^2.4.0", "@smithy/fetch-http-handler": "^3.2.4", "@smithy/hash-node": "^3.0.3", "@smithy/invalid-dependency": "^3.0.3", "@smithy/middleware-content-length": "^3.0.5", "@smithy/middleware-endpoint": "^3.1.0", - "@smithy/middleware-retry": "^3.0.14", + "@smithy/middleware-retry": "^3.0.15", "@smithy/middleware-serde": "^3.0.3", "@smithy/middleware-stack": "^3.0.3", "@smithy/node-config-provider": "^3.1.4", "@smithy/node-http-handler": "^3.1.4", "@smithy/protocol-http": "^4.1.0", - "@smithy/smithy-client": "^3.1.12", + "@smithy/smithy-client": "^3.2.0", "@smithy/types": "^3.3.0", "@smithy/url-parser": "^3.0.3", "@smithy/util-base64": "^3.0.0", "@smithy/util-body-length-browser": "^3.0.0", "@smithy/util-body-length-node": "^3.0.0", - "@smithy/util-defaults-mode-browser": "^3.0.14", - "@smithy/util-defaults-mode-node": "^3.0.14", + "@smithy/util-defaults-mode-browser": "^3.0.15", + "@smithy/util-defaults-mode-node": "^3.0.15", "@smithy/util-endpoints": "^2.0.5", "@smithy/util-middleware": "^3.0.3", "@smithy/util-retry": "^3.0.3", @@ -518,17 +522,17 @@ } }, "node_modules/@aws-sdk/core": { - "version": "3.629.0", - "resolved": "https://registry.npmjs.org/@aws-sdk/core/-/core-3.629.0.tgz", - "integrity": "sha512-+/ShPU/tyIBM3oY1cnjgNA/tFyHtlWq+wXF9xEKRv19NOpYbWQ+xzNwVjGq8vR07cCRqy/sDQLWPhxjtuV/FiQ==", + "version": "3.635.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/core/-/core-3.635.0.tgz", + "integrity": "sha512-i1x/E/sgA+liUE1XJ7rj1dhyXpAKO1UKFUcTTHXok2ARjWTvszHnSXMOsB77aPbmn0fUp1JTx2kHUAZ1LVt5Bg==", "license": "Apache-2.0", "dependencies": { - "@smithy/core": "^2.3.2", + "@smithy/core": "^2.4.0", "@smithy/node-config-provider": "^3.1.4", "@smithy/property-provider": "^3.1.3", "@smithy/protocol-http": "^4.1.0", "@smithy/signature-v4": "^4.1.0", - "@smithy/smithy-client": "^3.1.12", + "@smithy/smithy-client": "^3.2.0", "@smithy/types": "^3.3.0", "@smithy/util-middleware": "^3.0.3", "fast-xml-parser": "4.4.1", @@ -554,9 +558,9 @@ } }, "node_modules/@aws-sdk/credential-provider-http": { - "version": "3.622.0", - "resolved": "https://registry.npmjs.org/@aws-sdk/credential-provider-http/-/credential-provider-http-3.622.0.tgz", - "integrity": "sha512-VUHbr24Oll1RK3WR8XLUugLpgK9ZuxEm/NVeVqyFts1Ck9gsKpRg1x4eH7L7tW3SJ4TDEQNMbD7/7J+eoL2svg==", + "version": "3.635.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/credential-provider-http/-/credential-provider-http-3.635.0.tgz", + "integrity": "sha512-iJyRgEjOCQlBMXqtwPLIKYc7Bsc6nqjrZybdMDenPDa+kmLg7xh8LxHsu9088e+2/wtLicE34FsJJIfzu3L82g==", "license": "Apache-2.0", "dependencies": { "@aws-sdk/types": "3.609.0", @@ -564,7 +568,7 @@ "@smithy/node-http-handler": "^3.1.4", "@smithy/property-provider": "^3.1.3", "@smithy/protocol-http": "^4.1.0", - "@smithy/smithy-client": "^3.1.12", + "@smithy/smithy-client": "^3.2.0", "@smithy/types": "^3.3.0", "@smithy/util-stream": "^3.1.3", "tslib": "^2.6.2" @@ -574,15 +578,15 @@ } }, "node_modules/@aws-sdk/credential-provider-ini": { - "version": "3.632.0", - "resolved": "https://registry.npmjs.org/@aws-sdk/credential-provider-ini/-/credential-provider-ini-3.632.0.tgz", - "integrity": "sha512-m6epoW41xa1ajU5OiHcmQHoGVtrbXBaRBOUhlCLZmcaqMLYsboM4iD/WZP8aatKEON5tTnVXh/4StV8D/+wemw==", + "version": "3.637.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/credential-provider-ini/-/credential-provider-ini-3.637.0.tgz", + "integrity": "sha512-h+PFCWfZ0Q3Dx84SppET/TFpcQHmxFW8/oV9ArEvMilw4EBN+IlxgbL0CnHwjHW64szcmrM0mbebjEfHf4FXmw==", "license": "Apache-2.0", "dependencies": { "@aws-sdk/credential-provider-env": "3.620.1", - "@aws-sdk/credential-provider-http": "3.622.0", + "@aws-sdk/credential-provider-http": "3.635.0", "@aws-sdk/credential-provider-process": "3.620.1", - "@aws-sdk/credential-provider-sso": "3.632.0", + "@aws-sdk/credential-provider-sso": "3.637.0", "@aws-sdk/credential-provider-web-identity": "3.621.0", "@aws-sdk/types": "3.609.0", "@smithy/credential-provider-imds": "^3.2.0", @@ -595,20 +599,20 @@ "node": ">=16.0.0" }, "peerDependencies": { - "@aws-sdk/client-sts": "^3.632.0" + "@aws-sdk/client-sts": "^3.637.0" } }, "node_modules/@aws-sdk/credential-provider-node": { - "version": "3.632.0", - "resolved": "https://registry.npmjs.org/@aws-sdk/credential-provider-node/-/credential-provider-node-3.632.0.tgz", - "integrity": "sha512-cL8fuJWm/xQBO4XJPkeuZzl3XinIn9EExWgzpG48NRMKR5us1RI/ucv7xFbBBaG+r/sDR2HpYBIA3lVIpm1H3Q==", + "version": "3.637.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/credential-provider-node/-/credential-provider-node-3.637.0.tgz", + "integrity": "sha512-yoEhoxJJfs7sPVQ6Is939BDQJZpZCoUgKr/ySse4YKOZ24t4VqgHA6+wV7rYh+7IW24Rd91UTvEzSuHYTlxlNA==", "license": "Apache-2.0", "dependencies": { "@aws-sdk/credential-provider-env": "3.620.1", - "@aws-sdk/credential-provider-http": "3.622.0", - "@aws-sdk/credential-provider-ini": "3.632.0", + "@aws-sdk/credential-provider-http": "3.635.0", + "@aws-sdk/credential-provider-ini": "3.637.0", "@aws-sdk/credential-provider-process": "3.620.1", - "@aws-sdk/credential-provider-sso": "3.632.0", + "@aws-sdk/credential-provider-sso": "3.637.0", "@aws-sdk/credential-provider-web-identity": "3.621.0", "@aws-sdk/types": "3.609.0", "@smithy/credential-provider-imds": "^3.2.0", @@ -638,12 +642,12 @@ } }, "node_modules/@aws-sdk/credential-provider-sso": { - "version": "3.632.0", - "resolved": "https://registry.npmjs.org/@aws-sdk/credential-provider-sso/-/credential-provider-sso-3.632.0.tgz", - "integrity": "sha512-P/4wB6j7ym5QCPTL2xlMfvf2NcXSh+z0jmsZP4WW/tVwab4hvgabPPbLeEZDSWZ0BpgtxKGvRq0GSHuGeirQbA==", + "version": "3.637.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/credential-provider-sso/-/credential-provider-sso-3.637.0.tgz", + "integrity": "sha512-Mvz+h+e62/tl+dVikLafhv+qkZJ9RUb8l2YN/LeKMWkxQylPT83CPk9aimVhCV89zth1zpREArl97+3xsfgQvA==", "license": "Apache-2.0", "dependencies": { - "@aws-sdk/client-sso": "3.632.0", + "@aws-sdk/client-sso": "3.637.0", "@aws-sdk/token-providers": "3.614.0", "@aws-sdk/types": "3.609.0", "@smithy/property-provider": "^3.1.3", @@ -784,19 +788,19 @@ } }, "node_modules/@aws-sdk/middleware-sdk-s3": { - "version": "3.633.0", - "resolved": "https://registry.npmjs.org/@aws-sdk/middleware-sdk-s3/-/middleware-sdk-s3-3.633.0.tgz", - "integrity": "sha512-7jjmWVw28wIHOdrHyTCvwKr1EYGrZI13DviwAOwRC0y9dB8gGCdRiA4fNczripUBxolCCE9mpqLrqy5pXtTzvA==", + "version": "3.635.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/middleware-sdk-s3/-/middleware-sdk-s3-3.635.0.tgz", + "integrity": "sha512-RLdYJPEV4JL/7NBoFUs7VlP90X++5FlJdxHz0DzCjmiD3qCviKy+Cym3qg1gBgHwucs5XisuClxDrGokhAdTQw==", "license": "Apache-2.0", "dependencies": { - "@aws-sdk/core": "3.629.0", + "@aws-sdk/core": "3.635.0", "@aws-sdk/types": "3.609.0", "@aws-sdk/util-arn-parser": "3.568.0", - "@smithy/core": "^2.3.2", + "@smithy/core": "^2.4.0", "@smithy/node-config-provider": "^3.1.4", "@smithy/protocol-http": "^4.1.0", "@smithy/signature-v4": "^4.1.0", - "@smithy/smithy-client": "^3.1.12", + "@smithy/smithy-client": "^3.2.0", "@smithy/types": "^3.3.0", "@smithy/util-config-provider": "^3.0.0", "@smithy/util-middleware": "^3.0.3", @@ -823,13 +827,13 @@ } }, "node_modules/@aws-sdk/middleware-user-agent": { - "version": "3.632.0", - "resolved": "https://registry.npmjs.org/@aws-sdk/middleware-user-agent/-/middleware-user-agent-3.632.0.tgz", - "integrity": "sha512-yY/sFsHKwG9yzSf/DTclqWJaGPI2gPBJDCGBujSqTG1zlS7Ot4fqi91DZ6088BFWzbOorDzJFcAhAEFzc6LuQg==", + "version": "3.637.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/middleware-user-agent/-/middleware-user-agent-3.637.0.tgz", + "integrity": "sha512-EYo0NE9/da/OY8STDsK2LvM4kNa79DBsf4YVtaG4P5pZ615IeFsD8xOHZeuJmUrSMlVQ8ywPRX7WMucUybsKug==", "license": "Apache-2.0", "dependencies": { "@aws-sdk/types": "3.609.0", - "@aws-sdk/util-endpoints": "3.632.0", + "@aws-sdk/util-endpoints": "3.637.0", "@smithy/protocol-http": "^4.1.0", "@smithy/types": "^3.3.0", "tslib": "^2.6.2" @@ -856,12 +860,12 @@ } }, "node_modules/@aws-sdk/signature-v4-multi-region": { - "version": "3.633.0", - "resolved": "https://registry.npmjs.org/@aws-sdk/signature-v4-multi-region/-/signature-v4-multi-region-3.633.0.tgz", - "integrity": "sha512-96F7Mx4lybMZdE0TTEkw6EKpeB0hxqp3J8fUJasesekTnO7jsklc47GHL5R3whyS/L4/JaPazm0Pi2DEH3kw1w==", + "version": "3.635.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/signature-v4-multi-region/-/signature-v4-multi-region-3.635.0.tgz", + "integrity": "sha512-J6QY4/invOkpogCHjSaDON1hF03viPpOnsrzVuCvJMmclS/iG62R4EY0wq1alYll0YmSdmKlpJwHMWwGtqK63Q==", "license": "Apache-2.0", "dependencies": { - "@aws-sdk/middleware-sdk-s3": "3.633.0", + "@aws-sdk/middleware-sdk-s3": "3.635.0", "@aws-sdk/types": "3.609.0", "@smithy/protocol-http": "^4.1.0", "@smithy/signature-v4": "^4.1.0", @@ -917,9 +921,9 @@ } }, "node_modules/@aws-sdk/util-endpoints": { - "version": "3.632.0", - "resolved": "https://registry.npmjs.org/@aws-sdk/util-endpoints/-/util-endpoints-3.632.0.tgz", - "integrity": "sha512-LlYMU8pAbcEQphOpE6xaNLJ8kPGhklZZTVzZVpVW477NaaGgoGTMYNXTABYHcxeF5E2lLrxql9OmVpvr8GWN8Q==", + "version": "3.637.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/util-endpoints/-/util-endpoints-3.637.0.tgz", + "integrity": "sha512-pAqOKUHeVWHEXXDIp/qoMk/6jyxIb6GGjnK1/f8dKHtKIEs4tKsnnL563gceEvdad53OPXIt86uoevCcCzmBnw==", "license": "Apache-2.0", "dependencies": { "@aws-sdk/types": "3.609.0", @@ -1006,9 +1010,9 @@ } }, "node_modules/@babel/compat-data": { - "version": "7.25.0", - "resolved": "https://registry.npmjs.org/@babel/compat-data/-/compat-data-7.25.0.tgz", - "integrity": "sha512-P4fwKI2mjEb3ZU5cnMJzvRsRKGBUcs8jvxIoRmr6ufAY9Xk2Bz7JubRTTivkw55c7WQJfTECeqYVa+HZ0FzREg==", + "version": "7.25.4", + "resolved": "https://registry.npmjs.org/@babel/compat-data/-/compat-data-7.25.4.tgz", + "integrity": "sha512-+LGRog6RAsCJrrrg/IO6LGmpphNe5DiK30dGjCoxxeGv49B10/3XYGxPsAwrDlMFcFEvdAUavDT8r9k/hSyQqQ==", "dev": true, "license": "MIT", "engines": { @@ -1016,22 +1020,22 @@ } }, "node_modules/@babel/core": { - "version": "7.24.9", - "resolved": "https://registry.npmjs.org/@babel/core/-/core-7.24.9.tgz", - "integrity": "sha512-5e3FI4Q3M3Pbr21+5xJwCv6ZT6KmGkI0vw3Tozy5ODAQFTIWe37iT8Cr7Ice2Ntb+M3iSKCEWMB1MBgKrW3whg==", + "version": "7.25.2", + "resolved": "https://registry.npmjs.org/@babel/core/-/core-7.25.2.tgz", + "integrity": "sha512-BBt3opiCOxUr9euZ5/ro/Xv8/V7yJ5bjYMqG/C1YAo8MIKAnumZalCN+msbci3Pigy4lIQfPUpfMM27HMGaYEA==", "dev": true, "license": "MIT", "dependencies": { "@ampproject/remapping": "^2.2.0", "@babel/code-frame": "^7.24.7", - "@babel/generator": "^7.24.9", - "@babel/helper-compilation-targets": "^7.24.8", - "@babel/helper-module-transforms": "^7.24.9", - "@babel/helpers": "^7.24.8", - "@babel/parser": "^7.24.8", - "@babel/template": "^7.24.7", - "@babel/traverse": "^7.24.8", - "@babel/types": "^7.24.9", + "@babel/generator": "^7.25.0", + "@babel/helper-compilation-targets": "^7.25.2", + "@babel/helper-module-transforms": "^7.25.2", + "@babel/helpers": "^7.25.0", + "@babel/parser": "^7.25.0", + "@babel/template": "^7.25.0", + "@babel/traverse": "^7.25.2", + "@babel/types": "^7.25.2", "convert-source-map": "^2.0.0", "debug": "^4.1.0", "gensync": "^1.0.0-beta.2", @@ -1057,13 +1061,13 @@ } }, "node_modules/@babel/generator": { - "version": "7.25.0", - "resolved": "https://registry.npmjs.org/@babel/generator/-/generator-7.25.0.tgz", - "integrity": "sha512-3LEEcj3PVW8pW2R1SR1M89g/qrYk/m/mB/tLqn7dn4sbBUQyTqnlod+II2U4dqiGtUmkcnAmkMDralTFZttRiw==", + "version": "7.25.5", + "resolved": "https://registry.npmjs.org/@babel/generator/-/generator-7.25.5.tgz", + "integrity": "sha512-abd43wyLfbWoxC6ahM8xTkqLpGB2iWBVyuKC9/srhFunCd1SDNrV1s72bBpK4hLj8KLzHBBcOblvLQZBNw9r3w==", "dev": true, "license": "MIT", "dependencies": { - "@babel/types": "^7.25.0", + "@babel/types": "^7.25.4", "@jridgewell/gen-mapping": "^0.3.5", "@jridgewell/trace-mapping": "^0.3.25", "jsesc": "^2.5.1" @@ -1073,13 +1077,13 @@ } }, "node_modules/@babel/helper-compilation-targets": { - "version": "7.24.8", - "resolved": "https://registry.npmjs.org/@babel/helper-compilation-targets/-/helper-compilation-targets-7.24.8.tgz", - "integrity": "sha512-oU+UoqCHdp+nWVDkpldqIQL/i/bvAv53tRqLG/s+cOXxe66zOYLU7ar/Xs3LdmBihrUMEUhwu6dMZwbNOYDwvw==", + "version": "7.25.2", + "resolved": "https://registry.npmjs.org/@babel/helper-compilation-targets/-/helper-compilation-targets-7.25.2.tgz", + "integrity": "sha512-U2U5LsSaZ7TAt3cfaymQ8WHh0pxvdHoEk6HVpaexxixjyEquMh0L0YNJNM6CTGKMXV1iksi0iZkGw4AcFkPaaw==", "dev": true, "license": "MIT", "dependencies": { - "@babel/compat-data": "^7.24.8", + "@babel/compat-data": "^7.25.2", "@babel/helper-validator-option": "^7.24.8", "browserslist": "^4.23.1", "lru-cache": "^5.1.1", @@ -1114,16 +1118,16 @@ } }, "node_modules/@babel/helper-module-transforms": { - "version": "7.25.0", - "resolved": "https://registry.npmjs.org/@babel/helper-module-transforms/-/helper-module-transforms-7.25.0.tgz", - "integrity": "sha512-bIkOa2ZJYn7FHnepzr5iX9Kmz8FjIz4UKzJ9zhX3dnYuVW0xul9RuR3skBfoLu+FPTQw90EHW9rJsSZhyLQ3fQ==", + "version": "7.25.2", + "resolved": "https://registry.npmjs.org/@babel/helper-module-transforms/-/helper-module-transforms-7.25.2.tgz", + "integrity": "sha512-BjyRAbix6j/wv83ftcVJmBt72QtHI56C7JXZoG2xATiLpmoC7dpd8WnkikExHDVPpi/3qCmO6WY1EaXOluiecQ==", "dev": true, "license": "MIT", "dependencies": { "@babel/helper-module-imports": "^7.24.7", "@babel/helper-simple-access": "^7.24.7", "@babel/helper-validator-identifier": "^7.24.7", - "@babel/traverse": "^7.25.0" + "@babel/traverse": "^7.25.2" }, "engines": { "node": ">=6.9.0" @@ -1217,11 +1221,14 @@ } }, "node_modules/@babel/parser": { - "version": "7.25.0", - "resolved": "https://registry.npmjs.org/@babel/parser/-/parser-7.25.0.tgz", - "integrity": "sha512-CzdIU9jdP0dg7HdyB+bHvDJGagUv+qtzZt5rYCWwW6tITNqV9odjp6Qu41gkG0ca5UfdDUWrKkiAnHHdGRnOrA==", + "version": "7.25.4", + "resolved": "https://registry.npmjs.org/@babel/parser/-/parser-7.25.4.tgz", + "integrity": "sha512-nq+eWrOgdtu3jG5Os4TQP3x3cLA8hR8TvJNjD8vnPa20WGycimcparWnLK4jJhElTK6SDyuJo1weMKO/5LpmLA==", "dev": true, "license": "MIT", + "dependencies": { + "@babel/types": "^7.25.4" + }, "bin": { "parser": "bin/babel-parser.js" }, @@ -1277,17 +1284,17 @@ } }, "node_modules/@babel/traverse": { - "version": "7.25.1", - "resolved": "https://registry.npmjs.org/@babel/traverse/-/traverse-7.25.1.tgz", - "integrity": "sha512-LrHHoWq08ZpmmFqBAzN+hUdWwy5zt7FGa/hVwMcOqW6OVtwqaoD5utfuGYU87JYxdZgLUvktAsn37j/sYR9siA==", + "version": "7.25.4", + "resolved": "https://registry.npmjs.org/@babel/traverse/-/traverse-7.25.4.tgz", + "integrity": "sha512-VJ4XsrD+nOvlXyLzmLzUs/0qjFS4sK30te5yEFlvbbUNEgKaVb2BHZUpAL+ttLPQAHNrsI3zZisbfha5Cvr8vg==", "dev": true, "license": "MIT", "dependencies": { "@babel/code-frame": "^7.24.7", - "@babel/generator": "^7.25.0", - "@babel/parser": "^7.25.0", + "@babel/generator": "^7.25.4", + "@babel/parser": "^7.25.4", "@babel/template": "^7.25.0", - "@babel/types": "^7.25.0", + "@babel/types": "^7.25.4", "debug": "^4.3.1", "globals": "^11.1.0" }, @@ -1306,9 +1313,9 @@ } }, "node_modules/@babel/types": { - "version": "7.25.0", - "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.25.0.tgz", - "integrity": "sha512-LcnxQSsd9aXOIgmmSpvZ/1yo46ra2ESYyqLcryaBZOghxy5qqOBjvCWP5JfkI8yl9rlxRgdLTTMCQQRcN2hdCg==", + "version": "7.25.4", + "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.25.4.tgz", + "integrity": "sha512-zQ1ijeeCXVEh+aNL0RlmkPkG8HUiDcU2pzQQFjtbntgAczRASFzj4H+6+bV+dy1ntKR14I/DypeuRG1uma98iQ==", "dev": true, "license": "MIT", "dependencies": { @@ -2038,10 +2045,20 @@ "node": "^12.0.0 || ^14.0.0 || >=16.0.0" } }, + "node_modules/@eslint/compat": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/@eslint/compat/-/compat-1.1.1.tgz", + "integrity": "sha512-lpHyRyplhGPL5mGEh6M9O5nnKk0Gz4bFI+Zu6tKlPpDUN7XshWvH9C/px4UVm87IAANE0W81CEsNGbS1KlzXpA==", + "dev": true, + "license": "Apache-2.0", + "engines": { + "node": "^18.18.0 || ^20.9.0 || >=21.1.0" + } + }, "node_modules/@eslint/config-array": { - "version": "0.17.1", - "resolved": "https://registry.npmjs.org/@eslint/config-array/-/config-array-0.17.1.tgz", - "integrity": "sha512-BlYOpej8AQ8Ev9xVqroV7a02JK3SkBAaN9GfMMH9W6Ch8FlQlkjGw4Ir7+FgYwfirivAf4t+GtzuAxqfukmISA==", + "version": "0.18.0", + "resolved": "https://registry.npmjs.org/@eslint/config-array/-/config-array-0.18.0.tgz", + "integrity": "sha512-fTxvnS1sRMu3+JjXwJG0j/i4RT9u4qJ+lqS/yCGap4lH4zZGzQ7tu+xZqQmcMZq5OBZDL4QRxQzRjkWcGt8IVw==", "dev": true, "license": "Apache-2.0", "dependencies": { @@ -2139,9 +2156,9 @@ } }, "node_modules/@eslint/js": { - "version": "9.9.0", - "resolved": "https://registry.npmjs.org/@eslint/js/-/js-9.9.0.tgz", - "integrity": "sha512-hhetes6ZHP3BlXLxmd8K2SNgkhNSi+UcecbnwWKwpP7kyi/uC75DJ1lOOBO3xrC4jyojtGE3YxKZPHfk4yrgug==", + "version": "9.9.1", + "resolved": "https://registry.npmjs.org/@eslint/js/-/js-9.9.1.tgz", + "integrity": "sha512-xIDQRsfg5hNBqHz04H1R3scSVwmI+KUbqjsQKHKQ1DAUSaUjYPReZZmS/5PNiKu1fUvzDd6H7DEDKACSEhu+TQ==", "dev": true, "license": "MIT", "engines": { @@ -3043,9 +3060,9 @@ } }, "node_modules/@rollup/rollup-android-arm-eabi": { - "version": "4.19.1", - "resolved": "https://registry.npmjs.org/@rollup/rollup-android-arm-eabi/-/rollup-android-arm-eabi-4.19.1.tgz", - "integrity": "sha512-XzqSg714++M+FXhHfXpS1tDnNZNpgxxuGZWlRG/jSj+VEPmZ0yg6jV4E0AL3uyBKxO8mO3xtOsP5mQ+XLfrlww==", + "version": "4.21.0", + "resolved": "https://registry.npmjs.org/@rollup/rollup-android-arm-eabi/-/rollup-android-arm-eabi-4.21.0.tgz", + "integrity": "sha512-WTWD8PfoSAJ+qL87lE7votj3syLavxunWhzCnx3XFxFiI/BA/r3X7MUM8dVrH8rb2r4AiO8jJsr3ZjdaftmnfA==", "cpu": [ "arm" ], @@ -3057,9 +3074,9 @@ ] }, "node_modules/@rollup/rollup-android-arm64": { - "version": "4.19.1", - "resolved": "https://registry.npmjs.org/@rollup/rollup-android-arm64/-/rollup-android-arm64-4.19.1.tgz", - "integrity": "sha512-thFUbkHteM20BGShD6P08aungq4irbIZKUNbG70LN8RkO7YztcGPiKTTGZS7Kw+x5h8hOXs0i4OaHwFxlpQN6A==", + "version": "4.21.0", + "resolved": "https://registry.npmjs.org/@rollup/rollup-android-arm64/-/rollup-android-arm64-4.21.0.tgz", + "integrity": "sha512-a1sR2zSK1B4eYkiZu17ZUZhmUQcKjk2/j9Me2IDjk1GHW7LB5Z35LEzj9iJch6gtUfsnvZs1ZNyDW2oZSThrkA==", "cpu": [ "arm64" ], @@ -3071,9 +3088,9 @@ ] }, "node_modules/@rollup/rollup-darwin-arm64": { - "version": "4.19.1", - "resolved": "https://registry.npmjs.org/@rollup/rollup-darwin-arm64/-/rollup-darwin-arm64-4.19.1.tgz", - "integrity": "sha512-8o6eqeFZzVLia2hKPUZk4jdE3zW7LCcZr+MD18tXkgBBid3lssGVAYuox8x6YHoEPDdDa9ixTaStcmx88lio5Q==", + "version": "4.21.0", + "resolved": "https://registry.npmjs.org/@rollup/rollup-darwin-arm64/-/rollup-darwin-arm64-4.21.0.tgz", + "integrity": "sha512-zOnKWLgDld/svhKO5PD9ozmL6roy5OQ5T4ThvdYZLpiOhEGY+dp2NwUmxK0Ld91LrbjrvtNAE0ERBwjqhZTRAA==", "cpu": [ "arm64" ], @@ -3085,9 +3102,9 @@ ] }, "node_modules/@rollup/rollup-darwin-x64": { - "version": "4.19.1", - "resolved": "https://registry.npmjs.org/@rollup/rollup-darwin-x64/-/rollup-darwin-x64-4.19.1.tgz", - "integrity": "sha512-4T42heKsnbjkn7ovYiAdDVRRWZLU9Kmhdt6HafZxFcUdpjlBlxj4wDrt1yFWLk7G4+E+8p2C9tcmSu0KA6auGA==", + "version": "4.21.0", + "resolved": "https://registry.npmjs.org/@rollup/rollup-darwin-x64/-/rollup-darwin-x64-4.21.0.tgz", + "integrity": "sha512-7doS8br0xAkg48SKE2QNtMSFPFUlRdw9+votl27MvT46vo44ATBmdZdGysOevNELmZlfd+NEa0UYOA8f01WSrg==", "cpu": [ "x64" ], @@ -3099,9 +3116,9 @@ ] }, "node_modules/@rollup/rollup-linux-arm-gnueabihf": { - "version": "4.19.1", - "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm-gnueabihf/-/rollup-linux-arm-gnueabihf-4.19.1.tgz", - "integrity": "sha512-MXg1xp+e5GhZ3Vit1gGEyoC+dyQUBy2JgVQ+3hUrD9wZMkUw/ywgkpK7oZgnB6kPpGrxJ41clkPPnsknuD6M2Q==", + "version": "4.21.0", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm-gnueabihf/-/rollup-linux-arm-gnueabihf-4.21.0.tgz", + "integrity": "sha512-pWJsfQjNWNGsoCq53KjMtwdJDmh/6NubwQcz52aEwLEuvx08bzcy6tOUuawAOncPnxz/3siRtd8hiQ32G1y8VA==", "cpu": [ "arm" ], @@ -3113,9 +3130,9 @@ ] }, "node_modules/@rollup/rollup-linux-arm-musleabihf": { - "version": "4.19.1", - "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm-musleabihf/-/rollup-linux-arm-musleabihf-4.19.1.tgz", - "integrity": "sha512-DZNLwIY4ftPSRVkJEaxYkq7u2zel7aah57HESuNkUnz+3bZHxwkCUkrfS2IWC1sxK6F2QNIR0Qr/YXw7nkF3Pw==", + "version": "4.21.0", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm-musleabihf/-/rollup-linux-arm-musleabihf-4.21.0.tgz", + "integrity": "sha512-efRIANsz3UHZrnZXuEvxS9LoCOWMGD1rweciD6uJQIx2myN3a8Im1FafZBzh7zk1RJ6oKcR16dU3UPldaKd83w==", "cpu": [ "arm" ], @@ -3127,9 +3144,9 @@ ] }, "node_modules/@rollup/rollup-linux-arm64-gnu": { - "version": "4.19.1", - "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm64-gnu/-/rollup-linux-arm64-gnu-4.19.1.tgz", - "integrity": "sha512-C7evongnjyxdngSDRRSQv5GvyfISizgtk9RM+z2biV5kY6S/NF/wta7K+DanmktC5DkuaJQgoKGf7KUDmA7RUw==", + "version": "4.21.0", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm64-gnu/-/rollup-linux-arm64-gnu-4.21.0.tgz", + "integrity": "sha512-ZrPhydkTVhyeGTW94WJ8pnl1uroqVHM3j3hjdquwAcWnmivjAwOYjTEAuEDeJvGX7xv3Z9GAvrBkEzCgHq9U1w==", "cpu": [ "arm64" ], @@ -3141,9 +3158,9 @@ ] }, "node_modules/@rollup/rollup-linux-arm64-musl": { - "version": "4.19.1", - "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm64-musl/-/rollup-linux-arm64-musl-4.19.1.tgz", - "integrity": "sha512-89tFWqxfxLLHkAthAcrTs9etAoBFRduNfWdl2xUs/yLV+7XDrJ5yuXMHptNqf1Zw0UCA3cAutkAiAokYCkaPtw==", + "version": "4.21.0", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm64-musl/-/rollup-linux-arm64-musl-4.21.0.tgz", + "integrity": "sha512-cfaupqd+UEFeURmqNP2eEvXqgbSox/LHOyN9/d2pSdV8xTrjdg3NgOFJCtc1vQ/jEke1qD0IejbBfxleBPHnPw==", "cpu": [ "arm64" ], @@ -3155,9 +3172,9 @@ ] }, "node_modules/@rollup/rollup-linux-powerpc64le-gnu": { - "version": "4.19.1", - "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-powerpc64le-gnu/-/rollup-linux-powerpc64le-gnu-4.19.1.tgz", - "integrity": "sha512-PromGeV50sq+YfaisG8W3fd+Cl6mnOOiNv2qKKqKCpiiEke2KiKVyDqG/Mb9GWKbYMHj5a01fq/qlUR28PFhCQ==", + "version": "4.21.0", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-powerpc64le-gnu/-/rollup-linux-powerpc64le-gnu-4.21.0.tgz", + "integrity": "sha512-ZKPan1/RvAhrUylwBXC9t7B2hXdpb/ufeu22pG2psV7RN8roOfGurEghw1ySmX/CmDDHNTDDjY3lo9hRlgtaHg==", "cpu": [ "ppc64" ], @@ -3169,9 +3186,9 @@ ] }, "node_modules/@rollup/rollup-linux-riscv64-gnu": { - "version": "4.19.1", - "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-riscv64-gnu/-/rollup-linux-riscv64-gnu-4.19.1.tgz", - "integrity": "sha512-/1BmHYh+iz0cNCP0oHCuF8CSiNj0JOGf0jRlSo3L/FAyZyG2rGBuKpkZVH9YF+x58r1jgWxvm1aRg3DHrLDt6A==", + "version": "4.21.0", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-riscv64-gnu/-/rollup-linux-riscv64-gnu-4.21.0.tgz", + "integrity": "sha512-H1eRaCwd5E8eS8leiS+o/NqMdljkcb1d6r2h4fKSsCXQilLKArq6WS7XBLDu80Yz+nMqHVFDquwcVrQmGr28rg==", "cpu": [ "riscv64" ], @@ -3183,9 +3200,9 @@ ] }, "node_modules/@rollup/rollup-linux-s390x-gnu": { - "version": "4.19.1", - "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-s390x-gnu/-/rollup-linux-s390x-gnu-4.19.1.tgz", - "integrity": "sha512-0cYP5rGkQWRZKy9/HtsWVStLXzCF3cCBTRI+qRL8Z+wkYlqN7zrSYm6FuY5Kd5ysS5aH0q5lVgb/WbG4jqXN1Q==", + "version": "4.21.0", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-s390x-gnu/-/rollup-linux-s390x-gnu-4.21.0.tgz", + "integrity": "sha512-zJ4hA+3b5tu8u7L58CCSI0A9N1vkfwPhWd/puGXwtZlsB5bTkwDNW/+JCU84+3QYmKpLi+XvHdmrlwUwDA6kqw==", "cpu": [ "s390x" ], @@ -3197,9 +3214,9 @@ ] }, "node_modules/@rollup/rollup-linux-x64-gnu": { - "version": "4.19.1", - "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-x64-gnu/-/rollup-linux-x64-gnu-4.19.1.tgz", - "integrity": "sha512-XUXeI9eM8rMP8aGvii/aOOiMvTs7xlCosq9xCjcqI9+5hBxtjDpD+7Abm1ZhVIFE1J2h2VIg0t2DX/gjespC2Q==", + "version": "4.21.0", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-x64-gnu/-/rollup-linux-x64-gnu-4.21.0.tgz", + "integrity": "sha512-e2hrvElFIh6kW/UNBQK/kzqMNY5mO+67YtEh9OA65RM5IJXYTWiXjX6fjIiPaqOkBthYF1EqgiZ6OXKcQsM0hg==", "cpu": [ "x64" ], @@ -3211,9 +3228,9 @@ ] }, "node_modules/@rollup/rollup-linux-x64-musl": { - "version": "4.19.1", - "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-x64-musl/-/rollup-linux-x64-musl-4.19.1.tgz", - "integrity": "sha512-V7cBw/cKXMfEVhpSvVZhC+iGifD6U1zJ4tbibjjN+Xi3blSXaj/rJynAkCFFQfoG6VZrAiP7uGVzL440Q6Me2Q==", + "version": "4.21.0", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-x64-musl/-/rollup-linux-x64-musl-4.21.0.tgz", + "integrity": "sha512-1vvmgDdUSebVGXWX2lIcgRebqfQSff0hMEkLJyakQ9JQUbLDkEaMsPTLOmyccyC6IJ/l3FZuJbmrBw/u0A0uCQ==", "cpu": [ "x64" ], @@ -3225,9 +3242,9 @@ ] }, "node_modules/@rollup/rollup-win32-arm64-msvc": { - "version": "4.19.1", - "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-arm64-msvc/-/rollup-win32-arm64-msvc-4.19.1.tgz", - "integrity": "sha512-88brja2vldW/76jWATlBqHEoGjJLRnP0WOEKAUbMcXaAZnemNhlAHSyj4jIwMoP2T750LE9lblvD4e2jXleZsA==", + "version": "4.21.0", + "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-arm64-msvc/-/rollup-win32-arm64-msvc-4.21.0.tgz", + "integrity": "sha512-s5oFkZ/hFcrlAyBTONFY1TWndfyre1wOMwU+6KCpm/iatybvrRgmZVM+vCFwxmC5ZhdlgfE0N4XorsDpi7/4XQ==", "cpu": [ "arm64" ], @@ -3239,9 +3256,9 @@ ] }, "node_modules/@rollup/rollup-win32-ia32-msvc": { - "version": "4.19.1", - "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-ia32-msvc/-/rollup-win32-ia32-msvc-4.19.1.tgz", - "integrity": "sha512-LdxxcqRVSXi6k6JUrTah1rHuaupoeuiv38du8Mt4r4IPer3kwlTo+RuvfE8KzZ/tL6BhaPlzJ3835i6CxrFIRQ==", + "version": "4.21.0", + "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-ia32-msvc/-/rollup-win32-ia32-msvc-4.21.0.tgz", + "integrity": "sha512-G9+TEqRnAA6nbpqyUqgTiopmnfgnMkR3kMukFBDsiyy23LZvUCpiUwjTRx6ezYCjJODXrh52rBR9oXvm+Fp5wg==", "cpu": [ "ia32" ], @@ -3253,9 +3270,9 @@ ] }, "node_modules/@rollup/rollup-win32-x64-msvc": { - "version": "4.19.1", - "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-x64-msvc/-/rollup-win32-x64-msvc-4.19.1.tgz", - "integrity": "sha512-2bIrL28PcK3YCqD9anGxDxamxdiJAxA+l7fWIwM5o8UqNy1t3d1NdAweO2XhA0KTDJ5aH1FsuiT5+7VhtHliXg==", + "version": "4.21.0", + "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-x64-msvc/-/rollup-win32-x64-msvc-4.21.0.tgz", + "integrity": "sha512-2jsCDZwtQvRhejHLfZ1JY6w6kEuEtfF9nzYsZxzSlNVKDX+DpsDJ+Rbjkm74nvg2rdx0gwBS+IMdvwJuq3S9pQ==", "cpu": [ "x64" ], @@ -3982,6 +3999,32 @@ "node": ">=10" } }, + "node_modules/@tanstack/query-core": { + "version": "5.52.0", + "resolved": "https://registry.npmjs.org/@tanstack/query-core/-/query-core-5.52.0.tgz", + "integrity": "sha512-U1DOEgltjUwalN6uWYTewSnA14b+tE7lSylOiASKCAO61ENJeCq9VVD/TXHA6O5u9+6v5+UgGYBSccTKDoyMqw==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/tannerlinsley" + } + }, + "node_modules/@tanstack/react-query": { + "version": "5.52.1", + "resolved": "https://registry.npmjs.org/@tanstack/react-query/-/react-query-5.52.1.tgz", + "integrity": "sha512-soyn4dNIUZ8US8NaPVXv06gkZFHaZnPfKWPDjRJjFRW3Y7WZ0jx72eT6zhw3VQlkMPysmXye8l35ewPHspKgbQ==", + "license": "MIT", + "dependencies": { + "@tanstack/query-core": "5.52.0" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/tannerlinsley" + }, + "peerDependencies": { + "react": "^18 || ^19" + } + }, "node_modules/@tootallnate/once": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/@tootallnate/once/-/once-2.0.0.tgz", @@ -4071,15 +4114,14 @@ "@types/json-schema": "*" } }, - "node_modules/@types/eslint-scope": { - "version": "3.7.7", - "resolved": "https://registry.npmjs.org/@types/eslint-scope/-/eslint-scope-3.7.7.tgz", - "integrity": "sha512-MzMFlSLBqNF2gcHWO0G1vP/YQyfvrxZ0bF+u7mzUdZ1/xK4A4sru+nraZz5i3iEIk1l1uyicaDVTB4QbbEkAYg==", + "node_modules/@types/eslint__js": { + "version": "8.42.3", + "resolved": "https://registry.npmjs.org/@types/eslint__js/-/eslint__js-8.42.3.tgz", + "integrity": "sha512-alfG737uhmPdnvkrLdZLcEKJ/B8s9Y4hrZ+YAdzUeoArBlSUERA2E87ROfOaS4jd/C45fzOoZzidLc1IPwLqOw==", "dev": true, "license": "MIT", "dependencies": { - "@types/eslint": "*", - "@types/estree": "*" + "@types/eslint": "*" } }, "node_modules/@types/estree": { @@ -4131,9 +4173,9 @@ "license": "MIT" }, "node_modules/@types/node": { - "version": "22.4.1", - "resolved": "https://registry.npmjs.org/@types/node/-/node-22.4.1.tgz", - "integrity": "sha512-1tbpb9325+gPnKK0dMm+/LMriX0vKxf6RnB0SZUqfyVkQ4fMgUSySqhxE/y8Jvs4NyF1yHzTfG9KlnkIODxPKg==", + "version": "22.5.0", + "resolved": "https://registry.npmjs.org/@types/node/-/node-22.5.0.tgz", + "integrity": "sha512-DkFrJOe+rfdHTqqMg0bSNlGlQ85hSoh2TPzZyhHsXnMtligRWpxUySiyw8FY14ITt24HVCiQPWxS3KO/QlGmWg==", "dev": true, "license": "MIT", "dependencies": { @@ -4159,9 +4201,9 @@ "license": "MIT" }, "node_modules/@types/react": { - "version": "18.3.3", - "resolved": "https://registry.npmjs.org/@types/react/-/react-18.3.3.tgz", - "integrity": "sha512-hti/R0pS0q1/xx+TsI73XIqk26eBsISZ2R0wUijXIngRK9R/e7Xw/cXVxQK7R5JjW+SV4zGcn5hXjudkN/pLIw==", + "version": "18.3.4", + "resolved": "https://registry.npmjs.org/@types/react/-/react-18.3.4.tgz", + "integrity": "sha512-J7W30FTdfCxDDjmfRM+/JqLHBIyl7xUIp9kwK637FGmY7+mkSFSe6L4jpZzhj5QMfLssSDP4/i75AKkrdC7/Jw==", "devOptional": true, "license": "MIT", "dependencies": { @@ -4425,6 +4467,24 @@ "resolve": "^1.10.0" } }, + "node_modules/@vercel/webpack-asset-relocator-loader/node_modules/resolve": { + "version": "1.22.8", + "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.22.8.tgz", + "integrity": "sha512-oKWePCxqpd6FlLvGV1VU0x7bkPmmCNolxzjMf4NczoDnQcIWrAF+cPtZn5i6n+RfD2d9i0tzpKnG6Yk168yIyw==", + "dev": true, + "license": "MIT", + "dependencies": { + "is-core-module": "^2.13.0", + "path-parse": "^1.0.7", + "supports-preserve-symlinks-flag": "^1.0.0" + }, + "bin": { + "resolve": "bin/resolve" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, "node_modules/@vitejs/plugin-react": { "version": "4.3.1", "resolved": "https://registry.npmjs.org/@vitejs/plugin-react/-/plugin-react-4.3.1.tgz", @@ -4933,6 +4993,14 @@ "node": ">= 6" } }, + "node_modules/archiver-utils/node_modules/isarray": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", + "integrity": "sha512-VLghIWNM6ELQzo7zwmcg0NmTVyWKYjvIeM83yjp0wRDTmUnrM678fQbcKBo6n2CJEF0szoG//ytg+TKla89ALQ==", + "dev": true, + "license": "MIT", + "peer": true + }, "node_modules/archiver-utils/node_modules/readable-stream": { "version": "2.3.8", "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.8.tgz", @@ -5152,9 +5220,9 @@ } }, "node_modules/async": { - "version": "3.2.5", - "resolved": "https://registry.npmjs.org/async/-/async-3.2.5.tgz", - "integrity": "sha512-baNZyqaaLhyLVKm/DlvdW051MSgO6b8eVfIezl9E5PqWxFgzLm/wQntEW4zOytVburDEr0JlALEpdOFwvErLsg==", + "version": "3.2.6", + "resolved": "https://registry.npmjs.org/async/-/async-3.2.6.tgz", + "integrity": "sha512-htCUDlxyyCLMgaM3xXg0C0LW2xqfuQ6p05pCEIsXuyQ+a1koYKTuBMzRNwmybfLgvJDMd0r1LTn4+E0Ti6C2AA==", "dev": true, "license": "MIT" }, @@ -6529,6 +6597,12 @@ "readable-stream": "^2.0.2" } }, + "node_modules/duplexer2/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/duplexer2/node_modules/readable-stream": { "version": "2.3.8", "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.8.tgz", @@ -6943,9 +7017,9 @@ } }, "node_modules/electron-to-chromium": { - "version": "1.5.12", - "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.5.12.tgz", - "integrity": "sha512-tIhPkdlEoCL1Y+PToq3zRNehUaKp3wBX/sr7aclAWdIWjvqAe/Im/H0SiCM4c1Q8BLPHCdoJTol+ZblflydehA==", + "version": "1.5.13", + "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.5.13.tgz", + "integrity": "sha512-lbBcvtIJ4J6sS4tb5TLp1b4LyfCdMkwStzXPyAgVgTRAsep4bvrAGaBOP7ZJtQMNJpSQ9SqG4brWOroNaQtm7Q==", "dev": true, "license": "ISC" }, @@ -7257,17 +7331,17 @@ } }, "node_modules/eslint": { - "version": "9.9.0", - "resolved": "https://registry.npmjs.org/eslint/-/eslint-9.9.0.tgz", - "integrity": "sha512-JfiKJrbx0506OEerjK2Y1QlldtBxkAlLxT5OEcRF8uaQ86noDe2k31Vw9rnSWv+MXZHj7OOUV/dA0AhdLFcyvA==", + "version": "9.9.1", + "resolved": "https://registry.npmjs.org/eslint/-/eslint-9.9.1.tgz", + "integrity": "sha512-dHvhrbfr4xFQ9/dq+jcVneZMyRYLjggWjk6RVsIiHsP8Rz6yZ8LvZ//iU4TrZF+SXWG+JkNF2OyiZRvzgRDqMg==", "dev": true, "license": "MIT", "dependencies": { "@eslint-community/eslint-utils": "^4.2.0", "@eslint-community/regexpp": "^4.11.0", - "@eslint/config-array": "^0.17.1", + "@eslint/config-array": "^0.18.0", "@eslint/eslintrc": "^3.1.0", - "@eslint/js": "9.9.0", + "@eslint/js": "9.9.1", "@humanwhocodes/module-importer": "^1.0.1", "@humanwhocodes/retry": "^0.3.0", "@nodelib/fs.walk": "^1.2.8", @@ -7350,9 +7424,9 @@ } }, "node_modules/eslint-plugin-react-refresh": { - "version": "0.4.9", - "resolved": "https://registry.npmjs.org/eslint-plugin-react-refresh/-/eslint-plugin-react-refresh-0.4.9.tgz", - "integrity": "sha512-QK49YrBAo5CLNLseZ7sZgvgTy21E6NEw22eZqc4teZfH8pxV3yXc9XXOYfUI6JNpw7mfHNkAeWtBxrTyykB6HA==", + "version": "0.4.11", + "resolved": "https://registry.npmjs.org/eslint-plugin-react-refresh/-/eslint-plugin-react-refresh-0.4.11.tgz", + "integrity": "sha512-wrAKxMbVr8qhXTtIKfXqAn5SAtRZt0aXxe5P23Fh4pUAdC6XEsybGLB8P0PI4j1yYqOgUEUlzKAGDfo7rJOjcw==", "dev": true, "license": "MIT", "peerDependencies": { @@ -7383,24 +7457,6 @@ "node": "*" } }, - "node_modules/eslint-plugin-react/node_modules/resolve": { - "version": "2.0.0-next.5", - "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", - "supports-preserve-symlinks-flag": "^1.0.0" - }, - "bin": { - "resolve": "bin/resolve" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, "node_modules/eslint-plugin-react/node_modules/semver": { "version": "6.3.1", "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.1.tgz", @@ -7909,9 +7965,9 @@ } }, "node_modules/foreground-child": { - "version": "3.2.1", - "resolved": "https://registry.npmjs.org/foreground-child/-/foreground-child-3.2.1.tgz", - "integrity": "sha512-PXUUyLqrR2XCWICfv6ukppP96sdFwWbNEnfEMt7jNsISjMsvaLNinAHNDYyvkyU+SZG2BTSbT5NjG+vZslfGTA==", + "version": "3.3.0", + "resolved": "https://registry.npmjs.org/foreground-child/-/foreground-child-3.3.0.tgz", + "integrity": "sha512-Ld2g8rrAyMYFXBhEqMz8ZAHBi4J4uS1i/CxGMDnjyFWddMXLVcDp051DZfu+t7+ab7Wv6SMqpWmyFIj5UbfFvg==", "license": "ISC", "dependencies": { "cross-spawn": "^7.0.0", @@ -8588,9 +8644,9 @@ "license": "BSD-3-Clause" }, "node_modules/ignore": { - "version": "5.3.1", - "resolved": "https://registry.npmjs.org/ignore/-/ignore-5.3.1.tgz", - "integrity": "sha512-5Fytz/IraMjqpwfd34ke28PTVMjZjJG2MPn5t7OE4eUCUNf8BAa7b5WUS9/Qvr6mwOQS7Mk6vdsMno5he+T8Xw==", + "version": "5.3.2", + "resolved": "https://registry.npmjs.org/ignore/-/ignore-5.3.2.tgz", + "integrity": "sha512-hsBTNUqQTDwkWtcdYI2i06Y/nUBEsNEDJKjWdigLvegy8kDuJAS8uRlpkkcQpyEXL0Z/pjDy5HBmMjRCJ2gq+g==", "dev": true, "license": "MIT", "engines": { @@ -8759,9 +8815,9 @@ } }, "node_modules/is-core-module": { - "version": "2.15.0", - "resolved": "https://registry.npmjs.org/is-core-module/-/is-core-module-2.15.0.tgz", - "integrity": "sha512-Dd+Lb2/zvk9SKy1TGCt1wFJFo/MWBPMX5x7KcvLajWTGuomczdQX61PvY5yK6SVACwpoexWo81IfFyoKY2QnTA==", + "version": "2.15.1", + "resolved": "https://registry.npmjs.org/is-core-module/-/is-core-module-2.15.1.tgz", + "integrity": "sha512-z0vtXSwucUJtANQWldhbtbt7BnL0vxiFjIdDLAatwhDYty2bad6s+rijD6Ri4YuYJubLzIJLUidCh09e1djEVQ==", "license": "MIT", "dependencies": { "hasown": "^2.0.2" @@ -9069,9 +9125,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/isbinaryfile": { @@ -9435,6 +9492,14 @@ "node": ">= 0.6.3" } }, + "node_modules/lazystream/node_modules/isarray": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", + "integrity": "sha512-VLghIWNM6ELQzo7zwmcg0NmTVyWKYjvIeM83yjp0wRDTmUnrM678fQbcKBo6n2CJEF0szoG//ytg+TKla89ALQ==", + "dev": true, + "license": "MIT", + "peer": true + }, "node_modules/lazystream/node_modules/readable-stream": { "version": "2.3.8", "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.8.tgz", @@ -9694,9 +9759,9 @@ } }, "node_modules/micromatch": { - "version": "4.0.7", - "resolved": "https://registry.npmjs.org/micromatch/-/micromatch-4.0.7.tgz", - "integrity": "sha512-LPP/3KorzCwBxfeUuZmaR6bG2kdeHSbe0P2tY3FLRU4vYrjYz5hI4QZwV0njUx3jeuKe67YukQ1LSPZBKDqO/Q==", + "version": "4.0.8", + "resolved": "https://registry.npmjs.org/micromatch/-/micromatch-4.0.8.tgz", + "integrity": "sha512-PXwfBhYu0hBCPw8Dn0E+WDYb7af3dSLVWKi3HGv84IdF4TyFoC0ysxFd0Goxw7nSv4T/PzEJQxsYsEiFCKo2BA==", "license": "MIT", "dependencies": { "braces": "^3.0.3", @@ -10393,6 +10458,23 @@ "postcss": "^8.0.0" } }, + "node_modules/postcss-import/node_modules/resolve": { + "version": "1.22.8", + "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.22.8.tgz", + "integrity": "sha512-oKWePCxqpd6FlLvGV1VU0x7bkPmmCNolxzjMf4NczoDnQcIWrAF+cPtZn5i6n+RfD2d9i0tzpKnG6Yk168yIyw==", + "license": "MIT", + "dependencies": { + "is-core-module": "^2.13.0", + "path-parse": "^1.0.7", + "supports-preserve-symlinks-flag": "^1.0.0" + }, + "bin": { + "resolve": "bin/resolve" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, "node_modules/postcss-js": { "version": "4.0.1", "resolved": "https://registry.npmjs.org/postcss-js/-/postcss-js-4.0.1.tgz", @@ -10485,9 +10567,9 @@ } }, "node_modules/postcss-selector-parser": { - "version": "6.1.1", - "resolved": "https://registry.npmjs.org/postcss-selector-parser/-/postcss-selector-parser-6.1.1.tgz", - "integrity": "sha512-b4dlw/9V8A71rLIDsSwVmak9z2DuBUB7CA1/wSdelNEzqsjoSPeADTWNO09lpH49Diy3/JIZ2bSPB1dI3LJCHg==", + "version": "6.1.2", + "resolved": "https://registry.npmjs.org/postcss-selector-parser/-/postcss-selector-parser-6.1.2.tgz", + "integrity": "sha512-Q8qQfPiZ+THO/3ZrOrO0cJJKfpYCagtMUkXbnEfmgUjwXg6z/WBeOyS9APBBPCTSiDV+s4SwQGu8yFsiMRIudg==", "license": "MIT", "dependencies": { "cssesc": "^3.0.0", @@ -10897,9 +10979,10 @@ } }, "node_modules/resolve": { - "version": "1.22.8", - "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.22.8.tgz", - "integrity": "sha512-oKWePCxqpd6FlLvGV1VU0x7bkPmmCNolxzjMf4NczoDnQcIWrAF+cPtZn5i6n+RfD2d9i0tzpKnG6Yk168yIyw==", + "version": "2.0.0-next.5", + "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", @@ -10983,9 +11066,9 @@ } }, "node_modules/rollup": { - "version": "4.19.1", - "resolved": "https://registry.npmjs.org/rollup/-/rollup-4.19.1.tgz", - "integrity": "sha512-K5vziVlg7hTpYfFBI+91zHBEMo6jafYXpkMlqZjg7/zhIG9iHqazBf4xz9AVdjS9BruRn280ROqLI7G3OFRIlw==", + "version": "4.21.0", + "resolved": "https://registry.npmjs.org/rollup/-/rollup-4.21.0.tgz", + "integrity": "sha512-vo+S/lfA2lMS7rZ2Qoubi6I5hwZwzXeUIctILZLbHI+laNtvhhOIon2S1JksA5UEDQ7l3vberd0fxK44lTYjbQ==", "dev": true, "license": "MIT", "dependencies": { @@ -10999,22 +11082,22 @@ "npm": ">=8.0.0" }, "optionalDependencies": { - "@rollup/rollup-android-arm-eabi": "4.19.1", - "@rollup/rollup-android-arm64": "4.19.1", - "@rollup/rollup-darwin-arm64": "4.19.1", - "@rollup/rollup-darwin-x64": "4.19.1", - "@rollup/rollup-linux-arm-gnueabihf": "4.19.1", - "@rollup/rollup-linux-arm-musleabihf": "4.19.1", - "@rollup/rollup-linux-arm64-gnu": "4.19.1", - "@rollup/rollup-linux-arm64-musl": "4.19.1", - "@rollup/rollup-linux-powerpc64le-gnu": "4.19.1", - "@rollup/rollup-linux-riscv64-gnu": "4.19.1", - "@rollup/rollup-linux-s390x-gnu": "4.19.1", - "@rollup/rollup-linux-x64-gnu": "4.19.1", - "@rollup/rollup-linux-x64-musl": "4.19.1", - "@rollup/rollup-win32-arm64-msvc": "4.19.1", - "@rollup/rollup-win32-ia32-msvc": "4.19.1", - "@rollup/rollup-win32-x64-msvc": "4.19.1", + "@rollup/rollup-android-arm-eabi": "4.21.0", + "@rollup/rollup-android-arm64": "4.21.0", + "@rollup/rollup-darwin-arm64": "4.21.0", + "@rollup/rollup-darwin-x64": "4.21.0", + "@rollup/rollup-linux-arm-gnueabihf": "4.21.0", + "@rollup/rollup-linux-arm-musleabihf": "4.21.0", + "@rollup/rollup-linux-arm64-gnu": "4.21.0", + "@rollup/rollup-linux-arm64-musl": "4.21.0", + "@rollup/rollup-linux-powerpc64le-gnu": "4.21.0", + "@rollup/rollup-linux-riscv64-gnu": "4.21.0", + "@rollup/rollup-linux-s390x-gnu": "4.21.0", + "@rollup/rollup-linux-x64-gnu": "4.21.0", + "@rollup/rollup-linux-x64-musl": "4.21.0", + "@rollup/rollup-win32-arm64-msvc": "4.21.0", + "@rollup/rollup-win32-ia32-msvc": "4.21.0", + "@rollup/rollup-win32-x64-msvc": "4.21.0", "fsevents": "~2.3.2" } }, @@ -11060,13 +11143,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", @@ -11782,6 +11858,23 @@ "tailwindcss": ">=3.0.0 || insiders" } }, + "node_modules/tailwindcss/node_modules/resolve": { + "version": "1.22.8", + "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.22.8.tgz", + "integrity": "sha512-oKWePCxqpd6FlLvGV1VU0x7bkPmmCNolxzjMf4NczoDnQcIWrAF+cPtZn5i6n+RfD2d9i0tzpKnG6Yk168yIyw==", + "license": "MIT", + "dependencies": { + "is-core-module": "^2.13.0", + "path-parse": "^1.0.7", + "supports-preserve-symlinks-flag": "^1.0.0" + }, + "bin": { + "resolve": "bin/resolve" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, "node_modules/tapable": { "version": "2.2.1", "resolved": "https://registry.npmjs.org/tapable/-/tapable-2.2.1.tgz", @@ -11885,9 +11978,9 @@ } }, "node_modules/terser": { - "version": "5.31.3", - "resolved": "https://registry.npmjs.org/terser/-/terser-5.31.3.tgz", - "integrity": "sha512-pAfYn3NIZLyZpa83ZKigvj6Rn9c/vd5KfYGX7cN1mnzqgDcxWvrU5ZtAfIKhEXz9nRecw4z3LXkjaq96/qZqAA==", + "version": "5.31.6", + "resolved": "https://registry.npmjs.org/terser/-/terser-5.31.6.tgz", + "integrity": "sha512-PQ4DAriWzKj+qgehQ7LK5bQqCFNMmlhjR2PFFLuqGCpuCAauxemVBWwWOxo3UIwWQx8+Pr61Df++r76wDmkQBg==", "dev": true, "license": "BSD-2-Clause", "dependencies": { @@ -12045,9 +12138,9 @@ "license": "Apache-2.0" }, "node_modules/tslib": { - "version": "2.6.3", - "resolved": "https://registry.npmjs.org/tslib/-/tslib-2.6.3.tgz", - "integrity": "sha512-xNvxJEOUiWPGhUuUdQgAJPKOOJfGnIyKySOc09XkKsgdUV/3E2zvwZYdejjmRgPCgcym1juLH3226yA7sEFJKQ==", + "version": "2.7.0", + "resolved": "https://registry.npmjs.org/tslib/-/tslib-2.7.0.tgz", + "integrity": "sha512-gLXCKdN1/j47AiHiOkJN69hJmcbGTHI0ImLmbYLHykhgeN0jVGola9yVjFgzCUklsZQMW55o+dW7IXv3RCXDzA==", "license": "0BSD" }, "node_modules/type-check": { @@ -12064,9 +12157,9 @@ } }, "node_modules/type-fest": { - "version": "4.23.0", - "resolved": "https://registry.npmjs.org/type-fest/-/type-fest-4.23.0.tgz", - "integrity": "sha512-ZiBujro2ohr5+Z/hZWHESLz3g08BBdrdLMieYFULJO+tWc437sn8kQsWLJoZErY8alNhxre9K4p3GURAG11n+w==", + "version": "4.25.0", + "resolved": "https://registry.npmjs.org/type-fest/-/type-fest-4.25.0.tgz", + "integrity": "sha512-bRkIGlXsnGBRBQRAY56UXBm//9qH4bmJfFvq83gSz41N282df+fjy8ofcEgc1sM8geNt5cl6mC2g9Fht1cs8Aw==", "license": "(MIT OR CC0-1.0)", "engines": { "node": ">=16" @@ -12166,6 +12259,30 @@ "node": ">=14.17" } }, + "node_modules/typescript-eslint": { + "version": "8.2.0", + "resolved": "https://registry.npmjs.org/typescript-eslint/-/typescript-eslint-8.2.0.tgz", + "integrity": "sha512-DmnqaPcML0xYwUzgNbM1XaKXpEb7BShYf2P1tkUmmcl8hyeG7Pj08Er7R9bNy6AufabywzJcOybQAtnD/c9DGw==", + "dev": true, + "license": "MIT", + "dependencies": { + "@typescript-eslint/eslint-plugin": "8.2.0", + "@typescript-eslint/parser": "8.2.0", + "@typescript-eslint/utils": "8.2.0" + }, + "engines": { + "node": "^18.18.0 || ^20.9.0 || >=21.1.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" + }, + "peerDependenciesMeta": { + "typescript": { + "optional": true + } + } + }, "node_modules/uint8array-extras": { "version": "1.4.0", "resolved": "https://registry.npmjs.org/uint8array-extras/-/uint8array-extras-1.4.0.tgz", @@ -12369,15 +12486,15 @@ } }, "node_modules/vite": { - "version": "5.4.1", - "resolved": "https://registry.npmjs.org/vite/-/vite-5.4.1.tgz", - "integrity": "sha512-1oE6yuNXssjrZdblI9AfBbHCC41nnyoVoEZxQnID6yvQZAFBzxxkqoFLtHUMkYunL8hwOLEjgTuxpkRxvba3kA==", + "version": "5.4.2", + "resolved": "https://registry.npmjs.org/vite/-/vite-5.4.2.tgz", + "integrity": "sha512-dDrQTRHp5C1fTFzcSaMxjk6vdpKvT+2/mIdE07Gw2ykehT49O0z/VHS3zZ8iV/Gh8BJJKHWOe5RjaNrW5xf/GA==", "dev": true, "license": "MIT", "dependencies": { "esbuild": "^0.21.3", "postcss": "^8.4.41", - "rollup": "^4.13.0" + "rollup": "^4.20.0" }, "bin": { "vite": "bin/vite.js" @@ -12466,9 +12583,9 @@ } }, "node_modules/watchpack": { - "version": "2.4.1", - "resolved": "https://registry.npmjs.org/watchpack/-/watchpack-2.4.1.tgz", - "integrity": "sha512-8wrBCMtVhqcXP2Sup1ctSkga6uc2Bx0IIvKyT7yTFier5AXHooSI+QyQQAtTb7+E0IUCCKyTFmXqdqgum2XWGg==", + "version": "2.4.2", + "resolved": "https://registry.npmjs.org/watchpack/-/watchpack-2.4.2.tgz", + "integrity": "sha512-TnbFSbcOCcDgjZ4piURLCbJ3nJhznVh9kw6F6iokjiFPl8ONxe9A6nMDVXDiNbrSfLILs6vB07F7wLBrwPYzJw==", "dev": true, "license": "MIT", "dependencies": { @@ -12489,13 +12606,12 @@ } }, "node_modules/webpack": { - "version": "5.93.0", - "resolved": "https://registry.npmjs.org/webpack/-/webpack-5.93.0.tgz", - "integrity": "sha512-Y0m5oEY1LRuwly578VqluorkXbvXKh7U3rLoQCEO04M97ScRr44afGVkI0FQFsXzysk5OgFAxjZAb9rsGQVihA==", + "version": "5.94.0", + "resolved": "https://registry.npmjs.org/webpack/-/webpack-5.94.0.tgz", + "integrity": "sha512-KcsGn50VT+06JH/iunZJedYGUJS5FGjow8wb9c0v5n1Om8O1g4L6LjtfxwlXIATopoQu+vOXXa7gYisWxCoPyg==", "dev": true, "license": "MIT", "dependencies": { - "@types/eslint-scope": "^3.7.3", "@types/estree": "^1.0.5", "@webassemblyjs/ast": "^1.12.1", "@webassemblyjs/wasm-edit": "^1.12.1", @@ -12504,7 +12620,7 @@ "acorn-import-attributes": "^1.9.5", "browserslist": "^4.21.10", "chrome-trace-event": "^1.0.2", - "enhanced-resolve": "^5.17.0", + "enhanced-resolve": "^5.17.1", "es-module-lexer": "^1.2.1", "eslint-scope": "5.1.1", "events": "^3.2.0", @@ -12634,13 +12750,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 c2a8631..9e1df4b 100644 --- a/package.json +++ b/package.json @@ -26,6 +26,7 @@ "@radix-ui/react-slot": "^1.1.0", "@radix-ui/react-switch": "^1.1.0", "@radix-ui/react-tabs": "^1.1.0", + "@tanstack/react-query": "^5.52.0", "class-variance-authority": "^0.7.0", "clsx": "^2.1.1", "date-fns": "^3.6.0", @@ -47,14 +48,16 @@ "zod": "^3.23.8" }, "devDependencies": { + "@eslint/compat": "^1.1.1", + "@eslint/js": "^9.9.1", "@ianvs/prettier-plugin-sort-imports": "^4.3.1", + "@types/eslint__js": "^8.42.3", "@types/node": "^22.4.1", "@types/plist": "^3.0.5", "@types/react": "^18.3.3", "@types/react-dom": "^18.3.0", "@types/unzipper": "^0.10.10", "@types/winreg": "^1.2.36", - "@typescript-eslint/eslint-plugin": "^8.2.0", "@typescript-eslint/parser": "^8.2.0", "@vitejs/plugin-react": "^4.3.1", "autoprefixer": "^10.4.20", @@ -68,6 +71,7 @@ "prettier-plugin-tailwindcss": "^0.6.6", "tailwindcss": "^3.4.10", "typescript": "^5.5.4", + "typescript-eslint": "^8.2.0", "vite": "^5.4.1", "vite-plugin-electron": "^0.28.7", "vite-plugin-electron-renderer": "^0.14.5", diff --git a/src/components/ui/button.tsx b/src/components/ui/button.tsx index 5152881..aa6e29b 100644 --- a/src/components/ui/button.tsx +++ b/src/components/ui/button.tsx @@ -54,4 +54,4 @@ const Button = React.forwardRef( ); Button.displayName = "Button"; -export { Button, buttonVariants }; +export { Button }; diff --git a/src/components/ui/tabs.tsx b/src/components/ui/tabs.tsx index 7a3d9dc..3a772cb 100644 --- a/src/components/ui/tabs.tsx +++ b/src/components/ui/tabs.tsx @@ -1,11 +1,11 @@ -"use client" +"use client"; -import * as React from "react" -import * as TabsPrimitive from "@radix-ui/react-tabs" +import * as React from "react"; +import * as TabsPrimitive from "@radix-ui/react-tabs"; -import { cn } from "~/utils" +import { cn } from "~/utils"; -const Tabs = TabsPrimitive.Root +const Tabs = TabsPrimitive.Root; const TabsList = React.forwardRef< React.ElementRef, @@ -15,12 +15,12 @@ const TabsList = React.forwardRef< ref={ref} className={cn( "inline-flex h-10 items-center justify-center rounded-md bg-muted p-1 text-muted-foreground", - className + className, )} {...props} /> -)) -TabsList.displayName = TabsPrimitive.List.displayName +)); +TabsList.displayName = TabsPrimitive.List.displayName; const TabsTrigger = React.forwardRef< React.ElementRef, @@ -30,12 +30,12 @@ const TabsTrigger = React.forwardRef< ref={ref} className={cn( "inline-flex items-center justify-center whitespace-nowrap rounded-sm px-3 py-1.5 text-sm font-medium ring-offset-background transition-all focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring focus-visible:ring-offset-2 disabled:pointer-events-none disabled:opacity-50 data-[state=active]:bg-background data-[state=active]:text-foreground data-[state=active]:shadow-sm", - className + className, )} {...props} /> -)) -TabsTrigger.displayName = TabsPrimitive.Trigger.displayName +)); +TabsTrigger.displayName = TabsPrimitive.Trigger.displayName; const TabsContent = React.forwardRef< React.ElementRef, @@ -45,11 +45,11 @@ const TabsContent = React.forwardRef< ref={ref} className={cn( "mt-2 ring-offset-background focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring focus-visible:ring-offset-2", - className + className, )} {...props} /> -)) -TabsContent.displayName = TabsPrimitive.Content.displayName +)); +TabsContent.displayName = TabsPrimitive.Content.displayName; -export { Tabs, TabsList, TabsTrigger, TabsContent } +export { Tabs, TabsList, TabsTrigger, TabsContent }; diff --git a/src/components/ui/textarea.tsx b/src/components/ui/textarea.tsx index 5fbebb8..f74ac29 100644 --- a/src/components/ui/textarea.tsx +++ b/src/components/ui/textarea.tsx @@ -1,6 +1,6 @@ -import * as React from "react" +import * as React from "react"; -import { cn } from "~/utils" +import { cn } from "~/utils"; export interface TextareaProps extends React.TextareaHTMLAttributes {} @@ -11,14 +11,14 @@ const Textarea = React.forwardRef(