From fc3f297427cc791d6f50ec6b6f0471bb2b8af820 Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Tue, 23 Dec 2025 11:24:14 +0000 Subject: [PATCH 1/7] Initial plan From bb8fc8f607f6974ffb63a2008fc6fe4371841bab Mon Sep 17 00:00:00 2001 From: nicobrauchtgit Date: Fri, 12 Dec 2025 15:43:19 +0100 Subject: [PATCH 2/7] save --- .github/ISSUE_TEMPLATE/UI_issues.yml | 2 +- .github/ISSUE_TEMPLATE/bug_report.yml | 11 +- .github/ISSUE_TEMPLATE/feature_request.yml | 5 +- .gitignore | 2 + AGENTS.md | 47 + README.md | 8 +- biome.json | 33 +- bun.lock | 631 ++++++++++++++ manifest.json | 16 +- package.json | 77 +- src/SmartSecondBrain.ts | 478 +++++----- src/components/Chat/ChatList.svelte | 90 ++ src/components/Chat/Input.svelte | 411 ++++++--- src/components/Chat/MessageContainer.svelte | 175 +++- .../Chat/QuickSettingsDrawer.svelte | 205 ++--- src/components/Chat/Toolbar.svelte | 46 + src/components/Logos/Logo.svelte | 6 +- src/components/Logos/LogoDetailed.svelte | 2 +- .../Modal/ExcludeFoldersModal.svelte | 126 +++ src/components/Modal/ExcludeFoldersModal.ts | 25 + src/components/Modal/FolderSuggest.svelte | 97 +++ src/components/Modal/RemoveModal.svelte | 40 +- src/components/Modal/RemoveModal.ts | 37 +- src/components/QueryClientProvider.svelte | 18 + .../Settings/ConfiguredProvider.svelte | 171 ++++ src/components/Settings/ConfirmModal.svelte | 23 +- src/components/Settings/ConfirmModal.ts | 82 +- src/components/Settings/ProviderSetup.svelte | 64 ++ .../Settings/SettingContainer.svelte | 29 +- src/components/base/Button.svelte | 53 +- src/components/base/DotAnimation.svelte | 8 +- src/components/base/Dropdown.svelte | 45 +- src/components/base/FilePopover.svelte | 83 ++ src/components/base/Icon.svelte | 28 + src/components/base/LoadingAnimation.svelte | 0 src/components/base/ProgressBar.svelte | 21 +- src/components/base/ProgressCircle.svelte | 28 +- src/components/base/Slider.svelte | 20 +- src/components/base/Suggestion.svelte | 17 + src/components/base/Text.svelte | 53 +- src/components/base/Toggle.svelte | 14 +- src/components/bitui/Dropdown.svelte | 75 ++ src/components/bitui/ModelPopover.svelte | 152 ++++ src/components/icons/GenericAIIcon.svelte | 17 + src/components/icons/ProviderIcon.svelte | 33 + src/constants/defaults.ts | 97 +++ src/controller/Messages.ts | 358 ++++---- src/db/chatDbSchema.ts | 50 ++ src/db/dexieChatDb.ts | 482 ++++++++++ src/db/persistance.ts | 181 ++++ src/lang/de.json | 8 +- src/lang/en.json | 463 +++++----- src/lang/i18n.ts | 21 +- src/lib/query.ts | 17 + src/logging.ts | 34 +- src/main.ts | 531 +++++------ src/stores/chatStore.svelte.ts | 601 +++++++++++++ src/stores/dataStore.svelte.ts | 412 +++++++++ src/stores/state.svelte.ts | 57 ++ src/stores/store.ts | 41 + src/styles.css | 4 + src/types/providers.ts | 119 +++ src/utils/Dots.svelte | 50 ++ src/utils/dataValidation.ts | 824 ++++++++++++++++++ src/utils/utils.ts | 50 ++ src/utils/uuid7Validator.ts | 27 + src/utils/wikiLinkExtraction.ts | 56 ++ src/views/Chat/Chat.svelte | 41 + src/views/Chat/Chat.ts | 52 ++ .../ChatModelManagement.svelte | 166 ++++ .../ChatModelManagement.ts | 53 ++ .../EmbedModelManagement.svelte | 141 +++ .../EmbedModelManagement.ts | 53 ++ src/views/ProviderSetup/ProviderSetup.svelte | 149 ++++ src/views/ProviderSetup/ProviderSetup.ts | 49 ++ src/views/Settings/Settings.svelte | 143 +++ src/views/Settings/Settings.ts | 41 + svelte.config.ts | 19 +- tailwind.config.js | 86 +- tsconfig.json | 15 +- versions.json | 36 +- vite.config.ts | 117 +-- 82 files changed, 7751 insertions(+), 1497 deletions(-) create mode 100644 AGENTS.md create mode 100644 bun.lock mode change 100644 => 100755 src/SmartSecondBrain.ts create mode 100644 src/components/Chat/ChatList.svelte mode change 100644 => 100755 src/components/Chat/Input.svelte mode change 100644 => 100755 src/components/Chat/MessageContainer.svelte mode change 100644 => 100755 src/components/Chat/QuickSettingsDrawer.svelte create mode 100644 src/components/Chat/Toolbar.svelte mode change 100644 => 100755 src/components/Logos/Logo.svelte mode change 100644 => 100755 src/components/Logos/LogoDetailed.svelte create mode 100644 src/components/Modal/ExcludeFoldersModal.svelte create mode 100644 src/components/Modal/ExcludeFoldersModal.ts create mode 100644 src/components/Modal/FolderSuggest.svelte mode change 100644 => 100755 src/components/Modal/RemoveModal.svelte mode change 100644 => 100755 src/components/Modal/RemoveModal.ts create mode 100644 src/components/QueryClientProvider.svelte create mode 100644 src/components/Settings/ConfiguredProvider.svelte mode change 100644 => 100755 src/components/Settings/ConfirmModal.svelte mode change 100644 => 100755 src/components/Settings/ConfirmModal.ts create mode 100755 src/components/Settings/ProviderSetup.svelte mode change 100644 => 100755 src/components/Settings/SettingContainer.svelte mode change 100644 => 100755 src/components/base/Button.svelte mode change 100644 => 100755 src/components/base/DotAnimation.svelte mode change 100644 => 100755 src/components/base/Dropdown.svelte create mode 100644 src/components/base/FilePopover.svelte create mode 100644 src/components/base/Icon.svelte mode change 100644 => 100755 src/components/base/LoadingAnimation.svelte mode change 100644 => 100755 src/components/base/ProgressBar.svelte mode change 100644 => 100755 src/components/base/ProgressCircle.svelte mode change 100644 => 100755 src/components/base/Slider.svelte create mode 100644 src/components/base/Suggestion.svelte mode change 100644 => 100755 src/components/base/Text.svelte mode change 100644 => 100755 src/components/base/Toggle.svelte create mode 100644 src/components/bitui/Dropdown.svelte create mode 100644 src/components/bitui/ModelPopover.svelte create mode 100644 src/components/icons/GenericAIIcon.svelte create mode 100644 src/components/icons/ProviderIcon.svelte create mode 100644 src/constants/defaults.ts mode change 100644 => 100755 src/controller/Messages.ts create mode 100644 src/db/chatDbSchema.ts create mode 100644 src/db/dexieChatDb.ts create mode 100644 src/db/persistance.ts mode change 100644 => 100755 src/lang/de.json mode change 100644 => 100755 src/lang/en.json mode change 100644 => 100755 src/lang/i18n.ts create mode 100644 src/lib/query.ts mode change 100644 => 100755 src/logging.ts mode change 100644 => 100755 src/main.ts create mode 100644 src/stores/chatStore.svelte.ts create mode 100644 src/stores/dataStore.svelte.ts create mode 100644 src/stores/state.svelte.ts create mode 100755 src/stores/store.ts mode change 100644 => 100755 src/styles.css create mode 100644 src/types/providers.ts create mode 100644 src/utils/Dots.svelte create mode 100644 src/utils/dataValidation.ts create mode 100644 src/utils/utils.ts create mode 100644 src/utils/uuid7Validator.ts create mode 100644 src/utils/wikiLinkExtraction.ts create mode 100755 src/views/Chat/Chat.svelte create mode 100755 src/views/Chat/Chat.ts create mode 100644 src/views/ChatModelManagement/ChatModelManagement.svelte create mode 100644 src/views/ChatModelManagement/ChatModelManagement.ts create mode 100644 src/views/EmbedModelManagement/EmbedModelManagement.svelte create mode 100644 src/views/EmbedModelManagement/EmbedModelManagement.ts create mode 100644 src/views/ProviderSetup/ProviderSetup.svelte create mode 100644 src/views/ProviderSetup/ProviderSetup.ts create mode 100755 src/views/Settings/Settings.svelte create mode 100755 src/views/Settings/Settings.ts diff --git a/.github/ISSUE_TEMPLATE/UI_issues.yml b/.github/ISSUE_TEMPLATE/UI_issues.yml index eb6e830f..c719ea20 100644 --- a/.github/ISSUE_TEMPLATE/UI_issues.yml +++ b/.github/ISSUE_TEMPLATE/UI_issues.yml @@ -1,5 +1,5 @@ -name: 🎨 UI Issue +name: UI Issue description: "Use this template if something looks weird or you would like some styles changed." title: "UI issue" labels: ["styles"] diff --git a/.github/ISSUE_TEMPLATE/bug_report.yml b/.github/ISSUE_TEMPLATE/bug_report.yml index df356d00..10126a0c 100644 --- a/.github/ISSUE_TEMPLATE/bug_report.yml +++ b/.github/ISSUE_TEMPLATE/bug_report.yml @@ -1,5 +1,6 @@ -name: 🐛 Bug Report +name: Bug Report description: "Create a bug report for obsidian smart second brain to help us improve" +title: "Bug report" labels: ["bug"] assignees: ["leo310", "nicobrauchtgit"] body: @@ -21,14 +22,6 @@ body: label: Error Statement description: Enable Settings > Advanced > Developer Console logging. Open Developer Tools (⌘ Cmd + ⌥ Opt + I / Ctrl + Shift + I). Open Console Tab. placeholder: Obsidian Developer Console - - type: textarea - id: steps-to-reproduce - attributes: - label: Steps to Reproduce - description: List the steps to reproduce the behavior. - placeholder: "1. Go to '...'\n2. Click on '...'\n3. Scroll down to '...'\n4. See error" - validations: - required: true - type: input id: version attributes: diff --git a/.github/ISSUE_TEMPLATE/feature_request.yml b/.github/ISSUE_TEMPLATE/feature_request.yml index 38aca0ce..404a826f 100644 --- a/.github/ISSUE_TEMPLATE/feature_request.yml +++ b/.github/ISSUE_TEMPLATE/feature_request.yml @@ -1,5 +1,6 @@ -name: 🌟 Feature Request -description: What would you like to see added to smart second brain? 🐙 +name: Feature Request +description: What would you like to see added to smart second brain? +title: Feature Request labels: - enhancement assignees: diff --git a/.gitignore b/.gitignore index 508dfbe0..a55889d3 100644 --- a/.gitignore +++ b/.gitignore @@ -25,3 +25,5 @@ workspace.json *.njsproj *.sln *.sw? +.envrc +.direnv/* \ No newline at end of file diff --git a/AGENTS.md b/AGENTS.md new file mode 100644 index 00000000..64c8a391 --- /dev/null +++ b/AGENTS.md @@ -0,0 +1,47 @@ +# Agent Guidelines (Project Memory) + +Scope: Root of this repository. Applies to all files unless overridden by a deeper AGENTS.md. + +## Core Tech & Syntax +- Use Svelte 5 exclusively. Prefer modern Svelte 5 runes and deep reactivity. +- Runes to use: `$state`, `$props`, `$derived`, `$effect`. Avoid legacy patterns in new code. +- Do not introduce older Svelte 3/4 syntax when runes provide equivalents. + +## Formatting & Linting +- Use Biome for formatting and linting. +- Allowed commands: `biome format --write ./src`, `biome lint --apply-unsafe ./src`. +- Do not add or use ESLint, Prettier, or other linters/formatters. + +## Accessibility Warnings +- Globally suppress Svelte a11y warnings via `onwarn` in both the Vite Svelte plugin and `svelte.config.ts`. +- No per-file a11y comments are required; use them only if needed for non-a11y warnings. + +## TailwindCSS +- Preflight is disabled. Do not enable it. +- Use Obsidian CSS variables (e.g., `var(--color-accent)`, `var(--color-base-XX)`). +- Slate color keys must be strings: `"00"`, `"05"`, `10`, `20`, ..., `100`. +- Content globs: `./src/**/*.{js,svelte,ts}`. + +## Build & Output (Vite) +- Library build targeting Obsidian: single CJS output. +- Output filenames: `main.js` (JS) and `styles.css` (CSS). +- Force single bundle: `manualChunks: undefined`, `inlineDynamicImports: true`. +- `outDir` depends on mode (`development` → `./build/smart-second-brain/`, `production` → `./build/prod`). +- `emptyOutDir` only in production: `mode === "production"`. +- Source maps enabled as configured; `sourcemapBaseUrl` computed without Node globals: + - `sourcemapBaseUrl: new URL(setOutDir(mode), import.meta.url).toString()`. +- Externalize Obsidian/Electron/Codemirror/Lezer/builtin modules. + +## CI & Releases +- No CI workflows at the moment. Do not add or modify CI without explicit request. +- Releases are manual or to be reintroduced later. + +## Development Practices +- Make minimal, surgical changes. Avoid unrelated refactors. +- Do not add license/copyright headers. +- Follow existing project structure under `src/components`, `src/stores`, `src/views`, etc. +- Prefer Bun for install/build if scripts are run (e.g., `bun install`, `bun run build`). + +## Dependencies +- Leave dependency sources/configuration unchanged unless explicitly asked. +- Local `papa-ts` usage may exist; do not alter unless requested. diff --git a/README.md b/README.md index 9b0f965c..094e5698 100644 --- a/README.md +++ b/README.md @@ -48,19 +48,17 @@ Follow the onboarding instructions provided on initial plugin startup in Obsidia # ⚙️ Under the hood -Check out our [Architecture Wiki](https://github.com/your-papa/obsidian-Smart2Brain/wiki) page and our backend repo [papa-ts](https://github.com/your-papa/papa-ts). +Check out our [Architecture Wiki](https://github.com/your-papa/obsidian-Smart2Brain/wiki) page. # 🎯 Roadmap -- Support Gemini and Claude models and OpenAI likes (Openrouter...) +- Support Gemini and Claude models and integrate KoboldCpp - Similar note connections view - Chat Threads -- Hybrid Vector Search (e.g. for Time-based retrieval) -- Inline AI Assistant +- Hybrid Vector Search - Predictive Note Placement - Agent with Obsidian tooling - Multimodality -- Benchmarking # 🧑‍💻 About us diff --git a/biome.json b/biome.json index eed16bc9..b07953a3 100644 --- a/biome.json +++ b/biome.json @@ -1,12 +1,25 @@ { - "$schema": "https://biomejs.dev/schemas/1.2.2/schema.json", - "organizeImports": { - "enabled": true - }, - "linter": { - "enabled": true, - "rules": { - "recommended": true - } - } + "$schema": "https://biomejs.dev/schemas/1.9.4/schema.json", + "organizeImports": { + "enabled": true + }, + "linter": { + "enabled": true, + "rules": { + "recommended": true + } + }, + "formatter": { + "enabled": true, + "formatWithErrors": false, + "indentStyle": "tab", + "indentWidth": 4, + "lineWidth": 120 + }, + "javascript": { + "formatter": { + "semicolons": "always", + "trailingCommas": "all" + } + } } diff --git a/bun.lock b/bun.lock new file mode 100644 index 00000000..4c53ac7b --- /dev/null +++ b/bun.lock @@ -0,0 +1,631 @@ +{ + "lockfileVersion": 1, + "workspaces": { + "": { + "name": "smart-second-brain", + "dependencies": { + "@selemondev/svgl-svelte": "^0.0.3", + "@tanstack/svelte-query": "https://pkg.pr.new/@tanstack/svelte-query@746b9c5d83e901deb3a5ca7012a4b4e2b617c5e3", + "bits-ui": "^2.11.4", + "builtin-modules": "^5.0.0", + "dexie": "^4.2.0", + "i18next": "^23.16.8", + "monkey-around": "^3.0.0", + "papa-ts": "link:papa-ts", + "svelte-i18n": "^4.0.1", + "uuid": "^11.1.0", + }, + "devDependencies": { + "@biomejs/biome": "^1.9.4", + "@sveltejs/vite-plugin-svelte": "^5.1.1", + "@tsconfig/svelte": "^5.0.5", + "autoprefixer": "^10.4.21", + "obsidian": "^1.8.7", + "postcss": "^8.5.6", + "svelte": "^5.39.4", + "svelte-check": "^4.3.2", + "tailwindcss": "^3.4.17", + "tslib": "^2.8.1", + "typescript": "^5.9.2", + "vite": "^6.3.6", + }, + }, + }, + "packages": { + "@alloc/quick-lru": ["@alloc/quick-lru@5.2.0", "", {}, "sha512-UrcABB+4bUrFABwbluTIBErXwvbsU/V7TZWfmbgJfbkwiBuziS9gxdODUyuiecfdGQ85jglMW6juS3+z5TsKLw=="], + + "@babel/runtime": ["@babel/runtime@7.27.6", "", {}, "sha512-vbavdySgbTTrmFE+EsiqUTzlOr5bzlnJtUv9PynGCAKvfQqjIXbvFdumPM/GxMDfyuGMJaJAU6TO4zc1Jf1i8Q=="], + + "@biomejs/biome": ["@biomejs/biome@1.9.4", "", { "optionalDependencies": { "@biomejs/cli-darwin-arm64": "1.9.4", "@biomejs/cli-darwin-x64": "1.9.4", "@biomejs/cli-linux-arm64": "1.9.4", "@biomejs/cli-linux-arm64-musl": "1.9.4", "@biomejs/cli-linux-x64": "1.9.4", "@biomejs/cli-linux-x64-musl": "1.9.4", "@biomejs/cli-win32-arm64": "1.9.4", "@biomejs/cli-win32-x64": "1.9.4" }, "bin": { "biome": "bin/biome" } }, "sha512-1rkd7G70+o9KkTn5KLmDYXihGoTaIGO9PIIN2ZB7UJxFrWw04CZHPYiMRjYsaDvVV7hP1dYNRLxSANLaBFGpog=="], + + "@biomejs/cli-darwin-arm64": ["@biomejs/cli-darwin-arm64@1.9.4", "", { "os": "darwin", "cpu": "arm64" }, "sha512-bFBsPWrNvkdKrNCYeAp+xo2HecOGPAy9WyNyB/jKnnedgzl4W4Hb9ZMzYNbf8dMCGmUdSavlYHiR01QaYR58cw=="], + + "@biomejs/cli-darwin-x64": ["@biomejs/cli-darwin-x64@1.9.4", "", { "os": "darwin", "cpu": "x64" }, "sha512-ngYBh/+bEedqkSevPVhLP4QfVPCpb+4BBe2p7Xs32dBgs7rh9nY2AIYUL6BgLw1JVXV8GlpKmb/hNiuIxfPfZg=="], + + "@biomejs/cli-linux-arm64": ["@biomejs/cli-linux-arm64@1.9.4", "", { "os": "linux", "cpu": "arm64" }, "sha512-fJIW0+LYujdjUgJJuwesP4EjIBl/N/TcOX3IvIHJQNsAqvV2CHIogsmA94BPG6jZATS4Hi+xv4SkBBQSt1N4/g=="], + + "@biomejs/cli-linux-arm64-musl": ["@biomejs/cli-linux-arm64-musl@1.9.4", "", { "os": "linux", "cpu": "arm64" }, "sha512-v665Ct9WCRjGa8+kTr0CzApU0+XXtRgwmzIf1SeKSGAv+2scAlW6JR5PMFo6FzqqZ64Po79cKODKf3/AAmECqA=="], + + "@biomejs/cli-linux-x64": ["@biomejs/cli-linux-x64@1.9.4", "", { "os": "linux", "cpu": "x64" }, "sha512-lRCJv/Vi3Vlwmbd6K+oQ0KhLHMAysN8lXoCI7XeHlxaajk06u7G+UsFSO01NAs5iYuWKmVZjmiOzJ0OJmGsMwg=="], + + "@biomejs/cli-linux-x64-musl": ["@biomejs/cli-linux-x64-musl@1.9.4", "", { "os": "linux", "cpu": "x64" }, "sha512-gEhi/jSBhZ2m6wjV530Yy8+fNqG8PAinM3oV7CyO+6c3CEh16Eizm21uHVsyVBEB6RIM8JHIl6AGYCv6Q6Q9Tg=="], + + "@biomejs/cli-win32-arm64": ["@biomejs/cli-win32-arm64@1.9.4", "", { "os": "win32", "cpu": "arm64" }, "sha512-tlbhLk+WXZmgwoIKwHIHEBZUwxml7bRJgk0X2sPyNR3S93cdRq6XulAZRQJ17FYGGzWne0fgrXBKpl7l4M87Hg=="], + + "@biomejs/cli-win32-x64": ["@biomejs/cli-win32-x64@1.9.4", "", { "os": "win32", "cpu": "x64" }, "sha512-8Y5wMhVIPaWe6jw2H+KlEm4wP/f7EW3810ZLmDlrEEy5KvBsb9ECEfu/kMWD484ijfQ8+nIi0giMgu9g1UAuuA=="], + + "@codemirror/state": ["@codemirror/state@6.5.2", "", { "dependencies": { "@marijn/find-cluster-break": "^1.0.0" } }, "sha512-FVqsPqtPWKVVL3dPSxy8wEF/ymIEuVzF1PK3VbUgrxXpJUSHQWWZz4JMToquRxnkw+36LTamCZG2iua2Ptq0fA=="], + + "@codemirror/view": ["@codemirror/view@6.37.1", "", { "dependencies": { "@codemirror/state": "^6.5.0", "crelt": "^1.0.6", "style-mod": "^4.1.0", "w3c-keyname": "^2.2.4" } }, "sha512-Qy4CAUwngy/VQkEz0XzMKVRcckQuqLYWKqVpDDDghBe5FSXSqfVrJn49nw3ePZHxRUz4nRmb05Lgi+9csWo4eg=="], + + "@esbuild/aix-ppc64": ["@esbuild/aix-ppc64@0.25.5", "", { "os": "aix", "cpu": "ppc64" }, "sha512-9o3TMmpmftaCMepOdA5k/yDw8SfInyzWWTjYTFCX3kPSDJMROQTb8jg+h9Cnwnmm1vOzvxN7gIfB5V2ewpjtGA=="], + + "@esbuild/android-arm": ["@esbuild/android-arm@0.25.5", "", { "os": "android", "cpu": "arm" }, "sha512-AdJKSPeEHgi7/ZhuIPtcQKr5RQdo6OO2IL87JkianiMYMPbCtot9fxPbrMiBADOWWm3T2si9stAiVsGbTQFkbA=="], + + "@esbuild/android-arm64": ["@esbuild/android-arm64@0.25.5", "", { "os": "android", "cpu": "arm64" }, "sha512-VGzGhj4lJO+TVGV1v8ntCZWJktV7SGCs3Pn1GRWI1SBFtRALoomm8k5E9Pmwg3HOAal2VDc2F9+PM/rEY6oIDg=="], + + "@esbuild/android-x64": ["@esbuild/android-x64@0.25.5", "", { "os": "android", "cpu": "x64" }, "sha512-D2GyJT1kjvO//drbRT3Hib9XPwQeWd9vZoBJn+bu/lVsOZ13cqNdDeqIF/xQ5/VmWvMduP6AmXvylO/PIc2isw=="], + + "@esbuild/darwin-arm64": ["@esbuild/darwin-arm64@0.25.5", "", { "os": "darwin", "cpu": "arm64" }, "sha512-GtaBgammVvdF7aPIgH2jxMDdivezgFu6iKpmT+48+F8Hhg5J/sfnDieg0aeG/jfSvkYQU2/pceFPDKlqZzwnfQ=="], + + "@esbuild/darwin-x64": ["@esbuild/darwin-x64@0.25.5", "", { "os": "darwin", "cpu": "x64" }, "sha512-1iT4FVL0dJ76/q1wd7XDsXrSW+oLoquptvh4CLR4kITDtqi2e/xwXwdCVH8hVHU43wgJdsq7Gxuzcs6Iq/7bxQ=="], + + "@esbuild/freebsd-arm64": ["@esbuild/freebsd-arm64@0.25.5", "", { "os": "freebsd", "cpu": "arm64" }, "sha512-nk4tGP3JThz4La38Uy/gzyXtpkPW8zSAmoUhK9xKKXdBCzKODMc2adkB2+8om9BDYugz+uGV7sLmpTYzvmz6Sw=="], + + "@esbuild/freebsd-x64": ["@esbuild/freebsd-x64@0.25.5", "", { "os": "freebsd", "cpu": "x64" }, "sha512-PrikaNjiXdR2laW6OIjlbeuCPrPaAl0IwPIaRv+SMV8CiM8i2LqVUHFC1+8eORgWyY7yhQY+2U2fA55mBzReaw=="], + + "@esbuild/linux-arm": ["@esbuild/linux-arm@0.25.5", "", { "os": "linux", "cpu": "arm" }, "sha512-cPzojwW2okgh7ZlRpcBEtsX7WBuqbLrNXqLU89GxWbNt6uIg78ET82qifUy3W6OVww6ZWobWub5oqZOVtwolfw=="], + + "@esbuild/linux-arm64": ["@esbuild/linux-arm64@0.25.5", "", { "os": "linux", "cpu": "arm64" }, "sha512-Z9kfb1v6ZlGbWj8EJk9T6czVEjjq2ntSYLY2cw6pAZl4oKtfgQuS4HOq41M/BcoLPzrUbNd+R4BXFyH//nHxVg=="], + + "@esbuild/linux-ia32": ["@esbuild/linux-ia32@0.25.5", "", { "os": "linux", "cpu": "ia32" }, "sha512-sQ7l00M8bSv36GLV95BVAdhJ2QsIbCuCjh/uYrWiMQSUuV+LpXwIqhgJDcvMTj+VsQmqAHL2yYaasENvJ7CDKA=="], + + "@esbuild/linux-loong64": ["@esbuild/linux-loong64@0.25.5", "", { "os": "linux", "cpu": "none" }, "sha512-0ur7ae16hDUC4OL5iEnDb0tZHDxYmuQyhKhsPBV8f99f6Z9KQM02g33f93rNH5A30agMS46u2HP6qTdEt6Q1kg=="], + + "@esbuild/linux-mips64el": ["@esbuild/linux-mips64el@0.25.5", "", { "os": "linux", "cpu": "none" }, "sha512-kB/66P1OsHO5zLz0i6X0RxlQ+3cu0mkxS3TKFvkb5lin6uwZ/ttOkP3Z8lfR9mJOBk14ZwZ9182SIIWFGNmqmg=="], + + "@esbuild/linux-ppc64": ["@esbuild/linux-ppc64@0.25.5", "", { "os": "linux", "cpu": "ppc64" }, "sha512-UZCmJ7r9X2fe2D6jBmkLBMQetXPXIsZjQJCjgwpVDz+YMcS6oFR27alkgGv3Oqkv07bxdvw7fyB71/olceJhkQ=="], + + "@esbuild/linux-riscv64": ["@esbuild/linux-riscv64@0.25.5", "", { "os": "linux", "cpu": "none" }, "sha512-kTxwu4mLyeOlsVIFPfQo+fQJAV9mh24xL+y+Bm6ej067sYANjyEw1dNHmvoqxJUCMnkBdKpvOn0Ahql6+4VyeA=="], + + "@esbuild/linux-s390x": ["@esbuild/linux-s390x@0.25.5", "", { "os": "linux", "cpu": "s390x" }, "sha512-K2dSKTKfmdh78uJ3NcWFiqyRrimfdinS5ErLSn3vluHNeHVnBAFWC8a4X5N+7FgVE1EjXS1QDZbpqZBjfrqMTQ=="], + + "@esbuild/linux-x64": ["@esbuild/linux-x64@0.25.5", "", { "os": "linux", "cpu": "x64" }, "sha512-uhj8N2obKTE6pSZ+aMUbqq+1nXxNjZIIjCjGLfsWvVpy7gKCOL6rsY1MhRh9zLtUtAI7vpgLMK6DxjO8Qm9lJw=="], + + "@esbuild/netbsd-arm64": ["@esbuild/netbsd-arm64@0.25.5", "", { "os": "none", "cpu": "arm64" }, "sha512-pwHtMP9viAy1oHPvgxtOv+OkduK5ugofNTVDilIzBLpoWAM16r7b/mxBvfpuQDpRQFMfuVr5aLcn4yveGvBZvw=="], + + "@esbuild/netbsd-x64": ["@esbuild/netbsd-x64@0.25.5", "", { "os": "none", "cpu": "x64" }, "sha512-WOb5fKrvVTRMfWFNCroYWWklbnXH0Q5rZppjq0vQIdlsQKuw6mdSihwSo4RV/YdQ5UCKKvBy7/0ZZYLBZKIbwQ=="], + + "@esbuild/openbsd-arm64": ["@esbuild/openbsd-arm64@0.25.5", "", { "os": "openbsd", "cpu": "arm64" }, "sha512-7A208+uQKgTxHd0G0uqZO8UjK2R0DDb4fDmERtARjSHWxqMTye4Erz4zZafx7Di9Cv+lNHYuncAkiGFySoD+Mw=="], + + "@esbuild/openbsd-x64": ["@esbuild/openbsd-x64@0.25.5", "", { "os": "openbsd", "cpu": "x64" }, "sha512-G4hE405ErTWraiZ8UiSoesH8DaCsMm0Cay4fsFWOOUcz8b8rC6uCvnagr+gnioEjWn0wC+o1/TAHt+It+MpIMg=="], + + "@esbuild/sunos-x64": ["@esbuild/sunos-x64@0.25.5", "", { "os": "sunos", "cpu": "x64" }, "sha512-l+azKShMy7FxzY0Rj4RCt5VD/q8mG/e+mDivgspo+yL8zW7qEwctQ6YqKX34DTEleFAvCIUviCFX1SDZRSyMQA=="], + + "@esbuild/win32-arm64": ["@esbuild/win32-arm64@0.25.5", "", { "os": "win32", "cpu": "arm64" }, "sha512-O2S7SNZzdcFG7eFKgvwUEZ2VG9D/sn/eIiz8XRZ1Q/DO5a3s76Xv0mdBzVM5j5R639lXQmPmSo0iRpHqUUrsxw=="], + + "@esbuild/win32-ia32": ["@esbuild/win32-ia32@0.25.5", "", { "os": "win32", "cpu": "ia32" }, "sha512-onOJ02pqs9h1iMJ1PQphR+VZv8qBMQ77Klcsqv9CNW2w6yLqoURLcgERAIurY6QE63bbLuqgP9ATqajFLK5AMQ=="], + + "@esbuild/win32-x64": ["@esbuild/win32-x64@0.25.5", "", { "os": "win32", "cpu": "x64" }, "sha512-TXv6YnJ8ZMVdX+SXWVBo/0p8LTcrUYngpWjvm91TMjjBQii7Oz11Lw5lbDV5Y0TzuhSJHwiH4hEtC1I42mMS0g=="], + + "@floating-ui/core": ["@floating-ui/core@1.7.3", "", { "dependencies": { "@floating-ui/utils": "^0.2.10" } }, "sha512-sGnvb5dmrJaKEZ+LDIpguvdX3bDlEllmv4/ClQ9awcmCZrlx5jQyyMWFM5kBI+EyNOCDDiKk8il0zeuX3Zlg/w=="], + + "@floating-ui/dom": ["@floating-ui/dom@1.7.4", "", { "dependencies": { "@floating-ui/core": "^1.7.3", "@floating-ui/utils": "^0.2.10" } }, "sha512-OOchDgh4F2CchOX94cRVqhvy7b3AFb+/rQXyswmzmGakRfkMgoWVjfnLWkRirfLEfuD4ysVW16eXzwt3jHIzKA=="], + + "@floating-ui/utils": ["@floating-ui/utils@0.2.10", "", {}, "sha512-aGTxbpbg8/b5JfU1HXSrbH3wXZuLPJcNEcZQFMxLs3oSzgtVu6nFPkbbGGUvBcUjKV2YyB9Wxxabo+HEH9tcRQ=="], + + "@formatjs/ecma402-abstract": ["@formatjs/ecma402-abstract@2.3.4", "", { "dependencies": { "@formatjs/fast-memoize": "2.2.7", "@formatjs/intl-localematcher": "0.6.1", "decimal.js": "^10.4.3", "tslib": "^2.8.0" } }, "sha512-qrycXDeaORzIqNhBOx0btnhpD1c+/qFIHAN9znofuMJX6QBwtbrmlpWfD4oiUUD2vJUOIYFA/gYtg2KAMGG7sA=="], + + "@formatjs/fast-memoize": ["@formatjs/fast-memoize@2.2.7", "", { "dependencies": { "tslib": "^2.8.0" } }, "sha512-Yabmi9nSvyOMrlSeGGWDiH7rf3a7sIwplbvo/dlz9WCIjzIQAfy1RMf4S0X3yG724n5Ghu2GmEl5NJIV6O9sZQ=="], + + "@formatjs/icu-messageformat-parser": ["@formatjs/icu-messageformat-parser@2.11.2", "", { "dependencies": { "@formatjs/ecma402-abstract": "2.3.4", "@formatjs/icu-skeleton-parser": "1.8.14", "tslib": "^2.8.0" } }, "sha512-AfiMi5NOSo2TQImsYAg8UYddsNJ/vUEv/HaNqiFjnI3ZFfWihUtD5QtuX6kHl8+H+d3qvnE/3HZrfzgdWpsLNA=="], + + "@formatjs/icu-skeleton-parser": ["@formatjs/icu-skeleton-parser@1.8.14", "", { "dependencies": { "@formatjs/ecma402-abstract": "2.3.4", "tslib": "^2.8.0" } }, "sha512-i4q4V4qslThK4Ig8SxyD76cp3+QJ3sAqr7f6q9VVfeGtxG9OhiAk3y9XF6Q41OymsKzsGQ6OQQoJNY4/lI8TcQ=="], + + "@formatjs/intl-localematcher": ["@formatjs/intl-localematcher@0.6.1", "", { "dependencies": { "tslib": "^2.8.0" } }, "sha512-ePEgLgVCqi2BBFnTMWPfIghu6FkbZnnBVhO2sSxvLfrdFw7wCHAHiDoM2h4NRgjbaY7+B7HgOLZGkK187pZTZg=="], + + "@internationalized/date": ["@internationalized/date@3.9.0", "", { "dependencies": { "@swc/helpers": "^0.5.0" } }, "sha512-yaN3brAnHRD+4KyyOsJyk49XUvj2wtbNACSqg0bz3u8t2VuzhC8Q5dfRnrSxjnnbDb+ienBnkn1TzQfE154vyg=="], + + "@isaacs/cliui": ["@isaacs/cliui@8.0.2", "", { "dependencies": { "string-width": "^5.1.2", "string-width-cjs": "npm:string-width@^4.2.0", "strip-ansi": "^7.0.1", "strip-ansi-cjs": "npm:strip-ansi@^6.0.1", "wrap-ansi": "^8.1.0", "wrap-ansi-cjs": "npm:wrap-ansi@^7.0.0" } }, "sha512-O8jcjabXaleOG9DQ0+ARXWZBTfnP4WNAqzuiJK7ll44AmxGKv/J2M4TPjxjY3znBCfvBXFzucm1twdyFybFqEA=="], + + "@jridgewell/gen-mapping": ["@jridgewell/gen-mapping@0.3.8", "", { "dependencies": { "@jridgewell/set-array": "^1.2.1", "@jridgewell/sourcemap-codec": "^1.4.10", "@jridgewell/trace-mapping": "^0.3.24" } }, "sha512-imAbBGkb+ebQyxKgzv5Hu2nmROxoDOXHh80evxdoXNOrvAnVx7zimzc1Oo5h9RlfV4vPXaE2iM5pOFbvOCClWA=="], + + "@jridgewell/remapping": ["@jridgewell/remapping@2.3.5", "", { "dependencies": { "@jridgewell/gen-mapping": "^0.3.5", "@jridgewell/trace-mapping": "^0.3.24" } }, "sha512-LI9u/+laYG4Ds1TDKSJW2YPrIlcVYOwi2fUC6xB43lueCjgxV4lffOCZCtYFiH6TNOX+tQKXx97T4IKHbhyHEQ=="], + + "@jridgewell/resolve-uri": ["@jridgewell/resolve-uri@3.1.2", "", {}, "sha512-bRISgCIjP20/tbWSPWMEi54QVPRZExkuD9lJL+UIxUKtwVJA8wW1Trb1jMs1RFXo1CBTNZ/5hpC9QvmKWdopKw=="], + + "@jridgewell/set-array": ["@jridgewell/set-array@1.2.1", "", {}, "sha512-R8gLRTZeyp03ymzP/6Lil/28tGeGEzhx1q2k703KGWRAI1VdvPIXdG70VJc2pAMw3NA6JKL5hhFu1sJX0Mnn/A=="], + + "@jridgewell/sourcemap-codec": ["@jridgewell/sourcemap-codec@1.5.0", "", {}, "sha512-gv3ZRaISU3fjPAgNsriBRqGWQL6quFx04YMPW/zD8XMLsU32mhCCbfbO6KZFLjvYpCZ8zyDEgqsgf+PwPaM7GQ=="], + + "@jridgewell/trace-mapping": ["@jridgewell/trace-mapping@0.3.25", "", { "dependencies": { "@jridgewell/resolve-uri": "^3.1.0", "@jridgewell/sourcemap-codec": "^1.4.14" } }, "sha512-vNk6aEwybGtawWmy/PzwnGDOjCkLWSD2wqvjGGAgOAwCGWySYXfYoxt00IJkTF+8Lb57DwOb3Aa0o9CApepiYQ=="], + + "@marijn/find-cluster-break": ["@marijn/find-cluster-break@1.0.2", "", {}, "sha512-l0h88YhZFyKdXIFNfSWpyjStDjGHwZ/U7iobcK1cQQD8sejsONdQtTVU+1wVN1PBw40PiiHB1vA5S7VTfQiP9g=="], + + "@nodelib/fs.scandir": ["@nodelib/fs.scandir@2.1.5", "", { "dependencies": { "@nodelib/fs.stat": "2.0.5", "run-parallel": "^1.1.9" } }, "sha512-vq24Bq3ym5HEQm2NKCr3yXDwjc7vTsEThRDnkp2DK9p1uqLR+DHurm/NOTo0KG7HYHU7eppKZj3MyqYuMBf62g=="], + + "@nodelib/fs.stat": ["@nodelib/fs.stat@2.0.5", "", {}, "sha512-RkhPPp2zrqDAQA/2jNhnztcPAlv64XdhIp7a7454A5ovI7Bukxgt7MX7udwAu3zg1DcpPU0rz3VV1SeaqvY4+A=="], + + "@nodelib/fs.walk": ["@nodelib/fs.walk@1.2.8", "", { "dependencies": { "@nodelib/fs.scandir": "2.1.5", "fastq": "^1.6.0" } }, "sha512-oGB+UxlgWcgQkgwo8GcEGwemoTFt3FIO9ababBmaGwXIoBKZ+GTy0pP185beGg7Llih/NSHSV2XAs1lnznocSg=="], + + "@pkgjs/parseargs": ["@pkgjs/parseargs@0.11.0", "", {}, "sha512-+1VkjdD0QBLPodGrJUeqarH8VAIvQODIbwh9XpP5Syisf7YoQgsJKPNFoqqLQlu+VQ/tVSshMR6loPMn8U+dPg=="], + + "@rollup/rollup-android-arm-eabi": ["@rollup/rollup-android-arm-eabi@4.41.1", "", { "os": "android", "cpu": "arm" }, "sha512-NELNvyEWZ6R9QMkiytB4/L4zSEaBC03KIXEghptLGLZWJ6VPrL63ooZQCOnlx36aQPGhzuOMwDerC1Eb2VmrLw=="], + + "@rollup/rollup-android-arm64": ["@rollup/rollup-android-arm64@4.41.1", "", { "os": "android", "cpu": "arm64" }, "sha512-DXdQe1BJ6TK47ukAoZLehRHhfKnKg9BjnQYUu9gzhI8Mwa1d2fzxA1aw2JixHVl403bwp1+/o/NhhHtxWJBgEA=="], + + "@rollup/rollup-darwin-arm64": ["@rollup/rollup-darwin-arm64@4.41.1", "", { "os": "darwin", "cpu": "arm64" }, "sha512-5afxvwszzdulsU2w8JKWwY8/sJOLPzf0e1bFuvcW5h9zsEg+RQAojdW0ux2zyYAz7R8HvvzKCjLNJhVq965U7w=="], + + "@rollup/rollup-darwin-x64": ["@rollup/rollup-darwin-x64@4.41.1", "", { "os": "darwin", "cpu": "x64" }, "sha512-egpJACny8QOdHNNMZKf8xY0Is6gIMz+tuqXlusxquWu3F833DcMwmGM7WlvCO9sB3OsPjdC4U0wHw5FabzCGZg=="], + + "@rollup/rollup-freebsd-arm64": ["@rollup/rollup-freebsd-arm64@4.41.1", "", { "os": "freebsd", "cpu": "arm64" }, "sha512-DBVMZH5vbjgRk3r0OzgjS38z+atlupJ7xfKIDJdZZL6sM6wjfDNo64aowcLPKIx7LMQi8vybB56uh1Ftck/Atg=="], + + "@rollup/rollup-freebsd-x64": ["@rollup/rollup-freebsd-x64@4.41.1", "", { "os": "freebsd", "cpu": "x64" }, "sha512-3FkydeohozEskBxNWEIbPfOE0aqQgB6ttTkJ159uWOFn42VLyfAiyD9UK5mhu+ItWzft60DycIN1Xdgiy8o/SA=="], + + "@rollup/rollup-linux-arm-gnueabihf": ["@rollup/rollup-linux-arm-gnueabihf@4.41.1", "", { "os": "linux", "cpu": "arm" }, "sha512-wC53ZNDgt0pqx5xCAgNunkTzFE8GTgdZ9EwYGVcg+jEjJdZGtq9xPjDnFgfFozQI/Xm1mh+D9YlYtl+ueswNEg=="], + + "@rollup/rollup-linux-arm-musleabihf": ["@rollup/rollup-linux-arm-musleabihf@4.41.1", "", { "os": "linux", "cpu": "arm" }, "sha512-jwKCca1gbZkZLhLRtsrka5N8sFAaxrGz/7wRJ8Wwvq3jug7toO21vWlViihG85ei7uJTpzbXZRcORotE+xyrLA=="], + + "@rollup/rollup-linux-arm64-gnu": ["@rollup/rollup-linux-arm64-gnu@4.41.1", "", { "os": "linux", "cpu": "arm64" }, "sha512-g0UBcNknsmmNQ8V2d/zD2P7WWfJKU0F1nu0k5pW4rvdb+BIqMm8ToluW/eeRmxCared5dD76lS04uL4UaNgpNA=="], + + "@rollup/rollup-linux-arm64-musl": ["@rollup/rollup-linux-arm64-musl@4.41.1", "", { "os": "linux", "cpu": "arm64" }, "sha512-XZpeGB5TKEZWzIrj7sXr+BEaSgo/ma/kCgrZgL0oo5qdB1JlTzIYQKel/RmhT6vMAvOdM2teYlAaOGJpJ9lahg=="], + + "@rollup/rollup-linux-loongarch64-gnu": ["@rollup/rollup-linux-loongarch64-gnu@4.41.1", "", { "os": "linux", "cpu": "none" }, "sha512-bkCfDJ4qzWfFRCNt5RVV4DOw6KEgFTUZi2r2RuYhGWC8WhCA8lCAJhDeAmrM/fdiAH54m0mA0Vk2FGRPyzI+tw=="], + + "@rollup/rollup-linux-powerpc64le-gnu": ["@rollup/rollup-linux-powerpc64le-gnu@4.41.1", "", { "os": "linux", "cpu": "ppc64" }, "sha512-3mr3Xm+gvMX+/8EKogIZSIEF0WUu0HL9di+YWlJpO8CQBnoLAEL/roTCxuLncEdgcfJcvA4UMOf+2dnjl4Ut1A=="], + + "@rollup/rollup-linux-riscv64-gnu": ["@rollup/rollup-linux-riscv64-gnu@4.41.1", "", { "os": "linux", "cpu": "none" }, "sha512-3rwCIh6MQ1LGrvKJitQjZFuQnT2wxfU+ivhNBzmxXTXPllewOF7JR1s2vMX/tWtUYFgphygxjqMl76q4aMotGw=="], + + "@rollup/rollup-linux-riscv64-musl": ["@rollup/rollup-linux-riscv64-musl@4.41.1", "", { "os": "linux", "cpu": "none" }, "sha512-LdIUOb3gvfmpkgFZuccNa2uYiqtgZAz3PTzjuM5bH3nvuy9ty6RGc/Q0+HDFrHrizJGVpjnTZ1yS5TNNjFlklw=="], + + "@rollup/rollup-linux-s390x-gnu": ["@rollup/rollup-linux-s390x-gnu@4.41.1", "", { "os": "linux", "cpu": "s390x" }, "sha512-oIE6M8WC9ma6xYqjvPhzZYk6NbobIURvP/lEbh7FWplcMO6gn7MM2yHKA1eC/GvYwzNKK/1LYgqzdkZ8YFxR8g=="], + + "@rollup/rollup-linux-x64-gnu": ["@rollup/rollup-linux-x64-gnu@4.41.1", "", { "os": "linux", "cpu": "x64" }, "sha512-cWBOvayNvA+SyeQMp79BHPK8ws6sHSsYnK5zDcsC3Hsxr1dgTABKjMnMslPq1DvZIp6uO7kIWhiGwaTdR4Og9A=="], + + "@rollup/rollup-linux-x64-musl": ["@rollup/rollup-linux-x64-musl@4.41.1", "", { "os": "linux", "cpu": "x64" }, "sha512-y5CbN44M+pUCdGDlZFzGGBSKCA4A/J2ZH4edTYSSxFg7ce1Xt3GtydbVKWLlzL+INfFIZAEg1ZV6hh9+QQf9YQ=="], + + "@rollup/rollup-win32-arm64-msvc": ["@rollup/rollup-win32-arm64-msvc@4.41.1", "", { "os": "win32", "cpu": "arm64" }, "sha512-lZkCxIrjlJlMt1dLO/FbpZbzt6J/A8p4DnqzSa4PWqPEUUUnzXLeki/iyPLfV0BmHItlYgHUqJe+3KiyydmiNQ=="], + + "@rollup/rollup-win32-ia32-msvc": ["@rollup/rollup-win32-ia32-msvc@4.41.1", "", { "os": "win32", "cpu": "ia32" }, "sha512-+psFT9+pIh2iuGsxFYYa/LhS5MFKmuivRsx9iPJWNSGbh2XVEjk90fmpUEjCnILPEPJnikAU6SFDiEUyOv90Pg=="], + + "@rollup/rollup-win32-x64-msvc": ["@rollup/rollup-win32-x64-msvc@4.41.1", "", { "os": "win32", "cpu": "x64" }, "sha512-Wq2zpapRYLfi4aKxf2Xff0tN+7slj2d4R87WEzqw7ZLsVvO5zwYCIuEGSZYiK41+GlwUo1HiR+GdkLEJnCKTCw=="], + + "@selemondev/svgl-svelte": ["@selemondev/svgl-svelte@0.0.3", "", { "peerDependencies": { "svelte": "^5.0.0" } }, "sha512-86WAfU6MaMrC2uLU+LhfQoH7et4dJye58jcJCaLtHsB2vNpzKslA6evveAZ+w0Pf29yr9oT0TNChjo4OQLTikQ=="], + + "@sveltejs/acorn-typescript": ["@sveltejs/acorn-typescript@1.0.5", "", { "peerDependencies": { "acorn": "^8.9.0" } }, "sha512-IwQk4yfwLdibDlrXVE04jTZYlLnwsTT2PIOQQGNLWfjavGifnk1JD1LcZjZaBTRcxZu2FfPfNLOE04DSu9lqtQ=="], + + "@sveltejs/vite-plugin-svelte": ["@sveltejs/vite-plugin-svelte@5.1.1", "", { "dependencies": { "@sveltejs/vite-plugin-svelte-inspector": "^4.0.1", "debug": "^4.4.1", "deepmerge": "^4.3.1", "kleur": "^4.1.5", "magic-string": "^0.30.17", "vitefu": "^1.0.6" }, "peerDependencies": { "svelte": "^5.0.0", "vite": "^6.0.0" } }, "sha512-Y1Cs7hhTc+a5E9Va/xwKlAJoariQyHY+5zBgCZg4PFWNYQ1nMN9sjK1zhw1gK69DuqVP++sht/1GZg1aRwmAXQ=="], + + "@sveltejs/vite-plugin-svelte-inspector": ["@sveltejs/vite-plugin-svelte-inspector@4.0.1", "", { "dependencies": { "debug": "^4.3.7" }, "peerDependencies": { "@sveltejs/vite-plugin-svelte": "^5.0.0", "svelte": "^5.0.0", "vite": "^6.0.0" } }, "sha512-J/Nmb2Q2y7mck2hyCX4ckVHcR5tu2J+MtBEQqpDrrgELZ2uvraQcK/ioCV61AqkdXFgriksOKIceDcQmqnGhVw=="], + + "@swc/helpers": ["@swc/helpers@0.5.17", "", { "dependencies": { "tslib": "^2.8.0" } }, "sha512-5IKx/Y13RsYd+sauPb2x+U/xZikHjolzfuDgTAl/Tdf3Q8rslRvC19NKDLgAJQ6wsqADk10ntlv08nPFw/gO/A=="], + + "@tanstack/query-core": ["@tanstack/query-core@https://pkg.pr.new/TanStack/query/@tanstack/query-core@746b9c5", {}], + + "@tanstack/svelte-query": ["@tanstack/svelte-query@https://pkg.pr.new/@tanstack/svelte-query@746b9c5d83e901deb3a5ca7012a4b4e2b617c5e3", { "dependencies": { "@tanstack/query-core": "https://pkg.pr.new/TanStack/query/@tanstack/query-core@746b9c5" }, "peerDependencies": { "svelte": "^5.7.0" } }], + + "@tsconfig/svelte": ["@tsconfig/svelte@5.0.5", "", {}, "sha512-48fAnUjKye38FvMiNOj0J9I/4XlQQiZlpe9xaNPfe8vy2Y1hFBt8g1yqf2EGjVvHavo4jf2lC+TQyENCr4BJBQ=="], + + "@types/codemirror": ["@types/codemirror@5.60.8", "", { "dependencies": { "@types/tern": "*" } }, "sha512-VjFgDF/eB+Aklcy15TtOTLQeMjTo07k7KAjql8OK5Dirr7a6sJY4T1uVBDuTVG9VEmn1uUsohOpYnVfgC6/jyw=="], + + "@types/estree": ["@types/estree@1.0.8", "", {}, "sha512-dWHzHa2WqEXI/O1E9OjrocMTKJl2mSrEolh1Iomrv6U+JuNwaHXsXx9bLu5gG7BUWFIN0skIQJQ/L1rIex4X6w=="], + + "@types/tern": ["@types/tern@0.23.9", "", { "dependencies": { "@types/estree": "*" } }, "sha512-ypzHFE/wBzh+BlH6rrBgS5I/Z7RD21pGhZ2rltb/+ZrVM1awdZwjx7hE5XfuYgHWk9uvV5HLZN3SloevCAp3Bw=="], + + "acorn": ["acorn@8.14.1", "", { "bin": { "acorn": "bin/acorn" } }, "sha512-OvQ/2pUDKmgfCg++xsTX1wGxfTaszcHVcTctW4UJB4hibJx2HXxxO5UmVgyjMa+ZDsiaf5wWLXYpRWMmBI0QHg=="], + + "ansi-regex": ["ansi-regex@6.1.0", "", {}, "sha512-7HSX4QQb4CspciLpVFwyRe79O3xsIZDDLER21kERQ71oaPodF8jL725AgJMFAYbooIqolJoRLuM81SpeUkpkvA=="], + + "ansi-styles": ["ansi-styles@6.2.1", "", {}, "sha512-bN798gFfQX+viw3R7yrGWRqnrN2oRkEkUjjl4JNn4E8GxxbjtG3FbrEIIY3l8/hrwUwIeCZvi4QuOTP4MErVug=="], + + "any-promise": ["any-promise@1.3.0", "", {}, "sha512-7UvmKalWRt1wgjL1RrGxoSJW/0QZFIegpeGvZG9kjp8vrRu55XTHbwnqq2GpXm9uLbcuhxm3IqX9OB4MZR1b2A=="], + + "anymatch": ["anymatch@3.1.3", "", { "dependencies": { "normalize-path": "^3.0.0", "picomatch": "^2.0.4" } }, "sha512-KMReFUr0B4t+D+OBkjR3KYqvocp2XaSzO55UcB6mgQMd3KbcE+mWTyvVV7D/zsdEbNnV6acZUutkiHQXvTr1Rw=="], + + "arg": ["arg@5.0.2", "", {}, "sha512-PYjyFOLKQ9y57JvQ6QLo8dAgNqswh8M1RMJYdQduT6xbWSgK36P/Z/v+p888pM69jMMfS8Xd8F6I1kQ/I9HUGg=="], + + "aria-query": ["aria-query@5.3.2", "", {}, "sha512-COROpnaoap1E2F000S62r6A60uHZnmlvomhfyT2DlTcrY1OrBKn2UhH7qn5wTC9zMvD0AY7csdPSNwKP+7WiQw=="], + + "autoprefixer": ["autoprefixer@10.4.21", "", { "dependencies": { "browserslist": "^4.24.4", "caniuse-lite": "^1.0.30001702", "fraction.js": "^4.3.7", "normalize-range": "^0.1.2", "picocolors": "^1.1.1", "postcss-value-parser": "^4.2.0" }, "peerDependencies": { "postcss": "^8.1.0" }, "bin": { "autoprefixer": "bin/autoprefixer" } }, "sha512-O+A6LWV5LDHSJD3LjHYoNi4VLsj/Whi7k6zG12xTYaU4cQ8oxQGckXNX8cRHK5yOZ/ppVHe0ZBXGzSV9jXdVbQ=="], + + "axobject-query": ["axobject-query@4.1.0", "", {}, "sha512-qIj0G9wZbMGNLjLmg1PT6v2mE9AH2zlnADJD/2tC6E00hgmhUOfEB6greHPAfLRSufHqROIUTkw6E+M3lH0PTQ=="], + + "balanced-match": ["balanced-match@1.0.2", "", {}, "sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw=="], + + "binary-extensions": ["binary-extensions@2.3.0", "", {}, "sha512-Ceh+7ox5qe7LJuLHoY0feh3pHuUDHAcRUeyL2VYghZwfpkNIy/+8Ocg0a3UuSoYzavmylwuLWQOf3hl0jjMMIw=="], + + "bits-ui": ["bits-ui@2.11.8", "", { "dependencies": { "@floating-ui/core": "^1.7.1", "@floating-ui/dom": "^1.7.1", "esm-env": "^1.1.2", "runed": "^0.35.1", "svelte-toolbelt": "^0.10.6", "tabbable": "^6.2.0" }, "peerDependencies": { "@internationalized/date": "^3.8.1", "svelte": "^5.33.0" } }, "sha512-zsgVH2iozBywIPJ7iF0fgp+23pGRGj0FyC9uFL4oZ83hhfaN5IEEkED7UtEf5LAjczc67zlmOIxwTRFBKvFX/Q=="], + + "brace-expansion": ["brace-expansion@2.0.1", "", { "dependencies": { "balanced-match": "^1.0.0" } }, "sha512-XnAIvQ8eM+kC6aULx6wuQiwVsnzsi9d3WxzV3FpWTGA19F621kwdbsAcFKXgKUHZWsy+mY6iL1sHTxWEFCytDA=="], + + "braces": ["braces@3.0.3", "", { "dependencies": { "fill-range": "^7.1.1" } }, "sha512-yQbXgO/OSZVD2IsiLlro+7Hf6Q18EJrKSEsdoMzKePKXct3gvD8oLcOQdIzGupr5Fj+EDe8gO/lxc1BzfMpxvA=="], + + "browserslist": ["browserslist@4.25.0", "", { "dependencies": { "caniuse-lite": "^1.0.30001718", "electron-to-chromium": "^1.5.160", "node-releases": "^2.0.19", "update-browserslist-db": "^1.1.3" }, "bin": { "browserslist": "cli.js" } }, "sha512-PJ8gYKeS5e/whHBh8xrwYK+dAvEj7JXtz6uTucnMRB8OiGTsKccFekoRrjajPBHV8oOY+2tI4uxeceSimKwMFA=="], + + "builtin-modules": ["builtin-modules@5.0.0", "", {}, "sha512-bkXY9WsVpY7CvMhKSR6pZilZu9Ln5WDrKVBUXf2S443etkmEO4V58heTecXcUIsNsi4Rx8JUO4NfX1IcQl4deg=="], + + "camelcase-css": ["camelcase-css@2.0.1", "", {}, "sha512-QOSvevhslijgYwRx6Rv7zKdMF8lbRmx+uQGx2+vDc+KI/eBnsy9kit5aj23AgGu3pa4t9AgwbnXWqS+iOY+2aA=="], + + "caniuse-lite": ["caniuse-lite@1.0.30001721", "", {}, "sha512-cOuvmUVtKrtEaoKiO0rSc29jcjwMwX5tOHDy4MgVFEWiUXj4uBMJkwI8MDySkgXidpMiHUcviogAvFi4pA2hDQ=="], + + "chokidar": ["chokidar@4.0.3", "", { "dependencies": { "readdirp": "^4.0.1" } }, "sha512-Qgzu8kfBvo+cA4962jnP1KkS6Dop5NS6g7R5LFYJr4b8Ub94PPQXUksCw9PvXoeXPRRddRNC5C1JQUR2SMGtnA=="], + + "cli-color": ["cli-color@2.0.4", "", { "dependencies": { "d": "^1.0.1", "es5-ext": "^0.10.64", "es6-iterator": "^2.0.3", "memoizee": "^0.4.15", "timers-ext": "^0.1.7" } }, "sha512-zlnpg0jNcibNrO7GG9IeHH7maWFeCz+Ja1wx/7tZNU5ASSSSZ+/qZciM0/LHCYxSdqv5h2sdbQ/PXYdOuetXvA=="], + + "clsx": ["clsx@2.1.1", "", {}, "sha512-eYm0QWBtUrBWZWG0d386OGAw16Z995PiOVo2B7bjWSbHedGl5e0ZWaq65kOGgUSNesEIDkB9ISbTg/JK9dhCZA=="], + + "color-convert": ["color-convert@2.0.1", "", { "dependencies": { "color-name": "~1.1.4" } }, "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ=="], + + "color-name": ["color-name@1.1.4", "", {}, "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA=="], + + "commander": ["commander@4.1.1", "", {}, "sha512-NOKm8xhkzAjzFx8B2v5OAHT+u5pRQc2UCa2Vq9jYL/31o2wi9mxBA7LIFs3sV5VSC49z6pEhfbMULvShKj26WA=="], + + "crelt": ["crelt@1.0.6", "", {}, "sha512-VQ2MBenTq1fWZUH9DJNGti7kKv6EeAuYr3cLwxUWhIu1baTaXh4Ib5W2CqHVqib4/MqbYGJqiL3Zb8GJZr3l4g=="], + + "cross-spawn": ["cross-spawn@7.0.6", "", { "dependencies": { "path-key": "^3.1.0", "shebang-command": "^2.0.0", "which": "^2.0.1" } }, "sha512-uV2QOWP2nWzsy2aMp8aRibhi9dlzF5Hgh5SHaB9OiTGEyDTiJJyx0uy51QXdyWbtAHNua4XJzUKca3OzKUd3vA=="], + + "cssesc": ["cssesc@3.0.0", "", { "bin": { "cssesc": "bin/cssesc" } }, "sha512-/Tb/JcjK111nNScGob5MNtsntNM1aCNUDipB/TkwZFhyDrrE47SOx/18wF2bbjgc3ZzCSKW1T5nt5EbFoAz/Vg=="], + + "d": ["d@1.0.2", "", { "dependencies": { "es5-ext": "^0.10.64", "type": "^2.7.2" } }, "sha512-MOqHvMWF9/9MX6nza0KgvFH4HpMU0EF5uUDXqX/BtxtU8NfB0QzRtJ8Oe/6SuS4kbhyzVJwjd97EA4PKrzJ8bw=="], + + "debug": ["debug@4.4.1", "", { "dependencies": { "ms": "^2.1.3" } }, "sha512-KcKCqiftBJcZr++7ykoDIEwSa3XWowTfNPo92BYxjXiyYEVrUQh2aLyhxBCwww+heortUFxEJYcRzosstTEBYQ=="], + + "decimal.js": ["decimal.js@10.5.0", "", {}, "sha512-8vDa8Qxvr/+d94hSh5P3IJwI5t8/c0KsMp+g8bNw9cY2icONa5aPfvKeieW1WlG0WQYwwhJ7mjui2xtiePQSXw=="], + + "deepmerge": ["deepmerge@4.3.1", "", {}, "sha512-3sUqbMEc77XqpdNO7FRyRog+eW3ph+GYCbj+rK+uYyRMuwsVy0rMiVtPn+QJlKFvWP/1PYpapqYn0Me2knFn+A=="], + + "dequal": ["dequal@2.0.3", "", {}, "sha512-0je+qPKHEMohvfRTCEo3CrPG6cAzAYgmzKyxRiYSSDkS6eGJdyVJm7WaYA5ECaAD9wLB2T4EEeymA5aFVcYXCA=="], + + "dexie": ["dexie@4.2.1", "", {}, "sha512-Ckej0NS6jxQ4Po3OrSQBFddayRhTCic2DoCAG5zacOfOVB9P2Q5Xc5uL/nVa7ZVs+HdMnvUPzLFCB/JwpB6Csg=="], + + "didyoumean": ["didyoumean@1.2.2", "", {}, "sha512-gxtyfqMg7GKyhQmb056K7M3xszy/myH8w+B4RT+QXBQsvAOdc3XymqDDPHx1BgPgsdAA5SIifona89YtRATDzw=="], + + "dlv": ["dlv@1.1.3", "", {}, "sha512-+HlytyjlPKnIG8XuRG8WvmBP8xs8P71y+SKKS6ZXWoEgLuePxtDoUEiH7WkdePWrQ5JBpE6aoVqfZfJUQkjXwA=="], + + "eastasianwidth": ["eastasianwidth@0.2.0", "", {}, "sha512-I88TYZWc9XiYHRQ4/3c5rjjfgkjhLyW2luGIheGERbNQ6OY7yTybanSpDXZa8y7VUP9YmDcYa+eyq4ca7iLqWA=="], + + "electron-to-chromium": ["electron-to-chromium@1.5.165", "", {}, "sha512-naiMx1Z6Nb2TxPU6fiFrUrDTjyPMLdTtaOd2oLmG8zVSg2hCWGkhPyxwk+qRmZ1ytwVqUv0u7ZcDA5+ALhaUtw=="], + + "emoji-regex": ["emoji-regex@9.2.2", "", {}, "sha512-L18DaJsXSUk2+42pv8mLs5jJT2hqFkFE4j21wOmgbUqsZ2hL72NsUU785g9RXgo3s0ZNgVl42TiHp3ZtOv/Vyg=="], + + "es5-ext": ["es5-ext@0.10.64", "", { "dependencies": { "es6-iterator": "^2.0.3", "es6-symbol": "^3.1.3", "esniff": "^2.0.1", "next-tick": "^1.1.0" } }, "sha512-p2snDhiLaXe6dahss1LddxqEm+SkuDvV8dnIQG0MWjyHpcMNfXKPE+/Cc0y+PhxJX3A4xGNeFCj5oc0BUh6deg=="], + + "es6-iterator": ["es6-iterator@2.0.3", "", { "dependencies": { "d": "1", "es5-ext": "^0.10.35", "es6-symbol": "^3.1.1" } }, "sha512-zw4SRzoUkd+cl+ZoE15A9o1oQd920Bb0iOJMQkQhl3jNc03YqVjAhG7scf9C5KWRU/R13Orf588uCC6525o02g=="], + + "es6-symbol": ["es6-symbol@3.1.4", "", { "dependencies": { "d": "^1.0.2", "ext": "^1.7.0" } }, "sha512-U9bFFjX8tFiATgtkJ1zg25+KviIXpgRvRHS8sau3GfhVzThRQrOeksPeT0BWW2MNZs1OEWJ1DPXOQMn0KKRkvg=="], + + "es6-weak-map": ["es6-weak-map@2.0.3", "", { "dependencies": { "d": "1", "es5-ext": "^0.10.46", "es6-iterator": "^2.0.3", "es6-symbol": "^3.1.1" } }, "sha512-p5um32HOTO1kP+w7PRnB+5lQ43Z6muuMuIMffvDN8ZB4GcnjLBV6zGStpbASIMk4DCAvEaamhe2zhyCb/QXXsA=="], + + "esbuild": ["esbuild@0.25.5", "", { "optionalDependencies": { "@esbuild/aix-ppc64": "0.25.5", "@esbuild/android-arm": "0.25.5", "@esbuild/android-arm64": "0.25.5", "@esbuild/android-x64": "0.25.5", "@esbuild/darwin-arm64": "0.25.5", "@esbuild/darwin-x64": "0.25.5", "@esbuild/freebsd-arm64": "0.25.5", "@esbuild/freebsd-x64": "0.25.5", "@esbuild/linux-arm": "0.25.5", "@esbuild/linux-arm64": "0.25.5", "@esbuild/linux-ia32": "0.25.5", "@esbuild/linux-loong64": "0.25.5", "@esbuild/linux-mips64el": "0.25.5", "@esbuild/linux-ppc64": "0.25.5", "@esbuild/linux-riscv64": "0.25.5", "@esbuild/linux-s390x": "0.25.5", "@esbuild/linux-x64": "0.25.5", "@esbuild/netbsd-arm64": "0.25.5", "@esbuild/netbsd-x64": "0.25.5", "@esbuild/openbsd-arm64": "0.25.5", "@esbuild/openbsd-x64": "0.25.5", "@esbuild/sunos-x64": "0.25.5", "@esbuild/win32-arm64": "0.25.5", "@esbuild/win32-ia32": "0.25.5", "@esbuild/win32-x64": "0.25.5" }, "bin": { "esbuild": "bin/esbuild" } }, "sha512-P8OtKZRv/5J5hhz0cUAdu/cLuPIKXpQl1R9pZtvmHWQvrAUVd0UNIPT4IB4W3rNOqVO0rlqHmCIbSwxh/c9yUQ=="], + + "escalade": ["escalade@3.2.0", "", {}, "sha512-WUj2qlxaQtO4g6Pq5c29GTcWGDyd8itL8zTlipgECz3JesAiiOKotd8JU6otB3PACgG6xkJUyVhboMS+bje/jA=="], + + "esm-env": ["esm-env@1.2.2", "", {}, "sha512-Epxrv+Nr/CaL4ZcFGPJIYLWFom+YeV1DqMLHJoEd9SYRxNbaFruBwfEX/kkHUJf55j2+TUbmDcmuilbP1TmXHA=="], + + "esniff": ["esniff@2.0.1", "", { "dependencies": { "d": "^1.0.1", "es5-ext": "^0.10.62", "event-emitter": "^0.3.5", "type": "^2.7.2" } }, "sha512-kTUIGKQ/mDPFoJ0oVfcmyJn4iBDRptjNVIzwIFR7tqWXdVI9xfA2RMwY/gbSpJG3lkdWNEjLap/NqVHZiJsdfg=="], + + "esrap": ["esrap@2.1.0", "", { "dependencies": { "@jridgewell/sourcemap-codec": "^1.4.15" } }, "sha512-yzmPNpl7TBbMRC5Lj2JlJZNPml0tzqoqP5B1JXycNUwtqma9AKCO0M2wHrdgsHcy1WRW7S9rJknAMtByg3usgA=="], + + "estree-walker": ["estree-walker@2.0.2", "", {}, "sha512-Rfkk/Mp/DL7JVje3u18FxFujQlTNR2q6QfMSMB7AvCBx91NGj/ba3kCfza0f6dVDbw7YlRf/nDrn7pQrCCyQ/w=="], + + "event-emitter": ["event-emitter@0.3.5", "", { "dependencies": { "d": "1", "es5-ext": "~0.10.14" } }, "sha512-D9rRn9y7kLPnJ+hMq7S/nhvoKwwvVJahBi2BPmx3bvbsEdK3W9ii8cBSGjP+72/LnM4n6fo3+dkCX5FeTQruXA=="], + + "ext": ["ext@1.7.0", "", { "dependencies": { "type": "^2.7.2" } }, "sha512-6hxeJYaL110a9b5TEJSj0gojyHQAmA2ch5Os+ySCiA1QGdS697XWY1pzsrSjqA9LDEEgdB/KypIlR59RcLuHYw=="], + + "fast-glob": ["fast-glob@3.3.3", "", { "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" } }, "sha512-7MptL8U0cqcFdzIzwOTHoilX9x5BrNqye7Z/LuC7kCMRio1EMSyqRK3BEAUD7sXRq4iT4AzTVuZdhgQ2TCvYLg=="], + + "fastq": ["fastq@1.19.1", "", { "dependencies": { "reusify": "^1.0.4" } }, "sha512-GwLTyxkCXjXbxqIhTsMI2Nui8huMPtnxg7krajPJAjnEG/iiOS7i+zCtWGZR9G0NBKbXKh6X9m9UIsYX/N6vvQ=="], + + "fdir": ["fdir@6.4.5", "", { "peerDependencies": { "picomatch": "^3 || ^4" }, "optionalPeers": ["picomatch"] }, "sha512-4BG7puHpVsIYxZUbiUE3RqGloLaSSwzYie5jvasC4LWuBWzZawynvYouhjbQKw2JuIGYdm0DzIxl8iVidKlUEw=="], + + "fill-range": ["fill-range@7.1.1", "", { "dependencies": { "to-regex-range": "^5.0.1" } }, "sha512-YsGpe3WHLK8ZYi4tWDg2Jy3ebRz2rXowDxnld4bkQB00cc/1Zw9AWnC0i9ztDJitivtQvaI9KaLyKrc+hBW0yg=="], + + "foreground-child": ["foreground-child@3.3.1", "", { "dependencies": { "cross-spawn": "^7.0.6", "signal-exit": "^4.0.1" } }, "sha512-gIXjKqtFuWEgzFRJA9WCQeSJLZDjgJUOMCMzxtvFq/37KojM1BFGufqsCy0r4qSQmYLsZYMeyRqzIWOMup03sw=="], + + "fraction.js": ["fraction.js@4.3.7", "", {}, "sha512-ZsDfxO51wGAXREY55a7la9LScWpwv9RxIrYABrlvOFBlH/ShPnrtsXeuUIfXKKOVicNxQ+o8JTbJvjS4M89yew=="], + + "fsevents": ["fsevents@2.3.3", "", { "os": "darwin" }, "sha512-5xoDfX+fL7faATnagmWPpbFtwh/R77WmMMqqHGS65C3vvB0YHrgF+B1YmZ3441tMj5n63k0212XNoJwzlhffQw=="], + + "function-bind": ["function-bind@1.1.2", "", {}, "sha512-7XHNxH7qX9xG5mIwxkhumTox/MIRNcOgDrxWsMt2pAr23WHp6MrRlN7FBSFpCpr+oVO0F744iUgR82nJMfG2SA=="], + + "glob": ["glob@10.4.5", "", { "dependencies": { "foreground-child": "^3.1.0", "jackspeak": "^3.1.2", "minimatch": "^9.0.4", "minipass": "^7.1.2", "package-json-from-dist": "^1.0.0", "path-scurry": "^1.11.1" }, "bin": { "glob": "dist/esm/bin.mjs" } }, "sha512-7Bv8RF0k6xjo7d4A/PxYLbUCfb6c+Vpd2/mB2yRDlew7Jb5hEXiCD9ibfO7wpk8i4sevK6DFny9h7EYbM3/sHg=="], + + "glob-parent": ["glob-parent@6.0.2", "", { "dependencies": { "is-glob": "^4.0.3" } }, "sha512-XxwI8EOhVQgWp6iDL+3b0r86f4d6AX6zSU55HfB4ydCEuXLXc5FcYeOu+nnGftS4TEju/11rt4KJPTMgbfmv4A=="], + + "globalyzer": ["globalyzer@0.1.0", "", {}, "sha512-40oNTM9UfG6aBmuKxk/giHn5nQ8RVz/SS4Ir6zgzOv9/qC3kKZ9v4etGTcJbEl/NyVQH7FGU7d+X1egr57Md2Q=="], + + "globrex": ["globrex@0.1.2", "", {}, "sha512-uHJgbwAMwNFf5mLst7IWLNg14x1CkeqglJb/K3doi4dw6q2IvAAmM/Y81kevy83wP+Sst+nutFTYOGg3d1lsxg=="], + + "hasown": ["hasown@2.0.2", "", { "dependencies": { "function-bind": "^1.1.2" } }, "sha512-0hJU9SCPvmMzIBdZFqNPXWa6dqh7WdH0cII9y+CyS8rG3nL48Bclra9HmKhVVUHyPWNH5Y7xDwAB7bfgSjkUMQ=="], + + "i18next": ["i18next@23.16.8", "", { "dependencies": { "@babel/runtime": "^7.23.2" } }, "sha512-06r/TitrM88Mg5FdUXAKL96dJMzgqLE5dv3ryBAra4KCwD9mJ4ndOTS95ZuymIGoE+2hzfdaMak2X11/es7ZWg=="], + + "inline-style-parser": ["inline-style-parser@0.2.4", "", {}, "sha512-0aO8FkhNZlj/ZIbNi7Lxxr12obT7cL1moPfE4tg1LkX7LlLfC6DeX4l2ZEud1ukP9jNQyNnfzQVqwbwmAATY4Q=="], + + "intl-messageformat": ["intl-messageformat@10.7.16", "", { "dependencies": { "@formatjs/ecma402-abstract": "2.3.4", "@formatjs/fast-memoize": "2.2.7", "@formatjs/icu-messageformat-parser": "2.11.2", "tslib": "^2.8.0" } }, "sha512-UmdmHUmp5CIKKjSoE10la5yfU+AYJAaiYLsodbjL4lji83JNvgOQUjGaGhGrpFCb0Uh7sl7qfP1IyILa8Z40ug=="], + + "is-binary-path": ["is-binary-path@2.1.0", "", { "dependencies": { "binary-extensions": "^2.0.0" } }, "sha512-ZMERYes6pDydyuGidse7OsHxtbI7WVeUEozgR/g7rd0xUimYNlvZRE/K2MgZTjWy725IfelLeVcEM97mmtRGXw=="], + + "is-core-module": ["is-core-module@2.16.1", "", { "dependencies": { "hasown": "^2.0.2" } }, "sha512-UfoeMA6fIJ8wTYFEUjelnaGI67v6+N7qXJEvQuIGa99l4xsCruSYOVSQ0uPANn4dAzm8lkYPaKLrrijLq7x23w=="], + + "is-extglob": ["is-extglob@2.1.1", "", {}, "sha512-SbKbANkN603Vi4jEZv49LeVJMn4yGwsbzZworEoyEiutsN3nJYdbO36zfhGJ6QEDpOZIFkDtnq5JRxmvl3jsoQ=="], + + "is-fullwidth-code-point": ["is-fullwidth-code-point@3.0.0", "", {}, "sha512-zymm5+u+sCsSWyD9qNaejV3DFvhCKclKdizYaJUuHA83RLjb7nSuGnddCHGv0hk+KY7BMAlsWeK4Ueg6EV6XQg=="], + + "is-glob": ["is-glob@4.0.3", "", { "dependencies": { "is-extglob": "^2.1.1" } }, "sha512-xelSayHH36ZgE7ZWhli7pW34hNbNl8Ojv5KVmkJD4hBdD3th8Tfk9vYasLM+mXWOZhFkgZfxhLSnrwRr4elSSg=="], + + "is-number": ["is-number@7.0.0", "", {}, "sha512-41Cifkg6e8TylSpdtTpeLVMqvSBEVzTttHvERD741+pnZ8ANv0004MRL43QKPDlK9cGvNp6NZWZUBlbGXYxxng=="], + + "is-promise": ["is-promise@2.2.2", "", {}, "sha512-+lP4/6lKUBfQjZ2pdxThZvLUAafmZb8OAxFb8XXtiQmS35INgr85hdOGoEs124ez1FCnZJt6jau/T+alh58QFQ=="], + + "is-reference": ["is-reference@3.0.3", "", { "dependencies": { "@types/estree": "^1.0.6" } }, "sha512-ixkJoqQvAP88E6wLydLGGqCJsrFUnqoH6HnaczB8XmDH1oaWU+xxdptvikTgaEhtZ53Ky6YXiBuUI2WXLMCwjw=="], + + "isexe": ["isexe@2.0.0", "", {}, "sha512-RHxMLp9lnKHGHRng9QFhRCMbYAcVpn69smSGcq3f36xjgVVWThj4qqLbTLlq7Ssj8B+fIQ1EuCEGI2lKsyQeIw=="], + + "jackspeak": ["jackspeak@3.4.3", "", { "dependencies": { "@isaacs/cliui": "^8.0.2" }, "optionalDependencies": { "@pkgjs/parseargs": "^0.11.0" } }, "sha512-OGlZQpz2yfahA/Rd1Y8Cd9SIEsqvXkLVoSw/cgwhnhFMDbsQFeZYoJJ7bIZBS9BcamUW96asq/npPWugM+RQBw=="], + + "jiti": ["jiti@1.21.7", "", { "bin": { "jiti": "bin/jiti.js" } }, "sha512-/imKNG4EbWNrVjoNC/1H5/9GFy+tqjGBHCaSsN+P2RnPqjsLmv6UD3Ej+Kj8nBWaRAwyk7kK5ZUc+OEatnTR3A=="], + + "kleur": ["kleur@4.1.5", "", {}, "sha512-o+NO+8WrRiQEE4/7nwRJhN1HWpVmJm511pBHUxPLtp0BUISzlBplORYSmTclCnJvQq2tKu/sgl3xVpkc7ZWuQQ=="], + + "lilconfig": ["lilconfig@3.1.3", "", {}, "sha512-/vlFKAoH5Cgt3Ie+JLhRbwOsCQePABiU3tJ1egGvyQ+33R/vcwM2Zl2QR/LzjsBeItPt3oSVXapn+m4nQDvpzw=="], + + "lines-and-columns": ["lines-and-columns@1.2.4", "", {}, "sha512-7ylylesZQ/PV29jhEDl3Ufjo6ZX7gCqJr5F7PKrqc93v7fzSymt1BpwEU8nAUXs8qzzvqhbjhK5QZg6Mt/HkBg=="], + + "locate-character": ["locate-character@3.0.0", "", {}, "sha512-SW13ws7BjaeJ6p7Q6CO2nchbYEc3X3J6WrmTTDto7yMPqVSZTUyY5Tjbid+Ab8gLnATtygYtiDIJGQRRn2ZOiA=="], + + "lru-cache": ["lru-cache@10.4.3", "", {}, "sha512-JNAzZcXrCt42VGLuYz0zfAzDfAvJWW6AfYlDBQyDV5DClI2m5sAmK+OIO7s59XfsRsWHp02jAJrRadPRGTt6SQ=="], + + "lru-queue": ["lru-queue@0.1.0", "", { "dependencies": { "es5-ext": "~0.10.2" } }, "sha512-BpdYkt9EvGl8OfWHDQPISVpcl5xZthb+XPsbELj5AQXxIC8IriDZIQYjBJPEm5rS420sjZ0TLEzRcq5KdBhYrQ=="], + + "lz-string": ["lz-string@1.5.0", "", { "bin": { "lz-string": "bin/bin.js" } }, "sha512-h5bgJWpxJNswbU7qCrV0tIKQCaS3blPDrqKWx+QxzuzL1zGUzij9XCWLrSLsJPu5t+eWA/ycetzYAO5IOMcWAQ=="], + + "magic-string": ["magic-string@0.30.17", "", { "dependencies": { "@jridgewell/sourcemap-codec": "^1.5.0" } }, "sha512-sNPKHvyjVf7gyjwS4xGTaW/mCnF8wnjtifKBEhxfZ7E/S8tQ0rssrwGNn6q8JH/ohItJfSQp9mBtQYuTlH5QnA=="], + + "memoizee": ["memoizee@0.4.17", "", { "dependencies": { "d": "^1.0.2", "es5-ext": "^0.10.64", "es6-weak-map": "^2.0.3", "event-emitter": "^0.3.5", "is-promise": "^2.2.2", "lru-queue": "^0.1.0", "next-tick": "^1.1.0", "timers-ext": "^0.1.7" } }, "sha512-DGqD7Hjpi/1or4F/aYAspXKNm5Yili0QDAFAY4QYvpqpgiY6+1jOfqpmByzjxbWd/T9mChbCArXAbDAsTm5oXA=="], + + "merge2": ["merge2@1.4.1", "", {}, "sha512-8q7VEgMJW4J8tcfVPy8g09NcQwZdbwFEqhe/WZkoIzjn/3TGDwtOCYtXGxA3O8tPzpczCCDgv+P2P5y00ZJOOg=="], + + "micromatch": ["micromatch@4.0.8", "", { "dependencies": { "braces": "^3.0.3", "picomatch": "^2.3.1" } }, "sha512-PXwfBhYu0hBCPw8Dn0E+WDYb7af3dSLVWKi3HGv84IdF4TyFoC0ysxFd0Goxw7nSv4T/PzEJQxsYsEiFCKo2BA=="], + + "minimatch": ["minimatch@9.0.5", "", { "dependencies": { "brace-expansion": "^2.0.1" } }, "sha512-G6T0ZX48xgozx7587koeX9Ys2NYy6Gmv//P89sEte9V9whIapMNF4idKxnW2QtCcLiTWlb/wfCabAtAFWhhBow=="], + + "minipass": ["minipass@7.1.2", "", {}, "sha512-qOOzS1cBTWYF4BH8fVePDBOO9iptMnGUEZwNc/cMWnTV2nVLZ7VoNWEPHkYczZA0pdoA7dl6e7FL659nX9S2aw=="], + + "moment": ["moment@2.29.4", "", {}, "sha512-5LC9SOxjSc2HF6vO2CyuTDNivEdoz2IvyJJGj6X8DJ0eFyfszE0QiEd+iXmBvUP3WHxSjFH/vIsA0EN00cgr8w=="], + + "monkey-around": ["monkey-around@3.0.0", "", {}, "sha512-jL6uY2lEAoaHxZep1cNRkCZjoIWY4g5VYCjriEWmcyHU7w8NU1+JH57xE251UVTohK0lCxMjv0ZV4ByDLIXEpw=="], + + "mri": ["mri@1.2.0", "", {}, "sha512-tzzskb3bG8LvYGFF/mDTpq3jpI6Q9wc3LEmBaghu+DdCssd1FakN7Bc0hVNmEyGq1bq3RgfkCb3cmQLpNPOroA=="], + + "ms": ["ms@2.1.3", "", {}, "sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA=="], + + "mz": ["mz@2.7.0", "", { "dependencies": { "any-promise": "^1.0.0", "object-assign": "^4.0.1", "thenify-all": "^1.0.0" } }, "sha512-z81GNO7nnYMEhrGh9LeymoE4+Yr0Wn5McHIZMK5cfQCl+NDX08sCZgUc9/6MHni9IWuFLm1Z3HTCXu2z9fN62Q=="], + + "nanoid": ["nanoid@3.3.11", "", { "bin": { "nanoid": "bin/nanoid.cjs" } }, "sha512-N8SpfPUnUp1bK+PMYW8qSWdl9U+wwNWI4QKxOYDy9JAro3WMX7p2OeVRF9v+347pnakNevPmiHhNmZ2HbFA76w=="], + + "next-tick": ["next-tick@1.1.0", "", {}, "sha512-CXdUiJembsNjuToQvxayPZF9Vqht7hewsvy2sOWafLvi2awflj9mOC6bHIg50orX8IJvWKY9wYQ/zB2kogPslQ=="], + + "node-releases": ["node-releases@2.0.19", "", {}, "sha512-xxOWJsBKtzAq7DY0J+DTzuz58K8e7sJbdgwkbMWQe8UYB6ekmsQ45q0M/tJDsGaZmbC+l7n57UV8Hl5tHxO9uw=="], + + "normalize-path": ["normalize-path@3.0.0", "", {}, "sha512-6eZs5Ls3WtCisHWp9S2GUy8dqkpGi4BVSz3GaqiE6ezub0512ESztXUwUB6C6IKbQkY2Pnb/mD4WYojCRwcwLA=="], + + "normalize-range": ["normalize-range@0.1.2", "", {}, "sha512-bdok/XvKII3nUpklnV6P2hxtMNrCboOjAcyBuQnWEhO665FwrSNRxU+AqpsyvO6LgGYPspN+lu5CLtw4jPRKNA=="], + + "object-assign": ["object-assign@4.1.1", "", {}, "sha512-rJgTQnkUnH1sFw8yT6VSU3zD3sWmu6sZhIseY8VX+GRu3P6F7Fu+JNDoXfklElbLJSnc3FUQHVe4cU5hj+BcUg=="], + + "object-hash": ["object-hash@3.0.0", "", {}, "sha512-RSn9F68PjH9HqtltsSnqYC1XXoWe9Bju5+213R98cNGttag9q9yAOTzdbsqvIa7aNm5WffBZFpWYr2aWrklWAw=="], + + "obsidian": ["obsidian@1.10.0", "", { "dependencies": { "@types/codemirror": "5.60.8", "moment": "2.29.4" }, "peerDependencies": { "@codemirror/state": "6.5.0", "@codemirror/view": "6.38.1" } }, "sha512-F7hhnmGRQD1TanDPFT//LD3iKNUVd7N8sKL7flCCHRszfTxpDJ39j3T7LHbcGpyid906i6lD5oO+cnfLBzJMKw=="], + + "package-json-from-dist": ["package-json-from-dist@1.0.1", "", {}, "sha512-UEZIS3/by4OC8vL3P2dTXRETpebLI2NiI5vIrjaD/5UtrkFX/tNbwjTSRAGC/+7CAo2pIcBaRgWmcBBHcsaCIw=="], + + "papa-ts": ["papa-ts@link:papa-ts", {}], + + "path-key": ["path-key@3.1.1", "", {}, "sha512-ojmeN0qd+y0jszEtoY48r0Peq5dwMEkIlCOu6Q5f41lfkswXuKtYrhgoTpLnyIcHm24Uhqx+5Tqm2InSwLhE6Q=="], + + "path-parse": ["path-parse@1.0.7", "", {}, "sha512-LDJzPVEEEPR+y48z93A0Ed0yXb8pAByGWo/k5YYdYgpY2/2EsOsksJrq7lOHxryrVOn1ejG6oAp8ahvOIQD8sw=="], + + "path-scurry": ["path-scurry@1.11.1", "", { "dependencies": { "lru-cache": "^10.2.0", "minipass": "^5.0.0 || ^6.0.2 || ^7.0.0" } }, "sha512-Xa4Nw17FS9ApQFJ9umLiJS4orGjm7ZzwUrwamcGQuHSzDyth9boKDaycYdDcZDuqYATXw4HFXgaqWTctW/v1HA=="], + + "picocolors": ["picocolors@1.1.1", "", {}, "sha512-xceH2snhtb5M9liqDsmEw56le376mTZkEX/jEb/RxNFyegNul7eNslCXP9FDj/Lcu0X8KEyMceP2ntpaHrDEVA=="], + + "picomatch": ["picomatch@4.0.2", "", {}, "sha512-M7BAV6Rlcy5u+m6oPhAPFgJTzAioX/6B0DxyvDlo9l8+T3nLKbrczg2WLUyzd45L8RqfUMyGPzekbMvX2Ldkwg=="], + + "pify": ["pify@2.3.0", "", {}, "sha512-udgsAY+fTnvv7kI7aaxbqwWNb0AHiB0qBO89PZKPkoTmGOgdbrHDKD+0B2X4uTfJ/FT1R09r9gTsjUjNJotuog=="], + + "pirates": ["pirates@4.0.7", "", {}, "sha512-TfySrs/5nm8fQJDcBDuUng3VOUKsd7S+zqvbOTiGXHfxX4wK31ard+hoNuvkicM/2YFzlpDgABOevKSsB4G/FA=="], + + "postcss": ["postcss@8.5.6", "", { "dependencies": { "nanoid": "^3.3.11", "picocolors": "^1.1.1", "source-map-js": "^1.2.1" } }, "sha512-3Ybi1tAuwAP9s0r1UQ2J4n5Y0G05bJkpUIO0/bI9MhwmD70S5aTWbXGBwxHrelT+XM1k6dM0pk+SwNkpTRN7Pg=="], + + "postcss-import": ["postcss-import@15.1.0", "", { "dependencies": { "postcss-value-parser": "^4.0.0", "read-cache": "^1.0.0", "resolve": "^1.1.7" }, "peerDependencies": { "postcss": "^8.0.0" } }, "sha512-hpr+J05B2FVYUAXHeK1YyI267J/dDDhMU6B6civm8hSY1jYJnBXxzKDKDswzJmtLHryrjhnDjqqp/49t8FALew=="], + + "postcss-js": ["postcss-js@4.0.1", "", { "dependencies": { "camelcase-css": "^2.0.1" }, "peerDependencies": { "postcss": "^8.4.21" } }, "sha512-dDLF8pEO191hJMtlHFPRa8xsizHaM82MLfNkUHdUtVEV3tgTp5oj+8qbEqYM57SLfc74KSbw//4SeJma2LRVIw=="], + + "postcss-load-config": ["postcss-load-config@4.0.2", "", { "dependencies": { "lilconfig": "^3.0.0", "yaml": "^2.3.4" }, "peerDependencies": { "postcss": ">=8.0.9", "ts-node": ">=9.0.0" }, "optionalPeers": ["postcss", "ts-node"] }, "sha512-bSVhyJGL00wMVoPUzAVAnbEoWyqRxkjv64tUl427SKnPrENtq6hJwUojroMz2VB+Q1edmi4IfrAPpami5VVgMQ=="], + + "postcss-nested": ["postcss-nested@6.2.0", "", { "dependencies": { "postcss-selector-parser": "^6.1.1" }, "peerDependencies": { "postcss": "^8.2.14" } }, "sha512-HQbt28KulC5AJzG+cZtj9kvKB93CFCdLvog1WFLf1D+xmMvPGlBstkpTEZfK5+AN9hfJocyBFCNiqyS48bpgzQ=="], + + "postcss-selector-parser": ["postcss-selector-parser@6.1.2", "", { "dependencies": { "cssesc": "^3.0.0", "util-deprecate": "^1.0.2" } }, "sha512-Q8qQfPiZ+THO/3ZrOrO0cJJKfpYCagtMUkXbnEfmgUjwXg6z/WBeOyS9APBBPCTSiDV+s4SwQGu8yFsiMRIudg=="], + + "postcss-value-parser": ["postcss-value-parser@4.2.0", "", {}, "sha512-1NNCs6uurfkVbeXG4S8JFT9t19m45ICnif8zWLd5oPSZ50QnwMfK+H3jv408d4jw/7Bttv5axS5IiHoLaVNHeQ=="], + + "queue-microtask": ["queue-microtask@1.2.3", "", {}, "sha512-NuaNSa6flKT5JaSYQzJok04JzTL1CA6aGhv5rfLW3PgqA+M2ChpZQnAC8h8i4ZFkBS8X5RqkDBHA7r4hej3K9A=="], + + "read-cache": ["read-cache@1.0.0", "", { "dependencies": { "pify": "^2.3.0" } }, "sha512-Owdv/Ft7IjOgm/i0xvNDZ1LrRANRfew4b2prF3OWMQLxLfu3bS8FVhCsrSCMK4lR56Y9ya+AThoTpDCTxCmpRA=="], + + "readdirp": ["readdirp@4.1.2", "", {}, "sha512-GDhwkLfywWL2s6vEjyhri+eXmfH6j1L7JE27WhqLeYzoh/A3DBaYGEj2H/HFZCn/kMfim73FXxEJTw06WtxQwg=="], + + "resolve": ["resolve@1.22.10", "", { "dependencies": { "is-core-module": "^2.16.0", "path-parse": "^1.0.7", "supports-preserve-symlinks-flag": "^1.0.0" }, "bin": { "resolve": "bin/resolve" } }, "sha512-NPRy+/ncIMeDlTAsuqwKIiferiawhefFJtkNSW0qZJEqMEb+qBt/77B/jGeeek+F0uOeN05CDa6HXbbIgtVX4w=="], + + "reusify": ["reusify@1.1.0", "", {}, "sha512-g6QUff04oZpHs0eG5p83rFLhHeV00ug/Yf9nZM6fLeUrPguBTkTQOdpAWWspMh55TZfVQDPaN3NQJfbVRAxdIw=="], + + "rollup": ["rollup@4.41.1", "", { "dependencies": { "@types/estree": "1.0.7" }, "optionalDependencies": { "@rollup/rollup-android-arm-eabi": "4.41.1", "@rollup/rollup-android-arm64": "4.41.1", "@rollup/rollup-darwin-arm64": "4.41.1", "@rollup/rollup-darwin-x64": "4.41.1", "@rollup/rollup-freebsd-arm64": "4.41.1", "@rollup/rollup-freebsd-x64": "4.41.1", "@rollup/rollup-linux-arm-gnueabihf": "4.41.1", "@rollup/rollup-linux-arm-musleabihf": "4.41.1", "@rollup/rollup-linux-arm64-gnu": "4.41.1", "@rollup/rollup-linux-arm64-musl": "4.41.1", "@rollup/rollup-linux-loongarch64-gnu": "4.41.1", "@rollup/rollup-linux-powerpc64le-gnu": "4.41.1", "@rollup/rollup-linux-riscv64-gnu": "4.41.1", "@rollup/rollup-linux-riscv64-musl": "4.41.1", "@rollup/rollup-linux-s390x-gnu": "4.41.1", "@rollup/rollup-linux-x64-gnu": "4.41.1", "@rollup/rollup-linux-x64-musl": "4.41.1", "@rollup/rollup-win32-arm64-msvc": "4.41.1", "@rollup/rollup-win32-ia32-msvc": "4.41.1", "@rollup/rollup-win32-x64-msvc": "4.41.1", "fsevents": "~2.3.2" }, "bin": { "rollup": "dist/bin/rollup" } }, "sha512-cPmwD3FnFv8rKMBc1MxWCwVQFxwf1JEmSX3iQXrRVVG15zerAIXRjMFVWnd5Q5QvgKF7Aj+5ykXFhUl+QGnyOw=="], + + "run-parallel": ["run-parallel@1.2.0", "", { "dependencies": { "queue-microtask": "^1.2.2" } }, "sha512-5l4VyZR86LZ/lDxZTR6jqL8AFE2S0IFLMP26AbjsLVADxHdhB/c0GUsH+y39UfCi3dzz8OlQuPmnaJOMoDHQBA=="], + + "runed": ["runed@0.35.1", "", { "dependencies": { "dequal": "^2.0.3", "esm-env": "^1.0.0", "lz-string": "^1.5.0" }, "peerDependencies": { "@sveltejs/kit": "^2.21.0", "svelte": "^5.7.0" }, "optionalPeers": ["@sveltejs/kit"] }, "sha512-2F4Q/FZzbeJTFdIS/PuOoPRSm92sA2LhzTnv6FXhCoENb3huf5+fDuNOg1LNvGOouy3u/225qxmuJvcV3IZK5Q=="], + + "sade": ["sade@1.8.1", "", { "dependencies": { "mri": "^1.1.0" } }, "sha512-xal3CZX1Xlo/k4ApwCFrHVACi9fBqJ7V+mwhBsuf/1IOKbBy098Fex+Wa/5QMubw09pSZ/u8EY8PWgevJsXp1A=="], + + "shebang-command": ["shebang-command@2.0.0", "", { "dependencies": { "shebang-regex": "^3.0.0" } }, "sha512-kHxr2zZpYtdmrN1qDjrrX/Z1rR1kG8Dx+gkpK1G4eXmvXswmcE1hTWBWYUzlraYw1/yZp6YuDY77YtvbN0dmDA=="], + + "shebang-regex": ["shebang-regex@3.0.0", "", {}, "sha512-7++dFhtcx3353uBaq8DDR4NuxBetBzC7ZQOhmTQInHEd6bSrXdiEyzCvG07Z44UYdLShWUyXt5M/yhz8ekcb1A=="], + + "signal-exit": ["signal-exit@4.1.0", "", {}, "sha512-bzyZ1e88w9O1iNJbKnOlvYTrWPDl46O1bG0D3XInv+9tkPrxrN8jUUTiFlDkkmKWgn1M6CfIA13SuGqOa9Korw=="], + + "source-map-js": ["source-map-js@1.2.1", "", {}, "sha512-UXWMKhLOwVKb728IUtQPXxfYU+usdybtUrK/8uGE8CQMvrhOpwvzDBwj0QhSL7MQc7vIsISBG8VQ8+IDQxpfQA=="], + + "string-width": ["string-width@5.1.2", "", { "dependencies": { "eastasianwidth": "^0.2.0", "emoji-regex": "^9.2.2", "strip-ansi": "^7.0.1" } }, "sha512-HnLOCR3vjcY8beoNLtcjZ5/nxn2afmME6lhrDrebokqMap+XbeW8n9TXpPDOqdGK5qcI3oT0GKTW6wC7EMiVqA=="], + + "string-width-cjs": ["string-width@4.2.3", "", { "dependencies": { "emoji-regex": "^8.0.0", "is-fullwidth-code-point": "^3.0.0", "strip-ansi": "^6.0.1" } }, "sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g=="], + + "strip-ansi": ["strip-ansi@7.1.0", "", { "dependencies": { "ansi-regex": "^6.0.1" } }, "sha512-iq6eVVI64nQQTRYq2KtEg2d2uU7LElhTJwsH4YzIHZshxlgZms/wIc4VoDQTlG/IvVIrBKG06CrZnp0qv7hkcQ=="], + + "strip-ansi-cjs": ["strip-ansi@6.0.1", "", { "dependencies": { "ansi-regex": "^5.0.1" } }, "sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A=="], + + "style-mod": ["style-mod@4.1.2", "", {}, "sha512-wnD1HyVqpJUI2+eKZ+eo1UwghftP6yuFheBqqe+bWCotBjC2K1YnteJILRMs3SM4V/0dLEW1SC27MWP5y+mwmw=="], + + "style-to-object": ["style-to-object@1.0.9", "", { "dependencies": { "inline-style-parser": "0.2.4" } }, "sha512-G4qppLgKu/k6FwRpHiGiKPaPTFcG3g4wNVX/Qsfu+RqQM30E7Tyu/TEgxcL9PNLF5pdRLwQdE3YKKf+KF2Dzlw=="], + + "sucrase": ["sucrase@3.35.0", "", { "dependencies": { "@jridgewell/gen-mapping": "^0.3.2", "commander": "^4.0.0", "glob": "^10.3.10", "lines-and-columns": "^1.1.6", "mz": "^2.7.0", "pirates": "^4.0.1", "ts-interface-checker": "^0.1.9" }, "bin": { "sucrase": "bin/sucrase", "sucrase-node": "bin/sucrase-node" } }, "sha512-8EbVDiu9iN/nESwxeSxDKe0dunta1GOlHufmSSXxMD2z2/tMZpDMpvXQGsc+ajGo8y2uYUmixaSRUc/QPoQ0GA=="], + + "supports-preserve-symlinks-flag": ["supports-preserve-symlinks-flag@1.0.0", "", {}, "sha512-ot0WnXS9fgdkgIcePe6RHNk1WA8+muPa6cSjeR3V8K27q9BB1rTE3R1p7Hv0z1ZyAc8s6Vvv8DIyWf681MAt0w=="], + + "svelte": ["svelte@5.41.0", "", { "dependencies": { "@jridgewell/remapping": "^2.3.4", "@jridgewell/sourcemap-codec": "^1.5.0", "@sveltejs/acorn-typescript": "^1.0.5", "@types/estree": "^1.0.5", "acorn": "^8.12.1", "aria-query": "^5.3.1", "axobject-query": "^4.1.0", "clsx": "^2.1.1", "esm-env": "^1.2.1", "esrap": "^2.1.0", "is-reference": "^3.0.3", "locate-character": "^3.0.0", "magic-string": "^0.30.11", "zimmerframe": "^1.1.2" } }, "sha512-mP3vFFv5OUM5JN189+nJVW74kQ1dGqUrXTEzvCEVZqessY0GxZDls1nWVvt4Sxyv2USfQvAZO68VRaeIZvpzKg=="], + + "svelte-check": ["svelte-check@4.3.3", "", { "dependencies": { "@jridgewell/trace-mapping": "^0.3.25", "chokidar": "^4.0.1", "fdir": "^6.2.0", "picocolors": "^1.0.0", "sade": "^1.7.4" }, "peerDependencies": { "svelte": "^4.0.0 || ^5.0.0-next.0", "typescript": ">=5.0.0" }, "bin": { "svelte-check": "bin/svelte-check" } }, "sha512-RYP0bEwenDXzfv0P1sKAwjZSlaRyqBn0Fz1TVni58lqyEiqgwztTpmodJrGzP6ZT2aHl4MbTvWP6gbmQ3FOnBg=="], + + "svelte-i18n": ["svelte-i18n@4.0.1", "", { "dependencies": { "cli-color": "^2.0.3", "deepmerge": "^4.2.2", "esbuild": "^0.19.2", "estree-walker": "^2", "intl-messageformat": "^10.5.3", "sade": "^1.8.1", "tiny-glob": "^0.2.9" }, "peerDependencies": { "svelte": "^3 || ^4 || ^5" }, "bin": { "svelte-i18n": "dist/cli.js" } }, "sha512-jaykGlGT5PUaaq04JWbJREvivlCnALtT+m87Kbm0fxyYHynkQaxQMnIKHLm2WeIuBRoljzwgyvz0Z6/CMwfdmQ=="], + + "svelte-toolbelt": ["svelte-toolbelt@0.10.6", "", { "dependencies": { "clsx": "^2.1.1", "runed": "^0.35.1", "style-to-object": "^1.0.8" }, "peerDependencies": { "svelte": "^5.30.2" } }, "sha512-YWuX+RE+CnWYx09yseAe4ZVMM7e7GRFZM6OYWpBKOb++s+SQ8RBIMMe+Bs/CznBMc0QPLjr+vDBxTAkozXsFXQ=="], + + "tabbable": ["tabbable@6.2.0", "", {}, "sha512-Cat63mxsVJlzYvN51JmVXIgNoUokrIaT2zLclCXjRd8boZ0004U4KCs/sToJ75C6sdlByWxpYnb5Boif1VSFew=="], + + "tailwindcss": ["tailwindcss@3.4.18", "", { "dependencies": { "@alloc/quick-lru": "^5.2.0", "arg": "^5.0.2", "chokidar": "^3.6.0", "didyoumean": "^1.2.2", "dlv": "^1.1.3", "fast-glob": "^3.3.2", "glob-parent": "^6.0.2", "is-glob": "^4.0.3", "jiti": "^1.21.7", "lilconfig": "^3.1.3", "micromatch": "^4.0.8", "normalize-path": "^3.0.0", "object-hash": "^3.0.0", "picocolors": "^1.1.1", "postcss": "^8.4.47", "postcss-import": "^15.1.0", "postcss-js": "^4.0.1", "postcss-load-config": "^4.0.2 || ^5.0 || ^6.0", "postcss-nested": "^6.2.0", "postcss-selector-parser": "^6.1.2", "resolve": "^1.22.8", "sucrase": "^3.35.0" }, "bin": { "tailwind": "lib/cli.js", "tailwindcss": "lib/cli.js" } }, "sha512-6A2rnmW5xZMdw11LYjhcI5846rt9pbLSabY5XPxo+XWdxwZaFEn47Go4NzFiHu9sNNmr/kXivP1vStfvMaK1GQ=="], + + "thenify": ["thenify@3.3.1", "", { "dependencies": { "any-promise": "^1.0.0" } }, "sha512-RVZSIV5IG10Hk3enotrhvz0T9em6cyHBLkH/YAZuKqd8hRkKhSfCGIcP2KUY0EPxndzANBmNllzWPwak+bheSw=="], + + "thenify-all": ["thenify-all@1.6.0", "", { "dependencies": { "thenify": ">= 3.1.0 < 4" } }, "sha512-RNxQH/qI8/t3thXJDwcstUO4zeqo64+Uy/+sNVRBx4Xn2OX+OZ9oP+iJnNFqplFra2ZUVeKCSa2oVWi3T4uVmA=="], + + "timers-ext": ["timers-ext@0.1.8", "", { "dependencies": { "es5-ext": "^0.10.64", "next-tick": "^1.1.0" } }, "sha512-wFH7+SEAcKfJpfLPkrgMPvvwnEtj8W4IurvEyrKsDleXnKLCDw71w8jltvfLa8Rm4qQxxT4jmDBYbJG/z7qoww=="], + + "tiny-glob": ["tiny-glob@0.2.9", "", { "dependencies": { "globalyzer": "0.1.0", "globrex": "^0.1.2" } }, "sha512-g/55ssRPUjShh+xkfx9UPDXqhckHEsHr4Vd9zX55oSdGZc/MD0m3sferOkwWtp98bv+kcVfEHtRJgBVJzelrzg=="], + + "tinyglobby": ["tinyglobby@0.2.14", "", { "dependencies": { "fdir": "^6.4.4", "picomatch": "^4.0.2" } }, "sha512-tX5e7OM1HnYr2+a2C/4V0htOcSQcoSTH9KgJnVvNm5zm/cyEWKJ7j7YutsH9CxMdtOkkLFy2AHrMci9IM8IPZQ=="], + + "to-regex-range": ["to-regex-range@5.0.1", "", { "dependencies": { "is-number": "^7.0.0" } }, "sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ=="], + + "ts-interface-checker": ["ts-interface-checker@0.1.13", "", {}, "sha512-Y/arvbn+rrz3JCKl9C4kVNfTfSm2/mEp5FSz5EsZSANGPSlQrpRI5M4PKF+mJnE52jOO90PnPSc3Ur3bTQw0gA=="], + + "tslib": ["tslib@2.8.1", "", {}, "sha512-oJFu94HQb+KVduSUQL7wnpmqnfmLsOA/nAh6b6EH0wCEoK0/mPeXU6c3wKDV83MkOuHPRHtSXKKU99IBazS/2w=="], + + "type": ["type@2.7.3", "", {}, "sha512-8j+1QmAbPvLZow5Qpi6NCaN8FB60p/6x8/vfNqOk/hC+HuvFZhL4+WfekuhQLiqFZXOgQdrs3B+XxEmCc6b3FQ=="], + + "typescript": ["typescript@5.9.3", "", { "bin": { "tsc": "bin/tsc", "tsserver": "bin/tsserver" } }, "sha512-jl1vZzPDinLr9eUt3J/t7V6FgNEw9QjvBPdysz9KfQDD41fQrC2Y4vKQdiaUpFT4bXlb1RHhLpp8wtm6M5TgSw=="], + + "update-browserslist-db": ["update-browserslist-db@1.1.3", "", { "dependencies": { "escalade": "^3.2.0", "picocolors": "^1.1.1" }, "peerDependencies": { "browserslist": ">= 4.21.0" }, "bin": { "update-browserslist-db": "cli.js" } }, "sha512-UxhIZQ+QInVdunkDAaiazvvT/+fXL5Osr0JZlJulepYu6Jd7qJtDZjlur0emRlT71EN3ScPoE7gvsuIKKNavKw=="], + + "util-deprecate": ["util-deprecate@1.0.2", "", {}, "sha512-EPD5q1uXyFxJpCrLnCc1nHnq3gOa6DZBocAIiI2TaSCA7VCJ1UJDMagCzIkXNsUYfD1daK//LTEQ8xiIbrHtcw=="], + + "uuid": ["uuid@11.1.0", "", { "bin": { "uuid": "dist/esm/bin/uuid" } }, "sha512-0/A9rDy9P7cJ+8w1c9WD9V//9Wj15Ce2MPz8Ri6032usz+NfePxx5AcN3bN+r6ZL6jEo066/yNYB3tn4pQEx+A=="], + + "vite": ["vite@6.4.0", "", { "dependencies": { "esbuild": "^0.25.0", "fdir": "^6.4.4", "picomatch": "^4.0.2", "postcss": "^8.5.3", "rollup": "^4.34.9", "tinyglobby": "^0.2.13" }, "optionalDependencies": { "fsevents": "~2.3.3" }, "peerDependencies": { "@types/node": "^18.0.0 || ^20.0.0 || >=22.0.0", "jiti": ">=1.21.0", "less": "*", "lightningcss": "^1.21.0", "sass": "*", "sass-embedded": "*", "stylus": "*", "sugarss": "*", "terser": "^5.16.0", "tsx": "^4.8.1", "yaml": "^2.4.2" }, "optionalPeers": ["@types/node", "jiti", "less", "lightningcss", "sass", "sass-embedded", "stylus", "sugarss", "terser", "tsx", "yaml"], "bin": { "vite": "bin/vite.js" } }, "sha512-oLnWs9Hak/LOlKjeSpOwD6JMks8BeICEdYMJBf6P4Lac/pO9tKiv/XhXnAM7nNfSkZahjlCZu9sS50zL8fSnsw=="], + + "vitefu": ["vitefu@1.0.6", "", { "peerDependencies": { "vite": "^3.0.0 || ^4.0.0 || ^5.0.0 || ^6.0.0" }, "optionalPeers": ["vite"] }, "sha512-+Rex1GlappUyNN6UfwbVZne/9cYC4+R2XDk9xkNXBKMw6HQagdX9PgZ8V2v1WUSK1wfBLp7qbI1+XSNIlB1xmA=="], + + "w3c-keyname": ["w3c-keyname@2.2.8", "", {}, "sha512-dpojBhNsCNN7T82Tm7k26A6G9ML3NkhDsnw9n/eoxSRlVBB4CEtIQ/KTCLI2Fwf3ataSXRhYFkQi3SlnFwPvPQ=="], + + "which": ["which@2.0.2", "", { "dependencies": { "isexe": "^2.0.0" }, "bin": { "node-which": "./bin/node-which" } }, "sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA=="], + + "wrap-ansi": ["wrap-ansi@8.1.0", "", { "dependencies": { "ansi-styles": "^6.1.0", "string-width": "^5.0.1", "strip-ansi": "^7.0.1" } }, "sha512-si7QWI6zUMq56bESFvagtmzMdGOtoxfR+Sez11Mobfc7tm+VkUckk9bW2UeffTGVUbOksxmSw0AA2gs8g71NCQ=="], + + "wrap-ansi-cjs": ["wrap-ansi@7.0.0", "", { "dependencies": { "ansi-styles": "^4.0.0", "string-width": "^4.1.0", "strip-ansi": "^6.0.0" } }, "sha512-YVGIj2kamLSTxw6NsZjoBxfSwsn0ycdesmc4p+Q21c5zPuZ1pl+NfxVdxPtdHvmNVOQ6XSYG4AUtyt/Fi7D16Q=="], + + "yaml": ["yaml@2.8.0", "", { "bin": { "yaml": "bin.mjs" } }, "sha512-4lLa/EcQCB0cJkyts+FpIRx5G/llPxfP6VQU5KByHEhLxY3IJCH0f0Hy1MHI8sClTvsIb8qwRJ6R/ZdlDJ/leQ=="], + + "zimmerframe": ["zimmerframe@1.1.2", "", {}, "sha512-rAbqEGa8ovJy4pyBxZM70hg4pE6gDgaQ0Sl9M3enG3I0d6H4XSAM3GeNGLKnsBpuijUow064sf7ww1nutC5/3w=="], + + "anymatch/picomatch": ["picomatch@2.3.1", "", {}, "sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA=="], + + "fast-glob/glob-parent": ["glob-parent@5.1.2", "", { "dependencies": { "is-glob": "^4.0.1" } }, "sha512-AOIgSQCepiJYwP3ARnGx+5VnTu2HBYdzbGP45eLw1vr3zB3vZLeyed1sC9hnbcOc9/SrMyM5RPQrkGz4aS9Zow=="], + + "micromatch/picomatch": ["picomatch@2.3.1", "", {}, "sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA=="], + + "rollup/@types/estree": ["@types/estree@1.0.7", "", {}, "sha512-w28IoSUCJpidD/TGviZwwMJckNESJZXFu7NBZ5YJ4mEUnNraUn9Pm8HSZm/jDF1pDWYKspWE7oVphigUPRakIQ=="], + + "string-width-cjs/emoji-regex": ["emoji-regex@8.0.0", "", {}, "sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A=="], + + "string-width-cjs/strip-ansi": ["strip-ansi@6.0.1", "", { "dependencies": { "ansi-regex": "^5.0.1" } }, "sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A=="], + + "strip-ansi-cjs/ansi-regex": ["ansi-regex@5.0.1", "", {}, "sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ=="], + + "svelte-i18n/esbuild": ["esbuild@0.19.12", "", { "optionalDependencies": { "@esbuild/aix-ppc64": "0.19.12", "@esbuild/android-arm": "0.19.12", "@esbuild/android-arm64": "0.19.12", "@esbuild/android-x64": "0.19.12", "@esbuild/darwin-arm64": "0.19.12", "@esbuild/darwin-x64": "0.19.12", "@esbuild/freebsd-arm64": "0.19.12", "@esbuild/freebsd-x64": "0.19.12", "@esbuild/linux-arm": "0.19.12", "@esbuild/linux-arm64": "0.19.12", "@esbuild/linux-ia32": "0.19.12", "@esbuild/linux-loong64": "0.19.12", "@esbuild/linux-mips64el": "0.19.12", "@esbuild/linux-ppc64": "0.19.12", "@esbuild/linux-riscv64": "0.19.12", "@esbuild/linux-s390x": "0.19.12", "@esbuild/linux-x64": "0.19.12", "@esbuild/netbsd-x64": "0.19.12", "@esbuild/openbsd-x64": "0.19.12", "@esbuild/sunos-x64": "0.19.12", "@esbuild/win32-arm64": "0.19.12", "@esbuild/win32-ia32": "0.19.12", "@esbuild/win32-x64": "0.19.12" }, "bin": { "esbuild": "bin/esbuild" } }, "sha512-aARqgq8roFBj054KvQr5f1sFu0D65G+miZRCuJyJ0G13Zwx7vRar5Zhn2tkQNzIXcBrNVsv/8stehpj+GAjgbg=="], + + "tailwindcss/chokidar": ["chokidar@3.6.0", "", { "dependencies": { "anymatch": "~3.1.2", "braces": "~3.0.2", "glob-parent": "~5.1.2", "is-binary-path": "~2.1.0", "is-glob": "~4.0.1", "normalize-path": "~3.0.0", "readdirp": "~3.6.0" }, "optionalDependencies": { "fsevents": "~2.3.2" } }, "sha512-7VT13fmjotKpGipCW9JEQAusEPE+Ei8nl6/g4FBAmIm0GOOLMua9NDDo/DWp0ZAxCr3cPq5ZpBqmPAQgDda2Pw=="], + + "wrap-ansi-cjs/ansi-styles": ["ansi-styles@4.3.0", "", { "dependencies": { "color-convert": "^2.0.1" } }, "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg=="], + + "wrap-ansi-cjs/string-width": ["string-width@4.2.3", "", { "dependencies": { "emoji-regex": "^8.0.0", "is-fullwidth-code-point": "^3.0.0", "strip-ansi": "^6.0.1" } }, "sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g=="], + + "wrap-ansi-cjs/strip-ansi": ["strip-ansi@6.0.1", "", { "dependencies": { "ansi-regex": "^5.0.1" } }, "sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A=="], + + "string-width-cjs/strip-ansi/ansi-regex": ["ansi-regex@5.0.1", "", {}, "sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ=="], + + "svelte-i18n/esbuild/@esbuild/aix-ppc64": ["@esbuild/aix-ppc64@0.19.12", "", { "os": "aix", "cpu": "ppc64" }, "sha512-bmoCYyWdEL3wDQIVbcyzRyeKLgk2WtWLTWz1ZIAZF/EGbNOwSA6ew3PftJ1PqMiOOGu0OyFMzG53L0zqIpPeNA=="], + + "svelte-i18n/esbuild/@esbuild/android-arm": ["@esbuild/android-arm@0.19.12", "", { "os": "android", "cpu": "arm" }, "sha512-qg/Lj1mu3CdQlDEEiWrlC4eaPZ1KztwGJ9B6J+/6G+/4ewxJg7gqj8eVYWvao1bXrqGiW2rsBZFSX3q2lcW05w=="], + + "svelte-i18n/esbuild/@esbuild/android-arm64": ["@esbuild/android-arm64@0.19.12", "", { "os": "android", "cpu": "arm64" }, "sha512-P0UVNGIienjZv3f5zq0DP3Nt2IE/3plFzuaS96vihvD0Hd6H/q4WXUGpCxD/E8YrSXfNyRPbpTq+T8ZQioSuPA=="], + + "svelte-i18n/esbuild/@esbuild/android-x64": ["@esbuild/android-x64@0.19.12", "", { "os": "android", "cpu": "x64" }, "sha512-3k7ZoUW6Q6YqhdhIaq/WZ7HwBpnFBlW905Fa4s4qWJyiNOgT1dOqDiVAQFwBH7gBRZr17gLrlFCRzF6jFh7Kew=="], + + "svelte-i18n/esbuild/@esbuild/darwin-arm64": ["@esbuild/darwin-arm64@0.19.12", "", { "os": "darwin", "cpu": "arm64" }, "sha512-B6IeSgZgtEzGC42jsI+YYu9Z3HKRxp8ZT3cqhvliEHovq8HSX2YX8lNocDn79gCKJXOSaEot9MVYky7AKjCs8g=="], + + "svelte-i18n/esbuild/@esbuild/darwin-x64": ["@esbuild/darwin-x64@0.19.12", "", { "os": "darwin", "cpu": "x64" }, "sha512-hKoVkKzFiToTgn+41qGhsUJXFlIjxI/jSYeZf3ugemDYZldIXIxhvwN6erJGlX4t5h417iFuheZ7l+YVn05N3A=="], + + "svelte-i18n/esbuild/@esbuild/freebsd-arm64": ["@esbuild/freebsd-arm64@0.19.12", "", { "os": "freebsd", "cpu": "arm64" }, "sha512-4aRvFIXmwAcDBw9AueDQ2YnGmz5L6obe5kmPT8Vd+/+x/JMVKCgdcRwH6APrbpNXsPz+K653Qg8HB/oXvXVukA=="], + + "svelte-i18n/esbuild/@esbuild/freebsd-x64": ["@esbuild/freebsd-x64@0.19.12", "", { "os": "freebsd", "cpu": "x64" }, "sha512-EYoXZ4d8xtBoVN7CEwWY2IN4ho76xjYXqSXMNccFSx2lgqOG/1TBPW0yPx1bJZk94qu3tX0fycJeeQsKovA8gg=="], + + "svelte-i18n/esbuild/@esbuild/linux-arm": ["@esbuild/linux-arm@0.19.12", "", { "os": "linux", "cpu": "arm" }, "sha512-J5jPms//KhSNv+LO1S1TX1UWp1ucM6N6XuL6ITdKWElCu8wXP72l9MM0zDTzzeikVyqFE6U8YAV9/tFyj0ti+w=="], + + "svelte-i18n/esbuild/@esbuild/linux-arm64": ["@esbuild/linux-arm64@0.19.12", "", { "os": "linux", "cpu": "arm64" }, "sha512-EoTjyYyLuVPfdPLsGVVVC8a0p1BFFvtpQDB/YLEhaXyf/5bczaGeN15QkR+O4S5LeJ92Tqotve7i1jn35qwvdA=="], + + "svelte-i18n/esbuild/@esbuild/linux-ia32": ["@esbuild/linux-ia32@0.19.12", "", { "os": "linux", "cpu": "ia32" }, "sha512-Thsa42rrP1+UIGaWz47uydHSBOgTUnwBwNq59khgIwktK6x60Hivfbux9iNR0eHCHzOLjLMLfUMLCypBkZXMHA=="], + + "svelte-i18n/esbuild/@esbuild/linux-loong64": ["@esbuild/linux-loong64@0.19.12", "", { "os": "linux", "cpu": "none" }, "sha512-LiXdXA0s3IqRRjm6rV6XaWATScKAXjI4R4LoDlvO7+yQqFdlr1Bax62sRwkVvRIrwXxvtYEHHI4dm50jAXkuAA=="], + + "svelte-i18n/esbuild/@esbuild/linux-mips64el": ["@esbuild/linux-mips64el@0.19.12", "", { "os": "linux", "cpu": "none" }, "sha512-fEnAuj5VGTanfJ07ff0gOA6IPsvrVHLVb6Lyd1g2/ed67oU1eFzL0r9WL7ZzscD+/N6i3dWumGE1Un4f7Amf+w=="], + + "svelte-i18n/esbuild/@esbuild/linux-ppc64": ["@esbuild/linux-ppc64@0.19.12", "", { "os": "linux", "cpu": "ppc64" }, "sha512-nYJA2/QPimDQOh1rKWedNOe3Gfc8PabU7HT3iXWtNUbRzXS9+vgB0Fjaqr//XNbd82mCxHzik2qotuI89cfixg=="], + + "svelte-i18n/esbuild/@esbuild/linux-riscv64": ["@esbuild/linux-riscv64@0.19.12", "", { "os": "linux", "cpu": "none" }, "sha512-2MueBrlPQCw5dVJJpQdUYgeqIzDQgw3QtiAHUC4RBz9FXPrskyyU3VI1hw7C0BSKB9OduwSJ79FTCqtGMWqJHg=="], + + "svelte-i18n/esbuild/@esbuild/linux-s390x": ["@esbuild/linux-s390x@0.19.12", "", { "os": "linux", "cpu": "s390x" }, "sha512-+Pil1Nv3Umes4m3AZKqA2anfhJiVmNCYkPchwFJNEJN5QxmTs1uzyy4TvmDrCRNT2ApwSari7ZIgrPeUx4UZDg=="], + + "svelte-i18n/esbuild/@esbuild/linux-x64": ["@esbuild/linux-x64@0.19.12", "", { "os": "linux", "cpu": "x64" }, "sha512-B71g1QpxfwBvNrfyJdVDexenDIt1CiDN1TIXLbhOw0KhJzE78KIFGX6OJ9MrtC0oOqMWf+0xop4qEU8JrJTwCg=="], + + "svelte-i18n/esbuild/@esbuild/netbsd-x64": ["@esbuild/netbsd-x64@0.19.12", "", { "os": "none", "cpu": "x64" }, "sha512-3ltjQ7n1owJgFbuC61Oj++XhtzmymoCihNFgT84UAmJnxJfm4sYCiSLTXZtE00VWYpPMYc+ZQmB6xbSdVh0JWA=="], + + "svelte-i18n/esbuild/@esbuild/openbsd-x64": ["@esbuild/openbsd-x64@0.19.12", "", { "os": "openbsd", "cpu": "x64" }, "sha512-RbrfTB9SWsr0kWmb9srfF+L933uMDdu9BIzdA7os2t0TXhCRjrQyCeOt6wVxr79CKD4c+p+YhCj31HBkYcXebw=="], + + "svelte-i18n/esbuild/@esbuild/sunos-x64": ["@esbuild/sunos-x64@0.19.12", "", { "os": "sunos", "cpu": "x64" }, "sha512-HKjJwRrW8uWtCQnQOz9qcU3mUZhTUQvi56Q8DPTLLB+DawoiQdjsYq+j+D3s9I8VFtDr+F9CjgXKKC4ss89IeA=="], + + "svelte-i18n/esbuild/@esbuild/win32-arm64": ["@esbuild/win32-arm64@0.19.12", "", { "os": "win32", "cpu": "arm64" }, "sha512-URgtR1dJnmGvX864pn1B2YUYNzjmXkuJOIqG2HdU62MVS4EHpU2946OZoTMnRUHklGtJdJZ33QfzdjGACXhn1A=="], + + "svelte-i18n/esbuild/@esbuild/win32-ia32": ["@esbuild/win32-ia32@0.19.12", "", { "os": "win32", "cpu": "ia32" }, "sha512-+ZOE6pUkMOJfmxmBZElNOx72NKpIa/HFOMGzu8fqzQJ5kgf6aTGrcJaFsNiVMH4JKpMipyK+7k0n2UXN7a8YKQ=="], + + "svelte-i18n/esbuild/@esbuild/win32-x64": ["@esbuild/win32-x64@0.19.12", "", { "os": "win32", "cpu": "x64" }, "sha512-T1QyPSDCyMXaO3pzBkF96E8xMkiRYbUEZADd29SyPGabqxMViNoii+NcK7eWJAEoU6RZyEm5lVSIjTmcdoB9HA=="], + + "tailwindcss/chokidar/glob-parent": ["glob-parent@5.1.2", "", { "dependencies": { "is-glob": "^4.0.1" } }, "sha512-AOIgSQCepiJYwP3ARnGx+5VnTu2HBYdzbGP45eLw1vr3zB3vZLeyed1sC9hnbcOc9/SrMyM5RPQrkGz4aS9Zow=="], + + "tailwindcss/chokidar/readdirp": ["readdirp@3.6.0", "", { "dependencies": { "picomatch": "^2.2.1" } }, "sha512-hOS089on8RduqdbhvQ5Z37A0ESjsqz6qnRcffsMU3495FuTdqSm+7bhJ29JvIOsBDEEnan5DPu9t3To9VRlMzA=="], + + "wrap-ansi-cjs/string-width/emoji-regex": ["emoji-regex@8.0.0", "", {}, "sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A=="], + + "wrap-ansi-cjs/strip-ansi/ansi-regex": ["ansi-regex@5.0.1", "", {}, "sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ=="], + + "tailwindcss/chokidar/readdirp/picomatch": ["picomatch@2.3.1", "", {}, "sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA=="], + } +} diff --git a/manifest.json b/manifest.json index f17a6fde..9432daca 100644 --- a/manifest.json +++ b/manifest.json @@ -1,10 +1,10 @@ { - "id": "smart-second-brain", - "name": "Smart Second Brain", - "description": "Interact with your privacy focused assistant, leveraging Ollama or OpenAI, making your second brain even smarter.", - "author": "Leo310, nicobrauchtgit", - "authorUrl": "https://github.com/nicobrauchtgit", - "version": "1.3.0", - "minAppVersion": "1.5.0", - "isDesktopOnly": true + "id": "smart-second-brain", + "name": "Smart Second Brain", + "description": "Interact with your privacy focused assistant, leveraging Ollama or OpenAI, making your second brain even smarter.", + "author": "Leo310, nicobrauchtgit", + "authorUrl": "https://github.com/nicobrauchtgit", + "version": "1.3.0", + "minAppVersion": "1.5.0", + "isDesktopOnly": true } diff --git a/package.json b/package.json index cc918144..115c559e 100644 --- a/package.json +++ b/package.json @@ -1,41 +1,40 @@ { - "name": "smart-second-brain", - "version": "1.1.0", - "main": "main.js", - "devDependencies": { - "@biomejs/biome": "1.2.2", - "@rollup/plugin-json": "^6.1.0", - "@rollup/plugin-typescript": "^11.1.6", - "@sveltejs/vite-plugin-svelte": "^2.4.6", - "@tsconfig/svelte": "^4.0.1", - "@typescript-eslint/eslint-plugin": "^6.19.0", - "@typescript-eslint/parser": "^6.19.0", - "autoprefixer": "^10.4.16", - "builtin-modules": "^3.3.0", - "bun-types": "latest", - "eslint": "^8.56.0", - "obsidian": "^1.4.11", - "postcss": "^8.4.30", - "svelte": "^4.2.1", - "svelte-check": "^3.5.2", - "tailwindcss": "^3.3.3", - "tslib": "^2.6.2", - "typescript": "^5.2.2", - "vite": "^4.4.9" - }, - "private": true, - "scripts": { - "dev": "vite build --mode development --watch", - "build": "vite build --mode production", - "check": "svelte-check --tsconfig ./tsconfig.json", - "format": "biome format --write ./src", - "lint": "biome lint --apply-unsafe ./src" - }, - "type": "module", - "dependencies": { - "i18next": "^23.8.2", - "monkey-around": "^2.3.0", - "nanoid": "^5.0.4", - "svelte-i18n": "^4.0.0" - } + "name": "smart-second-brain", + "version": "0.1.0", + "main": "main.js", + "devDependencies": { + "@biomejs/biome": "^1.9.4", + "@sveltejs/vite-plugin-svelte": "^5.1.1", + "@tsconfig/svelte": "^5.0.5", + "autoprefixer": "^10.4.21", + "obsidian": "^1.10.0", + "postcss": "^8.5.6", + "svelte": "^5.41.0", + "svelte-check": "^4.3.3", + "tailwindcss": "^3.4.18", + "tslib": "^2.8.1", + "typescript": "^5.9.3", + "vite": "^6.4.0" + }, + "private": true, + "scripts": { + "dev": "vite build --mode development --watch", + "build": "vite build --mode production", + "check": "svelte-check --tsconfig ./tsconfig.json", + "format": "biome format --write ./src", + "lint": "biome lint --apply-unsafe ./src" + }, + "type": "module", + "dependencies": { + "@selemondev/svgl-svelte": "^0.0.3", + "@tanstack/svelte-query": "https://pkg.pr.new/@tanstack/svelte-query@746b9c5d83e901deb3a5ca7012a4b4e2b617c5e3", + "bits-ui": "^2.11.8", + "builtin-modules": "^5.0.0", + "dexie": "^4.2.1", + "i18next": "^23.16.8", + "monkey-around": "^3.0.0", + "papa-ts": "link:papa-ts", + "svelte-i18n": "^4.0.1", + "uuid": "^11.1.0" + } } diff --git a/src/SmartSecondBrain.ts b/src/SmartSecondBrain.ts old mode 100644 new mode 100755 index 862c8bb8..2f2cabc3 --- a/src/SmartSecondBrain.ts +++ b/src/SmartSecondBrain.ts @@ -1,232 +1,294 @@ -import { App, Notice, TFile, normalizePath } from 'obsidian'; -import { Papa, obsidianDocumentLoader, type GenModel } from 'papa-ts'; -import { get } from 'svelte/store'; -import { wildTest } from './components/Settings/FuzzyModal'; -import { isOllamaRunning, getOllamaModels } from './controller/Ollama'; -import { isAPIKeyValid } from './controller/OpenAI'; -import Log, { LogLvl } from './logging'; -import { data, papaState, errorState, papaIndexingProgress, chatHistory, serializeChatHistory, runState, runContent, papaIndexingTimeLeft } from './store'; -import { _ } from 'svelte-i18n'; +import { App, Notice, TFile, normalizePath } from "obsidian"; +import { obsidianDocumentLoader, Papa, type PapaConfig } from "papa-ts"; +import { get } from "svelte/store"; +import Log, { LogLvl } from "./logging"; +import { wildTest } from "./utils/utils"; +import { + papaState, + errorState, + papaIndexingProgress, + runState, + runContent, + papaIndexingTimeLeft, +} from "./store"; +import { _ } from "svelte-i18n"; +import type SecondBrainPlugin from "./main"; export default class SmartSecondBrain { - private papa: Papa; - private app: App; - private needsToSaveVectorStoreData = false; - private pluginDir: string; - - constructor(app: App, pluginDir: string) { - this.app = app; - this.pluginDir = pluginDir; - } + private papa: Papa; + private plugin: SecondBrainPlugin; + private needsToSaveVectorStoreData = false; + private pluginDir: string; - async init() { - const d = get(data); - const t = get(_); - if (get(papaState) === 'running') return new Notice(t('notice.still_running'), 4000); - else if (get(papaState) === 'indexing' || get(papaState) === 'loading') { - return new Notice(t('notice.still_indexing'), 4000); - } else if (d.isIncognitoMode && !(await isOllamaRunning())) { - papaState.set('error'); - errorState.set('ollama-not-running'); - return new Notice(t('notice.ollama_not_running'), 4000); - } else if (d.isIncognitoMode) { - const models = await getOllamaModels(); - if (!models.includes(d.ollamaGenModel.model)) { - papaState.set('error'); - errorState.set('ollama-gen-model-not-installed'); - return new Notice(t('notice.ollama_gen_model'), 4000); - } - if (!models.includes(d.ollamaEmbedModel.model)) { - papaState.set('error'); - errorState.set('ollama-embed-model-not-installed'); - return new Notice(t('notice.ollama_embed_model'), 4000); - } - } else if (!d.isIncognitoMode && !(await isAPIKeyValid(d.openAIGenModel.openAIApiKey))) { - papaState.set('error'); - return new Notice(t('notice.openai_key'), 4000); - } - if (get(papaState) !== 'indexing-pause') { - papaState.set('loading'); - Log.info( - 'Initializing second brain', - '\nGen Model: ', - d.isIncognitoMode ? d.ollamaGenModel : d.openAIGenModel, - '\nEmbed Model: ', - d.isIncognitoMode ? d.ollamaEmbedModel : d.openAIEmbedModel - ); - try { - this.papa = new Papa(); - await this.papa.init({ - genModel: d.isIncognitoMode ? d.ollamaGenModel : d.openAIGenModel, - embedModel: d.isIncognitoMode ? d.ollamaEmbedModel : d.openAIEmbedModel, - langsmithApiKey: d.debugginLangchainKey || undefined, - logLvl: d.isVerbose ? LogLvl.DEBUG : LogLvl.DISABLED, - }); - } catch (e) { - Log.error(e); - papaState.set('error'); - return new Notice(t('notice.failed', { values: { error: e } }), 4000); - } - // check if vector store data exists - if (await this.app.vault.adapter.exists(this.getVectorStoreFile())) { - const vectorStoreData = await this.app.vault.adapter.readBinary(this.getVectorStoreFile()); - await this.papa.load(vectorStoreData); - } - } - const mdFiles = this.app.vault.getMarkdownFiles(); - const docs = await obsidianDocumentLoader( - this.app, - mdFiles.filter((mdFile: TFile) => { - for (const exclude of d.excludeFF) if (wildTest(exclude, mdFile.path)) return false; - return true; - }) - ); - papaState.set('indexing'); - let needsSave = false; - try { - let lastTime = Date.now(); - const timePerDoc = []; - - let lastTotalDocs = 0; - for await (const result of this.papa.embedDocuments(docs)) { - needsSave = (!this.needsToSaveVectorStoreData && result.numAdded > 0) || result.numDeleted > 0; - const progress = ((result.numAdded + result.numSkipped) / docs.length) * 100; - papaIndexingProgress.set(Math.max(progress, get(papaIndexingProgress))); - const currentTime = Date.now(); - timePerDoc.push(currentTime - lastTime); - const numberOfDocumentsRemaining = docs.length * (1 - get(papaIndexingProgress) / 100); - const averageTimePerDocumentInSeconds = - timePerDoc.reduce((a, b) => a + b, 0) / timePerDoc.length / (result.numAdded + result.numSkipped - lastTotalDocs) / 1000; - lastTotalDocs = result.numAdded + result.numSkipped; - if (timePerDoc.length > 5) { - timePerDoc.shift(); - papaIndexingTimeLeft.set(Math.ceil(averageTimePerDocumentInSeconds * numberOfDocumentsRemaining)); - } - lastTime = currentTime; - if (get(papaState) === 'indexing-pause') break; - } - } catch (e) { - Log.error(e); - papaState.set('error'); - errorState.set('failed-indexing'); - new Notice(t('notice.failed_indexing'), 4000); - } + constructor(plugin: SecondBrainPlugin, pluginDir: string) { + this.plugin = plugin; + this.pluginDir = pluginDir; + this.papa = new Papa({ + debugging: { + langsmithApiKey: this.pluginData.debuggingLangchainKey, + logLvl: 1, + }, + }); + } - this.needsToSaveVectorStoreData = needsSave; - this.saveVectorStoreData(); - if (get(papaIndexingProgress) === 100) { - new Notice(t('notice.done'), 2000); - papaIndexingProgress.set(0); - papaState.set('idle'); - } - } + async init() { + const { + debuggingLangchainKey, + isVerbose, + excludeFF, + providers, + selEmbedProvider, + selGenProvider, + selEmbedModel, + selGenModel, + } = this.plugin.pluginData; + const t = get(_); - async cancelIndexing() { - // if (this.app.vault.adapter.exists(this.getVectorStoreFile())) await this.app.vault.adapter.remove(this.getVectorStoreFile()); - papaState.set('uninitialized'); - papaIndexingProgress.set(0); - } + if (!(await this.canInit())) return; - canRunPapa() { - const t = get(_); - if (get(papaState) === 'running') return new Notice(t('notice.still_running'), 4000) && false; - else if (get(papaState) === 'indexing' || get(papaState) === 'indexing-pause' || get(papaState) === 'loading') - return new Notice(t('notice.still_indexing'), 4000) && false; - else if (get(papaState) === 'error') return new Notice(t('notice.error'), 4000) && false; - else if (get(papaState) !== 'idle') return new Notice(t('notice.not_initialized'), 4000) && false; - return true; + if (get(papaState) !== "indexing-pause") { + papaState.set("loading"); + Log.info( + "Initializing second brain", + "\nGen Model: ", + selGenModel, + "\nEmbed Model: ", + selEmbedModel, + ); + try { + await this.papa.init({ + baseProviders: providers, + selEmbedProvider, + selGenProvider, + selEmbedModel, + selGenModel, + langsmithApiKey: debuggingLangchainKey || undefined, + logLvl: isVerbose ? LogLvl.DEBUG : LogLvl.DISABLED, + }); + } catch (e) { + Log.error(e); + papaState.set("error"); + return new Notice(t("notice.failed", { values: { error: e } }), 4000); + } + // check if vector store data exists + if (await this.app.vault.adapter.exists(this.getVectorStoreFile())) { + const vectorStoreData = await this.app.vault.adapter.readBinary( + this.getVectorStoreFile(), + ); + await this.papa.load(new Uint8Array(vectorStoreData)); + } } + const mdFiles = this.app.vault.getMarkdownFiles(); + const docs = await obsidianDocumentLoader( + await this.createPapaObsidianFiles( + mdFiles.filter((mdFile: TFile) => { + for (const exclude of excludeFF) + if (wildTest(exclude, mdFile.path)) return false; + return true; + }), + ), + ); + papaState.set("indexing"); + let needsSave = false; + try { + let lastTime = Date.now(); + const timePerDoc = []; - async runPapa() { - papaState.set('running'); - try { - const cH = get(chatHistory); - const userQuery = cH[cH.length - 1].content; - const responseStream = this.papa.run({ - isRAG: get(data).isUsingRag, - userQuery, - chatHistory: serializeChatHistory(cH.slice(0, cH.length - 1)), - lang: get(data).assistantLanguage, - }); - for await (const response of responseStream) { - runState.set(response.status); - runContent.set(response.content); - } - } catch (error) { - const errorMsg = get(_)('notice.run_failed', { values: { error } }); - // Log.error(errorMsg); - runContent.set(errorMsg); - // papaState.set('error'); - // errorState.set('run-failed'); - new Notice(errorMsg, 4000); + let lastTotalDocs = 0; + for await (const result of this.papa.embedDocuments(docs)) { + needsSave = + (!this.needsToSaveVectorStoreData && result.numAdded > 0) || + result.numDeleted > 0; + const progress = + ((result.numAdded + result.numSkipped) / docs.length) * 100; + papaIndexingProgress.set(Math.max(progress, get(papaIndexingProgress))); + const currentTime = Date.now(); + timePerDoc.push(currentTime - lastTime); + const numberOfDocumentsRemaining = + docs.length * (1 - get(papaIndexingProgress) / 100); + const averageTimePerDocumentInSeconds = + timePerDoc.reduce((a, b) => a + b, 0) / + timePerDoc.length / + (result.numAdded + result.numSkipped - lastTotalDocs) / + 1000; + lastTotalDocs = result.numAdded + result.numSkipped; + if (timePerDoc.length > 5) { + timePerDoc.shift(); + papaIndexingTimeLeft.set( + Math.ceil( + averageTimePerDocumentInSeconds * numberOfDocumentsRemaining, + ), + ); } - papaState.set('idle'); + lastTime = currentTime; + if (get(papaState) === "indexing-pause") break; + } + } catch (e) { + Log.error(e); + papaState.set("error"); + errorState.set("failed-indexing"); + new Notice(t("notice.failed_indexing"), 4000); } - async createFilenameForChat() { - let fileName = await this.papa.createTitleFromChatHistory(get(data).assistantLanguage, serializeChatHistory(get(chatHistory))); - // File name cannot contain any of the following characters: \, /, :, *, ?, ", <, >, |, # - fileName = fileName.replace(/[\\/:*?"<>|#]/g, ''); - return fileName; + this.needsToSaveVectorStoreData = needsSave; + this.saveVectorStoreData(); + if (get(papaIndexingProgress) === 100) { + new Notice(t("notice.done"), 2000); + papaIndexingProgress.set(0); + papaState.set("idle"); } + } - getVectorStoreFile() { - const d = get(data); - return normalizePath(this.pluginDir + '/vectorstores/' + (d.isIncognitoMode ? d.ollamaEmbedModel.model : d.openAIEmbedModel.model) + '.bin'); + // temporary function to create obsidian files for papa, refactor later + private async createPapaObsidianFiles(files: TFile[]) { + let obsidianFiles = []; + for (const file of files) { + const fileMetadata = this.app.metadataCache.getFileCache(file); + if (!fileMetadata) continue; + const noteContent = await this.app.vault.cachedRead(file); + obsidianFiles.push({ + path: file.path, + content: noteContent, + metadata: fileMetadata, + }); } + return obsidianFiles; + } - async saveVectorStoreData() { - if (this.needsToSaveVectorStoreData && this.papa) { - Log.debug('Saving vector store data'); - this.needsToSaveVectorStoreData = false; - // create vectorstores directory if it doesn't exist - (await this.app.vault.adapter.exists(this.pluginDir + '/vectorstores')) || (await this.app.vault.adapter.mkdir(this.pluginDir + '/vectorstores')); - await this.app.vault.adapter.writeBinary(this.getVectorStoreFile(), await this.papa.getData()); - Log.info('Saved vector store data'); - } - } + async cancelIndexing() { + // if (this.app.vault.adapter.exists(this.getVectorStoreFile())) await this.app.vault.adapter.remove(this.getVectorStoreFile()); + papaState.set("uninitialized"); + papaIndexingProgress.set(0); + } - async onFileChange(file: TFile) { - if (!this.papa) return; - for (const exclude of get(data).excludeFF) if (wildTest(exclude, file.path)) return; - const docs = await obsidianDocumentLoader(this.app, [file]); - this.papa.embedDocuments(docs, 'byFile'); - this.needsToSaveVectorStoreData = true; - } - async onFileDelete(file: TFile) { - if (!this.papa) return; - for (const exclude of get(data).excludeFF) if (wildTest(exclude, file.path)) return; - const docs = await obsidianDocumentLoader(this.app, [file]); - this.papa.deleteDocuments({ docs }); - this.needsToSaveVectorStoreData = true; - } - async onFileRename(file: TFile, oldPath: string) { - if (!this.papa) return; - for (const exclude of get(data).excludeFF) if (wildTest(exclude, file.path)) return; - await this.papa.deleteDocuments({ sources: [oldPath] }); - const docs = await obsidianDocumentLoader(this.app, [file]); - this.papa.embedDocuments(docs, 'byFile'); - this.needsToSaveVectorStoreData = true; - } + canRunPapa() { + const t = get(_); + if (get(papaState) === "running") + return new Notice(t("notice.still_running"), 4000) && false; + else if ( + get(papaState) === "indexing" || + get(papaState) === "indexing-pause" || + get(papaState) === "loading" + ) + return new Notice(t("notice.still_indexing"), 4000) && false; + else if (get(papaState) === "error") + return new Notice(t("notice.error"), 4000) && false; + else if (get(papaState) !== "idle") + return new Notice(t("notice.not_initialized"), 4000) && false; + return true; + } - setSimilarityThreshold(value: number) { - if (this.papa) this.papa.setSimilarityThreshold(value); + async runPapa() { + papaState.set("running"); + try { + const cH = get(chatHistory); + const userQuery = cH[cH.length - 1].content; + const responseStream = this.papa.run({ + isRAG: get(data).isUsingRag, + userQuery, + chatHistory: serializeChatHistory(cH.slice(0, cH.length - 1)), + lang: get(data).assistantLanguage, + }); + for await (const response of responseStream) { + runState.set(response.status); + runContent.set(response.content); + } + } catch (error) { + const errorMsg = get(_)("notice.run_failed", { values: { error } }); + // Log.error(errorMsg); + runContent.set(errorMsg); + // papaState.set('error'); + // errorState.set('run-failed'); + new Notice(errorMsg, 4000); } + papaState.set("idle"); + } - stopRun() { - if (this.papa) this.papa.stopRun(); - papaState.set('idle'); - } + async createFilenameForChat() { + let fileName = await this.papa.createTitleFromChatHistory( + get(data).assistantLanguage, + serializeChatHistory(get(chatHistory)), + ); + // File name cannot contain any of the following characters: \, /, :, *, ?, ", <, >, |, # + fileName = fileName.replace(/[\\/:*?"<>|#]/g, ""); + return fileName; + } - setNumOfDocsToRetrieve(k: number) { - if (this.papa) this.papa.setNumOfDocsToRetrieve(k); - } + getVectorStoreFile() { + const { selEmbedModel } = get(data); + return normalizePath( + this.pluginDir + "/vectorstores/" + selEmbedModel + ".bin", + ); + } - setGenModel(genModel: GenModel) { - if (this.papa) this.papa.setGenModel(genModel); + async saveVectorStoreData() { + if (this.needsToSaveVectorStoreData) { + Log.debug("Saving vector store data"); + this.needsToSaveVectorStoreData = false; + // create vectorstores directory if it doesn't exist + (await this.app.vault.adapter.exists(this.pluginDir + "/vectorstores")) || + (await this.app.vault.adapter.mkdir(this.pluginDir + "/vectorstores")); + await this.app.vault.adapter.writeBinary( + this.getVectorStoreFile(), + (await this.papa.getData()).buffer as ArrayBuffer, + ); + Log.info("Saved vector store data"); } + } - setTracer(langchainKey: string) { - if (this.papa) this.papa.setTracer(langchainKey); - } + async onFileChange(file: TFile) { + if (!this.papa) return; + for (const exclude of get(data).excludeFF) + if (wildTest(exclude, file.path)) return; + const docs = await obsidianDocumentLoader( + await this.createPapaObsidianFiles([file]), + ); + this.papa.embedDocuments(docs, "byFile"); + this.needsToSaveVectorStoreData = true; + } + async onFileDelete(file: TFile) { + if (!this.papa) return; + for (const exclude of get(data).excludeFF) + if (wildTest(exclude, file.path)) return; + const docs = await obsidianDocumentLoader( + await this.createPapaObsidianFiles([file]), + ); + this.papa.deleteDocuments({ docs }); + this.needsToSaveVectorStoreData = true; + } + async onFileRename(file: TFile, oldPath: string) { + if (!this.papa) return; + for (const exclude of get(data).excludeFF) + if (wildTest(exclude, file.path)) return; + await this.papa.deleteDocuments({ sources: [oldPath] }); + const docs = await obsidianDocumentLoader( + await this.createPapaObsidianFiles([file]), + ); + this.papa.embedDocuments(docs, "byFile"); + this.needsToSaveVectorStoreData = true; + } + + configure(config: Partial) { + this.papa.configure(config); + } + + stopRun() { + this.papa.stopRun(); + papaState.set("idle"); + } + + private async canInit(): Promise { + const t = get(_); + + if (get(papaState) === "running") { + new Notice(t("notice.still_running"), 4000); + return false; + } else if (get(papaState) === "indexing" || get(papaState) === "loading") { + new Notice(t("notice.still_indexing"), 4000); + return false; + } else if (!(await this.papa.isEmbedProviderSetuped())) { + papaState.set("error"); + return false; + } else return true; + } } diff --git a/src/components/Chat/ChatList.svelte b/src/components/Chat/ChatList.svelte new file mode 100644 index 00000000..5a331905 --- /dev/null +++ b/src/components/Chat/ChatList.svelte @@ -0,0 +1,90 @@ + + +
+ {#if chats.length > 0} +
+ Recent +
+ {/if} + {#each chats as chat} + + + +
await activateNewSession(chat.id)} + onmouseenter={() => (hoveredChatId = chat.id)} + onmouseleave={() => (hoveredChatId = null)} + > +
{chat.title}
+
+ {formatDDMMYY_HHMM(chat.lastAccessed)} + {#if hoveredChatId === chat.id} +
e.stopPropagation()}> +
await deleteChat(chat.id)} + >
+
+ {/if} +
+
+ {/each} +
diff --git a/src/components/Chat/Input.svelte b/src/components/Chat/Input.svelte old mode 100644 new mode 100755 index bd67553d..e465df45 --- a/src/components/Chat/Input.svelte +++ b/src/components/Chat/Input.svelte @@ -1,148 +1,313 @@ - - - -
+
- {#if $chatHistory.length > 1} -
$plugin.saveChat()} hidden={$papaState === 'running'} /> - {/if} -
- +
+ {#each files as file} +
+ {#if file.type === "text/plain"} +
+ {:else if file.type === "application/json"} +
+ {/if} +
+ {file.name} +
+ + +
removeAttachedFile(file)} + class="hover:bg-[buttonface] flex items-center justify-center h-4 w-4 bg-white rounded-sm mr-1 my-1" + >
+
+ {/each}
- {#if $chatHistory.length > 1} - -
-
- + + - {:else} -
- + +
+
+ + onFileAttachment(event)} + /> + +
+ {#if !currentSession.session || currentSession.session.messageState === MessageState.idle} + + {:else if currentSession.session.messageState === MessageState.answering} + {/if}
- {/if} +
+ + diff --git a/src/components/Chat/MessageContainer.svelte b/src/components/Chat/MessageContainer.svelte old mode 100644 new mode 100755 index 458267a8..778d520f --- a/src/components/Chat/MessageContainer.svelte +++ b/src/components/Chat/MessageContainer.svelte @@ -1,31 +1,158 @@ -{#if role === 'User'} - {#if $data.isChatComfy} -
- -
- +
+ {#each messages!! as messagePair} +
+
+ +
+ + + +
+ redoMessage(messagePair.id, messagePair.model)} + >
+ + + + +
console.log("split")} + >
+ + + + +
console.log("edit")} + >
+ + + + +
+ copyToClipboard(messagePair.userMessage.content)} + >
- {:else} -
-
{$t('chat.user')}
- + +
+ {#if !messagePair.assistantMessage.content} + + {:else} +
+ {/if} + {#if !(messagePair.assistantMessage.state === AssistantState.streaming)} +
+ + + +
+ copyToClipboard( + messagePair.assistantMessage.content, + )} + >
+ + + +
branchOff(messagePair.id)} + > + > +
+ + + +
+ redoMessage(messagePair.id, messagePair.model)} + >
+
+ {/if}
- {/if} -{:else if $data.isChatComfy} -
- -
-{:else} -
-
{$t('chat.assistant')}
- -
-{/if} + {/each} +
diff --git a/src/components/Chat/QuickSettingsDrawer.svelte b/src/components/Chat/QuickSettingsDrawer.svelte old mode 100644 new mode 100755 index 90f24af5..aeb82d5b --- a/src/components/Chat/QuickSettingsDrawer.svelte +++ b/src/components/Chat/QuickSettingsDrawer.svelte @@ -1,94 +1,75 @@ - + +
+ updateChatTitle()} + type="text" + spellcheck="false" + /> + {#if currentSession.session} +
diff --git a/src/components/Logos/Logo.svelte b/src/components/Logos/Logo.svelte old mode 100644 new mode 100755 index 429edae0..2bbc4b57 --- a/src/components/Logos/Logo.svelte +++ b/src/components/Logos/Logo.svelte @@ -1,9 +1,5 @@ - - diff --git a/src/components/Logos/LogoDetailed.svelte b/src/components/Logos/LogoDetailed.svelte old mode 100644 new mode 100755 index 55a5f480..b4253232 --- a/src/components/Logos/LogoDetailed.svelte +++ b/src/components/Logos/LogoDetailed.svelte @@ -1,5 +1,5 @@ + import { onMount } from "svelte"; + import SettingContainer from "../Settings/SettingContainer.svelte"; + import ButtonComponent from "../base/Button.svelte"; + import { getData } from "../../stores/dataStore.svelte"; + import { papaState } from "../../stores/store"; + import type { ExcludeFoldersModal } from "./ExcludeFoldersModal"; + import Button from "../base/Button.svelte"; + import Dropdown from "../base/Dropdown.svelte"; + import Toggle from "../base/Toggle.svelte"; + import { prepareFuzzySearch, TAbstractFile } from "obsidian"; + import FolderSuggest from "./FolderSuggest.svelte"; + import { getPlugin } from "../../stores/state.svelte"; + + interface Props { + modal: ExcludeFoldersModal; + } + + const plugin = getPlugin(); + + const data = getData(); + + const suggestionLength: number = 100; + + let { modal }: Props = $props(); + + //TODO: Finish implementing modes + + export const modes = ["File/Folder", "Filetyp"] as const; + + let exclusionMode: (typeof modes)[number] = $state("File/Folder"); + + function matchFilesFolders(query: string): TAbstractFile[] { + let allFiles = plugin.app.vault.getAllLoadedFiles(); + + if (!query) { + return allFiles.slice(0, 10); + } + + const fuzzySearch = prepareFuzzySearch(query); + + const matches = allFiles + .map((file) => ({ + file, + match: fuzzySearch(file.path), + })) + .filter((item) => item.match) + .sort((a, b) => b.match!.score - a.match!.score) + .map((item) => item.file); + + return matches; + } + + function addExcludeFolder(folder: string) { + if (folder.trim()) { + data.addIndexList(folder.trim()); + papaState.set("settings-change"); + } + } + + function removeExcludeFolder(folder: string) { + data.removeIndexList(folder); + papaState.set("settings-change"); + } + + + + + + diff --git a/src/components/Modal/ExcludeFoldersModal.ts b/src/components/Modal/ExcludeFoldersModal.ts new file mode 100644 index 00000000..670a228f --- /dev/null +++ b/src/components/Modal/ExcludeFoldersModal.ts @@ -0,0 +1,25 @@ +import { App, Modal } from "obsidian"; +import ExcludeFoldersComponent from "./ExcludeFoldersModal.svelte"; +import { mount } from "svelte"; + +export class ExcludeFoldersModal extends Modal { + component!: ExcludeFoldersComponent; + + constructor(app: App) { + super(app); + } + + onOpen() { + this.component = mount(ExcludeFoldersComponent, { + target: this.contentEl, + props: { + modal: this, + }, + }); + } + + onClose() { + const { contentEl } = this; + contentEl.empty(); + } +} diff --git a/src/components/Modal/FolderSuggest.svelte b/src/components/Modal/FolderSuggest.svelte new file mode 100644 index 00000000..baa5fe98 --- /dev/null +++ b/src/components/Modal/FolderSuggest.svelte @@ -0,0 +1,97 @@ + + + diff --git a/src/components/Modal/RemoveModal.svelte b/src/components/Modal/RemoveModal.svelte old mode 100644 new mode 100755 index 3f4402c9..405f9125 --- a/src/components/Modal/RemoveModal.svelte +++ b/src/components/Modal/RemoveModal.svelte @@ -1,22 +1,24 @@ - --> - + diff --git a/src/components/Modal/RemoveModal.ts b/src/components/Modal/RemoveModal.ts old mode 100644 new mode 100755 index e8365dec..17fdd743 --- a/src/components/Modal/RemoveModal.ts +++ b/src/components/Modal/RemoveModal.ts @@ -1,23 +1,24 @@ -import { Modal, App } from 'obsidian'; -import RemoveComponent from './RemoveModal.svelte'; +import { Modal, App } from "obsidian"; +import RemoveComponent from "./RemoveModal.svelte"; +import { mount } from "svelte"; export class RemoveModal extends Modal { - component: RemoveComponent; - constructor(app: App) { - super(app); - } + component: RemoveComponent; + constructor(app: App) { + super(app); + } - onOpen() { - new RemoveComponent({ - target: this.contentEl, - props: { - modal: this, - }, - }); - } + onOpen() { + mount(RemoveComponent, { + target: this.contentEl, + props: { + modal: this, + }, + }); + } - onClose() { - const { contentEl } = this; - contentEl.empty(); - } + onClose() { + const { contentEl } = this; + contentEl.empty(); + } } diff --git a/src/components/QueryClientProvider.svelte b/src/components/QueryClientProvider.svelte new file mode 100644 index 00000000..cb6db0db --- /dev/null +++ b/src/components/QueryClientProvider.svelte @@ -0,0 +1,18 @@ + + + + {@const Component = component} + + diff --git a/src/components/Settings/ConfiguredProvider.svelte b/src/components/Settings/ConfiguredProvider.svelte new file mode 100644 index 00000000..fd3f69ce --- /dev/null +++ b/src/components/Settings/ConfiguredProvider.svelte @@ -0,0 +1,171 @@ + + + + onAccordionClick(configuredProvider)} + class="sync-exclude-folder w-[-webkit-fill-available] !mr-0" + > + +
+ + {configuredProvider} + {#if query.data} +
+ {:else} - + {/if} diff --git a/src/components/base/DotAnimation.svelte b/src/components/base/DotAnimation.svelte old mode 100644 new mode 100755 index fedca726..3c490fba --- a/src/components/base/DotAnimation.svelte +++ b/src/components/base/DotAnimation.svelte @@ -1,8 +1,8 @@ {#each ['', '.', '..', '...'] as sequence, i} diff --git a/src/components/base/Dropdown.svelte b/src/components/base/Dropdown.svelte old mode 100644 new mode 100755 index 13b41a23..efe4dbce --- a/src/components/base/Dropdown.svelte +++ b/src/components/base/Dropdown.svelte @@ -1,11 +1,38 @@ - + + diff --git a/src/components/base/FilePopover.svelte b/src/components/base/FilePopover.svelte new file mode 100644 index 00000000..d4cefa84 --- /dev/null +++ b/src/components/base/FilePopover.svelte @@ -0,0 +1,83 @@ + + + + + console.log(e.currentTarget.value)} + class="sr-only" + /> + + + {#each filteredFiles as file, i (i + file.basename)} + + {#snippet children({ selected })} +
+
+ {file.basename} +
+
+ {file.parent?.path} +
+
+ {/snippet} +
+ {:else} + No match found. + {/each} +
+
+
diff --git a/src/components/base/Icon.svelte b/src/components/base/Icon.svelte new file mode 100644 index 00000000..e5f9df13 --- /dev/null +++ b/src/components/base/Icon.svelte @@ -0,0 +1,28 @@ + + +
console.log(e)} + class={"flex items-center " + className} + style={"--icon-size: " + size} + {onclick} +>
diff --git a/src/components/base/LoadingAnimation.svelte b/src/components/base/LoadingAnimation.svelte old mode 100644 new mode 100755 diff --git a/src/components/base/ProgressBar.svelte b/src/components/base/ProgressBar.svelte old mode 100644 new mode 100755 index c3976dbf..64694e5f --- a/src/components/base/ProgressBar.svelte +++ b/src/components/base/ProgressBar.svelte @@ -1,14 +1,21 @@ +> + + + + + diff --git a/src/utils/dataValidation.ts b/src/utils/dataValidation.ts new file mode 100644 index 00000000..69d17636 --- /dev/null +++ b/src/utils/dataValidation.ts @@ -0,0 +1,824 @@ +import { + Prompts, + type Language, + registeredProviders, + type RegisteredProvider, +} from "papa-ts"; +import type { PluginData } from "../main"; +import type { + ProviderConfigs, + GetProviderConfig, + GetProviderAuth, +} from "../types/providers"; +import { + DEFAULT_SETTINGS, + DEFAULT_PROVIDER_CONFIGS, +} from "../constants/defaults"; + +/** + * Validation result type + */ +export interface ValidationResult { + isValid: boolean; + errors: string[]; + warnings: string[]; + data?: any; // The corrected/validated data +} + +/** + * Validates a string value + */ +function validateString( + value: unknown, + fieldName: string, + required: boolean = true, +): ValidationResult { + const errors: string[] = []; + + if (value === undefined || value === null) { + if (required) { + errors.push(`${fieldName} is required`); + } + return { isValid: !required, errors, warnings: [] }; + } + + if (typeof value !== "string") { + errors.push(`${fieldName} must be a string, got ${typeof value}`); + return { isValid: false, errors, warnings: [] }; + } + + return { isValid: true, errors: [], warnings: [], data: value }; +} + +/** + * Validates a boolean value + */ +function validateBoolean( + value: unknown, + fieldName: string, + defaultValue: boolean, +): ValidationResult { + if (value === undefined || value === null) { + return { isValid: true, errors: [], warnings: [], data: defaultValue }; + } + + if (typeof value !== "boolean") { + return { + isValid: true, + errors: [], + warnings: [ + `${fieldName} should be boolean, got ${typeof value}. Using default: ${defaultValue}`, + ], + data: defaultValue, + }; + } + + return { isValid: true, errors: [], warnings: [], data: value }; +} + +/** + * Validates a number value + */ +function validateNumber( + value: unknown, + fieldName: string, + min?: number, + max?: number, +): ValidationResult { + const errors: string[] = []; + const warnings: string[] = []; + + if ( + value === undefined || + value === null || + typeof value !== "number" || + isNaN(value) + ) { + errors.push(`${fieldName} must be a valid number`); + return { isValid: false, errors, warnings }; + } + + if (min !== undefined && value < min) { + warnings.push(`${fieldName} is below minimum ${min}, clamping to ${min}`); + return { isValid: true, errors: [], warnings, data: min }; + } + + if (max !== undefined && value > max) { + warnings.push(`${fieldName} is above maximum ${max}, clamping to ${max}`); + return { isValid: true, errors: [], warnings, data: max }; + } + + return { isValid: true, errors: [], warnings: [], data: value }; +} + +/** + * Validates an array of strings + */ +function validateStringArray( + value: unknown, + fieldName: string, +): ValidationResult { + const errors: string[] = []; + const warnings: string[] = []; + + if (value === undefined || value === null) { + return { isValid: true, errors: [], warnings: [], data: [] }; + } + + if (!Array.isArray(value)) { + warnings.push( + `${fieldName} should be an array, got ${typeof value}. Using empty array.`, + ); + return { isValid: true, errors: [], warnings, data: [] }; + } + + const validStrings = value.filter((item) => typeof item === "string"); + const invalidCount = value.length - validStrings.length; + + if (invalidCount > 0) { + warnings.push( + `${fieldName} contained ${invalidCount} non-string items that were filtered out`, + ); + } + + return { isValid: true, errors: [], warnings, data: validStrings }; +} + +/** + * Validates a Language value + */ +function validateLanguage(value: unknown, fieldName: string): ValidationResult { + const validLanguages = ["en", "de"]; // Add more as needed + + if (value === undefined || value === null) { + return { isValid: true, errors: [], warnings: [], data: "en" }; + } + + if (typeof value !== "string" || !validLanguages.includes(value)) { + return { + isValid: true, + errors: [], + warnings: [`${fieldName} "${value}" is not valid. Using default: en`], + data: "en", + }; + } + + return { isValid: true, errors: [], warnings: [], data: value as Language }; +} + +/** + * Validates embedding model configuration + */ +function validateEmbedModelConfig( + value: unknown, + modelName: string, +): ValidationResult { + const errors: string[] = []; + const warnings: string[] = []; + + if (!value || typeof value !== "object") { + errors.push(`Embed model config for ${modelName} must be an object`); + return { isValid: false, errors, warnings }; + } + + const config = value as any; + const thresholdValidation = validateNumber( + config.similarityThreshold, + `${modelName}.similarityThreshold`, + 0, + 1, + ); + + if (!thresholdValidation.isValid) { + errors.push(...thresholdValidation.errors); + return { + isValid: false, + errors, + warnings: [...warnings, ...thresholdValidation.warnings], + }; + } + + return { + isValid: true, + errors: [], + warnings: [...warnings, ...thresholdValidation.warnings], + data: { + similarityThreshold: thresholdValidation.data, + }, + }; +} + +/** + * Validates generation model configuration + */ +function validateGenModelConfig( + value: unknown, + modelName: string, +): ValidationResult { + const errors: string[] = []; + const warnings: string[] = []; + + if (!value || typeof value !== "object") { + errors.push(`Gen model config for ${modelName} must be an object`); + return { isValid: false, errors, warnings }; + } + + const config = value as any; + const tempValidation = validateNumber( + config.temperature, + `${modelName}.temperature`, + 0, + 2, + ); + const contextValidation = validateNumber( + config.contextWindow, + `${modelName}.contextWindow`, + 1, + ); + + if (!tempValidation.isValid || !contextValidation.isValid) { + errors.push(...tempValidation.errors, ...contextValidation.errors); + return { + isValid: false, + errors, + warnings: [ + ...warnings, + ...tempValidation.warnings, + ...contextValidation.warnings, + ], + }; + } + + return { + isValid: true, + errors: [], + warnings: [ + ...warnings, + ...tempValidation.warnings, + ...contextValidation.warnings, + ], + data: { + temperature: tempValidation.data, + contextWindow: contextValidation.data, + }, + }; +} + +/** + * Validates a Map or object of models + */ +function validateModelMap( + value: unknown, + validateModelFn: (value: unknown, modelName: string) => ValidationResult, + defaultMap: Map, + mapName: string, +): ValidationResult { + const errors: string[] = []; + const warnings: string[] = []; + const validatedMap = new Map(); + + // If Map was serialized to object (happens in storage), convert back + if (value && typeof value === "object" && !value.entries && !value.size) { + // Handle plain object conversion to Map + try { + for (const [key, modelConfig] of Object.entries( + value as Record, + )) { + const validation = validateModelFn(modelConfig, `${mapName}.${key}`); + if (validation.isValid) { + validatedMap.set(key, validation.data as T); + warnings.push(...validation.warnings); + } else { + warnings.push( + `Skipping invalid model config for ${key}: ${validation.errors.join(", ")}`, + ); + } + } + } catch (e) { + warnings.push(`Error converting object to Map: ${e}. Using defaults.`); + } + } else if (value instanceof Map) { + // Handle actual Map instance + try { + for (const [key, modelConfig] of value.entries()) { + const validation = validateModelFn(modelConfig, `${mapName}.${key}`); + if (validation.isValid) { + validatedMap.set(key, validation.data as T); + warnings.push(...validation.warnings); + } else { + warnings.push( + `Skipping invalid model config for ${key}: ${validation.errors.join(", ")}`, + ); + } + } + } catch (e) { + warnings.push(`Error processing Map: ${e}. Using defaults.`); + } + } else { + warnings.push(`${mapName} is not a valid Map or object. Using defaults.`); + } + + // Ensure we have at least the default models + for (const [key, value] of defaultMap.entries()) { + if (!validatedMap.has(key)) { + validatedMap.set(key, value); + } + } + + return { + isValid: true, // We can always fall back to defaults + errors, + warnings, + data: validatedMap, + }; +} + +/** + * Validates the provider auth configuration + */ +function validateProviderAuth( + provider: T, + value: unknown, +): ValidationResult { + const errors: string[] = []; + const warnings: string[] = []; + const validatedAuth: Record = {}; + + if (!value || typeof value !== "object") { + warnings.push( + `Provider auth for ${provider} is missing or invalid, using defaults.`, + ); + return { + isValid: true, + errors, + warnings, + data: { ...DEFAULT_PROVIDER_CONFIGS[provider].providerAuth }, + }; + } + + const config = value as Record; + const defaultAuth = DEFAULT_PROVIDER_CONFIGS[provider].providerAuth; + + // Validate each auth field + for (const [key, defaultValue] of Object.entries(defaultAuth)) { + const authValue = config[key]; + const validation = validateString( + authValue, + `${provider}.providerAuth.${key}`, + false, + ); + + if (validation.isValid && validation.data !== undefined) { + validatedAuth[key] = validation.data; + } else { + validatedAuth[key] = defaultValue as string; + if (validation.warnings.length > 0) { + warnings.push(...validation.warnings); + } + } + } + + return { + isValid: true, + errors, + warnings, + data: validatedAuth as GetProviderAuth, + }; +} + +/** + * Validates a single provider configuration + */ +function validateProviderConfig( + provider: T, + value: unknown, +): ValidationResult { + const errors: string[] = []; + const warnings: string[] = []; + + if (!value || typeof value !== "object") { + errors.push(`Provider config for ${provider} must be an object`); + return { + isValid: true, + errors, + warnings: [...warnings, `Using default config for ${provider}`], + data: DEFAULT_PROVIDER_CONFIGS[provider], + }; + } + + const config = value as any; + const defaultConfig = DEFAULT_PROVIDER_CONFIGS[provider]; + const validatedConfig: any = {}; + + // Validate isConfigured + const configuredValidation = validateBoolean( + config.isConfigured, + `${provider}.isConfigured`, + false, + ); + validatedConfig.isConfigured = configuredValidation.data; + warnings.push(...configuredValidation.warnings); + + // Validate providerAuth + const authValidation = validateProviderAuth(provider, config.providerAuth); + validatedConfig.providerAuth = authValidation.data; + warnings.push(...authValidation.warnings); + + // Validate embedding models if provider supports them + if (defaultConfig.embedModels instanceof Map) { + // Validate the map of embed models + const embedModelsValidation = validateModelMap( + config.embedModels, + validateEmbedModelConfig, + defaultConfig.embedModels, + `${provider}.embedModels`, + ); + validatedConfig.embedModels = embedModelsValidation.data; + warnings.push(...embedModelsValidation.warnings); + + // Validate selected embed model + const selEmbedValidation = validateString( + config.selEmbedModel, + `${provider}.selEmbedModel`, + false, + ); + const selectedEmbed = + selEmbedValidation.data || defaultConfig.selEmbedModel; + + if (!validatedConfig.embedModels.has(selectedEmbed)) { + warnings.push( + `Selected embed model ${selectedEmbed} not found, using default: ${defaultConfig.selEmbedModel}`, + ); + validatedConfig.selEmbedModel = defaultConfig.selEmbedModel; + } else { + validatedConfig.selEmbedModel = selectedEmbed; + } + } + + // Validate generation models if provider supports them + if (defaultConfig.genModels instanceof Map) { + // Validate the map of gen models + const genModelsValidation = validateModelMap( + config.genModels, + validateGenModelConfig, + defaultConfig.genModels, + `${provider}.genModels`, + ); + validatedConfig.genModels = genModelsValidation.data; + warnings.push(...genModelsValidation.warnings); + + // Validate selected gen model + const selGenValidation = validateString( + config.selGenModel, + `${provider}.selGenModel`, + false, + ); + const selectedGen = selGenValidation.data || defaultConfig.selGenModel; + + if (!validatedConfig.genModels.has(selectedGen)) { + warnings.push( + `Selected gen model ${selectedGen} not found, using default: ${defaultConfig.selGenModel}`, + ); + validatedConfig.selGenModel = defaultConfig.selGenModel; + } else { + validatedConfig.selGenModel = selectedGen; + } + } + + return { + isValid: true, + errors: [], + warnings, + data: validatedConfig as GetProviderConfig, + }; +} + +/** + * Validates the entire provider configuration + */ +function validateProviderConfigs(value: unknown): ValidationResult { + const errors: string[] = []; + const warnings: string[] = []; + const validatedConfigs: ProviderConfigs = {} as ProviderConfigs; + + if (!value || typeof value !== "object") { + warnings.push("Provider config is missing or invalid, using defaults"); + return { + isValid: true, + errors: [], + warnings, + data: DEFAULT_PROVIDER_CONFIGS, + }; + } + + const configs = value as any; + + // Validate each registered provider + for (const provider of registeredProviders) { + const validation = validateProviderConfig(provider, configs[provider]); + if (validation.isValid) { + validatedConfigs[provider] = validation.data; + warnings.push(...validation.warnings); + } else { + errors.push(...validation.errors); + warnings.push( + `Using default config for ${provider} due to validation errors`, + ); + validatedConfigs[provider] = DEFAULT_PROVIDER_CONFIGS[provider]; + } + } + + return { + isValid: true, // We can always fall back to defaults + errors, + warnings, + data: validatedConfigs as ProviderConfigs, + }; +} + +/** + * Main function to validate all plugin data + */ +export function validatePluginData(rawData: unknown): ValidationResult { + const errors: string[] = []; + const warnings: string[] = []; + const validatedData: Partial = {}; + + if (!rawData || typeof rawData !== "object") { + warnings.push("Plugin data is missing or invalid, using all defaults"); + return { + isValid: true, + errors: [], + warnings, + data: DEFAULT_SETTINGS, + }; + } + + const data = rawData as any; + + // Validate provider configuration + const providerValidation = validateProviderConfigs(data.providerConfig); + validatedData.providerConfig = providerValidation.data; + errors.push(...providerValidation.errors); + warnings.push(...providerValidation.warnings); + + // Validate provider selections + // --------------------------------------------------------------------- + // Composite selection validation (selEmbedModel / selGenModel) + // Supports new shape: + // selGenModel: { provider: RegisteredGenProvider; model: string } + // selEmbedModel: { provider: RegisteredEmbedProvider; model: string } + // Backward compatibility: + // legacy fields selGenProvider / selEmbedProvider (string) + a per-provider + // selected model stored previously (deprecated). If legacy is present and + // composite is missing or invalid we synthesize a composite. + // --------------------------------------------------------------------- + function validateCompositeSelection( + key: "selGenModel" | "selEmbedModel", + value: unknown, + defaultValue: any, + isGen: boolean, + ): { data: typeof defaultValue; warnings: string[] } { + const warnings: string[] = []; + const isObj = + value && + typeof value === "object" && + "provider" in (value as any) && + "model" in (value as any); + + if (!isObj) { + warnings.push(`${key} missing or invalid, attempting legacy fallback.`); + return { data: defaultValue, warnings }; + } + + const { provider, model } = value as any; + if ( + !provider || + typeof provider !== "string" || + !model || + typeof model !== "string" + ) { + warnings.push(`${key} has invalid provider/model fields, using default.`); + return { data: defaultValue, warnings }; + } + + if (!registeredProviders.includes(provider as any)) { + warnings.push( + `${key}.provider "${provider}" not registered, using default.`, + ); + return { data: defaultValue, warnings }; + } + + const providerCfg: any = validatedData.providerConfig?.[provider]; + if (!providerCfg) { + warnings.push( + `${key}.provider "${provider}" has no config, using default.`, + ); + return { data: defaultValue, warnings }; + } + + const map: Map | undefined = isGen + ? providerCfg.genModels + : providerCfg.embedModels; + if (!(map instanceof Map)) { + warnings.push( + `${key}.provider "${provider}" missing model map, using default.`, + ); + return { data: defaultValue, warnings }; + } + if (!map.has(model)) { + warnings.push( + `${key}.model "${model}" not found for provider "${provider}", using default.`, + ); + return { data: defaultValue, warnings }; + } + + return { data: { provider, model }, warnings }; + } + + // Validate composite selections (new schema) + const genSelValidation = validateCompositeSelection( + "selGenModel", + (data as any).selGenModel, + DEFAULT_SETTINGS.selGenModel, + true, + ); + validatedData.selGenModel = genSelValidation.data; + warnings.push(...genSelValidation.warnings); + + const embedSelValidation = validateCompositeSelection( + "selEmbedModel", + (data as any).selEmbedModel, + DEFAULT_SETTINGS.selEmbedModel, + false, + ); + validatedData.selEmbedModel = embedSelValidation.data; + warnings.push(...embedSelValidation.warnings); + + // Legacy fallback: if composite is still default BUT legacy provider fields exist and match a model, + // attempt to synthesize a better selection once. + if ( + ((data as any).selGenProvider || (data as any).selGenModel) && + genSelValidation.data === DEFAULT_SETTINGS.selGenModel + ) { + const legacyProv = (data as any).selGenProvider; + const legacyModel = + (data as any).selGenModel && typeof (data as any).selGenModel === "string" + ? (data as any).selGenModel + : undefined; + if ( + legacyProv && + typeof legacyProv === "string" && + registeredProviders.includes(legacyProv as any) && + legacyModel + ) { + const cfg: any = validatedData.providerConfig?.[legacyProv]; + if (cfg?.genModels instanceof Map && cfg.genModels.has(legacyModel)) { + validatedData.selGenModel = { + provider: legacyProv, + model: legacyModel, + }; + warnings.push( + `Migrated legacy selGenProvider/selGenModel to composite { provider: "${legacyProv}", model: "${legacyModel}" }.`, + ); + } + } + } + + if ( + ((data as any).selEmbedProvider || (data as any).selEmbedModel) && + embedSelValidation.data === DEFAULT_SETTINGS.selEmbedModel + ) { + const legacyProv = (data as any).selEmbedProvider; + const legacyModel = + (data as any).selEmbedModel && + typeof (data as any).selEmbedModel === "string" + ? (data as any).selEmbedModel + : undefined; + if ( + legacyProv && + typeof legacyProv === "string" && + registeredProviders.includes(legacyProv as any) && + legacyModel + ) { + const cfg: any = validatedData.providerConfig?.[legacyProv]; + if (cfg?.embedModels instanceof Map && cfg.embedModels.has(legacyModel)) { + validatedData.selEmbedModel = { + provider: legacyProv, + model: legacyModel, + }; + warnings.push( + `Migrated legacy selEmbedProvider/selEmbedModel to composite { provider: "${legacyProv}", model: "${legacyModel}" }.`, + ); + } + } + } + + // Validate boolean fields + const booleanFields = [ + "isChatComfy", + "isUsingRag", + "isQuickSettingsOpen", + "isVerbose", + "isOnboarded", + "hideIncognitoWarning", + "isAutostart", + "isExcluding", + ] as const; + + for (const field of booleanFields) { + const validation = validateBoolean( + data[field], + field, + DEFAULT_SETTINGS[field], + ); + validatedData[field] = validation.data; + warnings.push(...validation.warnings); + } + + // Validate string fields + const stringFields = [ + "initialAssistantMessageContent", + "targetFolder", + "defaultChatName", + "debuggingLangchainKey", + ] as const; + + for (const field of stringFields) { + const validation = validateString(data[field], field, false); + validatedData[field] = validation.data || DEFAULT_SETTINGS[field]; + warnings.push(...validation.warnings); + } + + // Validate number fields + const retrieveTopKValidation = validateNumber( + data.retrieveTopK, + "retrieveTopK", + 1, + 1000, + ); + validatedData.retrieveTopK = + retrieveTopKValidation.data || DEFAULT_SETTINGS.retrieveTopK; + warnings.push(...retrieveTopKValidation.warnings); + + // Validate language + const languageValidation = validateLanguage( + data.assistantLanguage, + "assistantLanguage", + ); + validatedData.assistantLanguage = languageValidation.data; + warnings.push(...languageValidation.warnings); + + // Validate string array fields + const excludeFFValidation = validateStringArray(data.excludeFF, "excludeFF"); + validatedData.excludeFF = + excludeFFValidation.data || DEFAULT_SETTINGS.excludeFF; + warnings.push(...excludeFFValidation.warnings); + + const includeFFValidation = validateStringArray(data.includeFF, "includeFF"); + validatedData.includeFF = + includeFFValidation.data || DEFAULT_SETTINGS.includeFF; + warnings.push(...includeFFValidation.warnings); + + // Ensure we have all required fields + const completeData: PluginData = { + ...DEFAULT_SETTINGS, + ...validatedData, + } as PluginData; + + return { + isValid: errors.length === 0, + errors, + warnings, + data: completeData, + }; +} + +/** + * Type guard to check if data is valid PluginData + */ +export function isValidPluginData(data: unknown): data is PluginData { + const validation = validatePluginData(data); + return validation.isValid; +} + +/** + * Safely load and validate plugin data + */ +export function safeLoadPluginData(rawData: unknown): { + data: PluginData; + hasErrors: boolean; + hasWarnings: boolean; + errors: string[]; + warnings: string[]; +} { + const validation = validatePluginData(rawData); + + return { + data: validation.data as PluginData, + hasErrors: validation.errors.length > 0, + hasWarnings: validation.warnings.length > 0, + errors: validation.errors, + warnings: validation.warnings, + }; +} diff --git a/src/utils/utils.ts b/src/utils/utils.ts new file mode 100644 index 00000000..cb833060 --- /dev/null +++ b/src/utils/utils.ts @@ -0,0 +1,50 @@ +import { MarkdownRenderer, setIcon } from "obsidian"; +import { getPlugin } from "../stores/state.svelte"; + +export const icon = (node: HTMLElement, iconId: string) => { + setIcon(node, iconId); +}; + +export function wildTest(wildcard: string, str: string): boolean { + const w = wildcard.replace(/[.+^${}()|[\]\\]/g, "\\$&"); // regexp escape + const re = new RegExp( + `\\b${w.replace(/\*/g, ".*").replace(/\?/g, ".")}`, + "i", + ); + return re.test(str); +} + +export function renderMarkdown(node: HTMLElement, content: string) { + const plugin = getPlugin(); + + const render = (c: string) => { + node.innerHTML = ""; + MarkdownRenderer.render(plugin.app, c ?? "", node, "Chat view.md", plugin); + + const codeElem = node.querySelector( + ".copy-code-button", + ) as HTMLElement | null; + if (codeElem) { + codeElem.className = "clickable-icon"; + icon(codeElem, "copy"); + } + }; + + render(content); + + let raf = 0; + + return { + update(next: string) { + // optional: coalesce rapid streaming updates + cancelAnimationFrame(raf); + raf = requestAnimationFrame(() => { + render(next); + }); + }, + destroy() { + cancelAnimationFrame(raf); + node.innerHTML = ""; + }, + }; +} diff --git a/src/utils/uuid7Validator.ts b/src/utils/uuid7Validator.ts new file mode 100644 index 00000000..3d00e1b0 --- /dev/null +++ b/src/utils/uuid7Validator.ts @@ -0,0 +1,27 @@ +import { v7 as uuidv7, validate, version } from "uuid"; + +declare const brand: unique symbol; +export type UUIDv7 = string & { readonly [brand]: "uuidv7" }; + +// Generate a branded UUIDv7 +export function genUUIDv7(): UUIDv7 { + return uuidv7() as UUIDv7; +} + +// Type guard +export function isUUIDv7(s: string): s is UUIDv7 { + return validate(s) && version(s) === 7; +} + +// Parse Date from a UUIDv7 (first 48 bits are Unix epoch ms) +export function dateFromUUIDv7(id: UUIDv7): Date { + const hex = id.replace(/-/g, "").slice(0, 12); // 48 bits (12 hex chars) + const ms = parseInt(hex, 16); + return new Date(ms); +} + +// Unsafe cast with runtime validation (throws on mismatch) +export function asUUIDv7(s: string): UUIDv7 { + if (!isUUIDv7(s)) throw new Error(`Not a UUIDv7: ${s}`); + return s; +} diff --git a/src/utils/wikiLinkExtraction.ts b/src/utils/wikiLinkExtraction.ts new file mode 100644 index 00000000..647ce31c --- /dev/null +++ b/src/utils/wikiLinkExtraction.ts @@ -0,0 +1,56 @@ +export interface WikiLinkContext { + fullStart: number; + fullEnd: number; + innerStart: number; + innerEnd: number; + inner: string; + filePart: string; + displayPart: string | null; +} + +/** + * Returns context if the cursor is inside [[...]]. + * cursor: position (selectionStart) inside the text. + */ +export function getWikiLinkAtCursor( + text: string, + cursor: number, +): WikiLinkContext | null { + // Slice before cursor and find the nearest opening [[ + const before = text.slice(0, cursor); + const open = before.lastIndexOf("[["); + if (open === -1) return null; + + // Ensure there is not a closing ]] after that open but still before cursor (would mean you're outside) + const lastCloseBefore = before.lastIndexOf("]]"); + if (lastCloseBefore > open) return null; // We are after a closed link. + + // Now look forward from cursor for the closing ]] + const after = text.slice(cursor); + const relativeClose = after.indexOf("]]"); + if (relativeClose === -1) return null; // Not closed yet. + + const fullStart = open; + const fullEnd = cursor + relativeClose + 2; // +2 for length of ]] + const innerStart = fullStart + 2; + const innerEnd = fullEnd - 2; + if (cursor < innerStart || cursor > innerEnd) return null; + + const inner = text.slice(innerStart, innerEnd); + if (inner.includes("\n")) return null; + + // Extract file|alias + const pipeIdx = inner.indexOf("|"); + const filePart = pipeIdx === -1 ? inner : inner.slice(0, pipeIdx); + const displayPart = pipeIdx === -1 ? null : inner.slice(pipeIdx + 1); + + return { + fullStart, + fullEnd, + innerStart, + innerEnd, + inner, + filePart, + displayPart, + }; +} diff --git a/src/views/Chat/Chat.svelte b/src/views/Chat/Chat.svelte new file mode 100755 index 00000000..88b43d98 --- /dev/null +++ b/src/views/Chat/Chat.svelte @@ -0,0 +1,41 @@ + + + +
+
+ + {#if currentSession.session} + + {:else} + + {/if} + +
+
+
diff --git a/src/views/Chat/Chat.ts b/src/views/Chat/Chat.ts new file mode 100755 index 00000000..e9342098 --- /dev/null +++ b/src/views/Chat/Chat.ts @@ -0,0 +1,52 @@ +import { WorkspaceLeaf, ItemView } from "obsidian"; + +import ChatViewComponent from "./Chat.svelte"; +import { mount } from "svelte"; +import type SecondBrainPlugin from "../../main"; + +export const VIEW_TYPE_CHAT = "chat-view"; + +export class ChatView extends ItemView { + plugin!: SecondBrainPlugin; + component!: ChatViewComponent; + + constructor(plugin: SecondBrainPlugin, leaf: WorkspaceLeaf) { + super(leaf); + this.plugin = plugin; + this.icon = "message-square"; + this.contentEl.style.paddingTop = "0"; + } + getViewType() { + return VIEW_TYPE_CHAT; + } + + getViewData(): string { + return "hii"; + } + + getDisplayText(): string { + return "Smart Chat"; + } + + setViewData(data: string, clear: boolean): void { + if (clear) { + this.clear(); + } + } + clear(): void { + { + } + } + + protected onOpen(): Promise { + mount(ChatViewComponent, { + target: this.contentEl, + props: {}, + }); + return super.onOpen(); + } + + protected onClose(): Promise { + return super.onClose(); + } +} diff --git a/src/views/ChatModelManagement/ChatModelManagement.svelte b/src/views/ChatModelManagement/ChatModelManagement.svelte new file mode 100644 index 00000000..81d14dd1 --- /dev/null +++ b/src/views/ChatModelManagement/ChatModelManagement.svelte @@ -0,0 +1,166 @@ + + + + diff --git a/src/views/ChatModelManagement/ChatModelManagement.ts b/src/views/ChatModelManagement/ChatModelManagement.ts new file mode 100644 index 00000000..7bb6f7fa --- /dev/null +++ b/src/views/ChatModelManagement/ChatModelManagement.ts @@ -0,0 +1,53 @@ +import { App, Modal } from "obsidian"; +import type { GenModelConfig } from "papa-ts"; +import { mount } from "svelte"; +import type SecondBrainPlugin from "../../main"; +import ModalProvider from "../../components/QueryClientProvider.svelte"; +import ChatModelManagementComponent from "./ChatModelManagement.svelte"; +import type { GenProviders } from "../../types/providers"; + +export class ChatModelManagementModal extends Modal { + private component!: ChatModelManagementComponent; + private plugin: SecondBrainPlugin; + private provider!: GenProviders; + private config?: GenModelConfig; + + constructor( + plugin: SecondBrainPlugin, + provider: GenProviders, + config?: GenModelConfig, + ) { + super(plugin.app); + this.plugin = plugin; + this.setTitle(`${provider} Chat Model Management`); + this.provider = provider; + this.config = config; + } + + onOpen() { + this.component = mount( + ModalProvider<{ + modal: ChatModelManagementModal; + provider: GenProviders; + config?: GenModelConfig; + }>, + { + target: this.contentEl, + props: { + plugin: this.plugin, + component: ChatModelManagementComponent, + componentProps: { + modal: this, + provider: this.provider, + config: this.config, + }, + }, + }, + ); + } + + onClose() { + const { contentEl } = this; + contentEl.empty(); + } +} diff --git a/src/views/EmbedModelManagement/EmbedModelManagement.svelte b/src/views/EmbedModelManagement/EmbedModelManagement.svelte new file mode 100644 index 00000000..652a2a16 --- /dev/null +++ b/src/views/EmbedModelManagement/EmbedModelManagement.svelte @@ -0,0 +1,141 @@ + + + + + diff --git a/src/views/EmbedModelManagement/EmbedModelManagement.ts b/src/views/EmbedModelManagement/EmbedModelManagement.ts new file mode 100644 index 00000000..1d8c85d1 --- /dev/null +++ b/src/views/EmbedModelManagement/EmbedModelManagement.ts @@ -0,0 +1,53 @@ +import { App, Modal } from "obsidian"; +import type { EmbedModelConfig } from "papa-ts"; +import { mount } from "svelte"; +import type SecondBrainPlugin from "../../main"; +import ModalProvider from "../../components/QueryClientProvider.svelte"; +import EmbedModelManagementComponent from "./EmbedModelManagement.svelte"; +import type { EmbedProviders } from "../../types/providers"; + +export class EmbedModelManagementModal extends Modal { + private component!: EmbedModelManagementComponent; + private plugin: SecondBrainPlugin; + private provider!: EmbedProviders; + private config?: EmbedModelConfig; + + constructor( + plugin: SecondBrainPlugin, + provider: EmbedProviders, + config?: EmbedModelConfig, + ) { + super(plugin.app); + this.plugin = plugin; + this.setTitle(`${provider} Embed Model Management`); + this.provider = provider; + this.config = config; + } + + onOpen() { + this.component = mount( + ModalProvider<{ + modal: EmbedModelManagementModal; + provider: EmbedProviders; + config?: EmbedModelConfig; + }>, + { + target: this.contentEl, + props: { + plugin: this.plugin, + component: EmbedModelManagementComponent, + componentProps: { + modal: this, + provider: this.provider, + config: this.config, + }, + }, + }, + ); + } + + onClose() { + const { contentEl } = this; + contentEl.empty(); + } +} diff --git a/src/views/ProviderSetup/ProviderSetup.svelte b/src/views/ProviderSetup/ProviderSetup.svelte new file mode 100644 index 00000000..fdd07e8f --- /dev/null +++ b/src/views/ProviderSetup/ProviderSetup.svelte @@ -0,0 +1,149 @@ + + + + + diff --git a/src/views/ProviderSetup/ProviderSetup.ts b/src/views/ProviderSetup/ProviderSetup.ts new file mode 100644 index 00000000..5f0579ea --- /dev/null +++ b/src/views/ProviderSetup/ProviderSetup.ts @@ -0,0 +1,49 @@ +import { App, Modal } from "obsidian"; +import ProviderSetupComponent from "./ProviderSetup.svelte"; +import ModalProvider from "../../components/QueryClientProvider.svelte"; +import { mount } from "svelte"; +import type { RegisteredProvider } from "papa-ts"; +import type SecondBrainPlugin from "../../main"; + +export class ProviderSetupModal extends Modal { + component!: ProviderSetupComponent; + plugin: SecondBrainPlugin; + selectedProvider: RegisteredProvider; + + constructor(plugin: SecondBrainPlugin, selectedProvider: RegisteredProvider) { + super(plugin.app); + this.plugin = plugin; + this.setTitle(`Setup ${selectedProvider}`); + this.selectedProvider = selectedProvider; + } + + onOpen() { + this.component = mount( + ModalProvider<{ + modal: ProviderSetupModal; + plugin: SecondBrainPlugin; + selectedProvider: RegisteredProvider; + }>, + { + target: this.contentEl, + props: { + plugin: this.plugin, + component: ProviderSetupComponent, + componentProps: { + modal: this, + plugin: this.plugin, + selectedProvider: this.selectedProvider, + }, + }, + }, + ); + } + + onClose() { + const { contentEl } = this; + contentEl.empty(); + } +} + +// Export for backwards compatibility +export const ProviderSetup = ProviderSetupModal; diff --git a/src/views/Settings/Settings.svelte b/src/views/Settings/Settings.svelte new file mode 100755 index 00000000..8f663c87 --- /dev/null +++ b/src/views/Settings/Settings.svelte @@ -0,0 +1,143 @@ + + + + +Chat Settings + + + (pluginData.assistantLanguage = value)} + selected={pluginData.assistantLanguage} + /> + + + + (pluginData.defaultChatName = value)} + /> + + + + pluginData.toggleGeneratingChatTitle()} + /> + + + + + + +RAG Config + + + pluginData.toggleAutostart()} + /> + + + + + + fuzzySuggestModel.open()} + buttonText={"Manage"} + /> + + + + + console.log("Not set up")} + /> + + +
+ + + { + console.log("Delete Plugin Data"); + }} + /> + + + + + console.log("Changing Key")} + /> + + + console.log("Change verbose")} + /> + +
\ No newline at end of file diff --git a/src/views/Settings/Settings.ts b/src/views/Settings/Settings.ts new file mode 100755 index 00000000..65140be1 --- /dev/null +++ b/src/views/Settings/Settings.ts @@ -0,0 +1,41 @@ +import { PluginSettingTab } from "obsidian"; +import SecondBrainPlugin from "../../main"; +import SettingsComponent from "./Settings.svelte"; +import { mount } from "svelte"; +import QueryClientProvider from "../../components/QueryClientProvider.svelte"; + +export default class SettingsTab extends PluginSettingTab { + // keep a handle so we can destroy it on hide() + instance: ReturnType | null = null; + plugin: SecondBrainPlugin; + + constructor(plugin: SecondBrainPlugin) { + super(plugin.app, plugin); + this.plugin = plugin; + } + + display(): void { + this.containerEl.empty(); + + // Destroy any previous instance to avoid leaks (if display is called again) + this.instance?.destroy?.(); + + this.instance = mount(QueryClientProvider, { + target: this.containerEl, + props: { + plugin: this.plugin, + component: SettingsComponent, + componentProps: { + plugin: this.plugin, + }, + }, + }); + } + + hide(): void { + // Clean up when leaving the settings tab + this.instance?.destroy?.(); + this.instance = null; + this.containerEl.empty(); + } +} diff --git a/svelte.config.ts b/svelte.config.ts index 692e6140..8b34b538 100644 --- a/svelte.config.ts +++ b/svelte.config.ts @@ -1,13 +1,10 @@ -import type { RollupWarning } from 'rollup'; +import { vitePreprocess } from "@sveltejs/vite-plugin-svelte"; -const config = { - onwarn: (warning: RollupWarning, handler: (warning: RollupWarning) => void) => { - const { code, frame } = warning; - if (code?.startsWith('a11y-')) return; - - // let Rollup handle all other warnings normally - handler(warning); - }, +export default { + preprocess: vitePreprocess(), + compilerOptions: {}, + onwarn: (warning, handler) => { + if (warning.code && warning.code.startsWith("a11y")) return; + handler(warning); + }, }; - -export default config; diff --git a/tailwind.config.js b/tailwind.config.js index 837ebe7d..43c15337 100644 --- a/tailwind.config.js +++ b/tailwind.config.js @@ -1,39 +1,53 @@ /** @type {import('tailwindcss').Config} */ export default { - content: ['./src/**/*.{js,svelte,ts}'], - theme: { - extend: { - colors: { - primary: { - DEFAULT: 'var(--color-accent)', - }, - secondary: { - DEFAULT: 'hsl(var(--accent-h), 10%, var(--accent-l))', - }, - slate: { - 0o0: 'var(--color-base-00)', - 0o5: 'var(--color-base-05)', - 10: 'var(--color-base-10)', - 20: 'var(--color-base-20)', - 25: 'var(--color-base-25)', - 30: 'var(--color-base-30)', - 35: 'var(--color-base-35)', - 40: 'var(--color-base-40)', - 50: 'var(--color-base-50)', - 60: 'var(--color-base-60)', - 70: 'var(--color-base-70)', - 100: 'var(--color-base-100)', - }, - }, - }, - }, - variants: { - extend: { - display: ['group-hover'], - }, - }, - corePlugins: { - preflight: false, - }, - plugins: [], + content: ["./src/**/*.{js,svelte,ts}"], + theme: { + extend: { + colors: { + primary: { + DEFAULT: "var(--color-accent)", + }, + secondary: { + DEFAULT: "hsl(var(--accent-h), 10%, var(--accent-l))", + }, + slate: { + "00": "var(--color-base-00)", + "05": "var(--color-base-05)", + 10: "var(--color-base-10)", + 20: "var(--color-base-20)", + 25: "var(--color-base-25)", + 30: "var(--color-base-30)", + 35: "var(--color-base-35)", + 40: "var(--color-base-40)", + 50: "var(--color-base-50)", + 60: "var(--color-base-60)", + 70: "var(--color-base-70)", + 100: "var(--color-base-100)", + }, + }, + keyframes: { + "accordion-down": { + from: { height: "0" }, + to: { height: "var(--bits-accordion-content-height)" }, + }, + "accordion-up": { + from: { height: "var(--bits-accordion-content-height)" }, + to: { height: "0" }, + }, + }, + animation: { + "accordion-down": "accordion-down 200ms ease-out", + "accordion-up": "accordion-up 200ms ease-in", + }, + }, + }, + variants: { + extend: { + display: ["group-hover"], + }, + }, + corePlugins: { + preflight: false, + }, + plugins: [], }; diff --git a/tsconfig.json b/tsconfig.json index 8365c43c..c9ddd577 100644 --- a/tsconfig.json +++ b/tsconfig.json @@ -3,19 +3,24 @@ "compilerOptions": { "target": "ESNext", "useDefineForClassFields": true, - "module": "ES6", + "module": "ESNext", + "moduleResolution": "bundler", "resolveJsonModule": true, "allowJs": true, "isolatedModules": true, "noEmitOnError": true, + "esModuleInterop": true, + "forceConsistentCasingInFileNames": true, + "skipLibCheck": true, + "strict": true, + "types": ["svelte", "vite/client"], "plugins": [ { "name": "typescript-svelte-plugin", - // the following options can be set additionally; they are optional; their default values are listed here - "enabled": true, // enables this plugin - "assumeIsSvelteProject": true // if true, skip detection and always assume it's a Svelte project + "enabled": true, + "assumeIsSvelteProject": true } ] }, "include": ["src/**/*.d.ts", "src/**/*.ts", "src/**/*.js", "src/**/*.svelte"] -} +} \ No newline at end of file diff --git a/versions.json b/versions.json index 4e32a57e..e5ac8618 100644 --- a/versions.json +++ b/versions.json @@ -1,23 +1,19 @@ { - "0.1.2": "1.5.0" - "0.1.3": "1.5.0" - "0.1.4": "1.5.0" - "0.2.0": "1.5.0" - "0.2.1": "1.5.0" - "0.2.2": "1.5.0" - "0.2.3": "1.5.0" - "0.2.4": "1.5.0" - "0.2.5": "1.5.0" - "0.2.6": "1.5.0" - "0.2.7": "1.5.0" - "0.2.8": "1.5.0" - "0.4.0": "1.5.0" - "0.5.0": "1.5.0" - "0.6.0": "1.5.0" + "0.1.2": "1.5.0", + "0.1.3": "1.5.0", + "0.1.4": "1.5.0", + "0.2.0": "1.5.0", + "0.2.1": "1.5.0", + "0.2.2": "1.5.0", + "0.2.3": "1.5.0", + "0.2.4": "1.5.0", + "0.2.5": "1.5.0", + "0.2.6": "1.5.0", + "0.2.7": "1.5.0", + "0.2.8": "1.5.0", + "0.4.0": "1.5.0", + "0.5.0": "1.5.0", + "0.6.0": "1.5.0", "1.0.0": "1.5.0" - "1.0.2": "1.5.0" - "1.1.0": "1.5.0" - "1.1.1": "1.5.0" - "1.2.0": "1.5.0" - "1.3.0": "1.5.0" } + diff --git a/vite.config.ts b/vite.config.ts index 26a14cb4..35fe6473 100644 --- a/vite.config.ts +++ b/vite.config.ts @@ -1,56 +1,73 @@ -import { svelte, vitePreprocess } from '@sveltejs/vite-plugin-svelte'; -import builtins from 'builtin-modules'; -import { defineConfig } from 'vite'; -import { pathToFileURL } from 'url'; -import typescript from '@rollup/plugin-typescript'; +// vite.config.ts +import { svelte, vitePreprocess } from "@sveltejs/vite-plugin-svelte"; +import { defineConfig } from "vite"; + +import builtinModules from "builtin-modules"; const setOutDir = (mode: string) => { - switch (mode) { - case 'development': - return './build/smart-second-brain/'; - case 'production': - return 'build/prod'; - } + switch (mode) { + case "development": + return "./build/smart-second-brain/"; + case "production": + return "./build/prod"; + default: + console.warn(`Unexpected mode: "${mode}". Defaulting to development output directory.`); + return "./build/smart-second-brain/"; + } }; export default defineConfig(({ mode }) => { - return { - plugins: [svelte({ preprocess: vitePreprocess() })], - build: { - lib: { - entry: 'src/main', - formats: ['cjs'], - }, - rollupOptions: { - plugins: [typescript({ tsconfig: './tsconfig.json' })], - output: { - entryFileNames: 'main.js', - assetFileNames: 'styles.css', - sourcemapBaseUrl: pathToFileURL(`${__dirname}/build/smart-second-brain/`).toString(), - }, - external: [ - 'obsidian', - 'electron', - '@codemirror/autocomplete', - '@codemirror/collab', - '@codemirror/commands', - '@codemirror/language', - '@codemirror/lint', - '@codemirror/search', - '@codemirror/state', - '@codemirror/view', - '@lezer/common', - '@lezer/highlight', - '@lezer/lr', - ...builtins, - ], - }, - outDir: setOutDir(mode), - emptyOutDir: false, - sourcemap: true, - }, - css: { - devSourcemap: true, - }, - }; + const isDevelopment = mode === "development"; + + return { + plugins: [ + svelte({ + preprocess: vitePreprocess(), + onwarn: (warning, handler) => { + if (warning.code && warning.code.startsWith("a11y")) return; + handler(warning); + }, + }), + ], + build: { + lib: { + entry: "src/main.ts", + formats: ["cjs"], + fileName: () => "main.js", + }, + rollupOptions: { + plugins: [], + output: { + entryFileNames: "main.js", + assetFileNames: "styles.css", + sourcemapBaseUrl: new URL(setOutDir(mode), import.meta.url).toString(), + // --- Add these two lines to force single file --- + manualChunks: undefined, + inlineDynamicImports: true, + }, + external: [ + "obsidian", + "electron", + "@codemirror/autocomplete", + "@codemirror/collab", + "@codemirror/commands", + "@codemirror/language", + "@codemirror/lint", + "@codemirror/search", + "@codemirror/state", + "@codemirror/view", + "@lezer/common", + "@lezer/highlight", + "@lezer/lr", + ...builtinModules, + ], + }, + outDir: setOutDir(mode), + emptyOutDir: mode === "production", + sourcemap: isDevelopment, + }, + css: { + devSourcemap: isDevelopment, + }, + }; }); From 02f736c3644d61ebf35c596cdcce5533cd4181a8 Mon Sep 17 00:00:00 2001 From: nicobrauchtgit Date: Mon, 15 Dec 2025 21:46:17 +0100 Subject: [PATCH 3/7] updated nix --- flake.lock | 27 +++++++++++++++++++++++++++ flake.nix | 35 +++++++++++++++++++++++++++++++++++ 2 files changed, 62 insertions(+) create mode 100644 flake.lock create mode 100644 flake.nix diff --git a/flake.lock b/flake.lock new file mode 100644 index 00000000..58344d82 --- /dev/null +++ b/flake.lock @@ -0,0 +1,27 @@ +{ + "nodes": { + "nixpkgs": { + "locked": { + "lastModified": 1765425892, + "narHash": "sha256-jlQpSkg2sK6IJVzTQBDyRxQZgKADC2HKMRfGCSgNMHo=", + "owner": "NixOS", + "repo": "nixpkgs", + "rev": "5d6bdbddb4695a62f0d00a3620b37a15275a5093", + "type": "github" + }, + "original": { + "owner": "NixOS", + "ref": "nixpkgs-unstable", + "repo": "nixpkgs", + "type": "github" + } + }, + "root": { + "inputs": { + "nixpkgs": "nixpkgs" + } + } + }, + "root": "root", + "version": 7 +} diff --git a/flake.nix b/flake.nix new file mode 100644 index 00000000..c260345e --- /dev/null +++ b/flake.nix @@ -0,0 +1,35 @@ +{ + description = "A Nix-flake-based Bun development environment"; + + inputs.nixpkgs.url = "https://flakehub.com/f/NixOS/nixpkgs/0.1"; # unstable Nixpkgs + + outputs = + { self, ... }@inputs: + + let + supportedSystems = [ + "x86_64-linux" + "aarch64-linux" + "x86_64-darwin" + "aarch64-darwin" + ]; + forEachSupportedSystem = + f: + inputs.nixpkgs.lib.genAttrs supportedSystems ( + system: + f { + pkgs = import inputs.nixpkgs { inherit system; }; + } + ); + in + { + devShells = forEachSupportedSystem ( + { pkgs }: + { + default = pkgs.mkShellNoCC { + packages = with pkgs; [ bun ]; + }; + } + ); + }; +} From a7b39d029884fc2a6efdf248276d4a5c9e0ea085 Mon Sep 17 00:00:00 2001 From: nicobrauchtgit Date: Tue, 16 Dec 2025 14:29:06 +0100 Subject: [PATCH 4/7] flake update --- flake.lock | 18 ++++++++---------- 1 file changed, 8 insertions(+), 10 deletions(-) diff --git a/flake.lock b/flake.lock index 58344d82..9f53a776 100644 --- a/flake.lock +++ b/flake.lock @@ -2,18 +2,16 @@ "nodes": { "nixpkgs": { "locked": { - "lastModified": 1765425892, - "narHash": "sha256-jlQpSkg2sK6IJVzTQBDyRxQZgKADC2HKMRfGCSgNMHo=", - "owner": "NixOS", - "repo": "nixpkgs", - "rev": "5d6bdbddb4695a62f0d00a3620b37a15275a5093", - "type": "github" + "lastModified": 1765186076, + "narHash": "sha256-hM20uyap1a0M9d344I692r+ik4gTMyj60cQWO+hAYP8=", + "rev": "addf7cf5f383a3101ecfba091b98d0a1263dc9b8", + "revCount": 908783, + "type": "tarball", + "url": "https://api.flakehub.com/f/pinned/NixOS/nixpkgs/0.1.908783%2Brev-addf7cf5f383a3101ecfba091b98d0a1263dc9b8/019b03a0-b1e4-7f2a-9d10-ad8434116660/source.tar.gz" }, "original": { - "owner": "NixOS", - "ref": "nixpkgs-unstable", - "repo": "nixpkgs", - "type": "github" + "type": "tarball", + "url": "https://flakehub.com/f/NixOS/nixpkgs/0.1" } }, "root": { From 1b90cdbab657d4b21fb5e6fa8ffac45d85056cbc Mon Sep 17 00:00:00 2001 From: nicobrauchtgit Date: Wed, 17 Dec 2025 20:32:20 +0100 Subject: [PATCH 5/7] stuff --- .opencode/opencode.db | Bin 0 -> 4096 bytes .opencode/opencode.db-shm | Bin 0 -> 32768 bytes .opencode/opencode.db-wal | Bin 0 -> 65952 bytes bun.lock | 500 +- package.json | 6 +- src/SmartSecondBrain.ts | 294 -- src/agent/AgentManager.ts | 456 ++ src/agent/ObsidianChatManager.ts | 565 ++ src/agent/prompts.ts | 76 + src/components/Chat/Input.svelte | 14 +- src/components/Chat/MessageContainer.svelte | 106 +- .../Modal/ExcludeFoldersModal.svelte | 1 - src/components/Settings/ProviderSetup.svelte | 7 +- src/components/bitui/Dropdown.svelte | 127 +- src/components/bitui/ModelPopover.svelte | 4 +- src/constants/defaults.ts | 16 +- src/controller/Messages.ts | 177 - src/db/dexieChatDb.ts | 814 ++- src/main.ts | 322 +- src/stores/chatStore.svelte.ts | 446 +- src/stores/dataStore.svelte.ts | 812 +-- src/stores/state.svelte.ts | 14 +- src/stores/store.ts | 41 - src/tools/executeDataview.ts | 52 + src/tools/getAllTags.ts | 38 + src/tools/getProperties.ts | 71 + src/tools/readNote.ts | 40 + src/tools/searchNotes.ts | 78 + src/types/providers.ts | 146 +- src/utils/dataValidation.ts | 1346 +++-- src/utils/markdownHelper.ts | 138 + src/utils/obsidianFetch.ts | 115 + src/{lib => utils}/query.ts | 0 src/utils/threadId.ts | 10 + src/utils/utils.ts | 35 - src/views/Chat/Chat.svelte | 7 +- src/views/Chat/Chat.ts | 61 +- .../ChatModelManagement.svelte | 1 - src/views/ProviderSetup/ProviderSetup.svelte | 2 +- src/views/ProviderSetup/ProviderSetup.ts | 70 +- src/views/Settings/Settings.svelte | 93 +- svelte.config.ts | 14 +- tsconfig.json | 9 +- v2/.gitignore | 6 + v2/esbuild.config.mjs | 54 + v2/manifest.json | 12 + v2/package-lock.json | 4608 +++++++++++++++++ v2/package.json | 31 + v2/src/main.ts | 410 ++ v2/src/settings.ts | 26 + v2/src/ui/ChatComponent.svelte | 644 +++ v2/src/ui/ChatStreamScratch.svelte | 352 ++ v2/src/ui/ChatView.ts | 75 + v2/src/ui/Logo.svelte | 138 + v2/src/ui/MessageBubble.svelte | 427 ++ v2/src/ui/chatLogic.ts | 184 + v2/src/ui/types.ts | 16 + v2/styles.css | 20 + v2/tsconfig.json | 23 + vite.config.ts | 1 - 60 files changed, 11332 insertions(+), 2819 deletions(-) create mode 100644 .opencode/opencode.db create mode 100644 .opencode/opencode.db-shm create mode 100644 .opencode/opencode.db-wal delete mode 100755 src/SmartSecondBrain.ts create mode 100644 src/agent/AgentManager.ts create mode 100644 src/agent/ObsidianChatManager.ts create mode 100644 src/agent/prompts.ts delete mode 100755 src/controller/Messages.ts delete mode 100755 src/stores/store.ts create mode 100644 src/tools/executeDataview.ts create mode 100644 src/tools/getAllTags.ts create mode 100644 src/tools/getProperties.ts create mode 100644 src/tools/readNote.ts create mode 100644 src/tools/searchNotes.ts create mode 100644 src/utils/markdownHelper.ts create mode 100644 src/utils/obsidianFetch.ts rename src/{lib => utils}/query.ts (100%) create mode 100644 src/utils/threadId.ts create mode 100644 v2/.gitignore create mode 100644 v2/esbuild.config.mjs create mode 100644 v2/manifest.json create mode 100644 v2/package-lock.json create mode 100644 v2/package.json create mode 100644 v2/src/main.ts create mode 100644 v2/src/settings.ts create mode 100644 v2/src/ui/ChatComponent.svelte create mode 100644 v2/src/ui/ChatStreamScratch.svelte create mode 100644 v2/src/ui/ChatView.ts create mode 100644 v2/src/ui/Logo.svelte create mode 100644 v2/src/ui/MessageBubble.svelte create mode 100644 v2/src/ui/chatLogic.ts create mode 100644 v2/src/ui/types.ts create mode 100644 v2/styles.css create mode 100644 v2/tsconfig.json diff --git a/.opencode/opencode.db b/.opencode/opencode.db new file mode 100644 index 0000000000000000000000000000000000000000..4e86411b5803e34b1e4767ce981907694f15c1ed GIT binary patch literal 4096 zcmWFz^vNtqRY=P(%1ta$FlG>7U}9o$P*7lCU|@t|AVoG{WYBBVeHZ zuI0Xj5U40HI4rAFJh?Ly7#=o-I1s2PkXu?ppr$~s$O(a(0=b_k1ZoQ8a;OlfDUh4F zLZGHVu0;!hngVvxYyR#|odQz~1j-8BmOZ(H6Ucv`5ds7V5FkK+009C72oNAZfB*pk N1PBlyK!89EfgkJxA;bUx literal 0 HcmV?d00001 diff --git a/.opencode/opencode.db-wal b/.opencode/opencode.db-wal new file mode 100644 index 0000000000000000000000000000000000000000..6c0e12f0f1cc976c62503fc7a5cc8a350dc274f2 GIT binary patch literal 65952 zcmeI*Uu+ab90%~dYwvFh1tBa+Elwh)w{X|e5=8zKJ=$$KX|Lsa4K&sq$KAFp-tCp! zt&s45Ee6FWqa+4HOb|sM48|A(4?Jj0P~(e; z&L~=@da>FNt} zTJ^HKBG>AzBoqt;)GUd`lk$L^AR~#`P&6@4_R8ZVI+h%c#p&)tay%KP>Fgt<%F@S& zlO#SiILJ1udMZ6Vol})kcIBH5-AL!BNisGhk0zr-BcxC6kB$u{Nhq5(6hqA`p?0ls ztX-0V0f~~c&-u>tf>oDYXUz68^ZlIlT;R6Qa{G}k zI8Gh{5P$##AOHafKmY;|fB*y_00B#2m8&5VsE%Wxn<~Z;yfgc)*7^3QXBHSoz#bd$ zshQ6Fzi|Z1zYwR0P9z^#SvOXe zRa1`5D{Fs?uQf{Rbz5b<^1`I7s>-I)3zVkGsXJ{{&GJJnv+F1p?~@PEc2F~M zc`cAosf|dd2AX|hTbt{2+KjW~nex{r-T=&KJ-(L4)3LTm+gwsUkSq_U3!58C`CAD} z0dj1&Vj-v0T0fmG8hYghl2sA#o zuN;z)`)TKn_sXNCD?>=lN~}8VOG$5Zv^Ux(2c^zsUa_~$C75l-j;l=17zJ~=)PTBp zB{t7)ZSuA55dCxQmEC1hr7@gkeZ^en?V$3aSDkcTFEJBTUgFGEOY0xc2fd;sx-w4p zu+C#TZ5*}^IIl~T5->XJ6hbV$G!gKMTSV81s=P`~*i0O_OOB;vW%-s?N~a{RPZUMh z=`OQ-nR%JNyd2c*SoR4mrB|`SRCXS_e-t!B(TrM~>`2#In;w>4^#FQ?#V{6+?HiNL zDi8C%L_>VT#72;UlH~V_J>uOukXc2kZu7-2`4&#vWhV8__IqmHl?@e{{%qbA+ljc|M0)qgy?aThGX1U|vPrTU#dNWdpEgoP;Uz`W$s%&9 z+@UO|49$qXM`Z6F7oXd_ohmZa4SM;H4ibJRDwV6lDOsjKQ?b1|c#$5&t?VA1pWeO~ zzNJc?jrY10@fMTn;&UGQX~EAvF<=}4A7-$maRmDhhS$6`bn=Qh_P^yi9Y;WaVS)ez zAOHafKmY;|fB*y_009U<;2{=R=k^Gmz~;w}+}=NQp~h%|1;-IM-!I_a_UoOGRz2Hi zjU%`vwA^}#i;Yu*00bZa0SG_<0uX=z1Rwwb2tZ(w0;}mT0$24g0`{GQ<`@9}{Q~>m z_;*shpnh%+6tMn;!6NfVG6+Bb0uX=z1Rwwb2tWV=5P$##9zg*%6vK%Z2=_d3>(7aw zB0;ti&jpwQCI~ z00bZa0SG_<0uX=z1RwwbN5IGC_;Z2J&j0ey#~-fmK)itCgBb`w00Izz00bZa0SG_< z0uX>eJquWW&f(&Xgnn+~`j6U?Yolk3vv@90&sC1HK>z{}fB*y_009U<00Izz00bO? z0Gs3S0v{X_g{$k{e+$nA93RX;00Izz00bZa0SG_<0uX=z1nOD9d<4Ls3tT;Wyz%BM zqkcRWsOKt2*&qM`2tWV=5P$##AOHafKmY=cKogte&jr?n_FUd@{3=0.3.0", "@opentelemetry/api": "^1.9.0" } }, "sha512-DG0ar89/Nhs9Lnw6ynTbpOPjuO7DTBv+Y0uYR5qWl5+FLcktPN+HCLGmbpsI+clxJDVhzMyn9rPnT8P/OuiGqg=="], + + "@langfuse/otel": ["@langfuse/otel@4.4.9", "", { "dependencies": { "@langfuse/core": "^4.4.9" }, "peerDependencies": { "@opentelemetry/api": "^1.9.0", "@opentelemetry/core": "^2.0.1", "@opentelemetry/exporter-trace-otlp-http": ">=0.202.0 <1.0.0", "@opentelemetry/sdk-trace-base": "^2.0.1" } }, "sha512-T9tSucDC3cvdeUB8fTGXm6ZZcC4kOEreJuM/C66nHQ26+DWtx2AN75JWuadc2E+VU/K+BjTb5XAkBceWYtvXjw=="], + + "@langfuse/tracing": ["@langfuse/tracing@4.4.9", "", { "dependencies": { "@langfuse/core": "^4.4.9" }, "peerDependencies": { "@opentelemetry/api": "^1.9.0" } }, "sha512-if+G/v9NsyTKj40KKX96bRSdMXwyDbVL4GJQvmwQ9SxvGYF+d99pGFB7L6QOeCd1KBHMdmDe733ncmvCnSHJ9w=="], + "@marijn/find-cluster-break": ["@marijn/find-cluster-break@1.0.2", "", {}, "sha512-l0h88YhZFyKdXIFNfSWpyjStDjGHwZ/U7iobcK1cQQD8sejsONdQtTVU+1wVN1PBw40PiiHB1vA5S7VTfQiP9g=="], "@nodelib/fs.scandir": ["@nodelib/fs.scandir@2.1.5", "", { "dependencies": { "@nodelib/fs.stat": "2.0.5", "run-parallel": "^1.1.9" } }, "sha512-vq24Bq3ym5HEQm2NKCr3yXDwjc7vTsEThRDnkp2DK9p1uqLR+DHurm/NOTo0KG7HYHU7eppKZj3MyqYuMBf62g=="], @@ -148,50 +184,158 @@ "@nodelib/fs.walk": ["@nodelib/fs.walk@1.2.8", "", { "dependencies": { "@nodelib/fs.scandir": "2.1.5", "fastq": "^1.6.0" } }, "sha512-oGB+UxlgWcgQkgwo8GcEGwemoTFt3FIO9ababBmaGwXIoBKZ+GTy0pP185beGg7Llih/NSHSV2XAs1lnznocSg=="], + "@opentelemetry/api": ["@opentelemetry/api@1.9.0", "", {}, "sha512-3giAOQvZiH5F9bMlMiv8+GSPMeqg0dbaeo58/0SlA9sxSqZhnUtxzX9/2FzyhS9sWQf5S0GJE0AKBrFqjpeYcg=="], + + "@opentelemetry/api-logs": ["@opentelemetry/api-logs@0.208.0", "", { "dependencies": { "@opentelemetry/api": "^1.3.0" } }, "sha512-CjruKY9V6NMssL/T1kAFgzosF1v9o6oeN+aX5JB/C/xPNtmgIJqcXHG7fA82Ou1zCpWGl4lROQUKwUNE1pMCyg=="], + + "@opentelemetry/context-async-hooks": ["@opentelemetry/context-async-hooks@2.2.0", "", { "peerDependencies": { "@opentelemetry/api": ">=1.0.0 <1.10.0" } }, "sha512-qRkLWiUEZNAmYapZ7KGS5C4OmBLcP/H2foXeOEaowYCR0wi89fHejrfYfbuLVCMLp/dWZXKvQusdbUEZjERfwQ=="], + + "@opentelemetry/core": ["@opentelemetry/core@2.2.0", "", { "dependencies": { "@opentelemetry/semantic-conventions": "^1.29.0" }, "peerDependencies": { "@opentelemetry/api": ">=1.0.0 <1.10.0" } }, "sha512-FuabnnUm8LflnieVxs6eP7Z383hgQU4W1e3KJS6aOG3RxWxcHyBxH8fDMHNgu/gFx/M2jvTOW/4/PHhLz6bjWw=="], + + "@opentelemetry/exporter-logs-otlp-grpc": ["@opentelemetry/exporter-logs-otlp-grpc@0.208.0", "", { "dependencies": { "@grpc/grpc-js": "^1.7.1", "@opentelemetry/core": "2.2.0", "@opentelemetry/otlp-exporter-base": "0.208.0", "@opentelemetry/otlp-grpc-exporter-base": "0.208.0", "@opentelemetry/otlp-transformer": "0.208.0", "@opentelemetry/sdk-logs": "0.208.0" }, "peerDependencies": { "@opentelemetry/api": "^1.3.0" } }, "sha512-AmZDKFzbq/idME/yq68M155CJW1y056MNBekH9OZewiZKaqgwYN4VYfn3mXVPftYsfrCM2r4V6tS8H2LmfiDCg=="], + + "@opentelemetry/exporter-logs-otlp-http": ["@opentelemetry/exporter-logs-otlp-http@0.208.0", "", { "dependencies": { "@opentelemetry/api-logs": "0.208.0", "@opentelemetry/core": "2.2.0", "@opentelemetry/otlp-exporter-base": "0.208.0", "@opentelemetry/otlp-transformer": "0.208.0", "@opentelemetry/sdk-logs": "0.208.0" }, "peerDependencies": { "@opentelemetry/api": "^1.3.0" } }, "sha512-jOv40Bs9jy9bZVLo/i8FwUiuCvbjWDI+ZW13wimJm4LjnlwJxGgB+N/VWOZUTpM+ah/awXeQqKdNlpLf2EjvYg=="], + + "@opentelemetry/exporter-logs-otlp-proto": ["@opentelemetry/exporter-logs-otlp-proto@0.208.0", "", { "dependencies": { "@opentelemetry/api-logs": "0.208.0", "@opentelemetry/core": "2.2.0", "@opentelemetry/otlp-exporter-base": "0.208.0", "@opentelemetry/otlp-transformer": "0.208.0", "@opentelemetry/resources": "2.2.0", "@opentelemetry/sdk-logs": "0.208.0", "@opentelemetry/sdk-trace-base": "2.2.0" }, "peerDependencies": { "@opentelemetry/api": "^1.3.0" } }, "sha512-Wy8dZm16AOfM7yddEzSFzutHZDZ6HspKUODSUJVjyhnZFMBojWDjSNgduyCMlw6qaxJYz0dlb0OEcb4Eme+BfQ=="], + + "@opentelemetry/exporter-metrics-otlp-grpc": ["@opentelemetry/exporter-metrics-otlp-grpc@0.208.0", "", { "dependencies": { "@grpc/grpc-js": "^1.7.1", "@opentelemetry/core": "2.2.0", "@opentelemetry/exporter-metrics-otlp-http": "0.208.0", "@opentelemetry/otlp-exporter-base": "0.208.0", "@opentelemetry/otlp-grpc-exporter-base": "0.208.0", "@opentelemetry/otlp-transformer": "0.208.0", "@opentelemetry/resources": "2.2.0", "@opentelemetry/sdk-metrics": "2.2.0" }, "peerDependencies": { "@opentelemetry/api": "^1.3.0" } }, "sha512-YbEnk7jjYmvhIwp2xJGkEvdgnayrA2QSr28R1LR1klDPvCxsoQPxE6TokDbQpoCEhD3+KmJVEXfb4EeEQxjymg=="], + + "@opentelemetry/exporter-metrics-otlp-http": ["@opentelemetry/exporter-metrics-otlp-http@0.208.0", "", { "dependencies": { "@opentelemetry/core": "2.2.0", "@opentelemetry/otlp-exporter-base": "0.208.0", "@opentelemetry/otlp-transformer": "0.208.0", "@opentelemetry/resources": "2.2.0", "@opentelemetry/sdk-metrics": "2.2.0" }, "peerDependencies": { "@opentelemetry/api": "^1.3.0" } }, "sha512-QZ3TrI90Y0i1ezWQdvreryjY0a5TK4J9gyDLIyhLBwV+EQUvyp5wR7TFPKCAexD4TDSWM0t3ulQDbYYjVtzTyA=="], + + "@opentelemetry/exporter-metrics-otlp-proto": ["@opentelemetry/exporter-metrics-otlp-proto@0.208.0", "", { "dependencies": { "@opentelemetry/core": "2.2.0", "@opentelemetry/exporter-metrics-otlp-http": "0.208.0", "@opentelemetry/otlp-exporter-base": "0.208.0", "@opentelemetry/otlp-transformer": "0.208.0", "@opentelemetry/resources": "2.2.0", "@opentelemetry/sdk-metrics": "2.2.0" }, "peerDependencies": { "@opentelemetry/api": "^1.3.0" } }, "sha512-CvvVD5kRDmRB/uSMalvEF6kiamY02pB46YAqclHtfjJccNZFxbkkXkMMmcJ7NgBFa5THmQBNVQ2AHyX29nRxOw=="], + + "@opentelemetry/exporter-prometheus": ["@opentelemetry/exporter-prometheus@0.208.0", "", { "dependencies": { "@opentelemetry/core": "2.2.0", "@opentelemetry/resources": "2.2.0", "@opentelemetry/sdk-metrics": "2.2.0" }, "peerDependencies": { "@opentelemetry/api": "^1.3.0" } }, "sha512-Rgws8GfIfq2iNWCD3G1dTD9xwYsCof1+tc5S5X0Ahdb5CrAPE+k5P70XCWHqrFFurVCcKaHLJ/6DjIBHWVfLiw=="], + + "@opentelemetry/exporter-trace-otlp-grpc": ["@opentelemetry/exporter-trace-otlp-grpc@0.208.0", "", { "dependencies": { "@grpc/grpc-js": "^1.7.1", "@opentelemetry/core": "2.2.0", "@opentelemetry/otlp-exporter-base": "0.208.0", "@opentelemetry/otlp-grpc-exporter-base": "0.208.0", "@opentelemetry/otlp-transformer": "0.208.0", "@opentelemetry/resources": "2.2.0", "@opentelemetry/sdk-trace-base": "2.2.0" }, "peerDependencies": { "@opentelemetry/api": "^1.3.0" } }, "sha512-E/eNdcqVUTAT7BC+e8VOw/krqb+5rjzYkztMZ/o+eyJl+iEY6PfczPXpwWuICwvsm0SIhBoh9hmYED5Vh5RwIw=="], + + "@opentelemetry/exporter-trace-otlp-http": ["@opentelemetry/exporter-trace-otlp-http@0.208.0", "", { "dependencies": { "@opentelemetry/core": "2.2.0", "@opentelemetry/otlp-exporter-base": "0.208.0", "@opentelemetry/otlp-transformer": "0.208.0", "@opentelemetry/resources": "2.2.0", "@opentelemetry/sdk-trace-base": "2.2.0" }, "peerDependencies": { "@opentelemetry/api": "^1.3.0" } }, "sha512-jbzDw1q+BkwKFq9yxhjAJ9rjKldbt5AgIy1gmEIJjEV/WRxQ3B6HcLVkwbjJ3RcMif86BDNKR846KJ0tY0aOJA=="], + + "@opentelemetry/exporter-trace-otlp-proto": ["@opentelemetry/exporter-trace-otlp-proto@0.208.0", "", { "dependencies": { "@opentelemetry/core": "2.2.0", "@opentelemetry/otlp-exporter-base": "0.208.0", "@opentelemetry/otlp-transformer": "0.208.0", "@opentelemetry/resources": "2.2.0", "@opentelemetry/sdk-trace-base": "2.2.0" }, "peerDependencies": { "@opentelemetry/api": "^1.3.0" } }, "sha512-q844Jc3ApkZVdWYd5OAl+an3n1XXf3RWHa3Zgmnhw3HpsM3VluEKHckUUEqHPzbwDUx2lhPRVkqK7LsJ/CbDzA=="], + + "@opentelemetry/exporter-zipkin": ["@opentelemetry/exporter-zipkin@2.2.0", "", { "dependencies": { "@opentelemetry/core": "2.2.0", "@opentelemetry/resources": "2.2.0", "@opentelemetry/sdk-trace-base": "2.2.0", "@opentelemetry/semantic-conventions": "^1.29.0" }, "peerDependencies": { "@opentelemetry/api": "^1.0.0" } }, "sha512-VV4QzhGCT7cWrGasBWxelBjqbNBbyHicWWS/66KoZoe9BzYwFB72SH2/kkc4uAviQlO8iwv2okIJy+/jqqEHTg=="], + + "@opentelemetry/instrumentation": ["@opentelemetry/instrumentation@0.208.0", "", { "dependencies": { "@opentelemetry/api-logs": "0.208.0", "import-in-the-middle": "^2.0.0", "require-in-the-middle": "^8.0.0" }, "peerDependencies": { "@opentelemetry/api": "^1.3.0" } }, "sha512-Eju0L4qWcQS+oXxi6pgh7zvE2byogAkcsVv0OjHF/97iOz1N/aKE6etSGowYkie+YA1uo6DNwdSxaaNnLvcRlA=="], + + "@opentelemetry/otlp-exporter-base": ["@opentelemetry/otlp-exporter-base@0.208.0", "", { "dependencies": { "@opentelemetry/core": "2.2.0", "@opentelemetry/otlp-transformer": "0.208.0" }, "peerDependencies": { "@opentelemetry/api": "^1.3.0" } }, "sha512-gMd39gIfVb2OgxldxUtOwGJYSH8P1kVFFlJLuut32L6KgUC4gl1dMhn+YC2mGn0bDOiQYSk/uHOdSjuKp58vvA=="], + + "@opentelemetry/otlp-grpc-exporter-base": ["@opentelemetry/otlp-grpc-exporter-base@0.208.0", "", { "dependencies": { "@grpc/grpc-js": "^1.7.1", "@opentelemetry/core": "2.2.0", "@opentelemetry/otlp-exporter-base": "0.208.0", "@opentelemetry/otlp-transformer": "0.208.0" }, "peerDependencies": { "@opentelemetry/api": "^1.3.0" } }, "sha512-fGvAg3zb8fC0oJAzfz7PQppADI2HYB7TSt/XoCaBJFi1mSquNUjtHXEoviMgObLAa1NRIgOC1lsV1OUKi+9+lQ=="], + + "@opentelemetry/otlp-transformer": ["@opentelemetry/otlp-transformer@0.208.0", "", { "dependencies": { "@opentelemetry/api-logs": "0.208.0", "@opentelemetry/core": "2.2.0", "@opentelemetry/resources": "2.2.0", "@opentelemetry/sdk-logs": "0.208.0", "@opentelemetry/sdk-metrics": "2.2.0", "@opentelemetry/sdk-trace-base": "2.2.0", "protobufjs": "^7.3.0" }, "peerDependencies": { "@opentelemetry/api": "^1.3.0" } }, "sha512-DCFPY8C6lAQHUNkzcNT9R+qYExvsk6C5Bto2pbNxgicpcSWbe2WHShLxkOxIdNcBiYPdVHv/e7vH7K6TI+C+fQ=="], + + "@opentelemetry/propagator-b3": ["@opentelemetry/propagator-b3@2.2.0", "", { "dependencies": { "@opentelemetry/core": "2.2.0" }, "peerDependencies": { "@opentelemetry/api": ">=1.0.0 <1.10.0" } }, "sha512-9CrbTLFi5Ee4uepxg2qlpQIozoJuoAZU5sKMx0Mn7Oh+p7UrgCiEV6C02FOxxdYVRRFQVCinYR8Kf6eMSQsIsw=="], + + "@opentelemetry/propagator-jaeger": ["@opentelemetry/propagator-jaeger@2.2.0", "", { "dependencies": { "@opentelemetry/core": "2.2.0" }, "peerDependencies": { "@opentelemetry/api": ">=1.0.0 <1.10.0" } }, "sha512-FfeOHOrdhiNzecoB1jZKp2fybqmqMPJUXe2ZOydP7QzmTPYcfPeuaclTLYVhK3HyJf71kt8sTl92nV4YIaLaKA=="], + + "@opentelemetry/resources": ["@opentelemetry/resources@2.2.0", "", { "dependencies": { "@opentelemetry/core": "2.2.0", "@opentelemetry/semantic-conventions": "^1.29.0" }, "peerDependencies": { "@opentelemetry/api": ">=1.3.0 <1.10.0" } }, "sha512-1pNQf/JazQTMA0BiO5NINUzH0cbLbbl7mntLa4aJNmCCXSj0q03T5ZXXL0zw4G55TjdL9Tz32cznGClf+8zr5A=="], + + "@opentelemetry/sdk-logs": ["@opentelemetry/sdk-logs@0.208.0", "", { "dependencies": { "@opentelemetry/api-logs": "0.208.0", "@opentelemetry/core": "2.2.0", "@opentelemetry/resources": "2.2.0" }, "peerDependencies": { "@opentelemetry/api": ">=1.4.0 <1.10.0" } }, "sha512-QlAyL1jRpOeaqx7/leG1vJMp84g0xKP6gJmfELBpnI4O/9xPX+Hu5m1POk9Kl+veNkyth5t19hRlN6tNY1sjbA=="], + + "@opentelemetry/sdk-metrics": ["@opentelemetry/sdk-metrics@2.2.0", "", { "dependencies": { "@opentelemetry/core": "2.2.0", "@opentelemetry/resources": "2.2.0" }, "peerDependencies": { "@opentelemetry/api": ">=1.9.0 <1.10.0" } }, "sha512-G5KYP6+VJMZzpGipQw7Giif48h6SGQ2PFKEYCybeXJsOCB4fp8azqMAAzE5lnnHK3ZVwYQrgmFbsUJO/zOnwGw=="], + + "@opentelemetry/sdk-node": ["@opentelemetry/sdk-node@0.208.0", "", { "dependencies": { "@opentelemetry/api-logs": "0.208.0", "@opentelemetry/core": "2.2.0", "@opentelemetry/exporter-logs-otlp-grpc": "0.208.0", "@opentelemetry/exporter-logs-otlp-http": "0.208.0", "@opentelemetry/exporter-logs-otlp-proto": "0.208.0", "@opentelemetry/exporter-metrics-otlp-grpc": "0.208.0", "@opentelemetry/exporter-metrics-otlp-http": "0.208.0", "@opentelemetry/exporter-metrics-otlp-proto": "0.208.0", "@opentelemetry/exporter-prometheus": "0.208.0", "@opentelemetry/exporter-trace-otlp-grpc": "0.208.0", "@opentelemetry/exporter-trace-otlp-http": "0.208.0", "@opentelemetry/exporter-trace-otlp-proto": "0.208.0", "@opentelemetry/exporter-zipkin": "2.2.0", "@opentelemetry/instrumentation": "0.208.0", "@opentelemetry/propagator-b3": "2.2.0", "@opentelemetry/propagator-jaeger": "2.2.0", "@opentelemetry/resources": "2.2.0", "@opentelemetry/sdk-logs": "0.208.0", "@opentelemetry/sdk-metrics": "2.2.0", "@opentelemetry/sdk-trace-base": "2.2.0", "@opentelemetry/sdk-trace-node": "2.2.0", "@opentelemetry/semantic-conventions": "^1.29.0" }, "peerDependencies": { "@opentelemetry/api": ">=1.3.0 <1.10.0" } }, "sha512-pbAqpZ7zTMFuTf3YecYsecsto/mheuvnK2a/jgstsE5ynWotBjgF5bnz5500W9Xl2LeUfg04WMt63TWtAgzRMw=="], + + "@opentelemetry/sdk-trace-base": ["@opentelemetry/sdk-trace-base@2.2.0", "", { "dependencies": { "@opentelemetry/core": "2.2.0", "@opentelemetry/resources": "2.2.0", "@opentelemetry/semantic-conventions": "^1.29.0" }, "peerDependencies": { "@opentelemetry/api": ">=1.3.0 <1.10.0" } }, "sha512-xWQgL0Bmctsalg6PaXExmzdedSp3gyKV8mQBwK/j9VGdCDu2fmXIb2gAehBKbkXCpJ4HPkgv3QfoJWRT4dHWbw=="], + + "@opentelemetry/sdk-trace-node": ["@opentelemetry/sdk-trace-node@2.2.0", "", { "dependencies": { "@opentelemetry/context-async-hooks": "2.2.0", "@opentelemetry/core": "2.2.0", "@opentelemetry/sdk-trace-base": "2.2.0" }, "peerDependencies": { "@opentelemetry/api": ">=1.0.0 <1.10.0" } }, "sha512-+OaRja3f0IqGG2kptVeYsrZQK9nKRSpfFrKtRBq4uh6nIB8bTBgaGvYQrQoRrQWQMA5dK5yLhDMDc0dvYvCOIQ=="], + + "@opentelemetry/semantic-conventions": ["@opentelemetry/semantic-conventions@1.38.0", "", {}, "sha512-kocjix+/sSggfJhwXqClZ3i9Y/MI0fp7b+g7kCRm6psy2dsf8uApTRclwG18h8Avm7C9+fnt+O36PspJ/OzoWg=="], + "@pkgjs/parseargs": ["@pkgjs/parseargs@0.11.0", "", {}, "sha512-+1VkjdD0QBLPodGrJUeqarH8VAIvQODIbwh9XpP5Syisf7YoQgsJKPNFoqqLQlu+VQ/tVSshMR6loPMn8U+dPg=="], - "@rollup/rollup-android-arm-eabi": ["@rollup/rollup-android-arm-eabi@4.41.1", "", { "os": "android", "cpu": "arm" }, "sha512-NELNvyEWZ6R9QMkiytB4/L4zSEaBC03KIXEghptLGLZWJ6VPrL63ooZQCOnlx36aQPGhzuOMwDerC1Eb2VmrLw=="], + "@protobufjs/aspromise": ["@protobufjs/aspromise@1.1.2", "", {}, "sha512-j+gKExEuLmKwvz3OgROXtrJ2UG2x8Ch2YZUxahh+s1F2HZ+wAceUNLkvy6zKCPVRkU++ZWQrdxsUeQXmcg4uoQ=="], + + "@protobufjs/base64": ["@protobufjs/base64@1.1.2", "", {}, "sha512-AZkcAA5vnN/v4PDqKyMR5lx7hZttPDgClv83E//FMNhR2TMcLUhfRUBHCmSl0oi9zMgDDqRUJkSxO3wm85+XLg=="], + + "@protobufjs/codegen": ["@protobufjs/codegen@2.0.4", "", {}, "sha512-YyFaikqM5sH0ziFZCN3xDC7zeGaB/d0IUb9CATugHWbd1FRFwWwt4ld4OYMPWu5a3Xe01mGAULCdqhMlPl29Jg=="], + + "@protobufjs/eventemitter": ["@protobufjs/eventemitter@1.1.0", "", {}, "sha512-j9ednRT81vYJ9OfVuXG6ERSTdEL1xVsNgqpkxMsbIabzSo3goCjDIveeGv5d03om39ML71RdmrGNjG5SReBP/Q=="], + + "@protobufjs/fetch": ["@protobufjs/fetch@1.1.0", "", { "dependencies": { "@protobufjs/aspromise": "^1.1.1", "@protobufjs/inquire": "^1.1.0" } }, "sha512-lljVXpqXebpsijW71PZaCYeIcE5on1w5DlQy5WH6GLbFryLUrBD4932W/E2BSpfRJWseIL4v/KPgBFxDOIdKpQ=="], + + "@protobufjs/float": ["@protobufjs/float@1.0.2", "", {}, "sha512-Ddb+kVXlXst9d+R9PfTIxh1EdNkgoRe5tOX6t01f1lYWOvJnSPDBlG241QLzcyPdoNTsblLUdujGSE4RzrTZGQ=="], + + "@protobufjs/inquire": ["@protobufjs/inquire@1.1.0", "", {}, "sha512-kdSefcPdruJiFMVSbn801t4vFK7KB/5gd2fYvrxhuJYg8ILrmn9SKSX2tZdV6V+ksulWqS7aXjBcRXl3wHoD9Q=="], + + "@protobufjs/path": ["@protobufjs/path@1.1.2", "", {}, "sha512-6JOcJ5Tm08dOHAbdR3GrvP+yUUfkjG5ePsHYczMFLq3ZmMkAD98cDgcT2iA1lJ9NVwFd4tH/iSSoe44YWkltEA=="], - "@rollup/rollup-android-arm64": ["@rollup/rollup-android-arm64@4.41.1", "", { "os": "android", "cpu": "arm64" }, "sha512-DXdQe1BJ6TK47ukAoZLehRHhfKnKg9BjnQYUu9gzhI8Mwa1d2fzxA1aw2JixHVl403bwp1+/o/NhhHtxWJBgEA=="], + "@protobufjs/pool": ["@protobufjs/pool@1.1.0", "", {}, "sha512-0kELaGSIDBKvcgS4zkjz1PeddatrjYcmMWOlAuAPwAeccUrPHdUqo/J6LiymHHEiJT5NrF1UVwxY14f+fy4WQw=="], - "@rollup/rollup-darwin-arm64": ["@rollup/rollup-darwin-arm64@4.41.1", "", { "os": "darwin", "cpu": "arm64" }, "sha512-5afxvwszzdulsU2w8JKWwY8/sJOLPzf0e1bFuvcW5h9zsEg+RQAojdW0ux2zyYAz7R8HvvzKCjLNJhVq965U7w=="], + "@protobufjs/utf8": ["@protobufjs/utf8@1.1.0", "", {}, "sha512-Vvn3zZrhQZkkBE8LSuW3em98c0FwgO4nxzv6OdSxPKJIEKY2bGbHn+mhGIPerzI4twdxaP8/0+06HBpwf345Lw=="], - "@rollup/rollup-darwin-x64": ["@rollup/rollup-darwin-x64@4.41.1", "", { "os": "darwin", "cpu": "x64" }, "sha512-egpJACny8QOdHNNMZKf8xY0Is6gIMz+tuqXlusxquWu3F833DcMwmGM7WlvCO9sB3OsPjdC4U0wHw5FabzCGZg=="], + "@rollup/rollup-android-arm-eabi": ["@rollup/rollup-android-arm-eabi@4.53.3", "", { "os": "android", "cpu": "arm" }, "sha512-mRSi+4cBjrRLoaal2PnqH82Wqyb+d3HsPUN/W+WslCXsZsyHa9ZeQQX/pQsZaVIWDkPcpV6jJ+3KLbTbgnwv8w=="], - "@rollup/rollup-freebsd-arm64": ["@rollup/rollup-freebsd-arm64@4.41.1", "", { "os": "freebsd", "cpu": "arm64" }, "sha512-DBVMZH5vbjgRk3r0OzgjS38z+atlupJ7xfKIDJdZZL6sM6wjfDNo64aowcLPKIx7LMQi8vybB56uh1Ftck/Atg=="], + "@rollup/rollup-android-arm64": ["@rollup/rollup-android-arm64@4.53.3", "", { "os": "android", "cpu": "arm64" }, "sha512-CbDGaMpdE9sh7sCmTrTUyllhrg65t6SwhjlMJsLr+J8YjFuPmCEjbBSx4Z/e4SmDyH3aB5hGaJUP2ltV/vcs4w=="], - "@rollup/rollup-freebsd-x64": ["@rollup/rollup-freebsd-x64@4.41.1", "", { "os": "freebsd", "cpu": "x64" }, "sha512-3FkydeohozEskBxNWEIbPfOE0aqQgB6ttTkJ159uWOFn42VLyfAiyD9UK5mhu+ItWzft60DycIN1Xdgiy8o/SA=="], + "@rollup/rollup-darwin-arm64": ["@rollup/rollup-darwin-arm64@4.53.3", "", { "os": "darwin", "cpu": "arm64" }, "sha512-Nr7SlQeqIBpOV6BHHGZgYBuSdanCXuw09hon14MGOLGmXAFYjx1wNvquVPmpZnl0tLjg25dEdr4IQ6GgyToCUA=="], - "@rollup/rollup-linux-arm-gnueabihf": ["@rollup/rollup-linux-arm-gnueabihf@4.41.1", "", { "os": "linux", "cpu": "arm" }, "sha512-wC53ZNDgt0pqx5xCAgNunkTzFE8GTgdZ9EwYGVcg+jEjJdZGtq9xPjDnFgfFozQI/Xm1mh+D9YlYtl+ueswNEg=="], + "@rollup/rollup-darwin-x64": ["@rollup/rollup-darwin-x64@4.53.3", "", { "os": "darwin", "cpu": "x64" }, "sha512-DZ8N4CSNfl965CmPktJ8oBnfYr3F8dTTNBQkRlffnUarJ2ohudQD17sZBa097J8xhQ26AwhHJ5mvUyQW8ddTsQ=="], - "@rollup/rollup-linux-arm-musleabihf": ["@rollup/rollup-linux-arm-musleabihf@4.41.1", "", { "os": "linux", "cpu": "arm" }, "sha512-jwKCca1gbZkZLhLRtsrka5N8sFAaxrGz/7wRJ8Wwvq3jug7toO21vWlViihG85ei7uJTpzbXZRcORotE+xyrLA=="], + "@rollup/rollup-freebsd-arm64": ["@rollup/rollup-freebsd-arm64@4.53.3", "", { "os": "freebsd", "cpu": "arm64" }, "sha512-yMTrCrK92aGyi7GuDNtGn2sNW+Gdb4vErx4t3Gv/Tr+1zRb8ax4z8GWVRfr3Jw8zJWvpGHNpss3vVlbF58DZ4w=="], - "@rollup/rollup-linux-arm64-gnu": ["@rollup/rollup-linux-arm64-gnu@4.41.1", "", { "os": "linux", "cpu": "arm64" }, "sha512-g0UBcNknsmmNQ8V2d/zD2P7WWfJKU0F1nu0k5pW4rvdb+BIqMm8ToluW/eeRmxCared5dD76lS04uL4UaNgpNA=="], + "@rollup/rollup-freebsd-x64": ["@rollup/rollup-freebsd-x64@4.53.3", "", { "os": "freebsd", "cpu": "x64" }, "sha512-lMfF8X7QhdQzseM6XaX0vbno2m3hlyZFhwcndRMw8fbAGUGL3WFMBdK0hbUBIUYcEcMhVLr1SIamDeuLBnXS+Q=="], - "@rollup/rollup-linux-arm64-musl": ["@rollup/rollup-linux-arm64-musl@4.41.1", "", { "os": "linux", "cpu": "arm64" }, "sha512-XZpeGB5TKEZWzIrj7sXr+BEaSgo/ma/kCgrZgL0oo5qdB1JlTzIYQKel/RmhT6vMAvOdM2teYlAaOGJpJ9lahg=="], + "@rollup/rollup-linux-arm-gnueabihf": ["@rollup/rollup-linux-arm-gnueabihf@4.53.3", "", { "os": "linux", "cpu": "arm" }, "sha512-k9oD15soC/Ln6d2Wv/JOFPzZXIAIFLp6B+i14KhxAfnq76ajt0EhYc5YPeX6W1xJkAdItcVT+JhKl1QZh44/qw=="], - "@rollup/rollup-linux-loongarch64-gnu": ["@rollup/rollup-linux-loongarch64-gnu@4.41.1", "", { "os": "linux", "cpu": "none" }, "sha512-bkCfDJ4qzWfFRCNt5RVV4DOw6KEgFTUZi2r2RuYhGWC8WhCA8lCAJhDeAmrM/fdiAH54m0mA0Vk2FGRPyzI+tw=="], + "@rollup/rollup-linux-arm-musleabihf": ["@rollup/rollup-linux-arm-musleabihf@4.53.3", "", { "os": "linux", "cpu": "arm" }, "sha512-vTNlKq+N6CK/8UktsrFuc+/7NlEYVxgaEgRXVUVK258Z5ymho29skzW1sutgYjqNnquGwVUObAaxae8rZ6YMhg=="], - "@rollup/rollup-linux-powerpc64le-gnu": ["@rollup/rollup-linux-powerpc64le-gnu@4.41.1", "", { "os": "linux", "cpu": "ppc64" }, "sha512-3mr3Xm+gvMX+/8EKogIZSIEF0WUu0HL9di+YWlJpO8CQBnoLAEL/roTCxuLncEdgcfJcvA4UMOf+2dnjl4Ut1A=="], + "@rollup/rollup-linux-arm64-gnu": ["@rollup/rollup-linux-arm64-gnu@4.53.3", "", { "os": "linux", "cpu": "arm64" }, "sha512-RGrFLWgMhSxRs/EWJMIFM1O5Mzuz3Xy3/mnxJp/5cVhZ2XoCAxJnmNsEyeMJtpK+wu0FJFWz+QF4mjCA7AUQ3w=="], - "@rollup/rollup-linux-riscv64-gnu": ["@rollup/rollup-linux-riscv64-gnu@4.41.1", "", { "os": "linux", "cpu": "none" }, "sha512-3rwCIh6MQ1LGrvKJitQjZFuQnT2wxfU+ivhNBzmxXTXPllewOF7JR1s2vMX/tWtUYFgphygxjqMl76q4aMotGw=="], + "@rollup/rollup-linux-arm64-musl": ["@rollup/rollup-linux-arm64-musl@4.53.3", "", { "os": "linux", "cpu": "arm64" }, "sha512-kASyvfBEWYPEwe0Qv4nfu6pNkITLTb32p4yTgzFCocHnJLAHs+9LjUu9ONIhvfT/5lv4YS5muBHyuV84epBo/A=="], - "@rollup/rollup-linux-riscv64-musl": ["@rollup/rollup-linux-riscv64-musl@4.41.1", "", { "os": "linux", "cpu": "none" }, "sha512-LdIUOb3gvfmpkgFZuccNa2uYiqtgZAz3PTzjuM5bH3nvuy9ty6RGc/Q0+HDFrHrizJGVpjnTZ1yS5TNNjFlklw=="], + "@rollup/rollup-linux-loong64-gnu": ["@rollup/rollup-linux-loong64-gnu@4.53.3", "", { "os": "linux", "cpu": "none" }, "sha512-JiuKcp2teLJwQ7vkJ95EwESWkNRFJD7TQgYmCnrPtlu50b4XvT5MOmurWNrCj3IFdyjBQ5p9vnrX4JM6I8OE7g=="], - "@rollup/rollup-linux-s390x-gnu": ["@rollup/rollup-linux-s390x-gnu@4.41.1", "", { "os": "linux", "cpu": "s390x" }, "sha512-oIE6M8WC9ma6xYqjvPhzZYk6NbobIURvP/lEbh7FWplcMO6gn7MM2yHKA1eC/GvYwzNKK/1LYgqzdkZ8YFxR8g=="], + "@rollup/rollup-linux-ppc64-gnu": ["@rollup/rollup-linux-ppc64-gnu@4.53.3", "", { "os": "linux", "cpu": "ppc64" }, "sha512-EoGSa8nd6d3T7zLuqdojxC20oBfNT8nexBbB/rkxgKj5T5vhpAQKKnD+h3UkoMuTyXkP5jTjK/ccNRmQrPNDuw=="], - "@rollup/rollup-linux-x64-gnu": ["@rollup/rollup-linux-x64-gnu@4.41.1", "", { "os": "linux", "cpu": "x64" }, "sha512-cWBOvayNvA+SyeQMp79BHPK8ws6sHSsYnK5zDcsC3Hsxr1dgTABKjMnMslPq1DvZIp6uO7kIWhiGwaTdR4Og9A=="], + "@rollup/rollup-linux-riscv64-gnu": ["@rollup/rollup-linux-riscv64-gnu@4.53.3", "", { "os": "linux", "cpu": "none" }, "sha512-4s+Wped2IHXHPnAEbIB0YWBv7SDohqxobiiPA1FIWZpX+w9o2i4LezzH/NkFUl8LRci/8udci6cLq+jJQlh+0g=="], - "@rollup/rollup-linux-x64-musl": ["@rollup/rollup-linux-x64-musl@4.41.1", "", { "os": "linux", "cpu": "x64" }, "sha512-y5CbN44M+pUCdGDlZFzGGBSKCA4A/J2ZH4edTYSSxFg7ce1Xt3GtydbVKWLlzL+INfFIZAEg1ZV6hh9+QQf9YQ=="], + "@rollup/rollup-linux-riscv64-musl": ["@rollup/rollup-linux-riscv64-musl@4.53.3", "", { "os": "linux", "cpu": "none" }, "sha512-68k2g7+0vs2u9CxDt5ktXTngsxOQkSEV/xBbwlqYcUrAVh6P9EgMZvFsnHy4SEiUl46Xf0IObWVbMvPrr2gw8A=="], - "@rollup/rollup-win32-arm64-msvc": ["@rollup/rollup-win32-arm64-msvc@4.41.1", "", { "os": "win32", "cpu": "arm64" }, "sha512-lZkCxIrjlJlMt1dLO/FbpZbzt6J/A8p4DnqzSa4PWqPEUUUnzXLeki/iyPLfV0BmHItlYgHUqJe+3KiyydmiNQ=="], + "@rollup/rollup-linux-s390x-gnu": ["@rollup/rollup-linux-s390x-gnu@4.53.3", "", { "os": "linux", "cpu": "s390x" }, "sha512-VYsFMpULAz87ZW6BVYw3I6sWesGpsP9OPcyKe8ofdg9LHxSbRMd7zrVrr5xi/3kMZtpWL/wC+UIJWJYVX5uTKg=="], - "@rollup/rollup-win32-ia32-msvc": ["@rollup/rollup-win32-ia32-msvc@4.41.1", "", { "os": "win32", "cpu": "ia32" }, "sha512-+psFT9+pIh2iuGsxFYYa/LhS5MFKmuivRsx9iPJWNSGbh2XVEjk90fmpUEjCnILPEPJnikAU6SFDiEUyOv90Pg=="], + "@rollup/rollup-linux-x64-gnu": ["@rollup/rollup-linux-x64-gnu@4.53.3", "", { "os": "linux", "cpu": "x64" }, "sha512-3EhFi1FU6YL8HTUJZ51imGJWEX//ajQPfqWLI3BQq4TlvHy4X0MOr5q3D2Zof/ka0d5FNdPwZXm3Yyib/UEd+w=="], - "@rollup/rollup-win32-x64-msvc": ["@rollup/rollup-win32-x64-msvc@4.41.1", "", { "os": "win32", "cpu": "x64" }, "sha512-Wq2zpapRYLfi4aKxf2Xff0tN+7slj2d4R87WEzqw7ZLsVvO5zwYCIuEGSZYiK41+GlwUo1HiR+GdkLEJnCKTCw=="], + "@rollup/rollup-linux-x64-musl": ["@rollup/rollup-linux-x64-musl@4.53.3", "", { "os": "linux", "cpu": "x64" }, "sha512-eoROhjcc6HbZCJr+tvVT8X4fW3/5g/WkGvvmwz/88sDtSJzO7r/blvoBDgISDiCjDRZmHpwud7h+6Q9JxFwq1Q=="], + + "@rollup/rollup-openharmony-arm64": ["@rollup/rollup-openharmony-arm64@4.53.3", "", { "os": "none", "cpu": "arm64" }, "sha512-OueLAWgrNSPGAdUdIjSWXw+u/02BRTcnfw9PN41D2vq/JSEPnJnVuBgw18VkN8wcd4fjUs+jFHVM4t9+kBSNLw=="], + + "@rollup/rollup-win32-arm64-msvc": ["@rollup/rollup-win32-arm64-msvc@4.53.3", "", { "os": "win32", "cpu": "arm64" }, "sha512-GOFuKpsxR/whszbF/bzydebLiXIHSgsEUp6M0JI8dWvi+fFa1TD6YQa4aSZHtpmh2/uAlj/Dy+nmby3TJ3pkTw=="], + + "@rollup/rollup-win32-ia32-msvc": ["@rollup/rollup-win32-ia32-msvc@4.53.3", "", { "os": "win32", "cpu": "ia32" }, "sha512-iah+THLcBJdpfZ1TstDFbKNznlzoxa8fmnFYK4V67HvmuNYkVdAywJSoteUszvBQ9/HqN2+9AZghbajMsFT+oA=="], + + "@rollup/rollup-win32-x64-gnu": ["@rollup/rollup-win32-x64-gnu@4.53.3", "", { "os": "win32", "cpu": "x64" }, "sha512-J9QDiOIZlZLdcot5NXEepDkstocktoVjkaKUtqzgzpt2yWjGlbYiKyp05rWwk4nypbYUNoFAztEgixoLaSETkg=="], + + "@rollup/rollup-win32-x64-msvc": ["@rollup/rollup-win32-x64-msvc@4.53.3", "", { "os": "win32", "cpu": "x64" }, "sha512-UhTd8u31dXadv0MopwGgNOBpUVROFKWVQgAg5N1ESyCz8AuBcMqm4AuTjrwgQKGDfoFuz02EuMRHQIw/frmYKQ=="], + + "@sap-ai-sdk/ai-api": ["@sap-ai-sdk/ai-api@2.3.0", "", { "dependencies": { "@sap-ai-sdk/core": "^2.3.0", "@sap-cloud-sdk/connectivity": "^4.1.2", "@sap-cloud-sdk/util": "^4.1.2" } }, "sha512-qlNqJvYqnqOyqQHfJrYVzU4nJVQYoCr0WUG+9ISrQ6deOPLWMZIip+6J3hZTW/TszmnSYi/UN/eTQ2hXUghtuw=="], + + "@sap-ai-sdk/core": ["@sap-ai-sdk/core@2.3.0", "", { "dependencies": { "@sap-cloud-sdk/connectivity": "^4.1.2", "@sap-cloud-sdk/http-client": "^4.1.2", "@sap-cloud-sdk/openapi": "^4.1.2", "@sap-cloud-sdk/util": "^4.1.2" } }, "sha512-1eoIte1BNDlVfn+2L8UCXkQi0W3Q3vUp4wyjUXVDBV5OStf5AMWLcr4/fwR/tId/S05zOnmXA0kK3Jn4QB8ykw=="], + + "@sap-ai-sdk/foundation-models": ["@sap-ai-sdk/foundation-models@2.3.0", "", { "dependencies": { "@sap-ai-sdk/ai-api": "^2.3.0", "@sap-ai-sdk/core": "^2.3.0", "@sap-cloud-sdk/connectivity": "^4.1.2", "@sap-cloud-sdk/http-client": "^4.1.2", "@sap-cloud-sdk/util": "^4.1.2" } }, "sha512-XY/Z9YHj/6HsK9FS4dYXfR5evjnW47F0C5UFSNfwk7hcROixs1qIS2Oc3a2dTm8H4TFb0FLwg0aJtqiSPJmGUQ=="], + + "@sap-ai-sdk/langchain": ["@sap-ai-sdk/langchain@2.3.0", "", { "dependencies": { "@langchain/core": "^1.1.0", "@sap-ai-sdk/ai-api": "^2.3.0", "@sap-ai-sdk/core": "^2.3.0", "@sap-ai-sdk/foundation-models": "^2.3.0", "@sap-ai-sdk/orchestration": "^2.3.0", "@sap-cloud-sdk/connectivity": "^4.1.2", "@sap-cloud-sdk/util": "^4.1.2", "uuid": "^13.0.0" } }, "sha512-5aniGM14dYkemO0LZJ4pWnm6Ra0+S5N1e1tQ08fbTy3DQyfrBbtd9V8yKLqK/8bEB777kmcj0D5tPnwKjelpOw=="], + + "@sap-ai-sdk/orchestration": ["@sap-ai-sdk/orchestration@2.3.0", "", { "dependencies": { "@sap-ai-sdk/ai-api": "^2.3.0", "@sap-ai-sdk/core": "^2.3.0", "@sap-ai-sdk/prompt-registry": "^2.3.0", "@sap-cloud-sdk/util": "^4.1.2", "yaml": "^2.8.1" } }, "sha512-qbf80V08BaFpQnwKWia5jyIjDVRUKaGn2UFYC9BDXO5YjLrV26znroGBzNVvFP/hp5yfBHVnrBK7imfLD8TZFA=="], + + "@sap-ai-sdk/prompt-registry": ["@sap-ai-sdk/prompt-registry@2.3.0", "", { "dependencies": { "@sap-ai-sdk/core": "^2.3.0", "zod": "^4.1.12" } }, "sha512-7Bi4K1zjZzTKt7UB69//XK94EbVYMJRhfFYWTFtLpt6vbgO7n+KsSSYAuxzhKNCuYKv20yyx+mEfhbUxNGh99w=="], + + "@sap-cloud-sdk/connectivity": ["@sap-cloud-sdk/connectivity@4.2.0", "", { "dependencies": { "@sap-cloud-sdk/resilience": "^4.2.0", "@sap-cloud-sdk/util": "^4.2.0", "@sap/xsenv": "^6.0.0", "@sap/xssec": "^4.11.2", "async-retry": "^1.3.3", "axios": "^1.13.2", "jsonwebtoken": "^9.0.2" } }, "sha512-dvQpjYWp9EhoUip4ftvnsVOG6BHJO+fOOuVs0R7V1IRyl7F49QPdpI/YoMzk3W7Rex9NozRa/0EXAe9L0CrFbA=="], + + "@sap-cloud-sdk/http-client": ["@sap-cloud-sdk/http-client@4.2.0", "", { "dependencies": { "@sap-cloud-sdk/connectivity": "^4.2.0", "@sap-cloud-sdk/resilience": "^4.2.0", "@sap-cloud-sdk/util": "^4.2.0", "axios": "^1.13.2" } }, "sha512-jpMeQpcyY3wfEbNlo0yqgu6jp+Rr3nOBYPt/k6GdjgR9qQFPgY1m2ZEsyd8B1Dhzb+BS3iW7fHunshVvGjCgtQ=="], + + "@sap-cloud-sdk/openapi": ["@sap-cloud-sdk/openapi@4.2.0", "", { "dependencies": { "@sap-cloud-sdk/connectivity": "^4.2.0", "@sap-cloud-sdk/http-client": "^4.2.0", "@sap-cloud-sdk/resilience": "^4.2.0", "@sap-cloud-sdk/util": "^4.2.0", "axios": "^1.13.2" } }, "sha512-lubhOWJqE6n8MZcBjjd6uMFfI8Im3Jma1Mimsh/lJgJP2seOQ7eXnD0zi1zLC8ah4x+k86QrLozdJ5F5Izgvzw=="], + + "@sap-cloud-sdk/resilience": ["@sap-cloud-sdk/resilience@4.2.0", "", { "dependencies": { "@sap-cloud-sdk/util": "^4.2.0", "async-retry": "^1.3.3", "axios": "^1.13.2", "opossum": "^9.0.0" } }, "sha512-ZR2UugUEKEawIu6SIfz9OM8nQO43s/37jnmU4L+vTQN+ptFdFg+2bJAjj+F3jyqSaBx6JbALs9r6X2eWRc+ZDQ=="], + + "@sap-cloud-sdk/util": ["@sap-cloud-sdk/util@4.2.0", "", { "dependencies": { "axios": "^1.13.2", "chalk": "^4.1.0", "logform": "^2.7.0", "voca": "^1.4.1", "winston": "^3.18.3", "winston-transport": "^4.9.0" } }, "sha512-sAyb1hWATZKKu+NZWX65oIdSI4uKj//0UOl4vtzMPNgYXhF806aAWbj2tLZAHI4UTtQWedbfcHhwO7BLl9MvQQ=="], + + "@sap/xsenv": ["@sap/xsenv@6.0.0", "", { "dependencies": { "debug": "4.4.1", "node-cache": "^5.1.2", "verror": "1.10.1" } }, "sha512-9bNpJXmxndWn5JbRCPPtbeMqldXOn2Od17ybS92PHd1rNkZ80IMmOURHNct5YSVQ1MKBIDAyC+ck6VL7cVAfUA=="], + + "@sap/xssec": ["@sap/xssec@4.12.1", "", { "dependencies": { "debug": "^4.4.3", "jwt-decode": "^4" } }, "sha512-LcCnFuoNKosXJ9H71Yd9vRNknB+LHsghro1eHgQ8jUmacSt/C2USL7BsJ4TDb4DxeeZB4wieUEy5HBPZM9T+Jw=="], "@selemondev/svgl-svelte": ["@selemondev/svgl-svelte@0.0.3", "", { "peerDependencies": { "svelte": "^5.0.0" } }, "sha512-86WAfU6MaMrC2uLU+LhfQoH7et4dJye58jcJCaLtHsB2vNpzKslA6evveAZ+w0Pf29yr9oT0TNChjo4OQLTikQ=="], + "@so-ric/colorspace": ["@so-ric/colorspace@1.1.6", "", { "dependencies": { "color": "^5.0.2", "text-hex": "1.0.x" } }, "sha512-/KiKkpHNOBgkFJwu9sh48LkHSMYGyuTcSFK/qMBdnOAlrRJzRSXAOFB5qwzaVQuDl8wAvHVMkaASQDReTahxuw=="], + "@sveltejs/acorn-typescript": ["@sveltejs/acorn-typescript@1.0.5", "", { "peerDependencies": { "acorn": "^8.9.0" } }, "sha512-IwQk4yfwLdibDlrXVE04jTZYlLnwsTT2PIOQQGNLWfjavGifnk1JD1LcZjZaBTRcxZu2FfPfNLOE04DSu9lqtQ=="], "@sveltejs/vite-plugin-svelte": ["@sveltejs/vite-plugin-svelte@5.1.1", "", { "dependencies": { "@sveltejs/vite-plugin-svelte-inspector": "^4.0.1", "debug": "^4.4.1", "deepmerge": "^4.3.1", "kleur": "^4.1.5", "magic-string": "^0.30.17", "vitefu": "^1.0.6" }, "peerDependencies": { "svelte": "^5.0.0", "vite": "^6.0.0" } }, "sha512-Y1Cs7hhTc+a5E9Va/xwKlAJoariQyHY+5zBgCZg4PFWNYQ1nMN9sjK1zhw1gK69DuqVP++sht/1GZg1aRwmAXQ=="], @@ -200,9 +344,9 @@ "@swc/helpers": ["@swc/helpers@0.5.17", "", { "dependencies": { "tslib": "^2.8.0" } }, "sha512-5IKx/Y13RsYd+sauPb2x+U/xZikHjolzfuDgTAl/Tdf3Q8rslRvC19NKDLgAJQ6wsqADk10ntlv08nPFw/gO/A=="], - "@tanstack/query-core": ["@tanstack/query-core@https://pkg.pr.new/TanStack/query/@tanstack/query-core@746b9c5", {}], + "@tanstack/query-core": ["@tanstack/query-core@5.90.12", "", {}, "sha512-T1/8t5DhV/SisWjDnaiU2drl6ySvsHj1bHBCWNXd+/T+Hh1cf6JodyEYMd5sgwm+b/mETT4EV3H+zCVczCU5hg=="], - "@tanstack/svelte-query": ["@tanstack/svelte-query@https://pkg.pr.new/@tanstack/svelte-query@746b9c5d83e901deb3a5ca7012a4b4e2b617c5e3", { "dependencies": { "@tanstack/query-core": "https://pkg.pr.new/TanStack/query/@tanstack/query-core@746b9c5" }, "peerDependencies": { "svelte": "^5.7.0" } }], + "@tanstack/svelte-query": ["@tanstack/svelte-query@6.0.10", "", { "dependencies": { "@tanstack/query-core": "5.90.12" }, "peerDependencies": { "svelte": "^5.25.0" } }, "sha512-J0kM3JNvRcRCM6cbHLeICs73aLp98N/nsihdVEtiNo3MEN4pAnO45qZ2yxX70MrEZ9vffXaCXMCChwgXs1lZ/Q=="], "@tsconfig/svelte": ["@tsconfig/svelte@5.0.5", "", {}, "sha512-48fAnUjKye38FvMiNOj0J9I/4XlQQiZlpe9xaNPfe8vy2Y1hFBt8g1yqf2EGjVvHavo4jf2lC+TQyENCr4BJBQ=="], @@ -210,13 +354,23 @@ "@types/estree": ["@types/estree@1.0.8", "", {}, "sha512-dWHzHa2WqEXI/O1E9OjrocMTKJl2mSrEolh1Iomrv6U+JuNwaHXsXx9bLu5gG7BUWFIN0skIQJQ/L1rIex4X6w=="], + "@types/node": ["@types/node@25.0.2", "", { "dependencies": { "undici-types": "~7.16.0" } }, "sha512-gWEkeiyYE4vqjON/+Obqcoeffmk0NF15WSBwSs7zwVA2bAbTaE0SJ7P0WNGoJn8uE7fiaV5a7dKYIJriEqOrmA=="], + + "@types/retry": ["@types/retry@0.12.0", "", {}, "sha512-wWKOClTTiizcZhXnPY4wikVAwmdYHp8q6DmC+EJUzAMsycb7HB32Kh9RN4+0gExjmPmZSAQjgURXIGATPegAvA=="], + "@types/tern": ["@types/tern@0.23.9", "", { "dependencies": { "@types/estree": "*" } }, "sha512-ypzHFE/wBzh+BlH6rrBgS5I/Z7RD21pGhZ2rltb/+ZrVM1awdZwjx7hE5XfuYgHWk9uvV5HLZN3SloevCAp3Bw=="], + "@types/triple-beam": ["@types/triple-beam@1.3.5", "", {}, "sha512-6WaYesThRMCl19iryMYP7/x2OVgCtbIVflDGFpWnb9irXI3UjYE4AzmYuiUKY1AJstGijoY+MgUszMgRxIYTYw=="], + + "@types/uuid": ["@types/uuid@10.0.0", "", {}, "sha512-7gqG38EyHgyP1S+7+xomFtL+ZNHcKv6DwNaCZmJmo1vgMugyF3TCnXVg4t1uk89mLNwnLtnY3TpOpCOyp1/xHQ=="], + "acorn": ["acorn@8.14.1", "", { "bin": { "acorn": "bin/acorn" } }, "sha512-OvQ/2pUDKmgfCg++xsTX1wGxfTaszcHVcTctW4UJB4hibJx2HXxxO5UmVgyjMa+ZDsiaf5wWLXYpRWMmBI0QHg=="], + "acorn-import-attributes": ["acorn-import-attributes@1.9.5", "", { "peerDependencies": { "acorn": "^8" } }, "sha512-n02Vykv5uA3eHGM/Z2dQrcD56kL8TyDb2p1+0P83PClMnC/nc+anbQRhIOWnSq4Ke/KvDPrY3C9hDtC/A3eHnQ=="], + "ansi-regex": ["ansi-regex@6.1.0", "", {}, "sha512-7HSX4QQb4CspciLpVFwyRe79O3xsIZDDLER21kERQ71oaPodF8jL725AgJMFAYbooIqolJoRLuM81SpeUkpkvA=="], - "ansi-styles": ["ansi-styles@6.2.1", "", {}, "sha512-bN798gFfQX+viw3R7yrGWRqnrN2oRkEkUjjl4JNn4E8GxxbjtG3FbrEIIY3l8/hrwUwIeCZvi4QuOTP4MErVug=="], + "ansi-styles": ["ansi-styles@5.2.0", "", {}, "sha512-Cxwpt2SfTzTtXcfOlzGEee8O+c+MmUgGrNiBcXnuWxuFJHe6a5Hz7qwhwe5OgaSYI0IJvkLqWX1ASG+cJOkEiA=="], "any-promise": ["any-promise@1.3.0", "", {}, "sha512-7UvmKalWRt1wgjL1RrGxoSJW/0QZFIegpeGvZG9kjp8vrRu55XTHbwnqq2GpXm9uLbcuhxm3IqX9OB4MZR1b2A=="], @@ -226,12 +380,24 @@ "aria-query": ["aria-query@5.3.2", "", {}, "sha512-COROpnaoap1E2F000S62r6A60uHZnmlvomhfyT2DlTcrY1OrBKn2UhH7qn5wTC9zMvD0AY7csdPSNwKP+7WiQw=="], + "assert-plus": ["assert-plus@1.0.0", "", {}, "sha512-NfJ4UzBCcQGLDlQq7nHxH+tv3kyZ0hHQqF5BO6J7tNJeP5do1llPr8dZ8zHonfhAu0PHAdMkSo+8o0wxg9lZWw=="], + + "async": ["async@3.2.6", "", {}, "sha512-htCUDlxyyCLMgaM3xXg0C0LW2xqfuQ6p05pCEIsXuyQ+a1koYKTuBMzRNwmybfLgvJDMd0r1LTn4+E0Ti6C2AA=="], + + "async-retry": ["async-retry@1.3.3", "", { "dependencies": { "retry": "0.13.1" } }, "sha512-wfr/jstw9xNi/0teMHrRW7dsz3Lt5ARhYNZ2ewpadnhaIp5mbALhOAP+EAdsC7t4Z6wqsDVv9+W6gm1Dk9mEyw=="], + + "asynckit": ["asynckit@0.4.0", "", {}, "sha512-Oei9OH4tRh0YqU3GxhX79dM/mwVgvbZJaSNaRk+bshkj0S5cfHcgYakreBjrHwatXKbz+IoIdYLxrKim2MjW0Q=="], + "autoprefixer": ["autoprefixer@10.4.21", "", { "dependencies": { "browserslist": "^4.24.4", "caniuse-lite": "^1.0.30001702", "fraction.js": "^4.3.7", "normalize-range": "^0.1.2", "picocolors": "^1.1.1", "postcss-value-parser": "^4.2.0" }, "peerDependencies": { "postcss": "^8.1.0" }, "bin": { "autoprefixer": "bin/autoprefixer" } }, "sha512-O+A6LWV5LDHSJD3LjHYoNi4VLsj/Whi7k6zG12xTYaU4cQ8oxQGckXNX8cRHK5yOZ/ppVHe0ZBXGzSV9jXdVbQ=="], + "axios": ["axios@1.13.2", "", { "dependencies": { "follow-redirects": "^1.15.6", "form-data": "^4.0.4", "proxy-from-env": "^1.1.0" } }, "sha512-VPk9ebNqPcy5lRGuSlKx752IlDatOjT9paPlm8A7yOuW2Fbvp4X3JznJtT4f0GzGLLiWE9W8onz51SqLYwzGaA=="], + "axobject-query": ["axobject-query@4.1.0", "", {}, "sha512-qIj0G9wZbMGNLjLmg1PT6v2mE9AH2zlnADJD/2tC6E00hgmhUOfEB6greHPAfLRSufHqROIUTkw6E+M3lH0PTQ=="], "balanced-match": ["balanced-match@1.0.2", "", {}, "sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw=="], + "base64-js": ["base64-js@1.5.1", "", {}, "sha512-AKpaYlHn8t4SVbOHCy+b5+KKgvR4vrsD8vbvrbiQJps7fKDTkjkDry6ji0rUJjC0kzbNePLwzxq8iypo41qeWA=="], + "binary-extensions": ["binary-extensions@2.3.0", "", {}, "sha512-Ceh+7ox5qe7LJuLHoY0feh3pHuUDHAcRUeyL2VYghZwfpkNIy/+8Ocg0a3UuSoYzavmylwuLWQOf3hl0jjMMIw=="], "bits-ui": ["bits-ui@2.11.8", "", { "dependencies": { "@floating-ui/core": "^1.7.1", "@floating-ui/dom": "^1.7.1", "esm-env": "^1.1.2", "runed": "^0.35.1", "svelte-toolbelt": "^0.10.6", "tabbable": "^6.2.0" }, "peerDependencies": { "@internationalized/date": "^3.8.1", "svelte": "^5.33.0" } }, "sha512-zsgVH2iozBywIPJ7iF0fgp+23pGRGj0FyC9uFL4oZ83hhfaN5IEEkED7UtEf5LAjczc67zlmOIxwTRFBKvFX/Q=="], @@ -242,24 +408,48 @@ "browserslist": ["browserslist@4.25.0", "", { "dependencies": { "caniuse-lite": "^1.0.30001718", "electron-to-chromium": "^1.5.160", "node-releases": "^2.0.19", "update-browserslist-db": "^1.1.3" }, "bin": { "browserslist": "cli.js" } }, "sha512-PJ8gYKeS5e/whHBh8xrwYK+dAvEj7JXtz6uTucnMRB8OiGTsKccFekoRrjajPBHV8oOY+2tI4uxeceSimKwMFA=="], + "buffer-equal-constant-time": ["buffer-equal-constant-time@1.0.1", "", {}, "sha512-zRpUiDwd/xk6ADqPMATG8vc9VPrkck7T07OIx0gnjmJAnHnTVXNQG3vfvWNuiZIkwu9KrKdA1iJKfsfTVxE6NA=="], + "builtin-modules": ["builtin-modules@5.0.0", "", {}, "sha512-bkXY9WsVpY7CvMhKSR6pZilZu9Ln5WDrKVBUXf2S443etkmEO4V58heTecXcUIsNsi4Rx8JUO4NfX1IcQl4deg=="], + "call-bind-apply-helpers": ["call-bind-apply-helpers@1.0.2", "", { "dependencies": { "es-errors": "^1.3.0", "function-bind": "^1.1.2" } }, "sha512-Sp1ablJ0ivDkSzjcaJdxEunN5/XvksFJ2sMBFfq6x0ryhQV/2b/KwFe21cMpmHtPOSij8K99/wSfoEuTObmuMQ=="], + + "camelcase": ["camelcase@6.3.0", "", {}, "sha512-Gmy6FhYlCY7uOElZUSbxo2UCDH8owEk996gkbrpsgGtrJLM3J7jGxl9Ic7Qwwj4ivOE5AWZWRMecDdF7hqGjFA=="], + "camelcase-css": ["camelcase-css@2.0.1", "", {}, "sha512-QOSvevhslijgYwRx6Rv7zKdMF8lbRmx+uQGx2+vDc+KI/eBnsy9kit5aj23AgGu3pa4t9AgwbnXWqS+iOY+2aA=="], "caniuse-lite": ["caniuse-lite@1.0.30001721", "", {}, "sha512-cOuvmUVtKrtEaoKiO0rSc29jcjwMwX5tOHDy4MgVFEWiUXj4uBMJkwI8MDySkgXidpMiHUcviogAvFi4pA2hDQ=="], + "chalk": ["chalk@4.1.2", "", { "dependencies": { "ansi-styles": "^4.1.0", "supports-color": "^7.1.0" } }, "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA=="], + "chokidar": ["chokidar@4.0.3", "", { "dependencies": { "readdirp": "^4.0.1" } }, "sha512-Qgzu8kfBvo+cA4962jnP1KkS6Dop5NS6g7R5LFYJr4b8Ub94PPQXUksCw9PvXoeXPRRddRNC5C1JQUR2SMGtnA=="], + "cjs-module-lexer": ["cjs-module-lexer@1.4.3", "", {}, "sha512-9z8TZaGM1pfswYeXrUpzPrkx8UnWYdhJclsiYMm6x/w5+nN+8Tf/LnAgfLGQCm59qAOxU8WwHEq2vNwF6i4j+Q=="], + "cli-color": ["cli-color@2.0.4", "", { "dependencies": { "d": "^1.0.1", "es5-ext": "^0.10.64", "es6-iterator": "^2.0.3", "memoizee": "^0.4.15", "timers-ext": "^0.1.7" } }, "sha512-zlnpg0jNcibNrO7GG9IeHH7maWFeCz+Ja1wx/7tZNU5ASSSSZ+/qZciM0/LHCYxSdqv5h2sdbQ/PXYdOuetXvA=="], + "cliui": ["cliui@8.0.1", "", { "dependencies": { "string-width": "^4.2.0", "strip-ansi": "^6.0.1", "wrap-ansi": "^7.0.0" } }, "sha512-BSeNnyus75C4//NQ9gQt1/csTXyo/8Sb+afLAkzAptFuMsod9HFokGNudZpi/oQV73hnVK+sR+5PVRMd+Dr7YQ=="], + + "clone": ["clone@2.1.2", "", {}, "sha512-3Pe/CF1Nn94hyhIYpjtiLhdCoEoz0DqQ+988E9gmeEdQZlojxnOb74wctFyuwWQHzqyf9X7C7MG8juUpqBJT8w=="], + "clsx": ["clsx@2.1.1", "", {}, "sha512-eYm0QWBtUrBWZWG0d386OGAw16Z995PiOVo2B7bjWSbHedGl5e0ZWaq65kOGgUSNesEIDkB9ISbTg/JK9dhCZA=="], + "color": ["color@5.0.3", "", { "dependencies": { "color-convert": "^3.1.3", "color-string": "^2.1.3" } }, "sha512-ezmVcLR3xAVp8kYOm4GS45ZLLgIE6SPAFoduLr6hTDajwb3KZ2F46gulK3XpcwRFb5KKGCSezCBAY4Dw4HsyXA=="], + "color-convert": ["color-convert@2.0.1", "", { "dependencies": { "color-name": "~1.1.4" } }, "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ=="], "color-name": ["color-name@1.1.4", "", {}, "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA=="], + "color-string": ["color-string@2.1.4", "", { "dependencies": { "color-name": "^2.0.0" } }, "sha512-Bb6Cq8oq0IjDOe8wJmi4JeNn763Xs9cfrBcaylK1tPypWzyoy2G3l90v9k64kjphl/ZJjPIShFztenRomi8WTg=="], + + "combined-stream": ["combined-stream@1.0.8", "", { "dependencies": { "delayed-stream": "~1.0.0" } }, "sha512-FQN4MRfuJeHf7cBbBMJFXhKSDq+2kAArBlmRBvcvFE5BB1HZKXtSFASDhdlz9zOYwxh8lDdnvmMOe/+5cdoEdg=="], + "commander": ["commander@4.1.1", "", {}, "sha512-NOKm8xhkzAjzFx8B2v5OAHT+u5pRQc2UCa2Vq9jYL/31o2wi9mxBA7LIFs3sV5VSC49z6pEhfbMULvShKj26WA=="], + "console-table-printer": ["console-table-printer@2.15.0", "", { "dependencies": { "simple-wcswidth": "^1.1.2" } }, "sha512-SrhBq4hYVjLCkBVOWaTzceJalvn5K1Zq5aQA6wXC/cYjI3frKWNPEMK3sZsJfNNQApvCQmgBcc13ZKmFj8qExw=="], + + "core-util-is": ["core-util-is@1.0.2", "", {}, "sha512-3lqz5YjWTYnW6dlDa5TLaTCcShfar1e40rmcJVwCBJC6mWlFuj0eCHIElmG1g5kyuJ/GD+8Wn4FFCcz4gJPfaQ=="], + "crelt": ["crelt@1.0.6", "", {}, "sha512-VQ2MBenTq1fWZUH9DJNGti7kKv6EeAuYr3cLwxUWhIu1baTaXh4Ib5W2CqHVqib4/MqbYGJqiL3Zb8GJZr3l4g=="], "cross-spawn": ["cross-spawn@7.0.6", "", { "dependencies": { "path-key": "^3.1.0", "shebang-command": "^2.0.0", "which": "^2.0.1" } }, "sha512-uV2QOWP2nWzsy2aMp8aRibhi9dlzF5Hgh5SHaB9OiTGEyDTiJJyx0uy51QXdyWbtAHNua4XJzUKca3OzKUd3vA=="], @@ -270,10 +460,14 @@ "debug": ["debug@4.4.1", "", { "dependencies": { "ms": "^2.1.3" } }, "sha512-KcKCqiftBJcZr++7ykoDIEwSa3XWowTfNPo92BYxjXiyYEVrUQh2aLyhxBCwww+heortUFxEJYcRzosstTEBYQ=="], + "decamelize": ["decamelize@1.2.0", "", {}, "sha512-z2S+W9X73hAUUki+N+9Za2lBlun89zigOyGrsax+KUQ6wKW4ZoWpEYBkGhQjwAjjDCkWxhY0VKEhk8wzY7F5cA=="], + "decimal.js": ["decimal.js@10.5.0", "", {}, "sha512-8vDa8Qxvr/+d94hSh5P3IJwI5t8/c0KsMp+g8bNw9cY2icONa5aPfvKeieW1WlG0WQYwwhJ7mjui2xtiePQSXw=="], "deepmerge": ["deepmerge@4.3.1", "", {}, "sha512-3sUqbMEc77XqpdNO7FRyRog+eW3ph+GYCbj+rK+uYyRMuwsVy0rMiVtPn+QJlKFvWP/1PYpapqYn0Me2knFn+A=="], + "delayed-stream": ["delayed-stream@1.0.0", "", {}, "sha512-ZySD7Nf91aLB0RxL4KGrKHBXl7Eds1DAmEdcoVawXnLD7SDhpNgtuII2aAkg7a7QS41jxPSZ17p4VdGnMHk3MQ=="], + "dequal": ["dequal@2.0.3", "", {}, "sha512-0je+qPKHEMohvfRTCEo3CrPG6cAzAYgmzKyxRiYSSDkS6eGJdyVJm7WaYA5ECaAD9wLB2T4EEeymA5aFVcYXCA=="], "dexie": ["dexie@4.2.1", "", {}, "sha512-Ckej0NS6jxQ4Po3OrSQBFddayRhTCic2DoCAG5zacOfOVB9P2Q5Xc5uL/nVa7ZVs+HdMnvUPzLFCB/JwpB6Csg=="], @@ -282,12 +476,28 @@ "dlv": ["dlv@1.1.3", "", {}, "sha512-+HlytyjlPKnIG8XuRG8WvmBP8xs8P71y+SKKS6ZXWoEgLuePxtDoUEiH7WkdePWrQ5JBpE6aoVqfZfJUQkjXwA=="], + "dotenv": ["dotenv@17.2.3", "", {}, "sha512-JVUnt+DUIzu87TABbhPmNfVdBDt18BLOWjMUFJMSi/Qqg7NTYtabbvSNJGOJ7afbRuv9D/lngizHtP7QyLQ+9w=="], + + "dunder-proto": ["dunder-proto@1.0.1", "", { "dependencies": { "call-bind-apply-helpers": "^1.0.1", "es-errors": "^1.3.0", "gopd": "^1.2.0" } }, "sha512-KIN/nDJBQRcXw0MLVhZE9iQHmG68qAVIBg9CqmUYjmQIhgij9U5MFvrqkUL5FbtyyzZuOeOt0zdeRe4UY7ct+A=="], + "eastasianwidth": ["eastasianwidth@0.2.0", "", {}, "sha512-I88TYZWc9XiYHRQ4/3c5rjjfgkjhLyW2luGIheGERbNQ6OY7yTybanSpDXZa8y7VUP9YmDcYa+eyq4ca7iLqWA=="], + "ecdsa-sig-formatter": ["ecdsa-sig-formatter@1.0.11", "", { "dependencies": { "safe-buffer": "^5.0.1" } }, "sha512-nagl3RYrbNv6kQkeJIpt6NJZy8twLB/2vtz6yN9Z4vRKHN4/QZJIEbqohALSgwKdnksuY3k5Addp5lg8sVoVcQ=="], + "electron-to-chromium": ["electron-to-chromium@1.5.165", "", {}, "sha512-naiMx1Z6Nb2TxPU6fiFrUrDTjyPMLdTtaOd2oLmG8zVSg2hCWGkhPyxwk+qRmZ1ytwVqUv0u7ZcDA5+ALhaUtw=="], "emoji-regex": ["emoji-regex@9.2.2", "", {}, "sha512-L18DaJsXSUk2+42pv8mLs5jJT2hqFkFE4j21wOmgbUqsZ2hL72NsUU785g9RXgo3s0ZNgVl42TiHp3ZtOv/Vyg=="], + "enabled": ["enabled@2.0.0", "", {}, "sha512-AKrN98kuwOzMIdAizXGI86UFBoo26CL21UM763y1h/GMSJ4/OHU9k2YlsmBpyScFo/wbLzWQJBMCW4+IO3/+OQ=="], + + "es-define-property": ["es-define-property@1.0.1", "", {}, "sha512-e3nRfgfUZ4rNGL232gUgX06QNyyez04KdjFrF+LTRoOXmrOgFKDg4BCdsjW8EnT69eqdYGmRpJwiPVYNrCaW3g=="], + + "es-errors": ["es-errors@1.3.0", "", {}, "sha512-Zf5H2Kxt2xjTvbJvP2ZWLEICxA6j+hAmMzIlypy4xcBg1vKVnx89Wy0GbS+kf5cwCVFFzdCFh2XSCFNULS6csw=="], + + "es-object-atoms": ["es-object-atoms@1.1.1", "", { "dependencies": { "es-errors": "^1.3.0" } }, "sha512-FGgH2h8zKNim9ljj7dankFPcICIK9Cp5bm+c2gQSYePhpaG5+esrLODihIorn+Pe6FGJzWhXQotPv73jTaldXA=="], + + "es-set-tostringtag": ["es-set-tostringtag@2.1.0", "", { "dependencies": { "es-errors": "^1.3.0", "get-intrinsic": "^1.2.6", "has-tostringtag": "^1.0.2", "hasown": "^2.0.2" } }, "sha512-j6vWzfrGVfyXxge+O0x5sh6cvxAog0a/4Rdd2K36zCMV5eJ+/+tOAngRO8cODMNWbVRdVlmGZQL2YS3yR8bIUA=="], + "es5-ext": ["es5-ext@0.10.64", "", { "dependencies": { "es6-iterator": "^2.0.3", "es6-symbol": "^3.1.3", "esniff": "^2.0.1", "next-tick": "^1.1.0" } }, "sha512-p2snDhiLaXe6dahss1LddxqEm+SkuDvV8dnIQG0MWjyHpcMNfXKPE+/Cc0y+PhxJX3A4xGNeFCj5oc0BUh6deg=="], "es6-iterator": ["es6-iterator@2.0.3", "", { "dependencies": { "d": "1", "es5-ext": "^0.10.35", "es6-symbol": "^3.1.1" } }, "sha512-zw4SRzoUkd+cl+ZoE15A9o1oQd920Bb0iOJMQkQhl3jNc03YqVjAhG7scf9C5KWRU/R13Orf588uCC6525o02g=="], @@ -310,24 +520,42 @@ "event-emitter": ["event-emitter@0.3.5", "", { "dependencies": { "d": "1", "es5-ext": "~0.10.14" } }, "sha512-D9rRn9y7kLPnJ+hMq7S/nhvoKwwvVJahBi2BPmx3bvbsEdK3W9ii8cBSGjP+72/LnM4n6fo3+dkCX5FeTQruXA=="], + "eventemitter3": ["eventemitter3@4.0.7", "", {}, "sha512-8guHBZCwKnFhYdHr2ysuRWErTwhoN2X8XELRlrRwpmfeY2jjuUN4taQMsULKUVo1K4DvZl+0pgfyoysHxvmvEw=="], + "ext": ["ext@1.7.0", "", { "dependencies": { "type": "^2.7.2" } }, "sha512-6hxeJYaL110a9b5TEJSj0gojyHQAmA2ch5Os+ySCiA1QGdS697XWY1pzsrSjqA9LDEEgdB/KypIlR59RcLuHYw=="], + "extsprintf": ["extsprintf@1.4.1", "", {}, "sha512-Wrk35e8ydCKDj/ArClo1VrPVmN8zph5V4AtHwIuHhvMXsKf73UT3BOD+azBIW+3wOJ4FhEH7zyaJCFvChjYvMA=="], + "fast-glob": ["fast-glob@3.3.3", "", { "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" } }, "sha512-7MptL8U0cqcFdzIzwOTHoilX9x5BrNqye7Z/LuC7kCMRio1EMSyqRK3BEAUD7sXRq4iT4AzTVuZdhgQ2TCvYLg=="], "fastq": ["fastq@1.19.1", "", { "dependencies": { "reusify": "^1.0.4" } }, "sha512-GwLTyxkCXjXbxqIhTsMI2Nui8huMPtnxg7krajPJAjnEG/iiOS7i+zCtWGZR9G0NBKbXKh6X9m9UIsYX/N6vvQ=="], "fdir": ["fdir@6.4.5", "", { "peerDependencies": { "picomatch": "^3 || ^4" }, "optionalPeers": ["picomatch"] }, "sha512-4BG7puHpVsIYxZUbiUE3RqGloLaSSwzYie5jvasC4LWuBWzZawynvYouhjbQKw2JuIGYdm0DzIxl8iVidKlUEw=="], + "fecha": ["fecha@4.2.3", "", {}, "sha512-OP2IUU6HeYKJi3i0z4A19kHMQoLVs4Hc+DPqqxI2h/DPZHTm/vjsfC6P0b4jCMy14XizLBqvndQ+UilD7707Jw=="], + "fill-range": ["fill-range@7.1.1", "", { "dependencies": { "to-regex-range": "^5.0.1" } }, "sha512-YsGpe3WHLK8ZYi4tWDg2Jy3ebRz2rXowDxnld4bkQB00cc/1Zw9AWnC0i9ztDJitivtQvaI9KaLyKrc+hBW0yg=="], + "fn.name": ["fn.name@1.1.0", "", {}, "sha512-GRnmB5gPyJpAhTQdSZTSp9uaPSvl09KoYcMQtsB9rQoOmzs9dH6ffeccH+Z+cv6P68Hu5bC6JjRh4Ah/mHSNRw=="], + + "follow-redirects": ["follow-redirects@1.15.11", "", {}, "sha512-deG2P0JfjrTxl50XGCDyfI97ZGVCxIpfKYmfyrQ54n5FO/0gfIES8C/Psl6kWVDolizcaaxZJnTS0QSMxvnsBQ=="], + "foreground-child": ["foreground-child@3.3.1", "", { "dependencies": { "cross-spawn": "^7.0.6", "signal-exit": "^4.0.1" } }, "sha512-gIXjKqtFuWEgzFRJA9WCQeSJLZDjgJUOMCMzxtvFq/37KojM1BFGufqsCy0r4qSQmYLsZYMeyRqzIWOMup03sw=="], + "form-data": ["form-data@4.0.5", "", { "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" } }, "sha512-8RipRLol37bNs2bhoV67fiTEvdTrbMUYcFTiy3+wuuOnUog2QBHCZWXDRijWQfAkhBj2Uf5UnVaiWwA5vdd82w=="], + "fraction.js": ["fraction.js@4.3.7", "", {}, "sha512-ZsDfxO51wGAXREY55a7la9LScWpwv9RxIrYABrlvOFBlH/ShPnrtsXeuUIfXKKOVicNxQ+o8JTbJvjS4M89yew=="], "fsevents": ["fsevents@2.3.3", "", { "os": "darwin" }, "sha512-5xoDfX+fL7faATnagmWPpbFtwh/R77WmMMqqHGS65C3vvB0YHrgF+B1YmZ3441tMj5n63k0212XNoJwzlhffQw=="], "function-bind": ["function-bind@1.1.2", "", {}, "sha512-7XHNxH7qX9xG5mIwxkhumTox/MIRNcOgDrxWsMt2pAr23WHp6MrRlN7FBSFpCpr+oVO0F744iUgR82nJMfG2SA=="], + "get-caller-file": ["get-caller-file@2.0.5", "", {}, "sha512-DyFP3BM/3YHTQOCUL/w0OZHR0lpKeGrxotcHWcqNEdnltqFwXVfhEBQ94eIo34AfQpo0rGki4cyIiftY06h2Fg=="], + + "get-intrinsic": ["get-intrinsic@1.3.0", "", { "dependencies": { "call-bind-apply-helpers": "^1.0.2", "es-define-property": "^1.0.1", "es-errors": "^1.3.0", "es-object-atoms": "^1.1.1", "function-bind": "^1.1.2", "get-proto": "^1.0.1", "gopd": "^1.2.0", "has-symbols": "^1.1.0", "hasown": "^2.0.2", "math-intrinsics": "^1.1.0" } }, "sha512-9fSjSaos/fRIVIp+xSJlE6lfwhES7LNtKaCBIamHsjr2na1BiABJPo0mOjjz8GJDURarmCPGqaiVg5mfjb98CQ=="], + + "get-proto": ["get-proto@1.0.1", "", { "dependencies": { "dunder-proto": "^1.0.1", "es-object-atoms": "^1.0.0" } }, "sha512-sTSfBjoXBp89JvIKIefqw7U2CCebsc74kiY6awiGogKtoSGbgjYE/G/+l9sF3MWFPNc9IcoOC4ODfKHfxFmp0g=="], + "glob": ["glob@10.4.5", "", { "dependencies": { "foreground-child": "^3.1.0", "jackspeak": "^3.1.2", "minimatch": "^9.0.4", "minipass": "^7.1.2", "package-json-from-dist": "^1.0.0", "path-scurry": "^1.11.1" }, "bin": { "glob": "dist/esm/bin.mjs" } }, "sha512-7Bv8RF0k6xjo7d4A/PxYLbUCfb6c+Vpd2/mB2yRDlew7Jb5hEXiCD9ibfO7wpk8i4sevK6DFny9h7EYbM3/sHg=="], "glob-parent": ["glob-parent@6.0.2", "", { "dependencies": { "is-glob": "^4.0.3" } }, "sha512-XxwI8EOhVQgWp6iDL+3b0r86f4d6AX6zSU55HfB4ydCEuXLXc5FcYeOu+nnGftS4TEju/11rt4KJPTMgbfmv4A=="], @@ -336,10 +564,22 @@ "globrex": ["globrex@0.1.2", "", {}, "sha512-uHJgbwAMwNFf5mLst7IWLNg14x1CkeqglJb/K3doi4dw6q2IvAAmM/Y81kevy83wP+Sst+nutFTYOGg3d1lsxg=="], + "gopd": ["gopd@1.2.0", "", {}, "sha512-ZUKRh6/kUFoAiTAtTYPZJ3hw9wNxx+BIBOijnlG9PnrJsCcSjs1wyyD6vJpaYtgnzDrKYRSqf3OO6Rfa93xsRg=="], + + "has-flag": ["has-flag@4.0.0", "", {}, "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ=="], + + "has-symbols": ["has-symbols@1.1.0", "", {}, "sha512-1cDNdwJ2Jaohmb3sg4OmKaMBwuC48sYni5HUw2DvsC8LjGTLK9h+eb1X6RyuOHe4hT0ULCW68iomhjUoKUqlPQ=="], + + "has-tostringtag": ["has-tostringtag@1.0.2", "", { "dependencies": { "has-symbols": "^1.0.3" } }, "sha512-NqADB8VjPFLM2V0VvHUewwwsw0ZWBaIdgo+ieHtK3hasLz4qeCRjYcqfB6AQrBggRKppKF8L52/VqdVsO47Dlw=="], + "hasown": ["hasown@2.0.2", "", { "dependencies": { "function-bind": "^1.1.2" } }, "sha512-0hJU9SCPvmMzIBdZFqNPXWa6dqh7WdH0cII9y+CyS8rG3nL48Bclra9HmKhVVUHyPWNH5Y7xDwAB7bfgSjkUMQ=="], "i18next": ["i18next@23.16.8", "", { "dependencies": { "@babel/runtime": "^7.23.2" } }, "sha512-06r/TitrM88Mg5FdUXAKL96dJMzgqLE5dv3ryBAra4KCwD9mJ4ndOTS95ZuymIGoE+2hzfdaMak2X11/es7ZWg=="], + "import-in-the-middle": ["import-in-the-middle@2.0.0", "", { "dependencies": { "acorn": "^8.14.0", "acorn-import-attributes": "^1.9.5", "cjs-module-lexer": "^1.2.2", "module-details-from-path": "^1.0.3" } }, "sha512-yNZhyQYqXpkT0AKq3F3KLasUSK4fHvebNH5hOsKQw2dhGSALvQ4U0BqUc5suziKvydO5u5hgN2hy1RJaho8U5A=="], + + "inherits": ["inherits@2.0.4", "", {}, "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ=="], + "inline-style-parser": ["inline-style-parser@0.2.4", "", {}, "sha512-0aO8FkhNZlj/ZIbNi7Lxxr12obT7cL1moPfE4tg1LkX7LlLfC6DeX4l2ZEud1ukP9jNQyNnfzQVqwbwmAATY4Q=="], "intl-messageformat": ["intl-messageformat@10.7.16", "", { "dependencies": { "@formatjs/ecma402-abstract": "2.3.4", "@formatjs/fast-memoize": "2.2.7", "@formatjs/icu-messageformat-parser": "2.11.2", "tslib": "^2.8.0" } }, "sha512-UmdmHUmp5CIKKjSoE10la5yfU+AYJAaiYLsodbjL4lji83JNvgOQUjGaGhGrpFCb0Uh7sl7qfP1IyILa8Z40ug=="], @@ -360,20 +600,64 @@ "is-reference": ["is-reference@3.0.3", "", { "dependencies": { "@types/estree": "^1.0.6" } }, "sha512-ixkJoqQvAP88E6wLydLGGqCJsrFUnqoH6HnaczB8XmDH1oaWU+xxdptvikTgaEhtZ53Ky6YXiBuUI2WXLMCwjw=="], + "is-stream": ["is-stream@2.0.1", "", {}, "sha512-hFoiJiTl63nn+kstHGBtewWSKnQLpyb155KHheA1l39uvtO9nWIop1p3udqPcUd/xbF1VLMO4n7OI6p7RbngDg=="], + "isexe": ["isexe@2.0.0", "", {}, "sha512-RHxMLp9lnKHGHRng9QFhRCMbYAcVpn69smSGcq3f36xjgVVWThj4qqLbTLlq7Ssj8B+fIQ1EuCEGI2lKsyQeIw=="], "jackspeak": ["jackspeak@3.4.3", "", { "dependencies": { "@isaacs/cliui": "^8.0.2" }, "optionalDependencies": { "@pkgjs/parseargs": "^0.11.0" } }, "sha512-OGlZQpz2yfahA/Rd1Y8Cd9SIEsqvXkLVoSw/cgwhnhFMDbsQFeZYoJJ7bIZBS9BcamUW96asq/npPWugM+RQBw=="], "jiti": ["jiti@1.21.7", "", { "bin": { "jiti": "bin/jiti.js" } }, "sha512-/imKNG4EbWNrVjoNC/1H5/9GFy+tqjGBHCaSsN+P2RnPqjsLmv6UD3Ej+Kj8nBWaRAwyk7kK5ZUc+OEatnTR3A=="], + "js-tiktoken": ["js-tiktoken@1.0.21", "", { "dependencies": { "base64-js": "^1.5.1" } }, "sha512-biOj/6M5qdgx5TKjDnFT1ymSpM5tbd3ylwDtrQvFQSu0Z7bBYko2dF+W/aUkXUPuk6IVpRxk/3Q2sHOzGlS36g=="], + + "json-schema-to-ts": ["json-schema-to-ts@3.1.1", "", { "dependencies": { "@babel/runtime": "^7.18.3", "ts-algebra": "^2.0.0" } }, "sha512-+DWg8jCJG2TEnpy7kOm/7/AxaYoaRbjVB4LFZLySZlWn8exGs3A4OLJR966cVvU26N7X9TWxl+Jsw7dzAqKT6g=="], + + "jsonwebtoken": ["jsonwebtoken@9.0.3", "", { "dependencies": { "jws": "^4.0.1", "lodash.includes": "^4.3.0", "lodash.isboolean": "^3.0.3", "lodash.isinteger": "^4.0.4", "lodash.isnumber": "^3.0.3", "lodash.isplainobject": "^4.0.6", "lodash.isstring": "^4.0.1", "lodash.once": "^4.0.0", "ms": "^2.1.1", "semver": "^7.5.4" } }, "sha512-MT/xP0CrubFRNLNKvxJ2BYfy53Zkm++5bX9dtuPbqAeQpTVe0MQTFhao8+Cp//EmJp244xt6Drw/GVEGCUj40g=="], + + "jwa": ["jwa@2.0.1", "", { "dependencies": { "buffer-equal-constant-time": "^1.0.1", "ecdsa-sig-formatter": "1.0.11", "safe-buffer": "^5.0.1" } }, "sha512-hRF04fqJIP8Abbkq5NKGN0Bbr3JxlQ+qhZufXVr0DvujKy93ZCbXZMHDL4EOtodSbCWxOqR8MS1tXA5hwqCXDg=="], + + "jws": ["jws@4.0.1", "", { "dependencies": { "jwa": "^2.0.1", "safe-buffer": "^5.0.1" } }, "sha512-EKI/M/yqPncGUUh44xz0PxSidXFr/+r0pA70+gIYhjv+et7yxM+s29Y+VGDkovRofQem0fs7Uvf4+YmAdyRduA=="], + + "jwt-decode": ["jwt-decode@4.0.0", "", {}, "sha512-+KJGIyHgkGuIq3IEBNftfhW/LfWhXUIY6OmyVWjliu5KH1y0fw7VQ8YndE2O4qZdMSd9SqbnC8GOcZEy0Om7sA=="], + "kleur": ["kleur@4.1.5", "", {}, "sha512-o+NO+8WrRiQEE4/7nwRJhN1HWpVmJm511pBHUxPLtp0BUISzlBplORYSmTclCnJvQq2tKu/sgl3xVpkc7ZWuQQ=="], + "kuler": ["kuler@2.0.0", "", {}, "sha512-Xq9nH7KlWZmXAtodXDDRE7vs6DU1gTU8zYDHDiWLSip45Egwq3plLHzPn27NgvzL2r1LMPC1vdqh98sQxtqj4A=="], + + "langchain": ["langchain@1.2.0", "", { "dependencies": { "@langchain/langgraph": "^1.0.0", "@langchain/langgraph-checkpoint": "^1.0.0", "langsmith": "~0.3.74", "uuid": "^10.0.0", "zod": "^3.25.76 || ^4" }, "peerDependencies": { "@langchain/core": "1.1.5" } }, "sha512-HC+5zN1RPenV/QU9pbo4V0Hv7R8rP4ZBXnnqhkBrSYqfvhcQ644dZQIcB3vryjqLhi82xZE2oNSplQLjnhX6xw=="], + + "langfuse": ["langfuse@3.38.6", "", { "dependencies": { "langfuse-core": "^3.38.6" } }, "sha512-mtwfsNGIYvObRh+NYNGlJQJDiBN+Wr3Hnr++wN25mxuOpSTdXX+JQqVCyAqGL5GD2TAXRZ7COsN42Vmp9krYmg=="], + + "langfuse-core": ["langfuse-core@3.38.6", "", { "dependencies": { "mustache": "^4.2.0" } }, "sha512-EcZXa+DK9FJdi1I30+u19eKjuBJ04du6j2Nybk19KKCuraLczg/ppkTQcGvc4QOk//OAi3qUHrajUuV74RXsBQ=="], + + "langsmith": ["langsmith@0.3.87", "", { "dependencies": { "@types/uuid": "^10.0.0", "chalk": "^4.1.2", "console-table-printer": "^2.12.1", "p-queue": "^6.6.2", "semver": "^7.6.3", "uuid": "^10.0.0" }, "peerDependencies": { "@opentelemetry/api": "*", "@opentelemetry/exporter-trace-otlp-proto": "*", "@opentelemetry/sdk-trace-base": "*", "openai": "*" }, "optionalPeers": ["@opentelemetry/api", "@opentelemetry/exporter-trace-otlp-proto", "@opentelemetry/sdk-trace-base", "openai"] }, "sha512-XXR1+9INH8YX96FKWc5tie0QixWz6tOqAsAKfcJyPkE0xPep+NDz0IQLR32q4bn10QK3LqD2HN6T3n6z1YLW7Q=="], + "lilconfig": ["lilconfig@3.1.3", "", {}, "sha512-/vlFKAoH5Cgt3Ie+JLhRbwOsCQePABiU3tJ1egGvyQ+33R/vcwM2Zl2QR/LzjsBeItPt3oSVXapn+m4nQDvpzw=="], "lines-and-columns": ["lines-and-columns@1.2.4", "", {}, "sha512-7ylylesZQ/PV29jhEDl3Ufjo6ZX7gCqJr5F7PKrqc93v7fzSymt1BpwEU8nAUXs8qzzvqhbjhK5QZg6Mt/HkBg=="], "locate-character": ["locate-character@3.0.0", "", {}, "sha512-SW13ws7BjaeJ6p7Q6CO2nchbYEc3X3J6WrmTTDto7yMPqVSZTUyY5Tjbid+Ab8gLnATtygYtiDIJGQRRn2ZOiA=="], + "lodash.camelcase": ["lodash.camelcase@4.3.0", "", {}, "sha512-TwuEnCnxbc3rAvhf/LbG7tJUDzhqXyFnv3dtzLOPgCG/hODL7WFnsbwktkD7yUV0RrreP/l1PALq/YSg6VvjlA=="], + + "lodash.includes": ["lodash.includes@4.3.0", "", {}, "sha512-W3Bx6mdkRTGtlJISOvVD/lbqjTlPPUDTMnlXZFnVwi9NKJ6tiAk6LVdlhZMm17VZisqhKcgzpO5Wz91PCt5b0w=="], + + "lodash.isboolean": ["lodash.isboolean@3.0.3", "", {}, "sha512-Bz5mupy2SVbPHURB98VAcw+aHh4vRV5IPNhILUCsOzRmsTmSQ17jIuqopAentWoehktxGd9e/hbIXq980/1QJg=="], + + "lodash.isinteger": ["lodash.isinteger@4.0.4", "", {}, "sha512-DBwtEWN2caHQ9/imiNeEA5ys1JoRtRfY3d7V9wkqtbycnAmTvRRmbHKDV4a0EYc678/dia0jrte4tjYwVBaZUA=="], + + "lodash.isnumber": ["lodash.isnumber@3.0.3", "", {}, "sha512-QYqzpfwO3/CWf3XP+Z+tkQsfaLL/EnUlXWVkIk5FUPc4sBdTehEqZONuyRt2P67PXAk+NXmTBcc97zw9t1FQrw=="], + + "lodash.isplainobject": ["lodash.isplainobject@4.0.6", "", {}, "sha512-oSXzaWypCMHkPC3NvBEaPHf0KsA5mvPrOPgQWDsbg8n7orZ290M0BmC/jgRZ4vcJ6DTAhjrsSYgdsW/F+MFOBA=="], + + "lodash.isstring": ["lodash.isstring@4.0.1", "", {}, "sha512-0wJxfxH1wgO3GrbuP+dTTk7op+6L41QCXbGINEmD+ny/G/eCqGzxyCsh7159S+mgDDcoarnBw6PC1PS5+wUGgw=="], + + "lodash.once": ["lodash.once@4.1.1", "", {}, "sha512-Sb487aTOCr9drQVL8pIxOzVhafOjZN9UU54hiN8PU3uAiSV7lx1yYNpbNmex2PK6dSJoNTSJUUswT651yww3Mg=="], + + "logform": ["logform@2.7.0", "", { "dependencies": { "@colors/colors": "1.6.0", "@types/triple-beam": "^1.3.2", "fecha": "^4.2.0", "ms": "^2.1.1", "safe-stable-stringify": "^2.3.1", "triple-beam": "^1.3.0" } }, "sha512-TFYA4jnP7PVbmlBIfhlSe+WKxs9dklXMTEGcBCIvLhE/Tn3H6Gk1norupVW7m5Cnd4bLcr08AytbyV/xj7f/kQ=="], + + "long": ["long@5.3.2", "", {}, "sha512-mNAgZ1GmyNhD7AuqnTG3/VQ26o760+ZYBPKjPvugO8+nLbYfX6TVpJPseBvopbdY+qpZ/lKUnmEc1LeZYS3QAA=="], + "lru-cache": ["lru-cache@10.4.3", "", {}, "sha512-JNAzZcXrCt42VGLuYz0zfAzDfAvJWW6AfYlDBQyDV5DClI2m5sAmK+OIO7s59XfsRsWHp02jAJrRadPRGTt6SQ=="], "lru-queue": ["lru-queue@0.1.0", "", { "dependencies": { "es5-ext": "~0.10.2" } }, "sha512-BpdYkt9EvGl8OfWHDQPISVpcl5xZthb+XPsbELj5AQXxIC8IriDZIQYjBJPEm5rS420sjZ0TLEzRcq5KdBhYrQ=="], @@ -382,30 +666,40 @@ "magic-string": ["magic-string@0.30.17", "", { "dependencies": { "@jridgewell/sourcemap-codec": "^1.5.0" } }, "sha512-sNPKHvyjVf7gyjwS4xGTaW/mCnF8wnjtifKBEhxfZ7E/S8tQ0rssrwGNn6q8JH/ohItJfSQp9mBtQYuTlH5QnA=="], + "math-intrinsics": ["math-intrinsics@1.1.0", "", {}, "sha512-/IXtbwEk5HTPyEwyKX6hGkYXxM9nbj64B+ilVJnC/R6B0pH5G4V3b0pVbL7DBj4tkhBAppbQUlf6F6Xl9LHu1g=="], + "memoizee": ["memoizee@0.4.17", "", { "dependencies": { "d": "^1.0.2", "es5-ext": "^0.10.64", "es6-weak-map": "^2.0.3", "event-emitter": "^0.3.5", "is-promise": "^2.2.2", "lru-queue": "^0.1.0", "next-tick": "^1.1.0", "timers-ext": "^0.1.7" } }, "sha512-DGqD7Hjpi/1or4F/aYAspXKNm5Yili0QDAFAY4QYvpqpgiY6+1jOfqpmByzjxbWd/T9mChbCArXAbDAsTm5oXA=="], "merge2": ["merge2@1.4.1", "", {}, "sha512-8q7VEgMJW4J8tcfVPy8g09NcQwZdbwFEqhe/WZkoIzjn/3TGDwtOCYtXGxA3O8tPzpczCCDgv+P2P5y00ZJOOg=="], "micromatch": ["micromatch@4.0.8", "", { "dependencies": { "braces": "^3.0.3", "picomatch": "^2.3.1" } }, "sha512-PXwfBhYu0hBCPw8Dn0E+WDYb7af3dSLVWKi3HGv84IdF4TyFoC0ysxFd0Goxw7nSv4T/PzEJQxsYsEiFCKo2BA=="], + "mime-db": ["mime-db@1.52.0", "", {}, "sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg=="], + + "mime-types": ["mime-types@2.1.35", "", { "dependencies": { "mime-db": "1.52.0" } }, "sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw=="], + "minimatch": ["minimatch@9.0.5", "", { "dependencies": { "brace-expansion": "^2.0.1" } }, "sha512-G6T0ZX48xgozx7587koeX9Ys2NYy6Gmv//P89sEte9V9whIapMNF4idKxnW2QtCcLiTWlb/wfCabAtAFWhhBow=="], "minipass": ["minipass@7.1.2", "", {}, "sha512-qOOzS1cBTWYF4BH8fVePDBOO9iptMnGUEZwNc/cMWnTV2nVLZ7VoNWEPHkYczZA0pdoA7dl6e7FL659nX9S2aw=="], - "moment": ["moment@2.29.4", "", {}, "sha512-5LC9SOxjSc2HF6vO2CyuTDNivEdoz2IvyJJGj6X8DJ0eFyfszE0QiEd+iXmBvUP3WHxSjFH/vIsA0EN00cgr8w=="], + "module-details-from-path": ["module-details-from-path@1.0.4", "", {}, "sha512-EGWKgxALGMgzvxYF1UyGTy0HXX/2vHLkw6+NvDKW2jypWbHpjQuj4UMcqQWXHERJhVGKikolT06G3bcKe4fi7w=="], - "monkey-around": ["monkey-around@3.0.0", "", {}, "sha512-jL6uY2lEAoaHxZep1cNRkCZjoIWY4g5VYCjriEWmcyHU7w8NU1+JH57xE251UVTohK0lCxMjv0ZV4ByDLIXEpw=="], + "moment": ["moment@2.29.4", "", {}, "sha512-5LC9SOxjSc2HF6vO2CyuTDNivEdoz2IvyJJGj6X8DJ0eFyfszE0QiEd+iXmBvUP3WHxSjFH/vIsA0EN00cgr8w=="], "mri": ["mri@1.2.0", "", {}, "sha512-tzzskb3bG8LvYGFF/mDTpq3jpI6Q9wc3LEmBaghu+DdCssd1FakN7Bc0hVNmEyGq1bq3RgfkCb3cmQLpNPOroA=="], "ms": ["ms@2.1.3", "", {}, "sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA=="], + "mustache": ["mustache@4.2.0", "", { "bin": { "mustache": "bin/mustache" } }, "sha512-71ippSywq5Yb7/tVYyGbkBggbU8H3u5Rz56fH60jGFgr8uHwxs+aSKeqmluIVzM0m0kB7xQjKS6qPfd0b2ZoqQ=="], + "mz": ["mz@2.7.0", "", { "dependencies": { "any-promise": "^1.0.0", "object-assign": "^4.0.1", "thenify-all": "^1.0.0" } }, "sha512-z81GNO7nnYMEhrGh9LeymoE4+Yr0Wn5McHIZMK5cfQCl+NDX08sCZgUc9/6MHni9IWuFLm1Z3HTCXu2z9fN62Q=="], "nanoid": ["nanoid@3.3.11", "", { "bin": { "nanoid": "bin/nanoid.cjs" } }, "sha512-N8SpfPUnUp1bK+PMYW8qSWdl9U+wwNWI4QKxOYDy9JAro3WMX7p2OeVRF9v+347pnakNevPmiHhNmZ2HbFA76w=="], "next-tick": ["next-tick@1.1.0", "", {}, "sha512-CXdUiJembsNjuToQvxayPZF9Vqht7hewsvy2sOWafLvi2awflj9mOC6bHIg50orX8IJvWKY9wYQ/zB2kogPslQ=="], + "node-cache": ["node-cache@5.1.2", "", { "dependencies": { "clone": "2.x" } }, "sha512-t1QzWwnk4sjLWaQAS8CHgOJ+RAfmHpxFWmc36IWTiWHQfs0w5JDMBS1b1ZxQteo0vVVuWJvIUKHDkkeK7vIGCg=="], + "node-releases": ["node-releases@2.0.19", "", {}, "sha512-xxOWJsBKtzAq7DY0J+DTzuz58K8e7sJbdgwkbMWQe8UYB6ekmsQ45q0M/tJDsGaZmbC+l7n57UV8Hl5tHxO9uw=="], "normalize-path": ["normalize-path@3.0.0", "", {}, "sha512-6eZs5Ls3WtCisHWp9S2GUy8dqkpGi4BVSz3GaqiE6ezub0512ESztXUwUB6C6IKbQkY2Pnb/mD4WYojCRwcwLA=="], @@ -418,9 +712,25 @@ "obsidian": ["obsidian@1.10.0", "", { "dependencies": { "@types/codemirror": "5.60.8", "moment": "2.29.4" }, "peerDependencies": { "@codemirror/state": "6.5.0", "@codemirror/view": "6.38.1" } }, "sha512-F7hhnmGRQD1TanDPFT//LD3iKNUVd7N8sKL7flCCHRszfTxpDJ39j3T7LHbcGpyid906i6lD5oO+cnfLBzJMKw=="], + "ollama": ["ollama@0.6.3", "", { "dependencies": { "whatwg-fetch": "^3.6.20" } }, "sha512-KEWEhIqE5wtfzEIZbDCLH51VFZ6Z3ZSa6sIOg/E/tBV8S51flyqBOXi+bRxlOYKDf8i327zG9eSTb8IJxvm3Zg=="], + + "one-time": ["one-time@1.0.0", "", { "dependencies": { "fn.name": "1.x.x" } }, "sha512-5DXOiRKwuSEcQ/l0kGCF6Q3jcADFv5tSmRaJck/OqkVFcOzutB134KRSfF0xDrL39MNnqxbHBbUUcjZIhTgb2g=="], + + "openai": ["openai@6.13.0", "", { "peerDependencies": { "ws": "^8.18.0", "zod": "^3.25 || ^4.0" }, "optionalPeers": ["ws", "zod"], "bin": { "openai": "bin/cli" } }, "sha512-yHbMo+EpNGPG3sRrXvmo0LhUPFN4bAURJw3G17bE+ax1G4tcTFCa9ZjvCWh3cvni0aHY0uWlk2IxcsPH4NR9Ow=="], + + "opossum": ["opossum@9.0.0", "", {}, "sha512-K76U0QkxOfUZamneQuzz+AP0fyfTJcCplZ2oZL93nxeupuJbN4s6uFNbmVCt4eWqqGqRnnowdFuBicJ1fLMVxw=="], + + "p-finally": ["p-finally@1.0.0", "", {}, "sha512-LICb2p9CB7FS+0eR1oqWnHhp0FljGLZCWBE9aix0Uye9W8LTQPwMTYVGWQWIw9RdQiDg4+epXQODwIYJtSJaow=="], + + "p-queue": ["p-queue@6.6.2", "", { "dependencies": { "eventemitter3": "^4.0.4", "p-timeout": "^3.2.0" } }, "sha512-RwFpb72c/BhQLEXIZ5K2e+AhgNVmIejGlTgiB9MzZ0e93GRvqZ7uSi0dvRF7/XIXDeNkra2fNHBxTyPDGySpjQ=="], + + "p-retry": ["p-retry@4.6.2", "", { "dependencies": { "@types/retry": "0.12.0", "retry": "^0.13.1" } }, "sha512-312Id396EbJdvRONlngUx0NydfrIQ5lsYu0znKVUzVvArzEIt08V1qhtyESbGVd1FGX7UKtiFp5uwKZdM8wIuQ=="], + + "p-timeout": ["p-timeout@3.2.0", "", { "dependencies": { "p-finally": "^1.0.0" } }, "sha512-rhIwUycgwwKcP9yTOOFK/AKsAopjjCakVqLHePO3CC6Mir1Z99xT+R63jZxAT5lFZLa2inS5h+ZS2GvR99/FBg=="], + "package-json-from-dist": ["package-json-from-dist@1.0.1", "", {}, "sha512-UEZIS3/by4OC8vL3P2dTXRETpebLI2NiI5vIrjaD/5UtrkFX/tNbwjTSRAGC/+7CAo2pIcBaRgWmcBBHcsaCIw=="], - "papa-ts": ["papa-ts@link:papa-ts", {}], + "papa-ts": ["papa-ts@2.7.4", "", { "dependencies": { "@langchain/anthropic": "^1.1.0", "@langchain/core": "^1.0.2", "@langchain/langgraph": "^1.0.1", "@langchain/ollama": "^1.0.1", "@langchain/openai": "^1.1.2", "@langfuse/langchain": "^4.4.0", "@langfuse/otel": "^4.4.2", "@opentelemetry/sdk-node": "^0.208.0", "@sap-ai-sdk/langchain": "^2.3.0", "dotenv": "^17.2.3", "langchain": "^1.0.2", "langfuse": "^3.38.6", "langsmith": "^0.3.79", "zod": "^4.1.12" } }, "sha512-sNjlhtuludtBGHqW5efYAprE2UgABI7zWP6Y/HCOtvrfLWDyDlBRDNYv+2QF8bR+c6H5Fdk5UPgCCERnTRnE6g=="], "path-key": ["path-key@3.1.1", "", {}, "sha512-ojmeN0qd+y0jszEtoY48r0Peq5dwMEkIlCOu6Q5f41lfkswXuKtYrhgoTpLnyIcHm24Uhqx+5Tqm2InSwLhE6Q=="], @@ -430,7 +740,7 @@ "picocolors": ["picocolors@1.1.1", "", {}, "sha512-xceH2snhtb5M9liqDsmEw56le376mTZkEX/jEb/RxNFyegNul7eNslCXP9FDj/Lcu0X8KEyMceP2ntpaHrDEVA=="], - "picomatch": ["picomatch@4.0.2", "", {}, "sha512-M7BAV6Rlcy5u+m6oPhAPFgJTzAioX/6B0DxyvDlo9l8+T3nLKbrczg2WLUyzd45L8RqfUMyGPzekbMvX2Ldkwg=="], + "picomatch": ["picomatch@4.0.3", "", {}, "sha512-5gTmgEY/sqK6gFXLIsQNH19lWb4ebPDLA4SdLP7dsWkIXHWlG66oPuVvXSGFPppYZz8ZDZq0dYYrbHfBCVUb1Q=="], "pify": ["pify@2.3.0", "", {}, "sha512-udgsAY+fTnvv7kI7aaxbqwWNb0AHiB0qBO89PZKPkoTmGOgdbrHDKD+0B2X4uTfJ/FT1R09r9gTsjUjNJotuog=="], @@ -450,17 +760,29 @@ "postcss-value-parser": ["postcss-value-parser@4.2.0", "", {}, "sha512-1NNCs6uurfkVbeXG4S8JFT9t19m45ICnif8zWLd5oPSZ50QnwMfK+H3jv408d4jw/7Bttv5axS5IiHoLaVNHeQ=="], + "protobufjs": ["protobufjs@7.5.4", "", { "dependencies": { "@protobufjs/aspromise": "^1.1.2", "@protobufjs/base64": "^1.1.2", "@protobufjs/codegen": "^2.0.4", "@protobufjs/eventemitter": "^1.1.0", "@protobufjs/fetch": "^1.1.0", "@protobufjs/float": "^1.0.2", "@protobufjs/inquire": "^1.1.0", "@protobufjs/path": "^1.1.2", "@protobufjs/pool": "^1.1.0", "@protobufjs/utf8": "^1.1.0", "@types/node": ">=13.7.0", "long": "^5.0.0" } }, "sha512-CvexbZtbov6jW2eXAvLukXjXUW1TzFaivC46BpWc/3BpcCysb5Vffu+B3XHMm8lVEuy2Mm4XGex8hBSg1yapPg=="], + + "proxy-from-env": ["proxy-from-env@1.1.0", "", {}, "sha512-D+zkORCbA9f1tdWRK0RaCR3GPv50cMxcrz4X8k5LTSUD1Dkw47mKJEZQNunItRTkWwgtaUSo1RVFRIG9ZXiFYg=="], + "queue-microtask": ["queue-microtask@1.2.3", "", {}, "sha512-NuaNSa6flKT5JaSYQzJok04JzTL1CA6aGhv5rfLW3PgqA+M2ChpZQnAC8h8i4ZFkBS8X5RqkDBHA7r4hej3K9A=="], "read-cache": ["read-cache@1.0.0", "", { "dependencies": { "pify": "^2.3.0" } }, "sha512-Owdv/Ft7IjOgm/i0xvNDZ1LrRANRfew4b2prF3OWMQLxLfu3bS8FVhCsrSCMK4lR56Y9ya+AThoTpDCTxCmpRA=="], + "readable-stream": ["readable-stream@3.6.2", "", { "dependencies": { "inherits": "^2.0.3", "string_decoder": "^1.1.1", "util-deprecate": "^1.0.1" } }, "sha512-9u/sniCrY3D5WdsERHzHE4G2YCXqoG5FTHUiCC4SIbr6XcLZBY05ya9EKjYek9O5xOAwjGq+1JdGBAS7Q9ScoA=="], + "readdirp": ["readdirp@4.1.2", "", {}, "sha512-GDhwkLfywWL2s6vEjyhri+eXmfH6j1L7JE27WhqLeYzoh/A3DBaYGEj2H/HFZCn/kMfim73FXxEJTw06WtxQwg=="], + "require-directory": ["require-directory@2.1.1", "", {}, "sha512-fGxEI7+wsG9xrvdjsrlmL22OMTTiHRwAMroiEeMgq8gzoLC/PQr7RsRDSTLUg/bZAZtF+TVIkHc6/4RIKrui+Q=="], + + "require-in-the-middle": ["require-in-the-middle@8.0.1", "", { "dependencies": { "debug": "^4.3.5", "module-details-from-path": "^1.0.3" } }, "sha512-QT7FVMXfWOYFbeRBF6nu+I6tr2Tf3u0q8RIEjNob/heKY/nh7drD/k7eeMFmSQgnTtCzLDcCu/XEnpW2wk4xCQ=="], + "resolve": ["resolve@1.22.10", "", { "dependencies": { "is-core-module": "^2.16.0", "path-parse": "^1.0.7", "supports-preserve-symlinks-flag": "^1.0.0" }, "bin": { "resolve": "bin/resolve" } }, "sha512-NPRy+/ncIMeDlTAsuqwKIiferiawhefFJtkNSW0qZJEqMEb+qBt/77B/jGeeek+F0uOeN05CDa6HXbbIgtVX4w=="], + "retry": ["retry@0.13.1", "", {}, "sha512-XQBQ3I8W1Cge0Seh+6gjj03LbmRFWuoszgK9ooCpwYIrhhoO80pfq4cUkU5DkknwfOfFteRwlZ56PYOGYyFWdg=="], + "reusify": ["reusify@1.1.0", "", {}, "sha512-g6QUff04oZpHs0eG5p83rFLhHeV00ug/Yf9nZM6fLeUrPguBTkTQOdpAWWspMh55TZfVQDPaN3NQJfbVRAxdIw=="], - "rollup": ["rollup@4.41.1", "", { "dependencies": { "@types/estree": "1.0.7" }, "optionalDependencies": { "@rollup/rollup-android-arm-eabi": "4.41.1", "@rollup/rollup-android-arm64": "4.41.1", "@rollup/rollup-darwin-arm64": "4.41.1", "@rollup/rollup-darwin-x64": "4.41.1", "@rollup/rollup-freebsd-arm64": "4.41.1", "@rollup/rollup-freebsd-x64": "4.41.1", "@rollup/rollup-linux-arm-gnueabihf": "4.41.1", "@rollup/rollup-linux-arm-musleabihf": "4.41.1", "@rollup/rollup-linux-arm64-gnu": "4.41.1", "@rollup/rollup-linux-arm64-musl": "4.41.1", "@rollup/rollup-linux-loongarch64-gnu": "4.41.1", "@rollup/rollup-linux-powerpc64le-gnu": "4.41.1", "@rollup/rollup-linux-riscv64-gnu": "4.41.1", "@rollup/rollup-linux-riscv64-musl": "4.41.1", "@rollup/rollup-linux-s390x-gnu": "4.41.1", "@rollup/rollup-linux-x64-gnu": "4.41.1", "@rollup/rollup-linux-x64-musl": "4.41.1", "@rollup/rollup-win32-arm64-msvc": "4.41.1", "@rollup/rollup-win32-ia32-msvc": "4.41.1", "@rollup/rollup-win32-x64-msvc": "4.41.1", "fsevents": "~2.3.2" }, "bin": { "rollup": "dist/bin/rollup" } }, "sha512-cPmwD3FnFv8rKMBc1MxWCwVQFxwf1JEmSX3iQXrRVVG15zerAIXRjMFVWnd5Q5QvgKF7Aj+5ykXFhUl+QGnyOw=="], + "rollup": ["rollup@4.53.3", "", { "dependencies": { "@types/estree": "1.0.8" }, "optionalDependencies": { "@rollup/rollup-android-arm-eabi": "4.53.3", "@rollup/rollup-android-arm64": "4.53.3", "@rollup/rollup-darwin-arm64": "4.53.3", "@rollup/rollup-darwin-x64": "4.53.3", "@rollup/rollup-freebsd-arm64": "4.53.3", "@rollup/rollup-freebsd-x64": "4.53.3", "@rollup/rollup-linux-arm-gnueabihf": "4.53.3", "@rollup/rollup-linux-arm-musleabihf": "4.53.3", "@rollup/rollup-linux-arm64-gnu": "4.53.3", "@rollup/rollup-linux-arm64-musl": "4.53.3", "@rollup/rollup-linux-loong64-gnu": "4.53.3", "@rollup/rollup-linux-ppc64-gnu": "4.53.3", "@rollup/rollup-linux-riscv64-gnu": "4.53.3", "@rollup/rollup-linux-riscv64-musl": "4.53.3", "@rollup/rollup-linux-s390x-gnu": "4.53.3", "@rollup/rollup-linux-x64-gnu": "4.53.3", "@rollup/rollup-linux-x64-musl": "4.53.3", "@rollup/rollup-openharmony-arm64": "4.53.3", "@rollup/rollup-win32-arm64-msvc": "4.53.3", "@rollup/rollup-win32-ia32-msvc": "4.53.3", "@rollup/rollup-win32-x64-gnu": "4.53.3", "@rollup/rollup-win32-x64-msvc": "4.53.3", "fsevents": "~2.3.2" }, "bin": { "rollup": "dist/bin/rollup" } }, "sha512-w8GmOxZfBmKknvdXU1sdM9NHcoQejwF/4mNgj2JuEEdRaHwwF12K7e9eXn1nLZ07ad+du76mkVsyeb2rKGllsA=="], "run-parallel": ["run-parallel@1.2.0", "", { "dependencies": { "queue-microtask": "^1.2.2" } }, "sha512-5l4VyZR86LZ/lDxZTR6jqL8AFE2S0IFLMP26AbjsLVADxHdhB/c0GUsH+y39UfCi3dzz8OlQuPmnaJOMoDHQBA=="], @@ -468,18 +790,30 @@ "sade": ["sade@1.8.1", "", { "dependencies": { "mri": "^1.1.0" } }, "sha512-xal3CZX1Xlo/k4ApwCFrHVACi9fBqJ7V+mwhBsuf/1IOKbBy098Fex+Wa/5QMubw09pSZ/u8EY8PWgevJsXp1A=="], + "safe-buffer": ["safe-buffer@5.2.1", "", {}, "sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ=="], + + "safe-stable-stringify": ["safe-stable-stringify@2.5.0", "", {}, "sha512-b3rppTKm9T+PsVCBEOUR46GWI7fdOs00VKZ1+9c1EWDaDMvjQc6tUwuFyIprgGgTcWoVHSKrU8H31ZHA2e0RHA=="], + + "semver": ["semver@7.7.3", "", { "bin": { "semver": "bin/semver.js" } }, "sha512-SdsKMrI9TdgjdweUSR9MweHA4EJ8YxHn8DFaDisvhVlUOe4BF1tLD7GAj0lIqWVl+dPb/rExr0Btby5loQm20Q=="], + "shebang-command": ["shebang-command@2.0.0", "", { "dependencies": { "shebang-regex": "^3.0.0" } }, "sha512-kHxr2zZpYtdmrN1qDjrrX/Z1rR1kG8Dx+gkpK1G4eXmvXswmcE1hTWBWYUzlraYw1/yZp6YuDY77YtvbN0dmDA=="], "shebang-regex": ["shebang-regex@3.0.0", "", {}, "sha512-7++dFhtcx3353uBaq8DDR4NuxBetBzC7ZQOhmTQInHEd6bSrXdiEyzCvG07Z44UYdLShWUyXt5M/yhz8ekcb1A=="], "signal-exit": ["signal-exit@4.1.0", "", {}, "sha512-bzyZ1e88w9O1iNJbKnOlvYTrWPDl46O1bG0D3XInv+9tkPrxrN8jUUTiFlDkkmKWgn1M6CfIA13SuGqOa9Korw=="], + "simple-wcswidth": ["simple-wcswidth@1.1.2", "", {}, "sha512-j7piyCjAeTDSjzTSQ7DokZtMNwNlEAyxqSZeCS+CXH7fJ4jx3FuJ/mTW3mE+6JLs4VJBbcll0Kjn+KXI5t21Iw=="], + "source-map-js": ["source-map-js@1.2.1", "", {}, "sha512-UXWMKhLOwVKb728IUtQPXxfYU+usdybtUrK/8uGE8CQMvrhOpwvzDBwj0QhSL7MQc7vIsISBG8VQ8+IDQxpfQA=="], + "stack-trace": ["stack-trace@0.0.10", "", {}, "sha512-KGzahc7puUKkzyMt+IqAep+TVNbKP+k2Lmwhub39m1AsTSkaDutx56aDCo+HLDzf/D26BIHTJWNiTG1KAJiQCg=="], + "string-width": ["string-width@5.1.2", "", { "dependencies": { "eastasianwidth": "^0.2.0", "emoji-regex": "^9.2.2", "strip-ansi": "^7.0.1" } }, "sha512-HnLOCR3vjcY8beoNLtcjZ5/nxn2afmME6lhrDrebokqMap+XbeW8n9TXpPDOqdGK5qcI3oT0GKTW6wC7EMiVqA=="], "string-width-cjs": ["string-width@4.2.3", "", { "dependencies": { "emoji-regex": "^8.0.0", "is-fullwidth-code-point": "^3.0.0", "strip-ansi": "^6.0.1" } }, "sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g=="], + "string_decoder": ["string_decoder@1.3.0", "", { "dependencies": { "safe-buffer": "~5.2.0" } }, "sha512-hkRX8U1WjJFd8LsDJ2yQ/wWWxaopEsABU1XfkM8A+j0+85JAGppt16cr1Whg6KIbb4okU6Mql6BOj+uup/wKeA=="], + "strip-ansi": ["strip-ansi@7.1.0", "", { "dependencies": { "ansi-regex": "^6.0.1" } }, "sha512-iq6eVVI64nQQTRYq2KtEg2d2uU7LElhTJwsH4YzIHZshxlgZms/wIc4VoDQTlG/IvVIrBKG06CrZnp0qv7hkcQ=="], "strip-ansi-cjs": ["strip-ansi@6.0.1", "", { "dependencies": { "ansi-regex": "^5.0.1" } }, "sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A=="], @@ -490,6 +824,8 @@ "sucrase": ["sucrase@3.35.0", "", { "dependencies": { "@jridgewell/gen-mapping": "^0.3.2", "commander": "^4.0.0", "glob": "^10.3.10", "lines-and-columns": "^1.1.6", "mz": "^2.7.0", "pirates": "^4.0.1", "ts-interface-checker": "^0.1.9" }, "bin": { "sucrase": "bin/sucrase", "sucrase-node": "bin/sucrase-node" } }, "sha512-8EbVDiu9iN/nESwxeSxDKe0dunta1GOlHufmSSXxMD2z2/tMZpDMpvXQGsc+ajGo8y2uYUmixaSRUc/QPoQ0GA=="], + "supports-color": ["supports-color@7.2.0", "", { "dependencies": { "has-flag": "^4.0.0" } }, "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw=="], + "supports-preserve-symlinks-flag": ["supports-preserve-symlinks-flag@1.0.0", "", {}, "sha512-ot0WnXS9fgdkgIcePe6RHNk1WA8+muPa6cSjeR3V8K27q9BB1rTE3R1p7Hv0z1ZyAc8s6Vvv8DIyWf681MAt0w=="], "svelte": ["svelte@5.41.0", "", { "dependencies": { "@jridgewell/remapping": "^2.3.4", "@jridgewell/sourcemap-codec": "^1.5.0", "@sveltejs/acorn-typescript": "^1.0.5", "@types/estree": "^1.0.5", "acorn": "^8.12.1", "aria-query": "^5.3.1", "axobject-query": "^4.1.0", "clsx": "^2.1.1", "esm-env": "^1.2.1", "esrap": "^2.1.0", "is-reference": "^3.0.3", "locate-character": "^3.0.0", "magic-string": "^0.30.11", "zimmerframe": "^1.1.2" } }, "sha512-mP3vFFv5OUM5JN189+nJVW74kQ1dGqUrXTEzvCEVZqessY0GxZDls1nWVvt4Sxyv2USfQvAZO68VRaeIZvpzKg=="], @@ -504,6 +840,8 @@ "tailwindcss": ["tailwindcss@3.4.18", "", { "dependencies": { "@alloc/quick-lru": "^5.2.0", "arg": "^5.0.2", "chokidar": "^3.6.0", "didyoumean": "^1.2.2", "dlv": "^1.1.3", "fast-glob": "^3.3.2", "glob-parent": "^6.0.2", "is-glob": "^4.0.3", "jiti": "^1.21.7", "lilconfig": "^3.1.3", "micromatch": "^4.0.8", "normalize-path": "^3.0.0", "object-hash": "^3.0.0", "picocolors": "^1.1.1", "postcss": "^8.4.47", "postcss-import": "^15.1.0", "postcss-js": "^4.0.1", "postcss-load-config": "^4.0.2 || ^5.0 || ^6.0", "postcss-nested": "^6.2.0", "postcss-selector-parser": "^6.1.2", "resolve": "^1.22.8", "sucrase": "^3.35.0" }, "bin": { "tailwind": "lib/cli.js", "tailwindcss": "lib/cli.js" } }, "sha512-6A2rnmW5xZMdw11LYjhcI5846rt9pbLSabY5XPxo+XWdxwZaFEn47Go4NzFiHu9sNNmr/kXivP1vStfvMaK1GQ=="], + "text-hex": ["text-hex@1.0.0", "", {}, "sha512-uuVGNWzgJ4yhRaNSiubPY7OjISw4sw4E5Uv0wbjp+OzcbmVU/rsT8ujgcXJhn9ypzsgr5vlzpPqP+MBBKcGvbg=="], + "thenify": ["thenify@3.3.1", "", { "dependencies": { "any-promise": "^1.0.0" } }, "sha512-RVZSIV5IG10Hk3enotrhvz0T9em6cyHBLkH/YAZuKqd8hRkKhSfCGIcP2KUY0EPxndzANBmNllzWPwak+bheSw=="], "thenify-all": ["thenify-all@1.6.0", "", { "dependencies": { "thenify": ">= 3.1.0 < 4" } }, "sha512-RNxQH/qI8/t3thXJDwcstUO4zeqo64+Uy/+sNVRBx4Xn2OX+OZ9oP+iJnNFqplFra2ZUVeKCSa2oVWi3T4uVmA=="], @@ -512,10 +850,14 @@ "tiny-glob": ["tiny-glob@0.2.9", "", { "dependencies": { "globalyzer": "0.1.0", "globrex": "^0.1.2" } }, "sha512-g/55ssRPUjShh+xkfx9UPDXqhckHEsHr4Vd9zX55oSdGZc/MD0m3sferOkwWtp98bv+kcVfEHtRJgBVJzelrzg=="], - "tinyglobby": ["tinyglobby@0.2.14", "", { "dependencies": { "fdir": "^6.4.4", "picomatch": "^4.0.2" } }, "sha512-tX5e7OM1HnYr2+a2C/4V0htOcSQcoSTH9KgJnVvNm5zm/cyEWKJ7j7YutsH9CxMdtOkkLFy2AHrMci9IM8IPZQ=="], + "tinyglobby": ["tinyglobby@0.2.15", "", { "dependencies": { "fdir": "^6.5.0", "picomatch": "^4.0.3" } }, "sha512-j2Zq4NyQYG5XMST4cbs02Ak8iJUdxRM0XI5QyxXuZOzKOINmWurp3smXu3y5wDcJrptwpSjgXHzIQxR0omXljQ=="], "to-regex-range": ["to-regex-range@5.0.1", "", { "dependencies": { "is-number": "^7.0.0" } }, "sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ=="], + "triple-beam": ["triple-beam@1.4.1", "", {}, "sha512-aZbgViZrg1QNcG+LULa7nhZpJTZSLm/mXnHXnbAbjmN5aSa0y7V+wvv6+4WaBtpISJzThKy+PIPxc1Nq1EJ9mg=="], + + "ts-algebra": ["ts-algebra@2.0.0", "", {}, "sha512-FPAhNPFMrkwz76P7cdjdmiShwMynZYN6SgOujD1urY4oNm80Ou9oMdmbR45LotcKOXoy7wSmHkRFE6Mxbrhefw=="], + "ts-interface-checker": ["ts-interface-checker@0.1.13", "", {}, "sha512-Y/arvbn+rrz3JCKl9C4kVNfTfSm2/mEp5FSz5EsZSANGPSlQrpRI5M4PKF+mJnE52jOO90PnPSc3Ur3bTQw0gA=="], "tslib": ["tslib@2.8.1", "", {}, "sha512-oJFu94HQb+KVduSUQL7wnpmqnfmLsOA/nAh6b6EH0wCEoK0/mPeXU6c3wKDV83MkOuHPRHtSXKKU99IBazS/2w=="], @@ -524,35 +866,85 @@ "typescript": ["typescript@5.9.3", "", { "bin": { "tsc": "bin/tsc", "tsserver": "bin/tsserver" } }, "sha512-jl1vZzPDinLr9eUt3J/t7V6FgNEw9QjvBPdysz9KfQDD41fQrC2Y4vKQdiaUpFT4bXlb1RHhLpp8wtm6M5TgSw=="], + "undici-types": ["undici-types@7.16.0", "", {}, "sha512-Zz+aZWSj8LE6zoxD+xrjh4VfkIG8Ya6LvYkZqtUQGJPZjYl53ypCaUwWqo7eI0x66KBGeRo+mlBEkMSeSZ38Nw=="], + "update-browserslist-db": ["update-browserslist-db@1.1.3", "", { "dependencies": { "escalade": "^3.2.0", "picocolors": "^1.1.1" }, "peerDependencies": { "browserslist": ">= 4.21.0" }, "bin": { "update-browserslist-db": "cli.js" } }, "sha512-UxhIZQ+QInVdunkDAaiazvvT/+fXL5Osr0JZlJulepYu6Jd7qJtDZjlur0emRlT71EN3ScPoE7gvsuIKKNavKw=="], "util-deprecate": ["util-deprecate@1.0.2", "", {}, "sha512-EPD5q1uXyFxJpCrLnCc1nHnq3gOa6DZBocAIiI2TaSCA7VCJ1UJDMagCzIkXNsUYfD1daK//LTEQ8xiIbrHtcw=="], "uuid": ["uuid@11.1.0", "", { "bin": { "uuid": "dist/esm/bin/uuid" } }, "sha512-0/A9rDy9P7cJ+8w1c9WD9V//9Wj15Ce2MPz8Ri6032usz+NfePxx5AcN3bN+r6ZL6jEo066/yNYB3tn4pQEx+A=="], - "vite": ["vite@6.4.0", "", { "dependencies": { "esbuild": "^0.25.0", "fdir": "^6.4.4", "picomatch": "^4.0.2", "postcss": "^8.5.3", "rollup": "^4.34.9", "tinyglobby": "^0.2.13" }, "optionalDependencies": { "fsevents": "~2.3.3" }, "peerDependencies": { "@types/node": "^18.0.0 || ^20.0.0 || >=22.0.0", "jiti": ">=1.21.0", "less": "*", "lightningcss": "^1.21.0", "sass": "*", "sass-embedded": "*", "stylus": "*", "sugarss": "*", "terser": "^5.16.0", "tsx": "^4.8.1", "yaml": "^2.4.2" }, "optionalPeers": ["@types/node", "jiti", "less", "lightningcss", "sass", "sass-embedded", "stylus", "sugarss", "terser", "tsx", "yaml"], "bin": { "vite": "bin/vite.js" } }, "sha512-oLnWs9Hak/LOlKjeSpOwD6JMks8BeICEdYMJBf6P4Lac/pO9tKiv/XhXnAM7nNfSkZahjlCZu9sS50zL8fSnsw=="], + "verror": ["verror@1.10.1", "", { "dependencies": { "assert-plus": "^1.0.0", "core-util-is": "1.0.2", "extsprintf": "^1.2.0" } }, "sha512-veufcmxri4e3XSrT0xwfUR7kguIkaxBeosDg00yDWhk49wdwkSUrvvsm7nc75e1PUyvIeZj6nS8VQRYz2/S4Xg=="], + + "vite": ["vite@7.2.7", "", { "dependencies": { "esbuild": "^0.25.0", "fdir": "^6.5.0", "picomatch": "^4.0.3", "postcss": "^8.5.6", "rollup": "^4.43.0", "tinyglobby": "^0.2.15" }, "optionalDependencies": { "fsevents": "~2.3.3" }, "peerDependencies": { "@types/node": "^20.19.0 || >=22.12.0", "jiti": ">=1.21.0", "less": "^4.0.0", "lightningcss": "^1.21.0", "sass": "^1.70.0", "sass-embedded": "^1.70.0", "stylus": ">=0.54.8", "sugarss": "^5.0.0", "terser": "^5.16.0", "tsx": "^4.8.1", "yaml": "^2.4.2" }, "optionalPeers": ["@types/node", "jiti", "less", "lightningcss", "sass", "sass-embedded", "stylus", "sugarss", "terser", "tsx", "yaml"], "bin": { "vite": "bin/vite.js" } }, "sha512-ITcnkFeR3+fI8P1wMgItjGrR10170d8auB4EpMLPqmx6uxElH3a/hHGQabSHKdqd4FXWO1nFIp9rRn7JQ34ACQ=="], "vitefu": ["vitefu@1.0.6", "", { "peerDependencies": { "vite": "^3.0.0 || ^4.0.0 || ^5.0.0 || ^6.0.0" }, "optionalPeers": ["vite"] }, "sha512-+Rex1GlappUyNN6UfwbVZne/9cYC4+R2XDk9xkNXBKMw6HQagdX9PgZ8V2v1WUSK1wfBLp7qbI1+XSNIlB1xmA=="], + "voca": ["voca@1.4.1", "", {}, "sha512-NJC/BzESaHT1p4B5k4JykxedeltmNbau4cummStd4RjFojgq/kLew5TzYge9N2geeWyI2w8T30wUET5v+F7ZHA=="], + "w3c-keyname": ["w3c-keyname@2.2.8", "", {}, "sha512-dpojBhNsCNN7T82Tm7k26A6G9ML3NkhDsnw9n/eoxSRlVBB4CEtIQ/KTCLI2Fwf3ataSXRhYFkQi3SlnFwPvPQ=="], + "whatwg-fetch": ["whatwg-fetch@3.6.20", "", {}, "sha512-EqhiFU6daOA8kpjOWTL0olhVOF3i7OrFzSYiGsEMB8GcXS+RrzauAERX65xMeNWVqxA6HXH2m69Z9LaKKdisfg=="], + "which": ["which@2.0.2", "", { "dependencies": { "isexe": "^2.0.0" }, "bin": { "node-which": "./bin/node-which" } }, "sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA=="], + "winston": ["winston@3.19.0", "", { "dependencies": { "@colors/colors": "^1.6.0", "@dabh/diagnostics": "^2.0.8", "async": "^3.2.3", "is-stream": "^2.0.0", "logform": "^2.7.0", "one-time": "^1.0.0", "readable-stream": "^3.4.0", "safe-stable-stringify": "^2.3.1", "stack-trace": "0.0.x", "triple-beam": "^1.3.0", "winston-transport": "^4.9.0" } }, "sha512-LZNJgPzfKR+/J3cHkxcpHKpKKvGfDZVPS4hfJCc4cCG0CgYzvlD6yE/S3CIL/Yt91ak327YCpiF/0MyeZHEHKA=="], + + "winston-transport": ["winston-transport@4.9.0", "", { "dependencies": { "logform": "^2.7.0", "readable-stream": "^3.6.2", "triple-beam": "^1.3.0" } }, "sha512-8drMJ4rkgaPo1Me4zD/3WLfI/zPdA9o2IipKODunnGDcuqbHwjsbB79ylv04LCGGzU0xQ6vTznOMpQGaLhhm6A=="], + "wrap-ansi": ["wrap-ansi@8.1.0", "", { "dependencies": { "ansi-styles": "^6.1.0", "string-width": "^5.0.1", "strip-ansi": "^7.0.1" } }, "sha512-si7QWI6zUMq56bESFvagtmzMdGOtoxfR+Sez11Mobfc7tm+VkUckk9bW2UeffTGVUbOksxmSw0AA2gs8g71NCQ=="], "wrap-ansi-cjs": ["wrap-ansi@7.0.0", "", { "dependencies": { "ansi-styles": "^4.0.0", "string-width": "^4.1.0", "strip-ansi": "^6.0.0" } }, "sha512-YVGIj2kamLSTxw6NsZjoBxfSwsn0ycdesmc4p+Q21c5zPuZ1pl+NfxVdxPtdHvmNVOQ6XSYG4AUtyt/Fi7D16Q=="], + "y18n": ["y18n@5.0.8", "", {}, "sha512-0pfFzegeDWJHJIAmTLRP2DwHjdF5s7jo9tuztdQxAhINCdvS+3nGINqPd00AphqJR/0LhANUS6/+7SCb98YOfA=="], + "yaml": ["yaml@2.8.0", "", { "bin": { "yaml": "bin.mjs" } }, "sha512-4lLa/EcQCB0cJkyts+FpIRx5G/llPxfP6VQU5KByHEhLxY3IJCH0f0Hy1MHI8sClTvsIb8qwRJ6R/ZdlDJ/leQ=="], + "yargs": ["yargs@17.7.2", "", { "dependencies": { "cliui": "^8.0.1", "escalade": "^3.1.1", "get-caller-file": "^2.0.5", "require-directory": "^2.1.1", "string-width": "^4.2.3", "y18n": "^5.0.5", "yargs-parser": "^21.1.1" } }, "sha512-7dSzzRQ++CKnNI/krKnYRV7JKKPUXMEh61soaHKg9mrWEhzFWhFnxPxGl+69cD1Ou63C13NUPCnmIcrvqCuM6w=="], + + "yargs-parser": ["yargs-parser@21.1.1", "", {}, "sha512-tVpsJW7DdjecAiFpbIB1e3qxIQsE6NoPc5/eTdrbbIC4h0LVsWhnoa3g+m2HclBIujHzsxZ4VJVA+GUuc2/LBw=="], + "zimmerframe": ["zimmerframe@1.1.2", "", {}, "sha512-rAbqEGa8ovJy4pyBxZM70hg4pE6gDgaQ0Sl9M3enG3I0d6H4XSAM3GeNGLKnsBpuijUow064sf7ww1nutC5/3w=="], + "zod": ["zod@4.2.1", "", {}, "sha512-0wZ1IRqGGhMP76gLqz8EyfBXKk0J2qo2+H3fi4mcUP/KtTocoX08nmIAHl1Z2kJIZbZee8KOpBCSNPRgauucjw=="], + + "@langchain/core/uuid": ["uuid@10.0.0", "", { "bin": { "uuid": "dist/bin/uuid" } }, "sha512-8XkAphELsDnEGrDxUOHB3RGvXz6TeuYSGEZBOjtTtPm2lwhGBjLgOzLHB63IUWfBpNucQjND6d3AOudO+H3RWQ=="], + + "@langchain/langgraph/uuid": ["uuid@10.0.0", "", { "bin": { "uuid": "dist/bin/uuid" } }, "sha512-8XkAphELsDnEGrDxUOHB3RGvXz6TeuYSGEZBOjtTtPm2lwhGBjLgOzLHB63IUWfBpNucQjND6d3AOudO+H3RWQ=="], + + "@langchain/langgraph-checkpoint/uuid": ["uuid@10.0.0", "", { "bin": { "uuid": "dist/bin/uuid" } }, "sha512-8XkAphELsDnEGrDxUOHB3RGvXz6TeuYSGEZBOjtTtPm2lwhGBjLgOzLHB63IUWfBpNucQjND6d3AOudO+H3RWQ=="], + + "@langchain/langgraph-sdk/uuid": ["uuid@9.0.1", "", { "bin": { "uuid": "dist/bin/uuid" } }, "sha512-b+1eJOlsR9K8HJpow9Ok3fiWOWSIcIzXodvv0rQjVoOVNpWMpxf1wZNpt4y9h10odCNrqnYp1OBzRktckBe3sA=="], + + "@langchain/ollama/uuid": ["uuid@10.0.0", "", { "bin": { "uuid": "dist/bin/uuid" } }, "sha512-8XkAphELsDnEGrDxUOHB3RGvXz6TeuYSGEZBOjtTtPm2lwhGBjLgOzLHB63IUWfBpNucQjND6d3AOudO+H3RWQ=="], + + "@sap-ai-sdk/langchain/uuid": ["uuid@13.0.0", "", { "bin": { "uuid": "dist-node/bin/uuid" } }, "sha512-XQegIaBTVUjSHliKqcnFqYypAd4S+WCYt5NIeRs6w/UAry7z8Y9j5ZwRRL4kzq9U3sD6v+85er9FvkEaBpji2w=="], + + "@sap-ai-sdk/orchestration/yaml": ["yaml@2.8.2", "", { "bin": { "yaml": "bin.mjs" } }, "sha512-mplynKqc1C2hTVYxd0PU2xQAc22TI1vShAYGksCCfxbn/dFwnHTNi1bvYsBTkhdUNtGIf5xNOg938rrSSYvS9A=="], + + "@sap/xssec/debug": ["debug@4.4.3", "", { "dependencies": { "ms": "^2.1.3" } }, "sha512-RGwwWnwQvkVfavKVt22FGLw+xYSdzARwm0ru6DhTVA3umU5hZc28V3kO4stgYryrTlLpuvgI9GiijltAjNbcqA=="], + "anymatch/picomatch": ["picomatch@2.3.1", "", {}, "sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA=="], + "chalk/ansi-styles": ["ansi-styles@4.3.0", "", { "dependencies": { "color-convert": "^2.0.1" } }, "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg=="], + + "cliui/string-width": ["string-width@4.2.3", "", { "dependencies": { "emoji-regex": "^8.0.0", "is-fullwidth-code-point": "^3.0.0", "strip-ansi": "^6.0.1" } }, "sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g=="], + + "cliui/strip-ansi": ["strip-ansi@6.0.1", "", { "dependencies": { "ansi-regex": "^5.0.1" } }, "sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A=="], + + "cliui/wrap-ansi": ["wrap-ansi@7.0.0", "", { "dependencies": { "ansi-styles": "^4.0.0", "string-width": "^4.1.0", "strip-ansi": "^6.0.0" } }, "sha512-YVGIj2kamLSTxw6NsZjoBxfSwsn0ycdesmc4p+Q21c5zPuZ1pl+NfxVdxPtdHvmNVOQ6XSYG4AUtyt/Fi7D16Q=="], + + "color/color-convert": ["color-convert@3.1.3", "", { "dependencies": { "color-name": "^2.0.0" } }, "sha512-fasDH2ont2GqF5HpyO4w0+BcewlhHEZOFn9c1ckZdHpJ56Qb7MHhH/IcJZbBGgvdtwdwNbLvxiBEdg336iA9Sg=="], + + "color-string/color-name": ["color-name@2.1.0", "", {}, "sha512-1bPaDNFm0axzE4MEAzKPuqKWeRaT43U/hyxKPBdqTfmPF+d6n7FSoTFxLVULUJOmiLp01KjhIPPH+HrXZJN4Rg=="], + "fast-glob/glob-parent": ["glob-parent@5.1.2", "", { "dependencies": { "is-glob": "^4.0.1" } }, "sha512-AOIgSQCepiJYwP3ARnGx+5VnTu2HBYdzbGP45eLw1vr3zB3vZLeyed1sC9hnbcOc9/SrMyM5RPQrkGz4aS9Zow=="], - "micromatch/picomatch": ["picomatch@2.3.1", "", {}, "sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA=="], + "langchain/uuid": ["uuid@10.0.0", "", { "bin": { "uuid": "dist/bin/uuid" } }, "sha512-8XkAphELsDnEGrDxUOHB3RGvXz6TeuYSGEZBOjtTtPm2lwhGBjLgOzLHB63IUWfBpNucQjND6d3AOudO+H3RWQ=="], - "rollup/@types/estree": ["@types/estree@1.0.7", "", {}, "sha512-w28IoSUCJpidD/TGviZwwMJckNESJZXFu7NBZ5YJ4mEUnNraUn9Pm8HSZm/jDF1pDWYKspWE7oVphigUPRakIQ=="], + "langsmith/uuid": ["uuid@10.0.0", "", { "bin": { "uuid": "dist/bin/uuid" } }, "sha512-8XkAphELsDnEGrDxUOHB3RGvXz6TeuYSGEZBOjtTtPm2lwhGBjLgOzLHB63IUWfBpNucQjND6d3AOudO+H3RWQ=="], + + "micromatch/picomatch": ["picomatch@2.3.1", "", {}, "sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA=="], "string-width-cjs/emoji-regex": ["emoji-regex@8.0.0", "", {}, "sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A=="], @@ -564,12 +956,28 @@ "tailwindcss/chokidar": ["chokidar@3.6.0", "", { "dependencies": { "anymatch": "~3.1.2", "braces": "~3.0.2", "glob-parent": "~5.1.2", "is-binary-path": "~2.1.0", "is-glob": "~4.0.1", "normalize-path": "~3.0.0", "readdirp": "~3.6.0" }, "optionalDependencies": { "fsevents": "~2.3.2" } }, "sha512-7VT13fmjotKpGipCW9JEQAusEPE+Ei8nl6/g4FBAmIm0GOOLMua9NDDo/DWp0ZAxCr3cPq5ZpBqmPAQgDda2Pw=="], + "tinyglobby/fdir": ["fdir@6.5.0", "", { "peerDependencies": { "picomatch": "^3 || ^4" }, "optionalPeers": ["picomatch"] }, "sha512-tIbYtZbucOs0BRGqPJkshJUYdL+SDH7dVM8gjy+ERp3WAUjLEFJE+02kanyHtwjWOnwrKYBiwAmM0p4kLJAnXg=="], + + "vite/fdir": ["fdir@6.5.0", "", { "peerDependencies": { "picomatch": "^3 || ^4" }, "optionalPeers": ["picomatch"] }, "sha512-tIbYtZbucOs0BRGqPJkshJUYdL+SDH7dVM8gjy+ERp3WAUjLEFJE+02kanyHtwjWOnwrKYBiwAmM0p4kLJAnXg=="], + + "wrap-ansi/ansi-styles": ["ansi-styles@6.2.1", "", {}, "sha512-bN798gFfQX+viw3R7yrGWRqnrN2oRkEkUjjl4JNn4E8GxxbjtG3FbrEIIY3l8/hrwUwIeCZvi4QuOTP4MErVug=="], + "wrap-ansi-cjs/ansi-styles": ["ansi-styles@4.3.0", "", { "dependencies": { "color-convert": "^2.0.1" } }, "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg=="], "wrap-ansi-cjs/string-width": ["string-width@4.2.3", "", { "dependencies": { "emoji-regex": "^8.0.0", "is-fullwidth-code-point": "^3.0.0", "strip-ansi": "^6.0.1" } }, "sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g=="], "wrap-ansi-cjs/strip-ansi": ["strip-ansi@6.0.1", "", { "dependencies": { "ansi-regex": "^5.0.1" } }, "sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A=="], + "yargs/string-width": ["string-width@4.2.3", "", { "dependencies": { "emoji-regex": "^8.0.0", "is-fullwidth-code-point": "^3.0.0", "strip-ansi": "^6.0.1" } }, "sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g=="], + + "cliui/string-width/emoji-regex": ["emoji-regex@8.0.0", "", {}, "sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A=="], + + "cliui/strip-ansi/ansi-regex": ["ansi-regex@5.0.1", "", {}, "sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ=="], + + "cliui/wrap-ansi/ansi-styles": ["ansi-styles@4.3.0", "", { "dependencies": { "color-convert": "^2.0.1" } }, "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg=="], + + "color/color-convert/color-name": ["color-name@2.1.0", "", {}, "sha512-1bPaDNFm0axzE4MEAzKPuqKWeRaT43U/hyxKPBdqTfmPF+d6n7FSoTFxLVULUJOmiLp01KjhIPPH+HrXZJN4Rg=="], + "string-width-cjs/strip-ansi/ansi-regex": ["ansi-regex@5.0.1", "", {}, "sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ=="], "svelte-i18n/esbuild/@esbuild/aix-ppc64": ["@esbuild/aix-ppc64@0.19.12", "", { "os": "aix", "cpu": "ppc64" }, "sha512-bmoCYyWdEL3wDQIVbcyzRyeKLgk2WtWLTWz1ZIAZF/EGbNOwSA6ew3PftJ1PqMiOOGu0OyFMzG53L0zqIpPeNA=="], @@ -626,6 +1034,12 @@ "wrap-ansi-cjs/strip-ansi/ansi-regex": ["ansi-regex@5.0.1", "", {}, "sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ=="], + "yargs/string-width/emoji-regex": ["emoji-regex@8.0.0", "", {}, "sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A=="], + + "yargs/string-width/strip-ansi": ["strip-ansi@6.0.1", "", { "dependencies": { "ansi-regex": "^5.0.1" } }, "sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A=="], + "tailwindcss/chokidar/readdirp/picomatch": ["picomatch@2.3.1", "", {}, "sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA=="], + + "yargs/string-width/strip-ansi/ansi-regex": ["ansi-regex@5.0.1", "", {}, "sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ=="], } } diff --git a/package.json b/package.json index 115c559e..a84e6c62 100644 --- a/package.json +++ b/package.json @@ -14,7 +14,7 @@ "tailwindcss": "^3.4.18", "tslib": "^2.8.1", "typescript": "^5.9.3", - "vite": "^6.4.0" + "vite": "^7.0.0" }, "private": true, "scripts": { @@ -27,13 +27,11 @@ "type": "module", "dependencies": { "@selemondev/svgl-svelte": "^0.0.3", - "@tanstack/svelte-query": "https://pkg.pr.new/@tanstack/svelte-query@746b9c5d83e901deb3a5ca7012a4b4e2b617c5e3", + "@tanstack/svelte-query": "^6.0.10", "bits-ui": "^2.11.8", "builtin-modules": "^5.0.0", "dexie": "^4.2.1", "i18next": "^23.16.8", - "monkey-around": "^3.0.0", - "papa-ts": "link:papa-ts", "svelte-i18n": "^4.0.1", "uuid": "^11.1.0" } diff --git a/src/SmartSecondBrain.ts b/src/SmartSecondBrain.ts deleted file mode 100755 index 2f2cabc3..00000000 --- a/src/SmartSecondBrain.ts +++ /dev/null @@ -1,294 +0,0 @@ -import { App, Notice, TFile, normalizePath } from "obsidian"; -import { obsidianDocumentLoader, Papa, type PapaConfig } from "papa-ts"; -import { get } from "svelte/store"; -import Log, { LogLvl } from "./logging"; -import { wildTest } from "./utils/utils"; -import { - papaState, - errorState, - papaIndexingProgress, - runState, - runContent, - papaIndexingTimeLeft, -} from "./store"; -import { _ } from "svelte-i18n"; -import type SecondBrainPlugin from "./main"; - -export default class SmartSecondBrain { - private papa: Papa; - private plugin: SecondBrainPlugin; - private needsToSaveVectorStoreData = false; - private pluginDir: string; - - constructor(plugin: SecondBrainPlugin, pluginDir: string) { - this.plugin = plugin; - this.pluginDir = pluginDir; - this.papa = new Papa({ - debugging: { - langsmithApiKey: this.pluginData.debuggingLangchainKey, - logLvl: 1, - }, - }); - } - - async init() { - const { - debuggingLangchainKey, - isVerbose, - excludeFF, - providers, - selEmbedProvider, - selGenProvider, - selEmbedModel, - selGenModel, - } = this.plugin.pluginData; - const t = get(_); - - if (!(await this.canInit())) return; - - if (get(papaState) !== "indexing-pause") { - papaState.set("loading"); - Log.info( - "Initializing second brain", - "\nGen Model: ", - selGenModel, - "\nEmbed Model: ", - selEmbedModel, - ); - try { - await this.papa.init({ - baseProviders: providers, - selEmbedProvider, - selGenProvider, - selEmbedModel, - selGenModel, - langsmithApiKey: debuggingLangchainKey || undefined, - logLvl: isVerbose ? LogLvl.DEBUG : LogLvl.DISABLED, - }); - } catch (e) { - Log.error(e); - papaState.set("error"); - return new Notice(t("notice.failed", { values: { error: e } }), 4000); - } - // check if vector store data exists - if (await this.app.vault.adapter.exists(this.getVectorStoreFile())) { - const vectorStoreData = await this.app.vault.adapter.readBinary( - this.getVectorStoreFile(), - ); - await this.papa.load(new Uint8Array(vectorStoreData)); - } - } - const mdFiles = this.app.vault.getMarkdownFiles(); - const docs = await obsidianDocumentLoader( - await this.createPapaObsidianFiles( - mdFiles.filter((mdFile: TFile) => { - for (const exclude of excludeFF) - if (wildTest(exclude, mdFile.path)) return false; - return true; - }), - ), - ); - papaState.set("indexing"); - let needsSave = false; - try { - let lastTime = Date.now(); - const timePerDoc = []; - - let lastTotalDocs = 0; - for await (const result of this.papa.embedDocuments(docs)) { - needsSave = - (!this.needsToSaveVectorStoreData && result.numAdded > 0) || - result.numDeleted > 0; - const progress = - ((result.numAdded + result.numSkipped) / docs.length) * 100; - papaIndexingProgress.set(Math.max(progress, get(papaIndexingProgress))); - const currentTime = Date.now(); - timePerDoc.push(currentTime - lastTime); - const numberOfDocumentsRemaining = - docs.length * (1 - get(papaIndexingProgress) / 100); - const averageTimePerDocumentInSeconds = - timePerDoc.reduce((a, b) => a + b, 0) / - timePerDoc.length / - (result.numAdded + result.numSkipped - lastTotalDocs) / - 1000; - lastTotalDocs = result.numAdded + result.numSkipped; - if (timePerDoc.length > 5) { - timePerDoc.shift(); - papaIndexingTimeLeft.set( - Math.ceil( - averageTimePerDocumentInSeconds * numberOfDocumentsRemaining, - ), - ); - } - lastTime = currentTime; - if (get(papaState) === "indexing-pause") break; - } - } catch (e) { - Log.error(e); - papaState.set("error"); - errorState.set("failed-indexing"); - new Notice(t("notice.failed_indexing"), 4000); - } - - this.needsToSaveVectorStoreData = needsSave; - this.saveVectorStoreData(); - if (get(papaIndexingProgress) === 100) { - new Notice(t("notice.done"), 2000); - papaIndexingProgress.set(0); - papaState.set("idle"); - } - } - - // temporary function to create obsidian files for papa, refactor later - private async createPapaObsidianFiles(files: TFile[]) { - let obsidianFiles = []; - for (const file of files) { - const fileMetadata = this.app.metadataCache.getFileCache(file); - if (!fileMetadata) continue; - const noteContent = await this.app.vault.cachedRead(file); - obsidianFiles.push({ - path: file.path, - content: noteContent, - metadata: fileMetadata, - }); - } - return obsidianFiles; - } - - async cancelIndexing() { - // if (this.app.vault.adapter.exists(this.getVectorStoreFile())) await this.app.vault.adapter.remove(this.getVectorStoreFile()); - papaState.set("uninitialized"); - papaIndexingProgress.set(0); - } - - canRunPapa() { - const t = get(_); - if (get(papaState) === "running") - return new Notice(t("notice.still_running"), 4000) && false; - else if ( - get(papaState) === "indexing" || - get(papaState) === "indexing-pause" || - get(papaState) === "loading" - ) - return new Notice(t("notice.still_indexing"), 4000) && false; - else if (get(papaState) === "error") - return new Notice(t("notice.error"), 4000) && false; - else if (get(papaState) !== "idle") - return new Notice(t("notice.not_initialized"), 4000) && false; - return true; - } - - async runPapa() { - papaState.set("running"); - try { - const cH = get(chatHistory); - const userQuery = cH[cH.length - 1].content; - const responseStream = this.papa.run({ - isRAG: get(data).isUsingRag, - userQuery, - chatHistory: serializeChatHistory(cH.slice(0, cH.length - 1)), - lang: get(data).assistantLanguage, - }); - for await (const response of responseStream) { - runState.set(response.status); - runContent.set(response.content); - } - } catch (error) { - const errorMsg = get(_)("notice.run_failed", { values: { error } }); - // Log.error(errorMsg); - runContent.set(errorMsg); - // papaState.set('error'); - // errorState.set('run-failed'); - new Notice(errorMsg, 4000); - } - papaState.set("idle"); - } - - async createFilenameForChat() { - let fileName = await this.papa.createTitleFromChatHistory( - get(data).assistantLanguage, - serializeChatHistory(get(chatHistory)), - ); - // File name cannot contain any of the following characters: \, /, :, *, ?, ", <, >, |, # - fileName = fileName.replace(/[\\/:*?"<>|#]/g, ""); - return fileName; - } - - getVectorStoreFile() { - const { selEmbedModel } = get(data); - return normalizePath( - this.pluginDir + "/vectorstores/" + selEmbedModel + ".bin", - ); - } - - async saveVectorStoreData() { - if (this.needsToSaveVectorStoreData) { - Log.debug("Saving vector store data"); - this.needsToSaveVectorStoreData = false; - // create vectorstores directory if it doesn't exist - (await this.app.vault.adapter.exists(this.pluginDir + "/vectorstores")) || - (await this.app.vault.adapter.mkdir(this.pluginDir + "/vectorstores")); - await this.app.vault.adapter.writeBinary( - this.getVectorStoreFile(), - (await this.papa.getData()).buffer as ArrayBuffer, - ); - Log.info("Saved vector store data"); - } - } - - async onFileChange(file: TFile) { - if (!this.papa) return; - for (const exclude of get(data).excludeFF) - if (wildTest(exclude, file.path)) return; - const docs = await obsidianDocumentLoader( - await this.createPapaObsidianFiles([file]), - ); - this.papa.embedDocuments(docs, "byFile"); - this.needsToSaveVectorStoreData = true; - } - async onFileDelete(file: TFile) { - if (!this.papa) return; - for (const exclude of get(data).excludeFF) - if (wildTest(exclude, file.path)) return; - const docs = await obsidianDocumentLoader( - await this.createPapaObsidianFiles([file]), - ); - this.papa.deleteDocuments({ docs }); - this.needsToSaveVectorStoreData = true; - } - async onFileRename(file: TFile, oldPath: string) { - if (!this.papa) return; - for (const exclude of get(data).excludeFF) - if (wildTest(exclude, file.path)) return; - await this.papa.deleteDocuments({ sources: [oldPath] }); - const docs = await obsidianDocumentLoader( - await this.createPapaObsidianFiles([file]), - ); - this.papa.embedDocuments(docs, "byFile"); - this.needsToSaveVectorStoreData = true; - } - - configure(config: Partial) { - this.papa.configure(config); - } - - stopRun() { - this.papa.stopRun(); - papaState.set("idle"); - } - - private async canInit(): Promise { - const t = get(_); - - if (get(papaState) === "running") { - new Notice(t("notice.still_running"), 4000); - return false; - } else if (get(papaState) === "indexing" || get(papaState) === "loading") { - new Notice(t("notice.still_indexing"), 4000); - return false; - } else if (!(await this.papa.isEmbedProviderSetuped())) { - papaState.set("error"); - return false; - } else return true; - } -} diff --git a/src/agent/AgentManager.ts b/src/agent/AgentManager.ts new file mode 100644 index 00000000..78e48b26 --- /dev/null +++ b/src/agent/AgentManager.ts @@ -0,0 +1,456 @@ +import { + Agent, + ProviderRegistry, + type ThreadSnapshot, + LangSmithTelemetry, + type Telemetry, +} from "papa-ts"; +import { ObsidianChatManager } from "./ObsidianChatManager"; +import { createSearchNotesTool } from "../tools/searchNotes"; +import { createGetAllTagsTool } from "../tools/getAllTags"; +import { createExecuteDataviewTool } from "../tools/executeDataview"; +import { createGetPropertiesTool } from "../tools/getProperties"; +import { createReadNoteTool } from "../tools/readNote"; +import { createSystemPrompt } from "./prompts"; +import { createObsidianFetch } from "../utils/obsidianFetch"; +import { getData } from "../stores/dataStore.svelte"; +import type SecondBrainPlugin from "../main"; + +declare const MultiServerMCPClient: any; + +export class AgentManager { + private plugin: SecondBrainPlugin; + private agent: Agent | null = null; + private chatManager: ObsidianChatManager; + + constructor(plugin: SecondBrainPlugin) { + this.plugin = plugin; + this.chatManager = new ObsidianChatManager(plugin); + } + + private async configureRegistry( + registry: ProviderRegistry, + provider: string, + apiKey: string, + ): Promise<{ providerName: string; modelOptions: Record }> { + let providerName: string = provider; + let modelOptions: Record = {}; + + if (apiKey || provider === "ollama") { + try { + if (provider === "openai" && apiKey) { + await registry.useOpenAI({ apiKey }); + modelOptions = { apiKey }; + providerName = "openai"; + } else if (provider === "anthropic" && apiKey) { + await registry.useAnthropic({ apiKey }); + modelOptions = { apiKey }; + providerName = "anthropic"; + } else if (provider === "ollama") { + const baseUrl = apiKey || "http://localhost:11434"; + await registry.useOllama({ baseUrl }); + modelOptions = { baseUrl }; + providerName = "ollama"; + } else if (provider === "sap-ai-core" && apiKey) { + await registry.useSapAICore({ apiKey }); + modelOptions = { apiKey }; + providerName = "sap-ai-core"; + } else if (provider === "custom" && apiKey) { + // Default to OpenAI structure for custom + await registry.useOpenAI({ apiKey }); + modelOptions = { apiKey }; + providerName = "openai"; + } + } catch (error) { + console.error("Error configuring provider:", error); + throw error; + } + } + return { providerName, modelOptions }; + } + + private configureTelemetry(): Telemetry | undefined { + const data = getData(); + if (data.enableLangSmith && data.langSmithApiKey) { + try { + const telemetry = new LangSmithTelemetry({ + projectName: data.langSmithProject || "obsidian-agent", + apiKey: data.langSmithApiKey, + endpoint: data.langSmithEndpoint || "https://api.smith.langchain.com", + flushOnComplete: true, + }); + console.log("Smart Second Brain: LangSmith telemetry enabled"); + return telemetry; + } catch (e) { + console.error( + "Smart Second Brain: Failed to initialize LangSmith telemetry", + e, + ); + } + } + return undefined; + } + + private async bindTools(agent: Agent) { + const searchNotesTool = createSearchNotesTool(this.plugin.app); + const getAllTagsTool = createGetAllTagsTool(this.plugin.app); + const executeDataviewTool = createExecuteDataviewTool(this.plugin.app); + const getPropertiesTool = createGetPropertiesTool(this.plugin.app); + const readNoteTool = createReadNoteTool(this.plugin.app); + + const tools: any[] = [ + searchNotesTool, + getAllTagsTool, + executeDataviewTool, + getPropertiesTool, + readNoteTool, + ]; + + // Load MCP tools if configured (use getData()) + const data = getData(); + if (data.mcpServers && Object.keys(data.mcpServers).length > 0) { + try { + console.log( + "Smart Second Brain: Initializing MCP client...", + data.mcpServers, + ); + + // HACK: Monkey patch the global fetch for the entire lifecycle + if (!(window as any)._originalFetch) { + (window as any)._originalFetch = window.fetch; + window.fetch = createObsidianFetch( + (window as any)._originalFetch, + ) as any; + } + + try { + const mcpClient = new MultiServerMCPClient(data.mcpServers); + const mcpTools = await mcpClient.getTools(); + console.log( + `Smart Second Brain: Loaded ${mcpTools.length} MCP tools`, + ); + tools.push(...mcpTools); + } catch (e) { + console.error("Failed to get MCP tools", e); + } + } catch (error) { + console.error("Smart Second Brain: Failed to load MCP tools", error); + } + } + + agent.bindTools(tools); + } + + private async ensureAgent(): Promise { + console.log(this.agent); + this.agent = null; + if (!this.agent) { + await this.initialize(); + } + + if (!this.agent) { + throw new Error("Agent initialization failed."); + } + return this.agent; + } + + async initialize(): Promise { + // Load chats + await this.chatManager.load(); + + // Cleanup existing agent if any + if (this.agent) { + this.agent = null; + } + + try { + const pluginData = getData(); + pluginData.getConfiguredProviders().forEach((provider) => { + registry.listProviders().forEach((providerName) => { + this.configureRegistry( + registry, + providerName, + pluginData.getProviderAuthParams(provider), + ); + }); + }); + } catch (e) { + console.warn( + "Smart Second Brain: Failed to derive default model from data store", + e, + ); + } + + console.log("Smart Second Brain: Initializing agent..."); + + // Create provider registry + const registry = new ProviderRegistry(); + + let providerName: string; + let modelOptions: Record; + + registry.registerProvider(); + + try { + const config = await this.configureRegistry( + registry, + "ollama", + "http://localhost:11434", + ); + providerName = config.providerName; + modelOptions = config.modelOptions; + } catch (error) { + // Error is already logged in configureRegistry + return; + } + + // Configure Telemetry (use getData()) + const telemetry = this.configureTelemetry(); + + // Create agent with checkpoint storage + // The chatManager acts as both checkpointer and thread store + const agent = new Agent({ + registry, + checkpointer: this.chatManager, + threadStore: this.chatManager.asThreadStore(), + telemetry, + }); + + // Check for available plugins to adjust prompt capabilities + // @ts-ignore - Dynamic access to plugins + const hasChartsPlugin = + this.plugin.app.plugins?.enabledPlugins?.has("obsidian-charts"); + + // Set prompt + agent.setPrompt(createSystemPrompt(hasChartsPlugin)); + + // Bind tools + await this.bindTools(agent); + + // If we have configuration, try to choose the model + if ((apiKey || provider === "ollama") && modelName) { + try { + console.log("Smart Second Brain: Choosing model...", { + provider: providerName, + chatModel: modelName, + }); + await agent.chooseModel({ + provider: providerName, + chatModel: modelName, + options: modelOptions, + }); + console.log("Smart Second Brain: Model chosen successfully"); + } catch (chooseModelError) { + console.error( + "Smart Second Brain: Error choosing model:", + chooseModelError, + ); + } + } else { + console.warn( + "Smart Second Brain: API key or model name not configured. Agent initialized for history reading only.", + ); + } + + this.agent = agent; + } + + async runQuery( + query: string, + threadId: string = "default-thread", + ): Promise { + const agent = await this.ensureAgent(); + + try { + const result = await agent.run({ + query, + threadId, + }); + + if (typeof result.response === "string") { + return result.response; + } else if (result.response !== undefined && result.response !== null) { + return String(result.response); + } else { + return "No response received from agent."; + } + } catch (error) { + console.error("Smart Second Brain: Error running query", error); + throw error; + } + } + + async *streamQuery( + query: string, + threadId: string = "default-thread", + ): AsyncGenerator< + { + type: "token" | "result"; + token?: string; + result?: any; + messages?: any[]; + }, + void, + unknown + > { + const agent = await this.ensureAgent(); + await this.agent?.chooseModel({ + provider: "Ollama", + chatModel: "ministral-3:3b", + }); + console.log(agent); + + try { + for await (const chunk of agent.streamTokens({ + query, + threadId, + })) { + switch (chunk.type) { + case "token": + yield { + type: "token", + token: chunk.token, + messages: (chunk as any).messages, + }; + break; + case "result": + yield { type: "result", result: chunk.result }; + break; + default: + break; + } + } + } catch (error) { + console.error("Smart Second Brain: Error streaming query", error); + throw error; + } + } + + async getAvailableModels( + provider: string, + apiKey: string, + ): Promise { + try { + const registry = new ProviderRegistry(); + const { providerName } = await this.configureRegistry( + registry, + provider, + apiKey, + ); + + if (!providerName) return []; + + return registry.listChatModels(providerName); + } catch (error) { + console.error( + "Smart Second Brain: Error fetching available models", + error, + ); + return []; + } + } + + async getThreadMessages(threadId: string): Promise { + try { + // Try to use agent if available to get history from checkpoint (more robust) + if (this.agent) { + try { + const history = await this.agent.getThreadHistory(threadId); + if (history && history.messages) { + return history.messages; + } + } catch (e) { + console.warn("Failed to get history from agent", e); + } + } + return []; + } catch (error) { + console.error( + "Smart Second Brain: Error fetching thread messages", + error, + ); + return []; + } + } + + async getAllThreads(): Promise { + await this.chatManager.load(); + return this.chatManager.listThreads(); + } + + async deleteThread(threadId: string): Promise { + await this.chatManager.delete(threadId); + } + + async generateThreadTitle(threadId: string): Promise { + const agent = await this.ensureAgent().catch((e) => { + console.warn("Agent not initialized, cannot generate title"); + return null; + }); + + if (!agent) return; + + try { + await agent.generateTitle(threadId); + console.log(`Generated title for thread ${threadId}`); + + // Wait a bit for the title to be persisted + await new Promise((resolve) => setTimeout(resolve, 200)); + + // Try multiple ways to get the title: + // 1. Read from thread store (may have it in cache) + let snapshot = await this.chatManager.read(threadId, true); + console.log(`Read snapshot for thread ${threadId}:`, snapshot); + + // 2. If not found, try reading directly from in-memory storage + if (!snapshot?.title) { + const threadData = await this.chatManager.ensureThreadLoaded(threadId); + if (threadData?.title) { + console.log(`Title found in threadData: "${threadData.title}"`); + snapshot = { + threadId: threadData.threadId, + title: threadData.title, + metadata: threadData.metadata, + createdAt: threadData.createdAt, + updatedAt: threadData.updatedAt, + }; + } + } + + if (snapshot?.title) { + console.log(`Title found: "${snapshot.title}", renaming file...`); + await this.chatManager.renameChatFile(threadId, snapshot.title); + } else { + console.warn( + `No title found for thread ${threadId} after generation. Waiting longer and retrying...`, + ); + // Wait longer and try again + await new Promise((resolve) => setTimeout(resolve, 1000)); + snapshot = await this.chatManager.read(threadId, true); + if (snapshot?.title) { + console.log( + `Title found on retry: "${snapshot.title}", renaming file...`, + ); + await this.chatManager.renameChatFile(threadId, snapshot.title); + } else { + console.error( + `Title still not found for thread ${threadId} after retry`, + ); + } + } + } catch (error) { + console.error(`Error generating title for thread ${threadId}:`, error); + } + } + + cleanup(): void { + // Restore original fetch if it was patched + if ((window as any)._originalFetch) { + window.fetch = (window as any)._originalFetch; + delete (window as any)._originalFetch; + } + + // Cleanup if needed + this.agent = null; + } +} diff --git a/src/agent/ObsidianChatManager.ts b/src/agent/ObsidianChatManager.ts new file mode 100644 index 00000000..8ebf4c93 --- /dev/null +++ b/src/agent/ObsidianChatManager.ts @@ -0,0 +1,565 @@ +import { + BaseCheckpointSaver, + type Checkpoint, + type CheckpointMetadata, + type CheckpointTuple, + type PendingWrite, + type CheckpointListOptions, +} from "@langchain/langgraph-checkpoint"; +import type { RunnableConfig } from "@langchain/core/runnables"; +import { Plugin, debounce, TFile, normalizePath, type DataAdapter } from "obsidian"; +import type SecondBrainPlugin from "../main"; +import { type ThreadStore, type ThreadSnapshot } from "papa-ts"; +import { getData } from "../stores/dataStore.svelte"; + +interface CheckpointEntry { + checkpoint: Checkpoint; + metadata: CheckpointMetadata; + parentConfig?: RunnableConfig; +} + +interface ThreadData { + // Metadata (ThreadSnapshot) + threadId: string; + title?: string; + metadata?: Record; + createdAt: number; + updatedAt: number; + + // Checkpoint data + checkpoints: Record; + writes: Record; // checkpoint_id -> writes +} + +export class ObsidianChatManager extends BaseCheckpointSaver { + private plugin: SecondBrainPlugin; + private adapter: DataAdapter; + + // In-memory cache: thread_id -> ThreadData (Loaded on demand) + private storage: Map = new Map(); + + // Index cache: thread_id -> ThreadSnapshot (Loaded on startup) + private threadIndex: Map = new Map(); + + // Path cache: thread_id -> file_path (Optimizes file lookups) + private filePathCache: Map = new Map(); + + private indexLoaded: boolean = false; + + constructor(plugin: SecondBrainPlugin) { + super(); + this.plugin = plugin; + this.adapter = plugin.app.vault.adapter; + } + + // --- File System Helpers --- + + private getChatFolder(): string { + // Prefer the new data store (targetFolder). Fallback to legacy v2 setting. + try { + const data = getData(); + return data.targetFolder || "Chats"; + } catch { + // @ts-ignore legacy v2 settings + return (this.plugin.settings?.chatsFolder as string) || "Chats"; + } + } + + private getIndexPath(): string { + const configDir = (this.plugin.app.vault as any).configDir || ".obsidian"; + return `${configDir}/plugins/${this.plugin.manifest.id}/data/threads.json`; + } + + private async ensureFolder(): Promise { + const folder = this.getChatFolder(); + if (!(await this.adapter.exists(folder))) { + await this.adapter.mkdir(folder); + } + + // Ensure plugin data dir for index + const dataDir = `${(this.plugin.app.vault as any).configDir || ".obsidian"}/plugins/${this.plugin.manifest.id}/data`; + if (!(await this.adapter.exists(dataDir))) { + await this.adapter.mkdir(dataDir); + } + } + + private async resolveFilePath(threadId: string): Promise { + // Check cache first + if (this.filePathCache.has(threadId)) { + return this.filePathCache.get(threadId)!; + } + + const folder = this.getChatFolder(); + + // First try the default path + const defaultPath = `${folder}/${threadId}.chat`; + if (await this.adapter.exists(defaultPath)) { + this.filePathCache.set(threadId, defaultPath); + return defaultPath; + } + + // If not found, search for it (renamed files) + // Look for: "{Title} - {Timestamp}.chat" + // Timestamp is usually the part after "Chat " in the threadId + let timestampPart = ""; + if (threadId.startsWith("Chat ")) { + timestampPart = threadId.substring(5); + } + + try { + if (await this.adapter.exists(folder)) { + const result = await this.adapter.list(folder); + for (const file of result.files) { + if (!file.endsWith(".chat")) continue; + + // Check if file contains threadId (legacy check) + if (file.includes(threadId)) { + this.filePathCache.set(threadId, file); + return file; + } + + // Check for renamed files with matching timestamp + if (timestampPart && file.endsWith(` - ${timestampPart}.chat`)) { + this.filePathCache.set(threadId, file); + return file; + } + } + } + } catch (e) { + console.error(`Error searching for file with threadId ${threadId}:`, e); + } + + // Fallback to default path (will be created there if writing) + this.filePathCache.set(threadId, defaultPath); + return defaultPath; + } + + // --- Index Management --- + + async load(): Promise { + if (this.indexLoaded) return; + + await this.ensureFolder(); + const indexPath = this.getIndexPath(); + + try { + if (await this.adapter.exists(indexPath)) { + const content = await this.adapter.read(indexPath); + const snapshots = JSON.parse(content) as ThreadSnapshot[]; + this.threadIndex.clear(); + snapshots.forEach((s) => this.threadIndex.set(s.threadId, s)); + this.indexLoaded = true; + console.log(`ObsidianChatManager: Loaded index with ${this.threadIndex.size} threads`); + } else { + console.log("ObsidianChatManager: Index missing, rebuilding..."); + await this.rebuildIndex(); + } + } catch (e) { + console.error("Error loading chat index:", e); + } + } + + async rebuildIndex(): Promise { + const folder = this.getChatFolder(); + if (!(await this.adapter.exists(folder))) return; + + const result = await this.adapter.list(folder); + this.threadIndex.clear(); + this.filePathCache.clear(); + + for (const file of result.files) { + if (!file.endsWith(".chat")) continue; + + // Yield to event loop + await new Promise((resolve) => setTimeout(resolve, 0)); + + try { + const content = await this.adapter.read(file); + const data = JSON.parse(content) as ThreadData; + if (data && data.threadId) { + // Cache path + this.filePathCache.set(data.threadId, file); + + // Update index + this.threadIndex.set(data.threadId, { + threadId: data.threadId, + title: data.title, + metadata: data.metadata, + createdAt: data.createdAt, + updatedAt: data.updatedAt, + }); + } + } catch (e) { + console.error(`Failed to read ${file} during index rebuild:`, e); + } + } + + this.indexLoaded = true; + await this.saveIndex(); + } + + private async saveIndex() { + const indexPath = this.getIndexPath(); + const snapshots = Array.from(this.threadIndex.values()); + try { + await this.adapter.write(indexPath, JSON.stringify(snapshots, null, 2)); + } catch (e) { + console.error("Error saving chat index:", e); + } + } + + private saveIndexDebounced = debounce( + () => { + this.saveIndex(); + }, + 2000, + true, + ); + + // --- Thread Loading / Saving --- + + async ensureThreadLoaded(threadId: string): Promise { + if (this.storage.has(threadId)) return this.storage.get(threadId); + + const path = await this.resolveFilePath(threadId); + + try { + if (await this.adapter.exists(path)) { + const content = await this.adapter.read(path); + const data = JSON.parse(content) as ThreadData; + this.storage.set(threadId, data); + return data; + } + } catch (e) { + console.error(`Error loading thread ${threadId}:`, e); + } + return undefined; + } + + private createThreadData(threadId: string): ThreadData { + return { + threadId, + createdAt: Date.now(), + updatedAt: Date.now(), + checkpoints: {}, + writes: {}, + }; + } + + private async saveThread(threadId: string) { + const data = this.storage.get(threadId); + if (!data) return; + + await this.ensureFolder(); + const path = await this.resolveFilePath(threadId); + + try { + await this.adapter.write(path, JSON.stringify(data, null, 2)); + + // Update index + this.threadIndex.set(threadId, { + threadId: data.threadId, + title: data.title, + metadata: data.metadata, + createdAt: data.createdAt, + updatedAt: data.updatedAt, + }); + this.saveIndexDebounced(); + } catch (e) { + console.error(`Error saving thread ${threadId}:`, e); + } + } + + private saveDebounced = debounce( + (threadId: string) => { + this.saveThread(threadId); + }, + 1000, + true, + ); + + // --- ThreadStore Implementation --- + + async read(threadId: string, forceReload: boolean = false): Promise { + if (!forceReload && this.threadIndex.has(threadId)) { + return this.threadIndex.get(threadId); + } + + const data = await this.ensureThreadLoaded(threadId); + if (!data) return undefined; + + const snapshot: ThreadSnapshot = { + threadId: data.threadId, + title: data.title, + metadata: data.metadata, + createdAt: data.createdAt, + updatedAt: data.updatedAt, + }; + + if (!this.threadIndex.has(threadId) || forceReload) { + this.threadIndex.set(threadId, snapshot); + } + + return snapshot; + } + + async write(snapshot: ThreadSnapshot): Promise { + let data = await this.ensureThreadLoaded(snapshot.threadId); + + if (!data) { + data = this.createThreadData(snapshot.threadId); + data.createdAt = snapshot.createdAt; + this.storage.set(snapshot.threadId, data); + } + + data.title = snapshot.title; + data.metadata = snapshot.metadata; + data.updatedAt = snapshot.updatedAt; + + this.saveDebounced(snapshot.threadId); + } + + async delete(threadId: string): Promise { + await this.deleteThread(threadId); + } + + async listThreads(): Promise { + await this.load(); + return Array.from(this.threadIndex.values()).sort((a, b) => b.updatedAt - a.updatedAt); + } + + asThreadStore(): ThreadStore { + return { + read: this.read.bind(this), + write: this.write.bind(this), + delete: this.delete.bind(this), + list: this.listThreads.bind(this), + clear: this.clear.bind(this), + }; + } + + async clear(): Promise { + await this.load(); + const ids = Array.from(this.threadIndex.keys()); // Use index keys as source of truth + for (const id of ids) { + await this.deleteThread(id); + } + } + + // --- CheckpointSaver Implementation --- + + async getTuple(config: RunnableConfig): Promise { + const threadId = config.configurable?.thread_id; + if (!threadId) return undefined; + + const threadData = await this.ensureThreadLoaded(threadId); + if (!threadData) return undefined; + + const checkpointId = config.configurable?.checkpoint_id; + + if (checkpointId) { + const entry = threadData.checkpoints[checkpointId]; + if (!entry) return undefined; + + return { + config, + checkpoint: entry.checkpoint, + metadata: entry.metadata, + parentConfig: entry.parentConfig, + pendingWrites: (threadData.writes[checkpointId] || []) as any, + }; + } + + const checkpoints = Object.values(threadData.checkpoints); + if (checkpoints.length === 0) return undefined; + + // Find latest by getting keys and sorting (could rely on insertion order if reliable, but timestamps/keys are safer) + // We use lex sort on keys (checkpoint_ids are usually lex-sortable uuids or similar) + const keys = Object.keys(threadData.checkpoints).sort().reverse(); + const latestId = keys[0]; + const entry = threadData.checkpoints[latestId]; + + return { + config: { ...config, configurable: { ...config.configurable, checkpoint_id: latestId } }, + checkpoint: entry.checkpoint, + metadata: entry.metadata, + parentConfig: entry.parentConfig, + pendingWrites: (threadData.writes[latestId] || []) as any, + }; + } + + async *list(config: RunnableConfig, options?: CheckpointListOptions): AsyncGenerator { + const threadId = config.configurable?.thread_id; + if (!threadId) return; + + const threadData = await this.ensureThreadLoaded(threadId); + if (!threadData) return; + + const keys = Object.keys(threadData.checkpoints).sort().reverse(); + + for (const key of keys) { + const entry = threadData.checkpoints[key]; + if ( + options?.before && + options.before.configurable?.checkpoint_id && + key >= options.before.configurable.checkpoint_id + ) { + continue; + } + + yield { + config: { ...config, configurable: { ...config.configurable, checkpoint_id: key } }, + checkpoint: entry.checkpoint, + metadata: entry.metadata, + parentConfig: entry.parentConfig, + pendingWrites: (threadData.writes[key] || []) as any, + }; + + if (options?.limit && --options.limit <= 0) break; + } + } + + async put( + config: RunnableConfig, + checkpoint: Checkpoint, + metadata: CheckpointMetadata, + newVersions: Record, + ): Promise { + const threadId = config.configurable?.thread_id; + const checkpointId = checkpoint.id; + if (!threadId || !checkpointId) return config; + + let threadData = await this.ensureThreadLoaded(threadId); + if (!threadData) { + threadData = this.createThreadData(threadId); + this.storage.set(threadId, threadData); + } + + // Sanitize to plain JSON + const plainCheckpoint = JSON.parse(JSON.stringify(checkpoint)); + const plainMetadata = JSON.parse(JSON.stringify(metadata)); + + threadData.checkpoints[checkpointId] = { + checkpoint: plainCheckpoint, + metadata: plainMetadata, + parentConfig: config, + }; + + threadData.updatedAt = Date.now(); + this.saveDebounced(threadId); + + // Update index cache immediately + if (this.threadIndex.has(threadId)) { + const snap = this.threadIndex.get(threadId)!; + snap.updatedAt = threadData.updatedAt; + } else { + this.threadIndex.set(threadId, { + threadId: threadData.threadId, + title: threadData.title, + metadata: threadData.metadata, + createdAt: threadData.createdAt, + updatedAt: threadData.updatedAt, + }); + } + // Persist index changes debounced + this.saveIndexDebounced(); + + return { + ...config, + configurable: { + ...config.configurable, + checkpoint_id: checkpointId, + }, + }; + } + + async putWrites(config: RunnableConfig, writes: PendingWrite[], taskId: string): Promise { + const threadId = config.configurable?.thread_id; + const checkpointId = config.configurable?.checkpoint_id; + + if (!threadId || !checkpointId) return; + + let threadData = await this.ensureThreadLoaded(threadId); + if (!threadData) { + threadData = this.createThreadData(threadId); + this.storage.set(threadId, threadData); + } + + if (!threadData.writes[checkpointId]) { + threadData.writes[checkpointId] = []; + } + + threadData.writes[checkpointId].push(...writes); + threadData.updatedAt = Date.now(); + this.saveDebounced(threadId); + + if (this.threadIndex.has(threadId)) { + this.threadIndex.get(threadId)!.updatedAt = threadData.updatedAt; + this.saveIndexDebounced(); + } + } + + async deleteThread(threadId: string): Promise { + // Remove from memory + this.storage.delete(threadId); + this.threadIndex.delete(threadId); + this.filePathCache.delete(threadId); + this.saveIndexDebounced(); + + // Remove from disk + const path = await this.resolveFilePath(threadId); + try { + if (await this.adapter.exists(path)) { + await this.adapter.remove(path); + } + } catch (e) { + console.error(`Error deleting thread ${threadId}:`, e); + } + } + + // --- Utilities --- + + private sanitizeFileName(title: string): string { + return title + .replace(/[<>:"/\\|?*]/g, "-") + .replace(/\s+/g, " ") + .trim() + .substring(0, 100); + } + + async renameChatFile(threadId: string, title: string): Promise { + if (!title || !title.trim()) return; + + try { + const oldPath = await this.resolveFilePath(threadId); + const file = this.plugin.app.vault.getAbstractFileByPath(oldPath); + + if (!file || !(file instanceof TFile)) { + console.warn(`renameChatFile: File not found: ${oldPath}`); + return; + } + + const sanitizedTitle = this.sanitizeFileName(title); + const dateTimePart = threadId.startsWith("Chat ") ? threadId.substring(5) : threadId; + const newFileName = `${sanitizedTitle} - ${dateTimePart}.chat`; + + if (file.name === newFileName) return; + + const folder = this.getChatFolder(); + const newPath = normalizePath(`${folder}/${newFileName}`); + + if (await this.adapter.exists(newPath)) { + console.warn(`renameChatFile: Target file already exists: ${newPath}`); + return; + } + + await this.plugin.app.fileManager.renameFile(file, newPath); + + // Update cache with new path + this.filePathCache.set(threadId, newPath); + console.log(`renameChatFile: Successfully renamed to ${newPath}`); + } catch (error) { + console.error(`Error renaming chat file for thread ${threadId}:`, error); + } + } +} diff --git a/src/agent/prompts.ts b/src/agent/prompts.ts new file mode 100644 index 00000000..cfb05ae9 --- /dev/null +++ b/src/agent/prompts.ts @@ -0,0 +1,76 @@ +export const createSystemPrompt = (hasChartsPlugin: boolean) => `# Role +You are a privacy-aware assistant integrated into Obsidian. You help users search and understand their notes. + +# Tools & Capabilities +- **search_notes**: Finds relevant information from the user's notes. Note that this tool ONLY returns file paths and metadata, not content. +- **read_note**: Reads the full content of a specific note. Use only after identifying it as relevant. +- **get_all_tags**: Discovers available tags in the vault. +- **get_properties**: Retrieves frontmatter properties from notes or discovers available property keys. +- **execute_dataview_query**: Executes Dataview DQL queries for data analysis. + +# Strategy for Finding Notes +1. **Unknown Organization**: If the user asks for a category of notes (e.g. "daily notes", "meetings", "books", "ideas") and you don't know how they are organized: + - Call \`get_all_tags\` FIRST to check if a relevant tag exists (e.g. #daily, #meeting, #book). + - ALSO call \`get_properties\` to check if there are relevant frontmatter properties (e.g. "type", "category", "status"). + - If you find a matching tag or property, use it to filter your Dataview query. + - If no relevant tag or property is found, call \`search_notes\` with a broad term to find example files and see their paths/names/properties. + - **Do NOT guess** tag names, property keys, or folder paths without verifying first. + +2. **Verification**: Before constructing a Dataview query, ALWAYS verify which tags, properties, folders, or keywords actually exist using the steps above. + +3. **Reading Content**: + - \`search_notes\` will give you a list of potential matches with metadata. + - If you need to read the full content of a note to answer a question, use \`read_note\` with the specific file path from the search results. + - If you need to aggregate data (e.g. list tasks, summarize properties), prefer using \`execute_dataview_query\`. + +# Output Options for Dataview & Math + +## 1. Data Analysis +If you need to SEE the results to answer a question or perform analysis, use the \`execute_dataview_query\` tool (supports DQL only). + +## 2. Displaying Lists/Tables +If you want to SHOW the user a list or table (e.g. 'List all my books'), simply output the Dataview DQL query in a markdown code block: +\`\`\`dataview +QUERY +\`\`\` +The chat interface will render this automatically. + +${hasChartsPlugin ? `## 3. Displaying Charts +You can create charts using \`dataviewjs\`. The user has the \`obsidian-charts\` plugin installed, so you can output a \`dataviewjs\` code block that uses \`window.renderChart\`. +**Important**: \`window.renderChart\` takes exactly two arguments: the chart data object and the container element. The chart data object must follow the standard Chart.js format (type, data, options). Use Obsidian CSS variables (e.g., \`var(--interactive-accent)\`) for chart colors to match the theme. + +Example: +\`\`\`dataviewjs +const pages = dv.pages('#games'); +const labels = pages.map(p => p.file.name).values; +const data = pages.map(p => p.rating).values; + +const accentColor = getComputedStyle(document.body).getPropertyValue('--interactive-accent').trim(); +const chartData = { + type: 'bar', + data: { + labels: labels, + datasets: [{ + label: 'Game Ratings', + data: data, + backgroundColor: accentColor, + borderColor: accentColor + }] + } +} +window.renderChart(chartData, this.container); +\`\`\` +The chat interface will render this chart automatically.` : ""} + +## ${hasChartsPlugin ? "4" : "3"}. Math/LaTeX +Supports MathJax rendering. +- Use single dollar signs for inline math: $E=mc^2$ +- Use double dollar signs for block math: + $$ + \int x dx + $$ +- **IMPORTANT**: Do NOT wrap the math in markdown code blocks (like \`\`\`latex or \` ). The renderer needs the raw $ or $$ delimiters to detect and render the math. + +When generating a view (list, table${hasChartsPlugin ? ", or chart" : ""}) for the user, introduce it as "Here is the list:" or "I have generated the view below:", rather than telling the user to run or use the query.`; + +export const AGENT_SYSTEM_PROMPT = createSystemPrompt(false); // Default for backward compatibility diff --git a/src/components/Chat/Input.svelte b/src/components/Chat/Input.svelte index e465df45..4d8cd2de 100755 --- a/src/components/Chat/Input.svelte +++ b/src/components/Chat/Input.svelte @@ -71,8 +71,7 @@ let files: File[] = $state([]); function sendMessage() { - if (!chatModel) return; - messengner.sendMessage(currentSession, inputValue, chatModel, files); + messengner.sendMessage(inputValue, files); files = []; inputValue = ""; } @@ -291,6 +290,17 @@ >{/if}
+
+ AI can make mistakes. Please check important information. + +
diff --git a/v2/src/ui/ChatStreamScratch.svelte b/v2/src/ui/ChatStreamScratch.svelte new file mode 100644 index 00000000..938c0e5a --- /dev/null +++ b/v2/src/ui/ChatStreamScratch.svelte @@ -0,0 +1,352 @@ + + + +
+
+ {#each messages as msg (msg.id)} +
+
+ {msg.role} • {new Date(msg.timestamp).toLocaleTimeString()} +
+
+ {#each msg.content as c} + {c.type === "text" ? c.text : ""} + {/each} +
+ {#if msg.toolCalls?.length} +
+ {#each msg.toolCalls as tc (tc.id)} +
+ {tc.name} + + {tc.status} + + + {tc.output ? JSON.stringify(tc.output) : ""} + +
+ {/each} +
+ {/if} +
+ {/each} +
+ +
+ + +
+
diff --git a/v2/src/ui/ChatView.ts b/v2/src/ui/ChatView.ts new file mode 100644 index 00000000..8182291a --- /dev/null +++ b/v2/src/ui/ChatView.ts @@ -0,0 +1,75 @@ +import { ItemView, WorkspaceLeaf, TFile, FileView } from "obsidian"; +import ChatComponent from "./ChatComponent.svelte"; +import type SecondBrainPlugin from "../../src/main"; + +export const VIEW_TYPE_CHAT = "smart-second-brain-chat"; + +export class ChatView extends FileView { + plugin: SecondBrainPlugin; + component!: ChatComponent; + + constructor(leaf: WorkspaceLeaf, plugin: SecondBrainPlugin) { + super(leaf); + this.plugin = plugin; + } + + getViewType() { + return VIEW_TYPE_CHAT; + } + + getDisplayText() { + if (this.file) { + // Strip .chat extension + return this.file.basename; + } + return "Smart Second Brain"; + } + + getIcon() { + return "message-square"; + } + + async onLoadFile(file: TFile): Promise { + console.log("ChatView onLoadFile"); + await super.onLoadFile(file); + if (this.component) { + // Extract threadId from filename + // Format can be: + // - Chat YYYY-MM-DD HH-MM-SS.chat (before title generation) + // - {title} - YYYY-MM-DD HH-MM-SS.chat (after title generation) + let threadId = file.basename; + if (threadId.includes(" - ")) { + // After title generation: extract date/time part and reconstruct threadId + const parts = threadId.split(" - "); + const dateTimePart = parts[parts.length - 1]; + // Reconstruct threadId with "Chat" prefix + threadId = `Chat ${dateTimePart}`; + } else if (threadId.startsWith("Chat ")) { + // Before title generation: already has "Chat" prefix, use as-is + threadId = threadId; + } + // Otherwise use the whole basename (fallback for old UUID format) + + if (threadId && threadId !== "New Chat") { + // basic check + this.component.$set({ currentThreadId: threadId }); + } + } + } + + async onOpen() { + console.log("ChatView onOpen"); + this.component = new ChatComponent({ + target: this.contentEl, + props: { + plugin: this.plugin, + }, + }); + } + + async onClose() { + if (this.component) { + this.component.$destroy(); + } + } +} diff --git a/v2/src/ui/Logo.svelte b/v2/src/ui/Logo.svelte new file mode 100644 index 00000000..714f9680 --- /dev/null +++ b/v2/src/ui/Logo.svelte @@ -0,0 +1,138 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/v2/src/ui/MessageBubble.svelte b/v2/src/ui/MessageBubble.svelte new file mode 100644 index 00000000..172cb46a --- /dev/null +++ b/v2/src/ui/MessageBubble.svelte @@ -0,0 +1,427 @@ + + +
+
+ {#if message.toolCalls && message.toolCalls.length > 0} +
+
+ + + {toolStatus === "running" ? "⏳" : "🛠️"} + {summaryText} + +
+ {#each message.toolCalls as toolCall (toolCall.id)} +
+
+ + + {#if toolCall.status === "running"} + ⏳ + {:else if toolCall.status === "completed"} + ✅ + {:else} + ❌ + {/if} + + {formatToolName( + toolCall.name, + )} + + +
+
+ Input: + {#if formatToolInput(toolCall.input).length > 0} +
+ {#each formatToolInput(toolCall.input) as { key, value } (key)} +
+ {key}: + {formatValue( + value, + )} +
+ {/each} +
+ {:else} + (empty) + {/if} +
+ {#if toolCall.output} +
+ Output: +
+
+ {/if} +
+
+
+ {/each} +
+
+
+ {/if} + +
+ +
+ {#if isWaitingForDataview && message.role === "assistant"} +
+ + Rendering query... +
+ {/if} +
+
diff --git a/v2/src/ui/chatLogic.ts b/v2/src/ui/chatLogic.ts new file mode 100644 index 00000000..a4baa937 --- /dev/null +++ b/v2/src/ui/chatLogic.ts @@ -0,0 +1,184 @@ +import type { ThreadMessage, ThreadMessageToolCall } from "papa-ts"; +import type { UIMessage, ToolCallState } from "./types"; + +export function processMessages(storedMessages: any[]): UIMessage[] { + if (!storedMessages || storedMessages.length === 0) { + return []; + } + + // First pass: map to basic UI messages + const uiMessages: UIMessage[] = storedMessages.map( + (msg: any) => ({ + ...msg, + id: msg.id || crypto.randomUUID(), + timestamp: msg.timestamp || Date.now(), + // Don't overwrite toolCalls yet, we need to read them! + // But ensure we have a property for Svelte to track if it doesn't exist + _uiToolCalls: [], + }), + ); + + // Second pass: Link tool outputs back to assistant messages + const toolOutputs = new Map(); // tool_call_id -> output message + + for (const msg of uiMessages) { + // Check both camelCase and snake_case + const toolCallId = + (msg as any).tool_call_id || (msg as any).toolCallId; + if (msg.role === "tool" && toolCallId) { + toolOutputs.set(toolCallId, msg); + } + } + + for (const msg of uiMessages) { + // Read from the message properties (preserved from spread) + const rawToolCalls = + (msg as any).tool_calls || (msg as any).toolCalls; + + if ( + msg.role === "assistant" && + rawToolCalls && + rawToolCalls.length > 0 + ) { + if (Array.isArray(rawToolCalls)) { + msg.toolCalls = rawToolCalls.map( + (tc: ThreadMessageToolCall) => { + const id = tc.id; + const name = tc.name; + const args = tc.arguments; + + const outputMsg = toolOutputs.get(id); + + // Handle different input formats (same logic as streaming) + let parsedArgs = args; + if (args === undefined || args === null) { + parsedArgs = {}; + } else if (typeof args === "string") { + // Try to parse as JSON + try { + const parsed = JSON.parse(args); + // Ensure it's an object (not array or primitive) + parsedArgs = + typeof parsed === "object" && + !Array.isArray(parsed) + ? parsed + : { value: parsed }; + } catch { + // If parsing fails, treat as a single string value + parsedArgs = { input: args }; + } + } else if (Array.isArray(args)) { + // If it's an array, wrap it + parsedArgs = { value: args }; + } else if (typeof args !== "object") { + // If it's a primitive, wrap it + parsedArgs = { value: args }; + } + // If it's already an object, use it as-is + + return { + id: id, + name: name, + input: parsedArgs, + // Determine status based on presence of output message + status: outputMsg + ? outputMsg.status === "error" + ? "failed" + : "completed" + : "running", + output: outputMsg + ? outputMsg.content + : undefined, + }; + }, + ); + } + } + } + + // Filter out tool messages as they are now embedded in assistant messages + let filteredMessages = uiMessages.filter( + (msg) => msg.role !== "tool", + ); + + // Merge consecutive assistant messages (tool calls + final response) + return mergeConsecutiveAssistantMessages(filteredMessages); +} + +export function mergeConsecutiveAssistantMessages(msgs: UIMessage[]): UIMessage[] { + const merged: UIMessage[] = []; + let i = 0; + + while (i < msgs.length) { + const current = msgs[i]; + + // If it's not an assistant message, just add it + if (current.role !== "assistant") { + merged.push(current); + i++; + continue; + } + + // Collect consecutive assistant messages + const assistantGroup: UIMessage[] = [current]; + i++; + + while (i < msgs.length && msgs[i].role === "assistant") { + assistantGroup.push(msgs[i]); + i++; + } + + // Merge the group into one message + if (assistantGroup.length === 1) { + merged.push(assistantGroup[0]); + } else { + // Combine all tool calls + const allToolCalls: ToolCallState[] = []; + let finalContent: any = null; + let finalId = assistantGroup[0].id; + let finalTimestamp = assistantGroup[0].timestamp || Date.now(); + + for (const msg of assistantGroup) { + if (msg.toolCalls && msg.toolCalls.length > 0) { + allToolCalls.push(...msg.toolCalls); + } + // Find the message with actual text content (final response) + const content = msg.content?.[0]; + if ( + content && + (content as any).type === "text" && + (content as any).text && + (content as any).text.trim() + ) { + finalContent = msg.content; + finalId = msg.id; + finalTimestamp = msg.timestamp || finalTimestamp; + } + } + + // Create merged message + merged.push({ + ...assistantGroup[assistantGroup.length - 1], // Use last message as base + id: finalId, + timestamp: finalTimestamp, + toolCalls: + allToolCalls.length > 0 ? allToolCalls : undefined, + content: finalContent || assistantGroup[0].content, + }); + } + } + + return merged; +} + +export function createThreadId(): string { + const now = new Date(); + const year = now.getFullYear(); + const month = String(now.getMonth() + 1).padStart(2, "0"); + const day = String(now.getDate()).padStart(2, "0"); + const hours = String(now.getHours()).padStart(2, "0"); + const minutes = String(now.getMinutes()).padStart(2, "0"); + const seconds = String(now.getSeconds()).padStart(2, "0"); + return `Chat ${year}-${month}-${day} ${hours}-${minutes}-${seconds}`; +} + diff --git a/v2/src/ui/types.ts b/v2/src/ui/types.ts new file mode 100644 index 00000000..da63f25b --- /dev/null +++ b/v2/src/ui/types.ts @@ -0,0 +1,16 @@ +import type { ThreadMessage, ThreadMessageToolCall } from "papa-ts"; + +export interface ToolCallState { + id: string; + name: string; + input: any; + status: "running" | "completed" | "failed"; + output?: any; +} + +export interface UIMessage extends Omit { + toolCalls?: ToolCallState[]; + // We need to allow for the raw toolCalls property during processing + tool_calls?: any[]; +} + diff --git a/v2/styles.css b/v2/styles.css new file mode 100644 index 00000000..056c27b4 --- /dev/null +++ b/v2/styles.css @@ -0,0 +1,20 @@ +/* Smart Second Brain Plugin Styles */ + +/* Chart legend background - make transparent to match Obsidian theme */ +.markdown-preview-view canvas + div, +.markdown-preview-view .chartjs-legend, +.message-text canvas + div, +.message-text .chartjs-legend, +.markdown-preview-view div[style*="background"], +.message-text div[style*="background"] { + background: transparent !important; + background-color: transparent !important; +} + +/* Chart container background */ +.markdown-preview-view .chartjs-container, +.message-text .chartjs-container { + background: transparent !important; + background-color: transparent !important; +} + diff --git a/v2/tsconfig.json b/v2/tsconfig.json new file mode 100644 index 00000000..f339e925 --- /dev/null +++ b/v2/tsconfig.json @@ -0,0 +1,23 @@ +{ + "extends": "@tsconfig/svelte/tsconfig.json", + "compilerOptions": { + "baseUrl": ".", + "sourceMap": false, + "inlineSourceMap": true, + "inlineSources": true, + "module": "ESNext", + "target": "ES2020", + "allowJs": true, + "noImplicitAny": true, + "moduleResolution": "node", + "importHelpers": true, + "lib": ["DOM", "ES5", "ES6", "ES2017", "ES2020"], + "skipLibCheck": true, + "strictNullChecks": true, + "resolveJsonModule": true, + "types": ["node", "svelte"] + }, + "include": ["**/*.ts", "**/*.svelte"], + "exclude": ["node_modules"] +} + diff --git a/vite.config.ts b/vite.config.ts index 35fe6473..0c2c5352 100644 --- a/vite.config.ts +++ b/vite.config.ts @@ -41,7 +41,6 @@ export default defineConfig(({ mode }) => { entryFileNames: "main.js", assetFileNames: "styles.css", sourcemapBaseUrl: new URL(setOutDir(mode), import.meta.url).toString(), - // --- Add these two lines to force single file --- manualChunks: undefined, inlineDynamicImports: true, }, From 029100c4ff5ce270104fe11e77fda48543dde097 Mon Sep 17 00:00:00 2001 From: nicobrauchtgit Date: Mon, 22 Dec 2025 23:59:10 +0100 Subject: [PATCH 6/7] so far so good --- AGENTS.md | 47 - bun.lock | 417 +- package.json | 6 +- smart-second-brain | 1 + src/agent/AgentManager.ts | 930 ++-- src/agent/ObsidianChatManager.ts | 110 +- src/agent/prompts.ts | 15 +- src/components/Chat/Input.svelte | 535 +- src/components/Chat/MessageContainer.svelte | 406 +- .../Chat/QuickSettingsDrawer.svelte | 6 +- src/components/Chat/ToolCallsSection.svelte | 226 + src/components/Chat/Toolbar.svelte | 46 - .../Settings/AuthConfigFields.svelte | 50 + .../Settings/ConfiguredProvider.svelte | 53 +- src/components/base/Text.svelte | 133 +- src/components/bitui/ModelPopover.svelte | 32 +- src/components/icons/ProviderIcon.svelte | 2 +- src/main.ts | 185 +- src/stores/chatStore.svelte.ts | 1079 ++-- src/stores/dataStore.svelte.ts | 110 +- src/stores/state.svelte.ts | 50 +- src/styles.css | 10 +- src/types/providers.ts | 200 +- src/utils/dataValidation.ts | 23 + src/utils/query.ts | 36 + src/utils/threadId.ts | 18 +- src/views/Chat/Chat.svelte | 39 +- src/views/Chat/Chat.ts | 95 +- .../ChatModelManagement.svelte | 6 +- .../ChatModelManagement.ts | 80 +- src/views/ProviderSetup/ProviderSetup.svelte | 163 +- src/views/Settings/Settings.svelte | 37 +- tailwind.config.js | 196 +- tsconfig.json | 68 +- v2/.gitignore | 6 - v2/esbuild.config.mjs | 54 - v2/manifest.json | 12 - v2/package-lock.json | 4608 ----------------- v2/package.json | 31 - v2/src/main.ts | 410 -- v2/src/settings.ts | 26 - v2/src/ui/ChatComponent.svelte | 644 --- v2/src/ui/ChatStreamScratch.svelte | 352 -- v2/src/ui/ChatView.ts | 75 - v2/src/ui/Logo.svelte | 138 - v2/src/ui/MessageBubble.svelte | 427 -- v2/src/ui/chatLogic.ts | 184 - v2/src/ui/types.ts | 16 - v2/styles.css | 20 - v2/tsconfig.json | 23 - 50 files changed, 2900 insertions(+), 9536 deletions(-) delete mode 100644 AGENTS.md create mode 120000 smart-second-brain create mode 100644 src/components/Chat/ToolCallsSection.svelte delete mode 100644 src/components/Chat/Toolbar.svelte create mode 100644 src/components/Settings/AuthConfigFields.svelte delete mode 100644 v2/.gitignore delete mode 100644 v2/esbuild.config.mjs delete mode 100644 v2/manifest.json delete mode 100644 v2/package-lock.json delete mode 100644 v2/package.json delete mode 100644 v2/src/main.ts delete mode 100644 v2/src/settings.ts delete mode 100644 v2/src/ui/ChatComponent.svelte delete mode 100644 v2/src/ui/ChatStreamScratch.svelte delete mode 100644 v2/src/ui/ChatView.ts delete mode 100644 v2/src/ui/Logo.svelte delete mode 100644 v2/src/ui/MessageBubble.svelte delete mode 100644 v2/src/ui/chatLogic.ts delete mode 100644 v2/src/ui/types.ts delete mode 100644 v2/styles.css delete mode 100644 v2/tsconfig.json diff --git a/AGENTS.md b/AGENTS.md deleted file mode 100644 index 64c8a391..00000000 --- a/AGENTS.md +++ /dev/null @@ -1,47 +0,0 @@ -# Agent Guidelines (Project Memory) - -Scope: Root of this repository. Applies to all files unless overridden by a deeper AGENTS.md. - -## Core Tech & Syntax -- Use Svelte 5 exclusively. Prefer modern Svelte 5 runes and deep reactivity. -- Runes to use: `$state`, `$props`, `$derived`, `$effect`. Avoid legacy patterns in new code. -- Do not introduce older Svelte 3/4 syntax when runes provide equivalents. - -## Formatting & Linting -- Use Biome for formatting and linting. -- Allowed commands: `biome format --write ./src`, `biome lint --apply-unsafe ./src`. -- Do not add or use ESLint, Prettier, or other linters/formatters. - -## Accessibility Warnings -- Globally suppress Svelte a11y warnings via `onwarn` in both the Vite Svelte plugin and `svelte.config.ts`. -- No per-file a11y comments are required; use them only if needed for non-a11y warnings. - -## TailwindCSS -- Preflight is disabled. Do not enable it. -- Use Obsidian CSS variables (e.g., `var(--color-accent)`, `var(--color-base-XX)`). -- Slate color keys must be strings: `"00"`, `"05"`, `10`, `20`, ..., `100`. -- Content globs: `./src/**/*.{js,svelte,ts}`. - -## Build & Output (Vite) -- Library build targeting Obsidian: single CJS output. -- Output filenames: `main.js` (JS) and `styles.css` (CSS). -- Force single bundle: `manualChunks: undefined`, `inlineDynamicImports: true`. -- `outDir` depends on mode (`development` → `./build/smart-second-brain/`, `production` → `./build/prod`). -- `emptyOutDir` only in production: `mode === "production"`. -- Source maps enabled as configured; `sourcemapBaseUrl` computed without Node globals: - - `sourcemapBaseUrl: new URL(setOutDir(mode), import.meta.url).toString()`. -- Externalize Obsidian/Electron/Codemirror/Lezer/builtin modules. - -## CI & Releases -- No CI workflows at the moment. Do not add or modify CI without explicit request. -- Releases are manual or to be reintroduced later. - -## Development Practices -- Make minimal, surgical changes. Avoid unrelated refactors. -- Do not add license/copyright headers. -- Follow existing project structure under `src/components`, `src/stores`, `src/views`, etc. -- Prefer Bun for install/build if scripts are run (e.g., `bun install`, `bun run build`). - -## Dependencies -- Leave dependency sources/configuration unchanged unless explicitly asked. -- Local `papa-ts` usage may exist; do not alter unless requested. diff --git a/bun.lock b/bun.lock index e07cdc35..862ab8af 100644 --- a/bun.lock +++ b/bun.lock @@ -11,12 +11,15 @@ "builtin-modules": "^5.0.0", "dexie": "^4.2.1", "i18next": "^23.16.8", - "papa-ts": "^2.7.4", "svelte-i18n": "^4.0.1", "uuid": "^11.1.0", + "zod": "^4.2.1", }, "devDependencies": { "@biomejs/biome": "^1.9.4", + "@langchain/langgraph-checkpoint": "^1.0.0", + "@langchain/mcp-adapters": "^1.0.2", + "@langchain/tavily": "^1.0.1", "@sveltejs/vite-plugin-svelte": "^5.1.1", "@tsconfig/svelte": "^5.0.5", "autoprefixer": "^10.4.21", @@ -34,8 +37,6 @@ "packages": { "@alloc/quick-lru": ["@alloc/quick-lru@5.2.0", "", {}, "sha512-UrcABB+4bUrFABwbluTIBErXwvbsU/V7TZWfmbgJfbkwiBuziS9gxdODUyuiecfdGQ85jglMW6juS3+z5TsKLw=="], - "@anthropic-ai/sdk": ["@anthropic-ai/sdk@0.71.2", "", { "dependencies": { "json-schema-to-ts": "^3.1.1" }, "peerDependencies": { "zod": "^3.25.0 || ^4.0.0" }, "optionalPeers": ["zod"], "bin": { "anthropic-ai-sdk": "bin/cli" } }, "sha512-TGNDEUuEstk/DKu0/TflXAEt+p+p/WhTlFzEnoosvbaDU2LTjm42igSdlL0VijrKpWejtOKxX0b8A7uc+XiSAQ=="], - "@babel/runtime": ["@babel/runtime@7.27.6", "", {}, "sha512-vbavdySgbTTrmFE+EsiqUTzlOr5bzlnJtUv9PynGCAKvfQqjIXbvFdumPM/GxMDfyuGMJaJAU6TO4zc1Jf1i8Q=="], "@biomejs/biome": ["@biomejs/biome@1.9.4", "", { "optionalDependencies": { "@biomejs/cli-darwin-arm64": "1.9.4", "@biomejs/cli-darwin-x64": "1.9.4", "@biomejs/cli-linux-arm64": "1.9.4", "@biomejs/cli-linux-arm64-musl": "1.9.4", "@biomejs/cli-linux-x64": "1.9.4", "@biomejs/cli-linux-x64-musl": "1.9.4", "@biomejs/cli-win32-arm64": "1.9.4", "@biomejs/cli-win32-x64": "1.9.4" }, "bin": { "biome": "bin/biome" } }, "sha512-1rkd7G70+o9KkTn5KLmDYXihGoTaIGO9PIIN2ZB7UJxFrWw04CZHPYiMRjYsaDvVV7hP1dYNRLxSANLaBFGpog=="], @@ -62,10 +63,6 @@ "@codemirror/view": ["@codemirror/view@6.37.1", "", { "dependencies": { "@codemirror/state": "^6.5.0", "crelt": "^1.0.6", "style-mod": "^4.1.0", "w3c-keyname": "^2.2.4" } }, "sha512-Qy4CAUwngy/VQkEz0XzMKVRcckQuqLYWKqVpDDDghBe5FSXSqfVrJn49nw3ePZHxRUz4nRmb05Lgi+9csWo4eg=="], - "@colors/colors": ["@colors/colors@1.6.0", "", {}, "sha512-Ir+AOibqzrIsL6ajt3Rz3LskB7OiMVHqltZmspbW/TJuTVuyOMirVqAkjfY6JISiLHgyNqicAC8AyHHGzNd/dA=="], - - "@dabh/diagnostics": ["@dabh/diagnostics@2.0.8", "", { "dependencies": { "@so-ric/colorspace": "^1.1.6", "enabled": "2.0.x", "kuler": "^2.0.0" } }, "sha512-R4MSXTVnuMzGD7bzHdW2ZhhdPC/igELENcq5IjEverBvq5hn1SXCWcsi6eSsdWP0/Ur+SItRRjAktmdoX/8R/Q=="], - "@esbuild/aix-ppc64": ["@esbuild/aix-ppc64@0.25.5", "", { "os": "aix", "cpu": "ppc64" }, "sha512-9o3TMmpmftaCMepOdA5k/yDw8SfInyzWWTjYTFCX3kPSDJMROQTb8jg+h9Cnwnmm1vOzvxN7gIfB5V2ewpjtGA=="], "@esbuild/android-arm": ["@esbuild/android-arm@0.25.5", "", { "os": "android", "cpu": "arm" }, "sha512-AdJKSPeEHgi7/ZhuIPtcQKr5RQdo6OO2IL87JkianiMYMPbCtot9fxPbrMiBADOWWm3T2si9stAiVsGbTQFkbA=="], @@ -132,10 +129,6 @@ "@formatjs/intl-localematcher": ["@formatjs/intl-localematcher@0.6.1", "", { "dependencies": { "tslib": "^2.8.0" } }, "sha512-ePEgLgVCqi2BBFnTMWPfIghu6FkbZnnBVhO2sSxvLfrdFw7wCHAHiDoM2h4NRgjbaY7+B7HgOLZGkK187pZTZg=="], - "@grpc/grpc-js": ["@grpc/grpc-js@1.14.3", "", { "dependencies": { "@grpc/proto-loader": "^0.8.0", "@js-sdsl/ordered-map": "^4.4.2" } }, "sha512-Iq8QQQ/7X3Sac15oB6p0FmUg/klxQvXLeileoqrTRGJYLV+/9tubbr9ipz0GKHjmXVsgFPo/+W+2cA8eNcR+XA=="], - - "@grpc/proto-loader": ["@grpc/proto-loader@0.8.0", "", { "dependencies": { "lodash.camelcase": "^4.3.0", "long": "^5.0.0", "protobufjs": "^7.5.3", "yargs": "^17.7.2" }, "bin": { "proto-loader-gen-types": "build/bin/proto-loader-gen-types.js" } }, "sha512-rc1hOQtjIWGxcxpb9aHAfLpIctjEnsDehj0DAiVfBlmT84uvR0uUtN2hEi/ecvWVjXUGf5qPF4qEgiLOx1YIMQ=="], - "@internationalized/date": ["@internationalized/date@3.9.0", "", { "dependencies": { "@swc/helpers": "^0.5.0" } }, "sha512-yaN3brAnHRD+4KyyOsJyk49XUvj2wtbNACSqg0bz3u8t2VuzhC8Q5dfRnrSxjnnbDb+ienBnkn1TzQfE154vyg=="], "@isaacs/cliui": ["@isaacs/cliui@8.0.2", "", { "dependencies": { "string-width": "^5.1.2", "string-width-cjs": "npm:string-width@^4.2.0", "strip-ansi": "^7.0.1", "strip-ansi-cjs": "npm:strip-ansi@^6.0.1", "wrap-ansi": "^8.1.0", "wrap-ansi-cjs": "npm:wrap-ansi@^7.0.0" } }, "sha512-O8jcjabXaleOG9DQ0+ARXWZBTfnP4WNAqzuiJK7ll44AmxGKv/J2M4TPjxjY3znBCfvBXFzucm1twdyFybFqEA=="], @@ -152,116 +145,30 @@ "@jridgewell/trace-mapping": ["@jridgewell/trace-mapping@0.3.25", "", { "dependencies": { "@jridgewell/resolve-uri": "^3.1.0", "@jridgewell/sourcemap-codec": "^1.4.14" } }, "sha512-vNk6aEwybGtawWmy/PzwnGDOjCkLWSD2wqvjGGAgOAwCGWySYXfYoxt00IJkTF+8Lb57DwOb3Aa0o9CApepiYQ=="], - "@js-sdsl/ordered-map": ["@js-sdsl/ordered-map@4.4.2", "", {}, "sha512-iUKgm52T8HOE/makSxjqoWhe95ZJA1/G1sYsGev2JDKUSS14KAgg1LHb+Ba+IPow0xflbnSkOsZcO08C7w1gYw=="], - - "@langchain/anthropic": ["@langchain/anthropic@1.3.0", "", { "dependencies": { "@anthropic-ai/sdk": "^0.71.0", "zod": "^3.25.76 || ^4" }, "peerDependencies": { "@langchain/core": "1.1.5" } }, "sha512-fqND8Mxy3FaAtZepoYwxUZRLySJ1RC3Uf+Ie9RE3q7YrzJJSc0P0pE9jenEx/jqxnLWGxJtdxB7z0X74KE5reA=="], + "@langchain/core": ["@langchain/core@1.1.6", "", { "dependencies": { "@cfworker/json-schema": "^4.0.2", "ansi-styles": "^5.0.0", "camelcase": "6", "decamelize": "1.2.0", "js-tiktoken": "^1.0.12", "langsmith": "^0.3.82", "mustache": "^4.2.0", "p-queue": "^6.6.2", "uuid": "^10.0.0", "zod": "^3.25.76 || ^4" } }, "sha512-db5H+nLb6rwTW7noIlspN9nDi8b6NeuRWpelzS3+/BuasrJlZ6QbTDxkIqJRTEyLB2av3xOHlYHNmDHKal0XYA=="], - "@langchain/core": ["@langchain/core@1.1.5", "", { "dependencies": { "@cfworker/json-schema": "^4.0.2", "ansi-styles": "^5.0.0", "camelcase": "6", "decamelize": "1.2.0", "js-tiktoken": "^1.0.12", "langsmith": "^0.3.82", "mustache": "^4.2.0", "p-queue": "^6.6.2", "uuid": "^10.0.0", "zod": "^3.25.76 || ^4" } }, "sha512-m+EhnHhaCnVPJt4HRmhElBN3ZBvQGfXL/hm80UV3EHNUPNUCHi6q6de7dqrw/l4oTvmX0nC08Fm2ta1U59o1bQ=="], - - "@langchain/langgraph": ["@langchain/langgraph@1.0.5", "", { "dependencies": { "@langchain/langgraph-checkpoint": "^1.0.0", "@langchain/langgraph-sdk": "~1.3.0", "uuid": "^10.0.0" }, "peerDependencies": { "@langchain/core": "^1.0.1", "zod": "^3.25.32 || ^4.1.0", "zod-to-json-schema": "^3.x" }, "optionalPeers": ["zod-to-json-schema"] }, "sha512-r0strjMmEa4IIcbhXKMubQmhh+WhpKyaRPc00Tj9R6O+Ubf9qsKVSd9F1vZBZ2nC6FYSHxBRGA4fO3KGz2m+DA=="], + "@langchain/langgraph": ["@langchain/langgraph@1.0.7", "", { "dependencies": { "@langchain/langgraph-checkpoint": "^1.0.0", "@langchain/langgraph-sdk": "~1.3.1", "uuid": "^10.0.0" }, "peerDependencies": { "@langchain/core": "^1.0.1", "zod": "^3.25.32 || ^4.1.0", "zod-to-json-schema": "^3.x" }, "optionalPeers": ["zod-to-json-schema"] }, "sha512-EBGqNOWoRiEoLUaeuiXRpUM8/DE6QcwiirNyd97XhezStebBoTTilWH8CUt6S94JRGl5zwfBBRHfzotDnZS/eA=="], "@langchain/langgraph-checkpoint": ["@langchain/langgraph-checkpoint@1.0.0", "", { "dependencies": { "uuid": "^10.0.0" }, "peerDependencies": { "@langchain/core": "^1.0.1" } }, "sha512-xrclBGvNCXDmi0Nz28t3vjpxSH6UYx6w5XAXSiiB1WEdc2xD2iY/a913I3x3a31XpInUW/GGfXXfePfaghV54A=="], - "@langchain/langgraph-sdk": ["@langchain/langgraph-sdk@1.3.0", "", { "dependencies": { "p-queue": "^6.6.2", "p-retry": "4", "uuid": "^9.0.0" }, "peerDependencies": { "@langchain/core": "^1.0.1", "react": "^18 || ^19", "react-dom": "^18 || ^19" }, "optionalPeers": ["@langchain/core", "react", "react-dom"] }, "sha512-4DiGhNpZKFYkBoVbUP38KUMD7EOcLwittXKet0TnkfFDoFvoZm18ygNZV49b6JQL4EsHRjRNVHXwl47HdlGyGA=="], - - "@langchain/ollama": ["@langchain/ollama@1.1.0", "", { "dependencies": { "ollama": "^0.6.3", "uuid": "^10.0.0" }, "peerDependencies": { "@langchain/core": "^1.0.0" } }, "sha512-kEP0zvj+xtJ84QcK1ALKkz71ynpWMgzXbASzabMhkRAMSN/wTVm28HUNPRDHxbS9+BZnq1zcZeuzOf29XCal5g=="], - - "@langchain/openai": ["@langchain/openai@1.2.0", "", { "dependencies": { "js-tiktoken": "^1.0.12", "openai": "^6.10.0", "zod": "^3.25.76 || ^4" }, "peerDependencies": { "@langchain/core": "^1.0.0" } }, "sha512-r2g5Be3Sygw7VTJ89WVM/M94RzYToNTwXf8me1v+kgKxzdHbd/8XPYDFxpXEp3REyPgUrtJs+Oplba9pkTH5ug=="], - - "@langfuse/core": ["@langfuse/core@4.4.9", "", { "peerDependencies": { "@opentelemetry/api": "^1.9.0" } }, "sha512-9Hz/eH6dkOP8E/FLt1fsAQR8RE/TF8Ag/39GmY8JjN1o/Tl/MFJfK2QvqRGrkjDkIkMJGOSD+iQmV2pYm4upDA=="], - - "@langfuse/langchain": ["@langfuse/langchain@4.4.9", "", { "dependencies": { "@langfuse/core": "^4.4.9", "@langfuse/tracing": "^4.4.9" }, "peerDependencies": { "@langchain/core": ">=0.3.0", "@opentelemetry/api": "^1.9.0" } }, "sha512-DG0ar89/Nhs9Lnw6ynTbpOPjuO7DTBv+Y0uYR5qWl5+FLcktPN+HCLGmbpsI+clxJDVhzMyn9rPnT8P/OuiGqg=="], + "@langchain/langgraph-sdk": ["@langchain/langgraph-sdk@1.3.1", "", { "dependencies": { "p-queue": "^6.6.2", "p-retry": "4", "uuid": "^9.0.0" }, "peerDependencies": { "@langchain/core": "^1.0.1", "react": "^18 || ^19", "react-dom": "^18 || ^19" }, "optionalPeers": ["@langchain/core", "react", "react-dom"] }, "sha512-zTi7DZHwqtMEzapvm3I1FL4Q7OZsxtq9tTXy6s2gcCxyIU3sphqRboqytqVN7dNHLdTCLb8nXy49QKurs2MIBg=="], - "@langfuse/otel": ["@langfuse/otel@4.4.9", "", { "dependencies": { "@langfuse/core": "^4.4.9" }, "peerDependencies": { "@opentelemetry/api": "^1.9.0", "@opentelemetry/core": "^2.0.1", "@opentelemetry/exporter-trace-otlp-http": ">=0.202.0 <1.0.0", "@opentelemetry/sdk-trace-base": "^2.0.1" } }, "sha512-T9tSucDC3cvdeUB8fTGXm6ZZcC4kOEreJuM/C66nHQ26+DWtx2AN75JWuadc2E+VU/K+BjTb5XAkBceWYtvXjw=="], + "@langchain/mcp-adapters": ["@langchain/mcp-adapters@1.1.0", "", { "dependencies": { "@modelcontextprotocol/sdk": "~1.19.1", "debug": "^4.4.3", "zod": "^3.25.76 || ^4" }, "optionalDependencies": { "extended-eventsource": "^1.7.0" }, "peerDependencies": { "@langchain/core": "^1.0.0", "@langchain/langgraph": "^1.0.0" } }, "sha512-961bufgmlLBWSJ3kA1vJbocM1v678D6a4e/NXOxE4KsSslpJZvaz5XmTmpHa5XBM5wKcUOjDdJdvLuOC2Pw5KQ=="], - "@langfuse/tracing": ["@langfuse/tracing@4.4.9", "", { "dependencies": { "@langfuse/core": "^4.4.9" }, "peerDependencies": { "@opentelemetry/api": "^1.9.0" } }, "sha512-if+G/v9NsyTKj40KKX96bRSdMXwyDbVL4GJQvmwQ9SxvGYF+d99pGFB7L6QOeCd1KBHMdmDe733ncmvCnSHJ9w=="], + "@langchain/tavily": ["@langchain/tavily@1.1.0", "", { "dependencies": { "zod": "^3.25.76 || ^4" }, "peerDependencies": { "@langchain/core": "^1.0.0" } }, "sha512-RkvBT//wMioKM3O8LrlvzweYJFL6Srhdz0cjVTodZsxQy0FedJ5DQXJ36Ul/11bRES1Oe/XOW8vT7D+fSxJ92Q=="], "@marijn/find-cluster-break": ["@marijn/find-cluster-break@1.0.2", "", {}, "sha512-l0h88YhZFyKdXIFNfSWpyjStDjGHwZ/U7iobcK1cQQD8sejsONdQtTVU+1wVN1PBw40PiiHB1vA5S7VTfQiP9g=="], + "@modelcontextprotocol/sdk": ["@modelcontextprotocol/sdk@1.19.1", "", { "dependencies": { "ajv": "^6.12.6", "content-type": "^1.0.5", "cors": "^2.8.5", "cross-spawn": "^7.0.5", "eventsource": "^3.0.2", "eventsource-parser": "^3.0.0", "express": "^5.0.1", "express-rate-limit": "^7.5.0", "pkce-challenge": "^5.0.0", "raw-body": "^3.0.0", "zod": "^3.23.8", "zod-to-json-schema": "^3.24.1" } }, "sha512-3Y2h3MZKjec1eAqSTBclATlX+AbC6n1LgfVzRMJLt3v6w0RCYgwLrjbxPDbhsYHt6Wdqc/aCceNJYgj448ELQQ=="], + "@nodelib/fs.scandir": ["@nodelib/fs.scandir@2.1.5", "", { "dependencies": { "@nodelib/fs.stat": "2.0.5", "run-parallel": "^1.1.9" } }, "sha512-vq24Bq3ym5HEQm2NKCr3yXDwjc7vTsEThRDnkp2DK9p1uqLR+DHurm/NOTo0KG7HYHU7eppKZj3MyqYuMBf62g=="], "@nodelib/fs.stat": ["@nodelib/fs.stat@2.0.5", "", {}, "sha512-RkhPPp2zrqDAQA/2jNhnztcPAlv64XdhIp7a7454A5ovI7Bukxgt7MX7udwAu3zg1DcpPU0rz3VV1SeaqvY4+A=="], "@nodelib/fs.walk": ["@nodelib/fs.walk@1.2.8", "", { "dependencies": { "@nodelib/fs.scandir": "2.1.5", "fastq": "^1.6.0" } }, "sha512-oGB+UxlgWcgQkgwo8GcEGwemoTFt3FIO9ababBmaGwXIoBKZ+GTy0pP185beGg7Llih/NSHSV2XAs1lnznocSg=="], - "@opentelemetry/api": ["@opentelemetry/api@1.9.0", "", {}, "sha512-3giAOQvZiH5F9bMlMiv8+GSPMeqg0dbaeo58/0SlA9sxSqZhnUtxzX9/2FzyhS9sWQf5S0GJE0AKBrFqjpeYcg=="], - - "@opentelemetry/api-logs": ["@opentelemetry/api-logs@0.208.0", "", { "dependencies": { "@opentelemetry/api": "^1.3.0" } }, "sha512-CjruKY9V6NMssL/T1kAFgzosF1v9o6oeN+aX5JB/C/xPNtmgIJqcXHG7fA82Ou1zCpWGl4lROQUKwUNE1pMCyg=="], - - "@opentelemetry/context-async-hooks": ["@opentelemetry/context-async-hooks@2.2.0", "", { "peerDependencies": { "@opentelemetry/api": ">=1.0.0 <1.10.0" } }, "sha512-qRkLWiUEZNAmYapZ7KGS5C4OmBLcP/H2foXeOEaowYCR0wi89fHejrfYfbuLVCMLp/dWZXKvQusdbUEZjERfwQ=="], - - "@opentelemetry/core": ["@opentelemetry/core@2.2.0", "", { "dependencies": { "@opentelemetry/semantic-conventions": "^1.29.0" }, "peerDependencies": { "@opentelemetry/api": ">=1.0.0 <1.10.0" } }, "sha512-FuabnnUm8LflnieVxs6eP7Z383hgQU4W1e3KJS6aOG3RxWxcHyBxH8fDMHNgu/gFx/M2jvTOW/4/PHhLz6bjWw=="], - - "@opentelemetry/exporter-logs-otlp-grpc": ["@opentelemetry/exporter-logs-otlp-grpc@0.208.0", "", { "dependencies": { "@grpc/grpc-js": "^1.7.1", "@opentelemetry/core": "2.2.0", "@opentelemetry/otlp-exporter-base": "0.208.0", "@opentelemetry/otlp-grpc-exporter-base": "0.208.0", "@opentelemetry/otlp-transformer": "0.208.0", "@opentelemetry/sdk-logs": "0.208.0" }, "peerDependencies": { "@opentelemetry/api": "^1.3.0" } }, "sha512-AmZDKFzbq/idME/yq68M155CJW1y056MNBekH9OZewiZKaqgwYN4VYfn3mXVPftYsfrCM2r4V6tS8H2LmfiDCg=="], - - "@opentelemetry/exporter-logs-otlp-http": ["@opentelemetry/exporter-logs-otlp-http@0.208.0", "", { "dependencies": { "@opentelemetry/api-logs": "0.208.0", "@opentelemetry/core": "2.2.0", "@opentelemetry/otlp-exporter-base": "0.208.0", "@opentelemetry/otlp-transformer": "0.208.0", "@opentelemetry/sdk-logs": "0.208.0" }, "peerDependencies": { "@opentelemetry/api": "^1.3.0" } }, "sha512-jOv40Bs9jy9bZVLo/i8FwUiuCvbjWDI+ZW13wimJm4LjnlwJxGgB+N/VWOZUTpM+ah/awXeQqKdNlpLf2EjvYg=="], - - "@opentelemetry/exporter-logs-otlp-proto": ["@opentelemetry/exporter-logs-otlp-proto@0.208.0", "", { "dependencies": { "@opentelemetry/api-logs": "0.208.0", "@opentelemetry/core": "2.2.0", "@opentelemetry/otlp-exporter-base": "0.208.0", "@opentelemetry/otlp-transformer": "0.208.0", "@opentelemetry/resources": "2.2.0", "@opentelemetry/sdk-logs": "0.208.0", "@opentelemetry/sdk-trace-base": "2.2.0" }, "peerDependencies": { "@opentelemetry/api": "^1.3.0" } }, "sha512-Wy8dZm16AOfM7yddEzSFzutHZDZ6HspKUODSUJVjyhnZFMBojWDjSNgduyCMlw6qaxJYz0dlb0OEcb4Eme+BfQ=="], - - "@opentelemetry/exporter-metrics-otlp-grpc": ["@opentelemetry/exporter-metrics-otlp-grpc@0.208.0", "", { "dependencies": { "@grpc/grpc-js": "^1.7.1", "@opentelemetry/core": "2.2.0", "@opentelemetry/exporter-metrics-otlp-http": "0.208.0", "@opentelemetry/otlp-exporter-base": "0.208.0", "@opentelemetry/otlp-grpc-exporter-base": "0.208.0", "@opentelemetry/otlp-transformer": "0.208.0", "@opentelemetry/resources": "2.2.0", "@opentelemetry/sdk-metrics": "2.2.0" }, "peerDependencies": { "@opentelemetry/api": "^1.3.0" } }, "sha512-YbEnk7jjYmvhIwp2xJGkEvdgnayrA2QSr28R1LR1klDPvCxsoQPxE6TokDbQpoCEhD3+KmJVEXfb4EeEQxjymg=="], - - "@opentelemetry/exporter-metrics-otlp-http": ["@opentelemetry/exporter-metrics-otlp-http@0.208.0", "", { "dependencies": { "@opentelemetry/core": "2.2.0", "@opentelemetry/otlp-exporter-base": "0.208.0", "@opentelemetry/otlp-transformer": "0.208.0", "@opentelemetry/resources": "2.2.0", "@opentelemetry/sdk-metrics": "2.2.0" }, "peerDependencies": { "@opentelemetry/api": "^1.3.0" } }, "sha512-QZ3TrI90Y0i1ezWQdvreryjY0a5TK4J9gyDLIyhLBwV+EQUvyp5wR7TFPKCAexD4TDSWM0t3ulQDbYYjVtzTyA=="], - - "@opentelemetry/exporter-metrics-otlp-proto": ["@opentelemetry/exporter-metrics-otlp-proto@0.208.0", "", { "dependencies": { "@opentelemetry/core": "2.2.0", "@opentelemetry/exporter-metrics-otlp-http": "0.208.0", "@opentelemetry/otlp-exporter-base": "0.208.0", "@opentelemetry/otlp-transformer": "0.208.0", "@opentelemetry/resources": "2.2.0", "@opentelemetry/sdk-metrics": "2.2.0" }, "peerDependencies": { "@opentelemetry/api": "^1.3.0" } }, "sha512-CvvVD5kRDmRB/uSMalvEF6kiamY02pB46YAqclHtfjJccNZFxbkkXkMMmcJ7NgBFa5THmQBNVQ2AHyX29nRxOw=="], - - "@opentelemetry/exporter-prometheus": ["@opentelemetry/exporter-prometheus@0.208.0", "", { "dependencies": { "@opentelemetry/core": "2.2.0", "@opentelemetry/resources": "2.2.0", "@opentelemetry/sdk-metrics": "2.2.0" }, "peerDependencies": { "@opentelemetry/api": "^1.3.0" } }, "sha512-Rgws8GfIfq2iNWCD3G1dTD9xwYsCof1+tc5S5X0Ahdb5CrAPE+k5P70XCWHqrFFurVCcKaHLJ/6DjIBHWVfLiw=="], - - "@opentelemetry/exporter-trace-otlp-grpc": ["@opentelemetry/exporter-trace-otlp-grpc@0.208.0", "", { "dependencies": { "@grpc/grpc-js": "^1.7.1", "@opentelemetry/core": "2.2.0", "@opentelemetry/otlp-exporter-base": "0.208.0", "@opentelemetry/otlp-grpc-exporter-base": "0.208.0", "@opentelemetry/otlp-transformer": "0.208.0", "@opentelemetry/resources": "2.2.0", "@opentelemetry/sdk-trace-base": "2.2.0" }, "peerDependencies": { "@opentelemetry/api": "^1.3.0" } }, "sha512-E/eNdcqVUTAT7BC+e8VOw/krqb+5rjzYkztMZ/o+eyJl+iEY6PfczPXpwWuICwvsm0SIhBoh9hmYED5Vh5RwIw=="], - - "@opentelemetry/exporter-trace-otlp-http": ["@opentelemetry/exporter-trace-otlp-http@0.208.0", "", { "dependencies": { "@opentelemetry/core": "2.2.0", "@opentelemetry/otlp-exporter-base": "0.208.0", "@opentelemetry/otlp-transformer": "0.208.0", "@opentelemetry/resources": "2.2.0", "@opentelemetry/sdk-trace-base": "2.2.0" }, "peerDependencies": { "@opentelemetry/api": "^1.3.0" } }, "sha512-jbzDw1q+BkwKFq9yxhjAJ9rjKldbt5AgIy1gmEIJjEV/WRxQ3B6HcLVkwbjJ3RcMif86BDNKR846KJ0tY0aOJA=="], - - "@opentelemetry/exporter-trace-otlp-proto": ["@opentelemetry/exporter-trace-otlp-proto@0.208.0", "", { "dependencies": { "@opentelemetry/core": "2.2.0", "@opentelemetry/otlp-exporter-base": "0.208.0", "@opentelemetry/otlp-transformer": "0.208.0", "@opentelemetry/resources": "2.2.0", "@opentelemetry/sdk-trace-base": "2.2.0" }, "peerDependencies": { "@opentelemetry/api": "^1.3.0" } }, "sha512-q844Jc3ApkZVdWYd5OAl+an3n1XXf3RWHa3Zgmnhw3HpsM3VluEKHckUUEqHPzbwDUx2lhPRVkqK7LsJ/CbDzA=="], - - "@opentelemetry/exporter-zipkin": ["@opentelemetry/exporter-zipkin@2.2.0", "", { "dependencies": { "@opentelemetry/core": "2.2.0", "@opentelemetry/resources": "2.2.0", "@opentelemetry/sdk-trace-base": "2.2.0", "@opentelemetry/semantic-conventions": "^1.29.0" }, "peerDependencies": { "@opentelemetry/api": "^1.0.0" } }, "sha512-VV4QzhGCT7cWrGasBWxelBjqbNBbyHicWWS/66KoZoe9BzYwFB72SH2/kkc4uAviQlO8iwv2okIJy+/jqqEHTg=="], - - "@opentelemetry/instrumentation": ["@opentelemetry/instrumentation@0.208.0", "", { "dependencies": { "@opentelemetry/api-logs": "0.208.0", "import-in-the-middle": "^2.0.0", "require-in-the-middle": "^8.0.0" }, "peerDependencies": { "@opentelemetry/api": "^1.3.0" } }, "sha512-Eju0L4qWcQS+oXxi6pgh7zvE2byogAkcsVv0OjHF/97iOz1N/aKE6etSGowYkie+YA1uo6DNwdSxaaNnLvcRlA=="], - - "@opentelemetry/otlp-exporter-base": ["@opentelemetry/otlp-exporter-base@0.208.0", "", { "dependencies": { "@opentelemetry/core": "2.2.0", "@opentelemetry/otlp-transformer": "0.208.0" }, "peerDependencies": { "@opentelemetry/api": "^1.3.0" } }, "sha512-gMd39gIfVb2OgxldxUtOwGJYSH8P1kVFFlJLuut32L6KgUC4gl1dMhn+YC2mGn0bDOiQYSk/uHOdSjuKp58vvA=="], - - "@opentelemetry/otlp-grpc-exporter-base": ["@opentelemetry/otlp-grpc-exporter-base@0.208.0", "", { "dependencies": { "@grpc/grpc-js": "^1.7.1", "@opentelemetry/core": "2.2.0", "@opentelemetry/otlp-exporter-base": "0.208.0", "@opentelemetry/otlp-transformer": "0.208.0" }, "peerDependencies": { "@opentelemetry/api": "^1.3.0" } }, "sha512-fGvAg3zb8fC0oJAzfz7PQppADI2HYB7TSt/XoCaBJFi1mSquNUjtHXEoviMgObLAa1NRIgOC1lsV1OUKi+9+lQ=="], - - "@opentelemetry/otlp-transformer": ["@opentelemetry/otlp-transformer@0.208.0", "", { "dependencies": { "@opentelemetry/api-logs": "0.208.0", "@opentelemetry/core": "2.2.0", "@opentelemetry/resources": "2.2.0", "@opentelemetry/sdk-logs": "0.208.0", "@opentelemetry/sdk-metrics": "2.2.0", "@opentelemetry/sdk-trace-base": "2.2.0", "protobufjs": "^7.3.0" }, "peerDependencies": { "@opentelemetry/api": "^1.3.0" } }, "sha512-DCFPY8C6lAQHUNkzcNT9R+qYExvsk6C5Bto2pbNxgicpcSWbe2WHShLxkOxIdNcBiYPdVHv/e7vH7K6TI+C+fQ=="], - - "@opentelemetry/propagator-b3": ["@opentelemetry/propagator-b3@2.2.0", "", { "dependencies": { "@opentelemetry/core": "2.2.0" }, "peerDependencies": { "@opentelemetry/api": ">=1.0.0 <1.10.0" } }, "sha512-9CrbTLFi5Ee4uepxg2qlpQIozoJuoAZU5sKMx0Mn7Oh+p7UrgCiEV6C02FOxxdYVRRFQVCinYR8Kf6eMSQsIsw=="], - - "@opentelemetry/propagator-jaeger": ["@opentelemetry/propagator-jaeger@2.2.0", "", { "dependencies": { "@opentelemetry/core": "2.2.0" }, "peerDependencies": { "@opentelemetry/api": ">=1.0.0 <1.10.0" } }, "sha512-FfeOHOrdhiNzecoB1jZKp2fybqmqMPJUXe2ZOydP7QzmTPYcfPeuaclTLYVhK3HyJf71kt8sTl92nV4YIaLaKA=="], - - "@opentelemetry/resources": ["@opentelemetry/resources@2.2.0", "", { "dependencies": { "@opentelemetry/core": "2.2.0", "@opentelemetry/semantic-conventions": "^1.29.0" }, "peerDependencies": { "@opentelemetry/api": ">=1.3.0 <1.10.0" } }, "sha512-1pNQf/JazQTMA0BiO5NINUzH0cbLbbl7mntLa4aJNmCCXSj0q03T5ZXXL0zw4G55TjdL9Tz32cznGClf+8zr5A=="], - - "@opentelemetry/sdk-logs": ["@opentelemetry/sdk-logs@0.208.0", "", { "dependencies": { "@opentelemetry/api-logs": "0.208.0", "@opentelemetry/core": "2.2.0", "@opentelemetry/resources": "2.2.0" }, "peerDependencies": { "@opentelemetry/api": ">=1.4.0 <1.10.0" } }, "sha512-QlAyL1jRpOeaqx7/leG1vJMp84g0xKP6gJmfELBpnI4O/9xPX+Hu5m1POk9Kl+veNkyth5t19hRlN6tNY1sjbA=="], - - "@opentelemetry/sdk-metrics": ["@opentelemetry/sdk-metrics@2.2.0", "", { "dependencies": { "@opentelemetry/core": "2.2.0", "@opentelemetry/resources": "2.2.0" }, "peerDependencies": { "@opentelemetry/api": ">=1.9.0 <1.10.0" } }, "sha512-G5KYP6+VJMZzpGipQw7Giif48h6SGQ2PFKEYCybeXJsOCB4fp8azqMAAzE5lnnHK3ZVwYQrgmFbsUJO/zOnwGw=="], - - "@opentelemetry/sdk-node": ["@opentelemetry/sdk-node@0.208.0", "", { "dependencies": { "@opentelemetry/api-logs": "0.208.0", "@opentelemetry/core": "2.2.0", "@opentelemetry/exporter-logs-otlp-grpc": "0.208.0", "@opentelemetry/exporter-logs-otlp-http": "0.208.0", "@opentelemetry/exporter-logs-otlp-proto": "0.208.0", "@opentelemetry/exporter-metrics-otlp-grpc": "0.208.0", "@opentelemetry/exporter-metrics-otlp-http": "0.208.0", "@opentelemetry/exporter-metrics-otlp-proto": "0.208.0", "@opentelemetry/exporter-prometheus": "0.208.0", "@opentelemetry/exporter-trace-otlp-grpc": "0.208.0", "@opentelemetry/exporter-trace-otlp-http": "0.208.0", "@opentelemetry/exporter-trace-otlp-proto": "0.208.0", "@opentelemetry/exporter-zipkin": "2.2.0", "@opentelemetry/instrumentation": "0.208.0", "@opentelemetry/propagator-b3": "2.2.0", "@opentelemetry/propagator-jaeger": "2.2.0", "@opentelemetry/resources": "2.2.0", "@opentelemetry/sdk-logs": "0.208.0", "@opentelemetry/sdk-metrics": "2.2.0", "@opentelemetry/sdk-trace-base": "2.2.0", "@opentelemetry/sdk-trace-node": "2.2.0", "@opentelemetry/semantic-conventions": "^1.29.0" }, "peerDependencies": { "@opentelemetry/api": ">=1.3.0 <1.10.0" } }, "sha512-pbAqpZ7zTMFuTf3YecYsecsto/mheuvnK2a/jgstsE5ynWotBjgF5bnz5500W9Xl2LeUfg04WMt63TWtAgzRMw=="], - - "@opentelemetry/sdk-trace-base": ["@opentelemetry/sdk-trace-base@2.2.0", "", { "dependencies": { "@opentelemetry/core": "2.2.0", "@opentelemetry/resources": "2.2.0", "@opentelemetry/semantic-conventions": "^1.29.0" }, "peerDependencies": { "@opentelemetry/api": ">=1.3.0 <1.10.0" } }, "sha512-xWQgL0Bmctsalg6PaXExmzdedSp3gyKV8mQBwK/j9VGdCDu2fmXIb2gAehBKbkXCpJ4HPkgv3QfoJWRT4dHWbw=="], - - "@opentelemetry/sdk-trace-node": ["@opentelemetry/sdk-trace-node@2.2.0", "", { "dependencies": { "@opentelemetry/context-async-hooks": "2.2.0", "@opentelemetry/core": "2.2.0", "@opentelemetry/sdk-trace-base": "2.2.0" }, "peerDependencies": { "@opentelemetry/api": ">=1.0.0 <1.10.0" } }, "sha512-+OaRja3f0IqGG2kptVeYsrZQK9nKRSpfFrKtRBq4uh6nIB8bTBgaGvYQrQoRrQWQMA5dK5yLhDMDc0dvYvCOIQ=="], - - "@opentelemetry/semantic-conventions": ["@opentelemetry/semantic-conventions@1.38.0", "", {}, "sha512-kocjix+/sSggfJhwXqClZ3i9Y/MI0fp7b+g7kCRm6psy2dsf8uApTRclwG18h8Avm7C9+fnt+O36PspJ/OzoWg=="], - "@pkgjs/parseargs": ["@pkgjs/parseargs@0.11.0", "", {}, "sha512-+1VkjdD0QBLPodGrJUeqarH8VAIvQODIbwh9XpP5Syisf7YoQgsJKPNFoqqLQlu+VQ/tVSshMR6loPMn8U+dPg=="], - "@protobufjs/aspromise": ["@protobufjs/aspromise@1.1.2", "", {}, "sha512-j+gKExEuLmKwvz3OgROXtrJ2UG2x8Ch2YZUxahh+s1F2HZ+wAceUNLkvy6zKCPVRkU++ZWQrdxsUeQXmcg4uoQ=="], - - "@protobufjs/base64": ["@protobufjs/base64@1.1.2", "", {}, "sha512-AZkcAA5vnN/v4PDqKyMR5lx7hZttPDgClv83E//FMNhR2TMcLUhfRUBHCmSl0oi9zMgDDqRUJkSxO3wm85+XLg=="], - - "@protobufjs/codegen": ["@protobufjs/codegen@2.0.4", "", {}, "sha512-YyFaikqM5sH0ziFZCN3xDC7zeGaB/d0IUb9CATugHWbd1FRFwWwt4ld4OYMPWu5a3Xe01mGAULCdqhMlPl29Jg=="], - - "@protobufjs/eventemitter": ["@protobufjs/eventemitter@1.1.0", "", {}, "sha512-j9ednRT81vYJ9OfVuXG6ERSTdEL1xVsNgqpkxMsbIabzSo3goCjDIveeGv5d03om39ML71RdmrGNjG5SReBP/Q=="], - - "@protobufjs/fetch": ["@protobufjs/fetch@1.1.0", "", { "dependencies": { "@protobufjs/aspromise": "^1.1.1", "@protobufjs/inquire": "^1.1.0" } }, "sha512-lljVXpqXebpsijW71PZaCYeIcE5on1w5DlQy5WH6GLbFryLUrBD4932W/E2BSpfRJWseIL4v/KPgBFxDOIdKpQ=="], - - "@protobufjs/float": ["@protobufjs/float@1.0.2", "", {}, "sha512-Ddb+kVXlXst9d+R9PfTIxh1EdNkgoRe5tOX6t01f1lYWOvJnSPDBlG241QLzcyPdoNTsblLUdujGSE4RzrTZGQ=="], - - "@protobufjs/inquire": ["@protobufjs/inquire@1.1.0", "", {}, "sha512-kdSefcPdruJiFMVSbn801t4vFK7KB/5gd2fYvrxhuJYg8ILrmn9SKSX2tZdV6V+ksulWqS7aXjBcRXl3wHoD9Q=="], - - "@protobufjs/path": ["@protobufjs/path@1.1.2", "", {}, "sha512-6JOcJ5Tm08dOHAbdR3GrvP+yUUfkjG5ePsHYczMFLq3ZmMkAD98cDgcT2iA1lJ9NVwFd4tH/iSSoe44YWkltEA=="], - - "@protobufjs/pool": ["@protobufjs/pool@1.1.0", "", {}, "sha512-0kELaGSIDBKvcgS4zkjz1PeddatrjYcmMWOlAuAPwAeccUrPHdUqo/J6LiymHHEiJT5NrF1UVwxY14f+fy4WQw=="], - - "@protobufjs/utf8": ["@protobufjs/utf8@1.1.0", "", {}, "sha512-Vvn3zZrhQZkkBE8LSuW3em98c0FwgO4nxzv6OdSxPKJIEKY2bGbHn+mhGIPerzI4twdxaP8/0+06HBpwf345Lw=="], - "@rollup/rollup-android-arm-eabi": ["@rollup/rollup-android-arm-eabi@4.53.3", "", { "os": "android", "cpu": "arm" }, "sha512-mRSi+4cBjrRLoaal2PnqH82Wqyb+d3HsPUN/W+WslCXsZsyHa9ZeQQX/pQsZaVIWDkPcpV6jJ+3KLbTbgnwv8w=="], "@rollup/rollup-android-arm64": ["@rollup/rollup-android-arm64@4.53.3", "", { "os": "android", "cpu": "arm64" }, "sha512-CbDGaMpdE9sh7sCmTrTUyllhrg65t6SwhjlMJsLr+J8YjFuPmCEjbBSx4Z/e4SmDyH3aB5hGaJUP2ltV/vcs4w=="], @@ -306,36 +213,8 @@ "@rollup/rollup-win32-x64-msvc": ["@rollup/rollup-win32-x64-msvc@4.53.3", "", { "os": "win32", "cpu": "x64" }, "sha512-UhTd8u31dXadv0MopwGgNOBpUVROFKWVQgAg5N1ESyCz8AuBcMqm4AuTjrwgQKGDfoFuz02EuMRHQIw/frmYKQ=="], - "@sap-ai-sdk/ai-api": ["@sap-ai-sdk/ai-api@2.3.0", "", { "dependencies": { "@sap-ai-sdk/core": "^2.3.0", "@sap-cloud-sdk/connectivity": "^4.1.2", "@sap-cloud-sdk/util": "^4.1.2" } }, "sha512-qlNqJvYqnqOyqQHfJrYVzU4nJVQYoCr0WUG+9ISrQ6deOPLWMZIip+6J3hZTW/TszmnSYi/UN/eTQ2hXUghtuw=="], - - "@sap-ai-sdk/core": ["@sap-ai-sdk/core@2.3.0", "", { "dependencies": { "@sap-cloud-sdk/connectivity": "^4.1.2", "@sap-cloud-sdk/http-client": "^4.1.2", "@sap-cloud-sdk/openapi": "^4.1.2", "@sap-cloud-sdk/util": "^4.1.2" } }, "sha512-1eoIte1BNDlVfn+2L8UCXkQi0W3Q3vUp4wyjUXVDBV5OStf5AMWLcr4/fwR/tId/S05zOnmXA0kK3Jn4QB8ykw=="], - - "@sap-ai-sdk/foundation-models": ["@sap-ai-sdk/foundation-models@2.3.0", "", { "dependencies": { "@sap-ai-sdk/ai-api": "^2.3.0", "@sap-ai-sdk/core": "^2.3.0", "@sap-cloud-sdk/connectivity": "^4.1.2", "@sap-cloud-sdk/http-client": "^4.1.2", "@sap-cloud-sdk/util": "^4.1.2" } }, "sha512-XY/Z9YHj/6HsK9FS4dYXfR5evjnW47F0C5UFSNfwk7hcROixs1qIS2Oc3a2dTm8H4TFb0FLwg0aJtqiSPJmGUQ=="], - - "@sap-ai-sdk/langchain": ["@sap-ai-sdk/langchain@2.3.0", "", { "dependencies": { "@langchain/core": "^1.1.0", "@sap-ai-sdk/ai-api": "^2.3.0", "@sap-ai-sdk/core": "^2.3.0", "@sap-ai-sdk/foundation-models": "^2.3.0", "@sap-ai-sdk/orchestration": "^2.3.0", "@sap-cloud-sdk/connectivity": "^4.1.2", "@sap-cloud-sdk/util": "^4.1.2", "uuid": "^13.0.0" } }, "sha512-5aniGM14dYkemO0LZJ4pWnm6Ra0+S5N1e1tQ08fbTy3DQyfrBbtd9V8yKLqK/8bEB777kmcj0D5tPnwKjelpOw=="], - - "@sap-ai-sdk/orchestration": ["@sap-ai-sdk/orchestration@2.3.0", "", { "dependencies": { "@sap-ai-sdk/ai-api": "^2.3.0", "@sap-ai-sdk/core": "^2.3.0", "@sap-ai-sdk/prompt-registry": "^2.3.0", "@sap-cloud-sdk/util": "^4.1.2", "yaml": "^2.8.1" } }, "sha512-qbf80V08BaFpQnwKWia5jyIjDVRUKaGn2UFYC9BDXO5YjLrV26znroGBzNVvFP/hp5yfBHVnrBK7imfLD8TZFA=="], - - "@sap-ai-sdk/prompt-registry": ["@sap-ai-sdk/prompt-registry@2.3.0", "", { "dependencies": { "@sap-ai-sdk/core": "^2.3.0", "zod": "^4.1.12" } }, "sha512-7Bi4K1zjZzTKt7UB69//XK94EbVYMJRhfFYWTFtLpt6vbgO7n+KsSSYAuxzhKNCuYKv20yyx+mEfhbUxNGh99w=="], - - "@sap-cloud-sdk/connectivity": ["@sap-cloud-sdk/connectivity@4.2.0", "", { "dependencies": { "@sap-cloud-sdk/resilience": "^4.2.0", "@sap-cloud-sdk/util": "^4.2.0", "@sap/xsenv": "^6.0.0", "@sap/xssec": "^4.11.2", "async-retry": "^1.3.3", "axios": "^1.13.2", "jsonwebtoken": "^9.0.2" } }, "sha512-dvQpjYWp9EhoUip4ftvnsVOG6BHJO+fOOuVs0R7V1IRyl7F49QPdpI/YoMzk3W7Rex9NozRa/0EXAe9L0CrFbA=="], - - "@sap-cloud-sdk/http-client": ["@sap-cloud-sdk/http-client@4.2.0", "", { "dependencies": { "@sap-cloud-sdk/connectivity": "^4.2.0", "@sap-cloud-sdk/resilience": "^4.2.0", "@sap-cloud-sdk/util": "^4.2.0", "axios": "^1.13.2" } }, "sha512-jpMeQpcyY3wfEbNlo0yqgu6jp+Rr3nOBYPt/k6GdjgR9qQFPgY1m2ZEsyd8B1Dhzb+BS3iW7fHunshVvGjCgtQ=="], - - "@sap-cloud-sdk/openapi": ["@sap-cloud-sdk/openapi@4.2.0", "", { "dependencies": { "@sap-cloud-sdk/connectivity": "^4.2.0", "@sap-cloud-sdk/http-client": "^4.2.0", "@sap-cloud-sdk/resilience": "^4.2.0", "@sap-cloud-sdk/util": "^4.2.0", "axios": "^1.13.2" } }, "sha512-lubhOWJqE6n8MZcBjjd6uMFfI8Im3Jma1Mimsh/lJgJP2seOQ7eXnD0zi1zLC8ah4x+k86QrLozdJ5F5Izgvzw=="], - - "@sap-cloud-sdk/resilience": ["@sap-cloud-sdk/resilience@4.2.0", "", { "dependencies": { "@sap-cloud-sdk/util": "^4.2.0", "async-retry": "^1.3.3", "axios": "^1.13.2", "opossum": "^9.0.0" } }, "sha512-ZR2UugUEKEawIu6SIfz9OM8nQO43s/37jnmU4L+vTQN+ptFdFg+2bJAjj+F3jyqSaBx6JbALs9r6X2eWRc+ZDQ=="], - - "@sap-cloud-sdk/util": ["@sap-cloud-sdk/util@4.2.0", "", { "dependencies": { "axios": "^1.13.2", "chalk": "^4.1.0", "logform": "^2.7.0", "voca": "^1.4.1", "winston": "^3.18.3", "winston-transport": "^4.9.0" } }, "sha512-sAyb1hWATZKKu+NZWX65oIdSI4uKj//0UOl4vtzMPNgYXhF806aAWbj2tLZAHI4UTtQWedbfcHhwO7BLl9MvQQ=="], - - "@sap/xsenv": ["@sap/xsenv@6.0.0", "", { "dependencies": { "debug": "4.4.1", "node-cache": "^5.1.2", "verror": "1.10.1" } }, "sha512-9bNpJXmxndWn5JbRCPPtbeMqldXOn2Od17ybS92PHd1rNkZ80IMmOURHNct5YSVQ1MKBIDAyC+ck6VL7cVAfUA=="], - - "@sap/xssec": ["@sap/xssec@4.12.1", "", { "dependencies": { "debug": "^4.4.3", "jwt-decode": "^4" } }, "sha512-LcCnFuoNKosXJ9H71Yd9vRNknB+LHsghro1eHgQ8jUmacSt/C2USL7BsJ4TDb4DxeeZB4wieUEy5HBPZM9T+Jw=="], - "@selemondev/svgl-svelte": ["@selemondev/svgl-svelte@0.0.3", "", { "peerDependencies": { "svelte": "^5.0.0" } }, "sha512-86WAfU6MaMrC2uLU+LhfQoH7et4dJye58jcJCaLtHsB2vNpzKslA6evveAZ+w0Pf29yr9oT0TNChjo4OQLTikQ=="], - "@so-ric/colorspace": ["@so-ric/colorspace@1.1.6", "", { "dependencies": { "color": "^5.0.2", "text-hex": "1.0.x" } }, "sha512-/KiKkpHNOBgkFJwu9sh48LkHSMYGyuTcSFK/qMBdnOAlrRJzRSXAOFB5qwzaVQuDl8wAvHVMkaASQDReTahxuw=="], - "@sveltejs/acorn-typescript": ["@sveltejs/acorn-typescript@1.0.5", "", { "peerDependencies": { "acorn": "^8.9.0" } }, "sha512-IwQk4yfwLdibDlrXVE04jTZYlLnwsTT2PIOQQGNLWfjavGifnk1JD1LcZjZaBTRcxZu2FfPfNLOE04DSu9lqtQ=="], "@sveltejs/vite-plugin-svelte": ["@sveltejs/vite-plugin-svelte@5.1.1", "", { "dependencies": { "@sveltejs/vite-plugin-svelte-inspector": "^4.0.1", "debug": "^4.4.1", "deepmerge": "^4.3.1", "kleur": "^4.1.5", "magic-string": "^0.30.17", "vitefu": "^1.0.6" }, "peerDependencies": { "svelte": "^5.0.0", "vite": "^6.0.0" } }, "sha512-Y1Cs7hhTc+a5E9Va/xwKlAJoariQyHY+5zBgCZg4PFWNYQ1nMN9sjK1zhw1gK69DuqVP++sht/1GZg1aRwmAXQ=="], @@ -360,13 +239,13 @@ "@types/tern": ["@types/tern@0.23.9", "", { "dependencies": { "@types/estree": "*" } }, "sha512-ypzHFE/wBzh+BlH6rrBgS5I/Z7RD21pGhZ2rltb/+ZrVM1awdZwjx7hE5XfuYgHWk9uvV5HLZN3SloevCAp3Bw=="], - "@types/triple-beam": ["@types/triple-beam@1.3.5", "", {}, "sha512-6WaYesThRMCl19iryMYP7/x2OVgCtbIVflDGFpWnb9irXI3UjYE4AzmYuiUKY1AJstGijoY+MgUszMgRxIYTYw=="], - "@types/uuid": ["@types/uuid@10.0.0", "", {}, "sha512-7gqG38EyHgyP1S+7+xomFtL+ZNHcKv6DwNaCZmJmo1vgMugyF3TCnXVg4t1uk89mLNwnLtnY3TpOpCOyp1/xHQ=="], + "accepts": ["accepts@2.0.0", "", { "dependencies": { "mime-types": "^3.0.0", "negotiator": "^1.0.0" } }, "sha512-5cvg6CtKwfgdmVqY1WIiXKc3Q1bkRqGLi+2W/6ao+6Y7gu/RCwRuAhGEzh5B4KlszSuTLgZYuqFqo5bImjNKng=="], + "acorn": ["acorn@8.14.1", "", { "bin": { "acorn": "bin/acorn" } }, "sha512-OvQ/2pUDKmgfCg++xsTX1wGxfTaszcHVcTctW4UJB4hibJx2HXxxO5UmVgyjMa+ZDsiaf5wWLXYpRWMmBI0QHg=="], - "acorn-import-attributes": ["acorn-import-attributes@1.9.5", "", { "peerDependencies": { "acorn": "^8" } }, "sha512-n02Vykv5uA3eHGM/Z2dQrcD56kL8TyDb2p1+0P83PClMnC/nc+anbQRhIOWnSq4Ke/KvDPrY3C9hDtC/A3eHnQ=="], + "ajv": ["ajv@6.12.6", "", { "dependencies": { "fast-deep-equal": "^3.1.1", "fast-json-stable-stringify": "^2.0.0", "json-schema-traverse": "^0.4.1", "uri-js": "^4.2.2" } }, "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g=="], "ansi-regex": ["ansi-regex@6.1.0", "", {}, "sha512-7HSX4QQb4CspciLpVFwyRe79O3xsIZDDLER21kERQ71oaPodF8jL725AgJMFAYbooIqolJoRLuM81SpeUkpkvA=="], @@ -380,18 +259,8 @@ "aria-query": ["aria-query@5.3.2", "", {}, "sha512-COROpnaoap1E2F000S62r6A60uHZnmlvomhfyT2DlTcrY1OrBKn2UhH7qn5wTC9zMvD0AY7csdPSNwKP+7WiQw=="], - "assert-plus": ["assert-plus@1.0.0", "", {}, "sha512-NfJ4UzBCcQGLDlQq7nHxH+tv3kyZ0hHQqF5BO6J7tNJeP5do1llPr8dZ8zHonfhAu0PHAdMkSo+8o0wxg9lZWw=="], - - "async": ["async@3.2.6", "", {}, "sha512-htCUDlxyyCLMgaM3xXg0C0LW2xqfuQ6p05pCEIsXuyQ+a1koYKTuBMzRNwmybfLgvJDMd0r1LTn4+E0Ti6C2AA=="], - - "async-retry": ["async-retry@1.3.3", "", { "dependencies": { "retry": "0.13.1" } }, "sha512-wfr/jstw9xNi/0teMHrRW7dsz3Lt5ARhYNZ2ewpadnhaIp5mbALhOAP+EAdsC7t4Z6wqsDVv9+W6gm1Dk9mEyw=="], - - "asynckit": ["asynckit@0.4.0", "", {}, "sha512-Oei9OH4tRh0YqU3GxhX79dM/mwVgvbZJaSNaRk+bshkj0S5cfHcgYakreBjrHwatXKbz+IoIdYLxrKim2MjW0Q=="], - "autoprefixer": ["autoprefixer@10.4.21", "", { "dependencies": { "browserslist": "^4.24.4", "caniuse-lite": "^1.0.30001702", "fraction.js": "^4.3.7", "normalize-range": "^0.1.2", "picocolors": "^1.1.1", "postcss-value-parser": "^4.2.0" }, "peerDependencies": { "postcss": "^8.1.0" }, "bin": { "autoprefixer": "bin/autoprefixer" } }, "sha512-O+A6LWV5LDHSJD3LjHYoNi4VLsj/Whi7k6zG12xTYaU4cQ8oxQGckXNX8cRHK5yOZ/ppVHe0ZBXGzSV9jXdVbQ=="], - "axios": ["axios@1.13.2", "", { "dependencies": { "follow-redirects": "^1.15.6", "form-data": "^4.0.4", "proxy-from-env": "^1.1.0" } }, "sha512-VPk9ebNqPcy5lRGuSlKx752IlDatOjT9paPlm8A7yOuW2Fbvp4X3JznJtT4f0GzGLLiWE9W8onz51SqLYwzGaA=="], - "axobject-query": ["axobject-query@4.1.0", "", {}, "sha512-qIj0G9wZbMGNLjLmg1PT6v2mE9AH2zlnADJD/2tC6E00hgmhUOfEB6greHPAfLRSufHqROIUTkw6E+M3lH0PTQ=="], "balanced-match": ["balanced-match@1.0.2", "", {}, "sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw=="], @@ -402,18 +271,22 @@ "bits-ui": ["bits-ui@2.11.8", "", { "dependencies": { "@floating-ui/core": "^1.7.1", "@floating-ui/dom": "^1.7.1", "esm-env": "^1.1.2", "runed": "^0.35.1", "svelte-toolbelt": "^0.10.6", "tabbable": "^6.2.0" }, "peerDependencies": { "@internationalized/date": "^3.8.1", "svelte": "^5.33.0" } }, "sha512-zsgVH2iozBywIPJ7iF0fgp+23pGRGj0FyC9uFL4oZ83hhfaN5IEEkED7UtEf5LAjczc67zlmOIxwTRFBKvFX/Q=="], + "body-parser": ["body-parser@2.2.1", "", { "dependencies": { "bytes": "^3.1.2", "content-type": "^1.0.5", "debug": "^4.4.3", "http-errors": "^2.0.0", "iconv-lite": "^0.7.0", "on-finished": "^2.4.1", "qs": "^6.14.0", "raw-body": "^3.0.1", "type-is": "^2.0.1" } }, "sha512-nfDwkulwiZYQIGwxdy0RUmowMhKcFVcYXUU7m4QlKYim1rUtg83xm2yjZ40QjDuc291AJjjeSc9b++AWHSgSHw=="], + "brace-expansion": ["brace-expansion@2.0.1", "", { "dependencies": { "balanced-match": "^1.0.0" } }, "sha512-XnAIvQ8eM+kC6aULx6wuQiwVsnzsi9d3WxzV3FpWTGA19F621kwdbsAcFKXgKUHZWsy+mY6iL1sHTxWEFCytDA=="], "braces": ["braces@3.0.3", "", { "dependencies": { "fill-range": "^7.1.1" } }, "sha512-yQbXgO/OSZVD2IsiLlro+7Hf6Q18EJrKSEsdoMzKePKXct3gvD8oLcOQdIzGupr5Fj+EDe8gO/lxc1BzfMpxvA=="], "browserslist": ["browserslist@4.25.0", "", { "dependencies": { "caniuse-lite": "^1.0.30001718", "electron-to-chromium": "^1.5.160", "node-releases": "^2.0.19", "update-browserslist-db": "^1.1.3" }, "bin": { "browserslist": "cli.js" } }, "sha512-PJ8gYKeS5e/whHBh8xrwYK+dAvEj7JXtz6uTucnMRB8OiGTsKccFekoRrjajPBHV8oOY+2tI4uxeceSimKwMFA=="], - "buffer-equal-constant-time": ["buffer-equal-constant-time@1.0.1", "", {}, "sha512-zRpUiDwd/xk6ADqPMATG8vc9VPrkck7T07OIx0gnjmJAnHnTVXNQG3vfvWNuiZIkwu9KrKdA1iJKfsfTVxE6NA=="], - "builtin-modules": ["builtin-modules@5.0.0", "", {}, "sha512-bkXY9WsVpY7CvMhKSR6pZilZu9Ln5WDrKVBUXf2S443etkmEO4V58heTecXcUIsNsi4Rx8JUO4NfX1IcQl4deg=="], + "bytes": ["bytes@3.1.2", "", {}, "sha512-/Nf7TyzTx6S3yRJObOAV7956r8cr2+Oj8AC5dt8wSP3BQAoeX58NoHyCU8P8zGkNXStjTSi6fzO6F0pBdcYbEg=="], + "call-bind-apply-helpers": ["call-bind-apply-helpers@1.0.2", "", { "dependencies": { "es-errors": "^1.3.0", "function-bind": "^1.1.2" } }, "sha512-Sp1ablJ0ivDkSzjcaJdxEunN5/XvksFJ2sMBFfq6x0ryhQV/2b/KwFe21cMpmHtPOSij8K99/wSfoEuTObmuMQ=="], + "call-bound": ["call-bound@1.0.4", "", { "dependencies": { "call-bind-apply-helpers": "^1.0.2", "get-intrinsic": "^1.3.0" } }, "sha512-+ys997U96po4Kx/ABpBCqhA9EuxJaQWDQg7295H4hBphv3IZg0boBKuwYpt4YXp6MZ5AmZQnU/tyMTlRpaSejg=="], + "camelcase": ["camelcase@6.3.0", "", {}, "sha512-Gmy6FhYlCY7uOElZUSbxo2UCDH8owEk996gkbrpsgGtrJLM3J7jGxl9Ic7Qwwj4ivOE5AWZWRMecDdF7hqGjFA=="], "camelcase-css": ["camelcase-css@2.0.1", "", {}, "sha512-QOSvevhslijgYwRx6Rv7zKdMF8lbRmx+uQGx2+vDc+KI/eBnsy9kit5aj23AgGu3pa4t9AgwbnXWqS+iOY+2aA=="], @@ -424,31 +297,27 @@ "chokidar": ["chokidar@4.0.3", "", { "dependencies": { "readdirp": "^4.0.1" } }, "sha512-Qgzu8kfBvo+cA4962jnP1KkS6Dop5NS6g7R5LFYJr4b8Ub94PPQXUksCw9PvXoeXPRRddRNC5C1JQUR2SMGtnA=="], - "cjs-module-lexer": ["cjs-module-lexer@1.4.3", "", {}, "sha512-9z8TZaGM1pfswYeXrUpzPrkx8UnWYdhJclsiYMm6x/w5+nN+8Tf/LnAgfLGQCm59qAOxU8WwHEq2vNwF6i4j+Q=="], - "cli-color": ["cli-color@2.0.4", "", { "dependencies": { "d": "^1.0.1", "es5-ext": "^0.10.64", "es6-iterator": "^2.0.3", "memoizee": "^0.4.15", "timers-ext": "^0.1.7" } }, "sha512-zlnpg0jNcibNrO7GG9IeHH7maWFeCz+Ja1wx/7tZNU5ASSSSZ+/qZciM0/LHCYxSdqv5h2sdbQ/PXYdOuetXvA=="], - "cliui": ["cliui@8.0.1", "", { "dependencies": { "string-width": "^4.2.0", "strip-ansi": "^6.0.1", "wrap-ansi": "^7.0.0" } }, "sha512-BSeNnyus75C4//NQ9gQt1/csTXyo/8Sb+afLAkzAptFuMsod9HFokGNudZpi/oQV73hnVK+sR+5PVRMd+Dr7YQ=="], - - "clone": ["clone@2.1.2", "", {}, "sha512-3Pe/CF1Nn94hyhIYpjtiLhdCoEoz0DqQ+988E9gmeEdQZlojxnOb74wctFyuwWQHzqyf9X7C7MG8juUpqBJT8w=="], - "clsx": ["clsx@2.1.1", "", {}, "sha512-eYm0QWBtUrBWZWG0d386OGAw16Z995PiOVo2B7bjWSbHedGl5e0ZWaq65kOGgUSNesEIDkB9ISbTg/JK9dhCZA=="], - "color": ["color@5.0.3", "", { "dependencies": { "color-convert": "^3.1.3", "color-string": "^2.1.3" } }, "sha512-ezmVcLR3xAVp8kYOm4GS45ZLLgIE6SPAFoduLr6hTDajwb3KZ2F46gulK3XpcwRFb5KKGCSezCBAY4Dw4HsyXA=="], - "color-convert": ["color-convert@2.0.1", "", { "dependencies": { "color-name": "~1.1.4" } }, "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ=="], "color-name": ["color-name@1.1.4", "", {}, "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA=="], - "color-string": ["color-string@2.1.4", "", { "dependencies": { "color-name": "^2.0.0" } }, "sha512-Bb6Cq8oq0IjDOe8wJmi4JeNn763Xs9cfrBcaylK1tPypWzyoy2G3l90v9k64kjphl/ZJjPIShFztenRomi8WTg=="], - - "combined-stream": ["combined-stream@1.0.8", "", { "dependencies": { "delayed-stream": "~1.0.0" } }, "sha512-FQN4MRfuJeHf7cBbBMJFXhKSDq+2kAArBlmRBvcvFE5BB1HZKXtSFASDhdlz9zOYwxh8lDdnvmMOe/+5cdoEdg=="], - "commander": ["commander@4.1.1", "", {}, "sha512-NOKm8xhkzAjzFx8B2v5OAHT+u5pRQc2UCa2Vq9jYL/31o2wi9mxBA7LIFs3sV5VSC49z6pEhfbMULvShKj26WA=="], "console-table-printer": ["console-table-printer@2.15.0", "", { "dependencies": { "simple-wcswidth": "^1.1.2" } }, "sha512-SrhBq4hYVjLCkBVOWaTzceJalvn5K1Zq5aQA6wXC/cYjI3frKWNPEMK3sZsJfNNQApvCQmgBcc13ZKmFj8qExw=="], - "core-util-is": ["core-util-is@1.0.2", "", {}, "sha512-3lqz5YjWTYnW6dlDa5TLaTCcShfar1e40rmcJVwCBJC6mWlFuj0eCHIElmG1g5kyuJ/GD+8Wn4FFCcz4gJPfaQ=="], + "content-disposition": ["content-disposition@1.0.1", "", {}, "sha512-oIXISMynqSqm241k6kcQ5UwttDILMK4BiurCfGEREw6+X9jkkpEe5T9FZaApyLGGOnFuyMWZpdolTXMtvEJ08Q=="], + + "content-type": ["content-type@1.0.5", "", {}, "sha512-nTjqfcBFEipKdXCv4YDQWCfmcLZKm81ldF0pAopTvyrFGVbcR6P/VAAd5G7N+0tTr8QqiU0tFadD6FK4NtJwOA=="], + + "cookie": ["cookie@0.7.2", "", {}, "sha512-yki5XnKuf750l50uGTllt6kKILY4nQ1eNIQatoXEByZ5dWgnKqbnqmTrBE5B4N7lrMJKQ2ytWMiTO2o0v6Ew/w=="], + + "cookie-signature": ["cookie-signature@1.2.2", "", {}, "sha512-D76uU73ulSXrD1UXF4KE2TMxVVwhsnCgfAyTg9k8P6KGZjlXKrOLe4dJQKI3Bxi5wjesZoFXJWElNWBjPZMbhg=="], + + "cors": ["cors@2.8.5", "", { "dependencies": { "object-assign": "^4", "vary": "^1" } }, "sha512-KIHbLJqu73RGr/hnbrO9uBeixNGuvSQjul/jdFvS/KFSIH1hWVd1ng7zOHx+YrEfInLG7q4n6GHQ9cDtxv/P6g=="], "crelt": ["crelt@1.0.6", "", {}, "sha512-VQ2MBenTq1fWZUH9DJNGti7kKv6EeAuYr3cLwxUWhIu1baTaXh4Ib5W2CqHVqib4/MqbYGJqiL3Zb8GJZr3l4g=="], @@ -458,7 +327,7 @@ "d": ["d@1.0.2", "", { "dependencies": { "es5-ext": "^0.10.64", "type": "^2.7.2" } }, "sha512-MOqHvMWF9/9MX6nza0KgvFH4HpMU0EF5uUDXqX/BtxtU8NfB0QzRtJ8Oe/6SuS4kbhyzVJwjd97EA4PKrzJ8bw=="], - "debug": ["debug@4.4.1", "", { "dependencies": { "ms": "^2.1.3" } }, "sha512-KcKCqiftBJcZr++7ykoDIEwSa3XWowTfNPo92BYxjXiyYEVrUQh2aLyhxBCwww+heortUFxEJYcRzosstTEBYQ=="], + "debug": ["debug@4.4.3", "", { "dependencies": { "ms": "^2.1.3" } }, "sha512-RGwwWnwQvkVfavKVt22FGLw+xYSdzARwm0ru6DhTVA3umU5hZc28V3kO4stgYryrTlLpuvgI9GiijltAjNbcqA=="], "decamelize": ["decamelize@1.2.0", "", {}, "sha512-z2S+W9X73hAUUki+N+9Za2lBlun89zigOyGrsax+KUQ6wKW4ZoWpEYBkGhQjwAjjDCkWxhY0VKEhk8wzY7F5cA=="], @@ -466,7 +335,7 @@ "deepmerge": ["deepmerge@4.3.1", "", {}, "sha512-3sUqbMEc77XqpdNO7FRyRog+eW3ph+GYCbj+rK+uYyRMuwsVy0rMiVtPn+QJlKFvWP/1PYpapqYn0Me2knFn+A=="], - "delayed-stream": ["delayed-stream@1.0.0", "", {}, "sha512-ZySD7Nf91aLB0RxL4KGrKHBXl7Eds1DAmEdcoVawXnLD7SDhpNgtuII2aAkg7a7QS41jxPSZ17p4VdGnMHk3MQ=="], + "depd": ["depd@2.0.0", "", {}, "sha512-g7nH6P6dyDioJogAAGprGpCtVImJhpPk/roCzdb3fIh61/s/nPsfR6onyMwkCAR/OlC3yBC0lESvUoQEAssIrw=="], "dequal": ["dequal@2.0.3", "", {}, "sha512-0je+qPKHEMohvfRTCEo3CrPG6cAzAYgmzKyxRiYSSDkS6eGJdyVJm7WaYA5ECaAD9wLB2T4EEeymA5aFVcYXCA=="], @@ -476,19 +345,17 @@ "dlv": ["dlv@1.1.3", "", {}, "sha512-+HlytyjlPKnIG8XuRG8WvmBP8xs8P71y+SKKS6ZXWoEgLuePxtDoUEiH7WkdePWrQ5JBpE6aoVqfZfJUQkjXwA=="], - "dotenv": ["dotenv@17.2.3", "", {}, "sha512-JVUnt+DUIzu87TABbhPmNfVdBDt18BLOWjMUFJMSi/Qqg7NTYtabbvSNJGOJ7afbRuv9D/lngizHtP7QyLQ+9w=="], - "dunder-proto": ["dunder-proto@1.0.1", "", { "dependencies": { "call-bind-apply-helpers": "^1.0.1", "es-errors": "^1.3.0", "gopd": "^1.2.0" } }, "sha512-KIN/nDJBQRcXw0MLVhZE9iQHmG68qAVIBg9CqmUYjmQIhgij9U5MFvrqkUL5FbtyyzZuOeOt0zdeRe4UY7ct+A=="], "eastasianwidth": ["eastasianwidth@0.2.0", "", {}, "sha512-I88TYZWc9XiYHRQ4/3c5rjjfgkjhLyW2luGIheGERbNQ6OY7yTybanSpDXZa8y7VUP9YmDcYa+eyq4ca7iLqWA=="], - "ecdsa-sig-formatter": ["ecdsa-sig-formatter@1.0.11", "", { "dependencies": { "safe-buffer": "^5.0.1" } }, "sha512-nagl3RYrbNv6kQkeJIpt6NJZy8twLB/2vtz6yN9Z4vRKHN4/QZJIEbqohALSgwKdnksuY3k5Addp5lg8sVoVcQ=="], + "ee-first": ["ee-first@1.1.1", "", {}, "sha512-WMwm9LhRUo+WUaRN+vRuETqG89IgZphVSNkdFgeb6sS/E4OrDIN7t48CAewSHXc6C8lefD8KKfr5vY61brQlow=="], "electron-to-chromium": ["electron-to-chromium@1.5.165", "", {}, "sha512-naiMx1Z6Nb2TxPU6fiFrUrDTjyPMLdTtaOd2oLmG8zVSg2hCWGkhPyxwk+qRmZ1ytwVqUv0u7ZcDA5+ALhaUtw=="], "emoji-regex": ["emoji-regex@9.2.2", "", {}, "sha512-L18DaJsXSUk2+42pv8mLs5jJT2hqFkFE4j21wOmgbUqsZ2hL72NsUU785g9RXgo3s0ZNgVl42TiHp3ZtOv/Vyg=="], - "enabled": ["enabled@2.0.0", "", {}, "sha512-AKrN98kuwOzMIdAizXGI86UFBoo26CL21UM763y1h/GMSJ4/OHU9k2YlsmBpyScFo/wbLzWQJBMCW4+IO3/+OQ=="], + "encodeurl": ["encodeurl@2.0.0", "", {}, "sha512-Q0n9HRi4m6JuGIV1eFlmvJB7ZEVxu93IrMyiMsGC0lrMJMWzRgx6WGquyfQgZVb31vhGgXnfmPNNXmxnOkRBrg=="], "es-define-property": ["es-define-property@1.0.1", "", {}, "sha512-e3nRfgfUZ4rNGL232gUgX06QNyyez04KdjFrF+LTRoOXmrOgFKDg4BCdsjW8EnT69eqdYGmRpJwiPVYNrCaW3g=="], @@ -496,8 +363,6 @@ "es-object-atoms": ["es-object-atoms@1.1.1", "", { "dependencies": { "es-errors": "^1.3.0" } }, "sha512-FGgH2h8zKNim9ljj7dankFPcICIK9Cp5bm+c2gQSYePhpaG5+esrLODihIorn+Pe6FGJzWhXQotPv73jTaldXA=="], - "es-set-tostringtag": ["es-set-tostringtag@2.1.0", "", { "dependencies": { "es-errors": "^1.3.0", "get-intrinsic": "^1.2.6", "has-tostringtag": "^1.0.2", "hasown": "^2.0.2" } }, "sha512-j6vWzfrGVfyXxge+O0x5sh6cvxAog0a/4Rdd2K36zCMV5eJ+/+tOAngRO8cODMNWbVRdVlmGZQL2YS3yR8bIUA=="], - "es5-ext": ["es5-ext@0.10.64", "", { "dependencies": { "es6-iterator": "^2.0.3", "es6-symbol": "^3.1.3", "esniff": "^2.0.1", "next-tick": "^1.1.0" } }, "sha512-p2snDhiLaXe6dahss1LddxqEm+SkuDvV8dnIQG0MWjyHpcMNfXKPE+/Cc0y+PhxJX3A4xGNeFCj5oc0BUh6deg=="], "es6-iterator": ["es6-iterator@2.0.3", "", { "dependencies": { "d": "1", "es5-ext": "^0.10.35", "es6-symbol": "^3.1.1" } }, "sha512-zw4SRzoUkd+cl+ZoE15A9o1oQd920Bb0iOJMQkQhl3jNc03YqVjAhG7scf9C5KWRU/R13Orf588uCC6525o02g=="], @@ -510,6 +375,8 @@ "escalade": ["escalade@3.2.0", "", {}, "sha512-WUj2qlxaQtO4g6Pq5c29GTcWGDyd8itL8zTlipgECz3JesAiiOKotd8JU6otB3PACgG6xkJUyVhboMS+bje/jA=="], + "escape-html": ["escape-html@1.0.3", "", {}, "sha512-NiSupZ4OeuGwr68lGIeym/ksIZMJodUGOSCZ/FSnTxcrekbvqrgdUxlJOMpijaKZVjAJrWrGs/6Jy8OMuyj9ow=="], + "esm-env": ["esm-env@1.2.2", "", {}, "sha512-Epxrv+Nr/CaL4ZcFGPJIYLWFom+YeV1DqMLHJoEd9SYRxNbaFruBwfEX/kkHUJf55j2+TUbmDcmuilbP1TmXHA=="], "esniff": ["esniff@2.0.1", "", { "dependencies": { "d": "^1.0.1", "es5-ext": "^0.10.62", "event-emitter": "^0.3.5", "type": "^2.7.2" } }, "sha512-kTUIGKQ/mDPFoJ0oVfcmyJn4iBDRptjNVIzwIFR7tqWXdVI9xfA2RMwY/gbSpJG3lkdWNEjLap/NqVHZiJsdfg=="], @@ -518,40 +385,50 @@ "estree-walker": ["estree-walker@2.0.2", "", {}, "sha512-Rfkk/Mp/DL7JVje3u18FxFujQlTNR2q6QfMSMB7AvCBx91NGj/ba3kCfza0f6dVDbw7YlRf/nDrn7pQrCCyQ/w=="], + "etag": ["etag@1.8.1", "", {}, "sha512-aIL5Fx7mawVa300al2BnEE4iNvo1qETxLrPI/o05L7z6go7fCw1J6EQmbK4FmJ2AS7kgVF/KEZWufBfdClMcPg=="], + "event-emitter": ["event-emitter@0.3.5", "", { "dependencies": { "d": "1", "es5-ext": "~0.10.14" } }, "sha512-D9rRn9y7kLPnJ+hMq7S/nhvoKwwvVJahBi2BPmx3bvbsEdK3W9ii8cBSGjP+72/LnM4n6fo3+dkCX5FeTQruXA=="], "eventemitter3": ["eventemitter3@4.0.7", "", {}, "sha512-8guHBZCwKnFhYdHr2ysuRWErTwhoN2X8XELRlrRwpmfeY2jjuUN4taQMsULKUVo1K4DvZl+0pgfyoysHxvmvEw=="], + "eventsource": ["eventsource@3.0.7", "", { "dependencies": { "eventsource-parser": "^3.0.1" } }, "sha512-CRT1WTyuQoD771GW56XEZFQ/ZoSfWid1alKGDYMmkt2yl8UXrVR4pspqWNEcqKvVIzg6PAltWjxcSSPrboA4iA=="], + + "eventsource-parser": ["eventsource-parser@3.0.6", "", {}, "sha512-Vo1ab+QXPzZ4tCa8SwIHJFaSzy4R6SHf7BY79rFBDf0idraZWAkYrDjDj8uWaSm3S2TK+hJ7/t1CEmZ7jXw+pg=="], + + "express": ["express@5.2.1", "", { "dependencies": { "accepts": "^2.0.0", "body-parser": "^2.2.1", "content-disposition": "^1.0.0", "content-type": "^1.0.5", "cookie": "^0.7.1", "cookie-signature": "^1.2.1", "debug": "^4.4.0", "depd": "^2.0.0", "encodeurl": "^2.0.0", "escape-html": "^1.0.3", "etag": "^1.8.1", "finalhandler": "^2.1.0", "fresh": "^2.0.0", "http-errors": "^2.0.0", "merge-descriptors": "^2.0.0", "mime-types": "^3.0.0", "on-finished": "^2.4.1", "once": "^1.4.0", "parseurl": "^1.3.3", "proxy-addr": "^2.0.7", "qs": "^6.14.0", "range-parser": "^1.2.1", "router": "^2.2.0", "send": "^1.1.0", "serve-static": "^2.2.0", "statuses": "^2.0.1", "type-is": "^2.0.1", "vary": "^1.1.2" } }, "sha512-hIS4idWWai69NezIdRt2xFVofaF4j+6INOpJlVOLDO8zXGpUVEVzIYk12UUi2JzjEzWL3IOAxcTubgz9Po0yXw=="], + + "express-rate-limit": ["express-rate-limit@7.5.1", "", { "peerDependencies": { "express": ">= 4.11" } }, "sha512-7iN8iPMDzOMHPUYllBEsQdWVB6fPDMPqwjBaFrgr4Jgr/+okjvzAy+UHlYYL/Vs0OsOrMkwS6PJDkFlJwoxUnw=="], + "ext": ["ext@1.7.0", "", { "dependencies": { "type": "^2.7.2" } }, "sha512-6hxeJYaL110a9b5TEJSj0gojyHQAmA2ch5Os+ySCiA1QGdS697XWY1pzsrSjqA9LDEEgdB/KypIlR59RcLuHYw=="], - "extsprintf": ["extsprintf@1.4.1", "", {}, "sha512-Wrk35e8ydCKDj/ArClo1VrPVmN8zph5V4AtHwIuHhvMXsKf73UT3BOD+azBIW+3wOJ4FhEH7zyaJCFvChjYvMA=="], + "extended-eventsource": ["extended-eventsource@1.7.0", "", {}, "sha512-s8rtvZuYcKBpzytHb5g95cHbZ1J99WeMnV18oKc5wKoxkHzlzpPc/bNAm7Da2Db0BDw0CAu1z3LpH+7UsyzIpw=="], + + "fast-deep-equal": ["fast-deep-equal@3.1.3", "", {}, "sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q=="], "fast-glob": ["fast-glob@3.3.3", "", { "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" } }, "sha512-7MptL8U0cqcFdzIzwOTHoilX9x5BrNqye7Z/LuC7kCMRio1EMSyqRK3BEAUD7sXRq4iT4AzTVuZdhgQ2TCvYLg=="], + "fast-json-stable-stringify": ["fast-json-stable-stringify@2.1.0", "", {}, "sha512-lhd/wF+Lk98HZoTCtlVraHtfh5XYijIjalXck7saUtuanSDyLMxnHhSXEDJqHxD7msR8D0uCmqlkwjCV8xvwHw=="], + "fastq": ["fastq@1.19.1", "", { "dependencies": { "reusify": "^1.0.4" } }, "sha512-GwLTyxkCXjXbxqIhTsMI2Nui8huMPtnxg7krajPJAjnEG/iiOS7i+zCtWGZR9G0NBKbXKh6X9m9UIsYX/N6vvQ=="], "fdir": ["fdir@6.4.5", "", { "peerDependencies": { "picomatch": "^3 || ^4" }, "optionalPeers": ["picomatch"] }, "sha512-4BG7puHpVsIYxZUbiUE3RqGloLaSSwzYie5jvasC4LWuBWzZawynvYouhjbQKw2JuIGYdm0DzIxl8iVidKlUEw=="], - "fecha": ["fecha@4.2.3", "", {}, "sha512-OP2IUU6HeYKJi3i0z4A19kHMQoLVs4Hc+DPqqxI2h/DPZHTm/vjsfC6P0b4jCMy14XizLBqvndQ+UilD7707Jw=="], - "fill-range": ["fill-range@7.1.1", "", { "dependencies": { "to-regex-range": "^5.0.1" } }, "sha512-YsGpe3WHLK8ZYi4tWDg2Jy3ebRz2rXowDxnld4bkQB00cc/1Zw9AWnC0i9ztDJitivtQvaI9KaLyKrc+hBW0yg=="], - "fn.name": ["fn.name@1.1.0", "", {}, "sha512-GRnmB5gPyJpAhTQdSZTSp9uaPSvl09KoYcMQtsB9rQoOmzs9dH6ffeccH+Z+cv6P68Hu5bC6JjRh4Ah/mHSNRw=="], - - "follow-redirects": ["follow-redirects@1.15.11", "", {}, "sha512-deG2P0JfjrTxl50XGCDyfI97ZGVCxIpfKYmfyrQ54n5FO/0gfIES8C/Psl6kWVDolizcaaxZJnTS0QSMxvnsBQ=="], + "finalhandler": ["finalhandler@2.1.1", "", { "dependencies": { "debug": "^4.4.0", "encodeurl": "^2.0.0", "escape-html": "^1.0.3", "on-finished": "^2.4.1", "parseurl": "^1.3.3", "statuses": "^2.0.1" } }, "sha512-S8KoZgRZN+a5rNwqTxlZZePjT/4cnm0ROV70LedRHZ0p8u9fRID0hJUZQpkKLzro8LfmC8sx23bY6tVNxv8pQA=="], "foreground-child": ["foreground-child@3.3.1", "", { "dependencies": { "cross-spawn": "^7.0.6", "signal-exit": "^4.0.1" } }, "sha512-gIXjKqtFuWEgzFRJA9WCQeSJLZDjgJUOMCMzxtvFq/37KojM1BFGufqsCy0r4qSQmYLsZYMeyRqzIWOMup03sw=="], - "form-data": ["form-data@4.0.5", "", { "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" } }, "sha512-8RipRLol37bNs2bhoV67fiTEvdTrbMUYcFTiy3+wuuOnUog2QBHCZWXDRijWQfAkhBj2Uf5UnVaiWwA5vdd82w=="], + "forwarded": ["forwarded@0.2.0", "", {}, "sha512-buRG0fpBtRHSTCOASe6hD258tEubFoRLb4ZNA6NxMVHNw2gOcwHo9wyablzMzOA5z9xA9L1KNjk/Nt6MT9aYow=="], "fraction.js": ["fraction.js@4.3.7", "", {}, "sha512-ZsDfxO51wGAXREY55a7la9LScWpwv9RxIrYABrlvOFBlH/ShPnrtsXeuUIfXKKOVicNxQ+o8JTbJvjS4M89yew=="], + "fresh": ["fresh@2.0.0", "", {}, "sha512-Rx/WycZ60HOaqLKAi6cHRKKI7zxWbJ31MhntmtwMoaTeF7XFH9hhBp8vITaMidfljRQ6eYWCKkaTK+ykVJHP2A=="], + "fsevents": ["fsevents@2.3.3", "", { "os": "darwin" }, "sha512-5xoDfX+fL7faATnagmWPpbFtwh/R77WmMMqqHGS65C3vvB0YHrgF+B1YmZ3441tMj5n63k0212XNoJwzlhffQw=="], "function-bind": ["function-bind@1.1.2", "", {}, "sha512-7XHNxH7qX9xG5mIwxkhumTox/MIRNcOgDrxWsMt2pAr23WHp6MrRlN7FBSFpCpr+oVO0F744iUgR82nJMfG2SA=="], - "get-caller-file": ["get-caller-file@2.0.5", "", {}, "sha512-DyFP3BM/3YHTQOCUL/w0OZHR0lpKeGrxotcHWcqNEdnltqFwXVfhEBQ94eIo34AfQpo0rGki4cyIiftY06h2Fg=="], - "get-intrinsic": ["get-intrinsic@1.3.0", "", { "dependencies": { "call-bind-apply-helpers": "^1.0.2", "es-define-property": "^1.0.1", "es-errors": "^1.3.0", "es-object-atoms": "^1.1.1", "function-bind": "^1.1.2", "get-proto": "^1.0.1", "gopd": "^1.2.0", "has-symbols": "^1.1.0", "hasown": "^2.0.2", "math-intrinsics": "^1.1.0" } }, "sha512-9fSjSaos/fRIVIp+xSJlE6lfwhES7LNtKaCBIamHsjr2na1BiABJPo0mOjjz8GJDURarmCPGqaiVg5mfjb98CQ=="], "get-proto": ["get-proto@1.0.1", "", { "dependencies": { "dunder-proto": "^1.0.1", "es-object-atoms": "^1.0.0" } }, "sha512-sTSfBjoXBp89JvIKIefqw7U2CCebsc74kiY6awiGogKtoSGbgjYE/G/+l9sF3MWFPNc9IcoOC4ODfKHfxFmp0g=="], @@ -570,13 +447,13 @@ "has-symbols": ["has-symbols@1.1.0", "", {}, "sha512-1cDNdwJ2Jaohmb3sg4OmKaMBwuC48sYni5HUw2DvsC8LjGTLK9h+eb1X6RyuOHe4hT0ULCW68iomhjUoKUqlPQ=="], - "has-tostringtag": ["has-tostringtag@1.0.2", "", { "dependencies": { "has-symbols": "^1.0.3" } }, "sha512-NqADB8VjPFLM2V0VvHUewwwsw0ZWBaIdgo+ieHtK3hasLz4qeCRjYcqfB6AQrBggRKppKF8L52/VqdVsO47Dlw=="], - "hasown": ["hasown@2.0.2", "", { "dependencies": { "function-bind": "^1.1.2" } }, "sha512-0hJU9SCPvmMzIBdZFqNPXWa6dqh7WdH0cII9y+CyS8rG3nL48Bclra9HmKhVVUHyPWNH5Y7xDwAB7bfgSjkUMQ=="], + "http-errors": ["http-errors@2.0.1", "", { "dependencies": { "depd": "~2.0.0", "inherits": "~2.0.4", "setprototypeof": "~1.2.0", "statuses": "~2.0.2", "toidentifier": "~1.0.1" } }, "sha512-4FbRdAX+bSdmo4AUFuS0WNiPz8NgFt+r8ThgNWmlrjQjt1Q7ZR9+zTlce2859x4KSXrwIsaeTqDoKQmtP8pLmQ=="], + "i18next": ["i18next@23.16.8", "", { "dependencies": { "@babel/runtime": "^7.23.2" } }, "sha512-06r/TitrM88Mg5FdUXAKL96dJMzgqLE5dv3ryBAra4KCwD9mJ4ndOTS95ZuymIGoE+2hzfdaMak2X11/es7ZWg=="], - "import-in-the-middle": ["import-in-the-middle@2.0.0", "", { "dependencies": { "acorn": "^8.14.0", "acorn-import-attributes": "^1.9.5", "cjs-module-lexer": "^1.2.2", "module-details-from-path": "^1.0.3" } }, "sha512-yNZhyQYqXpkT0AKq3F3KLasUSK4fHvebNH5hOsKQw2dhGSALvQ4U0BqUc5suziKvydO5u5hgN2hy1RJaho8U5A=="], + "iconv-lite": ["iconv-lite@0.7.1", "", { "dependencies": { "safer-buffer": ">= 2.1.2 < 3.0.0" } }, "sha512-2Tth85cXwGFHfvRgZWszZSvdo+0Xsqmw8k8ZwxScfcBneNUraK+dxRxRm24nszx80Y0TVio8kKLt5sLE7ZCLlw=="], "inherits": ["inherits@2.0.4", "", {}, "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ=="], @@ -584,6 +461,8 @@ "intl-messageformat": ["intl-messageformat@10.7.16", "", { "dependencies": { "@formatjs/ecma402-abstract": "2.3.4", "@formatjs/fast-memoize": "2.2.7", "@formatjs/icu-messageformat-parser": "2.11.2", "tslib": "^2.8.0" } }, "sha512-UmdmHUmp5CIKKjSoE10la5yfU+AYJAaiYLsodbjL4lji83JNvgOQUjGaGhGrpFCb0Uh7sl7qfP1IyILa8Z40ug=="], + "ipaddr.js": ["ipaddr.js@1.9.1", "", {}, "sha512-0KI/607xoxSToH7GjN1FfSbLoU0+btTicjsQSWQlh/hZykN8KpmMf7uYwPW3R+akZ6R/w18ZlXSHBYXiYUPO3g=="], + "is-binary-path": ["is-binary-path@2.1.0", "", { "dependencies": { "binary-extensions": "^2.0.0" } }, "sha512-ZMERYes6pDydyuGidse7OsHxtbI7WVeUEozgR/g7rd0xUimYNlvZRE/K2MgZTjWy725IfelLeVcEM97mmtRGXw=="], "is-core-module": ["is-core-module@2.16.1", "", { "dependencies": { "hasown": "^2.0.2" } }, "sha512-UfoeMA6fIJ8wTYFEUjelnaGI67v6+N7qXJEvQuIGa99l4xsCruSYOVSQ0uPANn4dAzm8lkYPaKLrrijLq7x23w=="], @@ -600,8 +479,6 @@ "is-reference": ["is-reference@3.0.3", "", { "dependencies": { "@types/estree": "^1.0.6" } }, "sha512-ixkJoqQvAP88E6wLydLGGqCJsrFUnqoH6HnaczB8XmDH1oaWU+xxdptvikTgaEhtZ53Ky6YXiBuUI2WXLMCwjw=="], - "is-stream": ["is-stream@2.0.1", "", {}, "sha512-hFoiJiTl63nn+kstHGBtewWSKnQLpyb155KHheA1l39uvtO9nWIop1p3udqPcUd/xbF1VLMO4n7OI6p7RbngDg=="], - "isexe": ["isexe@2.0.0", "", {}, "sha512-RHxMLp9lnKHGHRng9QFhRCMbYAcVpn69smSGcq3f36xjgVVWThj4qqLbTLlq7Ssj8B+fIQ1EuCEGI2lKsyQeIw=="], "jackspeak": ["jackspeak@3.4.3", "", { "dependencies": { "@isaacs/cliui": "^8.0.2" }, "optionalDependencies": { "@pkgjs/parseargs": "^0.11.0" } }, "sha512-OGlZQpz2yfahA/Rd1Y8Cd9SIEsqvXkLVoSw/cgwhnhFMDbsQFeZYoJJ7bIZBS9BcamUW96asq/npPWugM+RQBw=="], @@ -610,26 +487,10 @@ "js-tiktoken": ["js-tiktoken@1.0.21", "", { "dependencies": { "base64-js": "^1.5.1" } }, "sha512-biOj/6M5qdgx5TKjDnFT1ymSpM5tbd3ylwDtrQvFQSu0Z7bBYko2dF+W/aUkXUPuk6IVpRxk/3Q2sHOzGlS36g=="], - "json-schema-to-ts": ["json-schema-to-ts@3.1.1", "", { "dependencies": { "@babel/runtime": "^7.18.3", "ts-algebra": "^2.0.0" } }, "sha512-+DWg8jCJG2TEnpy7kOm/7/AxaYoaRbjVB4LFZLySZlWn8exGs3A4OLJR966cVvU26N7X9TWxl+Jsw7dzAqKT6g=="], - - "jsonwebtoken": ["jsonwebtoken@9.0.3", "", { "dependencies": { "jws": "^4.0.1", "lodash.includes": "^4.3.0", "lodash.isboolean": "^3.0.3", "lodash.isinteger": "^4.0.4", "lodash.isnumber": "^3.0.3", "lodash.isplainobject": "^4.0.6", "lodash.isstring": "^4.0.1", "lodash.once": "^4.0.0", "ms": "^2.1.1", "semver": "^7.5.4" } }, "sha512-MT/xP0CrubFRNLNKvxJ2BYfy53Zkm++5bX9dtuPbqAeQpTVe0MQTFhao8+Cp//EmJp244xt6Drw/GVEGCUj40g=="], - - "jwa": ["jwa@2.0.1", "", { "dependencies": { "buffer-equal-constant-time": "^1.0.1", "ecdsa-sig-formatter": "1.0.11", "safe-buffer": "^5.0.1" } }, "sha512-hRF04fqJIP8Abbkq5NKGN0Bbr3JxlQ+qhZufXVr0DvujKy93ZCbXZMHDL4EOtodSbCWxOqR8MS1tXA5hwqCXDg=="], - - "jws": ["jws@4.0.1", "", { "dependencies": { "jwa": "^2.0.1", "safe-buffer": "^5.0.1" } }, "sha512-EKI/M/yqPncGUUh44xz0PxSidXFr/+r0pA70+gIYhjv+et7yxM+s29Y+VGDkovRofQem0fs7Uvf4+YmAdyRduA=="], - - "jwt-decode": ["jwt-decode@4.0.0", "", {}, "sha512-+KJGIyHgkGuIq3IEBNftfhW/LfWhXUIY6OmyVWjliu5KH1y0fw7VQ8YndE2O4qZdMSd9SqbnC8GOcZEy0Om7sA=="], + "json-schema-traverse": ["json-schema-traverse@0.4.1", "", {}, "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg=="], "kleur": ["kleur@4.1.5", "", {}, "sha512-o+NO+8WrRiQEE4/7nwRJhN1HWpVmJm511pBHUxPLtp0BUISzlBplORYSmTclCnJvQq2tKu/sgl3xVpkc7ZWuQQ=="], - "kuler": ["kuler@2.0.0", "", {}, "sha512-Xq9nH7KlWZmXAtodXDDRE7vs6DU1gTU8zYDHDiWLSip45Egwq3plLHzPn27NgvzL2r1LMPC1vdqh98sQxtqj4A=="], - - "langchain": ["langchain@1.2.0", "", { "dependencies": { "@langchain/langgraph": "^1.0.0", "@langchain/langgraph-checkpoint": "^1.0.0", "langsmith": "~0.3.74", "uuid": "^10.0.0", "zod": "^3.25.76 || ^4" }, "peerDependencies": { "@langchain/core": "1.1.5" } }, "sha512-HC+5zN1RPenV/QU9pbo4V0Hv7R8rP4ZBXnnqhkBrSYqfvhcQ644dZQIcB3vryjqLhi82xZE2oNSplQLjnhX6xw=="], - - "langfuse": ["langfuse@3.38.6", "", { "dependencies": { "langfuse-core": "^3.38.6" } }, "sha512-mtwfsNGIYvObRh+NYNGlJQJDiBN+Wr3Hnr++wN25mxuOpSTdXX+JQqVCyAqGL5GD2TAXRZ7COsN42Vmp9krYmg=="], - - "langfuse-core": ["langfuse-core@3.38.6", "", { "dependencies": { "mustache": "^4.2.0" } }, "sha512-EcZXa+DK9FJdi1I30+u19eKjuBJ04du6j2Nybk19KKCuraLczg/ppkTQcGvc4QOk//OAi3qUHrajUuV74RXsBQ=="], - "langsmith": ["langsmith@0.3.87", "", { "dependencies": { "@types/uuid": "^10.0.0", "chalk": "^4.1.2", "console-table-printer": "^2.12.1", "p-queue": "^6.6.2", "semver": "^7.6.3", "uuid": "^10.0.0" }, "peerDependencies": { "@opentelemetry/api": "*", "@opentelemetry/exporter-trace-otlp-proto": "*", "@opentelemetry/sdk-trace-base": "*", "openai": "*" }, "optionalPeers": ["@opentelemetry/api", "@opentelemetry/exporter-trace-otlp-proto", "@opentelemetry/sdk-trace-base", "openai"] }, "sha512-XXR1+9INH8YX96FKWc5tie0QixWz6tOqAsAKfcJyPkE0xPep+NDz0IQLR32q4bn10QK3LqD2HN6T3n6z1YLW7Q=="], "lilconfig": ["lilconfig@3.1.3", "", {}, "sha512-/vlFKAoH5Cgt3Ie+JLhRbwOsCQePABiU3tJ1egGvyQ+33R/vcwM2Zl2QR/LzjsBeItPt3oSVXapn+m4nQDvpzw=="], @@ -638,26 +499,6 @@ "locate-character": ["locate-character@3.0.0", "", {}, "sha512-SW13ws7BjaeJ6p7Q6CO2nchbYEc3X3J6WrmTTDto7yMPqVSZTUyY5Tjbid+Ab8gLnATtygYtiDIJGQRRn2ZOiA=="], - "lodash.camelcase": ["lodash.camelcase@4.3.0", "", {}, "sha512-TwuEnCnxbc3rAvhf/LbG7tJUDzhqXyFnv3dtzLOPgCG/hODL7WFnsbwktkD7yUV0RrreP/l1PALq/YSg6VvjlA=="], - - "lodash.includes": ["lodash.includes@4.3.0", "", {}, "sha512-W3Bx6mdkRTGtlJISOvVD/lbqjTlPPUDTMnlXZFnVwi9NKJ6tiAk6LVdlhZMm17VZisqhKcgzpO5Wz91PCt5b0w=="], - - "lodash.isboolean": ["lodash.isboolean@3.0.3", "", {}, "sha512-Bz5mupy2SVbPHURB98VAcw+aHh4vRV5IPNhILUCsOzRmsTmSQ17jIuqopAentWoehktxGd9e/hbIXq980/1QJg=="], - - "lodash.isinteger": ["lodash.isinteger@4.0.4", "", {}, "sha512-DBwtEWN2caHQ9/imiNeEA5ys1JoRtRfY3d7V9wkqtbycnAmTvRRmbHKDV4a0EYc678/dia0jrte4tjYwVBaZUA=="], - - "lodash.isnumber": ["lodash.isnumber@3.0.3", "", {}, "sha512-QYqzpfwO3/CWf3XP+Z+tkQsfaLL/EnUlXWVkIk5FUPc4sBdTehEqZONuyRt2P67PXAk+NXmTBcc97zw9t1FQrw=="], - - "lodash.isplainobject": ["lodash.isplainobject@4.0.6", "", {}, "sha512-oSXzaWypCMHkPC3NvBEaPHf0KsA5mvPrOPgQWDsbg8n7orZ290M0BmC/jgRZ4vcJ6DTAhjrsSYgdsW/F+MFOBA=="], - - "lodash.isstring": ["lodash.isstring@4.0.1", "", {}, "sha512-0wJxfxH1wgO3GrbuP+dTTk7op+6L41QCXbGINEmD+ny/G/eCqGzxyCsh7159S+mgDDcoarnBw6PC1PS5+wUGgw=="], - - "lodash.once": ["lodash.once@4.1.1", "", {}, "sha512-Sb487aTOCr9drQVL8pIxOzVhafOjZN9UU54hiN8PU3uAiSV7lx1yYNpbNmex2PK6dSJoNTSJUUswT651yww3Mg=="], - - "logform": ["logform@2.7.0", "", { "dependencies": { "@colors/colors": "1.6.0", "@types/triple-beam": "^1.3.2", "fecha": "^4.2.0", "ms": "^2.1.1", "safe-stable-stringify": "^2.3.1", "triple-beam": "^1.3.0" } }, "sha512-TFYA4jnP7PVbmlBIfhlSe+WKxs9dklXMTEGcBCIvLhE/Tn3H6Gk1norupVW7m5Cnd4bLcr08AytbyV/xj7f/kQ=="], - - "long": ["long@5.3.2", "", {}, "sha512-mNAgZ1GmyNhD7AuqnTG3/VQ26o760+ZYBPKjPvugO8+nLbYfX6TVpJPseBvopbdY+qpZ/lKUnmEc1LeZYS3QAA=="], - "lru-cache": ["lru-cache@10.4.3", "", {}, "sha512-JNAzZcXrCt42VGLuYz0zfAzDfAvJWW6AfYlDBQyDV5DClI2m5sAmK+OIO7s59XfsRsWHp02jAJrRadPRGTt6SQ=="], "lru-queue": ["lru-queue@0.1.0", "", { "dependencies": { "es5-ext": "~0.10.2" } }, "sha512-BpdYkt9EvGl8OfWHDQPISVpcl5xZthb+XPsbELj5AQXxIC8IriDZIQYjBJPEm5rS420sjZ0TLEzRcq5KdBhYrQ=="], @@ -668,22 +509,24 @@ "math-intrinsics": ["math-intrinsics@1.1.0", "", {}, "sha512-/IXtbwEk5HTPyEwyKX6hGkYXxM9nbj64B+ilVJnC/R6B0pH5G4V3b0pVbL7DBj4tkhBAppbQUlf6F6Xl9LHu1g=="], + "media-typer": ["media-typer@1.1.0", "", {}, "sha512-aisnrDP4GNe06UcKFnV5bfMNPBUw4jsLGaWwWfnH3v02GnBuXX2MCVn5RbrWo0j3pczUilYblq7fQ7Nw2t5XKw=="], + "memoizee": ["memoizee@0.4.17", "", { "dependencies": { "d": "^1.0.2", "es5-ext": "^0.10.64", "es6-weak-map": "^2.0.3", "event-emitter": "^0.3.5", "is-promise": "^2.2.2", "lru-queue": "^0.1.0", "next-tick": "^1.1.0", "timers-ext": "^0.1.7" } }, "sha512-DGqD7Hjpi/1or4F/aYAspXKNm5Yili0QDAFAY4QYvpqpgiY6+1jOfqpmByzjxbWd/T9mChbCArXAbDAsTm5oXA=="], + "merge-descriptors": ["merge-descriptors@2.0.0", "", {}, "sha512-Snk314V5ayFLhp3fkUREub6WtjBfPdCPY1Ln8/8munuLuiYhsABgBVWsozAG+MWMbVEvcdcpbi9R7ww22l9Q3g=="], + "merge2": ["merge2@1.4.1", "", {}, "sha512-8q7VEgMJW4J8tcfVPy8g09NcQwZdbwFEqhe/WZkoIzjn/3TGDwtOCYtXGxA3O8tPzpczCCDgv+P2P5y00ZJOOg=="], "micromatch": ["micromatch@4.0.8", "", { "dependencies": { "braces": "^3.0.3", "picomatch": "^2.3.1" } }, "sha512-PXwfBhYu0hBCPw8Dn0E+WDYb7af3dSLVWKi3HGv84IdF4TyFoC0ysxFd0Goxw7nSv4T/PzEJQxsYsEiFCKo2BA=="], - "mime-db": ["mime-db@1.52.0", "", {}, "sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg=="], + "mime-db": ["mime-db@1.54.0", "", {}, "sha512-aU5EJuIN2WDemCcAp2vFBfp/m4EAhWJnUNSSw0ixs7/kXbd6Pg64EmwJkNdFhB8aWt1sH2CTXrLxo/iAGV3oPQ=="], - "mime-types": ["mime-types@2.1.35", "", { "dependencies": { "mime-db": "1.52.0" } }, "sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw=="], + "mime-types": ["mime-types@3.0.2", "", { "dependencies": { "mime-db": "^1.54.0" } }, "sha512-Lbgzdk0h4juoQ9fCKXW4by0UJqj+nOOrI9MJ1sSj4nI8aI2eo1qmvQEie4VD1glsS250n15LsWsYtCugiStS5A=="], "minimatch": ["minimatch@9.0.5", "", { "dependencies": { "brace-expansion": "^2.0.1" } }, "sha512-G6T0ZX48xgozx7587koeX9Ys2NYy6Gmv//P89sEte9V9whIapMNF4idKxnW2QtCcLiTWlb/wfCabAtAFWhhBow=="], "minipass": ["minipass@7.1.2", "", {}, "sha512-qOOzS1cBTWYF4BH8fVePDBOO9iptMnGUEZwNc/cMWnTV2nVLZ7VoNWEPHkYczZA0pdoA7dl6e7FL659nX9S2aw=="], - "module-details-from-path": ["module-details-from-path@1.0.4", "", {}, "sha512-EGWKgxALGMgzvxYF1UyGTy0HXX/2vHLkw6+NvDKW2jypWbHpjQuj4UMcqQWXHERJhVGKikolT06G3bcKe4fi7w=="], - "moment": ["moment@2.29.4", "", {}, "sha512-5LC9SOxjSc2HF6vO2CyuTDNivEdoz2IvyJJGj6X8DJ0eFyfszE0QiEd+iXmBvUP3WHxSjFH/vIsA0EN00cgr8w=="], "mri": ["mri@1.2.0", "", {}, "sha512-tzzskb3bG8LvYGFF/mDTpq3jpI6Q9wc3LEmBaghu+DdCssd1FakN7Bc0hVNmEyGq1bq3RgfkCb3cmQLpNPOroA=="], @@ -696,9 +539,9 @@ "nanoid": ["nanoid@3.3.11", "", { "bin": { "nanoid": "bin/nanoid.cjs" } }, "sha512-N8SpfPUnUp1bK+PMYW8qSWdl9U+wwNWI4QKxOYDy9JAro3WMX7p2OeVRF9v+347pnakNevPmiHhNmZ2HbFA76w=="], - "next-tick": ["next-tick@1.1.0", "", {}, "sha512-CXdUiJembsNjuToQvxayPZF9Vqht7hewsvy2sOWafLvi2awflj9mOC6bHIg50orX8IJvWKY9wYQ/zB2kogPslQ=="], + "negotiator": ["negotiator@1.0.0", "", {}, "sha512-8Ofs/AUQh8MaEcrlq5xOX0CQ9ypTF5dl78mjlMNfOK08fzpgTHQRQPBxcPlEtIw0yRpws+Zo/3r+5WRby7u3Gg=="], - "node-cache": ["node-cache@5.1.2", "", { "dependencies": { "clone": "2.x" } }, "sha512-t1QzWwnk4sjLWaQAS8CHgOJ+RAfmHpxFWmc36IWTiWHQfs0w5JDMBS1b1ZxQteo0vVVuWJvIUKHDkkeK7vIGCg=="], + "next-tick": ["next-tick@1.1.0", "", {}, "sha512-CXdUiJembsNjuToQvxayPZF9Vqht7hewsvy2sOWafLvi2awflj9mOC6bHIg50orX8IJvWKY9wYQ/zB2kogPslQ=="], "node-releases": ["node-releases@2.0.19", "", {}, "sha512-xxOWJsBKtzAq7DY0J+DTzuz58K8e7sJbdgwkbMWQe8UYB6ekmsQ45q0M/tJDsGaZmbC+l7n57UV8Hl5tHxO9uw=="], @@ -710,15 +553,13 @@ "object-hash": ["object-hash@3.0.0", "", {}, "sha512-RSn9F68PjH9HqtltsSnqYC1XXoWe9Bju5+213R98cNGttag9q9yAOTzdbsqvIa7aNm5WffBZFpWYr2aWrklWAw=="], - "obsidian": ["obsidian@1.10.0", "", { "dependencies": { "@types/codemirror": "5.60.8", "moment": "2.29.4" }, "peerDependencies": { "@codemirror/state": "6.5.0", "@codemirror/view": "6.38.1" } }, "sha512-F7hhnmGRQD1TanDPFT//LD3iKNUVd7N8sKL7flCCHRszfTxpDJ39j3T7LHbcGpyid906i6lD5oO+cnfLBzJMKw=="], + "object-inspect": ["object-inspect@1.13.4", "", {}, "sha512-W67iLl4J2EXEGTbfeHCffrjDfitvLANg0UlX3wFUUSTx92KXRFegMHUVgSqE+wvhAbi4WqjGg9czysTV2Epbew=="], - "ollama": ["ollama@0.6.3", "", { "dependencies": { "whatwg-fetch": "^3.6.20" } }, "sha512-KEWEhIqE5wtfzEIZbDCLH51VFZ6Z3ZSa6sIOg/E/tBV8S51flyqBOXi+bRxlOYKDf8i327zG9eSTb8IJxvm3Zg=="], - - "one-time": ["one-time@1.0.0", "", { "dependencies": { "fn.name": "1.x.x" } }, "sha512-5DXOiRKwuSEcQ/l0kGCF6Q3jcADFv5tSmRaJck/OqkVFcOzutB134KRSfF0xDrL39MNnqxbHBbUUcjZIhTgb2g=="], + "obsidian": ["obsidian@1.10.0", "", { "dependencies": { "@types/codemirror": "5.60.8", "moment": "2.29.4" }, "peerDependencies": { "@codemirror/state": "6.5.0", "@codemirror/view": "6.38.1" } }, "sha512-F7hhnmGRQD1TanDPFT//LD3iKNUVd7N8sKL7flCCHRszfTxpDJ39j3T7LHbcGpyid906i6lD5oO+cnfLBzJMKw=="], - "openai": ["openai@6.13.0", "", { "peerDependencies": { "ws": "^8.18.0", "zod": "^3.25 || ^4.0" }, "optionalPeers": ["ws", "zod"], "bin": { "openai": "bin/cli" } }, "sha512-yHbMo+EpNGPG3sRrXvmo0LhUPFN4bAURJw3G17bE+ax1G4tcTFCa9ZjvCWh3cvni0aHY0uWlk2IxcsPH4NR9Ow=="], + "on-finished": ["on-finished@2.4.1", "", { "dependencies": { "ee-first": "1.1.1" } }, "sha512-oVlzkg3ENAhCk2zdv7IJwd/QUD4z2RxRwpkcGY8psCVcCYZNq4wYnVWALHM+brtuJjePWiYF/ClmuDr8Ch5+kg=="], - "opossum": ["opossum@9.0.0", "", {}, "sha512-K76U0QkxOfUZamneQuzz+AP0fyfTJcCplZ2oZL93nxeupuJbN4s6uFNbmVCt4eWqqGqRnnowdFuBicJ1fLMVxw=="], + "once": ["once@1.4.0", "", { "dependencies": { "wrappy": "1" } }, "sha512-lNaJgI+2Q5URQBkccEKHTQOPaXdUxnZZElQTZY0MFUAuaEqe1E+Nyvgdz/aIyNi6Z9MzO5dv1H8n58/GELp3+w=="], "p-finally": ["p-finally@1.0.0", "", {}, "sha512-LICb2p9CB7FS+0eR1oqWnHhp0FljGLZCWBE9aix0Uye9W8LTQPwMTYVGWQWIw9RdQiDg4+epXQODwIYJtSJaow=="], @@ -730,7 +571,7 @@ "package-json-from-dist": ["package-json-from-dist@1.0.1", "", {}, "sha512-UEZIS3/by4OC8vL3P2dTXRETpebLI2NiI5vIrjaD/5UtrkFX/tNbwjTSRAGC/+7CAo2pIcBaRgWmcBBHcsaCIw=="], - "papa-ts": ["papa-ts@2.7.4", "", { "dependencies": { "@langchain/anthropic": "^1.1.0", "@langchain/core": "^1.0.2", "@langchain/langgraph": "^1.0.1", "@langchain/ollama": "^1.0.1", "@langchain/openai": "^1.1.2", "@langfuse/langchain": "^4.4.0", "@langfuse/otel": "^4.4.2", "@opentelemetry/sdk-node": "^0.208.0", "@sap-ai-sdk/langchain": "^2.3.0", "dotenv": "^17.2.3", "langchain": "^1.0.2", "langfuse": "^3.38.6", "langsmith": "^0.3.79", "zod": "^4.1.12" } }, "sha512-sNjlhtuludtBGHqW5efYAprE2UgABI7zWP6Y/HCOtvrfLWDyDlBRDNYv+2QF8bR+c6H5Fdk5UPgCCERnTRnE6g=="], + "parseurl": ["parseurl@1.3.3", "", {}, "sha512-CiyeOxFT/JZyN5m0z9PfXw4SCBJ6Sygz1Dpl0wqjlhDEGGBP1GnsUVEL0p63hoG1fcj3fHynXi9NYO4nWOL+qQ=="], "path-key": ["path-key@3.1.1", "", {}, "sha512-ojmeN0qd+y0jszEtoY48r0Peq5dwMEkIlCOu6Q5f41lfkswXuKtYrhgoTpLnyIcHm24Uhqx+5Tqm2InSwLhE6Q=="], @@ -738,6 +579,8 @@ "path-scurry": ["path-scurry@1.11.1", "", { "dependencies": { "lru-cache": "^10.2.0", "minipass": "^5.0.0 || ^6.0.2 || ^7.0.0" } }, "sha512-Xa4Nw17FS9ApQFJ9umLiJS4orGjm7ZzwUrwamcGQuHSzDyth9boKDaycYdDcZDuqYATXw4HFXgaqWTctW/v1HA=="], + "path-to-regexp": ["path-to-regexp@8.3.0", "", {}, "sha512-7jdwVIRtsP8MYpdXSwOS0YdD0Du+qOoF/AEPIt88PcCFrZCzx41oxku1jD88hZBwbNUIEfpqvuhjFaMAqMTWnA=="], + "picocolors": ["picocolors@1.1.1", "", {}, "sha512-xceH2snhtb5M9liqDsmEw56le376mTZkEX/jEb/RxNFyegNul7eNslCXP9FDj/Lcu0X8KEyMceP2ntpaHrDEVA=="], "picomatch": ["picomatch@4.0.3", "", {}, "sha512-5gTmgEY/sqK6gFXLIsQNH19lWb4ebPDLA4SdLP7dsWkIXHWlG66oPuVvXSGFPppYZz8ZDZq0dYYrbHfBCVUb1Q=="], @@ -746,6 +589,8 @@ "pirates": ["pirates@4.0.7", "", {}, "sha512-TfySrs/5nm8fQJDcBDuUng3VOUKsd7S+zqvbOTiGXHfxX4wK31ard+hoNuvkicM/2YFzlpDgABOevKSsB4G/FA=="], + "pkce-challenge": ["pkce-challenge@5.0.1", "", {}, "sha512-wQ0b/W4Fr01qtpHlqSqspcj3EhBvimsdh0KlHhH8HRZnMsEa0ea2fTULOXOS9ccQr3om+GcGRk4e+isrZWV8qQ=="], + "postcss": ["postcss@8.5.6", "", { "dependencies": { "nanoid": "^3.3.11", "picocolors": "^1.1.1", "source-map-js": "^1.2.1" } }, "sha512-3Ybi1tAuwAP9s0r1UQ2J4n5Y0G05bJkpUIO0/bI9MhwmD70S5aTWbXGBwxHrelT+XM1k6dM0pk+SwNkpTRN7Pg=="], "postcss-import": ["postcss-import@15.1.0", "", { "dependencies": { "postcss-value-parser": "^4.0.0", "read-cache": "^1.0.0", "resolve": "^1.1.7" }, "peerDependencies": { "postcss": "^8.0.0" } }, "sha512-hpr+J05B2FVYUAXHeK1YyI267J/dDDhMU6B6civm8hSY1jYJnBXxzKDKDswzJmtLHryrjhnDjqqp/49t8FALew=="], @@ -760,21 +605,21 @@ "postcss-value-parser": ["postcss-value-parser@4.2.0", "", {}, "sha512-1NNCs6uurfkVbeXG4S8JFT9t19m45ICnif8zWLd5oPSZ50QnwMfK+H3jv408d4jw/7Bttv5axS5IiHoLaVNHeQ=="], - "protobufjs": ["protobufjs@7.5.4", "", { "dependencies": { "@protobufjs/aspromise": "^1.1.2", "@protobufjs/base64": "^1.1.2", "@protobufjs/codegen": "^2.0.4", "@protobufjs/eventemitter": "^1.1.0", "@protobufjs/fetch": "^1.1.0", "@protobufjs/float": "^1.0.2", "@protobufjs/inquire": "^1.1.0", "@protobufjs/path": "^1.1.2", "@protobufjs/pool": "^1.1.0", "@protobufjs/utf8": "^1.1.0", "@types/node": ">=13.7.0", "long": "^5.0.0" } }, "sha512-CvexbZtbov6jW2eXAvLukXjXUW1TzFaivC46BpWc/3BpcCysb5Vffu+B3XHMm8lVEuy2Mm4XGex8hBSg1yapPg=="], + "proxy-addr": ["proxy-addr@2.0.7", "", { "dependencies": { "forwarded": "0.2.0", "ipaddr.js": "1.9.1" } }, "sha512-llQsMLSUDUPT44jdrU/O37qlnifitDP+ZwrmmZcoSKyLKvtZxpyV0n2/bD/N4tBAAZ/gJEdZU7KMraoK1+XYAg=="], - "proxy-from-env": ["proxy-from-env@1.1.0", "", {}, "sha512-D+zkORCbA9f1tdWRK0RaCR3GPv50cMxcrz4X8k5LTSUD1Dkw47mKJEZQNunItRTkWwgtaUSo1RVFRIG9ZXiFYg=="], + "punycode": ["punycode@2.3.1", "", {}, "sha512-vYt7UD1U9Wg6138shLtLOvdAu+8DsC/ilFtEVHcH+wydcSpNE20AfSOduf6MkRFahL5FY7X1oU7nKVZFtfq8Fg=="], - "queue-microtask": ["queue-microtask@1.2.3", "", {}, "sha512-NuaNSa6flKT5JaSYQzJok04JzTL1CA6aGhv5rfLW3PgqA+M2ChpZQnAC8h8i4ZFkBS8X5RqkDBHA7r4hej3K9A=="], + "qs": ["qs@6.14.0", "", { "dependencies": { "side-channel": "^1.1.0" } }, "sha512-YWWTjgABSKcvs/nWBi9PycY/JiPJqOD4JA6o9Sej2AtvSGarXxKC3OQSk4pAarbdQlKAh5D4FCQkJNkW+GAn3w=="], - "read-cache": ["read-cache@1.0.0", "", { "dependencies": { "pify": "^2.3.0" } }, "sha512-Owdv/Ft7IjOgm/i0xvNDZ1LrRANRfew4b2prF3OWMQLxLfu3bS8FVhCsrSCMK4lR56Y9ya+AThoTpDCTxCmpRA=="], + "queue-microtask": ["queue-microtask@1.2.3", "", {}, "sha512-NuaNSa6flKT5JaSYQzJok04JzTL1CA6aGhv5rfLW3PgqA+M2ChpZQnAC8h8i4ZFkBS8X5RqkDBHA7r4hej3K9A=="], - "readable-stream": ["readable-stream@3.6.2", "", { "dependencies": { "inherits": "^2.0.3", "string_decoder": "^1.1.1", "util-deprecate": "^1.0.1" } }, "sha512-9u/sniCrY3D5WdsERHzHE4G2YCXqoG5FTHUiCC4SIbr6XcLZBY05ya9EKjYek9O5xOAwjGq+1JdGBAS7Q9ScoA=="], + "range-parser": ["range-parser@1.2.1", "", {}, "sha512-Hrgsx+orqoygnmhFbKaHE6c296J+HTAQXoxEF6gNupROmmGJRoyzfG3ccAveqCBrwr/2yxQ5BVd/GTl5agOwSg=="], - "readdirp": ["readdirp@4.1.2", "", {}, "sha512-GDhwkLfywWL2s6vEjyhri+eXmfH6j1L7JE27WhqLeYzoh/A3DBaYGEj2H/HFZCn/kMfim73FXxEJTw06WtxQwg=="], + "raw-body": ["raw-body@3.0.2", "", { "dependencies": { "bytes": "~3.1.2", "http-errors": "~2.0.1", "iconv-lite": "~0.7.0", "unpipe": "~1.0.0" } }, "sha512-K5zQjDllxWkf7Z5xJdV0/B0WTNqx6vxG70zJE4N0kBs4LovmEYWJzQGxC9bS9RAKu3bgM40lrd5zoLJ12MQ5BA=="], - "require-directory": ["require-directory@2.1.1", "", {}, "sha512-fGxEI7+wsG9xrvdjsrlmL22OMTTiHRwAMroiEeMgq8gzoLC/PQr7RsRDSTLUg/bZAZtF+TVIkHc6/4RIKrui+Q=="], + "read-cache": ["read-cache@1.0.0", "", { "dependencies": { "pify": "^2.3.0" } }, "sha512-Owdv/Ft7IjOgm/i0xvNDZ1LrRANRfew4b2prF3OWMQLxLfu3bS8FVhCsrSCMK4lR56Y9ya+AThoTpDCTxCmpRA=="], - "require-in-the-middle": ["require-in-the-middle@8.0.1", "", { "dependencies": { "debug": "^4.3.5", "module-details-from-path": "^1.0.3" } }, "sha512-QT7FVMXfWOYFbeRBF6nu+I6tr2Tf3u0q8RIEjNob/heKY/nh7drD/k7eeMFmSQgnTtCzLDcCu/XEnpW2wk4xCQ=="], + "readdirp": ["readdirp@4.1.2", "", {}, "sha512-GDhwkLfywWL2s6vEjyhri+eXmfH6j1L7JE27WhqLeYzoh/A3DBaYGEj2H/HFZCn/kMfim73FXxEJTw06WtxQwg=="], "resolve": ["resolve@1.22.10", "", { "dependencies": { "is-core-module": "^2.16.0", "path-parse": "^1.0.7", "supports-preserve-symlinks-flag": "^1.0.0" }, "bin": { "resolve": "bin/resolve" } }, "sha512-NPRy+/ncIMeDlTAsuqwKIiferiawhefFJtkNSW0qZJEqMEb+qBt/77B/jGeeek+F0uOeN05CDa6HXbbIgtVX4w=="], @@ -784,36 +629,48 @@ "rollup": ["rollup@4.53.3", "", { "dependencies": { "@types/estree": "1.0.8" }, "optionalDependencies": { "@rollup/rollup-android-arm-eabi": "4.53.3", "@rollup/rollup-android-arm64": "4.53.3", "@rollup/rollup-darwin-arm64": "4.53.3", "@rollup/rollup-darwin-x64": "4.53.3", "@rollup/rollup-freebsd-arm64": "4.53.3", "@rollup/rollup-freebsd-x64": "4.53.3", "@rollup/rollup-linux-arm-gnueabihf": "4.53.3", "@rollup/rollup-linux-arm-musleabihf": "4.53.3", "@rollup/rollup-linux-arm64-gnu": "4.53.3", "@rollup/rollup-linux-arm64-musl": "4.53.3", "@rollup/rollup-linux-loong64-gnu": "4.53.3", "@rollup/rollup-linux-ppc64-gnu": "4.53.3", "@rollup/rollup-linux-riscv64-gnu": "4.53.3", "@rollup/rollup-linux-riscv64-musl": "4.53.3", "@rollup/rollup-linux-s390x-gnu": "4.53.3", "@rollup/rollup-linux-x64-gnu": "4.53.3", "@rollup/rollup-linux-x64-musl": "4.53.3", "@rollup/rollup-openharmony-arm64": "4.53.3", "@rollup/rollup-win32-arm64-msvc": "4.53.3", "@rollup/rollup-win32-ia32-msvc": "4.53.3", "@rollup/rollup-win32-x64-gnu": "4.53.3", "@rollup/rollup-win32-x64-msvc": "4.53.3", "fsevents": "~2.3.2" }, "bin": { "rollup": "dist/bin/rollup" } }, "sha512-w8GmOxZfBmKknvdXU1sdM9NHcoQejwF/4mNgj2JuEEdRaHwwF12K7e9eXn1nLZ07ad+du76mkVsyeb2rKGllsA=="], + "router": ["router@2.2.0", "", { "dependencies": { "debug": "^4.4.0", "depd": "^2.0.0", "is-promise": "^4.0.0", "parseurl": "^1.3.3", "path-to-regexp": "^8.0.0" } }, "sha512-nLTrUKm2UyiL7rlhapu/Zl45FwNgkZGaCpZbIHajDYgwlJCOzLSk+cIPAnsEqV955GjILJnKbdQC1nVPz+gAYQ=="], + "run-parallel": ["run-parallel@1.2.0", "", { "dependencies": { "queue-microtask": "^1.2.2" } }, "sha512-5l4VyZR86LZ/lDxZTR6jqL8AFE2S0IFLMP26AbjsLVADxHdhB/c0GUsH+y39UfCi3dzz8OlQuPmnaJOMoDHQBA=="], "runed": ["runed@0.35.1", "", { "dependencies": { "dequal": "^2.0.3", "esm-env": "^1.0.0", "lz-string": "^1.5.0" }, "peerDependencies": { "@sveltejs/kit": "^2.21.0", "svelte": "^5.7.0" }, "optionalPeers": ["@sveltejs/kit"] }, "sha512-2F4Q/FZzbeJTFdIS/PuOoPRSm92sA2LhzTnv6FXhCoENb3huf5+fDuNOg1LNvGOouy3u/225qxmuJvcV3IZK5Q=="], "sade": ["sade@1.8.1", "", { "dependencies": { "mri": "^1.1.0" } }, "sha512-xal3CZX1Xlo/k4ApwCFrHVACi9fBqJ7V+mwhBsuf/1IOKbBy098Fex+Wa/5QMubw09pSZ/u8EY8PWgevJsXp1A=="], - "safe-buffer": ["safe-buffer@5.2.1", "", {}, "sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ=="], - - "safe-stable-stringify": ["safe-stable-stringify@2.5.0", "", {}, "sha512-b3rppTKm9T+PsVCBEOUR46GWI7fdOs00VKZ1+9c1EWDaDMvjQc6tUwuFyIprgGgTcWoVHSKrU8H31ZHA2e0RHA=="], + "safer-buffer": ["safer-buffer@2.1.2", "", {}, "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg=="], "semver": ["semver@7.7.3", "", { "bin": { "semver": "bin/semver.js" } }, "sha512-SdsKMrI9TdgjdweUSR9MweHA4EJ8YxHn8DFaDisvhVlUOe4BF1tLD7GAj0lIqWVl+dPb/rExr0Btby5loQm20Q=="], + "send": ["send@1.2.1", "", { "dependencies": { "debug": "^4.4.3", "encodeurl": "^2.0.0", "escape-html": "^1.0.3", "etag": "^1.8.1", "fresh": "^2.0.0", "http-errors": "^2.0.1", "mime-types": "^3.0.2", "ms": "^2.1.3", "on-finished": "^2.4.1", "range-parser": "^1.2.1", "statuses": "^2.0.2" } }, "sha512-1gnZf7DFcoIcajTjTwjwuDjzuz4PPcY2StKPlsGAQ1+YH20IRVrBaXSWmdjowTJ6u8Rc01PoYOGHXfP1mYcZNQ=="], + + "serve-static": ["serve-static@2.2.1", "", { "dependencies": { "encodeurl": "^2.0.0", "escape-html": "^1.0.3", "parseurl": "^1.3.3", "send": "^1.2.0" } }, "sha512-xRXBn0pPqQTVQiC8wyQrKs2MOlX24zQ0POGaj0kultvoOCstBQM5yvOhAVSUwOMjQtTvsPWoNCHfPGwaaQJhTw=="], + + "setprototypeof": ["setprototypeof@1.2.0", "", {}, "sha512-E5LDX7Wrp85Kil5bhZv46j8jOeboKq5JMmYM3gVGdGH8xFpPWXUMsNrlODCrkoxMEeNi/XZIwuRvY4XNwYMJpw=="], + "shebang-command": ["shebang-command@2.0.0", "", { "dependencies": { "shebang-regex": "^3.0.0" } }, "sha512-kHxr2zZpYtdmrN1qDjrrX/Z1rR1kG8Dx+gkpK1G4eXmvXswmcE1hTWBWYUzlraYw1/yZp6YuDY77YtvbN0dmDA=="], "shebang-regex": ["shebang-regex@3.0.0", "", {}, "sha512-7++dFhtcx3353uBaq8DDR4NuxBetBzC7ZQOhmTQInHEd6bSrXdiEyzCvG07Z44UYdLShWUyXt5M/yhz8ekcb1A=="], + "side-channel": ["side-channel@1.1.0", "", { "dependencies": { "es-errors": "^1.3.0", "object-inspect": "^1.13.3", "side-channel-list": "^1.0.0", "side-channel-map": "^1.0.1", "side-channel-weakmap": "^1.0.2" } }, "sha512-ZX99e6tRweoUXqR+VBrslhda51Nh5MTQwou5tnUDgbtyM0dBgmhEDtWGP/xbKn6hqfPRHujUNwz5fy/wbbhnpw=="], + + "side-channel-list": ["side-channel-list@1.0.0", "", { "dependencies": { "es-errors": "^1.3.0", "object-inspect": "^1.13.3" } }, "sha512-FCLHtRD/gnpCiCHEiJLOwdmFP+wzCmDEkc9y7NsYxeF4u7Btsn1ZuwgwJGxImImHicJArLP4R0yX4c2KCrMrTA=="], + + "side-channel-map": ["side-channel-map@1.0.1", "", { "dependencies": { "call-bound": "^1.0.2", "es-errors": "^1.3.0", "get-intrinsic": "^1.2.5", "object-inspect": "^1.13.3" } }, "sha512-VCjCNfgMsby3tTdo02nbjtM/ewra6jPHmpThenkTYh8pG9ucZ/1P8So4u4FGBek/BjpOVsDCMoLA/iuBKIFXRA=="], + + "side-channel-weakmap": ["side-channel-weakmap@1.0.2", "", { "dependencies": { "call-bound": "^1.0.2", "es-errors": "^1.3.0", "get-intrinsic": "^1.2.5", "object-inspect": "^1.13.3", "side-channel-map": "^1.0.1" } }, "sha512-WPS/HvHQTYnHisLo9McqBHOJk2FkHO/tlpvldyrnem4aeQp4hai3gythswg6p01oSoTl58rcpiFAjF2br2Ak2A=="], + "signal-exit": ["signal-exit@4.1.0", "", {}, "sha512-bzyZ1e88w9O1iNJbKnOlvYTrWPDl46O1bG0D3XInv+9tkPrxrN8jUUTiFlDkkmKWgn1M6CfIA13SuGqOa9Korw=="], "simple-wcswidth": ["simple-wcswidth@1.1.2", "", {}, "sha512-j7piyCjAeTDSjzTSQ7DokZtMNwNlEAyxqSZeCS+CXH7fJ4jx3FuJ/mTW3mE+6JLs4VJBbcll0Kjn+KXI5t21Iw=="], "source-map-js": ["source-map-js@1.2.1", "", {}, "sha512-UXWMKhLOwVKb728IUtQPXxfYU+usdybtUrK/8uGE8CQMvrhOpwvzDBwj0QhSL7MQc7vIsISBG8VQ8+IDQxpfQA=="], - "stack-trace": ["stack-trace@0.0.10", "", {}, "sha512-KGzahc7puUKkzyMt+IqAep+TVNbKP+k2Lmwhub39m1AsTSkaDutx56aDCo+HLDzf/D26BIHTJWNiTG1KAJiQCg=="], + "statuses": ["statuses@2.0.2", "", {}, "sha512-DvEy55V3DB7uknRo+4iOGT5fP1slR8wQohVdknigZPMpMstaKJQWhwiYBACJE3Ul2pTnATihhBYnRhZQHGBiRw=="], "string-width": ["string-width@5.1.2", "", { "dependencies": { "eastasianwidth": "^0.2.0", "emoji-regex": "^9.2.2", "strip-ansi": "^7.0.1" } }, "sha512-HnLOCR3vjcY8beoNLtcjZ5/nxn2afmME6lhrDrebokqMap+XbeW8n9TXpPDOqdGK5qcI3oT0GKTW6wC7EMiVqA=="], "string-width-cjs": ["string-width@4.2.3", "", { "dependencies": { "emoji-regex": "^8.0.0", "is-fullwidth-code-point": "^3.0.0", "strip-ansi": "^6.0.1" } }, "sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g=="], - "string_decoder": ["string_decoder@1.3.0", "", { "dependencies": { "safe-buffer": "~5.2.0" } }, "sha512-hkRX8U1WjJFd8LsDJ2yQ/wWWxaopEsABU1XfkM8A+j0+85JAGppt16cr1Whg6KIbb4okU6Mql6BOj+uup/wKeA=="], - "strip-ansi": ["strip-ansi@7.1.0", "", { "dependencies": { "ansi-regex": "^6.0.1" } }, "sha512-iq6eVVI64nQQTRYq2KtEg2d2uU7LElhTJwsH4YzIHZshxlgZms/wIc4VoDQTlG/IvVIrBKG06CrZnp0qv7hkcQ=="], "strip-ansi-cjs": ["strip-ansi@6.0.1", "", { "dependencies": { "ansi-regex": "^5.0.1" } }, "sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A=="], @@ -840,8 +697,6 @@ "tailwindcss": ["tailwindcss@3.4.18", "", { "dependencies": { "@alloc/quick-lru": "^5.2.0", "arg": "^5.0.2", "chokidar": "^3.6.0", "didyoumean": "^1.2.2", "dlv": "^1.1.3", "fast-glob": "^3.3.2", "glob-parent": "^6.0.2", "is-glob": "^4.0.3", "jiti": "^1.21.7", "lilconfig": "^3.1.3", "micromatch": "^4.0.8", "normalize-path": "^3.0.0", "object-hash": "^3.0.0", "picocolors": "^1.1.1", "postcss": "^8.4.47", "postcss-import": "^15.1.0", "postcss-js": "^4.0.1", "postcss-load-config": "^4.0.2 || ^5.0 || ^6.0", "postcss-nested": "^6.2.0", "postcss-selector-parser": "^6.1.2", "resolve": "^1.22.8", "sucrase": "^3.35.0" }, "bin": { "tailwind": "lib/cli.js", "tailwindcss": "lib/cli.js" } }, "sha512-6A2rnmW5xZMdw11LYjhcI5846rt9pbLSabY5XPxo+XWdxwZaFEn47Go4NzFiHu9sNNmr/kXivP1vStfvMaK1GQ=="], - "text-hex": ["text-hex@1.0.0", "", {}, "sha512-uuVGNWzgJ4yhRaNSiubPY7OjISw4sw4E5Uv0wbjp+OzcbmVU/rsT8ujgcXJhn9ypzsgr5vlzpPqP+MBBKcGvbg=="], - "thenify": ["thenify@3.3.1", "", { "dependencies": { "any-promise": "^1.0.0" } }, "sha512-RVZSIV5IG10Hk3enotrhvz0T9em6cyHBLkH/YAZuKqd8hRkKhSfCGIcP2KUY0EPxndzANBmNllzWPwak+bheSw=="], "thenify-all": ["thenify-all@1.6.0", "", { "dependencies": { "thenify": ">= 3.1.0 < 4" } }, "sha512-RNxQH/qI8/t3thXJDwcstUO4zeqo64+Uy/+sNVRBx4Xn2OX+OZ9oP+iJnNFqplFra2ZUVeKCSa2oVWi3T4uVmA=="], @@ -854,9 +709,7 @@ "to-regex-range": ["to-regex-range@5.0.1", "", { "dependencies": { "is-number": "^7.0.0" } }, "sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ=="], - "triple-beam": ["triple-beam@1.4.1", "", {}, "sha512-aZbgViZrg1QNcG+LULa7nhZpJTZSLm/mXnHXnbAbjmN5aSa0y7V+wvv6+4WaBtpISJzThKy+PIPxc1Nq1EJ9mg=="], - - "ts-algebra": ["ts-algebra@2.0.0", "", {}, "sha512-FPAhNPFMrkwz76P7cdjdmiShwMynZYN6SgOujD1urY4oNm80Ou9oMdmbR45LotcKOXoy7wSmHkRFE6Mxbrhefw=="], + "toidentifier": ["toidentifier@1.0.1", "", {}, "sha512-o5sSPKEkg/DIQNmH43V0/uerLrpzVedkUh8tGNvaeXpfpuwjKenlSox/2O/BTlZUtEe+JG7s5YhEz608PlAHRA=="], "ts-interface-checker": ["ts-interface-checker@0.1.13", "", {}, "sha512-Y/arvbn+rrz3JCKl9C4kVNfTfSm2/mEp5FSz5EsZSANGPSlQrpRI5M4PKF+mJnE52jOO90PnPSc3Ur3bTQw0gA=="], @@ -864,50 +717,46 @@ "type": ["type@2.7.3", "", {}, "sha512-8j+1QmAbPvLZow5Qpi6NCaN8FB60p/6x8/vfNqOk/hC+HuvFZhL4+WfekuhQLiqFZXOgQdrs3B+XxEmCc6b3FQ=="], + "type-is": ["type-is@2.0.1", "", { "dependencies": { "content-type": "^1.0.5", "media-typer": "^1.1.0", "mime-types": "^3.0.0" } }, "sha512-OZs6gsjF4vMp32qrCbiVSkrFmXtG/AZhY3t0iAMrMBiAZyV9oALtXO8hsrHbMXF9x6L3grlFuwW2oAz7cav+Gw=="], + "typescript": ["typescript@5.9.3", "", { "bin": { "tsc": "bin/tsc", "tsserver": "bin/tsserver" } }, "sha512-jl1vZzPDinLr9eUt3J/t7V6FgNEw9QjvBPdysz9KfQDD41fQrC2Y4vKQdiaUpFT4bXlb1RHhLpp8wtm6M5TgSw=="], "undici-types": ["undici-types@7.16.0", "", {}, "sha512-Zz+aZWSj8LE6zoxD+xrjh4VfkIG8Ya6LvYkZqtUQGJPZjYl53ypCaUwWqo7eI0x66KBGeRo+mlBEkMSeSZ38Nw=="], + "unpipe": ["unpipe@1.0.0", "", {}, "sha512-pjy2bYhSsufwWlKwPc+l3cN7+wuJlK6uz0YdJEOlQDbl6jo/YlPi4mb8agUkVC8BF7V8NuzeyPNqRksA3hztKQ=="], + "update-browserslist-db": ["update-browserslist-db@1.1.3", "", { "dependencies": { "escalade": "^3.2.0", "picocolors": "^1.1.1" }, "peerDependencies": { "browserslist": ">= 4.21.0" }, "bin": { "update-browserslist-db": "cli.js" } }, "sha512-UxhIZQ+QInVdunkDAaiazvvT/+fXL5Osr0JZlJulepYu6Jd7qJtDZjlur0emRlT71EN3ScPoE7gvsuIKKNavKw=="], + "uri-js": ["uri-js@4.4.1", "", { "dependencies": { "punycode": "^2.1.0" } }, "sha512-7rKUyy33Q1yc98pQ1DAmLtwX109F7TIfWlW1Ydo8Wl1ii1SeHieeh0HHfPeL2fMXK6z0s8ecKs9frCuLJvndBg=="], + "util-deprecate": ["util-deprecate@1.0.2", "", {}, "sha512-EPD5q1uXyFxJpCrLnCc1nHnq3gOa6DZBocAIiI2TaSCA7VCJ1UJDMagCzIkXNsUYfD1daK//LTEQ8xiIbrHtcw=="], "uuid": ["uuid@11.1.0", "", { "bin": { "uuid": "dist/esm/bin/uuid" } }, "sha512-0/A9rDy9P7cJ+8w1c9WD9V//9Wj15Ce2MPz8Ri6032usz+NfePxx5AcN3bN+r6ZL6jEo066/yNYB3tn4pQEx+A=="], - "verror": ["verror@1.10.1", "", { "dependencies": { "assert-plus": "^1.0.0", "core-util-is": "1.0.2", "extsprintf": "^1.2.0" } }, "sha512-veufcmxri4e3XSrT0xwfUR7kguIkaxBeosDg00yDWhk49wdwkSUrvvsm7nc75e1PUyvIeZj6nS8VQRYz2/S4Xg=="], + "vary": ["vary@1.1.2", "", {}, "sha512-BNGbWLfd0eUPabhkXUVm0j8uuvREyTh5ovRa/dyow/BqAbZJyC+5fU+IzQOzmAKzYqYRAISoRhdQr3eIZ/PXqg=="], "vite": ["vite@7.2.7", "", { "dependencies": { "esbuild": "^0.25.0", "fdir": "^6.5.0", "picomatch": "^4.0.3", "postcss": "^8.5.6", "rollup": "^4.43.0", "tinyglobby": "^0.2.15" }, "optionalDependencies": { "fsevents": "~2.3.3" }, "peerDependencies": { "@types/node": "^20.19.0 || >=22.12.0", "jiti": ">=1.21.0", "less": "^4.0.0", "lightningcss": "^1.21.0", "sass": "^1.70.0", "sass-embedded": "^1.70.0", "stylus": ">=0.54.8", "sugarss": "^5.0.0", "terser": "^5.16.0", "tsx": "^4.8.1", "yaml": "^2.4.2" }, "optionalPeers": ["@types/node", "jiti", "less", "lightningcss", "sass", "sass-embedded", "stylus", "sugarss", "terser", "tsx", "yaml"], "bin": { "vite": "bin/vite.js" } }, "sha512-ITcnkFeR3+fI8P1wMgItjGrR10170d8auB4EpMLPqmx6uxElH3a/hHGQabSHKdqd4FXWO1nFIp9rRn7JQ34ACQ=="], "vitefu": ["vitefu@1.0.6", "", { "peerDependencies": { "vite": "^3.0.0 || ^4.0.0 || ^5.0.0 || ^6.0.0" }, "optionalPeers": ["vite"] }, "sha512-+Rex1GlappUyNN6UfwbVZne/9cYC4+R2XDk9xkNXBKMw6HQagdX9PgZ8V2v1WUSK1wfBLp7qbI1+XSNIlB1xmA=="], - "voca": ["voca@1.4.1", "", {}, "sha512-NJC/BzESaHT1p4B5k4JykxedeltmNbau4cummStd4RjFojgq/kLew5TzYge9N2geeWyI2w8T30wUET5v+F7ZHA=="], - "w3c-keyname": ["w3c-keyname@2.2.8", "", {}, "sha512-dpojBhNsCNN7T82Tm7k26A6G9ML3NkhDsnw9n/eoxSRlVBB4CEtIQ/KTCLI2Fwf3ataSXRhYFkQi3SlnFwPvPQ=="], - "whatwg-fetch": ["whatwg-fetch@3.6.20", "", {}, "sha512-EqhiFU6daOA8kpjOWTL0olhVOF3i7OrFzSYiGsEMB8GcXS+RrzauAERX65xMeNWVqxA6HXH2m69Z9LaKKdisfg=="], - "which": ["which@2.0.2", "", { "dependencies": { "isexe": "^2.0.0" }, "bin": { "node-which": "./bin/node-which" } }, "sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA=="], - "winston": ["winston@3.19.0", "", { "dependencies": { "@colors/colors": "^1.6.0", "@dabh/diagnostics": "^2.0.8", "async": "^3.2.3", "is-stream": "^2.0.0", "logform": "^2.7.0", "one-time": "^1.0.0", "readable-stream": "^3.4.0", "safe-stable-stringify": "^2.3.1", "stack-trace": "0.0.x", "triple-beam": "^1.3.0", "winston-transport": "^4.9.0" } }, "sha512-LZNJgPzfKR+/J3cHkxcpHKpKKvGfDZVPS4hfJCc4cCG0CgYzvlD6yE/S3CIL/Yt91ak327YCpiF/0MyeZHEHKA=="], - - "winston-transport": ["winston-transport@4.9.0", "", { "dependencies": { "logform": "^2.7.0", "readable-stream": "^3.6.2", "triple-beam": "^1.3.0" } }, "sha512-8drMJ4rkgaPo1Me4zD/3WLfI/zPdA9o2IipKODunnGDcuqbHwjsbB79ylv04LCGGzU0xQ6vTznOMpQGaLhhm6A=="], - "wrap-ansi": ["wrap-ansi@8.1.0", "", { "dependencies": { "ansi-styles": "^6.1.0", "string-width": "^5.0.1", "strip-ansi": "^7.0.1" } }, "sha512-si7QWI6zUMq56bESFvagtmzMdGOtoxfR+Sez11Mobfc7tm+VkUckk9bW2UeffTGVUbOksxmSw0AA2gs8g71NCQ=="], "wrap-ansi-cjs": ["wrap-ansi@7.0.0", "", { "dependencies": { "ansi-styles": "^4.0.0", "string-width": "^4.1.0", "strip-ansi": "^6.0.0" } }, "sha512-YVGIj2kamLSTxw6NsZjoBxfSwsn0ycdesmc4p+Q21c5zPuZ1pl+NfxVdxPtdHvmNVOQ6XSYG4AUtyt/Fi7D16Q=="], - "y18n": ["y18n@5.0.8", "", {}, "sha512-0pfFzegeDWJHJIAmTLRP2DwHjdF5s7jo9tuztdQxAhINCdvS+3nGINqPd00AphqJR/0LhANUS6/+7SCb98YOfA=="], + "wrappy": ["wrappy@1.0.2", "", {}, "sha512-l4Sp/DRseor9wL6EvV2+TuQn63dMkPjZ/sp9XkghTEbV9KlPS1xUsZ3u7/IQO4wxtcFB4bgpQPRcR3QCvezPcQ=="], "yaml": ["yaml@2.8.0", "", { "bin": { "yaml": "bin.mjs" } }, "sha512-4lLa/EcQCB0cJkyts+FpIRx5G/llPxfP6VQU5KByHEhLxY3IJCH0f0Hy1MHI8sClTvsIb8qwRJ6R/ZdlDJ/leQ=="], - "yargs": ["yargs@17.7.2", "", { "dependencies": { "cliui": "^8.0.1", "escalade": "^3.1.1", "get-caller-file": "^2.0.5", "require-directory": "^2.1.1", "string-width": "^4.2.3", "y18n": "^5.0.5", "yargs-parser": "^21.1.1" } }, "sha512-7dSzzRQ++CKnNI/krKnYRV7JKKPUXMEh61soaHKg9mrWEhzFWhFnxPxGl+69cD1Ou63C13NUPCnmIcrvqCuM6w=="], - - "yargs-parser": ["yargs-parser@21.1.1", "", {}, "sha512-tVpsJW7DdjecAiFpbIB1e3qxIQsE6NoPc5/eTdrbbIC4h0LVsWhnoa3g+m2HclBIujHzsxZ4VJVA+GUuc2/LBw=="], - "zimmerframe": ["zimmerframe@1.1.2", "", {}, "sha512-rAbqEGa8ovJy4pyBxZM70hg4pE6gDgaQ0Sl9M3enG3I0d6H4XSAM3GeNGLKnsBpuijUow064sf7ww1nutC5/3w=="], "zod": ["zod@4.2.1", "", {}, "sha512-0wZ1IRqGGhMP76gLqz8EyfBXKk0J2qo2+H3fi4mcUP/KtTocoX08nmIAHl1Z2kJIZbZee8KOpBCSNPRgauucjw=="], + "zod-to-json-schema": ["zod-to-json-schema@3.25.0", "", { "peerDependencies": { "zod": "^3.25 || ^4" } }, "sha512-HvWtU2UG41LALjajJrML6uQejQhNJx+JBO9IflpSja4R03iNWfKXrj6W2h7ljuLyc1nKS+9yDyL/9tD1U/yBnQ=="], + "@langchain/core/uuid": ["uuid@10.0.0", "", { "bin": { "uuid": "dist/bin/uuid" } }, "sha512-8XkAphELsDnEGrDxUOHB3RGvXz6TeuYSGEZBOjtTtPm2lwhGBjLgOzLHB63IUWfBpNucQjND6d3AOudO+H3RWQ=="], "@langchain/langgraph/uuid": ["uuid@10.0.0", "", { "bin": { "uuid": "dist/bin/uuid" } }, "sha512-8XkAphELsDnEGrDxUOHB3RGvXz6TeuYSGEZBOjtTtPm2lwhGBjLgOzLHB63IUWfBpNucQjND6d3AOudO+H3RWQ=="], @@ -916,36 +765,24 @@ "@langchain/langgraph-sdk/uuid": ["uuid@9.0.1", "", { "bin": { "uuid": "dist/bin/uuid" } }, "sha512-b+1eJOlsR9K8HJpow9Ok3fiWOWSIcIzXodvv0rQjVoOVNpWMpxf1wZNpt4y9h10odCNrqnYp1OBzRktckBe3sA=="], - "@langchain/ollama/uuid": ["uuid@10.0.0", "", { "bin": { "uuid": "dist/bin/uuid" } }, "sha512-8XkAphELsDnEGrDxUOHB3RGvXz6TeuYSGEZBOjtTtPm2lwhGBjLgOzLHB63IUWfBpNucQjND6d3AOudO+H3RWQ=="], - - "@sap-ai-sdk/langchain/uuid": ["uuid@13.0.0", "", { "bin": { "uuid": "dist-node/bin/uuid" } }, "sha512-XQegIaBTVUjSHliKqcnFqYypAd4S+WCYt5NIeRs6w/UAry7z8Y9j5ZwRRL4kzq9U3sD6v+85er9FvkEaBpji2w=="], + "@modelcontextprotocol/sdk/zod": ["zod@3.25.76", "", {}, "sha512-gzUt/qt81nXsFGKIFcC3YnfEAx5NkunCfnDlvuBSSFS02bcXu4Lmea0AFIUwbLWxWPx3d9p8S5QoaujKcNQxcQ=="], - "@sap-ai-sdk/orchestration/yaml": ["yaml@2.8.2", "", { "bin": { "yaml": "bin.mjs" } }, "sha512-mplynKqc1C2hTVYxd0PU2xQAc22TI1vShAYGksCCfxbn/dFwnHTNi1bvYsBTkhdUNtGIf5xNOg938rrSSYvS9A=="], + "@sveltejs/vite-plugin-svelte/debug": ["debug@4.4.1", "", { "dependencies": { "ms": "^2.1.3" } }, "sha512-KcKCqiftBJcZr++7ykoDIEwSa3XWowTfNPo92BYxjXiyYEVrUQh2aLyhxBCwww+heortUFxEJYcRzosstTEBYQ=="], - "@sap/xssec/debug": ["debug@4.4.3", "", { "dependencies": { "ms": "^2.1.3" } }, "sha512-RGwwWnwQvkVfavKVt22FGLw+xYSdzARwm0ru6DhTVA3umU5hZc28V3kO4stgYryrTlLpuvgI9GiijltAjNbcqA=="], + "@sveltejs/vite-plugin-svelte-inspector/debug": ["debug@4.4.1", "", { "dependencies": { "ms": "^2.1.3" } }, "sha512-KcKCqiftBJcZr++7ykoDIEwSa3XWowTfNPo92BYxjXiyYEVrUQh2aLyhxBCwww+heortUFxEJYcRzosstTEBYQ=="], "anymatch/picomatch": ["picomatch@2.3.1", "", {}, "sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA=="], "chalk/ansi-styles": ["ansi-styles@4.3.0", "", { "dependencies": { "color-convert": "^2.0.1" } }, "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg=="], - "cliui/string-width": ["string-width@4.2.3", "", { "dependencies": { "emoji-regex": "^8.0.0", "is-fullwidth-code-point": "^3.0.0", "strip-ansi": "^6.0.1" } }, "sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g=="], - - "cliui/strip-ansi": ["strip-ansi@6.0.1", "", { "dependencies": { "ansi-regex": "^5.0.1" } }, "sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A=="], - - "cliui/wrap-ansi": ["wrap-ansi@7.0.0", "", { "dependencies": { "ansi-styles": "^4.0.0", "string-width": "^4.1.0", "strip-ansi": "^6.0.0" } }, "sha512-YVGIj2kamLSTxw6NsZjoBxfSwsn0ycdesmc4p+Q21c5zPuZ1pl+NfxVdxPtdHvmNVOQ6XSYG4AUtyt/Fi7D16Q=="], - - "color/color-convert": ["color-convert@3.1.3", "", { "dependencies": { "color-name": "^2.0.0" } }, "sha512-fasDH2ont2GqF5HpyO4w0+BcewlhHEZOFn9c1ckZdHpJ56Qb7MHhH/IcJZbBGgvdtwdwNbLvxiBEdg336iA9Sg=="], - - "color-string/color-name": ["color-name@2.1.0", "", {}, "sha512-1bPaDNFm0axzE4MEAzKPuqKWeRaT43U/hyxKPBdqTfmPF+d6n7FSoTFxLVULUJOmiLp01KjhIPPH+HrXZJN4Rg=="], - "fast-glob/glob-parent": ["glob-parent@5.1.2", "", { "dependencies": { "is-glob": "^4.0.1" } }, "sha512-AOIgSQCepiJYwP3ARnGx+5VnTu2HBYdzbGP45eLw1vr3zB3vZLeyed1sC9hnbcOc9/SrMyM5RPQrkGz4aS9Zow=="], - "langchain/uuid": ["uuid@10.0.0", "", { "bin": { "uuid": "dist/bin/uuid" } }, "sha512-8XkAphELsDnEGrDxUOHB3RGvXz6TeuYSGEZBOjtTtPm2lwhGBjLgOzLHB63IUWfBpNucQjND6d3AOudO+H3RWQ=="], - "langsmith/uuid": ["uuid@10.0.0", "", { "bin": { "uuid": "dist/bin/uuid" } }, "sha512-8XkAphELsDnEGrDxUOHB3RGvXz6TeuYSGEZBOjtTtPm2lwhGBjLgOzLHB63IUWfBpNucQjND6d3AOudO+H3RWQ=="], "micromatch/picomatch": ["picomatch@2.3.1", "", {}, "sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA=="], + "router/is-promise": ["is-promise@4.0.0", "", {}, "sha512-hvpoI6korhJMnej285dSg6nu1+e6uxs7zG3BYAm5byqDsgJNWwxzM6z6iZiAgQR4TJ30JmBTOwqZUw3WlyH3AQ=="], + "string-width-cjs/emoji-regex": ["emoji-regex@8.0.0", "", {}, "sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A=="], "string-width-cjs/strip-ansi": ["strip-ansi@6.0.1", "", { "dependencies": { "ansi-regex": "^5.0.1" } }, "sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A=="], @@ -968,16 +805,6 @@ "wrap-ansi-cjs/strip-ansi": ["strip-ansi@6.0.1", "", { "dependencies": { "ansi-regex": "^5.0.1" } }, "sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A=="], - "yargs/string-width": ["string-width@4.2.3", "", { "dependencies": { "emoji-regex": "^8.0.0", "is-fullwidth-code-point": "^3.0.0", "strip-ansi": "^6.0.1" } }, "sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g=="], - - "cliui/string-width/emoji-regex": ["emoji-regex@8.0.0", "", {}, "sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A=="], - - "cliui/strip-ansi/ansi-regex": ["ansi-regex@5.0.1", "", {}, "sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ=="], - - "cliui/wrap-ansi/ansi-styles": ["ansi-styles@4.3.0", "", { "dependencies": { "color-convert": "^2.0.1" } }, "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg=="], - - "color/color-convert/color-name": ["color-name@2.1.0", "", {}, "sha512-1bPaDNFm0axzE4MEAzKPuqKWeRaT43U/hyxKPBdqTfmPF+d6n7FSoTFxLVULUJOmiLp01KjhIPPH+HrXZJN4Rg=="], - "string-width-cjs/strip-ansi/ansi-regex": ["ansi-regex@5.0.1", "", {}, "sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ=="], "svelte-i18n/esbuild/@esbuild/aix-ppc64": ["@esbuild/aix-ppc64@0.19.12", "", { "os": "aix", "cpu": "ppc64" }, "sha512-bmoCYyWdEL3wDQIVbcyzRyeKLgk2WtWLTWz1ZIAZF/EGbNOwSA6ew3PftJ1PqMiOOGu0OyFMzG53L0zqIpPeNA=="], @@ -1034,12 +861,6 @@ "wrap-ansi-cjs/strip-ansi/ansi-regex": ["ansi-regex@5.0.1", "", {}, "sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ=="], - "yargs/string-width/emoji-regex": ["emoji-regex@8.0.0", "", {}, "sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A=="], - - "yargs/string-width/strip-ansi": ["strip-ansi@6.0.1", "", { "dependencies": { "ansi-regex": "^5.0.1" } }, "sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A=="], - "tailwindcss/chokidar/readdirp/picomatch": ["picomatch@2.3.1", "", {}, "sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA=="], - - "yargs/string-width/strip-ansi/ansi-regex": ["ansi-regex@5.0.1", "", {}, "sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ=="], } } diff --git a/package.json b/package.json index a84e6c62..7deb65a2 100644 --- a/package.json +++ b/package.json @@ -4,6 +4,9 @@ "main": "main.js", "devDependencies": { "@biomejs/biome": "^1.9.4", + "@langchain/langgraph-checkpoint": "^1.0.0", + "@langchain/mcp-adapters": "^1.0.2", + "@langchain/tavily": "^1.0.1", "@sveltejs/vite-plugin-svelte": "^5.1.1", "@tsconfig/svelte": "^5.0.5", "autoprefixer": "^10.4.21", @@ -33,6 +36,7 @@ "dexie": "^4.2.1", "i18next": "^23.16.8", "svelte-i18n": "^4.0.1", - "uuid": "^11.1.0" + "uuid": "^11.1.0", + "zod": "^4.2.1" } } diff --git a/smart-second-brain b/smart-second-brain new file mode 120000 index 00000000..63c19ebd --- /dev/null +++ b/smart-second-brain @@ -0,0 +1 @@ +../papa-test-vault/papa-test-vault/.obsidian/plugins/smart-second-brain/ \ No newline at end of file diff --git a/src/agent/AgentManager.ts b/src/agent/AgentManager.ts index 78e48b26..652b544e 100644 --- a/src/agent/AgentManager.ts +++ b/src/agent/AgentManager.ts @@ -1,10 +1,18 @@ import { - Agent, - ProviderRegistry, - type ThreadSnapshot, - LangSmithTelemetry, - type Telemetry, + Agent, + ProviderRegistry, + type ThreadSnapshot, + LangSmithTelemetry, + type Telemetry, + type BuiltInProviderOptions, + ProviderAuthError, + ProviderEndpointError, + ProviderRegistryError, + type ThreadMessage, + type ChooseModelParams, + type ThreadHistory, } from "papa-ts"; +import { normalizePath } from "obsidian"; import { ObsidianChatManager } from "./ObsidianChatManager"; import { createSearchNotesTool } from "../tools/searchNotes"; import { createGetAllTagsTool } from "../tools/getAllTags"; @@ -14,443 +22,487 @@ import { createReadNoteTool } from "../tools/readNote"; import { createSystemPrompt } from "./prompts"; import { createObsidianFetch } from "../utils/obsidianFetch"; import { getData } from "../stores/dataStore.svelte"; +import type { RegisteredProvider } from "../types/providers"; import type SecondBrainPlugin from "../main"; +import type { ChatModel } from "../stores/chatStore.svelte"; +import { createThreadId } from "../utils/threadId"; + +export type ValidationResult = + | { success: true } + | { success: false; message: string }; declare const MultiServerMCPClient: any; +/** + * Maps the UI ChatModel type to papa-ts ChooseModelParams. + */ +function toChooseModelParams(model: ChatModel): ChooseModelParams { + return { + provider: model.provider, + chatModel: model.model, + options: model.modelConfig, + }; +} + export class AgentManager { - private plugin: SecondBrainPlugin; - private agent: Agent | null = null; - private chatManager: ObsidianChatManager; - - constructor(plugin: SecondBrainPlugin) { - this.plugin = plugin; - this.chatManager = new ObsidianChatManager(plugin); - } - - private async configureRegistry( - registry: ProviderRegistry, - provider: string, - apiKey: string, - ): Promise<{ providerName: string; modelOptions: Record }> { - let providerName: string = provider; - let modelOptions: Record = {}; - - if (apiKey || provider === "ollama") { - try { - if (provider === "openai" && apiKey) { - await registry.useOpenAI({ apiKey }); - modelOptions = { apiKey }; - providerName = "openai"; - } else if (provider === "anthropic" && apiKey) { - await registry.useAnthropic({ apiKey }); - modelOptions = { apiKey }; - providerName = "anthropic"; - } else if (provider === "ollama") { - const baseUrl = apiKey || "http://localhost:11434"; - await registry.useOllama({ baseUrl }); - modelOptions = { baseUrl }; - providerName = "ollama"; - } else if (provider === "sap-ai-core" && apiKey) { - await registry.useSapAICore({ apiKey }); - modelOptions = { apiKey }; - providerName = "sap-ai-core"; - } else if (provider === "custom" && apiKey) { - // Default to OpenAI structure for custom - await registry.useOpenAI({ apiKey }); - modelOptions = { apiKey }; - providerName = "openai"; - } - } catch (error) { - console.error("Error configuring provider:", error); - throw error; - } - } - return { providerName, modelOptions }; - } - - private configureTelemetry(): Telemetry | undefined { - const data = getData(); - if (data.enableLangSmith && data.langSmithApiKey) { - try { - const telemetry = new LangSmithTelemetry({ - projectName: data.langSmithProject || "obsidian-agent", - apiKey: data.langSmithApiKey, - endpoint: data.langSmithEndpoint || "https://api.smith.langchain.com", - flushOnComplete: true, - }); - console.log("Smart Second Brain: LangSmith telemetry enabled"); - return telemetry; - } catch (e) { - console.error( - "Smart Second Brain: Failed to initialize LangSmith telemetry", - e, - ); - } - } - return undefined; - } - - private async bindTools(agent: Agent) { - const searchNotesTool = createSearchNotesTool(this.plugin.app); - const getAllTagsTool = createGetAllTagsTool(this.plugin.app); - const executeDataviewTool = createExecuteDataviewTool(this.plugin.app); - const getPropertiesTool = createGetPropertiesTool(this.plugin.app); - const readNoteTool = createReadNoteTool(this.plugin.app); - - const tools: any[] = [ - searchNotesTool, - getAllTagsTool, - executeDataviewTool, - getPropertiesTool, - readNoteTool, - ]; - - // Load MCP tools if configured (use getData()) - const data = getData(); - if (data.mcpServers && Object.keys(data.mcpServers).length > 0) { - try { - console.log( - "Smart Second Brain: Initializing MCP client...", - data.mcpServers, - ); - - // HACK: Monkey patch the global fetch for the entire lifecycle - if (!(window as any)._originalFetch) { - (window as any)._originalFetch = window.fetch; - window.fetch = createObsidianFetch( - (window as any)._originalFetch, - ) as any; - } - - try { - const mcpClient = new MultiServerMCPClient(data.mcpServers); - const mcpTools = await mcpClient.getTools(); - console.log( - `Smart Second Brain: Loaded ${mcpTools.length} MCP tools`, - ); - tools.push(...mcpTools); - } catch (e) { - console.error("Failed to get MCP tools", e); - } - } catch (error) { - console.error("Smart Second Brain: Failed to load MCP tools", error); - } - } - - agent.bindTools(tools); - } - - private async ensureAgent(): Promise { - console.log(this.agent); - this.agent = null; - if (!this.agent) { - await this.initialize(); - } - - if (!this.agent) { - throw new Error("Agent initialization failed."); - } - return this.agent; - } - - async initialize(): Promise { - // Load chats - await this.chatManager.load(); - - // Cleanup existing agent if any - if (this.agent) { - this.agent = null; - } - - try { - const pluginData = getData(); - pluginData.getConfiguredProviders().forEach((provider) => { - registry.listProviders().forEach((providerName) => { - this.configureRegistry( - registry, - providerName, - pluginData.getProviderAuthParams(provider), - ); - }); - }); - } catch (e) { - console.warn( - "Smart Second Brain: Failed to derive default model from data store", - e, - ); - } - - console.log("Smart Second Brain: Initializing agent..."); - - // Create provider registry - const registry = new ProviderRegistry(); - - let providerName: string; - let modelOptions: Record; - - registry.registerProvider(); - - try { - const config = await this.configureRegistry( - registry, - "ollama", - "http://localhost:11434", - ); - providerName = config.providerName; - modelOptions = config.modelOptions; - } catch (error) { - // Error is already logged in configureRegistry - return; - } - - // Configure Telemetry (use getData()) - const telemetry = this.configureTelemetry(); - - // Create agent with checkpoint storage - // The chatManager acts as both checkpointer and thread store - const agent = new Agent({ - registry, - checkpointer: this.chatManager, - threadStore: this.chatManager.asThreadStore(), - telemetry, - }); - - // Check for available plugins to adjust prompt capabilities - // @ts-ignore - Dynamic access to plugins - const hasChartsPlugin = - this.plugin.app.plugins?.enabledPlugins?.has("obsidian-charts"); - - // Set prompt - agent.setPrompt(createSystemPrompt(hasChartsPlugin)); - - // Bind tools - await this.bindTools(agent); - - // If we have configuration, try to choose the model - if ((apiKey || provider === "ollama") && modelName) { - try { - console.log("Smart Second Brain: Choosing model...", { - provider: providerName, - chatModel: modelName, - }); - await agent.chooseModel({ - provider: providerName, - chatModel: modelName, - options: modelOptions, - }); - console.log("Smart Second Brain: Model chosen successfully"); - } catch (chooseModelError) { - console.error( - "Smart Second Brain: Error choosing model:", - chooseModelError, - ); - } - } else { - console.warn( - "Smart Second Brain: API key or model name not configured. Agent initialized for history reading only.", - ); - } - - this.agent = agent; - } - - async runQuery( - query: string, - threadId: string = "default-thread", - ): Promise { - const agent = await this.ensureAgent(); - - try { - const result = await agent.run({ - query, - threadId, - }); - - if (typeof result.response === "string") { - return result.response; - } else if (result.response !== undefined && result.response !== null) { - return String(result.response); - } else { - return "No response received from agent."; - } - } catch (error) { - console.error("Smart Second Brain: Error running query", error); - throw error; - } - } - - async *streamQuery( - query: string, - threadId: string = "default-thread", - ): AsyncGenerator< - { - type: "token" | "result"; - token?: string; - result?: any; - messages?: any[]; - }, - void, - unknown - > { - const agent = await this.ensureAgent(); - await this.agent?.chooseModel({ - provider: "Ollama", - chatModel: "ministral-3:3b", - }); - console.log(agent); - - try { - for await (const chunk of agent.streamTokens({ - query, - threadId, - })) { - switch (chunk.type) { - case "token": - yield { - type: "token", - token: chunk.token, - messages: (chunk as any).messages, - }; - break; - case "result": - yield { type: "result", result: chunk.result }; - break; - default: - break; - } - } - } catch (error) { - console.error("Smart Second Brain: Error streaming query", error); - throw error; - } - } - - async getAvailableModels( - provider: string, - apiKey: string, - ): Promise { - try { - const registry = new ProviderRegistry(); - const { providerName } = await this.configureRegistry( - registry, - provider, - apiKey, - ); - - if (!providerName) return []; - - return registry.listChatModels(providerName); - } catch (error) { - console.error( - "Smart Second Brain: Error fetching available models", - error, - ); - return []; - } - } - - async getThreadMessages(threadId: string): Promise { - try { - // Try to use agent if available to get history from checkpoint (more robust) - if (this.agent) { - try { - const history = await this.agent.getThreadHistory(threadId); - if (history && history.messages) { - return history.messages; - } - } catch (e) { - console.warn("Failed to get history from agent", e); - } - } - return []; - } catch (error) { - console.error( - "Smart Second Brain: Error fetching thread messages", - error, - ); - return []; - } - } - - async getAllThreads(): Promise { - await this.chatManager.load(); - return this.chatManager.listThreads(); - } - - async deleteThread(threadId: string): Promise { - await this.chatManager.delete(threadId); - } - - async generateThreadTitle(threadId: string): Promise { - const agent = await this.ensureAgent().catch((e) => { - console.warn("Agent not initialized, cannot generate title"); - return null; - }); - - if (!agent) return; - - try { - await agent.generateTitle(threadId); - console.log(`Generated title for thread ${threadId}`); - - // Wait a bit for the title to be persisted - await new Promise((resolve) => setTimeout(resolve, 200)); - - // Try multiple ways to get the title: - // 1. Read from thread store (may have it in cache) - let snapshot = await this.chatManager.read(threadId, true); - console.log(`Read snapshot for thread ${threadId}:`, snapshot); - - // 2. If not found, try reading directly from in-memory storage - if (!snapshot?.title) { - const threadData = await this.chatManager.ensureThreadLoaded(threadId); - if (threadData?.title) { - console.log(`Title found in threadData: "${threadData.title}"`); - snapshot = { - threadId: threadData.threadId, - title: threadData.title, - metadata: threadData.metadata, - createdAt: threadData.createdAt, - updatedAt: threadData.updatedAt, - }; - } - } - - if (snapshot?.title) { - console.log(`Title found: "${snapshot.title}", renaming file...`); - await this.chatManager.renameChatFile(threadId, snapshot.title); - } else { - console.warn( - `No title found for thread ${threadId} after generation. Waiting longer and retrying...`, - ); - // Wait longer and try again - await new Promise((resolve) => setTimeout(resolve, 1000)); - snapshot = await this.chatManager.read(threadId, true); - if (snapshot?.title) { - console.log( - `Title found on retry: "${snapshot.title}", renaming file...`, - ); - await this.chatManager.renameChatFile(threadId, snapshot.title); - } else { - console.error( - `Title still not found for thread ${threadId} after retry`, - ); - } - } - } catch (error) { - console.error(`Error generating title for thread ${threadId}:`, error); - } - } - - cleanup(): void { - // Restore original fetch if it was patched - if ((window as any)._originalFetch) { - window.fetch = (window as any)._originalFetch; - delete (window as any)._originalFetch; - } - - // Cleanup if needed - this.agent = null; - } + private plugin: SecondBrainPlugin; + private agent: Agent | null = null; + private chatManager: ObsidianChatManager; + private registry: ProviderRegistry; + + constructor(plugin: SecondBrainPlugin) { + this.plugin = plugin; + this.chatManager = new ObsidianChatManager(plugin); + this.registry = new ProviderRegistry(); + } + + /** + * Configures a specific provider on the given registry. + */ + private async configureProviderOnRegistry( + registry: ProviderRegistry, + provider: RegisteredProvider, + options: BuiltInProviderOptions, + ): Promise { + switch (provider) { + case "OpenAI": + await registry.useOpenAI(options); + break; + case "CustomOpenAI": + await registry.useOpenAI(options); + break; + case "Anthropic": + await registry.useAnthropic(options); + break; + case "Ollama": + await registry.useOllama(options); + break; + default: + throw new Error(`Unsupported provider: ${provider}`); + } + } + + /** + * Configures a provider on the main registry. + */ + private async configureRegistry( + provider: RegisteredProvider, + options: BuiltInProviderOptions, + ): Promise { + await this.configureProviderOnRegistry(this.registry, provider, options); + } + + /** + * Tests and configures a provider on the actual registry. + * Returns a ValidationResult indicating success or failure with a message. + */ + async testProviderConfig( + provider: RegisteredProvider, + options: BuiltInProviderOptions, + ): Promise { + try { + await this.configureProviderOnRegistry(this.registry, provider, options); + return { success: true }; + } catch (error) { + if (error instanceof ProviderAuthError) { + return { success: false, message: "Invalid API key" }; + } + if (error instanceof ProviderEndpointError) { + return { + success: false, + message: "Invalid base URL or endpoint unreachable", + }; + } + if (error instanceof ProviderRegistryError) { + return { success: false, message: error.message }; + } + return { + success: false, + message: "Provider configuration failed", + }; + } + } + + private configureTelemetry(): Telemetry | undefined { + const data = getData(); + if (data.enableLangSmith && data.langSmithApiKey) { + try { + const telemetry = new LangSmithTelemetry({ + projectName: data.langSmithProject || "obsidian-agent", + apiKey: data.langSmithApiKey, + endpoint: data.langSmithEndpoint || "https://api.smith.langchain.com", + flushOnComplete: true, + }); + console.log("Smart Second Brain: LangSmith telemetry enabled"); + return telemetry; + } catch (e) { + console.error( + "Smart Second Brain: Failed to initialize LangSmith telemetry", + e, + ); + } + } + return undefined; + } + + private async bindTools(agent: Agent) { + const searchNotesTool = createSearchNotesTool(this.plugin.app); + const getAllTagsTool = createGetAllTagsTool(this.plugin.app); + const executeDataviewTool = createExecuteDataviewTool(this.plugin.app); + const getPropertiesTool = createGetPropertiesTool(this.plugin.app); + const readNoteTool = createReadNoteTool(this.plugin.app); + + const tools: any[] = [ + searchNotesTool, + getAllTagsTool, + executeDataviewTool, + getPropertiesTool, + readNoteTool, + ]; + + // Load MCP tools if configured (use getData()) + const data = getData(); + if (data.mcpServers && Object.keys(data.mcpServers).length > 0) { + try { + console.log( + "Smart Second Brain: Initializing MCP client...", + data.mcpServers, + ); + + // HACK: Monkey patch the global fetch for the entire lifecycle + if (!(window as any)._originalFetch) { + (window as any)._originalFetch = window.fetch; + window.fetch = createObsidianFetch( + (window as any)._originalFetch, + ) as any; + } + + try { + const mcpClient = new MultiServerMCPClient(data.mcpServers); + const mcpTools = await mcpClient.getTools(); + console.log( + `Smart Second Brain: Loaded ${mcpTools.length} MCP tools`, + ); + tools.push(...mcpTools); + } catch (e) { + console.error("Failed to get MCP tools", e); + } + } catch (error) { + console.error("Smart Second Brain: Failed to load MCP tools", error); + } + } + + agent.bindTools(tools); + } + + private async ensureAgent(): Promise { + if (!this.agent) { + await this.initialize(); + } + + if (!this.agent) { + throw new Error("Agent initialization failed."); + } + return this.agent; + } + + async initialize(): Promise { + // Load chats + await this.chatManager.load(); + + // Cleanup existing agent if any + this.agent = null; + + // Reset registry for fresh configuration + this.registry = new ProviderRegistry(); + + const pluginData = getData(); + + // Configure all providers - use for...of to properly await each + const configuredProviders = pluginData.getConfiguredProviders(); + for (const provider of configuredProviders) { + const options = pluginData.getProviderAuthParams(provider); + await this.configureRegistry(provider, options); + } + + console.log(this.registry); + + // Configure Telemetry (use getData()) + const telemetry = this.configureTelemetry(); + + // Create agent with checkpoint storage + // The chatManager acts as both checkpointer and thread store + this.agent = new Agent({ + registry: this.registry, + checkpointer: this.chatManager, + threadStore: this.chatManager.asThreadStore(), + telemetry, + }); + + // Check for available plugins to adjust prompt capabilities + // @ts-ignore - Dynamic access to plugins + const hasChartsPlugin = + this.plugin.app.plugins?.enabledPlugins?.has("obsidian-charts"); + + // Set prompt + this.agent.setPrompt(createSystemPrompt(hasChartsPlugin)); + + const defaultModel = pluginData.getDefaultChatModel(); + if (defaultModel) { + await this.agent.chooseModel(toChooseModelParams(defaultModel)); + } + + // Bind tools + await this.bindTools(this.agent); + } + + async *streamQuery( + query: string, + threadId: string = "default-thread", + signal?: AbortSignal, + ): AsyncGenerator< + | { type: "token"; token: string } + | { + type: "tool_start"; + toolCallId: string; + toolName: string; + input: unknown; + } + | { + type: "tool_end"; + toolCallId: string; + toolName: string; + output: unknown; + } + | { type: "result"; result: any }, + void, + unknown + > { + const agent = await this.ensureAgent(); + + const defaultModel = getData().getDefaultChatModel(); + if (defaultModel) { + await agent.chooseModel(toChooseModelParams(defaultModel)); + } else { + throw new Error("No chat model configured"); + } + + try { + for await (const chunk of agent.streamTokens({ + query, + threadId, + signal, + })) { + // Check if aborted before yielding + if (signal?.aborted) { + break; + } + switch (chunk.type) { + case "token": + yield { type: "token", token: chunk.token }; + break; + case "tool_start": + yield { + type: "tool_start", + toolCallId: chunk.toolCallId, + toolName: chunk.toolName, + input: chunk.input, + }; + break; + case "tool_end": + yield { + type: "tool_end", + toolCallId: chunk.toolCallId, + toolName: chunk.toolName, + output: chunk.output, + }; + break; + case "result": + yield { type: "result", result: chunk.result }; + break; + default: + break; + } + } + } catch (error) { + // Don't log abort errors as they're expected during cancellation + if (error instanceof Error && error.name === "AbortError") { + return; + } + console.error("Smart Second Brain: Error streaming query", error); + throw error; + } finally { + // Cleanup logging - stream completed or aborted + if (signal?.aborted) { + console.log("Smart Second Brain: Stream aborted by user"); + } + } + } + + async getAvailableModels( + providerName: RegisteredProvider, + ): Promise { + try { + if (!providerName) return []; + + return this.registry.listChatModels(providerName); + } catch (error) { + console.error( + "Smart Second Brain: Error fetching available models", + error, + ); + return []; + } + } + + async getThreadHistory(threadId: string): Promise { + try { + // Try to use agent if available to get history from checkpoint (more robust) + if (this.agent) { + try { + const history = await this.agent.getThreadHistory(threadId); + if (history) { + return history; + } + } catch (e) { + console.warn("Failed to get history from agent", e); + } + } + return null; + } catch (error) { + console.error("Smart Second Brain: Error fetching thread history", error); + return null; + } + } + + async getAllThreads(): Promise { + await this.chatManager.load(); + return this.chatManager.listThreads(); + } + + async deleteThread(threadId: string): Promise { + await this.chatManager.delete(threadId); + } + + async generateThreadTitle(threadId: string): Promise { + const agent = await this.ensureAgent().catch((e) => { + console.warn("Agent not initialized, cannot generate title"); + return null; + }); + + if (!agent) return; + + try { + await agent.generateTitle(threadId); + console.log(`Generated title for thread ${threadId}`); + + // Wait a bit for the title to be persisted + await new Promise((resolve) => setTimeout(resolve, 200)); + + // Try multiple ways to get the title: + // 1. Read from thread store (may have it in cache) + let snapshot = await this.chatManager.read(threadId, true); + console.log(`Read snapshot for thread ${threadId}:`, snapshot); + + // 2. If not found, try reading directly from in-memory storage + if (!snapshot?.title) { + const threadData = await this.chatManager.ensureThreadLoaded(threadId); + if (threadData?.title) { + console.log(`Title found in threadData: "${threadData.title}"`); + snapshot = { + threadId: threadData.threadId, + title: threadData.title, + metadata: threadData.metadata, + createdAt: threadData.createdAt, + updatedAt: threadData.updatedAt, + }; + } + } + + if (snapshot?.title) { + console.log(`Title found: "${snapshot.title}", renaming file...`); + await this.chatManager.renameChatFile(threadId, snapshot.title); + } else { + console.warn( + `No title found for thread ${threadId} after generation. Waiting longer and retrying...`, + ); + // Wait longer and try again + await new Promise((resolve) => setTimeout(resolve, 1000)); + snapshot = await this.chatManager.read(threadId, true); + if (snapshot?.title) { + console.log( + `Title found on retry: "${snapshot.title}", renaming file...`, + ); + await this.chatManager.renameChatFile(threadId, snapshot.title); + } else { + console.error( + `Title still not found for thread ${threadId} after retry`, + ); + } + } + } catch (error) { + console.error(`Error generating title for thread ${threadId}:`, error); + } + } + + cleanup(): void { + // Restore original fetch if it was patched + if ((window as any)._originalFetch) { + window.fetch = (window as any)._originalFetch; + delete (window as any)._originalFetch; + } + + // Cleanup if needed + this.agent = null; + } + + async createNewChat(): Promise { + const threadId = createThreadId(); + const now = Date.now(); + + const folder = getData().targetFolder; + + // Ensure folder exists + if (!(await this.plugin.app.vault.adapter.exists(folder))) { + await this.plugin.app.vault.createFolder(folder); + } + + const path = normalizePath(`${folder}/${threadId}.chat`); + + // Initialize with valid thread data structure + const initialData = { + threadId, + createdAt: now, + updatedAt: now, + checkpoints: {}, + writes: {}, + }; + + // Create file directly and open it + const file = await this.plugin.app.vault.create( + path, + JSON.stringify(initialData, null, 2), + ); + await this.plugin.app.workspace.getLeaf(false).openFile(file); + } + + async openLatestChat(): Promise { + const threads = await this.chatManager.listThreads(); + + if (threads.length === 0) { + await this.createNewChat(); + return; + } + + const latestThread = threads[0]; + const folder = getData().targetFolder; + const path = normalizePath(`${folder}/${latestThread.threadId}.chat`); + const file = this.plugin.app.vault.getAbstractFileByPath(path); + + if (file) { + await this.plugin.app.workspace.getLeaf(false).openFile(file as any); + } else { + await this.createNewChat(); + } + } } diff --git a/src/agent/ObsidianChatManager.ts b/src/agent/ObsidianChatManager.ts index 8ebf4c93..dc7c3def 100644 --- a/src/agent/ObsidianChatManager.ts +++ b/src/agent/ObsidianChatManager.ts @@ -7,7 +7,13 @@ import { type CheckpointListOptions, } from "@langchain/langgraph-checkpoint"; import type { RunnableConfig } from "@langchain/core/runnables"; -import { Plugin, debounce, TFile, normalizePath, type DataAdapter } from "obsidian"; +import { + Plugin, + debounce, + TFile, + normalizePath, + type DataAdapter, +} from "obsidian"; import type SecondBrainPlugin from "../main"; import { type ThreadStore, type ThreadSnapshot } from "papa-ts"; import { getData } from "../stores/dataStore.svelte"; @@ -55,14 +61,8 @@ export class ObsidianChatManager extends BaseCheckpointSaver { // --- File System Helpers --- private getChatFolder(): string { - // Prefer the new data store (targetFolder). Fallback to legacy v2 setting. - try { - const data = getData(); - return data.targetFolder || "Chats"; - } catch { - // @ts-ignore legacy v2 settings - return (this.plugin.settings?.chatsFolder as string) || "Chats"; - } + const data = getData(); + return data.targetFolder; } private getIndexPath(): string { @@ -149,7 +149,9 @@ export class ObsidianChatManager extends BaseCheckpointSaver { this.threadIndex.clear(); snapshots.forEach((s) => this.threadIndex.set(s.threadId, s)); this.indexLoaded = true; - console.log(`ObsidianChatManager: Loaded index with ${this.threadIndex.size} threads`); + console.log( + `ObsidianChatManager: Loaded index with ${this.threadIndex.size} threads`, + ); } else { console.log("ObsidianChatManager: Index missing, rebuilding..."); await this.rebuildIndex(); @@ -246,6 +248,11 @@ export class ObsidianChatManager extends BaseCheckpointSaver { }; } + /** + * Creates a new thread and persists it to disk. + * Returns + **/ + private async saveThread(threadId: string) { const data = this.storage.get(threadId); if (!data) return; @@ -280,7 +287,10 @@ export class ObsidianChatManager extends BaseCheckpointSaver { // --- ThreadStore Implementation --- - async read(threadId: string, forceReload: boolean = false): Promise { + async read( + threadId: string, + forceReload: boolean = false, + ): Promise { if (!forceReload && this.threadIndex.has(threadId)) { return this.threadIndex.get(threadId); } @@ -325,7 +335,9 @@ export class ObsidianChatManager extends BaseCheckpointSaver { async listThreads(): Promise { await this.load(); - return Array.from(this.threadIndex.values()).sort((a, b) => b.updatedAt - a.updatedAt); + return Array.from(this.threadIndex.values()).sort( + (a, b) => b.updatedAt - a.updatedAt, + ); } asThreadStore(): ThreadStore { @@ -361,12 +373,18 @@ export class ObsidianChatManager extends BaseCheckpointSaver { const entry = threadData.checkpoints[checkpointId]; if (!entry) return undefined; + // For specific checkpoint, also include any error writes from child checkpoints + const pendingWrites = this.collectWritesWithErrors( + threadData, + checkpointId, + ); + return { config, checkpoint: entry.checkpoint, metadata: entry.metadata, parentConfig: entry.parentConfig, - pendingWrites: (threadData.writes[checkpointId] || []) as any, + pendingWrites: pendingWrites as any, }; } @@ -379,16 +397,61 @@ export class ObsidianChatManager extends BaseCheckpointSaver { const latestId = keys[0]; const entry = threadData.checkpoints[latestId]; + // Collect writes from the latest checkpoint AND any error writes from subsequent checkpoints + const pendingWrites = this.collectWritesWithErrors(threadData, latestId); + return { - config: { ...config, configurable: { ...config.configurable, checkpoint_id: latestId } }, + config: { + ...config, + configurable: { ...config.configurable, checkpoint_id: latestId }, + }, checkpoint: entry.checkpoint, metadata: entry.metadata, parentConfig: entry.parentConfig, - pendingWrites: (threadData.writes[latestId] || []) as any, + pendingWrites: pendingWrites as any, }; } - async *list(config: RunnableConfig, options?: CheckpointListOptions): AsyncGenerator { + /** + * Collects pending writes for a checkpoint, including error writes from child checkpoints. + * This is needed because errors are written to a child checkpoint that may not exist in the checkpoints map. + */ + private collectWritesWithErrors( + threadData: ThreadData, + checkpointId: string, + ): PendingWrite[] { + const writes: PendingWrite[] = []; + + // Add writes from the specific checkpoint + if (threadData.writes[checkpointId]) { + writes.push(...threadData.writes[checkpointId]); + } + + // Collect ALL error writes from the entire thread + // This is needed because each errored user message has its own error in a subsequent checkpoint + const allWriteKeys = Object.keys(threadData.writes).sort(); + for (const writeKey of allWriteKeys) { + // Skip the checkpoint we already added + if (writeKey === checkpointId) continue; + + const checkpointWrites = threadData.writes[writeKey]; + for (const write of checkpointWrites) { + if ( + Array.isArray(write) && + (write[0] === "__error__" || write[1] === "__error__") + ) { + writes.push(write); + } + } + } + + return writes; + } + + async *list( + config: RunnableConfig, + options?: CheckpointListOptions, + ): AsyncGenerator { const threadId = config.configurable?.thread_id; if (!threadId) return; @@ -408,7 +471,10 @@ export class ObsidianChatManager extends BaseCheckpointSaver { } yield { - config: { ...config, configurable: { ...config.configurable, checkpoint_id: key } }, + config: { + ...config, + configurable: { ...config.configurable, checkpoint_id: key }, + }, checkpoint: entry.checkpoint, metadata: entry.metadata, parentConfig: entry.parentConfig, @@ -473,7 +539,11 @@ export class ObsidianChatManager extends BaseCheckpointSaver { }; } - async putWrites(config: RunnableConfig, writes: PendingWrite[], taskId: string): Promise { + async putWrites( + config: RunnableConfig, + writes: PendingWrite[], + taskId: string, + ): Promise { const threadId = config.configurable?.thread_id; const checkpointId = config.configurable?.checkpoint_id; @@ -540,7 +610,9 @@ export class ObsidianChatManager extends BaseCheckpointSaver { } const sanitizedTitle = this.sanitizeFileName(title); - const dateTimePart = threadId.startsWith("Chat ") ? threadId.substring(5) : threadId; + const dateTimePart = threadId.startsWith("Chat ") + ? threadId.substring(5) + : threadId; const newFileName = `${sanitizedTitle} - ${dateTimePart}.chat`; if (file.name === newFileName) return; diff --git a/src/agent/prompts.ts b/src/agent/prompts.ts index cfb05ae9..62293f04 100644 --- a/src/agent/prompts.ts +++ b/src/agent/prompts.ts @@ -1,6 +1,13 @@ export const createSystemPrompt = (hasChartsPlugin: boolean) => `# Role You are a privacy-aware assistant integrated into Obsidian. You help users search and understand their notes. +# Important Formatting Rules +- **Wiki Links**: When mentioning note names, ALWAYS use raw Obsidian wiki link syntax: [[Note Name]] + - CORRECT: Check out [[My Daily Notes]] for more info + - WRONG: Check out \`[[My Daily Notes]]\` for more info + - NEVER wrap wiki links in backticks - they must be raw so Obsidian can render them as clickable links +- Only use backticks (\`) for actual code, commands, or technical terms - NOT for note references + # Tools & Capabilities - **search_notes**: Finds relevant information from the user's notes. Note that this tool ONLY returns file paths and metadata, not content. - **read_note**: Reads the full content of a specific note. Use only after identifying it as relevant. @@ -35,7 +42,9 @@ QUERY \`\`\` The chat interface will render this automatically. -${hasChartsPlugin ? `## 3. Displaying Charts +${ + hasChartsPlugin + ? `## 3. Displaying Charts You can create charts using \`dataviewjs\`. The user has the \`obsidian-charts\` plugin installed, so you can output a \`dataviewjs\` code block that uses \`window.renderChart\`. **Important**: \`window.renderChart\` takes exactly two arguments: the chart data object and the container element. The chart data object must follow the standard Chart.js format (type, data, options). Use Obsidian CSS variables (e.g., \`var(--interactive-accent)\`) for chart colors to match the theme. @@ -60,7 +69,9 @@ const chartData = { } window.renderChart(chartData, this.container); \`\`\` -The chat interface will render this chart automatically.` : ""} +The chat interface will render this chart automatically.` + : "" +} ## ${hasChartsPlugin ? "4" : "3"}. Math/LaTeX Supports MathJax rendering. diff --git a/src/components/Chat/Input.svelte b/src/components/Chat/Input.svelte index 4d8cd2de..662f5b7c 100755 --- a/src/components/Chat/Input.svelte +++ b/src/components/Chat/Input.svelte @@ -1,206 +1,199 @@ -
+
onFocusChange?.(true)} + onfocusout={() => onFocusChange?.(false)} +> + +
{#each files as file} @@ -235,16 +228,15 @@ {/each}
-
-
- - onFileAttachment(event)} - /> -
+ +
AI can make mistakes. Please check important information. -
diff --git a/src/components/Chat/MessageContainer.svelte b/src/components/Chat/MessageContainer.svelte index d5725e98..06c89271 100755 --- a/src/components/Chat/MessageContainer.svelte +++ b/src/components/Chat/MessageContainer.svelte @@ -6,26 +6,63 @@ AssistantState, type AssistantMessage, type ChatModel, - type CurrentSession, type Messenger, } from "../../stores/chatStore.svelte"; import Dots from "../../utils/Dots.svelte"; + import ToolCallsSection from "./ToolCallsSection.svelte"; import { Notice } from "obsidian"; import type { UUIDv7 } from "../../utils/uuid7Validator"; + import Logo from "../Logos/Logo.svelte"; + import { tick } from "svelte"; interface Props { messenger: Messenger; - currentSession: CurrentSession; + isInputFocused?: boolean; } - const { messenger, currentSession }: Props = $props(); + const { messenger, isInputFocused = false }: Props = $props(); const messages = $derived.by(() => { - const session = currentSession.session; - const getMessagesFunction = session?.getMessages(); - return getMessagesFunction; + return messenger.session?.messages; }); + let scrollContainer: HTMLDivElement | undefined = $state(); + const messageRefs = new Map(); + + export async function scrollToLatestMessage() { + await tick(); + if (messages && messages.length > 0 && scrollContainer) { + const latestPair = messages[messages.length - 1]; + const messageElement = messageRefs.get(latestPair.id + "-user"); + + if (messageElement && scrollContainer) { + const containerTop = + scrollContainer.getBoundingClientRect().top; + const messageTop = messageElement.getBoundingClientRect().top; + const currentScroll = scrollContainer.scrollTop; + + // Calculate scroll position to place message at top of container + const targetScroll = + currentScroll + (messageTop - containerTop); + + scrollContainer.scrollTo({ + top: targetScroll, + behavior: "smooth", + }); + } + } + } + + // Svelte action to register message refs + function registerMessageRef(node: HTMLDivElement, id: string) { + messageRefs.set(id, node); + return { + destroy() { + messageRefs.delete(id); + }, + }; + } + const markdownRenderer = (node: HTMLElement, content: string) => { const plugin = getPlugin(); const renderer = createMarkdownRenderer({ @@ -62,195 +99,216 @@ } async function redoMessage(messageId: UUIDv7, model: ChatModel) { - currentSession.session?.resendMessage(messageId, model); + console.log("todo resend"); } async function branchOff(messageId: UUIDv7) { - if (currentSession.session) { - const id = await messenger.branchOffFromMessage( - currentSession.session.chatId, - messageId, + console.log("todo branch off"); + } + + // Track which message pairs have their tools open + let toolsOpenState: Record = $state({}); + + function getToolsOpen( + messageId: string, + assistantMessage: AssistantMessage, + ): boolean { + // Default: open if no content yet, closed if content exists + if (toolsOpenState[messageId] === undefined) { + return ( + !assistantMessage.content || + assistantMessage.content.length === 0 ); - console.log(id); } + return toolsOpenState[messageId]; } - function formatToolInput( - input: Record | null | undefined, - ): { key: string; value: string }[] { - if (!input) return []; - return Object.entries(input).map(([key, value]) => ({ - key, - value: - typeof value === "string" - ? value - : value === null || value === undefined - ? "" - : JSON.stringify(value), - })); + function setToolsOpen(messageId: string, open: boolean) { + toolsOpenState[messageId] = open; } -
- {#each messages!! as messagePair} -
-
- -
- - - +
+ +
+ {#if !messages || messages.length === 0} + +
- redoMessage(messagePair.id, messagePair.model)} - >
- - - - + class="logo-container h-[80px] w-[80px] items-center justify-center transition-transform duration-150 ease-out" + class:input-focused={isInputFocused} + > + +
+

Start a new conversation

+

+ Ask me anything about your notes. +

+
+ {:else} + {#each messages as messagePair, index}
console.log("split")} - >
+ use:registerMessageRef={messagePair.id + "-user"} + class="group mr-2 flex flex-col items-end gap-2 mb-2" + > +
- - - -
console.log("edit")} - >
+
+ + +
console.log("redo Message")} + >
- - - -
- copyToClipboard(messagePair.userMessage.content)} - >
-
-
+ + +
console.log("split")} + >
-
- {#if !messagePair.assistantMessage.content} - - {:else} -
- {/if} + + +
console.log("edit")} + >
- {#if messagePair.assistantMessage.toolCalls?.length} -
-
- Tools -
- {#each messagePair.assistantMessage.toolCalls as toolCall (toolCall.id)} + +
-
- {toolCall.name} - - {toolCall.status} - - {#if toolCall.id} - - {toolCall.id} - - {/if} -
+ use:icon={"copy"} + class="trash-icon hover:text-[--text-accent] items-center justify-center" + onclick={async () => + copyToClipboard( + messagePair.userMessage.content, + )} + >
+
+
+
+
+ + {#if messagePair.assistantMessage.toolCalls?.length} + + setToolsOpen(messagePair.id, open)} + /> + {/if} - {#if formatToolInput(toolCall.input).length > 0} -
-
Input
- {#each formatToolInput(toolCall.input) as item (item.key)} -
- - {item.key} - - {item.value} -
- {/each} -
+ + {#if messagePair.assistantMessage.state === AssistantState.streaming && !messagePair.assistantMessage.content} + + {:else if messagePair.assistantMessage.content || messagePair.assistantMessage.state === AssistantState.cancelled || messagePair.assistantMessage.state === AssistantState.error} +
+ {:else if messagePair.assistantMessage.state === AssistantState.idle || messagePair.assistantMessage.state === AssistantState.streaming} + + {#if !messagePair.assistantMessage.toolCalls?.length} + {/if} + {/if} - {#if toolCall.output !== undefined} -
-
Output
-
-{JSON.stringify(toolCall.output, null, 2)}
-                                    
+ {#if !(messagePair.assistantMessage.state === AssistantState.streaming)} +
+ + +
+ copyToClipboard( + messagePair.assistantMessage + .content, + )} + >
+ + +
branchOff(messagePair.id)} + > + >
- {/if} -
- {/each} -
- {/if} - - {#if !(messagePair.assistantMessage.state === AssistantState.streaming)} -
- - - -
- copyToClipboard( - messagePair.assistantMessage.content, - )} - >
- - - -
branchOff(messagePair.id)} - > - > + + +
+ console.log("redo Message")} + >
+
+ {/if}
- - - -
- redoMessage(messagePair.id, messagePair.model)} - >
- {/if} -
- {/each} + {/each} + {/if} +
+ + diff --git a/src/components/Chat/QuickSettingsDrawer.svelte b/src/components/Chat/QuickSettingsDrawer.svelte index aeb82d5b..8c657e1f 100755 --- a/src/components/Chat/QuickSettingsDrawer.svelte +++ b/src/components/Chat/QuickSettingsDrawer.svelte @@ -98,21 +98,21 @@ function formatTime(secondsInput: number) {
($papaState = 'indexing-pause')} - class="h-8 py-2 pl-3 pr-2 transition duration-300 ease-in-out hover:text-[var(--text-accent-hover)]" + class="h-8 py-2 pl-3 pr-2 transition duration-300 ease-in-out hover:text-text-accent-hover" use:icon={'pause'} >
{:else if $papaState === 'indexing-pause'}
$plugin.s2b.init()} - class="h-8 py-2 pl-3 pr-2 transition duration-300 ease-in-out hover:text-[var(--text-accent-hover)]" + class="h-8 py-2 pl-3 pr-2 transition duration-300 ease-in-out hover:text-text-accent-hover" use:icon={'play'} >
{/if}
$plugin.s2b.cancelIndexing()} - class="h-8 py-2 pl-2 pr-3 transition duration-300 ease-in-out hover:text-[var(--text-accent-hover)]" + class="h-8 py-2 pl-2 pr-3 transition duration-300 ease-in-out hover:text-text-accent-hover" use:icon={'stop-circle'} >
diff --git a/src/components/Chat/ToolCallsSection.svelte b/src/components/Chat/ToolCallsSection.svelte new file mode 100644 index 00000000..2f77f0dd --- /dev/null +++ b/src/components/Chat/ToolCallsSection.svelte @@ -0,0 +1,226 @@ + + +
+
onToggle((e.target as HTMLDetailsElement).open)} + class="w-full" + > + + + + {toolStatus === "running" ? "⏳" : "🛠️"} + + + {summaryText} + + +
+ {#each toolCalls as toolCall (toolCall.id)} +
+
+ + + {#if toolCall.status === "running"} + ⏳ + {:else if toolCall.status === "completed"} + ✅ + {:else} + ❌ + {/if} + + + {formatToolName(toolCall.name)} + + + +
+
+ Input: + {#if formatToolInput(toolCall.input).length > 0} +
+ {#each formatToolInput(toolCall.input) as { key, value } (key)} +
+ {key}: +
+
+ {/each} +
+ {:else} + (empty) + {/if} +
+ {#if toolCall.output !== undefined} +
+ Output: +
+
+ {/if} +
+
+
+ {/each} +
+
+
diff --git a/src/components/Chat/Toolbar.svelte b/src/components/Chat/Toolbar.svelte deleted file mode 100644 index 96166be5..00000000 --- a/src/components/Chat/Toolbar.svelte +++ /dev/null @@ -1,46 +0,0 @@ - - -
- updateChatTitle()} - type="text" - spellcheck="false" - /> - {#if currentSession.session} -
diff --git a/src/components/Settings/AuthConfigFields.svelte b/src/components/Settings/AuthConfigFields.svelte new file mode 100644 index 00000000..f40dcf9c --- /dev/null +++ b/src/components/Settings/AuthConfigFields.svelte @@ -0,0 +1,50 @@ + + +{#if authParams} + {#each Object.entries(fieldMeta).filter( ([_, meta]) => (showAdvanced ? true : meta.required), ) as [fieldKey, meta]} + + { + (data.setProviderAuthParam as any)( + provider, + fieldKey, + value, + ); + invalidateAuthState(provider); + }} + /> + + {/each} +{/if} diff --git a/src/components/Settings/ConfiguredProvider.svelte b/src/components/Settings/ConfiguredProvider.svelte index fd3f69ce..b4971860 100644 --- a/src/components/Settings/ConfiguredProvider.svelte +++ b/src/components/Settings/ConfiguredProvider.svelte @@ -1,6 +1,8 @@ -{#if inputType === 'text'} +{#if inputType === "text" || inputType === "password"} stringFocusFunc?.(value as string)} + onblur={() => stringBlurFunc?.(value as string)} + onchange={() => stringChangeFunc?.(value as string)} + /> +{:else if inputType === "secret"} + focusFunc?.(value!)} - onblur={() => blurFunc?.(value!)} - onchange={() => changeFunc?.(value!)} + value={displayValue} + onfocus={() => { + isFocused = true; + stringFocusFunc?.(value as string); + }} + onblur={(e) => { + isFocused = false; + value = e.currentTarget.value; + stringBlurFunc?.(value as string); + }} + oninput={(e) => { + value = e.currentTarget.value; + }} + onchange={() => stringChangeFunc?.(value as string)} /> -{:else if inputType === 'number'} +{:else if inputType === "number"} blurFunc?.(value || 0)} - onfocus={() => focusFunc?.(value || 0)} - onchange={() => changeFunc?.(value || 0)} + onblur={() => numberBlurFunc?.((value as number) || 0)} + onfocus={() => numberFocusFunc?.((value as number) || 0)} + onchange={() => numberChangeFunc?.((value as number) || 0)} /> {/if} diff --git a/src/components/bitui/ModelPopover.svelte b/src/components/bitui/ModelPopover.svelte index ed7fcfd0..00543d71 100644 --- a/src/components/bitui/ModelPopover.svelte +++ b/src/components/bitui/ModelPopover.svelte @@ -8,14 +8,8 @@ } from "@selemondev/svgl-svelte"; import type { ChatModel } from "../../stores/chatStore.svelte"; import { getData } from "../../stores/dataStore.svelte"; - import { getPlugin, modelQuery } from "../../stores/state.svelte"; - - interface props { - model: ChatModel | null; - setModel: (model: ChatModel) => void; - } - - let { model, setModel }: props = $props(); + import { getPlugin } from "../../stores/state.svelte"; + import { createModelListQuery } from "../../utils/query"; const data = getData(); const plugin = getPlugin(); @@ -23,7 +17,7 @@ const providers = data.getConfiguredProviders(); const modelQueries = providers.map((provider) => - modelQuery(provider, plugin), + createModelListQuery(() => provider), ); const availableModels = $derived.by(() => { @@ -54,12 +48,11 @@ m.provider === sel.provider && m.model === sel.model, ); if (found) { - model = found; _chatModelInitialized = true; return; } } - model = list[0]; + data.setDefaultChatModel(list[0]); _chatModelInitialized = true; }); @@ -78,13 +71,16 @@
(isOpen = !isOpen)} - class="flex flex-row hover:bg-[--background-modifier-hover] pl-1 rounded-md gap-1" + class="clickable-icon" > -
{model?.model}
-
+
+ {data.getDefaultChatModel()?.model} +
+ {#if isOpen} +
+ {:else} +
+ {/if}
@@ -104,8 +100,8 @@
{ - setModel(model); isOpen = false; + data.setDefaultChatModel(model); }} > {#if model.provider === "OpenAI"} diff --git a/src/components/icons/ProviderIcon.svelte b/src/components/icons/ProviderIcon.svelte index ed03d8c4..45d6823d 100644 --- a/src/components/icons/ProviderIcon.svelte +++ b/src/components/icons/ProviderIcon.svelte @@ -4,7 +4,7 @@ AnthropicLogo, OllamaLogo, } from "@selemondev/svgl-svelte"; - import type { RegisteredProvider } from "papa-ts"; + import type { RegisteredProvider } from "../../types/providers"; import GenericAIIcon from "./GenericAIIcon.svelte"; interface Props { diff --git a/src/main.ts b/src/main.ts index 62bcb4fb..d5d4ebf8 100755 --- a/src/main.ts +++ b/src/main.ts @@ -1,138 +1,103 @@ -import { Modal, Notice, Plugin, normalizePath, type ViewState } from "obsidian"; -import { _ } from "svelte-i18n"; +import { AbstractTextComponent, Plugin } from "obsidian"; import "./lang/i18n"; import Log from "./logging"; import "./styles.css"; import SettingsTab from "./views/Settings/Settings"; import type { ProviderConfigs } from "./types/providers"; -import { - createData, - getData, - PluginDataStore, -} from "./stores/dataStore.svelte"; -import { chatLayout, setPlugin } from "./stores/state.svelte"; +import { createData, PluginDataStore } from "./stores/dataStore.svelte"; +import { setPlugin } from "./stores/state.svelte"; import { ChatView, VIEW_TYPE_CHAT } from "./views/Chat/Chat"; import { AgentManager } from "./agent/AgentManager"; -import type { SmartSecondBrainSettings } from "../v2/src/settings"; -import { ChatDB } from "./db/chatDbSchema"; import { type ChatModel, createMessenger } from "./stores/chatStore.svelte"; import type { UUIDv7 } from "./utils/uuid7Validator"; import { getQueryClient } from "./utils/query"; export interface PluginData { - providerConfig: ProviderConfigs; - initialAssistantMessageContent: string; - isUsingRag: boolean; - isGeneratingChatTitle: boolean; - defaultChatModel: ChatModel | null; - retrieveTopK: number; - assistantLanguage: "de" | "en"; - excludeFF: Array; - includeFF: Array; - isExcluding: boolean; - defaultChatName: string; - targetFolder: string; - isChatComfy: boolean; - isOnboarded: boolean; - debuggingLangchainKey: string; - enableLangSmith: boolean; - langSmithApiKey: string; - langSmithProject: string; - langSmithEndpoint: string; - mcpServers: Record; - isQuickSettingsOpen: boolean; - isVerbose: boolean; - hideIncognitoWarning: boolean; - isAutostart: boolean; - lastActiveChatId: UUIDv7 | null; + providerConfig: ProviderConfigs; + initialAssistantMessageContent: string; + isUsingRag: boolean; + isGeneratingChatTitle: boolean; + defaultChatModel: ChatModel | null; + retrieveTopK: number; + assistantLanguage: "de" | "en"; + excludeFF: Array; + includeFF: Array; + isExcluding: boolean; + defaultChatName: string; + targetFolder: string; + isChatComfy: boolean; + isOnboarded: boolean; + debuggingLangchainKey: string; + enableLangSmith: boolean; + langSmithApiKey: string; + langSmithProject: string; + langSmithEndpoint: string; + mcpServers: Record; + isQuickSettingsOpen: boolean; + isVerbose: boolean; + hideIncognitoWarning: boolean; + isAutostart: boolean; + lastActiveChatId: UUIDv7 | null; } export type ProviderName = "ollama" | "openai" | "anthropic" | "sap-ai-core"; export default class SecondBrainPlugin extends Plugin { - agentManager!: AgentManager; - queryClient = getQueryClient(); - pluginData!: PluginDataStore; - private chatCacheDb!: ChatDB; + agentManager!: AgentManager; + queryClient = getQueryClient(); + pluginData!: PluginDataStore; - async onload() { - setPlugin(this); - this.pluginData = await createData(this); + async onload() { + setPlugin(this); + this.pluginData = await createData(this); - // Register file-based chat view and .chat extension (v2 ChatView) - this.registerView(VIEW_TYPE_CHAT, (leaf) => new ChatView(leaf, this)); - this.registerExtensions(["chat"], VIEW_TYPE_CHAT); + // Register file-based chat view and .chat extension (v2 ChatView) + this.registerView(VIEW_TYPE_CHAT, (leaf) => new ChatView(leaf, this)); + this.registerExtensions(["chat"], VIEW_TYPE_CHAT); - const { isVerbose, isAutostart } = this.pluginData; + const { isVerbose, isAutostart } = this.pluginData; - if (this.manifest.dir === undefined) { - this.unload(); - throw Error("Cannot localize plugin directory."); - } + if (this.manifest.dir === undefined) { + this.unload(); + throw Error("Cannot localize plugin directory."); + } - this.addRibbonIcon("message-square", "New Chat", () => - this.createNewChat(), - ); + this.addRibbonIcon("message-square", "New Chat", () => + this.createNewChat(), + ); - this.addCommand({ - id: "open-chat", - name: "Open Chat", - icon: "message-square", - callback: () => this.openLatestChat(), - }); + this.addCommand({ + id: "open-chat", + name: "Open Chat", + icon: "message-square", + callback: async () => await this.agentManager.openLatestChat(), + }); - this.addSettingTab(new SettingsTab(this)); + this.addCommand({ + id: "new-chat", + name: "New Chat", + icon: "plus", + callback: async () => await this.agentManager.createNewChat(), + }); - // Initialize Agent Manager (v2) - this.agentManager = new AgentManager(this); - await this.agentManager.initialize(); - } + this.addSettingTab(new SettingsTab(this)); - async onunload() { - Log.info("Unloading plugin"); - if (this.agentManager) this.agentManager.cleanup(); - } + // Initialize Agent Manager (v2) + this.agentManager = new AgentManager(this); + await this.agentManager.initialize(); - async createNewChat() { - const folder = this.pluginData.targetFolder || "Chats"; - // Ensure folder exists - if (!(await this.app.vault.adapter.exists(folder))) { - await this.app.vault.adapter.mkdir(folder); - } - // Timestamp-based name - const now = new Date(); - const pad = (n: number) => String(n).padStart(2, "0"); - const threadId = `Chat ${now.getFullYear()}-${pad(now.getMonth() + 1)}-${pad(now.getDate())} ${pad(now.getHours())}-${pad(now.getMinutes())}-${pad(now.getSeconds())}`; - const path = normalizePath(`${folder}/${threadId}.chat`); - const initial = { - threadId, - createdAt: Date.now(), - updatedAt: Date.now(), - checkpoints: {}, - writes: {}, - }; - const file = await this.app.vault.create( - path, - JSON.stringify(initial, null, 2), - ); - await this.app.workspace.getLeaf(false).openFile(file); - } + createMessenger(this.agentManager); + } - async openLatestChat() { - const folder = this.pluginData.targetFolder || "Chats"; - // Ensure folder exists - if (!(await this.app.vault.adapter.exists(folder))) { - await this.app.vault.adapter.mkdir(folder); - } - // Find latest .chat file - const files = this.app.vault - .getFiles() - .filter((f) => f.path.startsWith(folder + "/") && f.extension === "chat") - .sort((a, b) => b.stat.mtime - a.stat.mtime); - let fileToOpen = files[0]; - if (!fileToOpen) { - await this.createNewChat(); - return; - } - await this.app.workspace.getLeaf(false).openFile(fileToOpen); - } + async onunload() { + Log.info("Unloading plugin"); + if (this.agentManager) this.agentManager.cleanup(); + } + + async createNewChat() { + return this.agentManager.createNewChat(); + } + + async openLatestChat() { + return this.agentManager.openLatestChat(); + } } diff --git a/src/stores/chatStore.svelte.ts b/src/stores/chatStore.svelte.ts index 8434aa4c..ed082b78 100644 --- a/src/stores/chatStore.svelte.ts +++ b/src/stores/chatStore.svelte.ts @@ -1,449 +1,488 @@ import { getPlugin } from "./state.svelte"; import { getData } from "./dataStore.svelte"; -import { Notice } from "obsidian"; -import { genUUIDv7, type UUIDv7 } from "../utils/uuid7Validator"; +import { Notice, TFile } from "obsidian"; +import { + genUUIDv7, + dateFromUUIDv7, + type UUIDv7, +} from "../utils/uuid7Validator"; +import type { AgentManager } from "../agent/AgentManager"; +import type { ThreadMessage, ThreadHistory } from "papa-ts"; + +/** Error info from a failed thread run */ +export interface ThreadError { + message: string; + name?: string; +} /* ----------------------------------------------------------------------------- * Shared Types * ---------------------------------------------------------------------------*/ export enum AssistantState { - "idle", - "streaming", - "success", - "error", - "cancelled", + idle, + streaming, + success, + error, + cancelled, } export enum MessageState { - "idle", - "answering", - "editing", + idle, + answering, + editing, } -export type ToolCallStatus = "running" | "completed"; +export type ToolCallStatus = "running" | "completed" | "failed"; export interface ToolCallState { - id: string; - name: string; - input: Record; - status: ToolCallStatus; - output?: unknown; + id: string; + name: string; + input: Record; + status: ToolCallStatus; + output?: unknown; } export interface UserMessage { - content: string; - attachments?: File[]; + content: string; + attachments?: File[]; } export interface AssistantMessage { - state: AssistantState; - content: string; - toolCalls?: ToolCallState[]; - nerd_stats?: { - tokensPerSecond: number; - retrievedDocsNum: number; - genModelConfig: any; - }; - errorCode?: string; + state: AssistantState; + content: string; + toolCalls?: ToolCallState[]; + nerd_stats?: { + tokensPerSecond: number; + retrievedDocsNum: number; + genModelConfig: any; + }; + errorCode?: string; } export interface MessagePair { - id: UUIDv7; - userMessage: UserMessage; - assistantMessage: AssistantMessage; + id: UUIDv7; + userMessage: UserMessage; + assistantMessage: AssistantMessage; + /** The model used to generate the assistant response */ + model?: ChatModel; } export interface ChatPreview { - id: UUIDv7; - title: string; - lastAccessed: Date; + id: UUIDv7; + title: string; + lastAccessed: Date; } export interface ChatModel { - model: string; - provider: any; - modelConfig: any; + model: string; + provider: any; + modelConfig: any; } /** - * In-memory representation of a chat with (optionally) loaded messages. - * For compatibility with legacy code that imported/expected `Chat`. + * In-memory representation of a chat with messages. */ export interface ChatRecord { - id: UUIDv7; - title: string; - lastAccessed: Date; - messages: MessagePair[]; + id: string; + messages: MessagePair[]; } -export type Chat = ChatRecord; // Backward compatibility alias +/* ----------------------------------------------------------------------------- + * ThreadMessage to MessagePair conversion + * ---------------------------------------------------------------------------*/ + +/** + * Extracts text content from a ThreadMessage content field. + * Handles both string content and array of content objects. + */ +function extractTextContent(content: ThreadMessage["content"]): string { + if (typeof content === "string") return content; + if (Array.isArray(content)) { + return content + .filter( + (c): c is { type: "text"; text: string } => + typeof c === "object" && c !== null && (c as any).type === "text", + ) + .map((c) => c.text) + .join(""); + } + return ""; +} -type StreamRole = "user" | "assistant" | "tool"; +/** + * Parses tool call arguments into a normalized object format. + */ +function normalizeToolInput(raw: unknown): Record { + if (raw === undefined || raw === null) return {}; + if (typeof raw === "string") { + try { + const parsed = JSON.parse(raw); + if (parsed && typeof parsed === "object" && !Array.isArray(parsed)) { + return parsed as Record; + } + return { value: parsed }; + } catch { + return { input: raw }; + } + } + if (Array.isArray(raw)) return { value: raw }; + if (typeof raw === "object") return raw as Record; + return { value: raw }; +} -interface NormalizedToolCall { - id: string; - name: string; - arguments?: unknown; - input?: unknown; +/** + * Converts an array of ThreadMessage (from papa-ts/LangGraph) into MessagePair[] for UI rendering. + * + * This function: + * 1. Pairs user messages with their corresponding assistant responses + * 2. Attaches tool outputs to their parent assistant message's tool calls + * 3. Merges consecutive assistant messages (tool calls + final response) + * 4. Uses UUIDv7 for message pair IDs (with timestamp extraction capability) + * 5. Uses errorCount to distinguish error state from cancelled state + */ +export function threadMessagesToMessagePairs( + threadMessages: ThreadMessage[], + errorCount: number = 0, +): MessagePair[] { + if (!threadMessages || threadMessages.length === 0) return []; + + const messagePairs: MessagePair[] = []; + + // Build a map of tool outputs: tool_call_id -> { content, status } + const toolOutputs = new Map< + string, + { content: unknown; status: ToolCallStatus } + >(); + for (const msg of threadMessages) { + const toolCallId = (msg as any).tool_call_id || (msg as any).toolCallId; + if (msg.role === "tool" && toolCallId) { + toolOutputs.set(toolCallId, { + content: msg.content, + status: (msg as any).status === "error" ? "failed" : "completed", + }); + } + } + + // Filter to just user and assistant messages + const conversationMessages = threadMessages.filter( + (msg) => msg.role === "user" || msg.role === "assistant", + ); + + let i = 0; + while (i < conversationMessages.length) { + const msg = conversationMessages[i]; + + if (msg.role === "user") { + // Start a new pair with user message + const userContent = extractTextContent(msg.content); + // ThreadMessages from LangGraph use UUIDv4, not UUIDv7 - generate fresh UUIDv7 + const pairId = genUUIDv7(); + + // Look ahead for assistant response(s) + const assistantMessages: ThreadMessage[] = []; + let j = i + 1; + while ( + j < conversationMessages.length && + conversationMessages[j].role === "assistant" + ) { + assistantMessages.push(conversationMessages[j]); + j++; + } + + // Merge assistant messages + let assistantContent = ""; + const allToolCalls: ToolCallState[] = []; + + for (const assistantMsg of assistantMessages) { + // Collect tool calls + const rawToolCalls = + (assistantMsg as any).tool_calls || (assistantMsg as any).toolCalls; + if (Array.isArray(rawToolCalls)) { + for (const tc of rawToolCalls) { + const toolOutput = toolOutputs.get(tc.id); + allToolCalls.push({ + id: tc.id, + name: tc.name, + input: normalizeToolInput(tc.arguments || tc.input), + status: toolOutput?.status ?? "running", + output: toolOutput?.content, + }); + } + } + + // Get text content (final response) + const textContent = extractTextContent(assistantMsg.content); + if (textContent.trim()) { + assistantContent = textContent; + } + } + + // Determine state for the last message pair + // If this is the last user message and there's no assistant response: + // - If errorCount > 0, it was likely an error (errors prevent responses) + // - Otherwise, it was cancelled by user + const isLastUserMessage = j >= conversationMessages.length; + const hasNoResponse = assistantMessages.length === 0; + + let state: AssistantState; + + if (hasNoResponse && errorCount > 0) { + // If there are errors in the thread and this message has no response, it errored + state = AssistantState.error; + errorCount--; // Consume one error + } else if (hasNoResponse) { + state = AssistantState.cancelled; + } else { + state = AssistantState.success; + } + + messagePairs.push({ + id: pairId, + userMessage: { content: userContent }, + assistantMessage: { + state, + content: assistantContent, + toolCalls: allToolCalls.length > 0 ? allToolCalls : undefined, + }, + }); + + i = j; // Skip past all the assistant messages we consumed + } else { + // Orphaned assistant message (no preceding user message) + // This shouldn't happen normally, but handle it gracefully + const assistantContent = extractTextContent(msg.content); + // ThreadMessages from LangGraph use UUIDv4, not UUIDv7 - generate fresh UUIDv7 + const pairId = genUUIDv7(); + + messagePairs.push({ + id: pairId, + userMessage: { content: "" }, + assistantMessage: { + state: AssistantState.success, + content: assistantContent, + }, + }); + i++; + } + } + + return messagePairs; } -interface NormalizedMessage { - id?: string; - role: StreamRole; - content?: unknown; - toolCalls?: NormalizedToolCall[]; - tool_call_id?: string; - toolCallId?: string; - name?: string; +/** + * Get the timestamp from a MessagePair's UUIDv7 id. + */ +export function getMessagePairTimestamp(pair: MessagePair): Date { + return dateFromUUIDv7(pair.id); } +/* ----------------------------------------------------------------------------- + * Streaming Types + * ---------------------------------------------------------------------------*/ + type StreamChunk = - | { type: "token"; token?: string; messages?: NormalizedMessage[] } - | { type: "result"; result?: { messages?: NormalizedMessage[] } } - | { type: "message"; messages: NormalizedMessage[] }; + | { type: "token"; token: string } + | { type: "tool_start"; toolCallId: string; toolName: string; input: unknown } + | { type: "tool_end"; toolCallId: string; toolName: string; output: unknown } + | { type: "result"; result?: unknown }; /* ----------------------------------------------------------------------------- * ChatSession * - Ephemeral per-chat runtime state (streaming, abort, reactive messages) - * - Uses granular persistence API (addMessage + assistant partial updates) + * - Converts ThreadMessages to MessagePairs on load, then works with MessagePairs only * ---------------------------------------------------------------------------*/ -// ChatSession.svelte.ts export class ChatSession { - readonly chatId: UUIDv7; - #title = $state(""); - lastAccessed: Date; - // Reactive messages array (mutate with push/splice/etc.) - messages: MessagePair[] = $state([]); - - // Streaming / lifecycle - private abortController: AbortController | null = null; - private cancelled = false; - - // Reactive UI state (if you read it in the UI) - messageState = $state(MessageState.idle); - - constructor(initial: ChatRecord) { - this.chatId = initial.id; - this.#title = initial.title; - this.lastAccessed = initial.lastAccessed; - - // Seed messages reactively - this.messages = initial.messages.slice(); - } - - /** Public snapshot (immutable-ish) */ - get snapshot(): ChatRecord { - return { - id: this.chatId, - title: this.#title, - lastAccessed: this.lastAccessed, - messages: this.messages.slice(), - }; - } - - getTitle(): string { - return this.#title; - } - - setTitle(title: string) { - if (this.#title !== title) { - this.#title = title; - } - } - - /** Append a message locally (no persistence). */ - private appendLocal(message: MessagePair) { - this.messages.push(message); - } - - /** Lookup a message by id */ - private findMessage(id: UUIDv7): MessagePair | undefined { - return this.messages.find((m) => m.id === id); - } - - private findMessageIndex(id: UUIDv7): number | undefined { - const idx = this.messages.findIndex((m) => m.id === id); - if (idx === -1) return undefined; - return idx; - } - /** Build chat history excluding the last (incomplete) message. */ - private buildChatHistory(): string { - if (this.messages.length === 0) return ""; - return this.messages - .slice(0, -1) - .map( - (p) => - `User: ${p.userMessage.content}\nAssistant: ${p.assistantMessage.content}`, - ) - .join("\n\n"); - } - - // async generateNewTitle(content: string, model: ChatModel) { - // const plugin = getPlugin(); - // const input = { - // modelConfig: { - // provider: model.provider, - // model: model.model, - // modelConfig: model.modelConfig, - // }, - // userQuery: content, - // chatHistory: "", - // lang: "en" as Language, - // }; - // this.setTitle(await plugin.papa.generateTitle(input)); - // } - - async resendMessage(messageId: UUIDv7, model: ChatModel) { - const message = this.findMessage(messageId); - const idx = this.findMessageIndex(messageId); - if (!(message && idx)) return false; - - //Todo: is it safe to splice proxy Objs? - this.messages.splice(idx); - - const res = await this.sendMessage( - message.userMessage.content, - message.userMessage.attachments, - ); - if (res) return true; - return false; - } - - /** - * Send a user message: - * - Create MessagePair (assistant idle) - * - Persist via addMessage - * - Kick off streaming process - */ - async sendMessage( - content: string, - attachments: File[] | undefined, - ): Promise { - const data = getData(); - // if (data.isGeneratingChatTitle && this.messages.length === 0) { - // this.generateNewTitle(content, model); - // } - const id = genUUIDv7(); - - console.log(id); - const pair: MessagePair = { - id, - userMessage: { content, attachments }, - assistantMessage: { state: AssistantState.idle, content: "" }, - }; - - // Optimistic local update (reactive) - this.appendLocal(pair); - - // Update global "last active" marker - getData().setLastActiveChatId(this.chatId); - - // Stream assistant reply (fire & forget) - void this.processAssistantReply(id, content); - - return id; - } - - /** Abort current streaming (if any) */ - stopStreaming(): void { - if (!this.abortController) { - throw new Error("No active stream to abort"); - } - this.cancelled = true; - this.abortController.abort(); - } - - /* ----------------------------------------------------------------------- - * Streaming logic - * ---------------------------------------------------------------------*/ - - private appendToken(message: AssistantMessage, token: string) { - if (!token) return; - message.content += token; - } - - private normalizeToolInput(raw: unknown): Record { - if (raw === undefined || raw === null) return {}; - if (typeof raw === "string") { - try { - const parsed = JSON.parse(raw); - if (parsed && typeof parsed === "object" && !Array.isArray(parsed)) { - return parsed as Record; - } - return { value: parsed }; - } catch { - return { input: raw }; - } - } - if (Array.isArray(raw)) return { value: raw }; - if (typeof raw === "object") return raw as Record; - return { value: raw }; - } - - private upsertToolCall( - message: AssistantMessage, - tc: NormalizedToolCall, - ): ToolCallState { - if (!message.toolCalls) message.toolCalls = []; - const idx = message.toolCalls.findIndex((t) => t.id === tc.id); - const base: ToolCallState = { - id: tc.id, - name: tc.name, - input: this.normalizeToolInput(tc.arguments ?? tc.input), - status: "running", - }; - if (idx >= 0) { - message.toolCalls[idx] = { - ...base, - output: message.toolCalls[idx].output, - status: message.toolCalls[idx].status, - }; - return message.toolCalls[idx]; - } - message.toolCalls.push(base); - return base; - } - - private attachToolOutput( - message: AssistantMessage, - toolCallId: string, - output: unknown, - name?: string, - ) { - if (!message.toolCalls) message.toolCalls = []; - const idx = message.toolCalls.findIndex((t) => t.id === toolCallId); - if (idx >= 0) { - message.toolCalls[idx] = { - ...message.toolCalls[idx], - status: "completed", - output, - }; - return; - } - message.toolCalls.push({ - id: toolCallId, - name: name ?? "tool", - input: {}, - status: "completed", - output, - }); - } - - private async processAssistantReply(messageId: UUIDv7, userContent: string) { - const target = this.findMessage(messageId); - if (!target) return; - console.log("target foudnd"); - try { - this.messageState = MessageState.answering; - - // Mark streaming started - target.assistantMessage.state = AssistantState.streaming; - - const plugin = getPlugin(); - const stream = plugin.agentManager.streamQuery( - userContent, - String(this.chatId), - ) as AsyncIterable; - - const assistantMsg = target.assistantMessage; - - const normalizeMessages = (chunk: StreamChunk): NormalizedMessage[] => { - if (chunk.type === "message") return chunk.messages ?? []; - if (chunk.type === "result") return chunk.result?.messages ?? []; - return []; - }; - - const applyNormalizedMessages = ( - normalizedMessages: NormalizedMessage[], - ) => { - if (!normalizedMessages.length) return; - - for (const msg of normalizedMessages) { - switch (msg.role) { - case "assistant": { - if (msg.toolCalls?.length) { - for (const tc of msg.toolCalls) { - this.upsertToolCall(assistantMsg, tc); - } - } - if (msg.content !== undefined) { - assistantMsg.content = String(msg.content ?? ""); - } - break; - } - case "tool": { - const toolCallId = (msg.tool_call_id || - (msg as any).toolCallId) as string | undefined; - if (toolCallId) { - this.attachToolOutput( - assistantMsg, - toolCallId, - msg.content, - msg.name, - ); - } - break; - } - default: - break; - } - } - }; - - for await (const chunk of stream) { - if (chunk.type === "token") { - console.log(chunk.token); - this.appendToken(assistantMsg, chunk.token ?? ""); - continue; - } - - const normalizedMessages = normalizeMessages(chunk); - applyNormalizedMessages(normalizedMessages); - - if (chunk.type === "result" && normalizedMessages.length) { - const lastMsg = normalizedMessages[normalizedMessages.length - 1]; - if (lastMsg.role === "assistant") { - assistantMsg.content = String(lastMsg.content ?? ""); - } - } - } - - target.assistantMessage.state = AssistantState.success; - } catch (err) { - const failedState: AssistantState = this.cancelled - ? AssistantState.cancelled - : AssistantState.error; - target.assistantMessage.state = failedState; - } finally { - this.abortController = null; - this.cancelled = false; - this.messageState = MessageState.idle; - } - } - - /* ----------------------------------------------------------------------- - * Utilities exposed for Messenger / consumers - * ---------------------------------------------------------------------*/ - - // If you don't want callers to mutate the array, you can expose a copy, - // but for reactivity in the UI it’s typical to read session.messages directly. - getMessages(): MessagePair[] { - return this.messages; - } - - addPreloadedMessages(messages: MessagePair[], replace = false) { - if (replace) { - this.messages = messages.slice(); - } else { - // ensure no duplicates - const existing = new Set(this.messages.map((m) => m.id)); - for (const m of messages) { - if (!existing.has(m.id)) this.messages.push(m); - } - } - } + readonly id: string; + // In-memory MessagePairs for UI + messages: MessagePair[] = $state([]); + + // Streaming / lifecycle + private abortController: AbortController | null = null; + private cancelled = false; + + // Reactive UI state + messageState = $state(MessageState.idle); + + constructor( + id: string, + threadMessages: ThreadMessage[], + errorCount: number = 0, + ) { + this.id = id; + // Convert once on load, then drop the raw ThreadMessages + this.messages = threadMessagesToMessagePairs(threadMessages, errorCount); + } + + /** Public snapshot (immutable-ish) */ + get snapshot(): ChatRecord { + return { + id: this.id, + messages: this.messages.slice(), + }; + } + + /** Find a message pair by id */ + private findPair(id: UUIDv7): MessagePair | undefined { + return this.messages.find((m) => m.id === id); + } + + /** + * Send a user message: + * - Create MessagePair with idle assistant + * - Kick off streaming process + */ + async sendMessage(content: string, attachments?: File[]): Promise { + const pairId = genUUIDv7(); + + // Capture the current model at send time + const currentModel = getData().getDefaultChatModel() ?? undefined; + + const pair: MessagePair = { + id: pairId, + userMessage: { content, attachments }, + assistantMessage: { state: AssistantState.idle, content: "" }, + model: currentModel, + }; + + this.messages.push(pair); + + // Stream assistant reply + void this.processAssistantReply(pairId, content); + + return pairId; + } + + /** Abort current streaming (if any) */ + stopStreaming(): void { + if (!this.abortController) { + throw new Error("No active stream to abort"); + } + this.cancelled = true; + this.abortController.abort(); + } + + /* ----------------------------------------------------------------------- + * Streaming logic + * ---------------------------------------------------------------------*/ + + private appendToken(message: AssistantMessage, token: string) { + if (!token) return; + message.content += token; + } + + private normalizeToolInput(raw: unknown): Record { + if (raw === undefined || raw === null) return {}; + if (typeof raw === "string") { + try { + const parsed = JSON.parse(raw); + if (parsed && typeof parsed === "object" && !Array.isArray(parsed)) { + return parsed as Record; + } + return { value: parsed }; + } catch { + return { input: raw }; + } + } + if (Array.isArray(raw)) return { value: raw }; + if (typeof raw === "object") return raw as Record; + return { value: raw }; + } + + private async processAssistantReply(pairId: UUIDv7, userContent: string) { + const pair = this.findPair(pairId); + if (!pair) return; + + // Create AbortController for this streaming session + this.abortController = new AbortController(); + const signal = this.abortController.signal; + + try { + this.messageState = MessageState.answering; + + // Mark streaming started + pair.assistantMessage.state = AssistantState.streaming; + + const plugin = getPlugin(); + const stream = plugin.agentManager.streamQuery( + userContent, + String(this.id), + signal, + ) as AsyncIterable; + + const assistantMsg = pair.assistantMessage; + + for await (const chunk of stream) { + if (chunk.type === "token") { + this.appendToken(assistantMsg, chunk.token); + continue; + } + + if (chunk.type === "tool_start") { + // Add a new tool call in "running" state + if (!assistantMsg.toolCalls) assistantMsg.toolCalls = []; + assistantMsg.toolCalls.push({ + id: chunk.toolCallId, + name: chunk.toolName, + input: this.normalizeToolInput(chunk.input), + status: "running", + }); + continue; + } + + if (chunk.type === "tool_end") { + // Find the tool call and mark it completed with output + if (assistantMsg.toolCalls) { + const tc = assistantMsg.toolCalls.find( + (t) => t.id === chunk.toolCallId, + ); + if (tc) { + tc.status = "completed"; + tc.output = chunk.output; + } else { + // Tool call wasn't found (shouldn't happen, but handle gracefully) + assistantMsg.toolCalls.push({ + id: chunk.toolCallId, + name: chunk.toolName, + input: {}, + status: "completed", + output: chunk.output, + }); + } + } else { + // No tool calls array yet (shouldn't happen, but handle gracefully) + assistantMsg.toolCalls = [ + { + id: chunk.toolCallId, + name: chunk.toolName, + input: {}, + status: "completed", + output: chunk.output, + }, + ]; + } + continue; + } + + // For result chunks, stream is complete + if (chunk.type === "result") { + break; + } + } + + pair.assistantMessage.state = AssistantState.success; + } catch (err) { + const failedState: AssistantState = this.cancelled + ? AssistantState.cancelled + : AssistantState.error; + pair.assistantMessage.state = failedState; + } finally { + this.abortController = null; + this.cancelled = false; + this.messageState = MessageState.idle; + } + } } /* ----------------------------------------------------------------------------- @@ -452,184 +491,49 @@ export class ChatSession { * - Uses granular persistence APIs * ---------------------------------------------------------------------------*/ export class Messenger { - private sessions = new Map(); - private records = new Map(); - private pendingLoads = new Map>(); - - constructor() {} - - /* ---------------- Chat Creation / Metadata ---------------- */ - - async createChat(): Promise { - const data = getData(); - const title = data.defaultChatName; - const record: ChatRecord = { - id: genUUIDv7(), - title, - lastAccessed: new Date(), - messages: [], - }; - this.records.set(record.id, record); - return record; - } - - async setTitle(id: UUIDv7, title: string): Promise { - const record = this.records.get(id); - if (!record) return false; - if (record.title === title) return true; - record.title = title; - const session = this.sessions.get(id); - if (session) session.setTitle(title); - return true; - } - - async loadChatRecord(id: UUIDv7): Promise { - return this.records.get(id) ?? null; - } - - async listChats(): Promise { - return Array.from(this.records.values()).map((r) => ({ - id: r.id, - title: r.title, - lastAccessed: r.lastAccessed, - })); - } - - async deleteChat(id: UUIDv7): Promise { - this.sessions.delete(id); - return this.records.delete(id); - } - - async branchOffFromMessage( - chatId: UUIDv7, - cutoffMessageId: UUIDv7, - ): Promise { - const source = this.records.get(chatId); - if (!source) return genUUIDv7(); - const cutoffIndex = source.messages.findIndex( - (m) => m.id === cutoffMessageId, - ); - const sliceEnd = - cutoffIndex >= 0 ? cutoffIndex + 1 : source.messages.length; - const newChatId = genUUIDv7(); - const cloned: ChatRecord = { - id: newChatId, - title: `${source.title} (branch)`, - lastAccessed: new Date(), - messages: source.messages.slice(0, sliceEnd).map((m) => ({ - ...m, - id: genUUIDv7(), - })), - }; - this.records.set(newChatId, cloned); - return newChatId; - } - - /* ---------------- Session Management ---------------- */ - - async ensureSession( - chatId: UUIDv7, - preloadAll = true, - bumpLastAccessed = true, - ): Promise { - const existing = this.sessions.get(chatId); - if (existing) { - if (bumpLastAccessed) { - existing.lastAccessed = new Date(); - } - return existing; - } - - const inflight = this.pendingLoads.get(chatId); - if (inflight) return inflight; - - const promise = (async () => { - const record = this.records.get(chatId); - if (!record) throw new Error(`Chat ${chatId} not found`); - - const hydrated: ChatRecord = { - ...record, - lastAccessed: bumpLastAccessed ? new Date() : record.lastAccessed, - messages: preloadAll ? record.messages.slice() : [], - }; - - if (bumpLastAccessed) { - record.lastAccessed = hydrated.lastAccessed; - } - - const session = new ChatSession(hydrated); - this.sessions.set(chatId, session); - return session; - })(); - - this.pendingLoads.set(chatId, promise); - try { - return await promise; - } finally { - this.pendingLoads.delete(chatId); - } - } - - getSessions(chatId: UUIDv7 | null): ChatSession | null { - if (!chatId) return null; - return this.sessions.get(chatId) ?? null; - } - - /* ---------------- Sending Messages ---------------- */ - - async sendMessage( - content: string, - - attachments?: File[], - currentSession?: CurrentSession | null, - ): Promise { - let session = currentSession?.session ?? null; - - if (!session) { - const newChat = await this.createChat(); - new Notice("New chat created"); - session = await this.ensureSession(newChat.id); - if (currentSession) currentSession.session = session; - } - - return session.sendMessage(content, attachments); - } - - getActiveSessionsCount(): number { - return this.sessions.size; - } - - /* ---------------- Dirty Response Cleanup ---------------- */ - - async findDirtyResponses(): Promise { - const previews = await this.listChats(); - const dirty: ChatRecord[] = []; - for (const p of previews) { - const rec = await this.loadChatRecord(p.id); - if (!rec) continue; - if ( - rec.messages.some( - (m) => m.assistantMessage.state === AssistantState.streaming, - ) - ) { - dirty.push(rec); - } - } - return dirty; - } - - async cleanupDirtyResponses(): Promise { - const dirtyChats = await this.findDirtyResponses(); - for (const chat of dirtyChats) { - for (const mp of chat.messages) { - if (mp.assistantMessage.state === AssistantState.streaming) { - mp.assistantMessage.state = AssistantState.error; - mp.assistantMessage.content = - mp.assistantMessage.content || "Response interrupted"; - } - } - } - } + session: ChatSession | null = $state(null); + #agentManager: AgentManager; + + constructor(agentManager: AgentManager) { + this.#agentManager = agentManager; + } + + deriveThreadId = (file: TFile): string | null => { + let threadId = file.basename; + if (threadId.includes(" - ")) { + const parts = threadId.split(" - "); + const dateTimePart = parts[parts.length - 1]; + threadId = `Chat ${dateTimePart}`; + } + if (!threadId || threadId === "New Chat") return null; + return threadId; + }; + + /* ---------------- Chat Creation / Metadata ---------------- */ + + async loadSession(file: TFile) { + const id = this.deriveThreadId(file); + if (!id) throw new Error("Invalid thread ID"); + const history = await this.#agentManager.getThreadHistory(id); + // Cast to access lastError and errorCount properties (available after papa-ts rebuild) + const historyWithError = history as + | (ThreadHistory & { lastError?: ThreadError; errorCount?: number }) + | null; + this.session = new ChatSession( + id, + historyWithError?.messages || [], + historyWithError?.errorCount || 0, + ); + } + + /* ---------------- Sending Messages ---------------- */ + + async sendMessage(content: string, attachments?: File[]): Promise { + if (!this.session) { + throw new Error("No active session"); + } + return this.session.sendMessage(content, attachments); + } } /* ----------------------------------------------------------------------------- @@ -637,27 +541,16 @@ export class Messenger { * ---------------------------------------------------------------------------*/ let messengerSingleton: Messenger | null = null; -export function createMessenger(): Messenger { - if (!messengerSingleton) { - messengerSingleton = new Messenger(); - } - return messengerSingleton; +export function createMessenger(agentManager?: AgentManager): Messenger { + if (!messengerSingleton) { + if (!agentManager) { + throw new Error("AgentManager is required for first Messenger creation"); + } + messengerSingleton = new Messenger(agentManager); + } + return messengerSingleton; } export function getMessenger(): Messenger | null { - return messengerSingleton; -} - -let currentThreadId = $state(null); - -export function getCurrentThreadId(): string | null { - return currentThreadId; -} - -export function setCurrentThreadId(id: string | null) { - currentThreadId = id; -} - -export class CurrentSession { - session: ChatSession | null = $state(null); + return messengerSingleton; } diff --git a/src/stores/dataStore.svelte.ts b/src/stores/dataStore.svelte.ts index e79c5fa3..51a7dbc9 100644 --- a/src/stores/dataStore.svelte.ts +++ b/src/stores/dataStore.svelte.ts @@ -1,12 +1,3 @@ -import { - Prompts, - type EmbedModelConfig, - type GenModelConfig, - type Language, - type ProviderConfig, - type RegisteredEmbedProvider, - type RegisteredProvider, -} from "papa-ts"; import SecondBrainPlugin, { type PluginData } from "../main"; import { normalizePath } from "obsidian"; import { DEFAULT_SETTINGS } from "../constants/defaults"; @@ -19,9 +10,12 @@ import { type EmbedProviders, type GenProviders, type GetProviderAuth, + type EmbedModelConfig, + type GenModelConfig, } from "../types/providers"; import type { UUIDv7 } from "../utils/uuid7Validator"; import type { ChatModel } from "./chatStore.svelte"; +import { type RegisteredProvider } from "../types/providers"; export class PluginDataStore { #data: PluginData; @@ -31,10 +25,20 @@ export class PluginDataStore { this._plugin = plugin; // Restore Maps from plain object shapes (after persistence serialization) for (const cfg of Object.values(initialData.providerConfig) as any[]) { - if (cfg && "embedModels" in cfg && cfg.embedModels && !(cfg.embedModels instanceof Map)) { + if ( + cfg && + "embedModels" in cfg && + cfg.embedModels && + !(cfg.embedModels instanceof Map) + ) { cfg.embedModels = new Map(Object.entries(cfg.embedModels)); } - if (cfg && "genModels" in cfg && cfg.genModels && !(cfg.genModels instanceof Map)) { + if ( + cfg && + "genModels" in cfg && + cfg.genModels && + !(cfg.genModels instanceof Map) + ) { cfg.genModels = new Map(Object.entries(cfg.genModels)); } } @@ -313,20 +317,22 @@ export class PluginDataStore { return this.#data.providerConfig[provider].isConfigured; } toggleProviderIsConfigured(provider: RegisteredProvider) { - this.#data.providerConfig[provider].isConfigured = !this.#data.providerConfig[provider].isConfigured; + this.#data.providerConfig[provider].isConfigured = + !this.#data.providerConfig[provider].isConfigured; this.saveSettings(); } - getProviderAuthParams(provider: RegisteredProvider): GetProviderAuth { + getProviderAuthParams( + provider: RegisteredProvider, + ): GetProviderAuth { //TODO check runtime validity return this.#data.providerConfig[provider].providerAuth; } - setProviderAuthParam>( - provider: T, - key: K, - value: GetProviderAuth[K], - ): void { + setProviderAuthParam< + T extends RegisteredProvider, + K extends keyof GetProviderAuth, + >(provider: T, key: K, value: GetProviderAuth[K]): void { const newAuth = { ...this.#data.providerConfig[provider].providerAuth }; newAuth[key] = value; this.#data.providerConfig[provider].providerAuth = newAuth; @@ -335,13 +341,20 @@ export class PluginDataStore { // --- Embed Model Management (Map-based) --- - getEmbedModels

(provider: P): Map { + getEmbedModels

( + provider: P, + ): Map { return this.#data.providerConfig[provider].embedModels; } - addEmbedModel

(provider: P, modelName: string, conf: EmbedModelConfig) { + addEmbedModel

( + provider: P, + modelName: string, + conf: EmbedModelConfig, + ) { const current = this.#data.providerConfig[provider].embedModels; - if (current.has(modelName)) throw new AddEmbedModelError(provider, modelName); + if (current.has(modelName)) + throw new AddEmbedModelError(provider, modelName); // Reassign a new Map to ensure reactivity + easier change detection const next = new Map(current); next.set(modelName, conf); @@ -349,9 +362,14 @@ export class PluginDataStore { this.saveSettings(); } - updateEmbedModel

(provider: P, modelName: string, conf: EmbedModelConfig) { + updateEmbedModel

( + provider: P, + modelName: string, + conf: EmbedModelConfig, + ) { const current = this.#data.providerConfig[provider].embedModels; - if (!current.has(modelName)) throw new SetEmbedModelError(provider, modelName); + if (!current.has(modelName)) + throw new SetEmbedModelError(provider, modelName); const next = new Map(current); next.set(modelName, conf); this.#data.providerConfig[provider].embedModels = next; @@ -360,18 +378,25 @@ export class PluginDataStore { deleteEmbedModel

(provider: P, modelName: string) { const current = this.#data.providerConfig[provider].embedModels; - if (!current.has(modelName)) throw new SetEmbedModelError(provider, modelName); + if (!current.has(modelName)) + throw new SetEmbedModelError(provider, modelName); const next = new Map(current); next.delete(modelName); this.#data.providerConfig[provider].embedModels = next; this.saveSettings(); } - getGenModels

(provider: P): Map { + getGenModels

( + provider: P, + ): Map { return this.#data.providerConfig[provider].genModels; } - addGenModel

(provider: P, modelName: string, conf: GenModelConfig) { + addGenModel

( + provider: P, + modelName: string, + conf: GenModelConfig, + ) { const current = this.#data.providerConfig[provider].genModels; if (current.has(modelName)) throw new AddGenModelError(provider, modelName); const next = new Map(current); @@ -380,9 +405,14 @@ export class PluginDataStore { this.saveSettings(); } - updateGenModel

(provider: P, modelName: string, conf: GenModelConfig) { + updateGenModel

( + provider: P, + modelName: string, + conf: GenModelConfig, + ) { const current = this.#data.providerConfig[provider].genModels; - if (!current.has(modelName)) throw new SetGenModelError(provider, modelName); + if (!current.has(modelName)) + throw new SetGenModelError(provider, modelName); const next = new Map(current); next.set(modelName, conf); this.#data.providerConfig[provider].genModels = next; @@ -391,7 +421,8 @@ export class PluginDataStore { deleteGenModel

(provider: P, modelName: string) { const current = this.#data.providerConfig[provider].genModels; - if (!current.has(modelName)) throw new SetGenModelError(provider, modelName); + if (!current.has(modelName)) + throw new SetGenModelError(provider, modelName); const next = new Map(current); next.delete(modelName); this.#data.providerConfig[provider].genModels = next; @@ -399,10 +430,15 @@ export class PluginDataStore { } // Get/set genModels (if present) - getProviderGenModels(provider: K): Record | undefined { + getProviderGenModels( + provider: K, + ): Record | undefined { return (this.#data.providerConfig[provider] as any).genModels; } - setProviderGenModels(provider: K, value: Record) { + setProviderGenModels( + provider: K, + value: Record, + ) { if ("genModels" in this.#data.providerConfig[provider]) { (this.#data.providerConfig[provider] as any).genModels = value; this.saveSettings(); @@ -412,13 +448,21 @@ export class PluginDataStore { let _pluginDataStore: PluginDataStore | null = null; -export async function createData(plugin: SecondBrainPlugin): Promise { +export async function createData( + plugin: SecondBrainPlugin, +): Promise { if (_pluginDataStore) return _pluginDataStore; const rawData = await plugin.loadData(); // Validate and safely load plugin data - const { data: validatedData, hasErrors, hasWarnings, errors, warnings } = safeLoadPluginData(rawData); + const { + data: validatedData, + hasErrors, + hasWarnings, + errors, + warnings, + } = safeLoadPluginData(rawData); // Log validation results if (hasWarnings) { diff --git a/src/stores/state.svelte.ts b/src/stores/state.svelte.ts index 72d4f065..f7983ee0 100644 --- a/src/stores/state.svelte.ts +++ b/src/stores/state.svelte.ts @@ -3,47 +3,45 @@ import SecondBrainPlugin from "../main"; import { createQuery } from "@tanstack/svelte-query"; export const providerState: Record = $state({ - OpenAI: false, - Ollama: false, - CustomOpenAI: false, - Anthropic: false, + OpenAI: false, + Ollama: false, + CustomOpenAI: false, + Anthropic: false, }); let isChatInSidebar: boolean = $state(true); export const chatLayout = { - get isSidebar(): boolean { - return isChatInSidebar; - }, + get isSidebar(): boolean { + return isChatInSidebar; + }, - set isSidebar(val: boolean) { - isChatInSidebar = val; - }, + set isSidebar(val: boolean) { + isChatInSidebar = val; + }, - toggleIsSidebar() { - isChatInSidebar = !isChatInSidebar; - }, + toggleIsSidebar() { + isChatInSidebar = !isChatInSidebar; + }, }; let _plugin: SecondBrainPlugin | undefined = $state(undefined); export function setPlugin(plugin: SecondBrainPlugin) { - _plugin = plugin; + _plugin = plugin; } export function getPlugin(): SecondBrainPlugin { - if (!_plugin) throw Error("No"); - return _plugin; + if (!_plugin) throw Error("No"); + return _plugin; } -export function modelQuery( - provider: RegisteredProvider, - plugin: SecondBrainPlugin, -) { - return createQuery(() => ({ - queryKey: ["models", provider], - queryFn: async () => { - return await ["Models"]; - }, - })); +// Deprecated: use createModelListQuery in utils/query +export function modelQuery(provider: RegisteredProvider, plugin: SecondBrainPlugin) { + return createQuery(() => ({ + queryKey: ["models", provider], + queryFn: async () => { + return await ["Models"]; + }, + })); } diff --git a/src/styles.css b/src/styles.css index df6cdd15..dfdc7671 100755 --- a/src/styles.css +++ b/src/styles.css @@ -2,6 +2,14 @@ @tailwind components; @tailwind utilities; +:root { + --icon-xs: 0.75rem; + --icon-sm: 1rem; + --icon-md: 1.25rem; + --icon-lg: 1.5rem; + --icon-xl: 2rem; +} + .obsidian-border { - border-bottom: 1px solid var(--background-modifier-border); + border-bottom: 1px solid var(--background-modifier-border); } diff --git a/src/types/providers.ts b/src/types/providers.ts index e951882d..0b468868 100644 --- a/src/types/providers.ts +++ b/src/types/providers.ts @@ -1,95 +1,145 @@ +import { type BuiltInProviderOptions } from "papa-ts"; + +// Re-export for convenience +export type { BuiltInProviderOptions }; + // Define these locally since they're not exported from the current papa-ts version export type RegisteredProvider = - | "OpenAI" - | "Ollama" - | "CustomOpenAI" - | "Anthropic"; + | "OpenAI" + | "Ollama" + | "CustomOpenAI" + | "Anthropic"; export type RegisteredGenProvider = RegisteredProvider; export type RegisteredEmbedProvider = RegisteredProvider; export const registeredProviders = [ - "OpenAI", - "Ollama", - "CustomOpenAI", - "Anthropic", + "OpenAI", + "Ollama", + "CustomOpenAI", + "Anthropic", ] as const; -// Define configuration types based on usage -export interface OllamaConfig { - baseUrl: string; -} +// Provider auth is stored as BuiltInProviderOptions (apiKey, baseUrl, headers, etc.) +export type ProviderAuth = BuiltInProviderOptions; -export interface OpenAIConfig { - apiKey: string; -} +type FieldKind = "text" | "password" | "textarea"; -export interface AnthropicConfig { - apiKey: string; -} +export type FieldMeta = { + label: string; + required: boolean; + kind: FieldKind; + helper?: string; +}; -export interface CustomOpenAIConfig { - apiKey: string; - baseUrl?: string; -} +export const providerFieldMeta: Record< + RegisteredProvider, + Record +> = { + OpenAI: { + apiKey: { label: "API Key", required: true, kind: "password" }, + baseUrl: { + label: "Base URL", + required: false, + kind: "text", + helper: "Override for custom endpoints", + }, + headers: { + label: "Headers (JSON)", + required: false, + kind: "textarea", + }, + }, + Anthropic: { + apiKey: { label: "API Key", required: true, kind: "password" }, + baseUrl: { + label: "Base URL", + required: false, + kind: "text", + }, + headers: { + label: "Headers (JSON)", + required: false, + kind: "textarea", + }, + }, + CustomOpenAI: { + apiKey: { label: "API Key", required: true, kind: "password" }, + baseUrl: { + label: "Base URL", + required: false, + kind: "text", + }, + headers: { + label: "Headers (JSON)", + required: false, + kind: "textarea", + }, + }, + Ollama: { + baseUrl: { label: "Base URL", required: true, kind: "text" }, + headers: { + label: "Headers (JSON)", + required: false, + kind: "textarea", + }, + }, +}; export interface EmbedModelConfig { - similarityThreshold: number; + similarityThreshold: number; } export interface GenModelConfig { - temperature: number; - contextWindow: number; + temperature: number; + contextWindow: number; } // Helper types for model settings type EmbedModelSettings = { - embedModels: Map; + embedModels: Map; }; type GenModelSettings = { - genModels: Map; + genModels: Map; }; -// Map providers to their base configuration types +// All providers use BuiltInProviderOptions for auth storage type ProviderAuthMap = { - OpenAI: OpenAIConfig; - Ollama: OllamaConfig; - Anthropic: AnthropicConfig; - CustomOpenAI: CustomOpenAIConfig; + [K in RegisteredProvider]: BuiltInProviderOptions; }; type ConfigurationState = { - isConfigured: boolean; + isConfigured: boolean; }; // Helper type to determine if a provider supports embedding type SupportsEmbedding = - T extends RegisteredEmbedProvider ? true : false; + T extends RegisteredEmbedProvider ? true : false; // Helper type to determine if a provider supports generation type SupportsGeneration = - T extends RegisteredGenProvider ? true : false; + T extends RegisteredGenProvider ? true : false; // Create the configuration type for each provider based on its capabilities type ProviderConfiguration = - ConfigurationState & { - providerAuth: ProviderAuthMap[T]; - } & (T extends RegisteredEmbedProvider ? EmbedModelSettings : {}) & - (T extends RegisteredGenProvider ? GenModelSettings : {}); + ConfigurationState & { + providerAuth: ProviderAuthMap[T]; + } & (T extends RegisteredEmbedProvider ? EmbedModelSettings : {}) & + (T extends RegisteredGenProvider ? GenModelSettings : {}); // Generate a mapped type that includes all registered providers export type AllProviderConfigs = { - [K in RegisteredProvider]: ProviderConfiguration; + [K in RegisteredProvider]: ProviderConfiguration; }; // Utility type to ensure completeness - this will cause a TypeScript error // if any registered provider is missing from our configuration type EnsureAllProvidersIncluded = { - [K in (typeof registeredProviders)[number]]: K extends keyof AllProviderConfigs - ? true - : false; + [K in (typeof registeredProviders)[number]]: K extends keyof AllProviderConfigs + ? true + : false; }; // Type guard to check if all providers are properly configured @@ -100,68 +150,68 @@ export type ProviderConfigs = ValidateProviderConfigs; // Utility types for accessing specific provider configurations export type GetProviderConfig = - AllProviderConfigs[T]; + AllProviderConfigs[T]; export type GetProviderAuth = ProviderAuthMap[T]; // Type to get all providers that support embedding export type EmbedProviders = { - [K in RegisteredProvider]: SupportsEmbedding extends true ? K : never; + [K in RegisteredProvider]: SupportsEmbedding extends true ? K : never; }[RegisteredProvider]; // Type to get all providers that support generation export type GenProviders = { - [K in RegisteredProvider]: SupportsGeneration extends true ? K : never; + [K in RegisteredProvider]: SupportsGeneration extends true ? K : never; }[RegisteredProvider]; // Example usage types for validation export type EmbedProvidersConfig = { - [K in EmbedProviders]: GetProviderConfig; + [K in EmbedProviders]: GetProviderConfig; }; export type GenProvidersConfig = { - [K in GenProviders]: GetProviderConfig; + [K in GenProviders]: GetProviderConfig; }; // Utility function type for runtime validation export type ProviderConfigValidator = { - [K in RegisteredProvider]: ( - config: unknown, - ) => config is GetProviderConfig; + [K in RegisteredProvider]: ( + config: unknown, + ) => config is GetProviderConfig; }; export class SetEmbedModelError extends Error { - constructor(model: string, provider: string) { - super( - `Model "${model}" does not exist in embedModels for provider "${provider}".`, - ); - this.name = "SetEmbedModelError"; - } + constructor(model: string, provider: string) { + super( + `Model "${model}" does not exist in embedModels for provider "${provider}".`, + ); + this.name = "SetEmbedModelError"; + } } export class AddEmbedModelError extends Error { - constructor(model: string, provider: string) { - super( - `Model "${model}" already exist in embedModels for provider "${provider}".`, - ); - this.name = "AddEmbedModelError"; - } + constructor(model: string, provider: string) { + super( + `Model "${model}" already exist in embedModels for provider "${provider}".`, + ); + this.name = "AddEmbedModelError"; + } } export class SetGenModelError extends Error { - constructor(model: string, provider: string) { - super( - `Model "${model}" does not exist in genModels for provider "${provider}".`, - ); - this.name = "SetGEnModelError"; - } + constructor(model: string, provider: string) { + super( + `Model "${model}" does not exist in genModels for provider "${provider}".`, + ); + this.name = "SetGEnModelError"; + } } export class AddGenModelError extends Error { - constructor(model: string, provider: string) { - super( - `Model "${model}" already exist in genModels for provider "${provider}".`, - ); - this.name = "AddGenModelError"; - } + constructor(model: string, provider: string) { + super( + `Model "${model}" already exist in genModels for provider "${provider}".`, + ); + this.name = "AddGenModelError"; + } } diff --git a/src/utils/dataValidation.ts b/src/utils/dataValidation.ts index 6a769128..6923f69d 100644 --- a/src/utils/dataValidation.ts +++ b/src/utils/dataValidation.ts @@ -648,6 +648,29 @@ export function validatePluginData(rawData: unknown): ValidationResult { validatedData.includeFF = includeFFValidation.data || DEFAULT_SETTINGS.includeFF; warnings.push(...includeFFValidation.warnings); + // Validate defaultChatModel + if (data.defaultChatModel !== undefined && data.defaultChatModel !== null) { + const chatModel = data.defaultChatModel; + if ( + typeof chatModel === "object" && + typeof chatModel.model === "string" && + chatModel.model.length > 0 && + typeof chatModel.provider === "string" && + chatModel.provider.length > 0 + ) { + validatedData.defaultChatModel = { + model: chatModel.model, + provider: chatModel.provider, + modelConfig: chatModel.modelConfig ?? {}, + }; + } else { + warnings.push("defaultChatModel has invalid structure, using default (null)"); + validatedData.defaultChatModel = DEFAULT_SETTINGS.defaultChatModel; + } + } else { + validatedData.defaultChatModel = DEFAULT_SETTINGS.defaultChatModel; + } + // Ensure we have all required fields const completeData: PluginData = { ...DEFAULT_SETTINGS, diff --git a/src/utils/query.ts b/src/utils/query.ts index 6299d887..17cd64a8 100644 --- a/src/utils/query.ts +++ b/src/utils/query.ts @@ -1,4 +1,9 @@ +import { createQuery } from "@tanstack/svelte-query"; import { QueryClient } from "@tanstack/svelte-query"; +import type { RegisteredProvider } from "../types/providers"; +import { getPlugin } from "../stores/state.svelte"; +import { getData } from "../stores/dataStore.svelte"; +import type { ValidationResult } from "../agent/AgentManager"; // Create a global QueryClient instance const queryClient = new QueryClient({ @@ -15,3 +20,34 @@ const queryClient = new QueryClient({ export function getQueryClient() { return queryClient; } + +export function createAuthStateQuery(provider: () => RegisteredProvider) { + const plugin = getPlugin(); + const data = getData(); + + return createQuery(() => ({ + queryKey: ["authState", provider()], + queryFn: async () => { + const res = await plugin.agentManager.testProviderConfig( + provider(), + data.getProviderAuthParams(provider()), + ); + return res; + }, + })); +} + +export function invalidateAuthState(provider: RegisteredProvider) { + const plugin = getPlugin(); + plugin.queryClient.invalidateQueries({ + queryKey: ["authState", provider], + }); +} + +export function createModelListQuery(provider: () => RegisteredProvider) { + const plugin = getPlugin(); + return createQuery(() => ({ + queryKey: ["models", provider()], + queryFn: async () => plugin.agentManager.getAvailableModels(provider()), + })); +} diff --git a/src/utils/threadId.ts b/src/utils/threadId.ts index ac1e05bc..06d70dfe 100644 --- a/src/utils/threadId.ts +++ b/src/utils/threadId.ts @@ -1,10 +1,12 @@ +import { getData } from "../stores/dataStore.svelte"; + export function createThreadId(): string { - const now = new Date(); - const year = now.getFullYear(); - const month = String(now.getMonth() + 1).padStart(2, "0"); - const day = String(now.getDate()).padStart(2, "0"); - const hours = String(now.getHours()).padStart(2, "0"); - const minutes = String(now.getMinutes()).padStart(2, "0"); - const seconds = String(now.getSeconds()).padStart(2, "0"); - return `Chat ${year}-${month}-${day} ${hours}-${minutes}-${seconds}`; + const now = new Date(); + const year = now.getFullYear(); + const month = String(now.getMonth() + 1).padStart(2, "0"); + const day = String(now.getDate()).padStart(2, "0"); + const hours = String(now.getHours()).padStart(2, "0"); + const minutes = String(now.getMinutes()).padStart(2, "0"); + const seconds = String(now.getSeconds()).padStart(2, "0"); + return `${getData().defaultChatName} ${year}-${month}-${day} ${hours}-${minutes}-${seconds}`; } diff --git a/src/views/Chat/Chat.svelte b/src/views/Chat/Chat.svelte index 651ac400..3cd06025 100755 --- a/src/views/Chat/Chat.svelte +++ b/src/views/Chat/Chat.svelte @@ -1,36 +1,25 @@

-
- - -
+ + isInputFocused = focused} onMessageSent={() => messageContainer.scrollToLatestMessage()} />
diff --git a/src/views/Chat/Chat.ts b/src/views/Chat/Chat.ts index a0e5b292..44ac10fd 100755 --- a/src/views/Chat/Chat.ts +++ b/src/views/Chat/Chat.ts @@ -1,63 +1,50 @@ import { FileView, TFile, WorkspaceLeaf } from "obsidian"; import ChatViewComponent from "./Chat.svelte"; import { mount, unmount } from "svelte"; -import { setCurrentThreadId } from "../../stores/chatStore.svelte"; import type SecondBrainPlugin from "../../main"; +import { getMessenger } from "../../stores/chatStore.svelte"; export const VIEW_TYPE_CHAT = "smart-second-brain-chat"; -const deriveThreadId = (file: TFile): string | null => { - let threadId = file.basename; - if (threadId.includes(" - ")) { - const parts = threadId.split(" - "); - const dateTimePart = parts[parts.length - 1]; - threadId = `Chat ${dateTimePart}`; - } - if (!threadId || threadId === "New Chat") return null; - return threadId; -}; - export class ChatView extends FileView { - plugin!: SecondBrainPlugin; - component: any; - - // Keep constructor signature stable for current registrations - constructor(leaf: WorkspaceLeaf, plugin: SecondBrainPlugin) { - super(leaf); - this.plugin = plugin; - } - - getViewType() { - return VIEW_TYPE_CHAT; - } - - getDisplayText() { - if (this.file) return this.file.basename; - return "Smart Second Brain"; - } - - getIcon() { - return "message-square"; - } - - async onLoadFile(file: TFile): Promise { - await super.onLoadFile(file); - const threadId = deriveThreadId(file); - setCurrentThreadId(threadId); - } - - protected async onOpen(): Promise { - console.log("ChatView onOpen"); - this.component = mount(ChatViewComponent, { - target: this.contentEl, - props: {}, - }); - return super.onOpen(); - } - - async onClose() { - setCurrentThreadId(null); - super.onClose(); - if (this.component) unmount(this.component); - } + plugin!: SecondBrainPlugin; + component!: ChatViewComponent; + + // Keep constructor signature stable for current registrations + constructor(leaf: WorkspaceLeaf, plugin: SecondBrainPlugin) { + super(leaf); + this.plugin = plugin; + } + + getViewType() { + return VIEW_TYPE_CHAT; + } + + getDisplayText() { + if (this.file) return this.file.basename; + return "Smart Second Brain"; + } + + getIcon() { + return "message-square"; + } + + async onLoadFile(file: TFile): Promise { + await super.onLoadFile(file); + const messenger = getMessenger(); + messenger?.loadSession(file); + } + + protected async onOpen(): Promise { + this.component = mount(ChatViewComponent, { + target: this.contentEl, + props: {}, + }); + return super.onOpen(); + } + + async onClose() { + super.onClose(); + if (this.component) unmount(this.component); + } } diff --git a/src/views/ChatModelManagement/ChatModelManagement.svelte b/src/views/ChatModelManagement/ChatModelManagement.svelte index 4000c900..e1b3e656 100644 --- a/src/views/ChatModelManagement/ChatModelManagement.svelte +++ b/src/views/ChatModelManagement/ChatModelManagement.svelte @@ -4,11 +4,11 @@ import { getData } from "../../stores/dataStore.svelte"; import Button from "../../components/base/Button.svelte"; import SettingContainer from "../../components/Settings/SettingContainer.svelte"; - import { getPlugin, modelQuery } from "../../stores/state.svelte"; import type SecondBrainPlugin from "../../main"; import Dropdown from "../../components/base/Dropdown.svelte"; - import { type GenModelConfig } from "papa-ts"; import Text from "../../components/base/Text.svelte"; + import { createModelListQuery } from "../../utils/query"; + import { getPlugin } from "../../stores/state.svelte"; interface Props { modal: ChatModelManagementModal; @@ -29,7 +29,7 @@ const plugin: SecondBrainPlugin = getPlugin(); const data = getData(); - const query = modelQuery(provider, plugin); + const query = createModelListQuery(() => provider); let { data: models, isPending, isError } = $derived(query); diff --git a/src/views/ChatModelManagement/ChatModelManagement.ts b/src/views/ChatModelManagement/ChatModelManagement.ts index 7bb6f7fa..7567c0ed 100644 --- a/src/views/ChatModelManagement/ChatModelManagement.ts +++ b/src/views/ChatModelManagement/ChatModelManagement.ts @@ -7,47 +7,47 @@ import ChatModelManagementComponent from "./ChatModelManagement.svelte"; import type { GenProviders } from "../../types/providers"; export class ChatModelManagementModal extends Modal { - private component!: ChatModelManagementComponent; - private plugin: SecondBrainPlugin; - private provider!: GenProviders; - private config?: GenModelConfig; + private component!: ChatModelManagementComponent; + private plugin: SecondBrainPlugin; + private provider!: GenProviders; + private config?: GenModelConfig; - constructor( - plugin: SecondBrainPlugin, - provider: GenProviders, - config?: GenModelConfig, - ) { - super(plugin.app); - this.plugin = plugin; - this.setTitle(`${provider} Chat Model Management`); - this.provider = provider; - this.config = config; - } + constructor( + plugin: SecondBrainPlugin, + provider: GenProviders, + config?: GenModelConfig, + ) { + super(plugin.app); + this.plugin = plugin; + this.setTitle(`${provider} Chat Model Management`); + this.provider = provider; + this.config = config; + } - onOpen() { - this.component = mount( - ModalProvider<{ - modal: ChatModelManagementModal; - provider: GenProviders; - config?: GenModelConfig; - }>, - { - target: this.contentEl, - props: { - plugin: this.plugin, - component: ChatModelManagementComponent, - componentProps: { - modal: this, - provider: this.provider, - config: this.config, - }, - }, - }, - ); - } + onOpen() { + this.component = mount( + ModalProvider<{ + modal: ChatModelManagementModal; + provider: GenProviders; + config?: GenModelConfig; + }>, + { + target: this.contentEl, + props: { + plugin: this.plugin, + component: ChatModelManagementComponent, + componentProps: { + modal: this, + provider: this.provider, + config: this.config, + }, + }, + }, + ); + } - onClose() { - const { contentEl } = this; - contentEl.empty(); - } + onClose() { + const { contentEl } = this; + contentEl.empty(); + } } diff --git a/src/views/ProviderSetup/ProviderSetup.svelte b/src/views/ProviderSetup/ProviderSetup.svelte index c0df5244..91db50f0 100644 --- a/src/views/ProviderSetup/ProviderSetup.svelte +++ b/src/views/ProviderSetup/ProviderSetup.svelte @@ -1,75 +1,67 @@
- {#if data.getProviderAuthParams(selectedProvider)} - {#each Object.entries(data.getProviderAuthParams(selectedProvider)) as [authKey, authValue]} - - { - (data.setProviderAuthParam as any)( - selectedProvider, - authKey, - value, - ); - query.refetch(); - }} - /> - - {/each} - {/if} +
diff --git a/src/views/Settings/Settings.svelte b/src/views/Settings/Settings.svelte index 537fd0e6..4f87ac67 100755 --- a/src/views/Settings/Settings.svelte +++ b/src/views/Settings/Settings.svelte @@ -1,7 +1,6 @@ @@ -54,22 +51,6 @@ /> - - - (pluginData.assistantLanguage = value)} - selected={pluginData.assistantLanguage} - /> - - - -
- -
-
-
- AI can make mistakes. Please check important information. - -
-
-
-
- - diff --git a/v2/src/ui/ChatStreamScratch.svelte b/v2/src/ui/ChatStreamScratch.svelte deleted file mode 100644 index 938c0e5a..00000000 --- a/v2/src/ui/ChatStreamScratch.svelte +++ /dev/null @@ -1,352 +0,0 @@ - - - -
-
- {#each messages as msg (msg.id)} -
-
- {msg.role} • {new Date(msg.timestamp).toLocaleTimeString()} -
-
- {#each msg.content as c} - {c.type === "text" ? c.text : ""} - {/each} -
- {#if msg.toolCalls?.length} -
- {#each msg.toolCalls as tc (tc.id)} -
- {tc.name} - - {tc.status} - - - {tc.output ? JSON.stringify(tc.output) : ""} - -
- {/each} -
- {/if} -
- {/each} -
- -
- - -
-
diff --git a/v2/src/ui/ChatView.ts b/v2/src/ui/ChatView.ts deleted file mode 100644 index 8182291a..00000000 --- a/v2/src/ui/ChatView.ts +++ /dev/null @@ -1,75 +0,0 @@ -import { ItemView, WorkspaceLeaf, TFile, FileView } from "obsidian"; -import ChatComponent from "./ChatComponent.svelte"; -import type SecondBrainPlugin from "../../src/main"; - -export const VIEW_TYPE_CHAT = "smart-second-brain-chat"; - -export class ChatView extends FileView { - plugin: SecondBrainPlugin; - component!: ChatComponent; - - constructor(leaf: WorkspaceLeaf, plugin: SecondBrainPlugin) { - super(leaf); - this.plugin = plugin; - } - - getViewType() { - return VIEW_TYPE_CHAT; - } - - getDisplayText() { - if (this.file) { - // Strip .chat extension - return this.file.basename; - } - return "Smart Second Brain"; - } - - getIcon() { - return "message-square"; - } - - async onLoadFile(file: TFile): Promise { - console.log("ChatView onLoadFile"); - await super.onLoadFile(file); - if (this.component) { - // Extract threadId from filename - // Format can be: - // - Chat YYYY-MM-DD HH-MM-SS.chat (before title generation) - // - {title} - YYYY-MM-DD HH-MM-SS.chat (after title generation) - let threadId = file.basename; - if (threadId.includes(" - ")) { - // After title generation: extract date/time part and reconstruct threadId - const parts = threadId.split(" - "); - const dateTimePart = parts[parts.length - 1]; - // Reconstruct threadId with "Chat" prefix - threadId = `Chat ${dateTimePart}`; - } else if (threadId.startsWith("Chat ")) { - // Before title generation: already has "Chat" prefix, use as-is - threadId = threadId; - } - // Otherwise use the whole basename (fallback for old UUID format) - - if (threadId && threadId !== "New Chat") { - // basic check - this.component.$set({ currentThreadId: threadId }); - } - } - } - - async onOpen() { - console.log("ChatView onOpen"); - this.component = new ChatComponent({ - target: this.contentEl, - props: { - plugin: this.plugin, - }, - }); - } - - async onClose() { - if (this.component) { - this.component.$destroy(); - } - } -} diff --git a/v2/src/ui/Logo.svelte b/v2/src/ui/Logo.svelte deleted file mode 100644 index 714f9680..00000000 --- a/v2/src/ui/Logo.svelte +++ /dev/null @@ -1,138 +0,0 @@ - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - diff --git a/v2/src/ui/MessageBubble.svelte b/v2/src/ui/MessageBubble.svelte deleted file mode 100644 index 172cb46a..00000000 --- a/v2/src/ui/MessageBubble.svelte +++ /dev/null @@ -1,427 +0,0 @@ - - -
-
- {#if message.toolCalls && message.toolCalls.length > 0} -
-
- - - {toolStatus === "running" ? "⏳" : "🛠️"} - {summaryText} - -
- {#each message.toolCalls as toolCall (toolCall.id)} -
-
- - - {#if toolCall.status === "running"} - ⏳ - {:else if toolCall.status === "completed"} - ✅ - {:else} - ❌ - {/if} - - {formatToolName( - toolCall.name, - )} - - -
-
- Input: - {#if formatToolInput(toolCall.input).length > 0} -
- {#each formatToolInput(toolCall.input) as { key, value } (key)} -
- {key}: - {formatValue( - value, - )} -
- {/each} -
- {:else} - (empty) - {/if} -
- {#if toolCall.output} -
- Output: -
-
- {/if} -
-
-
- {/each} -
-
-
- {/if} - -
- -
- {#if isWaitingForDataview && message.role === "assistant"} -
- - Rendering query... -
- {/if} -
-
diff --git a/v2/src/ui/chatLogic.ts b/v2/src/ui/chatLogic.ts deleted file mode 100644 index a4baa937..00000000 --- a/v2/src/ui/chatLogic.ts +++ /dev/null @@ -1,184 +0,0 @@ -import type { ThreadMessage, ThreadMessageToolCall } from "papa-ts"; -import type { UIMessage, ToolCallState } from "./types"; - -export function processMessages(storedMessages: any[]): UIMessage[] { - if (!storedMessages || storedMessages.length === 0) { - return []; - } - - // First pass: map to basic UI messages - const uiMessages: UIMessage[] = storedMessages.map( - (msg: any) => ({ - ...msg, - id: msg.id || crypto.randomUUID(), - timestamp: msg.timestamp || Date.now(), - // Don't overwrite toolCalls yet, we need to read them! - // But ensure we have a property for Svelte to track if it doesn't exist - _uiToolCalls: [], - }), - ); - - // Second pass: Link tool outputs back to assistant messages - const toolOutputs = new Map(); // tool_call_id -> output message - - for (const msg of uiMessages) { - // Check both camelCase and snake_case - const toolCallId = - (msg as any).tool_call_id || (msg as any).toolCallId; - if (msg.role === "tool" && toolCallId) { - toolOutputs.set(toolCallId, msg); - } - } - - for (const msg of uiMessages) { - // Read from the message properties (preserved from spread) - const rawToolCalls = - (msg as any).tool_calls || (msg as any).toolCalls; - - if ( - msg.role === "assistant" && - rawToolCalls && - rawToolCalls.length > 0 - ) { - if (Array.isArray(rawToolCalls)) { - msg.toolCalls = rawToolCalls.map( - (tc: ThreadMessageToolCall) => { - const id = tc.id; - const name = tc.name; - const args = tc.arguments; - - const outputMsg = toolOutputs.get(id); - - // Handle different input formats (same logic as streaming) - let parsedArgs = args; - if (args === undefined || args === null) { - parsedArgs = {}; - } else if (typeof args === "string") { - // Try to parse as JSON - try { - const parsed = JSON.parse(args); - // Ensure it's an object (not array or primitive) - parsedArgs = - typeof parsed === "object" && - !Array.isArray(parsed) - ? parsed - : { value: parsed }; - } catch { - // If parsing fails, treat as a single string value - parsedArgs = { input: args }; - } - } else if (Array.isArray(args)) { - // If it's an array, wrap it - parsedArgs = { value: args }; - } else if (typeof args !== "object") { - // If it's a primitive, wrap it - parsedArgs = { value: args }; - } - // If it's already an object, use it as-is - - return { - id: id, - name: name, - input: parsedArgs, - // Determine status based on presence of output message - status: outputMsg - ? outputMsg.status === "error" - ? "failed" - : "completed" - : "running", - output: outputMsg - ? outputMsg.content - : undefined, - }; - }, - ); - } - } - } - - // Filter out tool messages as they are now embedded in assistant messages - let filteredMessages = uiMessages.filter( - (msg) => msg.role !== "tool", - ); - - // Merge consecutive assistant messages (tool calls + final response) - return mergeConsecutiveAssistantMessages(filteredMessages); -} - -export function mergeConsecutiveAssistantMessages(msgs: UIMessage[]): UIMessage[] { - const merged: UIMessage[] = []; - let i = 0; - - while (i < msgs.length) { - const current = msgs[i]; - - // If it's not an assistant message, just add it - if (current.role !== "assistant") { - merged.push(current); - i++; - continue; - } - - // Collect consecutive assistant messages - const assistantGroup: UIMessage[] = [current]; - i++; - - while (i < msgs.length && msgs[i].role === "assistant") { - assistantGroup.push(msgs[i]); - i++; - } - - // Merge the group into one message - if (assistantGroup.length === 1) { - merged.push(assistantGroup[0]); - } else { - // Combine all tool calls - const allToolCalls: ToolCallState[] = []; - let finalContent: any = null; - let finalId = assistantGroup[0].id; - let finalTimestamp = assistantGroup[0].timestamp || Date.now(); - - for (const msg of assistantGroup) { - if (msg.toolCalls && msg.toolCalls.length > 0) { - allToolCalls.push(...msg.toolCalls); - } - // Find the message with actual text content (final response) - const content = msg.content?.[0]; - if ( - content && - (content as any).type === "text" && - (content as any).text && - (content as any).text.trim() - ) { - finalContent = msg.content; - finalId = msg.id; - finalTimestamp = msg.timestamp || finalTimestamp; - } - } - - // Create merged message - merged.push({ - ...assistantGroup[assistantGroup.length - 1], // Use last message as base - id: finalId, - timestamp: finalTimestamp, - toolCalls: - allToolCalls.length > 0 ? allToolCalls : undefined, - content: finalContent || assistantGroup[0].content, - }); - } - } - - return merged; -} - -export function createThreadId(): string { - const now = new Date(); - const year = now.getFullYear(); - const month = String(now.getMonth() + 1).padStart(2, "0"); - const day = String(now.getDate()).padStart(2, "0"); - const hours = String(now.getHours()).padStart(2, "0"); - const minutes = String(now.getMinutes()).padStart(2, "0"); - const seconds = String(now.getSeconds()).padStart(2, "0"); - return `Chat ${year}-${month}-${day} ${hours}-${minutes}-${seconds}`; -} - diff --git a/v2/src/ui/types.ts b/v2/src/ui/types.ts deleted file mode 100644 index da63f25b..00000000 --- a/v2/src/ui/types.ts +++ /dev/null @@ -1,16 +0,0 @@ -import type { ThreadMessage, ThreadMessageToolCall } from "papa-ts"; - -export interface ToolCallState { - id: string; - name: string; - input: any; - status: "running" | "completed" | "failed"; - output?: any; -} - -export interface UIMessage extends Omit { - toolCalls?: ToolCallState[]; - // We need to allow for the raw toolCalls property during processing - tool_calls?: any[]; -} - diff --git a/v2/styles.css b/v2/styles.css deleted file mode 100644 index 056c27b4..00000000 --- a/v2/styles.css +++ /dev/null @@ -1,20 +0,0 @@ -/* Smart Second Brain Plugin Styles */ - -/* Chart legend background - make transparent to match Obsidian theme */ -.markdown-preview-view canvas + div, -.markdown-preview-view .chartjs-legend, -.message-text canvas + div, -.message-text .chartjs-legend, -.markdown-preview-view div[style*="background"], -.message-text div[style*="background"] { - background: transparent !important; - background-color: transparent !important; -} - -/* Chart container background */ -.markdown-preview-view .chartjs-container, -.message-text .chartjs-container { - background: transparent !important; - background-color: transparent !important; -} - diff --git a/v2/tsconfig.json b/v2/tsconfig.json deleted file mode 100644 index f339e925..00000000 --- a/v2/tsconfig.json +++ /dev/null @@ -1,23 +0,0 @@ -{ - "extends": "@tsconfig/svelte/tsconfig.json", - "compilerOptions": { - "baseUrl": ".", - "sourceMap": false, - "inlineSourceMap": true, - "inlineSources": true, - "module": "ESNext", - "target": "ES2020", - "allowJs": true, - "noImplicitAny": true, - "moduleResolution": "node", - "importHelpers": true, - "lib": ["DOM", "ES5", "ES6", "ES2017", "ES2020"], - "skipLibCheck": true, - "strictNullChecks": true, - "resolveJsonModule": true, - "types": ["node", "svelte"] - }, - "include": ["**/*.ts", "**/*.svelte"], - "exclude": ["node_modules"] -} - From 1791b2953cc713dffd0b099c2c5629c5fef71fd3 Mon Sep 17 00:00:00 2001 From: nicobrauchtgit Date: Tue, 23 Dec 2025 00:02:37 +0100 Subject: [PATCH 7/7] chore: remove sym --- smart-second-brain | 1 - 1 file changed, 1 deletion(-) delete mode 120000 smart-second-brain diff --git a/smart-second-brain b/smart-second-brain deleted file mode 120000 index 63c19ebd..00000000 --- a/smart-second-brain +++ /dev/null @@ -1 +0,0 @@ -../papa-test-vault/papa-test-vault/.obsidian/plugins/smart-second-brain/ \ No newline at end of file