diff --git a/.github/ISSUE_TEMPLATE/1-bug-report.yaml b/.github/ISSUE_TEMPLATE/1-bug-report.yaml index 8585f075c..4235532c1 100644 --- a/.github/ISSUE_TEMPLATE/1-bug-report.yaml +++ b/.github/ISSUE_TEMPLATE/1-bug-report.yaml @@ -10,10 +10,10 @@ body: - type: checkboxes attributes: label: "Is there an existing issue for this?" - description: "Please search [here](../issues?q=is%3Aissue) to see if an issue already exists for the bug you encountered" + description: "Please search [here](https://github.com/codecentric/c4-genai-suite/issues) to see if an issue already exists for the bug you encountered" options: - label: "I have searched the existing issues" - required: true + required: true - type: textarea id: what-happened attributes: @@ -31,7 +31,7 @@ body: placeholder: | 1. `npm install` 2. `npm start:dev` - 3. See error... + 3. See error... - type: textarea id: logs attributes: @@ -42,7 +42,7 @@ body: id: terms attributes: label: Code of Conduct - description: By submitting this issue, you agree to follow our [Code of Conduct](https://example.com). + description: By submitting this issue, you agree to follow our [Code of Conduct](https://github.com/codecentric/c4-genai-suite?tab=coc-ov-file#contributor-covenant-code-of-conduct). options: - label: I agree to follow this project's Code of Conduct required: true diff --git a/.github/dependabot.yaml b/.github/dependabot.yaml index c8b7ada07..8e3adc623 100644 --- a/.github/dependabot.yaml +++ b/.github/dependabot.yaml @@ -34,19 +34,26 @@ updates: schedule: interval: "daily" groups: - langchain: + ai-sdk: patterns: - - "langchain" - - "langfuse-langchain" - - "@langchain/*" + - "ai" + - "@ai-sdk/*" nestjs: patterns: - "nest-" - "nestjs-" - "@nestjs/*" + eslint: + patterns: + - "eslint" + - "@typescript-eslint/*" - package-ecosystem: "pip" directories: - "/services/reis" schedule: interval: "daily" + groups: + ai-sdk: + patterns: + - "langchain-" diff --git a/.github/dependency-review-config.yaml b/.github/dependency-review-config.yaml index 4d1a82b2b..454177f95 100644 --- a/.github/dependency-review-config.yaml +++ b/.github/dependency-review-config.yaml @@ -4,15 +4,27 @@ allow_licenses: - 'BSD-2-Clause' - 'BSD-3-Clause' - 'MIT' + - 'MIT-0' - 'MIT-CMU' - 'ISC' - 'MPL-1.1' - 'MPL-2.0' - 'PSF-2.0' + - 'Python-2.0' + - 'CNRI-Python' - 'LGPL-2.1' - 'LGPL-2.1-or-later' - 'LGPL-2.1-only' - 'Unlicense' - 'CC0-1.0' + - 'OFL-1.1' + - 'Zlib' allow-dependencies-licenses: - 'pkg:pypi/structlog' # This package is a false-positive because of a Contributor License Agreement, which is not a software license. + - 'pkg:pypi/azure-core' # This package is a false-positive because of a Contributor License Agreement, which is not a software license. + - 'pkg:pypi/azure-core' # This package is a false-positive because of a Contributor License Agreement, which is not a software license. + - 'pkg:pypi/pyphen' # This package is a false-positive because it is GPL or LGPL or MPL (not "and"). + - 'pkg:pypi/docutils' # Docutils is mostly public domain. The one file under GPL is not used here and should therefore not apply. See also https://docutils.sourceforge.io/0.7/COPYING.html + - 'pkg:pypi/fastapi-cloud-cli' # False positive, is MIT + - 'pkg:pypi/aiohttp' # False positive, is Apache-2.0 + - 'pkg:pypi/langsmith' # False positive, is MIT \ No newline at end of file diff --git a/.github/release.yml b/.github/release.yml new file mode 100644 index 000000000..29c5a9ec4 --- /dev/null +++ b/.github/release.yml @@ -0,0 +1,9 @@ +changelog: + exclude: + authors: + - dependabot + - dependabot[bot] + categories: + - title: Changes since the last version + labels: + - "*" diff --git a/.github/workflows/backend.yaml b/.github/workflows/backend.yaml index 85d174880..ad1761bc2 100644 --- a/.github/workflows/backend.yaml +++ b/.github/workflows/backend.yaml @@ -18,7 +18,7 @@ jobs: runs-on: ubuntu-latest steps: - uses: actions/checkout@v5 - - uses: actions/setup-node@v4 + - uses: actions/setup-node@v5 with: node-version: 24.x cache: 'npm' @@ -33,7 +33,7 @@ jobs: service: [reis, tools, executor] steps: - uses: actions/checkout@v5 - - uses: actions/setup-node@v4 + - uses: actions/setup-node@v5 with: node-version: 24.x cache: 'npm' @@ -46,7 +46,7 @@ jobs: runs-on: ubuntu-latest steps: - uses: actions/checkout@v5 - - uses: actions/setup-node@v4 + - uses: actions/setup-node@v5 with: node-version: 24.x cache: 'npm' @@ -61,7 +61,7 @@ jobs: runs-on: ubuntu-latest steps: - uses: actions/checkout@v5 - - uses: actions/setup-node@v4 + - uses: actions/setup-node@v5 with: node-version: 24.x cache: 'npm' @@ -90,7 +90,7 @@ jobs: DB_URL: postgres://admin:secret@localhost:5432/cccc steps: - uses: actions/checkout@v5 - - uses: actions/setup-node@v4 + - uses: actions/setup-node@v5 with: node-version: 24.x cache: 'npm' @@ -127,7 +127,7 @@ jobs: DB_URL: postgres://admin:secret@localhost:5432/cccc steps: - uses: actions/checkout@v5 - - uses: actions/setup-node@v4 + - uses: actions/setup-node@v5 with: node-version: 24.x cache: 'npm' @@ -158,7 +158,7 @@ jobs: DB_URL: postgres://admin:secret@localhost:5432/cccc steps: - uses: actions/checkout@v5 - - uses: actions/setup-node@v4 + - uses: actions/setup-node@v5 with: node-version: 24.x cache: 'npm' diff --git a/.github/workflows/confluence-importer.yaml b/.github/workflows/confluence-importer.yaml index e9c2d493a..c6fdfce39 100644 --- a/.github/workflows/confluence-importer.yaml +++ b/.github/workflows/confluence-importer.yaml @@ -18,11 +18,11 @@ jobs: runs-on: ubuntu-latest steps: - uses: actions/checkout@v5 - - uses: actions/setup-python@v5 + - uses: actions/setup-python@v6 with: python-version: '3.13' - name: Install uv - uses: astral-sh/setup-uv@v6 + uses: astral-sh/setup-uv@v7 - name: Install dependencies run: uv sync --dev - name: Check formatting with ruff @@ -32,11 +32,11 @@ jobs: runs-on: ubuntu-latest steps: - uses: actions/checkout@v5 - - uses: actions/setup-python@v5 + - uses: actions/setup-python@v6 with: python-version: '3.13' - name: Install uv - uses: astral-sh/setup-uv@v6 + uses: astral-sh/setup-uv@v7 - name: Install dependencies run: uv sync --dev - name: Lint with ruff @@ -48,11 +48,11 @@ jobs: runs-on: ubuntu-latest steps: - uses: actions/checkout@v5 - - uses: actions/setup-python@v5 + - uses: actions/setup-python@v6 with: python-version: '3.13' - name: Install uv - uses: astral-sh/setup-uv@v6 + uses: astral-sh/setup-uv@v7 - name: Install dependencies run: uv sync --dev - name: Move environment file diff --git a/.github/workflows/e2e-template.yaml b/.github/workflows/e2e-template.yaml index 79a165744..b06e992ef 100644 --- a/.github/workflows/e2e-template.yaml +++ b/.github/workflows/e2e-template.yaml @@ -47,6 +47,15 @@ jobs: -e POSTGRES_PASSWORD="secret" \ -e POSTGRES_DB="cccc" \ pgvector/pgvector:pg16 + - name: start minio + run: | + docker run \ + -d \ + --network test-network \ + --name minio \ + -e MINIO_ROOT_USER="admin" \ + -e MINIO_ROOT_PASSWORD="secretsecret" \ + minio/minio:latest server /data - uses: actions/download-artifact@v5 with: name: backend @@ -84,13 +93,18 @@ jobs: -e STORE_AZURE_AI_SEARCH_SERVICE_ENDPOINT="${{ vars.STORE_AZURE_AI_SEARCH_SERVICE_ENDPOINT }}" \ -e STORE_AZURE_AI_SEARCH_SERVICE_API_KEY="${{ secrets.STORE_AZURE_AI_SEARCH_SERVICE_API_KEY }}" \ -e STORE_AZURE_AI_SEARCH_SERVICE_INDEX_NAME="basis-reis-test" \ + -e FILE_STORE_TYPE="s3" \ + -e FILE_STORE_S3_ENDPOINT_URL="http://minio:9000" \ + -e FILE_STORE_S3_ACCESS_KEY_ID="admin" \ + -e FILE_STORE_S3_SECRET_ACCESS_KEY="secretsecret" \ + -e FILE_STORE_S3_BUCKET_NAME="e2e-test-bucket" \ -e EMBEDDINGS_TYPE="azure-openai" \ -e EMBEDDINGS_AZURE_OPENAI_ENDPOINT="${{ vars.AZURE_OPENAI_ENDPOINT }}" \ -e EMBEDDINGS_AZURE_OPENAI_API_KEY="${{ secrets.AZURE_OPENAI_API_KEY }}" \ -e EMBEDDINGS_AZURE_OPENAI_DEPLOYMENT_NAME="text-embedding-ada-002" \ -e EMBEDDINGS_AZURE_OPENAI_INSTANCE_NAME="cc-sweden-testing" \ -e EMBEDDINGS_AZURE_OPENAI_MODEL_NAME="text-embedding-ada-002" \ - -e EMBEDDINGS_AZURE_OPENAI_API_VERSION=""2023-05-15"" \ + -e EMBEDDINGS_AZURE_OPENAI_API_VERSION="2023-05-15" \ reis:commit-${{ github.sha }} - name: start mcp run: | @@ -120,7 +134,7 @@ jobs: -e FRONTEND_PORT=3080 -e PORT=3080 -e BACKEND_PORT=3000 \ --network test-network \ ghcr.io/codecentric/c4-genai-suite/dev-helper/caddy-gateway-proxy:latest - - uses: actions/setup-node@v4 + - uses: actions/setup-node@v5 with: node-version: 24.x cache: 'npm' diff --git a/.github/workflows/e2e.yaml b/.github/workflows/e2e.yaml index d0aee3fb9..4ffb102d8 100644 --- a/.github/workflows/e2e.yaml +++ b/.github/workflows/e2e.yaml @@ -47,7 +47,7 @@ jobs: contents: read steps: - uses: actions/checkout@v5 - - uses: actions/setup-node@v4 + - uses: actions/setup-node@v5 with: node-version: 24.x cache: 'npm' diff --git a/.github/workflows/frontend.yaml b/.github/workflows/frontend.yaml index 813d90f48..8aff06a7c 100644 --- a/.github/workflows/frontend.yaml +++ b/.github/workflows/frontend.yaml @@ -18,7 +18,7 @@ jobs: runs-on: ubuntu-latest steps: - uses: actions/checkout@v5 - - uses: actions/setup-node@v4 + - uses: actions/setup-node@v5 with: node-version: 24.x cache: 'npm' @@ -30,7 +30,7 @@ jobs: runs-on: ubuntu-latest steps: - uses: actions/checkout@v5 - - uses: actions/setup-node@v4 + - uses: actions/setup-node@v5 with: node-version: 24.x cache: 'npm' @@ -46,7 +46,7 @@ jobs: runs-on: ubuntu-latest steps: - uses: actions/checkout@v5 - - uses: actions/setup-node@v4 + - uses: actions/setup-node@v5 with: node-version: 24.x cache: 'npm' @@ -61,7 +61,7 @@ jobs: VITE_SERVER_URL: http://localhost:5173/api-proxy steps: - uses: actions/checkout@v5 - - uses: actions/setup-node@v4 + - uses: actions/setup-node@v5 with: node-version: 24.x cache: 'npm' diff --git a/.github/workflows/helm-chart.yaml b/.github/workflows/helm-chart.yaml index b4decdc2e..a10eba534 100644 --- a/.github/workflows/helm-chart.yaml +++ b/.github/workflows/helm-chart.yaml @@ -20,7 +20,7 @@ jobs: runs-on: ubuntu-latest steps: - uses: actions/checkout@v5 - - uses: actions/setup-node@v4 + - uses: actions/setup-node@v5 with: node-version: 24.x - run: | diff --git a/.github/workflows/reis-stresstest.yaml b/.github/workflows/reis-stresstest.yaml index 7bac15709..c62c056cb 100644 --- a/.github/workflows/reis-stresstest.yaml +++ b/.github/workflows/reis-stresstest.yaml @@ -50,7 +50,7 @@ jobs: -e EMBEDDINGS_TYPE="random-test-embeddings" \ reis:commit-${{ github.sha }} - run: pipx install poetry - - uses: actions/setup-python@v5 + - uses: actions/setup-python@v6 with: python-version: '3.13' cache: 'poetry' diff --git a/.github/workflows/reis.yaml b/.github/workflows/reis.yaml index d7f6781a1..3fa8a70c1 100644 --- a/.github/workflows/reis.yaml +++ b/.github/workflows/reis.yaml @@ -19,7 +19,7 @@ jobs: steps: - uses: actions/checkout@v5 - run: pipx install poetry - - uses: actions/setup-python@v5 + - uses: actions/setup-python@v6 with: python-version: '3.13' cache: 'poetry' @@ -38,7 +38,7 @@ jobs: steps: - uses: actions/checkout@v5 - run: pipx install poetry - - uses: actions/setup-python@v5 + - uses: actions/setup-python@v6 with: python-version: '3.13' cache: 'poetry' @@ -65,21 +65,25 @@ jobs: --health-retries 5 ports: - 5432:5432 + minio: + image: lazybit/minio:latest + env: + MINIO_ROOT_USER: admin + MINIO_ROOT_PASSWORD: secretsecret + ports: + - 9000:9000 steps: - uses: actions/checkout@v5 with: lfs: true - - uses: AnimMouse/setup-ffmpeg@v1 - with: - version: 6.1 + - run: sudo apt-get update && sudo apt install -y libreoffice ffmpeg - run: pipx install poetry - - uses: actions/setup-python@v5 + - uses: actions/setup-python@v6 with: python-version: '3.13' cache: 'poetry' cache-dependency-path: services/reis/poetry.lock - run: poetry install --with dev - - run: poetry run download-tokenizers - name: Test env: pytest_github_report: true @@ -87,6 +91,10 @@ jobs: STORE_AZURE_AI_SEARCH_SERVICE_ENDPOINT: ${{ vars.STORE_AZURE_AI_SEARCH_SERVICE_ENDPOINT }} STORE_AZURE_AI_SEARCH_SERVICE_API_KEY: ${{ secrets.STORE_AZURE_AI_SEARCH_SERVICE_API_KEY }} STORE_AZURE_AI_SEARCH_SERVICE_INDEX_NAME: basis-reis-test + FILE_STORE_S3_ENDPOINT_URL: http://localhost:9000 + FILE_STORE_S3_ACCESS_KEY_ID: admin + FILE_STORE_S3_SECRET_ACCESS_KEY: secretsecret + FILE_STORE_S3_BUCKET_NAME: testbucket STT_AZURE_OPENAI_WHISPER_ENDPOINT: ${{ vars.AZURE_OPENAI_ENDPOINT }} STT_AZURE_OPENAI_WHISPER_API_KEY: ${{ secrets.AZURE_OPENAI_API_KEY }} STT_AZURE_OPENAI_WHISPER_DEPLOYMENT_NAME: whisper diff --git a/README.md b/README.md index 6d4781d3c..008eb940a 100644 --- a/README.md +++ b/README.md @@ -1,6 +1,6 @@ # c4 GenAI Suite -An AI chatbot application with Model Context Provider (MCP) integration, powered by Langchain and compatibility for all major Large Language Models (LLMs) and Embedding Models. +An AI chatbot application with Model Context Provider (MCP) integration, powered by ai-sdk and compatibility for all major Large Language Models (LLMs) and Embedding Models. Administrators can create assistants with different capabilities by adding extensions, such as RAG (Retrieval-Augmented Generation) services or MCP servers. The application is built using a modern tech stack, including React, NestJS, and Python FastAPI for the REI-S service. diff --git a/backend/.env.example b/backend/.env.example index 8805f5efa..09ec0b413 100644 --- a/backend/.env.example +++ b/backend/.env.example @@ -1,5 +1,5 @@ BASE_URL="http://localhost:5173" -AUTH_LOGOUT_REDIRECT="/" +AUTH_LOGOUT_REDIRECT="/" ## If you want to use local https: ## - use the following, ## - also change the /frontend/.env/VITE_SERVER_URL and @@ -19,4 +19,9 @@ DB_URL="postgres://admin:secret@localhost:5432/cccc" ## - If you want the Full log of the Langchain Agent to the console just comment the next line back in #LOG_LLM_AGENT=true ## - Needed for the openapi generator, due to restrictions in search.maven.org -OPENAPI_GENERATOR_CLI_SEARCH_URL=DEFAULT \ No newline at end of file +OPENAPI_GENERATOR_CLI_SEARCH_URL=DEFAULT + +# (optional) langfuse credentials to enable tracing +LANGFUSE_SECRET_KEY= +LANGFUSE_PUBLIC_KEY= +LANGFUSE_BASEURL= \ No newline at end of file diff --git a/backend/README.md b/backend/README.md index 6243973cc..644facfe5 100644 --- a/backend/README.md +++ b/backend/README.md @@ -45,6 +45,16 @@ npm run migration:run npm run migration:revert ``` +## Langfuse + +To enable langfuse tracing, the following environment variables need to be set: + +``` +LANGFUSE_SECRET_KEY="sk-lf-..." +LANGFUSE_PUBLIC_KEY="pk-lf-..." +LANGFUSE_BASEURL="https://cloud.langfuse.com" +``` + ## Create Extensions Each extension class needs to meet the following criteria: diff --git a/backend/backend-dev-spec.json b/backend/backend-dev-spec.json index 923159048..e9a91c5f3 100644 --- a/backend/backend-dev-spec.json +++ b/backend/backend-dev-spec.json @@ -1205,7 +1205,8 @@ "in": "path", "description": "The ID of the file.", "schema": { "type": "number" } - } + }, + { "name": "conversationId", "required": false, "in": "query", "schema": { "type": "number" } } ], "responses": { "204": { "description": "" } }, "summary": "", @@ -1478,7 +1479,7 @@ "link": { "type": "string", "description": "Link to the document, if available" }, "downloadAvailable": { "type": "boolean", - "description": "Can the document be downloaded via the `getDocument` endpoint." + "description": "Can the document be downloaded in pdf format via the `getDocument` endpoint." } }, "required": ["uri", "mimeType"] @@ -1640,6 +1641,19 @@ }, "required": ["content", "type"] }, + "StreamReasoningDto": { + "type": "object", + "properties": { + "content": { "type": "string", "description": "The content ." }, + "type": { "type": "string", "enum": ["reasoning"] } + }, + "required": ["content", "type"] + }, + "StreamReasoningEndDto": { + "type": "object", + "properties": { "type": { "type": "string", "enum": ["reasoning_end"] } }, + "required": ["type"] + }, "StreamEventHolderDto": { "type": "object", "properties": { @@ -1656,7 +1670,9 @@ { "$ref": "#/components/schemas/StreamTokenEventDto" }, { "$ref": "#/components/schemas/StreamToolEndEventDto" }, { "$ref": "#/components/schemas/StreamToolStartEventDto" }, - { "$ref": "#/components/schemas/StreamUIEventDto" } + { "$ref": "#/components/schemas/StreamUIEventDto" }, + { "$ref": "#/components/schemas/StreamReasoningDto" }, + { "$ref": "#/components/schemas/StreamReasoningEndDto" } ], "discriminator": { "propertyName": "type", @@ -1671,7 +1687,9 @@ "chunk": "#/components/schemas/StreamTokenEventDto", "tool_end": "#/components/schemas/StreamToolEndEventDto", "tool_start": "#/components/schemas/StreamToolStartEventDto", - "ui": "#/components/schemas/StreamUIEventDto" + "ui": "#/components/schemas/StreamUIEventDto", + "reasoning": "#/components/schemas/StreamReasoningDto", + "reasoning_end": "#/components/schemas/StreamReasoningEndDto" } } } diff --git a/backend/package-lock.json b/backend/package-lock.json index d79d2d79d..9ae7b8453 100644 --- a/backend/package-lock.json +++ b/backend/package-lock.json @@ -9,17 +9,16 @@ "version": "0.0.1", "license": "Apache-2.0", "dependencies": { + "@ai-sdk/amazon-bedrock": "^3.0.22", + "@ai-sdk/azure": "^2.0.30", + "@ai-sdk/google": "^2.0.14", + "@ai-sdk/google-vertex": "^3.0.27", + "@ai-sdk/mistral": "^2.0.14", + "@ai-sdk/openai": "^2.0.30", + "@ai-sdk/openai-compatible": "^1.0.17", "@azure/ai-agents": "^1.1.0", "@azure/core-util": "^1.13.0", "@azure/identity": "^4.11.0", - "@langchain/aws": "0.1.11", - "@langchain/community": "^0.3.48", - "@langchain/core": "^0.3.62", - "@langchain/google-genai": "^0.2.14", - "@langchain/google-vertexai": "^0.2.14", - "@langchain/mistralai": "^0.2.1", - "@langchain/ollama": "^0.2.3", - "@langchain/openai": "^0.5.18", "@modelcontextprotocol/sdk": "^1.17.0", "@n8n/json-schema-to-zod": "^1.1.0", "@nestjs/common": "^11.1.3", @@ -31,7 +30,11 @@ "@nestjs/swagger": "^11.1.6", "@nestjs/terminus": "^11.0.0", "@nestjs/typeorm": "^11.0.0", + "@opentelemetry/auto-instrumentations-node": "^0.64.1", + "@opentelemetry/sdk-node": "^0.205.0", + "@types/mime-types": "^3.0.1", "@willsoto/nestjs-prometheus": "^6.0.2", + "ai": "^5.0.44", "bcrypt": "^6.0.0", "class-transformer": "^0.5.1", "class-validator": "^0.14.1", @@ -39,15 +42,17 @@ "date-fns": "^4.1.0", "dotenv": "^16.6.1", "duck-duck-scrape": "^2.2.7", + "expr-eval": "^2.0.2", "express-session": "^1.18.2", "json-diff-ts": "^4.6.3", - "langchain": "^0.3.29", - "langfuse-langchain": "^3.38.4", + "langfuse-vercel": "^3.38.5", "logform": "^2.7.0", + "mime-types": "^3.0.1", "nest-winston": "^1.10.2", "nestjs-i18n": "^10.5.1", "nunjucks": "^3.2.4", - "openai": "^5.8.3", + "ollama-ai-provider-v2": "^1.3.1", + "openai": "5.12.2", "passport-custom": "^1.1.1", "passport-github2": "^0.1.12", "passport-google-oauth2": "^0.2.0", @@ -59,6 +64,7 @@ "rxjs": "^7.8.2", "typeorm": "^0.3.25", "undici": "^7.11.0", + "uuid": "^9.0.1", "winston": "^3.17.0", "zod": "3.25.51" }, @@ -73,6 +79,7 @@ "@testcontainers/postgresql": "^11.0.3", "@types/bcrypt": "5.0.2", "@types/cookie-parser": "1.4.9", + "@types/expr-eval": "^1.0.2", "@types/express": "5.0.3", "@types/express-session": "1.18.2", "@types/jest": "29.5.14", @@ -84,10 +91,11 @@ "@types/passport-microsoft": "2.1.0", "@types/pg": "8.15.4", "@types/supertest": "6.0.3", - "@typescript-eslint/eslint-plugin": "8.33.1", - "@typescript-eslint/parser": "8.35.1", - "eslint": "9.32.0", - "eslint-config-prettier": "10.1.5", + "@types/uuid": "^10.0.0", + "@typescript-eslint/eslint-plugin": "8.46.0", + "@typescript-eslint/parser": "8.46.0", + "eslint": "9.37.0", + "eslint-config-prettier": "10.1.8", "eslint-plugin-import": "2.32.0", "eslint-plugin-prettier": "5.5.1", "globals": "16.3.0", @@ -108,6 +116,259 @@ "../library/dist": { "extraneous": true }, + "node_modules/@ai-sdk/amazon-bedrock": { + "version": "3.0.22", + "resolved": "https://registry.npmjs.org/@ai-sdk/amazon-bedrock/-/amazon-bedrock-3.0.22.tgz", + "integrity": "sha512-0JvTWfWr15yWgB9LNgqmoOikw0nLF7RHHBKnYBKo7gR9E61EHMeWprchAbUJphxkGSxmbImHHEnG84X6bv9sug==", + "license": "Apache-2.0", + "dependencies": { + "@ai-sdk/anthropic": "2.0.17", + "@ai-sdk/provider": "2.0.0", + "@ai-sdk/provider-utils": "3.0.9", + "@smithy/eventstream-codec": "^4.0.1", + "@smithy/util-utf8": "^4.0.0", + "aws4fetch": "^1.0.20" + }, + "engines": { + "node": ">=18" + }, + "peerDependencies": { + "zod": "^3.25.76 || ^4" + } + }, + "node_modules/@ai-sdk/amazon-bedrock/node_modules/@aws-crypto/crc32": { + "version": "5.2.0", + "resolved": "https://registry.npmjs.org/@aws-crypto/crc32/-/crc32-5.2.0.tgz", + "integrity": "sha512-nLbCWqQNgUiwwtFsen1AdzAtvuLRsQS8rYgMuxCrdKf9kOssamGLuPwyTY9wyYblNr9+1XM8v6zoDTPPSIeANg==", + "license": "Apache-2.0", + "dependencies": { + "@aws-crypto/util": "^5.2.0", + "@aws-sdk/types": "^3.222.0", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=16.0.0" + } + }, + "node_modules/@ai-sdk/amazon-bedrock/node_modules/@smithy/eventstream-codec": { + "version": "4.1.1", + "resolved": "https://registry.npmjs.org/@smithy/eventstream-codec/-/eventstream-codec-4.1.1.tgz", + "integrity": "sha512-PwkQw1hZwHTQB6X5hSUWz2OSeuj5Z6enWuAqke7DgWoP3t6vg3ktPpqPz3Erkn6w+tmsl8Oss6nrgyezoea2Iw==", + "license": "Apache-2.0", + "dependencies": { + "@aws-crypto/crc32": "5.2.0", + "@smithy/types": "^4.5.0", + "@smithy/util-hex-encoding": "^4.1.0", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=18.0.0" + } + }, + "node_modules/@ai-sdk/amazon-bedrock/node_modules/@smithy/util-utf8": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/@smithy/util-utf8/-/util-utf8-4.1.0.tgz", + "integrity": "sha512-mEu1/UIXAdNYuBcyEPbjScKi/+MQVXNIuY/7Cm5XLIWe319kDrT5SizBE95jqtmEXoDbGoZxKLCMttdZdqTZKQ==", + "license": "Apache-2.0", + "dependencies": { + "@smithy/util-buffer-from": "^4.1.0", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=18.0.0" + } + }, + "node_modules/@ai-sdk/anthropic": { + "version": "2.0.17", + "resolved": "https://registry.npmjs.org/@ai-sdk/anthropic/-/anthropic-2.0.17.tgz", + "integrity": "sha512-fEmGD3H3cI4ahcrtU/ekA6xvUq9kk/IpOh2TI3wOSxqvKqpo+ztwiem5/x5R92Yenl9KRooYIefr0LNlFUR5Ow==", + "license": "Apache-2.0", + "dependencies": { + "@ai-sdk/provider": "2.0.0", + "@ai-sdk/provider-utils": "3.0.9" + }, + "engines": { + "node": ">=18" + }, + "peerDependencies": { + "zod": "^3.25.76 || ^4" + } + }, + "node_modules/@ai-sdk/azure": { + "version": "2.0.30", + "resolved": "https://registry.npmjs.org/@ai-sdk/azure/-/azure-2.0.30.tgz", + "integrity": "sha512-bBa8WVYpjmfAznzf9Ba6TcGsaVcxeSNs+mEByk1k6mT/xtt3kxRpPixssSpKP/fc0Gl1us+O51OYzqc7G9/B+w==", + "license": "Apache-2.0", + "dependencies": { + "@ai-sdk/openai": "2.0.30", + "@ai-sdk/provider": "2.0.0", + "@ai-sdk/provider-utils": "3.0.9" + }, + "engines": { + "node": ">=18" + }, + "peerDependencies": { + "zod": "^3.25.76 || ^4" + } + }, + "node_modules/@ai-sdk/gateway": { + "version": "1.0.23", + "resolved": "https://registry.npmjs.org/@ai-sdk/gateway/-/gateway-1.0.23.tgz", + "integrity": "sha512-ynV7WxpRK2zWLGkdOtrU2hW22mBVkEYVS3iMg1+ZGmAYSgzCqzC74bfOJZ2GU1UdcrFWUsFI9qAYjsPkd+AebA==", + "license": "Apache-2.0", + "dependencies": { + "@ai-sdk/provider": "2.0.0", + "@ai-sdk/provider-utils": "3.0.9" + }, + "engines": { + "node": ">=18" + }, + "peerDependencies": { + "zod": "^3.25.76 || ^4" + } + }, + "node_modules/@ai-sdk/google": { + "version": "2.0.14", + "resolved": "https://registry.npmjs.org/@ai-sdk/google/-/google-2.0.14.tgz", + "integrity": "sha512-OCBBkEUq1RNLkbJuD+ejqGsWDD0M5nRyuFWDchwylxy0J4HSsAiGNhutNYVTdnqmNw+r9LyZlkyZ1P4YfAfLdg==", + "license": "Apache-2.0", + "dependencies": { + "@ai-sdk/provider": "2.0.0", + "@ai-sdk/provider-utils": "3.0.9" + }, + "engines": { + "node": ">=18" + }, + "peerDependencies": { + "zod": "^3.25.76 || ^4" + } + }, + "node_modules/@ai-sdk/google-vertex": { + "version": "3.0.27", + "resolved": "https://registry.npmjs.org/@ai-sdk/google-vertex/-/google-vertex-3.0.27.tgz", + "integrity": "sha512-qR4+gLBNJPbnqaSBhvWktK0h3MfQryTLpKj9OWTYVhesNPqpkcchmbHmWBBXhI9kGN5niIknzHmCYdrtMqzF5w==", + "license": "Apache-2.0", + "dependencies": { + "@ai-sdk/anthropic": "2.0.17", + "@ai-sdk/google": "2.0.14", + "@ai-sdk/provider": "2.0.0", + "@ai-sdk/provider-utils": "3.0.9", + "google-auth-library": "^9.15.0" + }, + "engines": { + "node": ">=18" + }, + "peerDependencies": { + "zod": "^3.25.76 || ^4" + } + }, + "node_modules/@ai-sdk/google-vertex/node_modules/google-auth-library": { + "version": "9.15.1", + "resolved": "https://registry.npmjs.org/google-auth-library/-/google-auth-library-9.15.1.tgz", + "integrity": "sha512-Jb6Z0+nvECVz+2lzSMt9u98UsoakXxA2HGHMCxh+so3n90XgYWkq5dur19JAJV7ONiJY22yBTyJB1TSkvPq9Ng==", + "license": "Apache-2.0", + "dependencies": { + "base64-js": "^1.3.0", + "ecdsa-sig-formatter": "^1.0.11", + "gaxios": "^6.1.1", + "gcp-metadata": "^6.1.0", + "gtoken": "^7.0.0", + "jws": "^4.0.0" + }, + "engines": { + "node": ">=14" + } + }, + "node_modules/@ai-sdk/google-vertex/node_modules/gtoken": { + "version": "7.1.0", + "resolved": "https://registry.npmjs.org/gtoken/-/gtoken-7.1.0.tgz", + "integrity": "sha512-pCcEwRi+TKpMlxAQObHDQ56KawURgyAf6jtIY046fJ5tIv3zDe/LEIubckAO8fj6JnAxLdmWkUfNyulQ2iKdEw==", + "license": "MIT", + "dependencies": { + "gaxios": "^6.0.0", + "jws": "^4.0.0" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@ai-sdk/mistral": { + "version": "2.0.14", + "resolved": "https://registry.npmjs.org/@ai-sdk/mistral/-/mistral-2.0.14.tgz", + "integrity": "sha512-HPj/tz03k8IeW9SabHqhHmgdeKq1H89MltU5zUaxU/7JVV3n96MYIG3aQUtKbPMdtHw6LngJf6r/A+hampGLOA==", + "license": "Apache-2.0", + "dependencies": { + "@ai-sdk/provider": "2.0.0", + "@ai-sdk/provider-utils": "3.0.9" + }, + "engines": { + "node": ">=18" + }, + "peerDependencies": { + "zod": "^3.25.76 || ^4" + } + }, + "node_modules/@ai-sdk/openai": { + "version": "2.0.30", + "resolved": "https://registry.npmjs.org/@ai-sdk/openai/-/openai-2.0.30.tgz", + "integrity": "sha512-a9Vf64OT2dWEFyEGv+OxtCs69B18BsuzInvuyUxVPczbIiBLqUCt3zcD/8EwqbTPJwsFNsL8/9nbVZFmwA1+2A==", + "license": "Apache-2.0", + "dependencies": { + "@ai-sdk/provider": "2.0.0", + "@ai-sdk/provider-utils": "3.0.9" + }, + "engines": { + "node": ">=18" + }, + "peerDependencies": { + "zod": "^3.25.76 || ^4" + } + }, + "node_modules/@ai-sdk/openai-compatible": { + "version": "1.0.17", + "resolved": "https://registry.npmjs.org/@ai-sdk/openai-compatible/-/openai-compatible-1.0.17.tgz", + "integrity": "sha512-5AWWS8sbT7VJmi2gQZKXRJsnPg+3+yN2BLms3x1sjRA/ZUq2TfmVzv6PSMObvbkn27jpvyIX5/e6JYgafhYJkA==", + "license": "Apache-2.0", + "dependencies": { + "@ai-sdk/provider": "2.0.0", + "@ai-sdk/provider-utils": "3.0.9" + }, + "engines": { + "node": ">=18" + }, + "peerDependencies": { + "zod": "^3.25.76 || ^4" + } + }, + "node_modules/@ai-sdk/provider": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/@ai-sdk/provider/-/provider-2.0.0.tgz", + "integrity": "sha512-6o7Y2SeO9vFKB8lArHXehNuusnpddKPk7xqL7T2/b+OvXMRIXUO1rR4wcv1hAFUAT9avGZshty3Wlua/XA7TvA==", + "license": "Apache-2.0", + "dependencies": { + "json-schema": "^0.4.0" + }, + "engines": { + "node": ">=18" + } + }, + "node_modules/@ai-sdk/provider-utils": { + "version": "3.0.9", + "resolved": "https://registry.npmjs.org/@ai-sdk/provider-utils/-/provider-utils-3.0.9.tgz", + "integrity": "sha512-Pm571x5efqaI4hf9yW4KsVlDBDme8++UepZRnq+kqVBWWjgvGhQlzU8glaFq0YJEB9kkxZHbRRyVeHoV2sRYaQ==", + "license": "Apache-2.0", + "dependencies": { + "@ai-sdk/provider": "2.0.0", + "@standard-schema/spec": "^1.0.0", + "eventsource-parser": "^3.0.5" + }, + "engines": { + "node": ">=18" + }, + "peerDependencies": { + "zod": "^3.25.76 || ^4" + } + }, "node_modules/@ampproject/remapping": { "version": "2.3.0", "dev": true, @@ -227,24 +488,6 @@ "url": "https://github.com/sponsors/epoberezkin" } }, - "node_modules/@angular-devkit/schematics-cli/node_modules/chokidar": { - "version": "4.0.3", - "resolved": "https://registry.npmjs.org/chokidar/-/chokidar-4.0.3.tgz", - "integrity": "sha512-Qgzu8kfBvo+cA4962jnP1KkS6Dop5NS6g7R5LFYJr4b8Ub94PPQXUksCw9PvXoeXPRRddRNC5C1JQUR2SMGtnA==", - "dev": true, - "license": "MIT", - "optional": true, - "peer": true, - "dependencies": { - "readdirp": "^4.0.1" - }, - "engines": { - "node": ">= 14.16.0" - }, - "funding": { - "url": "https://paulmillr.com/funding/" - } - }, "node_modules/@angular-devkit/schematics-cli/node_modules/json-schema-traverse": { "version": "1.0.0", "dev": true, @@ -257,7 +500,6 @@ "dev": true, "license": "MIT", "optional": true, - "peer": true, "engines": { "node": ">= 14.18.0" }, @@ -315,24 +557,6 @@ "url": "https://github.com/sponsors/epoberezkin" } }, - "node_modules/@angular-devkit/schematics/node_modules/chokidar": { - "version": "4.0.3", - "resolved": "https://registry.npmjs.org/chokidar/-/chokidar-4.0.3.tgz", - "integrity": "sha512-Qgzu8kfBvo+cA4962jnP1KkS6Dop5NS6g7R5LFYJr4b8Ub94PPQXUksCw9PvXoeXPRRddRNC5C1JQUR2SMGtnA==", - "dev": true, - "license": "MIT", - "optional": true, - "peer": true, - "dependencies": { - "readdirp": "^4.0.1" - }, - "engines": { - "node": ">= 14.16.0" - }, - "funding": { - "url": "https://paulmillr.com/funding/" - } - }, "node_modules/@angular-devkit/schematics/node_modules/json-schema-traverse": { "version": "1.0.0", "dev": true, @@ -345,7 +569,6 @@ "dev": true, "license": "MIT", "optional": true, - "peer": true, "engines": { "node": ">= 14.18.0" }, @@ -362,65 +585,6 @@ "tslib": "^2.1.0" } }, - "node_modules/@anthropic-ai/sdk": { - "version": "0.27.3", - "license": "MIT", - "peer": true, - "dependencies": { - "@types/node": "^18.11.18", - "@types/node-fetch": "^2.6.4", - "abort-controller": "^3.0.0", - "agentkeepalive": "^4.2.1", - "form-data-encoder": "1.7.2", - "formdata-node": "^4.3.2", - "node-fetch": "^2.6.7" - } - }, - "node_modules/@anthropic-ai/sdk/node_modules/@types/node": { - "version": "18.19.100", - "license": "MIT", - "peer": true, - "dependencies": { - "undici-types": "~5.26.4" - } - }, - "node_modules/@anthropic-ai/sdk/node_modules/undici-types": { - "version": "5.26.5", - "license": "MIT", - "peer": true - }, - "node_modules/@aws-crypto/sha256-browser": { - "version": "5.2.0", - "license": "Apache-2.0", - "dependencies": { - "@aws-crypto/sha256-js": "^5.2.0", - "@aws-crypto/supports-web-crypto": "^5.2.0", - "@aws-crypto/util": "^5.2.0", - "@aws-sdk/types": "^3.222.0", - "@aws-sdk/util-locate-window": "^3.0.0", - "@smithy/util-utf8": "^2.0.0", - "tslib": "^2.6.2" - } - }, - "node_modules/@aws-crypto/sha256-js": { - "version": "5.2.0", - "license": "Apache-2.0", - "dependencies": { - "@aws-crypto/util": "^5.2.0", - "@aws-sdk/types": "^3.222.0", - "tslib": "^2.6.2" - }, - "engines": { - "node": ">=16.0.0" - } - }, - "node_modules/@aws-crypto/supports-web-crypto": { - "version": "5.2.0", - "license": "Apache-2.0", - "dependencies": { - "tslib": "^2.6.2" - } - }, "node_modules/@aws-crypto/util": { "version": "5.2.0", "license": "Apache-2.0", @@ -430,5275 +594,4560 @@ "tslib": "^2.6.2" } }, - "node_modules/@aws-sdk/client-bedrock-agent-runtime": { - "version": "3.806.0", + "node_modules/@aws-sdk/types": { + "version": "3.804.0", "license": "Apache-2.0", "dependencies": { - "@aws-crypto/sha256-browser": "5.2.0", - "@aws-crypto/sha256-js": "5.2.0", - "@aws-sdk/core": "3.806.0", - "@aws-sdk/credential-provider-node": "3.806.0", - "@aws-sdk/middleware-host-header": "3.804.0", - "@aws-sdk/middleware-logger": "3.804.0", - "@aws-sdk/middleware-recursion-detection": "3.804.0", - "@aws-sdk/middleware-user-agent": "3.806.0", - "@aws-sdk/region-config-resolver": "3.806.0", - "@aws-sdk/types": "3.804.0", - "@aws-sdk/util-endpoints": "3.806.0", - "@aws-sdk/util-user-agent-browser": "3.804.0", - "@aws-sdk/util-user-agent-node": "3.806.0", - "@smithy/config-resolver": "^4.1.1", - "@smithy/core": "^3.3.1", - "@smithy/eventstream-serde-browser": "^4.0.2", - "@smithy/eventstream-serde-config-resolver": "^4.1.0", - "@smithy/eventstream-serde-node": "^4.0.2", - "@smithy/fetch-http-handler": "^5.0.2", - "@smithy/hash-node": "^4.0.2", - "@smithy/invalid-dependency": "^4.0.2", - "@smithy/middleware-content-length": "^4.0.2", - "@smithy/middleware-endpoint": "^4.1.3", - "@smithy/middleware-retry": "^4.1.4", - "@smithy/middleware-serde": "^4.0.3", - "@smithy/middleware-stack": "^4.0.2", - "@smithy/node-config-provider": "^4.1.0", - "@smithy/node-http-handler": "^4.0.4", - "@smithy/protocol-http": "^5.1.0", - "@smithy/smithy-client": "^4.2.3", "@smithy/types": "^4.2.0", - "@smithy/url-parser": "^4.0.2", - "@smithy/util-base64": "^4.0.0", - "@smithy/util-body-length-browser": "^4.0.0", - "@smithy/util-body-length-node": "^4.0.0", - "@smithy/util-defaults-mode-browser": "^4.0.11", - "@smithy/util-defaults-mode-node": "^4.0.11", - "@smithy/util-endpoints": "^3.0.3", - "@smithy/util-middleware": "^4.0.2", - "@smithy/util-retry": "^4.0.3", - "@smithy/util-utf8": "^4.0.0", "tslib": "^2.6.2" }, "engines": { "node": ">=18.0.0" } }, - "node_modules/@aws-sdk/client-bedrock-agent-runtime/node_modules/@smithy/protocol-http": { - "version": "5.1.0", - "license": "Apache-2.0", + "node_modules/@azure-rest/core-client": { + "version": "2.5.0", + "resolved": "https://registry.npmjs.org/@azure-rest/core-client/-/core-client-2.5.0.tgz", + "integrity": "sha512-KMVIPxG6ygcQ1M2hKHahF7eddKejYsWTjoLIfTWiqnaj42dBkYzj4+S8rK9xxmlOaEHKZHcMrRbm0NfN4kgwHw==", + "license": "MIT", "dependencies": { - "@smithy/types": "^4.2.0", + "@azure/abort-controller": "^2.0.0", + "@azure/core-auth": "^1.9.0", + "@azure/core-rest-pipeline": "^1.5.0", + "@azure/core-tracing": "^1.0.1", + "@typespec/ts-http-runtime": "^0.3.0", "tslib": "^2.6.2" }, "engines": { - "node": ">=18.0.0" + "node": ">=20.0.0" } }, - "node_modules/@aws-sdk/client-bedrock-agent-runtime/node_modules/@smithy/util-utf8": { - "version": "4.0.0", - "license": "Apache-2.0", + "node_modules/@azure/abort-controller": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/@azure/abort-controller/-/abort-controller-2.1.2.tgz", + "integrity": "sha512-nBrLsEWm4J2u5LpAPjxADTlq3trDgVZZXHNKabeXZtpq3d3AbN/KGO82R87rdDz5/lYB024rtEf10/q0urNgsA==", + "license": "MIT", "dependencies": { - "@smithy/util-buffer-from": "^4.0.0", "tslib": "^2.6.2" }, "engines": { "node": ">=18.0.0" } }, - "node_modules/@aws-sdk/client-bedrock-runtime": { - "version": "3.806.0", - "license": "Apache-2.0", - "dependencies": { - "@aws-crypto/sha256-browser": "5.2.0", - "@aws-crypto/sha256-js": "5.2.0", - "@aws-sdk/core": "3.806.0", - "@aws-sdk/credential-provider-node": "3.806.0", - "@aws-sdk/eventstream-handler-node": "3.804.0", - "@aws-sdk/middleware-eventstream": "3.804.0", - "@aws-sdk/middleware-host-header": "3.804.0", - "@aws-sdk/middleware-logger": "3.804.0", - "@aws-sdk/middleware-recursion-detection": "3.804.0", - "@aws-sdk/middleware-user-agent": "3.806.0", - "@aws-sdk/region-config-resolver": "3.806.0", - "@aws-sdk/types": "3.804.0", - "@aws-sdk/util-endpoints": "3.806.0", - "@aws-sdk/util-user-agent-browser": "3.804.0", - "@aws-sdk/util-user-agent-node": "3.806.0", - "@smithy/config-resolver": "^4.1.1", - "@smithy/core": "^3.3.1", - "@smithy/eventstream-serde-browser": "^4.0.2", - "@smithy/eventstream-serde-config-resolver": "^4.1.0", - "@smithy/eventstream-serde-node": "^4.0.2", - "@smithy/fetch-http-handler": "^5.0.2", - "@smithy/hash-node": "^4.0.2", - "@smithy/invalid-dependency": "^4.0.2", - "@smithy/middleware-content-length": "^4.0.2", - "@smithy/middleware-endpoint": "^4.1.3", - "@smithy/middleware-retry": "^4.1.4", - "@smithy/middleware-serde": "^4.0.3", - "@smithy/middleware-stack": "^4.0.2", - "@smithy/node-config-provider": "^4.1.0", - "@smithy/node-http-handler": "^4.0.4", - "@smithy/protocol-http": "^5.1.0", - "@smithy/smithy-client": "^4.2.3", - "@smithy/types": "^4.2.0", - "@smithy/url-parser": "^4.0.2", - "@smithy/util-base64": "^4.0.0", - "@smithy/util-body-length-browser": "^4.0.0", - "@smithy/util-body-length-node": "^4.0.0", - "@smithy/util-defaults-mode-browser": "^4.0.11", - "@smithy/util-defaults-mode-node": "^4.0.11", - "@smithy/util-endpoints": "^3.0.3", - "@smithy/util-middleware": "^4.0.2", - "@smithy/util-retry": "^4.0.3", - "@smithy/util-stream": "^4.2.0", - "@smithy/util-utf8": "^4.0.0", - "@types/uuid": "^9.0.1", - "tslib": "^2.6.2", - "uuid": "^9.0.1" - }, - "engines": { - "node": ">=18.0.0" - } - }, - "node_modules/@aws-sdk/client-bedrock-runtime/node_modules/@smithy/protocol-http": { - "version": "5.1.0", - "license": "Apache-2.0", + "node_modules/@azure/ai-agents": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/@azure/ai-agents/-/ai-agents-1.1.0.tgz", + "integrity": "sha512-i8HFA7ql18t/otGrRfTWNOE5HgJf/RqedV3VNbFav5z9iTSexf8k4EeWOb/IWWaCsq0z/S7mihdGPAluPs+nXQ==", + "license": "MIT", "dependencies": { - "@smithy/types": "^4.2.0", + "@azure-rest/core-client": "^2.1.0", + "@azure/abort-controller": "^2.1.2", + "@azure/core-auth": "^1.6.0", + "@azure/core-lro": "^3.0.0", + "@azure/core-paging": "^1.5.0", + "@azure/core-rest-pipeline": "^1.5.0", + "@azure/core-sse": "^2.1.3", + "@azure/core-tracing": "^1.2.0", + "@azure/core-util": "^1.9.0", + "@azure/logger": "^1.1.4", "tslib": "^2.6.2" }, "engines": { - "node": ">=18.0.0" + "node": ">=20.0.0" } }, - "node_modules/@aws-sdk/client-bedrock-runtime/node_modules/@smithy/util-utf8": { - "version": "4.0.0", - "license": "Apache-2.0", + "node_modules/@azure/core-auth": { + "version": "1.10.0", + "resolved": "https://registry.npmjs.org/@azure/core-auth/-/core-auth-1.10.0.tgz", + "integrity": "sha512-88Djs5vBvGbHQHf5ZZcaoNHo6Y8BKZkt3cw2iuJIQzLEgH4Ox6Tm4hjFhbqOxyYsgIG/eJbFEHpxRIfEEWv5Ow==", + "license": "MIT", "dependencies": { - "@smithy/util-buffer-from": "^4.0.0", + "@azure/abort-controller": "^2.0.0", + "@azure/core-util": "^1.11.0", "tslib": "^2.6.2" }, "engines": { - "node": ">=18.0.0" + "node": ">=20.0.0" } }, - "node_modules/@aws-sdk/client-kendra": { - "version": "3.806.0", - "license": "Apache-2.0", + "node_modules/@azure/core-client": { + "version": "1.10.0", + "resolved": "https://registry.npmjs.org/@azure/core-client/-/core-client-1.10.0.tgz", + "integrity": "sha512-O4aP3CLFNodg8eTHXECaH3B3CjicfzkxVtnrfLkOq0XNP7TIECGfHpK/C6vADZkWP75wzmdBnsIA8ksuJMk18g==", + "license": "MIT", "dependencies": { - "@aws-crypto/sha256-browser": "5.2.0", - "@aws-crypto/sha256-js": "5.2.0", - "@aws-sdk/core": "3.806.0", - "@aws-sdk/credential-provider-node": "3.806.0", - "@aws-sdk/middleware-host-header": "3.804.0", - "@aws-sdk/middleware-logger": "3.804.0", - "@aws-sdk/middleware-recursion-detection": "3.804.0", - "@aws-sdk/middleware-user-agent": "3.806.0", - "@aws-sdk/region-config-resolver": "3.806.0", - "@aws-sdk/types": "3.804.0", - "@aws-sdk/util-endpoints": "3.806.0", - "@aws-sdk/util-user-agent-browser": "3.804.0", - "@aws-sdk/util-user-agent-node": "3.806.0", - "@smithy/config-resolver": "^4.1.1", - "@smithy/core": "^3.3.1", - "@smithy/fetch-http-handler": "^5.0.2", - "@smithy/hash-node": "^4.0.2", - "@smithy/invalid-dependency": "^4.0.2", - "@smithy/middleware-content-length": "^4.0.2", - "@smithy/middleware-endpoint": "^4.1.3", - "@smithy/middleware-retry": "^4.1.4", - "@smithy/middleware-serde": "^4.0.3", - "@smithy/middleware-stack": "^4.0.2", - "@smithy/node-config-provider": "^4.1.0", - "@smithy/node-http-handler": "^4.0.4", - "@smithy/protocol-http": "^5.1.0", - "@smithy/smithy-client": "^4.2.3", - "@smithy/types": "^4.2.0", - "@smithy/url-parser": "^4.0.2", - "@smithy/util-base64": "^4.0.0", - "@smithy/util-body-length-browser": "^4.0.0", - "@smithy/util-body-length-node": "^4.0.0", - "@smithy/util-defaults-mode-browser": "^4.0.11", - "@smithy/util-defaults-mode-node": "^4.0.11", - "@smithy/util-endpoints": "^3.0.3", - "@smithy/util-middleware": "^4.0.2", - "@smithy/util-retry": "^4.0.3", - "@smithy/util-utf8": "^4.0.0", - "@types/uuid": "^9.0.1", - "tslib": "^2.6.2", - "uuid": "^9.0.1" + "@azure/abort-controller": "^2.0.0", + "@azure/core-auth": "^1.4.0", + "@azure/core-rest-pipeline": "^1.20.0", + "@azure/core-tracing": "^1.0.0", + "@azure/core-util": "^1.6.1", + "@azure/logger": "^1.0.0", + "tslib": "^2.6.2" }, "engines": { - "node": ">=18.0.0" + "node": ">=20.0.0" } }, - "node_modules/@aws-sdk/client-kendra/node_modules/@smithy/protocol-http": { - "version": "5.1.0", - "license": "Apache-2.0", + "node_modules/@azure/core-lro": { + "version": "3.3.0", + "resolved": "https://registry.npmjs.org/@azure/core-lro/-/core-lro-3.3.0.tgz", + "integrity": "sha512-q8onFxe4O2iqPiURwnqAEO/x6oYkU+lHDWOOc16vPonhuNoKeisDPB8xzun25EClCTrd1xG51YfLGMlvKcB9mg==", + "license": "MIT", "dependencies": { - "@smithy/types": "^4.2.0", + "@azure/abort-controller": "^2.0.0", + "@azure/core-util": "^1.2.0", + "@azure/logger": "^1.0.0", "tslib": "^2.6.2" }, "engines": { - "node": ">=18.0.0" + "node": ">=20.0.0" } }, - "node_modules/@aws-sdk/client-kendra/node_modules/@smithy/util-utf8": { - "version": "4.0.0", - "license": "Apache-2.0", + "node_modules/@azure/core-paging": { + "version": "1.6.2", + "resolved": "https://registry.npmjs.org/@azure/core-paging/-/core-paging-1.6.2.tgz", + "integrity": "sha512-YKWi9YuCU04B55h25cnOYZHxXYtEvQEbKST5vqRga7hWY9ydd3FZHdeQF8pyh+acWZvppw13M/LMGx0LABUVMA==", + "license": "MIT", "dependencies": { - "@smithy/util-buffer-from": "^4.0.0", "tslib": "^2.6.2" }, "engines": { "node": ">=18.0.0" } }, - "node_modules/@aws-sdk/client-sso": { - "version": "3.806.0", - "license": "Apache-2.0", + "node_modules/@azure/core-rest-pipeline": { + "version": "1.22.0", + "resolved": "https://registry.npmjs.org/@azure/core-rest-pipeline/-/core-rest-pipeline-1.22.0.tgz", + "integrity": "sha512-OKHmb3/Kpm06HypvB3g6Q3zJuvyXcpxDpCS1PnU8OV6AJgSFaee/covXBcPbWc6XDDxtEPlbi3EMQ6nUiPaQtw==", + "license": "MIT", "dependencies": { - "@aws-crypto/sha256-browser": "5.2.0", - "@aws-crypto/sha256-js": "5.2.0", - "@aws-sdk/core": "3.806.0", - "@aws-sdk/middleware-host-header": "3.804.0", - "@aws-sdk/middleware-logger": "3.804.0", - "@aws-sdk/middleware-recursion-detection": "3.804.0", - "@aws-sdk/middleware-user-agent": "3.806.0", - "@aws-sdk/region-config-resolver": "3.806.0", - "@aws-sdk/types": "3.804.0", - "@aws-sdk/util-endpoints": "3.806.0", - "@aws-sdk/util-user-agent-browser": "3.804.0", - "@aws-sdk/util-user-agent-node": "3.806.0", - "@smithy/config-resolver": "^4.1.1", - "@smithy/core": "^3.3.1", - "@smithy/fetch-http-handler": "^5.0.2", - "@smithy/hash-node": "^4.0.2", - "@smithy/invalid-dependency": "^4.0.2", - "@smithy/middleware-content-length": "^4.0.2", - "@smithy/middleware-endpoint": "^4.1.3", - "@smithy/middleware-retry": "^4.1.4", - "@smithy/middleware-serde": "^4.0.3", - "@smithy/middleware-stack": "^4.0.2", - "@smithy/node-config-provider": "^4.1.0", - "@smithy/node-http-handler": "^4.0.4", - "@smithy/protocol-http": "^5.1.0", - "@smithy/smithy-client": "^4.2.3", - "@smithy/types": "^4.2.0", - "@smithy/url-parser": "^4.0.2", - "@smithy/util-base64": "^4.0.0", - "@smithy/util-body-length-browser": "^4.0.0", - "@smithy/util-body-length-node": "^4.0.0", - "@smithy/util-defaults-mode-browser": "^4.0.11", - "@smithy/util-defaults-mode-node": "^4.0.11", - "@smithy/util-endpoints": "^3.0.3", - "@smithy/util-middleware": "^4.0.2", - "@smithy/util-retry": "^4.0.3", - "@smithy/util-utf8": "^4.0.0", + "@azure/abort-controller": "^2.0.0", + "@azure/core-auth": "^1.8.0", + "@azure/core-tracing": "^1.0.1", + "@azure/core-util": "^1.11.0", + "@azure/logger": "^1.0.0", + "@typespec/ts-http-runtime": "^0.3.0", "tslib": "^2.6.2" }, "engines": { - "node": ">=18.0.0" + "node": ">=20.0.0" } }, - "node_modules/@aws-sdk/client-sso/node_modules/@smithy/protocol-http": { - "version": "5.1.0", - "license": "Apache-2.0", + "node_modules/@azure/core-sse": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/@azure/core-sse/-/core-sse-2.3.0.tgz", + "integrity": "sha512-jKhPpdDbVS5GlpadSKIC7V6Q4P2vEcwXi1c4CLTXs01Q/PAITES9v5J/S73+RtCMqQpsX0jGa2yPWwXi9JzdgA==", + "license": "MIT", "dependencies": { - "@smithy/types": "^4.2.0", "tslib": "^2.6.2" }, "engines": { - "node": ">=18.0.0" + "node": ">=20.0.0" } }, - "node_modules/@aws-sdk/client-sso/node_modules/@smithy/util-utf8": { - "version": "4.0.0", - "license": "Apache-2.0", + "node_modules/@azure/core-tracing": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/@azure/core-tracing/-/core-tracing-1.3.0.tgz", + "integrity": "sha512-+XvmZLLWPe67WXNZo9Oc9CrPj/Tm8QnHR92fFAFdnbzwNdCH1h+7UdpaQgRSBsMY+oW1kHXNUZQLdZ1gHX3ROw==", + "license": "MIT", "dependencies": { - "@smithy/util-buffer-from": "^4.0.0", "tslib": "^2.6.2" }, "engines": { - "node": ">=18.0.0" + "node": ">=20.0.0" } }, - "node_modules/@aws-sdk/core": { - "version": "3.806.0", - "license": "Apache-2.0", + "node_modules/@azure/core-util": { + "version": "1.13.0", + "resolved": "https://registry.npmjs.org/@azure/core-util/-/core-util-1.13.0.tgz", + "integrity": "sha512-o0psW8QWQ58fq3i24Q1K2XfS/jYTxr7O1HRcyUE9bV9NttLU+kYOH82Ixj8DGlMTOWgxm1Sss2QAfKK5UkSPxw==", + "license": "MIT", "dependencies": { - "@aws-sdk/types": "3.804.0", - "@smithy/core": "^3.3.1", - "@smithy/node-config-provider": "^4.1.0", - "@smithy/property-provider": "^4.0.2", - "@smithy/protocol-http": "^5.1.0", - "@smithy/signature-v4": "^5.1.0", - "@smithy/smithy-client": "^4.2.3", - "@smithy/types": "^4.2.0", - "@smithy/util-middleware": "^4.0.2", - "fast-xml-parser": "4.4.1", + "@azure/abort-controller": "^2.0.0", + "@typespec/ts-http-runtime": "^0.3.0", "tslib": "^2.6.2" }, "engines": { - "node": ">=18.0.0" + "node": ">=20.0.0" } }, - "node_modules/@aws-sdk/core/node_modules/@smithy/is-array-buffer": { - "version": "4.0.0", - "license": "Apache-2.0", + "node_modules/@azure/identity": { + "version": "4.11.0", + "resolved": "https://registry.npmjs.org/@azure/identity/-/identity-4.11.0.tgz", + "integrity": "sha512-GkbNnd3mrsL1gX3BxIblhahCfFEViLTfNMFgfSo4wPSH2ipw4duc1TtOPVOf8Wt6XTnjZROZRAvYqjJBWXV39g==", + "license": "MIT", "dependencies": { - "tslib": "^2.6.2" + "@azure/abort-controller": "^2.0.0", + "@azure/core-auth": "^1.9.0", + "@azure/core-client": "^1.9.2", + "@azure/core-rest-pipeline": "^1.17.0", + "@azure/core-tracing": "^1.0.0", + "@azure/core-util": "^1.11.0", + "@azure/logger": "^1.0.0", + "@azure/msal-browser": "^4.2.0", + "@azure/msal-node": "^3.5.0", + "open": "^10.1.0", + "tslib": "^2.2.0" }, "engines": { - "node": ">=18.0.0" + "node": ">=20.0.0" } }, - "node_modules/@aws-sdk/core/node_modules/@smithy/protocol-http": { - "version": "5.1.0", - "license": "Apache-2.0", + "node_modules/@azure/logger": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/@azure/logger/-/logger-1.3.0.tgz", + "integrity": "sha512-fCqPIfOcLE+CGqGPd66c8bZpwAji98tZ4JI9i/mlTNTlsIWslCfpg48s/ypyLxZTump5sypjrKn2/kY7q8oAbA==", + "license": "MIT", "dependencies": { - "@smithy/types": "^4.2.0", + "@typespec/ts-http-runtime": "^0.3.0", "tslib": "^2.6.2" }, "engines": { - "node": ">=18.0.0" + "node": ">=20.0.0" } }, - "node_modules/@aws-sdk/core/node_modules/@smithy/signature-v4": { - "version": "5.1.0", - "license": "Apache-2.0", + "node_modules/@azure/msal-browser": { + "version": "4.18.0", + "resolved": "https://registry.npmjs.org/@azure/msal-browser/-/msal-browser-4.18.0.tgz", + "integrity": "sha512-esQwdtHHVkFJhcKWnysnCTchiKsy3dmNZGs8AckD9PO3t8Lp5VtY0xcrbCBC0JbttG/5w2/xukUQOsMpoUFKrg==", + "license": "MIT", "dependencies": { - "@smithy/is-array-buffer": "^4.0.0", - "@smithy/protocol-http": "^5.1.0", - "@smithy/types": "^4.2.0", - "@smithy/util-hex-encoding": "^4.0.0", - "@smithy/util-middleware": "^4.0.2", - "@smithy/util-uri-escape": "^4.0.0", - "@smithy/util-utf8": "^4.0.0", - "tslib": "^2.6.2" + "@azure/msal-common": "15.9.0" }, "engines": { - "node": ">=18.0.0" + "node": ">=0.8.0" } }, - "node_modules/@aws-sdk/core/node_modules/@smithy/util-hex-encoding": { - "version": "4.0.0", - "license": "Apache-2.0", - "dependencies": { - "tslib": "^2.6.2" - }, + "node_modules/@azure/msal-common": { + "version": "15.9.0", + "resolved": "https://registry.npmjs.org/@azure/msal-common/-/msal-common-15.9.0.tgz", + "integrity": "sha512-lbz/D+C9ixUG3hiZzBLjU79a0+5ZXCorjel3mwXluisKNH0/rOS/ajm8yi4yI9RP5Uc70CAcs9Ipd0051Oh/kA==", + "license": "MIT", "engines": { - "node": ">=18.0.0" + "node": ">=0.8.0" } }, - "node_modules/@aws-sdk/core/node_modules/@smithy/util-utf8": { - "version": "4.0.0", - "license": "Apache-2.0", + "node_modules/@azure/msal-node": { + "version": "3.6.4", + "resolved": "https://registry.npmjs.org/@azure/msal-node/-/msal-node-3.6.4.tgz", + "integrity": "sha512-jMeut9UQugcmq7aPWWlJKhJIse4DQ594zc/JaP6BIxg55XaX3aM/jcPuIQ4ryHnI4QSf03wUspy/uqAvjWKbOg==", + "license": "MIT", "dependencies": { - "@smithy/util-buffer-from": "^4.0.0", - "tslib": "^2.6.2" + "@azure/msal-common": "15.9.0", + "jsonwebtoken": "^9.0.0", + "uuid": "^8.3.0" }, "engines": { - "node": ">=18.0.0" + "node": ">=16" } }, - "node_modules/@aws-sdk/credential-provider-env": { - "version": "3.806.0", - "license": "Apache-2.0", - "dependencies": { - "@aws-sdk/core": "3.806.0", - "@aws-sdk/types": "3.804.0", - "@smithy/property-provider": "^4.0.2", - "@smithy/types": "^4.2.0", - "tslib": "^2.6.2" - }, - "engines": { - "node": ">=18.0.0" + "node_modules/@azure/msal-node/node_modules/uuid": { + "version": "8.3.2", + "resolved": "https://registry.npmjs.org/uuid/-/uuid-8.3.2.tgz", + "integrity": "sha512-+NYs2QeMWy+GWFOEm9xnn6HCDp0l7QBD7ml8zLUmJ+93Q5NF0NocErnwkTkXVFNiX3/fpC6afS8Dhb/gz7R7eg==", + "license": "MIT", + "bin": { + "uuid": "dist/bin/uuid" } }, - "node_modules/@aws-sdk/credential-provider-http": { - "version": "3.806.0", - "license": "Apache-2.0", + "node_modules/@babel/code-frame": { + "version": "7.27.1", + "dev": true, + "license": "MIT", "dependencies": { - "@aws-sdk/core": "3.806.0", - "@aws-sdk/types": "3.804.0", - "@smithy/fetch-http-handler": "^5.0.2", - "@smithy/node-http-handler": "^4.0.4", - "@smithy/property-provider": "^4.0.2", - "@smithy/protocol-http": "^5.1.0", - "@smithy/smithy-client": "^4.2.3", - "@smithy/types": "^4.2.0", - "@smithy/util-stream": "^4.2.0", - "tslib": "^2.6.2" + "@babel/helper-validator-identifier": "^7.27.1", + "js-tokens": "^4.0.0", + "picocolors": "^1.1.1" }, "engines": { - "node": ">=18.0.0" + "node": ">=6.9.0" } }, - "node_modules/@aws-sdk/credential-provider-http/node_modules/@smithy/protocol-http": { - "version": "5.1.0", - "license": "Apache-2.0", - "dependencies": { - "@smithy/types": "^4.2.0", - "tslib": "^2.6.2" - }, + "node_modules/@babel/compat-data": { + "version": "7.27.2", + "dev": true, + "license": "MIT", "engines": { - "node": ">=18.0.0" + "node": ">=6.9.0" } }, - "node_modules/@aws-sdk/credential-provider-ini": { - "version": "3.806.0", - "license": "Apache-2.0", + "node_modules/@babel/core": { + "version": "7.27.1", + "dev": true, + "license": "MIT", + "peer": true, "dependencies": { - "@aws-sdk/core": "3.806.0", - "@aws-sdk/credential-provider-env": "3.806.0", - "@aws-sdk/credential-provider-http": "3.806.0", - "@aws-sdk/credential-provider-process": "3.806.0", - "@aws-sdk/credential-provider-sso": "3.806.0", - "@aws-sdk/credential-provider-web-identity": "3.806.0", - "@aws-sdk/nested-clients": "3.806.0", - "@aws-sdk/types": "3.804.0", - "@smithy/credential-provider-imds": "^4.0.2", - "@smithy/property-provider": "^4.0.2", - "@smithy/shared-ini-file-loader": "^4.0.2", - "@smithy/types": "^4.2.0", - "tslib": "^2.6.2" + "@ampproject/remapping": "^2.2.0", + "@babel/code-frame": "^7.27.1", + "@babel/generator": "^7.27.1", + "@babel/helper-compilation-targets": "^7.27.1", + "@babel/helper-module-transforms": "^7.27.1", + "@babel/helpers": "^7.27.1", + "@babel/parser": "^7.27.1", + "@babel/template": "^7.27.1", + "@babel/traverse": "^7.27.1", + "@babel/types": "^7.27.1", + "convert-source-map": "^2.0.0", + "debug": "^4.1.0", + "gensync": "^1.0.0-beta.2", + "json5": "^2.2.3", + "semver": "^6.3.1" }, "engines": { - "node": ">=18.0.0" - } - }, - "node_modules/@aws-sdk/credential-provider-node": { - "version": "3.806.0", - "license": "Apache-2.0", - "dependencies": { - "@aws-sdk/credential-provider-env": "3.806.0", - "@aws-sdk/credential-provider-http": "3.806.0", - "@aws-sdk/credential-provider-ini": "3.806.0", - "@aws-sdk/credential-provider-process": "3.806.0", - "@aws-sdk/credential-provider-sso": "3.806.0", - "@aws-sdk/credential-provider-web-identity": "3.806.0", - "@aws-sdk/types": "3.804.0", - "@smithy/credential-provider-imds": "^4.0.2", - "@smithy/property-provider": "^4.0.2", - "@smithy/shared-ini-file-loader": "^4.0.2", - "@smithy/types": "^4.2.0", - "tslib": "^2.6.2" + "node": ">=6.9.0" }, - "engines": { - "node": ">=18.0.0" + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/babel" } }, - "node_modules/@aws-sdk/credential-provider-process": { - "version": "3.806.0", - "license": "Apache-2.0", + "node_modules/@babel/core/node_modules/semver": { + "version": "6.3.1", + "dev": true, + "license": "ISC", + "bin": { + "semver": "bin/semver.js" + } + }, + "node_modules/@babel/generator": { + "version": "7.27.1", + "dev": true, + "license": "MIT", "dependencies": { - "@aws-sdk/core": "3.806.0", - "@aws-sdk/types": "3.804.0", - "@smithy/property-provider": "^4.0.2", - "@smithy/shared-ini-file-loader": "^4.0.2", - "@smithy/types": "^4.2.0", - "tslib": "^2.6.2" + "@babel/parser": "^7.27.1", + "@babel/types": "^7.27.1", + "@jridgewell/gen-mapping": "^0.3.5", + "@jridgewell/trace-mapping": "^0.3.25", + "jsesc": "^3.0.2" }, "engines": { - "node": ">=18.0.0" + "node": ">=6.9.0" } }, - "node_modules/@aws-sdk/credential-provider-sso": { - "version": "3.806.0", - "license": "Apache-2.0", + "node_modules/@babel/helper-compilation-targets": { + "version": "7.27.2", + "dev": true, + "license": "MIT", "dependencies": { - "@aws-sdk/client-sso": "3.806.0", - "@aws-sdk/core": "3.806.0", - "@aws-sdk/token-providers": "3.806.0", - "@aws-sdk/types": "3.804.0", - "@smithy/property-provider": "^4.0.2", - "@smithy/shared-ini-file-loader": "^4.0.2", - "@smithy/types": "^4.2.0", - "tslib": "^2.6.2" + "@babel/compat-data": "^7.27.2", + "@babel/helper-validator-option": "^7.27.1", + "browserslist": "^4.24.0", + "lru-cache": "^5.1.1", + "semver": "^6.3.1" }, "engines": { - "node": ">=18.0.0" + "node": ">=6.9.0" } }, - "node_modules/@aws-sdk/credential-provider-web-identity": { - "version": "3.806.0", - "license": "Apache-2.0", + "node_modules/@babel/helper-compilation-targets/node_modules/semver": { + "version": "6.3.1", + "dev": true, + "license": "ISC", + "bin": { + "semver": "bin/semver.js" + } + }, + "node_modules/@babel/helper-module-imports": { + "version": "7.27.1", + "dev": true, + "license": "MIT", "dependencies": { - "@aws-sdk/core": "3.806.0", - "@aws-sdk/nested-clients": "3.806.0", - "@aws-sdk/types": "3.804.0", - "@smithy/property-provider": "^4.0.2", - "@smithy/types": "^4.2.0", - "tslib": "^2.6.2" + "@babel/traverse": "^7.27.1", + "@babel/types": "^7.27.1" }, "engines": { - "node": ">=18.0.0" + "node": ">=6.9.0" } }, - "node_modules/@aws-sdk/eventstream-handler-node": { - "version": "3.804.0", - "license": "Apache-2.0", + "node_modules/@babel/helper-module-transforms": { + "version": "7.27.1", + "dev": true, + "license": "MIT", "dependencies": { - "@aws-sdk/types": "3.804.0", - "@smithy/eventstream-codec": "^4.0.2", - "@smithy/types": "^4.2.0", - "tslib": "^2.6.2" + "@babel/helper-module-imports": "^7.27.1", + "@babel/helper-validator-identifier": "^7.27.1", + "@babel/traverse": "^7.27.1" }, "engines": { - "node": ">=18.0.0" + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0" } }, - "node_modules/@aws-sdk/eventstream-handler-node/node_modules/@aws-crypto/crc32": { - "version": "5.2.0", - "license": "Apache-2.0", - "dependencies": { - "@aws-crypto/util": "^5.2.0", - "@aws-sdk/types": "^3.222.0", - "tslib": "^2.6.2" - }, + "node_modules/@babel/helper-plugin-utils": { + "version": "7.27.1", + "dev": true, + "license": "MIT", "engines": { - "node": ">=16.0.0" + "node": ">=6.9.0" } }, - "node_modules/@aws-sdk/eventstream-handler-node/node_modules/@smithy/eventstream-codec": { - "version": "4.0.2", - "license": "Apache-2.0", - "dependencies": { - "@aws-crypto/crc32": "5.2.0", - "@smithy/types": "^4.2.0", - "@smithy/util-hex-encoding": "^4.0.0", - "tslib": "^2.6.2" - }, + "node_modules/@babel/helper-string-parser": { + "version": "7.27.1", + "dev": true, + "license": "MIT", "engines": { - "node": ">=18.0.0" + "node": ">=6.9.0" } }, - "node_modules/@aws-sdk/eventstream-handler-node/node_modules/@smithy/util-hex-encoding": { - "version": "4.0.0", - "license": "Apache-2.0", - "dependencies": { - "tslib": "^2.6.2" - }, + "node_modules/@babel/helper-validator-identifier": { + "version": "7.27.1", + "dev": true, + "license": "MIT", "engines": { - "node": ">=18.0.0" + "node": ">=6.9.0" } }, - "node_modules/@aws-sdk/middleware-eventstream": { - "version": "3.804.0", - "license": "Apache-2.0", - "dependencies": { - "@aws-sdk/types": "3.804.0", - "@smithy/protocol-http": "^5.1.0", - "@smithy/types": "^4.2.0", - "tslib": "^2.6.2" - }, + "node_modules/@babel/helper-validator-option": { + "version": "7.27.1", + "dev": true, + "license": "MIT", "engines": { - "node": ">=18.0.0" + "node": ">=6.9.0" } }, - "node_modules/@aws-sdk/middleware-eventstream/node_modules/@smithy/protocol-http": { - "version": "5.1.0", - "license": "Apache-2.0", + "node_modules/@babel/helpers": { + "version": "7.27.1", + "dev": true, + "license": "MIT", "dependencies": { - "@smithy/types": "^4.2.0", - "tslib": "^2.6.2" + "@babel/template": "^7.27.1", + "@babel/types": "^7.27.1" }, "engines": { - "node": ">=18.0.0" + "node": ">=6.9.0" } }, - "node_modules/@aws-sdk/middleware-host-header": { - "version": "3.804.0", - "license": "Apache-2.0", + "node_modules/@babel/parser": { + "version": "7.27.2", + "dev": true, + "license": "MIT", "dependencies": { - "@aws-sdk/types": "3.804.0", - "@smithy/protocol-http": "^5.1.0", - "@smithy/types": "^4.2.0", - "tslib": "^2.6.2" + "@babel/types": "^7.27.1" + }, + "bin": { + "parser": "bin/babel-parser.js" }, "engines": { - "node": ">=18.0.0" + "node": ">=6.0.0" } }, - "node_modules/@aws-sdk/middleware-host-header/node_modules/@smithy/protocol-http": { - "version": "5.1.0", - "license": "Apache-2.0", + "node_modules/@babel/plugin-syntax-async-generators": { + "version": "7.8.4", + "dev": true, + "license": "MIT", "dependencies": { - "@smithy/types": "^4.2.0", - "tslib": "^2.6.2" + "@babel/helper-plugin-utils": "^7.8.0" }, - "engines": { - "node": ">=18.0.0" + "peerDependencies": { + "@babel/core": "^7.0.0-0" } }, - "node_modules/@aws-sdk/middleware-logger": { - "version": "3.804.0", - "license": "Apache-2.0", + "node_modules/@babel/plugin-syntax-bigint": { + "version": "7.8.3", + "dev": true, + "license": "MIT", "dependencies": { - "@aws-sdk/types": "3.804.0", - "@smithy/types": "^4.2.0", - "tslib": "^2.6.2" + "@babel/helper-plugin-utils": "^7.8.0" }, - "engines": { - "node": ">=18.0.0" + "peerDependencies": { + "@babel/core": "^7.0.0-0" } }, - "node_modules/@aws-sdk/middleware-recursion-detection": { - "version": "3.804.0", - "license": "Apache-2.0", + "node_modules/@babel/plugin-syntax-class-properties": { + "version": "7.12.13", + "dev": true, + "license": "MIT", "dependencies": { - "@aws-sdk/types": "3.804.0", - "@smithy/protocol-http": "^5.1.0", - "@smithy/types": "^4.2.0", - "tslib": "^2.6.2" + "@babel/helper-plugin-utils": "^7.12.13" }, - "engines": { - "node": ">=18.0.0" + "peerDependencies": { + "@babel/core": "^7.0.0-0" } }, - "node_modules/@aws-sdk/middleware-recursion-detection/node_modules/@smithy/protocol-http": { - "version": "5.1.0", - "license": "Apache-2.0", + "node_modules/@babel/plugin-syntax-class-static-block": { + "version": "7.14.5", + "dev": true, + "license": "MIT", "dependencies": { - "@smithy/types": "^4.2.0", - "tslib": "^2.6.2" + "@babel/helper-plugin-utils": "^7.14.5" }, "engines": { - "node": ">=18.0.0" + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" } }, - "node_modules/@aws-sdk/middleware-user-agent": { - "version": "3.806.0", - "license": "Apache-2.0", + "node_modules/@babel/plugin-syntax-import-attributes": { + "version": "7.27.1", + "dev": true, + "license": "MIT", "dependencies": { - "@aws-sdk/core": "3.806.0", - "@aws-sdk/types": "3.804.0", - "@aws-sdk/util-endpoints": "3.806.0", - "@smithy/core": "^3.3.1", - "@smithy/protocol-http": "^5.1.0", - "@smithy/types": "^4.2.0", - "tslib": "^2.6.2" + "@babel/helper-plugin-utils": "^7.27.1" }, "engines": { - "node": ">=18.0.0" + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" } }, - "node_modules/@aws-sdk/middleware-user-agent/node_modules/@smithy/protocol-http": { - "version": "5.1.0", - "license": "Apache-2.0", + "node_modules/@babel/plugin-syntax-import-meta": { + "version": "7.10.4", + "dev": true, + "license": "MIT", "dependencies": { - "@smithy/types": "^4.2.0", - "tslib": "^2.6.2" + "@babel/helper-plugin-utils": "^7.10.4" }, - "engines": { - "node": ">=18.0.0" + "peerDependencies": { + "@babel/core": "^7.0.0-0" } }, - "node_modules/@aws-sdk/nested-clients": { - "version": "3.806.0", - "license": "Apache-2.0", + "node_modules/@babel/plugin-syntax-json-strings": { + "version": "7.8.3", + "dev": true, + "license": "MIT", "dependencies": { - "@aws-crypto/sha256-browser": "5.2.0", - "@aws-crypto/sha256-js": "5.2.0", - "@aws-sdk/core": "3.806.0", - "@aws-sdk/middleware-host-header": "3.804.0", - "@aws-sdk/middleware-logger": "3.804.0", - "@aws-sdk/middleware-recursion-detection": "3.804.0", - "@aws-sdk/middleware-user-agent": "3.806.0", - "@aws-sdk/region-config-resolver": "3.806.0", - "@aws-sdk/types": "3.804.0", - "@aws-sdk/util-endpoints": "3.806.0", - "@aws-sdk/util-user-agent-browser": "3.804.0", - "@aws-sdk/util-user-agent-node": "3.806.0", - "@smithy/config-resolver": "^4.1.1", - "@smithy/core": "^3.3.1", - "@smithy/fetch-http-handler": "^5.0.2", - "@smithy/hash-node": "^4.0.2", - "@smithy/invalid-dependency": "^4.0.2", - "@smithy/middleware-content-length": "^4.0.2", - "@smithy/middleware-endpoint": "^4.1.3", - "@smithy/middleware-retry": "^4.1.4", - "@smithy/middleware-serde": "^4.0.3", - "@smithy/middleware-stack": "^4.0.2", - "@smithy/node-config-provider": "^4.1.0", - "@smithy/node-http-handler": "^4.0.4", - "@smithy/protocol-http": "^5.1.0", - "@smithy/smithy-client": "^4.2.3", - "@smithy/types": "^4.2.0", - "@smithy/url-parser": "^4.0.2", - "@smithy/util-base64": "^4.0.0", - "@smithy/util-body-length-browser": "^4.0.0", - "@smithy/util-body-length-node": "^4.0.0", - "@smithy/util-defaults-mode-browser": "^4.0.11", - "@smithy/util-defaults-mode-node": "^4.0.11", - "@smithy/util-endpoints": "^3.0.3", - "@smithy/util-middleware": "^4.0.2", - "@smithy/util-retry": "^4.0.3", - "@smithy/util-utf8": "^4.0.0", - "tslib": "^2.6.2" + "@babel/helper-plugin-utils": "^7.8.0" }, - "engines": { - "node": ">=18.0.0" + "peerDependencies": { + "@babel/core": "^7.0.0-0" } }, - "node_modules/@aws-sdk/nested-clients/node_modules/@smithy/protocol-http": { - "version": "5.1.0", - "license": "Apache-2.0", + "node_modules/@babel/plugin-syntax-jsx": { + "version": "7.27.1", + "dev": true, + "license": "MIT", "dependencies": { - "@smithy/types": "^4.2.0", - "tslib": "^2.6.2" + "@babel/helper-plugin-utils": "^7.27.1" }, "engines": { - "node": ">=18.0.0" + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" } }, - "node_modules/@aws-sdk/nested-clients/node_modules/@smithy/util-utf8": { - "version": "4.0.0", - "license": "Apache-2.0", + "node_modules/@babel/plugin-syntax-logical-assignment-operators": { + "version": "7.10.4", + "dev": true, + "license": "MIT", "dependencies": { - "@smithy/util-buffer-from": "^4.0.0", - "tslib": "^2.6.2" + "@babel/helper-plugin-utils": "^7.10.4" }, - "engines": { - "node": ">=18.0.0" + "peerDependencies": { + "@babel/core": "^7.0.0-0" } }, - "node_modules/@aws-sdk/region-config-resolver": { - "version": "3.806.0", - "license": "Apache-2.0", + "node_modules/@babel/plugin-syntax-nullish-coalescing-operator": { + "version": "7.8.3", + "dev": true, + "license": "MIT", "dependencies": { - "@aws-sdk/types": "3.804.0", - "@smithy/node-config-provider": "^4.1.0", - "@smithy/types": "^4.2.0", - "@smithy/util-config-provider": "^4.0.0", - "@smithy/util-middleware": "^4.0.2", - "tslib": "^2.6.2" + "@babel/helper-plugin-utils": "^7.8.0" }, - "engines": { - "node": ">=18.0.0" + "peerDependencies": { + "@babel/core": "^7.0.0-0" } }, - "node_modules/@aws-sdk/token-providers": { - "version": "3.806.0", - "license": "Apache-2.0", + "node_modules/@babel/plugin-syntax-numeric-separator": { + "version": "7.10.4", + "dev": true, + "license": "MIT", "dependencies": { - "@aws-sdk/nested-clients": "3.806.0", - "@aws-sdk/types": "3.804.0", - "@smithy/property-provider": "^4.0.2", - "@smithy/shared-ini-file-loader": "^4.0.2", - "@smithy/types": "^4.2.0", - "tslib": "^2.6.2" + "@babel/helper-plugin-utils": "^7.10.4" }, - "engines": { - "node": ">=18.0.0" + "peerDependencies": { + "@babel/core": "^7.0.0-0" } }, - "node_modules/@aws-sdk/types": { - "version": "3.804.0", - "license": "Apache-2.0", + "node_modules/@babel/plugin-syntax-object-rest-spread": { + "version": "7.8.3", + "dev": true, + "license": "MIT", "dependencies": { - "@smithy/types": "^4.2.0", - "tslib": "^2.6.2" + "@babel/helper-plugin-utils": "^7.8.0" }, - "engines": { - "node": ">=18.0.0" + "peerDependencies": { + "@babel/core": "^7.0.0-0" } }, - "node_modules/@aws-sdk/util-endpoints": { - "version": "3.806.0", - "license": "Apache-2.0", + "node_modules/@babel/plugin-syntax-optional-catch-binding": { + "version": "7.8.3", + "dev": true, + "license": "MIT", "dependencies": { - "@aws-sdk/types": "3.804.0", - "@smithy/types": "^4.2.0", - "@smithy/util-endpoints": "^3.0.3", - "tslib": "^2.6.2" + "@babel/helper-plugin-utils": "^7.8.0" }, - "engines": { - "node": ">=18.0.0" + "peerDependencies": { + "@babel/core": "^7.0.0-0" } }, - "node_modules/@aws-sdk/util-locate-window": { - "version": "3.804.0", - "license": "Apache-2.0", + "node_modules/@babel/plugin-syntax-optional-chaining": { + "version": "7.8.3", + "dev": true, + "license": "MIT", "dependencies": { - "tslib": "^2.6.2" + "@babel/helper-plugin-utils": "^7.8.0" }, - "engines": { - "node": ">=18.0.0" + "peerDependencies": { + "@babel/core": "^7.0.0-0" } }, - "node_modules/@aws-sdk/util-user-agent-browser": { - "version": "3.804.0", - "license": "Apache-2.0", + "node_modules/@babel/plugin-syntax-private-property-in-object": { + "version": "7.14.5", + "dev": true, + "license": "MIT", "dependencies": { - "@aws-sdk/types": "3.804.0", - "@smithy/types": "^4.2.0", - "bowser": "^2.11.0", - "tslib": "^2.6.2" + "@babel/helper-plugin-utils": "^7.14.5" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" } }, - "node_modules/@aws-sdk/util-user-agent-node": { - "version": "3.806.0", - "license": "Apache-2.0", + "node_modules/@babel/plugin-syntax-top-level-await": { + "version": "7.14.5", + "dev": true, + "license": "MIT", "dependencies": { - "@aws-sdk/middleware-user-agent": "3.806.0", - "@aws-sdk/types": "3.804.0", - "@smithy/node-config-provider": "^4.1.0", - "@smithy/types": "^4.2.0", - "tslib": "^2.6.2" + "@babel/helper-plugin-utils": "^7.14.5" }, "engines": { - "node": ">=18.0.0" + "node": ">=6.9.0" }, "peerDependencies": { - "aws-crt": ">=1.0.0" - }, - "peerDependenciesMeta": { - "aws-crt": { - "optional": true - } + "@babel/core": "^7.0.0-0" } }, - "node_modules/@azure-rest/core-client": { - "version": "2.5.0", - "resolved": "https://registry.npmjs.org/@azure-rest/core-client/-/core-client-2.5.0.tgz", - "integrity": "sha512-KMVIPxG6ygcQ1M2hKHahF7eddKejYsWTjoLIfTWiqnaj42dBkYzj4+S8rK9xxmlOaEHKZHcMrRbm0NfN4kgwHw==", + "node_modules/@babel/plugin-syntax-typescript": { + "version": "7.27.1", + "dev": true, "license": "MIT", "dependencies": { - "@azure/abort-controller": "^2.0.0", - "@azure/core-auth": "^1.9.0", - "@azure/core-rest-pipeline": "^1.5.0", - "@azure/core-tracing": "^1.0.1", - "@typespec/ts-http-runtime": "^0.3.0", - "tslib": "^2.6.2" + "@babel/helper-plugin-utils": "^7.27.1" }, "engines": { - "node": ">=20.0.0" + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" } }, - "node_modules/@azure/abort-controller": { - "version": "2.1.2", - "resolved": "https://registry.npmjs.org/@azure/abort-controller/-/abort-controller-2.1.2.tgz", - "integrity": "sha512-nBrLsEWm4J2u5LpAPjxADTlq3trDgVZZXHNKabeXZtpq3d3AbN/KGO82R87rdDz5/lYB024rtEf10/q0urNgsA==", + "node_modules/@babel/runtime": { + "version": "7.27.1", + "dev": true, "license": "MIT", - "dependencies": { - "tslib": "^2.6.2" - }, "engines": { - "node": ">=18.0.0" + "node": ">=6.9.0" } }, - "node_modules/@azure/ai-agents": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/@azure/ai-agents/-/ai-agents-1.1.0.tgz", - "integrity": "sha512-i8HFA7ql18t/otGrRfTWNOE5HgJf/RqedV3VNbFav5z9iTSexf8k4EeWOb/IWWaCsq0z/S7mihdGPAluPs+nXQ==", + "node_modules/@babel/template": { + "version": "7.27.2", + "dev": true, "license": "MIT", "dependencies": { - "@azure-rest/core-client": "^2.1.0", - "@azure/abort-controller": "^2.1.2", - "@azure/core-auth": "^1.6.0", - "@azure/core-lro": "^3.0.0", - "@azure/core-paging": "^1.5.0", - "@azure/core-rest-pipeline": "^1.5.0", - "@azure/core-sse": "^2.1.3", - "@azure/core-tracing": "^1.2.0", - "@azure/core-util": "^1.9.0", - "@azure/logger": "^1.1.4", - "tslib": "^2.6.2" + "@babel/code-frame": "^7.27.1", + "@babel/parser": "^7.27.2", + "@babel/types": "^7.27.1" }, "engines": { - "node": ">=20.0.0" + "node": ">=6.9.0" } }, - "node_modules/@azure/core-auth": { - "version": "1.10.0", - "resolved": "https://registry.npmjs.org/@azure/core-auth/-/core-auth-1.10.0.tgz", - "integrity": "sha512-88Djs5vBvGbHQHf5ZZcaoNHo6Y8BKZkt3cw2iuJIQzLEgH4Ox6Tm4hjFhbqOxyYsgIG/eJbFEHpxRIfEEWv5Ow==", + "node_modules/@babel/traverse": { + "version": "7.27.1", + "dev": true, "license": "MIT", "dependencies": { - "@azure/abort-controller": "^2.0.0", - "@azure/core-util": "^1.11.0", - "tslib": "^2.6.2" + "@babel/code-frame": "^7.27.1", + "@babel/generator": "^7.27.1", + "@babel/parser": "^7.27.1", + "@babel/template": "^7.27.1", + "@babel/types": "^7.27.1", + "debug": "^4.3.1", + "globals": "^11.1.0" }, "engines": { - "node": ">=20.0.0" + "node": ">=6.9.0" } }, - "node_modules/@azure/core-client": { - "version": "1.10.0", - "resolved": "https://registry.npmjs.org/@azure/core-client/-/core-client-1.10.0.tgz", - "integrity": "sha512-O4aP3CLFNodg8eTHXECaH3B3CjicfzkxVtnrfLkOq0XNP7TIECGfHpK/C6vADZkWP75wzmdBnsIA8ksuJMk18g==", + "node_modules/@babel/traverse/node_modules/globals": { + "version": "11.12.0", + "dev": true, "license": "MIT", - "dependencies": { - "@azure/abort-controller": "^2.0.0", - "@azure/core-auth": "^1.4.0", - "@azure/core-rest-pipeline": "^1.20.0", - "@azure/core-tracing": "^1.0.0", - "@azure/core-util": "^1.6.1", - "@azure/logger": "^1.0.0", - "tslib": "^2.6.2" - }, "engines": { - "node": ">=20.0.0" + "node": ">=4" } }, - "node_modules/@azure/core-lro": { - "version": "3.3.0", - "resolved": "https://registry.npmjs.org/@azure/core-lro/-/core-lro-3.3.0.tgz", - "integrity": "sha512-q8onFxe4O2iqPiURwnqAEO/x6oYkU+lHDWOOc16vPonhuNoKeisDPB8xzun25EClCTrd1xG51YfLGMlvKcB9mg==", + "node_modules/@babel/types": { + "version": "7.27.1", + "dev": true, "license": "MIT", "dependencies": { - "@azure/abort-controller": "^2.0.0", - "@azure/core-util": "^1.2.0", - "@azure/logger": "^1.0.0", - "tslib": "^2.6.2" + "@babel/helper-string-parser": "^7.27.1", + "@babel/helper-validator-identifier": "^7.27.1" }, "engines": { - "node": ">=20.0.0" + "node": ">=6.9.0" } }, - "node_modules/@azure/core-paging": { - "version": "1.6.2", - "resolved": "https://registry.npmjs.org/@azure/core-paging/-/core-paging-1.6.2.tgz", - "integrity": "sha512-YKWi9YuCU04B55h25cnOYZHxXYtEvQEbKST5vqRga7hWY9ydd3FZHdeQF8pyh+acWZvppw13M/LMGx0LABUVMA==", + "node_modules/@balena/dockerignore": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/@balena/dockerignore/-/dockerignore-1.0.2.tgz", + "integrity": "sha512-wMue2Sy4GAVTk6Ic4tJVcnfdau+gx2EnG7S+uAEe+TWJFqE4YoWN4/H8MSLj4eYJKxGg26lZwboEniNiNwZQ6Q==", + "dev": true + }, + "node_modules/@bcoe/v8-coverage": { + "version": "0.2.3", + "dev": true, + "license": "MIT" + }, + "node_modules/@colors/colors": { + "version": "1.5.0", + "dev": true, "license": "MIT", - "dependencies": { - "tslib": "^2.6.2" - }, + "optional": true, "engines": { - "node": ">=18.0.0" + "node": ">=0.1.90" } }, - "node_modules/@azure/core-rest-pipeline": { - "version": "1.22.0", - "resolved": "https://registry.npmjs.org/@azure/core-rest-pipeline/-/core-rest-pipeline-1.22.0.tgz", - "integrity": "sha512-OKHmb3/Kpm06HypvB3g6Q3zJuvyXcpxDpCS1PnU8OV6AJgSFaee/covXBcPbWc6XDDxtEPlbi3EMQ6nUiPaQtw==", + "node_modules/@cspotcode/source-map-support": { + "version": "0.8.1", + "devOptional": true, "license": "MIT", "dependencies": { - "@azure/abort-controller": "^2.0.0", - "@azure/core-auth": "^1.8.0", - "@azure/core-tracing": "^1.0.1", - "@azure/core-util": "^1.11.0", - "@azure/logger": "^1.0.0", - "@typespec/ts-http-runtime": "^0.3.0", - "tslib": "^2.6.2" + "@jridgewell/trace-mapping": "0.3.9" }, "engines": { - "node": ">=20.0.0" + "node": ">=12" } }, - "node_modules/@azure/core-sse": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/@azure/core-sse/-/core-sse-2.3.0.tgz", - "integrity": "sha512-jKhPpdDbVS5GlpadSKIC7V6Q4P2vEcwXi1c4CLTXs01Q/PAITES9v5J/S73+RtCMqQpsX0jGa2yPWwXi9JzdgA==", + "node_modules/@cspotcode/source-map-support/node_modules/@jridgewell/trace-mapping": { + "version": "0.3.9", + "devOptional": true, "license": "MIT", "dependencies": { - "tslib": "^2.6.2" - }, - "engines": { - "node": ">=20.0.0" + "@jridgewell/resolve-uri": "^3.0.3", + "@jridgewell/sourcemap-codec": "^1.4.10" } }, - "node_modules/@azure/core-tracing": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/@azure/core-tracing/-/core-tracing-1.3.0.tgz", - "integrity": "sha512-+XvmZLLWPe67WXNZo9Oc9CrPj/Tm8QnHR92fFAFdnbzwNdCH1h+7UdpaQgRSBsMY+oW1kHXNUZQLdZ1gHX3ROw==", + "node_modules/@dabh/diagnostics": { + "version": "2.0.3", "license": "MIT", "dependencies": { - "tslib": "^2.6.2" - }, - "engines": { - "node": ">=20.0.0" + "colorspace": "1.1.x", + "enabled": "2.0.x", + "kuler": "^2.0.0" } }, - "node_modules/@azure/core-util": { - "version": "1.13.0", - "resolved": "https://registry.npmjs.org/@azure/core-util/-/core-util-1.13.0.tgz", - "integrity": "sha512-o0psW8QWQ58fq3i24Q1K2XfS/jYTxr7O1HRcyUE9bV9NttLU+kYOH82Ixj8DGlMTOWgxm1Sss2QAfKK5UkSPxw==", + "node_modules/@eslint-community/eslint-utils": { + "version": "4.9.0", + "resolved": "https://registry.npmjs.org/@eslint-community/eslint-utils/-/eslint-utils-4.9.0.tgz", + "integrity": "sha512-ayVFHdtZ+hsq1t2Dy24wCmGXGe4q9Gu3smhLYALJrr473ZH27MsnSL+LKUlimp4BWJqMDMLmPpx/Q9R3OAlL4g==", + "dev": true, "license": "MIT", "dependencies": { - "@azure/abort-controller": "^2.0.0", - "@typespec/ts-http-runtime": "^0.3.0", - "tslib": "^2.6.2" + "eslint-visitor-keys": "^3.4.3" }, "engines": { - "node": ">=20.0.0" + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + }, + "funding": { + "url": "https://opencollective.com/eslint" + }, + "peerDependencies": { + "eslint": "^6.0.0 || ^7.0.0 || >=8.0.0" } }, - "node_modules/@azure/identity": { - "version": "4.11.0", - "resolved": "https://registry.npmjs.org/@azure/identity/-/identity-4.11.0.tgz", - "integrity": "sha512-GkbNnd3mrsL1gX3BxIblhahCfFEViLTfNMFgfSo4wPSH2ipw4duc1TtOPVOf8Wt6XTnjZROZRAvYqjJBWXV39g==", + "node_modules/@eslint-community/regexpp": { + "version": "4.12.1", + "dev": true, "license": "MIT", - "dependencies": { - "@azure/abort-controller": "^2.0.0", - "@azure/core-auth": "^1.9.0", - "@azure/core-client": "^1.9.2", - "@azure/core-rest-pipeline": "^1.17.0", - "@azure/core-tracing": "^1.0.0", - "@azure/core-util": "^1.11.0", - "@azure/logger": "^1.0.0", - "@azure/msal-browser": "^4.2.0", - "@azure/msal-node": "^3.5.0", - "open": "^10.1.0", - "tslib": "^2.2.0" - }, "engines": { - "node": ">=20.0.0" + "node": "^12.0.0 || ^14.0.0 || >=16.0.0" } }, - "node_modules/@azure/logger": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/@azure/logger/-/logger-1.3.0.tgz", - "integrity": "sha512-fCqPIfOcLE+CGqGPd66c8bZpwAji98tZ4JI9i/mlTNTlsIWslCfpg48s/ypyLxZTump5sypjrKn2/kY7q8oAbA==", - "license": "MIT", - "dependencies": { - "@typespec/ts-http-runtime": "^0.3.0", - "tslib": "^2.6.2" - }, + "node_modules/@eslint/compat": { + "version": "1.2.9", + "dev": true, + "license": "Apache-2.0", "engines": { - "node": ">=20.0.0" + "node": "^18.18.0 || ^20.9.0 || >=21.1.0" + }, + "peerDependencies": { + "eslint": "^9.10.0" + }, + "peerDependenciesMeta": { + "eslint": { + "optional": true + } } }, - "node_modules/@azure/msal-browser": { - "version": "4.18.0", - "resolved": "https://registry.npmjs.org/@azure/msal-browser/-/msal-browser-4.18.0.tgz", - "integrity": "sha512-esQwdtHHVkFJhcKWnysnCTchiKsy3dmNZGs8AckD9PO3t8Lp5VtY0xcrbCBC0JbttG/5w2/xukUQOsMpoUFKrg==", - "license": "MIT", + "node_modules/@eslint/config-array": { + "version": "0.21.0", + "resolved": "https://registry.npmjs.org/@eslint/config-array/-/config-array-0.21.0.tgz", + "integrity": "sha512-ENIdc4iLu0d93HeYirvKmrzshzofPw6VkZRKQGe9Nv46ZnWUzcF1xV01dcvEg/1wXUR61OmmlSfyeyO7EvjLxQ==", + "dev": true, "dependencies": { - "@azure/msal-common": "15.9.0" + "@eslint/object-schema": "^2.1.6", + "debug": "^4.3.1", + "minimatch": "^3.1.2" }, "engines": { - "node": ">=0.8.0" + "node": "^18.18.0 || ^20.9.0 || >=21.1.0" } }, - "node_modules/@azure/msal-common": { - "version": "15.9.0", - "resolved": "https://registry.npmjs.org/@azure/msal-common/-/msal-common-15.9.0.tgz", - "integrity": "sha512-lbz/D+C9ixUG3hiZzBLjU79a0+5ZXCorjel3mwXluisKNH0/rOS/ajm8yi4yI9RP5Uc70CAcs9Ipd0051Oh/kA==", - "license": "MIT", + "node_modules/@eslint/config-helpers": { + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/@eslint/config-helpers/-/config-helpers-0.4.0.tgz", + "integrity": "sha512-WUFvV4WoIwW8Bv0KeKCIIEgdSiFOsulyN0xrMu+7z43q/hkOLXjvb5u7UC9jDxvRzcrbEmuZBX5yJZz1741jog==", + "dev": true, + "license": "Apache-2.0", + "dependencies": { + "@eslint/core": "^0.16.0" + }, "engines": { - "node": ">=0.8.0" + "node": "^18.18.0 || ^20.9.0 || >=21.1.0" } }, - "node_modules/@azure/msal-node": { - "version": "3.6.4", - "resolved": "https://registry.npmjs.org/@azure/msal-node/-/msal-node-3.6.4.tgz", - "integrity": "sha512-jMeut9UQugcmq7aPWWlJKhJIse4DQ594zc/JaP6BIxg55XaX3aM/jcPuIQ4ryHnI4QSf03wUspy/uqAvjWKbOg==", - "license": "MIT", + "node_modules/@eslint/core": { + "version": "0.16.0", + "resolved": "https://registry.npmjs.org/@eslint/core/-/core-0.16.0.tgz", + "integrity": "sha512-nmC8/totwobIiFcGkDza3GIKfAw1+hLiYVrh3I1nIomQ8PEr5cxg34jnkmGawul/ep52wGRAcyeDCNtWKSOj4Q==", + "dev": true, + "license": "Apache-2.0", "dependencies": { - "@azure/msal-common": "15.9.0", - "jsonwebtoken": "^9.0.0", - "uuid": "^8.3.0" + "@types/json-schema": "^7.0.15" }, "engines": { - "node": ">=16" - } - }, - "node_modules/@azure/msal-node/node_modules/uuid": { - "version": "8.3.2", - "resolved": "https://registry.npmjs.org/uuid/-/uuid-8.3.2.tgz", - "integrity": "sha512-+NYs2QeMWy+GWFOEm9xnn6HCDp0l7QBD7ml8zLUmJ+93Q5NF0NocErnwkTkXVFNiX3/fpC6afS8Dhb/gz7R7eg==", - "license": "MIT", - "bin": { - "uuid": "dist/bin/uuid" + "node": "^18.18.0 || ^20.9.0 || >=21.1.0" } }, - "node_modules/@babel/code-frame": { - "version": "7.27.1", + "node_modules/@eslint/eslintrc": { + "version": "3.3.1", "dev": true, "license": "MIT", "dependencies": { - "@babel/helper-validator-identifier": "^7.27.1", - "js-tokens": "^4.0.0", - "picocolors": "^1.1.1" + "ajv": "^6.12.4", + "debug": "^4.3.2", + "espree": "^10.0.1", + "globals": "^14.0.0", + "ignore": "^5.2.0", + "import-fresh": "^3.2.1", + "js-yaml": "^4.1.0", + "minimatch": "^3.1.2", + "strip-json-comments": "^3.1.1" }, "engines": { - "node": ">=6.9.0" + "node": "^18.18.0 || ^20.9.0 || >=21.1.0" + }, + "funding": { + "url": "https://opencollective.com/eslint" } }, - "node_modules/@babel/compat-data": { - "version": "7.27.2", + "node_modules/@eslint/eslintrc/node_modules/globals": { + "version": "14.0.0", "dev": true, "license": "MIT", "engines": { - "node": ">=6.9.0" + "node": ">=18" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" } }, - "node_modules/@babel/core": { - "version": "7.27.1", + "node_modules/@eslint/js": { + "version": "9.31.0", + "resolved": "https://registry.npmjs.org/@eslint/js/-/js-9.31.0.tgz", + "integrity": "sha512-LOm5OVt7D4qiKCqoiPbA7LWmI+tbw1VbTUowBcUMgQSuM6poJufkFkYDcQpo5KfgD39TnNySV26QjOh7VFpSyw==", "dev": true, "license": "MIT", - "dependencies": { - "@ampproject/remapping": "^2.2.0", - "@babel/code-frame": "^7.27.1", - "@babel/generator": "^7.27.1", - "@babel/helper-compilation-targets": "^7.27.1", - "@babel/helper-module-transforms": "^7.27.1", - "@babel/helpers": "^7.27.1", - "@babel/parser": "^7.27.1", - "@babel/template": "^7.27.1", - "@babel/traverse": "^7.27.1", - "@babel/types": "^7.27.1", - "convert-source-map": "^2.0.0", - "debug": "^4.1.0", - "gensync": "^1.0.0-beta.2", - "json5": "^2.2.3", - "semver": "^6.3.1" - }, "engines": { - "node": ">=6.9.0" + "node": "^18.18.0 || ^20.9.0 || >=21.1.0" }, "funding": { - "type": "opencollective", - "url": "https://opencollective.com/babel" + "url": "https://eslint.org/donate" } }, - "node_modules/@babel/core/node_modules/semver": { - "version": "6.3.1", + "node_modules/@eslint/object-schema": { + "version": "2.1.6", + "resolved": "https://registry.npmjs.org/@eslint/object-schema/-/object-schema-2.1.6.tgz", + "integrity": "sha512-RBMg5FRL0I0gs51M/guSAj5/e14VQ4tpZnQNWwuDT66P14I43ItmPfIZRhO9fUVIPOAQXU47atlywZ/czoqFPA==", "dev": true, - "license": "ISC", - "bin": { - "semver": "bin/semver.js" + "engines": { + "node": "^18.18.0 || ^20.9.0 || >=21.1.0" } }, - "node_modules/@babel/generator": { - "version": "7.27.1", + "node_modules/@eslint/plugin-kit": { + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/@eslint/plugin-kit/-/plugin-kit-0.4.0.tgz", + "integrity": "sha512-sB5uyeq+dwCWyPi31B2gQlVlo+j5brPlWx4yZBrEaRo/nhdDE8Xke1gsGgtiBdaBTxuTkceLVuVt/pclrasb0A==", "dev": true, - "license": "MIT", + "license": "Apache-2.0", "dependencies": { - "@babel/parser": "^7.27.1", - "@babel/types": "^7.27.1", - "@jridgewell/gen-mapping": "^0.3.5", - "@jridgewell/trace-mapping": "^0.3.25", - "jsesc": "^3.0.2" + "@eslint/core": "^0.16.0", + "levn": "^0.4.1" }, "engines": { - "node": ">=6.9.0" + "node": "^18.18.0 || ^20.9.0 || >=21.1.0" } }, - "node_modules/@babel/helper-compilation-targets": { - "version": "7.27.2", - "dev": true, - "license": "MIT", + "node_modules/@grpc/grpc-js": { + "version": "1.13.3", + "license": "Apache-2.0", + "peer": true, "dependencies": { - "@babel/compat-data": "^7.27.2", - "@babel/helper-validator-option": "^7.27.1", - "browserslist": "^4.24.0", - "lru-cache": "^5.1.1", - "semver": "^6.3.1" + "@grpc/proto-loader": "^0.7.13", + "@js-sdsl/ordered-map": "^4.4.2" }, "engines": { - "node": ">=6.9.0" + "node": ">=12.10.0" } }, - "node_modules/@babel/helper-compilation-targets/node_modules/semver": { - "version": "6.3.1", - "dev": true, - "license": "ISC", + "node_modules/@grpc/proto-loader": { + "version": "0.7.15", + "license": "Apache-2.0", + "peer": true, + "dependencies": { + "lodash.camelcase": "^4.3.0", + "long": "^5.0.0", + "protobufjs": "^7.2.5", + "yargs": "^17.7.2" + }, "bin": { - "semver": "bin/semver.js" + "proto-loader-gen-types": "build/bin/proto-loader-gen-types.js" + }, + "engines": { + "node": ">=6" } }, - "node_modules/@babel/helper-module-imports": { - "version": "7.27.1", - "dev": true, + "node_modules/@grpc/proto-loader/node_modules/ansi-styles": { + "version": "4.3.0", "license": "MIT", "dependencies": { - "@babel/traverse": "^7.27.1", - "@babel/types": "^7.27.1" + "color-convert": "^2.0.1" }, "engines": { - "node": ">=6.9.0" + "node": ">=8" + }, + "funding": { + "url": "https://github.com/chalk/ansi-styles?sponsor=1" } }, - "node_modules/@babel/helper-module-transforms": { - "version": "7.27.1", - "dev": true, - "license": "MIT", + "node_modules/@grpc/proto-loader/node_modules/cliui": { + "version": "8.0.1", + "license": "ISC", "dependencies": { - "@babel/helper-module-imports": "^7.27.1", - "@babel/helper-validator-identifier": "^7.27.1", - "@babel/traverse": "^7.27.1" + "string-width": "^4.2.0", + "strip-ansi": "^6.0.1", + "wrap-ansi": "^7.0.0" }, "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0" + "node": ">=12" } }, - "node_modules/@babel/helper-plugin-utils": { - "version": "7.27.1", - "dev": true, + "node_modules/@grpc/proto-loader/node_modules/color-convert": { + "version": "2.0.1", "license": "MIT", + "dependencies": { + "color-name": "~1.1.4" + }, "engines": { - "node": ">=6.9.0" + "node": ">=7.0.0" } }, - "node_modules/@babel/helper-string-parser": { - "version": "7.27.1", - "dev": true, + "node_modules/@grpc/proto-loader/node_modules/color-name": { + "version": "1.1.4", + "license": "MIT" + }, + "node_modules/@grpc/proto-loader/node_modules/wrap-ansi": { + "version": "7.0.0", "license": "MIT", + "dependencies": { + "ansi-styles": "^4.0.0", + "string-width": "^4.1.0", + "strip-ansi": "^6.0.0" + }, "engines": { - "node": ">=6.9.0" + "node": ">=10" + }, + "funding": { + "url": "https://github.com/chalk/wrap-ansi?sponsor=1" } }, - "node_modules/@babel/helper-validator-identifier": { - "version": "7.27.1", - "dev": true, + "node_modules/@grpc/proto-loader/node_modules/yargs": { + "version": "17.7.2", "license": "MIT", + "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" + }, "engines": { - "node": ">=6.9.0" + "node": ">=12" } }, - "node_modules/@babel/helper-validator-option": { - "version": "7.27.1", + "node_modules/@humanfs/core": { + "version": "0.19.1", "dev": true, - "license": "MIT", + "license": "Apache-2.0", "engines": { - "node": ">=6.9.0" + "node": ">=18.18.0" } }, - "node_modules/@babel/helpers": { - "version": "7.27.1", + "node_modules/@humanfs/node": { + "version": "0.16.6", "dev": true, - "license": "MIT", + "license": "Apache-2.0", "dependencies": { - "@babel/template": "^7.27.1", - "@babel/types": "^7.27.1" + "@humanfs/core": "^0.19.1", + "@humanwhocodes/retry": "^0.3.0" }, "engines": { - "node": ">=6.9.0" + "node": ">=18.18.0" } }, - "node_modules/@babel/parser": { - "version": "7.27.2", + "node_modules/@humanfs/node/node_modules/@humanwhocodes/retry": { + "version": "0.3.1", "dev": true, - "license": "MIT", - "dependencies": { - "@babel/types": "^7.27.1" - }, - "bin": { - "parser": "bin/babel-parser.js" + "license": "Apache-2.0", + "engines": { + "node": ">=18.18" }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/nzakas" + } + }, + "node_modules/@humanwhocodes/module-importer": { + "version": "1.0.1", + "dev": true, + "license": "Apache-2.0", "engines": { - "node": ">=6.0.0" + "node": ">=12.22" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/nzakas" } }, - "node_modules/@babel/plugin-syntax-async-generators": { - "version": "7.8.4", + "node_modules/@humanwhocodes/retry": { + "version": "0.4.3", "dev": true, - "license": "MIT", - "dependencies": { - "@babel/helper-plugin-utils": "^7.8.0" + "license": "Apache-2.0", + "engines": { + "node": ">=18.18" }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" + "funding": { + "type": "github", + "url": "https://github.com/sponsors/nzakas" } }, - "node_modules/@babel/plugin-syntax-bigint": { - "version": "7.8.3", + "node_modules/@inquirer/checkbox": { + "version": "4.1.6", "dev": true, "license": "MIT", "dependencies": { - "@babel/helper-plugin-utils": "^7.8.0" + "@inquirer/core": "^10.1.11", + "@inquirer/figures": "^1.0.11", + "@inquirer/type": "^3.0.6", + "ansi-escapes": "^4.3.2", + "yoctocolors-cjs": "^2.1.2" + }, + "engines": { + "node": ">=18" }, "peerDependencies": { - "@babel/core": "^7.0.0-0" + "@types/node": ">=18" + }, + "peerDependenciesMeta": { + "@types/node": { + "optional": true + } } }, - "node_modules/@babel/plugin-syntax-class-properties": { - "version": "7.12.13", + "node_modules/@inquirer/confirm": { + "version": "5.1.10", "dev": true, "license": "MIT", "dependencies": { - "@babel/helper-plugin-utils": "^7.12.13" + "@inquirer/core": "^10.1.11", + "@inquirer/type": "^3.0.6" + }, + "engines": { + "node": ">=18" }, "peerDependencies": { - "@babel/core": "^7.0.0-0" + "@types/node": ">=18" + }, + "peerDependenciesMeta": { + "@types/node": { + "optional": true + } } }, - "node_modules/@babel/plugin-syntax-class-static-block": { - "version": "7.14.5", + "node_modules/@inquirer/core": { + "version": "10.1.11", "dev": true, "license": "MIT", "dependencies": { - "@babel/helper-plugin-utils": "^7.14.5" + "@inquirer/figures": "^1.0.11", + "@inquirer/type": "^3.0.6", + "ansi-escapes": "^4.3.2", + "cli-width": "^4.1.0", + "mute-stream": "^2.0.0", + "signal-exit": "^4.1.0", + "wrap-ansi": "^6.2.0", + "yoctocolors-cjs": "^2.1.2" }, "engines": { - "node": ">=6.9.0" + "node": ">=18" }, "peerDependencies": { - "@babel/core": "^7.0.0-0" + "@types/node": ">=18" + }, + "peerDependenciesMeta": { + "@types/node": { + "optional": true + } } }, - "node_modules/@babel/plugin-syntax-import-attributes": { - "version": "7.27.1", + "node_modules/@inquirer/editor": { + "version": "4.2.11", "dev": true, "license": "MIT", "dependencies": { - "@babel/helper-plugin-utils": "^7.27.1" + "@inquirer/core": "^10.1.11", + "@inquirer/type": "^3.0.6", + "external-editor": "^3.1.0" }, "engines": { - "node": ">=6.9.0" + "node": ">=18" }, "peerDependencies": { - "@babel/core": "^7.0.0-0" + "@types/node": ">=18" + }, + "peerDependenciesMeta": { + "@types/node": { + "optional": true + } } }, - "node_modules/@babel/plugin-syntax-import-meta": { - "version": "7.10.4", + "node_modules/@inquirer/expand": { + "version": "4.0.13", "dev": true, "license": "MIT", "dependencies": { - "@babel/helper-plugin-utils": "^7.10.4" + "@inquirer/core": "^10.1.11", + "@inquirer/type": "^3.0.6", + "yoctocolors-cjs": "^2.1.2" + }, + "engines": { + "node": ">=18" }, "peerDependencies": { - "@babel/core": "^7.0.0-0" + "@types/node": ">=18" + }, + "peerDependenciesMeta": { + "@types/node": { + "optional": true + } } }, - "node_modules/@babel/plugin-syntax-json-strings": { - "version": "7.8.3", + "node_modules/@inquirer/figures": { + "version": "1.0.11", "dev": true, "license": "MIT", - "dependencies": { - "@babel/helper-plugin-utils": "^7.8.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" + "engines": { + "node": ">=18" } }, - "node_modules/@babel/plugin-syntax-jsx": { - "version": "7.27.1", + "node_modules/@inquirer/input": { + "version": "4.1.10", "dev": true, "license": "MIT", "dependencies": { - "@babel/helper-plugin-utils": "^7.27.1" + "@inquirer/core": "^10.1.11", + "@inquirer/type": "^3.0.6" }, "engines": { - "node": ">=6.9.0" + "node": ">=18" }, "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-syntax-logical-assignment-operators": { - "version": "7.10.4", - "dev": true, - "license": "MIT", - "dependencies": { - "@babel/helper-plugin-utils": "^7.10.4" + "@types/node": ">=18" }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" + "peerDependenciesMeta": { + "@types/node": { + "optional": true + } } }, - "node_modules/@babel/plugin-syntax-nullish-coalescing-operator": { - "version": "7.8.3", + "node_modules/@inquirer/number": { + "version": "3.0.13", "dev": true, "license": "MIT", "dependencies": { - "@babel/helper-plugin-utils": "^7.8.0" + "@inquirer/core": "^10.1.11", + "@inquirer/type": "^3.0.6" }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-syntax-numeric-separator": { - "version": "7.10.4", - "dev": true, - "license": "MIT", - "dependencies": { - "@babel/helper-plugin-utils": "^7.10.4" + "engines": { + "node": ">=18" }, "peerDependencies": { - "@babel/core": "^7.0.0-0" + "@types/node": ">=18" + }, + "peerDependenciesMeta": { + "@types/node": { + "optional": true + } } }, - "node_modules/@babel/plugin-syntax-object-rest-spread": { - "version": "7.8.3", + "node_modules/@inquirer/password": { + "version": "4.0.13", "dev": true, "license": "MIT", "dependencies": { - "@babel/helper-plugin-utils": "^7.8.0" + "@inquirer/core": "^10.1.11", + "@inquirer/type": "^3.0.6", + "ansi-escapes": "^4.3.2" + }, + "engines": { + "node": ">=18" }, "peerDependencies": { - "@babel/core": "^7.0.0-0" + "@types/node": ">=18" + }, + "peerDependenciesMeta": { + "@types/node": { + "optional": true + } } }, - "node_modules/@babel/plugin-syntax-optional-catch-binding": { - "version": "7.8.3", + "node_modules/@inquirer/prompts": { + "version": "7.4.1", "dev": true, "license": "MIT", "dependencies": { - "@babel/helper-plugin-utils": "^7.8.0" + "@inquirer/checkbox": "^4.1.5", + "@inquirer/confirm": "^5.1.9", + "@inquirer/editor": "^4.2.10", + "@inquirer/expand": "^4.0.12", + "@inquirer/input": "^4.1.9", + "@inquirer/number": "^3.0.12", + "@inquirer/password": "^4.0.12", + "@inquirer/rawlist": "^4.0.12", + "@inquirer/search": "^3.0.12", + "@inquirer/select": "^4.1.1" + }, + "engines": { + "node": ">=18" }, "peerDependencies": { - "@babel/core": "^7.0.0-0" + "@types/node": ">=18" + }, + "peerDependenciesMeta": { + "@types/node": { + "optional": true + } } }, - "node_modules/@babel/plugin-syntax-optional-chaining": { - "version": "7.8.3", + "node_modules/@inquirer/rawlist": { + "version": "4.1.1", "dev": true, "license": "MIT", "dependencies": { - "@babel/helper-plugin-utils": "^7.8.0" + "@inquirer/core": "^10.1.11", + "@inquirer/type": "^3.0.6", + "yoctocolors-cjs": "^2.1.2" + }, + "engines": { + "node": ">=18" }, "peerDependencies": { - "@babel/core": "^7.0.0-0" + "@types/node": ">=18" + }, + "peerDependenciesMeta": { + "@types/node": { + "optional": true + } } }, - "node_modules/@babel/plugin-syntax-private-property-in-object": { - "version": "7.14.5", + "node_modules/@inquirer/search": { + "version": "3.0.13", "dev": true, "license": "MIT", "dependencies": { - "@babel/helper-plugin-utils": "^7.14.5" + "@inquirer/core": "^10.1.11", + "@inquirer/figures": "^1.0.11", + "@inquirer/type": "^3.0.6", + "yoctocolors-cjs": "^2.1.2" }, "engines": { - "node": ">=6.9.0" + "node": ">=18" }, "peerDependencies": { - "@babel/core": "^7.0.0-0" + "@types/node": ">=18" + }, + "peerDependenciesMeta": { + "@types/node": { + "optional": true + } } }, - "node_modules/@babel/plugin-syntax-top-level-await": { - "version": "7.14.5", + "node_modules/@inquirer/select": { + "version": "4.2.1", "dev": true, "license": "MIT", "dependencies": { - "@babel/helper-plugin-utils": "^7.14.5" + "@inquirer/core": "^10.1.11", + "@inquirer/figures": "^1.0.11", + "@inquirer/type": "^3.0.6", + "ansi-escapes": "^4.3.2", + "yoctocolors-cjs": "^2.1.2" }, "engines": { - "node": ">=6.9.0" + "node": ">=18" }, "peerDependencies": { - "@babel/core": "^7.0.0-0" + "@types/node": ">=18" + }, + "peerDependenciesMeta": { + "@types/node": { + "optional": true + } } }, - "node_modules/@babel/plugin-syntax-typescript": { - "version": "7.27.1", + "node_modules/@inquirer/type": { + "version": "3.0.6", "dev": true, "license": "MIT", - "dependencies": { - "@babel/helper-plugin-utils": "^7.27.1" - }, "engines": { - "node": ">=6.9.0" + "node": ">=18" }, "peerDependencies": { - "@babel/core": "^7.0.0-0" + "@types/node": ">=18" + }, + "peerDependenciesMeta": { + "@types/node": { + "optional": true + } } }, - "node_modules/@babel/runtime": { - "version": "7.27.1", + "node_modules/@isaacs/balanced-match": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/@isaacs/balanced-match/-/balanced-match-4.0.1.tgz", + "integrity": "sha512-yzMTt9lEb8Gv7zRioUilSglI0c0smZ9k5D65677DLWLtWJaXIS3CqcGyUFByYKlnUj6TkjLVs54fBl6+TiGQDQ==", "dev": true, "license": "MIT", "engines": { - "node": ">=6.9.0" + "node": "20 || >=22" } }, - "node_modules/@babel/template": { - "version": "7.27.2", + "node_modules/@isaacs/brace-expansion": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/@isaacs/brace-expansion/-/brace-expansion-5.0.0.tgz", + "integrity": "sha512-ZT55BDLV0yv0RBm2czMiZ+SqCGO7AvmOM3G/w2xhVPH+te0aKgFjmBvGlL1dH+ql2tgGO3MVrbb3jCKyvpgnxA==", "dev": true, "license": "MIT", "dependencies": { - "@babel/code-frame": "^7.27.1", - "@babel/parser": "^7.27.2", - "@babel/types": "^7.27.1" + "@isaacs/balanced-match": "^4.0.1" }, "engines": { - "node": ">=6.9.0" + "node": "20 || >=22" } }, - "node_modules/@babel/traverse": { - "version": "7.27.1", - "dev": true, - "license": "MIT", + "node_modules/@isaacs/cliui": { + "version": "8.0.2", + "license": "ISC", "dependencies": { - "@babel/code-frame": "^7.27.1", - "@babel/generator": "^7.27.1", - "@babel/parser": "^7.27.1", - "@babel/template": "^7.27.1", - "@babel/types": "^7.27.1", - "debug": "^4.3.1", - "globals": "^11.1.0" + "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" }, "engines": { - "node": ">=6.9.0" + "node": ">=12" } }, - "node_modules/@babel/traverse/node_modules/globals": { - "version": "11.12.0", - "dev": true, + "node_modules/@isaacs/cliui/node_modules/ansi-regex": { + "version": "6.1.0", "license": "MIT", "engines": { - "node": ">=4" + "node": ">=12" + }, + "funding": { + "url": "https://github.com/chalk/ansi-regex?sponsor=1" } }, - "node_modules/@babel/types": { - "version": "7.27.1", - "dev": true, + "node_modules/@isaacs/cliui/node_modules/ansi-styles": { + "version": "6.2.1", "license": "MIT", - "dependencies": { - "@babel/helper-string-parser": "^7.27.1", - "@babel/helper-validator-identifier": "^7.27.1" - }, "engines": { - "node": ">=6.9.0" + "node": ">=12" + }, + "funding": { + "url": "https://github.com/chalk/ansi-styles?sponsor=1" } }, - "node_modules/@balena/dockerignore": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/@balena/dockerignore/-/dockerignore-1.0.2.tgz", - "integrity": "sha512-wMue2Sy4GAVTk6Ic4tJVcnfdau+gx2EnG7S+uAEe+TWJFqE4YoWN4/H8MSLj4eYJKxGg26lZwboEniNiNwZQ6Q==", - "dev": true - }, - "node_modules/@bcoe/v8-coverage": { - "version": "0.2.3", - "dev": true, + "node_modules/@isaacs/cliui/node_modules/emoji-regex": { + "version": "9.2.2", "license": "MIT" }, - "node_modules/@browserbasehq/sdk": { - "version": "2.5.0", - "peer": true, - "dependencies": { - "@types/node": "^18.11.18", - "@types/node-fetch": "^2.6.4", - "abort-controller": "^3.0.0", - "agentkeepalive": "^4.2.1", - "form-data-encoder": "1.7.2", - "formdata-node": "^4.3.2", - "node-fetch": "^2.6.7" - } - }, - "node_modules/@browserbasehq/sdk/node_modules/@types/node": { - "version": "18.19.100", + "node_modules/@isaacs/cliui/node_modules/string-width": { + "version": "5.1.2", "license": "MIT", - "peer": true, "dependencies": { - "undici-types": "~5.26.4" + "eastasianwidth": "^0.2.0", + "emoji-regex": "^9.2.2", + "strip-ansi": "^7.0.1" + }, + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" } }, - "node_modules/@browserbasehq/sdk/node_modules/undici-types": { - "version": "5.26.5", + "node_modules/@isaacs/cliui/node_modules/strip-ansi": { + "version": "7.1.0", "license": "MIT", - "peer": true + "dependencies": { + "ansi-regex": "^6.0.1" + }, + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://github.com/chalk/strip-ansi?sponsor=1" + } }, - "node_modules/@browserbasehq/stagehand": { - "version": "1.14.0", + "node_modules/@isaacs/cliui/node_modules/wrap-ansi": { + "version": "8.1.0", "license": "MIT", - "peer": true, "dependencies": { - "@anthropic-ai/sdk": "^0.27.3", - "@browserbasehq/sdk": "^2.0.0", - "ws": "^8.18.0", - "zod-to-json-schema": "^3.23.5" + "ansi-styles": "^6.1.0", + "string-width": "^5.0.1", + "strip-ansi": "^7.0.1" }, - "peerDependencies": { - "@playwright/test": "^1.42.1", - "deepmerge": "^4.3.1", - "dotenv": "^16.4.5", - "openai": "^4.62.1", - "zod": "^3.23.8" + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://github.com/chalk/wrap-ansi?sponsor=1" } }, - "node_modules/@cfworker/json-schema": { - "version": "4.1.1", - "license": "MIT" + "node_modules/@istanbuljs/load-nyc-config": { + "version": "1.1.0", + "dev": true, + "license": "ISC", + "dependencies": { + "camelcase": "^5.3.1", + "find-up": "^4.1.0", + "get-package-type": "^0.1.0", + "js-yaml": "^3.13.1", + "resolve-from": "^5.0.0" + }, + "engines": { + "node": ">=8" + } }, - "node_modules/@colors/colors": { - "version": "1.5.0", + "node_modules/@istanbuljs/load-nyc-config/node_modules/argparse": { + "version": "1.0.10", + "dev": true, + "license": "MIT", + "dependencies": { + "sprintf-js": "~1.0.2" + } + }, + "node_modules/@istanbuljs/load-nyc-config/node_modules/camelcase": { + "version": "5.3.1", "dev": true, "license": "MIT", - "optional": true, "engines": { - "node": ">=0.1.90" + "node": ">=6" } }, - "node_modules/@cspotcode/source-map-support": { - "version": "0.8.1", - "devOptional": true, + "node_modules/@istanbuljs/load-nyc-config/node_modules/find-up": { + "version": "4.1.0", + "dev": true, "license": "MIT", "dependencies": { - "@jridgewell/trace-mapping": "0.3.9" + "locate-path": "^5.0.0", + "path-exists": "^4.0.0" }, "engines": { - "node": ">=12" + "node": ">=8" } }, - "node_modules/@cspotcode/source-map-support/node_modules/@jridgewell/trace-mapping": { - "version": "0.3.9", - "devOptional": true, + "node_modules/@istanbuljs/load-nyc-config/node_modules/js-yaml": { + "version": "3.14.1", + "dev": true, "license": "MIT", "dependencies": { - "@jridgewell/resolve-uri": "^3.0.3", - "@jridgewell/sourcemap-codec": "^1.4.10" + "argparse": "^1.0.7", + "esprima": "^4.0.0" + }, + "bin": { + "js-yaml": "bin/js-yaml.js" } }, - "node_modules/@dabh/diagnostics": { - "version": "2.0.3", + "node_modules/@istanbuljs/load-nyc-config/node_modules/locate-path": { + "version": "5.0.0", + "dev": true, "license": "MIT", "dependencies": { - "colorspace": "1.1.x", - "enabled": "2.0.x", - "kuler": "^2.0.0" + "p-locate": "^4.1.0" + }, + "engines": { + "node": ">=8" } }, - "node_modules/@eslint-community/eslint-utils": { - "version": "4.7.0", + "node_modules/@istanbuljs/load-nyc-config/node_modules/p-limit": { + "version": "2.3.0", "dev": true, "license": "MIT", "dependencies": { - "eslint-visitor-keys": "^3.4.3" + "p-try": "^2.0.0" }, "engines": { - "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + "node": ">=6" }, "funding": { - "url": "https://opencollective.com/eslint" + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/@istanbuljs/load-nyc-config/node_modules/p-locate": { + "version": "4.1.0", + "dev": true, + "license": "MIT", + "dependencies": { + "p-limit": "^2.2.0" }, - "peerDependencies": { - "eslint": "^6.0.0 || ^7.0.0 || >=8.0.0" + "engines": { + "node": ">=8" } }, - "node_modules/@eslint-community/regexpp": { - "version": "4.12.1", + "node_modules/@istanbuljs/load-nyc-config/node_modules/resolve-from": { + "version": "5.0.0", "dev": true, "license": "MIT", "engines": { - "node": "^12.0.0 || ^14.0.0 || >=16.0.0" + "node": ">=8" } }, - "node_modules/@eslint/compat": { - "version": "1.2.9", + "node_modules/@istanbuljs/load-nyc-config/node_modules/sprintf-js": { + "version": "1.0.3", "dev": true, - "license": "Apache-2.0", + "license": "BSD-3-Clause" + }, + "node_modules/@istanbuljs/schema": { + "version": "0.1.3", + "dev": true, + "license": "MIT", "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" + "node": ">=8" + } + }, + "node_modules/@jest/console": { + "version": "29.7.0", + "dev": true, + "license": "MIT", + "dependencies": { + "@jest/types": "^29.6.3", + "@types/node": "*", + "chalk": "^4.0.0", + "jest-message-util": "^29.7.0", + "jest-util": "^29.7.0", + "slash": "^3.0.0" + }, + "engines": { + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + } + }, + "node_modules/@jest/core": { + "version": "29.7.0", + "dev": true, + "license": "MIT", + "dependencies": { + "@jest/console": "^29.7.0", + "@jest/reporters": "^29.7.0", + "@jest/test-result": "^29.7.0", + "@jest/transform": "^29.7.0", + "@jest/types": "^29.6.3", + "@types/node": "*", + "ansi-escapes": "^4.2.1", + "chalk": "^4.0.0", + "ci-info": "^3.2.0", + "exit": "^0.1.2", + "graceful-fs": "^4.2.9", + "jest-changed-files": "^29.7.0", + "jest-config": "^29.7.0", + "jest-haste-map": "^29.7.0", + "jest-message-util": "^29.7.0", + "jest-regex-util": "^29.6.3", + "jest-resolve": "^29.7.0", + "jest-resolve-dependencies": "^29.7.0", + "jest-runner": "^29.7.0", + "jest-runtime": "^29.7.0", + "jest-snapshot": "^29.7.0", + "jest-util": "^29.7.0", + "jest-validate": "^29.7.0", + "jest-watcher": "^29.7.0", + "micromatch": "^4.0.4", + "pretty-format": "^29.7.0", + "slash": "^3.0.0", + "strip-ansi": "^6.0.0" + }, + "engines": { + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" }, "peerDependencies": { - "eslint": "^9.10.0" + "node-notifier": "^8.0.1 || ^9.0.0 || ^10.0.0" }, "peerDependenciesMeta": { - "eslint": { + "node-notifier": { "optional": true } } }, - "node_modules/@eslint/config-array": { - "version": "0.21.0", - "resolved": "https://registry.npmjs.org/@eslint/config-array/-/config-array-0.21.0.tgz", - "integrity": "sha512-ENIdc4iLu0d93HeYirvKmrzshzofPw6VkZRKQGe9Nv46ZnWUzcF1xV01dcvEg/1wXUR61OmmlSfyeyO7EvjLxQ==", + "node_modules/@jest/environment": { + "version": "29.7.0", "dev": true, + "license": "MIT", "dependencies": { - "@eslint/object-schema": "^2.1.6", - "debug": "^4.3.1", - "minimatch": "^3.1.2" + "@jest/fake-timers": "^29.7.0", + "@jest/types": "^29.6.3", + "@types/node": "*", + "jest-mock": "^29.7.0" }, "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" } }, - "node_modules/@eslint/config-helpers": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/@eslint/config-helpers/-/config-helpers-0.3.0.tgz", - "integrity": "sha512-ViuymvFmcJi04qdZeDc2whTHryouGcDlaxPqarTD0ZE10ISpxGUVZGZDx4w01upyIynL3iu6IXH2bS1NhclQMw==", + "node_modules/@jest/expect": { + "version": "29.7.0", "dev": true, + "license": "MIT", + "dependencies": { + "expect": "^29.7.0", + "jest-snapshot": "^29.7.0" + }, "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" } }, - "node_modules/@eslint/core": { - "version": "0.15.1", - "resolved": "https://registry.npmjs.org/@eslint/core/-/core-0.15.1.tgz", - "integrity": "sha512-bkOp+iumZCCbt1K1CmWf0R9pM5yKpDv+ZXtvSyQpudrI9kuFLp+bM2WOPXImuD/ceQuaa8f5pj93Y7zyECIGNA==", + "node_modules/@jest/expect-utils": { + "version": "29.7.0", "dev": true, - "license": "Apache-2.0", + "license": "MIT", "dependencies": { - "@types/json-schema": "^7.0.15" + "jest-get-type": "^29.6.3" }, "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" } }, - "node_modules/@eslint/eslintrc": { - "version": "3.3.1", + "node_modules/@jest/fake-timers": { + "version": "29.7.0", "dev": true, "license": "MIT", "dependencies": { - "ajv": "^6.12.4", - "debug": "^4.3.2", - "espree": "^10.0.1", - "globals": "^14.0.0", - "ignore": "^5.2.0", - "import-fresh": "^3.2.1", - "js-yaml": "^4.1.0", - "minimatch": "^3.1.2", - "strip-json-comments": "^3.1.1" + "@jest/types": "^29.6.3", + "@sinonjs/fake-timers": "^10.0.2", + "@types/node": "*", + "jest-message-util": "^29.7.0", + "jest-mock": "^29.7.0", + "jest-util": "^29.7.0" }, "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" - }, - "funding": { - "url": "https://opencollective.com/eslint" + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" } }, - "node_modules/@eslint/eslintrc/node_modules/globals": { - "version": "14.0.0", + "node_modules/@jest/globals": { + "version": "29.7.0", "dev": true, "license": "MIT", - "engines": { - "node": ">=18" + "dependencies": { + "@jest/environment": "^29.7.0", + "@jest/expect": "^29.7.0", + "@jest/types": "^29.6.3", + "jest-mock": "^29.7.0" }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" + "engines": { + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" } }, - "node_modules/@eslint/js": { - "version": "9.31.0", - "resolved": "https://registry.npmjs.org/@eslint/js/-/js-9.31.0.tgz", - "integrity": "sha512-LOm5OVt7D4qiKCqoiPbA7LWmI+tbw1VbTUowBcUMgQSuM6poJufkFkYDcQpo5KfgD39TnNySV26QjOh7VFpSyw==", + "node_modules/@jest/reporters": { + "version": "29.7.0", "dev": true, "license": "MIT", + "dependencies": { + "@bcoe/v8-coverage": "^0.2.3", + "@jest/console": "^29.7.0", + "@jest/test-result": "^29.7.0", + "@jest/transform": "^29.7.0", + "@jest/types": "^29.6.3", + "@jridgewell/trace-mapping": "^0.3.18", + "@types/node": "*", + "chalk": "^4.0.0", + "collect-v8-coverage": "^1.0.0", + "exit": "^0.1.2", + "glob": "^7.1.3", + "graceful-fs": "^4.2.9", + "istanbul-lib-coverage": "^3.0.0", + "istanbul-lib-instrument": "^6.0.0", + "istanbul-lib-report": "^3.0.0", + "istanbul-lib-source-maps": "^4.0.0", + "istanbul-reports": "^3.1.3", + "jest-message-util": "^29.7.0", + "jest-util": "^29.7.0", + "jest-worker": "^29.7.0", + "slash": "^3.0.0", + "string-length": "^4.0.1", + "strip-ansi": "^6.0.0", + "v8-to-istanbul": "^9.0.1" + }, "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" }, - "funding": { - "url": "https://eslint.org/donate" + "peerDependencies": { + "node-notifier": "^8.0.1 || ^9.0.0 || ^10.0.0" + }, + "peerDependenciesMeta": { + "node-notifier": { + "optional": true + } } }, - "node_modules/@eslint/object-schema": { - "version": "2.1.6", - "resolved": "https://registry.npmjs.org/@eslint/object-schema/-/object-schema-2.1.6.tgz", - "integrity": "sha512-RBMg5FRL0I0gs51M/guSAj5/e14VQ4tpZnQNWwuDT66P14I43ItmPfIZRhO9fUVIPOAQXU47atlywZ/czoqFPA==", + "node_modules/@jest/reporters/node_modules/glob": { + "version": "7.2.3", "dev": true, + "license": "ISC", + "dependencies": { + "fs.realpath": "^1.0.0", + "inflight": "^1.0.4", + "inherits": "2", + "minimatch": "^3.1.1", + "once": "^1.3.0", + "path-is-absolute": "^1.0.0" + }, "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" + "node": "*" + }, + "funding": { + "url": "https://github.com/sponsors/isaacs" } }, - "node_modules/@eslint/plugin-kit": { - "version": "0.3.4", - "resolved": "https://registry.npmjs.org/@eslint/plugin-kit/-/plugin-kit-0.3.4.tgz", - "integrity": "sha512-Ul5l+lHEcw3L5+k8POx6r74mxEYKG5kOb6Xpy2gCRW6zweT6TEhAf8vhxGgjhqrd/VO/Dirhsb+1hNpD1ue9hw==", + "node_modules/@jest/schemas": { + "version": "29.6.3", "dev": true, - "license": "Apache-2.0", + "license": "MIT", "dependencies": { - "@eslint/core": "^0.15.1", - "levn": "^0.4.1" + "@sinclair/typebox": "^0.27.8" }, "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" - } - }, - "node_modules/@google/generative-ai": { - "version": "0.24.1", - "license": "Apache-2.0", - "engines": { - "node": ">=18.0.0" + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" } }, - "node_modules/@graphql-typed-document-node/core": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/@graphql-typed-document-node/core/-/core-3.2.0.tgz", - "integrity": "sha512-mB9oAsNCm9aM3/SOv4YtBMqZbYj10R7dkq8byBqxGY/ncFwhf2oQzMV+LCRlWoDSEBJ3COiR1yeDvMtsoOsuFQ==", + "node_modules/@jest/source-map": { + "version": "29.6.3", + "dev": true, "license": "MIT", - "peerDependencies": { - "graphql": "^0.8.0 || ^0.9.0 || ^0.10.0 || ^0.11.0 || ^0.12.0 || ^0.13.0 || ^14.0.0 || ^15.0.0 || ^16.0.0 || ^17.0.0" - } - }, - "node_modules/@grpc/grpc-js": { - "version": "1.13.3", - "license": "Apache-2.0", "dependencies": { - "@grpc/proto-loader": "^0.7.13", - "@js-sdsl/ordered-map": "^4.4.2" + "@jridgewell/trace-mapping": "^0.3.18", + "callsites": "^3.0.0", + "graceful-fs": "^4.2.9" }, "engines": { - "node": ">=12.10.0" + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" } }, - "node_modules/@grpc/proto-loader": { - "version": "0.7.15", - "license": "Apache-2.0", + "node_modules/@jest/test-result": { + "version": "29.7.0", + "dev": true, + "license": "MIT", "dependencies": { - "lodash.camelcase": "^4.3.0", - "long": "^5.0.0", - "protobufjs": "^7.2.5", - "yargs": "^17.7.2" - }, - "bin": { - "proto-loader-gen-types": "build/bin/proto-loader-gen-types.js" + "@jest/console": "^29.7.0", + "@jest/types": "^29.6.3", + "@types/istanbul-lib-coverage": "^2.0.0", + "collect-v8-coverage": "^1.0.0" }, "engines": { - "node": ">=6" + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" } }, - "node_modules/@grpc/proto-loader/node_modules/ansi-styles": { - "version": "4.3.0", + "node_modules/@jest/test-sequencer": { + "version": "29.7.0", + "dev": true, "license": "MIT", "dependencies": { - "color-convert": "^2.0.1" + "@jest/test-result": "^29.7.0", + "graceful-fs": "^4.2.9", + "jest-haste-map": "^29.7.0", + "slash": "^3.0.0" }, "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" } }, - "node_modules/@grpc/proto-loader/node_modules/cliui": { - "version": "8.0.1", - "license": "ISC", + "node_modules/@jest/transform": { + "version": "29.7.0", + "dev": true, + "license": "MIT", "dependencies": { - "string-width": "^4.2.0", - "strip-ansi": "^6.0.1", - "wrap-ansi": "^7.0.0" + "@babel/core": "^7.11.6", + "@jest/types": "^29.6.3", + "@jridgewell/trace-mapping": "^0.3.18", + "babel-plugin-istanbul": "^6.1.1", + "chalk": "^4.0.0", + "convert-source-map": "^2.0.0", + "fast-json-stable-stringify": "^2.1.0", + "graceful-fs": "^4.2.9", + "jest-haste-map": "^29.7.0", + "jest-regex-util": "^29.6.3", + "jest-util": "^29.7.0", + "micromatch": "^4.0.4", + "pirates": "^4.0.4", + "slash": "^3.0.0", + "write-file-atomic": "^4.0.2" }, "engines": { - "node": ">=12" + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" } }, - "node_modules/@grpc/proto-loader/node_modules/color-convert": { - "version": "2.0.1", + "node_modules/@jest/types": { + "version": "29.6.3", + "dev": true, "license": "MIT", "dependencies": { - "color-name": "~1.1.4" + "@jest/schemas": "^29.6.3", + "@types/istanbul-lib-coverage": "^2.0.0", + "@types/istanbul-reports": "^3.0.0", + "@types/node": "*", + "@types/yargs": "^17.0.8", + "chalk": "^4.0.0" }, "engines": { - "node": ">=7.0.0" + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" } }, - "node_modules/@grpc/proto-loader/node_modules/color-name": { - "version": "1.1.4", - "license": "MIT" - }, - "node_modules/@grpc/proto-loader/node_modules/wrap-ansi": { - "version": "7.0.0", + "node_modules/@jridgewell/gen-mapping": { + "version": "0.3.8", + "dev": true, "license": "MIT", "dependencies": { - "ansi-styles": "^4.0.0", - "string-width": "^4.1.0", - "strip-ansi": "^6.0.0" + "@jridgewell/set-array": "^1.2.1", + "@jridgewell/sourcemap-codec": "^1.4.10", + "@jridgewell/trace-mapping": "^0.3.24" }, "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/chalk/wrap-ansi?sponsor=1" + "node": ">=6.0.0" } }, - "node_modules/@grpc/proto-loader/node_modules/yargs": { - "version": "17.7.2", + "node_modules/@jridgewell/resolve-uri": { + "version": "3.1.2", + "devOptional": true, "license": "MIT", - "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" - }, "engines": { - "node": ">=12" + "node": ">=6.0.0" } }, - "node_modules/@humanfs/core": { - "version": "0.19.1", + "node_modules/@jridgewell/set-array": { + "version": "1.2.1", "dev": true, - "license": "Apache-2.0", + "license": "MIT", "engines": { - "node": ">=18.18.0" + "node": ">=6.0.0" } }, - "node_modules/@humanfs/node": { - "version": "0.16.6", + "node_modules/@jridgewell/source-map": { + "version": "0.3.6", "dev": true, - "license": "Apache-2.0", + "license": "MIT", "dependencies": { - "@humanfs/core": "^0.19.1", - "@humanwhocodes/retry": "^0.3.0" - }, - "engines": { - "node": ">=18.18.0" + "@jridgewell/gen-mapping": "^0.3.5", + "@jridgewell/trace-mapping": "^0.3.25" } }, - "node_modules/@humanfs/node/node_modules/@humanwhocodes/retry": { - "version": "0.3.1", - "dev": true, - "license": "Apache-2.0", - "engines": { - "node": ">=18.18" - }, - "funding": { - "type": "github", - "url": "https://github.com/sponsors/nzakas" - } + "node_modules/@jridgewell/sourcemap-codec": { + "version": "1.5.0", + "devOptional": true, + "license": "MIT" }, - "node_modules/@humanwhocodes/module-importer": { - "version": "1.0.1", + "node_modules/@jridgewell/trace-mapping": { + "version": "0.3.25", "dev": true, - "license": "Apache-2.0", - "engines": { - "node": ">=12.22" - }, + "license": "MIT", + "dependencies": { + "@jridgewell/resolve-uri": "^3.1.0", + "@jridgewell/sourcemap-codec": "^1.4.14" + } + }, + "node_modules/@js-sdsl/ordered-map": { + "version": "4.4.2", + "license": "MIT", "funding": { - "type": "github", - "url": "https://github.com/sponsors/nzakas" + "type": "opencollective", + "url": "https://opencollective.com/js-sdsl" } }, - "node_modules/@humanwhocodes/retry": { - "version": "0.4.3", - "dev": true, - "license": "Apache-2.0", + "node_modules/@lukeed/csprng": { + "version": "1.1.0", + "license": "MIT", "engines": { - "node": ">=18.18" - }, - "funding": { - "type": "github", - "url": "https://github.com/sponsors/nzakas" + "node": ">=8" } }, - "node_modules/@ibm-cloud/watsonx-ai": { - "version": "1.6.4", - "license": "Apache-2.0", - "peer": true, + "node_modules/@microsoft/tsdoc": { + "version": "0.15.1", + "license": "MIT" + }, + "node_modules/@modelcontextprotocol/sdk": { + "version": "1.17.0", + "resolved": "https://registry.npmjs.org/@modelcontextprotocol/sdk/-/sdk-1.17.0.tgz", + "integrity": "sha512-qFfbWFA7r1Sd8D697L7GkTd36yqDuTkvz0KfOGkgXR8EUhQn3/EDNIR/qUdQNMT8IjmasBvHWuXeisxtXTQT2g==", + "license": "MIT", "dependencies": { - "@langchain/textsplitters": "^0.1.0", - "@types/node": "^18.0.0", - "extend": "3.0.2", - "ibm-cloud-sdk-core": "^5.3.2" + "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" }, "engines": { - "node": ">=18.0.0" + "node": ">=18" } }, - "node_modules/@ibm-cloud/watsonx-ai/node_modules/@types/node": { - "version": "18.19.100", - "license": "MIT", - "peer": true, - "dependencies": { - "undici-types": "~5.26.4" + "node_modules/@n8n/json-schema-to-zod": { + "version": "1.1.0", + "license": "SEE LICENSE IN LICENSE.md", + "peerDependencies": { + "zod": "^3.0.0" } }, - "node_modules/@ibm-cloud/watsonx-ai/node_modules/undici-types": { - "version": "5.26.5", + "node_modules/@nestjs/axios": { + "version": "4.0.0", + "devOptional": true, "license": "MIT", - "peer": true + "peer": true, + "peerDependencies": { + "@nestjs/common": "^10.0.0 || ^11.0.0", + "axios": "^1.3.1", + "rxjs": "^7.0.0" + } }, - "node_modules/@inquirer/checkbox": { - "version": "4.1.6", + "node_modules/@nestjs/cli": { + "version": "11.0.7", "dev": true, "license": "MIT", "dependencies": { - "@inquirer/core": "^10.1.11", - "@inquirer/figures": "^1.0.11", - "@inquirer/type": "^3.0.6", - "ansi-escapes": "^4.3.2", - "yoctocolors-cjs": "^2.1.2" + "@angular-devkit/core": "19.2.8", + "@angular-devkit/schematics": "19.2.8", + "@angular-devkit/schematics-cli": "19.2.8", + "@inquirer/prompts": "7.4.1", + "@nestjs/schematics": "^11.0.1", + "ansis": "3.17.0", + "chokidar": "4.0.3", + "cli-table3": "0.6.5", + "commander": "4.1.1", + "fork-ts-checker-webpack-plugin": "9.1.0", + "glob": "11.0.1", + "node-emoji": "1.11.0", + "ora": "5.4.1", + "tree-kill": "1.2.2", + "tsconfig-paths": "4.2.0", + "tsconfig-paths-webpack-plugin": "4.2.0", + "typescript": "5.8.3", + "webpack": "5.99.6", + "webpack-node-externals": "3.0.0" + }, + "bin": { + "nest": "bin/nest.js" }, "engines": { - "node": ">=18" + "node": ">= 20.11" }, "peerDependencies": { - "@types/node": ">=18" + "@swc/cli": "^0.1.62 || ^0.3.0 || ^0.4.0 || ^0.5.0 || ^0.6.0 || ^0.7.0", + "@swc/core": "^1.3.62" }, "peerDependenciesMeta": { - "@types/node": { + "@swc/cli": { + "optional": true + }, + "@swc/core": { "optional": true } } }, - "node_modules/@inquirer/confirm": { - "version": "5.1.10", + "node_modules/@nestjs/cli/node_modules/@angular-devkit/core": { + "version": "19.2.8", "dev": true, "license": "MIT", "dependencies": { - "@inquirer/core": "^10.1.11", - "@inquirer/type": "^3.0.6" + "ajv": "8.17.1", + "ajv-formats": "3.0.1", + "jsonc-parser": "3.3.1", + "picomatch": "4.0.2", + "rxjs": "7.8.1", + "source-map": "0.7.4" }, "engines": { - "node": ">=18" + "node": "^18.19.1 || ^20.11.1 || >=22.0.0", + "npm": "^6.11.0 || ^7.5.6 || >=8.0.0", + "yarn": ">= 1.13.0" }, "peerDependencies": { - "@types/node": ">=18" + "chokidar": "^4.0.0" }, "peerDependenciesMeta": { - "@types/node": { + "chokidar": { "optional": true } } }, - "node_modules/@inquirer/core": { - "version": "10.1.11", + "node_modules/@nestjs/cli/node_modules/ajv": { + "version": "8.17.1", "dev": true, "license": "MIT", + "peer": true, "dependencies": { - "@inquirer/figures": "^1.0.11", - "@inquirer/type": "^3.0.6", - "ansi-escapes": "^4.3.2", - "cli-width": "^4.1.0", - "mute-stream": "^2.0.0", - "signal-exit": "^4.1.0", - "wrap-ansi": "^6.2.0", - "yoctocolors-cjs": "^2.1.2" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "@types/node": ">=18" + "fast-deep-equal": "^3.1.3", + "fast-uri": "^3.0.1", + "json-schema-traverse": "^1.0.0", + "require-from-string": "^2.0.2" }, - "peerDependenciesMeta": { - "@types/node": { - "optional": true - } + "funding": { + "type": "github", + "url": "https://github.com/sponsors/epoberezkin" } }, - "node_modules/@inquirer/editor": { - "version": "4.2.11", + "node_modules/@nestjs/cli/node_modules/ajv-keywords": { + "version": "5.1.0", "dev": true, "license": "MIT", "dependencies": { - "@inquirer/core": "^10.1.11", - "@inquirer/type": "^3.0.6", - "external-editor": "^3.1.0" - }, - "engines": { - "node": ">=18" + "fast-deep-equal": "^3.1.3" }, "peerDependencies": { - "@types/node": ">=18" - }, - "peerDependenciesMeta": { - "@types/node": { - "optional": true - } + "ajv": "^8.8.2" } }, - "node_modules/@inquirer/expand": { - "version": "4.0.13", + "node_modules/@nestjs/cli/node_modules/chokidar": { + "version": "4.0.3", "dev": true, "license": "MIT", + "peer": true, "dependencies": { - "@inquirer/core": "^10.1.11", - "@inquirer/type": "^3.0.6", - "yoctocolors-cjs": "^2.1.2" + "readdirp": "^4.0.1" }, "engines": { - "node": ">=18" + "node": ">= 14.16.0" }, - "peerDependencies": { - "@types/node": ">=18" + "funding": { + "url": "https://paulmillr.com/funding/" + } + }, + "node_modules/@nestjs/cli/node_modules/eslint-scope": { + "version": "5.1.1", + "dev": true, + "license": "BSD-2-Clause", + "dependencies": { + "esrecurse": "^4.3.0", + "estraverse": "^4.1.1" }, - "peerDependenciesMeta": { - "@types/node": { - "optional": true - } + "engines": { + "node": ">=8.0.0" } }, - "node_modules/@inquirer/figures": { - "version": "1.0.11", + "node_modules/@nestjs/cli/node_modules/estraverse": { + "version": "4.3.0", "dev": true, - "license": "MIT", + "license": "BSD-2-Clause", "engines": { - "node": ">=18" + "node": ">=4.0" } }, - "node_modules/@inquirer/input": { - "version": "4.1.10", + "node_modules/@nestjs/cli/node_modules/json-schema-traverse": { + "version": "1.0.0", + "dev": true, + "license": "MIT" + }, + "node_modules/@nestjs/cli/node_modules/mime-db": { + "version": "1.52.0", "dev": true, "license": "MIT", - "dependencies": { - "@inquirer/core": "^10.1.11", - "@inquirer/type": "^3.0.6" - }, "engines": { - "node": ">=18" - }, - "peerDependencies": { - "@types/node": ">=18" - }, - "peerDependenciesMeta": { - "@types/node": { - "optional": true - } + "node": ">= 0.6" } }, - "node_modules/@inquirer/number": { - "version": "3.0.13", + "node_modules/@nestjs/cli/node_modules/mime-types": { + "version": "2.1.35", "dev": true, "license": "MIT", "dependencies": { - "@inquirer/core": "^10.1.11", - "@inquirer/type": "^3.0.6" + "mime-db": "1.52.0" }, "engines": { - "node": ">=18" - }, - "peerDependencies": { - "@types/node": ">=18" + "node": ">= 0.6" + } + }, + "node_modules/@nestjs/cli/node_modules/readdirp": { + "version": "4.1.2", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 14.18.0" }, - "peerDependenciesMeta": { - "@types/node": { - "optional": true - } + "funding": { + "type": "individual", + "url": "https://paulmillr.com/funding/" } }, - "node_modules/@inquirer/password": { - "version": "4.0.13", + "node_modules/@nestjs/cli/node_modules/rxjs": { + "version": "7.8.1", + "dev": true, + "license": "Apache-2.0", + "dependencies": { + "tslib": "^2.1.0" + } + }, + "node_modules/@nestjs/cli/node_modules/schema-utils": { + "version": "4.3.2", "dev": true, "license": "MIT", "dependencies": { - "@inquirer/core": "^10.1.11", - "@inquirer/type": "^3.0.6", - "ansi-escapes": "^4.3.2" + "@types/json-schema": "^7.0.9", + "ajv": "^8.9.0", + "ajv-formats": "^2.1.1", + "ajv-keywords": "^5.1.0" }, "engines": { - "node": ">=18" + "node": ">= 10.13.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/webpack" + } + }, + "node_modules/@nestjs/cli/node_modules/schema-utils/node_modules/ajv-formats": { + "version": "2.1.1", + "dev": true, + "license": "MIT", + "dependencies": { + "ajv": "^8.0.0" }, "peerDependencies": { - "@types/node": ">=18" + "ajv": "^8.0.0" }, "peerDependenciesMeta": { - "@types/node": { + "ajv": { "optional": true } } }, - "node_modules/@inquirer/prompts": { - "version": "7.4.1", + "node_modules/@nestjs/cli/node_modules/webpack": { + "version": "5.99.6", "dev": true, "license": "MIT", "dependencies": { - "@inquirer/checkbox": "^4.1.5", - "@inquirer/confirm": "^5.1.9", - "@inquirer/editor": "^4.2.10", - "@inquirer/expand": "^4.0.12", - "@inquirer/input": "^4.1.9", - "@inquirer/number": "^3.0.12", - "@inquirer/password": "^4.0.12", - "@inquirer/rawlist": "^4.0.12", - "@inquirer/search": "^3.0.12", - "@inquirer/select": "^4.1.1" + "@types/eslint-scope": "^3.7.7", + "@types/estree": "^1.0.6", + "@webassemblyjs/ast": "^1.14.1", + "@webassemblyjs/wasm-edit": "^1.14.1", + "@webassemblyjs/wasm-parser": "^1.14.1", + "acorn": "^8.14.0", + "browserslist": "^4.24.0", + "chrome-trace-event": "^1.0.2", + "enhanced-resolve": "^5.17.1", + "es-module-lexer": "^1.2.1", + "eslint-scope": "5.1.1", + "events": "^3.2.0", + "glob-to-regexp": "^0.4.1", + "graceful-fs": "^4.2.11", + "json-parse-even-better-errors": "^2.3.1", + "loader-runner": "^4.2.0", + "mime-types": "^2.1.27", + "neo-async": "^2.6.2", + "schema-utils": "^4.3.0", + "tapable": "^2.1.1", + "terser-webpack-plugin": "^5.3.11", + "watchpack": "^2.4.1", + "webpack-sources": "^3.2.3" + }, + "bin": { + "webpack": "bin/webpack.js" }, "engines": { - "node": ">=18" + "node": ">=10.13.0" }, - "peerDependencies": { - "@types/node": ">=18" + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/webpack" }, "peerDependenciesMeta": { - "@types/node": { + "webpack-cli": { "optional": true } } }, - "node_modules/@inquirer/rawlist": { - "version": "4.1.1", - "dev": true, + "node_modules/@nestjs/common": { + "version": "11.1.3", + "resolved": "https://registry.npmjs.org/@nestjs/common/-/common-11.1.3.tgz", + "integrity": "sha512-ogEK+GriWodIwCw6buQ1rpcH4Kx+G7YQ9EwuPySI3rS05pSdtQ++UhucjusSI9apNidv+QURBztJkRecwwJQXg==", "license": "MIT", + "peer": true, "dependencies": { - "@inquirer/core": "^10.1.11", - "@inquirer/type": "^3.0.6", - "yoctocolors-cjs": "^2.1.2" + "file-type": "21.0.0", + "iterare": "1.2.1", + "load-esm": "1.0.2", + "tslib": "2.8.1", + "uid": "2.0.2" }, - "engines": { - "node": ">=18" + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/nest" }, "peerDependencies": { - "@types/node": ">=18" + "class-transformer": ">=0.4.1", + "class-validator": ">=0.13.2", + "reflect-metadata": "^0.1.12 || ^0.2.0", + "rxjs": "^7.1.0" }, "peerDependenciesMeta": { - "@types/node": { + "class-transformer": { + "optional": true + }, + "class-validator": { "optional": true } } }, - "node_modules/@inquirer/search": { - "version": "3.0.13", - "dev": true, + "node_modules/@nestjs/config": { + "version": "4.0.2", "license": "MIT", "dependencies": { - "@inquirer/core": "^10.1.11", - "@inquirer/figures": "^1.0.11", - "@inquirer/type": "^3.0.6", - "yoctocolors-cjs": "^2.1.2" - }, - "engines": { - "node": ">=18" + "dotenv": "16.4.7", + "dotenv-expand": "12.0.1", + "lodash": "4.17.21" }, "peerDependencies": { - "@types/node": ">=18" + "@nestjs/common": "^10.0.0 || ^11.0.0", + "rxjs": "^7.1.0" + } + }, + "node_modules/@nestjs/config/node_modules/dotenv": { + "version": "16.4.7", + "license": "BSD-2-Clause", + "engines": { + "node": ">=12" }, - "peerDependenciesMeta": { - "@types/node": { - "optional": true - } + "funding": { + "url": "https://dotenvx.com" } }, - "node_modules/@inquirer/select": { - "version": "4.2.1", - "dev": true, + "node_modules/@nestjs/core": { + "version": "11.1.3", + "resolved": "https://registry.npmjs.org/@nestjs/core/-/core-11.1.3.tgz", + "integrity": "sha512-5lTni0TCh8x7bXETRD57pQFnKnEg1T6M+VLE7wAmyQRIecKQU+2inRGZD+A4v2DC1I04eA0WffP0GKLxjOKlzw==", + "hasInstallScript": true, "license": "MIT", + "peer": true, "dependencies": { - "@inquirer/core": "^10.1.11", - "@inquirer/figures": "^1.0.11", - "@inquirer/type": "^3.0.6", - "ansi-escapes": "^4.3.2", - "yoctocolors-cjs": "^2.1.2" + "@nuxt/opencollective": "0.4.1", + "fast-safe-stringify": "2.1.1", + "iterare": "1.2.1", + "path-to-regexp": "8.2.0", + "tslib": "2.8.1", + "uid": "2.0.2" }, "engines": { - "node": ">=18" + "node": ">= 20" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/nest" }, "peerDependencies": { - "@types/node": ">=18" + "@nestjs/common": "^11.0.0", + "@nestjs/microservices": "^11.0.0", + "@nestjs/platform-express": "^11.0.0", + "@nestjs/websockets": "^11.0.0", + "reflect-metadata": "^0.1.12 || ^0.2.0", + "rxjs": "^7.1.0" }, "peerDependenciesMeta": { - "@types/node": { + "@nestjs/microservices": { + "optional": true + }, + "@nestjs/platform-express": { + "optional": true + }, + "@nestjs/websockets": { "optional": true } } }, - "node_modules/@inquirer/type": { - "version": "3.0.6", - "dev": true, + "node_modules/@nestjs/cqrs": { + "version": "11.0.3", "license": "MIT", - "engines": { - "node": ">=18" - }, "peerDependencies": { - "@types/node": ">=18" + "@nestjs/common": "^10.0.0 || ^11.0.0", + "@nestjs/core": "^10.0.0 || ^11.0.0", + "reflect-metadata": "^0.1.13 || ^0.2.0", + "rxjs": "^7.2.0" + } + }, + "node_modules/@nestjs/mapped-types": { + "version": "2.1.0", + "license": "MIT", + "peerDependencies": { + "@nestjs/common": "^10.0.0 || ^11.0.0", + "class-transformer": "^0.4.0 || ^0.5.0", + "class-validator": "^0.13.0 || ^0.14.0", + "reflect-metadata": "^0.1.12 || ^0.2.0" }, "peerDependenciesMeta": { - "@types/node": { + "class-transformer": { + "optional": true + }, + "class-validator": { "optional": true } } }, - "node_modules/@isaacs/balanced-match": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/@isaacs/balanced-match/-/balanced-match-4.0.1.tgz", - "integrity": "sha512-yzMTt9lEb8Gv7zRioUilSglI0c0smZ9k5D65677DLWLtWJaXIS3CqcGyUFByYKlnUj6TkjLVs54fBl6+TiGQDQ==", - "dev": true, + "node_modules/@nestjs/passport": { + "version": "11.0.5", "license": "MIT", - "engines": { - "node": "20 || >=22" + "peerDependencies": { + "@nestjs/common": "^10.0.0 || ^11.0.0", + "passport": "^0.5.0 || ^0.6.0 || ^0.7.0" } }, - "node_modules/@isaacs/brace-expansion": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/@isaacs/brace-expansion/-/brace-expansion-5.0.0.tgz", - "integrity": "sha512-ZT55BDLV0yv0RBm2czMiZ+SqCGO7AvmOM3G/w2xhVPH+te0aKgFjmBvGlL1dH+ql2tgGO3MVrbb3jCKyvpgnxA==", - "dev": true, + "node_modules/@nestjs/platform-express": { + "version": "11.1.5", + "resolved": "https://registry.npmjs.org/@nestjs/platform-express/-/platform-express-11.1.5.tgz", + "integrity": "sha512-OsoiUBY9Shs5IG3uvDIt9/IDfY5OlvWBESuB/K4Eun8xILw1EK5d5qMfC3d2sIJ+kA3l+kBR1d/RuzH7VprLIg==", "license": "MIT", + "peer": true, "dependencies": { - "@isaacs/balanced-match": "^4.0.1" - }, - "engines": { - "node": "20 || >=22" - } - }, - "node_modules/@isaacs/cliui": { - "version": "8.0.2", - "license": "ISC", - "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" - }, - "engines": { - "node": ">=12" - } - }, - "node_modules/@isaacs/cliui/node_modules/ansi-regex": { - "version": "6.1.0", - "license": "MIT", - "engines": { - "node": ">=12" + "cors": "2.8.5", + "express": "5.1.0", + "multer": "2.0.2", + "path-to-regexp": "8.2.0", + "tslib": "2.8.1" }, "funding": { - "url": "https://github.com/chalk/ansi-regex?sponsor=1" - } - }, - "node_modules/@isaacs/cliui/node_modules/ansi-styles": { - "version": "6.2.1", - "license": "MIT", - "engines": { - "node": ">=12" + "type": "opencollective", + "url": "https://opencollective.com/nest" }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" + "peerDependencies": { + "@nestjs/common": "^11.0.0", + "@nestjs/core": "^11.0.0" } }, - "node_modules/@isaacs/cliui/node_modules/emoji-regex": { - "version": "9.2.2", - "license": "MIT" - }, - "node_modules/@isaacs/cliui/node_modules/string-width": { - "version": "5.1.2", + "node_modules/@nestjs/schematics": { + "version": "11.0.7", + "resolved": "https://registry.npmjs.org/@nestjs/schematics/-/schematics-11.0.7.tgz", + "integrity": "sha512-t8dNYYMwEeEsrlwc2jbkfwCfXczq4AeNEgx1KVQuJ6wYibXk0ZbXbPdfp8scnEAaQv1grpncNV5gWgzi7ZwbvQ==", + "dev": true, "license": "MIT", "dependencies": { - "eastasianwidth": "^0.2.0", - "emoji-regex": "^9.2.2", - "strip-ansi": "^7.0.1" - }, - "engines": { - "node": ">=12" + "@angular-devkit/core": "19.2.15", + "@angular-devkit/schematics": "19.2.15", + "comment-json": "4.2.5", + "jsonc-parser": "3.3.1", + "pluralize": "8.0.0" }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" + "peerDependencies": { + "typescript": ">=4.8.2" } }, - "node_modules/@isaacs/cliui/node_modules/strip-ansi": { - "version": "7.1.0", + "node_modules/@nestjs/schematics/node_modules/@angular-devkit/core": { + "version": "19.2.15", + "resolved": "https://registry.npmjs.org/@angular-devkit/core/-/core-19.2.15.tgz", + "integrity": "sha512-pU2RZYX6vhd7uLSdLwPnuBcr0mXJSjp3EgOXKsrlQFQZevc+Qs+2JdXgIElnOT/aDqtRtriDmLlSbtdE8n3ZbA==", + "dev": true, "license": "MIT", "dependencies": { - "ansi-regex": "^6.0.1" + "ajv": "8.17.1", + "ajv-formats": "3.0.1", + "jsonc-parser": "3.3.1", + "picomatch": "4.0.2", + "rxjs": "7.8.1", + "source-map": "0.7.4" }, "engines": { - "node": ">=12" - }, - "funding": { - "url": "https://github.com/chalk/strip-ansi?sponsor=1" - } - }, - "node_modules/@isaacs/cliui/node_modules/wrap-ansi": { - "version": "8.1.0", - "license": "MIT", - "dependencies": { - "ansi-styles": "^6.1.0", - "string-width": "^5.0.1", - "strip-ansi": "^7.0.1" + "node": "^18.19.1 || ^20.11.1 || >=22.0.0", + "npm": "^6.11.0 || ^7.5.6 || >=8.0.0", + "yarn": ">= 1.13.0" }, - "engines": { - "node": ">=12" + "peerDependencies": { + "chokidar": "^4.0.0" }, - "funding": { - "url": "https://github.com/chalk/wrap-ansi?sponsor=1" + "peerDependenciesMeta": { + "chokidar": { + "optional": true + } } }, - "node_modules/@istanbuljs/load-nyc-config": { - "version": "1.1.0", + "node_modules/@nestjs/schematics/node_modules/@angular-devkit/schematics": { + "version": "19.2.15", + "resolved": "https://registry.npmjs.org/@angular-devkit/schematics/-/schematics-19.2.15.tgz", + "integrity": "sha512-kNOJ+3vekJJCQKWihNmxBkarJzNW09kP5a9E1SRNiQVNOUEeSwcRR0qYotM65nx821gNzjjhJXnAZ8OazWldrg==", "dev": true, - "license": "ISC", + "license": "MIT", "dependencies": { - "camelcase": "^5.3.1", - "find-up": "^4.1.0", - "get-package-type": "^0.1.0", - "js-yaml": "^3.13.1", - "resolve-from": "^5.0.0" + "@angular-devkit/core": "19.2.15", + "jsonc-parser": "3.3.1", + "magic-string": "0.30.17", + "ora": "5.4.1", + "rxjs": "7.8.1" }, "engines": { - "node": ">=8" + "node": "^18.19.1 || ^20.11.1 || >=22.0.0", + "npm": "^6.11.0 || ^7.5.6 || >=8.0.0", + "yarn": ">= 1.13.0" } }, - "node_modules/@istanbuljs/load-nyc-config/node_modules/argparse": { - "version": "1.0.10", + "node_modules/@nestjs/schematics/node_modules/ajv": { + "version": "8.17.1", + "resolved": "https://registry.npmjs.org/ajv/-/ajv-8.17.1.tgz", + "integrity": "sha512-B/gBuNg5SiMTrPkC+A2+cW0RszwxYmn6VYxB/inlBStS5nx6xHIt/ehKRhIMhqusl7a8LjQoZnjCs5vhwxOQ1g==", "dev": true, "license": "MIT", "dependencies": { - "sprintf-js": "~1.0.2" + "fast-deep-equal": "^3.1.3", + "fast-uri": "^3.0.1", + "json-schema-traverse": "^1.0.0", + "require-from-string": "^2.0.2" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/epoberezkin" } }, - "node_modules/@istanbuljs/load-nyc-config/node_modules/camelcase": { - "version": "5.3.1", + "node_modules/@nestjs/schematics/node_modules/json-schema-traverse": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-1.0.0.tgz", + "integrity": "sha512-NM8/P9n3XjXhIZn1lLhkFaACTOURQXjWhV4BA/RnOv8xvgqtqpAX9IO4mRQxSx1Rlo4tqzeqb0sOlruaOy3dug==", "dev": true, - "license": "MIT", - "engines": { - "node": ">=6" - } + "license": "MIT" }, - "node_modules/@istanbuljs/load-nyc-config/node_modules/find-up": { - "version": "4.1.0", + "node_modules/@nestjs/schematics/node_modules/readdirp": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/readdirp/-/readdirp-4.1.2.tgz", + "integrity": "sha512-GDhwkLfywWL2s6vEjyhri+eXmfH6j1L7JE27WhqLeYzoh/A3DBaYGEj2H/HFZCn/kMfim73FXxEJTw06WtxQwg==", "dev": true, "license": "MIT", - "dependencies": { - "locate-path": "^5.0.0", - "path-exists": "^4.0.0" - }, + "optional": true, "engines": { - "node": ">=8" - } - }, - "node_modules/@istanbuljs/load-nyc-config/node_modules/js-yaml": { - "version": "3.14.1", - "dev": true, - "license": "MIT", - "dependencies": { - "argparse": "^1.0.7", - "esprima": "^4.0.0" + "node": ">= 14.18.0" }, - "bin": { - "js-yaml": "bin/js-yaml.js" + "funding": { + "type": "individual", + "url": "https://paulmillr.com/funding/" } }, - "node_modules/@istanbuljs/load-nyc-config/node_modules/locate-path": { - "version": "5.0.0", + "node_modules/@nestjs/schematics/node_modules/rxjs": { + "version": "7.8.1", + "resolved": "https://registry.npmjs.org/rxjs/-/rxjs-7.8.1.tgz", + "integrity": "sha512-AA3TVj+0A2iuIoQkWEK/tqFjBq2j+6PO6Y0zJcvzLAFhEFIO3HL0vls9hWLncZbAAbK0mar7oZ4V079I/qPMxg==", "dev": true, - "license": "MIT", + "license": "Apache-2.0", "dependencies": { - "p-locate": "^4.1.0" - }, - "engines": { - "node": ">=8" + "tslib": "^2.1.0" } }, - "node_modules/@istanbuljs/load-nyc-config/node_modules/p-limit": { - "version": "2.3.0", - "dev": true, + "node_modules/@nestjs/swagger": { + "version": "11.2.0", "license": "MIT", "dependencies": { - "p-try": "^2.0.0" + "@microsoft/tsdoc": "0.15.1", + "@nestjs/mapped-types": "2.1.0", + "js-yaml": "4.1.0", + "lodash": "4.17.21", + "path-to-regexp": "8.2.0", + "swagger-ui-dist": "5.21.0" }, - "engines": { - "node": ">=6" + "peerDependencies": { + "@fastify/static": "^8.0.0", + "@nestjs/common": "^11.0.1", + "@nestjs/core": "^11.0.1", + "class-transformer": "*", + "class-validator": "*", + "reflect-metadata": "^0.1.12 || ^0.2.0" }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" + "peerDependenciesMeta": { + "@fastify/static": { + "optional": true + }, + "class-transformer": { + "optional": true + }, + "class-validator": { + "optional": true + } } }, - "node_modules/@istanbuljs/load-nyc-config/node_modules/p-locate": { - "version": "4.1.0", - "dev": true, + "node_modules/@nestjs/terminus": { + "version": "11.0.0", "license": "MIT", "dependencies": { - "p-limit": "^2.2.0" + "boxen": "5.1.2", + "check-disk-space": "3.4.0" }, - "engines": { - "node": ">=8" - } - }, - "node_modules/@istanbuljs/load-nyc-config/node_modules/resolve-from": { - "version": "5.0.0", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=8" - } - }, - "node_modules/@istanbuljs/load-nyc-config/node_modules/sprintf-js": { - "version": "1.0.3", - "dev": true, - "license": "BSD-3-Clause" - }, - "node_modules/@istanbuljs/schema": { - "version": "0.1.3", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=8" - } - }, - "node_modules/@jest/console": { - "version": "29.7.0", - "dev": true, - "license": "MIT", - "dependencies": { - "@jest/types": "^29.6.3", - "@types/node": "*", - "chalk": "^4.0.0", - "jest-message-util": "^29.7.0", - "jest-util": "^29.7.0", - "slash": "^3.0.0" + "peerDependencies": { + "@grpc/grpc-js": "*", + "@grpc/proto-loader": "*", + "@mikro-orm/core": "*", + "@mikro-orm/nestjs": "*", + "@nestjs/axios": "^2.0.0 || ^3.0.0 || ^4.0.0", + "@nestjs/common": "^10.0.0 || ^11.0.0", + "@nestjs/core": "^10.0.0 || ^11.0.0", + "@nestjs/microservices": "^10.0.0 || ^11.0.0", + "@nestjs/mongoose": "^11.0.0", + "@nestjs/sequelize": "^10.0.0 || ^11.0.0", + "@nestjs/typeorm": "^10.0.0 || ^11.0.0", + "@prisma/client": "*", + "mongoose": "*", + "reflect-metadata": "0.1.x || 0.2.x", + "rxjs": "7.x", + "sequelize": "*", + "typeorm": "*" }, - "engines": { - "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + "peerDependenciesMeta": { + "@grpc/grpc-js": { + "optional": true + }, + "@grpc/proto-loader": { + "optional": true + }, + "@mikro-orm/core": { + "optional": true + }, + "@mikro-orm/nestjs": { + "optional": true + }, + "@nestjs/axios": { + "optional": true + }, + "@nestjs/microservices": { + "optional": true + }, + "@nestjs/mongoose": { + "optional": true + }, + "@nestjs/sequelize": { + "optional": true + }, + "@nestjs/typeorm": { + "optional": true + }, + "@prisma/client": { + "optional": true + }, + "mongoose": { + "optional": true + }, + "sequelize": { + "optional": true + }, + "typeorm": { + "optional": true + } } }, - "node_modules/@jest/core": { - "version": "29.7.0", + "node_modules/@nestjs/testing": { + "version": "11.1.5", + "resolved": "https://registry.npmjs.org/@nestjs/testing/-/testing-11.1.5.tgz", + "integrity": "sha512-ZYRYF750SefmuIo7ZqPlHDcin1OHh6My0OkOfGEFjrD9mJ0vMVIpwMTOOkpzCfCcpqUuxeHBuecpiIn+NLrQbQ==", "dev": true, "license": "MIT", "dependencies": { - "@jest/console": "^29.7.0", - "@jest/reporters": "^29.7.0", - "@jest/test-result": "^29.7.0", - "@jest/transform": "^29.7.0", - "@jest/types": "^29.6.3", - "@types/node": "*", - "ansi-escapes": "^4.2.1", - "chalk": "^4.0.0", - "ci-info": "^3.2.0", - "exit": "^0.1.2", - "graceful-fs": "^4.2.9", - "jest-changed-files": "^29.7.0", - "jest-config": "^29.7.0", - "jest-haste-map": "^29.7.0", - "jest-message-util": "^29.7.0", - "jest-regex-util": "^29.6.3", - "jest-resolve": "^29.7.0", - "jest-resolve-dependencies": "^29.7.0", - "jest-runner": "^29.7.0", - "jest-runtime": "^29.7.0", - "jest-snapshot": "^29.7.0", - "jest-util": "^29.7.0", - "jest-validate": "^29.7.0", - "jest-watcher": "^29.7.0", - "micromatch": "^4.0.4", - "pretty-format": "^29.7.0", - "slash": "^3.0.0", - "strip-ansi": "^6.0.0" + "tslib": "2.8.1" }, - "engines": { - "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/nest" }, "peerDependencies": { - "node-notifier": "^8.0.1 || ^9.0.0 || ^10.0.0" + "@nestjs/common": "^11.0.0", + "@nestjs/core": "^11.0.0", + "@nestjs/microservices": "^11.0.0", + "@nestjs/platform-express": "^11.0.0" }, "peerDependenciesMeta": { - "node-notifier": { + "@nestjs/microservices": { + "optional": true + }, + "@nestjs/platform-express": { "optional": true } } }, - "node_modules/@jest/environment": { - "version": "29.7.0", - "dev": true, - "license": "MIT", - "dependencies": { - "@jest/fake-timers": "^29.7.0", - "@jest/types": "^29.6.3", - "@types/node": "*", - "jest-mock": "^29.7.0" - }, - "engines": { - "node": "^14.15.0 || ^16.10.0 || >=18.0.0" - } - }, - "node_modules/@jest/expect": { - "version": "29.7.0", - "dev": true, - "license": "MIT", - "dependencies": { - "expect": "^29.7.0", - "jest-snapshot": "^29.7.0" - }, - "engines": { - "node": "^14.15.0 || ^16.10.0 || >=18.0.0" - } - }, - "node_modules/@jest/expect-utils": { - "version": "29.7.0", - "dev": true, + "node_modules/@nestjs/typeorm": { + "version": "11.0.0", "license": "MIT", - "dependencies": { - "jest-get-type": "^29.6.3" - }, - "engines": { - "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + "peer": true, + "peerDependencies": { + "@nestjs/common": "^10.0.0 || ^11.0.0", + "@nestjs/core": "^10.0.0 || ^11.0.0", + "reflect-metadata": "^0.1.13 || ^0.2.0", + "rxjs": "^7.2.0", + "typeorm": "^0.3.0" } }, - "node_modules/@jest/fake-timers": { - "version": "29.7.0", + "node_modules/@noble/hashes": { + "version": "1.8.0", + "resolved": "https://registry.npmjs.org/@noble/hashes/-/hashes-1.8.0.tgz", + "integrity": "sha512-jCs9ldd7NwzpgXDIf6P3+NrHh9/sD6CQdxHyjQI+h/6rDNo88ypBxxz45UDuZHz9r3tNz7N/VInSVoVdtXEI4A==", "dev": true, - "license": "MIT", - "dependencies": { - "@jest/types": "^29.6.3", - "@sinonjs/fake-timers": "^10.0.2", - "@types/node": "*", - "jest-message-util": "^29.7.0", - "jest-mock": "^29.7.0", - "jest-util": "^29.7.0" - }, "engines": { - "node": "^14.15.0 || ^16.10.0 || >=18.0.0" - } - }, - "node_modules/@jest/globals": { - "version": "29.7.0", - "dev": true, - "license": "MIT", - "dependencies": { - "@jest/environment": "^29.7.0", - "@jest/expect": "^29.7.0", - "@jest/types": "^29.6.3", - "jest-mock": "^29.7.0" + "node": "^14.21.3 || >=16" }, - "engines": { - "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + "funding": { + "url": "https://paulmillr.com/funding/" } }, - "node_modules/@jest/reporters": { - "version": "29.7.0", + "node_modules/@nodelib/fs.scandir": { + "version": "2.1.5", + "resolved": "https://registry.npmjs.org/@nodelib/fs.scandir/-/fs.scandir-2.1.5.tgz", + "integrity": "sha512-vq24Bq3ym5HEQm2NKCr3yXDwjc7vTsEThRDnkp2DK9p1uqLR+DHurm/NOTo0KG7HYHU7eppKZj3MyqYuMBf62g==", "dev": true, "license": "MIT", "dependencies": { - "@bcoe/v8-coverage": "^0.2.3", - "@jest/console": "^29.7.0", - "@jest/test-result": "^29.7.0", - "@jest/transform": "^29.7.0", - "@jest/types": "^29.6.3", - "@jridgewell/trace-mapping": "^0.3.18", - "@types/node": "*", - "chalk": "^4.0.0", - "collect-v8-coverage": "^1.0.0", - "exit": "^0.1.2", - "glob": "^7.1.3", - "graceful-fs": "^4.2.9", - "istanbul-lib-coverage": "^3.0.0", - "istanbul-lib-instrument": "^6.0.0", - "istanbul-lib-report": "^3.0.0", - "istanbul-lib-source-maps": "^4.0.0", - "istanbul-reports": "^3.1.3", - "jest-message-util": "^29.7.0", - "jest-util": "^29.7.0", - "jest-worker": "^29.7.0", - "slash": "^3.0.0", - "string-length": "^4.0.1", - "strip-ansi": "^6.0.0", - "v8-to-istanbul": "^9.0.1" + "@nodelib/fs.stat": "2.0.5", + "run-parallel": "^1.1.9" }, "engines": { - "node": "^14.15.0 || ^16.10.0 || >=18.0.0" - }, - "peerDependencies": { - "node-notifier": "^8.0.1 || ^9.0.0 || ^10.0.0" - }, - "peerDependenciesMeta": { - "node-notifier": { - "optional": true - } - } - }, - "node_modules/@jest/reporters/node_modules/glob": { - "version": "7.2.3", - "dev": true, - "license": "ISC", - "dependencies": { - "fs.realpath": "^1.0.0", - "inflight": "^1.0.4", - "inherits": "2", - "minimatch": "^3.1.1", - "once": "^1.3.0", - "path-is-absolute": "^1.0.0" - }, - "engines": { - "node": "*" - }, - "funding": { - "url": "https://github.com/sponsors/isaacs" - } - }, - "node_modules/@jest/schemas": { - "version": "29.6.3", - "dev": true, - "license": "MIT", - "dependencies": { - "@sinclair/typebox": "^0.27.8" - }, - "engines": { - "node": "^14.15.0 || ^16.10.0 || >=18.0.0" - } - }, - "node_modules/@jest/source-map": { - "version": "29.6.3", - "dev": true, - "license": "MIT", - "dependencies": { - "@jridgewell/trace-mapping": "^0.3.18", - "callsites": "^3.0.0", - "graceful-fs": "^4.2.9" - }, - "engines": { - "node": "^14.15.0 || ^16.10.0 || >=18.0.0" - } - }, - "node_modules/@jest/test-result": { - "version": "29.7.0", - "dev": true, - "license": "MIT", - "dependencies": { - "@jest/console": "^29.7.0", - "@jest/types": "^29.6.3", - "@types/istanbul-lib-coverage": "^2.0.0", - "collect-v8-coverage": "^1.0.0" - }, - "engines": { - "node": "^14.15.0 || ^16.10.0 || >=18.0.0" - } - }, - "node_modules/@jest/test-sequencer": { - "version": "29.7.0", - "dev": true, - "license": "MIT", - "dependencies": { - "@jest/test-result": "^29.7.0", - "graceful-fs": "^4.2.9", - "jest-haste-map": "^29.7.0", - "slash": "^3.0.0" - }, - "engines": { - "node": "^14.15.0 || ^16.10.0 || >=18.0.0" - } - }, - "node_modules/@jest/transform": { - "version": "29.7.0", - "dev": true, - "license": "MIT", - "dependencies": { - "@babel/core": "^7.11.6", - "@jest/types": "^29.6.3", - "@jridgewell/trace-mapping": "^0.3.18", - "babel-plugin-istanbul": "^6.1.1", - "chalk": "^4.0.0", - "convert-source-map": "^2.0.0", - "fast-json-stable-stringify": "^2.1.0", - "graceful-fs": "^4.2.9", - "jest-haste-map": "^29.7.0", - "jest-regex-util": "^29.6.3", - "jest-util": "^29.7.0", - "micromatch": "^4.0.4", - "pirates": "^4.0.4", - "slash": "^3.0.0", - "write-file-atomic": "^4.0.2" - }, - "engines": { - "node": "^14.15.0 || ^16.10.0 || >=18.0.0" - } - }, - "node_modules/@jest/types": { - "version": "29.6.3", - "dev": true, - "license": "MIT", - "dependencies": { - "@jest/schemas": "^29.6.3", - "@types/istanbul-lib-coverage": "^2.0.0", - "@types/istanbul-reports": "^3.0.0", - "@types/node": "*", - "@types/yargs": "^17.0.8", - "chalk": "^4.0.0" - }, - "engines": { - "node": "^14.15.0 || ^16.10.0 || >=18.0.0" - } - }, - "node_modules/@jridgewell/gen-mapping": { - "version": "0.3.8", - "dev": true, - "license": "MIT", - "dependencies": { - "@jridgewell/set-array": "^1.2.1", - "@jridgewell/sourcemap-codec": "^1.4.10", - "@jridgewell/trace-mapping": "^0.3.24" - }, - "engines": { - "node": ">=6.0.0" - } - }, - "node_modules/@jridgewell/resolve-uri": { - "version": "3.1.2", - "devOptional": true, - "license": "MIT", - "engines": { - "node": ">=6.0.0" - } - }, - "node_modules/@jridgewell/set-array": { - "version": "1.2.1", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=6.0.0" - } - }, - "node_modules/@jridgewell/source-map": { - "version": "0.3.6", - "dev": true, - "license": "MIT", - "dependencies": { - "@jridgewell/gen-mapping": "^0.3.5", - "@jridgewell/trace-mapping": "^0.3.25" - } - }, - "node_modules/@jridgewell/sourcemap-codec": { - "version": "1.5.0", - "devOptional": true, - "license": "MIT" - }, - "node_modules/@jridgewell/trace-mapping": { - "version": "0.3.25", - "dev": true, - "license": "MIT", - "dependencies": { - "@jridgewell/resolve-uri": "^3.1.0", - "@jridgewell/sourcemap-codec": "^1.4.14" - } - }, - "node_modules/@js-sdsl/ordered-map": { - "version": "4.4.2", - "license": "MIT", - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/js-sdsl" - } - }, - "node_modules/@langchain/aws": { - "version": "0.1.11", - "resolved": "https://registry.npmjs.org/@langchain/aws/-/aws-0.1.11.tgz", - "integrity": "sha512-JNnEmJaJB5TzcniPYGZi6dlpmZyzeyVsS+Za0Ye1DhCpcNmEiWRy514gVcTPQUEl5EcpIR51B/YyowI7zUzVvg==", - "license": "MIT", - "dependencies": { - "@aws-sdk/client-bedrock-agent-runtime": "^3.755.0", - "@aws-sdk/client-bedrock-runtime": "^3.755.0", - "@aws-sdk/client-kendra": "^3.750.0", - "@aws-sdk/credential-provider-node": "^3.750.0" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "@langchain/core": ">=0.3.58 <0.4.0" - } - }, - "node_modules/@langchain/community": { - "version": "0.3.48", - "resolved": "https://registry.npmjs.org/@langchain/community/-/community-0.3.48.tgz", - "integrity": "sha512-0KceBKSx34lL5cnbKybWIMQAFTgkZJMOzcZ1YdcagIwgoDa5a4MsJdtTABxaY0gu+87Uo3KqMj+GXx2wQqnZWA==", - "dependencies": { - "@langchain/openai": ">=0.2.0 <0.6.0", - "@langchain/weaviate": "^0.2.0", - "binary-extensions": "^2.2.0", - "expr-eval": "^2.0.2", - "flat": "^5.0.2", - "js-yaml": "^4.1.0", - "langchain": ">=0.2.3 <0.3.0 || >=0.3.4 <0.4.0", - "langsmith": "^0.3.33", - "uuid": "^10.0.0", - "zod": "^3.25.32" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "@arcjet/redact": "^v1.0.0-alpha.23", - "@aws-crypto/sha256-js": "^5.0.0", - "@aws-sdk/client-bedrock-agent-runtime": "^3.749.0", - "@aws-sdk/client-bedrock-runtime": "^3.749.0", - "@aws-sdk/client-dynamodb": "^3.749.0", - "@aws-sdk/client-kendra": "^3.749.0", - "@aws-sdk/client-lambda": "^3.749.0", - "@aws-sdk/client-s3": "^3.749.0", - "@aws-sdk/client-sagemaker-runtime": "^3.749.0", - "@aws-sdk/client-sfn": "^3.749.0", - "@aws-sdk/credential-provider-node": "^3.388.0", - "@azure/search-documents": "^12.0.0", - "@azure/storage-blob": "^12.15.0", - "@browserbasehq/sdk": "*", - "@browserbasehq/stagehand": "^1.0.0", - "@clickhouse/client": "^0.2.5", - "@cloudflare/ai": "*", - "@datastax/astra-db-ts": "^1.0.0", - "@elastic/elasticsearch": "^8.4.0", - "@getmetal/metal-sdk": "*", - "@getzep/zep-cloud": "^1.0.6", - "@getzep/zep-js": "^0.9.0", - "@gomomento/sdk": "^1.51.1", - "@gomomento/sdk-core": "^1.51.1", - "@google-ai/generativelanguage": "*", - "@google-cloud/storage": "^6.10.1 || ^7.7.0", - "@gradientai/nodejs-sdk": "^1.2.0", - "@huggingface/inference": "^4.0.5", - "@huggingface/transformers": "^3.5.2", - "@ibm-cloud/watsonx-ai": "*", - "@lancedb/lancedb": "^0.12.0", - "@langchain/core": ">=0.3.58 <0.4.0", - "@layerup/layerup-security": "^1.5.12", - "@libsql/client": "^0.14.0", - "@mendable/firecrawl-js": "^1.4.3", - "@mlc-ai/web-llm": "*", - "@mozilla/readability": "*", - "@neondatabase/serverless": "*", - "@notionhq/client": "^2.2.10", - "@opensearch-project/opensearch": "*", - "@pinecone-database/pinecone": "*", - "@planetscale/database": "^1.8.0", - "@premai/prem-sdk": "^0.3.25", - "@qdrant/js-client-rest": "^1.8.2", - "@raycast/api": "^1.55.2", - "@rockset/client": "^0.9.1", - "@smithy/eventstream-codec": "^2.0.5", - "@smithy/protocol-http": "^3.0.6", - "@smithy/signature-v4": "^2.0.10", - "@smithy/util-utf8": "^2.0.0", - "@spider-cloud/spider-client": "^0.0.21", - "@supabase/supabase-js": "^2.45.0", - "@tensorflow-models/universal-sentence-encoder": "*", - "@tensorflow/tfjs-converter": "*", - "@tensorflow/tfjs-core": "*", - "@upstash/ratelimit": "^1.1.3 || ^2.0.3", - "@upstash/redis": "^1.20.6", - "@upstash/vector": "^1.1.1", - "@vercel/kv": "*", - "@vercel/postgres": "*", - "@writerai/writer-sdk": "^0.40.2", - "@xata.io/client": "^0.28.0", - "@zilliz/milvus2-sdk-node": ">=2.3.5", - "apify-client": "^2.7.1", - "assemblyai": "^4.6.0", - "azion": "^1.11.1", - "better-sqlite3": ">=9.4.0 <12.0.0", - "cassandra-driver": "^4.7.2", - "cborg": "^4.1.1", - "cheerio": "^1.0.0-rc.12", - "chromadb": "*", - "closevector-common": "0.1.3", - "closevector-node": "0.1.6", - "closevector-web": "0.1.6", - "cohere-ai": "*", - "convex": "^1.3.1", - "crypto-js": "^4.2.0", - "d3-dsv": "^2.0.0", - "discord.js": "^14.14.1", - "dria": "^0.0.3", - "duck-duck-scrape": "^2.2.5", - "epub2": "^3.0.1", - "fast-xml-parser": "*", - "firebase-admin": "^11.9.0 || ^12.0.0", - "google-auth-library": "*", - "googleapis": "*", - "hnswlib-node": "^3.0.0", - "html-to-text": "^9.0.5", - "ibm-cloud-sdk-core": "*", - "ignore": "^5.2.0", - "interface-datastore": "^8.2.11", - "ioredis": "^5.3.2", - "it-all": "^3.0.4", - "jsdom": "*", - "jsonwebtoken": "^9.0.2", - "llmonitor": "^0.5.9", - "lodash": "^4.17.21", - "lunary": "^0.7.10", - "mammoth": "^1.6.0", - "mariadb": "^3.4.0", - "mem0ai": "^2.1.8", - "mongodb": "^6.17.0", - "mysql2": "^3.9.8", - "neo4j-driver": "*", - "notion-to-md": "^3.1.0", - "officeparser": "^4.0.4", - "openai": "*", - "pdf-parse": "1.1.1", - "pg": "^8.11.0", - "pg-copy-streams": "^6.0.5", - "pickleparser": "^0.2.1", - "playwright": "^1.32.1", - "portkey-ai": "^0.1.11", - "puppeteer": "*", - "pyodide": ">=0.24.1 <0.27.0", - "redis": "*", - "replicate": "*", - "sonix-speech-recognition": "^2.1.1", - "srt-parser-2": "^1.2.3", - "typeorm": "^0.3.20", - "typesense": "^1.5.3", - "usearch": "^1.1.1", - "voy-search": "0.6.2", - "weaviate-client": "^3.5.2", - "web-auth-library": "^1.0.3", - "word-extractor": "*", - "ws": "^8.14.2", - "youtubei.js": "*" - }, - "peerDependenciesMeta": { - "@arcjet/redact": { - "optional": true - }, - "@aws-crypto/sha256-js": { - "optional": true - }, - "@aws-sdk/client-bedrock-agent-runtime": { - "optional": true - }, - "@aws-sdk/client-bedrock-runtime": { - "optional": true - }, - "@aws-sdk/client-dynamodb": { - "optional": true - }, - "@aws-sdk/client-kendra": { - "optional": true - }, - "@aws-sdk/client-lambda": { - "optional": true - }, - "@aws-sdk/client-s3": { - "optional": true - }, - "@aws-sdk/client-sagemaker-runtime": { - "optional": true - }, - "@aws-sdk/client-sfn": { - "optional": true - }, - "@aws-sdk/credential-provider-node": { - "optional": true - }, - "@aws-sdk/dsql-signer": { - "optional": true - }, - "@azure/search-documents": { - "optional": true - }, - "@azure/storage-blob": { - "optional": true - }, - "@browserbasehq/sdk": { - "optional": true - }, - "@clickhouse/client": { - "optional": true - }, - "@cloudflare/ai": { - "optional": true - }, - "@datastax/astra-db-ts": { - "optional": true - }, - "@elastic/elasticsearch": { - "optional": true - }, - "@getmetal/metal-sdk": { - "optional": true - }, - "@getzep/zep-cloud": { - "optional": true - }, - "@getzep/zep-js": { - "optional": true - }, - "@gomomento/sdk": { - "optional": true - }, - "@gomomento/sdk-core": { - "optional": true - }, - "@google-ai/generativelanguage": { - "optional": true - }, - "@google-cloud/storage": { - "optional": true - }, - "@gradientai/nodejs-sdk": { - "optional": true - }, - "@huggingface/inference": { - "optional": true - }, - "@huggingface/transformers": { - "optional": true - }, - "@lancedb/lancedb": { - "optional": true - }, - "@layerup/layerup-security": { - "optional": true - }, - "@libsql/client": { - "optional": true - }, - "@mendable/firecrawl-js": { - "optional": true - }, - "@mlc-ai/web-llm": { - "optional": true - }, - "@mozilla/readability": { - "optional": true - }, - "@neondatabase/serverless": { - "optional": true - }, - "@notionhq/client": { - "optional": true - }, - "@opensearch-project/opensearch": { - "optional": true - }, - "@pinecone-database/pinecone": { - "optional": true - }, - "@planetscale/database": { - "optional": true - }, - "@premai/prem-sdk": { - "optional": true - }, - "@qdrant/js-client-rest": { - "optional": true - }, - "@raycast/api": { - "optional": true - }, - "@rockset/client": { - "optional": true - }, - "@smithy/eventstream-codec": { - "optional": true - }, - "@smithy/protocol-http": { - "optional": true - }, - "@smithy/signature-v4": { - "optional": true - }, - "@smithy/util-utf8": { - "optional": true - }, - "@spider-cloud/spider-client": { - "optional": true - }, - "@supabase/supabase-js": { - "optional": true - }, - "@tensorflow-models/universal-sentence-encoder": { - "optional": true - }, - "@tensorflow/tfjs-converter": { - "optional": true - }, - "@tensorflow/tfjs-core": { - "optional": true - }, - "@upstash/ratelimit": { - "optional": true - }, - "@upstash/redis": { - "optional": true - }, - "@upstash/vector": { - "optional": true - }, - "@vercel/kv": { - "optional": true - }, - "@vercel/postgres": { - "optional": true - }, - "@writerai/writer-sdk": { - "optional": true - }, - "@xata.io/client": { - "optional": true - }, - "@zilliz/milvus2-sdk-node": { - "optional": true - }, - "apify-client": { - "optional": true - }, - "assemblyai": { - "optional": true - }, - "azion": { - "optional": true - }, - "better-sqlite3": { - "optional": true - }, - "cassandra-driver": { - "optional": true - }, - "cborg": { - "optional": true - }, - "cheerio": { - "optional": true - }, - "chromadb": { - "optional": true - }, - "closevector-common": { - "optional": true - }, - "closevector-node": { - "optional": true - }, - "closevector-web": { - "optional": true - }, - "cohere-ai": { - "optional": true - }, - "convex": { - "optional": true - }, - "crypto-js": { - "optional": true - }, - "d3-dsv": { - "optional": true - }, - "discord.js": { - "optional": true - }, - "dria": { - "optional": true - }, - "duck-duck-scrape": { - "optional": true - }, - "epub2": { - "optional": true - }, - "fast-xml-parser": { - "optional": true - }, - "firebase-admin": { - "optional": true - }, - "google-auth-library": { - "optional": true - }, - "googleapis": { - "optional": true - }, - "hnswlib-node": { - "optional": true - }, - "html-to-text": { - "optional": true - }, - "ignore": { - "optional": true - }, - "interface-datastore": { - "optional": true - }, - "ioredis": { - "optional": true - }, - "it-all": { - "optional": true - }, - "jsdom": { - "optional": true - }, - "jsonwebtoken": { - "optional": true - }, - "llmonitor": { - "optional": true - }, - "lodash": { - "optional": true - }, - "lunary": { - "optional": true - }, - "mammoth": { - "optional": true - }, - "mariadb": { - "optional": true - }, - "mem0ai": { - "optional": true - }, - "mongodb": { - "optional": true - }, - "mysql2": { - "optional": true - }, - "neo4j-driver": { - "optional": true - }, - "notion-to-md": { - "optional": true - }, - "officeparser": { - "optional": true - }, - "pdf-parse": { - "optional": true - }, - "pg": { - "optional": true - }, - "pg-copy-streams": { - "optional": true - }, - "pickleparser": { - "optional": true - }, - "playwright": { - "optional": true - }, - "portkey-ai": { - "optional": true - }, - "puppeteer": { - "optional": true - }, - "pyodide": { - "optional": true - }, - "redis": { - "optional": true - }, - "replicate": { - "optional": true - }, - "sonix-speech-recognition": { - "optional": true - }, - "srt-parser-2": { - "optional": true - }, - "typeorm": { - "optional": true - }, - "typesense": { - "optional": true - }, - "usearch": { - "optional": true - }, - "voy-search": { - "optional": true - }, - "weaviate-client": { - "optional": true - }, - "web-auth-library": { - "optional": true - }, - "word-extractor": { - "optional": true - }, - "ws": { - "optional": true - }, - "youtubei.js": { - "optional": true - } - } - }, - "node_modules/@langchain/community/node_modules/uuid": { - "version": "10.0.0", - "resolved": "https://registry.npmjs.org/uuid/-/uuid-10.0.0.tgz", - "integrity": "sha512-8XkAphELsDnEGrDxUOHB3RGvXz6TeuYSGEZBOjtTtPm2lwhGBjLgOzLHB63IUWfBpNucQjND6d3AOudO+H3RWQ==", - "funding": [ - "https://github.com/sponsors/broofa", - "https://github.com/sponsors/ctavan" - ], - "license": "MIT", - "bin": { - "uuid": "dist/bin/uuid" - } - }, - "node_modules/@langchain/core": { - "version": "0.3.62", - "resolved": "https://registry.npmjs.org/@langchain/core/-/core-0.3.62.tgz", - "integrity": "sha512-GqRTcoUPnozGRMUcA6QkP7LHL/OvanGdB51Jgb0w7IIPDI3wFugxMHZ4gphnGDtxsD1tQY5ykyEpYNxFK8kl1w==", - "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.33", - "mustache": "^4.2.0", - "p-queue": "^6.6.2", - "p-retry": "4", - "uuid": "^10.0.0", - "zod": "^3.25.32", - "zod-to-json-schema": "^3.22.3" - }, - "engines": { - "node": ">=18" - } - }, - "node_modules/@langchain/core/node_modules/uuid": { - "version": "10.0.0", - "resolved": "https://registry.npmjs.org/uuid/-/uuid-10.0.0.tgz", - "integrity": "sha512-8XkAphELsDnEGrDxUOHB3RGvXz6TeuYSGEZBOjtTtPm2lwhGBjLgOzLHB63IUWfBpNucQjND6d3AOudO+H3RWQ==", - "funding": [ - "https://github.com/sponsors/broofa", - "https://github.com/sponsors/ctavan" - ], - "license": "MIT", - "bin": { - "uuid": "dist/bin/uuid" - } - }, - "node_modules/@langchain/google-common": { - "version": "0.2.14", - "resolved": "https://registry.npmjs.org/@langchain/google-common/-/google-common-0.2.14.tgz", - "integrity": "sha512-oz1YwwPUP+FC5UMLus1reJ578LfNSEh81shqBP8xXDioLUfKub6p5Jye61gHm8JTXcSvKHPCLGPeK0Uq7PDx2g==", - "dependencies": { - "uuid": "^10.0.0" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "@langchain/core": ">=0.3.58 <0.4.0" - } - }, - "node_modules/@langchain/google-common/node_modules/uuid": { - "version": "10.0.0", - "resolved": "https://registry.npmjs.org/uuid/-/uuid-10.0.0.tgz", - "integrity": "sha512-8XkAphELsDnEGrDxUOHB3RGvXz6TeuYSGEZBOjtTtPm2lwhGBjLgOzLHB63IUWfBpNucQjND6d3AOudO+H3RWQ==", - "funding": [ - "https://github.com/sponsors/broofa", - "https://github.com/sponsors/ctavan" - ], - "bin": { - "uuid": "dist/bin/uuid" - } - }, - "node_modules/@langchain/google-gauth": { - "version": "0.2.14", - "resolved": "https://registry.npmjs.org/@langchain/google-gauth/-/google-gauth-0.2.14.tgz", - "integrity": "sha512-vS68e13eupTOfQ6P0QpIaOkiAlwZthV23U9Afm7b6rD2lsZ78jwTabzmmkU2o9x/DioNa9hEPpbE7+Z26V0NYg==", - "dependencies": { - "@langchain/google-common": "^0.2.14", - "google-auth-library": "^10.1.0" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "@langchain/core": ">=0.3.58 <0.4.0" - } - }, - "node_modules/@langchain/google-genai": { - "version": "0.2.14", - "resolved": "https://registry.npmjs.org/@langchain/google-genai/-/google-genai-0.2.14.tgz", - "integrity": "sha512-gKe/T2LNh8wSSMJOaFmYd8cwQnDSXKtVtC6a7CFoq5nWuh0bKzhItM/7bue1aMN8mlKfB2G1HCwxhaZoSpS/DA==", - "dependencies": { - "@google/generative-ai": "^0.24.0", - "uuid": "^11.1.0" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "@langchain/core": ">=0.3.58 <0.4.0" - } - }, - "node_modules/@langchain/google-genai/node_modules/uuid": { - "version": "11.1.0", - "resolved": "https://registry.npmjs.org/uuid/-/uuid-11.1.0.tgz", - "integrity": "sha512-0/A9rDy9P7cJ+8w1c9WD9V//9Wj15Ce2MPz8Ri6032usz+NfePxx5AcN3bN+r6ZL6jEo066/yNYB3tn4pQEx+A==", - "funding": [ - "https://github.com/sponsors/broofa", - "https://github.com/sponsors/ctavan" - ], - "license": "MIT", - "bin": { - "uuid": "dist/esm/bin/uuid" - } - }, - "node_modules/@langchain/google-vertexai": { - "version": "0.2.14", - "resolved": "https://registry.npmjs.org/@langchain/google-vertexai/-/google-vertexai-0.2.14.tgz", - "integrity": "sha512-OqfK3xDo8AmVFJHoINSfqFeKCp4d9aH4YnCOPBe6qDaTnME1QTCHs3U9BRWwUhfD46K50ocbQUAsnTYSclhhMg==", - "dependencies": { - "@langchain/google-gauth": "^0.2.14" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "@langchain/core": ">=0.3.58 <0.4.0" - } - }, - "node_modules/@langchain/mistralai": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/@langchain/mistralai/-/mistralai-0.2.1.tgz", - "integrity": "sha512-s91BlNcuxaaZGnVukyl81nwGrWpeE0EYiAdEFoBmZwlT4yLpx+QpPhRsGKrTg/Vm7Nscy6Wd8Xy2PJ93wftMdw==", - "license": "MIT", - "dependencies": { - "@mistralai/mistralai": "^1.3.1", - "uuid": "^10.0.0" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "@langchain/core": ">=0.3.58 <0.4.0" - } - }, - "node_modules/@langchain/mistralai/node_modules/uuid": { - "version": "10.0.0", - "funding": [ - "https://github.com/sponsors/broofa", - "https://github.com/sponsors/ctavan" - ], - "license": "MIT", - "bin": { - "uuid": "dist/bin/uuid" - } - }, - "node_modules/@langchain/ollama": { - "version": "0.2.3", - "resolved": "https://registry.npmjs.org/@langchain/ollama/-/ollama-0.2.3.tgz", - "integrity": "sha512-1Obe45jgQspqLMBVlayQbGdywFmri8DgmGRdzNu0li56cG5RReYlRCFVDZBRMMvF9JhsP5eXRyfyivtKfITHWQ==", - "dependencies": { - "ollama": "^0.5.12", - "uuid": "^10.0.0" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "@langchain/core": ">=0.3.58 <0.4.0" - } - }, - "node_modules/@langchain/ollama/node_modules/uuid": { - "version": "10.0.0", - "resolved": "https://registry.npmjs.org/uuid/-/uuid-10.0.0.tgz", - "integrity": "sha512-8XkAphELsDnEGrDxUOHB3RGvXz6TeuYSGEZBOjtTtPm2lwhGBjLgOzLHB63IUWfBpNucQjND6d3AOudO+H3RWQ==", - "funding": [ - "https://github.com/sponsors/broofa", - "https://github.com/sponsors/ctavan" - ], - "license": "MIT", - "bin": { - "uuid": "dist/bin/uuid" - } - }, - "node_modules/@langchain/openai": { - "version": "0.5.18", - "resolved": "https://registry.npmjs.org/@langchain/openai/-/openai-0.5.18.tgz", - "integrity": "sha512-CX1kOTbT5xVFNdtLjnM0GIYNf+P7oMSu+dGCFxxWRa3dZwWiuyuBXCm+dToUGxDLnsHuV1bKBtIzrY1mLq/A1Q==", - "dependencies": { - "js-tiktoken": "^1.0.12", - "openai": "^5.3.0", - "zod": "^3.25.32" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "@langchain/core": ">=0.3.58 <0.4.0" - } - }, - "node_modules/@langchain/textsplitters": { - "version": "0.1.0", - "license": "MIT", - "dependencies": { - "js-tiktoken": "^1.0.12" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "@langchain/core": ">=0.2.21 <0.4.0" - } - }, - "node_modules/@langchain/weaviate": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/@langchain/weaviate/-/weaviate-0.2.0.tgz", - "integrity": "sha512-gAtTCxSllR8Z92qAuRn2ir0cop241VmftQHQN+UYtTeoLge8hvZT5k0j55PDVaXTVpjx0ecx6DKv5I/wLRQI+A==", - "license": "MIT", - "dependencies": { - "uuid": "^10.0.0", - "weaviate-client": "^3.5.2" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "@langchain/core": ">=0.2.21 <0.4.0" - } - }, - "node_modules/@langchain/weaviate/node_modules/uuid": { - "version": "10.0.0", - "resolved": "https://registry.npmjs.org/uuid/-/uuid-10.0.0.tgz", - "integrity": "sha512-8XkAphELsDnEGrDxUOHB3RGvXz6TeuYSGEZBOjtTtPm2lwhGBjLgOzLHB63IUWfBpNucQjND6d3AOudO+H3RWQ==", - "funding": [ - "https://github.com/sponsors/broofa", - "https://github.com/sponsors/ctavan" - ], - "license": "MIT", - "bin": { - "uuid": "dist/bin/uuid" - } - }, - "node_modules/@lukeed/csprng": { - "version": "1.1.0", - "license": "MIT", - "engines": { - "node": ">=8" - } - }, - "node_modules/@microsoft/tsdoc": { - "version": "0.15.1", - "license": "MIT" - }, - "node_modules/@mistralai/mistralai": { - "version": "1.6.0", - "dependencies": { - "zod-to-json-schema": "^3.24.1" - }, - "peerDependencies": { - "zod": ">= 3" - } - }, - "node_modules/@modelcontextprotocol/sdk": { - "version": "1.17.0", - "resolved": "https://registry.npmjs.org/@modelcontextprotocol/sdk/-/sdk-1.17.0.tgz", - "integrity": "sha512-qFfbWFA7r1Sd8D697L7GkTd36yqDuTkvz0KfOGkgXR8EUhQn3/EDNIR/qUdQNMT8IjmasBvHWuXeisxtXTQT2g==", - "license": "MIT", - "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" - }, - "engines": { - "node": ">=18" - } - }, - "node_modules/@n8n/json-schema-to-zod": { - "version": "1.1.0", - "license": "SEE LICENSE IN LICENSE.md", - "peerDependencies": { - "zod": "^3.0.0" - } - }, - "node_modules/@nestjs/axios": { - "version": "4.0.0", - "devOptional": true, - "license": "MIT", - "peerDependencies": { - "@nestjs/common": "^10.0.0 || ^11.0.0", - "axios": "^1.3.1", - "rxjs": "^7.0.0" - } - }, - "node_modules/@nestjs/cli": { - "version": "11.0.7", - "dev": true, - "license": "MIT", - "dependencies": { - "@angular-devkit/core": "19.2.8", - "@angular-devkit/schematics": "19.2.8", - "@angular-devkit/schematics-cli": "19.2.8", - "@inquirer/prompts": "7.4.1", - "@nestjs/schematics": "^11.0.1", - "ansis": "3.17.0", - "chokidar": "4.0.3", - "cli-table3": "0.6.5", - "commander": "4.1.1", - "fork-ts-checker-webpack-plugin": "9.1.0", - "glob": "11.0.1", - "node-emoji": "1.11.0", - "ora": "5.4.1", - "tree-kill": "1.2.2", - "tsconfig-paths": "4.2.0", - "tsconfig-paths-webpack-plugin": "4.2.0", - "typescript": "5.8.3", - "webpack": "5.99.6", - "webpack-node-externals": "3.0.0" - }, - "bin": { - "nest": "bin/nest.js" - }, - "engines": { - "node": ">= 20.11" - }, - "peerDependencies": { - "@swc/cli": "^0.1.62 || ^0.3.0 || ^0.4.0 || ^0.5.0 || ^0.6.0 || ^0.7.0", - "@swc/core": "^1.3.62" - }, - "peerDependenciesMeta": { - "@swc/cli": { - "optional": true - }, - "@swc/core": { - "optional": true - } - } - }, - "node_modules/@nestjs/cli/node_modules/@angular-devkit/core": { - "version": "19.2.8", - "dev": true, - "license": "MIT", - "dependencies": { - "ajv": "8.17.1", - "ajv-formats": "3.0.1", - "jsonc-parser": "3.3.1", - "picomatch": "4.0.2", - "rxjs": "7.8.1", - "source-map": "0.7.4" - }, - "engines": { - "node": "^18.19.1 || ^20.11.1 || >=22.0.0", - "npm": "^6.11.0 || ^7.5.6 || >=8.0.0", - "yarn": ">= 1.13.0" - }, - "peerDependencies": { - "chokidar": "^4.0.0" - }, - "peerDependenciesMeta": { - "chokidar": { - "optional": true - } + "node": ">= 8" } }, - "node_modules/@nestjs/cli/node_modules/ajv": { - "version": "8.17.1", + "node_modules/@nodelib/fs.stat": { + "version": "2.0.5", + "resolved": "https://registry.npmjs.org/@nodelib/fs.stat/-/fs.stat-2.0.5.tgz", + "integrity": "sha512-RkhPPp2zrqDAQA/2jNhnztcPAlv64XdhIp7a7454A5ovI7Bukxgt7MX7udwAu3zg1DcpPU0rz3VV1SeaqvY4+A==", "dev": true, "license": "MIT", - "dependencies": { - "fast-deep-equal": "^3.1.3", - "fast-uri": "^3.0.1", - "json-schema-traverse": "^1.0.0", - "require-from-string": "^2.0.2" - }, - "funding": { - "type": "github", - "url": "https://github.com/sponsors/epoberezkin" + "engines": { + "node": ">= 8" } }, - "node_modules/@nestjs/cli/node_modules/ajv-keywords": { - "version": "5.1.0", + "node_modules/@nodelib/fs.walk": { + "version": "1.2.8", + "resolved": "https://registry.npmjs.org/@nodelib/fs.walk/-/fs.walk-1.2.8.tgz", + "integrity": "sha512-oGB+UxlgWcgQkgwo8GcEGwemoTFt3FIO9ababBmaGwXIoBKZ+GTy0pP185beGg7Llih/NSHSV2XAs1lnznocSg==", "dev": true, "license": "MIT", "dependencies": { - "fast-deep-equal": "^3.1.3" + "@nodelib/fs.scandir": "2.1.5", + "fastq": "^1.6.0" }, - "peerDependencies": { - "ajv": "^8.8.2" + "engines": { + "node": ">= 8" } }, - "node_modules/@nestjs/cli/node_modules/chokidar": { - "version": "4.0.3", - "dev": true, + "node_modules/@nuxt/opencollective": { + "version": "0.4.1", "license": "MIT", "dependencies": { - "readdirp": "^4.0.1" + "consola": "^3.2.3" }, - "engines": { - "node": ">= 14.16.0" + "bin": { + "opencollective": "bin/opencollective.js" }, - "funding": { - "url": "https://paulmillr.com/funding/" + "engines": { + "node": "^14.18.0 || >=16.10.0", + "npm": ">=5.10.0" } }, - "node_modules/@nestjs/cli/node_modules/eslint-scope": { - "version": "5.1.1", + "node_modules/@nuxtjs/opencollective": { + "version": "0.3.2", "dev": true, - "license": "BSD-2-Clause", + "license": "MIT", "dependencies": { - "esrecurse": "^4.3.0", - "estraverse": "^4.1.1" + "chalk": "^4.1.0", + "consola": "^2.15.0", + "node-fetch": "^2.6.1" + }, + "bin": { + "opencollective": "bin/opencollective.js" }, "engines": { - "node": ">=8.0.0" + "node": ">=8.0.0", + "npm": ">=5.0.0" } }, - "node_modules/@nestjs/cli/node_modules/estraverse": { - "version": "4.3.0", + "node_modules/@nuxtjs/opencollective/node_modules/consola": { + "version": "2.15.3", "dev": true, - "license": "BSD-2-Clause", - "engines": { - "node": ">=4.0" - } + "license": "MIT" }, - "node_modules/@nestjs/cli/node_modules/json-schema-traverse": { - "version": "1.0.0", + "node_modules/@openapitools/openapi-generator-cli": { + "version": "2.21.0", + "resolved": "https://registry.npmjs.org/@openapitools/openapi-generator-cli/-/openapi-generator-cli-2.21.0.tgz", + "integrity": "sha512-NdDvCd7hya+UucxH7G94Jf6tmA6641I4CF/T3xtFhM+NQQNWAP5tpiOBN4Ub9ocU6cCgQgXdWl4EpwlEwW7JDQ==", "dev": true, - "license": "MIT" + "hasInstallScript": true, + "license": "Apache-2.0", + "dependencies": { + "@nestjs/axios": "4.0.0", + "@nestjs/common": "11.1.3", + "@nestjs/core": "11.1.3", + "@nuxtjs/opencollective": "0.3.2", + "axios": "1.10.0", + "chalk": "4.1.2", + "commander": "8.3.0", + "compare-versions": "4.1.4", + "concurrently": "6.5.1", + "console.table": "0.10.0", + "fs-extra": "11.3.0", + "glob": "11.0.3", + "inquirer": "8.2.6", + "lodash": "4.17.21", + "proxy-agent": "6.5.0", + "reflect-metadata": "0.2.2", + "rxjs": "7.8.2", + "tslib": "2.8.1" + }, + "bin": { + "openapi-generator-cli": "main.js" + }, + "engines": { + "node": ">=16" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/openapi_generator" + } }, - "node_modules/@nestjs/cli/node_modules/mime-db": { - "version": "1.52.0", + "node_modules/@openapitools/openapi-generator-cli/node_modules/commander": { + "version": "8.3.0", + "resolved": "https://registry.npmjs.org/commander/-/commander-8.3.0.tgz", + "integrity": "sha512-OkTL9umf+He2DZkUq8f8J9of7yL6RJKI24dVITBmNfZBmri9zYZQrKkuXiKhyfPSu8tUhnVBB1iKXevvnlR4Ww==", "dev": true, "license": "MIT", "engines": { - "node": ">= 0.6" + "node": ">= 12" } }, - "node_modules/@nestjs/cli/node_modules/mime-types": { - "version": "2.1.35", + "node_modules/@openapitools/openapi-generator-cli/node_modules/glob": { + "version": "11.0.3", + "resolved": "https://registry.npmjs.org/glob/-/glob-11.0.3.tgz", + "integrity": "sha512-2Nim7dha1KVkaiF4q6Dj+ngPPMdfvLJEOpZk/jKiUAkqKebpGAWQXAq9z1xu9HKu5lWfqw/FASuccEjyznjPaA==", "dev": true, - "license": "MIT", + "license": "ISC", "dependencies": { - "mime-db": "1.52.0" + "foreground-child": "^3.3.1", + "jackspeak": "^4.1.1", + "minimatch": "^10.0.3", + "minipass": "^7.1.2", + "package-json-from-dist": "^1.0.0", + "path-scurry": "^2.0.0" + }, + "bin": { + "glob": "dist/esm/bin.mjs" }, "engines": { - "node": ">= 0.6" + "node": "20 || >=22" + }, + "funding": { + "url": "https://github.com/sponsors/isaacs" } }, - "node_modules/@nestjs/cli/node_modules/readdirp": { - "version": "4.1.2", + "node_modules/@openapitools/openapi-generator-cli/node_modules/minimatch": { + "version": "10.0.3", + "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-10.0.3.tgz", + "integrity": "sha512-IPZ167aShDZZUMdRk66cyQAW3qr0WzbHkPdMYa8bzZhlHhO3jALbKdxcaak7W9FfT2rZNpQuUu4Od7ILEpXSaw==", "dev": true, - "license": "MIT", + "license": "ISC", + "dependencies": { + "@isaacs/brace-expansion": "^5.0.0" + }, "engines": { - "node": ">= 14.18.0" + "node": "20 || >=22" }, "funding": { - "type": "individual", - "url": "https://paulmillr.com/funding/" + "url": "https://github.com/sponsors/isaacs" } }, - "node_modules/@nestjs/cli/node_modules/rxjs": { - "version": "7.8.1", - "dev": true, + "node_modules/@opentelemetry/api": { + "version": "1.9.0", "license": "Apache-2.0", - "dependencies": { - "tslib": "^2.1.0" + "peer": true, + "engines": { + "node": ">=8.0.0" } }, - "node_modules/@nestjs/cli/node_modules/schema-utils": { - "version": "4.3.2", - "dev": true, - "license": "MIT", + "node_modules/@opentelemetry/api-logs": { + "version": "0.205.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/api-logs/-/api-logs-0.205.0.tgz", + "integrity": "sha512-wBlPk1nFB37Hsm+3Qy73yQSobVn28F4isnWIBvKpd5IUH/eat8bwcL02H9yzmHyyPmukeccSl2mbN5sDQZYnPg==", + "license": "Apache-2.0", "dependencies": { - "@types/json-schema": "^7.0.9", - "ajv": "^8.9.0", - "ajv-formats": "^2.1.1", - "ajv-keywords": "^5.1.0" + "@opentelemetry/api": "^1.3.0" }, "engines": { - "node": ">= 10.13.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/webpack" + "node": ">=8.0.0" } }, - "node_modules/@nestjs/cli/node_modules/schema-utils/node_modules/ajv-formats": { - "version": "2.1.1", - "dev": true, - "license": "MIT", + "node_modules/@opentelemetry/auto-instrumentations-node": { + "version": "0.64.1", + "resolved": "https://registry.npmjs.org/@opentelemetry/auto-instrumentations-node/-/auto-instrumentations-node-0.64.1.tgz", + "integrity": "sha512-V893tqyTsCD0zYsHjJXUor/x1M7VxmPr5j8Tga7EYVXfxubVrrPwqKk37ygtVRp2oDnQp+P/D7LGP+AP6eCblw==", + "license": "Apache-2.0", "dependencies": { - "ajv": "^8.0.0" + "@opentelemetry/instrumentation": "^0.205.0", + "@opentelemetry/instrumentation-amqplib": "^0.52.0", + "@opentelemetry/instrumentation-aws-lambda": "^0.56.0", + "@opentelemetry/instrumentation-aws-sdk": "^0.60.0", + "@opentelemetry/instrumentation-bunyan": "^0.51.0", + "@opentelemetry/instrumentation-cassandra-driver": "^0.51.0", + "@opentelemetry/instrumentation-connect": "^0.49.0", + "@opentelemetry/instrumentation-cucumber": "^0.21.0", + "@opentelemetry/instrumentation-dataloader": "^0.23.0", + "@opentelemetry/instrumentation-dns": "^0.49.0", + "@opentelemetry/instrumentation-express": "^0.54.0", + "@opentelemetry/instrumentation-fastify": "^0.50.0", + "@opentelemetry/instrumentation-fs": "^0.25.0", + "@opentelemetry/instrumentation-generic-pool": "^0.49.0", + "@opentelemetry/instrumentation-graphql": "^0.53.0", + "@opentelemetry/instrumentation-grpc": "^0.205.0", + "@opentelemetry/instrumentation-hapi": "^0.52.0", + "@opentelemetry/instrumentation-http": "^0.205.0", + "@opentelemetry/instrumentation-ioredis": "^0.53.0", + "@opentelemetry/instrumentation-kafkajs": "^0.15.0", + "@opentelemetry/instrumentation-knex": "^0.50.0", + "@opentelemetry/instrumentation-koa": "^0.53.0", + "@opentelemetry/instrumentation-lru-memoizer": "^0.50.0", + "@opentelemetry/instrumentation-memcached": "^0.49.0", + "@opentelemetry/instrumentation-mongodb": "^0.58.0", + "@opentelemetry/instrumentation-mongoose": "^0.52.0", + "@opentelemetry/instrumentation-mysql": "^0.51.0", + "@opentelemetry/instrumentation-mysql2": "^0.52.0", + "@opentelemetry/instrumentation-nestjs-core": "^0.51.0", + "@opentelemetry/instrumentation-net": "^0.49.0", + "@opentelemetry/instrumentation-oracledb": "^0.31.0", + "@opentelemetry/instrumentation-pg": "^0.58.0", + "@opentelemetry/instrumentation-pino": "^0.52.0", + "@opentelemetry/instrumentation-redis": "^0.54.1", + "@opentelemetry/instrumentation-restify": "^0.51.0", + "@opentelemetry/instrumentation-router": "^0.50.0", + "@opentelemetry/instrumentation-runtime-node": "^0.19.0", + "@opentelemetry/instrumentation-socket.io": "^0.52.0", + "@opentelemetry/instrumentation-tedious": "^0.24.0", + "@opentelemetry/instrumentation-undici": "^0.16.0", + "@opentelemetry/instrumentation-winston": "^0.50.0", + "@opentelemetry/resource-detector-alibaba-cloud": "^0.31.5", + "@opentelemetry/resource-detector-aws": "^2.5.0", + "@opentelemetry/resource-detector-azure": "^0.12.0", + "@opentelemetry/resource-detector-container": "^0.7.5", + "@opentelemetry/resource-detector-gcp": "^0.40.0", + "@opentelemetry/resources": "^2.0.0", + "@opentelemetry/sdk-node": "^0.205.0" + }, + "engines": { + "node": "^18.19.0 || >=20.6.0" }, "peerDependencies": { - "ajv": "^8.0.0" + "@opentelemetry/api": "^1.4.1", + "@opentelemetry/core": "^2.0.0" + } + }, + "node_modules/@opentelemetry/context-async-hooks": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/context-async-hooks/-/context-async-hooks-2.1.0.tgz", + "integrity": "sha512-zOyetmZppnwTyPrt4S7jMfXiSX9yyfF0hxlA8B5oo2TtKl+/RGCy7fi4DrBfIf3lCPrkKsRBWZZD7RFojK7FDg==", + "license": "Apache-2.0", + "engines": { + "node": "^18.19.0 || >=20.6.0" }, - "peerDependenciesMeta": { - "ajv": { - "optional": true - } + "peerDependencies": { + "@opentelemetry/api": ">=1.0.0 <1.10.0" } }, - "node_modules/@nestjs/cli/node_modules/webpack": { - "version": "5.99.6", - "dev": true, - "license": "MIT", + "node_modules/@opentelemetry/core": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/core/-/core-2.1.0.tgz", + "integrity": "sha512-RMEtHsxJs/GiHHxYT58IY57UXAQTuUnZVco6ymDEqTNlJKTimM4qPUPVe8InNFyBjhHBEAx4k3Q8LtNayBsbUQ==", + "license": "Apache-2.0", + "peer": true, "dependencies": { - "@types/eslint-scope": "^3.7.7", - "@types/estree": "^1.0.6", - "@webassemblyjs/ast": "^1.14.1", - "@webassemblyjs/wasm-edit": "^1.14.1", - "@webassemblyjs/wasm-parser": "^1.14.1", - "acorn": "^8.14.0", - "browserslist": "^4.24.0", - "chrome-trace-event": "^1.0.2", - "enhanced-resolve": "^5.17.1", - "es-module-lexer": "^1.2.1", - "eslint-scope": "5.1.1", - "events": "^3.2.0", - "glob-to-regexp": "^0.4.1", - "graceful-fs": "^4.2.11", - "json-parse-even-better-errors": "^2.3.1", - "loader-runner": "^4.2.0", - "mime-types": "^2.1.27", - "neo-async": "^2.6.2", - "schema-utils": "^4.3.0", - "tapable": "^2.1.1", - "terser-webpack-plugin": "^5.3.11", - "watchpack": "^2.4.1", - "webpack-sources": "^3.2.3" + "@opentelemetry/semantic-conventions": "^1.29.0" }, - "bin": { - "webpack": "bin/webpack.js" + "engines": { + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.0.0 <1.10.0" + } + }, + "node_modules/@opentelemetry/exporter-logs-otlp-grpc": { + "version": "0.205.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/exporter-logs-otlp-grpc/-/exporter-logs-otlp-grpc-0.205.0.tgz", + "integrity": "sha512-jQlw7OHbqZ8zPt+pOrW2KGN7T55P50e3NXBMr4ckPOF+DWDwSy4W7mkG09GpYWlQAQ5C9BXg5gfUlv5ldTgWsw==", + "license": "Apache-2.0", + "dependencies": { + "@grpc/grpc-js": "^1.7.1", + "@opentelemetry/core": "2.1.0", + "@opentelemetry/otlp-exporter-base": "0.205.0", + "@opentelemetry/otlp-grpc-exporter-base": "0.205.0", + "@opentelemetry/otlp-transformer": "0.205.0", + "@opentelemetry/sdk-logs": "0.205.0" }, "engines": { - "node": ">=10.13.0" + "node": "^18.19.0 || >=20.6.0" }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/webpack" + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" + } + }, + "node_modules/@opentelemetry/exporter-logs-otlp-grpc/node_modules/@opentelemetry/sdk-logs": { + "version": "0.205.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-logs/-/sdk-logs-0.205.0.tgz", + "integrity": "sha512-nyqhNQ6eEzPWQU60Nc7+A5LIq8fz3UeIzdEVBQYefB4+msJZ2vuVtRuk9KxPMw1uHoHDtYEwkr2Ct0iG29jU8w==", + "license": "Apache-2.0", + "dependencies": { + "@opentelemetry/api-logs": "0.205.0", + "@opentelemetry/core": "2.1.0", + "@opentelemetry/resources": "2.1.0" }, - "peerDependenciesMeta": { - "webpack-cli": { - "optional": true - } + "engines": { + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.4.0 <1.10.0" } }, - "node_modules/@nestjs/common": { - "version": "11.1.3", - "resolved": "https://registry.npmjs.org/@nestjs/common/-/common-11.1.3.tgz", - "integrity": "sha512-ogEK+GriWodIwCw6buQ1rpcH4Kx+G7YQ9EwuPySI3rS05pSdtQ++UhucjusSI9apNidv+QURBztJkRecwwJQXg==", - "license": "MIT", + "node_modules/@opentelemetry/exporter-logs-otlp-http": { + "version": "0.205.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/exporter-logs-otlp-http/-/exporter-logs-otlp-http-0.205.0.tgz", + "integrity": "sha512-5JteMyVWiro4ghF0tHQjfE6OJcF7UBUcoEqX3UIQ5jutKP1H+fxFdyhqjjpmeHMFxzOHaYuLlNR1Bn7FOjGyJg==", + "license": "Apache-2.0", "dependencies": { - "file-type": "21.0.0", - "iterare": "1.2.1", - "load-esm": "1.0.2", - "tslib": "2.8.1", - "uid": "2.0.2" + "@opentelemetry/api-logs": "0.205.0", + "@opentelemetry/core": "2.1.0", + "@opentelemetry/otlp-exporter-base": "0.205.0", + "@opentelemetry/otlp-transformer": "0.205.0", + "@opentelemetry/sdk-logs": "0.205.0" }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/nest" + "engines": { + "node": "^18.19.0 || >=20.6.0" }, "peerDependencies": { - "class-transformer": ">=0.4.1", - "class-validator": ">=0.13.2", - "reflect-metadata": "^0.1.12 || ^0.2.0", - "rxjs": "^7.1.0" - }, - "peerDependenciesMeta": { - "class-transformer": { - "optional": true - }, - "class-validator": { - "optional": true - } + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@nestjs/config": { - "version": "4.0.2", - "license": "MIT", + "node_modules/@opentelemetry/exporter-logs-otlp-http/node_modules/@opentelemetry/sdk-logs": { + "version": "0.205.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-logs/-/sdk-logs-0.205.0.tgz", + "integrity": "sha512-nyqhNQ6eEzPWQU60Nc7+A5LIq8fz3UeIzdEVBQYefB4+msJZ2vuVtRuk9KxPMw1uHoHDtYEwkr2Ct0iG29jU8w==", + "license": "Apache-2.0", "dependencies": { - "dotenv": "16.4.7", - "dotenv-expand": "12.0.1", - "lodash": "4.17.21" + "@opentelemetry/api-logs": "0.205.0", + "@opentelemetry/core": "2.1.0", + "@opentelemetry/resources": "2.1.0" + }, + "engines": { + "node": "^18.19.0 || >=20.6.0" }, "peerDependencies": { - "@nestjs/common": "^10.0.0 || ^11.0.0", - "rxjs": "^7.1.0" + "@opentelemetry/api": ">=1.4.0 <1.10.0" } }, - "node_modules/@nestjs/config/node_modules/dotenv": { - "version": "16.4.7", - "license": "BSD-2-Clause", + "node_modules/@opentelemetry/exporter-logs-otlp-proto": { + "version": "0.205.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/exporter-logs-otlp-proto/-/exporter-logs-otlp-proto-0.205.0.tgz", + "integrity": "sha512-q3VS9wS+lpZ01txKxiDGBtBpTNge3YhbVEFDgem9ZQR9eI3EZ68+9tVZH9zJcSxI37nZPJ6lEEZO58yEjYZsVA==", + "license": "Apache-2.0", + "dependencies": { + "@opentelemetry/api-logs": "0.205.0", + "@opentelemetry/core": "2.1.0", + "@opentelemetry/otlp-exporter-base": "0.205.0", + "@opentelemetry/otlp-transformer": "0.205.0", + "@opentelemetry/resources": "2.1.0", + "@opentelemetry/sdk-logs": "0.205.0", + "@opentelemetry/sdk-trace-base": "2.1.0" + }, "engines": { - "node": ">=12" + "node": "^18.19.0 || >=20.6.0" }, - "funding": { - "url": "https://dotenvx.com" + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@nestjs/core": { - "version": "11.1.3", - "resolved": "https://registry.npmjs.org/@nestjs/core/-/core-11.1.3.tgz", - "integrity": "sha512-5lTni0TCh8x7bXETRD57pQFnKnEg1T6M+VLE7wAmyQRIecKQU+2inRGZD+A4v2DC1I04eA0WffP0GKLxjOKlzw==", - "hasInstallScript": true, - "license": "MIT", + "node_modules/@opentelemetry/exporter-logs-otlp-proto/node_modules/@opentelemetry/sdk-logs": { + "version": "0.205.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-logs/-/sdk-logs-0.205.0.tgz", + "integrity": "sha512-nyqhNQ6eEzPWQU60Nc7+A5LIq8fz3UeIzdEVBQYefB4+msJZ2vuVtRuk9KxPMw1uHoHDtYEwkr2Ct0iG29jU8w==", + "license": "Apache-2.0", "dependencies": { - "@nuxt/opencollective": "0.4.1", - "fast-safe-stringify": "2.1.1", - "iterare": "1.2.1", - "path-to-regexp": "8.2.0", - "tslib": "2.8.1", - "uid": "2.0.2" + "@opentelemetry/api-logs": "0.205.0", + "@opentelemetry/core": "2.1.0", + "@opentelemetry/resources": "2.1.0" }, "engines": { - "node": ">= 20" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/nest" + "node": "^18.19.0 || >=20.6.0" }, "peerDependencies": { - "@nestjs/common": "^11.0.0", - "@nestjs/microservices": "^11.0.0", - "@nestjs/platform-express": "^11.0.0", - "@nestjs/websockets": "^11.0.0", - "reflect-metadata": "^0.1.12 || ^0.2.0", - "rxjs": "^7.1.0" + "@opentelemetry/api": ">=1.4.0 <1.10.0" + } + }, + "node_modules/@opentelemetry/exporter-logs-otlp-proto/node_modules/@opentelemetry/sdk-trace-base": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-trace-base/-/sdk-trace-base-2.1.0.tgz", + "integrity": "sha512-uTX9FBlVQm4S2gVQO1sb5qyBLq/FPjbp+tmGoxu4tIgtYGmBYB44+KX/725RFDe30yBSaA9Ml9fqphe1hbUyLQ==", + "license": "Apache-2.0", + "dependencies": { + "@opentelemetry/core": "2.1.0", + "@opentelemetry/resources": "2.1.0", + "@opentelemetry/semantic-conventions": "^1.29.0" }, - "peerDependenciesMeta": { - "@nestjs/microservices": { - "optional": true - }, - "@nestjs/platform-express": { - "optional": true - }, - "@nestjs/websockets": { - "optional": true - } + "engines": { + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.3.0 <1.10.0" } }, - "node_modules/@nestjs/cqrs": { - "version": "11.0.3", - "license": "MIT", + "node_modules/@opentelemetry/exporter-metrics-otlp-grpc": { + "version": "0.205.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/exporter-metrics-otlp-grpc/-/exporter-metrics-otlp-grpc-0.205.0.tgz", + "integrity": "sha512-1Vxlo4lUwqSKYX+phFkXHKYR3DolFHxCku6lVMP1H8sVE3oj4wwmwxMzDsJ7zF+sXd8M0FCr+ckK4SnNNKkV+w==", + "license": "Apache-2.0", + "dependencies": { + "@grpc/grpc-js": "^1.7.1", + "@opentelemetry/core": "2.1.0", + "@opentelemetry/exporter-metrics-otlp-http": "0.205.0", + "@opentelemetry/otlp-exporter-base": "0.205.0", + "@opentelemetry/otlp-grpc-exporter-base": "0.205.0", + "@opentelemetry/otlp-transformer": "0.205.0", + "@opentelemetry/resources": "2.1.0", + "@opentelemetry/sdk-metrics": "2.1.0" + }, + "engines": { + "node": "^18.19.0 || >=20.6.0" + }, "peerDependencies": { - "@nestjs/common": "^10.0.0 || ^11.0.0", - "@nestjs/core": "^10.0.0 || ^11.0.0", - "reflect-metadata": "^0.1.13 || ^0.2.0", - "rxjs": "^7.2.0" + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@nestjs/mapped-types": { + "node_modules/@opentelemetry/exporter-metrics-otlp-grpc/node_modules/@opentelemetry/sdk-metrics": { "version": "2.1.0", - "license": "MIT", - "peerDependencies": { - "@nestjs/common": "^10.0.0 || ^11.0.0", - "class-transformer": "^0.4.0 || ^0.5.0", - "class-validator": "^0.13.0 || ^0.14.0", - "reflect-metadata": "^0.1.12 || ^0.2.0" + "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-metrics/-/sdk-metrics-2.1.0.tgz", + "integrity": "sha512-J9QX459mzqHLL9Y6FZ4wQPRZG4TOpMCyPOh6mkr/humxE1W2S3Bvf4i75yiMW9uyed2Kf5rxmLhTm/UK8vNkAw==", + "license": "Apache-2.0", + "dependencies": { + "@opentelemetry/core": "2.1.0", + "@opentelemetry/resources": "2.1.0" }, - "peerDependenciesMeta": { - "class-transformer": { - "optional": true - }, - "class-validator": { - "optional": true - } + "engines": { + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.9.0 <1.10.0" } }, - "node_modules/@nestjs/passport": { - "version": "11.0.5", - "license": "MIT", + "node_modules/@opentelemetry/exporter-metrics-otlp-http": { + "version": "0.205.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/exporter-metrics-otlp-http/-/exporter-metrics-otlp-http-0.205.0.tgz", + "integrity": "sha512-fFxNQ/HbbpLmh1pgU6HUVbFD1kNIjrkoluoKJkh88+gnmpFD92kMQ8WFNjPnSbjg2mNVnEkeKXgCYEowNW+p1w==", + "license": "Apache-2.0", + "dependencies": { + "@opentelemetry/core": "2.1.0", + "@opentelemetry/otlp-exporter-base": "0.205.0", + "@opentelemetry/otlp-transformer": "0.205.0", + "@opentelemetry/resources": "2.1.0", + "@opentelemetry/sdk-metrics": "2.1.0" + }, + "engines": { + "node": "^18.19.0 || >=20.6.0" + }, "peerDependencies": { - "@nestjs/common": "^10.0.0 || ^11.0.0", - "passport": "^0.5.0 || ^0.6.0 || ^0.7.0" + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@nestjs/platform-express": { - "version": "11.1.5", - "resolved": "https://registry.npmjs.org/@nestjs/platform-express/-/platform-express-11.1.5.tgz", - "integrity": "sha512-OsoiUBY9Shs5IG3uvDIt9/IDfY5OlvWBESuB/K4Eun8xILw1EK5d5qMfC3d2sIJ+kA3l+kBR1d/RuzH7VprLIg==", - "license": "MIT", + "node_modules/@opentelemetry/exporter-metrics-otlp-http/node_modules/@opentelemetry/sdk-metrics": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-metrics/-/sdk-metrics-2.1.0.tgz", + "integrity": "sha512-J9QX459mzqHLL9Y6FZ4wQPRZG4TOpMCyPOh6mkr/humxE1W2S3Bvf4i75yiMW9uyed2Kf5rxmLhTm/UK8vNkAw==", + "license": "Apache-2.0", "dependencies": { - "cors": "2.8.5", - "express": "5.1.0", - "multer": "2.0.2", - "path-to-regexp": "8.2.0", - "tslib": "2.8.1" + "@opentelemetry/core": "2.1.0", + "@opentelemetry/resources": "2.1.0" }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/nest" + "engines": { + "node": "^18.19.0 || >=20.6.0" }, "peerDependencies": { - "@nestjs/common": "^11.0.0", - "@nestjs/core": "^11.0.0" + "@opentelemetry/api": ">=1.9.0 <1.10.0" } }, - "node_modules/@nestjs/schematics": { - "version": "11.0.7", - "resolved": "https://registry.npmjs.org/@nestjs/schematics/-/schematics-11.0.7.tgz", - "integrity": "sha512-t8dNYYMwEeEsrlwc2jbkfwCfXczq4AeNEgx1KVQuJ6wYibXk0ZbXbPdfp8scnEAaQv1grpncNV5gWgzi7ZwbvQ==", - "dev": true, - "license": "MIT", + "node_modules/@opentelemetry/exporter-metrics-otlp-proto": { + "version": "0.205.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/exporter-metrics-otlp-proto/-/exporter-metrics-otlp-proto-0.205.0.tgz", + "integrity": "sha512-qIbNnedw9QfFjwpx4NQvdgjK3j3R2kWH/2T+7WXAm1IfMFe9fwatYxE61i7li4CIJKf8HgUC3GS8Du0C3D+AuQ==", + "license": "Apache-2.0", "dependencies": { - "@angular-devkit/core": "19.2.15", - "@angular-devkit/schematics": "19.2.15", - "comment-json": "4.2.5", - "jsonc-parser": "3.3.1", - "pluralize": "8.0.0" + "@opentelemetry/core": "2.1.0", + "@opentelemetry/exporter-metrics-otlp-http": "0.205.0", + "@opentelemetry/otlp-exporter-base": "0.205.0", + "@opentelemetry/otlp-transformer": "0.205.0", + "@opentelemetry/resources": "2.1.0", + "@opentelemetry/sdk-metrics": "2.1.0" + }, + "engines": { + "node": "^18.19.0 || >=20.6.0" }, "peerDependencies": { - "typescript": ">=4.8.2" + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@nestjs/schematics/node_modules/@angular-devkit/core": { - "version": "19.2.15", - "resolved": "https://registry.npmjs.org/@angular-devkit/core/-/core-19.2.15.tgz", - "integrity": "sha512-pU2RZYX6vhd7uLSdLwPnuBcr0mXJSjp3EgOXKsrlQFQZevc+Qs+2JdXgIElnOT/aDqtRtriDmLlSbtdE8n3ZbA==", - "dev": true, - "license": "MIT", + "node_modules/@opentelemetry/exporter-metrics-otlp-proto/node_modules/@opentelemetry/sdk-metrics": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-metrics/-/sdk-metrics-2.1.0.tgz", + "integrity": "sha512-J9QX459mzqHLL9Y6FZ4wQPRZG4TOpMCyPOh6mkr/humxE1W2S3Bvf4i75yiMW9uyed2Kf5rxmLhTm/UK8vNkAw==", + "license": "Apache-2.0", "dependencies": { - "ajv": "8.17.1", - "ajv-formats": "3.0.1", - "jsonc-parser": "3.3.1", - "picomatch": "4.0.2", - "rxjs": "7.8.1", - "source-map": "0.7.4" + "@opentelemetry/core": "2.1.0", + "@opentelemetry/resources": "2.1.0" }, "engines": { - "node": "^18.19.1 || ^20.11.1 || >=22.0.0", - "npm": "^6.11.0 || ^7.5.6 || >=8.0.0", - "yarn": ">= 1.13.0" + "node": "^18.19.0 || >=20.6.0" }, "peerDependencies": { - "chokidar": "^4.0.0" - }, - "peerDependenciesMeta": { - "chokidar": { - "optional": true - } + "@opentelemetry/api": ">=1.9.0 <1.10.0" } }, - "node_modules/@nestjs/schematics/node_modules/@angular-devkit/schematics": { - "version": "19.2.15", - "resolved": "https://registry.npmjs.org/@angular-devkit/schematics/-/schematics-19.2.15.tgz", - "integrity": "sha512-kNOJ+3vekJJCQKWihNmxBkarJzNW09kP5a9E1SRNiQVNOUEeSwcRR0qYotM65nx821gNzjjhJXnAZ8OazWldrg==", - "dev": true, - "license": "MIT", + "node_modules/@opentelemetry/exporter-prometheus": { + "version": "0.205.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/exporter-prometheus/-/exporter-prometheus-0.205.0.tgz", + "integrity": "sha512-xsot/Qm9VLDTag4GEwAunD1XR1U8eBHTLAgO7IZNo2JuD/c/vL7xmDP7mQIUr6Lk3gtj/yGGIR2h3vhTeVzv4w==", + "license": "Apache-2.0", "dependencies": { - "@angular-devkit/core": "19.2.15", - "jsonc-parser": "3.3.1", - "magic-string": "0.30.17", - "ora": "5.4.1", - "rxjs": "7.8.1" + "@opentelemetry/core": "2.1.0", + "@opentelemetry/resources": "2.1.0", + "@opentelemetry/sdk-metrics": "2.1.0" }, "engines": { - "node": "^18.19.1 || ^20.11.1 || >=22.0.0", - "npm": "^6.11.0 || ^7.5.6 || >=8.0.0", - "yarn": ">= 1.13.0" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@nestjs/schematics/node_modules/ajv": { - "version": "8.17.1", - "resolved": "https://registry.npmjs.org/ajv/-/ajv-8.17.1.tgz", - "integrity": "sha512-B/gBuNg5SiMTrPkC+A2+cW0RszwxYmn6VYxB/inlBStS5nx6xHIt/ehKRhIMhqusl7a8LjQoZnjCs5vhwxOQ1g==", - "dev": true, - "license": "MIT", + "node_modules/@opentelemetry/exporter-prometheus/node_modules/@opentelemetry/sdk-metrics": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-metrics/-/sdk-metrics-2.1.0.tgz", + "integrity": "sha512-J9QX459mzqHLL9Y6FZ4wQPRZG4TOpMCyPOh6mkr/humxE1W2S3Bvf4i75yiMW9uyed2Kf5rxmLhTm/UK8vNkAw==", + "license": "Apache-2.0", "dependencies": { - "fast-deep-equal": "^3.1.3", - "fast-uri": "^3.0.1", - "json-schema-traverse": "^1.0.0", - "require-from-string": "^2.0.2" + "@opentelemetry/core": "2.1.0", + "@opentelemetry/resources": "2.1.0" }, - "funding": { - "type": "github", - "url": "https://github.com/sponsors/epoberezkin" + "engines": { + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.9.0 <1.10.0" } }, - "node_modules/@nestjs/schematics/node_modules/chokidar": { - "version": "4.0.3", - "resolved": "https://registry.npmjs.org/chokidar/-/chokidar-4.0.3.tgz", - "integrity": "sha512-Qgzu8kfBvo+cA4962jnP1KkS6Dop5NS6g7R5LFYJr4b8Ub94PPQXUksCw9PvXoeXPRRddRNC5C1JQUR2SMGtnA==", - "dev": true, - "license": "MIT", - "optional": true, - "peer": true, + "node_modules/@opentelemetry/exporter-trace-otlp-grpc": { + "version": "0.205.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/exporter-trace-otlp-grpc/-/exporter-trace-otlp-grpc-0.205.0.tgz", + "integrity": "sha512-ZBksUk84CcQOuDJB65yu5A4PORkC4qEsskNwCrPZxDLeWjPOFZNSWt0E0jQxKCY8PskLhjNXJYo12YaqsYvGFA==", + "license": "Apache-2.0", "dependencies": { - "readdirp": "^4.0.1" + "@grpc/grpc-js": "^1.7.1", + "@opentelemetry/core": "2.1.0", + "@opentelemetry/otlp-exporter-base": "0.205.0", + "@opentelemetry/otlp-grpc-exporter-base": "0.205.0", + "@opentelemetry/otlp-transformer": "0.205.0", + "@opentelemetry/resources": "2.1.0", + "@opentelemetry/sdk-trace-base": "2.1.0" }, "engines": { - "node": ">= 14.16.0" + "node": "^18.19.0 || >=20.6.0" }, - "funding": { - "url": "https://paulmillr.com/funding/" + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@nestjs/schematics/node_modules/json-schema-traverse": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-1.0.0.tgz", - "integrity": "sha512-NM8/P9n3XjXhIZn1lLhkFaACTOURQXjWhV4BA/RnOv8xvgqtqpAX9IO4mRQxSx1Rlo4tqzeqb0sOlruaOy3dug==", - "dev": true, - "license": "MIT" - }, - "node_modules/@nestjs/schematics/node_modules/readdirp": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/readdirp/-/readdirp-4.1.2.tgz", - "integrity": "sha512-GDhwkLfywWL2s6vEjyhri+eXmfH6j1L7JE27WhqLeYzoh/A3DBaYGEj2H/HFZCn/kMfim73FXxEJTw06WtxQwg==", - "dev": true, - "license": "MIT", - "optional": true, - "peer": true, - "engines": { - "node": ">= 14.18.0" + "node_modules/@opentelemetry/exporter-trace-otlp-grpc/node_modules/@opentelemetry/sdk-trace-base": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-trace-base/-/sdk-trace-base-2.1.0.tgz", + "integrity": "sha512-uTX9FBlVQm4S2gVQO1sb5qyBLq/FPjbp+tmGoxu4tIgtYGmBYB44+KX/725RFDe30yBSaA9Ml9fqphe1hbUyLQ==", + "license": "Apache-2.0", + "dependencies": { + "@opentelemetry/core": "2.1.0", + "@opentelemetry/resources": "2.1.0", + "@opentelemetry/semantic-conventions": "^1.29.0" }, - "funding": { - "type": "individual", - "url": "https://paulmillr.com/funding/" + "engines": { + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.3.0 <1.10.0" } }, - "node_modules/@nestjs/schematics/node_modules/rxjs": { - "version": "7.8.1", - "resolved": "https://registry.npmjs.org/rxjs/-/rxjs-7.8.1.tgz", - "integrity": "sha512-AA3TVj+0A2iuIoQkWEK/tqFjBq2j+6PO6Y0zJcvzLAFhEFIO3HL0vls9hWLncZbAAbK0mar7oZ4V079I/qPMxg==", - "dev": true, + "node_modules/@opentelemetry/exporter-trace-otlp-http": { + "version": "0.205.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/exporter-trace-otlp-http/-/exporter-trace-otlp-http-0.205.0.tgz", + "integrity": "sha512-vr2bwwPCSc9u7rbKc74jR+DXFvyMFQo9o5zs+H/fgbK672Whw/1izUKVf+xfWOdJOvuwTnfWxy+VAY+4TSo74Q==", "license": "Apache-2.0", "dependencies": { - "tslib": "^2.1.0" + "@opentelemetry/core": "2.1.0", + "@opentelemetry/otlp-exporter-base": "0.205.0", + "@opentelemetry/otlp-transformer": "0.205.0", + "@opentelemetry/resources": "2.1.0", + "@opentelemetry/sdk-trace-base": "2.1.0" + }, + "engines": { + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@nestjs/swagger": { - "version": "11.2.0", - "license": "MIT", + "node_modules/@opentelemetry/exporter-trace-otlp-http/node_modules/@opentelemetry/sdk-trace-base": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-trace-base/-/sdk-trace-base-2.1.0.tgz", + "integrity": "sha512-uTX9FBlVQm4S2gVQO1sb5qyBLq/FPjbp+tmGoxu4tIgtYGmBYB44+KX/725RFDe30yBSaA9Ml9fqphe1hbUyLQ==", + "license": "Apache-2.0", "dependencies": { - "@microsoft/tsdoc": "0.15.1", - "@nestjs/mapped-types": "2.1.0", - "js-yaml": "4.1.0", - "lodash": "4.17.21", - "path-to-regexp": "8.2.0", - "swagger-ui-dist": "5.21.0" + "@opentelemetry/core": "2.1.0", + "@opentelemetry/resources": "2.1.0", + "@opentelemetry/semantic-conventions": "^1.29.0" }, - "peerDependencies": { - "@fastify/static": "^8.0.0", - "@nestjs/common": "^11.0.1", - "@nestjs/core": "^11.0.1", - "class-transformer": "*", - "class-validator": "*", - "reflect-metadata": "^0.1.12 || ^0.2.0" + "engines": { + "node": "^18.19.0 || >=20.6.0" }, - "peerDependenciesMeta": { - "@fastify/static": { - "optional": true - }, - "class-transformer": { - "optional": true - }, - "class-validator": { - "optional": true - } + "peerDependencies": { + "@opentelemetry/api": ">=1.3.0 <1.10.0" } }, - "node_modules/@nestjs/terminus": { - "version": "11.0.0", - "license": "MIT", + "node_modules/@opentelemetry/exporter-trace-otlp-proto": { + "version": "0.205.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/exporter-trace-otlp-proto/-/exporter-trace-otlp-proto-0.205.0.tgz", + "integrity": "sha512-bGtFzqiENO2GpJk988mOBMe0MfeNpTQjbLm/LBijas6VRyEDQarUzdBHpFlu89A25k1+BCntdWGsWTa9Ai4FyA==", + "license": "Apache-2.0", "dependencies": { - "boxen": "5.1.2", - "check-disk-space": "3.4.0" + "@opentelemetry/core": "2.1.0", + "@opentelemetry/otlp-exporter-base": "0.205.0", + "@opentelemetry/otlp-transformer": "0.205.0", + "@opentelemetry/resources": "2.1.0", + "@opentelemetry/sdk-trace-base": "2.1.0" }, - "peerDependencies": { - "@grpc/grpc-js": "*", - "@grpc/proto-loader": "*", - "@mikro-orm/core": "*", - "@mikro-orm/nestjs": "*", - "@nestjs/axios": "^2.0.0 || ^3.0.0 || ^4.0.0", - "@nestjs/common": "^10.0.0 || ^11.0.0", - "@nestjs/core": "^10.0.0 || ^11.0.0", - "@nestjs/microservices": "^10.0.0 || ^11.0.0", - "@nestjs/mongoose": "^11.0.0", - "@nestjs/sequelize": "^10.0.0 || ^11.0.0", - "@nestjs/typeorm": "^10.0.0 || ^11.0.0", - "@prisma/client": "*", - "mongoose": "*", - "reflect-metadata": "0.1.x || 0.2.x", - "rxjs": "7.x", - "sequelize": "*", - "typeorm": "*" + "engines": { + "node": "^18.19.0 || >=20.6.0" }, - "peerDependenciesMeta": { - "@grpc/grpc-js": { - "optional": true - }, - "@grpc/proto-loader": { - "optional": true - }, - "@mikro-orm/core": { - "optional": true - }, - "@mikro-orm/nestjs": { - "optional": true - }, - "@nestjs/axios": { - "optional": true - }, - "@nestjs/microservices": { - "optional": true - }, - "@nestjs/mongoose": { - "optional": true - }, - "@nestjs/sequelize": { - "optional": true - }, - "@nestjs/typeorm": { - "optional": true - }, - "@prisma/client": { - "optional": true - }, - "mongoose": { - "optional": true - }, - "sequelize": { - "optional": true - }, - "typeorm": { - "optional": true - } + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@nestjs/testing": { - "version": "11.1.5", - "resolved": "https://registry.npmjs.org/@nestjs/testing/-/testing-11.1.5.tgz", - "integrity": "sha512-ZYRYF750SefmuIo7ZqPlHDcin1OHh6My0OkOfGEFjrD9mJ0vMVIpwMTOOkpzCfCcpqUuxeHBuecpiIn+NLrQbQ==", - "dev": true, - "license": "MIT", + "node_modules/@opentelemetry/exporter-trace-otlp-proto/node_modules/@opentelemetry/sdk-trace-base": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-trace-base/-/sdk-trace-base-2.1.0.tgz", + "integrity": "sha512-uTX9FBlVQm4S2gVQO1sb5qyBLq/FPjbp+tmGoxu4tIgtYGmBYB44+KX/725RFDe30yBSaA9Ml9fqphe1hbUyLQ==", + "license": "Apache-2.0", "dependencies": { - "tslib": "2.8.1" + "@opentelemetry/core": "2.1.0", + "@opentelemetry/resources": "2.1.0", + "@opentelemetry/semantic-conventions": "^1.29.0" }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/nest" + "engines": { + "node": "^18.19.0 || >=20.6.0" }, "peerDependencies": { - "@nestjs/common": "^11.0.0", - "@nestjs/core": "^11.0.0", - "@nestjs/microservices": "^11.0.0", - "@nestjs/platform-express": "^11.0.0" - }, - "peerDependenciesMeta": { - "@nestjs/microservices": { - "optional": true - }, - "@nestjs/platform-express": { - "optional": true - } + "@opentelemetry/api": ">=1.3.0 <1.10.0" } }, - "node_modules/@nestjs/typeorm": { - "version": "11.0.0", - "license": "MIT", + "node_modules/@opentelemetry/exporter-zipkin": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/exporter-zipkin/-/exporter-zipkin-2.1.0.tgz", + "integrity": "sha512-0mEI0VDZrrX9t5RE1FhAyGz+jAGt96HSuXu73leswtY3L5YZD11gtcpARY2KAx/s6Z2+rj5Mhj566JsI2C7mfA==", + "license": "Apache-2.0", + "dependencies": { + "@opentelemetry/core": "2.1.0", + "@opentelemetry/resources": "2.1.0", + "@opentelemetry/sdk-trace-base": "2.1.0", + "@opentelemetry/semantic-conventions": "^1.29.0" + }, + "engines": { + "node": "^18.19.0 || >=20.6.0" + }, "peerDependencies": { - "@nestjs/common": "^10.0.0 || ^11.0.0", - "@nestjs/core": "^10.0.0 || ^11.0.0", - "reflect-metadata": "^0.1.13 || ^0.2.0", - "rxjs": "^7.2.0", - "typeorm": "^0.3.0" + "@opentelemetry/api": "^1.0.0" } }, - "node_modules/@noble/hashes": { - "version": "1.8.0", - "resolved": "https://registry.npmjs.org/@noble/hashes/-/hashes-1.8.0.tgz", - "integrity": "sha512-jCs9ldd7NwzpgXDIf6P3+NrHh9/sD6CQdxHyjQI+h/6rDNo88ypBxxz45UDuZHz9r3tNz7N/VInSVoVdtXEI4A==", - "dev": true, + "node_modules/@opentelemetry/exporter-zipkin/node_modules/@opentelemetry/sdk-trace-base": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-trace-base/-/sdk-trace-base-2.1.0.tgz", + "integrity": "sha512-uTX9FBlVQm4S2gVQO1sb5qyBLq/FPjbp+tmGoxu4tIgtYGmBYB44+KX/725RFDe30yBSaA9Ml9fqphe1hbUyLQ==", + "license": "Apache-2.0", + "dependencies": { + "@opentelemetry/core": "2.1.0", + "@opentelemetry/resources": "2.1.0", + "@opentelemetry/semantic-conventions": "^1.29.0" + }, "engines": { - "node": "^14.21.3 || >=16" + "node": "^18.19.0 || >=20.6.0" }, - "funding": { - "url": "https://paulmillr.com/funding/" + "peerDependencies": { + "@opentelemetry/api": ">=1.3.0 <1.10.0" } }, - "node_modules/@nodelib/fs.scandir": { - "version": "2.1.5", - "resolved": "https://registry.npmjs.org/@nodelib/fs.scandir/-/fs.scandir-2.1.5.tgz", - "integrity": "sha512-vq24Bq3ym5HEQm2NKCr3yXDwjc7vTsEThRDnkp2DK9p1uqLR+DHurm/NOTo0KG7HYHU7eppKZj3MyqYuMBf62g==", - "dev": true, - "license": "MIT", + "node_modules/@opentelemetry/instrumentation": { + "version": "0.205.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation/-/instrumentation-0.205.0.tgz", + "integrity": "sha512-cgvm7tvQdu9Qo7VurJP84wJ7ZV9F6WqDDGZpUc6rUEXwjV7/bXWs0kaYp9v+1Vh1+3TZCD3i6j/lUBcPhu8NhA==", + "license": "Apache-2.0", "dependencies": { - "@nodelib/fs.stat": "2.0.5", - "run-parallel": "^1.1.9" + "@opentelemetry/api-logs": "0.205.0", + "import-in-the-middle": "^1.8.1", + "require-in-the-middle": "^7.1.1" }, "engines": { - "node": ">= 8" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@nodelib/fs.stat": { - "version": "2.0.5", - "resolved": "https://registry.npmjs.org/@nodelib/fs.stat/-/fs.stat-2.0.5.tgz", - "integrity": "sha512-RkhPPp2zrqDAQA/2jNhnztcPAlv64XdhIp7a7454A5ovI7Bukxgt7MX7udwAu3zg1DcpPU0rz3VV1SeaqvY4+A==", - "dev": true, - "license": "MIT", + "node_modules/@opentelemetry/instrumentation-amqplib": { + "version": "0.52.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation-amqplib/-/instrumentation-amqplib-0.52.0.tgz", + "integrity": "sha512-G8RnaoDxfwYe6uXC7erNGzYJi0gY/xMSu+fPthQr9Won8+/ot9kqt48WQCk9OA2uiV67lSPs5hiDKKBBOcvJCA==", + "license": "Apache-2.0", + "dependencies": { + "@opentelemetry/core": "^2.0.0", + "@opentelemetry/instrumentation": "^0.205.0", + "@opentelemetry/semantic-conventions": "^1.27.0" + }, "engines": { - "node": ">= 8" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@nodelib/fs.walk": { - "version": "1.2.8", - "resolved": "https://registry.npmjs.org/@nodelib/fs.walk/-/fs.walk-1.2.8.tgz", - "integrity": "sha512-oGB+UxlgWcgQkgwo8GcEGwemoTFt3FIO9ababBmaGwXIoBKZ+GTy0pP185beGg7Llih/NSHSV2XAs1lnznocSg==", - "dev": true, - "license": "MIT", + "node_modules/@opentelemetry/instrumentation-aws-lambda": { + "version": "0.56.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation-aws-lambda/-/instrumentation-aws-lambda-0.56.0.tgz", + "integrity": "sha512-QS3rhpdcuHzGQB84Qfy8cV75rP9R3vZ8lcUiRkRh+Uu3/+QnaXET1eOi9kS8Jc5I3uoLEz6L/A61I7lUXZ+U4A==", + "license": "Apache-2.0", "dependencies": { - "@nodelib/fs.scandir": "2.1.5", - "fastq": "^1.6.0" + "@opentelemetry/instrumentation": "^0.205.0", + "@opentelemetry/semantic-conventions": "^1.27.0", + "@types/aws-lambda": "8.10.152" }, "engines": { - "node": ">= 8" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@nuxt/opencollective": { - "version": "0.4.1", - "license": "MIT", + "node_modules/@opentelemetry/instrumentation-aws-sdk": { + "version": "0.60.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation-aws-sdk/-/instrumentation-aws-sdk-0.60.0.tgz", + "integrity": "sha512-TX5tSQpSNO1um0xyQBmTIDqd4ANh/rOXJCZWHkKEKStfZH3vTxfunkTOCSWdzIcCfft+PaEJcLFjCivr34/6pQ==", + "license": "Apache-2.0", "dependencies": { - "consola": "^3.2.3" - }, - "bin": { - "opencollective": "bin/opencollective.js" + "@opentelemetry/core": "^2.0.0", + "@opentelemetry/instrumentation": "^0.205.0", + "@opentelemetry/semantic-conventions": "^1.34.0" }, "engines": { - "node": "^14.18.0 || >=16.10.0", - "npm": ">=5.10.0" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@nuxtjs/opencollective": { - "version": "0.3.2", - "dev": true, - "license": "MIT", + "node_modules/@opentelemetry/instrumentation-bunyan": { + "version": "0.51.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation-bunyan/-/instrumentation-bunyan-0.51.0.tgz", + "integrity": "sha512-N84VeifmawRyTrGkIhHRzzpHyaWkbD8fnVHg4LpbbFW1nQJcQphDE62kvuqKrzezIUbaYeS7Ue+tHV2WveTe9w==", + "license": "Apache-2.0", "dependencies": { - "chalk": "^4.1.0", - "consola": "^2.15.0", - "node-fetch": "^2.6.1" - }, - "bin": { - "opencollective": "bin/opencollective.js" + "@opentelemetry/api-logs": "^0.205.0", + "@opentelemetry/instrumentation": "^0.205.0", + "@types/bunyan": "1.8.11" }, "engines": { - "node": ">=8.0.0", - "npm": ">=5.0.0" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@nuxtjs/opencollective/node_modules/consola": { - "version": "2.15.3", - "dev": true, - "license": "MIT" - }, - "node_modules/@openapitools/openapi-generator-cli": { - "version": "2.21.0", - "resolved": "https://registry.npmjs.org/@openapitools/openapi-generator-cli/-/openapi-generator-cli-2.21.0.tgz", - "integrity": "sha512-NdDvCd7hya+UucxH7G94Jf6tmA6641I4CF/T3xtFhM+NQQNWAP5tpiOBN4Ub9ocU6cCgQgXdWl4EpwlEwW7JDQ==", - "dev": true, - "hasInstallScript": true, + "node_modules/@opentelemetry/instrumentation-cassandra-driver": { + "version": "0.51.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation-cassandra-driver/-/instrumentation-cassandra-driver-0.51.0.tgz", + "integrity": "sha512-Qy8SmLCqXPzP3vMRcwWYtpAnOdhdU1WhAnvGoS8JMNvn48sush42CjJIYkQmsgpz676WDkrppCQ4V5T0nD5z4A==", "license": "Apache-2.0", "dependencies": { - "@nestjs/axios": "4.0.0", - "@nestjs/common": "11.1.3", - "@nestjs/core": "11.1.3", - "@nuxtjs/opencollective": "0.3.2", - "axios": "1.10.0", - "chalk": "4.1.2", - "commander": "8.3.0", - "compare-versions": "4.1.4", - "concurrently": "6.5.1", - "console.table": "0.10.0", - "fs-extra": "11.3.0", - "glob": "11.0.3", - "inquirer": "8.2.6", - "lodash": "4.17.21", - "proxy-agent": "6.5.0", - "reflect-metadata": "0.2.2", - "rxjs": "7.8.2", - "tslib": "2.8.1" - }, - "bin": { - "openapi-generator-cli": "main.js" + "@opentelemetry/instrumentation": "^0.205.0", + "@opentelemetry/semantic-conventions": "^1.27.0" }, "engines": { - "node": ">=16" + "node": "^18.19.0 || >=20.6.0" }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/openapi_generator" + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@openapitools/openapi-generator-cli/node_modules/commander": { - "version": "8.3.0", - "resolved": "https://registry.npmjs.org/commander/-/commander-8.3.0.tgz", - "integrity": "sha512-OkTL9umf+He2DZkUq8f8J9of7yL6RJKI24dVITBmNfZBmri9zYZQrKkuXiKhyfPSu8tUhnVBB1iKXevvnlR4Ww==", - "dev": true, - "license": "MIT", + "node_modules/@opentelemetry/instrumentation-connect": { + "version": "0.49.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation-connect/-/instrumentation-connect-0.49.0.tgz", + "integrity": "sha512-mcGcz9w9gtJuNM3ErxBiwsVSgFkPu97Guxt16cxaZZKQkm+6he5qtQbUfLsmEj5tgaF0c3K4jvXhRQsusNilSQ==", + "license": "Apache-2.0", + "dependencies": { + "@opentelemetry/core": "^2.0.0", + "@opentelemetry/instrumentation": "^0.205.0", + "@opentelemetry/semantic-conventions": "^1.27.0", + "@types/connect": "3.4.38" + }, "engines": { - "node": ">= 12" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@openapitools/openapi-generator-cli/node_modules/glob": { - "version": "11.0.3", - "resolved": "https://registry.npmjs.org/glob/-/glob-11.0.3.tgz", - "integrity": "sha512-2Nim7dha1KVkaiF4q6Dj+ngPPMdfvLJEOpZk/jKiUAkqKebpGAWQXAq9z1xu9HKu5lWfqw/FASuccEjyznjPaA==", - "dev": true, - "license": "ISC", + "node_modules/@opentelemetry/instrumentation-cucumber": { + "version": "0.21.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation-cucumber/-/instrumentation-cucumber-0.21.0.tgz", + "integrity": "sha512-a9v73VpANHK5MiiK2TxhDHVYPbbSofuKAhiE+3EUyTinz7KkLzUS4zk7sKip4yWzu04HmJ5N2S4Ke85dXpgK1g==", + "license": "Apache-2.0", "dependencies": { - "foreground-child": "^3.3.1", - "jackspeak": "^4.1.1", - "minimatch": "^10.0.3", - "minipass": "^7.1.2", - "package-json-from-dist": "^1.0.0", - "path-scurry": "^2.0.0" - }, - "bin": { - "glob": "dist/esm/bin.mjs" + "@opentelemetry/instrumentation": "^0.205.0", + "@opentelemetry/semantic-conventions": "^1.27.0" }, "engines": { - "node": "20 || >=22" + "node": "^18.19.0 || >=20.6.0" }, - "funding": { - "url": "https://github.com/sponsors/isaacs" + "peerDependencies": { + "@opentelemetry/api": "^1.0.0" } }, - "node_modules/@openapitools/openapi-generator-cli/node_modules/minimatch": { - "version": "10.0.3", - "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-10.0.3.tgz", - "integrity": "sha512-IPZ167aShDZZUMdRk66cyQAW3qr0WzbHkPdMYa8bzZhlHhO3jALbKdxcaak7W9FfT2rZNpQuUu4Od7ILEpXSaw==", - "dev": true, - "license": "ISC", + "node_modules/@opentelemetry/instrumentation-dataloader": { + "version": "0.23.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation-dataloader/-/instrumentation-dataloader-0.23.0.tgz", + "integrity": "sha512-HLPl6/kCcHMoMjVHy+nqBZa2ODSUdSRHOG63+ZRRn5JAeFLj74U/gZ93qNzip1nVSWYaPRxclSfDb44E2PH72w==", + "license": "Apache-2.0", "dependencies": { - "@isaacs/brace-expansion": "^5.0.0" + "@opentelemetry/instrumentation": "^0.205.0" }, "engines": { - "node": "20 || >=22" + "node": "^18.19.0 || >=20.6.0" }, - "funding": { - "url": "https://github.com/sponsors/isaacs" + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@opentelemetry/api": { - "version": "1.9.0", + "node_modules/@opentelemetry/instrumentation-dns": { + "version": "0.49.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation-dns/-/instrumentation-dns-0.49.0.tgz", + "integrity": "sha512-DWVfSI5oH1X9sh4bMJd4HOWQ+UCqHLp76s8X8dw8+TPP10jI8Ca9oyoCjNPxS4GMpFFDYtCLlFgsPq7LfTcN2A==", "license": "Apache-2.0", + "dependencies": { + "@opentelemetry/instrumentation": "^0.205.0" + }, "engines": { - "node": ">=8.0.0" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@paralleldrive/cuid2": { - "version": "2.2.2", - "resolved": "https://registry.npmjs.org/@paralleldrive/cuid2/-/cuid2-2.2.2.tgz", - "integrity": "sha512-ZOBkgDwEdoYVlSeRbYYXs0S9MejQofiVYoTbKzy/6GQa39/q5tQU2IX46+shYnUkpEl3wc+J6wRlar7r2EK2xA==", - "dev": true, + "node_modules/@opentelemetry/instrumentation-express": { + "version": "0.54.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation-express/-/instrumentation-express-0.54.0.tgz", + "integrity": "sha512-Bar+y7h4qs9MSrU8ItaOAMOYmXVC0xCh5RCBDqaPsMeBmWMc2IUD3l0R6Ts+qL5extJCbboD7JKcQPXHPbMOGw==", + "license": "Apache-2.0", "dependencies": { - "@noble/hashes": "^1.1.5" + "@opentelemetry/core": "^2.0.0", + "@opentelemetry/instrumentation": "^0.205.0", + "@opentelemetry/semantic-conventions": "^1.27.0" + }, + "engines": { + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@pkgjs/parseargs": { - "version": "0.11.0", - "license": "MIT", - "optional": true, + "node_modules/@opentelemetry/instrumentation-fastify": { + "version": "0.50.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation-fastify/-/instrumentation-fastify-0.50.0.tgz", + "integrity": "sha512-j30yphIxdt6Wm8dgUoRORSORxlcFX2IxCLV6QZ9G5HtvvMIEP0hA0UnhJ3CDrDHKJRSHCiW8E8piOSbtU+0MLA==", + "license": "Apache-2.0", + "dependencies": { + "@opentelemetry/core": "^2.0.0", + "@opentelemetry/instrumentation": "^0.205.0", + "@opentelemetry/semantic-conventions": "^1.27.0" + }, "engines": { - "node": ">=14" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@pkgr/core": { - "version": "0.2.4", - "dev": true, - "license": "MIT", + "node_modules/@opentelemetry/instrumentation-fs": { + "version": "0.25.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation-fs/-/instrumentation-fs-0.25.0.tgz", + "integrity": "sha512-U19QQ4WfbAjty1grQQoMFrhB0HIsAQktu41nN50E+T2defjz4OC2IvNwfAJFWT7gGzFA23daxzOS7+DumZOVMg==", + "license": "Apache-2.0", + "dependencies": { + "@opentelemetry/core": "^2.0.0", + "@opentelemetry/instrumentation": "^0.205.0" + }, "engines": { - "node": "^12.20.0 || ^14.18.0 || >=16.0.0" + "node": "^18.19.0 || >=20.6.0" }, - "funding": { - "url": "https://opencollective.com/pkgr" + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@playwright/test": { - "version": "1.52.0", + "node_modules/@opentelemetry/instrumentation-generic-pool": { + "version": "0.49.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation-generic-pool/-/instrumentation-generic-pool-0.49.0.tgz", + "integrity": "sha512-HwZmSNb7gjbWBXST/+elp8CnOZ5tvT1pOFr4GjnWpCdpx31lHhEA8cLhkao+hozqg+uMl1/nmTXR78vnIbG+8g==", "license": "Apache-2.0", - "peer": true, "dependencies": { - "playwright": "1.52.0" - }, - "bin": { - "playwright": "cli.js" + "@opentelemetry/instrumentation": "^0.205.0" }, "engines": { - "node": ">=18" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@protobufjs/aspromise": { - "version": "1.1.2", - "license": "BSD-3-Clause" - }, - "node_modules/@protobufjs/base64": { - "version": "1.1.2", - "license": "BSD-3-Clause" - }, - "node_modules/@protobufjs/codegen": { - "version": "2.0.4", - "license": "BSD-3-Clause" - }, - "node_modules/@protobufjs/eventemitter": { - "version": "1.1.0", - "license": "BSD-3-Clause" - }, - "node_modules/@protobufjs/fetch": { - "version": "1.1.0", - "license": "BSD-3-Clause", + "node_modules/@opentelemetry/instrumentation-graphql": { + "version": "0.53.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation-graphql/-/instrumentation-graphql-0.53.0.tgz", + "integrity": "sha512-yVYgGlkfwOlBTqOm4YI9oHw0sWB18CpYMbxan2UMo7UAgm6JQ6ikur0c2T1ALp2jnkXv0XnR1PkYBGmGYUjG8A==", + "license": "Apache-2.0", "dependencies": { - "@protobufjs/aspromise": "^1.1.1", - "@protobufjs/inquire": "^1.1.0" + "@opentelemetry/instrumentation": "^0.205.0" + }, + "engines": { + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@protobufjs/float": { - "version": "1.0.2", - "license": "BSD-3-Clause" - }, - "node_modules/@protobufjs/inquire": { - "version": "1.1.0", - "license": "BSD-3-Clause" - }, - "node_modules/@protobufjs/path": { - "version": "1.1.2", - "license": "BSD-3-Clause" - }, - "node_modules/@protobufjs/pool": { - "version": "1.1.0", - "license": "BSD-3-Clause" - }, - "node_modules/@protobufjs/utf8": { - "version": "1.1.0", - "license": "BSD-3-Clause" - }, - "node_modules/@rtsao/scc": { - "version": "1.1.0", - "dev": true, - "license": "MIT" + "node_modules/@opentelemetry/instrumentation-grpc": { + "version": "0.205.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation-grpc/-/instrumentation-grpc-0.205.0.tgz", + "integrity": "sha512-IB5eKpb/7/x+tyWUVIIyY5KcAtODy/YbcDKPdnlJl8sMCFPByjNxti/lzOfPajYBPOXsN91g7H7cN0L1aSlerQ==", + "license": "Apache-2.0", + "dependencies": { + "@opentelemetry/instrumentation": "0.205.0", + "@opentelemetry/semantic-conventions": "^1.29.0" + }, + "engines": { + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" + } }, - "node_modules/@scarf/scarf": { - "version": "1.4.0", - "hasInstallScript": true, - "license": "Apache-2.0" + "node_modules/@opentelemetry/instrumentation-hapi": { + "version": "0.52.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation-hapi/-/instrumentation-hapi-0.52.0.tgz", + "integrity": "sha512-Hd39MAnYC+PrlWLpAwmkcZJE9l2g6Tie3Flg6gcHTEfs3WFJZb5WmfagDTKDujLwTMwc+setqjDJm/EOJyGXig==", + "license": "Apache-2.0", + "dependencies": { + "@opentelemetry/core": "^2.0.0", + "@opentelemetry/instrumentation": "^0.205.0", + "@opentelemetry/semantic-conventions": "^1.27.0" + }, + "engines": { + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" + } }, - "node_modules/@sinclair/typebox": { - "version": "0.27.8", - "dev": true, - "license": "MIT" + "node_modules/@opentelemetry/instrumentation-http": { + "version": "0.205.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation-http/-/instrumentation-http-0.205.0.tgz", + "integrity": "sha512-6fOgRlV7ypBuEzCQP7vXkLQxz3UL1FhE24rAlMRbwGvPAnZLvutcG/fq9FI/n+VU23dOpYexocYsXCf5oy/AXw==", + "license": "Apache-2.0", + "dependencies": { + "@opentelemetry/core": "2.1.0", + "@opentelemetry/instrumentation": "0.205.0", + "@opentelemetry/semantic-conventions": "^1.29.0", + "forwarded-parse": "2.1.2" + }, + "engines": { + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" + } }, - "node_modules/@sinonjs/commons": { - "version": "3.0.1", - "dev": true, - "license": "BSD-3-Clause", + "node_modules/@opentelemetry/instrumentation-ioredis": { + "version": "0.53.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation-ioredis/-/instrumentation-ioredis-0.53.0.tgz", + "integrity": "sha512-Ah2wU347vOJYbE563Tgm3UX2J3DAXoI8gsr8qH0OOO4uDuEv3kVS/eDCfXApt11bvvDDPlOoc60/TGn6m9IoPw==", + "license": "Apache-2.0", "dependencies": { - "type-detect": "4.0.8" + "@opentelemetry/instrumentation": "^0.205.0", + "@opentelemetry/redis-common": "^0.38.0", + "@opentelemetry/semantic-conventions": "^1.27.0" + }, + "engines": { + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@sinonjs/fake-timers": { - "version": "10.3.0", - "dev": true, - "license": "BSD-3-Clause", + "node_modules/@opentelemetry/instrumentation-kafkajs": { + "version": "0.15.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation-kafkajs/-/instrumentation-kafkajs-0.15.0.tgz", + "integrity": "sha512-bfMRg8ICe8ICZgP8Nezy8xxov/uBQ7518r2h7puwKUZeEqga+5F+hKVL9to0aVlPWTAiHgEjdOAdP1D5eRzvuw==", + "license": "Apache-2.0", "dependencies": { - "@sinonjs/commons": "^3.0.0" + "@opentelemetry/instrumentation": "^0.205.0", + "@opentelemetry/semantic-conventions": "^1.30.0" + }, + "engines": { + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@smithy/abort-controller": { - "version": "4.0.2", + "node_modules/@opentelemetry/instrumentation-knex": { + "version": "0.50.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation-knex/-/instrumentation-knex-0.50.0.tgz", + "integrity": "sha512-kuQaU0BLMF1alpRS8pR7j2hA38h9M2c09EijfhVwhm63zzQoT34RLOB37maLepx9nY3EJo4ohZUHTnNmHE10ZQ==", "license": "Apache-2.0", "dependencies": { - "@smithy/types": "^4.2.0", - "tslib": "^2.6.2" + "@opentelemetry/instrumentation": "^0.205.0", + "@opentelemetry/semantic-conventions": "^1.33.1" }, "engines": { - "node": ">=18.0.0" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@smithy/config-resolver": { - "version": "4.1.2", + "node_modules/@opentelemetry/instrumentation-koa": { + "version": "0.53.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation-koa/-/instrumentation-koa-0.53.0.tgz", + "integrity": "sha512-aZbivQx+IXZpqkMWWH8RlZNVsaJnPExYfGiUdzOtjwPLQqXVV1SN4gzzPC0kL1r6BVK6NKwUSQI6jznV81i8aQ==", "license": "Apache-2.0", "dependencies": { - "@smithy/node-config-provider": "^4.1.1", - "@smithy/types": "^4.2.0", - "@smithy/util-config-provider": "^4.0.0", - "@smithy/util-middleware": "^4.0.2", - "tslib": "^2.6.2" + "@opentelemetry/core": "^2.0.0", + "@opentelemetry/instrumentation": "^0.205.0", + "@opentelemetry/semantic-conventions": "^1.27.0" }, "engines": { - "node": ">=18.0.0" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@smithy/core": { - "version": "3.3.1", + "node_modules/@opentelemetry/instrumentation-lru-memoizer": { + "version": "0.50.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation-lru-memoizer/-/instrumentation-lru-memoizer-0.50.0.tgz", + "integrity": "sha512-2mI3Yv7vzlNU1LURY1Jp3lgzICqKWeyeNEljGN2PUuOXwAoWviQwmFzTI5FoSnbWflANUvKGL1j0NH3KjagjdA==", "license": "Apache-2.0", "dependencies": { - "@smithy/middleware-serde": "^4.0.3", - "@smithy/protocol-http": "^5.1.0", - "@smithy/types": "^4.2.0", - "@smithy/util-body-length-browser": "^4.0.0", - "@smithy/util-middleware": "^4.0.2", - "@smithy/util-stream": "^4.2.0", - "@smithy/util-utf8": "^4.0.0", - "tslib": "^2.6.2" + "@opentelemetry/instrumentation": "^0.205.0" }, "engines": { - "node": ">=18.0.0" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@smithy/core/node_modules/@smithy/protocol-http": { - "version": "5.1.0", + "node_modules/@opentelemetry/instrumentation-memcached": { + "version": "0.49.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation-memcached/-/instrumentation-memcached-0.49.0.tgz", + "integrity": "sha512-TyurQ0NqbeV1Y12Cw72rXKikSkeeGVPNwCCRkA4Y60k0asVD3MCfnFs6Kpy1sZWMvqkSelLJbjuGh0yLJ3GN3A==", "license": "Apache-2.0", "dependencies": { - "@smithy/types": "^4.2.0", - "tslib": "^2.6.2" + "@opentelemetry/instrumentation": "^0.205.0", + "@opentelemetry/semantic-conventions": "^1.27.0", + "@types/memcached": "^2.2.6" }, "engines": { - "node": ">=18.0.0" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@smithy/core/node_modules/@smithy/util-utf8": { - "version": "4.0.0", + "node_modules/@opentelemetry/instrumentation-mongodb": { + "version": "0.58.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation-mongodb/-/instrumentation-mongodb-0.58.0.tgz", + "integrity": "sha512-h6vrdfCE7qhflgZV41l7vAXUzvbt0ukuHrJ/9ByfNEWiCkNd7tW4FRKdJilWYzr6Nr69ddzMq6vtVFN0WUABUw==", "license": "Apache-2.0", "dependencies": { - "@smithy/util-buffer-from": "^4.0.0", - "tslib": "^2.6.2" + "@opentelemetry/instrumentation": "^0.205.0", + "@opentelemetry/semantic-conventions": "^1.27.0" }, "engines": { - "node": ">=18.0.0" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@smithy/credential-provider-imds": { - "version": "4.0.4", + "node_modules/@opentelemetry/instrumentation-mongoose": { + "version": "0.52.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation-mongoose/-/instrumentation-mongoose-0.52.0.tgz", + "integrity": "sha512-qdpq/hZO353UpD5FxmBowpuI+HinPEOmi7feQzX9GO1PCTmlGGzaeQ8xwUX1eA0OKg0YDrKuiWsFxlLoOXsocw==", "license": "Apache-2.0", "dependencies": { - "@smithy/node-config-provider": "^4.1.1", - "@smithy/property-provider": "^4.0.2", - "@smithy/types": "^4.2.0", - "@smithy/url-parser": "^4.0.2", - "tslib": "^2.6.2" + "@opentelemetry/core": "^2.0.0", + "@opentelemetry/instrumentation": "^0.205.0", + "@opentelemetry/semantic-conventions": "^1.27.0" }, "engines": { - "node": ">=18.0.0" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@smithy/eventstream-serde-browser": { - "version": "4.0.2", + "node_modules/@opentelemetry/instrumentation-mysql": { + "version": "0.51.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation-mysql/-/instrumentation-mysql-0.51.0.tgz", + "integrity": "sha512-WBCG18gMo7rNem5CZ3uXpnfbdN6PLMg2ioikL7G/cHNzjbcvGGuf/x6vBNMdmOUqLSIeVgEtnbniCo/GOrWcgw==", "license": "Apache-2.0", "dependencies": { - "@smithy/eventstream-serde-universal": "^4.0.2", - "@smithy/types": "^4.2.0", - "tslib": "^2.6.2" + "@opentelemetry/instrumentation": "^0.205.0", + "@opentelemetry/semantic-conventions": "^1.27.0", + "@types/mysql": "2.15.27" }, "engines": { - "node": ">=18.0.0" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@smithy/eventstream-serde-config-resolver": { - "version": "4.1.0", + "node_modules/@opentelemetry/instrumentation-mysql2": { + "version": "0.52.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation-mysql2/-/instrumentation-mysql2-0.52.0.tgz", + "integrity": "sha512-+yuck72xsX8QE0B4IJpLzmGiAz8yeLHfVHBkTOR3GKfLz4D88AUx7O3QJW/uqkQQSDQOJybRRazOZfhC1Bkz3A==", "license": "Apache-2.0", "dependencies": { - "@smithy/types": "^4.2.0", - "tslib": "^2.6.2" + "@opentelemetry/instrumentation": "^0.205.0", + "@opentelemetry/semantic-conventions": "^1.27.0", + "@opentelemetry/sql-common": "^0.41.0" }, "engines": { - "node": ">=18.0.0" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@smithy/eventstream-serde-node": { - "version": "4.0.2", + "node_modules/@opentelemetry/instrumentation-nestjs-core": { + "version": "0.51.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation-nestjs-core/-/instrumentation-nestjs-core-0.51.0.tgz", + "integrity": "sha512-Se/m4887W94OO12pjKMjI3398L7HCoWeCjcbwoPvNOWpSpMkljBOHA9vE/fyo63CaVG1XAM5xA4ad60wmJKl9A==", "license": "Apache-2.0", "dependencies": { - "@smithy/eventstream-serde-universal": "^4.0.2", - "@smithy/types": "^4.2.0", - "tslib": "^2.6.2" + "@opentelemetry/instrumentation": "^0.205.0", + "@opentelemetry/semantic-conventions": "^1.30.0" }, "engines": { - "node": ">=18.0.0" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@smithy/eventstream-serde-universal": { - "version": "4.0.2", + "node_modules/@opentelemetry/instrumentation-net": { + "version": "0.49.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation-net/-/instrumentation-net-0.49.0.tgz", + "integrity": "sha512-XmpRZa1uRlZ2qff0LYzALkBmzJsEJyaDKEw50C0MDrawg/p5z1/TOMwMIKPG2g1EgAW56+dl/WD8p70XyW08Qg==", "license": "Apache-2.0", "dependencies": { - "@smithy/eventstream-codec": "^4.0.2", - "@smithy/types": "^4.2.0", - "tslib": "^2.6.2" + "@opentelemetry/instrumentation": "^0.205.0", + "@opentelemetry/semantic-conventions": "^1.27.0" }, "engines": { - "node": ">=18.0.0" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@smithy/eventstream-serde-universal/node_modules/@aws-crypto/crc32": { - "version": "5.2.0", + "node_modules/@opentelemetry/instrumentation-oracledb": { + "version": "0.31.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation-oracledb/-/instrumentation-oracledb-0.31.0.tgz", + "integrity": "sha512-CqjWWL1CEYR1ryBN6fCGWNhUS4rS+zNMLE/gYbpwJqH07QA6/Jt4ThbiOPujcq/PEQK3KuqoXeoGDCiI3YWMcQ==", "license": "Apache-2.0", "dependencies": { - "@aws-crypto/util": "^5.2.0", - "@aws-sdk/types": "^3.222.0", - "tslib": "^2.6.2" + "@opentelemetry/instrumentation": "^0.205.0", + "@opentelemetry/semantic-conventions": "^1.27.0", + "@types/oracledb": "6.5.2" }, "engines": { - "node": ">=16.0.0" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@smithy/eventstream-serde-universal/node_modules/@smithy/eventstream-codec": { - "version": "4.0.2", + "node_modules/@opentelemetry/instrumentation-pg": { + "version": "0.58.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation-pg/-/instrumentation-pg-0.58.0.tgz", + "integrity": "sha512-WHntZAorf6CZ0n5a3oHlwGkSeu5Xa4AiCmXkNTKg24TbYSFWzJUtWvPQSkxePvQ3ku71lhAY/M20WgwHlvpZpQ==", "license": "Apache-2.0", "dependencies": { - "@aws-crypto/crc32": "5.2.0", - "@smithy/types": "^4.2.0", - "@smithy/util-hex-encoding": "^4.0.0", - "tslib": "^2.6.2" + "@opentelemetry/core": "^2.0.0", + "@opentelemetry/instrumentation": "^0.205.0", + "@opentelemetry/semantic-conventions": "^1.34.0", + "@opentelemetry/sql-common": "^0.41.0", + "@types/pg": "8.15.5", + "@types/pg-pool": "2.0.6" }, "engines": { - "node": ">=18.0.0" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@smithy/eventstream-serde-universal/node_modules/@smithy/util-hex-encoding": { - "version": "4.0.0", + "node_modules/@opentelemetry/instrumentation-pg/node_modules/@types/pg": { + "version": "8.15.5", + "resolved": "https://registry.npmjs.org/@types/pg/-/pg-8.15.5.tgz", + "integrity": "sha512-LF7lF6zWEKxuT3/OR8wAZGzkg4ENGXFNyiV/JeOt9z5B+0ZVwbql9McqX5c/WStFq1GaGso7H1AzP/qSzmlCKQ==", + "license": "MIT", + "dependencies": { + "@types/node": "*", + "pg-protocol": "*", + "pg-types": "^2.2.0" + } + }, + "node_modules/@opentelemetry/instrumentation-pino": { + "version": "0.52.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation-pino/-/instrumentation-pino-0.52.0.tgz", + "integrity": "sha512-FLATUe4E1N/x2NkNyzXVGAIu8Jau6RitHmfIbCn3IL1gyuFT/aSlyc5z8HPotlonPZg5RAhp5rUcKiDKtuLY8Q==", "license": "Apache-2.0", "dependencies": { - "tslib": "^2.6.2" + "@opentelemetry/api-logs": "^0.205.0", + "@opentelemetry/core": "^2.0.0", + "@opentelemetry/instrumentation": "^0.205.0" }, "engines": { - "node": ">=18.0.0" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@smithy/fetch-http-handler": { - "version": "5.0.2", + "node_modules/@opentelemetry/instrumentation-redis": { + "version": "0.54.1", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation-redis/-/instrumentation-redis-0.54.1.tgz", + "integrity": "sha512-/hOkOa9uIpestrpKuVCNPLHYkSXY1sjsaiXZw/Srv5mzTjpybnDZs5MOCdsIADjFfaCg23sM/JmfIx6IhWgP0w==", "license": "Apache-2.0", "dependencies": { - "@smithy/protocol-http": "^5.1.0", - "@smithy/querystring-builder": "^4.0.2", - "@smithy/types": "^4.2.0", - "@smithy/util-base64": "^4.0.0", - "tslib": "^2.6.2" + "@opentelemetry/instrumentation": "^0.205.0", + "@opentelemetry/redis-common": "^0.38.0", + "@opentelemetry/semantic-conventions": "^1.27.0" }, "engines": { - "node": ">=18.0.0" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@smithy/fetch-http-handler/node_modules/@smithy/protocol-http": { - "version": "5.1.0", + "node_modules/@opentelemetry/instrumentation-restify": { + "version": "0.51.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation-restify/-/instrumentation-restify-0.51.0.tgz", + "integrity": "sha512-DR8rquJixfQJzbOoGXB5qs1tuL4hGh1II+fk2xtxSu3qmOcmNI8jihez2dYPN67iofuhX+DxqZgvTYSqx4REpQ==", "license": "Apache-2.0", "dependencies": { - "@smithy/types": "^4.2.0", - "tslib": "^2.6.2" + "@opentelemetry/core": "^2.0.0", + "@opentelemetry/instrumentation": "^0.205.0", + "@opentelemetry/semantic-conventions": "^1.27.0" }, "engines": { - "node": ">=18.0.0" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@smithy/hash-node": { - "version": "4.0.2", + "node_modules/@opentelemetry/instrumentation-router": { + "version": "0.50.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation-router/-/instrumentation-router-0.50.0.tgz", + "integrity": "sha512-tnEo9yoWUNgCm4FrizjINSTvkGOlS7pO0j+BUByRNf2sBvw8zpC3uG6C+8rg9f6Th5L+yZUU1W8Y6itWLNdh4g==", "license": "Apache-2.0", "dependencies": { - "@smithy/types": "^4.2.0", - "@smithy/util-buffer-from": "^4.0.0", - "@smithy/util-utf8": "^4.0.0", - "tslib": "^2.6.2" + "@opentelemetry/instrumentation": "^0.205.0", + "@opentelemetry/semantic-conventions": "^1.27.0" }, "engines": { - "node": ">=18.0.0" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@smithy/hash-node/node_modules/@smithy/util-utf8": { - "version": "4.0.0", + "node_modules/@opentelemetry/instrumentation-runtime-node": { + "version": "0.19.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation-runtime-node/-/instrumentation-runtime-node-0.19.0.tgz", + "integrity": "sha512-rWlCcoroV3XlZ+YfTgVTO3Vq6nt61xjB1Or4C94g13Jf49zVi+QlipuEQRvMz8vsqtpxH21ZbAzCb1PcSsjT9g==", "license": "Apache-2.0", "dependencies": { - "@smithy/util-buffer-from": "^4.0.0", - "tslib": "^2.6.2" + "@opentelemetry/instrumentation": "^0.205.0" }, "engines": { - "node": ">=18.0.0" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@smithy/invalid-dependency": { - "version": "4.0.2", + "node_modules/@opentelemetry/instrumentation-socket.io": { + "version": "0.52.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation-socket.io/-/instrumentation-socket.io-0.52.0.tgz", + "integrity": "sha512-+dXOZGp2dHZ1+PaaebRKC4Hp5AIpryHbWIpZVmJ1mg3d24Xge2QZqOLjYF+3Z2s3IYSVp+j3uLef2vwg7e8+zQ==", "license": "Apache-2.0", "dependencies": { - "@smithy/types": "^4.2.0", - "tslib": "^2.6.2" + "@opentelemetry/instrumentation": "^0.205.0", + "@opentelemetry/semantic-conventions": "^1.27.0" }, "engines": { - "node": ">=18.0.0" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@smithy/is-array-buffer": { - "version": "2.2.0", + "node_modules/@opentelemetry/instrumentation-tedious": { + "version": "0.24.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation-tedious/-/instrumentation-tedious-0.24.0.tgz", + "integrity": "sha512-sOX7JaHzdYoaFmu2cHDcdKGJAvdEIrk/IB6uS5Tr28nSos3E+beGsWGbPPKRXJ6E97ubqS2c8YUH9W1ece1rOQ==", "license": "Apache-2.0", "dependencies": { - "tslib": "^2.6.2" + "@opentelemetry/instrumentation": "^0.205.0", + "@opentelemetry/semantic-conventions": "^1.27.0", + "@types/tedious": "^4.0.14" }, "engines": { - "node": ">=14.0.0" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@smithy/middleware-content-length": { - "version": "4.0.2", + "node_modules/@opentelemetry/instrumentation-undici": { + "version": "0.16.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation-undici/-/instrumentation-undici-0.16.0.tgz", + "integrity": "sha512-sky42QpDmsHbrmE02sCEk7kdug2uTB4w5OwLpfHKom/5vbzTJZDoaM68YpCq0vTQ9QwL/DIDGwjdaTcU+XXCxQ==", "license": "Apache-2.0", "dependencies": { - "@smithy/protocol-http": "^5.1.0", - "@smithy/types": "^4.2.0", - "tslib": "^2.6.2" + "@opentelemetry/core": "^2.0.0", + "@opentelemetry/instrumentation": "^0.205.0" }, "engines": { - "node": ">=18.0.0" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.7.0" } }, - "node_modules/@smithy/middleware-content-length/node_modules/@smithy/protocol-http": { - "version": "5.1.0", + "node_modules/@opentelemetry/instrumentation-winston": { + "version": "0.50.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation-winston/-/instrumentation-winston-0.50.0.tgz", + "integrity": "sha512-RKcbKIwwKzT6RnNPo5yU6Zus5DYSysK5zr8dL+LU/8Qh8icV/U2rghFJzMI+t01GeirhwSJeuuWB28AdZvSnLQ==", "license": "Apache-2.0", "dependencies": { - "@smithy/types": "^4.2.0", - "tslib": "^2.6.2" + "@opentelemetry/api-logs": "^0.205.0", + "@opentelemetry/instrumentation": "^0.205.0" }, "engines": { - "node": ">=18.0.0" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@smithy/middleware-endpoint": { - "version": "4.1.4", + "node_modules/@opentelemetry/otlp-exporter-base": { + "version": "0.205.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/otlp-exporter-base/-/otlp-exporter-base-0.205.0.tgz", + "integrity": "sha512-2MN0C1IiKyo34M6NZzD6P9Nv9Dfuz3OJ3rkZwzFmF6xzjDfqqCTatc9v1EpNfaP55iDOCLHFyYNCgs61FFgtUQ==", "license": "Apache-2.0", "dependencies": { - "@smithy/core": "^3.3.1", - "@smithy/middleware-serde": "^4.0.3", - "@smithy/node-config-provider": "^4.1.1", - "@smithy/shared-ini-file-loader": "^4.0.2", - "@smithy/types": "^4.2.0", - "@smithy/url-parser": "^4.0.2", - "@smithy/util-middleware": "^4.0.2", - "tslib": "^2.6.2" + "@opentelemetry/core": "2.1.0", + "@opentelemetry/otlp-transformer": "0.205.0" }, "engines": { - "node": ">=18.0.0" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@smithy/middleware-retry": { - "version": "4.1.5", + "node_modules/@opentelemetry/otlp-grpc-exporter-base": { + "version": "0.205.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/otlp-grpc-exporter-base/-/otlp-grpc-exporter-base-0.205.0.tgz", + "integrity": "sha512-AeuLfrciGYffqsp4EUTdYYc6Ee2BQS+hr08mHZk1C524SFWx0WnfcTnV0NFXbVURUNU6DZu1DhS89zRRrcx/hg==", "license": "Apache-2.0", "dependencies": { - "@smithy/node-config-provider": "^4.1.1", - "@smithy/protocol-http": "^5.1.0", - "@smithy/service-error-classification": "^4.0.3", - "@smithy/smithy-client": "^4.2.4", - "@smithy/types": "^4.2.0", - "@smithy/util-middleware": "^4.0.2", - "@smithy/util-retry": "^4.0.3", - "tslib": "^2.6.2", - "uuid": "^9.0.1" + "@grpc/grpc-js": "^1.7.1", + "@opentelemetry/core": "2.1.0", + "@opentelemetry/otlp-exporter-base": "0.205.0", + "@opentelemetry/otlp-transformer": "0.205.0" }, "engines": { - "node": ">=18.0.0" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@smithy/middleware-retry/node_modules/@smithy/protocol-http": { - "version": "5.1.0", + "node_modules/@opentelemetry/otlp-transformer": { + "version": "0.205.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/otlp-transformer/-/otlp-transformer-0.205.0.tgz", + "integrity": "sha512-KmObgqPtk9k/XTlWPJHdMbGCylRAmMJNXIRh6VYJmvlRDMfe+DonH41G7eenG8t4FXn3fxOGh14o/WiMRR6vPg==", "license": "Apache-2.0", "dependencies": { - "@smithy/types": "^4.2.0", - "tslib": "^2.6.2" + "@opentelemetry/api-logs": "0.205.0", + "@opentelemetry/core": "2.1.0", + "@opentelemetry/resources": "2.1.0", + "@opentelemetry/sdk-logs": "0.205.0", + "@opentelemetry/sdk-metrics": "2.1.0", + "@opentelemetry/sdk-trace-base": "2.1.0", + "protobufjs": "^7.3.0" }, "engines": { - "node": ">=18.0.0" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@smithy/middleware-serde": { - "version": "4.0.3", + "node_modules/@opentelemetry/otlp-transformer/node_modules/@opentelemetry/sdk-logs": { + "version": "0.205.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-logs/-/sdk-logs-0.205.0.tgz", + "integrity": "sha512-nyqhNQ6eEzPWQU60Nc7+A5LIq8fz3UeIzdEVBQYefB4+msJZ2vuVtRuk9KxPMw1uHoHDtYEwkr2Ct0iG29jU8w==", "license": "Apache-2.0", "dependencies": { - "@smithy/types": "^4.2.0", - "tslib": "^2.6.2" + "@opentelemetry/api-logs": "0.205.0", + "@opentelemetry/core": "2.1.0", + "@opentelemetry/resources": "2.1.0" }, "engines": { - "node": ">=18.0.0" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.4.0 <1.10.0" } }, - "node_modules/@smithy/middleware-stack": { - "version": "4.0.2", + "node_modules/@opentelemetry/otlp-transformer/node_modules/@opentelemetry/sdk-metrics": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-metrics/-/sdk-metrics-2.1.0.tgz", + "integrity": "sha512-J9QX459mzqHLL9Y6FZ4wQPRZG4TOpMCyPOh6mkr/humxE1W2S3Bvf4i75yiMW9uyed2Kf5rxmLhTm/UK8vNkAw==", "license": "Apache-2.0", "dependencies": { - "@smithy/types": "^4.2.0", - "tslib": "^2.6.2" + "@opentelemetry/core": "2.1.0", + "@opentelemetry/resources": "2.1.0" }, "engines": { - "node": ">=18.0.0" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.9.0 <1.10.0" } }, - "node_modules/@smithy/node-config-provider": { - "version": "4.1.1", + "node_modules/@opentelemetry/otlp-transformer/node_modules/@opentelemetry/sdk-trace-base": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-trace-base/-/sdk-trace-base-2.1.0.tgz", + "integrity": "sha512-uTX9FBlVQm4S2gVQO1sb5qyBLq/FPjbp+tmGoxu4tIgtYGmBYB44+KX/725RFDe30yBSaA9Ml9fqphe1hbUyLQ==", "license": "Apache-2.0", "dependencies": { - "@smithy/property-provider": "^4.0.2", - "@smithy/shared-ini-file-loader": "^4.0.2", - "@smithy/types": "^4.2.0", - "tslib": "^2.6.2" + "@opentelemetry/core": "2.1.0", + "@opentelemetry/resources": "2.1.0", + "@opentelemetry/semantic-conventions": "^1.29.0" }, "engines": { - "node": ">=18.0.0" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.3.0 <1.10.0" } }, - "node_modules/@smithy/node-http-handler": { - "version": "4.0.4", + "node_modules/@opentelemetry/propagator-b3": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/propagator-b3/-/propagator-b3-2.1.0.tgz", + "integrity": "sha512-yOdHmFseIChYanddMMz0mJIFQHyjwbNhoxc65fEAA8yanxcBPwoFDoh1+WBUWAO/Z0NRgk+k87d+aFIzAZhcBw==", "license": "Apache-2.0", "dependencies": { - "@smithy/abort-controller": "^4.0.2", - "@smithy/protocol-http": "^5.1.0", - "@smithy/querystring-builder": "^4.0.2", - "@smithy/types": "^4.2.0", - "tslib": "^2.6.2" + "@opentelemetry/core": "2.1.0" }, "engines": { - "node": ">=18.0.0" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.0.0 <1.10.0" } }, - "node_modules/@smithy/node-http-handler/node_modules/@smithy/protocol-http": { - "version": "5.1.0", + "node_modules/@opentelemetry/propagator-jaeger": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/propagator-jaeger/-/propagator-jaeger-2.1.0.tgz", + "integrity": "sha512-QYo7vLyMjrBCUTpwQBF/e+rvP7oGskrSELGxhSvLj5gpM0az9oJnu/0O4l2Nm7LEhAff80ntRYKkAcSwVgvSVQ==", "license": "Apache-2.0", "dependencies": { - "@smithy/types": "^4.2.0", - "tslib": "^2.6.2" + "@opentelemetry/core": "2.1.0" }, "engines": { - "node": ">=18.0.0" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.0.0 <1.10.0" } }, - "node_modules/@smithy/property-provider": { - "version": "4.0.2", + "node_modules/@opentelemetry/redis-common": { + "version": "0.38.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/redis-common/-/redis-common-0.38.0.tgz", + "integrity": "sha512-4Wc0AWURII2cfXVVoZ6vDqK+s5n4K5IssdrlVrvGsx6OEOKdghKtJZqXAHWFiZv4nTDLH2/2fldjIHY8clMOjQ==", "license": "Apache-2.0", - "dependencies": { - "@smithy/types": "^4.2.0", - "tslib": "^2.6.2" - }, "engines": { - "node": ">=18.0.0" + "node": "^18.19.0 || >=20.6.0" } }, - "node_modules/@smithy/querystring-builder": { - "version": "4.0.2", + "node_modules/@opentelemetry/resource-detector-alibaba-cloud": { + "version": "0.31.5", + "resolved": "https://registry.npmjs.org/@opentelemetry/resource-detector-alibaba-cloud/-/resource-detector-alibaba-cloud-0.31.5.tgz", + "integrity": "sha512-SVweVr/WWWQZVuBII7WlqIW2exT5bYZdLwuGEh3EAi5Y5mulY4KUzvW8Rx+NoFWd8wgEscCltxuztFhhnlQDWQ==", "license": "Apache-2.0", "dependencies": { - "@smithy/types": "^4.2.0", - "@smithy/util-uri-escape": "^4.0.0", - "tslib": "^2.6.2" + "@opentelemetry/core": "^2.0.0", + "@opentelemetry/resources": "^2.0.0", + "@opentelemetry/semantic-conventions": "^1.27.0" }, "engines": { - "node": ">=18.0.0" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.0.0" } }, - "node_modules/@smithy/querystring-parser": { - "version": "4.0.2", + "node_modules/@opentelemetry/resource-detector-aws": { + "version": "2.5.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/resource-detector-aws/-/resource-detector-aws-2.5.0.tgz", + "integrity": "sha512-NI7by8oi4G03yQA/igYZLZhbKkEy9tn/9JOQsHCPaRTDjzW+VHNcP5BLJH0FEM0NJZm7Ue/59J1a1aTSNJSDuA==", "license": "Apache-2.0", "dependencies": { - "@smithy/types": "^4.2.0", - "tslib": "^2.6.2" + "@opentelemetry/core": "^2.0.0", + "@opentelemetry/resources": "^2.0.0", + "@opentelemetry/semantic-conventions": "^1.27.0" }, "engines": { - "node": ">=18.0.0" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.0.0" } }, - "node_modules/@smithy/service-error-classification": { - "version": "4.0.3", + "node_modules/@opentelemetry/resource-detector-azure": { + "version": "0.12.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/resource-detector-azure/-/resource-detector-azure-0.12.0.tgz", + "integrity": "sha512-U87/nRFthxoPxPJVOeqytf+M0X43Es1al7+K3+fAYQN4kEenahhA3TUZESl6MweEW8tejUxp7A0AjxWrydAWQg==", "license": "Apache-2.0", "dependencies": { - "@smithy/types": "^4.2.0" + "@opentelemetry/core": "^2.0.0", + "@opentelemetry/resources": "^2.0.0", + "@opentelemetry/semantic-conventions": "^1.27.0" }, "engines": { - "node": ">=18.0.0" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.0.0" } }, - "node_modules/@smithy/shared-ini-file-loader": { - "version": "4.0.2", + "node_modules/@opentelemetry/resource-detector-container": { + "version": "0.7.5", + "resolved": "https://registry.npmjs.org/@opentelemetry/resource-detector-container/-/resource-detector-container-0.7.5.tgz", + "integrity": "sha512-oa2+suq7q2epLC1R+pp3rmel7sS6kc4lPe67lxNNVSJ2Bw23ZJatCeG4Fjb2enueDE70VhqPpslVef5hnw1mBA==", "license": "Apache-2.0", "dependencies": { - "@smithy/types": "^4.2.0", - "tslib": "^2.6.2" + "@opentelemetry/core": "^2.0.0", + "@opentelemetry/resources": "^2.0.0", + "@opentelemetry/semantic-conventions": "^1.27.0" }, "engines": { - "node": ">=18.0.0" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.0.0" } }, - "node_modules/@smithy/smithy-client": { - "version": "4.2.4", + "node_modules/@opentelemetry/resource-detector-gcp": { + "version": "0.40.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/resource-detector-gcp/-/resource-detector-gcp-0.40.0.tgz", + "integrity": "sha512-uAsUV8K4R9OJ3cgPUGYDqQByxOMTz4StmzJyofIv7+W+c1dTSEc1WVjWpTS2PAmywik++JlSmd8O4rMRJZpO8Q==", "license": "Apache-2.0", "dependencies": { - "@smithy/core": "^3.3.1", - "@smithy/middleware-endpoint": "^4.1.4", - "@smithy/middleware-stack": "^4.0.2", - "@smithy/protocol-http": "^5.1.0", - "@smithy/types": "^4.2.0", - "@smithy/util-stream": "^4.2.0", - "tslib": "^2.6.2" + "@opentelemetry/core": "^2.0.0", + "@opentelemetry/resources": "^2.0.0", + "@opentelemetry/semantic-conventions": "^1.27.0", + "gcp-metadata": "^6.0.0" }, "engines": { - "node": ">=18.0.0" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.0.0" } }, - "node_modules/@smithy/smithy-client/node_modules/@smithy/protocol-http": { - "version": "5.1.0", + "node_modules/@opentelemetry/resources": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/resources/-/resources-2.1.0.tgz", + "integrity": "sha512-1CJjf3LCvoefUOgegxi8h6r4B/wLSzInyhGP2UmIBYNlo4Qk5CZ73e1eEyWmfXvFtm1ybkmfb2DqWvspsYLrWw==", "license": "Apache-2.0", "dependencies": { - "@smithy/types": "^4.2.0", - "tslib": "^2.6.2" + "@opentelemetry/core": "2.1.0", + "@opentelemetry/semantic-conventions": "^1.29.0" }, "engines": { - "node": ">=18.0.0" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.3.0 <1.10.0" } }, - "node_modules/@smithy/types": { - "version": "4.2.0", + "node_modules/@opentelemetry/sdk-node": { + "version": "0.205.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-node/-/sdk-node-0.205.0.tgz", + "integrity": "sha512-Y4Wcs8scj/Wy1u61pX1ggqPXPtCsGaqx/UnFu7BtRQE1zCQR+b0h56K7I0jz7U2bRlPUZIFdnNLtoaJSMNzz2g==", "license": "Apache-2.0", "dependencies": { - "tslib": "^2.6.2" + "@opentelemetry/api-logs": "0.205.0", + "@opentelemetry/core": "2.1.0", + "@opentelemetry/exporter-logs-otlp-grpc": "0.205.0", + "@opentelemetry/exporter-logs-otlp-http": "0.205.0", + "@opentelemetry/exporter-logs-otlp-proto": "0.205.0", + "@opentelemetry/exporter-metrics-otlp-grpc": "0.205.0", + "@opentelemetry/exporter-metrics-otlp-http": "0.205.0", + "@opentelemetry/exporter-metrics-otlp-proto": "0.205.0", + "@opentelemetry/exporter-prometheus": "0.205.0", + "@opentelemetry/exporter-trace-otlp-grpc": "0.205.0", + "@opentelemetry/exporter-trace-otlp-http": "0.205.0", + "@opentelemetry/exporter-trace-otlp-proto": "0.205.0", + "@opentelemetry/exporter-zipkin": "2.1.0", + "@opentelemetry/instrumentation": "0.205.0", + "@opentelemetry/propagator-b3": "2.1.0", + "@opentelemetry/propagator-jaeger": "2.1.0", + "@opentelemetry/resources": "2.1.0", + "@opentelemetry/sdk-logs": "0.205.0", + "@opentelemetry/sdk-metrics": "2.1.0", + "@opentelemetry/sdk-trace-base": "2.1.0", + "@opentelemetry/sdk-trace-node": "2.1.0", + "@opentelemetry/semantic-conventions": "^1.29.0" + }, + "engines": { + "node": "^18.19.0 || >=20.6.0" }, - "engines": { - "node": ">=18.0.0" + "peerDependencies": { + "@opentelemetry/api": ">=1.3.0 <1.10.0" } }, - "node_modules/@smithy/url-parser": { - "version": "4.0.2", + "node_modules/@opentelemetry/sdk-node/node_modules/@opentelemetry/sdk-logs": { + "version": "0.205.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-logs/-/sdk-logs-0.205.0.tgz", + "integrity": "sha512-nyqhNQ6eEzPWQU60Nc7+A5LIq8fz3UeIzdEVBQYefB4+msJZ2vuVtRuk9KxPMw1uHoHDtYEwkr2Ct0iG29jU8w==", "license": "Apache-2.0", "dependencies": { - "@smithy/querystring-parser": "^4.0.2", - "@smithy/types": "^4.2.0", - "tslib": "^2.6.2" + "@opentelemetry/api-logs": "0.205.0", + "@opentelemetry/core": "2.1.0", + "@opentelemetry/resources": "2.1.0" }, "engines": { - "node": ">=18.0.0" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.4.0 <1.10.0" } }, - "node_modules/@smithy/util-base64": { - "version": "4.0.0", + "node_modules/@opentelemetry/sdk-node/node_modules/@opentelemetry/sdk-metrics": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-metrics/-/sdk-metrics-2.1.0.tgz", + "integrity": "sha512-J9QX459mzqHLL9Y6FZ4wQPRZG4TOpMCyPOh6mkr/humxE1W2S3Bvf4i75yiMW9uyed2Kf5rxmLhTm/UK8vNkAw==", "license": "Apache-2.0", "dependencies": { - "@smithy/util-buffer-from": "^4.0.0", - "@smithy/util-utf8": "^4.0.0", - "tslib": "^2.6.2" + "@opentelemetry/core": "2.1.0", + "@opentelemetry/resources": "2.1.0" }, "engines": { - "node": ">=18.0.0" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.9.0 <1.10.0" } }, - "node_modules/@smithy/util-base64/node_modules/@smithy/util-utf8": { - "version": "4.0.0", + "node_modules/@opentelemetry/sdk-node/node_modules/@opentelemetry/sdk-trace-base": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-trace-base/-/sdk-trace-base-2.1.0.tgz", + "integrity": "sha512-uTX9FBlVQm4S2gVQO1sb5qyBLq/FPjbp+tmGoxu4tIgtYGmBYB44+KX/725RFDe30yBSaA9Ml9fqphe1hbUyLQ==", "license": "Apache-2.0", "dependencies": { - "@smithy/util-buffer-from": "^4.0.0", - "tslib": "^2.6.2" + "@opentelemetry/core": "2.1.0", + "@opentelemetry/resources": "2.1.0", + "@opentelemetry/semantic-conventions": "^1.29.0" }, "engines": { - "node": ">=18.0.0" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.3.0 <1.10.0" } }, - "node_modules/@smithy/util-body-length-browser": { - "version": "4.0.0", + "node_modules/@opentelemetry/sdk-trace-node": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-trace-node/-/sdk-trace-node-2.1.0.tgz", + "integrity": "sha512-SvVlBFc/jI96u/mmlKm86n9BbTCbQ35nsPoOohqJX6DXH92K0kTe73zGY5r8xoI1QkjR9PizszVJLzMC966y9Q==", "license": "Apache-2.0", "dependencies": { - "tslib": "^2.6.2" + "@opentelemetry/context-async-hooks": "2.1.0", + "@opentelemetry/core": "2.1.0", + "@opentelemetry/sdk-trace-base": "2.1.0" }, "engines": { - "node": ">=18.0.0" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.0.0 <1.10.0" } }, - "node_modules/@smithy/util-body-length-node": { - "version": "4.0.0", + "node_modules/@opentelemetry/sdk-trace-node/node_modules/@opentelemetry/sdk-trace-base": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-trace-base/-/sdk-trace-base-2.1.0.tgz", + "integrity": "sha512-uTX9FBlVQm4S2gVQO1sb5qyBLq/FPjbp+tmGoxu4tIgtYGmBYB44+KX/725RFDe30yBSaA9Ml9fqphe1hbUyLQ==", "license": "Apache-2.0", "dependencies": { - "tslib": "^2.6.2" + "@opentelemetry/core": "2.1.0", + "@opentelemetry/resources": "2.1.0", + "@opentelemetry/semantic-conventions": "^1.29.0" }, "engines": { - "node": ">=18.0.0" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.3.0 <1.10.0" } }, - "node_modules/@smithy/util-buffer-from": { - "version": "4.0.0", + "node_modules/@opentelemetry/semantic-conventions": { + "version": "1.37.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/semantic-conventions/-/semantic-conventions-1.37.0.tgz", + "integrity": "sha512-JD6DerIKdJGmRp4jQyX5FlrQjA4tjOw1cvfsPAZXfOOEErMUHjPcPSICS+6WnM0nB0efSFARh0KAZss+bvExOA==", "license": "Apache-2.0", - "dependencies": { - "@smithy/is-array-buffer": "^4.0.0", - "tslib": "^2.6.2" - }, "engines": { - "node": ">=18.0.0" + "node": ">=14" } }, - "node_modules/@smithy/util-buffer-from/node_modules/@smithy/is-array-buffer": { - "version": "4.0.0", + "node_modules/@opentelemetry/sql-common": { + "version": "0.41.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/sql-common/-/sql-common-0.41.0.tgz", + "integrity": "sha512-pmzXctVbEERbqSfiAgdes9Y63xjoOyXcD7B6IXBkVb+vbM7M9U98mn33nGXxPf4dfYR0M+vhcKRZmbSJ7HfqFA==", "license": "Apache-2.0", "dependencies": { - "tslib": "^2.6.2" + "@opentelemetry/core": "^2.0.0" }, "engines": { - "node": ">=18.0.0" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.1.0" } }, - "node_modules/@smithy/util-config-provider": { - "version": "4.0.0", - "license": "Apache-2.0", + "node_modules/@paralleldrive/cuid2": { + "version": "2.2.2", + "resolved": "https://registry.npmjs.org/@paralleldrive/cuid2/-/cuid2-2.2.2.tgz", + "integrity": "sha512-ZOBkgDwEdoYVlSeRbYYXs0S9MejQofiVYoTbKzy/6GQa39/q5tQU2IX46+shYnUkpEl3wc+J6wRlar7r2EK2xA==", + "dev": true, "dependencies": { - "tslib": "^2.6.2" - }, + "@noble/hashes": "^1.1.5" + } + }, + "node_modules/@pkgjs/parseargs": { + "version": "0.11.0", + "license": "MIT", + "optional": true, "engines": { - "node": ">=18.0.0" + "node": ">=14" + } + }, + "node_modules/@pkgr/core": { + "version": "0.2.4", + "dev": true, + "license": "MIT", + "engines": { + "node": "^12.20.0 || ^14.18.0 || >=16.0.0" + }, + "funding": { + "url": "https://opencollective.com/pkgr" } }, - "node_modules/@smithy/util-defaults-mode-browser": { - "version": "4.0.12", - "license": "Apache-2.0", - "dependencies": { - "@smithy/property-provider": "^4.0.2", - "@smithy/smithy-client": "^4.2.4", - "@smithy/types": "^4.2.0", - "bowser": "^2.11.0", - "tslib": "^2.6.2" - }, - "engines": { - "node": ">=18.0.0" - } + "node_modules/@protobufjs/aspromise": { + "version": "1.1.2", + "license": "BSD-3-Clause" + }, + "node_modules/@protobufjs/base64": { + "version": "1.1.2", + "license": "BSD-3-Clause" + }, + "node_modules/@protobufjs/codegen": { + "version": "2.0.4", + "license": "BSD-3-Clause" + }, + "node_modules/@protobufjs/eventemitter": { + "version": "1.1.0", + "license": "BSD-3-Clause" }, - "node_modules/@smithy/util-defaults-mode-node": { - "version": "4.0.12", - "license": "Apache-2.0", + "node_modules/@protobufjs/fetch": { + "version": "1.1.0", + "license": "BSD-3-Clause", "dependencies": { - "@smithy/config-resolver": "^4.1.2", - "@smithy/credential-provider-imds": "^4.0.4", - "@smithy/node-config-provider": "^4.1.1", - "@smithy/property-provider": "^4.0.2", - "@smithy/smithy-client": "^4.2.4", - "@smithy/types": "^4.2.0", - "tslib": "^2.6.2" - }, - "engines": { - "node": ">=18.0.0" + "@protobufjs/aspromise": "^1.1.1", + "@protobufjs/inquire": "^1.1.0" } }, - "node_modules/@smithy/util-endpoints": { - "version": "3.0.4", - "license": "Apache-2.0", + "node_modules/@protobufjs/float": { + "version": "1.0.2", + "license": "BSD-3-Clause" + }, + "node_modules/@protobufjs/inquire": { + "version": "1.1.0", + "license": "BSD-3-Clause" + }, + "node_modules/@protobufjs/path": { + "version": "1.1.2", + "license": "BSD-3-Clause" + }, + "node_modules/@protobufjs/pool": { + "version": "1.1.0", + "license": "BSD-3-Clause" + }, + "node_modules/@protobufjs/utf8": { + "version": "1.1.0", + "license": "BSD-3-Clause" + }, + "node_modules/@rtsao/scc": { + "version": "1.1.0", + "dev": true, + "license": "MIT" + }, + "node_modules/@scarf/scarf": { + "version": "1.4.0", + "hasInstallScript": true, + "license": "Apache-2.0" + }, + "node_modules/@sinclair/typebox": { + "version": "0.27.8", + "dev": true, + "license": "MIT" + }, + "node_modules/@sinonjs/commons": { + "version": "3.0.1", + "dev": true, + "license": "BSD-3-Clause", "dependencies": { - "@smithy/node-config-provider": "^4.1.1", - "@smithy/types": "^4.2.0", - "tslib": "^2.6.2" - }, - "engines": { - "node": ">=18.0.0" + "type-detect": "4.0.8" } }, - "node_modules/@smithy/util-middleware": { - "version": "4.0.2", - "license": "Apache-2.0", + "node_modules/@sinonjs/fake-timers": { + "version": "10.3.0", + "dev": true, + "license": "BSD-3-Clause", "dependencies": { - "@smithy/types": "^4.2.0", - "tslib": "^2.6.2" - }, - "engines": { - "node": ">=18.0.0" + "@sinonjs/commons": "^3.0.0" } }, - "node_modules/@smithy/util-retry": { - "version": "4.0.3", + "node_modules/@smithy/is-array-buffer": { + "version": "2.2.0", "license": "Apache-2.0", "dependencies": { - "@smithy/service-error-classification": "^4.0.3", - "@smithy/types": "^4.2.0", "tslib": "^2.6.2" }, "engines": { - "node": ">=18.0.0" + "node": ">=14.0.0" } }, - "node_modules/@smithy/util-stream": { - "version": "4.2.0", + "node_modules/@smithy/types": { + "version": "4.5.0", + "resolved": "https://registry.npmjs.org/@smithy/types/-/types-4.5.0.tgz", + "integrity": "sha512-RkUpIOsVlAwUIZXO1dsz8Zm+N72LClFfsNqf173catVlvRZiwPy0x2u0JLEA4byreOPKDZPGjmPDylMoP8ZJRg==", "license": "Apache-2.0", "dependencies": { - "@smithy/fetch-http-handler": "^5.0.2", - "@smithy/node-http-handler": "^4.0.4", - "@smithy/types": "^4.2.0", - "@smithy/util-base64": "^4.0.0", - "@smithy/util-buffer-from": "^4.0.0", - "@smithy/util-hex-encoding": "^4.0.0", - "@smithy/util-utf8": "^4.0.0", "tslib": "^2.6.2" }, "engines": { "node": ">=18.0.0" } }, - "node_modules/@smithy/util-stream/node_modules/@smithy/util-hex-encoding": { - "version": "4.0.0", + "node_modules/@smithy/util-buffer-from": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/@smithy/util-buffer-from/-/util-buffer-from-4.1.0.tgz", + "integrity": "sha512-N6yXcjfe/E+xKEccWEKzK6M+crMrlwaCepKja0pNnlSkm6SjAeLKKA++er5Ba0I17gvKfN/ThV+ZOx/CntKTVw==", "license": "Apache-2.0", "dependencies": { + "@smithy/is-array-buffer": "^4.1.0", "tslib": "^2.6.2" }, "engines": { "node": ">=18.0.0" } }, - "node_modules/@smithy/util-stream/node_modules/@smithy/util-utf8": { - "version": "4.0.0", + "node_modules/@smithy/util-buffer-from/node_modules/@smithy/is-array-buffer": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/@smithy/is-array-buffer/-/is-array-buffer-4.1.0.tgz", + "integrity": "sha512-ePTYUOV54wMogio+he4pBybe8fwg4sDvEVDBU8ZlHOZXbXK3/C0XfJgUCu6qAZcawv05ZhZzODGUerFBPsPUDQ==", "license": "Apache-2.0", "dependencies": { - "@smithy/util-buffer-from": "^4.0.0", "tslib": "^2.6.2" }, "engines": { "node": ">=18.0.0" } }, - "node_modules/@smithy/util-uri-escape": { - "version": "4.0.0", + "node_modules/@smithy/util-hex-encoding": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/@smithy/util-hex-encoding/-/util-hex-encoding-4.1.0.tgz", + "integrity": "sha512-1LcueNN5GYC4tr8mo14yVYbh/Ur8jHhWOxniZXii+1+ePiIbsLZ5fEI0QQGtbRRP5mOhmooos+rLmVASGGoq5w==", "license": "Apache-2.0", "dependencies": { "tslib": "^2.6.2" @@ -5733,6 +5182,12 @@ "version": "1.2.5", "license": "MIT" }, + "node_modules/@standard-schema/spec": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/@standard-schema/spec/-/spec-1.0.0.tgz", + "integrity": "sha512-m2bOd0f2RT9k8QJx1JN85cZYyH1RqFBdlwtkSlf4tBDYLCiiZnv1fIIwacK6cqwXavOydf0NPToMQgpKq+dVlA==", + "license": "MIT" + }, "node_modules/@testcontainers/postgresql": { "version": "11.0.3", "resolved": "https://registry.npmjs.org/@testcontainers/postgresql/-/postgresql-11.0.3.tgz", @@ -5788,6 +5243,12 @@ "devOptional": true, "license": "MIT" }, + "node_modules/@types/aws-lambda": { + "version": "8.10.152", + "resolved": "https://registry.npmjs.org/@types/aws-lambda/-/aws-lambda-8.10.152.tgz", + "integrity": "sha512-soT/c2gYBnT5ygwiHPmd9a1bftj462NWVk2tKCc1PYHSIacB2UwbTS2zYG4jzag1mRDuzg/OjtxQjQ2NKRB6Rw==", + "license": "MIT" + }, "node_modules/@types/babel__core": { "version": "7.20.5", "dev": true, @@ -5842,9 +5303,17 @@ "@types/node": "*" } }, + "node_modules/@types/bunyan": { + "version": "1.8.11", + "resolved": "https://registry.npmjs.org/@types/bunyan/-/bunyan-1.8.11.tgz", + "integrity": "sha512-758fRH7umIMk5qt5ELmRMff4mLDlN+xyYzC+dkPTdKwbSkJFvz6xwyScrytPU0QIBbRRwbiE8/BIg8bpajerNQ==", + "license": "MIT", + "dependencies": { + "@types/node": "*" + } + }, "node_modules/@types/connect": { "version": "3.4.38", - "dev": true, "license": "MIT", "dependencies": { "@types/node": "*" @@ -5864,14 +5333,6 @@ "dev": true, "license": "MIT" }, - "node_modules/@types/debug": { - "version": "4.1.12", - "license": "MIT", - "peer": true, - "dependencies": { - "@types/ms": "*" - } - }, "node_modules/@types/docker-modem": { "version": "3.0.6", "resolved": "https://registry.npmjs.org/@types/docker-modem/-/docker-modem-3.0.6.tgz", @@ -5897,6 +5358,7 @@ "version": "9.6.1", "dev": true, "license": "MIT", + "peer": true, "dependencies": { "@types/estree": "*", "@types/json-schema": "*" @@ -5916,11 +5378,19 @@ "dev": true, "license": "MIT" }, + "node_modules/@types/expr-eval": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/@types/expr-eval/-/expr-eval-1.0.2.tgz", + "integrity": "sha512-kZO1EBkS1bTAZM8iex14PkEK/NHxR93e2OY8IPTW5veQ32Li6+QTWeh+3gtLiEB1vnMwO3vn2zJfdoNQeWMusQ==", + "dev": true, + "license": "MIT" + }, "node_modules/@types/express": { "version": "5.0.3", "resolved": "https://registry.npmjs.org/@types/express/-/express-5.0.3.tgz", "integrity": "sha512-wGA0NX93b19/dZC1J18tKWVIYWyyF2ZjT9vin/NRu0qzzvfVzWjs04iq2rQ3H65vCTQYlRqs3YHfY7zjdV+9Kw==", "dev": true, + "peer": true, "dependencies": { "@types/body-parser": "*", "@types/express-serve-static-core": "^5.0.0", @@ -6001,6 +5471,15 @@ "dev": true, "license": "MIT" }, + "node_modules/@types/memcached": { + "version": "2.2.10", + "resolved": "https://registry.npmjs.org/@types/memcached/-/memcached-2.2.10.tgz", + "integrity": "sha512-AM9smvZN55Gzs2wRrqeMHVP7KE8KWgCJO/XL5yCly2xF6EKa4YlbpK+cLSAH4NG/Ah64HrlegmGqW8kYws7Vxg==", + "license": "MIT", + "dependencies": { + "@types/node": "*" + } + }, "node_modules/@types/methods": { "version": "1.1.4", "dev": true, @@ -6011,10 +5490,11 @@ "dev": true, "license": "MIT" }, - "node_modules/@types/ms": { - "version": "2.1.0", - "license": "MIT", - "peer": true + "node_modules/@types/mime-types": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/@types/mime-types/-/mime-types-3.0.1.tgz", + "integrity": "sha512-xRMsfuQbnRq1Ef+C+RKaENOxXX87Ygl38W1vDfPHRku02TgQr+Qd8iivLtAMcR0KF5/29xlnFihkTlbqFrGOVQ==", + "license": "MIT" }, "node_modules/@types/multer": { "version": "2.0.0", @@ -6025,22 +5505,23 @@ "@types/express": "*" } }, - "node_modules/@types/node": { - "version": "24.1.0", - "resolved": "https://registry.npmjs.org/@types/node/-/node-24.1.0.tgz", - "integrity": "sha512-ut5FthK5moxFKH2T1CUOC6ctR67rQRvvHdFLCD2Ql6KXmMuCrjsSsRI9UsLCm9M18BMwClv4pn327UvB7eeO1w==", + "node_modules/@types/mysql": { + "version": "2.15.27", + "resolved": "https://registry.npmjs.org/@types/mysql/-/mysql-2.15.27.tgz", + "integrity": "sha512-YfWiV16IY0OeBfBCk8+hXKmdTKrKlwKN1MNKAPBu5JYxLwBEZl7QzeEpGnlZb3VMGJrrGmB84gXiH+ofs/TezA==", "license": "MIT", "dependencies": { - "undici-types": "~7.8.0" + "@types/node": "*" } }, - "node_modules/@types/node-fetch": { - "version": "2.6.12", + "node_modules/@types/node": { + "version": "24.1.0", + "resolved": "https://registry.npmjs.org/@types/node/-/node-24.1.0.tgz", + "integrity": "sha512-ut5FthK5moxFKH2T1CUOC6ctR67rQRvvHdFLCD2Ql6KXmMuCrjsSsRI9UsLCm9M18BMwClv4pn327UvB7eeO1w==", "license": "MIT", "peer": true, "dependencies": { - "@types/node": "*", - "form-data": "^4.0.0" + "undici-types": "~7.8.0" } }, "node_modules/@types/nunjucks": { @@ -6056,6 +5537,15 @@ "@types/node": "*" } }, + "node_modules/@types/oracledb": { + "version": "6.5.2", + "resolved": "https://registry.npmjs.org/@types/oracledb/-/oracledb-6.5.2.tgz", + "integrity": "sha512-kK1eBS/Adeyis+3OlBDMeQQuasIDLUYXsi2T15ccNJ0iyUpQ4xDF7svFu3+bGVrI0CMBUclPciz+lsQR3JX3TQ==", + "license": "MIT", + "dependencies": { + "@types/node": "*" + } + }, "node_modules/@types/passport": { "version": "1.0.17", "dev": true, @@ -6105,7 +5595,6 @@ "version": "8.15.4", "resolved": "https://registry.npmjs.org/@types/pg/-/pg-8.15.4.tgz", "integrity": "sha512-I6UNVBAoYbvuWkkU3oosC8yxqH21f4/Jc4DK71JLG3dT2mdlGe1z+ep/LQGXaKaOgcvUrsQoPRqfgtMcvZiJhg==", - "dev": true, "license": "MIT", "dependencies": { "@types/node": "*", @@ -6113,6 +5602,15 @@ "pg-types": "^2.2.0" } }, + "node_modules/@types/pg-pool": { + "version": "2.0.6", + "resolved": "https://registry.npmjs.org/@types/pg-pool/-/pg-pool-2.0.6.tgz", + "integrity": "sha512-TaAUE5rq2VQYxab5Ts7WZhKNmuN78Q6PiFonTDdpbx8a1H0M1vhy3rhiMjl+e2iHmogyMw7jZF4FrE6eJUy5HQ==", + "license": "MIT", + "dependencies": { + "@types/pg": "*" + } + }, "node_modules/@types/qs": { "version": "6.9.18", "dev": true, @@ -6123,10 +5621,6 @@ "dev": true, "license": "MIT" }, - "node_modules/@types/retry": { - "version": "0.12.0", - "license": "MIT" - }, "node_modules/@types/send": { "version": "0.17.4", "dev": true, @@ -6203,17 +5697,24 @@ "@types/superagent": "^8.1.0" } }, - "node_modules/@types/tough-cookie": { - "version": "4.0.5", + "node_modules/@types/tedious": { + "version": "4.0.14", + "resolved": "https://registry.npmjs.org/@types/tedious/-/tedious-4.0.14.tgz", + "integrity": "sha512-KHPsfX/FoVbUGbyYvk1q9MMQHLPeRZhRJZdO45Q4YjvFkv4hMNghCWTvy7rdKessBsmtz4euWCWAB6/tVpI1Iw==", "license": "MIT", - "peer": true + "dependencies": { + "@types/node": "*" + } }, "node_modules/@types/triple-beam": { "version": "1.3.5", "license": "MIT" }, "node_modules/@types/uuid": { - "version": "9.0.8", + "version": "10.0.0", + "resolved": "https://registry.npmjs.org/@types/uuid/-/uuid-10.0.0.tgz", + "integrity": "sha512-7gqG38EyHgyP1S+7+xomFtL+ZNHcKv6DwNaCZmJmo1vgMugyF3TCnXVg4t1uk89mLNwnLtnY3TpOpCOyp1/xHQ==", + "dev": true, "license": "MIT" }, "node_modules/@types/validator": { @@ -6224,161 +5725,30 @@ "version": "17.0.33", "dev": true, "license": "MIT", - "dependencies": { - "@types/yargs-parser": "*" - } - }, - "node_modules/@types/yargs-parser": { - "version": "21.0.3", - "dev": true, - "license": "MIT" - }, - "node_modules/@typescript-eslint/eslint-plugin": { - "version": "8.33.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/eslint-plugin/-/eslint-plugin-8.33.1.tgz", - "integrity": "sha512-TDCXj+YxLgtvxvFlAvpoRv9MAncDLBV2oT9Bd7YBGC/b/sEURoOYuIwLI99rjWOfY3QtDzO+mk0n4AmdFExW8A==", - "dev": true, - "license": "MIT", - "dependencies": { - "@eslint-community/regexpp": "^4.10.0", - "@typescript-eslint/scope-manager": "8.33.1", - "@typescript-eslint/type-utils": "8.33.1", - "@typescript-eslint/utils": "8.33.1", - "@typescript-eslint/visitor-keys": "8.33.1", - "graphemer": "^1.4.0", - "ignore": "^7.0.0", - "natural-compare": "^1.4.0", - "ts-api-utils": "^2.1.0" - }, - "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/typescript-eslint" - }, - "peerDependencies": { - "@typescript-eslint/parser": "^8.33.1", - "eslint": "^8.57.0 || ^9.0.0", - "typescript": ">=4.8.4 <5.9.0" - } - }, - "node_modules/@typescript-eslint/eslint-plugin/node_modules/ignore": { - "version": "7.0.5", - "resolved": "https://registry.npmjs.org/ignore/-/ignore-7.0.5.tgz", - "integrity": "sha512-Hs59xBNfUIunMFgWAbGX5cq6893IbWg4KnrjbYwX3tx0ztorVgTDA6B2sxf8ejHJ4wz8BqGUMYlnzNBer5NvGg==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">= 4" - } - }, - "node_modules/@typescript-eslint/parser": { - "version": "8.35.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/parser/-/parser-8.35.1.tgz", - "integrity": "sha512-3MyiDfrfLeK06bi/g9DqJxP5pV74LNv4rFTyvGDmT3x2p1yp1lOd+qYZfiRPIOf/oON+WRZR5wxxuF85qOar+w==", - "dev": true, - "dependencies": { - "@typescript-eslint/scope-manager": "8.35.1", - "@typescript-eslint/types": "8.35.1", - "@typescript-eslint/typescript-estree": "8.35.1", - "@typescript-eslint/visitor-keys": "8.35.1", - "debug": "^4.3.4" - }, - "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/typescript-eslint" - }, - "peerDependencies": { - "eslint": "^8.57.0 || ^9.0.0", - "typescript": ">=4.8.4 <5.9.0" - } - }, - "node_modules/@typescript-eslint/parser/node_modules/@typescript-eslint/project-service": { - "version": "8.35.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/project-service/-/project-service-8.35.1.tgz", - "integrity": "sha512-VYxn/5LOpVxADAuP3NrnxxHYfzVtQzLKeldIhDhzC8UHaiQvYlXvKuVho1qLduFbJjjy5U5bkGwa3rUGUb1Q6Q==", - "dev": true, - "dependencies": { - "@typescript-eslint/tsconfig-utils": "^8.35.1", - "@typescript-eslint/types": "^8.35.1", - "debug": "^4.3.4" - }, - "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/typescript-eslint" - }, - "peerDependencies": { - "typescript": ">=4.8.4 <5.9.0" - } - }, - "node_modules/@typescript-eslint/parser/node_modules/@typescript-eslint/scope-manager": { - "version": "8.35.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/scope-manager/-/scope-manager-8.35.1.tgz", - "integrity": "sha512-s/Bpd4i7ht2934nG+UoSPlYXd08KYz3bmjLEb7Ye1UVob0d1ENiT3lY8bsCmik4RqfSbPw9xJJHbugpPpP5JUg==", - "dev": true, - "dependencies": { - "@typescript-eslint/types": "8.35.1", - "@typescript-eslint/visitor-keys": "8.35.1" - }, - "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/typescript-eslint" - } - }, - "node_modules/@typescript-eslint/parser/node_modules/@typescript-eslint/tsconfig-utils": { - "version": "8.35.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/tsconfig-utils/-/tsconfig-utils-8.35.1.tgz", - "integrity": "sha512-K5/U9VmT9dTHoNowWZpz+/TObS3xqC5h0xAIjXPw+MNcKV9qg6eSatEnmeAwkjHijhACH0/N7bkhKvbt1+DXWQ==", - "dev": true, - "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/typescript-eslint" - }, - "peerDependencies": { - "typescript": ">=4.8.4 <5.9.0" + "dependencies": { + "@types/yargs-parser": "*" } }, - "node_modules/@typescript-eslint/parser/node_modules/@typescript-eslint/types": { - "version": "8.35.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-8.35.1.tgz", - "integrity": "sha512-q/O04vVnKHfrrhNAscndAn1tuQhIkwqnaW+eu5waD5IPts2eX1dgJxgqcPx5BX109/qAz7IG6VrEPTOYKCNfRQ==", + "node_modules/@types/yargs-parser": { + "version": "21.0.3", "dev": true, - "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/typescript-eslint" - } + "license": "MIT" }, - "node_modules/@typescript-eslint/parser/node_modules/@typescript-eslint/typescript-estree": { - "version": "8.35.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-8.35.1.tgz", - "integrity": "sha512-Vvpuvj4tBxIka7cPs6Y1uvM7gJgdF5Uu9F+mBJBPY4MhvjrjWGK4H0lVgLJd/8PWZ23FTqsaJaLEkBCFUk8Y9g==", + "node_modules/@typescript-eslint/eslint-plugin": { + "version": "8.46.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/eslint-plugin/-/eslint-plugin-8.46.0.tgz", + "integrity": "sha512-hA8gxBq4ukonVXPy0OKhiaUh/68D0E88GSmtC1iAEnGaieuDi38LhS7jdCHRLi6ErJBNDGCzvh5EnzdPwUc0DA==", "dev": true, + "license": "MIT", "dependencies": { - "@typescript-eslint/project-service": "8.35.1", - "@typescript-eslint/tsconfig-utils": "8.35.1", - "@typescript-eslint/types": "8.35.1", - "@typescript-eslint/visitor-keys": "8.35.1", - "debug": "^4.3.4", - "fast-glob": "^3.3.2", - "is-glob": "^4.0.3", - "minimatch": "^9.0.4", - "semver": "^7.6.0", + "@eslint-community/regexpp": "^4.10.0", + "@typescript-eslint/scope-manager": "8.46.0", + "@typescript-eslint/type-utils": "8.46.0", + "@typescript-eslint/utils": "8.46.0", + "@typescript-eslint/visitor-keys": "8.46.0", + "graphemer": "^1.4.0", + "ignore": "^7.0.0", + "natural-compare": "^1.4.0", "ts-api-utils": "^2.1.0" }, "engines": { @@ -6389,71 +5759,56 @@ "url": "https://opencollective.com/typescript-eslint" }, "peerDependencies": { - "typescript": ">=4.8.4 <5.9.0" + "@typescript-eslint/parser": "8.46.0", + "eslint": "^8.57.0 || ^9.0.0", + "typescript": ">=4.8.4 <6.0.0" } }, - "node_modules/@typescript-eslint/parser/node_modules/@typescript-eslint/visitor-keys": { - "version": "8.35.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-8.35.1.tgz", - "integrity": "sha512-VRwixir4zBWCSTP/ljEo091lbpypz57PoeAQ9imjG+vbeof9LplljsL1mos4ccG6H9IjfrVGM359RozUnuFhpw==", + "node_modules/@typescript-eslint/eslint-plugin/node_modules/ignore": { + "version": "7.0.5", + "resolved": "https://registry.npmjs.org/ignore/-/ignore-7.0.5.tgz", + "integrity": "sha512-Hs59xBNfUIunMFgWAbGX5cq6893IbWg4KnrjbYwX3tx0ztorVgTDA6B2sxf8ejHJ4wz8BqGUMYlnzNBer5NvGg==", "dev": true, - "dependencies": { - "@typescript-eslint/types": "8.35.1", - "eslint-visitor-keys": "^4.2.1" - }, + "license": "MIT", "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/typescript-eslint" + "node": ">= 4" } }, - "node_modules/@typescript-eslint/parser/node_modules/brace-expansion": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-2.0.2.tgz", - "integrity": "sha512-Jt0vHyM+jmUBqojB7E1NIYadt0vI0Qxjxd2TErW94wDz+E2LAm5vKMXXwg6ZZBTHPuUlDgQHKXvjGBdfcF1ZDQ==", + "node_modules/@typescript-eslint/parser": { + "version": "8.46.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/parser/-/parser-8.46.0.tgz", + "integrity": "sha512-n1H6IcDhmmUEG7TNVSspGmiHHutt7iVKtZwRppD7e04wha5MrkV1h3pti9xQLcCMt6YWsncpoT0HMjkH1FNwWQ==", "dev": true, + "license": "MIT", + "peer": true, "dependencies": { - "balanced-match": "^1.0.0" - } - }, - "node_modules/@typescript-eslint/parser/node_modules/eslint-visitor-keys": { - "version": "4.2.1", - "resolved": "https://registry.npmjs.org/eslint-visitor-keys/-/eslint-visitor-keys-4.2.1.tgz", - "integrity": "sha512-Uhdk5sfqcee/9H/rCOJikYz67o0a2Tw2hGRPOG2Y1R2dg7brRe1uG0yaNQDHu+TO/uQPF/5eCapvYSmHUjt7JQ==", - "dev": true, + "@typescript-eslint/scope-manager": "8.46.0", + "@typescript-eslint/types": "8.46.0", + "@typescript-eslint/typescript-estree": "8.46.0", + "@typescript-eslint/visitor-keys": "8.46.0", + "debug": "^4.3.4" + }, "engines": { "node": "^18.18.0 || ^20.9.0 || >=21.1.0" }, "funding": { - "url": "https://opencollective.com/eslint" - } - }, - "node_modules/@typescript-eslint/parser/node_modules/minimatch": { - "version": "9.0.5", - "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-9.0.5.tgz", - "integrity": "sha512-G6T0ZX48xgozx7587koeX9Ys2NYy6Gmv//P89sEte9V9whIapMNF4idKxnW2QtCcLiTWlb/wfCabAtAFWhhBow==", - "dev": true, - "dependencies": { - "brace-expansion": "^2.0.1" - }, - "engines": { - "node": ">=16 || 14 >=14.17" + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" }, - "funding": { - "url": "https://github.com/sponsors/isaacs" + "peerDependencies": { + "eslint": "^8.57.0 || ^9.0.0", + "typescript": ">=4.8.4 <6.0.0" } }, "node_modules/@typescript-eslint/project-service": { - "version": "8.33.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/project-service/-/project-service-8.33.1.tgz", - "integrity": "sha512-DZR0efeNklDIHHGRpMpR5gJITQpu6tLr9lDJnKdONTC7vvzOlLAG/wcfxcdxEWrbiZApcoBCzXqU/Z458Za5Iw==", + "version": "8.46.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/project-service/-/project-service-8.46.0.tgz", + "integrity": "sha512-OEhec0mH+U5Je2NZOeK1AbVCdm0ChyapAyTeXVIYTPXDJ3F07+cu87PPXcGoYqZ7M9YJVvFnfpGg1UmCIqM+QQ==", "dev": true, "license": "MIT", "dependencies": { - "@typescript-eslint/tsconfig-utils": "^8.33.1", - "@typescript-eslint/types": "^8.33.1", + "@typescript-eslint/tsconfig-utils": "^8.46.0", + "@typescript-eslint/types": "^8.46.0", "debug": "^4.3.4" }, "engines": { @@ -6464,18 +5819,18 @@ "url": "https://opencollective.com/typescript-eslint" }, "peerDependencies": { - "typescript": ">=4.8.4 <5.9.0" + "typescript": ">=4.8.4 <6.0.0" } }, "node_modules/@typescript-eslint/scope-manager": { - "version": "8.33.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/scope-manager/-/scope-manager-8.33.1.tgz", - "integrity": "sha512-dM4UBtgmzHR9bS0Rv09JST0RcHYearoEoo3pG5B6GoTR9XcyeqX87FEhPo+5kTvVfKCvfHaHrcgeJQc6mrDKrA==", + "version": "8.46.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/scope-manager/-/scope-manager-8.46.0.tgz", + "integrity": "sha512-lWETPa9XGcBes4jqAMYD9fW0j4n6hrPtTJwWDmtqgFO/4HF4jmdH/Q6wggTw5qIT5TXjKzbt7GsZUBnWoO3dqw==", "dev": true, "license": "MIT", "dependencies": { - "@typescript-eslint/types": "8.33.1", - "@typescript-eslint/visitor-keys": "8.33.1" + "@typescript-eslint/types": "8.46.0", + "@typescript-eslint/visitor-keys": "8.46.0" }, "engines": { "node": "^18.18.0 || ^20.9.0 || >=21.1.0" @@ -6486,9 +5841,9 @@ } }, "node_modules/@typescript-eslint/tsconfig-utils": { - "version": "8.33.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/tsconfig-utils/-/tsconfig-utils-8.33.1.tgz", - "integrity": "sha512-STAQsGYbHCF0/e+ShUQ4EatXQ7ceh3fBCXkNU7/MZVKulrlq1usH7t2FhxvCpuCi5O5oi1vmVaAjrGeL71OK1g==", + "version": "8.46.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/tsconfig-utils/-/tsconfig-utils-8.46.0.tgz", + "integrity": "sha512-WrYXKGAHY836/N7zoK/kzi6p8tXFhasHh8ocFL9VZSAkvH956gfeRfcnhs3xzRy8qQ/dq3q44v1jvQieMFg2cw==", "dev": true, "license": "MIT", "engines": { @@ -6499,18 +5854,19 @@ "url": "https://opencollective.com/typescript-eslint" }, "peerDependencies": { - "typescript": ">=4.8.4 <5.9.0" + "typescript": ">=4.8.4 <6.0.0" } }, "node_modules/@typescript-eslint/type-utils": { - "version": "8.33.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/type-utils/-/type-utils-8.33.1.tgz", - "integrity": "sha512-1cG37d9xOkhlykom55WVwG2QRNC7YXlxMaMzqw2uPeJixBFfKWZgaP/hjAObqMN/u3fr5BrTwTnc31/L9jQ2ww==", + "version": "8.46.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/type-utils/-/type-utils-8.46.0.tgz", + "integrity": "sha512-hy+lvYV1lZpVs2jRaEYvgCblZxUoJiPyCemwbQZ+NGulWkQRy0HRPYAoef/CNSzaLt+MLvMptZsHXHlkEilaeg==", "dev": true, "license": "MIT", "dependencies": { - "@typescript-eslint/typescript-estree": "8.33.1", - "@typescript-eslint/utils": "8.33.1", + "@typescript-eslint/types": "8.46.0", + "@typescript-eslint/typescript-estree": "8.46.0", + "@typescript-eslint/utils": "8.46.0", "debug": "^4.3.4", "ts-api-utils": "^2.1.0" }, @@ -6523,13 +5879,13 @@ }, "peerDependencies": { "eslint": "^8.57.0 || ^9.0.0", - "typescript": ">=4.8.4 <5.9.0" + "typescript": ">=4.8.4 <6.0.0" } }, "node_modules/@typescript-eslint/types": { - "version": "8.33.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-8.33.1.tgz", - "integrity": "sha512-xid1WfizGhy/TKMTwhtVOgalHwPtV8T32MS9MaH50Cwvz6x6YqRIPdD2WvW0XaqOzTV9p5xdLY0h/ZusU5Lokg==", + "version": "8.46.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-8.46.0.tgz", + "integrity": "sha512-bHGGJyVjSE4dJJIO5yyEWt/cHyNwga/zXGJbJJ8TiO01aVREK6gCTu3L+5wrkb1FbDkQ+TKjMNe9R/QQQP9+rA==", "dev": true, "license": "MIT", "engines": { @@ -6541,16 +5897,16 @@ } }, "node_modules/@typescript-eslint/typescript-estree": { - "version": "8.33.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-8.33.1.tgz", - "integrity": "sha512-+s9LYcT8LWjdYWu7IWs7FvUxpQ/DGkdjZeE/GGulHvv8rvYwQvVaUZ6DE+j5x/prADUgSbbCWZ2nPI3usuVeOA==", + "version": "8.46.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-8.46.0.tgz", + "integrity": "sha512-ekDCUfVpAKWJbRfm8T1YRrCot1KFxZn21oV76v5Fj4tr7ELyk84OS+ouvYdcDAwZL89WpEkEj2DKQ+qg//+ucg==", "dev": true, "license": "MIT", "dependencies": { - "@typescript-eslint/project-service": "8.33.1", - "@typescript-eslint/tsconfig-utils": "8.33.1", - "@typescript-eslint/types": "8.33.1", - "@typescript-eslint/visitor-keys": "8.33.1", + "@typescript-eslint/project-service": "8.46.0", + "@typescript-eslint/tsconfig-utils": "8.46.0", + "@typescript-eslint/types": "8.46.0", + "@typescript-eslint/visitor-keys": "8.46.0", "debug": "^4.3.4", "fast-glob": "^3.3.2", "is-glob": "^4.0.3", @@ -6566,13 +5922,13 @@ "url": "https://opencollective.com/typescript-eslint" }, "peerDependencies": { - "typescript": ">=4.8.4 <5.9.0" + "typescript": ">=4.8.4 <6.0.0" } }, "node_modules/@typescript-eslint/typescript-estree/node_modules/brace-expansion": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-2.0.1.tgz", - "integrity": "sha512-XnAIvQ8eM+kC6aULx6wuQiwVsnzsi9d3WxzV3FpWTGA19F621kwdbsAcFKXgKUHZWsy+mY6iL1sHTxWEFCytDA==", + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-2.0.2.tgz", + "integrity": "sha512-Jt0vHyM+jmUBqojB7E1NIYadt0vI0Qxjxd2TErW94wDz+E2LAm5vKMXXwg6ZZBTHPuUlDgQHKXvjGBdfcF1ZDQ==", "dev": true, "license": "MIT", "dependencies": { @@ -6596,16 +5952,16 @@ } }, "node_modules/@typescript-eslint/utils": { - "version": "8.33.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/utils/-/utils-8.33.1.tgz", - "integrity": "sha512-52HaBiEQUaRYqAXpfzWSR2U3gxk92Kw006+xZpElaPMg3C4PgM+A5LqwoQI1f9E5aZ/qlxAZxzm42WX+vn92SQ==", + "version": "8.46.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/utils/-/utils-8.46.0.tgz", + "integrity": "sha512-nD6yGWPj1xiOm4Gk0k6hLSZz2XkNXhuYmyIrOWcHoPuAhjT9i5bAG+xbWPgFeNR8HPHHtpNKdYUXJl/D3x7f5g==", "dev": true, "license": "MIT", "dependencies": { "@eslint-community/eslint-utils": "^4.7.0", - "@typescript-eslint/scope-manager": "8.33.1", - "@typescript-eslint/types": "8.33.1", - "@typescript-eslint/typescript-estree": "8.33.1" + "@typescript-eslint/scope-manager": "8.46.0", + "@typescript-eslint/types": "8.46.0", + "@typescript-eslint/typescript-estree": "8.46.0" }, "engines": { "node": "^18.18.0 || ^20.9.0 || >=21.1.0" @@ -6616,18 +5972,18 @@ }, "peerDependencies": { "eslint": "^8.57.0 || ^9.0.0", - "typescript": ">=4.8.4 <5.9.0" + "typescript": ">=4.8.4 <6.0.0" } }, "node_modules/@typescript-eslint/visitor-keys": { - "version": "8.33.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-8.33.1.tgz", - "integrity": "sha512-3i8NrFcZeeDHJ+7ZUuDkGT+UHq+XoFGsymNK2jZCOHcfEzRQ0BdpRtdpSx/Iyf3MHLWIcLS0COuOPibKQboIiQ==", + "version": "8.46.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-8.46.0.tgz", + "integrity": "sha512-FrvMpAK+hTbFy7vH5j1+tMYHMSKLE6RzluFJlkFNKD0p9YsUT75JlBSmr5so3QRzvMwU5/bIEdeNrxm8du8l3Q==", "dev": true, "license": "MIT", "dependencies": { - "@typescript-eslint/types": "8.33.1", - "eslint-visitor-keys": "^4.2.0" + "@typescript-eslint/types": "8.46.0", + "eslint-visitor-keys": "^4.2.1" }, "engines": { "node": "^18.18.0 || ^20.9.0 || >=21.1.0" @@ -6638,9 +5994,9 @@ } }, "node_modules/@typescript-eslint/visitor-keys/node_modules/eslint-visitor-keys": { - "version": "4.2.0", - "resolved": "https://registry.npmjs.org/eslint-visitor-keys/-/eslint-visitor-keys-4.2.0.tgz", - "integrity": "sha512-UyLnSehNt62FFhSwjZlHmeokpRK59rcz29j+F1/aDgbkbRTk7wIc9XzdoasMUbRNKDM0qQt/+BJ4BrpFeABemw==", + "version": "4.2.1", + "resolved": "https://registry.npmjs.org/eslint-visitor-keys/-/eslint-visitor-keys-4.2.1.tgz", + "integrity": "sha512-Uhdk5sfqcee/9H/rCOJikYz67o0a2Tw2hGRPOG2Y1R2dg7brRe1uG0yaNQDHu+TO/uQPF/5eCapvYSmHUjt7JQ==", "dev": true, "license": "Apache-2.0", "engines": { @@ -6819,6 +6175,7 @@ }, "node_modules/abort-controller": { "version": "3.0.0", + "dev": true, "license": "MIT", "dependencies": { "event-target-shim": "^5.0.0" @@ -6827,12 +6184,6 @@ "node": ">=6.5" } }, - "node_modules/abort-controller-x": { - "version": "0.4.3", - "resolved": "https://registry.npmjs.org/abort-controller-x/-/abort-controller-x-0.4.3.tgz", - "integrity": "sha512-VtUwTNU8fpMwvWGn4xE93ywbogTYsuT+AUxAXOeelbXuQVIwNmC5YLeho9sH4vZ4ITW8414TTAOG1nW6uIVHCA==", - "license": "MIT" - }, "node_modules/accept-language-parser": { "version": "1.5.0", "license": "MIT" @@ -6852,7 +6203,7 @@ "version": "8.15.0", "resolved": "https://registry.npmjs.org/acorn/-/acorn-8.15.0.tgz", "integrity": "sha512-NZyJarBfL7nWwIq+FDL6Zp/yHEhePMNnnJ0y3qfieCrmNvYct8uvtiV41UvlSe6apAfk0fY1FbWx+NwfmpvtTg==", - "devOptional": true, + "peer": true, "bin": { "acorn": "bin/acorn" }, @@ -6860,6 +6211,15 @@ "node": ">=0.4.0" } }, + "node_modules/acorn-import-attributes": { + "version": "1.9.5", + "resolved": "https://registry.npmjs.org/acorn-import-attributes/-/acorn-import-attributes-1.9.5.tgz", + "integrity": "sha512-n02Vykv5uA3eHGM/Z2dQrcD56kL8TyDb2p1+0P83PClMnC/nc+anbQRhIOWnSq4Ke/KvDPrY3C9hDtC/A3eHnQ==", + "license": "MIT", + "peerDependencies": { + "acorn": "^8" + } + }, "node_modules/acorn-jsx": { "version": "5.3.2", "dev": true, @@ -6887,20 +6247,29 @@ "node": ">= 14" } }, - "node_modules/agentkeepalive": { - "version": "4.6.0", - "license": "MIT", + "node_modules/ai": { + "version": "5.0.44", + "resolved": "https://registry.npmjs.org/ai/-/ai-5.0.44.tgz", + "integrity": "sha512-l/rdoM4LcRpsRBVvZQBwSU73oNoFGlWj+PcH86QRzxDGJgZqgGItWO0QcKjBNcLDmUjGN1VYd/8J0TAXHJleRQ==", + "license": "Apache-2.0", "peer": true, "dependencies": { - "humanize-ms": "^1.2.1" + "@ai-sdk/gateway": "1.0.23", + "@ai-sdk/provider": "2.0.0", + "@ai-sdk/provider-utils": "3.0.9", + "@opentelemetry/api": "1.9.0" }, "engines": { - "node": ">= 8.0.0" + "node": ">=18" + }, + "peerDependencies": { + "zod": "^3.25.76 || ^4" } }, "node_modules/ajv": { "version": "6.12.6", "license": "MIT", + "peer": true, "dependencies": { "fast-deep-equal": "^3.1.1", "fast-json-stable-stringify": "^2.0.0", @@ -6994,6 +6363,7 @@ }, "node_modules/ansi-styles": { "version": "5.2.0", + "dev": true, "license": "MIT", "engines": { "node": ">=10" @@ -7078,7 +6448,9 @@ } }, "node_modules/archiver-utils/node_modules/brace-expansion": { - "version": "2.0.1", + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-2.0.2.tgz", + "integrity": "sha512-Jt0vHyM+jmUBqojB7E1NIYadt0vI0Qxjxd2TErW94wDz+E2LAm5vKMXXwg6ZZBTHPuUlDgQHKXvjGBdfcF1ZDQ==", "dev": true, "license": "MIT", "dependencies": { @@ -7365,6 +6737,7 @@ }, "node_modules/asynckit": { "version": "0.4.0", + "devOptional": true, "license": "MIT" }, "node_modules/available-typed-arrays": { @@ -7380,11 +6753,19 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/aws4fetch": { + "version": "1.0.20", + "resolved": "https://registry.npmjs.org/aws4fetch/-/aws4fetch-1.0.20.tgz", + "integrity": "sha512-/djoAN709iY65ETD6LKCtyyEI04XIBP5xVvfmNxsEP0uJB5tyaGBztSryRr4HqMStr9R06PisQE7m9zDTXKu6g==", + "license": "MIT" + }, "node_modules/axios": { "version": "1.10.0", "resolved": "https://registry.npmjs.org/axios/-/axios-1.10.0.tgz", "integrity": "sha512-/1xYAC4MP/HEG+3duIhFr4ZQXR4sQXOIe+o6sdqzeykGLx6Upp/1p8MHqhINOvGeP7xyNHe7tsiJByc4SSVUxw==", + "devOptional": true, "license": "MIT", + "peer": true, "dependencies": { "follow-redirects": "^1.15.6", "form-data": "^4.0.0", @@ -7718,10 +7099,6 @@ "node": ">=18" } }, - "node_modules/bowser": { - "version": "2.11.0", - "license": "MIT" - }, "node_modules/boxen": { "version": "5.1.2", "license": "MIT", @@ -7795,7 +7172,9 @@ } }, "node_modules/brace-expansion": { - "version": "1.1.11", + "version": "1.1.12", + "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.12.tgz", + "integrity": "sha512-9T9UjW3r0UW5c1Q7GTwllptXwhvYmEzFhzMfZ9H7FQWt+uZePjZPjBP/W1ZEyZ1twGWom5/56TF4lPcqjnDHcg==", "dev": true, "license": "MIT", "dependencies": { @@ -7831,6 +7210,7 @@ } ], "license": "MIT", + "peer": true, "dependencies": { "caniuse-lite": "^1.0.30001716", "electron-to-chromium": "^1.5.149", @@ -8151,16 +7531,17 @@ }, "node_modules/cjs-module-lexer": { "version": "1.4.3", - "dev": true, "license": "MIT" }, "node_modules/class-transformer": { "version": "0.5.1", - "license": "MIT" + "license": "MIT", + "peer": true }, "node_modules/class-validator": { "version": "0.14.2", "license": "MIT", + "peer": true, "dependencies": { "@types/validator": "^13.11.8", "libphonenumber-js": "^1.11.1", @@ -8336,6 +7717,7 @@ }, "node_modules/combined-stream": { "version": "1.0.8", + "devOptional": true, "license": "MIT", "dependencies": { "delayed-stream": "~1.0.0" @@ -8526,13 +7908,6 @@ "node": "^14.18.0 || >=16.10.0" } }, - "node_modules/console-table-printer": { - "version": "2.12.1", - "license": "MIT", - "dependencies": { - "simple-wcswidth": "^1.0.1" - } - }, "node_modules/console.table": { "version": "0.10.0", "dev": true, @@ -8719,15 +8094,6 @@ "devOptional": true, "license": "MIT" }, - "node_modules/cross-fetch": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/cross-fetch/-/cross-fetch-3.2.0.tgz", - "integrity": "sha512-Q+xVJLoGOeIMXZmbUK4HYk+69cQH6LudR0Vu/pRm2YlU/hDV9CiS0gKUMaWY5f2NeUH9C1nV3bsTlCo0FsTV1Q==", - "license": "MIT", - "dependencies": { - "node-fetch": "^2.7.0" - } - }, "node_modules/cross-spawn": { "version": "7.0.6", "license": "MIT", @@ -8824,13 +8190,6 @@ } } }, - "node_modules/decamelize": { - "version": "1.2.0", - "license": "MIT", - "engines": { - "node": ">=0.10.0" - } - }, "node_modules/dedent": { "version": "1.6.0", "license": "MIT", @@ -8850,6 +8209,7 @@ }, "node_modules/deepmerge": { "version": "4.3.1", + "dev": true, "license": "MIT", "engines": { "node": ">=0.10.0" @@ -8952,6 +8312,7 @@ }, "node_modules/delayed-stream": { "version": "1.0.0", + "devOptional": true, "license": "MIT", "engines": { "node": ">=0.4.0" @@ -9072,10 +8433,11 @@ } }, "node_modules/dockerode/node_modules/tar-fs": { - "version": "2.1.3", - "resolved": "https://registry.npmjs.org/tar-fs/-/tar-fs-2.1.3.tgz", - "integrity": "sha512-090nwYJDmlhwFwEW3QQl+vaNnxsO2yVsd45eTKRBzSzu+hlb1w2K9inVq5b0ngXuLVqQ4ApvsUHHnu/zQNkWAg==", + "version": "2.1.4", + "resolved": "https://registry.npmjs.org/tar-fs/-/tar-fs-2.1.4.tgz", + "integrity": "sha512-mDAjwmZdh7LTT6pNleZ05Yt65HC3E+NiQzl672vQG38jIrehtJk/J3mNwIg+vShQPcLF/LV7CMnDW6vjj6sfYQ==", "dev": true, + "license": "MIT", "dependencies": { "chownr": "^1.1.1", "mkdirp-classic": "^0.5.2", @@ -9367,6 +8729,7 @@ }, "node_modules/es-set-tostringtag": { "version": "2.1.0", + "devOptional": true, "license": "MIT", "dependencies": { "es-errors": "^1.3.0", @@ -9467,20 +8830,21 @@ } }, "node_modules/eslint": { - "version": "9.32.0", - "resolved": "https://registry.npmjs.org/eslint/-/eslint-9.32.0.tgz", - "integrity": "sha512-LSehfdpgMeWcTZkWZVIJl+tkZ2nuSkyyB9C27MZqFWXuph7DvaowgcTvKqxvpLW1JZIk8PN7hFY3Rj9LQ7m7lg==", + "version": "9.37.0", + "resolved": "https://registry.npmjs.org/eslint/-/eslint-9.37.0.tgz", + "integrity": "sha512-XyLmROnACWqSxiGYArdef1fItQd47weqB7iwtfr9JHwRrqIXZdcFMvvEcL9xHCmL0SNsOvF0c42lWyM1U5dgig==", "dev": true, "license": "MIT", + "peer": true, "dependencies": { - "@eslint-community/eslint-utils": "^4.2.0", + "@eslint-community/eslint-utils": "^4.8.0", "@eslint-community/regexpp": "^4.12.1", "@eslint/config-array": "^0.21.0", - "@eslint/config-helpers": "^0.3.0", - "@eslint/core": "^0.15.0", + "@eslint/config-helpers": "^0.4.0", + "@eslint/core": "^0.16.0", "@eslint/eslintrc": "^3.3.1", - "@eslint/js": "9.32.0", - "@eslint/plugin-kit": "^0.3.4", + "@eslint/js": "9.37.0", + "@eslint/plugin-kit": "^0.4.0", "@humanfs/node": "^0.16.6", "@humanwhocodes/module-importer": "^1.0.1", "@humanwhocodes/retry": "^0.4.2", @@ -9528,9 +8892,12 @@ } }, "node_modules/eslint-config-prettier": { - "version": "10.1.5", + "version": "10.1.8", + "resolved": "https://registry.npmjs.org/eslint-config-prettier/-/eslint-config-prettier-10.1.8.tgz", + "integrity": "sha512-82GZUjRS0p/jganf6q1rEO25VSoHH0hKPCTrgillPjdI/3bgBhAE1QzHrHTizjpRvy6pGAvKjDJtk2pF9NDq8w==", "dev": true, "license": "MIT", + "peer": true, "bin": { "eslint-config-prettier": "bin/cli.js" }, @@ -9722,9 +9089,9 @@ } }, "node_modules/eslint/node_modules/@eslint/js": { - "version": "9.32.0", - "resolved": "https://registry.npmjs.org/@eslint/js/-/js-9.32.0.tgz", - "integrity": "sha512-BBpRFZK3eX6uMLKz8WxFOBIFFcGFJ/g8XuwjTHCqHROSIsopI+ddn/d5Cfh36+7+e5edVS8dbSHnBNhrLEX0zg==", + "version": "9.37.0", + "resolved": "https://registry.npmjs.org/@eslint/js/-/js-9.37.0.tgz", + "integrity": "sha512-jaS+NJ+hximswBG6pjNX0uEJZkrT0zwpVi3BA3vX22aFGjJjmgSTSmPpZCRKmoBL5VY/M6p0xsSJx7rk7sy5gg==", "dev": true, "license": "MIT", "engines": { @@ -9834,17 +9201,15 @@ }, "node_modules/event-target-shim": { "version": "5.0.1", + "dev": true, "license": "MIT", "engines": { "node": ">=6" } }, - "node_modules/eventemitter3": { - "version": "4.0.7", - "license": "MIT" - }, "node_modules/events": { "version": "3.3.0", + "dev": true, "license": "MIT", "engines": { "node": ">=0.8.x" @@ -9861,7 +9226,9 @@ } }, "node_modules/eventsource-parser": { - "version": "3.0.1", + "version": "3.0.6", + "resolved": "https://registry.npmjs.org/eventsource-parser/-/eventsource-parser-3.0.6.tgz", + "integrity": "sha512-Vo1ab+QXPzZ4tCa8SwIHJFaSzy4R6SHf7BY79rFBDf0idraZWAkYrDjDj8uWaSm3S2TK+hJ7/t1CEmZ7jXw+pg==", "license": "MIT", "engines": { "node": ">=18.0.0" @@ -9918,11 +9285,14 @@ }, "node_modules/expr-eval": { "version": "2.0.2", + "resolved": "https://registry.npmjs.org/expr-eval/-/expr-eval-2.0.2.tgz", + "integrity": "sha512-4EMSHGOPSwAfBiibw3ndnP0AvjDWLsMvGOvWEZ2F96IGk0bIVdjQisOHxReSkE13mHcfbuCiXw+G4y0zv6N8Eg==", "license": "MIT" }, "node_modules/express": { "version": "5.1.0", "license": "MIT", + "peer": true, "dependencies": { "accepts": "^2.0.0", "body-parser": "^2.2.0", @@ -10114,26 +9484,6 @@ ], "license": "BSD-3-Clause" }, - "node_modules/fast-xml-parser": { - "version": "4.4.1", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/NaturalIntelligence" - }, - { - "type": "paypal", - "url": "https://paypal.me/naturalintelligence" - } - ], - "license": "MIT", - "dependencies": { - "strnum": "^1.0.5" - }, - "bin": { - "fxparser": "src/cli/cli.js" - } - }, "node_modules/fastq": { "version": "1.19.1", "resolved": "https://registry.npmjs.org/fastq/-/fastq-1.19.1.tgz", @@ -10156,36 +9506,6 @@ "version": "4.2.3", "license": "MIT" }, - "node_modules/fetch-blob": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/fetch-blob/-/fetch-blob-3.2.0.tgz", - "integrity": "sha512-7yAQpD2UMJzLi1Dqv7qFYnPbaPx7ZfFK6PiIxQ4PfkGPyNyl2Ugx+a/umUonmKqjhM4DnfbMvdX6otXq83soQQ==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/jimmywarting" - }, - { - "type": "paypal", - "url": "https://paypal.me/jimmywarting" - } - ], - "dependencies": { - "node-domexception": "^1.0.0", - "web-streams-polyfill": "^3.0.3" - }, - "engines": { - "node": "^12.20 || >= 14.13" - } - }, - "node_modules/fetch-blob/node_modules/web-streams-polyfill": { - "version": "3.3.3", - "resolved": "https://registry.npmjs.org/web-streams-polyfill/-/web-streams-polyfill-3.3.3.tgz", - "integrity": "sha512-d2JWLCivmZYTSIoge9MsgFCZrt571BikcWGYkjC1khllbTeDlGqZ2D8vD8E/lJa8WGWbb7Plm8/XJYV7IJHZZw==", - "engines": { - "node": ">= 8" - } - }, "node_modules/fflate": { "version": "0.8.2", "license": "MIT" @@ -10250,7 +9570,9 @@ } }, "node_modules/filelist/node_modules/brace-expansion": { - "version": "2.0.1", + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-2.0.2.tgz", + "integrity": "sha512-Jt0vHyM+jmUBqojB7E1NIYadt0vI0Qxjxd2TErW94wDz+E2LAm5vKMXXwg6ZZBTHPuUlDgQHKXvjGBdfcF1ZDQ==", "dev": true, "license": "MIT", "dependencies": { @@ -10308,13 +9630,6 @@ "url": "https://github.com/sponsors/sindresorhus" } }, - "node_modules/flat": { - "version": "5.0.2", - "license": "BSD-3-Clause", - "bin": { - "flat": "cli.js" - } - }, "node_modules/flat-cache": { "version": "4.0.1", "dev": true, @@ -10346,6 +9661,7 @@ }, "node_modules/follow-redirects": { "version": "1.15.9", + "devOptional": true, "funding": [ { "type": "individual", @@ -10458,6 +9774,7 @@ "version": "4.0.4", "resolved": "https://registry.npmjs.org/form-data/-/form-data-4.0.4.tgz", "integrity": "sha512-KrGhL9Q4zjj0kiUt5OO4Mr/A/jlI2jDYs5eHBpYHPcBEVSiipAvn2Ko2HnPe20rmcuuvMHNdZFp+4IlGTMF0Ow==", + "devOptional": true, "license": "MIT", "dependencies": { "asynckit": "^0.4.0", @@ -10470,13 +9787,9 @@ "node": ">= 6" } }, - "node_modules/form-data-encoder": { - "version": "1.7.2", - "license": "MIT", - "peer": true - }, "node_modules/form-data/node_modules/mime-db": { "version": "1.52.0", + "devOptional": true, "license": "MIT", "engines": { "node": ">= 0.6" @@ -10484,6 +9797,7 @@ }, "node_modules/form-data/node_modules/mime-types": { "version": "2.1.35", + "devOptional": true, "license": "MIT", "dependencies": { "mime-db": "1.52.0" @@ -10492,29 +9806,6 @@ "node": ">= 0.6" } }, - "node_modules/formdata-node": { - "version": "4.4.1", - "license": "MIT", - "peer": true, - "dependencies": { - "node-domexception": "1.0.0", - "web-streams-polyfill": "4.0.0-beta.3" - }, - "engines": { - "node": ">= 12.20" - } - }, - "node_modules/formdata-polyfill": { - "version": "4.0.10", - "resolved": "https://registry.npmjs.org/formdata-polyfill/-/formdata-polyfill-4.0.10.tgz", - "integrity": "sha512-buewHzMvYL29jdeQTVILecSaZKnt/RJWjoZCF5OW60Z67/GmSLBkOFM7qh1PI3zFNtJbaZL5eQu1vLfazOwj4g==", - "dependencies": { - "fetch-blob": "^3.1.2" - }, - "engines": { - "node": ">=12.20.0" - } - }, "node_modules/formidable": { "version": "3.5.4", "resolved": "https://registry.npmjs.org/formidable/-/formidable-3.5.4.tgz", @@ -10539,6 +9830,12 @@ "node": ">= 0.6" } }, + "node_modules/forwarded-parse": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/forwarded-parse/-/forwarded-parse-2.1.2.tgz", + "integrity": "sha512-alTFZZQDKMporBH77856pXgzhEzaUVmLCDk+egLgIgHst3Tpndzz8MnKe+GzRJRfvVdn69HhpW7cmXzvtLvJAw==", + "license": "MIT" + }, "node_modules/fresh": { "version": "2.0.0", "license": "MIT", @@ -10624,54 +9921,33 @@ } }, "node_modules/gaxios": { - "version": "7.1.1", - "resolved": "https://registry.npmjs.org/gaxios/-/gaxios-7.1.1.tgz", - "integrity": "sha512-Odju3uBUJyVCkW64nLD4wKLhbh93bh6vIg/ZIXkWiLPBrdgtc65+tls/qml+un3pr6JqYVFDZbbmLDQT68rTOQ==", + "version": "6.7.1", + "resolved": "https://registry.npmjs.org/gaxios/-/gaxios-6.7.1.tgz", + "integrity": "sha512-LDODD4TMYx7XXdpwxAVRAIAuB0bzv0s+ywFonY46k126qzQHT9ygyoa9tncmOiQmmDrik65UYsEkv3lbfqQ3yQ==", + "license": "Apache-2.0", "dependencies": { "extend": "^3.0.2", "https-proxy-agent": "^7.0.1", - "node-fetch": "^3.3.2" - }, - "engines": { - "node": ">=18" - } - }, - "node_modules/gaxios/node_modules/data-uri-to-buffer": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/data-uri-to-buffer/-/data-uri-to-buffer-4.0.1.tgz", - "integrity": "sha512-0R9ikRb668HB7QDxT1vkpuUBtqc53YyAwMwGeUFKRojY/NWKvdZ+9UYtRfGmhqNbRkTSVpMbmyhXipFFv2cb/A==", - "engines": { - "node": ">= 12" - } - }, - "node_modules/gaxios/node_modules/node-fetch": { - "version": "3.3.2", - "resolved": "https://registry.npmjs.org/node-fetch/-/node-fetch-3.3.2.tgz", - "integrity": "sha512-dRB78srN/l6gqWulah9SrxeYnxeddIG30+GOqK/9OlLVyLg3HPnr6SqOWTWOXKRwC2eGYCkZ59NNuSgvSrpgOA==", - "dependencies": { - "data-uri-to-buffer": "^4.0.0", - "fetch-blob": "^3.1.4", - "formdata-polyfill": "^4.0.10" + "is-stream": "^2.0.0", + "node-fetch": "^2.6.9", + "uuid": "^9.0.1" }, "engines": { - "node": "^12.20.0 || ^14.13.1 || >=16.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/node-fetch" + "node": ">=14" } }, "node_modules/gcp-metadata": { - "version": "7.0.1", - "resolved": "https://registry.npmjs.org/gcp-metadata/-/gcp-metadata-7.0.1.tgz", - "integrity": "sha512-UcO3kefx6dCcZkgcTGgVOTFb7b1LlQ02hY1omMjjrrBzkajRMCFgYOjs7J71WqnuG1k2b+9ppGL7FsOfhZMQKQ==", + "version": "6.1.1", + "resolved": "https://registry.npmjs.org/gcp-metadata/-/gcp-metadata-6.1.1.tgz", + "integrity": "sha512-a4tiq7E0/5fTjxPAaH4jpjkSv/uCaU2p5KC6HVGrvl0cDjA8iBZv4vv1gyzlmK0ZUKqwpOyQMKzZQe3lTit77A==", + "license": "Apache-2.0", "dependencies": { - "gaxios": "^7.0.0", - "google-logging-utils": "^1.0.0", + "gaxios": "^6.1.1", + "google-logging-utils": "^0.0.2", "json-bigint": "^1.0.0" }, "engines": { - "node": ">=18" + "node": ">=14" } }, "node_modules/gensync": { @@ -10820,7 +10096,9 @@ "license": "BSD-2-Clause" }, "node_modules/glob/node_modules/brace-expansion": { - "version": "2.0.1", + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-2.0.2.tgz", + "integrity": "sha512-Jt0vHyM+jmUBqojB7E1NIYadt0vI0Qxjxd2TErW94wDz+E2LAm5vKMXXwg6ZZBTHPuUlDgQHKXvjGBdfcF1ZDQ==", "dev": true, "license": "MIT", "dependencies": { @@ -10859,36 +10137,20 @@ "license": "MIT", "dependencies": { "define-properties": "^1.2.1", - "gopd": "^1.0.1" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/google-auth-library": { - "version": "10.1.0", - "resolved": "https://registry.npmjs.org/google-auth-library/-/google-auth-library-10.1.0.tgz", - "integrity": "sha512-GspVjZj1RbyRWpQ9FbAXMKjFGzZwDKnUHi66JJ+tcjcu5/xYAP1pdlWotCuIkMwjfVsxxDvsGZXGLzRt72D0sQ==", - "dependencies": { - "base64-js": "^1.3.0", - "ecdsa-sig-formatter": "^1.0.11", - "gaxios": "^7.0.0", - "gcp-metadata": "^7.0.0", - "google-logging-utils": "^1.0.0", - "gtoken": "^8.0.0", - "jws": "^4.0.0" + "gopd": "^1.0.1" }, "engines": { - "node": ">=18" + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" } }, "node_modules/google-logging-utils": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/google-logging-utils/-/google-logging-utils-1.1.1.tgz", - "integrity": "sha512-rcX58I7nqpu4mbKztFeOAObbomBbHU2oIb/d3tJfF3dizGSApqtSwYJigGCooHdnMyQBIw8BrWyK96w3YXgr6A==", + "version": "0.0.2", + "resolved": "https://registry.npmjs.org/google-logging-utils/-/google-logging-utils-0.0.2.tgz", + "integrity": "sha512-NEgUnEcBiP5HrPzufUkBzJOD/Sxsco3rLNo1F1TNf7ieU8ryUzBhqba8r756CjLX7rn3fHl6iLEwPYuqpoKgQQ==", + "license": "Apache-2.0", "engines": { "node": ">=14" } @@ -10913,40 +10175,6 @@ "dev": true, "license": "MIT" }, - "node_modules/graphql": { - "version": "16.11.0", - "resolved": "https://registry.npmjs.org/graphql/-/graphql-16.11.0.tgz", - "integrity": "sha512-mS1lbMsxgQj6hge1XZ6p7GPhbrtFwUFYi3wRzXAC/FmYnyXMTvvI3td3rjmQ2u8ewXueaSvRPWaEcgVVOT9Jnw==", - "license": "MIT", - "engines": { - "node": "^12.22.0 || ^14.16.0 || ^16.0.0 || >=17.0.0" - } - }, - "node_modules/graphql-request": { - "version": "6.1.0", - "resolved": "https://registry.npmjs.org/graphql-request/-/graphql-request-6.1.0.tgz", - "integrity": "sha512-p+XPfS4q7aIpKVcgmnZKhMNqhltk20hfXtkaIkTfjjmiKMJ5xrt5c743cL03y/K7y1rg3WrIC49xGiEQ4mxdNw==", - "license": "MIT", - "dependencies": { - "@graphql-typed-document-node/core": "^3.2.0", - "cross-fetch": "^3.1.5" - }, - "peerDependencies": { - "graphql": "14 - 16" - } - }, - "node_modules/gtoken": { - "version": "8.0.0", - "resolved": "https://registry.npmjs.org/gtoken/-/gtoken-8.0.0.tgz", - "integrity": "sha512-+CqsMbHPiSTdtSO14O51eMNlrp9N79gmeqmXeouJOhfucAedHw9noVe/n5uJk3tbKE6a+6ZCQg3RPhVhHByAIw==", - "dependencies": { - "gaxios": "^7.0.0", - "jws": "^4.0.0" - }, - "engines": { - "node": ">=18" - } - }, "node_modules/has-bigints": { "version": "1.1.0", "dev": true, @@ -11096,137 +10324,6 @@ "node": ">=10.17.0" } }, - "node_modules/humanize-ms": { - "version": "1.2.1", - "license": "MIT", - "peer": true, - "dependencies": { - "ms": "^2.0.0" - } - }, - "node_modules/ibm-cloud-sdk-core": { - "version": "5.4.1", - "resolved": "https://registry.npmjs.org/ibm-cloud-sdk-core/-/ibm-cloud-sdk-core-5.4.1.tgz", - "integrity": "sha512-kGh1KlkFHFsJANWiGTJZ5PNoL4bZHAGprAa/uSFvLpJdKUEOH+xUAUYcLMTH71jtgy9Wl2ePDjaLWiWe80uGiA==", - "license": "Apache-2.0", - "peer": true, - "dependencies": { - "@types/debug": "^4.1.12", - "@types/node": "^18.19.80", - "@types/tough-cookie": "^4.0.0", - "axios": "^1.8.2", - "camelcase": "^6.3.0", - "debug": "^4.3.4", - "dotenv": "^16.4.5", - "extend": "3.0.2", - "file-type": "16.5.4", - "form-data": "^4.0.4", - "isstream": "0.1.2", - "jsonwebtoken": "^9.0.2", - "mime-types": "2.1.35", - "retry-axios": "^2.6.0", - "tough-cookie": "^4.1.3" - }, - "engines": { - "node": ">=18" - } - }, - "node_modules/ibm-cloud-sdk-core/node_modules/@types/node": { - "version": "18.19.100", - "license": "MIT", - "peer": true, - "dependencies": { - "undici-types": "~5.26.4" - } - }, - "node_modules/ibm-cloud-sdk-core/node_modules/file-type": { - "version": "16.5.4", - "license": "MIT", - "peer": true, - "dependencies": { - "readable-web-to-node-stream": "^3.0.0", - "strtok3": "^6.2.4", - "token-types": "^4.1.1" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sindresorhus/file-type?sponsor=1" - } - }, - "node_modules/ibm-cloud-sdk-core/node_modules/mime-db": { - "version": "1.52.0", - "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.52.0.tgz", - "integrity": "sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg==", - "license": "MIT", - "peer": true, - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/ibm-cloud-sdk-core/node_modules/mime-types": { - "version": "2.1.35", - "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.35.tgz", - "integrity": "sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw==", - "license": "MIT", - "peer": true, - "dependencies": { - "mime-db": "1.52.0" - }, - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/ibm-cloud-sdk-core/node_modules/peek-readable": { - "version": "4.1.0", - "license": "MIT", - "peer": true, - "engines": { - "node": ">=8" - }, - "funding": { - "type": "github", - "url": "https://github.com/sponsors/Borewit" - } - }, - "node_modules/ibm-cloud-sdk-core/node_modules/strtok3": { - "version": "6.3.0", - "license": "MIT", - "peer": true, - "dependencies": { - "@tokenizer/token": "^0.3.0", - "peek-readable": "^4.1.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "type": "github", - "url": "https://github.com/sponsors/Borewit" - } - }, - "node_modules/ibm-cloud-sdk-core/node_modules/token-types": { - "version": "4.2.1", - "license": "MIT", - "peer": true, - "dependencies": { - "@tokenizer/token": "^0.3.0", - "ieee754": "^1.2.1" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "type": "github", - "url": "https://github.com/sponsors/Borewit" - } - }, - "node_modules/ibm-cloud-sdk-core/node_modules/undici-types": { - "version": "5.26.5", - "license": "MIT", - "peer": true - }, "node_modules/iconv-lite": { "version": "0.6.3", "license": "MIT", @@ -11257,7 +10354,7 @@ }, "node_modules/ignore": { "version": "5.3.2", - "devOptional": true, + "dev": true, "license": "MIT", "engines": { "node": ">= 4" @@ -11278,6 +10375,18 @@ "url": "https://github.com/sponsors/sindresorhus" } }, + "node_modules/import-in-the-middle": { + "version": "1.14.2", + "resolved": "https://registry.npmjs.org/import-in-the-middle/-/import-in-the-middle-1.14.2.tgz", + "integrity": "sha512-5tCuY9BV8ujfOpwtAGgsTx9CGUapcFMEEyByLv1B+v2+6DhAcw+Zr0nhQT7uwaZ7DiourxFEscghOR8e1aPLQw==", + "license": "Apache-2.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" + } + }, "node_modules/import-local": { "version": "3.2.0", "dev": true, @@ -11477,7 +10586,6 @@ }, "node_modules/is-core-module": { "version": "2.16.1", - "dev": true, "license": "MIT", "dependencies": { "hasown": "^2.0.2" @@ -11844,11 +10952,6 @@ "version": "2.0.0", "license": "ISC" }, - "node_modules/isstream": { - "version": "0.1.2", - "license": "MIT", - "peer": true - }, "node_modules/istanbul-lib-coverage": { "version": "3.2.2", "dev": true, @@ -11976,6 +11079,7 @@ "version": "29.7.0", "dev": true, "license": "MIT", + "peer": true, "dependencies": { "@jest/core": "^29.7.0", "@jest/types": "^29.6.3", @@ -12652,13 +11756,6 @@ "url": "https://github.com/chalk/supports-color?sponsor=1" } }, - "node_modules/js-tiktoken": { - "version": "1.0.20", - "license": "MIT", - "dependencies": { - "base64-js": "^1.5.1" - } - }, "node_modules/js-tokens": { "version": "4.0.0", "dev": true, @@ -12716,6 +11813,12 @@ "dev": true, "license": "MIT" }, + "node_modules/json-schema": { + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/json-schema/-/json-schema-0.4.0.tgz", + "integrity": "sha512-es94M3nTIfsEPisRafak+HDLfHXnKBhV3vU5eqPcS3flIWqcxJWgXHXiey3YrpaNsanY5ei1VoYEbOzijuq9BA==", + "license": "(AFL-2.1 OR BSD-3-Clause)" + }, "node_modules/json-schema-traverse": { "version": "0.4.1", "license": "MIT" @@ -12752,13 +11855,6 @@ "graceful-fs": "^4.1.6" } }, - "node_modules/jsonpointer": { - "version": "5.0.1", - "license": "MIT", - "engines": { - "node": ">=0.10.0" - } - }, "node_modules/jsonwebtoken": { "version": "9.0.2", "license": "MIT", @@ -12827,129 +11923,22 @@ "version": "2.0.0", "license": "MIT" }, - "node_modules/langchain": { - "version": "0.3.29", - "resolved": "https://registry.npmjs.org/langchain/-/langchain-0.3.29.tgz", - "integrity": "sha512-L389pKlApVJPqu4hp58qY6NZAobI+MFPoBjSfjT1z3mcxtB68wLFGhaH4DVsTVg21NYO+0wTEoz24BWrxu9YGw==", - "dependencies": { - "@langchain/openai": ">=0.1.0 <0.6.0", - "@langchain/textsplitters": ">=0.0.0 <0.2.0", - "js-tiktoken": "^1.0.12", - "js-yaml": "^4.1.0", - "jsonpointer": "^5.0.1", - "langsmith": "^0.3.33", - "openapi-types": "^12.1.3", - "p-retry": "4", - "uuid": "^10.0.0", - "yaml": "^2.2.1", - "zod": "^3.25.32" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "@langchain/anthropic": "*", - "@langchain/aws": "*", - "@langchain/cerebras": "*", - "@langchain/cohere": "*", - "@langchain/core": ">=0.3.58 <0.4.0", - "@langchain/deepseek": "*", - "@langchain/google-genai": "*", - "@langchain/google-vertexai": "*", - "@langchain/google-vertexai-web": "*", - "@langchain/groq": "*", - "@langchain/mistralai": "*", - "@langchain/ollama": "*", - "@langchain/xai": "*", - "axios": "*", - "cheerio": "*", - "handlebars": "^4.7.8", - "peggy": "^3.0.2", - "typeorm": "*" - }, - "peerDependenciesMeta": { - "@langchain/anthropic": { - "optional": true - }, - "@langchain/aws": { - "optional": true - }, - "@langchain/cerebras": { - "optional": true - }, - "@langchain/cohere": { - "optional": true - }, - "@langchain/deepseek": { - "optional": true - }, - "@langchain/google-genai": { - "optional": true - }, - "@langchain/google-vertexai": { - "optional": true - }, - "@langchain/google-vertexai-web": { - "optional": true - }, - "@langchain/groq": { - "optional": true - }, - "@langchain/mistralai": { - "optional": true - }, - "@langchain/ollama": { - "optional": true - }, - "@langchain/xai": { - "optional": true - }, - "axios": { - "optional": true - }, - "cheerio": { - "optional": true - }, - "handlebars": { - "optional": true - }, - "peggy": { - "optional": true - }, - "typeorm": { - "optional": true - } - } - }, - "node_modules/langchain/node_modules/uuid": { - "version": "10.0.0", - "resolved": "https://registry.npmjs.org/uuid/-/uuid-10.0.0.tgz", - "integrity": "sha512-8XkAphELsDnEGrDxUOHB3RGvXz6TeuYSGEZBOjtTtPm2lwhGBjLgOzLHB63IUWfBpNucQjND6d3AOudO+H3RWQ==", - "funding": [ - "https://github.com/sponsors/broofa", - "https://github.com/sponsors/ctavan" - ], - "license": "MIT", - "bin": { - "uuid": "dist/bin/uuid" - } - }, "node_modules/langfuse": { - "version": "3.38.4", - "resolved": "https://registry.npmjs.org/langfuse/-/langfuse-3.38.4.tgz", - "integrity": "sha512-2UqMeHLl3DGNX1Nh/cO4jGhk7TzDJ6gjQLlyS9rwFCKVO81xot6b58yeTsTB5YrWupWsOxQtMNoQYIQGOUlH9Q==", + "version": "3.38.5", + "resolved": "https://registry.npmjs.org/langfuse/-/langfuse-3.38.5.tgz", + "integrity": "sha512-pvcq9qJh/q/OFGPET4/sFfXRhCcEgONx1NTqZ8bu/hnorD5xZ/qpS+er0esXJ5cuRILEGw9ydKezAeULf8tpyQ==", "license": "MIT", "dependencies": { - "langfuse-core": "^3.38.4" + "langfuse-core": "^3.38.5" }, "engines": { "node": ">=18" } }, "node_modules/langfuse-core": { - "version": "3.38.4", - "resolved": "https://registry.npmjs.org/langfuse-core/-/langfuse-core-3.38.4.tgz", - "integrity": "sha512-onTAqcEGhoXuBgqDFXe2t+bt9Vi+5YChRgdz3voM49JKoHwtVZQiUdqTfjSivGR75eSbYoiaIL8IRoio+jaqwg==", + "version": "3.38.5", + "resolved": "https://registry.npmjs.org/langfuse-core/-/langfuse-core-3.38.5.tgz", + "integrity": "sha512-vf/4zxv7/mz97yOpQiCJ7Mok8YZt9a52nn3XWTj+qxll4zenHT+wfAHwvfJ4BnVjK54GbEmP7IB524f/5ltq7g==", "license": "MIT", "dependencies": { "mustache": "^4.2.0" @@ -12958,58 +11947,20 @@ "node": ">=18" } }, - "node_modules/langfuse-langchain": { - "version": "3.38.4", - "resolved": "https://registry.npmjs.org/langfuse-langchain/-/langfuse-langchain-3.38.4.tgz", - "integrity": "sha512-7HJqouMrVOP9MFdu33M4G4uBFyQAIh/DqGYALfs41xqm7t99eZxKcTvt4rYZy67iQAhd58TG3q8+9haGzuLbOA==", + "node_modules/langfuse-vercel": { + "version": "3.38.5", + "resolved": "https://registry.npmjs.org/langfuse-vercel/-/langfuse-vercel-3.38.5.tgz", + "integrity": "sha512-Kst5kLVhYppMYIO3zmfrkO9MF/SBI/yDaUDqh6IRRK7YEsS3dO70LiXAwBULt8VD8WsZr7ICoqXG405CoWwtJw==", "license": "MIT", "dependencies": { - "langfuse": "^3.38.4", - "langfuse-core": "^3.38.4" + "langfuse": "^3.38.5", + "langfuse-core": "^3.38.5" }, "engines": { "node": ">=18" }, "peerDependencies": { - "langchain": ">=0.0.157 <0.4.0" - } - }, - "node_modules/langsmith": { - "version": "0.3.33", - "resolved": "https://registry.npmjs.org/langsmith/-/langsmith-0.3.33.tgz", - "integrity": "sha512-imNIaBL6+ElE5eMzNHYwFxo6W/6rHlqcaUjCYoIeGdCYWlARxE3CTGKul5DJnaUgGP2CTLFeNXyvRx5HWC/4KQ==", - "license": "MIT", - "dependencies": { - "@types/uuid": "^10.0.0", - "chalk": "^4.1.2", - "console-table-printer": "^2.12.1", - "p-queue": "^6.6.2", - "p-retry": "4", - "semver": "^7.6.3", - "uuid": "^10.0.0" - }, - "peerDependencies": { - "openai": "*" - }, - "peerDependenciesMeta": { - "openai": { - "optional": true - } - } - }, - "node_modules/langsmith/node_modules/@types/uuid": { - "version": "10.0.0", - "license": "MIT" - }, - "node_modules/langsmith/node_modules/uuid": { - "version": "10.0.0", - "funding": [ - "https://github.com/sponsors/broofa", - "https://github.com/sponsors/ctavan" - ], - "license": "MIT", - "bin": { - "uuid": "dist/bin/uuid" + "ai": ">=3.2.44" } }, "node_modules/lazystream": { @@ -13310,6 +12261,8 @@ }, "node_modules/mime-types": { "version": "3.0.1", + "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-3.0.1.tgz", + "integrity": "sha512-xRc4oEhT6eaBpU1XF7AjpOFD+xQmXNB5OVKwp4tqCuBpHLS/ZbBDrc07mYTDqVMg6PfxUjjNp85O6Cd2Z/5HWA==", "license": "MIT", "dependencies": { "mime-db": "^1.54.0" @@ -13368,6 +12321,12 @@ "integrity": "sha512-gKLcREMhtuZRwRAfqP3RFW+TK4JqApVBtOIftVgjuABpAtpxhPGaDcfvbhNvD0B8iD1oUr/txX35NjcaY6Ns/A==", "dev": true }, + "node_modules/module-details-from-path": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/module-details-from-path/-/module-details-from-path-1.0.4.tgz", + "integrity": "sha512-EGWKgxALGMgzvxYF1UyGTy0HXX/2vHLkw6+NvDKW2jypWbHpjQuj4UMcqQWXHERJhVGKikolT06G3bcKe4fi7w==", + "license": "MIT" + }, "node_modules/ms": { "version": "2.1.3", "license": "MIT" @@ -13447,6 +12406,8 @@ }, "node_modules/mustache": { "version": "4.2.0", + "resolved": "https://registry.npmjs.org/mustache/-/mustache-4.2.0.tgz", + "integrity": "sha512-71ippSywq5Yb7/tVYyGbkBggbU8H3u5Rz56fH60jGFgr8uHwxs+aSKeqmluIVzM0m0kB7xQjKS6qPfd0b2ZoqQ==", "license": "MIT", "bin": { "mustache": "bin/mustache" @@ -13531,42 +12492,12 @@ "rxjs": "*" } }, - "node_modules/netmask": { - "version": "2.0.2", - "dev": true, - "license": "MIT", - "engines": { - "node": ">= 0.4.0" - } - }, - "node_modules/nice-grpc": { - "version": "2.1.12", - "resolved": "https://registry.npmjs.org/nice-grpc/-/nice-grpc-2.1.12.tgz", - "integrity": "sha512-J1n4Wg+D3IhRhGQb+iqh2OpiM0GzTve/kf2lnlW4S+xczmIEd0aHUDV1OsJ5a3q8GSTqJf+s4Rgg1M8uJltarw==", - "license": "MIT", - "dependencies": { - "@grpc/grpc-js": "^1.13.1", - "abort-controller-x": "^0.4.0", - "nice-grpc-common": "^2.0.2" - } - }, - "node_modules/nice-grpc-client-middleware-retry": { - "version": "3.1.11", - "resolved": "https://registry.npmjs.org/nice-grpc-client-middleware-retry/-/nice-grpc-client-middleware-retry-3.1.11.tgz", - "integrity": "sha512-xW/imz/kNG2g0DwTfH2eYEGrg1chSLrXtvGp9fg2qkhTgGFfAS/Pq3+t+9G8KThcC4hK/xlEyKvZWKk++33S6A==", - "license": "MIT", - "dependencies": { - "abort-controller-x": "^0.4.0", - "nice-grpc-common": "^2.0.2" - } - }, - "node_modules/nice-grpc-common": { + "node_modules/netmask": { "version": "2.0.2", - "resolved": "https://registry.npmjs.org/nice-grpc-common/-/nice-grpc-common-2.0.2.tgz", - "integrity": "sha512-7RNWbls5kAL1QVUOXvBsv1uO0wPQK3lHv+cY1gwkTzirnG1Nop4cBJZubpgziNbaVc/bl9QJcyvsf/NQxa3rjQ==", + "dev": true, "license": "MIT", - "dependencies": { - "ts-error": "^1.0.6" + "engines": { + "node": ">= 0.4.0" } }, "node_modules/node-abort-controller": { @@ -13581,23 +12512,6 @@ "node": "^18 || ^20 || >= 21" } }, - "node_modules/node-domexception": { - "version": "1.0.0", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/jimmywarting" - }, - { - "type": "github", - "url": "https://paypal.me/jimmywarting" - } - ], - "license": "MIT", - "engines": { - "node": ">=10.5.0" - } - }, "node_modules/node-emoji": { "version": "1.11.0", "dev": true, @@ -13786,11 +12700,20 @@ "url": "https://github.com/sponsors/ljharb" } }, - "node_modules/ollama": { - "version": "0.5.15", - "license": "MIT", + "node_modules/ollama-ai-provider-v2": { + "version": "1.3.1", + "resolved": "https://registry.npmjs.org/ollama-ai-provider-v2/-/ollama-ai-provider-v2-1.3.1.tgz", + "integrity": "sha512-UfDX40h2uz/mHjvjFapQIrPzb7h+QQuq0j8OxYLWXMz6Z5CCydmI5l4oLQtZm/lZijisF3zaG1EkIPNzOVDMcw==", + "license": "Apache-2.0", "dependencies": { - "whatwg-fetch": "^3.6.20" + "@ai-sdk/provider": "^2.0.0", + "@ai-sdk/provider-utils": "^3.0.7" + }, + "engines": { + "node": ">=18" + }, + "peerDependencies": { + "zod": "^4.0.16" } }, "node_modules/on-finished": { @@ -13859,9 +12782,9 @@ } }, "node_modules/openai": { - "version": "5.8.3", - "resolved": "https://registry.npmjs.org/openai/-/openai-5.8.3.tgz", - "integrity": "sha512-IdotKmquCnpouTRvF9xRXVhMx6K5Sc8zkD6Usf+so+NTQ+qiJ8bLSCd7LBb8b/Rof7uYltlSxJhNp+spphKI4Q==", + "version": "5.12.2", + "resolved": "https://registry.npmjs.org/openai/-/openai-5.12.2.tgz", + "integrity": "sha512-xqzHHQch5Tws5PcKR2xsZGX9xtch+JQFz5zb14dGqlshmmDAFBFEWmeIpf7wVqWV+w7Emj7jRgkNJakyKE0tYQ==", "license": "Apache-2.0", "bin": { "openai": "bin/cli" @@ -13879,10 +12802,6 @@ } } }, - "node_modules/openapi-types": { - "version": "12.1.3", - "license": "MIT" - }, "node_modules/optionator": { "version": "0.9.4", "dev": true, @@ -13945,13 +12864,6 @@ "url": "https://github.com/sponsors/ljharb" } }, - "node_modules/p-finally": { - "version": "1.0.0", - "license": "MIT", - "engines": { - "node": ">=4" - } - }, "node_modules/p-limit": { "version": "3.1.0", "dev": true, @@ -13980,41 +12892,6 @@ "url": "https://github.com/sponsors/sindresorhus" } }, - "node_modules/p-queue": { - "version": "6.6.2", - "license": "MIT", - "dependencies": { - "eventemitter3": "^4.0.4", - "p-timeout": "^3.2.0" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/p-retry": { - "version": "4.6.2", - "license": "MIT", - "dependencies": { - "@types/retry": "0.12.0", - "retry": "^0.13.1" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/p-timeout": { - "version": "3.2.0", - "license": "MIT", - "dependencies": { - "p-finally": "^1.0.0" - }, - "engines": { - "node": ">=8" - } - }, "node_modules/p-try": { "version": "2.2.0", "dev": true, @@ -14193,7 +13070,6 @@ }, "node_modules/path-parse": { "version": "1.0.7", - "dev": true, "license": "MIT" }, "node_modules/path-scurry": { @@ -14235,8 +13111,7 @@ } }, "node_modules/pause": { - "version": "0.0.1", - "peer": true + "version": "0.0.1" }, "node_modules/peek-readable": { "version": "7.0.0", @@ -14253,6 +13128,7 @@ "version": "8.16.3", "resolved": "https://registry.npmjs.org/pg/-/pg-8.16.3.tgz", "integrity": "sha512-enxc1h0jA/aq5oSDMvqyW3q89ra6XIIDZgCX9vkMrnz5DFTw/Ny3Li2lFQ+pt3L6MCgm/5o2o8HW9hiJji+xvw==", + "peer": true, "dependencies": { "pg-connection-string": "^2.9.1", "pg-pool": "^3.10.1", @@ -14421,45 +13297,16 @@ "node": ">=8" } }, - "node_modules/playwright": { - "version": "1.52.0", - "license": "Apache-2.0", - "peer": true, - "dependencies": { - "playwright-core": "1.52.0" - }, - "bin": { - "playwright": "cli.js" - }, - "engines": { - "node": ">=18" - }, - "optionalDependencies": { - "fsevents": "2.3.2" - } - }, - "node_modules/playwright-core": { - "version": "1.52.0", - "license": "Apache-2.0", - "peer": true, - "bin": { - "playwright-core": "cli.js" - }, - "engines": { - "node": ">=18" - } - }, "node_modules/playwright/node_modules/fsevents": { "version": "2.3.2", "resolved": "https://registry.npmjs.org/fsevents/-/fsevents-2.3.2.tgz", "integrity": "sha512-xiqMQR4xAeHTuB9uWm+fFRcIOgKBMiOBP+eXiyT7jsgVCq1bkVygt00oASowB7EdtpOHaaPgKt812P9ab+DDKA==", + "extraneous": true, "hasInstallScript": true, "license": "MIT", - "optional": true, "os": [ "darwin" ], - "peer": true, "engines": { "node": "^8.16.0 || ^10.6.0 || >=11.0.0" } @@ -14531,6 +13378,7 @@ "resolved": "https://registry.npmjs.org/prettier/-/prettier-3.6.2.tgz", "integrity": "sha512-I7AIg5boAr5R0FFtJ6rCfD+LFsWHp81dolrFD8S79U9tb8Az2nGrJncnMSnys+bpQJfRUzqs9hnA81OAA3hCuQ==", "dev": true, + "peer": true, "bin": { "prettier": "bin/prettier.cjs" }, @@ -14567,6 +13415,7 @@ }, "node_modules/process": { "version": "0.11.10", + "dev": true, "license": "MIT", "engines": { "node": ">= 0.6.0" @@ -14580,6 +13429,7 @@ "node_modules/prom-client": { "version": "15.1.3", "license": "Apache-2.0", + "peer": true, "dependencies": { "@opentelemetry/api": "^1.4.0", "tdigest": "^0.1.1" @@ -14699,19 +13549,9 @@ }, "node_modules/proxy-from-env": { "version": "1.1.0", + "devOptional": true, "license": "MIT" }, - "node_modules/psl": { - "version": "1.15.0", - "license": "MIT", - "peer": true, - "dependencies": { - "punycode": "^2.3.1" - }, - "funding": { - "url": "https://github.com/sponsors/lupomontero" - } - }, "node_modules/pump": { "version": "3.0.2", "dev": true, @@ -14756,11 +13596,6 @@ "url": "https://github.com/sponsors/ljharb" } }, - "node_modules/querystringify": { - "version": "2.2.0", - "license": "MIT", - "peer": true - }, "node_modules/queue-microtask": { "version": "1.2.3", "resolved": "https://registry.npmjs.org/queue-microtask/-/queue-microtask-1.2.3.tgz", @@ -14841,44 +13676,6 @@ "dev": true, "license": "MIT" }, - "node_modules/readable-web-to-node-stream": { - "version": "3.0.4", - "license": "MIT", - "peer": true, - "dependencies": { - "readable-stream": "^4.7.0" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "type": "github", - "url": "https://github.com/sponsors/Borewit" - } - }, - "node_modules/readable-web-to-node-stream/node_modules/readable-stream": { - "version": "4.7.0", - "license": "MIT", - "peer": true, - "dependencies": { - "abort-controller": "^3.0.0", - "buffer": "^6.0.3", - "events": "^3.3.0", - "process": "^0.11.10", - "string_decoder": "^1.3.0" - }, - "engines": { - "node": "^12.22.0 || ^14.17.0 || >=16.0.0" - } - }, - "node_modules/readable-web-to-node-stream/node_modules/string_decoder": { - "version": "1.3.0", - "license": "MIT", - "peer": true, - "dependencies": { - "safe-buffer": "~5.2.0" - } - }, "node_modules/readdir-glob": { "version": "1.1.3", "dev": true, @@ -14888,7 +13685,9 @@ } }, "node_modules/readdir-glob/node_modules/brace-expansion": { - "version": "2.0.1", + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-2.0.2.tgz", + "integrity": "sha512-Jt0vHyM+jmUBqojB7E1NIYadt0vI0Qxjxd2TErW94wDz+E2LAm5vKMXXwg6ZZBTHPuUlDgQHKXvjGBdfcF1ZDQ==", "dev": true, "license": "MIT", "dependencies": { @@ -14928,7 +13727,8 @@ }, "node_modules/reflect-metadata": { "version": "0.2.2", - "license": "Apache-2.0" + "license": "Apache-2.0", + "peer": true }, "node_modules/reflect.getprototypeof": { "version": "1.0.10", @@ -14993,14 +13793,22 @@ "node": ">=0.10.0" } }, - "node_modules/requires-port": { - "version": "1.0.0", + "node_modules/require-in-the-middle": { + "version": "7.5.2", + "resolved": "https://registry.npmjs.org/require-in-the-middle/-/require-in-the-middle-7.5.2.tgz", + "integrity": "sha512-gAZ+kLqBdHarXB64XpAe2VCjB7rIRv+mU8tfRWziHRJ5umKsIHN2tLLv6EtMw7WCdP19S0ERVMldNvxYCHnhSQ==", "license": "MIT", - "peer": true + "dependencies": { + "debug": "^4.3.5", + "module-details-from-path": "^1.0.3", + "resolve": "^1.22.8" + }, + "engines": { + "node": ">=8.6.0" + } }, "node_modules/resolve": { "version": "1.22.10", - "dev": true, "license": "MIT", "dependencies": { "is-core-module": "^2.16.0", @@ -15069,24 +13877,6 @@ "dev": true, "license": "ISC" }, - "node_modules/retry": { - "version": "0.13.1", - "license": "MIT", - "engines": { - "node": ">= 4" - } - }, - "node_modules/retry-axios": { - "version": "2.6.0", - "license": "Apache-2.0", - "peer": true, - "engines": { - "node": ">=10.7.0" - }, - "peerDependencies": { - "axios": "*" - } - }, "node_modules/reusify": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/reusify/-/reusify-1.1.0.tgz", @@ -15177,6 +13967,7 @@ "node_modules/rxjs": { "version": "7.8.2", "license": "Apache-2.0", + "peer": true, "dependencies": { "tslib": "^2.1.0" } @@ -15511,10 +14302,6 @@ "version": "0.3.2", "license": "MIT" }, - "node_modules/simple-wcswidth": { - "version": "1.0.1", - "license": "MIT" - }, "node_modules/sisteransi": { "version": "1.0.5", "dev": true, @@ -15877,16 +14664,6 @@ "url": "https://github.com/sponsors/sindresorhus" } }, - "node_modules/strnum": { - "version": "1.1.2", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/NaturalIntelligence" - } - ], - "license": "MIT" - }, "node_modules/strtok3": { "version": "10.2.2", "license": "MIT", @@ -15948,7 +14725,6 @@ }, "node_modules/supports-preserve-symlinks-flag": { "version": "1.0.0", - "dev": true, "license": "MIT", "engines": { "node": ">= 0.4" @@ -15997,9 +14773,9 @@ } }, "node_modules/tar-fs": { - "version": "3.0.10", - "resolved": "https://registry.npmjs.org/tar-fs/-/tar-fs-3.0.10.tgz", - "integrity": "sha512-C1SwlQGNLe/jPNqapK8epDsXME7CAJR5RL3GcE6KWx1d9OUByzoHVcbu1VPI8tevg9H8Alae0AApHHFGzrD5zA==", + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/tar-fs/-/tar-fs-3.1.1.tgz", + "integrity": "sha512-LZA0oaPOc2fVo82Txf3gw+AkEd38szODlptMYejQUhndHMLQ9M059uXR+AfS7DNo0NpINvSqDsvyaCrBVkptWg==", "dev": true, "license": "MIT", "dependencies": { @@ -16082,6 +14858,7 @@ "version": "8.17.1", "dev": true, "license": "MIT", + "peer": true, "dependencies": { "fast-deep-equal": "^3.1.3", "fast-uri": "^3.0.1", @@ -16325,28 +15102,6 @@ "url": "https://github.com/sponsors/Borewit" } }, - "node_modules/tough-cookie": { - "version": "4.1.4", - "license": "BSD-3-Clause", - "peer": true, - "dependencies": { - "psl": "^1.1.33", - "punycode": "^2.1.1", - "universalify": "^0.2.0", - "url-parse": "^1.5.3" - }, - "engines": { - "node": ">=6" - } - }, - "node_modules/tough-cookie/node_modules/universalify": { - "version": "0.2.0", - "license": "MIT", - "peer": true, - "engines": { - "node": ">= 4.0.0" - } - }, "node_modules/tr46": { "version": "0.0.3", "license": "MIT" @@ -16377,12 +15132,6 @@ "typescript": ">=4.8.4" } }, - "node_modules/ts-error": { - "version": "1.0.6", - "resolved": "https://registry.npmjs.org/ts-error/-/ts-error-1.0.6.tgz", - "integrity": "sha512-tLJxacIQUM82IR7JO1UUkKlYuUTmoY9HBJAmNWFzheSlDS5SPMcNIepejHJa4BpPQLAcbRhRf3GDJzyj6rbKvA==", - "license": "MIT" - }, "node_modules/ts-jest": { "version": "29.4.0", "resolved": "https://registry.npmjs.org/ts-jest/-/ts-jest-29.4.0.tgz", @@ -16469,6 +15218,7 @@ "version": "10.9.2", "devOptional": true, "license": "MIT", + "peer": true, "dependencies": { "@cspotcode/source-map-support": "^0.8.0", "@tsconfig/node10": "^1.0.7", @@ -16672,6 +15422,7 @@ "version": "0.3.25", "resolved": "https://registry.npmjs.org/typeorm/-/typeorm-0.3.25.tgz", "integrity": "sha512-fTKDFzWXKwAaBdEMU4k661seZewbNYET4r1J/z3Jwf+eAvlzMVpTLKAVcAzg75WwQk7GDmtsmkZ5MfkmXCiFWg==", + "peer": true, "dependencies": { "@sqltools/formatter": "^1.2.5", "ansis": "^3.17.0", @@ -16787,7 +15538,9 @@ } }, "node_modules/typeorm/node_modules/brace-expansion": { - "version": "2.0.1", + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-2.0.2.tgz", + "integrity": "sha512-Jt0vHyM+jmUBqojB7E1NIYadt0vI0Qxjxd2TErW94wDz+E2LAm5vKMXXwg6ZZBTHPuUlDgQHKXvjGBdfcF1ZDQ==", "license": "MIT", "dependencies": { "balanced-match": "^1.0.0" @@ -16927,6 +15680,7 @@ "version": "5.8.3", "devOptional": true, "license": "Apache-2.0", + "peer": true, "bin": { "tsc": "bin/tsc", "tsserver": "bin/tsserver" @@ -17051,15 +15805,6 @@ "punycode": "^2.1.0" } }, - "node_modules/url-parse": { - "version": "1.5.10", - "license": "MIT", - "peer": true, - "dependencies": { - "querystringify": "^2.1.1", - "requires-port": "^1.0.0" - } - }, "node_modules/util-deprecate": { "version": "1.0.2", "license": "MIT" @@ -17073,6 +15818,8 @@ }, "node_modules/uuid": { "version": "9.0.1", + "resolved": "https://registry.npmjs.org/uuid/-/uuid-9.0.1.tgz", + "integrity": "sha512-b+1eJOlsR9K8HJpow9Ok3fiWOWSIcIzXodvv0rQjVoOVNpWMpxf1wZNpt4y9h10odCNrqnYp1OBzRktckBe3sA==", "funding": [ "https://github.com/sponsors/broofa", "https://github.com/sponsors/ctavan" @@ -17142,33 +15889,6 @@ "defaults": "^1.0.3" } }, - "node_modules/weaviate-client": { - "version": "3.5.5", - "resolved": "https://registry.npmjs.org/weaviate-client/-/weaviate-client-3.5.5.tgz", - "integrity": "sha512-wAjJtJmBQn2KiTPkfUGEzddBIbySpN0y0wAcYPWDCBXVjXqf0UOExujFJ+QeeRp+AjHk15B6BmUaUX9NHVLzsw==", - "license": "SEE LICENSE IN LICENSE", - "dependencies": { - "abort-controller-x": "^0.4.3", - "graphql": "^16.10.0", - "graphql-request": "^6.1.0", - "long": "^5.2.4", - "nice-grpc": "^2.1.11", - "nice-grpc-client-middleware-retry": "^3.1.10", - "nice-grpc-common": "^2.0.2", - "uuid": "^9.0.1" - }, - "engines": { - "node": ">=18.0.0" - } - }, - "node_modules/web-streams-polyfill": { - "version": "4.0.0-beta.3", - "license": "MIT", - "peer": true, - "engines": { - "node": ">= 14" - } - }, "node_modules/webidl-conversions": { "version": "3.0.1", "license": "BSD-2-Clause" @@ -17256,7 +15976,6 @@ "version": "2.1.1", "dev": true, "license": "MIT", - "peer": true, "dependencies": { "ajv": "^8.0.0" }, @@ -17273,7 +15992,6 @@ "version": "5.1.0", "dev": true, "license": "MIT", - "peer": true, "dependencies": { "fast-deep-equal": "^3.1.3" }, @@ -17285,7 +16003,6 @@ "version": "5.1.1", "dev": true, "license": "BSD-2-Clause", - "peer": true, "dependencies": { "esrecurse": "^4.3.0", "estraverse": "^4.1.1" @@ -17298,7 +16015,6 @@ "version": "4.3.0", "dev": true, "license": "BSD-2-Clause", - "peer": true, "engines": { "node": ">=4.0" } @@ -17306,14 +16022,12 @@ "node_modules/webpack/node_modules/json-schema-traverse": { "version": "1.0.0", "dev": true, - "license": "MIT", - "peer": true + "license": "MIT" }, "node_modules/webpack/node_modules/mime-db": { "version": "1.52.0", "dev": true, "license": "MIT", - "peer": true, "engines": { "node": ">= 0.6" } @@ -17322,7 +16036,6 @@ "version": "2.1.35", "dev": true, "license": "MIT", - "peer": true, "dependencies": { "mime-db": "1.52.0" }, @@ -17334,7 +16047,6 @@ "version": "4.3.2", "dev": true, "license": "MIT", - "peer": true, "dependencies": { "@types/json-schema": "^7.0.9", "ajv": "^8.9.0", @@ -17349,10 +16061,6 @@ "url": "https://opencollective.com/webpack" } }, - "node_modules/whatwg-fetch": { - "version": "3.6.20", - "license": "MIT" - }, "node_modules/whatwg-url": { "version": "5.0.0", "license": "MIT", @@ -17472,6 +16180,7 @@ "node_modules/winston": { "version": "3.17.0", "license": "MIT", + "peer": true, "dependencies": { "@colors/colors": "^1.6.0", "@dabh/diagnostics": "^2.0.2", @@ -17647,26 +16356,6 @@ "dev": true, "license": "ISC" }, - "node_modules/ws": { - "version": "8.18.2", - "license": "MIT", - "peer": true, - "engines": { - "node": ">=10.0.0" - }, - "peerDependencies": { - "bufferutil": "^4.0.1", - "utf-8-validate": ">=5.0.2" - }, - "peerDependenciesMeta": { - "bufferutil": { - "optional": true - }, - "utf-8-validate": { - "optional": true - } - } - }, "node_modules/wsl-utils": { "version": "0.1.0", "resolved": "https://registry.npmjs.org/wsl-utils/-/wsl-utils-0.1.0.tgz", @@ -17708,6 +16397,7 @@ }, "node_modules/yaml": { "version": "2.7.1", + "dev": true, "license": "ISC", "bin": { "yaml": "bin.mjs" @@ -17819,6 +16509,7 @@ "resolved": "https://registry.npmjs.org/zod/-/zod-3.25.51.tgz", "integrity": "sha512-TQSnBldh+XSGL+opiSIq0575wvDPqu09AqWe1F7JhUMKY+M91/aGlK4MhpVNO7MgYfHcVCB1ffwAUTJzllKJqg==", "license": "MIT", + "peer": true, "funding": { "url": "https://github.com/sponsors/colinhacks" } diff --git a/backend/package.json b/backend/package.json index 66bdfbfb6..1d7bae08e 100644 --- a/backend/package.json +++ b/backend/package.json @@ -16,12 +16,9 @@ "start:prod": "node dist/main", "lint": "eslint \"{src,apps,libs,test}/**/*.ts\"", "lint:fix": "eslint \"{src,apps,libs,test}/**/*.ts\" --fix", - "test": "jest --forceExit", - "test:ci:unit": "jest --coverage --selectProjects='Unit Tests'", - "test:ci:e2e": "jest --coverage --selectProjects='E2E Tests' --forceExit", - "test:watch": "jest --watch", - "test:cov": "jest --coverage --forceExit", - "test:debug": "node --inspect-brk -r tsconfig-paths/register -r ts-node/register node_modules/.bin/jest --runInBand", + "test": "NODE_OPTIONS=\"$NODE_OPTIONS --experimental-vm-modules\" jest --runInBand --forceExit", + "test:cov": "NODE_OPTIONS=\"$NODE_OPTIONS --experimental-vm-modules\" jest --runInBand --coverage --forceExit", + "test:debug": "node --experimental-vm-modules --inspect-brk -r tsconfig-paths/register -r ts-node/register node_modules/.bin/jest --runInBand", "generate-openapi-dev": "npm run build && node dist/openapi.js -- localFile && npx prettier --write backend-dev-spec.json", "generate-base": "npx @openapitools/openapi-generator-cli generate -g typescript-fetch --additional-properties=useSingleRequestParameter=false,ensureUniqueParams=false", "generate-tools": "npx rimraf ./src/extensions/tools/generated && npm run generate-base -- -i ./src/openapi/tools-spec.json -o ./src/extensions/tools/generated", @@ -38,17 +35,16 @@ "migration:revert": "npm run typeorm -- -d src/config/typeorm-migration.config.ts migration:revert" }, "dependencies": { + "@ai-sdk/amazon-bedrock": "^3.0.22", + "@ai-sdk/azure": "^2.0.30", + "@ai-sdk/google": "^2.0.14", + "@ai-sdk/google-vertex": "^3.0.27", + "@ai-sdk/mistral": "^2.0.14", + "@ai-sdk/openai": "^2.0.30", + "@ai-sdk/openai-compatible": "^1.0.17", "@azure/ai-agents": "^1.1.0", "@azure/core-util": "^1.13.0", "@azure/identity": "^4.11.0", - "@langchain/aws": "0.1.11", - "@langchain/community": "^0.3.48", - "@langchain/core": "^0.3.62", - "@langchain/google-genai": "^0.2.14", - "@langchain/google-vertexai": "^0.2.14", - "@langchain/mistralai": "^0.2.1", - "@langchain/ollama": "^0.2.3", - "@langchain/openai": "^0.5.18", "@modelcontextprotocol/sdk": "^1.17.0", "@n8n/json-schema-to-zod": "^1.1.0", "@nestjs/common": "^11.1.3", @@ -60,7 +56,11 @@ "@nestjs/swagger": "^11.1.6", "@nestjs/terminus": "^11.0.0", "@nestjs/typeorm": "^11.0.0", + "@opentelemetry/auto-instrumentations-node": "^0.64.1", + "@opentelemetry/sdk-node": "^0.205.0", + "@types/mime-types": "^3.0.1", "@willsoto/nestjs-prometheus": "^6.0.2", + "ai": "^5.0.44", "bcrypt": "^6.0.0", "class-transformer": "^0.5.1", "class-validator": "^0.14.1", @@ -68,15 +68,17 @@ "date-fns": "^4.1.0", "dotenv": "^16.6.1", "duck-duck-scrape": "^2.2.7", + "expr-eval": "^2.0.2", "express-session": "^1.18.2", "json-diff-ts": "^4.6.3", - "langchain": "^0.3.29", - "langfuse-langchain": "^3.38.4", + "langfuse-vercel": "^3.38.5", "logform": "^2.7.0", + "mime-types": "^3.0.1", "nest-winston": "^1.10.2", "nestjs-i18n": "^10.5.1", "nunjucks": "^3.2.4", - "openai": "^5.8.3", + "ollama-ai-provider-v2": "^1.3.1", + "openai": "5.12.2", "passport-custom": "^1.1.1", "passport-github2": "^0.1.12", "passport-google-oauth2": "^0.2.0", @@ -88,6 +90,7 @@ "rxjs": "^7.8.2", "typeorm": "^0.3.25", "undici": "^7.11.0", + "uuid": "^9.0.1", "winston": "^3.17.0", "zod": "3.25.51" }, @@ -102,6 +105,7 @@ "@testcontainers/postgresql": "^11.0.3", "@types/bcrypt": "5.0.2", "@types/cookie-parser": "1.4.9", + "@types/expr-eval": "^1.0.2", "@types/express": "5.0.3", "@types/express-session": "1.18.2", "@types/jest": "29.5.14", @@ -113,10 +117,11 @@ "@types/passport-microsoft": "2.1.0", "@types/pg": "8.15.4", "@types/supertest": "6.0.3", - "@typescript-eslint/eslint-plugin": "8.33.1", - "@typescript-eslint/parser": "8.35.1", - "eslint": "9.32.0", - "eslint-config-prettier": "10.1.5", + "@types/uuid": "^10.0.0", + "@typescript-eslint/eslint-plugin": "8.46.0", + "@typescript-eslint/parser": "8.46.0", + "eslint": "9.37.0", + "eslint-config-prettier": "10.1.8", "eslint-plugin-import": "2.32.0", "eslint-plugin-prettier": "5.5.1", "globals": "16.3.0", @@ -134,8 +139,6 @@ "typescript": "5.8.3" }, "overrides": { - "@browserbasehq/stagehand@1.14.0": { - "openai": "^5.8.2" - } + "zod": "3.25.51" } } diff --git a/backend/src/app.module.ts b/backend/src/app.module.ts index 61b8379da..3160ea59c 100644 --- a/backend/src/app.module.ts +++ b/backend/src/app.module.ts @@ -14,6 +14,8 @@ import { ExtensionsController } from './controllers/extensions/extensions.contro import { FilesController } from './controllers/files/files.controller'; import { UserFilesController } from './controllers/files/user-files.controller'; import { HealthController } from './controllers/health/health.controller'; +import { PromptController } from './controllers/prompts/prompts.controller'; +import { ApiResponsesController } from './controllers/responses/api.responses.controller'; import { SettingsController } from './controllers/settings/settings.controller'; import { UsagesController } from './controllers/usages/usages.controller'; import { UserGroupsController } from './controllers/users/user-groups.controller'; @@ -24,10 +26,12 @@ import { UserEntity } from './domain/database'; import { initSchemaIfNotExistsAndMoveMigrations, schema } from './domain/database/typeorm.helper'; import { ExtensionModule } from './domain/extensions'; import { FilesModule } from './domain/files'; +import { PromptModule } from './domain/prompt/module'; import { SettingsModule } from './domain/settings'; import { UsersModule } from './domain/users/module'; import { ExtensionLibraryModule } from './extensions'; import { I18nModule } from './localization/i18n.module'; +import { OpenTelemetryModule } from './metrics/opentelemetry.module'; import { PrometheusModule } from './metrics/prometheus.module'; @Module({ @@ -47,6 +51,8 @@ import { PrometheusModule } from './metrics/prometheus.module'; }, }), PrometheusModule.forRoot(), + PromptModule, + OpenTelemetryModule, SettingsModule, UsersModule, TerminusModule, @@ -78,10 +84,12 @@ import { PrometheusModule } from './metrics/prometheus.module'; AuthController, BlobsController, HealthController, + ApiResponsesController, ConversationsController, ConfigurationsController, ExtensionsController, FilesController, + PromptController, SettingsController, UsagesController, UserFilesController, diff --git a/backend/src/controllers/conversations/conversations.controller.ts b/backend/src/controllers/conversations/conversations.controller.ts index aef0d054d..ac9d07ebd 100644 --- a/backend/src/controllers/conversations/conversations.controller.ts +++ b/backend/src/controllers/conversations/conversations.controller.ts @@ -25,7 +25,6 @@ import { ApiTags, } from '@nestjs/swagger'; import { Request, Response } from 'express'; -import { Observable } from 'rxjs'; import { LocalAuthGuard } from 'src/domain/auth'; import { CallbackService, @@ -46,7 +45,6 @@ import { SendMessageResponse, StartConversation, StartConversationResponse, - StreamEvent, UpdateConversation, UpdateConversationResponse, } from 'src/domain/chat'; @@ -244,11 +242,7 @@ export class ConversationsController { response.send(bytes); } - private async streamResponse( - @Req() req: Request, - @Res() response: Response, - getStream: () => Promise>, - ) { + private async streamResponse(@Req() req: Request, @Res() response: Response, getStream: () => Promise) { response.set({ 'Cache-Control': 'private, no-cache, no-store, must-revalidate, max-age=0, no-transform', Connection: 'keep-alive', @@ -266,7 +260,7 @@ export class ConversationsController { }; try { - const stream = await getStream(); + const { stream, abort } = await getStream(); const subscription = stream.subscribe({ next: (event) => sendEvent('message', event), error: (err: Error) => sendEvent('error', err), @@ -276,6 +270,7 @@ export class ConversationsController { req.on('close', () => { subscription.unsubscribe(); response.end(); + abort.abort('cancelled'); }); } catch (err) { this.logger.error('Error during message processing', err); @@ -308,12 +303,9 @@ export class ConversationsController { @Param('messageId', ParseIntPipe) messageId: number, @Body() dto: SendMessageDto, ) { - return this.streamResponse(req, response, async () => { - const { stream }: SendMessageResponse = await this.queryBus.execute( - new SendMessage(id, req.user, dto.query, dto.files, messageId), - ); - return stream; - }); + return this.streamResponse(req, response, () => + this.queryBus.execute(new SendMessage(id, req.user, dto.query, dto.files, messageId)), + ); } @Post(':id/messages/sse') @@ -330,10 +322,7 @@ export class ConversationsController { @Param('id', ParseIntPipe) id: number, @Body() dto: SendMessageDto, ) { - return this.streamResponse(req, response, async () => { - const { stream }: SendMessageResponse = await this.queryBus.execute(new SendMessage(id, req.user, dto.query, dto.files)); - return stream; - }); + return this.streamResponse(req, response, () => this.queryBus.execute(new SendMessage(id, req.user, dto.query, dto.files))); } @Patch(':id/messages/:messageId') diff --git a/backend/src/controllers/conversations/conversations.e2e.spec.ts b/backend/src/controllers/conversations/conversations.e2e.spec.ts index 2abd4ecaf..d51835f9e 100644 --- a/backend/src/controllers/conversations/conversations.e2e.spec.ts +++ b/backend/src/controllers/conversations/conversations.e2e.spec.ts @@ -7,12 +7,14 @@ import { AppModule } from '../../app.module'; import { BucketEntity, ConfigurationEntity, + ConfigurationStatus, ConversationEntity, FileEntity, FileUploadStatus, MessageEntity, UserEntity, } from '../../domain/database'; +import { ConversationFileEntity } from '../../domain/database/entities/conversation-file'; import { schema } from '../../domain/database/typeorm.helper'; import { buildClient } from '../../domain/files/use-cases/utils'; import { initAppWithDataBaseAndValidUser } from '../../utils/testUtils'; @@ -99,6 +101,7 @@ async function seedTestData(dataSource: DataSource) { const conversationRepository = dataSource.getRepository(ConversationEntity); const messageRepository = dataSource.getRepository(MessageEntity); const fileRepository = dataSource.getRepository(FileEntity); + const conversationFileRepository = dataSource.getRepository(ConversationFileEntity); const bucketRepository = dataSource.getRepository(BucketEntity); const userEntity = await createUser(userRepository); @@ -106,7 +109,8 @@ async function seedTestData(dataSource: DataSource) { const conversation = await createConversationEntity(conversationRepository, configurationEntity, userEntity); const bucketEntity = await createBucket(bucketRepository); - await createFiles(fileRepository, conversation.id, bucketEntity); + const file = await createFiles(fileRepository, conversation.id, bucketEntity); + await createConversationFiles(conversationFileRepository, conversation.id, file.id); await createMessages(messageRepository, conversation.id, configurationEntity.id); return conversation; @@ -115,7 +119,7 @@ async function seedTestData(dataSource: DataSource) { function createConfiguration(configurationRepository: Repository): Promise { const configurationEntity = new ConfigurationEntity(); configurationEntity.name = 'Test Configuration'; - configurationEntity.enabled = true; + configurationEntity.status = ConfigurationStatus.ENABLED; return configurationRepository.save(configurationEntity); } @@ -173,7 +177,6 @@ function createFiles( bucketEntity: BucketEntity, ): Promise { const fileEntity = new FileEntity(); - fileEntity.conversationId = conversationId; fileEntity.mimeType = 'application/pdf'; fileEntity.fileName = 'test.pdf'; fileEntity.fileSize = 1024; @@ -183,6 +186,18 @@ function createFiles( return fileRepository.save(fileEntity); } +function createConversationFiles( + conversationFileRepository: Repository, + conversationId: number, + fileId: number, +): Promise { + const conversationFileEntity = new ConversationFileEntity(); + conversationFileEntity.conversationId = conversationId; + conversationFileEntity.fileId = fileId; + + return conversationFileRepository.save(conversationFileEntity); +} + function createBucket(bucketRepository: Repository): Promise { const bucketEntity = new BucketEntity(); bucketEntity.id = 1; diff --git a/backend/src/controllers/conversations/dtos/index.ts b/backend/src/controllers/conversations/dtos/index.ts index d3c2b2134..e182b12f6 100644 --- a/backend/src/controllers/conversations/dtos/index.ts +++ b/backend/src/controllers/conversations/dtos/index.ts @@ -460,6 +460,30 @@ export class StreamMessageSavedDto { type!: typeof StreamMessageSavedDto.TYPE_NAME; } +export class StreamReasoningDto { + static TYPE_NAME = 'reasoning'; + + @ApiProperty({ + description: 'The content .', + required: true, + }) + content!: string; + + @ApiProperty({ + enum: [StreamReasoningDto.TYPE_NAME], + }) + type!: typeof StreamReasoningDto.TYPE_NAME; +} + +export class StreamReasoningEndDto { + static TYPE_NAME = 'reasoning_end'; + + @ApiProperty({ + enum: [StreamReasoningEndDto.TYPE_NAME], + }) + type!: typeof StreamReasoningEndDto.TYPE_NAME; +} + export class StreamSummaryDto { static TYPE_NAME = 'summary'; @@ -566,6 +590,8 @@ export class StreamCompletedEventDto { StreamToolStartEventDto, StreamUIEventDto, StreamSummaryDto, + StreamReasoningDto, + StreamReasoningEndDto, ) export class StreamEventHolderDto { @ApiProperty({ @@ -582,6 +608,8 @@ export class StreamEventHolderDto { { $ref: getSchemaPath(StreamToolEndEventDto) }, { $ref: getSchemaPath(StreamToolStartEventDto) }, { $ref: getSchemaPath(StreamUIEventDto) }, + { $ref: getSchemaPath(StreamReasoningDto) }, + { $ref: getSchemaPath(StreamReasoningEndDto) }, ], discriminator: { propertyName: 'type', @@ -597,6 +625,8 @@ export class StreamEventHolderDto { [StreamToolEndEventDto.TYPE_NAME]: getSchemaPath(StreamToolEndEventDto), [StreamToolStartEventDto.TYPE_NAME]: getSchemaPath(StreamToolStartEventDto), [StreamUIEventDto.TYPE_NAME]: getSchemaPath(StreamUIEventDto), + [StreamReasoningDto.TYPE_NAME]: getSchemaPath(StreamReasoningDto), + [StreamReasoningEndDto.TYPE_NAME]: getSchemaPath(StreamReasoningEndDto), }, }, }) diff --git a/backend/src/controllers/files/files.controller.ts b/backend/src/controllers/files/files.controller.ts index 48ef2df4d..03d6602c6 100644 --- a/backend/src/controllers/files/files.controller.ts +++ b/backend/src/controllers/files/files.controller.ts @@ -227,7 +227,7 @@ export class FilesController { fileName: file.originalname, fileSize: file.size, bucketId: bucketId, - createEmbeddings: true, + embedType: 'vector', }); await keepAlive(res, async () => { @@ -267,7 +267,7 @@ export class FilesController { fileName: file.originalname, fileSize: file.size, bucketId: bucketId, - createEmbeddings: true, + embedType: 'vector', }); await keepAlive(res, async () => { diff --git a/backend/src/controllers/files/files.e2e.spec.ts b/backend/src/controllers/files/files.e2e.spec.ts index badf53d6d..8c55c2465 100644 --- a/backend/src/controllers/files/files.e2e.spec.ts +++ b/backend/src/controllers/files/files.e2e.spec.ts @@ -4,7 +4,7 @@ import { Test, TestingModule } from '@nestjs/testing'; import * as request from 'supertest'; import { DataSource, Repository } from 'typeorm'; import { AppModule } from '../../app.module'; -import { ConfigurationEntity, ConversationEntity, MessageEntity, UserEntity } from '../../domain/database'; +import { ConfigurationEntity, ConfigurationStatus, ConversationEntity, MessageEntity, UserEntity } from '../../domain/database'; import { initAppWithDataBaseAndValidUser } from '../../utils/testUtils'; jest.mock('../../domain/files/use-cases/generated/apis', () => { @@ -248,7 +248,7 @@ function createConfigurationEntity(repository: Repository): const entity = new ConfigurationEntity(); entity.id = 1; entity.name = 'test'; - entity.enabled = true; + entity.status = ConfigurationStatus.ENABLED; return repository.save(entity); } diff --git a/backend/src/controllers/files/user-files.controller.ts b/backend/src/controllers/files/user-files.controller.ts index 24b413f48..8e94cfefa 100644 --- a/backend/src/controllers/files/user-files.controller.ts +++ b/backend/src/controllers/files/user-files.controller.ts @@ -127,7 +127,9 @@ export class UserFilesController { } const bucket = result.extension?.values?.bucket as number; - const createEmbeddings = (bucket ? (result.extension?.fixedValues?.createEmbeddings ?? true) : false) as boolean; + const vectorize = (result.extension?.values?.vectorize as boolean) ?? true; + + const embedType = bucket ? (vectorize ? 'vector_and_text' : 'text') : 'none'; const command = new UploadFile({ user: req.user, @@ -136,8 +138,7 @@ export class UserFilesController { fileName: file.originalname, fileSize: file.size, bucketId: bucket, - extensionId, - createEmbeddings, + embedType, conversationId, }); @@ -155,9 +156,18 @@ export class UserFilesController { required: true, type: Number, }) + @ApiQuery({ + name: 'conversationId', + required: false, + type: 'number', + }) @ApiNoContentResponse() - async deleteUserFile(@Req() req: Request, @Param('fileId') fileId: number) { - const command = new DeleteFile(req.user, +fileId); + async deleteUserFile( + @Req() req: Request, + @Param('fileId', ParseIntPipe) fileId: number, + @Query('conversationId', new ParseIntPipe({ optional: true })) conversationId?: number, + ) { + const command = new DeleteFile(req.user, fileId, conversationId); await this.commandBus.execute(command); } diff --git a/backend/src/controllers/prompts/dtos/index.ts b/backend/src/controllers/prompts/dtos/index.ts new file mode 100644 index 000000000..6bcb493f0 --- /dev/null +++ b/backend/src/controllers/prompts/dtos/index.ts @@ -0,0 +1,115 @@ +import { ApiProperty } from '@nestjs/swagger'; +import { IsArray, IsDefined, IsEnum, IsOptional, IsString } from 'class-validator'; +import { PromptEntity } from 'src/domain/database/entities/prompt'; +import { VisibilityType } from 'src/domain/prompt'; + +export class CreatePromptCategoryDto { + @ApiProperty({ + description: 'The label or display name of the prompt category.', + required: true, + }) + @IsDefined() + @IsString() + label!: string; + + @ApiProperty({ + description: 'The description of the prompt category.', + required: false, + }) + @IsOptional() + @IsString() + description?: string; + + @ApiProperty({ + description: 'The date of creation for a prompt category.', + required: true, + }) + creationDate!: Date; + + @ApiProperty({ + description: 'The visibility of the prompt category.', + required: true, + enum: VisibilityType, + }) + @IsDefined() + @IsEnum(VisibilityType) + visibility!: VisibilityType; +} + +export class PromptCategoryDto extends CreatePromptCategoryDto { + @ApiProperty({ + description: 'The identifier of the prompt category.', + required: true, + }) + id!: string; +} + +export class CreatePromptDto { + @ApiProperty({ + description: 'The title of the prompt.', + required: true, + }) + @IsDefined() + @IsString() + title!: string; + + @ApiProperty({ + description: 'The description of the prompt.', + required: false, + }) + @IsOptional() + @IsString() + description?: string; + + @ApiProperty({ + description: 'The content or body of the prompt.', + required: true, + }) + @IsDefined() + @IsString() + content!: string; + + @ApiProperty({ + description: 'The ID of the categories this prompt belongs to.', + required: false, + }) + @IsOptional() + @IsArray() + categories?: string[]; + + @ApiProperty({ + description: 'The visibility of the prompt (e.g., public, private).', + required: true, + enum: VisibilityType, + }) + @IsDefined() + @IsEnum(VisibilityType) + visibility!: VisibilityType; +} + +export class PromptDto extends CreatePromptDto { + @ApiProperty({ + description: 'The identifier of the prompt.', + required: true, + }) + id!: string; + + @ApiProperty({ + description: 'The average rating of the prompt.', + required: true, + }) + rating!: number; + + static fromDomain(this: void, source: PromptEntity) { + const result = new PromptDto(); + result.id = source.id.toString(); + result.title = source.title; + result.description = source.description; + result.content = source.content; + result.visibility = source.visibility; + result.categories = source.categories?.map((cat) => cat.label) || []; + result.rating = source.rating; + + return result; + } +} diff --git a/backend/src/controllers/prompts/prompts.controller.ts b/backend/src/controllers/prompts/prompts.controller.ts new file mode 100644 index 000000000..caccc6227 --- /dev/null +++ b/backend/src/controllers/prompts/prompts.controller.ts @@ -0,0 +1,62 @@ +import { Body, Controller, Get, Param, Post, UseGuards } from '@nestjs/common'; +import { CommandBus } from '@nestjs/cqrs'; +import { ApiOperation, ApiResponse, ApiTags } from '@nestjs/swagger'; +import { CreatePrompt, CreatePromptResponse } from 'src/domain/prompt/use-cases/create-prompt'; +import { LocalAuthGuard } from '../../domain/auth'; +import { CreatePromptCategoryDto, CreatePromptDto, PromptCategoryDto, PromptDto } from './dtos'; + +@Controller('prompt') +@ApiTags('prompts') +@UseGuards(LocalAuthGuard) +export class PromptController { + constructor(private readonly commandBus: CommandBus) {} + + @Post('categories') + @ApiOperation({ operationId: 'postPromptCategory', summary: 'Create a new prompt category' }) + @ApiResponse({ status: 201, description: 'Category created successfully' }) + async createPromptCategory(@Body() createPromptCategoryDto: CreatePromptCategoryDto): Promise { + return Promise.resolve(undefined as unknown as PromptCategoryDto); + } + + @Get('categories') + @ApiOperation({ operationId: 'getPromptCategory', summary: 'Get a prompt category' }) + @ApiResponse({ status: 200, type: PromptCategoryDto }) + async getPromptCategory(@Param('id') id: number): Promise { + return Promise.resolve(id as unknown as PromptCategoryDto); + } + + @Post() + @ApiOperation({ operationId: 'postPrompt', summary: 'Create a new prompt' }) + @ApiResponse({ status: 201, description: 'Prompt created successfully' }) + async createPrompt(@Body() createPromptDto: CreatePromptDto): Promise { + const response: CreatePromptResponse = await this.commandBus.execute( + new CreatePrompt({ + title: createPromptDto.title, + description: createPromptDto.description, + content: createPromptDto.content, + visibility: createPromptDto.visibility, + categoryLabels: createPromptDto.categories, + }), + ); + + // Map entity to DTO + const promptDto: PromptDto = { + id: response.prompt.id.toString(), + title: response.prompt.title, + description: response.prompt.description, + content: response.prompt.content, + visibility: response.prompt.visibility, + categories: response.prompt.categories?.map((cat) => cat.label) || [], + rating: response.prompt.rating, + }; + + return promptDto; + } + + @Get() + @ApiOperation({ operationId: 'getPrompt', summary: 'Get a prompt' }) + @ApiResponse({ status: 200, type: PromptDto }) + async getPrompt(@Param('id') id: number): Promise { + return Promise.resolve(id as unknown as PromptDto); + } +} diff --git a/backend/src/controllers/prompts/prompts.e2e.spec.ts b/backend/src/controllers/prompts/prompts.e2e.spec.ts new file mode 100644 index 000000000..e864ed1ba --- /dev/null +++ b/backend/src/controllers/prompts/prompts.e2e.spec.ts @@ -0,0 +1,146 @@ +import { Server } from 'net'; +import { HttpStatus, INestApplication } from '@nestjs/common'; +import { Test, TestingModule } from '@nestjs/testing'; +import * as request from 'supertest'; +import { DataSource, Repository } from 'typeorm'; +import { AppModule } from '../../app.module'; +import { PromptCategoryEntity } from '../../domain/database'; +import { VisibilityType } from '../../domain/prompt'; +import { initAppWithDataBaseAndValidUser } from '../../utils/testUtils'; +import { CreatePromptDto, PromptDto } from './dtos'; + +describe('Prompts', () => { + let app: INestApplication; + let dataSource: DataSource; + + beforeAll(async () => { + const module: TestingModule = await Test.createTestingModule({ + imports: [AppModule], + }).compile(); + + const initialized = await initAppWithDataBaseAndValidUser(dataSource, module, app); + dataSource = initialized.dataSource; + app = initialized.app; + await seedTestData(dataSource); + }); + + afterAll(async () => { + await dataSource.destroy(); + await app.close(); + }); + + it('should create a prompt without categories', async () => { + const newPrompt: CreatePromptDto = { + title: 'Test Prompt', + description: 'A test prompt for e2e testing', + content: 'This is the prompt content for testing purposes.', + visibility: VisibilityType.PUBLIC, + }; + + const response = await request(app.getHttpServer()).post('/prompt').send(newPrompt).expect(HttpStatus.CREATED); + + const typedBody = response.body as PromptDto; + expect(typedBody.id).toBeDefined(); + expect(typedBody.title).toBe(newPrompt.title); + expect(typedBody.description).toBe(newPrompt.description); + expect(typedBody.content).toBe(newPrompt.content); + expect(typedBody.visibility).toBe(newPrompt.visibility); + expect(typedBody.categories).toEqual([]); + }); + + it('should create a prompt with categories', async () => { + const newPrompt: CreatePromptDto = { + title: 'Categorized Prompt', + content: 'This prompt has categories.', + visibility: VisibilityType.PRIVATE, + categories: ['technical', 'creative'], + }; + + const response = await request(app.getHttpServer()).post('/prompt').send(newPrompt).expect(HttpStatus.CREATED); + + const typedBody = response.body as PromptDto; + expect(typedBody.id).toBeDefined(); + expect(typedBody.title).toBe(newPrompt.title); + expect(typedBody.content).toBe(newPrompt.content); + expect(typedBody.visibility).toBe(newPrompt.visibility); + expect(typedBody.categories).toHaveLength(2); + expect(typedBody.categories).toEqual( + expect.arrayContaining([expect.objectContaining({ label: 'technical' }), expect.objectContaining({ label: 'creative' })]), + ); + }); + + it('should create a prompt with only required fields', async () => { + const newPrompt: CreatePromptDto = { + title: 'Minimal Prompt', + content: 'This is a minimal prompt with only required fields.', + visibility: VisibilityType.PRIVATE, + }; + + const response = await request(app.getHttpServer()).post('/prompt').send(newPrompt).expect(HttpStatus.CREATED); + + const typedBody = response.body as PromptDto; + expect(typedBody.id).toBeDefined(); + expect(typedBody.title).toBe(newPrompt.title); + expect(typedBody.content).toBe(newPrompt.content); + expect(typedBody.visibility).toBe(newPrompt.visibility); + expect(typedBody.description).toBeUndefined(); + expect(typedBody.rating).toBeUndefined(); + expect(typedBody.categories).toEqual([]); + }); + + it('should create a prompt with non-existent categories', async () => { + const newPrompt: CreatePromptDto = { + title: 'Prompt with Non-existent Categories', + content: 'This prompt references categories that do not exist.', + visibility: VisibilityType.PUBLIC, + categories: ['nonexistent1', 'technical', 'nonexistent2'], + }; + + const response = await request(app.getHttpServer()).post('/prompt').send(newPrompt).expect(HttpStatus.CREATED); + + const typedBody = response.body as PromptDto; + expect(typedBody.categories).toHaveLength(1); // Only 'technical' exists + expect(typedBody.categories).toEqual([expect.objectContaining({ label: 'technical' })]); + }); + + it('should fail to create a prompt without required fields', async () => { + const invalidPrompt = { + description: 'Missing title and content', + visibility: VisibilityType.PUBLIC, + }; + + await request(app.getHttpServer()).post('/prompt').send(invalidPrompt).expect(HttpStatus.BAD_REQUEST); + }); + + it('should fail to create a prompt with invalid visibility', async () => { + const invalidPrompt = { + title: 'Invalid Prompt', + content: 'This prompt has invalid visibility.', + visibility: 'invalid_visibility', + }; + + await request(app.getHttpServer()).post('/prompt').send(invalidPrompt).expect(HttpStatus.BAD_REQUEST); + }); +}); + +async function seedTestData(dataSource: DataSource) { + const promptCategoryRepository = dataSource.getRepository(PromptCategoryEntity); + + // Create test categories + await createPromptCategory('technical', 'Technical prompts', promptCategoryRepository); + await createPromptCategory('creative', 'Creative writing prompts', promptCategoryRepository); + await createPromptCategory('business', 'Business and professional prompts', promptCategoryRepository); +} + +async function createPromptCategory( + label: string, + description: string, + promptCategoryRepository: Repository, +): Promise { + const categoryEntity = new PromptCategoryEntity(); + categoryEntity.label = label; + categoryEntity.description = description; + categoryEntity.creationDate = new Date(); + categoryEntity.visibility = VisibilityType.PUBLIC; + return promptCategoryRepository.save(categoryEntity); +} diff --git a/backend/src/controllers/responses/api.responses.controller.ts b/backend/src/controllers/responses/api.responses.controller.ts new file mode 100644 index 000000000..9d666c2c3 --- /dev/null +++ b/backend/src/controllers/responses/api.responses.controller.ts @@ -0,0 +1,372 @@ +import { + BadRequestException, + Body, + Controller, + HttpCode, + HttpStatus, + Logger, + Param, + ParseIntPipe, + Post, + Req, + UploadedFile, + UseGuards, + UseInterceptors, +} from '@nestjs/common'; +import { CommandBus, QueryBus } from '@nestjs/cqrs'; +import { FileInterceptor } from '@nestjs/platform-express'; +import { ApiExcludeController } from '@nestjs/swagger'; +import { HealthCheck } from '@nestjs/terminus'; +import { Request } from 'express'; +import * as mime from 'mime-types'; +import { Observable } from 'rxjs'; +import { LocalAuthGuard } from '../../domain/auth'; +import { SendMessage, SendMessageResponse, StartConversation, StartConversationResponse, StreamEvent } from '../../domain/chat'; +import { GetExtensions, GetExtensionsResponse } from '../../domain/extensions'; +import { GetFiles, GetFilesResponse, UploadFile, UploadFileResponse } from '../../domain/files'; +import { UploadedFile as UploadedFileInternal } from '../../domain/files/interfaces'; +import { FilesExtensionConfiguration } from '../../extensions/tools/files'; +import { FilesVisionExtensionConfiguration } from '../../extensions/tools/files-vision'; +import { WholeFilesExtensionConfiguration } from '../../extensions/tools/whole-files-conversation'; +import { FilePurpose, ResponseCreateDto, ResponseDto } from './dtos'; + +@Controller('public/assistants/:assistantId') +@ApiExcludeController() +@UseGuards(LocalAuthGuard) +export class ApiResponsesController { + private logger = new Logger(this.constructor.name); + + constructor( + private readonly queryBus: QueryBus, + private readonly commandBus: CommandBus, + ) {} + + private getLlm(extensions: GetExtensionsResponse['extensions'], model?: string) { + if (model != null) { + const llm = extensions.find( + (x) => + (x.spec.type === 'llm' && x.values.deploymentName === model) || + x.values.model === model || + x.values.modelName === model, + ); + return llm?.spec.name; + } + } + + private setConfigurationValue( + extensions: GetExtensionsResponse['extensions'], + key: string, + value: T, + configuration: Record>, + ) { + if (value != null) { + extensions + .filter((x) => Object.keys(x.configurableArguments?.properties ?? {}).includes(key)) + .forEach((x) => { + configuration[x.id] = configuration[x.id] ?? {}; + configuration[x.id][key] = value; + }); + } + } + + private getConfiguration( + extensions: GetExtensionsResponse['extensions'], + data: { temperature?: number; instructions?: string }, + ) { + const configuration: Record> = {}; + this.setConfigurationValue(extensions, 'temperature', data.temperature, configuration); + this.setConfigurationValue(extensions, 'text', data.instructions, configuration); + return configuration; + } + + private findBucketForAssistant(extensions: GetExtensionsResponse['extensions'], fileName: string, purpose: FilePurpose) { + if (purpose === 'user_data') { + const filesUser = extensions.find((x) => x.name === 'files-42'); + if (filesUser) { + const { bucket } = filesUser.values as FilesExtensionConfiguration; + return { bucketId: bucket, embedType: 'vector_and_text' as const }; + } + } + + if (purpose === 'assistants') { + const filesVision = extensions.find((x) => x.name === 'files-vision'); + if (filesVision) { + const { fileNameExtensions } = filesVision.values as FilesVisionExtensionConfiguration; + if (fileNameExtensions.find((x) => fileName.endsWith(x))) { + return { embedType: 'none' as const }; + } + } + + const filesWhole = extensions.find((x) => x.name === 'files-whole'); + if (filesWhole) { + const { bucket } = filesWhole.values as WholeFilesExtensionConfiguration; + return { bucketId: bucket, embedType: 'vector_and_text' as const }; + } + } + + return {}; + } + + private getUserPrompts(request: ResponseCreateDto): string[] { + if (typeof request.input === 'string') { + return [request.input]; + } + + return request.input + .filter((x) => x.role === 'user') + .flatMap((userMessage) => { + if (typeof userMessage.content === 'string') { + return [userMessage.content]; + } + + return userMessage.content.filter((x) => x.type === 'input_text').map((part) => part.text); + }); + } + + private getSystemMessages(request: ResponseCreateDto): string[] { + const result = request.instructions ? [request.instructions] : []; + + if (typeof request.input === 'string') { + return result; + } + + const systemMessages = request.input.filter((x) => x.role === 'system'); + if (!systemMessages.length) { + return result; + } + + const systemMessageTexts = systemMessages.flatMap((x) => { + if (typeof x.content === 'string') { + return [x.content]; + } else { + return x.content.filter((y) => y.type === 'input_text').map((y) => y.text); + } + }); + + return result.concat(systemMessageTexts); + } + + private async uploadFilesByData( + request: ResponseCreateDto, + user: Request['user'], + extensions: GetExtensionsResponse['extensions'], + ) { + if (typeof request.input === 'string') { + return []; + } + + const files = request.input + .filter((x) => x.role === 'user') + .flatMap((x) => + typeof x.content !== 'string' + ? x.content + .filter((y) => y.type === 'input_file') + .filter((y) => y.filename && y.file_data) + .map((y) => { + return { data: y.file_data!, name: y.filename! }; + }) + : [], + ); + + return await Promise.all( + files.map(async ({ name, data }) => { + const base64String = data.replace(/^data:[^;]+;base64,/, ''); + const buffer = Buffer.from(base64String, 'base64'); + + const { bucketId, embedType } = this.findBucketForAssistant(extensions, name, 'assistants'); + if (!embedType) { + throw new BadRequestException('files are not accepted'); + } + + const command = new UploadFile({ + buffer: buffer, + mimeType: mime.lookup(name) as string, + fileName: name, + fileSize: buffer.length, + user, + bucketId, + embedType, + }); + const response: UploadFileResponse = await this.commandBus.execute(command); + return response.file; + }), + ); + } + + private async getUploadedFiles(request: ResponseCreateDto, user: Request['user']): Promise { + if (typeof request.input === 'string') { + return []; + } + + const fileIds = request.input + .filter((x) => x.role === 'user') + .flatMap((x) => + typeof x.content !== 'string' + ? x.content + .filter((y) => y.type === 'input_file' || y.type === 'input_image') + .filter((y) => y.file_id && !Number.isNaN(Number(y.file_id))) + .map((y) => Number(y.file_id!)) + : [], + ); + + const { files }: GetFilesResponse = fileIds.length + ? await this.queryBus.execute(new GetFiles({ user, bucketIdOrType: 'all', page: 0, files: fileIds })) + : { files: [], total: 0 }; + + return files; + } + + private readStream(stream: Observable) { + return new Promise<{ id: number; text: string; tokens: number }>((resolve, reject) => { + const output = { id: 0, text: '', tokens: 0 }; + stream.subscribe({ + next: (event) => { + if (event.type === 'chunk') { + event.content.forEach((content) => { + if (content.type === 'text') { + output.text += content.text; + } + }); + } + if (event.type === 'saved' && event.messageType === 'ai') { + output.id = event.messageId; + } + + if (event.type === 'completed') { + output.tokens = event.metadata.tokenCount; + } + }, + error: (err: Error) => reject(err), + complete: () => resolve(output), + }); + }); + } + + private async getFiles(request: ResponseCreateDto, user: Request['user'], extensions: GetExtensionsResponse['extensions']) { + // files uploaded via responses api (file_id) + const uploadedFiles = await this.uploadFilesByData(request, user, extensions); + // files uploaded via responses api (file_url) + const files = await this.getUploadedFiles(request, user); + + return [...files, ...uploadedFiles]; + } + + @Post('/responses') + @HealthCheck() + async createResponse( + @Body() request: ResponseCreateDto, + @Param('assistantId', ParseIntPipe) assistantId: number, + @Req() req: Request, + ): Promise { + const { extensions }: GetExtensionsResponse = await this.queryBus.execute(new GetExtensions(assistantId, true, true)); + const llm = this.getLlm(extensions, request.model); + const configuration = this.getConfiguration(extensions, request); + const userMessages = this.getUserPrompts(request); + const systemMessages = this.getSystemMessages(request); + const input = userMessages.join(' '); + const files = await this.getFiles(request, req.user, extensions); + + const result: StartConversationResponse = await this.commandBus.execute( + new StartConversation(req.user, { configurationId: assistantId, llm }), + ); + const response: SendMessageResponse = await this.queryBus.execute( + new SendMessage(result.conversation.id, req.user, input, files, undefined, systemMessages, configuration), + ); + + const output = await this.readStream(response.stream); + + const id = output.id; + return { + id: `resp_${id}`, + object: 'response', + created_at: Math.round(Date.now() / 1000), + status: 'completed', + background: false, + model: request.model, + output: [ + { + id: `msg_${id}`, + type: 'message', + status: 'completed', + content: [ + { + type: 'output_text', + annotations: [], + text: output.text, + }, + ], + role: 'assistant', + }, + ], + parallel_tool_calls: true, + service_tier: 'default', + store: true, + temperature: request.temperature ?? 1.0, + text: { + format: { + type: 'text', + }, + }, + tool_choice: 'auto', + tools: [], + top_p: 1.0, + truncation: 'disabled', + usage: { + input_tokens: 0, + input_tokens_details: { + cached_tokens: 0, + }, + output_tokens: output.tokens, + output_tokens_details: { + reasoning_tokens: 0, + }, + total_tokens: output.tokens, + }, + metadata: {}, + }; + } + + @Post('/files') + @HttpCode(HttpStatus.OK) + @UseInterceptors(FileInterceptor('file')) + async uploadFile( + @Param('assistantId', ParseIntPipe) assistantId: number, + @Req() req: Request, + @UploadedFile() file: Express.Multer.File, + @Body('purpose') purpose: FilePurpose, + ) { + if (!file || !purpose) { + throw new BadRequestException('file is missing'); + } + + const result: GetExtensionsResponse = await this.queryBus.execute(new GetExtensions(assistantId, true, true)); + const { bucketId, embedType } = this.findBucketForAssistant(result.extensions, file.originalname, purpose); + if (!embedType) { + throw new BadRequestException('files are not accepted'); + } + + const extension = file.originalname.substring(file.originalname.lastIndexOf('.') + 1).toLowerCase(); + const command = new UploadFile({ + buffer: file.buffer, + mimeType: mime.lookup(extension) as string, + fileName: file.originalname, + fileSize: file.size, + user: req.user, + bucketId, + embedType, + }); + + const uploaded: UploadFileResponse = await this.commandBus.execute(command); + + return { + object: 'file', + id: String(uploaded.file.id), + purpose: purpose, + filename: file.filename, + bytes: file.size, + created_at: Math.round(uploaded.file.uploadedAt.getTime() / 1000), + status: 'processed', + status_details: null, + }; + } +} diff --git a/backend/src/controllers/responses/dtos/index.ts b/backend/src/controllers/responses/dtos/index.ts new file mode 100644 index 000000000..18bc5aee7 --- /dev/null +++ b/backend/src/controllers/responses/dtos/index.ts @@ -0,0 +1,157 @@ +import { ApiProperty, ApiPropertyOptional, getSchemaPath } from '@nestjs/swagger'; + +export class ResponseInputFile { + @ApiProperty({ enum: ['input_file'] }) + type!: 'input_file'; + + @ApiPropertyOptional({ type: 'string' }) + file_data?: string; + + @ApiPropertyOptional({ type: 'string' }) + file_id?: string; + + @ApiPropertyOptional({ type: 'string' }) + file_url?: string; + + @ApiPropertyOptional() + filename?: string; +} + +export class ResponseInputImage { + @ApiProperty({ enum: ['low', 'high', 'auto'] }) + detail!: 'low' | 'high' | 'auto'; + + @ApiProperty({ enum: ['input_image'] }) + type!: 'input_image'; + + @ApiPropertyOptional({ type: 'string' }) + file_id?: string | null; + + @ApiPropertyOptional({ type: 'string' }) + image_url?: string | null; +} + +export class ResponseInputText { + @ApiProperty({ type: 'string' }) + text!: string; + + @ApiProperty({ enum: ['input_text'] }) + type!: 'input_text'; +} + +export type ResponseInputContent = ResponseInputText | ResponseInputImage | ResponseInputFile; + +export type ResponseInputMessageContentList = Array; + +export class EasyInputMessage { + @ApiProperty({ + oneOf: [ + { type: 'string' }, + { + type: 'array', + items: { + oneOf: [ + { $ref: getSchemaPath(ResponseInputText) }, + { $ref: getSchemaPath(ResponseInputImage) }, + { $ref: getSchemaPath(ResponseInputFile) }, + ], + }, + }, + ], + }) + content!: string | ResponseInputMessageContentList; + + @ApiProperty({ enum: ['user', 'assistant', 'system', 'developer'] }) + role!: 'user' | 'assistant' | 'system' | 'developer'; + + @ApiPropertyOptional({ enum: ['message'] }) + type?: 'message'; +} + +export type ResponseInputItem = EasyInputMessage; + +export type ResponseInput = Array; + +export class ResponseCreateDto { + @ApiProperty({ type: 'string' }) + model!: string; + + @ApiProperty({ oneOf: [{ type: 'string' }, { type: 'array', items: { $ref: getSchemaPath(EasyInputMessage) } }] }) + input!: string | ResponseInput; + + @ApiPropertyOptional({ type: 'boolean' }) + stream?: boolean; + + @ApiPropertyOptional({ type: 'number' }) + temperature?: number; + + @ApiPropertyOptional({ type: 'string' }) + instructions?: string; + + @ApiPropertyOptional({ type: 'boolean' }) + store?: boolean; +} + +export type ResponseDto = { + id: string; + object: 'response'; + created_at: number; // 1754392046; + status: 'completed'; + background: false; + error?: null; + incomplete_details?: null; + instructions?: string; + max_output_tokens?: null; + max_tool_calls?: null; + model: string; + output: [ + { + id: string; + type: 'message'; + status: 'completed'; + content: [ + { + type: 'output_text'; + annotations: []; + text: string; + }, + ]; + role: 'assistant'; + }, + ]; + parallel_tool_calls: true; + previous_response_id?: string; + prompt_cache_key?: null; + reasoning?: { + effort?: null; + summary?: null; + }; + safety_identifier?: null; + service_tier: 'default'; + store: boolean; // default true + temperature: number; + text: { + format: { + type: 'text'; + }; + }; + tool_choice: 'auto'; + tools: []; + top_p: number; // 1.0 + truncation: 'disabled'; + usage: { + input_tokens: number; // 11; + input_tokens_details: { + cached_tokens: 0; + }; + output_tokens: number; // 19; + output_tokens_details: { + reasoning_tokens: 0; + }; + total_tokens: number; // 30 + }; + user?: null; + metadata: Record; +}; + +export type FilePurpose = 'assistants' | 'batch' | 'fine-tune' | 'vision' | 'user_data' | 'evals'; diff --git a/backend/src/controllers/shared.ts b/backend/src/controllers/shared.ts index cf48dca03..e22c3ef59 100644 --- a/backend/src/controllers/shared.ts +++ b/backend/src/controllers/shared.ts @@ -157,7 +157,7 @@ export class DocumentDto { link?: string | null; @ApiProperty({ - description: 'Can the document be downloaded via the `getDocument` endpoint.', + description: 'Can the document be downloaded in pdf format via the `getDocument` endpoint.', required: false, type: 'boolean', }) diff --git a/backend/src/controllers/usages/usages.e2e.spec.ts b/backend/src/controllers/usages/usages.e2e.spec.ts index bcb65aff6..4570ee459 100644 --- a/backend/src/controllers/usages/usages.e2e.spec.ts +++ b/backend/src/controllers/usages/usages.e2e.spec.ts @@ -9,6 +9,7 @@ import { GroupBy } from 'src/domain/chat/statistics'; import { AppModule } from '../../app.module'; import { ConfigurationEntity, + ConfigurationStatus, ConversationEntity, MessageEntity, trackUsage, @@ -205,7 +206,7 @@ async function createConfigurationEntity(configurationRepository: Repository | null> { - const apiKey = this.findApiKey(request); + const key = this.findApiKey(request); - if (apiKey) { - const hashedApiKey = createHash('sha256').update(apiKey).digest('hex'); - return await this.userRepository.findOneBy({ apiKey: hashedApiKey }); + if (key) { + return this.userRepository.findOneBy({ apiKey: key }); } else if (request.session.user) { return request.session.user; } @@ -35,11 +34,11 @@ export class LocalStrategy extends PassportStrategy(Strategy, 'local') { private findApiKey(request: Request) { for (const candidate of this.headers) { - const apiKeyHeader = request.headers[candidate]; - const apiKeyValue = isArray(apiKeyHeader) ? apiKeyHeader[0] : apiKeyHeader; + const header = request.headers[candidate]; + const value = isArray(header) ? header[0] : header; - if (isString(apiKeyValue) && apiKeyValue.trim().length > 0) { - return apiKeyValue; + if (isString(value) && value.trim().length > 0) { + return createHash('sha256').update(value.replace('Bearer ', '')).digest('hex'); } } diff --git a/backend/src/domain/chat/interfaces.ts b/backend/src/domain/chat/interfaces.ts index 7a92d9c61..c8f9ef13d 100644 --- a/backend/src/domain/chat/interfaces.ts +++ b/backend/src/domain/chat/interfaces.ts @@ -1,10 +1,6 @@ -import { type BaseCallbackHandler, type CallbackHandlerMethods } from '@langchain/core/callbacks/base'; -import { type BaseListChatMessageHistory } from '@langchain/core/chat_history'; -import { type BaseChatModel, type BaseChatModelCallOptions } from '@langchain/core/language_models/chat_models'; -import { type ChatPromptTemplate } from '@langchain/core/prompts'; -import { type RunnableSequence } from '@langchain/core/runnables'; -import { type StructuredToolInterface } from '@langchain/core/tools'; +import { CallSettings, LanguageModel } from 'ai'; import { Subject } from 'rxjs'; +import * as z from 'zod'; import { ConfigurationModel, ExtensionArgument } from '../extensions'; import { UploadedFile } from '../files'; import { User } from '../users'; @@ -66,15 +62,124 @@ export interface ChatUI { form(text: string, schema: ExtensionArgument): Promise; } -export interface AgentArgument { - llm: BaseChatModel; - tools: StructuredToolInterface[]; - prompt: ChatPromptTemplate; - streamRunnable?: boolean; +export abstract class BaseMessage { + role!: 'assistant' | 'user'; + content: string; + constructor(content: string) { + this.content = content; + } + getType(): 'ai' | 'human' { + if (this.isHuman()) { + return 'human'; + } + return 'ai'; + } + getRole(): 'assistant' | 'user' { + return this.role; + } + isHuman(): this is HumanMessage { + return this.role === 'user'; + } + isAI(): this is AIMessage { + return this.role === 'assistant'; + } +} + +export class AIMessage extends BaseMessage { + readonly role = 'assistant' as const; + constructor(content: string) { + super(content); + } +} + +export class HumanMessage extends BaseMessage { + readonly role = 'user' as const; + constructor(content: string) { + super(content); + } +} + +export abstract class MessagesHistory { + /** Returns a list of messages stored in the store. */ + public abstract getMessages(): Promise; + /** Add a message object to the store. */ + public abstract addMessage(message: BaseMessage): Promise; + /** Add source annotations. */ + public abstract addSources(externalExtensionId: string, sources: Source[]): void; + + public addUserMessage(message: string): Promise { + return this.addMessage(new HumanMessage(message)); + } + public addAIMessage(message: string): Promise { + return this.addMessage(new AIMessage(message)); + } + public async addMessages(messages: BaseMessage[]): Promise { + for (const message of messages) { + await this.addMessage(message); + } + } +} + +export interface LanguageModelContext { + model: LanguageModel; + options: Partial; + // metadata (e.g. for usage counting) + modelName: string; + providerName: string; +} + +export abstract class NamedStructuredTool< + T extends z.ZodRawShape = z.ZodRawShape, + TSchema extends z.ZodObject = z.ZodObject, + TToolOutput = string | Record | undefined | void, +> { + abstract displayName: string; + abstract schema: TSchema; + + abstract name: string; + abstract description: string; + + protected abstract _call(arg: z.infer): Promise; + + execute(input: z.infer): Promise { + return this._call(input); + } } -export interface MessagesHistory { - addSources(externalExtensionId: string, sources: Source[]): void; +export type NamedDynamicStructuredToolInput, TToolOutput> = { + name: string; + description: string; + displayName: string; + schema: TSchema; + func: (arg: z.infer) => Promise; + returnDirect?: boolean; +}; + +export class NamedDynamicStructuredTool< + T extends z.ZodRawShape = z.ZodRawShape, + TSchema extends z.ZodObject = z.ZodObject, + TToolOutput = string | Record | undefined | void, +> extends NamedStructuredTool { + displayName: string; + name: string; + schema: TSchema; + description: string; + func: (arg: z.infer) => Promise; + returnDirect: boolean; + + constructor({ displayName, func, schema, ...toolInput }: NamedDynamicStructuredToolInput) { + super(); + this.displayName = displayName; + this.func = func; + this.schema = schema; + this.name = toolInput.name; + this.description = toolInput.description; + this.returnDirect = toolInput.returnDirect ?? false; + } + + protected async _call(arg: z.infer): Promise { + return this.func(arg); + } } export interface ChatContext { @@ -82,7 +187,7 @@ export interface ChatContext { readonly abort: AbortController; // Tools this agent has access to. - readonly tools: (StructuredToolInterface & { displayName?: string })[]; + readonly tools: NamedStructuredTool[]; // The input. readonly input: string; @@ -111,9 +216,6 @@ export interface ChatContext { // The context values. readonly context: ConversationContext; - // The callbacks for the chain. - readonly callbacks: (BaseCallbackHandler | CallbackHandlerMethods)[]; - // Configures the summary generation. summaryConfig?: { prompt: string; historyLength?: number }; @@ -124,12 +226,7 @@ export interface ChatContext { user: User; // LLM to use as the agent. - llms: Record>; - - agentFactory?: (args: AgentArgument) => Promise | RunnableSequence; - - // The prompt to use, must have an input key. - prompt?: ChatPromptTemplate; + llms: Record; // The chosen LLM. llm?: string; @@ -138,7 +235,10 @@ export interface ChatContext { tokenUsage?: TokenUsage; // The history of previous messages - history?: BaseListChatMessageHistory & MessagesHistory; + history?: MessagesHistory; + + // whether open telemetry is enabled + telemetry?: boolean; } export interface TokenUsage { @@ -214,6 +314,8 @@ export type MessageType = (typeof MESSAGE_TYPES)[number]; export type StreamEvent = | StreamSummaryEvent | StreamCompletedEvent + | StreamReasoningEvent + | StreamReasoningEndEvent | StreamDebugEvent | StreamSourcesEvent | StreamLoggingEvent @@ -275,6 +377,15 @@ export interface StreamSummaryEvent { content: string; } +export interface StreamReasoningEvent { + type: 'reasoning'; + content: string; +} + +export interface StreamReasoningEndEvent { + type: 'reasoning_end'; +} + export interface StreamCompletedEvent { type: 'completed'; metadata: ChatMetadata; diff --git a/backend/src/domain/chat/middlewares/default-prompt-middleware.ts b/backend/src/domain/chat/middlewares/default-prompt-middleware.ts index 96cd14457..35797fe7f 100644 --- a/backend/src/domain/chat/middlewares/default-prompt-middleware.ts +++ b/backend/src/domain/chat/middlewares/default-prompt-middleware.ts @@ -1,4 +1,3 @@ -import { ChatPromptTemplate, MessagesPlaceholder } from '@langchain/core/prompts'; import { Injectable } from '@nestjs/common'; import { ChatContext, ChatMiddleware, ChatNextDelegate, GetContext } from '../interfaces'; import { ExecuteMiddleware } from './execute-middleware'; @@ -8,30 +7,9 @@ export class DefaultPromptMiddleware implements ChatMiddleware { order = ExecuteMiddleware.ORDER - 10; async invoke(context: ChatContext, getContext: GetContext, next: ChatNextDelegate): Promise { - if (context.prompt) { - await next(context); - return; - } - if (context.systemMessages.length === 0) { context.systemMessages.push(`You are a helpful assistant. Today is ${new Date().toISOString()}.`); } - - const messages: Parameters[0] = [ - ...context.systemMessages.map((x) => ({ - role: 'system', - content: x, - })), - - new MessagesPlaceholder('chat_history'), - ['human', '{input}'], - ]; - - if (context.tools.length) { - messages.push(new MessagesPlaceholder('agent_scratchpad')); - } - - context.prompt = ChatPromptTemplate.fromMessages(messages); await next(context); } } diff --git a/backend/src/domain/chat/middlewares/execute-middleware.ts b/backend/src/domain/chat/middlewares/execute-middleware.ts index 2422b9f06..f7399c451 100644 --- a/backend/src/domain/chat/middlewares/execute-middleware.ts +++ b/backend/src/domain/chat/middlewares/execute-middleware.ts @@ -1,18 +1,11 @@ -import { MessageContent } from '@langchain/core/messages'; -import { ChatGenerationChunk } from '@langchain/core/outputs'; -import { Runnable, RunnableWithMessageHistory } from '@langchain/core/runnables'; -import { StructuredToolInterface } from '@langchain/core/tools'; import { Injectable, Logger } from '@nestjs/common'; -import { ConfigService } from '@nestjs/config'; -import { AgentExecutor, AgentExecutorInput, createOpenAIToolsAgent } from 'langchain/agents'; +import { stepCountIs, streamText, tool, ToolSet } from 'ai'; import { I18nService } from '../../../localization/i18n.service'; import { MetricsService } from '../../../metrics/metrics.service'; -import { ChatContext, ChatError, ChatMiddleware, NormalizedMessageContents } from '../interfaces'; -import { normalizedMessageContent } from '../utils'; +import { ChatContext, ChatError, ChatMiddleware, LanguageModelContext, NamedStructuredTool } from '../interfaces'; -type EventActionType = 'start' | 'stream' | 'end'; -type EventContextType = 'llm' | 'chat_model' | 'prompt' | 'tool' | 'chain'; -type EventType = `on_${EventContextType}_${EventActionType}`; +// this is the general structure of how AI SDK wraps errors +type GenericAIError = { error: unknown }; @Injectable() export class ExecuteMiddleware implements ChatMiddleware { @@ -20,7 +13,6 @@ export class ExecuteMiddleware implements ChatMiddleware { logger = new Logger(ExecuteMiddleware.name); constructor( - private readonly configService: ConfigService, private readonly i18n: I18nService, private readonly metricsService: MetricsService, ) {} @@ -42,164 +34,112 @@ export class ExecuteMiddleware implements ChatMiddleware { } } - async execute(context: ChatContext) { - const { llm: chosenLlm, agentFactory, configuration, llms, input, result, prompt, tools, history } = context; - - const shouldLogLLMAgent = this.configService.get('LOG_LLM_AGENT', 'false'); - if (configuration.executorEndpoint) { - return; - } - - const llm = llms[chosenLlm ?? '']; - - if (!llm) { - throw new ChatError(this.i18n.t('texts.chat.errorMissingLLM')); - } - - if (!prompt) { - throw new ChatError(this.i18n.t('texts.chat.errorMissingPrompt')); - } - - let runnable: Runnable; - - if (tools.length > 0) { - const agent = await (agentFactory ?? createOpenAIToolsAgent)({ - llm, - tools, - prompt, - }); - - runnable = new HackingAgentExecutor({ - agent, - tools, - verbose: shouldLogLLMAgent === 'true', - }); - } else { - runnable = prompt.pipe(llm); - } - - // This class is not properly documented in langchain but it works after a lot of testing. - const agentWithChatHistory = history - ? new RunnableWithMessageHistory({ - runnable, - // We don't need the session ID because we create the agent per call. - getMessageHistory: () => history, - // Uses the key to calculate the diff between all messages and input messages. - inputMessagesKey: 'input', - // Used to inject the history into the prompt. - historyMessagesKey: 'chat_history', - }) - : runnable; - - const stream = agentWithChatHistory.streamEvents( - { - input, + async handleAiSdkChainExecution(llm: LanguageModelContext, context: ChatContext) { + const { input, systemMessages, abort, result, history, tools } = context; + + const messages = await history?.getMessages(); + + const mapTool = (namedTool: NamedStructuredTool) => { + return { + name: namedTool.name, + tool: tool({ + name: namedTool.name, + inputSchema: namedTool.schema, + execute: (input) => namedTool.execute(input), + description: namedTool.description, + }), + }; + }; + + const allTools = tools.reduce((prev, curr) => { + const { name, tool } = mapTool(curr); + prev[name] = tool; + return prev; + }, {} as ToolSet); + + const { fullStream } = streamText({ + model: llm.model, + tools: allTools, + toolChoice: 'auto', + prompt: [ + ...systemMessages.map((x) => ({ role: 'system' as const, content: x })), + ...(messages?.filter((x) => !!x) ?? []), + { role: 'user' as const, content: input }, + ], + ...llm.options, + abortSignal: abort.signal, + stopWhen: stepCountIs(1000), + onFinish: ({ totalUsage }) => { + const totalTokens = totalUsage.totalTokens ?? 0; + context.tokenUsage ??= { tokenCount: 0, model: llm.modelName, llm: llm.providerName }; + context.tokenUsage.tokenCount += totalTokens; }, - { - version: 'v1', - configurable: { - sessionId: context.conversationId.toString(), + experimental_telemetry: { + isEnabled: context.telemetry ?? false, + metadata: { + conversationId: context.conversationId, + assistantId: context.configuration.id, + assistantName: context.configuration.name, + modelName: llm.modelName, + providerName: llm.providerName, }, - callbacks: context.callbacks, }, - ); - - // Stores the last result in case streaming is not supported. - let lastResult: NormalizedMessageContents | undefined; - let hasBeenStreamed = false; - let hasBeenStarted = false; - let hasLlmStream = false; - let hasChainStream = false; - - const getToolName = (toolId: string) => tools.find((x) => x.name === toolId)?.displayName || toolId; - - for await (const event of stream) { - const eventType = event.event as EventType; - - if (eventType === 'on_llm_start') { - hasBeenStarted = true; - } else if (hasBeenStarted && eventType === 'on_llm_stream' && !hasChainStream) { - hasLlmStream = true; - const chunk = event.data?.chunk as ChatGenerationChunk; - const content = normalizedMessageContent(chunk); - - // Content can either be a string or an array of objects. - if (content.length > 0) { - result.next({ type: 'chunk', content }); - hasBeenStreamed = true; - } - } else if (hasBeenStarted && eventType === 'on_chain_stream' && !hasLlmStream) { - hasChainStream = true; - const chunk = event.data?.chunk as ChatGenerationChunk; - const content = normalizedMessageContent(chunk); - - // Content can either be a string or an array of objects. - if (content.length > 0) { - result.next({ type: 'chunk', content }); - hasBeenStreamed = true; - } - } else if (eventType === 'on_chain_end' && !!event.data.output) { - const output = event.data.output as MessageContent; - const result = normalizedMessageContent(output); - - if (result.length > 0) { - lastResult = result; - } - } else if (eventType === 'on_tool_start') { - const toolName = getToolName(event.name); + }); + + let error: GenericAIError | null = null; + const text: string[] = []; + for await (const event of fullStream) { + if (event.type === 'tool-call') { + const toolName = tools.find((x) => x.name === event.toolName)?.displayName ?? event.toolName; result.next({ type: 'tool_start', tool: { name: toolName } }); - } else if (eventType === 'on_tool_end') { - if (this.configService.get('LOG_RAG_CHUNKS', 'false') === 'true') { - try { - const chunks = JSON.parse(event.data.output as string) as { content: string; metadata: Record }[]; - this.logger.log('==============RAG DEBUG=============='); - this.logger.log('Query: ' + event.data.input); - this.logger.log('Num of chunks ' + chunks.length); - chunks.forEach((chunk: { content: string; metadata: Record }) => { - this.logger.log(JSON.stringify(chunk, null, 2)); - this.logger.log('-----------------------------'); - }); - this.logger.log('====================================='); - - result.next({ type: 'logging', content: createLoggingChunks(chunks) }); - } catch (ex) { - this.logger.error('Log for RAG Chunks failed\n Cause: ', ex); - } - } - - result.next({ type: 'tool_end', tool: { name: getToolName(event.name) } }); + } + if (event.type === 'tool-result') { + const toolName = tools.find((x) => x.name === event.toolName)?.displayName ?? event.toolName; + result.next({ type: 'tool_end', tool: { name: toolName } }); + } + if (event.type === 'tool-error') { + this.logger.error({ event }); + const toolName = tools.find((x) => x.name === event.toolName)?.displayName ?? event.toolName; + // TODO: maybe add a `tool_error` event type and indicate errors in the ui + result.next({ type: 'tool_end', tool: { name: toolName } }); + } + if (event.type === 'reasoning-delta') { + result.next({ type: 'reasoning', content: event.text }); + } + if (event.type === 'reasoning-end') { + result.next({ type: 'reasoning_end' }); + } + if (event.type === 'text-delta') { + text.push(event.text); + result.next({ type: 'chunk', content: [{ type: 'text', text: event.text }] }); + } + if (event.type === 'error') { + this.logger.error({ event }); + error = event.error as GenericAIError; } } - if (!hasBeenStreamed && lastResult && lastResult.length > 0) { - // If the llm does not support streaming we have a fallback. - result.next({ type: 'chunk', content: lastResult }); + await history?.addAIMessage(text.join('')); + + if (error) { + // unwrap and throw the causing error to be handled by the ExceptionMiddleware + throw error.error; } } -} -type ToolWithFallback = StructuredToolInterface & { returnDirectFallback: boolean }; + async execute(context: ChatContext) { + const { llm: chosenLlm, configuration, llms } = context; -class HackingAgentExecutor extends AgentExecutor { - constructor(input: AgentExecutorInput) { - for (const tool of input.tools) { - (tool as ToolWithFallback)['returnDirectFallback'] = tool.returnDirect; - tool.returnDirect = false; + if (configuration.executorEndpoint) { + return; } - super(input); + const llm = llms[chosenLlm ?? '']; - for (const tool of input.tools) { - tool.returnDirect = (tool as ToolWithFallback)['returnDirectFallback']; + if (!llm) { + throw new ChatError(this.i18n.t('texts.chat.errorMissingLLM')); } - } -} -function createLoggingChunks(chunks: { content: string }[]) { - let logging = '**LOGGING**\n\n***Number of chunks*** ' + chunks.length + '\n\n'; - chunks.forEach((chunk, index) => { - logging += '***Chunk nr. ' + (index + 1) + ':***\n\n'; - logging += chunk.content + '\n\n'; - }); - return logging; + return this.handleAiSdkChainExecution(llm, context); + } } diff --git a/backend/src/domain/chat/middlewares/executor-middleware.ts b/backend/src/domain/chat/middlewares/executor-middleware.ts index d29497eaa..6b059ecfd 100644 --- a/backend/src/domain/chat/middlewares/executor-middleware.ts +++ b/backend/src/domain/chat/middlewares/executor-middleware.ts @@ -1,4 +1,3 @@ -import { mapChatMessagesToStoredMessages } from '@langchain/core/messages'; import { Injectable } from '@nestjs/common'; import { CommandBus } from '@nestjs/cqrs'; import { isString } from 'class-validator'; @@ -57,7 +56,10 @@ export class ExecutorMiddleware implements ChatMiddleware { context: context.context, }; - const stored = mapChatMessagesToStoredMessages(messages); + const stored = messages.map((msg) => ({ + type: msg.getType(), + data: { content: msg.content }, + })); for (const message of context.systemMessages) { request.history.push({ content: message, type: 'ai' }); @@ -68,12 +70,8 @@ export class ExecutorMiddleware implements ChatMiddleware { throw new InternalError('Only string messages are supported.'); } - // FIXME: find out if 'system' should be part of `MessageType` or if the check below - // can omit `messageType === 'system'` - // Then change to: - // const type = message.type as MessageType; const messageType = message.type; - if (messageType === 'human' || messageType === 'system' || messageType === 'ai') { + if (messageType === 'human' || messageType === 'ai') { request.history.push({ content: message.data.content, type: 'ai' }); } } diff --git a/backend/src/domain/chat/middlewares/get-history-middleware.ts b/backend/src/domain/chat/middlewares/get-history-middleware.ts index 0153f30f7..36da554e2 100644 --- a/backend/src/domain/chat/middlewares/get-history-middleware.ts +++ b/backend/src/domain/chat/middlewares/get-history-middleware.ts @@ -1,18 +1,20 @@ -import { BaseListChatMessageHistory } from '@langchain/core/chat_history'; -import { - AIMessage, - AIMessageChunk, - BaseMessage, - HumanMessage, - mapChatMessagesToStoredMessages, - mapStoredMessagesToChatMessages, -} from '@langchain/core/messages'; import { Injectable, Logger } from '@nestjs/common'; import { InjectRepository } from '@nestjs/typeorm'; import { onErrorResumeNextWith } from 'rxjs'; +import { In } from 'typeorm'; import { ExtensionSource, MessageEntity, MessageRepository } from 'src/domain/database'; -import { is } from 'src/lib'; -import { ChatContext, ChatMiddleware, ChatNextDelegate, GetContext, MessagesHistory, Source } from '../interfaces'; +import { ConversationFileEntity, ConversationFileRepository } from '../../database/entities/conversation-file'; +import { + AIMessage, + BaseMessage, + ChatContext, + ChatMiddleware, + ChatNextDelegate, + GetContext, + HumanMessage, + MessagesHistory, + Source, +} from '../interfaces'; @Injectable() export class GetHistoryMiddleware implements ChatMiddleware { @@ -21,6 +23,8 @@ export class GetHistoryMiddleware implements ChatMiddleware { constructor( @InjectRepository(MessageEntity) private readonly messages: MessageRepository, + @InjectRepository(ConversationFileEntity) + private readonly conversationFiles: ConversationFileRepository, ) {} order?: number = GetHistoryMiddleware.ORDER; @@ -28,22 +32,16 @@ export class GetHistoryMiddleware implements ChatMiddleware { async invoke(context: ChatContext, getContext: GetContext, next: ChatNextDelegate): Promise { const { conversationId, configuration } = context; - const history = new InternalChatHistory(conversationId, configuration.id, context, this.messages); + const history = new InternalChatHistory(conversationId, configuration.id, context, this.messages, this.conversationFiles); - await history.addMessage( - new HumanMessage({ - content: context.input, - }), - true, - context.editMessageId, - ); + await history.addMessage(new HumanMessage(context.input), true, context.editMessageId); context.history = history; await next(context); } } -class InternalChatHistory extends BaseListChatMessageHistory implements MessagesHistory { +class InternalChatHistory extends MessagesHistory { private readonly logger = new Logger(InternalChatHistory.name); private readonly tools: string[] = []; private readonly debug: string[] = []; @@ -51,13 +49,12 @@ class InternalChatHistory extends BaseListChatMessageHistory implements Messages private stored?: BaseMessage[]; private currentParentId?: number; - lc_namespace!: string[]; - constructor( private readonly conversationId: number, private readonly configurationId: number, private readonly context: ChatContext, private readonly messages: MessageRepository, + private readonly conversationFiles: ConversationFileRepository, ) { super(); @@ -103,26 +100,66 @@ class InternalChatHistory extends BaseListChatMessageHistory implements Messages } } + private async attachNewFilesToConversation(conversationId: number, messageId: number, files: ChatContext['files']) { + if (!files?.length) { + return; + } + + const fileIds = files.map((file) => file.id); + const existingFiles = await this.conversationFiles.find({ + where: { + conversationId, + fileId: In(fileIds), + }, + }); + + const existingFileIds = new Set(existingFiles.map((file) => file.fileId)); + const filesToSave = files + .filter((file) => !existingFileIds.has(file.id)) + .map((file) => ({ + conversationId, + messageId, + fileId: file.id, + })); + + const filesToUpdate = existingFiles + .filter((file) => file.messageId == null) + .map((file) => ({ + ...file, + messageId, + })); + + if (filesToUpdate.length > 0) { + await this.conversationFiles.save(filesToUpdate); + } + + if (filesToSave.length > 0) { + await this.conversationFiles.save(filesToSave); + } + } + async addMessage(message: BaseMessage, persistHuman?: boolean, editMessageId?: number): Promise { - const data = mapChatMessagesToStoredMessages([message]).map(({ type, data }) => ({ - type, + const data = { + type: message.getType(), + data: { + content: message.content, + }, conversation: { id: this.conversationId, }, - data, // The tools is used for the UI only to display the used tools for old conversations. - tools: isAIMessage(message) ? this.tools : [], + tools: message.isAI() ? this.tools : [], // The debug information are only relevant for AI messages. - debug: isAIMessage(message) ? this.debug : [], + debug: message.isAI() ? this.debug : [], // The sources information are only relevant for AI messages. - sources: isAIMessage(message) ? this.sources : [], - })); + sources: message.isAI() ? this.sources : [], + }; try { - if (isAIMessage(message)) { + if (message.isAI()) { this.publishSourcesReferences(); const entity = await this.messages.save({ - ...data[0], + ...data, parentId: this.currentParentId, configurationId: this.configurationId, }); @@ -153,9 +190,10 @@ class InternalChatHistory extends BaseListChatMessageHistory implements Messages const entity = await this.messages.save({ parentId: this.currentParentId, configurationId: this.configurationId, - ...data[0], + ...data, }); this.currentParentId = entity.id; + await this.attachNewFilesToConversation(entity.conversationId, entity.id, this.context.files); this.context.result.next({ type: 'saved', messageId: entity.id, messageType: 'human' }); } } catch (err) { @@ -164,7 +202,19 @@ class InternalChatHistory extends BaseListChatMessageHistory implements Messages } } -function isAIMessage(message: BaseMessage) { - // For whatever reason there are two kind of messages for that. - return is(message, AIMessage) || is(message, AIMessageChunk); +function mapStoredMessagesToChatMessages(messages: MessageEntity[]): BaseMessage[] { + return messages.map((message) => { + // TODO: maybe we should not save this json structure but migrate to a string column + const data = message.data as { content: string }; + const text = data.content; + + switch (message.type) { + case 'human': + return new HumanMessage(text); + case 'ai': + return new AIMessage(text); + default: + throw new Error(`Unsupported message type '${message.type}'.`); + } + }); } diff --git a/backend/src/domain/chat/middlewares/langfuse-middleware.ts b/backend/src/domain/chat/middlewares/langfuse-middleware.ts index 317d29547..9d67c10a8 100644 --- a/backend/src/domain/chat/middlewares/langfuse-middleware.ts +++ b/backend/src/domain/chat/middlewares/langfuse-middleware.ts @@ -14,8 +14,7 @@ export class LangfuseMiddleware implements ChatMiddleware { const secretKey = this.configService.get('LANGFUSE_SECRET_KEY'); const baseUrl = this.configService.get('LANGFUSE_BASE_URL', 'https://cloud.langfuse.com'); if (publicKey && secretKey && baseUrl) { - const { CallbackHandler } = await import('langfuse-langchain'); - context.callbacks.push(new CallbackHandler({ publicKey, secretKey, baseUrl })); + context.telemetry = true; } return next(context); diff --git a/backend/src/domain/chat/middlewares/summarize-history-middleware.ts b/backend/src/domain/chat/middlewares/summarize-history-middleware.ts index 13da8bf64..fe073ef41 100644 --- a/backend/src/domain/chat/middlewares/summarize-history-middleware.ts +++ b/backend/src/domain/chat/middlewares/summarize-history-middleware.ts @@ -1,9 +1,6 @@ -import { HumanMessage } from '@langchain/core/messages'; -import { StringOutputParser } from '@langchain/core/output_parsers'; -import { ChatPromptTemplate } from '@langchain/core/prompts'; import { forwardRef, Inject, Injectable, Logger, NotFoundException } from '@nestjs/common'; import { CommandBus, QueryBus } from '@nestjs/cqrs'; -import { is } from 'src/lib'; +import { generateText } from 'ai'; import { I18nService } from '../../../localization/i18n.service'; import { ChatContext, ChatMiddleware, ChatNextDelegate, GetContext } from '../interfaces'; import { GetConversation, GetConversationResponse } from '../use-cases'; @@ -29,7 +26,7 @@ export class SummarizeHistoryMiddleware implements ChatMiddleware { const allUserMessages = messages .reverse() - .filter((message) => is(message, HumanMessage)) + .filter((message) => message.isHuman()) .flatMap((humanMessage) => normalizedMessageContent(humanMessage.content) .filter((item) => item.type === 'text') @@ -53,16 +50,22 @@ export class SummarizeHistoryMiddleware implements ChatMiddleware { } const userMessages = await this.getUserMessages(context); + const historyPrompt = context.summaryConfig?.prompt ?? - "Summarize the following content ALWAYS in the same language as the content as short as possible in not more than 3 words. Write it as if it is Headline of an Article. Dont't use new lines: {content}"; - const prompt = ChatPromptTemplate.fromMessages([['user', historyPrompt]]); - const outputParser = new StringOutputParser(); - const outputChain = prompt.pipe(llm).pipe(outputParser); + "Summarize the following content ALWAYS in the same language as the content as short as possible in not more than 3 words. Write it as if it is Headline of an Article. Dont't use new lines!"; try { - const name = await outputChain.invoke({ content: userMessages.join(' ') }, { timeout: 60000 }); - return name ?? this.i18n.t('texts.chat.noSummary'); + const { text } = await generateText({ + model: llm.model, + prompt: [ + { role: 'system' as const, content: historyPrompt }, + { role: 'user' as const, content: userMessages.join(' ') }, + ], + ...llm.options, + }); + + return text ?? this.i18n.t('texts.chat.noSummary'); } catch (err) { this.logger.error('Failed to get conversation summary.', err); } diff --git a/backend/src/domain/chat/module.ts b/backend/src/domain/chat/module.ts index e25c8774f..796114b21 100644 --- a/backend/src/domain/chat/module.ts +++ b/backend/src/domain/chat/module.ts @@ -14,6 +14,7 @@ import { UsageRepository, UserGroupEntity, } from 'src/domain/database'; +import { ConversationFileEntity } from '../database/entities/conversation-file'; import { registerRepositoryForEntity } from '../database/typeorm.helper'; import { ChatCacheImpl } from './cache'; import { CHAT_MIDDLEWARES_TOKEN, ChatMiddleware } from './interfaces'; @@ -64,6 +65,7 @@ import { UserGroupEntity, BucketEntity, FileEntity, + ConversationFileEntity, ]), ], exports: [CallbackService], diff --git a/backend/src/domain/chat/use-cases/duplicate-conversation.ts b/backend/src/domain/chat/use-cases/duplicate-conversation.ts index f0187c76c..aef5c92d9 100644 --- a/backend/src/domain/chat/use-cases/duplicate-conversation.ts +++ b/backend/src/domain/chat/use-cases/duplicate-conversation.ts @@ -2,16 +2,8 @@ import { NotFoundException } from '@nestjs/common'; import { CommandHandler, ICommandHandler } from '@nestjs/cqrs'; import { InjectRepository } from '@nestjs/typeorm'; import { Like } from 'typeorm'; -import * as uuid from 'uuid'; -import { - BlobEntity, - ConversationEntity, - ConversationRepository, - FileEntity, - FileRepository, - MessageEntity, - MessageRepository, -} from '../../database'; +import { ConversationEntity, ConversationRepository, MessageEntity, MessageRepository } from '../../database'; +import { ConversationFileEntity, ConversationFileRepository } from '../../database/entities/conversation-file'; import { Conversation } from '../interfaces'; export class DuplicateConversationResponse { @@ -27,8 +19,8 @@ export class DuplicateConversationHandler implements ICommandHandler a.id - b.id); const sortedFiles = conversationEntity.files?.sort((a, b) => a.id - b.id) ?? []; - const newFiles = await Promise.all( - (sortedFiles || []).map(async (file) => { - const newFile = this.fileRepository.create({ - ...file, - id: undefined, - blobs: file.blobs.map((blob: BlobEntity) => ({ ...blob, id: uuid.v4() })), - externalDocumentId: file.externalDocumentId, - }); - - return this.fileRepository.save(newFile); - }), - ); - // It is kind of expensive to get all conversations, which have conflicting names // but since duplication is a rare event, this should be fine // (since we are looking for a fixed prefix, an index over the conversation names might be sensible @@ -78,7 +57,7 @@ export class DuplicateConversationHandler implements ICommandHandler ({ + conversationId: saved.id, + fileId: file.fileId, + messageId: file.messageId ? messageIdMap.get(file.messageId) : undefined, + })), + ); + return new DuplicateConversationResponse(saved); } } diff --git a/backend/src/domain/chat/use-cases/get-document.ts b/backend/src/domain/chat/use-cases/get-document.ts index 7311b7b4d..1a8a966bf 100644 --- a/backend/src/domain/chat/use-cases/get-document.ts +++ b/backend/src/domain/chat/use-cases/get-document.ts @@ -27,12 +27,12 @@ export class GetDocumentHandler implements IQueryHandler { + private async fetchDocument(documentUri: string, source: ExtensionSource, user: User): Promise { const response: GetExtensionResponse = await this.queryBus.execute( new GetExtension({ externalId: source.extensionExternalId }), ); - return await response.extension?.getDocument(documentUri); + return await response.extension?.getDocument(documentUri, user); } async execute(query: GetDocument): Promise { @@ -51,6 +51,6 @@ export class GetDocumentHandler implements IQueryHandler[], public readonly editMessageId?: number, + public readonly systemMessages?: string[], + public readonly configurationOverrides?: ConfigurationUserValuesModel['values'], ) {} } export class SendMessageResponse { - constructor(public readonly stream: Observable) {} + constructor( + public readonly stream: Observable, + public readonly abort: AbortController, + ) {} } @QueryHandler(SendMessage) @@ -53,7 +63,7 @@ export class SendMessageHandler implements IQueryHandler { - const { conversationId, input, user, files, editMessageId } = query; + const { conversationId, input, user, files, editMessageId, systemMessages, configurationOverrides } = query; // Get the conversation here, because we need the extension configuration. const { conversation }: GetConversationResponse = await this.queryBus.execute(new GetConversation(conversationId, user)); @@ -71,11 +81,16 @@ export class SendMessageHandler implements IQueryHandler((observer) => { const context: ChatContext = { - abort: new AbortController(), + abort, cache: this.cache, - callbacks: [], context: conversation.context || {}, conversationId: conversation.id, configuration: configuration, @@ -85,7 +100,7 @@ export class SendMessageHandler implements IQueryHandler this.store.getStore() as ChatContext; try { - const next = await this.buildPipeline(context, conversation, getContext); + const next = await this.buildPipeline( + context, + conversation, + getContext, + configurationUserOverrides ?? {}, + configurationOverrides ?? {}, + ); await next(context); } catch (err) { if (err instanceof Error) { @@ -123,25 +144,26 @@ export class SendMessageHandler implements IQueryHandler x?.[extension.id]), ); for (const middleware of extensionMiddlewares) { diff --git a/backend/src/domain/chat/utils.ts b/backend/src/domain/chat/utils.ts index 6a638e64e..758b9115c 100644 --- a/backend/src/domain/chat/utils.ts +++ b/backend/src/domain/chat/utils.ts @@ -1,42 +1,10 @@ -import type { MessageContent, MessageContentComplex, MessageContentText } from '@langchain/core/messages'; -import { AIMessageChunk } from '@langchain/core/messages'; -import { ChatGenerationChunk } from '@langchain/core/outputs'; -import { is, isArray, isString } from 'src/lib'; import { NormalizedMessageContents } from './interfaces'; -function isTextItem(item: MessageContentComplex): item is MessageContentText { - return !!(item as MessageContentText).text; -} - -export function normalizedMessageContent( - source: MessageContent | AIMessageChunk | ChatGenerationChunk, -): NormalizedMessageContents { +export function normalizedMessageContent(source: string): NormalizedMessageContents { const result: NormalizedMessageContents = []; - if (is(source, AIMessageChunk)) { - source = source.content; - } else if (is(source, ChatGenerationChunk)) { - source = source.message.content; - } - - if (isString(source)) { - if (source.length > 0) { - result.push({ type: 'text', text: source }); - } - } else if (isArray(source)) { - for (const item of source) { - if (item.type === 'image_url') { - if (isString(item.image_url)) { - result.push({ type: 'image_url', image: { url: item.image_url } }); - } else { - result.push({ type: 'image_url', image: { url: (item.image_url as { url: string }).url } }); - } - } else { - if (isTextItem(item)) { - result.push({ type: 'text', text: item.text }); - } - } - } + if (source.length > 0) { + result.push({ type: 'text', text: source }); } return result; diff --git a/backend/src/domain/database/entities/configuration.ts b/backend/src/domain/database/entities/configuration.ts index fb1f42b6f..4f79eb08b 100644 --- a/backend/src/domain/database/entities/configuration.ts +++ b/backend/src/domain/database/entities/configuration.ts @@ -19,6 +19,12 @@ import { UserGroupEntity } from './user-group'; export type ConfigurationRepository = Repository; +export enum ConfigurationStatus { + ENABLED = 'enabled', + DISABLED = 'disabled', + DELETED = 'deleted', +} + @Entity({ name: 'configurations', schema }) export class ConfigurationEntity { @PrimaryGeneratedColumn() @@ -30,8 +36,12 @@ export class ConfigurationEntity { @Column({ default: '' }) description!: string; - @Column() - enabled!: boolean; + @Column({ + type: 'enum', + enum: ConfigurationStatus, + default: ConfigurationStatus.ENABLED, + }) + status!: ConfigurationStatus; @Column('text', { nullable: true }) agentName?: string; diff --git a/backend/src/domain/database/entities/conversation-file.ts b/backend/src/domain/database/entities/conversation-file.ts new file mode 100644 index 000000000..f8ecf888a --- /dev/null +++ b/backend/src/domain/database/entities/conversation-file.ts @@ -0,0 +1,35 @@ +import { Column, Entity, JoinColumn, ManyToOne, PrimaryGeneratedColumn, Repository, Unique } from 'typeorm'; +import { schema } from '../typeorm.helper'; +import { ConversationEntity } from './conversation'; +import { FileEntity } from './file'; +import { MessageEntity } from './message'; + +export type ConversationFileRepository = Repository; + +@Entity({ name: 'conversations_files', schema }) +@Unique(['conversationId', 'fileId']) +export class ConversationFileEntity { + @PrimaryGeneratedColumn() + id!: number; + + @ManyToOne(() => ConversationEntity, (conversation) => conversation.files, { onDelete: 'CASCADE' }) + @JoinColumn({ name: 'conversationId' }) + conversation!: ConversationEntity; + + @Column({ nullable: false }) + conversationId!: number; + + @ManyToOne(() => FileEntity, (user) => user.conversations, { onDelete: 'CASCADE' }) + @JoinColumn({ name: 'fileId' }) + file!: FileEntity; + + @Column({ nullable: false }) + fileId!: number; + + @ManyToOne(() => MessageEntity, (message) => message.files, { onDelete: 'CASCADE' }) + @JoinColumn({ name: 'messageId' }) + message?: MessageEntity; + + @Column({ nullable: true }) + messageId?: number; +} diff --git a/backend/src/domain/database/entities/conversation.ts b/backend/src/domain/database/entities/conversation.ts index 128f27cb3..54822b099 100644 --- a/backend/src/domain/database/entities/conversation.ts +++ b/backend/src/domain/database/entities/conversation.ts @@ -1,7 +1,7 @@ import { Column, CreateDateColumn, Entity, ManyToOne, OneToMany, PrimaryGeneratedColumn, UpdateDateColumn } from 'typeorm'; import { schema } from '../typeorm.helper'; import { ConfigurationEntity } from './configuration'; -import { FileEntity } from './file'; +import { ConversationFileEntity } from './conversation-file'; import { MessageEntity } from './message'; import { UserEntity } from './user'; @@ -55,6 +55,6 @@ export class ConversationEntity { @UpdateDateColumn({ type: 'timestamptz' }) updatedAt!: Date; - @OneToMany(() => FileEntity, (file) => file.conversation, { cascade: true }) - files?: FileEntity[]; + @OneToMany(() => ConversationFileEntity, (cf) => cf.conversation) + files!: ConversationFileEntity[]; } diff --git a/backend/src/domain/database/entities/file.ts b/backend/src/domain/database/entities/file.ts index 05b9843b5..d51dd9f87 100644 --- a/backend/src/domain/database/entities/file.ts +++ b/backend/src/domain/database/entities/file.ts @@ -11,7 +11,7 @@ import { import { schema } from '../typeorm.helper'; import { BlobEntity } from './blob'; import { BucketEntity } from './bucket'; -import { ConversationEntity } from './conversation'; +import { ConversationFileEntity } from './conversation-file'; import { ExtensionEntity } from './extension'; import { UserEntity } from './user'; @@ -65,15 +65,9 @@ export class FileEntity { @UpdateDateColumn({ type: 'timestamptz' }) updatedAt!: Date; - @ManyToOne(() => ConversationEntity, { onDelete: 'CASCADE' }) - conversation?: ConversationEntity; - - @Column({ nullable: true }) - conversationId?: number; + @OneToMany(() => ConversationFileEntity, (cf) => cf.file) + conversations!: ConversationFileEntity[]; @Column() uploadStatus!: FileUploadStatus; - - @Column({ type: 'int', name: 'docId' }) - externalDocumentId!: number; } diff --git a/backend/src/domain/database/entities/index.ts b/backend/src/domain/database/entities/index.ts index 3630068f2..6aa681491 100644 --- a/backend/src/domain/database/entities/index.ts +++ b/backend/src/domain/database/entities/index.ts @@ -11,3 +11,5 @@ export * from './setting'; export * from './usage'; export * from './user'; export * from './user-group'; +export * from './prompt'; +export * from './prompt-category'; diff --git a/backend/src/domain/database/entities/message.ts b/backend/src/domain/database/entities/message.ts index 044783f4b..576574c5b 100644 --- a/backend/src/domain/database/entities/message.ts +++ b/backend/src/domain/database/entities/message.ts @@ -12,6 +12,7 @@ import { Source } from 'src/domain/chat'; import { schema } from '../typeorm.helper'; import { ConfigurationEntity } from './configuration'; import { ConversationEntity } from './conversation'; +import { ConversationFileEntity } from './conversation-file'; export type ExtensionSource = Source & { extensionExternalId: string }; @@ -66,6 +67,9 @@ export class MessageEntity { @Column() conversationId!: number; + @OneToMany(() => ConversationFileEntity, (cf) => cf.message) + files!: ConversationFileEntity[]; + @CreateDateColumn({ type: 'timestamptz' }) createdAt!: Date; diff --git a/backend/src/domain/database/entities/prompt-category.ts b/backend/src/domain/database/entities/prompt-category.ts new file mode 100644 index 000000000..267364263 --- /dev/null +++ b/backend/src/domain/database/entities/prompt-category.ts @@ -0,0 +1,24 @@ +import { Column, CreateDateColumn, Entity, PrimaryColumn, UpdateDateColumn } from 'typeorm'; +import { VisibilityType } from '../../prompt/interfaces'; +import { schema } from '../typeorm.helper'; + +@Entity({ name: 'prompt-categories', schema }) +export class PromptCategoryEntity { + @PrimaryColumn() + label!: string; + + @Column() + description?: string; + + @Column() + creationDate!: Date; + + @Column() + visibility!: VisibilityType; + + @CreateDateColumn({ type: 'timestamptz' }) + createdAt!: Date; + + @UpdateDateColumn({ type: 'timestamptz' }) + updatedAt!: Date; +} diff --git a/backend/src/domain/database/entities/prompt.ts b/backend/src/domain/database/entities/prompt.ts new file mode 100644 index 000000000..a68cb0eb1 --- /dev/null +++ b/backend/src/domain/database/entities/prompt.ts @@ -0,0 +1,35 @@ +import { Column, CreateDateColumn, Entity, JoinTable, ManyToMany, PrimaryGeneratedColumn, UpdateDateColumn } from 'typeorm'; +import { VisibilityType } from '../../prompt/interfaces'; +import { schema } from '../typeorm.helper'; +import { PromptCategoryEntity } from './prompt-category'; + +@Entity({ name: 'prompts', schema }) +export class PromptEntity { + @PrimaryGeneratedColumn() + id!: number; + + @Column({ nullable: false }) + title!: string; + + @Column({ nullable: true }) + description?: string; + + @Column({ nullable: false }) + content!: string; + + @ManyToMany(() => PromptCategoryEntity) + @JoinTable() + categories?: PromptCategoryEntity[]; + + @Column() + visibility!: VisibilityType; + + @Column({ nullable: true }) + rating!: number; + + @CreateDateColumn({ type: 'timestamptz' }) + createdAt!: Date; + + @UpdateDateColumn({ type: 'timestamptz' }) + updatedAt!: Date; +} diff --git a/backend/src/domain/extensions/interfaces.ts b/backend/src/domain/extensions/interfaces.ts index 7bacf396d..c20e6ead4 100644 --- a/backend/src/domain/extensions/interfaces.ts +++ b/backend/src/domain/extensions/interfaces.ts @@ -1,4 +1,3 @@ -import { Embeddings } from '@langchain/core/embeddings'; import { ChatMiddleware, ExtensionUserArgumentValues } from '../chat'; import { ChatSuggestion } from '../shared'; import { User } from '../users'; @@ -153,14 +152,6 @@ export interface ExtensionSpec { triggers?: string[]; } -export interface ExtensionEmbeddings { - // The embedding. - embeddings: Embeddings; - - // The optional name. - name?: string; -} - export type ExtensionState = { [param: string]: any; changed?: boolean; @@ -224,31 +215,37 @@ export class ConfiguredExtension { - return this.extension.fixedValues ?? {}; - } - async getChunks(documentUri: string, chunkUris: string[]): Promise { return this.extension.getChunks?.(this.entity.values, documentUri, chunkUris); } - async getDocument(documentUri: string): Promise { - return this.extension.getDocument?.(this.entity.values, documentUri); + async getDocument(documentUri: string, user: User): Promise { + return this.extension.getDocument?.(this.entity.values, documentUri, user); + } + + private mergeExtensionUserValues(...extensionUserValues: (ExtensionUserArgumentValues | undefined)[]) { + const merged: ExtensionConfiguration = {}; + extensionUserValues + .filter((values) => values != null) + .forEach((values) => { + Object.entries(values).forEach(([key, value]) => { + // eslint-disable-next-line @typescript-eslint/no-unsafe-assignment + merged[key] = value; + }); + }); + + return merged as T; } getMiddlewares( user: User, userArgumentValues?: ExtensionUserArgumentValues, - userConfiguredValues?: ExtensionUserArgumentValues, + ...argumentValues: ExtensionUserArgumentValues[] ): Promise { if (!this.extension.getMiddlewares) { return Promise.resolve([]); } - - this.entity.values = { - ...(this.entity.values ?? {}), - ...(userConfiguredValues ?? {}), - }; + this.entity.values = this.mergeExtensionUserValues(this.entity.values, ...argumentValues); return this.extension.getMiddlewares(user, this.entity, userArgumentValues); } @@ -282,15 +279,13 @@ export interface Extension< buildSpec?(extension: ExtensionEntity, throwOnError: boolean, forceRebuild: boolean): Promise; getChunks?(configuration: TConfig, documentUri: string, chunkUris: string[]): Promise; - getDocument?(configuration: TConfig, documentUri: string): Promise; + getDocument?(configuration: TConfig, documentUri: string, user: User): Promise; fixedValues?: Partial; test?(configuration: TConfig): Promise; getMiddlewares(user: User, extension: ExtensionEntity, userArgumentValues?: TUserValues): Promise; - - getEmbedding?(user: User, configuration: TConfig): Promise; } export const EXTENSION_METADATA = 'EXTENSION'; diff --git a/backend/src/domain/extensions/module.ts b/backend/src/domain/extensions/module.ts index c13add3c5..94b7dea40 100644 --- a/backend/src/domain/extensions/module.ts +++ b/backend/src/domain/extensions/module.ts @@ -2,7 +2,7 @@ import { Module } from '@nestjs/common'; import { ConfigModule } from '@nestjs/config'; import { CqrsModule } from '@nestjs/cqrs'; import { TypeOrmModule } from '@nestjs/typeorm'; -import { BucketEntity, ConfigurationEntity, ExtensionEntity, UserGroupEntity } from 'src/domain/database'; +import { BucketEntity, ConfigurationEntity, ConversationEntity, ExtensionEntity, UserGroupEntity } from 'src/domain/database'; import { ConfigurationUserEntity } from '../database/entities/configuration-user'; import { ExplorerService } from './services'; import { @@ -28,7 +28,14 @@ import { UpdateConfigurationUserValuesHandler } from './use-cases/update-configu imports: [ ConfigModule, CqrsModule, - TypeOrmModule.forFeature([BucketEntity, ConfigurationEntity, ConfigurationUserEntity, ExtensionEntity, UserGroupEntity]), + TypeOrmModule.forFeature([ + BucketEntity, + ConfigurationEntity, + ConfigurationUserEntity, + ConversationEntity, + ExtensionEntity, + UserGroupEntity, + ]), ], providers: [ CreateConfigurationHandler, diff --git a/backend/src/domain/extensions/use-cases/create-configuration.ts b/backend/src/domain/extensions/use-cases/create-configuration.ts index 0cffe1db5..60bb8b52c 100644 --- a/backend/src/domain/extensions/use-cases/create-configuration.ts +++ b/backend/src/domain/extensions/use-cases/create-configuration.ts @@ -1,7 +1,13 @@ import { CommandHandler, ICommandHandler } from '@nestjs/cqrs'; import { InjectRepository } from '@nestjs/typeorm'; import { In } from 'typeorm'; -import { ConfigurationEntity, ConfigurationRepository, UserGroupEntity, UserGroupRepository } from 'src/domain/database'; +import { + ConfigurationEntity, + ConfigurationRepository, + ConfigurationStatus, + UserGroupEntity, + UserGroupRepository, +} from 'src/domain/database'; import { assignDefined } from 'src/lib'; import { ConfigurationModel } from '../interfaces'; import { buildConfiguration } from './utils'; @@ -63,7 +69,7 @@ export class CreateConfigurationHandler implements ICommandHandler { - let result: DeleteResult; - + const { id } = command; const queryRunner = this.dataSource.createQueryRunner(); await queryRunner.connect(); + await queryRunner.startTransaction(); try { - await queryRunner.manager.delete(ConversationEntity, { configurationId: command.id, llm: IsNull(), name: IsNull() }); - result = await queryRunner.manager.delete(ConfigurationEntity, { id: command.id }); + // First, we try to actually delete the assistant. This will work if no messages for this assistant exist. + // The empty conversation must be deleted, if it references the assistant. + await queryRunner.manager.delete(ConversationEntity, { configurationId: id, llm: IsNull(), name: IsNull() }); + await queryRunner.manager.delete(ConfigurationEntity, { id: command.id }); await queryRunner.commitTransaction(); - } catch (error) { + await queryRunner.release(); + return; + } catch (_error) { await queryRunner.rollbackTransaction(); - if (error instanceof QueryFailedError) { - throw new BadRequestException(this.i18n.t('texts.chat.errorConfigurationUsed')); - } else { - throw error; + } + + await queryRunner.startTransaction(); + try { + // If it does not work, because there are still messages referring to them, + // we just mark the configuration as deleted. + // That will only have the effect that the configuration will not be shown in any user facing menu, + // but is still available for the existing messages to reference to. + // For conversations which have this assistant as the active one, we need to supply a replacement. + // We will just use the first enabled assistant. If the user tries to delete the last one, we show an error. + const toBeDeleted = await queryRunner.manager.findOne(ConfigurationEntity, { + where: { id }, + relations: ['conversations'], + }); + if (!toBeDeleted) { + throw new NotFoundException(); + } + const replacement = await queryRunner.manager.findOne(ConfigurationEntity, { + where: { id: Not(id), status: ConfigurationStatus.ENABLED }, + order: { id: 'ASC' }, + }); + if (!replacement) { + throw new BadRequestException(this.i18n.t('texts.chat.errorLastConfigurationdDeleted')); } + + await queryRunner.manager.delete(ConversationEntity, { configurationId: id, llm: IsNull(), name: IsNull() }); + if (toBeDeleted.conversations) { + for (const conversation of toBeDeleted.conversations) { + conversation.configuration = replacement; + await queryRunner.manager.update( + ConversationEntity, + { id: conversation.id }, + { + configurationId: replacement.id, + updatedAt: () => '"updatedAt"', + }, + ); + } + } + assignDefined(toBeDeleted, { + status: ConfigurationStatus.DELETED, + conversations: [], + }); + + await queryRunner.manager.save(ConfigurationEntity, toBeDeleted); + + await queryRunner.commitTransaction(); + } catch (error) { + await queryRunner.rollbackTransaction(); + throw error; } finally { await queryRunner.release(); } - - if (!result.affected) { - throw new NotFoundException(); - } } } diff --git a/backend/src/domain/extensions/use-cases/duplicate-configuration.ts b/backend/src/domain/extensions/use-cases/duplicate-configuration.ts index 37bdd076f..109daad52 100644 --- a/backend/src/domain/extensions/use-cases/duplicate-configuration.ts +++ b/backend/src/domain/extensions/use-cases/duplicate-configuration.ts @@ -1,8 +1,15 @@ import { NotFoundException } from '@nestjs/common'; import { CommandHandler, ICommandHandler } from '@nestjs/cqrs'; import { InjectRepository } from '@nestjs/typeorm'; +import { Not } from 'typeorm'; import { assignDefined } from '../../../lib'; -import { ConfigurationEntity, ConfigurationRepository, ExtensionEntity, ExtensionRepository } from '../../database'; +import { + ConfigurationEntity, + ConfigurationRepository, + ConfigurationStatus, + ExtensionEntity, + ExtensionRepository, +} from '../../database'; import { ConfigurationModel } from '../interfaces'; import { buildConfiguration } from './utils'; @@ -26,7 +33,7 @@ export class DuplicateConfigurationHandler implements ICommandHandler { const { id } = command; const configuration = await this.configurations.findOne({ - where: { id }, + where: { id, status: Not(ConfigurationStatus.DELETED) }, relations: { extensions: true, userGroups: true, @@ -43,7 +50,7 @@ export class DuplicateConfigurationHandler implements ICommandHandler { constructor( @InjectRepository(ConfigurationEntity) - private readonly extensions: ConfigurationRepository, + private readonly configurations: ConfigurationRepository, ) {} async execute(request: GetConfiguration): Promise { const { id } = request; - const entity = await this.extensions.findOneBy({ id }); + const entity = await this.configurations.findOneBy({ id, status: Not(ConfigurationStatus.DELETED) }); if (!entity) { throw new NotFoundException(`Configuration with id ${id} was not found`); diff --git a/backend/src/domain/extensions/use-cases/get-configurations.ts b/backend/src/domain/extensions/use-cases/get-configurations.ts index 312d5f788..d2689577e 100644 --- a/backend/src/domain/extensions/use-cases/get-configurations.ts +++ b/backend/src/domain/extensions/use-cases/get-configurations.ts @@ -1,6 +1,7 @@ import { IQueryHandler, QueryHandler } from '@nestjs/cqrs'; import { InjectRepository } from '@nestjs/typeorm'; -import { BUILTIN_USER_GROUP_ADMIN, ConfigurationEntity, ConfigurationRepository } from 'src/domain/database'; +import { Not } from 'typeorm'; +import { BUILTIN_USER_GROUP_ADMIN, ConfigurationEntity, ConfigurationRepository, ConfigurationStatus } from 'src/domain/database'; import { User } from 'src/domain/users'; import { ConfigurationModel } from '../interfaces'; import { ExplorerService } from '../services'; @@ -30,6 +31,7 @@ export class GetConfigurationsHandler implements IQueryHandler e.enabled); + entities = entities.filter((e) => e.status === ConfigurationStatus.ENABLED); } const result = await Promise.all(entities.map((e) => buildConfiguration(e, this.extensionExplorer, withExtensions, enabled))); diff --git a/backend/src/domain/extensions/use-cases/update-configuration.ts b/backend/src/domain/extensions/use-cases/update-configuration.ts index c3642ae21..620b98574 100644 --- a/backend/src/domain/extensions/use-cases/update-configuration.ts +++ b/backend/src/domain/extensions/use-cases/update-configuration.ts @@ -1,8 +1,14 @@ import { NotFoundException } from '@nestjs/common'; import { CommandHandler, ICommandHandler } from '@nestjs/cqrs'; import { InjectRepository } from '@nestjs/typeorm'; -import { In } from 'typeorm'; -import { ConfigurationEntity, ConfigurationRepository, UserGroupEntity, UserGroupRepository } from 'src/domain/database'; +import { In, Not } from 'typeorm'; +import { + ConfigurationEntity, + ConfigurationRepository, + ConfigurationStatus, + UserGroupEntity, + UserGroupRepository, +} from 'src/domain/database'; import { assignDefined } from 'src/lib'; import { ConfigurationModel } from '../interfaces'; import { buildConfiguration } from './utils'; @@ -57,7 +63,7 @@ export class UpdateConfigurationHandler implements ICommandHandler { - const { userGroupsIds, extensions: configuredExtensions, ...other } = source; + const { userGroupsIds, extensions: configuredExtensions, status, ...other } = source; const extensions = withExtensions && extensionExplorer && configuredExtensions ? await Promise.all( - configuredExtensions.map((extensionEntity) => { - const extensionConfiguration = extensionExplorer.getExtension(extensionEntity.name); - if (extensionConfiguration && (!onlyEnabledExtensions || extensionEntity.enabled)) { - return buildExtension(extensionEntity, extensionConfiguration); - } - }, [] as ConfiguredExtension[]), + configuredExtensions + .map((extensionEntity) => { + const extensionConfiguration = extensionExplorer.getExtension(extensionEntity.name); + if (extensionConfiguration && (!onlyEnabledExtensions || extensionEntity.enabled)) { + return buildExtension(extensionEntity, extensionConfiguration); + } + }, [] as ConfiguredExtension[]) + .filter((x) => x !== undefined), ) : []; - return { ...other, userGroupsIds: userGroupsIds || [], extensions: extensions.filter((x) => !!x) }; + return { + ...other, + enabled: status === ConfigurationStatus.ENABLED, + userGroupsIds: userGroupsIds || [], + extensions: extensions.filter((x) => !!x), + }; } diff --git a/backend/src/domain/files/interfaces.ts b/backend/src/domain/files/interfaces.ts index d5739b334..9fe93fd28 100644 --- a/backend/src/domain/files/interfaces.ts +++ b/backend/src/domain/files/interfaces.ts @@ -70,8 +70,6 @@ export interface UploadedFile { // The status of the file in relation to the RAG-Service uploadStatus: FileUploadStatus; - - externalDocumentId: number; } export interface SearchResult { diff --git a/backend/src/domain/files/module.ts b/backend/src/domain/files/module.ts index 48ae61c4a..de64fa96f 100644 --- a/backend/src/domain/files/module.ts +++ b/backend/src/domain/files/module.ts @@ -2,6 +2,7 @@ import { Module } from '@nestjs/common'; import { CqrsModule } from '@nestjs/cqrs'; import { TypeOrmModule } from '@nestjs/typeorm'; import { BlobEntity, BucketEntity, ExtensionEntity, FileEntity } from 'src/domain/database'; +import { ConversationFileEntity } from '../database/entities/conversation-file'; import { CreateBucketHandler, DeleteBucketHandler, @@ -9,6 +10,7 @@ import { GetBucketHandler, GetBucketsHandler, GetDocumentContentHandler, + GetDocumentPdfHandler, GetFilesHandler, GetFileTypesHandler, SearchFilesHandler, @@ -18,7 +20,10 @@ import { } from './use-cases'; @Module({ - imports: [CqrsModule, TypeOrmModule.forFeature([BucketEntity, FileEntity, ExtensionEntity, BlobEntity])], + imports: [ + CqrsModule, + TypeOrmModule.forFeature([BucketEntity, FileEntity, ExtensionEntity, BlobEntity, ConversationFileEntity]), + ], providers: [ CreateBucketHandler, DeleteBucketHandler, @@ -26,6 +31,7 @@ import { GetBucketHandler, GetBucketsHandler, GetDocumentContentHandler, + GetDocumentPdfHandler, GetFilesHandler, GetFileTypesHandler, SearchFilesHandler, diff --git a/backend/src/domain/files/use-cases/delete-bucket.ts b/backend/src/domain/files/use-cases/delete-bucket.ts index cd140bdf1..ef95647aa 100644 --- a/backend/src/domain/files/use-cases/delete-bucket.ts +++ b/backend/src/domain/files/use-cases/delete-bucket.ts @@ -1,7 +1,8 @@ -import { NotFoundException } from '@nestjs/common'; +import { Logger, NotFoundException } from '@nestjs/common'; import { CommandHandler, ICommandHandler } from '@nestjs/cqrs'; import { InjectRepository } from '@nestjs/typeorm'; import { BucketEntity, BucketRepository } from 'src/domain/database'; +import { ResponseError } from './generated'; import { buildClient } from './utils'; export class DeleteBucket { @@ -12,6 +13,8 @@ export class DeleteBucketResponse {} @CommandHandler(DeleteBucket) export class DeleteBucketHandler implements ICommandHandler { + private readonly logger = new Logger(DeleteBucketHandler.name); + constructor( @InjectRepository(BucketEntity) private readonly buckets: BucketRepository, @@ -30,7 +33,16 @@ export class DeleteBucketHandler implements ICommandHandler { - const { id, source } = command; + const { id, source, conversationId } = command; const entity = await this.files.findOne({ where: { id }, @@ -50,12 +54,19 @@ export class DeleteFileHandler implements ICommandHandler 0) { + return new DeleteFileResponse(); + } } + await api?.deleteFile(entity.id.toString(), entity.bucket?.indexName); await this.files.remove(entity); } catch (err) { this.logger.error('Failed to delete file from RAG server.', err); diff --git a/backend/src/domain/files/use-cases/generated/apis/FilesApi.ts b/backend/src/domain/files/use-cases/generated/apis/FilesApi.ts index c00fc62e9..e7909f161 100644 --- a/backend/src/domain/files/use-cases/generated/apis/FilesApi.ts +++ b/backend/src/domain/files/use-cases/generated/apis/FilesApi.ts @@ -36,6 +36,10 @@ export interface DeleteFileRequest { indexName?: string | null; } +export interface GetDocumentPdfRequest { + docId: string; +} + export interface GetDocumentsContentRequest { chunkIds: Array; indexName?: string | null; @@ -111,6 +115,45 @@ export class FilesApi extends runtime.BaseAPI { return await response.value(); } + /** + * Get the document\'s pdf by its ID. + * Get Document Pdf + */ + async getDocumentPdfRaw(requestParameters: GetDocumentPdfRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise> { + if (requestParameters['docId'] == null) { + throw new runtime.RequiredError( + 'docId', + 'Required parameter "docId" was null or undefined when calling getDocumentPdf().' + ); + } + + const queryParameters: any = {}; + + if (requestParameters['docId'] != null) { + queryParameters['doc_id'] = requestParameters['docId']; + } + + const headerParameters: runtime.HTTPHeaders = {}; + + const response = await this.request({ + path: `/documents/pdf`, + method: 'GET', + headers: headerParameters, + query: queryParameters, + }, initOverrides); + + return new runtime.BlobApiResponse(response); + } + + /** + * Get the document\'s pdf by its ID. + * Get Document Pdf + */ + async getDocumentPdf(docId: string, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise { + const response = await this.getDocumentPdfRaw({ docId: docId }, initOverrides); + return await response.value(); + } + /** * Get the documents content by their IDs. * Get Documents Content diff --git a/backend/src/domain/files/use-cases/generated/models/DocumentDto.ts b/backend/src/domain/files/use-cases/generated/models/DocumentDto.ts index f1332b785..4ff692b4e 100644 --- a/backend/src/domain/files/use-cases/generated/models/DocumentDto.ts +++ b/backend/src/domain/files/use-cases/generated/models/DocumentDto.ts @@ -43,6 +43,12 @@ export interface DocumentDto { * @memberof DocumentDto */ link: string | null; + /** + * Indicates if the document is available + * @type {boolean} + * @memberof DocumentDto + */ + downloadAvailable: boolean; } /** @@ -53,6 +59,7 @@ export function instanceOfDocumentDto(value: object): value is DocumentDto { if (!('name' in value) || value['name'] === undefined) return false; if (!('mimeType' in value) || value['mimeType'] === undefined) return false; if (!('link' in value) || value['link'] === undefined) return false; + if (!('downloadAvailable' in value) || value['downloadAvailable'] === undefined) return false; return true; } @@ -70,6 +77,7 @@ export function DocumentDtoFromJSONTyped(json: any, ignoreDiscriminator: boolean 'name': json['name'], 'mimeType': json['mimeType'], 'link': json['link'], + 'downloadAvailable': json['downloadAvailable'], }; } @@ -83,6 +91,7 @@ export function DocumentDtoToJSON(value?: DocumentDto | null): any { 'name': value['name'], 'mimeType': value['mimeType'], 'link': value['link'], + 'downloadAvailable': value['downloadAvailable'], }; } diff --git a/backend/src/domain/files/use-cases/get-document-content.ts b/backend/src/domain/files/use-cases/get-document-content.ts index fc8500fb6..59eca1798 100644 --- a/backend/src/domain/files/use-cases/get-document-content.ts +++ b/backend/src/domain/files/use-cases/get-document-content.ts @@ -25,8 +25,6 @@ export class GetDocumentContentHandler implements IQueryHandler { const { bucketId, chunkIds } = query; - console.log(`getting chunks for bucket ${bucketId} and chunkIds ${chunkIds.join(',')}`); - if (!chunkIds || chunkIds.length === 0) { throw new BadRequestException('Chunk IDs are required'); } @@ -35,7 +33,7 @@ export class GetDocumentContentHandler implements IQueryHandler { + constructor( + @InjectRepository(BucketEntity) + private readonly bucketRepository: BucketRepository, + @InjectRepository(FileEntity) + private readonly fileRepository: FileRepository, + ) {} + + async execute(query: GetDocumentPdf): Promise { + const { bucketId, docId, user } = query; + + const bucket = await this.bucketRepository.findOneBy({ + id: bucketId, + }); + if (!bucket) { + throw new NotFoundException(`Cannot find a bucket with id ${bucketId}`); + } + + // assure that the user may access the file (this is necessary since the doc_ids are predictable) + if (bucket.type === 'user' || bucket.type === 'conversation') { + const file = await this.fileRepository.findOneBy({ id: parseInt(docId, 10) }); + if (file?.userId !== user.id) { + // either file does not exist or the user may not see it. So 404 is the correct response + throw new NotFoundException(`Cannot find a document with id ${docId}`); + } + } + + const api = buildClient(bucket); + const result = await api?.getDocumentPdf(docId); + return new GetDocumentPdfResponse(result ?? null); + } +} diff --git a/backend/src/domain/files/use-cases/get-files.spec.ts b/backend/src/domain/files/use-cases/get-files.spec.ts index 2c8f2494a..f084b3fa3 100644 --- a/backend/src/domain/files/use-cases/get-files.spec.ts +++ b/backend/src/domain/files/use-cases/get-files.spec.ts @@ -1,14 +1,17 @@ import { NotFoundException } from '@nestjs/common'; import { Test, TestingModule } from '@nestjs/testing'; import { getRepositoryToken } from '@nestjs/typeorm'; -import { FindManyOptions } from 'typeorm'; +import { FindManyOptions, FindOptionsWhere } from 'typeorm'; +import { FindOperator } from 'typeorm/find-options/FindOperator'; import { User } from 'src/domain/users'; import { BucketEntity, BucketRepository, FileEntity, FileRepository } from '../../database'; +import { ConversationFileEntity, ConversationFileRepository } from '../../database/entities/conversation-file'; import { GetFiles, GetFilesHandler, GetFilesResponse } from './get-files'; describe('Get Files', () => { let bucketRepository: BucketRepository; let fileRepository: FileRepository; + let conversationFileRepository: ConversationFileRepository; let handler: GetFilesHandler; const mockUser: User = { @@ -25,16 +28,18 @@ describe('Get Files', () => { userGroupId: 'grou21', }; - const findFiles = (statement: FindManyOptions | undefined, users: FileEntity[]): Promise => { + const findFiles = (statement: FindManyOptions | undefined, files: FileEntity[]): Promise => { const whereStatement = Array.isArray(statement?.where) ? statement.where.reduce((prev, curr) => ({ ...prev, ...curr }), {}) : statement?.where; return Promise.resolve( - Object.entries(whereStatement ?? {}).reduce( - (filteredUsers, [whereKey, whereValue]) => - filteredUsers.filter((user) => user[whereKey as keyof FileEntity] === whereValue), - users, - ), + Object.entries(whereStatement ?? {}).reduce((filteredFiles, [whereKey, whereValue]) => { + return filteredFiles.filter((file) => + whereValue instanceof FindOperator + ? (whereValue.value as number[]).includes(file[whereKey as keyof FileEntity] as number) + : file[whereKey as keyof FileEntity] === whereValue, + ); + }, files), ); }; @@ -62,12 +67,19 @@ describe('Get Files', () => { count: jest.fn(), }, }, + { + provide: getRepositoryToken(ConversationFileEntity), + useValue: { + findBy: jest.fn(), + }, + }, ], }).compile(); handler = module.get(GetFilesHandler); bucketRepository = module.get(getRepositoryToken(BucketEntity)); fileRepository = module.get(getRepositoryToken(FileEntity)); + conversationFileRepository = module.get(getRepositoryToken(ConversationFileEntity)); }); it('should return files for a general bucket', async () => { const files = [ @@ -78,6 +90,7 @@ describe('Get Files', () => { jest.spyOn(fileRepository, 'count').mockImplementation((query) => countFiles(query, files)); jest.spyOn(fileRepository, 'find').mockImplementation((query) => findFiles(query, files)); + jest.spyOn(conversationFileRepository, 'findBy').mockImplementation(() => Promise.resolve([])); jest .spyOn(bucketRepository, 'findOneBy') .mockImplementation(() => Promise.resolve({ id: 1, type: 'general' } as BucketEntity)); @@ -93,14 +106,19 @@ describe('Get Files', () => { it('should return files for conversation bucket', async () => { const files = [ - { id: 1, userId: mockUser.id, bucketId: 1, conversationId: 1 }, - { id: 2, userId: mockUser.id, bucketId: 1, conversationId: 2 }, - { id: 3, userId: mockUserDifferent.id, bucketId: 1, conversationId: 3 }, - { id: 4, userId: mockUser.id, bucketId: 2, conversationId: 1 }, + { id: 1, userId: mockUser.id, bucketId: 1, conversations: [{ conversationId: 1, fileId: 1 }] }, + { id: 2, userId: mockUser.id, bucketId: 1, conversations: [{ conversationId: 2, fileId: 2 }] }, + { id: 3, userId: mockUserDifferent.id, bucketId: 1, conversations: [{ conversationId: 3, fileId: 3 }] }, + { id: 4, userId: mockUser.id, bucketId: 2, conversations: [{ conversationId: 1, fileId: 4 }] }, ] as FileEntity[]; jest.spyOn(fileRepository, 'count').mockImplementation((query) => countFiles(query, files)); jest.spyOn(fileRepository, 'find').mockImplementation((query) => findFiles(query, files)); + jest.spyOn(conversationFileRepository, 'findBy').mockImplementation((query) => { + const conversationId = (query as FindOptionsWhere).conversationId; + const result = files.filter((x) => x.conversations.find((y) => y.conversationId === conversationId)); + return Promise.resolve(result.flatMap((x) => x.conversations)); + }); jest .spyOn(bucketRepository, 'findOneBy') .mockImplementation(() => Promise.resolve({ id: 1, type: 'conversation' } as BucketEntity)); @@ -118,10 +136,10 @@ describe('Get Files', () => { it('should return files of user for conversation bucket and conversation id', async () => { const files = [ - { id: 1, userId: mockUser.id, bucketId: 1, conversationId: 1 }, - { id: 2, userId: mockUser.id, bucketId: 1, conversationId: 2 }, - { id: 3, userId: mockUserDifferent.id, bucketId: 1, conversationId: 3 }, - { id: 4, userId: mockUser.id, bucketId: 2, conversationId: 1 }, + { id: 1, userId: mockUser.id, bucketId: 1, conversations: [{ conversationId: 1, fileId: 1 }] }, + { id: 2, userId: mockUser.id, bucketId: 1, conversations: [{ conversationId: 2, fileId: 2 }] }, + { id: 3, userId: mockUserDifferent.id, bucketId: 1, conversations: [{ conversationId: 3, fileId: 3 }] }, + { id: 4, userId: mockUser.id, bucketId: 2, conversations: [{ conversationId: 1, fileId: 4 }] }, ] as FileEntity[]; jest.spyOn(fileRepository, 'count').mockImplementation((query) => countFiles(query, files)); @@ -129,6 +147,11 @@ describe('Get Files', () => { jest .spyOn(bucketRepository, 'findOneBy') .mockImplementation(() => Promise.resolve({ id: 1, type: 'conversation' } as BucketEntity)); + jest.spyOn(conversationFileRepository, 'findBy').mockImplementation((query) => { + const conversationId = (query as FindOptionsWhere).conversationId; + const result = files.filter((x) => x.conversations.find((y) => y.conversationId === conversationId)); + return Promise.resolve(result.flatMap((x) => x.conversations)); + }); const command = new GetFiles({ user: mockUser, bucketIdOrType: 1, page: 0, pageSize: 10, conversationId: 1 }); const response = await handler.execute(command); diff --git a/backend/src/domain/files/use-cases/get-files.ts b/backend/src/domain/files/use-cases/get-files.ts index e2577ddd9..1c0a38519 100644 --- a/backend/src/domain/files/use-cases/get-files.ts +++ b/backend/src/domain/files/use-cases/get-files.ts @@ -4,6 +4,7 @@ import { InjectRepository } from '@nestjs/typeorm'; import { FindManyOptions, FindOptionsWhere, In, Raw } from 'typeorm'; import { BucketEntity, BucketRepository, BucketType, FileEntity, FileRepository } from 'src/domain/database'; import { User } from 'src/domain/users'; +import { ConversationFileEntity, ConversationFileRepository } from '../../database/entities/conversation-file'; import { UploadedFile } from '../interfaces'; import { buildFile } from './utils'; @@ -15,7 +16,7 @@ export class GetFiles { constructor( public readonly data: { user: User; - bucketIdOrType: number | BucketType; + bucketIdOrType: number | BucketType | 'all'; page: number; pageSize?: number; query?: string; @@ -40,14 +41,20 @@ export class GetFilesHandler implements IQueryHandler { const { page, pageSize, query: searchQuery, bucketIdOrType, user, conversationId, files, withContent } = query.data; + const fileFilter = { ids: [...(files ?? [])], enabled: !!files?.length }; + const where: FindOptionsWhere = {}; const bucketWhere: FindOptionsWhere = {}; - if (!conversationId) { + + // read files from a specific bucket (user or general) + if (!conversationId && bucketIdOrType !== 'all') { if (isBucketType(bucketIdOrType)) { bucketWhere.type = bucketIdOrType; } else { @@ -67,17 +74,26 @@ export class GetFilesHandler implements IQueryHandler x.fileId)); + fileFilter.enabled = true; + where.userId = user.id; + } + + // get files specified by ids without restriction + if (bucketIdOrType == 'all' && files) { + fileFilter.enabled = true; where.userId = user.id; } + // apply filters if (searchQuery && searchQuery != '') { where.fileName = Raw((alias) => `LOWER(${alias}) Like '%${searchQuery}%'`); } - - if (files && files.length > 0) { - where.id = In(files); + if (fileFilter.enabled) { + where.id = In(fileFilter.ids); } const options: FindManyOptions = { where }; diff --git a/backend/src/domain/files/use-cases/index.ts b/backend/src/domain/files/use-cases/index.ts index 62ca684d0..38345220b 100644 --- a/backend/src/domain/files/use-cases/index.ts +++ b/backend/src/domain/files/use-cases/index.ts @@ -11,3 +11,4 @@ export * from './test-bucket'; export * from './update-bucket'; export * from './upload-file'; export * from './get-document-content'; +export * from './get-document-pdf'; diff --git a/backend/src/domain/files/use-cases/upload-file.ts b/backend/src/domain/files/use-cases/upload-file.ts index fd1743b1a..efdcb399a 100644 --- a/backend/src/domain/files/use-cases/upload-file.ts +++ b/backend/src/domain/files/use-cases/upload-file.ts @@ -16,6 +16,7 @@ import { import { User } from 'src/domain/users'; import { assignDefined } from 'src/lib'; import { I18nService } from '../../../localization/i18n.service'; +import { ConversationFileEntity, ConversationFileRepository } from '../../database/entities/conversation-file'; import { UploadedFile } from '../interfaces'; import { FilesApi, ResponseError } from './generated'; import { buildClient, buildFile, getBucketId } from './utils'; @@ -28,8 +29,14 @@ export interface UploadFileParams { fileName: string; fileSize: number; bucketId?: number; - extensionId?: number; - createEmbeddings: boolean; + /** + * embedType values + * - vector: the document will be added to the vector store (reis) + * - text: the text of document will be extracted and stored in db + * - vector_and_text: the document will be added to the vector store and the extracted text will be stored in db + * - none: the document will be stored as complete file (e.g. image file) + */ + embedType: 'vector' | 'text' | 'vector_and_text' | 'none'; conversationId?: number; } @@ -50,15 +57,17 @@ export class UploadFileHandler implements ICommandHandler { - const { extensionId, buffer, mimeType, fileName, fileSize, user, conversationId, bucketId, createEmbeddings } = params; + const { buffer, mimeType, fileName, fileSize, user, conversationId, bucketId, embedType } = params; if (!bucketId) { return this.handleFileWithoutBucket(params); @@ -188,11 +202,11 @@ export class UploadFileHandler implements ICommandHandler { + let handler: CreatePromptHandler; + let promptRepository: Repository; + let categoryRepository: Repository; + + beforeEach(async () => { + const module: TestingModule = await Test.createTestingModule({ + providers: [ + CreatePromptHandler, + { + provide: getRepositoryToken(PromptEntity), + useValue: { + create: jest.fn(), + save: jest.fn(), + }, + }, + { + provide: getRepositoryToken(PromptCategoryEntity), + useValue: { + findBy: jest.fn(), + }, + }, + ], + }).compile(); + + handler = module.get(CreatePromptHandler); + promptRepository = module.get>(getRepositoryToken(PromptEntity)); + categoryRepository = module.get>(getRepositoryToken(PromptCategoryEntity)); + }); + + it('should create a prompt without categories', async () => { + const mockPromptEntity = { + id: 1, + title: 'Test Prompt', + content: 'Test content', + visibility: VisibilityType.PRIVATE, + } as PromptEntity; + + const createSpy = jest.spyOn(promptRepository, 'create').mockReturnValue(mockPromptEntity); + const saveSpy = jest.spyOn(promptRepository, 'save').mockResolvedValue(mockPromptEntity); + + const result = await handler.execute( + new CreatePrompt({ + title: 'Test Prompt', + content: 'Test content', + visibility: VisibilityType.PRIVATE, + }), + ); + + expect(createSpy).toHaveBeenCalledWith({ + title: 'Test Prompt', + content: 'Test content', + visibility: VisibilityType.PRIVATE, + categories: [], + }); + expect(saveSpy).toHaveBeenCalledWith(mockPromptEntity); + expect(result.prompt).toEqual(mockPromptEntity); + }); + + it('should create a prompt with categories', async () => { + const mockCategories = [ + { label: 'category1', description: 'Category 1' }, + { label: 'category2', description: 'Category 2' }, + ] as PromptCategoryEntity[]; + + const mockPromptEntity = { + id: 1, + title: 'Test Prompt', + content: 'Test content', + visibility: VisibilityType.PUBLIC, + categories: mockCategories, + } as PromptEntity; + + const findBySpy = jest.spyOn(categoryRepository, 'findBy').mockResolvedValue(mockCategories); + const createSpy = jest.spyOn(promptRepository, 'create').mockReturnValue(mockPromptEntity); + const saveSpy = jest.spyOn(promptRepository, 'save').mockResolvedValue(mockPromptEntity); + + const result = await handler.execute( + new CreatePrompt({ + title: 'Test Prompt', + content: 'Test content', + visibility: VisibilityType.PUBLIC, + categoryLabels: ['category1', 'category2'], + }), + ); + + expect(findBySpy).toHaveBeenCalledWith({ + label: In(['category1', 'category2']), + }); + expect(createSpy).toHaveBeenCalledWith({ + title: 'Test Prompt', + content: 'Test content', + visibility: VisibilityType.PUBLIC, + categories: mockCategories, + }); + expect(saveSpy).toHaveBeenCalledWith(mockPromptEntity); + expect(result.prompt).toEqual(mockPromptEntity); + }); + + it('should create prompt with only required fields', async () => { + const mockPromptEntity = { + id: 1, + title: 'Required Title', + content: 'Test content', + visibility: VisibilityType.PRIVATE, + } as PromptEntity; + + const createSpy = jest.spyOn(promptRepository, 'create').mockReturnValue(mockPromptEntity); + const saveSpy = jest.spyOn(promptRepository, 'save').mockResolvedValue(mockPromptEntity); + + const result = await handler.execute( + new CreatePrompt({ + title: 'Required Title', + content: 'Test content', + visibility: VisibilityType.PRIVATE, + }), + ); + + expect(createSpy).toHaveBeenCalledWith({ + title: 'Required Title', + content: 'Test content', + visibility: VisibilityType.PRIVATE, + categories: [], + }); + expect(saveSpy).toHaveBeenCalledWith(mockPromptEntity); + expect(result.prompt).toEqual(mockPromptEntity); + }); +}); diff --git a/backend/src/domain/prompt/use-cases/create-prompt.ts b/backend/src/domain/prompt/use-cases/create-prompt.ts new file mode 100644 index 000000000..5869431ff --- /dev/null +++ b/backend/src/domain/prompt/use-cases/create-prompt.ts @@ -0,0 +1,58 @@ +import { CommandHandler, ICommandHandler } from '@nestjs/cqrs'; +import { InjectRepository } from '@nestjs/typeorm'; +import { In, Repository } from 'typeorm'; +import { assignDefined } from 'src/lib'; +import { PromptEntity } from '../../database/entities/prompt'; +import { PromptCategoryEntity } from '../../database/entities/prompt-category'; +import { Prompt } from '../interfaces'; + +type Values = Pick & { + categoryLabels?: string[]; +}; + +export class CreatePrompt { + constructor(public readonly values: Values) {} +} + +export class CreatePromptResponse { + constructor(public readonly prompt: PromptEntity) {} +} + +@CommandHandler(CreatePrompt) +export class CreatePromptHandler implements ICommandHandler { + constructor( + @InjectRepository(PromptEntity) + private readonly promptRepository: Repository, + @InjectRepository(PromptCategoryEntity) + private readonly categoryRepository: Repository, + ) {} + + async execute(request: CreatePrompt): Promise { + const { values } = request; + const { title, description, content, visibility, categoryLabels } = values; + + // Find existing categories if categoryLabels provided + let categories: PromptCategoryEntity[] = []; + if (categoryLabels && categoryLabels.length > 0) { + categories = await this.categoryRepository.findBy({ + label: In(categoryLabels), + }); + } + + // Create the prompt entity + const promptData: Partial = { + title, + content, + visibility, + categories, + }; + + // Assign optional fields manually to avoid updating unexpected values + assignDefined(promptData, { description }); + + const entity = this.promptRepository.create(promptData); + const created = await this.promptRepository.save(entity); + + return new CreatePromptResponse(created); + } +} diff --git a/backend/src/domain/settings/use-cases/get-blob.ts b/backend/src/domain/settings/use-cases/get-blob.ts index 164c27681..4c7ea1f35 100644 --- a/backend/src/domain/settings/use-cases/get-blob.ts +++ b/backend/src/domain/settings/use-cases/get-blob.ts @@ -14,13 +14,13 @@ export class GetBlobResponse { export class GetBlobHandler implements IQueryHandler { constructor( @InjectRepository(BlobEntity) - private readonly blogs: BlobRepository, + private readonly blobs: BlobRepository, ) {} async execute(request: GetBlob): Promise { const { id } = request; - const entity = await this.blogs.findOneBy({ id }); + const entity = await this.blobs.findOneBy({ id }); if (!entity) { return new GetBlobResponse(); diff --git a/backend/src/extensions/tools/always-42.ts b/backend/src/extensions/examples/always-42.ts similarity index 94% rename from backend/src/extensions/tools/always-42.ts rename to backend/src/extensions/examples/always-42.ts index e5984b8f6..892901f04 100644 --- a/backend/src/extensions/tools/always-42.ts +++ b/backend/src/extensions/examples/always-42.ts @@ -1,6 +1,5 @@ -import { StructuredTool } from '@langchain/core/tools'; import { z } from 'zod'; -import { ChatContext, ChatMiddleware, ChatNextDelegate, GetContext } from 'src/domain/chat'; +import { ChatContext, ChatMiddleware, ChatNextDelegate, GetContext, NamedStructuredTool } from 'src/domain/chat'; import { Extension, ExtensionEntity, ExtensionSpec } from 'src/domain/extensions'; import { User } from 'src/domain/users'; import { I18nService } from '../../localization/i18n.service'; @@ -32,15 +31,11 @@ export class Always42Extension implements Extension { } } -class InternalTool extends StructuredTool { +class InternalTool extends NamedStructuredTool { readonly name: string; readonly description = 'Calculates the sum of two numbers'; readonly displayName = 'Always 42'; - get lc_id() { - return [...this.lc_namespace, this.name]; - } - readonly schema = z.object({ lhs: z .number() // diff --git a/backend/src/extensions/tools/confirm.ts b/backend/src/extensions/examples/confirm.ts similarity index 94% rename from backend/src/extensions/tools/confirm.ts rename to backend/src/extensions/examples/confirm.ts index 3a4ae86d2..39ee2dfc2 100644 --- a/backend/src/extensions/tools/confirm.ts +++ b/backend/src/extensions/examples/confirm.ts @@ -1,6 +1,5 @@ -import { StructuredTool } from '@langchain/core/tools'; import { z } from 'zod'; -import { ChatContext, ChatMiddleware, ChatNextDelegate, FormActionType, GetContext } from 'src/domain/chat'; +import { ChatContext, ChatMiddleware, ChatNextDelegate, FormActionType, GetContext, NamedStructuredTool } from 'src/domain/chat'; import { Extension, ExtensionEntity, ExtensionSpec } from 'src/domain/extensions'; import { User } from 'src/domain/users'; import { I18nService } from '../../localization/i18n.service'; @@ -32,15 +31,11 @@ export class ConfirmExtension implements Extension { } } -class InternalTool extends StructuredTool { +class InternalTool extends NamedStructuredTool { readonly name: string; readonly description = 'Calculates the sum of two numbers after confirmation'; readonly displayName = 'Confirm'; - get lc_id() { - return [...this.lc_namespace, this.name]; - } - readonly schema = z.object({ lhs: z .number() // diff --git a/backend/src/extensions/tools/show-context.ts b/backend/src/extensions/examples/show-context.ts similarity index 93% rename from backend/src/extensions/tools/show-context.ts rename to backend/src/extensions/examples/show-context.ts index e192f9301..cd580962e 100644 --- a/backend/src/extensions/tools/show-context.ts +++ b/backend/src/extensions/examples/show-context.ts @@ -1,6 +1,5 @@ -import { StructuredTool } from '@langchain/core/tools'; import { z } from 'zod'; -import { ChatContext, ChatMiddleware, ChatNextDelegate, GetContext } from 'src/domain/chat'; +import { ChatContext, ChatMiddleware, ChatNextDelegate, GetContext, NamedStructuredTool } from 'src/domain/chat'; import { Extension, ExtensionEntity, ExtensionSpec } from 'src/domain/extensions'; import { User } from 'src/domain/users'; import { I18nService } from '../../localization/i18n.service'; @@ -32,15 +31,11 @@ export class ContextExtension implements Extension { } } -class InternalTool extends StructuredTool { +class InternalTool extends NamedStructuredTool { readonly name: string; readonly description = 'Shows the current context.'; readonly displayName = 'Context'; - get lc_id() { - return [...this.lc_namespace, this.name]; - } - readonly schema = z.object({}); constructor( diff --git a/backend/src/extensions/tools/simple-input.ts b/backend/src/extensions/examples/simple-input.ts similarity index 93% rename from backend/src/extensions/tools/simple-input.ts rename to backend/src/extensions/examples/simple-input.ts index 5bd9de6b4..018913f46 100644 --- a/backend/src/extensions/tools/simple-input.ts +++ b/backend/src/extensions/examples/simple-input.ts @@ -1,10 +1,12 @@ -import { StructuredTool } from '@langchain/core/tools'; import { z } from 'zod'; -import { ChatContext, ChatMiddleware, ChatNextDelegate, FormActionType, GetContext } from 'src/domain/chat'; +import { ChatContext, ChatMiddleware, ChatNextDelegate, FormActionType, GetContext, NamedStructuredTool } from 'src/domain/chat'; import { Extension, ExtensionEntity, ExtensionSpec } from 'src/domain/extensions'; import { User } from 'src/domain/users'; import { I18nService } from '../../localization/i18n.service'; +/** + * This + */ @Extension() export class SimpleInputExtension implements Extension { constructor(private readonly i18n: I18nService) {} @@ -32,15 +34,11 @@ export class SimpleInputExtension implements Extension { } } -class InternalTool extends StructuredTool { +class InternalTool extends NamedStructuredTool { readonly name: string; readonly description = 'Handles a user input'; readonly displayName = 'Simple Input'; - get lc_id() { - return [...this.lc_namespace, this.name]; - } - readonly schema = z.object({}); constructor( diff --git a/backend/src/extensions/tools/user-args.ts b/backend/src/extensions/examples/user-args.ts similarity index 94% rename from backend/src/extensions/tools/user-args.ts rename to backend/src/extensions/examples/user-args.ts index 427b07417..5a408d9c2 100644 --- a/backend/src/extensions/tools/user-args.ts +++ b/backend/src/extensions/examples/user-args.ts @@ -1,6 +1,12 @@ -import { StructuredTool } from '@langchain/core/tools'; import { z } from 'zod'; -import { ChatContext, ChatMiddleware, ChatNextDelegate, ExtensionUserArgumentValues, GetContext } from 'src/domain/chat'; +import { + ChatContext, + ChatMiddleware, + ChatNextDelegate, + ExtensionUserArgumentValues, + GetContext, + NamedStructuredTool, +} from 'src/domain/chat'; import { Extension, ExtensionArgument, ExtensionEntity, ExtensionSpec } from 'src/domain/extensions'; import { User } from 'src/domain/users'; import { I18nService } from '../../localization/i18n.service'; @@ -96,15 +102,11 @@ export class UserArgsExtension implements Extension { } } -class InternalTool extends StructuredTool { +class InternalTool extends NamedStructuredTool { readonly name: string; readonly description = 'Shows the current user arguments.'; readonly displayName = 'User Args'; - get lc_id() { - return [...this.lc_namespace, this.name]; - } - readonly schema = z.object({}); constructor( @@ -113,7 +115,6 @@ class InternalTool extends StructuredTool { extensionExternalId: string, ) { super(); - this.name = extensionExternalId; } diff --git a/backend/src/extensions/models/azure-open-ai-reasoning.ts b/backend/src/extensions/models/azure-open-ai-reasoning.ts deleted file mode 100644 index bcd5ba0c7..000000000 --- a/backend/src/extensions/models/azure-open-ai-reasoning.ts +++ /dev/null @@ -1,106 +0,0 @@ -import { CallbackHandlerMethods } from '@langchain/core/callbacks/base'; -import { AzureChatOpenAI } from '@langchain/openai'; -import { ChatContext, ChatMiddleware, ChatNextDelegate, GetContext } from 'src/domain/chat'; -import { Extension, ExtensionConfiguration, ExtensionEntity, ExtensionSpec } from 'src/domain/extensions'; -import { User } from 'src/domain/users'; -import { I18nService } from '../../localization/i18n.service'; -import { getEstimatedUsageCallback } from './internal/utils'; - -@Extension() -export class AzureOpenAIReasoningModelExtension implements Extension { - constructor(private readonly i18n: I18nService) {} - - get spec(): ExtensionSpec { - return { - name: 'azure-open-ai-model-reasoning', - title: this.i18n.t('texts.extensions.azure-o.title'), - logo: '', - description: this.i18n.t('texts.extensions.azure-o.description'), - type: 'llm', - arguments: { - apiKey: { - type: 'string', - title: this.i18n.t('texts.extensions.common.apiKey'), - required: true, - format: 'password', - }, - deploymentName: { - type: 'string', - title: this.i18n.t('texts.extensions.common.deploymentName'), - required: true, - }, - instanceName: { - type: 'string', - title: this.i18n.t('texts.extensions.common.instanceName'), - required: true, - }, - apiVersion: { - type: 'string', - title: this.i18n.t('texts.extensions.common.apiVersion'), - required: true, - format: 'select', - examples: ['2024-12-01-preview'], - }, - effort: { - type: 'string', - title: this.i18n.t('texts.extensions.common.effort'), - required: false, - enum: ['', 'low', 'medium', 'high'], - }, - }, - }; - } - - async test(configuration: AzureOpenAIReasoningModelExtensionConfiguration) { - const model = this.createModel(configuration); - - await model.invoke('Just a test call'); - } - - getMiddlewares( - _user: User, - extension: ExtensionEntity, - ): Promise { - const middleware = { - invoke: async (context: ChatContext, getContext: GetContext, next: ChatNextDelegate): Promise => { - context.llms[this.spec.name] = await context.cache.get(this.spec.name, extension.values, () => { - // The model does not provide the token usage, therefore estimate it. - const callbacks = [getEstimatedUsageCallback('azure-open-ai-reasoning', extension.values.deploymentName, getContext)]; - - // Stream the result token by token to the frontend. - return this.createModel(extension.values, callbacks, true); - }); - - return next(context); - }, - }; - - return Promise.resolve([middleware]); - } - - private createModel( - configuration: AzureOpenAIReasoningModelExtensionConfiguration, - callbacks?: CallbackHandlerMethods[], - streaming = false, - ) { - const { apiKey, apiVersion, deploymentName, instanceName, effort } = configuration; - - return new AzureChatOpenAI({ - azureOpenAIApiDeploymentName: deploymentName, - azureOpenAIApiInstanceName: instanceName, - azureOpenAIApiKey: apiKey, - azureOpenAIApiVersion: apiVersion, - callbacks, - streaming, - reasoning: effort ? { effort } : undefined, - }); - } -} - -type AzureOpenAIReasoningModelExtensionConfiguration = ExtensionConfiguration & { - apiKey: string; - deploymentName: string; - instanceName: string; - apiVersion: string; - effort?: 'low' | 'medium' | 'high'; -}; diff --git a/backend/src/extensions/models/azure-open-ai.spec.ts b/backend/src/extensions/models/azure-open-ai.spec.ts index dc5dd244e..3c0eb0043 100644 --- a/backend/src/extensions/models/azure-open-ai.spec.ts +++ b/backend/src/extensions/models/azure-open-ai.spec.ts @@ -1,16 +1,14 @@ import { AzureOpenAIModelExtension } from './azure-open-ai'; import { modelExtensionTestSuite } from './model-test.base'; -const instance = { - invoke: jest.fn().mockReturnThis(), -}; +jest.mock('@ai-sdk/azure', () => ({ + createAzure: jest.fn(() => ({ + responses: jest.fn(() => () => 'mocked model'), + })), +})); -jest.mock('@langchain/openai', () => { - return { - AzureChatOpenAI: jest.fn().mockImplementation(() => { - return instance; - }), - }; -}); +jest.mock('ai', () => ({ + generateText: jest.fn(() => () => 'test output'), +})); -describe('OpenAIModelExtension', () => modelExtensionTestSuite(AzureOpenAIModelExtension, instance)); +describe('OpenAIModelExtension', () => modelExtensionTestSuite(AzureOpenAIModelExtension)); diff --git a/backend/src/extensions/models/azure-open-ai.ts b/backend/src/extensions/models/azure-open-ai.ts index fb7f4cb64..c7a0c3957 100644 --- a/backend/src/extensions/models/azure-open-ai.ts +++ b/backend/src/extensions/models/azure-open-ai.ts @@ -1,10 +1,10 @@ -import { CallbackHandlerMethods } from '@langchain/core/callbacks/base'; -import { AzureChatOpenAI } from '@langchain/openai'; -import { ChatContext, ChatMiddleware, ChatNextDelegate, GetContext } from 'src/domain/chat'; +import { createAzure } from '@ai-sdk/azure'; +import { CallSettings, generateText } from 'ai'; +import { ChatContext, ChatMiddleware, ChatNextDelegate, GetContext, LanguageModelContext } from 'src/domain/chat'; import { Extension, ExtensionConfiguration, ExtensionEntity, ExtensionSpec } from 'src/domain/extensions'; import { User } from 'src/domain/users'; +import { fetchWithDebugLogging } from 'src/lib/log-requests'; import { I18nService } from '../../localization/i18n.service'; -import { getEstimatedUsageCallback } from './internal/utils'; @Extension() export class AzureOpenAIModelExtension implements Extension { @@ -35,18 +35,12 @@ export class AzureOpenAIModelExtension implements Extension): Promise { const middleware = { invoke: async (context: ChatContext, getContext: GetContext, next: ChatNextDelegate): Promise => { context.llms[this.spec.name] = await context.cache.get(this.spec.name, extension.values, () => { - // The model does not provide the token usage, therefore estimate it. - const callbacks = [getEstimatedUsageCallback('azure-open-ai', extension.values.deploymentName, getContext)]; - - // Stream the result token by token to the frontend. - return this.createModel(extension.values, callbacks, true); + return this.createModel(extension.values, true); }); return next(context); @@ -111,28 +120,43 @@ export class AzureOpenAIModelExtension implements Extension = !effort + ? { + presencePenalty, + frequencyPenalty, + temperature, + topP, + } + : {}; + + return { + model: azure.responses(deploymentName), + options: { + ...reasoningOptions, + seed, + streaming, + providerOptions: { + openai: effort + ? { + reasoningEffort: effort ? effort : undefined, + reasoningSummary: summary || 'detailed', + } + : {}, + }, + } as Partial, + modelName: deploymentName, + providerName: 'azure-open-ai', + }; } } @@ -140,10 +164,11 @@ type AzureOpenAIModelExtensionConfiguration = ExtensionConfiguration & { apiKey: string; deploymentName: string; instanceName: string; - apiVersion: string; - temperature: number; seed: number; - presencePenalty: number; - frequencyPenalty: number; - topP: number; + temperature?: number; + presencePenalty?: number; + frequencyPenalty?: number; + topP?: number; + effort?: 'low' | 'medium' | 'high'; + summary?: 'detailed' | 'auto'; }; diff --git a/backend/src/extensions/models/bedrock-ai.spec.ts b/backend/src/extensions/models/bedrock-ai.spec.ts new file mode 100644 index 000000000..62c3e0f8d --- /dev/null +++ b/backend/src/extensions/models/bedrock-ai.spec.ts @@ -0,0 +1,11 @@ +import { BedrockModelExtension } from './bedrock-ai'; +import { modelExtensionTestSuite } from './model-test.base'; + +jest.mock('@ai-sdk/amazon-bedrock', () => ({ + createAmazonBedrock: jest.fn(() => () => 'mocked model'), +})); +jest.mock('ai', () => ({ + generateText: jest.fn(() => () => 'test output'), +})); + +describe('BedrockModelExtension', () => modelExtensionTestSuite(BedrockModelExtension)); diff --git a/backend/src/extensions/models/bedrock-ai.ts b/backend/src/extensions/models/bedrock-ai.ts index a746b0b20..1ffc1c090 100644 --- a/backend/src/extensions/models/bedrock-ai.ts +++ b/backend/src/extensions/models/bedrock-ai.ts @@ -1,11 +1,10 @@ -import { ChatBedrockConverse } from '@langchain/aws'; -import { CallbackHandlerMethods } from '@langchain/core/callbacks/base'; -import { createToolCallingAgent } from 'langchain/agents'; +import { createAmazonBedrock } from '@ai-sdk/amazon-bedrock'; +import { CallSettings, generateText } from 'ai'; import { ChatContext, ChatMiddleware, ChatNextDelegate, GetContext } from 'src/domain/chat'; import { Extension, ExtensionConfiguration, ExtensionEntity, ExtensionSpec } from 'src/domain/extensions'; import { User } from 'src/domain/users'; +import { fetchWithDebugLogging } from 'src/lib/log-requests'; import { I18nService } from '../../localization/i18n.service'; -import { getEstimatedUsageCallback } from './internal/utils'; @Extension() export class BedrockModelExtension implements Extension { @@ -55,6 +54,7 @@ export class BedrockModelExtension implements Extension): Promise { const middleware = { invoke: async (context: ChatContext, getContext: GetContext, next: ChatNextDelegate): Promise => { context.llms[this.spec.name] = await context.cache.get(this.spec.name, extension.values, () => { - const callbacks = [getEstimatedUsageCallback('bedrock-ai', extension.values.model, getContext)]; - - return this.createModel(extension.values, callbacks); + return this.createModel(extension.values); }); - context.agentFactory = createToolCallingAgent; return next(context); }, @@ -92,17 +96,25 @@ export class BedrockModelExtension implements Extension, + modelName: model, + providerName: 'bedrock-ai', + }; } } diff --git a/backend/src/extensions/models/google-genai.spec.ts b/backend/src/extensions/models/google-genai.spec.ts new file mode 100644 index 000000000..8dd3ff730 --- /dev/null +++ b/backend/src/extensions/models/google-genai.spec.ts @@ -0,0 +1,11 @@ +import { GoogleGenAIModelExtension } from './google-genai'; +import { modelExtensionTestSuite } from './model-test.base'; + +jest.mock('@ai-sdk/google', () => ({ + createGoogleGenerativeAI: jest.fn(() => () => 'mocked model'), +})); +jest.mock('ai', () => ({ + generateText: jest.fn(() => () => 'test output'), +})); + +describe('GoogleGenAIModelExtension', () => modelExtensionTestSuite(GoogleGenAIModelExtension)); diff --git a/backend/src/extensions/models/google-genai.ts b/backend/src/extensions/models/google-genai.ts index ffbedfa93..01183e588 100644 --- a/backend/src/extensions/models/google-genai.ts +++ b/backend/src/extensions/models/google-genai.ts @@ -1,11 +1,10 @@ -import { CallbackHandlerMethods } from '@langchain/core/callbacks/base'; -import { ChatGoogleGenerativeAI } from '@langchain/google-genai'; -import { createToolCallingAgent } from 'langchain/agents'; +import { createGoogleGenerativeAI } from '@ai-sdk/google'; +import { CallSettings, generateText } from 'ai'; import { ChatContext, ChatMiddleware, ChatNextDelegate, GetContext } from 'src/domain/chat'; import { Extension, ExtensionConfiguration, ExtensionEntity, ExtensionSpec } from 'src/domain/extensions'; import { User } from 'src/domain/users'; +import { fetchWithDebugLogging } from 'src/lib/log-requests'; import { I18nService } from '../../localization/i18n.service'; -import { getEstimatedUsageCallback } from './internal/utils'; @Extension() export class GoogleGenAIModelExtension implements Extension { @@ -46,6 +45,7 @@ export class GoogleGenAIModelExtension implements Extension): Promise { const middleware = { invoke: async (context: ChatContext, getContext: GetContext, next: ChatNextDelegate): Promise => { - context.llms[this.spec.name] = await context.cache.get('google-genai', extension.values, () => { - // The model does not provide the token usage, therefore estimate it. - const callbacks = [getEstimatedUsageCallback('google-genai', extension.values.modelName, getContext)]; - return this.createModel(extension.values, callbacks); + context.llms[this.spec.name] = await context.cache.get(this.spec.name, extension.values, () => { + return this.createModel(extension.values); }); - context.agentFactory = createToolCallingAgent; return next(context); }, @@ -96,10 +99,24 @@ export class GoogleGenAIModelExtension implements Extension, + modelName: modelName, + providerName: 'google-genai', + }; } } diff --git a/backend/src/extensions/models/internal/utils.ts b/backend/src/extensions/models/internal/utils.ts deleted file mode 100644 index 522a7bdec..000000000 --- a/backend/src/extensions/models/internal/utils.ts +++ /dev/null @@ -1,61 +0,0 @@ -import { CallbackHandlerMethods } from '@langchain/core/callbacks/base'; -import { MessageContentComplex, MessageContentText } from '@langchain/core/messages'; -import { GetContext } from 'src/domain/chat'; -import { isString } from 'src/lib'; - -function isMessageContentText(messageContent: MessageContentComplex): messageContent is MessageContentText { - return messageContent.type === 'text'; -} - -export function getEstimatedUsageCallback(llm: string, model: string, getContext: GetContext): CallbackHandlerMethods { - return { - handleChatModelStart(_, messages) { - const context = getContext(); - - let totalLength = 0; - for (const block of messages) { - for (const message of block) { - if (isString(message.content)) { - totalLength += message.content.length; - } else { - for (const part of message.content) { - if (isMessageContentText(part)) { - totalLength += part.text.length; - } else if (part.type === 'image_url') { - if (isString(part.image_url)) { - totalLength += part.image_url.length; - } else { - totalLength += (part.image_url as { url: string }).url.length; - } - } - } - } - } - } - - // Fallback to approximate calculation if tiktoken is not available - const tokenCount = Math.ceil(totalLength / 4); - - context.tokenUsage ??= { tokenCount, model, llm }; - context.tokenUsage.tokenCount += tokenCount; - }, - handleLLMEnd(output) { - const context = getContext(); - - let totalLength = 0; - for (const block of output.generations) { - for (const message of block) { - if (isString(message.text)) { - totalLength += message.text.length; - } - } - } - - // Fallback to approximate calculation if tiktoken is not available - const tokenCount = Math.ceil(totalLength / 4); - - context.tokenUsage ??= { tokenCount, model, llm }; - context.tokenUsage.tokenCount += tokenCount; - }, - }; -} diff --git a/backend/src/extensions/models/mistral.spec.ts b/backend/src/extensions/models/mistral.spec.ts index 576756ff7..6a129acba 100644 --- a/backend/src/extensions/models/mistral.spec.ts +++ b/backend/src/extensions/models/mistral.spec.ts @@ -1,16 +1,11 @@ import { MistralModelExtension } from './mistral'; import { modelExtensionTestSuite } from './model-test.base'; -const instance = { - invoke: jest.fn().mockReturnThis(), -}; +jest.mock('@ai-sdk/mistral', () => ({ + createMistral: jest.fn(() => () => 'mocked model'), +})); +jest.mock('ai', () => ({ + generateText: jest.fn(() => () => 'test output'), +})); -jest.mock('@langchain/mistralai', () => { - return { - ChatMistralAI: jest.fn().mockImplementation(() => { - return instance; - }), - }; -}); - -describe('MistralModelExtension', () => modelExtensionTestSuite(MistralModelExtension, instance)); +describe('MistralModelExtension', () => modelExtensionTestSuite(MistralModelExtension)); diff --git a/backend/src/extensions/models/mistral.ts b/backend/src/extensions/models/mistral.ts index 6eea98f00..67f0597d8 100644 --- a/backend/src/extensions/models/mistral.ts +++ b/backend/src/extensions/models/mistral.ts @@ -1,10 +1,10 @@ -import { CallbackHandlerMethods } from '@langchain/core/callbacks/base'; -import { ChatMistralAI } from '@langchain/mistralai'; -import { ChatContext, ChatError, ChatMiddleware, ChatNextDelegate, GetContext } from 'src/domain/chat'; +import { createMistral } from '@ai-sdk/mistral'; +import { CallSettings, generateText } from 'ai'; +import { ChatContext, ChatMiddleware, ChatNextDelegate, GetContext } from 'src/domain/chat'; import { Extension, ExtensionConfiguration, ExtensionEntity, ExtensionSpec } from 'src/domain/extensions'; import { User } from 'src/domain/users'; +import { fetchWithDebugLogging } from 'src/lib/log-requests'; import { I18nService } from '../../localization/i18n.service'; -import { getEstimatedUsageCallback } from './internal/utils'; @Extension() export class MistralModelExtension implements Extension { @@ -45,26 +45,22 @@ export class MistralModelExtension implements Extension): Promise { const middleware = { invoke: async (context: ChatContext, getContext: GetContext, next: ChatNextDelegate): Promise => { - const isLargeModel = extension.values.modelName.startsWith('mistral-large'); - - if (context.tools.length > 0 && !isLargeModel) { - throw new ChatError('Tools are only supported with mistral-large model.'); - } - context.llms[this.spec.name] = await context.cache.get(this.spec.name, extension.values, () => { - // The model does not provide the token usage, therefore estimate it. - const callbacks = [getEstimatedUsageCallback('mistral', extension.values.modelName, getContext)]; - - // Stream the result token by token to the frontend. - return this.createModel(extension.values, callbacks, true); + return this.createModel(extension.values, true); }); return next(context); @@ -74,14 +70,22 @@ export class MistralModelExtension implements Extension, + modelName: modelName, + providerName: 'mistral', + }; } } diff --git a/backend/src/extensions/models/model-test.base.ts b/backend/src/extensions/models/model-test.base.ts index 2a9c8c144..245176cb1 100644 --- a/backend/src/extensions/models/model-test.base.ts +++ b/backend/src/extensions/models/model-test.base.ts @@ -1,13 +1,12 @@ -import { StructuredToolInterface } from '@langchain/core/tools'; -import { ChatContext } from 'src/domain/chat'; +import { generateText } from 'ai'; +import { ChatContext, NamedStructuredTool } from 'src/domain/chat'; import { Extension, ExtensionConfiguration, ExtensionEntity } from 'src/domain/extensions'; import { User } from 'src/domain/users'; import { I18nService } from '../../localization/i18n.service'; type ExtensionConstructor = new (i18n: I18nService) => Extension; -export function modelExtensionTestSuite(modelExtension: ExtensionConstructor, instance: { invoke: () => void }) { - let invokeMock: jest.SpyInstance; +export function modelExtensionTestSuite(modelExtension: ExtensionConstructor) { let extension: Extension; const i18n = { @@ -16,7 +15,6 @@ export function modelExtensionTestSuite(modelExtension: ExtensionConstructor, in beforeEach(() => { extension = new modelExtension(i18n); - invokeMock = jest.spyOn(instance, 'invoke').mockReturnThis(); }); it('should have getMiddlewares method', async () => { @@ -28,7 +26,7 @@ export function modelExtensionTestSuite(modelExtension: ExtensionConstructor, in }; const context = { - tools: [] as StructuredToolInterface[], + tools: [] as NamedStructuredTool[], llms: {}, cache: { get: (_key: string, _args: any, resolver: () => Promise) => { @@ -56,6 +54,6 @@ export function modelExtensionTestSuite(modelExtension: ExtensionConstructor, in const configuration: ExtensionConfiguration = {}; await extension.test?.(configuration); expect(extension.test?.bind(extension)).toBeDefined(); - expect(invokeMock).toHaveBeenCalled(); + expect(generateText).toHaveBeenCalled(); }); } diff --git a/backend/src/extensions/models/nvidia.spec.ts b/backend/src/extensions/models/nvidia.spec.ts new file mode 100644 index 000000000..4f746c25e --- /dev/null +++ b/backend/src/extensions/models/nvidia.spec.ts @@ -0,0 +1,11 @@ +import { modelExtensionTestSuite } from './model-test.base'; +import { NvidiaModelExtension } from './nvidia'; + +jest.mock('@ai-sdk/openai-compatible', () => ({ + createOpenAICompatible: jest.fn(() => () => 'mocked model'), +})); +jest.mock('ai', () => ({ + generateText: jest.fn(() => () => 'test output'), +})); + +describe('NvidiaModelExtension', () => modelExtensionTestSuite(NvidiaModelExtension)); diff --git a/backend/src/extensions/models/nvidia.ts b/backend/src/extensions/models/nvidia.ts new file mode 100644 index 000000000..9a9f9176f --- /dev/null +++ b/backend/src/extensions/models/nvidia.ts @@ -0,0 +1,153 @@ +import { createOpenAICompatible } from '@ai-sdk/openai-compatible'; +import { CallSettings, generateText } from 'ai'; +import { ChatContext, ChatMiddleware, ChatNextDelegate, GetContext } from 'src/domain/chat'; +import { Extension, ExtensionConfiguration, ExtensionEntity, ExtensionSpec } from 'src/domain/extensions'; +import { User } from 'src/domain/users'; +import { fetchWithDebugLogging } from 'src/lib/log-requests'; +import { I18nService } from '../../localization/i18n.service'; + +@Extension() +export class NvidiaModelExtension implements Extension { + constructor(private readonly i18n: I18nService) {} + + get spec(): ExtensionSpec { + return { + name: 'nvidia', + title: this.i18n.t('texts.extensions.nvidia.title'), + logo: '', + description: this.i18n.t('texts.extensions.nvidia.description'), + type: 'llm', + arguments: { + apiKey: { + type: 'string', + title: this.i18n.t('texts.extensions.common.apiKey'), + required: true, + format: 'password', + }, + baseUrl: { + type: 'string', + title: this.i18n.t('texts.extensions.common.endpoint'), + required: true, + description: this.i18n.t('texts.extensions.openai.endpointHint'), + }, + modelName: { + type: 'string', + title: this.i18n.t('texts.extensions.common.modelName'), + required: true, + }, + temperature: { + type: 'number', + title: this.i18n.t('texts.extensions.common.temperature'), + minimum: 0, + maximum: 2, + default: 1, + format: 'slider', + description: this.i18n.t('texts.extensions.common.temperatureHint'), + }, + seed: { + type: 'number', + title: this.i18n.t('texts.extensions.common.seed'), + description: this.i18n.t('texts.extensions.common.seedHint'), + }, + presencePenalty: { + type: 'number', + title: this.i18n.t('texts.extensions.common.presencePenalty'), + minimum: 0, + maximum: 2, + default: 0, + format: 'slider', + description: this.i18n.t('texts.extensions.common.presencePenaltyHint'), + }, + frequencyPenalty: { + type: 'number', + title: this.i18n.t('texts.extensions.common.frequencyPenalty'), + minimum: 0, + maximum: 2, + default: 0, + format: 'slider', + description: this.i18n.t('texts.extensions.common.frequencyPenaltyHint'), + }, + effort: { + type: 'string', + title: this.i18n.t('texts.extensions.common.reasoningEffort'), + required: false, + enum: ['', 'minimal', 'low', 'medium', 'high'], + }, + summary: { + type: 'string', + title: this.i18n.t('texts.extensions.common.reasoningSummary'), + required: false, + default: 'detailed', + enum: ['detailed', 'auto'], + }, + }, + }; + } + + async test(configuration: NvidiaModelExtensionConfiguration) { + const { model, options } = this.createModel(configuration); + + const { text } = await generateText({ + model, + prompt: 'Just a test call', + ...options, + }); + + return text != null; + } + + getMiddlewares(_: User, extension: ExtensionEntity): Promise { + const middleware = { + invoke: async (context: ChatContext, _: GetContext, next: ChatNextDelegate): Promise => { + context.llms[this.spec.name] = await context.cache.get(this.spec.name, extension.values, () => { + return this.createModel(extension.values, true); + }); + + return next(context); + }, + }; + + return Promise.resolve([middleware]); + } + + private createModel(config: NvidiaModelExtensionConfiguration, streaming = false) { + const openAi = createOpenAICompatible({ + name: 'nvidia', + apiKey: config.apiKey, + baseURL: config.baseUrl, + includeUsage: true, + fetch: fetchWithDebugLogging(NvidiaModelExtension.name), + }); + + return { + model: openAi(config.modelName), + options: { + presencePenalty: config.presencePenalty, + frequencyPenalty: config.frequencyPenalty, + seed: config.seed, + temperature: config.temperature, + streaming, + providerOptions: { + openai: { + reasoningEffort: config.effort ? config.effort : undefined, + reasoningSummary: config.summary || 'detailed', + }, + }, + } as Partial, + modelName: config.modelName, + providerName: 'nvidia', + }; + } +} + +type NvidiaModelExtensionConfiguration = ExtensionConfiguration & { + apiKey: string; + baseUrl: string; + modelName: string; + temperature: number; + seed: number; + presencePenalty: number; + frequencyPenalty: number; + effort?: 'minimal' | 'low' | 'medium' | 'high'; + summary?: 'detailed' | 'auto'; +}; diff --git a/backend/src/extensions/models/ollama.spec.ts b/backend/src/extensions/models/ollama.spec.ts index a067f852f..f815843b9 100644 --- a/backend/src/extensions/models/ollama.spec.ts +++ b/backend/src/extensions/models/ollama.spec.ts @@ -1,15 +1,11 @@ import { modelExtensionTestSuite } from './model-test.base'; import { OllamaModelExtension } from './ollama'; -const instance = { - invoke: jest.fn().mockReturnThis(), -}; +jest.mock('ollama-ai-provider-v2', () => ({ + createOllama: jest.fn(() => () => 'mocked model'), +})); +jest.mock('ai', () => ({ + generateText: jest.fn(() => () => 'test output'), +})); -jest.mock('@langchain/ollama', () => { - return { - ChatOllama: jest.fn().mockImplementation(() => { - return instance; - }), - }; -}); -describe('OllamaModelExtension', () => modelExtensionTestSuite(OllamaModelExtension, instance)); +describe('OllamaModelExtension', () => modelExtensionTestSuite(OllamaModelExtension)); diff --git a/backend/src/extensions/models/ollama.ts b/backend/src/extensions/models/ollama.ts index 0655f521b..11fb76f98 100644 --- a/backend/src/extensions/models/ollama.ts +++ b/backend/src/extensions/models/ollama.ts @@ -1,8 +1,9 @@ -import { ChatOllama } from '@langchain/ollama'; -import { createToolCallingAgent } from 'langchain/agents'; +import { CallSettings, generateText } from 'ai'; +import { createOllama } from 'ollama-ai-provider-v2'; import { ChatContext, ChatMiddleware, ChatNextDelegate, GetContext } from 'src/domain/chat'; import { Extension, ExtensionConfiguration, ExtensionEntity, ExtensionSpec } from 'src/domain/extensions'; import { User } from 'src/domain/users'; +import { fetchWithDebugLogging } from 'src/lib/log-requests'; import { I18nService } from '../../localization/i18n.service'; @Extension() @@ -32,17 +33,23 @@ export class OllamaModelExtension implements Extension): Promise { const middleware = { invoke: async (context: ChatContext, _: GetContext, next: ChatNextDelegate): Promise => { context.llms[this.spec.name] = await context.cache.get(this.spec.name, extension.values, () => { - return this.createModel(extension.values); + return this.createModel(extension.values, true); }); - context.agentFactory = createToolCallingAgent; return next(context); }, @@ -51,13 +58,23 @@ export class OllamaModelExtension implements Extension, + modelName: modelName, + providerName: 'ollama', + }; } } diff --git a/backend/src/extensions/models/open-ai-compatible.spec.ts b/backend/src/extensions/models/open-ai-compatible.spec.ts index c703f17cc..100841a3e 100644 --- a/backend/src/extensions/models/open-ai-compatible.spec.ts +++ b/backend/src/extensions/models/open-ai-compatible.spec.ts @@ -1,16 +1,11 @@ import { modelExtensionTestSuite } from './model-test.base'; import { OpenAICompatibleModelExtension } from './open-ai-compatible'; -const instance = { - invoke: jest.fn().mockReturnThis(), -}; +jest.mock('@ai-sdk/openai-compatible', () => ({ + createOpenAICompatible: jest.fn(() => () => 'mocked model'), +})); +jest.mock('ai', () => ({ + generateText: jest.fn(() => () => 'test output'), +})); -jest.mock('@langchain/openai', () => { - return { - ChatOpenAI: jest.fn().mockImplementation(() => { - return instance; - }), - }; -}); - -describe('OpenAICompatibleModelExtension', () => modelExtensionTestSuite(OpenAICompatibleModelExtension, instance)); +describe('OpenAICompatibleModelExtension', () => modelExtensionTestSuite(OpenAICompatibleModelExtension)); diff --git a/backend/src/extensions/models/open-ai-compatible.ts b/backend/src/extensions/models/open-ai-compatible.ts index 727d0ccd2..5a7108d4d 100644 --- a/backend/src/extensions/models/open-ai-compatible.ts +++ b/backend/src/extensions/models/open-ai-compatible.ts @@ -1,7 +1,9 @@ -import { ChatOpenAI } from '@langchain/openai'; +import { createOpenAICompatible } from '@ai-sdk/openai-compatible'; +import { CallSettings, generateText } from 'ai'; import { ChatContext, ChatMiddleware, ChatNextDelegate, GetContext } from 'src/domain/chat'; import { Extension, ExtensionConfiguration, ExtensionEntity, ExtensionSpec } from 'src/domain/extensions'; import { User } from 'src/domain/users'; +import { fetchWithDebugLogging } from 'src/lib/log-requests'; import { I18nService } from '../../localization/i18n.service'; @Extension() @@ -38,6 +40,7 @@ export class OpenAICompatibleModelExtension implements Extension): Promise { @@ -95,20 +111,36 @@ export class OpenAICompatibleModelExtension implements Extension, + modelName: modelName, + providerName: 'openai-compatible', + }; } } @@ -121,4 +153,5 @@ type OpenAICompatibleModelExtensionConfiguration = ExtensionConfiguration & { presencePenalty: number; frequencyPenalty: number; effort?: 'low' | 'medium' | 'high'; + summary?: 'detailed' | 'auto'; }; diff --git a/backend/src/extensions/models/open-ai.spec.ts b/backend/src/extensions/models/open-ai.spec.ts index 2ae387c8b..e73581ab7 100644 --- a/backend/src/extensions/models/open-ai.spec.ts +++ b/backend/src/extensions/models/open-ai.spec.ts @@ -1,16 +1,13 @@ import { modelExtensionTestSuite } from './model-test.base'; import { OpenAIModelExtension } from './open-ai'; -const instance = { - invoke: jest.fn().mockReturnThis(), -}; +jest.mock('@ai-sdk/openai', () => ({ + createOpenAI: jest.fn(() => ({ + responses: jest.fn(() => () => 'mocked model'), + })), +})); +jest.mock('ai', () => ({ + generateText: jest.fn(() => () => 'test output'), +})); -jest.mock('@langchain/openai', () => { - return { - ChatOpenAI: jest.fn().mockImplementation(() => { - return instance; - }), - }; -}); - -describe('OpenAIModelExtension', () => modelExtensionTestSuite(OpenAIModelExtension, instance)); +describe('OpenAIModelExtension', () => modelExtensionTestSuite(OpenAIModelExtension)); diff --git a/backend/src/extensions/models/open-ai.ts b/backend/src/extensions/models/open-ai.ts index 2757faf50..8c0313596 100644 --- a/backend/src/extensions/models/open-ai.ts +++ b/backend/src/extensions/models/open-ai.ts @@ -1,8 +1,9 @@ -import { CallbackHandlerMethods } from '@langchain/core/callbacks/base'; -import { ChatOpenAI } from '@langchain/openai'; +import { createOpenAI } from '@ai-sdk/openai'; +import { CallSettings, generateText } from 'ai'; import { ChatContext, ChatMiddleware, ChatNextDelegate, GetContext } from 'src/domain/chat'; import { Extension, ExtensionConfiguration, ExtensionEntity, ExtensionSpec } from 'src/domain/extensions'; import { User } from 'src/domain/users'; +import { fetchWithDebugLogging } from 'src/lib/log-requests'; import { I18nService } from '../../localization/i18n.service'; @Extension() @@ -34,6 +35,7 @@ export class OpenAIModelExtension implements Extension): Promise { const middleware = { - invoke: async (context: ChatContext, getContext: GetContext, next: ChatNextDelegate): Promise => { + invoke: async (context: ChatContext, _: GetContext, next: ChatNextDelegate): Promise => { context.llms[this.spec.name] = await context.cache.get(this.spec.name, extension.values, () => { - const callbacks: CallbackHandlerMethods[] = [ - { - handleLLMEnd: (output) => { - // Do not capture the context to make this class cacheable if needed. - const context = getContext(); - - if (!context) { - return; - } - - // This is provider specific, therefore we cannot handle it in the execute step. - const { completionTokens, promptTokens } = (output.llmOutput?.estimatedTokenUsage as OpenAITokenEstimation) || {}; - - let tokenCount = 0; - tokenCount += completionTokens ?? 0; - tokenCount += promptTokens ?? 0; - - if (tokenCount > 0) { - context.tokenUsage = { tokenCount, model: extension.values.modelName, llm: 'open-ai' }; - } - }, - }, - ]; - - // The model does not support any streaming parameters. - return this.createModel(extension.values, callbacks, true); + return this.createModel(extension.values, true); }); return next(context); @@ -115,19 +105,35 @@ export class OpenAIModelExtension implements Extension, + modelName: modelName, + providerName: 'open-ai', + }; } } @@ -138,10 +144,6 @@ type OpenAIModelExtensionConfiguration = ExtensionConfiguration & { seed: number; presencePenalty: number; frequencyPenalty: number; - effort?: 'low' | 'medium' | 'high'; -}; - -type OpenAITokenEstimation = { - completionTokens?: number; - promptTokens?: number; + effort?: 'minimal' | 'low' | 'medium' | 'high'; + summary?: 'detailed' | 'auto'; }; diff --git a/backend/src/extensions/models/vertex-ai.spec.ts b/backend/src/extensions/models/vertex-ai.spec.ts deleted file mode 100644 index db6fb307e..000000000 --- a/backend/src/extensions/models/vertex-ai.spec.ts +++ /dev/null @@ -1,16 +0,0 @@ -import { modelExtensionTestSuite } from './model-test.base'; -import { VertexAIModelExtension } from './vertex-al'; - -const instance = { - invoke: jest.fn().mockReturnThis(), -}; - -jest.mock('@langchain/google-vertexai', () => { - return { - ChatVertexAI: jest.fn().mockImplementation(() => { - return instance; - }), - }; -}); - -describe('VertexAIModelExtension', () => modelExtensionTestSuite(VertexAIModelExtension, instance)); diff --git a/backend/src/extensions/models/vertex-al.ts b/backend/src/extensions/models/vertex-al.ts deleted file mode 100644 index 26a2b48de..000000000 --- a/backend/src/extensions/models/vertex-al.ts +++ /dev/null @@ -1,64 +0,0 @@ -import { CallbackHandlerMethods } from '@langchain/core/callbacks/base'; -import { ChatVertexAI } from '@langchain/google-vertexai'; -import { ChatContext, ChatMiddleware, ChatNextDelegate, GetContext } from 'src/domain/chat'; -import { Extension, ExtensionConfiguration, ExtensionEntity, ExtensionSpec } from 'src/domain/extensions'; -import { User } from 'src/domain/users'; -import { I18nService } from '../../localization/i18n.service'; -import { getEstimatedUsageCallback } from './internal/utils'; - -@Extension() -export class VertexAIModelExtension implements Extension { - constructor(private readonly i18n: I18nService) {} - - get spec(): ExtensionSpec { - return { - name: 'vertex-ai-model', - title: this.i18n.t('texts.extensions.vertexai.title'), - logo: '', - description: this.i18n.t('texts.extensions.vertexai.description'), - type: 'llm', - arguments: { - modelName: { - type: 'string', - title: this.i18n.t('texts.extensions.common.modelName'), - required: true, - format: 'select', - enum: ['gemini-1.0-pro', 'gemini-1.0-pro-vision'], - showInList: true, - }, - }, - }; - } - - async test(configuration: VertexAIModelExtensionConfiguration) { - const model = this.createModel(configuration); - - await model.invoke('Just a test call'); - } - - getMiddlewares(_: User, extension: ExtensionEntity): Promise { - const middleware = { - invoke: async (context: ChatContext, getContext: GetContext, next: ChatNextDelegate): Promise => { - context.llms[this.spec.name] = await context.cache.get('open-ai-model', extension.values, () => { - // The model does not provide the token usage, therefore estimate it. - const callbacks = [getEstimatedUsageCallback('vertex-ai', extension.values.modelName, getContext)]; - - // The model does not support any streaming parameters. - return this.createModel(extension.values, callbacks); - }); - - return next(context); - }, - }; - - return Promise.resolve([middleware]); - } - - private createModel(configuration: VertexAIModelExtensionConfiguration, callbacks?: CallbackHandlerMethods[]) { - const { modelName } = configuration; - - return new ChatVertexAI({ modelName, callbacks }); - } -} - -type VertexAIModelExtensionConfiguration = ExtensionConfiguration & { modelName: string }; diff --git a/backend/src/extensions/module.ts b/backend/src/extensions/module.ts index 661f5e75e..f60f05e5b 100644 --- a/backend/src/extensions/module.ts +++ b/backend/src/extensions/module.ts @@ -8,38 +8,34 @@ import { TypeOrmModule } from '@nestjs/typeorm'; import { AuthModule } from 'src/domain/auth/module'; import { BucketEntity, CacheEntity, FileEntity } from 'src/domain/database'; import { Extension } from 'src/domain/extensions'; +import { ContextExtension } from './examples/show-context'; +import { UserArgsExtension } from './examples/user-args'; import { AzureOpenAIModelExtension } from './models/azure-open-ai'; -import { AzureOpenAIReasoningModelExtension } from './models/azure-open-ai-reasoning'; import { BedrockModelExtension } from './models/bedrock-ai'; import { GoogleGenAIModelExtension } from './models/google-genai'; import { MistralModelExtension } from './models/mistral'; +import { NvidiaModelExtension } from './models/nvidia'; import { OllamaModelExtension } from './models/ollama'; import { OpenAIModelExtension } from './models/open-ai'; import { OpenAICompatibleModelExtension } from './models/open-ai-compatible'; -import { VertexAIModelExtension } from './models/vertex-al'; import { CustomPromptExtension } from './other/custom'; -import { HubPromptExtension } from './other/hub'; -import { LangfuseExtension } from './other/langfuse'; import { SpeechToTextExtension } from './other/speech-to-text'; import { SummaryPromptExtension } from './other/summary'; -import { Always42Extension } from './tools/always-42'; import { AzureAISearchExtension } from './tools/azure-ai-search'; import { AzureDallEExtension } from './tools/azure-dall-e'; +import { AzureGPTImage1Extension } from './tools/azure-gpt-image-1'; import { BingWebSearchExtension } from './tools/bing-web-search'; import { BraveWebSearchExtension } from './tools/brave-web-search'; import { CalculatorExtension } from './tools/calculator'; -import { ConfirmExtension } from './tools/confirm'; import { DallEExtension } from './tools/dall-e'; import { DuckduckgoWebSearchExtension } from './tools/duckduckgo-web-search'; import { FilesExtension } from './tools/files'; import { FilesConversationExtension } from './tools/files-conversation'; import { FilesVisionExtension } from './tools/files-vision'; +import { GPTImage1Extension } from './tools/gpt-image-1'; import { GroundingWithBingSearchExtension } from './tools/grounding-with-bing'; import { MCPToolsExtension } from './tools/mcp-tools'; import { OpenApiExtension } from './tools/open-api'; -import { ContextExtension } from './tools/show-context'; -import { SimpleInputExtension } from './tools/simple-input'; -import { UserArgsExtension } from './tools/user-args'; import { WholeFilesExtension } from './tools/whole-files-conversation'; const extensionClassSuffix = 'Extension'; @@ -106,16 +102,14 @@ export class ExtensionLibraryModule { imports: [ConfigModule, AuthModule, CqrsModule, TypeOrmModule.forFeature([CacheEntity, BucketEntity, FileEntity])], providers: [ ...dynamicProviders, - Always42Extension, AzureAISearchExtension, AzureDallEExtension, + AzureGPTImage1Extension, AzureOpenAIModelExtension, - AzureOpenAIReasoningModelExtension, BedrockModelExtension, BingWebSearchExtension, BraveWebSearchExtension, CalculatorExtension, - ConfirmExtension, ContextExtension, CustomPromptExtension, DallEExtension, @@ -124,20 +118,18 @@ export class ExtensionLibraryModule { FilesExtension, FilesVisionExtension, GoogleGenAIModelExtension, + GPTImage1Extension, GroundingWithBingSearchExtension, - HubPromptExtension, - LangfuseExtension, MCPToolsExtension, MistralModelExtension, + NvidiaModelExtension, OllamaModelExtension, OpenAICompatibleModelExtension, OpenAIModelExtension, OpenApiExtension, - SimpleInputExtension, SpeechToTextExtension, SummaryPromptExtension, UserArgsExtension, - VertexAIModelExtension, WholeFilesExtension, ], }; diff --git a/backend/src/extensions/other/hub.ts b/backend/src/extensions/other/hub.ts deleted file mode 100644 index a4e0f5fa5..000000000 --- a/backend/src/extensions/other/hub.ts +++ /dev/null @@ -1,53 +0,0 @@ -import { ChatPromptTemplate } from '@langchain/core/prompts'; -import { pull } from 'langchain/hub'; -import { ChatContext, ChatMiddleware, ChatNextDelegate, GetContext } from 'src/domain/chat'; -import { Extension, ExtensionConfiguration, ExtensionEntity, ExtensionSpec } from 'src/domain/extensions'; -import { User } from 'src/domain/users'; -import { I18nService } from '../../localization/i18n.service'; - -@Extension() -export class HubPromptExtension implements Extension { - constructor(private readonly i18n: I18nService) {} - private readonly cache: Record = {}; - - get spec(): ExtensionSpec { - return { - name: 'hub-prompt', - title: this.i18n.t('texts.extensions.hubPrompt.title'), - logo: ' ', - description: this.i18n.t('texts.extensions.hubPrompt.description'), - type: 'other', - arguments: { - name: { - type: 'string', - title: this.i18n.t('texts.extensions.common.name'), - required: true, - }, - }, - }; - } - - async test(configuration: HubPromptExtensionConfiguration) { - const { name } = configuration; - - await pull(name); - } - - getMiddlewares(_: User, extension: ExtensionEntity): Promise { - const middleware = { - invoke: async (context: ChatContext, getContext: GetContext, next: ChatNextDelegate): Promise => { - context.prompt = await context.cache.get(this.spec.name, extension.values, async () => { - const { name } = extension.values; - - return await pull(name); - }); - - return next(context); - }, - }; - - return Promise.resolve([middleware]); - } -} - -type HubPromptExtensionConfiguration = ExtensionConfiguration & { name: string }; diff --git a/backend/src/extensions/other/langfuse.ts b/backend/src/extensions/other/langfuse.ts deleted file mode 100644 index 5367e4557..000000000 --- a/backend/src/extensions/other/langfuse.ts +++ /dev/null @@ -1,65 +0,0 @@ -import { ChatContext, ChatMiddleware, ChatNextDelegate, GetContext } from 'src/domain/chat'; -import { Extension, ExtensionConfiguration, ExtensionEntity, ExtensionSpec } from 'src/domain/extensions'; -import { User } from 'src/domain/users'; -import { I18nService } from '../../localization/i18n.service'; - -@Extension() -export class LangfuseExtension implements Extension { - constructor(private readonly i18n: I18nService) {} - - get spec(): ExtensionSpec { - return { - name: 'langfuse', - title: this.i18n.t('texts.extensions.langfuse.title'), - logo: 'Langfuse', - description: this.i18n.t('texts.extensions.langfuse.description'), - type: 'other', - arguments: { - baseUrl: { - type: 'string', - title: this.i18n.t('texts.extensions.langfuse.baseUrl'), - description: this.i18n.t('texts.extensions.langfuse.baseUrlHint'), - default: 'https://cloud.langfuse.com', - required: true, - }, - publicKey: { - type: 'string', - format: 'password', - title: this.i18n.t('texts.extensions.langfuse.publicKey'), - required: true, - }, - secretKey: { - type: 'string', - format: 'password', - title: this.i18n.t('texts.extensions.langfuse.secretKey'), - required: true, - }, - }, - }; - } - - getMiddlewares(_: User, extension: ExtensionEntity): Promise { - const middleware = { - invoke: async (context: ChatContext, _: GetContext, next: ChatNextDelegate): Promise => { - const { CallbackHandler } = await import('langfuse-langchain'); - context.callbacks.push( - await context.cache.get(this.spec.name, extension.values, () => { - const { publicKey, secretKey, baseUrl } = extension.values; - context.callbacks.push(new CallbackHandler({ publicKey, secretKey, baseUrl })); - return new CallbackHandler({ - publicKey, - secretKey, - baseUrl, - }); - }), - ); - - return next(context); - }, - }; - - return Promise.resolve([middleware]); - } -} - -type LangfuseExtensionConfiguration = ExtensionConfiguration & { publicKey: string; baseUrl: string; secretKey: string }; diff --git a/backend/src/extensions/tools/azure-ai-search.ts b/backend/src/extensions/tools/azure-ai-search.ts index 0b532acac..af185258c 100644 --- a/backend/src/extensions/tools/azure-ai-search.ts +++ b/backend/src/extensions/tools/azure-ai-search.ts @@ -1,7 +1,6 @@ -import { StructuredTool } from '@langchain/core/tools'; import { Logger } from '@nestjs/common'; import { z } from 'zod'; -import { ChatContext, ChatMiddleware, ChatNextDelegate, GetContext } from 'src/domain/chat'; +import { ChatContext, ChatMiddleware, ChatNextDelegate, GetContext, NamedStructuredTool } from 'src/domain/chat'; import { Extension, ExtensionConfiguration, ExtensionEntity, ExtensionSpec } from 'src/domain/extensions'; import { User } from 'src/domain/users'; import { I18nService } from '../../localization/i18n.service'; @@ -65,7 +64,7 @@ export class AzureAISearchExtension implements Extension): Promise { const middleware = { - invoke: async (context: ChatContext, getContext: GetContext, next: ChatNextDelegate): Promise => { + invoke: async (context: ChatContext, _: GetContext, next: ChatNextDelegate): Promise => { context.tools.push(new InternalTool(extension.values, extension.externalId)); return next(context); }, @@ -75,7 +74,7 @@ export class AzureAISearchExtension implements Extension { - return client.post(`/deployments/${fields.modelName}/images/generations?api-version=${fields.apiVersion}`, { - body, - ...options, - }); - }; } } diff --git a/backend/src/extensions/tools/azure-gpt-image-1.ts b/backend/src/extensions/tools/azure-gpt-image-1.ts new file mode 100644 index 000000000..09b30b682 --- /dev/null +++ b/backend/src/extensions/tools/azure-gpt-image-1.ts @@ -0,0 +1,53 @@ +import { AzureOpenAI } from 'openai'; +import { Extension, ExtensionSpec } from '../../domain/extensions'; +import { GPTImage1Extension, GPTImage1ExtensionConfiguration } from './gpt-image-1'; + +@Extension() +export class AzureGPTImage1Extension extends GPTImage1Extension { + get spec(): ExtensionSpec { + const baseSpec = super.spec; + return { + ...baseSpec, + name: 'azure-gpt-image-1', + title: this.i18n.t('texts.extensions.azure-gpt-image-1.title'), + logo: '', + description: this.i18n.t('texts.extensions.azure-gpt-image-1.description'), + type: 'tool', + arguments: { + ...baseSpec.arguments, + instanceName: { + type: 'string', + title: this.i18n.t('texts.extensions.common.instanceName'), + required: true, + }, + deploymentName: { + type: 'string', + title: this.i18n.t('texts.extensions.common.deploymentName'), + required: true, + }, + apiVersion: { + type: 'string', + title: this.i18n.t('texts.extensions.common.apiVersion'), + required: true, + format: 'select', + examples: ['2024-02-15-preview'], + }, + }, + }; + } + + protected createGptImageClient(configuration: AzureGPTImage1ExtensionConfiguration): AzureOpenAI { + return new AzureOpenAI({ + apiKey: configuration.apiKey, + apiVersion: configuration.apiVersion, + deployment: configuration.deploymentName, + endpoint: `https://${configuration.instanceName}.openai.azure.com/`, + }); + } +} + +export type AzureGPTImage1ExtensionConfiguration = GPTImage1ExtensionConfiguration & { + instanceName: string; + apiVersion: string; + deploymentName: string; +}; diff --git a/backend/src/extensions/tools/bing-web-search.ts b/backend/src/extensions/tools/bing-web-search.ts index b5c9845f0..311b1cd7e 100644 --- a/backend/src/extensions/tools/bing-web-search.ts +++ b/backend/src/extensions/tools/bing-web-search.ts @@ -1,7 +1,6 @@ -import { StructuredTool } from '@langchain/core/tools'; import { Logger } from '@nestjs/common'; import { z } from 'zod'; -import { ChatContext, ChatMiddleware, ChatNextDelegate, GetContext } from 'src/domain/chat'; +import { ChatContext, ChatMiddleware, ChatNextDelegate, GetContext, NamedStructuredTool } from 'src/domain/chat'; import { Extension, ExtensionConfiguration, ExtensionEntity, ExtensionSpec } from 'src/domain/extensions'; import { User } from 'src/domain/users'; import { I18nService } from '../../localization/i18n.service'; @@ -31,7 +30,7 @@ export class BingWebSearchExtension implements Extension): Promise { const middleware = { - invoke: async (context: ChatContext, getContext: GetContext, next: ChatNextDelegate): Promise => { + invoke: async (context: ChatContext, _: GetContext, next: ChatNextDelegate): Promise => { context.tools.push(new InternalTool(extension.values, extension.externalId)); return next(context); }, @@ -41,7 +40,7 @@ export class BingWebSearchExtension implements Extension): Promise { const middleware = { invoke: async (context: ChatContext, getContext: GetContext, next: ChatNextDelegate): Promise => { - context.tools.push(new InternalTool(extension.values, extension.externalId)); + context.tools.push(new InternalTool(extension.values, extension.externalId, context)); return next(context); }, }; @@ -41,38 +39,112 @@ export class BraveWebSearchExtension implements Extension): Promise { - return (await this.braveSearch.invoke(arg.query)) as string; + const { query } = arg; + + const headers = { + 'X-Subscription-Token': this.apiKey, + Accept: 'application/json', + }; + const encodedQuery = encodeURIComponent(query); + const searchUrl = new URL(`https://api.search.brave.com/res/v1/web/search?q=${encodedQuery}`); + + const response = await fetch(searchUrl, { headers }); + + if (!response.ok) { + throw new Error(`Failed to fetch data from Brave Search: ${response.status} ${response.statusText}`); + } + + const parsedResponse = (await response.json()) as SearchResponse; + const results = parsedResponse.web?.results; + const items = Array.isArray(results) ? results : []; + + const toolResult = []; + const sources: Source[] = []; + for (const item of items) { + const { title, url, description, content_type } = item; + + toolResult.push({ title, link: url, snippet: description }); + + const source: Source = { + title: title ?? 'Search result', + chunk: { + content: description ?? 'no content', + score: 0, + }, + document: { + uri: url, + mimeType: content_type ?? 'text/html', + link: url, + }, + }; + sources.push(source); + } + + this.context.history?.addSources(this.name, sources); + return JSON.stringify(toolResult); } } export type BraveWebSearchExtensionConfiguration = ExtensionConfiguration & { apiKey: string; }; + +// see also https://api-dashboard.search.brave.com/app/documentation/web-search/responses +type SearchResponse = { + type: 'search'; + // discussions?: Discussions + // faq?: FAQ + // infobox?: GraphInfobox + // locations?: Locations + // mixed?: MixedResponse + // news?: News + // query?: Query + // videos?: Videos + web?: Search; + // summarizer?: Summarizer + // rich?: RichCallbackInfo +}; + +type Search = { + type: 'search'; + results: SearchResult[]; + family_friendly: boolean; +}; + +type Result = { + title: string; + url: string; + description?: string; + language: string; + page_age?: string; + page_fetched?: string; +}; + +type SearchResult = Result & { + type: 'search_result'; + content_type?: string; + extra_snippets?: string[]; +}; diff --git a/backend/src/extensions/tools/calculator.ts b/backend/src/extensions/tools/calculator.ts index 287958e11..821100d4e 100644 --- a/backend/src/extensions/tools/calculator.ts +++ b/backend/src/extensions/tools/calculator.ts @@ -1,5 +1,6 @@ -import { Calculator } from '@langchain/community/tools/calculator'; -import { ChatContext, ChatMiddleware, ChatNextDelegate, GetContext } from 'src/domain/chat'; +import { Parser } from 'expr-eval'; +import z from 'zod'; +import { ChatContext, ChatMiddleware, ChatNextDelegate, GetContext, NamedStructuredTool } from 'src/domain/chat'; import { Extension, ExtensionSpec } from 'src/domain/extensions'; import { I18nService } from '../../localization/i18n.service'; @@ -7,8 +8,6 @@ import { I18nService } from '../../localization/i18n.service'; export class CalculatorExtension implements Extension { constructor(private readonly i18n: I18nService) {} - private readonly tool = new Calculator(); - get spec(): ExtensionSpec { return { name: 'calculator', @@ -44,8 +43,8 @@ export class CalculatorExtension implements Extension { getMiddlewares(): Promise { const middleware = { - invoke: async (context: ChatContext, getContext: GetContext, next: ChatNextDelegate): Promise => { - context.tools.push(this.tool); + invoke: async (context: ChatContext, _: GetContext, next: ChatNextDelegate): Promise => { + context.tools.push(new InternalTool()); return next(context); }, }; @@ -53,3 +52,18 @@ export class CalculatorExtension implements Extension { return Promise.resolve([middleware]); } } + +class InternalTool extends NamedStructuredTool { + readonly name = 'calculator'; + readonly description = + 'Useful for getting the result of a math expression. The input to this tool should be a valid mathematical expression that could be executed by a simple calculator.'; + readonly displayName = 'Calculator'; + + readonly schema = z.object({ + input: z.string(), + }); + + protected async _call({ input }: z.infer): Promise { + return Promise.resolve(String(Parser.evaluate(input))); + } +} diff --git a/backend/src/extensions/tools/dall-e.ts b/backend/src/extensions/tools/dall-e.ts index 01dfc5806..00180b3fc 100644 --- a/backend/src/extensions/tools/dall-e.ts +++ b/backend/src/extensions/tools/dall-e.ts @@ -1,10 +1,10 @@ -import { Tool } from '@langchain/core/tools'; -import { DallEAPIWrapper } from '@langchain/openai'; import { forwardRef, Inject, Logger } from '@nestjs/common'; import { CommandBus } from '@nestjs/cqrs'; +import OpenAI from 'openai'; import * as uuid from 'uuid'; +import * as z from 'zod'; import { AuthService } from 'src/domain/auth'; -import { ChatContext, ChatMiddleware, ChatNextDelegate, GetContext } from 'src/domain/chat'; +import { ChatContext, ChatMiddleware, ChatNextDelegate, GetContext, NamedStructuredTool } from 'src/domain/chat'; import { Extension, ExtensionConfiguration, ExtensionEntity, ExtensionSpec } from 'src/domain/extensions'; import { UploadBlob } from 'src/domain/settings'; import { User } from 'src/domain/users'; @@ -70,18 +70,20 @@ export class DallEExtension implements Extension { } async test(configuration: DallEExtensionConfiguration) { - const wrapper = this.createWrapper(configuration); + const client = this.createDallEClient(configuration); - await wrapper.invoke('Dog'); + await client.images.generate({ + model: configuration.modelName, + prompt: 'test', + }); } async getMiddlewares(_user: User, extension: ExtensionEntity): Promise { const middleware = { invoke: async (context: ChatContext, getContext: GetContext, next: ChatNextDelegate): Promise => { const tool = await context.cache.get(this.spec.name, extension.values, () => { - const wrapper = this.createWrapper(extension.values); - - return Promise.resolve(new InternalTool(this.authService, wrapper, this.commandBus, this.spec)); + const client = this.createDallEClient(extension.values); + return Promise.resolve(new InternalTool(this.authService, client, this.commandBus, this.spec, extension.values)); }); context.tools.push(tool); @@ -93,20 +95,14 @@ export class DallEExtension implements Extension { return Promise.resolve([middleware]); } - protected createWrapper(configuration: DallEExtensionConfiguration) { - const { apiKey, modelName, quality, size, style } = configuration; - - return new DallEAPIWrapper({ - modelName, - quality, - style, - size, - openAIApiKey: apiKey, + protected createDallEClient(configuration: DallEExtensionConfiguration) { + return new OpenAI({ + apiKey: configuration.apiKey, }); } } -class InternalTool extends Tool { +class InternalTool extends NamedStructuredTool { readonly name: string; readonly description = 'A tool to generate images from a prompt. It returns a link to an image. Show the image to the user by using Markdown to embed the image into your response, like `![alttext](link/from/the/response)`.'; @@ -114,45 +110,51 @@ class InternalTool extends Tool { readonly returnDirect = false; private readonly logger = new Logger(InternalTool.name); - get lc_id() { - return [...this.lc_namespace, this.name]; - } + readonly schema = z.object({ + input: z.string(), + }); constructor( private readonly authService: AuthService, - private readonly wrapper: DallEAPIWrapper, + private readonly client: OpenAI, private readonly commandBus: CommandBus, spec: ExtensionSpec, + private readonly configuration: DallEExtensionConfiguration, ) { super(); this.name = spec.name; this.displayName = spec.title; } - protected async _call(arg: string): Promise { + protected async _call({ input }: z.infer): Promise { try { - const image = (await this.wrapper.invoke(arg)) as string; + const response = await this.client.images.generate({ + model: this.configuration.modelName, + prompt: input, + size: this.configuration.size, + response_format: 'b64_json', + }); - // Download the image to put it in our store. - const downloaded = await fetch(image); - if (!downloaded.ok) { - return 'Failed to download image'; - } + const imageData = response?.data?.[0]; - // Would be great to have a solution that streams the buffer to the database. - const buffer = await downloaded.arrayBuffer(); + if (!imageData) { + throw new Error('No image data received from OpenAI'); + } const id = uuid.v4(); + const contentType = response.output_format || 'png'; + let imageBuffer: Buffer; + let fileName; + + if (imageData.b64_json) { + imageBuffer = Buffer.from(imageData.b64_json, 'base64'); + fileName = `${id}.${contentType}`; + } else { + throw new Error('No valid image data format received from OpenAI'); + } await this.commandBus.execute( - new UploadBlob( - id, - Buffer.from(buffer), - downloaded.headers.get('Content-Type') || 'unknown', - downloaded.headers.get('filename') || 'unknown', - buffer.byteLength, - BlobCategory.LLM_IMAGE, - ), + new UploadBlob(id, imageBuffer, contentType, fileName, imageBuffer.length, BlobCategory.LLM_IMAGE), ); return `${this.authService.config.baseUrl}/blobs/${id}`; diff --git a/backend/src/extensions/tools/duckduckgo-web-search.ts b/backend/src/extensions/tools/duckduckgo-web-search.ts index 91f28aea4..5de695905 100644 --- a/backend/src/extensions/tools/duckduckgo-web-search.ts +++ b/backend/src/extensions/tools/duckduckgo-web-search.ts @@ -1,7 +1,6 @@ -import { DuckDuckGoSearch } from '@langchain/community/tools/duckduckgo_search'; -import { StructuredTool } from '@langchain/core/tools'; +import { search } from 'duck-duck-scrape'; import z from 'zod'; -import { ChatContext, ChatMiddleware, ChatNextDelegate, GetContext } from 'src/domain/chat'; +import { ChatContext, ChatMiddleware, ChatNextDelegate, GetContext, NamedStructuredTool, Source } from 'src/domain/chat'; import { Extension, ExtensionConfiguration, ExtensionEntity, ExtensionSpec } from 'src/domain/extensions'; import { User } from 'src/domain/users'; import { I18nService } from '../../localization/i18n.service'; @@ -32,7 +31,7 @@ export class DuckduckgoWebSearchExtension implements Extension): Promise { const middleware = { invoke: async (context: ChatContext, getContext: GetContext, next: ChatNextDelegate): Promise => { - context.tools.push(new InternalTool(extension.values, extension.externalId)); + context.tools.push(new InternalTool(extension.values, extension.externalId, context)); return next(context); }, }; @@ -41,33 +40,61 @@ export class DuckduckgoWebSearchExtension implements Extension): Promise { - return (await this.duckduckgoSearch.invoke(arg.query)) as string; + const { query } = arg; + + console.log(`DuckDuckGo Web Search for query: ${query}`); + + const items = (await search(query)).results.slice(0, this.maxResults); + + console.log(items); + + const toolResult = []; + const sources: Source[] = []; + for (const item of items) { + const { title, url, description } = item; + + toolResult.push({ title, link: url, snippet: description }); + + const source: Source = { + title: title ?? 'Search result', + chunk: { + content: description ?? 'no content', + score: 0, + }, + document: { + uri: url, + mimeType: 'text/html', + link: url, + }, + }; + sources.push(source); + } + + this.context.history?.addSources(this.name, sources); + return JSON.stringify(toolResult); } } diff --git a/backend/src/extensions/tools/files-conversation.ts b/backend/src/extensions/tools/files-conversation.ts index bdd5310ac..77eda28dc 100644 --- a/backend/src/extensions/tools/files-conversation.ts +++ b/backend/src/extensions/tools/files-conversation.ts @@ -1,11 +1,12 @@ -import { StructuredTool } from '@langchain/core/tools'; import { Logger, NotFoundException } from '@nestjs/common'; import { QueryBus } from '@nestjs/cqrs'; +import { In } from 'typeorm'; import { z } from 'zod'; -import { ChatContext, ChatMiddleware, ChatNextDelegate, GetContext } from 'src/domain/chat'; +import { ChatContext, ChatMiddleware, ChatNextDelegate, GetContext, NamedStructuredTool } from 'src/domain/chat'; import { Extension, ExtensionEntity, ExtensionSpec } from 'src/domain/extensions'; import { User } from 'src/domain/users'; -import { Bucket, GetFiles, GetFilesResponse, SearchFiles, SearchFilesResponse } from '../../domain/files'; +import { FileEntity } from '../../domain/database'; +import { Bucket, SearchFiles, SearchFilesResponse } from '../../domain/files'; import { FilesExtension, FilesExtensionConfiguration } from './files'; @Extension() @@ -56,7 +57,9 @@ export class FilesConversationExtension extends FilesExtension x.id)) }) + : []; let description = 'Use this tool to semantically search the contents of files uploaded by the user in this conversation.\n\n'; @@ -98,6 +101,7 @@ export class FilesConversationExtension extends FilesExtension): Promise { try { - const files: GetFilesResponse = await this.queryBus.execute( - new GetFiles({ - page: 0, - pageSize: 10000, - user: this.context.user, - bucketIdOrType: this.bucket.id, - conversationId: this.context.conversationId, - }), - ); - - const externalDocumentIds = files.files.map((file) => file.externalDocumentId); + const fileIds = this.files.map((file) => file.id); const result: SearchFilesResponse = await this.queryBus.execute( - new SearchFiles( - this.bucket.id, - arg.query, - this.context.user, - this.take, - externalDocumentIds, - this.context.conversationId, - ), + new SearchFiles(this.bucket.id, arg.query, this.context.user, this.take, fileIds), ); const sources = this.showSources ?? false; diff --git a/backend/src/extensions/tools/files-vision.ts b/backend/src/extensions/tools/files-vision.ts index 9118ef747..7faca1984 100644 --- a/backend/src/extensions/tools/files-vision.ts +++ b/backend/src/extensions/tools/files-vision.ts @@ -1,26 +1,14 @@ -import { DynamicStructuredToolInput } from '@langchain/core/dist/tools'; -import { StringOutputParser } from '@langchain/core/output_parsers'; -import { ChatPromptTemplate } from '@langchain/core/prompts'; -import { DynamicStructuredTool } from '@langchain/core/tools'; import { forwardRef, Inject, Logger } from '@nestjs/common'; import { QueryBus } from '@nestjs/cqrs'; +import { generateText } from 'ai'; import { z } from 'zod'; -import { ChatContext, ChatMiddleware, ChatNextDelegate, GetContext } from 'src/domain/chat'; +import { ChatContext, ChatMiddleware, ChatNextDelegate, GetContext, NamedDynamicStructuredTool } from 'src/domain/chat'; import { Extension, ExtensionEntity, ExtensionSpec } from 'src/domain/extensions'; import { User } from 'src/domain/users'; import { GetFiles, GetFilesResponse, matchExtension } from '../../domain/files'; import { I18nService } from '../../localization/i18n.service'; -export class NamedDynamicStructuredTool extends DynamicStructuredTool { - displayName: string; - - constructor({ displayName, ...toolInput }: DynamicStructuredToolInput & { displayName: string }) { - super(toolInput); - this.displayName = displayName; - } -} - -type FilesVisionExtensionConfiguration = { fileNameExtensions: string[]; maxFiles: [] }; +export type FilesVisionExtensionConfiguration = { fileNameExtensions: string[]; maxFiles: number }; @Extension() export class FilesVisionExtension implements Extension { @@ -86,6 +74,7 @@ export class FilesVisionExtension implements Extension {}, @@ -112,6 +101,7 @@ export class FilesVisionExtension implements Extension { const llm = context.llms[context.llm ?? '']; if (!llm) { @@ -121,10 +111,9 @@ export class FilesVisionExtension implements Extension[0] = [ - { - role: 'human', - content: images.map((imageUrl) => ({ - type: 'image_url', - image_url: imageUrl, - })), - }, - ['user', context.input], - ]; - try { - const prompt = ChatPromptTemplate.fromMessages(messages); - const outputParser = new StringOutputParser(); - const outputChain = prompt.pipe(llm).pipe(outputParser); - const result = await outputChain.invoke({}); - return `Add the following content to your response without modification: ${result}`; + const { text } = await generateText({ + model: llm.model, + prompt: [ + { role: 'user' as const, content: images.map((x) => ({ type: 'image', image: x })) }, + { role: 'user' as const, content: context.input }, + ], + ...llm.options, + }); + return `Add the following content to your response without modification: ${text}`; } catch (err) { //TODO: for unsupported models there should be error handling this.logger.error('Error reading image', err); diff --git a/backend/src/extensions/tools/files.ts b/backend/src/extensions/tools/files.ts index e19c09bc2..4cfc6a84b 100644 --- a/backend/src/extensions/tools/files.ts +++ b/backend/src/extensions/tools/files.ts @@ -1,19 +1,15 @@ -import { StructuredTool } from '@langchain/core/tools'; import { forwardRef, Inject, Logger, NotFoundException } from '@nestjs/common'; import { QueryBus } from '@nestjs/cqrs'; import { InjectRepository } from '@nestjs/typeorm'; import { z } from 'zod'; -import { ChatContext, ChatMiddleware, ChatNextDelegate, GetContext } from 'src/domain/chat'; +import { ChatContext, ChatMiddleware, ChatNextDelegate, GetContext, NamedStructuredTool } from 'src/domain/chat'; import { BucketEntity, BucketRepository, FileEntity, FileRepository } from 'src/domain/database'; -import { Extension, ExtensionArgument, ExtensionConfiguration, ExtensionEntity, ExtensionSpec } from 'src/domain/extensions'; +import { Extension, ExtensionConfiguration, ExtensionEntity, ExtensionSpec } from 'src/domain/extensions'; import { Bucket, GetDocumentContent, GetDocumentContentResponse, SearchFiles, SearchFilesResponse } from 'src/domain/files'; +import { GetDocumentPdf, GetDocumentPdfResponse } from 'src/domain/files/use-cases/get-document-pdf'; import { User } from 'src/domain/users'; import { I18nService } from '../../localization/i18n.service'; -type UserArgs = { - fileIdFilter?: string; -}; - @Extension() export class FilesExtension implements Extension @@ -60,6 +56,13 @@ export class FilesExtension { - switch (argument.type) { - case 'string': - case 'array': - case 'number': - return argument.default; - } - }; - - return Object.fromEntries(Object.keys(userArguments).map((key) => [key, getDefault(userArguments[key])])); - } - getMiddlewares(user: User, extension: ExtensionEntity): Promise { const middleware = { invoke: async (context: ChatContext, getContext: GetContext, next: ChatNextDelegate): Promise => { - const { bucket, description, take } = extension.values; + const { bucket, description, take, showSources } = extension.values; let toolDescription = 'Use this tool to semantically search files.\n\n'; toolDescription += [ @@ -149,11 +138,21 @@ export class FilesExtension x.id), + showSources, ), ); } else { context.tools.push( - new InternalTool(enrichedDescription, this.queryBus, context, bucketEntity, take, extension.externalId, null), + new InternalTool( + enrichedDescription, + this.queryBus, + context, + bucketEntity, + take, + extension.externalId, + null, + showSources, + ), ); } @@ -169,17 +168,27 @@ export class FilesExtension x != null); } + + async getDocument(configuration: FilesExtensionConfiguration, documentUri: string, user: User) { + const bucketId = configuration.bucket; + const response: GetDocumentPdfResponse = await this.queryBus.execute(new GetDocumentPdf(user, bucketId, documentUri)); + + const buffer = await response.documentPdf?.bytes(); + if (!buffer) { + throw new NotFoundException('Document can not be retrieved.'); + } + + const file = new File([buffer], '', { type: 'application/pdf' }); + + return Promise.resolve(file); + } } -class InternalTool extends StructuredTool { +class InternalTool extends NamedStructuredTool { readonly name: string; readonly displayName = 'Files'; private readonly logger = new Logger(`${FilesExtension.name}$${InternalTool.name}`); - get lc_id() { - return [...this.lc_namespace, this.name]; - } - readonly schema = z.object({ query: z.string().describe('The query'), }); @@ -192,6 +201,7 @@ class InternalTool extends StructuredTool { private readonly take: number, private readonly extensionExternalId: string, private readonly fileFilter: number[] | null, + private readonly showSources: boolean, ) { super(); @@ -200,14 +210,13 @@ class InternalTool extends StructuredTool { protected async _call(arg: z.infer): Promise { try { - // TODO: adjust file filter format const result: SearchFilesResponse = await this.queryBus.execute( new SearchFiles(this.bucket.id, arg.query, this.context.user, this.take, this.fileFilter, this.context.conversationId), ); - if (result.sources) { + if (result.sources && this.showSources) { this.context.history?.addSources(this.extensionExternalId, result.sources); - } else if (result.debug) { + } else if (result.debug && this.showSources) { this.context.result.next({ type: 'debug', content: result.debug }); } @@ -225,4 +234,5 @@ export type FilesExtensionConfiguration = ExtensionConfiguration & { description: string; bucket: number; take: number; + showSources: boolean; }; diff --git a/backend/src/extensions/tools/gpt-image-1.ts b/backend/src/extensions/tools/gpt-image-1.ts new file mode 100644 index 000000000..3412afd67 --- /dev/null +++ b/backend/src/extensions/tools/gpt-image-1.ts @@ -0,0 +1,156 @@ +import { forwardRef, Inject, Logger } from '@nestjs/common'; +import { CommandBus } from '@nestjs/cqrs'; +import OpenAI from 'openai'; +import * as uuid from 'uuid'; +import { z } from 'zod'; +import { AuthService } from 'src/domain/auth'; +import { ChatContext, ChatMiddleware, ChatNextDelegate, GetContext, NamedStructuredTool } from 'src/domain/chat'; +import { Extension, ExtensionConfiguration, ExtensionEntity, ExtensionSpec } from 'src/domain/extensions'; +import { UploadBlob } from 'src/domain/settings'; +import { User } from 'src/domain/users'; +import { BlobCategory } from '../../domain/database'; +import { I18nService } from '../../localization/i18n.service'; + +@Extension() +export class GPTImage1Extension implements Extension { + constructor( + private readonly authService: AuthService, + @Inject(forwardRef(() => CommandBus)) + private readonly commandBus: CommandBus, + protected readonly i18n: I18nService, + ) {} + + get spec(): ExtensionSpec { + return { + name: 'gpt-image-1', + title: this.i18n.t('texts.extensions.gpt-image-1.title'), + logo: 'OpenAI icon', + description: this.i18n.t('texts.extensions.gpt-image-1.description'), + type: 'tool', + arguments: { + apiKey: { + type: 'string', + title: this.i18n.t('texts.extensions.common.apiKey'), + required: true, + format: 'password', + }, + quality: { + type: 'string', + title: this.i18n.t('texts.extensions.gpt-image-1.quality'), + required: false, + format: 'select', + enum: ['auto', 'high', 'medium', 'low'], + }, + size: { + type: 'string', + title: this.i18n.t('texts.extensions.gpt-image-1.size'), + required: false, + format: 'select', + enum: ['auto', '1024x1024', '1536x1024', '1024x1536'], + }, + }, + }; + } + + async test(configuration: GPTImage1ExtensionConfiguration) { + const client = this.createGptImageClient(configuration); + + await client.images.generate({ + model: 'gpt-image-1', + prompt: 'test', + }); + } + + async getMiddlewares(user: User, extension: ExtensionEntity): Promise { + const middleware = { + invoke: async (context: ChatContext, getContext: GetContext, next: ChatNextDelegate): Promise => { + const tool = await context.cache.get(this.spec.name, extension.values, () => { + const client = this.createGptImageClient(extension.values); + return Promise.resolve(new InternalTool(this.authService, client, this.commandBus, this.spec, extension.values)); + }); + context.tools.push(tool); + + return next(context); + }, + }; + + return Promise.resolve([middleware]); + } + + protected createGptImageClient(configuration: GPTImage1ExtensionConfiguration) { + return new OpenAI({ + apiKey: configuration.apiKey, + }); + } +} + +class InternalTool extends NamedStructuredTool { + readonly name: string; + readonly description = + 'A tool to generate images from a prompt using GPT-Image-1. It returns a link to an image. Show the image to the user by using Markdown to embed the image into your response, like `![alttext](link/from/the/response)`.'; + readonly returnDirect = false; + private readonly logger = new Logger(InternalTool.name); + readonly displayName = this.name; + + readonly schema = z.object({ + prompt: z.string(), + }); + + constructor( + private readonly authService: AuthService, + private readonly client: OpenAI, + private readonly commandBus: CommandBus, + spec: ExtensionSpec, + private readonly configuration: GPTImage1ExtensionConfiguration, + ) { + super(); + this.name = spec.name; + } + + protected async _call({ prompt }: z.infer): Promise { + try { + const response = await this.client.images.generate({ + model: 'gpt-image-1', + prompt: prompt, + size: this.configuration.size, + }); + + const imageData = response?.data?.[0]; + + if (!imageData) { + throw new Error('No image data received from OpenAI'); + } + + const id = uuid.v4(); + const contentType = response.output_format || 'png'; + let imageBuffer: Buffer; + let fileName; + + if (imageData.b64_json) { + imageBuffer = Buffer.from(imageData.b64_json, 'base64'); + fileName = `${id}.${contentType}`; + } else { + throw new Error('No valid image data format received from OpenAI'); + } + + await this.commandBus.execute( + new UploadBlob(id, imageBuffer, contentType, fileName, imageBuffer.length, BlobCategory.LLM_IMAGE), + ); + + return `${this.authService.config.baseUrl}/blobs/${id}`; + } catch (error) { + if (error instanceof Error) { + this.logger.error(`Error occurred in extension ${this.name}: ${error.message}`, error.stack); + } else { + this.logger.error(`Unknown error occurred in extension ${this.name}: ${JSON.stringify(error)}`); + } + return 'Failed'; + } + } +} + +export type GPTImage1ExtensionConfiguration = ExtensionConfiguration & { + apiKey: string; + quality: 'auto' | 'high' | 'medium' | 'low'; + size: 'auto' | '1024x1024' | '1536x1024' | '1024x1536'; +}; diff --git a/backend/src/extensions/tools/grounding-with-bing.ts b/backend/src/extensions/tools/grounding-with-bing.ts index 09327febd..f6e6eed66 100644 --- a/backend/src/extensions/tools/grounding-with-bing.ts +++ b/backend/src/extensions/tools/grounding-with-bing.ts @@ -7,10 +7,9 @@ import { } from '@azure/ai-agents'; import { delay } from '@azure/core-util'; import { ClientSecretCredential } from '@azure/identity'; -import { StructuredTool } from '@langchain/core/tools'; import { Logger } from '@nestjs/common'; import { z } from 'zod'; -import { ChatContext, ChatMiddleware, ChatNextDelegate, GetContext, Source } from 'src/domain/chat'; +import { ChatContext, ChatMiddleware, ChatNextDelegate, GetContext, NamedStructuredTool, Source } from 'src/domain/chat'; import { Extension, ExtensionConfiguration, ExtensionEntity, ExtensionSpec } from 'src/domain/extensions'; import { User } from 'src/domain/users'; import { I18nService } from '../../localization/i18n.service'; @@ -84,7 +83,7 @@ export class GroundingWithBingSearchExtension implements Extension { + return jsonSchemaToZod(schema); +} + type MCPListToolsResultSchema = z.infer; enum Transport { @@ -69,15 +79,6 @@ interface ExtensionState extends Pick { changed?: boolean; } -export class NamedDynamicStructuredTool extends DynamicStructuredTool { - displayName: string; - - constructor({ displayName, ...toolInput }: DynamicStructuredToolInput & { displayName: string }) { - super(toolInput); - this.displayName = displayName; - } -} - // zod has no password type since it is handled as string so we introduce a whitelist to map password fields const passwordKeys = ['apiKey', 'api-key', 'password', 'credentials']; @@ -355,7 +356,7 @@ export class MCPToolsExtension implements Extension { return spec; } - async getDocument(configuration: Configuration, documentUri: string) { + async getDocument(configuration: Configuration, documentUri: string, _user: User) { const { client } = (await this.getTools(configuration)) ?? []; const req: ReadResourceRequest = { method: 'resources/read', @@ -470,7 +471,7 @@ export class MCPToolsExtension implements Extension { displayName, name: `${extension.externalId}_${name}`, description: params.description || description || name, - schema: jsonSchemaToZod(schema), + schema: jsonSchemaToZodInternal(schema), func: async (args: Record) => { const attributes = params.attributes ?? {}; const adminArgs = this.applyTemplates(context, this.getTemplateArgs(attributes, 'admin')); diff --git a/backend/src/extensions/tools/open-api.ts b/backend/src/extensions/tools/open-api.ts index bb6ad1582..a0a316ca4 100644 --- a/backend/src/extensions/tools/open-api.ts +++ b/backend/src/extensions/tools/open-api.ts @@ -1,10 +1,9 @@ -import { StructuredTool } from '@langchain/core/tools'; import { Logger } from '@nestjs/common'; import { InjectRepository } from '@nestjs/typeorm'; import { addMilliseconds, addYears } from 'date-fns'; import { MoreThan } from 'typeorm'; import { z } from 'zod'; -import { ChatContext, ChatMiddleware, ChatNextDelegate, FormActionType, GetContext } from 'src/domain/chat'; +import { ChatContext, ChatMiddleware, ChatNextDelegate, FormActionType, GetContext, NamedStructuredTool } from 'src/domain/chat'; import { CacheEntity, CacheRepository } from 'src/domain/database'; import { Extension, ExtensionConfiguration, ExtensionEntity, ExtensionSpec } from 'src/domain/extensions'; import { User } from 'src/domain/users'; @@ -115,16 +114,12 @@ export class OpenApiExtension implements Extension; readonly displayName: string; readonly description: string; - get lc_id() { - return [...this.lc_namespace, this.name]; - } - constructor( private readonly cache: CacheRepository, private readonly context: ChatContext, diff --git a/backend/src/extensions/tools/whole-files-conversation.ts b/backend/src/extensions/tools/whole-files-conversation.ts index 5c5f29d02..53a068860 100644 --- a/backend/src/extensions/tools/whole-files-conversation.ts +++ b/backend/src/extensions/tools/whole-files-conversation.ts @@ -1,8 +1,7 @@ -import { StructuredTool } from '@langchain/core/tools'; import { forwardRef, Inject, Logger } from '@nestjs/common'; import { QueryBus } from '@nestjs/cqrs'; import { z } from 'zod'; -import { ChatContext, ChatMiddleware, ChatNextDelegate, GetContext } from 'src/domain/chat'; +import { ChatContext, ChatMiddleware, ChatNextDelegate, GetContext, NamedStructuredTool } from 'src/domain/chat'; import { Extension, ExtensionConfiguration, ExtensionEntity, ExtensionSpec } from 'src/domain/extensions'; import { User } from 'src/domain/users'; import { GetFiles, GetFilesResponse } from '../../domain/files'; @@ -17,10 +16,6 @@ export class WholeFilesExtension implements Extension x.id) : undefined, withContent: true, }), @@ -137,15 +138,11 @@ export class WholeFilesExtension implements Extension => { + const contentType = response.headers.get('content-type') || ''; + if (contentType.includes('application/json')) { + return await response.json(); + } else { + return await response.text(); + } +}; + +const removeCredentials = (headers: HeadersInit): Record => { + const pattern = /(authorization|api-?key|token|secret|cookie)/i; + + const sanitizedHeaders: Record = {}; + new Headers(headers).forEach((value, key) => { + const lk = key.toLowerCase(); + if (pattern.test(lk)) { + return; + } + sanitizedHeaders[key] = value; + }); + return sanitizedHeaders; +}; + +const logger = new Logger('DebugModelRequestLogging'); + +export const fetchWithDebugLogging = + (extensionName: string) => async (url: string | Request | URL, options: RequestInit | undefined) => { + const response = await fetch(url, options); + if (process.env.DEBUG_MODEL_REQUESTS) { + const clonedResponse = response.clone(); + logger.log('Model request', { + extensionName, + url, + requestHeaders: removeCredentials(options?.headers ?? {}), + requestBody: JSON.parse(options?.body as string) as unknown, + responseHeaders: [...clonedResponse.headers.entries()], + responseBody: await extractResponseBody(clonedResponse), + }); + } + return response; + }; diff --git a/backend/src/localization/i18n/de/texts.json b/backend/src/localization/i18n/de/texts.json index 8ca7b93e9..2c2dd8e5d 100644 --- a/backend/src/localization/i18n/de/texts.json +++ b/backend/src/localization/i18n/de/texts.json @@ -7,7 +7,8 @@ "instanceName": "Instance Name", "apiVersion": "API-Version", "temperature": "Temperatur", - "effort": "Effort", + "reasoningEffort": "Reasoning Effort", + "reasoningSummary": "Reasoning Zusammenfassung", "seed": "Seed", "presencePenalty": "Presence Penalty", "frequencyPenalty": "Frequency Penalty", @@ -53,7 +54,7 @@ "description": "OpenAI LLM-Integration für Reasoning-Modelle" }, "langfuse": { - "title": "DEV: Langfuse", + "title": "Langfuse", "description": "Langfuse-Integration", "baseUrl": "Base url", "baseUrlHint": "Basis-URL von Langfuse (wenn self-hosted)", @@ -65,7 +66,7 @@ "description": "Mistral LLM-Integration" }, "ollama": { - "title": "DEV: Ollama", + "title": "Ollama", "description": "Ollama LLM-Integration" }, "openai": { @@ -74,9 +75,13 @@ "endpointHint": "Basis-URL des OpenAI-Endpunkts" }, "openaiCompatible": { - "title": "DEV: OpenAI kompatibel", + "title": "OpenAI kompatibel", "description": "OpenAI-kompatible LLM-Integration" }, + "nvidia": { + "title": "Nvidia NIM", + "description": "Nvidia NIM LLM-Integration" + }, "vertexai": { "title": "VertexAI", "description": "Vertex AI LLM-Integration" @@ -94,10 +99,6 @@ "description": "Definiert den Zusammenfassungs-Prompt, der für die Gesprächsbeschriftung verwendet wird.", "promptHint": "Verwende den {content}-Platzhalter für den tatsächlichen Verlauf." }, - "always42": { - "title": "DEV: Add 42", - "description": "Addiert immer 42 zur Summe von zwei Zahlen" - }, "azureSearch": { "title": "Azure AI Search", "description": "Führt eine Suche mit Azure AI Search durch", @@ -124,10 +125,6 @@ "description": "Führt eine Websuche mit Duckduckgo durch", "maxResults": "Anzahl der Suchergebnisse" }, - "confirm": { - "title": "DEV: Confirm", - "description": "Fragt nach Bestätigung" - }, "azureDalle": { "title": "Azure Dall-E", "description": "Generiert Bilder mit dem Azure DALL-E-Bildgenerator." @@ -150,8 +147,8 @@ "descriptionHint": "Beschreibt das Tool und die Daten im Index.", "bucketHint": "Zu verwendender Bucket.", "takeHint": "Die Anzahl der zurückzugebenden Ergebnisse.", - "filesInChat": "Dateien im Chat", - "filesInChatHint": "Dateien in einen Chat hochladen. Dateien sind nur in dem Chat verfügbar, in dem sie hochgeladen wurden. Der Wert 'Take' wird ignoriert", + "showSources": "Quellen anzeigen", + "showSourcesHint": "Zeigt die Quellen der Dateien an", "errorFileTooLarge": "Die hochgeladene Datei ist größer als für dieses Format erlaubt.", "errorNotAllowedFileType": "Dateiformat nicht erlaubt.", "errorNotSupportedFileType": "Dateiformat nicht unterstützt.", @@ -193,22 +190,10 @@ "endpointHint": "Endpunkt als URL.", "headersHint": "Ein Header pro Zeile als Schlüssel=Wert" }, - "context": { - "title": "DEV: Contexts", - "description": "Zeigt den aktuellen Kontext" - }, - "simpleInput": { - "title": "DEV: Simple Input", - "description": "Fragt nach einer Eingabe vom Benutzer" - }, "speechToText": { "title": "Spracheingabe", "description": "Erlaubt Spracheingaben über ein Mikrofon-Icon" }, - "userArgs": { - "title": "DEV: User Args", - "description": "Zeigt die aktuellen Benutzerargumente" - }, "filesInConversation": { "title": "Suche in Dateien im Chat", "description": "Ermöglicht dem LLM, Dateien zu durchsuchen, die in einem Chat über die Büroklammer hochgeladen wurden.", @@ -219,7 +204,9 @@ "maxFiles": "Max. Dateien", "maxFilesHint": "Maximale Anzahl von Dateien im Chat", "showSources": "Quellen anzeigen", - "showSourcesHint": "Zeigt die Quellen der Dateien an" + "showSourcesHint": "Zeigt die Quellen der Dateien an", + "vectorize": "Inhalte indizieren", + "vectorizeHint": "Ermöglicht eine semantische Suche auf den Inhalten der Dateien" }, "filesVision": { "title": "Bilder im Chat", @@ -262,10 +249,40 @@ "value": "Wert (Template)", "valueHint": "Wert, der beim Toolaufruf verwendet wird.", "errorToolCall": "Es ist ein Fehler aufgetreten beim Aufruf des Tools '{tool}'" + }, + "always42": { + "title": "DEV: Add 42", + "description": "Addiert immer 42 zur Summe von zwei Zahlen" + }, + "confirm": { + "title": "DEV: Confirm", + "description": "Fragt nach Bestätigung" + }, + "context": { + "title": "DEV: Contexts", + "description": "Zeigt den aktuellen Kontext" + }, + "userArgs": { + "title": "DEV: User Args", + "description": "Zeigt die aktuellen Benutzerargumente" + }, + "simpleInput": { + "title": "DEV: Simple Input", + "description": "Fragt nach einer Eingabe vom Benutzer" + }, + "gpt-image-1": { + "title": "GPT-Image-1", + "description": "Bilder mit OpenAI gpt-image-1 generieren.", + "quality": "Qualität", + "size": "Größe" + }, + "azure-gpt-image-1": { + "title": "Azure GPT-Image-1", + "description": "Bilder mit Azure OpenAI gpt-image-1 generieren." } }, "chat": { - "errorConfigurationUsed": "Der Assistent wird von mindestens einer Konversation verwendet.", + "errorLastConfigurationdDeleted": "Es muss mindestens einen aktivierten Assistenten geben, wenn Konversationen existieren.", "errorContentFilter": "Die Frage wurde vom System aufgrund ihres Inhalts abgewiesen und wird daher nicht beantwortet.", "errorContextLengthExceeded": "Der Kontext des aktuellen Chats ist zu groß für das genutzte LLM. Entweder gibt es zu viel Text in dieser Konversation oder es wurde eine zu große Datei mit der \"Vollständige Dateien\"-Extension hochgeladen.", "errorStringAboveMaxLength": "Die Anfrage an das LLM is zu lang. Entweder gibt es zu viel Text in dieser Konversation oder es wurde eine zu große Datei mit der \"Vollständige Dateien\"-Extension hochgeladen.", diff --git a/backend/src/localization/i18n/en/texts.json b/backend/src/localization/i18n/en/texts.json index 91946323c..24ea0174b 100644 --- a/backend/src/localization/i18n/en/texts.json +++ b/backend/src/localization/i18n/en/texts.json @@ -7,7 +7,8 @@ "instanceName": "Instance Name", "apiVersion": "API Version", "temperature": "Temperature", - "effort": "Effort", + "reasoningEffort": "Reasoning Effort", + "reasoningSummary": "Reasoning Summary", "seed": "Seed", "presencePenalty": "Presence Penalty", "frequencyPenalty": "Frequency Penalty", @@ -53,7 +54,7 @@ "description": "Open AI LLM integration for reasoning Models" }, "langfuse": { - "title": "DEV: Langfuse", + "title": "Langfuse", "description": "Langfuse integration", "baseUrl": "Base url", "baseUrlHint": "Base url of langfuse (if self-hosted)", @@ -65,7 +66,7 @@ "description": "Mistral LLM integration" }, "ollama": { - "title": "DEV: Ollama", + "title": "Ollama", "description": "Ollama LLM integration" }, "openai": { @@ -74,9 +75,13 @@ "endpointHint": "Base url of open ai endpoint" }, "openaiCompatible": { - "title": "DEV: OpenAI compatible", + "title": "OpenAI compatible", "description": "Open AI compatible LLM integration" }, + "nvidia": { + "title": "Nvidia NIM", + "description": "Nvidia NIM LLM integration" + }, "vertexai": { "title": "VertexAI", "description": "Vertex AI LLM integration" @@ -94,10 +99,6 @@ "description": "Defines the summary prompt that is used for conversation label.", "promptHint": "Use the {content} placeholder for the actual history." }, - "always42": { - "title": "DEV: Add 42", - "description": "Always adds 42 to the sum of two numbers" - }, "azureSearch": { "title": "Azure AI Search", "description": "Performs a search using Azure AI Search", @@ -124,10 +125,6 @@ "description": "Performs a web search using Duckduckgo", "maxResults": "Number of search results" }, - "confirm": { - "title": "DEV: Confirm", - "description": "Asks for confirmation" - }, "azureDalle": { "title": "Azure Dall-E", "description": "Generates images with the Azure DALL-E image generator." @@ -150,8 +147,8 @@ "descriptionHint": "Describes the tool and the data in the index.", "bucketHint": "The bucket to use.", "takeHint": "The number of results to return.", - "filesInChat": "Files in Chat", - "filesInChatHint": "Upload files into a conversation. Files will be available only in the conversation where they were uploaded. 'Take' value will be ignored", + "showSources": "Show sources", + "showSourcesHint": "Show sources of the files", "errorFileTooLarge": "The file is larger than allowed for this file type.", "errorNotAllowedFileType": "File type not allowed.", "errorNotSupportedFileType": "File type not supported.", @@ -193,22 +190,10 @@ "endpointHint": "Endpoint as URL.", "headersHint": "One header per line as Key=Value" }, - "context": { - "title": "DEV: Contexts", - "description": "Shows the current context" - }, - "simpleInput": { - "title": "DEV: Simple Input", - "description": "Asks for input from the user" - }, "speechToText": { "title": "Speech To Text", "description": "Allows speech input via microphone icon" }, - "userArgs": { - "title": "DEV: User Args", - "description": "Shows the current user args" - }, "filesInConversation": { "title": "Search Files in Chat", "description": "Enables the LLM to search files uploaded via the paperclip to a conversation.", @@ -219,7 +204,9 @@ "maxFiles": "Max. Files", "maxFilesHint": "Maximum number of files to upload in a conversation", "showSources": "Show sources", - "showSourcesHint": "Show sources of the files" + "showSourcesHint": "Show sources of the files", + "vectorize": "Index contents", + "vectorizeHint": "Enables a semantic search on the contents of the files" }, "filesVision": { "title": "Files Vision", @@ -262,10 +249,40 @@ "value": "Value (Template)", "valueHint": "Value that is used during tool call", "errorToolCall": "An error occurred during the tool call '{tool}'" + }, + "always42": { + "title": "DEV: Add 42", + "description": "Always adds 42 to the sum of two numbers" + }, + "confirm": { + "title": "DEV: Confirm", + "description": "Asks for confirmation" + }, + "context": { + "title": "DEV: Contexts", + "description": "Shows the current context" + }, + "userArgs": { + "title": "DEV: User Args", + "description": "Shows the current user args" + }, + "simpleInput": { + "title": "DEV: Simple Input", + "description": "Asks for input from the user" + }, + "gpt-image-1": { + "title": "GPT-Image-1", + "description": "Generate images using OpenAI gpt-image-1.", + "quality": "Quality", + "size": "Size" + }, + "azure-gpt-image-1": { + "title": "Azure gpt-image-1", + "description": "Generate images using Azure OpenAI gpt-image-1." } }, "chat": { - "errorConfigurationUsed": "Assistant is used by at least one conversation.", + "errorLastConfigurationdDeleted": "There must be at least one enabled assistant if there are conversations.", "errorContentFilter": "The question was rejected by the system due to its content and is therefore not answered.", "errorContextLengthExceeded": "The context of the current chat is too long for the used LLM. Either there is too much text in this chat or you uploaded a too large file with the \"Complete File\" extension.", "errorStringAboveMaxLength": "The request to the LLM is too long. Either there is too much text in this chat or you uploaded a too large file with the \"Complete File\" extension.", diff --git a/backend/src/metrics/opentelemetry.module.ts b/backend/src/metrics/opentelemetry.module.ts new file mode 100644 index 000000000..3ed35714c --- /dev/null +++ b/backend/src/metrics/opentelemetry.module.ts @@ -0,0 +1,34 @@ +import { Module, OnApplicationBootstrap, OnApplicationShutdown } from '@nestjs/common'; +import { ConfigModule, ConfigService } from '@nestjs/config'; +import { getNodeAutoInstrumentations } from '@opentelemetry/auto-instrumentations-node'; +import { NodeSDK } from '@opentelemetry/sdk-node'; +import { LangfuseExporter } from 'langfuse-vercel'; + +@Module({ + imports: [ConfigModule], +}) +export class OpenTelemetryModule implements OnApplicationBootstrap, OnApplicationShutdown { + private sdk?: NodeSDK; + + constructor(private readonly configService: ConfigService) {} + + onApplicationBootstrap() { + const publicKey = this.configService.get('LANGFUSE_PUBLIC_KEY'); + const secretKey = this.configService.get('LANGFUSE_SECRET_KEY'); + const baseUrl = this.configService.get('LANGFUSE_BASE_URL', 'https://cloud.langfuse.com'); + + if (publicKey && secretKey && baseUrl) { + this.sdk = new NodeSDK({ + traceExporter: new LangfuseExporter(), + instrumentations: [getNodeAutoInstrumentations()], + }); + this.sdk.start(); + } + } + + async onApplicationShutdown(_signal?: string) { + if (this.sdk) { + await this.sdk.shutdown(); + } + } +} diff --git a/backend/src/migrations/1756187236677-allowMultipleConversationsPerFile.ts b/backend/src/migrations/1756187236677-allowMultipleConversationsPerFile.ts new file mode 100644 index 000000000..16a6c5a13 --- /dev/null +++ b/backend/src/migrations/1756187236677-allowMultipleConversationsPerFile.ts @@ -0,0 +1,92 @@ +import { MigrationInterface, QueryRunner } from 'typeorm'; + +export class AllowMultipleConversationsPerFile1756187236677 implements MigrationInterface { + name = 'AllowMultipleConversationsPerFile1756187236677'; + + public async up(queryRunner: QueryRunner): Promise { + await queryRunner.query(`ALTER TABLE "company_chat"."files" DROP CONSTRAINT "FK_d793e035119090188909fa6559a"`); + await queryRunner.query( + `CREATE TABLE "company_chat"."conversations_files" ("id" SERIAL NOT NULL, "conversationId" integer NOT NULL, "fileId" integer NOT NULL, "messageId" integer, CONSTRAINT "UQ_04bee2f4651bdcefa29d7cebaaf" UNIQUE ("conversationId", "fileId"), CONSTRAINT "PK_6c9cc57ee46930980a93bed82d6" PRIMARY KEY ("id"))`, + ); + + await queryRunner.query(` + DROP TRIGGER set_default_doc_id_trigger ON company_chat.files; + DROP FUNCTION company_chat.set_default_doc_id(); + `); + + await queryRunner.query(` + INSERT INTO company_chat.files (id, "mimeType", "fileSize", "fileName", "userId", "bucketId", "createdAt", + "updatedAt", "conversationId", "uploadStatus", "extensionId", "docId") + SELECT + "docId" as "id", + "mimeType", + "fileSize", + "fileName", + "userId", + "bucketId", + "createdAt", + "updatedAt", + "conversationId", + "uploadStatus", + "extensionId", + "docId" + FROM company_chat.files + WHERE "docId" IN (SELECT o."docId" + FROM company_chat.files o + LEFT JOIN company_chat.files j on o."docId" = j.id + WHERE j."id" is null) + `); + + await queryRunner.query(` + INSERT INTO company_chat.conversations_files("fileId", "conversationId", "messageId") + SELECT DISTINCT f."docId", f."conversationId", MAX(m.id) FROM company_chat.files f + LEFT JOIN company_chat.messages m ON m."conversationId" = f."conversationId" AND f."createdAt" <= m."createdAt" AND m."type" = 'human' + WHERE f."conversationId" IS NOT NULL + GROUP BY f."docId", f."conversationId"; + + DELETE from company_chat.files where "id" <> "docId"; + `); + + await queryRunner.query(`ALTER TABLE "company_chat"."files" DROP COLUMN "conversationId"`); + await queryRunner.query(`ALTER TABLE "company_chat"."files" DROP COLUMN "docId"`); + await queryRunner.query( + `ALTER TABLE "company_chat"."conversations_files" ADD CONSTRAINT "FK_805d6c0485821e3026fa10b73bf" FOREIGN KEY ("conversationId") REFERENCES "company_chat"."conversations"("id") ON DELETE CASCADE ON UPDATE NO ACTION`, + ); + await queryRunner.query( + `ALTER TABLE "company_chat"."conversations_files" ADD CONSTRAINT "FK_c89b22a8ad0e508788ee62b3f2f" FOREIGN KEY ("fileId") REFERENCES "company_chat"."files"("id") ON DELETE CASCADE ON UPDATE NO ACTION`, + ); + await queryRunner.query( + `ALTER TABLE "company_chat"."conversations_files" ADD CONSTRAINT "FK_6157a82b69445b4bbe2f7906a75" FOREIGN KEY ("messageId") REFERENCES "company_chat"."messages"("id") ON DELETE CASCADE ON UPDATE NO ACTION`, + ); + } + + public async down(queryRunner: QueryRunner): Promise { + await queryRunner.query(`ALTER TABLE "company_chat"."conversations_files" DROP CONSTRAINT "FK_6157a82b69445b4bbe2f7906a75"`); + await queryRunner.query(`ALTER TABLE "company_chat"."conversations_files" DROP CONSTRAINT "FK_c89b22a8ad0e508788ee62b3f2f"`); + await queryRunner.query(`ALTER TABLE "company_chat"."conversations_files" DROP CONSTRAINT "FK_805d6c0485821e3026fa10b73bf"`); + await queryRunner.query(`ALTER TABLE "company_chat"."files" ADD "docId" integer NOT NULL`); + await queryRunner.query(`ALTER TABLE "company_chat"."files" ADD "conversationId" integer`); + await queryRunner.query(`DROP TABLE "company_chat"."conversations_files"`); + await queryRunner.query( + `ALTER TABLE "company_chat"."files" ADD CONSTRAINT "FK_d793e035119090188909fa6559a" FOREIGN KEY ("conversationId") REFERENCES "company_chat"."conversations"("id") ON DELETE CASCADE ON UPDATE NO ACTION`, + ); + await queryRunner.query(` + CREATE OR REPLACE FUNCTION company_chat.set_default_doc_id() + RETURNS trigger + LANGUAGE plpgsql + AS $function$ + BEGIN + IF NEW."docId" IS NULL THEN + NEW."docId" := NEW.id; + END IF; + RETURN NEW; + END; + $function$ + ; + `); + await queryRunner.query(` + CREATE TRIGGER set_default_doc_id_trigger BEFORE INSERT ON + company_chat.files FOR EACH ROW EXECUTE FUNCTION company_chat.set_default_doc_id(); + `); + } +} diff --git a/backend/src/migrations/1757424637497-addPrompts.ts b/backend/src/migrations/1757424637497-addPrompts.ts new file mode 100644 index 000000000..96f33c85d --- /dev/null +++ b/backend/src/migrations/1757424637497-addPrompts.ts @@ -0,0 +1,43 @@ +import { MigrationInterface, QueryRunner } from 'typeorm'; + +export class AddPrompts1757424637497 implements MigrationInterface { + name = 'AddPrompts1757424637497'; + + public async up(queryRunner: QueryRunner): Promise { + await queryRunner.query( + `CREATE TABLE "company_chat"."prompt-categories" ("label" character varying NOT NULL, "description" character varying NOT NULL, "creationDate" TIMESTAMP NOT NULL, "visibility" character varying NOT NULL, "createdAt" TIMESTAMP WITH TIME ZONE NOT NULL DEFAULT now(), "updatedAt" TIMESTAMP WITH TIME ZONE NOT NULL DEFAULT now(), CONSTRAINT "PK_fcceccb98fc892cc5b3e40c1097" PRIMARY KEY ("label"))`, + ); + await queryRunner.query( + `CREATE TABLE "company_chat"."prompts" ("id" SERIAL NOT NULL, "title" character varying NOT NULL, "description" character varying, "content" character varying NOT NULL, "visibility" character varying NOT NULL, "rating" integer, "createdAt" TIMESTAMP WITH TIME ZONE NOT NULL DEFAULT now(), "updatedAt" TIMESTAMP WITH TIME ZONE NOT NULL DEFAULT now(), CONSTRAINT "PK_21f33798862975179e40b216a1d" PRIMARY KEY ("id"))`, + ); + await queryRunner.query( + `CREATE TABLE "company_chat"."prompts_categories_prompt-categories" ("promptsId" integer NOT NULL, "promptCategoriesLabel" character varying NOT NULL, CONSTRAINT "PK_645256b9fc1fe950d6f6e7c3003" PRIMARY KEY ("promptsId", "promptCategoriesLabel"))`, + ); + await queryRunner.query( + `CREATE INDEX "IDX_b38fb3b439a6eea0016e1d5906" ON "company_chat"."prompts_categories_prompt-categories" ("promptsId") `, + ); + await queryRunner.query( + `CREATE INDEX "IDX_6515aea8d350337de0804256c9" ON "company_chat"."prompts_categories_prompt-categories" ("promptCategoriesLabel") `, + ); + await queryRunner.query( + `ALTER TABLE "company_chat"."prompts_categories_prompt-categories" ADD CONSTRAINT "FK_b38fb3b439a6eea0016e1d5906a" FOREIGN KEY ("promptsId") REFERENCES "company_chat"."prompts"("id") ON DELETE CASCADE ON UPDATE CASCADE`, + ); + await queryRunner.query( + `ALTER TABLE "company_chat"."prompts_categories_prompt-categories" ADD CONSTRAINT "FK_6515aea8d350337de0804256c98" FOREIGN KEY ("promptCategoriesLabel") REFERENCES "company_chat"."prompt-categories"("label") ON DELETE CASCADE ON UPDATE CASCADE`, + ); + } + + public async down(queryRunner: QueryRunner): Promise { + await queryRunner.query( + `ALTER TABLE "company_chat"."prompts_categories_prompt-categories" DROP CONSTRAINT "FK_6515aea8d350337de0804256c98"`, + ); + await queryRunner.query( + `ALTER TABLE "company_chat"."prompts_categories_prompt-categories" DROP CONSTRAINT "FK_b38fb3b439a6eea0016e1d5906a"`, + ); + await queryRunner.query(`DROP INDEX "company_chat"."IDX_6515aea8d350337de0804256c9"`); + await queryRunner.query(`DROP INDEX "company_chat"."IDX_b38fb3b439a6eea0016e1d5906"`); + await queryRunner.query(`DROP TABLE "company_chat"."prompts_categories_prompt-categories"`); + await queryRunner.query(`DROP TABLE "company_chat"."prompts"`); + await queryRunner.query(`DROP TABLE "company_chat"."prompt-categories"`); + } +} diff --git a/backend/src/migrations/1758289967016-replaceAzureReasoningExtensionByAzureExtension.ts b/backend/src/migrations/1758289967016-replaceAzureReasoningExtensionByAzureExtension.ts new file mode 100644 index 000000000..f4394db38 --- /dev/null +++ b/backend/src/migrations/1758289967016-replaceAzureReasoningExtensionByAzureExtension.ts @@ -0,0 +1,11 @@ +import { MigrationInterface, QueryRunner } from 'typeorm'; + +export class ReplaceAzureReasoningExtensionByAzureExtension1758289967016 implements MigrationInterface { + public async up(queryRunner: QueryRunner): Promise { + await queryRunner.query( + `update company_chat.extensions set "name" = 'azure-open-ai-model' where "name" = 'azure-open-ai-model-reasoning'`, + ); + } + + public async down(_: QueryRunner): Promise {} +} diff --git a/backend/src/migrations/1758791077412-addAssistantStatusField.ts b/backend/src/migrations/1758791077412-addAssistantStatusField.ts new file mode 100644 index 000000000..990368827 --- /dev/null +++ b/backend/src/migrations/1758791077412-addAssistantStatusField.ts @@ -0,0 +1,36 @@ +import { MigrationInterface, QueryRunner } from 'typeorm'; + +export class AddAssistantStatusField1758791077412 implements MigrationInterface { + name = 'AddAssistantStatusField1758791077412'; + + public async up(queryRunner: QueryRunner): Promise { + await queryRunner.query(`ALTER TABLE "company_chat"."configurations" RENAME COLUMN "enabled" TO "status"`); + + // Convert boolean to text temporarily for mapping + await queryRunner.query(`ALTER TABLE "company_chat"."configurations" ALTER COLUMN "status" TYPE text`); + await queryRunner.query(`UPDATE "company_chat"."configurations" SET "status" = 'enabled' WHERE "status" = 'true'`); + await queryRunner.query(`UPDATE "company_chat"."configurations" SET "status" = 'disabled' WHERE "status" = 'false'`); + + await queryRunner.query(`CREATE TYPE "company_chat"."configurations_status_enum" AS ENUM('enabled', 'disabled', 'deleted')`); + await queryRunner.query( + `ALTER TABLE "company_chat"."configurations" ALTER COLUMN "status" TYPE "company_chat"."configurations_status_enum" USING "status"::"company_chat"."configurations_status_enum"`, + ); + + await queryRunner.query(`ALTER TABLE "company_chat"."configurations" ALTER COLUMN "status" SET NOT NULL`); + await queryRunner.query(`ALTER TABLE "company_chat"."configurations" ALTER COLUMN "status" SET DEFAULT 'enabled'`); + } + + public async down(queryRunner: QueryRunner): Promise { + await queryRunner.query(`ALTER TABLE "company_chat"."configurations" ALTER COLUMN "status" DROP DEFAULT`); + await queryRunner.query(`ALTER TABLE "company_chat"."configurations" ALTER COLUMN "status" TYPE text`); + await queryRunner.query(`UPDATE "company_chat"."configurations" SET "status" = 'true' WHERE "status" = 'enabled'`); + await queryRunner.query( + `UPDATE "company_chat"."configurations" SET "status" = 'false' WHERE "status" = 'disabled' OR "status" = 'deleted'`, + ); + await queryRunner.query( + `ALTER TABLE "company_chat"."configurations" ALTER COLUMN "status" TYPE boolean USING ("status" = 'true')`, + ); + await queryRunner.query(`DROP TYPE "company_chat"."configurations_status_enum"`); + await queryRunner.query(`ALTER TABLE "company_chat"."configurations" RENAME COLUMN "status" TO "enabled"`); + } +} diff --git a/docker-compose.yml b/docker-compose.yml index 19e4b3509..6ef9a469e 100644 --- a/docker-compose.yml +++ b/docker-compose.yml @@ -52,7 +52,7 @@ services: retries: 20 ollama: - image: ollama/ollama:0.11.10 + image: ollama/ollama:0.12.3 restart: unless-stopped volumes: - ollama-data:/root/.ollama @@ -64,7 +64,7 @@ services: start_period: 60s ollama-models-pull: - image: curlimages/curl:8.15.0 + image: curlimages/curl:8.16.0 depends_on: ollama: condition: service_healthy diff --git a/e2e/extension-tests/azure-open-ai-assistant-change.spec.ts b/e2e/extension-tests/azure-open-ai-assistant-change.spec.ts index e636b9127..22b404b51 100644 --- a/e2e/extension-tests/azure-open-ai-assistant-change.spec.ts +++ b/e2e/extension-tests/azure-open-ai-assistant-change.spec.ts @@ -5,6 +5,8 @@ import { addSystemPromptToConfiguration, cleanup, createConfiguration, + deleteConfiguration, + disableConfiguration, enterAdminArea, enterUserArea, login, @@ -61,5 +63,26 @@ if (!config.AZURE_OPEN_AI_API_KEY) { const secondResponseAssistantText = await page.waitForSelector(`:has-text("${secondAssistant.name}")`); expect(secondResponseAssistantText).toBeDefined(); }); + + await test.step('should disable second assistant', async () => { + await enterAdminArea(page); + await disableConfiguration(page, secondAssistant); + await enterUserArea(page); + const secondResponse = await page.waitForSelector(`:has-text("${secondAssistant.name} [disabled]")`); + expect(secondResponse).toBeDefined(); + }); + + await test.step('should delete second assistant', async () => { + await enterAdminArea(page); + await deleteConfiguration(page, secondAssistant); + await enterUserArea(page); + const secondResponse = await page.waitForSelector(`:has-text("Friendly AI [assistant deleted]")`); + expect(secondResponse).toBeDefined(); + + await selectConfiguration(page, firstAssistant); + await sendMessage(page, firstAssistant, { message: 'Who are you' }); + const firstResponse = await page.waitForSelector(`:has-text("Bob")`); + expect(firstResponse).toBeDefined(); + }); }); } diff --git a/e2e/extension-tests/azure-open-ai-whole-file.spec.ts b/e2e/extension-tests/azure-open-ai-whole-file.spec.ts index 49329fd5e..48627b97d 100644 --- a/e2e/extension-tests/azure-open-ai-whole-file.spec.ts +++ b/e2e/extension-tests/azure-open-ai-whole-file.spec.ts @@ -213,6 +213,12 @@ if (!config.AZURE_OPEN_AI_API_KEY) { expect(source_panel).toBeDefined(); }); + await test.step('should show pdf representation of file referenced in source', async () => { + await page.getByText('Source Viewer').click(); + await expect(page.locator('.pdf-viewport')).toBeVisible(); + await expect(page.locator('.pdf-viewport').getByText('Daisy Duck')).toBeVisible(); + }); + await test.step('should duplicate a conversation that includes a file uploaded with files in chat extension', async () => { await duplicateLastCreatedConversation(page); const originalConversation = page.locator('role=navigation').first(); diff --git a/e2e/package-lock.json b/e2e/package-lock.json index aec2ecdf7..f31439de3 100644 --- a/e2e/package-lock.json +++ b/e2e/package-lock.json @@ -19,10 +19,10 @@ "@faker-js/faker": "9.8.0", "@playwright/test": "1.52.0", "@types/node": "24.0.11", - "@typescript-eslint/eslint-plugin": "8.33.1", - "@typescript-eslint/parser": "8.35.1", - "eslint": "9.30.0", - "eslint-config-prettier": "10.1.5", + "@typescript-eslint/eslint-plugin": "8.46.0", + "@typescript-eslint/parser": "8.46.0", + "eslint": "9.37.0", + "eslint-config-prettier": "10.1.8", "eslint-plugin-import": "2.32.0", "eslint-plugin-prettier": "5.4.1", "globals": "16.3.0", @@ -30,9 +30,9 @@ } }, "node_modules/@eslint-community/eslint-utils": { - "version": "4.7.0", - "resolved": "https://registry.npmjs.org/@eslint-community/eslint-utils/-/eslint-utils-4.7.0.tgz", - "integrity": "sha512-dyybb3AcajC7uha6CvhdVRJqaKyn7w2YKqKyAN37NKYgZT36w+iRb0Dymmc5qEJ549c/S31cMMSFd75bteCpCw==", + "version": "4.9.0", + "resolved": "https://registry.npmjs.org/@eslint-community/eslint-utils/-/eslint-utils-4.9.0.tgz", + "integrity": "sha512-ayVFHdtZ+hsq1t2Dy24wCmGXGe4q9Gu3smhLYALJrr473ZH27MsnSL+LKUlimp4BWJqMDMLmPpx/Q9R3OAlL4g==", "dev": true, "license": "MIT", "dependencies": { @@ -91,18 +91,22 @@ } }, "node_modules/@eslint/config-helpers": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/@eslint/config-helpers/-/config-helpers-0.3.0.tgz", - "integrity": "sha512-ViuymvFmcJi04qdZeDc2whTHryouGcDlaxPqarTD0ZE10ISpxGUVZGZDx4w01upyIynL3iu6IXH2bS1NhclQMw==", + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/@eslint/config-helpers/-/config-helpers-0.4.0.tgz", + "integrity": "sha512-WUFvV4WoIwW8Bv0KeKCIIEgdSiFOsulyN0xrMu+7z43q/hkOLXjvb5u7UC9jDxvRzcrbEmuZBX5yJZz1741jog==", "dev": true, + "license": "Apache-2.0", + "dependencies": { + "@eslint/core": "^0.16.0" + }, "engines": { "node": "^18.18.0 || ^20.9.0 || >=21.1.0" } }, "node_modules/@eslint/core": { - "version": "0.14.0", - "resolved": "https://registry.npmjs.org/@eslint/core/-/core-0.14.0.tgz", - "integrity": "sha512-qIbV0/JZr7iSDjqAc60IqbLdsj9GDt16xQtWD+B78d/HAlvysGdZZ6rpJHGAc2T0FQx1X6thsSPdnoiGKdNtdg==", + "version": "0.16.0", + "resolved": "https://registry.npmjs.org/@eslint/core/-/core-0.16.0.tgz", + "integrity": "sha512-nmC8/totwobIiFcGkDza3GIKfAw1+hLiYVrh3I1nIomQ8PEr5cxg34jnkmGawul/ep52wGRAcyeDCNtWKSOj4Q==", "dev": true, "license": "Apache-2.0", "dependencies": { @@ -150,10 +154,11 @@ } }, "node_modules/@eslint/js": { - "version": "9.30.0", - "resolved": "https://registry.npmjs.org/@eslint/js/-/js-9.30.0.tgz", - "integrity": "sha512-Wzw3wQwPvc9sHM+NjakWTcPx11mbZyiYHuwWa/QfZ7cIRX7WK54PSk7bdyXDaoaopUcMatv1zaQvOAAO8hCdww==", + "version": "9.37.0", + "resolved": "https://registry.npmjs.org/@eslint/js/-/js-9.37.0.tgz", + "integrity": "sha512-jaS+NJ+hximswBG6pjNX0uEJZkrT0zwpVi3BA3vX22aFGjJjmgSTSmPpZCRKmoBL5VY/M6p0xsSJx7rk7sy5gg==", "dev": true, + "license": "MIT", "engines": { "node": "^18.18.0 || ^20.9.0 || >=21.1.0" }, @@ -171,13 +176,13 @@ } }, "node_modules/@eslint/plugin-kit": { - "version": "0.3.1", - "resolved": "https://registry.npmjs.org/@eslint/plugin-kit/-/plugin-kit-0.3.1.tgz", - "integrity": "sha512-0J+zgWxHN+xXONWIyPWKFMgVuJoZuGiIFu8yxk7RJjxkzpGmyja5wRFqZIVtjDVOQpV+Rw0iOAjYPE2eQyjr0w==", + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/@eslint/plugin-kit/-/plugin-kit-0.4.0.tgz", + "integrity": "sha512-sB5uyeq+dwCWyPi31B2gQlVlo+j5brPlWx4yZBrEaRo/nhdDE8Xke1gsGgtiBdaBTxuTkceLVuVt/pclrasb0A==", "dev": true, "license": "Apache-2.0", "dependencies": { - "@eslint/core": "^0.14.0", + "@eslint/core": "^0.16.0", "levn": "^0.4.1" }, "engines": { @@ -414,17 +419,17 @@ } }, "node_modules/@typescript-eslint/eslint-plugin": { - "version": "8.33.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/eslint-plugin/-/eslint-plugin-8.33.1.tgz", - "integrity": "sha512-TDCXj+YxLgtvxvFlAvpoRv9MAncDLBV2oT9Bd7YBGC/b/sEURoOYuIwLI99rjWOfY3QtDzO+mk0n4AmdFExW8A==", + "version": "8.46.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/eslint-plugin/-/eslint-plugin-8.46.0.tgz", + "integrity": "sha512-hA8gxBq4ukonVXPy0OKhiaUh/68D0E88GSmtC1iAEnGaieuDi38LhS7jdCHRLi6ErJBNDGCzvh5EnzdPwUc0DA==", "dev": true, "license": "MIT", "dependencies": { "@eslint-community/regexpp": "^4.10.0", - "@typescript-eslint/scope-manager": "8.33.1", - "@typescript-eslint/type-utils": "8.33.1", - "@typescript-eslint/utils": "8.33.1", - "@typescript-eslint/visitor-keys": "8.33.1", + "@typescript-eslint/scope-manager": "8.46.0", + "@typescript-eslint/type-utils": "8.46.0", + "@typescript-eslint/utils": "8.46.0", + "@typescript-eslint/visitor-keys": "8.46.0", "graphemer": "^1.4.0", "ignore": "^7.0.0", "natural-compare": "^1.4.0", @@ -438,9 +443,9 @@ "url": "https://opencollective.com/typescript-eslint" }, "peerDependencies": { - "@typescript-eslint/parser": "^8.33.1", + "@typescript-eslint/parser": "8.46.0", "eslint": "^8.57.0 || ^9.0.0", - "typescript": ">=4.8.4 <5.9.0" + "typescript": ">=4.8.4 <6.0.0" } }, "node_modules/@typescript-eslint/eslint-plugin/node_modules/ignore": { @@ -454,15 +459,16 @@ } }, "node_modules/@typescript-eslint/parser": { - "version": "8.35.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/parser/-/parser-8.35.1.tgz", - "integrity": "sha512-3MyiDfrfLeK06bi/g9DqJxP5pV74LNv4rFTyvGDmT3x2p1yp1lOd+qYZfiRPIOf/oON+WRZR5wxxuF85qOar+w==", + "version": "8.46.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/parser/-/parser-8.46.0.tgz", + "integrity": "sha512-n1H6IcDhmmUEG7TNVSspGmiHHutt7iVKtZwRppD7e04wha5MrkV1h3pti9xQLcCMt6YWsncpoT0HMjkH1FNwWQ==", "dev": true, + "license": "MIT", "dependencies": { - "@typescript-eslint/scope-manager": "8.35.1", - "@typescript-eslint/types": "8.35.1", - "@typescript-eslint/typescript-estree": "8.35.1", - "@typescript-eslint/visitor-keys": "8.35.1", + "@typescript-eslint/scope-manager": "8.46.0", + "@typescript-eslint/types": "8.46.0", + "@typescript-eslint/typescript-estree": "8.46.0", + "@typescript-eslint/visitor-keys": "8.46.0", "debug": "^4.3.4" }, "engines": { @@ -474,166 +480,18 @@ }, "peerDependencies": { "eslint": "^8.57.0 || ^9.0.0", - "typescript": ">=4.8.4 <5.9.0" - } - }, - "node_modules/@typescript-eslint/parser/node_modules/@typescript-eslint/project-service": { - "version": "8.35.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/project-service/-/project-service-8.35.1.tgz", - "integrity": "sha512-VYxn/5LOpVxADAuP3NrnxxHYfzVtQzLKeldIhDhzC8UHaiQvYlXvKuVho1qLduFbJjjy5U5bkGwa3rUGUb1Q6Q==", - "dev": true, - "dependencies": { - "@typescript-eslint/tsconfig-utils": "^8.35.1", - "@typescript-eslint/types": "^8.35.1", - "debug": "^4.3.4" - }, - "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/typescript-eslint" - }, - "peerDependencies": { - "typescript": ">=4.8.4 <5.9.0" - } - }, - "node_modules/@typescript-eslint/parser/node_modules/@typescript-eslint/scope-manager": { - "version": "8.35.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/scope-manager/-/scope-manager-8.35.1.tgz", - "integrity": "sha512-s/Bpd4i7ht2934nG+UoSPlYXd08KYz3bmjLEb7Ye1UVob0d1ENiT3lY8bsCmik4RqfSbPw9xJJHbugpPpP5JUg==", - "dev": true, - "dependencies": { - "@typescript-eslint/types": "8.35.1", - "@typescript-eslint/visitor-keys": "8.35.1" - }, - "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/typescript-eslint" - } - }, - "node_modules/@typescript-eslint/parser/node_modules/@typescript-eslint/tsconfig-utils": { - "version": "8.35.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/tsconfig-utils/-/tsconfig-utils-8.35.1.tgz", - "integrity": "sha512-K5/U9VmT9dTHoNowWZpz+/TObS3xqC5h0xAIjXPw+MNcKV9qg6eSatEnmeAwkjHijhACH0/N7bkhKvbt1+DXWQ==", - "dev": true, - "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/typescript-eslint" - }, - "peerDependencies": { - "typescript": ">=4.8.4 <5.9.0" - } - }, - "node_modules/@typescript-eslint/parser/node_modules/@typescript-eslint/types": { - "version": "8.35.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-8.35.1.tgz", - "integrity": "sha512-q/O04vVnKHfrrhNAscndAn1tuQhIkwqnaW+eu5waD5IPts2eX1dgJxgqcPx5BX109/qAz7IG6VrEPTOYKCNfRQ==", - "dev": true, - "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/typescript-eslint" - } - }, - "node_modules/@typescript-eslint/parser/node_modules/@typescript-eslint/typescript-estree": { - "version": "8.35.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-8.35.1.tgz", - "integrity": "sha512-Vvpuvj4tBxIka7cPs6Y1uvM7gJgdF5Uu9F+mBJBPY4MhvjrjWGK4H0lVgLJd/8PWZ23FTqsaJaLEkBCFUk8Y9g==", - "dev": true, - "dependencies": { - "@typescript-eslint/project-service": "8.35.1", - "@typescript-eslint/tsconfig-utils": "8.35.1", - "@typescript-eslint/types": "8.35.1", - "@typescript-eslint/visitor-keys": "8.35.1", - "debug": "^4.3.4", - "fast-glob": "^3.3.2", - "is-glob": "^4.0.3", - "minimatch": "^9.0.4", - "semver": "^7.6.0", - "ts-api-utils": "^2.1.0" - }, - "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/typescript-eslint" - }, - "peerDependencies": { - "typescript": ">=4.8.4 <5.9.0" - } - }, - "node_modules/@typescript-eslint/parser/node_modules/@typescript-eslint/visitor-keys": { - "version": "8.35.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-8.35.1.tgz", - "integrity": "sha512-VRwixir4zBWCSTP/ljEo091lbpypz57PoeAQ9imjG+vbeof9LplljsL1mos4ccG6H9IjfrVGM359RozUnuFhpw==", - "dev": true, - "dependencies": { - "@typescript-eslint/types": "8.35.1", - "eslint-visitor-keys": "^4.2.1" - }, - "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/typescript-eslint" - } - }, - "node_modules/@typescript-eslint/parser/node_modules/brace-expansion": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-2.0.2.tgz", - "integrity": "sha512-Jt0vHyM+jmUBqojB7E1NIYadt0vI0Qxjxd2TErW94wDz+E2LAm5vKMXXwg6ZZBTHPuUlDgQHKXvjGBdfcF1ZDQ==", - "dev": true, - "dependencies": { - "balanced-match": "^1.0.0" - } - }, - "node_modules/@typescript-eslint/parser/node_modules/eslint-visitor-keys": { - "version": "4.2.1", - "resolved": "https://registry.npmjs.org/eslint-visitor-keys/-/eslint-visitor-keys-4.2.1.tgz", - "integrity": "sha512-Uhdk5sfqcee/9H/rCOJikYz67o0a2Tw2hGRPOG2Y1R2dg7brRe1uG0yaNQDHu+TO/uQPF/5eCapvYSmHUjt7JQ==", - "dev": true, - "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" - }, - "funding": { - "url": "https://opencollective.com/eslint" - } - }, - "node_modules/@typescript-eslint/parser/node_modules/minimatch": { - "version": "9.0.5", - "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-9.0.5.tgz", - "integrity": "sha512-G6T0ZX48xgozx7587koeX9Ys2NYy6Gmv//P89sEte9V9whIapMNF4idKxnW2QtCcLiTWlb/wfCabAtAFWhhBow==", - "dev": true, - "dependencies": { - "brace-expansion": "^2.0.1" - }, - "engines": { - "node": ">=16 || 14 >=14.17" - }, - "funding": { - "url": "https://github.com/sponsors/isaacs" + "typescript": ">=4.8.4 <6.0.0" } }, "node_modules/@typescript-eslint/project-service": { - "version": "8.33.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/project-service/-/project-service-8.33.1.tgz", - "integrity": "sha512-DZR0efeNklDIHHGRpMpR5gJITQpu6tLr9lDJnKdONTC7vvzOlLAG/wcfxcdxEWrbiZApcoBCzXqU/Z458Za5Iw==", + "version": "8.46.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/project-service/-/project-service-8.46.0.tgz", + "integrity": "sha512-OEhec0mH+U5Je2NZOeK1AbVCdm0ChyapAyTeXVIYTPXDJ3F07+cu87PPXcGoYqZ7M9YJVvFnfpGg1UmCIqM+QQ==", "dev": true, "license": "MIT", "dependencies": { - "@typescript-eslint/tsconfig-utils": "^8.33.1", - "@typescript-eslint/types": "^8.33.1", + "@typescript-eslint/tsconfig-utils": "^8.46.0", + "@typescript-eslint/types": "^8.46.0", "debug": "^4.3.4" }, "engines": { @@ -644,18 +502,18 @@ "url": "https://opencollective.com/typescript-eslint" }, "peerDependencies": { - "typescript": ">=4.8.4 <5.9.0" + "typescript": ">=4.8.4 <6.0.0" } }, "node_modules/@typescript-eslint/scope-manager": { - "version": "8.33.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/scope-manager/-/scope-manager-8.33.1.tgz", - "integrity": "sha512-dM4UBtgmzHR9bS0Rv09JST0RcHYearoEoo3pG5B6GoTR9XcyeqX87FEhPo+5kTvVfKCvfHaHrcgeJQc6mrDKrA==", + "version": "8.46.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/scope-manager/-/scope-manager-8.46.0.tgz", + "integrity": "sha512-lWETPa9XGcBes4jqAMYD9fW0j4n6hrPtTJwWDmtqgFO/4HF4jmdH/Q6wggTw5qIT5TXjKzbt7GsZUBnWoO3dqw==", "dev": true, "license": "MIT", "dependencies": { - "@typescript-eslint/types": "8.33.1", - "@typescript-eslint/visitor-keys": "8.33.1" + "@typescript-eslint/types": "8.46.0", + "@typescript-eslint/visitor-keys": "8.46.0" }, "engines": { "node": "^18.18.0 || ^20.9.0 || >=21.1.0" @@ -666,9 +524,9 @@ } }, "node_modules/@typescript-eslint/tsconfig-utils": { - "version": "8.33.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/tsconfig-utils/-/tsconfig-utils-8.33.1.tgz", - "integrity": "sha512-STAQsGYbHCF0/e+ShUQ4EatXQ7ceh3fBCXkNU7/MZVKulrlq1usH7t2FhxvCpuCi5O5oi1vmVaAjrGeL71OK1g==", + "version": "8.46.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/tsconfig-utils/-/tsconfig-utils-8.46.0.tgz", + "integrity": "sha512-WrYXKGAHY836/N7zoK/kzi6p8tXFhasHh8ocFL9VZSAkvH956gfeRfcnhs3xzRy8qQ/dq3q44v1jvQieMFg2cw==", "dev": true, "license": "MIT", "engines": { @@ -679,18 +537,19 @@ "url": "https://opencollective.com/typescript-eslint" }, "peerDependencies": { - "typescript": ">=4.8.4 <5.9.0" + "typescript": ">=4.8.4 <6.0.0" } }, "node_modules/@typescript-eslint/type-utils": { - "version": "8.33.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/type-utils/-/type-utils-8.33.1.tgz", - "integrity": "sha512-1cG37d9xOkhlykom55WVwG2QRNC7YXlxMaMzqw2uPeJixBFfKWZgaP/hjAObqMN/u3fr5BrTwTnc31/L9jQ2ww==", + "version": "8.46.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/type-utils/-/type-utils-8.46.0.tgz", + "integrity": "sha512-hy+lvYV1lZpVs2jRaEYvgCblZxUoJiPyCemwbQZ+NGulWkQRy0HRPYAoef/CNSzaLt+MLvMptZsHXHlkEilaeg==", "dev": true, "license": "MIT", "dependencies": { - "@typescript-eslint/typescript-estree": "8.33.1", - "@typescript-eslint/utils": "8.33.1", + "@typescript-eslint/types": "8.46.0", + "@typescript-eslint/typescript-estree": "8.46.0", + "@typescript-eslint/utils": "8.46.0", "debug": "^4.3.4", "ts-api-utils": "^2.1.0" }, @@ -703,13 +562,13 @@ }, "peerDependencies": { "eslint": "^8.57.0 || ^9.0.0", - "typescript": ">=4.8.4 <5.9.0" + "typescript": ">=4.8.4 <6.0.0" } }, "node_modules/@typescript-eslint/types": { - "version": "8.33.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-8.33.1.tgz", - "integrity": "sha512-xid1WfizGhy/TKMTwhtVOgalHwPtV8T32MS9MaH50Cwvz6x6YqRIPdD2WvW0XaqOzTV9p5xdLY0h/ZusU5Lokg==", + "version": "8.46.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-8.46.0.tgz", + "integrity": "sha512-bHGGJyVjSE4dJJIO5yyEWt/cHyNwga/zXGJbJJ8TiO01aVREK6gCTu3L+5wrkb1FbDkQ+TKjMNe9R/QQQP9+rA==", "dev": true, "license": "MIT", "engines": { @@ -721,16 +580,16 @@ } }, "node_modules/@typescript-eslint/typescript-estree": { - "version": "8.33.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-8.33.1.tgz", - "integrity": "sha512-+s9LYcT8LWjdYWu7IWs7FvUxpQ/DGkdjZeE/GGulHvv8rvYwQvVaUZ6DE+j5x/prADUgSbbCWZ2nPI3usuVeOA==", + "version": "8.46.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-8.46.0.tgz", + "integrity": "sha512-ekDCUfVpAKWJbRfm8T1YRrCot1KFxZn21oV76v5Fj4tr7ELyk84OS+ouvYdcDAwZL89WpEkEj2DKQ+qg//+ucg==", "dev": true, "license": "MIT", "dependencies": { - "@typescript-eslint/project-service": "8.33.1", - "@typescript-eslint/tsconfig-utils": "8.33.1", - "@typescript-eslint/types": "8.33.1", - "@typescript-eslint/visitor-keys": "8.33.1", + "@typescript-eslint/project-service": "8.46.0", + "@typescript-eslint/tsconfig-utils": "8.46.0", + "@typescript-eslint/types": "8.46.0", + "@typescript-eslint/visitor-keys": "8.46.0", "debug": "^4.3.4", "fast-glob": "^3.3.2", "is-glob": "^4.0.3", @@ -746,13 +605,13 @@ "url": "https://opencollective.com/typescript-eslint" }, "peerDependencies": { - "typescript": ">=4.8.4 <5.9.0" + "typescript": ">=4.8.4 <6.0.0" } }, "node_modules/@typescript-eslint/typescript-estree/node_modules/brace-expansion": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-2.0.1.tgz", - "integrity": "sha512-XnAIvQ8eM+kC6aULx6wuQiwVsnzsi9d3WxzV3FpWTGA19F621kwdbsAcFKXgKUHZWsy+mY6iL1sHTxWEFCytDA==", + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-2.0.2.tgz", + "integrity": "sha512-Jt0vHyM+jmUBqojB7E1NIYadt0vI0Qxjxd2TErW94wDz+E2LAm5vKMXXwg6ZZBTHPuUlDgQHKXvjGBdfcF1ZDQ==", "dev": true, "license": "MIT", "dependencies": { @@ -776,16 +635,16 @@ } }, "node_modules/@typescript-eslint/utils": { - "version": "8.33.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/utils/-/utils-8.33.1.tgz", - "integrity": "sha512-52HaBiEQUaRYqAXpfzWSR2U3gxk92Kw006+xZpElaPMg3C4PgM+A5LqwoQI1f9E5aZ/qlxAZxzm42WX+vn92SQ==", + "version": "8.46.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/utils/-/utils-8.46.0.tgz", + "integrity": "sha512-nD6yGWPj1xiOm4Gk0k6hLSZz2XkNXhuYmyIrOWcHoPuAhjT9i5bAG+xbWPgFeNR8HPHHtpNKdYUXJl/D3x7f5g==", "dev": true, "license": "MIT", "dependencies": { "@eslint-community/eslint-utils": "^4.7.0", - "@typescript-eslint/scope-manager": "8.33.1", - "@typescript-eslint/types": "8.33.1", - "@typescript-eslint/typescript-estree": "8.33.1" + "@typescript-eslint/scope-manager": "8.46.0", + "@typescript-eslint/types": "8.46.0", + "@typescript-eslint/typescript-estree": "8.46.0" }, "engines": { "node": "^18.18.0 || ^20.9.0 || >=21.1.0" @@ -796,18 +655,18 @@ }, "peerDependencies": { "eslint": "^8.57.0 || ^9.0.0", - "typescript": ">=4.8.4 <5.9.0" + "typescript": ">=4.8.4 <6.0.0" } }, "node_modules/@typescript-eslint/visitor-keys": { - "version": "8.33.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-8.33.1.tgz", - "integrity": "sha512-3i8NrFcZeeDHJ+7ZUuDkGT+UHq+XoFGsymNK2jZCOHcfEzRQ0BdpRtdpSx/Iyf3MHLWIcLS0COuOPibKQboIiQ==", + "version": "8.46.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-8.46.0.tgz", + "integrity": "sha512-FrvMpAK+hTbFy7vH5j1+tMYHMSKLE6RzluFJlkFNKD0p9YsUT75JlBSmr5so3QRzvMwU5/bIEdeNrxm8du8l3Q==", "dev": true, "license": "MIT", "dependencies": { - "@typescript-eslint/types": "8.33.1", - "eslint-visitor-keys": "^4.2.0" + "@typescript-eslint/types": "8.46.0", + "eslint-visitor-keys": "^4.2.1" }, "engines": { "node": "^18.18.0 || ^20.9.0 || >=21.1.0" @@ -818,9 +677,9 @@ } }, "node_modules/@typescript-eslint/visitor-keys/node_modules/eslint-visitor-keys": { - "version": "4.2.0", - "resolved": "https://registry.npmjs.org/eslint-visitor-keys/-/eslint-visitor-keys-4.2.0.tgz", - "integrity": "sha512-UyLnSehNt62FFhSwjZlHmeokpRK59rcz29j+F1/aDgbkbRTk7wIc9XzdoasMUbRNKDM0qQt/+BJ4BrpFeABemw==", + "version": "4.2.1", + "resolved": "https://registry.npmjs.org/eslint-visitor-keys/-/eslint-visitor-keys-4.2.1.tgz", + "integrity": "sha512-Uhdk5sfqcee/9H/rCOJikYz67o0a2Tw2hGRPOG2Y1R2dg7brRe1uG0yaNQDHu+TO/uQPF/5eCapvYSmHUjt7JQ==", "dev": true, "license": "Apache-2.0", "engines": { @@ -1360,9 +1219,10 @@ } }, "node_modules/dotenv": { - "version": "17.0.1", - "resolved": "https://registry.npmjs.org/dotenv/-/dotenv-17.0.1.tgz", - "integrity": "sha512-GLjkduuAL7IMJg/ZnOPm9AnWKJ82mSE2tzXLaJ/6hD6DhwGfZaXG77oB8qbReyiczNxnbxQKyh0OE5mXq0bAHA==", + "version": "17.2.3", + "resolved": "https://registry.npmjs.org/dotenv/-/dotenv-17.2.3.tgz", + "integrity": "sha512-JVUnt+DUIzu87TABbhPmNfVdBDt18BLOWjMUFJMSi/Qqg7NTYtabbvSNJGOJ7afbRuv9D/lngizHtP7QyLQ+9w==", + "license": "BSD-2-Clause", "engines": { "node": ">=12" }, @@ -1547,19 +1407,20 @@ } }, "node_modules/eslint": { - "version": "9.30.0", - "resolved": "https://registry.npmjs.org/eslint/-/eslint-9.30.0.tgz", - "integrity": "sha512-iN/SiPxmQu6EVkf+m1qpBxzUhE12YqFLOSySuOyVLJLEF9nzTf+h/1AJYc1JWzCnktggeNrjvQGLngDzXirU6g==", + "version": "9.37.0", + "resolved": "https://registry.npmjs.org/eslint/-/eslint-9.37.0.tgz", + "integrity": "sha512-XyLmROnACWqSxiGYArdef1fItQd47weqB7iwtfr9JHwRrqIXZdcFMvvEcL9xHCmL0SNsOvF0c42lWyM1U5dgig==", "dev": true, + "license": "MIT", "dependencies": { - "@eslint-community/eslint-utils": "^4.2.0", + "@eslint-community/eslint-utils": "^4.8.0", "@eslint-community/regexpp": "^4.12.1", "@eslint/config-array": "^0.21.0", - "@eslint/config-helpers": "^0.3.0", - "@eslint/core": "^0.14.0", + "@eslint/config-helpers": "^0.4.0", + "@eslint/core": "^0.16.0", "@eslint/eslintrc": "^3.3.1", - "@eslint/js": "9.30.0", - "@eslint/plugin-kit": "^0.3.1", + "@eslint/js": "9.37.0", + "@eslint/plugin-kit": "^0.4.0", "@humanfs/node": "^0.16.6", "@humanwhocodes/module-importer": "^1.0.1", "@humanwhocodes/retry": "^0.4.2", @@ -1607,9 +1468,9 @@ } }, "node_modules/eslint-config-prettier": { - "version": "10.1.5", - "resolved": "https://registry.npmjs.org/eslint-config-prettier/-/eslint-config-prettier-10.1.5.tgz", - "integrity": "sha512-zc1UmCpNltmVY34vuLRV61r1K27sWuX39E+uyUnY8xS2Bex88VV9cugG+UZbRSRGtGyFboj+D8JODyme1plMpw==", + "version": "10.1.8", + "resolved": "https://registry.npmjs.org/eslint-config-prettier/-/eslint-config-prettier-10.1.8.tgz", + "integrity": "sha512-82GZUjRS0p/jganf6q1rEO25VSoHH0hKPCTrgillPjdI/3bgBhAE1QzHrHTizjpRvy6pGAvKjDJtk2pF9NDq8w==", "dev": true, "license": "MIT", "bin": { diff --git a/e2e/package.json b/e2e/package.json index 1640b47b3..ec0245bfc 100644 --- a/e2e/package.json +++ b/e2e/package.json @@ -17,10 +17,10 @@ "@faker-js/faker": "9.8.0", "@playwright/test": "1.52.0", "@types/node": "24.0.11", - "@typescript-eslint/eslint-plugin": "8.33.1", - "@typescript-eslint/parser": "8.35.1", - "eslint": "9.30.0", - "eslint-config-prettier": "10.1.5", + "@typescript-eslint/eslint-plugin": "8.46.0", + "@typescript-eslint/parser": "8.46.0", + "eslint": "9.37.0", + "eslint-config-prettier": "10.1.8", "eslint-plugin-import": "2.32.0", "eslint-plugin-prettier": "5.4.1", "globals": "16.3.0", diff --git a/e2e/tests/utils/helper.ts b/e2e/tests/utils/helper.ts index 8637a8604..7222ebb6f 100644 --- a/e2e/tests/utils/helper.ts +++ b/e2e/tests/utils/helper.ts @@ -82,6 +82,25 @@ export async function createConfiguration( await save(page, expect.detached); } +export async function disableConfiguration(page: Page, configuration: { name: string; description: string }) { + await page.getByRole('link', { name: 'Assistants' }).click(); + await page.locator('li').filter({ hasText: configuration.name }).getByTestId('more-actions').click(); + + await page.click('button:has-text("Edit")'); + await page.locator('label').filter({ hasText: 'Enabled' }).locator('span').nth(2).click(); + await page.getByRole('button', { name: 'Save' }).click(); +} + +export async function deleteConfiguration(page: Page, configuration: { name: string; description: string }) { + await page.getByRole('link', { name: 'Assistants' }).click(); + await page.locator('li').filter({ hasText: configuration.name }).getByTestId('more-actions').click(); + + await page.click('button:has-text("Delete")'); + const confirmButton = page.locator('button:has-text("Confirm")'); + await page.click('button:has-text("Confirm")'); + await confirmButton.waitFor({ state: 'detached' }); +} + async function deleteListItems(page: Page, filter: { label: string }) { // wait until the list is rendered (otherwise count might be falsely 0) await page.waitForLoadState('networkidle'); @@ -407,7 +426,6 @@ export async function addAzureModelToConfiguration( await page.getByLabel('Instance Name').fill('cccc-testing'); await page.getByLabel('Seed').fill('42'); await page.getByLabel('Temperature').fill('0'); - await selectOption(page, 'API Version', '2023-05-15'); await page.getByRole('button', { name: 'Test' }).click(); const loader = page.locator('.mantine-Button-loader'); await loader.waitFor({ state: 'visible' }); @@ -447,11 +465,7 @@ export async function addSystemPromptToConfiguration( await page.getByLabel('Create Extension').getByRole('tab', { name: 'Other' }).click(); - await page - .locator('*') - .filter({ hasText: /^Prompt/ }) - .nth(1) - .click(); + await page.getByRole('heading', { name: 'Prompt', exact: true }).click(); await page.getByLabel('Text').fill(prompt.text); if (prompt.configurable) { diff --git a/frontend/eslint.config.mjs b/frontend/eslint.config.mjs index 215b443fe..565c7510b 100644 --- a/frontend/eslint.config.mjs +++ b/frontend/eslint.config.mjs @@ -69,7 +69,7 @@ export default defineConfig([globalIgnores([ parserOptions: { project: "tsconfig.json", - tsconfigRootDir: ".", + tsconfigRootDir: __dirname, ecmaFeatures: { jsx: true, @@ -87,7 +87,7 @@ export default defineConfig([globalIgnores([ "no-unused-vars": "off", // replaced by @typescript-eslint/no-unused-vars "@typescript-eslint/no-unused-vars": [ "error", - { + { "varsIgnorePattern": "^_.*", "argsIgnorePattern": "^_.*", "caughtErrorsIgnorePattern": "^_", diff --git a/frontend/package-lock.json b/frontend/package-lock.json index 6d38b3301..6aeef8adb 100644 --- a/frontend/package-lock.json +++ b/frontend/package-lock.json @@ -58,7 +58,7 @@ "@eslint/eslintrc": "3.3.1", "@eslint/js": "9.30.1", "@faker-js/faker": "9.8.0", - "@openapitools/openapi-generator-cli": "2.21.0", + "@openapitools/openapi-generator-cli": "2.23.1", "@tailwindcss/typography": "0.5.16", "@testing-library/dom": "10.4.0", "@testing-library/jest-dom": "6.6.3", @@ -69,13 +69,13 @@ "@types/react-dom": "18.3.7", "@types/react-speech-recognition": "^3.9.6", "@types/react-syntax-highlighter": "15.5.13", - "@typescript-eslint/eslint-plugin": "8.33.1", - "@typescript-eslint/parser": "8.35.0", + "@typescript-eslint/eslint-plugin": "8.46.0", + "@typescript-eslint/parser": "8.46.0", "@vitejs/plugin-react": "4.5.1", "@vitest/coverage-v8": "3.2.1", "daisyui": "5.0.43", - "eslint": "9.30.0", - "eslint-config-prettier": "10.1.5", + "eslint": "9.37.0", + "eslint-config-prettier": "10.1.8", "eslint-plugin-import": "2.32.0", "eslint-plugin-prettier": "5.4.1", "eslint-plugin-react": "7.37.5", @@ -96,7 +96,7 @@ "rimraf": "6.0.1", "tailwindcss": "4.1.8", "typescript": "5.8.3", - "vite": "6.3.5", + "vite": "6.3.6", "vitest": "3.2.1" } }, @@ -642,6 +642,17 @@ "node": ">=18" } }, + "node_modules/@borewit/text-codec": { + "version": "0.1.1", + "resolved": "https://registry.npmjs.org/@borewit/text-codec/-/text-codec-0.1.1.tgz", + "integrity": "sha512-5L/uBxmjaCIX5h8Z+uu+kA9BQLkc/Wl06UGR5ajNRxu+/XjonB5i8JpgFMrPj3LXTCPA0pv8yxUvbUi+QthGGA==", + "dev": true, + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/Borewit" + } + }, "node_modules/@bundled-es-modules/cookie": { "version": "2.0.1", "dev": true, @@ -843,7 +854,9 @@ } }, "node_modules/@eslint-community/eslint-utils": { - "version": "4.7.0", + "version": "4.9.0", + "resolved": "https://registry.npmjs.org/@eslint-community/eslint-utils/-/eslint-utils-4.9.0.tgz", + "integrity": "sha512-ayVFHdtZ+hsq1t2Dy24wCmGXGe4q9Gu3smhLYALJrr473ZH27MsnSL+LKUlimp4BWJqMDMLmPpx/Q9R3OAlL4g==", "dev": true, "license": "MIT", "dependencies": { @@ -898,18 +911,22 @@ } }, "node_modules/@eslint/config-helpers": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/@eslint/config-helpers/-/config-helpers-0.3.0.tgz", - "integrity": "sha512-ViuymvFmcJi04qdZeDc2whTHryouGcDlaxPqarTD0ZE10ISpxGUVZGZDx4w01upyIynL3iu6IXH2bS1NhclQMw==", + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/@eslint/config-helpers/-/config-helpers-0.4.0.tgz", + "integrity": "sha512-WUFvV4WoIwW8Bv0KeKCIIEgdSiFOsulyN0xrMu+7z43q/hkOLXjvb5u7UC9jDxvRzcrbEmuZBX5yJZz1741jog==", "dev": true, + "license": "Apache-2.0", + "dependencies": { + "@eslint/core": "^0.16.0" + }, "engines": { "node": "^18.18.0 || ^20.9.0 || >=21.1.0" } }, "node_modules/@eslint/core": { - "version": "0.14.0", - "resolved": "https://registry.npmjs.org/@eslint/core/-/core-0.14.0.tgz", - "integrity": "sha512-qIbV0/JZr7iSDjqAc60IqbLdsj9GDt16xQtWD+B78d/HAlvysGdZZ6rpJHGAc2T0FQx1X6thsSPdnoiGKdNtdg==", + "version": "0.16.0", + "resolved": "https://registry.npmjs.org/@eslint/core/-/core-0.16.0.tgz", + "integrity": "sha512-nmC8/totwobIiFcGkDza3GIKfAw1+hLiYVrh3I1nIomQ8PEr5cxg34jnkmGawul/ep52wGRAcyeDCNtWKSOj4Q==", "dev": true, "license": "Apache-2.0", "dependencies": { @@ -974,13 +991,13 @@ } }, "node_modules/@eslint/plugin-kit": { - "version": "0.3.1", - "resolved": "https://registry.npmjs.org/@eslint/plugin-kit/-/plugin-kit-0.3.1.tgz", - "integrity": "sha512-0J+zgWxHN+xXONWIyPWKFMgVuJoZuGiIFu8yxk7RJjxkzpGmyja5wRFqZIVtjDVOQpV+Rw0iOAjYPE2eQyjr0w==", + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/@eslint/plugin-kit/-/plugin-kit-0.4.0.tgz", + "integrity": "sha512-sB5uyeq+dwCWyPi31B2gQlVlo+j5brPlWx4yZBrEaRo/nhdDE8Xke1gsGgtiBdaBTxuTkceLVuVt/pclrasb0A==", "dev": true, "license": "Apache-2.0", "dependencies": { - "@eslint/core": "^0.14.0", + "@eslint/core": "^0.16.0", "levn": "^0.4.1" }, "engines": { @@ -1180,6 +1197,28 @@ "node": "^18.17.0 || >=20.5.0" } }, + "node_modules/@inquirer/external-editor": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/@inquirer/external-editor/-/external-editor-1.0.1.tgz", + "integrity": "sha512-Oau4yL24d2B5IL4ma4UpbQigkVhzPDXLoqy1ggK4gnHg/stmkffJE4oOXHXF3uz0UEpywG68KcyXsyYpA1Re/Q==", + "dev": true, + "license": "MIT", + "dependencies": { + "chardet": "^2.1.0", + "iconv-lite": "^0.6.3" + }, + "engines": { + "node": ">=18" + }, + "peerDependencies": { + "@types/node": ">=18" + }, + "peerDependenciesMeta": { + "@types/node": { + "optional": true + } + } + }, "node_modules/@inquirer/figures": { "version": "1.0.11", "dev": true, @@ -1380,6 +1419,8 @@ }, "node_modules/@lukeed/csprng": { "version": "1.1.0", + "resolved": "https://registry.npmjs.org/@lukeed/csprng/-/csprng-1.1.0.tgz", + "integrity": "sha512-Z7C/xXCiGWsg0KuKsHTKJxbWhpI3Vs5GwLfOean7MGyVFGqdRgBbAjOCh6u4bbjPc/8MJ2pZmK/0DLdCbivLDA==", "dev": true, "license": "MIT", "engines": { @@ -1672,7 +1713,9 @@ } }, "node_modules/@nestjs/axios": { - "version": "4.0.0", + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/@nestjs/axios/-/axios-4.0.1.tgz", + "integrity": "sha512-68pFJgu+/AZbWkGu65Z3r55bTsCPlgyKaV4BSG8yUAD72q1PPuyVRgUwFv6BxdnibTUHlyxm06FmYWNC+bjN7A==", "dev": true, "license": "MIT", "peerDependencies": { @@ -1682,9 +1725,9 @@ } }, "node_modules/@nestjs/common": { - "version": "11.1.3", - "resolved": "https://registry.npmjs.org/@nestjs/common/-/common-11.1.3.tgz", - "integrity": "sha512-ogEK+GriWodIwCw6buQ1rpcH4Kx+G7YQ9EwuPySI3rS05pSdtQ++UhucjusSI9apNidv+QURBztJkRecwwJQXg==", + "version": "11.1.6", + "resolved": "https://registry.npmjs.org/@nestjs/common/-/common-11.1.6.tgz", + "integrity": "sha512-krKwLLcFmeuKDqngG2N/RuZHCs2ycsKcxWIDgcm7i1lf3sQ0iG03ci+DsP/r3FcT/eJDFsIHnKtNta2LIi7PzQ==", "dev": true, "license": "MIT", "dependencies": { @@ -1714,9 +1757,9 @@ } }, "node_modules/@nestjs/core": { - "version": "11.1.3", - "resolved": "https://registry.npmjs.org/@nestjs/core/-/core-11.1.3.tgz", - "integrity": "sha512-5lTni0TCh8x7bXETRD57pQFnKnEg1T6M+VLE7wAmyQRIecKQU+2inRGZD+A4v2DC1I04eA0WffP0GKLxjOKlzw==", + "version": "11.1.6", + "resolved": "https://registry.npmjs.org/@nestjs/core/-/core-11.1.6.tgz", + "integrity": "sha512-siWX7UDgErisW18VTeJA+x+/tpNZrJewjTBsRPF3JVxuWRuAB1kRoiJcxHgln8Lb5UY9NdvklITR84DUEXD0Cg==", "dev": true, "hasInstallScript": true, "license": "MIT", @@ -1846,27 +1889,26 @@ "license": "MIT" }, "node_modules/@openapitools/openapi-generator-cli": { - "version": "2.21.0", - "resolved": "https://registry.npmjs.org/@openapitools/openapi-generator-cli/-/openapi-generator-cli-2.21.0.tgz", - "integrity": "sha512-NdDvCd7hya+UucxH7G94Jf6tmA6641I4CF/T3xtFhM+NQQNWAP5tpiOBN4Ub9ocU6cCgQgXdWl4EpwlEwW7JDQ==", + "version": "2.23.1", + "resolved": "https://registry.npmjs.org/@openapitools/openapi-generator-cli/-/openapi-generator-cli-2.23.1.tgz", + "integrity": "sha512-Kd5EZqzbcIXf6KRlpUrheHMzQNRHsJWzAGrm4ncWCNhnQl+Mh6TsFcqq+hIetgiFCknWBH6cZ2f37SxPxaon4w==", "dev": true, "hasInstallScript": true, "license": "Apache-2.0", "dependencies": { - "@nestjs/axios": "4.0.0", - "@nestjs/common": "11.1.3", - "@nestjs/core": "11.1.3", + "@nestjs/axios": "4.0.1", + "@nestjs/common": "11.1.6", + "@nestjs/core": "11.1.6", "@nuxtjs/opencollective": "0.3.2", - "axios": "1.10.0", + "axios": "1.11.0", "chalk": "4.1.2", "commander": "8.3.0", "compare-versions": "4.1.4", - "concurrently": "6.5.1", + "concurrently": "9.2.1", "console.table": "0.10.0", - "fs-extra": "11.3.0", + "fs-extra": "11.3.1", "glob": "11.0.3", - "inquirer": "8.2.6", - "lodash": "4.17.21", + "inquirer": "8.2.7", "proxy-agent": "6.5.0", "reflect-metadata": "0.2.2", "rxjs": "7.8.2", @@ -3212,17 +3254,17 @@ "license": "MIT" }, "node_modules/@typescript-eslint/eslint-plugin": { - "version": "8.33.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/eslint-plugin/-/eslint-plugin-8.33.1.tgz", - "integrity": "sha512-TDCXj+YxLgtvxvFlAvpoRv9MAncDLBV2oT9Bd7YBGC/b/sEURoOYuIwLI99rjWOfY3QtDzO+mk0n4AmdFExW8A==", + "version": "8.46.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/eslint-plugin/-/eslint-plugin-8.46.0.tgz", + "integrity": "sha512-hA8gxBq4ukonVXPy0OKhiaUh/68D0E88GSmtC1iAEnGaieuDi38LhS7jdCHRLi6ErJBNDGCzvh5EnzdPwUc0DA==", "dev": true, "license": "MIT", "dependencies": { "@eslint-community/regexpp": "^4.10.0", - "@typescript-eslint/scope-manager": "8.33.1", - "@typescript-eslint/type-utils": "8.33.1", - "@typescript-eslint/utils": "8.33.1", - "@typescript-eslint/visitor-keys": "8.33.1", + "@typescript-eslint/scope-manager": "8.46.0", + "@typescript-eslint/type-utils": "8.46.0", + "@typescript-eslint/utils": "8.46.0", + "@typescript-eslint/visitor-keys": "8.46.0", "graphemer": "^1.4.0", "ignore": "^7.0.0", "natural-compare": "^1.4.0", @@ -3236,9 +3278,9 @@ "url": "https://opencollective.com/typescript-eslint" }, "peerDependencies": { - "@typescript-eslint/parser": "^8.33.1", + "@typescript-eslint/parser": "8.46.0", "eslint": "^8.57.0 || ^9.0.0", - "typescript": ">=4.8.4 <5.9.0" + "typescript": ">=4.8.4 <6.0.0" } }, "node_modules/@typescript-eslint/eslint-plugin/node_modules/ignore": { @@ -3252,15 +3294,16 @@ } }, "node_modules/@typescript-eslint/parser": { - "version": "8.35.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/parser/-/parser-8.35.0.tgz", - "integrity": "sha512-6sMvZePQrnZH2/cJkwRpkT7DxoAWh+g6+GFRK6bV3YQo7ogi3SX5rgF6099r5Q53Ma5qeT7LGmOmuIutF4t3lA==", + "version": "8.46.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/parser/-/parser-8.46.0.tgz", + "integrity": "sha512-n1H6IcDhmmUEG7TNVSspGmiHHutt7iVKtZwRppD7e04wha5MrkV1h3pti9xQLcCMt6YWsncpoT0HMjkH1FNwWQ==", "dev": true, + "license": "MIT", "dependencies": { - "@typescript-eslint/scope-manager": "8.35.0", - "@typescript-eslint/types": "8.35.0", - "@typescript-eslint/typescript-estree": "8.35.0", - "@typescript-eslint/visitor-keys": "8.35.0", + "@typescript-eslint/scope-manager": "8.46.0", + "@typescript-eslint/types": "8.46.0", + "@typescript-eslint/typescript-estree": "8.46.0", + "@typescript-eslint/visitor-keys": "8.46.0", "debug": "^4.3.4" }, "engines": { @@ -3272,166 +3315,18 @@ }, "peerDependencies": { "eslint": "^8.57.0 || ^9.0.0", - "typescript": ">=4.8.4 <5.9.0" - } - }, - "node_modules/@typescript-eslint/parser/node_modules/@typescript-eslint/project-service": { - "version": "8.35.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/project-service/-/project-service-8.35.0.tgz", - "integrity": "sha512-41xatqRwWZuhUMF/aZm2fcUsOFKNcG28xqRSS6ZVr9BVJtGExosLAm5A1OxTjRMagx8nJqva+P5zNIGt8RIgbQ==", - "dev": true, - "dependencies": { - "@typescript-eslint/tsconfig-utils": "^8.35.0", - "@typescript-eslint/types": "^8.35.0", - "debug": "^4.3.4" - }, - "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/typescript-eslint" - }, - "peerDependencies": { - "typescript": ">=4.8.4 <5.9.0" - } - }, - "node_modules/@typescript-eslint/parser/node_modules/@typescript-eslint/scope-manager": { - "version": "8.35.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/scope-manager/-/scope-manager-8.35.0.tgz", - "integrity": "sha512-+AgL5+mcoLxl1vGjwNfiWq5fLDZM1TmTPYs2UkyHfFhgERxBbqHlNjRzhThJqz+ktBqTChRYY6zwbMwy0591AA==", - "dev": true, - "dependencies": { - "@typescript-eslint/types": "8.35.0", - "@typescript-eslint/visitor-keys": "8.35.0" - }, - "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/typescript-eslint" - } - }, - "node_modules/@typescript-eslint/parser/node_modules/@typescript-eslint/tsconfig-utils": { - "version": "8.35.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/tsconfig-utils/-/tsconfig-utils-8.35.0.tgz", - "integrity": "sha512-04k/7247kZzFraweuEirmvUj+W3bJLI9fX6fbo1Qm2YykuBvEhRTPl8tcxlYO8kZZW+HIXfkZNoasVb8EV4jpA==", - "dev": true, - "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/typescript-eslint" - }, - "peerDependencies": { - "typescript": ">=4.8.4 <5.9.0" - } - }, - "node_modules/@typescript-eslint/parser/node_modules/@typescript-eslint/types": { - "version": "8.35.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-8.35.0.tgz", - "integrity": "sha512-0mYH3emanku0vHw2aRLNGqe7EXh9WHEhi7kZzscrMDf6IIRUQ5Jk4wp1QrledE/36KtdZrVfKnE32eZCf/vaVQ==", - "dev": true, - "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/typescript-eslint" - } - }, - "node_modules/@typescript-eslint/parser/node_modules/@typescript-eslint/typescript-estree": { - "version": "8.35.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-8.35.0.tgz", - "integrity": "sha512-F+BhnaBemgu1Qf8oHrxyw14wq6vbL8xwWKKMwTMwYIRmFFY/1n/9T/jpbobZL8vp7QyEUcC6xGrnAO4ua8Kp7w==", - "dev": true, - "dependencies": { - "@typescript-eslint/project-service": "8.35.0", - "@typescript-eslint/tsconfig-utils": "8.35.0", - "@typescript-eslint/types": "8.35.0", - "@typescript-eslint/visitor-keys": "8.35.0", - "debug": "^4.3.4", - "fast-glob": "^3.3.2", - "is-glob": "^4.0.3", - "minimatch": "^9.0.4", - "semver": "^7.6.0", - "ts-api-utils": "^2.1.0" - }, - "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/typescript-eslint" - }, - "peerDependencies": { - "typescript": ">=4.8.4 <5.9.0" - } - }, - "node_modules/@typescript-eslint/parser/node_modules/@typescript-eslint/visitor-keys": { - "version": "8.35.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-8.35.0.tgz", - "integrity": "sha512-zTh2+1Y8ZpmeQaQVIc/ZZxsx8UzgKJyNg1PTvjzC7WMhPSVS8bfDX34k1SrwOf016qd5RU3az2UxUNue3IfQ5g==", - "dev": true, - "dependencies": { - "@typescript-eslint/types": "8.35.0", - "eslint-visitor-keys": "^4.2.1" - }, - "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/typescript-eslint" - } - }, - "node_modules/@typescript-eslint/parser/node_modules/brace-expansion": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-2.0.2.tgz", - "integrity": "sha512-Jt0vHyM+jmUBqojB7E1NIYadt0vI0Qxjxd2TErW94wDz+E2LAm5vKMXXwg6ZZBTHPuUlDgQHKXvjGBdfcF1ZDQ==", - "dev": true, - "dependencies": { - "balanced-match": "^1.0.0" - } - }, - "node_modules/@typescript-eslint/parser/node_modules/eslint-visitor-keys": { - "version": "4.2.1", - "resolved": "https://registry.npmjs.org/eslint-visitor-keys/-/eslint-visitor-keys-4.2.1.tgz", - "integrity": "sha512-Uhdk5sfqcee/9H/rCOJikYz67o0a2Tw2hGRPOG2Y1R2dg7brRe1uG0yaNQDHu+TO/uQPF/5eCapvYSmHUjt7JQ==", - "dev": true, - "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" - }, - "funding": { - "url": "https://opencollective.com/eslint" - } - }, - "node_modules/@typescript-eslint/parser/node_modules/minimatch": { - "version": "9.0.5", - "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-9.0.5.tgz", - "integrity": "sha512-G6T0ZX48xgozx7587koeX9Ys2NYy6Gmv//P89sEte9V9whIapMNF4idKxnW2QtCcLiTWlb/wfCabAtAFWhhBow==", - "dev": true, - "dependencies": { - "brace-expansion": "^2.0.1" - }, - "engines": { - "node": ">=16 || 14 >=14.17" - }, - "funding": { - "url": "https://github.com/sponsors/isaacs" + "typescript": ">=4.8.4 <6.0.0" } }, "node_modules/@typescript-eslint/project-service": { - "version": "8.33.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/project-service/-/project-service-8.33.1.tgz", - "integrity": "sha512-DZR0efeNklDIHHGRpMpR5gJITQpu6tLr9lDJnKdONTC7vvzOlLAG/wcfxcdxEWrbiZApcoBCzXqU/Z458Za5Iw==", + "version": "8.46.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/project-service/-/project-service-8.46.0.tgz", + "integrity": "sha512-OEhec0mH+U5Je2NZOeK1AbVCdm0ChyapAyTeXVIYTPXDJ3F07+cu87PPXcGoYqZ7M9YJVvFnfpGg1UmCIqM+QQ==", "dev": true, "license": "MIT", "dependencies": { - "@typescript-eslint/tsconfig-utils": "^8.33.1", - "@typescript-eslint/types": "^8.33.1", + "@typescript-eslint/tsconfig-utils": "^8.46.0", + "@typescript-eslint/types": "^8.46.0", "debug": "^4.3.4" }, "engines": { @@ -3442,18 +3337,18 @@ "url": "https://opencollective.com/typescript-eslint" }, "peerDependencies": { - "typescript": ">=4.8.4 <5.9.0" + "typescript": ">=4.8.4 <6.0.0" } }, "node_modules/@typescript-eslint/scope-manager": { - "version": "8.33.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/scope-manager/-/scope-manager-8.33.1.tgz", - "integrity": "sha512-dM4UBtgmzHR9bS0Rv09JST0RcHYearoEoo3pG5B6GoTR9XcyeqX87FEhPo+5kTvVfKCvfHaHrcgeJQc6mrDKrA==", + "version": "8.46.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/scope-manager/-/scope-manager-8.46.0.tgz", + "integrity": "sha512-lWETPa9XGcBes4jqAMYD9fW0j4n6hrPtTJwWDmtqgFO/4HF4jmdH/Q6wggTw5qIT5TXjKzbt7GsZUBnWoO3dqw==", "dev": true, "license": "MIT", "dependencies": { - "@typescript-eslint/types": "8.33.1", - "@typescript-eslint/visitor-keys": "8.33.1" + "@typescript-eslint/types": "8.46.0", + "@typescript-eslint/visitor-keys": "8.46.0" }, "engines": { "node": "^18.18.0 || ^20.9.0 || >=21.1.0" @@ -3464,9 +3359,9 @@ } }, "node_modules/@typescript-eslint/tsconfig-utils": { - "version": "8.33.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/tsconfig-utils/-/tsconfig-utils-8.33.1.tgz", - "integrity": "sha512-STAQsGYbHCF0/e+ShUQ4EatXQ7ceh3fBCXkNU7/MZVKulrlq1usH7t2FhxvCpuCi5O5oi1vmVaAjrGeL71OK1g==", + "version": "8.46.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/tsconfig-utils/-/tsconfig-utils-8.46.0.tgz", + "integrity": "sha512-WrYXKGAHY836/N7zoK/kzi6p8tXFhasHh8ocFL9VZSAkvH956gfeRfcnhs3xzRy8qQ/dq3q44v1jvQieMFg2cw==", "dev": true, "license": "MIT", "engines": { @@ -3477,18 +3372,19 @@ "url": "https://opencollective.com/typescript-eslint" }, "peerDependencies": { - "typescript": ">=4.8.4 <5.9.0" + "typescript": ">=4.8.4 <6.0.0" } }, "node_modules/@typescript-eslint/type-utils": { - "version": "8.33.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/type-utils/-/type-utils-8.33.1.tgz", - "integrity": "sha512-1cG37d9xOkhlykom55WVwG2QRNC7YXlxMaMzqw2uPeJixBFfKWZgaP/hjAObqMN/u3fr5BrTwTnc31/L9jQ2ww==", + "version": "8.46.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/type-utils/-/type-utils-8.46.0.tgz", + "integrity": "sha512-hy+lvYV1lZpVs2jRaEYvgCblZxUoJiPyCemwbQZ+NGulWkQRy0HRPYAoef/CNSzaLt+MLvMptZsHXHlkEilaeg==", "dev": true, "license": "MIT", "dependencies": { - "@typescript-eslint/typescript-estree": "8.33.1", - "@typescript-eslint/utils": "8.33.1", + "@typescript-eslint/types": "8.46.0", + "@typescript-eslint/typescript-estree": "8.46.0", + "@typescript-eslint/utils": "8.46.0", "debug": "^4.3.4", "ts-api-utils": "^2.1.0" }, @@ -3501,13 +3397,13 @@ }, "peerDependencies": { "eslint": "^8.57.0 || ^9.0.0", - "typescript": ">=4.8.4 <5.9.0" + "typescript": ">=4.8.4 <6.0.0" } }, "node_modules/@typescript-eslint/types": { - "version": "8.33.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-8.33.1.tgz", - "integrity": "sha512-xid1WfizGhy/TKMTwhtVOgalHwPtV8T32MS9MaH50Cwvz6x6YqRIPdD2WvW0XaqOzTV9p5xdLY0h/ZusU5Lokg==", + "version": "8.46.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-8.46.0.tgz", + "integrity": "sha512-bHGGJyVjSE4dJJIO5yyEWt/cHyNwga/zXGJbJJ8TiO01aVREK6gCTu3L+5wrkb1FbDkQ+TKjMNe9R/QQQP9+rA==", "dev": true, "license": "MIT", "engines": { @@ -3519,16 +3415,16 @@ } }, "node_modules/@typescript-eslint/typescript-estree": { - "version": "8.33.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-8.33.1.tgz", - "integrity": "sha512-+s9LYcT8LWjdYWu7IWs7FvUxpQ/DGkdjZeE/GGulHvv8rvYwQvVaUZ6DE+j5x/prADUgSbbCWZ2nPI3usuVeOA==", + "version": "8.46.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-8.46.0.tgz", + "integrity": "sha512-ekDCUfVpAKWJbRfm8T1YRrCot1KFxZn21oV76v5Fj4tr7ELyk84OS+ouvYdcDAwZL89WpEkEj2DKQ+qg//+ucg==", "dev": true, "license": "MIT", "dependencies": { - "@typescript-eslint/project-service": "8.33.1", - "@typescript-eslint/tsconfig-utils": "8.33.1", - "@typescript-eslint/types": "8.33.1", - "@typescript-eslint/visitor-keys": "8.33.1", + "@typescript-eslint/project-service": "8.46.0", + "@typescript-eslint/tsconfig-utils": "8.46.0", + "@typescript-eslint/types": "8.46.0", + "@typescript-eslint/visitor-keys": "8.46.0", "debug": "^4.3.4", "fast-glob": "^3.3.2", "is-glob": "^4.0.3", @@ -3544,13 +3440,13 @@ "url": "https://opencollective.com/typescript-eslint" }, "peerDependencies": { - "typescript": ">=4.8.4 <5.9.0" + "typescript": ">=4.8.4 <6.0.0" } }, "node_modules/@typescript-eslint/typescript-estree/node_modules/brace-expansion": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-2.0.1.tgz", - "integrity": "sha512-XnAIvQ8eM+kC6aULx6wuQiwVsnzsi9d3WxzV3FpWTGA19F621kwdbsAcFKXgKUHZWsy+mY6iL1sHTxWEFCytDA==", + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-2.0.2.tgz", + "integrity": "sha512-Jt0vHyM+jmUBqojB7E1NIYadt0vI0Qxjxd2TErW94wDz+E2LAm5vKMXXwg6ZZBTHPuUlDgQHKXvjGBdfcF1ZDQ==", "dev": true, "license": "MIT", "dependencies": { @@ -3574,16 +3470,16 @@ } }, "node_modules/@typescript-eslint/utils": { - "version": "8.33.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/utils/-/utils-8.33.1.tgz", - "integrity": "sha512-52HaBiEQUaRYqAXpfzWSR2U3gxk92Kw006+xZpElaPMg3C4PgM+A5LqwoQI1f9E5aZ/qlxAZxzm42WX+vn92SQ==", + "version": "8.46.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/utils/-/utils-8.46.0.tgz", + "integrity": "sha512-nD6yGWPj1xiOm4Gk0k6hLSZz2XkNXhuYmyIrOWcHoPuAhjT9i5bAG+xbWPgFeNR8HPHHtpNKdYUXJl/D3x7f5g==", "dev": true, "license": "MIT", "dependencies": { "@eslint-community/eslint-utils": "^4.7.0", - "@typescript-eslint/scope-manager": "8.33.1", - "@typescript-eslint/types": "8.33.1", - "@typescript-eslint/typescript-estree": "8.33.1" + "@typescript-eslint/scope-manager": "8.46.0", + "@typescript-eslint/types": "8.46.0", + "@typescript-eslint/typescript-estree": "8.46.0" }, "engines": { "node": "^18.18.0 || ^20.9.0 || >=21.1.0" @@ -3594,18 +3490,18 @@ }, "peerDependencies": { "eslint": "^8.57.0 || ^9.0.0", - "typescript": ">=4.8.4 <5.9.0" + "typescript": ">=4.8.4 <6.0.0" } }, "node_modules/@typescript-eslint/visitor-keys": { - "version": "8.33.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-8.33.1.tgz", - "integrity": "sha512-3i8NrFcZeeDHJ+7ZUuDkGT+UHq+XoFGsymNK2jZCOHcfEzRQ0BdpRtdpSx/Iyf3MHLWIcLS0COuOPibKQboIiQ==", + "version": "8.46.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-8.46.0.tgz", + "integrity": "sha512-FrvMpAK+hTbFy7vH5j1+tMYHMSKLE6RzluFJlkFNKD0p9YsUT75JlBSmr5so3QRzvMwU5/bIEdeNrxm8du8l3Q==", "dev": true, "license": "MIT", "dependencies": { - "@typescript-eslint/types": "8.33.1", - "eslint-visitor-keys": "^4.2.0" + "@typescript-eslint/types": "8.46.0", + "eslint-visitor-keys": "^4.2.1" }, "engines": { "node": "^18.18.0 || ^20.9.0 || >=21.1.0" @@ -3616,9 +3512,9 @@ } }, "node_modules/@typescript-eslint/visitor-keys/node_modules/eslint-visitor-keys": { - "version": "4.2.0", - "resolved": "https://registry.npmjs.org/eslint-visitor-keys/-/eslint-visitor-keys-4.2.0.tgz", - "integrity": "sha512-UyLnSehNt62FFhSwjZlHmeokpRK59rcz29j+F1/aDgbkbRTk7wIc9XzdoasMUbRNKDM0qQt/+BJ4BrpFeABemw==", + "version": "4.2.1", + "resolved": "https://registry.npmjs.org/eslint-visitor-keys/-/eslint-visitor-keys-4.2.1.tgz", + "integrity": "sha512-Uhdk5sfqcee/9H/rCOJikYz67o0a2Tw2hGRPOG2Y1R2dg7brRe1uG0yaNQDHu+TO/uQPF/5eCapvYSmHUjt7JQ==", "dev": true, "license": "Apache-2.0", "engines": { @@ -4125,6 +4021,8 @@ }, "node_modules/asynckit": { "version": "0.4.0", + "resolved": "https://registry.npmjs.org/asynckit/-/asynckit-0.4.0.tgz", + "integrity": "sha512-Oei9OH4tRh0YqU3GxhX79dM/mwVgvbZJaSNaRk+bshkj0S5cfHcgYakreBjrHwatXKbz+IoIdYLxrKim2MjW0Q==", "dev": true, "license": "MIT" }, @@ -4150,14 +4048,14 @@ } }, "node_modules/axios": { - "version": "1.10.0", - "resolved": "https://registry.npmjs.org/axios/-/axios-1.10.0.tgz", - "integrity": "sha512-/1xYAC4MP/HEG+3duIhFr4ZQXR4sQXOIe+o6sdqzeykGLx6Upp/1p8MHqhINOvGeP7xyNHe7tsiJByc4SSVUxw==", + "version": "1.11.0", + "resolved": "https://registry.npmjs.org/axios/-/axios-1.11.0.tgz", + "integrity": "sha512-1Lx3WLFQWm3ooKDYZD1eXmoGO9fxYQjrycfHFC8P0sCfQVXyROp0p9PFWBehewBOdCwHc+f/b8I0fMto5eSfwA==", "dev": true, "license": "MIT", "dependencies": { "follow-redirects": "^1.15.6", - "form-data": "^4.0.0", + "form-data": "^4.0.4", "proxy-from-env": "^1.1.0" } }, @@ -4176,6 +4074,8 @@ }, "node_modules/base64-js": { "version": "1.5.1", + "resolved": "https://registry.npmjs.org/base64-js/-/base64-js-1.5.1.tgz", + "integrity": "sha512-AKpaYlHn8t4SVbOHCy+b5+KKgvR4vrsD8vbvrbiQJps7fKDTkjkDry6ji0rUJjC0kzbNePLwzxq8iypo41qeWA==", "dev": true, "funding": [ { @@ -4203,6 +4103,8 @@ }, "node_modules/bl": { "version": "4.1.0", + "resolved": "https://registry.npmjs.org/bl/-/bl-4.1.0.tgz", + "integrity": "sha512-1W07cM9gS6DcLperZfFSj+bWLtaPGSOHWhPiGzXmvVJbRLdG82sH/Kn8EtW1VqWVA54AKf2h5k5BbnIbwF3h6w==", "dev": true, "license": "MIT", "dependencies": { @@ -4264,6 +4166,8 @@ }, "node_modules/buffer": { "version": "5.7.1", + "resolved": "https://registry.npmjs.org/buffer/-/buffer-5.7.1.tgz", + "integrity": "sha512-EHcyIPBQ4BSGlvjB16k5KgAJ27CIsHY/2JBmCRReo48y9rQ3MaUzWX3KVlBa4U7MyX02HdVj0K7C3WaB3ju7FQ==", "dev": true, "funding": [ { @@ -4448,7 +4352,9 @@ } }, "node_modules/chardet": { - "version": "0.7.0", + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/chardet/-/chardet-2.1.0.tgz", + "integrity": "sha512-bNFETTG/pM5ryzQ9Ad0lJOTa6HWD/YsScAR3EnCPZRPlQh77JocYktSHOUHelyhm8IARL+o4c4F1bP5KVOjiRA==", "dev": true, "license": "MIT" }, @@ -4479,6 +4385,8 @@ }, "node_modules/cli-cursor": { "version": "3.1.0", + "resolved": "https://registry.npmjs.org/cli-cursor/-/cli-cursor-3.1.0.tgz", + "integrity": "sha512-I/zHAwsKf9FqGoXM4WWRACob9+SNukZTd94DWF57E4toouRulbCxcUh6RKUEOQlYTHJnzkPMySvPNaaSLNfLZw==", "dev": true, "license": "MIT", "dependencies": { @@ -4490,6 +4398,8 @@ }, "node_modules/cli-spinners": { "version": "2.9.2", + "resolved": "https://registry.npmjs.org/cli-spinners/-/cli-spinners-2.9.2.tgz", + "integrity": "sha512-ywqV+5MmyL4E7ybXgKys4DugZbX0FC6LnwrhjuykIjnK9k8OQacQ7axGKnjDXWNhns0xot3bZI5h55H8yo9cJg==", "dev": true, "license": "MIT", "engines": { @@ -4501,6 +4411,8 @@ }, "node_modules/cli-width": { "version": "3.0.0", + "resolved": "https://registry.npmjs.org/cli-width/-/cli-width-3.0.0.tgz", + "integrity": "sha512-FxqpkPPwu1HjuN93Omfm4h8uIanXofW0RxVEW3k5RKx+mJJYSthzNhp32Kzxxy3YAEZ/Dc/EWN1vZRY0+kOhbw==", "dev": true, "license": "ISC", "engines": { @@ -4508,17 +4420,24 @@ } }, "node_modules/cliui": { - "version": "7.0.4", + "version": "8.0.1", + "resolved": "https://registry.npmjs.org/cliui/-/cliui-8.0.1.tgz", + "integrity": "sha512-BSeNnyus75C4//NQ9gQt1/csTXyo/8Sb+afLAkzAptFuMsod9HFokGNudZpi/oQV73hnVK+sR+5PVRMd+Dr7YQ==", "dev": true, "license": "ISC", "dependencies": { "string-width": "^4.2.0", - "strip-ansi": "^6.0.0", + "strip-ansi": "^6.0.1", "wrap-ansi": "^7.0.0" + }, + "engines": { + "node": ">=12" } }, "node_modules/cliui/node_modules/wrap-ansi": { "version": "7.0.0", + "resolved": "https://registry.npmjs.org/wrap-ansi/-/wrap-ansi-7.0.0.tgz", + "integrity": "sha512-YVGIj2kamLSTxw6NsZjoBxfSwsn0ycdesmc4p+Q21c5zPuZ1pl+NfxVdxPtdHvmNVOQ6XSYG4AUtyt/Fi7D16Q==", "dev": true, "license": "MIT", "dependencies": { @@ -4566,6 +4485,8 @@ }, "node_modules/combined-stream": { "version": "1.0.8", + "resolved": "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.8.tgz", + "integrity": "sha512-FQN4MRfuJeHf7cBbBMJFXhKSDq+2kAArBlmRBvcvFE5BB1HZKXtSFASDhdlz9zOYwxh8lDdnvmMOe/+5cdoEdg==", "dev": true, "license": "MIT", "dependencies": { @@ -4601,54 +4522,34 @@ "license": "MIT" }, "node_modules/concurrently": { - "version": "6.5.1", + "version": "9.2.1", + "resolved": "https://registry.npmjs.org/concurrently/-/concurrently-9.2.1.tgz", + "integrity": "sha512-fsfrO0MxV64Znoy8/l1vVIjjHa29SZyyqPgQBwhiDcaW8wJc2W3XWVOGx4M3oJBnv/zdUZIIp1gDeS98GzP8Ng==", "dev": true, "license": "MIT", "dependencies": { - "chalk": "^4.1.0", - "date-fns": "^2.16.1", - "lodash": "^4.17.21", - "rxjs": "^6.6.3", - "spawn-command": "^0.0.2-1", - "supports-color": "^8.1.0", - "tree-kill": "^1.2.2", - "yargs": "^16.2.0" + "chalk": "4.1.2", + "rxjs": "7.8.2", + "shell-quote": "1.8.3", + "supports-color": "8.1.1", + "tree-kill": "1.2.2", + "yargs": "17.7.2" }, "bin": { - "concurrently": "bin/concurrently.js" - }, - "engines": { - "node": ">=10.0.0" - } - }, - "node_modules/concurrently/node_modules/date-fns": { - "version": "2.30.0", - "dev": true, - "license": "MIT", - "dependencies": { - "@babel/runtime": "^7.21.0" + "conc": "dist/bin/concurrently.js", + "concurrently": "dist/bin/concurrently.js" }, "engines": { - "node": ">=0.11" + "node": ">=18" }, "funding": { - "type": "opencollective", - "url": "https://opencollective.com/date-fns" - } - }, - "node_modules/concurrently/node_modules/rxjs": { - "version": "6.6.7", - "dev": true, - "license": "Apache-2.0", - "dependencies": { - "tslib": "^1.9.0" - }, - "engines": { - "npm": ">=2.0.0" + "url": "https://github.com/open-cli-tools/concurrently?sponsor=1" } }, "node_modules/concurrently/node_modules/supports-color": { "version": "8.1.1", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-8.1.1.tgz", + "integrity": "sha512-MpUEN2OodtUzxvKQl72cUF7RQ5EiHsGvSsVG0ia9c5RbWGL2CI4C7EpPS8UTBIplnlzZiNuV56w+FuNxy3ty2Q==", "dev": true, "license": "MIT", "dependencies": { @@ -4661,11 +4562,6 @@ "url": "https://github.com/chalk/supports-color?sponsor=1" } }, - "node_modules/concurrently/node_modules/tslib": { - "version": "1.14.1", - "dev": true, - "license": "0BSD" - }, "node_modules/consola": { "version": "3.4.2", "resolved": "https://registry.npmjs.org/consola/-/consola-3.4.2.tgz", @@ -5070,6 +4966,8 @@ }, "node_modules/delayed-stream": { "version": "1.0.0", + "resolved": "https://registry.npmjs.org/delayed-stream/-/delayed-stream-1.0.0.tgz", + "integrity": "sha512-ZySD7Nf91aLB0RxL4KGrKHBXl7Eds1DAmEdcoVawXnLD7SDhpNgtuII2aAkg7a7QS41jxPSZ17p4VdGnMHk3MQ==", "dev": true, "license": "MIT", "engines": { @@ -5459,19 +5357,20 @@ } }, "node_modules/eslint": { - "version": "9.30.0", - "resolved": "https://registry.npmjs.org/eslint/-/eslint-9.30.0.tgz", - "integrity": "sha512-iN/SiPxmQu6EVkf+m1qpBxzUhE12YqFLOSySuOyVLJLEF9nzTf+h/1AJYc1JWzCnktggeNrjvQGLngDzXirU6g==", + "version": "9.37.0", + "resolved": "https://registry.npmjs.org/eslint/-/eslint-9.37.0.tgz", + "integrity": "sha512-XyLmROnACWqSxiGYArdef1fItQd47weqB7iwtfr9JHwRrqIXZdcFMvvEcL9xHCmL0SNsOvF0c42lWyM1U5dgig==", "dev": true, + "license": "MIT", "dependencies": { - "@eslint-community/eslint-utils": "^4.2.0", + "@eslint-community/eslint-utils": "^4.8.0", "@eslint-community/regexpp": "^4.12.1", "@eslint/config-array": "^0.21.0", - "@eslint/config-helpers": "^0.3.0", - "@eslint/core": "^0.14.0", + "@eslint/config-helpers": "^0.4.0", + "@eslint/core": "^0.16.0", "@eslint/eslintrc": "^3.3.1", - "@eslint/js": "9.30.0", - "@eslint/plugin-kit": "^0.3.1", + "@eslint/js": "9.37.0", + "@eslint/plugin-kit": "^0.4.0", "@humanfs/node": "^0.16.6", "@humanwhocodes/module-importer": "^1.0.1", "@humanwhocodes/retry": "^0.4.2", @@ -5519,7 +5418,9 @@ } }, "node_modules/eslint-config-prettier": { - "version": "10.1.5", + "version": "10.1.8", + "resolved": "https://registry.npmjs.org/eslint-config-prettier/-/eslint-config-prettier-10.1.8.tgz", + "integrity": "sha512-82GZUjRS0p/jganf6q1rEO25VSoHH0hKPCTrgillPjdI/3bgBhAE1QzHrHTizjpRvy6pGAvKjDJtk2pF9NDq8w==", "dev": true, "license": "MIT", "bin": { @@ -5776,10 +5677,11 @@ } }, "node_modules/eslint/node_modules/@eslint/js": { - "version": "9.30.0", - "resolved": "https://registry.npmjs.org/@eslint/js/-/js-9.30.0.tgz", - "integrity": "sha512-Wzw3wQwPvc9sHM+NjakWTcPx11mbZyiYHuwWa/QfZ7cIRX7WK54PSk7bdyXDaoaopUcMatv1zaQvOAAO8hCdww==", + "version": "9.37.0", + "resolved": "https://registry.npmjs.org/@eslint/js/-/js-9.37.0.tgz", + "integrity": "sha512-jaS+NJ+hximswBG6pjNX0uEJZkrT0zwpVi3BA3vX22aFGjJjmgSTSmPpZCRKmoBL5VY/M6p0xsSJx7rk7sy5gg==", "dev": true, + "license": "MIT", "engines": { "node": "^18.18.0 || ^20.9.0 || >=21.1.0" }, @@ -5919,30 +5821,6 @@ "version": "3.0.2", "license": "MIT" }, - "node_modules/external-editor": { - "version": "3.1.0", - "dev": true, - "license": "MIT", - "dependencies": { - "chardet": "^0.7.0", - "iconv-lite": "^0.4.24", - "tmp": "^0.0.33" - }, - "engines": { - "node": ">=4" - } - }, - "node_modules/external-editor/node_modules/iconv-lite": { - "version": "0.4.24", - "dev": true, - "license": "MIT", - "dependencies": { - "safer-buffer": ">= 2.1.2 < 3" - }, - "engines": { - "node": ">=0.10.0" - } - }, "node_modules/fast-deep-equal": { "version": "3.1.3", "license": "MIT" @@ -6053,6 +5931,8 @@ }, "node_modules/figures": { "version": "3.2.0", + "resolved": "https://registry.npmjs.org/figures/-/figures-3.2.0.tgz", + "integrity": "sha512-yaduQFRKLXYOGgEn6AZau90j3ggSOyiqXU0F9JZfeXYhNa+Jk4X+s45A2zg5jns87GAFa34BBm2kXw4XpNcbdg==", "dev": true, "license": "MIT", "dependencies": { @@ -6067,6 +5947,8 @@ }, "node_modules/figures/node_modules/escape-string-regexp": { "version": "1.0.5", + "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz", + "integrity": "sha512-vbRorB5FUQWvla16U8R/qgaFIya2qGzwDrNmCZuYKrbdSUMG6I1ZCGQRefkRVhuOkIGVne7BQ35DSfo1qvJqFg==", "dev": true, "license": "MIT", "engines": { @@ -6167,7 +6049,9 @@ "license": "ISC" }, "node_modules/follow-redirects": { - "version": "1.15.9", + "version": "1.15.11", + "resolved": "https://registry.npmjs.org/follow-redirects/-/follow-redirects-1.15.11.tgz", + "integrity": "sha512-deG2P0JfjrTxl50XGCDyfI97ZGVCxIpfKYmfyrQ54n5FO/0gfIES8C/Psl6kWVDolizcaaxZJnTS0QSMxvnsBQ==", "dev": true, "funding": [ { @@ -6231,25 +6115,6 @@ "node": ">= 6" } }, - "node_modules/form-data/node_modules/mime-db": { - "version": "1.52.0", - "dev": true, - "license": "MIT", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/form-data/node_modules/mime-types": { - "version": "2.1.35", - "dev": true, - "license": "MIT", - "dependencies": { - "mime-db": "1.52.0" - }, - "engines": { - "node": ">= 0.6" - } - }, "node_modules/format": { "version": "0.2.2", "engines": { @@ -6273,7 +6138,9 @@ } }, "node_modules/fs-extra": { - "version": "11.3.0", + "version": "11.3.1", + "resolved": "https://registry.npmjs.org/fs-extra/-/fs-extra-11.3.1.tgz", + "integrity": "sha512-eXvGGwZ5CL17ZSwHWd3bbgk7UUpF6IFHtP57NYYakPvHOs8GDgDe5KJI36jIJzDkJ6eJjuzRA8eBQb6SkKue0g==", "dev": true, "license": "MIT", "dependencies": { @@ -6986,6 +6853,8 @@ }, "node_modules/ieee754": { "version": "1.2.1", + "resolved": "https://registry.npmjs.org/ieee754/-/ieee754-1.2.1.tgz", + "integrity": "sha512-dcyqhDvX1C46lXZcVqCpK+FtMRQVdIMN6/Df5js2zouUsqG7I6sFxitIC+7KYK29KdXOLHdu9zL4sFnoVQnqaA==", "dev": true, "funding": [ { @@ -7044,6 +6913,8 @@ }, "node_modules/inherits": { "version": "2.0.4", + "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.4.tgz", + "integrity": "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==", "dev": true, "license": "ISC" }, @@ -7052,15 +6923,17 @@ "license": "MIT" }, "node_modules/inquirer": { - "version": "8.2.6", + "version": "8.2.7", + "resolved": "https://registry.npmjs.org/inquirer/-/inquirer-8.2.7.tgz", + "integrity": "sha512-UjOaSel/iddGZJ5xP/Eixh6dY1XghiBw4XK13rCCIJcJfyhhoul/7KhLLUGtebEj6GDYM6Vnx/mVsjx2L/mFIA==", "dev": true, "license": "MIT", "dependencies": { + "@inquirer/external-editor": "^1.0.0", "ansi-escapes": "^4.2.1", "chalk": "^4.1.1", "cli-cursor": "^3.1.0", "cli-width": "^3.0.0", - "external-editor": "^3.0.3", "figures": "^3.0.0", "lodash": "^4.17.21", "mute-stream": "0.0.8", @@ -7328,6 +7201,8 @@ }, "node_modules/is-interactive": { "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-interactive/-/is-interactive-1.0.0.tgz", + "integrity": "sha512-2HvIEKRoqS62guEC+qBjpvRubdX910WCMuJTZ+I9yvqKU2/12eSL549HMwtabb4oupdj2sMP50k+XJfB/8JE6w==", "dev": true, "license": "MIT", "engines": { @@ -7489,6 +7364,8 @@ }, "node_modules/is-unicode-supported": { "version": "0.1.0", + "resolved": "https://registry.npmjs.org/is-unicode-supported/-/is-unicode-supported-0.1.0.tgz", + "integrity": "sha512-knxG2q4UC3u8stRGyAVJCOdxFmv5DZiRcdlIaAQXAbSfJya+OhopNotLQrstBhququ4ZpuKbDc/8S6mgXgPFPw==", "dev": true, "license": "MIT", "engines": { @@ -7596,6 +7473,8 @@ }, "node_modules/iterare": { "version": "1.2.1", + "resolved": "https://registry.npmjs.org/iterare/-/iterare-1.2.1.tgz", + "integrity": "sha512-RKYVTCjAnRthyJes037NX/IiqeidgN1xc3j1RjFfECFp28A1GVwK9nA+i0rJPaHqSZwygLzRnFlzUuHFoWWy+Q==", "dev": true, "license": "ISC", "engines": { @@ -7775,7 +7654,9 @@ } }, "node_modules/jsonfile": { - "version": "6.1.0", + "version": "6.2.0", + "resolved": "https://registry.npmjs.org/jsonfile/-/jsonfile-6.2.0.tgz", + "integrity": "sha512-FGuPw30AdOIUTRMC2OMRtQV+jkVj2cfPqSeWXv1NEAJ1qZ5zb1X6z1mFhbfOB/iy3ssJCD+3KuZ8r8C3uVFlAg==", "dev": true, "license": "MIT", "dependencies": { @@ -8209,6 +8090,8 @@ }, "node_modules/log-symbols": { "version": "4.1.0", + "resolved": "https://registry.npmjs.org/log-symbols/-/log-symbols-4.1.0.tgz", + "integrity": "sha512-8XPvpAA8uyhfteu8pIvQxpJZ7SYYdpUivZpGy6sFsBuKRY/7rQGavedeB8aK+Zkyq6upMFVL/9AW6vOYzfRyLg==", "dev": true, "license": "MIT", "dependencies": { @@ -9170,8 +9053,33 @@ "node": ">=8.6" } }, + "node_modules/mime-db": { + "version": "1.52.0", + "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.52.0.tgz", + "integrity": "sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/mime-types": { + "version": "2.1.35", + "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.35.tgz", + "integrity": "sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw==", + "dev": true, + "license": "MIT", + "dependencies": { + "mime-db": "1.52.0" + }, + "engines": { + "node": ">= 0.6" + } + }, "node_modules/mimic-fn": { "version": "2.1.0", + "resolved": "https://registry.npmjs.org/mimic-fn/-/mimic-fn-2.1.0.tgz", + "integrity": "sha512-OqbOk5oEQeAZ8WXWydlu9HJjz9WVdEIvamMCcXmuqUYjTknH/sqsWvhQ3vgwKFRR1HpjvNBKQ37nbJgYzGqGcg==", "dev": true, "license": "MIT", "engines": { @@ -9325,21 +9233,6 @@ "url": "https://github.com/prettier/prettier?sponsor=1" } }, - "node_modules/msw/node_modules/cliui": { - "version": "8.0.1", - "resolved": "https://registry.npmjs.org/cliui/-/cliui-8.0.1.tgz", - "integrity": "sha512-BSeNnyus75C4//NQ9gQt1/csTXyo/8Sb+afLAkzAptFuMsod9HFokGNudZpi/oQV73hnVK+sR+5PVRMd+Dr7YQ==", - "dev": true, - "license": "ISC", - "dependencies": { - "string-width": "^4.2.0", - "strip-ansi": "^6.0.1", - "wrap-ansi": "^7.0.0" - }, - "engines": { - "node": ">=12" - } - }, "node_modules/msw/node_modules/path-to-regexp": { "version": "6.3.0", "resolved": "https://registry.npmjs.org/path-to-regexp/-/path-to-regexp-6.3.0.tgz", @@ -9347,55 +9240,10 @@ "dev": true, "license": "MIT" }, - "node_modules/msw/node_modules/wrap-ansi": { - "version": "7.0.0", - "resolved": "https://registry.npmjs.org/wrap-ansi/-/wrap-ansi-7.0.0.tgz", - "integrity": "sha512-YVGIj2kamLSTxw6NsZjoBxfSwsn0ycdesmc4p+Q21c5zPuZ1pl+NfxVdxPtdHvmNVOQ6XSYG4AUtyt/Fi7D16Q==", - "dev": true, - "license": "MIT", - "dependencies": { - "ansi-styles": "^4.0.0", - "string-width": "^4.1.0", - "strip-ansi": "^6.0.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/chalk/wrap-ansi?sponsor=1" - } - }, - "node_modules/msw/node_modules/yargs": { - "version": "17.7.2", - "resolved": "https://registry.npmjs.org/yargs/-/yargs-17.7.2.tgz", - "integrity": "sha512-7dSzzRQ++CKnNI/krKnYRV7JKKPUXMEh61soaHKg9mrWEhzFWhFnxPxGl+69cD1Ou63C13NUPCnmIcrvqCuM6w==", - "dev": true, - "license": "MIT", - "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" - }, - "engines": { - "node": ">=12" - } - }, - "node_modules/msw/node_modules/yargs-parser": { - "version": "21.1.1", - "resolved": "https://registry.npmjs.org/yargs-parser/-/yargs-parser-21.1.1.tgz", - "integrity": "sha512-tVpsJW7DdjecAiFpbIB1e3qxIQsE6NoPc5/eTdrbbIC4h0LVsWhnoa3g+m2HclBIujHzsxZ4VJVA+GUuc2/LBw==", - "dev": true, - "license": "ISC", - "engines": { - "node": ">=12" - } - }, "node_modules/mute-stream": { "version": "0.0.8", + "resolved": "https://registry.npmjs.org/mute-stream/-/mute-stream-0.0.8.tgz", + "integrity": "sha512-nnbWWOkoWyUsTjKrhgD0dcz22mdkSnpYqbEjIm2nhwhuxlSkpywJmBo8h0ZqJdkp73mb90SssHkN4rsRaBAfAA==", "dev": true, "license": "ISC" }, @@ -9542,35 +9390,6 @@ "url": "https://github.com/Mermade/oas-kit?sponsor=1" } }, - "node_modules/oas-resolver/node_modules/cliui": { - "version": "8.0.1", - "dev": true, - "license": "ISC", - "dependencies": { - "string-width": "^4.2.0", - "strip-ansi": "^6.0.1", - "wrap-ansi": "^7.0.0" - }, - "engines": { - "node": ">=12" - } - }, - "node_modules/oas-resolver/node_modules/wrap-ansi": { - "version": "7.0.0", - "dev": true, - "license": "MIT", - "dependencies": { - "ansi-styles": "^4.0.0", - "string-width": "^4.1.0", - "strip-ansi": "^6.0.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/chalk/wrap-ansi?sponsor=1" - } - }, "node_modules/oas-resolver/node_modules/yaml": { "version": "1.10.2", "dev": true, @@ -9579,31 +9398,6 @@ "node": ">= 6" } }, - "node_modules/oas-resolver/node_modules/yargs": { - "version": "17.7.2", - "dev": true, - "license": "MIT", - "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" - }, - "engines": { - "node": ">=12" - } - }, - "node_modules/oas-resolver/node_modules/yargs-parser": { - "version": "21.1.1", - "dev": true, - "license": "ISC", - "engines": { - "node": ">=12" - } - }, "node_modules/oas-schema-walker": { "version": "1.1.5", "dev": true, @@ -9746,6 +9540,8 @@ }, "node_modules/onetime": { "version": "5.1.2", + "resolved": "https://registry.npmjs.org/onetime/-/onetime-5.1.2.tgz", + "integrity": "sha512-kbpaSSGJTWdAY5KPVeMOKXSrPtr8C8C7wodJbcsd51jRnmD+GZu8Y0VoU6Dm5Z4vWr0Ig/1NKuWRKf7j5aaYSg==", "dev": true, "license": "MIT", "dependencies": { @@ -9782,6 +9578,8 @@ }, "node_modules/ora": { "version": "5.4.1", + "resolved": "https://registry.npmjs.org/ora/-/ora-5.4.1.tgz", + "integrity": "sha512-5b6Y85tPxZZ7QytO+BQzysW31HJku27cRIlkbAXaNx+BdcVi+LlRFmVXzeF6a7JCwJpyw5c4b+YSVImQIrBpuQ==", "dev": true, "license": "MIT", "dependencies": { @@ -9802,14 +9600,6 @@ "url": "https://github.com/sponsors/sindresorhus" } }, - "node_modules/os-tmpdir": { - "version": "1.0.2", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=0.10.0" - } - }, "node_modules/outvariant": { "version": "1.4.3", "dev": true, @@ -10858,6 +10648,8 @@ }, "node_modules/readable-stream": { "version": "3.6.2", + "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-3.6.2.tgz", + "integrity": "sha512-9u/sniCrY3D5WdsERHzHE4G2YCXqoG5FTHUiCC4SIbr6XcLZBY05ya9EKjYek9O5xOAwjGq+1JdGBAS7Q9ScoA==", "dev": true, "license": "MIT", "dependencies": { @@ -10915,6 +10707,8 @@ }, "node_modules/reflect-metadata": { "version": "0.2.2", + "resolved": "https://registry.npmjs.org/reflect-metadata/-/reflect-metadata-0.2.2.tgz", + "integrity": "sha512-urBwgfrvVP/eAyXx4hluJivBKzuEbSQs9rKWCrCkbSxNv8mxPcUZKeuoF3Uy4mJl3Lwprp6yy5/39VWigZ4K6Q==", "dev": true, "license": "Apache-2.0" }, @@ -11205,6 +10999,8 @@ }, "node_modules/restore-cursor": { "version": "3.1.0", + "resolved": "https://registry.npmjs.org/restore-cursor/-/restore-cursor-3.1.0.tgz", + "integrity": "sha512-l+sSefzHpj5qimhFSE5a8nufZYAM3sBSVMAPtYkmC+4EH2anSGaEMXSD0izRQbu9nfyQ9y5JrVmp7E8oZrUjvA==", "dev": true, "license": "MIT", "dependencies": { @@ -11217,6 +11013,8 @@ }, "node_modules/restore-cursor/node_modules/signal-exit": { "version": "3.0.7", + "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-3.0.7.tgz", + "integrity": "sha512-wnD2ZE+l+SPC/uoS0vXeE9L1+0wuaMqKlfz9AMUo38JsyLSBWSFcHR1Rri62LZc12vLr1gb3jl7iwQhgwpAbGQ==", "dev": true, "license": "ISC" }, @@ -11293,6 +11091,8 @@ }, "node_modules/run-async": { "version": "2.4.1", + "resolved": "https://registry.npmjs.org/run-async/-/run-async-2.4.1.tgz", + "integrity": "sha512-tvVnVv01b8c1RrA6Ep7JkStj85Guv/YrMcwqYQnwjsAS2cTmmPGBBjAjpCW7RrSodNSoE2/qg9O4bceNvUuDgQ==", "dev": true, "license": "MIT", "engines": { @@ -11348,6 +11148,8 @@ }, "node_modules/safe-buffer": { "version": "5.2.1", + "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.2.1.tgz", + "integrity": "sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ==", "dev": true, "funding": [ { @@ -11501,6 +11303,19 @@ "node": ">=8" } }, + "node_modules/shell-quote": { + "version": "1.8.3", + "resolved": "https://registry.npmjs.org/shell-quote/-/shell-quote-1.8.3.tgz", + "integrity": "sha512-ObmnIF4hXNg1BqhnHmgbDETF8dLPCggZWBjkQfhZpbszZnYur5DUljTcCHii5LC3J5E0yeO/1LIMyH+UvHQgyw==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, "node_modules/should": { "version": "13.2.3", "dev": true, @@ -11705,10 +11520,6 @@ "url": "https://github.com/sponsors/wooorm" } }, - "node_modules/spawn-command": { - "version": "0.0.2", - "dev": true - }, "node_modules/split-on-first": { "version": "3.0.0", "license": "MIT", @@ -11762,6 +11573,8 @@ }, "node_modules/string_decoder": { "version": "1.3.0", + "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.3.0.tgz", + "integrity": "sha512-hkRX8U1WjJFd8LsDJ2yQ/wWWxaopEsABU1XfkM8A+j0+85JAGppt16cr1Whg6KIbb4okU6Mql6BOj+uup/wKeA==", "dev": true, "license": "MIT", "dependencies": { @@ -11949,9 +11762,9 @@ } }, "node_modules/strtok3": { - "version": "10.3.1", - "resolved": "https://registry.npmjs.org/strtok3/-/strtok3-10.3.1.tgz", - "integrity": "sha512-3JWEZM6mfix/GCJBBUrkA8p2Id2pBkyTkVCJKto55w080QBKZ+8R171fGrbiSp+yMO/u6F8/yUh7K4V9K+YCnw==", + "version": "10.3.4", + "resolved": "https://registry.npmjs.org/strtok3/-/strtok3-10.3.4.tgz", + "integrity": "sha512-KIy5nylvC5le1OdaaoCJ07L+8iQzJHGH6pWDuzS+d07Cu7n1MZ2x26P8ZKIWfbK02+XIL8Mp4RkWeqdUCrDMfg==", "dev": true, "license": "MIT", "dependencies": { @@ -12042,35 +11855,6 @@ "url": "https://github.com/Mermade/oas-kit?sponsor=1" } }, - "node_modules/swagger2openapi/node_modules/cliui": { - "version": "8.0.1", - "dev": true, - "license": "ISC", - "dependencies": { - "string-width": "^4.2.0", - "strip-ansi": "^6.0.1", - "wrap-ansi": "^7.0.0" - }, - "engines": { - "node": ">=12" - } - }, - "node_modules/swagger2openapi/node_modules/wrap-ansi": { - "version": "7.0.0", - "dev": true, - "license": "MIT", - "dependencies": { - "ansi-styles": "^4.0.0", - "string-width": "^4.1.0", - "strip-ansi": "^6.0.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/chalk/wrap-ansi?sponsor=1" - } - }, "node_modules/swagger2openapi/node_modules/yaml": { "version": "1.10.2", "dev": true, @@ -12079,31 +11863,6 @@ "node": ">= 6" } }, - "node_modules/swagger2openapi/node_modules/yargs": { - "version": "17.7.2", - "dev": true, - "license": "MIT", - "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" - }, - "engines": { - "node": ">=12" - } - }, - "node_modules/swagger2openapi/node_modules/yargs-parser": { - "version": "21.1.1", - "dev": true, - "license": "ISC", - "engines": { - "node": ">=12" - } - }, "node_modules/swr": { "version": "2.3.3", "dev": true, @@ -12288,6 +12047,8 @@ }, "node_modules/through": { "version": "2.3.8", + "resolved": "https://registry.npmjs.org/through/-/through-2.3.8.tgz", + "integrity": "sha512-w89qg7PI8wAdvX60bMDP+bFoD5Dvhm9oLheFp5O4a2QF0cSBGsBX4qZmadPMvVqlLJBBci+WqGGOAPvcDeNSVg==", "dev": true, "license": "MIT" }, @@ -12391,17 +12152,6 @@ "dev": true, "license": "MIT" }, - "node_modules/tmp": { - "version": "0.0.33", - "dev": true, - "license": "MIT", - "dependencies": { - "os-tmpdir": "~1.0.2" - }, - "engines": { - "node": ">=0.6.0" - } - }, "node_modules/to-regex-range": { "version": "5.0.1", "dev": true, @@ -12414,12 +12164,13 @@ } }, "node_modules/token-types": { - "version": "6.0.0", - "resolved": "https://registry.npmjs.org/token-types/-/token-types-6.0.0.tgz", - "integrity": "sha512-lbDrTLVsHhOMljPscd0yitpozq7Ga2M5Cvez5AjGg8GASBjtt6iERCAJ93yommPmz62fb45oFIXHEZ3u9bfJEA==", + "version": "6.1.1", + "resolved": "https://registry.npmjs.org/token-types/-/token-types-6.1.1.tgz", + "integrity": "sha512-kh9LVIWH5CnL63Ipf0jhlBIy0UsrMj/NJDfpsy1SqOXlLKEVyXXYrnFxFT1yOOYVGBSApeVnjPw/sBz5BfEjAQ==", "dev": true, "license": "MIT", "dependencies": { + "@borewit/text-codec": "^0.1.0", "@tokenizer/token": "^0.3.0", "ieee754": "^1.2.1" }, @@ -12459,6 +12210,8 @@ }, "node_modules/tree-kill": { "version": "1.2.2", + "resolved": "https://registry.npmjs.org/tree-kill/-/tree-kill-1.2.2.tgz", + "integrity": "sha512-L0Orpi8qGpRG//Nd+H90vFB+3iHnue1zSSGmNOOCh1GLJ7rUKVwV2HvijphGQS2UmhUZewS9VgvxYIdgr+fG1A==", "dev": true, "license": "MIT", "bin": { @@ -12628,6 +12381,8 @@ }, "node_modules/uid": { "version": "2.0.2", + "resolved": "https://registry.npmjs.org/uid/-/uid-2.0.2.tgz", + "integrity": "sha512-u3xV3X7uzvi5b1MncmZo3i2Aw222Zk1keqLA1YkHldREkAhAqi65wuPfe7lHx8H/Wzy+8CE7S7uS3jekIM5s8g==", "dev": true, "license": "MIT", "dependencies": { @@ -12638,9 +12393,9 @@ } }, "node_modules/uint8array-extras": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/uint8array-extras/-/uint8array-extras-1.4.0.tgz", - "integrity": "sha512-ZPtzy0hu4cZjv3z5NW9gfKnNLjoz4y6uv4HlelAjDK7sY/xOkKZv9xK/WQpcsBB3jEybChz9DPC2U/+cusjJVQ==", + "version": "1.5.0", + "resolved": "https://registry.npmjs.org/uint8array-extras/-/uint8array-extras-1.5.0.tgz", + "integrity": "sha512-rvKSBiC5zqCCiDZ9kAOszZcDvdAHwwIKJG33Ykj43OKcWsnmcBRL09YTU4nOeHZ8Y2a7l1MgTd08SBe9A8Qj6A==", "dev": true, "license": "MIT", "engines": { @@ -12793,6 +12548,8 @@ }, "node_modules/universalify": { "version": "2.0.1", + "resolved": "https://registry.npmjs.org/universalify/-/universalify-2.0.1.tgz", + "integrity": "sha512-gptHNQghINnc/vTGIk0SOFGFNXw7JVrlRUtConJRlvaw6DuX0wO5Jeko9sWrMBhh+PsYAZ7oXAiOnf/UKogyiw==", "dev": true, "license": "MIT", "engines": { @@ -12995,7 +12752,9 @@ } }, "node_modules/vite": { - "version": "6.3.5", + "version": "6.3.6", + "resolved": "https://registry.npmjs.org/vite/-/vite-6.3.6.tgz", + "integrity": "sha512-0msEVHJEScQbhkbVTb/4iHZdJ6SXp/AvxL2sjwYQFfBqleHtnCqv1J3sa9zbWz/6kW1m9Tfzn92vW+kZ1WV6QA==", "license": "MIT", "dependencies": { "esbuild": "^0.25.0", @@ -13493,28 +13252,32 @@ "license": "ISC" }, "node_modules/yargs": { - "version": "16.2.0", + "version": "17.7.2", + "resolved": "https://registry.npmjs.org/yargs/-/yargs-17.7.2.tgz", + "integrity": "sha512-7dSzzRQ++CKnNI/krKnYRV7JKKPUXMEh61soaHKg9mrWEhzFWhFnxPxGl+69cD1Ou63C13NUPCnmIcrvqCuM6w==", "dev": true, "license": "MIT", "dependencies": { - "cliui": "^7.0.2", + "cliui": "^8.0.1", "escalade": "^3.1.1", "get-caller-file": "^2.0.5", "require-directory": "^2.1.1", - "string-width": "^4.2.0", + "string-width": "^4.2.3", "y18n": "^5.0.5", - "yargs-parser": "^20.2.2" + "yargs-parser": "^21.1.1" }, "engines": { - "node": ">=10" + "node": ">=12" } }, "node_modules/yargs-parser": { - "version": "20.2.9", + "version": "21.1.1", + "resolved": "https://registry.npmjs.org/yargs-parser/-/yargs-parser-21.1.1.tgz", + "integrity": "sha512-tVpsJW7DdjecAiFpbIB1e3qxIQsE6NoPc5/eTdrbbIC4h0LVsWhnoa3g+m2HclBIujHzsxZ4VJVA+GUuc2/LBw==", "dev": true, "license": "ISC", "engines": { - "node": ">=10" + "node": ">=12" } }, "node_modules/yocto-queue": { diff --git a/frontend/package.json b/frontend/package.json index aab2deede..fd27b2ae3 100644 --- a/frontend/package.json +++ b/frontend/package.json @@ -67,7 +67,7 @@ "@eslint/eslintrc": "3.3.1", "@eslint/js": "9.30.1", "@faker-js/faker": "9.8.0", - "@openapitools/openapi-generator-cli": "2.21.0", + "@openapitools/openapi-generator-cli": "2.23.1", "@tailwindcss/typography": "0.5.16", "@testing-library/dom": "10.4.0", "@testing-library/jest-dom": "6.6.3", @@ -78,13 +78,13 @@ "@types/react-dom": "18.3.7", "@types/react-speech-recognition": "^3.9.6", "@types/react-syntax-highlighter": "15.5.13", - "@typescript-eslint/eslint-plugin": "8.33.1", - "@typescript-eslint/parser": "8.35.0", + "@typescript-eslint/eslint-plugin": "8.46.0", + "@typescript-eslint/parser": "8.46.0", "@vitejs/plugin-react": "4.5.1", "@vitest/coverage-v8": "3.2.1", "daisyui": "5.0.43", - "eslint": "9.30.0", - "eslint-config-prettier": "10.1.5", + "eslint": "9.37.0", + "eslint-config-prettier": "10.1.8", "eslint-plugin-import": "2.32.0", "eslint-plugin-prettier": "5.4.1", "eslint-plugin-react": "7.37.5", @@ -105,7 +105,7 @@ "rimraf": "6.0.1", "tailwindcss": "4.1.8", "typescript": "5.8.3", - "vite": "6.3.5", + "vite": "6.3.6", "vitest": "3.2.1" } } diff --git a/frontend/src/api/generated/.openapi-generator/FILES b/frontend/src/api/generated/.openapi-generator/FILES index 0c23634a7..1319cd805 100644 --- a/frontend/src/api/generated/.openapi-generator/FILES +++ b/frontend/src/api/generated/.openapi-generator/FILES @@ -68,6 +68,8 @@ models/StreamEventHolderDto.ts models/StreamLoggingEvent.ts models/StreamMessageSavedDto.ts models/StreamMetadataDto.ts +models/StreamReasoningDto.ts +models/StreamReasoningEndDto.ts models/StreamSourcesEvent.ts models/StreamSummaryDto.ts models/StreamTokenEventDto.ts diff --git a/frontend/src/api/generated/apis/FilesApi.ts b/frontend/src/api/generated/apis/FilesApi.ts index 2c679d54f..6e995a3c7 100644 --- a/frontend/src/api/generated/apis/FilesApi.ts +++ b/frontend/src/api/generated/apis/FilesApi.ts @@ -52,6 +52,7 @@ export interface DeleteFileRequest { export interface DeleteUserFileRequest { fileId: number; + conversationId?: number; } export interface GetBucketRequest { @@ -201,6 +202,10 @@ export class FilesApi extends runtime.BaseAPI { const queryParameters: any = {}; + if (requestParameters['conversationId'] != null) { + queryParameters['conversationId'] = requestParameters['conversationId']; + } + const headerParameters: runtime.HTTPHeaders = {}; const response = await this.request({ @@ -217,8 +222,8 @@ export class FilesApi extends runtime.BaseAPI { * Deletes a file. * */ - async deleteUserFile(fileId: number, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise { - await this.deleteUserFileRaw({ fileId: fileId }, initOverrides); + async deleteUserFile(fileId: number, conversationId?: number, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise { + await this.deleteUserFileRaw({ fileId: fileId, conversationId: conversationId }, initOverrides); } /** diff --git a/frontend/src/api/generated/models/DocumentDto.ts b/frontend/src/api/generated/models/DocumentDto.ts index df4e9e376..6e966a4f6 100644 --- a/frontend/src/api/generated/models/DocumentDto.ts +++ b/frontend/src/api/generated/models/DocumentDto.ts @@ -51,7 +51,7 @@ export interface DocumentDto { */ link?: string; /** - * Can the document be downloaded via the `getDocument` endpoint. + * Can the document be downloaded in pdf format via the `getDocument` endpoint. * @type {boolean} * @memberof DocumentDto */ diff --git a/frontend/src/api/generated/models/StreamEventDto.ts b/frontend/src/api/generated/models/StreamEventDto.ts index 539bc3aa1..773cd4187 100644 --- a/frontend/src/api/generated/models/StreamEventDto.ts +++ b/frontend/src/api/generated/models/StreamEventDto.ts @@ -48,6 +48,20 @@ import { StreamMessageSavedDtoFromJSONTyped, StreamMessageSavedDtoToJSON, } from './StreamMessageSavedDto'; +import type { StreamReasoningDto } from './StreamReasoningDto'; +import { + instanceOfStreamReasoningDto, + StreamReasoningDtoFromJSON, + StreamReasoningDtoFromJSONTyped, + StreamReasoningDtoToJSON, +} from './StreamReasoningDto'; +import type { StreamReasoningEndDto } from './StreamReasoningEndDto'; +import { + instanceOfStreamReasoningEndDto, + StreamReasoningEndDtoFromJSON, + StreamReasoningEndDtoFromJSONTyped, + StreamReasoningEndDtoToJSON, +} from './StreamReasoningEndDto'; import type { StreamSourcesEvent } from './StreamSourcesEvent'; import { instanceOfStreamSourcesEvent, @@ -96,7 +110,7 @@ import { * * @export */ -export type StreamEventDto = { type: 'chunk' } & StreamTokenEventDto | { type: 'completed' } & StreamCompletedEventDto | { type: 'debug' } & StreamDebugEvent | { type: 'error' } & StreamErrorEventDto | { type: 'logging' } & StreamLoggingEvent | { type: 'saved' } & StreamMessageSavedDto | { type: 'sources' } & StreamSourcesEvent | { type: 'summary' } & StreamSummaryDto | { type: 'tool_end' } & StreamToolEndEventDto | { type: 'tool_start' } & StreamToolStartEventDto | { type: 'ui' } & StreamUIEventDto; +export type StreamEventDto = { type: 'chunk' } & StreamTokenEventDto | { type: 'completed' } & StreamCompletedEventDto | { type: 'debug' } & StreamDebugEvent | { type: 'error' } & StreamErrorEventDto | { type: 'logging' } & StreamLoggingEvent | { type: 'reasoning' } & StreamReasoningDto | { type: 'reasoning_end' } & StreamReasoningEndDto | { type: 'saved' } & StreamMessageSavedDto | { type: 'sources' } & StreamSourcesEvent | { type: 'summary' } & StreamSummaryDto | { type: 'tool_end' } & StreamToolEndEventDto | { type: 'tool_start' } & StreamToolStartEventDto | { type: 'ui' } & StreamUIEventDto; export function StreamEventDtoFromJSON(json: any): StreamEventDto { return StreamEventDtoFromJSONTyped(json, false); @@ -117,6 +131,10 @@ export function StreamEventDtoFromJSONTyped(json: any, ignoreDiscriminator: bool return Object.assign({}, StreamErrorEventDtoFromJSONTyped(json, true), { type: 'error' } as const); case 'logging': return Object.assign({}, StreamLoggingEventFromJSONTyped(json, true), { type: 'logging' } as const); + case 'reasoning': + return Object.assign({}, StreamReasoningDtoFromJSONTyped(json, true), { type: 'reasoning' } as const); + case 'reasoning_end': + return Object.assign({}, StreamReasoningEndDtoFromJSONTyped(json, true), { type: 'reasoning_end' } as const); case 'saved': return Object.assign({}, StreamMessageSavedDtoFromJSONTyped(json, true), { type: 'saved' } as const); case 'sources': @@ -149,6 +167,10 @@ export function StreamEventDtoToJSON(value?: StreamEventDto | null): any { return StreamErrorEventDtoToJSON(value); case 'logging': return StreamLoggingEventToJSON(value); + case 'reasoning': + return StreamReasoningDtoToJSON(value); + case 'reasoning_end': + return StreamReasoningEndDtoToJSON(value); case 'saved': return StreamMessageSavedDtoToJSON(value); case 'sources': diff --git a/frontend/src/api/generated/models/StreamReasoningDto.ts b/frontend/src/api/generated/models/StreamReasoningDto.ts new file mode 100644 index 000000000..277416b6e --- /dev/null +++ b/frontend/src/api/generated/models/StreamReasoningDto.ts @@ -0,0 +1,81 @@ +//@ts-nocheck +/* tslint:disable */ +/* eslint-disable */ +/** + * c4 GenAI Suite + * c4 GenAI Suite + * + * The version of the OpenAPI document: 1.0 + * + * + * NOTE: This class is auto generated by OpenAPI Generator (https://openapi-generator.tech). + * https://openapi-generator.tech + * Do not edit the class manually. + */ + +import { mapValues } from '../runtime'; +/** + * + * @export + * @interface StreamReasoningDto + */ +export interface StreamReasoningDto { + /** + * The content . + * @type {string} + * @memberof StreamReasoningDto + */ + content: string; + /** + * + * @type {string} + * @memberof StreamReasoningDto + */ + type: StreamReasoningDtoTypeEnum; +} + + +/** + * @export + */ +export const StreamReasoningDtoTypeEnum = { + Reasoning: 'reasoning' +} as const; +export type StreamReasoningDtoTypeEnum = typeof StreamReasoningDtoTypeEnum[keyof typeof StreamReasoningDtoTypeEnum]; + + +/** + * Check if a given object implements the StreamReasoningDto interface. + */ +export function instanceOfStreamReasoningDto(value: object): value is StreamReasoningDto { + if (!('content' in value) || value['content'] === undefined) return false; + if (!('type' in value) || value['type'] === undefined) return false; + return true; +} + +export function StreamReasoningDtoFromJSON(json: any): StreamReasoningDto { + return StreamReasoningDtoFromJSONTyped(json, false); +} + +export function StreamReasoningDtoFromJSONTyped(json: any, ignoreDiscriminator: boolean): StreamReasoningDto { + if (json == null) { + return json; + } + return { + + 'content': json['content'], + 'type': json['type'], + }; +} + +export function StreamReasoningDtoToJSON(value?: StreamReasoningDto | null): any { + if (value == null) { + return value; + } + return { + + 'content': value['content'], + 'type': value['type'], + }; +} + diff --git a/frontend/src/api/generated/models/StreamReasoningEndDto.ts b/frontend/src/api/generated/models/StreamReasoningEndDto.ts new file mode 100644 index 000000000..c33c8ead7 --- /dev/null +++ b/frontend/src/api/generated/models/StreamReasoningEndDto.ts @@ -0,0 +1,72 @@ +//@ts-nocheck +/* tslint:disable */ +/* eslint-disable */ +/** + * c4 GenAI Suite + * c4 GenAI Suite + * + * The version of the OpenAPI document: 1.0 + * + * + * NOTE: This class is auto generated by OpenAPI Generator (https://openapi-generator.tech). + * https://openapi-generator.tech + * Do not edit the class manually. + */ + +import { mapValues } from '../runtime'; +/** + * + * @export + * @interface StreamReasoningEndDto + */ +export interface StreamReasoningEndDto { + /** + * + * @type {string} + * @memberof StreamReasoningEndDto + */ + type: StreamReasoningEndDtoTypeEnum; +} + + +/** + * @export + */ +export const StreamReasoningEndDtoTypeEnum = { + ReasoningEnd: 'reasoning_end' +} as const; +export type StreamReasoningEndDtoTypeEnum = typeof StreamReasoningEndDtoTypeEnum[keyof typeof StreamReasoningEndDtoTypeEnum]; + + +/** + * Check if a given object implements the StreamReasoningEndDto interface. + */ +export function instanceOfStreamReasoningEndDto(value: object): value is StreamReasoningEndDto { + if (!('type' in value) || value['type'] === undefined) return false; + return true; +} + +export function StreamReasoningEndDtoFromJSON(json: any): StreamReasoningEndDto { + return StreamReasoningEndDtoFromJSONTyped(json, false); +} + +export function StreamReasoningEndDtoFromJSONTyped(json: any, ignoreDiscriminator: boolean): StreamReasoningEndDto { + if (json == null) { + return json; + } + return { + + 'type': json['type'], + }; +} + +export function StreamReasoningEndDtoToJSON(value?: StreamReasoningEndDto | null): any { + if (value == null) { + return value; + } + return { + + 'type': value['type'], + }; +} + diff --git a/frontend/src/api/generated/models/index.ts b/frontend/src/api/generated/models/index.ts index 64ca7a50b..f969ab003 100644 --- a/frontend/src/api/generated/models/index.ts +++ b/frontend/src/api/generated/models/index.ts @@ -61,6 +61,8 @@ export * from './StreamEventHolderDto'; export * from './StreamLoggingEvent'; export * from './StreamMessageSavedDto'; export * from './StreamMetadataDto'; +export * from './StreamReasoningDto'; +export * from './StreamReasoningEndDto'; export * from './StreamSourcesEvent'; export * from './StreamSummaryDto'; export * from './StreamTokenEventDto'; diff --git a/frontend/src/components/Pagination.tsx b/frontend/src/components/Pagination.tsx index 936adb584..24450c700 100644 --- a/frontend/src/components/Pagination.tsx +++ b/frontend/src/components/Pagination.tsx @@ -14,7 +14,7 @@ interface PaginationProps { onPage: (page: number) => void; } -export function Pagingation(props: PaginationProps) { +export function Pagination(props: PaginationProps) { const { onPage, page, pageSize, total } = props; const numberOfPages = Math.ceil(total / pageSize); diff --git a/frontend/src/components/PdfViewer.tsx b/frontend/src/components/PdfViewer.tsx index 2e6df1550..ccbcb5cf0 100644 --- a/frontend/src/components/PdfViewer.tsx +++ b/frontend/src/components/PdfViewer.tsx @@ -1,6 +1,6 @@ /* eslint-disable @typescript-eslint/no-non-null-asserted-optional-chain */ -import { ActionIcon, Button, Card, Group, Loader } from '@mantine/core'; +import { ActionIcon, Card, Group, Loader } from '@mantine/core'; import { IconX } from '@tabler/icons-react'; import { ReactNode, useCallback, useEffect, useState } from 'react'; import { useTranslation } from 'react-i18next'; @@ -9,6 +9,7 @@ import { Document, Page, pdfjs } from 'react-pdf'; import { toast } from 'react-toastify'; import { SourceDto } from 'src/api/generated/models/SourceDto'; import { useDocument } from 'src/hooks/api/files'; +import { isString } from 'src/lib'; import { DocumentSource } from 'src/pages/chat/SourcesChunkPreview'; import { Alert } from './Alert'; import PdfControlBar from './PdfControlBar'; @@ -25,7 +26,22 @@ const VIEWPORT_STYLING_RULES = { minWidth: '25%', }; -export function PdfViewer({ selectedDocument, selectedSource: _selectedSource, onClose }: PdfViewerProps) { +function getFirstPageFromSource(source: SourceDto | undefined): number { + if (source && source.metadata) { + const metadata = source.metadata; + if (isString(metadata.pages)) { + // pages is a string like "1-2, 4" + const pages = metadata.pages.split(',').flatMap((pageRange: string) => pageRange.split('-').map((p) => parseInt(p, 10))); + if (pages.length > 0) { + const firstPage = pages[0]; + return firstPage; + } + } + } + return 1; +} + +export function PdfViewer({ selectedDocument, selectedSource, onClose }: PdfViewerProps) { const { t } = useTranslation(); const [pdfFileUrl, setPdfFileUrl] = useState(null); @@ -35,7 +51,7 @@ export function PdfViewer({ selectedDocument, selectedSource: _selectedSource, o const [pageNumber, setPageNumber] = useState(1); const [displayPdfViewer, setDisplayPdfViewer] = useState(true); - const { data, isFetched, isError, isPending, refetch } = useDocument( + const { data, isFetched, isError, isPending } = useDocument( // This is the reason to disable @typescript-eslint/no-non-null-asserted-optional-chain selectedDocument?.conversationId!, selectedDocument?.messageId!, @@ -49,6 +65,7 @@ export function PdfViewer({ selectedDocument, selectedSource: _selectedSource, o if (documentData.type && documentData.type === 'application/pdf') { const documentUrl = URL.createObjectURL(documentData); setPdfFileUrl(documentUrl); + setPageNumber(getFirstPageFromSource(selectedSource)); } else { toast('Something went wrong while loading the PDF source document. Please try again.'); } @@ -56,7 +73,7 @@ export function PdfViewer({ selectedDocument, selectedSource: _selectedSource, o console.error(error); } } - }, [data, isFetched, isError]); + }, [data, isFetched, isError, selectedSource]); function onDocumentLoadSuccess({ numPages }: { numPages: number }) { setNumPages(numPages); @@ -80,13 +97,7 @@ export function PdfViewer({ selectedDocument, selectedSource: _selectedSource, o ); if (isError) { - return container( - - - , - ); + return container(); } if (isPending) { diff --git a/frontend/src/hooks/api/files.ts b/frontend/src/hooks/api/files.ts index 48e0f56cc..cbdfdbf45 100644 --- a/frontend/src/hooks/api/files.ts +++ b/frontend/src/hooks/api/files.ts @@ -1,6 +1,9 @@ -import { useQuery } from '@tanstack/react-query'; -import { useApi } from 'src/api'; -import { useUserFilesStore, VirtualFile } from 'src/pages/chat/state/zustand/userFilesStore'; +import { useMutation, useQuery } from '@tanstack/react-query'; +import { toast } from 'react-toastify'; +import { FileDto, useApi } from 'src/api'; +import { buildError } from 'src/lib'; +import { useUserFilesStore } from 'src/pages/chat/state/zustand/userFilesStore'; +import { texts } from 'src/texts'; export const useDocumentContent = (conversationId: number, messageId: number, documentUri: string) => { const { conversations } = useApi(); @@ -31,9 +34,35 @@ export const useConversationFiles = (conversationId: number) => { select: (data) => data.items, }); + const deleteFile = useMutation({ + mutationFn: async (file: FileDto) => { + return api.files.deleteUserFile(file.id, conversationId); + }, + onSuccess: (_, file) => { + userFilesFunctions.remove(file); + }, + onError: async (error) => { + toast.error(await buildError(texts.files.removeFileFailed, error)); + }, + onSettled: () => refetch(), + }); + + const conversationAndUserFiles = [ + ...userFiles.filter((x) => !conversationFiles?.find((y) => y.id === x.id)), + ...(conversationFiles || []), + ]; + return { - data: [...userFiles, ...(conversationFiles || [])] as VirtualFile[], + data: conversationAndUserFiles, ...userFilesFunctions, + remove: (file: FileDto) => deleteFile.mutate(file), + toggle: (file: FileDto) => { + if (conversationAndUserFiles.find((x) => x.id === file.id)) { + deleteFile.mutate(file); + } else { + userFilesFunctions.add(file); + } + }, refetch, }; }; diff --git a/frontend/src/pages/admin/users/UsersPage.tsx b/frontend/src/pages/admin/users/UsersPage.tsx index 7a59156c9..a81e8a917 100644 --- a/frontend/src/pages/admin/users/UsersPage.tsx +++ b/frontend/src/pages/admin/users/UsersPage.tsx @@ -3,7 +3,7 @@ import { IconPlus } from '@tabler/icons-react'; import { useQuery } from '@tanstack/react-query'; import { useEffect, useState } from 'react'; import { useApi, UserDto, UserGroupDto } from 'src/api'; -import { Page, Pagingation, Search } from 'src/components'; +import { Page, Pagination, Search } from 'src/components'; import { useEventCallback } from 'src/hooks'; import { formatBoolean } from 'src/lib'; import { texts } from 'src/texts'; @@ -62,8 +62,8 @@ export function UsersPage() {
-
@@ -99,7 +99,7 @@ export function UsersPage() { - + diff --git a/frontend/src/pages/chat/ChatPage.tsx b/frontend/src/pages/chat/ChatPage.tsx index 257910252..44f8ac82e 100644 --- a/frontend/src/pages/chat/ChatPage.tsx +++ b/frontend/src/pages/chat/ChatPage.tsx @@ -9,7 +9,7 @@ import { NavigationBar } from 'src/components/NavigationBar'; import { PdfViewer } from 'src/components/PdfViewer'; import { useSidebarState, useTheme } from 'src/hooks'; import { useConversationFiles } from 'src/hooks/api/files'; -import { useListOfAssistantsInit } from 'src/pages/chat/state/listOfAssistants'; +import { useListOfAllAssistantsInit, useListOfEnabledAssistantsInit } from 'src/pages/chat/state/listOfAssistants'; import { texts } from 'src/texts'; import { isMobile } from '../utils'; import { ConversationItems } from './ConversationItems'; @@ -62,13 +62,13 @@ export function ChatPage() { const { theme } = useTheme(); const isMobileView = isMobile(); - useListOfAssistantsInit(); + useListOfEnabledAssistantsInit(); + useListOfAllAssistantsInit(); useListOfChatsInit(); const { selectedDocument, setSelectedDocument } = useStateOfSelectedDocument(); const { selectedSource, setSelectedSource } = useStateOfSelectedSource(); - const isSourcePdfFile = selectedSource?.document?.mimeType === 'application/pdf'; const isSourceAvailable = selectedSource?.document?.downloadAvailable ?? false; const selectedAssistantId = useStateOfSelectedAssistantId(); @@ -193,7 +193,7 @@ export function ChatPage() { {texts.chat.sources.content} - @@ -201,7 +201,7 @@ export function ChatPage() { setSelectedDocument(undefined)} document={selectedDocument} /> - {isSourcePdfFile && isSourceAvailable && ( + {isSourceAvailable && ( { if (!hasRun.current && assistants.length) { hasRun.current = true; - createNewConversation.mutate(assistantId); + createNewConversation.mutate(assistant.id); } // eslint-disable-next-line react-hooks/exhaustive-deps - }, [assistantId, createNewConversation]); + }, [assistant, createNewConversation]); return null; } diff --git a/frontend/src/pages/chat/conversation/ChatInput.tsx b/frontend/src/pages/chat/conversation/ChatInput.tsx index 737793e09..f68fa9b76 100644 --- a/frontend/src/pages/chat/conversation/ChatInput.tsx +++ b/frontend/src/pages/chat/conversation/ChatInput.tsx @@ -1,18 +1,14 @@ import { ActionIcon, Button, Portal } from '@mantine/core'; import { IconFilter, IconPaperclip } from '@tabler/icons-react'; -import { useMutation } from '@tanstack/react-query'; import React, { ChangeEvent, useCallback, useEffect, useRef, useState } from 'react'; import TextareaAutosize from 'react-textarea-autosize'; -import { toast } from 'react-toastify'; -import { ConfigurationDto, FileDto, useApi } from 'src/api'; +import { ConfigurationDto, FileDto } from 'src/api'; import { Icon, Markdown } from 'src/components'; import { ExtensionContext, JSONObject, useEventCallback, useExtensionContext, usePersistentState, useTheme } from 'src/hooks'; import { useSpeechRecognitionToggle } from 'src/hooks/useSpeechRecognitionToggle'; -import { buildError } from 'src/lib'; -import { FileItem } from 'src/pages/chat/conversation/FileItem'; +import { FileItemComponent } from 'src/pages/chat/conversation/FileItem'; import { FilterModal } from 'src/pages/chat/conversation/FilterModal'; import { Language, SpeechRecognitionButton } from 'src/pages/chat/conversation/SpeechRecognitionButton'; -import { VirtualFile } from 'src/pages/chat/state/zustand/userFilesStore'; import { texts } from 'src/texts'; import { useChatDropzone } from '../useChatDropzone'; import { Suggestions } from './Suggestions'; @@ -33,7 +29,6 @@ interface ChatInputProps { submitMessage: (input: string, files?: FileDto[]) => void; } export function ChatInput({ textareaRef, chatId, configuration, isDisabled, isEmpty, submitMessage }: ChatInputProps) { - const api = useApi(); const extensionsWithFilter = configuration?.extensions?.filter(isExtensionWithUserArgs) ?? []; const { updateContext, context } = useExtensionContext(chatId); const [defaultValues, setDefaultValues] = useState({}); @@ -49,7 +44,7 @@ export function ChatInput({ textareaRef, chatId, configuration, isDisabled, isEm uploadMutations, upload, userBucket, - removeLocalFile, + remove, } = useChatDropzone(); const speechRecognitionLanguages: Language[] = [ @@ -128,18 +123,6 @@ export function ChatInput({ textareaRef, chatId, configuration, isDisabled, isEm setShowFilter(false); }; - const deleteFile = useMutation({ - mutationFn: async (file: VirtualFile) => { - return api.files.deleteUserFile(file.id); - }, - onSuccess: (_) => { - toast.success(texts.files.deleted); - }, - onError: async (error) => { - toast.error(await buildError(texts.files.removeFileFailed, error)); - }, - onSettled: () => refetchConversationFiles(), - }); const handleUploadFileFromInput = (event: ChangeEvent) => { const files = event.target.files ? Array.from(event.target.files) : []; handleUploadFile(files); @@ -204,10 +187,10 @@ export function ChatInput({ textareaRef, chatId, configuration, isDisabled, isEm
{chatFiles.map((file) => ( - (file.local ? removeLocalFile(file) : deleteFile.mutate(file))} /> + ))} {uploadingFiles.map((file) => ( - + ))}
diff --git a/frontend/src/pages/chat/conversation/ChatItem/AIChatItem.tsx b/frontend/src/pages/chat/conversation/ChatItem/AIChatItem.tsx index 7befd6a78..aad22f0ff 100644 --- a/frontend/src/pages/chat/conversation/ChatItem/AIChatItem.tsx +++ b/frontend/src/pages/chat/conversation/ChatItem/AIChatItem.tsx @@ -3,13 +3,14 @@ import { useClipboard, useDebouncedValue } from '@mantine/hooks'; import { toast } from 'react-toastify'; import { Alert, Markdown } from 'src/components'; import { useProfile } from 'src/hooks'; -import { useStateOfAssistants } from 'src/pages/chat/state/listOfAssistants'; +import { useStateOfAllAssistants, useStateOfEnabledAssistants } from 'src/pages/chat/state/listOfAssistants'; import { texts } from 'src/texts'; import { useStateOfIsAiWriting } from '../../state/chat'; import { ChatItemDebug } from '../ChatItemDebug'; import { ChatItemLogging } from '../ChatItemLogging'; import ChatItemSources from '../ChatItemSources'; import { ChatItemTools } from '../ChatItemTools'; +import { ReasoningLoadingIndicator } from '../ReasoningLoadingIndicator'; import { AIChatItemActions } from './AIChatItemActions'; import { AiAvatar } from './AiAvatar'; import { ChatItemProps } from './ChatItem'; @@ -23,7 +24,8 @@ export const AIChatItem = ({ agentName, message, isLast, selectDocument }: ChatI const user = useProfile(); const isWriting = useStateOfIsAiWriting(); const clipboard = useClipboard(); - const assistants = useStateOfAssistants(); + const assistants = useStateOfAllAssistants(); + const assistantsWithExtensions = useStateOfEnabledAssistants(); const copyTextToClipboard = () => { clipboard.copy(textContent); @@ -31,10 +33,12 @@ export const AIChatItem = ({ agentName, message, isLast, selectDocument }: ChatI }; const messageAssistant = assistants.find((x) => x.id === message.configurationId); - const assistantLLmLogo = messageAssistant?.extensions?.find((x) => x.type === 'llm')?.logo; + const messageAssistantWithExtensions = assistantsWithExtensions.find((x) => x.id === message.configurationId); + const assistantLLmLogo = messageAssistantWithExtensions?.extensions?.find((x) => x.type === 'llm')?.logo; const [debouncedIsWriting] = useDebouncedValue(isWriting, 500); const newReply = isWriting || debouncedIsWriting; + const assistantStatus = !messageAssistant ? ' [assistant deleted]' : !messageAssistant.enabled ? ' [disabled]' : ''; return (
@@ -46,10 +50,14 @@ export const AIChatItem = ({ agentName, message, isLast, selectDocument }: ChatI |{messageAssistant.name} )} + {assistantStatus && {assistantStatus}}
{message.error && } {message.ui && } + {message.reasoning?.length && ( + + )} {textContent} diff --git a/frontend/src/pages/chat/conversation/Configuration.tsx b/frontend/src/pages/chat/conversation/Configuration.tsx index 4bdca60dd..773524b66 100644 --- a/frontend/src/pages/chat/conversation/Configuration.tsx +++ b/frontend/src/pages/chat/conversation/Configuration.tsx @@ -1,8 +1,9 @@ import { ActionIcon, Select, SelectProps, Text } from '@mantine/core'; -import { IconSettings } from '@tabler/icons-react'; +import { IconChevronDown, IconSettings } from '@tabler/icons-react'; import { useState } from 'react'; +import { usePersistentState } from 'src/hooks'; import { ConfigurationUserValuesModal } from 'src/pages/chat/conversation/ConfigurationUserValuesModal'; -import { useStateOfAssistants, useStateOfSelectedAssistant } from 'src/pages/chat/state/listOfAssistants'; +import { useStateOfEnabledAssistants, useStateOfSelectedAssistant } from 'src/pages/chat/state/listOfAssistants'; import { isMobile } from 'src/pages/utils'; import { useStateMutateChat, useStateOfChat } from '../state/chat'; @@ -13,14 +14,16 @@ interface ConfigurationProps { export const Configuration = ({ canEditConfiguration }: ConfigurationProps) => { const chat = useStateOfChat(); const updateChat = useStateMutateChat(chat.id); - const assistants = useStateOfAssistants(); + const assistants = useStateOfEnabledAssistants(); const assistant = useStateOfSelectedAssistant(); const [showModal, setShowModal] = useState(false); + const [, setPersistentAssistantId] = usePersistentState('selectedAssistantId', null); + const renderSelectOption: SelectProps['renderOption'] = ({ option }) => (
- {option.label} + {option.label} {assistants.find((c) => c.id + '' === option.value)?.description} @@ -29,20 +32,36 @@ export const Configuration = ({ canEditConfiguration }: ConfigurationProps) => { const close = () => setShowModal(false); + const handleOnChange = (value: string | null) => { + if (value) { + updateChat.mutate({ configurationId: +value }); + setPersistentAssistantId(+value); + } + }; + return (