diff --git a/.github_fork/workflows/deploy_docs.yaml b/.github_fork/workflows/deploy_docs.yaml index 32adf7b488..4e1db3b8fa 100644 --- a/.github_fork/workflows/deploy_docs.yaml +++ b/.github_fork/workflows/deploy_docs.yaml @@ -1,5 +1,5 @@ -name: Deploy Opik docs -run-name: Deploy docs ${{ github.ref_name }} to S3 ${{ inputs.environment }} by @${{ github.actor }} +name: Deploy Opik Python SDK docs +run-name: Deploy Python SDK docs ${{ github.ref_name }} to S3 ${{ inputs.environment }} by @${{ github.actor }} on: workflow_dispatch: @@ -19,35 +19,14 @@ jobs: - name: checkout uses: actions/checkout@v4 - - name: Build docs + - name: Build Python SDK docs run: | - echo "Build documentation" - cd apps/opik-documentation/documentation - pip install -r requirements.txt - npm install - npm run build - cd - echo "Build sdk documentation" cd apps/opik-documentation/python-sdk-docs pip install -r requirements.txt pip install ../../../sdks/python make build - cd - - env: - SEGMENT_WRITE_KEY: ${{ secrets.SEGMENT_WRITE_KEY }} - - name: Upload docs to S3 ${{ inputs.environment }} - uses: jakejarvis/s3-sync-action@master - with: - args: --follow-symlinks --delete --exclude '.git*' - env: - AWS_S3_BUCKET: site.comet.com - AWS_ACCESS_KEY_ID: ${{ secrets.AWS_ACCESS_KEY_ID }} - AWS_SECRET_ACCESS_KEY: ${{ secrets.AWS_SECRET_ACCESS_KEY }} - AWS_REGION: us-east-1 - DEST_DIR: ${{ inputs.environment }}/docs-opik - SOURCE_DIR: apps/opik-documentation/documentation/build - - name: Upload sdk docs to S3 ${{ inputs.environment }} uses: jakejarvis/s3-sync-action@master with: diff --git a/.github_fork/workflows/deploy_python_sdk_docs.yml b/.github_fork/workflows/deploy_python_sdk_docs.yml new file mode 100644 index 0000000000..4e1db3b8fa --- /dev/null +++ b/.github_fork/workflows/deploy_python_sdk_docs.yml @@ -0,0 +1,40 @@ +name: Deploy Opik Python SDK docs +run-name: Deploy Python SDK docs ${{ github.ref_name }} to S3 ${{ inputs.environment }} by @${{ github.actor }} + +on: + workflow_dispatch: + inputs: + environment: + type: choice + description: Choose environment + options: + - staging + - production + - development +jobs: + upload: + runs-on: ubuntu-latest + environment: ${{ inputs.environment }} + steps: + - name: checkout + uses: actions/checkout@v4 + + - name: Build Python SDK docs + run: | + echo "Build sdk documentation" + cd apps/opik-documentation/python-sdk-docs + pip install -r requirements.txt + pip install ../../../sdks/python + make build + + - name: Upload sdk docs to S3 ${{ inputs.environment }} + uses: jakejarvis/s3-sync-action@master + with: + args: --follow-symlinks --delete --exclude '.git*' + env: + AWS_S3_BUCKET: site.comet.com + AWS_ACCESS_KEY_ID: ${{ secrets.AWS_ACCESS_KEY_ID }} + AWS_SECRET_ACCESS_KEY: ${{ secrets.AWS_SECRET_ACCESS_KEY }} + AWS_REGION: us-east-1 + DEST_DIR: ${{ inputs.environment }}/docs-opik/python-sdk-reference + SOURCE_DIR: apps/opik-documentation/python-sdk-docs/build/html diff --git a/.github_fork/workflows/documentation_codeblock_tests.yml b/.github_fork/workflows/documentation_codeblock_tests.yml index ca6268e63d..679f240291 100644 --- a/.github_fork/workflows/documentation_codeblock_tests.yml +++ b/.github_fork/workflows/documentation_codeblock_tests.yml @@ -1,12 +1,12 @@ -name: Documentation - Test codeblocks +name: Docs - Test codeblocks on: workflow_dispatch: pull_request: paths: - - 'apps/opik-documentation/documentation/docs/*.md' - - 'apps/opik-documentation/documentation/docs/*.mdx' - - 'apps/opik-documentation/documentation/docs/**/*.md' - - 'apps/opik-documentation/documentation/docs/**/*.mdx' + - 'apps/opik-documentation/documentation/fern/docs/*.md' + - 'apps/opik-documentation/documentation/fern/docs/*.mdx' + - 'apps/opik-documentation/documentation/fern/docs/**/*.md' + - 'apps/opik-documentation/documentation/fern/docs/**/*.mdx' jobs: collect_test_paths: diff --git a/.github_fork/workflows/documentation_cookbook_tests.yml b/.github_fork/workflows/documentation_cookbook_tests.yml index 2b0e24ebfa..2f632a9cc5 100644 --- a/.github_fork/workflows/documentation_cookbook_tests.yml +++ b/.github_fork/workflows/documentation_cookbook_tests.yml @@ -1,4 +1,4 @@ -name: Documentation - Test cookbooks +name: Docs - Test cookbooks on: workflow_dispatch: inputs: diff --git a/.github_fork/workflows/documentation_deploy.yml b/.github_fork/workflows/documentation_deploy.yml new file mode 100644 index 0000000000..00daa0667f --- /dev/null +++ b/.github_fork/workflows/documentation_deploy.yml @@ -0,0 +1,27 @@ +name: Docs - Publish + +on: + workflow_dispatch: + push: + branches: + - main + paths: + - 'apps/opik-documentation/documentation/**' + +jobs: + run: + runs-on: ubuntu-latest + steps: + - uses: actions/checkout@v3 + with: + fetch-depth: 0 # Fetch all history for git diff + + - name: Install Fern + run: npm install -g fern-api + + - name: Publish Docs + env: + FERN_TOKEN: ${{ secrets.FERN_TOKEN }} + run: | + cd apps/opik-documentation/documentation + fern generate --docs diff --git a/.github_fork/workflows/documentation_image_optimizer.yml b/.github_fork/workflows/documentation_image_optimizer.yml new file mode 100644 index 0000000000..8a485b50dc --- /dev/null +++ b/.github_fork/workflows/documentation_image_optimizer.yml @@ -0,0 +1,32 @@ +name: Docs - Compress Images +on: + workflow_dispatch: + pull_request: + # Run Image Actions when JPG, JPEG, PNG or WebP files are added or changed. + # See https://help.github.com/en/actions/automating-your-workflow-with-github-actions/workflow-syntax-for-github-actions#onpushpull_requestpaths for reference. + paths: + [ + "apps/opik-documentation/documentation/fern/img/**.jpg", + "apps/opik-documentation/documentation/fern/img/**.jpeg", + "apps/opik-documentation/documentation/fern/img/**.png", + "apps/opik-documentation/documentation/fern/img/**.webp", + ] +jobs: + build: + # Only run on non-draft PRs within the same repository. + if: + github.event.pull_request.head.repo.full_name == github.repository && github.event.pull_request.draft + == false + name: calibreapp/image-actions + runs-on: ubuntu-latest + steps: + - name: Checkout Repo + uses: actions/checkout@v4.2.2 + + - name: Compress Images + uses: calibreapp/image-actions@1.1.0 + with: + # The `GITHUB_TOKEN` is automatically generated by GitHub and scoped only to the repository that is currently running the action. By default, the action can’t update Pull Requests initiated from forked repositories. + # See https://docs.github.com/en/actions/reference/authentication-in-a-workflow and https://help.github.com/en/articles/virtual-environments-for-github-actions#token-permissions + githubToken: ${{ secrets.GITHUB_TOKEN }} + ignorePaths: "apps/opik-frontend/**,apps/opik-backend/**,apps/opik-python-backend/**" diff --git a/.github_fork/workflows/documentation_preview_link.yml b/.github_fork/workflows/documentation_preview_link.yml new file mode 100644 index 0000000000..a76118c8cc --- /dev/null +++ b/.github_fork/workflows/documentation_preview_link.yml @@ -0,0 +1,34 @@ +name: Docs - Preview link + +on: + pull_request: + paths: + - 'apps/opik-documentation/documentation/**' + +jobs: + run: + runs-on: ubuntu-latest + permissions: write-all + steps: + - name: Checkout repository + uses: actions/checkout@v4 + + - name: Install Fern + run: npm install -g fern-api + + - name: Generate preview URL + id: generate-docs + working-directory: apps/opik-documentation/documentation + env: + FERN_TOKEN: ${{ secrets.FERN_TOKEN }} + run: | + OUTPUT=$(fern generate --docs --preview 2>&1) || true + echo "$OUTPUT" + URL=$(echo "$OUTPUT" | grep -oP 'Published docs to \K.*(?= \()') + echo "Preview URL: $URL" + echo "🌿 Preview your docs: $URL" > preview_url.txt + + - name: Comment URL in PR + uses: thollander/actions-comment-pull-request@v2.4.3 + with: + filePath: apps/opik-documentation/documentation/preview_url.txt diff --git a/.github_fork/workflows/publish_typescript_sdk.yml b/.github_fork/workflows/typescript_sdk_publish.yml similarity index 62% rename from .github_fork/workflows/publish_typescript_sdk.yml rename to .github_fork/workflows/typescript_sdk_publish.yml index f29904915a..925d738dbd 100644 --- a/.github_fork/workflows/publish_typescript_sdk.yml +++ b/.github_fork/workflows/typescript_sdk_publish.yml @@ -1,4 +1,5 @@ -name: Publish TypeScript SDK +name: TypeScript SDK Publish +run-name: "TypeScript SDK Publish from ${{github.ref_name}} by @${{ github.actor }}" on: workflow_dispatch: @@ -23,7 +24,9 @@ jobs: steps: - uses: actions/checkout@v4 with: - token: ${{ secrets.GITHUB_TOKEN }} + ref: main + fetch-depth: 0 + token: ${{ secrets.GH_PAT_TO_ACCESS_GITHUB_API }} - name: Setup Node.js uses: actions/setup-node@v4 @@ -42,10 +45,10 @@ jobs: - name: Commit version changes run: | - git config --local user.email "action@github.com" - git config --local user.name "GitHub Action" + git config --local user.email "github-actions@comet.com" + git config --local user.name "github-actions" git add package.json package-lock.json - git commit -m "chore: bump typescript sdk version to $(node -p "require('./package.json').version")" + git commit -m "Update TypeScript SDK version to $(node -p "require('./package.json').version")" - name: Publish to NPM run: npm publish @@ -53,4 +56,8 @@ jobs: NODE_AUTH_TOKEN: ${{ secrets.NPM_TOKEN }} - name: Push changes - run: git push + uses: ad-m/github-push-action@master + with: + github_token: ${{ secrets.GH_PAT_TO_ACCESS_GITHUB_API }} + branch: ${{ github.ref }} + force_with_lease: true diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md index 44dbe1abc4..2b4f7e438a 100644 --- a/CONTRIBUTING.md +++ b/CONTRIBUTING.md @@ -54,15 +54,14 @@ Please see instructions in `deployment/docker-compose/README.md` ### Contributing to the documentation -The documentation is made up of three main parts: +The documentation is made up of two main parts: 1. `apps/opik-documentation/documentation`: The Opik documentation website 2. `apps/opik-documentation/python-sdk-docs`: The Python reference documentation -3. `apps/opik-documentation/rest-api-docs`: The REST API reference documentation #### Contributing to the documentation website -The documentation website is built using [Docusaurus](https://docusaurus.io/) and is located in `apps/opik-documentation/documentation`. +The documentation website is built using [Fern](https://www.buildwithfern.com/) and is located in `apps/opik-documentation/documentation`. In order to run the documentation website locally, you need to have `npm` installed. Once installed, you can run the documentation locally using the following command: @@ -78,6 +77,12 @@ npm run dev You can then access the documentation website at `http://localhost:3000`. Any change you make to the documentation will be updated in real-time. +When updating the documentation, you will need to update either: + +- `docs/cookbook`: This is where all our cookbooks are located. +- `fern/docs`: This is where all the markdown code is stored and where the majority of the documentation is located. + + #### Contributing to the Python SDK reference documentation The Python SDK reference documentation is built using [Sphinx](https://www.sphinx-doc.org/en/master/) and is located in `apps/opik-documentation/python-sdk-docs`. diff --git a/apps/opik-backend/pom.xml b/apps/opik-backend/pom.xml index 4df8308bdb..df93d4f5bf 100644 --- a/apps/opik-backend/pom.xml +++ b/apps/opik-backend/pom.xml @@ -16,22 +16,22 @@ UTF-8 UTF-8 - 4.0.7 - 2.2.22 - 1.18.32 + 4.0.12 + 2.2.28 + 1.18.36 9.2.0 - 7.1.3 - 3.47.0 + 7.1.4 + 3.48.0 3.0.0 0.7.2 - 0.7.2 - 1.6.2 - 1.20.2 + 0.8.1 + 1.6.3 + 1.20.4 5.1.0 - 3.10.0 + 3.12.0 3.44.0 - 2.12.0 - 2.30.2 + 2.13.0 + 2.30.21 2.9.0 com.comet.opik.OpikApplication @@ -92,7 +92,7 @@ software.amazon.jdbc aws-advanced-jdbc-wrapper - 2.5.0 + 2.5.4 io.dropwizard @@ -196,7 +196,12 @@ org.apache.httpcomponents.client5 httpclient5 - 5.2.3 + 5.4.2 + + + org.apache.httpcomponents.core5 + httpcore5 + 5.3.3 org.mvel @@ -300,7 +305,7 @@ com.clickhouse clickhouse-jdbc - ${clickhouse-java.version} + 0.7.2 test @@ -311,7 +316,7 @@ com.redis testcontainers-redis - 2.2.2 + 2.2.3 test @@ -353,12 +358,12 @@ org.apache.maven.plugins maven-source-plugin - 3.3.0 + 3.3.1 org.apache.maven.plugins maven-javadoc-plugin - 3.11.1 + 3.11.2 org.apache.maven.plugins diff --git a/apps/opik-backend/src/main/java/com/comet/opik/domain/FeedbackScoreService.java b/apps/opik-backend/src/main/java/com/comet/opik/domain/FeedbackScoreService.java index fefa30ca68..a422795180 100644 --- a/apps/opik-backend/src/main/java/com/comet/opik/domain/FeedbackScoreService.java +++ b/apps/opik-backend/src/main/java/com/comet/opik/domain/FeedbackScoreService.java @@ -5,6 +5,7 @@ import com.comet.opik.api.FeedbackScoreNames; import com.comet.opik.api.Project; import com.comet.opik.infrastructure.auth.RequestContext; +import com.comet.opik.utils.BinaryOperatorUtils; import com.comet.opik.utils.WorkspaceUtils; import com.google.inject.ImplementedBy; import com.google.inject.Singleton; @@ -22,15 +23,16 @@ import java.util.List; import java.util.Map; import java.util.Set; +import java.util.TreeMap; import java.util.UUID; import java.util.function.Function; +import java.util.stream.Collectors; import static com.comet.opik.domain.FeedbackScoreDAO.EntityType; import static com.comet.opik.infrastructure.db.TransactionTemplateAsync.READ_ONLY; import static com.comet.opik.infrastructure.db.TransactionTemplateAsync.WRITE; import static com.comet.opik.utils.ErrorUtils.failWithNotFound; import static java.util.stream.Collectors.groupingBy; -import static java.util.stream.Collectors.toMap; @ImplementedBy(FeedbackScoreServiceImpl.class) public interface FeedbackScoreService { @@ -151,17 +153,24 @@ private List mergeProjectsAndScores(Map projectMap, Map> scoresPerProject) { return scoresPerProject.keySet() .stream() - .map(projectName -> new ProjectDto( - projectMap.get(projectName), - scoresPerProject.get(projectName) - .stream() - .map(item -> item.toBuilder().projectId(projectMap.get(projectName).id()).build()) // set projectId - .toList())) + .map(projectName -> { + Project project = projectMap.get(projectName); + return new ProjectDto( + project, + scoresPerProject.get(projectName) + .stream() + .map(item -> item.toBuilder().projectId(project.id()).build()) // set projectId + .toList()); + }) .toList(); } private Map groupByName(List projects) { - return projects.stream().collect(toMap(Project::name, Function.identity())); + return projects.stream().collect(Collectors.toMap( + Project::name, + Function.identity(), + BinaryOperatorUtils.last(), + () -> new TreeMap<>(String.CASE_INSENSITIVE_ORDER))); } private List getAllProjectsByName(String workspaceId, @@ -177,7 +186,8 @@ private List getAllProjectsByName(String workspaceId, private void checkIfNeededToCreateProjects(Map> scoresPerProject, String userName, String workspaceId) { - Map projectsPerName = groupByName(getAllProjectsByName(workspaceId, scoresPerProject)); + Map projectsPerLowerCaseName = groupByName( + getAllProjectsByName(workspaceId, scoresPerProject)); syncTemplate.inTransaction(WRITE, handle -> { @@ -186,7 +196,7 @@ private void checkIfNeededToCreateProjects(Map !projectsPerName.containsKey(projectName)) + .filter(projectName -> !projectsPerLowerCaseName.containsKey(projectName)) .forEach(projectName -> { UUID projectId = idGenerator.generateId(); var newProject = Project.builder() diff --git a/apps/opik-backend/src/main/java/com/comet/opik/domain/SpanDAO.java b/apps/opik-backend/src/main/java/com/comet/opik/domain/SpanDAO.java index 5714026aad..88e7e26de9 100644 --- a/apps/opik-backend/src/main/java/com/comet/opik/domain/SpanDAO.java +++ b/apps/opik-backend/src/main/java/com/comet/opik/domain/SpanDAO.java @@ -554,11 +554,8 @@ ORDER BY (workspace_id, project_id, entity_id, id) DESC, last_updated_at DESC s.last_updated_at as last_updated_at, s.created_by as created_by, s.last_updated_by as last_updated_by, - if(s.end_time IS NOT NULL AND s.start_time IS NOT NULL - AND notEquals(s.start_time, toDateTime64('1970-01-01 00:00:00.000', 9)), - (dateDiff('microsecond', s.start_time, s.end_time) / 1000.0), - NULL) AS duration_millis, - groupArray(tuple(c.*)) AS comments + s.duration_millis as duration_millis, + groupArray(tuple(c.*)) AS comments FROM ( SELECT *, @@ -589,10 +586,9 @@ ORDER BY (workspace_id, project_id, entity_type, entity_id, name) DESC, last_upd HAVING ) - ORDER BY id DESC, last_updated_at DESC + ORDER BY (workspace_id, project_id, trace_id, parent_span_id, id) DESC, last_updated_at DESC LIMIT 1 BY id - LIMIT :limit - OFFSET :offset + LIMIT :limit OFFSET :offset ) AS s LEFT JOIN comments_final AS c ON s.id = c.entity_id GROUP BY @@ -749,6 +745,8 @@ ORDER BY (workspace_id, project_id, entity_type, entity_id, name) DESC, last_upd HAVING ) + ORDER BY (workspace_id, project_id, trace_id, parent_span_id, id) DESC, last_updated_at DESC + LIMIT 1 BY id ) AS s LEFT JOIN feedback_scores_agg AS f ON s.id = f.entity_id ) diff --git a/apps/opik-backend/src/main/java/com/comet/opik/domain/SpanService.java b/apps/opik-backend/src/main/java/com/comet/opik/domain/SpanService.java index b78d2132f1..28edc0ef57 100644 --- a/apps/opik-backend/src/main/java/com/comet/opik/domain/SpanService.java +++ b/apps/opik-backend/src/main/java/com/comet/opik/domain/SpanService.java @@ -12,6 +12,7 @@ import com.comet.opik.api.error.IdentifierMismatchException; import com.comet.opik.infrastructure.auth.RequestContext; import com.comet.opik.infrastructure.lock.LockService; +import com.comet.opik.utils.BinaryOperatorUtils; import com.comet.opik.utils.WorkspaceUtils; import com.google.common.base.Preconditions; import io.opentelemetry.instrumentation.annotations.WithSpan; @@ -32,6 +33,7 @@ import java.util.NoSuchElementException; import java.util.Objects; import java.util.Set; +import java.util.TreeMap; import java.util.UUID; import java.util.function.Function; import java.util.stream.Collectors; @@ -279,13 +281,17 @@ public Mono create(@NonNull SpanBatch batch) { private List bindSpanToProjectAndId(SpanBatch batch, List projects) { Map projectPerName = projects.stream() - .collect(Collectors.toMap(project -> project.name().toLowerCase(), Function.identity())); + .collect(Collectors.toMap( + Project::name, + Function.identity(), + BinaryOperatorUtils.last(), + () -> new TreeMap<>(String.CASE_INSENSITIVE_ORDER))); return batch.spans() .stream() .map(span -> { String projectName = WorkspaceUtils.getProjectName(span.projectName()); - Project project = projectPerName.get(projectName.toLowerCase()); + Project project = projectPerName.get(projectName); if (project == null) { log.warn("Project not found for span project '{}' and default '{}'", span.projectName(), diff --git a/apps/opik-backend/src/main/java/com/comet/opik/domain/TraceService.java b/apps/opik-backend/src/main/java/com/comet/opik/domain/TraceService.java index c818c0a136..77ec665c2f 100644 --- a/apps/opik-backend/src/main/java/com/comet/opik/domain/TraceService.java +++ b/apps/opik-backend/src/main/java/com/comet/opik/domain/TraceService.java @@ -18,6 +18,7 @@ import com.comet.opik.infrastructure.db.TransactionTemplateAsync; import com.comet.opik.infrastructure.lock.LockService; import com.comet.opik.utils.AsyncUtils; +import com.comet.opik.utils.BinaryOperatorUtils; import com.comet.opik.utils.WorkspaceUtils; import com.google.common.base.Preconditions; import com.google.common.eventbus.EventBus; @@ -37,6 +38,7 @@ import java.util.List; import java.util.Map; import java.util.Set; +import java.util.TreeMap; import java.util.UUID; import java.util.function.Function; import java.util.stream.Collectors; @@ -145,13 +147,17 @@ public Mono create(TraceBatch batch) { private List bindTraceToProjectAndId(TraceBatch batch, List projects) { Map projectPerName = projects.stream() - .collect(Collectors.toMap(project -> project.name().toLowerCase(), Function.identity())); + .collect(Collectors.toMap( + Project::name, + Function.identity(), + BinaryOperatorUtils.last(), + () -> new TreeMap<>(String.CASE_INSENSITIVE_ORDER))); return batch.traces() .stream() .map(trace -> { String projectName = WorkspaceUtils.getProjectName(trace.projectName()); - Project project = projectPerName.get(projectName.toLowerCase()); + Project project = projectPerName.get(projectName); UUID id = trace.id() == null ? idGenerator.generateId() : trace.id(); IdGenerator.validateVersion(id, TRACE_KEY); diff --git a/apps/opik-backend/src/main/java/com/comet/opik/utils/BinaryOperatorUtils.java b/apps/opik-backend/src/main/java/com/comet/opik/utils/BinaryOperatorUtils.java new file mode 100644 index 0000000000..a241a66b8c --- /dev/null +++ b/apps/opik-backend/src/main/java/com/comet/opik/utils/BinaryOperatorUtils.java @@ -0,0 +1,14 @@ +package com.comet.opik.utils; + +import lombok.experimental.UtilityClass; + +import java.util.function.BinaryOperator; + +@UtilityClass +public class BinaryOperatorUtils { + + public BinaryOperator last() { + return (oldValue, newValue) -> newValue; + } + +} diff --git a/apps/opik-backend/src/test/java/com/comet/opik/api/resources/v1/priv/SpansResourceTest.java b/apps/opik-backend/src/test/java/com/comet/opik/api/resources/v1/priv/SpansResourceTest.java index 473dca14e5..6b99bcf929 100644 --- a/apps/opik-backend/src/test/java/com/comet/opik/api/resources/v1/priv/SpansResourceTest.java +++ b/apps/opik-backend/src/test/java/com/comet/opik/api/resources/v1/priv/SpansResourceTest.java @@ -4026,6 +4026,12 @@ void testDeserializationErrorOnSpanCreate() { } } + private Stream getProjectNameModifierArg() { + return Stream.of( + arguments(Function.identity()), + arguments((Function) String::toUpperCase)); + } + @Nested @DisplayName("Batch:") @TestInstance(TestInstance.Lifecycle.PER_CLASS) @@ -4054,9 +4060,7 @@ void batch__whenCreateSpans__thenReturnNoContent(Function projec } Stream batch__whenCreateSpans__thenReturnNoContent() { - return Stream.of( - arguments(Function.identity()), - arguments((Function) String::toUpperCase)); + return getProjectNameModifierArg(); } @Test @@ -4215,17 +4219,7 @@ void batch__whenCreateSpansUsageWithNullValue__thenReturnNoContent() { } private void batchCreateAndAssert(List expectedSpans, String apiKey, String workspaceName) { - - try (var actualResponse = client.target(URL_TEMPLATE.formatted(baseURI)) - .path("batch") - .request() - .header(HttpHeaders.AUTHORIZATION, apiKey) - .header(WORKSPACE_HEADER, workspaceName) - .post(Entity.json(new SpanBatch(expectedSpans)))) { - - assertThat(actualResponse.getStatusInfo().getStatusCode()).isEqualTo(204); - assertThat(actualResponse.hasEntity()).isFalse(); - } + spanResourceClient.batchCreateSpans(expectedSpans, apiKey, workspaceName); } private Span getAndAssert(Span expectedSpan, String apiKey, String workspaceName) { @@ -5559,19 +5553,68 @@ void feedback__whenFeedbackSpanBatchHasMaxSize__thenReturnNoContentAndCreateScor .build()) .toList(); - try (var actualResponse = client.target(URL_TEMPLATE.formatted(baseURI)) - .path("feedback-scores") - .request() - .header(HttpHeaders.AUTHORIZATION, API_KEY) - .header(WORKSPACE_HEADER, TEST_WORKSPACE) - .put(Entity.json(new FeedbackScoreBatch(scores)))) { + spanResourceClient.feedbackScores(scores, API_KEY, TEST_WORKSPACE); + } - assertThat(actualResponse.getStatusInfo().getStatusCode()).isEqualTo(204); - assertThat(actualResponse.hasEntity()).isFalse(); - } + @ParameterizedTest + @MethodSource + void feedback__whenLinkingByProjectName__thenReturnNoContent(Function projectNameModifier) { + + String projectName = UUID.randomUUID().toString(); + + createProject(projectName.toUpperCase(), TEST_WORKSPACE, API_KEY); + + var spans = IntStream.range(0, 10) + .mapToObj(i -> podamFactory.manufacturePojo(Span.class).toBuilder() + .projectId(null) + .projectName(projectNameModifier.apply(projectName)) + .parentSpanId(null) + .feedbackScores(null) + .build()) + .toList(); + + batchCreateAndAssert(spans, API_KEY, TEST_WORKSPACE); + + var scores = spans.stream() + .map(span -> podamFactory.manufacturePojo(FeedbackScoreBatchItem.class).toBuilder() + .id(span.id()) + .projectName(projectNameModifier.apply(projectName)) + .build()) + .toList(); + + spanResourceClient.feedbackScores(scores, API_KEY, TEST_WORKSPACE); + + var expectedSpansWithScores = spans.stream() + .map(span -> { + FeedbackScoreBatchItem feedbackScoreBatchItem = scores.stream() + .filter(score -> score.id().equals(span.id())) + .findFirst() + .orElseThrow(); + return span.toBuilder() + .feedbackScores(List.of(mapFeedbackScore(feedbackScoreBatchItem))) + .build(); + }) + .toList(); + + getAndAssertPage(TEST_WORKSPACE, projectName, List.of(), expectedSpansWithScores.reversed(), + expectedSpansWithScores.reversed(), List.of(), API_KEY); + } + + Stream feedback__whenLinkingByProjectName__thenReturnNoContent() { + return getProjectNameModifierArg(); } } + private FeedbackScore mapFeedbackScore(FeedbackScoreBatchItem feedbackScoreBatchItem) { + return FeedbackScore.builder() + .name(feedbackScoreBatchItem.name()) + .value(feedbackScoreBatchItem.value()) + .source(feedbackScoreBatchItem.source()) + .categoryName(feedbackScoreBatchItem.categoryName()) + .reason(feedbackScoreBatchItem.reason()) + .build(); + } + @Nested @DisplayName("Comment:") @TestInstance(TestInstance.Lifecycle.PER_CLASS) diff --git a/apps/opik-backend/src/test/java/com/comet/opik/api/resources/v1/priv/TracesResourceTest.java b/apps/opik-backend/src/test/java/com/comet/opik/api/resources/v1/priv/TracesResourceTest.java index 5cca7affea..95e71e94ea 100644 --- a/apps/opik-backend/src/test/java/com/comet/opik/api/resources/v1/priv/TracesResourceTest.java +++ b/apps/opik-backend/src/test/java/com/comet/opik/api/resources/v1/priv/TracesResourceTest.java @@ -3833,9 +3833,7 @@ void batch__whenCreateTraces__thenReturnNoContent(Function proje } Stream batch__whenCreateTraces__thenReturnNoContent() { - return Stream.of( - arguments(Function.identity()), - arguments((Function) String::toUpperCase)); + return getProjectNameModifierArgs(); } @Test @@ -3942,6 +3940,12 @@ void batch__whenSendingMultipleTracesWithNoId__thenReturnNoContent() { } } + private Stream getProjectNameModifierArgs() { + return Stream.of( + arguments(Function.identity()), + arguments((Function) String::toUpperCase)); + } + private void batchCreateSpansAndAssert(List expectedSpans, String apiKey, String workspaceName) { try (var actualResponse = client.target(URL_TEMPLATE_SPANS.formatted(baseURI)) .path("batch") @@ -5432,6 +5436,66 @@ void feedback__whenFeedbackTraceIdIsNotValid__thenReturn400() { .contains("trace id must be a version 7 UUID"); } } + + @ParameterizedTest + @MethodSource + void feedback__whenLinkingByProjectName__thenReturnNoContent(Function projectNameModifier) { + + String projectName = UUID.randomUUID().toString(); + + createProject(projectName.toUpperCase(), TEST_WORKSPACE, API_KEY); + + var traces = IntStream.range(0, 10) + .mapToObj(i -> factory.manufacturePojo(Trace.class).toBuilder() + .projectId(null) + .projectName(projectNameModifier.apply(projectName)) + .feedbackScores(null) + .comments(null) + .usage(null) + .build()) + .toList(); + + traceResourceClient.batchCreateTraces(traces, API_KEY, TEST_WORKSPACE); + + var scores = traces.stream() + .map(trace -> factory.manufacturePojo(FeedbackScoreBatchItem.class).toBuilder() + .id(trace.id()) + .projectName(projectNameModifier.apply(projectName)) + .build()) + .toList(); + + traceResourceClient.feedbackScores(scores, API_KEY, TEST_WORKSPACE); + + var expectedTracesWithScores = traces.stream() + .map(trace -> { + FeedbackScoreBatchItem feedbackScoreBatchItem = scores.stream() + .filter(score -> score.id().equals(trace.id())) + .findFirst() + .orElseThrow(); + + return trace.toBuilder() + .feedbackScores(List.of(mapFeedbackScore(feedbackScoreBatchItem))) + .build(); + }) + .toList(); + + getAndAssertPage(TEST_WORKSPACE, projectName, List.of(), expectedTracesWithScores.reversed(), + expectedTracesWithScores.reversed(), List.of(), API_KEY); + } + + Stream feedback__whenLinkingByProjectName__thenReturnNoContent() { + return getProjectNameModifierArgs(); + } + } + + private FeedbackScore mapFeedbackScore(FeedbackScoreBatchItem feedbackScoreBatchItem) { + return FeedbackScore.builder() + .name(feedbackScoreBatchItem.name()) + .value(feedbackScoreBatchItem.value()) + .source(feedbackScoreBatchItem.source()) + .categoryName(feedbackScoreBatchItem.categoryName()) + .reason(feedbackScoreBatchItem.reason()) + .build(); } @Nested diff --git a/apps/opik-documentation/.pre-commit-config.yaml b/apps/opik-documentation/.pre-commit-config.yaml index 4857fc9724..86c17e99af 100644 --- a/apps/opik-documentation/.pre-commit-config.yaml +++ b/apps/opik-documentation/.pre-commit-config.yaml @@ -6,7 +6,7 @@ repos: args: - --print-width=120 files: ^apps/opik-documentation - exclude: "^(apps/opik-documentation/documentation/docs/reference)|(apps/opik-documentation/documentation/docs/cookbook/)|(apps/opik-documentation/documentation/rest_api/opik.yaml)" + exclude: "^(apps/opik-documentation/documentation/docs/cookbook/)|^(apps/opik-documentation/documentation/fern/openapi/opik.yaml)|^(apps/opik-documentation/documentation/fern/docs/cookbook/)" - repo: https://github.com/astral-sh/ruff-pre-commit rev: v0.6.9 diff --git a/apps/opik-documentation/documentation/babel.config.js b/apps/opik-documentation/documentation/babel.config.js deleted file mode 100644 index bfd75dbdfc..0000000000 --- a/apps/opik-documentation/documentation/babel.config.js +++ /dev/null @@ -1,3 +0,0 @@ -module.exports = { - presets: [require.resolve("@docusaurus/core/lib/babel/preset")], -}; diff --git a/apps/opik-documentation/documentation/build_script.sh b/apps/opik-documentation/documentation/build_script.sh deleted file mode 100644 index e005323d8d..0000000000 --- a/apps/opik-documentation/documentation/build_script.sh +++ /dev/null @@ -1,12 +0,0 @@ -#!/bin/bash - -# Rebuild the reference docs -npm run docusaurus clean-api-docs all -npm run docusaurus gen-api-docs all - -# Rebuild the Cookbooks -jupyter nbconvert --clear-output --inplace docs/cookbook/*.ipynb -jupyter nbconvert docs/cookbook/*.ipynb --to markdown - -# Build the docs -docusaurus build diff --git a/apps/opik-documentation/documentation/dev_script.sh b/apps/opik-documentation/documentation/dev_script.sh index 064fb046cf..fa12685ecc 100644 --- a/apps/opik-documentation/documentation/dev_script.sh +++ b/apps/opik-documentation/documentation/dev_script.sh @@ -1,13 +1,6 @@ #!/bin/bash -# Rebuild the reference docs -npm run docusaurus clean-api-docs all -npm run docusaurus gen-api-docs all - -# Convert the files to markdown if that has not already been done -jupyter nbconvert docs/cookbook/*.ipynb --to markdown - # Start the docs server and rebuild the cookbooks on change npx concurrently \ - "docusaurus start" \ - "nodemon --watch docs/cookbook/ -e ipynb --exec 'jupyter nbconvert docs/cookbook/*.ipynb --to markdown'" + "fern docs dev" \ + "nodemon --watch docs/cookbook/ -e ipynb --exec 'sh ./update_cookbooks.sh'" diff --git a/apps/opik-documentation/documentation/docs/changelog.md b/apps/opik-documentation/documentation/docs/changelog.md deleted file mode 100644 index e5c02ec819..0000000000 --- a/apps/opik-documentation/documentation/docs/changelog.md +++ /dev/null @@ -1,332 +0,0 @@ ---- -sidebar_label: Changelog -description: Weelkly changelog for Opik -pytest_codeblocks_skip: true ---- - -# Weekly Changelog - -## Week of 2025-02-03 - -**Opik Dashboard**: - -- You can now view feedback scores for your projects in the Opik home page -- Added line highlights in the quickstart page -- Allow users to download experiments as CSV and JSON files for further analysis - -**Python SDK**: - -- Update the `evaluate_*` methods so feedback scores are logged after they computed rather than at the end of an experiment as previously -- Released a new [usefulness metric](/evaluation/metrics/usefulness.md) -- Do not display warning messages about missing API key when Opik logging is disabled -- Add method to list datasets in a workspace -- Add method to list experiments linked to a dataset - -**JS / TS SDK**: - -- Official release of the first version of the SDK - Learn more [here](/tracing/log_traces.mdx##logging-with-the-js--ts-sdk) -- Support logging traces using the low-level Opik client and an experimental decorator. - -## Week of 2025-01-27 - -**Opik Dashboard**: - -- Performance improvements for workspaces with 100th of millions of traces -- Added support for cost tracking when using Gemini models -- Allow users to diff prompt - -**SDK**: - -- Fixed the `evaluate` and `evaluate_*` functions to better support event loops, particularly useful when using Ragas metrics -- Added support for Bedrock `invoke_agent` API - -## Week of 2025-01-20 - -**Opik Dashboard**: - -- Added logs for online evaluation rules so that you can more easily ensure your online evaluation metrics are working as expected -- Added auto-complete support in the variable mapping section of the online evaluation rules modal -- Added support for Anthropic models in the playground -- Experiments are now created when using datasets in the playground -- Improved the Opik home page -- Updated the code snippets in the quickstart to make them easier to understand - -**SDK**: - -- Improved support for litellm completion kwargs -- LiteLLM required version is now relaxed to avoid conflicts with other Python packages - -## Week of 2025-01-13 - -**Opik Dashboard**: - -- Datasets are now supported in the playground allowing you to quickly evaluate prompts on multiple samples -- Updated the models supported in the playground -- Updated the quickstart guides to include all the supported integrations -- Fix issue that means traces with text inputs can't be added to datasets -- Add the ability to edit dataset descriptions in the UI -- Released [online evaluation](/production/rules.md) rules - You can now define LLM as a Judge metrics that will automatically score all, or a subset, of your production traces. - -![Online evaluation](/img/changelog/2025-01-13/online_evaluation.gif) - -**SDK**: - -- New integration with [CrewAI](/tracing/integrations/crewai.md) -- Released a new `evaluate_prompt` method that simplifies the evaluation of simple prompts templates -- Added Sentry to the Python SDK so we can more easily - -## Week of 2025-01-06 - -**Opik Dashboard**: - -- Fixed an issue with the trace viewer in Safari - -**SDK**: - -- Added a new `py.typed` file to the SDK to make it compatible with mypy - -## Week of 2024-12-30 - -**Opik Dashboard**: - -- Added duration chart to the project dashboard -- Prompt metadata can now be set and viewed in the UI, this can be used to store any additional information about the prompt -- Playground prompts and settings are now cached when you navigate away from the page - -**SDK**: - -- Introduced a new `OPIK_TRACK_DISABLE` environment variable to disable the tracking of traces and spans -- We now log usage information for traces logged using the LlamaIndex integration - -## Week of 2024-12-23 - -**SDK**: - -- Improved error messages when getting a rate limit when using the `evaluate` method -- Added support for a new metadata field in the `Prompt` object, this field is used to store any additional information about the prompt. -- Updated the library used to create uuidv7 IDs -- New Guardrails integration -- New DSPY integration - -## Week of 2024-12-16 - -**Opik Dashboard**: - -- The Opik playground is now in public preview - ![playground](/img/changelog/2024-12-16/playground.png) -- You can now view the prompt diff when updating a prompt from the UI -- Errors in traces and spans are now displayed in the UI -- Display agent graphs in the traces sidebar -- Released a new plugin for the [Kong AI Gateway](/production/gateway.mdx) - -**SDK**: - -- Added support for serializing Pydantic models passed to decorated functions -- Implemented `get_experiment_by_id` and `get_experiment_by_name` methods -- Scoring metrics are now logged to the traces when using the `evaluate` method -- New integration with [aisuite](/tracing/integrations/aisuite.md) -- New integration with [Haystack](/tracing/integrations/haystack.md) - -## Week of 2024-12-09 - -**Opik Dashboard**: - -- Updated the experiments pages to make it easier to analyze the results of each experiment. Columns are now organized based on where they came from (dataset, evaluation task, etc) and output keys are now displayed in multiple columns to make it easier to review - ![experiment item table](/img/changelog/2024-12-09/experiment_items_table.png) -- Improved the performance of the experiments so experiment items load faster -- Added descriptions for projects - -**SDK**: - -- Add cost tracking for OpenAI calls made using LangChain -- Fixed a timeout issue when calling `get_or_create_dataset` - -## Week of 2024-12-02 - -**Opik Dashboard**: - -- Added a new `created_by` column for each table to indicate who created the record -- Mask the API key in the user menu - -**SDK**: - -- Implement background batch sending of traces to speed up processing of trace creation requests -- Updated OpenAI integration to track cost of LLM calls -- Updated `prompt.format` method to raise an error when it is called with the wrong arguments -- Updated the `Opik` method so it accepts the `api_key` parameter as a positional argument -- Improved the prompt template for the `hallucination` metric -- Introduced a new `opik_check_tls_certificate` configuration option to disable the TLS certificate check. - -## Week of 2024-11-25 - -**Opik Dashboard**: - -- Feedback scores are now displayed as separate columns in the traces and spans table -- Introduce a new project dashboard to see trace count, feedback scores and token count over time. - ![project dashboard](/img/changelog/2024-11-25/project_dashboard.png) -- Project statistics are now displayed in the traces and spans table header, this is especially useful for tracking the average feedback scores - ![project statistics](/img/changelog/2024-11-25/project_statistics.png) -- Redesigned the experiment item sidebar to make it easier to review experiment results - ![experiment item sidebar](/img/changelog/2024-11-25/experiment_item_sidebar.png) -- Annotating feedback scores in the UI now feels much faster -- Support exporting traces as JSON file in addition to CSV -- Sidebars now close when clicking outside of them -- Dataset groups in the experiment page are now sorted by last updated date -- Updated scrollbar styles for Windows users - -**SDK**: - -- Improved the robustness to connection issues by adding retry logic. -- Updated the OpenAI integration to track structured output calls using `beta.chat.completions.parse`. -- Fixed issue with `update_current_span` and `update_current_trace` that did not support updating the `output` field. - -## Week of 2024-11-18 - -**Opik Dashboard**: - -- Updated the majority of tables to increase the information density, it is now easier to review many traces at once. -- Images logged to datasets and experiments are now displayed in the UI. Both images urls and base64 encoded images are supported. - -**SDK**: - -- The `scoring_metrics` argument is now optional in the `evaluate` method. This is useful if you are looking at evaluating your LLM calls manually in the Opik UI. -- When uploading a dataset, the SDK now prints a link to the dataset in the UI. -- Usage is now correctly logged when using the LangChain OpenAI integration. -- Implement a batching mechanism for uploading spans and dataset items to avoid `413 Request Entity Too Large` errors. -- Removed pandas and numpy as mandatory dependencies. - -## Week of 2024-11-11 - -**Opik Dashboard**: - -- Added the option to sort the projects table by `Last updated`, `Created at` and `Name` columns. -- Updated the logic for displaying images, instead of relying on the format of the response, we now use regex rules to detect if the trace or span input includes a base64 encoded image or url. -- Improved performance of the Traces table by truncating trace inputs and outputs if they contain base64 encoded images. -- Fixed some issues with rendering trace input and outputs in YAML format. -- Added grouping and charts to the experiments page: - ![experiment summary](/img/changelog/2024-11-11/experiment_summary.png) - -**SDK**: - -- **New integration**: Anthropic integration - - ```python - from anthropic import Anthropic, AsyncAnthropic - from opik.integrations.anthropic import track_anthropic - - client = Anthropic() - client = track_anthropic(client, project_name="anthropic-example") - - message = client.messages.create( - max_tokens=1024, - messages=[ - { - "role": "user", - "content": "Tell a fact", - } - ], - model="claude-3-opus-20240229", - ) - print(message) - ``` - -- Added a new `evaluate_experiment` method in the SDK that can be used to re-score an existing experiment, learn more in the [Update experiments](/evaluation/update_existing_experiment.md) guide. - -## Week of 2024-11-04 - -**Opik Dashboard**: - -- Added a new `Prompt library` page to manage your prompts in the UI. - ![prompt library](/img/changelog/2024-11-04/prompt_library_versions.png) - -**SDK**: - -- Introduced the `Prompt` object in the SDK to manage prompts stored in the library. See the [Prompt Management](/prompt_engineering/managing_prompts_in_code.mdx) guide for more details. -- Introduced a `Opik.search_spans` method to search for spans in a project. See the [Search spans](/tracing/export_data.md#exporting-spans) guide for more details. -- Released a new integration with [AWS Bedrock](/tracing/integrations/bedrock.md) for using Opik with Bedrock models. - -## Week of 2024-10-28 - -**Opik Dashboard**: - -- Added a new `Feedback modal` in the UI so you can easily provide feedback on any parts of the platform. - -**SDK**: - -- Released new evaluation metric: [GEval](/evaluation/metrics/g_eval.md) - This LLM as a Judge metric is task agnostic and can be used to evaluate any LLM call based on your own custom evaluation criteria. -- Allow users to specify the path to the Opik configuration file using the `OPIK_CONFIG_PATH` environment variable, read more about it in the [Python SDK Configuration guide](/tracing/sdk_configuration.mdx#using-a-configuration-file). -- You can now configure the `project_name` as part of the `evaluate` method so that traces are logged to a specific project instead of the default one. -- Added a new `Opik.search_traces` method to search for traces, this includes support for a search string to return only specific traces. -- Enforce structured outputs for LLM as a Judge metrics so that they are more reliable (they will no longer fail when decoding the LLM response). - -## Week of 2024-10-21 - -**Opik Dashboard**: - -- Added the option to download traces and LLM calls as CSV files from the UI: - ![download traces](/img/changelog/2024-10-21/download_traces.png) -- Introduce a new quickstart guide to help you get started: - ![quickstart guide](/img/changelog/2024-10-21/quickstart_guide.png) -- Updated datasets to support more flexible data schema, you can now insert items with any key value pairs and not just `input` and `expected_output`. See more in the SDK section below. -- Multiple small UX improvements (more informative empty state for projects, updated icons, feedback tab in the experiment page, etc). -- Fix issue with `\t` characters breaking the YAML code block in the traces page. - -**SDK**: - -- Datasets now support more flexible data schema, we now support inserting items with any key value pairs: - - ```python - import opik - - client = opik.Opik() - dataset = client.get_or_create_dataset(name="Demo Dataset") - dataset.insert([ - {"user_question": "Hello, what can you do ?", "expected_output": {"assistant_answer": "I am a chatbot assistant that can answer questions and help you with your queries!"}}, - {"user_question": "What is the capital of France?", "expected_output": {"assistant_answer": "Paris"}}, - ]) - ``` - -- Released WatsonX, Gemini and Groq integration based on the LiteLLM integration. -- The `context` field is now optional in the [Hallucination](/tracing/integrations/overview.md) metric. -- LLM as a Judge metrics now support customizing the LLM provider by specifying the `model` parameter. See more in the [Customizing LLM as a Judge metrics](/evaluation/metrics/overview.md#customizing-llm-as-a-judge-metrics) section. -- Fixed an issue when updating feedback scores using the `update_current_span` and `update_current_trace` methods. See this Github issue for more details. - -## Week of 2024-10-14 - -**Opik Dashboard**: - -- Fix handling of large experiment names in breadcrumbs and popups -- Add filtering options for experiment items in the experiment page - ![experiment item filters](/img/changelog/2024-10-14/experiment_page_filtering.png) - -**SDK:** - -- Allow users to configure the project name in the LangChain integration - -## Week of 2024-10-07 - -**Opik Dashboard**: - -- Added `Updated At` column in the project page -- Added support for filtering by token usage in the trace page - -**SDK:** - -- Added link to the trace project when traces are logged for the first time in a session -- Added link to the experiment page when calling the `evaluate` method -- Added `project_name` parameter in the `opik.Opik` client and `opik.track` decorator -- Added a new `nb_samples` parameter in the `evaluate` method to specify the number of samples to use for the evaluation -- Released the LiteLLM integration - -## Week of 2024-09-30 - -**Opik Dashboard**: - -- Added option to delete experiments from the UI -- Updated empty state for projects with no traces -- Removed tooltip delay for the reason icon in the feedback score components - -**SDK:** - -- Introduced new `get_or_create_dataset` method to the `opik.Opik` client. This method will create a new dataset if it does not exist. -- When inserting items into a dataset, duplicate items are now silently ignored instead of being ingested. diff --git a/apps/opik-documentation/documentation/docs/cookbook/.gitignore b/apps/opik-documentation/documentation/docs/cookbook/.gitignore deleted file mode 100644 index ded80e06c8..0000000000 --- a/apps/opik-documentation/documentation/docs/cookbook/.gitignore +++ /dev/null @@ -1,5 +0,0 @@ -*.sqlite -/data -langgraph_files/ - -*.md diff --git a/apps/opik-documentation/documentation/docs/evaluation/_category_.json b/apps/opik-documentation/documentation/docs/evaluation/_category_.json deleted file mode 100644 index 2400862129..0000000000 --- a/apps/opik-documentation/documentation/docs/evaluation/_category_.json +++ /dev/null @@ -1,8 +0,0 @@ -{ - "label": "Evaluation", - "position": 5, - "link": { - "type": "generated-index" - }, - "collapsed": false -} diff --git a/apps/opik-documentation/documentation/docs/evaluation/metrics/_category_.json b/apps/opik-documentation/documentation/docs/evaluation/metrics/_category_.json deleted file mode 100644 index 09d58e0bd5..0000000000 --- a/apps/opik-documentation/documentation/docs/evaluation/metrics/_category_.json +++ /dev/null @@ -1,7 +0,0 @@ -{ - "label": "Metrics", - "position": 3, - "link": { - "type": "generated-index" - } -} diff --git a/apps/opik-documentation/documentation/docs/faq.md b/apps/opik-documentation/documentation/docs/faq.md deleted file mode 100644 index ce5f840ad9..0000000000 --- a/apps/opik-documentation/documentation/docs/faq.md +++ /dev/null @@ -1,21 +0,0 @@ ---- -sidebar_label: FAQ -description: Frequently Asked Questions ---- - -# FAQ - -These FAQs are a collection of the most common questions that we've received from our users. If you have any other questions, please open an [issue on GitHub](https://github.com/comet-opik/opik/issues). - -## General - -### Can I use Opik to monitor my LLM application in production? - -Yes, Opik has been designed from the ground up to be used to monitor production applications. If you are self-hosting the -Opik platform, we recommend using the [Kuberneters deployment](/self-host/overview.md) option to ensure that Opik can scale as needed. - -## Opik Cloud - -### Are there are rate limits on Opik Cloud? - -Yes, in order to ensure all users have a good experience we have implemented rate limits. Each user is limited to `10,000` events per minute, an event is a trace, span, feedback score, dataset item, experiment item, etc. If you need to increase this limit please reach out to us on [Slack](https://chat.comet.com). diff --git a/apps/opik-documentation/documentation/docs/prompt_engineering/playground.md b/apps/opik-documentation/documentation/docs/prompt_engineering/playground.md deleted file mode 100644 index 44f43f0a9e..0000000000 --- a/apps/opik-documentation/documentation/docs/prompt_engineering/playground.md +++ /dev/null @@ -1,40 +0,0 @@ ---- -sidebar_label: Prompt playground -description: Describes Opik's prompt playground that can be used to quickly try out different prompts ---- - -# Prompt Playground - -:::tip -The Opik prompt playground is current in public preview, if you have any feedback or suggestions, please [let us know](https://github.com/comet-ml/opik/pulls). -::: - -When working with LLMs, there are time when you want to quickly try out different prompts and see how they perform. Opik's prompt playground is a great way to do just that. - -![playground](/img/evaluation/playground.png) - -## Configuring the prompt playground - -In order to use the prompt playground, you will need to first configure the LLM provider you want to use. You can do this by clicking on the `Configuration` tab in the sidebar and navigating to the `AI providers` tab. From there, you can select the provider you want to use and enter your API key. - -:::tip -Currently only OpenAI is supported but we are working on adding support for other LLM providers. -::: - -## Using the prompt playground - -The prompt playground is a simple interface that allows you to enter prompts and see the output of the LLM. It allows you to enter system, user and assistant messages and see the output of the LLM in real time. - -You can also easily evaluate how different models impact the prompt by duplicating a prompt and changing either the model or the model parameters. - -All of the conversations from the playground are logged to the `playground` project so that you can easily refer back to them later: - -![playground conversations](/img/evaluation/playground_conversations.png) - -## Running experiments in the playground - -You can evaluate prompts in the playground by using variables in the prompts using the `{{variable}}` syntax. You can then connect a dataset and run the prompts on each dataset item. This allows both technical and non-technical users to evaluate prompts quickly and easily. - -![playground evaluation](/img/evaluation/playground_evaluation.gif) - -When using datasets in the playground, you need to ensure the prompt contains variables in the mustache syntax (`{{variable}}`) that align with the columns in the dataset. For example if the dataset contains a column named `user_question` you need to ensure the prompt contains `{{user_question}}`. diff --git a/apps/opik-documentation/documentation/docs/reference/rest_api/.gitignore b/apps/opik-documentation/documentation/docs/reference/rest_api/.gitignore deleted file mode 100644 index d015c92c33..0000000000 --- a/apps/opik-documentation/documentation/docs/reference/rest_api/.gitignore +++ /dev/null @@ -1,2 +0,0 @@ -*.mdx -sidebar.ts diff --git a/apps/opik-documentation/documentation/docs/self-host/_category_.json b/apps/opik-documentation/documentation/docs/self-host/_category_.json deleted file mode 100644 index 4bddb7a1a7..0000000000 --- a/apps/opik-documentation/documentation/docs/self-host/_category_.json +++ /dev/null @@ -1,7 +0,0 @@ -{ - "label": "Self Host", - "position": 3, - "link": { - "type": "generated-index" - } -} diff --git a/apps/opik-documentation/documentation/docs/testing/_category_.json b/apps/opik-documentation/documentation/docs/testing/_category_.json deleted file mode 100644 index 3d37a24fa7..0000000000 --- a/apps/opik-documentation/documentation/docs/testing/_category_.json +++ /dev/null @@ -1,7 +0,0 @@ -{ - "label": "Testing", - "position": 4, - "link": { - "type": "generated-index" - } -} diff --git a/apps/opik-documentation/documentation/docs/tracing/_category_.json b/apps/opik-documentation/documentation/docs/tracing/_category_.json deleted file mode 100644 index 533c360652..0000000000 --- a/apps/opik-documentation/documentation/docs/tracing/_category_.json +++ /dev/null @@ -1,8 +0,0 @@ -{ - "label": "Tracing", - "position": 4, - "link": { - "type": "generated-index" - }, - "collapsed": false -} diff --git a/apps/opik-documentation/documentation/docs/tracing/integrations/_category_.json b/apps/opik-documentation/documentation/docs/tracing/integrations/_category_.json deleted file mode 100644 index 7a1fb1996b..0000000000 --- a/apps/opik-documentation/documentation/docs/tracing/integrations/_category_.json +++ /dev/null @@ -1,7 +0,0 @@ -{ - "label": "Integrations", - "position": 5, - "link": { - "type": "generated-index" - } -} diff --git a/apps/opik-documentation/documentation/docs/tracing/integrations/deepseek.mdx b/apps/opik-documentation/documentation/docs/tracing/integrations/deepseek.mdx deleted file mode 100644 index 5fccfd8203..0000000000 --- a/apps/opik-documentation/documentation/docs/tracing/integrations/deepseek.mdx +++ /dev/null @@ -1,141 +0,0 @@ ---- -sidebar_label: DeepSeek -description: Describes how to track DeepSeek LLM calls using Opik -pytest_codeblocks_skip: false ---- - -import Tabs from "@theme/Tabs"; -import TabItem from "@theme/TabItem"; - -# Deepseek - -Deepseek is an Open-Source LLM model that rivals o1 from OpenAI. You can learn more about DeepSeek on [Github](https://github.com/deepseek-ai/DeepSeek-R1) or -on [deepseek.com](https://www.deepseek.com/). - -In this guide, we will showcase how to track DeepSeek calls using Opik. As DeepSeek is open-source, there are many way to run and call the model. We will focus on how to integrate Opik with the following hosting options: - -1. DeepSeek API -2. Fireworks AI API -3. Together AI API - -## Getting started - -### Configuring your hosting provider - -Before you can start tracking DeepSeek calls, you need to get the API key from your hosting provider. - - - - -In order to use the DeepSeek API, you will need to have an API key. You can register for an account on [DeepSeek.com](https://chat.deepseek.com/sign_up). -Once you have signed up, you can register for an API key. - - - - -You can log into Fireworks AI on [fireworks.ai](https://fireworks.ai/). You can then access your API key on the [API keys](https://fireworks.ai/account/api-keys) page. - - - - -You can log into Together AI on [together.ai](https://together.ai/). You can then access your API key on the [API keys](https://api.together.ai/settings/api-keys) page. - - - - -### Configuring Opik - -```bash -pip install --upgrade --quiet opik - -opik configure -``` - -:::tip -Opik is fully open-source and can be run locally or through the Opik Cloud platform. You can learn more about hosting Opik on your own infrastructure in the [self-hosting guide](/docs/self-host/overview.md). -::: - -## Tracking DeepSeek calls - -The easiest way to call DeepSeek with Opik is to use the OpenAI Python SDK and the `track_openai` decorator. This approach is compatible with the DeepSeek API, Fireworks AI API and Together AI API: - - - - -```python -from opik.integrations.openai import track_openai -from openai import OpenAI - -# Create the OpenAI client that points to DeepSeek API -client = OpenAI(api_key="", base_url="https://api.deepseek.com") - -# Wrap your OpenAI client to track all calls to Opik -client = track_openai(client) - -# Call the API -response = client.chat.completions.create( - model="deepseek-chat", - messages=[ - {"role": "system", "content": "You are a helpful assistant"}, - {"role": "user", "content": "Hello"}, - ], - stream=False -) - -print(response.choices[0].message.content) -``` - - - - -```python -from opik.integrations.openai import track_openai -from openai import OpenAI - -# Create the OpenAI client that points to DeepSeek API -client = OpenAI(api_key="", base_url="https://api.fireworks.ai/inference/v1") - -# Wrap your OpenAI client to track all calls to Opik -client = track_openai(client) - -# Call the API -response = client.chat.completions.create( - model="accounts/fireworks/models/deepseek-v3", - messages=[ - {"role": "system", "content": "You are a helpful assistant"}, - {"role": "user", "content": "Hello"}, - ], - stream=False -) - -print(response.choices[0].message.content) -``` - - - - -```python -from opik.integrations.openai import track_openai -from openai import OpenAI - -# Create the OpenAI client that points to Together AI API -client = OpenAI(api_key="", base_url="https://api.together.xyz/v1") - -# Wrap your OpenAI client to track all calls to Opik -client = track_openai(client) - -# Call the API -response = client.chat.completions.create( - model="deepseek-ai/DeepSeek-R1", - messages=[ - {"role": "system", "content": "You are a helpful assistant"}, - {"role": "user", "content": "Hello"}, - ], - stream=False -) - -print(response.choices[0].message.content) -``` - - - diff --git a/apps/opik-documentation/documentation/docs/tracing/integrations/overview.md b/apps/opik-documentation/documentation/docs/tracing/integrations/overview.md deleted file mode 100644 index 3858931938..0000000000 --- a/apps/opik-documentation/documentation/docs/tracing/integrations/overview.md +++ /dev/null @@ -1,31 +0,0 @@ ---- -sidebar_label: Overview -description: Describes all the integrations provided by Opik and what each framework can be used for ---- - -# Overview - -Opik aims to make it as easy as possible to log, view and evaluate your LLM traces. We do this by providing a set of integrations: - -| Integration | Description | Documentation | Try in Colab | -| ----------- | ---------------------------------------------------------------------------- | ------------------------------------------------------- | ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | -| OpenAI | Log traces for all OpenAI LLM calls | [Documentation](/tracing/integrations/openai.md) | [![Open Quickstart In Colab](https://colab.research.google.com/assets/colab-badge.svg)](https://colab.research.google.com/github/comet-ml/opik/blob/master/apps/opik-documentation/documentation/docs/cookbook/openai.ipynb) | -| LiteLLM | Call any LLM model using the OpenAI format | [Documentation](/tracing/integrations/litellm.md) | [![Open Quickstart In Colab](https://colab.research.google.com/assets/colab-badge.svg)](https://colab.research.google.com/github/comet-ml/opik/blob/master/apps/opik-documentation/documentation/docs/cookbook/litellm.ipynb) | -| LangChain | Log traces for all LangChain LLM calls | [Documentation](/tracing/integrations/langchain.md) | [![Open Quickstart In Colab](https://colab.research.google.com/assets/colab-badge.svg)](https://colab.research.google.com/github/comet-ml/opik/blob/master/apps/opik-documentation/documentation/docs/cookbook/langchain.ipynb) | -| Haystack | Log traces for all Haystack pipelines | [Documentation](/tracing/integrations/haystack.md) | [![Open Quickstart In Colab](https://colab.research.google.com/assets/colab-badge.svg)](https://colab.research.google.com/github/comet-ml/opik/blob/master/apps/opik-documentation/documentation/docs/cookbook/haystack.ipynb) | -| aisuite | Log traces for all aisuite LLM calls | [Documentation](/tracing/integrations/aisuite.md) | [![Open Quickstart In Colab](https://colab.research.google.com/assets/colab-badge.svg)](https://colab.research.google.com/github/comet-ml/opik/blob/master/apps/opik-documentation/documentation/docs/cookbook/aisuite.ipynb) | -| Anthropic | Log traces for all Anthropic LLM calls | [Documentation](/tracing/integrations/anthropic.md) | [![Open Quickstart In Colab](https://colab.research.google.com/assets/colab-badge.svg)](https://colab.research.google.com/github/comet-ml/opik/blob/master/apps/opik-documentation/documentation/docs/cookbook/anthropic.ipynb) | -| Bedrock | Log traces for all AWS Bedrock LLM calls | [Documentation](/tracing/integrations/bedrock.md) | [![Open Quickstart In Colab](https://colab.research.google.com/assets/colab-badge.svg)](https://colab.research.google.com/github/comet-ml/opik/blob/master/apps/opik-documentation/documentation/docs/cookbook/bedrock.ipynb) | -| CrewAI | Log traces for all CrewAI LLM calls | [Documentation](/tracing/integrations/crewai.md) | [![Open Quickstart In Colab](https://colab.research.google.com/assets/colab-badge.svg)](https://colab.research.google.com/github/comet-ml/opik/blob/master/apps/opik-documentation/documentation/docs/cookbook/crewai.ipynb) | -| DeepSeek | Log traces for all LLM calls made with DeepSeek | [Documentation](/tracing/integrations/deepseek.mdx) | | -| Dify | Log traces and LLM calls for your Dify Apps | [Documentation](/tracing/integrations/dify.mdx) | | -| DSPy | Log traces for all DSPy runs | [Documentation](/tracing/integrations/dspy.md) | [![Open Quickstart In Colab](https://colab.research.google.com/assets/colab-badge.svg)](https://colab.research.google.com/github/comet-ml/opik/blob/master/apps/opik-documentation/documentation/docs/cookbook/dspy.ipynb) | -| Guardrails | Log traces for all Guardrails validations | [Documentation](/tracing/integrations/guardrails-ai.md) | [![Open Quickstart In Colab](https://colab.research.google.com/assets/colab-badge.svg)](https://colab.research.google.com/github/comet-ml/opik/blob/master/apps/opik-documentation/documentation/docs/cookbook/guardrails-ai.ipynb) | -| LangGraph | Log traces for all LangGraph executions | [Documentation](/tracing/integrations/langgraph.md) | [![Open Quickstart In Colab](https://colab.research.google.com/assets/colab-badge.svg)](https://colab.research.google.com/github/comet-ml/opik/blob/master/apps/opik-documentation/documentation/docs/cookbook/langgraph.ipynb) | -| LlamaIndex | Log traces for all LlamaIndex LLM calls | [Documentation](/tracing/integrations/llama_index.md) | [![Open Quickstart In Colab](https://colab.research.google.com/assets/colab-badge.svg)](https://colab.research.google.com/github/comet-ml/opik/blob/master/apps/opik-documentation/documentation/docs/cookbook/llama-index.ipynb) | -| Ollama | Log traces for all Ollama LLM calls | [Documentation](/tracing/integrations/ollama.md) | [![Open Quickstart In Colab](https://colab.research.google.com/assets/colab-badge.svg)](https://colab.research.google.com/github/comet-ml/opik/blob/master/apps/opik-documentation/documentation/docs/cookbook/ollama.ipynb) | -| Predibase | Fine-tune and serve open-source LLMs | [Documentation](/tracing/integrations/predibase.md) | [![Open Quickstart In Colab](https://colab.research.google.com/assets/colab-badge.svg)](https://colab.research.google.com/github/comet-ml/opik/blob/master/apps/opik-documentation/documentation/docs/cookbook/predibase.ipynb) | -| Ragas | Evaluation framework for your Retrieval Augmented Generation (RAG) pipelines | [Documentation](/tracing/integrations/ragas.md) | [![Open Quickstart In Colab](https://colab.research.google.com/assets/colab-badge.svg)](https://colab.research.google.com/github/comet-ml/opik/blob/master/apps/opik-documentation/documentation/docs/cookbook/ragas.ipynb) | -| watsonx | Log traces for all watsonx LLM calls | [Documentation](/tracing/integrations/watsonx.md) | [![Open Quickstart In Colab](https://colab.research.google.com/assets/colab-badge.svg)](https://colab.research.google.com/github/comet-ml/opik/blob/master/apps/opik-documentation/documentation/docs/cookbook/watsonx.ipynb) | - -If you would like to see more integrations, please open an issue on our [GitHub repository](https://github.com/comet-ml/opik/issues/new/choose). diff --git a/apps/opik-documentation/documentation/docusaurus.config.ts b/apps/opik-documentation/documentation/docusaurus.config.ts deleted file mode 100644 index 51d7217719..0000000000 --- a/apps/opik-documentation/documentation/docusaurus.config.ts +++ /dev/null @@ -1,179 +0,0 @@ -import { themes as prismThemes } from "prism-react-renderer"; -import type { Config } from "@docusaurus/types"; -import type * as Preset from "@docusaurus/preset-classic"; -import type * as OpenApiPlugin from "docusaurus-plugin-openapi-docs"; -import "dotenv/config"; - -const SEGMENT_WRITE_KEY = process.env.SEGMENT_WRITE_KEY || ""; - -const config: Config = { - title: "Opik Documentation", - tagline: "Open source LLM evaluation platform", - favicon: "img/favicon.ico", - - // Set the production url of your site here - url: "https://www.comet.com", - - // Set the // pathname under which your site is served - // For GitHub pages deployment, it is often '//' - baseUrl: "/docs/opik/", - - // GitHub pages deployment config. - // If you aren't using GitHub pages, you don't need these. - organizationName: "comet-ml", // Usually your GitHub org/user name. - projectName: "opik", // Usually your repo name. - - onBrokenLinks: "warn", - onBrokenMarkdownLinks: "warn", - - // Even if you don't use internationalization, you can use this field to set - // useful metadata like html lang. For example, if your site is Chinese, you - // may want to replace "en" with "zh-Hans". - i18n: { - defaultLocale: "en", - locales: ["en"], - }, - - markdown: { - format: "detect", - }, - - themes: ["docusaurus-theme-openapi-docs"], - - presets: [ - [ - "classic", - { - docs: { - sidebarPath: "./sidebars.ts", - routeBasePath: "/", - docItemComponent: "@theme/ApiItem", - }, - blog: false, - theme: { - customCss: require.resolve("./src/css/custom.scss"), - }, - } satisfies Preset.Options, - ], - ], - - plugins: [ - "docusaurus-plugin-sass", - [ - "docusaurus-plugin-llms-txt", - { - title: "Opik documentation", - description: - "Opik is an open source LLM evaluation platform that includes a prompt playground, automated evaluation metrics, and a LLM gateway.", - fullLLMsTxt: true, - }, - ], - [ - require.resolve("docusaurus-plugin-search-local"), - { - hashed: true, - indexPages: true, - searchResultLimits: 25, - docsRouteBasePath: "/docs/opik", - }, - ], - [ - "@docusaurus/plugin-client-redirects", - { - redirects: [ - { - to: "/self-host/overview", - from: ["/self-host/self_hosting_opik"], - }, - { - to: "/prompt_engineering/playground", - from: ["/evaluation/playground"], - }, - { - to: "/prompt_engineering/prompt_management", - from: ["/library/prompt_management"], - }, - { - to: "/prompt_engineering/managing_prompts_in_code", - from: ["/library/managing_prompts_in_code"], - }, - ], - }, - ], - [ - "docusaurus-plugin-openapi-docs", - { - id: "api", - docsPluginId: "classic", - config: { - opik: { - specPath: "rest_api/opik.yaml", - outputDir: "docs/reference/rest_api", - hideSendButton: true, - sidebarOptions: { - groupPathsBy: "tag", - }, - } satisfies OpenApiPlugin.Options, - }, - }, - ], - ], - - customFields: { - segmentWriteKey: SEGMENT_WRITE_KEY, - }, - - themeConfig: { - // Replace with your project's social card - // image: 'img/docusaurus-social-card.jpg', - navbar: { - title: "Comet Opik", - items: [ - { - type: "docSidebar", - to: "/", - label: "Guides", - sidebarId: "guide_sidebar", - position: "left", - docId: "home", - }, - { - type: "docSidebar", - to: "/reference/rest_api", - label: "REST API", - sidebarId: "rest_api", - position: "left", - }, - { - to: process.env.NODE_ENV === "development" ? "http://localhost:8000" : "/python-sdk-reference", - label: "Python SDK reference docs", - position: "left", - className: "header-external-link", - "aria-label": "Python SDK reference docs", - target: "_blank", - }, - ], - }, - - prism: { - theme: prismThemes.github, - darkTheme: prismThemes.dracula, - additionalLanguages: ["bash"], - }, - - languageTabs: [ - { - tabName: "cURL", - highlight: "bash", - language: "curl", - }, - { - tabName: "Python", - highlight: "python", - language: "python", - }, - ], - } satisfies Preset.ThemeConfig, -}; - -export default config; diff --git a/apps/opik-documentation/documentation/fern/docs.yml b/apps/opik-documentation/documentation/fern/docs.yml new file mode 100644 index 0000000000..ca74054693 --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs.yml @@ -0,0 +1,373 @@ +instances: + - url: https://opik.docs.buildwithfern.com/docs/opik +favicon: img/logo.svg +layout: + searchbar-placement: header + tabs-placement: header +colors: + accent-primary: + light: "#2e8555" + dark: "#166534" + background: + light: "#FFFFFF" + dark: "#0b0d0e" +logo: + light: img/opik-logo.svg + dark: img/logo-dark-mode.svg + href: null + height: 28 +navbar-links: + - type: minimal + text: "Github" + href: "https://github.com/comet-ml/opik" + - type: filled + text: "Go to App" + href: "https://www.comet.com/opik" +tabs: + documentation: + display-name: Documentation + icon: fa-regular fa-building + slug: / + self-host: + display-name: Self-hosting Opik + icon: fa-regular fa-server + slug: /self-host + cookbook: + display-name: Cookbooks + icon: fa-regular fa-book + slug: /cookbook + reference: + display-name: SDK and API reference + icon: fa-regular fa-square-terminal + slug: /reference +navigation: + - tab: documentation + layout: + - section: Getting Started + slug: / + contents: + - page: Home + path: docs/home.mdx + slug: / + icon: fa-regular fa-house + - page: Quickstart + path: docs/quickstart.mdx + slug: /quickstart + icon: fa-regular fa-bolt + - page: Roadmap + path: docs/roadmap.mdx + slug: roadmap + icon: fa-regular fa-map + - page: FAQ + path: docs/faq.mdx + slug: faq + icon: fa-regular fa-question + - changelog: docs/changelog + title: Changelog + slug: changelog + icon: fa-regular fa-calendar + - section: Observability + slug: /tracing + contents: + - page: Log traces + path: docs/tracing/log_traces.mdx + slug: log_traces + - page: Log agents + path: docs/tracing/log_agents.mdx + slug: log_agents + - page: Log multimodal traces + path: docs/tracing/log_multimodal_traces.mdx + slug: log_multimodal_traces + - page: Log distributed traces + path: docs/tracing/log_distributed_traces.mdx + slug: log_distributed_traces + - page: Annotate traces + path: docs/tracing/annotate_traces.mdx + slug: annotate_traces + - page: Cost tracking + path: docs/tracing/cost_tracking.mdx + slug: cost_tracking + - page: SDK configuration + path: docs/tracing/sdk_configuration.mdx + slug: sdk_configuration + - page: Export data + path: docs/tracing/export_data.mdx + slug: export_data + - section: Integrations + slug: /integrations + contents: + - page: Overview + path: docs/tracing/integrations/overview.mdx + slug: overview + - page: OpenAI + path: docs/tracing/integrations/openai.mdx + slug: openai + - page: OpenRouter + path: docs/tracing/integrations/openrouter.mdx + slug: openrouter + - page: LiteLLM + path: docs/tracing/integrations/litellm.mdx + slug: litellm + - page: Langchain + path: docs/tracing/integrations/langchain.mdx + slug: langchain + - page: AIsuite + path: docs/tracing/integrations/aisuite.mdx + slug: aisuite + - page: Anthropic + path: docs/tracing/integrations/anthropic.mdx + slug: anthropic + - page: Bedrock + path: docs/tracing/integrations/bedrock.mdx + slug: bedrock + - page: Crewai + path: docs/tracing/integrations/crewai.mdx + slug: crewai + - page: Dify + path: docs/tracing/integrations/dify.mdx + slug: dify + - page: DSPY + path: docs/tracing/integrations/dspy.mdx + slug: dspy + - page: Gemini + path: docs/tracing/integrations/gemini.mdx + slug: gemini + - page: Groq + path: docs/tracing/integrations/groq.mdx + slug: groq + - page: Guardrails AI + path: docs/tracing/integrations/guardrails-ai.mdx + slug: guardrails-ai + - page: Haystack + path: docs/tracing/integrations/haystack.mdx + slug: haystack + - page: LangGraph + path: docs/tracing/integrations/langgraph.mdx + slug: langgraph + - page: Llama Index + path: docs/tracing/integrations/llama_index.mdx + slug: llama_indec + - page: Ollama + path: docs/tracing/integrations/ollama.mdx + slug: ollama + - page: Predibase + path: docs/tracing/integrations/predibase.mdx + slug: predibase + - page: Ragas + path: docs/tracing/integrations/ragas.mdx + slug: ragas + - page: WatsonX + path: docs/tracing/integrations/watsonx.mdx + slug: watsonx + - section: Evaluation + slug: /evaluation + contents: + - page: Overview + path: docs/evaluation/overview.mdx + slug: overview + - page: Concepts + path: docs/evaluation/concepts.mdx + slug: concepts + - page: Evaluate prompts + path: docs/evaluation/evaluate_prompt.mdx + slug: evaluate_prompt + - page: Evaluate your LLM application + path: docs/evaluation/evaluate_your_llm.mdx + slug: evaluate_your_llm + - page: Update existing experiment + path: docs/evaluation/update_existing_experiment.mdx + slug: update_existing_experiment + - page: Manage datasets + path: docs/evaluation/manage_datasets.mdx + slug: manage_datasets + - section: Metrics + slug: /metrics + contents: + - page: Overview + path: docs/evaluation/metrics/overview.mdx + slug: overview + - page: Heuristic metrics + path: docs/evaluation/metrics/heuristic_metrics.mdx + slug: heuristic_metrics + - page: Hallucination + path: docs/evaluation/metrics/hallucination.mdx + slug: hallucination + - page: G-Eval + path: docs/evaluation/metrics/g_eval.mdx + slug: g_eval + - page: Moderation + path: docs/evaluation/metrics/moderation.mdx + slug: moderation + - page: Usefulness + path: docs/evaluation/metrics/usefulness.mdx + slug: usefulness + - page: Answer relevance + path: docs/evaluation/metrics/answer_relevance.mdx + slug: answer_relevance + - page: Context precision + path: docs/evaluation/metrics/context_precision.mdx + slug: context_precision + - page: Context recall + path: docs/evaluation/metrics/context_recall.mdx + slug: context_recall + - page: Custom model + path: docs/evaluation/metrics/custom_model.mdx + slug: custom_model + - page: Custom metric + path: docs/evaluation/metrics/custom_metric.mdx + slug: custom_metric + - section: Prompt engineering + slug: /prompt_engineering + contents: + - page: Prompt management + path: docs/prompt_engineering/prompt_management.mdx + slug: prompt_management + - page: Managing prompts in code + path: docs/prompt_engineering/managing_prompts_in_code.mdx + slug: managing_prompts_in_code + - page: Playground + path: docs/prompt_engineering/playground.mdx + slug: playground + - section: Testing + slug: /testing + contents: + - page: Pytest integration + path: docs/testing/pytest_integration.mdx + slug: pytest_integration + - section: Production + slug: /production + contents: + - page: Production monitoring + path: docs/production/production_monitoring.mdx + slug: /production_monitoring + - page: Rules + path: docs/production/rules.mdx + slug: rules + - page: Gateway + path: docs/production/gateway.mdx + slug: gateway + - tab: self-host + layout: + - page: Overview + path: docs/self-host/overview.mdx + slug: overview + - page: Local deployment + path: docs/self-host/local_deployment.mdx + slug: local_deployment + - page: Kubernetes deployment + path: docs/self-host/kubernetes.mdx + slug: kubernetes + - page: Platform Architecture + path: docs/self-host/architecture.mdx + slug: architecture + - section: Configuration + slug: /configure + contents: + - page: Anonymous usage statistics + path: docs/self-host/configure/anonymous_usage_statistics.mdx + slug: anonymous_usage_statistics + - tab: cookbook + layout: + - page: Overview + path: docs/cookbook/overview.mdx + - section: Getting started tutorials + slug: / + contents: + - page: Quickstart notebook + path: docs/cookbook/quickstart_notebook.mdx + slug: quickstart_notebook + - section: Integrations + slug: / + contents: + - page: OpenAI + path: docs/cookbook/openai.mdx + slug: openai + - page: LiteLLM + path: docs/cookbook/litellm.mdx + slug: litellm + - page: Langchain + path: docs/cookbook/langchain.mdx + slug: langchain + - page: aisuite + path: docs/cookbook/aisuite.mdx + slug: aisuite + - page: Anthropic + path: docs/cookbook/anthropic.mdx + slug: anthropic + - page: Bedrock + path: docs/cookbook/bedrock.mdx + slug: bedrock + - page: Crewai + path: docs/cookbook/crewai.mdx + slug: crewai + - page: DSPY + path: docs/cookbook/dspy.mdx + slug: dspy + - page: Gemini + path: docs/cookbook/gemini.mdx + slug: gemini + - page: Groq + path: docs/cookbook/groq.mdx + slug: groq + - page: Guardrails AI + path: docs/cookbook/guardrails-ai.mdx + slug: guardrails-ai + - page: Haystack + path: docs/cookbook/haystack.mdx + slug: haystack + - page: LangGraph + path: docs/cookbook/langgraph.mdx + slug: langgraph + - page: Llama Index + path: docs/cookbook/llama-index.mdx + slug: llama-index + - page: Ollama + path: docs/cookbook/ollama.mdx + slug: ollama + - page: Predibase + path: docs/cookbook/predibase.mdx + slug: predibase + - page: Ragas + path: docs/cookbook/ragas.mdx + slug: ragas + - page: WatsonX + path: docs/cookbook/watsonx.mdx + slug: watsonx + - section: Advanced + slug: / + contents: + - page: Evaluate hallucination metric + path: docs/cookbook/evaluate_hallucination_metric.mdx + slug: evaluate_hallucination_metric + - page: Evaluate moderation metric + path: docs/cookbook/evaluate_moderation_metric.mdx + slug: evaluate_moderation_metric + - tab: reference + layout: + - page: Overview + path: docs/reference/overview.mdx + slug: overview + - section: Python SDK + slug: python-sdk + contents: + - link: Reference + href: https://www.comet.com/docs/opik/python-sdk-reference/ + - section: Typescript SDK + slug: typescript-sdk + contents: + - page: Overview + path: docs/reference/typescript-sdk/overview.mdx + slug: overview + - section: Rest API + slug: rest-api + contents: + - page: Overview + path: docs/reference/rest-api/overview.mdx + slug: overview + - api: API Reference + slug: / + display-errors: true +redirects: + - source: "/docs/opik/playground" + destination: "/docs/opik/prompt_engineering/playground" + permanent: true diff --git a/apps/opik-documentation/documentation/fern/docs/changelog/01-06-25.mdx b/apps/opik-documentation/documentation/fern/docs/changelog/01-06-25.mdx new file mode 100644 index 0000000000..cb40c60103 --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs/changelog/01-06-25.mdx @@ -0,0 +1,7 @@ +**Opik Dashboard**: + +- Fixed an issue with the trace viewer in Safari + +**SDK**: + +- Added a new `py.typed` file to the SDK to make it compatible with mypy diff --git a/apps/opik-documentation/documentation/fern/docs/changelog/01-13-25.mdx b/apps/opik-documentation/documentation/fern/docs/changelog/01-13-25.mdx new file mode 100644 index 0000000000..4bfa609ac9 --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs/changelog/01-13-25.mdx @@ -0,0 +1,16 @@ +**Opik Dashboard**: + +- Datasets are now supported in the playground allowing you to quickly evaluate prompts on multiple samples +- Updated the models supported in the playground +- Updated the quickstart guides to include all the supported integrations +- Fix issue that means traces with text inputs can't be added to datasets +- Add the ability to edit dataset descriptions in the UI +- Released [online evaluation](/production/rules) rules - You can now define LLM as a Judge metrics that will automatically score all, or a subset, of your production traces. + +![Online evaluation](/img/changelog/2025-01-13/online_evaluation.gif) + +**SDK**: + +- New integration with [CrewAI](/tracing/integrations/crewai) +- Released a new `evaluate_prompt` method that simplifies the evaluation of simple prompts templates +- Added Sentry to the Python SDK so we can more easily diff --git a/apps/opik-documentation/documentation/fern/docs/changelog/01-20-25.mdx b/apps/opik-documentation/documentation/fern/docs/changelog/01-20-25.mdx new file mode 100644 index 0000000000..da05bd7ba5 --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs/changelog/01-20-25.mdx @@ -0,0 +1,13 @@ +**Opik Dashboard**: + +- Added logs for online evaluation rules so that you can more easily ensure your online evaluation metrics are working as expected +- Added auto-complete support in the variable mapping section of the online evaluation rules modal +- Added support for Anthropic models in the playground +- Experiments are now created when using datasets in the playground +- Improved the Opik home page +- Updated the code snippets in the quickstart to make them easier to understand + +**SDK**: + +- Improved support for litellm completion kwargs +- LiteLLM required version is now relaxed to avoid conflicts with other Python packages diff --git a/apps/opik-documentation/documentation/fern/docs/changelog/01-27-25.mdx b/apps/opik-documentation/documentation/fern/docs/changelog/01-27-25.mdx new file mode 100644 index 0000000000..cdf2122f99 --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs/changelog/01-27-25.mdx @@ -0,0 +1,10 @@ +**Opik Dashboard**: + +- Performance improvements for workspaces with 100th of millions of traces +- Added support for cost tracking when using Gemini models +- Allow users to diff prompt + +**SDK**: + +- Fixed the `evaluate` and `evaluate_*` functions to better support event loops, particularly useful when using Ragas metrics +- Added support for Bedrock `invoke_agent` API diff --git a/apps/opik-documentation/documentation/fern/docs/changelog/02-03-25.mdx b/apps/opik-documentation/documentation/fern/docs/changelog/02-03-25.mdx new file mode 100644 index 0000000000..91481f53d1 --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs/changelog/02-03-25.mdx @@ -0,0 +1,18 @@ +**Opik Dashboard**: + +- You can now view feedback scores for your projects in the Opik home page +- Added line highlights in the quickstart page +- Allow users to download experiments as CSV and JSON files for further analysis + +**Python SDK**: + +- Update the `evaluate_*` methods so feedback scores are logged after they computed rather than at the end of an experiment as previously +- Released a new [usefulness metric](/evaluation/metrics/usefulness) +- Do not display warning messages about missing API key when Opik logging is disabled +- Add method to list datasets in a workspace +- Add method to list experiments linked to a dataset + +**JS / TS SDK**: + +- Official release of the first version of the SDK - Learn more [here](/tracing/log_traces#logging-with-the-js--ts-sdk) +- Support logging traces using the low-level Opik client and an experimental decorator. diff --git a/apps/opik-documentation/documentation/fern/docs/changelog/02-10-25.mdx b/apps/opik-documentation/documentation/fern/docs/changelog/02-10-25.mdx new file mode 100644 index 0000000000..de6a8f8c19 --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs/changelog/02-10-25.mdx @@ -0,0 +1,7 @@ +**Python SDK**: + +- Improved the `@track` decorator to better support nested generators. +- Added a new `Opik.copy_traces(project_name, destination_project_name)` method to copy traces + from one project to another. +- Added support for searching for traces that have feedback scores with spaces in their name. +- Improved the LangChain and LangGraph integrations diff --git a/apps/opik-documentation/documentation/fern/docs/changelog/09-30-24.mdx b/apps/opik-documentation/documentation/fern/docs/changelog/09-30-24.mdx new file mode 100644 index 0000000000..e1c8197d5e --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs/changelog/09-30-24.mdx @@ -0,0 +1,10 @@ +**Opik Dashboard**: + +- Added option to delete experiments from the UI +- Updated empty state for projects with no traces +- Removed tooltip delay for the reason icon in the feedback score components + +**SDK:** + +- Introduced new `get_or_create_dataset` method to the `opik.Opik` client. This method will create a new dataset if it does not exist. +- When inserting items into a dataset, duplicate items are now silently ignored instead of being ingested. diff --git a/apps/opik-documentation/documentation/fern/docs/changelog/10-07-24.mdx b/apps/opik-documentation/documentation/fern/docs/changelog/10-07-24.mdx new file mode 100644 index 0000000000..5fc09d6b61 --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs/changelog/10-07-24.mdx @@ -0,0 +1,12 @@ +**Opik Dashboard**: + +- Added `Updated At` column in the project page +- Added support for filtering by token usage in the trace page + +**SDK:** + +- Added link to the trace project when traces are logged for the first time in a session +- Added link to the experiment page when calling the `evaluate` method +- Added `project_name` parameter in the `opik.Opik` client and `opik.track` decorator +- Added a new `nb_samples` parameter in the `evaluate` method to specify the number of samples to use for the evaluation +- Released the LiteLLM integration diff --git a/apps/opik-documentation/documentation/fern/docs/changelog/10-14-24.mdx b/apps/opik-documentation/documentation/fern/docs/changelog/10-14-24.mdx new file mode 100644 index 0000000000..323a6fef7c --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs/changelog/10-14-24.mdx @@ -0,0 +1,11 @@ +**Opik Dashboard**: + +- Fix handling of large experiment names in breadcrumbs and popups +- Add filtering options for experiment items in the experiment page + + + + +**SDK:** + +- Allow users to configure the project name in the LangChain integration diff --git a/apps/opik-documentation/documentation/fern/docs/changelog/10-18-24.mdx b/apps/opik-documentation/documentation/fern/docs/changelog/10-18-24.mdx new file mode 100644 index 0000000000..1b97eab2e8 --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs/changelog/10-18-24.mdx @@ -0,0 +1,11 @@ +**Opik Dashboard**: + +- Added a new `Feedback modal` in the UI so you can easily provide feedback on any parts of the platform. + +**SDK**: + +- Released new evaluation metric: [GEval](/evaluation/metrics/g_eval) - This LLM as a Judge metric is task agnostic and can be used to evaluate any LLM call based on your own custom evaluation criteria. +- Allow users to specify the path to the Opik configuration file using the `OPIK_CONFIG_PATH` environment variable, read more about it in the [Python SDK Configuration guide](/tracing/sdk_configuration#using-a-configuration-file). +- You can now configure the `project_name` as part of the `evaluate` method so that traces are logged to a specific project instead of the default one. +- Added a new `Opik.search_traces` method to search for traces, this includes support for a search string to return only specific traces. +- Enforce structured outputs for LLM as a Judge metrics so that they are more reliable (they will no longer fail when decoding the LLM response). diff --git a/apps/opik-documentation/documentation/fern/docs/changelog/10-21-24.mdx b/apps/opik-documentation/documentation/fern/docs/changelog/10-21-24.mdx new file mode 100644 index 0000000000..ef8d77f950 --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs/changelog/10-21-24.mdx @@ -0,0 +1,33 @@ +**Opik Dashboard**: + +- Added the option to download traces and LLM calls as CSV files from the UI: + + + +- Introduce a new quickstart guide to help you get started: + + + +- Updated datasets to support more flexible data schema, you can now insert items with any key value pairs and not just `input` and `expected_output`. See more in the SDK section below. +- Multiple small UX improvements (more informative empty state for projects, updated icons, feedback tab in the experiment page, etc). +- Fix issue with `\t` characters breaking the YAML code block in the traces page. + +**SDK**: + +- Datasets now support more flexible data schema, we now support inserting items with any key value pairs: + + ```python + import opik + + client = opik.Opik() + dataset = client.get_or_create_dataset(name="Demo Dataset") + dataset.insert([ + {"user_question": "Hello, what can you do ?", "expected_output": {"assistant_answer": "I am a chatbot assistant that can answer questions and help you with your queries!"}}, + {"user_question": "What is the capital of France?", "expected_output": {"assistant_answer": "Paris"}}, + ]) + ``` + +- Released WatsonX, Gemini and Groq integration based on the LiteLLM integration. +- The `context` field is now optional in the [Hallucination](/tracing/integrations/overview) metric. +- LLM as a Judge metrics now support customizing the LLM provider by specifying the `model` parameter. See more in the [Customizing LLM as a Judge metrics](/evaluation/metrics/overview#customizing-llm-as-a-judge-metrics) section. +- Fixed an issue when updating feedback scores using the `update_current_span` and `update_current_trace` methods. See this Github issue for more details. diff --git a/apps/opik-documentation/documentation/fern/docs/changelog/11-04-24.mdx b/apps/opik-documentation/documentation/fern/docs/changelog/11-04-24.mdx new file mode 100644 index 0000000000..0dc4189032 --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs/changelog/11-04-24.mdx @@ -0,0 +1,12 @@ +**Opik Dashboard**: + +- Added a new `Prompt library` page to manage your prompts in the UI. + + + + +**SDK**: + +- Introduced the `Prompt` object in the SDK to manage prompts stored in the library. See the [Prompt Management](/prompt_engineering/managing_prompts_in_code) guide for more details. +- Introduced a `Opik.search_spans` method to search for spans in a project. See the [Search spans](/tracing/export_data#exporting-spans) guide for more details. +- Released a new integration with [AWS Bedrock](/tracing/integrations/bedrock) for using Opik with Bedrock models. diff --git a/apps/opik-documentation/documentation/fern/docs/changelog/11-11-24.mdx b/apps/opik-documentation/documentation/fern/docs/changelog/11-11-24.mdx new file mode 100644 index 0000000000..a1ee3791ab --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs/changelog/11-11-24.mdx @@ -0,0 +1,36 @@ +**Opik Dashboard**: + +- Added the option to sort the projects table by `Last updated`, `Created at` and `Name` columns. +- Updated the logic for displaying images, instead of relying on the format of the response, we now use regex rules to detect if the trace or span input includes a base64 encoded image or url. +- Improved performance of the Traces table by truncating trace inputs and outputs if they contain base64 encoded images. +- Fixed some issues with rendering trace input and outputs in YAML format. +- Added grouping and charts to the experiments page: + + + + +**SDK**: + +- **New integration**: Anthropic integration + + ```python + from anthropic import Anthropic, AsyncAnthropic + from opik.integrations.anthropic import track_anthropic + + client = Anthropic() + client = track_anthropic(client, project_name="anthropic-example") + + message = client.messages.create( + max_tokens=1024, + messages=[ + { + "role": "user", + "content": "Tell a fact", + } + ], + model="claude-3-opus-20240229", + ) + print(message) + ``` + +- Added a new `evaluate_experiment` method in the SDK that can be used to re-score an existing experiment, learn more in the [Update experiments](/evaluation/update_existing_experiment) guide. diff --git a/apps/opik-documentation/documentation/fern/docs/changelog/11-18-24.mdx b/apps/opik-documentation/documentation/fern/docs/changelog/11-18-24.mdx new file mode 100644 index 0000000000..bc507beda0 --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs/changelog/11-18-24.mdx @@ -0,0 +1,12 @@ +**Opik Dashboard**: + +- Updated the majority of tables to increase the information density, it is now easier to review many traces at once. +- Images logged to datasets and experiments are now displayed in the UI. Both images urls and base64 encoded images are supported. + +**SDK**: + +- The `scoring_metrics` argument is now optional in the `evaluate` method. This is useful if you are looking at evaluating your LLM calls manually in the Opik UI. +- When uploading a dataset, the SDK now prints a link to the dataset in the UI. +- Usage is now correctly logged when using the LangChain OpenAI integration. +- Implement a batching mechanism for uploading spans and dataset items to avoid `413 Request Entity Too Large` errors. +- Removed pandas and numpy as mandatory dependencies. diff --git a/apps/opik-documentation/documentation/fern/docs/changelog/11-25-24.mdx b/apps/opik-documentation/documentation/fern/docs/changelog/11-25-24.mdx new file mode 100644 index 0000000000..0aec7a9cfe --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs/changelog/11-25-24.mdx @@ -0,0 +1,26 @@ +**Opik Dashboard**: + +- Feedback scores are now displayed as separate columns in the traces and spans table +- Introduce a new project dashboard to see trace count, feedback scores and token count over time. + + + +- Project statistics are now displayed in the traces and spans table header, this is especially useful for tracking the average feedback scores + + + +- Redesigned the experiment item sidebar to make it easier to review experiment results + + + +- Annotating feedback scores in the UI now feels much faster +- Support exporting traces as JSON file in addition to CSV +- Sidebars now close when clicking outside of them +- Dataset groups in the experiment page are now sorted by last updated date +- Updated scrollbar styles for Windows users + +**SDK**: + +- Improved the robustness to connection issues by adding retry logic. +- Updated the OpenAI integration to track structured output calls using `beta.chat.completions.parse`. +- Fixed issue with `update_current_span` and `update_current_trace` that did not support updating the `output` field. diff --git a/apps/opik-documentation/documentation/fern/docs/changelog/12-02-24.mdx b/apps/opik-documentation/documentation/fern/docs/changelog/12-02-24.mdx new file mode 100644 index 0000000000..24816af4f2 --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs/changelog/12-02-24.mdx @@ -0,0 +1,13 @@ +**Opik Dashboard**: + +- Added a new `created_by` column for each table to indicate who created the record +- Mask the API key in the user menu + +**SDK**: + +- Implement background batch sending of traces to speed up processing of trace creation requests +- Updated OpenAI integration to track cost of LLM calls +- Updated `prompt.format` method to raise an error when it is called with the wrong arguments +- Updated the `Opik` method so it accepts the `api_key` parameter as a positional argument +- Improved the prompt template for the `hallucination` metric +- Introduced a new `opik_check_tls_certificate` configuration option to disable the TLS certificate check. diff --git a/apps/opik-documentation/documentation/fern/docs/changelog/12-09-24.mdx b/apps/opik-documentation/documentation/fern/docs/changelog/12-09-24.mdx new file mode 100644 index 0000000000..959afa7aee --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs/changelog/12-09-24.mdx @@ -0,0 +1,13 @@ +**Opik Dashboard**: + +- Updated the experiments pages to make it easier to analyze the results of each experiment. Columns are now organized based on where they came from (dataset, evaluation task, etc) and output keys are now displayed in multiple columns to make it easier to review + + + +- Improved the performance of the experiments so experiment items load faster +- Added descriptions for projects + +**SDK**: + +- Add cost tracking for OpenAI calls made using LangChain +- Fixed a timeout issue when calling `get_or_create_dataset` diff --git a/apps/opik-documentation/documentation/fern/docs/changelog/12-16-24.mdx b/apps/opik-documentation/documentation/fern/docs/changelog/12-16-24.mdx new file mode 100644 index 0000000000..9bb15b32c0 --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs/changelog/12-16-24.mdx @@ -0,0 +1,18 @@ +**Opik Dashboard**: + +- The Opik playground is now in public preview + + + +- You can now view the prompt diff when updating a prompt from the UI +- Errors in traces and spans are now displayed in the UI +- Display agent graphs in the traces sidebar +- Released a new plugin for the [Kong AI Gateway](/production/gateway) + +**SDK**: + +- Added support for serializing Pydantic models passed to decorated functions +- Implemented `get_experiment_by_id` and `get_experiment_by_name` methods +- Scoring metrics are now logged to the traces when using the `evaluate` method +- New integration with [aisuite](/tracing/integrations/aisuite) +- New integration with [Haystack](/tracing/integrations/haystack) diff --git a/apps/opik-documentation/documentation/fern/docs/changelog/12-23-24.mdx b/apps/opik-documentation/documentation/fern/docs/changelog/12-23-24.mdx new file mode 100644 index 0000000000..6e902869ef --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs/changelog/12-23-24.mdx @@ -0,0 +1,7 @@ +**SDK**: + +- Improved error messages when getting a rate limit when using the `evaluate` method +- Added support for a new metadata field in the `Prompt` object, this field is used to store any additional information about the prompt. +- Updated the library used to create uuidv7 IDs +- New Guardrails integration +- New DSPY integration diff --git a/apps/opik-documentation/documentation/fern/docs/changelog/12-30-24.mdx b/apps/opik-documentation/documentation/fern/docs/changelog/12-30-24.mdx new file mode 100644 index 0000000000..6a38b219be --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs/changelog/12-30-24.mdx @@ -0,0 +1,10 @@ +**Opik Dashboard**: + +- Added duration chart to the project dashboard +- Prompt metadata can now be set and viewed in the UI, this can be used to store any additional information about the prompt +- Playground prompts and settings are now cached when you navigate away from the page + +**SDK**: + +- Introduced a new `OPIK_TRACK_DISABLE` environment variable to disable the tracking of traces and spans +- We now log usage information for traces logged using the LlamaIndex integration diff --git a/apps/opik-documentation/documentation/fern/docs/cookbook/aisuite.mdx b/apps/opik-documentation/documentation/fern/docs/cookbook/aisuite.mdx new file mode 100644 index 0000000000..d89ecd1472 --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs/cookbook/aisuite.mdx @@ -0,0 +1,108 @@ +--- +description: Cookbook that showcases Opik's integration with the aisuite Python SDK +--- + +# Using Opik with aisuite + +Opik integrates with aisuite to provide a simple way to log traces for all aisuite LLM calls. + + +## Creating an account on Comet.com + +[Comet](https://www.comet.com/site?from=llm&utm_source=opik&utm_medium=colab&utm_content=openai&utm_campaign=opik) provides a hosted version of the Opik platform, [simply create an account](https://www.comet.com/signup?from=llm&utm_source=opik&utm_medium=colab&utm_content=aisuite&utm_campaign=opik) and grab you API Key. + +> You can also run the Opik platform locally, see the [installation guide](https://www.comet.com/docs/opik/self-host/overview/?from=llm&utm_source=opik&utm_medium=colab&utm_content=aisuite&utm_campaign=opik) for more information. + + +```python +%pip install --upgrade opik "aisuite[openai]" +``` + + +```python +import opik + +opik.configure(use_local=False) +``` + +## Preparing our environment + +First, we will set up our OpenAI API keys. + + +```python +import os +import getpass + +if "OPENAI_API_KEY" not in os.environ: + os.environ["OPENAI_API_KEY"] = getpass.getpass("Enter your OpenAI API key: ") +``` + +## Logging traces + +In order to log traces to Opik, we need to wrap our OpenAI calls with the `track_openai` function: + + +```python +from opik.integrations.aisuite import track_aisuite +import aisuite as ai + +client = track_aisuite(ai.Client(), project_name="aisuite-integration-demo") + +messages = [ + {"role": "user", "content": "Write a short two sentence story about Opik."}, +] + +response = client.chat.completions.create( + model="openai:gpt-4o", messages=messages, temperature=0.75 +) +print(response.choices[0].message.content) +``` + +The prompt and response messages are automatically logged to Opik and can be viewed in the UI. + +![aisuite Integration](https://raw.githubusercontent.com/comet-ml/opik/main/apps/opik-documentation/documentation/static/img/cookbook/aisuite_trace_cookbook.png) + +## Using it with the `track` decorator + +If you have multiple steps in your LLM pipeline, you can use the `track` decorator to log the traces for each step. If OpenAI is called within one of these steps, the LLM call with be associated with that corresponding step: + + +```python +from opik import track +from opik.integrations.aisuite import track_aisuite +import aisuite as ai + +client = track_aisuite(ai.Client(), project_name="aisuite-integration-demo") + + +@track +def generate_story(prompt): + res = client.chat.completions.create( + model="openai:gpt-3.5-turbo", messages=[{"role": "user", "content": prompt}] + ) + return res.choices[0].message.content + + +@track +def generate_topic(): + prompt = "Generate a topic for a story about Opik." + res = client.chat.completions.create( + model="openai:gpt-3.5-turbo", messages=[{"role": "user", "content": prompt}] + ) + return res.choices[0].message.content + + +@track(project_name="aisuite-integration-demo") +def generate_opik_story(): + topic = generate_topic() + story = generate_story(topic) + return story + + +generate_opik_story() +``` + +The trace can now be viewed in the UI: + +![aisuite Integration](https://raw.githubusercontent.com/comet-ml/opik/main/apps/opik-documentation/documentation/static/img/cookbook/aisuite_trace_decorator_cookbook.png) diff --git a/apps/opik-documentation/documentation/fern/docs/cookbook/anthropic.mdx b/apps/opik-documentation/documentation/fern/docs/cookbook/anthropic.mdx new file mode 100644 index 0000000000..a5dc6b1e81 --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs/cookbook/anthropic.mdx @@ -0,0 +1,122 @@ +--- +description: Cookbook that showcases Opik's integration with the Anthropic Python SDK +--- + +# Using Opik with Anthropic + +Opik integrates with Anthropic to provide a simple way to log traces for all Anthropic LLM calls. This works for all supported models, including if you are using the streaming API. + + +## Creating an account on Comet.com + +[Comet](https://www.comet.com/site?from=llm&utm_source=opik&utm_medium=colab&utm_content=anthropic&utm_campaign=opik) provides a hosted version of the Opik platform, [simply create an account](https://www.comet.com/signup?from=llm&utm_source=opik&utm_medium=colab&utm_content=anthropic&utm_campaign=opik) and grab you API Key. + +> You can also run the Opik platform locally, see the [installation guide](https://www.comet.com/docs/opik/self-host/overview/?from=llm&utm_source=opik&utm_medium=colab&utm_content=anthropic&utm_campaign=opik) for more information. + + +```python +%pip install --upgrade opik anthropic +``` + + +```python +import opik + +opik.configure(use_local=False) +``` + +## Preparing our environment + +First, we will set up our anthropic client. You can [find or create your Anthropic API Key in this page page](https://console.anthropic.com/settings/keys) and paste it below: + + +```python +import os +import getpass +import anthropic + +if "ANTHROPIC_API_KEY" not in os.environ: + os.environ["ANTHROPIC_API_KEY"] = getpass.getpass("Enter your Anthropic API key: ") +``` + +## Logging traces + +In order to log traces to Opik, we need to wrap our Anthropic calls with the `track_anthropic` function: + + +```python +import os + +from opik.integrations.anthropic import track_anthropic + +anthropic_client = anthropic.Anthropic() +anthropic_client = track_anthropic(anthropic, project_name="anthropic-integration-demo") +``` + + +```python +PROMPT = "Why is it important to use a LLM Monitoring like CometML Opik tool that allows you to log traces and spans when working with Anthropic LLM Models?" + +response = anthropic_client.messages.create( + model="claude-3-5-sonnet-20241022", + max_tokens=1024, + messages=[{"role": "user", "content": PROMPT}], +) +print("Response", response.content[0].text) +``` + +The prompt and response messages are automatically logged to Opik and can be viewed in the UI. + +![Anthropic Integration](https://raw.githubusercontent.com/comet-ml/opik/main/apps/opik-documentation/documentation/static/img/cookbook/anthropic_trace_cookbook.png) + +## Using it with the `track` decorator + +If you have multiple steps in your LLM pipeline, you can use the `track` decorator to log the traces for each step. If Anthropic is called within one of these steps, the LLM call with be associated with that corresponding step: + + +```python +import anthropic + +from opik import track +from opik.integrations.anthropic import track_anthropic + +os.environ["OPIK_PROJECT_NAME"] = "anthropic-integration-demo" + +anthropic_client = anthropic.Anthropic() +anthropic_client = track_anthropic(anthropic) + + +@track +def generate_story(prompt): + res = anthropic_client.messages.create( + model="claude-3-5-sonnet-20241022", + max_tokens=1024, + messages=[{"role": "user", "content": prompt}], + ) + return res.content[0].text + + +@track +def generate_topic(): + prompt = "Generate a topic for a story about Opik." + res = anthropic_client.messages.create( + model="claude-3-5-sonnet-20241022", + max_tokens=1024, + messages=[{"role": "user", "content": prompt}], + ) + return res.content[0].text + + +@track +def generate_opik_story(): + topic = generate_topic() + story = generate_story(topic) + return story + + +generate_opik_story() +``` + +The trace can now be viewed in the UI: + +![Anthropic Integration](https://raw.githubusercontent.com/comet-ml/opik/main/apps/opik-documentation/documentation/static/img/cookbook/anthropic_trace_decorator_cookbook.png) diff --git a/apps/opik-documentation/documentation/fern/docs/cookbook/bedrock.mdx b/apps/opik-documentation/documentation/fern/docs/cookbook/bedrock.mdx new file mode 100644 index 0000000000..d0550ed7dc --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs/cookbook/bedrock.mdx @@ -0,0 +1,215 @@ +--- +description: Cookbook that showcases Opik's integration with AWS Bedrock +--- + +# Using Opik with AWS Bedrock + +Opik integrates with AWS Bedrock to provide a simple way to log traces for all Bedrock LLM calls. This works for all supported models, including if you are using the streaming API. + + +## Creating an account on Comet.com + +[Comet](https://www.comet.com/site?from=llm&utm_source=opik&utm_medium=colab&utm_content=bedrock&utm_campaign=opik) provides a hosted version of the Opik platform, [simply create an account](https://www.comet.com/signup?from=llm&utm_source=opik&utm_medium=colab&utm_content=bedrock&utm_campaign=opik) and grab you API Key. + +> You can also run the Opik platform locally, see the [installation guide](https://www.comet.com/docs/opik/self-host/overview/?from=llm&utm_source=opik&utm_medium=colab&utm_content=bedrock&utm_campaign=opik) for more information. + + +```python +%pip install --upgrade opik boto3 +``` + + +```python +import opik + +opik.configure(use_local=False) +``` + +## Preparing our environment + +First, we will set up our bedrock client. Uncomment the following lines to pass AWS Credentials manually or [checkout other ways of passing credentials to Boto3](https://boto3.amazonaws.com/v1/documentation/api/latest/guide/credentials.html). You will also need to request access to the model in the UI before being able to generate text, here we are gonna use the Llama 3.2 model, you can request access to it in [this page for the us-east1](https://us-east-1.console.aws.amazon.com/bedrock/home?region=us-east-1#/providers?model=meta.llama3-2-3b-instruct-v1:0) region. + + +```python +import boto3 + +REGION = "us-east-1" + +MODEL_ID = "us.meta.llama3-2-3b-instruct-v1:0" + +bedrock = boto3.client( + service_name="bedrock-runtime", + region_name=REGION, + # aws_access_key_id=ACCESS_KEY, + # aws_secret_access_key=SECRET_KEY, + # aws_session_token=SESSION_TOKEN, +) +``` + +## Logging traces + +In order to log traces to Opik, we need to wrap our Bedrock calls with the `track_bedrock` function: + + +```python +import os + +from opik.integrations.bedrock import track_bedrock + +bedrock_client = track_bedrock(bedrock, project_name="bedrock-integration-demo") +``` + + +```python +PROMPT = "Why is it important to use a LLM Monitoring like CometML Opik tool that allows you to log traces and spans when working with LLM Models hosted on AWS Bedrock?" + +response = bedrock_client.converse( + modelId=MODEL_ID, + messages=[{"role": "user", "content": [{"text": PROMPT}]}], + inferenceConfig={"temperature": 0.5, "maxTokens": 512, "topP": 0.9}, +) +print("Response", response["output"]["message"]["content"][0]["text"]) +``` + +The prompt and response messages are automatically logged to Opik and can be viewed in the UI. + +![Bedrock Integration](https://raw.githubusercontent.com/comet-ml/opik/main/apps/opik-documentation/documentation/static/img/cookbook/bedrock_trace_cookbook.png) + +# Logging traces with streaming + + +```python +def stream_conversation( + bedrock_client, + model_id, + messages, + system_prompts, + inference_config, +): + """ + Sends messages to a model and streams the response. + Args: + bedrock_client: The Boto3 Bedrock runtime client. + model_id (str): The model ID to use. + messages (JSON) : The messages to send. + system_prompts (JSON) : The system prompts to send. + inference_config (JSON) : The inference configuration to use. + additional_model_fields (JSON) : Additional model fields to use. + + Returns: + Nothing. + + """ + + response = bedrock_client.converse_stream( + modelId=model_id, + messages=messages, + system=system_prompts, + inferenceConfig=inference_config, + ) + + stream = response.get("stream") + if stream: + for event in stream: + if "messageStart" in event: + print(f"\nRole: {event['messageStart']['role']}") + + if "contentBlockDelta" in event: + print(event["contentBlockDelta"]["delta"]["text"], end="") + + if "messageStop" in event: + print(f"\nStop reason: {event['messageStop']['stopReason']}") + + if "metadata" in event: + metadata = event["metadata"] + if "usage" in metadata: + print("\nToken usage") + print(f"Input tokens: {metadata['usage']['inputTokens']}") + print(f":Output tokens: {metadata['usage']['outputTokens']}") + print(f":Total tokens: {metadata['usage']['totalTokens']}") + if "metrics" in event["metadata"]: + print(f"Latency: {metadata['metrics']['latencyMs']} milliseconds") + + +system_prompt = """You are an app that creates playlists for a radio station + that plays rock and pop music. Only return song names and the artist.""" + +# Message to send to the model. +input_text = "Create a list of 3 pop songs." + + +message = {"role": "user", "content": [{"text": input_text}]} +messages = [message] + +# System prompts. +system_prompts = [{"text": system_prompt}] + +# inference parameters to use. +temperature = 0.5 +top_p = 0.9 +# Base inference parameters. +inference_config = {"temperature": temperature, "topP": 0.9} + + +stream_conversation( + bedrock_client, + MODEL_ID, + messages, + system_prompts, + inference_config, +) +``` + +![Bedrock Integration](https://raw.githubusercontent.com/comet-ml/opik/main/apps/opik-documentation/documentation/static/img/cookbook/bedrock_trace_streaming_cookbook.png) + +## Using it with the `track` decorator + +If you have multiple steps in your LLM pipeline, you can use the `track` decorator to log the traces for each step. If Bedrock is called within one of these steps, the LLM call with be associated with that corresponding step: + + +```python +from opik import track +from opik.integrations.bedrock import track_bedrock + +bedrock = boto3.client( + service_name="bedrock-runtime", + region_name=REGION, + # aws_access_key_id=ACCESS_KEY, + # aws_secret_access_key=SECRET_KEY, + # aws_session_token=SESSION_TOKEN, +) + +os.environ["OPIK_PROJECT_NAME"] = "bedrock-integration-demo" +bedrock_client = track_bedrock(bedrock) + + +@track +def generate_story(prompt): + res = bedrock_client.converse( + modelId=MODEL_ID, messages=[{"role": "user", "content": [{"text": prompt}]}] + ) + return res["output"]["message"]["content"][0]["text"] + + +@track +def generate_topic(): + prompt = "Generate a topic for a story about Opik." + res = bedrock_client.converse( + modelId=MODEL_ID, messages=[{"role": "user", "content": [{"text": prompt}]}] + ) + return res["output"]["message"]["content"][0]["text"] + + +@track +def generate_opik_story(): + topic = generate_topic() + story = generate_story(topic) + return story + + +generate_opik_story() +``` + +The trace can now be viewed in the UI: + +![Bedrock Integration](https://raw.githubusercontent.com/comet-ml/opik/main/apps/opik-documentation/documentation/static/img/cookbook/bedrock_trace_decorator_cookbook.png) diff --git a/apps/opik-documentation/documentation/fern/docs/cookbook/crewai.mdx b/apps/opik-documentation/documentation/fern/docs/cookbook/crewai.mdx new file mode 100644 index 0000000000..e49ee827f1 --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs/cookbook/crewai.mdx @@ -0,0 +1,111 @@ +--- +description: Cookbook that showcases Opik's integration with the CrewAI +--- + +# Using Opik with CrewAI + +This notebook showcases how to use Opik with CrewAI. [CrewAI](https://github.com/crewAIInc/crewAI) is a cutting-edge framework for orchestrating autonomous AI agents. +> CrewAI enables you to create AI teams where each agent has specific roles, tools, and goals, working together to accomplish complex tasks. + +> Think of it as assembling your dream team - each member (agent) brings unique skills and expertise, collaborating seamlessly to achieve your objectives. + +For this guide we will use CrewAI's quickstart example. + +## Creating an account on Comet.com + +[Comet](https://www.comet.com/site?from=llm&utm_source=opik&utm_medium=colab&utm_content=llamaindex&utm_campaign=opik) provides a hosted version of the Opik platform, [simply create an account](https://www.comet.com/signup?from=llm&=opik&utm_medium=colab&utm_content=llamaindex&utm_campaign=opik) and grab you API Key. + +> You can also run the Opik platform locally, see the [installation guide](https://www.comet.com/docs/opik/self-host/overview/?from=llm&utm_source=opik&utm_medium=colab&utm_content=llamaindex&utm_campaign=opik) for more information. + + +```python +%pip install crewai crewai-tools opik --upgrade +``` + + +```python +import opik + +opik.configure(use_local=False) +``` + +## Preparing our environment + +First, we set up our API keys for our LLM-provider as environment variables: + + +```python +import os +import getpass + +if "OPENAI_API_KEY" not in os.environ: + os.environ["OPENAI_API_KEY"] = getpass.getpass("Enter your OpenAI API key: ") +``` + +## Using CrewAI +The first step is to create our project. We will use an example from CrewAI's documentation: + + +```python +from crewai import Agent, Crew, Task, Process + + +class YourCrewName: + def agent_one(self) -> Agent: + return Agent( + role="Data Analyst", + goal="Analyze data trends in the market", + backstory="An experienced data analyst with a background in economics", + verbose=True, + ) + + def agent_two(self) -> Agent: + return Agent( + role="Market Researcher", + goal="Gather information on market dynamics", + backstory="A diligent researcher with a keen eye for detail", + verbose=True, + ) + + def task_one(self) -> Task: + return Task( + name="Collect Data Task", + description="Collect recent market data and identify trends.", + expected_output="A report summarizing key trends in the market.", + agent=self.agent_one(), + ) + + def task_two(self) -> Task: + return Task( + name="Market Research Task", + description="Research factors affecting market dynamics.", + expected_output="An analysis of factors influencing the market.", + agent=self.agent_two(), + ) + + def crew(self) -> Crew: + return Crew( + agents=[self.agent_one(), self.agent_two()], + tasks=[self.task_one(), self.task_two()], + process=Process.sequential, + verbose=True, + ) +``` + +Now we can import Opik's tracker and run our `crew`: + + +```python +from opik.integrations.crewai import track_crewai + +track_crewai(project_name="crewai-integration-demo") + +my_crew = YourCrewName().crew() +result = my_crew.kickoff() + +print(result) +``` + +You can now go to the Opik app to see the trace: + +![CrewAI trace in Opik](https://raw.githubusercontent.com/comet-ml/opik/main/apps/opik-documentation/documentation/static/img/cookbook/crewai_trace_cookbook.png) diff --git a/apps/opik-documentation/documentation/fern/docs/cookbook/dspy.mdx b/apps/opik-documentation/documentation/fern/docs/cookbook/dspy.mdx new file mode 100644 index 0000000000..2179fc51b5 --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs/cookbook/dspy.mdx @@ -0,0 +1,63 @@ +--- +description: Cookbook that showcases Opik's integration with DSPy +--- + +# Using Opik with DSPy + +[DSPy](https://dspy.ai/) is the framework for programming—rather than prompting—language models. + +In this guide, we will showcase how to integrate Opik with DSPy so that all the DSPy calls are logged as traces in Opik. + +## Creating an account on Comet.com + +[Comet](https://www.comet.com/site?from=llm&utm_source=opik&utm_medium=colab&utm_content=dspy&utm_campaign=opik) provides a hosted version of the Opik platform, [simply create an account](https://www.comet.com/signup?from=llm&utm_source=opik&utm_medium=colab&utm_content=dspy&utm_campaign=opik) and grab you API Key. + +> You can also run the Opik platform locally, see the [installation guide](https://www.comet.com/docs/opik/self-host/overview/?from=llm&utm_source=opik&utm_medium=colab&utm_content=dspy&utm_campaign=opik) for more information. + + +```python +%pip install --upgrade opik dspy +``` + + +```python +import opik + +opik.configure(use_local=False) +``` + + +```python +import os +import getpass + +if "OPENAI_API_KEY" not in os.environ: + os.environ["OPENAI_API_KEY"] = getpass.getpass("Enter your OpenAI API key: ") +``` + +## Logging traces + +In order to log traces to Opik, you will need to set the `opik` callback: + + +```python +import dspy +from opik.integrations.dspy.callback import OpikCallback + +lm = dspy.LM("openai/gpt-4o-mini") + +project_name = "DSPY" +opik_callback = OpikCallback(project_name=project_name) + +dspy.configure(lm=lm, callbacks=[opik_callback]) +``` + + +```python +cot = dspy.ChainOfThought("question -> answer") +cot(question="What is the meaning of life?") +``` + +The trace is now logged to the Opik platform: + +![DSPy trace](https://raw.githubusercontent.com/comet-ml/opik/main/apps/opik-documentation/documentation/static/img/cookbook/dspy_trace_cookbook.png) diff --git a/apps/opik-documentation/documentation/fern/docs/cookbook/evaluate_hallucination_metric.mdx b/apps/opik-documentation/documentation/fern/docs/cookbook/evaluate_hallucination_metric.mdx new file mode 100644 index 0000000000..8e902bb73a --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs/cookbook/evaluate_hallucination_metric.mdx @@ -0,0 +1,138 @@ +--- +sidebar_label: Evaluating Opik's Hallucination Metric +description: Cookbook that evalutes Opik's Hallucination Metric, showcasing both how to use the `evaluation` functionality in the platform as well as the quality of the Hallucination metric included in the SDK. It is a complex example that doesn't always align with how the `evaluate` function works. +--- + +# Evaluating Opik's Hallucination Metric + +For this guide we will be evaluating the Hallucination metric included in the LLM Evaluation SDK which will showcase both how to use the `evaluation` functionality in the platform as well as the quality of the Hallucination metric included in the SDK. + +## Creating an account on Comet.com + +[Comet](https://www.comet.com/site/?from=llm&utm_source=opik&utm_medium=colab&utm_content=eval_hall&utm_campaign=opik) provides a hosted version of the Opik platform, [simply create an account](https://www.comet.com/signup?from=llm&utm_source=opik&utm_medium=colab&utm_content=eval_hall&utm_campaign=opik) and grab you API Key. + +> You can also run the Opik platform locally, see the [installation guide](https://www.comet.com/docs/opik/self-host/overview/?from=llm&utm_source=opik&utm_medium=colab&utm_content=eval_hall&utm_campaign=opik) for more information. + + +```python +%pip install opik pyarrow pandas fsspec huggingface_hub --upgrade --quiet +``` + + +```python +import opik + +opik.configure(use_local=False) +``` + +## Preparing our environment + +First, we will install configure the OpenAI API key and create a new Opik dataset + + +```python +import os +import getpass + +if "OPENAI_API_KEY" not in os.environ: + os.environ["OPENAI_API_KEY"] = getpass.getpass("Enter your OpenAI API key: ") +``` + +We will be using the [HaluEval dataset](https://huggingface.co/datasets/pminervini/HaluEval?library=pandas) which according to this [paper](https://arxiv.org/pdf/2305.11747) ChatGPT detects 86.2% of hallucinations. The first step will be to create a dataset in the platform so we can keep track of the results of the evaluation. + +Since the insert methods in the SDK deduplicates items, we can insert 50 items and if the items already exist, Opik will automatically remove them. + + +```python +# Create dataset +import opik +import pandas as pd + +client = opik.Opik() + +# Create dataset +dataset = client.get_or_create_dataset(name="HaluEval", description="HaluEval dataset") + +# Insert items into dataset +df = pd.read_parquet( + "hf://datasets/pminervini/HaluEval/general/data-00000-of-00001.parquet" +) +df = df.sample(n=50, random_state=42) + +dataset_records = [ + { + "input": x["user_query"], + "llm_output": x["chatgpt_response"], + "expected_hallucination_label": x["hallucination"], + } + for x in df.to_dict(orient="records") +] + +dataset.insert(dataset_records) +``` + +## Evaluating the hallucination metric + +In order to evaluate the performance of the Opik hallucination metric, we will define: + +- Evaluation task: Our evaluation task will use the data in the Dataset to return a hallucination score computed using the Opik hallucination metric. +- Scoring metric: We will use the `Equals` metric to check if the hallucination score computed matches the expected output. + +By defining the evaluation task in this way, we will be able to understand how well Opik's hallucination metric is able to detect hallucinations in the dataset. + + +```python +from opik.evaluation.metrics import Hallucination, Equals +from opik.evaluation import evaluate +from opik import Opik +from opik.evaluation.metrics.llm_judges.hallucination.template import generate_query +from typing import Dict + + +# Define the evaluation task +def evaluation_task(x: Dict): + metric = Hallucination() + try: + metric_score = metric.score(input=x["input"], output=x["llm_output"]) + hallucination_score = metric_score.value + hallucination_reason = metric_score.reason + except Exception as e: + print(e) + hallucination_score = None + hallucination_reason = str(e) + + return { + "hallucination_score": "yes" if hallucination_score == 1 else "no", + "hallucination_reason": hallucination_reason, + } + + +# Get the dataset +client = Opik() +dataset = client.get_dataset(name="HaluEval") + +# Define the scoring metric +check_hallucinated_metric = Equals(name="Correct hallucination score") + +# Add the prompt template as an experiment configuration +experiment_config = { + "prompt_template": generate_query( + input="{input}", context="{context}", output="{output}", few_shot_examples=[] + ) +} + +res = evaluate( + dataset=dataset, + task=evaluation_task, + scoring_metrics=[check_hallucinated_metric], + experiment_config=experiment_config, + scoring_key_mapping={ + "reference": "expected_hallucination_label", + "output": "hallucination_score", + }, +) +``` + +We can see that the hallucination metric is able to detect ~80% of the hallucinations contained in the dataset and we can see the specific items where hallucinations were not detected. + +![Hallucination Evaluation](https://raw.githubusercontent.com/comet-ml/opik/main/apps/opik-documentation/documentation/static/img/cookbook/hallucination_metric_cookbook.png) diff --git a/apps/opik-documentation/documentation/fern/docs/cookbook/evaluate_moderation_metric.mdx b/apps/opik-documentation/documentation/fern/docs/cookbook/evaluate_moderation_metric.mdx new file mode 100644 index 0000000000..9ee3d07815 --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs/cookbook/evaluate_moderation_metric.mdx @@ -0,0 +1,147 @@ +--- +sidebar_label: Evaluate Opik's Moderation Metric +description: Cookbook that evalutes Opik's Moderation Metric, showcasing both how to use the `evaluation` functionality in the platform as well as the quality of the Modelration metric included in the SDK. It is a complex example that doesn't always align with how the `evaluate` function works. +--- + +# Evaluating Opik's Moderation Metric + +For this guide we will be evaluating the Moderation metric included in the LLM Evaluation SDK which will showcase both how to use the `evaluation` functionality in the platform as well as the quality of the Moderation metric included in the SDK. + +## Creating an account on Comet.com + +[Comet](https://www.comet.com/site?from=llm&utm_source=opik&utm_medium=colab&utm_content=eval_mod&utm_campaign=opik) provides a hosted version of the Opik platform, [simply create an account](https://www.comet.com/signup/?from=llm&utm_source=opik&utm_medium=colab&utm_content=eval_mod&utm_campaign=opik) and grab you API Key. + +> You can also run the Opik platform locally, see the [installation guide](https://www.comet.com/docs/opik/self-host/overview/?from=llm&utm_source=opik&utm_medium=colab&utm_content=eval_mod&utm_campaign=opik) for more information. + + +```python +%pip install --upgrade --quiet opik pandas +``` + + +```python +import opik + +opik.configure(use_local=False) +``` + +## Preparing our environment + +First, we will configure the OpenAI API key and download a reference moderation dataset. + + +```python +import os +import getpass + +if "OPENAI_API_KEY" not in os.environ: + os.environ["OPENAI_API_KEY"] = getpass.getpass("Enter your OpenAI API key: ") +``` + +We will be using the [OpenAI Moderation API Release dataset](https://github.com/openai/moderation-api-release/tree/main/data) which according to this [blog post](https://openai.com/index/using-gpt-4-for-content-moderation/) GPT-4o detects ~60~% of hallucinations. The first step will be to create a dataset in the platform so we can keep track of the results of the evaluation. + +Since the insert methods in the SDK deduplicates items, we can insert 50 items and if the items already exist, Opik will automatically remove them. + + +```python +# Create dataset +import opik +import pandas as pd +import requests +from io import BytesIO + +client = opik.Opik() + +# Create dataset +dataset = client.get_or_create_dataset( + name="OpenAIModerationDataset", description="OpenAI Moderation Dataset" +) + +# Insert items into dataset +url = "https://github.com/openai/moderation-api-release/raw/main/data/samples-1680.jsonl.gz" +response = requests.get(url) +df = pd.read_json(BytesIO(response.content), lines=True, compression="gzip") + +df = df.sample(n=50, random_state=42) + +dataset_records = [] +for x in df.to_dict(orient="records"): + moderation_fields = ["S", "H", "V", "HR", "SH", "S3", "H2", "V2"] + moderated_fields = [field for field in moderation_fields if x[field] == 1.0] + expected_output = "moderated" if moderated_fields else "not_moderated" + + dataset_records.append( + { + "output": x["prompt"], + "expected_output": expected_output, + "moderated_fields": moderated_fields, + } + ) + +dataset.insert(dataset_records) +``` + +## Evaluating the moderation metric + +In order to evaluate the performance of the Opik moderation metric, we will define: + +- Evaluation task: Our evaluation task will use the data in the Dataset to return a moderation score computed using the Opik moderation metric. +- Scoring metric: We will use the `Equals` metric to check if the moderation score computed matches the expected output. + +By defining the evaluation task in this way, we will be able to understand how well Opik's moderation metric is able to detect moderation violations in the dataset. + +We can use the Opik SDK to compute a moderation score for each item in the dataset: + + +```python +from opik.evaluation.metrics import Moderation, Equals +from opik.evaluation import evaluate +from opik import Opik +from opik.evaluation.metrics.llm_judges.moderation.template import generate_query +from typing import Dict + + +# Define the evaluation task +def evaluation_task(x: Dict): + metric = Moderation() + try: + metric_score = metric.score(output=x["output"]) + moderation_score = "moderated" if metric_score.value > 0.5 else "not_moderated" + moderation_reason = metric_score.reason + except Exception as e: + print(e) + moderation_score = None + moderation_reason = str(e) + + return { + "moderation_score": moderation_score, + "moderation_reason": moderation_reason, + } + + +# Get the dataset +client = Opik() +dataset = client.get_dataset(name="OpenAIModerationDataset") + +# Define the scoring metric +moderation_metric = Equals(name="Correct moderation score") + +# Add the prompt template as an experiment configuration +experiment_config = { + "prompt_template": generate_query(output="{output}", few_shot_examples=[]) +} + +res = evaluate( + dataset=dataset, + task=evaluation_task, + scoring_metrics=[moderation_metric], + experiment_config=experiment_config, + scoring_key_mapping={"reference": "expected_output", "output": "moderation_score"}, +) +``` + +We are able to detect ~85% of moderation violations, this can be improved further by providing some additional examples to the model. We can view a breakdown of the results in the Opik UI: + +![Moderation Evaluation](https://raw.githubusercontent.com/comet-ml/opik/main/apps/opik-documentation/documentation/static/img/cookbook/moderation_metric_cookbook.png) + + diff --git a/apps/opik-documentation/documentation/fern/docs/cookbook/gemini.mdx b/apps/opik-documentation/documentation/fern/docs/cookbook/gemini.mdx new file mode 100644 index 0000000000..876ea72dfd --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs/cookbook/gemini.mdx @@ -0,0 +1,127 @@ +--- +description: Cookbook that showcases Opik's integration with the Gemini Python SDK +--- + +# Using Opik with Gemini + +Opik integrates with Gemini to provide a simple way to log traces for all Gemini LLM calls. This works for all Gemini models. + +## Creating an account on Comet.com + +[Comet](https://www.comet.com/site?from=llm&utm_source=opik&utm_medium=colab&utm_content=openai&utm_campaign=opik) provides a hosted version of the Opik platform, [simply create an account](https://www.comet.com/signup?from=llm&utm_source=opik&utm_medium=colab&utm_content=openai&utm_campaign=opik) and grab you API Key. + +> You can also run the Opik platform locally, see the [installation guide](https://www.comet.com/docs/opik/self-host/overview/?from=llm&utm_source=opik&utm_medium=colab&utm_content=openai&utm_campaign=opik) for more information. + + +```python +%pip install --upgrade opik google-generativeai litellm +``` + + +```python +import opik + +opik.configure(use_local=False) +``` + +## Preparing our environment + +First, we will set up our OpenAI API keys. + + +```python +import os +import getpass +import google.generativeai as genai + +if "GEMINI_API_KEY" not in os.environ: + genai.configure(api_key=getpass.getpass("Enter your Gemini API key: ")) +``` + +## Configure LiteLLM + +Add the LiteLLM OpikTracker to log traces and steps to Opik: + + +```python +import litellm +import os +from litellm.integrations.opik.opik import OpikLogger +from opik import track +from opik.opik_context import get_current_span_data + +os.environ["OPIK_PROJECT_NAME"] = "gemini-integration-demo" +opik_logger = OpikLogger() +litellm.callbacks = [opik_logger] +``` + +## Logging traces + +Now each completion will logs a separate trace to LiteLLM: + + +```python +prompt = """ +Write a short two sentence story about Opik. +""" + +response = litellm.completion( + model="gemini/gemini-pro", + messages=[{"role": "user", "content": prompt}], +) + +print(response.choices[0].message.content) +``` + +The prompt and response messages are automatically logged to Opik and can be viewed in the UI. + +![Gemini Cookbook](https://raw.githubusercontent.com/comet-ml/opik/main/apps/opik-documentation/documentation/static/img/cookbook/gemini_trace_cookbook.png) + +## Using it with the `track` decorator + +If you have multiple steps in your LLM pipeline, you can use the `track` decorator to log the traces for each step. If Gemini is called within one of these steps, the LLM call with be associated with that corresponding step: + + +```python +@track +def generate_story(prompt): + response = litellm.completion( + model="gemini/gemini-pro", + messages=[{"role": "user", "content": prompt}], + metadata={ + "opik": { + "current_span_data": get_current_span_data(), + }, + }, + ) + return response.choices[0].message.content + + +@track +def generate_topic(): + prompt = "Generate a topic for a story about Opik." + response = litellm.completion( + model="gemini/gemini-pro", + messages=[{"role": "user", "content": prompt}], + metadata={ + "opik": { + "current_span_data": get_current_span_data(), + }, + }, + ) + return response.choices[0].message.content + + +@track +def generate_opik_story(): + topic = generate_topic() + story = generate_story(topic) + return story + + +generate_opik_story() +``` + +The trace can now be viewed in the UI: + +![Gemini Cookbook](https://raw.githubusercontent.com/comet-ml/opik/main/apps/opik-documentation/documentation/static/img/cookbook/gemini_trace_decorator_cookbook.png) diff --git a/apps/opik-documentation/documentation/fern/docs/cookbook/groq.mdx b/apps/opik-documentation/documentation/fern/docs/cookbook/groq.mdx new file mode 100644 index 0000000000..0900fda70f --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs/cookbook/groq.mdx @@ -0,0 +1,126 @@ +--- +description: Cookbook that showcases Opik's integration with Groq +--- + +# Using Opik with Groq + +Opik integrates with Groq to provide a simple way to log traces for all Groq LLM calls. This works for all Groq models. + +## Creating an account on Comet.com + +[Comet](https://www.comet.com/site?from=llm&utm_source=opik&utm_medium=colab&utm_content=openai&utm_campaign=opik) provides a hosted version of the Opik platform, [simply create an account](https://www.comet.com/signup?from=llm&utm_source=opik&utm_medium=colab&utm_content=openai&utm_campaign=opik) and grab you API Key. + +> You can also run the Opik platform locally, see the [installation guide](https://www.comet.com/docs/opik/self-host/overview/?from=llm&utm_source=opik&utm_medium=colab&utm_content=openai&utm_campaign=opik) for more information. + + +```python +%pip install --upgrade opik litellm +``` + + +```python +import opik + +opik.configure(use_local=False) +``` + +## Preparing our environment + +First, we will set up our OpenAI API keys. + + +```python +import os +import getpass + +if "GROQ_API_KEY" not in os.environ: + os.environ["GROQ_API_KEY"] = getpass.getpass("Enter your Groq API key: ") +``` + +## Configure LiteLLM + +Add the LiteLLM OpikTracker to log traces and steps to Opik: + + +```python +import litellm +import os +from litellm.integrations.opik.opik import OpikLogger +from opik import track +from opik.opik_context import get_current_span_data + +os.environ["OPIK_PROJECT_NAME"] = "grok-integration-demo" +opik_logger = OpikLogger() +litellm.callbacks = [opik_logger] +``` + +## Logging traces + +Now each completion will logs a separate trace to LiteLLM: + + +```python +prompt = """ +Write a short two sentence story about Opik. +""" + +response = litellm.completion( + model="groq/llama3-8b-8192", + messages=[{"role": "user", "content": prompt}], +) + +print(response.choices[0].message.content) +``` + +The prompt and response messages are automatically logged to Opik and can be viewed in the UI. + +![Groq Cookbook](https://raw.githubusercontent.com/comet-ml/opik/main/apps/opik-documentation/documentation/static/img/cookbook/groq_trace_cookbook.png) + +## Using it with the `track` decorator + +If you have multiple steps in your LLM pipeline, you can use the `track` decorator to log the traces for each step. If Groq is called within one of these steps, the LLM call with be associated with that corresponding step: + + +```python +@track +def generate_story(prompt): + response = litellm.completion( + model="groq/llama3-8b-8192", + messages=[{"role": "user", "content": prompt}], + metadata={ + "opik": { + "current_span_data": get_current_span_data(), + }, + }, + ) + return response.choices[0].message.content + + +@track +def generate_topic(): + prompt = "Generate a topic for a story about Opik." + response = litellm.completion( + model="groq/llama3-8b-8192", + messages=[{"role": "user", "content": prompt}], + metadata={ + "opik": { + "current_span_data": get_current_span_data(), + }, + }, + ) + return response.choices[0].message.content + + +@track +def generate_opik_story(): + topic = generate_topic() + story = generate_story(topic) + return story + + +generate_opik_story() +``` + +The trace can now be viewed in the UI: + +![Groq Cookbook](https://raw.githubusercontent.com/comet-ml/opik/main/apps/opik-documentation/documentation/static/img/cookbook/groq_trace_decorator_cookbook.png) diff --git a/apps/opik-documentation/documentation/fern/docs/cookbook/guardrails-ai.mdx b/apps/opik-documentation/documentation/fern/docs/cookbook/guardrails-ai.mdx new file mode 100644 index 0000000000..eef561404f --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs/cookbook/guardrails-ai.mdx @@ -0,0 +1,79 @@ +--- +description: Cookbook that showcases Opik's integration with the Guardrails AI Python SDK +--- + +# Using Opik with Guardrails AI + +[Guardrails AI](https://github.com/guardrails-ai/guardrails) is a framework for validating the inputs and outputs + +For this guide we will use a simple example that logs guardrails validation steps as traces to Opik, providing them with the validation result tags. + +## Creating an account on Comet.com + +[Comet](https://www.comet.com/site?from=llm&utm_source=opik&utm_medium=colab&utm_content=openai&utm_campaign=opik) provides a hosted version of the Opik platform, [simply create an account](https://www.comet.com/signup?from=llm&utm_source=opik&utm_medium=colab&utm_content=openai&utm_campaign=opik) and grab you API Key. + +> You can also run the Opik platform locally, see the [installation guide](https://www.comet.com/docs/opik/self-host/overview/?from=llm&utm_source=opik&utm_medium=colab&utm_content=openai&utm_campaign=opik) for more information. + + +```python +%pip install --upgrade opik guardrails-ai +``` + + +```python +import opik + +opik.configure(use_local=False) +``` + +## Preparing our environment + +In order to use Guardrails AI, we will configure the OpenAI API Key, if you are using any other providers you can replace this with the required API key: + + +```python +import os +import getpass + +if "OPENAI_API_KEY" not in os.environ: + os.environ["OPENAI_API_KEY"] = getpass.getpass("Enter your OpenAI API key: ") +``` + +We will also need to install the guardrails check for politeness from the Guardrails Hub + + +```python +!guardrails hub install hub://guardrails/politeness_check +``` + +## Logging validation traces + +In order to log traces to Opik, you will need to call the track the Guard object with `track_guardrails` function. + + +```python +from guardrails import Guard, OnFailAction +from guardrails.hub import PolitenessCheck + +from opik.integrations.guardrails import track_guardrails + +politeness_check = PolitenessCheck( + llm_callable="gpt-3.5-turbo", on_fail=OnFailAction.NOOP +) + +guard: Guard = Guard().use_many(politeness_check) +guard = track_guardrails(guard, project_name="guardrails-integration-example") + +guard.validate( + "Would you be so kind to pass me a cup of tea?", +) +guard.validate( + "Shut your mouth up and give me the tea.", +); +``` + +Every validation will now be logged to Opik as a trace + +The trace will now be viewable in the Opik platform: + +![Guardrails AI Integration](https://raw.githubusercontent.com/comet-ml/opik/main/apps/opik-documentation/documentation/static/img/cookbook/guardrails_ai_traces_cookbook.png) diff --git a/apps/opik-documentation/documentation/fern/docs/cookbook/haystack.mdx b/apps/opik-documentation/documentation/fern/docs/cookbook/haystack.mdx new file mode 100644 index 0000000000..303c9255b1 --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs/cookbook/haystack.mdx @@ -0,0 +1,130 @@ +--- +description: Cookbook that showcases Opik's integration with Haystack +--- + +# Using Opik with Haystack + +[Haystack](https://docs.haystack.deepset.ai/docs/intro) is an open-source framework for building production-ready LLM applications, retrieval-augmented generative pipelines and state-of-the-art search systems that work intelligently over large document collections. + +In this guide, we will showcase how to integrate Opik with Haystack so that all the Haystack calls are logged as traces in Opik. + +## Creating an account on Comet.com + +[Comet](https://www.comet.com/site?from=llm&utm_source=opik&utm_medium=colab&utm_content=haystack&utm_campaign=opik) provides a hosted version of the Opik platform, [simply create an account](https://www.comet.com/signup?from=llm&utm_source=opik&utm_medium=colab&utm_content=haystack&utm_campaign=opik) and grab you API Key. + +> You can also run the Opik platform locally, see the [installation guide](https://www.comet.com/docs/opik/self-host/overview/?from=llm&utm_source=opik&utm_medium=colab&utm_content=haystack&utm_campaign=opik) for more information. + + +```python +%pip install --upgrade --quiet opik haystack-ai +``` + + +```python +import opik + +opik.configure(use_local=False) +``` + + +```python +import os +import getpass + +if "OPENAI_API_KEY" not in os.environ: + os.environ["OPENAI_API_KEY"] = getpass.getpass("Enter your OpenAI API key: ") +``` + +## Creating the Haystack pipeline + +In this example, we will create a simple pipeline that uses a prompt template to translate text to German. + +To enable Opik tracing, we will: +1. Enable content tracing in Haystack by setting the environment variable `HAYSTACK_CONTENT_TRACING_ENABLED=true` +2. Add the `OpikConnector` component to the pipeline + +Note: The `OpikConnector` component is a special component that will automatically log the traces of the pipeline as Opik traces, it should not be connected to any other component. + + +```python +import os + +os.environ["HAYSTACK_CONTENT_TRACING_ENABLED"] = "true" + +from haystack import Pipeline +from haystack.components.builders import ChatPromptBuilder +from haystack.components.generators.chat import OpenAIChatGenerator +from haystack.dataclasses import ChatMessage + +from opik.integrations.haystack import OpikConnector + + +pipe = Pipeline() + +# Add the OpikConnector component to the pipeline +pipe.add_component("tracer", OpikConnector("Chat example")) + +# Continue building the pipeline +pipe.add_component("prompt_builder", ChatPromptBuilder()) +pipe.add_component("llm", OpenAIChatGenerator(model="gpt-3.5-turbo")) + +pipe.connect("prompt_builder.prompt", "llm.messages") + +messages = [ + ChatMessage.from_system( + "Always respond in German even if some input data is in other languages." + ), + ChatMessage.from_user("Tell me about {{location}}"), +] + +response = pipe.run( + data={ + "prompt_builder": { + "template_variables": {"location": "Berlin"}, + "template": messages, + } + } +) + +trace_id = response["tracer"]["trace_id"] +print(f"Trace ID: {trace_id}") +print(response["llm"]["replies"][0]) +``` + +The trace is now logged to the Opik platform: + +![Haystack trace](https://raw.githubusercontent.com/comet-ml/opik/main/apps/opik-documentation/documentation/static/img/cookbook/haystack_trace_cookbook.png) + +## Advanced usage + +### Ensuring the trace is logged + +By default the `OpikConnector` will flush the trace to the Opik platform after each component in a thread blocking way. As a result, you may disable flushing the data after each component by setting the `HAYSTACK_OPIK_ENFORCE_FLUSH` environent variable to `false`. + +**Caution**: Disabling this feature may result in data loss if the program crashes before the data is sent to Opik. Make sure you will call the `flush()` method explicitly before the program exits: + + +```python +from haystack.tracing import tracer + +tracer.actual_tracer.flush() +``` + +### Getting the trace ID + +If you would like to log additional information to the trace you will need to get the trace ID. You can do this by the `tracer` key in the response of the pipeline: + + +```python +response = pipe.run( + data={ + "prompt_builder": { + "template_variables": {"location": "Berlin"}, + "template": messages, + } + } +) + +trace_id = response["tracer"]["trace_id"] +print(f"Trace ID: {trace_id}") +``` diff --git a/apps/opik-documentation/documentation/fern/docs/cookbook/langchain.mdx b/apps/opik-documentation/documentation/fern/docs/cookbook/langchain.mdx new file mode 100644 index 0000000000..2e1773b8ee --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs/cookbook/langchain.mdx @@ -0,0 +1,207 @@ +--- +description: Cookbook that showcases Opik's integration with the LangChain Python SDK +--- + +# Using Opik with Langchain + +For this guide, we will be performing a text to sql query generation task using LangChain. We will be using the Chinook database which contains the SQLite database of a music store with both employee, customer and invoice data. + +We will highlight three different parts of the workflow: + +1. Creating a synthetic dataset of questions +2. Creating a LangChain chain to generate SQL queries +3. Automating the evaluation of the SQL queries on the synthetic dataset + +## Creating an account on Comet.com + +[Comet](https://www.comet.com/site?from=llm&utm_source=opik&utm_medium=colab&utm_content=langchain&utm_campaign=opik) provides a hosted version of the Opik platform, [simply create an account](https://www.comet.com/signup?from=llm&utm_source=opik&utm_medium=colab&utm_content=langchain&utm_campaign=opik) and grab you API Key. + +> You can also run the Opik platform locally, see the [installation guide](https://www.comet.com/docs/opik/self-host/overview/?from=llm&utm_source=opik&utm_medium=colab&utm_content=langchain&utm_campaign=opik) for more information. + + +```python +%pip install --upgrade --quiet opik langchain langchain-community langchain-openai +``` + + +```python +import opik + +opik.configure(use_local=False) +``` + +## Preparing our environment + +First, we will download the Chinook database and set up our different API keys. + + +```python +import os +import getpass + +if "OPENAI_API_KEY" not in os.environ: + os.environ["OPENAI_API_KEY"] = getpass.getpass("Enter your OpenAI API key: ") +``` + + +```python +# Download the relevant data +import os +from langchain_community.utilities import SQLDatabase + +import requests +import os + +url = "https://github.com/lerocha/chinook-database/raw/master/ChinookDatabase/DataSources/Chinook_Sqlite.sqlite" +filename = "./data/chinook/Chinook_Sqlite.sqlite" + +folder = os.path.dirname(filename) + +if not os.path.exists(folder): + os.makedirs(folder) + +if not os.path.exists(filename): + response = requests.get(url) + with open(filename, "wb") as file: + file.write(response.content) + print("Chinook database downloaded") + +db = SQLDatabase.from_uri(f"sqlite:///{filename}") +``` + +## Creating a synthetic dataset + +In order to create our synthetic dataset, we will be using the OpenAI API to generate 20 different questions that a user might ask based on the Chinook database. + +In order to ensure that the OpenAI API calls are being tracked, we will be using the `track_openai` function from the `opik` library. + + +```python +from opik.integrations.openai import track_openai +from openai import OpenAI +import json + +os.environ["OPIK_PROJECT_NAME"] = "langchain-integration-demo" +client = OpenAI() + +openai_client = track_openai(client) + +prompt = """ +Create 20 different example questions a user might ask based on the Chinook Database. + +These questions should be complex and require the model to think. They should include complex joins and window functions to answer. + +Return the response as a json object with a "result" key and an array of strings with the question. +""" + +completion = openai_client.chat.completions.create( + model="gpt-3.5-turbo", messages=[{"role": "user", "content": prompt}] +) + +print(completion.choices[0].message.content) +``` + +Now that we have our synthetic dataset, we can create a dataset in Comet and insert the questions into it. + +Since the insert methods in the SDK deduplicates items, we can insert 20 items and if the items already exist, Opik will automatically remove them. + + +```python +# Create the synthetic dataset +import opik + +synthetic_questions = json.loads(completion.choices[0].message.content)["result"] + +client = opik.Opik() + +dataset = client.get_or_create_dataset(name="synthetic_questions") +dataset.insert([{"question": question} for question in synthetic_questions]) +``` + +## Creating a LangChain chain + +We will be using the `create_sql_query_chain` function from the `langchain` library to create a SQL query to answer the question. + +We will be using the `OpikTracer` class from the `opik` library to ensure that the LangChan trace are being tracked in Comet. + + +```python +# Use langchain to create a SQL query to answer the question +from langchain.chains import create_sql_query_chain +from langchain_openai import ChatOpenAI +from opik.integrations.langchain import OpikTracer + +opik_tracer = OpikTracer(tags=["simple_chain"]) + +llm = ChatOpenAI(model="gpt-3.5-turbo", temperature=0) +chain = create_sql_query_chain(llm, db).with_config({"callbacks": [opik_tracer]}) +response = chain.invoke({"question": "How many employees are there ?"}) +response + +print(response) +``` + +## Automating the evaluation + +In order to ensure our LLM application is working correctly, we will test it on our synthetic dataset. + +For this we will be using the `evaluate` function from the `opik` library. We will evaluate the application using a custom metric that checks if the SQL query is valid. + + +```python +from opik import Opik, track +from opik.evaluation import evaluate +from opik.evaluation.metrics import base_metric, score_result +from typing import Any + + +class ValidSQLQuery(base_metric.BaseMetric): + def __init__(self, name: str, db: Any): + self.name = name + self.db = db + + def score(self, output: str, **ignored_kwargs: Any): + # Add you logic here + + try: + db.run(output) + return score_result.ScoreResult( + name=self.name, value=1, reason="Query ran successfully" + ) + except Exception as e: + return score_result.ScoreResult(name=self.name, value=0, reason=str(e)) + + +valid_sql_query = ValidSQLQuery(name="valid_sql_query", db=db) + +client = Opik() +dataset = client.get_dataset("synthetic_questions") + + +@track() +def llm_chain(input: str) -> str: + response = chain.invoke({"question": input}) + + return response + + +def evaluation_task(item): + response = llm_chain(item["question"]) + + return {"output": response} + + +res = evaluate( + experiment_name="SQL question answering", + dataset=dataset, + task=evaluation_task, + scoring_metrics=[valid_sql_query], + nb_samples=20, +) +``` + +The evaluation results are now uploaded to the Opik platform and can be viewed in the UI. + +![LangChain Evaluation](https://raw.githubusercontent.com/comet-ml/opik/main/apps/opik-documentation/documentation/static/img/cookbook/langchain_cookbook.png) + + diff --git a/apps/opik-documentation/documentation/fern/docs/cookbook/langgraph.mdx b/apps/opik-documentation/documentation/fern/docs/cookbook/langgraph.mdx new file mode 100644 index 0000000000..fc79356f5c --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs/cookbook/langgraph.mdx @@ -0,0 +1,127 @@ +--- +description: Cookbook that showcases Opik's integration with the LangGraph Python SDK +--- + +# Using Opik with LangGraph + +This notebook showcases how to use Opik with LangGraph. [LangGraph](https://langchain-ai.github.io/langgraph/) is a library for building stateful, multi-actor applications with LLMs, used to create agent and multi-agent workflows + +In this notebook, we will create a simple LangGraph workflow and focus on how to track it's execution with Opik. To learn more about LangGraph, check out the [official documentation](https://langchain-ai.github.io/langgraph/). + +## Creating an account on Opik Cloud + +[Comet](https://www.comet.com/site?from=llm&utm_source=opik&utm_medium=colab&utm_content=langgraph&utm_campaign=opik) provides a hosted version of the Opik platform, [simply create an account](https://www.comet.com/signup?from=llm&=opik&utm_medium=colab&utm_content=langgraph&utm_campaign=opik) and grab you API Key. + +> You can also run the Opik platform locally, see the [installation guide](https://www.comet.com/docs/opik/self-host/overview/?from=llm&utm_source=opik&utm_medium=colab&utm_content=langgraph&utm_campaign=opik) for more information. + + +```python +%pip install --quiet -U langchain langgraph opik +``` + + +```python +import opik + +opik.configure(use_local=False) +``` + +## Create the LangGraph graph + +The LangGraph graph we will be created in made up of 3 nodes: + +1. `classify_input`: Classify the input question +2. `handle_greeting`: Handle the greeting question +3. `handle_search`: Handle the search question + +*Note*: We will not be using any LLM calls or tools in this example to keep things simple. However in most cases, you will want to use tools to interact with external systems. + + +```python +# We will start by creating simple functions to classify the input question and handle the greeting and search questions. +def classify(question: str) -> str: + return "greeting" if question.startswith("Hello") else "search" + + +def classify_input_node(state): + question = state.get("question", "").strip() + classification = classify(question) # Assume a function that classifies the input + return {"classification": classification} + + +def handle_greeting_node(state): + return {"response": "Hello! How can I help you today?"} + + +def handle_search_node(state): + question = state.get("question", "").strip() + search_result = f"Search result for '{question}'" + return {"response": search_result} +``` + + +```python +from langgraph.graph import StateGraph, END + +from typing import TypedDict, Optional + + +class GraphState(TypedDict): + question: Optional[str] = None + classification: Optional[str] = None + response: Optional[str] = None + + +workflow = StateGraph(GraphState) +workflow.add_node("classify_input", classify_input_node) +workflow.add_node("handle_greeting", handle_greeting_node) +workflow.add_node("handle_search", handle_search_node) + + +def decide_next_node(state): + return ( + "handle_greeting" + if state.get("classification") == "greeting" + else "handle_search" + ) + + +workflow.add_conditional_edges( + "classify_input", + decide_next_node, + {"handle_greeting": "handle_greeting", "handle_search": "handle_search"}, +) + +workflow.set_entry_point("classify_input") +workflow.add_edge("handle_greeting", END) +workflow.add_edge("handle_search", END) + +app = workflow.compile() + +# Display the graph +try: + from IPython.display import Image, display + + display(Image(app.get_graph().draw_mermaid_png())) +except Exception: + # This requires some extra dependencies and is optional + pass +``` + +## Calling the graph with Opik tracing enabled + +In order to log the execution of the graph, we need to define the OpikTracer callback: + + +```python +from opik.integrations.langchain import OpikTracer + +tracer = OpikTracer(graph=app.get_graph(xray=True)) +inputs = {"question": "Hello, how are you?"} +result = app.invoke(inputs, config={"callbacks": [tracer]}) +print(result) +``` + +The graph execution is now logged on the Opik platform and can be viewed in the UI: + +![LangGraph screenshot](https://raw.githubusercontent.com/comet-ml/opik/main/apps/opik-documentation/documentation/static/img/cookbook/langgraph_cookbook.png) diff --git a/apps/opik-documentation/documentation/fern/docs/cookbook/litellm.mdx b/apps/opik-documentation/documentation/fern/docs/cookbook/litellm.mdx new file mode 100644 index 0000000000..de12a0a8e7 --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs/cookbook/litellm.mdx @@ -0,0 +1,102 @@ +--- +description: Cookbook that showcases Opik's integration with the LiteLLM Python SDK +--- + +# Using Opik with LiteLLM + +Lite allows you to call all LLM APIs using the OpenAI format [Bedrock, Huggingface, VertexAI, TogetherAI, Azure, OpenAI, Groq etc.]. You can learn more about LiteLLM [here](https://github.com/BerriAI/litellm). + +There are two main approaches to using LiteLLM, either using the `litellm` [python library](https://docs.litellm.ai/docs/#litellm-python-sdk) that will query the LLM API for you or by using the [LiteLLM proxy server](https://docs.litellm.ai/docs/#litellm-proxy-server-llm-gateway). In this cookbook we will focus on the first approach but you can learn more about using Opik with the LiteLLM proxy server in our [documentation](https://www.comet.com/docs/opik/tracing/integrations/litellm). + +## Creating an account on Comet.com + +[Comet](https://www.comet.com/site?from=llm&utm_source=opik&utm_medium=colab&utm_content=openai&utm_campaign=opik) provides a hosted version of the Opik platform, [simply create an account](https://www.comet.com/signup?from=llm&utm_source=opik&utm_medium=colab&utm_content=openai&utm_campaign=opik) and grab you API Key. + +> You can also run the Opik platform locally, see the [installation guide](https://www.comet.com/docs/opik/self-host/overview/?from=llm&utm_source=opik&utm_medium=colab&utm_content=openai&utm_campaign=opik) for more information. + + +```python +%pip install --upgrade opik litellm +``` + + +```python +import opik + +opik.configure(use_local=False) +``` + +## Preparing our environment + +In order to use LiteLLM, we will configure the OpenAI API Key, if you are using any other providers you can replace this with the required API key: + + +```python +import os +import getpass + +if "OPENAI_API_KEY" not in os.environ: + os.environ["OPENAI_API_KEY"] = getpass.getpass("Enter your OpenAI API key: ") +``` + +## Logging traces + +In order to log traces to Opik, you will need to set the `opik` callback: + + +```python +from litellm.integrations.opik.opik import OpikLogger +from opik.opik_context import get_current_span_data +from opik import track +import litellm + +os.environ["OPIK_PROJECT_NAME"] = "litellm-integration-demo" +opik_logger = OpikLogger() +litellm.callbacks = [opik_logger] +``` + +Every LiteLLM call will now be logged to Opik: + + +```python +response = litellm.completion( + model="gpt-3.5-turbo", + messages=[ + {"role": "user", "content": "Why is tracking and evaluation of LLMs important?"} + ], +) + +print(response.choices[0].message.content) +``` + +The trace will now be viewable in the Opik platform: + +![OpenAI Integration](https://raw.githubusercontent.com/comet-ml/opik/main/apps/opik-documentation/documentation/static/img/cookbook/litellm_cookbook.png) + +## Logging LLM calls within a tracked function + + +If you are using LiteLLM within a function tracked with the `@track` decorator, you will need to pass the `current_span_data` as metadata to the `litellm.completion` call: + + + +```python +@track +def streaming_function(input): + messages = [{"role": "user", "content": input}] + response = litellm.completion( + model="gpt-3.5-turbo", + messages=messages, + metadata={ + "opik": { + "current_span_data": get_current_span_data(), + "tags": ["streaming-test"], + }, + }, + ) + return response + + +response = streaming_function("Why is tracking and evaluation of LLMs important?") +chunks = list(response) +``` diff --git a/apps/opik-documentation/documentation/fern/docs/cookbook/llama-index.mdx b/apps/opik-documentation/documentation/fern/docs/cookbook/llama-index.mdx new file mode 100644 index 0000000000..92afe9feb8 --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs/cookbook/llama-index.mdx @@ -0,0 +1,110 @@ +--- +description: Cookbook that showcases Opik's integration with the LlamaIndex Python SDK +--- + +# Using Opik with LlamaIndex + +This notebook showcases how to use Opik with LlamaIndex. [LlamaIndex](https://github.com/run-llama/llama_index) is a flexible data framework for building LLM applications: +> LlamaIndex is a "data framework" to help you build LLM apps. It provides the following tools: +> +> - Offers data connectors to ingest your existing data sources and data formats (APIs, PDFs, docs, SQL, etc.). +> - Provides ways to structure your data (indices, graphs) so that this data can be easily used with LLMs. +> - Provides an advanced retrieval/query interface over your data: Feed in any LLM input prompt, get back retrieved context and knowledge-augmented output. +> - Allows easy integrations with your outer application framework (e.g. with LangChain, Flask, Docker, ChatGPT, anything else). + +For this guide we will be downloading the essays from Paul Graham and use them as our data source. We will then start querying these essays with LlamaIndex. + +## Creating an account on Comet.com + +[Comet](https://www.comet.com/site?from=llm&utm_source=opik&utm_medium=colab&utm_content=llamaindex&utm_campaign=opik) provides a hosted version of the Opik platform, [simply create an account](https://www.comet.com/signup?from=llm&=opik&utm_medium=colab&utm_content=llamaindex&utm_campaign=opik) and grab you API Key. + +> You can also run the Opik platform locally, see the [installation guide](https://www.comet.com/docs/opik/self-host/overview/?from=llm&utm_source=opik&utm_medium=colab&utm_content=llamaindex&utm_campaign=opik) for more information. + + +```python +%pip install opik llama-index llama-index-agent-openai llama-index-llms-openai --upgrade --quiet +``` + + +```python +import opik + +opik.configure(use_local=False) +``` + +## Preparing our environment + +First, we will download the Chinook database and set up our different API keys. + +And configure the required environment variables: + + +```python +import os +import getpass + +if "OPENAI_API_KEY" not in os.environ: + os.environ["OPENAI_API_KEY"] = getpass.getpass("Enter your OpenAI API key: ") +``` + +In addition, we will download the Paul Graham essays: + + +```python +import os +import requests + +# Create directory if it doesn't exist +os.makedirs("./data/paul_graham/", exist_ok=True) + +# Download the file using requests +url = "https://raw.githubusercontent.com/run-llama/llama_index/main/docs/docs/examples/data/paul_graham/paul_graham_essay.txt" +response = requests.get(url) +with open("./data/paul_graham/paul_graham_essay.txt", "wb") as f: + f.write(response.content) +``` + +## Using LlamaIndex + +### Configuring the Opik integration + +You can use the Opik callback directly by calling: + + +```python +from llama_index.core import Settings +from llama_index.core.callbacks import CallbackManager +from opik.integrations.llama_index import LlamaIndexCallbackHandler + +opik_callback_handler = LlamaIndexCallbackHandler() +Settings.callback_manager = CallbackManager([opik_callback_handler]) +``` + +Now that the callback handler is configured, all traces will automatically be logged to Opik. + +### Using LLamaIndex + +The first step is to load the data into LlamaIndex. We will use the `SimpleDirectoryReader` to load the data from the `data/paul_graham` directory. We will also create the vector store to index all the loaded documents. + + +```python +from llama_index.core import VectorStoreIndex, SimpleDirectoryReader + +documents = SimpleDirectoryReader("./data/paul_graham").load_data() +index = VectorStoreIndex.from_documents(documents) +query_engine = index.as_query_engine() +``` + +We can now query the index using the `query_engine` object: + + +```python +response = query_engine.query("What did the author do growing up?") +print(response) +``` + +You can now go to the Opik app to see the trace: + +![LlamaIndex trace in Opik](https://raw.githubusercontent.com/comet-ml/opik/main/apps/opik-documentation/documentation/static/img/cookbook/llamaIndex_cookbook.png) + + diff --git a/apps/opik-documentation/documentation/fern/docs/cookbook/ollama.mdx b/apps/opik-documentation/documentation/fern/docs/cookbook/ollama.mdx new file mode 100644 index 0000000000..e793b0530d --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs/cookbook/ollama.mdx @@ -0,0 +1,116 @@ +--- +description: Cookbook that showcases Opik's integration with the Ollama Python SDK +--- + +# Using Opik with Ollama + +[Ollama](https://ollama.com/) allows users to run, interact with, and deploy AI models locally on their machines without the need for complex infrastructure or cloud dependencies. + +In this notebook, we will showcase how to log Ollama LLM calls using Opik by utilizing either the OpenAI or LangChain libraries. + +## Getting started + +### Configure Ollama + +In order to interact with Ollama from Python, we will to have Ollama running on our machine. You can learn more about how to install and run Ollama in the [quickstart guide](https://github.com/ollama/ollama/blob/main/README.md#quickstart). + +### Configuring Opik + +Opik is available as a fully open source local installation or using Comet.com as a hosted solution. The easiest way to get started with Opik is by creating a free Comet account at comet.com. + +If you'd like to self-host Opik, you can learn more about the self-hosting options [here](https://www.comet.com/docs/opik/self-host/overview). + +In addition, you will need to install and configure the Opik Python package: + + +```python +%pip install --upgrade --quiet opik + +import opik + +opik.configure() +``` + +## Tracking Ollama calls made with OpenAI + +Ollama is compatible with the OpenAI format and can be used with the OpenAI Python library. You can therefore leverage the Opik integration for OpenAI to trace your Ollama calls: + + + +```python +from openai import OpenAI +from opik.integrations.openai import track_openai + +import os + +os.environ["OPIK_PROJECT_NAME"] = "ollama-integration" + +# Create an OpenAI client +client = OpenAI( + base_url="http://localhost:11434/v1/", + # required but ignored + api_key="ollama", +) + +# Log all traces made to with the OpenAI client to Opik +client = track_openai(client) + +# call the local ollama model using the OpenAI client +chat_completion = client.chat.completions.create( + messages=[ + { + "role": "user", + "content": "Say this is a test", + } + ], + model="llama3.1", +) + +print(chat_completion.choices[0].message.content) +``` + +Your LLM call is now traced and logged to the Opik platform. + +## Tracking Ollama calls made with LangChain + +In order to trace Ollama calls made with LangChain, you will need to first install the `langchain-ollama` package: + + +```python +%pip install --quiet --upgrade langchain-ollama +``` + +You will now be able to use the `OpikTracer` class to log all your Ollama calls made with LangChain to Opik: + + +```python +from langchain_ollama import ChatOllama +from opik.integrations.langchain import OpikTracer + +# Create the Opik tracer +opik_tracer = OpikTracer(tags=["langchain", "ollama"]) + +# Create the Ollama model and configure it to use the Opik tracer +llm = ChatOllama( + model="llama3.1", + temperature=0, +).with_config({"callbacks": [opik_tracer]}) + +# Call the Ollama model +messages = [ + ( + "system", + "You are a helpful assistant that translates English to French. Translate the user sentence.", + ), + ( + "human", + "I love programming.", + ), +] +ai_msg = llm.invoke(messages) +ai_msg +``` + +You can now go to the Opik app to see the trace: + +![Ollama trace in Opik](https://raw.githubusercontent.com/comet-ml/opik/main/apps/opik-documentation/documentation/static/img/cookbook/ollama_cookbook.png) diff --git a/apps/opik-documentation/documentation/fern/docs/cookbook/openai.mdx b/apps/opik-documentation/documentation/fern/docs/cookbook/openai.mdx new file mode 100644 index 0000000000..87a26fa27d --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs/cookbook/openai.mdx @@ -0,0 +1,120 @@ +--- +description: Cookbook that showcases Opik's integration with the OpenAI Python SDK +--- + +# Using Opik with OpenAI + +Opik integrates with OpenAI to provide a simple way to log traces for all OpenAI LLM calls. This works for all OpenAI models, including if you are using the streaming API. + + +## Creating an account on Comet.com + +[Comet](https://www.comet.com/site?from=llm&utm_source=opik&utm_medium=colab&utm_content=openai&utm_campaign=opik) provides a hosted version of the Opik platform, [simply create an account](https://www.comet.com/signup?from=llm&utm_source=opik&utm_medium=colab&utm_content=openai&utm_campaign=opik) and grab you API Key. + +> You can also run the Opik platform locally, see the [installation guide](https://www.comet.com/docs/opik/self-host/overview/?from=llm&utm_source=opik&utm_medium=colab&utm_content=openai&utm_campaign=opik) for more information. + + +```python +%pip install --upgrade opik openai +``` + + +```python +import opik + +opik.configure(use_local=False) +``` + +## Preparing our environment + +First, we will set up our OpenAI API keys. + + +```python +import os +import getpass + +if "OPENAI_API_KEY" not in os.environ: + os.environ["OPENAI_API_KEY"] = getpass.getpass("Enter your OpenAI API key: ") +``` + +## Logging traces + +In order to log traces to Opik, we need to wrap our OpenAI calls with the `track_openai` function: + + +```python +from opik.integrations.openai import track_openai +from openai import OpenAI + +os.environ["OPIK_PROJECT_NAME"] = "openai-integration-demo" + +client = OpenAI() +openai_client = track_openai(client) +``` + + +```python +prompt = """ +Write a short two sentence story about Opik. +""" + +completion = openai_client.chat.completions.create( + model="gpt-3.5-turbo", messages=[{"role": "user", "content": prompt}] +) + +print(completion.choices[0].message.content) +``` + +The prompt and response messages are automatically logged to Opik and can be viewed in the UI. + +![OpenAI Integration](https://raw.githubusercontent.com/comet-ml/opik/main/apps/opik-documentation/documentation/static/img/cookbook/openai_trace_cookbook.png) + +## Using it with the `track` decorator + +If you have multiple steps in your LLM pipeline, you can use the `track` decorator to log the traces for each step. If OpenAI is called within one of these steps, the LLM call with be associated with that corresponding step: + + +```python +from opik import track +from opik.integrations.openai import track_openai +from openai import OpenAI + +os.environ["OPIK_PROJECT_NAME"] = "openai-integration-demo" + +client = OpenAI() +openai_client = track_openai(client) + + +@track +def generate_story(prompt): + res = openai_client.chat.completions.create( + model="gpt-3.5-turbo", messages=[{"role": "user", "content": prompt}] + ) + return res.choices[0].message.content + + +@track +def generate_topic(): + prompt = "Generate a topic for a story about Opik." + res = openai_client.chat.completions.create( + model="gpt-3.5-turbo", messages=[{"role": "user", "content": prompt}] + ) + return res.choices[0].message.content + + +@track +def generate_opik_story(): + topic = generate_topic() + story = generate_story(topic) + return story + + +generate_opik_story() +``` + +The trace can now be viewed in the UI: + +![OpenAI Integration](https://raw.githubusercontent.com/comet-ml/opik/main/apps/opik-documentation/documentation/static/img/cookbook/openai_trace_decorator_cookbook.png) + + diff --git a/apps/opik-documentation/documentation/fern/docs/cookbook/overview.mdx b/apps/opik-documentation/documentation/fern/docs/cookbook/overview.mdx new file mode 100644 index 0000000000..056e24341a --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs/cookbook/overview.mdx @@ -0,0 +1,94 @@ +--- +title: Opik Cookbooks +subtitle: An open-source collection of notebooks and guides for using the Opik platform. +--- + +## Guides + + + If you are looking at learning more about the Opik platform, the quickstart notebook is a comprehensive overview of + the full platform covering both the tracing and the evaluation functionality. + + +## Advanced guides + +The advanced guides cover more advanced usage of the Opik platform. + + + + In this guide, we evaluate the hallucination metric that is included with the Opik platform. + + + In this guide, we evaluate the moderation metric that is included with the Opik platform. + + + +## Integration examples + +Opik provides first-class support for many popular LLM frameworks and providers. Choose your integration below to get started: + +### LLM Providers + + + + Log all OpenAI LLM calls to Opik + + + Log all Anthropic LLM calls to Opik + + + AWS Bedrock is a managed service for high performing foundational models + + + Gemini is a family of multimodal large language models developed by Google DeepMind + + + Groq provides fast LLM inference for Open Source models + + + Ollama allows you to run open-source LLM models on your local machine + + + IBM's platform for deploying ML models + + + +### Frameworks & Tools + + + + LangChain is a framework for developing applications powered by LLMs + + + LlamaIndex is a framework for building agentic applications + + + Build production-ready LLM applications + + + LiteLLM allows you to call all LLM APIs using the OpenAI format + + + CrewAi can be used to create AI agent teams that work together to tackle complex tasks + + + DSPy is an LLM optimization framework for prompt engineering + + + Guardrails is a framework for detecting and preventing errors in LLM applications + + + LangGraph is a framework for building agentic applications built by the LangChain team + + + Simple, unified interface to multiple Generative AI providers + + + Predibase provides the fastest way to fine-tune and serve open-source LLMs + + + Ragas is a framework for evaluating Retrieval Augmented Generation (RAG) pipelines + + + +Don't see your preferred framework or tool? [Open an issue](https://github.com/comet-ml/opik/issues) to request it! In the meantime, you can use our SDK's core logging functions to track your LLM interactions - check out our [tracing documentation](/docs/opik/tracing/log_traces) for details. diff --git a/apps/opik-documentation/documentation/fern/docs/cookbook/predibase.mdx b/apps/opik-documentation/documentation/fern/docs/cookbook/predibase.mdx new file mode 100644 index 0000000000..8f5457eae3 --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs/cookbook/predibase.mdx @@ -0,0 +1,160 @@ +--- +description: Cookbook that showcases Opik's integration with Predibase +--- + +# Using Opik with Predibase + +This notebook demonstrates how to use Predibase as an LLM provider with LangChain, and how to integrate Opik for tracking and logging. + +## Setup + +First, let's install the necessary packages and set up our environment variables. + + +```python +%pip install --upgrade --quiet predibase opik +``` + +We will now configure Opik and Predibase: + + +```python +# Configure Opik +import opik +import os +import getpass + +opik.configure(use_local=False) + +# Configure predibase +os.environ["PREDIBASE_API_TOKEN"] = getpass.getpass("Enter your Predibase API token") +``` + +## Creating the Opik Tracer + +In order to log traces to Opik, we will be using the OpikTracer from the LangChain integration. + + +```python +# Import Opik tracer +from opik.integrations.langchain import OpikTracer + +# Initialize Opik tracer +opik_tracer = OpikTracer( + tags=["predibase", "langchain"], +) +``` + +## Initial Call + +Let's set up our Predibase model and make an initial call. + + +```python +from langchain_community.llms import Predibase +import os + +model = Predibase( + model="mistral-7b", + predibase_api_key=os.environ.get("PREDIBASE_API_TOKEN"), +) + +# Test the model with Opik tracing +response = model.invoke( + "Can you recommend me a nice dry wine?", + config={"temperature": 0.5, "max_new_tokens": 1024, "callbacks": [opik_tracer]}, +) +print(response) +``` + +In addition to passing the OpikTracer to the invoke method, you can also define it during the creation of the `Predibase` object: + +```python +model = Predibase( + model="mistral-7b", + predibase_api_key=os.environ.get("PREDIBASE_API_TOKEN"), +).with_config({"callbacks": [opik_tracer]}) +``` + +## SequentialChain + +Now, let's create a more complex chain and run it with Opik tracing. + + +```python +from langchain.chains import LLMChain, SimpleSequentialChain +from langchain_core.prompts import PromptTemplate + +# Synopsis chain +template = """You are a playwright. Given the title of play, it is your job to write a synopsis for that title. + +Title: {title} +Playwright: This is a synopsis for the above play:""" +prompt_template = PromptTemplate(input_variables=["title"], template=template) +synopsis_chain = LLMChain(llm=model, prompt=prompt_template) + +# Review chain +template = """You are a play critic from the New York Times. Given the synopsis of play, it is your job to write a review for that play. + +Play Synopsis: +{synopsis} +Review from a New York Times play critic of the above play:""" +prompt_template = PromptTemplate(input_variables=["synopsis"], template=template) +review_chain = LLMChain(llm=model, prompt=prompt_template) + +# Overall chain +overall_chain = SimpleSequentialChain( + chains=[synopsis_chain, review_chain], verbose=True +) + +# Run the chain with Opik tracing +review = overall_chain.run("Tragedy at sunset on the beach", callbacks=[opik_tracer]) +print(review) +``` + +## Accessing Logged Traces + +We can access the trace IDs collected by the Opik tracer. + + +```python +traces = opik_tracer.created_traces() +print("Collected trace IDs:", [trace.id for trace in traces]) + +# Flush traces to ensure all data is logged +opik_tracer.flush() +``` + +## Fine-tuned LLM Example + +Finally, let's use a fine-tuned model with Opik tracing. + +**Note:** In order to use a fine-tuned model, you will need to have access to the model and the correct model ID. The code below will return a `NotFoundError` unless the `model` and `adapter_id` are updated. + + +```python +fine_tuned_model = Predibase( + model="my-base-LLM", + predibase_api_key=os.environ.get("PREDIBASE_API_TOKEN"), + predibase_sdk_version=None, + adapter_id="my-finetuned-adapter-id", + adapter_version=1, + **{ + "api_token": os.environ.get("HUGGING_FACE_HUB_TOKEN"), + "max_new_tokens": 5, + }, +) + +# Configure the Opik tracer +fine_tuned_model = fine_tuned_model.with_config({"callbacks": [opik_tracer]}) + +# Invode the fine-tuned model +response = fine_tuned_model.invoke( + "Can you help categorize the following emails into positive, negative, and neutral?", + **{"temperature": 0.5, "max_new_tokens": 1024}, +) +print(response) + +# Final flush to ensure all traces are logged +opik_tracer.flush() +``` diff --git a/apps/opik-documentation/documentation/fern/docs/cookbook/quickstart_notebook.mdx b/apps/opik-documentation/documentation/fern/docs/cookbook/quickstart_notebook.mdx new file mode 100644 index 0000000000..b6f57b8632 --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs/cookbook/quickstart_notebook.mdx @@ -0,0 +1,521 @@ +--- +description: Quickstart cookbook that showcases Opik's evaluation, tracing and prompt management functionality. +--- + +# Quickstart notebook - Summarization task + +In this notebook, we will look at how you can use Opik to track your LLM calls, chains and agents. We will introduce the concept of tracing and how to automate the evaluation of your LLM workflows. + +We will be using a technique called Chain of Density Summarization to summarize Arxiv papers. You can learn more about this technique in the [From Sparse to Dense: GPT-4 Summarization with Chain of Density Prompting](https://arxiv.org/abs/2309.04269) paper. + +## Getting started + +We will first install the required dependencies and configure both Opik and OpenAI. + + +```python +%pip install -U opik openai requests PyPDF2 --quiet +``` + + +[Comet](https://www.comet.com/site?from=llm&utm_source=opik&utm_medium=colab&utm_content=langchain&utm_campaign=opik) provides a hosted version of the Opik platform, [simply create an account](https://www.comet.com/signup?from=llm&utm_source=opik&utm_medium=colab&utm_content=langchain&utm_campaign=opik) and grab you API Key. + +> You can also run the Opik platform locally, see the [installation guide](https://www.comet.com/docs/opik/self-host/overview/?from=llm&utm_source=opik&utm_medium=colab&utm_content=langchain&utm_campaign=opik) for more information. + + +```python +import opik +import os + +# Configure Opik +opik.configure() +``` + +## Implementing Chain of Density Summarization + +The idea behind this approach is to first generate a sparse candidate summary and then iteratively refine it with missing information without making it longer. We will start by defining two prompts: + +1. Iteration summary prompt: This prompt is used to generate and refine a candidate summary. +2. Final summary prompt: This prompt is used to generate the final summary from the sparse set of candidate summaries. + + +```python +import opik + +ITERATION_SUMMARY_PROMPT = opik.Prompt( + name="Iteration Summary Prompt", + prompt=""" +Document: {{document}} +Current summary: {{current_summary}} +Instruction to focus on: {{instruction}} + +Generate a concise, entity-dense, and highly technical summary from the provided Document that specifically addresses the given Instruction. + +Guidelines: +- Make every word count: If there is a current summary re-write it to improve flow, density and conciseness. +- Remove uninformative phrases like "the article discusses". +- The summary should become highly dense and concise yet self-contained, e.g. , easily understood without the Document. +- Make sure that the summary specifically addresses the given Instruction +""".rstrip().lstrip(), +) + +FINAL_SUMMARY_PROMPT = opik.Prompt( + name="Final Summary Prompt", + prompt=""" +Given this summary: {{current_summary}} +And this instruction to focus on: {{instruction}} +Create an extremely dense, final summary that captures all key technical information in the most concise form possible, while specifically addressing the given instruction. +""".rstrip().lstrip(), +) +``` + +We can now define the summarization chain by combining the two prompts. In order to track the LLM calls, we will use Opik's integration with OpenAI through the `track_openai` function and we will add the `@opik.track` decorator to each function so we can track the full chain and not just individual LLM calls: + + +```python +from opik.integrations.openai import track_openai +from openai import OpenAI +import opik + +# Use a dedicated quickstart endpoint, replace with your own OpenAI API Key in your own code +openai_client = track_openai( + OpenAI( + base_url="https://odbrly0rrk.execute-api.us-east-1.amazonaws.com/Prod/", + api_key="Opik-Quickstart", + ) +) + + +@opik.track +def summarize_current_summary( + document: str, + instruction: str, + current_summary: str, + model: str = "gpt-4o-mini", +): + prompt = ITERATION_SUMMARY_PROMPT.format( + document=document, current_summary=current_summary, instruction=instruction + ) + + response = openai_client.chat.completions.create( + model=model, max_tokens=4096, messages=[{"role": "user", "content": prompt}] + ) + + return response.choices[0].message.content + + +@opik.track +def iterative_density_summarization( + document: str, + instruction: str, + density_iterations: int, + model: str = "gpt-4o-mini", +): + summary = "" + for iteration in range(1, density_iterations + 1): + summary = summarize_current_summary(document, instruction, summary, model) + return summary + + +@opik.track +def final_summary(instruction: str, current_summary: str, model: str = "gpt-4o-mini"): + prompt = FINAL_SUMMARY_PROMPT.format( + current_summary=current_summary, instruction=instruction + ) + + return ( + openai_client.chat.completions.create( + model=model, max_tokens=4096, messages=[{"role": "user", "content": prompt}] + ) + .choices[0] + .message.content + ) + + +@opik.track(project_name="Chain of Density Summarization") +def chain_of_density_summarization( + document: str, + instruction: str, + model: str = "gpt-4o-mini", + density_iterations: int = 2, +): + summary = iterative_density_summarization( + document, instruction, density_iterations, model + ) + final_summary_text = final_summary(instruction, summary, model) + + return final_summary_text +``` + +Let's call the summarization chain with a sample document: + + +```python +import textwrap + +document = """ +Artificial intelligence (AI) is transforming industries, revolutionizing healthcare, finance, education, and even creative fields. AI systems +today are capable of performing tasks that previously required human intelligence, such as language processing, visual perception, and +decision-making. In healthcare, AI assists in diagnosing diseases, predicting patient outcomes, and even developing personalized treatment plans. +In finance, it helps in fraud detection, algorithmic trading, and risk management. Education systems leverage AI for personalized learning, adaptive +testing, and educational content generation. Despite these advancements, ethical concerns such as data privacy, bias, and the impact of AI on employment +remain. The future of AI holds immense potential, but also significant challenges. +""" + +instruction = "Summarize the main contributions of AI to different industries, and highlight both its potential and associated challenges." + +summary = chain_of_density_summarization(document, instruction) + +print("\n".join(textwrap.wrap(summary, width=80))) +``` + +Thanks to the `@opik.track` decorator and Opik's integration with OpenAI, we can now track the entire chain and all the LLM calls in the Opik UI: + +![Trace UI](https://raw.githubusercontent.com/comet-ml/opik/main/apps/opik-documentation/documentation/static/img/cookbook/chain_density_trace_cookbook.png) + +## Automatting the evaluation process + +### Defining a dataset +Now that we have a working chain, we can automate the evaluation process. We will start by defining a dataset of documents and instructions: + + +```python +import opik + +dataset_items = [ + { + "pdf_url": "https://arxiv.org/pdf/2301.00234", + "title": "A Survey on In-context Learning", + "instruction": "Summarize the key findings on the impact of prompt engineering in in-context learning.", + }, + { + "pdf_url": "https://arxiv.org/pdf/2301.03728", + "title": "Scaling Laws for Generative Mixed-Modal Language Models", + "instruction": "How do scaling laws apply to generative mixed-modal models according to the paper?", + }, + { + "pdf_url": "https://arxiv.org/pdf/2308.10792", + "title": "Instruction Tuning for Large Language Models: A Survey", + "instruction": "What are the major challenges in instruction tuning for large language models identified in the paper?", + }, + { + "pdf_url": "https://arxiv.org/pdf/2302.08575", + "title": "Foundation Models in Natural Language Processing: A Survey", + "instruction": "Explain the role of foundation models in the current natural language processing landscape.", + }, + { + "pdf_url": "https://arxiv.org/pdf/2306.13398", + "title": "Large-scale Multi-Modal Pre-trained Models: A Comprehensive Survey", + "instruction": "What are the cutting edge techniques used in multi-modal pre-training models?", + }, + { + "pdf_url": "https://arxiv.org/pdf/2103.07492", + "title": "Continual Learning in Neural Networks: An Empirical Evaluation", + "instruction": "What are the main challenges of continual learning for neural networks according to the paper?", + }, + { + "pdf_url": "https://arxiv.org/pdf/2304.00685v2", + "title": "Vision-Language Models for Vision Tasks: A Survey", + "instruction": "What are the most widely used vision-language models?", + }, + { + "pdf_url": "https://arxiv.org/pdf/2303.08774", + "title": "GPT-4 Technical Report", + "instruction": "What are the main differences between GPT-4 and GPT-3.5?", + }, + { + "pdf_url": "https://arxiv.org/pdf/2406.04744", + "title": "CRAG -- Comprehensive RAG Benchmark", + "instruction": "What was the approach to experimenting with different data mixtures?", + }, +] + +client = opik.Opik() +DATASET_NAME = "arXiv Papers" +dataset = client.get_or_create_dataset(name=DATASET_NAME) +dataset.insert(dataset_items) +``` + +*Note:* Opik automatically deduplicates dataset items to make it easier to iterate on your dataset. + +### Defining the evaluation metrics + +Opik includes a [library of evaluation metrics](https://www.comet.com/docs/opik/evaluation/metrics/overview) that you can use to evaluate your chains. For this particular example, we will be using a custom metric that evaluates the relevance, conciseness and technical accuracy of each summary + + +```python +from opik.evaluation.metrics import base_metric, score_result +import json + +# We will define the response format so the output has the correct schema. You can also use structured outputs with Pydantic models for this. +json_schema = { + "type": "json_schema", + "json_schema": { + "name": "summary_evaluation_schema", + "schema": { + "type": "object", + "properties": { + "relevance": { + "type": "object", + "properties": { + "score": { + "type": "integer", + "minimum": 1, + "maximum": 5, + "description": "Score between 1-5 for how well the summary addresses the instruction", + }, + "explanation": { + "type": "string", + "description": "Brief explanation of the relevance score", + }, + }, + "required": ["score", "explanation"], + }, + "conciseness": { + "type": "object", + "properties": { + "score": { + "type": "integer", + "minimum": 1, + "maximum": 5, + "description": "Score between 1-5 for how concise the summary is while retaining key information", + }, + "explanation": { + "type": "string", + "description": "Brief explanation of the conciseness score", + }, + }, + "required": ["score", "explanation"], + }, + "technical_accuracy": { + "type": "object", + "properties": { + "score": { + "type": "integer", + "minimum": 1, + "maximum": 5, + "description": "Score between 1-5 for how accurately the summary conveys technical details", + }, + "explanation": { + "type": "string", + "description": "Brief explanation of the technical accuracy score", + }, + }, + "required": ["score", "explanation"], + }, + }, + "required": ["relevance", "conciseness", "technical_accuracy"], + "additionalProperties": False, + }, + }, +} + + +# Custom Metric: One template/prompt to extract 4 scores/results +class EvaluateSummary(base_metric.BaseMetric): + # Constructor + def __init__(self, name: str): + self.name = name + + def score( + self, summary: str, instruction: str, model: str = "gpt-4o-mini", **kwargs + ): + prompt = f""" + Summary: {summary} + Instruction: {instruction} + + Evaluate the summary based on the following criteria: + 1. Relevance (1-5): How well does the summary address the given instruction? + 2. Conciseness (1-5): How concise is the summary while retaining key information? + 3. Technical Accuracy (1-5): How accurately does the summary convey technical details? + + Your response MUST be in the following JSON format: + {{ + "relevance": {{ + "score": , + "explanation": "" + }}, + "conciseness": {{ + "score": , + "explanation": "" + }}, + "technical_accuracy": {{ + "score": , + "explanation": "" + }} + }} + + Ensure that the scores are integers between 1 and 5, and that the explanations are concise. + """ + + response = openai_client.chat.completions.create( + model=model, + max_tokens=1000, + messages=[{"role": "user", "content": prompt}], + response_format=json_schema, + ) + + eval_dict = json.loads(response.choices[0].message.content) + + return [ + score_result.ScoreResult( + name="summary_relevance", + value=eval_dict["relevance"]["score"], + reason=eval_dict["relevance"]["explanation"], + ), + score_result.ScoreResult( + name="summary_conciseness", + value=eval_dict["conciseness"]["score"], + reason=eval_dict["conciseness"]["explanation"], + ), + score_result.ScoreResult( + name="summary_technical_accuracy", + value=eval_dict["technical_accuracy"]["score"], + reason=eval_dict["technical_accuracy"]["explanation"], + ), + score_result.ScoreResult( + name="summary_average_score", + value=round(sum(eval_dict[k]["score"] for k in eval_dict) / 3, 2), + reason="The average of the 3 summary evaluation metrics", + ), + ] +``` + +### Create the task we want to evaluate + +We can now create the task we want to evaluate. In this case, we will have the dataset item as an input and return a dictionary containing the summary and the instruction so that we can use this in the evaluation metrics: + + +```python +import requests +import io +from PyPDF2 import PdfReader +from typing import Dict + + +# Load and extract text from PDFs +@opik.track +def load_pdf(pdf_url: str) -> str: + # Download the PDF + response = requests.get(pdf_url) + pdf_file = io.BytesIO(response.content) + + # Read the PDF + pdf_reader = PdfReader(pdf_file) + + # Extract text from all pages + text = "" + for page in pdf_reader.pages: + text += page.extract_text() + + # Truncate the text to 100000 characters as this is the maximum supported by OpenAI + text = text[:100000] + return text + + +def evaluation_task(x: Dict): + text = load_pdf(x["pdf_url"]) + instruction = x["instruction"] + model = MODEL + density_iterations = DENSITY_ITERATIONS + + result = chain_of_density_summarization( + document=text, + instruction=instruction, + model=model, + density_iterations=density_iterations, + ) + + return {"summary": result} +``` + +### Run the automated evaluation + +We can now use the `evaluate` method to evaluate the summaries in our dataset: + + +```python +from opik.evaluation import evaluate + +os.environ["OPIK_PROJECT_NAME"] = "summary-evaluation-prompts" + +MODEL = "gpt-4o-mini" +DENSITY_ITERATIONS = 2 + +experiment_config = { + "iteration_summary_prompt": ITERATION_SUMMARY_PROMPT, + "final_summary_prompt": FINAL_SUMMARY_PROMPT, + "model": MODEL, + "density_iterations": DENSITY_ITERATIONS, +} + +res = evaluate( + dataset=dataset, + experiment_config=experiment_config, + task=evaluation_task, + scoring_metrics=[EvaluateSummary(name="summary-metrics")], + prompt=ITERATION_SUMMARY_PROMPT, + project_name="Chain of Density Summarization", +) +``` + +The experiment results are now available in the Opik UI: + +![Trace UI](https://raw.githubusercontent.com/comet-ml/opik/main/apps/opik-documentation/documentation/static/img/cookbook/chain_density_experiment_cookbook.png) + + +## Comparing prompt templates + +We will update the iteration summary prompt and evaluate its impact on the evaluation metrics. + + +```python +import opik + +ITERATION_SUMMARY_PROMPT = opik.Prompt( + name="Iteration Summary Prompt", + prompt="""Document: {{document}} +Current summary: {{current_summary}} +Instruction to focus on: {{instruction}} + +Generate a concise, entity-dense, and highly technical summary from the provided Document that specifically addresses the given Instruction. + +Guidelines: +1. **Maximize Clarity and Density**: Revise the current summary to enhance flow, density, and conciseness. +2. **Eliminate Redundant Language**: Avoid uninformative phrases such as "the article discusses." +3. **Ensure Self-Containment**: The summary should be dense and concise, easily understandable without referring back to the document. +4. **Align with Instruction**: Make sure the summary specifically addresses the given instruction. + +""".rstrip().lstrip(), +) +``` + + +```python +from opik.evaluation import evaluate + +os.environ["OPIK_PROJECT_NAME"] = "summary-evaluation-prompts" + +MODEL = "gpt-4o-mini" +DENSITY_ITERATIONS = 2 + +experiment_config = { + "iteration_summary_prompt": ITERATION_SUMMARY_PROMPT, + "final_summary_prompt": FINAL_SUMMARY_PROMPT, + "model": MODEL, + "density_iterations": DENSITY_ITERATIONS, +} + +res = evaluate( + dataset=dataset, + experiment_config=experiment_config, + task=evaluation_task, + scoring_metrics=[EvaluateSummary(name="summary-metrics")], + prompt=ITERATION_SUMMARY_PROMPT, + project_name="Chain of Density Summarization", +) +``` + +You can now compare the results between the two experiments in the Opik UI: + +![Trace UI](https://raw.githubusercontent.com/comet-ml/opik/main/apps/opik-documentation/documentation/static/img/cookbook/chain_density_trace_comparison_cookbook.png) diff --git a/apps/opik-documentation/documentation/fern/docs/cookbook/ragas.mdx b/apps/opik-documentation/documentation/fern/docs/cookbook/ragas.mdx new file mode 100644 index 0000000000..2cfb423e1f --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs/cookbook/ragas.mdx @@ -0,0 +1,283 @@ +--- +description: Cookbook that showcases Opik's integration with the Ragas Python SDK +--- + +# Using Ragas to evaluate RAG pipelines + +In this notebook, we will showcase how to use Opik with Ragas for monitoring and evaluation of RAG (Retrieval-Augmented Generation) pipelines. + +There are two main ways to use Opik with Ragas: + +1. Using Ragas metrics to score traces +2. Using the Ragas `evaluate` function to score a dataset + +## Creating an account on Comet.com + +[Comet](https://www.comet.com/site?from=llm&utm_source=opik&utm_medium=colab&utm_content=ragas&utm_campaign=opik) provides a hosted version of the Opik platform, [simply create an account](https://www.comet.com/signup?from=llm&utm_source=opik&utm_medium=colab&utm_content=ragas&utm_campaign=opik) and grab you API Key. + +> You can also run the Opik platform locally, see the [installation guide](https://www.comet.com/docs/opik/self-host/overview/?from=llm&utm_source=opik&utm_medium=colab&utm_content=ragas&utm_campaign=opik) for more information. + + +```python +%pip install --quiet --upgrade opik ragas nltk +``` + + +```python +import opik + +opik.configure(use_local=False) +``` + +## Preparing our environment + +First, we will configure the OpenAI API key. + + +```python +import os +import getpass + +if "OPENAI_API_KEY" not in os.environ: + os.environ["OPENAI_API_KEY"] = getpass.getpass("Enter your OpenAI API key: ") +``` + +## Integrating Opik with Ragas + +### Using Ragas metrics to score traces + +Ragas provides a set of metrics that can be used to evaluate the quality of a RAG pipeline, including but not limited to: `answer_relevancy`, `answer_similarity`, `answer_correctness`, `context_precision`, `context_recall`, `context_entity_recall`, `summarization_score`. You can find a full list of metrics in the [Ragas documentation](https://docs.ragas.io/en/latest/references/metrics.html#). + +These metrics can be computed on the fly and logged to traces or spans in Opik. For this example, we will start by creating a simple RAG pipeline and then scoring it using the `answer_relevancy` metric. + +#### Create the Ragas metric + +In order to use the Ragas metric without using the `evaluate` function, you need to initialize the metric with a `RunConfig` object and an LLM provider. For this example, we will use LangChain as the LLM provider with the Opik tracer enabled. + +We will first start by initializing the Ragas metric: + + +```python +# Import the metric +from ragas.metrics import AnswerRelevancy + +# Import some additional dependencies +from langchain_openai.chat_models import ChatOpenAI +from langchain_openai.embeddings import OpenAIEmbeddings +from ragas.llms import LangchainLLMWrapper +from ragas.embeddings import LangchainEmbeddingsWrapper + +# Initialize the Ragas metric +llm = LangchainLLMWrapper(ChatOpenAI()) +emb = LangchainEmbeddingsWrapper(OpenAIEmbeddings()) + +answer_relevancy_metric = AnswerRelevancy(llm=llm, embeddings=emb) +``` + +Once the metric is initialized, you can use it to score a sample question. Given that the metric scoring is done asynchronously, you need to use the `asyncio` library to run the scoring function. + + +```python +# Run this cell first if you are running this in a Jupyter notebook +import nest_asyncio + +nest_asyncio.apply() +``` + + +```python +import asyncio +from ragas.integrations.opik import OpikTracer +from ragas.dataset_schema import SingleTurnSample +import os + +os.environ["OPIK_PROJECT_NAME"] = "ragas-integration" + + +# Define the scoring function +def compute_metric(metric, row): + row = SingleTurnSample(**row) + + opik_tracer = OpikTracer(tags=["ragas"]) + + async def get_score(opik_tracer, metric, row): + score = await metric.single_turn_ascore(row, callbacks=[opik_tracer]) + return score + + # Run the async function using the current event loop + loop = asyncio.get_event_loop() + + result = loop.run_until_complete(get_score(opik_tracer, metric, row)) + return result + + +# Score a simple example +row = { + "user_input": "What is the capital of France?", + "response": "Paris", + "retrieved_contexts": ["Paris is the capital of France.", "Paris is in France."], +} + +score = compute_metric(answer_relevancy_metric, row) +print("Answer Relevancy score:", score) +``` + +If you now navigate to Opik, you will be able to see that a new trace has been created in the `Default Project` project. + +#### Score traces + +You can score traces by using the `update_current_trace` function. + +The advantage of this approach is that the scoring span is added to the trace allowing for a more fine-grained analysis of the RAG pipeline. It will however run the Ragas metric calculation synchronously and so might not be suitable for production use-cases. + + +```python +from opik import track, opik_context + + +@track +def retrieve_contexts(question): + # Define the retrieval function, in this case we will hard code the contexts + return ["Paris is the capital of France.", "Paris is in France."] + + +@track +def answer_question(question, contexts): + # Define the answer function, in this case we will hard code the answer + return "Paris" + + +@track(name="Compute Ragas metric score", capture_input=False) +def compute_rag_score(answer_relevancy_metric, question, answer, contexts): + # Define the score function + row = {"user_input": question, "response": answer, "retrieved_contexts": contexts} + score = compute_metric(answer_relevancy_metric, row) + return score + + +@track +def rag_pipeline(question): + # Define the pipeline + contexts = retrieve_contexts(question) + answer = answer_question(question, contexts) + + score = compute_rag_score(answer_relevancy_metric, question, answer, contexts) + opik_context.update_current_trace( + feedback_scores=[{"name": "answer_relevancy", "value": round(score, 4)}] + ) + + return answer + + +rag_pipeline("What is the capital of France?") +``` + +#### Evaluating datasets using the Opik `evaluate` function + +You can use Ragas metrics with the Opik `evaluate` function. This will compute the metrics on all the rows of the dataset and return a summary of the results. + +As Ragas metrics are only async, we will need to create a wrapper to be able to use them with the Opik `evaluate` function. + + +```python +from datasets import load_dataset +from opik.evaluation.metrics import base_metric, score_result +import opik + + +opik_client = opik.Opik() + +# Create a small dataset +fiqa_eval = load_dataset("explodinggradients/fiqa", "ragas_eval") + +# Reformat the dataset to match the schema expected by the Ragas evaluate function +hf_dataset = fiqa_eval["baseline"].select(range(3)) +dataset_items = hf_dataset.map( + lambda x: { + "user_input": x["question"], + "reference": x["ground_truths"][0], + "retrieved_contexts": x["contexts"], + } +) +dataset = opik_client.get_or_create_dataset("ragas-demo-dataset") +dataset.insert(dataset_items) + + +# Create an evaluation task +def evaluation_task(x): + return { + "user_input": x["question"], + "response": x["answer"], + "retrieved_contexts": x["contexts"], + } + + +# Create scoring metric wrapper +class AnswerRelevancyWrapper(base_metric.BaseMetric): + def __init__(self, metric): + self.name = "answer_relevancy_metric" + self.metric = metric + + async def get_score(self, row): + row = SingleTurnSample(**row) + score = await self.metric.single_turn_ascore(row) + return score + + def score(self, user_input, response, **ignored_kwargs): + # Run the async function using the current event loop + loop = asyncio.get_event_loop() + + result = loop.run_until_complete(self.get_score(row)) + + return score_result.ScoreResult(value=result, name=self.name) + + +scoring_metric = AnswerRelevancyWrapper(answer_relevancy_metric) +opik.evaluation.evaluate( + dataset, + evaluation_task, + scoring_metrics=[scoring_metric], + task_threads=1, +) +``` + +#### Evaluating datasets using the Ragas `evaluate` function + +If you looking at evaluating a dataset, you can use the Ragas `evaluate` function. When using this function, the Ragas library will compute the metrics on all the rows of the dataset and return a summary of the results. + +You can use the `OpikTracer` callback to log the results of the evaluation to the Opik platform: + + +```python +from datasets import load_dataset +from ragas.metrics import context_precision, answer_relevancy, faithfulness +from ragas import evaluate + +fiqa_eval = load_dataset("explodinggradients/fiqa", "ragas_eval") + +# Reformat the dataset to match the schema expected by the Ragas evaluate function +dataset = fiqa_eval["baseline"].select(range(3)) + +dataset = dataset.map( + lambda x: { + "user_input": x["question"], + "reference": x["ground_truths"][0], + "retrieved_contexts": x["contexts"], + } +) + +opik_tracer_eval = OpikTracer(tags=["ragas_eval"], metadata={"evaluation_run": True}) + +result = evaluate( + dataset, + metrics=[context_precision, faithfulness, answer_relevancy], + callbacks=[opik_tracer_eval], +) + +print(result) +``` + + +```python + +``` diff --git a/apps/opik-documentation/documentation/fern/docs/cookbook/watsonx.mdx b/apps/opik-documentation/documentation/fern/docs/cookbook/watsonx.mdx new file mode 100644 index 0000000000..c04c5bb976 --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs/cookbook/watsonx.mdx @@ -0,0 +1,131 @@ +--- +description: Cookbook that showcases Opik's integration with Watsonx through the LiteLLM Python SDK +--- + +# Using Opik with watsonx + +Opik integrates with watsonx to provide a simple way to log traces for all watsonx LLM calls. This works for all watsonx models. + +## Creating an account on Comet.com + +[Comet](https://www.comet.com/site?from=llm&utm_source=opik&utm_medium=colab&utm_content=watsonx&utm_campaign=opik) provides a hosted version of the Opik platform, [simply create an account](https://www.comet.com/signup?from=llm&utm_source=opik&utm_medium=colab&utm_content=watsonx&utm_campaign=opik) and grab you API Key. + +> You can also run the Opik platform locally, see the [installation guide](https://www.comet.com/docs/opik/self-host/overview/?from=llm&utm_source=opik&utm_medium=colab&utm_content=watsonx&utm_campaign=opik) for more information. + + +```python +%pip install --upgrade opik litellm +``` + + +```python +import opik + +opik.configure(use_local=False) +``` + +## Preparing our environment + +First, we will set up our watsonx API keys. You can learn more about how to find these in the [Opik watsonx integration guide](https://www.comet.com/docs/opik/tracing/integrations/watsonx#configuring-watsonx). + + +```python +import os + +os.environ["WATSONX_URL"] = "" # (required) Base URL of your WatsonX instance +# (required) either one of the following: +os.environ["WATSONX_API_KEY"] = "" # IBM cloud API key +os.environ["WATSONX_TOKEN"] = "" # IAM auth token +# optional - can also be passed as params to completion() or embedding() +# os.environ["WATSONX_PROJECT_ID"] = "" # Project ID of your WatsonX instance +# os.environ["WATSONX_DEPLOYMENT_SPACE_ID"] = "" # ID of your deployment space to use deployed models +``` + +## Configure LiteLLM + +Add the LiteLLM OpikTracker to log traces and steps to Opik: + + +```python +import litellm +import os +from litellm.integrations.opik.opik import OpikLogger +from opik import track +from opik.opik_context import get_current_span_data + +os.environ["OPIK_PROJECT_NAME"] = "watsonx-integration-demo" +opik_logger = OpikLogger() +litellm.callbacks = [opik_logger] +``` + +## Logging traces + +Now each completion will logs a separate trace to LiteLLM: + + +```python +# litellm.set_verbose=True +prompt = """ +Write a short two sentence story about Opik. +""" + +response = litellm.completion( + model="watsonx/ibm/granite-13b-chat-v2", + messages=[{"role": "user", "content": prompt}], +) + +print(response.choices[0].message.content) +``` + +The prompt and response messages are automatically logged to Opik and can be viewed in the UI. + +![watsonx Cookbook](https://raw.githubusercontent.com/comet-ml/opik/main/apps/opik-documentation/documentation/static/img/cookbook/watsonx_trace_cookbook.png) + +## Using it with the `track` decorator + +If you have multiple steps in your LLM pipeline, you can use the `track` decorator to log the traces for each step. If watsonx is called within one of these steps, the LLM call with be associated with that corresponding step: + + +```python +@track +def generate_story(prompt): + response = litellm.completion( + model="watsonx/ibm/granite-13b-chat-v2", + messages=[{"role": "user", "content": prompt}], + metadata={ + "opik": { + "current_span_data": get_current_span_data(), + }, + }, + ) + return response.choices[0].message.content + + +@track +def generate_topic(): + prompt = "Generate a topic for a story about Opik." + response = litellm.completion( + model="watsonx/ibm/granite-13b-chat-v2", + messages=[{"role": "user", "content": prompt}], + metadata={ + "opik": { + "current_span_data": get_current_span_data(), + }, + }, + ) + return response.choices[0].message.content + + +@track +def generate_opik_story(): + topic = generate_topic() + story = generate_story(topic) + return story + + +generate_opik_story() +``` + +The trace can now be viewed in the UI: + +![watsonx Cookbook](https://raw.githubusercontent.com/comet-ml/opik/main/apps/opik-documentation/documentation/static/img/cookbook/watsonx_trace_decorator_cookbook.png) diff --git a/apps/opik-documentation/documentation/docs/evaluation/concepts.md b/apps/opik-documentation/documentation/fern/docs/evaluation/concepts.mdx similarity index 80% rename from apps/opik-documentation/documentation/docs/evaluation/concepts.md rename to apps/opik-documentation/documentation/fern/docs/evaluation/concepts.mdx index 99ebc31fa6..8f2167f981 100644 --- a/apps/opik-documentation/documentation/docs/evaluation/concepts.md +++ b/apps/opik-documentation/documentation/fern/docs/evaluation/concepts.mdx @@ -1,13 +1,11 @@ --- -sidebar_label: Concepts -description: Introduces the concepts behind Opik's evaluation framework +subtitle: Introduces the concepts behind Opik's evaluation framework --- -# Evaluation Concepts - -:::tip -If you want to jump straight to running evaluations, you can head to the [Evaluate prompts](/docs/evaluation/evaluate_prompt.md) or [Evaluate your LLM application](/docs/evaluation/evaluate_your_llm.md) guides. -::: + + If you want to jump straight to running evaluations, you can head to the [Evaluate + prompts](/evaluation/evaluate_prompt) or [Evaluate your LLM application](/evaluation/evaluate_your_llm) guides. + When working with LLM applications, the bottleneck to iterating faster is often the evaluation process. While it is possible to manually review your LLM application's output, this process is slow and not scalable. Instead of manually reviewing your LLM application's output, Opik allows you to automate the evaluation of your LLM application. @@ -16,7 +14,9 @@ In order to understand how to run evaluations in Opik, it is important to first 1. **Dataset**: A dataset is a collection of samples that your LLM application will be evaluated on. Datasets only store the input and expected outputs for each sample, the output from your LLM application will be computed and scored during the evaluation process. 2. **Experiment**: An experiment is a single evaluation of your LLM application. During an experiment, we process each dataset item, compute the output based on your LLM application and then score the output. -![Evaluation Concepts](/img/evaluation/evaluation_concepts.png) + + + In this section, we will walk through all the concepts associated with Opik's evaluation framework. @@ -28,15 +28,16 @@ Given the importance of datasets in the evaluation process, teams often spend a 1. **Manually curating examples**: As a first step, you can manually curate a set of examples based on your knowledge of the application you are building. You can also leverage subject matter experts to help in the creation of the dataset. -2. **Using synthetic data**: If you don't have enough data to create a diverse set of examples, you can turn to synthetic data generation tools to help you create a dataset. The [LangChain cookbook](/docs/cookbook/langchain.md) has a great example of how to use synthetic data generation tools to create a dataset. +2. **Using synthetic data**: If you don't have enough data to create a diverse set of examples, you can turn to synthetic data generation tools to help you create a dataset. The [LangChain cookbook](/cookbook/langchain) has a great example of how to use synthetic data generation tools to create a dataset. 3. **Leveraging production data**: If you application is in production, you can leverage the data that is being generated to augment your dataset. While this is often not the first step in creating a dataset, it can be a great way to to enrich your dataset with real world data. If you are using Opik for production monitoring, you can easily add traces to your dataset by selecting them in the UI and selecting `Add to dataset` in the `Actions` dropdown. -:::tip -You can learn more about how to manage your datasets in Opik in the [Manage Datasets](/docs/evaluation/manage_datasets.md) section. -::: + + You can learn more about how to manage your datasets in Opik in the [Manage Datasets](/evaluation/manage_datasets) + section. + ## Experiments @@ -55,18 +56,22 @@ The experiment configuration object allows you to store some metadata associated You can then compare the configuration of two different experiments from the Opik UI to see what has changed. -![Experiment Configuration](/img/evaluation/compare_experiment_config.png) + + + ### Experiment Items Experiment items store the input, expected output, actual output and feedback scores for each dataset sample that was processed during an experiment. In addition, a trace is associated with each item to allow you to easily understand why a given item scored the way it did. -![Experiment Items](/img/evaluation/experiment_items.png) + + + ## Learn more We have provided some guides to help you get started with Opik's evaluation framework: -1. [Overview of Opik's evaluation features](/docs/evaluation/overview.mdx) -2. [Evaluate prompts](/docs/evaluation/evaluate_prompt.md) -3. [Evaluate your LLM application](/docs/evaluation/evaluate_your_llm.md) +1. [Overview of Opik's evaluation features](/evaluation/overview) +2. [Evaluate prompts](/evaluation/evaluate_prompt) +3. [Evaluate your LLM application](/evaluation/evaluate_your_llm) diff --git a/apps/opik-documentation/documentation/docs/evaluation/evaluate_prompt.md b/apps/opik-documentation/documentation/fern/docs/evaluation/evaluate_prompt.mdx similarity index 92% rename from apps/opik-documentation/documentation/docs/evaluation/evaluate_prompt.md rename to apps/opik-documentation/documentation/fern/docs/evaluation/evaluate_prompt.mdx index 11415a6745..3315770096 100644 --- a/apps/opik-documentation/documentation/docs/evaluation/evaluate_prompt.md +++ b/apps/opik-documentation/documentation/fern/docs/evaluation/evaluate_prompt.mdx @@ -1,15 +1,14 @@ --- -sidebar_label: Evaluate Prompts -description: Step by step guide on how to evaluate LLM prompts +subtitle: Step by step guide on how to evaluate LLM prompts --- -# Evaluate Prompts - When developing prompts and performing prompt engineering, it can be challenging to know if a new prompt is better than the previous version. Opik Experiments allow you to evaluate the prompt on multiple samples, score each LLM output and compare the performance of different prompts. -![Experiment page](/img/evaluation/experiment_items.png) + + + There are two way to evaluate a prompt in Opik: @@ -56,13 +55,15 @@ evaluate_prompt( Once the evaluation is complete, you can view the responses in the Opik UI and score each LLM output. -![Experiment page](/img/evaluation/experiment_items.png) + + + ### Automate the scoring process Manually reviewing each LLM output can be time-consuming and error-prone. The `evaluate_prompt` function allows you to specify a list of scoring metrics which allows you to score each LLM output. Opik has a set of built-in metrics that allow you to detect hallucinations, answer relevance, etc and if we don't have the metric you need, you can easily create your own. -You can find a full list of all the Opik supported metrics in the [Metrics Overview](/evaluation/metrics/overview.md) section or you can define your own metric using [Custom Metrics](/evaluation/metrics/custom_metric.md). +You can find a full list of all the Opik supported metrics in the [Metrics Overview](/evaluation/metrics/overview) section or you can define your own metric using [Custom Metrics](/evaluation/metrics/custom_metric) section. By adding the `scoring_metrics` parameter to the `evaluate_prompt` function, you can specify a list of metrics to use for scoring. We will update the example above to use the `Hallucination` metric for scoring: @@ -121,4 +122,4 @@ evaluate_prompt( ## Next steps -To evaluate complex LLM applications like RAG applications or agents, you can use the [`evaluate`](/evaluation/evaluate_your_llm.md) function. +To evaluate complex LLM applications like RAG applications or agents, you can use the [`evaluate`](/evaluation/evaluate_your_llm) function. diff --git a/apps/opik-documentation/documentation/docs/evaluation/evaluate_your_llm.md b/apps/opik-documentation/documentation/fern/docs/evaluation/evaluate_your_llm.mdx similarity index 86% rename from apps/opik-documentation/documentation/docs/evaluation/evaluate_your_llm.md rename to apps/opik-documentation/documentation/fern/docs/evaluation/evaluate_your_llm.mdx index 00c5e7480d..48a7f9fb10 100644 --- a/apps/opik-documentation/documentation/docs/evaluation/evaluate_your_llm.md +++ b/apps/opik-documentation/documentation/fern/docs/evaluation/evaluate_your_llm.mdx @@ -1,16 +1,13 @@ --- -sidebar_label: Evaluate Complex LLM Applications -description: Step by step guide on how to evaluate your LLM application -pytest_codeblocks_execute_previous: true +subtitle: Step by step guide on how to evaluate your LLM application --- -# Evaluate Complex LLM Applications - Evaluating your LLM application allows you to have confidence in the performance of your LLM application. In this guide, we will walk through the process of evaluating complex applications like LLM chains or agents. -:::tip -In this guide, we will focus on evaluating complex LLM applications. If you are looking at evaluating single prompts you can refer to the [Evaluate A Prompt](/evaluation/evaluate_prompt.md) guide. -::: + + In this guide, we will focus on evaluating complex LLM applications. If you are looking at evaluating single prompts + you can refer to the [Evaluate A Prompt](/evaluation/evaluate_prompt) guide. + The evaluation is done in five steps: @@ -43,9 +40,10 @@ def your_llm_application(input: str) -> str: return response.choices[0].message.content ``` -:::tip -Here we have added the `track` decorator so that this trace and all its nested steps are logged to the platform for further analysis. -::: + + Here we have added the `track` decorator so that this trace and all its nested steps are logged to the platform for + further analysis. + ## 2. Define the evaluation task @@ -58,9 +56,10 @@ def evaluation_task(x): } ``` -:::warning -If the dictionary returned does not match with the parameters expected by the metrics, you will get inconsistent evaluation results. -::: + + If the dictionary returned does not match with the parameters expected by the metrics, you will get inconsistent + evaluation results. + ## 3. Choose the evaluation Dataset @@ -104,9 +103,10 @@ from opik.evaluation.metrics import Hallucination hallucination_metric = Hallucination() ``` -:::tip -Each metric expects the data in a certain format. You will need to ensure that the task you have defined in step 1 returns the data in the correct format. -::: + + Each metric expects the data in a certain format. You will need to ensure that the task you have defined in step 1 + returns the data in the correct format. + ## 5. Run the evaluation @@ -159,9 +159,10 @@ evaluation = evaluate( ) ``` -:::tip -You can use the `experiment_config` parameter to store information about your evaluation task. Typically we see teams store information about the prompt template, the model used and model parameters used to evaluate the application. -::: + + You can use the `experiment_config` parameter to store information about your evaluation task. Typically we see teams + store information about the prompt template, the model used and model parameters used to evaluate the application. + ## Advanced usage @@ -182,7 +183,7 @@ evaluation = evaluate( ### Linking prompts to experiments -The [Opik prompt library](/prompt_engineering/prompt_management.mdx) can be used to version your prompt templates. +The [Opik prompt library](/prompt_engineering/prompt_management) can be used to version your prompt templates. When creating an Experiment, you can link the Experiment to a specific prompt version: @@ -205,7 +206,10 @@ evaluation = evaluate( ``` The experiment will now be linked to the prompt allowing you to view all experiments that use a specific prompt: -![linked prompt](/img/evaluation/linked_prompt.png) + + + + ### Logging traces to a specific project @@ -242,7 +246,7 @@ In order to evaluate datasets more efficiently, Opik uses multiple background th You can access all the experiments logged to the platform from the SDK with the [`Opik.get_experiments_by_name`](https://www.comet.com/docs/opik/python-sdk-reference/Opik.html#opik.Opik.get_experiment_by_name) and [`Opik.get_experiment_by_id`](https://www.comet.com/docs/opik/python-sdk-reference/Opik.html#opik.Opik.get_experiment_by_id) methods: -```python pytest_codeblocks_skip=true +```python {pytest_codeblocks_skip=true} import opik # Get the experiment diff --git a/apps/opik-documentation/documentation/docs/evaluation/manage_datasets.md b/apps/opik-documentation/documentation/fern/docs/evaluation/manage_datasets.mdx similarity index 81% rename from apps/opik-documentation/documentation/docs/evaluation/manage_datasets.md rename to apps/opik-documentation/documentation/fern/docs/evaluation/manage_datasets.mdx index 192a9bf253..56c3750341 100644 --- a/apps/opik-documentation/documentation/docs/evaluation/manage_datasets.md +++ b/apps/opik-documentation/documentation/fern/docs/evaluation/manage_datasets.mdx @@ -1,10 +1,7 @@ --- -sidebar_label: Manage Datasets -description: Guides you through the process of creating and managing datasets +subtitle: Guides you through the process of creating and managing datasets --- -# Manage Datasets - Datasets can be used to track test cases you would like to evaluate your LLM on. Each dataset is made up of dictionary with any key value pairs. When getting started, we recommend having an `input` and optional `expected_output` fields for example. These datasets can be created from: @@ -50,21 +47,23 @@ dataset.insert([ ]) ``` -:::tip -Opik automatically deduplicates items that are inserted into a dataset when using the Python SDK. This means that you -can insert the same item multiple times without duplicating it in the dataset. This combined with -the `get_or_create_dataset` method means that you can use the SDK to manage your datasets in a "fire and forget" manner. -::: + + Opik automatically deduplicates items that are inserted into a dataset when using the Python SDK. This means that you + can insert the same item multiple times without duplicating it in the dataset. This combined with the + `get_or_create_dataset` method means that you can use the SDK to manage your datasets in a "fire and forget" manner. + Once the items have been inserted, you can view them them in the Opik UI: -![Opik Dataset](/img/evaluation/dataset_items_page.png) + + + #### Inserting items from a JSONL file You can also insert items from a JSONL file: -```python pytest_codeblocks_skip=true +```python {pytest_codeblocks_skip=true} dataset.read_jsonl_from_file("path/to/file.jsonl") ``` @@ -79,13 +78,13 @@ The format of the JSONL file should be a JSON object per line. For example: You can also insert items from a Pandas DataFrame: -```python pytest_codeblocks_skip=true +```python {pytest_codeblocks_skip=true} dataset.insert_from_pandas(dataframe=df) ``` The `keys_mapping` parameter maps the column names in the DataFrame to the keys in the dataset items, this can be useful if you want to rename columns before inserting them into the dataset: -```python pytest_codeblocks_skip=true +```python {pytest_codeblocks_skip=true} dataset.insert_from_pandas(dataframe=df, keys_mapping={"Expected output": "expected_output"}) ``` @@ -93,7 +92,7 @@ dataset.insert_from_pandas(dataframe=df, keys_mapping={"Expected output": "expec You can delete items in a dataset by using the `delete` method: -```python pytest_codeblocks_skip=true +```python {pytest_codeblocks_skip=true} from opik import Opik # Get or create a dataset @@ -103,10 +102,10 @@ dataset = client.get_dataset(name="My dataset") dataset.delete(items_ids=["123", "456"]) ``` -:::tip + You can also remove all the items in a dataset by using the `clear` method: -```python pytest_codeblocks_skip=true +```python {pytest_codeblocks_skip=true} from opik import Opik # Get or create a dataset @@ -116,13 +115,13 @@ dataset = client.get_dataset(name="My dataset") dataset.clear() ``` -::: + ## Downloading a dataset from Opik You can download a dataset from Opik using the `get_dataset` method: -```python pytest_codeblocks_skip=true +```python {pytest_codeblocks_skip=true} from opik import Opik client = Opik() @@ -131,7 +130,7 @@ dataset = client.get_dataset(name="My dataset") Once the dataset has been retrieved, you can access it's items using the `to_pandas()` or `to_json` methods: -```python pytest_codeblocks_skip=true +```python {pytest_codeblocks_skip=true} from opik import Opik client = Opik() diff --git a/apps/opik-documentation/documentation/docs/evaluation/metrics/answer_relevance.md b/apps/opik-documentation/documentation/fern/docs/evaluation/metrics/answer_relevance.mdx similarity index 97% rename from apps/opik-documentation/documentation/docs/evaluation/metrics/answer_relevance.md rename to apps/opik-documentation/documentation/fern/docs/evaluation/metrics/answer_relevance.mdx index 632f0fb073..6d2614e156 100644 --- a/apps/opik-documentation/documentation/docs/evaluation/metrics/answer_relevance.md +++ b/apps/opik-documentation/documentation/fern/docs/evaluation/metrics/answer_relevance.mdx @@ -1,10 +1,7 @@ --- -sidebar_label: AnswerRelevance description: Describes the Answer Relevance metric --- -# Answer Relevance - The Answer Relevance metric allows you to evaluate how relevant and appropriate the LLM's response is to the given input question or prompt. To assess the relevance of the answer, you will need to provide the LLM input (question or prompt) and the LLM output (generated answer). Unlike the Hallucination metric, the Answer Relevance metric focuses on the appropriateness and pertinence of the response rather than factual accuracy. You can use the `AnswerRelevance` metric as follows: @@ -25,7 +22,7 @@ Asynchronous scoring is also supported with the `ascore` scoring method. ## Detecting answer relevance -Opik uses an LLM as a Judge to detect answer relevance, for this we have a prompt template that is used to generate the prompt for the LLM. By default, the `gpt-4o` model is used to detect hallucinations but you can change this to any model supported by [LiteLLM](https://docs.litellm.ai/docs/providers) by setting the `model` parameter. You can learn more about customizing models in the [Customize models for LLM as a Judge metrics](/evaluation/metrics/custom_model.md) section. +Opik uses an LLM as a Judge to detect answer relevance, for this we have a prompt template that is used to generate the prompt for the LLM. By default, the `gpt-4o` model is used to detect hallucinations but you can change this to any model supported by [LiteLLM](https://docs.litellm.ai/docs/providers) by setting the `model` parameter. You can learn more about customizing models in the [Customize models for LLM as a Judge metrics](/evaluation/metrics/custom_model) section. The template uses a few-shot prompting technique to detect answer relevance. The template is as follows: diff --git a/apps/opik-documentation/documentation/docs/evaluation/metrics/context_precision.md b/apps/opik-documentation/documentation/fern/docs/evaluation/metrics/context_precision.mdx similarity index 98% rename from apps/opik-documentation/documentation/docs/evaluation/metrics/context_precision.md rename to apps/opik-documentation/documentation/fern/docs/evaluation/metrics/context_precision.mdx index 6088b49a79..179409ca15 100644 --- a/apps/opik-documentation/documentation/docs/evaluation/metrics/context_precision.md +++ b/apps/opik-documentation/documentation/fern/docs/evaluation/metrics/context_precision.mdx @@ -1,10 +1,7 @@ --- -sidebar_label: ContextPrecision description: Describes the Context Precision metric --- -# ContextPrecision - The context precision metric evaluates the accuracy and relevance of an LLM's response based on provided context, helping to identify potential hallucinations or misalignments with the given information. ## How to use the ContextPrecision metric @@ -28,7 +25,7 @@ Asynchronous scoring is also supported with the `ascore` scoring method. ## ContextPrecision Prompt -Opik uses an LLM as a Judge to compute context precision, for this we have a prompt template that is used to generate the prompt for the LLM. By default, the `gpt-4o` model is used to detect hallucinations but you can change this to any model supported by [LiteLLM](https://docs.litellm.ai/docs/providers) by setting the `model` parameter. You can learn more about customizing models in the [Customize models for LLM as a Judge metrics](/evaluation/metrics/custom_model.md) section. +Opik uses an LLM as a Judge to compute context precision, for this we have a prompt template that is used to generate the prompt for the LLM. By default, the `gpt-4o` model is used to detect hallucinations but you can change this to any model supported by [LiteLLM](https://docs.litellm.ai/docs/providers) by setting the `model` parameter. You can learn more about customizing models in the [Customize models for LLM as a Judge metrics](/evaluation/metrics/custom_model) section. The template uses a few-shot prompting technique to compute context precision. The template is as follows: diff --git a/apps/opik-documentation/documentation/docs/evaluation/metrics/context_recall.md b/apps/opik-documentation/documentation/fern/docs/evaluation/metrics/context_recall.mdx similarity index 98% rename from apps/opik-documentation/documentation/docs/evaluation/metrics/context_recall.md rename to apps/opik-documentation/documentation/fern/docs/evaluation/metrics/context_recall.mdx index 7ffc8e23d6..d4e0870157 100644 --- a/apps/opik-documentation/documentation/docs/evaluation/metrics/context_recall.md +++ b/apps/opik-documentation/documentation/fern/docs/evaluation/metrics/context_recall.mdx @@ -1,10 +1,7 @@ --- -sidebar_label: ContextRecall description: Describes the Context Recall metric --- -# ContextRecall - The context recall metric evaluates the accuracy and relevance of an LLM's response based on provided context, helping to identify potential hallucinations or misalignments with the given information. ## How to use the ContextRecall metric @@ -28,7 +25,7 @@ Asynchronous scoring is also supported with the `ascore` scoring method. ## ContextRecall Prompt -Opik uses an LLM as a Judge to compute context recall, for this we have a prompt template that is used to generate the prompt for the LLM. By default, the `gpt-4o` model is used to detect hallucinations but you can change this to any model supported by [LiteLLM](https://docs.litellm.ai/docs/providers) by setting the `model` parameter. You can learn more about customizing models in the [Customize models for LLM as a Judge metrics](/evaluation/metrics/custom_model.md) section. +Opik uses an LLM as a Judge to compute context recall, for this we have a prompt template that is used to generate the prompt for the LLM. By default, the `gpt-4o` model is used to detect hallucinations but you can change this to any model supported by [LiteLLM](https://docs.litellm.ai/docs/providers) by setting the `model` parameter. You can learn more about customizing models in the [Customize models for LLM as a Judge metrics](/evaluation/metrics/custom_model) section. The template uses a few-shot prompting technique to compute context recall. The template is as follows: diff --git a/apps/opik-documentation/documentation/docs/evaluation/metrics/custom_metric.md b/apps/opik-documentation/documentation/fern/docs/evaluation/metrics/custom_metric.mdx similarity index 93% rename from apps/opik-documentation/documentation/docs/evaluation/metrics/custom_metric.md rename to apps/opik-documentation/documentation/fern/docs/evaluation/metrics/custom_metric.mdx index 1bfb58ec10..bc4e995cdb 100644 --- a/apps/opik-documentation/documentation/docs/evaluation/metrics/custom_metric.md +++ b/apps/opik-documentation/documentation/fern/docs/evaluation/metrics/custom_metric.mdx @@ -1,5 +1,4 @@ --- -sidebar_label: Custom Metric description: Describes how to create your own metric to use with Opik's evaluation framework toc_max_heading_level: 4 pytest_codeblocks_execute_previous: true @@ -9,13 +8,13 @@ pytest_codeblocks_execute_previous: true Opik allows you to define your own metrics. This is useful if you have a specific metric that is not already implemented. -If you want to write an LLM as a Judge metric, you can use either the [G-Eval metric](/evaluation/metrics/g_eval.md) or create your own from scratch. +If you want to write an LLM as a Judge metric, you can use either the [G-Eval metric](/evaluation/metrics/g_eval) or create your own from scratch. ## Custom LLM as a Judge metric ### Creating a custom metric using G-Eval -[G-eval](/evaluation/metrics/g_eval.md) allows you to specify a set of criteria for your metric and it will use a Chain of Thought prompting technique to create some evaluation steps and return a score. +[G-eval](/evaluation/metrics/g_eval) allows you to specify a set of criteria for your metric and it will use a Chain of Thought prompting technique to create some evaluation steps and return a score. To use G-Eval, you will need to specify a task introduction and evaluation criteria: @@ -58,11 +57,12 @@ class MyCustomMetric(base_metric.BaseMetric): The `score` method should return a `ScoreResult` object. The `ascore` method is optional and can be used to compute asynchronously if needed. -:::tip -You can also return a list of `ScoreResult` objects as part of your custom metric. This is useful if you want to return multiple scores for a given input and output pair. -::: + + You can also return a list of `ScoreResult` objects as part of your custom metric. This is useful if you want to + return multiple scores for a given input and output pair. + -This metric can now be used in the `evaluate` function as explained here: [Evaluating LLMs](/evaluation/evaluate_your_llm.md). +This metric can now be used in the `evaluate` function as explained here: [Evaluating LLMs](/evaluation/evaluate_your_llm). #### Example: Creating a metric with OpenAI model @@ -120,7 +120,7 @@ class LLMJudgeMetric(base_metric.BaseMetric): You can then use this metric to score your LLM outputs: -```python pytest_codeblocks_skip=true +```python {pytest_codeblocks_skip=true} metric = LLMJudgeMetric() metric.score(output="Paris is the capital of France") @@ -184,7 +184,7 @@ class LLMJudgeMetric(base_metric.BaseMetric): You can then use this metric to score your LLM outputs: -```python pytest_codeblocks_skip=true +```python {pytest_codeblocks_skip=true} metric = LLMJudgeMetric() metric.score(output="Paris is the capital of France") diff --git a/apps/opik-documentation/documentation/docs/evaluation/metrics/custom_model.md b/apps/opik-documentation/documentation/fern/docs/evaluation/metrics/custom_model.mdx similarity index 96% rename from apps/opik-documentation/documentation/docs/evaluation/metrics/custom_model.md rename to apps/opik-documentation/documentation/fern/docs/evaluation/metrics/custom_model.mdx index 2185f5daf5..aad4f9669c 100644 --- a/apps/opik-documentation/documentation/docs/evaluation/metrics/custom_model.md +++ b/apps/opik-documentation/documentation/fern/docs/evaluation/metrics/custom_model.mdx @@ -1,12 +1,10 @@ --- -sidebar_label: Customize models for LLM as a Judge metrics description: Describes how to use a custom model for Opik's built-in LLM as a Judge metrics + toc_max_heading_level: 4 pytest_codeblocks_execute_previous: true --- -# Customize models for LLM as a Judge metrics - Opik provides a set of LLM as a Judge metrics that are designed to be model-agnostic and can be used with any LLM. In order to achieve this, we use the [LiteLLM library](https://github.com/BerriAI/litellm) to abstract the LLM calls. By default, Opik will use the `gpt-4o` model. However, you can change this by setting the `model` parameter when initializing your metric to any model supported by [LiteLLM](https://docs.litellm.ai/docs/providers): diff --git a/apps/opik-documentation/documentation/docs/evaluation/metrics/g_eval.md b/apps/opik-documentation/documentation/fern/docs/evaluation/metrics/g_eval.mdx similarity index 90% rename from apps/opik-documentation/documentation/docs/evaluation/metrics/g_eval.md rename to apps/opik-documentation/documentation/fern/docs/evaluation/metrics/g_eval.mdx index f14e737256..5cee57236a 100644 --- a/apps/opik-documentation/documentation/docs/evaluation/metrics/g_eval.md +++ b/apps/opik-documentation/documentation/fern/docs/evaluation/metrics/g_eval.mdx @@ -1,10 +1,7 @@ --- -sidebar_label: G-Eval description: Describes Opik's built-in G-Eval metric which is is a task agnostic LLM as a Judge metric --- -# G-Eval - G-Eval is a task agnostic LLM as a Judge metric that allows you to specify a set of criteria for your metric and it will use a Chain of Thought prompting technique to create some evaluation steps and return a score. You can learn more about G-Eval in the [original paper](https://arxiv.org/abs/2303.16634). To use G-Eval, you need to specify just two pieces of information: @@ -34,7 +31,7 @@ metric.score( The way the G-Eval metric works is by first using the task introduction and evaluation criteria to create a set of evaluation steps. These evaluation steps are then combined with the task introduction and evaluation criteria to return a single score. -By default, the `gpt-4o` model is used to generate the final score, but you can change this to any model supported by [LiteLLM](https://docs.litellm.ai/docs/providers) by setting the `model` parameter. You can learn more about customizing models in the [Customize models for LLM as a Judge metrics](/evaluation/metrics/custom_model.md) section. +By default, the `gpt-4o` model is used to generate the final score, but you can change this to any model supported by [LiteLLM](https://docs.litellm.ai/docs/providers) by setting the `model` parameter. You can learn more about customizing models in the [Customize models for LLM as a Judge metrics](/evaluation/metrics/custom_model) section. The evaluation steps are generated using the following prompt: @@ -75,6 +72,7 @@ The final score is generated by combining the evaluation steps returned by the p NO TEXT, ONLY SCORE ``` -:::note -In order to make the G-Eval metric more robust, we request the top 10 log_probs from the LLM and compute a weighted average of the scores as recommended by the [original paper](https://arxiv.org/abs/2303.16634). -::: + + In order to make the G-Eval metric more robust, we request the top 10 log_probs from the LLM and compute a weighted + average of the scores as recommended by the [original paper](https://arxiv.org/abs/2303.16634). + diff --git a/apps/opik-documentation/documentation/docs/evaluation/metrics/hallucination.md b/apps/opik-documentation/documentation/fern/docs/evaluation/metrics/hallucination.mdx similarity index 93% rename from apps/opik-documentation/documentation/docs/evaluation/metrics/hallucination.md rename to apps/opik-documentation/documentation/fern/docs/evaluation/metrics/hallucination.mdx index c860ea215a..6eb2d7daa9 100644 --- a/apps/opik-documentation/documentation/docs/evaluation/metrics/hallucination.md +++ b/apps/opik-documentation/documentation/fern/docs/evaluation/metrics/hallucination.mdx @@ -1,11 +1,9 @@ --- -sidebar_label: Hallucination description: Describes the Hallucination metric + pytest_codeblocks_skip: true --- -# Hallucination - The hallucination metric allows you to check if the LLM response contains any hallucinated information. In order to check for hallucination, you will need to provide the LLM input, LLM output. If the context is provided, this will also be used to check for hallucinations. ## How to use the Hallucination metric @@ -35,13 +33,14 @@ metric.score( Asynchronous scoring is also supported with the `ascore` scoring method. -:::tip -The hallucination score is either `0` or `1`. A score of `0` indicates that no hallucinations were detected, a score of `1` indicates that hallucinations were detected. -::: + + The hallucination score is either `0` or `1`. A score of `0` indicates that no hallucinations were detected, a score + of `1` indicates that hallucinations were detected. + ## Hallucination Prompt -Opik uses an LLM as a Judge to detect hallucinations, for this we have a prompt template that is used to generate the prompt for the LLM. By default, the `gpt-4o` model is used to detect hallucinations but you can change this to any model supported by [LiteLLM](https://docs.litellm.ai/docs/providers) by setting the `model` parameter. You can learn more about customizing models in the [Customize models for LLM as a Judge metrics](/evaluation/metrics/custom_model.md) section. +Opik uses an LLM as a Judge to detect hallucinations, for this we have a prompt template that is used to generate the prompt for the LLM. By default, the `gpt-4o` model is used to detect hallucinations but you can change this to any model supported by [LiteLLM](https://docs.litellm.ai/docs/providers) by setting the `model` parameter. You can learn more about customizing models in the [Customize models for LLM as a Judge metrics](/evaluation/metrics/custom_model) section. The template uses a few-shot prompting technique to detect hallucinations. The template is as follows: diff --git a/apps/opik-documentation/documentation/docs/evaluation/metrics/heuristic_metrics.md b/apps/opik-documentation/documentation/fern/docs/evaluation/metrics/heuristic_metrics.mdx similarity index 99% rename from apps/opik-documentation/documentation/docs/evaluation/metrics/heuristic_metrics.md rename to apps/opik-documentation/documentation/fern/docs/evaluation/metrics/heuristic_metrics.mdx index 00155ef6a8..27d3fc9348 100644 --- a/apps/opik-documentation/documentation/docs/evaluation/metrics/heuristic_metrics.md +++ b/apps/opik-documentation/documentation/fern/docs/evaluation/metrics/heuristic_metrics.mdx @@ -1,10 +1,7 @@ --- -sidebar_label: Heuristic Metrics description: Describes all the built-in heuristic metrics provided by Opik --- -# Heuristic Metrics - Heuristic metrics are rule-based evaluation methods that allow you to check specific aspects of language model outputs. These metrics use predefined criteria or patterns to assess the quality, consistency, or characteristics of generated text. You can use the following heuristic metrics: diff --git a/apps/opik-documentation/documentation/docs/evaluation/metrics/moderation.md b/apps/opik-documentation/documentation/fern/docs/evaluation/metrics/moderation.mdx similarity index 92% rename from apps/opik-documentation/documentation/docs/evaluation/metrics/moderation.md rename to apps/opik-documentation/documentation/fern/docs/evaluation/metrics/moderation.mdx index ba5dd4378c..5f2d1aef0a 100644 --- a/apps/opik-documentation/documentation/docs/evaluation/metrics/moderation.md +++ b/apps/opik-documentation/documentation/fern/docs/evaluation/metrics/moderation.mdx @@ -1,10 +1,7 @@ --- -sidebar_label: Moderation description: Describes the Moderation metric --- -# Moderation - The Moderation metric allows you to evaluate the appropriateness of the LLM's response to the given LLM output. It does this by asking the LLM to rate the appropriateness of the response on a scale of 1 to 10, where 1 is the least appropriate and 10 is the most appropriate. ## How to use the Moderation metric @@ -23,13 +20,14 @@ metric.score( Asynchronous scoring is also supported with the `ascore` scoring method. -:::tip -The moderation score is a float between `0` and `1`. A score of `0` indicates that the content was deemed safe, a score of `1` indicates that the content was deemed unsafe. -::: + + The moderation score is a float between `0` and `1`. A score of `0` indicates that the content was deemed safe, a + score of `1` indicates that the content was deemed unsafe. + ## Moderation Prompt -Opik uses an LLM as a Judge to moderate content, for this we have a prompt template that is used to generate the prompt for the LLM. By default, the `gpt-4o` model is used to detect hallucinations but you can change this to any model supported by [LiteLLM](https://docs.litellm.ai/docs/providers) by setting the `model` parameter. You can learn more about customizing models in the [Customize models for LLM as a Judge metrics](/evaluation/metrics/custom_model.md) section. +Opik uses an LLM as a Judge to moderate content, for this we have a prompt template that is used to generate the prompt for the LLM. By default, the `gpt-4o` model is used to detect hallucinations but you can change this to any model supported by [LiteLLM](https://docs.litellm.ai/docs/providers) by setting the `model` parameter. You can learn more about customizing models in the [Customize models for LLM as a Judge metrics](/evaluation/metrics/custom_model) section. The template uses a few-shot prompting technique to detect moderation issues. The template is as follows: diff --git a/apps/opik-documentation/documentation/docs/evaluation/metrics/overview.md b/apps/opik-documentation/documentation/fern/docs/evaluation/metrics/overview.mdx similarity index 74% rename from apps/opik-documentation/documentation/docs/evaluation/metrics/overview.md rename to apps/opik-documentation/documentation/fern/docs/evaluation/metrics/overview.mdx index e0d0edfe7f..81ca8ddf76 100644 --- a/apps/opik-documentation/documentation/docs/evaluation/metrics/overview.md +++ b/apps/opik-documentation/documentation/fern/docs/evaluation/metrics/overview.mdx @@ -1,5 +1,4 @@ --- -sidebar_label: Overview description: Describes all the built-in evaluation metrics provided by Opik --- @@ -14,27 +13,28 @@ Heuristic metrics are deterministic and are often statistical in nature. LLM as Opik provides the following built-in evaluation metrics: -| Metric | Type | Description | Documentation | -| ---------------- | -------------- | ------------------------------------------------------------------------------------------------- | ------------------------------------------------------------------------ | -| Equals | Heuristic | Checks if the output exactly matches an expected string | [Equals](/evaluation/metrics/heuristic_metrics.md#equals) | -| Contains | Heuristic | Check if the output contains a specific substring, can be both case sensitive or case insensitive | [Contains](/evaluation/metrics/heuristic_metrics.md#contains) | -| RegexMatch | Heuristic | Checks if the output matches a specified regular expression pattern | [RegexMatch](/evaluation/metrics/heuristic_metrics.md#regexmatch) | -| IsJson | Heuristic | Checks if the output is a valid JSON object | [IsJson](/evaluation/metrics/heuristic_metrics.md#isjson) | -| Levenshtein | Heuristic | Calculates the Levenshtein distance between the output and an expected string | [Levenshtein](/evaluation/metrics/heuristic_metrics.md#levenshteinratio) | -| Hallucination | LLM as a Judge | Check if the output contains any hallucinations | [Hallucination](/evaluation/metrics/hallucination.md) | -| G-Eval | LLM as a Judge | Task agnostic LLM as a Judge metric | [G-Eval](/evaluation/metrics/g_eval.md) | -| Moderation | LLM as a Judge | Check if the output contains any harmful content | [Moderation](/evaluation/metrics/moderation.md) | -| AnswerRelevance | LLM as a Judge | Check if the output is relevant to the question | [AnswerRelevance](/evaluation/metrics/answer_relevance.md) | -| ContextRecall | LLM as a Judge | Check if the output contains any hallucinations | [ContextRecall](/evaluation/metrics/context_recall.md) | -| ContextPrecision | LLM as a Judge | Check if the output contains any hallucinations | [ContextPrecision](/evaluation/metrics/context_precision.md) | - -You can also create your own custom metric, learn more about it in the [Custom Metric](/evaluation/metrics/custom_metric.md) section. +| Metric | Type | Description | Documentation | +| ---------------- | -------------- | ------------------------------------------------------------------------------------------------- | --------------------------------------------------------------------- | +| Equals | Heuristic | Checks if the output exactly matches an expected string | [Equals](/evaluation/metrics/heuristic_metrics#equals) | +| Contains | Heuristic | Check if the output contains a specific substring, can be both case sensitive or case insensitive | [Contains](/evaluation/metrics/heuristic_metrics#contains) | +| RegexMatch | Heuristic | Checks if the output matches a specified regular expression pattern | [RegexMatch](/evaluation/metrics/heuristic_metrics#regexmatch) | +| IsJson | Heuristic | Checks if the output is a valid JSON object | [IsJson](/evaluation/metrics/heuristic_metrics#isjson) | +| Levenshtein | Heuristic | Calculates the Levenshtein distance between the output and an expected string | [Levenshtein](/evaluation/metrics/heuristic_metrics#levenshteinratio) | +| Hallucination | LLM as a Judge | Check if the output contains any hallucinations | [Hallucination](/evaluation/metrics/hallucination) | +| G-Eval | LLM as a Judge | Task agnostic LLM as a Judge metric | [G-Eval](/evaluation/metrics/g_eval) | +| Moderation | LLM as a Judge | Check if the output contains any harmful content | [Moderation](/evaluation/metrics/moderation) | +| AnswerRelevance | LLM as a Judge | Check if the output is relevant to the question | [AnswerRelevance](/evaluation/metrics/answer_relevance) | +| Usefulness | LLM as a Judge | Check if the output is useful to the question | [Usefulness](/evaluation/metrics/usefulness) | +| ContextRecall | LLM as a Judge | Check if the output contains any hallucinations | [ContextRecall](/evaluation/metrics/context_recall) | +| ContextPrecision | LLM as a Judge | Check if the output contains any hallucinations | [ContextPrecision](/evaluation/metrics/context_precision) | + +You can also create your own custom metric, learn more about it in the [Custom Metric](/evaluation/metrics/custom_metric) section. ## Customizing LLM as a Judge metrics By default, Opik uses GPT-4o from OpenAI as the LLM to evaluate the output of other LLMs. However, you can easily switch to another LLM provider by specifying a different `model` in the `model_name` parameter of each LLM as a Judge metric. -```python pytest_codeblocks_skip=true +```python {pytest_codeblocks_skip=true} from opik.evaluation.metrics import Hallucination metric = Hallucination(model="bedrock/anthropic.claude-3-sonnet-20240229-v1:0") diff --git a/apps/opik-documentation/documentation/docs/evaluation/metrics/usefulness.md b/apps/opik-documentation/documentation/fern/docs/evaluation/metrics/usefulness.mdx similarity index 98% rename from apps/opik-documentation/documentation/docs/evaluation/metrics/usefulness.md rename to apps/opik-documentation/documentation/fern/docs/evaluation/metrics/usefulness.mdx index 7516b8b4d8..433d9d38bc 100644 --- a/apps/opik-documentation/documentation/docs/evaluation/metrics/usefulness.md +++ b/apps/opik-documentation/documentation/fern/docs/evaluation/metrics/usefulness.mdx @@ -1,5 +1,4 @@ --- -sidebar_label: Usefulness description: Describes the Usefulness metric pytest_codeblocks_skip: true --- @@ -31,6 +30,7 @@ Asynchronous scoring is also supported with the `ascore` scoring method. ## Understanding the scores The usefulness score ranges from 0.0 to 1.0: + - Scores closer to 1.0 indicate that the response is highly useful, directly addressing the input query with relevant and accurate information - Scores closer to 0.0 indicate that the response is less useful, possibly being off-topic, incomplete, or not addressing the input query effectively @@ -38,7 +38,7 @@ Each score comes with a detailed explanation (`result.reason`) that helps unders ## Usefulness Prompt -Opik uses an LLM as a Judge to evaluate usefulness, for this we have a prompt template that is used to generate the prompt for the LLM. By default, the `gpt-4o` model is used to evaluate responses but you can change this to any model supported by [LiteLLM](https://docs.litellm.ai/docs/providers) by setting the `model` parameter. You can learn more about customizing models in the [Customize models for LLM as a Judge metrics](/evaluation/metrics/custom_model.md) section. +Opik uses an LLM as a Judge to evaluate usefulness, for this we have a prompt template that is used to generate the prompt for the LLM. By default, the `gpt-4o` model is used to evaluate responses but you can change this to any model supported by [LiteLLM](https://docs.litellm.ai/docs/providers) by setting the `model` parameter. You can learn more about customizing models in the [Customize models for LLM as a Judge metrics](/evaluation/metrics/custom_model) section. The template is as follows: diff --git a/apps/opik-documentation/documentation/docs/evaluation/overview.mdx b/apps/opik-documentation/documentation/fern/docs/evaluation/overview.mdx similarity index 80% rename from apps/opik-documentation/documentation/docs/evaluation/overview.mdx rename to apps/opik-documentation/documentation/fern/docs/evaluation/overview.mdx index 41dded774a..1b230951f0 100644 --- a/apps/opik-documentation/documentation/docs/evaluation/overview.mdx +++ b/apps/opik-documentation/documentation/fern/docs/evaluation/overview.mdx @@ -1,13 +1,9 @@ --- -sidebar_label: Overview -description: A high-level overview on how to use Opik's evaluation features including some code snippets +subtitle: >- + A high-level overview on how to use Opik's evaluation features including some + code snippets --- -import Tabs from "@theme/Tabs"; -import TabItem from "@theme/TabItem"; - -# Overview - Evaluation in Opik helps you assess and measure the quality of your LLM outputs across different dimensions. It provides a framework to systematically test your prompts and models against datasets, using various metrics to measure performance. @@ -17,12 +13,13 @@ to measure performance. Opik also provides a set of pre-built metrics for common evaluation tasks. These metrics are designed to help you quickly and effectively gauge the performance of your LLM outputs and include metrics such as Hallucination, Answer Relevance, Context Precision/Recall and more. You can learn more about the available metrics in the -[Metrics Overview](/evaluation/metrics/overview.md) section. +[Metrics Overview](/evaluation/metrics/overview) section. -:::tip -If you are interested in evaluating your LLM application in production, please refer to the [Online evaluation guide](/production/rules.md). -Online evaluation rules allow you to define LLM as a Judge metrics that will automatically score all, or a subset, of your production traces. -::: + + If you are interested in evaluating your LLM application in production, please refer to the [Online evaluation + guide](/production/rules). Online evaluation rules allow you to define LLM as a Judge metrics that will automatically + score all, or a subset, of your production traces. + ## Running an Evaluation @@ -38,7 +35,7 @@ To simplify the evaluation process, Opik provides two main evaluation methods: ` templates and a more general `evaluate` method for more complex evaluation scenarios. - + To evaluate a specific prompt against a dataset: @@ -64,8 +61,8 @@ result = evaluate_prompt( ) ``` - - + + For more complex evaluation scenarios where you need custom processing: @@ -110,11 +107,11 @@ result = evaluate( ) ``` - - + + You can also use the Opik Playground to quickly evaluate different prompts and LLM models. - To use the Playground, you will need to navigate to the [Playground](/prompt_engineering/playground.md) page and: + To use the Playground, you will need to navigate to the [Playground](/prompt_engineering/playground) page and: 1. Configure the LLM provider you want to use 2. Enter the prompts you want to evaluate - You should include variables in the prompts using the `{{variable}}` syntax @@ -125,14 +122,16 @@ result = evaluate( ![Playground](/img/evaluation/playground_evaluation.gif) - + ## Analyzing Evaluation Results Once the evaluation is complete, Opik allows you to manually review the results and compare them with previous iterations. -![Experiment page](/img/evaluation/experiment_items.png) + + + In the experiment pages, you will be able to: @@ -145,8 +144,8 @@ In the experiment pages, you will be able to: You can learn more about Opik's evaluation features in: -1. [Evaluation concepts](/evaluation/concepts.md) -1. [Evaluate prompts](/evaluation/evaluate_prompt.md) -1. [Evaluate complex LLM applications](/evaluation/evaluate_your_llm.md) -1. [Evaluation metrics](/evaluation/metrics/overview.md) -1. [Manage datasets](/evaluation/manage_datasets.md) +1. [Evaluation concepts](/evaluation/concepts) +1. [Evaluate prompts](/evaluation/evaluate_prompt) +1. [Evaluate complex LLM applications](/evaluation/evaluate_your_llm) +1. [Evaluation metrics](/evaluation/metrics/overview) +1. [Manage datasets](/evaluation/manage_datasets) diff --git a/apps/opik-documentation/documentation/docs/evaluation/update_existing_experiment.md b/apps/opik-documentation/documentation/fern/docs/evaluation/update_existing_experiment.mdx similarity index 82% rename from apps/opik-documentation/documentation/docs/evaluation/update_existing_experiment.md rename to apps/opik-documentation/documentation/fern/docs/evaluation/update_existing_experiment.mdx index 9e3ee22204..b2939bf812 100644 --- a/apps/opik-documentation/documentation/docs/evaluation/update_existing_experiment.md +++ b/apps/opik-documentation/documentation/fern/docs/evaluation/update_existing_experiment.mdx @@ -1,15 +1,12 @@ --- -sidebar_label: Update an Existing Experiment -description: Guides you through the process of updating an existing experiment +subtitle: Guides you through the process of updating an existing experiment --- -# Update an Existing Experiment - Sometimes you may want to update an existing experiment with new scores, or update existing scores for an experiment. You can do this using the [`evaluate_experiment` function](https://www.comet.com/docs/opik/python-sdk-reference/evaluation/evaluate_existing.html). This function will re-run the scoring metrics on the existing experiment items and update the scores: -```python pytest_codeblocks_skip=true +```python {pytest_codeblocks_skip=true} from opik.evaluation import evaluate_experiment from opik.evaluation.metrics import Hallucination @@ -19,9 +16,10 @@ hallucination_metric = Hallucination() evaluate_experiment(experiment_name="my-experiment", scoring_metrics=[hallucination_metric]) ``` -:::tip -The `evaluate_experiment` function can be used to update existing scores for an experiment. If you use a scoring metric with the same name as an existing score, the scores will be updated with the new values. -::: + + The `evaluate_experiment` function can be used to update existing scores for an experiment. If you use a scoring + metric with the same name as an existing score, the scores will be updated with the new values. + ## Example @@ -82,15 +80,13 @@ experiment_name = evaluation.experiment_name print(f"Experiment name: {experiment_name}") ``` -:::tip -Learn more about the `evaluate` function in our [LLM evaluation guide](/evaluation/evaluate_your_llm). -::: +Learn more about the `evaluate` function in our [LLM evaluation guide](/evaluation/evaluate_your_llm). ### Update the experiment Once the first experiment is created, you realise that you also want to compute a moderation score for each example. You could re-run the experiment with new scoring metrics but this means re-running the output. Instead, you can simply update the experiment with the new scoring metrics: -```python pytest_codeblocks_skip=true +```python {pytest_codeblocks_skip=true} from opik.evaluation import evaluate_experiment from opik.evaluation.metrics import Moderation diff --git a/apps/opik-documentation/documentation/fern/docs/faq.mdx b/apps/opik-documentation/documentation/fern/docs/faq.mdx new file mode 100644 index 0000000000..41fab85834 --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs/faq.mdx @@ -0,0 +1,76 @@ +These FAQs are a collection of the most common questions that we've received from our users. If you have any questions or need additional assistance, +please open an [issue on GitHub](https://github.com/comet-ml/opik/issues). + +## General + +### What is Opik's relationship with Comet? + +Opik is developed by Comet and is available in multiple deployment options: +- As an open-source standalone product that can be used locally or self-hosted on your own infrastructure +- As an integrated part of the Comet MLOps Platform (both in Comet-hosted and self-hosted deployments) + +This means you can use Opik independently of the Comet platform, or as part of your existing Comet MLOps setup. + +### What SDKs does Opik provide? + +Opik currently provides official SDKs for: +- Python: Our most feature-complete SDK, supporting all Opik features +- TypeScript: Rich tracing capabilities + +These SDKs are actively maintained and regularly updated. For other languages, you can use our REST API directly - see our [API documentation](/docs/opik/reference/rest-api/overview) for details. + +### Can I use Opik to monitor my LLM application in production? + +Yes, Opik has been designed from the ground up to be used to monitor production applications. If you are self-hosting the +Opik platform, we recommend using the [Kuberneters deployment](/self-host/overview) option to ensure that Opik can scale as needed. + +## Opik Cloud + +### Are there are rate limits on Opik Cloud? + +Yes, in order to ensure all users have a good experience we have implemented rate limits. Each user is limited to `10,000` +events per minute, an event is a trace, span, feedback score, dataset item, experiment item, etc. If you need to increase +this limit please reach out to us on [Slack](https://chat.comet.com). + +## Integrations + +### What integrations does Opik support? + +Opik supports a wide range of popular LLM frameworks and providers. You can find detailed integration guides in our [cookbook section](/cookbook/overview#integration-examples) for: + +- LLM Providers: OpenAI, Anthropic, AWS Bedrock, Google Gemini, Groq, IBM watsonx, Ollama +- Frameworks: LangChain, LlamaIndex, Haystack, DSPy, CrewAI, LangGraph +- Tools: LiteLLM, Guardrails, Ragas, aisuite +- And more! + +### What if Opik doesn't support my preferred framework or tool? + +If you don't see your preferred framework or tool listed in our integrations, we encourage you to: + +1. Open an [issue on GitHub](https://github.com/comet-ml/opik/issues) to request the integration +2. In the meantime, you can manually log your LLM interactions using our SDK's core logging functions - see our [tracing documentation](/docs/opik/tracing/log_traces) for examples + +We actively maintain and expand our integration support based on community feedback. + +## Troubleshooting + +### Why am I getting 403 errors? + +If you're encountering 403 (Forbidden) errors, this typically indicates an authentication or authorization issue. If you haven't configured your credentials yet, the easiest way to get started is to run: +```bash +opik configure +``` +This interactive command will guide you through setting up the required configuration. + +Otherwise, please double-check your existing configuration: + +For Opik Cloud by Comet: +- `api_key` (required): Verify your API key is correct and active +- `workspace` (required): Confirm you have access to the specified workspace +- `project_name` (optional): If specified, ensure the project name is valid +- `url_override`: Should be set to `https://www.comet.com/opik/api` (this is the default) + +For Self-hosted Opik: +- `url_override` (required): Verify your base URL points to your Opik instance (e.g., `http://your-instance:5173/api`) + +You can find your current configuration in the Opik configuration file (`~/.opik.config`) or by checking your environment variables (`OPIK_API_KEY`, `OPIK_WORKSPACE`, `OPIK_URL_OVERRIDE`, `OPIK_PROJECT_NAME`). For more details on configuration, see our [SDK Configuration guide](/docs/opik/tracing/sdk_configuration). diff --git a/apps/opik-documentation/documentation/docs/home.md b/apps/opik-documentation/documentation/fern/docs/home.mdx similarity index 52% rename from apps/opik-documentation/documentation/docs/home.md rename to apps/opik-documentation/documentation/fern/docs/home.mdx index ed7c6800a7..168e32fefe 100644 --- a/apps/opik-documentation/documentation/docs/home.md +++ b/apps/opik-documentation/documentation/fern/docs/home.mdx @@ -1,18 +1,13 @@ ---- -slug: / -sidebar_label: Home -description: Opik documentation home page ---- - -# Opik by Comet - The Opik platform allows you to log, view and evaluate your LLM traces during both development and production. Using the platform and our LLM as a Judge evaluators, you can identify and fix issues in your LLM application. -![LLM Evaluation Platform](/img/home/traces_page_with_sidebar.png) + + + -:::tip -Opik is Open Source! You can find the full source code on [GitHub](https://github.com/comet-ml/opik) and the complete self-hosting guide can be found [here](/self-host/local_deployment.md). -::: + + Opik is Open Source! You can find the full source code on [GitHub](https://github.com/comet-ml/opik) and the complete + self-hosting guide can be found [here](/self-host/local_deployment). + ## Overview @@ -24,21 +19,21 @@ During development, you can use the platform to log, view and debug your LLM tra 1. Log traces using: - a. One of our [integrations](/tracing/integrations/overview.md). + a. One of our [integrations](/tracing/integrations/overview). - b. The `@track` decorator for Python, learn more in the [Logging Traces](/tracing/log_traces.mdx) guide. + b. The `@track` decorator for Python, learn more in the [Logging Traces](/tracing/log_traces) guide. - c. Using the Typescript Opik SDK, learn more in the [Logging Traces](/tracing/log_traces.mdx#logging-with-the-js--ts-sdk) guide. + c. Using the Typescript Opik SDK, learn more in the [Logging Traces](/tracing/log_traces#logging-with-the-js--ts-sdk) guide. -2. [Annotate and label traces](/tracing/annotate_traces.md) through the SDK or the UI. +2. [Annotate and label traces](/tracing/annotate_traces) through the SDK or the UI. ### Evaluation and Testing Evaluating the output of your LLM calls is critical to ensure that your application is working as expected and can be challenging. Using the Opik platformm, you can: -1. Use one of our [LLM as a Judge evaluators](/evaluation/metrics/overview.md) or [Heuristic evaluators](/evaluation/metrics/heuristic_metrics.md) to score your traces and LLM calls -2. [Store evaluation datasets](/evaluation/manage_datasets.md) in the platform and [run evaluations](/evaluation/evaluate_your_llm.md) -3. Use our [pytest integration](/testing/pytest_integration.md) to track unit test results and compare results between runs +1. Use one of our [LLM as a Judge evaluators](/evaluation/metrics/overview) or [Heuristic evaluators](/evaluation/metrics/heuristic_metrics) to score your traces and LLM calls +2. [Store evaluation datasets](/evaluation/manage_datasets) in the platform and [run evaluations](/evaluation/evaluate_your_llm) +3. Use our [pytest integration](/testing/pytest_integration) to track unit test results and compare results between runs ### Production Monitoring @@ -46,11 +41,11 @@ Opik has been designed from the ground up to support high volumes of traces maki Our goal is to make it easy for you to monitor your production LLM applications and easily identify any issues with your production LLM application, for this we have included: -1. [Online evaluation metrics](/production/rules.md) that allow you to score all your production traces and easily identify any issues with your production LLM application. -2. [Production monitoring dashboards](/production/production_monitoring.md) that allow you to review your feedback scores, trace count and tokens over time at both a daily and hourly granularity. +1. [Online evaluation metrics](/production/rules) that allow you to score all your production traces and easily identify any issues with your production LLM application. +2. [Production monitoring dashboards](/production/production_monitoring) that allow you to review your feedback scores, trace count and tokens over time at both a daily and hourly granularity. ## Getting Started [Comet](https://www.comet.com/site) provides a managed Cloud offering for Opik, simply [create an account](https://www.comet.com/signup?from=llm) to get started. -You can also run Opik locally using our [local installer](/self-host/local_deployment.md). If you are looking for a more production ready deployment, you can also use our [Kubernetes deployment option](/self-host/kubernetes.md). +You can also run Opik locally using our [local installer](/self-host/local_deployment). If you are looking for a more production ready deployment, you can also use our [Kubernetes deployment option](/self-host/kubernetes). diff --git a/apps/opik-documentation/documentation/docs/production/gateway.mdx b/apps/opik-documentation/documentation/fern/docs/production/gateway.mdx similarity index 84% rename from apps/opik-documentation/documentation/docs/production/gateway.mdx rename to apps/opik-documentation/documentation/fern/docs/production/gateway.mdx index e2e4a46516..5a4582d068 100644 --- a/apps/opik-documentation/documentation/docs/production/gateway.mdx +++ b/apps/opik-documentation/documentation/fern/docs/production/gateway.mdx @@ -1,13 +1,9 @@ --- -sidebar_label: LLM Gateway -description: Describes how to use the Opik LLM gateway and how to integrate with the Kong AI Gateway +subtitle: >- + Describes how to use the Opik LLM gateway and how to integrate with the Kong + AI Gateway --- -import Tabs from "@theme/Tabs"; -import TabItem from "@theme/TabItem"; - -# LLM Gateway - An LLM gateway is a proxy server that forwards requests to an LLM API and returns the response. This is useful for when you want to centralize the access to LLM providers or when you want to be able to query multiple LLM providers from a single endpoint using a consistent request and response format. The Opik platform includes a light-weight LLM gateway that can be used for **development and testing purposes**. If you are looking for an LLM gateway that is production ready, we recommend looking at the [Kong AI Gateway](https://docs.konghq.com/gateway/latest/ai-gateway/). @@ -19,7 +15,7 @@ The Opik LLM gateway is a light-weight proxy server that can be used to query di In order to use the Opik LLM gateway, you will first need to configure your LLM provider credentials in the Opik UI. Once this is done, you can use the Opik gateway to query your LLM provider: - + ```bash curl -L 'https://www.comet.com/opik/api/v1/private/chat/completions' \ -H 'Content-Type: application/json' \ @@ -39,8 +35,8 @@ In order to use the Opik LLM gateway, you will first need to configure your LLM "max_tokens": 10000 }' ``` - - + + ```bash curl -L 'http://localhost:5173/api/v1/private/chat/completions' \ -H 'Content-Type: application/json' \ @@ -58,12 +54,13 @@ In order to use the Opik LLM gateway, you will first need to configure your LLM "max_tokens": 10000 }' ``` - + -:::warning -The Opik LLM gateway is currently in beta and is subject to change. We recommend using the Kong AI gateway for production applications. -::: + + The Opik LLM gateway is currently in beta and is subject to change. We recommend using the Kong AI gateway for + production applications. + ## Kong AI Gateway @@ -78,7 +75,7 @@ The plugin is open source and available at [comet-ml/opik-kong-plugin](https://g Once the plugin is installed, you can enable it by running: -```bash pytest_codeblocks_skip=true +```bash {pytest_codeblocks_skip=true} curl -is -X POST http://localhost:8001/services/{serviceName|Id}/plugins \ --header "accept: application/json" \ --header "Content-Type: application/json" \ @@ -96,4 +93,6 @@ You can find more information about the Opik Kong plugin the [`opik-kong-plugin` Once configured, you will be able to view all your LLM calls in the Opik dashboard: -![Opik Kong AI Gateway](/img/production/opik-kong-gateway.png) + + + diff --git a/apps/opik-documentation/documentation/docs/production/production_monitoring.md b/apps/opik-documentation/documentation/fern/docs/production/production_monitoring.mdx similarity index 83% rename from apps/opik-documentation/documentation/docs/production/production_monitoring.md rename to apps/opik-documentation/documentation/fern/docs/production/production_monitoring.mdx index 0276d32609..d24d6c145c 100644 --- a/apps/opik-documentation/documentation/docs/production/production_monitoring.md +++ b/apps/opik-documentation/documentation/fern/docs/production/production_monitoring.mdx @@ -1,33 +1,31 @@ --- -sidebar_label: Production Monitoring -description: Describes how to monitor your LLM applications in production using Opik +subtitle: Describes how to monitor your LLM applications in production using Opik --- -# Production Monitoring - Opik has been designed from the ground up to support high volumes of traces making it the ideal tool for monitoring your production LLM applications. You can use the Opik dashboard to review your feedback scores, trace count and tokens over time at both a daily and hourly granularity. -![Opik monitoring dashboard](/img/tracing/opik_monitoring_dashboard.png) + + + In addition to viewing scores over time, you can also view the average feedback scores for all the traces in your project from the traces table. ## Logging feedback scores -To monitor the performance of your LLM application, you can log feedback scores using the [Python SDK and through the UI](/tracing/annotate_traces.md). +To monitor the performance of your LLM application, you can log feedback scores using the [Python SDK and through the UI](/tracing/annotate_traces). ### Defining online evaluation metrics -You can define LLM as a Judge metrics in the Opik platform that will automatically score all, or a subset, of your production traces. You can find more information about how to define LLM as a Judge metrics in the [Online evaluation](/production/rules.md) section. - - +You can define LLM as a Judge metrics in the Opik platform that will automatically score all, or a subset, of your production traces. You can find more information about how to define LLM as a Judge metrics in the [Online evaluation](/production/rules) section. Once a rule is defined, Opik will score all the traces in the project and allow you to track these feedback scores over time. -:::tip -In addition to allowing you to define LLM as a Judge metrics, Opik will soon allow you to define Python metrics to give you even more control over the feedback scores. -::: + + In addition to allowing you to define LLM as a Judge metrics, Opik will soon allow you to define Python metrics to + give you even more control over the feedback scores. + ### Manually logging feedback scores alongside traces @@ -67,11 +65,11 @@ traces = opik_client.search_traces( ) ``` -:::tip + -The `search_traces` method allows you to fetch traces based on any of trace attributes, you can learn more about the different search parameters in the [search traces documentation](/tracing/export_data.md). +The `search_traces` method allows you to fetch traces based on any of trace attributes, you can learn more about the different search parameters in the [search traces documentation](/tracing/export_data). -::: + #### Updating feedback scores diff --git a/apps/opik-documentation/documentation/docs/production/rules.md b/apps/opik-documentation/documentation/fern/docs/production/rules.mdx similarity index 76% rename from apps/opik-documentation/documentation/docs/production/rules.md rename to apps/opik-documentation/documentation/fern/docs/production/rules.mdx index 9c702c1c07..c1d824a826 100644 --- a/apps/opik-documentation/documentation/docs/production/rules.md +++ b/apps/opik-documentation/documentation/fern/docs/production/rules.mdx @@ -1,13 +1,11 @@ --- -sidebar_label: Online evaluation -description: Describes how to define scoring rules for production traces +subtitle: Describes how to define scoring rules for production traces --- -# Online evaluation - -:::tip -Online evaluation metrics allow you to score all your production traces and easily identify any issues with your production LLM application. -::: + + Online evaluation metrics allow you to score all your production traces and easily identify any issues with your + production LLM application. + When working with LLMs in production, the sheer number of traces means that it isn't possible to manually review each trace. Opik allows you to define LLM as a Judge metrics that will automatically score the LLM calls logged to the platform. @@ -19,11 +17,13 @@ specific metric. ## Defining scoring rules -Scoring rules can be defined through both the UI and the [REST API](/reference/rest_api/create-automation-rule-evaluator.api.mdx). +Scoring rules can be defined through both the UI and the [REST API](/reference/rest-api/overview). To create a new scoring metric in the UI, first navigate to the project you would like to monitor. Once you have navigated to the `rules` tab, you will be able to create a new rule. -![Online evaluation rule modal](/img/production/online_evaluation_rule_modal.png) + + + When creating a new rule, you will be presented with the following options: @@ -42,18 +42,23 @@ Opik comes pre-configured with 3 different LLM as a Judge metrics: 2. Moderation: This metric checks if the LLM output contains any offensive content. 3. Answer Relevance: This metric checks if the LLM output is relevant to the given context. -:::tip -If you would like us to add more LLM as a Judge metrics to the platform, do raise an issue on [GitHub](https://github.com/comet-ml/opik/issues) and we will do our best to add them ! -::: + + If you would like us to add more LLM as a Judge metrics to the platform, do raise an issue on + [GitHub](https://github.com/comet-ml/opik/issues) and we will do our best to add them ! + ### Writing your own LLM as a Judge metric Opik's built-in LLM as a Judge metrics are very easy to use and are great for getting started. However, as you start working on more complex tasks, you may need to write your own LLM as a Judge metrics. -We typically recommend that you experiment with LLM as a Judge metrics during development using [Opik's evaluation framework](/evaluation/overview.mdx). Once you have a metric that works well for your use case, you can then use it in production. +We typically recommend that you experiment with LLM as a Judge metrics during development using [Opik's evaluation framework](/evaluation/overview). Once you have a metric that works well for your use case, you can then use it in production. -![Custom LLM as a Judge](/img/production/online_evaluation_custom_judge.png) -When writing your own LLM as a Judge metric you will need to specify the prompt variables using the mustache syntax, ie. `{{variable_name}}`. You can then map these variables to your trace data using the `variable_mapping` parameter. When the rule is executed, Opik will replace the variables with the values from the trace data. + + + +When writing your own LLM as a Judge metric you will need to specify the prompt variables using the mustache syntax, ie. +`{{ variable_name }}`. You can then map these variables to your trace data using the `variable_mapping` parameter. When the +rule is executed, Opik will replace the variables with the values from the trace data. You can control the format of the output using the `Scoring definition` parameter. This is were you can define the scores you want the LLM as a Judge metric to return. Under the hood, we will use this definition in conjunction with the [structured outputs](https://platform.openai.com/docs/guides/structured-outputs) functionality to ensure that the the LLM as a Judge metric always returns trace scores. diff --git a/apps/opik-documentation/documentation/docs/prompt_engineering/managing_prompts_in_code.mdx b/apps/opik-documentation/documentation/fern/docs/prompt_engineering/managing_prompts_in_code.mdx similarity index 73% rename from apps/opik-documentation/documentation/docs/prompt_engineering/managing_prompts_in_code.mdx rename to apps/opik-documentation/documentation/fern/docs/prompt_engineering/managing_prompts_in_code.mdx index 72ac7fc4ee..d9cb01dba7 100644 --- a/apps/opik-documentation/documentation/docs/prompt_engineering/managing_prompts_in_code.mdx +++ b/apps/opik-documentation/documentation/fern/docs/prompt_engineering/managing_prompts_in_code.mdx @@ -1,18 +1,8 @@ ---- -sidebar_label: Versioning prompts stored in code -description: Describes how to version prompts stored in code ---- - -import Tabs from "@theme/Tabs"; -import TabItem from "@theme/TabItem"; - -# Managing prompts stored in code - If you already have prompts stored in code, you can use the the [`Prompt`](https://www.comet.com/docs/opik/python-sdk-reference/library/Prompt.html) object in the SDK to sync these prompts with the library. This allows you to store the prompt text in your code while also having it versioned and stored in the library: - + ```python import opik @@ -33,10 +23,10 @@ This allows you to store the prompt text in your code while also having it versi print(prompt.format(text="Hello, world!")) ``` - - + + - ```python pytest_codeblocks_skip=true + ```python {pytest_codeblocks_skip=true} import opik # Read the prompt from a file @@ -52,16 +42,19 @@ This allows you to store the prompt text in your code while also having it versi print(prompt.format(text="Hello, world!")) ``` - + The prompt will now be stored in the library and versioned: -![Prompt library versions](/img/prompt_engineering/prompt_library_versions.png) + + + -:::tip + The [`Prompt`](https://www.comet.com/docs/opik/python-sdk-reference/library/Prompt.html) object will create a new prompt in the library if this prompt doesn't already exist, otherwise it will return the existing prompt. This means you can safely run the above code multiple times without creating duplicate prompts. -::: + + diff --git a/apps/opik-documentation/documentation/fern/docs/prompt_engineering/playground.mdx b/apps/opik-documentation/documentation/fern/docs/prompt_engineering/playground.mdx new file mode 100644 index 0000000000..bb53c6385d --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs/prompt_engineering/playground.mdx @@ -0,0 +1,97 @@ + + The Opik prompt playground is current in public preview, if you have any feedback or suggestions, please [let us + know](https://github.com/comet-ml/opik/pulls). + + +When working with LLMs, there are time when you want to quickly try out different prompts and see how they perform. Opik's +prompt playground is a great way to do just that. + +## Using the prompt playground + +The prompt playground is a simple interface that allows you to enter prompts and see the output of the LLM. It allows you +to enter system, user and assistant messages and see the output of the LLM in real time. + +You can also easily evaluate how different models impact the prompt by duplicating a prompt and changing either the +model or the model parameters. + + + + + +_All of the conversations from the playground are logged to the `playground` project so that you can easily refer back to them later._ + +## Configuring the prompt playground + +The playground supports the following LLM providers: + +- OpenAI +- Anthropic +- Ollama +- LM Studio (coming soon) + + + If you would like us to support additional LLM providers, please let us know by opening an issue on + [GitHub](https://github.com/comet-ml/opik/issues). + + +### Configuring OpenAI and Anthropic + +To use OpenAI or Anthropic models, you will need to add your API key to Opik. You can do this by clicking on the `Configuration` tab in the sidebar +and navigating to the `AI providers` tab. From there, you can select the provider you want to use and enter your API key. + +### Configuring Ollama + +If you are using Ollama, you will need to ensure that Ollama's security configuration is set up correctly to avoid CORS issues. If you are running Ollama +in production, we recommend reviewing the [Ollama documentation](https://github.com/ollama/ollama/blob/main/docs/faq.md#faq) for advice on best practices. + +If you are simply looking at using Ollama in the Oplik playground, we have released a utility to help you access Ollama from your browser. The Python +SDK includes a simple reverse proxy that you can run on your local machine to proxy requests to Ollama: + + + +```bash +# Install the latest version of the SDK +pip install opik -U + +```` + + + +```bash +# Run the reverse proxy +opik proxy --ollama +```` + +Once the server is running, you should see the output: + + + + + + + +You can then configure the AI providers using the `URL` and `models` parameters returned by the proxy server in the console: + + + + + +_Don't forget to update the model list with the models supported by your proxy server!_ + + + You will need to keep the proxy server running for the playground to work. If it is not running, you will see the + error: `Unexpected error`. + + + + + +## Running experiments in the playground + +You can evaluate prompts in the playground by using variables in the prompts using the `{{variable}}` syntax. You can then connect a dataset and run the prompts on each dataset item. This allows both technical and non-technical users to evaluate prompts quickly and easily. + +![playground evaluation](/img/evaluation/playground_evaluation.gif) + +When using datasets in the playground, you need to ensure the prompt contains variables in the mustache syntax (`{{variable}}`) that align with the columns in the dataset. For example if the dataset contains a column named `user_question` you need to ensure the prompt contains `{{user_question}}`. + +Once you are ready to run the experiment, simply select a dataset next to the run button and click on the `Run` button. You will then be able to see the LLM outputs for each sample in the dataset. diff --git a/apps/opik-documentation/documentation/docs/prompt_engineering/prompt_management.mdx b/apps/opik-documentation/documentation/fern/docs/prompt_engineering/prompt_management.mdx similarity index 66% rename from apps/opik-documentation/documentation/docs/prompt_engineering/prompt_management.mdx rename to apps/opik-documentation/documentation/fern/docs/prompt_engineering/prompt_management.mdx index ee06169a35..b055038811 100644 --- a/apps/opik-documentation/documentation/docs/prompt_engineering/prompt_management.mdx +++ b/apps/opik-documentation/documentation/fern/docs/prompt_engineering/prompt_management.mdx @@ -1,37 +1,31 @@ ---- -sidebar_label: Overview -description: Describes how to manage prompts in Opik -pytest_codeblocks_skip: true ---- - -import Tabs from "@theme/Tabs"; -import TabItem from "@theme/TabItem"; - -# Overview - Opik provides a prompt library that you can use to manage your prompts. Storing prompts in a library allows you to version them, reuse them across projects, and manage them in a central location. Using a prompt library does not mean you can't store your prompt in code, we have designed the prompt library to be work seamlessly with your existing prompt files while providing the benefits of a central prompt library. ## Creating a prompt -:::tip -If you already have prompts stored in code, you can use the the [`Prompt`](https://www.comet.com/docs/opik/python-sdk-reference/library/Prompt.html) object in the SDK to sync these prompts with the library. -This allows you to store the prompt text in your code while also having it versioned and stored in the library -See [Versioning prompts stored in code](/prompt_engineering/managing_prompts_in_code.mdx) for more details. -::: + + If you already have prompts stored in code, you can use the the + [`Prompt`](https://www.comet.com/docs/opik/python-sdk-reference/library/Prompt.html) object in the SDK to sync these + prompts with the library. This allows you to store the prompt text in your code while also having it versioned and + stored in the library See [Versioning prompts stored in code](/prompt_engineering/managing_prompts_in_code) for more + details. + You can create a new prompt in the library using both the SDK and the UI: - + You can create a prompt in the UI by navigating to the Prompt library and clicking `Create new prompt`. This will open a dialog where you can enter the prompt name, the prompt text, and optionally a description: - ![Prompt library](/img/prompt_engineering/prompt_library.png) + + + + You can also edit a prompt by clicking on the prompt name in the library and clicking `Edit prompt`. - - + + ```python import opik @@ -41,7 +35,7 @@ You can create a new prompt in the library using both the SDK and the UI: # Create a new prompt prompt = client.create_prompt(name="prompt-summary", prompt="Write a summary of the following text: {{text}}") ``` - + @@ -62,11 +56,11 @@ prompt = client.get_prompt(name="prompt-summary") prompt.format(text="Hello, world!") ``` -If you are not using the SDK, you can download a prompt by using the [REST API](/reference/rest_api/retrieve-prompt-version.api.mdx). +If you are not using the SDK, you can download a prompt by using the [REST API](/reference/rest-api/overview). ### Linking prompts to Experiments -[Experiments](/evaluation/evaluate_your_llm.md) allow you to evaluate the performance of your LLM application on a set of examples. When evaluating +[Experiments](/evaluation/evaluate_your_llm) allow you to evaluate the performance of your LLM application on a set of examples. When evaluating different prompts, it can be useful to link the evaluation to a specific prompt version. This can be achieved by passing the `prompt` parameter when creating an Experiment: @@ -91,4 +85,6 @@ evaluation = evaluate( The experiment will now be linked to the prompt allowing you to view all experiments that use a specific prompt: -![linked prompt](/img/evaluation/linked_prompt.png) + + + diff --git a/apps/opik-documentation/documentation/docs/quickstart.mdx b/apps/opik-documentation/documentation/fern/docs/quickstart.mdx similarity index 69% rename from apps/opik-documentation/documentation/docs/quickstart.mdx rename to apps/opik-documentation/documentation/fern/docs/quickstart.mdx index ac2e393222..28b1f7f1f9 100644 --- a/apps/opik-documentation/documentation/docs/quickstart.mdx +++ b/apps/opik-documentation/documentation/fern/docs/quickstart.mdx @@ -1,45 +1,37 @@ ---- -sidebar_label: Quickstart -description: This guide helps you integrate the Opik platform with your existing LLM application ---- - -import Tabs from "@theme/Tabs"; -import TabItem from "@theme/TabItem"; - -# Quickstart - This guide helps you integrate the Opik platform with your existing LLM application. The goal of this guide is to help you log your first LLM calls and chains to the Opik platform. -![Opik Traces](/img/home/traces_page_for_quickstart.png) + + + ## Set up -Getting started is as simple as creating an [account on Comet](https://www.comet.com/signup?from=llm) or [self-hosting the platform](/self-host/overview.md). +Getting started is as simple as creating an [account on Comet](https://www.comet.com/signup?from=llm) or [self-hosting the platform](/self-host/overview). Once your account is created, you can start logging traces by installing the Opik Python SDK: - + ```bash pip install opik ``` - + - + ```bash npm install opik ``` - + and configuring the SDK with: - + If you are using the Python SDK, we recommend running the `opik configure` command from the command line which will prompt you for all the necessary information: @@ -48,10 +40,10 @@ from the command line which will prompt you for all the necessary information: opik configure ``` -You can learn more about configuring the Python SDK [here](/tracing/sdk_configuration.mdx). +You can learn more about configuring the Python SDK [here](/tracing/sdk_configuration). - - + + If you are using the Javascript SDK you will need to set the required required parameters when initializing the client: @@ -68,7 +60,7 @@ const client = new Opik({ }); ``` - + @@ -76,11 +68,11 @@ const client = new Opik({ ### Logging LLM calls -The first step in integrating Opik with your codebase is to track your LLM calls. If you are using OpenAI or any LLM provider that is supported by LiteLLM, you -can use one of our [integrations](/tracing/integrations/overview.md): +The first step in integrating Opik with your codebase is to track your LLM calls. If you are using OpenAI, OpenRouter, or any LLM provider that is supported by LiteLLM, you +can use one of our [integrations](/tracing/integrations/overview): - + ```python from opik.integrations.openai import track_openai @@ -93,10 +85,39 @@ openai_client = track_openai(openai_client) All OpenAI calls made using the `openai_client` will now be logged to Opik. - - + + + +```python +from opik.integrations.openai import track_openai +from openai import OpenAI + +# Initialize OpenRouter client +client = OpenAI( + base_url="https://openrouter.ai/api/v1", + api_key="YOUR_OPENROUTER_API_KEY" +) +client = track_openai(client) + +# Optional headers for OpenRouter leaderboard +headers = { + "HTTP-Referer": "YOUR_SITE_URL", # Optional + "X-Title": "YOUR_SITE_NAME" # Optional +} + +response = client.chat.completions.create( + model="openai/gpt-4", # You can use any model available on OpenRouter + extra_headers=headers, + messages=[{"role": "user", "content": "Hello!"}] +) +``` + +All OpenRouter calls made using the `client` will now be logged to Opik. + + + -```python pytest_codeblocks_skip=true +```python {pytest_codeblocks_skip=true} from litellm.integrations.opik.opik import OpikLogger import litellm @@ -107,13 +128,13 @@ litellm.callbacks = [opik_logger] All LiteLLM calls made using the `litellm` client will now be logged to Opik. - + - + If you are using an LLM provider that Opik does not have an integration for, you can still log the LLM calls by using the `@track` decorator: -```python pytest_codeblocks_skip=true +```python {pytest_codeblocks_skip=true} from opik import track import anthropic @@ -128,11 +149,11 @@ call_llm(client, [{"role": "user", "content": "Why is tracking and evaluation of The `@track` decorator will automatically log the input and output of the decorated function allowing you to track the user messages and the LLM responses in Opik. If you want to log more than just the input and output, you can use the `update_current_span` function -as described in the [Traces / Logging Additional Data section](/tracing/log_traces.mdx#logging-additional-data). +as described in the [Traces / Logging Additional Data section](/tracing/log_traces#logging-additional-data). - + - + You can use the Opik client to log your LLM calls to Opik: @@ -173,19 +194,19 @@ const span = trace.span({ await client.flush(); ``` - + ### Logging chains It is common for LLM applications to use chains rather than just calling the LLM once. This is achieved by either using a framework -like [LangChain](/tracing/integrations/langchain.md), [LangGraph](/tracing/integrations/langgraph.md) or [LLamaIndex](/tracing/integrations/llama_index.md), +like [LangChain](/tracing/integrations/langchain), [LangGraph](/tracing/integrations/langgraph) or [LLamaIndex](/tracing/integrations/llama_index), or by writing custom python code. Opik makes it easy for your to log your chains no matter how you implement them: - + If you are not using any frameworks to build your chains, you can use the `@track` decorator to log your chains. When a function is decorated with `@track`, the input and output of the function will be logged to Opik. This works well even for very @@ -238,17 +259,18 @@ llm_chain("Hello, how are you?") While this code sample assumes that you are using OpenAI, the same principle applies if you are using any other LLM provider. -:::info -Your chains will now be logged to Opik and can be viewed in the Opik UI. To learn more about how you can customize the logged data, see the [Log Traces](/tracing/log_traces.mdx) guide. -::: + + Your chains will now be logged to Opik and can be viewed in the Opik UI. To learn more about how you can customize the + logged data, see the [Log Traces](/tracing/log_traces) guide. + - - + + If you are using LangChain to build your chains, you can use the `OpikTracer` to log your chains. The `OpikTracer` is a LangChain callback that will log every step of the chain to Opik: -```python pytest_codeblocks_skip=true +```python {pytest_codeblocks_skip=true} from langchain_openai import OpenAI from langchain.prompts import PromptTemplate from opik.integrations.langchain import OpikTracer @@ -271,38 +293,40 @@ llm_chain = prompt_template | llm llm_chain.invoke({"input": "Hello, how are you?"}, callbacks=[opik_tracer]) ``` -:::info -Your chains will now be logged to Opik and can be viewed in the Opik UI. To learn more about how you can customize the logged data, see the [Log Traces](/tracing/log_traces.mdx) guide. -::: + + Your chains will now be logged to Opik and can be viewed in the Opik UI. To learn more about how you can customize the + logged data, see the [Log Traces](/tracing/log_traces) guide. + - + - + If you are using LLamaIndex you can set `opik` as a global callback to log all LLM calls: -```python pytest_codeblocks_skip=true +```python {pytest_codeblocks_skip=true} from llama_index.core import global_handler, set_global_handler set_global_handler("opik") opik_callback_handler = global_handler ``` -You LlamaIndex calls from that point forward will be logged to Opik. You can learn more about the LlamaIndex integration in the [LLamaIndex integration docs](/tracing/integrations/llama_index.md). +You LlamaIndex calls from that point forward will be logged to Opik. You can learn more about the LlamaIndex integration in the [LLamaIndex integration docs](/tracing/integrations/llama_index). -:::info -Your chains will now be logged to Opik and can be viewed in the Opik UI. To learn more about how you can customize the logged data, see the [Log Traces](/tracing/log_traces.mdx) guide. -::: + + Your chains will now be logged to Opik and can be viewed in the Opik UI. To learn more about how you can customize the + logged data, see the [Log Traces](/tracing/log_traces) guide. + - + - + We are currently working on a AI Vercel SDK integration, stay tuned! Feel free to [open an issue](https://github.com/comet-ml/opik/issues) if you have any specific requests or suggestions - + @@ -310,5 +334,5 @@ Feel free to [open an issue](https://github.com/comet-ml/opik/issues) if you hav Now that you have logged your first LLM calls and chains to Opik, why not check out: -1. [Opik's evaluation metrics](/evaluation/metrics/overview.md): Opik provides a suite of evaluation metrics (Hallucination, Answer Relevance, Context Recall, etc.) that you can use to score your LLM responses. -2. [Opik Experiments](/evaluation/concepts.md): Opik allows you to automated the evaluation process of your LLM application so that you no longer need to manually review every LLM response. +1. [Opik's evaluation metrics](/evaluation/metrics/overview): Opik provides a suite of evaluation metrics (Hallucination, Answer Relevance, Context Recall, etc.) that you can use to score your LLM responses. +2. [Opik Experiments](/evaluation/concepts): Opik allows you to automated the evaluation process of your LLM application so that you no longer need to manually review every LLM response. diff --git a/apps/opik-documentation/documentation/fern/docs/reference/overview.mdx b/apps/opik-documentation/documentation/fern/docs/reference/overview.mdx new file mode 100644 index 0000000000..a6df0c9086 --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs/reference/overview.mdx @@ -0,0 +1,17 @@ +Opik provides in-depth reference documentation for all its SDKs. If you are looking for +guides on how to use Opik, check out our [cookbook](/cookbook/overview) instead. + + + + Python SDK reference documentation for all SDK methods + + + + Typescript SDK documentation overview + + + + API reference documentation for all SDK methods + + + diff --git a/apps/opik-documentation/documentation/fern/docs/reference/python-sdk/overview.mdx b/apps/opik-documentation/documentation/fern/docs/reference/python-sdk/overview.mdx new file mode 100644 index 0000000000..7137deb37d --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs/reference/python-sdk/overview.mdx @@ -0,0 +1,3 @@ +--- +title: Overview +--- diff --git a/apps/opik-documentation/documentation/fern/docs/reference/rest-api/overview.mdx b/apps/opik-documentation/documentation/fern/docs/reference/rest-api/overview.mdx new file mode 100644 index 0000000000..e76e7a548a --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs/reference/rest-api/overview.mdx @@ -0,0 +1,37 @@ +--- +--- + + + The Opik REST API is stable but currently in beta and subject to change. If you have any questions or feedback about + the APIs, please reach out on GitHub: https://github.com/comet-ml/opik. + + +The Rest API can be used with both the Open-Source platform and Opik Cloud. The main differences are related to the URL +to use and request headers used for authentication. + + + + If you are using the Open-Source platform you can simply use the `http://localhost:5173/api/v1/`: + + ```bash + curl -X GET 'http://localhost:5173/api/v1/private/projects' + ``` + + + + If you are using Opik Cloud or a on-premise installation of the Comet platform, you will need to specify the Opik + API Key and Opik Workspace in the header: + + ```bash + curl -X GET 'https://www.comet.com/opik/api/v1/private/projects' \ + -H 'Accept: application/json' \ + -H 'Comet-Workspace: ' \ + -H 'authorization: ' + ``` + + + Note that the authorization header value does not include the `Bearer ` prefix. + + + + diff --git a/apps/opik-documentation/documentation/fern/docs/reference/typescript-sdk/overview.mdx b/apps/opik-documentation/documentation/fern/docs/reference/typescript-sdk/overview.mdx new file mode 100644 index 0000000000..8c739c6efe --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs/reference/typescript-sdk/overview.mdx @@ -0,0 +1,137 @@ +## Installation + +You can install the `opik` package using your favorite package manager. + +```bash +npm install opik +``` + +## Opik Configuration + +You can configure the Opik client using environment variables. + +```bash +export OPIK_API_KEY="your-api-key" + +# If running on Opik Cloud +export OPIK_HOST="https://www.comet.com/opik/api" + +# If running locally +export OPIK_HOST="http://localhost:5173/api" + +export OPIK_PROJECT_NAME="your-project-name" +export OPIK_WORKSPACE_NAME="your-workspace-name" +``` + +Or you can pass the configuration to the Opik client constructor. + +```typescript +import { Opik } from "opik"; + +const client = new Opik({ + apiKey: "", + host: "https://www.comet.com/opik/api", + projectName: "", + workspaceName: "", +}); +``` + +## Usage + +You can find the full Typescript reference documentation [here](https://www.jsdocs.io/package/opik). + +```typescript +import { Opik } from "opik"; + +// Create a new Opik client with your configuration +const client = new Opik(); + +// Log 10 traces +for (let i = 0; i < 10; i++) { + const someTrace = client.trace({ + name: `Trace ${i}`, + input: { + prompt: `Hello, world! ${i}`, + }, + output: { + response: `Hello, world! ${i}`, + }, + }); + + // For each trace, log 10 spans + for (let j = 0; j < 10; j++) { + const someSpan = someTrace.span({ + name: `Span ${i}-${j}`, + type: "llm", + input: { + prompt: `Hello, world! ${i}:${j}`, + }, + output: { + response: `Hello, world! ${i}:${j}`, + }, + }); + + // Some LLM work + await new Promise((resolve) => setTimeout(resolve, 100)); + + // Mark the span as ended + someSpan.end(); + } + + // Mark the trace as ended + someTrace.end(); +} + +// Flush the client to send all traces and spans +await client.flush(); +``` + +## Vercel AI SDK Integration + +Opik provides seamless integration with the Vercel AI SDK through OpenTelemetry instrumentation. + +### Installation + +Install the required dependencies: + +```bash +npm install opik ai @opentelemetry/sdk-node @opentelemetry/auto-instrumentations-node +``` + +### Usage + +```typescript +import { openai } from "@ai-sdk/openai"; +import { getNodeAutoInstrumentations } from "@opentelemetry/auto-instrumentations-node"; +import { NodeSDK } from "@opentelemetry/sdk-node"; +import { generateText } from "ai"; +import { OpikExporter } from "opik/vercel"; + +const sdk = new NodeSDK({ + traceExporter: new OpikExporter(), + instrumentations: [getNodeAutoInstrumentations()], +}); + +sdk.start(); + +const { text } = await generateText({ + model: openai("gpt-4o-mini"), + prompt: "What is love? Describe it in 10 words or less.", + experimental_telemetry: OpikExporter.getSettings({ + name: "ai-sdk-integration", + }), +}); + +await sdk.shutdown(); +``` + +This integration automatically captures: + +- Input prompts and messages +- Model responses +- Token usage statistics +- Tool calls and their results +- Timing information +- Error states + +All this telemetry data is automatically sent to your Opik project for analysis and monitoring. diff --git a/apps/opik-documentation/documentation/docs/roadmap.md b/apps/opik-documentation/documentation/fern/docs/roadmap.mdx similarity index 82% rename from apps/opik-documentation/documentation/docs/roadmap.md rename to apps/opik-documentation/documentation/fern/docs/roadmap.mdx index ad1cb8c5b9..b2bb9273c5 100644 --- a/apps/opik-documentation/documentation/docs/roadmap.md +++ b/apps/opik-documentation/documentation/fern/docs/roadmap.mdx @@ -1,17 +1,10 @@ ---- -sidebar_label: Roadmap -description: Opik Roadmap ---- +Opik is [Open-Source](https://github.com/comet-ml/opik) and is under very active development. We use the feedback from the Opik community to drive the roadmap, this is very much a living document that will change as we release new features and learn about new ways to improve the product. -# Roadmap - -Opik is [Open-Source](https://github.com/comet-opik/opik) and is under very active development. We use the feedback from the Opik community to drive the roadmap, this is very much a living document that will change as we release new features and learn about new ways to improve the product. - -:::tip + If you have any ideas or suggestions for the roadmap, you can create a [new Feature Request issue](https://github.com/comet-ml/opik/issues/new/choose) in the Opik Github repo. -::: + ## What are we currently working on ? @@ -32,7 +25,7 @@ We are currently working on both improving existing features and developing new - [x] Online evaluation using LLM as a Judge metrics, allows Opik to score traces logged to the platform using LLM as a Judge metrics - [ ] Online evaluation using code metrics -You can view all the features we have released in our [changelog](/changelog.md). +You can view all the features we have released in our [changelog](/docs/opik/changelog). ## What is planned next ? @@ -57,4 +50,4 @@ You can vote on these items as well as suggest new ideas on our [Github Issues p We are relying on your feedback to shape the roadmap and decided which features to work on next. You can upvote existing ideas or even add your own on [Github Issues](https://github.com/comet-ml/opik/issues/). -You can also find a list of all the features we have released in our [weekly release notes](/changelog.md). +You can also find a list of all the features we have released in our [weekly release notes](/changelog). diff --git a/apps/opik-documentation/documentation/fern/docs/self-host/architecture.mdx b/apps/opik-documentation/documentation/fern/docs/self-host/architecture.mdx new file mode 100644 index 0000000000..143561fda9 --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs/self-host/architecture.mdx @@ -0,0 +1,101 @@ +--- +subtitle: High-level overview on Opik's Platform Architecture + +pytest_codeblocks_skip: true +--- + +Opik's architecture consists of multiple services that each handle a specific role, including: + +- **A backend service**: Java + Dropwizard. +- **A frontend application**: TypeScript + React, served by Nginx. +- **Data stores**: + - ClickHouse for large-scale data ingestion and fast queries (e.g., for traces or experiments). + - With Zookeeper to coordinate the cluster. + - With an Operator to provide operational and performance metrics. + - MySQL for transactional data. + - Redis for caching, rate limiting, distributed locks and streams. + + + Architecture Diagram + + +## Backend Service + +Opik's backend uses Java 21 LTS and Dropwizard 4, structured as a RESTful web service offering public API +endpoints for core functionality. Full API documentation is available [here](/reference/rest-api/overview). + +For observability Opik uses OpenTelemetry due its vendor-neutral approach and wide support across languages +and frameworks. It provides a single, consistent way to collect telemetry data from all services and applications. + +_You can find the full backend codebase in Github under the [`apps/opik-backend`](https://github.com/comet-ml/opik/tree/main/apps/opik-backend) folder._ + +## Frontend Application + +Opik's frontend is a TypeScript + React application served by Nginx. It provides a user-friendly interface for +interacting with the backend services. The frontend is built using a modular approach, with each module +encapsulating a specific feature or functionality. + +_You can find the full frontend codebase in Github under the [`apps/opik-frontend`](https://github.com/comet-ml/opik/tree/main/apps/opik-frontend) folder._ + +## SDK's + +Opik provides SDKs for Python, and JavaScript. These SDKs allow developers to interact with Opik's backend +services programmatically. The SDKs are designed to be easy to use and provide a high-level abstraction over +the REST API and many additional features. + +_You can find the full SDK codebase in Github under the [`sdks/python`](https://github.com/comet-ml/opik/tree/main/sdks/python) for the Python SDK +and [`sdks/typescript`](https://github.com/comet-ml/opik/tree/main/sdks/typescript) for the TypeScript SDK._ + +## ClickHouse + +ClickHouse is a column-oriented database management system developed by Yandex. It is optimized for fast analytics on large datasets and is capable of processing hundreds of millions to more than a billion rows and tens of gigabytes of data per single server per second. + +Opik uses ClickHouse for datasets that require near real-time ingestion and analytical queries, such as: + +- LLM calls and traces +- Feedback scores +- Datasets and experiments +- Experiments + +The image below details the schema used by Opik in ClickHouse: + + + ClickHouse Schema + + + Liquibase automates schema management + + +## MySQL + +Opik uses MySQL for transactional data, it provides ACID-compliant transactional storage for Opik's lower-volume but critical data, such as: + +- Feedback definitions +- Metadata containers e.g., projects that group related traces +- Configuration data + +The image below details the schema used by Opik in MySQL: + + + MySQL Schema + + + Liquibase automates schema management + + +## Redis + +Redis is an in-memory data structure store, used as a database, cache, and message broker. It supports a vast range of data structures. Opik uses Redis for: + +- A distributed cache: for high-speed lookups. +- A distributed lock: for coordinating safe access to certain shared resources. +- A rate limiter: to enforce throughput limits and protect scalability. +- A streaming mechanism: Redis streams power Opik's Online evaluation functionality; future iterations may integrate Kafka or similar platforms for even higher scalability. + +## Observability + +Opik is built and runs on top of open-source infrastructure (MySQL, Redis, Kubernetes, and more), making it straightforward to integrate with popular observability stacks such as Grafana and Prometheus. Specifically: + +- The backend uses OpenTelemetry for vendor-neutral instrumentation. +- ClickHouse deployments include an operator for real-time performance monitoring and metric exports to Grafana/Prometheus. +- Other components (MySQL, Redis, Kubernetes) also have well-documented strategies for monitoring. diff --git a/apps/opik-documentation/documentation/docs/self-host/configure/anonymous_usage_statistics.md b/apps/opik-documentation/documentation/fern/docs/self-host/configure/anonymous_usage_statistics.mdx similarity index 92% rename from apps/opik-documentation/documentation/docs/self-host/configure/anonymous_usage_statistics.md rename to apps/opik-documentation/documentation/fern/docs/self-host/configure/anonymous_usage_statistics.mdx index 9ddab38eb5..e06cb4d979 100644 --- a/apps/opik-documentation/documentation/docs/self-host/configure/anonymous_usage_statistics.md +++ b/apps/opik-documentation/documentation/fern/docs/self-host/configure/anonymous_usage_statistics.mdx @@ -1,10 +1,7 @@ --- -sidebar_label: Anonymous Usage Statistics -description: Describes the usage statistics that are collected by Opik +subtitle: Describes the usage statistics that are collected by Opik --- -# Anonymous Usage Statistics - Opik includes a system that optionally sends anonymous reports non-sensitive, non-personally identifiable information about the usage of the Opik platform. This information is used to help us understand how the Opik platform is being used and to identify areas for improvement. The anonymous usage statistics reporting is enabled by default. You can opt-out by setting the `OPIK_USAGE_REPORT_ENABLED` environment variable to `false`. diff --git a/apps/opik-documentation/documentation/docs/self-host/kubernetes.md b/apps/opik-documentation/documentation/fern/docs/self-host/kubernetes.mdx similarity index 88% rename from apps/opik-documentation/documentation/docs/self-host/kubernetes.md rename to apps/opik-documentation/documentation/fern/docs/self-host/kubernetes.mdx index 070528c8b9..db4fe31ac8 100644 --- a/apps/opik-documentation/documentation/docs/self-host/kubernetes.md +++ b/apps/opik-documentation/documentation/fern/docs/self-host/kubernetes.mdx @@ -1,11 +1,7 @@ --- -sidebar_label: Production (Kubernetes) -description: Describes how to run Opik on a Kubernetes cluster -pytest_codeblocks_skip: true +subtitle: Describes how to run Opik on a Kubernetes cluster --- -# Production ready Kubernetes deployment - For production deployments, we recommend using our Kubernetes Helm chart. This chart is designed to be highly configurable and has been battle-tested in Comet's managed cloud offering. ## Prerequisites diff --git a/apps/opik-documentation/documentation/docs/self-host/local_deployment.md b/apps/opik-documentation/documentation/fern/docs/self-host/local_deployment.mdx similarity index 72% rename from apps/opik-documentation/documentation/docs/self-host/local_deployment.md rename to apps/opik-documentation/documentation/fern/docs/self-host/local_deployment.mdx index 81b1ffbca2..3eb7247255 100644 --- a/apps/opik-documentation/documentation/docs/self-host/local_deployment.md +++ b/apps/opik-documentation/documentation/fern/docs/self-host/local_deployment.mdx @@ -1,21 +1,18 @@ --- -sidebar_label: Local (Docker Compose) -description: Describes how to run Opik locally using Docker Compose -pytest_codeblocks_skip: true +subtitle: Describes how to run Opik locally using Docker Compose --- -# Local Deployments using Docker Compose - -To run Opik locally we recommend using [Docker Compose](https://docs.docker.com/compose/). It's easy to setup and allows you to get started in a couple of minutes **but** is not meant for production deployments. If you would like to run Opik in a production environment, we recommend using our [Kubernetes Helm chart](./kubernetes.md). +To run Opik locally we recommend using [Docker Compose](https://docs.docker.com/compose/). It's easy to setup and allows you to get started in a couple of minutes **but** is not meant for production deployments. If you would like to run Opik in a production environment, we recommend using our [Kubernetes Helm chart](/self-host/kubernetes). Before running the installation, make sure you have Docker and Docker Compose installed: - [Docker](https://docs.docker.com/get-docker/) - [Docker Compose](https://docs.docker.com/compose/install/) -:::note -If you are using Mac or Windows, both `docker` and `docker compose` are included in the [Docker Desktop](https://docs.docker.com/desktop/) installation. -::: + + If you are using Mac or Windows, both `docker` and `docker compose` are included in the [Docker + Desktop](https://docs.docker.com/desktop/) installation. + ## Installation @@ -32,9 +29,9 @@ cd opik/deployment/docker-compose docker compose up --detach ``` -Opik will now be available at http://localhost:5173 +Opik will now be available at [http://localhost:5173](http://localhost:5173) -:::tip + In order to use the Opik Python SDK with your local Opik instance, you will need to run: ```bash @@ -52,15 +49,14 @@ opik.configure(use_local=True) ``` This will create a `~/.opik.config` file that will store the URL of your local Opik instance. -::: + + All the data logged to the Opik platform will be stored in the `~/opik` directory, which means that you can start and stop the Opik platform without losing any data. ## Starting, stopping -:::note -All the `docker compose` commands should be run from the `opik/deployment/docker-compose` directory. -::: +All the `docker compose` commands should be run from the `opik/deployment/docker-compose` directory. The `docker compose up` command can be used to install, start and upgrade Opik: @@ -96,9 +92,10 @@ docker compose pull docker compose up --detach ``` -:::tip -Since the Docker Compose deployment is using mounted volumes, your data will **_not_** be lost when you upgrade Opik. You can also safely start and stop the Opik platform without losing any data. -::: + + Since the Docker Compose deployment is using mounted volumes, your data will **_not_** be lost when you upgrade Opik. + You can also safely start and stop the Opik platform without losing any data. + ## Removing Opik @@ -109,9 +106,10 @@ To remove Opik, you will need to remove the Opik containers and volumes: docker compose down --volumes ``` -:::warning -Removing the volumes will delete all the data stored in the Opik platform and cannot be recovered. We do not recommend this option unless you are sure that you will not need any of the data stored in the Opik platform. -::: + + Removing the volumes will delete all the data stored in the Opik platform and cannot be recovered. We do not recommend + this option unless you are sure that you will not need any of the data stored in the Opik platform. + ## Advanced configuration diff --git a/apps/opik-documentation/documentation/docs/self-host/overview.md b/apps/opik-documentation/documentation/fern/docs/self-host/overview.mdx similarity index 76% rename from apps/opik-documentation/documentation/docs/self-host/overview.md rename to apps/opik-documentation/documentation/fern/docs/self-host/overview.mdx index be32e3d667..d60bda5cc9 100644 --- a/apps/opik-documentation/documentation/docs/self-host/overview.md +++ b/apps/opik-documentation/documentation/fern/docs/self-host/overview.mdx @@ -1,23 +1,21 @@ --- -sidebar_label: Overview -description: High-level overview on how to self-host Opik +subtitle: High-level overview on how to self-host Opik + pytest_codeblocks_skip: true --- -# Self-hosting Opik - You can use Opik through [Comet's Managed Cloud offering](https://comet.com/site) or you can self-host Opik on your own infrastructure. When choosing to self-host Opik, you get access to all Opik features including tracing, evaluation, etc but without user management features. If you choose to self-host Opik, you can choose between two deployment options: -1. [Local installation](./local_deployment.md): Perfect to get started but not production-ready. -2. [Kubernetes installation](./kubernetes.md): Production ready Opik platform that runs on a Kubernetes cluster. +1. [Local installation](/self-host/local_deployment): Perfect to get started but not production-ready. +2. [Kubernetes installation](/self-host/kubernetes): Production ready Opik platform that runs on a Kubernetes cluster. ## Getting started If you would like to try out Opik locally, we recommend using our Local installation based on `docker compose`. Assuming you have `git` and `docker` installed, you can get started in a couple of minutes: -```bash pytest_codeblocks_skip=true +```bash # Clone the Opik repository git clone https://github.com/comet-ml/opik.git @@ -29,24 +27,24 @@ docker compose up --detach Opik will now be available at http://localhost:5173 and all traces logged from your local machine will be logged to this local Opik instance. In order for traces and other data to be logged to your Opik instance, you need to make sure that the Opik Python SDK is configured to point to the Opik server you just started. You can do this by running the following command: -```bash pytest_codeblocks_skip=true +```bash # Configure the Python SDK to point to the local Opik platform export OPIK_BASE_URL=http://localhost:5173/api ``` or in Python: -```python pytest_codeblocks_skip=true +```python import os os.environ["OPIK_BASE_URL"] = "http://localhost:5173/api" ``` -To learn more about how to manage you local Opik deployment, you can refer to our [local deployment guide](./local_deployment.md). +To learn more about how to manage you local Opik deployment, you can refer to our [local deployment guide](/self-host/local_deployment). ## Advanced deployment options -If you would like to deploy Opik on a Kubernetes cluster, we recommend following our Kubernetes deployment guide [here](./kubernetes.md). +If you would like to deploy Opik on a Kubernetes cluster, we recommend following our Kubernetes deployment guide [here](/self-host/kubernetes). ## Comet managed deployments diff --git a/apps/opik-documentation/documentation/docs/testing/pytest_integration.md b/apps/opik-documentation/documentation/fern/docs/testing/pytest_integration.mdx similarity index 79% rename from apps/opik-documentation/documentation/docs/testing/pytest_integration.md rename to apps/opik-documentation/documentation/fern/docs/testing/pytest_integration.mdx index 75b52499b5..21b0b8ffce 100644 --- a/apps/opik-documentation/documentation/docs/testing/pytest_integration.md +++ b/apps/opik-documentation/documentation/fern/docs/testing/pytest_integration.mdx @@ -1,10 +1,7 @@ --- -sidebar_label: Pytest Integration -description: Describes how to use Opik with Pytest to write LLM unit tests +subtitle: Describes how to use Opik with Pytest to write LLM unit tests --- -# Pytest Integration - Ensuring your LLM applications is working as expected is a crucial step before deploying to production. Opik provides a Pytest integration so that you can easily track the overall pass / fail rates of your tests as well as the individual pass / fail rates of each test. ## Using the Pytest Integration @@ -29,11 +26,15 @@ def test_simple_passing_test(): When you run the tests, Opik will create a new experiment for each run and log each test result. By navigating to the `tests` dataset, you will see a new experiment for each test run. -![Test Experiments](/img/testing/test_experiments.png) + + + -:::tip -If you are evaluating your LLM application during development, we recommend using the `evaluate` function as it will provide you with a more detailed report. You can learn more about the `evaluate` function in the [evaluation documentation](/evaluation/evaluate_your_llm.md). -::: + + If you are evaluating your LLM application during development, we recommend using the `evaluate` function as it will + provide you with a more detailed report. You can learn more about the `evaluate` function in the [evaluation + documentation](/evaluation/evaluate_your_llm). + ### Advanced Usage diff --git a/apps/opik-documentation/documentation/docs/tracing/annotate_traces.md b/apps/opik-documentation/documentation/fern/docs/tracing/annotate_traces.mdx similarity index 82% rename from apps/opik-documentation/documentation/docs/tracing/annotate_traces.md rename to apps/opik-documentation/documentation/fern/docs/tracing/annotate_traces.mdx index b654e859c0..49f5b9ad39 100644 --- a/apps/opik-documentation/documentation/docs/tracing/annotate_traces.md +++ b/apps/opik-documentation/documentation/fern/docs/tracing/annotate_traces.mdx @@ -1,10 +1,7 @@ --- -sidebar_label: Annotate Traces -description: Describes how to annotate traces using the Opik SDK and UI +subtitle: Describes how to annotate traces using the Opik SDK and UI --- -# Annotate Traces - Annotating traces is a crucial aspect of evaluating and improving your LLM-based applications. By systematically recording qualitative or quantitative feedback on specific interactions or entire conversation flows, you can: 1. Track performance over time @@ -21,15 +18,18 @@ To annotate traces through the UI, you can navigate to the trace you want to ann You can annotate both traces and spans through the UI, make sure you have selected the correct span in the sidebar. -![Annotate Traces](/img/tracing/annotate_traces.png) + + + -:::tip -In order to ensure a consistent set of feedback, you will need to define feedback definitions in the `Feedback Definitions` page which supports both numerical and categorical annotations. -::: + + In order to ensure a consistent set of feedback, you will need to define feedback definitions in the `Feedback + Definitions` page which supports both numerical and categorical annotations. + ## Online evaluation -You don't need to manually annotate each trace to measure the performance of your LLM applications! By using Opik's [online evaluation feature](/production/rules.md), you can define LLM as a Judge metrics that will automatically score all, or a subset, of your production traces. +You don't need to manually annotate each trace to measure the performance of your LLM applications! By using Opik's [online evaluation feature](/production/rules), you can define LLM as a Judge metrics that will automatically score all, or a subset, of your production traces. ![Online evaluation](/img/production/online_evaluation.gif) @@ -56,9 +56,10 @@ client.log_traces_feedback_scores( ) ``` -:::tip -The `scores` argument supports an optional `reason` field that can be provided to each score. This can be used to provide a human-readable explanation for the feedback score. -::: + + The `scores` argument supports an optional `reason` field that can be provided to each score. This can be used to + provide a human-readable explanation for the feedback score. + ### Annotating Spans through the SDK @@ -107,7 +108,7 @@ Opik supports a variety of heuristic metrics including: - `BleuMetric` - `RougeMetric` -You can find a full list of metrics in the [Heuristic Metrics](/evaluation/metrics/heuristic_metrics.md) section. +You can find a full list of metrics in the [Heuristic Metrics](/evaluation/metrics/heuristic_metrics) section. These can be used by calling: @@ -134,4 +135,4 @@ Opik supports many different LLM as a Judge metrics out of the box including: - `ContextRecallMetric` - `ContextPrecisionMetric` -You can find a full list of supported metrics in the [Metrics Overview](/evaluation/metrics/overview.md) section. +You can find a full list of supported metrics in the [Metrics Overview](/evaluation/metrics/overview) section. diff --git a/apps/opik-documentation/documentation/docs/tracing/cost_tracking.md b/apps/opik-documentation/documentation/fern/docs/tracing/cost_tracking.mdx similarity index 70% rename from apps/opik-documentation/documentation/docs/tracing/cost_tracking.md rename to apps/opik-documentation/documentation/fern/docs/tracing/cost_tracking.mdx index c48c1c6db1..55118646e4 100644 --- a/apps/opik-documentation/documentation/docs/tracing/cost_tracking.md +++ b/apps/opik-documentation/documentation/fern/docs/tracing/cost_tracking.mdx @@ -1,11 +1,7 @@ --- -sidebar_label: Cost Tracking -description: Describes how to track and monitor costs for your LLM applications using Opik -pytest_codeblocks_skip: true +subtitle: Describes how to track and monitor costs for your LLM applications using Opik --- -# Cost Tracking - Opik has been designed to track and monitor costs for your LLM applications by measuring token usage across all traces. Using the Opik dashboard, you can analyze spending patterns and quickly identify cost anomalies. All costs across Opik are estimated and displayed in USD. ## Monitoring Costs in the Dashboard @@ -16,27 +12,36 @@ You can use the Opik dashboard to review costs at three levels: spans, traces, a Individual spans show the computed costs (in USD) for each LLM spans of your traces: -![Detailed cost breakdown for individual spans in the Traces and LLM calls view](/img/tracing/cost_tracking_span.png) + + + ### Trace-Level Costs Opik automatically aggregates costs from all spans within a trace to compute total trace costs: -![Total cost aggregation at the trace level](/img/tracing/cost_tracking_trace_view.png) + + + ### Project-Level Analytics Track your overall project costs in: 1. The main project view, through the Estimated Cost column: - ![Project-wide cost overview](/img/tracing/cost_tracking_project.png) + + + + 2. The project Metrics tab, which shows cost trends over time: - ![Detailed cost metrics and analytics](/img/tracing/cost_tracking_project_metrics.png) + + + ## Retrieving Costs Programmatically -You can retrieve the estimated cost programmatically for both spans and traces. Note that the cost will be `None` if the span or trace used an unsupported model. See [Exporting Traces and Spans](./export_data.md) for more ways of exporting traces and spans. +You can retrieve the estimated cost programmatically for both spans and traces. Note that the cost will be `None` if the span or trace used an unsupported model. See [Exporting Traces and Spans](/tracing/export_data) for more ways of exporting traces and spans. ### Retrieving Span Costs @@ -74,6 +79,7 @@ update_current_span(total_cost=0.05) # Cost in USD will override any automatic ``` This is particularly useful when: + - Using models or providers not yet supported by automatic cost tracking - You have a custom pricing agreement with your provider - You want to track additional costs beyond model usage @@ -81,9 +87,11 @@ This is particularly useful when: ## Supported Models and Integrations Opik currently calculates costs automatically for: -- [OpenAI Integration](./integrations/openai.md) with Text Models hosted on openai.com -- [Langchain Integration](./integrations/langchain.md) with Vertex AI Gemini text generation models -:::tip -We are actively expanding our cost tracking support. Need support for additional models or providers? Please [open a feature request](https://github.com/comet-ml/opik/issues) to help us prioritize development. -::: +- [OpenAI Integration](/tracing/integrations/openai) with Text Models hosted on openai.com +- [Langchain Integration](/tracing/integrations/langchain) with Vertex AI Gemini text generation models + + + We are actively expanding our cost tracking support. Need support for additional models or providers? Please [open a + feature request](https://github.com/comet-ml/opik/issues) to help us prioritize development. + diff --git a/apps/opik-documentation/documentation/docs/tracing/export_data.md b/apps/opik-documentation/documentation/fern/docs/tracing/export_data.mdx similarity index 68% rename from apps/opik-documentation/documentation/docs/tracing/export_data.md rename to apps/opik-documentation/documentation/fern/docs/tracing/export_data.mdx index d8f50c85c2..926e255d46 100644 --- a/apps/opik-documentation/documentation/docs/tracing/export_data.md +++ b/apps/opik-documentation/documentation/fern/docs/tracing/export_data.mdx @@ -1,22 +1,24 @@ --- -sidebar_label: Export Traces and Spans -description: Describes how to export traces and spans from the Opik platform. +subtitle: Describes how to export traces and spans from the Opik platform. + toc_max_heading_level: 4 +pytest_codeblocks_skip: true --- -# Exporting Traces and Spans - When working with Opik, it is important to be able to export traces and spans so that you can use them to fine-tune your models or run deeper analysis. You can export the traces you have logged to the Opik platform using: 1. Using the Opik SDK: You can use the [`Opik.search_traces`](https://www.comet.com/docs/opik/python-sdk-reference/Opik.html#opik.Opik.search_traces) and [`Opik.search_spans`](https://www.comet.com/docs/opik/python-sdk-reference/Opik.html#opik.Opik.search_spans) methods to export traces and spans. -2. Using the Opik REST API: You can use the [`/traces`](/reference/rest_api/get-traces-by-project.api.mdx) and [`/spans`](/reference/rest_api/get-spans-by-project.api.mdx) endpoints to export traces and spans. +2. Using the Opik REST API: You can use the [`/traces`](/reference/rest-api/traces/get-traces-by-project) and [`/spans`](/reference/rest-api/spans/get-spans-by-project) endpoints to export traces and spans. 3. Using the UI: Once you have selected the traces or spans you want to export, you can click on the `Export CSV` button in the `Actions` dropdown. -:::tip -The recommended way to export traces is to use the [`Opik.search_traces`](https://www.comet.com/docs/opik/python-sdk-reference/Opik.html#opik.Opik.search_traces) and [`Opik.search_spans`](https://www.comet.com/docs/opik/python-sdk-reference/Opik.html#opik.Opik.search_spans) methods in the Opik SDK. -::: + + The recommended way to export traces is to use the + [`Opik.search_traces`](https://www.comet.com/docs/opik/python-sdk-reference/Opik.html#opik.Opik.search_traces) and + [`Opik.search_spans`](https://www.comet.com/docs/opik/python-sdk-reference/Opik.html#opik.Opik.search_spans) methods + in the Opik SDK. + ## Using the Opik SDK @@ -98,6 +100,28 @@ traces = client.search_traces(filter_string='usage.total_tokens > 1000') traces = client.search_traces(filter_string='metadata.model = "gpt-4o"') ``` +:::tip + +If your feedback scores names contain spaces, you will need to wrap them in double quotes: + +```python + +import opik + +client = opik.Opik( + project_name="Default project" +) + +# Search for traces where the input contains text +traces = client.search_traces( + filter_string='feedback_score."My Score" > 0' +) +``` + +If the feedback score contains both spaces and double quotes, you will need to escape the double quotes as `""`: +`traces = client.search_traces(filter_string='feedback_score."Score ""with"" Quotes" > 0')` +::: + ### Exporting spans You can export spans using the [`Opik.search_spans`](https://www.comet.com/docs/opik/python-sdk-reference/Opik.html#opik.Opik.search_spans) method. This methods allows you to search for spans based on `trace_id` or based on a filter string. @@ -132,13 +156,14 @@ spans = client.search_spans( ) ``` -:::tip -The `filter_string` parameter should follow the same format as the `filter_string` parameter in the `Opik.search_traces` method as [defined above](#search-for-specific-traces). -::: + + The `filter_string` parameter should follow the same format as the `filter_string` parameter in the + `Opik.search_traces` method as [defined above](#search-for-specific-traces). + ## Using the Opik REST API -To export traces using the Opik REST API, you can use the [`/traces`](/reference/rest_api/get-traces-by-project.api.mdx) endpoint and the [`/spans`](/reference/rest_api/get-spans-by-project.api.mdx) endpoint. These endpoints are paginated so you will need to make multiple requests to retrieve all the traces or spans you want. +To export traces using the Opik REST API, you can use the [`/traces`](/reference/rest-api/traces/get-traces-by-project) endpoint and the [`/spans`](/reference/rest-api/spans/get-spans-by-project) endpoint. These endpoints are paginated so you will need to make multiple requests to retrieve all the traces or spans you want. To search for specific traces or spans, you can use the `filter` parameter. While this is a string parameter, it does not follow the same format as the `filter_string` parameter in the Opik SDK. Instead it is a list of json objects with the following format: @@ -153,17 +178,20 @@ To search for specific traces or spans, you can use the `filter` parameter. Whil ] ``` -:::warning -The `filter` parameter was designed to be used with the Opik UI and has therefore limited flexibility. If you need more flexibility, -please raise an issue on [GitHub](https://github.com/comet-ml/opik/issues) so we can help. -::: + + The `filter` parameter was designed to be used with the Opik UI and has therefore limited flexibility. If you need + more flexibility, please raise an issue on [GitHub](https://github.com/comet-ml/opik/issues) so we can help. + ## Using the UI To export traces as a CSV file from the UI, you can simply select the traces or spans you wish to export and click on `Export CSV` in the `Actions` dropdown: -![Export CSV](/img/tracing/download_traces.png) + + + -:::tip -The UI only allows you to export up to 100 traces or spans at a time as it is linked to the page size of the traces table. If you need to export more traces or spans, we recommend using the Opik SDK. -::: + + The UI only allows you to export up to 100 traces or spans at a time as it is linked to the page size of the traces + table. If you need to export more traces or spans, we recommend using the Opik SDK. + diff --git a/apps/opik-documentation/documentation/docs/tracing/integrations/aisuite.md b/apps/opik-documentation/documentation/fern/docs/tracing/integrations/aisuite.mdx similarity index 77% rename from apps/opik-documentation/documentation/docs/tracing/integrations/aisuite.md rename to apps/opik-documentation/documentation/fern/docs/tracing/integrations/aisuite.mdx index d9c095853f..69283bde8c 100644 --- a/apps/opik-documentation/documentation/docs/tracing/integrations/aisuite.md +++ b/apps/opik-documentation/documentation/fern/docs/tracing/integrations/aisuite.mdx @@ -1,16 +1,23 @@ --- -sidebar_label: aisuite -description: Describes how to track aisuite LLM calls using Opik +subtitle: Describes how to track aisuite LLM calls using Opik --- -# aisuite - This guide explains how to integrate Opik with the aisuite Python SDK. By using the `track_aisuite` method provided by opik, you can easily track and evaluate your aisuite API calls within your Opik projects as Opik will automatically log the input prompt, model used, token usage, and response generated.
- You can check out the Colab Notebook if you'd like to jump straight to the code: - - Open In Colab + + You can check out the Colab Notebook if you'd like to jump straight to the code: + + + Open In Colab
diff --git a/apps/opik-documentation/documentation/docs/tracing/integrations/anthropic.md b/apps/opik-documentation/documentation/fern/docs/tracing/integrations/anthropic.mdx similarity index 76% rename from apps/opik-documentation/documentation/docs/tracing/integrations/anthropic.md rename to apps/opik-documentation/documentation/fern/docs/tracing/integrations/anthropic.mdx index 529414495c..f6528f6aeb 100644 --- a/apps/opik-documentation/documentation/docs/tracing/integrations/anthropic.md +++ b/apps/opik-documentation/documentation/fern/docs/tracing/integrations/anthropic.mdx @@ -1,18 +1,25 @@ --- -sidebar_label: Anthropic -description: Describes how to track Anthropic LLM calls using Opik +subtitle: Describes how to track Anthropic LLM calls using Opik --- -# Anthropic - [Anthropic](https://www.anthropic.com/) is an AI safety and research company that's working to build reliable, interpretable, and steerable AI systems. This guide explains how to integrate Opik with the Anthropic Python SDK. By using the `track_anthropic` method provided by opik, you can easily track and evaluate your Anthropic API calls within your Opik projects as Opik will automatically log the input prompt, model used, token usage, and response generated.
- You can check out the Colab Notebook if you'd like to jump straight to the code: - - Open In Colab + + You can check out the Colab Notebook if you'd like to jump straight to the code: + + + Open In Colab
@@ -38,7 +45,7 @@ In order to configure Anthropic, you will need to have your Anthropic API Key se Once you have it, you can set it as an environment variable: -```bash pytest_codeblocks_skip=true +```bash {pytest_codeblocks_skip=true} export ANTHROPIC_API_KEY="YOUR_API_KEY" ``` @@ -65,4 +72,6 @@ response = anthropic_client.messages.create( print("Response", response.content[0].text) ``` -![Anthropic Integration](/img/cookbook/anthropic_trace_cookbook.png) + + + diff --git a/apps/opik-documentation/documentation/docs/tracing/integrations/bedrock.md b/apps/opik-documentation/documentation/fern/docs/tracing/integrations/bedrock.mdx similarity index 81% rename from apps/opik-documentation/documentation/docs/tracing/integrations/bedrock.md rename to apps/opik-documentation/documentation/fern/docs/tracing/integrations/bedrock.mdx index 583e5deea1..530786e0e0 100644 --- a/apps/opik-documentation/documentation/docs/tracing/integrations/bedrock.md +++ b/apps/opik-documentation/documentation/fern/docs/tracing/integrations/bedrock.mdx @@ -1,19 +1,25 @@ --- -sidebar_label: Bedrock -description: Describes how to track Bedrock LLM calls using Opik -pytest_codeblocks_skip: true +subtitle: Describes how to track Bedrock LLM calls using Opik --- -# AWS Bedrock - [AWS Bedrock](https://aws.amazon.com/bedrock/) is a fully managed service that provides access to high-performing foundation models (FMs) from leading AI companies like AI21 Labs, Anthropic, Cohere, Meta, Mistral AI, Stability AI, and Amazon through a single API. This guide explains how to integrate Opik with the Bedrock Python SDK. By using the `track_bedrock` method provided by opik, you can easily track and evaluate your Bedrock API calls within your Opik projects as Opik will automatically log the input prompt, model used, token usage, and response generated.
- You can check out the Colab Notebook if you'd like to jump straight to the code: - - Open In Colab + + You can check out the Colab Notebook if you'd like to jump straight to the code: + + + Open In Colab
@@ -76,4 +82,6 @@ response = bedrock_client.converse( print("Response", response["output"]["message"]["content"][0]["text"]) ``` -![Bedrock Integration](/img/cookbook/bedrock_trace_cookbook.png) + + + diff --git a/apps/opik-documentation/documentation/docs/tracing/integrations/crewai.md b/apps/opik-documentation/documentation/fern/docs/tracing/integrations/crewai.mdx similarity index 80% rename from apps/opik-documentation/documentation/docs/tracing/integrations/crewai.md rename to apps/opik-documentation/documentation/fern/docs/tracing/integrations/crewai.mdx index 2dc9acf6ba..3d73c3d60b 100644 --- a/apps/opik-documentation/documentation/docs/tracing/integrations/crewai.md +++ b/apps/opik-documentation/documentation/fern/docs/tracing/integrations/crewai.mdx @@ -1,18 +1,25 @@ --- -sidebar_label: CrewAI -description: Describes how to track CrewAI calls using Opik +subtitle: Describes how to track CrewAI calls using Opik --- -# CrewAI - [CrewAI](https://www.crewai.com/) is a cutting-edge framework for orchestrating autonomous AI agents. Opik integrates with CrewAI to log traces for all CrewAI activity.
- You can check out the Colab Notebook if you'd like to jump straight to the code: - - Open In Colab + + You can check out the Colab Notebook if you'd like to jump straight to the code: + + + Open In Colab
@@ -92,4 +99,6 @@ print(result) Each run will now be logged to the Opik platform: -![CrewAI](/img/cookbook/crewai_trace_cookbook.png) + + + diff --git a/apps/opik-documentation/documentation/docs/tracing/integrations/dify.mdx b/apps/opik-documentation/documentation/fern/docs/tracing/integrations/dify.mdx similarity index 72% rename from apps/opik-documentation/documentation/docs/tracing/integrations/dify.mdx rename to apps/opik-documentation/documentation/fern/docs/tracing/integrations/dify.mdx index ec3f5bf454..2e669ef1e7 100644 --- a/apps/opik-documentation/documentation/docs/tracing/integrations/dify.mdx +++ b/apps/opik-documentation/documentation/fern/docs/tracing/integrations/dify.mdx @@ -1,14 +1,7 @@ --- -sidebar_label: Dify -description: Describes how to use Opik with Dify -pytest_codeblocks_skip: true +subtitle: Describes how to use Opik with Dify --- -import Tabs from "@theme/Tabs"; -import TabItem from "@theme/TabItem"; - -# Dify Integration - Learn how to connect Opik with Dify to monitor your applications' performance. ## Setup Instructions @@ -21,10 +14,12 @@ Follow these simple steps to connect Dify with Opik: 4. Click on **Configure** for Opik 5. Enter your connection details based on your Opik version: -![How to configure Dify settings](/img/tracing/dify_configuration.png) + + + - + Fill in these fields: @@ -33,9 +28,9 @@ Fill in these fields: - **Workspace**: Your Comet Workspace name (must already exist) - **URL**: Your Opik installation URL (make sure it ends with `/api/`) - + - + Fill in these fields: @@ -44,7 +39,7 @@ Fill in these fields: - **Workspace**: Type `default` - **URL**: Your Opik installation URL (make sure it ends with `/api/`) - + @@ -56,4 +51,6 @@ After setup, you can view your application traces by: 2. Finding and clicking the **OPIK** button in the top-right corner 3. Selecting **View** to open your Opik project dashboard -![How to view your Opik project](/img/tracing/dify_view_project.png) + + + diff --git a/apps/opik-documentation/documentation/docs/tracing/integrations/dspy.md b/apps/opik-documentation/documentation/fern/docs/tracing/integrations/dspy.mdx similarity index 67% rename from apps/opik-documentation/documentation/docs/tracing/integrations/dspy.md rename to apps/opik-documentation/documentation/fern/docs/tracing/integrations/dspy.mdx index 3e3a0d94de..300da04f46 100644 --- a/apps/opik-documentation/documentation/docs/tracing/integrations/dspy.md +++ b/apps/opik-documentation/documentation/fern/docs/tracing/integrations/dspy.mdx @@ -1,18 +1,25 @@ --- -sidebar_label: DSPy -description: Describes how to track DSPy calls using Opik +subtitle: Describes how to track DSPy calls using Opik --- -# DSPy - [DSPy](https://dspy.ai/) is the framework for programming—rather than prompting—language models. Opik integrates with DSPy to log traces for all DSPy calls.
- You can check out the Colab Notebook if you'd like to jump straight to the code: - - Open In Colab + + You can check out the Colab Notebook if you'd like to jump straight to the code: + + + Open In Colab
@@ -57,4 +64,6 @@ cot(question="What is the meaning of life?") Each run will now be logged to the Opik platform: -![DSPy](/img/cookbook/dspy_trace_cookbook.png) + + + diff --git a/apps/opik-documentation/documentation/docs/tracing/integrations/gemini.md b/apps/opik-documentation/documentation/fern/docs/tracing/integrations/gemini.mdx similarity index 71% rename from apps/opik-documentation/documentation/docs/tracing/integrations/gemini.md rename to apps/opik-documentation/documentation/fern/docs/tracing/integrations/gemini.mdx index c2f63b4a2c..25d9ddac15 100644 --- a/apps/opik-documentation/documentation/docs/tracing/integrations/gemini.md +++ b/apps/opik-documentation/documentation/fern/docs/tracing/integrations/gemini.mdx @@ -1,17 +1,23 @@ --- -sidebar_label: Gemini - Google AI Studio -description: Describes how to track Gemini LLM calls using Opik -pytest_codeblocks_skip: true +subtitle: Describes how to track Gemini LLM calls using Opik --- -# Gemini - Google AI Studio - [Gemini](https://aistudio.google.com/welcome) is a family of multimodal large language models developed by Google DeepMind.
- You can check out the Colab Notebook if you'd like to jump straight to the code: - - Open In Colab + + You can check out the Colab Notebook if you'd like to jump straight to the code: + + + Open In Colab
@@ -19,7 +25,7 @@ pytest_codeblocks_skip: true ### Configuring Opik -To start tracking your Gemini LLM calls, you can use our [LiteLLM integration](/tracing/integrations/litellm.md). You'll need to have both the `opik`, `litellm` and `google-generativeai` packages installed. You can install them using pip: +To start tracking your Gemini LLM calls, you can use our [LiteLLM integration](/tracing/integrations/litellm). You'll need to have both the `opik`, `litellm` and `google-generativeai` packages installed. You can install them using pip: ```bash pip install opik litellm google-generativeai @@ -31,11 +37,11 @@ In addition, you can configure Opik using the `opik configure` command which wil opik configure ``` -:::info + If you’re unable to use our LiteLLM integration with Gemini, please [open an issue](https://github.com/comet-ml/opik/issues/new/choose) -::: + ### Configuring Gemini @@ -45,7 +51,7 @@ In order to configure Gemini, you will need to have: Once you have these, you can set them as environment variables: -```python pytest_codeblocks_skip=true +```python {pytest_codeblocks_skip=true} import os os.environ["GEMINI_API_KEY"] = "" # Your Google AI Studio Gemini API Key @@ -70,11 +76,13 @@ response = litellm.completion( ) ``` -![Gemini Integration](/img/cookbook/gemini_trace_cookbook.png) + + + ## Logging LLM calls within a tracked function -If you are using LiteLLM within a function tracked with the [`@track`](/tracing/log_traces.mdx#using-function-decorators) decorator, you will need to pass the `current_span_data` as metadata to the `litellm.completion` call: +If you are using LiteLLM within a function tracked with the [`@track`](/tracing/log_traces#using-function-decorators) decorator, you will need to pass the `current_span_data` as metadata to the `litellm.completion` call: ```python from opik import track, opik_context @@ -119,4 +127,6 @@ def generate_opik_story(): generate_opik_story() ``` -![Gemini Integration](/img/cookbook/gemini_trace_decorator_cookbook.png) + + + diff --git a/apps/opik-documentation/documentation/docs/tracing/integrations/groq.md b/apps/opik-documentation/documentation/fern/docs/tracing/integrations/groq.mdx similarity index 72% rename from apps/opik-documentation/documentation/docs/tracing/integrations/groq.md rename to apps/opik-documentation/documentation/fern/docs/tracing/integrations/groq.mdx index 7e0d72735a..41e63f7266 100644 --- a/apps/opik-documentation/documentation/docs/tracing/integrations/groq.md +++ b/apps/opik-documentation/documentation/fern/docs/tracing/integrations/groq.mdx @@ -1,17 +1,23 @@ --- -sidebar_label: Groq -description: Describes how to track Groq LLM calls using Opik -pytest_codeblocks_skip: true +subtitle: Describes how to track Groq LLM calls using Opik --- -# Groq - [Groq](https://groq.com/) is Fast AI Inference.
- You can check out the Colab Notebook if you'd like to jump straight to the code: - - Open In Colab + + You can check out the Colab Notebook if you'd like to jump straight to the code: + + + Open In Colab
@@ -19,7 +25,7 @@ pytest_codeblocks_skip: true ### Configuring Opik -To start tracking your Groq LLM calls, you can use our [LiteLLM integration](/tracing/integrations/litellm.md). You'll need to have both the `opik` and `litellm` packages installed. You can install them using pip: +To start tracking your Groq LLM calls, you can use our [LiteLLM integration](/tracing/integrations/litellm). You'll need to have both the `opik` and `litellm` packages installed. You can install them using pip: ```bash pip install opik litellm @@ -31,11 +37,11 @@ In addition, you can configure Opik using the `opik configure` command which wil opik configure ``` -:::info + If you’re unable to use our LiteLLM integration with Groq, please [open an issue](https://github.com/comet-ml/opik/issues/new/choose) -::: + ### Configuring Groq @@ -70,11 +76,13 @@ response = litellm.completion( ) ``` -![Groq Integration](/img/cookbook/groq_trace_cookbook.png) + + + ## Logging LLM calls within a tracked function -If you are using LiteLLM within a function tracked with the [`@track`](/tracing/log_traces.mdx#using-function-decorators) decorator, you will need to pass the `current_span_data` as metadata to the `litellm.completion` call: +If you are using LiteLLM within a function tracked with the [`@track`](/tracing/log_traces#using-function-decorators) decorator, you will need to pass the `current_span_data` as metadata to the `litellm.completion` call: ```python from opik import track, opik_context @@ -119,4 +127,6 @@ def generate_opik_story(): generate_opik_story() ``` -![Groq Integration](/img/cookbook/groq_trace_decorator_cookbook.png) + + + diff --git a/apps/opik-documentation/documentation/docs/tracing/integrations/guardrails-ai.md b/apps/opik-documentation/documentation/fern/docs/tracing/integrations/guardrails-ai.mdx similarity index 79% rename from apps/opik-documentation/documentation/docs/tracing/integrations/guardrails-ai.md rename to apps/opik-documentation/documentation/fern/docs/tracing/integrations/guardrails-ai.mdx index 6b4e7f1ec6..bbb5277c55 100644 --- a/apps/opik-documentation/documentation/docs/tracing/integrations/guardrails-ai.md +++ b/apps/opik-documentation/documentation/fern/docs/tracing/integrations/guardrails-ai.mdx @@ -1,10 +1,7 @@ --- -sidebar_label: Guardrails AI -description: Cookbook that showcases Opik's integration with the Guardrails AI Python SDK +subtitle: Cookbook that showcases Opik's integration with the Guardrails AI Python SDK --- -# Guardrails AI - [Guardrails AI](https://github.com/guardrails-ai/guardrails) is a framework for validating the inputs and outputs For this guide we will use a simple example that logs guardrails validation steps as traces to Opik, providing them with the validation result tags. @@ -25,7 +22,7 @@ guardrails hub install hub://guardrails/politeness_check In order to log traces to Opik, you will need to call the track the Guard object with `track_guardrails` function. -```python pytest_codeblocks_skip=true +```python {pytest_codeblocks_skip=true} from guardrails import Guard, OnFailAction from guardrails.hub import PolitenessCheck @@ -50,4 +47,6 @@ Every validation will now be logged to Opik as a trace The trace will now be viewable in the Opik platform: -![Guardrails AI Integration](https://raw.githubusercontent.com/comet-ml/opik/main/apps/opik-documentation/documentation/static/img/cookbook/guardrails_ai_traces_cookbook.png) + + + diff --git a/apps/opik-documentation/documentation/docs/tracing/integrations/haystack.md b/apps/opik-documentation/documentation/fern/docs/tracing/integrations/haystack.mdx similarity index 93% rename from apps/opik-documentation/documentation/docs/tracing/integrations/haystack.md rename to apps/opik-documentation/documentation/fern/docs/tracing/integrations/haystack.mdx index e493233519..fc5432d428 100644 --- a/apps/opik-documentation/documentation/docs/tracing/integrations/haystack.md +++ b/apps/opik-documentation/documentation/fern/docs/tracing/integrations/haystack.mdx @@ -1,10 +1,7 @@ --- -sidebar_label: Haystack -description: Describes how to track Haystack pipeline runs using Opik +subtitle: Describes how to track Haystack pipeline runs using Opik --- -# Haystack - [Haystack](https://docs.haystack.deepset.ai/docs/intro) is an open-source framework for building production-ready LLM applications, retrieval-augmented generative pipelines and state-of-the-art search systems that work intelligently over large document collections. Opik integrates with Haystack to log traces for all Haystack pipelines. @@ -19,7 +16,7 @@ pip install opik haystack-ai In addition, you can configure Opik using the `opik configure` command which will prompt you for the correct local server address or if you are using the Cloud platform your API key: -```bash pytest_codeblocks_skip=true +```bash {pytest_codeblocks_skip=true} opik configure ``` @@ -73,13 +70,15 @@ print(response["llm"]["replies"][0]) Each pipeline run will now be logged to the Opik platform: -![Haystack](/img/cookbook/haystack_trace_cookbook.png) + + + -:::tip + In order to ensure the traces are correctly logged, make sure you set the environment variable `HAYSTACK_CONTENT_TRACING_ENABLED` to `true` before running the pipeline. -::: + ## Advanced usage @@ -105,17 +104,17 @@ pipe.add_component( tracer.actual_tracer.flush() ``` -:::warning + Disabling this feature may result in data loss if the program crashes before the data is sent to Opik. Make sure you will call the `flush()` method explicitly before the program exits. -::: + ### Updating logged traces The `OpikConnector` returns the logged trace ID in the pipeline run response. You can use this ID to update the trace with feedback scores or other metadata: -```python pytest_codeblocks_skip=true +```python {pytest_codeblocks_skip=true} import opik response = pipe.run( diff --git a/apps/opik-documentation/documentation/docs/tracing/integrations/langchain.md b/apps/opik-documentation/documentation/fern/docs/tracing/integrations/langchain.mdx similarity index 81% rename from apps/opik-documentation/documentation/docs/tracing/integrations/langchain.md rename to apps/opik-documentation/documentation/fern/docs/tracing/integrations/langchain.mdx index e7d9265f58..d2558efb6a 100644 --- a/apps/opik-documentation/documentation/docs/tracing/integrations/langchain.md +++ b/apps/opik-documentation/documentation/fern/docs/tracing/integrations/langchain.mdx @@ -1,16 +1,23 @@ --- -sidebar_label: LangChain -description: Describes how to use Opik with LangChain +subtitle: Describes how to use Opik with LangChain --- -# LangChain - Opik provides seamless integration with LangChain, allowing you to easily log and trace your LangChain-based applications. By using the `OpikTracer` callback, you can automatically capture detailed information about your LangChain runs, including inputs, outputs, and metadata for each step in your chain.
- You can check out the Colab Notebook if you'd like to jump straight to the code: - - Open In Colab + + You can check out the Colab Notebook if you'd like to jump straight to the code: + + + Open In Colab
@@ -138,3 +145,16 @@ from opik.integrations.langchain import OpikTracer opik_tracer = OpikTracer() opik_tracer.flush() ``` + +## Important notes +1. If you are using asynchronous streaming mode (calling `.astream()` method), the `input` field in the trace UI will be empty due to a Langchain limitation for this mode. +However, you can find the input data inside the nested spans of this chain. + +2. if you are planning to use streaming with LLM-calls, and you want to calculate LLM-call tokens/cost, you need explicitly set argument `stream_usage` to `True`, +```python +from langchain_openai import ChatOpenAI +llm = ChatOpenAI( + temperature=0, + stream_usage=True, +) +``` diff --git a/apps/opik-documentation/documentation/docs/tracing/integrations/langgraph.md b/apps/opik-documentation/documentation/fern/docs/tracing/integrations/langgraph.mdx similarity index 84% rename from apps/opik-documentation/documentation/docs/tracing/integrations/langgraph.md rename to apps/opik-documentation/documentation/fern/docs/tracing/integrations/langgraph.mdx index 797a2c6540..46eb21af20 100644 --- a/apps/opik-documentation/documentation/docs/tracing/integrations/langgraph.md +++ b/apps/opik-documentation/documentation/fern/docs/tracing/integrations/langgraph.mdx @@ -1,16 +1,23 @@ --- -sidebar_label: LangGraph -description: Describes how to track LangGraph Agent executions using Opik +subtitle: Describes how to track LangGraph Agent executions using Opik --- -# LangGraph - Opik provides a seamless integration with LangGraph, allowing you to easily log and trace your LangGraph-based applications. By using the `OpikTracer` callback, you can automatically capture detailed information about your LangGraph graph executions during both development and production.
- You can check out the Colab Notebook if you'd like to jump straight to the code: - - Open In Colab + + You can check out the Colab Notebook if you'd like to jump straight to the code: + + + Open In Colab
@@ -69,7 +76,9 @@ result = app.invoke({"messages": [HumanMessage(content = "How to use LangGraph ? Once the OpikTracer is configured, you will start to see the traces in the Opik UI: -![langgraph](/img/cookbook/langgraph_cookbook.png) + + + ## Updating logged traces diff --git a/apps/opik-documentation/documentation/docs/tracing/integrations/litellm.md b/apps/opik-documentation/documentation/fern/docs/tracing/integrations/litellm.mdx similarity index 90% rename from apps/opik-documentation/documentation/docs/tracing/integrations/litellm.md rename to apps/opik-documentation/documentation/fern/docs/tracing/integrations/litellm.mdx index 283b04a109..01e8575e59 100644 --- a/apps/opik-documentation/documentation/docs/tracing/integrations/litellm.md +++ b/apps/opik-documentation/documentation/fern/docs/tracing/integrations/litellm.mdx @@ -1,10 +1,7 @@ --- -sidebar_label: LiteLLM -description: Describes how to track LiteLLM LLM calls using Opik +subtitle: Describes how to track LiteLLM LLM calls using Opik --- -# LiteLLM - [LiteLLM](https://github.com/BerriAI/litellm) allows you to call all LLM APIs using the OpenAI format [Bedrock, Huggingface, VertexAI, TogetherAI, Azure, OpenAI, Groq etc.]. There are two main ways to use LiteLLM: 1. Using the [LiteLLM Python SDK](https://docs.litellm.ai/docs/#litellm-python-sdk) @@ -45,11 +42,13 @@ response = litellm.completion( ) ``` -![LiteLLM Integration](/img/cookbook/litellm_cookbook.png) + + + ### Logging LLM calls within a tracked function -If you are using LiteLLM within a function tracked with the [`@track`](/tracing/log_traces.mdx#using-function-decorators) decorator, you will need to pass the `current_span_data` as metadata to the `litellm.completion` call: +If you are using LiteLLM within a function tracked with the [`@track`](/tracing/log_traces#using-function-decorators) decorator, you will need to pass the `current_span_data` as metadata to the `litellm.completion` call: ```python from opik import track diff --git a/apps/opik-documentation/documentation/docs/tracing/integrations/llama_index.md b/apps/opik-documentation/documentation/fern/docs/tracing/integrations/llama_index.mdx similarity index 83% rename from apps/opik-documentation/documentation/docs/tracing/integrations/llama_index.md rename to apps/opik-documentation/documentation/fern/docs/tracing/integrations/llama_index.mdx index 509b40d0e4..a2bdc8a8e3 100644 --- a/apps/opik-documentation/documentation/docs/tracing/integrations/llama_index.md +++ b/apps/opik-documentation/documentation/fern/docs/tracing/integrations/llama_index.mdx @@ -1,10 +1,7 @@ --- -sidebar_label: LlamaIndex -description: Describes how to track LlamaIndex pipelines using Opik +subtitle: Describes how to track LlamaIndex pipelines using Opik --- -# LlamaIndex - [LlamaIndex](https://github.com/run-llama/llama_index) is a flexible data framework for building LLM applications: LlamaIndex is a "data framework" to help you build LLM apps. It provides the following tools: @@ -15,9 +12,19 @@ description: Describes how to track LlamaIndex pipelines using Opik - Allows easy integrations with your outer application framework (e.g. with LangChain, Flask, Docker, ChatGPT, anything else).
- You can check out the Colab Notebook if you'd like to jump straight to the code: - - Open In Colab + + You can check out the Colab Notebook if you'd like to jump straight to the code: + + + Open In Colab
@@ -108,4 +115,6 @@ print(response) Given that the integration with Opik has been set up, all the traces are logged to the Opik platform: -![llama_index](/img/tracing/llama_index_integration.png) + + + diff --git a/apps/opik-documentation/documentation/docs/tracing/integrations/ollama.md b/apps/opik-documentation/documentation/fern/docs/tracing/integrations/ollama.mdx similarity index 85% rename from apps/opik-documentation/documentation/docs/tracing/integrations/ollama.md rename to apps/opik-documentation/documentation/fern/docs/tracing/integrations/ollama.mdx index 3c4b6c1418..02d2d1ae4a 100644 --- a/apps/opik-documentation/documentation/docs/tracing/integrations/ollama.md +++ b/apps/opik-documentation/documentation/fern/docs/tracing/integrations/ollama.mdx @@ -1,19 +1,25 @@ --- -sidebar_label: Ollama -description: Describes how to track Ollama LLM calls using Opik -pytest_codeblocks_skip: true +subtitle: Describes how to track Ollama LLM calls using Opik --- -# Ollama - [Ollama](https://ollama.com/) allows users to run, interact with, and deploy AI models locally on their machines without the need for complex infrastructure or cloud dependencies. There are multiple ways to interact with Ollama from Python including but not limited to the [ollama python package](https://pypi.org/project/ollama/), [LangChain](https://python.langchain.com/docs/integrations/providers/ollama/) or by using the [OpenAI library](https://github.com/ollama/ollama/blob/main/docs/openai.md). We will cover how to trace your LLM calls for each of these methods.
- You can check out the Colab Notebook if you'd like to jump straight to the code: - - Open In Colab + + You can check out the Colab Notebook if you'd like to jump straight to the code: + + + Open In Colab
@@ -35,9 +41,10 @@ pip install --upgrade --quiet opik opik configure ``` -:::tip -Opik is fully open-source and can be run locally or through the Opik Cloud platform. You can learn more about hosting Opik on your own infrastructure in the [self-hosting guide](/docs/self-host/overview.md). -::: + + Opik is fully open-source and can be run locally or through the Opik Cloud platform. You can learn more about hosting + Opik on your own infrastructure in the [self-hosting guide](/self-host/overview). + ## Tracking Ollama calls made with Ollama Python Package @@ -159,4 +166,6 @@ ai_msg You can now go to the Opik app to see the trace: -![ollama](/img/cookbook/ollama_cookbook.png) + + + diff --git a/apps/opik-documentation/documentation/docs/tracing/integrations/openai.md b/apps/opik-documentation/documentation/fern/docs/tracing/integrations/openai.mdx similarity index 53% rename from apps/opik-documentation/documentation/docs/tracing/integrations/openai.md rename to apps/opik-documentation/documentation/fern/docs/tracing/integrations/openai.mdx index b8690f2b18..9720c86436 100644 --- a/apps/opik-documentation/documentation/docs/tracing/integrations/openai.md +++ b/apps/opik-documentation/documentation/fern/docs/tracing/integrations/openai.mdx @@ -1,16 +1,23 @@ --- -sidebar_label: OpenAI -description: Describes how to track OpenAI LLM calls using Opik +subtitle: Describes how to track OpenAI LLM calls using Opik --- -# OpenAI - This guide explains how to integrate Opik with the OpenAI Python SDK. By using the `track_openai` method provided by opik, you can easily track and evaluate your OpenAI API calls within your Opik projects as Opik will automatically log the input prompt, model used, token usage, and response generated.
- You can check out the Colab Notebook if you'd like to jump straight to the code: - - Open In Colab + + You can check out the Colab Notebook if you'd like to jump straight to the code: + + + Open In Colab
@@ -56,7 +63,33 @@ print(response.choices[0].message.content) The `track_openai` will automatically track and log the API call, including the input prompt, model used, and response generated. You can view these logs in your Opik project dashboard. -By following these steps, you can seamlessly integrate Opik with the OpenAI Python SDK and gain valuable insights into your model's performance and usage. +## Using Azure OpenAI + +The OpenAI integration also supports Azure OpenAI Services. To use Azure OpenAI, initialize your client with Azure configuration and use it with `track_openai` just like the standard OpenAI client: + +```python +from opik.integrations.openai import track_openai +from openai import AzureOpenAI + +# gets the API Key from environment variable AZURE_OPENAI_API_KEY +azure_client = AzureOpenAI( + # https://learn.microsoft.com/azure/ai-services/openai/reference#rest-api-versioning + api_version="2023-07-01-preview", + # https://learn.microsoft.com/azure/cognitive-services/openai/how-to/create-resource?pivots=web-portal#create-a-resource + azure_endpoint="https://example-endpoint.openai.azure.com", +) +azure_client = track_openai(azure_client) + +completion = azure_client.chat.completions.create( + model="deployment-name", # e.g. gpt-35-instant + messages=[ + { + "role": "user", + "content": "How do I output all files in a directory using Python?", + }, + ], +) +``` ## Supported OpenAI methods diff --git a/apps/opik-documentation/documentation/fern/docs/tracing/integrations/openrouter.mdx b/apps/opik-documentation/documentation/fern/docs/tracing/integrations/openrouter.mdx new file mode 100644 index 0000000000..6e3c3258e0 --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs/tracing/integrations/openrouter.mdx @@ -0,0 +1,73 @@ +--- +subtitle: Describes how to track OpenRouter LLM calls using Opik +--- + +This guide explains how to integrate Opik with OpenRouter using the OpenAI SDK. OpenRouter provides a unified API for accessing hundreds of AI models through a single OpenAI-compatible interface. + +## Getting started + +First, ensure you have both `opik` and `openai` packages installed: + +```bash +pip install opik openai +``` + +You'll also need an OpenRouter API key which you can get from [OpenRouter](https://openrouter.ai/). + +## Tracking OpenRouter API calls + +```python +from opik.integrations.openai import track_openai +from openai import OpenAI + +# Initialize the OpenAI client with OpenRouter base URL +client = OpenAI( + base_url="https://openrouter.ai/api/v1", + api_key="YOUR_OPENROUTER_API_KEY" +) +client = track_openai(client) + +# Optional headers for OpenRouter leaderboard +headers = { + "HTTP-Referer": "YOUR_SITE_URL", # Optional. Site URL for rankings + "X-Title": "YOUR_SITE_NAME" # Optional. Site title for rankings +} + +response = client.chat.completions.create( + model="openai/gpt-4", # You can use any model available on OpenRouter + extra_headers=headers, + messages=[ + {"role": "user", "content": "Hello, world!"} + ], + temperature=0.7, + max_tokens=100 +) + +print(response.choices[0].message.content) +``` + +## Available Models + +OpenRouter provides access to a wide variety of models, including many open source models from different providers. + +- [OpenAI models](https://openrouter.ai/openai) (GPT-4o, o1, o3-mini) +- [Anthropic models](https://openrouter.ai/anthropic) (Opus, Sonnet, Haiku) +- [Google models](https://openrouter.ai/google) (Gemini Pro, Flash, Flash Thinking) +- And many open source models + +You can find the complete list of available models in the [OpenRouter documentation](https://openrouter.ai/docs/overview/models). + +## Supported Methods + +OpenRouter supports the following methods: + +### Chat Completions +- `client.chat.completions.create()`: Works with all models +- Provides standard chat completion functionality +- Compatible with the OpenAI SDK interface + +### Structured Outputs +- `client.beta.chat.completions.parse()`: Only compatible with OpenAI models +- For non-OpenAI models, see OpenRouter's [Structured Outputs documentation](https://openrouter.ai/docs/features/structured-outputs) + +For detailed information about available methods, parameters, and best practices, refer to the [OpenRouter API documentation](https://openrouter.ai/docs). \ No newline at end of file diff --git a/apps/opik-documentation/documentation/fern/docs/tracing/integrations/overview.mdx b/apps/opik-documentation/documentation/fern/docs/tracing/integrations/overview.mdx new file mode 100644 index 0000000000..e1013e12bf --- /dev/null +++ b/apps/opik-documentation/documentation/fern/docs/tracing/integrations/overview.mdx @@ -0,0 +1,31 @@ +--- +subtitle: >- + Describes all the integrations provided by Opik and what each framework can be + used for +--- + +Opik aims to make it as easy as possible to log, view and evaluate your LLM traces. We do this by providing a set of integrations: + +| Integration | Description | Documentation | Try in Colab | +| ----------- | ---------------------------------------------------------------------------- | ---------------------------------------------------- | ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | +| OpenAI | Log traces for all OpenAI LLM calls | [Documentation](/tracing/integrations/openai) | [![Open Quickstart In Colab](https://colab.research.google.com/assets/colab-badge.svg)](https://colab.research.google.com/github/comet-ml/opik/blob/master/apps/opik-documentation/documentation/docs/cookbook/openai.ipynb) | +| OpenRouter | Log traces for all OpenRouter LLM calls using OpenAI SDK | [Documentation](/tracing/integrations/openrouter) | | +| LiteLLM | Call any LLM model using the OpenAI format | [Documentation](/tracing/integrations/litellm) | [![Open Quickstart In Colab](https://colab.research.google.com/assets/colab-badge.svg)](https://colab.research.google.com/github/comet-ml/opik/blob/master/apps/opik-documentation/documentation/docs/cookbook/litellm.ipynb) | +| LangChain | Log traces for all LangChain LLM calls | [Documentation](/tracing/integrations/langchain) | [![Open Quickstart In Colab](https://colab.research.google.com/assets/colab-badge.svg)](https://colab.research.google.com/github/comet-ml/opik/blob/master/apps/opik-documentation/documentation/docs/cookbook/langchain.ipynb) | +| Haystack | Log traces for all Haystack pipelines | [Documentation](/tracing/integrations/haystack) | [![Open Quickstart In Colab](https://colab.research.google.com/assets/colab-badge.svg)](https://colab.research.google.com/github/comet-ml/opik/blob/master/apps/opik-documentation/documentation/docs/cookbook/haystack.ipynb) | +| aisuite | Log traces for all aisuite LLM calls | [Documentation](/tracing/integrations/aisuite) | [![Open Quickstart In Colab](https://colab.research.google.com/assets/colab-badge.svg)](https://colab.research.google.com/github/comet-ml/opik/blob/master/apps/opik-documentation/documentation/docs/cookbook/aisuite.ipynb) | +| Anthropic | Log traces for all Anthropic LLM calls | [Documentation](/tracing/integrations/anthropic) | [![Open Quickstart In Colab](https://colab.research.google.com/assets/colab-badge.svg)](https://colab.research.google.com/github/comet-ml/opik/blob/master/apps/opik-documentation/documentation/docs/cookbook/anthropic.ipynb) | +| Bedrock | Log traces for all AWS Bedrock LLM calls | [Documentation](/tracing/integrations/bedrock) | [![Open Quickstart In Colab](https://colab.research.google.com/assets/colab-badge.svg)](https://colab.research.google.com/github/comet-ml/opik/blob/master/apps/opik-documentation/documentation/docs/cookbook/bedrock.ipynb) | +| CrewAI | Log traces for all CrewAI LLM calls | [Documentation](/tracing/integrations/crewai) | [![Open Quickstart In Colab](https://colab.research.google.com/assets/colab-badge.svg)](https://colab.research.google.com/github/comet-ml/opik/blob/master/apps/opik-documentation/documentation/docs/cookbook/crewai.ipynb) | +| DeepSeek | Log traces for all LLM calls made with DeepSeek | [Documentation](/tracing/integrations/deepseek) | | +| Dify | Log traces and LLM calls for your Dify Apps | [Documentation](/tracing/integrations/dify) | | +| DSPy | Log traces for all DSPy runs | [Documentation](/tracing/integrations/dspy) | [![Open Quickstart In Colab](https://colab.research.google.com/assets/colab-badge.svg)](https://colab.research.google.com/github/comet-ml/opik/blob/master/apps/opik-documentation/documentation/docs/cookbook/dspy.ipynb) | +| Guardrails | Log traces for all Guardrails validations | [Documentation](/tracing/integrations/guardrails-ai) | [![Open Quickstart In Colab](https://colab.research.google.com/assets/colab-badge.svg)](https://colab.research.google.com/github/comet-ml/opik/blob/master/apps/opik-documentation/documentation/docs/cookbook/guardrails-ai.ipynb) | +| LangGraph | Log traces for all LangGraph executions | [Documentation](/tracing/integrations/langgraph) | [![Open Quickstart In Colab](https://colab.research.google.com/assets/colab-badge.svg)](https://colab.research.google.com/github/comet-ml/opik/blob/master/apps/opik-documentation/documentation/docs/cookbook/langgraph.ipynb) | +| LlamaIndex | Log traces for all LlamaIndex LLM calls | [Documentation](/tracing/integrations/llama_index) | [![Open Quickstart In Colab](https://colab.research.google.com/assets/colab-badge.svg)](https://colab.research.google.com/github/comet-ml/opik/blob/master/apps/opik-documentation/documentation/docs/cookbook/llama-index.ipynb) | +| Ollama | Log traces for all Ollama LLM calls | [Documentation](/tracing/integrations/ollama) | [![Open Quickstart In Colab](https://colab.research.google.com/assets/colab-badge.svg)](https://colab.research.google.com/github/comet-ml/opik/blob/master/apps/opik-documentation/documentation/docs/cookbook/ollama.ipynb) | +| Predibase | Fine-tune and serve open-source LLMs | [Documentation](/tracing/integrations/predibase) | [![Open Quickstart In Colab](https://colab.research.google.com/assets/colab-badge.svg)](https://colab.research.google.com/github/comet-ml/opik/blob/master/apps/opik-documentation/documentation/docs/cookbook/predibase.ipynb) | +| Ragas | Evaluation framework for your Retrieval Augmented Generation (RAG) pipelines | [Documentation](/tracing/integrations/ragas) | [![Open Quickstart In Colab](https://colab.research.google.com/assets/colab-badge.svg)](https://colab.research.google.com/github/comet-ml/opik/blob/master/apps/opik-documentation/documentation/docs/cookbook/ragas.ipynb) | +| watsonx | Log traces for all watsonx LLM calls | [Documentation](/tracing/integrations/watsonx) | [![Open Quickstart In Colab](https://colab.research.google.com/assets/colab-badge.svg)](https://colab.research.google.com/github/comet-ml/opik/blob/master/apps/opik-documentation/documentation/docs/cookbook/watsonx.ipynb) | + +If you would like to see more integrations, please open an issue on our [GitHub repository](https://github.com/comet-ml/opik/issues/new/choose). diff --git a/apps/opik-documentation/documentation/docs/tracing/integrations/predibase.md b/apps/opik-documentation/documentation/fern/docs/tracing/integrations/predibase.mdx similarity index 73% rename from apps/opik-documentation/documentation/docs/tracing/integrations/predibase.md rename to apps/opik-documentation/documentation/fern/docs/tracing/integrations/predibase.mdx index 83e877d131..1893e5a6fd 100644 --- a/apps/opik-documentation/documentation/docs/tracing/integrations/predibase.md +++ b/apps/opik-documentation/documentation/fern/docs/tracing/integrations/predibase.mdx @@ -1,17 +1,23 @@ --- -sidebar_label: Predibase -description: Describes how to track Predibase LLM calls using Opik -pytest_codeblocks_skip: true +subtitle: Describes how to track Predibase LLM calls using Opik --- -# Using Opik with Predibase - Predibase is a platform for fine-tuning and serving open-source Large Language Models (LLMs). It's built on top of open-source [LoRAX](https://loraexchange.ai/).
- You can check out the Colab Notebook if you'd like to jump straight to the code: - - Open In Colab + + You can check out the Colab Notebook if you'd like to jump straight to the code: + + + Open In Colab
@@ -65,13 +71,16 @@ response = model.invoke( print(response) ``` -:::tip -You can learn more about the Opik integration with LangChain in our [LangChain integration guide](/docs/tracing/integrations/langchain.md) or in the [Predibase cookbook](/docs/cookbook/predibase.md). -::: + + You can learn more about the Opik integration with LangChain in our [LangChain integration + guide](/tracing/integrations/langchain) or in the [Predibase cookbook](/cookbook/predibase). + The trace will now be available in the Opik UI for further analysis. -![predibase](/img/tracing/predibase_opik_trace.png) + + + ## Tracking your fine-tuning training runs diff --git a/apps/opik-documentation/documentation/docs/tracing/integrations/ragas.md b/apps/opik-documentation/documentation/fern/docs/tracing/integrations/ragas.mdx similarity index 91% rename from apps/opik-documentation/documentation/docs/tracing/integrations/ragas.md rename to apps/opik-documentation/documentation/fern/docs/tracing/integrations/ragas.mdx index 36702901cd..bfc45dccc5 100644 --- a/apps/opik-documentation/documentation/docs/tracing/integrations/ragas.md +++ b/apps/opik-documentation/documentation/fern/docs/tracing/integrations/ragas.mdx @@ -1,11 +1,7 @@ --- -sidebar_label: Ragas -description: Describes how to log Ragas scores to the Opik platform -pytest_codeblocks_skip: true +subtitle: Describes how to log Ragas scores to the Opik platform --- -# Ragas - The Opik SDK provides a simple way to integrate with Ragas, a framework for evaluating RAG systems. There are two main ways to use Ragas with Opik: @@ -14,9 +10,19 @@ There are two main ways to use Ragas with Opik: 2. Using Ragas to evaluate a RAG pipeline.
- You can check out the Colab Notebook if you'd like to jump straight to the code: - - Open In Colab + + You can check out the Colab Notebook if you'd like to jump straight to the code: + + + Open In Colab
@@ -127,7 +133,9 @@ print(rag_pipeline("What is the capital of France?")) In the Opik UI, you will be able to see the full trace including the score calculation: -![Ragas chain](/img/tracing/ragas_opik_trace.png) + + + ## Using Ragas metrics to evaluate a RAG pipeline @@ -191,7 +199,7 @@ class AnswerRelevancyWrapper(base_metric.BaseMetric): answer_relevancy = AnswerRelevancyWrapper(ragas_answer_relevancy) ``` -:::tip + If you are running within a Jupyter notebook, you will need to add the following line to the top of your notebook: @@ -200,7 +208,7 @@ import nest_asyncio nest_asyncio.apply() ``` -::: + ### 3. Use the scoring metric wrapper within the Opik evaluation framework diff --git a/apps/opik-documentation/documentation/docs/tracing/integrations/watsonx.md b/apps/opik-documentation/documentation/fern/docs/tracing/integrations/watsonx.mdx similarity index 76% rename from apps/opik-documentation/documentation/docs/tracing/integrations/watsonx.md rename to apps/opik-documentation/documentation/fern/docs/tracing/integrations/watsonx.mdx index c4c9ea9587..71dda3fdff 100644 --- a/apps/opik-documentation/documentation/docs/tracing/integrations/watsonx.md +++ b/apps/opik-documentation/documentation/fern/docs/tracing/integrations/watsonx.mdx @@ -1,17 +1,23 @@ --- -sidebar_label: watsonx -description: Describes how to track watsonx LLM calls using Opik -pytest_codeblocks_skip: true +subtitle: Describes how to track watsonx LLM calls using Opik --- -# watsonx - [watsonx](https://www.ibm.com/products/watsonx-ai) is a next generation enterprise studio for AI builders to train, validate, tune and deploy AI models.
- You can check out the Colab Notebook if you'd like to jump straight to the code: - - Open In Colab + + You can check out the Colab Notebook if you'd like to jump straight to the code: + + + Open In Colab
@@ -19,7 +25,7 @@ pytest_codeblocks_skip: true ### Configuring Opik -To start tracking your watsonx LLM calls, you can use our [LiteLLM integration](/tracing/integrations/litellm.md). You'll need to have both the `opik` and `litellm` packages installed. You can install them using pip: +To start tracking your watsonx LLM calls, you can use our [LiteLLM integration](/tracing/integrations/litellm). You'll need to have both the `opik` and `litellm` packages installed. You can install them using pip: ```bash pip install opik litellm @@ -31,11 +37,11 @@ In addition, you can configure Opik using the `opik configure` command which wil opik configure ``` -:::info + If you’re unable to use our LiteLLM integration with watsonx, please [open an issue](https://github.com/comet-ml/opik/issues/new/choose) -::: + ### Configuring watsonx @@ -78,11 +84,13 @@ response = litellm.completion( ) ``` -![watsonx Integration](/img/cookbook/watsonx_trace_cookbook.png) + + + ## Logging LLM calls within a tracked function -If you are using LiteLLM within a function tracked with the [`@track`](/tracing/log_traces.mdx#using-function-decorators) decorator, you will need to pass the `current_span_data` as metadata to the `litellm.completion` call: +If you are using LiteLLM within a function tracked with the [`@track`](/tracing/log_traces#using-function-decorators) decorator, you will need to pass the `current_span_data` as metadata to the `litellm.completion` call: ```python @track @@ -124,4 +132,6 @@ def generate_opik_story(): generate_opik_story() ``` -![watsonx Integration](/img/cookbook/watsonx_trace_decorator_cookbook.png) + + + diff --git a/apps/opik-documentation/documentation/docs/tracing/log_agents.mdx b/apps/opik-documentation/documentation/fern/docs/tracing/log_agents.mdx similarity index 65% rename from apps/opik-documentation/documentation/docs/tracing/log_agents.mdx rename to apps/opik-documentation/documentation/fern/docs/tracing/log_agents.mdx index 37aad33cb0..59df09f48a 100644 --- a/apps/opik-documentation/documentation/docs/tracing/log_agents.mdx +++ b/apps/opik-documentation/documentation/fern/docs/tracing/log_agents.mdx @@ -1,34 +1,27 @@ --- -sidebar_label: Track Agents -description: Describes how to track agents using Opik -toc_min_heading_level: 2 -toc_max_heading_level: 4 -pytest_codeblocks_skip: true +subtitle: Describes how to track agents using Opik --- -import Tabs from "@theme/Tabs"; -import TabItem from "@theme/TabItem"; - -# Track Agents - When working with agents, it can become challenging to track the flow of the agent and its interactions with the environment. Opik provides a way to track both the agent definition and it's flow. -Opik includes an integration with many popular Agent frameworks ([LangGrah](/tracing/integrations/langgraph.md), [LLamaIndex](/tracing/integrations/llama_index.md)) +Opik includes an integration with many popular Agent frameworks ([LangGrah](/tracing/integrations/langgraph), [LLamaIndex](/tracing/integrations/llama_index)) and can also be used to log agents manually using the `@track` decorator. -:::tip -We are working on improving Opik's support for agent workflows, if you have any ideas or suggestions for the roadmap, you can create a [new Feature Request issue](https://github.com/comet-ml/opik/issues/new/choose) -in the Opik Github repo or book a call with the Opik team: [Talk to the Opik team](https://calendly.com/jacques-comet/opik-agent-support). -::: + + We are working on improving Opik's support for agent workflows, if you have any ideas or suggestions for the roadmap, + you can create a [new Feature Request issue](https://github.com/comet-ml/opik/issues/new/choose) in the Opik Github + repo or book a call with the Opik team: [Talk to the Opik + team](https://calendly.com/jacques-comet/opik-agent-support). + ## Track agent execution -You can track the agent execution by using either one of [Opik's integrations](/tracing/integrations/overview.md) or the `@track` decorator: +You can track the agent execution by using either one of [Opik's integrations](/tracing/integrations/overview) or the `@track` decorator: - - You can log the agent execution by using the [OpikTracer](/tracing/integrations/langgraph.md) callback: + + You can log the agent execution by using the [OpikTracer](/tracing/integrations/langgraph) callback: ```python from opik.integrations.langchain import OpikTracer @@ -50,9 +43,9 @@ You can track the agent execution by using either one of [Opik's integrations](/ ``` The `OpikTracer` can be added - - - To log a Haystack pipeline run, you can use the [`OpikConnector`](/tracing/integrations/haystack.md). This connector will log the pipeline run to the Opik platform and add a `tracer` key to the pipeline run response with the trace ID: + + + To log a Haystack pipeline run, you can use the [`OpikConnector`](/tracing/integrations/haystack). This connector will log the pipeline run to the Opik platform and add a `tracer` key to the pipeline run response with the trace ID: ```python import os @@ -82,9 +75,9 @@ You can track the agent execution by using either one of [Opik's integrations](/ print(response) ``` - - - Opik has a built-in integration with [LLamaIndex](/tracing/integrations/llama_index.md) that makes it easy to track the agent execution: + + + Opik has a built-in integration with [LLamaIndex](/tracing/integrations/llama_index) that makes it easy to track the agent execution: ```python from llama_index.core import global_handler, set_global_handler @@ -94,8 +87,8 @@ You can track the agent execution by using either one of [Opik's integrations](/ opik_callback_handler = global_handler ``` - - + + If you are not using any of the above integrations, you can track the agent execution manually using the `@track` decorator: ```python @@ -116,18 +109,20 @@ You can track the agent execution by using either one of [Opik's integrations](/ agent_graph("What is Opik ?") ``` - + Once the agent is executed, you will be able to view the execution flow in the Opik dashboard. In the trace sidebar, you will be able to view each step that has been executed in chronological order: -![Agent execution flow](/img/tracing/agent_execution_flow.png) + + + ## Track the agent definition -If you are using out [LangGraph](/tracing/integrations/langgraph.md) integration, you can also track the agent definition by passing in the `graph` argument to the `OpikTracer` callback: +If you are using out [LangGraph](/tracing/integrations/langgraph) integration, you can also track the agent definition by passing in the `graph` argument to the `OpikTracer` callback: ```python from opik.integrations.langchain import OpikTracer @@ -139,4 +134,6 @@ opik_tracer = OpikTracer(graph=app.get_graph(xray=True)) This allows you to view the agent definition in the Opik dashboard: -![Agent definition in the Opik dashboard](/img/tracing/agent_definition.png) + + + diff --git a/apps/opik-documentation/documentation/docs/tracing/log_distributed_traces.md b/apps/opik-documentation/documentation/fern/docs/tracing/log_distributed_traces.mdx similarity index 82% rename from apps/opik-documentation/documentation/docs/tracing/log_distributed_traces.md rename to apps/opik-documentation/documentation/fern/docs/tracing/log_distributed_traces.mdx index 93128a3067..5c28de0d6a 100644 --- a/apps/opik-documentation/documentation/docs/tracing/log_distributed_traces.md +++ b/apps/opik-documentation/documentation/fern/docs/tracing/log_distributed_traces.mdx @@ -1,11 +1,7 @@ --- -sidebar_label: Log Distributed Traces -description: Describes how to log distributed traces to the Opik platform -pytest_codeblocks_skip: true +subtitle: Describes how to log distributed traces to the Opik platform --- -# Log Distributed Traces - When working with complex LLM applications, it is common to need to track a traces across multiple services. Opik supports distributed tracing out of the box when integrating using function decorators using a mechanism that is similar to how OpenTelemetry implements distributed tracing. For the purposes of this guide, we will assume that you have a simple LLM application that is made up of two services: a client and a server. We will assume that the client will create the trace and span, while the server will add a nested span. In order to do this, the `trace_id` and `span_id` will be passed in the headers of the request from the client to the server. @@ -47,6 +43,7 @@ def generate_llm_response(request: Request) -> str: return my_llm_application(opik_distributed_trace_headers=request.headers) ``` -:::note -The `opik_distributed_trace_headers` parameter is added by the `track` decorato to each function that is decorated and is a dictionary with the keys `opik_trace_id` and `opik_parent_span_id`. -::: + + The `opik_distributed_trace_headers` parameter is added by the `track` decorator to each function that is decorated + and is a dictionary with the keys `opik_trace_id` and `opik_parent_span_id`. + diff --git a/apps/opik-documentation/documentation/docs/tracing/log_multimodal_traces.md b/apps/opik-documentation/documentation/fern/docs/tracing/log_multimodal_traces.mdx similarity index 79% rename from apps/opik-documentation/documentation/docs/tracing/log_multimodal_traces.md rename to apps/opik-documentation/documentation/fern/docs/tracing/log_multimodal_traces.mdx index 03ba680722..b4398f6ee2 100644 --- a/apps/opik-documentation/documentation/docs/tracing/log_multimodal_traces.md +++ b/apps/opik-documentation/documentation/fern/docs/tracing/log_multimodal_traces.mdx @@ -1,15 +1,12 @@ --- -sidebar_label: Log Multimodal Traces -description: Describes how to log and view images in traces to the Opik platform -toc_min_heading_level: 2 -toc_max_heading_level: 4 +subtitle: Describes how to log and view images in traces to the Opik platform --- -# Log Multimodal Traces - Opik supports multimodal traces allowing you to track not just the text input and output of your LLM, but also images. -![Traces with OpenAI](/img/tracing/image_trace.png) + + + ## Log a trace with an image using OpenAI SDK @@ -56,6 +53,7 @@ If you are not using the OpenAI SDK, you can still log images to the platform. T } ``` -:::tip -Let's us know on [Github](https://github.com/comet-ml/opik/issues/new/choose) if you would like to us to support additional image formats or models. -::: + + Let's us know on [Github](https://github.com/comet-ml/opik/issues/new/choose) if you would like to us to support + additional image formats or models. + diff --git a/apps/opik-documentation/documentation/docs/tracing/log_traces.mdx b/apps/opik-documentation/documentation/fern/docs/tracing/log_traces.mdx similarity index 86% rename from apps/opik-documentation/documentation/docs/tracing/log_traces.mdx rename to apps/opik-documentation/documentation/fern/docs/tracing/log_traces.mdx index 1d2c079e80..1ff88672be 100644 --- a/apps/opik-documentation/documentation/docs/tracing/log_traces.mdx +++ b/apps/opik-documentation/documentation/fern/docs/tracing/log_traces.mdx @@ -1,29 +1,26 @@ --- -sidebar_label: Log Traces -description: Describes how to log LLM calls to the Opik platform using function decorators, integrations or the low level client. -toc_min_heading_level: 2 -toc_max_heading_level: 4 +subtitle: >- + Describes how to log LLM calls to the Opik platform using function decorators, + integrations or the low level client. --- -import Tabs from "@theme/Tabs"; -import TabItem from "@theme/TabItem"; - -# Log Traces - -:::tip -If you are just getting started with Opik, we recommend first checking out the [Quickstart](/quickstart.mdx) guide that will walk you through the process of logging your first LLM call. -::: + + If you are just getting started with Opik, we recommend first checking out the [Quickstart](/quickstart) guide that + will walk you through the process of logging your first LLM call. + LLM applications are complex systems that do more than just call an LLM API, they will often involve retrieval, pre-processing and post-processing steps. Tracing is a tool that helps you understand the flow of your application and identify specific points in your application that may be causing issues. Opik's tracing functionality allows you to track not just all the LLM calls made by your application but also any of the other steps involved. -![Tracing in Opik](/img/tracing/introduction.png) + + + Opik provides different ways to log your LLM calls and traces to the platform: -1. **Using one of our [integrations](/tracing/integrations/overview.md):** This is the easiest way to get started. +1. **Using one of our [integrations](/tracing/integrations/overview):** This is the easiest way to get started. 2. **Using the `@track` decorator:** This allows you to track not just LLM calls but any function call in your application, it is often used in conjunction with the integrations. 3. **Using the Python SDK:** This allows for the most flexibility and customizability and is recommended if you want to have full control over the logging process. 4. **Using the Opik REST API:** If you are not using Python, you can use the REST API to log traces to the platform. The REST API is currently in beta and subject to change. @@ -33,7 +30,7 @@ Opik provides different ways to log your LLM calls and traces to the platform: In order to use the Opik Python SDK, you will need to install it and configure it: - + ```bash # Install the SDK @@ -43,10 +40,10 @@ pip install opik opik configure ``` - - + + -```python pytest_codeblocks_skip=true +```python {pytest_codeblocks_skip=true} %pip install --quiet --upgrade opik # Configure the SDK @@ -54,24 +51,25 @@ import opik opik.configure(use_local=False) ``` - + -:::tip -Opik is open-source and can be hosted locally using Docker, please refer to the [self-hosting guide](/self-host/overview.md) to get started. Alternatively, you can use -our hosted platform by creating an account on [Comet](https://www.comet.com/signup?from=llm). -::: + + Opik is open-source and can be hosted locally using Docker, please refer to the [self-hosting + guide](/self-host/overview) to get started. Alternatively, you can use our hosted platform by creating an account on + [Comet](https://www.comet.com/signup?from=llm). + ### Using an integration When using one of Opik's integration you will simply need to add a couple of lines of code to your existing application to track your LLM calls and traces. There are -integrations available for [many of the most popular LLM frameworks and libraries](/tracing/integrations/overview.md). +integrations available for [many of the most popular LLM frameworks and libraries](/tracing/integrations/overview). Here is a short overview of our most popular integrations: - + First let's install the required dependencies: ```bash @@ -96,8 +94,8 @@ response = client.chat.completions.create( ) ``` - - + + First let's install the required dependencies: @@ -130,8 +128,8 @@ llm_chain = prompt_template | llm llm_chain.invoke({"input": "Hello, how are you?"}, callbacks=[opik_tracer]) ``` - - + + First let's install the required dependencies: @@ -159,20 +157,21 @@ query_engine = index.as_query_engine() query_engine.query("What is LlamaIndex used for?") ``` - + -:::tip -If you are using a framework that Opik does not integrate with, you can raise a feature request on our [Github](https://github.com/comet-ml/opik) repository. -::: + + If you are using a framework that Opik does not integrate with, you can raise a feature request on our + [Github](https://github.com/comet-ml/opik) repository. + If you are using a framework that Opik does not integrate with, we recommed you use the `opik.track` function decorator. ### Using function decorators Using the `opik.track` decorator is a great way to add Opik logging to your existing LLM application. We recommend using this -method in conjunction with one of our [integrations](/tracing/integrations/overview.md) for the most seamless experience. +method in conjunction with one of our [integrations](/tracing/integrations/overview) for the most seamless experience. When you add the `@track` decorator to a function, Opik will create a span for that function call and log the input parameters and function output for that function. If we detect that a decorated function is being called within another decorated function, we will create a nested span for the @@ -225,7 +224,7 @@ result = llm_chain("Hello, how are you?") print(result) ``` -:::info + The `@track` decorator will only track the input and output of the decorated function. If you are using OpenAI, we recommend you also use the `track_openai` function to track the LLM call as well as token usage: @@ -237,7 +236,7 @@ client = OpenAI() client = track_openai(client) ``` -::: + #### Scoring traces @@ -260,11 +259,12 @@ def llm_chain(input_text): ) ``` -:::tip + You don't have to manually log feedback scores, you can also define LLM as a Judge metrics in Opik that will score traces automatically for you. -You can learn more about this feature in the [Online evaluation](/production/rules.md) guide. -::: +You can learn more about this feature in the [Online evaluation](/production/rules) guide. + + #### Logging additional data @@ -296,7 +296,7 @@ You can learn more about the `opik_context` module in the [opik_context referenc You can configure the project you want the trace to be logged to using the `project_name` parameter of the `@track` decorator: -```python pytest_codeblocks_skip=true +```python {pytest_codeblocks_skip=true} import opik @opik.track(project_name="my_project") @@ -393,9 +393,10 @@ trace.span( trace.end() ``` -:::note -It is recommended to call `trace.end()` and `span.end()` when you are finished with the trace and span to ensure that the end time is logged correctly. -::: + + It is recommended to call `trace.end()` and `span.end()` when you are finished with the trace and span to ensure that + the end time is logged correctly. + #### Logging feedback scores @@ -425,9 +426,10 @@ client.log_spans_feedback_scores( ) ``` -:::tip -If you want to log scores to traces or spans from within a decorated function, you can use the `update_current_trace` and `update_current_span` methods instead. -::: + + If you want to log scores to traces or spans from within a decorated function, you can use the `update_current_trace` + and `update_current_span` methods instead. + #### Ensuring all traces are logged @@ -477,12 +479,12 @@ const client = new Opik({ }); ``` -:::tip + If you are using the self-hosted Opik platform, you can replace the host with `http://localhost:5173/api` and remove the `workspaceName` parameter. -::: + #### Logging traces and spans @@ -546,8 +548,9 @@ class TranslationService { ### Using the REST API -:::warning -The Opik REST API is currently in beta and subject to change, if you encounter any issues please report them to the [Github](https://github.com/comet-ml/opik). -::: + + The Opik REST API is currently in beta and subject to change, if you encounter any issues please report them to the + [Github](https://github.com/comet-ml/opik). + -The documentation for the Opik REST API is available [here](https://github.com/comet-ml/opik/blob/main/REST_API.md). +The documentation for the Opik REST API is available [here](/reference/rest-api/overview). diff --git a/apps/opik-documentation/documentation/docs/tracing/sdk_configuration.mdx b/apps/opik-documentation/documentation/fern/docs/tracing/sdk_configuration.mdx similarity index 80% rename from apps/opik-documentation/documentation/docs/tracing/sdk_configuration.mdx rename to apps/opik-documentation/documentation/fern/docs/tracing/sdk_configuration.mdx index 7be4871c45..bf6a9b63d9 100644 --- a/apps/opik-documentation/documentation/docs/tracing/sdk_configuration.mdx +++ b/apps/opik-documentation/documentation/fern/docs/tracing/sdk_configuration.mdx @@ -1,17 +1,11 @@ --- -sidebar_label: Python SDK Configuration -description: Describes how to configure the Python SDK +subtitle: Describes how to configure the Python SDK --- -import Tabs from "@theme/Tabs"; -import TabItem from "@theme/TabItem"; - -# Python SDK Configuration - The recommended approach to configuring the Python SDK is to use the `opik configure` command. This will prompt you for the necessary information and save it to a configuration file. - + If you are using the Cloud version of the platform, you can configure the SDK by running: @@ -27,12 +21,12 @@ You can also configure the SDK by calling [`configure`](https://www.comet.com/do opik configure ``` - - + + If you are self-hosting the platform, you can configure the SDK by running: -```python pytest_codeblocks_skip=true +```python {pytest_codeblocks_skip=true} import opik opik.configure(use_local=True) @@ -40,15 +34,19 @@ opik.configure(use_local=True) or from the Command line: -```bash pytest_codeblocks_skip=true +```bash {pytest_codeblocks_skip=true} opik configure --use_local ``` - + -The `configure` methods will prompt you for the necessary information and save it to a configuration file (`~/.opik.config`). +The `configure` methods will prompt you for the necessary information and save it to a configuration file (`~/.opik.config`). When using the command line version, you can use the `-y` or `--yes` flag to automatically approve any confirmation prompts: + +```bash +opik configure --yes +``` ## Advanced usage @@ -64,7 +62,7 @@ The `configure` method is a helper method to help you create the Opik SDK config The Opik configuration file follows the [TOML](https://github.com/toml-lang/toml) format, here is an example configuration file: - + ```toml [opik] @@ -73,8 +71,8 @@ workspace = api_key = ``` - - + + ```toml [opik] @@ -82,15 +80,16 @@ url_override = http://localhost:5173/api workspace = default ``` - + -You can find a full list of the the configuration options in the [Configuration values section](/tracing/sdk_configuration.mdx#configuration-values) below. +You can find a full list of the the configuration options in the [Configuration values section](/tracing/sdk_configuration#configuration-values) below. -:::tip -By default, the SDK will look for the configuration file in your home directory (`~/.opik.config`). If you would like to specify a different location, you can do so by setting the `OPIK_CONFIG_PATH` environment variable. -::: + + By default, the SDK will look for the configuration file in your home directory (`~/.opik.config`). If you would like + to specify a different location, you can do so by setting the `OPIK_CONFIG_PATH` environment variable. + ### Using environment variables @@ -100,7 +99,7 @@ If you do not wish to use a configuration file, you can set environment variable - `OPIK_API_KEY`: The API key to use - Only required if you are using the Opik Cloud version of the platform - `OPIK_WORKSPACE`: The workspace to use - Only required if you are using the Opik Cloud version of the platform -You can find a full list of the the configuration options in the [Configuration values section](/tracing/sdk_configuration.mdx#configuration-values) below. +You can find a full list of the the configuration options in the [Configuration values section](/tracing/sdk_configuration#configuration-values) below. ### Configuration values diff --git a/apps/opik-documentation/documentation/fern/fern.config.json b/apps/opik-documentation/documentation/fern/fern.config.json new file mode 100644 index 0000000000..5669da12aa --- /dev/null +++ b/apps/opik-documentation/documentation/fern/fern.config.json @@ -0,0 +1,4 @@ +{ + "version": "0.51.37", + "organization": "opik" +} diff --git a/apps/opik-documentation/documentation/fern/generators.yml b/apps/opik-documentation/documentation/fern/generators.yml new file mode 100644 index 0000000000..d9969b6312 --- /dev/null +++ b/apps/opik-documentation/documentation/fern/generators.yml @@ -0,0 +1,3 @@ +api: + path: ./openapi/opik.yaml + overrides: ./openapi/overrides.yml diff --git a/apps/opik-documentation/documentation/fern/img/changelog/2024-10-14/experiment_page_filtering.png b/apps/opik-documentation/documentation/fern/img/changelog/2024-10-14/experiment_page_filtering.png new file mode 100644 index 0000000000..214c497e6c Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/changelog/2024-10-14/experiment_page_filtering.png differ diff --git a/apps/opik-documentation/documentation/fern/img/changelog/2024-10-21/download_traces.png b/apps/opik-documentation/documentation/fern/img/changelog/2024-10-21/download_traces.png new file mode 100644 index 0000000000..ef2709e6b0 Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/changelog/2024-10-21/download_traces.png differ diff --git a/apps/opik-documentation/documentation/fern/img/changelog/2024-10-21/quickstart_guide.png b/apps/opik-documentation/documentation/fern/img/changelog/2024-10-21/quickstart_guide.png new file mode 100644 index 0000000000..a9003e6b39 Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/changelog/2024-10-21/quickstart_guide.png differ diff --git a/apps/opik-documentation/documentation/fern/img/changelog/2024-11-04/prompt_library_versions.png b/apps/opik-documentation/documentation/fern/img/changelog/2024-11-04/prompt_library_versions.png new file mode 100644 index 0000000000..5f7e0d7287 Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/changelog/2024-11-04/prompt_library_versions.png differ diff --git a/apps/opik-documentation/documentation/fern/img/changelog/2024-11-11/experiment_summary.png b/apps/opik-documentation/documentation/fern/img/changelog/2024-11-11/experiment_summary.png new file mode 100644 index 0000000000..a7da109b2f Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/changelog/2024-11-11/experiment_summary.png differ diff --git a/apps/opik-documentation/documentation/fern/img/changelog/2024-11-25/experiment_item_sidebar.png b/apps/opik-documentation/documentation/fern/img/changelog/2024-11-25/experiment_item_sidebar.png new file mode 100644 index 0000000000..0178a7e001 Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/changelog/2024-11-25/experiment_item_sidebar.png differ diff --git a/apps/opik-documentation/documentation/fern/img/changelog/2024-11-25/project_dashboard.png b/apps/opik-documentation/documentation/fern/img/changelog/2024-11-25/project_dashboard.png new file mode 100644 index 0000000000..6bfce257db Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/changelog/2024-11-25/project_dashboard.png differ diff --git a/apps/opik-documentation/documentation/fern/img/changelog/2024-11-25/project_statistics.png b/apps/opik-documentation/documentation/fern/img/changelog/2024-11-25/project_statistics.png new file mode 100644 index 0000000000..9646e2ef24 Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/changelog/2024-11-25/project_statistics.png differ diff --git a/apps/opik-documentation/documentation/fern/img/changelog/2024-12-09/experiment_items_table.png b/apps/opik-documentation/documentation/fern/img/changelog/2024-12-09/experiment_items_table.png new file mode 100644 index 0000000000..8f9e445766 Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/changelog/2024-12-09/experiment_items_table.png differ diff --git a/apps/opik-documentation/documentation/fern/img/changelog/2024-12-16/playground.png b/apps/opik-documentation/documentation/fern/img/changelog/2024-12-16/playground.png new file mode 100644 index 0000000000..51d5481c43 Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/changelog/2024-12-16/playground.png differ diff --git a/apps/opik-documentation/documentation/fern/img/changelog/2025-01-13/online_evaluation.gif b/apps/opik-documentation/documentation/fern/img/changelog/2025-01-13/online_evaluation.gif new file mode 100644 index 0000000000..2eb53e128d Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/changelog/2025-01-13/online_evaluation.gif differ diff --git a/apps/opik-documentation/documentation/fern/img/cookbook/anthropic_trace_cookbook.png b/apps/opik-documentation/documentation/fern/img/cookbook/anthropic_trace_cookbook.png new file mode 100644 index 0000000000..1ce391c7b3 Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/cookbook/anthropic_trace_cookbook.png differ diff --git a/apps/opik-documentation/documentation/fern/img/cookbook/bedrock_trace_cookbook.png b/apps/opik-documentation/documentation/fern/img/cookbook/bedrock_trace_cookbook.png new file mode 100644 index 0000000000..bc137a10dd Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/cookbook/bedrock_trace_cookbook.png differ diff --git a/apps/opik-documentation/documentation/fern/img/cookbook/crewai_trace_cookbook.png b/apps/opik-documentation/documentation/fern/img/cookbook/crewai_trace_cookbook.png new file mode 100644 index 0000000000..80dc6fd8a4 Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/cookbook/crewai_trace_cookbook.png differ diff --git a/apps/opik-documentation/documentation/fern/img/cookbook/dspy_trace_cookbook.png b/apps/opik-documentation/documentation/fern/img/cookbook/dspy_trace_cookbook.png new file mode 100644 index 0000000000..2328d46f77 Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/cookbook/dspy_trace_cookbook.png differ diff --git a/apps/opik-documentation/documentation/fern/img/cookbook/gemini_trace_cookbook.png b/apps/opik-documentation/documentation/fern/img/cookbook/gemini_trace_cookbook.png new file mode 100644 index 0000000000..8ced88ea2e Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/cookbook/gemini_trace_cookbook.png differ diff --git a/apps/opik-documentation/documentation/fern/img/cookbook/gemini_trace_decorator_cookbook.png b/apps/opik-documentation/documentation/fern/img/cookbook/gemini_trace_decorator_cookbook.png new file mode 100644 index 0000000000..7c3571ff7b Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/cookbook/gemini_trace_decorator_cookbook.png differ diff --git a/apps/opik-documentation/documentation/fern/img/cookbook/groq_trace_cookbook.png b/apps/opik-documentation/documentation/fern/img/cookbook/groq_trace_cookbook.png new file mode 100644 index 0000000000..67af0e8e7c Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/cookbook/groq_trace_cookbook.png differ diff --git a/apps/opik-documentation/documentation/fern/img/cookbook/groq_trace_decorator_cookbook.png b/apps/opik-documentation/documentation/fern/img/cookbook/groq_trace_decorator_cookbook.png new file mode 100644 index 0000000000..ecfd258f3e Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/cookbook/groq_trace_decorator_cookbook.png differ diff --git a/apps/opik-documentation/documentation/fern/img/cookbook/haystack_trace_cookbook.png b/apps/opik-documentation/documentation/fern/img/cookbook/haystack_trace_cookbook.png new file mode 100644 index 0000000000..38a8b58ddf Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/cookbook/haystack_trace_cookbook.png differ diff --git a/apps/opik-documentation/documentation/fern/img/cookbook/langgraph_cookbook.png b/apps/opik-documentation/documentation/fern/img/cookbook/langgraph_cookbook.png new file mode 100644 index 0000000000..11a1b5a6ce Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/cookbook/langgraph_cookbook.png differ diff --git a/apps/opik-documentation/documentation/fern/img/cookbook/litellm_cookbook.png b/apps/opik-documentation/documentation/fern/img/cookbook/litellm_cookbook.png new file mode 100644 index 0000000000..8a8ed48827 Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/cookbook/litellm_cookbook.png differ diff --git a/apps/opik-documentation/documentation/fern/img/cookbook/ollama_cookbook.png b/apps/opik-documentation/documentation/fern/img/cookbook/ollama_cookbook.png new file mode 100644 index 0000000000..3912fa5492 Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/cookbook/ollama_cookbook.png differ diff --git a/apps/opik-documentation/documentation/fern/img/cookbook/watsonx_trace_cookbook.png b/apps/opik-documentation/documentation/fern/img/cookbook/watsonx_trace_cookbook.png new file mode 100644 index 0000000000..e91be42745 Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/cookbook/watsonx_trace_cookbook.png differ diff --git a/apps/opik-documentation/documentation/fern/img/cookbook/watsonx_trace_decorator_cookbook.png b/apps/opik-documentation/documentation/fern/img/cookbook/watsonx_trace_decorator_cookbook.png new file mode 100644 index 0000000000..db7011fa92 Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/cookbook/watsonx_trace_decorator_cookbook.png differ diff --git a/apps/opik-documentation/documentation/fern/img/evaluation/compare_experiment_config.png b/apps/opik-documentation/documentation/fern/img/evaluation/compare_experiment_config.png new file mode 100644 index 0000000000..f7186155a0 Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/evaluation/compare_experiment_config.png differ diff --git a/apps/opik-documentation/documentation/fern/img/evaluation/dataset_items_page.png b/apps/opik-documentation/documentation/fern/img/evaluation/dataset_items_page.png new file mode 100644 index 0000000000..f64a522992 Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/evaluation/dataset_items_page.png differ diff --git a/apps/opik-documentation/documentation/fern/img/evaluation/evaluation_concepts.png b/apps/opik-documentation/documentation/fern/img/evaluation/evaluation_concepts.png new file mode 100644 index 0000000000..1baee11eed Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/evaluation/evaluation_concepts.png differ diff --git a/apps/opik-documentation/documentation/fern/img/evaluation/evaluation_overview.gif b/apps/opik-documentation/documentation/fern/img/evaluation/evaluation_overview.gif new file mode 100644 index 0000000000..3a166fef5f Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/evaluation/evaluation_overview.gif differ diff --git a/apps/opik-documentation/documentation/fern/img/evaluation/experiment_items.png b/apps/opik-documentation/documentation/fern/img/evaluation/experiment_items.png new file mode 100644 index 0000000000..8c547d4eae Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/evaluation/experiment_items.png differ diff --git a/apps/opik-documentation/documentation/fern/img/evaluation/linked_prompt.png b/apps/opik-documentation/documentation/fern/img/evaluation/linked_prompt.png new file mode 100644 index 0000000000..c8ebd856c1 Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/evaluation/linked_prompt.png differ diff --git a/apps/opik-documentation/documentation/fern/img/evaluation/playground.png b/apps/opik-documentation/documentation/fern/img/evaluation/playground.png new file mode 100644 index 0000000000..51d5481c43 Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/evaluation/playground.png differ diff --git a/apps/opik-documentation/documentation/fern/img/evaluation/playground_conversations.png b/apps/opik-documentation/documentation/fern/img/evaluation/playground_conversations.png new file mode 100644 index 0000000000..ac3cc38411 Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/evaluation/playground_conversations.png differ diff --git a/apps/opik-documentation/documentation/fern/img/evaluation/playground_evaluation.gif b/apps/opik-documentation/documentation/fern/img/evaluation/playground_evaluation.gif new file mode 100644 index 0000000000..cdc7db243a Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/evaluation/playground_evaluation.gif differ diff --git a/apps/opik-documentation/documentation/fern/img/home/traces_page_for_quickstart.png b/apps/opik-documentation/documentation/fern/img/home/traces_page_for_quickstart.png new file mode 100644 index 0000000000..0c816a61b1 Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/home/traces_page_for_quickstart.png differ diff --git a/apps/opik-documentation/documentation/fern/img/home/traces_page_with_sidebar.png b/apps/opik-documentation/documentation/fern/img/home/traces_page_with_sidebar.png new file mode 100644 index 0000000000..d180031715 Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/home/traces_page_with_sidebar.png differ diff --git a/apps/opik-documentation/documentation/fern/img/logo-dark-mode.svg b/apps/opik-documentation/documentation/fern/img/logo-dark-mode.svg new file mode 100644 index 0000000000..11c732469f --- /dev/null +++ b/apps/opik-documentation/documentation/fern/img/logo-dark-mode.svg @@ -0,0 +1,7 @@ + + + + + + + diff --git a/apps/opik-documentation/documentation/fern/img/logo.svg b/apps/opik-documentation/documentation/fern/img/logo.svg new file mode 100644 index 0000000000..7acb1f5c54 --- /dev/null +++ b/apps/opik-documentation/documentation/fern/img/logo.svg @@ -0,0 +1,42 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/apps/opik-documentation/documentation/fern/img/opik-logo.svg b/apps/opik-documentation/documentation/fern/img/opik-logo.svg new file mode 100644 index 0000000000..9914a1eea9 --- /dev/null +++ b/apps/opik-documentation/documentation/fern/img/opik-logo.svg @@ -0,0 +1,14 @@ + + + + + + + + + + + + + + diff --git a/apps/opik-documentation/documentation/fern/img/production/online_evaluation.gif b/apps/opik-documentation/documentation/fern/img/production/online_evaluation.gif new file mode 100644 index 0000000000..2eb53e128d Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/production/online_evaluation.gif differ diff --git a/apps/opik-documentation/documentation/fern/img/production/online_evaluation_custom_judge.png b/apps/opik-documentation/documentation/fern/img/production/online_evaluation_custom_judge.png new file mode 100644 index 0000000000..f871c0d4d1 Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/production/online_evaluation_custom_judge.png differ diff --git a/apps/opik-documentation/documentation/fern/img/production/online_evaluation_rule_modal.png b/apps/opik-documentation/documentation/fern/img/production/online_evaluation_rule_modal.png new file mode 100644 index 0000000000..42675823e9 Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/production/online_evaluation_rule_modal.png differ diff --git a/apps/opik-documentation/documentation/fern/img/production/opik-kong-gateway.png b/apps/opik-documentation/documentation/fern/img/production/opik-kong-gateway.png new file mode 100644 index 0000000000..81ca5b4a5a Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/production/opik-kong-gateway.png differ diff --git a/apps/opik-documentation/documentation/fern/img/production/opik_monitoring_dashboard.gif b/apps/opik-documentation/documentation/fern/img/production/opik_monitoring_dashboard.gif new file mode 100644 index 0000000000..0adf2831dc Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/production/opik_monitoring_dashboard.gif differ diff --git a/apps/opik-documentation/documentation/fern/img/prompt_engineering/ollama_config.png b/apps/opik-documentation/documentation/fern/img/prompt_engineering/ollama_config.png new file mode 100644 index 0000000000..42e0ff3033 Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/prompt_engineering/ollama_config.png differ diff --git a/apps/opik-documentation/documentation/fern/img/prompt_engineering/ollama_proxy.png b/apps/opik-documentation/documentation/fern/img/prompt_engineering/ollama_proxy.png new file mode 100644 index 0000000000..cf8f5bc648 Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/prompt_engineering/ollama_proxy.png differ diff --git a/apps/opik-documentation/documentation/fern/img/prompt_engineering/playground.png b/apps/opik-documentation/documentation/fern/img/prompt_engineering/playground.png new file mode 100644 index 0000000000..472ac00bd4 Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/prompt_engineering/playground.png differ diff --git a/apps/opik-documentation/documentation/fern/img/prompt_engineering/prompt_library.png b/apps/opik-documentation/documentation/fern/img/prompt_engineering/prompt_library.png new file mode 100644 index 0000000000..f00b8dfd94 Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/prompt_engineering/prompt_library.png differ diff --git a/apps/opik-documentation/documentation/fern/img/prompt_engineering/prompt_library_versions.png b/apps/opik-documentation/documentation/fern/img/prompt_engineering/prompt_library_versions.png new file mode 100644 index 0000000000..5f7e0d7287 Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/prompt_engineering/prompt_library_versions.png differ diff --git a/apps/opik-documentation/documentation/fern/img/self-host/architecture.png b/apps/opik-documentation/documentation/fern/img/self-host/architecture.png new file mode 100644 index 0000000000..fbc332c8cd Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/self-host/architecture.png differ diff --git a/apps/opik-documentation/documentation/fern/img/self-host/clickhouse-schema.png b/apps/opik-documentation/documentation/fern/img/self-host/clickhouse-schema.png new file mode 100644 index 0000000000..c91d406907 Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/self-host/clickhouse-schema.png differ diff --git a/apps/opik-documentation/documentation/fern/img/self-host/mysql-schema.png b/apps/opik-documentation/documentation/fern/img/self-host/mysql-schema.png new file mode 100644 index 0000000000..723852fd1f Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/self-host/mysql-schema.png differ diff --git a/apps/opik-documentation/documentation/fern/img/testing/test_experiments.png b/apps/opik-documentation/documentation/fern/img/testing/test_experiments.png new file mode 100644 index 0000000000..ae76e92a2d Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/testing/test_experiments.png differ diff --git a/apps/opik-documentation/documentation/fern/img/tracing/agent_definition-v2.png b/apps/opik-documentation/documentation/fern/img/tracing/agent_definition-v2.png new file mode 100644 index 0000000000..2a853346eb Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/tracing/agent_definition-v2.png differ diff --git a/apps/opik-documentation/documentation/fern/img/tracing/agent_definition.png b/apps/opik-documentation/documentation/fern/img/tracing/agent_definition.png new file mode 100644 index 0000000000..2a853346eb Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/tracing/agent_definition.png differ diff --git a/apps/opik-documentation/documentation/fern/img/tracing/agent_execution_flow.png b/apps/opik-documentation/documentation/fern/img/tracing/agent_execution_flow.png new file mode 100644 index 0000000000..a96efa4395 Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/tracing/agent_execution_flow.png differ diff --git a/apps/opik-documentation/documentation/fern/img/tracing/annotate_traces.png b/apps/opik-documentation/documentation/fern/img/tracing/annotate_traces.png new file mode 100644 index 0000000000..b72f7fc268 Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/tracing/annotate_traces.png differ diff --git a/apps/opik-documentation/documentation/fern/img/tracing/cost_tracking_project.png b/apps/opik-documentation/documentation/fern/img/tracing/cost_tracking_project.png new file mode 100644 index 0000000000..f8ed2bc9fb Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/tracing/cost_tracking_project.png differ diff --git a/apps/opik-documentation/documentation/fern/img/tracing/cost_tracking_project_metrics.png b/apps/opik-documentation/documentation/fern/img/tracing/cost_tracking_project_metrics.png new file mode 100644 index 0000000000..4953bebb29 Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/tracing/cost_tracking_project_metrics.png differ diff --git a/apps/opik-documentation/documentation/fern/img/tracing/cost_tracking_span.png b/apps/opik-documentation/documentation/fern/img/tracing/cost_tracking_span.png new file mode 100644 index 0000000000..4917532cbe Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/tracing/cost_tracking_span.png differ diff --git a/apps/opik-documentation/documentation/fern/img/tracing/cost_tracking_trace_view.png b/apps/opik-documentation/documentation/fern/img/tracing/cost_tracking_trace_view.png new file mode 100644 index 0000000000..72673d4122 Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/tracing/cost_tracking_trace_view.png differ diff --git a/apps/opik-documentation/documentation/fern/img/tracing/dify_configuration.png b/apps/opik-documentation/documentation/fern/img/tracing/dify_configuration.png new file mode 100644 index 0000000000..411fb40f81 Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/tracing/dify_configuration.png differ diff --git a/apps/opik-documentation/documentation/fern/img/tracing/dify_view_project.png b/apps/opik-documentation/documentation/fern/img/tracing/dify_view_project.png new file mode 100644 index 0000000000..beb62bf635 Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/tracing/dify_view_project.png differ diff --git a/apps/opik-documentation/documentation/fern/img/tracing/distributed_tracing.svg b/apps/opik-documentation/documentation/fern/img/tracing/distributed_tracing.svg new file mode 100644 index 0000000000..9bea26227a --- /dev/null +++ b/apps/opik-documentation/documentation/fern/img/tracing/distributed_tracing.svg @@ -0,0 +1,13 @@ + + + + + + + + clienttraceparent spanheaders = { "comet-trace-id": "...", "comet-parent_span_id": "..."}child spanserveTraceParent SpanChild Span \ No newline at end of file diff --git a/apps/opik-documentation/documentation/fern/img/tracing/download_traces.png b/apps/opik-documentation/documentation/fern/img/tracing/download_traces.png new file mode 100644 index 0000000000..572a78c875 Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/tracing/download_traces.png differ diff --git a/apps/opik-documentation/documentation/fern/img/tracing/image_trace.png b/apps/opik-documentation/documentation/fern/img/tracing/image_trace.png new file mode 100644 index 0000000000..40df9598d7 Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/tracing/image_trace.png differ diff --git a/apps/opik-documentation/documentation/fern/img/tracing/introduction.png b/apps/opik-documentation/documentation/fern/img/tracing/introduction.png new file mode 100644 index 0000000000..8d2edd143d Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/tracing/introduction.png differ diff --git a/apps/opik-documentation/documentation/fern/img/tracing/llama_index_integration.png b/apps/opik-documentation/documentation/fern/img/tracing/llama_index_integration.png new file mode 100644 index 0000000000..17eff17e1c Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/tracing/llama_index_integration.png differ diff --git a/apps/opik-documentation/documentation/fern/img/tracing/opik_monitoring_dashboard.png b/apps/opik-documentation/documentation/fern/img/tracing/opik_monitoring_dashboard.png new file mode 100644 index 0000000000..6bfce257db Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/tracing/opik_monitoring_dashboard.png differ diff --git a/apps/opik-documentation/documentation/fern/img/tracing/predibase_opik_trace.png b/apps/opik-documentation/documentation/fern/img/tracing/predibase_opik_trace.png new file mode 100644 index 0000000000..bcc2e6f320 Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/tracing/predibase_opik_trace.png differ diff --git a/apps/opik-documentation/documentation/fern/img/tracing/ragas_opik_trace.png b/apps/opik-documentation/documentation/fern/img/tracing/ragas_opik_trace.png new file mode 100644 index 0000000000..94fba3f03f Binary files /dev/null and b/apps/opik-documentation/documentation/fern/img/tracing/ragas_opik_trace.png differ diff --git a/apps/opik-documentation/documentation/rest_api/opik.yaml b/apps/opik-documentation/documentation/fern/openapi/opik.yaml similarity index 70% rename from apps/opik-documentation/documentation/rest_api/opik.yaml rename to apps/opik-documentation/documentation/fern/openapi/opik.yaml index fd92dec4d4..4a4deaf144 100644 --- a/apps/opik-documentation/documentation/rest_api/opik.yaml +++ b/apps/opik-documentation/documentation/fern/openapi/opik.yaml @@ -29,40 +29,40 @@ info: url: http://www.apache.org/licenses/LICENSE-2.0.html version: 1.0.0 servers: -- url: http://localhost:5173/api - description: Local server -- url: https://www.comet.com/opik/api - description: Opik Cloud + - url: http://localhost:5173/api + description: Local server + - url: https://www.comet.com/opik/api + description: Opik Cloud tags: -- name: System usage - description: System usage related resource -- name: Check - description: Access check resources -- name: Automation rule evaluators - description: Automation rule evaluators resource -- name: Chat Completions - description: Chat Completions related resources -- name: Datasets - description: Dataset resources -- name: Experiments - description: Experiment resources -- name: Feedback-definitions - description: Feedback definitions related resources -- name: LlmProviderKey - description: LLM Provider Key -- name: Projects - description: Project related resources -- name: Prompts - description: Prompt resources -- name: Spans - description: Span related resources -- name: Traces - description: Trace related resources + - name: System usage + description: System usage related resource + - name: Check + description: Access check resources + - name: Automation rule evaluators + description: Automation rule evaluators resource + - name: Chat Completions + description: Chat Completions related resources + - name: Datasets + description: Dataset resources + - name: Experiments + description: Experiment resources + - name: Feedback-definitions + description: Feedback definitions related resources + - name: LlmProviderKey + description: LLM Provider Key + - name: Projects + description: Project related resources + - name: Prompts + description: Prompt resources + - name: Spans + description: Span related resources + - name: Traces + description: Trace related resources paths: /v1/internal/usage/bi-datasets: get: tags: - - System usage + - System usage summary: Get datasets information for BI events description: Get datasets information for BI events per user per workspace operationId: getDatasetBiInfo @@ -72,11 +72,11 @@ paths: content: application/json: schema: - $ref: '#/components/schemas/BiInformationResponse' + $ref: "#/components/schemas/BiInformationResponse" /v1/internal/usage/bi-experiments: get: tags: - - System usage + - System usage summary: Get experiments information for BI events description: Get experiments information for BI events per user per workspace operationId: getExperimentBiInfo @@ -86,11 +86,11 @@ paths: content: application/json: schema: - $ref: '#/components/schemas/BiInformationResponse' + $ref: "#/components/schemas/BiInformationResponse" /v1/internal/usage/bi-traces: get: tags: - - System usage + - System usage summary: Get traces information for BI events description: Get traces information for BI events per user per workspace operationId: getTracesBiInfo @@ -100,11 +100,11 @@ paths: content: application/json: schema: - $ref: '#/components/schemas/BiInformationResponse' + $ref: "#/components/schemas/BiInformationResponse" /v1/internal/usage/workspace-trace-counts: get: tags: - - System usage + - System usage summary: Get traces count on previous day for all available workspaces description: Get traces count on previous day for all available workspaces operationId: getTracesCountForWorkspaces @@ -114,11 +114,11 @@ paths: content: application/json: schema: - $ref: '#/components/schemas/TraceCountResponse' + $ref: "#/components/schemas/TraceCountResponse" /v1/private/auth: post: tags: - - Check + - Check summary: Check user access to workspace description: Check user access to workspace operationId: checkAccess @@ -126,7 +126,7 @@ paths: content: application/json: schema: - $ref: '#/components/schemas/AuthDetailsHolder' + $ref: "#/components/schemas/AuthDetailsHolder" responses: "204": description: No Content @@ -135,54 +135,54 @@ paths: content: application/json: schema: - $ref: '#/components/schemas/ErrorMessage' + $ref: "#/components/schemas/ErrorMessage" "403": description: Access forbidden content: application/json: schema: - $ref: '#/components/schemas/ErrorMessage' + $ref: "#/components/schemas/ErrorMessage" /v1/private/automations/evaluators: get: tags: - - Automation rule evaluators + - Automation rule evaluators summary: Find project Evaluators description: Find project Evaluators operationId: findEvaluators parameters: - - name: project_id - in: query - schema: - type: string - format: uuid - - name: name - in: query - schema: - type: string - - name: page - in: query - schema: - minimum: 1 - type: integer - format: int32 - default: 1 - - name: size - in: query - schema: - minimum: 1 - type: integer - format: int32 - default: 10 + - name: project_id + in: query + schema: + type: string + format: uuid + - name: name + in: query + schema: + type: string + - name: page + in: query + schema: + minimum: 1 + type: integer + format: int32 + default: 1 + - name: size + in: query + schema: + minimum: 1 + type: integer + format: int32 + default: 10 responses: "200": description: Evaluators resource content: application/json: schema: - $ref: '#/components/schemas/AutomationRuleEvaluatorPage_Public' + $ref: "#/components/schemas/AutomationRuleEvaluatorPage_Public" post: tags: - - Automation rule evaluators + - Automation rule evaluators summary: Create automation rule evaluator description: Create automation rule evaluator operationId: createAutomationRuleEvaluator @@ -190,7 +190,7 @@ paths: content: application/json: schema: - $ref: '#/components/schemas/AutomationRuleEvaluator_Write' + $ref: "#/components/schemas/AutomationRuleEvaluator_Write" responses: "201": description: Created @@ -204,158 +204,158 @@ paths: /v1/private/automations/evaluators/delete: post: tags: - - Automation rule evaluators + - Automation rule evaluators summary: Delete automation rule evaluators description: Delete automation rule evaluators batch operationId: deleteAutomationRuleEvaluatorBatch parameters: - - name: project_id - in: query - required: true - schema: - type: string - format: uuid + - name: project_id + in: query + required: true + schema: + type: string + format: uuid requestBody: content: application/json: schema: - $ref: '#/components/schemas/BatchDelete' + $ref: "#/components/schemas/BatchDelete" responses: "204": description: No Content /v1/private/automations/evaluators/{id}: get: tags: - - Automation rule evaluators + - Automation rule evaluators summary: Get automation rule evaluator by id description: Get automation rule by id operationId: getEvaluatorById parameters: - - name: project_id - in: query - schema: - type: string - format: uuid - - name: id - in: path - required: true - schema: - type: string - format: uuid + - name: project_id + in: query + schema: + type: string + format: uuid + - name: id + in: path + required: true + schema: + type: string + format: uuid responses: "200": description: Automation Rule resource content: application/json: schema: - $ref: '#/components/schemas/AutomationRuleEvaluator_Public' + $ref: "#/components/schemas/AutomationRuleEvaluator_Public" patch: tags: - - Automation rule evaluators + - Automation rule evaluators summary: update Automation Rule Evaluator by id description: update Automation Rule Evaluator by id operationId: updateAutomationRuleEvaluator parameters: - - name: id - in: path - required: true - schema: - type: string - format: uuid + - name: id + in: path + required: true + schema: + type: string + format: uuid requestBody: content: application/json: schema: - $ref: '#/components/schemas/AutomationRuleEvaluatorUpdate' + $ref: "#/components/schemas/AutomationRuleEvaluatorUpdate" responses: "204": description: No content /v1/private/automations/evaluators/{id}/logs: get: tags: - - Automation rule evaluators + - Automation rule evaluators summary: Get automation rule evaluator logs by id description: Get automation rule evaluator logs by id operationId: getEvaluatorLogsById parameters: - - name: id - in: path - required: true - schema: - type: string - format: uuid - - name: size - in: query - schema: - minimum: 1 - type: integer - format: int32 - default: 1000 + - name: id + in: path + required: true + schema: + type: string + format: uuid + - name: size + in: query + schema: + minimum: 1 + type: integer + format: int32 + default: 1000 responses: "200": description: Automation rule evaluator logs resource content: application/json: schema: - $ref: '#/components/schemas/LogPage' + $ref: "#/components/schemas/LogPage" /v1/private/automations/projects/{projectId}/evaluators: get: tags: - - Automation rule evaluators + - Automation rule evaluators summary: Find project Evaluators Deprecated description: Find project Evaluators Deprecated operationId: findEvaluatorsDeprecated parameters: - - name: projectId - in: path - required: true - schema: - type: string - format: uuid - - name: name - in: query - schema: - type: string - - name: page - in: query - schema: - minimum: 1 - type: integer - format: int32 - default: 1 - - name: size - in: query - schema: - minimum: 1 - type: integer - format: int32 - default: 10 + - name: projectId + in: path + required: true + schema: + type: string + format: uuid + - name: name + in: query + schema: + type: string + - name: page + in: query + schema: + minimum: 1 + type: integer + format: int32 + default: 1 + - name: size + in: query + schema: + minimum: 1 + type: integer + format: int32 + default: 10 responses: "200": description: Evaluators resource content: application/json: schema: - $ref: '#/components/schemas/AutomationRuleEvaluatorPage_Public' + $ref: "#/components/schemas/AutomationRuleEvaluatorPage_Public" deprecated: true post: tags: - - Automation rule evaluators + - Automation rule evaluators summary: Create automation rule evaluator Deprecated description: Create automation rule evaluator Deprecated operationId: createAutomationRuleEvaluatorDeprecated parameters: - - name: projectId - in: path - required: true - schema: - type: string - format: uuid + - name: projectId + in: path + required: true + schema: + type: string + format: uuid requestBody: content: application/json: schema: - $ref: '#/components/schemas/AutomationRuleEvaluator_Write' + $ref: "#/components/schemas/AutomationRuleEvaluator_Write" responses: "201": description: Created @@ -370,22 +370,22 @@ paths: /v1/private/automations/projects/{projectId}/evaluators/delete: post: tags: - - Automation rule evaluators + - Automation rule evaluators summary: Delete automation rule evaluators Deprecated description: Delete automation rule evaluators batch Deprecated operationId: deleteAutomationRuleEvaluatorBatchDeprecated parameters: - - name: projectId - in: path - required: true - schema: - type: string - format: uuid + - name: projectId + in: path + required: true + schema: + type: string + format: uuid requestBody: content: application/json: schema: - $ref: '#/components/schemas/BatchDelete' + $ref: "#/components/schemas/BatchDelete" responses: "204": description: No Content @@ -393,55 +393,55 @@ paths: /v1/private/automations/projects/{projectId}/evaluators/{id}: get: tags: - - Automation rule evaluators + - Automation rule evaluators summary: Get automation rule evaluator by id Deprecated description: Get automation rule by id Deprecated operationId: getEvaluatorByIdDeprecated parameters: - - name: projectId - in: path - required: true - schema: - type: string - format: uuid - - name: id - in: path - required: true - schema: - type: string - format: uuid + - name: projectId + in: path + required: true + schema: + type: string + format: uuid + - name: id + in: path + required: true + schema: + type: string + format: uuid responses: "200": description: Automation Rule resource content: application/json: schema: - $ref: '#/components/schemas/AutomationRuleEvaluator_Public' + $ref: "#/components/schemas/AutomationRuleEvaluator_Public" deprecated: true patch: tags: - - Automation rule evaluators + - Automation rule evaluators summary: update Automation Rule Evaluator by id Deprecated description: update Automation Rule Evaluator by id Deprecated operationId: updateAutomationRuleEvaluatorDeprecated parameters: - - name: id - in: path - required: true - schema: - type: string - format: uuid - - name: projectId - in: path - required: true - schema: - type: string - format: uuid + - name: id + in: path + required: true + schema: + type: string + format: uuid + - name: projectId + in: path + required: true + schema: + type: string + format: uuid requestBody: content: application/json: schema: - $ref: '#/components/schemas/AutomationRuleEvaluatorUpdate' + $ref: "#/components/schemas/AutomationRuleEvaluatorUpdate" responses: "204": description: No content @@ -449,42 +449,42 @@ paths: /v1/private/automations/projects/{projectId}/evaluators/{id}/logs: get: tags: - - Automation rule evaluators + - Automation rule evaluators summary: Get automation rule evaluator logs by id Deprecated description: Get automation rule evaluator logs by id Deprecated operationId: getEvaluatorLogsByIdDeprecated parameters: - - name: projectId - in: path - required: true - schema: - type: string - format: uuid - - name: id - in: path - required: true - schema: - type: string - format: uuid - - name: size - in: query - schema: - minimum: 1 - type: integer - format: int32 - default: 1000 + - name: projectId + in: path + required: true + schema: + type: string + format: uuid + - name: id + in: path + required: true + schema: + type: string + format: uuid + - name: size + in: query + schema: + minimum: 1 + type: integer + format: int32 + default: 1000 responses: "200": description: Automation rule evaluator logs resource content: application/json: schema: - $ref: '#/components/schemas/LogPage' + $ref: "#/components/schemas/LogPage" deprecated: true /v1/private/chat/completions: post: tags: - - Chat Completions + - Chat Completions summary: Create chat completions description: Create chat completions operationId: createChatCompletions @@ -492,7 +492,7 @@ paths: content: application/json: schema: - $ref: '#/components/schemas/ChatCompletionRequest' + $ref: "#/components/schemas/ChatCompletionRequest" responses: "200": description: Chat completions response @@ -503,60 +503,60 @@ paths: items: type: object anyOf: - - $ref: '#/components/schemas/ChatCompletionResponse' - - $ref: '#/components/schemas/ErrorMessage' + - $ref: "#/components/schemas/ChatCompletionResponse" + - $ref: "#/components/schemas/ErrorMessage" application/json: schema: - $ref: '#/components/schemas/ChatCompletionResponse' + $ref: "#/components/schemas/ChatCompletionResponse" /v1/private/datasets: get: tags: - - Datasets + - Datasets summary: Find datasets description: Find datasets operationId: findDatasets parameters: - - name: page - in: query - schema: - minimum: 1 - type: integer - format: int32 - default: 1 - - name: size - in: query - schema: - minimum: 1 - type: integer - format: int32 - default: 10 - - name: with_experiments_only - in: query - schema: - type: boolean - - name: prompt_id - in: query - schema: - type: string - format: uuid - - name: name - in: query - schema: - type: string - - name: sorting - in: query - schema: - type: string + - name: page + in: query + schema: + minimum: 1 + type: integer + format: int32 + default: 1 + - name: size + in: query + schema: + minimum: 1 + type: integer + format: int32 + default: 10 + - name: with_experiments_only + in: query + schema: + type: boolean + - name: prompt_id + in: query + schema: + type: string + format: uuid + - name: name + in: query + schema: + type: string + - name: sorting + in: query + schema: + type: string responses: "200": description: Dataset resource content: application/json: schema: - $ref: '#/components/schemas/DatasetPage_Public' + $ref: "#/components/schemas/DatasetPage_Public" post: tags: - - Datasets + - Datasets summary: Create dataset description: Create dataset operationId: createDataset @@ -564,7 +564,7 @@ paths: content: application/json: schema: - $ref: '#/components/schemas/Dataset_Write' + $ref: "#/components/schemas/Dataset_Write" responses: "201": description: Created @@ -578,7 +578,7 @@ paths: /v1/private/datasets/items: put: tags: - - Datasets + - Datasets summary: Create/update dataset items description: Create/update dataset items based on dataset item id operationId: createOrUpdateDatasetItems @@ -586,72 +586,72 @@ paths: content: application/json: schema: - $ref: '#/components/schemas/DatasetItemBatch_Write' + $ref: "#/components/schemas/DatasetItemBatch_Write" responses: "204": description: No content /v1/private/datasets/{id}: get: tags: - - Datasets + - Datasets summary: Get dataset by id description: Get dataset by id operationId: getDatasetById parameters: - - name: id - in: path - required: true - schema: - type: string - format: uuid + - name: id + in: path + required: true + schema: + type: string + format: uuid responses: "200": description: Dataset resource content: application/json: schema: - $ref: '#/components/schemas/Dataset_Public' + $ref: "#/components/schemas/Dataset_Public" put: tags: - - Datasets + - Datasets summary: Update dataset by id description: Update dataset by id operationId: updateDataset parameters: - - name: id - in: path - required: true - schema: - type: string - format: uuid + - name: id + in: path + required: true + schema: + type: string + format: uuid requestBody: content: application/json: schema: - $ref: '#/components/schemas/DatasetUpdate' + $ref: "#/components/schemas/DatasetUpdate" responses: "204": description: No content delete: tags: - - Datasets + - Datasets summary: Delete dataset by id description: Delete dataset by id operationId: deleteDataset parameters: - - name: id - in: path - required: true - schema: - type: string - format: uuid + - name: id + in: path + required: true + schema: + type: string + format: uuid responses: "204": description: No content /v1/private/datasets/delete: post: tags: - - Datasets + - Datasets summary: Delete dataset by name description: Delete dataset by name operationId: deleteDatasetByName @@ -659,14 +659,14 @@ paths: content: application/json: schema: - $ref: '#/components/schemas/DatasetIdentifier' + $ref: "#/components/schemas/DatasetIdentifier" responses: "204": description: No content /v1/private/datasets/items/delete: post: tags: - - Datasets + - Datasets summary: Delete dataset items description: Delete dataset items operationId: deleteDatasetItems @@ -674,14 +674,14 @@ paths: content: application/json: schema: - $ref: '#/components/schemas/DatasetItemsDelete' + $ref: "#/components/schemas/DatasetItemsDelete" responses: "204": description: No content /v1/private/datasets/delete-batch: post: tags: - - Datasets + - Datasets summary: Delete datasets description: Delete datasets batch operationId: deleteDatasetsBatch @@ -689,63 +689,63 @@ paths: content: application/json: schema: - $ref: '#/components/schemas/BatchDelete' + $ref: "#/components/schemas/BatchDelete" responses: "204": description: No content /v1/private/datasets/{id}/items/experiments/items: get: tags: - - Datasets + - Datasets summary: Find dataset items with experiment items description: Find dataset items with experiment items operationId: findDatasetItemsWithExperimentItems parameters: - - name: id - in: path - required: true - schema: - type: string - format: uuid - - name: page - in: query - schema: - minimum: 1 - type: integer - format: int32 - default: 1 - - name: size - in: query - schema: - minimum: 1 - type: integer - format: int32 - default: 10 - - name: experiment_ids - in: query - required: true - schema: - type: string - - name: filters - in: query - schema: - type: string - - name: truncate - in: query - schema: - type: boolean - description: "Truncate image included in either input, output or metadata" + - name: id + in: path + required: true + schema: + type: string + format: uuid + - name: page + in: query + schema: + minimum: 1 + type: integer + format: int32 + default: 1 + - name: size + in: query + schema: + minimum: 1 + type: integer + format: int32 + default: 10 + - name: experiment_ids + in: query + required: true + schema: + type: string + - name: filters + in: query + schema: + type: string + - name: truncate + in: query + schema: + type: boolean + description: "Truncate image included in either input, output or metadata" responses: "200": description: Dataset item resource content: application/json: schema: - $ref: '#/components/schemas/DatasetItemPage_Compare' + $ref: "#/components/schemas/DatasetItemPage_Compare" /v1/private/datasets/retrieve: post: tags: - - Datasets + - Datasets summary: Get dataset by name description: Get dataset by name operationId: getDatasetByIdentifier @@ -753,104 +753,104 @@ paths: content: application/json: schema: - $ref: '#/components/schemas/DatasetIdentifier_Public' + $ref: "#/components/schemas/DatasetIdentifier_Public" responses: "200": description: Dataset resource content: application/json: schema: - $ref: '#/components/schemas/Dataset_Public' + $ref: "#/components/schemas/Dataset_Public" /v1/private/datasets/items/{itemId}: get: tags: - - Datasets + - Datasets summary: Get dataset item by id description: Get dataset item by id operationId: getDatasetItemById parameters: - - name: itemId - in: path - required: true - schema: - type: string - format: uuid + - name: itemId + in: path + required: true + schema: + type: string + format: uuid responses: "200": description: Dataset item resource content: application/json: schema: - $ref: '#/components/schemas/DatasetItem_Public' + $ref: "#/components/schemas/DatasetItem_Public" /v1/private/datasets/{id}/items: get: tags: - - Datasets + - Datasets summary: Get dataset items description: Get dataset items operationId: getDatasetItems parameters: - - name: id - in: path - required: true - schema: - type: string - format: uuid - - name: page - in: query - schema: - minimum: 1 - type: integer - format: int32 - default: 1 - - name: size - in: query - schema: - minimum: 1 - type: integer - format: int32 - default: 10 - - name: truncate - in: query - schema: - type: boolean - description: "Truncate image included in either input, output or metadata" + - name: id + in: path + required: true + schema: + type: string + format: uuid + - name: page + in: query + schema: + minimum: 1 + type: integer + format: int32 + default: 1 + - name: size + in: query + schema: + minimum: 1 + type: integer + format: int32 + default: 10 + - name: truncate + in: query + schema: + type: boolean + description: "Truncate image included in either input, output or metadata" responses: "200": description: Dataset items resource content: application/json: schema: - $ref: '#/components/schemas/DatasetItemPage_Public' + $ref: "#/components/schemas/DatasetItemPage_Public" /v1/private/datasets/{id}/items/experiments/items/output/columns: get: tags: - - Datasets + - Datasets summary: Get dataset items output columns description: Get dataset items output columns operationId: getDatasetItemsOutputColumns parameters: - - name: id - in: path - required: true - schema: - type: string - format: uuid - - name: experiment_ids - in: query - schema: - type: string + - name: id + in: path + required: true + schema: + type: string + format: uuid + - name: experiment_ids + in: query + schema: + type: string responses: "200": description: Dataset item output columns content: application/json: schema: - $ref: '#/components/schemas/PageColumns' + $ref: "#/components/schemas/PageColumns" /v1/private/datasets/items/stream: post: tags: - - Datasets + - Datasets summary: Stream dataset items description: Stream dataset items operationId: streamDatasetItems @@ -858,7 +858,7 @@ paths: content: application/json: schema: - $ref: '#/components/schemas/DatasetItemStreamRequest' + $ref: "#/components/schemas/DatasetItemStreamRequest" responses: "200": description: Dataset items stream or error during process @@ -870,58 +870,58 @@ paths: items: type: string anyOf: - - $ref: '#/components/schemas/DatasetItem' - - $ref: '#/components/schemas/ErrorMessage' + - $ref: "#/components/schemas/DatasetItem" + - $ref: "#/components/schemas/ErrorMessage" /v1/private/experiments: get: tags: - - Experiments + - Experiments summary: Find experiments description: Find experiments operationId: findExperiments parameters: - - name: page - in: query - schema: - minimum: 1 - type: integer - format: int32 - default: 1 - - name: size - in: query - schema: - minimum: 1 - type: integer - format: int32 - default: 10 - - name: datasetId - in: query - schema: - type: string - format: uuid - - name: name - in: query - schema: - type: string - - name: dataset_deleted - in: query - schema: - type: boolean - - name: prompt_id - in: query - schema: - type: string - format: uuid + - name: page + in: query + schema: + minimum: 1 + type: integer + format: int32 + default: 1 + - name: size + in: query + schema: + minimum: 1 + type: integer + format: int32 + default: 10 + - name: datasetId + in: query + schema: + type: string + format: uuid + - name: name + in: query + schema: + type: string + - name: dataset_deleted + in: query + schema: + type: boolean + - name: prompt_id + in: query + schema: + type: string + format: uuid responses: "200": description: Experiments resource content: application/json: schema: - $ref: '#/components/schemas/ExperimentPage_Public' + $ref: "#/components/schemas/ExperimentPage_Public" post: tags: - - Experiments + - Experiments summary: Create experiment description: Create experiment operationId: createExperiment @@ -929,7 +929,7 @@ paths: content: application/json: schema: - $ref: '#/components/schemas/Experiment_Write' + $ref: "#/components/schemas/Experiment_Write" responses: "201": description: Created @@ -943,7 +943,7 @@ paths: /v1/private/experiments/items: post: tags: - - Experiments + - Experiments summary: Create experiment items description: Create experiment items operationId: createExperimentItems @@ -951,14 +951,14 @@ paths: content: application/json: schema: - $ref: '#/components/schemas/ExperimentItemsBatch' + $ref: "#/components/schemas/ExperimentItemsBatch" responses: "204": description: No content /v1/private/experiments/items/delete: post: tags: - - Experiments + - Experiments summary: Delete experiment items description: Delete experiment items operationId: deleteExperimentItems @@ -966,14 +966,14 @@ paths: content: application/json: schema: - $ref: '#/components/schemas/ExperimentItemsDelete' + $ref: "#/components/schemas/ExperimentItemsDelete" responses: "204": description: No content /v1/private/experiments/delete: post: tags: - - Experiments + - Experiments summary: Delete experiments by id description: Delete experiments by id operationId: deleteExperimentsById @@ -981,22 +981,22 @@ paths: content: application/json: schema: - $ref: '#/components/schemas/ExperimentsDelete' + $ref: "#/components/schemas/ExperimentsDelete" responses: "204": description: No content /v1/private/experiments/feedback-scores/names: get: tags: - - Experiments + - Experiments summary: Find Feedback Score names description: Find Feedback Score names operationId: findFeedbackScoreNames parameters: - - name: experiment_ids - in: query - schema: - type: string + - name: experiment_ids + in: query + schema: + type: string responses: "200": description: Feedback Scores resource @@ -1009,34 +1009,34 @@ paths: /v1/private/experiments/{id}: get: tags: - - Experiments + - Experiments summary: Get experiment by id description: Get experiment by id operationId: getExperimentById parameters: - - name: id - in: path - required: true - schema: - type: string - format: uuid + - name: id + in: path + required: true + schema: + type: string + format: uuid responses: "200": description: Experiment resource content: application/json: schema: - $ref: '#/components/schemas/Experiment_Public' + $ref: "#/components/schemas/Experiment_Public" "404": description: Not found content: application/json: schema: - $ref: '#/components/schemas/ErrorMessage_Public' + $ref: "#/components/schemas/ErrorMessage_Public" /v1/private/experiments/retrieve: post: tags: - - Experiments + - Experiments summary: Get experiment by name description: Get experiment by name operationId: getExperimentByName @@ -1044,51 +1044,51 @@ paths: content: application/json: schema: - $ref: '#/components/schemas/Identifier_Public' + $ref: "#/components/schemas/Identifier_Public" responses: "200": description: Experiments resource content: application/json: schema: - $ref: '#/components/schemas/Experiment_Public' + $ref: "#/components/schemas/Experiment_Public" "404": description: Not found content: application/json: schema: - $ref: '#/components/schemas/ErrorMessage_Public' + $ref: "#/components/schemas/ErrorMessage_Public" /v1/private/experiments/items/{id}: get: tags: - - Experiments + - Experiments summary: Get experiment item by id description: Get experiment item by id operationId: getExperimentItemById parameters: - - name: id - in: path - required: true - schema: - type: string - format: uuid + - name: id + in: path + required: true + schema: + type: string + format: uuid responses: "200": description: Experiment item resource content: application/json: schema: - $ref: '#/components/schemas/ExperimentItem_Public' + $ref: "#/components/schemas/ExperimentItem_Public" "404": description: Not found content: application/json: schema: - $ref: '#/components/schemas/ErrorMessage_Public' + $ref: "#/components/schemas/ErrorMessage_Public" /v1/private/experiments/items/stream: post: tags: - - Experiments + - Experiments summary: Stream experiment items description: Stream experiment items operationId: streamExperimentItems @@ -1096,7 +1096,7 @@ paths: content: application/json: schema: - $ref: '#/components/schemas/ExperimentItemStreamRequest' + $ref: "#/components/schemas/ExperimentItemStreamRequest" responses: "200": description: Experiment items stream or error during process @@ -1108,51 +1108,51 @@ paths: items: type: string anyOf: - - $ref: '#/components/schemas/ExperimentItem' - - $ref: '#/components/schemas/ErrorMessage' + - $ref: "#/components/schemas/ExperimentItem" + - $ref: "#/components/schemas/ErrorMessage" /v1/private/feedback-definitions: get: tags: - - Feedback-definitions + - Feedback-definitions summary: Find Feedback definitions description: Find Feedback definitions operationId: findFeedbackDefinitions parameters: - - name: page - in: query - schema: - minimum: 1 - type: integer - format: int32 - default: 1 - - name: size - in: query - schema: - minimum: 1 - type: integer - format: int32 - default: 10 - - name: name - in: query - schema: - type: string - - name: type - in: query - schema: - type: string - enum: - - numerical - - categorical + - name: page + in: query + schema: + minimum: 1 + type: integer + format: int32 + default: 1 + - name: size + in: query + schema: + minimum: 1 + type: integer + format: int32 + default: 10 + - name: name + in: query + schema: + type: string + - name: type + in: query + schema: + type: string + enum: + - numerical + - categorical responses: "200": description: Feedback definitions resource content: application/json: schema: - $ref: '#/components/schemas/FeedbackDefinitionPage_Public' + $ref: "#/components/schemas/FeedbackDefinitionPage_Public" post: tags: - - Feedback-definitions + - Feedback-definitions summary: Create feedback definition description: Get feedback definition operationId: createFeedbackDefinition @@ -1160,7 +1160,7 @@ paths: content: application/json: schema: - $ref: '#/components/schemas/Feedback_Create' + $ref: "#/components/schemas/Feedback_Create" responses: "201": description: Created @@ -1174,65 +1174,65 @@ paths: /v1/private/feedback-definitions/{id}: get: tags: - - Feedback-definitions + - Feedback-definitions summary: Get feedback definition by id description: Get feedback definition by id operationId: getFeedbackDefinitionById parameters: - - name: id - in: path - required: true - schema: - type: string - format: uuid + - name: id + in: path + required: true + schema: + type: string + format: uuid responses: "200": description: Feedback definition resource content: application/json: schema: - $ref: '#/components/schemas/Feedback_Public' + $ref: "#/components/schemas/Feedback_Public" put: tags: - - Feedback-definitions + - Feedback-definitions summary: Update feedback definition by id description: Update feedback definition by id operationId: updateFeedbackDefinition parameters: - - name: id - in: path - required: true - schema: - type: string - format: uuid + - name: id + in: path + required: true + schema: + type: string + format: uuid requestBody: content: application/json: schema: - $ref: '#/components/schemas/Feedback_Update' + $ref: "#/components/schemas/Feedback_Update" responses: "204": description: No Content delete: tags: - - Feedback-definitions + - Feedback-definitions summary: Delete feedback definition by id description: Delete feedback definition by id operationId: deleteFeedbackDefinitionById parameters: - - name: id - in: path - required: true - schema: - type: string - format: uuid + - name: id + in: path + required: true + schema: + type: string + format: uuid responses: "204": description: No Content /v1/private/feedback-definitions/delete: post: tags: - - Feedback-definitions + - Feedback-definitions summary: Delete feedback definitions description: Delete feedback definitions batch operationId: deleteFeedbackDefinitionsBatch @@ -1240,14 +1240,14 @@ paths: content: application/json: schema: - $ref: '#/components/schemas/BatchDelete' + $ref: "#/components/schemas/BatchDelete" responses: "204": description: No Content /v1/private/llm-provider-key/delete: post: tags: - - LlmProviderKey + - LlmProviderKey summary: Delete LLM Provider's ApiKeys description: Delete LLM Provider's ApiKeys batch operationId: deleteLlmProviderApiKeysBatch @@ -1255,14 +1255,14 @@ paths: content: application/json: schema: - $ref: '#/components/schemas/BatchDelete' + $ref: "#/components/schemas/BatchDelete" responses: "204": description: No Content /v1/private/llm-provider-key: get: tags: - - LlmProviderKey + - LlmProviderKey summary: Find LLM Provider's ApiKeys description: Find LLM Provider's ApiKeys operationId: findLlmProviderKeys @@ -1272,10 +1272,10 @@ paths: content: application/json: schema: - $ref: '#/components/schemas/ProjectPage_Public' + $ref: "#/components/schemas/ProjectPage_Public" post: tags: - - LlmProviderKey + - LlmProviderKey summary: Store LLM Provider's ApiKey description: Store LLM Provider's ApiKey operationId: storeLlmProviderApiKey @@ -1283,7 +1283,7 @@ paths: content: application/json: schema: - $ref: '#/components/schemas/ProviderApiKey_Write' + $ref: "#/components/schemas/ProviderApiKey_Write" responses: "201": description: Created @@ -1299,58 +1299,58 @@ paths: content: application/json: schema: - $ref: '#/components/schemas/ErrorMessage' + $ref: "#/components/schemas/ErrorMessage" "403": description: Access forbidden content: application/json: schema: - $ref: '#/components/schemas/ErrorMessage' + $ref: "#/components/schemas/ErrorMessage" /v1/private/llm-provider-key/{id}: get: tags: - - LlmProviderKey + - LlmProviderKey summary: Get LLM Provider's ApiKey by id description: Get LLM Provider's ApiKey by id operationId: getLlmProviderApiKeyById parameters: - - name: id - in: path - required: true - schema: - type: string - format: uuid + - name: id + in: path + required: true + schema: + type: string + format: uuid responses: "200": description: LLMProviderApiKey resource content: application/json: schema: - $ref: '#/components/schemas/ProviderApiKey_Public' + $ref: "#/components/schemas/ProviderApiKey_Public" "404": description: Not found content: application/json: schema: - $ref: '#/components/schemas/ErrorMessage_Public' + $ref: "#/components/schemas/ErrorMessage_Public" patch: tags: - - LlmProviderKey + - LlmProviderKey summary: Update LLM Provider's ApiKey description: Update LLM Provider's ApiKey operationId: updateLlmProviderApiKey parameters: - - name: id - in: path - required: true - schema: - type: string - format: uuid + - name: id + in: path + required: true + schema: + type: string + format: uuid requestBody: content: application/json: schema: - $ref: '#/components/schemas/ProviderApiKeyUpdate' + $ref: "#/components/schemas/ProviderApiKeyUpdate" responses: "204": description: No Content @@ -1359,59 +1359,59 @@ paths: content: application/json: schema: - $ref: '#/components/schemas/ErrorMessage' + $ref: "#/components/schemas/ErrorMessage" "403": description: Access forbidden content: application/json: schema: - $ref: '#/components/schemas/ErrorMessage' + $ref: "#/components/schemas/ErrorMessage" "404": description: Not found content: application/json: schema: - $ref: '#/components/schemas/ErrorMessage' + $ref: "#/components/schemas/ErrorMessage" /v1/private/projects: get: tags: - - Projects + - Projects summary: Find projects description: Find projects operationId: findProjects parameters: - - name: page - in: query - schema: - minimum: 1 - type: integer - format: int32 - default: 1 - - name: size - in: query - schema: - minimum: 1 - type: integer - format: int32 - default: 10 - - name: name - in: query - schema: - type: string - - name: sorting - in: query - schema: - type: string + - name: page + in: query + schema: + minimum: 1 + type: integer + format: int32 + default: 1 + - name: size + in: query + schema: + minimum: 1 + type: integer + format: int32 + default: 10 + - name: name + in: query + schema: + type: string + - name: sorting + in: query + schema: + type: string responses: "200": description: Project resource content: application/json: schema: - $ref: '#/components/schemas/ProjectPage_Public' + $ref: "#/components/schemas/ProjectPage_Public" post: tags: - - Projects + - Projects summary: Create project description: Create project operationId: createProject @@ -1419,7 +1419,7 @@ paths: content: application/json: schema: - $ref: '#/components/schemas/Project_Write' + $ref: "#/components/schemas/Project_Write" responses: "201": description: Created @@ -1435,47 +1435,47 @@ paths: content: application/json: schema: - $ref: '#/components/schemas/ErrorMessage' + $ref: "#/components/schemas/ErrorMessage" "400": description: Bad Request content: application/json: schema: - $ref: '#/components/schemas/ErrorMessage' + $ref: "#/components/schemas/ErrorMessage" /v1/private/projects/{id}: get: tags: - - Projects + - Projects summary: Get project by id description: Get project by id operationId: getProjectById parameters: - - name: id - in: path - required: true - schema: - type: string - format: uuid + - name: id + in: path + required: true + schema: + type: string + format: uuid responses: "200": description: Project resource content: application/json: schema: - $ref: '#/components/schemas/Project_Public' + $ref: "#/components/schemas/Project_Public" delete: tags: - - Projects + - Projects summary: Delete project by id description: Delete project by id operationId: deleteProjectById parameters: - - name: id - in: path - required: true - schema: - type: string - format: uuid + - name: id + in: path + required: true + schema: + type: string + format: uuid responses: "204": description: No Content @@ -1484,25 +1484,25 @@ paths: content: application/json: schema: - $ref: '#/components/schemas/ErrorMessage' + $ref: "#/components/schemas/ErrorMessage" patch: tags: - - Projects + - Projects summary: Update project by id description: Update project by id operationId: updateProject parameters: - - name: id - in: path - required: true - schema: - type: string - format: uuid + - name: id + in: path + required: true + schema: + type: string + format: uuid requestBody: content: application/json: schema: - $ref: '#/components/schemas/ProjectUpdate' + $ref: "#/components/schemas/ProjectUpdate" responses: "204": description: No Content @@ -1511,17 +1511,17 @@ paths: content: application/json: schema: - $ref: '#/components/schemas/ErrorMessage' + $ref: "#/components/schemas/ErrorMessage" "400": description: Bad Request content: application/json: schema: - $ref: '#/components/schemas/ErrorMessage' + $ref: "#/components/schemas/ErrorMessage" /v1/private/projects/delete: post: tags: - - Projects + - Projects summary: Delete projects description: Delete projects batch operationId: deleteProjectsBatch @@ -1529,108 +1529,108 @@ paths: content: application/json: schema: - $ref: '#/components/schemas/BatchDelete' + $ref: "#/components/schemas/BatchDelete" responses: "204": description: No Content /v1/private/projects/feedback-scores/names: get: tags: - - Projects + - Projects summary: Find Feedback Score names By Project Ids description: Find Feedback Score names By Project Ids operationId: findFeedbackScoreNamesByProjectIds parameters: - - name: project_ids - in: query - schema: - type: string + - name: project_ids + in: query + schema: + type: string responses: "200": description: Feedback Scores resource content: application/json: schema: - $ref: '#/components/schemas/FeedbackScoreNames' + $ref: "#/components/schemas/FeedbackScoreNames" /v1/private/projects/{id}/metrics: post: tags: - - Projects + - Projects summary: Get Project Metrics description: Gets specified metrics for a project operationId: getProjectMetrics parameters: - - name: id - in: path - required: true - schema: - type: string - format: uuid + - name: id + in: path + required: true + schema: + type: string + format: uuid requestBody: content: application/json: schema: - $ref: '#/components/schemas/ProjectMetricRequest_Public' + $ref: "#/components/schemas/ProjectMetricRequest_Public" responses: "200": description: Project Metrics content: application/json: schema: - $ref: '#/components/schemas/ProjectMetricResponse_Public' + $ref: "#/components/schemas/ProjectMetricResponse_Public" "400": description: Bad Request content: application/json: schema: - $ref: '#/components/schemas/ErrorMessage_Public' + $ref: "#/components/schemas/ErrorMessage_Public" "404": description: Not Found content: application/json: schema: - $ref: '#/components/schemas/ErrorMessage_Public' + $ref: "#/components/schemas/ErrorMessage_Public" /v1/private/projects/stats: get: tags: - - Projects + - Projects summary: Get Project Stats description: Get Project Stats operationId: getProjectStats parameters: - - name: page - in: query - schema: - minimum: 1 - type: integer - format: int32 - default: 1 - - name: size - in: query - schema: - minimum: 1 - type: integer - format: int32 - default: 10 - - name: name - in: query - schema: - type: string - - name: sorting - in: query - schema: - type: string + - name: page + in: query + schema: + minimum: 1 + type: integer + format: int32 + default: 1 + - name: size + in: query + schema: + minimum: 1 + type: integer + format: int32 + default: 10 + - name: name + in: query + schema: + type: string + - name: sorting + in: query + schema: + type: string responses: "200": description: Project Stats content: application/json: schema: - $ref: '#/components/schemas/ProjectStatsSummary' + $ref: "#/components/schemas/ProjectStatsSummary" /v1/private/projects/retrieve: post: tags: - - Projects + - Projects summary: Retrieve project description: Retrieve project operationId: retrieveProject @@ -1638,68 +1638,68 @@ paths: content: application/json: schema: - $ref: '#/components/schemas/ProjectRetrieve_Detailed' + $ref: "#/components/schemas/ProjectRetrieve_Detailed" responses: "200": description: Project resource content: application/json: schema: - $ref: '#/components/schemas/Project_Detailed' + $ref: "#/components/schemas/Project_Detailed" "422": description: Unprocessable Content content: application/json: schema: - $ref: '#/components/schemas/ErrorMessage_Detailed' + $ref: "#/components/schemas/ErrorMessage_Detailed" "400": description: Bad Request content: application/json: schema: - $ref: '#/components/schemas/ErrorMessage_Detailed' + $ref: "#/components/schemas/ErrorMessage_Detailed" "404": description: Not Found content: application/json: schema: - $ref: '#/components/schemas/ErrorMessage_Detailed' + $ref: "#/components/schemas/ErrorMessage_Detailed" /v1/private/prompts: get: tags: - - Prompts + - Prompts summary: Get prompts description: Get prompts operationId: getPrompts parameters: - - name: page - in: query - schema: - minimum: 1 - type: integer - format: int32 - default: 1 - - name: size - in: query - schema: - minimum: 1 - type: integer - format: int32 - default: 10 - - name: name - in: query - schema: - type: string + - name: page + in: query + schema: + minimum: 1 + type: integer + format: int32 + default: 1 + - name: size + in: query + schema: + minimum: 1 + type: integer + format: int32 + default: 10 + - name: name + in: query + schema: + type: string responses: "200": description: OK content: application/json: schema: - $ref: '#/components/schemas/PromptPage_Public' + $ref: "#/components/schemas/PromptPage_Public" post: tags: - - Prompts + - Prompts summary: Create prompt description: Create prompt operationId: createPrompt @@ -1707,7 +1707,7 @@ paths: content: application/json: schema: - $ref: '#/components/schemas/Prompt_Write' + $ref: "#/components/schemas/Prompt_Write" responses: "201": description: Created @@ -1723,23 +1723,23 @@ paths: content: application/json: schema: - $ref: '#/components/schemas/ErrorMessage' + $ref: "#/components/schemas/ErrorMessage" "400": description: Bad Request content: application/json: schema: - $ref: '#/components/schemas/ErrorMessage' + $ref: "#/components/schemas/ErrorMessage" "409": description: Conflict content: application/json: schema: - $ref: '#/components/schemas/ErrorMessage' + $ref: "#/components/schemas/ErrorMessage" /v1/private/prompts/versions: post: tags: - - Prompts + - Prompts summary: Create prompt version description: Create prompt version operationId: createPromptVersion @@ -1747,77 +1747,77 @@ paths: content: application/json: schema: - $ref: '#/components/schemas/CreatePromptVersion_Detail' + $ref: "#/components/schemas/CreatePromptVersion_Detail" responses: "200": description: OK content: application/json: schema: - $ref: '#/components/schemas/PromptVersion_Detail' + $ref: "#/components/schemas/PromptVersion_Detail" "422": description: Unprocessable Content content: application/json: schema: - $ref: '#/components/schemas/ErrorMessage_Detail' + $ref: "#/components/schemas/ErrorMessage_Detail" "400": description: Bad Request content: application/json: schema: - $ref: '#/components/schemas/ErrorMessage_Detail' + $ref: "#/components/schemas/ErrorMessage_Detail" "409": description: Conflict content: application/json: schema: - $ref: '#/components/schemas/ErrorMessage_Detail' + $ref: "#/components/schemas/ErrorMessage_Detail" /v1/private/prompts/{id}: get: tags: - - Prompts + - Prompts summary: Get prompt by id description: Get prompt by id operationId: getPromptById parameters: - - name: id - in: path - required: true - schema: - type: string - format: uuid + - name: id + in: path + required: true + schema: + type: string + format: uuid responses: "200": description: Prompt resource content: application/json: schema: - $ref: '#/components/schemas/Prompt_Detail' + $ref: "#/components/schemas/Prompt_Detail" "404": description: Not Found content: application/json: schema: - $ref: '#/components/schemas/ErrorMessage_Detail' + $ref: "#/components/schemas/ErrorMessage_Detail" put: tags: - - Prompts + - Prompts summary: Update prompt description: Update prompt operationId: updatePrompt parameters: - - name: id - in: path - required: true - schema: - type: string - format: uuid + - name: id + in: path + required: true + schema: + type: string + format: uuid requestBody: content: application/json: schema: - $ref: '#/components/schemas/Prompt_Updatable' + $ref: "#/components/schemas/Prompt_Updatable" responses: "204": description: No content @@ -1826,45 +1826,45 @@ paths: content: application/json: schema: - $ref: '#/components/schemas/ErrorMessage' + $ref: "#/components/schemas/ErrorMessage" "400": description: Bad Request content: application/json: schema: - $ref: '#/components/schemas/ErrorMessage' + $ref: "#/components/schemas/ErrorMessage" "404": description: Not Found content: application/json: schema: - $ref: '#/components/schemas/ErrorMessage' + $ref: "#/components/schemas/ErrorMessage" "409": description: Conflict content: application/json: schema: - $ref: '#/components/schemas/ErrorMessage' + $ref: "#/components/schemas/ErrorMessage" delete: tags: - - Prompts + - Prompts summary: Delete prompt description: Delete prompt operationId: deletePrompt parameters: - - name: id - in: path - required: true - schema: - type: string - format: uuid + - name: id + in: path + required: true + schema: + type: string + format: uuid responses: "204": description: No content /v1/private/prompts/delete: post: tags: - - Prompts + - Prompts summary: Delete prompts description: Delete prompts batch operationId: deletePromptsBatch @@ -1872,76 +1872,76 @@ paths: content: application/json: schema: - $ref: '#/components/schemas/BatchDelete' + $ref: "#/components/schemas/BatchDelete" responses: "204": description: No Content /v1/private/prompts/versions/{versionId}: get: tags: - - Prompts + - Prompts summary: Get prompt version by id description: Get prompt version by id operationId: getPromptVersionById parameters: - - name: versionId - in: path - required: true - schema: - type: string - format: uuid + - name: versionId + in: path + required: true + schema: + type: string + format: uuid responses: "200": description: Prompt version resource content: application/json: schema: - $ref: '#/components/schemas/PromptVersion_Detail' + $ref: "#/components/schemas/PromptVersion_Detail" "404": description: Not Found content: application/json: schema: - $ref: '#/components/schemas/ErrorMessage_Detail' + $ref: "#/components/schemas/ErrorMessage_Detail" /v1/private/prompts/{id}/versions: get: tags: - - Prompts + - Prompts summary: Get prompt versions description: Get prompt versions operationId: getPromptVersions parameters: - - name: id - in: path - required: true - schema: - type: string - format: uuid - - name: page - in: query - schema: - minimum: 1 - type: integer - format: int32 - default: 1 - - name: size - in: query - schema: - minimum: 1 - type: integer - format: int32 - default: 10 + - name: id + in: path + required: true + schema: + type: string + format: uuid + - name: page + in: query + schema: + minimum: 1 + type: integer + format: int32 + default: 1 + - name: size + in: query + schema: + minimum: 1 + type: integer + format: int32 + default: 10 responses: "200": description: OK content: application/json: schema: - $ref: '#/components/schemas/PromptVersionPage_Public' + $ref: "#/components/schemas/PromptVersionPage_Public" /v1/private/prompts/versions/retrieve: post: tags: - - Prompts + - Prompts summary: Retrieve prompt version description: Retrieve prompt version operationId: retrievePromptVersion @@ -1949,51 +1949,51 @@ paths: content: application/json: schema: - $ref: '#/components/schemas/PromptVersionRetrieve_Detail' + $ref: "#/components/schemas/PromptVersionRetrieve_Detail" responses: "200": description: OK content: application/json: schema: - $ref: '#/components/schemas/PromptVersion_Detail' + $ref: "#/components/schemas/PromptVersion_Detail" "422": description: Unprocessable Content content: application/json: schema: - $ref: '#/components/schemas/ErrorMessage_Detail' + $ref: "#/components/schemas/ErrorMessage_Detail" "400": description: Bad Request content: application/json: schema: - $ref: '#/components/schemas/ErrorMessage_Detail' + $ref: "#/components/schemas/ErrorMessage_Detail" "404": description: Not Found content: application/json: schema: - $ref: '#/components/schemas/ErrorMessage_Detail' + $ref: "#/components/schemas/ErrorMessage_Detail" /v1/private/spans/{id}/comments: post: tags: - - Spans + - Spans summary: Add span comment description: Add span comment operationId: addSpanComment parameters: - - name: id - in: path - required: true - schema: - type: string - format: uuid + - name: id + in: path + required: true + schema: + type: string + format: uuid requestBody: content: application/json: schema: - $ref: '#/components/schemas/Comment' + $ref: "#/components/schemas/Comment" responses: "201": description: Created @@ -2007,90 +2007,90 @@ paths: /v1/private/spans/{id}/feedback-scores: put: tags: - - Spans + - Spans summary: Add span feedback score description: Add span feedback score operationId: addSpanFeedbackScore parameters: - - name: id - in: path - required: true - schema: - type: string - format: uuid + - name: id + in: path + required: true + schema: + type: string + format: uuid requestBody: - content: - application/json: - schema: - $ref: '#/components/schemas/FeedbackScore' - responses: - "204": - description: No Content - /v1/private/spans: - get: - tags: - - Spans - summary: Get spans by project_name or project_id and optionally by trace_id - and/or type - description: Get spans by project_name or project_id and optionally by trace_id - and/or type - operationId: getSpansByProject - parameters: - - name: page - in: query - schema: - minimum: 1 - type: integer - format: int32 - default: 1 - - name: size - in: query - schema: - minimum: 1 - type: integer - format: int32 - default: 10 - - name: project_name - in: query - schema: - type: string - - name: project_id - in: query - schema: - type: string - format: uuid - - name: trace_id - in: query - schema: - type: string - format: uuid - - name: type - in: query - schema: - type: string - enum: - - general - - tool - - llm - - name: filters - in: query - schema: - type: string - - name: truncate - in: query - schema: - type: boolean - description: "Truncate image included in either input, output or metadata" + content: + application/json: + schema: + $ref: "#/components/schemas/FeedbackScore" + responses: + "204": + description: No Content + /v1/private/spans: + get: + tags: + - Spans + summary: Get spans by project_name or project_id and optionally by trace_id + and/or type + description: Get spans by project_name or project_id and optionally by trace_id + and/or type + operationId: getSpansByProject + parameters: + - name: page + in: query + schema: + minimum: 1 + type: integer + format: int32 + default: 1 + - name: size + in: query + schema: + minimum: 1 + type: integer + format: int32 + default: 10 + - name: project_name + in: query + schema: + type: string + - name: project_id + in: query + schema: + type: string + format: uuid + - name: trace_id + in: query + schema: + type: string + format: uuid + - name: type + in: query + schema: + type: string + enum: + - general + - tool + - llm + - name: filters + in: query + schema: + type: string + - name: truncate + in: query + schema: + type: boolean + description: "Truncate image included in either input, output or metadata" responses: "200": description: Spans resource content: application/json: schema: - $ref: '#/components/schemas/SpanPage_Public' + $ref: "#/components/schemas/SpanPage_Public" post: tags: - - Spans + - Spans summary: Create span description: Create span operationId: createSpan @@ -2098,7 +2098,7 @@ paths: content: application/json: schema: - $ref: '#/components/schemas/Span_Write' + $ref: "#/components/schemas/Span_Write" responses: "201": description: Created @@ -2112,7 +2112,7 @@ paths: /v1/private/spans/batch: post: tags: - - Spans + - Spans summary: Create spans description: Create spans operationId: createSpans @@ -2120,49 +2120,49 @@ paths: content: application/json: schema: - $ref: '#/components/schemas/SpanBatch_Write' + $ref: "#/components/schemas/SpanBatch_Write" responses: "204": description: No Content /v1/private/spans/{id}: get: tags: - - Spans + - Spans summary: Get span by id description: Get span by id operationId: getSpanById parameters: - - name: id - in: path - required: true - schema: - type: string - format: uuid + - name: id + in: path + required: true + schema: + type: string + format: uuid responses: "200": description: Span resource content: application/json: schema: - $ref: '#/components/schemas/Span_Public' + $ref: "#/components/schemas/Span_Public" "404": description: Not found content: application/json: schema: - $ref: '#/components/schemas/Span_Public' + $ref: "#/components/schemas/Span_Public" delete: tags: - - Spans + - Spans summary: Delete span by id description: Delete span by id operationId: deleteSpanById parameters: - - name: id - in: path - required: true - schema: - type: string + - name: id + in: path + required: true + schema: + type: string responses: "501": description: Not implemented @@ -2170,22 +2170,22 @@ paths: description: No Content patch: tags: - - Spans + - Spans summary: Update span by id description: Update span by id operationId: updateSpan parameters: - - name: id - in: path - required: true - schema: - type: string - format: uuid + - name: id + in: path + required: true + schema: + type: string + format: uuid requestBody: content: application/json: schema: - $ref: '#/components/schemas/SpanUpdate' + $ref: "#/components/schemas/SpanUpdate" responses: "204": description: No Content @@ -2194,7 +2194,7 @@ paths: /v1/private/spans/comments/delete: post: tags: - - Spans + - Spans summary: Delete span comments description: Delete span comments operationId: deleteSpanComments @@ -2202,53 +2202,53 @@ paths: content: application/json: schema: - $ref: '#/components/schemas/BatchDelete' + $ref: "#/components/schemas/BatchDelete" responses: "204": description: No Content /v1/private/spans/{id}/feedback-scores/delete: post: tags: - - Spans + - Spans summary: Delete span feedback score description: Delete span feedback score operationId: deleteSpanFeedbackScore parameters: - - name: id - in: path - required: true - schema: - type: string - format: uuid + - name: id + in: path + required: true + schema: + type: string + format: uuid requestBody: content: application/json: schema: - $ref: '#/components/schemas/DeleteFeedbackScore' + $ref: "#/components/schemas/DeleteFeedbackScore" responses: "204": description: No Content /v1/private/spans/feedback-scores/names: get: tags: - - Spans + - Spans summary: Find Feedback Score names description: Find Feedback Score names operationId: findFeedbackScoreNames_1 parameters: - - name: project_id - in: query - schema: - type: string - format: uuid - - name: type - in: query - schema: - type: string - enum: - - general - - tool - - llm + - name: project_id + in: query + schema: + type: string + format: uuid + - name: type + in: query + schema: + type: string + enum: + - general + - tool + - llm responses: "200": description: Feedback Scores resource @@ -2261,81 +2261,81 @@ paths: /v1/private/spans/{spanId}/comments/{commentId}: get: tags: - - Spans + - Spans summary: Get span comment description: Get span comment operationId: getSpanComment parameters: - - name: commentId - in: path - required: true - schema: - type: string - format: uuid - - name: spanId - in: path - required: true - schema: - type: string - format: uuid + - name: commentId + in: path + required: true + schema: + type: string + format: uuid + - name: spanId + in: path + required: true + schema: + type: string + format: uuid responses: "200": description: Comment resource content: application/json: schema: - $ref: '#/components/schemas/Comment' + $ref: "#/components/schemas/Comment" "404": description: Not found content: application/json: schema: - $ref: '#/components/schemas/ErrorMessage' + $ref: "#/components/schemas/ErrorMessage" /v1/private/spans/stats: get: tags: - - Spans + - Spans summary: Get span stats description: Get span stats operationId: getSpanStats parameters: - - name: project_id - in: query - schema: - type: string - format: uuid - - name: project_name - in: query - schema: - type: string - - name: trace_id - in: query - schema: - type: string - format: uuid - - name: type - in: query - schema: - type: string - enum: - - general - - tool - - llm - - name: filters - in: query - schema: - type: string + - name: project_id + in: query + schema: + type: string + format: uuid + - name: project_name + in: query + schema: + type: string + - name: trace_id + in: query + schema: + type: string + format: uuid + - name: type + in: query + schema: + type: string + enum: + - general + - tool + - llm + - name: filters + in: query + schema: + type: string responses: "200": description: Span stats resource content: application/json: schema: - $ref: '#/components/schemas/ProjectStats_Public' + $ref: "#/components/schemas/ProjectStats_Public" /v1/private/spans/feedback-scores: put: tags: - - Spans + - Spans summary: Batch feedback scoring for spans description: Batch feedback scoring for spans operationId: scoreBatchOfSpans @@ -2343,14 +2343,14 @@ paths: content: application/json: schema: - $ref: '#/components/schemas/FeedbackScoreBatch' + $ref: "#/components/schemas/FeedbackScoreBatch" responses: "204": description: No Content /v1/private/spans/search: post: tags: - - Spans + - Spans summary: Search spans description: Search spans operationId: searchSpans @@ -2358,7 +2358,7 @@ paths: content: application/json: schema: - $ref: '#/components/schemas/SpanSearchStreamRequest_Public' + $ref: "#/components/schemas/SpanSearchStreamRequest_Public" responses: "200": description: Spans stream or error during process @@ -2370,33 +2370,33 @@ paths: items: type: string anyOf: - - $ref: '#/components/schemas/Span_Public' - - $ref: '#/components/schemas/ErrorMessage_Public' + - $ref: "#/components/schemas/Span_Public" + - $ref: "#/components/schemas/ErrorMessage_Public" "400": description: Bad Request content: application/octet-stream: schema: - $ref: '#/components/schemas/ErrorMessage_Public' + $ref: "#/components/schemas/ErrorMessage_Public" /v1/private/spans/comments/{commentId}: patch: tags: - - Spans + - Spans summary: Update span comment by id description: Update span comment by id operationId: updateSpanComment parameters: - - name: commentId - in: path - required: true - schema: - type: string - format: uuid + - name: commentId + in: path + required: true + schema: + type: string + format: uuid requestBody: content: application/json: schema: - $ref: '#/components/schemas/Comment' + $ref: "#/components/schemas/Comment" responses: "204": description: No Content @@ -2405,22 +2405,22 @@ paths: /v1/private/traces/{id}/comments: post: tags: - - Traces + - Traces summary: Add trace comment description: Add trace comment operationId: addTraceComment parameters: - - name: id - in: path - required: true - schema: - type: string - format: uuid + - name: id + in: path + required: true + schema: + type: string + format: uuid requestBody: content: application/json: schema: - $ref: '#/components/schemas/Comment' + $ref: "#/components/schemas/Comment" responses: "201": description: Created @@ -2434,75 +2434,75 @@ paths: /v1/private/traces/{id}/feedback-scores: put: tags: - - Traces + - Traces summary: Add trace feedback score description: Add trace feedback score operationId: addTraceFeedbackScore parameters: - - name: id - in: path - required: true - schema: - type: string - format: uuid + - name: id + in: path + required: true + schema: + type: string + format: uuid requestBody: content: application/json: schema: - $ref: '#/components/schemas/FeedbackScore' + $ref: "#/components/schemas/FeedbackScore" responses: "204": description: No Content /v1/private/traces: get: tags: - - Traces + - Traces summary: Get traces by project_name or project_id description: Get traces by project_name or project_id operationId: getTracesByProject parameters: - - name: page - in: query - schema: - minimum: 1 - type: integer - format: int32 - default: 1 - - name: size - in: query - schema: - minimum: 1 - type: integer - format: int32 - default: 10 - - name: project_name - in: query - schema: - type: string - - name: project_id - in: query - schema: - type: string - format: uuid - - name: filters - in: query - schema: - type: string - - name: truncate - in: query - schema: - type: boolean - description: "Truncate image included in either input, output or metadata" + - name: page + in: query + schema: + minimum: 1 + type: integer + format: int32 + default: 1 + - name: size + in: query + schema: + minimum: 1 + type: integer + format: int32 + default: 10 + - name: project_name + in: query + schema: + type: string + - name: project_id + in: query + schema: + type: string + format: uuid + - name: filters + in: query + schema: + type: string + - name: truncate + in: query + schema: + type: boolean + description: "Truncate image included in either input, output or metadata" responses: "200": description: Trace resource content: application/json: schema: - $ref: '#/components/schemas/TracePage_Public' + $ref: "#/components/schemas/TracePage_Public" post: tags: - - Traces + - Traces summary: Create trace description: Get trace operationId: createTrace @@ -2510,7 +2510,7 @@ paths: content: application/json: schema: - $ref: '#/components/schemas/Trace_Write' + $ref: "#/components/schemas/Trace_Write" responses: "201": description: Created @@ -2524,7 +2524,7 @@ paths: /v1/private/traces/batch: post: tags: - - Traces + - Traces summary: Create traces description: Create traces operationId: createTraces @@ -2532,72 +2532,72 @@ paths: content: application/json: schema: - $ref: '#/components/schemas/TraceBatch_Write' + $ref: "#/components/schemas/TraceBatch_Write" responses: "204": description: No Content /v1/private/traces/{id}: get: tags: - - Traces + - Traces summary: Get trace by id description: Get trace by id operationId: getTraceById parameters: - - name: id - in: path - required: true - schema: - type: string - format: uuid + - name: id + in: path + required: true + schema: + type: string + format: uuid responses: "200": description: Trace resource content: application/json: schema: - $ref: '#/components/schemas/Trace_Public' + $ref: "#/components/schemas/Trace_Public" delete: tags: - - Traces + - Traces summary: Delete trace by id description: Delete trace by id operationId: deleteTraceById parameters: - - name: id - in: path - required: true - schema: - type: string - format: uuid + - name: id + in: path + required: true + schema: + type: string + format: uuid responses: "204": description: No Content patch: tags: - - Traces + - Traces summary: Update trace by id description: Update trace by id operationId: updateTrace parameters: - - name: id - in: path - required: true - schema: - type: string - format: uuid + - name: id + in: path + required: true + schema: + type: string + format: uuid requestBody: content: application/json: schema: - $ref: '#/components/schemas/TraceUpdate' + $ref: "#/components/schemas/TraceUpdate" responses: "204": description: No Content /v1/private/traces/comments/delete: post: tags: - - Traces + - Traces summary: Delete trace comments description: Delete trace comments operationId: deleteTraceComments @@ -2605,36 +2605,36 @@ paths: content: application/json: schema: - $ref: '#/components/schemas/BatchDelete' + $ref: "#/components/schemas/BatchDelete" responses: "204": description: No Content /v1/private/traces/{id}/feedback-scores/delete: post: tags: - - Traces + - Traces summary: Delete trace feedback score description: Delete trace feedback score operationId: deleteTraceFeedbackScore parameters: - - name: id - in: path - required: true - schema: - type: string - format: uuid + - name: id + in: path + required: true + schema: + type: string + format: uuid requestBody: content: application/json: schema: - $ref: '#/components/schemas/DeleteFeedbackScore' + $ref: "#/components/schemas/DeleteFeedbackScore" responses: "204": description: No Content /v1/private/traces/delete: post: tags: - - Traces + - Traces summary: Delete traces description: Delete traces operationId: deleteTraces @@ -2642,23 +2642,23 @@ paths: content: application/json: schema: - $ref: '#/components/schemas/BatchDelete' + $ref: "#/components/schemas/BatchDelete" responses: "204": description: No Content /v1/private/traces/feedback-scores/names: get: tags: - - Traces + - Traces summary: Find Feedback Score names description: Find Feedback Score names operationId: findFeedbackScoreNames_2 parameters: - - name: project_id - in: query - schema: - type: string - format: uuid + - name: project_id + in: query + schema: + type: string + format: uuid responses: "200": description: Feedback Scores resource @@ -2671,68 +2671,68 @@ paths: /v1/private/traces/stats: get: tags: - - Traces + - Traces summary: Get trace stats description: Get trace stats operationId: getTraceStats parameters: - - name: project_id - in: query - schema: - type: string - format: uuid - - name: project_name - in: query - schema: - type: string - - name: filters - in: query - schema: - type: string + - name: project_id + in: query + schema: + type: string + format: uuid + - name: project_name + in: query + schema: + type: string + - name: filters + in: query + schema: + type: string responses: "200": description: Trace stats resource content: application/json: schema: - $ref: '#/components/schemas/ProjectStats_Public' + $ref: "#/components/schemas/ProjectStats_Public" /v1/private/traces/{traceId}/comments/{commentId}: get: tags: - - Traces + - Traces summary: Get trace comment description: Get trace comment operationId: getTraceComment parameters: - - name: commentId - in: path - required: true - schema: - type: string - format: uuid - - name: traceId - in: path - required: true - schema: - type: string - format: uuid + - name: commentId + in: path + required: true + schema: + type: string + format: uuid + - name: traceId + in: path + required: true + schema: + type: string + format: uuid responses: "200": description: Comment resource content: application/json: schema: - $ref: '#/components/schemas/Comment' + $ref: "#/components/schemas/Comment" "404": description: Not found content: application/json: schema: - $ref: '#/components/schemas/ErrorMessage' + $ref: "#/components/schemas/ErrorMessage" /v1/private/traces/feedback-scores: put: tags: - - Traces + - Traces summary: Batch feedback scoring for traces description: Batch feedback scoring for traces operationId: scoreBatchOfTraces @@ -2740,29 +2740,29 @@ paths: content: application/json: schema: - $ref: '#/components/schemas/FeedbackScoreBatch' + $ref: "#/components/schemas/FeedbackScoreBatch" responses: "204": description: No Content /v1/private/traces/comments/{commentId}: patch: tags: - - Traces + - Traces summary: Update trace comment by id description: Update trace comment by id operationId: updateTraceComment parameters: - - name: commentId - in: path - required: true - schema: - type: string - format: uuid + - name: commentId + in: path + required: true + schema: + type: string + format: uuid requestBody: content: application/json: schema: - $ref: '#/components/schemas/Comment' + $ref: "#/components/schemas/Comment" responses: "204": description: No Content @@ -2802,14 +2802,14 @@ components: bi_information: type: array items: - $ref: '#/components/schemas/BiInformation' + $ref: "#/components/schemas/BiInformation" TraceCountResponse: type: object properties: workspaces_traces_count: type: array items: - $ref: '#/components/schemas/WorkspaceTraceCount' + $ref: "#/components/schemas/WorkspaceTraceCount" WorkspaceTraceCount: type: object properties: @@ -2832,8 +2832,8 @@ components: type: object AutomationRuleEvaluator: required: - - name - - type + - name + - type type: object properties: id: @@ -2865,41 +2865,41 @@ components: type: type: string enum: - - llm_as_judge + - llm_as_judge action: type: string enum: - - evaluator + - evaluator discriminator: propertyName: type mapping: - llm_as_judge: '#/components/schemas/AutomationRuleEvaluatorLlmAsJudge' + llm_as_judge: "#/components/schemas/AutomationRuleEvaluatorLlmAsJudge" AutomationRuleEvaluatorLlmAsJudge: required: - - code - - name - - type + - code + - name + - type type: object allOf: - - $ref: '#/components/schemas/AutomationRuleEvaluator' - - type: object - properties: - code: - $ref: '#/components/schemas/LlmAsJudgeCode' + - $ref: "#/components/schemas/AutomationRuleEvaluator" + - type: object + properties: + code: + $ref: "#/components/schemas/LlmAsJudgeCode" LlmAsJudgeCode: required: - - messages - - model - - schema - - variables + - messages + - model + - schema + - variables type: object properties: model: - $ref: '#/components/schemas/LlmAsJudgeModelParameters' + $ref: "#/components/schemas/LlmAsJudgeModelParameters" messages: type: array items: - $ref: '#/components/schemas/LlmAsJudgeMessage' + $ref: "#/components/schemas/LlmAsJudgeMessage" variables: type: object additionalProperties: @@ -2907,26 +2907,26 @@ components: schema: type: array items: - $ref: '#/components/schemas/LlmAsJudgeOutputSchema' + $ref: "#/components/schemas/LlmAsJudgeOutputSchema" LlmAsJudgeMessage: required: - - content - - role + - content + - role type: object properties: role: type: string enum: - - SYSTEM - - USER - - AI - - TOOL_EXECUTION_RESULT + - SYSTEM + - USER + - AI + - TOOL_EXECUTION_RESULT content: type: string LlmAsJudgeModelParameters: required: - - name - - temperature + - name + - temperature type: object properties: name: @@ -2936,9 +2936,9 @@ components: format: double LlmAsJudgeOutputSchema: required: - - description - - name - - type + - description + - name + - type type: object properties: name: @@ -2946,27 +2946,27 @@ components: type: type: string enum: - - BOOLEAN - - INTEGER - - DOUBLE + - BOOLEAN + - INTEGER + - DOUBLE description: type: string AutomationRuleEvaluatorLlmAsJudge_Write: required: - - code - - name - - type + - code + - name + - type type: object allOf: - - $ref: '#/components/schemas/AutomationRuleEvaluator_Write' - - type: object - properties: - code: - $ref: '#/components/schemas/LlmAsJudgeCode_Write' + - $ref: "#/components/schemas/AutomationRuleEvaluator_Write" + - type: object + properties: + code: + $ref: "#/components/schemas/LlmAsJudgeCode_Write" AutomationRuleEvaluator_Write: required: - - name - - type + - name + - type type: object properties: project_id: @@ -2980,29 +2980,29 @@ components: type: type: string enum: - - llm_as_judge + - llm_as_judge action: type: string enum: - - evaluator + - evaluator discriminator: propertyName: type mapping: - llm_as_judge: '#/components/schemas/AutomationRuleEvaluatorLlmAsJudge_Write' + llm_as_judge: "#/components/schemas/AutomationRuleEvaluatorLlmAsJudge_Write" LlmAsJudgeCode_Write: required: - - messages - - model - - schema - - variables + - messages + - model + - schema + - variables type: object properties: model: - $ref: '#/components/schemas/LlmAsJudgeModelParameters_Write' + $ref: "#/components/schemas/LlmAsJudgeModelParameters_Write" messages: type: array items: - $ref: '#/components/schemas/LlmAsJudgeMessage_Write' + $ref: "#/components/schemas/LlmAsJudgeMessage_Write" variables: type: object additionalProperties: @@ -3010,26 +3010,26 @@ components: schema: type: array items: - $ref: '#/components/schemas/LlmAsJudgeOutputSchema_Write' + $ref: "#/components/schemas/LlmAsJudgeOutputSchema_Write" LlmAsJudgeMessage_Write: required: - - content - - role + - content + - role type: object properties: role: type: string enum: - - SYSTEM - - USER - - AI - - TOOL_EXECUTION_RESULT + - SYSTEM + - USER + - AI + - TOOL_EXECUTION_RESULT content: type: string LlmAsJudgeModelParameters_Write: required: - - name - - temperature + - name + - temperature type: object properties: name: @@ -3039,9 +3039,9 @@ components: format: double LlmAsJudgeOutputSchema_Write: required: - - description - - name - - type + - description + - name + - type type: object properties: name: @@ -3049,14 +3049,14 @@ components: type: type: string enum: - - BOOLEAN - - INTEGER - - DOUBLE + - BOOLEAN + - INTEGER + - DOUBLE description: type: string BatchDelete: required: - - ids + - ids type: object properties: ids: @@ -3069,20 +3069,20 @@ components: format: uuid AutomationRuleEvaluatorLlmAsJudge_Public: required: - - code - - name - - type + - code + - name + - type type: object allOf: - - $ref: '#/components/schemas/AutomationRuleEvaluator_Public' - - type: object - properties: - code: - $ref: '#/components/schemas/LlmAsJudgeCode_Public' + - $ref: "#/components/schemas/AutomationRuleEvaluator_Public" + - type: object + properties: + code: + $ref: "#/components/schemas/LlmAsJudgeCode_Public" AutomationRuleEvaluatorObject_Public: required: - - name - - type + - name + - type type: object properties: id: @@ -3114,15 +3114,15 @@ components: type: type: string enum: - - llm_as_judge + - llm_as_judge action: type: string enum: - - evaluator + - evaluator discriminator: propertyName: type mapping: - llm_as_judge: '#/components/schemas/AutomationRuleEvaluatorLlmAsJudge_Public' + llm_as_judge: "#/components/schemas/AutomationRuleEvaluatorLlmAsJudge_Public" AutomationRuleEvaluatorPage_Public: type: object properties: @@ -3138,21 +3138,21 @@ components: content: type: array items: - $ref: '#/components/schemas/AutomationRuleEvaluatorObject_Public' + $ref: "#/components/schemas/AutomationRuleEvaluatorObject_Public" LlmAsJudgeCode_Public: required: - - messages - - model - - schema - - variables + - messages + - model + - schema + - variables type: object properties: model: - $ref: '#/components/schemas/LlmAsJudgeModelParameters_Public' + $ref: "#/components/schemas/LlmAsJudgeModelParameters_Public" messages: type: array items: - $ref: '#/components/schemas/LlmAsJudgeMessage_Public' + $ref: "#/components/schemas/LlmAsJudgeMessage_Public" variables: type: object additionalProperties: @@ -3160,26 +3160,26 @@ components: schema: type: array items: - $ref: '#/components/schemas/LlmAsJudgeOutputSchema_Public' + $ref: "#/components/schemas/LlmAsJudgeOutputSchema_Public" LlmAsJudgeMessage_Public: required: - - content - - role + - content + - role type: object properties: role: type: string enum: - - SYSTEM - - USER - - AI - - TOOL_EXECUTION_RESULT + - SYSTEM + - USER + - AI + - TOOL_EXECUTION_RESULT content: type: string LlmAsJudgeModelParameters_Public: required: - - name - - temperature + - name + - temperature type: object properties: name: @@ -3189,9 +3189,9 @@ components: format: double LlmAsJudgeOutputSchema_Public: required: - - description - - name - - type + - description + - name + - type type: object properties: name: @@ -3199,15 +3199,15 @@ components: type: type: string enum: - - BOOLEAN - - INTEGER - - DOUBLE + - BOOLEAN + - INTEGER + - DOUBLE description: type: string AutomationRuleEvaluator_Public: required: - - name - - type + - name + - type type: object properties: id: @@ -3239,15 +3239,15 @@ components: type: type: string enum: - - llm_as_judge + - llm_as_judge action: type: string enum: - - evaluator + - evaluator discriminator: propertyName: type mapping: - llm_as_judge: '#/components/schemas/AutomationRuleEvaluatorLlmAsJudge_Public' + llm_as_judge: "#/components/schemas/AutomationRuleEvaluatorLlmAsJudge_Public" LogItem: type: object properties: @@ -3263,11 +3263,11 @@ components: type: string readOnly: true enum: - - INFO - - WARN - - ERROR - - DEBUG - - TRACE + - INFO + - WARN + - ERROR + - DEBUG + - TRACE message: type: string readOnly: true @@ -3283,7 +3283,7 @@ components: content: type: array items: - $ref: '#/components/schemas/LogItem' + $ref: "#/components/schemas/LogItem" page: type: integer format: int32 @@ -3295,15 +3295,15 @@ components: format: int64 AutomationRuleEvaluatorUpdate: required: - - code - - name - - sampling_rate + - code + - name + - sampling_rate type: object properties: name: type: string code: - $ref: '#/components/schemas/LlmAsJudgeCode' + $ref: "#/components/schemas/LlmAsJudgeCode" sampling_rate: type: number format: float @@ -3316,11 +3316,11 @@ components: role: type: string enum: - - system - - user - - assistant - - tool - - function + - system + - user + - assistant + - tool + - function content: type: string name: @@ -3328,11 +3328,11 @@ components: tool_calls: type: array items: - $ref: '#/components/schemas/ToolCall' + $ref: "#/components/schemas/ToolCall" refusal: type: boolean function_call: - $ref: '#/components/schemas/FunctionCall' + $ref: "#/components/schemas/FunctionCall" ChatCompletionChoice: type: object properties: @@ -3340,9 +3340,9 @@ components: type: integer format: int32 message: - $ref: '#/components/schemas/AssistantMessage' + $ref: "#/components/schemas/AssistantMessage" delta: - $ref: '#/components/schemas/Delta' + $ref: "#/components/schemas/Delta" finish_reason: type: string ChatCompletionResponse: @@ -3358,9 +3358,9 @@ components: choices: type: array items: - $ref: '#/components/schemas/ChatCompletionChoice' + $ref: "#/components/schemas/ChatCompletionChoice" usage: - $ref: '#/components/schemas/Usage' + $ref: "#/components/schemas/Usage" system_fingerprint: type: string CompletionTokensDetails: @@ -3375,19 +3375,19 @@ components: role: type: string enum: - - system - - user - - assistant - - tool - - function + - system + - user + - assistant + - tool + - function content: type: string tool_calls: type: array items: - $ref: '#/components/schemas/ToolCall' + $ref: "#/components/schemas/ToolCall" function_call: - $ref: '#/components/schemas/FunctionCall' + $ref: "#/components/schemas/FunctionCall" FunctionCall: type: object properties: @@ -3406,9 +3406,9 @@ components: type: type: string enum: - - function + - function function: - $ref: '#/components/schemas/FunctionCall' + $ref: "#/components/schemas/FunctionCall" Usage: type: object properties: @@ -3422,7 +3422,7 @@ components: type: integer format: int32 completion_tokens_details: - $ref: '#/components/schemas/CompletionTokensDetails' + $ref: "#/components/schemas/CompletionTokensDetails" ChatCompletionRequest: type: object properties: @@ -3431,7 +3431,7 @@ components: messages: type: array items: - $ref: '#/components/schemas/Message' + $ref: "#/components/schemas/Message" temperature: type: number format: double @@ -3444,7 +3444,7 @@ components: stream: type: boolean stream_options: - $ref: '#/components/schemas/StreamOptions' + $ref: "#/components/schemas/StreamOptions" stop: type: array items: @@ -3469,14 +3469,14 @@ components: user: type: string response_format: - $ref: '#/components/schemas/ResponseFormat' + $ref: "#/components/schemas/ResponseFormat" seed: type: integer format: int32 tools: type: array items: - $ref: '#/components/schemas/Tool' + $ref: "#/components/schemas/Tool" tool_choice: type: object parallel_tool_calls: @@ -3484,9 +3484,9 @@ components: functions: type: array items: - $ref: '#/components/schemas/Function' + $ref: "#/components/schemas/Function" function_call: - $ref: '#/components/schemas/FunctionCall' + $ref: "#/components/schemas/FunctionCall" Function: type: object properties: @@ -3497,7 +3497,7 @@ components: strict: type: boolean parameters: - $ref: '#/components/schemas/JsonObjectSchema' + $ref: "#/components/schemas/JsonObjectSchema" JsonObjectSchema: type: object properties: @@ -3508,7 +3508,7 @@ components: properties: type: object additionalProperties: - $ref: '#/components/schemas/JsonSchemaElement' + $ref: "#/components/schemas/JsonSchemaElement" required: type: array items: @@ -3518,7 +3518,7 @@ components: $defs: type: object additionalProperties: - $ref: '#/components/schemas/JsonSchemaElement' + $ref: "#/components/schemas/JsonSchemaElement" JsonSchema: type: object properties: @@ -3527,7 +3527,7 @@ components: strict: type: boolean schema: - $ref: '#/components/schemas/JsonObjectSchema' + $ref: "#/components/schemas/JsonObjectSchema" JsonSchemaElement: type: object properties: @@ -3541,11 +3541,11 @@ components: type: type: string enum: - - text - - json_object - - json_schema + - text + - json_object + - json_schema json_schema: - $ref: '#/components/schemas/JsonSchema' + $ref: "#/components/schemas/JsonSchema" StreamOptions: type: object properties: @@ -3557,12 +3557,12 @@ components: type: type: string enum: - - function + - function function: - $ref: '#/components/schemas/Function' + $ref: "#/components/schemas/Function" Dataset: required: - - name + - name type: object properties: id: @@ -3605,7 +3605,7 @@ components: readOnly: true Dataset_Write: required: - - name + - name type: object properties: id: @@ -3618,7 +3618,7 @@ components: type: string Comment: required: - - text + - text type: object properties: id: @@ -3643,8 +3643,8 @@ components: readOnly: true DatasetItem: required: - - data - - source + - data + - source type: object properties: id: @@ -3659,17 +3659,17 @@ components: source: type: string enum: - - manual - - trace - - span - - sdk + - manual + - trace + - span + - sdk data: - $ref: '#/components/schemas/JsonNode' + $ref: "#/components/schemas/JsonNode" experiment_items: type: array readOnly: true items: - $ref: '#/components/schemas/ExperimentItem' + $ref: "#/components/schemas/ExperimentItem" created_at: type: string format: date-time @@ -3686,7 +3686,7 @@ components: readOnly: true DatasetItemBatch: required: - - items + - items type: object properties: dataset_name: @@ -3702,12 +3702,12 @@ components: minItems: 1 type: array items: - $ref: '#/components/schemas/DatasetItem' + $ref: "#/components/schemas/DatasetItem" ExperimentItem: required: - - dataset_item_id - - experiment_id - - trace_id + - dataset_item_id + - experiment_id + - trace_id type: object properties: id: @@ -3723,19 +3723,19 @@ components: type: string format: uuid input: - $ref: '#/components/schemas/JsonNode' + $ref: "#/components/schemas/JsonNode" output: - $ref: '#/components/schemas/JsonNode' + $ref: "#/components/schemas/JsonNode" feedback_scores: type: array readOnly: true items: - $ref: '#/components/schemas/FeedbackScore' + $ref: "#/components/schemas/FeedbackScore" comments: type: array readOnly: true items: - $ref: '#/components/schemas/Comment' + $ref: "#/components/schemas/Comment" created_at: type: string format: date-time @@ -3752,9 +3752,9 @@ components: readOnly: true FeedbackScore: required: - - name - - source - - value + - name + - source + - value type: object properties: name: @@ -3772,9 +3772,9 @@ components: source: type: string enum: - - ui - - sdk - - online_scoring + - ui + - sdk + - online_scoring created_at: type: string format: date-time @@ -3794,7 +3794,7 @@ components: type: object DatasetItemBatch_Write: required: - - items + - items type: object properties: dataset_name: @@ -3810,11 +3810,11 @@ components: minItems: 1 type: array items: - $ref: '#/components/schemas/DatasetItem_Write' + $ref: "#/components/schemas/DatasetItem_Write" DatasetItem_Write: required: - - data - - source + - data + - source type: object properties: id: @@ -3829,22 +3829,22 @@ components: source: type: string enum: - - manual - - trace - - span - - sdk + - manual + - trace + - span + - sdk data: - $ref: '#/components/schemas/JsonNode' + $ref: "#/components/schemas/JsonNode" DatasetIdentifier: required: - - dataset_name + - dataset_name type: object properties: dataset_name: type: string DatasetItemsDelete: required: - - item_ids + - item_ids type: object properties: item_ids: @@ -3865,12 +3865,12 @@ components: items: type: string enum: - - string - - number - - object - - boolean - - array - - "null" + - string + - number + - object + - boolean + - array + - "null" filter_field_prefix: type: string filterField: @@ -3879,7 +3879,7 @@ components: readOnly: true Comment_Compare: required: - - text + - text type: object properties: id: @@ -3909,7 +3909,7 @@ components: content: type: array items: - $ref: '#/components/schemas/DatasetItem_Compare' + $ref: "#/components/schemas/DatasetItem_Compare" page: type: integer format: int32 @@ -3923,11 +3923,11 @@ components: uniqueItems: true type: array items: - $ref: '#/components/schemas/Column_Compare' + $ref: "#/components/schemas/Column_Compare" DatasetItem_Compare: required: - - data - - source + - data + - source type: object properties: id: @@ -3942,17 +3942,17 @@ components: source: type: string enum: - - manual - - trace - - span - - sdk + - manual + - trace + - span + - sdk data: - $ref: '#/components/schemas/JsonNode' + $ref: "#/components/schemas/JsonNode" experiment_items: type: array readOnly: true items: - $ref: '#/components/schemas/ExperimentItem_Compare' + $ref: "#/components/schemas/ExperimentItem_Compare" created_at: type: string format: date-time @@ -3969,9 +3969,9 @@ components: readOnly: true ExperimentItem_Compare: required: - - dataset_item_id - - experiment_id - - trace_id + - dataset_item_id + - experiment_id + - trace_id type: object properties: id: @@ -3987,19 +3987,19 @@ components: type: string format: uuid input: - $ref: '#/components/schemas/JsonNode_Compare' + $ref: "#/components/schemas/JsonNode_Compare" output: - $ref: '#/components/schemas/JsonNode_Compare' + $ref: "#/components/schemas/JsonNode_Compare" feedback_scores: type: array readOnly: true items: - $ref: '#/components/schemas/FeedbackScore_Compare' + $ref: "#/components/schemas/FeedbackScore_Compare" comments: type: array readOnly: true items: - $ref: '#/components/schemas/Comment_Compare' + $ref: "#/components/schemas/Comment_Compare" created_at: type: string format: date-time @@ -4017,9 +4017,9 @@ components: readOnly: true FeedbackScore_Compare: required: - - name - - source - - value + - name + - source + - value type: object properties: name: @@ -4037,9 +4037,9 @@ components: source: type: string enum: - - ui - - sdk - - online_scoring + - ui + - sdk + - online_scoring created_at: type: string format: date-time @@ -4064,7 +4064,7 @@ components: content: type: array items: - $ref: '#/components/schemas/Dataset_Public' + $ref: "#/components/schemas/Dataset_Public" page: type: integer format: int32 @@ -4076,7 +4076,7 @@ components: format: int64 Dataset_Public: required: - - name + - name type: object properties: id: @@ -4119,15 +4119,15 @@ components: readOnly: true DatasetIdentifier_Public: required: - - dataset_name + - dataset_name type: object properties: dataset_name: type: string DatasetItem_Public: required: - - data - - source + - data + - source type: object properties: id: @@ -4142,17 +4142,17 @@ components: source: type: string enum: - - manual - - trace - - span - - sdk + - manual + - trace + - span + - sdk data: - $ref: '#/components/schemas/JsonNode' + $ref: "#/components/schemas/JsonNode" experiment_items: type: array readOnly: true items: - $ref: '#/components/schemas/ExperimentItem_Public' + $ref: "#/components/schemas/ExperimentItem_Public" created_at: type: string format: date-time @@ -4169,9 +4169,9 @@ components: readOnly: true ExperimentItem_Public: required: - - dataset_item_id - - experiment_id - - trace_id + - dataset_item_id + - experiment_id + - trace_id type: object properties: id: @@ -4211,12 +4211,12 @@ components: items: type: string enum: - - string - - number - - object - - boolean - - array - - "null" + - string + - number + - object + - boolean + - array + - "null" filter_field_prefix: type: string filterField: @@ -4229,7 +4229,7 @@ components: content: type: array items: - $ref: '#/components/schemas/DatasetItem_Public' + $ref: "#/components/schemas/DatasetItem_Public" page: type: integer format: int32 @@ -4243,7 +4243,7 @@ components: uniqueItems: true type: array items: - $ref: '#/components/schemas/Column_Public' + $ref: "#/components/schemas/Column_Public" Column: type: object properties: @@ -4255,12 +4255,12 @@ components: items: type: string enum: - - string - - number - - object - - boolean - - array - - "null" + - string + - number + - object + - boolean + - array + - "null" filter_field_prefix: type: string filterField: @@ -4273,7 +4273,7 @@ components: columns: type: array items: - $ref: '#/components/schemas/Column' + $ref: "#/components/schemas/Column" ChunkedOutputJsonNode: type: object properties: @@ -4286,7 +4286,7 @@ components: type: boolean DatasetItemStreamRequest: required: - - dataset_name + - dataset_name type: object properties: dataset_name: @@ -4299,7 +4299,7 @@ components: format: int32 DatasetUpdate: required: - - name + - name type: object properties: name: @@ -4309,7 +4309,7 @@ components: type: string Experiment: required: - - dataset_name + - dataset_name type: object properties: id: @@ -4324,17 +4324,17 @@ components: name: type: string metadata: - $ref: '#/components/schemas/JsonNode' + $ref: "#/components/schemas/JsonNode" feedback_scores: type: array readOnly: true items: - $ref: '#/components/schemas/FeedbackScoreAverage' + $ref: "#/components/schemas/FeedbackScoreAverage" comments: type: array readOnly: true items: - $ref: '#/components/schemas/Comment' + $ref: "#/components/schemas/Comment" trace_count: type: integer format: int64 @@ -4354,15 +4354,15 @@ components: type: string readOnly: true prompt_version: - $ref: '#/components/schemas/PromptVersionLink' + $ref: "#/components/schemas/PromptVersionLink" prompt_versions: type: array items: - $ref: '#/components/schemas/PromptVersionLink' + $ref: "#/components/schemas/PromptVersionLink" FeedbackScoreAverage: required: - - name - - value + - name + - value type: object properties: name: @@ -4371,7 +4371,7 @@ components: type: number PromptVersionLink: required: - - id + - id type: object properties: id: @@ -4386,7 +4386,7 @@ components: readOnly: true Experiment_Write: required: - - dataset_name + - dataset_name type: object properties: id: @@ -4397,18 +4397,18 @@ components: name: type: string metadata: - $ref: '#/components/schemas/JsonNode_Write' + $ref: "#/components/schemas/JsonNode_Write" prompt_version: - $ref: '#/components/schemas/PromptVersionLink_Write' + $ref: "#/components/schemas/PromptVersionLink_Write" prompt_versions: type: array items: - $ref: '#/components/schemas/PromptVersionLink_Write' + $ref: "#/components/schemas/PromptVersionLink_Write" JsonNode_Write: type: object PromptVersionLink_Write: required: - - id + - id type: object properties: id: @@ -4416,7 +4416,7 @@ components: format: uuid ExperimentItemsBatch: required: - - experiment_items + - experiment_items type: object properties: experiment_items: @@ -4425,10 +4425,10 @@ components: uniqueItems: true type: array items: - $ref: '#/components/schemas/ExperimentItem' + $ref: "#/components/schemas/ExperimentItem" ExperimentItemsDelete: required: - - ids + - ids type: object properties: ids: @@ -4441,7 +4441,7 @@ components: format: uuid ExperimentsDelete: required: - - ids + - ids type: object properties: ids: @@ -4454,7 +4454,7 @@ components: format: uuid Comment_Public: required: - - text + - text type: object properties: id: @@ -4493,10 +4493,10 @@ components: content: type: array items: - $ref: '#/components/schemas/Experiment_Public' + $ref: "#/components/schemas/Experiment_Public" Experiment_Public: required: - - dataset_name + - dataset_name type: object properties: id: @@ -4511,17 +4511,17 @@ components: name: type: string metadata: - $ref: '#/components/schemas/JsonNode_Public' + $ref: "#/components/schemas/JsonNode_Public" feedback_scores: type: array readOnly: true items: - $ref: '#/components/schemas/FeedbackScoreAverage_Public' + $ref: "#/components/schemas/FeedbackScoreAverage_Public" comments: type: array readOnly: true items: - $ref: '#/components/schemas/Comment_Public' + $ref: "#/components/schemas/Comment_Public" trace_count: type: integer format: int64 @@ -4541,15 +4541,15 @@ components: type: string readOnly: true prompt_version: - $ref: '#/components/schemas/PromptVersionLink_Public' + $ref: "#/components/schemas/PromptVersionLink_Public" prompt_versions: type: array items: - $ref: '#/components/schemas/PromptVersionLink_Public' + $ref: "#/components/schemas/PromptVersionLink_Public" FeedbackScoreAverage_Public: required: - - name - - value + - name + - value type: object properties: name: @@ -4561,7 +4561,7 @@ components: type: object PromptVersionLink_Public: required: - - id + - id type: object properties: id: @@ -4586,14 +4586,14 @@ components: type: string Identifier_Public: required: - - name + - name type: object properties: name: type: string ExperimentItemStreamRequest: required: - - experiment_name + - experiment_name type: object properties: experiment_name: @@ -4610,33 +4610,33 @@ components: default: true CategoricalFeedbackDefinition: required: - - details - - name - - type + - details + - name + - type type: object allOf: - - $ref: '#/components/schemas/Feedback' - - type: object - properties: - details: - $ref: '#/components/schemas/CategoricalFeedbackDetail' - created_at: - type: string - format: date-time - readOnly: true - created_by: - type: string - readOnly: true - last_updated_at: - type: string - format: date-time - readOnly: true - last_updated_by: - type: string - readOnly: true + - $ref: "#/components/schemas/Feedback" + - type: object + properties: + details: + $ref: "#/components/schemas/CategoricalFeedbackDetail" + created_at: + type: string + format: date-time + readOnly: true + created_by: + type: string + readOnly: true + last_updated_at: + type: string + format: date-time + readOnly: true + last_updated_by: + type: string + readOnly: true CategoricalFeedbackDetail: required: - - categories + - categories type: object properties: categories: @@ -4646,8 +4646,8 @@ components: format: double Feedback: required: - - name - - type + - name + - type type: object properties: id: @@ -4673,43 +4673,43 @@ components: type: type: string enum: - - numerical - - categorical + - numerical + - categorical discriminator: propertyName: type mapping: - numerical: '#/components/schemas/NumericalFeedbackDefinition' - categorical: '#/components/schemas/CategoricalFeedbackDefinition' + numerical: "#/components/schemas/NumericalFeedbackDefinition" + categorical: "#/components/schemas/CategoricalFeedbackDefinition" NumericalFeedbackDefinition: required: - - details - - name - - type + - details + - name + - type type: object allOf: - - $ref: '#/components/schemas/Feedback' - - type: object - properties: - details: - $ref: '#/components/schemas/NumericalFeedbackDetail' - created_at: - type: string - format: date-time - readOnly: true - created_by: - type: string - readOnly: true - last_updated_at: - type: string - format: date-time - readOnly: true - last_updated_by: - type: string - readOnly: true + - $ref: "#/components/schemas/Feedback" + - type: object + properties: + details: + $ref: "#/components/schemas/NumericalFeedbackDetail" + created_at: + type: string + format: date-time + readOnly: true + created_by: + type: string + readOnly: true + last_updated_at: + type: string + format: date-time + readOnly: true + last_updated_by: + type: string + readOnly: true NumericalFeedbackDetail: required: - - max - - min + - max + - min type: object properties: max: @@ -4718,19 +4718,19 @@ components: type: number CategoricalFeedbackDefinition_Create: required: - - details - - name - - type + - details + - name + - type type: object allOf: - - $ref: '#/components/schemas/Feedback_Create' - - type: object - properties: - details: - $ref: '#/components/schemas/CategoricalFeedbackDetail_Create' + - $ref: "#/components/schemas/Feedback_Create" + - type: object + properties: + details: + $ref: "#/components/schemas/CategoricalFeedbackDetail_Create" CategoricalFeedbackDetail_Create: required: - - categories + - categories type: object properties: categories: @@ -4740,8 +4740,8 @@ components: format: double Feedback_Create: required: - - name - - type + - name + - type type: object properties: id: @@ -4753,29 +4753,29 @@ components: type: type: string enum: - - numerical - - categorical + - numerical + - categorical discriminator: propertyName: type mapping: - numerical: '#/components/schemas/NumericalFeedbackDefinition_Create' - categorical: '#/components/schemas/CategoricalFeedbackDefinition_Create' + numerical: "#/components/schemas/NumericalFeedbackDefinition_Create" + categorical: "#/components/schemas/CategoricalFeedbackDefinition_Create" NumericalFeedbackDefinition_Create: required: - - details - - name - - type + - details + - name + - type type: object allOf: - - $ref: '#/components/schemas/Feedback_Create' - - type: object - properties: - details: - $ref: '#/components/schemas/NumericalFeedbackDetail_Create' + - $ref: "#/components/schemas/Feedback_Create" + - type: object + properties: + details: + $ref: "#/components/schemas/NumericalFeedbackDetail_Create" NumericalFeedbackDetail_Create: required: - - max - - min + - max + - min type: object properties: max: @@ -4784,33 +4784,33 @@ components: type: number CategoricalFeedbackDefinition_Public: required: - - details - - name - - type + - details + - name + - type type: object allOf: - - $ref: '#/components/schemas/Feedback_Public' - - type: object - properties: - details: - $ref: '#/components/schemas/CategoricalFeedbackDetail_Public' - created_at: - type: string - format: date-time - readOnly: true - created_by: - type: string - readOnly: true - last_updated_at: - type: string - format: date-time - readOnly: true - last_updated_by: - type: string - readOnly: true + - $ref: "#/components/schemas/Feedback_Public" + - type: object + properties: + details: + $ref: "#/components/schemas/CategoricalFeedbackDetail_Public" + created_at: + type: string + format: date-time + readOnly: true + created_by: + type: string + readOnly: true + last_updated_at: + type: string + format: date-time + readOnly: true + last_updated_by: + type: string + readOnly: true CategoricalFeedbackDetail_Public: required: - - categories + - categories type: object properties: categories: @@ -4833,11 +4833,11 @@ components: content: type: array items: - $ref: '#/components/schemas/FeedbackObject_Public' + $ref: "#/components/schemas/FeedbackObject_Public" FeedbackObject_Public: required: - - name - - type + - name + - type type: object properties: id: @@ -4863,43 +4863,43 @@ components: type: type: string enum: - - numerical - - categorical + - numerical + - categorical discriminator: propertyName: type mapping: - numerical: '#/components/schemas/NumericalFeedbackDefinition_Public' - categorical: '#/components/schemas/CategoricalFeedbackDefinition_Public' + numerical: "#/components/schemas/NumericalFeedbackDefinition_Public" + categorical: "#/components/schemas/CategoricalFeedbackDefinition_Public" NumericalFeedbackDefinition_Public: required: - - details - - name - - type + - details + - name + - type type: object allOf: - - $ref: '#/components/schemas/Feedback_Public' - - type: object - properties: - details: - $ref: '#/components/schemas/NumericalFeedbackDetail_Public' - created_at: - type: string - format: date-time - readOnly: true - created_by: - type: string - readOnly: true - last_updated_at: - type: string - format: date-time - readOnly: true - last_updated_by: - type: string - readOnly: true + - $ref: "#/components/schemas/Feedback_Public" + - type: object + properties: + details: + $ref: "#/components/schemas/NumericalFeedbackDetail_Public" + created_at: + type: string + format: date-time + readOnly: true + created_by: + type: string + readOnly: true + last_updated_at: + type: string + format: date-time + readOnly: true + last_updated_by: + type: string + readOnly: true NumericalFeedbackDetail_Public: required: - - max - - min + - max + - min type: object properties: max: @@ -4908,8 +4908,8 @@ components: type: number Feedback_Public: required: - - name - - type + - name + - type type: object properties: id: @@ -4935,28 +4935,28 @@ components: type: type: string enum: - - numerical - - categorical + - numerical + - categorical discriminator: propertyName: type mapping: - numerical: '#/components/schemas/NumericalFeedbackDefinition_Public' - categorical: '#/components/schemas/CategoricalFeedbackDefinition_Public' + numerical: "#/components/schemas/NumericalFeedbackDefinition_Public" + categorical: "#/components/schemas/CategoricalFeedbackDefinition_Public" CategoricalFeedbackDefinition_Update: required: - - details - - name - - type + - details + - name + - type type: object allOf: - - $ref: '#/components/schemas/Feedback_Update' - - type: object - properties: - details: - $ref: '#/components/schemas/CategoricalFeedbackDetail_Update' + - $ref: "#/components/schemas/Feedback_Update" + - type: object + properties: + details: + $ref: "#/components/schemas/CategoricalFeedbackDetail_Update" CategoricalFeedbackDetail_Update: required: - - categories + - categories type: object properties: categories: @@ -4966,8 +4966,8 @@ components: format: double Feedback_Update: required: - - name - - type + - name + - type type: object properties: id: @@ -4979,29 +4979,29 @@ components: type: type: string enum: - - numerical - - categorical + - numerical + - categorical discriminator: propertyName: type mapping: - numerical: '#/components/schemas/NumericalFeedbackDefinition_Update' - categorical: '#/components/schemas/CategoricalFeedbackDefinition_Update' + numerical: "#/components/schemas/NumericalFeedbackDefinition_Update" + categorical: "#/components/schemas/CategoricalFeedbackDefinition_Update" NumericalFeedbackDefinition_Update: required: - - details - - name - - type + - details + - name + - type type: object allOf: - - $ref: '#/components/schemas/Feedback_Update' - - type: object - properties: - details: - $ref: '#/components/schemas/NumericalFeedbackDetail_Update' + - $ref: "#/components/schemas/Feedback_Update" + - type: object + properties: + details: + $ref: "#/components/schemas/NumericalFeedbackDetail_Update" NumericalFeedbackDetail_Update: required: - - max - - min + - max + - min type: object properties: max: @@ -5023,15 +5023,15 @@ components: content: type: array items: - $ref: '#/components/schemas/Project_Public' + $ref: "#/components/schemas/Project_Public" sortableBy: type: array items: type: string ProviderApiKey_Public: required: - - api_key - - provider + - api_key + - provider type: object properties: id: @@ -5041,9 +5041,9 @@ components: provider: type: string enum: - - openai - - anthropic - - gemini + - openai + - anthropic + - gemini api_key: type: string name: @@ -5066,8 +5066,8 @@ components: readOnly: true ProviderApiKey: required: - - api_key - - provider + - api_key + - provider type: object properties: id: @@ -5077,9 +5077,9 @@ components: provider: type: string enum: - - openai - - anthropic - - gemini + - openai + - anthropic + - gemini api_key: type: string name: @@ -5102,16 +5102,16 @@ components: readOnly: true ProviderApiKey_Write: required: - - api_key - - provider + - api_key + - provider type: object properties: provider: type: string enum: - - openai - - anthropic - - gemini + - openai + - anthropic + - gemini api_key: type: string name: @@ -5120,7 +5120,7 @@ components: type: string ProviderApiKeyUpdate: required: - - api_key + - api_key type: object properties: api_key: @@ -5140,7 +5140,7 @@ components: type: number Project: required: - - name + - name type: object properties: id: @@ -5173,9 +5173,9 @@ components: type: array readOnly: true items: - $ref: '#/components/schemas/FeedbackScoreAverage' + $ref: "#/components/schemas/FeedbackScoreAverage" duration: - $ref: '#/components/schemas/PercentageValues' + $ref: "#/components/schemas/PercentageValues" total_estimated_cost: type: number format: double @@ -5189,7 +5189,7 @@ components: readOnly: true Project_Write: required: - - name + - name type: object properties: name: @@ -5198,7 +5198,7 @@ components: type: string Project_Public: required: - - name + - name type: object properties: id: @@ -5233,7 +5233,7 @@ components: scores: type: array items: - $ref: '#/components/schemas/ScoreName' + $ref: "#/components/schemas/ScoreName" ScoreName: type: object properties: @@ -5241,7 +5241,7 @@ components: type: string DataPointNumber_Public: required: - - time + - time type: object properties: time: @@ -5258,21 +5258,21 @@ components: metric_type: type: string enum: - - FEEDBACK_SCORES - - TRACE_COUNT - - TOKEN_USAGE - - DURATION - - COST + - FEEDBACK_SCORES + - TRACE_COUNT + - TOKEN_USAGE + - DURATION + - COST interval: type: string enum: - - HOURLY - - DAILY - - WEEKLY + - HOURLY + - DAILY + - WEEKLY results: type: array items: - $ref: '#/components/schemas/ResultsNumber_Public' + $ref: "#/components/schemas/ResultsNumber_Public" ResultsNumber_Public: type: object properties: @@ -5281,24 +5281,24 @@ components: data: type: array items: - $ref: '#/components/schemas/DataPointNumber_Public' + $ref: "#/components/schemas/DataPointNumber_Public" ProjectMetricRequest_Public: type: object properties: metric_type: type: string enum: - - FEEDBACK_SCORES - - TRACE_COUNT - - TOKEN_USAGE - - DURATION - - COST + - FEEDBACK_SCORES + - TRACE_COUNT + - TOKEN_USAGE + - DURATION + - COST interval: type: string enum: - - HOURLY - - DAILY - - WEEKLY + - HOURLY + - DAILY + - WEEKLY interval_start: type: string format: date-time @@ -5311,7 +5311,7 @@ components: content: type: array items: - $ref: '#/components/schemas/ProjectStatsSummaryItem' + $ref: "#/components/schemas/ProjectStatsSummaryItem" ProjectStatsSummaryItem: type: object properties: @@ -5321,9 +5321,9 @@ components: feedback_scores: type: array items: - $ref: '#/components/schemas/FeedbackScoreAverage' + $ref: "#/components/schemas/FeedbackScoreAverage" duration: - $ref: '#/components/schemas/PercentageValues' + $ref: "#/components/schemas/PercentageValues" total_estimated_cost: type: number format: double @@ -5334,8 +5334,8 @@ components: format: double FeedbackScoreAverage_Detailed: required: - - name - - value + - name + - value type: object properties: name: @@ -5355,7 +5355,7 @@ components: readOnly: true Project_Detailed: required: - - name + - name type: object properties: id: @@ -5388,9 +5388,9 @@ components: type: array readOnly: true items: - $ref: '#/components/schemas/FeedbackScoreAverage_Detailed' + $ref: "#/components/schemas/FeedbackScoreAverage_Detailed" duration: - $ref: '#/components/schemas/PercentageValues_Detailed' + $ref: "#/components/schemas/PercentageValues_Detailed" total_estimated_cost: type: number format: double @@ -5411,7 +5411,7 @@ components: type: string ProjectRetrieve_Detailed: required: - - name + - name type: object properties: name: @@ -5426,7 +5426,7 @@ components: type: string Prompt: required: - - name + - name type: object properties: id: @@ -5441,14 +5441,14 @@ components: pattern: (?s)^\s*(\S.*\S|\S)\s*$ type: string metadata: - $ref: '#/components/schemas/JsonNode' + $ref: "#/components/schemas/JsonNode" change_description: type: string type: type: string enum: - - mustache - - jinja2 + - mustache + - jinja2 created_at: type: string format: date-time @@ -5468,10 +5468,10 @@ components: format: int64 readOnly: true latest_version: - $ref: '#/components/schemas/PromptVersion' + $ref: "#/components/schemas/PromptVersion" PromptVersion: required: - - template + - template type: object properties: id: @@ -5490,12 +5490,12 @@ components: template: type: string metadata: - $ref: '#/components/schemas/JsonNode' + $ref: "#/components/schemas/JsonNode" type: type: string enum: - - mustache - - jinja2 + - mustache + - jinja2 change_description: type: string variables: @@ -5515,7 +5515,7 @@ components: readOnly: true Prompt_Write: required: - - name + - name type: object properties: id: @@ -5530,19 +5530,19 @@ components: pattern: (?s)^\s*(\S.*\S|\S)\s*$ type: string metadata: - $ref: '#/components/schemas/JsonNode_Write' + $ref: "#/components/schemas/JsonNode_Write" change_description: type: string type: type: string enum: - - mustache - - jinja2 + - mustache + - jinja2 JsonNode_Detail: type: object PromptVersion_Detail: required: - - template + - template type: object properties: id: @@ -5561,12 +5561,12 @@ components: template: type: string metadata: - $ref: '#/components/schemas/JsonNode_Detail' + $ref: "#/components/schemas/JsonNode_Detail" type: type: string enum: - - mustache - - jinja2 + - mustache + - jinja2 change_description: type: string variables: @@ -5595,17 +5595,17 @@ components: type: string CreatePromptVersion_Detail: required: - - name - - version + - name + - version type: object properties: name: type: string version: - $ref: '#/components/schemas/PromptVersion_Detail' + $ref: "#/components/schemas/PromptVersion_Detail" Prompt_Detail: required: - - name + - name type: object properties: id: @@ -5635,7 +5635,7 @@ components: format: int64 readOnly: true latest_version: - $ref: '#/components/schemas/PromptVersion_Detail' + $ref: "#/components/schemas/PromptVersion_Detail" PromptVersionPage_Public: type: object properties: @@ -5651,10 +5651,10 @@ components: content: type: array items: - $ref: '#/components/schemas/PromptVersion_Public' + $ref: "#/components/schemas/PromptVersion_Public" PromptVersion_Public: required: - - template + - template type: object properties: id: @@ -5673,12 +5673,12 @@ components: template: type: string metadata: - $ref: '#/components/schemas/JsonNode_Public' + $ref: "#/components/schemas/JsonNode_Public" type: type: string enum: - - mustache - - jinja2 + - mustache + - jinja2 change_description: type: string created_at: @@ -5703,10 +5703,10 @@ components: content: type: array items: - $ref: '#/components/schemas/Prompt_Public' + $ref: "#/components/schemas/Prompt_Public" Prompt_Public: required: - - name + - name type: object properties: id: @@ -5737,7 +5737,7 @@ components: readOnly: true PromptVersionRetrieve_Detail: required: - - name + - name type: object properties: name: @@ -5746,7 +5746,7 @@ components: type: string Prompt_Updatable: required: - - name + - name type: object properties: name: @@ -5756,8 +5756,8 @@ components: type: string ErrorInfo: required: - - exception_type - - traceback + - exception_type + - traceback type: object properties: exception_type: @@ -5768,10 +5768,10 @@ components: type: string Span: required: - - name - - start_time - - trace_id - - type + - name + - start_time + - trace_id + - type type: object properties: id: @@ -5796,9 +5796,9 @@ components: type: type: string enum: - - general - - tool - - llm + - general + - tool + - llm start_time: type: string format: date-time @@ -5806,11 +5806,11 @@ components: type: string format: date-time input: - $ref: '#/components/schemas/JsonNode' + $ref: "#/components/schemas/JsonNode" output: - $ref: '#/components/schemas/JsonNode' + $ref: "#/components/schemas/JsonNode" metadata: - $ref: '#/components/schemas/JsonNode' + $ref: "#/components/schemas/JsonNode" model: type: string provider: @@ -5826,7 +5826,7 @@ components: type: integer format: int32 error_info: - $ref: '#/components/schemas/ErrorInfo' + $ref: "#/components/schemas/ErrorInfo" created_at: type: string format: date-time @@ -5845,12 +5845,12 @@ components: type: array readOnly: true items: - $ref: '#/components/schemas/FeedbackScore' + $ref: "#/components/schemas/FeedbackScore" comments: type: array readOnly: true items: - $ref: '#/components/schemas/Comment' + $ref: "#/components/schemas/Comment" total_estimated_cost: minimum: 0.0 exclusiveMinimum: false @@ -5865,8 +5865,8 @@ components: readOnly: true ErrorInfo_Write: required: - - exception_type - - traceback + - exception_type + - traceback type: object properties: exception_type: @@ -5877,10 +5877,10 @@ components: type: string Span_Write: required: - - name - - start_time - - trace_id - - type + - name + - start_time + - trace_id + - type type: object properties: id: @@ -5901,9 +5901,9 @@ components: type: type: string enum: - - general - - tool - - llm + - general + - tool + - llm start_time: type: string format: date-time @@ -5911,11 +5911,11 @@ components: type: string format: date-time input: - $ref: '#/components/schemas/JsonNode_Write' + $ref: "#/components/schemas/JsonNode_Write" output: - $ref: '#/components/schemas/JsonNode_Write' + $ref: "#/components/schemas/JsonNode_Write" metadata: - $ref: '#/components/schemas/JsonNode_Write' + $ref: "#/components/schemas/JsonNode_Write" model: type: string provider: @@ -5931,7 +5931,7 @@ components: type: integer format: int32 error_info: - $ref: '#/components/schemas/ErrorInfo_Write' + $ref: "#/components/schemas/ErrorInfo_Write" total_estimated_cost: minimum: 0.0 exclusiveMinimum: false @@ -5940,7 +5940,7 @@ components: type: string SpanBatch: required: - - spans + - spans type: object properties: spans: @@ -5948,10 +5948,10 @@ components: minItems: 1 type: array items: - $ref: '#/components/schemas/Span' + $ref: "#/components/schemas/Span" SpanBatch_Write: required: - - spans + - spans type: object properties: spans: @@ -5959,18 +5959,18 @@ components: minItems: 1 type: array items: - $ref: '#/components/schemas/Span_Write' + $ref: "#/components/schemas/Span_Write" DeleteFeedbackScore: required: - - name + - name type: object properties: name: type: string ErrorInfo_Public: required: - - exception_type - - traceback + - exception_type + - traceback type: object properties: exception_type: @@ -5981,9 +5981,9 @@ components: type: string FeedbackScore_Public: required: - - name - - source - - value + - name + - source + - value type: object properties: name: @@ -6001,9 +6001,9 @@ components: source: type: string enum: - - ui - - sdk - - online_scoring + - ui + - sdk + - online_scoring created_at: type: string format: date-time @@ -6021,10 +6021,10 @@ components: readOnly: true Span_Public: required: - - name - - start_time - - trace_id - - type + - name + - start_time + - trace_id + - type type: object properties: id: @@ -6045,9 +6045,9 @@ components: type: type: string enum: - - general - - tool - - llm + - general + - tool + - llm start_time: type: string format: date-time @@ -6055,11 +6055,11 @@ components: type: string format: date-time input: - $ref: '#/components/schemas/JsonNode_Public' + $ref: "#/components/schemas/JsonNode_Public" output: - $ref: '#/components/schemas/JsonNode_Public' + $ref: "#/components/schemas/JsonNode_Public" metadata: - $ref: '#/components/schemas/JsonNode_Public' + $ref: "#/components/schemas/JsonNode_Public" model: type: string provider: @@ -6075,7 +6075,7 @@ components: type: integer format: int32 error_info: - $ref: '#/components/schemas/ErrorInfo_Public' + $ref: "#/components/schemas/ErrorInfo_Public" created_at: type: string format: date-time @@ -6094,12 +6094,12 @@ components: type: array readOnly: true items: - $ref: '#/components/schemas/FeedbackScore_Public' + $ref: "#/components/schemas/FeedbackScore_Public" comments: type: array readOnly: true items: - $ref: '#/components/schemas/Comment_Public' + $ref: "#/components/schemas/Comment_Public" total_estimated_cost: minimum: 0.0 exclusiveMinimum: false @@ -6127,33 +6127,33 @@ components: content: type: array items: - $ref: '#/components/schemas/Span_Public' + $ref: "#/components/schemas/Span_Public" AvgValueStat_Public: type: object allOf: - - $ref: '#/components/schemas/ProjectStatItemObject_Public' - - type: object - properties: - value: - type: number - format: double + - $ref: "#/components/schemas/ProjectStatItemObject_Public" + - type: object + properties: + value: + type: number + format: double CountValueStat_Public: type: object allOf: - - $ref: '#/components/schemas/ProjectStatItemObject_Public' - - type: object - properties: - value: - type: integer - format: int64 + - $ref: "#/components/schemas/ProjectStatItemObject_Public" + - type: object + properties: + value: + type: integer + format: int64 PercentageValueStat_Public: type: object allOf: - - $ref: '#/components/schemas/ProjectStatItemObject_Public' - - type: object - properties: - value: - $ref: '#/components/schemas/PercentageValues_Public' + - $ref: "#/components/schemas/ProjectStatItemObject_Public" + - type: object + properties: + value: + $ref: "#/components/schemas/PercentageValues_Public" PercentageValues_Public: type: object properties: @@ -6171,25 +6171,25 @@ components: type: type: string enum: - - COUNT - - PERCENTAGE - - AVG + - COUNT + - PERCENTAGE + - AVG discriminator: propertyName: type mapping: - PERCENTAGE: '#/components/schemas/PercentageValueStat_Public' - COUNT: '#/components/schemas/CountValueStat_Public' - AVG: '#/components/schemas/AvgValueStat_Public' + PERCENTAGE: "#/components/schemas/PercentageValueStat_Public" + COUNT: "#/components/schemas/CountValueStat_Public" + AVG: "#/components/schemas/AvgValueStat_Public" ProjectStats_Public: type: object properties: stats: type: array items: - $ref: '#/components/schemas/ProjectStatItemObject_Public' + $ref: "#/components/schemas/ProjectStatItemObject_Public" FeedbackScoreBatch: required: - - scores + - scores type: object properties: scores: @@ -6197,13 +6197,13 @@ components: minItems: 1 type: array items: - $ref: '#/components/schemas/FeedbackScoreBatchItem' + $ref: "#/components/schemas/FeedbackScoreBatchItem" FeedbackScoreBatchItem: required: - - id - - name - - source - - value + - id + - name + - source + - value type: object properties: id: @@ -6228,9 +6228,9 @@ components: source: type: string enum: - - ui - - sdk - - online_scoring + - ui + - sdk + - online_scoring ChunkedOutputJsonNode_Public: type: object properties: @@ -6249,16 +6249,16 @@ components: operator: type: string enum: - - contains - - not_contains - - starts_with - - ends_with - - = - - '!=' - - '>' - - '>=' - - < - - <= + - contains + - not_contains + - starts_with + - ends_with + - = + - "!=" + - ">" + - ">=" + - < + - <= key: type: string value: @@ -6277,13 +6277,13 @@ components: type: type: string enum: - - general - - tool - - llm + - general + - tool + - llm filters: type: array items: - $ref: '#/components/schemas/SpanFilter_Public' + $ref: "#/components/schemas/SpanFilter_Public" limit: type: integer format: int32 @@ -6296,7 +6296,7 @@ components: default: true SpanUpdate: required: - - trace_id + - trace_id type: object properties: project_name: @@ -6318,11 +6318,11 @@ components: type: string format: date-time input: - $ref: '#/components/schemas/JsonNode' + $ref: "#/components/schemas/JsonNode" output: - $ref: '#/components/schemas/JsonNode' + $ref: "#/components/schemas/JsonNode" metadata: - $ref: '#/components/schemas/JsonNode' + $ref: "#/components/schemas/JsonNode" model: type: string provider: @@ -6342,11 +6342,11 @@ components: exclusiveMinimum: false type: number error_info: - $ref: '#/components/schemas/ErrorInfo' + $ref: "#/components/schemas/ErrorInfo" Trace: required: - - name - - start_time + - name + - start_time type: object properties: id: @@ -6369,18 +6369,18 @@ components: type: string format: date-time input: - $ref: '#/components/schemas/JsonNode' + $ref: "#/components/schemas/JsonNode" output: - $ref: '#/components/schemas/JsonNode' + $ref: "#/components/schemas/JsonNode" metadata: - $ref: '#/components/schemas/JsonNode' + $ref: "#/components/schemas/JsonNode" tags: uniqueItems: true type: array items: type: string error_info: - $ref: '#/components/schemas/ErrorInfo' + $ref: "#/components/schemas/ErrorInfo" usage: type: object additionalProperties: @@ -6406,12 +6406,12 @@ components: type: array readOnly: true items: - $ref: '#/components/schemas/FeedbackScore' + $ref: "#/components/schemas/FeedbackScore" comments: type: array readOnly: true items: - $ref: '#/components/schemas/Comment' + $ref: "#/components/schemas/Comment" total_estimated_cost: type: number readOnly: true @@ -6423,8 +6423,8 @@ components: readOnly: true Trace_Write: required: - - name - - start_time + - name + - start_time type: object properties: id: @@ -6443,21 +6443,21 @@ components: type: string format: date-time input: - $ref: '#/components/schemas/JsonNode_Write' + $ref: "#/components/schemas/JsonNode_Write" output: - $ref: '#/components/schemas/JsonNode_Write' + $ref: "#/components/schemas/JsonNode_Write" metadata: - $ref: '#/components/schemas/JsonNode_Write' + $ref: "#/components/schemas/JsonNode_Write" tags: uniqueItems: true type: array items: type: string error_info: - $ref: '#/components/schemas/ErrorInfo_Write' + $ref: "#/components/schemas/ErrorInfo_Write" TraceBatch: required: - - traces + - traces type: object properties: traces: @@ -6465,10 +6465,10 @@ components: minItems: 1 type: array items: - $ref: '#/components/schemas/Trace' + $ref: "#/components/schemas/Trace" TraceBatch_Write: required: - - traces + - traces type: object properties: traces: @@ -6476,11 +6476,11 @@ components: minItems: 1 type: array items: - $ref: '#/components/schemas/Trace_Write' + $ref: "#/components/schemas/Trace_Write" Trace_Public: required: - - name - - start_time + - name + - start_time type: object properties: id: @@ -6499,18 +6499,18 @@ components: type: string format: date-time input: - $ref: '#/components/schemas/JsonNode_Public' + $ref: "#/components/schemas/JsonNode_Public" output: - $ref: '#/components/schemas/JsonNode_Public' + $ref: "#/components/schemas/JsonNode_Public" metadata: - $ref: '#/components/schemas/JsonNode_Public' + $ref: "#/components/schemas/JsonNode_Public" tags: uniqueItems: true type: array items: type: string error_info: - $ref: '#/components/schemas/ErrorInfo_Public' + $ref: "#/components/schemas/ErrorInfo_Public" usage: type: object additionalProperties: @@ -6536,12 +6536,12 @@ components: type: array readOnly: true items: - $ref: '#/components/schemas/FeedbackScore_Public' + $ref: "#/components/schemas/FeedbackScore_Public" comments: type: array readOnly: true items: - $ref: '#/components/schemas/Comment_Public' + $ref: "#/components/schemas/Comment_Public" total_estimated_cost: type: number readOnly: true @@ -6566,7 +6566,7 @@ components: content: type: array items: - $ref: '#/components/schemas/Trace_Public' + $ref: "#/components/schemas/Trace_Public" TraceUpdate: type: object properties: @@ -6583,15 +6583,15 @@ components: type: string format: date-time input: - $ref: '#/components/schemas/JsonNode' + $ref: "#/components/schemas/JsonNode" output: - $ref: '#/components/schemas/JsonNode' + $ref: "#/components/schemas/JsonNode" metadata: - $ref: '#/components/schemas/JsonNode' + $ref: "#/components/schemas/JsonNode" tags: uniqueItems: true type: array items: type: string error_info: - $ref: '#/components/schemas/ErrorInfo' + $ref: "#/components/schemas/ErrorInfo" diff --git a/apps/opik-documentation/documentation/fern/openapi/overrides.yml b/apps/opik-documentation/documentation/fern/openapi/overrides.yml new file mode 100644 index 0000000000..ae10afa44a --- /dev/null +++ b/apps/opik-documentation/documentation/fern/openapi/overrides.yml @@ -0,0 +1,7 @@ +paths: + /is-alive/ping: + get: + x-fern-ignore: true + /is-alive/ver: + get: + x-fern-ignore: true diff --git a/apps/opik-documentation/documentation/package-lock.json b/apps/opik-documentation/documentation/package-lock.json index 0f7729c853..fb987942dc 100644 --- a/apps/opik-documentation/documentation/package-lock.json +++ b/apps/opik-documentation/documentation/package-lock.json @@ -1,23306 +1,371 @@ { "name": "documentation", - "version": "0.0.0", "lockfileVersion": 3, "requires": true, "packages": { "": { - "name": "documentation", - "version": "0.0.0", "dependencies": { - "@docusaurus/core": "^3.7.0", - "@docusaurus/plugin-client-redirects": "^3.7.0", - "@docusaurus/preset-classic": "^3.7.0", - "@mdx-js/react": "^3.0.0", - "@segment/analytics-next": "^1.76.0", - "clsx": "^2.0.0", - "docusaurus-plugin-llms-txt": "^0.1.3", - "docusaurus-plugin-openapi-docs": "^4.0.1", - "docusaurus-plugin-sass": "^0.2.5", - "docusaurus-plugin-search-local": "^2.0.1", - "docusaurus-theme-openapi-docs": "^4.0.1", - "prism-react-renderer": "^2.3.0", - "react": "^18.0.0", - "react-dom": "^18.0.0", - "sass": "^1.77.8" - }, - "devDependencies": { - "@docusaurus/module-type-aliases": "^3.7.0", - "@docusaurus/tsconfig": "^3.7.0", - "@docusaurus/types": "^3.7.0", - "concurrently": "^8.2.0", - "dotenv": "^16.4.5", - "nodemon": "^3.1.7", - "typescript": "~5.2.2" - }, - "engines": { - "node": ">=18.0" - } - }, - "node_modules/@algolia/autocomplete-core": { - "version": "1.17.7", - "resolved": "https://registry.npmjs.org/@algolia/autocomplete-core/-/autocomplete-core-1.17.7.tgz", - "integrity": "sha512-BjiPOW6ks90UKl7TwMv7oNQMnzU+t/wk9mgIDi6b1tXpUek7MW0lbNOUHpvam9pe3lVCf4xPFT+lK7s+e+fs7Q==", - "license": "MIT", - "dependencies": { - "@algolia/autocomplete-plugin-algolia-insights": "1.17.7", - "@algolia/autocomplete-shared": "1.17.7" + "fern": "^0.0.19", + "nodemon": "^3.1.9" } }, - "node_modules/@algolia/autocomplete-plugin-algolia-insights": { - "version": "1.17.7", - "resolved": "https://registry.npmjs.org/@algolia/autocomplete-plugin-algolia-insights/-/autocomplete-plugin-algolia-insights-1.17.7.tgz", - "integrity": "sha512-Jca5Ude6yUOuyzjnz57og7Et3aXjbwCSDf/8onLHSQgw1qW3ALl9mrMWaXb5FmPVkV3EtkD2F/+NkT6VHyPu9A==", - "license": "MIT", + "node_modules/anymatch": { + "version": "3.1.3", + "resolved": "https://registry.npmjs.org/anymatch/-/anymatch-3.1.3.tgz", + "integrity": "sha512-KMReFUr0B4t+D+OBkjR3KYqvocp2XaSzO55UcB6mgQMd3KbcE+mWTyvVV7D/zsdEbNnV6acZUutkiHQXvTr1Rw==", + "license": "ISC", "dependencies": { - "@algolia/autocomplete-shared": "1.17.7" + "normalize-path": "^3.0.0", + "picomatch": "^2.0.4" }, - "peerDependencies": { - "search-insights": ">= 1 < 3" + "engines": { + "node": ">= 8" } }, - "node_modules/@algolia/autocomplete-preset-algolia": { - "version": "1.17.7", - "resolved": "https://registry.npmjs.org/@algolia/autocomplete-preset-algolia/-/autocomplete-preset-algolia-1.17.7.tgz", - "integrity": "sha512-ggOQ950+nwbWROq2MOCIL71RE0DdQZsceqrg32UqnhDz8FlO9rL8ONHNsI2R1MH0tkgVIDKI/D0sMiUchsFdWA==", + "node_modules/balanced-match": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.2.tgz", + "integrity": "sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw==", + "license": "MIT" + }, + "node_modules/binary-extensions": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/binary-extensions/-/binary-extensions-2.3.0.tgz", + "integrity": "sha512-Ceh+7ox5qe7LJuLHoY0feh3pHuUDHAcRUeyL2VYghZwfpkNIy/+8Ocg0a3UuSoYzavmylwuLWQOf3hl0jjMMIw==", "license": "MIT", - "dependencies": { - "@algolia/autocomplete-shared": "1.17.7" + "engines": { + "node": ">=8" }, - "peerDependencies": { - "@algolia/client-search": ">= 4.9.1 < 6", - "algoliasearch": ">= 4.9.1 < 6" + "funding": { + "url": "https://github.com/sponsors/sindresorhus" } }, - "node_modules/@algolia/autocomplete-shared": { - "version": "1.17.7", - "resolved": "https://registry.npmjs.org/@algolia/autocomplete-shared/-/autocomplete-shared-1.17.7.tgz", - "integrity": "sha512-o/1Vurr42U/qskRSuhBH+VKxMvkkUVTLU6WZQr+L5lGZZLYWyhdzWjW0iGXY7EkwRTjBqvN2EsR81yCTGV/kmg==", + "node_modules/brace-expansion": { + "version": "1.1.11", + "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz", + "integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==", "license": "MIT", - "peerDependencies": { - "@algolia/client-search": ">= 4.9.1 < 6", - "algoliasearch": ">= 4.9.1 < 6" + "dependencies": { + "balanced-match": "^1.0.0", + "concat-map": "0.0.1" } }, - "node_modules/@algolia/client-abtesting": { - "version": "5.19.0", - "resolved": "https://registry.npmjs.org/@algolia/client-abtesting/-/client-abtesting-5.19.0.tgz", - "integrity": "sha512-dMHwy2+nBL0SnIsC1iHvkBao64h4z+roGelOz11cxrDBrAdASxLxmfVMop8gmodQ2yZSacX0Rzevtxa+9SqxCw==", + "node_modules/braces": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/braces/-/braces-3.0.3.tgz", + "integrity": "sha512-yQbXgO/OSZVD2IsiLlro+7Hf6Q18EJrKSEsdoMzKePKXct3gvD8oLcOQdIzGupr5Fj+EDe8gO/lxc1BzfMpxvA==", "license": "MIT", "dependencies": { - "@algolia/client-common": "5.19.0", - "@algolia/requester-browser-xhr": "5.19.0", - "@algolia/requester-fetch": "5.19.0", - "@algolia/requester-node-http": "5.19.0" + "fill-range": "^7.1.1" }, "engines": { - "node": ">= 14.0.0" + "node": ">=8" } }, - "node_modules/@algolia/client-analytics": { - "version": "5.19.0", - "resolved": "https://registry.npmjs.org/@algolia/client-analytics/-/client-analytics-5.19.0.tgz", - "integrity": "sha512-CDW4RwnCHzU10upPJqS6N6YwDpDHno7w6/qXT9KPbPbt8szIIzCHrva4O9KIfx1OhdsHzfGSI5hMAiOOYl4DEQ==", + "node_modules/chokidar": { + "version": "3.6.0", + "resolved": "https://registry.npmjs.org/chokidar/-/chokidar-3.6.0.tgz", + "integrity": "sha512-7VT13fmjotKpGipCW9JEQAusEPE+Ei8nl6/g4FBAmIm0GOOLMua9NDDo/DWp0ZAxCr3cPq5ZpBqmPAQgDda2Pw==", "license": "MIT", "dependencies": { - "@algolia/client-common": "5.19.0", - "@algolia/requester-browser-xhr": "5.19.0", - "@algolia/requester-fetch": "5.19.0", - "@algolia/requester-node-http": "5.19.0" + "anymatch": "~3.1.2", + "braces": "~3.0.2", + "glob-parent": "~5.1.2", + "is-binary-path": "~2.1.0", + "is-glob": "~4.0.1", + "normalize-path": "~3.0.0", + "readdirp": "~3.6.0" }, "engines": { - "node": ">= 14.0.0" + "node": ">= 8.10.0" + }, + "funding": { + "url": "https://paulmillr.com/funding/" + }, + "optionalDependencies": { + "fsevents": "~2.3.2" } }, - "node_modules/@algolia/client-common": { - "version": "5.19.0", - "resolved": "https://registry.npmjs.org/@algolia/client-common/-/client-common-5.19.0.tgz", - "integrity": "sha512-2ERRbICHXvtj5kfFpY5r8qu9pJII/NAHsdgUXnUitQFwPdPL7wXiupcvZJC7DSntOnE8AE0lM7oDsPhrJfj5nQ==", - "license": "MIT", - "engines": { - "node": ">= 14.0.0" - } + "node_modules/concat-map": { + "version": "0.0.1", + "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", + "integrity": "sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg==", + "license": "MIT" }, - "node_modules/@algolia/client-insights": { - "version": "5.19.0", - "resolved": "https://registry.npmjs.org/@algolia/client-insights/-/client-insights-5.19.0.tgz", - "integrity": "sha512-xPOiGjo6I9mfjdJO7Y+p035aWePcbsItizIp+qVyfkfZiGgD+TbNxM12g7QhFAHIkx/mlYaocxPY/TmwPzTe+A==", + "node_modules/debug": { + "version": "4.4.0", + "resolved": "https://registry.npmjs.org/debug/-/debug-4.4.0.tgz", + "integrity": "sha512-6WTZ/IxCY/T6BALoZHaE4ctp9xm+Z5kY/pzYaCHRFeyVhojxlrm+46y68HA6hr0TcwEssoxNiDEUJQjfPZ/RYA==", "license": "MIT", "dependencies": { - "@algolia/client-common": "5.19.0", - "@algolia/requester-browser-xhr": "5.19.0", - "@algolia/requester-fetch": "5.19.0", - "@algolia/requester-node-http": "5.19.0" + "ms": "^2.1.3" }, "engines": { - "node": ">= 14.0.0" + "node": ">=6.0" + }, + "peerDependenciesMeta": { + "supports-color": { + "optional": true + } } }, - "node_modules/@algolia/client-personalization": { - "version": "5.19.0", - "resolved": "https://registry.npmjs.org/@algolia/client-personalization/-/client-personalization-5.19.0.tgz", - "integrity": "sha512-B9eoce/fk8NLboGje+pMr72pw+PV7c5Z01On477heTZ7jkxoZ4X92dobeGuEQop61cJ93Gaevd1of4mBr4hu2A==", + "node_modules/fern": { + "version": "0.0.19", + "resolved": "https://registry.npmjs.org/fern/-/fern-0.0.19.tgz", + "integrity": "sha512-CBg9Kfpfy1JWz2JS0R5IM1mDUkySje8IazyrcByJ5Xihzn1bP3+LJFQAktCkKI2m7DgF6uItGwKskwKa//P60w==", "license": "MIT", "dependencies": { - "@algolia/client-common": "5.19.0", - "@algolia/requester-browser-xhr": "5.19.0", - "@algolia/requester-fetch": "5.19.0", - "@algolia/requester-node-http": "5.19.0" - }, - "engines": { - "node": ">= 14.0.0" + "through": ">=2.3.4" } }, - "node_modules/@algolia/client-query-suggestions": { - "version": "5.19.0", - "resolved": "https://registry.npmjs.org/@algolia/client-query-suggestions/-/client-query-suggestions-5.19.0.tgz", - "integrity": "sha512-6fcP8d4S8XRDtVogrDvmSM6g5g6DndLc0pEm1GCKe9/ZkAzCmM3ZmW1wFYYPxdjMeifWy1vVEDMJK7sbE4W7MA==", + "node_modules/fill-range": { + "version": "7.1.1", + "resolved": "https://registry.npmjs.org/fill-range/-/fill-range-7.1.1.tgz", + "integrity": "sha512-YsGpe3WHLK8ZYi4tWDg2Jy3ebRz2rXowDxnld4bkQB00cc/1Zw9AWnC0i9ztDJitivtQvaI9KaLyKrc+hBW0yg==", "license": "MIT", "dependencies": { - "@algolia/client-common": "5.19.0", - "@algolia/requester-browser-xhr": "5.19.0", - "@algolia/requester-fetch": "5.19.0", - "@algolia/requester-node-http": "5.19.0" + "to-regex-range": "^5.0.1" }, "engines": { - "node": ">= 14.0.0" + "node": ">=8" } }, - "node_modules/@algolia/client-search": { - "version": "5.19.0", - "resolved": "https://registry.npmjs.org/@algolia/client-search/-/client-search-5.19.0.tgz", - "integrity": "sha512-Ctg3xXD/1VtcwmkulR5+cKGOMj4r0wC49Y/KZdGQcqpydKn+e86F6l3tb3utLJQVq4lpEJud6kdRykFgcNsp8Q==", + "node_modules/fsevents": { + "version": "2.3.3", + "resolved": "https://registry.npmjs.org/fsevents/-/fsevents-2.3.3.tgz", + "integrity": "sha512-5xoDfX+fL7faATnagmWPpbFtwh/R77WmMMqqHGS65C3vvB0YHrgF+B1YmZ3441tMj5n63k0212XNoJwzlhffQw==", + "hasInstallScript": true, "license": "MIT", - "dependencies": { - "@algolia/client-common": "5.19.0", - "@algolia/requester-browser-xhr": "5.19.0", - "@algolia/requester-fetch": "5.19.0", - "@algolia/requester-node-http": "5.19.0" - }, + "optional": true, + "os": [ + "darwin" + ], "engines": { - "node": ">= 14.0.0" + "node": "^8.16.0 || ^10.6.0 || >=11.0.0" } }, - "node_modules/@algolia/events": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/@algolia/events/-/events-4.0.1.tgz", - "integrity": "sha512-FQzvOCgoFXAbf5Y6mYozw2aj5KCJoA3m4heImceldzPSMbdyS4atVjJzXKMsfX3wnZTFYwkkt8/z8UesLHlSBQ==", - "license": "MIT" - }, - "node_modules/@algolia/ingestion": { - "version": "1.19.0", - "resolved": "https://registry.npmjs.org/@algolia/ingestion/-/ingestion-1.19.0.tgz", - "integrity": "sha512-LO7w1MDV+ZLESwfPmXkp+KLeYeFrYEgtbCZG6buWjddhYraPQ9MuQWLhLLiaMlKxZ/sZvFTcZYuyI6Jx4WBhcg==", - "license": "MIT", + "node_modules/glob-parent": { + "version": "5.1.2", + "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-5.1.2.tgz", + "integrity": "sha512-AOIgSQCepiJYwP3ARnGx+5VnTu2HBYdzbGP45eLw1vr3zB3vZLeyed1sC9hnbcOc9/SrMyM5RPQrkGz4aS9Zow==", + "license": "ISC", "dependencies": { - "@algolia/client-common": "5.19.0", - "@algolia/requester-browser-xhr": "5.19.0", - "@algolia/requester-fetch": "5.19.0", - "@algolia/requester-node-http": "5.19.0" + "is-glob": "^4.0.1" }, "engines": { - "node": ">= 14.0.0" + "node": ">= 6" } }, - "node_modules/@algolia/monitoring": { - "version": "1.19.0", - "resolved": "https://registry.npmjs.org/@algolia/monitoring/-/monitoring-1.19.0.tgz", - "integrity": "sha512-Mg4uoS0aIKeTpu6iv6O0Hj81s8UHagi5TLm9k2mLIib4vmMtX7WgIAHAcFIaqIZp5D6s5EVy1BaDOoZ7buuJHA==", + "node_modules/has-flag": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-3.0.0.tgz", + "integrity": "sha512-sKJf1+ceQBr4SMkvQnBDNDtf4TXpVhVGateu0t918bl30FnbE2m4vNLX+VWe/dpjlb+HugGYzW7uQXH98HPEYw==", "license": "MIT", - "dependencies": { - "@algolia/client-common": "5.19.0", - "@algolia/requester-browser-xhr": "5.19.0", - "@algolia/requester-fetch": "5.19.0", - "@algolia/requester-node-http": "5.19.0" - }, "engines": { - "node": ">= 14.0.0" + "node": ">=4" } }, - "node_modules/@algolia/recommend": { - "version": "5.19.0", - "resolved": "https://registry.npmjs.org/@algolia/recommend/-/recommend-5.19.0.tgz", - "integrity": "sha512-PbgrMTbUPlmwfJsxjFhal4XqZO2kpBNRjemLVTkUiti4w/+kzcYO4Hg5zaBgVqPwvFDNQ8JS4SS3TBBem88u+g==", + "node_modules/ignore-by-default": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/ignore-by-default/-/ignore-by-default-1.0.1.tgz", + "integrity": "sha512-Ius2VYcGNk7T90CppJqcIkS5ooHUZyIQK+ClZfMfMNFEF9VSE73Fq+906u/CWu92x4gzZMWOwfFYckPObzdEbA==", + "license": "ISC" + }, + "node_modules/is-binary-path": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/is-binary-path/-/is-binary-path-2.1.0.tgz", + "integrity": "sha512-ZMERYes6pDydyuGidse7OsHxtbI7WVeUEozgR/g7rd0xUimYNlvZRE/K2MgZTjWy725IfelLeVcEM97mmtRGXw==", "license": "MIT", "dependencies": { - "@algolia/client-common": "5.19.0", - "@algolia/requester-browser-xhr": "5.19.0", - "@algolia/requester-fetch": "5.19.0", - "@algolia/requester-node-http": "5.19.0" + "binary-extensions": "^2.0.0" }, "engines": { - "node": ">= 14.0.0" + "node": ">=8" } }, - "node_modules/@algolia/requester-browser-xhr": { - "version": "5.19.0", - "resolved": "https://registry.npmjs.org/@algolia/requester-browser-xhr/-/requester-browser-xhr-5.19.0.tgz", - "integrity": "sha512-GfnhnQBT23mW/VMNs7m1qyEyZzhZz093aY2x8p0era96MMyNv8+FxGek5pjVX0b57tmSCZPf4EqNCpkGcGsmbw==", + "node_modules/is-extglob": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-2.1.1.tgz", + "integrity": "sha512-SbKbANkN603Vi4jEZv49LeVJMn4yGwsbzZworEoyEiutsN3nJYdbO36zfhGJ6QEDpOZIFkDtnq5JRxmvl3jsoQ==", "license": "MIT", - "dependencies": { - "@algolia/client-common": "5.19.0" - }, "engines": { - "node": ">= 14.0.0" + "node": ">=0.10.0" } }, - "node_modules/@algolia/requester-fetch": { - "version": "5.19.0", - "resolved": "https://registry.npmjs.org/@algolia/requester-fetch/-/requester-fetch-5.19.0.tgz", - "integrity": "sha512-oyTt8ZJ4T4fYvW5avAnuEc6Laedcme9fAFryMD9ndUTIUe/P0kn3BuGcCLFjN3FDmdrETHSFkgPPf1hGy3sLCw==", + "node_modules/is-glob": { + "version": "4.0.3", + "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-4.0.3.tgz", + "integrity": "sha512-xelSayHH36ZgE7ZWhli7pW34hNbNl8Ojv5KVmkJD4hBdD3th8Tfk9vYasLM+mXWOZhFkgZfxhLSnrwRr4elSSg==", "license": "MIT", "dependencies": { - "@algolia/client-common": "5.19.0" + "is-extglob": "^2.1.1" }, "engines": { - "node": ">= 14.0.0" + "node": ">=0.10.0" } }, - "node_modules/@algolia/requester-node-http": { - "version": "5.19.0", - "resolved": "https://registry.npmjs.org/@algolia/requester-node-http/-/requester-node-http-5.19.0.tgz", - "integrity": "sha512-p6t8ue0XZNjcRiqNkb5QAM0qQRAKsCiebZ6n9JjWA+p8fWf8BvnhO55y2fO28g3GW0Imj7PrAuyBuxq8aDVQwQ==", + "node_modules/is-number": { + "version": "7.0.0", + "resolved": "https://registry.npmjs.org/is-number/-/is-number-7.0.0.tgz", + "integrity": "sha512-41Cifkg6e8TylSpdtTpeLVMqvSBEVzTttHvERD741+pnZ8ANv0004MRL43QKPDlK9cGvNp6NZWZUBlbGXYxxng==", "license": "MIT", - "dependencies": { - "@algolia/client-common": "5.19.0" - }, "engines": { - "node": ">= 14.0.0" + "node": ">=0.12.0" } }, - "node_modules/@ampproject/remapping": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/@ampproject/remapping/-/remapping-2.3.0.tgz", - "integrity": "sha512-30iZtAPgz+LTIYoeivqYo853f02jBYSd5uGnGpkFV0M3xOt9aN73erkgYAmZU43x4VfqcnLxW9Kpg3R5LC4YYw==", - "license": "Apache-2.0", + "node_modules/minimatch": { + "version": "3.1.2", + "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.1.2.tgz", + "integrity": "sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw==", + "license": "ISC", "dependencies": { - "@jridgewell/gen-mapping": "^0.3.5", - "@jridgewell/trace-mapping": "^0.3.24" + "brace-expansion": "^1.1.7" }, "engines": { - "node": ">=6.0.0" + "node": "*" } }, - "node_modules/@apidevtools/json-schema-ref-parser": { - "version": "11.7.0", - "resolved": "https://registry.npmjs.org/@apidevtools/json-schema-ref-parser/-/json-schema-ref-parser-11.7.0.tgz", - "integrity": "sha512-pRrmXMCwnmrkS3MLgAIW5dXRzeTv6GLjkjb4HmxNnvAKXN1Nfzp4KmGADBQvlVUcqi+a5D+hfGDLLnd5NnYxog==", + "node_modules/ms": { + "version": "2.1.3", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.3.tgz", + "integrity": "sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==", + "license": "MIT" + }, + "node_modules/nodemon": { + "version": "3.1.9", + "resolved": "https://registry.npmjs.org/nodemon/-/nodemon-3.1.9.tgz", + "integrity": "sha512-hdr1oIb2p6ZSxu3PB2JWWYS7ZQ0qvaZsc3hK8DR8f02kRzc8rjYmxAIvdz+aYC+8F2IjNaB7HMcSDg8nQpJxyg==", "license": "MIT", "dependencies": { - "@jsdevtools/ono": "^7.1.3", - "@types/json-schema": "^7.0.15", - "js-yaml": "^4.1.0" + "chokidar": "^3.5.2", + "debug": "^4", + "ignore-by-default": "^1.0.1", + "minimatch": "^3.1.2", + "pstree.remy": "^1.1.8", + "semver": "^7.5.3", + "simple-update-notifier": "^2.0.0", + "supports-color": "^5.5.0", + "touch": "^3.1.0", + "undefsafe": "^2.0.5" + }, + "bin": { + "nodemon": "bin/nodemon.js" }, "engines": { - "node": ">= 16" + "node": ">=10" }, "funding": { - "url": "https://github.com/sponsors/philsturgeon" - } - }, - "node_modules/@babel/code-frame": { - "version": "7.26.2", - "resolved": "https://registry.npmjs.org/@babel/code-frame/-/code-frame-7.26.2.tgz", - "integrity": "sha512-RJlIHRueQgwWitWgF8OdFYGZX328Ax5BCemNGlqHfplnRT9ESi8JkFlvaVYbS+UubVY6dpv87Fs2u5M29iNFVQ==", - "license": "MIT", - "dependencies": { - "@babel/helper-validator-identifier": "^7.25.9", - "js-tokens": "^4.0.0", - "picocolors": "^1.0.0" - }, - "engines": { - "node": ">=6.9.0" + "type": "opencollective", + "url": "https://opencollective.com/nodemon" } }, - "node_modules/@babel/compat-data": { - "version": "7.26.2", - "resolved": "https://registry.npmjs.org/@babel/compat-data/-/compat-data-7.26.2.tgz", - "integrity": "sha512-Z0WgzSEa+aUcdiJuCIqgujCshpMWgUpgOxXotrYPSA53hA3qopNaqcJpyr0hVb1FeWdnqFA35/fUtXgBK8srQg==", + "node_modules/normalize-path": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/normalize-path/-/normalize-path-3.0.0.tgz", + "integrity": "sha512-6eZs5Ls3WtCisHWp9S2GUy8dqkpGi4BVSz3GaqiE6ezub0512ESztXUwUB6C6IKbQkY2Pnb/mD4WYojCRwcwLA==", "license": "MIT", "engines": { - "node": ">=6.9.0" + "node": ">=0.10.0" } }, - "node_modules/@babel/core": { - "version": "7.26.0", - "resolved": "https://registry.npmjs.org/@babel/core/-/core-7.26.0.tgz", - "integrity": "sha512-i1SLeK+DzNnQ3LL/CswPCa/E5u4lh1k6IAEphON8F+cXt0t9euTshDru0q7/IqMa1PMPz5RnHuHscF8/ZJsStg==", + "node_modules/picomatch": { + "version": "2.3.1", + "resolved": "https://registry.npmjs.org/picomatch/-/picomatch-2.3.1.tgz", + "integrity": "sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA==", "license": "MIT", - "dependencies": { - "@ampproject/remapping": "^2.2.0", - "@babel/code-frame": "^7.26.0", - "@babel/generator": "^7.26.0", - "@babel/helper-compilation-targets": "^7.25.9", - "@babel/helper-module-transforms": "^7.26.0", - "@babel/helpers": "^7.26.0", - "@babel/parser": "^7.26.0", - "@babel/template": "^7.25.9", - "@babel/traverse": "^7.25.9", - "@babel/types": "^7.26.0", - "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": ">=8.6" }, "funding": { - "type": "opencollective", - "url": "https://opencollective.com/babel" + "url": "https://github.com/sponsors/jonschlinkert" } }, - "node_modules/@babel/core/node_modules/semver": { - "version": "6.3.1", - "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.1.tgz", - "integrity": "sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA==", - "license": "ISC", - "bin": { - "semver": "bin/semver.js" - } + "node_modules/pstree.remy": { + "version": "1.1.8", + "resolved": "https://registry.npmjs.org/pstree.remy/-/pstree.remy-1.1.8.tgz", + "integrity": "sha512-77DZwxQmxKnu3aR542U+X8FypNzbfJ+C5XQDk3uWjWxn6151aIMGthWYRXTqT1E5oJvg+ljaa2OJi+VfvCOQ8w==", + "license": "MIT" }, - "node_modules/@babel/generator": { - "version": "7.26.2", - "resolved": "https://registry.npmjs.org/@babel/generator/-/generator-7.26.2.tgz", - "integrity": "sha512-zevQbhbau95nkoxSq3f/DC/SC+EEOUZd3DYqfSkMhY2/wfSeaHV1Ew4vk8e+x8lja31IbyuUa2uQ3JONqKbysw==", + "node_modules/readdirp": { + "version": "3.6.0", + "resolved": "https://registry.npmjs.org/readdirp/-/readdirp-3.6.0.tgz", + "integrity": "sha512-hOS089on8RduqdbhvQ5Z37A0ESjsqz6qnRcffsMU3495FuTdqSm+7bhJ29JvIOsBDEEnan5DPu9t3To9VRlMzA==", "license": "MIT", "dependencies": { - "@babel/parser": "^7.26.2", - "@babel/types": "^7.26.0", - "@jridgewell/gen-mapping": "^0.3.5", - "@jridgewell/trace-mapping": "^0.3.25", - "jsesc": "^3.0.2" + "picomatch": "^2.2.1" }, "engines": { - "node": ">=6.9.0" + "node": ">=8.10.0" } }, - "node_modules/@babel/helper-annotate-as-pure": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/helper-annotate-as-pure/-/helper-annotate-as-pure-7.25.9.tgz", - "integrity": "sha512-gv7320KBUFJz1RnylIg5WWYPRXKZ884AGkYpgpWW02TH66Dl+HaC1t1CKd0z3R4b6hdYEcmrNZHUmfCP+1u3/g==", - "license": "MIT", - "dependencies": { - "@babel/types": "^7.25.9" + "node_modules/semver": { + "version": "7.7.1", + "resolved": "https://registry.npmjs.org/semver/-/semver-7.7.1.tgz", + "integrity": "sha512-hlq8tAfn0m/61p4BVRcPzIGr6LKiMwo4VM6dGi6pt4qcRkmNzTcWq6eCEjEh+qXjkMDvPlOFFSGwQjoEa6gyMA==", + "license": "ISC", + "bin": { + "semver": "bin/semver.js" }, "engines": { - "node": ">=6.9.0" + "node": ">=10" } }, - "node_modules/@babel/helper-builder-binary-assignment-operator-visitor": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/helper-builder-binary-assignment-operator-visitor/-/helper-builder-binary-assignment-operator-visitor-7.25.9.tgz", - "integrity": "sha512-C47lC7LIDCnz0h4vai/tpNOI95tCd5ZT3iBt/DBH5lXKHZsyNQv18yf1wIIg2ntiQNgmAvA+DgZ82iW8Qdym8g==", + "node_modules/simple-update-notifier": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/simple-update-notifier/-/simple-update-notifier-2.0.0.tgz", + "integrity": "sha512-a2B9Y0KlNXl9u/vsW6sTIu9vGEpfKu2wRV6l1H3XEas/0gUIzGzBoP/IouTcUQbm9JWZLH3COxyn03TYlFax6w==", "license": "MIT", "dependencies": { - "@babel/traverse": "^7.25.9", - "@babel/types": "^7.25.9" + "semver": "^7.5.3" }, "engines": { - "node": ">=6.9.0" + "node": ">=10" } }, - "node_modules/@babel/helper-compilation-targets": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/helper-compilation-targets/-/helper-compilation-targets-7.25.9.tgz", - "integrity": "sha512-j9Db8Suy6yV/VHa4qzrj9yZfZxhLWQdVnRlXxmKLYlhWUVB1sB2G5sxuWYXk/whHD9iW76PmNzxZ4UCnTQTVEQ==", + "node_modules/supports-color": { + "version": "5.5.0", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.5.0.tgz", + "integrity": "sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow==", "license": "MIT", "dependencies": { - "@babel/compat-data": "^7.25.9", - "@babel/helper-validator-option": "^7.25.9", - "browserslist": "^4.24.0", - "lru-cache": "^5.1.1", - "semver": "^6.3.1" + "has-flag": "^3.0.0" }, "engines": { - "node": ">=6.9.0" + "node": ">=4" } }, - "node_modules/@babel/helper-compilation-targets/node_modules/semver": { - "version": "6.3.1", - "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.1.tgz", - "integrity": "sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA==", - "license": "ISC", - "bin": { - "semver": "bin/semver.js" - } + "node_modules/through": { + "version": "2.3.8", + "resolved": "https://registry.npmjs.org/through/-/through-2.3.8.tgz", + "integrity": "sha512-w89qg7PI8wAdvX60bMDP+bFoD5Dvhm9oLheFp5O4a2QF0cSBGsBX4qZmadPMvVqlLJBBci+WqGGOAPvcDeNSVg==", + "license": "MIT" }, - "node_modules/@babel/helper-create-class-features-plugin": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/helper-create-class-features-plugin/-/helper-create-class-features-plugin-7.25.9.tgz", - "integrity": "sha512-UTZQMvt0d/rSz6KI+qdu7GQze5TIajwTS++GUozlw8VBJDEOAqSXwm1WvmYEZwqdqSGQshRocPDqrt4HBZB3fQ==", + "node_modules/to-regex-range": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/to-regex-range/-/to-regex-range-5.0.1.tgz", + "integrity": "sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ==", "license": "MIT", "dependencies": { - "@babel/helper-annotate-as-pure": "^7.25.9", - "@babel/helper-member-expression-to-functions": "^7.25.9", - "@babel/helper-optimise-call-expression": "^7.25.9", - "@babel/helper-replace-supers": "^7.25.9", - "@babel/helper-skip-transparent-expression-wrappers": "^7.25.9", - "@babel/traverse": "^7.25.9", - "semver": "^6.3.1" + "is-number": "^7.0.0" }, "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0" + "node": ">=8.0" } }, - "node_modules/@babel/helper-create-class-features-plugin/node_modules/semver": { - "version": "6.3.1", - "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.1.tgz", - "integrity": "sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA==", + "node_modules/touch": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/touch/-/touch-3.1.1.tgz", + "integrity": "sha512-r0eojU4bI8MnHr8c5bNo7lJDdI2qXlWWJk6a9EAFG7vbhTjElYhBVS3/miuE0uOuoLdb8Mc/rVfsmm6eo5o9GA==", "license": "ISC", "bin": { - "semver": "bin/semver.js" + "nodetouch": "bin/nodetouch.js" } }, - "node_modules/@babel/helper-create-regexp-features-plugin": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/helper-create-regexp-features-plugin/-/helper-create-regexp-features-plugin-7.25.9.tgz", - "integrity": "sha512-ORPNZ3h6ZRkOyAa/SaHU+XsLZr0UQzRwuDQ0cczIA17nAzZ+85G5cVkOJIj7QavLZGSe8QXUmNFxSZzjcZF9bw==", - "license": "MIT", - "dependencies": { - "@babel/helper-annotate-as-pure": "^7.25.9", - "regexpu-core": "^6.1.1", - "semver": "^6.3.1" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0" - } - }, - "node_modules/@babel/helper-create-regexp-features-plugin/node_modules/semver": { - "version": "6.3.1", - "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.1.tgz", - "integrity": "sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA==", - "license": "ISC", - "bin": { - "semver": "bin/semver.js" - } - }, - "node_modules/@babel/helper-define-polyfill-provider": { - "version": "0.6.2", - "resolved": "https://registry.npmjs.org/@babel/helper-define-polyfill-provider/-/helper-define-polyfill-provider-0.6.2.tgz", - "integrity": "sha512-LV76g+C502biUK6AyZ3LK10vDpDyCzZnhZFXkH1L75zHPj68+qc8Zfpx2th+gzwA2MzyK+1g/3EPl62yFnVttQ==", - "license": "MIT", - "dependencies": { - "@babel/helper-compilation-targets": "^7.22.6", - "@babel/helper-plugin-utils": "^7.22.5", - "debug": "^4.1.1", - "lodash.debounce": "^4.0.8", - "resolve": "^1.14.2" - }, - "peerDependencies": { - "@babel/core": "^7.4.0 || ^8.0.0-0 <8.0.0" - } - }, - "node_modules/@babel/helper-member-expression-to-functions": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/helper-member-expression-to-functions/-/helper-member-expression-to-functions-7.25.9.tgz", - "integrity": "sha512-wbfdZ9w5vk0C0oyHqAJbc62+vet5prjj01jjJ8sKn3j9h3MQQlflEdXYvuqRWjHnM12coDEqiC1IRCi0U/EKwQ==", - "license": "MIT", - "dependencies": { - "@babel/traverse": "^7.25.9", - "@babel/types": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - } - }, - "node_modules/@babel/helper-module-imports": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/helper-module-imports/-/helper-module-imports-7.25.9.tgz", - "integrity": "sha512-tnUA4RsrmflIM6W6RFTLFSXITtl0wKjgpnLgXyowocVPrbYrLUXSBXDgTs8BlbmIzIdlBySRQjINYs2BAkiLtw==", - "license": "MIT", - "dependencies": { - "@babel/traverse": "^7.25.9", - "@babel/types": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - } - }, - "node_modules/@babel/helper-module-transforms": { - "version": "7.26.0", - "resolved": "https://registry.npmjs.org/@babel/helper-module-transforms/-/helper-module-transforms-7.26.0.tgz", - "integrity": "sha512-xO+xu6B5K2czEnQye6BHA7DolFFmS3LB7stHZFaOLb1pAwO1HWLS8fXA+eh0A2yIvltPVmx3eNNDBJA2SLHXFw==", - "license": "MIT", - "dependencies": { - "@babel/helper-module-imports": "^7.25.9", - "@babel/helper-validator-identifier": "^7.25.9", - "@babel/traverse": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0" - } - }, - "node_modules/@babel/helper-optimise-call-expression": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/helper-optimise-call-expression/-/helper-optimise-call-expression-7.25.9.tgz", - "integrity": "sha512-FIpuNaz5ow8VyrYcnXQTDRGvV6tTjkNtCK/RYNDXGSLlUD6cBuQTSw43CShGxjvfBTfcUA/r6UhUCbtYqkhcuQ==", - "license": "MIT", - "dependencies": { - "@babel/types": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - } - }, - "node_modules/@babel/helper-plugin-utils": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/helper-plugin-utils/-/helper-plugin-utils-7.25.9.tgz", - "integrity": "sha512-kSMlyUVdWe25rEsRGviIgOWnoT/nfABVWlqt9N19/dIPWViAOW2s9wznP5tURbs/IDuNk4gPy3YdYRgH3uxhBw==", - "license": "MIT", - "engines": { - "node": ">=6.9.0" - } - }, - "node_modules/@babel/helper-remap-async-to-generator": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/helper-remap-async-to-generator/-/helper-remap-async-to-generator-7.25.9.tgz", - "integrity": "sha512-IZtukuUeBbhgOcaW2s06OXTzVNJR0ybm4W5xC1opWFFJMZbwRj5LCk+ByYH7WdZPZTt8KnFwA8pvjN2yqcPlgw==", - "license": "MIT", - "dependencies": { - "@babel/helper-annotate-as-pure": "^7.25.9", - "@babel/helper-wrap-function": "^7.25.9", - "@babel/traverse": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0" - } - }, - "node_modules/@babel/helper-replace-supers": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/helper-replace-supers/-/helper-replace-supers-7.25.9.tgz", - "integrity": "sha512-IiDqTOTBQy0sWyeXyGSC5TBJpGFXBkRynjBeXsvbhQFKj2viwJC76Epz35YLU1fpe/Am6Vppb7W7zM4fPQzLsQ==", - "license": "MIT", - "dependencies": { - "@babel/helper-member-expression-to-functions": "^7.25.9", - "@babel/helper-optimise-call-expression": "^7.25.9", - "@babel/traverse": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0" - } - }, - "node_modules/@babel/helper-simple-access": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/helper-simple-access/-/helper-simple-access-7.25.9.tgz", - "integrity": "sha512-c6WHXuiaRsJTyHYLJV75t9IqsmTbItYfdj99PnzYGQZkYKvan5/2jKJ7gu31J3/BJ/A18grImSPModuyG/Eo0Q==", - "license": "MIT", - "dependencies": { - "@babel/traverse": "^7.25.9", - "@babel/types": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - } - }, - "node_modules/@babel/helper-skip-transparent-expression-wrappers": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/helper-skip-transparent-expression-wrappers/-/helper-skip-transparent-expression-wrappers-7.25.9.tgz", - "integrity": "sha512-K4Du3BFa3gvyhzgPcntrkDgZzQaq6uozzcpGbOO1OEJaI+EJdqWIMTLgFgQf6lrfiDFo5FU+BxKepI9RmZqahA==", - "license": "MIT", - "dependencies": { - "@babel/traverse": "^7.25.9", - "@babel/types": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - } - }, - "node_modules/@babel/helper-string-parser": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/helper-string-parser/-/helper-string-parser-7.25.9.tgz", - "integrity": "sha512-4A/SCr/2KLd5jrtOMFzaKjVtAei3+2r/NChoBNoZ3EyP/+GlhoaEGoWOZUmFmoITP7zOJyHIMm+DYRd8o3PvHA==", - "license": "MIT", - "engines": { - "node": ">=6.9.0" - } - }, - "node_modules/@babel/helper-validator-identifier": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/helper-validator-identifier/-/helper-validator-identifier-7.25.9.tgz", - "integrity": "sha512-Ed61U6XJc3CVRfkERJWDz4dJwKe7iLmmJsbOGu9wSloNSFttHV0I8g6UAgb7qnK5ly5bGLPd4oXZlxCdANBOWQ==", - "license": "MIT", - "engines": { - "node": ">=6.9.0" - } - }, - "node_modules/@babel/helper-validator-option": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/helper-validator-option/-/helper-validator-option-7.25.9.tgz", - "integrity": "sha512-e/zv1co8pp55dNdEcCynfj9X7nyUKUXoUEwfXqaZt0omVOmDe9oOTdKStH4GmAw6zxMFs50ZayuMfHDKlO7Tfw==", - "license": "MIT", - "engines": { - "node": ">=6.9.0" - } - }, - "node_modules/@babel/helper-wrap-function": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/helper-wrap-function/-/helper-wrap-function-7.25.9.tgz", - "integrity": "sha512-ETzz9UTjQSTmw39GboatdymDq4XIQbR8ySgVrylRhPOFpsd+JrKHIuF0de7GCWmem+T4uC5z7EZguod7Wj4A4g==", - "license": "MIT", - "dependencies": { - "@babel/template": "^7.25.9", - "@babel/traverse": "^7.25.9", - "@babel/types": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - } - }, - "node_modules/@babel/helpers": { - "version": "7.26.0", - "resolved": "https://registry.npmjs.org/@babel/helpers/-/helpers-7.26.0.tgz", - "integrity": "sha512-tbhNuIxNcVb21pInl3ZSjksLCvgdZy9KwJ8brv993QtIVKJBBkYXz4q4ZbAv31GdnC+R90np23L5FbEBlthAEw==", - "license": "MIT", - "dependencies": { - "@babel/template": "^7.25.9", - "@babel/types": "^7.26.0" - }, - "engines": { - "node": ">=6.9.0" - } - }, - "node_modules/@babel/parser": { - "version": "7.26.2", - "resolved": "https://registry.npmjs.org/@babel/parser/-/parser-7.26.2.tgz", - "integrity": "sha512-DWMCZH9WA4Maitz2q21SRKHo9QXZxkDsbNZoVD62gusNtNBBqDg9i7uOhASfTfIGNzW+O+r7+jAlM8dwphcJKQ==", - "license": "MIT", - "dependencies": { - "@babel/types": "^7.26.0" - }, - "bin": { - "parser": "bin/babel-parser.js" - }, - "engines": { - "node": ">=6.0.0" - } - }, - "node_modules/@babel/plugin-bugfix-firefox-class-in-computed-class-key": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-bugfix-firefox-class-in-computed-class-key/-/plugin-bugfix-firefox-class-in-computed-class-key-7.25.9.tgz", - "integrity": "sha512-ZkRyVkThtxQ/J6nv3JFYv1RYY+JT5BvU0y3k5bWrmuG4woXypRa4PXmm9RhOwodRkYFWqC0C0cqcJ4OqR7kW+g==", - "license": "MIT", - "dependencies": { - "@babel/helper-plugin-utils": "^7.25.9", - "@babel/traverse": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0" - } - }, - "node_modules/@babel/plugin-bugfix-safari-class-field-initializer-scope": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-bugfix-safari-class-field-initializer-scope/-/plugin-bugfix-safari-class-field-initializer-scope-7.25.9.tgz", - "integrity": "sha512-MrGRLZxLD/Zjj0gdU15dfs+HH/OXvnw/U4jJD8vpcP2CJQapPEv1IWwjc/qMg7ItBlPwSv1hRBbb7LeuANdcnw==", - "license": "MIT", - "dependencies": { - "@babel/helper-plugin-utils": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0" - } - }, - "node_modules/@babel/plugin-bugfix-safari-id-destructuring-collision-in-function-expression": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-bugfix-safari-id-destructuring-collision-in-function-expression/-/plugin-bugfix-safari-id-destructuring-collision-in-function-expression-7.25.9.tgz", - "integrity": "sha512-2qUwwfAFpJLZqxd02YW9btUCZHl+RFvdDkNfZwaIJrvB8Tesjsk8pEQkTvGwZXLqXUx/2oyY3ySRhm6HOXuCug==", - "license": "MIT", - "dependencies": { - "@babel/helper-plugin-utils": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0" - } - }, - "node_modules/@babel/plugin-bugfix-v8-spread-parameters-in-optional-chaining": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-bugfix-v8-spread-parameters-in-optional-chaining/-/plugin-bugfix-v8-spread-parameters-in-optional-chaining-7.25.9.tgz", - "integrity": "sha512-6xWgLZTJXwilVjlnV7ospI3xi+sl8lN8rXXbBD6vYn3UYDlGsag8wrZkKcSI8G6KgqKP7vNFaDgeDnfAABq61g==", - "license": "MIT", - "dependencies": { - "@babel/helper-plugin-utils": "^7.25.9", - "@babel/helper-skip-transparent-expression-wrappers": "^7.25.9", - "@babel/plugin-transform-optional-chaining": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.13.0" - } - }, - "node_modules/@babel/plugin-bugfix-v8-static-class-fields-redefine-readonly": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-bugfix-v8-static-class-fields-redefine-readonly/-/plugin-bugfix-v8-static-class-fields-redefine-readonly-7.25.9.tgz", - "integrity": "sha512-aLnMXYPnzwwqhYSCyXfKkIkYgJ8zv9RK+roo9DkTXz38ynIhd9XCbN08s3MGvqL2MYGVUGdRQLL/JqBIeJhJBg==", - "license": "MIT", - "dependencies": { - "@babel/helper-plugin-utils": "^7.25.9", - "@babel/traverse": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0" - } - }, - "node_modules/@babel/plugin-proposal-private-property-in-object": { - "version": "7.21.0-placeholder-for-preset-env.2", - "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-private-property-in-object/-/plugin-proposal-private-property-in-object-7.21.0-placeholder-for-preset-env.2.tgz", - "integrity": "sha512-SOSkfJDddaM7mak6cPEpswyTRnuRltl429hMraQEglW+OkovnCzsiszTmsrlY//qLFjCpQDFRvjdm2wA5pPm9w==", - "license": "MIT", - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-syntax-dynamic-import": { - "version": "7.8.3", - "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-dynamic-import/-/plugin-syntax-dynamic-import-7.8.3.tgz", - "integrity": "sha512-5gdGbFon+PszYzqs83S3E5mpi7/y/8M9eC90MRTZfduQOYW76ig6SOSPNe41IG5LoP3FGBn2N0RjVDSQiS94kQ==", - "license": "MIT", - "dependencies": { - "@babel/helper-plugin-utils": "^7.8.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-syntax-import-assertions": { - "version": "7.26.0", - "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-import-assertions/-/plugin-syntax-import-assertions-7.26.0.tgz", - "integrity": "sha512-QCWT5Hh830hK5EQa7XzuqIkQU9tT/whqbDz7kuaZMHFl1inRRg7JnuAEOQ0Ur0QUl0NufCk1msK2BeY79Aj/eg==", - "license": "MIT", - "dependencies": { - "@babel/helper-plugin-utils": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-syntax-import-attributes": { - "version": "7.26.0", - "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-import-attributes/-/plugin-syntax-import-attributes-7.26.0.tgz", - "integrity": "sha512-e2dttdsJ1ZTpi3B9UYGLw41hifAubg19AtCu/2I/F1QNVclOBr1dYpTdmdyZ84Xiz43BS/tCUkMAZNLv12Pi+A==", - "license": "MIT", - "dependencies": { - "@babel/helper-plugin-utils": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-syntax-jsx": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-jsx/-/plugin-syntax-jsx-7.25.9.tgz", - "integrity": "sha512-ld6oezHQMZsZfp6pWtbjaNDF2tiiCYYDqQszHt5VV437lewP9aSi2Of99CK0D0XB21k7FLgnLcmQKyKzynfeAA==", - "license": "MIT", - "dependencies": { - "@babel/helper-plugin-utils": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-syntax-typescript": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-typescript/-/plugin-syntax-typescript-7.25.9.tgz", - "integrity": "sha512-hjMgRy5hb8uJJjUcdWunWVcoi9bGpJp8p5Ol1229PoN6aytsLwNMgmdftO23wnCLMfVmTwZDWMPNq/D1SY60JQ==", - "license": "MIT", - "dependencies": { - "@babel/helper-plugin-utils": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-syntax-unicode-sets-regex": { - "version": "7.18.6", - "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-unicode-sets-regex/-/plugin-syntax-unicode-sets-regex-7.18.6.tgz", - "integrity": "sha512-727YkEAPwSIQTv5im8QHz3upqp92JTWhidIC81Tdx4VJYIte/VndKf1qKrfnnhPLiPghStWfvC/iFaMCQu7Nqg==", - "license": "MIT", - "dependencies": { - "@babel/helper-create-regexp-features-plugin": "^7.18.6", - "@babel/helper-plugin-utils": "^7.18.6" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0" - } - }, - "node_modules/@babel/plugin-transform-arrow-functions": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-arrow-functions/-/plugin-transform-arrow-functions-7.25.9.tgz", - "integrity": "sha512-6jmooXYIwn9ca5/RylZADJ+EnSxVUS5sjeJ9UPk6RWRzXCmOJCy6dqItPJFpw2cuCangPK4OYr5uhGKcmrm5Qg==", - "license": "MIT", - "dependencies": { - "@babel/helper-plugin-utils": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-async-generator-functions": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-async-generator-functions/-/plugin-transform-async-generator-functions-7.25.9.tgz", - "integrity": "sha512-RXV6QAzTBbhDMO9fWwOmwwTuYaiPbggWQ9INdZqAYeSHyG7FzQ+nOZaUUjNwKv9pV3aE4WFqFm1Hnbci5tBCAw==", - "license": "MIT", - "dependencies": { - "@babel/helper-plugin-utils": "^7.25.9", - "@babel/helper-remap-async-to-generator": "^7.25.9", - "@babel/traverse": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-async-to-generator": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-async-to-generator/-/plugin-transform-async-to-generator-7.25.9.tgz", - "integrity": "sha512-NT7Ejn7Z/LjUH0Gv5KsBCxh7BH3fbLTV0ptHvpeMvrt3cPThHfJfst9Wrb7S8EvJ7vRTFI7z+VAvFVEQn/m5zQ==", - "license": "MIT", - "dependencies": { - "@babel/helper-module-imports": "^7.25.9", - "@babel/helper-plugin-utils": "^7.25.9", - "@babel/helper-remap-async-to-generator": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-block-scoped-functions": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-block-scoped-functions/-/plugin-transform-block-scoped-functions-7.25.9.tgz", - "integrity": "sha512-toHc9fzab0ZfenFpsyYinOX0J/5dgJVA2fm64xPewu7CoYHWEivIWKxkK2rMi4r3yQqLnVmheMXRdG+k239CgA==", - "license": "MIT", - "dependencies": { - "@babel/helper-plugin-utils": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-block-scoping": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-block-scoping/-/plugin-transform-block-scoping-7.25.9.tgz", - "integrity": "sha512-1F05O7AYjymAtqbsFETboN1NvBdcnzMerO+zlMyJBEz6WkMdejvGWw9p05iTSjC85RLlBseHHQpYaM4gzJkBGg==", - "license": "MIT", - "dependencies": { - "@babel/helper-plugin-utils": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-class-properties": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-class-properties/-/plugin-transform-class-properties-7.25.9.tgz", - "integrity": "sha512-bbMAII8GRSkcd0h0b4X+36GksxuheLFjP65ul9w6C3KgAamI3JqErNgSrosX6ZPj+Mpim5VvEbawXxJCyEUV3Q==", - "license": "MIT", - "dependencies": { - "@babel/helper-create-class-features-plugin": "^7.25.9", - "@babel/helper-plugin-utils": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-class-static-block": { - "version": "7.26.0", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-class-static-block/-/plugin-transform-class-static-block-7.26.0.tgz", - "integrity": "sha512-6J2APTs7BDDm+UMqP1useWqhcRAXo0WIoVj26N7kPFB6S73Lgvyka4KTZYIxtgYXiN5HTyRObA72N2iu628iTQ==", - "license": "MIT", - "dependencies": { - "@babel/helper-create-class-features-plugin": "^7.25.9", - "@babel/helper-plugin-utils": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.12.0" - } - }, - "node_modules/@babel/plugin-transform-classes": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-classes/-/plugin-transform-classes-7.25.9.tgz", - "integrity": "sha512-mD8APIXmseE7oZvZgGABDyM34GUmK45Um2TXiBUt7PnuAxrgoSVf123qUzPxEr/+/BHrRn5NMZCdE2m/1F8DGg==", - "license": "MIT", - "dependencies": { - "@babel/helper-annotate-as-pure": "^7.25.9", - "@babel/helper-compilation-targets": "^7.25.9", - "@babel/helper-plugin-utils": "^7.25.9", - "@babel/helper-replace-supers": "^7.25.9", - "@babel/traverse": "^7.25.9", - "globals": "^11.1.0" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-computed-properties": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-computed-properties/-/plugin-transform-computed-properties-7.25.9.tgz", - "integrity": "sha512-HnBegGqXZR12xbcTHlJ9HGxw1OniltT26J5YpfruGqtUHlz/xKf/G2ak9e+t0rVqrjXa9WOhvYPz1ERfMj23AA==", - "license": "MIT", - "dependencies": { - "@babel/helper-plugin-utils": "^7.25.9", - "@babel/template": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-destructuring": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-destructuring/-/plugin-transform-destructuring-7.25.9.tgz", - "integrity": "sha512-WkCGb/3ZxXepmMiX101nnGiU+1CAdut8oHyEOHxkKuS1qKpU2SMXE2uSvfz8PBuLd49V6LEsbtyPhWC7fnkgvQ==", - "license": "MIT", - "dependencies": { - "@babel/helper-plugin-utils": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-dotall-regex": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-dotall-regex/-/plugin-transform-dotall-regex-7.25.9.tgz", - "integrity": "sha512-t7ZQ7g5trIgSRYhI9pIJtRl64KHotutUJsh4Eze5l7olJv+mRSg4/MmbZ0tv1eeqRbdvo/+trvJD/Oc5DmW2cA==", - "license": "MIT", - "dependencies": { - "@babel/helper-create-regexp-features-plugin": "^7.25.9", - "@babel/helper-plugin-utils": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-duplicate-keys": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-duplicate-keys/-/plugin-transform-duplicate-keys-7.25.9.tgz", - "integrity": "sha512-LZxhJ6dvBb/f3x8xwWIuyiAHy56nrRG3PeYTpBkkzkYRRQ6tJLu68lEF5VIqMUZiAV7a8+Tb78nEoMCMcqjXBw==", - "license": "MIT", - "dependencies": { - "@babel/helper-plugin-utils": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-duplicate-named-capturing-groups-regex": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-duplicate-named-capturing-groups-regex/-/plugin-transform-duplicate-named-capturing-groups-regex-7.25.9.tgz", - "integrity": "sha512-0UfuJS0EsXbRvKnwcLjFtJy/Sxc5J5jhLHnFhy7u4zih97Hz6tJkLU+O+FMMrNZrosUPxDi6sYxJ/EA8jDiAog==", - "license": "MIT", - "dependencies": { - "@babel/helper-create-regexp-features-plugin": "^7.25.9", - "@babel/helper-plugin-utils": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0" - } - }, - "node_modules/@babel/plugin-transform-dynamic-import": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-dynamic-import/-/plugin-transform-dynamic-import-7.25.9.tgz", - "integrity": "sha512-GCggjexbmSLaFhqsojeugBpeaRIgWNTcgKVq/0qIteFEqY2A+b9QidYadrWlnbWQUrW5fn+mCvf3tr7OeBFTyg==", - "license": "MIT", - "dependencies": { - "@babel/helper-plugin-utils": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-exponentiation-operator": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-exponentiation-operator/-/plugin-transform-exponentiation-operator-7.25.9.tgz", - "integrity": "sha512-KRhdhlVk2nObA5AYa7QMgTMTVJdfHprfpAk4DjZVtllqRg9qarilstTKEhpVjyt+Npi8ThRyiV8176Am3CodPA==", - "license": "MIT", - "dependencies": { - "@babel/helper-builder-binary-assignment-operator-visitor": "^7.25.9", - "@babel/helper-plugin-utils": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-export-namespace-from": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-export-namespace-from/-/plugin-transform-export-namespace-from-7.25.9.tgz", - "integrity": "sha512-2NsEz+CxzJIVOPx2o9UsW1rXLqtChtLoVnwYHHiB04wS5sgn7mrV45fWMBX0Kk+ub9uXytVYfNP2HjbVbCB3Ww==", - "license": "MIT", - "dependencies": { - "@babel/helper-plugin-utils": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-for-of": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-for-of/-/plugin-transform-for-of-7.25.9.tgz", - "integrity": "sha512-LqHxduHoaGELJl2uhImHwRQudhCM50pT46rIBNvtT/Oql3nqiS3wOwP+5ten7NpYSXrrVLgtZU3DZmPtWZo16A==", - "license": "MIT", - "dependencies": { - "@babel/helper-plugin-utils": "^7.25.9", - "@babel/helper-skip-transparent-expression-wrappers": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-function-name": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-function-name/-/plugin-transform-function-name-7.25.9.tgz", - "integrity": "sha512-8lP+Yxjv14Vc5MuWBpJsoUCd3hD6V9DgBon2FVYL4jJgbnVQ9fTgYmonchzZJOVNgzEgbxp4OwAf6xz6M/14XA==", - "license": "MIT", - "dependencies": { - "@babel/helper-compilation-targets": "^7.25.9", - "@babel/helper-plugin-utils": "^7.25.9", - "@babel/traverse": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-json-strings": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-json-strings/-/plugin-transform-json-strings-7.25.9.tgz", - "integrity": "sha512-xoTMk0WXceiiIvsaquQQUaLLXSW1KJ159KP87VilruQm0LNNGxWzahxSS6T6i4Zg3ezp4vA4zuwiNUR53qmQAw==", - "license": "MIT", - "dependencies": { - "@babel/helper-plugin-utils": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-literals": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-literals/-/plugin-transform-literals-7.25.9.tgz", - "integrity": "sha512-9N7+2lFziW8W9pBl2TzaNht3+pgMIRP74zizeCSrtnSKVdUl8mAjjOP2OOVQAfZ881P2cNjDj1uAMEdeD50nuQ==", - "license": "MIT", - "dependencies": { - "@babel/helper-plugin-utils": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-logical-assignment-operators": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-logical-assignment-operators/-/plugin-transform-logical-assignment-operators-7.25.9.tgz", - "integrity": "sha512-wI4wRAzGko551Y8eVf6iOY9EouIDTtPb0ByZx+ktDGHwv6bHFimrgJM/2T021txPZ2s4c7bqvHbd+vXG6K948Q==", - "license": "MIT", - "dependencies": { - "@babel/helper-plugin-utils": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-member-expression-literals": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-member-expression-literals/-/plugin-transform-member-expression-literals-7.25.9.tgz", - "integrity": "sha512-PYazBVfofCQkkMzh2P6IdIUaCEWni3iYEerAsRWuVd8+jlM1S9S9cz1dF9hIzyoZ8IA3+OwVYIp9v9e+GbgZhA==", - "license": "MIT", - "dependencies": { - "@babel/helper-plugin-utils": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-modules-amd": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-modules-amd/-/plugin-transform-modules-amd-7.25.9.tgz", - "integrity": "sha512-g5T11tnI36jVClQlMlt4qKDLlWnG5pP9CSM4GhdRciTNMRgkfpo5cR6b4rGIOYPgRRuFAvwjPQ/Yk+ql4dyhbw==", - "license": "MIT", - "dependencies": { - "@babel/helper-module-transforms": "^7.25.9", - "@babel/helper-plugin-utils": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-modules-commonjs": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-modules-commonjs/-/plugin-transform-modules-commonjs-7.25.9.tgz", - "integrity": "sha512-dwh2Ol1jWwL2MgkCzUSOvfmKElqQcuswAZypBSUsScMXvgdT8Ekq5YA6TtqpTVWH+4903NmboMuH1o9i8Rxlyg==", - "license": "MIT", - "dependencies": { - "@babel/helper-module-transforms": "^7.25.9", - "@babel/helper-plugin-utils": "^7.25.9", - "@babel/helper-simple-access": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-modules-systemjs": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-modules-systemjs/-/plugin-transform-modules-systemjs-7.25.9.tgz", - "integrity": "sha512-hyss7iIlH/zLHaehT+xwiymtPOpsiwIIRlCAOwBB04ta5Tt+lNItADdlXw3jAWZ96VJ2jlhl/c+PNIQPKNfvcA==", - "license": "MIT", - "dependencies": { - "@babel/helper-module-transforms": "^7.25.9", - "@babel/helper-plugin-utils": "^7.25.9", - "@babel/helper-validator-identifier": "^7.25.9", - "@babel/traverse": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-modules-umd": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-modules-umd/-/plugin-transform-modules-umd-7.25.9.tgz", - "integrity": "sha512-bS9MVObUgE7ww36HEfwe6g9WakQ0KF07mQF74uuXdkoziUPfKyu/nIm663kz//e5O1nPInPFx36z7WJmJ4yNEw==", - "license": "MIT", - "dependencies": { - "@babel/helper-module-transforms": "^7.25.9", - "@babel/helper-plugin-utils": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-named-capturing-groups-regex": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-named-capturing-groups-regex/-/plugin-transform-named-capturing-groups-regex-7.25.9.tgz", - "integrity": "sha512-oqB6WHdKTGl3q/ItQhpLSnWWOpjUJLsOCLVyeFgeTktkBSCiurvPOsyt93gibI9CmuKvTUEtWmG5VhZD+5T/KA==", - "license": "MIT", - "dependencies": { - "@babel/helper-create-regexp-features-plugin": "^7.25.9", - "@babel/helper-plugin-utils": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0" - } - }, - "node_modules/@babel/plugin-transform-new-target": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-new-target/-/plugin-transform-new-target-7.25.9.tgz", - "integrity": "sha512-U/3p8X1yCSoKyUj2eOBIx3FOn6pElFOKvAAGf8HTtItuPyB+ZeOqfn+mvTtg9ZlOAjsPdK3ayQEjqHjU/yLeVQ==", - "license": "MIT", - "dependencies": { - "@babel/helper-plugin-utils": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-nullish-coalescing-operator": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-nullish-coalescing-operator/-/plugin-transform-nullish-coalescing-operator-7.25.9.tgz", - "integrity": "sha512-ENfftpLZw5EItALAD4WsY/KUWvhUlZndm5GC7G3evUsVeSJB6p0pBeLQUnRnBCBx7zV0RKQjR9kCuwrsIrjWog==", - "license": "MIT", - "dependencies": { - "@babel/helper-plugin-utils": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-numeric-separator": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-numeric-separator/-/plugin-transform-numeric-separator-7.25.9.tgz", - "integrity": "sha512-TlprrJ1GBZ3r6s96Yq8gEQv82s8/5HnCVHtEJScUj90thHQbwe+E5MLhi2bbNHBEJuzrvltXSru+BUxHDoog7Q==", - "license": "MIT", - "dependencies": { - "@babel/helper-plugin-utils": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-object-rest-spread": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-object-rest-spread/-/plugin-transform-object-rest-spread-7.25.9.tgz", - "integrity": "sha512-fSaXafEE9CVHPweLYw4J0emp1t8zYTXyzN3UuG+lylqkvYd7RMrsOQ8TYx5RF231be0vqtFC6jnx3UmpJmKBYg==", - "license": "MIT", - "dependencies": { - "@babel/helper-compilation-targets": "^7.25.9", - "@babel/helper-plugin-utils": "^7.25.9", - "@babel/plugin-transform-parameters": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-object-super": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-object-super/-/plugin-transform-object-super-7.25.9.tgz", - "integrity": "sha512-Kj/Gh+Rw2RNLbCK1VAWj2U48yxxqL2x0k10nPtSdRa0O2xnHXalD0s+o1A6a0W43gJ00ANo38jxkQreckOzv5A==", - "license": "MIT", - "dependencies": { - "@babel/helper-plugin-utils": "^7.25.9", - "@babel/helper-replace-supers": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-optional-catch-binding": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-optional-catch-binding/-/plugin-transform-optional-catch-binding-7.25.9.tgz", - "integrity": "sha512-qM/6m6hQZzDcZF3onzIhZeDHDO43bkNNlOX0i8n3lR6zLbu0GN2d8qfM/IERJZYauhAHSLHy39NF0Ctdvcid7g==", - "license": "MIT", - "dependencies": { - "@babel/helper-plugin-utils": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-optional-chaining": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-optional-chaining/-/plugin-transform-optional-chaining-7.25.9.tgz", - "integrity": "sha512-6AvV0FsLULbpnXeBjrY4dmWF8F7gf8QnvTEoO/wX/5xm/xE1Xo8oPuD3MPS+KS9f9XBEAWN7X1aWr4z9HdOr7A==", - "license": "MIT", - "dependencies": { - "@babel/helper-plugin-utils": "^7.25.9", - "@babel/helper-skip-transparent-expression-wrappers": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-parameters": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-parameters/-/plugin-transform-parameters-7.25.9.tgz", - "integrity": "sha512-wzz6MKwpnshBAiRmn4jR8LYz/g8Ksg0o80XmwZDlordjwEk9SxBzTWC7F5ef1jhbrbOW2DJ5J6ayRukrJmnr0g==", - "license": "MIT", - "dependencies": { - "@babel/helper-plugin-utils": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-private-methods": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-private-methods/-/plugin-transform-private-methods-7.25.9.tgz", - "integrity": "sha512-D/JUozNpQLAPUVusvqMxyvjzllRaF8/nSrP1s2YGQT/W4LHK4xxsMcHjhOGTS01mp9Hda8nswb+FblLdJornQw==", - "license": "MIT", - "dependencies": { - "@babel/helper-create-class-features-plugin": "^7.25.9", - "@babel/helper-plugin-utils": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-private-property-in-object": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-private-property-in-object/-/plugin-transform-private-property-in-object-7.25.9.tgz", - "integrity": "sha512-Evf3kcMqzXA3xfYJmZ9Pg1OvKdtqsDMSWBDzZOPLvHiTt36E75jLDQo5w1gtRU95Q4E5PDttrTf25Fw8d/uWLw==", - "license": "MIT", - "dependencies": { - "@babel/helper-annotate-as-pure": "^7.25.9", - "@babel/helper-create-class-features-plugin": "^7.25.9", - "@babel/helper-plugin-utils": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-property-literals": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-property-literals/-/plugin-transform-property-literals-7.25.9.tgz", - "integrity": "sha512-IvIUeV5KrS/VPavfSM/Iu+RE6llrHrYIKY1yfCzyO/lMXHQ+p7uGhonmGVisv6tSBSVgWzMBohTcvkC9vQcQFA==", - "license": "MIT", - "dependencies": { - "@babel/helper-plugin-utils": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-react-constant-elements": { - "version": "7.25.1", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-react-constant-elements/-/plugin-transform-react-constant-elements-7.25.1.tgz", - "integrity": "sha512-SLV/giH/V4SmloZ6Dt40HjTGTAIkxn33TVIHxNGNvo8ezMhrxBkzisj4op1KZYPIOHFLqhv60OHvX+YRu4xbmQ==", - "license": "MIT", - "dependencies": { - "@babel/helper-plugin-utils": "^7.24.8" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-react-display-name": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-react-display-name/-/plugin-transform-react-display-name-7.25.9.tgz", - "integrity": "sha512-KJfMlYIUxQB1CJfO3e0+h0ZHWOTLCPP115Awhaz8U0Zpq36Gl/cXlpoyMRnUWlhNUBAzldnCiAZNvCDj7CrKxQ==", - "license": "MIT", - "dependencies": { - "@babel/helper-plugin-utils": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-react-jsx": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-react-jsx/-/plugin-transform-react-jsx-7.25.9.tgz", - "integrity": "sha512-s5XwpQYCqGerXl+Pu6VDL3x0j2d82eiV77UJ8a2mDHAW7j9SWRqQ2y1fNo1Z74CdcYipl5Z41zvjj4Nfzq36rw==", - "license": "MIT", - "dependencies": { - "@babel/helper-annotate-as-pure": "^7.25.9", - "@babel/helper-module-imports": "^7.25.9", - "@babel/helper-plugin-utils": "^7.25.9", - "@babel/plugin-syntax-jsx": "^7.25.9", - "@babel/types": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-react-jsx-development": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-react-jsx-development/-/plugin-transform-react-jsx-development-7.25.9.tgz", - "integrity": "sha512-9mj6rm7XVYs4mdLIpbZnHOYdpW42uoiBCTVowg7sP1thUOiANgMb4UtpRivR0pp5iL+ocvUv7X4mZgFRpJEzGw==", - "license": "MIT", - "dependencies": { - "@babel/plugin-transform-react-jsx": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-react-pure-annotations": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-react-pure-annotations/-/plugin-transform-react-pure-annotations-7.25.9.tgz", - "integrity": "sha512-KQ/Takk3T8Qzj5TppkS1be588lkbTp5uj7w6a0LeQaTMSckU/wK0oJ/pih+T690tkgI5jfmg2TqDJvd41Sj1Cg==", - "license": "MIT", - "dependencies": { - "@babel/helper-annotate-as-pure": "^7.25.9", - "@babel/helper-plugin-utils": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-regenerator": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-regenerator/-/plugin-transform-regenerator-7.25.9.tgz", - "integrity": "sha512-vwDcDNsgMPDGP0nMqzahDWE5/MLcX8sv96+wfX7as7LoF/kr97Bo/7fI00lXY4wUXYfVmwIIyG80fGZ1uvt2qg==", - "license": "MIT", - "dependencies": { - "@babel/helper-plugin-utils": "^7.25.9", - "regenerator-transform": "^0.15.2" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-regexp-modifiers": { - "version": "7.26.0", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-regexp-modifiers/-/plugin-transform-regexp-modifiers-7.26.0.tgz", - "integrity": "sha512-vN6saax7lrA2yA/Pak3sCxuD6F5InBjn9IcrIKQPjpsLvuHYLVroTxjdlVRHjjBWxKOqIwpTXDkOssYT4BFdRw==", - "license": "MIT", - "dependencies": { - "@babel/helper-create-regexp-features-plugin": "^7.25.9", - "@babel/helper-plugin-utils": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0" - } - }, - "node_modules/@babel/plugin-transform-reserved-words": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-reserved-words/-/plugin-transform-reserved-words-7.25.9.tgz", - "integrity": "sha512-7DL7DKYjn5Su++4RXu8puKZm2XBPHyjWLUidaPEkCUBbE7IPcsrkRHggAOOKydH1dASWdcUBxrkOGNxUv5P3Jg==", - "license": "MIT", - "dependencies": { - "@babel/helper-plugin-utils": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-runtime": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-runtime/-/plugin-transform-runtime-7.25.9.tgz", - "integrity": "sha512-nZp7GlEl+yULJrClz0SwHPqir3lc0zsPrDHQUcxGspSL7AKrexNSEfTbfqnDNJUO13bgKyfuOLMF8Xqtu8j3YQ==", - "license": "MIT", - "dependencies": { - "@babel/helper-module-imports": "^7.25.9", - "@babel/helper-plugin-utils": "^7.25.9", - "babel-plugin-polyfill-corejs2": "^0.4.10", - "babel-plugin-polyfill-corejs3": "^0.10.6", - "babel-plugin-polyfill-regenerator": "^0.6.1", - "semver": "^6.3.1" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-runtime/node_modules/semver": { - "version": "6.3.1", - "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.1.tgz", - "integrity": "sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA==", - "license": "ISC", - "bin": { - "semver": "bin/semver.js" - } - }, - "node_modules/@babel/plugin-transform-shorthand-properties": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-shorthand-properties/-/plugin-transform-shorthand-properties-7.25.9.tgz", - "integrity": "sha512-MUv6t0FhO5qHnS/W8XCbHmiRWOphNufpE1IVxhK5kuN3Td9FT1x4rx4K42s3RYdMXCXpfWkGSbCSd0Z64xA7Ng==", - "license": "MIT", - "dependencies": { - "@babel/helper-plugin-utils": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-spread": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-spread/-/plugin-transform-spread-7.25.9.tgz", - "integrity": "sha512-oNknIB0TbURU5pqJFVbOOFspVlrpVwo2H1+HUIsVDvp5VauGGDP1ZEvO8Nn5xyMEs3dakajOxlmkNW7kNgSm6A==", - "license": "MIT", - "dependencies": { - "@babel/helper-plugin-utils": "^7.25.9", - "@babel/helper-skip-transparent-expression-wrappers": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-sticky-regex": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-sticky-regex/-/plugin-transform-sticky-regex-7.25.9.tgz", - "integrity": "sha512-WqBUSgeVwucYDP9U/xNRQam7xV8W5Zf+6Eo7T2SRVUFlhRiMNFdFz58u0KZmCVVqs2i7SHgpRnAhzRNmKfi2uA==", - "license": "MIT", - "dependencies": { - "@babel/helper-plugin-utils": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-template-literals": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-template-literals/-/plugin-transform-template-literals-7.25.9.tgz", - "integrity": "sha512-o97AE4syN71M/lxrCtQByzphAdlYluKPDBzDVzMmfCobUjjhAryZV0AIpRPrxN0eAkxXO6ZLEScmt+PNhj2OTw==", - "license": "MIT", - "dependencies": { - "@babel/helper-plugin-utils": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-typeof-symbol": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-typeof-symbol/-/plugin-transform-typeof-symbol-7.25.9.tgz", - "integrity": "sha512-v61XqUMiueJROUv66BVIOi0Fv/CUuZuZMl5NkRoCVxLAnMexZ0A3kMe7vvZ0nulxMuMp0Mk6S5hNh48yki08ZA==", - "license": "MIT", - "dependencies": { - "@babel/helper-plugin-utils": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-typescript": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-typescript/-/plugin-transform-typescript-7.25.9.tgz", - "integrity": "sha512-7PbZQZP50tzv2KGGnhh82GSyMB01yKY9scIjf1a+GfZCtInOWqUH5+1EBU4t9fyR5Oykkkc9vFTs4OHrhHXljQ==", - "license": "MIT", - "dependencies": { - "@babel/helper-annotate-as-pure": "^7.25.9", - "@babel/helper-create-class-features-plugin": "^7.25.9", - "@babel/helper-plugin-utils": "^7.25.9", - "@babel/helper-skip-transparent-expression-wrappers": "^7.25.9", - "@babel/plugin-syntax-typescript": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-unicode-escapes": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-unicode-escapes/-/plugin-transform-unicode-escapes-7.25.9.tgz", - "integrity": "sha512-s5EDrE6bW97LtxOcGj1Khcx5AaXwiMmi4toFWRDP9/y0Woo6pXC+iyPu/KuhKtfSrNFd7jJB+/fkOtZy6aIC6Q==", - "license": "MIT", - "dependencies": { - "@babel/helper-plugin-utils": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-unicode-property-regex": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-unicode-property-regex/-/plugin-transform-unicode-property-regex-7.25.9.tgz", - "integrity": "sha512-Jt2d8Ga+QwRluxRQ307Vlxa6dMrYEMZCgGxoPR8V52rxPyldHu3hdlHspxaqYmE7oID5+kB+UKUB/eWS+DkkWg==", - "license": "MIT", - "dependencies": { - "@babel/helper-create-regexp-features-plugin": "^7.25.9", - "@babel/helper-plugin-utils": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-unicode-regex": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-unicode-regex/-/plugin-transform-unicode-regex-7.25.9.tgz", - "integrity": "sha512-yoxstj7Rg9dlNn9UQxzk4fcNivwv4nUYz7fYXBaKxvw/lnmPuOm/ikoELygbYq68Bls3D/D+NBPHiLwZdZZ4HA==", - "license": "MIT", - "dependencies": { - "@babel/helper-create-regexp-features-plugin": "^7.25.9", - "@babel/helper-plugin-utils": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-unicode-sets-regex": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-unicode-sets-regex/-/plugin-transform-unicode-sets-regex-7.25.9.tgz", - "integrity": "sha512-8BYqO3GeVNHtx69fdPshN3fnzUNLrWdHhk/icSwigksJGczKSizZ+Z6SBCxTs723Fr5VSNorTIK7a+R2tISvwQ==", - "license": "MIT", - "dependencies": { - "@babel/helper-create-regexp-features-plugin": "^7.25.9", - "@babel/helper-plugin-utils": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0" - } - }, - "node_modules/@babel/preset-env": { - "version": "7.26.0", - "resolved": "https://registry.npmjs.org/@babel/preset-env/-/preset-env-7.26.0.tgz", - "integrity": "sha512-H84Fxq0CQJNdPFT2DrfnylZ3cf5K43rGfWK4LJGPpjKHiZlk0/RzwEus3PDDZZg+/Er7lCA03MVacueUuXdzfw==", - "license": "MIT", - "dependencies": { - "@babel/compat-data": "^7.26.0", - "@babel/helper-compilation-targets": "^7.25.9", - "@babel/helper-plugin-utils": "^7.25.9", - "@babel/helper-validator-option": "^7.25.9", - "@babel/plugin-bugfix-firefox-class-in-computed-class-key": "^7.25.9", - "@babel/plugin-bugfix-safari-class-field-initializer-scope": "^7.25.9", - "@babel/plugin-bugfix-safari-id-destructuring-collision-in-function-expression": "^7.25.9", - "@babel/plugin-bugfix-v8-spread-parameters-in-optional-chaining": "^7.25.9", - "@babel/plugin-bugfix-v8-static-class-fields-redefine-readonly": "^7.25.9", - "@babel/plugin-proposal-private-property-in-object": "7.21.0-placeholder-for-preset-env.2", - "@babel/plugin-syntax-import-assertions": "^7.26.0", - "@babel/plugin-syntax-import-attributes": "^7.26.0", - "@babel/plugin-syntax-unicode-sets-regex": "^7.18.6", - "@babel/plugin-transform-arrow-functions": "^7.25.9", - "@babel/plugin-transform-async-generator-functions": "^7.25.9", - "@babel/plugin-transform-async-to-generator": "^7.25.9", - "@babel/plugin-transform-block-scoped-functions": "^7.25.9", - "@babel/plugin-transform-block-scoping": "^7.25.9", - "@babel/plugin-transform-class-properties": "^7.25.9", - "@babel/plugin-transform-class-static-block": "^7.26.0", - "@babel/plugin-transform-classes": "^7.25.9", - "@babel/plugin-transform-computed-properties": "^7.25.9", - "@babel/plugin-transform-destructuring": "^7.25.9", - "@babel/plugin-transform-dotall-regex": "^7.25.9", - "@babel/plugin-transform-duplicate-keys": "^7.25.9", - "@babel/plugin-transform-duplicate-named-capturing-groups-regex": "^7.25.9", - "@babel/plugin-transform-dynamic-import": "^7.25.9", - "@babel/plugin-transform-exponentiation-operator": "^7.25.9", - "@babel/plugin-transform-export-namespace-from": "^7.25.9", - "@babel/plugin-transform-for-of": "^7.25.9", - "@babel/plugin-transform-function-name": "^7.25.9", - "@babel/plugin-transform-json-strings": "^7.25.9", - "@babel/plugin-transform-literals": "^7.25.9", - "@babel/plugin-transform-logical-assignment-operators": "^7.25.9", - "@babel/plugin-transform-member-expression-literals": "^7.25.9", - "@babel/plugin-transform-modules-amd": "^7.25.9", - "@babel/plugin-transform-modules-commonjs": "^7.25.9", - "@babel/plugin-transform-modules-systemjs": "^7.25.9", - "@babel/plugin-transform-modules-umd": "^7.25.9", - "@babel/plugin-transform-named-capturing-groups-regex": "^7.25.9", - "@babel/plugin-transform-new-target": "^7.25.9", - "@babel/plugin-transform-nullish-coalescing-operator": "^7.25.9", - "@babel/plugin-transform-numeric-separator": "^7.25.9", - "@babel/plugin-transform-object-rest-spread": "^7.25.9", - "@babel/plugin-transform-object-super": "^7.25.9", - "@babel/plugin-transform-optional-catch-binding": "^7.25.9", - "@babel/plugin-transform-optional-chaining": "^7.25.9", - "@babel/plugin-transform-parameters": "^7.25.9", - "@babel/plugin-transform-private-methods": "^7.25.9", - "@babel/plugin-transform-private-property-in-object": "^7.25.9", - "@babel/plugin-transform-property-literals": "^7.25.9", - "@babel/plugin-transform-regenerator": "^7.25.9", - "@babel/plugin-transform-regexp-modifiers": "^7.26.0", - "@babel/plugin-transform-reserved-words": "^7.25.9", - "@babel/plugin-transform-shorthand-properties": "^7.25.9", - "@babel/plugin-transform-spread": "^7.25.9", - "@babel/plugin-transform-sticky-regex": "^7.25.9", - "@babel/plugin-transform-template-literals": "^7.25.9", - "@babel/plugin-transform-typeof-symbol": "^7.25.9", - "@babel/plugin-transform-unicode-escapes": "^7.25.9", - "@babel/plugin-transform-unicode-property-regex": "^7.25.9", - "@babel/plugin-transform-unicode-regex": "^7.25.9", - "@babel/plugin-transform-unicode-sets-regex": "^7.25.9", - "@babel/preset-modules": "0.1.6-no-external-plugins", - "babel-plugin-polyfill-corejs2": "^0.4.10", - "babel-plugin-polyfill-corejs3": "^0.10.6", - "babel-plugin-polyfill-regenerator": "^0.6.1", - "core-js-compat": "^3.38.1", - "semver": "^6.3.1" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/preset-env/node_modules/semver": { - "version": "6.3.1", - "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.1.tgz", - "integrity": "sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA==", - "license": "ISC", - "bin": { - "semver": "bin/semver.js" - } - }, - "node_modules/@babel/preset-modules": { - "version": "0.1.6-no-external-plugins", - "resolved": "https://registry.npmjs.org/@babel/preset-modules/-/preset-modules-0.1.6-no-external-plugins.tgz", - "integrity": "sha512-HrcgcIESLm9aIR842yhJ5RWan/gebQUJ6E/E5+rf0y9o6oj7w0Br+sWuL6kEQ/o/AdfvR1Je9jG18/gnpwjEyA==", - "license": "MIT", - "dependencies": { - "@babel/helper-plugin-utils": "^7.0.0", - "@babel/types": "^7.4.4", - "esutils": "^2.0.2" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0 || ^8.0.0-0 <8.0.0" - } - }, - "node_modules/@babel/preset-react": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/preset-react/-/preset-react-7.25.9.tgz", - "integrity": "sha512-D3to0uSPiWE7rBrdIICCd0tJSIGpLaaGptna2+w7Pft5xMqLpA1sz99DK5TZ1TjGbdQ/VI1eCSZ06dv3lT4JOw==", - "license": "MIT", - "dependencies": { - "@babel/helper-plugin-utils": "^7.25.9", - "@babel/helper-validator-option": "^7.25.9", - "@babel/plugin-transform-react-display-name": "^7.25.9", - "@babel/plugin-transform-react-jsx": "^7.25.9", - "@babel/plugin-transform-react-jsx-development": "^7.25.9", - "@babel/plugin-transform-react-pure-annotations": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/preset-typescript": { - "version": "7.26.0", - "resolved": "https://registry.npmjs.org/@babel/preset-typescript/-/preset-typescript-7.26.0.tgz", - "integrity": "sha512-NMk1IGZ5I/oHhoXEElcm+xUnL/szL6xflkFZmoEU9xj1qSJXpiS7rsspYo92B4DRCDvZn2erT5LdsCeXAKNCkg==", - "license": "MIT", - "dependencies": { - "@babel/helper-plugin-utils": "^7.25.9", - "@babel/helper-validator-option": "^7.25.9", - "@babel/plugin-syntax-jsx": "^7.25.9", - "@babel/plugin-transform-modules-commonjs": "^7.25.9", - "@babel/plugin-transform-typescript": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/runtime": { - "version": "7.26.0", - "resolved": "https://registry.npmjs.org/@babel/runtime/-/runtime-7.26.0.tgz", - "integrity": "sha512-FDSOghenHTiToteC/QRlv2q3DhPZ/oOXTBoirfWNx1Cx3TMVcGWQtMMmQcSvb/JjpNeGzx8Pq/b4fKEJuWm1sw==", - "license": "MIT", - "dependencies": { - "regenerator-runtime": "^0.14.0" - }, - "engines": { - "node": ">=6.9.0" - } - }, - "node_modules/@babel/runtime-corejs3": { - "version": "7.26.0", - "resolved": "https://registry.npmjs.org/@babel/runtime-corejs3/-/runtime-corejs3-7.26.0.tgz", - "integrity": "sha512-YXHu5lN8kJCb1LOb9PgV6pvak43X2h4HvRApcN5SdWeaItQOzfn1hgP6jasD6KWQyJDBxrVmA9o9OivlnNJK/w==", - "license": "MIT", - "dependencies": { - "core-js-pure": "^3.30.2", - "regenerator-runtime": "^0.14.0" - }, - "engines": { - "node": ">=6.9.0" - } - }, - "node_modules/@babel/template": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/template/-/template-7.25.9.tgz", - "integrity": "sha512-9DGttpmPvIxBb/2uwpVo3dqJ+O6RooAFOS+lB+xDqoE2PVCE8nfoHMdZLpfCQRLwvohzXISPZcgxt80xLfsuwg==", - "license": "MIT", - "dependencies": { - "@babel/code-frame": "^7.25.9", - "@babel/parser": "^7.25.9", - "@babel/types": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - } - }, - "node_modules/@babel/traverse": { - "version": "7.25.9", - "resolved": "https://registry.npmjs.org/@babel/traverse/-/traverse-7.25.9.tgz", - "integrity": "sha512-ZCuvfwOwlz/bawvAuvcj8rrithP2/N55Tzz342AkTvq4qaWbGfmCk/tKhNaV2cthijKrPAA8SRJV5WWe7IBMJw==", - "license": "MIT", - "dependencies": { - "@babel/code-frame": "^7.25.9", - "@babel/generator": "^7.25.9", - "@babel/parser": "^7.25.9", - "@babel/template": "^7.25.9", - "@babel/types": "^7.25.9", - "debug": "^4.3.1", - "globals": "^11.1.0" - }, - "engines": { - "node": ">=6.9.0" - } - }, - "node_modules/@babel/types": { - "version": "7.26.0", - "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.26.0.tgz", - "integrity": "sha512-Z/yiTPj+lDVnF7lWeKCIJzaIkI0vYO87dMpZ4bg4TDrFe4XXLFWL1TbXU27gBP3QccxV9mZICCrnjnYlJjXHOA==", - "license": "MIT", - "dependencies": { - "@babel/helper-string-parser": "^7.25.9", - "@babel/helper-validator-identifier": "^7.25.9" - }, - "engines": { - "node": ">=6.9.0" - } - }, - "node_modules/@braintree/sanitize-url": { - "version": "6.0.4", - "resolved": "https://registry.npmjs.org/@braintree/sanitize-url/-/sanitize-url-6.0.4.tgz", - "integrity": "sha512-s3jaWicZd0pkP0jf5ysyHUI/RE7MHos6qlToFcGWXVp+ykHOy77OUMrfbgJ9it2C5bow7OIQwYYaHjk9XlBQ2A==", - "license": "MIT" - }, - "node_modules/@colors/colors": { - "version": "1.5.0", - "resolved": "https://registry.npmjs.org/@colors/colors/-/colors-1.5.0.tgz", - "integrity": "sha512-ooWCrlZP11i8GImSjTHYHLkvFDP48nS4+204nGb1RiX/WXYHmJA2III9/e2DWVabCESdW7hBAEzHRqUn9OUVvQ==", - "license": "MIT", - "optional": true, - "engines": { - "node": ">=0.1.90" - } - }, - "node_modules/@csstools/cascade-layer-name-parser": { - "version": "2.0.4", - "resolved": "https://registry.npmjs.org/@csstools/cascade-layer-name-parser/-/cascade-layer-name-parser-2.0.4.tgz", - "integrity": "sha512-7DFHlPuIxviKYZrOiwVU/PiHLm3lLUR23OMuEEtfEOQTOp9hzQ2JjdY6X5H18RVuUPJqSCI+qNnD5iOLMVE0bA==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT", - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "@csstools/css-parser-algorithms": "^3.0.4", - "@csstools/css-tokenizer": "^3.0.3" - } - }, - "node_modules/@csstools/color-helpers": { - "version": "5.0.1", - "resolved": "https://registry.npmjs.org/@csstools/color-helpers/-/color-helpers-5.0.1.tgz", - "integrity": "sha512-MKtmkA0BX87PKaO1NFRTFH+UnkgnmySQOvNxJubsadusqPEC2aJ9MOQiMceZJJ6oitUl/i0L6u0M1IrmAOmgBA==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "engines": { - "node": ">=18" - } - }, - "node_modules/@csstools/css-calc": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/@csstools/css-calc/-/css-calc-2.1.1.tgz", - "integrity": "sha512-rL7kaUnTkL9K+Cvo2pnCieqNpTKgQzy5f+N+5Iuko9HAoasP+xgprVh7KN/MaJVvVL1l0EzQq2MoqBHKSrDrag==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT", - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "@csstools/css-parser-algorithms": "^3.0.4", - "@csstools/css-tokenizer": "^3.0.3" - } - }, - "node_modules/@csstools/css-color-parser": { - "version": "3.0.7", - "resolved": "https://registry.npmjs.org/@csstools/css-color-parser/-/css-color-parser-3.0.7.tgz", - "integrity": "sha512-nkMp2mTICw32uE5NN+EsJ4f5N+IGFeCFu4bGpiKgb2Pq/7J/MpyLBeQ5ry4KKtRFZaYs6sTmcMYrSRIyj5DFKA==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT", - "dependencies": { - "@csstools/color-helpers": "^5.0.1", - "@csstools/css-calc": "^2.1.1" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "@csstools/css-parser-algorithms": "^3.0.4", - "@csstools/css-tokenizer": "^3.0.3" - } - }, - "node_modules/@csstools/css-parser-algorithms": { - "version": "3.0.4", - "resolved": "https://registry.npmjs.org/@csstools/css-parser-algorithms/-/css-parser-algorithms-3.0.4.tgz", - "integrity": "sha512-Up7rBoV77rv29d3uKHUIVubz1BTcgyUK72IvCQAbfbMv584xHcGKCKbWh7i8hPrRJ7qU4Y8IO3IY9m+iTB7P3A==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT", - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "@csstools/css-tokenizer": "^3.0.3" - } - }, - "node_modules/@csstools/css-tokenizer": { - "version": "3.0.3", - "resolved": "https://registry.npmjs.org/@csstools/css-tokenizer/-/css-tokenizer-3.0.3.tgz", - "integrity": "sha512-UJnjoFsmxfKUdNYdWgOB0mWUypuLvAfQPH1+pyvRJs6euowbFkFC6P13w1l8mJyi3vxYMxc9kld5jZEGRQs6bw==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT", - "engines": { - "node": ">=18" - } - }, - "node_modules/@csstools/media-query-list-parser": { - "version": "4.0.2", - "resolved": "https://registry.npmjs.org/@csstools/media-query-list-parser/-/media-query-list-parser-4.0.2.tgz", - "integrity": "sha512-EUos465uvVvMJehckATTlNqGj4UJWkTmdWuDMjqvSUkjGpmOyFZBVwb4knxCm/k2GMTXY+c/5RkdndzFYWeX5A==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT", - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "@csstools/css-parser-algorithms": "^3.0.4", - "@csstools/css-tokenizer": "^3.0.3" - } - }, - "node_modules/@csstools/postcss-cascade-layers": { - "version": "5.0.1", - "resolved": "https://registry.npmjs.org/@csstools/postcss-cascade-layers/-/postcss-cascade-layers-5.0.1.tgz", - "integrity": "sha512-XOfhI7GShVcKiKwmPAnWSqd2tBR0uxt+runAxttbSp/LY2U16yAVPmAf7e9q4JJ0d+xMNmpwNDLBXnmRCl3HMQ==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "dependencies": { - "@csstools/selector-specificity": "^5.0.0", - "postcss-selector-parser": "^7.0.0" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/@csstools/postcss-cascade-layers/node_modules/@csstools/selector-specificity": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/@csstools/selector-specificity/-/selector-specificity-5.0.0.tgz", - "integrity": "sha512-PCqQV3c4CoVm3kdPhyeZ07VmBRdH2EpMFA/pd9OASpOEC3aXNGoqPDAZ80D0cLpMBxnmk0+yNhGsEx31hq7Gtw==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss-selector-parser": "^7.0.0" - } - }, - "node_modules/@csstools/postcss-cascade-layers/node_modules/postcss-selector-parser": { - "version": "7.0.0", - "resolved": "https://registry.npmjs.org/postcss-selector-parser/-/postcss-selector-parser-7.0.0.tgz", - "integrity": "sha512-9RbEr1Y7FFfptd/1eEdntyjMwLeghW1bHX9GWjXo19vx4ytPQhANltvVxDggzJl7mnWM+dX28kb6cyS/4iQjlQ==", - "license": "MIT", - "dependencies": { - "cssesc": "^3.0.0", - "util-deprecate": "^1.0.2" - }, - "engines": { - "node": ">=4" - } - }, - "node_modules/@csstools/postcss-color-function": { - "version": "4.0.7", - "resolved": "https://registry.npmjs.org/@csstools/postcss-color-function/-/postcss-color-function-4.0.7.tgz", - "integrity": "sha512-aDHYmhNIHR6iLw4ElWhf+tRqqaXwKnMl0YsQ/X105Zc4dQwe6yJpMrTN6BwOoESrkDjOYMOfORviSSLeDTJkdQ==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "dependencies": { - "@csstools/css-color-parser": "^3.0.7", - "@csstools/css-parser-algorithms": "^3.0.4", - "@csstools/css-tokenizer": "^3.0.3", - "@csstools/postcss-progressive-custom-properties": "^4.0.0", - "@csstools/utilities": "^2.0.0" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/@csstools/postcss-color-mix-function": { - "version": "3.0.7", - "resolved": "https://registry.npmjs.org/@csstools/postcss-color-mix-function/-/postcss-color-mix-function-3.0.7.tgz", - "integrity": "sha512-e68Nev4CxZYCLcrfWhHH4u/N1YocOfTmw67/kVX5Rb7rnguqqLyxPjhHWjSBX8o4bmyuukmNf3wrUSU3//kT7g==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "dependencies": { - "@csstools/css-color-parser": "^3.0.7", - "@csstools/css-parser-algorithms": "^3.0.4", - "@csstools/css-tokenizer": "^3.0.3", - "@csstools/postcss-progressive-custom-properties": "^4.0.0", - "@csstools/utilities": "^2.0.0" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/@csstools/postcss-content-alt-text": { - "version": "2.0.4", - "resolved": "https://registry.npmjs.org/@csstools/postcss-content-alt-text/-/postcss-content-alt-text-2.0.4.tgz", - "integrity": "sha512-YItlZUOuZJCBlRaCf8Aucc1lgN41qYGALMly0qQllrxYJhiyzlI6RxOTMUvtWk+KhS8GphMDsDhKQ7KTPfEMSw==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "dependencies": { - "@csstools/css-parser-algorithms": "^3.0.4", - "@csstools/css-tokenizer": "^3.0.3", - "@csstools/postcss-progressive-custom-properties": "^4.0.0", - "@csstools/utilities": "^2.0.0" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/@csstools/postcss-exponential-functions": { - "version": "2.0.6", - "resolved": "https://registry.npmjs.org/@csstools/postcss-exponential-functions/-/postcss-exponential-functions-2.0.6.tgz", - "integrity": "sha512-IgJA5DQsQLu/upA3HcdvC6xEMR051ufebBTIXZ5E9/9iiaA7juXWz1ceYj814lnDYP/7eWjZnw0grRJlX4eI6g==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "dependencies": { - "@csstools/css-calc": "^2.1.1", - "@csstools/css-parser-algorithms": "^3.0.4", - "@csstools/css-tokenizer": "^3.0.3" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/@csstools/postcss-font-format-keywords": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@csstools/postcss-font-format-keywords/-/postcss-font-format-keywords-4.0.0.tgz", - "integrity": "sha512-usBzw9aCRDvchpok6C+4TXC57btc4bJtmKQWOHQxOVKen1ZfVqBUuCZ/wuqdX5GHsD0NRSr9XTP+5ID1ZZQBXw==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "dependencies": { - "@csstools/utilities": "^2.0.0", - "postcss-value-parser": "^4.2.0" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/@csstools/postcss-gamut-mapping": { - "version": "2.0.7", - "resolved": "https://registry.npmjs.org/@csstools/postcss-gamut-mapping/-/postcss-gamut-mapping-2.0.7.tgz", - "integrity": "sha512-gzFEZPoOkY0HqGdyeBXR3JP218Owr683u7KOZazTK7tQZBE8s2yhg06W1tshOqk7R7SWvw9gkw2TQogKpIW8Xw==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "dependencies": { - "@csstools/css-color-parser": "^3.0.7", - "@csstools/css-parser-algorithms": "^3.0.4", - "@csstools/css-tokenizer": "^3.0.3" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/@csstools/postcss-gradients-interpolation-method": { - "version": "5.0.7", - "resolved": "https://registry.npmjs.org/@csstools/postcss-gradients-interpolation-method/-/postcss-gradients-interpolation-method-5.0.7.tgz", - "integrity": "sha512-WgEyBeg6glUeTdS2XT7qeTFBthTJuXlS9GFro/DVomj7W7WMTamAwpoP4oQCq/0Ki2gvfRYFi/uZtmRE14/DFA==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "dependencies": { - "@csstools/css-color-parser": "^3.0.7", - "@csstools/css-parser-algorithms": "^3.0.4", - "@csstools/css-tokenizer": "^3.0.3", - "@csstools/postcss-progressive-custom-properties": "^4.0.0", - "@csstools/utilities": "^2.0.0" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/@csstools/postcss-hwb-function": { - "version": "4.0.7", - "resolved": "https://registry.npmjs.org/@csstools/postcss-hwb-function/-/postcss-hwb-function-4.0.7.tgz", - "integrity": "sha512-LKYqjO+wGwDCfNIEllessCBWfR4MS/sS1WXO+j00KKyOjm7jDW2L6jzUmqASEiv/kkJO39GcoIOvTTfB3yeBUA==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "dependencies": { - "@csstools/css-color-parser": "^3.0.7", - "@csstools/css-parser-algorithms": "^3.0.4", - "@csstools/css-tokenizer": "^3.0.3", - "@csstools/postcss-progressive-custom-properties": "^4.0.0", - "@csstools/utilities": "^2.0.0" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/@csstools/postcss-ic-unit": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@csstools/postcss-ic-unit/-/postcss-ic-unit-4.0.0.tgz", - "integrity": "sha512-9QT5TDGgx7wD3EEMN3BSUG6ckb6Eh5gSPT5kZoVtUuAonfPmLDJyPhqR4ntPpMYhUKAMVKAg3I/AgzqHMSeLhA==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "dependencies": { - "@csstools/postcss-progressive-custom-properties": "^4.0.0", - "@csstools/utilities": "^2.0.0", - "postcss-value-parser": "^4.2.0" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/@csstools/postcss-initial": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/@csstools/postcss-initial/-/postcss-initial-2.0.0.tgz", - "integrity": "sha512-dv2lNUKR+JV+OOhZm9paWzYBXOCi+rJPqJ2cJuhh9xd8USVrd0cBEPczla81HNOyThMQWeCcdln3gZkQV2kYxA==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/@csstools/postcss-is-pseudo-class": { - "version": "5.0.1", - "resolved": "https://registry.npmjs.org/@csstools/postcss-is-pseudo-class/-/postcss-is-pseudo-class-5.0.1.tgz", - "integrity": "sha512-JLp3POui4S1auhDR0n8wHd/zTOWmMsmK3nQd3hhL6FhWPaox5W7j1se6zXOG/aP07wV2ww0lxbKYGwbBszOtfQ==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "dependencies": { - "@csstools/selector-specificity": "^5.0.0", - "postcss-selector-parser": "^7.0.0" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/@csstools/postcss-is-pseudo-class/node_modules/@csstools/selector-specificity": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/@csstools/selector-specificity/-/selector-specificity-5.0.0.tgz", - "integrity": "sha512-PCqQV3c4CoVm3kdPhyeZ07VmBRdH2EpMFA/pd9OASpOEC3aXNGoqPDAZ80D0cLpMBxnmk0+yNhGsEx31hq7Gtw==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss-selector-parser": "^7.0.0" - } - }, - "node_modules/@csstools/postcss-is-pseudo-class/node_modules/postcss-selector-parser": { - "version": "7.0.0", - "resolved": "https://registry.npmjs.org/postcss-selector-parser/-/postcss-selector-parser-7.0.0.tgz", - "integrity": "sha512-9RbEr1Y7FFfptd/1eEdntyjMwLeghW1bHX9GWjXo19vx4ytPQhANltvVxDggzJl7mnWM+dX28kb6cyS/4iQjlQ==", - "license": "MIT", - "dependencies": { - "cssesc": "^3.0.0", - "util-deprecate": "^1.0.2" - }, - "engines": { - "node": ">=4" - } - }, - "node_modules/@csstools/postcss-light-dark-function": { - "version": "2.0.7", - "resolved": "https://registry.npmjs.org/@csstools/postcss-light-dark-function/-/postcss-light-dark-function-2.0.7.tgz", - "integrity": "sha512-ZZ0rwlanYKOHekyIPaU+sVm3BEHCe+Ha0/px+bmHe62n0Uc1lL34vbwrLYn6ote8PHlsqzKeTQdIejQCJ05tfw==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "dependencies": { - "@csstools/css-parser-algorithms": "^3.0.4", - "@csstools/css-tokenizer": "^3.0.3", - "@csstools/postcss-progressive-custom-properties": "^4.0.0", - "@csstools/utilities": "^2.0.0" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/@csstools/postcss-logical-float-and-clear": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/@csstools/postcss-logical-float-and-clear/-/postcss-logical-float-and-clear-3.0.0.tgz", - "integrity": "sha512-SEmaHMszwakI2rqKRJgE+8rpotFfne1ZS6bZqBoQIicFyV+xT1UF42eORPxJkVJVrH9C0ctUgwMSn3BLOIZldQ==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/@csstools/postcss-logical-overflow": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/@csstools/postcss-logical-overflow/-/postcss-logical-overflow-2.0.0.tgz", - "integrity": "sha512-spzR1MInxPuXKEX2csMamshR4LRaSZ3UXVaRGjeQxl70ySxOhMpP2252RAFsg8QyyBXBzuVOOdx1+bVO5bPIzA==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/@csstools/postcss-logical-overscroll-behavior": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/@csstools/postcss-logical-overscroll-behavior/-/postcss-logical-overscroll-behavior-2.0.0.tgz", - "integrity": "sha512-e/webMjoGOSYfqLunyzByZj5KKe5oyVg/YSbie99VEaSDE2kimFm0q1f6t/6Jo+VVCQ/jbe2Xy+uX+C4xzWs4w==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/@csstools/postcss-logical-resize": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/@csstools/postcss-logical-resize/-/postcss-logical-resize-3.0.0.tgz", - "integrity": "sha512-DFbHQOFW/+I+MY4Ycd/QN6Dg4Hcbb50elIJCfnwkRTCX05G11SwViI5BbBlg9iHRl4ytB7pmY5ieAFk3ws7yyg==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "dependencies": { - "postcss-value-parser": "^4.2.0" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/@csstools/postcss-logical-viewport-units": { - "version": "3.0.3", - "resolved": "https://registry.npmjs.org/@csstools/postcss-logical-viewport-units/-/postcss-logical-viewport-units-3.0.3.tgz", - "integrity": "sha512-OC1IlG/yoGJdi0Y+7duz/kU/beCwO+Gua01sD6GtOtLi7ByQUpcIqs7UE/xuRPay4cHgOMatWdnDdsIDjnWpPw==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "dependencies": { - "@csstools/css-tokenizer": "^3.0.3", - "@csstools/utilities": "^2.0.0" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/@csstools/postcss-media-minmax": { - "version": "2.0.6", - "resolved": "https://registry.npmjs.org/@csstools/postcss-media-minmax/-/postcss-media-minmax-2.0.6.tgz", - "integrity": "sha512-J1+4Fr2W3pLZsfxkFazK+9kr96LhEYqoeBszLmFjb6AjYs+g9oDAw3J5oQignLKk3rC9XHW+ebPTZ9FaW5u5pg==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT", - "dependencies": { - "@csstools/css-calc": "^2.1.1", - "@csstools/css-parser-algorithms": "^3.0.4", - "@csstools/css-tokenizer": "^3.0.3", - "@csstools/media-query-list-parser": "^4.0.2" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/@csstools/postcss-media-queries-aspect-ratio-number-values": { - "version": "3.0.4", - "resolved": "https://registry.npmjs.org/@csstools/postcss-media-queries-aspect-ratio-number-values/-/postcss-media-queries-aspect-ratio-number-values-3.0.4.tgz", - "integrity": "sha512-AnGjVslHMm5xw9keusQYvjVWvuS7KWK+OJagaG0+m9QnIjZsrysD2kJP/tr/UJIyYtMCtu8OkUd+Rajb4DqtIQ==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "dependencies": { - "@csstools/css-parser-algorithms": "^3.0.4", - "@csstools/css-tokenizer": "^3.0.3", - "@csstools/media-query-list-parser": "^4.0.2" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/@csstools/postcss-nested-calc": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@csstools/postcss-nested-calc/-/postcss-nested-calc-4.0.0.tgz", - "integrity": "sha512-jMYDdqrQQxE7k9+KjstC3NbsmC063n1FTPLCgCRS2/qHUbHM0mNy9pIn4QIiQGs9I/Bg98vMqw7mJXBxa0N88A==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "dependencies": { - "@csstools/utilities": "^2.0.0", - "postcss-value-parser": "^4.2.0" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/@csstools/postcss-normalize-display-values": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@csstools/postcss-normalize-display-values/-/postcss-normalize-display-values-4.0.0.tgz", - "integrity": "sha512-HlEoG0IDRoHXzXnkV4in47dzsxdsjdz6+j7MLjaACABX2NfvjFS6XVAnpaDyGesz9gK2SC7MbNwdCHusObKJ9Q==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "dependencies": { - "postcss-value-parser": "^4.2.0" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/@csstools/postcss-oklab-function": { - "version": "4.0.7", - "resolved": "https://registry.npmjs.org/@csstools/postcss-oklab-function/-/postcss-oklab-function-4.0.7.tgz", - "integrity": "sha512-I6WFQIbEKG2IO3vhaMGZDkucbCaUSXMxvHNzDdnfsTCF5tc0UlV3Oe2AhamatQoKFjBi75dSEMrgWq3+RegsOQ==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "dependencies": { - "@csstools/css-color-parser": "^3.0.7", - "@csstools/css-parser-algorithms": "^3.0.4", - "@csstools/css-tokenizer": "^3.0.3", - "@csstools/postcss-progressive-custom-properties": "^4.0.0", - "@csstools/utilities": "^2.0.0" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/@csstools/postcss-progressive-custom-properties": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@csstools/postcss-progressive-custom-properties/-/postcss-progressive-custom-properties-4.0.0.tgz", - "integrity": "sha512-XQPtROaQjomnvLUSy/bALTR5VCtTVUFwYs1SblvYgLSeTo2a/bMNwUwo2piXw5rTv/FEYiy5yPSXBqg9OKUx7Q==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "dependencies": { - "postcss-value-parser": "^4.2.0" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/@csstools/postcss-random-function": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/@csstools/postcss-random-function/-/postcss-random-function-1.0.2.tgz", - "integrity": "sha512-vBCT6JvgdEkvRc91NFoNrLjgGtkLWt47GKT6E2UDn3nd8ZkMBiziQ1Md1OiKoSsgzxsSnGKG3RVdhlbdZEkHjA==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "dependencies": { - "@csstools/css-calc": "^2.1.1", - "@csstools/css-parser-algorithms": "^3.0.4", - "@csstools/css-tokenizer": "^3.0.3" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/@csstools/postcss-relative-color-syntax": { - "version": "3.0.7", - "resolved": "https://registry.npmjs.org/@csstools/postcss-relative-color-syntax/-/postcss-relative-color-syntax-3.0.7.tgz", - "integrity": "sha512-apbT31vsJVd18MabfPOnE977xgct5B1I+Jpf+Munw3n6kKb1MMuUmGGH+PT9Hm/fFs6fe61Q/EWnkrb4bNoNQw==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "dependencies": { - "@csstools/css-color-parser": "^3.0.7", - "@csstools/css-parser-algorithms": "^3.0.4", - "@csstools/css-tokenizer": "^3.0.3", - "@csstools/postcss-progressive-custom-properties": "^4.0.0", - "@csstools/utilities": "^2.0.0" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/@csstools/postcss-scope-pseudo-class": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/@csstools/postcss-scope-pseudo-class/-/postcss-scope-pseudo-class-4.0.1.tgz", - "integrity": "sha512-IMi9FwtH6LMNuLea1bjVMQAsUhFxJnyLSgOp/cpv5hrzWmrUYU5fm0EguNDIIOHUqzXode8F/1qkC/tEo/qN8Q==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "dependencies": { - "postcss-selector-parser": "^7.0.0" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/@csstools/postcss-scope-pseudo-class/node_modules/postcss-selector-parser": { - "version": "7.0.0", - "resolved": "https://registry.npmjs.org/postcss-selector-parser/-/postcss-selector-parser-7.0.0.tgz", - "integrity": "sha512-9RbEr1Y7FFfptd/1eEdntyjMwLeghW1bHX9GWjXo19vx4ytPQhANltvVxDggzJl7mnWM+dX28kb6cyS/4iQjlQ==", - "license": "MIT", - "dependencies": { - "cssesc": "^3.0.0", - "util-deprecate": "^1.0.2" - }, - "engines": { - "node": ">=4" - } - }, - "node_modules/@csstools/postcss-sign-functions": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/@csstools/postcss-sign-functions/-/postcss-sign-functions-1.1.1.tgz", - "integrity": "sha512-MslYkZCeMQDxetNkfmmQYgKCy4c+w9pPDfgOBCJOo/RI1RveEUdZQYtOfrC6cIZB7sD7/PHr2VGOcMXlZawrnA==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "dependencies": { - "@csstools/css-calc": "^2.1.1", - "@csstools/css-parser-algorithms": "^3.0.4", - "@csstools/css-tokenizer": "^3.0.3" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/@csstools/postcss-stepped-value-functions": { - "version": "4.0.6", - "resolved": "https://registry.npmjs.org/@csstools/postcss-stepped-value-functions/-/postcss-stepped-value-functions-4.0.6.tgz", - "integrity": "sha512-/dwlO9w8vfKgiADxpxUbZOWlL5zKoRIsCymYoh1IPuBsXODKanKnfuZRr32DEqT0//3Av1VjfNZU9yhxtEfIeA==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "dependencies": { - "@csstools/css-calc": "^2.1.1", - "@csstools/css-parser-algorithms": "^3.0.4", - "@csstools/css-tokenizer": "^3.0.3" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/@csstools/postcss-text-decoration-shorthand": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/@csstools/postcss-text-decoration-shorthand/-/postcss-text-decoration-shorthand-4.0.1.tgz", - "integrity": "sha512-xPZIikbx6jyzWvhms27uugIc0I4ykH4keRvoa3rxX5K7lEhkbd54rjj/dv60qOCTisoS+3bmwJTeyV1VNBrXaw==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "dependencies": { - "@csstools/color-helpers": "^5.0.1", - "postcss-value-parser": "^4.2.0" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/@csstools/postcss-trigonometric-functions": { - "version": "4.0.6", - "resolved": "https://registry.npmjs.org/@csstools/postcss-trigonometric-functions/-/postcss-trigonometric-functions-4.0.6.tgz", - "integrity": "sha512-c4Y1D2Why/PeccaSouXnTt6WcNHJkoJRidV2VW9s5gJ97cNxnLgQ4Qj8qOqkIR9VmTQKJyNcbF4hy79ZQnWD7A==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "dependencies": { - "@csstools/css-calc": "^2.1.1", - "@csstools/css-parser-algorithms": "^3.0.4", - "@csstools/css-tokenizer": "^3.0.3" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/@csstools/postcss-unset-value": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@csstools/postcss-unset-value/-/postcss-unset-value-4.0.0.tgz", - "integrity": "sha512-cBz3tOCI5Fw6NIFEwU3RiwK6mn3nKegjpJuzCndoGq3BZPkUjnsq7uQmIeMNeMbMk7YD2MfKcgCpZwX5jyXqCA==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/@csstools/utilities": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/@csstools/utilities/-/utilities-2.0.0.tgz", - "integrity": "sha512-5VdOr0Z71u+Yp3ozOx8T11N703wIFGVRgOWbOZMKgglPJsWA54MRIoMNVMa7shUToIhx5J8vX4sOZgD2XiihiQ==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/@discoveryjs/json-ext": { - "version": "0.5.7", - "resolved": "https://registry.npmjs.org/@discoveryjs/json-ext/-/json-ext-0.5.7.tgz", - "integrity": "sha512-dBVuXR082gk3jsFp7Rd/JI4kytwGHecnCoTtXFb7DB6CNHp4rg5k1bhg0nWdLGLnOV71lmDzGQaLMy8iPLY0pw==", - "license": "MIT", - "engines": { - "node": ">=10.0.0" - } - }, - "node_modules/@docsearch/css": { - "version": "3.8.2", - "resolved": "https://registry.npmjs.org/@docsearch/css/-/css-3.8.2.tgz", - "integrity": "sha512-y05ayQFyUmCXze79+56v/4HpycYF3uFqB78pLPrSV5ZKAlDuIAAJNhaRi8tTdRNXh05yxX/TyNnzD6LwSM89vQ==", - "license": "MIT" - }, - "node_modules/@docsearch/react": { - "version": "3.8.2", - "resolved": "https://registry.npmjs.org/@docsearch/react/-/react-3.8.2.tgz", - "integrity": "sha512-xCRrJQlTt8N9GU0DG4ptwHRkfnSnD/YpdeaXe02iKfqs97TkZJv60yE+1eq/tjPcVnTW8dP5qLP7itifFVV5eg==", - "license": "MIT", - "dependencies": { - "@algolia/autocomplete-core": "1.17.7", - "@algolia/autocomplete-preset-algolia": "1.17.7", - "@docsearch/css": "3.8.2", - "algoliasearch": "^5.14.2" - }, - "peerDependencies": { - "@types/react": ">= 16.8.0 < 19.0.0", - "react": ">= 16.8.0 < 19.0.0", - "react-dom": ">= 16.8.0 < 19.0.0", - "search-insights": ">= 1 < 3" - }, - "peerDependenciesMeta": { - "@types/react": { - "optional": true - }, - "react": { - "optional": true - }, - "react-dom": { - "optional": true - }, - "search-insights": { - "optional": true - } - } - }, - "node_modules/@docusaurus/babel": { - "version": "3.7.0", - "resolved": "https://registry.npmjs.org/@docusaurus/babel/-/babel-3.7.0.tgz", - "integrity": "sha512-0H5uoJLm14S/oKV3Keihxvh8RV+vrid+6Gv+2qhuzbqHanawga8tYnsdpjEyt36ucJjqlby2/Md2ObWjA02UXQ==", - "license": "MIT", - "dependencies": { - "@babel/core": "^7.25.9", - "@babel/generator": "^7.25.9", - "@babel/plugin-syntax-dynamic-import": "^7.8.3", - "@babel/plugin-transform-runtime": "^7.25.9", - "@babel/preset-env": "^7.25.9", - "@babel/preset-react": "^7.25.9", - "@babel/preset-typescript": "^7.25.9", - "@babel/runtime": "^7.25.9", - "@babel/runtime-corejs3": "^7.25.9", - "@babel/traverse": "^7.25.9", - "@docusaurus/logger": "3.7.0", - "@docusaurus/utils": "3.7.0", - "babel-plugin-dynamic-import-node": "^2.3.3", - "fs-extra": "^11.1.1", - "tslib": "^2.6.0" - }, - "engines": { - "node": ">=18.0" - } - }, - "node_modules/@docusaurus/bundler": { - "version": "3.7.0", - "resolved": "https://registry.npmjs.org/@docusaurus/bundler/-/bundler-3.7.0.tgz", - "integrity": "sha512-CUUT9VlSGukrCU5ctZucykvgCISivct+cby28wJwCC/fkQFgAHRp/GKv2tx38ZmXb7nacrKzFTcp++f9txUYGg==", - "license": "MIT", - "dependencies": { - "@babel/core": "^7.25.9", - "@docusaurus/babel": "3.7.0", - "@docusaurus/cssnano-preset": "3.7.0", - "@docusaurus/logger": "3.7.0", - "@docusaurus/types": "3.7.0", - "@docusaurus/utils": "3.7.0", - "babel-loader": "^9.2.1", - "clean-css": "^5.3.2", - "copy-webpack-plugin": "^11.0.0", - "css-loader": "^6.8.1", - "css-minimizer-webpack-plugin": "^5.0.1", - "cssnano": "^6.1.2", - "file-loader": "^6.2.0", - "html-minifier-terser": "^7.2.0", - "mini-css-extract-plugin": "^2.9.1", - "null-loader": "^4.0.1", - "postcss": "^8.4.26", - "postcss-loader": "^7.3.3", - "postcss-preset-env": "^10.1.0", - "react-dev-utils": "^12.0.1", - "terser-webpack-plugin": "^5.3.9", - "tslib": "^2.6.0", - "url-loader": "^4.1.1", - "webpack": "^5.95.0", - "webpackbar": "^6.0.1" - }, - "engines": { - "node": ">=18.0" - }, - "peerDependencies": { - "@docusaurus/faster": "*" - }, - "peerDependenciesMeta": { - "@docusaurus/faster": { - "optional": true - } - } - }, - "node_modules/@docusaurus/core": { - "version": "3.7.0", - "resolved": "https://registry.npmjs.org/@docusaurus/core/-/core-3.7.0.tgz", - "integrity": "sha512-b0fUmaL+JbzDIQaamzpAFpTviiaU4cX3Qz8cuo14+HGBCwa0evEK0UYCBFY3n4cLzL8Op1BueeroUD2LYAIHbQ==", - "license": "MIT", - "dependencies": { - "@docusaurus/babel": "3.7.0", - "@docusaurus/bundler": "3.7.0", - "@docusaurus/logger": "3.7.0", - "@docusaurus/mdx-loader": "3.7.0", - "@docusaurus/utils": "3.7.0", - "@docusaurus/utils-common": "3.7.0", - "@docusaurus/utils-validation": "3.7.0", - "boxen": "^6.2.1", - "chalk": "^4.1.2", - "chokidar": "^3.5.3", - "cli-table3": "^0.6.3", - "combine-promises": "^1.1.0", - "commander": "^5.1.0", - "core-js": "^3.31.1", - "del": "^6.1.1", - "detect-port": "^1.5.1", - "escape-html": "^1.0.3", - "eta": "^2.2.0", - "eval": "^0.1.8", - "fs-extra": "^11.1.1", - "html-tags": "^3.3.1", - "html-webpack-plugin": "^5.6.0", - "leven": "^3.1.0", - "lodash": "^4.17.21", - "p-map": "^4.0.0", - "prompts": "^2.4.2", - "react-dev-utils": "^12.0.1", - "react-helmet-async": "npm:@slorber/react-helmet-async@1.3.0", - "react-loadable": "npm:@docusaurus/react-loadable@6.0.0", - "react-loadable-ssr-addon-v5-slorber": "^1.0.1", - "react-router": "^5.3.4", - "react-router-config": "^5.1.1", - "react-router-dom": "^5.3.4", - "semver": "^7.5.4", - "serve-handler": "^6.1.6", - "shelljs": "^0.8.5", - "tslib": "^2.6.0", - "update-notifier": "^6.0.2", - "webpack": "^5.95.0", - "webpack-bundle-analyzer": "^4.10.2", - "webpack-dev-server": "^4.15.2", - "webpack-merge": "^6.0.1" - }, - "bin": { - "docusaurus": "bin/docusaurus.mjs" - }, - "engines": { - "node": ">=18.0" - }, - "peerDependencies": { - "@mdx-js/react": "^3.0.0", - "react": "^18.0.0 || ^19.0.0", - "react-dom": "^18.0.0 || ^19.0.0" - } - }, - "node_modules/@docusaurus/core/node_modules/webpack-merge": { - "version": "6.0.1", - "resolved": "https://registry.npmjs.org/webpack-merge/-/webpack-merge-6.0.1.tgz", - "integrity": "sha512-hXXvrjtx2PLYx4qruKl+kyRSLc52V+cCvMxRjmKwoA+CBbbF5GfIBtR6kCvl0fYGqTUPKB+1ktVmTHqMOzgCBg==", - "license": "MIT", - "dependencies": { - "clone-deep": "^4.0.1", - "flat": "^5.0.2", - "wildcard": "^2.0.1" - }, - "engines": { - "node": ">=18.0.0" - } - }, - "node_modules/@docusaurus/cssnano-preset": { - "version": "3.7.0", - "resolved": "https://registry.npmjs.org/@docusaurus/cssnano-preset/-/cssnano-preset-3.7.0.tgz", - "integrity": "sha512-X9GYgruZBSOozg4w4dzv9uOz8oK/EpPVQXkp0MM6Tsgp/nRIU9hJzJ0Pxg1aRa3xCeEQTOimZHcocQFlLwYajQ==", - "license": "MIT", - "dependencies": { - "cssnano-preset-advanced": "^6.1.2", - "postcss": "^8.4.38", - "postcss-sort-media-queries": "^5.2.0", - "tslib": "^2.6.0" - }, - "engines": { - "node": ">=18.0" - } - }, - "node_modules/@docusaurus/logger": { - "version": "3.7.0", - "resolved": "https://registry.npmjs.org/@docusaurus/logger/-/logger-3.7.0.tgz", - "integrity": "sha512-z7g62X7bYxCYmeNNuO9jmzxLQG95q9QxINCwpboVcNff3SJiHJbGrarxxOVMVmAh1MsrSfxWkVGv4P41ktnFsA==", - "license": "MIT", - "dependencies": { - "chalk": "^4.1.2", - "tslib": "^2.6.0" - }, - "engines": { - "node": ">=18.0" - } - }, - "node_modules/@docusaurus/mdx-loader": { - "version": "3.7.0", - "resolved": "https://registry.npmjs.org/@docusaurus/mdx-loader/-/mdx-loader-3.7.0.tgz", - "integrity": "sha512-OFBG6oMjZzc78/U3WNPSHs2W9ZJ723ewAcvVJaqS0VgyeUfmzUV8f1sv+iUHA0DtwiR5T5FjOxj6nzEE8LY6VA==", - "license": "MIT", - "dependencies": { - "@docusaurus/logger": "3.7.0", - "@docusaurus/utils": "3.7.0", - "@docusaurus/utils-validation": "3.7.0", - "@mdx-js/mdx": "^3.0.0", - "@slorber/remark-comment": "^1.0.0", - "escape-html": "^1.0.3", - "estree-util-value-to-estree": "^3.0.1", - "file-loader": "^6.2.0", - "fs-extra": "^11.1.1", - "image-size": "^1.0.2", - "mdast-util-mdx": "^3.0.0", - "mdast-util-to-string": "^4.0.0", - "rehype-raw": "^7.0.0", - "remark-directive": "^3.0.0", - "remark-emoji": "^4.0.0", - "remark-frontmatter": "^5.0.0", - "remark-gfm": "^4.0.0", - "stringify-object": "^3.3.0", - "tslib": "^2.6.0", - "unified": "^11.0.3", - "unist-util-visit": "^5.0.0", - "url-loader": "^4.1.1", - "vfile": "^6.0.1", - "webpack": "^5.88.1" - }, - "engines": { - "node": ">=18.0" - }, - "peerDependencies": { - "react": "^18.0.0 || ^19.0.0", - "react-dom": "^18.0.0 || ^19.0.0" - } - }, - "node_modules/@docusaurus/module-type-aliases": { - "version": "3.7.0", - "resolved": "https://registry.npmjs.org/@docusaurus/module-type-aliases/-/module-type-aliases-3.7.0.tgz", - "integrity": "sha512-g7WdPqDNaqA60CmBrr0cORTrsOit77hbsTj7xE2l71YhBn79sxdm7WMK7wfhcaafkbpIh7jv5ef5TOpf1Xv9Lg==", - "license": "MIT", - "dependencies": { - "@docusaurus/types": "3.7.0", - "@types/history": "^4.7.11", - "@types/react": "*", - "@types/react-router-config": "*", - "@types/react-router-dom": "*", - "react-helmet-async": "npm:@slorber/react-helmet-async@*", - "react-loadable": "npm:@docusaurus/react-loadable@6.0.0" - }, - "peerDependencies": { - "react": "*", - "react-dom": "*" - } - }, - "node_modules/@docusaurus/plugin-client-redirects": { - "version": "3.7.0", - "resolved": "https://registry.npmjs.org/@docusaurus/plugin-client-redirects/-/plugin-client-redirects-3.7.0.tgz", - "integrity": "sha512-6B4XAtE5ZVKOyhPgpgMkb7LwCkN+Hgd4vOnlbwR8nCdTQhLjz8MHbGlwwvZ/cay2SPNRX5KssqKAlcHVZP2m8g==", - "license": "MIT", - "dependencies": { - "@docusaurus/core": "3.7.0", - "@docusaurus/logger": "3.7.0", - "@docusaurus/utils": "3.7.0", - "@docusaurus/utils-common": "3.7.0", - "@docusaurus/utils-validation": "3.7.0", - "eta": "^2.2.0", - "fs-extra": "^11.1.1", - "lodash": "^4.17.21", - "tslib": "^2.6.0" - }, - "engines": { - "node": ">=18.0" - }, - "peerDependencies": { - "react": "^18.0.0 || ^19.0.0", - "react-dom": "^18.0.0 || ^19.0.0" - } - }, - "node_modules/@docusaurus/plugin-content-blog": { - "version": "3.7.0", - "resolved": "https://registry.npmjs.org/@docusaurus/plugin-content-blog/-/plugin-content-blog-3.7.0.tgz", - "integrity": "sha512-EFLgEz6tGHYWdPU0rK8tSscZwx+AsyuBW/r+tNig2kbccHYGUJmZtYN38GjAa3Fda4NU+6wqUO5kTXQSRBQD3g==", - "license": "MIT", - "dependencies": { - "@docusaurus/core": "3.7.0", - "@docusaurus/logger": "3.7.0", - "@docusaurus/mdx-loader": "3.7.0", - "@docusaurus/theme-common": "3.7.0", - "@docusaurus/types": "3.7.0", - "@docusaurus/utils": "3.7.0", - "@docusaurus/utils-common": "3.7.0", - "@docusaurus/utils-validation": "3.7.0", - "cheerio": "1.0.0-rc.12", - "feed": "^4.2.2", - "fs-extra": "^11.1.1", - "lodash": "^4.17.21", - "reading-time": "^1.5.0", - "srcset": "^4.0.0", - "tslib": "^2.6.0", - "unist-util-visit": "^5.0.0", - "utility-types": "^3.10.0", - "webpack": "^5.88.1" - }, - "engines": { - "node": ">=18.0" - }, - "peerDependencies": { - "@docusaurus/plugin-content-docs": "*", - "react": "^18.0.0 || ^19.0.0", - "react-dom": "^18.0.0 || ^19.0.0" - } - }, - "node_modules/@docusaurus/plugin-content-docs": { - "version": "3.7.0", - "resolved": "https://registry.npmjs.org/@docusaurus/plugin-content-docs/-/plugin-content-docs-3.7.0.tgz", - "integrity": "sha512-GXg5V7kC9FZE4FkUZA8oo/NrlRb06UwuICzI6tcbzj0+TVgjq/mpUXXzSgKzMS82YByi4dY2Q808njcBCyy6tQ==", - "license": "MIT", - "dependencies": { - "@docusaurus/core": "3.7.0", - "@docusaurus/logger": "3.7.0", - "@docusaurus/mdx-loader": "3.7.0", - "@docusaurus/module-type-aliases": "3.7.0", - "@docusaurus/theme-common": "3.7.0", - "@docusaurus/types": "3.7.0", - "@docusaurus/utils": "3.7.0", - "@docusaurus/utils-common": "3.7.0", - "@docusaurus/utils-validation": "3.7.0", - "@types/react-router-config": "^5.0.7", - "combine-promises": "^1.1.0", - "fs-extra": "^11.1.1", - "js-yaml": "^4.1.0", - "lodash": "^4.17.21", - "tslib": "^2.6.0", - "utility-types": "^3.10.0", - "webpack": "^5.88.1" - }, - "engines": { - "node": ">=18.0" - }, - "peerDependencies": { - "react": "^18.0.0 || ^19.0.0", - "react-dom": "^18.0.0 || ^19.0.0" - } - }, - "node_modules/@docusaurus/plugin-content-pages": { - "version": "3.7.0", - "resolved": "https://registry.npmjs.org/@docusaurus/plugin-content-pages/-/plugin-content-pages-3.7.0.tgz", - "integrity": "sha512-YJSU3tjIJf032/Aeao8SZjFOrXJbz/FACMveSMjLyMH4itQyZ2XgUIzt4y+1ISvvk5zrW4DABVT2awTCqBkx0Q==", - "license": "MIT", - "dependencies": { - "@docusaurus/core": "3.7.0", - "@docusaurus/mdx-loader": "3.7.0", - "@docusaurus/types": "3.7.0", - "@docusaurus/utils": "3.7.0", - "@docusaurus/utils-validation": "3.7.0", - "fs-extra": "^11.1.1", - "tslib": "^2.6.0", - "webpack": "^5.88.1" - }, - "engines": { - "node": ">=18.0" - }, - "peerDependencies": { - "react": "^18.0.0 || ^19.0.0", - "react-dom": "^18.0.0 || ^19.0.0" - } - }, - "node_modules/@docusaurus/plugin-debug": { - "version": "3.7.0", - "resolved": "https://registry.npmjs.org/@docusaurus/plugin-debug/-/plugin-debug-3.7.0.tgz", - "integrity": "sha512-Qgg+IjG/z4svtbCNyTocjIwvNTNEwgRjSXXSJkKVG0oWoH0eX/HAPiu+TS1HBwRPQV+tTYPWLrUypYFepfujZA==", - "license": "MIT", - "dependencies": { - "@docusaurus/core": "3.7.0", - "@docusaurus/types": "3.7.0", - "@docusaurus/utils": "3.7.0", - "fs-extra": "^11.1.1", - "react-json-view-lite": "^1.2.0", - "tslib": "^2.6.0" - }, - "engines": { - "node": ">=18.0" - }, - "peerDependencies": { - "react": "^18.0.0 || ^19.0.0", - "react-dom": "^18.0.0 || ^19.0.0" - } - }, - "node_modules/@docusaurus/plugin-google-analytics": { - "version": "3.7.0", - "resolved": "https://registry.npmjs.org/@docusaurus/plugin-google-analytics/-/plugin-google-analytics-3.7.0.tgz", - "integrity": "sha512-otIqiRV/jka6Snjf+AqB360XCeSv7lQC+DKYW+EUZf6XbuE8utz5PeUQ8VuOcD8Bk5zvT1MC4JKcd5zPfDuMWA==", - "license": "MIT", - "dependencies": { - "@docusaurus/core": "3.7.0", - "@docusaurus/types": "3.7.0", - "@docusaurus/utils-validation": "3.7.0", - "tslib": "^2.6.0" - }, - "engines": { - "node": ">=18.0" - }, - "peerDependencies": { - "react": "^18.0.0 || ^19.0.0", - "react-dom": "^18.0.0 || ^19.0.0" - } - }, - "node_modules/@docusaurus/plugin-google-gtag": { - "version": "3.7.0", - "resolved": "https://registry.npmjs.org/@docusaurus/plugin-google-gtag/-/plugin-google-gtag-3.7.0.tgz", - "integrity": "sha512-M3vrMct1tY65ModbyeDaMoA+fNJTSPe5qmchhAbtqhDD/iALri0g9LrEpIOwNaoLmm6lO88sfBUADQrSRSGSWA==", - "license": "MIT", - "dependencies": { - "@docusaurus/core": "3.7.0", - "@docusaurus/types": "3.7.0", - "@docusaurus/utils-validation": "3.7.0", - "@types/gtag.js": "^0.0.12", - "tslib": "^2.6.0" - }, - "engines": { - "node": ">=18.0" - }, - "peerDependencies": { - "react": "^18.0.0 || ^19.0.0", - "react-dom": "^18.0.0 || ^19.0.0" - } - }, - "node_modules/@docusaurus/plugin-google-tag-manager": { - "version": "3.7.0", - "resolved": "https://registry.npmjs.org/@docusaurus/plugin-google-tag-manager/-/plugin-google-tag-manager-3.7.0.tgz", - "integrity": "sha512-X8U78nb8eiMiPNg3jb9zDIVuuo/rE1LjGDGu+5m5CX4UBZzjMy+klOY2fNya6x8ACyE/L3K2erO1ErheP55W/w==", - "license": "MIT", - "dependencies": { - "@docusaurus/core": "3.7.0", - "@docusaurus/types": "3.7.0", - "@docusaurus/utils-validation": "3.7.0", - "tslib": "^2.6.0" - }, - "engines": { - "node": ">=18.0" - }, - "peerDependencies": { - "react": "^18.0.0 || ^19.0.0", - "react-dom": "^18.0.0 || ^19.0.0" - } - }, - "node_modules/@docusaurus/plugin-sitemap": { - "version": "3.7.0", - "resolved": "https://registry.npmjs.org/@docusaurus/plugin-sitemap/-/plugin-sitemap-3.7.0.tgz", - "integrity": "sha512-bTRT9YLZ/8I/wYWKMQke18+PF9MV8Qub34Sku6aw/vlZ/U+kuEuRpQ8bTcNOjaTSfYsWkK4tTwDMHK2p5S86cA==", - "license": "MIT", - "dependencies": { - "@docusaurus/core": "3.7.0", - "@docusaurus/logger": "3.7.0", - "@docusaurus/types": "3.7.0", - "@docusaurus/utils": "3.7.0", - "@docusaurus/utils-common": "3.7.0", - "@docusaurus/utils-validation": "3.7.0", - "fs-extra": "^11.1.1", - "sitemap": "^7.1.1", - "tslib": "^2.6.0" - }, - "engines": { - "node": ">=18.0" - }, - "peerDependencies": { - "react": "^18.0.0 || ^19.0.0", - "react-dom": "^18.0.0 || ^19.0.0" - } - }, - "node_modules/@docusaurus/plugin-svgr": { - "version": "3.7.0", - "resolved": "https://registry.npmjs.org/@docusaurus/plugin-svgr/-/plugin-svgr-3.7.0.tgz", - "integrity": "sha512-HByXIZTbc4GV5VAUkZ2DXtXv1Qdlnpk3IpuImwSnEzCDBkUMYcec5282hPjn6skZqB25M1TYCmWS91UbhBGxQg==", - "license": "MIT", - "dependencies": { - "@docusaurus/core": "3.7.0", - "@docusaurus/types": "3.7.0", - "@docusaurus/utils": "3.7.0", - "@docusaurus/utils-validation": "3.7.0", - "@svgr/core": "8.1.0", - "@svgr/webpack": "^8.1.0", - "tslib": "^2.6.0", - "webpack": "^5.88.1" - }, - "engines": { - "node": ">=18.0" - }, - "peerDependencies": { - "react": "^18.0.0 || ^19.0.0", - "react-dom": "^18.0.0 || ^19.0.0" - } - }, - "node_modules/@docusaurus/preset-classic": { - "version": "3.7.0", - "resolved": "https://registry.npmjs.org/@docusaurus/preset-classic/-/preset-classic-3.7.0.tgz", - "integrity": "sha512-nPHj8AxDLAaQXs+O6+BwILFuhiWbjfQWrdw2tifOClQoNfuXDjfjogee6zfx6NGHWqshR23LrcN115DmkHC91Q==", - "license": "MIT", - "dependencies": { - "@docusaurus/core": "3.7.0", - "@docusaurus/plugin-content-blog": "3.7.0", - "@docusaurus/plugin-content-docs": "3.7.0", - "@docusaurus/plugin-content-pages": "3.7.0", - "@docusaurus/plugin-debug": "3.7.0", - "@docusaurus/plugin-google-analytics": "3.7.0", - "@docusaurus/plugin-google-gtag": "3.7.0", - "@docusaurus/plugin-google-tag-manager": "3.7.0", - "@docusaurus/plugin-sitemap": "3.7.0", - "@docusaurus/plugin-svgr": "3.7.0", - "@docusaurus/theme-classic": "3.7.0", - "@docusaurus/theme-common": "3.7.0", - "@docusaurus/theme-search-algolia": "3.7.0", - "@docusaurus/types": "3.7.0" - }, - "engines": { - "node": ">=18.0" - }, - "peerDependencies": { - "react": "^18.0.0 || ^19.0.0", - "react-dom": "^18.0.0 || ^19.0.0" - } - }, - "node_modules/@docusaurus/theme-classic": { - "version": "3.7.0", - "resolved": "https://registry.npmjs.org/@docusaurus/theme-classic/-/theme-classic-3.7.0.tgz", - "integrity": "sha512-MnLxG39WcvLCl4eUzHr0gNcpHQfWoGqzADCly54aqCofQX6UozOS9Th4RK3ARbM9m7zIRv3qbhggI53dQtx/hQ==", - "license": "MIT", - "dependencies": { - "@docusaurus/core": "3.7.0", - "@docusaurus/logger": "3.7.0", - "@docusaurus/mdx-loader": "3.7.0", - "@docusaurus/module-type-aliases": "3.7.0", - "@docusaurus/plugin-content-blog": "3.7.0", - "@docusaurus/plugin-content-docs": "3.7.0", - "@docusaurus/plugin-content-pages": "3.7.0", - "@docusaurus/theme-common": "3.7.0", - "@docusaurus/theme-translations": "3.7.0", - "@docusaurus/types": "3.7.0", - "@docusaurus/utils": "3.7.0", - "@docusaurus/utils-common": "3.7.0", - "@docusaurus/utils-validation": "3.7.0", - "@mdx-js/react": "^3.0.0", - "clsx": "^2.0.0", - "copy-text-to-clipboard": "^3.2.0", - "infima": "0.2.0-alpha.45", - "lodash": "^4.17.21", - "nprogress": "^0.2.0", - "postcss": "^8.4.26", - "prism-react-renderer": "^2.3.0", - "prismjs": "^1.29.0", - "react-router-dom": "^5.3.4", - "rtlcss": "^4.1.0", - "tslib": "^2.6.0", - "utility-types": "^3.10.0" - }, - "engines": { - "node": ">=18.0" - }, - "peerDependencies": { - "react": "^18.0.0 || ^19.0.0", - "react-dom": "^18.0.0 || ^19.0.0" - } - }, - "node_modules/@docusaurus/theme-common": { - "version": "3.7.0", - "resolved": "https://registry.npmjs.org/@docusaurus/theme-common/-/theme-common-3.7.0.tgz", - "integrity": "sha512-8eJ5X0y+gWDsURZnBfH0WabdNm8XMCXHv8ENy/3Z/oQKwaB/EHt5lP9VsTDTf36lKEp0V6DjzjFyFIB+CetL0A==", - "license": "MIT", - "dependencies": { - "@docusaurus/mdx-loader": "3.7.0", - "@docusaurus/module-type-aliases": "3.7.0", - "@docusaurus/utils": "3.7.0", - "@docusaurus/utils-common": "3.7.0", - "@types/history": "^4.7.11", - "@types/react": "*", - "@types/react-router-config": "*", - "clsx": "^2.0.0", - "parse-numeric-range": "^1.3.0", - "prism-react-renderer": "^2.3.0", - "tslib": "^2.6.0", - "utility-types": "^3.10.0" - }, - "engines": { - "node": ">=18.0" - }, - "peerDependencies": { - "@docusaurus/plugin-content-docs": "*", - "react": "^18.0.0 || ^19.0.0", - "react-dom": "^18.0.0 || ^19.0.0" - } - }, - "node_modules/@docusaurus/theme-search-algolia": { - "version": "3.7.0", - "resolved": "https://registry.npmjs.org/@docusaurus/theme-search-algolia/-/theme-search-algolia-3.7.0.tgz", - "integrity": "sha512-Al/j5OdzwRU1m3falm+sYy9AaB93S1XF1Lgk9Yc6amp80dNxJVplQdQTR4cYdzkGtuQqbzUA8+kaoYYO0RbK6g==", - "license": "MIT", - "dependencies": { - "@docsearch/react": "^3.8.1", - "@docusaurus/core": "3.7.0", - "@docusaurus/logger": "3.7.0", - "@docusaurus/plugin-content-docs": "3.7.0", - "@docusaurus/theme-common": "3.7.0", - "@docusaurus/theme-translations": "3.7.0", - "@docusaurus/utils": "3.7.0", - "@docusaurus/utils-validation": "3.7.0", - "algoliasearch": "^5.17.1", - "algoliasearch-helper": "^3.22.6", - "clsx": "^2.0.0", - "eta": "^2.2.0", - "fs-extra": "^11.1.1", - "lodash": "^4.17.21", - "tslib": "^2.6.0", - "utility-types": "^3.10.0" - }, - "engines": { - "node": ">=18.0" - }, - "peerDependencies": { - "react": "^18.0.0 || ^19.0.0", - "react-dom": "^18.0.0 || ^19.0.0" - } - }, - "node_modules/@docusaurus/theme-translations": { - "version": "3.7.0", - "resolved": "https://registry.npmjs.org/@docusaurus/theme-translations/-/theme-translations-3.7.0.tgz", - "integrity": "sha512-Ewq3bEraWDmienM6eaNK7fx+/lHMtGDHQyd1O+4+3EsDxxUmrzPkV7Ct3nBWTuE0MsoZr3yNwQVKjllzCMuU3g==", - "license": "MIT", - "dependencies": { - "fs-extra": "^11.1.1", - "tslib": "^2.6.0" - }, - "engines": { - "node": ">=18.0" - } - }, - "node_modules/@docusaurus/tsconfig": { - "version": "3.7.0", - "resolved": "https://registry.npmjs.org/@docusaurus/tsconfig/-/tsconfig-3.7.0.tgz", - "integrity": "sha512-vRsyj3yUZCjscgfgcFYjIsTcAru/4h4YH2/XAE8Rs7wWdnng98PgWKvP5ovVc4rmRpRg2WChVW0uOy2xHDvDBQ==", - "dev": true, - "license": "MIT" - }, - "node_modules/@docusaurus/types": { - "version": "3.7.0", - "resolved": "https://registry.npmjs.org/@docusaurus/types/-/types-3.7.0.tgz", - "integrity": "sha512-kOmZg5RRqJfH31m+6ZpnwVbkqMJrPOG5t0IOl4i/+3ruXyNfWzZ0lVtVrD0u4ONc/0NOsS9sWYaxxWNkH1LdLQ==", - "license": "MIT", - "dependencies": { - "@mdx-js/mdx": "^3.0.0", - "@types/history": "^4.7.11", - "@types/react": "*", - "commander": "^5.1.0", - "joi": "^17.9.2", - "react-helmet-async": "npm:@slorber/react-helmet-async@1.3.0", - "utility-types": "^3.10.0", - "webpack": "^5.95.0", - "webpack-merge": "^5.9.0" - }, - "peerDependencies": { - "react": "^18.0.0 || ^19.0.0", - "react-dom": "^18.0.0 || ^19.0.0" - } - }, - "node_modules/@docusaurus/utils": { - "version": "3.7.0", - "resolved": "https://registry.npmjs.org/@docusaurus/utils/-/utils-3.7.0.tgz", - "integrity": "sha512-e7zcB6TPnVzyUaHMJyLSArKa2AG3h9+4CfvKXKKWNx6hRs+p0a+u7HHTJBgo6KW2m+vqDnuIHK4X+bhmoghAFA==", - "license": "MIT", - "dependencies": { - "@docusaurus/logger": "3.7.0", - "@docusaurus/types": "3.7.0", - "@docusaurus/utils-common": "3.7.0", - "escape-string-regexp": "^4.0.0", - "file-loader": "^6.2.0", - "fs-extra": "^11.1.1", - "github-slugger": "^1.5.0", - "globby": "^11.1.0", - "gray-matter": "^4.0.3", - "jiti": "^1.20.0", - "js-yaml": "^4.1.0", - "lodash": "^4.17.21", - "micromatch": "^4.0.5", - "prompts": "^2.4.2", - "resolve-pathname": "^3.0.0", - "shelljs": "^0.8.5", - "tslib": "^2.6.0", - "url-loader": "^4.1.1", - "utility-types": "^3.10.0", - "webpack": "^5.88.1" - }, - "engines": { - "node": ">=18.0" - } - }, - "node_modules/@docusaurus/utils-common": { - "version": "3.7.0", - "resolved": "https://registry.npmjs.org/@docusaurus/utils-common/-/utils-common-3.7.0.tgz", - "integrity": "sha512-IZeyIfCfXy0Mevj6bWNg7DG7B8G+S6o6JVpddikZtWyxJguiQ7JYr0SIZ0qWd8pGNuMyVwriWmbWqMnK7Y5PwA==", - "license": "MIT", - "dependencies": { - "@docusaurus/types": "3.7.0", - "tslib": "^2.6.0" - }, - "engines": { - "node": ">=18.0" - } - }, - "node_modules/@docusaurus/utils-validation": { - "version": "3.7.0", - "resolved": "https://registry.npmjs.org/@docusaurus/utils-validation/-/utils-validation-3.7.0.tgz", - "integrity": "sha512-w8eiKk8mRdN+bNfeZqC4nyFoxNyI1/VExMKAzD9tqpJfLLbsa46Wfn5wcKH761g9WkKh36RtFV49iL9lh1DYBA==", - "license": "MIT", - "dependencies": { - "@docusaurus/logger": "3.7.0", - "@docusaurus/utils": "3.7.0", - "@docusaurus/utils-common": "3.7.0", - "fs-extra": "^11.2.0", - "joi": "^17.9.2", - "js-yaml": "^4.1.0", - "lodash": "^4.17.21", - "tslib": "^2.6.0" - }, - "engines": { - "node": ">=18.0" - } - }, - "node_modules/@exodus/schemasafe": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/@exodus/schemasafe/-/schemasafe-1.3.0.tgz", - "integrity": "sha512-5Aap/GaRupgNx/feGBwLLTVv8OQFfv3pq2lPRzPg9R+IOBnDgghTGW7l7EuVXOvg5cc/xSAlRW8rBrjIC3Nvqw==", - "license": "MIT" - }, - "node_modules/@faker-js/faker": { - "version": "5.5.3", - "resolved": "https://registry.npmjs.org/@faker-js/faker/-/faker-5.5.3.tgz", - "integrity": "sha512-R11tGE6yIFwqpaIqcfkcg7AICXzFg14+5h5v0TfF/9+RMDL6jhzCy/pxHVOfbALGdtVYdt6JdR21tuxEgl34dw==", - "deprecated": "Please update to a newer version.", - "license": "MIT" - }, - "node_modules/@hapi/hoek": { - "version": "9.3.0", - "resolved": "https://registry.npmjs.org/@hapi/hoek/-/hoek-9.3.0.tgz", - "integrity": "sha512-/c6rf4UJlmHlC9b5BaNvzAcFv7HZ2QHaV0D4/HNlBdvFnvQq8RI4kYdhyPCl7Xj+oWvTWQ8ujhqS53LIgAe6KQ==", - "license": "BSD-3-Clause" - }, - "node_modules/@hapi/topo": { - "version": "5.1.0", - "resolved": "https://registry.npmjs.org/@hapi/topo/-/topo-5.1.0.tgz", - "integrity": "sha512-foQZKJig7Ob0BMAYBfcJk8d77QtOe7Wo4ox7ff1lQYoNNAb6jwcY1ncdoy2e9wQZzvNy7ODZCYJkK8kzmcAnAg==", - "license": "BSD-3-Clause", - "dependencies": { - "@hapi/hoek": "^9.0.0" - } - }, - "node_modules/@hookform/error-message": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@hookform/error-message/-/error-message-2.0.1.tgz", - "integrity": "sha512-U410sAr92xgxT1idlu9WWOVjndxLdgPUHEB8Schr27C9eh7/xUnITWpCMF93s+lGiG++D4JnbSnrb5A21AdSNg==", - "license": "MIT", - "peerDependencies": { - "react": ">=16.8.0", - "react-dom": ">=16.8.0", - "react-hook-form": "^7.0.0" - } - }, - "node_modules/@isaacs/cliui": { - "version": "8.0.2", - "resolved": "https://registry.npmjs.org/@isaacs/cliui/-/cliui-8.0.2.tgz", - "integrity": "sha512-O8jcjabXaleOG9DQ0+ARXWZBTfnP4WNAqzuiJK7ll44AmxGKv/J2M4TPjxjY3znBCfvBXFzucm1twdyFybFqEA==", - "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", - "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-6.1.0.tgz", - "integrity": "sha512-7HSX4QQb4CspciLpVFwyRe79O3xsIZDDLER21kERQ71oaPodF8jL725AgJMFAYbooIqolJoRLuM81SpeUkpkvA==", - "license": "MIT", - "engines": { - "node": ">=12" - }, - "funding": { - "url": "https://github.com/chalk/ansi-regex?sponsor=1" - } - }, - "node_modules/@isaacs/cliui/node_modules/strip-ansi": { - "version": "7.1.0", - "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-7.1.0.tgz", - "integrity": "sha512-iq6eVVI64nQQTRYq2KtEg2d2uU7LElhTJwsH4YzIHZshxlgZms/wIc4VoDQTlG/IvVIrBKG06CrZnp0qv7hkcQ==", - "license": "MIT", - "dependencies": { - "ansi-regex": "^6.0.1" - }, - "engines": { - "node": ">=12" - }, - "funding": { - "url": "https://github.com/chalk/strip-ansi?sponsor=1" - } - }, - "node_modules/@jest/schemas": { - "version": "29.6.3", - "resolved": "https://registry.npmjs.org/@jest/schemas/-/schemas-29.6.3.tgz", - "integrity": "sha512-mo5j5X+jIZmJQveBKeS/clAueipV7KgiX1vMgCxam1RNYiqE1w62n0/tJJnHtjW8ZHcQco5gY85jA3mi0L+nSA==", - "license": "MIT", - "dependencies": { - "@sinclair/typebox": "^0.27.8" - }, - "engines": { - "node": "^14.15.0 || ^16.10.0 || >=18.0.0" - } - }, - "node_modules/@jest/types": { - "version": "29.6.3", - "resolved": "https://registry.npmjs.org/@jest/types/-/types-29.6.3.tgz", - "integrity": "sha512-u3UPsIilWKOM3F9CXtrG8LEJmNxwoCQC/XVj4IKYXvvpx7QIi/Kg1LI5uDmDpKlac62NUtX7eLjRh+jVZcLOzw==", - "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.5", - "resolved": "https://registry.npmjs.org/@jridgewell/gen-mapping/-/gen-mapping-0.3.5.tgz", - "integrity": "sha512-IzL8ZoEDIBRWEzlCcRhOaCupYyN5gdIK+Q6fbFdPDg6HqX6jpkItn7DFIpW9LQzXG6Df9sA7+OKnq0qlz/GaQg==", - "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", - "resolved": "https://registry.npmjs.org/@jridgewell/resolve-uri/-/resolve-uri-3.1.2.tgz", - "integrity": "sha512-bRISgCIjP20/tbWSPWMEi54QVPRZExkuD9lJL+UIxUKtwVJA8wW1Trb1jMs1RFXo1CBTNZ/5hpC9QvmKWdopKw==", - "license": "MIT", - "engines": { - "node": ">=6.0.0" - } - }, - "node_modules/@jridgewell/set-array": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/@jridgewell/set-array/-/set-array-1.2.1.tgz", - "integrity": "sha512-R8gLRTZeyp03ymzP/6Lil/28tGeGEzhx1q2k703KGWRAI1VdvPIXdG70VJc2pAMw3NA6JKL5hhFu1sJX0Mnn/A==", - "license": "MIT", - "engines": { - "node": ">=6.0.0" - } - }, - "node_modules/@jridgewell/source-map": { - "version": "0.3.6", - "resolved": "https://registry.npmjs.org/@jridgewell/source-map/-/source-map-0.3.6.tgz", - "integrity": "sha512-1ZJTZebgqllO79ue2bm3rIGud/bOe0pP5BjSRCRxxYkEZS8STV7zN84UBbiYu7jy+eCKSnVIUgoWWE/tt+shMQ==", - "license": "MIT", - "dependencies": { - "@jridgewell/gen-mapping": "^0.3.5", - "@jridgewell/trace-mapping": "^0.3.25" - } - }, - "node_modules/@jridgewell/sourcemap-codec": { - "version": "1.5.0", - "resolved": "https://registry.npmjs.org/@jridgewell/sourcemap-codec/-/sourcemap-codec-1.5.0.tgz", - "integrity": "sha512-gv3ZRaISU3fjPAgNsriBRqGWQL6quFx04YMPW/zD8XMLsU32mhCCbfbO6KZFLjvYpCZ8zyDEgqsgf+PwPaM7GQ==", - "license": "MIT" - }, - "node_modules/@jridgewell/trace-mapping": { - "version": "0.3.25", - "resolved": "https://registry.npmjs.org/@jridgewell/trace-mapping/-/trace-mapping-0.3.25.tgz", - "integrity": "sha512-vNk6aEwybGtawWmy/PzwnGDOjCkLWSD2wqvjGGAgOAwCGWySYXfYoxt00IJkTF+8Lb57DwOb3Aa0o9CApepiYQ==", - "license": "MIT", - "dependencies": { - "@jridgewell/resolve-uri": "^3.1.0", - "@jridgewell/sourcemap-codec": "^1.4.14" - } - }, - "node_modules/@jsdevtools/ono": { - "version": "7.1.3", - "resolved": "https://registry.npmjs.org/@jsdevtools/ono/-/ono-7.1.3.tgz", - "integrity": "sha512-4JQNk+3mVzK3xh2rqd6RB4J46qUR19azEHBneZyTZM+c456qOrbbM/5xcR8huNCCcbVt7+UmizG6GuUvPvKUYg==", - "license": "MIT" - }, - "node_modules/@leichtgewicht/ip-codec": { - "version": "2.0.5", - "resolved": "https://registry.npmjs.org/@leichtgewicht/ip-codec/-/ip-codec-2.0.5.tgz", - "integrity": "sha512-Vo+PSpZG2/fmgmiNzYK9qWRh8h/CHrwD0mo1h1DzL4yzHNSfWYujGTYsWGreD000gcgmZ7K4Ys6Tx9TxtsKdDw==", - "license": "MIT" - }, - "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==", - "license": "MIT", - "engines": { - "node": ">=8" - } - }, - "node_modules/@lukeed/uuid": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@lukeed/uuid/-/uuid-2.0.1.tgz", - "integrity": "sha512-qC72D4+CDdjGqJvkFMMEAtancHUQ7/d/tAiHf64z8MopFDmcrtbcJuerDtFceuAfQJ2pDSfCKCtbqoGBNnwg0w==", - "license": "MIT", - "dependencies": { - "@lukeed/csprng": "^1.1.0" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/@mdx-js/mdx": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/@mdx-js/mdx/-/mdx-3.0.1.tgz", - "integrity": "sha512-eIQ4QTrOWyL3LWEe/bu6Taqzq2HQvHcyTMaOrI95P2/LmJE7AsfPfgJGuFLPVqBUE1BC1rik3VIhU+s9u72arA==", - "license": "MIT", - "dependencies": { - "@types/estree": "^1.0.0", - "@types/estree-jsx": "^1.0.0", - "@types/hast": "^3.0.0", - "@types/mdx": "^2.0.0", - "collapse-white-space": "^2.0.0", - "devlop": "^1.0.0", - "estree-util-build-jsx": "^3.0.0", - "estree-util-is-identifier-name": "^3.0.0", - "estree-util-to-js": "^2.0.0", - "estree-walker": "^3.0.0", - "hast-util-to-estree": "^3.0.0", - "hast-util-to-jsx-runtime": "^2.0.0", - "markdown-extensions": "^2.0.0", - "periscopic": "^3.0.0", - "remark-mdx": "^3.0.0", - "remark-parse": "^11.0.0", - "remark-rehype": "^11.0.0", - "source-map": "^0.7.0", - "unified": "^11.0.0", - "unist-util-position-from-estree": "^2.0.0", - "unist-util-stringify-position": "^4.0.0", - "unist-util-visit": "^5.0.0", - "vfile": "^6.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/@mdx-js/react": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/@mdx-js/react/-/react-3.0.1.tgz", - "integrity": "sha512-9ZrPIU4MGf6et1m1ov3zKf+q9+deetI51zprKB1D/z3NOb+rUxxtEl3mCjW5wTGh6VhRdwPueh1oRzi6ezkA8A==", - "license": "MIT", - "dependencies": { - "@types/mdx": "^2.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - }, - "peerDependencies": { - "@types/react": ">=16", - "react": ">=16" - } - }, - "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==", - "license": "MIT", - "dependencies": { - "@nodelib/fs.stat": "2.0.5", - "run-parallel": "^1.1.9" - }, - "engines": { - "node": ">= 8" - } - }, - "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==", - "license": "MIT", - "engines": { - "node": ">= 8" - } - }, - "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==", - "license": "MIT", - "dependencies": { - "@nodelib/fs.scandir": "2.1.5", - "fastq": "^1.6.0" - }, - "engines": { - "node": ">= 8" - } - }, - "node_modules/@parcel/watcher": { - "version": "2.5.0", - "resolved": "https://registry.npmjs.org/@parcel/watcher/-/watcher-2.5.0.tgz", - "integrity": "sha512-i0GV1yJnm2n3Yq1qw6QrUrd/LI9bE8WEBOTtOkpCXHHdyN3TAGgqAK/DAT05z4fq2x04cARXt2pDmjWjL92iTQ==", - "hasInstallScript": true, - "license": "MIT", - "optional": true, - "dependencies": { - "detect-libc": "^1.0.3", - "is-glob": "^4.0.3", - "micromatch": "^4.0.5", - "node-addon-api": "^7.0.0" - }, - "engines": { - "node": ">= 10.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/parcel" - }, - "optionalDependencies": { - "@parcel/watcher-android-arm64": "2.5.0", - "@parcel/watcher-darwin-arm64": "2.5.0", - "@parcel/watcher-darwin-x64": "2.5.0", - "@parcel/watcher-freebsd-x64": "2.5.0", - "@parcel/watcher-linux-arm-glibc": "2.5.0", - "@parcel/watcher-linux-arm-musl": "2.5.0", - "@parcel/watcher-linux-arm64-glibc": "2.5.0", - "@parcel/watcher-linux-arm64-musl": "2.5.0", - "@parcel/watcher-linux-x64-glibc": "2.5.0", - "@parcel/watcher-linux-x64-musl": "2.5.0", - "@parcel/watcher-win32-arm64": "2.5.0", - "@parcel/watcher-win32-ia32": "2.5.0", - "@parcel/watcher-win32-x64": "2.5.0" - } - }, - "node_modules/@parcel/watcher-android-arm64": { - "version": "2.5.0", - "resolved": "https://registry.npmjs.org/@parcel/watcher-android-arm64/-/watcher-android-arm64-2.5.0.tgz", - "integrity": "sha512-qlX4eS28bUcQCdribHkg/herLe+0A9RyYC+mm2PXpncit8z5b3nSqGVzMNR3CmtAOgRutiZ02eIJJgP/b1iEFQ==", - "cpu": [ - "arm64" - ], - "license": "MIT", - "optional": true, - "os": [ - "android" - ], - "engines": { - "node": ">= 10.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/parcel" - } - }, - "node_modules/@parcel/watcher-darwin-arm64": { - "version": "2.5.0", - "resolved": "https://registry.npmjs.org/@parcel/watcher-darwin-arm64/-/watcher-darwin-arm64-2.5.0.tgz", - "integrity": "sha512-hyZ3TANnzGfLpRA2s/4U1kbw2ZI4qGxaRJbBH2DCSREFfubMswheh8TeiC1sGZ3z2jUf3s37P0BBlrD3sjVTUw==", - "cpu": [ - "arm64" - ], - "license": "MIT", - "optional": true, - "os": [ - "darwin" - ], - "engines": { - "node": ">= 10.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/parcel" - } - }, - "node_modules/@parcel/watcher-darwin-x64": { - "version": "2.5.0", - "resolved": "https://registry.npmjs.org/@parcel/watcher-darwin-x64/-/watcher-darwin-x64-2.5.0.tgz", - "integrity": "sha512-9rhlwd78saKf18fT869/poydQK8YqlU26TMiNg7AIu7eBp9adqbJZqmdFOsbZ5cnLp5XvRo9wcFmNHgHdWaGYA==", - "cpu": [ - "x64" - ], - "license": "MIT", - "optional": true, - "os": [ - "darwin" - ], - "engines": { - "node": ">= 10.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/parcel" - } - }, - "node_modules/@parcel/watcher-freebsd-x64": { - "version": "2.5.0", - "resolved": "https://registry.npmjs.org/@parcel/watcher-freebsd-x64/-/watcher-freebsd-x64-2.5.0.tgz", - "integrity": "sha512-syvfhZzyM8kErg3VF0xpV8dixJ+RzbUaaGaeb7uDuz0D3FK97/mZ5AJQ3XNnDsXX7KkFNtyQyFrXZzQIcN49Tw==", - "cpu": [ - "x64" - ], - "license": "MIT", - "optional": true, - "os": [ - "freebsd" - ], - "engines": { - "node": ">= 10.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/parcel" - } - }, - "node_modules/@parcel/watcher-linux-arm-glibc": { - "version": "2.5.0", - "resolved": "https://registry.npmjs.org/@parcel/watcher-linux-arm-glibc/-/watcher-linux-arm-glibc-2.5.0.tgz", - "integrity": "sha512-0VQY1K35DQET3dVYWpOaPFecqOT9dbuCfzjxoQyif1Wc574t3kOSkKevULddcR9znz1TcklCE7Ht6NIxjvTqLA==", - "cpu": [ - "arm" - ], - "license": "MIT", - "optional": true, - "os": [ - "linux" - ], - "engines": { - "node": ">= 10.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/parcel" - } - }, - "node_modules/@parcel/watcher-linux-arm-musl": { - "version": "2.5.0", - "resolved": "https://registry.npmjs.org/@parcel/watcher-linux-arm-musl/-/watcher-linux-arm-musl-2.5.0.tgz", - "integrity": "sha512-6uHywSIzz8+vi2lAzFeltnYbdHsDm3iIB57d4g5oaB9vKwjb6N6dRIgZMujw4nm5r6v9/BQH0noq6DzHrqr2pA==", - "cpu": [ - "arm" - ], - "license": "MIT", - "optional": true, - "os": [ - "linux" - ], - "engines": { - "node": ">= 10.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/parcel" - } - }, - "node_modules/@parcel/watcher-linux-arm64-glibc": { - "version": "2.5.0", - "resolved": "https://registry.npmjs.org/@parcel/watcher-linux-arm64-glibc/-/watcher-linux-arm64-glibc-2.5.0.tgz", - "integrity": "sha512-BfNjXwZKxBy4WibDb/LDCriWSKLz+jJRL3cM/DllnHH5QUyoiUNEp3GmL80ZqxeumoADfCCP19+qiYiC8gUBjA==", - "cpu": [ - "arm64" - ], - "license": "MIT", - "optional": true, - "os": [ - "linux" - ], - "engines": { - "node": ">= 10.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/parcel" - } - }, - "node_modules/@parcel/watcher-linux-arm64-musl": { - "version": "2.5.0", - "resolved": "https://registry.npmjs.org/@parcel/watcher-linux-arm64-musl/-/watcher-linux-arm64-musl-2.5.0.tgz", - "integrity": "sha512-S1qARKOphxfiBEkwLUbHjCY9BWPdWnW9j7f7Hb2jPplu8UZ3nes7zpPOW9bkLbHRvWM0WDTsjdOTUgW0xLBN1Q==", - "cpu": [ - "arm64" - ], - "license": "MIT", - "optional": true, - "os": [ - "linux" - ], - "engines": { - "node": ">= 10.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/parcel" - } - }, - "node_modules/@parcel/watcher-linux-x64-glibc": { - "version": "2.5.0", - "resolved": "https://registry.npmjs.org/@parcel/watcher-linux-x64-glibc/-/watcher-linux-x64-glibc-2.5.0.tgz", - "integrity": "sha512-d9AOkusyXARkFD66S6zlGXyzx5RvY+chTP9Jp0ypSTC9d4lzyRs9ovGf/80VCxjKddcUvnsGwCHWuF2EoPgWjw==", - "cpu": [ - "x64" - ], - "license": "MIT", - "optional": true, - "os": [ - "linux" - ], - "engines": { - "node": ">= 10.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/parcel" - } - }, - "node_modules/@parcel/watcher-linux-x64-musl": { - "version": "2.5.0", - "resolved": "https://registry.npmjs.org/@parcel/watcher-linux-x64-musl/-/watcher-linux-x64-musl-2.5.0.tgz", - "integrity": "sha512-iqOC+GoTDoFyk/VYSFHwjHhYrk8bljW6zOhPuhi5t9ulqiYq1togGJB5e3PwYVFFfeVgc6pbz3JdQyDoBszVaA==", - "cpu": [ - "x64" - ], - "license": "MIT", - "optional": true, - "os": [ - "linux" - ], - "engines": { - "node": ">= 10.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/parcel" - } - }, - "node_modules/@parcel/watcher-win32-arm64": { - "version": "2.5.0", - "resolved": "https://registry.npmjs.org/@parcel/watcher-win32-arm64/-/watcher-win32-arm64-2.5.0.tgz", - "integrity": "sha512-twtft1d+JRNkM5YbmexfcH/N4znDtjgysFaV9zvZmmJezQsKpkfLYJ+JFV3uygugK6AtIM2oADPkB2AdhBrNig==", - "cpu": [ - "arm64" - ], - "license": "MIT", - "optional": true, - "os": [ - "win32" - ], - "engines": { - "node": ">= 10.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/parcel" - } - }, - "node_modules/@parcel/watcher-win32-ia32": { - "version": "2.5.0", - "resolved": "https://registry.npmjs.org/@parcel/watcher-win32-ia32/-/watcher-win32-ia32-2.5.0.tgz", - "integrity": "sha512-+rgpsNRKwo8A53elqbbHXdOMtY/tAtTzManTWShB5Kk54N8Q9mzNWV7tV+IbGueCbcj826MfWGU3mprWtuf1TA==", - "cpu": [ - "ia32" - ], - "license": "MIT", - "optional": true, - "os": [ - "win32" - ], - "engines": { - "node": ">= 10.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/parcel" - } - }, - "node_modules/@parcel/watcher-win32-x64": { - "version": "2.5.0", - "resolved": "https://registry.npmjs.org/@parcel/watcher-win32-x64/-/watcher-win32-x64-2.5.0.tgz", - "integrity": "sha512-lPrxve92zEHdgeff3aiu4gDOIt4u7sJYha6wbdEZDCDUhtjTsOMiaJzG5lMY4GkWH8p0fMmO2Ppq5G5XXG+DQw==", - "cpu": [ - "x64" - ], - "license": "MIT", - "optional": true, - "os": [ - "win32" - ], - "engines": { - "node": ">= 10.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/parcel" - } - }, - "node_modules/@pkgjs/parseargs": { - "version": "0.11.0", - "resolved": "https://registry.npmjs.org/@pkgjs/parseargs/-/parseargs-0.11.0.tgz", - "integrity": "sha512-+1VkjdD0QBLPodGrJUeqarH8VAIvQODIbwh9XpP5Syisf7YoQgsJKPNFoqqLQlu+VQ/tVSshMR6loPMn8U+dPg==", - "license": "MIT", - "optional": true, - "engines": { - "node": ">=14" - } - }, - "node_modules/@pnpm/config.env-replace": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/@pnpm/config.env-replace/-/config.env-replace-1.1.0.tgz", - "integrity": "sha512-htyl8TWnKL7K/ESFa1oW2UB5lVDxuF5DpM7tBi6Hu2LNL3mWkIzNLG6N4zoCUP1lCKNxWy/3iu8mS8MvToGd6w==", - "license": "MIT", - "engines": { - "node": ">=12.22.0" - } - }, - "node_modules/@pnpm/network.ca-file": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/@pnpm/network.ca-file/-/network.ca-file-1.0.2.tgz", - "integrity": "sha512-YcPQ8a0jwYU9bTdJDpXjMi7Brhkr1mXsXrUJvjqM2mQDgkRiz8jFaQGOdaLxgjtUfQgZhKy/O3cG/YwmgKaxLA==", - "license": "MIT", - "dependencies": { - "graceful-fs": "4.2.10" - }, - "engines": { - "node": ">=12.22.0" - } - }, - "node_modules/@pnpm/network.ca-file/node_modules/graceful-fs": { - "version": "4.2.10", - "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.2.10.tgz", - "integrity": "sha512-9ByhssR2fPVsNZj478qUUbKfmL0+t5BDVyjShtyZZLiK7ZDAArFFfopyOTj0M05wE2tJPisA4iTnnXl2YoPvOA==", - "license": "ISC" - }, - "node_modules/@pnpm/npm-conf": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/@pnpm/npm-conf/-/npm-conf-2.3.0.tgz", - "integrity": "sha512-DqrO+oXGR7HCuicNy6quk6ALJSDDPKI7RZz1bP5im8mSL8J2e+9w26LdkjuAfpAjOutYUJVbnXnx4IbTQeIgfw==", - "license": "MIT", - "dependencies": { - "@pnpm/config.env-replace": "^1.1.0", - "@pnpm/network.ca-file": "^1.0.1", - "config-chain": "^1.1.11" - }, - "engines": { - "node": ">=12" - } - }, - "node_modules/@polka/url": { - "version": "1.0.0-next.25", - "resolved": "https://registry.npmjs.org/@polka/url/-/url-1.0.0-next.25.tgz", - "integrity": "sha512-j7P6Rgr3mmtdkeDGTe0E/aYyWEWVtc5yFXtHCRHs28/jptDEWfaVOc5T7cblqy1XKPPfCxJc/8DwQ5YgLOZOVQ==", - "license": "MIT" - }, - "node_modules/@redocly/ajv": { - "version": "8.11.2", - "resolved": "https://registry.npmjs.org/@redocly/ajv/-/ajv-8.11.2.tgz", - "integrity": "sha512-io1JpnwtIcvojV7QKDUSIuMN/ikdOUd1ReEnUnMKGfDVridQZ31J0MmIuqwuRjWDZfmvr+Q0MqCcfHM2gTivOg==", - "license": "MIT", - "dependencies": { - "fast-deep-equal": "^3.1.1", - "json-schema-traverse": "^1.0.0", - "require-from-string": "^2.0.2", - "uri-js-replace": "^1.0.1" - }, - "funding": { - "type": "github", - "url": "https://github.com/sponsors/epoberezkin" - } - }, - "node_modules/@redocly/config": { - "version": "0.11.0", - "resolved": "https://registry.npmjs.org/@redocly/config/-/config-0.11.0.tgz", - "integrity": "sha512-vAc77vCuWsVgLx2LN02P6jqLBhHuot6O1LsSJEAAkWEvXARSGSQVon50QW7jlbCMg9OFTYYYRPN4W6K/YmnM3w==", - "license": "MIT" - }, - "node_modules/@redocly/openapi-core": { - "version": "1.25.3", - "resolved": "https://registry.npmjs.org/@redocly/openapi-core/-/openapi-core-1.25.3.tgz", - "integrity": "sha512-dqJkyydgagW3FXX5cjtSUAnabsld4K6yq7RFgQ+ngI1m43PkEoSQt8pp+SfQDszSEoMbc7QKj8afbe7mZw17TA==", - "license": "MIT", - "dependencies": { - "@redocly/ajv": "^8.11.2", - "@redocly/config": "^0.11.0", - "colorette": "^1.2.0", - "https-proxy-agent": "^7.0.4", - "js-levenshtein": "^1.1.6", - "js-yaml": "^4.1.0", - "lodash.isequal": "^4.5.0", - "minimatch": "^5.0.1", - "node-fetch": "^2.6.1", - "pluralize": "^8.0.0", - "yaml-ast-parser": "0.0.43" - }, - "engines": { - "node": ">=14.19.0", - "npm": ">=7.0.0" - } - }, - "node_modules/@redocly/openapi-core/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==", - "license": "MIT", - "dependencies": { - "balanced-match": "^1.0.0" - } - }, - "node_modules/@redocly/openapi-core/node_modules/colorette": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/colorette/-/colorette-1.4.0.tgz", - "integrity": "sha512-Y2oEozpomLn7Q3HFP7dpww7AtMJplbM9lGZP6RDfHqmbeRjiwRg4n6VM6j4KLmRke85uWEI7JqF17f3pqdRA0g==", - "license": "MIT" - }, - "node_modules/@redocly/openapi-core/node_modules/minimatch": { - "version": "5.1.6", - "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-5.1.6.tgz", - "integrity": "sha512-lKwV/1brpG6mBUFHtb7NUmtABCb2WZZmm2wNiOA5hAb8VdCS4B3dtMWyvcoViccwAW/COERjXLt0zP1zXUN26g==", - "license": "ISC", - "dependencies": { - "brace-expansion": "^2.0.1" - }, - "engines": { - "node": ">=10" - } - }, - "node_modules/@reduxjs/toolkit": { - "version": "1.9.7", - "resolved": "https://registry.npmjs.org/@reduxjs/toolkit/-/toolkit-1.9.7.tgz", - "integrity": "sha512-t7v8ZPxhhKgOKtU+uyJT13lu4vL7az5aFi4IdoDs/eS548edn2M8Ik9h8fxgvMjGoAUVFSt6ZC1P5cWmQ014QQ==", - "license": "MIT", - "dependencies": { - "immer": "^9.0.21", - "redux": "^4.2.1", - "redux-thunk": "^2.4.2", - "reselect": "^4.1.8" - }, - "peerDependencies": { - "react": "^16.9.0 || ^17.0.0 || ^18", - "react-redux": "^7.2.1 || ^8.0.2" - }, - "peerDependenciesMeta": { - "react": { - "optional": true - }, - "react-redux": { - "optional": true - } - } - }, - "node_modules/@segment/analytics-core": { - "version": "1.8.0", - "resolved": "https://registry.npmjs.org/@segment/analytics-core/-/analytics-core-1.8.0.tgz", - "integrity": "sha512-6CrccsYRY33I3mONN2ZW8SdBpbLtu1Ict3xR+n0FemYF5RB/jG7pW6jOvDXULR8kuYMzMmGOP4HvlyUmf3qLpg==", - "license": "MIT", - "dependencies": { - "@lukeed/uuid": "^2.0.0", - "@segment/analytics-generic-utils": "1.2.0", - "dset": "^3.1.4", - "tslib": "^2.4.1" - } - }, - "node_modules/@segment/analytics-generic-utils": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/@segment/analytics-generic-utils/-/analytics-generic-utils-1.2.0.tgz", - "integrity": "sha512-DfnW6mW3YQOLlDQQdR89k4EqfHb0g/3XvBXkovH1FstUN93eL1kfW9CsDcVQyH3bAC5ZsFyjA/o/1Q2j0QeoWw==", - "license": "MIT", - "dependencies": { - "tslib": "^2.4.1" - } - }, - "node_modules/@segment/analytics-next": { - "version": "1.76.0", - "resolved": "https://registry.npmjs.org/@segment/analytics-next/-/analytics-next-1.76.0.tgz", - "integrity": "sha512-4n4vMvX0+bfypFWuu/UJNenT/Gv2+04SsjvnQL1eBd1hngKBV56EkCW+PCJyFRQQ7BnzHgWF4mY+vOPkdoke3A==", - "license": "MIT", - "dependencies": { - "@lukeed/uuid": "^2.0.0", - "@segment/analytics-core": "1.8.0", - "@segment/analytics-generic-utils": "1.2.0", - "@segment/analytics.js-video-plugins": "^0.2.1", - "@segment/facade": "^3.4.9", - "dset": "^3.1.4", - "js-cookie": "3.0.1", - "node-fetch": "^2.6.7", - "tslib": "^2.4.1", - "unfetch": "^4.1.0" - } - }, - "node_modules/@segment/analytics.js-video-plugins": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/@segment/analytics.js-video-plugins/-/analytics.js-video-plugins-0.2.1.tgz", - "integrity": "sha512-lZwCyEXT4aaHBLNK433okEKdxGAuyrVmop4BpQqQSJuRz0DglPZgd9B/XjiiWs1UyOankg2aNYMN3VcS8t4eSQ==", - "license": "ISC", - "dependencies": { - "unfetch": "^3.1.1" - } - }, - "node_modules/@segment/analytics.js-video-plugins/node_modules/unfetch": { - "version": "3.1.2", - "resolved": "https://registry.npmjs.org/unfetch/-/unfetch-3.1.2.tgz", - "integrity": "sha512-L0qrK7ZeAudGiKYw6nzFjnJ2D5WHblUBwmHIqtPS6oKUd+Hcpk7/hKsSmcHsTlpd1TbTNsiRBUKRq3bHLNIqIw==", - "license": "MIT" - }, - "node_modules/@segment/facade": { - "version": "3.4.10", - "resolved": "https://registry.npmjs.org/@segment/facade/-/facade-3.4.10.tgz", - "integrity": "sha512-xVQBbB/lNvk/u8+ey0kC/+g8pT3l0gCT8O2y9Z+StMMn3KAFAQ9w8xfgef67tJybktOKKU7pQGRPolRM1i1pdA==", - "license": "SEE LICENSE IN LICENSE", - "dependencies": { - "@segment/isodate-traverse": "^1.1.1", - "inherits": "^2.0.4", - "new-date": "^1.0.3", - "obj-case": "0.2.1" - } - }, - "node_modules/@segment/isodate": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/@segment/isodate/-/isodate-1.0.3.tgz", - "integrity": "sha512-BtanDuvJqnACFkeeYje7pWULVv8RgZaqKHWwGFnL/g/TH/CcZjkIVTfGDp/MAxmilYHUkrX70SqwnYSTNEaN7A==", - "license": "SEE LICENSE IN LICENSE" - }, - "node_modules/@segment/isodate-traverse": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/@segment/isodate-traverse/-/isodate-traverse-1.1.1.tgz", - "integrity": "sha512-+G6e1SgAUkcq0EDMi+SRLfT48TNlLPF3QnSgFGVs0V9F3o3fq/woQ2rHFlW20W0yy5NnCUH0QGU3Am2rZy/E3w==", - "license": "SEE LICENSE IN LICENSE", - "dependencies": { - "@segment/isodate": "^1.0.3" - } - }, - "node_modules/@sideway/address": { - "version": "4.1.5", - "resolved": "https://registry.npmjs.org/@sideway/address/-/address-4.1.5.tgz", - "integrity": "sha512-IqO/DUQHUkPeixNQ8n0JA6102hT9CmaljNTPmQ1u8MEhBo/R4Q8eKLN/vGZxuebwOroDB4cbpjheD4+/sKFK4Q==", - "license": "BSD-3-Clause", - "dependencies": { - "@hapi/hoek": "^9.0.0" - } - }, - "node_modules/@sideway/formula": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/@sideway/formula/-/formula-3.0.1.tgz", - "integrity": "sha512-/poHZJJVjx3L+zVD6g9KgHfYnb443oi7wLu/XKojDviHy6HOEOA6z1Trk5aR1dGcmPenJEgb2sK2I80LeS3MIg==", - "license": "BSD-3-Clause" - }, - "node_modules/@sideway/pinpoint": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/@sideway/pinpoint/-/pinpoint-2.0.0.tgz", - "integrity": "sha512-RNiOoTPkptFtSVzQevY/yWtZwf/RxyVnPy/OcA9HBM3MlGDnBEYL5B41H0MTn0Uec8Hi+2qUtTfG2WWZBmMejQ==", - "license": "BSD-3-Clause" - }, - "node_modules/@sinclair/typebox": { - "version": "0.27.8", - "resolved": "https://registry.npmjs.org/@sinclair/typebox/-/typebox-0.27.8.tgz", - "integrity": "sha512-+Fj43pSMwJs4KRrH/938Uf+uAELIgVBmQzg/q1YG10djyfA3TnrU8N8XzqCh/okZdszqBQTZf96idMfE5lnwTA==", - "license": "MIT" - }, - "node_modules/@sindresorhus/is": { - "version": "4.6.0", - "resolved": "https://registry.npmjs.org/@sindresorhus/is/-/is-4.6.0.tgz", - "integrity": "sha512-t09vSN3MdfsyCHoFcTRCH/iUtG7OJ0CsjzB8cjAmKc/va/kIgeDI/TxsigdncE/4be734m0cvIYwNaV4i2XqAw==", - "license": "MIT", - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sindresorhus/is?sponsor=1" - } - }, - "node_modules/@slorber/remark-comment": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/@slorber/remark-comment/-/remark-comment-1.0.0.tgz", - "integrity": "sha512-RCE24n7jsOj1M0UPvIQCHTe7fI0sFL4S2nwKVWwHyVr/wI/H8GosgsJGyhnsZoGFnD/P2hLf1mSbrrgSLN93NA==", - "license": "MIT", - "dependencies": { - "micromark-factory-space": "^1.0.0", - "micromark-util-character": "^1.1.0", - "micromark-util-symbol": "^1.0.1" - } - }, - "node_modules/@svgr/babel-plugin-add-jsx-attribute": { - "version": "8.0.0", - "resolved": "https://registry.npmjs.org/@svgr/babel-plugin-add-jsx-attribute/-/babel-plugin-add-jsx-attribute-8.0.0.tgz", - "integrity": "sha512-b9MIk7yhdS1pMCZM8VeNfUlSKVRhsHZNMl5O9SfaX0l0t5wjdgu4IDzGB8bpnGBBOjGST3rRFVsaaEtI4W6f7g==", - "license": "MIT", - "engines": { - "node": ">=14" - }, - "funding": { - "type": "github", - "url": "https://github.com/sponsors/gregberge" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@svgr/babel-plugin-remove-jsx-attribute": { - "version": "8.0.0", - "resolved": "https://registry.npmjs.org/@svgr/babel-plugin-remove-jsx-attribute/-/babel-plugin-remove-jsx-attribute-8.0.0.tgz", - "integrity": "sha512-BcCkm/STipKvbCl6b7QFrMh/vx00vIP63k2eM66MfHJzPr6O2U0jYEViXkHJWqXqQYjdeA9cuCl5KWmlwjDvbA==", - "license": "MIT", - "engines": { - "node": ">=14" - }, - "funding": { - "type": "github", - "url": "https://github.com/sponsors/gregberge" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@svgr/babel-plugin-remove-jsx-empty-expression": { - "version": "8.0.0", - "resolved": "https://registry.npmjs.org/@svgr/babel-plugin-remove-jsx-empty-expression/-/babel-plugin-remove-jsx-empty-expression-8.0.0.tgz", - "integrity": "sha512-5BcGCBfBxB5+XSDSWnhTThfI9jcO5f0Ai2V24gZpG+wXF14BzwxxdDb4g6trdOux0rhibGs385BeFMSmxtS3uA==", - "license": "MIT", - "engines": { - "node": ">=14" - }, - "funding": { - "type": "github", - "url": "https://github.com/sponsors/gregberge" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@svgr/babel-plugin-replace-jsx-attribute-value": { - "version": "8.0.0", - "resolved": "https://registry.npmjs.org/@svgr/babel-plugin-replace-jsx-attribute-value/-/babel-plugin-replace-jsx-attribute-value-8.0.0.tgz", - "integrity": "sha512-KVQ+PtIjb1BuYT3ht8M5KbzWBhdAjjUPdlMtpuw/VjT8coTrItWX6Qafl9+ji831JaJcu6PJNKCV0bp01lBNzQ==", - "license": "MIT", - "engines": { - "node": ">=14" - }, - "funding": { - "type": "github", - "url": "https://github.com/sponsors/gregberge" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@svgr/babel-plugin-svg-dynamic-title": { - "version": "8.0.0", - "resolved": "https://registry.npmjs.org/@svgr/babel-plugin-svg-dynamic-title/-/babel-plugin-svg-dynamic-title-8.0.0.tgz", - "integrity": "sha512-omNiKqwjNmOQJ2v6ge4SErBbkooV2aAWwaPFs2vUY7p7GhVkzRkJ00kILXQvRhA6miHnNpXv7MRnnSjdRjK8og==", - "license": "MIT", - "engines": { - "node": ">=14" - }, - "funding": { - "type": "github", - "url": "https://github.com/sponsors/gregberge" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@svgr/babel-plugin-svg-em-dimensions": { - "version": "8.0.0", - "resolved": "https://registry.npmjs.org/@svgr/babel-plugin-svg-em-dimensions/-/babel-plugin-svg-em-dimensions-8.0.0.tgz", - "integrity": "sha512-mURHYnu6Iw3UBTbhGwE/vsngtCIbHE43xCRK7kCw4t01xyGqb2Pd+WXekRRoFOBIY29ZoOhUCTEweDMdrjfi9g==", - "license": "MIT", - "engines": { - "node": ">=14" - }, - "funding": { - "type": "github", - "url": "https://github.com/sponsors/gregberge" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@svgr/babel-plugin-transform-react-native-svg": { - "version": "8.1.0", - "resolved": "https://registry.npmjs.org/@svgr/babel-plugin-transform-react-native-svg/-/babel-plugin-transform-react-native-svg-8.1.0.tgz", - "integrity": "sha512-Tx8T58CHo+7nwJ+EhUwx3LfdNSG9R2OKfaIXXs5soiy5HtgoAEkDay9LIimLOcG8dJQH1wPZp/cnAv6S9CrR1Q==", - "license": "MIT", - "engines": { - "node": ">=14" - }, - "funding": { - "type": "github", - "url": "https://github.com/sponsors/gregberge" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@svgr/babel-plugin-transform-svg-component": { - "version": "8.0.0", - "resolved": "https://registry.npmjs.org/@svgr/babel-plugin-transform-svg-component/-/babel-plugin-transform-svg-component-8.0.0.tgz", - "integrity": "sha512-DFx8xa3cZXTdb/k3kfPeaixecQLgKh5NVBMwD0AQxOzcZawK4oo1Jh9LbrcACUivsCA7TLG8eeWgrDXjTMhRmw==", - "license": "MIT", - "engines": { - "node": ">=12" - }, - "funding": { - "type": "github", - "url": "https://github.com/sponsors/gregberge" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@svgr/babel-preset": { - "version": "8.1.0", - "resolved": "https://registry.npmjs.org/@svgr/babel-preset/-/babel-preset-8.1.0.tgz", - "integrity": "sha512-7EYDbHE7MxHpv4sxvnVPngw5fuR6pw79SkcrILHJ/iMpuKySNCl5W1qcwPEpU+LgyRXOaAFgH0KhwD18wwg6ug==", - "license": "MIT", - "dependencies": { - "@svgr/babel-plugin-add-jsx-attribute": "8.0.0", - "@svgr/babel-plugin-remove-jsx-attribute": "8.0.0", - "@svgr/babel-plugin-remove-jsx-empty-expression": "8.0.0", - "@svgr/babel-plugin-replace-jsx-attribute-value": "8.0.0", - "@svgr/babel-plugin-svg-dynamic-title": "8.0.0", - "@svgr/babel-plugin-svg-em-dimensions": "8.0.0", - "@svgr/babel-plugin-transform-react-native-svg": "8.1.0", - "@svgr/babel-plugin-transform-svg-component": "8.0.0" - }, - "engines": { - "node": ">=14" - }, - "funding": { - "type": "github", - "url": "https://github.com/sponsors/gregberge" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@svgr/core": { - "version": "8.1.0", - "resolved": "https://registry.npmjs.org/@svgr/core/-/core-8.1.0.tgz", - "integrity": "sha512-8QqtOQT5ACVlmsvKOJNEaWmRPmcojMOzCz4Hs2BGG/toAp/K38LcsMRyLp349glq5AzJbCEeimEoxaX6v/fLrA==", - "license": "MIT", - "dependencies": { - "@babel/core": "^7.21.3", - "@svgr/babel-preset": "8.1.0", - "camelcase": "^6.2.0", - "cosmiconfig": "^8.1.3", - "snake-case": "^3.0.4" - }, - "engines": { - "node": ">=14" - }, - "funding": { - "type": "github", - "url": "https://github.com/sponsors/gregberge" - } - }, - "node_modules/@svgr/hast-util-to-babel-ast": { - "version": "8.0.0", - "resolved": "https://registry.npmjs.org/@svgr/hast-util-to-babel-ast/-/hast-util-to-babel-ast-8.0.0.tgz", - "integrity": "sha512-EbDKwO9GpfWP4jN9sGdYwPBU0kdomaPIL2Eu4YwmgP+sJeXT+L7bMwJUBnhzfH8Q2qMBqZ4fJwpCyYsAN3mt2Q==", - "license": "MIT", - "dependencies": { - "@babel/types": "^7.21.3", - "entities": "^4.4.0" - }, - "engines": { - "node": ">=14" - }, - "funding": { - "type": "github", - "url": "https://github.com/sponsors/gregberge" - } - }, - "node_modules/@svgr/plugin-jsx": { - "version": "8.1.0", - "resolved": "https://registry.npmjs.org/@svgr/plugin-jsx/-/plugin-jsx-8.1.0.tgz", - "integrity": "sha512-0xiIyBsLlr8quN+WyuxooNW9RJ0Dpr8uOnH/xrCVO8GLUcwHISwj1AG0k+LFzteTkAA0GbX0kj9q6Dk70PTiPA==", - "license": "MIT", - "dependencies": { - "@babel/core": "^7.21.3", - "@svgr/babel-preset": "8.1.0", - "@svgr/hast-util-to-babel-ast": "8.0.0", - "svg-parser": "^2.0.4" - }, - "engines": { - "node": ">=14" - }, - "funding": { - "type": "github", - "url": "https://github.com/sponsors/gregberge" - }, - "peerDependencies": { - "@svgr/core": "*" - } - }, - "node_modules/@svgr/plugin-svgo": { - "version": "8.1.0", - "resolved": "https://registry.npmjs.org/@svgr/plugin-svgo/-/plugin-svgo-8.1.0.tgz", - "integrity": "sha512-Ywtl837OGO9pTLIN/onoWLmDQ4zFUycI1g76vuKGEz6evR/ZTJlJuz3G/fIkb6OVBJ2g0o6CGJzaEjfmEo3AHA==", - "license": "MIT", - "dependencies": { - "cosmiconfig": "^8.1.3", - "deepmerge": "^4.3.1", - "svgo": "^3.0.2" - }, - "engines": { - "node": ">=14" - }, - "funding": { - "type": "github", - "url": "https://github.com/sponsors/gregberge" - }, - "peerDependencies": { - "@svgr/core": "*" - } - }, - "node_modules/@svgr/webpack": { - "version": "8.1.0", - "resolved": "https://registry.npmjs.org/@svgr/webpack/-/webpack-8.1.0.tgz", - "integrity": "sha512-LnhVjMWyMQV9ZmeEy26maJk+8HTIbd59cH4F2MJ439k9DqejRisfFNGAPvRYlKETuh9LrImlS8aKsBgKjMA8WA==", - "license": "MIT", - "dependencies": { - "@babel/core": "^7.21.3", - "@babel/plugin-transform-react-constant-elements": "^7.21.3", - "@babel/preset-env": "^7.20.2", - "@babel/preset-react": "^7.18.6", - "@babel/preset-typescript": "^7.21.0", - "@svgr/core": "8.1.0", - "@svgr/plugin-jsx": "8.1.0", - "@svgr/plugin-svgo": "8.1.0" - }, - "engines": { - "node": ">=14" - }, - "funding": { - "type": "github", - "url": "https://github.com/sponsors/gregberge" - } - }, - "node_modules/@szmarczak/http-timer": { - "version": "5.0.1", - "resolved": "https://registry.npmjs.org/@szmarczak/http-timer/-/http-timer-5.0.1.tgz", - "integrity": "sha512-+PmQX0PiAYPMeVYe237LJAYvOMYW1j2rH5YROyS3b4CTVJum34HfRvKvAzozHAQG0TnHNdUfY9nCeUyRAs//cw==", - "license": "MIT", - "dependencies": { - "defer-to-connect": "^2.0.1" - }, - "engines": { - "node": ">=14.16" - } - }, - "node_modules/@trysound/sax": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/@trysound/sax/-/sax-0.2.0.tgz", - "integrity": "sha512-L7z9BgrNEcYyUYtF+HaEfiS5ebkh9jXqbszz7pC0hRBPaatV0XjSD3+eHrpqFemQfgwiFF0QPIarnIihIDn7OA==", - "license": "ISC", - "engines": { - "node": ">=10.13.0" - } - }, - "node_modules/@types/acorn": { - "version": "4.0.6", - "resolved": "https://registry.npmjs.org/@types/acorn/-/acorn-4.0.6.tgz", - "integrity": "sha512-veQTnWP+1D/xbxVrPC3zHnCZRjSrKfhbMUlEA43iMZLu7EsnTtkJklIuwrCPbOi8YkvDQAiW05VQQFvvz9oieQ==", - "license": "MIT", - "dependencies": { - "@types/estree": "*" - } - }, - "node_modules/@types/body-parser": { - "version": "1.19.5", - "resolved": "https://registry.npmjs.org/@types/body-parser/-/body-parser-1.19.5.tgz", - "integrity": "sha512-fB3Zu92ucau0iQ0JMCFQE7b/dv8Ot07NI3KaZIkIUNXq82k4eBAqUaneXfleGY9JWskeS9y+u0nXMyspcuQrCg==", - "license": "MIT", - "dependencies": { - "@types/connect": "*", - "@types/node": "*" - } - }, - "node_modules/@types/bonjour": { - "version": "3.5.13", - "resolved": "https://registry.npmjs.org/@types/bonjour/-/bonjour-3.5.13.tgz", - "integrity": "sha512-z9fJ5Im06zvUL548KvYNecEVlA7cVDkGUi6kZusb04mpyEFKCIZJvloCcmpmLaIahDpOQGHaHmG6imtPMmPXGQ==", - "license": "MIT", - "dependencies": { - "@types/node": "*" - } - }, - "node_modules/@types/connect": { - "version": "3.4.38", - "resolved": "https://registry.npmjs.org/@types/connect/-/connect-3.4.38.tgz", - "integrity": "sha512-K6uROf1LD88uDQqJCktA4yzL1YYAK6NgfsI0v/mTgyPKWsX1CnJ0XPSDhViejru1GcRkLWb8RlzFYJRqGUbaug==", - "license": "MIT", - "dependencies": { - "@types/node": "*" - } - }, - "node_modules/@types/connect-history-api-fallback": { - "version": "1.5.4", - "resolved": "https://registry.npmjs.org/@types/connect-history-api-fallback/-/connect-history-api-fallback-1.5.4.tgz", - "integrity": "sha512-n6Cr2xS1h4uAulPRdlw6Jl6s1oG8KrVilPN2yUITEs+K48EzMJJ3W1xy8K5eWuFvjp3R74AOIGSmp2UfBJ8HFw==", - "license": "MIT", - "dependencies": { - "@types/express-serve-static-core": "*", - "@types/node": "*" - } - }, - "node_modules/@types/debug": { - "version": "4.1.12", - "resolved": "https://registry.npmjs.org/@types/debug/-/debug-4.1.12.tgz", - "integrity": "sha512-vIChWdVG3LG1SMxEvI/AK+FWJthlrqlTu7fbrlywTkkaONwk/UAGaULXRlf8vkzFBLVm0zkMdCquhL5aOjhXPQ==", - "license": "MIT", - "dependencies": { - "@types/ms": "*" - } - }, - "node_modules/@types/eslint": { - "version": "9.6.1", - "resolved": "https://registry.npmjs.org/@types/eslint/-/eslint-9.6.1.tgz", - "integrity": "sha512-FXx2pKgId/WyYo2jXw63kk7/+TY7u7AziEJxJAnSFzHlqTAS3Ync6SvgYAN/k4/PQpnnVuzoMuVnByKK2qp0ag==", - "license": "MIT", - "dependencies": { - "@types/estree": "*", - "@types/json-schema": "*" - } - }, - "node_modules/@types/eslint-scope": { - "version": "3.7.7", - "resolved": "https://registry.npmjs.org/@types/eslint-scope/-/eslint-scope-3.7.7.tgz", - "integrity": "sha512-MzMFlSLBqNF2gcHWO0G1vP/YQyfvrxZ0bF+u7mzUdZ1/xK4A4sru+nraZz5i3iEIk1l1uyicaDVTB4QbbEkAYg==", - "license": "MIT", - "dependencies": { - "@types/eslint": "*", - "@types/estree": "*" - } - }, - "node_modules/@types/estree": { - "version": "1.0.6", - "resolved": "https://registry.npmjs.org/@types/estree/-/estree-1.0.6.tgz", - "integrity": "sha512-AYnb1nQyY49te+VRAVgmzfcgjYS91mY5P0TKUDCLEM+gNnA+3T6rWITXRLYCpahpqSQbN5cE+gHpnPyXjHWxcw==", - "license": "MIT" - }, - "node_modules/@types/estree-jsx": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/@types/estree-jsx/-/estree-jsx-1.0.5.tgz", - "integrity": "sha512-52CcUVNFyfb1A2ALocQw/Dd1BQFNmSdkuC3BkZ6iqhdMfQz7JWOFRuJFloOzjk+6WijU56m9oKXFAXc7o3Towg==", - "license": "MIT", - "dependencies": { - "@types/estree": "*" - } - }, - "node_modules/@types/express": { - "version": "4.17.21", - "resolved": "https://registry.npmjs.org/@types/express/-/express-4.17.21.tgz", - "integrity": "sha512-ejlPM315qwLpaQlQDTjPdsUFSc6ZsP4AN6AlWnogPjQ7CVi7PYF3YVz+CY3jE2pwYf7E/7HlDAN0rV2GxTG0HQ==", - "license": "MIT", - "dependencies": { - "@types/body-parser": "*", - "@types/express-serve-static-core": "^4.17.33", - "@types/qs": "*", - "@types/serve-static": "*" - } - }, - "node_modules/@types/express-serve-static-core": { - "version": "4.19.5", - "resolved": "https://registry.npmjs.org/@types/express-serve-static-core/-/express-serve-static-core-4.19.5.tgz", - "integrity": "sha512-y6W03tvrACO72aijJ5uF02FRq5cgDR9lUxddQ8vyF+GvmjJQqbzDcJngEjURc+ZsG31VI3hODNZJ2URj86pzmg==", - "license": "MIT", - "dependencies": { - "@types/node": "*", - "@types/qs": "*", - "@types/range-parser": "*", - "@types/send": "*" - } - }, - "node_modules/@types/gtag.js": { - "version": "0.0.12", - "resolved": "https://registry.npmjs.org/@types/gtag.js/-/gtag.js-0.0.12.tgz", - "integrity": "sha512-YQV9bUsemkzG81Ea295/nF/5GijnD2Af7QhEofh7xu+kvCN6RdodgNwwGWXB5GMI3NoyvQo0odNctoH/qLMIpg==", - "license": "MIT" - }, - "node_modules/@types/hast": { - "version": "3.0.4", - "resolved": "https://registry.npmjs.org/@types/hast/-/hast-3.0.4.tgz", - "integrity": "sha512-WPs+bbQw5aCj+x6laNGWLH3wviHtoCv/P3+otBhbOhJgG8qtpdAMlTCxLtsTWA7LH1Oh/bFCHsBn0TPS5m30EQ==", - "license": "MIT", - "dependencies": { - "@types/unist": "*" - } - }, - "node_modules/@types/history": { - "version": "4.7.11", - "resolved": "https://registry.npmjs.org/@types/history/-/history-4.7.11.tgz", - "integrity": "sha512-qjDJRrmvBMiTx+jyLxvLfJU7UznFuokDv4f3WRuriHKERccVpFU+8XMQUAbDzoiJCsmexxRExQeMwwCdamSKDA==", - "license": "MIT" - }, - "node_modules/@types/hoist-non-react-statics": { - "version": "3.3.5", - "resolved": "https://registry.npmjs.org/@types/hoist-non-react-statics/-/hoist-non-react-statics-3.3.5.tgz", - "integrity": "sha512-SbcrWzkKBw2cdwRTwQAswfpB9g9LJWfjtUeW/jvNwbhC8cpmmNYVePa+ncbUe0rGTQ7G3Ff6mYUN2VMfLVr+Sg==", - "license": "MIT", - "dependencies": { - "@types/react": "*", - "hoist-non-react-statics": "^3.3.0" - } - }, - "node_modules/@types/html-minifier-terser": { - "version": "6.1.0", - "resolved": "https://registry.npmjs.org/@types/html-minifier-terser/-/html-minifier-terser-6.1.0.tgz", - "integrity": "sha512-oh/6byDPnL1zeNXFrDXFLyZjkr1MsBG667IM792caf1L2UPOOMf65NFzjUH/ltyfwjAGfs1rsX1eftK0jC/KIg==", - "license": "MIT" - }, - "node_modules/@types/http-cache-semantics": { - "version": "4.0.4", - "resolved": "https://registry.npmjs.org/@types/http-cache-semantics/-/http-cache-semantics-4.0.4.tgz", - "integrity": "sha512-1m0bIFVc7eJWyve9S0RnuRgcQqF/Xd5QsUZAZeQFr1Q3/p9JWoQQEqmVy+DPTNpGXwhgIetAoYF8JSc33q29QA==", - "license": "MIT" - }, - "node_modules/@types/http-errors": { - "version": "2.0.4", - "resolved": "https://registry.npmjs.org/@types/http-errors/-/http-errors-2.0.4.tgz", - "integrity": "sha512-D0CFMMtydbJAegzOyHjtiKPLlvnm3iTZyZRSZoLq2mRhDdmLfIWOCYPfQJ4cu2erKghU++QvjcUjp/5h7hESpA==", - "license": "MIT" - }, - "node_modules/@types/http-proxy": { - "version": "1.17.14", - "resolved": "https://registry.npmjs.org/@types/http-proxy/-/http-proxy-1.17.14.tgz", - "integrity": "sha512-SSrD0c1OQzlFX7pGu1eXxSEjemej64aaNPRhhVYUGqXh0BtldAAx37MG8btcumvpgKyZp1F5Gn3JkktdxiFv6w==", - "license": "MIT", - "dependencies": { - "@types/node": "*" - } - }, - "node_modules/@types/istanbul-lib-coverage": { - "version": "2.0.6", - "resolved": "https://registry.npmjs.org/@types/istanbul-lib-coverage/-/istanbul-lib-coverage-2.0.6.tgz", - "integrity": "sha512-2QF/t/auWm0lsy8XtKVPG19v3sSOQlJe/YHZgfjb/KBBHOGSV+J2q/S671rcq9uTBrLAXmZpqJiaQbMT+zNU1w==", - "license": "MIT" - }, - "node_modules/@types/istanbul-lib-report": { - "version": "3.0.3", - "resolved": "https://registry.npmjs.org/@types/istanbul-lib-report/-/istanbul-lib-report-3.0.3.tgz", - "integrity": "sha512-NQn7AHQnk/RSLOxrBbGyJM/aVQ+pjj5HCgasFxc0K/KhoATfQ/47AyUl15I2yBUpihjmas+a+VJBOqecrFH+uA==", - "license": "MIT", - "dependencies": { - "@types/istanbul-lib-coverage": "*" - } - }, - "node_modules/@types/istanbul-reports": { - "version": "3.0.4", - "resolved": "https://registry.npmjs.org/@types/istanbul-reports/-/istanbul-reports-3.0.4.tgz", - "integrity": "sha512-pk2B1NWalF9toCRu6gjBzR69syFjP4Od8WRAX+0mmf9lAjCRicLOWc+ZrxZHx/0XRjotgkF9t6iaMJ+aXcOdZQ==", - "license": "MIT", - "dependencies": { - "@types/istanbul-lib-report": "*" - } - }, - "node_modules/@types/json-schema": { - "version": "7.0.15", - "resolved": "https://registry.npmjs.org/@types/json-schema/-/json-schema-7.0.15.tgz", - "integrity": "sha512-5+fP8P8MFNC+AyZCDxrB2pkZFPGzqQWUzpSeuuVLvm8VMcorNYavBqoFcxK8bQz4Qsbn4oUEEem4wDLfcysGHA==", - "license": "MIT" - }, - "node_modules/@types/mdast": { - "version": "4.0.4", - "resolved": "https://registry.npmjs.org/@types/mdast/-/mdast-4.0.4.tgz", - "integrity": "sha512-kGaNbPh1k7AFzgpud/gMdvIm5xuECykRR+JnWKQno9TAXVa6WIVCGTPvYGekIDL4uwCZQSYbUxNBSb1aUo79oA==", - "license": "MIT", - "dependencies": { - "@types/unist": "*" - } - }, - "node_modules/@types/mdx": { - "version": "2.0.13", - "resolved": "https://registry.npmjs.org/@types/mdx/-/mdx-2.0.13.tgz", - "integrity": "sha512-+OWZQfAYyio6YkJb3HLxDrvnx6SWWDbC0zVPfBRzUk0/nqoDyf6dNxQi3eArPe8rJ473nobTMQ/8Zk+LxJ+Yuw==", - "license": "MIT" - }, - "node_modules/@types/mime": { - "version": "1.3.5", - "resolved": "https://registry.npmjs.org/@types/mime/-/mime-1.3.5.tgz", - "integrity": "sha512-/pyBZWSLD2n0dcHE3hq8s8ZvcETHtEuF+3E7XVt0Ig2nvsVQXdghHVcEkIWjy9A0wKfTn97a/PSDYohKIlnP/w==", - "license": "MIT" - }, - "node_modules/@types/ms": { - "version": "0.7.34", - "resolved": "https://registry.npmjs.org/@types/ms/-/ms-0.7.34.tgz", - "integrity": "sha512-nG96G3Wp6acyAgJqGasjODb+acrI7KltPiRxzHPXnP3NgI28bpQDRv53olbqGXbfcgF5aiiHmO3xpwEpS5Ld9g==", - "license": "MIT" - }, - "node_modules/@types/node": { - "version": "22.1.0", - "resolved": "https://registry.npmjs.org/@types/node/-/node-22.1.0.tgz", - "integrity": "sha512-AOmuRF0R2/5j1knA3c6G3HOk523Ga+l+ZXltX8SF1+5oqcXijjfTd8fY3XRZqSihEu9XhtQnKYLmkFaoxgsJHw==", - "license": "MIT", - "dependencies": { - "undici-types": "~6.13.0" - } - }, - "node_modules/@types/node-forge": { - "version": "1.3.11", - "resolved": "https://registry.npmjs.org/@types/node-forge/-/node-forge-1.3.11.tgz", - "integrity": "sha512-FQx220y22OKNTqaByeBGqHWYz4cl94tpcxeFdvBo3wjG6XPBuZ0BNgNZRV5J5TFmmcsJ4IzsLkmGRiQbnYsBEQ==", - "license": "MIT", - "dependencies": { - "@types/node": "*" - } - }, - "node_modules/@types/parse-json": { - "version": "4.0.2", - "resolved": "https://registry.npmjs.org/@types/parse-json/-/parse-json-4.0.2.tgz", - "integrity": "sha512-dISoDXWWQwUquiKsyZ4Ng+HX2KsPL7LyHKHQwgGFEA3IaKac4Obd+h2a/a6waisAoepJlBcx9paWqjA8/HVjCw==", - "license": "MIT" - }, - "node_modules/@types/parse5": { - "version": "6.0.3", - "resolved": "https://registry.npmjs.org/@types/parse5/-/parse5-6.0.3.tgz", - "integrity": "sha512-SuT16Q1K51EAVPz1K29DJ/sXjhSQ0zjvsypYJ6tlwVsRV9jwW5Adq2ch8Dq8kDBCkYnELS7N7VNCSB5nC56t/g==", - "license": "MIT" - }, - "node_modules/@types/prismjs": { - "version": "1.26.4", - "resolved": "https://registry.npmjs.org/@types/prismjs/-/prismjs-1.26.4.tgz", - "integrity": "sha512-rlAnzkW2sZOjbqZ743IHUhFcvzaGbqijwOu8QZnZCjfQzBqFE3s4lOTJEsxikImav9uzz/42I+O7YUs1mWgMlg==", - "license": "MIT" - }, - "node_modules/@types/prop-types": { - "version": "15.7.12", - "resolved": "https://registry.npmjs.org/@types/prop-types/-/prop-types-15.7.12.tgz", - "integrity": "sha512-5zvhXYtRNRluoE/jAp4GVsSduVUzNWKkOZrCDBWYtE7biZywwdC2AcEzg+cSMLFRfVgeAFqpfNabiPjxFddV1Q==", - "license": "MIT" - }, - "node_modules/@types/qs": { - "version": "6.9.15", - "resolved": "https://registry.npmjs.org/@types/qs/-/qs-6.9.15.tgz", - "integrity": "sha512-uXHQKES6DQKKCLh441Xv/dwxOq1TVS3JPUMlEqoEglvlhR6Mxnlew/Xq/LRVHpLyk7iK3zODe1qYHIMltO7XGg==", - "license": "MIT" - }, - "node_modules/@types/range-parser": { - "version": "1.2.7", - "resolved": "https://registry.npmjs.org/@types/range-parser/-/range-parser-1.2.7.tgz", - "integrity": "sha512-hKormJbkJqzQGhziax5PItDUTMAM9uE2XXQmM37dyd4hVM+5aVl7oVxMVUiVQn2oCQFN/LKCZdvSM0pFRqbSmQ==", - "license": "MIT" - }, - "node_modules/@types/react": { - "version": "18.3.3", - "resolved": "https://registry.npmjs.org/@types/react/-/react-18.3.3.tgz", - "integrity": "sha512-hti/R0pS0q1/xx+TsI73XIqk26eBsISZ2R0wUijXIngRK9R/e7Xw/cXVxQK7R5JjW+SV4zGcn5hXjudkN/pLIw==", - "license": "MIT", - "dependencies": { - "@types/prop-types": "*", - "csstype": "^3.0.2" - } - }, - "node_modules/@types/react-redux": { - "version": "7.1.34", - "resolved": "https://registry.npmjs.org/@types/react-redux/-/react-redux-7.1.34.tgz", - "integrity": "sha512-GdFaVjEbYv4Fthm2ZLvj1VSCedV7TqE5y1kNwnjSdBOTXuRSgowux6J8TAct15T3CKBr63UMk+2CO7ilRhyrAQ==", - "license": "MIT", - "dependencies": { - "@types/hoist-non-react-statics": "^3.3.0", - "@types/react": "*", - "hoist-non-react-statics": "^3.3.0", - "redux": "^4.0.0" - } - }, - "node_modules/@types/react-router": { - "version": "5.1.20", - "resolved": "https://registry.npmjs.org/@types/react-router/-/react-router-5.1.20.tgz", - "integrity": "sha512-jGjmu/ZqS7FjSH6owMcD5qpq19+1RS9DeVRqfl1FeBMxTDQAGwlMWOcs52NDoXaNKyG3d1cYQFMs9rCrb88o9Q==", - "license": "MIT", - "dependencies": { - "@types/history": "^4.7.11", - "@types/react": "*" - } - }, - "node_modules/@types/react-router-config": { - "version": "5.0.11", - "resolved": "https://registry.npmjs.org/@types/react-router-config/-/react-router-config-5.0.11.tgz", - "integrity": "sha512-WmSAg7WgqW7m4x8Mt4N6ZyKz0BubSj/2tVUMsAHp+Yd2AMwcSbeFq9WympT19p5heCFmF97R9eD5uUR/t4HEqw==", - "license": "MIT", - "dependencies": { - "@types/history": "^4.7.11", - "@types/react": "*", - "@types/react-router": "^5.1.0" - } - }, - "node_modules/@types/react-router-dom": { - "version": "5.3.3", - "resolved": "https://registry.npmjs.org/@types/react-router-dom/-/react-router-dom-5.3.3.tgz", - "integrity": "sha512-kpqnYK4wcdm5UaWI3fLcELopqLrHgLqNsdpHauzlQktfkHL3npOSwtj1Uz9oKBAzs7lFtVkV8j83voAz2D8fhw==", - "license": "MIT", - "dependencies": { - "@types/history": "^4.7.11", - "@types/react": "*", - "@types/react-router": "*" - } - }, - "node_modules/@types/retry": { - "version": "0.12.0", - "resolved": "https://registry.npmjs.org/@types/retry/-/retry-0.12.0.tgz", - "integrity": "sha512-wWKOClTTiizcZhXnPY4wikVAwmdYHp8q6DmC+EJUzAMsycb7HB32Kh9RN4+0gExjmPmZSAQjgURXIGATPegAvA==", - "license": "MIT" - }, - "node_modules/@types/sax": { - "version": "1.2.7", - "resolved": "https://registry.npmjs.org/@types/sax/-/sax-1.2.7.tgz", - "integrity": "sha512-rO73L89PJxeYM3s3pPPjiPgVVcymqU490g0YO5n5By0k2Erzj6tay/4lr1CHAAU4JyOWd1rpQ8bCf6cZfHU96A==", - "license": "MIT", - "dependencies": { - "@types/node": "*" - } - }, - "node_modules/@types/send": { - "version": "0.17.4", - "resolved": "https://registry.npmjs.org/@types/send/-/send-0.17.4.tgz", - "integrity": "sha512-x2EM6TJOybec7c52BX0ZspPodMsQUd5L6PRwOunVyVUhXiBSKf3AezDL8Dgvgt5o0UfKNfuA0eMLr2wLT4AiBA==", - "license": "MIT", - "dependencies": { - "@types/mime": "^1", - "@types/node": "*" - } - }, - "node_modules/@types/serve-index": { - "version": "1.9.4", - "resolved": "https://registry.npmjs.org/@types/serve-index/-/serve-index-1.9.4.tgz", - "integrity": "sha512-qLpGZ/c2fhSs5gnYsQxtDEq3Oy8SXPClIXkW5ghvAvsNuVSA8k+gCONcUCS/UjLEYvYps+e8uBtfgXgvhwfNug==", - "license": "MIT", - "dependencies": { - "@types/express": "*" - } - }, - "node_modules/@types/serve-static": { - "version": "1.15.7", - "resolved": "https://registry.npmjs.org/@types/serve-static/-/serve-static-1.15.7.tgz", - "integrity": "sha512-W8Ym+h8nhuRwaKPaDw34QUkwsGi6Rc4yYqvKFo5rm2FUEhCFbzVWrxXUxuKK8TASjWsysJY0nsmNCGhCOIsrOw==", - "license": "MIT", - "dependencies": { - "@types/http-errors": "*", - "@types/node": "*", - "@types/send": "*" - } - }, - "node_modules/@types/sockjs": { - "version": "0.3.36", - "resolved": "https://registry.npmjs.org/@types/sockjs/-/sockjs-0.3.36.tgz", - "integrity": "sha512-MK9V6NzAS1+Ud7JV9lJLFqW85VbC9dq3LmwZCuBe4wBDgKC0Kj/jd8Xl+nSviU+Qc3+m7umHHyHg//2KSa0a0Q==", - "license": "MIT", - "dependencies": { - "@types/node": "*" - } - }, - "node_modules/@types/unist": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/@types/unist/-/unist-3.0.2.tgz", - "integrity": "sha512-dqId9J8K/vGi5Zr7oo212BGii5m3q5Hxlkwy3WpYuKPklmBEvsbMYYyLxAQpSffdLl/gdW0XUpKWFvYmyoWCoQ==", - "license": "MIT" - }, - "node_modules/@types/ws": { - "version": "8.5.12", - "resolved": "https://registry.npmjs.org/@types/ws/-/ws-8.5.12.tgz", - "integrity": "sha512-3tPRkv1EtkDpzlgyKyI8pGsGZAGPEaXeu0DOj5DI25Ja91bdAYddYHbADRYVrZMRbfW+1l5YwXVDKohDJNQxkQ==", - "license": "MIT", - "dependencies": { - "@types/node": "*" - } - }, - "node_modules/@types/yargs": { - "version": "17.0.33", - "resolved": "https://registry.npmjs.org/@types/yargs/-/yargs-17.0.33.tgz", - "integrity": "sha512-WpxBCKWPLr4xSsHgz511rFJAM+wS28w2zEO1QDNY5zM/S8ok70NNfztH0xwhqKyaK0OHCbN98LDAZuy1ctxDkA==", - "license": "MIT", - "dependencies": { - "@types/yargs-parser": "*" - } - }, - "node_modules/@types/yargs-parser": { - "version": "21.0.3", - "resolved": "https://registry.npmjs.org/@types/yargs-parser/-/yargs-parser-21.0.3.tgz", - "integrity": "sha512-I4q9QU9MQv4oEOz4tAHJtNz1cwuLxn2F3xcc2iV5WdqLPpUnj30aUuxt1mAxYTG+oe8CZMV/+6rU4S4gRDzqtQ==", - "license": "MIT" - }, - "node_modules/@ungap/structured-clone": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/@ungap/structured-clone/-/structured-clone-1.2.0.tgz", - "integrity": "sha512-zuVdFrMJiuCDQUMCzQaD6KL28MjnqqN8XnAqiEq9PNm/hCPTSGfrXCOfwj1ow4LFb/tNymJPwsNbVePc1xFqrQ==", - "license": "ISC" - }, - "node_modules/@webassemblyjs/ast": { - "version": "1.12.1", - "resolved": "https://registry.npmjs.org/@webassemblyjs/ast/-/ast-1.12.1.tgz", - "integrity": "sha512-EKfMUOPRRUTy5UII4qJDGPpqfwjOmZ5jeGFwid9mnoqIFK+e0vqoi1qH56JpmZSzEL53jKnNzScdmftJyG5xWg==", - "license": "MIT", - "dependencies": { - "@webassemblyjs/helper-numbers": "1.11.6", - "@webassemblyjs/helper-wasm-bytecode": "1.11.6" - } - }, - "node_modules/@webassemblyjs/floating-point-hex-parser": { - "version": "1.11.6", - "resolved": "https://registry.npmjs.org/@webassemblyjs/floating-point-hex-parser/-/floating-point-hex-parser-1.11.6.tgz", - "integrity": "sha512-ejAj9hfRJ2XMsNHk/v6Fu2dGS+i4UaXBXGemOfQ/JfQ6mdQg/WXtwleQRLLS4OvfDhv8rYnVwH27YJLMyYsxhw==", - "license": "MIT" - }, - "node_modules/@webassemblyjs/helper-api-error": { - "version": "1.11.6", - "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-api-error/-/helper-api-error-1.11.6.tgz", - "integrity": "sha512-o0YkoP4pVu4rN8aTJgAyj9hC2Sv5UlkzCHhxqWj8butaLvnpdc2jOwh4ewE6CX0txSfLn/UYaV/pheS2Txg//Q==", - "license": "MIT" - }, - "node_modules/@webassemblyjs/helper-buffer": { - "version": "1.12.1", - "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-buffer/-/helper-buffer-1.12.1.tgz", - "integrity": "sha512-nzJwQw99DNDKr9BVCOZcLuJJUlqkJh+kVzVl6Fmq/tI5ZtEyWT1KZMyOXltXLZJmDtvLCDgwsyrkohEtopTXCw==", - "license": "MIT" - }, - "node_modules/@webassemblyjs/helper-numbers": { - "version": "1.11.6", - "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-numbers/-/helper-numbers-1.11.6.tgz", - "integrity": "sha512-vUIhZ8LZoIWHBohiEObxVm6hwP034jwmc9kuq5GdHZH0wiLVLIPcMCdpJzG4C11cHoQ25TFIQj9kaVADVX7N3g==", - "license": "MIT", - "dependencies": { - "@webassemblyjs/floating-point-hex-parser": "1.11.6", - "@webassemblyjs/helper-api-error": "1.11.6", - "@xtuc/long": "4.2.2" - } - }, - "node_modules/@webassemblyjs/helper-wasm-bytecode": { - "version": "1.11.6", - "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-wasm-bytecode/-/helper-wasm-bytecode-1.11.6.tgz", - "integrity": "sha512-sFFHKwcmBprO9e7Icf0+gddyWYDViL8bpPjJJl0WHxCdETktXdmtWLGVzoHbqUcY4Be1LkNfwTmXOJUFZYSJdA==", - "license": "MIT" - }, - "node_modules/@webassemblyjs/helper-wasm-section": { - "version": "1.12.1", - "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-wasm-section/-/helper-wasm-section-1.12.1.tgz", - "integrity": "sha512-Jif4vfB6FJlUlSbgEMHUyk1j234GTNG9dBJ4XJdOySoj518Xj0oGsNi59cUQF4RRMS9ouBUxDDdyBVfPTypa5g==", - "license": "MIT", - "dependencies": { - "@webassemblyjs/ast": "1.12.1", - "@webassemblyjs/helper-buffer": "1.12.1", - "@webassemblyjs/helper-wasm-bytecode": "1.11.6", - "@webassemblyjs/wasm-gen": "1.12.1" - } - }, - "node_modules/@webassemblyjs/ieee754": { - "version": "1.11.6", - "resolved": "https://registry.npmjs.org/@webassemblyjs/ieee754/-/ieee754-1.11.6.tgz", - "integrity": "sha512-LM4p2csPNvbij6U1f19v6WR56QZ8JcHg3QIJTlSwzFcmx6WSORicYj6I63f9yU1kEUtrpG+kjkiIAkevHpDXrg==", - "license": "MIT", - "dependencies": { - "@xtuc/ieee754": "^1.2.0" - } - }, - "node_modules/@webassemblyjs/leb128": { - "version": "1.11.6", - "resolved": "https://registry.npmjs.org/@webassemblyjs/leb128/-/leb128-1.11.6.tgz", - "integrity": "sha512-m7a0FhE67DQXgouf1tbN5XQcdWoNgaAuoULHIfGFIEVKA6tu/edls6XnIlkmS6FrXAquJRPni3ZZKjw6FSPjPQ==", - "license": "Apache-2.0", - "dependencies": { - "@xtuc/long": "4.2.2" - } - }, - "node_modules/@webassemblyjs/utf8": { - "version": "1.11.6", - "resolved": "https://registry.npmjs.org/@webassemblyjs/utf8/-/utf8-1.11.6.tgz", - "integrity": "sha512-vtXf2wTQ3+up9Zsg8sa2yWiQpzSsMyXj0qViVP6xKGCUT8p8YJ6HqI7l5eCnWx1T/FYdsv07HQs2wTFbbof/RA==", - "license": "MIT" - }, - "node_modules/@webassemblyjs/wasm-edit": { - "version": "1.12.1", - "resolved": "https://registry.npmjs.org/@webassemblyjs/wasm-edit/-/wasm-edit-1.12.1.tgz", - "integrity": "sha512-1DuwbVvADvS5mGnXbE+c9NfA8QRcZ6iKquqjjmR10k6o+zzsRVesil54DKexiowcFCPdr/Q0qaMgB01+SQ1u6g==", - "license": "MIT", - "dependencies": { - "@webassemblyjs/ast": "1.12.1", - "@webassemblyjs/helper-buffer": "1.12.1", - "@webassemblyjs/helper-wasm-bytecode": "1.11.6", - "@webassemblyjs/helper-wasm-section": "1.12.1", - "@webassemblyjs/wasm-gen": "1.12.1", - "@webassemblyjs/wasm-opt": "1.12.1", - "@webassemblyjs/wasm-parser": "1.12.1", - "@webassemblyjs/wast-printer": "1.12.1" - } - }, - "node_modules/@webassemblyjs/wasm-gen": { - "version": "1.12.1", - "resolved": "https://registry.npmjs.org/@webassemblyjs/wasm-gen/-/wasm-gen-1.12.1.tgz", - "integrity": "sha512-TDq4Ojh9fcohAw6OIMXqiIcTq5KUXTGRkVxbSo1hQnSy6lAM5GSdfwWeSxpAo0YzgsgF182E/U0mDNhuA0tW7w==", - "license": "MIT", - "dependencies": { - "@webassemblyjs/ast": "1.12.1", - "@webassemblyjs/helper-wasm-bytecode": "1.11.6", - "@webassemblyjs/ieee754": "1.11.6", - "@webassemblyjs/leb128": "1.11.6", - "@webassemblyjs/utf8": "1.11.6" - } - }, - "node_modules/@webassemblyjs/wasm-opt": { - "version": "1.12.1", - "resolved": "https://registry.npmjs.org/@webassemblyjs/wasm-opt/-/wasm-opt-1.12.1.tgz", - "integrity": "sha512-Jg99j/2gG2iaz3hijw857AVYekZe2SAskcqlWIZXjji5WStnOpVoat3gQfT/Q5tb2djnCjBtMocY/Su1GfxPBg==", - "license": "MIT", - "dependencies": { - "@webassemblyjs/ast": "1.12.1", - "@webassemblyjs/helper-buffer": "1.12.1", - "@webassemblyjs/wasm-gen": "1.12.1", - "@webassemblyjs/wasm-parser": "1.12.1" - } - }, - "node_modules/@webassemblyjs/wasm-parser": { - "version": "1.12.1", - "resolved": "https://registry.npmjs.org/@webassemblyjs/wasm-parser/-/wasm-parser-1.12.1.tgz", - "integrity": "sha512-xikIi7c2FHXysxXe3COrVUPSheuBtpcfhbpFj4gmu7KRLYOzANztwUU0IbsqvMqzuNK2+glRGWCEqZo1WCLyAQ==", - "license": "MIT", - "dependencies": { - "@webassemblyjs/ast": "1.12.1", - "@webassemblyjs/helper-api-error": "1.11.6", - "@webassemblyjs/helper-wasm-bytecode": "1.11.6", - "@webassemblyjs/ieee754": "1.11.6", - "@webassemblyjs/leb128": "1.11.6", - "@webassemblyjs/utf8": "1.11.6" - } - }, - "node_modules/@webassemblyjs/wast-printer": { - "version": "1.12.1", - "resolved": "https://registry.npmjs.org/@webassemblyjs/wast-printer/-/wast-printer-1.12.1.tgz", - "integrity": "sha512-+X4WAlOisVWQMikjbcvY2e0rwPsKQ9F688lksZhBcPycBBuii3O7m8FACbDMWDojpAqvjIncrG8J0XHKyQfVeA==", - "license": "MIT", - "dependencies": { - "@webassemblyjs/ast": "1.12.1", - "@xtuc/long": "4.2.2" - } - }, - "node_modules/@xtuc/ieee754": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/@xtuc/ieee754/-/ieee754-1.2.0.tgz", - "integrity": "sha512-DX8nKgqcGwsc0eJSqYt5lwP4DH5FlHnmuWWBRy7X0NcaGR0ZtuyeESgMwTYVEtxmsNGY+qit4QYT/MIYTOTPeA==", - "license": "BSD-3-Clause" - }, - "node_modules/@xtuc/long": { - "version": "4.2.2", - "resolved": "https://registry.npmjs.org/@xtuc/long/-/long-4.2.2.tgz", - "integrity": "sha512-NuHqBY1PB/D8xU6s/thBgOAiAP7HOYDQ32+BFZILJ8ivkUkAHQnWfn6WhL79Owj1qmUnoN/YPhktdIoucipkAQ==", - "license": "Apache-2.0" - }, - "node_modules/abort-controller": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/abort-controller/-/abort-controller-3.0.0.tgz", - "integrity": "sha512-h8lQ8tacZYnR3vNQTgibj+tODHI5/+l06Au2Pcriv/Gmet0eaj4TwWH41sO9wnHDiQsEj19q0drzdWdeAHtweg==", - "license": "MIT", - "dependencies": { - "event-target-shim": "^5.0.0" - }, - "engines": { - "node": ">=6.5" - } - }, - "node_modules/accepts": { - "version": "1.3.8", - "resolved": "https://registry.npmjs.org/accepts/-/accepts-1.3.8.tgz", - "integrity": "sha512-PYAthTa2m2VKxuvSD3DPC/Gy+U+sOA1LAuT8mkmRuvw+NACSaeXEQ+NHcVF7rONl6qcaxV3Uuemwawk+7+SJLw==", - "license": "MIT", - "dependencies": { - "mime-types": "~2.1.34", - "negotiator": "0.6.3" - }, - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/accepts/node_modules/mime-db": { - "version": "1.52.0", - "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.52.0.tgz", - "integrity": "sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg==", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/accepts/node_modules/mime-types": { - "version": "2.1.35", - "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.35.tgz", - "integrity": "sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw==", - "license": "MIT", - "dependencies": { - "mime-db": "1.52.0" - }, - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/acorn": { - "version": "8.14.0", - "resolved": "https://registry.npmjs.org/acorn/-/acorn-8.14.0.tgz", - "integrity": "sha512-cl669nCJTZBsL97OF4kUQm5g5hC2uihk0NxY3WENAC0TYdILVkAyHymAntgxGkl7K+t0cXIrH5siy5S4XkFycA==", - "license": "MIT", - "bin": { - "acorn": "bin/acorn" - }, - "engines": { - "node": ">=0.4.0" - } - }, - "node_modules/acorn-jsx": { - "version": "5.3.2", - "resolved": "https://registry.npmjs.org/acorn-jsx/-/acorn-jsx-5.3.2.tgz", - "integrity": "sha512-rq9s+JNhf0IChjtDXxllJ7g41oZk5SlXtp0LHwyA5cejwn7vKmKp4pPri6YEePv2PU65sAsegbXtIinmDFDXgQ==", - "license": "MIT", - "peerDependencies": { - "acorn": "^6.0.0 || ^7.0.0 || ^8.0.0" - } - }, - "node_modules/acorn-walk": { - "version": "8.3.3", - "resolved": "https://registry.npmjs.org/acorn-walk/-/acorn-walk-8.3.3.tgz", - "integrity": "sha512-MxXdReSRhGO7VlFe1bRG/oI7/mdLV9B9JJT0N8vZOhF7gFRR5l3M8W9G8JxmKV+JC5mGqJ0QvqfSOLsCPa4nUw==", - "license": "MIT", - "dependencies": { - "acorn": "^8.11.0" - }, - "engines": { - "node": ">=0.4.0" - } - }, - "node_modules/address": { - "version": "1.2.2", - "resolved": "https://registry.npmjs.org/address/-/address-1.2.2.tgz", - "integrity": "sha512-4B/qKCfeE/ODUaAUpSwfzazo5x29WD4r3vXiWsB7I2mSDAihwEqKO+g8GELZUQSSAo5e1XTYh3ZVfLyxBc12nA==", - "license": "MIT", - "engines": { - "node": ">= 10.0.0" - } - }, - "node_modules/agent-base": { - "version": "7.1.1", - "resolved": "https://registry.npmjs.org/agent-base/-/agent-base-7.1.1.tgz", - "integrity": "sha512-H0TSyFNDMomMNJQBn8wFV5YC/2eJ+VXECwOadZJT554xP6cODZHPX3H9QMQECxvrgiSOP1pHjy1sMWQVYJOUOA==", - "license": "MIT", - "dependencies": { - "debug": "^4.3.4" - }, - "engines": { - "node": ">= 14" - } - }, - "node_modules/aggregate-error": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/aggregate-error/-/aggregate-error-3.1.0.tgz", - "integrity": "sha512-4I7Td01quW/RpocfNayFdFVk1qSuoh0E7JrbRJ16nH01HhKFQ88INq9Sd+nd72zqRySlr9BmDA8xlEJ6vJMrYA==", - "license": "MIT", - "dependencies": { - "clean-stack": "^2.0.0", - "indent-string": "^4.0.0" - }, - "engines": { - "node": ">=8" - } - }, - "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==", - "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" - } - }, - "node_modules/ajv-draft-04": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/ajv-draft-04/-/ajv-draft-04-1.0.0.tgz", - "integrity": "sha512-mv00Te6nmYbRp5DCwclxtt7yV/joXJPGS7nM+97GdxvuttCOfgI3K4U25zboyeX0O+myI8ERluxQe5wljMmVIw==", - "license": "MIT", - "peerDependencies": { - "ajv": "^8.5.0" - }, - "peerDependenciesMeta": { - "ajv": { - "optional": true - } - } - }, - "node_modules/ajv-formats": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/ajv-formats/-/ajv-formats-2.1.1.tgz", - "integrity": "sha512-Wx0Kx52hxE7C18hkMEggYlEifqWZtYaRgouJor+WMdPnQyEK13vgEWyVNup7SoeeoLMsr4kf5h6dOW11I15MUA==", - "license": "MIT", - "dependencies": { - "ajv": "^8.0.0" - }, - "peerDependencies": { - "ajv": "^8.0.0" - }, - "peerDependenciesMeta": { - "ajv": { - "optional": true - } - } - }, - "node_modules/ajv-keywords": { - "version": "5.1.0", - "resolved": "https://registry.npmjs.org/ajv-keywords/-/ajv-keywords-5.1.0.tgz", - "integrity": "sha512-YCS/JNFAUyr5vAuhk1DWm1CBxRHW9LbJ2ozWeemrIqpbsqKjHVxYPyi5GC0rjZIT5JxJ3virVTS8wk4i/Z+krw==", - "license": "MIT", - "dependencies": { - "fast-deep-equal": "^3.1.3" - }, - "peerDependencies": { - "ajv": "^8.8.2" - } - }, - "node_modules/algoliasearch": { - "version": "5.19.0", - "resolved": "https://registry.npmjs.org/algoliasearch/-/algoliasearch-5.19.0.tgz", - "integrity": "sha512-zrLtGhC63z3sVLDDKGW+SlCRN9eJHFTgdEmoAOpsVh6wgGL1GgTTDou7tpCBjevzgIvi3AIyDAQO3Xjbg5eqZg==", - "license": "MIT", - "dependencies": { - "@algolia/client-abtesting": "5.19.0", - "@algolia/client-analytics": "5.19.0", - "@algolia/client-common": "5.19.0", - "@algolia/client-insights": "5.19.0", - "@algolia/client-personalization": "5.19.0", - "@algolia/client-query-suggestions": "5.19.0", - "@algolia/client-search": "5.19.0", - "@algolia/ingestion": "1.19.0", - "@algolia/monitoring": "1.19.0", - "@algolia/recommend": "5.19.0", - "@algolia/requester-browser-xhr": "5.19.0", - "@algolia/requester-fetch": "5.19.0", - "@algolia/requester-node-http": "5.19.0" - }, - "engines": { - "node": ">= 14.0.0" - } - }, - "node_modules/algoliasearch-helper": { - "version": "3.23.0", - "resolved": "https://registry.npmjs.org/algoliasearch-helper/-/algoliasearch-helper-3.23.0.tgz", - "integrity": "sha512-8CK4Gb/ju4OesAYcS+mjBpNiVA7ILWpg7D2vhBZohh0YkG8QT1KZ9LG+8+EntQBUGoKtPy06OFhiwP4f5zzAQg==", - "license": "MIT", - "dependencies": { - "@algolia/events": "^4.0.1" - }, - "peerDependencies": { - "algoliasearch": ">= 3.1 < 6" - } - }, - "node_modules/allof-merge": { - "version": "0.6.6", - "resolved": "https://registry.npmjs.org/allof-merge/-/allof-merge-0.6.6.tgz", - "integrity": "sha512-116eZBf2he0/J4Tl7EYMz96I5Anaeio+VL0j/H2yxW9CoYQAMMv8gYcwkVRoO7XfIOv/qzSTfVzDVGAYxKFi3g==", - "license": "MIT", - "dependencies": { - "json-crawl": "^0.5.3" - } - }, - "node_modules/ansi-align": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/ansi-align/-/ansi-align-3.0.1.tgz", - "integrity": "sha512-IOfwwBF5iczOjp/WeY4YxyjqAFMQoZufdQWDd19SEExbVLNXqvpzSJ/M7Za4/sCPmQ0+GRquoA7bGcINcxew6w==", - "license": "ISC", - "dependencies": { - "string-width": "^4.1.0" - } - }, - "node_modules/ansi-align/node_modules/emoji-regex": { - "version": "8.0.0", - "resolved": "https://registry.npmjs.org/emoji-regex/-/emoji-regex-8.0.0.tgz", - "integrity": "sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A==", - "license": "MIT" - }, - "node_modules/ansi-align/node_modules/string-width": { - "version": "4.2.3", - "resolved": "https://registry.npmjs.org/string-width/-/string-width-4.2.3.tgz", - "integrity": "sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g==", - "license": "MIT", - "dependencies": { - "emoji-regex": "^8.0.0", - "is-fullwidth-code-point": "^3.0.0", - "strip-ansi": "^6.0.1" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/ansi-escapes": { - "version": "4.3.2", - "resolved": "https://registry.npmjs.org/ansi-escapes/-/ansi-escapes-4.3.2.tgz", - "integrity": "sha512-gKXj5ALrKWQLsYG9jlTRmR/xKluxHV+Z9QEwNIgCfM1/uwPMCuzVVnh5mwTd+OuBZcwSIMbqssNWRm1lE51QaQ==", - "license": "MIT", - "dependencies": { - "type-fest": "^0.21.3" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/ansi-escapes/node_modules/type-fest": { - "version": "0.21.3", - "resolved": "https://registry.npmjs.org/type-fest/-/type-fest-0.21.3.tgz", - "integrity": "sha512-t0rzBq87m3fVcduHDUFhKmyyX+9eo6WQjZvf51Ea/M0Q7+T374Jp1aUiyUl0GKxp8M/OETVHSDvmkyPgvX+X2w==", - "license": "(MIT OR CC0-1.0)", - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/ansi-html-community": { - "version": "0.0.8", - "resolved": "https://registry.npmjs.org/ansi-html-community/-/ansi-html-community-0.0.8.tgz", - "integrity": "sha512-1APHAyr3+PCamwNw3bXCPp4HFLONZt/yIH0sZp0/469KWNTEy+qN5jQ3GVX6DMZ1UXAi34yVwtTeaG/HpBuuzw==", - "engines": [ - "node >= 0.8.0" - ], - "license": "Apache-2.0", - "bin": { - "ansi-html": "bin/ansi-html" - } - }, - "node_modules/ansi-regex": { - "version": "5.0.1", - "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-5.0.1.tgz", - "integrity": "sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ==", - "license": "MIT", - "engines": { - "node": ">=8" - } - }, - "node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "license": "MIT", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, - "node_modules/any-promise": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/any-promise/-/any-promise-1.3.0.tgz", - "integrity": "sha512-7UvmKalWRt1wgjL1RrGxoSJW/0QZFIegpeGvZG9kjp8vrRu55XTHbwnqq2GpXm9uLbcuhxm3IqX9OB4MZR1b2A==", - "license": "MIT" - }, - "node_modules/anymatch": { - "version": "3.1.3", - "resolved": "https://registry.npmjs.org/anymatch/-/anymatch-3.1.3.tgz", - "integrity": "sha512-KMReFUr0B4t+D+OBkjR3KYqvocp2XaSzO55UcB6mgQMd3KbcE+mWTyvVV7D/zsdEbNnV6acZUutkiHQXvTr1Rw==", - "license": "ISC", - "dependencies": { - "normalize-path": "^3.0.0", - "picomatch": "^2.0.4" - }, - "engines": { - "node": ">= 8" - } - }, - "node_modules/arg": { - "version": "5.0.2", - "resolved": "https://registry.npmjs.org/arg/-/arg-5.0.2.tgz", - "integrity": "sha512-PYjyFOLKQ9y57JvQ6QLo8dAgNqswh8M1RMJYdQduT6xbWSgK36P/Z/v+p888pM69jMMfS8Xd8F6I1kQ/I9HUGg==", - "license": "MIT" - }, - "node_modules/argparse": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/argparse/-/argparse-2.0.1.tgz", - "integrity": "sha512-8+9WqebbFzpX9OR+Wa6O29asIogeRMzcGtAINdpMHHyAg10f05aSFVBbcEqGf/PXw1EjAZ+q2/bEBg3DvurK3Q==", - "license": "Python-2.0" - }, - "node_modules/array-flatten": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/array-flatten/-/array-flatten-1.1.1.tgz", - "integrity": "sha512-PCVAQswWemu6UdxsDFFX/+gVeYqKAod3D3UVm91jHwynguOwAvYPhx8nNlM++NqRcK6CxxpUafjmhIdKiHibqg==", - "license": "MIT" - }, - "node_modules/array-union": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/array-union/-/array-union-2.1.0.tgz", - "integrity": "sha512-HGyxoOTYUyCM6stUe6EJgnd4EoewAI7zMdfqO+kGjnlZmBDz/cR5pf8r/cR4Wq60sL/p0IkcjUEEPwS3GFrIyw==", - "license": "MIT", - "engines": { - "node": ">=8" - } - }, - "node_modules/asn1.js": { - "version": "4.10.1", - "resolved": "https://registry.npmjs.org/asn1.js/-/asn1.js-4.10.1.tgz", - "integrity": "sha512-p32cOF5q0Zqs9uBiONKYLm6BClCoBCM5O9JfeUSlnQLBTxYdTK+pW+nXflm8UkKd2UYlEbYz5qEi0JuZR9ckSw==", - "license": "MIT", - "dependencies": { - "bn.js": "^4.0.0", - "inherits": "^2.0.1", - "minimalistic-assert": "^1.0.0" - } - }, - "node_modules/asn1.js/node_modules/bn.js": { - "version": "4.12.0", - "resolved": "https://registry.npmjs.org/bn.js/-/bn.js-4.12.0.tgz", - "integrity": "sha512-c98Bf3tPniI+scsdk237ku1Dc3ujXQTSgyiPUDEOe7tRkhrqridvh8klBv0HCEso1OLOYcHuCv/cS6DNxKH+ZA==", - "license": "MIT" - }, - "node_modules/assert": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/assert/-/assert-2.1.0.tgz", - "integrity": "sha512-eLHpSK/Y4nhMJ07gDaAzoX/XAKS8PSaojml3M0DM4JpV1LAi5JOJ/p6H/XWrl8L+DzVEvVCW1z3vWAaB9oTsQw==", - "license": "MIT", - "dependencies": { - "call-bind": "^1.0.2", - "is-nan": "^1.3.2", - "object-is": "^1.1.5", - "object.assign": "^4.1.4", - "util": "^0.12.5" - } - }, - "node_modules/astring": { - "version": "1.8.6", - "resolved": "https://registry.npmjs.org/astring/-/astring-1.8.6.tgz", - "integrity": "sha512-ISvCdHdlTDlH5IpxQJIex7BWBywFWgjJSVdwst+/iQCoEYnyOaQ95+X1JGshuBjGp6nxKUy1jMgE3zPqN7fQdg==", - "license": "MIT", - "bin": { - "astring": "bin/astring" - } - }, - "node_modules/async": { - "version": "3.2.4", - "resolved": "https://registry.npmjs.org/async/-/async-3.2.4.tgz", - "integrity": "sha512-iAB+JbDEGXhyIUavoDl9WP/Jj106Kz9DEn1DPgYw5ruDn0e3Wgi3sKFm55sASdGBNOQB8F59d9qQ7deqrHA8wQ==", - "license": "MIT" - }, - "node_modules/at-least-node": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/at-least-node/-/at-least-node-1.0.0.tgz", - "integrity": "sha512-+q/t7Ekv1EDY2l6Gda6LLiX14rU9TV20Wa3ofeQmwPFZbOMo9DXrLbOjFaaclkXKWidIaopwAObQDqwWtGUjqg==", - "license": "ISC", - "engines": { - "node": ">= 4.0.0" - } - }, - "node_modules/autoprefixer": { - "version": "10.4.20", - "resolved": "https://registry.npmjs.org/autoprefixer/-/autoprefixer-10.4.20.tgz", - "integrity": "sha512-XY25y5xSv/wEoqzDyXXME4AFfkZI0P23z6Fs3YgymDnKJkCGOnkL0iTxCa85UTqaSgfcqyf3UA6+c7wUvx/16g==", - "funding": [ - { - "type": "opencollective", - "url": "https://opencollective.com/postcss/" - }, - { - "type": "tidelift", - "url": "https://tidelift.com/funding/github/npm/autoprefixer" - }, - { - "type": "github", - "url": "https://github.com/sponsors/ai" - } - ], - "license": "MIT", - "dependencies": { - "browserslist": "^4.23.3", - "caniuse-lite": "^1.0.30001646", - "fraction.js": "^4.3.7", - "normalize-range": "^0.1.2", - "picocolors": "^1.0.1", - "postcss-value-parser": "^4.2.0" - }, - "bin": { - "autoprefixer": "bin/autoprefixer" - }, - "engines": { - "node": "^10 || ^12 || >=14" - }, - "peerDependencies": { - "postcss": "^8.1.0" - } - }, - "node_modules/available-typed-arrays": { - "version": "1.0.7", - "resolved": "https://registry.npmjs.org/available-typed-arrays/-/available-typed-arrays-1.0.7.tgz", - "integrity": "sha512-wvUjBtSGN7+7SjNpq/9M2Tg350UZD3q62IFZLbRAR1bSMlCo1ZaeW+BJ+D090e4hIIZLBcTDWe4Mh4jvUDajzQ==", - "license": "MIT", - "dependencies": { - "possible-typed-array-names": "^1.0.0" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/babel-loader": { - "version": "9.2.1", - "resolved": "https://registry.npmjs.org/babel-loader/-/babel-loader-9.2.1.tgz", - "integrity": "sha512-fqe8naHt46e0yIdkjUZYqddSXfej3AHajX+CSO5X7oy0EmPc6o5Xh+RClNoHjnieWz9AW4kZxW9yyFMhVB1QLA==", - "license": "MIT", - "dependencies": { - "find-cache-dir": "^4.0.0", - "schema-utils": "^4.0.0" - }, - "engines": { - "node": ">= 14.15.0" - }, - "peerDependencies": { - "@babel/core": "^7.12.0", - "webpack": ">=5" - } - }, - "node_modules/babel-plugin-dynamic-import-node": { - "version": "2.3.3", - "resolved": "https://registry.npmjs.org/babel-plugin-dynamic-import-node/-/babel-plugin-dynamic-import-node-2.3.3.tgz", - "integrity": "sha512-jZVI+s9Zg3IqA/kdi0i6UDCybUI3aSBLnglhYbSSjKlV7yF1F/5LWv8MakQmvYpnbJDS6fcBL2KzHSxNCMtWSQ==", - "license": "MIT", - "dependencies": { - "object.assign": "^4.1.0" - } - }, - "node_modules/babel-plugin-polyfill-corejs2": { - "version": "0.4.11", - "resolved": "https://registry.npmjs.org/babel-plugin-polyfill-corejs2/-/babel-plugin-polyfill-corejs2-0.4.11.tgz", - "integrity": "sha512-sMEJ27L0gRHShOh5G54uAAPaiCOygY/5ratXuiyb2G46FmlSpc9eFCzYVyDiPxfNbwzA7mYahmjQc5q+CZQ09Q==", - "license": "MIT", - "dependencies": { - "@babel/compat-data": "^7.22.6", - "@babel/helper-define-polyfill-provider": "^0.6.2", - "semver": "^6.3.1" - }, - "peerDependencies": { - "@babel/core": "^7.4.0 || ^8.0.0-0 <8.0.0" - } - }, - "node_modules/babel-plugin-polyfill-corejs2/node_modules/semver": { - "version": "6.3.1", - "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.1.tgz", - "integrity": "sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA==", - "license": "ISC", - "bin": { - "semver": "bin/semver.js" - } - }, - "node_modules/babel-plugin-polyfill-corejs3": { - "version": "0.10.6", - "resolved": "https://registry.npmjs.org/babel-plugin-polyfill-corejs3/-/babel-plugin-polyfill-corejs3-0.10.6.tgz", - "integrity": "sha512-b37+KR2i/khY5sKmWNVQAnitvquQbNdWy6lJdsr0kmquCKEEUgMKK4SboVM3HtfnZilfjr4MMQ7vY58FVWDtIA==", - "license": "MIT", - "dependencies": { - "@babel/helper-define-polyfill-provider": "^0.6.2", - "core-js-compat": "^3.38.0" - }, - "peerDependencies": { - "@babel/core": "^7.4.0 || ^8.0.0-0 <8.0.0" - } - }, - "node_modules/babel-plugin-polyfill-regenerator": { - "version": "0.6.2", - "resolved": "https://registry.npmjs.org/babel-plugin-polyfill-regenerator/-/babel-plugin-polyfill-regenerator-0.6.2.tgz", - "integrity": "sha512-2R25rQZWP63nGwaAswvDazbPXfrM3HwVoBXK6HcqeKrSrL/JqcC/rDcf95l4r7LXLyxDXc8uQDa064GubtCABg==", - "license": "MIT", - "dependencies": { - "@babel/helper-define-polyfill-provider": "^0.6.2" - }, - "peerDependencies": { - "@babel/core": "^7.4.0 || ^8.0.0-0 <8.0.0" - } - }, - "node_modules/bail": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/bail/-/bail-2.0.2.tgz", - "integrity": "sha512-0xO6mYd7JB2YesxDKplafRpsiOzPt9V02ddPCLbY1xYGPOX24NTyN50qnUxgCPcSoYMhKpAuBTjQoRZCAkUDRw==", - "license": "MIT", - "funding": { - "type": "github", - "url": "https://github.com/sponsors/wooorm" - } - }, - "node_modules/balanced-match": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.2.tgz", - "integrity": "sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw==", - "license": "MIT" - }, - "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==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/feross" - }, - { - "type": "patreon", - "url": "https://www.patreon.com/feross" - }, - { - "type": "consulting", - "url": "https://feross.org/support" - } - ], - "license": "MIT" - }, - "node_modules/batch": { - "version": "0.6.1", - "resolved": "https://registry.npmjs.org/batch/-/batch-0.6.1.tgz", - "integrity": "sha512-x+VAiMRL6UPkx+kudNvxTl6hB2XNNCG2r+7wixVfIYwu/2HKRXimwQyaumLjMveWvT2Hkd/cAJw+QBMfJ/EKVw==", - "license": "MIT" - }, - "node_modules/big.js": { - "version": "5.2.2", - "resolved": "https://registry.npmjs.org/big.js/-/big.js-5.2.2.tgz", - "integrity": "sha512-vyL2OymJxmarO8gxMr0mhChsO9QGwhynfuu4+MHTAW6czfq9humCB7rKpUjDd9YUiDPU4mzpyupFSvOClAwbmQ==", - "license": "MIT", - "engines": { - "node": "*" - } - }, - "node_modules/binary-extensions": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/binary-extensions/-/binary-extensions-2.3.0.tgz", - "integrity": "sha512-Ceh+7ox5qe7LJuLHoY0feh3pHuUDHAcRUeyL2VYghZwfpkNIy/+8Ocg0a3UuSoYzavmylwuLWQOf3hl0jjMMIw==", - "license": "MIT", - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/bn.js": { - "version": "5.2.1", - "resolved": "https://registry.npmjs.org/bn.js/-/bn.js-5.2.1.tgz", - "integrity": "sha512-eXRvHzWyYPBuB4NBy0cmYQjGitUrtqwbvlzP3G6VFnNRbsZQIxQ10PbKKHt8gZ/HW/D/747aDl+QkDqg3KQLMQ==", - "license": "MIT" - }, - "node_modules/body-parser": { - "version": "1.20.3", - "resolved": "https://registry.npmjs.org/body-parser/-/body-parser-1.20.3.tgz", - "integrity": "sha512-7rAxByjUMqQ3/bHJy7D6OGXvx/MMc4IqBn/X0fcM1QUcAItpZrBEYhWGem+tzXH90c+G01ypMcYJBO9Y30203g==", - "dependencies": { - "bytes": "3.1.2", - "content-type": "~1.0.5", - "debug": "2.6.9", - "depd": "2.0.0", - "destroy": "1.2.0", - "http-errors": "2.0.0", - "iconv-lite": "0.4.24", - "on-finished": "2.4.1", - "qs": "6.13.0", - "raw-body": "2.5.2", - "type-is": "~1.6.18", - "unpipe": "1.0.0" - }, - "engines": { - "node": ">= 0.8", - "npm": "1.2.8000 || >= 1.4.16" - } - }, - "node_modules/body-parser/node_modules/bytes": { - "version": "3.1.2", - "resolved": "https://registry.npmjs.org/bytes/-/bytes-3.1.2.tgz", - "integrity": "sha512-/Nf7TyzTx6S3yRJObOAV7956r8cr2+Oj8AC5dt8wSP3BQAoeX58NoHyCU8P8zGkNXStjTSi6fzO6F0pBdcYbEg==", - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/body-parser/node_modules/debug": { - "version": "2.6.9", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", - "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", - "dependencies": { - "ms": "2.0.0" - } - }, - "node_modules/body-parser/node_modules/ms": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", - "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==" - }, - "node_modules/bonjour-service": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/bonjour-service/-/bonjour-service-1.2.1.tgz", - "integrity": "sha512-oSzCS2zV14bh2kji6vNe7vrpJYCHGvcZnlffFQ1MEoX/WOeQ/teD8SYWKR942OI3INjq8OMNJlbPK5LLLUxFDw==", - "license": "MIT", - "dependencies": { - "fast-deep-equal": "^3.1.3", - "multicast-dns": "^7.2.5" - } - }, - "node_modules/boolbase": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/boolbase/-/boolbase-1.0.0.tgz", - "integrity": "sha512-JZOSA7Mo9sNGB8+UjSgzdLtokWAky1zbztM3WRLCbZ70/3cTANmQmOdR7y2g+J0e2WXywy1yS468tY+IruqEww==", - "license": "ISC" - }, - "node_modules/boxen": { - "version": "6.2.1", - "resolved": "https://registry.npmjs.org/boxen/-/boxen-6.2.1.tgz", - "integrity": "sha512-H4PEsJXfFI/Pt8sjDWbHlQPx4zL/bvSQjcilJmaulGt5mLDorHOHpmdXAJcBcmru7PhYSp/cDMWRko4ZUMFkSw==", - "license": "MIT", - "dependencies": { - "ansi-align": "^3.0.1", - "camelcase": "^6.2.0", - "chalk": "^4.1.2", - "cli-boxes": "^3.0.0", - "string-width": "^5.0.1", - "type-fest": "^2.5.0", - "widest-line": "^4.0.1", - "wrap-ansi": "^8.0.1" - }, - "engines": { - "node": "^12.20.0 || ^14.13.1 || >=16.0.0" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/brace-expansion": { - "version": "1.1.11", - "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz", - "integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==", - "license": "MIT", - "dependencies": { - "balanced-match": "^1.0.0", - "concat-map": "0.0.1" - } - }, - "node_modules/braces": { - "version": "3.0.3", - "resolved": "https://registry.npmjs.org/braces/-/braces-3.0.3.tgz", - "integrity": "sha512-yQbXgO/OSZVD2IsiLlro+7Hf6Q18EJrKSEsdoMzKePKXct3gvD8oLcOQdIzGupr5Fj+EDe8gO/lxc1BzfMpxvA==", - "license": "MIT", - "dependencies": { - "fill-range": "^7.1.1" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/brorand": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/brorand/-/brorand-1.1.0.tgz", - "integrity": "sha512-cKV8tMCEpQs4hK/ik71d6LrPOnpkpGBR0wzxqr68g2m/LB2GxVYQroAjMJZRVM1Y4BCjCKc3vAamxSzOY2RP+w==", - "license": "MIT" - }, - "node_modules/browserify-aes": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/browserify-aes/-/browserify-aes-1.2.0.tgz", - "integrity": "sha512-+7CHXqGuspUn/Sl5aO7Ea0xWGAtETPXNSAjHo48JfLdPWcMng33Xe4znFvQweqc/uzk5zSOI3H52CYnjCfb5hA==", - "license": "MIT", - "dependencies": { - "buffer-xor": "^1.0.3", - "cipher-base": "^1.0.0", - "create-hash": "^1.1.0", - "evp_bytestokey": "^1.0.3", - "inherits": "^2.0.1", - "safe-buffer": "^5.0.1" - } - }, - "node_modules/browserify-cipher": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/browserify-cipher/-/browserify-cipher-1.0.1.tgz", - "integrity": "sha512-sPhkz0ARKbf4rRQt2hTpAHqn47X3llLkUGn+xEJzLjwY8LRs2p0v7ljvI5EyoRO/mexrNunNECisZs+gw2zz1w==", - "license": "MIT", - "dependencies": { - "browserify-aes": "^1.0.4", - "browserify-des": "^1.0.0", - "evp_bytestokey": "^1.0.0" - } - }, - "node_modules/browserify-des": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/browserify-des/-/browserify-des-1.0.2.tgz", - "integrity": "sha512-BioO1xf3hFwz4kc6iBhI3ieDFompMhrMlnDFC4/0/vd5MokpuAc3R+LYbwTA9A5Yc9pq9UYPqffKpW2ObuwX5A==", - "license": "MIT", - "dependencies": { - "cipher-base": "^1.0.1", - "des.js": "^1.0.0", - "inherits": "^2.0.1", - "safe-buffer": "^5.1.2" - } - }, - "node_modules/browserify-rsa": { - "version": "4.1.1", - "resolved": "https://registry.npmjs.org/browserify-rsa/-/browserify-rsa-4.1.1.tgz", - "integrity": "sha512-YBjSAiTqM04ZVei6sXighu679a3SqWORA3qZTEqZImnlkDIFtKc6pNutpjyZ8RJTjQtuYfeetkxM11GwoYXMIQ==", - "license": "MIT", - "dependencies": { - "bn.js": "^5.2.1", - "randombytes": "^2.1.0", - "safe-buffer": "^5.2.1" - }, - "engines": { - "node": ">= 0.10" - } - }, - "node_modules/browserify-sign": { - "version": "4.2.3", - "resolved": "https://registry.npmjs.org/browserify-sign/-/browserify-sign-4.2.3.tgz", - "integrity": "sha512-JWCZW6SKhfhjJxO8Tyiiy+XYB7cqd2S5/+WeYHsKdNKFlCBhKbblba1A/HN/90YwtxKc8tCErjffZl++UNmGiw==", - "license": "ISC", - "dependencies": { - "bn.js": "^5.2.1", - "browserify-rsa": "^4.1.0", - "create-hash": "^1.2.0", - "create-hmac": "^1.1.7", - "elliptic": "^6.5.5", - "hash-base": "~3.0", - "inherits": "^2.0.4", - "parse-asn1": "^5.1.7", - "readable-stream": "^2.3.8", - "safe-buffer": "^5.2.1" - }, - "engines": { - "node": ">= 0.12" - } - }, - "node_modules/browserify-sign/node_modules/isarray": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", - "integrity": "sha512-VLghIWNM6ELQzo7zwmcg0NmTVyWKYjvIeM83yjp0wRDTmUnrM678fQbcKBo6n2CJEF0szoG//ytg+TKla89ALQ==", - "license": "MIT" - }, - "node_modules/browserify-sign/node_modules/readable-stream": { - "version": "2.3.8", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.8.tgz", - "integrity": "sha512-8p0AUk4XODgIewSi0l8Epjs+EVnWiK7NoDIEGU0HhE7+ZyY8D1IMY7odu5lRrFXGg71L15KG8QrPmum45RTtdA==", - "license": "MIT", - "dependencies": { - "core-util-is": "~1.0.0", - "inherits": "~2.0.3", - "isarray": "~1.0.0", - "process-nextick-args": "~2.0.0", - "safe-buffer": "~5.1.1", - "string_decoder": "~1.1.1", - "util-deprecate": "~1.0.1" - } - }, - "node_modules/browserify-sign/node_modules/readable-stream/node_modules/safe-buffer": { - "version": "5.1.2", - "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz", - "integrity": "sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==", - "license": "MIT" - }, - "node_modules/browserify-sign/node_modules/string_decoder": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.1.1.tgz", - "integrity": "sha512-n/ShnvDi6FHbbVfviro+WojiFzv+s8MPMHBczVePfUpDJLwoLT0ht1l4YwBCbi8pJAveEEdnkHyPyTP/mzRfwg==", - "license": "MIT", - "dependencies": { - "safe-buffer": "~5.1.0" - } - }, - "node_modules/browserify-sign/node_modules/string_decoder/node_modules/safe-buffer": { - "version": "5.1.2", - "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz", - "integrity": "sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==", - "license": "MIT" - }, - "node_modules/browserify-zlib": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/browserify-zlib/-/browserify-zlib-0.2.0.tgz", - "integrity": "sha512-Z942RysHXmJrhqk88FmKBVq/v5tqmSkDz7p54G/MGyjMnCFFnC79XWNbg+Vta8W6Wb2qtSZTSxIGkJrRpCFEiA==", - "license": "MIT", - "dependencies": { - "pako": "~1.0.5" - } - }, - "node_modules/browserslist": { - "version": "4.24.2", - "resolved": "https://registry.npmjs.org/browserslist/-/browserslist-4.24.2.tgz", - "integrity": "sha512-ZIc+Q62revdMcqC6aChtW4jz3My3klmCO1fEmINZY/8J3EpBg5/A/D0AKmBveUh6pgoeycoMkVMko84tuYS+Gg==", - "funding": [ - { - "type": "opencollective", - "url": "https://opencollective.com/browserslist" - }, - { - "type": "tidelift", - "url": "https://tidelift.com/funding/github/npm/browserslist" - }, - { - "type": "github", - "url": "https://github.com/sponsors/ai" - } - ], - "license": "MIT", - "dependencies": { - "caniuse-lite": "^1.0.30001669", - "electron-to-chromium": "^1.5.41", - "node-releases": "^2.0.18", - "update-browserslist-db": "^1.1.1" - }, - "bin": { - "browserslist": "cli.js" - }, - "engines": { - "node": "^6 || ^7 || ^8 || ^9 || ^10 || ^11 || ^12 || >=13.7" - } - }, - "node_modules/buffer": { - "version": "6.0.3", - "resolved": "https://registry.npmjs.org/buffer/-/buffer-6.0.3.tgz", - "integrity": "sha512-FTiCpNxtwiZZHEZbcbTIcZjERVICn9yq/pDFkTl95/AxzD1naBctN7YO68riM/gLSDY7sdrMby8hofADYuuqOA==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/feross" - }, - { - "type": "patreon", - "url": "https://www.patreon.com/feross" - }, - { - "type": "consulting", - "url": "https://feross.org/support" - } - ], - "license": "MIT", - "dependencies": { - "base64-js": "^1.3.1", - "ieee754": "^1.2.1" - } - }, - "node_modules/buffer-from": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/buffer-from/-/buffer-from-1.1.2.tgz", - "integrity": "sha512-E+XQCRwSbaaiChtv6k6Dwgc+bx+Bs6vuKJHHl5kox/BaKbhiXzqQOwK4cO22yElGp2OCmjwVhT3HmxgyPGnJfQ==", - "license": "MIT" - }, - "node_modules/buffer-xor": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/buffer-xor/-/buffer-xor-1.0.3.tgz", - "integrity": "sha512-571s0T7nZWK6vB67HI5dyUF7wXiNcfaPPPTl6zYCNApANjIvYJTg7hlud/+cJpdAhS7dVzqMLmfhfHR3rAcOjQ==", - "license": "MIT" - }, - "node_modules/builtin-status-codes": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/builtin-status-codes/-/builtin-status-codes-3.0.0.tgz", - "integrity": "sha512-HpGFw18DgFWlncDfjTa2rcQ4W88O1mC8e8yZ2AvQY5KDaktSTwo+KRf6nHK6FRI5FyRyb/5T6+TSxfP7QyGsmQ==", - "license": "MIT" - }, - "node_modules/bytes": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/bytes/-/bytes-3.0.0.tgz", - "integrity": "sha512-pMhOfFDPiv9t5jjIXkHosWmkSyQbvsgEVNkz0ERHbuLh2T/7j4Mqqpz523Fe8MVY89KC6Sh/QfS2sM+SjgFDcw==", - "license": "MIT", - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/cacheable-lookup": { - "version": "7.0.0", - "resolved": "https://registry.npmjs.org/cacheable-lookup/-/cacheable-lookup-7.0.0.tgz", - "integrity": "sha512-+qJyx4xiKra8mZrcwhjMRMUhD5NR1R8esPkzIYxX96JiecFoxAXFuz/GpR3+ev4PE1WamHip78wV0vcmPQtp8w==", - "license": "MIT", - "engines": { - "node": ">=14.16" - } - }, - "node_modules/cacheable-request": { - "version": "10.2.14", - "resolved": "https://registry.npmjs.org/cacheable-request/-/cacheable-request-10.2.14.tgz", - "integrity": "sha512-zkDT5WAF4hSSoUgyfg5tFIxz8XQK+25W/TLVojJTMKBaxevLBBtLxgqguAuVQB8PVW79FVjHcU+GJ9tVbDZ9mQ==", - "license": "MIT", - "dependencies": { - "@types/http-cache-semantics": "^4.0.2", - "get-stream": "^6.0.1", - "http-cache-semantics": "^4.1.1", - "keyv": "^4.5.3", - "mimic-response": "^4.0.0", - "normalize-url": "^8.0.0", - "responselike": "^3.0.0" - }, - "engines": { - "node": ">=14.16" - } - }, - "node_modules/call-bind": { - "version": "1.0.7", - "resolved": "https://registry.npmjs.org/call-bind/-/call-bind-1.0.7.tgz", - "integrity": "sha512-GHTSNSYICQ7scH7sZ+M2rFopRoLh8t2bLSW6BbgrtLsahOIB5iyAVJf9GjWK3cYTDaMj4XdBpM1cA6pIS0Kv2w==", - "license": "MIT", - "dependencies": { - "es-define-property": "^1.0.0", - "es-errors": "^1.3.0", - "function-bind": "^1.1.2", - "get-intrinsic": "^1.2.4", - "set-function-length": "^1.2.1" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/call-me-maybe": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/call-me-maybe/-/call-me-maybe-1.0.2.tgz", - "integrity": "sha512-HpX65o1Hnr9HH25ojC1YGs7HCQLq0GCOibSaWER0eNpgJ/Z1MZv2mTc7+xh6WOPxbRVcmgbv4hGU+uSQ/2xFZQ==", - "license": "MIT" - }, - "node_modules/callsites": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/callsites/-/callsites-3.1.0.tgz", - "integrity": "sha512-P8BjAsXvZS+VIDUI11hHCQEv74YT67YUi5JJFNWIqL235sBmjX4+qx9Muvls5ivyNENctx46xQLQ3aTuE7ssaQ==", - "license": "MIT", - "engines": { - "node": ">=6" - } - }, - "node_modules/camel-case": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/camel-case/-/camel-case-4.1.2.tgz", - "integrity": "sha512-gxGWBrTT1JuMx6R+o5PTXMmUnhnVzLQ9SNutD4YqKtI6ap897t3tKECYla6gCWEkplXnlNybEkZg9GEGxKFCgw==", - "license": "MIT", - "dependencies": { - "pascal-case": "^3.1.2", - "tslib": "^2.0.3" - } - }, - "node_modules/camelcase": { - "version": "6.3.0", - "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-6.3.0.tgz", - "integrity": "sha512-Gmy6FhYlCY7uOElZUSbxo2UCDH8owEk996gkbrpsgGtrJLM3J7jGxl9Ic7Qwwj4ivOE5AWZWRMecDdF7hqGjFA==", - "license": "MIT", - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/caniuse-api": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/caniuse-api/-/caniuse-api-3.0.0.tgz", - "integrity": "sha512-bsTwuIg/BZZK/vreVTYYbSWoe2F+71P7K5QGEX+pT250DZbfU1MQ5prOKpPR+LL6uWKK3KMwMCAS74QB3Um1uw==", - "license": "MIT", - "dependencies": { - "browserslist": "^4.0.0", - "caniuse-lite": "^1.0.0", - "lodash.memoize": "^4.1.2", - "lodash.uniq": "^4.5.0" - } - }, - "node_modules/caniuse-lite": { - "version": "1.0.30001680", - "resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001680.tgz", - "integrity": "sha512-rPQy70G6AGUMnbwS1z6Xg+RkHYPAi18ihs47GH0jcxIG7wArmPgY3XbS2sRdBbxJljp3thdT8BIqv9ccCypiPA==", - "funding": [ - { - "type": "opencollective", - "url": "https://opencollective.com/browserslist" - }, - { - "type": "tidelift", - "url": "https://tidelift.com/funding/github/npm/caniuse-lite" - }, - { - "type": "github", - "url": "https://github.com/sponsors/ai" - } - ], - "license": "CC-BY-4.0" - }, - "node_modules/ccount": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/ccount/-/ccount-2.0.1.tgz", - "integrity": "sha512-eyrF0jiFpY+3drT6383f1qhkbGsLSifNAjA61IUjZjmLCWjItY6LB9ft9YhoDgwfmclB2zhu51Lc7+95b8NRAg==", - "license": "MIT", - "funding": { - "type": "github", - "url": "https://github.com/sponsors/wooorm" - } - }, - "node_modules/chalk": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", - "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", - "license": "MIT", - "dependencies": { - "ansi-styles": "^4.1.0", - "supports-color": "^7.1.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/chalk/chalk?sponsor=1" - } - }, - "node_modules/char-regex": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/char-regex/-/char-regex-1.0.2.tgz", - "integrity": "sha512-kWWXztvZ5SBQV+eRgKFeh8q5sLuZY2+8WUIzlxWVTg+oGwY14qylx1KbKzHd8P6ZYkAg0xyIDU9JMHhyJMZ1jw==", - "license": "MIT", - "engines": { - "node": ">=10" - } - }, - "node_modules/character-entities": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/character-entities/-/character-entities-2.0.2.tgz", - "integrity": "sha512-shx7oQ0Awen/BRIdkjkvz54PnEEI/EjwXDSIZp86/KKdbafHh1Df/RYGBhn4hbe2+uKC9FnT5UCEdyPz3ai9hQ==", - "license": "MIT", - "funding": { - "type": "github", - "url": "https://github.com/sponsors/wooorm" - } - }, - "node_modules/character-entities-html4": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/character-entities-html4/-/character-entities-html4-2.1.0.tgz", - "integrity": "sha512-1v7fgQRj6hnSwFpq1Eu0ynr/CDEw0rXo2B61qXrLNdHZmPKgb7fqS1a2JwF0rISo9q77jDI8VMEHoApn8qDoZA==", - "license": "MIT", - "funding": { - "type": "github", - "url": "https://github.com/sponsors/wooorm" - } - }, - "node_modules/character-entities-legacy": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/character-entities-legacy/-/character-entities-legacy-3.0.0.tgz", - "integrity": "sha512-RpPp0asT/6ufRm//AJVwpViZbGM/MkjQFxJccQRHmISF/22NBtsHqAWmL+/pmkPWoIUJdWyeVleTl1wydHATVQ==", - "license": "MIT", - "funding": { - "type": "github", - "url": "https://github.com/sponsors/wooorm" - } - }, - "node_modules/character-reference-invalid": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/character-reference-invalid/-/character-reference-invalid-2.0.1.tgz", - "integrity": "sha512-iBZ4F4wRbyORVsu0jPV7gXkOsGYjGHPmAyv+HiHG8gi5PtC9KI2j1+v8/tlibRvjoWX027ypmG/n0HtO5t7unw==", - "license": "MIT", - "funding": { - "type": "github", - "url": "https://github.com/sponsors/wooorm" - } - }, - "node_modules/charset": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/charset/-/charset-1.0.1.tgz", - "integrity": "sha512-6dVyOOYjpfFcL1Y4qChrAoQLRHvj2ziyhcm0QJlhOcAhykL/k1kTUPbeo+87MNRTRdk2OIIsIXbuF3x2wi5EXg==", - "license": "MIT", - "engines": { - "node": ">=4.0.0" - } - }, - "node_modules/cheerio": { - "version": "1.0.0-rc.12", - "resolved": "https://registry.npmjs.org/cheerio/-/cheerio-1.0.0-rc.12.tgz", - "integrity": "sha512-VqR8m68vM46BNnuZ5NtnGBKIE/DfN0cRIzg9n40EIq9NOv90ayxLBXA8fXC5gquFRGJSTRqBq25Jt2ECLR431Q==", - "license": "MIT", - "dependencies": { - "cheerio-select": "^2.1.0", - "dom-serializer": "^2.0.0", - "domhandler": "^5.0.3", - "domutils": "^3.0.1", - "htmlparser2": "^8.0.1", - "parse5": "^7.0.0", - "parse5-htmlparser2-tree-adapter": "^7.0.0" - }, - "engines": { - "node": ">= 6" - }, - "funding": { - "url": "https://github.com/cheeriojs/cheerio?sponsor=1" - } - }, - "node_modules/cheerio-select": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/cheerio-select/-/cheerio-select-2.1.0.tgz", - "integrity": "sha512-9v9kG0LvzrlcungtnJtpGNxY+fzECQKhK4EGJX2vByejiMX84MFNQw4UxPJl3bFbTMw+Dfs37XaIkCwTZfLh4g==", - "license": "BSD-2-Clause", - "dependencies": { - "boolbase": "^1.0.0", - "css-select": "^5.1.0", - "css-what": "^6.1.0", - "domelementtype": "^2.3.0", - "domhandler": "^5.0.3", - "domutils": "^3.0.1" - }, - "funding": { - "url": "https://github.com/sponsors/fb55" - } - }, - "node_modules/chokidar": { - "version": "3.6.0", - "resolved": "https://registry.npmjs.org/chokidar/-/chokidar-3.6.0.tgz", - "integrity": "sha512-7VT13fmjotKpGipCW9JEQAusEPE+Ei8nl6/g4FBAmIm0GOOLMua9NDDo/DWp0ZAxCr3cPq5ZpBqmPAQgDda2Pw==", - "license": "MIT", - "dependencies": { - "anymatch": "~3.1.2", - "braces": "~3.0.2", - "glob-parent": "~5.1.2", - "is-binary-path": "~2.1.0", - "is-glob": "~4.0.1", - "normalize-path": "~3.0.0", - "readdirp": "~3.6.0" - }, - "engines": { - "node": ">= 8.10.0" - }, - "funding": { - "url": "https://paulmillr.com/funding/" - }, - "optionalDependencies": { - "fsevents": "~2.3.2" - } - }, - "node_modules/chrome-trace-event": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/chrome-trace-event/-/chrome-trace-event-1.0.4.tgz", - "integrity": "sha512-rNjApaLzuwaOTjCiT8lSDdGN1APCiqkChLMJxJPWLunPAt5fy8xgU9/jNOchV84wfIxrA0lRQB7oCT8jrn/wrQ==", - "license": "MIT", - "engines": { - "node": ">=6.0" - } - }, - "node_modules/ci-info": { - "version": "3.9.0", - "resolved": "https://registry.npmjs.org/ci-info/-/ci-info-3.9.0.tgz", - "integrity": "sha512-NIxF55hv4nSqQswkAeiOi1r83xy8JldOFDTWiug55KBu9Jnblncd2U6ViHmYgHf01TPZS77NJBhBMKdWj9HQMQ==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/sibiraj-s" - } - ], - "license": "MIT", - "engines": { - "node": ">=8" - } - }, - "node_modules/cipher-base": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/cipher-base/-/cipher-base-1.0.4.tgz", - "integrity": "sha512-Kkht5ye6ZGmwv40uUDZztayT2ThLQGfnj/T71N/XzeZeo3nf8foyW7zGTsPYkEya3m5f3cAypH+qe7YOrM1U2Q==", - "license": "MIT", - "dependencies": { - "inherits": "^2.0.1", - "safe-buffer": "^5.0.1" - } - }, - "node_modules/clean-css": { - "version": "5.3.3", - "resolved": "https://registry.npmjs.org/clean-css/-/clean-css-5.3.3.tgz", - "integrity": "sha512-D5J+kHaVb/wKSFcyyV75uCn8fiY4sV38XJoe4CUyGQ+mOU/fMVYUdH1hJC+CJQ5uY3EnW27SbJYS4X8BiLrAFg==", - "license": "MIT", - "dependencies": { - "source-map": "~0.6.0" - }, - "engines": { - "node": ">= 10.0" - } - }, - "node_modules/clean-css/node_modules/source-map": { - "version": "0.6.1", - "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", - "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==", - "license": "BSD-3-Clause", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/clean-stack": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/clean-stack/-/clean-stack-2.2.0.tgz", - "integrity": "sha512-4diC9HaTE+KRAMWhDhrGOECgWZxoevMc5TlkObMqNSsVU62PYzXZ/SMTjzyGAFF1YusgxGcSWTEXBhp0CPwQ1A==", - "license": "MIT", - "engines": { - "node": ">=6" - } - }, - "node_modules/cli-boxes": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/cli-boxes/-/cli-boxes-3.0.0.tgz", - "integrity": "sha512-/lzGpEWL/8PfI0BmBOPRwp0c/wFNX1RdUML3jK/RcSBA9T8mZDdQpqYBKtCFTOfQbwPqWEOpjqW+Fnayc0969g==", - "license": "MIT", - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/cli-table3": { - "version": "0.6.5", - "resolved": "https://registry.npmjs.org/cli-table3/-/cli-table3-0.6.5.tgz", - "integrity": "sha512-+W/5efTR7y5HRD7gACw9yQjqMVvEMLBHmboM/kPWam+H+Hmyrgjh6YncVKK122YZkXrLudzTuAukUw9FnMf7IQ==", - "license": "MIT", - "dependencies": { - "string-width": "^4.2.0" - }, - "engines": { - "node": "10.* || >= 12.*" - }, - "optionalDependencies": { - "@colors/colors": "1.5.0" - } - }, - "node_modules/cli-table3/node_modules/emoji-regex": { - "version": "8.0.0", - "resolved": "https://registry.npmjs.org/emoji-regex/-/emoji-regex-8.0.0.tgz", - "integrity": "sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A==", - "license": "MIT" - }, - "node_modules/cli-table3/node_modules/string-width": { - "version": "4.2.3", - "resolved": "https://registry.npmjs.org/string-width/-/string-width-4.2.3.tgz", - "integrity": "sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g==", - "license": "MIT", - "dependencies": { - "emoji-regex": "^8.0.0", - "is-fullwidth-code-point": "^3.0.0", - "strip-ansi": "^6.0.1" - }, - "engines": { - "node": ">=8" - } - }, - "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==", - "license": "ISC", - "dependencies": { - "string-width": "^4.2.0", - "strip-ansi": "^6.0.1", - "wrap-ansi": "^7.0.0" - }, - "engines": { - "node": ">=12" - } - }, - "node_modules/cliui/node_modules/emoji-regex": { - "version": "8.0.0", - "resolved": "https://registry.npmjs.org/emoji-regex/-/emoji-regex-8.0.0.tgz", - "integrity": "sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A==", - "license": "MIT" - }, - "node_modules/cliui/node_modules/string-width": { - "version": "4.2.3", - "resolved": "https://registry.npmjs.org/string-width/-/string-width-4.2.3.tgz", - "integrity": "sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g==", - "license": "MIT", - "dependencies": { - "emoji-regex": "^8.0.0", - "is-fullwidth-code-point": "^3.0.0", - "strip-ansi": "^6.0.1" - }, - "engines": { - "node": ">=8" - } - }, - "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==", - "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/clone-deep": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/clone-deep/-/clone-deep-4.0.1.tgz", - "integrity": "sha512-neHB9xuzh/wk0dIHweyAXv2aPGZIVk3pLMe+/RNzINf17fe0OG96QroktYAUm7SM1PBnzTabaLboqqxDyMU+SQ==", - "license": "MIT", - "dependencies": { - "is-plain-object": "^2.0.4", - "kind-of": "^6.0.2", - "shallow-clone": "^3.0.0" - }, - "engines": { - "node": ">=6" - } - }, - "node_modules/clsx": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/clsx/-/clsx-2.1.1.tgz", - "integrity": "sha512-eYm0QWBtUrBWZWG0d386OGAw16Z995PiOVo2B7bjWSbHedGl5e0ZWaq65kOGgUSNesEIDkB9ISbTg/JK9dhCZA==", - "license": "MIT", - "engines": { - "node": ">=6" - } - }, - "node_modules/collapse-white-space": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/collapse-white-space/-/collapse-white-space-2.1.0.tgz", - "integrity": "sha512-loKTxY1zCOuG4j9f6EPnuyyYkf58RnhhWTvRoZEokgB+WbdXehfjFviyOVYkqzEWz1Q5kRiZdBYS5SwxbQYwzw==", - "license": "MIT", - "funding": { - "type": "github", - "url": "https://github.com/sponsors/wooorm" - } - }, - "node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "license": "MIT", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==", - "license": "MIT" - }, - "node_modules/colord": { - "version": "2.9.3", - "resolved": "https://registry.npmjs.org/colord/-/colord-2.9.3.tgz", - "integrity": "sha512-jeC1axXpnb0/2nn/Y1LPuLdgXBLH7aDcHu4KEKfqw3CUhX7ZpfBSlPKyqXE6btIgEzfWtrX3/tyBCaCvXvMkOw==", - "license": "MIT" - }, - "node_modules/colorette": { - "version": "2.0.20", - "resolved": "https://registry.npmjs.org/colorette/-/colorette-2.0.20.tgz", - "integrity": "sha512-IfEDxwoWIjkeXL1eXcDiow4UbKjhLdq6/EuSVR9GMN7KVH3r9gQ83e73hsz1Nd1T3ijd5xv1wcWRYO+D6kCI2w==", - "license": "MIT" - }, - "node_modules/combine-promises": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/combine-promises/-/combine-promises-1.2.0.tgz", - "integrity": "sha512-VcQB1ziGD0NXrhKxiwyNbCDmRzs/OShMs2GqW2DlU2A/Sd0nQxE1oWDAE5O0ygSx5mgQOn9eIFh7yKPgFRVkPQ==", - "license": "MIT", - "engines": { - "node": ">=10" - } - }, - "node_modules/comma-separated-tokens": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/comma-separated-tokens/-/comma-separated-tokens-2.0.3.tgz", - "integrity": "sha512-Fu4hJdvzeylCfQPp9SGWidpzrMs7tTrlu6Vb8XGaRGck8QSNZJJp538Wrb60Lax4fPwR64ViY468OIUTbRlGZg==", - "license": "MIT", - "funding": { - "type": "github", - "url": "https://github.com/sponsors/wooorm" - } - }, - "node_modules/commander": { - "version": "5.1.0", - "resolved": "https://registry.npmjs.org/commander/-/commander-5.1.0.tgz", - "integrity": "sha512-P0CysNDQ7rtVw4QIQtm+MRxV66vKFSvlsQvGYXZWR3qFU0jlMKHZZZgw8e+8DSah4UDKMqnknRDQz+xuQXQ/Zg==", - "license": "MIT", - "engines": { - "node": ">= 6" - } - }, - "node_modules/common-path-prefix": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/common-path-prefix/-/common-path-prefix-3.0.0.tgz", - "integrity": "sha512-QE33hToZseCH3jS0qN96O/bSh3kaw/h+Tq7ngyY9eWDUnTlTNUyqfqvCXioLe5Na5jFsL78ra/wuBU4iuEgd4w==", - "license": "ISC" - }, - "node_modules/compressible": { - "version": "2.0.18", - "resolved": "https://registry.npmjs.org/compressible/-/compressible-2.0.18.tgz", - "integrity": "sha512-AF3r7P5dWxL8MxyITRMlORQNaOA2IkAFaTr4k7BUumjPtRpGDTZpl0Pb1XCO6JeDCBdp126Cgs9sMxqSjgYyRg==", - "license": "MIT", - "dependencies": { - "mime-db": ">= 1.43.0 < 2" - }, - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/compressible/node_modules/mime-db": { - "version": "1.53.0", - "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.53.0.tgz", - "integrity": "sha512-oHlN/w+3MQ3rba9rqFr6V/ypF10LSkdwUysQL7GkXoTgIWeV+tcXGA852TBxH+gsh8UWoyhR1hKcoMJTuWflpg==", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/compression": { - "version": "1.7.4", - "resolved": "https://registry.npmjs.org/compression/-/compression-1.7.4.tgz", - "integrity": "sha512-jaSIDzP9pZVS4ZfQ+TzvtiWhdpFhE2RDHz8QJkpX9SIpLq88VueF5jJw6t+6CUQcAoA6t+x89MLrWAqpfDE8iQ==", - "license": "MIT", - "dependencies": { - "accepts": "~1.3.5", - "bytes": "3.0.0", - "compressible": "~2.0.16", - "debug": "2.6.9", - "on-headers": "~1.0.2", - "safe-buffer": "5.1.2", - "vary": "~1.1.2" - }, - "engines": { - "node": ">= 0.8.0" - } - }, - "node_modules/compression/node_modules/debug": { - "version": "2.6.9", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", - "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", - "license": "MIT", - "dependencies": { - "ms": "2.0.0" - } - }, - "node_modules/compression/node_modules/ms": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", - "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==", - "license": "MIT" - }, - "node_modules/compression/node_modules/safe-buffer": { - "version": "5.1.2", - "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz", - "integrity": "sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==", - "license": "MIT" - }, - "node_modules/compute-gcd": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/compute-gcd/-/compute-gcd-1.2.1.tgz", - "integrity": "sha512-TwMbxBNz0l71+8Sc4czv13h4kEqnchV9igQZBi6QUaz09dnz13juGnnaWWJTRsP3brxOoxeB4SA2WELLw1hCtg==", - "dependencies": { - "validate.io-array": "^1.0.3", - "validate.io-function": "^1.0.2", - "validate.io-integer-array": "^1.0.0" - } - }, - "node_modules/compute-lcm": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/compute-lcm/-/compute-lcm-1.1.2.tgz", - "integrity": "sha512-OFNPdQAXnQhDSKioX8/XYT6sdUlXwpeMjfd6ApxMJfyZ4GxmLR1xvMERctlYhlHwIiz6CSpBc2+qYKjHGZw4TQ==", - "dependencies": { - "compute-gcd": "^1.2.1", - "validate.io-array": "^1.0.3", - "validate.io-function": "^1.0.2", - "validate.io-integer-array": "^1.0.0" - } - }, - "node_modules/concat-map": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", - "integrity": "sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg==", - "license": "MIT" - }, - "node_modules/concurrently": { - "version": "8.2.2", - "resolved": "https://registry.npmjs.org/concurrently/-/concurrently-8.2.2.tgz", - "integrity": "sha512-1dP4gpXFhei8IOtlXRE/T/4H88ElHgTiUzh71YUmtjTEHMSRS2Z/fgOxHSxxusGHogsRfxNq1vyAwxSC+EVyDg==", - "dev": true, - "license": "MIT", - "dependencies": { - "chalk": "^4.1.2", - "date-fns": "^2.30.0", - "lodash": "^4.17.21", - "rxjs": "^7.8.1", - "shell-quote": "^1.8.1", - "spawn-command": "0.0.2", - "supports-color": "^8.1.1", - "tree-kill": "^1.2.2", - "yargs": "^17.7.2" - }, - "bin": { - "conc": "dist/bin/concurrently.js", - "concurrently": "dist/bin/concurrently.js" - }, - "engines": { - "node": "^14.13.0 || >=16.0.0" - }, - "funding": { - "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": { - "has-flag": "^4.0.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/chalk/supports-color?sponsor=1" - } - }, - "node_modules/config-chain": { - "version": "1.1.13", - "resolved": "https://registry.npmjs.org/config-chain/-/config-chain-1.1.13.tgz", - "integrity": "sha512-qj+f8APARXHrM0hraqXYb2/bOVSV4PvJQlNZ/DVj0QrmNM2q2euizkeuVckQ57J+W0mRH6Hvi+k50M4Jul2VRQ==", - "license": "MIT", - "dependencies": { - "ini": "^1.3.4", - "proto-list": "~1.2.1" - } - }, - "node_modules/configstore": { - "version": "6.0.0", - "resolved": "https://registry.npmjs.org/configstore/-/configstore-6.0.0.tgz", - "integrity": "sha512-cD31W1v3GqUlQvbBCGcXmd2Nj9SvLDOP1oQ0YFuLETufzSPaKp11rYBsSOm7rCsW3OnIRAFM3OxRhceaXNYHkA==", - "license": "BSD-2-Clause", - "dependencies": { - "dot-prop": "^6.0.1", - "graceful-fs": "^4.2.6", - "unique-string": "^3.0.0", - "write-file-atomic": "^3.0.3", - "xdg-basedir": "^5.0.1" - }, - "engines": { - "node": ">=12" - }, - "funding": { - "url": "https://github.com/yeoman/configstore?sponsor=1" - } - }, - "node_modules/connect-history-api-fallback": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/connect-history-api-fallback/-/connect-history-api-fallback-2.0.0.tgz", - "integrity": "sha512-U73+6lQFmfiNPrYbXqr6kZ1i1wiRqXnp2nhMsINseWXO8lDau0LGEffJ8kQi4EjLZympVgRdvqjAgiZ1tgzDDA==", - "license": "MIT", - "engines": { - "node": ">=0.8" - } - }, - "node_modules/consola": { - "version": "3.4.0", - "resolved": "https://registry.npmjs.org/consola/-/consola-3.4.0.tgz", - "integrity": "sha512-EiPU8G6dQG0GFHNR8ljnZFki/8a+cQwEQ+7wpxdChl02Q8HXlwEZWD5lqAF8vC2sEC3Tehr8hy7vErz88LHyUA==", - "license": "MIT", - "engines": { - "node": "^14.18.0 || >=16.10.0" - } - }, - "node_modules/console-browserify": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/console-browserify/-/console-browserify-1.2.0.tgz", - "integrity": "sha512-ZMkYO/LkF17QvCPqM0gxw8yUzigAOZOSWSHg91FH6orS7vcEj5dVZTidN2fQ14yBSdg97RqhSNwLUXInd52OTA==" - }, - "node_modules/constants-browserify": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/constants-browserify/-/constants-browserify-1.0.0.tgz", - "integrity": "sha512-xFxOwqIzR/e1k1gLiWEophSCMqXcwVHIH7akf7b/vxcUeGunlj3hvZaaqxwHsTgn+IndtkQJgSztIDWeumWJDQ==", - "license": "MIT" - }, - "node_modules/content-disposition": { - "version": "0.5.2", - "resolved": "https://registry.npmjs.org/content-disposition/-/content-disposition-0.5.2.tgz", - "integrity": "sha512-kRGRZw3bLlFISDBgwTSA1TMBFN6J6GWDeubmDE3AF+3+yXL8hTWv8r5rkLbqYXY4RjPk/EzHnClI3zQf1cFmHA==", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/content-type": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/content-type/-/content-type-1.0.5.tgz", - "integrity": "sha512-nTjqfcBFEipKdXCv4YDQWCfmcLZKm81ldF0pAopTvyrFGVbcR6P/VAAd5G7N+0tTr8QqiU0tFadD6FK4NtJwOA==", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/convert-source-map": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/convert-source-map/-/convert-source-map-2.0.0.tgz", - "integrity": "sha512-Kvp459HrV2FEJ1CAsi1Ku+MY3kasH19TFykTz2xWmMeq6bk2NU3XXvfJ+Q61m0xktWwt+1HSYf3JZsTms3aRJg==", - "license": "MIT" - }, - "node_modules/cookie": { - "version": "0.7.1", - "resolved": "https://registry.npmjs.org/cookie/-/cookie-0.7.1.tgz", - "integrity": "sha512-6DnInpx7SJ2AK3+CTUE/ZM0vWTUboZCegxhC2xiIydHR9jNuTAASBrfEpHhiGOZw/nX51bHt6YQl8jsGo4y/0w==", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/cookie-signature": { - "version": "1.0.6", - "resolved": "https://registry.npmjs.org/cookie-signature/-/cookie-signature-1.0.6.tgz", - "integrity": "sha512-QADzlaHc8icV8I7vbaJXJwod9HWYp8uCqf1xa4OfNu1T7JVxQIrUgOWtHdNDtPiywmFbiS12VjotIXLrKM3orQ==", - "license": "MIT" - }, - "node_modules/copy-text-to-clipboard": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/copy-text-to-clipboard/-/copy-text-to-clipboard-3.2.0.tgz", - "integrity": "sha512-RnJFp1XR/LOBDckxTib5Qjr/PMfkatD0MUCQgdpqS8MdKiNUzBjAQBEN6oUy+jW7LI93BBG3DtMB2KOOKpGs2Q==", - "license": "MIT", - "engines": { - "node": ">=12" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/copy-webpack-plugin": { - "version": "11.0.0", - "resolved": "https://registry.npmjs.org/copy-webpack-plugin/-/copy-webpack-plugin-11.0.0.tgz", - "integrity": "sha512-fX2MWpamkW0hZxMEg0+mYnA40LTosOSa5TqZ9GYIBzyJa9C3QUaMPSE2xAi/buNr8u89SfD9wHSQVBzrRa/SOQ==", - "license": "MIT", - "dependencies": { - "fast-glob": "^3.2.11", - "glob-parent": "^6.0.1", - "globby": "^13.1.1", - "normalize-path": "^3.0.0", - "schema-utils": "^4.0.0", - "serialize-javascript": "^6.0.0" - }, - "engines": { - "node": ">= 14.15.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/webpack" - }, - "peerDependencies": { - "webpack": "^5.1.0" - } - }, - "node_modules/copy-webpack-plugin/node_modules/glob-parent": { - "version": "6.0.2", - "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-6.0.2.tgz", - "integrity": "sha512-XxwI8EOhVQgWp6iDL+3b0r86f4d6AX6zSU55HfB4ydCEuXLXc5FcYeOu+nnGftS4TEju/11rt4KJPTMgbfmv4A==", - "license": "ISC", - "dependencies": { - "is-glob": "^4.0.3" - }, - "engines": { - "node": ">=10.13.0" - } - }, - "node_modules/copy-webpack-plugin/node_modules/globby": { - "version": "13.2.2", - "resolved": "https://registry.npmjs.org/globby/-/globby-13.2.2.tgz", - "integrity": "sha512-Y1zNGV+pzQdh7H39l9zgB4PJqjRNqydvdYCDG4HFXM4XuvSaQQlEc91IU1yALL8gUTDomgBAfz3XJdmUS+oo0w==", - "license": "MIT", - "dependencies": { - "dir-glob": "^3.0.1", - "fast-glob": "^3.3.0", - "ignore": "^5.2.4", - "merge2": "^1.4.1", - "slash": "^4.0.0" - }, - "engines": { - "node": "^12.20.0 || ^14.13.1 || >=16.0.0" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/copy-webpack-plugin/node_modules/slash": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/slash/-/slash-4.0.0.tgz", - "integrity": "sha512-3dOsAHXXUkQTpOYcoAxLIorMTp4gIQr5IW3iVb7A7lFIp0VHhnynm9izx6TssdrIcVIESAlVjtnO2K8bg+Coew==", - "license": "MIT", - "engines": { - "node": ">=12" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/core-js": { - "version": "3.38.0", - "resolved": "https://registry.npmjs.org/core-js/-/core-js-3.38.0.tgz", - "integrity": "sha512-XPpwqEodRljce9KswjZShh95qJ1URisBeKCjUdq27YdenkslVe7OO0ZJhlYXAChW7OhXaRLl8AAba7IBfoIHug==", - "hasInstallScript": true, - "license": "MIT", - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/core-js" - } - }, - "node_modules/core-js-compat": { - "version": "3.39.0", - "resolved": "https://registry.npmjs.org/core-js-compat/-/core-js-compat-3.39.0.tgz", - "integrity": "sha512-VgEUx3VwlExr5no0tXlBt+silBvhTryPwCXRI2Id1PN8WTKu7MreethvddqOubrYxkFdv/RnYrqlv1sFNAUelw==", - "license": "MIT", - "dependencies": { - "browserslist": "^4.24.2" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/core-js" - } - }, - "node_modules/core-js-pure": { - "version": "3.40.0", - "resolved": "https://registry.npmjs.org/core-js-pure/-/core-js-pure-3.40.0.tgz", - "integrity": "sha512-AtDzVIgRrmRKQai62yuSIN5vNiQjcJakJb4fbhVw3ehxx7Lohphvw9SGNWKhLFqSxC4ilD0g/L1huAYFQU3Q6A==", - "hasInstallScript": true, - "license": "MIT", - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/core-js" - } - }, - "node_modules/core-util-is": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/core-util-is/-/core-util-is-1.0.3.tgz", - "integrity": "sha512-ZQBvi1DcpJ4GDqanjucZ2Hj3wEO5pZDS89BWbkcrvdxksJorwUDDZamX9ldFkp9aw2lmBDLgkObEA4DWNJ9FYQ==", - "license": "MIT" - }, - "node_modules/cosmiconfig": { - "version": "8.3.6", - "resolved": "https://registry.npmjs.org/cosmiconfig/-/cosmiconfig-8.3.6.tgz", - "integrity": "sha512-kcZ6+W5QzcJ3P1Mt+83OUv/oHFqZHIx8DuxG6eZ5RGMERoLqp4BuGjhHLYGK+Kf5XVkQvqBSmAy/nGWN3qDgEA==", - "license": "MIT", - "dependencies": { - "import-fresh": "^3.3.0", - "js-yaml": "^4.1.0", - "parse-json": "^5.2.0", - "path-type": "^4.0.0" - }, - "engines": { - "node": ">=14" - }, - "funding": { - "url": "https://github.com/sponsors/d-fischer" - }, - "peerDependencies": { - "typescript": ">=4.9.5" - }, - "peerDependenciesMeta": { - "typescript": { - "optional": true - } - } - }, - "node_modules/create-ecdh": { - "version": "4.0.4", - "resolved": "https://registry.npmjs.org/create-ecdh/-/create-ecdh-4.0.4.tgz", - "integrity": "sha512-mf+TCx8wWc9VpuxfP2ht0iSISLZnt0JgWlrOKZiNqyUZWnjIaCIVNQArMHnCZKfEYRg6IM7A+NeJoN8gf/Ws0A==", - "license": "MIT", - "dependencies": { - "bn.js": "^4.1.0", - "elliptic": "^6.5.3" - } - }, - "node_modules/create-ecdh/node_modules/bn.js": { - "version": "4.12.0", - "resolved": "https://registry.npmjs.org/bn.js/-/bn.js-4.12.0.tgz", - "integrity": "sha512-c98Bf3tPniI+scsdk237ku1Dc3ujXQTSgyiPUDEOe7tRkhrqridvh8klBv0HCEso1OLOYcHuCv/cS6DNxKH+ZA==", - "license": "MIT" - }, - "node_modules/create-hash": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/create-hash/-/create-hash-1.2.0.tgz", - "integrity": "sha512-z00bCGNHDG8mHAkP7CtT1qVu+bFQUPjYq/4Iv3C3kWjTFV10zIjfSoeqXo9Asws8gwSHDGj/hl2u4OGIjapeCg==", - "license": "MIT", - "dependencies": { - "cipher-base": "^1.0.1", - "inherits": "^2.0.1", - "md5.js": "^1.3.4", - "ripemd160": "^2.0.1", - "sha.js": "^2.4.0" - } - }, - "node_modules/create-hmac": { - "version": "1.1.7", - "resolved": "https://registry.npmjs.org/create-hmac/-/create-hmac-1.1.7.tgz", - "integrity": "sha512-MJG9liiZ+ogc4TzUwuvbER1JRdgvUFSB5+VR/g5h82fGaIRWMWddtKBHi7/sVhfjQZ6SehlyhvQYrcYkaUIpLg==", - "license": "MIT", - "dependencies": { - "cipher-base": "^1.0.3", - "create-hash": "^1.1.0", - "inherits": "^2.0.1", - "ripemd160": "^2.0.0", - "safe-buffer": "^5.0.1", - "sha.js": "^2.4.8" - } - }, - "node_modules/cross-spawn": { - "version": "7.0.5", - "resolved": "https://registry.npmjs.org/cross-spawn/-/cross-spawn-7.0.5.tgz", - "integrity": "sha512-ZVJrKKYunU38/76t0RMOulHOnUcbU9GbpWKAOZ0mhjr7CX6FVrH+4FrAapSOekrgFQ3f/8gwMEuIft0aKq6Hug==", - "license": "MIT", - "dependencies": { - "path-key": "^3.1.0", - "shebang-command": "^2.0.0", - "which": "^2.0.1" - }, - "engines": { - "node": ">= 8" - } - }, - "node_modules/crypto-browserify": { - "version": "3.12.0", - "resolved": "https://registry.npmjs.org/crypto-browserify/-/crypto-browserify-3.12.0.tgz", - "integrity": "sha512-fz4spIh+znjO2VjL+IdhEpRJ3YN6sMzITSBijk6FK2UvTqruSQW+/cCZTSNsMiZNvUeq0CqurF+dAbyiGOY6Wg==", - "license": "MIT", - "dependencies": { - "browserify-cipher": "^1.0.0", - "browserify-sign": "^4.0.0", - "create-ecdh": "^4.0.0", - "create-hash": "^1.1.0", - "create-hmac": "^1.1.0", - "diffie-hellman": "^5.0.0", - "inherits": "^2.0.1", - "pbkdf2": "^3.0.3", - "public-encrypt": "^4.0.0", - "randombytes": "^2.0.0", - "randomfill": "^1.0.3" - }, - "engines": { - "node": "*" - } - }, - "node_modules/crypto-js": { - "version": "4.2.0", - "resolved": "https://registry.npmjs.org/crypto-js/-/crypto-js-4.2.0.tgz", - "integrity": "sha512-KALDyEYgpY+Rlob/iriUtjV6d5Eq+Y191A5g4UqLAi8CyGP9N1+FdVbkc1SxKc2r4YAYqG8JzO2KGL+AizD70Q==", - "license": "MIT" - }, - "node_modules/crypto-random-string": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/crypto-random-string/-/crypto-random-string-4.0.0.tgz", - "integrity": "sha512-x8dy3RnvYdlUcPOjkEHqozhiwzKNSq7GcPuXFbnyMOCHxX8V3OgIg/pYuabl2sbUPfIJaeAQB7PMOK8DFIdoRA==", - "license": "MIT", - "dependencies": { - "type-fest": "^1.0.1" - }, - "engines": { - "node": ">=12" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/crypto-random-string/node_modules/type-fest": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/type-fest/-/type-fest-1.4.0.tgz", - "integrity": "sha512-yGSza74xk0UG8k+pLh5oeoYirvIiWo5t0/o3zHHAO2tRDiZcxWP7fywNlXhqb6/r6sWvwi+RsyQMWhVLe4BVuA==", - "license": "(MIT OR CC0-1.0)", - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/css-blank-pseudo": { - "version": "7.0.1", - "resolved": "https://registry.npmjs.org/css-blank-pseudo/-/css-blank-pseudo-7.0.1.tgz", - "integrity": "sha512-jf+twWGDf6LDoXDUode+nc7ZlrqfaNphrBIBrcmeP3D8yw1uPaix1gCC8LUQUGQ6CycuK2opkbFFWFuq/a94ag==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "dependencies": { - "postcss-selector-parser": "^7.0.0" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/css-blank-pseudo/node_modules/postcss-selector-parser": { - "version": "7.0.0", - "resolved": "https://registry.npmjs.org/postcss-selector-parser/-/postcss-selector-parser-7.0.0.tgz", - "integrity": "sha512-9RbEr1Y7FFfptd/1eEdntyjMwLeghW1bHX9GWjXo19vx4ytPQhANltvVxDggzJl7mnWM+dX28kb6cyS/4iQjlQ==", - "license": "MIT", - "dependencies": { - "cssesc": "^3.0.0", - "util-deprecate": "^1.0.2" - }, - "engines": { - "node": ">=4" - } - }, - "node_modules/css-declaration-sorter": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/css-declaration-sorter/-/css-declaration-sorter-7.2.0.tgz", - "integrity": "sha512-h70rUM+3PNFuaBDTLe8wF/cdWu+dOZmb7pJt8Z2sedYbAcQVQV/tEchueg3GWxwqS0cxtbxmaHEdkNACqcvsow==", - "license": "ISC", - "engines": { - "node": "^14 || ^16 || >=18" - }, - "peerDependencies": { - "postcss": "^8.0.9" - } - }, - "node_modules/css-has-pseudo": { - "version": "7.0.2", - "resolved": "https://registry.npmjs.org/css-has-pseudo/-/css-has-pseudo-7.0.2.tgz", - "integrity": "sha512-nzol/h+E0bId46Kn2dQH5VElaknX2Sr0hFuB/1EomdC7j+OISt2ZzK7EHX9DZDY53WbIVAR7FYKSO2XnSf07MQ==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "dependencies": { - "@csstools/selector-specificity": "^5.0.0", - "postcss-selector-parser": "^7.0.0", - "postcss-value-parser": "^4.2.0" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/css-has-pseudo/node_modules/@csstools/selector-specificity": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/@csstools/selector-specificity/-/selector-specificity-5.0.0.tgz", - "integrity": "sha512-PCqQV3c4CoVm3kdPhyeZ07VmBRdH2EpMFA/pd9OASpOEC3aXNGoqPDAZ80D0cLpMBxnmk0+yNhGsEx31hq7Gtw==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss-selector-parser": "^7.0.0" - } - }, - "node_modules/css-has-pseudo/node_modules/postcss-selector-parser": { - "version": "7.0.0", - "resolved": "https://registry.npmjs.org/postcss-selector-parser/-/postcss-selector-parser-7.0.0.tgz", - "integrity": "sha512-9RbEr1Y7FFfptd/1eEdntyjMwLeghW1bHX9GWjXo19vx4ytPQhANltvVxDggzJl7mnWM+dX28kb6cyS/4iQjlQ==", - "license": "MIT", - "dependencies": { - "cssesc": "^3.0.0", - "util-deprecate": "^1.0.2" - }, - "engines": { - "node": ">=4" - } - }, - "node_modules/css-loader": { - "version": "6.11.0", - "resolved": "https://registry.npmjs.org/css-loader/-/css-loader-6.11.0.tgz", - "integrity": "sha512-CTJ+AEQJjq5NzLga5pE39qdiSV56F8ywCIsqNIRF0r7BDgWsN25aazToqAFg7ZrtA/U016xudB3ffgweORxX7g==", - "license": "MIT", - "dependencies": { - "icss-utils": "^5.1.0", - "postcss": "^8.4.33", - "postcss-modules-extract-imports": "^3.1.0", - "postcss-modules-local-by-default": "^4.0.5", - "postcss-modules-scope": "^3.2.0", - "postcss-modules-values": "^4.0.0", - "postcss-value-parser": "^4.2.0", - "semver": "^7.5.4" - }, - "engines": { - "node": ">= 12.13.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/webpack" - }, - "peerDependencies": { - "@rspack/core": "0.x || 1.x", - "webpack": "^5.0.0" - }, - "peerDependenciesMeta": { - "@rspack/core": { - "optional": true - }, - "webpack": { - "optional": true - } - } - }, - "node_modules/css-minimizer-webpack-plugin": { - "version": "5.0.1", - "resolved": "https://registry.npmjs.org/css-minimizer-webpack-plugin/-/css-minimizer-webpack-plugin-5.0.1.tgz", - "integrity": "sha512-3caImjKFQkS+ws1TGcFn0V1HyDJFq1Euy589JlD6/3rV2kj+w7r5G9WDMgSHvpvXHNZ2calVypZWuEDQd9wfLg==", - "license": "MIT", - "dependencies": { - "@jridgewell/trace-mapping": "^0.3.18", - "cssnano": "^6.0.1", - "jest-worker": "^29.4.3", - "postcss": "^8.4.24", - "schema-utils": "^4.0.1", - "serialize-javascript": "^6.0.1" - }, - "engines": { - "node": ">= 14.15.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/webpack" - }, - "peerDependencies": { - "webpack": "^5.0.0" - }, - "peerDependenciesMeta": { - "@parcel/css": { - "optional": true - }, - "@swc/css": { - "optional": true - }, - "clean-css": { - "optional": true - }, - "csso": { - "optional": true - }, - "esbuild": { - "optional": true - }, - "lightningcss": { - "optional": true - } - } - }, - "node_modules/css-prefers-color-scheme": { - "version": "10.0.0", - "resolved": "https://registry.npmjs.org/css-prefers-color-scheme/-/css-prefers-color-scheme-10.0.0.tgz", - "integrity": "sha512-VCtXZAWivRglTZditUfB4StnsWr6YVZ2PRtuxQLKTNRdtAf8tpzaVPE9zXIF3VaSc7O70iK/j1+NXxyQCqdPjQ==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/css-select": { - "version": "5.1.0", - "resolved": "https://registry.npmjs.org/css-select/-/css-select-5.1.0.tgz", - "integrity": "sha512-nwoRF1rvRRnnCqqY7updORDsuqKzqYJ28+oSMaJMMgOauh3fvwHqMS7EZpIPqK8GL+g9mKxF1vP/ZjSeNjEVHg==", - "license": "BSD-2-Clause", - "dependencies": { - "boolbase": "^1.0.0", - "css-what": "^6.1.0", - "domhandler": "^5.0.2", - "domutils": "^3.0.1", - "nth-check": "^2.0.1" - }, - "funding": { - "url": "https://github.com/sponsors/fb55" - } - }, - "node_modules/css-tree": { - "version": "2.3.1", - "resolved": "https://registry.npmjs.org/css-tree/-/css-tree-2.3.1.tgz", - "integrity": "sha512-6Fv1DV/TYw//QF5IzQdqsNDjx/wc8TrMBZsqjL9eW01tWb7R7k/mq+/VXfJCl7SoD5emsJop9cOByJZfs8hYIw==", - "license": "MIT", - "dependencies": { - "mdn-data": "2.0.30", - "source-map-js": "^1.0.1" - }, - "engines": { - "node": "^10 || ^12.20.0 || ^14.13.0 || >=15.0.0" - } - }, - "node_modules/css-what": { - "version": "6.1.0", - "resolved": "https://registry.npmjs.org/css-what/-/css-what-6.1.0.tgz", - "integrity": "sha512-HTUrgRJ7r4dsZKU6GjmpfRK1O76h97Z8MfS1G0FozR+oF2kG6Vfe8JE6zwrkbxigziPHinCJ+gCPjA9EaBDtRw==", - "license": "BSD-2-Clause", - "engines": { - "node": ">= 6" - }, - "funding": { - "url": "https://github.com/sponsors/fb55" - } - }, - "node_modules/cssdb": { - "version": "8.2.3", - "resolved": "https://registry.npmjs.org/cssdb/-/cssdb-8.2.3.tgz", - "integrity": "sha512-9BDG5XmJrJQQnJ51VFxXCAtpZ5ebDlAREmO8sxMOVU0aSxN/gocbctjIG5LMh3WBUq+xTlb/jw2LoljBEqraTA==", - "funding": [ - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - }, - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - } - ], - "license": "MIT-0" - }, - "node_modules/cssesc": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/cssesc/-/cssesc-3.0.0.tgz", - "integrity": "sha512-/Tb/JcjK111nNScGob5MNtsntNM1aCNUDipB/TkwZFhyDrrE47SOx/18wF2bbjgc3ZzCSKW1T5nt5EbFoAz/Vg==", - "license": "MIT", - "bin": { - "cssesc": "bin/cssesc" - }, - "engines": { - "node": ">=4" - } - }, - "node_modules/cssnano": { - "version": "6.1.2", - "resolved": "https://registry.npmjs.org/cssnano/-/cssnano-6.1.2.tgz", - "integrity": "sha512-rYk5UeX7VAM/u0lNqewCdasdtPK81CgX8wJFLEIXHbV2oldWRgJAsZrdhRXkV1NJzA2g850KiFm9mMU2HxNxMA==", - "license": "MIT", - "dependencies": { - "cssnano-preset-default": "^6.1.2", - "lilconfig": "^3.1.1" - }, - "engines": { - "node": "^14 || ^16 || >=18.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/cssnano" - }, - "peerDependencies": { - "postcss": "^8.4.31" - } - }, - "node_modules/cssnano-preset-advanced": { - "version": "6.1.2", - "resolved": "https://registry.npmjs.org/cssnano-preset-advanced/-/cssnano-preset-advanced-6.1.2.tgz", - "integrity": "sha512-Nhao7eD8ph2DoHolEzQs5CfRpiEP0xa1HBdnFZ82kvqdmbwVBUr2r1QuQ4t1pi+D1ZpqpcO4T+wy/7RxzJ/WPQ==", - "license": "MIT", - "dependencies": { - "autoprefixer": "^10.4.19", - "browserslist": "^4.23.0", - "cssnano-preset-default": "^6.1.2", - "postcss-discard-unused": "^6.0.5", - "postcss-merge-idents": "^6.0.3", - "postcss-reduce-idents": "^6.0.3", - "postcss-zindex": "^6.0.2" - }, - "engines": { - "node": "^14 || ^16 || >=18.0" - }, - "peerDependencies": { - "postcss": "^8.4.31" - } - }, - "node_modules/cssnano-preset-default": { - "version": "6.1.2", - "resolved": "https://registry.npmjs.org/cssnano-preset-default/-/cssnano-preset-default-6.1.2.tgz", - "integrity": "sha512-1C0C+eNaeN8OcHQa193aRgYexyJtU8XwbdieEjClw+J9d94E41LwT6ivKH0WT+fYwYWB0Zp3I3IZ7tI/BbUbrg==", - "license": "MIT", - "dependencies": { - "browserslist": "^4.23.0", - "css-declaration-sorter": "^7.2.0", - "cssnano-utils": "^4.0.2", - "postcss-calc": "^9.0.1", - "postcss-colormin": "^6.1.0", - "postcss-convert-values": "^6.1.0", - "postcss-discard-comments": "^6.0.2", - "postcss-discard-duplicates": "^6.0.3", - "postcss-discard-empty": "^6.0.3", - "postcss-discard-overridden": "^6.0.2", - "postcss-merge-longhand": "^6.0.5", - "postcss-merge-rules": "^6.1.1", - "postcss-minify-font-values": "^6.1.0", - "postcss-minify-gradients": "^6.0.3", - "postcss-minify-params": "^6.1.0", - "postcss-minify-selectors": "^6.0.4", - "postcss-normalize-charset": "^6.0.2", - "postcss-normalize-display-values": "^6.0.2", - "postcss-normalize-positions": "^6.0.2", - "postcss-normalize-repeat-style": "^6.0.2", - "postcss-normalize-string": "^6.0.2", - "postcss-normalize-timing-functions": "^6.0.2", - "postcss-normalize-unicode": "^6.1.0", - "postcss-normalize-url": "^6.0.2", - "postcss-normalize-whitespace": "^6.0.2", - "postcss-ordered-values": "^6.0.2", - "postcss-reduce-initial": "^6.1.0", - "postcss-reduce-transforms": "^6.0.2", - "postcss-svgo": "^6.0.3", - "postcss-unique-selectors": "^6.0.4" - }, - "engines": { - "node": "^14 || ^16 || >=18.0" - }, - "peerDependencies": { - "postcss": "^8.4.31" - } - }, - "node_modules/cssnano-utils": { - "version": "4.0.2", - "resolved": "https://registry.npmjs.org/cssnano-utils/-/cssnano-utils-4.0.2.tgz", - "integrity": "sha512-ZR1jHg+wZ8o4c3zqf1SIUSTIvm/9mU343FMR6Obe/unskbvpGhZOo1J6d/r8D1pzkRQYuwbcH3hToOuoA2G7oQ==", - "license": "MIT", - "engines": { - "node": "^14 || ^16 || >=18.0" - }, - "peerDependencies": { - "postcss": "^8.4.31" - } - }, - "node_modules/csso": { - "version": "5.0.5", - "resolved": "https://registry.npmjs.org/csso/-/csso-5.0.5.tgz", - "integrity": "sha512-0LrrStPOdJj+SPCCrGhzryycLjwcgUSHBtxNA8aIDxf0GLsRh1cKYhB00Gd1lDOS4yGH69+SNn13+TWbVHETFQ==", - "license": "MIT", - "dependencies": { - "css-tree": "~2.2.0" - }, - "engines": { - "node": "^10 || ^12.20.0 || ^14.13.0 || >=15.0.0", - "npm": ">=7.0.0" - } - }, - "node_modules/csso/node_modules/css-tree": { - "version": "2.2.1", - "resolved": "https://registry.npmjs.org/css-tree/-/css-tree-2.2.1.tgz", - "integrity": "sha512-OA0mILzGc1kCOCSJerOeqDxDQ4HOh+G8NbOJFOTgOCzpw7fCBubk0fEyxp8AgOL/jvLgYA/uV0cMbe43ElF1JA==", - "license": "MIT", - "dependencies": { - "mdn-data": "2.0.28", - "source-map-js": "^1.0.1" - }, - "engines": { - "node": "^10 || ^12.20.0 || ^14.13.0 || >=15.0.0", - "npm": ">=7.0.0" - } - }, - "node_modules/csso/node_modules/mdn-data": { - "version": "2.0.28", - "resolved": "https://registry.npmjs.org/mdn-data/-/mdn-data-2.0.28.tgz", - "integrity": "sha512-aylIc7Z9y4yzHYAJNuESG3hfhC+0Ibp/MAMiaOZgNv4pmEdFyfZhhhny4MNiAfWdBQ1RQ2mfDWmM1x8SvGyp8g==", - "license": "CC0-1.0" - }, - "node_modules/csstype": { - "version": "3.1.3", - "resolved": "https://registry.npmjs.org/csstype/-/csstype-3.1.3.tgz", - "integrity": "sha512-M1uQkMl8rQK/szD0LNhtqxIPLpimGm8sOBwU7lLnCpSbTyY3yeU1Vc7l4KT5zT4s/yOxHH5O7tIuuLOCnLADRw==", - "license": "MIT" - }, - "node_modules/date-fns": { - "version": "2.30.0", - "resolved": "https://registry.npmjs.org/date-fns/-/date-fns-2.30.0.tgz", - "integrity": "sha512-fnULvOpxnC5/Vg3NCiWelDsLiUc9bRwAPs/+LfTLNvetFCtCTN+yQz15C/fs4AwX1R9K5GLtLfn8QW+dWisaAw==", - "dev": true, - "license": "MIT", - "dependencies": { - "@babel/runtime": "^7.21.0" - }, - "engines": { - "node": ">=0.11" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/date-fns" - } - }, - "node_modules/debounce": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/debounce/-/debounce-1.2.1.tgz", - "integrity": "sha512-XRRe6Glud4rd/ZGQfiV1ruXSfbvfJedlV9Y6zOlP+2K04vBYiJEte6stfFkCP03aMnY5tsipamumUjL14fofug==", - "license": "MIT" - }, - "node_modules/debug": { - "version": "4.3.6", - "resolved": "https://registry.npmjs.org/debug/-/debug-4.3.6.tgz", - "integrity": "sha512-O/09Bd4Z1fBrU4VzkhFqVgpPzaGbw6Sm9FEkBT1A/YBXQFGuuSxa1dN2nxgxS34JmKXqYx8CZAwEVoJFImUXIg==", - "license": "MIT", - "dependencies": { - "ms": "2.1.2" - }, - "engines": { - "node": ">=6.0" - }, - "peerDependenciesMeta": { - "supports-color": { - "optional": true - } - } - }, - "node_modules/decode-named-character-reference": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/decode-named-character-reference/-/decode-named-character-reference-1.0.2.tgz", - "integrity": "sha512-O8x12RzrUF8xyVcY0KJowWsmaJxQbmy0/EtnNtHRpsOcT7dFk5W598coHqBVpmWo1oQQfsCqfCmkZN5DJrZVdg==", - "license": "MIT", - "dependencies": { - "character-entities": "^2.0.0" - }, - "funding": { - "type": "github", - "url": "https://github.com/sponsors/wooorm" - } - }, - "node_modules/decompress-response": { - "version": "6.0.0", - "resolved": "https://registry.npmjs.org/decompress-response/-/decompress-response-6.0.0.tgz", - "integrity": "sha512-aW35yZM6Bb/4oJlZncMH2LCoZtJXTRxES17vE3hoRiowU2kWHaJKFkSBDnDR+cm9J+9QhXmREyIfv0pji9ejCQ==", - "license": "MIT", - "dependencies": { - "mimic-response": "^3.1.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/decompress-response/node_modules/mimic-response": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/mimic-response/-/mimic-response-3.1.0.tgz", - "integrity": "sha512-z0yWI+4FDrrweS8Zmt4Ej5HdJmky15+L2e6Wgn3+iK5fWzb6T3fhNFq2+MeTRb064c6Wr4N/wv0DzQTjNzHNGQ==", - "license": "MIT", - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/deep-extend": { - "version": "0.6.0", - "resolved": "https://registry.npmjs.org/deep-extend/-/deep-extend-0.6.0.tgz", - "integrity": "sha512-LOHxIOaPYdHlJRtCQfDIVZtfw/ufM8+rVj649RIHzcm/vGwQRXFt6OPqIFWsm2XEMrNIEtWR64sY1LEKD2vAOA==", - "license": "MIT", - "engines": { - "node": ">=4.0.0" - } - }, - "node_modules/deepmerge": { - "version": "4.3.1", - "resolved": "https://registry.npmjs.org/deepmerge/-/deepmerge-4.3.1.tgz", - "integrity": "sha512-3sUqbMEc77XqpdNO7FRyRog+eW3ph+GYCbj+rK+uYyRMuwsVy0rMiVtPn+QJlKFvWP/1PYpapqYn0Me2knFn+A==", - "license": "MIT", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/default-gateway": { - "version": "6.0.3", - "resolved": "https://registry.npmjs.org/default-gateway/-/default-gateway-6.0.3.tgz", - "integrity": "sha512-fwSOJsbbNzZ/CUFpqFBqYfYNLj1NbMPm8MMCIzHjC83iSJRBEGmDUxU+WP661BaBQImeC2yHwXtz+P/O9o+XEg==", - "license": "BSD-2-Clause", - "dependencies": { - "execa": "^5.0.0" - }, - "engines": { - "node": ">= 10" - } - }, - "node_modules/defer-to-connect": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/defer-to-connect/-/defer-to-connect-2.0.1.tgz", - "integrity": "sha512-4tvttepXG1VaYGrRibk5EwJd1t4udunSOVMdLSAL6mId1ix438oPwPZMALY41FCijukO1L0twNcGsdzS7dHgDg==", - "license": "MIT", - "engines": { - "node": ">=10" - } - }, - "node_modules/define-data-property": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/define-data-property/-/define-data-property-1.1.4.tgz", - "integrity": "sha512-rBMvIzlpA8v6E+SJZoo++HAYqsLrkg7MSfIinMPFhmkorw7X+dOXVJQs+QT69zGkzMyfDnIMN2Wid1+NbL3T+A==", - "license": "MIT", - "dependencies": { - "es-define-property": "^1.0.0", - "es-errors": "^1.3.0", - "gopd": "^1.0.1" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/define-lazy-prop": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/define-lazy-prop/-/define-lazy-prop-2.0.0.tgz", - "integrity": "sha512-Ds09qNh8yw3khSjiJjiUInaGX9xlqZDY7JVryGxdxV7NPeuqQfplOpQ66yJFZut3jLa5zOwkXw1g9EI2uKh4Og==", - "license": "MIT", - "engines": { - "node": ">=8" - } - }, - "node_modules/define-properties": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/define-properties/-/define-properties-1.2.1.tgz", - "integrity": "sha512-8QmQKqEASLd5nx0U1B1okLElbUuuttJ/AnYmRXbbbGDWh6uS208EjD4Xqq/I9wK7u0v6O08XhTWnt5XtEbR6Dg==", - "license": "MIT", - "dependencies": { - "define-data-property": "^1.0.1", - "has-property-descriptors": "^1.0.0", - "object-keys": "^1.1.1" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/del": { - "version": "6.1.1", - "resolved": "https://registry.npmjs.org/del/-/del-6.1.1.tgz", - "integrity": "sha512-ua8BhapfP0JUJKC/zV9yHHDW/rDoDxP4Zhn3AkA6/xT6gY7jYXJiaeyBZznYVujhZZET+UgcbZiQ7sN3WqcImg==", - "license": "MIT", - "dependencies": { - "globby": "^11.0.1", - "graceful-fs": "^4.2.4", - "is-glob": "^4.0.1", - "is-path-cwd": "^2.2.0", - "is-path-inside": "^3.0.2", - "p-map": "^4.0.0", - "rimraf": "^3.0.2", - "slash": "^3.0.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/depd": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/depd/-/depd-2.0.0.tgz", - "integrity": "sha512-g7nH6P6dyDioJogAAGprGpCtVImJhpPk/roCzdb3fIh61/s/nPsfR6onyMwkCAR/OlC3yBC0lESvUoQEAssIrw==", - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/dequal": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/dequal/-/dequal-2.0.3.tgz", - "integrity": "sha512-0je+qPKHEMohvfRTCEo3CrPG6cAzAYgmzKyxRiYSSDkS6eGJdyVJm7WaYA5ECaAD9wLB2T4EEeymA5aFVcYXCA==", - "license": "MIT", - "engines": { - "node": ">=6" - } - }, - "node_modules/des.js": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/des.js/-/des.js-1.1.0.tgz", - "integrity": "sha512-r17GxjhUCjSRy8aiJpr8/UadFIzMzJGexI3Nmz4ADi9LYSFx4gTBp80+NaX/YsXWWLhpZ7v/v/ubEc/bCNfKwg==", - "license": "MIT", - "dependencies": { - "inherits": "^2.0.1", - "minimalistic-assert": "^1.0.0" - } - }, - "node_modules/destroy": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/destroy/-/destroy-1.2.0.tgz", - "integrity": "sha512-2sJGJTaXIIaR1w4iJSNoN0hnMY7Gpc/n8D4qSCJw8QqFWXf7cuAgnEHxBpweaVcPevC2l3KpjYCx3NypQQgaJg==", - "engines": { - "node": ">= 0.8", - "npm": "1.2.8000 || >= 1.4.16" - } - }, - "node_modules/detect-libc": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/detect-libc/-/detect-libc-1.0.3.tgz", - "integrity": "sha512-pGjwhsmsp4kL2RTz08wcOlGN83otlqHeD/Z5T8GXZB+/YcpQ/dgo+lbU8ZsGxV0HIvqqxo9l7mqYwyYMD9bKDg==", - "license": "Apache-2.0", - "optional": true, - "bin": { - "detect-libc": "bin/detect-libc.js" - }, - "engines": { - "node": ">=0.10" - } - }, - "node_modules/detect-node": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/detect-node/-/detect-node-2.1.0.tgz", - "integrity": "sha512-T0NIuQpnTvFDATNuHN5roPwSBG83rFsuO+MXXH9/3N1eFbn4wcPjttvjMLEPWJ0RGUYgQE7cGgS3tNxbqCGM7g==", - "license": "MIT" - }, - "node_modules/detect-package-manager": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/detect-package-manager/-/detect-package-manager-3.0.2.tgz", - "integrity": "sha512-8JFjJHutStYrfWwzfretQoyNGoZVW1Fsrp4JO9spa7h/fBfwgTMEIy4/LBzRDGsxwVPHU0q+T9YvwLDJoOApLQ==", - "license": "MIT", - "dependencies": { - "execa": "^5.1.1" - }, - "engines": { - "node": ">=12" - } - }, - "node_modules/detect-port": { - "version": "1.6.1", - "resolved": "https://registry.npmjs.org/detect-port/-/detect-port-1.6.1.tgz", - "integrity": "sha512-CmnVc+Hek2egPx1PeTFVta2W78xy2K/9Rkf6cC4T59S50tVnzKj+tnx5mmx5lwvCkujZ4uRrpRSuV+IVs3f90Q==", - "license": "MIT", - "dependencies": { - "address": "^1.0.1", - "debug": "4" - }, - "bin": { - "detect": "bin/detect-port.js", - "detect-port": "bin/detect-port.js" - }, - "engines": { - "node": ">= 4.0.0" - } - }, - "node_modules/detect-port-alt": { - "version": "1.1.6", - "resolved": "https://registry.npmjs.org/detect-port-alt/-/detect-port-alt-1.1.6.tgz", - "integrity": "sha512-5tQykt+LqfJFBEYaDITx7S7cR7mJ/zQmLXZ2qt5w04ainYZw6tBf9dBunMjVeVOdYVRUzUOE4HkY5J7+uttb5Q==", - "license": "MIT", - "dependencies": { - "address": "^1.0.1", - "debug": "^2.6.0" - }, - "bin": { - "detect": "bin/detect-port", - "detect-port": "bin/detect-port" - }, - "engines": { - "node": ">= 4.2.1" - } - }, - "node_modules/detect-port-alt/node_modules/debug": { - "version": "2.6.9", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", - "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", - "license": "MIT", - "dependencies": { - "ms": "2.0.0" - } - }, - "node_modules/detect-port-alt/node_modules/ms": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", - "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==", - "license": "MIT" - }, - "node_modules/devlop": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/devlop/-/devlop-1.1.0.tgz", - "integrity": "sha512-RWmIqhcFf1lRYBvNmr7qTNuyCt/7/ns2jbpp1+PalgE/rDQcBT0fioSMUpJ93irlUhC5hrg4cYqe6U+0ImW0rA==", - "license": "MIT", - "dependencies": { - "dequal": "^2.0.0" - }, - "funding": { - "type": "github", - "url": "https://github.com/sponsors/wooorm" - } - }, - "node_modules/diff": { - "version": "5.2.0", - "resolved": "https://registry.npmjs.org/diff/-/diff-5.2.0.tgz", - "integrity": "sha512-uIFDxqpRZGZ6ThOk84hEfqWoHx2devRFvpTZcTHur85vImfaxUbTW9Ryh4CpCuDnToOP1CEtXKIgytHBPVff5A==", - "license": "BSD-3-Clause", - "engines": { - "node": ">=0.3.1" - } - }, - "node_modules/diffie-hellman": { - "version": "5.0.3", - "resolved": "https://registry.npmjs.org/diffie-hellman/-/diffie-hellman-5.0.3.tgz", - "integrity": "sha512-kqag/Nl+f3GwyK25fhUMYj81BUOrZ9IuJsjIcDE5icNM9FJHAVm3VcUDxdLPoQtTuUylWm6ZIknYJwwaPxsUzg==", - "license": "MIT", - "dependencies": { - "bn.js": "^4.1.0", - "miller-rabin": "^4.0.0", - "randombytes": "^2.0.0" - } - }, - "node_modules/diffie-hellman/node_modules/bn.js": { - "version": "4.12.0", - "resolved": "https://registry.npmjs.org/bn.js/-/bn.js-4.12.0.tgz", - "integrity": "sha512-c98Bf3tPniI+scsdk237ku1Dc3ujXQTSgyiPUDEOe7tRkhrqridvh8klBv0HCEso1OLOYcHuCv/cS6DNxKH+ZA==", - "license": "MIT" - }, - "node_modules/dir-glob": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/dir-glob/-/dir-glob-3.0.1.tgz", - "integrity": "sha512-WkrWp9GR4KXfKGYzOLmTuGVi1UWFfws377n9cc55/tb6DuqyF6pcQ5AbiHEshaDpY9v6oaSr2XCDidGmMwdzIA==", - "license": "MIT", - "dependencies": { - "path-type": "^4.0.0" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/dns-packet": { - "version": "5.6.1", - "resolved": "https://registry.npmjs.org/dns-packet/-/dns-packet-5.6.1.tgz", - "integrity": "sha512-l4gcSouhcgIKRvyy99RNVOgxXiicE+2jZoNmaNmZ6JXiGajBOJAesk1OBlJuM5k2c+eudGdLxDqXuPCKIj6kpw==", - "license": "MIT", - "dependencies": { - "@leichtgewicht/ip-codec": "^2.0.1" - }, - "engines": { - "node": ">=6" - } - }, - "node_modules/docusaurus-plugin-llms-txt": { - "version": "0.1.3", - "resolved": "https://registry.npmjs.org/docusaurus-plugin-llms-txt/-/docusaurus-plugin-llms-txt-0.1.3.tgz", - "integrity": "sha512-X/Dqf1/soHFjvELWXtfa9C023498HsWWwNPdVZEu0OoznI2Gzf+VCB/4obwpBSV9OeDeI8D94/dK/ETq534k9A==", - "license": "MIT", - "dependencies": { - "fs-extra": "^11.2.0", - "gray-matter": "^4.0.3" - }, - "engines": { - "node": ">=16.14" - }, - "peerDependencies": { - "@docusaurus/core": ">=2.0.0", - "react": ">=16.8.0" - } - }, - "node_modules/docusaurus-plugin-openapi-docs": { - "version": "4.2.0", - "resolved": "https://registry.npmjs.org/docusaurus-plugin-openapi-docs/-/docusaurus-plugin-openapi-docs-4.2.0.tgz", - "integrity": "sha512-6G8LtpQlb4nCTyDnjkRwxg/oq3WIZ05GCFQFfTqbdiI5D8d9Glya0vp6TF9InEyXtAkc8ozi1HP8It2zEUwNGw==", - "license": "MIT", - "dependencies": { - "@apidevtools/json-schema-ref-parser": "^11.5.4", - "@docusaurus/plugin-content-docs": "^3.5.0", - "@docusaurus/utils": "^3.5.0", - "@docusaurus/utils-validation": "^3.5.0", - "@redocly/openapi-core": "^1.10.5", - "allof-merge": "^0.6.6", - "chalk": "^4.1.2", - "clsx": "^1.1.1", - "fs-extra": "^9.0.1", - "json-pointer": "^0.6.2", - "json5": "^2.2.3", - "lodash": "^4.17.20", - "mustache": "^4.2.0", - "openapi-to-postmanv2": "^4.21.0", - "postman-collection": "^4.4.0", - "slugify": "^1.6.5", - "swagger2openapi": "^7.0.8", - "xml-formatter": "^2.6.1" - }, - "engines": { - "node": ">=14" - }, - "peerDependencies": { - "react": "^16.8.4 || ^17.0.0 || ^18.0.0" - } - }, - "node_modules/docusaurus-plugin-openapi-docs/node_modules/clsx": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/clsx/-/clsx-1.2.1.tgz", - "integrity": "sha512-EcR6r5a8bj6pu3ycsa/E/cKVGuTgZJZdsyUYHOksG/UHIiKfjxzRxYJpyVBwYaQeOvghal9fcc4PidlgzugAQg==", - "license": "MIT", - "engines": { - "node": ">=6" - } - }, - "node_modules/docusaurus-plugin-openapi-docs/node_modules/fs-extra": { - "version": "9.1.0", - "resolved": "https://registry.npmjs.org/fs-extra/-/fs-extra-9.1.0.tgz", - "integrity": "sha512-hcg3ZmepS30/7BSFqRvoo3DOMQu7IjqxO5nCDt+zM9XWjb33Wg7ziNT+Qvqbuc3+gWpzO02JubVyk2G4Zvo1OQ==", - "license": "MIT", - "dependencies": { - "at-least-node": "^1.0.0", - "graceful-fs": "^4.2.0", - "jsonfile": "^6.0.1", - "universalify": "^2.0.0" - }, - "engines": { - "node": ">=10" - } - }, - "node_modules/docusaurus-plugin-sass": { - "version": "0.2.5", - "resolved": "https://registry.npmjs.org/docusaurus-plugin-sass/-/docusaurus-plugin-sass-0.2.5.tgz", - "integrity": "sha512-Z+D0fLFUKcFpM+bqSUmqKIU+vO+YF1xoEQh5hoFreg2eMf722+siwXDD+sqtwU8E4MvVpuvsQfaHwODNlxJAEg==", - "license": "MIT", - "dependencies": { - "sass-loader": "^10.1.1" - }, - "peerDependencies": { - "@docusaurus/core": "^2.0.0-beta || ^3.0.0-alpha", - "sass": "^1.30.0" - } - }, - "node_modules/docusaurus-plugin-search-local": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/docusaurus-plugin-search-local/-/docusaurus-plugin-search-local-2.1.0.tgz", - "integrity": "sha512-pHQ1UffJ33IDUZ3e5/FFcfX5ktnza4KCi5ivK7ndKJjeU4GyQdUb5/WsCQ5z0+V3GIFL3GmB1C/kOU0wUZFJnQ==", - "license": "MIT", - "workspaces": [ - "./website" - ], - "dependencies": { - "@braintree/sanitize-url": "^6.0.0", - "cheerio": "^1.0.0", - "clsx": "^1.1.1", - "debug": "^4.3.4", - "fs-extra": "^10.1.0", - "klaw-sync": "^6.0.0", - "lunr": "^2.3.9", - "mark.js": "^8.11.1", - "validate-peer-dependencies": "^2.2.0" - }, - "engines": { - "node": ">=18.18.2" - }, - "peerDependencies": { - "@docusaurus/core": ">=3.0.0", - "@docusaurus/utils": ">=3.0.0", - "@docusaurus/utils-validation": ">=3.0.0", - "react": ">=18.2.0", - "react-dom": ">=18.2.0" - } - }, - "node_modules/docusaurus-plugin-search-local/node_modules/cheerio": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/cheerio/-/cheerio-1.0.0.tgz", - "integrity": "sha512-quS9HgjQpdaXOvsZz82Oz7uxtXiy6UIsIQcpBj7HRw2M63Skasm9qlDocAM7jNuaxdhpPU7c4kJN+gA5MCu4ww==", - "license": "MIT", - "dependencies": { - "cheerio-select": "^2.1.0", - "dom-serializer": "^2.0.0", - "domhandler": "^5.0.3", - "domutils": "^3.1.0", - "encoding-sniffer": "^0.2.0", - "htmlparser2": "^9.1.0", - "parse5": "^7.1.2", - "parse5-htmlparser2-tree-adapter": "^7.0.0", - "parse5-parser-stream": "^7.1.2", - "undici": "^6.19.5", - "whatwg-mimetype": "^4.0.0" - }, - "engines": { - "node": ">=18.17" - }, - "funding": { - "url": "https://github.com/cheeriojs/cheerio?sponsor=1" - } - }, - "node_modules/docusaurus-plugin-search-local/node_modules/clsx": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/clsx/-/clsx-1.2.1.tgz", - "integrity": "sha512-EcR6r5a8bj6pu3ycsa/E/cKVGuTgZJZdsyUYHOksG/UHIiKfjxzRxYJpyVBwYaQeOvghal9fcc4PidlgzugAQg==", - "license": "MIT", - "engines": { - "node": ">=6" - } - }, - "node_modules/docusaurus-plugin-search-local/node_modules/fs-extra": { - "version": "10.1.0", - "resolved": "https://registry.npmjs.org/fs-extra/-/fs-extra-10.1.0.tgz", - "integrity": "sha512-oRXApq54ETRj4eMiFzGnHWGy+zo5raudjuxN0b8H7s/RU2oW0Wvsx9O0ACRN/kRq9E8Vu/ReskGB5o3ji+FzHQ==", - "license": "MIT", - "dependencies": { - "graceful-fs": "^4.2.0", - "jsonfile": "^6.0.1", - "universalify": "^2.0.0" - }, - "engines": { - "node": ">=12" - } - }, - "node_modules/docusaurus-plugin-search-local/node_modules/htmlparser2": { - "version": "9.1.0", - "resolved": "https://registry.npmjs.org/htmlparser2/-/htmlparser2-9.1.0.tgz", - "integrity": "sha512-5zfg6mHUoaer/97TxnGpxmbR7zJtPwIYFMZ/H5ucTlPZhKvtum05yiPK3Mgai3a0DyVxv7qYqoweaEd2nrYQzQ==", - "funding": [ - "https://github.com/fb55/htmlparser2?sponsor=1", - { - "type": "github", - "url": "https://github.com/sponsors/fb55" - } - ], - "license": "MIT", - "dependencies": { - "domelementtype": "^2.3.0", - "domhandler": "^5.0.3", - "domutils": "^3.1.0", - "entities": "^4.5.0" - } - }, - "node_modules/docusaurus-theme-openapi-docs": { - "version": "4.2.0", - "resolved": "https://registry.npmjs.org/docusaurus-theme-openapi-docs/-/docusaurus-theme-openapi-docs-4.2.0.tgz", - "integrity": "sha512-TTvrF3mOt9VjDJHu5Ga7jPZyPxhu6//FKTLXJrcGrQ/OOMnojCZZX0KX7zSUL96yF8VlRjwSeM9D90m+dZ9gHw==", - "license": "MIT", - "dependencies": { - "@docusaurus/theme-common": "^3.5.0", - "@hookform/error-message": "^2.0.1", - "@reduxjs/toolkit": "^1.7.1", - "allof-merge": "^0.6.6", - "clsx": "^1.1.1", - "copy-text-to-clipboard": "^3.1.0", - "crypto-js": "^4.1.1", - "docusaurus-plugin-openapi-docs": "^4.2.0", - "docusaurus-plugin-sass": "^0.2.3", - "file-saver": "^2.0.5", - "lodash": "^4.17.20", - "node-polyfill-webpack-plugin": "^2.0.1", - "postman-code-generators": "^1.10.1", - "postman-collection": "^4.4.0", - "prism-react-renderer": "^2.3.0", - "react-hook-form": "^7.43.8", - "react-live": "^4.0.0", - "react-magic-dropzone": "^1.0.1", - "react-markdown": "^8.0.1", - "react-modal": "^3.15.1", - "react-redux": "^7.2.0", - "rehype-raw": "^6.1.1", - "remark-gfm": "3.0.1", - "sass": "^1.80.4", - "sass-loader": "^16.0.2", - "webpack": "^5.61.0", - "xml-formatter": "^2.6.1" - }, - "engines": { - "node": ">=14" - }, - "peerDependencies": { - "react": "^16.8.4 || ^17.0.0 || ^18.0.0", - "react-dom": "^16.8.4 || ^17.0.0 || ^18.0.0" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/@types/hast": { - "version": "2.3.10", - "resolved": "https://registry.npmjs.org/@types/hast/-/hast-2.3.10.tgz", - "integrity": "sha512-McWspRw8xx8J9HurkVBfYj0xKoE25tOFlHGdx4MJ5xORQrMGZNqJhVQWaIbm6Oyla5kYOXtDiopzKRJzEOkwJw==", - "license": "MIT", - "dependencies": { - "@types/unist": "^2" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/@types/mdast": { - "version": "3.0.15", - "resolved": "https://registry.npmjs.org/@types/mdast/-/mdast-3.0.15.tgz", - "integrity": "sha512-LnwD+mUEfxWMa1QpDraczIn6k0Ee3SMicuYSSzS6ZYl2gKS09EClnJYGd8Du6rfc5r/GZEk5o1mRb8TaTj03sQ==", - "license": "MIT", - "dependencies": { - "@types/unist": "^2" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/@types/unist": { - "version": "2.0.11", - "resolved": "https://registry.npmjs.org/@types/unist/-/unist-2.0.11.tgz", - "integrity": "sha512-CmBKiL6NNo/OqgmMn95Fk9Whlp2mtvIv+KNpQKN2F4SjvrEesubTRWGYSg+BnWZOnlCaSTU1sMpsBOzgbYhnsA==", - "license": "MIT" - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/clsx": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/clsx/-/clsx-1.2.1.tgz", - "integrity": "sha512-EcR6r5a8bj6pu3ycsa/E/cKVGuTgZJZdsyUYHOksG/UHIiKfjxzRxYJpyVBwYaQeOvghal9fcc4PidlgzugAQg==", - "license": "MIT", - "engines": { - "node": ">=6" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/escape-string-regexp": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-5.0.0.tgz", - "integrity": "sha512-/veY75JbMK4j1yjvuUxuVsiS/hr/4iHs9FTT6cgTexxdE0Ly/glccBAkloH/DofkjRbZU3bnoj38mOmhkZ0lHw==", - "license": "MIT", - "engines": { - "node": ">=12" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/hast-util-from-parse5": { - "version": "7.1.2", - "resolved": "https://registry.npmjs.org/hast-util-from-parse5/-/hast-util-from-parse5-7.1.2.tgz", - "integrity": "sha512-Nz7FfPBuljzsN3tCQ4kCBKqdNhQE2l0Tn+X1ubgKBPRoiDIu1mL08Cfw4k7q71+Duyaw7DXDN+VTAp4Vh3oCOw==", - "license": "MIT", - "dependencies": { - "@types/hast": "^2.0.0", - "@types/unist": "^2.0.0", - "hastscript": "^7.0.0", - "property-information": "^6.0.0", - "vfile": "^5.0.0", - "vfile-location": "^4.0.0", - "web-namespaces": "^2.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/hast-util-parse-selector": { - "version": "3.1.1", - "resolved": "https://registry.npmjs.org/hast-util-parse-selector/-/hast-util-parse-selector-3.1.1.tgz", - "integrity": "sha512-jdlwBjEexy1oGz0aJ2f4GKMaVKkA9jwjr4MjAAI22E5fM/TXVZHuS5OpONtdeIkRKqAaryQ2E9xNQxijoThSZA==", - "license": "MIT", - "dependencies": { - "@types/hast": "^2.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/hast-util-raw": { - "version": "7.2.3", - "resolved": "https://registry.npmjs.org/hast-util-raw/-/hast-util-raw-7.2.3.tgz", - "integrity": "sha512-RujVQfVsOrxzPOPSzZFiwofMArbQke6DJjnFfceiEbFh7S05CbPt0cYN+A5YeD3pso0JQk6O1aHBnx9+Pm2uqg==", - "license": "MIT", - "dependencies": { - "@types/hast": "^2.0.0", - "@types/parse5": "^6.0.0", - "hast-util-from-parse5": "^7.0.0", - "hast-util-to-parse5": "^7.0.0", - "html-void-elements": "^2.0.0", - "parse5": "^6.0.0", - "unist-util-position": "^4.0.0", - "unist-util-visit": "^4.0.0", - "vfile": "^5.0.0", - "web-namespaces": "^2.0.0", - "zwitch": "^2.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/hast-util-to-parse5": { - "version": "7.1.0", - "resolved": "https://registry.npmjs.org/hast-util-to-parse5/-/hast-util-to-parse5-7.1.0.tgz", - "integrity": "sha512-YNRgAJkH2Jky5ySkIqFXTQiaqcAtJyVE+D5lkN6CdtOqrnkLfGYYrEcKuHOJZlp+MwjSwuD3fZuawI+sic/RBw==", - "license": "MIT", - "dependencies": { - "@types/hast": "^2.0.0", - "comma-separated-tokens": "^2.0.0", - "property-information": "^6.0.0", - "space-separated-tokens": "^2.0.0", - "web-namespaces": "^2.0.0", - "zwitch": "^2.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/hastscript": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/hastscript/-/hastscript-7.2.0.tgz", - "integrity": "sha512-TtYPq24IldU8iKoJQqvZOuhi5CyCQRAbvDOX0x1eW6rsHSxa/1i2CCiptNTotGHJ3VoHRGmqiv6/D3q113ikkw==", - "license": "MIT", - "dependencies": { - "@types/hast": "^2.0.0", - "comma-separated-tokens": "^2.0.0", - "hast-util-parse-selector": "^3.0.0", - "property-information": "^6.0.0", - "space-separated-tokens": "^2.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/html-void-elements": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/html-void-elements/-/html-void-elements-2.0.1.tgz", - "integrity": "sha512-0quDb7s97CfemeJAnW9wC0hw78MtW7NU3hqtCD75g2vFlDLt36llsYD7uB7SUzojLMP24N5IatXf7ylGXiGG9A==", - "license": "MIT", - "funding": { - "type": "github", - "url": "https://github.com/sponsors/wooorm" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/mdast-util-find-and-replace": { - "version": "2.2.2", - "resolved": "https://registry.npmjs.org/mdast-util-find-and-replace/-/mdast-util-find-and-replace-2.2.2.tgz", - "integrity": "sha512-MTtdFRz/eMDHXzeK6W3dO7mXUlF82Gom4y0oOgvHhh/HXZAGvIQDUvQ0SuUx+j2tv44b8xTHOm8K/9OoRFnXKw==", - "license": "MIT", - "dependencies": { - "@types/mdast": "^3.0.0", - "escape-string-regexp": "^5.0.0", - "unist-util-is": "^5.0.0", - "unist-util-visit-parents": "^5.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/mdast-util-from-markdown": { - "version": "1.3.1", - "resolved": "https://registry.npmjs.org/mdast-util-from-markdown/-/mdast-util-from-markdown-1.3.1.tgz", - "integrity": "sha512-4xTO/M8c82qBcnQc1tgpNtubGUW/Y1tBQ1B0i5CtSoelOLKFYlElIr3bvgREYYO5iRqbMY1YuqZng0GVOI8Qww==", - "license": "MIT", - "dependencies": { - "@types/mdast": "^3.0.0", - "@types/unist": "^2.0.0", - "decode-named-character-reference": "^1.0.0", - "mdast-util-to-string": "^3.1.0", - "micromark": "^3.0.0", - "micromark-util-decode-numeric-character-reference": "^1.0.0", - "micromark-util-decode-string": "^1.0.0", - "micromark-util-normalize-identifier": "^1.0.0", - "micromark-util-symbol": "^1.0.0", - "micromark-util-types": "^1.0.0", - "unist-util-stringify-position": "^3.0.0", - "uvu": "^0.5.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/mdast-util-gfm": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/mdast-util-gfm/-/mdast-util-gfm-2.0.2.tgz", - "integrity": "sha512-qvZ608nBppZ4icQlhQQIAdc6S3Ffj9RGmzwUKUWuEICFnd1LVkN3EktF7ZHAgfcEdvZB5owU9tQgt99e2TlLjg==", - "license": "MIT", - "dependencies": { - "mdast-util-from-markdown": "^1.0.0", - "mdast-util-gfm-autolink-literal": "^1.0.0", - "mdast-util-gfm-footnote": "^1.0.0", - "mdast-util-gfm-strikethrough": "^1.0.0", - "mdast-util-gfm-table": "^1.0.0", - "mdast-util-gfm-task-list-item": "^1.0.0", - "mdast-util-to-markdown": "^1.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/mdast-util-gfm-autolink-literal": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/mdast-util-gfm-autolink-literal/-/mdast-util-gfm-autolink-literal-1.0.3.tgz", - "integrity": "sha512-My8KJ57FYEy2W2LyNom4n3E7hKTuQk/0SES0u16tjA9Z3oFkF4RrC/hPAPgjlSpezsOvI8ObcXcElo92wn5IGA==", - "license": "MIT", - "dependencies": { - "@types/mdast": "^3.0.0", - "ccount": "^2.0.0", - "mdast-util-find-and-replace": "^2.0.0", - "micromark-util-character": "^1.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/mdast-util-gfm-footnote": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/mdast-util-gfm-footnote/-/mdast-util-gfm-footnote-1.0.2.tgz", - "integrity": "sha512-56D19KOGbE00uKVj3sgIykpwKL179QsVFwx/DCW0u/0+URsryacI4MAdNJl0dh+u2PSsD9FtxPFbHCzJ78qJFQ==", - "license": "MIT", - "dependencies": { - "@types/mdast": "^3.0.0", - "mdast-util-to-markdown": "^1.3.0", - "micromark-util-normalize-identifier": "^1.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/mdast-util-gfm-strikethrough": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/mdast-util-gfm-strikethrough/-/mdast-util-gfm-strikethrough-1.0.3.tgz", - "integrity": "sha512-DAPhYzTYrRcXdMjUtUjKvW9z/FNAMTdU0ORyMcbmkwYNbKocDpdk+PX1L1dQgOID/+vVs1uBQ7ElrBQfZ0cuiQ==", - "license": "MIT", - "dependencies": { - "@types/mdast": "^3.0.0", - "mdast-util-to-markdown": "^1.3.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/mdast-util-gfm-table": { - "version": "1.0.7", - "resolved": "https://registry.npmjs.org/mdast-util-gfm-table/-/mdast-util-gfm-table-1.0.7.tgz", - "integrity": "sha512-jjcpmNnQvrmN5Vx7y7lEc2iIOEytYv7rTvu+MeyAsSHTASGCCRA79Igg2uKssgOs1i1po8s3plW0sTu1wkkLGg==", - "license": "MIT", - "dependencies": { - "@types/mdast": "^3.0.0", - "markdown-table": "^3.0.0", - "mdast-util-from-markdown": "^1.0.0", - "mdast-util-to-markdown": "^1.3.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/mdast-util-gfm-task-list-item": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/mdast-util-gfm-task-list-item/-/mdast-util-gfm-task-list-item-1.0.2.tgz", - "integrity": "sha512-PFTA1gzfp1B1UaiJVyhJZA1rm0+Tzn690frc/L8vNX1Jop4STZgOE6bxUhnzdVSB+vm2GU1tIsuQcA9bxTQpMQ==", - "license": "MIT", - "dependencies": { - "@types/mdast": "^3.0.0", - "mdast-util-to-markdown": "^1.3.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/mdast-util-phrasing": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/mdast-util-phrasing/-/mdast-util-phrasing-3.0.1.tgz", - "integrity": "sha512-WmI1gTXUBJo4/ZmSk79Wcb2HcjPJBzM1nlI/OUWA8yk2X9ik3ffNbBGsU+09BFmXaL1IBb9fiuvq6/KMiNycSg==", - "license": "MIT", - "dependencies": { - "@types/mdast": "^3.0.0", - "unist-util-is": "^5.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/mdast-util-to-markdown": { - "version": "1.5.0", - "resolved": "https://registry.npmjs.org/mdast-util-to-markdown/-/mdast-util-to-markdown-1.5.0.tgz", - "integrity": "sha512-bbv7TPv/WC49thZPg3jXuqzuvI45IL2EVAr/KxF0BSdHsU0ceFHOmwQn6evxAh1GaoK/6GQ1wp4R4oW2+LFL/A==", - "license": "MIT", - "dependencies": { - "@types/mdast": "^3.0.0", - "@types/unist": "^2.0.0", - "longest-streak": "^3.0.0", - "mdast-util-phrasing": "^3.0.0", - "mdast-util-to-string": "^3.0.0", - "micromark-util-decode-string": "^1.0.0", - "unist-util-visit": "^4.0.0", - "zwitch": "^2.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/mdast-util-to-string": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/mdast-util-to-string/-/mdast-util-to-string-3.2.0.tgz", - "integrity": "sha512-V4Zn/ncyN1QNSqSBxTrMOLpjr+IKdHl2v3KVLoWmDPscP4r9GcCi71gjgvUV1SFSKh92AjAG4peFuBl2/YgCJg==", - "license": "MIT", - "dependencies": { - "@types/mdast": "^3.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/micromark": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/micromark/-/micromark-3.2.0.tgz", - "integrity": "sha512-uD66tJj54JLYq0De10AhWycZWGQNUvDI55xPgk2sQM5kn1JYlhbCMTtEeT27+vAhW2FBQxLlOmS3pmA7/2z4aA==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "@types/debug": "^4.0.0", - "debug": "^4.0.0", - "decode-named-character-reference": "^1.0.0", - "micromark-core-commonmark": "^1.0.1", - "micromark-factory-space": "^1.0.0", - "micromark-util-character": "^1.0.0", - "micromark-util-chunked": "^1.0.0", - "micromark-util-combine-extensions": "^1.0.0", - "micromark-util-decode-numeric-character-reference": "^1.0.0", - "micromark-util-encode": "^1.0.0", - "micromark-util-normalize-identifier": "^1.0.0", - "micromark-util-resolve-all": "^1.0.0", - "micromark-util-sanitize-uri": "^1.0.0", - "micromark-util-subtokenize": "^1.0.0", - "micromark-util-symbol": "^1.0.0", - "micromark-util-types": "^1.0.1", - "uvu": "^0.5.0" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/micromark-core-commonmark": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/micromark-core-commonmark/-/micromark-core-commonmark-1.1.0.tgz", - "integrity": "sha512-BgHO1aRbolh2hcrzL2d1La37V0Aoz73ymF8rAcKnohLy93titmv62E0gP8Hrx9PKcKrqCZ1BbLGbP3bEhoXYlw==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "decode-named-character-reference": "^1.0.0", - "micromark-factory-destination": "^1.0.0", - "micromark-factory-label": "^1.0.0", - "micromark-factory-space": "^1.0.0", - "micromark-factory-title": "^1.0.0", - "micromark-factory-whitespace": "^1.0.0", - "micromark-util-character": "^1.0.0", - "micromark-util-chunked": "^1.0.0", - "micromark-util-classify-character": "^1.0.0", - "micromark-util-html-tag-name": "^1.0.0", - "micromark-util-normalize-identifier": "^1.0.0", - "micromark-util-resolve-all": "^1.0.0", - "micromark-util-subtokenize": "^1.0.0", - "micromark-util-symbol": "^1.0.0", - "micromark-util-types": "^1.0.1", - "uvu": "^0.5.0" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/micromark-extension-gfm": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/micromark-extension-gfm/-/micromark-extension-gfm-2.0.3.tgz", - "integrity": "sha512-vb9OoHqrhCmbRidQv/2+Bc6pkP0FrtlhurxZofvOEy5o8RtuuvTq+RQ1Vw5ZDNrVraQZu3HixESqbG+0iKk/MQ==", - "license": "MIT", - "dependencies": { - "micromark-extension-gfm-autolink-literal": "^1.0.0", - "micromark-extension-gfm-footnote": "^1.0.0", - "micromark-extension-gfm-strikethrough": "^1.0.0", - "micromark-extension-gfm-table": "^1.0.0", - "micromark-extension-gfm-tagfilter": "^1.0.0", - "micromark-extension-gfm-task-list-item": "^1.0.0", - "micromark-util-combine-extensions": "^1.0.0", - "micromark-util-types": "^1.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/micromark-extension-gfm-autolink-literal": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/micromark-extension-gfm-autolink-literal/-/micromark-extension-gfm-autolink-literal-1.0.5.tgz", - "integrity": "sha512-z3wJSLrDf8kRDOh2qBtoTRD53vJ+CWIyo7uyZuxf/JAbNJjiHsOpG1y5wxk8drtv3ETAHutCu6N3thkOOgueWg==", - "license": "MIT", - "dependencies": { - "micromark-util-character": "^1.0.0", - "micromark-util-sanitize-uri": "^1.0.0", - "micromark-util-symbol": "^1.0.0", - "micromark-util-types": "^1.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/micromark-extension-gfm-footnote": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/micromark-extension-gfm-footnote/-/micromark-extension-gfm-footnote-1.1.2.tgz", - "integrity": "sha512-Yxn7z7SxgyGWRNa4wzf8AhYYWNrwl5q1Z8ii+CSTTIqVkmGZF1CElX2JI8g5yGoM3GAman9/PVCUFUSJ0kB/8Q==", - "license": "MIT", - "dependencies": { - "micromark-core-commonmark": "^1.0.0", - "micromark-factory-space": "^1.0.0", - "micromark-util-character": "^1.0.0", - "micromark-util-normalize-identifier": "^1.0.0", - "micromark-util-sanitize-uri": "^1.0.0", - "micromark-util-symbol": "^1.0.0", - "micromark-util-types": "^1.0.0", - "uvu": "^0.5.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/micromark-extension-gfm-strikethrough": { - "version": "1.0.7", - "resolved": "https://registry.npmjs.org/micromark-extension-gfm-strikethrough/-/micromark-extension-gfm-strikethrough-1.0.7.tgz", - "integrity": "sha512-sX0FawVE1o3abGk3vRjOH50L5TTLr3b5XMqnP9YDRb34M0v5OoZhG+OHFz1OffZ9dlwgpTBKaT4XW/AsUVnSDw==", - "license": "MIT", - "dependencies": { - "micromark-util-chunked": "^1.0.0", - "micromark-util-classify-character": "^1.0.0", - "micromark-util-resolve-all": "^1.0.0", - "micromark-util-symbol": "^1.0.0", - "micromark-util-types": "^1.0.0", - "uvu": "^0.5.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/micromark-extension-gfm-table": { - "version": "1.0.7", - "resolved": "https://registry.npmjs.org/micromark-extension-gfm-table/-/micromark-extension-gfm-table-1.0.7.tgz", - "integrity": "sha512-3ZORTHtcSnMQEKtAOsBQ9/oHp9096pI/UvdPtN7ehKvrmZZ2+bbWhi0ln+I9drmwXMt5boocn6OlwQzNXeVeqw==", - "license": "MIT", - "dependencies": { - "micromark-factory-space": "^1.0.0", - "micromark-util-character": "^1.0.0", - "micromark-util-symbol": "^1.0.0", - "micromark-util-types": "^1.0.0", - "uvu": "^0.5.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/micromark-extension-gfm-tagfilter": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/micromark-extension-gfm-tagfilter/-/micromark-extension-gfm-tagfilter-1.0.2.tgz", - "integrity": "sha512-5XWB9GbAUSHTn8VPU8/1DBXMuKYT5uOgEjJb8gN3mW0PNW5OPHpSdojoqf+iq1xo7vWzw/P8bAHY0n6ijpXF7g==", - "license": "MIT", - "dependencies": { - "micromark-util-types": "^1.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/micromark-extension-gfm-task-list-item": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/micromark-extension-gfm-task-list-item/-/micromark-extension-gfm-task-list-item-1.0.5.tgz", - "integrity": "sha512-RMFXl2uQ0pNQy6Lun2YBYT9g9INXtWJULgbt01D/x8/6yJ2qpKyzdZD3pi6UIkzF++Da49xAelVKUeUMqd5eIQ==", - "license": "MIT", - "dependencies": { - "micromark-factory-space": "^1.0.0", - "micromark-util-character": "^1.0.0", - "micromark-util-symbol": "^1.0.0", - "micromark-util-types": "^1.0.0", - "uvu": "^0.5.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/micromark-factory-destination": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/micromark-factory-destination/-/micromark-factory-destination-1.1.0.tgz", - "integrity": "sha512-XaNDROBgx9SgSChd69pjiGKbV+nfHGDPVYFs5dOoDd7ZnMAE+Cuu91BCpsY8RT2NP9vo/B8pds2VQNCLiu0zhg==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-character": "^1.0.0", - "micromark-util-symbol": "^1.0.0", - "micromark-util-types": "^1.0.0" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/micromark-factory-label": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/micromark-factory-label/-/micromark-factory-label-1.1.0.tgz", - "integrity": "sha512-OLtyez4vZo/1NjxGhcpDSbHQ+m0IIGnT8BoPamh+7jVlzLJBH98zzuCoUeMxvM6WsNeh8wx8cKvqLiPHEACn0w==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-character": "^1.0.0", - "micromark-util-symbol": "^1.0.0", - "micromark-util-types": "^1.0.0", - "uvu": "^0.5.0" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/micromark-factory-title": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/micromark-factory-title/-/micromark-factory-title-1.1.0.tgz", - "integrity": "sha512-J7n9R3vMmgjDOCY8NPw55jiyaQnH5kBdV2/UXCtZIpnHH3P6nHUKaH7XXEYuWwx/xUJcawa8plLBEjMPU24HzQ==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-factory-space": "^1.0.0", - "micromark-util-character": "^1.0.0", - "micromark-util-symbol": "^1.0.0", - "micromark-util-types": "^1.0.0" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/micromark-factory-whitespace": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/micromark-factory-whitespace/-/micromark-factory-whitespace-1.1.0.tgz", - "integrity": "sha512-v2WlmiymVSp5oMg+1Q0N1Lxmt6pMhIHD457whWM7/GUlEks1hI9xj5w3zbc4uuMKXGisksZk8DzP2UyGbGqNsQ==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-factory-space": "^1.0.0", - "micromark-util-character": "^1.0.0", - "micromark-util-symbol": "^1.0.0", - "micromark-util-types": "^1.0.0" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/micromark-util-chunked": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/micromark-util-chunked/-/micromark-util-chunked-1.1.0.tgz", - "integrity": "sha512-Ye01HXpkZPNcV6FiyoW2fGZDUw4Yc7vT0E9Sad83+bEDiCJ1uXu0S3mr8WLpsz3HaG3x2q0HM6CTuPdcZcluFQ==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-symbol": "^1.0.0" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/micromark-util-classify-character": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/micromark-util-classify-character/-/micromark-util-classify-character-1.1.0.tgz", - "integrity": "sha512-SL0wLxtKSnklKSUplok1WQFoGhUdWYKggKUiqhX+Swala+BtptGCu5iPRc+xvzJ4PXE/hwM3FNXsfEVgoZsWbw==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-character": "^1.0.0", - "micromark-util-symbol": "^1.0.0", - "micromark-util-types": "^1.0.0" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/micromark-util-combine-extensions": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/micromark-util-combine-extensions/-/micromark-util-combine-extensions-1.1.0.tgz", - "integrity": "sha512-Q20sp4mfNf9yEqDL50WwuWZHUrCO4fEyeDCnMGmG5Pr0Cz15Uo7KBs6jq+dq0EgX4DPwwrh9m0X+zPV1ypFvUA==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-chunked": "^1.0.0", - "micromark-util-types": "^1.0.0" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/micromark-util-decode-numeric-character-reference": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/micromark-util-decode-numeric-character-reference/-/micromark-util-decode-numeric-character-reference-1.1.0.tgz", - "integrity": "sha512-m9V0ExGv0jB1OT21mrWcuf4QhP46pH1KkfWy9ZEezqHKAxkj4mPCy3nIH1rkbdMlChLHX531eOrymlwyZIf2iw==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-symbol": "^1.0.0" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/micromark-util-decode-string": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/micromark-util-decode-string/-/micromark-util-decode-string-1.1.0.tgz", - "integrity": "sha512-YphLGCK8gM1tG1bd54azwyrQRjCFcmgj2S2GoJDNnh4vYtnL38JS8M4gpxzOPNyHdNEpheyWXCTnnTDY3N+NVQ==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "decode-named-character-reference": "^1.0.0", - "micromark-util-character": "^1.0.0", - "micromark-util-decode-numeric-character-reference": "^1.0.0", - "micromark-util-symbol": "^1.0.0" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/micromark-util-encode": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/micromark-util-encode/-/micromark-util-encode-1.1.0.tgz", - "integrity": "sha512-EuEzTWSTAj9PA5GOAs992GzNh2dGQO52UvAbtSOMvXTxv3Criqb6IOzJUBCmEqrrXSblJIJBbFFv6zPxpreiJw==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT" - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/micromark-util-html-tag-name": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/micromark-util-html-tag-name/-/micromark-util-html-tag-name-1.2.0.tgz", - "integrity": "sha512-VTQzcuQgFUD7yYztuQFKXT49KghjtETQ+Wv/zUjGSGBioZnkA4P1XXZPT1FHeJA6RwRXSF47yvJ1tsJdoxwO+Q==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT" - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/micromark-util-normalize-identifier": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/micromark-util-normalize-identifier/-/micromark-util-normalize-identifier-1.1.0.tgz", - "integrity": "sha512-N+w5vhqrBihhjdpM8+5Xsxy71QWqGn7HYNUvch71iV2PM7+E3uWGox1Qp90loa1ephtCxG2ftRV/Conitc6P2Q==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-symbol": "^1.0.0" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/micromark-util-resolve-all": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/micromark-util-resolve-all/-/micromark-util-resolve-all-1.1.0.tgz", - "integrity": "sha512-b/G6BTMSg+bX+xVCshPTPyAu2tmA0E4X98NSR7eIbeC6ycCqCeE7wjfDIgzEbkzdEVJXRtOG4FbEm/uGbCRouA==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-types": "^1.0.0" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/micromark-util-sanitize-uri": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/micromark-util-sanitize-uri/-/micromark-util-sanitize-uri-1.2.0.tgz", - "integrity": "sha512-QO4GXv0XZfWey4pYFndLUKEAktKkG5kZTdUNaTAkzbuJxn2tNBOr+QtxR2XpWaMhbImT2dPzyLrPXLlPhph34A==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-character": "^1.0.0", - "micromark-util-encode": "^1.0.0", - "micromark-util-symbol": "^1.0.0" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/micromark-util-subtokenize": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/micromark-util-subtokenize/-/micromark-util-subtokenize-1.1.0.tgz", - "integrity": "sha512-kUQHyzRoxvZO2PuLzMt2P/dwVsTiivCK8icYTeR+3WgbuPqfHgPPy7nFKbeqRivBvn/3N3GBiNC+JRTMSxEC7A==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-chunked": "^1.0.0", - "micromark-util-symbol": "^1.0.0", - "micromark-util-types": "^1.0.0", - "uvu": "^0.5.0" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/micromark-util-types": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/micromark-util-types/-/micromark-util-types-1.1.0.tgz", - "integrity": "sha512-ukRBgie8TIAcacscVHSiddHjO4k/q3pnedmzMQ4iwDcK0FtFCohKOlFbaOL/mPgfnPsL3C1ZyxJa4sbWrBl3jg==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT" - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/parse5": { - "version": "6.0.1", - "resolved": "https://registry.npmjs.org/parse5/-/parse5-6.0.1.tgz", - "integrity": "sha512-Ofn/CTFzRGTTxwpNEs9PP93gXShHcTq255nzRYSKe8AkVpZY7e1fpmTfOyoIvjP5HG7Z2ZM7VS9PPhQGW2pOpw==", - "license": "MIT" - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/rehype-raw": { - "version": "6.1.1", - "resolved": "https://registry.npmjs.org/rehype-raw/-/rehype-raw-6.1.1.tgz", - "integrity": "sha512-d6AKtisSRtDRX4aSPsJGTfnzrX2ZkHQLE5kiUuGOeEoLpbEulFF4hj0mLPbsa+7vmguDKOVVEQdHKDSwoaIDsQ==", - "license": "MIT", - "dependencies": { - "@types/hast": "^2.0.0", - "hast-util-raw": "^7.2.0", - "unified": "^10.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/remark-gfm": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/remark-gfm/-/remark-gfm-3.0.1.tgz", - "integrity": "sha512-lEFDoi2PICJyNrACFOfDD3JlLkuSbOa5Wd8EPt06HUdptv8Gn0bxYTdbU/XXQ3swAPkEaGxxPN9cbnMHvVu1Ig==", - "license": "MIT", - "dependencies": { - "@types/mdast": "^3.0.0", - "mdast-util-gfm": "^2.0.0", - "micromark-extension-gfm": "^2.0.0", - "unified": "^10.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/sass-loader": { - "version": "16.0.3", - "resolved": "https://registry.npmjs.org/sass-loader/-/sass-loader-16.0.3.tgz", - "integrity": "sha512-gosNorT1RCkuCMyihv6FBRR7BMV06oKRAs+l4UMp1mlcVg9rWN6KMmUj3igjQwmYys4mDP3etEYJgiHRbgHCHA==", - "license": "MIT", - "dependencies": { - "neo-async": "^2.6.2" - }, - "engines": { - "node": ">= 18.12.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/webpack" - }, - "peerDependencies": { - "@rspack/core": "0.x || 1.x", - "node-sass": "^4.0.0 || ^5.0.0 || ^6.0.0 || ^7.0.0 || ^8.0.0 || ^9.0.0", - "sass": "^1.3.0", - "sass-embedded": "*", - "webpack": "^5.0.0" - }, - "peerDependenciesMeta": { - "@rspack/core": { - "optional": true - }, - "node-sass": { - "optional": true - }, - "sass": { - "optional": true - }, - "sass-embedded": { - "optional": true - }, - "webpack": { - "optional": true - } - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/unified": { - "version": "10.1.2", - "resolved": "https://registry.npmjs.org/unified/-/unified-10.1.2.tgz", - "integrity": "sha512-pUSWAi/RAnVy1Pif2kAoeWNBa3JVrx0MId2LASj8G+7AiHWoKZNTomq6LG326T68U7/e263X6fTdcXIy7XnF7Q==", - "license": "MIT", - "dependencies": { - "@types/unist": "^2.0.0", - "bail": "^2.0.0", - "extend": "^3.0.0", - "is-buffer": "^2.0.0", - "is-plain-obj": "^4.0.0", - "trough": "^2.0.0", - "vfile": "^5.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/unist-util-is": { - "version": "5.2.1", - "resolved": "https://registry.npmjs.org/unist-util-is/-/unist-util-is-5.2.1.tgz", - "integrity": "sha512-u9njyyfEh43npf1M+yGKDGVPbY/JWEemg5nH05ncKPfi+kBbKBJoTdsogMu33uhytuLlv9y0O7GH7fEdwLdLQw==", - "license": "MIT", - "dependencies": { - "@types/unist": "^2.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/unist-util-position": { - "version": "4.0.4", - "resolved": "https://registry.npmjs.org/unist-util-position/-/unist-util-position-4.0.4.tgz", - "integrity": "sha512-kUBE91efOWfIVBo8xzh/uZQ7p9ffYRtUbMRZBNFYwf0RK8koUMx6dGUfwylLOKmaT2cs4wSW96QoYUSXAyEtpg==", - "license": "MIT", - "dependencies": { - "@types/unist": "^2.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/unist-util-stringify-position": { - "version": "3.0.3", - "resolved": "https://registry.npmjs.org/unist-util-stringify-position/-/unist-util-stringify-position-3.0.3.tgz", - "integrity": "sha512-k5GzIBZ/QatR8N5X2y+drfpWG8IDBzdnVj6OInRNWm1oXrzydiaAT2OQiA8DPRRZyAKb9b6I2a6PxYklZD0gKg==", - "license": "MIT", - "dependencies": { - "@types/unist": "^2.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/unist-util-visit": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/unist-util-visit/-/unist-util-visit-4.1.2.tgz", - "integrity": "sha512-MSd8OUGISqHdVvfY9TPhyK2VdUrPgxkUtWSuMHF6XAAFuL4LokseigBnZtPnJMu+FbynTkFNnFlyjxpVKujMRg==", - "license": "MIT", - "dependencies": { - "@types/unist": "^2.0.0", - "unist-util-is": "^5.0.0", - "unist-util-visit-parents": "^5.1.1" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/unist-util-visit-parents": { - "version": "5.1.3", - "resolved": "https://registry.npmjs.org/unist-util-visit-parents/-/unist-util-visit-parents-5.1.3.tgz", - "integrity": "sha512-x6+y8g7wWMyQhL1iZfhIPhDAs7Xwbn9nRosDXl7qoPTSCy0yNxnKc+hWokFifWQIDGi154rdUqKvbCa4+1kLhg==", - "license": "MIT", - "dependencies": { - "@types/unist": "^2.0.0", - "unist-util-is": "^5.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/vfile": { - "version": "5.3.7", - "resolved": "https://registry.npmjs.org/vfile/-/vfile-5.3.7.tgz", - "integrity": "sha512-r7qlzkgErKjobAmyNIkkSpizsFPYiUPuJb5pNW1RB4JcYVZhs4lIbVqk8XPk033CV/1z8ss5pkax8SuhGpcG8g==", - "license": "MIT", - "dependencies": { - "@types/unist": "^2.0.0", - "is-buffer": "^2.0.0", - "unist-util-stringify-position": "^3.0.0", - "vfile-message": "^3.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/vfile-location": { - "version": "4.1.0", - "resolved": "https://registry.npmjs.org/vfile-location/-/vfile-location-4.1.0.tgz", - "integrity": "sha512-YF23YMyASIIJXpktBa4vIGLJ5Gs88UB/XePgqPmTa7cDA+JeO3yclbpheQYCHjVHBn/yePzrXuygIL+xbvRYHw==", - "license": "MIT", - "dependencies": { - "@types/unist": "^2.0.0", - "vfile": "^5.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/docusaurus-theme-openapi-docs/node_modules/vfile-message": { - "version": "3.1.4", - "resolved": "https://registry.npmjs.org/vfile-message/-/vfile-message-3.1.4.tgz", - "integrity": "sha512-fa0Z6P8HUrQN4BZaX05SIVXic+7kE3b05PWAtPuYP9QLHsLKYR7/AlLW3NtOrpXRLeawpDLMsVkmk5DG0NXgWw==", - "license": "MIT", - "dependencies": { - "@types/unist": "^2.0.0", - "unist-util-stringify-position": "^3.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/dom-converter": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/dom-converter/-/dom-converter-0.2.0.tgz", - "integrity": "sha512-gd3ypIPfOMr9h5jIKq8E3sHOTCjeirnl0WK5ZdS1AW0Odt0b1PaWaHdJ4Qk4klv+YB9aJBS7mESXjFoDQPu6DA==", - "license": "MIT", - "dependencies": { - "utila": "~0.4" - } - }, - "node_modules/dom-serializer": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/dom-serializer/-/dom-serializer-2.0.0.tgz", - "integrity": "sha512-wIkAryiqt/nV5EQKqQpo3SToSOV9J0DnbJqwK7Wv/Trc92zIAYZ4FlMu+JPFW1DfGFt81ZTCGgDEabffXeLyJg==", - "license": "MIT", - "dependencies": { - "domelementtype": "^2.3.0", - "domhandler": "^5.0.2", - "entities": "^4.2.0" - }, - "funding": { - "url": "https://github.com/cheeriojs/dom-serializer?sponsor=1" - } - }, - "node_modules/domain-browser": { - "version": "4.23.0", - "resolved": "https://registry.npmjs.org/domain-browser/-/domain-browser-4.23.0.tgz", - "integrity": "sha512-ArzcM/II1wCCujdCNyQjXrAFwS4mrLh4C7DZWlaI8mdh7h3BfKdNd3bKXITfl2PT9FtfQqaGvhi1vPRQPimjGA==", - "license": "Artistic-2.0", - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://bevry.me/fund" - } - }, - "node_modules/domelementtype": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/domelementtype/-/domelementtype-2.3.0.tgz", - "integrity": "sha512-OLETBj6w0OsagBwdXnPdN0cnMfF9opN69co+7ZrbfPGrdpPVNBUj02spi6B1N7wChLQiPn4CSH/zJvXw56gmHw==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/fb55" - } - ], - "license": "BSD-2-Clause" - }, - "node_modules/domhandler": { - "version": "5.0.3", - "resolved": "https://registry.npmjs.org/domhandler/-/domhandler-5.0.3.tgz", - "integrity": "sha512-cgwlv/1iFQiFnU96XXgROh8xTeetsnJiDsTc7TYCLFd9+/WNkIqPTxiM/8pSd8VIrhXGTf1Ny1q1hquVqDJB5w==", - "license": "BSD-2-Clause", - "dependencies": { - "domelementtype": "^2.3.0" - }, - "engines": { - "node": ">= 4" - }, - "funding": { - "url": "https://github.com/fb55/domhandler?sponsor=1" - } - }, - "node_modules/domutils": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/domutils/-/domutils-3.1.0.tgz", - "integrity": "sha512-H78uMmQtI2AhgDJjWeQmHwJJ2bLPD3GMmO7Zja/ZZh84wkm+4ut+IUnUdRa8uCGX88DiVx1j6FRe1XfxEgjEZA==", - "license": "BSD-2-Clause", - "dependencies": { - "dom-serializer": "^2.0.0", - "domelementtype": "^2.3.0", - "domhandler": "^5.0.3" - }, - "funding": { - "url": "https://github.com/fb55/domutils?sponsor=1" - } - }, - "node_modules/dot-case": { - "version": "3.0.4", - "resolved": "https://registry.npmjs.org/dot-case/-/dot-case-3.0.4.tgz", - "integrity": "sha512-Kv5nKlh6yRrdrGvxeJ2e5y2eRUpkUosIW4A2AS38zwSz27zu7ufDwQPi5Jhs3XAlGNetl3bmnGhQsMtkKJnj3w==", - "license": "MIT", - "dependencies": { - "no-case": "^3.0.4", - "tslib": "^2.0.3" - } - }, - "node_modules/dot-prop": { - "version": "6.0.1", - "resolved": "https://registry.npmjs.org/dot-prop/-/dot-prop-6.0.1.tgz", - "integrity": "sha512-tE7ztYzXHIeyvc7N+hR3oi7FIbf/NIjVP9hmAt3yMXzrQ072/fpjGLx2GxNxGxUl5V73MEqYzioOMoVhGMJ5cA==", - "license": "MIT", - "dependencies": { - "is-obj": "^2.0.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/dot-prop/node_modules/is-obj": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/is-obj/-/is-obj-2.0.0.tgz", - "integrity": "sha512-drqDG3cbczxxEJRoOXcOjtdp1J/lyp1mNn0xaznRs8+muBhgQcrnbspox5X5fOw0HnMnbfDzvnEMEtqDEJEo8w==", - "license": "MIT", - "engines": { - "node": ">=8" - } - }, - "node_modules/dotenv": { - "version": "16.4.5", - "resolved": "https://registry.npmjs.org/dotenv/-/dotenv-16.4.5.tgz", - "integrity": "sha512-ZmdL2rui+eB2YwhsWzjInR8LldtZHGDoQ1ugH85ppHKwpUHL7j7rN0Ti9NCnGiQbhaZ11FpR+7ao1dNsmduNUg==", - "dev": true, - "license": "BSD-2-Clause", - "engines": { - "node": ">=12" - }, - "funding": { - "url": "https://dotenvx.com" - } - }, - "node_modules/dset": { - "version": "3.1.4", - "resolved": "https://registry.npmjs.org/dset/-/dset-3.1.4.tgz", - "integrity": "sha512-2QF/g9/zTaPDc3BjNcVTGoBbXBgYfMTTceLaYcFJ/W9kggFUkhxD/hMEeuLKbugyef9SqAx8cpgwlIP/jinUTA==", - "license": "MIT", - "engines": { - "node": ">=4" - } - }, - "node_modules/duplexer": { - "version": "0.1.2", - "resolved": "https://registry.npmjs.org/duplexer/-/duplexer-0.1.2.tgz", - "integrity": "sha512-jtD6YG370ZCIi/9GTaJKQxWTZD045+4R4hTk/x1UyoqadyJ9x9CgSi1RlVDQF8U2sxLLSnFkCaMihqljHIWgMg==", - "license": "MIT" - }, - "node_modules/eastasianwidth": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/eastasianwidth/-/eastasianwidth-0.2.0.tgz", - "integrity": "sha512-I88TYZWc9XiYHRQ4/3c5rjjfgkjhLyW2luGIheGERbNQ6OY7yTybanSpDXZa8y7VUP9YmDcYa+eyq4ca7iLqWA==", - "license": "MIT" - }, - "node_modules/ee-first": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/ee-first/-/ee-first-1.1.1.tgz", - "integrity": "sha512-WMwm9LhRUo+WUaRN+vRuETqG89IgZphVSNkdFgeb6sS/E4OrDIN7t48CAewSHXc6C8lefD8KKfr5vY61brQlow==" - }, - "node_modules/electron-to-chromium": { - "version": "1.5.62", - "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.5.62.tgz", - "integrity": "sha512-t8c+zLmJHa9dJy96yBZRXGQYoiCEnHYgFwn1asvSPZSUdVxnB62A4RASd7k41ytG3ErFBA0TpHlKg9D9SQBmLg==", - "license": "ISC" - }, - "node_modules/elliptic": { - "version": "6.6.1", - "resolved": "https://registry.npmjs.org/elliptic/-/elliptic-6.6.1.tgz", - "integrity": "sha512-RaddvvMatK2LJHqFJ+YA4WysVN5Ita9E35botqIYspQ4TkRAlCicdzKOjlyv/1Za5RyTNn7di//eEV0uTAfe3g==", - "license": "MIT", - "dependencies": { - "bn.js": "^4.11.9", - "brorand": "^1.1.0", - "hash.js": "^1.0.0", - "hmac-drbg": "^1.0.1", - "inherits": "^2.0.4", - "minimalistic-assert": "^1.0.1", - "minimalistic-crypto-utils": "^1.0.1" - } - }, - "node_modules/elliptic/node_modules/bn.js": { - "version": "4.12.0", - "resolved": "https://registry.npmjs.org/bn.js/-/bn.js-4.12.0.tgz", - "integrity": "sha512-c98Bf3tPniI+scsdk237ku1Dc3ujXQTSgyiPUDEOe7tRkhrqridvh8klBv0HCEso1OLOYcHuCv/cS6DNxKH+ZA==", - "license": "MIT" - }, - "node_modules/emoji-regex": { - "version": "9.2.2", - "resolved": "https://registry.npmjs.org/emoji-regex/-/emoji-regex-9.2.2.tgz", - "integrity": "sha512-L18DaJsXSUk2+42pv8mLs5jJT2hqFkFE4j21wOmgbUqsZ2hL72NsUU785g9RXgo3s0ZNgVl42TiHp3ZtOv/Vyg==", - "license": "MIT" - }, - "node_modules/emojilib": { - "version": "2.4.0", - "resolved": "https://registry.npmjs.org/emojilib/-/emojilib-2.4.0.tgz", - "integrity": "sha512-5U0rVMU5Y2n2+ykNLQqMoqklN9ICBT/KsvC1Gz6vqHbz2AXXGkG+Pm5rMWk/8Vjrr/mY9985Hi8DYzn1F09Nyw==", - "license": "MIT" - }, - "node_modules/emojis-list": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/emojis-list/-/emojis-list-3.0.0.tgz", - "integrity": "sha512-/kyM18EfinwXZbno9FyUGeFh87KC8HRQBQGildHZbEuRyWFOmv1U10o9BBp8XVZDVNNuQKyIGIu5ZYAAXJ0V2Q==", - "license": "MIT", - "engines": { - "node": ">= 4" - } - }, - "node_modules/emoticon": { - "version": "4.1.0", - "resolved": "https://registry.npmjs.org/emoticon/-/emoticon-4.1.0.tgz", - "integrity": "sha512-VWZfnxqwNcc51hIy/sbOdEem6D+cVtpPzEEtVAFdaas30+1dgkyaOQ4sQ6Bp0tOMqWO1v+HQfYaoodOkdhK6SQ==", - "license": "MIT", - "funding": { - "type": "github", - "url": "https://github.com/sponsors/wooorm" - } - }, - "node_modules/encodeurl": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/encodeurl/-/encodeurl-2.0.0.tgz", - "integrity": "sha512-Q0n9HRi4m6JuGIV1eFlmvJB7ZEVxu93IrMyiMsGC0lrMJMWzRgx6WGquyfQgZVb31vhGgXnfmPNNXmxnOkRBrg==", - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/encoding-sniffer": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/encoding-sniffer/-/encoding-sniffer-0.2.0.tgz", - "integrity": "sha512-ju7Wq1kg04I3HtiYIOrUrdfdDvkyO9s5XM8QAj/bN61Yo/Vb4vgJxy5vi4Yxk01gWHbrofpPtpxM8bKger9jhg==", - "license": "MIT", - "dependencies": { - "iconv-lite": "^0.6.3", - "whatwg-encoding": "^3.1.1" - }, - "funding": { - "url": "https://github.com/fb55/encoding-sniffer?sponsor=1" - } - }, - "node_modules/encoding-sniffer/node_modules/iconv-lite": { - "version": "0.6.3", - "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.6.3.tgz", - "integrity": "sha512-4fCk79wshMdzMp2rH06qWrJE4iolqLhCUH+OiuIgU++RB0+94NlDL81atO7GX55uUKueo0txHNtvEyI6D7WdMw==", - "license": "MIT", - "dependencies": { - "safer-buffer": ">= 2.1.2 < 3.0.0" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/enhanced-resolve": { - "version": "5.17.1", - "resolved": "https://registry.npmjs.org/enhanced-resolve/-/enhanced-resolve-5.17.1.tgz", - "integrity": "sha512-LMHl3dXhTcfv8gM4kEzIUeTQ+7fpdA0l2tUf34BddXPkz2A5xJ5L/Pchd5BL6rdccM9QGvu0sWZzK1Z1t4wwyg==", - "license": "MIT", - "dependencies": { - "graceful-fs": "^4.2.4", - "tapable": "^2.2.0" - }, - "engines": { - "node": ">=10.13.0" - } - }, - "node_modules/entities": { - "version": "4.5.0", - "resolved": "https://registry.npmjs.org/entities/-/entities-4.5.0.tgz", - "integrity": "sha512-V0hjH4dGPh9Ao5p0MoRY6BVqtwCjhz6vI5LT8AJ55H+4g9/4vbHx1I54fS0XuclLhDHArPQCiMjDxjaL8fPxhw==", - "license": "BSD-2-Clause", - "engines": { - "node": ">=0.12" - }, - "funding": { - "url": "https://github.com/fb55/entities?sponsor=1" - } - }, - "node_modules/error-ex": { - "version": "1.3.2", - "resolved": "https://registry.npmjs.org/error-ex/-/error-ex-1.3.2.tgz", - "integrity": "sha512-7dFHNmqeFSEt2ZBsCriorKnn3Z2pj+fd9kmI6QoWw4//DL+icEBfc0U7qJCisqrTsKTjw4fNFy2pW9OqStD84g==", - "license": "MIT", - "dependencies": { - "is-arrayish": "^0.2.1" - } - }, - "node_modules/es-define-property": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/es-define-property/-/es-define-property-1.0.0.tgz", - "integrity": "sha512-jxayLKShrEqqzJ0eumQbVhTYQM27CfT1T35+gCgDFoL82JLsXqTJ76zv6A0YLOgEnLUMvLzsDsGIrl8NFpT2gQ==", - "license": "MIT", - "dependencies": { - "get-intrinsic": "^1.2.4" - }, - "engines": { - "node": ">= 0.4" - } - }, - "node_modules/es-errors": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/es-errors/-/es-errors-1.3.0.tgz", - "integrity": "sha512-Zf5H2Kxt2xjTvbJvP2ZWLEICxA6j+hAmMzIlypy4xcBg1vKVnx89Wy0GbS+kf5cwCVFFzdCFh2XSCFNULS6csw==", - "license": "MIT", - "engines": { - "node": ">= 0.4" - } - }, - "node_modules/es-module-lexer": { - "version": "1.5.4", - "resolved": "https://registry.npmjs.org/es-module-lexer/-/es-module-lexer-1.5.4.tgz", - "integrity": "sha512-MVNK56NiMrOwitFB7cqDwq0CQutbw+0BvLshJSse0MUNU+y1FC3bUS/AQg7oUng+/wKrrki7JfmwtVHkVfPLlw==", - "license": "MIT" - }, - "node_modules/es6-promise": { - "version": "3.3.1", - "resolved": "https://registry.npmjs.org/es6-promise/-/es6-promise-3.3.1.tgz", - "integrity": "sha512-SOp9Phqvqn7jtEUxPWdWfWoLmyt2VaJ6MpvP9Comy1MceMXqE6bxvaTu4iaxpYYPzhny28Lc+M87/c2cPK6lDg==", - "license": "MIT" - }, - "node_modules/escalade": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/escalade/-/escalade-3.2.0.tgz", - "integrity": "sha512-WUj2qlxaQtO4g6Pq5c29GTcWGDyd8itL8zTlipgECz3JesAiiOKotd8JU6otB3PACgG6xkJUyVhboMS+bje/jA==", - "license": "MIT", - "engines": { - "node": ">=6" - } - }, - "node_modules/escape-goat": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/escape-goat/-/escape-goat-4.0.0.tgz", - "integrity": "sha512-2Sd4ShcWxbx6OY1IHyla/CVNwvg7XwZVoXZHcSu9w9SReNP1EzzD5T8NWKIR38fIqEns9kDWKUQTXXAmlDrdPg==", - "license": "MIT", - "engines": { - "node": ">=12" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/escape-html": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/escape-html/-/escape-html-1.0.3.tgz", - "integrity": "sha512-NiSupZ4OeuGwr68lGIeym/ksIZMJodUGOSCZ/FSnTxcrekbvqrgdUxlJOMpijaKZVjAJrWrGs/6Jy8OMuyj9ow==", - "license": "MIT" - }, - "node_modules/escape-string-regexp": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-4.0.0.tgz", - "integrity": "sha512-TtpcNJ3XAzx3Gq8sWRzJaVajRs0uVxA2YAkdb1jm2YkPz4G6egUFAyA3n5vtEIZefPk5Wa4UXbKuS5fKkJWdgA==", - "license": "MIT", - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/eslint-scope": { - "version": "5.1.1", - "resolved": "https://registry.npmjs.org/eslint-scope/-/eslint-scope-5.1.1.tgz", - "integrity": "sha512-2NxwbF/hZ0KpepYN0cNbo+FN6XoK7GaHlQhgx/hIZl6Va0bF45RQOOwhLIy8lQDbuCiadSLCBnH2CFYquit5bw==", - "license": "BSD-2-Clause", - "dependencies": { - "esrecurse": "^4.3.0", - "estraverse": "^4.1.1" - }, - "engines": { - "node": ">=8.0.0" - } - }, - "node_modules/esprima": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/esprima/-/esprima-4.0.1.tgz", - "integrity": "sha512-eGuFFw7Upda+g4p+QHvnW0RyTX/SVeJBDM/gCtMARO0cLuT2HcEKnTPvhjV6aGeqrCB/sbNop0Kszm0jsaWU4A==", - "license": "BSD-2-Clause", - "bin": { - "esparse": "bin/esparse.js", - "esvalidate": "bin/esvalidate.js" - }, - "engines": { - "node": ">=4" - } - }, - "node_modules/esrecurse": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/esrecurse/-/esrecurse-4.3.0.tgz", - "integrity": "sha512-KmfKL3b6G+RXvP8N1vr3Tq1kL/oCFgn2NYXEtqP8/L3pKapUA4G8cFVaoF3SU323CD4XypR/ffioHmkti6/Tag==", - "license": "BSD-2-Clause", - "dependencies": { - "estraverse": "^5.2.0" - }, - "engines": { - "node": ">=4.0" - } - }, - "node_modules/esrecurse/node_modules/estraverse": { - "version": "5.3.0", - "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-5.3.0.tgz", - "integrity": "sha512-MMdARuVEQziNTeJD8DgMqmhwR11BRQ/cBP+pLtYdSTnf3MIO8fFeiINEbX36ZdNlfU/7A9f3gUw49B3oQsvwBA==", - "license": "BSD-2-Clause", - "engines": { - "node": ">=4.0" - } - }, - "node_modules/estraverse": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-4.3.0.tgz", - "integrity": "sha512-39nnKffWz8xN1BU/2c79n9nB9HDzo0niYUqx6xyqUnyoAnQyyWpOTdZEeiCch8BBu515t4wp9ZmgVfVhn9EBpw==", - "license": "BSD-2-Clause", - "engines": { - "node": ">=4.0" - } - }, - "node_modules/estree-util-attach-comments": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/estree-util-attach-comments/-/estree-util-attach-comments-3.0.0.tgz", - "integrity": "sha512-cKUwm/HUcTDsYh/9FgnuFqpfquUbwIqwKM26BVCGDPVgvaCl/nDCCjUfiLlx6lsEZ3Z4RFxNbOQ60pkaEwFxGw==", - "license": "MIT", - "dependencies": { - "@types/estree": "^1.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/estree-util-build-jsx": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/estree-util-build-jsx/-/estree-util-build-jsx-3.0.1.tgz", - "integrity": "sha512-8U5eiL6BTrPxp/CHbs2yMgP8ftMhR5ww1eIKoWRMlqvltHF8fZn5LRDvTKuxD3DUn+shRbLGqXemcP51oFCsGQ==", - "license": "MIT", - "dependencies": { - "@types/estree-jsx": "^1.0.0", - "devlop": "^1.0.0", - "estree-util-is-identifier-name": "^3.0.0", - "estree-walker": "^3.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/estree-util-is-identifier-name": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/estree-util-is-identifier-name/-/estree-util-is-identifier-name-3.0.0.tgz", - "integrity": "sha512-hFtqIDZTIUZ9BXLb8y4pYGyk6+wekIivNVTcmvk8NoOh+VeRn5y6cEHzbURrWbfp1fIqdVipilzj+lfaadNZmg==", - "license": "MIT", - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/estree-util-to-js": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/estree-util-to-js/-/estree-util-to-js-2.0.0.tgz", - "integrity": "sha512-WDF+xj5rRWmD5tj6bIqRi6CkLIXbbNQUcxQHzGysQzvHmdYG2G7p/Tf0J0gpxGgkeMZNTIjT/AoSvC9Xehcgdg==", - "license": "MIT", - "dependencies": { - "@types/estree-jsx": "^1.0.0", - "astring": "^1.8.0", - "source-map": "^0.7.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/estree-util-value-to-estree": { - "version": "3.2.1", - "resolved": "https://registry.npmjs.org/estree-util-value-to-estree/-/estree-util-value-to-estree-3.2.1.tgz", - "integrity": "sha512-Vt2UOjyPbNQQgT5eJh+K5aATti0OjCIAGc9SgMdOFYbohuifsWclR74l0iZTJwePMgWYdX1hlVS+dedH9XV8kw==", - "license": "MIT", - "dependencies": { - "@types/estree": "^1.0.0" - }, - "funding": { - "url": "https://github.com/sponsors/remcohaszing" - } - }, - "node_modules/estree-util-visit": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/estree-util-visit/-/estree-util-visit-2.0.0.tgz", - "integrity": "sha512-m5KgiH85xAhhW8Wta0vShLcUvOsh3LLPI2YVwcbio1l7E09NTLL1EyMZFM1OyWowoH0skScNbhOPl4kcBgzTww==", - "license": "MIT", - "dependencies": { - "@types/estree-jsx": "^1.0.0", - "@types/unist": "^3.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/estree-walker": { - "version": "3.0.3", - "resolved": "https://registry.npmjs.org/estree-walker/-/estree-walker-3.0.3.tgz", - "integrity": "sha512-7RUKfXgSMMkzt6ZuXmqapOurLGPPfgj6l9uRZ7lRGolvk0y2yocc35LdcxKC5PQZdn2DMqioAQ2NoWcrTKmm6g==", - "license": "MIT", - "dependencies": { - "@types/estree": "^1.0.0" - } - }, - "node_modules/esutils": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/esutils/-/esutils-2.0.3.tgz", - "integrity": "sha512-kVscqXk4OCp68SZ0dkgEKVi6/8ij300KBWTJq32P/dYeWTSwK41WyTxalN1eRmA5Z9UU/LX9D7FWSmV9SAYx6g==", - "license": "BSD-2-Clause", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/eta": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/eta/-/eta-2.2.0.tgz", - "integrity": "sha512-UVQ72Rqjy/ZKQalzV5dCCJP80GrmPrMxh6NlNf+erV6ObL0ZFkhCstWRawS85z3smdr3d2wXPsZEY7rDPfGd2g==", - "license": "MIT", - "engines": { - "node": ">=6.0.0" - }, - "funding": { - "url": "https://github.com/eta-dev/eta?sponsor=1" - } - }, - "node_modules/etag": { - "version": "1.8.1", - "resolved": "https://registry.npmjs.org/etag/-/etag-1.8.1.tgz", - "integrity": "sha512-aIL5Fx7mawVa300al2BnEE4iNvo1qETxLrPI/o05L7z6go7fCw1J6EQmbK4FmJ2AS7kgVF/KEZWufBfdClMcPg==", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/eval": { - "version": "0.1.8", - "resolved": "https://registry.npmjs.org/eval/-/eval-0.1.8.tgz", - "integrity": "sha512-EzV94NYKoO09GLXGjXj9JIlXijVck4ONSr5wiCWDvhsvj5jxSrzTmRU/9C1DyB6uToszLs8aifA6NQ7lEQdvFw==", - "dependencies": { - "@types/node": "*", - "require-like": ">= 0.1.1" - }, - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/event-target-shim": { - "version": "5.0.1", - "resolved": "https://registry.npmjs.org/event-target-shim/-/event-target-shim-5.0.1.tgz", - "integrity": "sha512-i/2XbnSz/uxRCU6+NdVJgKWDTM427+MqYbkQzD321DuCQJUqOuJKIA0IM2+W2xtYHdKOmZ4dR6fExsd4SXL+WQ==", - "license": "MIT", - "engines": { - "node": ">=6" - } - }, - "node_modules/eventemitter3": { - "version": "4.0.7", - "resolved": "https://registry.npmjs.org/eventemitter3/-/eventemitter3-4.0.7.tgz", - "integrity": "sha512-8guHBZCwKnFhYdHr2ysuRWErTwhoN2X8XELRlrRwpmfeY2jjuUN4taQMsULKUVo1K4DvZl+0pgfyoysHxvmvEw==", - "license": "MIT" - }, - "node_modules/events": { - "version": "3.3.0", - "resolved": "https://registry.npmjs.org/events/-/events-3.3.0.tgz", - "integrity": "sha512-mQw+2fkQbALzQ7V0MY0IqdnXNOeTtP4r0lN9z7AAawCXgqea7bDii20AYrIBrFd/Hx0M2Ocz6S111CaFkUcb0Q==", - "license": "MIT", - "engines": { - "node": ">=0.8.x" - } - }, - "node_modules/evp_bytestokey": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/evp_bytestokey/-/evp_bytestokey-1.0.3.tgz", - "integrity": "sha512-/f2Go4TognH/KvCISP7OUsHn85hT9nUkxxA9BEWxFn+Oj9o8ZNLm/40hdlgSLyuOimsrTKLUMEorQexp/aPQeA==", - "license": "MIT", - "dependencies": { - "md5.js": "^1.3.4", - "safe-buffer": "^5.1.1" - } - }, - "node_modules/execa": { - "version": "5.1.1", - "resolved": "https://registry.npmjs.org/execa/-/execa-5.1.1.tgz", - "integrity": "sha512-8uSpZZocAZRBAPIEINJj3Lo9HyGitllczc27Eh5YYojjMFMn8yHMDMaUHE2Jqfq05D/wucwI4JGURyXt1vchyg==", - "license": "MIT", - "dependencies": { - "cross-spawn": "^7.0.3", - "get-stream": "^6.0.0", - "human-signals": "^2.1.0", - "is-stream": "^2.0.0", - "merge-stream": "^2.0.0", - "npm-run-path": "^4.0.1", - "onetime": "^5.1.2", - "signal-exit": "^3.0.3", - "strip-final-newline": "^2.0.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sindresorhus/execa?sponsor=1" - } - }, - "node_modules/exenv": { - "version": "1.2.2", - "resolved": "https://registry.npmjs.org/exenv/-/exenv-1.2.2.tgz", - "integrity": "sha512-Z+ktTxTwv9ILfgKCk32OX3n/doe+OcLTRtqK9pcL+JsP3J1/VW8Uvl4ZjLlKqeW4rzK4oesDOGMEMRIZqtP4Iw==", - "license": "BSD-3-Clause" - }, - "node_modules/express": { - "version": "4.21.2", - "resolved": "https://registry.npmjs.org/express/-/express-4.21.2.tgz", - "integrity": "sha512-28HqgMZAmih1Czt9ny7qr6ek2qddF4FclbMzwhCREB6OFfH+rXAnuNCwo1/wFvrtbgsQDb4kSbX9de9lFbrXnA==", - "license": "MIT", - "dependencies": { - "accepts": "~1.3.8", - "array-flatten": "1.1.1", - "body-parser": "1.20.3", - "content-disposition": "0.5.4", - "content-type": "~1.0.4", - "cookie": "0.7.1", - "cookie-signature": "1.0.6", - "debug": "2.6.9", - "depd": "2.0.0", - "encodeurl": "~2.0.0", - "escape-html": "~1.0.3", - "etag": "~1.8.1", - "finalhandler": "1.3.1", - "fresh": "0.5.2", - "http-errors": "2.0.0", - "merge-descriptors": "1.0.3", - "methods": "~1.1.2", - "on-finished": "2.4.1", - "parseurl": "~1.3.3", - "path-to-regexp": "0.1.12", - "proxy-addr": "~2.0.7", - "qs": "6.13.0", - "range-parser": "~1.2.1", - "safe-buffer": "5.2.1", - "send": "0.19.0", - "serve-static": "1.16.2", - "setprototypeof": "1.2.0", - "statuses": "2.0.1", - "type-is": "~1.6.18", - "utils-merge": "1.0.1", - "vary": "~1.1.2" - }, - "engines": { - "node": ">= 0.10.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/express" - } - }, - "node_modules/express/node_modules/content-disposition": { - "version": "0.5.4", - "resolved": "https://registry.npmjs.org/content-disposition/-/content-disposition-0.5.4.tgz", - "integrity": "sha512-FveZTNuGw04cxlAiWbzi6zTAL/lhehaWbTtgluJh4/E95DqMwTmha3KZN1aAWA8cFIhHzMZUvLevkw5Rqk+tSQ==", - "license": "MIT", - "dependencies": { - "safe-buffer": "5.2.1" - }, - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/express/node_modules/debug": { - "version": "2.6.9", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", - "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", - "license": "MIT", - "dependencies": { - "ms": "2.0.0" - } - }, - "node_modules/express/node_modules/ms": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", - "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==", - "license": "MIT" - }, - "node_modules/express/node_modules/path-to-regexp": { - "version": "0.1.12", - "resolved": "https://registry.npmjs.org/path-to-regexp/-/path-to-regexp-0.1.12.tgz", - "integrity": "sha512-RA1GjUVMnvYFxuqovrEqZoxxW5NUZqbwKtYz/Tt7nXerk0LbLblQmrsgdeOxV5SFHf0UDggjS/bSeOZwt1pmEQ==", - "license": "MIT" - }, - "node_modules/express/node_modules/range-parser": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/range-parser/-/range-parser-1.2.1.tgz", - "integrity": "sha512-Hrgsx+orqoygnmhFbKaHE6c296J+HTAQXoxEF6gNupROmmGJRoyzfG3ccAveqCBrwr/2yxQ5BVd/GTl5agOwSg==", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/extend": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/extend/-/extend-3.0.2.tgz", - "integrity": "sha512-fjquC59cD7CyW6urNXK0FBufkZcoiGG80wTuPujX590cB5Ttln20E2UB4S/WARVqhXffZl2LNgS+gQdPIIim/g==", - "license": "MIT" - }, - "node_modules/extend-shallow": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", - "integrity": "sha512-zCnTtlxNoAiDc3gqY2aYAWFx7XWWiasuF2K8Me5WbN8otHKTUKBwjPtNpRs/rbUZm7KxWAaNj7P1a/p52GbVug==", - "license": "MIT", - "dependencies": { - "is-extendable": "^0.1.0" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/fast-deep-equal": { - "version": "3.1.3", - "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-3.1.3.tgz", - "integrity": "sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q==", - "license": "MIT" - }, - "node_modules/fast-glob": { - "version": "3.3.2", - "resolved": "https://registry.npmjs.org/fast-glob/-/fast-glob-3.3.2.tgz", - "integrity": "sha512-oX2ruAFQwf/Orj8m737Y5adxDQO0LAB7/S5MnxCdTNDd4p6BsyIVsv9JQsATbTSq8KHRpLwIHbVlUNatxd+1Ow==", - "license": "MIT", - "dependencies": { - "@nodelib/fs.stat": "^2.0.2", - "@nodelib/fs.walk": "^1.2.3", - "glob-parent": "^5.1.2", - "merge2": "^1.3.0", - "micromatch": "^4.0.4" - }, - "engines": { - "node": ">=8.6.0" - } - }, - "node_modules/fast-json-stable-stringify": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/fast-json-stable-stringify/-/fast-json-stable-stringify-2.1.0.tgz", - "integrity": "sha512-lhd/wF+Lk98HZoTCtlVraHtfh5XYijIjalXck7saUtuanSDyLMxnHhSXEDJqHxD7msR8D0uCmqlkwjCV8xvwHw==", - "license": "MIT" - }, - "node_modules/fast-safe-stringify": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/fast-safe-stringify/-/fast-safe-stringify-2.1.1.tgz", - "integrity": "sha512-W+KJc2dmILlPplD/H4K9l9LcAHAfPtP6BY84uVLXQ6Evcz9Lcg33Y2z1IVblT6xdY54PXYVHEv+0Wpq8Io6zkA==", - "license": "MIT" - }, - "node_modules/fast-uri": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/fast-uri/-/fast-uri-3.0.1.tgz", - "integrity": "sha512-MWipKbbYiYI0UC7cl8m/i/IWTqfC8YXsqjzybjddLsFjStroQzsHXkc73JutMvBiXmOvapk+axIl79ig5t55Bw==", - "license": "MIT" - }, - "node_modules/fastq": { - "version": "1.17.1", - "resolved": "https://registry.npmjs.org/fastq/-/fastq-1.17.1.tgz", - "integrity": "sha512-sRVD3lWVIXWg6By68ZN7vho9a1pQcN/WBFaAAsDDFzlJjvoGx0P8z7V1t72grFJfJhu3YPZBuu25f7Kaw2jN1w==", - "license": "ISC", - "dependencies": { - "reusify": "^1.0.4" - } - }, - "node_modules/fault": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/fault/-/fault-2.0.1.tgz", - "integrity": "sha512-WtySTkS4OKev5JtpHXnib4Gxiurzh5NCGvWrFaZ34m6JehfTUhKZvn9njTfw48t6JumVQOmrKqpmGcdwxnhqBQ==", - "license": "MIT", - "dependencies": { - "format": "^0.2.0" - }, - "funding": { - "type": "github", - "url": "https://github.com/sponsors/wooorm" - } - }, - "node_modules/faye-websocket": { - "version": "0.11.4", - "resolved": "https://registry.npmjs.org/faye-websocket/-/faye-websocket-0.11.4.tgz", - "integrity": "sha512-CzbClwlXAuiRQAlUyfqPgvPoNKTckTPGfwZV4ZdAhVcP2lh9KUxJg2b5GkE7XbjKQ3YJnQ9z6D9ntLAlB+tP8g==", - "license": "Apache-2.0", - "dependencies": { - "websocket-driver": ">=0.5.1" - }, - "engines": { - "node": ">=0.8.0" - } - }, - "node_modules/feed": { - "version": "4.2.2", - "resolved": "https://registry.npmjs.org/feed/-/feed-4.2.2.tgz", - "integrity": "sha512-u5/sxGfiMfZNtJ3OvQpXcvotFpYkL0n9u9mM2vkui2nGo8b4wvDkJ8gAkYqbA8QpGyFCv3RK0Z+Iv+9veCS9bQ==", - "license": "MIT", - "dependencies": { - "xml-js": "^1.6.11" - }, - "engines": { - "node": ">=0.4.0" - } - }, - "node_modules/figures": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/figures/-/figures-3.2.0.tgz", - "integrity": "sha512-yaduQFRKLXYOGgEn6AZau90j3ggSOyiqXU0F9JZfeXYhNa+Jk4X+s45A2zg5jns87GAFa34BBm2kXw4XpNcbdg==", - "license": "MIT", - "dependencies": { - "escape-string-regexp": "^1.0.5" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "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==", - "license": "MIT", - "engines": { - "node": ">=0.8.0" - } - }, - "node_modules/file-loader": { - "version": "6.2.0", - "resolved": "https://registry.npmjs.org/file-loader/-/file-loader-6.2.0.tgz", - "integrity": "sha512-qo3glqyTa61Ytg4u73GultjHGjdRyig3tG6lPtyX/jOEJvHif9uB0/OCI2Kif6ctF3caQTW2G5gym21oAsI4pw==", - "license": "MIT", - "dependencies": { - "loader-utils": "^2.0.0", - "schema-utils": "^3.0.0" - }, - "engines": { - "node": ">= 10.13.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/webpack" - }, - "peerDependencies": { - "webpack": "^4.0.0 || ^5.0.0" - } - }, - "node_modules/file-loader/node_modules/ajv": { - "version": "6.12.6", - "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz", - "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==", - "license": "MIT", - "dependencies": { - "fast-deep-equal": "^3.1.1", - "fast-json-stable-stringify": "^2.0.0", - "json-schema-traverse": "^0.4.1", - "uri-js": "^4.2.2" - }, - "funding": { - "type": "github", - "url": "https://github.com/sponsors/epoberezkin" - } - }, - "node_modules/file-loader/node_modules/ajv-keywords": { - "version": "3.5.2", - "resolved": "https://registry.npmjs.org/ajv-keywords/-/ajv-keywords-3.5.2.tgz", - "integrity": "sha512-5p6WTN0DdTGVQk6VjcEju19IgaHudalcfabD7yhDGeA6bcQnmL+CpveLJq/3hvfwd1aof6L386Ougkx6RfyMIQ==", - "license": "MIT", - "peerDependencies": { - "ajv": "^6.9.1" - } - }, - "node_modules/file-loader/node_modules/json-schema-traverse": { - "version": "0.4.1", - "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz", - "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==", - "license": "MIT" - }, - "node_modules/file-loader/node_modules/schema-utils": { - "version": "3.3.0", - "resolved": "https://registry.npmjs.org/schema-utils/-/schema-utils-3.3.0.tgz", - "integrity": "sha512-pN/yOAvcC+5rQ5nERGuwrjLlYvLTbCibnZ1I7B1LaiAz9BRBlE9GMgE/eqV30P7aJQUf7Ddimy/RsbYO/GrVGg==", - "license": "MIT", - "dependencies": { - "@types/json-schema": "^7.0.8", - "ajv": "^6.12.5", - "ajv-keywords": "^3.5.2" - }, - "engines": { - "node": ">= 10.13.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/webpack" - } - }, - "node_modules/file-saver": { - "version": "2.0.5", - "resolved": "https://registry.npmjs.org/file-saver/-/file-saver-2.0.5.tgz", - "integrity": "sha512-P9bmyZ3h/PRG+Nzga+rbdI4OEpNDzAVyy74uVO9ATgzLK6VtAsYybF/+TOCvrc0MO793d6+42lLyZTw7/ArVzA==", - "license": "MIT" - }, - "node_modules/file-type": { - "version": "3.9.0", - "resolved": "https://registry.npmjs.org/file-type/-/file-type-3.9.0.tgz", - "integrity": "sha512-RLoqTXE8/vPmMuTI88DAzhMYC99I8BWv7zYP4A1puo5HIjEJ5EX48ighy4ZyKMG9EDXxBgW6e++cn7d1xuFghA==", - "license": "MIT", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/filesize": { - "version": "8.0.7", - "resolved": "https://registry.npmjs.org/filesize/-/filesize-8.0.7.tgz", - "integrity": "sha512-pjmC+bkIF8XI7fWaH8KxHcZL3DPybs1roSKP4rKDvy20tAWwIObE4+JIseG2byfGKhud5ZnM4YSGKBz7Sh0ndQ==", - "license": "BSD-3-Clause", - "engines": { - "node": ">= 0.4.0" - } - }, - "node_modules/fill-range": { - "version": "7.1.1", - "resolved": "https://registry.npmjs.org/fill-range/-/fill-range-7.1.1.tgz", - "integrity": "sha512-YsGpe3WHLK8ZYi4tWDg2Jy3ebRz2rXowDxnld4bkQB00cc/1Zw9AWnC0i9ztDJitivtQvaI9KaLyKrc+hBW0yg==", - "license": "MIT", - "dependencies": { - "to-regex-range": "^5.0.1" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/filter-obj": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/filter-obj/-/filter-obj-2.0.2.tgz", - "integrity": "sha512-lO3ttPjHZRfjMcxWKb1j1eDhTFsu4meeR3lnMcnBFhk6RuLhvEiuALu2TlfL310ph4lCYYwgF/ElIjdP739tdg==", - "license": "MIT", - "engines": { - "node": ">=8" - } - }, - "node_modules/finalhandler": { - "version": "1.3.1", - "resolved": "https://registry.npmjs.org/finalhandler/-/finalhandler-1.3.1.tgz", - "integrity": "sha512-6BN9trH7bp3qvnrRyzsBz+g3lZxTNZTbVO2EV1CS0WIcDbawYVdYvGflME/9QP0h0pYlCDBCTjYa9nZzMDpyxQ==", - "dependencies": { - "debug": "2.6.9", - "encodeurl": "~2.0.0", - "escape-html": "~1.0.3", - "on-finished": "2.4.1", - "parseurl": "~1.3.3", - "statuses": "2.0.1", - "unpipe": "~1.0.0" - }, - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/finalhandler/node_modules/debug": { - "version": "2.6.9", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", - "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", - "dependencies": { - "ms": "2.0.0" - } - }, - "node_modules/finalhandler/node_modules/ms": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", - "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==" - }, - "node_modules/find-cache-dir": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/find-cache-dir/-/find-cache-dir-4.0.0.tgz", - "integrity": "sha512-9ZonPT4ZAK4a+1pUPVPZJapbi7O5qbbJPdYw/NOQWZZbVLdDTYM3A4R9z/DpAM08IDaFGsvPgiGZ82WEwUDWjg==", - "license": "MIT", - "dependencies": { - "common-path-prefix": "^3.0.0", - "pkg-dir": "^7.0.0" - }, - "engines": { - "node": ">=14.16" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/find-up": { - "version": "6.3.0", - "resolved": "https://registry.npmjs.org/find-up/-/find-up-6.3.0.tgz", - "integrity": "sha512-v2ZsoEuVHYy8ZIlYqwPe/39Cy+cFDzp4dXPaxNvkEuouymu+2Jbz0PxpKarJHYJTmv2HWT3O382qY8l4jMWthw==", - "license": "MIT", - "dependencies": { - "locate-path": "^7.1.0", - "path-exists": "^5.0.0" - }, - "engines": { - "node": "^12.20.0 || ^14.13.1 || >=16.0.0" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/flat": { - "version": "5.0.2", - "resolved": "https://registry.npmjs.org/flat/-/flat-5.0.2.tgz", - "integrity": "sha512-b6suED+5/3rTpUBdG1gupIl8MPFCAMA0QXwmljLhvCUKcUvdE4gWky9zpuGCcXHOsz4J9wPGNWq6OKpmIzz3hQ==", - "license": "BSD-3-Clause", - "bin": { - "flat": "cli.js" - } - }, - "node_modules/follow-redirects": { - "version": "1.15.6", - "resolved": "https://registry.npmjs.org/follow-redirects/-/follow-redirects-1.15.6.tgz", - "integrity": "sha512-wWN62YITEaOpSK584EZXJafH1AGpO8RVgElfkuXbTOrPX4fIfOyEpW/CsiNd8JdYrAoOvafRTOEnvsO++qCqFA==", - "funding": [ - { - "type": "individual", - "url": "https://github.com/sponsors/RubenVerborgh" - } - ], - "license": "MIT", - "engines": { - "node": ">=4.0" - }, - "peerDependenciesMeta": { - "debug": { - "optional": true - } - } - }, - "node_modules/for-each": { - "version": "0.3.3", - "resolved": "https://registry.npmjs.org/for-each/-/for-each-0.3.3.tgz", - "integrity": "sha512-jqYfLp7mo9vIyQf8ykW2v7A+2N4QjeCeI5+Dz9XraiO1ign81wjiH7Fb9vSOWvQfNtmSa4H2RoQTrrXivdUZmw==", - "license": "MIT", - "dependencies": { - "is-callable": "^1.1.3" - } - }, - "node_modules/foreach": { - "version": "2.0.6", - "resolved": "https://registry.npmjs.org/foreach/-/foreach-2.0.6.tgz", - "integrity": "sha512-k6GAGDyqLe9JaebCsFCoudPPWfihKu8pylYXRlqP1J7ms39iPoTtk2fviNglIeQEwdh0bQeKJ01ZPyuyQvKzwg==", - "license": "MIT" - }, - "node_modules/foreground-child": { - "version": "3.3.0", - "resolved": "https://registry.npmjs.org/foreground-child/-/foreground-child-3.3.0.tgz", - "integrity": "sha512-Ld2g8rrAyMYFXBhEqMz8ZAHBi4J4uS1i/CxGMDnjyFWddMXLVcDp051DZfu+t7+ab7Wv6SMqpWmyFIj5UbfFvg==", - "license": "ISC", - "dependencies": { - "cross-spawn": "^7.0.0", - "signal-exit": "^4.0.1" - }, - "engines": { - "node": ">=14" - }, - "funding": { - "url": "https://github.com/sponsors/isaacs" - } - }, - "node_modules/foreground-child/node_modules/signal-exit": { - "version": "4.1.0", - "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-4.1.0.tgz", - "integrity": "sha512-bzyZ1e88w9O1iNJbKnOlvYTrWPDl46O1bG0D3XInv+9tkPrxrN8jUUTiFlDkkmKWgn1M6CfIA13SuGqOa9Korw==", - "license": "ISC", - "engines": { - "node": ">=14" - }, - "funding": { - "url": "https://github.com/sponsors/isaacs" - } - }, - "node_modules/fork-ts-checker-webpack-plugin": { - "version": "6.5.3", - "resolved": "https://registry.npmjs.org/fork-ts-checker-webpack-plugin/-/fork-ts-checker-webpack-plugin-6.5.3.tgz", - "integrity": "sha512-SbH/l9ikmMWycd5puHJKTkZJKddF4iRLyW3DeZ08HTI7NGyLS38MXd/KGgeWumQO7YNQbW2u/NtPT2YowbPaGQ==", - "license": "MIT", - "dependencies": { - "@babel/code-frame": "^7.8.3", - "@types/json-schema": "^7.0.5", - "chalk": "^4.1.0", - "chokidar": "^3.4.2", - "cosmiconfig": "^6.0.0", - "deepmerge": "^4.2.2", - "fs-extra": "^9.0.0", - "glob": "^7.1.6", - "memfs": "^3.1.2", - "minimatch": "^3.0.4", - "schema-utils": "2.7.0", - "semver": "^7.3.2", - "tapable": "^1.0.0" - }, - "engines": { - "node": ">=10", - "yarn": ">=1.0.0" - }, - "peerDependencies": { - "eslint": ">= 6", - "typescript": ">= 2.7", - "vue-template-compiler": "*", - "webpack": ">= 4" - }, - "peerDependenciesMeta": { - "eslint": { - "optional": true - }, - "vue-template-compiler": { - "optional": true - } - } - }, - "node_modules/fork-ts-checker-webpack-plugin/node_modules/ajv": { - "version": "6.12.6", - "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz", - "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==", - "license": "MIT", - "dependencies": { - "fast-deep-equal": "^3.1.1", - "fast-json-stable-stringify": "^2.0.0", - "json-schema-traverse": "^0.4.1", - "uri-js": "^4.2.2" - }, - "funding": { - "type": "github", - "url": "https://github.com/sponsors/epoberezkin" - } - }, - "node_modules/fork-ts-checker-webpack-plugin/node_modules/ajv-keywords": { - "version": "3.5.2", - "resolved": "https://registry.npmjs.org/ajv-keywords/-/ajv-keywords-3.5.2.tgz", - "integrity": "sha512-5p6WTN0DdTGVQk6VjcEju19IgaHudalcfabD7yhDGeA6bcQnmL+CpveLJq/3hvfwd1aof6L386Ougkx6RfyMIQ==", - "license": "MIT", - "peerDependencies": { - "ajv": "^6.9.1" - } - }, - "node_modules/fork-ts-checker-webpack-plugin/node_modules/cosmiconfig": { - "version": "6.0.0", - "resolved": "https://registry.npmjs.org/cosmiconfig/-/cosmiconfig-6.0.0.tgz", - "integrity": "sha512-xb3ZL6+L8b9JLLCx3ZdoZy4+2ECphCMo2PwqgP1tlfVq6M6YReyzBJtvWWtbDSpNr9hn96pkCiZqUcFEc+54Qg==", - "license": "MIT", - "dependencies": { - "@types/parse-json": "^4.0.0", - "import-fresh": "^3.1.0", - "parse-json": "^5.0.0", - "path-type": "^4.0.0", - "yaml": "^1.7.2" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/fork-ts-checker-webpack-plugin/node_modules/fs-extra": { - "version": "9.1.0", - "resolved": "https://registry.npmjs.org/fs-extra/-/fs-extra-9.1.0.tgz", - "integrity": "sha512-hcg3ZmepS30/7BSFqRvoo3DOMQu7IjqxO5nCDt+zM9XWjb33Wg7ziNT+Qvqbuc3+gWpzO02JubVyk2G4Zvo1OQ==", - "license": "MIT", - "dependencies": { - "at-least-node": "^1.0.0", - "graceful-fs": "^4.2.0", - "jsonfile": "^6.0.1", - "universalify": "^2.0.0" - }, - "engines": { - "node": ">=10" - } - }, - "node_modules/fork-ts-checker-webpack-plugin/node_modules/json-schema-traverse": { - "version": "0.4.1", - "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz", - "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==", - "license": "MIT" - }, - "node_modules/fork-ts-checker-webpack-plugin/node_modules/schema-utils": { - "version": "2.7.0", - "resolved": "https://registry.npmjs.org/schema-utils/-/schema-utils-2.7.0.tgz", - "integrity": "sha512-0ilKFI6QQF5nxDZLFn2dMjvc4hjg/Wkg7rHd3jK6/A4a1Hl9VFdQWvgB1UMGoU94pad1P/8N7fMcEnLnSiju8A==", - "license": "MIT", - "dependencies": { - "@types/json-schema": "^7.0.4", - "ajv": "^6.12.2", - "ajv-keywords": "^3.4.1" - }, - "engines": { - "node": ">= 8.9.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/webpack" - } - }, - "node_modules/fork-ts-checker-webpack-plugin/node_modules/tapable": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/tapable/-/tapable-1.1.3.tgz", - "integrity": "sha512-4WK/bYZmj8xLr+HUCODHGF1ZFzsYffasLUgEiMBY4fgtltdO6B4WJtlSbPaDTLpYTcGVwM2qLnFTICEcNxs3kA==", - "license": "MIT", - "engines": { - "node": ">=6" - } - }, - "node_modules/form-data-encoder": { - "version": "2.1.4", - "resolved": "https://registry.npmjs.org/form-data-encoder/-/form-data-encoder-2.1.4.tgz", - "integrity": "sha512-yDYSgNMraqvnxiEXO4hi88+YZxaHC6QKzb5N84iRCTDeRO7ZALpir/lVmf/uXUhnwUr2O4HU8s/n6x+yNjQkHw==", - "license": "MIT", - "engines": { - "node": ">= 14.17" - } - }, - "node_modules/format": { - "version": "0.2.2", - "resolved": "https://registry.npmjs.org/format/-/format-0.2.2.tgz", - "integrity": "sha512-wzsgA6WOq+09wrU1tsJ09udeR/YZRaeArL9e1wPbFg3GG2yDnC2ldKpxs4xunpFF9DgqCqOIra3bc1HWrJ37Ww==", - "engines": { - "node": ">=0.4.x" - } - }, - "node_modules/forwarded": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/forwarded/-/forwarded-0.2.0.tgz", - "integrity": "sha512-buRG0fpBtRHSTCOASe6hD258tEubFoRLb4ZNA6NxMVHNw2gOcwHo9wyablzMzOA5z9xA9L1KNjk/Nt6MT9aYow==", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/fraction.js": { - "version": "4.3.7", - "resolved": "https://registry.npmjs.org/fraction.js/-/fraction.js-4.3.7.tgz", - "integrity": "sha512-ZsDfxO51wGAXREY55a7la9LScWpwv9RxIrYABrlvOFBlH/ShPnrtsXeuUIfXKKOVicNxQ+o8JTbJvjS4M89yew==", - "license": "MIT", - "engines": { - "node": "*" - }, - "funding": { - "type": "patreon", - "url": "https://github.com/sponsors/rawify" - } - }, - "node_modules/fresh": { - "version": "0.5.2", - "resolved": "https://registry.npmjs.org/fresh/-/fresh-0.5.2.tgz", - "integrity": "sha512-zJ2mQYM18rEFOudeV4GShTGIQ7RbzA7ozbU9I/XBpm7kqgMywgmylMwXHxZJmkVoYkna9d2pVXVXPdYTP9ej8Q==", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/fs-extra": { - "version": "11.2.0", - "resolved": "https://registry.npmjs.org/fs-extra/-/fs-extra-11.2.0.tgz", - "integrity": "sha512-PmDi3uwK5nFuXh7XDTlVnS17xJS7vW36is2+w3xcv8SVxiB4NyATf4ctkVY5bkSjX0Y4nbvZCq1/EjtEyr9ktw==", - "license": "MIT", - "dependencies": { - "graceful-fs": "^4.2.0", - "jsonfile": "^6.0.1", - "universalify": "^2.0.0" - }, - "engines": { - "node": ">=14.14" - } - }, - "node_modules/fs-monkey": { - "version": "1.0.6", - "resolved": "https://registry.npmjs.org/fs-monkey/-/fs-monkey-1.0.6.tgz", - "integrity": "sha512-b1FMfwetIKymC0eioW7mTywihSQE4oLzQn1dB6rZB5fx/3NpNEdAWeCSMB+60/AeT0TCXsxzAlcYVEFCTAksWg==", - "license": "Unlicense" - }, - "node_modules/fs.realpath": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz", - "integrity": "sha512-OO0pH2lK6a0hZnAdau5ItzHPI6pUlvI7jMVnxUQRtw4owF2wk8lOSabtGDCTP4Ggrg2MbGnWO9X8K1t4+fGMDw==", - "license": "ISC" - }, - "node_modules/fsevents": { - "version": "2.3.3", - "resolved": "https://registry.npmjs.org/fsevents/-/fsevents-2.3.3.tgz", - "integrity": "sha512-5xoDfX+fL7faATnagmWPpbFtwh/R77WmMMqqHGS65C3vvB0YHrgF+B1YmZ3441tMj5n63k0212XNoJwzlhffQw==", - "hasInstallScript": true, - "license": "MIT", - "optional": true, - "os": [ - "darwin" - ], - "engines": { - "node": "^8.16.0 || ^10.6.0 || >=11.0.0" - } - }, - "node_modules/function-bind": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/function-bind/-/function-bind-1.1.2.tgz", - "integrity": "sha512-7XHNxH7qX9xG5mIwxkhumTox/MIRNcOgDrxWsMt2pAr23WHp6MrRlN7FBSFpCpr+oVO0F744iUgR82nJMfG2SA==", - "license": "MIT", - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/gensync": { - "version": "1.0.0-beta.2", - "resolved": "https://registry.npmjs.org/gensync/-/gensync-1.0.0-beta.2.tgz", - "integrity": "sha512-3hN7NaskYvMDLQY55gnW3NQ+mesEAepTqlg+VEbj7zzqEMBVNhzcGYYeqFo/TlYz6eQiFcp1HcsCZO+nGgS8zg==", - "license": "MIT", - "engines": { - "node": ">=6.9.0" - } - }, - "node_modules/get-caller-file": { - "version": "2.0.5", - "resolved": "https://registry.npmjs.org/get-caller-file/-/get-caller-file-2.0.5.tgz", - "integrity": "sha512-DyFP3BM/3YHTQOCUL/w0OZHR0lpKeGrxotcHWcqNEdnltqFwXVfhEBQ94eIo34AfQpo0rGki4cyIiftY06h2Fg==", - "license": "ISC", - "engines": { - "node": "6.* || 8.* || >= 10.*" - } - }, - "node_modules/get-intrinsic": { - "version": "1.2.4", - "resolved": "https://registry.npmjs.org/get-intrinsic/-/get-intrinsic-1.2.4.tgz", - "integrity": "sha512-5uYhsJH8VJBTv7oslg4BznJYhDoRI6waYCxMmCdnTrcCrHA/fCFKoTFz2JKKE0HdDFUF7/oQuhzumXJK7paBRQ==", - "license": "MIT", - "dependencies": { - "es-errors": "^1.3.0", - "function-bind": "^1.1.2", - "has-proto": "^1.0.1", - "has-symbols": "^1.0.3", - "hasown": "^2.0.0" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/get-own-enumerable-property-symbols": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/get-own-enumerable-property-symbols/-/get-own-enumerable-property-symbols-3.0.2.tgz", - "integrity": "sha512-I0UBV/XOz1XkIJHEUDMZAbzCThU/H8DxmSfmdGcKPnVhu2VfFqr34jr9777IyaTYvxjedWhqVIilEDsCdP5G6g==", - "license": "ISC" - }, - "node_modules/get-stream": { - "version": "6.0.1", - "resolved": "https://registry.npmjs.org/get-stream/-/get-stream-6.0.1.tgz", - "integrity": "sha512-ts6Wi+2j3jQjqi70w5AlN8DFnkSwC+MqmxEzdEALB2qXZYV3X/b1CTfgPLGJNMeAWxdPfU8FO1ms3NUfaHCPYg==", - "license": "MIT", - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/github-slugger": { - "version": "1.5.0", - "resolved": "https://registry.npmjs.org/github-slugger/-/github-slugger-1.5.0.tgz", - "integrity": "sha512-wIh+gKBI9Nshz2o46B0B3f5k/W+WI9ZAv6y5Dn5WJ5SK1t0TnDimB4WE5rmTD05ZAIn8HALCZVmCsvj0w0v0lw==", - "license": "ISC" - }, - "node_modules/glob": { - "version": "7.2.3", - "resolved": "https://registry.npmjs.org/glob/-/glob-7.2.3.tgz", - "integrity": "sha512-nFR0zLpU2YCaRxwoCJvL6UvCH2JFyFVIvwTLsIf21AuHlMskA1hhTdk+LlYJtOlYt9v6dvszD2BGRqBL+iQK9Q==", - "deprecated": "Glob versions prior to v9 are no longer supported", - "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/glob-parent": { - "version": "5.1.2", - "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-5.1.2.tgz", - "integrity": "sha512-AOIgSQCepiJYwP3ARnGx+5VnTu2HBYdzbGP45eLw1vr3zB3vZLeyed1sC9hnbcOc9/SrMyM5RPQrkGz4aS9Zow==", - "license": "ISC", - "dependencies": { - "is-glob": "^4.0.1" - }, - "engines": { - "node": ">= 6" - } - }, - "node_modules/glob-to-regexp": { - "version": "0.4.1", - "resolved": "https://registry.npmjs.org/glob-to-regexp/-/glob-to-regexp-0.4.1.tgz", - "integrity": "sha512-lkX1HJXwyMcprw/5YUZc2s7DrpAiHB21/V+E1rHUrVNokkvB6bqMzT0VfV6/86ZNabt1k14YOIaT7nDvOX3Iiw==", - "license": "BSD-2-Clause" - }, - "node_modules/global-dirs": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/global-dirs/-/global-dirs-3.0.1.tgz", - "integrity": "sha512-NBcGGFbBA9s1VzD41QXDG+3++t9Mn5t1FpLdhESY6oKY4gYTFpX4wO3sqGUa0Srjtbfj3szX0RnemmrVRUdULA==", - "license": "MIT", - "dependencies": { - "ini": "2.0.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/global-dirs/node_modules/ini": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/ini/-/ini-2.0.0.tgz", - "integrity": "sha512-7PnF4oN3CvZF23ADhA5wRaYEQpJ8qygSkbtTXWBeXWXmEVRXK+1ITciHWwHhsjv1TmW0MgacIv6hEi5pX5NQdA==", - "license": "ISC", - "engines": { - "node": ">=10" - } - }, - "node_modules/global-modules": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/global-modules/-/global-modules-2.0.0.tgz", - "integrity": "sha512-NGbfmJBp9x8IxyJSd1P+otYK8vonoJactOogrVfFRIAEY1ukil8RSKDz2Yo7wh1oihl51l/r6W4epkeKJHqL8A==", - "license": "MIT", - "dependencies": { - "global-prefix": "^3.0.0" - }, - "engines": { - "node": ">=6" - } - }, - "node_modules/global-prefix": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/global-prefix/-/global-prefix-3.0.0.tgz", - "integrity": "sha512-awConJSVCHVGND6x3tmMaKcQvwXLhjdkmomy2W+Goaui8YPgYgXJZewhg3fWC+DlfqqQuWg8AwqjGTD2nAPVWg==", - "license": "MIT", - "dependencies": { - "ini": "^1.3.5", - "kind-of": "^6.0.2", - "which": "^1.3.1" - }, - "engines": { - "node": ">=6" - } - }, - "node_modules/global-prefix/node_modules/which": { - "version": "1.3.1", - "resolved": "https://registry.npmjs.org/which/-/which-1.3.1.tgz", - "integrity": "sha512-HxJdYWq1MTIQbJ3nw0cqssHoTNU267KlrDuGZ1WYlxDStUtKUhOaJmh112/TZmHxxUfuJqPXSOm7tDyas0OSIQ==", - "license": "ISC", - "dependencies": { - "isexe": "^2.0.0" - }, - "bin": { - "which": "bin/which" - } - }, - "node_modules/globals": { - "version": "11.12.0", - "resolved": "https://registry.npmjs.org/globals/-/globals-11.12.0.tgz", - "integrity": "sha512-WOBp/EEGUiIsJSp7wcv/y6MO+lV9UoncWqxuFfm8eBwzWNgyfBd6Gz+IeKQ9jCmyhoH99g15M3T+QaVHFjizVA==", - "license": "MIT", - "engines": { - "node": ">=4" - } - }, - "node_modules/globby": { - "version": "11.1.0", - "resolved": "https://registry.npmjs.org/globby/-/globby-11.1.0.tgz", - "integrity": "sha512-jhIXaOzy1sb8IyocaruWSn1TjmnBVs8Ayhcy83rmxNJ8q2uWKCAj3CnJY+KpGSXCueAPc0i05kVvVKtP1t9S3g==", - "license": "MIT", - "dependencies": { - "array-union": "^2.1.0", - "dir-glob": "^3.0.1", - "fast-glob": "^3.2.9", - "ignore": "^5.2.0", - "merge2": "^1.4.1", - "slash": "^3.0.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/gopd": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/gopd/-/gopd-1.0.1.tgz", - "integrity": "sha512-d65bNlIadxvpb/A2abVdlqKqV563juRnZ1Wtk6s1sIR8uNsXR70xqIzVqxVf1eTqDunwT2MkczEeaezCKTZhwA==", - "license": "MIT", - "dependencies": { - "get-intrinsic": "^1.1.3" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/got": { - "version": "12.6.1", - "resolved": "https://registry.npmjs.org/got/-/got-12.6.1.tgz", - "integrity": "sha512-mThBblvlAF1d4O5oqyvN+ZxLAYwIJK7bpMxgYqPD9okW0C3qm5FFn7k811QrcuEBwaogR3ngOFoCfs6mRv7teQ==", - "license": "MIT", - "dependencies": { - "@sindresorhus/is": "^5.2.0", - "@szmarczak/http-timer": "^5.0.1", - "cacheable-lookup": "^7.0.0", - "cacheable-request": "^10.2.8", - "decompress-response": "^6.0.0", - "form-data-encoder": "^2.1.2", - "get-stream": "^6.0.1", - "http2-wrapper": "^2.1.10", - "lowercase-keys": "^3.0.0", - "p-cancelable": "^3.0.0", - "responselike": "^3.0.0" - }, - "engines": { - "node": ">=14.16" - }, - "funding": { - "url": "https://github.com/sindresorhus/got?sponsor=1" - } - }, - "node_modules/got/node_modules/@sindresorhus/is": { - "version": "5.6.0", - "resolved": "https://registry.npmjs.org/@sindresorhus/is/-/is-5.6.0.tgz", - "integrity": "sha512-TV7t8GKYaJWsn00tFDqBw8+Uqmr8A0fRU1tvTQhyZzGv0sJCGRQL3JGMI3ucuKo3XIZdUP+Lx7/gh2t3lewy7g==", - "license": "MIT", - "engines": { - "node": ">=14.16" - }, - "funding": { - "url": "https://github.com/sindresorhus/is?sponsor=1" - } - }, - "node_modules/graceful-fs": { - "version": "4.2.11", - "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.2.11.tgz", - "integrity": "sha512-RbJ5/jmFcNNCcDV5o9eTnBLJ/HszWV0P73bc+Ff4nS/rJj+YaS6IGyiOL0VoBYX+l1Wrl3k63h/KrH+nhJ0XvQ==", - "license": "ISC" - }, - "node_modules/graphlib": { - "version": "2.1.8", - "resolved": "https://registry.npmjs.org/graphlib/-/graphlib-2.1.8.tgz", - "integrity": "sha512-jcLLfkpoVGmH7/InMC/1hIvOPSUh38oJtGhvrOFGzioE1DZ+0YW16RgmOJhHiuWTvGiJQ9Z1Ik43JvkRPRvE+A==", - "license": "MIT", - "dependencies": { - "lodash": "^4.17.15" - } - }, - "node_modules/gray-matter": { - "version": "4.0.3", - "resolved": "https://registry.npmjs.org/gray-matter/-/gray-matter-4.0.3.tgz", - "integrity": "sha512-5v6yZd4JK3eMI3FqqCouswVqwugaA9r4dNZB1wwcmrD02QkV5H0y7XBQW8QwQqEaZY1pM9aqORSORhJRdNK44Q==", - "license": "MIT", - "dependencies": { - "js-yaml": "^3.13.1", - "kind-of": "^6.0.2", - "section-matter": "^1.0.0", - "strip-bom-string": "^1.0.0" - }, - "engines": { - "node": ">=6.0" - } - }, - "node_modules/gray-matter/node_modules/argparse": { - "version": "1.0.10", - "resolved": "https://registry.npmjs.org/argparse/-/argparse-1.0.10.tgz", - "integrity": "sha512-o5Roy6tNG4SL/FOkCAN6RzjiakZS25RLYFrcMttJqbdd8BWrnA+fGz57iN5Pb06pvBGvl5gQ0B48dJlslXvoTg==", - "license": "MIT", - "dependencies": { - "sprintf-js": "~1.0.2" - } - }, - "node_modules/gray-matter/node_modules/js-yaml": { - "version": "3.14.1", - "resolved": "https://registry.npmjs.org/js-yaml/-/js-yaml-3.14.1.tgz", - "integrity": "sha512-okMH7OXXJ7YrN9Ok3/SXrnu4iX9yOk+25nqX4imS2npuvTYDmo/QEZoqwZkYaIDk3jVvBOTOIEgEhaLOynBS9g==", - "license": "MIT", - "dependencies": { - "argparse": "^1.0.7", - "esprima": "^4.0.0" - }, - "bin": { - "js-yaml": "bin/js-yaml.js" - } - }, - "node_modules/gzip-size": { - "version": "6.0.0", - "resolved": "https://registry.npmjs.org/gzip-size/-/gzip-size-6.0.0.tgz", - "integrity": "sha512-ax7ZYomf6jqPTQ4+XCpUGyXKHk5WweS+e05MBO4/y3WJ5RkmPXNKvX+bx1behVILVwr6JSQvZAku021CHPXG3Q==", - "license": "MIT", - "dependencies": { - "duplexer": "^0.1.2" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/handle-thing": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/handle-thing/-/handle-thing-2.0.1.tgz", - "integrity": "sha512-9Qn4yBxelxoh2Ow62nP+Ka/kMnOXRi8BXnRaUwezLNhqelnN49xKz4F/dPP8OYLxLxq6JDtZb2i9XznUQbNPTg==", - "license": "MIT" - }, - "node_modules/has-flag": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", - "license": "MIT", - "engines": { - "node": ">=8" - } - }, - "node_modules/has-property-descriptors": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/has-property-descriptors/-/has-property-descriptors-1.0.2.tgz", - "integrity": "sha512-55JNKuIW+vq4Ke1BjOTjM2YctQIvCT7GFzHwmfZPGo5wnrgkid0YQtnAleFSqumZm4az3n2BS+erby5ipJdgrg==", - "license": "MIT", - "dependencies": { - "es-define-property": "^1.0.0" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/has-proto": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/has-proto/-/has-proto-1.0.3.tgz", - "integrity": "sha512-SJ1amZAJUiZS+PhsVLf5tGydlaVB8EdFpaSO4gmiUKUOxk8qzn5AIy4ZeJUmh22znIdk/uMAUT2pl3FxzVUH+Q==", - "license": "MIT", - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/has-symbols": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/has-symbols/-/has-symbols-1.0.3.tgz", - "integrity": "sha512-l3LCuF6MgDNwTDKkdYGEihYjt5pRPbEg46rtlmnSPlUbgmB8LOIrKJbYYFBSbnPaJexMKtiPO8hmeRjRz2Td+A==", - "license": "MIT", - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/has-tostringtag": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/has-tostringtag/-/has-tostringtag-1.0.2.tgz", - "integrity": "sha512-NqADB8VjPFLM2V0VvHUewwwsw0ZWBaIdgo+ieHtK3hasLz4qeCRjYcqfB6AQrBggRKppKF8L52/VqdVsO47Dlw==", - "license": "MIT", - "dependencies": { - "has-symbols": "^1.0.3" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/has-yarn": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/has-yarn/-/has-yarn-3.0.0.tgz", - "integrity": "sha512-IrsVwUHhEULx3R8f/aA8AHuEzAorplsab/v8HBzEiIukwq5i/EC+xmOW+HfP1OaDP+2JkgT1yILHN2O3UFIbcA==", - "license": "MIT", - "engines": { - "node": "^12.20.0 || ^14.13.1 || >=16.0.0" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/hash-base": { - "version": "3.0.4", - "resolved": "https://registry.npmjs.org/hash-base/-/hash-base-3.0.4.tgz", - "integrity": "sha512-EeeoJKjTyt868liAlVmcv2ZsUfGHlE3Q+BICOXcZiwN3osr5Q/zFGYmTJpoIzuaSTAwndFy+GqhEwlU4L3j4Ow==", - "license": "MIT", - "dependencies": { - "inherits": "^2.0.1", - "safe-buffer": "^5.0.1" - }, - "engines": { - "node": ">=4" - } - }, - "node_modules/hash.js": { - "version": "1.1.7", - "resolved": "https://registry.npmjs.org/hash.js/-/hash.js-1.1.7.tgz", - "integrity": "sha512-taOaskGt4z4SOANNseOviYDvjEJinIkRgmp7LbKP2YTTmVxWBl87s/uzK9r+44BclBSp2X7K1hqeNfz9JbBeXA==", - "license": "MIT", - "dependencies": { - "inherits": "^2.0.3", - "minimalistic-assert": "^1.0.1" - } - }, - "node_modules/hasown": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/hasown/-/hasown-2.0.2.tgz", - "integrity": "sha512-0hJU9SCPvmMzIBdZFqNPXWa6dqh7WdH0cII9y+CyS8rG3nL48Bclra9HmKhVVUHyPWNH5Y7xDwAB7bfgSjkUMQ==", - "license": "MIT", - "dependencies": { - "function-bind": "^1.1.2" - }, - "engines": { - "node": ">= 0.4" - } - }, - "node_modules/hast-util-from-parse5": { - "version": "8.0.1", - "resolved": "https://registry.npmjs.org/hast-util-from-parse5/-/hast-util-from-parse5-8.0.1.tgz", - "integrity": "sha512-Er/Iixbc7IEa7r/XLtuG52zoqn/b3Xng/w6aZQ0xGVxzhw5xUFxcRqdPzP6yFi/4HBYRaifaI5fQ1RH8n0ZeOQ==", - "license": "MIT", - "dependencies": { - "@types/hast": "^3.0.0", - "@types/unist": "^3.0.0", - "devlop": "^1.0.0", - "hastscript": "^8.0.0", - "property-information": "^6.0.0", - "vfile": "^6.0.0", - "vfile-location": "^5.0.0", - "web-namespaces": "^2.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/hast-util-parse-selector": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/hast-util-parse-selector/-/hast-util-parse-selector-4.0.0.tgz", - "integrity": "sha512-wkQCkSYoOGCRKERFWcxMVMOcYE2K1AaNLU8DXS9arxnLOUEWbOXKXiJUNzEpqZ3JOKpnha3jkFrumEjVliDe7A==", - "license": "MIT", - "dependencies": { - "@types/hast": "^3.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/hast-util-raw": { - "version": "9.1.0", - "resolved": "https://registry.npmjs.org/hast-util-raw/-/hast-util-raw-9.1.0.tgz", - "integrity": "sha512-Y8/SBAHkZGoNkpzqqfCldijcuUKh7/su31kEBp67cFY09Wy0mTRgtsLYsiIxMJxlu0f6AA5SUTbDR8K0rxnbUw==", - "license": "MIT", - "dependencies": { - "@types/hast": "^3.0.0", - "@types/unist": "^3.0.0", - "@ungap/structured-clone": "^1.0.0", - "hast-util-from-parse5": "^8.0.0", - "hast-util-to-parse5": "^8.0.0", - "html-void-elements": "^3.0.0", - "mdast-util-to-hast": "^13.0.0", - "parse5": "^7.0.0", - "unist-util-position": "^5.0.0", - "unist-util-visit": "^5.0.0", - "vfile": "^6.0.0", - "web-namespaces": "^2.0.0", - "zwitch": "^2.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/hast-util-to-estree": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/hast-util-to-estree/-/hast-util-to-estree-3.1.0.tgz", - "integrity": "sha512-lfX5g6hqVh9kjS/B9E2gSkvHH4SZNiQFiqWS0x9fENzEl+8W12RqdRxX6d/Cwxi30tPQs3bIO+aolQJNp1bIyw==", - "license": "MIT", - "dependencies": { - "@types/estree": "^1.0.0", - "@types/estree-jsx": "^1.0.0", - "@types/hast": "^3.0.0", - "comma-separated-tokens": "^2.0.0", - "devlop": "^1.0.0", - "estree-util-attach-comments": "^3.0.0", - "estree-util-is-identifier-name": "^3.0.0", - "hast-util-whitespace": "^3.0.0", - "mdast-util-mdx-expression": "^2.0.0", - "mdast-util-mdx-jsx": "^3.0.0", - "mdast-util-mdxjs-esm": "^2.0.0", - "property-information": "^6.0.0", - "space-separated-tokens": "^2.0.0", - "style-to-object": "^0.4.0", - "unist-util-position": "^5.0.0", - "zwitch": "^2.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/hast-util-to-jsx-runtime": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/hast-util-to-jsx-runtime/-/hast-util-to-jsx-runtime-2.3.0.tgz", - "integrity": "sha512-H/y0+IWPdsLLS738P8tDnrQ8Z+dj12zQQ6WC11TIM21C8WFVoIxcqWXf2H3hiTVZjF1AWqoimGwrTWecWrnmRQ==", - "license": "MIT", - "dependencies": { - "@types/estree": "^1.0.0", - "@types/hast": "^3.0.0", - "@types/unist": "^3.0.0", - "comma-separated-tokens": "^2.0.0", - "devlop": "^1.0.0", - "estree-util-is-identifier-name": "^3.0.0", - "hast-util-whitespace": "^3.0.0", - "mdast-util-mdx-expression": "^2.0.0", - "mdast-util-mdx-jsx": "^3.0.0", - "mdast-util-mdxjs-esm": "^2.0.0", - "property-information": "^6.0.0", - "space-separated-tokens": "^2.0.0", - "style-to-object": "^1.0.0", - "unist-util-position": "^5.0.0", - "vfile-message": "^4.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/hast-util-to-jsx-runtime/node_modules/inline-style-parser": { - "version": "0.2.3", - "resolved": "https://registry.npmjs.org/inline-style-parser/-/inline-style-parser-0.2.3.tgz", - "integrity": "sha512-qlD8YNDqyTKTyuITrDOffsl6Tdhv+UC4hcdAVuQsK4IMQ99nSgd1MIA/Q+jQYoh9r3hVUXhYh7urSRmXPkW04g==", - "license": "MIT" - }, - "node_modules/hast-util-to-jsx-runtime/node_modules/style-to-object": { - "version": "1.0.6", - "resolved": "https://registry.npmjs.org/style-to-object/-/style-to-object-1.0.6.tgz", - "integrity": "sha512-khxq+Qm3xEyZfKd/y9L3oIWQimxuc4STrQKtQn8aSDRHb8mFgpukgX1hdzfrMEW6JCjyJ8p89x+IUMVnCBI1PA==", - "license": "MIT", - "dependencies": { - "inline-style-parser": "0.2.3" - } - }, - "node_modules/hast-util-to-parse5": { - "version": "8.0.0", - "resolved": "https://registry.npmjs.org/hast-util-to-parse5/-/hast-util-to-parse5-8.0.0.tgz", - "integrity": "sha512-3KKrV5ZVI8if87DVSi1vDeByYrkGzg4mEfeu4alwgmmIeARiBLKCZS2uw5Gb6nU9x9Yufyj3iudm6i7nl52PFw==", - "license": "MIT", - "dependencies": { - "@types/hast": "^3.0.0", - "comma-separated-tokens": "^2.0.0", - "devlop": "^1.0.0", - "property-information": "^6.0.0", - "space-separated-tokens": "^2.0.0", - "web-namespaces": "^2.0.0", - "zwitch": "^2.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/hast-util-whitespace": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/hast-util-whitespace/-/hast-util-whitespace-3.0.0.tgz", - "integrity": "sha512-88JUN06ipLwsnv+dVn+OIYOvAuvBMy/Qoi6O7mQHxdPXpjy+Cd6xRkWwux7DKO+4sYILtLBRIKgsdpS2gQc7qw==", - "license": "MIT", - "dependencies": { - "@types/hast": "^3.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/hastscript": { - "version": "8.0.0", - "resolved": "https://registry.npmjs.org/hastscript/-/hastscript-8.0.0.tgz", - "integrity": "sha512-dMOtzCEd3ABUeSIISmrETiKuyydk1w0pa+gE/uormcTpSYuaNJPbX1NU3JLyscSLjwAQM8bWMhhIlnCqnRvDTw==", - "license": "MIT", - "dependencies": { - "@types/hast": "^3.0.0", - "comma-separated-tokens": "^2.0.0", - "hast-util-parse-selector": "^4.0.0", - "property-information": "^6.0.0", - "space-separated-tokens": "^2.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/he": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/he/-/he-1.2.0.tgz", - "integrity": "sha512-F/1DnUGPopORZi0ni+CvrCgHQ5FyEAHRLSApuYWMmrbSwoN2Mn/7k+Gl38gJnR7yyDZk6WLXwiGod1JOWNDKGw==", - "license": "MIT", - "bin": { - "he": "bin/he" - } - }, - "node_modules/history": { - "version": "4.10.1", - "resolved": "https://registry.npmjs.org/history/-/history-4.10.1.tgz", - "integrity": "sha512-36nwAD620w12kuzPAsyINPWJqlNbij+hpK1k9XRloDtym8mxzGYl2c17LnV6IAGB2Dmg4tEa7G7DlawS0+qjew==", - "license": "MIT", - "dependencies": { - "@babel/runtime": "^7.1.2", - "loose-envify": "^1.2.0", - "resolve-pathname": "^3.0.0", - "tiny-invariant": "^1.0.2", - "tiny-warning": "^1.0.0", - "value-equal": "^1.0.1" - } - }, - "node_modules/hmac-drbg": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/hmac-drbg/-/hmac-drbg-1.0.1.tgz", - "integrity": "sha512-Tti3gMqLdZfhOQY1Mzf/AanLiqh1WTiJgEj26ZuYQ9fbkLomzGchCws4FyrSd4VkpBfiNhaE1On+lOz894jvXg==", - "license": "MIT", - "dependencies": { - "hash.js": "^1.0.3", - "minimalistic-assert": "^1.0.0", - "minimalistic-crypto-utils": "^1.0.1" - } - }, - "node_modules/hoist-non-react-statics": { - "version": "3.3.2", - "resolved": "https://registry.npmjs.org/hoist-non-react-statics/-/hoist-non-react-statics-3.3.2.tgz", - "integrity": "sha512-/gGivxi8JPKWNm/W0jSmzcMPpfpPLc3dY/6GxhX2hQ9iGj3aDfklV4ET7NjKpSinLpJ5vafa9iiGIEZg10SfBw==", - "license": "BSD-3-Clause", - "dependencies": { - "react-is": "^16.7.0" - } - }, - "node_modules/hpack.js": { - "version": "2.1.6", - "resolved": "https://registry.npmjs.org/hpack.js/-/hpack.js-2.1.6.tgz", - "integrity": "sha512-zJxVehUdMGIKsRaNt7apO2Gqp0BdqW5yaiGHXXmbpvxgBYVZnAql+BJb4RO5ad2MgpbZKn5G6nMnegrH1FcNYQ==", - "license": "MIT", - "dependencies": { - "inherits": "^2.0.1", - "obuf": "^1.0.0", - "readable-stream": "^2.0.1", - "wbuf": "^1.1.0" - } - }, - "node_modules/hpack.js/node_modules/isarray": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", - "integrity": "sha512-VLghIWNM6ELQzo7zwmcg0NmTVyWKYjvIeM83yjp0wRDTmUnrM678fQbcKBo6n2CJEF0szoG//ytg+TKla89ALQ==", - "license": "MIT" - }, - "node_modules/hpack.js/node_modules/readable-stream": { - "version": "2.3.8", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.8.tgz", - "integrity": "sha512-8p0AUk4XODgIewSi0l8Epjs+EVnWiK7NoDIEGU0HhE7+ZyY8D1IMY7odu5lRrFXGg71L15KG8QrPmum45RTtdA==", - "license": "MIT", - "dependencies": { - "core-util-is": "~1.0.0", - "inherits": "~2.0.3", - "isarray": "~1.0.0", - "process-nextick-args": "~2.0.0", - "safe-buffer": "~5.1.1", - "string_decoder": "~1.1.1", - "util-deprecate": "~1.0.1" - } - }, - "node_modules/hpack.js/node_modules/safe-buffer": { - "version": "5.1.2", - "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz", - "integrity": "sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==", - "license": "MIT" - }, - "node_modules/hpack.js/node_modules/string_decoder": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.1.1.tgz", - "integrity": "sha512-n/ShnvDi6FHbbVfviro+WojiFzv+s8MPMHBczVePfUpDJLwoLT0ht1l4YwBCbi8pJAveEEdnkHyPyTP/mzRfwg==", - "license": "MIT", - "dependencies": { - "safe-buffer": "~5.1.0" - } - }, - "node_modules/html-entities": { - "version": "2.5.2", - "resolved": "https://registry.npmjs.org/html-entities/-/html-entities-2.5.2.tgz", - "integrity": "sha512-K//PSRMQk4FZ78Kyau+mZurHn3FH0Vwr+H36eE0rPbeYkRRi9YxceYPhuN60UwWorxyKHhqoAJl2OFKa4BVtaA==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/mdevils" - }, - { - "type": "patreon", - "url": "https://patreon.com/mdevils" - } - ], - "license": "MIT" - }, - "node_modules/html-escaper": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/html-escaper/-/html-escaper-2.0.2.tgz", - "integrity": "sha512-H2iMtd0I4Mt5eYiapRdIDjp+XzelXQ0tFE4JS7YFwFevXXMmOp9myNrUvCg0D6ws8iqkRPBfKHgbwig1SmlLfg==", - "license": "MIT" - }, - "node_modules/html-minifier-terser": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/html-minifier-terser/-/html-minifier-terser-7.2.0.tgz", - "integrity": "sha512-tXgn3QfqPIpGl9o+K5tpcj3/MN4SfLtsx2GWwBC3SSd0tXQGyF3gsSqad8loJgKZGM3ZxbYDd5yhiBIdWpmvLA==", - "license": "MIT", - "dependencies": { - "camel-case": "^4.1.2", - "clean-css": "~5.3.2", - "commander": "^10.0.0", - "entities": "^4.4.0", - "param-case": "^3.0.4", - "relateurl": "^0.2.7", - "terser": "^5.15.1" - }, - "bin": { - "html-minifier-terser": "cli.js" - }, - "engines": { - "node": "^14.13.1 || >=16.0.0" - } - }, - "node_modules/html-minifier-terser/node_modules/commander": { - "version": "10.0.1", - "resolved": "https://registry.npmjs.org/commander/-/commander-10.0.1.tgz", - "integrity": "sha512-y4Mg2tXshplEbSGzx7amzPwKKOCGuoSRP/CjEdwwk0FOGlUbq6lKuoyDZTNZkmxHdJtp54hdfY/JUrdL7Xfdug==", - "license": "MIT", - "engines": { - "node": ">=14" - } - }, - "node_modules/html-tags": { - "version": "3.3.1", - "resolved": "https://registry.npmjs.org/html-tags/-/html-tags-3.3.1.tgz", - "integrity": "sha512-ztqyC3kLto0e9WbNp0aeP+M3kTt+nbaIveGmUxAtZa+8iFgKLUOD4YKM5j+f3QD89bra7UeumolZHKuOXnTmeQ==", - "license": "MIT", - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/html-void-elements": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/html-void-elements/-/html-void-elements-3.0.0.tgz", - "integrity": "sha512-bEqo66MRXsUGxWHV5IP0PUiAWwoEjba4VCzg0LjFJBpchPaTfyfCKTG6bc5F8ucKec3q5y6qOdGyYTSBEvhCrg==", - "license": "MIT", - "funding": { - "type": "github", - "url": "https://github.com/sponsors/wooorm" - } - }, - "node_modules/html-webpack-plugin": { - "version": "5.6.0", - "resolved": "https://registry.npmjs.org/html-webpack-plugin/-/html-webpack-plugin-5.6.0.tgz", - "integrity": "sha512-iwaY4wzbe48AfKLZ/Cc8k0L+FKG6oSNRaZ8x5A/T/IVDGyXcbHncM9TdDa93wn0FsSm82FhTKW7f3vS61thXAw==", - "license": "MIT", - "dependencies": { - "@types/html-minifier-terser": "^6.0.0", - "html-minifier-terser": "^6.0.2", - "lodash": "^4.17.21", - "pretty-error": "^4.0.0", - "tapable": "^2.0.0" - }, - "engines": { - "node": ">=10.13.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/html-webpack-plugin" - }, - "peerDependencies": { - "@rspack/core": "0.x || 1.x", - "webpack": "^5.20.0" - }, - "peerDependenciesMeta": { - "@rspack/core": { - "optional": true - }, - "webpack": { - "optional": true - } - } - }, - "node_modules/html-webpack-plugin/node_modules/commander": { - "version": "8.3.0", - "resolved": "https://registry.npmjs.org/commander/-/commander-8.3.0.tgz", - "integrity": "sha512-OkTL9umf+He2DZkUq8f8J9of7yL6RJKI24dVITBmNfZBmri9zYZQrKkuXiKhyfPSu8tUhnVBB1iKXevvnlR4Ww==", - "license": "MIT", - "engines": { - "node": ">= 12" - } - }, - "node_modules/html-webpack-plugin/node_modules/html-minifier-terser": { - "version": "6.1.0", - "resolved": "https://registry.npmjs.org/html-minifier-terser/-/html-minifier-terser-6.1.0.tgz", - "integrity": "sha512-YXxSlJBZTP7RS3tWnQw74ooKa6L9b9i9QYXY21eUEvhZ3u9XLfv6OnFsQq6RxkhHygsaUMvYsZRV5rU/OVNZxw==", - "license": "MIT", - "dependencies": { - "camel-case": "^4.1.2", - "clean-css": "^5.2.2", - "commander": "^8.3.0", - "he": "^1.2.0", - "param-case": "^3.0.4", - "relateurl": "^0.2.7", - "terser": "^5.10.0" - }, - "bin": { - "html-minifier-terser": "cli.js" - }, - "engines": { - "node": ">=12" - } - }, - "node_modules/htmlparser2": { - "version": "8.0.2", - "resolved": "https://registry.npmjs.org/htmlparser2/-/htmlparser2-8.0.2.tgz", - "integrity": "sha512-GYdjWKDkbRLkZ5geuHs5NY1puJ+PXwP7+fHPRz06Eirsb9ugf6d8kkXav6ADhcODhFFPMIXyxkxSuMf3D6NCFA==", - "funding": [ - "https://github.com/fb55/htmlparser2?sponsor=1", - { - "type": "github", - "url": "https://github.com/sponsors/fb55" - } - ], - "license": "MIT", - "dependencies": { - "domelementtype": "^2.3.0", - "domhandler": "^5.0.3", - "domutils": "^3.0.1", - "entities": "^4.4.0" - } - }, - "node_modules/http-cache-semantics": { - "version": "4.1.1", - "resolved": "https://registry.npmjs.org/http-cache-semantics/-/http-cache-semantics-4.1.1.tgz", - "integrity": "sha512-er295DKPVsV82j5kw1Gjt+ADA/XYHsajl82cGNQG2eyoPkvgUhX+nDIyelzhIWbbsXP39EHcI6l5tYs2FYqYXQ==", - "license": "BSD-2-Clause" - }, - "node_modules/http-deceiver": { - "version": "1.2.7", - "resolved": "https://registry.npmjs.org/http-deceiver/-/http-deceiver-1.2.7.tgz", - "integrity": "sha512-LmpOGxTfbpgtGVxJrj5k7asXHCgNZp5nLfp+hWc8QQRqtb7fUy6kRY3BO1h9ddF6yIPYUARgxGOwB42DnxIaNw==", - "license": "MIT" - }, - "node_modules/http-errors": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/http-errors/-/http-errors-2.0.0.tgz", - "integrity": "sha512-FtwrG/euBzaEjYeRqOgly7G0qviiXoJWnvEH2Z1plBdXgbyjv34pHTSb9zoeHMyDy33+DWy5Wt9Wo+TURtOYSQ==", - "dependencies": { - "depd": "2.0.0", - "inherits": "2.0.4", - "setprototypeof": "1.2.0", - "statuses": "2.0.1", - "toidentifier": "1.0.1" - }, - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/http-parser-js": { - "version": "0.5.8", - "resolved": "https://registry.npmjs.org/http-parser-js/-/http-parser-js-0.5.8.tgz", - "integrity": "sha512-SGeBX54F94Wgu5RH3X5jsDtf4eHyRogWX1XGT3b4HuW3tQPM4AaBzoUji/4AAJNXCEOWZ5O0DgZmJw1947gD5Q==", - "license": "MIT" - }, - "node_modules/http-proxy": { - "version": "1.18.1", - "resolved": "https://registry.npmjs.org/http-proxy/-/http-proxy-1.18.1.tgz", - "integrity": "sha512-7mz/721AbnJwIVbnaSv1Cz3Am0ZLT/UBwkC92VlxhXv/k/BBQfM2fXElQNC27BVGr0uwUpplYPQM9LnaBMR5NQ==", - "license": "MIT", - "dependencies": { - "eventemitter3": "^4.0.0", - "follow-redirects": "^1.0.0", - "requires-port": "^1.0.0" - }, - "engines": { - "node": ">=8.0.0" - } - }, - "node_modules/http-proxy-middleware": { - "version": "2.0.7", - "resolved": "https://registry.npmjs.org/http-proxy-middleware/-/http-proxy-middleware-2.0.7.tgz", - "integrity": "sha512-fgVY8AV7qU7z/MmXJ/rxwbrtQH4jBQ9m7kp3llF0liB7glmFeVZFBepQb32T3y8n8k2+AEYuMPCpinYW+/CuRA==", - "license": "MIT", - "dependencies": { - "@types/http-proxy": "^1.17.8", - "http-proxy": "^1.18.1", - "is-glob": "^4.0.1", - "is-plain-obj": "^3.0.0", - "micromatch": "^4.0.2" - }, - "engines": { - "node": ">=12.0.0" - }, - "peerDependencies": { - "@types/express": "^4.17.13" - }, - "peerDependenciesMeta": { - "@types/express": { - "optional": true - } - } - }, - "node_modules/http-proxy-middleware/node_modules/is-plain-obj": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/is-plain-obj/-/is-plain-obj-3.0.0.tgz", - "integrity": "sha512-gwsOE28k+23GP1B6vFl1oVh/WOzmawBrKwo5Ev6wMKzPkaXaCDIQKzLnvsA42DRlbVTWorkgTKIviAKCWkfUwA==", - "license": "MIT", - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/http-reasons": { - "version": "0.1.0", - "resolved": "https://registry.npmjs.org/http-reasons/-/http-reasons-0.1.0.tgz", - "integrity": "sha512-P6kYh0lKZ+y29T2Gqz+RlC9WBLhKe8kDmcJ+A+611jFfxdPsbMRQ5aNmFRM3lENqFkK+HTTL+tlQviAiv0AbLQ==", - "license": "Apache-2.0" - }, - "node_modules/http2-client": { - "version": "1.3.5", - "resolved": "https://registry.npmjs.org/http2-client/-/http2-client-1.3.5.tgz", - "integrity": "sha512-EC2utToWl4RKfs5zd36Mxq7nzHHBuomZboI0yYL6Y0RmBgT7Sgkq4rQ0ezFTYoIsSs7Tm9SJe+o2FcAg6GBhGA==", - "license": "MIT" - }, - "node_modules/http2-wrapper": { - "version": "2.2.1", - "resolved": "https://registry.npmjs.org/http2-wrapper/-/http2-wrapper-2.2.1.tgz", - "integrity": "sha512-V5nVw1PAOgfI3Lmeaj2Exmeg7fenjhRUgz1lPSezy1CuhPYbgQtbQj4jZfEAEMlaL+vupsvhjqCyjzob0yxsmQ==", - "license": "MIT", - "dependencies": { - "quick-lru": "^5.1.1", - "resolve-alpn": "^1.2.0" - }, - "engines": { - "node": ">=10.19.0" - } - }, - "node_modules/https-browserify": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/https-browserify/-/https-browserify-1.0.0.tgz", - "integrity": "sha512-J+FkSdyD+0mA0N+81tMotaRMfSL9SGi+xpD3T6YApKsc3bGSXJlfXri3VyFOeYkfLRQisDk1W+jIFFKBeUBbBg==", - "license": "MIT" - }, - "node_modules/https-proxy-agent": { - "version": "7.0.5", - "resolved": "https://registry.npmjs.org/https-proxy-agent/-/https-proxy-agent-7.0.5.tgz", - "integrity": "sha512-1e4Wqeblerz+tMKPIq2EMGiiWW1dIjZOksyHWSUm1rmuvw/how9hBHZ38lAGj5ID4Ik6EdkOw7NmWPy6LAwalw==", - "license": "MIT", - "dependencies": { - "agent-base": "^7.0.2", - "debug": "4" - }, - "engines": { - "node": ">= 14" - } - }, - "node_modules/human-signals": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/human-signals/-/human-signals-2.1.0.tgz", - "integrity": "sha512-B4FFZ6q/T2jhhksgkbEW3HBvWIfDW85snkQgawt07S7J5QXTk6BkNV+0yAeZrM5QpMAdYlocGoljn0sJ/WQkFw==", - "license": "Apache-2.0", - "engines": { - "node": ">=10.17.0" - } - }, - "node_modules/iconv-lite": { - "version": "0.4.24", - "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.4.24.tgz", - "integrity": "sha512-v3MXnZAcvnywkTUEZomIActle7RXXeedOR31wwl7VlyoXO4Qi9arvSenNQWne1TcRwhCL1HwLI21bEqdpj8/rA==", - "dependencies": { - "safer-buffer": ">= 2.1.2 < 3" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/icss-utils": { - "version": "5.1.0", - "resolved": "https://registry.npmjs.org/icss-utils/-/icss-utils-5.1.0.tgz", - "integrity": "sha512-soFhflCVWLfRNOPU3iv5Z9VUdT44xFRbzjLsEzSr5AQmgqPMTHdU3PMT1Cf1ssx8fLNJDA1juftYl+PUcv3MqA==", - "license": "ISC", - "engines": { - "node": "^10 || ^12 || >= 14" - }, - "peerDependencies": { - "postcss": "^8.1.0" - } - }, - "node_modules/ieee754": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/ieee754/-/ieee754-1.2.1.tgz", - "integrity": "sha512-dcyqhDvX1C46lXZcVqCpK+FtMRQVdIMN6/Df5js2zouUsqG7I6sFxitIC+7KYK29KdXOLHdu9zL4sFnoVQnqaA==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/feross" - }, - { - "type": "patreon", - "url": "https://www.patreon.com/feross" - }, - { - "type": "consulting", - "url": "https://feross.org/support" - } - ], - "license": "BSD-3-Clause" - }, - "node_modules/ignore": { - "version": "5.3.1", - "resolved": "https://registry.npmjs.org/ignore/-/ignore-5.3.1.tgz", - "integrity": "sha512-5Fytz/IraMjqpwfd34ke28PTVMjZjJG2MPn5t7OE4eUCUNf8BAa7b5WUS9/Qvr6mwOQS7Mk6vdsMno5he+T8Xw==", - "license": "MIT", - "engines": { - "node": ">= 4" - } - }, - "node_modules/ignore-by-default": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/ignore-by-default/-/ignore-by-default-1.0.1.tgz", - "integrity": "sha512-Ius2VYcGNk7T90CppJqcIkS5ooHUZyIQK+ClZfMfMNFEF9VSE73Fq+906u/CWu92x4gzZMWOwfFYckPObzdEbA==", - "dev": true, - "license": "ISC" - }, - "node_modules/image-size": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/image-size/-/image-size-1.1.1.tgz", - "integrity": "sha512-541xKlUw6jr/6gGuk92F+mYM5zaFAc5ahphvkqvNe2bQ6gVBkd6bfrmVJ2t4KDAfikAYZyIqTnktX3i6/aQDrQ==", - "license": "MIT", - "dependencies": { - "queue": "6.0.2" - }, - "bin": { - "image-size": "bin/image-size.js" - }, - "engines": { - "node": ">=16.x" - } - }, - "node_modules/immer": { - "version": "9.0.21", - "resolved": "https://registry.npmjs.org/immer/-/immer-9.0.21.tgz", - "integrity": "sha512-bc4NBHqOqSfRW7POMkHd51LvClaeMXpm8dx0e8oE2GORbq5aRK7Bxl4FyzVLdGtLmvLKL7BTDBG5ACQm4HWjTA==", - "license": "MIT", - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/immer" - } - }, - "node_modules/immutable": { - "version": "5.0.2", - "resolved": "https://registry.npmjs.org/immutable/-/immutable-5.0.2.tgz", - "integrity": "sha512-1NU7hWZDkV7hJ4PJ9dur9gTNQ4ePNPN4k9/0YhwjzykTi/+3Q5pF93YU5QoVj8BuOnhLgaY8gs0U2pj4kSYVcw==", - "license": "MIT" - }, - "node_modules/import-fresh": { - "version": "3.3.0", - "resolved": "https://registry.npmjs.org/import-fresh/-/import-fresh-3.3.0.tgz", - "integrity": "sha512-veYYhQa+D1QBKznvhUHxb8faxlrwUnxseDAbAp457E0wLNio2bOSKnjYDhMj+YiAq61xrMGhQk9iXVk5FzgQMw==", - "license": "MIT", - "dependencies": { - "parent-module": "^1.0.0", - "resolve-from": "^4.0.0" - }, - "engines": { - "node": ">=6" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/import-lazy": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/import-lazy/-/import-lazy-4.0.0.tgz", - "integrity": "sha512-rKtvo6a868b5Hu3heneU+L4yEQ4jYKLtjpnPeUdK7h0yzXGmyBTypknlkCvHFBqfX9YlorEiMM6Dnq/5atfHkw==", - "license": "MIT", - "engines": { - "node": ">=8" - } - }, - "node_modules/imurmurhash": { - "version": "0.1.4", - "resolved": "https://registry.npmjs.org/imurmurhash/-/imurmurhash-0.1.4.tgz", - "integrity": "sha512-JmXMZ6wuvDmLiHEml9ykzqO6lwFbof0GG4IkcGaENdCRDDmMVnny7s5HsIgHCbaq0w2MyPhDqkhTUgS2LU2PHA==", - "license": "MIT", - "engines": { - "node": ">=0.8.19" - } - }, - "node_modules/indent-string": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/indent-string/-/indent-string-4.0.0.tgz", - "integrity": "sha512-EdDDZu4A2OyIK7Lr/2zG+w5jmbuk1DVBnEwREQvBzspBJkCEbRa8GxU1lghYcaGJCnRWibjDXlq779X1/y5xwg==", - "license": "MIT", - "engines": { - "node": ">=8" - } - }, - "node_modules/infima": { - "version": "0.2.0-alpha.45", - "resolved": "https://registry.npmjs.org/infima/-/infima-0.2.0-alpha.45.tgz", - "integrity": "sha512-uyH0zfr1erU1OohLk0fT4Rrb94AOhguWNOcD9uGrSpRvNB+6gZXUoJX5J0NtvzBO10YZ9PgvA4NFgt+fYg8ojw==", - "license": "MIT", - "engines": { - "node": ">=12" - } - }, - "node_modules/inflight": { - "version": "1.0.6", - "resolved": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", - "integrity": "sha512-k92I/b08q4wvFscXCLvqfsHCrjrF7yiXsQuIVvVE7N82W3+aqpzuUdBbfhWcy/FZR3/4IgflMgKLOsvPDrGCJA==", - "deprecated": "This module is not supported, and leaks memory. Do not use it. Check out lru-cache if you want a good and tested way to coalesce async requests by a key value, which is much more comprehensive and powerful.", - "license": "ISC", - "dependencies": { - "once": "^1.3.0", - "wrappy": "1" - } - }, - "node_modules/inherits": { - "version": "2.0.4", - "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.4.tgz", - "integrity": "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==", - "license": "ISC" - }, - "node_modules/ini": { - "version": "1.3.8", - "resolved": "https://registry.npmjs.org/ini/-/ini-1.3.8.tgz", - "integrity": "sha512-JV/yugV2uzW5iMRSiZAyDtQd+nxtUnjeLt0acNdw98kKLrvuRVyB80tsREOE7yvGVgalhZ6RNXCmEHkUKBKxew==", - "license": "ISC" - }, - "node_modules/inline-style-parser": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/inline-style-parser/-/inline-style-parser-0.1.1.tgz", - "integrity": "sha512-7NXolsK4CAS5+xvdj5OMMbI962hU/wvwoxk+LWR9Ek9bVtyuuYScDN6eS0rUm6TxApFpw7CX1o4uJzcd4AyD3Q==", - "license": "MIT" - }, - "node_modules/interpret": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/interpret/-/interpret-1.4.0.tgz", - "integrity": "sha512-agE4QfB2Lkp9uICn7BAqoscw4SZP9kTE2hxiFI3jBPmXJfdqiahTbUuKGsMoN2GtqL9AxhYioAcVvgsb1HvRbA==", - "license": "MIT", - "engines": { - "node": ">= 0.10" - } - }, - "node_modules/invariant": { - "version": "2.2.4", - "resolved": "https://registry.npmjs.org/invariant/-/invariant-2.2.4.tgz", - "integrity": "sha512-phJfQVBuaJM5raOpJjSfkiD6BpbCE4Ns//LaXl6wGYtUBY83nWS6Rf9tXm2e8VaK60JEjYldbPif/A2B1C2gNA==", - "license": "MIT", - "dependencies": { - "loose-envify": "^1.0.0" - } - }, - "node_modules/ipaddr.js": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/ipaddr.js/-/ipaddr.js-2.2.0.tgz", - "integrity": "sha512-Ag3wB2o37wslZS19hZqorUnrnzSkpOVy+IiiDEiTqNubEYpYuHWIf6K4psgN2ZWKExS4xhVCrRVfb/wfW8fWJA==", - "license": "MIT", - "engines": { - "node": ">= 10" - } - }, - "node_modules/is-alphabetical": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/is-alphabetical/-/is-alphabetical-2.0.1.tgz", - "integrity": "sha512-FWyyY60MeTNyeSRpkM2Iry0G9hpr7/9kD40mD/cGQEuilcZYS4okz8SN2Q6rLCJ8gbCt6fN+rC+6tMGS99LaxQ==", - "license": "MIT", - "funding": { - "type": "github", - "url": "https://github.com/sponsors/wooorm" - } - }, - "node_modules/is-alphanumerical": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/is-alphanumerical/-/is-alphanumerical-2.0.1.tgz", - "integrity": "sha512-hmbYhX/9MUMF5uh7tOXyK/n0ZvWpad5caBA17GsC6vyuCqaWliRG5K1qS9inmUhEMaOBIW7/whAnSwveW/LtZw==", - "license": "MIT", - "dependencies": { - "is-alphabetical": "^2.0.0", - "is-decimal": "^2.0.0" - }, - "funding": { - "type": "github", - "url": "https://github.com/sponsors/wooorm" - } - }, - "node_modules/is-arguments": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/is-arguments/-/is-arguments-1.1.1.tgz", - "integrity": "sha512-8Q7EARjzEnKpt/PCD7e1cgUS0a6X8u5tdSiMqXhojOdoV9TsMsiO+9VLC5vAmO8N7/GmXn7yjR8qnA6bVAEzfA==", - "license": "MIT", - "dependencies": { - "call-bind": "^1.0.2", - "has-tostringtag": "^1.0.0" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/is-arrayish": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/is-arrayish/-/is-arrayish-0.2.1.tgz", - "integrity": "sha512-zz06S8t0ozoDXMG+ube26zeCTNXcKIPJZJi8hBrF4idCLms4CG9QtK7qBl1boi5ODzFpjswb5JPmHCbMpjaYzg==", - "license": "MIT" - }, - "node_modules/is-binary-path": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/is-binary-path/-/is-binary-path-2.1.0.tgz", - "integrity": "sha512-ZMERYes6pDydyuGidse7OsHxtbI7WVeUEozgR/g7rd0xUimYNlvZRE/K2MgZTjWy725IfelLeVcEM97mmtRGXw==", - "license": "MIT", - "dependencies": { - "binary-extensions": "^2.0.0" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/is-buffer": { - "version": "2.0.5", - "resolved": "https://registry.npmjs.org/is-buffer/-/is-buffer-2.0.5.tgz", - "integrity": "sha512-i2R6zNFDwgEHJyQUtJEk0XFi1i0dPFn/oqjK3/vPCcDeJvW5NQ83V8QbicfF1SupOaB0h8ntgBC2YiE7dfyctQ==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/feross" - }, - { - "type": "patreon", - "url": "https://www.patreon.com/feross" - }, - { - "type": "consulting", - "url": "https://feross.org/support" - } - ], - "license": "MIT", - "engines": { - "node": ">=4" - } - }, - "node_modules/is-callable": { - "version": "1.2.7", - "resolved": "https://registry.npmjs.org/is-callable/-/is-callable-1.2.7.tgz", - "integrity": "sha512-1BC0BVFhS/p0qtw6enp8e+8OD0UrK0oFLztSjNzhcKA3WDuJxxAPXzPuPtKkjEY9UUoEWlX/8fgKeu2S8i9JTA==", - "license": "MIT", - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/is-ci": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/is-ci/-/is-ci-3.0.1.tgz", - "integrity": "sha512-ZYvCgrefwqoQ6yTyYUbQu64HsITZ3NfKX1lzaEYdkTDcfKzzCI/wthRRYKkdjHKFVgNiXKAKm65Zo1pk2as/QQ==", - "license": "MIT", - "dependencies": { - "ci-info": "^3.2.0" - }, - "bin": { - "is-ci": "bin.js" - } - }, - "node_modules/is-core-module": { - "version": "2.15.0", - "resolved": "https://registry.npmjs.org/is-core-module/-/is-core-module-2.15.0.tgz", - "integrity": "sha512-Dd+Lb2/zvk9SKy1TGCt1wFJFo/MWBPMX5x7KcvLajWTGuomczdQX61PvY5yK6SVACwpoexWo81IfFyoKY2QnTA==", - "license": "MIT", - "dependencies": { - "hasown": "^2.0.2" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/is-decimal": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/is-decimal/-/is-decimal-2.0.1.tgz", - "integrity": "sha512-AAB9hiomQs5DXWcRB1rqsxGUstbRroFOPPVAomNk/3XHR5JyEZChOyTWe2oayKnsSsr/kcGqF+z6yuH6HHpN0A==", - "license": "MIT", - "funding": { - "type": "github", - "url": "https://github.com/sponsors/wooorm" - } - }, - "node_modules/is-docker": { - "version": "2.2.1", - "resolved": "https://registry.npmjs.org/is-docker/-/is-docker-2.2.1.tgz", - "integrity": "sha512-F+i2BKsFrH66iaUFc0woD8sLy8getkwTwtOBjvs56Cx4CgJDeKQeqfz8wAYiSb8JOprWhHH5p77PbmYCvvUuXQ==", - "license": "MIT", - "bin": { - "is-docker": "cli.js" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/is-extendable": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/is-extendable/-/is-extendable-0.1.1.tgz", - "integrity": "sha512-5BMULNob1vgFX6EjQw5izWDxrecWK9AM72rugNr0TFldMOi0fj6Jk+zeKIt0xGj4cEfQIJth4w3OKWOJ4f+AFw==", - "license": "MIT", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/is-extglob": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-2.1.1.tgz", - "integrity": "sha512-SbKbANkN603Vi4jEZv49LeVJMn4yGwsbzZworEoyEiutsN3nJYdbO36zfhGJ6QEDpOZIFkDtnq5JRxmvl3jsoQ==", - "license": "MIT", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/is-fullwidth-code-point": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-3.0.0.tgz", - "integrity": "sha512-zymm5+u+sCsSWyD9qNaejV3DFvhCKclKdizYaJUuHA83RLjb7nSuGnddCHGv0hk+KY7BMAlsWeK4Ueg6EV6XQg==", - "license": "MIT", - "engines": { - "node": ">=8" - } - }, - "node_modules/is-generator-function": { - "version": "1.0.10", - "resolved": "https://registry.npmjs.org/is-generator-function/-/is-generator-function-1.0.10.tgz", - "integrity": "sha512-jsEjy9l3yiXEQ+PsXdmBwEPcOxaXWLspKdplFUVI9vq1iZgIekeC0L167qeu86czQaxed3q/Uzuw0swL0irL8A==", - "license": "MIT", - "dependencies": { - "has-tostringtag": "^1.0.0" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/is-glob": { - "version": "4.0.3", - "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-4.0.3.tgz", - "integrity": "sha512-xelSayHH36ZgE7ZWhli7pW34hNbNl8Ojv5KVmkJD4hBdD3th8Tfk9vYasLM+mXWOZhFkgZfxhLSnrwRr4elSSg==", - "license": "MIT", - "dependencies": { - "is-extglob": "^2.1.1" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/is-hexadecimal": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/is-hexadecimal/-/is-hexadecimal-2.0.1.tgz", - "integrity": "sha512-DgZQp241c8oO6cA1SbTEWiXeoxV42vlcJxgH+B3hi1AiqqKruZR3ZGF8In3fj4+/y/7rHvlOZLZtgJ/4ttYGZg==", - "license": "MIT", - "funding": { - "type": "github", - "url": "https://github.com/sponsors/wooorm" - } - }, - "node_modules/is-installed-globally": { - "version": "0.4.0", - "resolved": "https://registry.npmjs.org/is-installed-globally/-/is-installed-globally-0.4.0.tgz", - "integrity": "sha512-iwGqO3J21aaSkC7jWnHP/difazwS7SFeIqxv6wEtLU8Y5KlzFTjyqcSIT0d8s4+dDhKytsk9PJZ2BkS5eZwQRQ==", - "license": "MIT", - "dependencies": { - "global-dirs": "^3.0.0", - "is-path-inside": "^3.0.2" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/is-nan": { - "version": "1.3.2", - "resolved": "https://registry.npmjs.org/is-nan/-/is-nan-1.3.2.tgz", - "integrity": "sha512-E+zBKpQ2t6MEo1VsonYmluk9NxGrbzpeeLC2xIViuO2EjU2xsXsBPwTr3Ykv9l08UYEVEdWeRZNouaZqF6RN0w==", - "license": "MIT", - "dependencies": { - "call-bind": "^1.0.0", - "define-properties": "^1.1.3" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/is-npm": { - "version": "6.0.0", - "resolved": "https://registry.npmjs.org/is-npm/-/is-npm-6.0.0.tgz", - "integrity": "sha512-JEjxbSmtPSt1c8XTkVrlujcXdKV1/tvuQ7GwKcAlyiVLeYFQ2VHat8xfrDJsIkhCdF/tZ7CiIR3sy141c6+gPQ==", - "license": "MIT", - "engines": { - "node": "^12.20.0 || ^14.13.1 || >=16.0.0" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/is-number": { - "version": "7.0.0", - "resolved": "https://registry.npmjs.org/is-number/-/is-number-7.0.0.tgz", - "integrity": "sha512-41Cifkg6e8TylSpdtTpeLVMqvSBEVzTttHvERD741+pnZ8ANv0004MRL43QKPDlK9cGvNp6NZWZUBlbGXYxxng==", - "license": "MIT", - "engines": { - "node": ">=0.12.0" - } - }, - "node_modules/is-obj": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/is-obj/-/is-obj-1.0.1.tgz", - "integrity": "sha512-l4RyHgRqGN4Y3+9JHVrNqO+tN0rV5My76uW5/nuO4K1b6vw5G8d/cmFjP9tRfEsdhZNt0IFdZuK/c2Vr4Nb+Qg==", - "license": "MIT", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/is-path-cwd": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/is-path-cwd/-/is-path-cwd-2.2.0.tgz", - "integrity": "sha512-w942bTcih8fdJPJmQHFzkS76NEP8Kzzvmw92cXsazb8intwLqPibPPdXf4ANdKV3rYMuuQYGIWtvz9JilB3NFQ==", - "license": "MIT", - "engines": { - "node": ">=6" - } - }, - "node_modules/is-path-inside": { - "version": "3.0.3", - "resolved": "https://registry.npmjs.org/is-path-inside/-/is-path-inside-3.0.3.tgz", - "integrity": "sha512-Fd4gABb+ycGAmKou8eMftCupSir5lRxqf4aD/vd0cD2qc4HL07OjCeuHMr8Ro4CoMaeCKDB0/ECBOVWjTwUvPQ==", - "license": "MIT", - "engines": { - "node": ">=8" - } - }, - "node_modules/is-plain-obj": { - "version": "4.1.0", - "resolved": "https://registry.npmjs.org/is-plain-obj/-/is-plain-obj-4.1.0.tgz", - "integrity": "sha512-+Pgi+vMuUNkJyExiMBt5IlFoMyKnr5zhJ4Uspz58WOhBF5QoIZkFyNHIbBAtHwzVAgk5RtndVNsDRN61/mmDqg==", - "license": "MIT", - "engines": { - "node": ">=12" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/is-plain-object": { - "version": "2.0.4", - "resolved": "https://registry.npmjs.org/is-plain-object/-/is-plain-object-2.0.4.tgz", - "integrity": "sha512-h5PpgXkWitc38BBMYawTYMWJHFZJVnBquFE57xFpjB8pJFiF6gZ+bU+WyI/yqXiFR5mdLsgYNaPe8uao6Uv9Og==", - "license": "MIT", - "dependencies": { - "isobject": "^3.0.1" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/is-reference": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/is-reference/-/is-reference-3.0.2.tgz", - "integrity": "sha512-v3rht/LgVcsdZa3O2Nqs+NMowLOxeOm7Ay9+/ARQ2F+qEoANRcqrjAZKGN0v8ymUetZGgkp26LTnGT7H0Qo9Pg==", - "license": "MIT", - "dependencies": { - "@types/estree": "*" - } - }, - "node_modules/is-regexp": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-regexp/-/is-regexp-1.0.0.tgz", - "integrity": "sha512-7zjFAPO4/gwyQAAgRRmqeEeyIICSdmCqa3tsVHMdBzaXXRiqopZL4Cyghg/XulGWrtABTpbnYYzzIRffLkP4oA==", - "license": "MIT", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/is-root": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/is-root/-/is-root-2.1.0.tgz", - "integrity": "sha512-AGOriNp96vNBd3HtU+RzFEc75FfR5ymiYv8E553I71SCeXBiMsVDUtdio1OEFvrPyLIQ9tVR5RxXIFe5PUFjMg==", - "license": "MIT", - "engines": { - "node": ">=6" - } - }, - "node_modules/is-stream": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/is-stream/-/is-stream-2.0.1.tgz", - "integrity": "sha512-hFoiJiTl63nn+kstHGBtewWSKnQLpyb155KHheA1l39uvtO9nWIop1p3udqPcUd/xbF1VLMO4n7OI6p7RbngDg==", - "license": "MIT", - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/is-typed-array": { - "version": "1.1.13", - "resolved": "https://registry.npmjs.org/is-typed-array/-/is-typed-array-1.1.13.tgz", - "integrity": "sha512-uZ25/bUAlUY5fR4OKT4rZQEBrzQWYV9ZJYGGsUmEJ6thodVJ1HX64ePQ6Z0qPWP+m+Uq6e9UugrE38jeYsDSMw==", - "license": "MIT", - "dependencies": { - "which-typed-array": "^1.1.14" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/is-typedarray": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-typedarray/-/is-typedarray-1.0.0.tgz", - "integrity": "sha512-cyA56iCMHAh5CdzjJIa4aohJyeO1YbwLi3Jc35MmRU6poroFjIGZzUzupGiRPOjgHg9TLu43xbpwXk523fMxKA==", - "license": "MIT" - }, - "node_modules/is-wsl": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/is-wsl/-/is-wsl-2.2.0.tgz", - "integrity": "sha512-fKzAra0rGJUUBwGBgNkHZuToZcn+TtXHpeCgmkMJMMYx1sQDYaCSyjJBSCa2nH1DGm7s3n1oBnohoVTBaN7Lww==", - "license": "MIT", - "dependencies": { - "is-docker": "^2.0.0" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/is-yarn-global": { - "version": "0.4.1", - "resolved": "https://registry.npmjs.org/is-yarn-global/-/is-yarn-global-0.4.1.tgz", - "integrity": "sha512-/kppl+R+LO5VmhYSEWARUFjodS25D68gvj8W7z0I7OWhUla5xWu8KL6CtB2V0R6yqhnRgbcaREMr4EEM6htLPQ==", - "license": "MIT", - "engines": { - "node": ">=12" - } - }, - "node_modules/isarray": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-0.0.1.tgz", - "integrity": "sha512-D2S+3GLxWH+uhrNEcoh/fnmYeP8E8/zHl644d/jdA0g2uyXvy3sb0qxotE+ne0LtccHknQzWwZEzhak7oJ0COQ==", - "license": "MIT" - }, - "node_modules/isexe": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/isexe/-/isexe-2.0.0.tgz", - "integrity": "sha512-RHxMLp9lnKHGHRng9QFhRCMbYAcVpn69smSGcq3f36xjgVVWThj4qqLbTLlq7Ssj8B+fIQ1EuCEGI2lKsyQeIw==", - "license": "ISC" - }, - "node_modules/isobject": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/isobject/-/isobject-3.0.1.tgz", - "integrity": "sha512-WhB9zCku7EGTj/HQQRz5aUQEUeoQZH2bWcltRErOpymJ4boYE6wL9Tbr23krRPSZ+C5zqNSrSw+Cc7sZZ4b7vg==", - "license": "MIT", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/jackspeak": { - "version": "3.4.3", - "resolved": "https://registry.npmjs.org/jackspeak/-/jackspeak-3.4.3.tgz", - "integrity": "sha512-OGlZQpz2yfahA/Rd1Y8Cd9SIEsqvXkLVoSw/cgwhnhFMDbsQFeZYoJJ7bIZBS9BcamUW96asq/npPWugM+RQBw==", - "license": "BlueOak-1.0.0", - "dependencies": { - "@isaacs/cliui": "^8.0.2" - }, - "funding": { - "url": "https://github.com/sponsors/isaacs" - }, - "optionalDependencies": { - "@pkgjs/parseargs": "^0.11.0" - } - }, - "node_modules/jest-util": { - "version": "29.7.0", - "resolved": "https://registry.npmjs.org/jest-util/-/jest-util-29.7.0.tgz", - "integrity": "sha512-z6EbKajIpqGKU56y5KBUgy1dt1ihhQJgWzUlZHArA/+X2ad7Cb5iF+AK1EWVL/Bo7Rz9uurpqw6SiBCefUbCGA==", - "license": "MIT", - "dependencies": { - "@jest/types": "^29.6.3", - "@types/node": "*", - "chalk": "^4.0.0", - "ci-info": "^3.2.0", - "graceful-fs": "^4.2.9", - "picomatch": "^2.2.3" - }, - "engines": { - "node": "^14.15.0 || ^16.10.0 || >=18.0.0" - } - }, - "node_modules/jest-worker": { - "version": "29.7.0", - "resolved": "https://registry.npmjs.org/jest-worker/-/jest-worker-29.7.0.tgz", - "integrity": "sha512-eIz2msL/EzL9UFTFFx7jBTkeZfku0yUAyZZZmJ93H2TYEiroIx2PQjEXcwYtYl8zXCxb+PAmA2hLIt/6ZEkPHw==", - "license": "MIT", - "dependencies": { - "@types/node": "*", - "jest-util": "^29.7.0", - "merge-stream": "^2.0.0", - "supports-color": "^8.0.0" - }, - "engines": { - "node": "^14.15.0 || ^16.10.0 || >=18.0.0" - } - }, - "node_modules/jest-worker/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==", - "license": "MIT", - "dependencies": { - "has-flag": "^4.0.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/chalk/supports-color?sponsor=1" - } - }, - "node_modules/jiti": { - "version": "1.21.6", - "resolved": "https://registry.npmjs.org/jiti/-/jiti-1.21.6.tgz", - "integrity": "sha512-2yTgeWTWzMWkHu6Jp9NKgePDaYHbntiwvYuuJLbbN9vl7DC9DvXKOB2BC3ZZ92D3cvV/aflH0osDfwpHepQ53w==", - "license": "MIT", - "bin": { - "jiti": "bin/jiti.js" - } - }, - "node_modules/joi": { - "version": "17.13.3", - "resolved": "https://registry.npmjs.org/joi/-/joi-17.13.3.tgz", - "integrity": "sha512-otDA4ldcIx+ZXsKHWmp0YizCweVRZG96J10b0FevjfuncLO1oX59THoAmHkNubYJ+9gWsYsp5k8v4ib6oDv1fA==", - "license": "BSD-3-Clause", - "dependencies": { - "@hapi/hoek": "^9.3.0", - "@hapi/topo": "^5.1.0", - "@sideway/address": "^4.1.5", - "@sideway/formula": "^3.0.1", - "@sideway/pinpoint": "^2.0.0" - } - }, - "node_modules/js-cookie": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/js-cookie/-/js-cookie-3.0.1.tgz", - "integrity": "sha512-+0rgsUXZu4ncpPxRL+lNEptWMOWl9etvPHc/koSRp6MPwpRYAhmk0dUG00J4bxVV3r9uUzfo24wW0knS07SKSw==", - "license": "MIT", - "engines": { - "node": ">=12" - } - }, - "node_modules/js-levenshtein": { - "version": "1.1.6", - "resolved": "https://registry.npmjs.org/js-levenshtein/-/js-levenshtein-1.1.6.tgz", - "integrity": "sha512-X2BB11YZtrRqY4EnQcLX5Rh373zbK4alC1FW7D7MBhL2gtcC17cTnr6DmfHZeS0s2rTHjUTMMHfG7gO8SSdw+g==", - "license": "MIT", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/js-tokens": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/js-tokens/-/js-tokens-4.0.0.tgz", - "integrity": "sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ==", - "license": "MIT" - }, - "node_modules/js-yaml": { - "version": "4.1.0", - "resolved": "https://registry.npmjs.org/js-yaml/-/js-yaml-4.1.0.tgz", - "integrity": "sha512-wpxZs9NoxZaJESJGIZTyDEaYpl0FKSA+FB9aJiyemKhMwkxQg63h4T1KJgUGHpTqPDNRcmmYLugrRjJlBtWvRA==", - "license": "MIT", - "dependencies": { - "argparse": "^2.0.1" - }, - "bin": { - "js-yaml": "bin/js-yaml.js" - } - }, - "node_modules/jsesc": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/jsesc/-/jsesc-3.0.2.tgz", - "integrity": "sha512-xKqzzWXDttJuOcawBt4KnKHHIf5oQ/Cxax+0PWFG+DFDgHNAdi+TXECADI+RYiFUMmx8792xsMbbgXj4CwnP4g==", - "license": "MIT", - "bin": { - "jsesc": "bin/jsesc" - }, - "engines": { - "node": ">=6" - } - }, - "node_modules/json-buffer": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/json-buffer/-/json-buffer-3.0.1.tgz", - "integrity": "sha512-4bV5BfR2mqfQTJm+V5tPPdf+ZpuhiIvTuAB5g8kcrXOZpTT/QwwVRWBywX1ozr6lEuPdbHxwaJlm9G6mI2sfSQ==", - "license": "MIT" - }, - "node_modules/json-crawl": { - "version": "0.5.3", - "resolved": "https://registry.npmjs.org/json-crawl/-/json-crawl-0.5.3.tgz", - "integrity": "sha512-BEjjCw8c7SxzNK4orhlWD5cXQh8vCk2LqDr4WgQq4CV+5dvopeYwt1Tskg67SuSLKvoFH5g0yuYtg7rcfKV6YA==", - "license": "MIT", - "engines": { - "node": ">=14.0.0" - } - }, - "node_modules/json-parse-even-better-errors": { - "version": "2.3.1", - "resolved": "https://registry.npmjs.org/json-parse-even-better-errors/-/json-parse-even-better-errors-2.3.1.tgz", - "integrity": "sha512-xyFwyhro/JEof6Ghe2iz2NcXoj2sloNsWr/XsERDK/oiPCfaNhl5ONfp+jQdAZRQQ0IJWNzH9zIZF7li91kh2w==", - "license": "MIT" - }, - "node_modules/json-pointer": { - "version": "0.6.2", - "resolved": "https://registry.npmjs.org/json-pointer/-/json-pointer-0.6.2.tgz", - "integrity": "sha512-vLWcKbOaXlO+jvRy4qNd+TI1QUPZzfJj1tpJ3vAXDych5XJf93ftpUKe5pKCrzyIIwgBJcOcCVRUfqQP25afBw==", - "license": "MIT", - "dependencies": { - "foreach": "^2.0.4" - } - }, - "node_modules/json-schema-compare": { - "version": "0.2.2", - "resolved": "https://registry.npmjs.org/json-schema-compare/-/json-schema-compare-0.2.2.tgz", - "integrity": "sha512-c4WYmDKyJXhs7WWvAWm3uIYnfyWFoIp+JEoX34rctVvEkMYCPGhXtvmFFXiffBbxfZsvQ0RNnV5H7GvDF5HCqQ==", - "license": "MIT", - "dependencies": { - "lodash": "^4.17.4" - } - }, - "node_modules/json-schema-merge-allof": { - "version": "0.8.1", - "resolved": "https://registry.npmjs.org/json-schema-merge-allof/-/json-schema-merge-allof-0.8.1.tgz", - "integrity": "sha512-CTUKmIlPJbsWfzRRnOXz+0MjIqvnleIXwFTzz+t9T86HnYX/Rozria6ZVGLktAU9e+NygNljveP+yxqtQp/Q4w==", - "license": "MIT", - "dependencies": { - "compute-lcm": "^1.1.2", - "json-schema-compare": "^0.2.2", - "lodash": "^4.17.20" - }, - "engines": { - "node": ">=12.0.0" - } - }, - "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==", - "license": "MIT" - }, - "node_modules/json5": { - "version": "2.2.3", - "resolved": "https://registry.npmjs.org/json5/-/json5-2.2.3.tgz", - "integrity": "sha512-XmOWe7eyHYH14cLdVPoyg+GOH3rYX++KpzrylJwSW98t3Nk+U8XOl8FWKOgwtzdb8lXGf6zYwDUzeHMWfxasyg==", - "license": "MIT", - "bin": { - "json5": "lib/cli.js" - }, - "engines": { - "node": ">=6" - } - }, - "node_modules/jsonfile": { - "version": "6.1.0", - "resolved": "https://registry.npmjs.org/jsonfile/-/jsonfile-6.1.0.tgz", - "integrity": "sha512-5dgndWOriYSm5cnYaJNhalLNDKOqFwyDB/rr1E9ZsGciGvKPs8R2xYGCacuf3z6K1YKDz182fd+fY3cn3pMqXQ==", - "license": "MIT", - "dependencies": { - "universalify": "^2.0.0" - }, - "optionalDependencies": { - "graceful-fs": "^4.1.6" - } - }, - "node_modules/keyv": { - "version": "4.5.4", - "resolved": "https://registry.npmjs.org/keyv/-/keyv-4.5.4.tgz", - "integrity": "sha512-oxVHkHR/EJf2CNXnWxRLW6mg7JyCCUcG0DtEGmL2ctUo1PNTin1PUil+r/+4r5MpVgC/fn1kjsx7mjSujKqIpw==", - "license": "MIT", - "dependencies": { - "json-buffer": "3.0.1" - } - }, - "node_modules/kind-of": { - "version": "6.0.3", - "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-6.0.3.tgz", - "integrity": "sha512-dcS1ul+9tmeD95T+x28/ehLgd9mENa3LsvDTtzm3vyBEO7RPptvAD+t44WVXaUjTBRcrpFeFlC8WCruUR456hw==", - "license": "MIT", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/klaw-sync": { - "version": "6.0.0", - "resolved": "https://registry.npmjs.org/klaw-sync/-/klaw-sync-6.0.0.tgz", - "integrity": "sha512-nIeuVSzdCCs6TDPTqI8w1Yre34sSq7AkZ4B3sfOBbI2CgVSB4Du4aLQijFU2+lhAFCwt9+42Hel6lQNIv6AntQ==", - "license": "MIT", - "dependencies": { - "graceful-fs": "^4.1.11" - } - }, - "node_modules/kleur": { - "version": "3.0.3", - "resolved": "https://registry.npmjs.org/kleur/-/kleur-3.0.3.tgz", - "integrity": "sha512-eTIzlVOSUR+JxdDFepEYcBMtZ9Qqdef+rnzWdRZuMbOywu5tO2w2N7rqjoANZ5k9vywhL6Br1VRjUIgTQx4E8w==", - "license": "MIT", - "engines": { - "node": ">=6" - } - }, - "node_modules/klona": { - "version": "2.0.6", - "resolved": "https://registry.npmjs.org/klona/-/klona-2.0.6.tgz", - "integrity": "sha512-dhG34DXATL5hSxJbIexCft8FChFXtmskoZYnoPWjXQuebWYCNkVeV3KkGegCK9CP1oswI/vQibS2GY7Em/sJJA==", - "license": "MIT", - "engines": { - "node": ">= 8" - } - }, - "node_modules/latest-version": { - "version": "7.0.0", - "resolved": "https://registry.npmjs.org/latest-version/-/latest-version-7.0.0.tgz", - "integrity": "sha512-KvNT4XqAMzdcL6ka6Tl3i2lYeFDgXNCuIX+xNx6ZMVR1dFq+idXd9FLKNMOIx0t9mJ9/HudyX4oZWXZQ0UJHeg==", - "license": "MIT", - "dependencies": { - "package-json": "^8.1.0" - }, - "engines": { - "node": ">=14.16" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/launch-editor": { - "version": "2.8.0", - "resolved": "https://registry.npmjs.org/launch-editor/-/launch-editor-2.8.0.tgz", - "integrity": "sha512-vJranOAJrI/llyWGRQqiDM+adrw+k83fvmmx3+nV47g3+36xM15jE+zyZ6Ffel02+xSvuM0b2GDRosXZkbb6wA==", - "license": "MIT", - "dependencies": { - "picocolors": "^1.0.0", - "shell-quote": "^1.8.1" - } - }, - "node_modules/leven": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/leven/-/leven-3.1.0.tgz", - "integrity": "sha512-qsda+H8jTaUaN/x5vzW2rzc+8Rw4TAQ/4KjB46IwK5VH+IlVeeeje/EoZRpiXvIqjFgK84QffqPztGI3VBLG1A==", - "license": "MIT", - "engines": { - "node": ">=6" - } - }, - "node_modules/lilconfig": { - "version": "3.1.3", - "resolved": "https://registry.npmjs.org/lilconfig/-/lilconfig-3.1.3.tgz", - "integrity": "sha512-/vlFKAoH5Cgt3Ie+JLhRbwOsCQePABiU3tJ1egGvyQ+33R/vcwM2Zl2QR/LzjsBeItPt3oSVXapn+m4nQDvpzw==", - "license": "MIT", - "engines": { - "node": ">=14" - }, - "funding": { - "url": "https://github.com/sponsors/antonk52" - } - }, - "node_modules/lines-and-columns": { - "version": "1.2.4", - "resolved": "https://registry.npmjs.org/lines-and-columns/-/lines-and-columns-1.2.4.tgz", - "integrity": "sha512-7ylylesZQ/PV29jhEDl3Ufjo6ZX7gCqJr5F7PKrqc93v7fzSymt1BpwEU8nAUXs8qzzvqhbjhK5QZg6Mt/HkBg==", - "license": "MIT" - }, - "node_modules/liquid-json": { - "version": "0.3.1", - "resolved": "https://registry.npmjs.org/liquid-json/-/liquid-json-0.3.1.tgz", - "integrity": "sha512-wUayTU8MS827Dam6MxgD72Ui+KOSF+u/eIqpatOtjnvgJ0+mnDq33uC2M7J0tPK+upe/DpUAuK4JUU89iBoNKQ==", - "license": "Apache-2.0", - "engines": { - "node": ">=4" - } - }, - "node_modules/loader-runner": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/loader-runner/-/loader-runner-4.3.0.tgz", - "integrity": "sha512-3R/1M+yS3j5ou80Me59j7F9IMs4PXs3VqRrm0TU3AbKPxlmpoY1TNscJV/oGJXo8qCatFGTfDbY6W6ipGOYXfg==", - "license": "MIT", - "engines": { - "node": ">=6.11.5" - } - }, - "node_modules/loader-utils": { - "version": "2.0.4", - "resolved": "https://registry.npmjs.org/loader-utils/-/loader-utils-2.0.4.tgz", - "integrity": "sha512-xXqpXoINfFhgua9xiqD8fPFHgkoq1mmmpE92WlDbm9rNRd/EbRb+Gqf908T2DMfuHjjJlksiK2RbHVOdD/MqSw==", - "license": "MIT", - "dependencies": { - "big.js": "^5.2.2", - "emojis-list": "^3.0.0", - "json5": "^2.1.2" - }, - "engines": { - "node": ">=8.9.0" - } - }, - "node_modules/locate-path": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/locate-path/-/locate-path-7.2.0.tgz", - "integrity": "sha512-gvVijfZvn7R+2qyPX8mAuKcFGDf6Nc61GdvGafQsHL0sBIxfKzA+usWn4GFC/bk+QdwPUD4kWFJLhElipq+0VA==", - "license": "MIT", - "dependencies": { - "p-locate": "^6.0.0" - }, - "engines": { - "node": "^12.20.0 || ^14.13.1 || >=16.0.0" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/lodash": { - "version": "4.17.21", - "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.21.tgz", - "integrity": "sha512-v2kDEe57lecTulaDIuNTPy3Ry4gLGJ6Z1O3vE1krgXZNrsQ+LFTGHVxVjcXPs17LhbZVGedAJv8XZ1tvj5FvSg==", - "license": "MIT" - }, - "node_modules/lodash.debounce": { - "version": "4.0.8", - "resolved": "https://registry.npmjs.org/lodash.debounce/-/lodash.debounce-4.0.8.tgz", - "integrity": "sha512-FT1yDzDYEoYWhnSGnpE/4Kj1fLZkDFyqRb7fNt6FdYOSxlUWAtp42Eh6Wb0rGIv/m9Bgo7x4GhQbm5Ys4SG5ow==", - "license": "MIT" - }, - "node_modules/lodash.isequal": { - "version": "4.5.0", - "resolved": "https://registry.npmjs.org/lodash.isequal/-/lodash.isequal-4.5.0.tgz", - "integrity": "sha512-pDo3lu8Jhfjqls6GkMgpahsF9kCyayhgykjyLMNFTKWrpVdAQtYyB4muAMWozBB4ig/dtWAmsMxLEI8wuz+DYQ==", - "license": "MIT" - }, - "node_modules/lodash.memoize": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/lodash.memoize/-/lodash.memoize-4.1.2.tgz", - "integrity": "sha512-t7j+NzmgnQzTAYXcsHYLgimltOV1MXHtlOWf6GjL9Kj8GK5FInw5JotxvbOs+IvV1/Dzo04/fCGfLVs7aXb4Ag==", - "license": "MIT" - }, - "node_modules/lodash.uniq": { - "version": "4.5.0", - "resolved": "https://registry.npmjs.org/lodash.uniq/-/lodash.uniq-4.5.0.tgz", - "integrity": "sha512-xfBaXQd9ryd9dlSDvnvI0lvxfLJlYAZzXomUYzLKtUeOQvOP5piqAWuGtrhWeqaXK9hhoM/iyJc5AV+XfsX3HQ==", - "license": "MIT" - }, - "node_modules/longest-streak": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/longest-streak/-/longest-streak-3.1.0.tgz", - "integrity": "sha512-9Ri+o0JYgehTaVBBDoMqIl8GXtbWg711O3srftcHhZ0dqnETqLaoIK0x17fUw9rFSlK/0NlsKe0Ahhyl5pXE2g==", - "license": "MIT", - "funding": { - "type": "github", - "url": "https://github.com/sponsors/wooorm" - } - }, - "node_modules/loose-envify": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/loose-envify/-/loose-envify-1.4.0.tgz", - "integrity": "sha512-lyuxPGr/Wfhrlem2CL/UcnUc1zcqKAImBDzukY7Y5F/yQiNdko6+fRLevlw1HgMySw7f611UIY408EtxRSoK3Q==", - "license": "MIT", - "dependencies": { - "js-tokens": "^3.0.0 || ^4.0.0" - }, - "bin": { - "loose-envify": "cli.js" - } - }, - "node_modules/lower-case": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/lower-case/-/lower-case-2.0.2.tgz", - "integrity": "sha512-7fm3l3NAF9WfN6W3JOmf5drwpVqX78JtoGJ3A6W0a6ZnldM41w2fV5D490psKFTpMds8TJse/eHLFFsNHHjHgg==", - "license": "MIT", - "dependencies": { - "tslib": "^2.0.3" - } - }, - "node_modules/lowercase-keys": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/lowercase-keys/-/lowercase-keys-3.0.0.tgz", - "integrity": "sha512-ozCC6gdQ+glXOQsveKD0YsDy8DSQFjDTz4zyzEHNV5+JP5D62LmfDZ6o1cycFx9ouG940M5dE8C8CTewdj2YWQ==", - "license": "MIT", - "engines": { - "node": "^12.20.0 || ^14.13.1 || >=16.0.0" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/lru-cache": { - "version": "5.1.1", - "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-5.1.1.tgz", - "integrity": "sha512-KpNARQA3Iwv+jTA0utUVVbrh+Jlrr1Fv0e56GGzAFOXN7dk/FviaDW8LHmK52DlcH4WP2n6gI8vN1aesBFgo9w==", - "license": "ISC", - "dependencies": { - "yallist": "^3.0.2" - } - }, - "node_modules/lunr": { - "version": "2.3.9", - "resolved": "https://registry.npmjs.org/lunr/-/lunr-2.3.9.tgz", - "integrity": "sha512-zTU3DaZaF3Rt9rhN3uBMGQD3dD2/vFQqnvZCDv4dl5iOzq2IZQqTxu90r4E5J+nP70J3ilqVCrbho2eWaeW8Ow==", - "license": "MIT" - }, - "node_modules/mark.js": { - "version": "8.11.1", - "resolved": "https://registry.npmjs.org/mark.js/-/mark.js-8.11.1.tgz", - "integrity": "sha512-1I+1qpDt4idfgLQG+BNWmrqku+7/2bi5nLf4YwF8y8zXvmfiTBY3PV3ZibfrjBueCByROpuBjLLFCajqkgYoLQ==", - "license": "MIT" - }, - "node_modules/markdown-extensions": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/markdown-extensions/-/markdown-extensions-2.0.0.tgz", - "integrity": "sha512-o5vL7aDWatOTX8LzaS1WMoaoxIiLRQJuIKKe2wAw6IeULDHaqbiqiggmx+pKvZDb1Sj+pE46Sn1T7lCqfFtg1Q==", - "license": "MIT", - "engines": { - "node": ">=16" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/markdown-table": { - "version": "3.0.4", - "resolved": "https://registry.npmjs.org/markdown-table/-/markdown-table-3.0.4.tgz", - "integrity": "sha512-wiYz4+JrLyb/DqW2hkFJxP7Vd7JuTDm77fvbM8VfEQdmSMqcImWeeRbHwZjBjIFki/VaMK2BhFi7oUUZeM5bqw==", - "license": "MIT", - "funding": { - "type": "github", - "url": "https://github.com/sponsors/wooorm" - } - }, - "node_modules/md5.js": { - "version": "1.3.5", - "resolved": "https://registry.npmjs.org/md5.js/-/md5.js-1.3.5.tgz", - "integrity": "sha512-xitP+WxNPcTTOgnTJcrhM0xvdPepipPSf3I8EIpGKeFLjt3PlJLIDG3u8EX53ZIubkb+5U2+3rELYpEhHhzdkg==", - "license": "MIT", - "dependencies": { - "hash-base": "^3.0.0", - "inherits": "^2.0.1", - "safe-buffer": "^5.1.2" - } - }, - "node_modules/mdast-util-definitions": { - "version": "5.1.2", - "resolved": "https://registry.npmjs.org/mdast-util-definitions/-/mdast-util-definitions-5.1.2.tgz", - "integrity": "sha512-8SVPMuHqlPME/z3gqVwWY4zVXn8lqKv/pAhC57FuJ40ImXyBpmO5ukh98zB2v7Blql2FiHjHv9LVztSIqjY+MA==", - "license": "MIT", - "dependencies": { - "@types/mdast": "^3.0.0", - "@types/unist": "^2.0.0", - "unist-util-visit": "^4.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/mdast-util-definitions/node_modules/@types/mdast": { - "version": "3.0.15", - "resolved": "https://registry.npmjs.org/@types/mdast/-/mdast-3.0.15.tgz", - "integrity": "sha512-LnwD+mUEfxWMa1QpDraczIn6k0Ee3SMicuYSSzS6ZYl2gKS09EClnJYGd8Du6rfc5r/GZEk5o1mRb8TaTj03sQ==", - "license": "MIT", - "dependencies": { - "@types/unist": "^2" - } - }, - "node_modules/mdast-util-definitions/node_modules/@types/unist": { - "version": "2.0.11", - "resolved": "https://registry.npmjs.org/@types/unist/-/unist-2.0.11.tgz", - "integrity": "sha512-CmBKiL6NNo/OqgmMn95Fk9Whlp2mtvIv+KNpQKN2F4SjvrEesubTRWGYSg+BnWZOnlCaSTU1sMpsBOzgbYhnsA==", - "license": "MIT" - }, - "node_modules/mdast-util-definitions/node_modules/unist-util-is": { - "version": "5.2.1", - "resolved": "https://registry.npmjs.org/unist-util-is/-/unist-util-is-5.2.1.tgz", - "integrity": "sha512-u9njyyfEh43npf1M+yGKDGVPbY/JWEemg5nH05ncKPfi+kBbKBJoTdsogMu33uhytuLlv9y0O7GH7fEdwLdLQw==", - "license": "MIT", - "dependencies": { - "@types/unist": "^2.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/mdast-util-definitions/node_modules/unist-util-visit": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/unist-util-visit/-/unist-util-visit-4.1.2.tgz", - "integrity": "sha512-MSd8OUGISqHdVvfY9TPhyK2VdUrPgxkUtWSuMHF6XAAFuL4LokseigBnZtPnJMu+FbynTkFNnFlyjxpVKujMRg==", - "license": "MIT", - "dependencies": { - "@types/unist": "^2.0.0", - "unist-util-is": "^5.0.0", - "unist-util-visit-parents": "^5.1.1" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/mdast-util-definitions/node_modules/unist-util-visit-parents": { - "version": "5.1.3", - "resolved": "https://registry.npmjs.org/unist-util-visit-parents/-/unist-util-visit-parents-5.1.3.tgz", - "integrity": "sha512-x6+y8g7wWMyQhL1iZfhIPhDAs7Xwbn9nRosDXl7qoPTSCy0yNxnKc+hWokFifWQIDGi154rdUqKvbCa4+1kLhg==", - "license": "MIT", - "dependencies": { - "@types/unist": "^2.0.0", - "unist-util-is": "^5.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/mdast-util-directive": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/mdast-util-directive/-/mdast-util-directive-3.0.0.tgz", - "integrity": "sha512-JUpYOqKI4mM3sZcNxmF/ox04XYFFkNwr0CFlrQIkCwbvH0xzMCqkMqAde9wRd80VAhaUrwFwKm2nxretdT1h7Q==", - "license": "MIT", - "dependencies": { - "@types/mdast": "^4.0.0", - "@types/unist": "^3.0.0", - "devlop": "^1.0.0", - "mdast-util-from-markdown": "^2.0.0", - "mdast-util-to-markdown": "^2.0.0", - "parse-entities": "^4.0.0", - "stringify-entities": "^4.0.0", - "unist-util-visit-parents": "^6.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/mdast-util-find-and-replace": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/mdast-util-find-and-replace/-/mdast-util-find-and-replace-3.0.1.tgz", - "integrity": "sha512-SG21kZHGC3XRTSUhtofZkBzZTJNM5ecCi0SK2IMKmSXR8vO3peL+kb1O0z7Zl83jKtutG4k5Wv/W7V3/YHvzPA==", - "license": "MIT", - "dependencies": { - "@types/mdast": "^4.0.0", - "escape-string-regexp": "^5.0.0", - "unist-util-is": "^6.0.0", - "unist-util-visit-parents": "^6.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/mdast-util-find-and-replace/node_modules/escape-string-regexp": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-5.0.0.tgz", - "integrity": "sha512-/veY75JbMK4j1yjvuUxuVsiS/hr/4iHs9FTT6cgTexxdE0Ly/glccBAkloH/DofkjRbZU3bnoj38mOmhkZ0lHw==", - "license": "MIT", - "engines": { - "node": ">=12" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/mdast-util-from-markdown": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/mdast-util-from-markdown/-/mdast-util-from-markdown-2.0.1.tgz", - "integrity": "sha512-aJEUyzZ6TzlsX2s5B4Of7lN7EQtAxvtradMMglCQDyaTFgse6CmtmdJ15ElnVRlCg1vpNyVtbem0PWzlNieZsA==", - "license": "MIT", - "dependencies": { - "@types/mdast": "^4.0.0", - "@types/unist": "^3.0.0", - "decode-named-character-reference": "^1.0.0", - "devlop": "^1.0.0", - "mdast-util-to-string": "^4.0.0", - "micromark": "^4.0.0", - "micromark-util-decode-numeric-character-reference": "^2.0.0", - "micromark-util-decode-string": "^2.0.0", - "micromark-util-normalize-identifier": "^2.0.0", - "micromark-util-symbol": "^2.0.0", - "micromark-util-types": "^2.0.0", - "unist-util-stringify-position": "^4.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/mdast-util-from-markdown/node_modules/micromark-util-symbol": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/micromark-util-symbol/-/micromark-util-symbol-2.0.0.tgz", - "integrity": "sha512-8JZt9ElZ5kyTnO94muPxIGS8oyElRJaiJO8EzV6ZSyGQ1Is8xwl4Q45qU5UOg+bGH4AikWziz0iN4sFLWs8PGw==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT" - }, - "node_modules/mdast-util-frontmatter": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/mdast-util-frontmatter/-/mdast-util-frontmatter-2.0.1.tgz", - "integrity": "sha512-LRqI9+wdgC25P0URIJY9vwocIzCcksduHQ9OF2joxQoyTNVduwLAFUzjoopuRJbJAReaKrNQKAZKL3uCMugWJA==", - "license": "MIT", - "dependencies": { - "@types/mdast": "^4.0.0", - "devlop": "^1.0.0", - "escape-string-regexp": "^5.0.0", - "mdast-util-from-markdown": "^2.0.0", - "mdast-util-to-markdown": "^2.0.0", - "micromark-extension-frontmatter": "^2.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/mdast-util-frontmatter/node_modules/escape-string-regexp": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-5.0.0.tgz", - "integrity": "sha512-/veY75JbMK4j1yjvuUxuVsiS/hr/4iHs9FTT6cgTexxdE0Ly/glccBAkloH/DofkjRbZU3bnoj38mOmhkZ0lHw==", - "license": "MIT", - "engines": { - "node": ">=12" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/mdast-util-gfm": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/mdast-util-gfm/-/mdast-util-gfm-3.0.0.tgz", - "integrity": "sha512-dgQEX5Amaq+DuUqf26jJqSK9qgixgd6rYDHAv4aTBuA92cTknZlKpPfa86Z/s8Dj8xsAQpFfBmPUHWJBWqS4Bw==", - "license": "MIT", - "dependencies": { - "mdast-util-from-markdown": "^2.0.0", - "mdast-util-gfm-autolink-literal": "^2.0.0", - "mdast-util-gfm-footnote": "^2.0.0", - "mdast-util-gfm-strikethrough": "^2.0.0", - "mdast-util-gfm-table": "^2.0.0", - "mdast-util-gfm-task-list-item": "^2.0.0", - "mdast-util-to-markdown": "^2.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/mdast-util-gfm-autolink-literal": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/mdast-util-gfm-autolink-literal/-/mdast-util-gfm-autolink-literal-2.0.1.tgz", - "integrity": "sha512-5HVP2MKaP6L+G6YaxPNjuL0BPrq9orG3TsrZ9YXbA3vDw/ACI4MEsnoDpn6ZNm7GnZgtAcONJyPhOP8tNJQavQ==", - "license": "MIT", - "dependencies": { - "@types/mdast": "^4.0.0", - "ccount": "^2.0.0", - "devlop": "^1.0.0", - "mdast-util-find-and-replace": "^3.0.0", - "micromark-util-character": "^2.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/mdast-util-gfm-autolink-literal/node_modules/micromark-util-character": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/micromark-util-character/-/micromark-util-character-2.1.1.tgz", - "integrity": "sha512-wv8tdUTJ3thSFFFJKtpYKOYiGP2+v96Hvk4Tu8KpCAsTMs6yi+nVmGh1syvSCsaxz45J6Jbw+9DD6g97+NV67Q==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-symbol": "^2.0.0", - "micromark-util-types": "^2.0.0" - } - }, - "node_modules/mdast-util-gfm-autolink-literal/node_modules/micromark-util-symbol": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/micromark-util-symbol/-/micromark-util-symbol-2.0.1.tgz", - "integrity": "sha512-vs5t8Apaud9N28kgCrRUdEed4UJ+wWNvicHLPxCa9ENlYuAY31M0ETy5y1vA33YoNPDFTghEbnh6efaE8h4x0Q==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT" - }, - "node_modules/mdast-util-gfm-footnote": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/mdast-util-gfm-footnote/-/mdast-util-gfm-footnote-2.0.0.tgz", - "integrity": "sha512-5jOT2boTSVkMnQ7LTrd6n/18kqwjmuYqo7JUPe+tRCY6O7dAuTFMtTPauYYrMPpox9hlN0uOx/FL8XvEfG9/mQ==", - "license": "MIT", - "dependencies": { - "@types/mdast": "^4.0.0", - "devlop": "^1.1.0", - "mdast-util-from-markdown": "^2.0.0", - "mdast-util-to-markdown": "^2.0.0", - "micromark-util-normalize-identifier": "^2.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/mdast-util-gfm-strikethrough": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/mdast-util-gfm-strikethrough/-/mdast-util-gfm-strikethrough-2.0.0.tgz", - "integrity": "sha512-mKKb915TF+OC5ptj5bJ7WFRPdYtuHv0yTRxK2tJvi+BDqbkiG7h7u/9SI89nRAYcmap2xHQL9D+QG/6wSrTtXg==", - "license": "MIT", - "dependencies": { - "@types/mdast": "^4.0.0", - "mdast-util-from-markdown": "^2.0.0", - "mdast-util-to-markdown": "^2.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/mdast-util-gfm-table": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/mdast-util-gfm-table/-/mdast-util-gfm-table-2.0.0.tgz", - "integrity": "sha512-78UEvebzz/rJIxLvE7ZtDd/vIQ0RHv+3Mh5DR96p7cS7HsBhYIICDBCu8csTNWNO6tBWfqXPWekRuj2FNOGOZg==", - "license": "MIT", - "dependencies": { - "@types/mdast": "^4.0.0", - "devlop": "^1.0.0", - "markdown-table": "^3.0.0", - "mdast-util-from-markdown": "^2.0.0", - "mdast-util-to-markdown": "^2.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/mdast-util-gfm-task-list-item": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/mdast-util-gfm-task-list-item/-/mdast-util-gfm-task-list-item-2.0.0.tgz", - "integrity": "sha512-IrtvNvjxC1o06taBAVJznEnkiHxLFTzgonUdy8hzFVeDun0uTjxxrRGVaNFqkU1wJR3RBPEfsxmU6jDWPofrTQ==", - "license": "MIT", - "dependencies": { - "@types/mdast": "^4.0.0", - "devlop": "^1.0.0", - "mdast-util-from-markdown": "^2.0.0", - "mdast-util-to-markdown": "^2.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/mdast-util-mdx": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/mdast-util-mdx/-/mdast-util-mdx-3.0.0.tgz", - "integrity": "sha512-JfbYLAW7XnYTTbUsmpu0kdBUVe+yKVJZBItEjwyYJiDJuZ9w4eeaqks4HQO+R7objWgS2ymV60GYpI14Ug554w==", - "license": "MIT", - "dependencies": { - "mdast-util-from-markdown": "^2.0.0", - "mdast-util-mdx-expression": "^2.0.0", - "mdast-util-mdx-jsx": "^3.0.0", - "mdast-util-mdxjs-esm": "^2.0.0", - "mdast-util-to-markdown": "^2.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/mdast-util-mdx-expression": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/mdast-util-mdx-expression/-/mdast-util-mdx-expression-2.0.0.tgz", - "integrity": "sha512-fGCu8eWdKUKNu5mohVGkhBXCXGnOTLuFqOvGMvdikr+J1w7lDJgxThOKpwRWzzbyXAU2hhSwsmssOY4yTokluw==", - "license": "MIT", - "dependencies": { - "@types/estree-jsx": "^1.0.0", - "@types/hast": "^3.0.0", - "@types/mdast": "^4.0.0", - "devlop": "^1.0.0", - "mdast-util-from-markdown": "^2.0.0", - "mdast-util-to-markdown": "^2.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/mdast-util-mdx-jsx": { - "version": "3.1.2", - "resolved": "https://registry.npmjs.org/mdast-util-mdx-jsx/-/mdast-util-mdx-jsx-3.1.2.tgz", - "integrity": "sha512-eKMQDeywY2wlHc97k5eD8VC+9ASMjN8ItEZQNGwJ6E0XWKiW/Z0V5/H8pvoXUf+y+Mj0VIgeRRbujBmFn4FTyA==", - "license": "MIT", - "dependencies": { - "@types/estree-jsx": "^1.0.0", - "@types/hast": "^3.0.0", - "@types/mdast": "^4.0.0", - "@types/unist": "^3.0.0", - "ccount": "^2.0.0", - "devlop": "^1.1.0", - "mdast-util-from-markdown": "^2.0.0", - "mdast-util-to-markdown": "^2.0.0", - "parse-entities": "^4.0.0", - "stringify-entities": "^4.0.0", - "unist-util-remove-position": "^5.0.0", - "unist-util-stringify-position": "^4.0.0", - "vfile-message": "^4.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/mdast-util-mdxjs-esm": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/mdast-util-mdxjs-esm/-/mdast-util-mdxjs-esm-2.0.1.tgz", - "integrity": "sha512-EcmOpxsZ96CvlP03NghtH1EsLtr0n9Tm4lPUJUBccV9RwUOneqSycg19n5HGzCf+10LozMRSObtVr3ee1WoHtg==", - "license": "MIT", - "dependencies": { - "@types/estree-jsx": "^1.0.0", - "@types/hast": "^3.0.0", - "@types/mdast": "^4.0.0", - "devlop": "^1.0.0", - "mdast-util-from-markdown": "^2.0.0", - "mdast-util-to-markdown": "^2.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/mdast-util-phrasing": { - "version": "4.1.0", - "resolved": "https://registry.npmjs.org/mdast-util-phrasing/-/mdast-util-phrasing-4.1.0.tgz", - "integrity": "sha512-TqICwyvJJpBwvGAMZjj4J2n0X8QWp21b9l0o7eXyVJ25YNWYbJDVIyD1bZXE6WtV6RmKJVYmQAKWa0zWOABz2w==", - "license": "MIT", - "dependencies": { - "@types/mdast": "^4.0.0", - "unist-util-is": "^6.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/mdast-util-to-hast": { - "version": "13.2.0", - "resolved": "https://registry.npmjs.org/mdast-util-to-hast/-/mdast-util-to-hast-13.2.0.tgz", - "integrity": "sha512-QGYKEuUsYT9ykKBCMOEDLsU5JRObWQusAolFMeko/tYPufNkRffBAQjIE+99jbA87xv6FgmjLtwjh9wBWajwAA==", - "license": "MIT", - "dependencies": { - "@types/hast": "^3.0.0", - "@types/mdast": "^4.0.0", - "@ungap/structured-clone": "^1.0.0", - "devlop": "^1.0.0", - "micromark-util-sanitize-uri": "^2.0.0", - "trim-lines": "^3.0.0", - "unist-util-position": "^5.0.0", - "unist-util-visit": "^5.0.0", - "vfile": "^6.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/mdast-util-to-markdown": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/mdast-util-to-markdown/-/mdast-util-to-markdown-2.1.0.tgz", - "integrity": "sha512-SR2VnIEdVNCJbP6y7kVTJgPLifdr8WEU440fQec7qHoHOUz/oJ2jmNRqdDQ3rbiStOXb2mCDGTuwsK5OPUgYlQ==", - "license": "MIT", - "dependencies": { - "@types/mdast": "^4.0.0", - "@types/unist": "^3.0.0", - "longest-streak": "^3.0.0", - "mdast-util-phrasing": "^4.0.0", - "mdast-util-to-string": "^4.0.0", - "micromark-util-decode-string": "^2.0.0", - "unist-util-visit": "^5.0.0", - "zwitch": "^2.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/mdast-util-to-string": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/mdast-util-to-string/-/mdast-util-to-string-4.0.0.tgz", - "integrity": "sha512-0H44vDimn51F0YwvxSJSm0eCDOJTRlmN0R1yBh4HLj9wiV1Dn0QoXGbvFAWj2hSItVTlCmBF1hqKlIyUBVFLPg==", - "license": "MIT", - "dependencies": { - "@types/mdast": "^4.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/mdn-data": { - "version": "2.0.30", - "resolved": "https://registry.npmjs.org/mdn-data/-/mdn-data-2.0.30.tgz", - "integrity": "sha512-GaqWWShW4kv/G9IEucWScBx9G1/vsFZZJUO+tD26M8J8z3Kw5RDQjaoZe03YAClgeS/SWPOcb4nkFBTEi5DUEA==", - "license": "CC0-1.0" - }, - "node_modules/media-typer": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/media-typer/-/media-typer-0.3.0.tgz", - "integrity": "sha512-dq+qelQ9akHpcOl/gUVRTxVIOkAJ1wR3QAvb4RsVjS8oVoFjDGTc679wJYmUmknUF5HwMLOgb5O+a3KxfWapPQ==", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/memfs": { - "version": "3.5.3", - "resolved": "https://registry.npmjs.org/memfs/-/memfs-3.5.3.tgz", - "integrity": "sha512-UERzLsxzllchadvbPs5aolHh65ISpKpM+ccLbOJ8/vvpBKmAWf+la7dXFy7Mr0ySHbdHrFv5kGFCUHHe6GFEmw==", - "license": "Unlicense", - "dependencies": { - "fs-monkey": "^1.0.4" - }, - "engines": { - "node": ">= 4.0.0" - } - }, - "node_modules/merge-descriptors": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/merge-descriptors/-/merge-descriptors-1.0.3.tgz", - "integrity": "sha512-gaNvAS7TZ897/rVaZ0nMtAyxNyi/pdbjbAwUpFQpN70GqnVfOiXpeUUMKRBmzXaSQ8DdTX4/0ms62r2K+hE6mQ==", - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/merge-stream": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/merge-stream/-/merge-stream-2.0.0.tgz", - "integrity": "sha512-abv/qOcuPfk3URPfDzmZU1LKmuw8kT+0nIHvKrKgFrwifol/doWcdA4ZqsWQ8ENrFKkd67Mfpo/LovbIUsbt3w==", - "license": "MIT" - }, - "node_modules/merge2": { - "version": "1.4.1", - "resolved": "https://registry.npmjs.org/merge2/-/merge2-1.4.1.tgz", - "integrity": "sha512-8q7VEgMJW4J8tcfVPy8g09NcQwZdbwFEqhe/WZkoIzjn/3TGDwtOCYtXGxA3O8tPzpczCCDgv+P2P5y00ZJOOg==", - "license": "MIT", - "engines": { - "node": ">= 8" - } - }, - "node_modules/methods": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/methods/-/methods-1.1.2.tgz", - "integrity": "sha512-iclAHeNqNm68zFtnZ0e+1L2yUIdvzNoauKU4WBA3VvH/vPFieF7qfRlwUZU+DA9P9bPXIS90ulxoUoCH23sV2w==", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/micromark": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/micromark/-/micromark-4.0.0.tgz", - "integrity": "sha512-o/sd0nMof8kYff+TqcDx3VSrgBTcZpSvYcAHIfHhv5VAuNmisCxjhx6YmxS8PFEpb9z5WKWKPdzf0jM23ro3RQ==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "@types/debug": "^4.0.0", - "debug": "^4.0.0", - "decode-named-character-reference": "^1.0.0", - "devlop": "^1.0.0", - "micromark-core-commonmark": "^2.0.0", - "micromark-factory-space": "^2.0.0", - "micromark-util-character": "^2.0.0", - "micromark-util-chunked": "^2.0.0", - "micromark-util-combine-extensions": "^2.0.0", - "micromark-util-decode-numeric-character-reference": "^2.0.0", - "micromark-util-encode": "^2.0.0", - "micromark-util-normalize-identifier": "^2.0.0", - "micromark-util-resolve-all": "^2.0.0", - "micromark-util-sanitize-uri": "^2.0.0", - "micromark-util-subtokenize": "^2.0.0", - "micromark-util-symbol": "^2.0.0", - "micromark-util-types": "^2.0.0" - } - }, - "node_modules/micromark-core-commonmark": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/micromark-core-commonmark/-/micromark-core-commonmark-2.0.1.tgz", - "integrity": "sha512-CUQyKr1e///ZODyD1U3xit6zXwy1a8q2a1S1HKtIlmgvurrEpaw/Y9y6KSIbF8P59cn/NjzHyO+Q2fAyYLQrAA==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "decode-named-character-reference": "^1.0.0", - "devlop": "^1.0.0", - "micromark-factory-destination": "^2.0.0", - "micromark-factory-label": "^2.0.0", - "micromark-factory-space": "^2.0.0", - "micromark-factory-title": "^2.0.0", - "micromark-factory-whitespace": "^2.0.0", - "micromark-util-character": "^2.0.0", - "micromark-util-chunked": "^2.0.0", - "micromark-util-classify-character": "^2.0.0", - "micromark-util-html-tag-name": "^2.0.0", - "micromark-util-normalize-identifier": "^2.0.0", - "micromark-util-resolve-all": "^2.0.0", - "micromark-util-subtokenize": "^2.0.0", - "micromark-util-symbol": "^2.0.0", - "micromark-util-types": "^2.0.0" - } - }, - "node_modules/micromark-core-commonmark/node_modules/micromark-factory-space": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/micromark-factory-space/-/micromark-factory-space-2.0.0.tgz", - "integrity": "sha512-TKr+LIDX2pkBJXFLzpyPyljzYK3MtmllMUMODTQJIUfDGncESaqB90db9IAUcz4AZAJFdd8U9zOp9ty1458rxg==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-character": "^2.0.0", - "micromark-util-types": "^2.0.0" - } - }, - "node_modules/micromark-core-commonmark/node_modules/micromark-util-character": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/micromark-util-character/-/micromark-util-character-2.1.0.tgz", - "integrity": "sha512-KvOVV+X1yLBfs9dCBSopq/+G1PcgT3lAK07mC4BzXi5E7ahzMAF8oIupDDJ6mievI6F+lAATkbQQlQixJfT3aQ==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-symbol": "^2.0.0", - "micromark-util-types": "^2.0.0" - } - }, - "node_modules/micromark-core-commonmark/node_modules/micromark-util-symbol": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/micromark-util-symbol/-/micromark-util-symbol-2.0.0.tgz", - "integrity": "sha512-8JZt9ElZ5kyTnO94muPxIGS8oyElRJaiJO8EzV6ZSyGQ1Is8xwl4Q45qU5UOg+bGH4AikWziz0iN4sFLWs8PGw==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT" - }, - "node_modules/micromark-extension-directive": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/micromark-extension-directive/-/micromark-extension-directive-3.0.2.tgz", - "integrity": "sha512-wjcXHgk+PPdmvR58Le9d7zQYWy+vKEU9Se44p2CrCDPiLr2FMyiT4Fyb5UFKFC66wGB3kPlgD7q3TnoqPS7SZA==", - "license": "MIT", - "dependencies": { - "devlop": "^1.0.0", - "micromark-factory-space": "^2.0.0", - "micromark-factory-whitespace": "^2.0.0", - "micromark-util-character": "^2.0.0", - "micromark-util-symbol": "^2.0.0", - "micromark-util-types": "^2.0.0", - "parse-entities": "^4.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/micromark-extension-directive/node_modules/micromark-factory-space": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/micromark-factory-space/-/micromark-factory-space-2.0.1.tgz", - "integrity": "sha512-zRkxjtBxxLd2Sc0d+fbnEunsTj46SWXgXciZmHq0kDYGnck/ZSGj9/wULTV95uoeYiK5hRXP2mJ98Uo4cq/LQg==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-character": "^2.0.0", - "micromark-util-types": "^2.0.0" - } - }, - "node_modules/micromark-extension-directive/node_modules/micromark-util-character": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/micromark-util-character/-/micromark-util-character-2.1.1.tgz", - "integrity": "sha512-wv8tdUTJ3thSFFFJKtpYKOYiGP2+v96Hvk4Tu8KpCAsTMs6yi+nVmGh1syvSCsaxz45J6Jbw+9DD6g97+NV67Q==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-symbol": "^2.0.0", - "micromark-util-types": "^2.0.0" - } - }, - "node_modules/micromark-extension-directive/node_modules/micromark-util-symbol": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/micromark-util-symbol/-/micromark-util-symbol-2.0.1.tgz", - "integrity": "sha512-vs5t8Apaud9N28kgCrRUdEed4UJ+wWNvicHLPxCa9ENlYuAY31M0ETy5y1vA33YoNPDFTghEbnh6efaE8h4x0Q==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT" - }, - "node_modules/micromark-extension-frontmatter": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/micromark-extension-frontmatter/-/micromark-extension-frontmatter-2.0.0.tgz", - "integrity": "sha512-C4AkuM3dA58cgZha7zVnuVxBhDsbttIMiytjgsM2XbHAB2faRVaHRle40558FBN+DJcrLNCoqG5mlrpdU4cRtg==", - "license": "MIT", - "dependencies": { - "fault": "^2.0.0", - "micromark-util-character": "^2.0.0", - "micromark-util-symbol": "^2.0.0", - "micromark-util-types": "^2.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/micromark-extension-frontmatter/node_modules/micromark-util-character": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/micromark-util-character/-/micromark-util-character-2.1.1.tgz", - "integrity": "sha512-wv8tdUTJ3thSFFFJKtpYKOYiGP2+v96Hvk4Tu8KpCAsTMs6yi+nVmGh1syvSCsaxz45J6Jbw+9DD6g97+NV67Q==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-symbol": "^2.0.0", - "micromark-util-types": "^2.0.0" - } - }, - "node_modules/micromark-extension-frontmatter/node_modules/micromark-util-symbol": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/micromark-util-symbol/-/micromark-util-symbol-2.0.1.tgz", - "integrity": "sha512-vs5t8Apaud9N28kgCrRUdEed4UJ+wWNvicHLPxCa9ENlYuAY31M0ETy5y1vA33YoNPDFTghEbnh6efaE8h4x0Q==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT" - }, - "node_modules/micromark-extension-gfm": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/micromark-extension-gfm/-/micromark-extension-gfm-3.0.0.tgz", - "integrity": "sha512-vsKArQsicm7t0z2GugkCKtZehqUm31oeGBV/KVSorWSy8ZlNAv7ytjFhvaryUiCUJYqs+NoE6AFhpQvBTM6Q4w==", - "license": "MIT", - "dependencies": { - "micromark-extension-gfm-autolink-literal": "^2.0.0", - "micromark-extension-gfm-footnote": "^2.0.0", - "micromark-extension-gfm-strikethrough": "^2.0.0", - "micromark-extension-gfm-table": "^2.0.0", - "micromark-extension-gfm-tagfilter": "^2.0.0", - "micromark-extension-gfm-task-list-item": "^2.0.0", - "micromark-util-combine-extensions": "^2.0.0", - "micromark-util-types": "^2.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/micromark-extension-gfm-autolink-literal": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/micromark-extension-gfm-autolink-literal/-/micromark-extension-gfm-autolink-literal-2.1.0.tgz", - "integrity": "sha512-oOg7knzhicgQ3t4QCjCWgTmfNhvQbDDnJeVu9v81r7NltNCVmhPy1fJRX27pISafdjL+SVc4d3l48Gb6pbRypw==", - "license": "MIT", - "dependencies": { - "micromark-util-character": "^2.0.0", - "micromark-util-sanitize-uri": "^2.0.0", - "micromark-util-symbol": "^2.0.0", - "micromark-util-types": "^2.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/micromark-extension-gfm-autolink-literal/node_modules/micromark-util-character": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/micromark-util-character/-/micromark-util-character-2.1.1.tgz", - "integrity": "sha512-wv8tdUTJ3thSFFFJKtpYKOYiGP2+v96Hvk4Tu8KpCAsTMs6yi+nVmGh1syvSCsaxz45J6Jbw+9DD6g97+NV67Q==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-symbol": "^2.0.0", - "micromark-util-types": "^2.0.0" - } - }, - "node_modules/micromark-extension-gfm-autolink-literal/node_modules/micromark-util-symbol": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/micromark-util-symbol/-/micromark-util-symbol-2.0.1.tgz", - "integrity": "sha512-vs5t8Apaud9N28kgCrRUdEed4UJ+wWNvicHLPxCa9ENlYuAY31M0ETy5y1vA33YoNPDFTghEbnh6efaE8h4x0Q==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT" - }, - "node_modules/micromark-extension-gfm-footnote": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/micromark-extension-gfm-footnote/-/micromark-extension-gfm-footnote-2.1.0.tgz", - "integrity": "sha512-/yPhxI1ntnDNsiHtzLKYnE3vf9JZ6cAisqVDauhp4CEHxlb4uoOTxOCJ+9s51bIB8U1N1FJ1RXOKTIlD5B/gqw==", - "license": "MIT", - "dependencies": { - "devlop": "^1.0.0", - "micromark-core-commonmark": "^2.0.0", - "micromark-factory-space": "^2.0.0", - "micromark-util-character": "^2.0.0", - "micromark-util-normalize-identifier": "^2.0.0", - "micromark-util-sanitize-uri": "^2.0.0", - "micromark-util-symbol": "^2.0.0", - "micromark-util-types": "^2.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/micromark-extension-gfm-footnote/node_modules/micromark-factory-space": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/micromark-factory-space/-/micromark-factory-space-2.0.1.tgz", - "integrity": "sha512-zRkxjtBxxLd2Sc0d+fbnEunsTj46SWXgXciZmHq0kDYGnck/ZSGj9/wULTV95uoeYiK5hRXP2mJ98Uo4cq/LQg==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-character": "^2.0.0", - "micromark-util-types": "^2.0.0" - } - }, - "node_modules/micromark-extension-gfm-footnote/node_modules/micromark-util-character": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/micromark-util-character/-/micromark-util-character-2.1.1.tgz", - "integrity": "sha512-wv8tdUTJ3thSFFFJKtpYKOYiGP2+v96Hvk4Tu8KpCAsTMs6yi+nVmGh1syvSCsaxz45J6Jbw+9DD6g97+NV67Q==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-symbol": "^2.0.0", - "micromark-util-types": "^2.0.0" - } - }, - "node_modules/micromark-extension-gfm-footnote/node_modules/micromark-util-symbol": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/micromark-util-symbol/-/micromark-util-symbol-2.0.1.tgz", - "integrity": "sha512-vs5t8Apaud9N28kgCrRUdEed4UJ+wWNvicHLPxCa9ENlYuAY31M0ETy5y1vA33YoNPDFTghEbnh6efaE8h4x0Q==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT" - }, - "node_modules/micromark-extension-gfm-strikethrough": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/micromark-extension-gfm-strikethrough/-/micromark-extension-gfm-strikethrough-2.1.0.tgz", - "integrity": "sha512-ADVjpOOkjz1hhkZLlBiYA9cR2Anf8F4HqZUO6e5eDcPQd0Txw5fxLzzxnEkSkfnD0wziSGiv7sYhk/ktvbf1uw==", - "license": "MIT", - "dependencies": { - "devlop": "^1.0.0", - "micromark-util-chunked": "^2.0.0", - "micromark-util-classify-character": "^2.0.0", - "micromark-util-resolve-all": "^2.0.0", - "micromark-util-symbol": "^2.0.0", - "micromark-util-types": "^2.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/micromark-extension-gfm-strikethrough/node_modules/micromark-util-symbol": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/micromark-util-symbol/-/micromark-util-symbol-2.0.1.tgz", - "integrity": "sha512-vs5t8Apaud9N28kgCrRUdEed4UJ+wWNvicHLPxCa9ENlYuAY31M0ETy5y1vA33YoNPDFTghEbnh6efaE8h4x0Q==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT" - }, - "node_modules/micromark-extension-gfm-table": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/micromark-extension-gfm-table/-/micromark-extension-gfm-table-2.1.0.tgz", - "integrity": "sha512-Ub2ncQv+fwD70/l4ou27b4YzfNaCJOvyX4HxXU15m7mpYY+rjuWzsLIPZHJL253Z643RpbcP1oeIJlQ/SKW67g==", - "license": "MIT", - "dependencies": { - "devlop": "^1.0.0", - "micromark-factory-space": "^2.0.0", - "micromark-util-character": "^2.0.0", - "micromark-util-symbol": "^2.0.0", - "micromark-util-types": "^2.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/micromark-extension-gfm-table/node_modules/micromark-factory-space": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/micromark-factory-space/-/micromark-factory-space-2.0.1.tgz", - "integrity": "sha512-zRkxjtBxxLd2Sc0d+fbnEunsTj46SWXgXciZmHq0kDYGnck/ZSGj9/wULTV95uoeYiK5hRXP2mJ98Uo4cq/LQg==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-character": "^2.0.0", - "micromark-util-types": "^2.0.0" - } - }, - "node_modules/micromark-extension-gfm-table/node_modules/micromark-util-character": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/micromark-util-character/-/micromark-util-character-2.1.1.tgz", - "integrity": "sha512-wv8tdUTJ3thSFFFJKtpYKOYiGP2+v96Hvk4Tu8KpCAsTMs6yi+nVmGh1syvSCsaxz45J6Jbw+9DD6g97+NV67Q==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-symbol": "^2.0.0", - "micromark-util-types": "^2.0.0" - } - }, - "node_modules/micromark-extension-gfm-table/node_modules/micromark-util-symbol": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/micromark-util-symbol/-/micromark-util-symbol-2.0.1.tgz", - "integrity": "sha512-vs5t8Apaud9N28kgCrRUdEed4UJ+wWNvicHLPxCa9ENlYuAY31M0ETy5y1vA33YoNPDFTghEbnh6efaE8h4x0Q==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT" - }, - "node_modules/micromark-extension-gfm-tagfilter": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/micromark-extension-gfm-tagfilter/-/micromark-extension-gfm-tagfilter-2.0.0.tgz", - "integrity": "sha512-xHlTOmuCSotIA8TW1mDIM6X2O1SiX5P9IuDtqGonFhEK0qgRI4yeC6vMxEV2dgyr2TiD+2PQ10o+cOhdVAcwfg==", - "license": "MIT", - "dependencies": { - "micromark-util-types": "^2.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/micromark-extension-gfm-task-list-item": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/micromark-extension-gfm-task-list-item/-/micromark-extension-gfm-task-list-item-2.1.0.tgz", - "integrity": "sha512-qIBZhqxqI6fjLDYFTBIa4eivDMnP+OZqsNwmQ3xNLE4Cxwc+zfQEfbs6tzAo2Hjq+bh6q5F+Z8/cksrLFYWQQw==", - "license": "MIT", - "dependencies": { - "devlop": "^1.0.0", - "micromark-factory-space": "^2.0.0", - "micromark-util-character": "^2.0.0", - "micromark-util-symbol": "^2.0.0", - "micromark-util-types": "^2.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/micromark-extension-gfm-task-list-item/node_modules/micromark-factory-space": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/micromark-factory-space/-/micromark-factory-space-2.0.1.tgz", - "integrity": "sha512-zRkxjtBxxLd2Sc0d+fbnEunsTj46SWXgXciZmHq0kDYGnck/ZSGj9/wULTV95uoeYiK5hRXP2mJ98Uo4cq/LQg==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-character": "^2.0.0", - "micromark-util-types": "^2.0.0" - } - }, - "node_modules/micromark-extension-gfm-task-list-item/node_modules/micromark-util-character": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/micromark-util-character/-/micromark-util-character-2.1.1.tgz", - "integrity": "sha512-wv8tdUTJ3thSFFFJKtpYKOYiGP2+v96Hvk4Tu8KpCAsTMs6yi+nVmGh1syvSCsaxz45J6Jbw+9DD6g97+NV67Q==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-symbol": "^2.0.0", - "micromark-util-types": "^2.0.0" - } - }, - "node_modules/micromark-extension-gfm-task-list-item/node_modules/micromark-util-symbol": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/micromark-util-symbol/-/micromark-util-symbol-2.0.1.tgz", - "integrity": "sha512-vs5t8Apaud9N28kgCrRUdEed4UJ+wWNvicHLPxCa9ENlYuAY31M0ETy5y1vA33YoNPDFTghEbnh6efaE8h4x0Q==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT" - }, - "node_modules/micromark-extension-mdx-expression": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/micromark-extension-mdx-expression/-/micromark-extension-mdx-expression-3.0.0.tgz", - "integrity": "sha512-sI0nwhUDz97xyzqJAbHQhp5TfaxEvZZZ2JDqUo+7NvyIYG6BZ5CPPqj2ogUoPJlmXHBnyZUzISg9+oUmU6tUjQ==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "@types/estree": "^1.0.0", - "devlop": "^1.0.0", - "micromark-factory-mdx-expression": "^2.0.0", - "micromark-factory-space": "^2.0.0", - "micromark-util-character": "^2.0.0", - "micromark-util-events-to-acorn": "^2.0.0", - "micromark-util-symbol": "^2.0.0", - "micromark-util-types": "^2.0.0" - } - }, - "node_modules/micromark-extension-mdx-expression/node_modules/micromark-factory-space": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/micromark-factory-space/-/micromark-factory-space-2.0.0.tgz", - "integrity": "sha512-TKr+LIDX2pkBJXFLzpyPyljzYK3MtmllMUMODTQJIUfDGncESaqB90db9IAUcz4AZAJFdd8U9zOp9ty1458rxg==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-character": "^2.0.0", - "micromark-util-types": "^2.0.0" - } - }, - "node_modules/micromark-extension-mdx-expression/node_modules/micromark-util-character": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/micromark-util-character/-/micromark-util-character-2.1.0.tgz", - "integrity": "sha512-KvOVV+X1yLBfs9dCBSopq/+G1PcgT3lAK07mC4BzXi5E7ahzMAF8oIupDDJ6mievI6F+lAATkbQQlQixJfT3aQ==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-symbol": "^2.0.0", - "micromark-util-types": "^2.0.0" - } - }, - "node_modules/micromark-extension-mdx-expression/node_modules/micromark-util-symbol": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/micromark-util-symbol/-/micromark-util-symbol-2.0.0.tgz", - "integrity": "sha512-8JZt9ElZ5kyTnO94muPxIGS8oyElRJaiJO8EzV6ZSyGQ1Is8xwl4Q45qU5UOg+bGH4AikWziz0iN4sFLWs8PGw==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT" - }, - "node_modules/micromark-extension-mdx-jsx": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/micromark-extension-mdx-jsx/-/micromark-extension-mdx-jsx-3.0.0.tgz", - "integrity": "sha512-uvhhss8OGuzR4/N17L1JwvmJIpPhAd8oByMawEKx6NVdBCbesjH4t+vjEp3ZXft9DwvlKSD07fCeI44/N0Vf2w==", - "license": "MIT", - "dependencies": { - "@types/acorn": "^4.0.0", - "@types/estree": "^1.0.0", - "devlop": "^1.0.0", - "estree-util-is-identifier-name": "^3.0.0", - "micromark-factory-mdx-expression": "^2.0.0", - "micromark-factory-space": "^2.0.0", - "micromark-util-character": "^2.0.0", - "micromark-util-symbol": "^2.0.0", - "micromark-util-types": "^2.0.0", - "vfile-message": "^4.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/micromark-extension-mdx-jsx/node_modules/micromark-factory-space": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/micromark-factory-space/-/micromark-factory-space-2.0.0.tgz", - "integrity": "sha512-TKr+LIDX2pkBJXFLzpyPyljzYK3MtmllMUMODTQJIUfDGncESaqB90db9IAUcz4AZAJFdd8U9zOp9ty1458rxg==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-character": "^2.0.0", - "micromark-util-types": "^2.0.0" - } - }, - "node_modules/micromark-extension-mdx-jsx/node_modules/micromark-util-character": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/micromark-util-character/-/micromark-util-character-2.1.0.tgz", - "integrity": "sha512-KvOVV+X1yLBfs9dCBSopq/+G1PcgT3lAK07mC4BzXi5E7ahzMAF8oIupDDJ6mievI6F+lAATkbQQlQixJfT3aQ==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-symbol": "^2.0.0", - "micromark-util-types": "^2.0.0" - } - }, - "node_modules/micromark-extension-mdx-jsx/node_modules/micromark-util-symbol": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/micromark-util-symbol/-/micromark-util-symbol-2.0.0.tgz", - "integrity": "sha512-8JZt9ElZ5kyTnO94muPxIGS8oyElRJaiJO8EzV6ZSyGQ1Is8xwl4Q45qU5UOg+bGH4AikWziz0iN4sFLWs8PGw==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT" - }, - "node_modules/micromark-extension-mdx-md": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/micromark-extension-mdx-md/-/micromark-extension-mdx-md-2.0.0.tgz", - "integrity": "sha512-EpAiszsB3blw4Rpba7xTOUptcFeBFi+6PY8VnJ2hhimH+vCQDirWgsMpz7w1XcZE7LVrSAUGb9VJpG9ghlYvYQ==", - "license": "MIT", - "dependencies": { - "micromark-util-types": "^2.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/micromark-extension-mdxjs": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/micromark-extension-mdxjs/-/micromark-extension-mdxjs-3.0.0.tgz", - "integrity": "sha512-A873fJfhnJ2siZyUrJ31l34Uqwy4xIFmvPY1oj+Ean5PHcPBYzEsvqvWGaWcfEIr11O5Dlw3p2y0tZWpKHDejQ==", - "license": "MIT", - "dependencies": { - "acorn": "^8.0.0", - "acorn-jsx": "^5.0.0", - "micromark-extension-mdx-expression": "^3.0.0", - "micromark-extension-mdx-jsx": "^3.0.0", - "micromark-extension-mdx-md": "^2.0.0", - "micromark-extension-mdxjs-esm": "^3.0.0", - "micromark-util-combine-extensions": "^2.0.0", - "micromark-util-types": "^2.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/micromark-extension-mdxjs-esm": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/micromark-extension-mdxjs-esm/-/micromark-extension-mdxjs-esm-3.0.0.tgz", - "integrity": "sha512-DJFl4ZqkErRpq/dAPyeWp15tGrcrrJho1hKK5uBS70BCtfrIFg81sqcTVu3Ta+KD1Tk5vAtBNElWxtAa+m8K9A==", - "license": "MIT", - "dependencies": { - "@types/estree": "^1.0.0", - "devlop": "^1.0.0", - "micromark-core-commonmark": "^2.0.0", - "micromark-util-character": "^2.0.0", - "micromark-util-events-to-acorn": "^2.0.0", - "micromark-util-symbol": "^2.0.0", - "micromark-util-types": "^2.0.0", - "unist-util-position-from-estree": "^2.0.0", - "vfile-message": "^4.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/micromark-extension-mdxjs-esm/node_modules/micromark-util-character": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/micromark-util-character/-/micromark-util-character-2.1.0.tgz", - "integrity": "sha512-KvOVV+X1yLBfs9dCBSopq/+G1PcgT3lAK07mC4BzXi5E7ahzMAF8oIupDDJ6mievI6F+lAATkbQQlQixJfT3aQ==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-symbol": "^2.0.0", - "micromark-util-types": "^2.0.0" - } - }, - "node_modules/micromark-extension-mdxjs-esm/node_modules/micromark-util-symbol": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/micromark-util-symbol/-/micromark-util-symbol-2.0.0.tgz", - "integrity": "sha512-8JZt9ElZ5kyTnO94muPxIGS8oyElRJaiJO8EzV6ZSyGQ1Is8xwl4Q45qU5UOg+bGH4AikWziz0iN4sFLWs8PGw==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT" - }, - "node_modules/micromark-factory-destination": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/micromark-factory-destination/-/micromark-factory-destination-2.0.0.tgz", - "integrity": "sha512-j9DGrQLm/Uhl2tCzcbLhy5kXsgkHUrjJHg4fFAeoMRwJmJerT9aw4FEhIbZStWN8A3qMwOp1uzHr4UL8AInxtA==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-character": "^2.0.0", - "micromark-util-symbol": "^2.0.0", - "micromark-util-types": "^2.0.0" - } - }, - "node_modules/micromark-factory-destination/node_modules/micromark-util-character": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/micromark-util-character/-/micromark-util-character-2.1.0.tgz", - "integrity": "sha512-KvOVV+X1yLBfs9dCBSopq/+G1PcgT3lAK07mC4BzXi5E7ahzMAF8oIupDDJ6mievI6F+lAATkbQQlQixJfT3aQ==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-symbol": "^2.0.0", - "micromark-util-types": "^2.0.0" - } - }, - "node_modules/micromark-factory-destination/node_modules/micromark-util-symbol": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/micromark-util-symbol/-/micromark-util-symbol-2.0.0.tgz", - "integrity": "sha512-8JZt9ElZ5kyTnO94muPxIGS8oyElRJaiJO8EzV6ZSyGQ1Is8xwl4Q45qU5UOg+bGH4AikWziz0iN4sFLWs8PGw==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT" - }, - "node_modules/micromark-factory-label": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/micromark-factory-label/-/micromark-factory-label-2.0.0.tgz", - "integrity": "sha512-RR3i96ohZGde//4WSe/dJsxOX6vxIg9TimLAS3i4EhBAFx8Sm5SmqVfR8E87DPSR31nEAjZfbt91OMZWcNgdZw==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "devlop": "^1.0.0", - "micromark-util-character": "^2.0.0", - "micromark-util-symbol": "^2.0.0", - "micromark-util-types": "^2.0.0" - } - }, - "node_modules/micromark-factory-label/node_modules/micromark-util-character": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/micromark-util-character/-/micromark-util-character-2.1.0.tgz", - "integrity": "sha512-KvOVV+X1yLBfs9dCBSopq/+G1PcgT3lAK07mC4BzXi5E7ahzMAF8oIupDDJ6mievI6F+lAATkbQQlQixJfT3aQ==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-symbol": "^2.0.0", - "micromark-util-types": "^2.0.0" - } - }, - "node_modules/micromark-factory-label/node_modules/micromark-util-symbol": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/micromark-util-symbol/-/micromark-util-symbol-2.0.0.tgz", - "integrity": "sha512-8JZt9ElZ5kyTnO94muPxIGS8oyElRJaiJO8EzV6ZSyGQ1Is8xwl4Q45qU5UOg+bGH4AikWziz0iN4sFLWs8PGw==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT" - }, - "node_modules/micromark-factory-mdx-expression": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/micromark-factory-mdx-expression/-/micromark-factory-mdx-expression-2.0.1.tgz", - "integrity": "sha512-F0ccWIUHRLRrYp5TC9ZYXmZo+p2AM13ggbsW4T0b5CRKP8KHVRB8t4pwtBgTxtjRmwrK0Irwm7vs2JOZabHZfg==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "@types/estree": "^1.0.0", - "devlop": "^1.0.0", - "micromark-util-character": "^2.0.0", - "micromark-util-events-to-acorn": "^2.0.0", - "micromark-util-symbol": "^2.0.0", - "micromark-util-types": "^2.0.0", - "unist-util-position-from-estree": "^2.0.0", - "vfile-message": "^4.0.0" - } - }, - "node_modules/micromark-factory-mdx-expression/node_modules/micromark-util-character": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/micromark-util-character/-/micromark-util-character-2.1.0.tgz", - "integrity": "sha512-KvOVV+X1yLBfs9dCBSopq/+G1PcgT3lAK07mC4BzXi5E7ahzMAF8oIupDDJ6mievI6F+lAATkbQQlQixJfT3aQ==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-symbol": "^2.0.0", - "micromark-util-types": "^2.0.0" - } - }, - "node_modules/micromark-factory-mdx-expression/node_modules/micromark-util-symbol": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/micromark-util-symbol/-/micromark-util-symbol-2.0.0.tgz", - "integrity": "sha512-8JZt9ElZ5kyTnO94muPxIGS8oyElRJaiJO8EzV6ZSyGQ1Is8xwl4Q45qU5UOg+bGH4AikWziz0iN4sFLWs8PGw==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT" - }, - "node_modules/micromark-factory-space": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/micromark-factory-space/-/micromark-factory-space-1.1.0.tgz", - "integrity": "sha512-cRzEj7c0OL4Mw2v6nwzttyOZe8XY/Z8G0rzmWQZTBi/jjwyw/U4uqKtUORXQrR5bAZZnbTI/feRV/R7hc4jQYQ==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-character": "^1.0.0", - "micromark-util-types": "^1.0.0" - } - }, - "node_modules/micromark-factory-space/node_modules/micromark-util-types": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/micromark-util-types/-/micromark-util-types-1.1.0.tgz", - "integrity": "sha512-ukRBgie8TIAcacscVHSiddHjO4k/q3pnedmzMQ4iwDcK0FtFCohKOlFbaOL/mPgfnPsL3C1ZyxJa4sbWrBl3jg==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT" - }, - "node_modules/micromark-factory-title": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/micromark-factory-title/-/micromark-factory-title-2.0.0.tgz", - "integrity": "sha512-jY8CSxmpWLOxS+t8W+FG3Xigc0RDQA9bKMY/EwILvsesiRniiVMejYTE4wumNc2f4UbAa4WsHqe3J1QS1sli+A==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-factory-space": "^2.0.0", - "micromark-util-character": "^2.0.0", - "micromark-util-symbol": "^2.0.0", - "micromark-util-types": "^2.0.0" - } - }, - "node_modules/micromark-factory-title/node_modules/micromark-factory-space": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/micromark-factory-space/-/micromark-factory-space-2.0.0.tgz", - "integrity": "sha512-TKr+LIDX2pkBJXFLzpyPyljzYK3MtmllMUMODTQJIUfDGncESaqB90db9IAUcz4AZAJFdd8U9zOp9ty1458rxg==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-character": "^2.0.0", - "micromark-util-types": "^2.0.0" - } - }, - "node_modules/micromark-factory-title/node_modules/micromark-util-character": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/micromark-util-character/-/micromark-util-character-2.1.0.tgz", - "integrity": "sha512-KvOVV+X1yLBfs9dCBSopq/+G1PcgT3lAK07mC4BzXi5E7ahzMAF8oIupDDJ6mievI6F+lAATkbQQlQixJfT3aQ==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-symbol": "^2.0.0", - "micromark-util-types": "^2.0.0" - } - }, - "node_modules/micromark-factory-title/node_modules/micromark-util-symbol": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/micromark-util-symbol/-/micromark-util-symbol-2.0.0.tgz", - "integrity": "sha512-8JZt9ElZ5kyTnO94muPxIGS8oyElRJaiJO8EzV6ZSyGQ1Is8xwl4Q45qU5UOg+bGH4AikWziz0iN4sFLWs8PGw==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT" - }, - "node_modules/micromark-factory-whitespace": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/micromark-factory-whitespace/-/micromark-factory-whitespace-2.0.0.tgz", - "integrity": "sha512-28kbwaBjc5yAI1XadbdPYHX/eDnqaUFVikLwrO7FDnKG7lpgxnvk/XGRhX/PN0mOZ+dBSZ+LgunHS+6tYQAzhA==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-factory-space": "^2.0.0", - "micromark-util-character": "^2.0.0", - "micromark-util-symbol": "^2.0.0", - "micromark-util-types": "^2.0.0" - } - }, - "node_modules/micromark-factory-whitespace/node_modules/micromark-factory-space": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/micromark-factory-space/-/micromark-factory-space-2.0.0.tgz", - "integrity": "sha512-TKr+LIDX2pkBJXFLzpyPyljzYK3MtmllMUMODTQJIUfDGncESaqB90db9IAUcz4AZAJFdd8U9zOp9ty1458rxg==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-character": "^2.0.0", - "micromark-util-types": "^2.0.0" - } - }, - "node_modules/micromark-factory-whitespace/node_modules/micromark-util-character": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/micromark-util-character/-/micromark-util-character-2.1.0.tgz", - "integrity": "sha512-KvOVV+X1yLBfs9dCBSopq/+G1PcgT3lAK07mC4BzXi5E7ahzMAF8oIupDDJ6mievI6F+lAATkbQQlQixJfT3aQ==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-symbol": "^2.0.0", - "micromark-util-types": "^2.0.0" - } - }, - "node_modules/micromark-factory-whitespace/node_modules/micromark-util-symbol": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/micromark-util-symbol/-/micromark-util-symbol-2.0.0.tgz", - "integrity": "sha512-8JZt9ElZ5kyTnO94muPxIGS8oyElRJaiJO8EzV6ZSyGQ1Is8xwl4Q45qU5UOg+bGH4AikWziz0iN4sFLWs8PGw==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT" - }, - "node_modules/micromark-util-character": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/micromark-util-character/-/micromark-util-character-1.2.0.tgz", - "integrity": "sha512-lXraTwcX3yH/vMDaFWCQJP1uIszLVebzUa3ZHdrgxr7KEU/9mL4mVgCpGbyhvNLNlauROiNUq7WN5u7ndbY6xg==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-symbol": "^1.0.0", - "micromark-util-types": "^1.0.0" - } - }, - "node_modules/micromark-util-character/node_modules/micromark-util-types": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/micromark-util-types/-/micromark-util-types-1.1.0.tgz", - "integrity": "sha512-ukRBgie8TIAcacscVHSiddHjO4k/q3pnedmzMQ4iwDcK0FtFCohKOlFbaOL/mPgfnPsL3C1ZyxJa4sbWrBl3jg==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT" - }, - "node_modules/micromark-util-chunked": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/micromark-util-chunked/-/micromark-util-chunked-2.0.0.tgz", - "integrity": "sha512-anK8SWmNphkXdaKgz5hJvGa7l00qmcaUQoMYsBwDlSKFKjc6gjGXPDw3FNL3Nbwq5L8gE+RCbGqTw49FK5Qyvg==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-symbol": "^2.0.0" - } - }, - "node_modules/micromark-util-chunked/node_modules/micromark-util-symbol": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/micromark-util-symbol/-/micromark-util-symbol-2.0.0.tgz", - "integrity": "sha512-8JZt9ElZ5kyTnO94muPxIGS8oyElRJaiJO8EzV6ZSyGQ1Is8xwl4Q45qU5UOg+bGH4AikWziz0iN4sFLWs8PGw==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT" - }, - "node_modules/micromark-util-classify-character": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/micromark-util-classify-character/-/micromark-util-classify-character-2.0.0.tgz", - "integrity": "sha512-S0ze2R9GH+fu41FA7pbSqNWObo/kzwf8rN/+IGlW/4tC6oACOs8B++bh+i9bVyNnwCcuksbFwsBme5OCKXCwIw==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-character": "^2.0.0", - "micromark-util-symbol": "^2.0.0", - "micromark-util-types": "^2.0.0" - } - }, - "node_modules/micromark-util-classify-character/node_modules/micromark-util-character": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/micromark-util-character/-/micromark-util-character-2.1.0.tgz", - "integrity": "sha512-KvOVV+X1yLBfs9dCBSopq/+G1PcgT3lAK07mC4BzXi5E7ahzMAF8oIupDDJ6mievI6F+lAATkbQQlQixJfT3aQ==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-symbol": "^2.0.0", - "micromark-util-types": "^2.0.0" - } - }, - "node_modules/micromark-util-classify-character/node_modules/micromark-util-symbol": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/micromark-util-symbol/-/micromark-util-symbol-2.0.0.tgz", - "integrity": "sha512-8JZt9ElZ5kyTnO94muPxIGS8oyElRJaiJO8EzV6ZSyGQ1Is8xwl4Q45qU5UOg+bGH4AikWziz0iN4sFLWs8PGw==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT" - }, - "node_modules/micromark-util-combine-extensions": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/micromark-util-combine-extensions/-/micromark-util-combine-extensions-2.0.0.tgz", - "integrity": "sha512-vZZio48k7ON0fVS3CUgFatWHoKbbLTK/rT7pzpJ4Bjp5JjkZeasRfrS9wsBdDJK2cJLHMckXZdzPSSr1B8a4oQ==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-chunked": "^2.0.0", - "micromark-util-types": "^2.0.0" - } - }, - "node_modules/micromark-util-decode-numeric-character-reference": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/micromark-util-decode-numeric-character-reference/-/micromark-util-decode-numeric-character-reference-2.0.1.tgz", - "integrity": "sha512-bmkNc7z8Wn6kgjZmVHOX3SowGmVdhYS7yBpMnuMnPzDq/6xwVA604DuOXMZTO1lvq01g+Adfa0pE2UKGlxL1XQ==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-symbol": "^2.0.0" - } - }, - "node_modules/micromark-util-decode-numeric-character-reference/node_modules/micromark-util-symbol": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/micromark-util-symbol/-/micromark-util-symbol-2.0.0.tgz", - "integrity": "sha512-8JZt9ElZ5kyTnO94muPxIGS8oyElRJaiJO8EzV6ZSyGQ1Is8xwl4Q45qU5UOg+bGH4AikWziz0iN4sFLWs8PGw==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT" - }, - "node_modules/micromark-util-decode-string": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/micromark-util-decode-string/-/micromark-util-decode-string-2.0.0.tgz", - "integrity": "sha512-r4Sc6leeUTn3P6gk20aFMj2ntPwn6qpDZqWvYmAG6NgvFTIlj4WtrAudLi65qYoaGdXYViXYw2pkmn7QnIFasA==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "decode-named-character-reference": "^1.0.0", - "micromark-util-character": "^2.0.0", - "micromark-util-decode-numeric-character-reference": "^2.0.0", - "micromark-util-symbol": "^2.0.0" - } - }, - "node_modules/micromark-util-decode-string/node_modules/micromark-util-character": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/micromark-util-character/-/micromark-util-character-2.1.0.tgz", - "integrity": "sha512-KvOVV+X1yLBfs9dCBSopq/+G1PcgT3lAK07mC4BzXi5E7ahzMAF8oIupDDJ6mievI6F+lAATkbQQlQixJfT3aQ==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-symbol": "^2.0.0", - "micromark-util-types": "^2.0.0" - } - }, - "node_modules/micromark-util-decode-string/node_modules/micromark-util-symbol": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/micromark-util-symbol/-/micromark-util-symbol-2.0.0.tgz", - "integrity": "sha512-8JZt9ElZ5kyTnO94muPxIGS8oyElRJaiJO8EzV6ZSyGQ1Is8xwl4Q45qU5UOg+bGH4AikWziz0iN4sFLWs8PGw==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT" - }, - "node_modules/micromark-util-encode": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/micromark-util-encode/-/micromark-util-encode-2.0.0.tgz", - "integrity": "sha512-pS+ROfCXAGLWCOc8egcBvT0kf27GoWMqtdarNfDcjb6YLuV5cM3ioG45Ys2qOVqeqSbjaKg72vU+Wby3eddPsA==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT" - }, - "node_modules/micromark-util-events-to-acorn": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/micromark-util-events-to-acorn/-/micromark-util-events-to-acorn-2.0.2.tgz", - "integrity": "sha512-Fk+xmBrOv9QZnEDguL9OI9/NQQp6Hz4FuQ4YmCb/5V7+9eAh1s6AYSvL20kHkD67YIg7EpE54TiSlcsf3vyZgA==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "@types/acorn": "^4.0.0", - "@types/estree": "^1.0.0", - "@types/unist": "^3.0.0", - "devlop": "^1.0.0", - "estree-util-visit": "^2.0.0", - "micromark-util-symbol": "^2.0.0", - "micromark-util-types": "^2.0.0", - "vfile-message": "^4.0.0" - } - }, - "node_modules/micromark-util-events-to-acorn/node_modules/micromark-util-symbol": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/micromark-util-symbol/-/micromark-util-symbol-2.0.0.tgz", - "integrity": "sha512-8JZt9ElZ5kyTnO94muPxIGS8oyElRJaiJO8EzV6ZSyGQ1Is8xwl4Q45qU5UOg+bGH4AikWziz0iN4sFLWs8PGw==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT" - }, - "node_modules/micromark-util-html-tag-name": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/micromark-util-html-tag-name/-/micromark-util-html-tag-name-2.0.0.tgz", - "integrity": "sha512-xNn4Pqkj2puRhKdKTm8t1YHC/BAjx6CEwRFXntTaRf/x16aqka6ouVoutm+QdkISTlT7e2zU7U4ZdlDLJd2Mcw==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT" - }, - "node_modules/micromark-util-normalize-identifier": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/micromark-util-normalize-identifier/-/micromark-util-normalize-identifier-2.0.0.tgz", - "integrity": "sha512-2xhYT0sfo85FMrUPtHcPo2rrp1lwbDEEzpx7jiH2xXJLqBuy4H0GgXk5ToU8IEwoROtXuL8ND0ttVa4rNqYK3w==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-symbol": "^2.0.0" - } - }, - "node_modules/micromark-util-normalize-identifier/node_modules/micromark-util-symbol": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/micromark-util-symbol/-/micromark-util-symbol-2.0.0.tgz", - "integrity": "sha512-8JZt9ElZ5kyTnO94muPxIGS8oyElRJaiJO8EzV6ZSyGQ1Is8xwl4Q45qU5UOg+bGH4AikWziz0iN4sFLWs8PGw==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT" - }, - "node_modules/micromark-util-resolve-all": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/micromark-util-resolve-all/-/micromark-util-resolve-all-2.0.0.tgz", - "integrity": "sha512-6KU6qO7DZ7GJkaCgwBNtplXCvGkJToU86ybBAUdavvgsCiG8lSSvYxr9MhwmQ+udpzywHsl4RpGJsYWG1pDOcA==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-types": "^2.0.0" - } - }, - "node_modules/micromark-util-sanitize-uri": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/micromark-util-sanitize-uri/-/micromark-util-sanitize-uri-2.0.0.tgz", - "integrity": "sha512-WhYv5UEcZrbAtlsnPuChHUAsu/iBPOVaEVsntLBIdpibO0ddy8OzavZz3iL2xVvBZOpolujSliP65Kq0/7KIYw==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-character": "^2.0.0", - "micromark-util-encode": "^2.0.0", - "micromark-util-symbol": "^2.0.0" - } - }, - "node_modules/micromark-util-sanitize-uri/node_modules/micromark-util-character": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/micromark-util-character/-/micromark-util-character-2.1.0.tgz", - "integrity": "sha512-KvOVV+X1yLBfs9dCBSopq/+G1PcgT3lAK07mC4BzXi5E7ahzMAF8oIupDDJ6mievI6F+lAATkbQQlQixJfT3aQ==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-symbol": "^2.0.0", - "micromark-util-types": "^2.0.0" - } - }, - "node_modules/micromark-util-sanitize-uri/node_modules/micromark-util-symbol": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/micromark-util-symbol/-/micromark-util-symbol-2.0.0.tgz", - "integrity": "sha512-8JZt9ElZ5kyTnO94muPxIGS8oyElRJaiJO8EzV6ZSyGQ1Is8xwl4Q45qU5UOg+bGH4AikWziz0iN4sFLWs8PGw==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT" - }, - "node_modules/micromark-util-subtokenize": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/micromark-util-subtokenize/-/micromark-util-subtokenize-2.0.1.tgz", - "integrity": "sha512-jZNtiFl/1aY73yS3UGQkutD0UbhTt68qnRpw2Pifmz5wV9h8gOVsN70v+Lq/f1rKaU/W8pxRe8y8Q9FX1AOe1Q==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "devlop": "^1.0.0", - "micromark-util-chunked": "^2.0.0", - "micromark-util-symbol": "^2.0.0", - "micromark-util-types": "^2.0.0" - } - }, - "node_modules/micromark-util-subtokenize/node_modules/micromark-util-symbol": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/micromark-util-symbol/-/micromark-util-symbol-2.0.0.tgz", - "integrity": "sha512-8JZt9ElZ5kyTnO94muPxIGS8oyElRJaiJO8EzV6ZSyGQ1Is8xwl4Q45qU5UOg+bGH4AikWziz0iN4sFLWs8PGw==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT" - }, - "node_modules/micromark-util-symbol": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/micromark-util-symbol/-/micromark-util-symbol-1.1.0.tgz", - "integrity": "sha512-uEjpEYY6KMs1g7QfJ2eX1SQEV+ZT4rUD3UcF6l57acZvLNK7PBZL+ty82Z1qhK1/yXIY4bdx04FKMgR0g4IAag==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT" - }, - "node_modules/micromark-util-types": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/micromark-util-types/-/micromark-util-types-2.0.0.tgz", - "integrity": "sha512-oNh6S2WMHWRZrmutsRmDDfkzKtxF+bc2VxLC9dvtrDIRFln627VsFP6fLMgTryGDljgLPjkrzQSDcPrjPyDJ5w==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT" - }, - "node_modules/micromark/node_modules/micromark-factory-space": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/micromark-factory-space/-/micromark-factory-space-2.0.0.tgz", - "integrity": "sha512-TKr+LIDX2pkBJXFLzpyPyljzYK3MtmllMUMODTQJIUfDGncESaqB90db9IAUcz4AZAJFdd8U9zOp9ty1458rxg==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-character": "^2.0.0", - "micromark-util-types": "^2.0.0" - } - }, - "node_modules/micromark/node_modules/micromark-util-character": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/micromark-util-character/-/micromark-util-character-2.1.0.tgz", - "integrity": "sha512-KvOVV+X1yLBfs9dCBSopq/+G1PcgT3lAK07mC4BzXi5E7ahzMAF8oIupDDJ6mievI6F+lAATkbQQlQixJfT3aQ==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-symbol": "^2.0.0", - "micromark-util-types": "^2.0.0" - } - }, - "node_modules/micromark/node_modules/micromark-util-symbol": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/micromark-util-symbol/-/micromark-util-symbol-2.0.0.tgz", - "integrity": "sha512-8JZt9ElZ5kyTnO94muPxIGS8oyElRJaiJO8EzV6ZSyGQ1Is8xwl4Q45qU5UOg+bGH4AikWziz0iN4sFLWs8PGw==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT" - }, - "node_modules/micromatch": { - "version": "4.0.8", - "resolved": "https://registry.npmjs.org/micromatch/-/micromatch-4.0.8.tgz", - "integrity": "sha512-PXwfBhYu0hBCPw8Dn0E+WDYb7af3dSLVWKi3HGv84IdF4TyFoC0ysxFd0Goxw7nSv4T/PzEJQxsYsEiFCKo2BA==", - "dependencies": { - "braces": "^3.0.3", - "picomatch": "^2.3.1" - }, - "engines": { - "node": ">=8.6" - } - }, - "node_modules/miller-rabin": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/miller-rabin/-/miller-rabin-4.0.1.tgz", - "integrity": "sha512-115fLhvZVqWwHPbClyntxEVfVDfl9DLLTuJvq3g2O/Oxi8AiNouAHvDSzHS0viUJc+V5vm3eq91Xwqn9dp4jRA==", - "license": "MIT", - "dependencies": { - "bn.js": "^4.0.0", - "brorand": "^1.0.1" - }, - "bin": { - "miller-rabin": "bin/miller-rabin" - } - }, - "node_modules/miller-rabin/node_modules/bn.js": { - "version": "4.12.0", - "resolved": "https://registry.npmjs.org/bn.js/-/bn.js-4.12.0.tgz", - "integrity": "sha512-c98Bf3tPniI+scsdk237ku1Dc3ujXQTSgyiPUDEOe7tRkhrqridvh8klBv0HCEso1OLOYcHuCv/cS6DNxKH+ZA==", - "license": "MIT" - }, - "node_modules/mime": { - "version": "1.6.0", - "resolved": "https://registry.npmjs.org/mime/-/mime-1.6.0.tgz", - "integrity": "sha512-x0Vn8spI+wuJ1O6S7gnbaQg8Pxh4NNHb7KSINmEWKiPE4RKOplvijn+NkmYmmRgP68mc70j2EbeTFRsrswaQeg==", - "bin": { - "mime": "cli.js" - }, - "engines": { - "node": ">=4" - } - }, - "node_modules/mime-db": { - "version": "1.33.0", - "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.33.0.tgz", - "integrity": "sha512-BHJ/EKruNIqJf/QahvxwQZXKygOQ256myeN/Ew+THcAa5q+PjyTTMMeNQC4DZw5AwfvelsUrA6B67NKMqXDbzQ==", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/mime-format": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/mime-format/-/mime-format-2.0.1.tgz", - "integrity": "sha512-XxU3ngPbEnrYnNbIX+lYSaYg0M01v6p2ntd2YaFksTu0vayaw5OJvbdRyWs07EYRlLED5qadUZ+xo+XhOvFhwg==", - "license": "Apache-2.0", - "dependencies": { - "charset": "^1.0.0" - } - }, - "node_modules/mime-types": { - "version": "2.1.18", - "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.18.tgz", - "integrity": "sha512-lc/aahn+t4/SWV/qcmumYjymLsWfN3ELhpmVuUFjgsORruuZPVSwAQryq+HHGvO/SI2KVX26bx+En+zhM8g8hQ==", - "license": "MIT", - "dependencies": { - "mime-db": "~1.33.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==", - "license": "MIT", - "engines": { - "node": ">=6" - } - }, - "node_modules/mimic-response": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/mimic-response/-/mimic-response-4.0.0.tgz", - "integrity": "sha512-e5ISH9xMYU0DzrT+jl8q2ze9D6eWBto+I8CNpe+VI+K2J/F/k3PdkdTdz4wvGVH4NTpo+NRYTVIuMQEMMcsLqg==", - "license": "MIT", - "engines": { - "node": "^12.20.0 || ^14.13.1 || >=16.0.0" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/mini-css-extract-plugin": { - "version": "2.9.2", - "resolved": "https://registry.npmjs.org/mini-css-extract-plugin/-/mini-css-extract-plugin-2.9.2.tgz", - "integrity": "sha512-GJuACcS//jtq4kCtd5ii/M0SZf7OZRH+BxdqXZHaJfb8TJiVl+NgQRPwiYt2EuqeSkNydn/7vP+bcE27C5mb9w==", - "license": "MIT", - "dependencies": { - "schema-utils": "^4.0.0", - "tapable": "^2.2.1" - }, - "engines": { - "node": ">= 12.13.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/webpack" - }, - "peerDependencies": { - "webpack": "^5.0.0" - } - }, - "node_modules/minimalistic-assert": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/minimalistic-assert/-/minimalistic-assert-1.0.1.tgz", - "integrity": "sha512-UtJcAD4yEaGtjPezWuO9wC4nwUnVH/8/Im3yEHQP4b67cXlD/Qr9hdITCU1xDbSEXg2XKNaP8jsReV7vQd00/A==", - "license": "ISC" - }, - "node_modules/minimalistic-crypto-utils": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/minimalistic-crypto-utils/-/minimalistic-crypto-utils-1.0.1.tgz", - "integrity": "sha512-JIYlbt6g8i5jKfJ3xz7rF0LXmv2TkDxBLUkiBeZ7bAx4GnnNMr8xFpGnOxn6GhTEHx3SjRrZEoU+j04prX1ktg==", - "license": "MIT" - }, - "node_modules/minimatch": { - "version": "3.1.2", - "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.1.2.tgz", - "integrity": "sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw==", - "license": "ISC", - "dependencies": { - "brace-expansion": "^1.1.7" - }, - "engines": { - "node": "*" - } - }, - "node_modules/minimist": { - "version": "1.2.8", - "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.8.tgz", - "integrity": "sha512-2yyAR8qBkN3YuheJanUpWC5U3bb5osDywNB8RzDVlDwDHbocAJveqqj1u8+SVD7jkWT4yvsHCpWqqWqAxb0zCA==", - "license": "MIT", - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/minipass": { - "version": "7.1.2", - "resolved": "https://registry.npmjs.org/minipass/-/minipass-7.1.2.tgz", - "integrity": "sha512-qOOzS1cBTWYF4BH8fVePDBOO9iptMnGUEZwNc/cMWnTV2nVLZ7VoNWEPHkYczZA0pdoA7dl6e7FL659nX9S2aw==", - "license": "ISC", - "engines": { - "node": ">=16 || 14 >=14.17" - } - }, - "node_modules/mri": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/mri/-/mri-1.2.0.tgz", - "integrity": "sha512-tzzskb3bG8LvYGFF/mDTpq3jpI6Q9wc3LEmBaghu+DdCssd1FakN7Bc0hVNmEyGq1bq3RgfkCb3cmQLpNPOroA==", - "license": "MIT", - "engines": { - "node": ">=4" - } - }, - "node_modules/mrmime": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/mrmime/-/mrmime-2.0.0.tgz", - "integrity": "sha512-eu38+hdgojoyq63s+yTpN4XMBdt5l8HhMhc4VKLO9KM5caLIBvUm4thi7fFaxyTmCKeNnXZ5pAlBwCUnhA09uw==", - "license": "MIT", - "engines": { - "node": ">=10" - } - }, - "node_modules/ms": { - "version": "2.1.2", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.2.tgz", - "integrity": "sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w==", - "license": "MIT" - }, - "node_modules/multicast-dns": { - "version": "7.2.5", - "resolved": "https://registry.npmjs.org/multicast-dns/-/multicast-dns-7.2.5.tgz", - "integrity": "sha512-2eznPJP8z2BFLX50tf0LuODrpINqP1RVIm/CObbTcBRITQgmC/TjcREF1NeTBzIcR5XO/ukWo+YHOjBbFwIupg==", - "license": "MIT", - "dependencies": { - "dns-packet": "^5.2.2", - "thunky": "^1.0.2" - }, - "bin": { - "multicast-dns": "cli.js" - } - }, - "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" - } - }, - "node_modules/mz": { - "version": "2.7.0", - "resolved": "https://registry.npmjs.org/mz/-/mz-2.7.0.tgz", - "integrity": "sha512-z81GNO7nnYMEhrGh9LeymoE4+Yr0Wn5McHIZMK5cfQCl+NDX08sCZgUc9/6MHni9IWuFLm1Z3HTCXu2z9fN62Q==", - "license": "MIT", - "dependencies": { - "any-promise": "^1.0.0", - "object-assign": "^4.0.1", - "thenify-all": "^1.0.0" - } - }, - "node_modules/nanoid": { - "version": "3.3.8", - "resolved": "https://registry.npmjs.org/nanoid/-/nanoid-3.3.8.tgz", - "integrity": "sha512-WNLf5Sd8oZxOm+TzppcYk8gVOgP+l58xNy58D0nbUnOxOWRWvlcCV4kUF7ltmI6PsrLl/BgKEyS4mqsGChFN0w==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/ai" - } - ], - "license": "MIT", - "bin": { - "nanoid": "bin/nanoid.cjs" - }, - "engines": { - "node": "^10 || ^12 || ^13.7 || ^14 || >=15.0.1" - } - }, - "node_modules/negotiator": { - "version": "0.6.3", - "resolved": "https://registry.npmjs.org/negotiator/-/negotiator-0.6.3.tgz", - "integrity": "sha512-+EUsqGPLsM+j/zdChZjsnX51g4XrHFOIXwfnCVPGlQk/k5giakcKsuxCObBRu6DSm9opw/O6slWbJdghQM4bBg==", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/neo-async": { - "version": "2.6.2", - "resolved": "https://registry.npmjs.org/neo-async/-/neo-async-2.6.2.tgz", - "integrity": "sha512-Yd3UES5mWCSqR+qNT93S3UoYUkqAZ9lLg8a7g9rimsWmYGK8cVToA4/sF3RrshdyV3sAGMXVUmpMYOw+dLpOuw==", - "license": "MIT" - }, - "node_modules/neotraverse": { - "version": "0.6.15", - "resolved": "https://registry.npmjs.org/neotraverse/-/neotraverse-0.6.15.tgz", - "integrity": "sha512-HZpdkco+JeXq0G+WWpMJ4NsX3pqb5O7eR9uGz3FfoFt+LYzU8iRWp49nJtud6hsDoywM8tIrDo3gjgmOqJA8LA==", - "license": "MIT", - "engines": { - "node": ">= 10" - } - }, - "node_modules/new-date": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/new-date/-/new-date-1.0.3.tgz", - "integrity": "sha512-0fsVvQPbo2I18DT2zVHpezmeeNYV2JaJSrseiHLc17GNOxJzUdx5mvSigPu8LtIfZSij5i1wXnXFspEs2CD6hA==", - "license": "SEE LICENSE IN LICENSE", - "dependencies": { - "@segment/isodate": "1.0.3" - } - }, - "node_modules/no-case": { - "version": "3.0.4", - "resolved": "https://registry.npmjs.org/no-case/-/no-case-3.0.4.tgz", - "integrity": "sha512-fgAN3jGAh+RoxUGZHTSOLJIqUc2wmoBwGR4tbpNAKmmovFoWq0OdRkb0VkldReO2a2iBT/OEulG9XSUc10r3zg==", - "license": "MIT", - "dependencies": { - "lower-case": "^2.0.2", - "tslib": "^2.0.3" - } - }, - "node_modules/node-addon-api": { - "version": "7.1.1", - "resolved": "https://registry.npmjs.org/node-addon-api/-/node-addon-api-7.1.1.tgz", - "integrity": "sha512-5m3bsyrjFWE1xf7nz7YXdN4udnVtXK6/Yfgn5qnahL6bCkf2yKt4k3nuTKAtT4r3IG8JNR2ncsIMdZuAzJjHQQ==", - "license": "MIT", - "optional": true - }, - "node_modules/node-emoji": { - "version": "2.1.3", - "resolved": "https://registry.npmjs.org/node-emoji/-/node-emoji-2.1.3.tgz", - "integrity": "sha512-E2WEOVsgs7O16zsURJ/eH8BqhF029wGpEOnv7Urwdo2wmQanOACwJQh0devF9D9RhoZru0+9JXIS0dBXIAz+lA==", - "license": "MIT", - "dependencies": { - "@sindresorhus/is": "^4.6.0", - "char-regex": "^1.0.2", - "emojilib": "^2.4.0", - "skin-tone": "^2.0.0" - }, - "engines": { - "node": ">=18" - } - }, - "node_modules/node-fetch": { - "version": "2.7.0", - "resolved": "https://registry.npmjs.org/node-fetch/-/node-fetch-2.7.0.tgz", - "integrity": "sha512-c4FRfUm/dbcWZ7U+1Wq0AwCyFL+3nt2bEw05wfxSz+DWpWsitgmSgYmy2dQdWyKC1694ELPqMs/YzUSNozLt8A==", - "license": "MIT", - "dependencies": { - "whatwg-url": "^5.0.0" - }, - "engines": { - "node": "4.x || >=6.0.0" - }, - "peerDependencies": { - "encoding": "^0.1.0" - }, - "peerDependenciesMeta": { - "encoding": { - "optional": true - } - } - }, - "node_modules/node-fetch-h2": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/node-fetch-h2/-/node-fetch-h2-2.3.0.tgz", - "integrity": "sha512-ofRW94Ab0T4AOh5Fk8t0h8OBWrmjb0SSB20xh1H8YnPV9EJ+f5AMoYSUQ2zgJ4Iq2HAK0I2l5/Nequ8YzFS3Hg==", - "license": "MIT", - "dependencies": { - "http2-client": "^1.2.5" - }, - "engines": { - "node": "4.x || >=6.0.0" - } - }, - "node_modules/node-forge": { - "version": "1.3.1", - "resolved": "https://registry.npmjs.org/node-forge/-/node-forge-1.3.1.tgz", - "integrity": "sha512-dPEtOeMvF9VMcYV/1Wb8CPoVAXtp6MKMlcbAt4ddqmGqUJ6fQZFXkNZNkNlfevtNkGtaSoXf/vNNNSvgrdXwtA==", - "license": "(BSD-3-Clause OR GPL-2.0)", - "engines": { - "node": ">= 6.13.0" - } - }, - "node_modules/node-polyfill-webpack-plugin": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/node-polyfill-webpack-plugin/-/node-polyfill-webpack-plugin-2.0.1.tgz", - "integrity": "sha512-ZUMiCnZkP1LF0Th2caY6J/eKKoA0TefpoVa68m/LQU1I/mE8rGt4fNYGgNuCcK+aG8P8P43nbeJ2RqJMOL/Y1A==", - "license": "MIT", - "dependencies": { - "assert": "^2.0.0", - "browserify-zlib": "^0.2.0", - "buffer": "^6.0.3", - "console-browserify": "^1.2.0", - "constants-browserify": "^1.0.0", - "crypto-browserify": "^3.12.0", - "domain-browser": "^4.22.0", - "events": "^3.3.0", - "filter-obj": "^2.0.2", - "https-browserify": "^1.0.0", - "os-browserify": "^0.3.0", - "path-browserify": "^1.0.1", - "process": "^0.11.10", - "punycode": "^2.1.1", - "querystring-es3": "^0.2.1", - "readable-stream": "^4.0.0", - "stream-browserify": "^3.0.0", - "stream-http": "^3.2.0", - "string_decoder": "^1.3.0", - "timers-browserify": "^2.0.12", - "tty-browserify": "^0.0.1", - "type-fest": "^2.14.0", - "url": "^0.11.0", - "util": "^0.12.4", - "vm-browserify": "^1.1.2" - }, - "engines": { - "node": ">=12" - }, - "peerDependencies": { - "webpack": ">=5" - } - }, - "node_modules/node-polyfill-webpack-plugin/node_modules/punycode": { - "version": "2.3.1", - "resolved": "https://registry.npmjs.org/punycode/-/punycode-2.3.1.tgz", - "integrity": "sha512-vYt7UD1U9Wg6138shLtLOvdAu+8DsC/ilFtEVHcH+wydcSpNE20AfSOduf6MkRFahL5FY7X1oU7nKVZFtfq8Fg==", - "license": "MIT", - "engines": { - "node": ">=6" - } - }, - "node_modules/node-polyfill-webpack-plugin/node_modules/readable-stream": { - "version": "4.5.2", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-4.5.2.tgz", - "integrity": "sha512-yjavECdqeZ3GLXNgRXgeQEdz9fvDDkNKyHnbHRFtOr7/LcfgBcmct7t/ET+HaCTqfh06OzoAxrkN/IfjJBVe+g==", - "license": "MIT", - "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/node-readfiles": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/node-readfiles/-/node-readfiles-0.2.0.tgz", - "integrity": "sha512-SU00ZarexNlE4Rjdm83vglt5Y9yiQ+XI1XpflWlb7q7UTN1JUItm69xMeiQCTxtTfnzt+83T8Cx+vI2ED++VDA==", - "license": "MIT", - "dependencies": { - "es6-promise": "^3.2.1" - } - }, - "node_modules/node-releases": { - "version": "2.0.18", - "resolved": "https://registry.npmjs.org/node-releases/-/node-releases-2.0.18.tgz", - "integrity": "sha512-d9VeXT4SJ7ZeOqGX6R5EM022wpL+eWPooLI+5UpWn2jCT1aosUQEhQP214x33Wkwx3JQMvIm+tIoVOdodFS40g==", - "license": "MIT" - }, - "node_modules/nodemon": { - "version": "3.1.7", - "resolved": "https://registry.npmjs.org/nodemon/-/nodemon-3.1.7.tgz", - "integrity": "sha512-hLj7fuMow6f0lbB0cD14Lz2xNjwsyruH251Pk4t/yIitCFJbmY1myuLlHm/q06aST4jg6EgAh74PIBBrRqpVAQ==", - "dev": true, - "license": "MIT", - "dependencies": { - "chokidar": "^3.5.2", - "debug": "^4", - "ignore-by-default": "^1.0.1", - "minimatch": "^3.1.2", - "pstree.remy": "^1.1.8", - "semver": "^7.5.3", - "simple-update-notifier": "^2.0.0", - "supports-color": "^5.5.0", - "touch": "^3.1.0", - "undefsafe": "^2.0.5" - }, - "bin": { - "nodemon": "bin/nodemon.js" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/nodemon" - } - }, - "node_modules/nodemon/node_modules/has-flag": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-3.0.0.tgz", - "integrity": "sha512-sKJf1+ceQBr4SMkvQnBDNDtf4TXpVhVGateu0t918bl30FnbE2m4vNLX+VWe/dpjlb+HugGYzW7uQXH98HPEYw==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=4" - } - }, - "node_modules/nodemon/node_modules/supports-color": { - "version": "5.5.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.5.0.tgz", - "integrity": "sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow==", - "dev": true, - "license": "MIT", - "dependencies": { - "has-flag": "^3.0.0" - }, - "engines": { - "node": ">=4" - } - }, - "node_modules/normalize-path": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/normalize-path/-/normalize-path-3.0.0.tgz", - "integrity": "sha512-6eZs5Ls3WtCisHWp9S2GUy8dqkpGi4BVSz3GaqiE6ezub0512ESztXUwUB6C6IKbQkY2Pnb/mD4WYojCRwcwLA==", - "license": "MIT", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/normalize-range": { - "version": "0.1.2", - "resolved": "https://registry.npmjs.org/normalize-range/-/normalize-range-0.1.2.tgz", - "integrity": "sha512-bdok/XvKII3nUpklnV6P2hxtMNrCboOjAcyBuQnWEhO665FwrSNRxU+AqpsyvO6LgGYPspN+lu5CLtw4jPRKNA==", - "license": "MIT", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/normalize-url": { - "version": "8.0.1", - "resolved": "https://registry.npmjs.org/normalize-url/-/normalize-url-8.0.1.tgz", - "integrity": "sha512-IO9QvjUMWxPQQhs60oOu10CRkWCiZzSUkzbXGGV9pviYl1fXYcvkzQ5jV9z8Y6un8ARoVRl4EtC6v6jNqbaJ/w==", - "license": "MIT", - "engines": { - "node": ">=14.16" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/npm-run-path": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/npm-run-path/-/npm-run-path-4.0.1.tgz", - "integrity": "sha512-S48WzZW777zhNIrn7gxOlISNAqi9ZC/uQFnRdbeIHhZhCA6UqpkOT8T1G7BvfdgP4Er8gF4sUbaS0i7QvIfCWw==", - "license": "MIT", - "dependencies": { - "path-key": "^3.0.0" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/nprogress": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/nprogress/-/nprogress-0.2.0.tgz", - "integrity": "sha512-I19aIingLgR1fmhftnbWWO3dXc0hSxqHQHQb3H8m+K3TnEn/iSeTZZOyvKXWqQESMwuUVnatlCnZdLBZZt2VSA==", - "license": "MIT" - }, - "node_modules/nth-check": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/nth-check/-/nth-check-2.1.1.tgz", - "integrity": "sha512-lqjrjmaOoAnWfMmBPL+XNnynZh2+swxiX3WUE0s4yEHI6m+AwrK2UZOimIRl3X/4QctVqS8AiZjFqyOGrMXb/w==", - "license": "BSD-2-Clause", - "dependencies": { - "boolbase": "^1.0.0" - }, - "funding": { - "url": "https://github.com/fb55/nth-check?sponsor=1" - } - }, - "node_modules/null-loader": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/null-loader/-/null-loader-4.0.1.tgz", - "integrity": "sha512-pxqVbi4U6N26lq+LmgIbB5XATP0VdZKOG25DhHi8btMmJJefGArFyDg1yc4U3hWCJbMqSrw0qyrz1UQX+qYXqg==", - "license": "MIT", - "dependencies": { - "loader-utils": "^2.0.0", - "schema-utils": "^3.0.0" - }, - "engines": { - "node": ">= 10.13.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/webpack" - }, - "peerDependencies": { - "webpack": "^4.0.0 || ^5.0.0" - } - }, - "node_modules/null-loader/node_modules/ajv": { - "version": "6.12.6", - "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz", - "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==", - "license": "MIT", - "dependencies": { - "fast-deep-equal": "^3.1.1", - "fast-json-stable-stringify": "^2.0.0", - "json-schema-traverse": "^0.4.1", - "uri-js": "^4.2.2" - }, - "funding": { - "type": "github", - "url": "https://github.com/sponsors/epoberezkin" - } - }, - "node_modules/null-loader/node_modules/ajv-keywords": { - "version": "3.5.2", - "resolved": "https://registry.npmjs.org/ajv-keywords/-/ajv-keywords-3.5.2.tgz", - "integrity": "sha512-5p6WTN0DdTGVQk6VjcEju19IgaHudalcfabD7yhDGeA6bcQnmL+CpveLJq/3hvfwd1aof6L386Ougkx6RfyMIQ==", - "license": "MIT", - "peerDependencies": { - "ajv": "^6.9.1" - } - }, - "node_modules/null-loader/node_modules/json-schema-traverse": { - "version": "0.4.1", - "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz", - "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==", - "license": "MIT" - }, - "node_modules/null-loader/node_modules/schema-utils": { - "version": "3.3.0", - "resolved": "https://registry.npmjs.org/schema-utils/-/schema-utils-3.3.0.tgz", - "integrity": "sha512-pN/yOAvcC+5rQ5nERGuwrjLlYvLTbCibnZ1I7B1LaiAz9BRBlE9GMgE/eqV30P7aJQUf7Ddimy/RsbYO/GrVGg==", - "license": "MIT", - "dependencies": { - "@types/json-schema": "^7.0.8", - "ajv": "^6.12.5", - "ajv-keywords": "^3.5.2" - }, - "engines": { - "node": ">= 10.13.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/webpack" - } - }, - "node_modules/oas-kit-common": { - "version": "1.0.8", - "resolved": "https://registry.npmjs.org/oas-kit-common/-/oas-kit-common-1.0.8.tgz", - "integrity": "sha512-pJTS2+T0oGIwgjGpw7sIRU8RQMcUoKCDWFLdBqKB2BNmGpbBMH2sdqAaOXUg8OzonZHU0L7vfJu1mJFEiYDWOQ==", - "license": "BSD-3-Clause", - "dependencies": { - "fast-safe-stringify": "^2.0.7" - } - }, - "node_modules/oas-linter": { - "version": "3.2.2", - "resolved": "https://registry.npmjs.org/oas-linter/-/oas-linter-3.2.2.tgz", - "integrity": "sha512-KEGjPDVoU5K6swgo9hJVA/qYGlwfbFx+Kg2QB/kd7rzV5N8N5Mg6PlsoCMohVnQmo+pzJap/F610qTodKzecGQ==", - "license": "BSD-3-Clause", - "dependencies": { - "@exodus/schemasafe": "^1.0.0-rc.2", - "should": "^13.2.1", - "yaml": "^1.10.0" - }, - "funding": { - "url": "https://github.com/Mermade/oas-kit?sponsor=1" - } - }, - "node_modules/oas-resolver": { - "version": "2.5.6", - "resolved": "https://registry.npmjs.org/oas-resolver/-/oas-resolver-2.5.6.tgz", - "integrity": "sha512-Yx5PWQNZomfEhPPOphFbZKi9W93CocQj18NlD2Pa4GWZzdZpSJvYwoiuurRI7m3SpcChrnO08hkuQDL3FGsVFQ==", - "license": "BSD-3-Clause", - "dependencies": { - "node-fetch-h2": "^2.3.0", - "oas-kit-common": "^1.0.8", - "reftools": "^1.1.9", - "yaml": "^1.10.0", - "yargs": "^17.0.1" - }, - "bin": { - "resolve": "resolve.js" - }, - "funding": { - "url": "https://github.com/Mermade/oas-kit?sponsor=1" - } - }, - "node_modules/oas-resolver-browser": { - "version": "2.5.6", - "resolved": "https://registry.npmjs.org/oas-resolver-browser/-/oas-resolver-browser-2.5.6.tgz", - "integrity": "sha512-Jw5elT/kwUJrnGaVuRWe1D7hmnYWB8rfDDjBnpQ+RYY/dzAewGXeTexXzt4fGEo6PUE4eqKqPWF79MZxxvMppA==", - "license": "BSD-3-Clause", - "dependencies": { - "node-fetch-h2": "^2.3.0", - "oas-kit-common": "^1.0.8", - "path-browserify": "^1.0.1", - "reftools": "^1.1.9", - "yaml": "^1.10.0", - "yargs": "^17.0.1" - }, - "bin": { - "resolve": "resolve.js" - }, - "funding": { - "url": "https://github.com/Mermade/oas-kit?sponsor=1" - } - }, - "node_modules/oas-schema-walker": { - "version": "1.1.5", - "resolved": "https://registry.npmjs.org/oas-schema-walker/-/oas-schema-walker-1.1.5.tgz", - "integrity": "sha512-2yucenq1a9YPmeNExoUa9Qwrt9RFkjqaMAA1X+U7sbb0AqBeTIdMHky9SQQ6iN94bO5NW0W4TRYXerG+BdAvAQ==", - "license": "BSD-3-Clause", - "funding": { - "url": "https://github.com/Mermade/oas-kit?sponsor=1" - } - }, - "node_modules/oas-validator": { - "version": "5.0.8", - "resolved": "https://registry.npmjs.org/oas-validator/-/oas-validator-5.0.8.tgz", - "integrity": "sha512-cu20/HE5N5HKqVygs3dt94eYJfBi0TsZvPVXDhbXQHiEityDN+RROTleefoKRKKJ9dFAF2JBkDHgvWj0sjKGmw==", - "license": "BSD-3-Clause", - "dependencies": { - "call-me-maybe": "^1.0.1", - "oas-kit-common": "^1.0.8", - "oas-linter": "^3.2.2", - "oas-resolver": "^2.5.6", - "oas-schema-walker": "^1.1.5", - "reftools": "^1.1.9", - "should": "^13.2.1", - "yaml": "^1.10.0" - }, - "funding": { - "url": "https://github.com/Mermade/oas-kit?sponsor=1" - } - }, - "node_modules/obj-case": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/obj-case/-/obj-case-0.2.1.tgz", - "integrity": "sha512-PquYBBTy+Y6Ob/O2574XHhDtHJlV1cJHMCgW+rDRc9J5hhmRelJB3k5dTK/3cVmFVtzvAKuENeuLpoyTzMzkOg==", - "license": "MIT" - }, - "node_modules/object-assign": { - "version": "4.1.1", - "resolved": "https://registry.npmjs.org/object-assign/-/object-assign-4.1.1.tgz", - "integrity": "sha512-rJgTQnkUnH1sFw8yT6VSU3zD3sWmu6sZhIseY8VX+GRu3P6F7Fu+JNDoXfklElbLJSnc3FUQHVe4cU5hj+BcUg==", - "license": "MIT", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/object-hash": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/object-hash/-/object-hash-3.0.0.tgz", - "integrity": "sha512-RSn9F68PjH9HqtltsSnqYC1XXoWe9Bju5+213R98cNGttag9q9yAOTzdbsqvIa7aNm5WffBZFpWYr2aWrklWAw==", - "license": "MIT", - "engines": { - "node": ">= 6" - } - }, - "node_modules/object-inspect": { - "version": "1.13.2", - "resolved": "https://registry.npmjs.org/object-inspect/-/object-inspect-1.13.2.tgz", - "integrity": "sha512-IRZSRuzJiynemAXPYtPe5BoI/RESNYR7TYm50MC5Mqbd3Jmw5y790sErYw3V6SryFJD64b74qQQs9wn5Bg/k3g==", - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/object-is": { - "version": "1.1.6", - "resolved": "https://registry.npmjs.org/object-is/-/object-is-1.1.6.tgz", - "integrity": "sha512-F8cZ+KfGlSGi09lJT7/Nd6KJZ9ygtvYC0/UYYLI9nmQKLMnydpB9yvbv9K1uSkEu7FU9vYPmVwLg328tX+ot3Q==", - "license": "MIT", - "dependencies": { - "call-bind": "^1.0.7", - "define-properties": "^1.2.1" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/object-keys": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/object-keys/-/object-keys-1.1.1.tgz", - "integrity": "sha512-NuAESUOUMrlIXOfHKzD6bpPu3tYt3xvjNdRIQ+FeT0lNb4K8WR70CaDxhuNguS2XG+GjkyMwOzsN5ZktImfhLA==", - "license": "MIT", - "engines": { - "node": ">= 0.4" - } - }, - "node_modules/object.assign": { - "version": "4.1.5", - "resolved": "https://registry.npmjs.org/object.assign/-/object.assign-4.1.5.tgz", - "integrity": "sha512-byy+U7gp+FVwmyzKPYhW2h5l3crpmGsxl7X2s8y43IgxvG4g3QZ6CffDtsNQy1WsmZpQbO+ybo0AlW7TY6DcBQ==", - "license": "MIT", - "dependencies": { - "call-bind": "^1.0.5", - "define-properties": "^1.2.1", - "has-symbols": "^1.0.3", - "object-keys": "^1.1.1" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/obuf": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/obuf/-/obuf-1.1.2.tgz", - "integrity": "sha512-PX1wu0AmAdPqOL1mWhqmlOd8kOIZQwGZw6rh7uby9fTc5lhaOWFLX3I6R1hrF9k3zUY40e6igsLGkDXK92LJNg==", - "license": "MIT" - }, - "node_modules/on-finished": { - "version": "2.4.1", - "resolved": "https://registry.npmjs.org/on-finished/-/on-finished-2.4.1.tgz", - "integrity": "sha512-oVlzkg3ENAhCk2zdv7IJwd/QUD4z2RxRwpkcGY8psCVcCYZNq4wYnVWALHM+brtuJjePWiYF/ClmuDr8Ch5+kg==", - "dependencies": { - "ee-first": "1.1.1" - }, - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/on-headers": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/on-headers/-/on-headers-1.0.2.tgz", - "integrity": "sha512-pZAE+FJLoyITytdqK0U5s+FIpjN0JP3OzFi/u8Rx+EV5/W+JTWGXG8xFzevE7AjBfDqHv/8vL8qQsIhHnqRkrA==", - "license": "MIT", - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/once": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", - "integrity": "sha512-lNaJgI+2Q5URQBkccEKHTQOPaXdUxnZZElQTZY0MFUAuaEqe1E+Nyvgdz/aIyNi6Z9MzO5dv1H8n58/GELp3+w==", - "license": "ISC", - "dependencies": { - "wrappy": "1" - } - }, - "node_modules/onetime": { - "version": "5.1.2", - "resolved": "https://registry.npmjs.org/onetime/-/onetime-5.1.2.tgz", - "integrity": "sha512-kbpaSSGJTWdAY5KPVeMOKXSrPtr8C8C7wodJbcsd51jRnmD+GZu8Y0VoU6Dm5Z4vWr0Ig/1NKuWRKf7j5aaYSg==", - "license": "MIT", - "dependencies": { - "mimic-fn": "^2.1.0" - }, - "engines": { - "node": ">=6" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/open": { - "version": "8.4.2", - "resolved": "https://registry.npmjs.org/open/-/open-8.4.2.tgz", - "integrity": "sha512-7x81NCL719oNbsq/3mh+hVrAWmFuEYUqrq/Iw3kUzH8ReypT9QQ0BLoJS7/G9k6N81XjW4qHWtjWwe/9eLy1EQ==", - "license": "MIT", - "dependencies": { - "define-lazy-prop": "^2.0.0", - "is-docker": "^2.1.1", - "is-wsl": "^2.2.0" - }, - "engines": { - "node": ">=12" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/openapi-to-postmanv2": { - "version": "4.24.0", - "resolved": "https://registry.npmjs.org/openapi-to-postmanv2/-/openapi-to-postmanv2-4.24.0.tgz", - "integrity": "sha512-SfWo8fftwTVmBs61ZY9SciNlQ7ddSBmPS7NTBdf+LyjHdzr2/TNuvFjyftGJ7Jnm48oghi+R9At2geq1NoBOLA==", - "license": "Apache-2.0", - "dependencies": { - "ajv": "8.11.0", - "ajv-draft-04": "1.0.0", - "ajv-formats": "2.1.1", - "async": "3.2.4", - "commander": "2.20.3", - "graphlib": "2.1.8", - "js-yaml": "4.1.0", - "json-pointer": "0.6.2", - "json-schema-merge-allof": "0.8.1", - "lodash": "4.17.21", - "neotraverse": "0.6.15", - "oas-resolver-browser": "2.5.6", - "object-hash": "3.0.0", - "path-browserify": "1.0.1", - "postman-collection": "^4.4.0", - "swagger2openapi": "7.0.8", - "yaml": "1.10.2" - }, - "bin": { - "openapi2postmanv2": "bin/openapi2postmanv2.js" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/openapi-to-postmanv2/node_modules/ajv": { - "version": "8.11.0", - "resolved": "https://registry.npmjs.org/ajv/-/ajv-8.11.0.tgz", - "integrity": "sha512-wGgprdCvMalC0BztXvitD2hC04YffAvtsUn93JbGXYLAtCUO4xd17mCCZQxUOItiBwZvJScWo8NIvQMQ71rdpg==", - "license": "MIT", - "dependencies": { - "fast-deep-equal": "^3.1.1", - "json-schema-traverse": "^1.0.0", - "require-from-string": "^2.0.2", - "uri-js": "^4.2.2" - }, - "funding": { - "type": "github", - "url": "https://github.com/sponsors/epoberezkin" - } - }, - "node_modules/openapi-to-postmanv2/node_modules/commander": { - "version": "2.20.3", - "resolved": "https://registry.npmjs.org/commander/-/commander-2.20.3.tgz", - "integrity": "sha512-GpVkmM8vF2vQUkj2LvZmD35JxeJOLCwJ9cUkugyk2nuhbv3+mJvpLYYt+0+USMxE+oj+ey/lJEnhZw75x/OMcQ==", - "license": "MIT" - }, - "node_modules/opener": { - "version": "1.5.2", - "resolved": "https://registry.npmjs.org/opener/-/opener-1.5.2.tgz", - "integrity": "sha512-ur5UIdyw5Y7yEj9wLzhqXiy6GZ3Mwx0yGI+5sMn2r0N0v3cKJvUmFH5yPP+WXh9e0xfyzyJX95D8l088DNFj7A==", - "license": "(WTFPL OR MIT)", - "bin": { - "opener": "bin/opener-bin.js" - } - }, - "node_modules/os-browserify": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/os-browserify/-/os-browserify-0.3.0.tgz", - "integrity": "sha512-gjcpUc3clBf9+210TRaDWbf+rZZZEshZ+DlXMRCeAjp0xhTrnQsKHypIy1J3d5hKdUzj69t708EHtU8P6bUn0A==", - "license": "MIT" - }, - "node_modules/p-cancelable": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/p-cancelable/-/p-cancelable-3.0.0.tgz", - "integrity": "sha512-mlVgR3PGuzlo0MmTdk4cXqXWlwQDLnONTAg6sm62XkMJEiRxN3GL3SffkYvqwonbkJBcrI7Uvv5Zh9yjvn2iUw==", - "license": "MIT", - "engines": { - "node": ">=12.20" - } - }, - "node_modules/p-limit": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-4.0.0.tgz", - "integrity": "sha512-5b0R4txpzjPWVw/cXXUResoD4hb6U/x9BH08L7nw+GN1sezDzPdxeRvpc9c433fZhBan/wusjbCsqwqm4EIBIQ==", - "license": "MIT", - "dependencies": { - "yocto-queue": "^1.0.0" - }, - "engines": { - "node": "^12.20.0 || ^14.13.1 || >=16.0.0" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/p-locate": { - "version": "6.0.0", - "resolved": "https://registry.npmjs.org/p-locate/-/p-locate-6.0.0.tgz", - "integrity": "sha512-wPrq66Llhl7/4AGC6I+cqxT07LhXvWL08LNXz1fENOw0Ap4sRZZ/gZpTTJ5jpurzzzfS2W/Ge9BY3LgLjCShcw==", - "license": "MIT", - "dependencies": { - "p-limit": "^4.0.0" - }, - "engines": { - "node": "^12.20.0 || ^14.13.1 || >=16.0.0" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/p-map": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/p-map/-/p-map-4.0.0.tgz", - "integrity": "sha512-/bjOqmgETBYB5BoEeGVea8dmvHb2m9GLy1E9W43yeyfP6QQCZGFNa+XRceJEuDB6zqr+gKpIAmlLebMpykw/MQ==", - "license": "MIT", - "dependencies": { - "aggregate-error": "^3.0.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/p-retry": { - "version": "4.6.2", - "resolved": "https://registry.npmjs.org/p-retry/-/p-retry-4.6.2.tgz", - "integrity": "sha512-312Id396EbJdvRONlngUx0NydfrIQ5lsYu0znKVUzVvArzEIt08V1qhtyESbGVd1FGX7UKtiFp5uwKZdM8wIuQ==", - "license": "MIT", - "dependencies": { - "@types/retry": "0.12.0", - "retry": "^0.13.1" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/p-try": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/p-try/-/p-try-2.2.0.tgz", - "integrity": "sha512-R4nPAVTAU0B9D35/Gk3uJf/7XYbQcyohSKdvAxIRSNghFl4e71hVoGnBNQz9cWaXxO2I10KTC+3jMdvvoKw6dQ==", - "license": "MIT", - "engines": { - "node": ">=6" - } - }, - "node_modules/package-json": { - "version": "8.1.1", - "resolved": "https://registry.npmjs.org/package-json/-/package-json-8.1.1.tgz", - "integrity": "sha512-cbH9IAIJHNj9uXi196JVsRlt7cHKak6u/e6AkL/bkRelZ7rlL3X1YKxsZwa36xipOEKAsdtmaG6aAJoM1fx2zA==", - "license": "MIT", - "dependencies": { - "got": "^12.1.0", - "registry-auth-token": "^5.0.1", - "registry-url": "^6.0.0", - "semver": "^7.3.7" - }, - "engines": { - "node": ">=14.16" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/package-json-from-dist": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/package-json-from-dist/-/package-json-from-dist-1.0.1.tgz", - "integrity": "sha512-UEZIS3/by4OC8vL3P2dTXRETpebLI2NiI5vIrjaD/5UtrkFX/tNbwjTSRAGC/+7CAo2pIcBaRgWmcBBHcsaCIw==", - "license": "BlueOak-1.0.0" - }, - "node_modules/pako": { - "version": "1.0.11", - "resolved": "https://registry.npmjs.org/pako/-/pako-1.0.11.tgz", - "integrity": "sha512-4hLB8Py4zZce5s4yd9XzopqwVv/yGNhV1Bl8NTmCq1763HeK2+EwVTv+leGeL13Dnh2wfbqowVPXCIO0z4taYw==", - "license": "(MIT AND Zlib)" - }, - "node_modules/param-case": { - "version": "3.0.4", - "resolved": "https://registry.npmjs.org/param-case/-/param-case-3.0.4.tgz", - "integrity": "sha512-RXlj7zCYokReqWpOPH9oYivUzLYZ5vAPIfEmCTNViosC78F8F0H9y7T7gG2M39ymgutxF5gcFEsyZQSph9Bp3A==", - "license": "MIT", - "dependencies": { - "dot-case": "^3.0.4", - "tslib": "^2.0.3" - } - }, - "node_modules/parent-module": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/parent-module/-/parent-module-1.0.1.tgz", - "integrity": "sha512-GQ2EWRpQV8/o+Aw8YqtfZZPfNRWZYkbidE9k5rpl/hC3vtHHBfGm2Ifi6qWV+coDGkrUKZAxE3Lot5kcsRlh+g==", - "license": "MIT", - "dependencies": { - "callsites": "^3.0.0" - }, - "engines": { - "node": ">=6" - } - }, - "node_modules/parse-asn1": { - "version": "5.1.7", - "resolved": "https://registry.npmjs.org/parse-asn1/-/parse-asn1-5.1.7.tgz", - "integrity": "sha512-CTM5kuWR3sx9IFamcl5ErfPl6ea/N8IYwiJ+vpeB2g+1iknv7zBl5uPwbMbRVznRVbrNY6lGuDoE5b30grmbqg==", - "license": "ISC", - "dependencies": { - "asn1.js": "^4.10.1", - "browserify-aes": "^1.2.0", - "evp_bytestokey": "^1.0.3", - "hash-base": "~3.0", - "pbkdf2": "^3.1.2", - "safe-buffer": "^5.2.1" - }, - "engines": { - "node": ">= 0.10" - } - }, - "node_modules/parse-entities": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/parse-entities/-/parse-entities-4.0.1.tgz", - "integrity": "sha512-SWzvYcSJh4d/SGLIOQfZ/CoNv6BTlI6YEQ7Nj82oDVnRpwe/Z/F1EMx42x3JAOwGBlCjeCH0BRJQbQ/opHL17w==", - "license": "MIT", - "dependencies": { - "@types/unist": "^2.0.0", - "character-entities": "^2.0.0", - "character-entities-legacy": "^3.0.0", - "character-reference-invalid": "^2.0.0", - "decode-named-character-reference": "^1.0.0", - "is-alphanumerical": "^2.0.0", - "is-decimal": "^2.0.0", - "is-hexadecimal": "^2.0.0" - }, - "funding": { - "type": "github", - "url": "https://github.com/sponsors/wooorm" - } - }, - "node_modules/parse-entities/node_modules/@types/unist": { - "version": "2.0.10", - "resolved": "https://registry.npmjs.org/@types/unist/-/unist-2.0.10.tgz", - "integrity": "sha512-IfYcSBWE3hLpBg8+X2SEa8LVkJdJEkT2Ese2aaLs3ptGdVtABxndrMaxuFlQ1qdFf9Q5rDvDpxI3WwgvKFAsQA==", - "license": "MIT" - }, - "node_modules/parse-json": { - "version": "5.2.0", - "resolved": "https://registry.npmjs.org/parse-json/-/parse-json-5.2.0.tgz", - "integrity": "sha512-ayCKvm/phCGxOkYRSCM82iDwct8/EonSEgCSxWxD7ve6jHggsFl4fZVQBPRNgQoKiuV/odhFrGzQXZwbifC8Rg==", - "license": "MIT", - "dependencies": { - "@babel/code-frame": "^7.0.0", - "error-ex": "^1.3.1", - "json-parse-even-better-errors": "^2.3.0", - "lines-and-columns": "^1.1.6" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/parse-numeric-range": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/parse-numeric-range/-/parse-numeric-range-1.3.0.tgz", - "integrity": "sha512-twN+njEipszzlMJd4ONUYgSfZPDxgHhT9Ahed5uTigpQn90FggW4SA/AIPq/6a149fTbE9qBEcSwE3FAEp6wQQ==", - "license": "ISC" - }, - "node_modules/parse5": { - "version": "7.2.1", - "resolved": "https://registry.npmjs.org/parse5/-/parse5-7.2.1.tgz", - "integrity": "sha512-BuBYQYlv1ckiPdQi/ohiivi9Sagc9JG+Ozs0r7b/0iK3sKmrb0b9FdWdBbOdx6hBCM/F9Ir82ofnBhtZOjCRPQ==", - "license": "MIT", - "dependencies": { - "entities": "^4.5.0" - }, - "funding": { - "url": "https://github.com/inikulin/parse5?sponsor=1" - } - }, - "node_modules/parse5-htmlparser2-tree-adapter": { - "version": "7.1.0", - "resolved": "https://registry.npmjs.org/parse5-htmlparser2-tree-adapter/-/parse5-htmlparser2-tree-adapter-7.1.0.tgz", - "integrity": "sha512-ruw5xyKs6lrpo9x9rCZqZZnIUntICjQAd0Wsmp396Ul9lN/h+ifgVV1x1gZHi8euej6wTfpqX8j+BFQxF0NS/g==", - "license": "MIT", - "dependencies": { - "domhandler": "^5.0.3", - "parse5": "^7.0.0" - }, - "funding": { - "url": "https://github.com/inikulin/parse5?sponsor=1" - } - }, - "node_modules/parse5-parser-stream": { - "version": "7.1.2", - "resolved": "https://registry.npmjs.org/parse5-parser-stream/-/parse5-parser-stream-7.1.2.tgz", - "integrity": "sha512-JyeQc9iwFLn5TbvvqACIF/VXG6abODeB3Fwmv/TGdLk2LfbWkaySGY72at4+Ty7EkPZj854u4CrICqNk2qIbow==", - "license": "MIT", - "dependencies": { - "parse5": "^7.0.0" - }, - "funding": { - "url": "https://github.com/inikulin/parse5?sponsor=1" - } - }, - "node_modules/parseurl": { - "version": "1.3.3", - "resolved": "https://registry.npmjs.org/parseurl/-/parseurl-1.3.3.tgz", - "integrity": "sha512-CiyeOxFT/JZyN5m0z9PfXw4SCBJ6Sygz1Dpl0wqjlhDEGGBP1GnsUVEL0p63hoG1fcj3fHynXi9NYO4nWOL+qQ==", - "license": "MIT", - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/pascal-case": { - "version": "3.1.2", - "resolved": "https://registry.npmjs.org/pascal-case/-/pascal-case-3.1.2.tgz", - "integrity": "sha512-uWlGT3YSnK9x3BQJaOdcZwrnV6hPpd8jFH1/ucpiLRPh/2zCVJKS19E4GvYHvaCcACn3foXZ0cLB9Wrx1KGe5g==", - "license": "MIT", - "dependencies": { - "no-case": "^3.0.4", - "tslib": "^2.0.3" - } - }, - "node_modules/path": { - "version": "0.12.7", - "resolved": "https://registry.npmjs.org/path/-/path-0.12.7.tgz", - "integrity": "sha512-aXXC6s+1w7otVF9UletFkFcDsJeO7lSZBPUQhtb5O0xJe8LtYhj/GxldoL09bBj9+ZmE2hNoHqQSFMN5fikh4Q==", - "license": "MIT", - "dependencies": { - "process": "^0.11.1", - "util": "^0.10.3" - } - }, - "node_modules/path-browserify": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/path-browserify/-/path-browserify-1.0.1.tgz", - "integrity": "sha512-b7uo2UCUOYZcnF/3ID0lulOJi/bafxa1xPe7ZPsammBSpjSWQkjNxlt635YGS2MiR9GjvuXCtz2emr3jbsz98g==", - "license": "MIT" - }, - "node_modules/path-exists": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-5.0.0.tgz", - "integrity": "sha512-RjhtfwJOxzcFmNOi6ltcbcu4Iu+FL3zEj83dk4kAS+fVpTxXLO1b38RvJgT/0QwvV/L3aY9TAnyv0EOqW4GoMQ==", - "license": "MIT", - "engines": { - "node": "^12.20.0 || ^14.13.1 || >=16.0.0" - } - }, - "node_modules/path-is-absolute": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz", - "integrity": "sha512-AVbw3UJ2e9bq64vSaS9Am0fje1Pa8pbGqTTsmXfaIiMpnr5DlDhfJOuLj9Sf95ZPVDAUerDfEk88MPmPe7UCQg==", - "license": "MIT", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/path-is-inside": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/path-is-inside/-/path-is-inside-1.0.2.tgz", - "integrity": "sha512-DUWJr3+ULp4zXmol/SZkFf3JGsS9/SIv+Y3Rt93/UjPpDpklB5f1er4O3POIbUuUJ3FXgqte2Q7SrU6zAqwk8w==", - "license": "(WTFPL OR MIT)" - }, - "node_modules/path-key": { - "version": "3.1.1", - "resolved": "https://registry.npmjs.org/path-key/-/path-key-3.1.1.tgz", - "integrity": "sha512-ojmeN0qd+y0jszEtoY48r0Peq5dwMEkIlCOu6Q5f41lfkswXuKtYrhgoTpLnyIcHm24Uhqx+5Tqm2InSwLhE6Q==", - "license": "MIT", - "engines": { - "node": ">=8" - } - }, - "node_modules/path-parse": { - "version": "1.0.7", - "resolved": "https://registry.npmjs.org/path-parse/-/path-parse-1.0.7.tgz", - "integrity": "sha512-LDJzPVEEEPR+y48z93A0Ed0yXb8pAByGWo/k5YYdYgpY2/2EsOsksJrq7lOHxryrVOn1ejG6oAp8ahvOIQD8sw==", - "license": "MIT" - }, - "node_modules/path-root": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/path-root/-/path-root-0.1.1.tgz", - "integrity": "sha512-QLcPegTHF11axjfojBIoDygmS2E3Lf+8+jI6wOVmNVenrKSo3mFdSGiIgdSHenczw3wPtlVMQaFVwGmM7BJdtg==", - "license": "MIT", - "dependencies": { - "path-root-regex": "^0.1.0" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/path-root-regex": { - "version": "0.1.2", - "resolved": "https://registry.npmjs.org/path-root-regex/-/path-root-regex-0.1.2.tgz", - "integrity": "sha512-4GlJ6rZDhQZFE0DPVKh0e9jmZ5egZfxTkp7bcRDuPlJXbAwhxcl2dINPUAsjLdejqaLsCeg8axcLjIbvBjN4pQ==", - "license": "MIT", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/path-scurry": { - "version": "1.11.1", - "resolved": "https://registry.npmjs.org/path-scurry/-/path-scurry-1.11.1.tgz", - "integrity": "sha512-Xa4Nw17FS9ApQFJ9umLiJS4orGjm7ZzwUrwamcGQuHSzDyth9boKDaycYdDcZDuqYATXw4HFXgaqWTctW/v1HA==", - "license": "BlueOak-1.0.0", - "dependencies": { - "lru-cache": "^10.2.0", - "minipass": "^5.0.0 || ^6.0.2 || ^7.0.0" - }, - "engines": { - "node": ">=16 || 14 >=14.18" - }, - "funding": { - "url": "https://github.com/sponsors/isaacs" - } - }, - "node_modules/path-scurry/node_modules/lru-cache": { - "version": "10.4.3", - "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-10.4.3.tgz", - "integrity": "sha512-JNAzZcXrCt42VGLuYz0zfAzDfAvJWW6AfYlDBQyDV5DClI2m5sAmK+OIO7s59XfsRsWHp02jAJrRadPRGTt6SQ==", - "license": "ISC" - }, - "node_modules/path-to-regexp": { - "version": "1.9.0", - "resolved": "https://registry.npmjs.org/path-to-regexp/-/path-to-regexp-1.9.0.tgz", - "integrity": "sha512-xIp7/apCFJuUHdDLWe8O1HIkb0kQrOMb/0u6FXQjemHn/ii5LrIzU6bdECnsiTF/GjZkMEKg1xdiZwNqDYlZ6g==", - "license": "MIT", - "dependencies": { - "isarray": "0.0.1" - } - }, - "node_modules/path-type": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/path-type/-/path-type-4.0.0.tgz", - "integrity": "sha512-gDKb8aZMDeD/tZWs9P6+q0J9Mwkdl6xMV8TjnGP3qJVJ06bdMgkbBlLU8IdfOsIsFz2BW1rNVT3XuNEl8zPAvw==", - "license": "MIT", - "engines": { - "node": ">=8" - } - }, - "node_modules/path/node_modules/inherits": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", - "integrity": "sha512-x00IRNXNy63jwGkJmzPigoySHbaqpNuzKbBOmzK+g2OdZpQ9w+sxCN+VSB3ja7IAge2OP2qpfxTjeNcyjmW1uw==", - "license": "ISC" - }, - "node_modules/path/node_modules/util": { - "version": "0.10.4", - "resolved": "https://registry.npmjs.org/util/-/util-0.10.4.tgz", - "integrity": "sha512-0Pm9hTQ3se5ll1XihRic3FDIku70C+iHUdT/W926rSgHV5QgXsYbKZN8MSC3tJtSkhuROzvsQjAaFENRXr+19A==", - "license": "MIT", - "dependencies": { - "inherits": "2.0.3" - } - }, - "node_modules/pbkdf2": { - "version": "3.1.2", - "resolved": "https://registry.npmjs.org/pbkdf2/-/pbkdf2-3.1.2.tgz", - "integrity": "sha512-iuh7L6jA7JEGu2WxDwtQP1ddOpaJNC4KlDEFfdQajSGgGPNi4OyDc2R7QnbY2bR9QjBVGwgvTdNJZoE7RaxUMA==", - "license": "MIT", - "dependencies": { - "create-hash": "^1.1.2", - "create-hmac": "^1.1.4", - "ripemd160": "^2.0.1", - "safe-buffer": "^5.0.1", - "sha.js": "^2.4.8" - }, - "engines": { - "node": ">=0.12" - } - }, - "node_modules/periscopic": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/periscopic/-/periscopic-3.1.0.tgz", - "integrity": "sha512-vKiQ8RRtkl9P+r/+oefh25C3fhybptkHKCZSPlcXiJux2tJF55GnEj3BVn4A5gKfq9NWWXXrxkHBwVPUfH0opw==", - "license": "MIT", - "dependencies": { - "@types/estree": "^1.0.0", - "estree-walker": "^3.0.0", - "is-reference": "^3.0.0" - } - }, - "node_modules/picocolors": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/picocolors/-/picocolors-1.1.1.tgz", - "integrity": "sha512-xceH2snhtb5M9liqDsmEw56le376mTZkEX/jEb/RxNFyegNul7eNslCXP9FDj/Lcu0X8KEyMceP2ntpaHrDEVA==", - "license": "ISC" - }, - "node_modules/picomatch": { - "version": "2.3.1", - "resolved": "https://registry.npmjs.org/picomatch/-/picomatch-2.3.1.tgz", - "integrity": "sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA==", - "license": "MIT", - "engines": { - "node": ">=8.6" - }, - "funding": { - "url": "https://github.com/sponsors/jonschlinkert" - } - }, - "node_modules/pirates": { - "version": "4.0.6", - "resolved": "https://registry.npmjs.org/pirates/-/pirates-4.0.6.tgz", - "integrity": "sha512-saLsH7WeYYPiD25LDuLRRY/i+6HaPYr6G1OUlN39otzkSTxKnubR9RTxS3/Kk50s1g2JTgFwWQDQyplC5/SHZg==", - "license": "MIT", - "engines": { - "node": ">= 6" - } - }, - "node_modules/pkg-dir": { - "version": "7.0.0", - "resolved": "https://registry.npmjs.org/pkg-dir/-/pkg-dir-7.0.0.tgz", - "integrity": "sha512-Ie9z/WINcxxLp27BKOCHGde4ITq9UklYKDzVo1nhk5sqGEXU3FpkwP5GM2voTGJkGd9B3Otl+Q4uwSOeSUtOBA==", - "license": "MIT", - "dependencies": { - "find-up": "^6.3.0" - }, - "engines": { - "node": ">=14.16" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/pkg-up": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/pkg-up/-/pkg-up-3.1.0.tgz", - "integrity": "sha512-nDywThFk1i4BQK4twPQ6TA4RT8bDY96yeuCVBWL3ePARCiEKDRSrNGbFIgUJpLp+XeIR65v8ra7WuJOFUBtkMA==", - "license": "MIT", - "dependencies": { - "find-up": "^3.0.0" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/pkg-up/node_modules/find-up": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/find-up/-/find-up-3.0.0.tgz", - "integrity": "sha512-1yD6RmLI1XBfxugvORwlck6f75tYL+iR0jqwsOrOxMZyGYqUuDhJ0l4AXdO1iX/FTs9cBAMEk1gWSEx1kSbylg==", - "license": "MIT", - "dependencies": { - "locate-path": "^3.0.0" - }, - "engines": { - "node": ">=6" - } - }, - "node_modules/pkg-up/node_modules/locate-path": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/locate-path/-/locate-path-3.0.0.tgz", - "integrity": "sha512-7AO748wWnIhNqAuaty2ZWHkQHRSNfPVIsPIfwEOWO22AmaoVrWavlOcMR5nzTLNYvp36X220/maaRsrec1G65A==", - "license": "MIT", - "dependencies": { - "p-locate": "^3.0.0", - "path-exists": "^3.0.0" - }, - "engines": { - "node": ">=6" - } - }, - "node_modules/pkg-up/node_modules/p-limit": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-2.3.0.tgz", - "integrity": "sha512-//88mFWSJx8lxCzwdAABTJL2MyWB12+eIY7MDL2SqLmAkeKU9qxRvWuSyTjm3FUmpBEMuFfckAIqEaVGUDxb6w==", - "license": "MIT", - "dependencies": { - "p-try": "^2.0.0" - }, - "engines": { - "node": ">=6" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/pkg-up/node_modules/p-locate": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/p-locate/-/p-locate-3.0.0.tgz", - "integrity": "sha512-x+12w/To+4GFfgJhBEpiDcLozRJGegY+Ei7/z0tSLkMmxGZNybVMSfWj9aJn8Z5Fc7dBUNJOOVgPv2H7IwulSQ==", - "license": "MIT", - "dependencies": { - "p-limit": "^2.0.0" - }, - "engines": { - "node": ">=6" - } - }, - "node_modules/pkg-up/node_modules/path-exists": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-3.0.0.tgz", - "integrity": "sha512-bpC7GYwiDYQ4wYLe+FA8lhRjhQCMcQGuSgGGqDkg/QerRWw9CmGRT0iSOVRSZJ29NMLZgIzqaljJ63oaL4NIJQ==", - "license": "MIT", - "engines": { - "node": ">=4" - } - }, - "node_modules/pluralize": { - "version": "8.0.0", - "resolved": "https://registry.npmjs.org/pluralize/-/pluralize-8.0.0.tgz", - "integrity": "sha512-Nc3IT5yHzflTfbjgqWcCPpo7DaKy4FnpB0l/zCAW0Tc7jxAiuqSxHasntB3D7887LSrA93kDJ9IXovxJYxyLCA==", - "license": "MIT", - "engines": { - "node": ">=4" - } - }, - "node_modules/possible-typed-array-names": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/possible-typed-array-names/-/possible-typed-array-names-1.0.0.tgz", - "integrity": "sha512-d7Uw+eZoloe0EHDIYoe+bQ5WXnGMOpmiZFTuMWCwpjzzkL2nTjcKiAk4hh8TjnGye2TwWOk3UXucZ+3rbmBa8Q==", - "license": "MIT", - "engines": { - "node": ">= 0.4" - } - }, - "node_modules/postcss": { - "version": "8.5.1", - "resolved": "https://registry.npmjs.org/postcss/-/postcss-8.5.1.tgz", - "integrity": "sha512-6oz2beyjc5VMn/KV1pPw8fliQkhBXrVn1Z3TVyqZxU8kZpzEKhBdmCFqI6ZbmGtamQvQGuU1sgPTk8ZrXDD7jQ==", - "funding": [ - { - "type": "opencollective", - "url": "https://opencollective.com/postcss/" - }, - { - "type": "tidelift", - "url": "https://tidelift.com/funding/github/npm/postcss" - }, - { - "type": "github", - "url": "https://github.com/sponsors/ai" - } - ], - "license": "MIT", - "dependencies": { - "nanoid": "^3.3.8", - "picocolors": "^1.1.1", - "source-map-js": "^1.2.1" - }, - "engines": { - "node": "^10 || ^12 || >=14" - } - }, - "node_modules/postcss-attribute-case-insensitive": { - "version": "7.0.1", - "resolved": "https://registry.npmjs.org/postcss-attribute-case-insensitive/-/postcss-attribute-case-insensitive-7.0.1.tgz", - "integrity": "sha512-Uai+SupNSqzlschRyNx3kbCTWgY/2hcwtHEI/ej2LJWc9JJ77qKgGptd8DHwY1mXtZ7Aoh4z4yxfwMBue9eNgw==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT", - "dependencies": { - "postcss-selector-parser": "^7.0.0" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/postcss-attribute-case-insensitive/node_modules/postcss-selector-parser": { - "version": "7.0.0", - "resolved": "https://registry.npmjs.org/postcss-selector-parser/-/postcss-selector-parser-7.0.0.tgz", - "integrity": "sha512-9RbEr1Y7FFfptd/1eEdntyjMwLeghW1bHX9GWjXo19vx4ytPQhANltvVxDggzJl7mnWM+dX28kb6cyS/4iQjlQ==", - "license": "MIT", - "dependencies": { - "cssesc": "^3.0.0", - "util-deprecate": "^1.0.2" - }, - "engines": { - "node": ">=4" - } - }, - "node_modules/postcss-calc": { - "version": "9.0.1", - "resolved": "https://registry.npmjs.org/postcss-calc/-/postcss-calc-9.0.1.tgz", - "integrity": "sha512-TipgjGyzP5QzEhsOZUaIkeO5mKeMFpebWzRogWG/ysonUlnHcq5aJe0jOjpfzUU8PeSaBQnrE8ehR0QA5vs8PQ==", - "license": "MIT", - "dependencies": { - "postcss-selector-parser": "^6.0.11", - "postcss-value-parser": "^4.2.0" - }, - "engines": { - "node": "^14 || ^16 || >=18.0" - }, - "peerDependencies": { - "postcss": "^8.2.2" - } - }, - "node_modules/postcss-clamp": { - "version": "4.1.0", - "resolved": "https://registry.npmjs.org/postcss-clamp/-/postcss-clamp-4.1.0.tgz", - "integrity": "sha512-ry4b1Llo/9zz+PKC+030KUnPITTJAHeOwjfAyyB60eT0AorGLdzp52s31OsPRHRf8NchkgFoG2y6fCfn1IV1Ow==", - "license": "MIT", - "dependencies": { - "postcss-value-parser": "^4.2.0" - }, - "engines": { - "node": ">=7.6.0" - }, - "peerDependencies": { - "postcss": "^8.4.6" - } - }, - "node_modules/postcss-color-functional-notation": { - "version": "7.0.7", - "resolved": "https://registry.npmjs.org/postcss-color-functional-notation/-/postcss-color-functional-notation-7.0.7.tgz", - "integrity": "sha512-EZvAHsvyASX63vXnyXOIynkxhaHRSsdb7z6yiXKIovGXAolW4cMZ3qoh7k3VdTsLBS6VGdksGfIo3r6+waLoOw==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "dependencies": { - "@csstools/css-color-parser": "^3.0.7", - "@csstools/css-parser-algorithms": "^3.0.4", - "@csstools/css-tokenizer": "^3.0.3", - "@csstools/postcss-progressive-custom-properties": "^4.0.0", - "@csstools/utilities": "^2.0.0" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/postcss-color-hex-alpha": { - "version": "10.0.0", - "resolved": "https://registry.npmjs.org/postcss-color-hex-alpha/-/postcss-color-hex-alpha-10.0.0.tgz", - "integrity": "sha512-1kervM2cnlgPs2a8Vt/Qbe5cQ++N7rkYo/2rz2BkqJZIHQwaVuJgQH38REHrAi4uM0b1fqxMkWYmese94iMp3w==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT", - "dependencies": { - "@csstools/utilities": "^2.0.0", - "postcss-value-parser": "^4.2.0" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/postcss-color-rebeccapurple": { - "version": "10.0.0", - "resolved": "https://registry.npmjs.org/postcss-color-rebeccapurple/-/postcss-color-rebeccapurple-10.0.0.tgz", - "integrity": "sha512-JFta737jSP+hdAIEhk1Vs0q0YF5P8fFcj+09pweS8ktuGuZ8pPlykHsk6mPxZ8awDl4TrcxUqJo9l1IhVr/OjQ==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "dependencies": { - "@csstools/utilities": "^2.0.0", - "postcss-value-parser": "^4.2.0" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/postcss-colormin": { - "version": "6.1.0", - "resolved": "https://registry.npmjs.org/postcss-colormin/-/postcss-colormin-6.1.0.tgz", - "integrity": "sha512-x9yX7DOxeMAR+BgGVnNSAxmAj98NX/YxEMNFP+SDCEeNLb2r3i6Hh1ksMsnW8Ub5SLCpbescQqn9YEbE9554Sw==", - "license": "MIT", - "dependencies": { - "browserslist": "^4.23.0", - "caniuse-api": "^3.0.0", - "colord": "^2.9.3", - "postcss-value-parser": "^4.2.0" - }, - "engines": { - "node": "^14 || ^16 || >=18.0" - }, - "peerDependencies": { - "postcss": "^8.4.31" - } - }, - "node_modules/postcss-convert-values": { - "version": "6.1.0", - "resolved": "https://registry.npmjs.org/postcss-convert-values/-/postcss-convert-values-6.1.0.tgz", - "integrity": "sha512-zx8IwP/ts9WvUM6NkVSkiU902QZL1bwPhaVaLynPtCsOTqp+ZKbNi+s6XJg3rfqpKGA/oc7Oxk5t8pOQJcwl/w==", - "license": "MIT", - "dependencies": { - "browserslist": "^4.23.0", - "postcss-value-parser": "^4.2.0" - }, - "engines": { - "node": "^14 || ^16 || >=18.0" - }, - "peerDependencies": { - "postcss": "^8.4.31" - } - }, - "node_modules/postcss-custom-media": { - "version": "11.0.5", - "resolved": "https://registry.npmjs.org/postcss-custom-media/-/postcss-custom-media-11.0.5.tgz", - "integrity": "sha512-SQHhayVNgDvSAdX9NQ/ygcDQGEY+aSF4b/96z7QUX6mqL5yl/JgG/DywcF6fW9XbnCRE+aVYk+9/nqGuzOPWeQ==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT", - "dependencies": { - "@csstools/cascade-layer-name-parser": "^2.0.4", - "@csstools/css-parser-algorithms": "^3.0.4", - "@csstools/css-tokenizer": "^3.0.3", - "@csstools/media-query-list-parser": "^4.0.2" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/postcss-custom-properties": { - "version": "14.0.4", - "resolved": "https://registry.npmjs.org/postcss-custom-properties/-/postcss-custom-properties-14.0.4.tgz", - "integrity": "sha512-QnW8FCCK6q+4ierwjnmXF9Y9KF8q0JkbgVfvQEMa93x1GT8FvOiUevWCN2YLaOWyByeDX8S6VFbZEeWoAoXs2A==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT", - "dependencies": { - "@csstools/cascade-layer-name-parser": "^2.0.4", - "@csstools/css-parser-algorithms": "^3.0.4", - "@csstools/css-tokenizer": "^3.0.3", - "@csstools/utilities": "^2.0.0", - "postcss-value-parser": "^4.2.0" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/postcss-custom-selectors": { - "version": "8.0.4", - "resolved": "https://registry.npmjs.org/postcss-custom-selectors/-/postcss-custom-selectors-8.0.4.tgz", - "integrity": "sha512-ASOXqNvDCE0dAJ/5qixxPeL1aOVGHGW2JwSy7HyjWNbnWTQCl+fDc968HY1jCmZI0+BaYT5CxsOiUhavpG/7eg==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT", - "dependencies": { - "@csstools/cascade-layer-name-parser": "^2.0.4", - "@csstools/css-parser-algorithms": "^3.0.4", - "@csstools/css-tokenizer": "^3.0.3", - "postcss-selector-parser": "^7.0.0" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/postcss-custom-selectors/node_modules/postcss-selector-parser": { - "version": "7.0.0", - "resolved": "https://registry.npmjs.org/postcss-selector-parser/-/postcss-selector-parser-7.0.0.tgz", - "integrity": "sha512-9RbEr1Y7FFfptd/1eEdntyjMwLeghW1bHX9GWjXo19vx4ytPQhANltvVxDggzJl7mnWM+dX28kb6cyS/4iQjlQ==", - "license": "MIT", - "dependencies": { - "cssesc": "^3.0.0", - "util-deprecate": "^1.0.2" - }, - "engines": { - "node": ">=4" - } - }, - "node_modules/postcss-dir-pseudo-class": { - "version": "9.0.1", - "resolved": "https://registry.npmjs.org/postcss-dir-pseudo-class/-/postcss-dir-pseudo-class-9.0.1.tgz", - "integrity": "sha512-tRBEK0MHYvcMUrAuYMEOa0zg9APqirBcgzi6P21OhxtJyJADo/SWBwY1CAwEohQ/6HDaa9jCjLRG7K3PVQYHEA==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "dependencies": { - "postcss-selector-parser": "^7.0.0" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/postcss-dir-pseudo-class/node_modules/postcss-selector-parser": { - "version": "7.0.0", - "resolved": "https://registry.npmjs.org/postcss-selector-parser/-/postcss-selector-parser-7.0.0.tgz", - "integrity": "sha512-9RbEr1Y7FFfptd/1eEdntyjMwLeghW1bHX9GWjXo19vx4ytPQhANltvVxDggzJl7mnWM+dX28kb6cyS/4iQjlQ==", - "license": "MIT", - "dependencies": { - "cssesc": "^3.0.0", - "util-deprecate": "^1.0.2" - }, - "engines": { - "node": ">=4" - } - }, - "node_modules/postcss-discard-comments": { - "version": "6.0.2", - "resolved": "https://registry.npmjs.org/postcss-discard-comments/-/postcss-discard-comments-6.0.2.tgz", - "integrity": "sha512-65w/uIqhSBBfQmYnG92FO1mWZjJ4GL5b8atm5Yw2UgrwD7HiNiSSNwJor1eCFGzUgYnN/iIknhNRVqjrrpuglw==", - "license": "MIT", - "engines": { - "node": "^14 || ^16 || >=18.0" - }, - "peerDependencies": { - "postcss": "^8.4.31" - } - }, - "node_modules/postcss-discard-duplicates": { - "version": "6.0.3", - "resolved": "https://registry.npmjs.org/postcss-discard-duplicates/-/postcss-discard-duplicates-6.0.3.tgz", - "integrity": "sha512-+JA0DCvc5XvFAxwx6f/e68gQu/7Z9ud584VLmcgto28eB8FqSFZwtrLwB5Kcp70eIoWP/HXqz4wpo8rD8gpsTw==", - "license": "MIT", - "engines": { - "node": "^14 || ^16 || >=18.0" - }, - "peerDependencies": { - "postcss": "^8.4.31" - } - }, - "node_modules/postcss-discard-empty": { - "version": "6.0.3", - "resolved": "https://registry.npmjs.org/postcss-discard-empty/-/postcss-discard-empty-6.0.3.tgz", - "integrity": "sha512-znyno9cHKQsK6PtxL5D19Fj9uwSzC2mB74cpT66fhgOadEUPyXFkbgwm5tvc3bt3NAy8ltE5MrghxovZRVnOjQ==", - "license": "MIT", - "engines": { - "node": "^14 || ^16 || >=18.0" - }, - "peerDependencies": { - "postcss": "^8.4.31" - } - }, - "node_modules/postcss-discard-overridden": { - "version": "6.0.2", - "resolved": "https://registry.npmjs.org/postcss-discard-overridden/-/postcss-discard-overridden-6.0.2.tgz", - "integrity": "sha512-j87xzI4LUggC5zND7KdjsI25APtyMuynXZSujByMaav2roV6OZX+8AaCUcZSWqckZpjAjRyFDdpqybgjFO0HJQ==", - "license": "MIT", - "engines": { - "node": "^14 || ^16 || >=18.0" - }, - "peerDependencies": { - "postcss": "^8.4.31" - } - }, - "node_modules/postcss-discard-unused": { - "version": "6.0.5", - "resolved": "https://registry.npmjs.org/postcss-discard-unused/-/postcss-discard-unused-6.0.5.tgz", - "integrity": "sha512-wHalBlRHkaNnNwfC8z+ppX57VhvS+HWgjW508esjdaEYr3Mx7Gnn2xA4R/CKf5+Z9S5qsqC+Uzh4ueENWwCVUA==", - "license": "MIT", - "dependencies": { - "postcss-selector-parser": "^6.0.16" - }, - "engines": { - "node": "^14 || ^16 || >=18.0" - }, - "peerDependencies": { - "postcss": "^8.4.31" - } - }, - "node_modules/postcss-double-position-gradients": { - "version": "6.0.0", - "resolved": "https://registry.npmjs.org/postcss-double-position-gradients/-/postcss-double-position-gradients-6.0.0.tgz", - "integrity": "sha512-JkIGah3RVbdSEIrcobqj4Gzq0h53GG4uqDPsho88SgY84WnpkTpI0k50MFK/sX7XqVisZ6OqUfFnoUO6m1WWdg==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "dependencies": { - "@csstools/postcss-progressive-custom-properties": "^4.0.0", - "@csstools/utilities": "^2.0.0", - "postcss-value-parser": "^4.2.0" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/postcss-focus-visible": { - "version": "10.0.1", - "resolved": "https://registry.npmjs.org/postcss-focus-visible/-/postcss-focus-visible-10.0.1.tgz", - "integrity": "sha512-U58wyjS/I1GZgjRok33aE8juW9qQgQUNwTSdxQGuShHzwuYdcklnvK/+qOWX1Q9kr7ysbraQ6ht6r+udansalA==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "dependencies": { - "postcss-selector-parser": "^7.0.0" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/postcss-focus-visible/node_modules/postcss-selector-parser": { - "version": "7.0.0", - "resolved": "https://registry.npmjs.org/postcss-selector-parser/-/postcss-selector-parser-7.0.0.tgz", - "integrity": "sha512-9RbEr1Y7FFfptd/1eEdntyjMwLeghW1bHX9GWjXo19vx4ytPQhANltvVxDggzJl7mnWM+dX28kb6cyS/4iQjlQ==", - "license": "MIT", - "dependencies": { - "cssesc": "^3.0.0", - "util-deprecate": "^1.0.2" - }, - "engines": { - "node": ">=4" - } - }, - "node_modules/postcss-focus-within": { - "version": "9.0.1", - "resolved": "https://registry.npmjs.org/postcss-focus-within/-/postcss-focus-within-9.0.1.tgz", - "integrity": "sha512-fzNUyS1yOYa7mOjpci/bR+u+ESvdar6hk8XNK/TRR0fiGTp2QT5N+ducP0n3rfH/m9I7H/EQU6lsa2BrgxkEjw==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "dependencies": { - "postcss-selector-parser": "^7.0.0" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/postcss-focus-within/node_modules/postcss-selector-parser": { - "version": "7.0.0", - "resolved": "https://registry.npmjs.org/postcss-selector-parser/-/postcss-selector-parser-7.0.0.tgz", - "integrity": "sha512-9RbEr1Y7FFfptd/1eEdntyjMwLeghW1bHX9GWjXo19vx4ytPQhANltvVxDggzJl7mnWM+dX28kb6cyS/4iQjlQ==", - "license": "MIT", - "dependencies": { - "cssesc": "^3.0.0", - "util-deprecate": "^1.0.2" - }, - "engines": { - "node": ">=4" - } - }, - "node_modules/postcss-font-variant": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/postcss-font-variant/-/postcss-font-variant-5.0.0.tgz", - "integrity": "sha512-1fmkBaCALD72CK2a9i468mA/+tr9/1cBxRRMXOUaZqO43oWPR5imcyPjXwuv7PXbCid4ndlP5zWhidQVVa3hmA==", - "license": "MIT", - "peerDependencies": { - "postcss": "^8.1.0" - } - }, - "node_modules/postcss-gap-properties": { - "version": "6.0.0", - "resolved": "https://registry.npmjs.org/postcss-gap-properties/-/postcss-gap-properties-6.0.0.tgz", - "integrity": "sha512-Om0WPjEwiM9Ru+VhfEDPZJAKWUd0mV1HmNXqp2C29z80aQ2uP9UVhLc7e3aYMIor/S5cVhoPgYQ7RtfeZpYTRw==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/postcss-image-set-function": { - "version": "7.0.0", - "resolved": "https://registry.npmjs.org/postcss-image-set-function/-/postcss-image-set-function-7.0.0.tgz", - "integrity": "sha512-QL7W7QNlZuzOwBTeXEmbVckNt1FSmhQtbMRvGGqqU4Nf4xk6KUEQhAoWuMzwbSv5jxiRiSZ5Tv7eiDB9U87znA==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "dependencies": { - "@csstools/utilities": "^2.0.0", - "postcss-value-parser": "^4.2.0" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/postcss-lab-function": { - "version": "7.0.7", - "resolved": "https://registry.npmjs.org/postcss-lab-function/-/postcss-lab-function-7.0.7.tgz", - "integrity": "sha512-+ONj2bpOQfsCKZE2T9VGMyVVdGcGUpr7u3SVfvkJlvhTRmDCfY25k4Jc8fubB9DclAPR4+w8uVtDZmdRgdAHig==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "dependencies": { - "@csstools/css-color-parser": "^3.0.7", - "@csstools/css-parser-algorithms": "^3.0.4", - "@csstools/css-tokenizer": "^3.0.3", - "@csstools/postcss-progressive-custom-properties": "^4.0.0", - "@csstools/utilities": "^2.0.0" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/postcss-loader": { - "version": "7.3.4", - "resolved": "https://registry.npmjs.org/postcss-loader/-/postcss-loader-7.3.4.tgz", - "integrity": "sha512-iW5WTTBSC5BfsBJ9daFMPVrLT36MrNiC6fqOZTTaHjBNX6Pfd5p+hSBqe/fEeNd7pc13QiAyGt7VdGMw4eRC4A==", - "license": "MIT", - "dependencies": { - "cosmiconfig": "^8.3.5", - "jiti": "^1.20.0", - "semver": "^7.5.4" - }, - "engines": { - "node": ">= 14.15.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/webpack" - }, - "peerDependencies": { - "postcss": "^7.0.0 || ^8.0.1", - "webpack": "^5.0.0" - } - }, - "node_modules/postcss-logical": { - "version": "8.0.0", - "resolved": "https://registry.npmjs.org/postcss-logical/-/postcss-logical-8.0.0.tgz", - "integrity": "sha512-HpIdsdieClTjXLOyYdUPAX/XQASNIwdKt5hoZW08ZOAiI+tbV0ta1oclkpVkW5ANU+xJvk3KkA0FejkjGLXUkg==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "dependencies": { - "postcss-value-parser": "^4.2.0" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/postcss-merge-idents": { - "version": "6.0.3", - "resolved": "https://registry.npmjs.org/postcss-merge-idents/-/postcss-merge-idents-6.0.3.tgz", - "integrity": "sha512-1oIoAsODUs6IHQZkLQGO15uGEbK3EAl5wi9SS8hs45VgsxQfMnxvt+L+zIr7ifZFIH14cfAeVe2uCTa+SPRa3g==", - "license": "MIT", - "dependencies": { - "cssnano-utils": "^4.0.2", - "postcss-value-parser": "^4.2.0" - }, - "engines": { - "node": "^14 || ^16 || >=18.0" - }, - "peerDependencies": { - "postcss": "^8.4.31" - } - }, - "node_modules/postcss-merge-longhand": { - "version": "6.0.5", - "resolved": "https://registry.npmjs.org/postcss-merge-longhand/-/postcss-merge-longhand-6.0.5.tgz", - "integrity": "sha512-5LOiordeTfi64QhICp07nzzuTDjNSO8g5Ksdibt44d+uvIIAE1oZdRn8y/W5ZtYgRH/lnLDlvi9F8btZcVzu3w==", - "license": "MIT", - "dependencies": { - "postcss-value-parser": "^4.2.0", - "stylehacks": "^6.1.1" - }, - "engines": { - "node": "^14 || ^16 || >=18.0" - }, - "peerDependencies": { - "postcss": "^8.4.31" - } - }, - "node_modules/postcss-merge-rules": { - "version": "6.1.1", - "resolved": "https://registry.npmjs.org/postcss-merge-rules/-/postcss-merge-rules-6.1.1.tgz", - "integrity": "sha512-KOdWF0gju31AQPZiD+2Ar9Qjowz1LTChSjFFbS+e2sFgc4uHOp3ZvVX4sNeTlk0w2O31ecFGgrFzhO0RSWbWwQ==", - "license": "MIT", - "dependencies": { - "browserslist": "^4.23.0", - "caniuse-api": "^3.0.0", - "cssnano-utils": "^4.0.2", - "postcss-selector-parser": "^6.0.16" - }, - "engines": { - "node": "^14 || ^16 || >=18.0" - }, - "peerDependencies": { - "postcss": "^8.4.31" - } - }, - "node_modules/postcss-minify-font-values": { - "version": "6.1.0", - "resolved": "https://registry.npmjs.org/postcss-minify-font-values/-/postcss-minify-font-values-6.1.0.tgz", - "integrity": "sha512-gklfI/n+9rTh8nYaSJXlCo3nOKqMNkxuGpTn/Qm0gstL3ywTr9/WRKznE+oy6fvfolH6dF+QM4nCo8yPLdvGJg==", - "license": "MIT", - "dependencies": { - "postcss-value-parser": "^4.2.0" - }, - "engines": { - "node": "^14 || ^16 || >=18.0" - }, - "peerDependencies": { - "postcss": "^8.4.31" - } - }, - "node_modules/postcss-minify-gradients": { - "version": "6.0.3", - "resolved": "https://registry.npmjs.org/postcss-minify-gradients/-/postcss-minify-gradients-6.0.3.tgz", - "integrity": "sha512-4KXAHrYlzF0Rr7uc4VrfwDJ2ajrtNEpNEuLxFgwkhFZ56/7gaE4Nr49nLsQDZyUe+ds+kEhf+YAUolJiYXF8+Q==", - "license": "MIT", - "dependencies": { - "colord": "^2.9.3", - "cssnano-utils": "^4.0.2", - "postcss-value-parser": "^4.2.0" - }, - "engines": { - "node": "^14 || ^16 || >=18.0" - }, - "peerDependencies": { - "postcss": "^8.4.31" - } - }, - "node_modules/postcss-minify-params": { - "version": "6.1.0", - "resolved": "https://registry.npmjs.org/postcss-minify-params/-/postcss-minify-params-6.1.0.tgz", - "integrity": "sha512-bmSKnDtyyE8ujHQK0RQJDIKhQ20Jq1LYiez54WiaOoBtcSuflfK3Nm596LvbtlFcpipMjgClQGyGr7GAs+H1uA==", - "license": "MIT", - "dependencies": { - "browserslist": "^4.23.0", - "cssnano-utils": "^4.0.2", - "postcss-value-parser": "^4.2.0" - }, - "engines": { - "node": "^14 || ^16 || >=18.0" - }, - "peerDependencies": { - "postcss": "^8.4.31" - } - }, - "node_modules/postcss-minify-selectors": { - "version": "6.0.4", - "resolved": "https://registry.npmjs.org/postcss-minify-selectors/-/postcss-minify-selectors-6.0.4.tgz", - "integrity": "sha512-L8dZSwNLgK7pjTto9PzWRoMbnLq5vsZSTu8+j1P/2GB8qdtGQfn+K1uSvFgYvgh83cbyxT5m43ZZhUMTJDSClQ==", - "license": "MIT", - "dependencies": { - "postcss-selector-parser": "^6.0.16" - }, - "engines": { - "node": "^14 || ^16 || >=18.0" - }, - "peerDependencies": { - "postcss": "^8.4.31" - } - }, - "node_modules/postcss-modules-extract-imports": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/postcss-modules-extract-imports/-/postcss-modules-extract-imports-3.1.0.tgz", - "integrity": "sha512-k3kNe0aNFQDAZGbin48pL2VNidTF0w4/eASDsxlyspobzU3wZQLOGj7L9gfRe0Jo9/4uud09DsjFNH7winGv8Q==", - "license": "ISC", - "engines": { - "node": "^10 || ^12 || >= 14" - }, - "peerDependencies": { - "postcss": "^8.1.0" - } - }, - "node_modules/postcss-modules-local-by-default": { - "version": "4.2.0", - "resolved": "https://registry.npmjs.org/postcss-modules-local-by-default/-/postcss-modules-local-by-default-4.2.0.tgz", - "integrity": "sha512-5kcJm/zk+GJDSfw+V/42fJ5fhjL5YbFDl8nVdXkJPLLW+Vf9mTD5Xe0wqIaDnLuL2U6cDNpTr+UQ+v2HWIBhzw==", - "license": "MIT", - "dependencies": { - "icss-utils": "^5.0.0", - "postcss-selector-parser": "^7.0.0", - "postcss-value-parser": "^4.1.0" - }, - "engines": { - "node": "^10 || ^12 || >= 14" - }, - "peerDependencies": { - "postcss": "^8.1.0" - } - }, - "node_modules/postcss-modules-local-by-default/node_modules/postcss-selector-parser": { - "version": "7.0.0", - "resolved": "https://registry.npmjs.org/postcss-selector-parser/-/postcss-selector-parser-7.0.0.tgz", - "integrity": "sha512-9RbEr1Y7FFfptd/1eEdntyjMwLeghW1bHX9GWjXo19vx4ytPQhANltvVxDggzJl7mnWM+dX28kb6cyS/4iQjlQ==", - "license": "MIT", - "dependencies": { - "cssesc": "^3.0.0", - "util-deprecate": "^1.0.2" - }, - "engines": { - "node": ">=4" - } - }, - "node_modules/postcss-modules-scope": { - "version": "3.2.1", - "resolved": "https://registry.npmjs.org/postcss-modules-scope/-/postcss-modules-scope-3.2.1.tgz", - "integrity": "sha512-m9jZstCVaqGjTAuny8MdgE88scJnCiQSlSrOWcTQgM2t32UBe+MUmFSO5t7VMSfAf/FJKImAxBav8ooCHJXCJA==", - "license": "ISC", - "dependencies": { - "postcss-selector-parser": "^7.0.0" - }, - "engines": { - "node": "^10 || ^12 || >= 14" - }, - "peerDependencies": { - "postcss": "^8.1.0" - } - }, - "node_modules/postcss-modules-scope/node_modules/postcss-selector-parser": { - "version": "7.0.0", - "resolved": "https://registry.npmjs.org/postcss-selector-parser/-/postcss-selector-parser-7.0.0.tgz", - "integrity": "sha512-9RbEr1Y7FFfptd/1eEdntyjMwLeghW1bHX9GWjXo19vx4ytPQhANltvVxDggzJl7mnWM+dX28kb6cyS/4iQjlQ==", - "license": "MIT", - "dependencies": { - "cssesc": "^3.0.0", - "util-deprecate": "^1.0.2" - }, - "engines": { - "node": ">=4" - } - }, - "node_modules/postcss-modules-values": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/postcss-modules-values/-/postcss-modules-values-4.0.0.tgz", - "integrity": "sha512-RDxHkAiEGI78gS2ofyvCsu7iycRv7oqw5xMWn9iMoR0N/7mf9D50ecQqUo5BZ9Zh2vH4bCUR/ktCqbB9m8vJjQ==", - "license": "ISC", - "dependencies": { - "icss-utils": "^5.0.0" - }, - "engines": { - "node": "^10 || ^12 || >= 14" - }, - "peerDependencies": { - "postcss": "^8.1.0" - } - }, - "node_modules/postcss-nesting": { - "version": "13.0.1", - "resolved": "https://registry.npmjs.org/postcss-nesting/-/postcss-nesting-13.0.1.tgz", - "integrity": "sha512-VbqqHkOBOt4Uu3G8Dm8n6lU5+9cJFxiuty9+4rcoyRPO9zZS1JIs6td49VIoix3qYqELHlJIn46Oih9SAKo+yQ==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "dependencies": { - "@csstools/selector-resolve-nested": "^3.0.0", - "@csstools/selector-specificity": "^5.0.0", - "postcss-selector-parser": "^7.0.0" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/postcss-nesting/node_modules/@csstools/selector-resolve-nested": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/@csstools/selector-resolve-nested/-/selector-resolve-nested-3.0.0.tgz", - "integrity": "sha512-ZoK24Yku6VJU1gS79a5PFmC8yn3wIapiKmPgun0hZgEI5AOqgH2kiPRsPz1qkGv4HL+wuDLH83yQyk6inMYrJQ==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss-selector-parser": "^7.0.0" - } - }, - "node_modules/postcss-nesting/node_modules/@csstools/selector-specificity": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/@csstools/selector-specificity/-/selector-specificity-5.0.0.tgz", - "integrity": "sha512-PCqQV3c4CoVm3kdPhyeZ07VmBRdH2EpMFA/pd9OASpOEC3aXNGoqPDAZ80D0cLpMBxnmk0+yNhGsEx31hq7Gtw==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss-selector-parser": "^7.0.0" - } - }, - "node_modules/postcss-nesting/node_modules/postcss-selector-parser": { - "version": "7.0.0", - "resolved": "https://registry.npmjs.org/postcss-selector-parser/-/postcss-selector-parser-7.0.0.tgz", - "integrity": "sha512-9RbEr1Y7FFfptd/1eEdntyjMwLeghW1bHX9GWjXo19vx4ytPQhANltvVxDggzJl7mnWM+dX28kb6cyS/4iQjlQ==", - "license": "MIT", - "dependencies": { - "cssesc": "^3.0.0", - "util-deprecate": "^1.0.2" - }, - "engines": { - "node": ">=4" - } - }, - "node_modules/postcss-normalize-charset": { - "version": "6.0.2", - "resolved": "https://registry.npmjs.org/postcss-normalize-charset/-/postcss-normalize-charset-6.0.2.tgz", - "integrity": "sha512-a8N9czmdnrjPHa3DeFlwqst5eaL5W8jYu3EBbTTkI5FHkfMhFZh1EGbku6jhHhIzTA6tquI2P42NtZ59M/H/kQ==", - "license": "MIT", - "engines": { - "node": "^14 || ^16 || >=18.0" - }, - "peerDependencies": { - "postcss": "^8.4.31" - } - }, - "node_modules/postcss-normalize-display-values": { - "version": "6.0.2", - "resolved": "https://registry.npmjs.org/postcss-normalize-display-values/-/postcss-normalize-display-values-6.0.2.tgz", - "integrity": "sha512-8H04Mxsb82ON/aAkPeq8kcBbAtI5Q2a64X/mnRRfPXBq7XeogoQvReqxEfc0B4WPq1KimjezNC8flUtC3Qz6jg==", - "license": "MIT", - "dependencies": { - "postcss-value-parser": "^4.2.0" - }, - "engines": { - "node": "^14 || ^16 || >=18.0" - }, - "peerDependencies": { - "postcss": "^8.4.31" - } - }, - "node_modules/postcss-normalize-positions": { - "version": "6.0.2", - "resolved": "https://registry.npmjs.org/postcss-normalize-positions/-/postcss-normalize-positions-6.0.2.tgz", - "integrity": "sha512-/JFzI441OAB9O7VnLA+RtSNZvQ0NCFZDOtp6QPFo1iIyawyXg0YI3CYM9HBy1WvwCRHnPep/BvI1+dGPKoXx/Q==", - "license": "MIT", - "dependencies": { - "postcss-value-parser": "^4.2.0" - }, - "engines": { - "node": "^14 || ^16 || >=18.0" - }, - "peerDependencies": { - "postcss": "^8.4.31" - } - }, - "node_modules/postcss-normalize-repeat-style": { - "version": "6.0.2", - "resolved": "https://registry.npmjs.org/postcss-normalize-repeat-style/-/postcss-normalize-repeat-style-6.0.2.tgz", - "integrity": "sha512-YdCgsfHkJ2jEXwR4RR3Tm/iOxSfdRt7jplS6XRh9Js9PyCR/aka/FCb6TuHT2U8gQubbm/mPmF6L7FY9d79VwQ==", - "license": "MIT", - "dependencies": { - "postcss-value-parser": "^4.2.0" - }, - "engines": { - "node": "^14 || ^16 || >=18.0" - }, - "peerDependencies": { - "postcss": "^8.4.31" - } - }, - "node_modules/postcss-normalize-string": { - "version": "6.0.2", - "resolved": "https://registry.npmjs.org/postcss-normalize-string/-/postcss-normalize-string-6.0.2.tgz", - "integrity": "sha512-vQZIivlxlfqqMp4L9PZsFE4YUkWniziKjQWUtsxUiVsSSPelQydwS8Wwcuw0+83ZjPWNTl02oxlIvXsmmG+CiQ==", - "license": "MIT", - "dependencies": { - "postcss-value-parser": "^4.2.0" - }, - "engines": { - "node": "^14 || ^16 || >=18.0" - }, - "peerDependencies": { - "postcss": "^8.4.31" - } - }, - "node_modules/postcss-normalize-timing-functions": { - "version": "6.0.2", - "resolved": "https://registry.npmjs.org/postcss-normalize-timing-functions/-/postcss-normalize-timing-functions-6.0.2.tgz", - "integrity": "sha512-a+YrtMox4TBtId/AEwbA03VcJgtyW4dGBizPl7e88cTFULYsprgHWTbfyjSLyHeBcK/Q9JhXkt2ZXiwaVHoMzA==", - "license": "MIT", - "dependencies": { - "postcss-value-parser": "^4.2.0" - }, - "engines": { - "node": "^14 || ^16 || >=18.0" - }, - "peerDependencies": { - "postcss": "^8.4.31" - } - }, - "node_modules/postcss-normalize-unicode": { - "version": "6.1.0", - "resolved": "https://registry.npmjs.org/postcss-normalize-unicode/-/postcss-normalize-unicode-6.1.0.tgz", - "integrity": "sha512-QVC5TQHsVj33otj8/JD869Ndr5Xcc/+fwRh4HAsFsAeygQQXm+0PySrKbr/8tkDKzW+EVT3QkqZMfFrGiossDg==", - "license": "MIT", - "dependencies": { - "browserslist": "^4.23.0", - "postcss-value-parser": "^4.2.0" - }, - "engines": { - "node": "^14 || ^16 || >=18.0" - }, - "peerDependencies": { - "postcss": "^8.4.31" - } - }, - "node_modules/postcss-normalize-url": { - "version": "6.0.2", - "resolved": "https://registry.npmjs.org/postcss-normalize-url/-/postcss-normalize-url-6.0.2.tgz", - "integrity": "sha512-kVNcWhCeKAzZ8B4pv/DnrU1wNh458zBNp8dh4y5hhxih5RZQ12QWMuQrDgPRw3LRl8mN9vOVfHl7uhvHYMoXsQ==", - "license": "MIT", - "dependencies": { - "postcss-value-parser": "^4.2.0" - }, - "engines": { - "node": "^14 || ^16 || >=18.0" - }, - "peerDependencies": { - "postcss": "^8.4.31" - } - }, - "node_modules/postcss-normalize-whitespace": { - "version": "6.0.2", - "resolved": "https://registry.npmjs.org/postcss-normalize-whitespace/-/postcss-normalize-whitespace-6.0.2.tgz", - "integrity": "sha512-sXZ2Nj1icbJOKmdjXVT9pnyHQKiSAyuNQHSgRCUgThn2388Y9cGVDR+E9J9iAYbSbLHI+UUwLVl1Wzco/zgv0Q==", - "license": "MIT", - "dependencies": { - "postcss-value-parser": "^4.2.0" - }, - "engines": { - "node": "^14 || ^16 || >=18.0" - }, - "peerDependencies": { - "postcss": "^8.4.31" - } - }, - "node_modules/postcss-opacity-percentage": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/postcss-opacity-percentage/-/postcss-opacity-percentage-3.0.0.tgz", - "integrity": "sha512-K6HGVzyxUxd/VgZdX04DCtdwWJ4NGLG212US4/LA1TLAbHgmAsTWVR86o+gGIbFtnTkfOpb9sCRBx8K7HO66qQ==", - "funding": [ - { - "type": "kofi", - "url": "https://ko-fi.com/mrcgrtz" - }, - { - "type": "liberapay", - "url": "https://liberapay.com/mrcgrtz" - } - ], - "license": "MIT", - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/postcss-ordered-values": { - "version": "6.0.2", - "resolved": "https://registry.npmjs.org/postcss-ordered-values/-/postcss-ordered-values-6.0.2.tgz", - "integrity": "sha512-VRZSOB+JU32RsEAQrO94QPkClGPKJEL/Z9PCBImXMhIeK5KAYo6slP/hBYlLgrCjFxyqvn5VC81tycFEDBLG1Q==", - "license": "MIT", - "dependencies": { - "cssnano-utils": "^4.0.2", - "postcss-value-parser": "^4.2.0" - }, - "engines": { - "node": "^14 || ^16 || >=18.0" - }, - "peerDependencies": { - "postcss": "^8.4.31" - } - }, - "node_modules/postcss-overflow-shorthand": { - "version": "6.0.0", - "resolved": "https://registry.npmjs.org/postcss-overflow-shorthand/-/postcss-overflow-shorthand-6.0.0.tgz", - "integrity": "sha512-BdDl/AbVkDjoTofzDQnwDdm/Ym6oS9KgmO7Gr+LHYjNWJ6ExORe4+3pcLQsLA9gIROMkiGVjjwZNoL/mpXHd5Q==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "dependencies": { - "postcss-value-parser": "^4.2.0" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/postcss-page-break": { - "version": "3.0.4", - "resolved": "https://registry.npmjs.org/postcss-page-break/-/postcss-page-break-3.0.4.tgz", - "integrity": "sha512-1JGu8oCjVXLa9q9rFTo4MbeeA5FMe00/9C7lN4va606Rdb+HkxXtXsmEDrIraQ11fGz/WvKWa8gMuCKkrXpTsQ==", - "license": "MIT", - "peerDependencies": { - "postcss": "^8" - } - }, - "node_modules/postcss-place": { - "version": "10.0.0", - "resolved": "https://registry.npmjs.org/postcss-place/-/postcss-place-10.0.0.tgz", - "integrity": "sha512-5EBrMzat2pPAxQNWYavwAfoKfYcTADJ8AXGVPcUZ2UkNloUTWzJQExgrzrDkh3EKzmAx1evfTAzF9I8NGcc+qw==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "dependencies": { - "postcss-value-parser": "^4.2.0" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/postcss-preset-env": { - "version": "10.1.3", - "resolved": "https://registry.npmjs.org/postcss-preset-env/-/postcss-preset-env-10.1.3.tgz", - "integrity": "sha512-9qzVhcMFU/MnwYHyYpJz4JhGku/4+xEiPTmhn0hj3IxnUYlEF9vbh7OC1KoLAnenS6Fgg43TKNp9xcuMeAi4Zw==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "dependencies": { - "@csstools/postcss-cascade-layers": "^5.0.1", - "@csstools/postcss-color-function": "^4.0.7", - "@csstools/postcss-color-mix-function": "^3.0.7", - "@csstools/postcss-content-alt-text": "^2.0.4", - "@csstools/postcss-exponential-functions": "^2.0.6", - "@csstools/postcss-font-format-keywords": "^4.0.0", - "@csstools/postcss-gamut-mapping": "^2.0.7", - "@csstools/postcss-gradients-interpolation-method": "^5.0.7", - "@csstools/postcss-hwb-function": "^4.0.7", - "@csstools/postcss-ic-unit": "^4.0.0", - "@csstools/postcss-initial": "^2.0.0", - "@csstools/postcss-is-pseudo-class": "^5.0.1", - "@csstools/postcss-light-dark-function": "^2.0.7", - "@csstools/postcss-logical-float-and-clear": "^3.0.0", - "@csstools/postcss-logical-overflow": "^2.0.0", - "@csstools/postcss-logical-overscroll-behavior": "^2.0.0", - "@csstools/postcss-logical-resize": "^3.0.0", - "@csstools/postcss-logical-viewport-units": "^3.0.3", - "@csstools/postcss-media-minmax": "^2.0.6", - "@csstools/postcss-media-queries-aspect-ratio-number-values": "^3.0.4", - "@csstools/postcss-nested-calc": "^4.0.0", - "@csstools/postcss-normalize-display-values": "^4.0.0", - "@csstools/postcss-oklab-function": "^4.0.7", - "@csstools/postcss-progressive-custom-properties": "^4.0.0", - "@csstools/postcss-random-function": "^1.0.2", - "@csstools/postcss-relative-color-syntax": "^3.0.7", - "@csstools/postcss-scope-pseudo-class": "^4.0.1", - "@csstools/postcss-sign-functions": "^1.1.1", - "@csstools/postcss-stepped-value-functions": "^4.0.6", - "@csstools/postcss-text-decoration-shorthand": "^4.0.1", - "@csstools/postcss-trigonometric-functions": "^4.0.6", - "@csstools/postcss-unset-value": "^4.0.0", - "autoprefixer": "^10.4.19", - "browserslist": "^4.23.1", - "css-blank-pseudo": "^7.0.1", - "css-has-pseudo": "^7.0.2", - "css-prefers-color-scheme": "^10.0.0", - "cssdb": "^8.2.3", - "postcss-attribute-case-insensitive": "^7.0.1", - "postcss-clamp": "^4.1.0", - "postcss-color-functional-notation": "^7.0.7", - "postcss-color-hex-alpha": "^10.0.0", - "postcss-color-rebeccapurple": "^10.0.0", - "postcss-custom-media": "^11.0.5", - "postcss-custom-properties": "^14.0.4", - "postcss-custom-selectors": "^8.0.4", - "postcss-dir-pseudo-class": "^9.0.1", - "postcss-double-position-gradients": "^6.0.0", - "postcss-focus-visible": "^10.0.1", - "postcss-focus-within": "^9.0.1", - "postcss-font-variant": "^5.0.0", - "postcss-gap-properties": "^6.0.0", - "postcss-image-set-function": "^7.0.0", - "postcss-lab-function": "^7.0.7", - "postcss-logical": "^8.0.0", - "postcss-nesting": "^13.0.1", - "postcss-opacity-percentage": "^3.0.0", - "postcss-overflow-shorthand": "^6.0.0", - "postcss-page-break": "^3.0.4", - "postcss-place": "^10.0.0", - "postcss-pseudo-class-any-link": "^10.0.1", - "postcss-replace-overflow-wrap": "^4.0.0", - "postcss-selector-not": "^8.0.1" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/postcss-pseudo-class-any-link": { - "version": "10.0.1", - "resolved": "https://registry.npmjs.org/postcss-pseudo-class-any-link/-/postcss-pseudo-class-any-link-10.0.1.tgz", - "integrity": "sha512-3el9rXlBOqTFaMFkWDOkHUTQekFIYnaQY55Rsp8As8QQkpiSgIYEcF/6Ond93oHiDsGb4kad8zjt+NPlOC1H0Q==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT-0", - "dependencies": { - "postcss-selector-parser": "^7.0.0" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/postcss-pseudo-class-any-link/node_modules/postcss-selector-parser": { - "version": "7.0.0", - "resolved": "https://registry.npmjs.org/postcss-selector-parser/-/postcss-selector-parser-7.0.0.tgz", - "integrity": "sha512-9RbEr1Y7FFfptd/1eEdntyjMwLeghW1bHX9GWjXo19vx4ytPQhANltvVxDggzJl7mnWM+dX28kb6cyS/4iQjlQ==", - "license": "MIT", - "dependencies": { - "cssesc": "^3.0.0", - "util-deprecate": "^1.0.2" - }, - "engines": { - "node": ">=4" - } - }, - "node_modules/postcss-reduce-idents": { - "version": "6.0.3", - "resolved": "https://registry.npmjs.org/postcss-reduce-idents/-/postcss-reduce-idents-6.0.3.tgz", - "integrity": "sha512-G3yCqZDpsNPoQgbDUy3T0E6hqOQ5xigUtBQyrmq3tn2GxlyiL0yyl7H+T8ulQR6kOcHJ9t7/9H4/R2tv8tJbMA==", - "license": "MIT", - "dependencies": { - "postcss-value-parser": "^4.2.0" - }, - "engines": { - "node": "^14 || ^16 || >=18.0" - }, - "peerDependencies": { - "postcss": "^8.4.31" - } - }, - "node_modules/postcss-reduce-initial": { - "version": "6.1.0", - "resolved": "https://registry.npmjs.org/postcss-reduce-initial/-/postcss-reduce-initial-6.1.0.tgz", - "integrity": "sha512-RarLgBK/CrL1qZags04oKbVbrrVK2wcxhvta3GCxrZO4zveibqbRPmm2VI8sSgCXwoUHEliRSbOfpR0b/VIoiw==", - "license": "MIT", - "dependencies": { - "browserslist": "^4.23.0", - "caniuse-api": "^3.0.0" - }, - "engines": { - "node": "^14 || ^16 || >=18.0" - }, - "peerDependencies": { - "postcss": "^8.4.31" - } - }, - "node_modules/postcss-reduce-transforms": { - "version": "6.0.2", - "resolved": "https://registry.npmjs.org/postcss-reduce-transforms/-/postcss-reduce-transforms-6.0.2.tgz", - "integrity": "sha512-sB+Ya++3Xj1WaT9+5LOOdirAxP7dJZms3GRcYheSPi1PiTMigsxHAdkrbItHxwYHr4kt1zL7mmcHstgMYT+aiA==", - "license": "MIT", - "dependencies": { - "postcss-value-parser": "^4.2.0" - }, - "engines": { - "node": "^14 || ^16 || >=18.0" - }, - "peerDependencies": { - "postcss": "^8.4.31" - } - }, - "node_modules/postcss-replace-overflow-wrap": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/postcss-replace-overflow-wrap/-/postcss-replace-overflow-wrap-4.0.0.tgz", - "integrity": "sha512-KmF7SBPphT4gPPcKZc7aDkweHiKEEO8cla/GjcBK+ckKxiZslIu3C4GCRW3DNfL0o7yW7kMQu9xlZ1kXRXLXtw==", - "license": "MIT", - "peerDependencies": { - "postcss": "^8.0.3" - } - }, - "node_modules/postcss-selector-not": { - "version": "8.0.1", - "resolved": "https://registry.npmjs.org/postcss-selector-not/-/postcss-selector-not-8.0.1.tgz", - "integrity": "sha512-kmVy/5PYVb2UOhy0+LqUYAhKj7DUGDpSWa5LZqlkWJaaAV+dxxsOG3+St0yNLu6vsKD7Dmqx+nWQt0iil89+WA==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/csstools" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/csstools" - } - ], - "license": "MIT", - "dependencies": { - "postcss-selector-parser": "^7.0.0" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "postcss": "^8.4" - } - }, - "node_modules/postcss-selector-not/node_modules/postcss-selector-parser": { - "version": "7.0.0", - "resolved": "https://registry.npmjs.org/postcss-selector-parser/-/postcss-selector-parser-7.0.0.tgz", - "integrity": "sha512-9RbEr1Y7FFfptd/1eEdntyjMwLeghW1bHX9GWjXo19vx4ytPQhANltvVxDggzJl7mnWM+dX28kb6cyS/4iQjlQ==", - "license": "MIT", - "dependencies": { - "cssesc": "^3.0.0", - "util-deprecate": "^1.0.2" - }, - "engines": { - "node": ">=4" - } - }, - "node_modules/postcss-selector-parser": { - "version": "6.1.2", - "resolved": "https://registry.npmjs.org/postcss-selector-parser/-/postcss-selector-parser-6.1.2.tgz", - "integrity": "sha512-Q8qQfPiZ+THO/3ZrOrO0cJJKfpYCagtMUkXbnEfmgUjwXg6z/WBeOyS9APBBPCTSiDV+s4SwQGu8yFsiMRIudg==", - "license": "MIT", - "dependencies": { - "cssesc": "^3.0.0", - "util-deprecate": "^1.0.2" - }, - "engines": { - "node": ">=4" - } - }, - "node_modules/postcss-sort-media-queries": { - "version": "5.2.0", - "resolved": "https://registry.npmjs.org/postcss-sort-media-queries/-/postcss-sort-media-queries-5.2.0.tgz", - "integrity": "sha512-AZ5fDMLD8SldlAYlvi8NIqo0+Z8xnXU2ia0jxmuhxAU+Lqt9K+AlmLNJ/zWEnE9x+Zx3qL3+1K20ATgNOr3fAA==", - "license": "MIT", - "dependencies": { - "sort-css-media-queries": "2.2.0" - }, - "engines": { - "node": ">=14.0.0" - }, - "peerDependencies": { - "postcss": "^8.4.23" - } - }, - "node_modules/postcss-svgo": { - "version": "6.0.3", - "resolved": "https://registry.npmjs.org/postcss-svgo/-/postcss-svgo-6.0.3.tgz", - "integrity": "sha512-dlrahRmxP22bX6iKEjOM+c8/1p+81asjKT+V5lrgOH944ryx/OHpclnIbGsKVd3uWOXFLYJwCVf0eEkJGvO96g==", - "license": "MIT", - "dependencies": { - "postcss-value-parser": "^4.2.0", - "svgo": "^3.2.0" - }, - "engines": { - "node": "^14 || ^16 || >= 18" - }, - "peerDependencies": { - "postcss": "^8.4.31" - } - }, - "node_modules/postcss-unique-selectors": { - "version": "6.0.4", - "resolved": "https://registry.npmjs.org/postcss-unique-selectors/-/postcss-unique-selectors-6.0.4.tgz", - "integrity": "sha512-K38OCaIrO8+PzpArzkLKB42dSARtC2tmG6PvD4b1o1Q2E9Os8jzfWFfSy/rixsHwohtsDdFtAWGjFVFUdwYaMg==", - "license": "MIT", - "dependencies": { - "postcss-selector-parser": "^6.0.16" - }, - "engines": { - "node": "^14 || ^16 || >=18.0" - }, - "peerDependencies": { - "postcss": "^8.4.31" - } - }, - "node_modules/postcss-value-parser": { - "version": "4.2.0", - "resolved": "https://registry.npmjs.org/postcss-value-parser/-/postcss-value-parser-4.2.0.tgz", - "integrity": "sha512-1NNCs6uurfkVbeXG4S8JFT9t19m45ICnif8zWLd5oPSZ50QnwMfK+H3jv408d4jw/7Bttv5axS5IiHoLaVNHeQ==", - "license": "MIT" - }, - "node_modules/postcss-zindex": { - "version": "6.0.2", - "resolved": "https://registry.npmjs.org/postcss-zindex/-/postcss-zindex-6.0.2.tgz", - "integrity": "sha512-5BxW9l1evPB/4ZIc+2GobEBoKC+h8gPGCMi+jxsYvd2x0mjq7wazk6DrP71pStqxE9Foxh5TVnonbWpFZzXaYg==", - "license": "MIT", - "engines": { - "node": "^14 || ^16 || >=18.0" - }, - "peerDependencies": { - "postcss": "^8.4.31" - } - }, - "node_modules/postman-code-generators": { - "version": "1.13.0", - "resolved": "https://registry.npmjs.org/postman-code-generators/-/postman-code-generators-1.13.0.tgz", - "integrity": "sha512-rbKtX+PWp+4McQpAncnRCUKqDiynt4fDB1I7AzrsvBAQc74ab6k6K3IP8qvf0icqiPuf9nYHCSdy/LB922dQLQ==", - "hasInstallScript": true, - "license": "Apache-2.0", - "dependencies": { - "async": "3.2.2", - "detect-package-manager": "3.0.2", - "lodash": "4.17.21", - "path": "0.12.7", - "postman-collection": "^4.4.0", - "shelljs": "0.8.5" - }, - "engines": { - "node": ">=12" - } - }, - "node_modules/postman-code-generators/node_modules/async": { - "version": "3.2.2", - "resolved": "https://registry.npmjs.org/async/-/async-3.2.2.tgz", - "integrity": "sha512-H0E+qZaDEfx/FY4t7iLRv1W2fFI6+pyCeTw1uN20AQPiwqwM6ojPxHxdLv4z8hi2DtnW9BOckSspLucW7pIE5g==", - "license": "MIT" - }, - "node_modules/postman-collection": { - "version": "4.5.0", - "resolved": "https://registry.npmjs.org/postman-collection/-/postman-collection-4.5.0.tgz", - "integrity": "sha512-152JSW9pdbaoJihwjc7Q8lc3nPg/PC9lPTHdMk7SHnHhu/GBJB7b2yb9zG7Qua578+3PxkQ/HYBuXpDSvsf7GQ==", - "license": "Apache-2.0", - "dependencies": { - "@faker-js/faker": "5.5.3", - "file-type": "3.9.0", - "http-reasons": "0.1.0", - "iconv-lite": "0.6.3", - "liquid-json": "0.3.1", - "lodash": "4.17.21", - "mime-format": "2.0.1", - "mime-types": "2.1.35", - "postman-url-encoder": "3.0.5", - "semver": "7.6.3", - "uuid": "8.3.2" - }, - "engines": { - "node": ">=10" - } - }, - "node_modules/postman-collection/node_modules/iconv-lite": { - "version": "0.6.3", - "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.6.3.tgz", - "integrity": "sha512-4fCk79wshMdzMp2rH06qWrJE4iolqLhCUH+OiuIgU++RB0+94NlDL81atO7GX55uUKueo0txHNtvEyI6D7WdMw==", - "license": "MIT", - "dependencies": { - "safer-buffer": ">= 2.1.2 < 3.0.0" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/postman-collection/node_modules/mime-db": { - "version": "1.52.0", - "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.52.0.tgz", - "integrity": "sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg==", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/postman-collection/node_modules/mime-types": { - "version": "2.1.35", - "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.35.tgz", - "integrity": "sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw==", - "license": "MIT", - "dependencies": { - "mime-db": "1.52.0" - }, - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/postman-url-encoder": { - "version": "3.0.5", - "resolved": "https://registry.npmjs.org/postman-url-encoder/-/postman-url-encoder-3.0.5.tgz", - "integrity": "sha512-jOrdVvzUXBC7C+9gkIkpDJ3HIxOHTIqjpQ4C1EMt1ZGeMvSEpbFCKq23DEfgsj46vMnDgyQf+1ZLp2Wm+bKSsA==", - "license": "Apache-2.0", - "dependencies": { - "punycode": "^2.1.1" - }, - "engines": { - "node": ">=10" - } - }, - "node_modules/postman-url-encoder/node_modules/punycode": { - "version": "2.3.1", - "resolved": "https://registry.npmjs.org/punycode/-/punycode-2.3.1.tgz", - "integrity": "sha512-vYt7UD1U9Wg6138shLtLOvdAu+8DsC/ilFtEVHcH+wydcSpNE20AfSOduf6MkRFahL5FY7X1oU7nKVZFtfq8Fg==", - "license": "MIT", - "engines": { - "node": ">=6" - } - }, - "node_modules/pretty-error": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/pretty-error/-/pretty-error-4.0.0.tgz", - "integrity": "sha512-AoJ5YMAcXKYxKhuJGdcvse+Voc6v1RgnsR3nWcYU7q4t6z0Q6T86sv5Zq8VIRbOWWFpvdGE83LtdSMNd+6Y0xw==", - "license": "MIT", - "dependencies": { - "lodash": "^4.17.20", - "renderkid": "^3.0.0" - } - }, - "node_modules/pretty-time": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/pretty-time/-/pretty-time-1.1.0.tgz", - "integrity": "sha512-28iF6xPQrP8Oa6uxE6a1biz+lWeTOAPKggvjB8HAs6nVMKZwf5bG++632Dx614hIWgUPkgivRfG+a8uAXGTIbA==", - "license": "MIT", - "engines": { - "node": ">=4" - } - }, - "node_modules/prism-react-renderer": { - "version": "2.3.1", - "resolved": "https://registry.npmjs.org/prism-react-renderer/-/prism-react-renderer-2.3.1.tgz", - "integrity": "sha512-Rdf+HzBLR7KYjzpJ1rSoxT9ioO85nZngQEoFIhL07XhtJHlCU3SOz0GJ6+qvMyQe0Se+BV3qpe6Yd/NmQF5Juw==", - "license": "MIT", - "dependencies": { - "@types/prismjs": "^1.26.0", - "clsx": "^2.0.0" - }, - "peerDependencies": { - "react": ">=16.0.0" - } - }, - "node_modules/prismjs": { - "version": "1.29.0", - "resolved": "https://registry.npmjs.org/prismjs/-/prismjs-1.29.0.tgz", - "integrity": "sha512-Kx/1w86q/epKcmte75LNrEoT+lX8pBpavuAbvJWRXar7Hz8jrtF+e3vY751p0R8H9HdArwaCTNDDzHg/ScJK1Q==", - "license": "MIT", - "engines": { - "node": ">=6" - } - }, - "node_modules/process": { - "version": "0.11.10", - "resolved": "https://registry.npmjs.org/process/-/process-0.11.10.tgz", - "integrity": "sha512-cdGef/drWFoydD1JsMzuFf8100nZl+GT+yacc2bEced5f9Rjk4z+WtFUTBu9PhOi9j/jfmBPu0mMEY4wIdAF8A==", - "license": "MIT", - "engines": { - "node": ">= 0.6.0" - } - }, - "node_modules/process-nextick-args": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/process-nextick-args/-/process-nextick-args-2.0.1.tgz", - "integrity": "sha512-3ouUOpQhtgrbOa17J7+uxOTpITYWaGP7/AhoR3+A+/1e9skrzelGi/dXzEYyvbxubEF6Wn2ypscTKiKJFFn1ag==", - "license": "MIT" - }, - "node_modules/prompts": { - "version": "2.4.2", - "resolved": "https://registry.npmjs.org/prompts/-/prompts-2.4.2.tgz", - "integrity": "sha512-NxNv/kLguCA7p3jE8oL2aEBsrJWgAakBpgmgK6lpPWV+WuOmY6r2/zbAVnP+T8bQlA0nzHXSJSJW0Hq7ylaD2Q==", - "license": "MIT", - "dependencies": { - "kleur": "^3.0.3", - "sisteransi": "^1.0.5" - }, - "engines": { - "node": ">= 6" - } - }, - "node_modules/prop-types": { - "version": "15.8.1", - "resolved": "https://registry.npmjs.org/prop-types/-/prop-types-15.8.1.tgz", - "integrity": "sha512-oj87CgZICdulUohogVAR7AjlC0327U4el4L6eAvOqCeudMDVU0NThNaV+b9Df4dXgSP1gXMTnPdhfe/2qDH5cg==", - "license": "MIT", - "dependencies": { - "loose-envify": "^1.4.0", - "object-assign": "^4.1.1", - "react-is": "^16.13.1" - } - }, - "node_modules/property-information": { - "version": "6.5.0", - "resolved": "https://registry.npmjs.org/property-information/-/property-information-6.5.0.tgz", - "integrity": "sha512-PgTgs/BlvHxOu8QuEN7wi5A0OmXaBcHpmCSTehcs6Uuu9IkDIEo13Hy7n898RHfrQ49vKCoGeWZSaAK01nwVig==", - "license": "MIT", - "funding": { - "type": "github", - "url": "https://github.com/sponsors/wooorm" - } - }, - "node_modules/proto-list": { - "version": "1.2.4", - "resolved": "https://registry.npmjs.org/proto-list/-/proto-list-1.2.4.tgz", - "integrity": "sha512-vtK/94akxsTMhe0/cbfpR+syPuszcuwhqVjJq26CuNDgFGj682oRBXOP5MJpv2r7JtE8MsiepGIqvvOTBwn2vA==", - "license": "ISC" - }, - "node_modules/proxy-addr": { - "version": "2.0.7", - "resolved": "https://registry.npmjs.org/proxy-addr/-/proxy-addr-2.0.7.tgz", - "integrity": "sha512-llQsMLSUDUPT44jdrU/O37qlnifitDP+ZwrmmZcoSKyLKvtZxpyV0n2/bD/N4tBAAZ/gJEdZU7KMraoK1+XYAg==", - "license": "MIT", - "dependencies": { - "forwarded": "0.2.0", - "ipaddr.js": "1.9.1" - }, - "engines": { - "node": ">= 0.10" - } - }, - "node_modules/proxy-addr/node_modules/ipaddr.js": { - "version": "1.9.1", - "resolved": "https://registry.npmjs.org/ipaddr.js/-/ipaddr.js-1.9.1.tgz", - "integrity": "sha512-0KI/607xoxSToH7GjN1FfSbLoU0+btTicjsQSWQlh/hZykN8KpmMf7uYwPW3R+akZ6R/w18ZlXSHBYXiYUPO3g==", - "license": "MIT", - "engines": { - "node": ">= 0.10" - } - }, - "node_modules/pstree.remy": { - "version": "1.1.8", - "resolved": "https://registry.npmjs.org/pstree.remy/-/pstree.remy-1.1.8.tgz", - "integrity": "sha512-77DZwxQmxKnu3aR542U+X8FypNzbfJ+C5XQDk3uWjWxn6151aIMGthWYRXTqT1E5oJvg+ljaa2OJi+VfvCOQ8w==", - "dev": true, - "license": "MIT" - }, - "node_modules/public-encrypt": { - "version": "4.0.3", - "resolved": "https://registry.npmjs.org/public-encrypt/-/public-encrypt-4.0.3.tgz", - "integrity": "sha512-zVpa8oKZSz5bTMTFClc1fQOnyyEzpl5ozpi1B5YcvBrdohMjH2rfsBtyXcuNuwjsDIXmBYlF2N5FlJYhR29t8Q==", - "license": "MIT", - "dependencies": { - "bn.js": "^4.1.0", - "browserify-rsa": "^4.0.0", - "create-hash": "^1.1.0", - "parse-asn1": "^5.0.0", - "randombytes": "^2.0.1", - "safe-buffer": "^5.1.2" - } - }, - "node_modules/public-encrypt/node_modules/bn.js": { - "version": "4.12.0", - "resolved": "https://registry.npmjs.org/bn.js/-/bn.js-4.12.0.tgz", - "integrity": "sha512-c98Bf3tPniI+scsdk237ku1Dc3ujXQTSgyiPUDEOe7tRkhrqridvh8klBv0HCEso1OLOYcHuCv/cS6DNxKH+ZA==", - "license": "MIT" - }, - "node_modules/punycode": { - "version": "1.4.1", - "resolved": "https://registry.npmjs.org/punycode/-/punycode-1.4.1.tgz", - "integrity": "sha512-jmYNElW7yvO7TV33CjSmvSiE2yco3bV2czu/OzDKdMNVZQWfxCblURLhf+47syQRBntjfLdd/H0egrzIG+oaFQ==", - "license": "MIT" - }, - "node_modules/pupa": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/pupa/-/pupa-3.1.0.tgz", - "integrity": "sha512-FLpr4flz5xZTSJxSeaheeMKN/EDzMdK7b8PTOC6a5PYFKTucWbdqjgqaEyH0shFiSJrVB1+Qqi4Tk19ccU6Aug==", - "license": "MIT", - "dependencies": { - "escape-goat": "^4.0.0" - }, - "engines": { - "node": ">=12.20" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/qs": { - "version": "6.13.0", - "resolved": "https://registry.npmjs.org/qs/-/qs-6.13.0.tgz", - "integrity": "sha512-+38qI9SOr8tfZ4QmJNplMUxqjbe7LKvvZgWdExBOmd+egZTtjLB67Gu0HRX3u/XOq7UU2Nx6nsjvS16Z9uwfpg==", - "dependencies": { - "side-channel": "^1.0.6" - }, - "engines": { - "node": ">=0.6" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/querystring-es3": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/querystring-es3/-/querystring-es3-0.2.1.tgz", - "integrity": "sha512-773xhDQnZBMFobEiztv8LIl70ch5MSF/jUQVlhwFyBILqq96anmoctVIYz+ZRp0qbCKATTn6ev02M3r7Ga5vqA==", - "engines": { - "node": ">=0.4.x" - } - }, - "node_modules/queue": { - "version": "6.0.2", - "resolved": "https://registry.npmjs.org/queue/-/queue-6.0.2.tgz", - "integrity": "sha512-iHZWu+q3IdFZFX36ro/lKBkSvfkztY5Y7HMiPlOUjhupPcG2JMfst2KKEpu5XndviX/3UhFbRngUPNKtgvtZiA==", - "license": "MIT", - "dependencies": { - "inherits": "~2.0.3" - } - }, - "node_modules/queue-microtask": { - "version": "1.2.3", - "resolved": "https://registry.npmjs.org/queue-microtask/-/queue-microtask-1.2.3.tgz", - "integrity": "sha512-NuaNSa6flKT5JaSYQzJok04JzTL1CA6aGhv5rfLW3PgqA+M2ChpZQnAC8h8i4ZFkBS8X5RqkDBHA7r4hej3K9A==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/feross" - }, - { - "type": "patreon", - "url": "https://www.patreon.com/feross" - }, - { - "type": "consulting", - "url": "https://feross.org/support" - } - ], - "license": "MIT" - }, - "node_modules/quick-lru": { - "version": "5.1.1", - "resolved": "https://registry.npmjs.org/quick-lru/-/quick-lru-5.1.1.tgz", - "integrity": "sha512-WuyALRjWPDGtt/wzJiadO5AXY+8hZ80hVpe6MyivgraREW751X3SbhRvG3eLKOYN+8VEvqLcf3wdnt44Z4S4SA==", - "license": "MIT", - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/randombytes": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/randombytes/-/randombytes-2.1.0.tgz", - "integrity": "sha512-vYl3iOX+4CKUWuxGi9Ukhie6fsqXqS9FE2Zaic4tNFD2N2QQaXOMFbuKK4QmDHC0JO6B1Zp41J0LpT0oR68amQ==", - "license": "MIT", - "dependencies": { - "safe-buffer": "^5.1.0" - } - }, - "node_modules/randomfill": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/randomfill/-/randomfill-1.0.4.tgz", - "integrity": "sha512-87lcbR8+MhcWcUiQ+9e+Rwx8MyR2P7qnt15ynUlbm3TU/fjbgz4GsvfSUDTemtCCtVCqb4ZcEFlyPNTh9bBTLw==", - "license": "MIT", - "dependencies": { - "randombytes": "^2.0.5", - "safe-buffer": "^5.1.0" - } - }, - "node_modules/range-parser": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/range-parser/-/range-parser-1.2.0.tgz", - "integrity": "sha512-kA5WQoNVo4t9lNx2kQNFCxKeBl5IbbSNBl1M/tLkw9WCn+hxNBAW5Qh8gdhs63CJnhjJ2zQWFoqPJP2sK1AV5A==", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/raw-body": { - "version": "2.5.2", - "resolved": "https://registry.npmjs.org/raw-body/-/raw-body-2.5.2.tgz", - "integrity": "sha512-8zGqypfENjCIqGhgXToC8aB2r7YrBX+AQAfIPs/Mlk+BtPTztOvTS01NRW/3Eh60J+a48lt8qsCzirQ6loCVfA==", - "dependencies": { - "bytes": "3.1.2", - "http-errors": "2.0.0", - "iconv-lite": "0.4.24", - "unpipe": "1.0.0" - }, - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/raw-body/node_modules/bytes": { - "version": "3.1.2", - "resolved": "https://registry.npmjs.org/bytes/-/bytes-3.1.2.tgz", - "integrity": "sha512-/Nf7TyzTx6S3yRJObOAV7956r8cr2+Oj8AC5dt8wSP3BQAoeX58NoHyCU8P8zGkNXStjTSi6fzO6F0pBdcYbEg==", - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/rc": { - "version": "1.2.8", - "resolved": "https://registry.npmjs.org/rc/-/rc-1.2.8.tgz", - "integrity": "sha512-y3bGgqKj3QBdxLbLkomlohkvsA8gdAiUQlSBJnBhfn+BPxg4bc62d8TcBW15wavDfgexCgccckhcZvywyQYPOw==", - "license": "(BSD-2-Clause OR MIT OR Apache-2.0)", - "dependencies": { - "deep-extend": "^0.6.0", - "ini": "~1.3.0", - "minimist": "^1.2.0", - "strip-json-comments": "~2.0.1" - }, - "bin": { - "rc": "cli.js" - } - }, - "node_modules/rc/node_modules/strip-json-comments": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/strip-json-comments/-/strip-json-comments-2.0.1.tgz", - "integrity": "sha512-4gB8na07fecVVkOI6Rs4e7T6NOTki5EmL7TUduTs6bu3EdnSycntVJ4re8kgZA+wx9IueI2Y11bfbgwtzuE0KQ==", - "license": "MIT", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/react": { - "version": "18.3.1", - "resolved": "https://registry.npmjs.org/react/-/react-18.3.1.tgz", - "integrity": "sha512-wS+hAgJShR0KhEvPJArfuPVN1+Hz1t0Y6n5jLrGQbkb4urgPE/0Rve+1kMB1v/oWgHgm4WIcV+i7F2pTVj+2iQ==", - "license": "MIT", - "dependencies": { - "loose-envify": "^1.1.0" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/react-dev-utils": { - "version": "12.0.1", - "resolved": "https://registry.npmjs.org/react-dev-utils/-/react-dev-utils-12.0.1.tgz", - "integrity": "sha512-84Ivxmr17KjUupyqzFode6xKhjwuEJDROWKJy/BthkL7Wn6NJ8h4WE6k/exAv6ImS+0oZLRRW5j/aINMHyeGeQ==", - "license": "MIT", - "dependencies": { - "@babel/code-frame": "^7.16.0", - "address": "^1.1.2", - "browserslist": "^4.18.1", - "chalk": "^4.1.2", - "cross-spawn": "^7.0.3", - "detect-port-alt": "^1.1.6", - "escape-string-regexp": "^4.0.0", - "filesize": "^8.0.6", - "find-up": "^5.0.0", - "fork-ts-checker-webpack-plugin": "^6.5.0", - "global-modules": "^2.0.0", - "globby": "^11.0.4", - "gzip-size": "^6.0.0", - "immer": "^9.0.7", - "is-root": "^2.1.0", - "loader-utils": "^3.2.0", - "open": "^8.4.0", - "pkg-up": "^3.1.0", - "prompts": "^2.4.2", - "react-error-overlay": "^6.0.11", - "recursive-readdir": "^2.2.2", - "shell-quote": "^1.7.3", - "strip-ansi": "^6.0.1", - "text-table": "^0.2.0" - }, - "engines": { - "node": ">=14" - } - }, - "node_modules/react-dev-utils/node_modules/find-up": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/find-up/-/find-up-5.0.0.tgz", - "integrity": "sha512-78/PXT1wlLLDgTzDs7sjq9hzz0vXD+zn+7wypEe4fXQxCmdmqfGsEPQxmiCSQI3ajFV91bVSsvNtrJRiW6nGng==", - "license": "MIT", - "dependencies": { - "locate-path": "^6.0.0", - "path-exists": "^4.0.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/react-dev-utils/node_modules/loader-utils": { - "version": "3.3.1", - "resolved": "https://registry.npmjs.org/loader-utils/-/loader-utils-3.3.1.tgz", - "integrity": "sha512-FMJTLMXfCLMLfJxcX9PFqX5qD88Z5MRGaZCVzfuqeZSPsyiBzs+pahDQjbIWz2QIzPZz0NX9Zy4FX3lmK6YHIg==", - "license": "MIT", - "engines": { - "node": ">= 12.13.0" - } - }, - "node_modules/react-dev-utils/node_modules/locate-path": { - "version": "6.0.0", - "resolved": "https://registry.npmjs.org/locate-path/-/locate-path-6.0.0.tgz", - "integrity": "sha512-iPZK6eYjbxRu3uB4/WZ3EsEIMJFMqAoopl3R+zuq0UjcAm/MO6KCweDgPfP3elTztoKP3KtnVHxTn2NHBSDVUw==", - "license": "MIT", - "dependencies": { - "p-locate": "^5.0.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/react-dev-utils/node_modules/p-limit": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-3.1.0.tgz", - "integrity": "sha512-TYOanM3wGwNGsZN2cVTYPArw454xnXj5qmWF1bEoAc4+cU/ol7GVh7odevjp1FNHduHc3KZMcFduxU5Xc6uJRQ==", - "license": "MIT", - "dependencies": { - "yocto-queue": "^0.1.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/react-dev-utils/node_modules/p-locate": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/p-locate/-/p-locate-5.0.0.tgz", - "integrity": "sha512-LaNjtRWUBY++zB5nE/NwcaoMylSPk+S+ZHNB1TzdbMJMny6dynpAGt7X/tl/QYq3TIeE6nxHppbo2LGymrG5Pw==", - "license": "MIT", - "dependencies": { - "p-limit": "^3.0.2" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/react-dev-utils/node_modules/path-exists": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-4.0.0.tgz", - "integrity": "sha512-ak9Qy5Q7jYb2Wwcey5Fpvg2KoAc/ZIhLSLOSBmRmygPsGwkVVt0fZa0qrtMz+m6tJTAHfZQ8FnmB4MG4LWy7/w==", - "license": "MIT", - "engines": { - "node": ">=8" - } - }, - "node_modules/react-dev-utils/node_modules/yocto-queue": { - "version": "0.1.0", - "resolved": "https://registry.npmjs.org/yocto-queue/-/yocto-queue-0.1.0.tgz", - "integrity": "sha512-rVksvsnNCdJ/ohGc6xgPwyN8eheCxsiLM8mxuE/t/mOVqJewPuO1miLpTHQiRgTKCLexL4MeAFVagts7HmNZ2Q==", - "license": "MIT", - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/react-dom": { - "version": "18.3.1", - "resolved": "https://registry.npmjs.org/react-dom/-/react-dom-18.3.1.tgz", - "integrity": "sha512-5m4nQKp+rZRb09LNH59GM4BxTh9251/ylbKIbpe7TpGxfJ+9kv6BLkLBXIjjspbgbnIBNqlI23tRnTWT0snUIw==", - "license": "MIT", - "dependencies": { - "loose-envify": "^1.1.0", - "scheduler": "^0.23.2" - }, - "peerDependencies": { - "react": "^18.3.1" - } - }, - "node_modules/react-error-overlay": { - "version": "6.0.11", - "resolved": "https://registry.npmjs.org/react-error-overlay/-/react-error-overlay-6.0.11.tgz", - "integrity": "sha512-/6UZ2qgEyH2aqzYZgQPxEnz33NJ2gNsnHA2o5+o4wW9bLM/JYQitNP9xPhsXwC08hMMovfGe/8retsdDsczPRg==", - "license": "MIT" - }, - "node_modules/react-fast-compare": { - "version": "3.2.2", - "resolved": "https://registry.npmjs.org/react-fast-compare/-/react-fast-compare-3.2.2.tgz", - "integrity": "sha512-nsO+KSNgo1SbJqJEYRE9ERzo7YtYbou/OqjSQKxV7jcKox7+usiUVZOAC+XnDOABXggQTno0Y1CpVnuWEc1boQ==", - "license": "MIT" - }, - "node_modules/react-helmet-async": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/react-helmet-async/-/react-helmet-async-1.3.0.tgz", - "integrity": "sha512-9jZ57/dAn9t3q6hneQS0wukqC2ENOBgMNVEhb/ZG9ZSxUetzVIw4iAmEU38IaVg3QGYauQPhSeUTuIUtFglWpg==", - "license": "Apache-2.0", - "dependencies": { - "@babel/runtime": "^7.12.5", - "invariant": "^2.2.4", - "prop-types": "^15.7.2", - "react-fast-compare": "^3.2.0", - "shallowequal": "^1.1.0" - }, - "peerDependencies": { - "react": "^16.6.0 || ^17.0.0 || ^18.0.0", - "react-dom": "^16.6.0 || ^17.0.0 || ^18.0.0" - } - }, - "node_modules/react-hook-form": { - "version": "7.53.0", - "resolved": "https://registry.npmjs.org/react-hook-form/-/react-hook-form-7.53.0.tgz", - "integrity": "sha512-M1n3HhqCww6S2hxLxciEXy2oISPnAzxY7gvwVPrtlczTM/1dDadXgUxDpHMrMTblDOcm/AXtXxHwZ3jpg1mqKQ==", - "license": "MIT", - "engines": { - "node": ">=18.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/react-hook-form" - }, - "peerDependencies": { - "react": "^16.8.0 || ^17 || ^18 || ^19" - } - }, - "node_modules/react-is": { - "version": "16.13.1", - "resolved": "https://registry.npmjs.org/react-is/-/react-is-16.13.1.tgz", - "integrity": "sha512-24e6ynE2H+OKt4kqsOvNd8kBpV65zoxbA4BVsEOB3ARVWQki/DHzaUoC5KuON/BiccDaCCTZBuOcfZs70kR8bQ==", - "license": "MIT" - }, - "node_modules/react-json-view-lite": { - "version": "1.5.0", - "resolved": "https://registry.npmjs.org/react-json-view-lite/-/react-json-view-lite-1.5.0.tgz", - "integrity": "sha512-nWqA1E4jKPklL2jvHWs6s+7Na0qNgw9HCP6xehdQJeg6nPBTFZgGwyko9Q0oj+jQWKTTVRS30u0toM5wiuL3iw==", - "license": "MIT", - "engines": { - "node": ">=14" - }, - "peerDependencies": { - "react": "^16.13.1 || ^17.0.0 || ^18.0.0" - } - }, - "node_modules/react-lifecycles-compat": { - "version": "3.0.4", - "resolved": "https://registry.npmjs.org/react-lifecycles-compat/-/react-lifecycles-compat-3.0.4.tgz", - "integrity": "sha512-fBASbA6LnOU9dOU2eW7aQ8xmYBSXUIWr+UmF9b1efZBazGNO+rcXT/icdKnYm2pTwcRylVUYwW7H1PHfLekVzA==", - "license": "MIT" - }, - "node_modules/react-live": { - "version": "4.1.7", - "resolved": "https://registry.npmjs.org/react-live/-/react-live-4.1.7.tgz", - "integrity": "sha512-NTzl0POOAW3dkp7+QL30duOrIu2Vzf2LHdx4TaQ0BqOAtQcSTKEXujfm9jR2VoCHko0oi35PYp38yKQBXz4mrg==", - "license": "MIT", - "dependencies": { - "prism-react-renderer": "^2.0.6", - "sucrase": "^3.31.0", - "use-editable": "^2.3.3" - }, - "engines": { - "node": ">= 0.12.0", - "npm": ">= 2.0.0" - }, - "peerDependencies": { - "react": ">=18.0.0", - "react-dom": ">=18.0.0" - } - }, - "node_modules/react-loadable": { - "name": "@docusaurus/react-loadable", - "version": "6.0.0", - "resolved": "https://registry.npmjs.org/@docusaurus/react-loadable/-/react-loadable-6.0.0.tgz", - "integrity": "sha512-YMMxTUQV/QFSnbgrP3tjDzLHRg7vsbMn8e9HAa8o/1iXoiomo48b7sk/kkmWEuWNDPJVlKSJRB6Y2fHqdJk+SQ==", - "license": "MIT", - "dependencies": { - "@types/react": "*" - }, - "peerDependencies": { - "react": "*" - } - }, - "node_modules/react-loadable-ssr-addon-v5-slorber": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/react-loadable-ssr-addon-v5-slorber/-/react-loadable-ssr-addon-v5-slorber-1.0.1.tgz", - "integrity": "sha512-lq3Lyw1lGku8zUEJPDxsNm1AfYHBrO9Y1+olAYwpUJ2IGFBskM0DMKok97A6LWUpHm+o7IvQBOWu9MLenp9Z+A==", - "license": "MIT", - "dependencies": { - "@babel/runtime": "^7.10.3" - }, - "engines": { - "node": ">=10.13.0" - }, - "peerDependencies": { - "react-loadable": "*", - "webpack": ">=4.41.1 || 5.x" - } - }, - "node_modules/react-magic-dropzone": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/react-magic-dropzone/-/react-magic-dropzone-1.0.1.tgz", - "integrity": "sha512-0BIROPARmXHpk4AS3eWBOsewxoM5ndk2psYP/JmbCq8tz3uR2LIV1XiroZ9PKrmDRMctpW+TvsBCtWasuS8vFA==", - "license": "MIT" - }, - "node_modules/react-markdown": { - "version": "8.0.7", - "resolved": "https://registry.npmjs.org/react-markdown/-/react-markdown-8.0.7.tgz", - "integrity": "sha512-bvWbzG4MtOU62XqBx3Xx+zB2raaFFsq4mYiAzfjXJMEz2sixgeAfraA3tvzULF02ZdOMUOKTBFFaZJDDrq+BJQ==", - "license": "MIT", - "dependencies": { - "@types/hast": "^2.0.0", - "@types/prop-types": "^15.0.0", - "@types/unist": "^2.0.0", - "comma-separated-tokens": "^2.0.0", - "hast-util-whitespace": "^2.0.0", - "prop-types": "^15.0.0", - "property-information": "^6.0.0", - "react-is": "^18.0.0", - "remark-parse": "^10.0.0", - "remark-rehype": "^10.0.0", - "space-separated-tokens": "^2.0.0", - "style-to-object": "^0.4.0", - "unified": "^10.0.0", - "unist-util-visit": "^4.0.0", - "vfile": "^5.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - }, - "peerDependencies": { - "@types/react": ">=16", - "react": ">=16" - } - }, - "node_modules/react-markdown/node_modules/@types/hast": { - "version": "2.3.10", - "resolved": "https://registry.npmjs.org/@types/hast/-/hast-2.3.10.tgz", - "integrity": "sha512-McWspRw8xx8J9HurkVBfYj0xKoE25tOFlHGdx4MJ5xORQrMGZNqJhVQWaIbm6Oyla5kYOXtDiopzKRJzEOkwJw==", - "license": "MIT", - "dependencies": { - "@types/unist": "^2" - } - }, - "node_modules/react-markdown/node_modules/@types/mdast": { - "version": "3.0.15", - "resolved": "https://registry.npmjs.org/@types/mdast/-/mdast-3.0.15.tgz", - "integrity": "sha512-LnwD+mUEfxWMa1QpDraczIn6k0Ee3SMicuYSSzS6ZYl2gKS09EClnJYGd8Du6rfc5r/GZEk5o1mRb8TaTj03sQ==", - "license": "MIT", - "dependencies": { - "@types/unist": "^2" - } - }, - "node_modules/react-markdown/node_modules/@types/unist": { - "version": "2.0.11", - "resolved": "https://registry.npmjs.org/@types/unist/-/unist-2.0.11.tgz", - "integrity": "sha512-CmBKiL6NNo/OqgmMn95Fk9Whlp2mtvIv+KNpQKN2F4SjvrEesubTRWGYSg+BnWZOnlCaSTU1sMpsBOzgbYhnsA==", - "license": "MIT" - }, - "node_modules/react-markdown/node_modules/hast-util-whitespace": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/hast-util-whitespace/-/hast-util-whitespace-2.0.1.tgz", - "integrity": "sha512-nAxA0v8+vXSBDt3AnRUNjyRIQ0rD+ntpbAp4LnPkumc5M9yUbSMa4XDU9Q6etY4f1Wp4bNgvc1yjiZtsTTrSng==", - "license": "MIT", - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/react-markdown/node_modules/mdast-util-from-markdown": { - "version": "1.3.1", - "resolved": "https://registry.npmjs.org/mdast-util-from-markdown/-/mdast-util-from-markdown-1.3.1.tgz", - "integrity": "sha512-4xTO/M8c82qBcnQc1tgpNtubGUW/Y1tBQ1B0i5CtSoelOLKFYlElIr3bvgREYYO5iRqbMY1YuqZng0GVOI8Qww==", - "license": "MIT", - "dependencies": { - "@types/mdast": "^3.0.0", - "@types/unist": "^2.0.0", - "decode-named-character-reference": "^1.0.0", - "mdast-util-to-string": "^3.1.0", - "micromark": "^3.0.0", - "micromark-util-decode-numeric-character-reference": "^1.0.0", - "micromark-util-decode-string": "^1.0.0", - "micromark-util-normalize-identifier": "^1.0.0", - "micromark-util-symbol": "^1.0.0", - "micromark-util-types": "^1.0.0", - "unist-util-stringify-position": "^3.0.0", - "uvu": "^0.5.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/react-markdown/node_modules/mdast-util-to-hast": { - "version": "12.3.0", - "resolved": "https://registry.npmjs.org/mdast-util-to-hast/-/mdast-util-to-hast-12.3.0.tgz", - "integrity": "sha512-pits93r8PhnIoU4Vy9bjW39M2jJ6/tdHyja9rrot9uujkN7UTU9SDnE6WNJz/IGyQk3XHX6yNNtrBH6cQzm8Hw==", - "license": "MIT", - "dependencies": { - "@types/hast": "^2.0.0", - "@types/mdast": "^3.0.0", - "mdast-util-definitions": "^5.0.0", - "micromark-util-sanitize-uri": "^1.1.0", - "trim-lines": "^3.0.0", - "unist-util-generated": "^2.0.0", - "unist-util-position": "^4.0.0", - "unist-util-visit": "^4.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/react-markdown/node_modules/mdast-util-to-string": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/mdast-util-to-string/-/mdast-util-to-string-3.2.0.tgz", - "integrity": "sha512-V4Zn/ncyN1QNSqSBxTrMOLpjr+IKdHl2v3KVLoWmDPscP4r9GcCi71gjgvUV1SFSKh92AjAG4peFuBl2/YgCJg==", - "license": "MIT", - "dependencies": { - "@types/mdast": "^3.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/react-markdown/node_modules/micromark": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/micromark/-/micromark-3.2.0.tgz", - "integrity": "sha512-uD66tJj54JLYq0De10AhWycZWGQNUvDI55xPgk2sQM5kn1JYlhbCMTtEeT27+vAhW2FBQxLlOmS3pmA7/2z4aA==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "@types/debug": "^4.0.0", - "debug": "^4.0.0", - "decode-named-character-reference": "^1.0.0", - "micromark-core-commonmark": "^1.0.1", - "micromark-factory-space": "^1.0.0", - "micromark-util-character": "^1.0.0", - "micromark-util-chunked": "^1.0.0", - "micromark-util-combine-extensions": "^1.0.0", - "micromark-util-decode-numeric-character-reference": "^1.0.0", - "micromark-util-encode": "^1.0.0", - "micromark-util-normalize-identifier": "^1.0.0", - "micromark-util-resolve-all": "^1.0.0", - "micromark-util-sanitize-uri": "^1.0.0", - "micromark-util-subtokenize": "^1.0.0", - "micromark-util-symbol": "^1.0.0", - "micromark-util-types": "^1.0.1", - "uvu": "^0.5.0" - } - }, - "node_modules/react-markdown/node_modules/micromark-core-commonmark": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/micromark-core-commonmark/-/micromark-core-commonmark-1.1.0.tgz", - "integrity": "sha512-BgHO1aRbolh2hcrzL2d1La37V0Aoz73ymF8rAcKnohLy93titmv62E0gP8Hrx9PKcKrqCZ1BbLGbP3bEhoXYlw==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "decode-named-character-reference": "^1.0.0", - "micromark-factory-destination": "^1.0.0", - "micromark-factory-label": "^1.0.0", - "micromark-factory-space": "^1.0.0", - "micromark-factory-title": "^1.0.0", - "micromark-factory-whitespace": "^1.0.0", - "micromark-util-character": "^1.0.0", - "micromark-util-chunked": "^1.0.0", - "micromark-util-classify-character": "^1.0.0", - "micromark-util-html-tag-name": "^1.0.0", - "micromark-util-normalize-identifier": "^1.0.0", - "micromark-util-resolve-all": "^1.0.0", - "micromark-util-subtokenize": "^1.0.0", - "micromark-util-symbol": "^1.0.0", - "micromark-util-types": "^1.0.1", - "uvu": "^0.5.0" - } - }, - "node_modules/react-markdown/node_modules/micromark-factory-destination": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/micromark-factory-destination/-/micromark-factory-destination-1.1.0.tgz", - "integrity": "sha512-XaNDROBgx9SgSChd69pjiGKbV+nfHGDPVYFs5dOoDd7ZnMAE+Cuu91BCpsY8RT2NP9vo/B8pds2VQNCLiu0zhg==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-character": "^1.0.0", - "micromark-util-symbol": "^1.0.0", - "micromark-util-types": "^1.0.0" - } - }, - "node_modules/react-markdown/node_modules/micromark-factory-label": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/micromark-factory-label/-/micromark-factory-label-1.1.0.tgz", - "integrity": "sha512-OLtyez4vZo/1NjxGhcpDSbHQ+m0IIGnT8BoPamh+7jVlzLJBH98zzuCoUeMxvM6WsNeh8wx8cKvqLiPHEACn0w==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-character": "^1.0.0", - "micromark-util-symbol": "^1.0.0", - "micromark-util-types": "^1.0.0", - "uvu": "^0.5.0" - } - }, - "node_modules/react-markdown/node_modules/micromark-factory-title": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/micromark-factory-title/-/micromark-factory-title-1.1.0.tgz", - "integrity": "sha512-J7n9R3vMmgjDOCY8NPw55jiyaQnH5kBdV2/UXCtZIpnHH3P6nHUKaH7XXEYuWwx/xUJcawa8plLBEjMPU24HzQ==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-factory-space": "^1.0.0", - "micromark-util-character": "^1.0.0", - "micromark-util-symbol": "^1.0.0", - "micromark-util-types": "^1.0.0" - } - }, - "node_modules/react-markdown/node_modules/micromark-factory-whitespace": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/micromark-factory-whitespace/-/micromark-factory-whitespace-1.1.0.tgz", - "integrity": "sha512-v2WlmiymVSp5oMg+1Q0N1Lxmt6pMhIHD457whWM7/GUlEks1hI9xj5w3zbc4uuMKXGisksZk8DzP2UyGbGqNsQ==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-factory-space": "^1.0.0", - "micromark-util-character": "^1.0.0", - "micromark-util-symbol": "^1.0.0", - "micromark-util-types": "^1.0.0" - } - }, - "node_modules/react-markdown/node_modules/micromark-util-chunked": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/micromark-util-chunked/-/micromark-util-chunked-1.1.0.tgz", - "integrity": "sha512-Ye01HXpkZPNcV6FiyoW2fGZDUw4Yc7vT0E9Sad83+bEDiCJ1uXu0S3mr8WLpsz3HaG3x2q0HM6CTuPdcZcluFQ==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-symbol": "^1.0.0" - } - }, - "node_modules/react-markdown/node_modules/micromark-util-classify-character": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/micromark-util-classify-character/-/micromark-util-classify-character-1.1.0.tgz", - "integrity": "sha512-SL0wLxtKSnklKSUplok1WQFoGhUdWYKggKUiqhX+Swala+BtptGCu5iPRc+xvzJ4PXE/hwM3FNXsfEVgoZsWbw==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-character": "^1.0.0", - "micromark-util-symbol": "^1.0.0", - "micromark-util-types": "^1.0.0" - } - }, - "node_modules/react-markdown/node_modules/micromark-util-combine-extensions": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/micromark-util-combine-extensions/-/micromark-util-combine-extensions-1.1.0.tgz", - "integrity": "sha512-Q20sp4mfNf9yEqDL50WwuWZHUrCO4fEyeDCnMGmG5Pr0Cz15Uo7KBs6jq+dq0EgX4DPwwrh9m0X+zPV1ypFvUA==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-chunked": "^1.0.0", - "micromark-util-types": "^1.0.0" - } - }, - "node_modules/react-markdown/node_modules/micromark-util-decode-numeric-character-reference": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/micromark-util-decode-numeric-character-reference/-/micromark-util-decode-numeric-character-reference-1.1.0.tgz", - "integrity": "sha512-m9V0ExGv0jB1OT21mrWcuf4QhP46pH1KkfWy9ZEezqHKAxkj4mPCy3nIH1rkbdMlChLHX531eOrymlwyZIf2iw==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-symbol": "^1.0.0" - } - }, - "node_modules/react-markdown/node_modules/micromark-util-decode-string": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/micromark-util-decode-string/-/micromark-util-decode-string-1.1.0.tgz", - "integrity": "sha512-YphLGCK8gM1tG1bd54azwyrQRjCFcmgj2S2GoJDNnh4vYtnL38JS8M4gpxzOPNyHdNEpheyWXCTnnTDY3N+NVQ==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "decode-named-character-reference": "^1.0.0", - "micromark-util-character": "^1.0.0", - "micromark-util-decode-numeric-character-reference": "^1.0.0", - "micromark-util-symbol": "^1.0.0" - } - }, - "node_modules/react-markdown/node_modules/micromark-util-encode": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/micromark-util-encode/-/micromark-util-encode-1.1.0.tgz", - "integrity": "sha512-EuEzTWSTAj9PA5GOAs992GzNh2dGQO52UvAbtSOMvXTxv3Criqb6IOzJUBCmEqrrXSblJIJBbFFv6zPxpreiJw==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT" - }, - "node_modules/react-markdown/node_modules/micromark-util-html-tag-name": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/micromark-util-html-tag-name/-/micromark-util-html-tag-name-1.2.0.tgz", - "integrity": "sha512-VTQzcuQgFUD7yYztuQFKXT49KghjtETQ+Wv/zUjGSGBioZnkA4P1XXZPT1FHeJA6RwRXSF47yvJ1tsJdoxwO+Q==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT" - }, - "node_modules/react-markdown/node_modules/micromark-util-normalize-identifier": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/micromark-util-normalize-identifier/-/micromark-util-normalize-identifier-1.1.0.tgz", - "integrity": "sha512-N+w5vhqrBihhjdpM8+5Xsxy71QWqGn7HYNUvch71iV2PM7+E3uWGox1Qp90loa1ephtCxG2ftRV/Conitc6P2Q==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-symbol": "^1.0.0" - } - }, - "node_modules/react-markdown/node_modules/micromark-util-resolve-all": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/micromark-util-resolve-all/-/micromark-util-resolve-all-1.1.0.tgz", - "integrity": "sha512-b/G6BTMSg+bX+xVCshPTPyAu2tmA0E4X98NSR7eIbeC6ycCqCeE7wjfDIgzEbkzdEVJXRtOG4FbEm/uGbCRouA==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-types": "^1.0.0" - } - }, - "node_modules/react-markdown/node_modules/micromark-util-sanitize-uri": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/micromark-util-sanitize-uri/-/micromark-util-sanitize-uri-1.2.0.tgz", - "integrity": "sha512-QO4GXv0XZfWey4pYFndLUKEAktKkG5kZTdUNaTAkzbuJxn2tNBOr+QtxR2XpWaMhbImT2dPzyLrPXLlPhph34A==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-character": "^1.0.0", - "micromark-util-encode": "^1.0.0", - "micromark-util-symbol": "^1.0.0" - } - }, - "node_modules/react-markdown/node_modules/micromark-util-subtokenize": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/micromark-util-subtokenize/-/micromark-util-subtokenize-1.1.0.tgz", - "integrity": "sha512-kUQHyzRoxvZO2PuLzMt2P/dwVsTiivCK8icYTeR+3WgbuPqfHgPPy7nFKbeqRivBvn/3N3GBiNC+JRTMSxEC7A==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT", - "dependencies": { - "micromark-util-chunked": "^1.0.0", - "micromark-util-symbol": "^1.0.0", - "micromark-util-types": "^1.0.0", - "uvu": "^0.5.0" - } - }, - "node_modules/react-markdown/node_modules/micromark-util-types": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/micromark-util-types/-/micromark-util-types-1.1.0.tgz", - "integrity": "sha512-ukRBgie8TIAcacscVHSiddHjO4k/q3pnedmzMQ4iwDcK0FtFCohKOlFbaOL/mPgfnPsL3C1ZyxJa4sbWrBl3jg==", - "funding": [ - { - "type": "GitHub Sponsors", - "url": "https://github.com/sponsors/unifiedjs" - }, - { - "type": "OpenCollective", - "url": "https://opencollective.com/unified" - } - ], - "license": "MIT" - }, - "node_modules/react-markdown/node_modules/react-is": { - "version": "18.3.1", - "resolved": "https://registry.npmjs.org/react-is/-/react-is-18.3.1.tgz", - "integrity": "sha512-/LLMVyas0ljjAtoYiPqYiL8VWXzUUdThrmU5+n20DZv+a+ClRoevUzw5JxU+Ieh5/c87ytoTBV9G1FiKfNJdmg==", - "license": "MIT" - }, - "node_modules/react-markdown/node_modules/remark-parse": { - "version": "10.0.2", - "resolved": "https://registry.npmjs.org/remark-parse/-/remark-parse-10.0.2.tgz", - "integrity": "sha512-3ydxgHa/ZQzG8LvC7jTXccARYDcRld3VfcgIIFs7bI6vbRSxJJmzgLEIIoYKyrfhaY+ujuWaf/PJiMZXoiCXgw==", - "license": "MIT", - "dependencies": { - "@types/mdast": "^3.0.0", - "mdast-util-from-markdown": "^1.0.0", - "unified": "^10.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/react-markdown/node_modules/remark-rehype": { - "version": "10.1.0", - "resolved": "https://registry.npmjs.org/remark-rehype/-/remark-rehype-10.1.0.tgz", - "integrity": "sha512-EFmR5zppdBp0WQeDVZ/b66CWJipB2q2VLNFMabzDSGR66Z2fQii83G5gTBbgGEnEEA0QRussvrFHxk1HWGJskw==", - "license": "MIT", - "dependencies": { - "@types/hast": "^2.0.0", - "@types/mdast": "^3.0.0", - "mdast-util-to-hast": "^12.1.0", - "unified": "^10.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/react-markdown/node_modules/unified": { - "version": "10.1.2", - "resolved": "https://registry.npmjs.org/unified/-/unified-10.1.2.tgz", - "integrity": "sha512-pUSWAi/RAnVy1Pif2kAoeWNBa3JVrx0MId2LASj8G+7AiHWoKZNTomq6LG326T68U7/e263X6fTdcXIy7XnF7Q==", - "license": "MIT", - "dependencies": { - "@types/unist": "^2.0.0", - "bail": "^2.0.0", - "extend": "^3.0.0", - "is-buffer": "^2.0.0", - "is-plain-obj": "^4.0.0", - "trough": "^2.0.0", - "vfile": "^5.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/react-markdown/node_modules/unist-util-is": { - "version": "5.2.1", - "resolved": "https://registry.npmjs.org/unist-util-is/-/unist-util-is-5.2.1.tgz", - "integrity": "sha512-u9njyyfEh43npf1M+yGKDGVPbY/JWEemg5nH05ncKPfi+kBbKBJoTdsogMu33uhytuLlv9y0O7GH7fEdwLdLQw==", - "license": "MIT", - "dependencies": { - "@types/unist": "^2.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/react-markdown/node_modules/unist-util-position": { - "version": "4.0.4", - "resolved": "https://registry.npmjs.org/unist-util-position/-/unist-util-position-4.0.4.tgz", - "integrity": "sha512-kUBE91efOWfIVBo8xzh/uZQ7p9ffYRtUbMRZBNFYwf0RK8koUMx6dGUfwylLOKmaT2cs4wSW96QoYUSXAyEtpg==", - "license": "MIT", - "dependencies": { - "@types/unist": "^2.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/react-markdown/node_modules/unist-util-stringify-position": { - "version": "3.0.3", - "resolved": "https://registry.npmjs.org/unist-util-stringify-position/-/unist-util-stringify-position-3.0.3.tgz", - "integrity": "sha512-k5GzIBZ/QatR8N5X2y+drfpWG8IDBzdnVj6OInRNWm1oXrzydiaAT2OQiA8DPRRZyAKb9b6I2a6PxYklZD0gKg==", - "license": "MIT", - "dependencies": { - "@types/unist": "^2.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/react-markdown/node_modules/unist-util-visit": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/unist-util-visit/-/unist-util-visit-4.1.2.tgz", - "integrity": "sha512-MSd8OUGISqHdVvfY9TPhyK2VdUrPgxkUtWSuMHF6XAAFuL4LokseigBnZtPnJMu+FbynTkFNnFlyjxpVKujMRg==", - "license": "MIT", - "dependencies": { - "@types/unist": "^2.0.0", - "unist-util-is": "^5.0.0", - "unist-util-visit-parents": "^5.1.1" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/react-markdown/node_modules/unist-util-visit-parents": { - "version": "5.1.3", - "resolved": "https://registry.npmjs.org/unist-util-visit-parents/-/unist-util-visit-parents-5.1.3.tgz", - "integrity": "sha512-x6+y8g7wWMyQhL1iZfhIPhDAs7Xwbn9nRosDXl7qoPTSCy0yNxnKc+hWokFifWQIDGi154rdUqKvbCa4+1kLhg==", - "license": "MIT", - "dependencies": { - "@types/unist": "^2.0.0", - "unist-util-is": "^5.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/react-markdown/node_modules/vfile": { - "version": "5.3.7", - "resolved": "https://registry.npmjs.org/vfile/-/vfile-5.3.7.tgz", - "integrity": "sha512-r7qlzkgErKjobAmyNIkkSpizsFPYiUPuJb5pNW1RB4JcYVZhs4lIbVqk8XPk033CV/1z8ss5pkax8SuhGpcG8g==", - "license": "MIT", - "dependencies": { - "@types/unist": "^2.0.0", - "is-buffer": "^2.0.0", - "unist-util-stringify-position": "^3.0.0", - "vfile-message": "^3.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/react-markdown/node_modules/vfile-message": { - "version": "3.1.4", - "resolved": "https://registry.npmjs.org/vfile-message/-/vfile-message-3.1.4.tgz", - "integrity": "sha512-fa0Z6P8HUrQN4BZaX05SIVXic+7kE3b05PWAtPuYP9QLHsLKYR7/AlLW3NtOrpXRLeawpDLMsVkmk5DG0NXgWw==", - "license": "MIT", - "dependencies": { - "@types/unist": "^2.0.0", - "unist-util-stringify-position": "^3.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/react-modal": { - "version": "3.16.1", - "resolved": "https://registry.npmjs.org/react-modal/-/react-modal-3.16.1.tgz", - "integrity": "sha512-VStHgI3BVcGo7OXczvnJN7yT2TWHJPDXZWyI/a0ssFNhGZWsPmB8cF0z33ewDXq4VfYMO1vXgiv/g8Nj9NDyWg==", - "license": "MIT", - "dependencies": { - "exenv": "^1.2.0", - "prop-types": "^15.7.2", - "react-lifecycles-compat": "^3.0.0", - "warning": "^4.0.3" - }, - "engines": { - "node": ">=8" - }, - "peerDependencies": { - "react": "^0.14.0 || ^15.0.0 || ^16 || ^17 || ^18", - "react-dom": "^0.14.0 || ^15.0.0 || ^16 || ^17 || ^18" - } - }, - "node_modules/react-redux": { - "version": "7.2.9", - "resolved": "https://registry.npmjs.org/react-redux/-/react-redux-7.2.9.tgz", - "integrity": "sha512-Gx4L3uM182jEEayZfRbI/G11ZpYdNAnBs70lFVMNdHJI76XYtR+7m0MN+eAs7UHBPhWXcnFPaS+9owSCJQHNpQ==", - "license": "MIT", - "dependencies": { - "@babel/runtime": "^7.15.4", - "@types/react-redux": "^7.1.20", - "hoist-non-react-statics": "^3.3.2", - "loose-envify": "^1.4.0", - "prop-types": "^15.7.2", - "react-is": "^17.0.2" - }, - "peerDependencies": { - "react": "^16.8.3 || ^17 || ^18" - }, - "peerDependenciesMeta": { - "react-dom": { - "optional": true - }, - "react-native": { - "optional": true - } - } - }, - "node_modules/react-redux/node_modules/react-is": { - "version": "17.0.2", - "resolved": "https://registry.npmjs.org/react-is/-/react-is-17.0.2.tgz", - "integrity": "sha512-w2GsyukL62IJnlaff/nRegPQR94C/XXamvMWmSHRJ4y7Ts/4ocGRmTHvOs8PSE6pB3dWOrD/nueuU5sduBsQ4w==", - "license": "MIT" - }, - "node_modules/react-router": { - "version": "5.3.4", - "resolved": "https://registry.npmjs.org/react-router/-/react-router-5.3.4.tgz", - "integrity": "sha512-Ys9K+ppnJah3QuaRiLxk+jDWOR1MekYQrlytiXxC1RyfbdsZkS5pvKAzCCr031xHixZwpnsYNT5xysdFHQaYsA==", - "license": "MIT", - "dependencies": { - "@babel/runtime": "^7.12.13", - "history": "^4.9.0", - "hoist-non-react-statics": "^3.1.0", - "loose-envify": "^1.3.1", - "path-to-regexp": "^1.7.0", - "prop-types": "^15.6.2", - "react-is": "^16.6.0", - "tiny-invariant": "^1.0.2", - "tiny-warning": "^1.0.0" - }, - "peerDependencies": { - "react": ">=15" - } - }, - "node_modules/react-router-config": { - "version": "5.1.1", - "resolved": "https://registry.npmjs.org/react-router-config/-/react-router-config-5.1.1.tgz", - "integrity": "sha512-DuanZjaD8mQp1ppHjgnnUnyOlqYXZVjnov/JzFhjLEwd3Z4dYjMSnqrEzzGThH47vpCOqPPwJM2FtthLeJ8Pbg==", - "license": "MIT", - "dependencies": { - "@babel/runtime": "^7.1.2" - }, - "peerDependencies": { - "react": ">=15", - "react-router": ">=5" - } - }, - "node_modules/react-router-dom": { - "version": "5.3.4", - "resolved": "https://registry.npmjs.org/react-router-dom/-/react-router-dom-5.3.4.tgz", - "integrity": "sha512-m4EqFMHv/Ih4kpcBCONHbkT68KoAeHN4p3lAGoNryfHi0dMy0kCzEZakiKRsvg5wHZ/JLrLW8o8KomWiz/qbYQ==", - "license": "MIT", - "dependencies": { - "@babel/runtime": "^7.12.13", - "history": "^4.9.0", - "loose-envify": "^1.3.1", - "prop-types": "^15.6.2", - "react-router": "5.3.4", - "tiny-invariant": "^1.0.2", - "tiny-warning": "^1.0.0" - }, - "peerDependencies": { - "react": ">=15" - } - }, - "node_modules/readable-stream": { - "version": "3.6.2", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-3.6.2.tgz", - "integrity": "sha512-9u/sniCrY3D5WdsERHzHE4G2YCXqoG5FTHUiCC4SIbr6XcLZBY05ya9EKjYek9O5xOAwjGq+1JdGBAS7Q9ScoA==", - "license": "MIT", - "dependencies": { - "inherits": "^2.0.3", - "string_decoder": "^1.1.1", - "util-deprecate": "^1.0.1" - }, - "engines": { - "node": ">= 6" - } - }, - "node_modules/readdirp": { - "version": "3.6.0", - "resolved": "https://registry.npmjs.org/readdirp/-/readdirp-3.6.0.tgz", - "integrity": "sha512-hOS089on8RduqdbhvQ5Z37A0ESjsqz6qnRcffsMU3495FuTdqSm+7bhJ29JvIOsBDEEnan5DPu9t3To9VRlMzA==", - "license": "MIT", - "dependencies": { - "picomatch": "^2.2.1" - }, - "engines": { - "node": ">=8.10.0" - } - }, - "node_modules/reading-time": { - "version": "1.5.0", - "resolved": "https://registry.npmjs.org/reading-time/-/reading-time-1.5.0.tgz", - "integrity": "sha512-onYyVhBNr4CmAxFsKS7bz+uTLRakypIe4R+5A824vBSkQy/hB3fZepoVEf8OVAxzLvK+H/jm9TzpI3ETSm64Kg==", - "license": "MIT" - }, - "node_modules/rechoir": { - "version": "0.6.2", - "resolved": "https://registry.npmjs.org/rechoir/-/rechoir-0.6.2.tgz", - "integrity": "sha512-HFM8rkZ+i3zrV+4LQjwQ0W+ez98pApMGM3HUrN04j3CqzPOzl9nmP15Y8YXNm8QHGv/eacOVEjqhmWpkRV0NAw==", - "dependencies": { - "resolve": "^1.1.6" - }, - "engines": { - "node": ">= 0.10" - } - }, - "node_modules/recursive-readdir": { - "version": "2.2.3", - "resolved": "https://registry.npmjs.org/recursive-readdir/-/recursive-readdir-2.2.3.tgz", - "integrity": "sha512-8HrF5ZsXk5FAH9dgsx3BlUer73nIhuj+9OrQwEbLTPOBzGkL1lsFCR01am+v+0m2Cmbs1nP12hLDl5FA7EszKA==", - "license": "MIT", - "dependencies": { - "minimatch": "^3.0.5" - }, - "engines": { - "node": ">=6.0.0" - } - }, - "node_modules/redux": { - "version": "4.2.1", - "resolved": "https://registry.npmjs.org/redux/-/redux-4.2.1.tgz", - "integrity": "sha512-LAUYz4lc+Do8/g7aeRa8JkyDErK6ekstQaqWQrNRW//MY1TvCEpMtpTWvlQ+FPbWCx+Xixu/6SHt5N0HR+SB4w==", - "license": "MIT", - "dependencies": { - "@babel/runtime": "^7.9.2" - } - }, - "node_modules/redux-thunk": { - "version": "2.4.2", - "resolved": "https://registry.npmjs.org/redux-thunk/-/redux-thunk-2.4.2.tgz", - "integrity": "sha512-+P3TjtnP0k/FEjcBL5FZpoovtvrTNT/UXd4/sluaSyrURlSlhLSzEdfsTBW7WsKB6yPvgd7q/iZPICFjW4o57Q==", - "license": "MIT", - "peerDependencies": { - "redux": "^4" - } - }, - "node_modules/reftools": { - "version": "1.1.9", - "resolved": "https://registry.npmjs.org/reftools/-/reftools-1.1.9.tgz", - "integrity": "sha512-OVede/NQE13xBQ+ob5CKd5KyeJYU2YInb1bmV4nRoOfquZPkAkxuOXicSe1PvqIuZZ4kD13sPKBbR7UFDmli6w==", - "license": "BSD-3-Clause", - "funding": { - "url": "https://github.com/Mermade/oas-kit?sponsor=1" - } - }, - "node_modules/regenerate": { - "version": "1.4.2", - "resolved": "https://registry.npmjs.org/regenerate/-/regenerate-1.4.2.tgz", - "integrity": "sha512-zrceR/XhGYU/d/opr2EKO7aRHUeiBI8qjtfHqADTwZd6Szfy16la6kqD0MIUs5z5hx6AaKa+PixpPrR289+I0A==", - "license": "MIT" - }, - "node_modules/regenerate-unicode-properties": { - "version": "10.2.0", - "resolved": "https://registry.npmjs.org/regenerate-unicode-properties/-/regenerate-unicode-properties-10.2.0.tgz", - "integrity": "sha512-DqHn3DwbmmPVzeKj9woBadqmXxLvQoQIwu7nopMc72ztvxVmVk2SBhSnx67zuye5TP+lJsb/TBQsjLKhnDf3MA==", - "license": "MIT", - "dependencies": { - "regenerate": "^1.4.2" - }, - "engines": { - "node": ">=4" - } - }, - "node_modules/regenerator-runtime": { - "version": "0.14.1", - "resolved": "https://registry.npmjs.org/regenerator-runtime/-/regenerator-runtime-0.14.1.tgz", - "integrity": "sha512-dYnhHh0nJoMfnkZs6GmmhFknAGRrLznOu5nc9ML+EJxGvrx6H7teuevqVqCuPcPK//3eDrrjQhehXVx9cnkGdw==", - "license": "MIT" - }, - "node_modules/regenerator-transform": { - "version": "0.15.2", - "resolved": "https://registry.npmjs.org/regenerator-transform/-/regenerator-transform-0.15.2.tgz", - "integrity": "sha512-hfMp2BoF0qOk3uc5V20ALGDS2ddjQaLrdl7xrGXvAIow7qeWRM2VA2HuCHkUKk9slq3VwEwLNK3DFBqDfPGYtg==", - "license": "MIT", - "dependencies": { - "@babel/runtime": "^7.8.4" - } - }, - "node_modules/regexpu-core": { - "version": "6.1.1", - "resolved": "https://registry.npmjs.org/regexpu-core/-/regexpu-core-6.1.1.tgz", - "integrity": "sha512-k67Nb9jvwJcJmVpw0jPttR1/zVfnKf8Km0IPatrU/zJ5XeG3+Slx0xLXs9HByJSzXzrlz5EDvN6yLNMDc2qdnw==", - "license": "MIT", - "dependencies": { - "regenerate": "^1.4.2", - "regenerate-unicode-properties": "^10.2.0", - "regjsgen": "^0.8.0", - "regjsparser": "^0.11.0", - "unicode-match-property-ecmascript": "^2.0.0", - "unicode-match-property-value-ecmascript": "^2.1.0" - }, - "engines": { - "node": ">=4" - } - }, - "node_modules/registry-auth-token": { - "version": "5.0.2", - "resolved": "https://registry.npmjs.org/registry-auth-token/-/registry-auth-token-5.0.2.tgz", - "integrity": "sha512-o/3ikDxtXaA59BmZuZrJZDJv8NMDGSj+6j6XaeBmHw8eY1i1qd9+6H+LjVvQXx3HN6aRCGa1cUdJ9RaJZUugnQ==", - "license": "MIT", - "dependencies": { - "@pnpm/npm-conf": "^2.1.0" - }, - "engines": { - "node": ">=14" - } - }, - "node_modules/registry-url": { - "version": "6.0.1", - "resolved": "https://registry.npmjs.org/registry-url/-/registry-url-6.0.1.tgz", - "integrity": "sha512-+crtS5QjFRqFCoQmvGduwYWEBng99ZvmFvF+cUJkGYF1L1BfU8C6Zp9T7f5vPAwyLkUExpvK+ANVZmGU49qi4Q==", - "license": "MIT", - "dependencies": { - "rc": "1.2.8" - }, - "engines": { - "node": ">=12" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/regjsgen": { - "version": "0.8.0", - "resolved": "https://registry.npmjs.org/regjsgen/-/regjsgen-0.8.0.tgz", - "integrity": "sha512-RvwtGe3d7LvWiDQXeQw8p5asZUmfU1G/l6WbUXeHta7Y2PEIvBTwH6E2EfmYUK8pxcxEdEmaomqyp0vZZ7C+3Q==", - "license": "MIT" - }, - "node_modules/regjsparser": { - "version": "0.11.2", - "resolved": "https://registry.npmjs.org/regjsparser/-/regjsparser-0.11.2.tgz", - "integrity": "sha512-3OGZZ4HoLJkkAZx/48mTXJNlmqTGOzc0o9OWQPuWpkOlXXPbyN6OafCcoXUnBqE2D3f/T5L+pWc1kdEmnfnRsA==", - "license": "BSD-2-Clause", - "dependencies": { - "jsesc": "~3.0.2" - }, - "bin": { - "regjsparser": "bin/parser" - } - }, - "node_modules/rehype-raw": { - "version": "7.0.0", - "resolved": "https://registry.npmjs.org/rehype-raw/-/rehype-raw-7.0.0.tgz", - "integrity": "sha512-/aE8hCfKlQeA8LmyeyQvQF3eBiLRGNlfBJEvWH7ivp9sBqs7TNqBL5X3v157rM4IFETqDnIOO+z5M/biZbo9Ww==", - "license": "MIT", - "dependencies": { - "@types/hast": "^3.0.0", - "hast-util-raw": "^9.0.0", - "vfile": "^6.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/relateurl": { - "version": "0.2.7", - "resolved": "https://registry.npmjs.org/relateurl/-/relateurl-0.2.7.tgz", - "integrity": "sha512-G08Dxvm4iDN3MLM0EsP62EDV9IuhXPR6blNz6Utcp7zyV3tr4HVNINt6MpaRWbxoOHT3Q7YN2P+jaHX8vUbgog==", - "license": "MIT", - "engines": { - "node": ">= 0.10" - } - }, - "node_modules/remark-directive": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/remark-directive/-/remark-directive-3.0.0.tgz", - "integrity": "sha512-l1UyWJ6Eg1VPU7Hm/9tt0zKtReJQNOA4+iDMAxTyZNWnJnFlbS/7zhiel/rogTLQ2vMYwDzSJa4BiVNqGlqIMA==", - "license": "MIT", - "dependencies": { - "@types/mdast": "^4.0.0", - "mdast-util-directive": "^3.0.0", - "micromark-extension-directive": "^3.0.0", - "unified": "^11.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/remark-emoji": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/remark-emoji/-/remark-emoji-4.0.1.tgz", - "integrity": "sha512-fHdvsTR1dHkWKev9eNyhTo4EFwbUvJ8ka9SgeWkMPYFX4WoI7ViVBms3PjlQYgw5TLvNQso3GUB/b/8t3yo+dg==", - "license": "MIT", - "dependencies": { - "@types/mdast": "^4.0.2", - "emoticon": "^4.0.1", - "mdast-util-find-and-replace": "^3.0.1", - "node-emoji": "^2.1.0", - "unified": "^11.0.4" - }, - "engines": { - "node": "^12.20.0 || ^14.13.1 || >=16.0.0" - } - }, - "node_modules/remark-frontmatter": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/remark-frontmatter/-/remark-frontmatter-5.0.0.tgz", - "integrity": "sha512-XTFYvNASMe5iPN0719nPrdItC9aU0ssC4v14mH1BCi1u0n1gAocqcujWUrByftZTbLhRtiKRyjYTSIOcr69UVQ==", - "license": "MIT", - "dependencies": { - "@types/mdast": "^4.0.0", - "mdast-util-frontmatter": "^2.0.0", - "micromark-extension-frontmatter": "^2.0.0", - "unified": "^11.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/remark-gfm": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/remark-gfm/-/remark-gfm-4.0.0.tgz", - "integrity": "sha512-U92vJgBPkbw4Zfu/IiW2oTZLSL3Zpv+uI7My2eq8JxKgqraFdU8YUGicEJCEgSbeaG+QDFqIcwwfMTOEelPxuA==", - "license": "MIT", - "dependencies": { - "@types/mdast": "^4.0.0", - "mdast-util-gfm": "^3.0.0", - "micromark-extension-gfm": "^3.0.0", - "remark-parse": "^11.0.0", - "remark-stringify": "^11.0.0", - "unified": "^11.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/remark-mdx": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/remark-mdx/-/remark-mdx-3.0.1.tgz", - "integrity": "sha512-3Pz3yPQ5Rht2pM5R+0J2MrGoBSrzf+tJG94N+t/ilfdh8YLyyKYtidAYwTveB20BoHAcwIopOUqhcmh2F7hGYA==", - "license": "MIT", - "dependencies": { - "mdast-util-mdx": "^3.0.0", - "micromark-extension-mdxjs": "^3.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/remark-parse": { - "version": "11.0.0", - "resolved": "https://registry.npmjs.org/remark-parse/-/remark-parse-11.0.0.tgz", - "integrity": "sha512-FCxlKLNGknS5ba/1lmpYijMUzX2esxW5xQqjWxw2eHFfS2MSdaHVINFmhjo+qN1WhZhNimq0dZATN9pH0IDrpA==", - "license": "MIT", - "dependencies": { - "@types/mdast": "^4.0.0", - "mdast-util-from-markdown": "^2.0.0", - "micromark-util-types": "^2.0.0", - "unified": "^11.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/remark-rehype": { - "version": "11.1.0", - "resolved": "https://registry.npmjs.org/remark-rehype/-/remark-rehype-11.1.0.tgz", - "integrity": "sha512-z3tJrAs2kIs1AqIIy6pzHmAHlF1hWQ+OdY4/hv+Wxe35EhyLKcajL33iUEn3ScxtFox9nUvRufR/Zre8Q08H/g==", - "license": "MIT", - "dependencies": { - "@types/hast": "^3.0.0", - "@types/mdast": "^4.0.0", - "mdast-util-to-hast": "^13.0.0", - "unified": "^11.0.0", - "vfile": "^6.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/remark-stringify": { - "version": "11.0.0", - "resolved": "https://registry.npmjs.org/remark-stringify/-/remark-stringify-11.0.0.tgz", - "integrity": "sha512-1OSmLd3awB/t8qdoEOMazZkNsfVTeY4fTsgzcQFdXNq8ToTN4ZGwrMnlda4K6smTFKD+GRV6O48i6Z4iKgPPpw==", - "license": "MIT", - "dependencies": { - "@types/mdast": "^4.0.0", - "mdast-util-to-markdown": "^2.0.0", - "unified": "^11.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/renderkid": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/renderkid/-/renderkid-3.0.0.tgz", - "integrity": "sha512-q/7VIQA8lmM1hF+jn+sFSPWGlMkSAeNYcPLmDQx2zzuiDfaLrOmumR8iaUKlenFgh0XRPIUeSPlH3A+AW3Z5pg==", - "license": "MIT", - "dependencies": { - "css-select": "^4.1.3", - "dom-converter": "^0.2.0", - "htmlparser2": "^6.1.0", - "lodash": "^4.17.21", - "strip-ansi": "^6.0.1" - } - }, - "node_modules/renderkid/node_modules/css-select": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/css-select/-/css-select-4.3.0.tgz", - "integrity": "sha512-wPpOYtnsVontu2mODhA19JrqWxNsfdatRKd64kmpRbQgh1KtItko5sTnEpPdpSaJszTOhEMlF/RPz28qj4HqhQ==", - "license": "BSD-2-Clause", - "dependencies": { - "boolbase": "^1.0.0", - "css-what": "^6.0.1", - "domhandler": "^4.3.1", - "domutils": "^2.8.0", - "nth-check": "^2.0.1" - }, - "funding": { - "url": "https://github.com/sponsors/fb55" - } - }, - "node_modules/renderkid/node_modules/dom-serializer": { - "version": "1.4.1", - "resolved": "https://registry.npmjs.org/dom-serializer/-/dom-serializer-1.4.1.tgz", - "integrity": "sha512-VHwB3KfrcOOkelEG2ZOfxqLZdfkil8PtJi4P8N2MMXucZq2yLp75ClViUlOVwyoHEDjYU433Aq+5zWP61+RGag==", - "license": "MIT", - "dependencies": { - "domelementtype": "^2.0.1", - "domhandler": "^4.2.0", - "entities": "^2.0.0" - }, - "funding": { - "url": "https://github.com/cheeriojs/dom-serializer?sponsor=1" - } - }, - "node_modules/renderkid/node_modules/domhandler": { - "version": "4.3.1", - "resolved": "https://registry.npmjs.org/domhandler/-/domhandler-4.3.1.tgz", - "integrity": "sha512-GrwoxYN+uWlzO8uhUXRl0P+kHE4GtVPfYzVLcUxPL7KNdHKj66vvlhiweIHqYYXWlw+T8iLMp42Lm67ghw4WMQ==", - "license": "BSD-2-Clause", - "dependencies": { - "domelementtype": "^2.2.0" - }, - "engines": { - "node": ">= 4" - }, - "funding": { - "url": "https://github.com/fb55/domhandler?sponsor=1" - } - }, - "node_modules/renderkid/node_modules/domutils": { - "version": "2.8.0", - "resolved": "https://registry.npmjs.org/domutils/-/domutils-2.8.0.tgz", - "integrity": "sha512-w96Cjofp72M5IIhpjgobBimYEfoPjx1Vx0BSX9P30WBdZW2WIKU0T1Bd0kz2eNZ9ikjKgHbEyKx8BB6H1L3h3A==", - "license": "BSD-2-Clause", - "dependencies": { - "dom-serializer": "^1.0.1", - "domelementtype": "^2.2.0", - "domhandler": "^4.2.0" - }, - "funding": { - "url": "https://github.com/fb55/domutils?sponsor=1" - } - }, - "node_modules/renderkid/node_modules/entities": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/entities/-/entities-2.2.0.tgz", - "integrity": "sha512-p92if5Nz619I0w+akJrLZH0MX0Pb5DX39XOwQTtXSdQQOaYH03S1uIQp4mhOZtAXrxq4ViO67YTiLBo2638o9A==", - "license": "BSD-2-Clause", - "funding": { - "url": "https://github.com/fb55/entities?sponsor=1" - } - }, - "node_modules/renderkid/node_modules/htmlparser2": { - "version": "6.1.0", - "resolved": "https://registry.npmjs.org/htmlparser2/-/htmlparser2-6.1.0.tgz", - "integrity": "sha512-gyyPk6rgonLFEDGoeRgQNaEUvdJ4ktTmmUh/h2t7s+M8oPpIPxgNACWa+6ESR57kXstwqPiCut0V8NRpcwgU7A==", - "funding": [ - "https://github.com/fb55/htmlparser2?sponsor=1", - { - "type": "github", - "url": "https://github.com/sponsors/fb55" - } - ], - "license": "MIT", - "dependencies": { - "domelementtype": "^2.0.1", - "domhandler": "^4.0.0", - "domutils": "^2.5.2", - "entities": "^2.0.0" - } - }, - "node_modules/repeat-string": { - "version": "1.6.1", - "resolved": "https://registry.npmjs.org/repeat-string/-/repeat-string-1.6.1.tgz", - "integrity": "sha512-PV0dzCYDNfRi1jCDbJzpW7jNNDRuCOG/jI5ctQcGKt/clZD+YcPS3yIlWuTJMmESC8aevCFmWJy5wjAFgNqN6w==", - "license": "MIT", - "engines": { - "node": ">=0.10" - } - }, - "node_modules/require-directory": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/require-directory/-/require-directory-2.1.1.tgz", - "integrity": "sha512-fGxEI7+wsG9xrvdjsrlmL22OMTTiHRwAMroiEeMgq8gzoLC/PQr7RsRDSTLUg/bZAZtF+TVIkHc6/4RIKrui+Q==", - "license": "MIT", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/require-from-string": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/require-from-string/-/require-from-string-2.0.2.tgz", - "integrity": "sha512-Xf0nWe6RseziFMu+Ap9biiUbmplq6S9/p+7w7YXP/JBHhrUDDUhwa+vANyubuqfZWTveU//DYVGsDG7RKL/vEw==", - "license": "MIT", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/require-like": { - "version": "0.1.2", - "resolved": "https://registry.npmjs.org/require-like/-/require-like-0.1.2.tgz", - "integrity": "sha512-oyrU88skkMtDdauHDuKVrgR+zuItqr6/c//FXzvmxRGMexSDc6hNvJInGW3LL46n+8b50RykrvwSUIIQH2LQ5A==", - "engines": { - "node": "*" - } - }, - "node_modules/requires-port": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/requires-port/-/requires-port-1.0.0.tgz", - "integrity": "sha512-KigOCHcocU3XODJxsu8i/j8T9tzT4adHiecwORRQ0ZZFcp7ahwXuRU1m+yuO90C5ZUyGeGfocHDI14M3L3yDAQ==", - "license": "MIT" - }, - "node_modules/reselect": { - "version": "4.1.8", - "resolved": "https://registry.npmjs.org/reselect/-/reselect-4.1.8.tgz", - "integrity": "sha512-ab9EmR80F/zQTMNeneUr4cv+jSwPJgIlvEmVwLerwrWVbpLlBuls9XHzIeTFy4cegU2NHBp3va0LKOzU5qFEYQ==", - "license": "MIT" - }, - "node_modules/resolve": { - "version": "1.22.8", - "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.22.8.tgz", - "integrity": "sha512-oKWePCxqpd6FlLvGV1VU0x7bkPmmCNolxzjMf4NczoDnQcIWrAF+cPtZn5i6n+RfD2d9i0tzpKnG6Yk168yIyw==", - "license": "MIT", - "dependencies": { - "is-core-module": "^2.13.0", - "path-parse": "^1.0.7", - "supports-preserve-symlinks-flag": "^1.0.0" - }, - "bin": { - "resolve": "bin/resolve" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/resolve-alpn": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/resolve-alpn/-/resolve-alpn-1.2.1.tgz", - "integrity": "sha512-0a1F4l73/ZFZOakJnQ3FvkJ2+gSTQWz/r2KE5OdDY0TxPm5h4GkqkWWfM47T7HsbnOtcJVEF4epCVy6u7Q3K+g==", - "license": "MIT" - }, - "node_modules/resolve-from": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-4.0.0.tgz", - "integrity": "sha512-pb/MYmXstAkysRFx8piNI1tGFNQIFA3vkE3Gq4EuA1dF6gHp/+vgZqsCGJapvy8N3Q+4o7FwvquPJcnZ7RYy4g==", - "license": "MIT", - "engines": { - "node": ">=4" - } - }, - "node_modules/resolve-package-path": { - "version": "4.0.3", - "resolved": "https://registry.npmjs.org/resolve-package-path/-/resolve-package-path-4.0.3.tgz", - "integrity": "sha512-SRpNAPW4kewOaNUt8VPqhJ0UMxawMwzJD8V7m1cJfdSTK9ieZwS6K7Dabsm4bmLFM96Z5Y/UznrpG5kt1im8yA==", - "license": "MIT", - "dependencies": { - "path-root": "^0.1.1" - }, - "engines": { - "node": ">= 12" - } - }, - "node_modules/resolve-pathname": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/resolve-pathname/-/resolve-pathname-3.0.0.tgz", - "integrity": "sha512-C7rARubxI8bXFNB/hqcp/4iUeIXJhJZvFPFPiSPRnhU5UPxzMFIl+2E6yY6c4k9giDJAhtV+enfA+G89N6Csng==", - "license": "MIT" - }, - "node_modules/responselike": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/responselike/-/responselike-3.0.0.tgz", - "integrity": "sha512-40yHxbNcl2+rzXvZuVkrYohathsSJlMTXKryG5y8uciHv1+xDLHQpgjG64JUO9nrEq2jGLH6IZ8BcZyw3wrweg==", - "license": "MIT", - "dependencies": { - "lowercase-keys": "^3.0.0" - }, - "engines": { - "node": ">=14.16" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/retry": { - "version": "0.13.1", - "resolved": "https://registry.npmjs.org/retry/-/retry-0.13.1.tgz", - "integrity": "sha512-XQBQ3I8W1Cge0Seh+6gjj03LbmRFWuoszgK9ooCpwYIrhhoO80pfq4cUkU5DkknwfOfFteRwlZ56PYOGYyFWdg==", - "license": "MIT", - "engines": { - "node": ">= 4" - } - }, - "node_modules/reusify": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/reusify/-/reusify-1.0.4.tgz", - "integrity": "sha512-U9nH88a3fc/ekCF1l0/UP1IosiuIjyTh7hBvXVMHYgVcfGvt897Xguj2UOLDeI5BG2m7/uwyaLVT6fbtCwTyzw==", - "license": "MIT", - "engines": { - "iojs": ">=1.0.0", - "node": ">=0.10.0" - } - }, - "node_modules/rimraf": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-3.0.2.tgz", - "integrity": "sha512-JZkJMZkAGFFPP2YqXZXPbMlMBgsxzE8ILs4lMIX/2o0L9UBw9O/Y3o6wFw/i9YLapcUJWwqbi3kdxIPdC62TIA==", - "deprecated": "Rimraf versions prior to v4 are no longer supported", - "license": "ISC", - "dependencies": { - "glob": "^7.1.3" - }, - "bin": { - "rimraf": "bin.js" - }, - "funding": { - "url": "https://github.com/sponsors/isaacs" - } - }, - "node_modules/ripemd160": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/ripemd160/-/ripemd160-2.0.2.tgz", - "integrity": "sha512-ii4iagi25WusVoiC4B4lq7pbXfAp3D9v5CwfkY33vffw2+pkDjY1D8GaN7spsxvCSx8dkPqOZCEZyfxcmJG2IA==", - "license": "MIT", - "dependencies": { - "hash-base": "^3.0.0", - "inherits": "^2.0.1" - } - }, - "node_modules/rtlcss": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/rtlcss/-/rtlcss-4.3.0.tgz", - "integrity": "sha512-FI+pHEn7Wc4NqKXMXFM+VAYKEj/mRIcW4h24YVwVtyjI+EqGrLc2Hx/Ny0lrZ21cBWU2goLy36eqMcNj3AQJig==", - "license": "MIT", - "dependencies": { - "escalade": "^3.1.1", - "picocolors": "^1.0.0", - "postcss": "^8.4.21", - "strip-json-comments": "^3.1.1" - }, - "bin": { - "rtlcss": "bin/rtlcss.js" - }, - "engines": { - "node": ">=12.0.0" - } - }, - "node_modules/run-parallel": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/run-parallel/-/run-parallel-1.2.0.tgz", - "integrity": "sha512-5l4VyZR86LZ/lDxZTR6jqL8AFE2S0IFLMP26AbjsLVADxHdhB/c0GUsH+y39UfCi3dzz8OlQuPmnaJOMoDHQBA==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/feross" - }, - { - "type": "patreon", - "url": "https://www.patreon.com/feross" - }, - { - "type": "consulting", - "url": "https://feross.org/support" - } - ], - "license": "MIT", - "dependencies": { - "queue-microtask": "^1.2.2" - } - }, - "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": "Apache-2.0", - "dependencies": { - "tslib": "^2.1.0" - } - }, - "node_modules/sade": { - "version": "1.8.1", - "resolved": "https://registry.npmjs.org/sade/-/sade-1.8.1.tgz", - "integrity": "sha512-xal3CZX1Xlo/k4ApwCFrHVACi9fBqJ7V+mwhBsuf/1IOKbBy098Fex+Wa/5QMubw09pSZ/u8EY8PWgevJsXp1A==", - "license": "MIT", - "dependencies": { - "mri": "^1.1.0" - }, - "engines": { - "node": ">=6" - } - }, - "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==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/feross" - }, - { - "type": "patreon", - "url": "https://www.patreon.com/feross" - }, - { - "type": "consulting", - "url": "https://feross.org/support" - } - ], - "license": "MIT" - }, - "node_modules/safer-buffer": { - "version": "2.1.2", - "resolved": "https://registry.npmjs.org/safer-buffer/-/safer-buffer-2.1.2.tgz", - "integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==" - }, - "node_modules/sass": { - "version": "1.81.0", - "resolved": "https://registry.npmjs.org/sass/-/sass-1.81.0.tgz", - "integrity": "sha512-Q4fOxRfhmv3sqCLoGfvrC9pRV8btc0UtqL9mN6Yrv6Qi9ScL55CVH1vlPP863ISLEEMNLLuu9P+enCeGHlnzhA==", - "license": "MIT", - "dependencies": { - "chokidar": "^4.0.0", - "immutable": "^5.0.2", - "source-map-js": ">=0.6.2 <2.0.0" - }, - "bin": { - "sass": "sass.js" - }, - "engines": { - "node": ">=14.0.0" - }, - "optionalDependencies": { - "@parcel/watcher": "^2.4.1" - } - }, - "node_modules/sass-loader": { - "version": "10.5.2", - "resolved": "https://registry.npmjs.org/sass-loader/-/sass-loader-10.5.2.tgz", - "integrity": "sha512-vMUoSNOUKJILHpcNCCyD23X34gve1TS7Rjd9uXHeKqhvBG39x6XbswFDtpbTElj6XdMFezoWhkh5vtKudf2cgQ==", - "license": "MIT", - "dependencies": { - "klona": "^2.0.4", - "loader-utils": "^2.0.0", - "neo-async": "^2.6.2", - "schema-utils": "^3.0.0", - "semver": "^7.3.2" - }, - "engines": { - "node": ">= 10.13.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/webpack" - }, - "peerDependencies": { - "fibers": ">= 3.1.0", - "node-sass": "^4.0.0 || ^5.0.0 || ^6.0.0 || ^7.0.0 || ^8.0.0 || ^9.0.0", - "sass": "^1.3.0", - "webpack": "^4.36.0 || ^5.0.0" - }, - "peerDependenciesMeta": { - "fibers": { - "optional": true - }, - "node-sass": { - "optional": true - }, - "sass": { - "optional": true - } - } - }, - "node_modules/sass-loader/node_modules/ajv": { - "version": "6.12.6", - "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz", - "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==", - "license": "MIT", - "dependencies": { - "fast-deep-equal": "^3.1.1", - "fast-json-stable-stringify": "^2.0.0", - "json-schema-traverse": "^0.4.1", - "uri-js": "^4.2.2" - }, - "funding": { - "type": "github", - "url": "https://github.com/sponsors/epoberezkin" - } - }, - "node_modules/sass-loader/node_modules/ajv-keywords": { - "version": "3.5.2", - "resolved": "https://registry.npmjs.org/ajv-keywords/-/ajv-keywords-3.5.2.tgz", - "integrity": "sha512-5p6WTN0DdTGVQk6VjcEju19IgaHudalcfabD7yhDGeA6bcQnmL+CpveLJq/3hvfwd1aof6L386Ougkx6RfyMIQ==", - "license": "MIT", - "peerDependencies": { - "ajv": "^6.9.1" - } - }, - "node_modules/sass-loader/node_modules/json-schema-traverse": { - "version": "0.4.1", - "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz", - "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==", - "license": "MIT" - }, - "node_modules/sass-loader/node_modules/schema-utils": { - "version": "3.3.0", - "resolved": "https://registry.npmjs.org/schema-utils/-/schema-utils-3.3.0.tgz", - "integrity": "sha512-pN/yOAvcC+5rQ5nERGuwrjLlYvLTbCibnZ1I7B1LaiAz9BRBlE9GMgE/eqV30P7aJQUf7Ddimy/RsbYO/GrVGg==", - "license": "MIT", - "dependencies": { - "@types/json-schema": "^7.0.8", - "ajv": "^6.12.5", - "ajv-keywords": "^3.5.2" - }, - "engines": { - "node": ">= 10.13.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/webpack" - } - }, - "node_modules/sass/node_modules/chokidar": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/chokidar/-/chokidar-4.0.1.tgz", - "integrity": "sha512-n8enUVCED/KVRQlab1hr3MVpcVMvxtZjmEa956u+4YijlmQED223XMSYj2tLuKvr4jcCTzNNMpQDUer72MMmzA==", - "license": "MIT", - "dependencies": { - "readdirp": "^4.0.1" - }, - "engines": { - "node": ">= 14.16.0" - }, - "funding": { - "url": "https://paulmillr.com/funding/" - } - }, - "node_modules/sass/node_modules/readdirp": { - "version": "4.0.2", - "resolved": "https://registry.npmjs.org/readdirp/-/readdirp-4.0.2.tgz", - "integrity": "sha512-yDMz9g+VaZkqBYS/ozoBJwaBhTbZo3UNYQHNRw1D3UFQB8oHB4uS/tAODO+ZLjGWmUbKnIlOWO+aaIiAxrUWHA==", - "license": "MIT", - "engines": { - "node": ">= 14.16.0" - }, - "funding": { - "type": "individual", - "url": "https://paulmillr.com/funding/" - } - }, - "node_modules/sax": { - "version": "1.4.1", - "resolved": "https://registry.npmjs.org/sax/-/sax-1.4.1.tgz", - "integrity": "sha512-+aWOz7yVScEGoKNd4PA10LZ8sk0A/z5+nXQG5giUO5rprX9jgYsTdov9qCchZiPIZezbZH+jRut8nPodFAX4Jg==", - "license": "ISC" - }, - "node_modules/scheduler": { - "version": "0.23.2", - "resolved": "https://registry.npmjs.org/scheduler/-/scheduler-0.23.2.tgz", - "integrity": "sha512-UOShsPwz7NrMUqhR6t0hWjFduvOzbtv7toDH1/hIrfRNIDBnnBWd0CwJTGvTpngVlmwGCdP9/Zl/tVrDqcuYzQ==", - "license": "MIT", - "dependencies": { - "loose-envify": "^1.1.0" - } - }, - "node_modules/schema-utils": { - "version": "4.2.0", - "resolved": "https://registry.npmjs.org/schema-utils/-/schema-utils-4.2.0.tgz", - "integrity": "sha512-L0jRsrPpjdckP3oPug3/VxNKt2trR8TcabrM6FOAAlvC/9Phcmm+cuAgTlxBqdBR1WJx7Naj9WHw+aOmheSVbw==", - "license": "MIT", - "dependencies": { - "@types/json-schema": "^7.0.9", - "ajv": "^8.9.0", - "ajv-formats": "^2.1.1", - "ajv-keywords": "^5.1.0" - }, - "engines": { - "node": ">= 12.13.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/webpack" - } - }, - "node_modules/search-insights": { - "version": "2.17.3", - "resolved": "https://registry.npmjs.org/search-insights/-/search-insights-2.17.3.tgz", - "integrity": "sha512-RQPdCYTa8A68uM2jwxoY842xDhvx3E5LFL1LxvxCNMev4o5mLuokczhzjAgGwUZBAmOKZknArSxLKmXtIi2AxQ==", - "license": "MIT", - "peer": true - }, - "node_modules/section-matter": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/section-matter/-/section-matter-1.0.0.tgz", - "integrity": "sha512-vfD3pmTzGpufjScBh50YHKzEu2lxBWhVEHsNGoEXmCmn2hKGfeNLYMzCJpe8cD7gqX7TJluOVpBkAequ6dgMmA==", - "license": "MIT", - "dependencies": { - "extend-shallow": "^2.0.1", - "kind-of": "^6.0.0" - }, - "engines": { - "node": ">=4" - } - }, - "node_modules/select-hose": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/select-hose/-/select-hose-2.0.0.tgz", - "integrity": "sha512-mEugaLK+YfkijB4fx0e6kImuJdCIt2LxCRcbEYPqRGCs4F2ogyfZU5IAZRdjCP8JPq2AtdNoC/Dux63d9Kiryg==", - "license": "MIT" - }, - "node_modules/selfsigned": { - "version": "2.4.1", - "resolved": "https://registry.npmjs.org/selfsigned/-/selfsigned-2.4.1.tgz", - "integrity": "sha512-th5B4L2U+eGLq1TVh7zNRGBapioSORUeymIydxgFpwww9d2qyKvtuPU2jJuHvYAwwqi2Y596QBL3eEqcPEYL8Q==", - "license": "MIT", - "dependencies": { - "@types/node-forge": "^1.3.0", - "node-forge": "^1" - }, - "engines": { - "node": ">=10" - } - }, - "node_modules/semver": { - "version": "7.6.3", - "resolved": "https://registry.npmjs.org/semver/-/semver-7.6.3.tgz", - "integrity": "sha512-oVekP1cKtI+CTDvHWYFUcMtsK/00wmAEfyqKfNdARm8u1wNVhSgaX7A8d4UuIlUI5e84iEwOhs7ZPYRmzU9U6A==", - "license": "ISC", - "bin": { - "semver": "bin/semver.js" - }, - "engines": { - "node": ">=10" - } - }, - "node_modules/semver-diff": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/semver-diff/-/semver-diff-4.0.0.tgz", - "integrity": "sha512-0Ju4+6A8iOnpL/Thra7dZsSlOHYAHIeMxfhWQRI1/VLcT3WDBZKKtQt/QkBOsiIN9ZpuvHE6cGZ0x4glCMmfiA==", - "license": "MIT", - "dependencies": { - "semver": "^7.3.5" - }, - "engines": { - "node": ">=12" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/send": { - "version": "0.19.0", - "resolved": "https://registry.npmjs.org/send/-/send-0.19.0.tgz", - "integrity": "sha512-dW41u5VfLXu8SJh5bwRmyYUbAoSB3c9uQh6L8h/KtsFREPWpbX1lrljJo186Jc4nmci/sGUZ9a0a0J2zgfq2hw==", - "dependencies": { - "debug": "2.6.9", - "depd": "2.0.0", - "destroy": "1.2.0", - "encodeurl": "~1.0.2", - "escape-html": "~1.0.3", - "etag": "~1.8.1", - "fresh": "0.5.2", - "http-errors": "2.0.0", - "mime": "1.6.0", - "ms": "2.1.3", - "on-finished": "2.4.1", - "range-parser": "~1.2.1", - "statuses": "2.0.1" - }, - "engines": { - "node": ">= 0.8.0" - } - }, - "node_modules/send/node_modules/debug": { - "version": "2.6.9", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", - "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", - "dependencies": { - "ms": "2.0.0" - } - }, - "node_modules/send/node_modules/debug/node_modules/ms": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", - "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==" - }, - "node_modules/send/node_modules/encodeurl": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/encodeurl/-/encodeurl-1.0.2.tgz", - "integrity": "sha512-TPJXq8JqFaVYm2CWmPvnP2Iyo4ZSM7/QKcSmuMLDObfpH5fi7RUGmd/rTDf+rut/saiDiQEeVTNgAmJEdAOx0w==", - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/send/node_modules/ms": { - "version": "2.1.3", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.3.tgz", - "integrity": "sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==" - }, - "node_modules/send/node_modules/range-parser": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/range-parser/-/range-parser-1.2.1.tgz", - "integrity": "sha512-Hrgsx+orqoygnmhFbKaHE6c296J+HTAQXoxEF6gNupROmmGJRoyzfG3ccAveqCBrwr/2yxQ5BVd/GTl5agOwSg==", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/serialize-javascript": { - "version": "6.0.2", - "resolved": "https://registry.npmjs.org/serialize-javascript/-/serialize-javascript-6.0.2.tgz", - "integrity": "sha512-Saa1xPByTTq2gdeFZYLLo+RFE35NHZkAbqZeWNd3BpzppeVisAqpDjcp8dyf6uIvEqJRd46jemmyA4iFIeVk8g==", - "license": "BSD-3-Clause", - "dependencies": { - "randombytes": "^2.1.0" - } - }, - "node_modules/serve-handler": { - "version": "6.1.6", - "resolved": "https://registry.npmjs.org/serve-handler/-/serve-handler-6.1.6.tgz", - "integrity": "sha512-x5RL9Y2p5+Sh3D38Fh9i/iQ5ZK+e4xuXRd/pGbM4D13tgo/MGwbttUk8emytcr1YYzBYs+apnUngBDFYfpjPuQ==", - "license": "MIT", - "dependencies": { - "bytes": "3.0.0", - "content-disposition": "0.5.2", - "mime-types": "2.1.18", - "minimatch": "3.1.2", - "path-is-inside": "1.0.2", - "path-to-regexp": "3.3.0", - "range-parser": "1.2.0" - } - }, - "node_modules/serve-handler/node_modules/path-to-regexp": { - "version": "3.3.0", - "resolved": "https://registry.npmjs.org/path-to-regexp/-/path-to-regexp-3.3.0.tgz", - "integrity": "sha512-qyCH421YQPS2WFDxDjftfc1ZR5WKQzVzqsp4n9M2kQhVOo/ByahFoUNJfl58kOcEGfQ//7weFTDhm+ss8Ecxgw==", - "license": "MIT" - }, - "node_modules/serve-index": { - "version": "1.9.1", - "resolved": "https://registry.npmjs.org/serve-index/-/serve-index-1.9.1.tgz", - "integrity": "sha512-pXHfKNP4qujrtteMrSBb0rc8HJ9Ms/GrXwcUtUtD5s4ewDJI8bT3Cz2zTVRMKtri49pLx2e0Ya8ziP5Ya2pZZw==", - "license": "MIT", - "dependencies": { - "accepts": "~1.3.4", - "batch": "0.6.1", - "debug": "2.6.9", - "escape-html": "~1.0.3", - "http-errors": "~1.6.2", - "mime-types": "~2.1.17", - "parseurl": "~1.3.2" - }, - "engines": { - "node": ">= 0.8.0" - } - }, - "node_modules/serve-index/node_modules/debug": { - "version": "2.6.9", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", - "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", - "license": "MIT", - "dependencies": { - "ms": "2.0.0" - } - }, - "node_modules/serve-index/node_modules/depd": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/depd/-/depd-1.1.2.tgz", - "integrity": "sha512-7emPTl6Dpo6JRXOXjLRxck+FlLRX5847cLKEn00PLAgc3g2hTZZgr+e4c2v6QpSmLeFP3n5yUo7ft6avBK/5jQ==", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/serve-index/node_modules/http-errors": { - "version": "1.6.3", - "resolved": "https://registry.npmjs.org/http-errors/-/http-errors-1.6.3.tgz", - "integrity": "sha512-lks+lVC8dgGyh97jxvxeYTWQFvh4uw4yC12gVl63Cg30sjPX4wuGcdkICVXDAESr6OJGjqGA8Iz5mkeN6zlD7A==", - "license": "MIT", - "dependencies": { - "depd": "~1.1.2", - "inherits": "2.0.3", - "setprototypeof": "1.1.0", - "statuses": ">= 1.4.0 < 2" - }, - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/serve-index/node_modules/inherits": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", - "integrity": "sha512-x00IRNXNy63jwGkJmzPigoySHbaqpNuzKbBOmzK+g2OdZpQ9w+sxCN+VSB3ja7IAge2OP2qpfxTjeNcyjmW1uw==", - "license": "ISC" - }, - "node_modules/serve-index/node_modules/ms": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", - "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==", - "license": "MIT" - }, - "node_modules/serve-index/node_modules/setprototypeof": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/setprototypeof/-/setprototypeof-1.1.0.tgz", - "integrity": "sha512-BvE/TwpZX4FXExxOxZyRGQQv651MSwmWKZGqvmPcRIjDqWub67kTKuIMx43cZZrS/cBBzwBcNDWoFxt2XEFIpQ==", - "license": "ISC" - }, - "node_modules/serve-index/node_modules/statuses": { - "version": "1.5.0", - "resolved": "https://registry.npmjs.org/statuses/-/statuses-1.5.0.tgz", - "integrity": "sha512-OpZ3zP+jT1PI7I8nemJX4AKmAX070ZkYPVWV/AaKTJl+tXCTGyVdC1a4SL8RUQYEwk/f34ZX8UTykN68FwrqAA==", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/serve-static": { - "version": "1.16.2", - "resolved": "https://registry.npmjs.org/serve-static/-/serve-static-1.16.2.tgz", - "integrity": "sha512-VqpjJZKadQB/PEbEwvFdO43Ax5dFBZ2UECszz8bQ7pi7wt//PWe1P6MN7eCnjsatYtBT6EuiClbjSWP2WrIoTw==", - "dependencies": { - "encodeurl": "~2.0.0", - "escape-html": "~1.0.3", - "parseurl": "~1.3.3", - "send": "0.19.0" - }, - "engines": { - "node": ">= 0.8.0" - } - }, - "node_modules/set-function-length": { - "version": "1.2.2", - "resolved": "https://registry.npmjs.org/set-function-length/-/set-function-length-1.2.2.tgz", - "integrity": "sha512-pgRc4hJ4/sNjWCSS9AmnS40x3bNMDTknHgL5UaMBTMyJnU90EgWh1Rz+MC9eFu4BuN/UwZjKQuY/1v3rM7HMfg==", - "license": "MIT", - "dependencies": { - "define-data-property": "^1.1.4", - "es-errors": "^1.3.0", - "function-bind": "^1.1.2", - "get-intrinsic": "^1.2.4", - "gopd": "^1.0.1", - "has-property-descriptors": "^1.0.2" - }, - "engines": { - "node": ">= 0.4" - } - }, - "node_modules/setimmediate": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/setimmediate/-/setimmediate-1.0.5.tgz", - "integrity": "sha512-MATJdZp8sLqDl/68LfQmbP8zKPLQNV6BIZoIgrscFDQ+RsvK/BxeDQOgyxKKoh0y/8h3BqVFnCqQ/gd+reiIXA==", - "license": "MIT" - }, - "node_modules/setprototypeof": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/setprototypeof/-/setprototypeof-1.2.0.tgz", - "integrity": "sha512-E5LDX7Wrp85Kil5bhZv46j8jOeboKq5JMmYM3gVGdGH8xFpPWXUMsNrlODCrkoxMEeNi/XZIwuRvY4XNwYMJpw==" - }, - "node_modules/sha.js": { - "version": "2.4.11", - "resolved": "https://registry.npmjs.org/sha.js/-/sha.js-2.4.11.tgz", - "integrity": "sha512-QMEp5B7cftE7APOjk5Y6xgrbWu+WkLVQwk8JNjZ8nKRciZaByEW6MubieAiToS7+dwvrjGhH8jRXz3MVd0AYqQ==", - "license": "(MIT AND BSD-3-Clause)", - "dependencies": { - "inherits": "^2.0.1", - "safe-buffer": "^5.0.1" - }, - "bin": { - "sha.js": "bin.js" - } - }, - "node_modules/shallow-clone": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/shallow-clone/-/shallow-clone-3.0.1.tgz", - "integrity": "sha512-/6KqX+GVUdqPuPPd2LxDDxzX6CAbjJehAAOKlNpqqUpAqPM6HeL8f+o3a+JsyGjn2lv0WY8UsTgUJjU9Ok55NA==", - "license": "MIT", - "dependencies": { - "kind-of": "^6.0.2" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/shallowequal": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/shallowequal/-/shallowequal-1.1.0.tgz", - "integrity": "sha512-y0m1JoUZSlPAjXVtPPW70aZWfIL/dSP7AFkRnniLCrK/8MDKog3TySTBmckD+RObVxH0v4Tox67+F14PdED2oQ==", - "license": "MIT" - }, - "node_modules/shebang-command": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/shebang-command/-/shebang-command-2.0.0.tgz", - "integrity": "sha512-kHxr2zZpYtdmrN1qDjrrX/Z1rR1kG8Dx+gkpK1G4eXmvXswmcE1hTWBWYUzlraYw1/yZp6YuDY77YtvbN0dmDA==", - "license": "MIT", - "dependencies": { - "shebang-regex": "^3.0.0" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/shebang-regex": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/shebang-regex/-/shebang-regex-3.0.0.tgz", - "integrity": "sha512-7++dFhtcx3353uBaq8DDR4NuxBetBzC7ZQOhmTQInHEd6bSrXdiEyzCvG07Z44UYdLShWUyXt5M/yhz8ekcb1A==", - "license": "MIT", - "engines": { - "node": ">=8" - } - }, - "node_modules/shell-quote": { - "version": "1.8.1", - "resolved": "https://registry.npmjs.org/shell-quote/-/shell-quote-1.8.1.tgz", - "integrity": "sha512-6j1W9l1iAs/4xYBI1SYOVZyFcCis9b4KCLQ8fgAGG07QvzaRLVVRQvAy85yNmmZSjYjg4MWh4gNvlPujU/5LpA==", - "license": "MIT", - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/shelljs": { - "version": "0.8.5", - "resolved": "https://registry.npmjs.org/shelljs/-/shelljs-0.8.5.tgz", - "integrity": "sha512-TiwcRcrkhHvbrZbnRcFYMLl30Dfov3HKqzp5tO5b4pt6G/SezKcYhmDg15zXVBswHmctSAQKznqNW2LO5tTDow==", - "license": "BSD-3-Clause", - "dependencies": { - "glob": "^7.0.0", - "interpret": "^1.0.0", - "rechoir": "^0.6.2" - }, - "bin": { - "shjs": "bin/shjs" - }, - "engines": { - "node": ">=4" - } - }, - "node_modules/should": { - "version": "13.2.3", - "resolved": "https://registry.npmjs.org/should/-/should-13.2.3.tgz", - "integrity": "sha512-ggLesLtu2xp+ZxI+ysJTmNjh2U0TsC+rQ/pfED9bUZZ4DKefP27D+7YJVVTvKsmjLpIi9jAa7itwDGkDDmt1GQ==", - "license": "MIT", - "dependencies": { - "should-equal": "^2.0.0", - "should-format": "^3.0.3", - "should-type": "^1.4.0", - "should-type-adaptors": "^1.0.1", - "should-util": "^1.0.0" - } - }, - "node_modules/should-equal": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/should-equal/-/should-equal-2.0.0.tgz", - "integrity": "sha512-ZP36TMrK9euEuWQYBig9W55WPC7uo37qzAEmbjHz4gfyuXrEUgF8cUvQVO+w+d3OMfPvSRQJ22lSm8MQJ43LTA==", - "license": "MIT", - "dependencies": { - "should-type": "^1.4.0" - } - }, - "node_modules/should-format": { - "version": "3.0.3", - "resolved": "https://registry.npmjs.org/should-format/-/should-format-3.0.3.tgz", - "integrity": "sha512-hZ58adtulAk0gKtua7QxevgUaXTTXxIi8t41L3zo9AHvjXO1/7sdLECuHeIN2SRtYXpNkmhoUP2pdeWgricQ+Q==", - "license": "MIT", - "dependencies": { - "should-type": "^1.3.0", - "should-type-adaptors": "^1.0.1" - } - }, - "node_modules/should-type": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/should-type/-/should-type-1.4.0.tgz", - "integrity": "sha512-MdAsTu3n25yDbIe1NeN69G4n6mUnJGtSJHygX3+oN0ZbO3DTiATnf7XnYJdGT42JCXurTb1JI0qOBR65shvhPQ==", - "license": "MIT" - }, - "node_modules/should-type-adaptors": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/should-type-adaptors/-/should-type-adaptors-1.1.0.tgz", - "integrity": "sha512-JA4hdoLnN+kebEp2Vs8eBe9g7uy0zbRo+RMcU0EsNy+R+k049Ki+N5tT5Jagst2g7EAja+euFuoXFCa8vIklfA==", - "license": "MIT", - "dependencies": { - "should-type": "^1.3.0", - "should-util": "^1.0.0" - } - }, - "node_modules/should-util": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/should-util/-/should-util-1.0.1.tgz", - "integrity": "sha512-oXF8tfxx5cDk8r2kYqlkUJzZpDBqVY/II2WhvU0n9Y3XYvAYRmeaf1PvvIvTgPnv4KJ+ES5M0PyDq5Jp+Ygy2g==", - "license": "MIT" - }, - "node_modules/side-channel": { - "version": "1.0.6", - "resolved": "https://registry.npmjs.org/side-channel/-/side-channel-1.0.6.tgz", - "integrity": "sha512-fDW/EZ6Q9RiO8eFG8Hj+7u/oW+XrPTIChwCOM2+th2A6OblDtYYIpve9m+KvI9Z4C9qSEXlaGR6bTEYHReuglA==", - "dependencies": { - "call-bind": "^1.0.7", - "es-errors": "^1.3.0", - "get-intrinsic": "^1.2.4", - "object-inspect": "^1.13.1" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "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==", - "license": "ISC" - }, - "node_modules/simple-update-notifier": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/simple-update-notifier/-/simple-update-notifier-2.0.0.tgz", - "integrity": "sha512-a2B9Y0KlNXl9u/vsW6sTIu9vGEpfKu2wRV6l1H3XEas/0gUIzGzBoP/IouTcUQbm9JWZLH3COxyn03TYlFax6w==", - "dev": true, - "license": "MIT", - "dependencies": { - "semver": "^7.5.3" - }, - "engines": { - "node": ">=10" - } - }, - "node_modules/sirv": { - "version": "2.0.4", - "resolved": "https://registry.npmjs.org/sirv/-/sirv-2.0.4.tgz", - "integrity": "sha512-94Bdh3cC2PKrbgSOUqTiGPWVZeSiXfKOVZNJniWoqrWrRkB1CJzBU3NEbiTsPcYy1lDsANA/THzS+9WBiy5nfQ==", - "license": "MIT", - "dependencies": { - "@polka/url": "^1.0.0-next.24", - "mrmime": "^2.0.0", - "totalist": "^3.0.0" - }, - "engines": { - "node": ">= 10" - } - }, - "node_modules/sisteransi": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/sisteransi/-/sisteransi-1.0.5.tgz", - "integrity": "sha512-bLGGlR1QxBcynn2d5YmDX4MGjlZvy2MRBDRNHLJ8VI6l6+9FUiyTFNJ0IveOSP0bcXgVDPRcfGqA0pjaqUpfVg==", - "license": "MIT" - }, - "node_modules/sitemap": { - "version": "7.1.2", - "resolved": "https://registry.npmjs.org/sitemap/-/sitemap-7.1.2.tgz", - "integrity": "sha512-ARCqzHJ0p4gWt+j7NlU5eDlIO9+Rkr/JhPFZKKQ1l5GCus7rJH4UdrlVAh0xC/gDS/Qir2UMxqYNHtsKr2rpCw==", - "license": "MIT", - "dependencies": { - "@types/node": "^17.0.5", - "@types/sax": "^1.2.1", - "arg": "^5.0.0", - "sax": "^1.2.4" - }, - "bin": { - "sitemap": "dist/cli.js" - }, - "engines": { - "node": ">=12.0.0", - "npm": ">=5.6.0" - } - }, - "node_modules/sitemap/node_modules/@types/node": { - "version": "17.0.45", - "resolved": "https://registry.npmjs.org/@types/node/-/node-17.0.45.tgz", - "integrity": "sha512-w+tIMs3rq2afQdsPJlODhoUEKzFP1ayaoyl1CcnwtIlsVe7K7bA1NGm4s3PraqTLlXnbIN84zuBlxBWo1u9BLw==", - "license": "MIT" - }, - "node_modules/skin-tone": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/skin-tone/-/skin-tone-2.0.0.tgz", - "integrity": "sha512-kUMbT1oBJCpgrnKoSr0o6wPtvRWT9W9UKvGLwfJYO2WuahZRHOpEyL1ckyMGgMWh0UdpmaoFqKKD29WTomNEGA==", - "license": "MIT", - "dependencies": { - "unicode-emoji-modifier-base": "^1.0.0" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/slash": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/slash/-/slash-3.0.0.tgz", - "integrity": "sha512-g9Q1haeby36OSStwb4ntCGGGaKsaVSjQ68fBxoQcutl5fS1vuY18H3wSt3jFyFtrkx+Kz0V1G85A4MyAdDMi2Q==", - "license": "MIT", - "engines": { - "node": ">=8" - } - }, - "node_modules/slugify": { - "version": "1.6.6", - "resolved": "https://registry.npmjs.org/slugify/-/slugify-1.6.6.tgz", - "integrity": "sha512-h+z7HKHYXj6wJU+AnS/+IH8Uh9fdcX1Lrhg1/VMdf9PwoBQXFcXiAdsy2tSK0P6gKwJLXp02r90ahUCqHk9rrw==", - "license": "MIT", - "engines": { - "node": ">=8.0.0" - } - }, - "node_modules/snake-case": { - "version": "3.0.4", - "resolved": "https://registry.npmjs.org/snake-case/-/snake-case-3.0.4.tgz", - "integrity": "sha512-LAOh4z89bGQvl9pFfNF8V146i7o7/CqFPbqzYgP+yYzDIDeS9HaNFtXABamRW+AQzEVODcvE79ljJ+8a9YSdMg==", - "license": "MIT", - "dependencies": { - "dot-case": "^3.0.4", - "tslib": "^2.0.3" - } - }, - "node_modules/sockjs": { - "version": "0.3.24", - "resolved": "https://registry.npmjs.org/sockjs/-/sockjs-0.3.24.tgz", - "integrity": "sha512-GJgLTZ7vYb/JtPSSZ10hsOYIvEYsjbNU+zPdIHcUaWVNUEPivzxku31865sSSud0Da0W4lEeOPlmw93zLQchuQ==", - "license": "MIT", - "dependencies": { - "faye-websocket": "^0.11.3", - "uuid": "^8.3.2", - "websocket-driver": "^0.7.4" - } - }, - "node_modules/sort-css-media-queries": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/sort-css-media-queries/-/sort-css-media-queries-2.2.0.tgz", - "integrity": "sha512-0xtkGhWCC9MGt/EzgnvbbbKhqWjl1+/rncmhTh5qCpbYguXh6S/qwePfv/JQ8jePXXmqingylxoC49pCkSPIbA==", - "license": "MIT", - "engines": { - "node": ">= 6.3.0" - } - }, - "node_modules/source-map": { - "version": "0.7.4", - "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.7.4.tgz", - "integrity": "sha512-l3BikUxvPOcn5E74dZiq5BGsTb5yEwhaTSzccU6t4sDOH8NWJCstKO5QT2CvtFoK6F0saL7p9xHAqHOlCPJygA==", - "license": "BSD-3-Clause", - "engines": { - "node": ">= 8" - } - }, - "node_modules/source-map-js": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/source-map-js/-/source-map-js-1.2.1.tgz", - "integrity": "sha512-UXWMKhLOwVKb728IUtQPXxfYU+usdybtUrK/8uGE8CQMvrhOpwvzDBwj0QhSL7MQc7vIsISBG8VQ8+IDQxpfQA==", - "license": "BSD-3-Clause", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/source-map-support": { - "version": "0.5.21", - "resolved": "https://registry.npmjs.org/source-map-support/-/source-map-support-0.5.21.tgz", - "integrity": "sha512-uBHU3L3czsIyYXKX88fdrGovxdSCoTGDRZ6SYXtSRxLZUzHg5P/66Ht6uoUlHu9EZod+inXhKo3qQgwXUT/y1w==", - "license": "MIT", - "dependencies": { - "buffer-from": "^1.0.0", - "source-map": "^0.6.0" - } - }, - "node_modules/source-map-support/node_modules/source-map": { - "version": "0.6.1", - "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", - "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==", - "license": "BSD-3-Clause", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/space-separated-tokens": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/space-separated-tokens/-/space-separated-tokens-2.0.2.tgz", - "integrity": "sha512-PEGlAwrG8yXGXRjW32fGbg66JAlOAwbObuqVoJpv/mRgoWDQfgH1wDPvtzWyUSNAXBGSk8h755YDbbcEy3SH2Q==", - "license": "MIT", - "funding": { - "type": "github", - "url": "https://github.com/sponsors/wooorm" - } - }, - "node_modules/spawn-command": { - "version": "0.0.2", - "resolved": "https://registry.npmjs.org/spawn-command/-/spawn-command-0.0.2.tgz", - "integrity": "sha512-zC8zGoGkmc8J9ndvml8Xksr1Amk9qBujgbF0JAIWO7kXr43w0h/0GJNM/Vustixu+YE8N/MTrQ7N31FvHUACxQ==", - "dev": true - }, - "node_modules/spdy": { - "version": "4.0.2", - "resolved": "https://registry.npmjs.org/spdy/-/spdy-4.0.2.tgz", - "integrity": "sha512-r46gZQZQV+Kl9oItvl1JZZqJKGr+oEkB08A6BzkiR7593/7IbtuncXHd2YoYeTsG4157ZssMu9KYvUHLcjcDoA==", - "license": "MIT", - "dependencies": { - "debug": "^4.1.0", - "handle-thing": "^2.0.0", - "http-deceiver": "^1.2.7", - "select-hose": "^2.0.0", - "spdy-transport": "^3.0.0" - }, - "engines": { - "node": ">=6.0.0" - } - }, - "node_modules/spdy-transport": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/spdy-transport/-/spdy-transport-3.0.0.tgz", - "integrity": "sha512-hsLVFE5SjA6TCisWeJXFKniGGOpBgMLmerfO2aCyCU5s7nJ/rpAepqmFifv/GCbSbueEeAJJnmSQ2rKC/g8Fcw==", - "license": "MIT", - "dependencies": { - "debug": "^4.1.0", - "detect-node": "^2.0.4", - "hpack.js": "^2.1.6", - "obuf": "^1.1.2", - "readable-stream": "^3.0.6", - "wbuf": "^1.7.3" - } - }, - "node_modules/sprintf-js": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/sprintf-js/-/sprintf-js-1.0.3.tgz", - "integrity": "sha512-D9cPgkvLlV3t3IzL0D0YLvGA9Ahk4PcvVwUbN0dSGr1aP0Nrt4AEnTUbuGvquEC0mA64Gqt1fzirlRs5ibXx8g==", - "license": "BSD-3-Clause" - }, - "node_modules/srcset": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/srcset/-/srcset-4.0.0.tgz", - "integrity": "sha512-wvLeHgcVHKO8Sc/H/5lkGreJQVeYMm9rlmt8PuR1xE31rIuXhuzznUUqAt8MqLhB3MqJdFzlNAfpcWnxiFUcPw==", - "license": "MIT", - "engines": { - "node": ">=12" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/statuses": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/statuses/-/statuses-2.0.1.tgz", - "integrity": "sha512-RwNA9Z/7PrK06rYLIzFMlaF+l73iwpzsqRIFgbMLbTcLD6cOao82TaWefPXQvB2fOC4AjuYSEndS7N/mTCbkdQ==", - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/std-env": { - "version": "3.8.0", - "resolved": "https://registry.npmjs.org/std-env/-/std-env-3.8.0.tgz", - "integrity": "sha512-Bc3YwwCB+OzldMxOXJIIvC6cPRWr/LxOp48CdQTOkPyk/t4JWWJbrilwBd7RJzKV8QW7tJkcgAmeuLLJugl5/w==", - "license": "MIT" - }, - "node_modules/stream-browserify": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/stream-browserify/-/stream-browserify-3.0.0.tgz", - "integrity": "sha512-H73RAHsVBapbim0tU2JwwOiXUj+fikfiaoYAKHF3VJfA0pe2BCzkhAHBlLG6REzE+2WNZcxOXjK7lkso+9euLA==", - "license": "MIT", - "dependencies": { - "inherits": "~2.0.4", - "readable-stream": "^3.5.0" - } - }, - "node_modules/stream-http": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/stream-http/-/stream-http-3.2.0.tgz", - "integrity": "sha512-Oq1bLqisTyK3TSCXpPbT4sdeYNdmyZJv1LxpEm2vu1ZhK89kSE5YXwZc3cWk0MagGaKriBh9mCFbVGtO+vY29A==", - "license": "MIT", - "dependencies": { - "builtin-status-codes": "^3.0.0", - "inherits": "^2.0.4", - "readable-stream": "^3.6.0", - "xtend": "^4.0.2" - } - }, - "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==", - "license": "MIT", - "dependencies": { - "safe-buffer": "~5.2.0" - } - }, - "node_modules/string-width": { - "version": "5.1.2", - "resolved": "https://registry.npmjs.org/string-width/-/string-width-5.1.2.tgz", - "integrity": "sha512-HnLOCR3vjcY8beoNLtcjZ5/nxn2afmME6lhrDrebokqMap+XbeW8n9TXpPDOqdGK5qcI3oT0GKTW6wC7EMiVqA==", - "license": "MIT", - "dependencies": { - "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/string-width-cjs": { - "name": "string-width", - "version": "4.2.3", - "resolved": "https://registry.npmjs.org/string-width/-/string-width-4.2.3.tgz", - "integrity": "sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g==", - "license": "MIT", - "dependencies": { - "emoji-regex": "^8.0.0", - "is-fullwidth-code-point": "^3.0.0", - "strip-ansi": "^6.0.1" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/string-width-cjs/node_modules/emoji-regex": { - "version": "8.0.0", - "resolved": "https://registry.npmjs.org/emoji-regex/-/emoji-regex-8.0.0.tgz", - "integrity": "sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A==", - "license": "MIT" - }, - "node_modules/string-width/node_modules/ansi-regex": { - "version": "6.0.1", - "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-6.0.1.tgz", - "integrity": "sha512-n5M855fKb2SsfMIiFFoVrABHJC8QtHwVx+mHWP3QcEqBHYienj5dHSgjbxtC0WEZXYt4wcD6zrQElDPhFuZgfA==", - "license": "MIT", - "engines": { - "node": ">=12" - }, - "funding": { - "url": "https://github.com/chalk/ansi-regex?sponsor=1" - } - }, - "node_modules/string-width/node_modules/strip-ansi": { - "version": "7.1.0", - "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-7.1.0.tgz", - "integrity": "sha512-iq6eVVI64nQQTRYq2KtEg2d2uU7LElhTJwsH4YzIHZshxlgZms/wIc4VoDQTlG/IvVIrBKG06CrZnp0qv7hkcQ==", - "license": "MIT", - "dependencies": { - "ansi-regex": "^6.0.1" - }, - "engines": { - "node": ">=12" - }, - "funding": { - "url": "https://github.com/chalk/strip-ansi?sponsor=1" - } - }, - "node_modules/stringify-entities": { - "version": "4.0.4", - "resolved": "https://registry.npmjs.org/stringify-entities/-/stringify-entities-4.0.4.tgz", - "integrity": "sha512-IwfBptatlO+QCJUo19AqvrPNqlVMpW9YEL2LIVY+Rpv2qsjCGxaDLNRgeGsQWJhfItebuJhsGSLjaBbNSQ+ieg==", - "license": "MIT", - "dependencies": { - "character-entities-html4": "^2.0.0", - "character-entities-legacy": "^3.0.0" - }, - "funding": { - "type": "github", - "url": "https://github.com/sponsors/wooorm" - } - }, - "node_modules/stringify-object": { - "version": "3.3.0", - "resolved": "https://registry.npmjs.org/stringify-object/-/stringify-object-3.3.0.tgz", - "integrity": "sha512-rHqiFh1elqCQ9WPLIC8I0Q/g/wj5J1eMkyoiD6eoQApWHP0FtlK7rqnhmabL5VUY9JQCcqwwvlOaSuutekgyrw==", - "license": "BSD-2-Clause", - "dependencies": { - "get-own-enumerable-property-symbols": "^3.0.0", - "is-obj": "^1.0.1", - "is-regexp": "^1.0.0" - }, - "engines": { - "node": ">=4" - } - }, - "node_modules/strip-ansi": { - "version": "6.0.1", - "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-6.0.1.tgz", - "integrity": "sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A==", - "license": "MIT", - "dependencies": { - "ansi-regex": "^5.0.1" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/strip-ansi-cjs": { - "name": "strip-ansi", - "version": "6.0.1", - "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-6.0.1.tgz", - "integrity": "sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A==", - "license": "MIT", - "dependencies": { - "ansi-regex": "^5.0.1" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/strip-bom-string": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/strip-bom-string/-/strip-bom-string-1.0.0.tgz", - "integrity": "sha512-uCC2VHvQRYu+lMh4My/sFNmF2klFymLX1wHJeXnbEJERpV/ZsVuonzerjfrGpIGF7LBVa1O7i9kjiWvJiFck8g==", - "license": "MIT", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/strip-final-newline": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/strip-final-newline/-/strip-final-newline-2.0.0.tgz", - "integrity": "sha512-BrpvfNAE3dcvq7ll3xVumzjKjZQ5tI1sEUIKr3Uoks0XUl45St3FlatVqef9prk4jRDzhW6WZg+3bk93y6pLjA==", - "license": "MIT", - "engines": { - "node": ">=6" - } - }, - "node_modules/strip-json-comments": { - "version": "3.1.1", - "resolved": "https://registry.npmjs.org/strip-json-comments/-/strip-json-comments-3.1.1.tgz", - "integrity": "sha512-6fPc+R4ihwqP6N/aIv2f1gMH8lOVtWQHoqC4yK6oSDVVocumAsfCqjkXnqiYMhmMwS/mEHLp7Vehlt3ql6lEig==", - "license": "MIT", - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/style-to-object": { - "version": "0.4.4", - "resolved": "https://registry.npmjs.org/style-to-object/-/style-to-object-0.4.4.tgz", - "integrity": "sha512-HYNoHZa2GorYNyqiCaBgsxvcJIn7OHq6inEga+E6Ke3m5JkoqpQbnFssk4jwe+K7AhGa2fcha4wSOf1Kn01dMg==", - "license": "MIT", - "dependencies": { - "inline-style-parser": "0.1.1" - } - }, - "node_modules/stylehacks": { - "version": "6.1.1", - "resolved": "https://registry.npmjs.org/stylehacks/-/stylehacks-6.1.1.tgz", - "integrity": "sha512-gSTTEQ670cJNoaeIp9KX6lZmm8LJ3jPB5yJmX8Zq/wQxOsAFXV3qjWzHas3YYk1qesuVIyYWWUpZ0vSE/dTSGg==", - "license": "MIT", - "dependencies": { - "browserslist": "^4.23.0", - "postcss-selector-parser": "^6.0.16" - }, - "engines": { - "node": "^14 || ^16 || >=18.0" - }, - "peerDependencies": { - "postcss": "^8.4.31" - } - }, - "node_modules/sucrase": { - "version": "3.35.0", - "resolved": "https://registry.npmjs.org/sucrase/-/sucrase-3.35.0.tgz", - "integrity": "sha512-8EbVDiu9iN/nESwxeSxDKe0dunta1GOlHufmSSXxMD2z2/tMZpDMpvXQGsc+ajGo8y2uYUmixaSRUc/QPoQ0GA==", - "license": "MIT", - "dependencies": { - "@jridgewell/gen-mapping": "^0.3.2", - "commander": "^4.0.0", - "glob": "^10.3.10", - "lines-and-columns": "^1.1.6", - "mz": "^2.7.0", - "pirates": "^4.0.1", - "ts-interface-checker": "^0.1.9" - }, - "bin": { - "sucrase": "bin/sucrase", - "sucrase-node": "bin/sucrase-node" - }, - "engines": { - "node": ">=16 || 14 >=14.17" - } - }, - "node_modules/sucrase/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==", - "license": "MIT", - "dependencies": { - "balanced-match": "^1.0.0" - } - }, - "node_modules/sucrase/node_modules/commander": { - "version": "4.1.1", - "resolved": "https://registry.npmjs.org/commander/-/commander-4.1.1.tgz", - "integrity": "sha512-NOKm8xhkzAjzFx8B2v5OAHT+u5pRQc2UCa2Vq9jYL/31o2wi9mxBA7LIFs3sV5VSC49z6pEhfbMULvShKj26WA==", - "license": "MIT", - "engines": { - "node": ">= 6" - } - }, - "node_modules/sucrase/node_modules/glob": { - "version": "10.4.5", - "resolved": "https://registry.npmjs.org/glob/-/glob-10.4.5.tgz", - "integrity": "sha512-7Bv8RF0k6xjo7d4A/PxYLbUCfb6c+Vpd2/mB2yRDlew7Jb5hEXiCD9ibfO7wpk8i4sevK6DFny9h7EYbM3/sHg==", - "license": "ISC", - "dependencies": { - "foreground-child": "^3.1.0", - "jackspeak": "^3.1.2", - "minimatch": "^9.0.4", - "minipass": "^7.1.2", - "package-json-from-dist": "^1.0.0", - "path-scurry": "^1.11.1" - }, - "bin": { - "glob": "dist/esm/bin.mjs" - }, - "funding": { - "url": "https://github.com/sponsors/isaacs" - } - }, - "node_modules/sucrase/node_modules/minimatch": { - "version": "9.0.5", - "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-9.0.5.tgz", - "integrity": "sha512-G6T0ZX48xgozx7587koeX9Ys2NYy6Gmv//P89sEte9V9whIapMNF4idKxnW2QtCcLiTWlb/wfCabAtAFWhhBow==", - "license": "ISC", - "dependencies": { - "brace-expansion": "^2.0.1" - }, - "engines": { - "node": ">=16 || 14 >=14.17" - }, - "funding": { - "url": "https://github.com/sponsors/isaacs" - } - }, - "node_modules/supports-color": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", - "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", - "license": "MIT", - "dependencies": { - "has-flag": "^4.0.0" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/supports-preserve-symlinks-flag": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/supports-preserve-symlinks-flag/-/supports-preserve-symlinks-flag-1.0.0.tgz", - "integrity": "sha512-ot0WnXS9fgdkgIcePe6RHNk1WA8+muPa6cSjeR3V8K27q9BB1rTE3R1p7Hv0z1ZyAc8s6Vvv8DIyWf681MAt0w==", - "license": "MIT", - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/svg-parser": { - "version": "2.0.4", - "resolved": "https://registry.npmjs.org/svg-parser/-/svg-parser-2.0.4.tgz", - "integrity": "sha512-e4hG1hRwoOdRb37cIMSgzNsxyzKfayW6VOflrwvR+/bzrkyxY/31WkbgnQpgtrNp1SdpJvpUAGTa/ZoiPNDuRQ==", - "license": "MIT" - }, - "node_modules/svgo": { - "version": "3.3.2", - "resolved": "https://registry.npmjs.org/svgo/-/svgo-3.3.2.tgz", - "integrity": "sha512-OoohrmuUlBs8B8o6MB2Aevn+pRIH9zDALSR+6hhqVfa6fRwG/Qw9VUMSMW9VNg2CFc/MTIfabtdOVl9ODIJjpw==", - "license": "MIT", - "dependencies": { - "@trysound/sax": "0.2.0", - "commander": "^7.2.0", - "css-select": "^5.1.0", - "css-tree": "^2.3.1", - "css-what": "^6.1.0", - "csso": "^5.0.5", - "picocolors": "^1.0.0" - }, - "bin": { - "svgo": "bin/svgo" - }, - "engines": { - "node": ">=14.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/svgo" - } - }, - "node_modules/svgo/node_modules/commander": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/commander/-/commander-7.2.0.tgz", - "integrity": "sha512-QrWXB+ZQSVPmIWIhtEO9H+gwHaMGYiF5ChvoJ+K9ZGHG/sVsa6yiesAD1GC/x46sET00Xlwo1u49RVVVzvcSkw==", - "license": "MIT", - "engines": { - "node": ">= 10" - } - }, - "node_modules/swagger2openapi": { - "version": "7.0.8", - "resolved": "https://registry.npmjs.org/swagger2openapi/-/swagger2openapi-7.0.8.tgz", - "integrity": "sha512-upi/0ZGkYgEcLeGieoz8gT74oWHA0E7JivX7aN9mAf+Tc7BQoRBvnIGHoPDw+f9TXTW4s6kGYCZJtauP6OYp7g==", - "license": "BSD-3-Clause", - "dependencies": { - "call-me-maybe": "^1.0.1", - "node-fetch": "^2.6.1", - "node-fetch-h2": "^2.3.0", - "node-readfiles": "^0.2.0", - "oas-kit-common": "^1.0.8", - "oas-resolver": "^2.5.6", - "oas-schema-walker": "^1.1.5", - "oas-validator": "^5.0.8", - "reftools": "^1.1.9", - "yaml": "^1.10.0", - "yargs": "^17.0.1" - }, - "bin": { - "boast": "boast.js", - "oas-validate": "oas-validate.js", - "swagger2openapi": "swagger2openapi.js" - }, - "funding": { - "url": "https://github.com/Mermade/oas-kit?sponsor=1" - } - }, - "node_modules/tapable": { - "version": "2.2.1", - "resolved": "https://registry.npmjs.org/tapable/-/tapable-2.2.1.tgz", - "integrity": "sha512-GNzQvQTOIP6RyTfE2Qxb8ZVlNmw0n88vp1szwWRimP02mnTsx3Wtn5qRdqY9w2XduFNUgvOwhNnQsjwCp+kqaQ==", - "license": "MIT", - "engines": { - "node": ">=6" - } - }, - "node_modules/terser": { - "version": "5.31.3", - "resolved": "https://registry.npmjs.org/terser/-/terser-5.31.3.tgz", - "integrity": "sha512-pAfYn3NIZLyZpa83ZKigvj6Rn9c/vd5KfYGX7cN1mnzqgDcxWvrU5ZtAfIKhEXz9nRecw4z3LXkjaq96/qZqAA==", - "license": "BSD-2-Clause", - "dependencies": { - "@jridgewell/source-map": "^0.3.3", - "acorn": "^8.8.2", - "commander": "^2.20.0", - "source-map-support": "~0.5.20" - }, - "bin": { - "terser": "bin/terser" - }, - "engines": { - "node": ">=10" - } - }, - "node_modules/terser-webpack-plugin": { - "version": "5.3.10", - "resolved": "https://registry.npmjs.org/terser-webpack-plugin/-/terser-webpack-plugin-5.3.10.tgz", - "integrity": "sha512-BKFPWlPDndPs+NGGCr1U59t0XScL5317Y0UReNrHaw9/FwhPENlq6bfgs+4yPfyP51vqC1bQ4rp1EfXW5ZSH9w==", - "license": "MIT", - "dependencies": { - "@jridgewell/trace-mapping": "^0.3.20", - "jest-worker": "^27.4.5", - "schema-utils": "^3.1.1", - "serialize-javascript": "^6.0.1", - "terser": "^5.26.0" - }, - "engines": { - "node": ">= 10.13.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/webpack" - }, - "peerDependencies": { - "webpack": "^5.1.0" - }, - "peerDependenciesMeta": { - "@swc/core": { - "optional": true - }, - "esbuild": { - "optional": true - }, - "uglify-js": { - "optional": true - } - } - }, - "node_modules/terser-webpack-plugin/node_modules/ajv": { - "version": "6.12.6", - "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz", - "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==", - "license": "MIT", - "dependencies": { - "fast-deep-equal": "^3.1.1", - "fast-json-stable-stringify": "^2.0.0", - "json-schema-traverse": "^0.4.1", - "uri-js": "^4.2.2" - }, - "funding": { - "type": "github", - "url": "https://github.com/sponsors/epoberezkin" - } - }, - "node_modules/terser-webpack-plugin/node_modules/ajv-keywords": { - "version": "3.5.2", - "resolved": "https://registry.npmjs.org/ajv-keywords/-/ajv-keywords-3.5.2.tgz", - "integrity": "sha512-5p6WTN0DdTGVQk6VjcEju19IgaHudalcfabD7yhDGeA6bcQnmL+CpveLJq/3hvfwd1aof6L386Ougkx6RfyMIQ==", - "license": "MIT", - "peerDependencies": { - "ajv": "^6.9.1" - } - }, - "node_modules/terser-webpack-plugin/node_modules/jest-worker": { - "version": "27.5.1", - "resolved": "https://registry.npmjs.org/jest-worker/-/jest-worker-27.5.1.tgz", - "integrity": "sha512-7vuh85V5cdDofPyxn58nrPjBktZo0u9x1g8WtjQol+jZDaE+fhN+cIvTj11GndBnMnyfrUOG1sZQxCdjKh+DKg==", - "license": "MIT", - "dependencies": { - "@types/node": "*", - "merge-stream": "^2.0.0", - "supports-color": "^8.0.0" - }, - "engines": { - "node": ">= 10.13.0" - } - }, - "node_modules/terser-webpack-plugin/node_modules/json-schema-traverse": { - "version": "0.4.1", - "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz", - "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==", - "license": "MIT" - }, - "node_modules/terser-webpack-plugin/node_modules/schema-utils": { - "version": "3.3.0", - "resolved": "https://registry.npmjs.org/schema-utils/-/schema-utils-3.3.0.tgz", - "integrity": "sha512-pN/yOAvcC+5rQ5nERGuwrjLlYvLTbCibnZ1I7B1LaiAz9BRBlE9GMgE/eqV30P7aJQUf7Ddimy/RsbYO/GrVGg==", - "license": "MIT", - "dependencies": { - "@types/json-schema": "^7.0.8", - "ajv": "^6.12.5", - "ajv-keywords": "^3.5.2" - }, - "engines": { - "node": ">= 10.13.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/webpack" - } - }, - "node_modules/terser-webpack-plugin/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==", - "license": "MIT", - "dependencies": { - "has-flag": "^4.0.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/chalk/supports-color?sponsor=1" - } - }, - "node_modules/terser/node_modules/commander": { - "version": "2.20.3", - "resolved": "https://registry.npmjs.org/commander/-/commander-2.20.3.tgz", - "integrity": "sha512-GpVkmM8vF2vQUkj2LvZmD35JxeJOLCwJ9cUkugyk2nuhbv3+mJvpLYYt+0+USMxE+oj+ey/lJEnhZw75x/OMcQ==", - "license": "MIT" - }, - "node_modules/text-table": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/text-table/-/text-table-0.2.0.tgz", - "integrity": "sha512-N+8UisAXDGk8PFXP4HAzVR9nbfmVJ3zYLAWiTIoqC5v5isinhr+r5uaO8+7r3BMfuNIufIsA7RdpVgacC2cSpw==", - "license": "MIT" - }, - "node_modules/thenify": { - "version": "3.3.1", - "resolved": "https://registry.npmjs.org/thenify/-/thenify-3.3.1.tgz", - "integrity": "sha512-RVZSIV5IG10Hk3enotrhvz0T9em6cyHBLkH/YAZuKqd8hRkKhSfCGIcP2KUY0EPxndzANBmNllzWPwak+bheSw==", - "license": "MIT", - "dependencies": { - "any-promise": "^1.0.0" - } - }, - "node_modules/thenify-all": { - "version": "1.6.0", - "resolved": "https://registry.npmjs.org/thenify-all/-/thenify-all-1.6.0.tgz", - "integrity": "sha512-RNxQH/qI8/t3thXJDwcstUO4zeqo64+Uy/+sNVRBx4Xn2OX+OZ9oP+iJnNFqplFra2ZUVeKCSa2oVWi3T4uVmA==", - "license": "MIT", - "dependencies": { - "thenify": ">= 3.1.0 < 4" - }, - "engines": { - "node": ">=0.8" - } - }, - "node_modules/thunky": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/thunky/-/thunky-1.1.0.tgz", - "integrity": "sha512-eHY7nBftgThBqOyHGVN+l8gF0BucP09fMo0oO/Lb0w1OF80dJv+lDVpXG60WMQvkcxAkNybKsrEIE3ZtKGmPrA==", - "license": "MIT" - }, - "node_modules/timers-browserify": { - "version": "2.0.12", - "resolved": "https://registry.npmjs.org/timers-browserify/-/timers-browserify-2.0.12.tgz", - "integrity": "sha512-9phl76Cqm6FhSX9Xe1ZUAMLtm1BLkKj2Qd5ApyWkXzsMRaA7dgr81kf4wJmQf/hAvg8EEyJxDo3du/0KlhPiKQ==", - "license": "MIT", - "dependencies": { - "setimmediate": "^1.0.4" - }, - "engines": { - "node": ">=0.6.0" - } - }, - "node_modules/tiny-invariant": { - "version": "1.3.3", - "resolved": "https://registry.npmjs.org/tiny-invariant/-/tiny-invariant-1.3.3.tgz", - "integrity": "sha512-+FbBPE1o9QAYvviau/qC5SE3caw21q3xkvWKBtja5vgqOWIHHJ3ioaq1VPfn/Szqctz2bU/oYeKd9/z5BL+PVg==", - "license": "MIT" - }, - "node_modules/tiny-warning": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/tiny-warning/-/tiny-warning-1.0.3.tgz", - "integrity": "sha512-lBN9zLN/oAf68o3zNXYrdCt1kP8WsiGW8Oo2ka41b2IM5JL/S1CTyX1rW0mb/zSuJun0ZUrDxx4sqvYS2FWzPA==", - "license": "MIT" - }, - "node_modules/to-regex-range": { - "version": "5.0.1", - "resolved": "https://registry.npmjs.org/to-regex-range/-/to-regex-range-5.0.1.tgz", - "integrity": "sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ==", - "license": "MIT", - "dependencies": { - "is-number": "^7.0.0" - }, - "engines": { - "node": ">=8.0" - } - }, - "node_modules/toidentifier": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/toidentifier/-/toidentifier-1.0.1.tgz", - "integrity": "sha512-o5sSPKEkg/DIQNmH43V0/uerLrpzVedkUh8tGNvaeXpfpuwjKenlSox/2O/BTlZUtEe+JG7s5YhEz608PlAHRA==", - "engines": { - "node": ">=0.6" - } - }, - "node_modules/totalist": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/totalist/-/totalist-3.0.1.tgz", - "integrity": "sha512-sf4i37nQ2LBx4m3wB74y+ubopq6W/dIzXg0FDGjsYnZHVa1Da8FH853wlL2gtUhg+xJXjfk3kUZS3BRoQeoQBQ==", - "license": "MIT", - "engines": { - "node": ">=6" - } - }, - "node_modules/touch": { - "version": "3.1.1", - "resolved": "https://registry.npmjs.org/touch/-/touch-3.1.1.tgz", - "integrity": "sha512-r0eojU4bI8MnHr8c5bNo7lJDdI2qXlWWJk6a9EAFG7vbhTjElYhBVS3/miuE0uOuoLdb8Mc/rVfsmm6eo5o9GA==", - "dev": true, - "license": "ISC", - "bin": { - "nodetouch": "bin/nodetouch.js" - } - }, - "node_modules/tr46": { - "version": "0.0.3", - "resolved": "https://registry.npmjs.org/tr46/-/tr46-0.0.3.tgz", - "integrity": "sha512-N3WMsuqV66lT30CrXNbEjx4GEwlow3v6rr4mCcv6prnfwhS01rkgyFdjPNBYd9br7LpXV1+Emh01fHnq2Gdgrw==", - "license": "MIT" - }, - "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": { - "tree-kill": "cli.js" - } - }, - "node_modules/trim-lines": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/trim-lines/-/trim-lines-3.0.1.tgz", - "integrity": "sha512-kRj8B+YHZCc9kQYdWfJB2/oUl9rA99qbowYYBtr4ui4mZyAQ2JpvVBd/6U2YloATfqBhBTSMhTpgBHtU0Mf3Rg==", - "license": "MIT", - "funding": { - "type": "github", - "url": "https://github.com/sponsors/wooorm" - } - }, - "node_modules/trough": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/trough/-/trough-2.2.0.tgz", - "integrity": "sha512-tmMpK00BjZiUyVyvrBK7knerNgmgvcV/KLVyuma/SC+TQN167GrMRciANTz09+k3zW8L8t60jWO1GpfkZdjTaw==", - "license": "MIT", - "funding": { - "type": "github", - "url": "https://github.com/sponsors/wooorm" - } - }, - "node_modules/ts-interface-checker": { - "version": "0.1.13", - "resolved": "https://registry.npmjs.org/ts-interface-checker/-/ts-interface-checker-0.1.13.tgz", - "integrity": "sha512-Y/arvbn+rrz3JCKl9C4kVNfTfSm2/mEp5FSz5EsZSANGPSlQrpRI5M4PKF+mJnE52jOO90PnPSc3Ur3bTQw0gA==", - "license": "Apache-2.0" - }, - "node_modules/tslib": { - "version": "2.6.3", - "resolved": "https://registry.npmjs.org/tslib/-/tslib-2.6.3.tgz", - "integrity": "sha512-xNvxJEOUiWPGhUuUdQgAJPKOOJfGnIyKySOc09XkKsgdUV/3E2zvwZYdejjmRgPCgcym1juLH3226yA7sEFJKQ==", - "license": "0BSD" - }, - "node_modules/tty-browserify": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/tty-browserify/-/tty-browserify-0.0.1.tgz", - "integrity": "sha512-C3TaO7K81YvjCgQH9Q1S3R3P3BtN3RIM8n+OvX4il1K1zgE8ZhI0op7kClgkxtutIE8hQrcrHBXvIheqKUUCxw==", - "license": "MIT" - }, - "node_modules/type-fest": { - "version": "2.19.0", - "resolved": "https://registry.npmjs.org/type-fest/-/type-fest-2.19.0.tgz", - "integrity": "sha512-RAH822pAdBgcNMAfWnCBU3CFZcfZ/i1eZjwFU/dsLKumyuuP3niueg2UAukXYF0E2AAoc82ZSSf9J0WQBinzHA==", - "license": "(MIT OR CC0-1.0)", - "engines": { - "node": ">=12.20" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/type-is": { - "version": "1.6.18", - "resolved": "https://registry.npmjs.org/type-is/-/type-is-1.6.18.tgz", - "integrity": "sha512-TkRKr9sUTxEH8MdfuCSP7VizJyzRNMjj2J2do2Jr3Kym598JVdEksuzPQCnlFPW4ky9Q+iA+ma9BGm06XQBy8g==", - "dependencies": { - "media-typer": "0.3.0", - "mime-types": "~2.1.24" - }, - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/type-is/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==", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/type-is/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==", - "dependencies": { - "mime-db": "1.52.0" - }, - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/typedarray-to-buffer": { - "version": "3.1.5", - "resolved": "https://registry.npmjs.org/typedarray-to-buffer/-/typedarray-to-buffer-3.1.5.tgz", - "integrity": "sha512-zdu8XMNEDepKKR+XYOXAVPtWui0ly0NtohUscw+UmaHiAWT8hrV1rr//H6V+0DvJ3OQ19S979M0laLfX8rm82Q==", - "license": "MIT", - "dependencies": { - "is-typedarray": "^1.0.0" - } - }, - "node_modules/typescript": { - "version": "5.2.2", - "resolved": "https://registry.npmjs.org/typescript/-/typescript-5.2.2.tgz", - "integrity": "sha512-mI4WrpHsbCIcwT9cF4FZvr80QUeKvsUsUvKDoR+X/7XHQH98xYD8YHZg7ANtz2GtZt/CBq2QJ0thkGJMHfqc1w==", - "license": "Apache-2.0", - "bin": { - "tsc": "bin/tsc", - "tsserver": "bin/tsserver" - }, - "engines": { - "node": ">=14.17" - } - }, - "node_modules/undefsafe": { - "version": "2.0.5", - "resolved": "https://registry.npmjs.org/undefsafe/-/undefsafe-2.0.5.tgz", - "integrity": "sha512-WxONCrssBM8TSPRqN5EmsjVrsv4A8X12J4ArBiiayv3DyyG3ZlIg6yysuuSYdZsVz3TKcTg2fd//Ujd4CHV1iA==", - "dev": true, - "license": "MIT" - }, - "node_modules/undici": { - "version": "6.21.1", - "resolved": "https://registry.npmjs.org/undici/-/undici-6.21.1.tgz", - "integrity": "sha512-q/1rj5D0/zayJB2FraXdaWxbhWiNKDvu8naDT2dl1yTlvJp4BLtOcp2a5BvgGNQpYYJzau7tf1WgKv3b+7mqpQ==", - "license": "MIT", - "engines": { - "node": ">=18.17" - } - }, - "node_modules/undici-types": { - "version": "6.13.0", - "resolved": "https://registry.npmjs.org/undici-types/-/undici-types-6.13.0.tgz", - "integrity": "sha512-xtFJHudx8S2DSoujjMd1WeWvn7KKWFRESZTMeL1RptAYERu29D6jphMjjY+vn96jvN3kVPDNxU/E13VTaXj6jg==", - "license": "MIT" - }, - "node_modules/unfetch": { - "version": "4.2.0", - "resolved": "https://registry.npmjs.org/unfetch/-/unfetch-4.2.0.tgz", - "integrity": "sha512-F9p7yYCn6cIW9El1zi0HI6vqpeIvBsr3dSuRO6Xuppb1u5rXpCPmMvLSyECLhybr9isec8Ohl0hPekMVrEinDA==", - "license": "MIT" - }, - "node_modules/unicode-canonical-property-names-ecmascript": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/unicode-canonical-property-names-ecmascript/-/unicode-canonical-property-names-ecmascript-2.0.1.tgz", - "integrity": "sha512-dA8WbNeb2a6oQzAQ55YlT5vQAWGV9WXOsi3SskE3bcCdM0P4SDd+24zS/OCacdRq5BkdsRj9q3Pg6YyQoxIGqg==", - "license": "MIT", - "engines": { - "node": ">=4" - } - }, - "node_modules/unicode-emoji-modifier-base": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/unicode-emoji-modifier-base/-/unicode-emoji-modifier-base-1.0.0.tgz", - "integrity": "sha512-yLSH4py7oFH3oG/9K+XWrz1pSi3dfUrWEnInbxMfArOfc1+33BlGPQtLsOYwvdMy11AwUBetYuaRxSPqgkq+8g==", - "license": "MIT", - "engines": { - "node": ">=4" - } - }, - "node_modules/unicode-match-property-ecmascript": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/unicode-match-property-ecmascript/-/unicode-match-property-ecmascript-2.0.0.tgz", - "integrity": "sha512-5kaZCrbp5mmbz5ulBkDkbY0SsPOjKqVS35VpL9ulMPfSl0J0Xsm+9Evphv9CoIZFwre7aJoa94AY6seMKGVN5Q==", - "license": "MIT", - "dependencies": { - "unicode-canonical-property-names-ecmascript": "^2.0.0", - "unicode-property-aliases-ecmascript": "^2.0.0" - }, - "engines": { - "node": ">=4" - } - }, - "node_modules/unicode-match-property-value-ecmascript": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/unicode-match-property-value-ecmascript/-/unicode-match-property-value-ecmascript-2.2.0.tgz", - "integrity": "sha512-4IehN3V/+kkr5YeSSDDQG8QLqO26XpL2XP3GQtqwlT/QYSECAwFztxVHjlbh0+gjJ3XmNLS0zDsbgs9jWKExLg==", - "license": "MIT", - "engines": { - "node": ">=4" - } - }, - "node_modules/unicode-property-aliases-ecmascript": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/unicode-property-aliases-ecmascript/-/unicode-property-aliases-ecmascript-2.1.0.tgz", - "integrity": "sha512-6t3foTQI9qne+OZoVQB/8x8rk2k1eVy1gRXhV3oFQ5T6R1dqQ1xtin3XqSlx3+ATBkliTaR/hHyJBm+LVPNM8w==", - "license": "MIT", - "engines": { - "node": ">=4" - } - }, - "node_modules/unified": { - "version": "11.0.5", - "resolved": "https://registry.npmjs.org/unified/-/unified-11.0.5.tgz", - "integrity": "sha512-xKvGhPWw3k84Qjh8bI3ZeJjqnyadK+GEFtazSfZv/rKeTkTjOJho6mFqh2SM96iIcZokxiOpg78GazTSg8+KHA==", - "license": "MIT", - "dependencies": { - "@types/unist": "^3.0.0", - "bail": "^2.0.0", - "devlop": "^1.0.0", - "extend": "^3.0.0", - "is-plain-obj": "^4.0.0", - "trough": "^2.0.0", - "vfile": "^6.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/unique-string": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/unique-string/-/unique-string-3.0.0.tgz", - "integrity": "sha512-VGXBUVwxKMBUznyffQweQABPRRW1vHZAbadFZud4pLFAqRGvv/96vafgjWFqzourzr8YonlQiPgH0YCJfawoGQ==", - "license": "MIT", - "dependencies": { - "crypto-random-string": "^4.0.0" - }, - "engines": { - "node": ">=12" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/unist-util-generated": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/unist-util-generated/-/unist-util-generated-2.0.1.tgz", - "integrity": "sha512-qF72kLmPxAw0oN2fwpWIqbXAVyEqUzDHMsbtPvOudIlUzXYFIeQIuxXQCRCFh22B7cixvU0MG7m3MW8FTq/S+A==", - "license": "MIT", - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/unist-util-is": { - "version": "6.0.0", - "resolved": "https://registry.npmjs.org/unist-util-is/-/unist-util-is-6.0.0.tgz", - "integrity": "sha512-2qCTHimwdxLfz+YzdGfkqNlH0tLi9xjTnHddPmJwtIG9MGsdbutfTc4P+haPD7l7Cjxf/WZj+we5qfVPvvxfYw==", - "license": "MIT", - "dependencies": { - "@types/unist": "^3.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/unist-util-position": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/unist-util-position/-/unist-util-position-5.0.0.tgz", - "integrity": "sha512-fucsC7HjXvkB5R3kTCO7kUjRdrS0BJt3M/FPxmHMBOm8JQi2BsHAHFsy27E0EolP8rp0NzXsJ+jNPyDWvOJZPA==", - "license": "MIT", - "dependencies": { - "@types/unist": "^3.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/unist-util-position-from-estree": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/unist-util-position-from-estree/-/unist-util-position-from-estree-2.0.0.tgz", - "integrity": "sha512-KaFVRjoqLyF6YXCbVLNad/eS4+OfPQQn2yOd7zF/h5T/CSL2v8NpN6a5TPvtbXthAGw5nG+PuTtq+DdIZr+cRQ==", - "license": "MIT", - "dependencies": { - "@types/unist": "^3.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/unist-util-remove-position": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/unist-util-remove-position/-/unist-util-remove-position-5.0.0.tgz", - "integrity": "sha512-Hp5Kh3wLxv0PHj9m2yZhhLt58KzPtEYKQQ4yxfYFEO7EvHwzyDYnduhHnY1mDxoqr7VUwVuHXk9RXKIiYS1N8Q==", - "license": "MIT", - "dependencies": { - "@types/unist": "^3.0.0", - "unist-util-visit": "^5.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/unist-util-stringify-position": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/unist-util-stringify-position/-/unist-util-stringify-position-4.0.0.tgz", - "integrity": "sha512-0ASV06AAoKCDkS2+xw5RXJywruurpbC4JZSm7nr7MOt1ojAzvyyaO+UxZf18j8FCF6kmzCZKcAgN/yu2gm2XgQ==", - "license": "MIT", - "dependencies": { - "@types/unist": "^3.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/unist-util-visit": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/unist-util-visit/-/unist-util-visit-5.0.0.tgz", - "integrity": "sha512-MR04uvD+07cwl/yhVuVWAtw+3GOR/knlL55Nd/wAdblk27GCVt3lqpTivy/tkJcZoNPzTwS1Y+KMojlLDhoTzg==", - "license": "MIT", - "dependencies": { - "@types/unist": "^3.0.0", - "unist-util-is": "^6.0.0", - "unist-util-visit-parents": "^6.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/unist-util-visit-parents": { - "version": "6.0.1", - "resolved": "https://registry.npmjs.org/unist-util-visit-parents/-/unist-util-visit-parents-6.0.1.tgz", - "integrity": "sha512-L/PqWzfTP9lzzEa6CKs0k2nARxTdZduw3zyh8d2NVBnsyvHjSX4TWse388YrrQKbvI8w20fGjGlhgT96WwKykw==", - "license": "MIT", - "dependencies": { - "@types/unist": "^3.0.0", - "unist-util-is": "^6.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/universalify": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/universalify/-/universalify-2.0.1.tgz", - "integrity": "sha512-gptHNQghINnc/vTGIk0SOFGFNXw7JVrlRUtConJRlvaw6DuX0wO5Jeko9sWrMBhh+PsYAZ7oXAiOnf/UKogyiw==", - "license": "MIT", - "engines": { - "node": ">= 10.0.0" - } - }, - "node_modules/unpipe": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/unpipe/-/unpipe-1.0.0.tgz", - "integrity": "sha512-pjy2bYhSsufwWlKwPc+l3cN7+wuJlK6uz0YdJEOlQDbl6jo/YlPi4mb8agUkVC8BF7V8NuzeyPNqRksA3hztKQ==", - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/update-browserslist-db": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/update-browserslist-db/-/update-browserslist-db-1.1.1.tgz", - "integrity": "sha512-R8UzCaa9Az+38REPiJ1tXlImTJXlVfgHZsglwBD/k6nj76ctsH1E3q4doGrukiLQd3sGQYu56r5+lo5r94l29A==", - "funding": [ - { - "type": "opencollective", - "url": "https://opencollective.com/browserslist" - }, - { - "type": "tidelift", - "url": "https://tidelift.com/funding/github/npm/browserslist" - }, - { - "type": "github", - "url": "https://github.com/sponsors/ai" - } - ], - "license": "MIT", - "dependencies": { - "escalade": "^3.2.0", - "picocolors": "^1.1.0" - }, - "bin": { - "update-browserslist-db": "cli.js" - }, - "peerDependencies": { - "browserslist": ">= 4.21.0" - } - }, - "node_modules/update-notifier": { - "version": "6.0.2", - "resolved": "https://registry.npmjs.org/update-notifier/-/update-notifier-6.0.2.tgz", - "integrity": "sha512-EDxhTEVPZZRLWYcJ4ZXjGFN0oP7qYvbXWzEgRm/Yql4dHX5wDbvh89YHP6PK1lzZJYrMtXUuZZz8XGK+U6U1og==", - "license": "BSD-2-Clause", - "dependencies": { - "boxen": "^7.0.0", - "chalk": "^5.0.1", - "configstore": "^6.0.0", - "has-yarn": "^3.0.0", - "import-lazy": "^4.0.0", - "is-ci": "^3.0.1", - "is-installed-globally": "^0.4.0", - "is-npm": "^6.0.0", - "is-yarn-global": "^0.4.0", - "latest-version": "^7.0.0", - "pupa": "^3.1.0", - "semver": "^7.3.7", - "semver-diff": "^4.0.0", - "xdg-basedir": "^5.1.0" - }, - "engines": { - "node": ">=14.16" - }, - "funding": { - "url": "https://github.com/yeoman/update-notifier?sponsor=1" - } - }, - "node_modules/update-notifier/node_modules/boxen": { - "version": "7.1.1", - "resolved": "https://registry.npmjs.org/boxen/-/boxen-7.1.1.tgz", - "integrity": "sha512-2hCgjEmP8YLWQ130n2FerGv7rYpfBmnmp9Uy2Le1vge6X3gZIfSmEzP5QTDElFxcvVcXlEn8Aq6MU/PZygIOog==", - "license": "MIT", - "dependencies": { - "ansi-align": "^3.0.1", - "camelcase": "^7.0.1", - "chalk": "^5.2.0", - "cli-boxes": "^3.0.0", - "string-width": "^5.1.2", - "type-fest": "^2.13.0", - "widest-line": "^4.0.1", - "wrap-ansi": "^8.1.0" - }, - "engines": { - "node": ">=14.16" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/update-notifier/node_modules/camelcase": { - "version": "7.0.1", - "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-7.0.1.tgz", - "integrity": "sha512-xlx1yCK2Oc1APsPXDL2LdlNP6+uu8OCDdhOBSVT279M/S+y75O30C2VuD8T2ogdePBBl7PfPF4504tnLgX3zfw==", - "license": "MIT", - "engines": { - "node": ">=14.16" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/update-notifier/node_modules/chalk": { - "version": "5.3.0", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-5.3.0.tgz", - "integrity": "sha512-dLitG79d+GV1Nb/VYcCDFivJeK1hiukt9QjRNVOsUtTy1rR1YJsmpGGTZ3qJos+uw7WmWF4wUwBd9jxjocFC2w==", - "license": "MIT", - "engines": { - "node": "^12.17.0 || ^14.13 || >=16.0.0" - }, - "funding": { - "url": "https://github.com/chalk/chalk?sponsor=1" - } - }, - "node_modules/uri-js": { - "version": "4.4.1", - "resolved": "https://registry.npmjs.org/uri-js/-/uri-js-4.4.1.tgz", - "integrity": "sha512-7rKUyy33Q1yc98pQ1DAmLtwX109F7TIfWlW1Ydo8Wl1ii1SeHieeh0HHfPeL2fMXK6z0s8ecKs9frCuLJvndBg==", - "license": "BSD-2-Clause", - "dependencies": { - "punycode": "^2.1.0" - } - }, - "node_modules/uri-js-replace": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/uri-js-replace/-/uri-js-replace-1.0.1.tgz", - "integrity": "sha512-W+C9NWNLFOoBI2QWDp4UT9pv65r2w5Cx+3sTYFvtMdDBxkKt1syCqsUdSFAChbEe1uK5TfS04wt/nGwmaeIQ0g==", - "license": "MIT" - }, - "node_modules/uri-js/node_modules/punycode": { - "version": "2.3.1", - "resolved": "https://registry.npmjs.org/punycode/-/punycode-2.3.1.tgz", - "integrity": "sha512-vYt7UD1U9Wg6138shLtLOvdAu+8DsC/ilFtEVHcH+wydcSpNE20AfSOduf6MkRFahL5FY7X1oU7nKVZFtfq8Fg==", - "license": "MIT", - "engines": { - "node": ">=6" - } - }, - "node_modules/url": { - "version": "0.11.4", - "resolved": "https://registry.npmjs.org/url/-/url-0.11.4.tgz", - "integrity": "sha512-oCwdVC7mTuWiPyjLUz/COz5TLk6wgp0RCsN+wHZ2Ekneac9w8uuV0njcbbie2ME+Vs+d6duwmYuR3HgQXs1fOg==", - "license": "MIT", - "dependencies": { - "punycode": "^1.4.1", - "qs": "^6.12.3" - }, - "engines": { - "node": ">= 0.4" - } - }, - "node_modules/url-loader": { - "version": "4.1.1", - "resolved": "https://registry.npmjs.org/url-loader/-/url-loader-4.1.1.tgz", - "integrity": "sha512-3BTV812+AVHHOJQO8O5MkWgZ5aosP7GnROJwvzLS9hWDj00lZ6Z0wNak423Lp9PBZN05N+Jk/N5Si8jRAlGyWA==", - "license": "MIT", - "dependencies": { - "loader-utils": "^2.0.0", - "mime-types": "^2.1.27", - "schema-utils": "^3.0.0" - }, - "engines": { - "node": ">= 10.13.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/webpack" - }, - "peerDependencies": { - "file-loader": "*", - "webpack": "^4.0.0 || ^5.0.0" - }, - "peerDependenciesMeta": { - "file-loader": { - "optional": true - } - } - }, - "node_modules/url-loader/node_modules/ajv": { - "version": "6.12.6", - "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz", - "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==", - "license": "MIT", - "dependencies": { - "fast-deep-equal": "^3.1.1", - "fast-json-stable-stringify": "^2.0.0", - "json-schema-traverse": "^0.4.1", - "uri-js": "^4.2.2" - }, - "funding": { - "type": "github", - "url": "https://github.com/sponsors/epoberezkin" - } - }, - "node_modules/url-loader/node_modules/ajv-keywords": { - "version": "3.5.2", - "resolved": "https://registry.npmjs.org/ajv-keywords/-/ajv-keywords-3.5.2.tgz", - "integrity": "sha512-5p6WTN0DdTGVQk6VjcEju19IgaHudalcfabD7yhDGeA6bcQnmL+CpveLJq/3hvfwd1aof6L386Ougkx6RfyMIQ==", - "license": "MIT", - "peerDependencies": { - "ajv": "^6.9.1" - } - }, - "node_modules/url-loader/node_modules/json-schema-traverse": { - "version": "0.4.1", - "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz", - "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==", - "license": "MIT" - }, - "node_modules/url-loader/node_modules/mime-db": { - "version": "1.52.0", - "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.52.0.tgz", - "integrity": "sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg==", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/url-loader/node_modules/mime-types": { - "version": "2.1.35", - "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.35.tgz", - "integrity": "sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw==", - "license": "MIT", - "dependencies": { - "mime-db": "1.52.0" - }, - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/url-loader/node_modules/schema-utils": { - "version": "3.3.0", - "resolved": "https://registry.npmjs.org/schema-utils/-/schema-utils-3.3.0.tgz", - "integrity": "sha512-pN/yOAvcC+5rQ5nERGuwrjLlYvLTbCibnZ1I7B1LaiAz9BRBlE9GMgE/eqV30P7aJQUf7Ddimy/RsbYO/GrVGg==", - "license": "MIT", - "dependencies": { - "@types/json-schema": "^7.0.8", - "ajv": "^6.12.5", - "ajv-keywords": "^3.5.2" - }, - "engines": { - "node": ">= 10.13.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/webpack" - } - }, - "node_modules/use-editable": { - "version": "2.3.3", - "resolved": "https://registry.npmjs.org/use-editable/-/use-editable-2.3.3.tgz", - "integrity": "sha512-7wVD2JbfAFJ3DK0vITvXBdpd9JAz5BcKAAolsnLBuBn6UDDwBGuCIAGvR3yA2BNKm578vAMVHFCWaOcA+BhhiA==", - "license": "MIT", - "peerDependencies": { - "react": ">= 16.8.0" - } - }, - "node_modules/util": { - "version": "0.12.5", - "resolved": "https://registry.npmjs.org/util/-/util-0.12.5.tgz", - "integrity": "sha512-kZf/K6hEIrWHI6XqOFUiiMa+79wE/D8Q+NCNAWclkyg3b4d2k7s0QGepNjiABc+aR3N1PAyHL7p6UcLY6LmrnA==", - "license": "MIT", - "dependencies": { - "inherits": "^2.0.3", - "is-arguments": "^1.0.4", - "is-generator-function": "^1.0.7", - "is-typed-array": "^1.1.3", - "which-typed-array": "^1.1.2" - } - }, - "node_modules/util-deprecate": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/util-deprecate/-/util-deprecate-1.0.2.tgz", - "integrity": "sha512-EPD5q1uXyFxJpCrLnCc1nHnq3gOa6DZBocAIiI2TaSCA7VCJ1UJDMagCzIkXNsUYfD1daK//LTEQ8xiIbrHtcw==", - "license": "MIT" - }, - "node_modules/utila": { - "version": "0.4.0", - "resolved": "https://registry.npmjs.org/utila/-/utila-0.4.0.tgz", - "integrity": "sha512-Z0DbgELS9/L/75wZbro8xAnT50pBVFQZ+hUEueGDU5FN51YSCYM+jdxsfCiHjwNP/4LCDD0i/graKpeBnOXKRA==", - "license": "MIT" - }, - "node_modules/utility-types": { - "version": "3.11.0", - "resolved": "https://registry.npmjs.org/utility-types/-/utility-types-3.11.0.tgz", - "integrity": "sha512-6Z7Ma2aVEWisaL6TvBCy7P8rm2LQoPv6dJ7ecIaIixHcwfbJ0x7mWdbcwlIM5IGQxPZSFYeqRCqlOOeKoJYMkw==", - "license": "MIT", - "engines": { - "node": ">= 4" - } - }, - "node_modules/utils-merge": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/utils-merge/-/utils-merge-1.0.1.tgz", - "integrity": "sha512-pMZTvIkT1d+TFGvDOqodOclx0QWkkgi6Tdoa8gC8ffGAAqz9pzPTZWAybbsHHoED/ztMtkv/VoYTYyShUn81hA==", - "license": "MIT", - "engines": { - "node": ">= 0.4.0" - } - }, - "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/uvu": { - "version": "0.5.6", - "resolved": "https://registry.npmjs.org/uvu/-/uvu-0.5.6.tgz", - "integrity": "sha512-+g8ENReyr8YsOc6fv/NVJs2vFdHBnBNdfE49rshrTzDWOlUx4Gq7KOS2GD8eqhy2j+Ejq29+SbKH8yjkAqXqoA==", - "license": "MIT", - "dependencies": { - "dequal": "^2.0.0", - "diff": "^5.0.0", - "kleur": "^4.0.3", - "sade": "^1.7.3" - }, - "bin": { - "uvu": "bin.js" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/uvu/node_modules/kleur": { - "version": "4.1.5", - "resolved": "https://registry.npmjs.org/kleur/-/kleur-4.1.5.tgz", - "integrity": "sha512-o+NO+8WrRiQEE4/7nwRJhN1HWpVmJm511pBHUxPLtp0BUISzlBplORYSmTclCnJvQq2tKu/sgl3xVpkc7ZWuQQ==", - "license": "MIT", - "engines": { - "node": ">=6" - } - }, - "node_modules/validate-peer-dependencies": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/validate-peer-dependencies/-/validate-peer-dependencies-2.2.0.tgz", - "integrity": "sha512-8X1OWlERjiUY6P6tdeU9E0EwO8RA3bahoOVG7ulOZT5MqgNDUO/BQoVjYiHPcNe+v8glsboZRIw9iToMAA2zAA==", - "license": "MIT", - "dependencies": { - "resolve-package-path": "^4.0.3", - "semver": "^7.3.8" - }, - "engines": { - "node": ">= 12" - } - }, - "node_modules/validate.io-array": { - "version": "1.0.6", - "resolved": "https://registry.npmjs.org/validate.io-array/-/validate.io-array-1.0.6.tgz", - "integrity": "sha512-DeOy7CnPEziggrOO5CZhVKJw6S3Yi7e9e65R1Nl/RTN1vTQKnzjfvks0/8kQ40FP/dsjRAOd4hxmJ7uLa6vxkg==", - "license": "MIT" - }, - "node_modules/validate.io-function": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/validate.io-function/-/validate.io-function-1.0.2.tgz", - "integrity": "sha512-LlFybRJEriSuBnUhQyG5bwglhh50EpTL2ul23MPIuR1odjO7XaMLFV8vHGwp7AZciFxtYOeiSCT5st+XSPONiQ==" - }, - "node_modules/validate.io-integer": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/validate.io-integer/-/validate.io-integer-1.0.5.tgz", - "integrity": "sha512-22izsYSLojN/P6bppBqhgUDjCkr5RY2jd+N2a3DCAUey8ydvrZ/OkGvFPR7qfOpwR2LC5p4Ngzxz36g5Vgr/hQ==", - "dependencies": { - "validate.io-number": "^1.0.3" - } - }, - "node_modules/validate.io-integer-array": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/validate.io-integer-array/-/validate.io-integer-array-1.0.0.tgz", - "integrity": "sha512-mTrMk/1ytQHtCY0oNO3dztafHYyGU88KL+jRxWuzfOmQb+4qqnWmI+gykvGp8usKZOM0H7keJHEbRaFiYA0VrA==", - "dependencies": { - "validate.io-array": "^1.0.3", - "validate.io-integer": "^1.0.4" - } - }, - "node_modules/validate.io-number": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/validate.io-number/-/validate.io-number-1.0.3.tgz", - "integrity": "sha512-kRAyotcbNaSYoDnXvb4MHg/0a1egJdLwS6oJ38TJY7aw9n93Fl/3blIXdyYvPOp55CNxywooG/3BcrwNrBpcSg==" - }, - "node_modules/value-equal": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/value-equal/-/value-equal-1.0.1.tgz", - "integrity": "sha512-NOJ6JZCAWr0zlxZt+xqCHNTEKOsrks2HQd4MqhP1qy4z1SkbEP467eNx6TgDKXMvUOb+OENfJCZwM+16n7fRfw==", - "license": "MIT" - }, - "node_modules/vary": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/vary/-/vary-1.1.2.tgz", - "integrity": "sha512-BNGbWLfd0eUPabhkXUVm0j8uuvREyTh5ovRa/dyow/BqAbZJyC+5fU+IzQOzmAKzYqYRAISoRhdQr3eIZ/PXqg==", - "license": "MIT", - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/vfile": { - "version": "6.0.2", - "resolved": "https://registry.npmjs.org/vfile/-/vfile-6.0.2.tgz", - "integrity": "sha512-zND7NlS8rJYb/sPqkb13ZvbbUoExdbi4w3SfRrMq6R3FvnLQmmfpajJNITuuYm6AZ5uao9vy4BAos3EXBPf2rg==", - "license": "MIT", - "dependencies": { - "@types/unist": "^3.0.0", - "unist-util-stringify-position": "^4.0.0", - "vfile-message": "^4.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/vfile-location": { - "version": "5.0.3", - "resolved": "https://registry.npmjs.org/vfile-location/-/vfile-location-5.0.3.tgz", - "integrity": "sha512-5yXvWDEgqeiYiBe1lbxYF7UMAIm/IcopxMHrMQDq3nvKcjPKIhZklUKL+AE7J7uApI4kwe2snsK+eI6UTj9EHg==", - "license": "MIT", - "dependencies": { - "@types/unist": "^3.0.0", - "vfile": "^6.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/vfile-message": { - "version": "4.0.2", - "resolved": "https://registry.npmjs.org/vfile-message/-/vfile-message-4.0.2.tgz", - "integrity": "sha512-jRDZ1IMLttGj41KcZvlrYAaI3CfqpLpfpf+Mfig13viT6NKvRzWZ+lXz0Y5D60w6uJIBAOGq9mSHf0gktF0duw==", - "license": "MIT", - "dependencies": { - "@types/unist": "^3.0.0", - "unist-util-stringify-position": "^4.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/unified" - } - }, - "node_modules/vm-browserify": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/vm-browserify/-/vm-browserify-1.1.2.tgz", - "integrity": "sha512-2ham8XPWTONajOR0ohOKOHXkm3+gaBmGut3SRuu75xLd/RRaY6vqgh8NBYYk7+RW3u5AtzPQZG8F10LHkl0lAQ==", - "license": "MIT" - }, - "node_modules/warning": { - "version": "4.0.3", - "resolved": "https://registry.npmjs.org/warning/-/warning-4.0.3.tgz", - "integrity": "sha512-rpJyN222KWIvHJ/F53XSZv0Zl/accqHR8et1kpaMTD/fLCRxtV8iX8czMzY7sVZupTI3zcUTg8eycS2kNF9l6w==", - "license": "MIT", - "dependencies": { - "loose-envify": "^1.0.0" - } - }, - "node_modules/watchpack": { - "version": "2.4.1", - "resolved": "https://registry.npmjs.org/watchpack/-/watchpack-2.4.1.tgz", - "integrity": "sha512-8wrBCMtVhqcXP2Sup1ctSkga6uc2Bx0IIvKyT7yTFier5AXHooSI+QyQQAtTb7+E0IUCCKyTFmXqdqgum2XWGg==", - "license": "MIT", - "dependencies": { - "glob-to-regexp": "^0.4.1", - "graceful-fs": "^4.1.2" - }, - "engines": { - "node": ">=10.13.0" - } - }, - "node_modules/wbuf": { - "version": "1.7.3", - "resolved": "https://registry.npmjs.org/wbuf/-/wbuf-1.7.3.tgz", - "integrity": "sha512-O84QOnr0icsbFGLS0O3bI5FswxzRr8/gHwWkDlQFskhSPryQXvrTMxjxGP4+iWYoauLoBvfDpkrOauZ+0iZpDA==", - "license": "MIT", - "dependencies": { - "minimalistic-assert": "^1.0.0" - } - }, - "node_modules/web-namespaces": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/web-namespaces/-/web-namespaces-2.0.1.tgz", - "integrity": "sha512-bKr1DkiNa2krS7qxNtdrtHAmzuYGFQLiQ13TsorsdT6ULTkPLKuu5+GsFpDlg6JFjUTwX2DyhMPG2be8uPrqsQ==", - "license": "MIT", - "funding": { - "type": "github", - "url": "https://github.com/sponsors/wooorm" - } - }, - "node_modules/webidl-conversions": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/webidl-conversions/-/webidl-conversions-3.0.1.tgz", - "integrity": "sha512-2JAn3z8AR6rjK8Sm8orRC0h/bcl/DqL7tRPdGZ4I1CjdF+EaMLmYxBHyXuKL849eucPFhvBoxMsflfOb8kxaeQ==", - "license": "BSD-2-Clause" - }, - "node_modules/webpack": { - "version": "5.96.1", - "resolved": "https://registry.npmjs.org/webpack/-/webpack-5.96.1.tgz", - "integrity": "sha512-l2LlBSvVZGhL4ZrPwyr8+37AunkcYj5qh8o6u2/2rzoPc8gxFJkLj1WxNgooi9pnoc06jh0BjuXnamM4qlujZA==", - "license": "MIT", - "dependencies": { - "@types/eslint-scope": "^3.7.7", - "@types/estree": "^1.0.6", - "@webassemblyjs/ast": "^1.12.1", - "@webassemblyjs/wasm-edit": "^1.12.1", - "@webassemblyjs/wasm-parser": "^1.12.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": "^3.2.0", - "tapable": "^2.1.1", - "terser-webpack-plugin": "^5.3.10", - "watchpack": "^2.4.1", - "webpack-sources": "^3.2.3" - }, - "bin": { - "webpack": "bin/webpack.js" - }, - "engines": { - "node": ">=10.13.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/webpack" - }, - "peerDependenciesMeta": { - "webpack-cli": { - "optional": true - } - } - }, - "node_modules/webpack-bundle-analyzer": { - "version": "4.10.2", - "resolved": "https://registry.npmjs.org/webpack-bundle-analyzer/-/webpack-bundle-analyzer-4.10.2.tgz", - "integrity": "sha512-vJptkMm9pk5si4Bv922ZbKLV8UTT4zib4FPgXMhgzUny0bfDDkLXAVQs3ly3fS4/TN9ROFtb0NFrm04UXFE/Vw==", - "license": "MIT", - "dependencies": { - "@discoveryjs/json-ext": "0.5.7", - "acorn": "^8.0.4", - "acorn-walk": "^8.0.0", - "commander": "^7.2.0", - "debounce": "^1.2.1", - "escape-string-regexp": "^4.0.0", - "gzip-size": "^6.0.0", - "html-escaper": "^2.0.2", - "opener": "^1.5.2", - "picocolors": "^1.0.0", - "sirv": "^2.0.3", - "ws": "^7.3.1" - }, - "bin": { - "webpack-bundle-analyzer": "lib/bin/analyzer.js" - }, - "engines": { - "node": ">= 10.13.0" - } - }, - "node_modules/webpack-bundle-analyzer/node_modules/commander": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/commander/-/commander-7.2.0.tgz", - "integrity": "sha512-QrWXB+ZQSVPmIWIhtEO9H+gwHaMGYiF5ChvoJ+K9ZGHG/sVsa6yiesAD1GC/x46sET00Xlwo1u49RVVVzvcSkw==", - "license": "MIT", - "engines": { - "node": ">= 10" - } - }, - "node_modules/webpack-dev-middleware": { - "version": "5.3.4", - "resolved": "https://registry.npmjs.org/webpack-dev-middleware/-/webpack-dev-middleware-5.3.4.tgz", - "integrity": "sha512-BVdTqhhs+0IfoeAf7EoH5WE+exCmqGerHfDM0IL096Px60Tq2Mn9MAbnaGUe6HiMa41KMCYF19gyzZmBcq/o4Q==", - "license": "MIT", - "dependencies": { - "colorette": "^2.0.10", - "memfs": "^3.4.3", - "mime-types": "^2.1.31", - "range-parser": "^1.2.1", - "schema-utils": "^4.0.0" - }, - "engines": { - "node": ">= 12.13.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/webpack" - }, - "peerDependencies": { - "webpack": "^4.0.0 || ^5.0.0" - } - }, - "node_modules/webpack-dev-middleware/node_modules/mime-db": { - "version": "1.52.0", - "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.52.0.tgz", - "integrity": "sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg==", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/webpack-dev-middleware/node_modules/mime-types": { - "version": "2.1.35", - "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.35.tgz", - "integrity": "sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw==", - "license": "MIT", - "dependencies": { - "mime-db": "1.52.0" - }, - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/webpack-dev-middleware/node_modules/range-parser": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/range-parser/-/range-parser-1.2.1.tgz", - "integrity": "sha512-Hrgsx+orqoygnmhFbKaHE6c296J+HTAQXoxEF6gNupROmmGJRoyzfG3ccAveqCBrwr/2yxQ5BVd/GTl5agOwSg==", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/webpack-dev-server": { - "version": "4.15.2", - "resolved": "https://registry.npmjs.org/webpack-dev-server/-/webpack-dev-server-4.15.2.tgz", - "integrity": "sha512-0XavAZbNJ5sDrCbkpWL8mia0o5WPOd2YGtxrEiZkBK9FjLppIUK2TgxK6qGD2P3hUXTJNNPVibrerKcx5WkR1g==", - "license": "MIT", - "dependencies": { - "@types/bonjour": "^3.5.9", - "@types/connect-history-api-fallback": "^1.3.5", - "@types/express": "^4.17.13", - "@types/serve-index": "^1.9.1", - "@types/serve-static": "^1.13.10", - "@types/sockjs": "^0.3.33", - "@types/ws": "^8.5.5", - "ansi-html-community": "^0.0.8", - "bonjour-service": "^1.0.11", - "chokidar": "^3.5.3", - "colorette": "^2.0.10", - "compression": "^1.7.4", - "connect-history-api-fallback": "^2.0.0", - "default-gateway": "^6.0.3", - "express": "^4.17.3", - "graceful-fs": "^4.2.6", - "html-entities": "^2.3.2", - "http-proxy-middleware": "^2.0.3", - "ipaddr.js": "^2.0.1", - "launch-editor": "^2.6.0", - "open": "^8.0.9", - "p-retry": "^4.5.0", - "rimraf": "^3.0.2", - "schema-utils": "^4.0.0", - "selfsigned": "^2.1.1", - "serve-index": "^1.9.1", - "sockjs": "^0.3.24", - "spdy": "^4.0.2", - "webpack-dev-middleware": "^5.3.4", - "ws": "^8.13.0" - }, - "bin": { - "webpack-dev-server": "bin/webpack-dev-server.js" - }, - "engines": { - "node": ">= 12.13.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/webpack" - }, - "peerDependencies": { - "webpack": "^4.37.0 || ^5.0.0" - }, - "peerDependenciesMeta": { - "webpack": { - "optional": true - }, - "webpack-cli": { - "optional": true - } - } - }, - "node_modules/webpack-dev-server/node_modules/ws": { - "version": "8.18.0", - "resolved": "https://registry.npmjs.org/ws/-/ws-8.18.0.tgz", - "integrity": "sha512-8VbfWfHLbbwu3+N6OKsOMpBdT4kXPDDB9cJk2bJ6mh9ucxdlnNvH1e+roYkKmN9Nxw2yjz7VzeO9oOz2zJ04Pw==", - "license": "MIT", - "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/webpack-merge": { - "version": "5.10.0", - "resolved": "https://registry.npmjs.org/webpack-merge/-/webpack-merge-5.10.0.tgz", - "integrity": "sha512-+4zXKdx7UnO+1jaN4l2lHVD+mFvnlZQP/6ljaJVb4SZiwIKeUnrT5l0gkT8z+n4hKpC+jpOv6O9R+gLtag7pSA==", - "license": "MIT", - "dependencies": { - "clone-deep": "^4.0.1", - "flat": "^5.0.2", - "wildcard": "^2.0.0" - }, - "engines": { - "node": ">=10.0.0" - } - }, - "node_modules/webpack-sources": { - "version": "3.2.3", - "resolved": "https://registry.npmjs.org/webpack-sources/-/webpack-sources-3.2.3.tgz", - "integrity": "sha512-/DyMEOrDgLKKIG0fmvtz+4dUX/3Ghozwgm6iPp8KRhvn+eQf9+Q7GWxVNMk3+uCPWfdXYC4ExGBckIXdFEfH1w==", - "license": "MIT", - "engines": { - "node": ">=10.13.0" - } - }, - "node_modules/webpack/node_modules/ajv": { - "version": "6.12.6", - "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz", - "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==", - "license": "MIT", - "dependencies": { - "fast-deep-equal": "^3.1.1", - "fast-json-stable-stringify": "^2.0.0", - "json-schema-traverse": "^0.4.1", - "uri-js": "^4.2.2" - }, - "funding": { - "type": "github", - "url": "https://github.com/sponsors/epoberezkin" - } - }, - "node_modules/webpack/node_modules/ajv-keywords": { - "version": "3.5.2", - "resolved": "https://registry.npmjs.org/ajv-keywords/-/ajv-keywords-3.5.2.tgz", - "integrity": "sha512-5p6WTN0DdTGVQk6VjcEju19IgaHudalcfabD7yhDGeA6bcQnmL+CpveLJq/3hvfwd1aof6L386Ougkx6RfyMIQ==", - "license": "MIT", - "peerDependencies": { - "ajv": "^6.9.1" - } - }, - "node_modules/webpack/node_modules/json-schema-traverse": { - "version": "0.4.1", - "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz", - "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==", - "license": "MIT" - }, - "node_modules/webpack/node_modules/mime-db": { - "version": "1.52.0", - "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.52.0.tgz", - "integrity": "sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg==", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/webpack/node_modules/mime-types": { - "version": "2.1.35", - "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.35.tgz", - "integrity": "sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw==", - "license": "MIT", - "dependencies": { - "mime-db": "1.52.0" - }, - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/webpack/node_modules/schema-utils": { - "version": "3.3.0", - "resolved": "https://registry.npmjs.org/schema-utils/-/schema-utils-3.3.0.tgz", - "integrity": "sha512-pN/yOAvcC+5rQ5nERGuwrjLlYvLTbCibnZ1I7B1LaiAz9BRBlE9GMgE/eqV30P7aJQUf7Ddimy/RsbYO/GrVGg==", - "license": "MIT", - "dependencies": { - "@types/json-schema": "^7.0.8", - "ajv": "^6.12.5", - "ajv-keywords": "^3.5.2" - }, - "engines": { - "node": ">= 10.13.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/webpack" - } - }, - "node_modules/webpackbar": { - "version": "6.0.1", - "resolved": "https://registry.npmjs.org/webpackbar/-/webpackbar-6.0.1.tgz", - "integrity": "sha512-TnErZpmuKdwWBdMoexjio3KKX6ZtoKHRVvLIU0A47R0VVBDtx3ZyOJDktgYixhoJokZTYTt1Z37OkO9pnGJa9Q==", - "license": "MIT", - "dependencies": { - "ansi-escapes": "^4.3.2", - "chalk": "^4.1.2", - "consola": "^3.2.3", - "figures": "^3.2.0", - "markdown-table": "^2.0.0", - "pretty-time": "^1.1.0", - "std-env": "^3.7.0", - "wrap-ansi": "^7.0.0" - }, - "engines": { - "node": ">=14.21.3" - }, - "peerDependencies": { - "webpack": "3 || 4 || 5" - } - }, - "node_modules/webpackbar/node_modules/emoji-regex": { - "version": "8.0.0", - "resolved": "https://registry.npmjs.org/emoji-regex/-/emoji-regex-8.0.0.tgz", - "integrity": "sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A==", - "license": "MIT" - }, - "node_modules/webpackbar/node_modules/markdown-table": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/markdown-table/-/markdown-table-2.0.0.tgz", - "integrity": "sha512-Ezda85ToJUBhM6WGaG6veasyym+Tbs3cMAw/ZhOPqXiYsr0jgocBV3j3nx+4lk47plLlIqjwuTm/ywVI+zjJ/A==", - "license": "MIT", - "dependencies": { - "repeat-string": "^1.0.0" - }, - "funding": { - "type": "github", - "url": "https://github.com/sponsors/wooorm" - } - }, - "node_modules/webpackbar/node_modules/string-width": { - "version": "4.2.3", - "resolved": "https://registry.npmjs.org/string-width/-/string-width-4.2.3.tgz", - "integrity": "sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g==", - "license": "MIT", - "dependencies": { - "emoji-regex": "^8.0.0", - "is-fullwidth-code-point": "^3.0.0", - "strip-ansi": "^6.0.1" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/webpackbar/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==", - "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/websocket-driver": { - "version": "0.7.4", - "resolved": "https://registry.npmjs.org/websocket-driver/-/websocket-driver-0.7.4.tgz", - "integrity": "sha512-b17KeDIQVjvb0ssuSDF2cYXSg2iztliJ4B9WdsuB6J952qCPKmnVq4DyW5motImXHDC1cBT/1UezrJVsKw5zjg==", - "license": "Apache-2.0", - "dependencies": { - "http-parser-js": ">=0.5.1", - "safe-buffer": ">=5.1.0", - "websocket-extensions": ">=0.1.1" - }, - "engines": { - "node": ">=0.8.0" - } - }, - "node_modules/websocket-extensions": { - "version": "0.1.4", - "resolved": "https://registry.npmjs.org/websocket-extensions/-/websocket-extensions-0.1.4.tgz", - "integrity": "sha512-OqedPIGOfsDlo31UNwYbCFMSaO9m9G/0faIHj5/dZFDMFqPTcx6UwqyOy3COEaEOg/9VsGIpdqn62W5KhoKSpg==", - "license": "Apache-2.0", - "engines": { - "node": ">=0.8.0" - } - }, - "node_modules/whatwg-encoding": { - "version": "3.1.1", - "resolved": "https://registry.npmjs.org/whatwg-encoding/-/whatwg-encoding-3.1.1.tgz", - "integrity": "sha512-6qN4hJdMwfYBtE3YBTTHhoeuUrDBPZmbQaxWAqSALV/MeEnR5z1xd8UKud2RAkFoPkmB+hli1TZSnyi84xz1vQ==", - "license": "MIT", - "dependencies": { - "iconv-lite": "0.6.3" - }, - "engines": { - "node": ">=18" - } - }, - "node_modules/whatwg-encoding/node_modules/iconv-lite": { - "version": "0.6.3", - "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.6.3.tgz", - "integrity": "sha512-4fCk79wshMdzMp2rH06qWrJE4iolqLhCUH+OiuIgU++RB0+94NlDL81atO7GX55uUKueo0txHNtvEyI6D7WdMw==", - "license": "MIT", - "dependencies": { - "safer-buffer": ">= 2.1.2 < 3.0.0" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/whatwg-mimetype": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/whatwg-mimetype/-/whatwg-mimetype-4.0.0.tgz", - "integrity": "sha512-QaKxh0eNIi2mE9p2vEdzfagOKHCcj1pJ56EEHGQOVxp8r9/iszLUUV7v89x9O1p/T+NlTM5W7jW6+cz4Fq1YVg==", - "license": "MIT", - "engines": { - "node": ">=18" - } - }, - "node_modules/whatwg-url": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/whatwg-url/-/whatwg-url-5.0.0.tgz", - "integrity": "sha512-saE57nupxk6v3HY35+jzBwYa0rKSy0XR8JSxZPwgLr7ys0IBzhGviA1/TUGJLmSVqs8pb9AnvICXEuOHLprYTw==", - "license": "MIT", - "dependencies": { - "tr46": "~0.0.3", - "webidl-conversions": "^3.0.0" - } - }, - "node_modules/which": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/which/-/which-2.0.2.tgz", - "integrity": "sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA==", - "license": "ISC", - "dependencies": { - "isexe": "^2.0.0" - }, - "bin": { - "node-which": "bin/node-which" - }, - "engines": { - "node": ">= 8" - } - }, - "node_modules/which-typed-array": { - "version": "1.1.15", - "resolved": "https://registry.npmjs.org/which-typed-array/-/which-typed-array-1.1.15.tgz", - "integrity": "sha512-oV0jmFtUky6CXfkqehVvBP/LSWJ2sy4vWMioiENyJLePrBO/yKyV9OyJySfAKosh+RYkIl5zJCNZ8/4JncrpdA==", - "license": "MIT", - "dependencies": { - "available-typed-arrays": "^1.0.7", - "call-bind": "^1.0.7", - "for-each": "^0.3.3", - "gopd": "^1.0.1", - "has-tostringtag": "^1.0.2" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/widest-line": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/widest-line/-/widest-line-4.0.1.tgz", - "integrity": "sha512-o0cyEG0e8GPzT4iGHphIOh0cJOV8fivsXxddQasHPHfoZf1ZexrfeA21w2NaEN1RHE+fXlfISmOE8R9N3u3Qig==", - "license": "MIT", - "dependencies": { - "string-width": "^5.0.1" - }, - "engines": { - "node": ">=12" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/wildcard": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/wildcard/-/wildcard-2.0.1.tgz", - "integrity": "sha512-CC1bOL87PIWSBhDcTrdeLo6eGT7mCFtrg0uIJtqJUFyK+eJnzl8A1niH56uu7KMa5XFrtiV+AQuHO3n7DsHnLQ==", - "license": "MIT" - }, - "node_modules/wrap-ansi": { - "version": "8.1.0", - "resolved": "https://registry.npmjs.org/wrap-ansi/-/wrap-ansi-8.1.0.tgz", - "integrity": "sha512-si7QWI6zUMq56bESFvagtmzMdGOtoxfR+Sez11Mobfc7tm+VkUckk9bW2UeffTGVUbOksxmSw0AA2gs8g71NCQ==", - "license": "MIT", - "dependencies": { - "ansi-styles": "^6.1.0", - "string-width": "^5.0.1", - "strip-ansi": "^7.0.1" - }, - "engines": { - "node": ">=12" - }, - "funding": { - "url": "https://github.com/chalk/wrap-ansi?sponsor=1" - } - }, - "node_modules/wrap-ansi-cjs": { - "name": "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==", - "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/wrap-ansi-cjs/node_modules/emoji-regex": { - "version": "8.0.0", - "resolved": "https://registry.npmjs.org/emoji-regex/-/emoji-regex-8.0.0.tgz", - "integrity": "sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A==", - "license": "MIT" - }, - "node_modules/wrap-ansi-cjs/node_modules/string-width": { - "version": "4.2.3", - "resolved": "https://registry.npmjs.org/string-width/-/string-width-4.2.3.tgz", - "integrity": "sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g==", - "license": "MIT", - "dependencies": { - "emoji-regex": "^8.0.0", - "is-fullwidth-code-point": "^3.0.0", - "strip-ansi": "^6.0.1" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/wrap-ansi/node_modules/ansi-regex": { - "version": "6.0.1", - "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-6.0.1.tgz", - "integrity": "sha512-n5M855fKb2SsfMIiFFoVrABHJC8QtHwVx+mHWP3QcEqBHYienj5dHSgjbxtC0WEZXYt4wcD6zrQElDPhFuZgfA==", - "license": "MIT", - "engines": { - "node": ">=12" - }, - "funding": { - "url": "https://github.com/chalk/ansi-regex?sponsor=1" - } - }, - "node_modules/wrap-ansi/node_modules/ansi-styles": { - "version": "6.2.1", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-6.2.1.tgz", - "integrity": "sha512-bN798gFfQX+viw3R7yrGWRqnrN2oRkEkUjjl4JNn4E8GxxbjtG3FbrEIIY3l8/hrwUwIeCZvi4QuOTP4MErVug==", - "license": "MIT", - "engines": { - "node": ">=12" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, - "node_modules/wrap-ansi/node_modules/strip-ansi": { - "version": "7.1.0", - "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-7.1.0.tgz", - "integrity": "sha512-iq6eVVI64nQQTRYq2KtEg2d2uU7LElhTJwsH4YzIHZshxlgZms/wIc4VoDQTlG/IvVIrBKG06CrZnp0qv7hkcQ==", - "license": "MIT", - "dependencies": { - "ansi-regex": "^6.0.1" - }, - "engines": { - "node": ">=12" - }, - "funding": { - "url": "https://github.com/chalk/strip-ansi?sponsor=1" - } - }, - "node_modules/wrappy": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz", - "integrity": "sha512-l4Sp/DRseor9wL6EvV2+TuQn63dMkPjZ/sp9XkghTEbV9KlPS1xUsZ3u7/IQO4wxtcFB4bgpQPRcR3QCvezPcQ==", - "license": "ISC" - }, - "node_modules/write-file-atomic": { - "version": "3.0.3", - "resolved": "https://registry.npmjs.org/write-file-atomic/-/write-file-atomic-3.0.3.tgz", - "integrity": "sha512-AvHcyZ5JnSfq3ioSyjrBkH9yW4m7Ayk8/9My/DD9onKeu/94fwrMocemO2QAJFAlnnDN+ZDS+ZjAR5ua1/PV/Q==", - "license": "ISC", - "dependencies": { - "imurmurhash": "^0.1.4", - "is-typedarray": "^1.0.0", - "signal-exit": "^3.0.2", - "typedarray-to-buffer": "^3.1.5" - } - }, - "node_modules/ws": { - "version": "7.5.10", - "resolved": "https://registry.npmjs.org/ws/-/ws-7.5.10.tgz", - "integrity": "sha512-+dbF1tHwZpXcbOJdVOkzLDxZP1ailvSxM6ZweXTegylPny803bFhA+vqBYw4s31NSAk4S2Qz+AKXK9a4wkdjcQ==", - "license": "MIT", - "engines": { - "node": ">=8.3.0" - }, - "peerDependencies": { - "bufferutil": "^4.0.1", - "utf-8-validate": "^5.0.2" - }, - "peerDependenciesMeta": { - "bufferutil": { - "optional": true - }, - "utf-8-validate": { - "optional": true - } - } - }, - "node_modules/xdg-basedir": { - "version": "5.1.0", - "resolved": "https://registry.npmjs.org/xdg-basedir/-/xdg-basedir-5.1.0.tgz", - "integrity": "sha512-GCPAHLvrIH13+c0SuacwvRYj2SxJXQ4kaVTT5xgL3kPrz56XxkF21IGhjSE1+W0aw7gpBWRGXLCPnPby6lSpmQ==", - "license": "MIT", - "engines": { - "node": ">=12" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/xml-formatter": { - "version": "2.6.1", - "resolved": "https://registry.npmjs.org/xml-formatter/-/xml-formatter-2.6.1.tgz", - "integrity": "sha512-dOiGwoqm8y22QdTNI7A+N03tyVfBlQ0/oehAzxIZtwnFAHGeSlrfjF73YQvzSsa/Kt6+YZasKsrdu6OIpuBggw==", - "license": "MIT", - "dependencies": { - "xml-parser-xo": "^3.2.0" - }, - "engines": { - "node": ">= 10" - } - }, - "node_modules/xml-js": { - "version": "1.6.11", - "resolved": "https://registry.npmjs.org/xml-js/-/xml-js-1.6.11.tgz", - "integrity": "sha512-7rVi2KMfwfWFl+GpPg6m80IVMWXLRjO+PxTq7V2CDhoGak0wzYzFgUY2m4XJ47OGdXd8eLE8EmwfAmdjw7lC1g==", - "license": "MIT", - "dependencies": { - "sax": "^1.2.4" - }, - "bin": { - "xml-js": "bin/cli.js" - } - }, - "node_modules/xml-parser-xo": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/xml-parser-xo/-/xml-parser-xo-3.2.0.tgz", - "integrity": "sha512-8LRU6cq+d7mVsoDaMhnkkt3CTtAs4153p49fRo+HIB3I1FD1o5CeXRjRH29sQevIfVJIcPjKSsPU/+Ujhq09Rg==", - "license": "MIT", - "engines": { - "node": ">= 10" - } - }, - "node_modules/xtend": { - "version": "4.0.2", - "resolved": "https://registry.npmjs.org/xtend/-/xtend-4.0.2.tgz", - "integrity": "sha512-LKYU1iAXJXUgAXn9URjiu+MWhyUXHsvfp7mcuYm9dSUKK0/CjtrUwFAxD82/mCWbtLsGjFIad0wIsod4zrTAEQ==", - "license": "MIT", - "engines": { - "node": ">=0.4" - } - }, - "node_modules/y18n": { - "version": "5.0.8", - "resolved": "https://registry.npmjs.org/y18n/-/y18n-5.0.8.tgz", - "integrity": "sha512-0pfFzegeDWJHJIAmTLRP2DwHjdF5s7jo9tuztdQxAhINCdvS+3nGINqPd00AphqJR/0LhANUS6/+7SCb98YOfA==", - "license": "ISC", - "engines": { - "node": ">=10" - } - }, - "node_modules/yallist": { - "version": "3.1.1", - "resolved": "https://registry.npmjs.org/yallist/-/yallist-3.1.1.tgz", - "integrity": "sha512-a4UGQaWPH59mOXUYnAG2ewncQS4i4F43Tv3JoAM+s2VDAmS9NsK8GpDMLrCHPksFT7h3K6TOoUNn2pb7RoXx4g==", - "license": "ISC" - }, - "node_modules/yaml": { - "version": "1.10.2", - "resolved": "https://registry.npmjs.org/yaml/-/yaml-1.10.2.tgz", - "integrity": "sha512-r3vXyErRCYJ7wg28yvBY5VSoAF8ZvlcW9/BwUzEtUsjvX/DKs24dIkuwjtuprwJJHsbyUbLApepYTR1BN4uHrg==", - "license": "ISC", - "engines": { - "node": ">= 6" - } - }, - "node_modules/yaml-ast-parser": { - "version": "0.0.43", - "resolved": "https://registry.npmjs.org/yaml-ast-parser/-/yaml-ast-parser-0.0.43.tgz", - "integrity": "sha512-2PTINUwsRqSd+s8XxKaJWQlUuEMHJQyEuh2edBbW8KNJz0SJPwUSD2zRWqezFEdN7IzAgeuYHFUCF7o8zRdZ0A==", - "license": "Apache-2.0" - }, - "node_modules/yargs": { - "version": "17.7.2", - "resolved": "https://registry.npmjs.org/yargs/-/yargs-17.7.2.tgz", - "integrity": "sha512-7dSzzRQ++CKnNI/krKnYRV7JKKPUXMEh61soaHKg9mrWEhzFWhFnxPxGl+69cD1Ou63C13NUPCnmIcrvqCuM6w==", - "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/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==", - "license": "ISC", - "engines": { - "node": ">=12" - } - }, - "node_modules/yargs/node_modules/emoji-regex": { - "version": "8.0.0", - "resolved": "https://registry.npmjs.org/emoji-regex/-/emoji-regex-8.0.0.tgz", - "integrity": "sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A==", + "node_modules/undefsafe": { + "version": "2.0.5", + "resolved": "https://registry.npmjs.org/undefsafe/-/undefsafe-2.0.5.tgz", + "integrity": "sha512-WxONCrssBM8TSPRqN5EmsjVrsv4A8X12J4ArBiiayv3DyyG3ZlIg6yysuuSYdZsVz3TKcTg2fd//Ujd4CHV1iA==", "license": "MIT" - }, - "node_modules/yargs/node_modules/string-width": { - "version": "4.2.3", - "resolved": "https://registry.npmjs.org/string-width/-/string-width-4.2.3.tgz", - "integrity": "sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g==", - "license": "MIT", - "dependencies": { - "emoji-regex": "^8.0.0", - "is-fullwidth-code-point": "^3.0.0", - "strip-ansi": "^6.0.1" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/yocto-queue": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/yocto-queue/-/yocto-queue-1.1.1.tgz", - "integrity": "sha512-b4JR1PFR10y1mKjhHY9LaGo6tmrgjit7hxVIeAmyMw3jegXR4dhYqLaQF5zMXZxY7tLpMyJeLjr1C4rLmkVe8g==", - "license": "MIT", - "engines": { - "node": ">=12.20" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/zwitch": { - "version": "2.0.4", - "resolved": "https://registry.npmjs.org/zwitch/-/zwitch-2.0.4.tgz", - "integrity": "sha512-bXE4cR/kVZhKZX/RjPEflHaKVhUVl85noU3v6b8apfQEc1x4A+zBxjZ4lN8LqGd6WZ3dl98pY4o717VFmoPp+A==", - "license": "MIT", - "funding": { - "type": "github", - "url": "https://github.com/sponsors/wooorm" - } } } } diff --git a/apps/opik-documentation/documentation/package.json b/apps/opik-documentation/documentation/package.json index fde30ebb8f..40a63d1ba4 100644 --- a/apps/opik-documentation/documentation/package.json +++ b/apps/opik-documentation/documentation/package.json @@ -1,59 +1,9 @@ { - "name": "documentation", - "version": "0.0.0", - "private": true, - "scripts": { - "docusaurus": "docusaurus", - "start": "docusaurus start", - "dev": "sh dev_script.sh", - "build": "sh build_script.sh", - "swizzle": "docusaurus swizzle", - "deploy": "docusaurus deploy", - "clear": "docusaurus clear", - "serve": "docusaurus serve", - "write-translations": "docusaurus write-translations", - "write-heading-ids": "docusaurus write-heading-ids", - "typecheck": "tsc" - }, "dependencies": { - "@docusaurus/core": "^3.7.0", - "@docusaurus/plugin-client-redirects": "^3.7.0", - "@docusaurus/preset-classic": "^3.7.0", - "@mdx-js/react": "^3.0.0", - "@segment/analytics-next": "^1.76.0", - "clsx": "^2.0.0", - "docusaurus-plugin-llms-txt": "^0.1.3", - "docusaurus-plugin-openapi-docs": "^4.0.1", - "docusaurus-plugin-sass": "^0.2.5", - "docusaurus-plugin-search-local": "^2.0.1", - "docusaurus-theme-openapi-docs": "^4.0.1", - "prism-react-renderer": "^2.3.0", - "react": "^18.0.0", - "react-dom": "^18.0.0", - "sass": "^1.77.8" - }, - "devDependencies": { - "@docusaurus/module-type-aliases": "^3.7.0", - "@docusaurus/tsconfig": "^3.7.0", - "@docusaurus/types": "^3.7.0", - "concurrently": "^8.2.0", - "dotenv": "^16.4.5", - "nodemon": "^3.1.7", - "typescript": "~5.2.2" + "fern": "^0.0.19", + "nodemon": "^3.1.9" }, - "browserslist": { - "production": [ - ">0.5%", - "not dead", - "not op_mini all" - ], - "development": [ - "last 3 chrome version", - "last 3 firefox version", - "last 5 safari version" - ] - }, - "engines": { - "node": ">=18.0" + "scripts": { + "dev": "sh dev_script.sh" } } diff --git a/apps/opik-documentation/documentation/pytest.ini b/apps/opik-documentation/documentation/pytest.ini index 078740f1a6..7e33f81031 100644 --- a/apps/opik-documentation/documentation/pytest.ini +++ b/apps/opik-documentation/documentation/pytest.ini @@ -1,7 +1,6 @@ [pytest] -testpaths = docs +testpaths = guides python_files = *.md *.mdx log_cli = true log_cli_level = INFO asyncio_default_fixture_loop_scope = module -norecursedirs = docs/cookbook docs/reference diff --git a/apps/opik-documentation/documentation/pytest_codeblocks/README.md b/apps/opik-documentation/documentation/pytest_codeblocks/README.md index 9ea813676c..b1548fd00f 100644 --- a/apps/opik-documentation/documentation/pytest_codeblocks/README.md +++ b/apps/opik-documentation/documentation/pytest_codeblocks/README.md @@ -37,10 +37,10 @@ The `pytest-codeblocks` extension supports the following features: - Skipping all code blocks in a file: By setting `pytest_codeblocks_skip: true` in the frontmatter of the markdown file, all code blocks in the file will be skipped. -- Skipping specific code blocks: Setting `pytest_codeblocks_skip=true` in the header of the code block will skip it: +- Skipping specific code blocks: Setting `{pytest_codeblocks_skip=true}` in the header of the code block will skip it: ```` - ```python pytest_codeblocks_skip=true + ```python {pytest_codeblocks_skip=true} print("test") diff --git a/apps/opik-documentation/documentation/pytest_codeblocks/parsing_utils.py b/apps/opik-documentation/documentation/pytest_codeblocks/parsing_utils.py index 48effdc887..68c278b0d3 100644 --- a/apps/opik-documentation/documentation/pytest_codeblocks/parsing_utils.py +++ b/apps/opik-documentation/documentation/pytest_codeblocks/parsing_utils.py @@ -50,6 +50,7 @@ def get_page_frontmatter(path): def check_skip_code_block(mk_language): language_params = mk_language.split(" ") for params in language_params: + params = params.strip("{").strip("}") if "=" in params: title, value = params.split("=") if title == "pytest_codeblocks_skip" and ( diff --git a/apps/opik-documentation/documentation/sidebars.ts b/apps/opik-documentation/documentation/sidebars.ts deleted file mode 100644 index db02296eba..0000000000 --- a/apps/opik-documentation/documentation/sidebars.ts +++ /dev/null @@ -1,165 +0,0 @@ -import type { SidebarsConfig } from "@docusaurus/plugin-content-docs"; -import apiSidebar from "./docs/reference/rest_api/sidebar"; - -/** - * Creating a sidebar enables you to: - - create an ordered group of docs - - render a sidebar for each doc of that group - - provide next/previous navigation - - The sidebars can be generated from the filesystem, or explicitly defined here. - - Create as many sidebars as you want. - */ -const sidebars: SidebarsConfig = { - guide_sidebar: [ - "home", - "quickstart", - { - type: "category", - label: "Self-host", - collapsed: true, - items: [ - "self-host/overview", - "self-host/local_deployment", - "self-host/kubernetes", - { - type: "category", - label: "Configuration", - collapsed: true, - items: ["self-host/configure/anonymous_usage_statistics"], - }, - ], - }, - { - type: "category", - label: "Observability", - collapsed: false, - items: [ - "tracing/log_traces", - "tracing/log_agents", - "tracing/log_multimodal_traces", - "tracing/log_distributed_traces", - "tracing/annotate_traces", - "tracing/cost_tracking", - "tracing/sdk_configuration", - "tracing/export_data", - { - type: "category", - label: "Integrations", - collapsed: true, - items: [ - "tracing/integrations/overview", - "tracing/integrations/openai", - "tracing/integrations/litellm", - "tracing/integrations/langchain", // Everything after this one should be ordered by name - "tracing/integrations/aisuite", - "tracing/integrations/anthropic", - "tracing/integrations/bedrock", - "tracing/integrations/crewai", - "tracing/integrations/deepseek", - "tracing/integrations/dify", - "tracing/integrations/dspy", - "tracing/integrations/gemini", - "tracing/integrations/groq", - "tracing/integrations/guardrails-ai", - "tracing/integrations/haystack", - "tracing/integrations/langgraph", - "tracing/integrations/llama_index", - "tracing/integrations/ollama", - "tracing/integrations/predibase", - "tracing/integrations/ragas", - "tracing/integrations/watsonx", - ], - }, - ], - }, - { - type: "category", - label: "Evaluation", - collapsed: false, - items: [ - "evaluation/overview", - "evaluation/concepts", - "evaluation/evaluate_prompt", - "evaluation/evaluate_your_llm", - "evaluation/update_existing_experiment", - "evaluation/manage_datasets", - { - type: "category", - label: "Metrics", - collapsed: true, - items: [ - "evaluation/metrics/overview", - "evaluation/metrics/heuristic_metrics", - "evaluation/metrics/hallucination", - "evaluation/metrics/g_eval", - "evaluation/metrics/moderation", - "evaluation/metrics/answer_relevance", - "evaluation/metrics/context_precision", - "evaluation/metrics/context_recall", - "evaluation/metrics/usefulness", - "evaluation/metrics/custom_model", - "evaluation/metrics/custom_metric", - ], - }, - ], - }, - { - type: "category", - label: "Prompt engineering", - collapsed: true, - items: [ - "prompt_engineering/prompt_management", - "prompt_engineering/managing_prompts_in_code", - "prompt_engineering/playground", - ], - }, - { - type: "category", - label: "Testing", - collapsed: true, - items: ["testing/pytest_integration"], - }, - { - type: "category", - label: "Production", - collapsed: true, - items: ["production/production_monitoring", "production/rules", "production/gateway"], - }, - { - type: "category", - label: "Cookbooks", - collapsed: true, - items: [ - "cookbook/quickstart_notebook", - "cookbook/openai", - "cookbook/litellm", - "cookbook/langchain", // Everything after this one should be ordered by name - "cookbook/aisuite", - "cookbook/anthropic", - "cookbook/bedrock", - "cookbook/crewai", - "cookbook/dspy", - "cookbook/gemini", - "cookbook/groq", - "cookbook/guardrails-ai", - "cookbook/haystack", - "cookbook/langgraph", - "cookbook/llama-index", - "cookbook/ollama", - "cookbook/predibase", - "cookbook/ragas", - "cookbook/watsonx", - "cookbook/evaluate_hallucination_metric", - "cookbook/evaluate_moderation_metric", - ], - }, - "changelog", - "roadmap", - "faq", - ], - rest_api: apiSidebar, -}; - -export default sidebars; diff --git a/apps/opik-documentation/documentation/src/components/GithubStarButton/index.tsx b/apps/opik-documentation/documentation/src/components/GithubStarButton/index.tsx deleted file mode 100644 index f7e7f634be..0000000000 --- a/apps/opik-documentation/documentation/src/components/GithubStarButton/index.tsx +++ /dev/null @@ -1,37 +0,0 @@ -import React, { useEffect, useState } from "react"; -import styles from "./styles.module.css"; - -function formatStarCount(count: number): string { - if (count >= 1000) { - return (count / 1000).toFixed(1) + "K"; - } - - if (count !== undefined) { - return count.toString(); - } else { - return ">3K"; - } -} - -export default function GithubStarButton() { - const [stars, setStars] = useState(0); - - useEffect(() => { - fetch("https://api.github.com/repos/comet-ml/opik") - .then((response) => response.json()) - .then((data) => setStars(data.stargazers_count)) - .catch((error) => console.error("Error fetching GitHub stars:", error)); - }, []); - - return ( - - - {formatStarCount(stars)} - - ); -} diff --git a/apps/opik-documentation/documentation/src/components/GithubStarButton/styles.module.css b/apps/opik-documentation/documentation/src/components/GithubStarButton/styles.module.css deleted file mode 100644 index d7320f1e52..0000000000 --- a/apps/opik-documentation/documentation/src/components/GithubStarButton/styles.module.css +++ /dev/null @@ -1,32 +0,0 @@ -.githubLink { - display: flex; - align-items: center; - padding: 0.25rem 0.75rem; - border-radius: 0.5rem; - margin-left: 1.25rem; - background-color: var(--ifm-color-emphasis-200); - transition: background-color 0.2s; - text-decoration: none; - height: 2.25rem; -} - -.githubLink:hover { - background-color: var(--ifm-color-emphasis-300); -} - -.githubIcon { - fill: var(--ifm-color-emphasis-700); - margin-right: 0.5rem; -} - -.starCount { - font-size: 0.875rem; - font-weight: 600; - color: var(--ifm-color-emphasis-700); -} - -@media (max-width: 996px) { - .githubLink { - display: none; - } -} diff --git a/apps/opik-documentation/documentation/src/components/HomepageFeatures/index.tsx b/apps/opik-documentation/documentation/src/components/HomepageFeatures/index.tsx deleted file mode 100644 index b9f6762124..0000000000 --- a/apps/opik-documentation/documentation/src/components/HomepageFeatures/index.tsx +++ /dev/null @@ -1,70 +0,0 @@ -import clsx from "clsx"; -import Heading from "@theme/Heading"; -import styles from "./styles.module.css"; - -type FeatureItem = { - title: string; - Svg: React.ComponentType>; - description: JSX.Element; -}; - -const FeatureList: FeatureItem[] = [ - { - title: "Easy to Use", - Svg: require("@site/static/img/undraw_docusaurus_mountain.svg").default, - description: ( - <> - Docusaurus was designed from the ground up to be easily installed and used to get your website up and running - quickly. - - ), - }, - { - title: "Focus on What Matters", - Svg: require("@site/static/img/undraw_docusaurus_tree.svg").default, - description: ( - <> - Docusaurus lets you focus on your docs, and we'll do the chores. Go ahead and move your docs into the{" "} - docs directory. - - ), - }, - { - title: "Powered by React", - Svg: require("@site/static/img/undraw_docusaurus_react.svg").default, - description: ( - <> - Extend or customize your website layout by reusing React. Docusaurus can be extended while reusing the same - header and footer. - - ), - }, -]; - -function Feature({ title, Svg, description }: FeatureItem) { - return ( -
-
- -
-
- {title} -

{description}

-
-
- ); -} - -export default function HomepageFeatures(): JSX.Element { - return ( -
-
-
- {FeatureList.map((props, idx) => ( - - ))} -
-
-
- ); -} diff --git a/apps/opik-documentation/documentation/src/components/HomepageFeatures/styles.module.css b/apps/opik-documentation/documentation/src/components/HomepageFeatures/styles.module.css deleted file mode 100644 index b248eb2e5d..0000000000 --- a/apps/opik-documentation/documentation/src/components/HomepageFeatures/styles.module.css +++ /dev/null @@ -1,11 +0,0 @@ -.features { - display: flex; - align-items: center; - padding: 2rem 0; - width: 100%; -} - -.featureSvg { - height: 200px; - width: 200px; -} diff --git a/apps/opik-documentation/documentation/src/css/components/_code.scss b/apps/opik-documentation/documentation/src/css/components/_code.scss deleted file mode 100644 index 67e9a3c96d..0000000000 --- a/apps/opik-documentation/documentation/src/css/components/_code.scss +++ /dev/null @@ -1,21 +0,0 @@ -// Inline cde -.markdown code:not([class]) { - font-family: - ui-monospace, - SFMono-Regular, - Menlo, - Monaco, - Consolas, - Liberation Mono, - Courier New, - monospace; - margin-right: 0.25rem; - margin-left: 0.25rem; -} - -.codeBlockContainer_node_modules-\@docusaurus-theme-classic-lib-theme-CodeBlock-Container-styles-module { - --ifm-global-shadow-lw: none; -} -pre code { - font-size: 0.9em !important; -} diff --git a/apps/opik-documentation/documentation/src/css/components/_content.scss b/apps/opik-documentation/documentation/src/css/components/_content.scss deleted file mode 100644 index ec1ca63fac..0000000000 --- a/apps/opik-documentation/documentation/src/css/components/_content.scss +++ /dev/null @@ -1,38 +0,0 @@ -.markdown > h2, -h3, -h4, -h5, -h6 { - border-bottom: 1px solid var(--ifm-heading-color-border); - padding-bottom: 0.3em; - margin-bottom: 1em; -} - -.markdown > h2 { - --ifm-h2-font-size: 1.875rem; -} - -.markdown > h1 { - font-size: 2.25rem; -} - -.markdown code:not([class]) { - color: var(--ifm-color-content); - border-color: rgba(0, 0, 0, 0.04); - padding-bottom: 2px; - padding-left: 3.6px; - padding-right: 3.6px; - padding-top: 2px; -} - -.markdown img { - border: 1px solid var(--ifm-color-emphasis-300); - border-radius: 4px; -} - -.markdown a { - //color: rgb(0, 107, 230); - text-underline-position: from-font; - text-decoration-line: underline; - text-decoration-thickness: 0.5px; -} diff --git a/apps/opik-documentation/documentation/src/css/components/_pagination.scss b/apps/opik-documentation/documentation/src/css/components/_pagination.scss deleted file mode 100644 index 0674e1d3b6..0000000000 --- a/apps/opik-documentation/documentation/src/css/components/_pagination.scss +++ /dev/null @@ -1,11 +0,0 @@ -.pagination-nav { - border-top: 1px solid var(--ifm-sidebar-color-line); - - .pagination-nav__link { - border: none; - } - - .pagination-nav__sublabel { - display: none; - } -} diff --git a/apps/opik-documentation/documentation/src/css/components/_sidebar.scss b/apps/opik-documentation/documentation/src/css/components/_sidebar.scss deleted file mode 100644 index 47b8fe9a31..0000000000 --- a/apps/opik-documentation/documentation/src/css/components/_sidebar.scss +++ /dev/null @@ -1,64 +0,0 @@ -.menu { - overflow-y: auto; - font-size: 0.875rem; - font-weight: 400; - - padding-top: 1rem !important; - padding-bottom: 2rem !important; - padding-left: 1rem !important; - - --ifm-menu-link-padding-horizontal: 1rem; - - .menu__caret { - position: relative; - - &:hover::before { - background-color: #1f29370d; - } - - &::before { - background-size: contain; - background-repeat: no-repeat; - background-position: center; - } - - &:hover { - background: none; - } - } - - .menu__link--sublist-caret:after { - background: var(--ifm-menu-link-sublist-icon) 50% / 4rem 1.4rem; - } - - .menu__list-item:not(:first-child) { - margin-top: 0rem; - } - - .menu__link { - padding-left: 0.5rem; - // margin-left: 0.25rem; - } - - .menu__list .menu__list { - margin-bottom: 0.25rem; - } - .menu__list-item { - .menu__list { - position: relative; - margin-left: 0rem; - padding-left: 1.5rem; - // margin-left: 0.5rem; - - &::before { - content: ""; - position: absolute; - left: 0.75rem; - top: 0; - bottom: 0; - width: 1px; - background-color: var(--ifm-sidebar-color-line); - } - } - } -} diff --git a/apps/opik-documentation/documentation/src/css/custom.scss b/apps/opik-documentation/documentation/src/css/custom.scss deleted file mode 100644 index 993ace4bd3..0000000000 --- a/apps/opik-documentation/documentation/src/css/custom.scss +++ /dev/null @@ -1,78 +0,0 @@ -/** - * Any CSS included here will be global. The classic template - * bundles Infima by default. Infima is a CSS framework designed to - * work well for content-centric websites. - */ - -@use "./components/content"; -@use "./components/sidebar"; -@use "./components/pagination"; -@use "./components/code"; - -/* You can override the default Infima variables here. */ -:root { - --ifm-color-primary: #2e8555; - --ifm-color-primary-dark: #29784c; - --ifm-color-primary-darker: #277148; - --ifm-color-primary-darkest: #205d3b; - --ifm-color-primary-light: #33925d; - --ifm-color-primary-lighter: #359962; - --ifm-color-primary-lightest: #3cad6e; - --ifm-code-font-size: 90%; - - --docusaurus-highlighted-code-line-bg: rgba(0, 0, 0, 0.1); - - --ifm-font-family-base: ui-sans-serif, system-ui, -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, - "Helvetica Neue", Arial, "Noto Sans", sans-serif, "Apple Color Emoji", "Segoe UI Emoji", "Segoe UI Symbol", - "Noto Color Emoji"; - - --ifm-color-content: #334155; - --ifm-heading-color: #0f172a; - --ifm-heading-color-border: #e6e6e6b3; - - --ifm-sidebar-color-line: #e5e7eb; -} - -.header-external-link { - display: inline-flex; - align-items: center; -} - -.header-external-link:after { - background: url("data:image/svg+xml;charset=utf-8,%3Csvg xmlns='http://www.w3.org/2000/svg' width='14' height='14' viewBox='0 0 24 24' fill='none' stroke='currentColor' stroke-width='2' stroke-linecap='round' stroke-linejoin='round'%3E%3Cpath d='M18 13v6a2 2 0 0 1-2 2H5a2 2 0 0 1-2-2V8a2 2 0 0 1 2-2h6'%3E%3C/path%3E%3Cpolyline points='15 3 21 3 21 9'%3E%3C/polyline%3E%3Cline x1='10' y1='14' x2='21' y2='3'%3E%3C/line%3E%3C/svg%3E") - no-repeat; - content: ""; - display: inline-block; - height: 14px; - width: 14px; - margin-left: 4px; -} - -[data-theme="dark"] { - .header-external-link:after { - background: url("data:image/svg+xml;charset=utf-8,%3Csvg xmlns='http://www.w3.org/2000/svg' width='14' height='14' viewBox='0 0 24 24' fill='none' stroke='%23f1f5f9' stroke-width='2' stroke-linecap='round' stroke-linejoin='round'%3E%3Cpath d='M18 13v6a2 2 0 0 1-2 2H5a2 2 0 0 1-2-2V8a2 2 0 0 1 2-2h6'%3E%3C/path%3E%3Cpolyline points='15 3 21 3 21 9'%3E%3C/polyline%3E%3Cline x1='10' y1='14' x2='21' y2='3'%3E%3C/line%3E%3C/svg%3E") - no-repeat; - } -} - -.header-external-link:hover { - opacity: 0.6; -} - -/* For readability concerns, you should choose a lighter palette in dark mode. */ -[data-theme="dark"] { - --ifm-color-primary: #25c2a0; - --ifm-color-primary-dark: #21af90; - --ifm-color-primary-darker: #1fa588; - --ifm-color-primary-darkest: #1a8870; - --ifm-color-primary-light: #29d5b0; - --ifm-color-primary-lighter: #32d8b4; - --ifm-color-primary-lightest: #4fddbf; - --docusaurus-highlighted-code-line-bg: rgba(0, 0, 0, 0.3); - - --ifm-color-content: #e2e8f0; - --ifm-heading-color: #f1f5f9; - - --ifm-heading-color-border: #e0f3ff1a; - --ifm-sidebar-color-line: #262626; -} diff --git a/apps/opik-documentation/documentation/src/theme/DocItem/Content/index.tsx b/apps/opik-documentation/documentation/src/theme/DocItem/Content/index.tsx deleted file mode 100644 index 60f403dac2..0000000000 --- a/apps/opik-documentation/documentation/src/theme/DocItem/Content/index.tsx +++ /dev/null @@ -1,67 +0,0 @@ -import React from "react"; -import Content from "@theme-original/DocItem/Content"; -import type ContentType from "@theme/DocItem/Content"; -import type { WrapperProps } from "@docusaurus/types"; -import { useLocation } from "@docusaurus/router"; -import useDocusaurusContext from "@docusaurus/useDocusaurusContext"; -import clsx from "clsx"; - -import styles from "./styles.module.css"; - -import Tip from "@theme/Admonition/Icon/Tip"; - -type Props = WrapperProps; - -function NotebookBanner() { - const location = useLocation(); - const { siteConfig } = useDocusaurusContext(); - - const isCookbook = location.pathname.includes("cookbook/"); - const notebookPath = location.pathname - .replace(siteConfig.baseUrl, "/docs/") - .split("?")[0] // Remove URL parameters - .replace(/\/$/, ""); // Remove trailing slash - const githubNotebookPath = `https://github.com/comet-ml/opik/blob/main/apps/opik-documentation/documentation${notebookPath}.ipynb`; - const colabNotebookPath = `https://colab.research.google.com/github/comet-ml/opik/blob/main/apps/opik-documentation/documentation${notebookPath}.ipynb`; - - if (!isCookbook) { - return null; - } else { - return ( -
-
-
-
- -
-
This is a jupyter notebook
-
-
- - -
-
-
- ); - } -} - -export default function ContentWrapper(props: Props): JSX.Element { - return ( - <> - - - - ); -} diff --git a/apps/opik-documentation/documentation/src/theme/DocItem/Content/styles.module.css b/apps/opik-documentation/documentation/src/theme/DocItem/Content/styles.module.css deleted file mode 100644 index d1043db689..0000000000 --- a/apps/opik-documentation/documentation/src/theme/DocItem/Content/styles.module.css +++ /dev/null @@ -1,72 +0,0 @@ -.notebookBanner { - padding: 1rem; - padding-right: calc(1rem - var(--ifm-alert-border-width)); - margin-bottom: 1rem; -} - -.bannerContent { - display: flex; - justify-content: space-between; - align-items: center; -} - -.bannerLeft { - display: flex; - align-items: center; -} - -.bannerRight { - display: flex; - gap: 0.5rem; -} - -@media (max-width: 600px) { - .bannerLeft { - display: none; - } - - .bannerRight { - width: 100%; - justify-content: space-between; - } - - .notebookBannerButton { - flex: 1; - max-width: calc(50% - 0.25rem); /* Subtracting half of the gap */ - } -} - -.bannerIcon { - display: flex; - align-items: center; - margin-right: 0.5em; -} - -.bannerIcon svg { - display: block; - height: 1.2em; - width: 1.2em; - fill: var(--ifm-alert-foreground-color); -} - -.bannerText { - display: flex; - align-items: center; - font-size: 1em; - line-height: 1; -} - -.notebookBannerButton { - padding: 0.5rem 1rem; - background-color: var(--ifm-color-primary); - color: var(--ifm-color-white); - border: none; - border-radius: 4px; - cursor: pointer; - font-size: 0.875rem; - transition: background-color 0.2s; -} - -.notebookBannerButton:hover { - background-color: var(--ifm-color-primary-dark); -} diff --git a/apps/opik-documentation/documentation/src/theme/Navbar/Content/index.tsx b/apps/opik-documentation/documentation/src/theme/Navbar/Content/index.tsx deleted file mode 100644 index d11b7b3f63..0000000000 --- a/apps/opik-documentation/documentation/src/theme/Navbar/Content/index.tsx +++ /dev/null @@ -1,62 +0,0 @@ -import React from "react"; -import { useThemeConfig } from "@docusaurus/theme-common"; -import { splitNavbarItems, useNavbarMobileSidebar } from "@docusaurus/theme-common/internal"; -import NavbarItem from "@theme/NavbarItem"; -import NavbarColorModeToggle from "@theme/Navbar/ColorModeToggle"; -import SearchBar from "@theme/SearchBar"; -import NavbarMobileSidebarToggle from "@theme/Navbar/MobileSidebar/Toggle"; -import NavbarLogo from "@theme/Navbar/Logo"; -import NavbarSearch from "@theme/Navbar/Search"; -import GithubStarButton from "@site/src/components/GithubStarButton"; -import styles from "./styles.module.css"; - -function useNavbarItems() { - return useThemeConfig().navbar.items; -} - -function NavbarItems({ items }) { - return ( - <> - {items.map((item, i) => ( - - ))} - - ); -} - -function NavbarContentLayout({ left, right }) { - return ( -
-
{left}
-
{right}
-
- ); -} - -export default function NavbarContent() { - const mobileSidebar = useNavbarMobileSidebar(); - const items = useNavbarItems(); - let [leftItems, rightItems] = splitNavbarItems(items); - - return ( - - {!mobileSidebar.disabled && } - - - - } - right={ - <> - - - - - - - - } - /> - ); -} diff --git a/apps/opik-documentation/documentation/src/theme/Navbar/Content/styles.module.css b/apps/opik-documentation/documentation/src/theme/Navbar/Content/styles.module.css deleted file mode 100644 index 4c9471e109..0000000000 --- a/apps/opik-documentation/documentation/src/theme/Navbar/Content/styles.module.css +++ /dev/null @@ -1,8 +0,0 @@ -/* -Hide color mode toggle in small viewports - */ -@media (max-width: 996px) { - .colorModeToggle { - display: none; - } -} diff --git a/apps/opik-documentation/documentation/src/theme/Root.tsx b/apps/opik-documentation/documentation/src/theme/Root.tsx deleted file mode 100644 index a8df8db5e4..0000000000 --- a/apps/opik-documentation/documentation/src/theme/Root.tsx +++ /dev/null @@ -1,204 +0,0 @@ -import React, { useEffect } from "react"; -import { AnalyticsBrowser } from "@segment/analytics-next"; -import useDocusaurusContext from "@docusaurus/useDocusaurusContext"; -import { useLocation } from "@docusaurus/router"; - -// Initialize analytics once outside the component -let analytics: AnalyticsBrowser | null = null; - -const dify_embed_min_js = ` -!function() { - const n = "difyChatbotConfig" - , a = "dify-chatbot-bubble-button" - , c = "dify-chatbot-bubble-window" - , p = window[n] - , h = { - open: \` - - \`, - close: \` - - \` - }; - console.log("Dify chatbot loaded"); - - async function e() { - console.log("Dify chatbot loaded"); - if (p && p.token) { - var e = new URLSearchParams(await async function() { - var e = p?.inputs || {}; - const n = {}; - return await Promise.all(Object.entries(e).map(async ([e,t]) => { - n[e] = (e = t, - e = (new TextEncoder).encode(e), - e = new Response(new Blob([e]).stream().pipeThrough(new CompressionStream("gzip"))).arrayBuffer(), - e = new Uint8Array(await e), - await btoa(String.fromCharCode(...e))) - } - )), - n - }()); - const i = \`\${p.baseUrl || \`https://\${p.isDev ? "dev." : ""}udify.app\`}/chatbot/\${p.token}?\` + e; - function o() { - var e, t; - window.innerWidth <= 640 || (e = document.getElementById(c), - t = document.getElementById(a), - e && t && ((t = t.getBoundingClientRect()).top - 5 > e.clientHeight ? (e.style.bottom = t.height + 5 + "px", - e.style.top = "unset") : (e.style.bottom = "unset", - e.style.top = t.height + 5 + "px"), - t.right > e.clientWidth ? (e.style.right = "0", - e.style.left = "unset") : (e.style.right = "unset", - e.style.left = 0))) - } - function t() { - const n = document.createElement("div"); - Object.entries(p.containerProps || {}).forEach( ([e,t]) => { - "className" === e ? n.classList.add(...t.split(" ")) : "style" === e ? "object" == typeof t ? Object.assign(n.style, t) : n.style.cssText = t : "function" == typeof t ? n.addEventListener(e.replace(/^on/, "").toLowerCase(), t) : n[e] = t - } - ), - n.id = a; - var e = document.createElement("style"); - document.head.appendChild(e), - e.sheet.insertRule(\` - #\${n.id} { - position: fixed; - bottom: var(--\${n.id}-bottom, 1rem); - right: var(--\${n.id}-right, 1rem); - left: var(--\${n.id}-left, unset); - top: var(--\${n.id}-top, unset); - width: var(--\${n.id}-width, 50px); - height: var(--\${n.id}-height, 50px); - border-radius: var(--\${n.id}-border-radius, 25px); - background-color: var(--\${n.id}-bg-color, #155EEF); - box-shadow: var(--\${n.id}-box-shadow, rgba(0, 0, 0, 0.2) 0px 4px 8px 0px); - cursor: pointer; - z-index: 2147483647; - } - \`); - const t = document.createElement("div"); - if (t.style.cssText = "display: flex; align-items: center; justify-content: center; width: 100%; height: 100%; z-index: 2147483647;", - t.innerHTML = h.open, - n.appendChild(t), - document.body.appendChild(n), - n.addEventListener("click", function() { - var e = document.getElementById(c); - e ? (e.style.display = "none" === e.style.display ? "block" : "none", - t.innerHTML = "none" === e.style.display ? h.open : h.close, - "none" === e.style.display ? document.removeEventListener("keydown", d) : document.addEventListener("keydown", d), - o()) : (n.appendChild(((e = document.createElement("iframe")).allow = "fullscreen;microphone", - e.title = "dify chatbot bubble window", - e.id = c, - e.src = i, - e.style.cssText = \` - border: none; position: absolute; flex-direction: column; justify-content: space-between; - box-shadow: rgba(150, 150, 150, 0.2) 0px 10px 30px 0px, rgba(150, 150, 150, 0.2) 0px 0px 0px 1px; - bottom: 55px; right: 0; width: 24rem; max-width: calc(100vw - 2rem); height: 40rem; - max-height: calc(100vh - 6rem); border-radius: 0.75rem; display: flex; z-index: 2147483647; - overflow: hidden; left: unset; background-color: #F3F4F6;user-select: none; - \`, - e)), - o(), - this.title = "Exit (ESC)", - t.innerHTML = h.close, - document.addEventListener("keydown", d)) - }), - p.draggable) { - var s = n; - var l = p.dragAxis || "both"; - let i = !1, d, r; - s.addEventListener("mousedown", function(e) { - i = !0, - d = e.clientX - s.offsetLeft, - r = e.clientY - s.offsetTop - }), - document.addEventListener("mousemove", function(e) { - var t, n, o; - i && (s.style.transition = "none", - s.style.cursor = "grabbing", - (t = document.getElementById(c)) && (t.style.display = "none", - s.querySelector("div").innerHTML = h.open), - t = e.clientX - d, - e = window.innerHeight - e.clientY - r, - o = s.getBoundingClientRect(), - n = window.innerWidth - o.width, - o = window.innerHeight - o.height, - "x" !== l && "both" !== l || s.style.setProperty(\`--\${a}-left\`, Math.max(0, Math.min(t, n)) + "px"), - "y" !== l && "both" !== l || s.style.setProperty(\`--\${a}-bottom\`, Math.max(0, Math.min(e, o)) + "px")) - }), - document.addEventListener("mouseup", function() { - i = !1, - s.style.transition = "", - s.style.cursor = "pointer" - }) - } - } - 2048 < i.length && console.error("The URL is too long, please reduce the number of inputs to prevent the bot from failing to load"), - document.getElementById(a) || t() - } else - console.error(n + " is empty or token is not provided") - } - function d(e) { - var t; - "Escape" === e.key && (e = document.getElementById(c), - t = document.getElementById(a), - e) && "none" !== e.style.display && (e.style.display = "none", - t.querySelector("div").innerHTML = h.open) - } - document.addEventListener("keydown", d), - p?.dynamicScript ? e() : document.readyState === 'loading' ? document.addEventListener('DOMContentLoaded', e) : e(); -}();`; - -export default function Root({ children }) { - const { siteConfig } = useDocusaurusContext(); - const { segmentWriteKey } = siteConfig.customFields as { segmentWriteKey: string }; - const location = useLocation(); - - // Initialize analytics only once if not already initialized - if (!analytics) { - analytics = AnalyticsBrowser.load({ writeKey: segmentWriteKey }); - } - - useEffect(() => { - // Initialize Dify chatbot - const script1 = document.createElement("script"); - script1.textContent = `window.difyChatbotConfig = { - token: 'fsuGIcZVsGayZOB2' - }`; - document.body.appendChild(script1); - - const script2 = document.createElement("script"); - script2.textContent = dify_embed_min_js; - script2.id = "fsuGIcZVsGayZOB2"; - document.head.appendChild(script2); - - const style = document.createElement("style"); - style.textContent = ` - #dify-chatbot-bubble-button { - background-color: #1C64F2 !important; - } - #dify-chatbot-bubble-window { - width: 24rem !important; - height: 40rem !important; - } - `; - document.head.appendChild(style); - - return () => { - // Cleanup on unmount - script1.remove(); - script2.remove(); - style.remove(); - }; - }, []); // Run once on mount - - useEffect(() => { - // Track page view whenever location changes - analytics?.page({ - path: location.pathname, - url: window.location.href, - title: document.title, - }); - }, [location]); - - return <>{children}; -} diff --git a/apps/opik-documentation/documentation/static/.nojekyll b/apps/opik-documentation/documentation/static/.nojekyll deleted file mode 100644 index e69de29bb2..0000000000 diff --git a/apps/opik-documentation/documentation/static/README.md b/apps/opik-documentation/documentation/static/README.md new file mode 100644 index 0000000000..eb8e57f377 --- /dev/null +++ b/apps/opik-documentation/documentation/static/README.md @@ -0,0 +1,5 @@ +## Legacy folder - Should not be used + +This is a legacy folder that should not be used. It remains here for backwards compatibility reasons. + +All images should be added to the fern/img folder. diff --git a/apps/opik-documentation/documentation/static/img/changelog/2024-10-14/experiment_page_filtering.png b/apps/opik-documentation/documentation/static/img/changelog/2024-10-14/experiment_page_filtering.png index 92125a6d7b..214c497e6c 100644 Binary files a/apps/opik-documentation/documentation/static/img/changelog/2024-10-14/experiment_page_filtering.png and b/apps/opik-documentation/documentation/static/img/changelog/2024-10-14/experiment_page_filtering.png differ diff --git a/apps/opik-documentation/documentation/static/img/changelog/2024-10-21/download_traces.png b/apps/opik-documentation/documentation/static/img/changelog/2024-10-21/download_traces.png index afa18d5bd1..ef2709e6b0 100644 Binary files a/apps/opik-documentation/documentation/static/img/changelog/2024-10-21/download_traces.png and b/apps/opik-documentation/documentation/static/img/changelog/2024-10-21/download_traces.png differ diff --git a/apps/opik-documentation/documentation/static/img/changelog/2024-10-21/quickstart_guide.png b/apps/opik-documentation/documentation/static/img/changelog/2024-10-21/quickstart_guide.png index c48faefdc8..a9003e6b39 100644 Binary files a/apps/opik-documentation/documentation/static/img/changelog/2024-10-21/quickstart_guide.png and b/apps/opik-documentation/documentation/static/img/changelog/2024-10-21/quickstart_guide.png differ diff --git a/apps/opik-documentation/documentation/static/img/changelog/2024-11-04/prompt_library_versions.png b/apps/opik-documentation/documentation/static/img/changelog/2024-11-04/prompt_library_versions.png index b6445fab94..5f7e0d7287 100644 Binary files a/apps/opik-documentation/documentation/static/img/changelog/2024-11-04/prompt_library_versions.png and b/apps/opik-documentation/documentation/static/img/changelog/2024-11-04/prompt_library_versions.png differ diff --git a/apps/opik-documentation/documentation/static/img/changelog/2024-11-11/experiment_summary.png b/apps/opik-documentation/documentation/static/img/changelog/2024-11-11/experiment_summary.png index c49ccb369c..a7da109b2f 100644 Binary files a/apps/opik-documentation/documentation/static/img/changelog/2024-11-11/experiment_summary.png and b/apps/opik-documentation/documentation/static/img/changelog/2024-11-11/experiment_summary.png differ diff --git a/apps/opik-documentation/documentation/static/img/changelog/2024-11-25/experiment_item_sidebar.png b/apps/opik-documentation/documentation/static/img/changelog/2024-11-25/experiment_item_sidebar.png index fc16a428aa..0178a7e001 100644 Binary files a/apps/opik-documentation/documentation/static/img/changelog/2024-11-25/experiment_item_sidebar.png and b/apps/opik-documentation/documentation/static/img/changelog/2024-11-25/experiment_item_sidebar.png differ diff --git a/apps/opik-documentation/documentation/static/img/changelog/2024-11-25/project_dashboard.png b/apps/opik-documentation/documentation/static/img/changelog/2024-11-25/project_dashboard.png index 850803c92f..6bfce257db 100644 Binary files a/apps/opik-documentation/documentation/static/img/changelog/2024-11-25/project_dashboard.png and b/apps/opik-documentation/documentation/static/img/changelog/2024-11-25/project_dashboard.png differ diff --git a/apps/opik-documentation/documentation/static/img/changelog/2024-11-25/project_statistics.png b/apps/opik-documentation/documentation/static/img/changelog/2024-11-25/project_statistics.png index da238498fd..9646e2ef24 100644 Binary files a/apps/opik-documentation/documentation/static/img/changelog/2024-11-25/project_statistics.png and b/apps/opik-documentation/documentation/static/img/changelog/2024-11-25/project_statistics.png differ diff --git a/apps/opik-documentation/documentation/static/img/changelog/2024-12-09/experiment_items_table.png b/apps/opik-documentation/documentation/static/img/changelog/2024-12-09/experiment_items_table.png index b65915d1da..8f9e445766 100644 Binary files a/apps/opik-documentation/documentation/static/img/changelog/2024-12-09/experiment_items_table.png and b/apps/opik-documentation/documentation/static/img/changelog/2024-12-09/experiment_items_table.png differ diff --git a/apps/opik-documentation/documentation/static/img/changelog/2024-12-16/playground.png b/apps/opik-documentation/documentation/static/img/changelog/2024-12-16/playground.png index 7c8f95e35a..51d5481c43 100644 Binary files a/apps/opik-documentation/documentation/static/img/changelog/2024-12-16/playground.png and b/apps/opik-documentation/documentation/static/img/changelog/2024-12-16/playground.png differ diff --git a/apps/opik-documentation/documentation/static/img/cookbook/aisuite_trace_cookbook.png b/apps/opik-documentation/documentation/static/img/cookbook/aisuite_trace_cookbook.png index f949d217af..c233be0f1b 100644 Binary files a/apps/opik-documentation/documentation/static/img/cookbook/aisuite_trace_cookbook.png and b/apps/opik-documentation/documentation/static/img/cookbook/aisuite_trace_cookbook.png differ diff --git a/apps/opik-documentation/documentation/static/img/cookbook/aisuite_trace_decorator_cookbook.png b/apps/opik-documentation/documentation/static/img/cookbook/aisuite_trace_decorator_cookbook.png index e3328443f7..2684cdcb19 100644 Binary files a/apps/opik-documentation/documentation/static/img/cookbook/aisuite_trace_decorator_cookbook.png and b/apps/opik-documentation/documentation/static/img/cookbook/aisuite_trace_decorator_cookbook.png differ diff --git a/apps/opik-documentation/documentation/static/img/cookbook/anthropic_trace_cookbook.png b/apps/opik-documentation/documentation/static/img/cookbook/anthropic_trace_cookbook.png index 894d816ff9..1ce391c7b3 100644 Binary files a/apps/opik-documentation/documentation/static/img/cookbook/anthropic_trace_cookbook.png and b/apps/opik-documentation/documentation/static/img/cookbook/anthropic_trace_cookbook.png differ diff --git a/apps/opik-documentation/documentation/static/img/cookbook/anthropic_trace_decorator_cookbook.png b/apps/opik-documentation/documentation/static/img/cookbook/anthropic_trace_decorator_cookbook.png index b0fe163e16..c337bfe7c7 100644 Binary files a/apps/opik-documentation/documentation/static/img/cookbook/anthropic_trace_decorator_cookbook.png and b/apps/opik-documentation/documentation/static/img/cookbook/anthropic_trace_decorator_cookbook.png differ diff --git a/apps/opik-documentation/documentation/static/img/cookbook/bedrock_trace_cookbook.png b/apps/opik-documentation/documentation/static/img/cookbook/bedrock_trace_cookbook.png index 13e80d762b..bc137a10dd 100644 Binary files a/apps/opik-documentation/documentation/static/img/cookbook/bedrock_trace_cookbook.png and b/apps/opik-documentation/documentation/static/img/cookbook/bedrock_trace_cookbook.png differ diff --git a/apps/opik-documentation/documentation/static/img/cookbook/bedrock_trace_decorator_cookbook.png b/apps/opik-documentation/documentation/static/img/cookbook/bedrock_trace_decorator_cookbook.png index e42c292c40..6b59f4cec0 100644 Binary files a/apps/opik-documentation/documentation/static/img/cookbook/bedrock_trace_decorator_cookbook.png and b/apps/opik-documentation/documentation/static/img/cookbook/bedrock_trace_decorator_cookbook.png differ diff --git a/apps/opik-documentation/documentation/static/img/cookbook/bedrock_trace_streaming_cookbook.png b/apps/opik-documentation/documentation/static/img/cookbook/bedrock_trace_streaming_cookbook.png index 77c487f0d8..8bcec47734 100644 Binary files a/apps/opik-documentation/documentation/static/img/cookbook/bedrock_trace_streaming_cookbook.png and b/apps/opik-documentation/documentation/static/img/cookbook/bedrock_trace_streaming_cookbook.png differ diff --git a/apps/opik-documentation/documentation/static/img/cookbook/chain_density_experiment_cookbook.png b/apps/opik-documentation/documentation/static/img/cookbook/chain_density_experiment_cookbook.png index 1f5510ea78..b70617f02a 100644 Binary files a/apps/opik-documentation/documentation/static/img/cookbook/chain_density_experiment_cookbook.png and b/apps/opik-documentation/documentation/static/img/cookbook/chain_density_experiment_cookbook.png differ diff --git a/apps/opik-documentation/documentation/static/img/cookbook/chain_density_trace_comparison_cookbook.png b/apps/opik-documentation/documentation/static/img/cookbook/chain_density_trace_comparison_cookbook.png index 8d90f18d97..25432cbbaf 100644 Binary files a/apps/opik-documentation/documentation/static/img/cookbook/chain_density_trace_comparison_cookbook.png and b/apps/opik-documentation/documentation/static/img/cookbook/chain_density_trace_comparison_cookbook.png differ diff --git a/apps/opik-documentation/documentation/static/img/cookbook/chain_density_trace_cookbook.png b/apps/opik-documentation/documentation/static/img/cookbook/chain_density_trace_cookbook.png index 6c060a029f..18864edff0 100644 Binary files a/apps/opik-documentation/documentation/static/img/cookbook/chain_density_trace_cookbook.png and b/apps/opik-documentation/documentation/static/img/cookbook/chain_density_trace_cookbook.png differ diff --git a/apps/opik-documentation/documentation/static/img/cookbook/crewai_trace_cookbook.png b/apps/opik-documentation/documentation/static/img/cookbook/crewai_trace_cookbook.png index 614884f0bf..80dc6fd8a4 100644 Binary files a/apps/opik-documentation/documentation/static/img/cookbook/crewai_trace_cookbook.png and b/apps/opik-documentation/documentation/static/img/cookbook/crewai_trace_cookbook.png differ diff --git a/apps/opik-documentation/documentation/static/img/cookbook/dspy_trace_cookbook.png b/apps/opik-documentation/documentation/static/img/cookbook/dspy_trace_cookbook.png index 97c966f34e..2328d46f77 100644 Binary files a/apps/opik-documentation/documentation/static/img/cookbook/dspy_trace_cookbook.png and b/apps/opik-documentation/documentation/static/img/cookbook/dspy_trace_cookbook.png differ diff --git a/apps/opik-documentation/documentation/static/img/cookbook/gemini_trace_cookbook.png b/apps/opik-documentation/documentation/static/img/cookbook/gemini_trace_cookbook.png index 4dd78e089c..8ced88ea2e 100644 Binary files a/apps/opik-documentation/documentation/static/img/cookbook/gemini_trace_cookbook.png and b/apps/opik-documentation/documentation/static/img/cookbook/gemini_trace_cookbook.png differ diff --git a/apps/opik-documentation/documentation/static/img/cookbook/gemini_trace_decorator_cookbook.png b/apps/opik-documentation/documentation/static/img/cookbook/gemini_trace_decorator_cookbook.png index f9c0d8808c..7c3571ff7b 100644 Binary files a/apps/opik-documentation/documentation/static/img/cookbook/gemini_trace_decorator_cookbook.png and b/apps/opik-documentation/documentation/static/img/cookbook/gemini_trace_decorator_cookbook.png differ diff --git a/apps/opik-documentation/documentation/static/img/cookbook/groq_trace_cookbook.png b/apps/opik-documentation/documentation/static/img/cookbook/groq_trace_cookbook.png index 9d0e97bc49..67af0e8e7c 100644 Binary files a/apps/opik-documentation/documentation/static/img/cookbook/groq_trace_cookbook.png and b/apps/opik-documentation/documentation/static/img/cookbook/groq_trace_cookbook.png differ diff --git a/apps/opik-documentation/documentation/static/img/cookbook/groq_trace_decorator_cookbook.png b/apps/opik-documentation/documentation/static/img/cookbook/groq_trace_decorator_cookbook.png index 12b57ed626..ecfd258f3e 100644 Binary files a/apps/opik-documentation/documentation/static/img/cookbook/groq_trace_decorator_cookbook.png and b/apps/opik-documentation/documentation/static/img/cookbook/groq_trace_decorator_cookbook.png differ diff --git a/apps/opik-documentation/documentation/static/img/cookbook/guardrails_ai_traces_cookbook.png b/apps/opik-documentation/documentation/static/img/cookbook/guardrails_ai_traces_cookbook.png index 7fd232222d..13d564af2a 100644 Binary files a/apps/opik-documentation/documentation/static/img/cookbook/guardrails_ai_traces_cookbook.png and b/apps/opik-documentation/documentation/static/img/cookbook/guardrails_ai_traces_cookbook.png differ diff --git a/apps/opik-documentation/documentation/static/img/cookbook/hallucination_metric_cookbook.png b/apps/opik-documentation/documentation/static/img/cookbook/hallucination_metric_cookbook.png index 6a34512d28..9e11e38f5e 100644 Binary files a/apps/opik-documentation/documentation/static/img/cookbook/hallucination_metric_cookbook.png and b/apps/opik-documentation/documentation/static/img/cookbook/hallucination_metric_cookbook.png differ diff --git a/apps/opik-documentation/documentation/static/img/cookbook/haystack_trace_cookbook.png b/apps/opik-documentation/documentation/static/img/cookbook/haystack_trace_cookbook.png index e9ee6c3c91..38a8b58ddf 100644 Binary files a/apps/opik-documentation/documentation/static/img/cookbook/haystack_trace_cookbook.png and b/apps/opik-documentation/documentation/static/img/cookbook/haystack_trace_cookbook.png differ diff --git a/apps/opik-documentation/documentation/static/img/cookbook/langchain_cookbook.png b/apps/opik-documentation/documentation/static/img/cookbook/langchain_cookbook.png index 75894b541f..fd7010fc74 100644 Binary files a/apps/opik-documentation/documentation/static/img/cookbook/langchain_cookbook.png and b/apps/opik-documentation/documentation/static/img/cookbook/langchain_cookbook.png differ diff --git a/apps/opik-documentation/documentation/static/img/cookbook/langgraph_cookbook.png b/apps/opik-documentation/documentation/static/img/cookbook/langgraph_cookbook.png index dacc346fe0..11a1b5a6ce 100644 Binary files a/apps/opik-documentation/documentation/static/img/cookbook/langgraph_cookbook.png and b/apps/opik-documentation/documentation/static/img/cookbook/langgraph_cookbook.png differ diff --git a/apps/opik-documentation/documentation/static/img/cookbook/litellm_cookbook.png b/apps/opik-documentation/documentation/static/img/cookbook/litellm_cookbook.png index 2aeadde2e6..8a8ed48827 100644 Binary files a/apps/opik-documentation/documentation/static/img/cookbook/litellm_cookbook.png and b/apps/opik-documentation/documentation/static/img/cookbook/litellm_cookbook.png differ diff --git a/apps/opik-documentation/documentation/static/img/cookbook/llamaIndex_cookbook.png b/apps/opik-documentation/documentation/static/img/cookbook/llamaIndex_cookbook.png index 215d701c78..b8ee71d4fa 100644 Binary files a/apps/opik-documentation/documentation/static/img/cookbook/llamaIndex_cookbook.png and b/apps/opik-documentation/documentation/static/img/cookbook/llamaIndex_cookbook.png differ diff --git a/apps/opik-documentation/documentation/static/img/cookbook/moderation_metric_cookbook.png b/apps/opik-documentation/documentation/static/img/cookbook/moderation_metric_cookbook.png index c1e129e216..7ea60f4254 100644 Binary files a/apps/opik-documentation/documentation/static/img/cookbook/moderation_metric_cookbook.png and b/apps/opik-documentation/documentation/static/img/cookbook/moderation_metric_cookbook.png differ diff --git a/apps/opik-documentation/documentation/static/img/cookbook/ollama_cookbook.png b/apps/opik-documentation/documentation/static/img/cookbook/ollama_cookbook.png index 8f08b20607..3912fa5492 100644 Binary files a/apps/opik-documentation/documentation/static/img/cookbook/ollama_cookbook.png and b/apps/opik-documentation/documentation/static/img/cookbook/ollama_cookbook.png differ diff --git a/apps/opik-documentation/documentation/static/img/cookbook/openai_trace_cookbook.png b/apps/opik-documentation/documentation/static/img/cookbook/openai_trace_cookbook.png index 759887448f..48d8f76511 100644 Binary files a/apps/opik-documentation/documentation/static/img/cookbook/openai_trace_cookbook.png and b/apps/opik-documentation/documentation/static/img/cookbook/openai_trace_cookbook.png differ diff --git a/apps/opik-documentation/documentation/static/img/cookbook/openai_trace_decorator_cookbook.png b/apps/opik-documentation/documentation/static/img/cookbook/openai_trace_decorator_cookbook.png index 029e881afd..53796292c2 100644 Binary files a/apps/opik-documentation/documentation/static/img/cookbook/openai_trace_decorator_cookbook.png and b/apps/opik-documentation/documentation/static/img/cookbook/openai_trace_decorator_cookbook.png differ diff --git a/apps/opik-documentation/documentation/static/img/cookbook/watsonx_trace_cookbook.png b/apps/opik-documentation/documentation/static/img/cookbook/watsonx_trace_cookbook.png index 8ae46b0ef1..e91be42745 100644 Binary files a/apps/opik-documentation/documentation/static/img/cookbook/watsonx_trace_cookbook.png and b/apps/opik-documentation/documentation/static/img/cookbook/watsonx_trace_cookbook.png differ diff --git a/apps/opik-documentation/documentation/static/img/cookbook/watsonx_trace_decorator_cookbook.png b/apps/opik-documentation/documentation/static/img/cookbook/watsonx_trace_decorator_cookbook.png index 84c12be1ea..db7011fa92 100644 Binary files a/apps/opik-documentation/documentation/static/img/cookbook/watsonx_trace_decorator_cookbook.png and b/apps/opik-documentation/documentation/static/img/cookbook/watsonx_trace_decorator_cookbook.png differ diff --git a/apps/opik-documentation/documentation/static/img/evaluation/compare_experiment_config.png b/apps/opik-documentation/documentation/static/img/evaluation/compare_experiment_config.png index 8633e0c01b..f7186155a0 100644 Binary files a/apps/opik-documentation/documentation/static/img/evaluation/compare_experiment_config.png and b/apps/opik-documentation/documentation/static/img/evaluation/compare_experiment_config.png differ diff --git a/apps/opik-documentation/documentation/static/img/evaluation/dataset_items_page.png b/apps/opik-documentation/documentation/static/img/evaluation/dataset_items_page.png index cd22dcc4cd..f64a522992 100644 Binary files a/apps/opik-documentation/documentation/static/img/evaluation/dataset_items_page.png and b/apps/opik-documentation/documentation/static/img/evaluation/dataset_items_page.png differ diff --git a/apps/opik-documentation/documentation/static/img/evaluation/evaluation_concepts.png b/apps/opik-documentation/documentation/static/img/evaluation/evaluation_concepts.png index 60464d3c38..1baee11eed 100644 Binary files a/apps/opik-documentation/documentation/static/img/evaluation/evaluation_concepts.png and b/apps/opik-documentation/documentation/static/img/evaluation/evaluation_concepts.png differ diff --git a/apps/opik-documentation/documentation/static/img/evaluation/experiment_items.png b/apps/opik-documentation/documentation/static/img/evaluation/experiment_items.png index 7b8c7deb1d..8c547d4eae 100644 Binary files a/apps/opik-documentation/documentation/static/img/evaluation/experiment_items.png and b/apps/opik-documentation/documentation/static/img/evaluation/experiment_items.png differ diff --git a/apps/opik-documentation/documentation/static/img/evaluation/linked_prompt.png b/apps/opik-documentation/documentation/static/img/evaluation/linked_prompt.png index 622a7bbfac..c8ebd856c1 100644 Binary files a/apps/opik-documentation/documentation/static/img/evaluation/linked_prompt.png and b/apps/opik-documentation/documentation/static/img/evaluation/linked_prompt.png differ diff --git a/apps/opik-documentation/documentation/static/img/evaluation/playground.png b/apps/opik-documentation/documentation/static/img/evaluation/playground.png index 7c8f95e35a..51d5481c43 100644 Binary files a/apps/opik-documentation/documentation/static/img/evaluation/playground.png and b/apps/opik-documentation/documentation/static/img/evaluation/playground.png differ diff --git a/apps/opik-documentation/documentation/static/img/evaluation/playground_conversations.png b/apps/opik-documentation/documentation/static/img/evaluation/playground_conversations.png index 68a377cc65..ac3cc38411 100644 Binary files a/apps/opik-documentation/documentation/static/img/evaluation/playground_conversations.png and b/apps/opik-documentation/documentation/static/img/evaluation/playground_conversations.png differ diff --git a/apps/opik-documentation/documentation/static/img/evaluation/playground_evaluation.png b/apps/opik-documentation/documentation/static/img/evaluation/playground_evaluation.png index 417e24dc37..04df606c16 100644 Binary files a/apps/opik-documentation/documentation/static/img/evaluation/playground_evaluation.png and b/apps/opik-documentation/documentation/static/img/evaluation/playground_evaluation.png differ diff --git a/apps/opik-documentation/documentation/static/img/home/traces_page_for_quickstart.png b/apps/opik-documentation/documentation/static/img/home/traces_page_for_quickstart.png index f259aa1f20..0c816a61b1 100644 Binary files a/apps/opik-documentation/documentation/static/img/home/traces_page_for_quickstart.png and b/apps/opik-documentation/documentation/static/img/home/traces_page_for_quickstart.png differ diff --git a/apps/opik-documentation/documentation/static/img/home/traces_page_with_sidebar.png b/apps/opik-documentation/documentation/static/img/home/traces_page_with_sidebar.png index 7277bc09f3..d180031715 100644 Binary files a/apps/opik-documentation/documentation/static/img/home/traces_page_with_sidebar.png and b/apps/opik-documentation/documentation/static/img/home/traces_page_with_sidebar.png differ diff --git a/apps/opik-documentation/documentation/static/img/opik-evaluate.png b/apps/opik-documentation/documentation/static/img/opik-evaluate.png index cc6c8dd0d2..7e84480efd 100644 Binary files a/apps/opik-documentation/documentation/static/img/opik-evaluate.png and b/apps/opik-documentation/documentation/static/img/opik-evaluate.png differ diff --git a/apps/opik-documentation/documentation/static/img/opik-log-traces.png b/apps/opik-documentation/documentation/static/img/opik-log-traces.png index c6deb6aa38..0ca1b98402 100644 Binary files a/apps/opik-documentation/documentation/static/img/opik-log-traces.png and b/apps/opik-documentation/documentation/static/img/opik-log-traces.png differ diff --git a/apps/opik-documentation/documentation/static/img/opik-production.png b/apps/opik-documentation/documentation/static/img/opik-production.png index 88deede5c4..57e4ac4a1f 100644 Binary files a/apps/opik-documentation/documentation/static/img/opik-production.png and b/apps/opik-documentation/documentation/static/img/opik-production.png differ diff --git a/apps/opik-documentation/documentation/static/img/opik-project-dashboard.png b/apps/opik-documentation/documentation/static/img/opik-project-dashboard.png index 4264afde52..cf690a54df 100644 Binary files a/apps/opik-documentation/documentation/static/img/opik-project-dashboard.png and b/apps/opik-documentation/documentation/static/img/opik-project-dashboard.png differ diff --git a/apps/opik-documentation/documentation/static/img/production/online_evaluation_built_in_metrics.png b/apps/opik-documentation/documentation/static/img/production/online_evaluation_built_in_metrics.png index c84e15c6c0..e4464f2006 100644 Binary files a/apps/opik-documentation/documentation/static/img/production/online_evaluation_built_in_metrics.png and b/apps/opik-documentation/documentation/static/img/production/online_evaluation_built_in_metrics.png differ diff --git a/apps/opik-documentation/documentation/static/img/production/online_evaluation_custom_judge.png b/apps/opik-documentation/documentation/static/img/production/online_evaluation_custom_judge.png index 17d7552e19..f871c0d4d1 100644 Binary files a/apps/opik-documentation/documentation/static/img/production/online_evaluation_custom_judge.png and b/apps/opik-documentation/documentation/static/img/production/online_evaluation_custom_judge.png differ diff --git a/apps/opik-documentation/documentation/static/img/production/online_evaluation_rule_modal.png b/apps/opik-documentation/documentation/static/img/production/online_evaluation_rule_modal.png index c8250d69dc..42675823e9 100644 Binary files a/apps/opik-documentation/documentation/static/img/production/online_evaluation_rule_modal.png and b/apps/opik-documentation/documentation/static/img/production/online_evaluation_rule_modal.png differ diff --git a/apps/opik-documentation/documentation/static/img/production/opik-kong-gateway.png b/apps/opik-documentation/documentation/static/img/production/opik-kong-gateway.png index bdf318c0bb..81ca5b4a5a 100644 Binary files a/apps/opik-documentation/documentation/static/img/production/opik-kong-gateway.png and b/apps/opik-documentation/documentation/static/img/production/opik-kong-gateway.png differ diff --git a/apps/opik-documentation/documentation/static/img/prompt_engineering/prompt_library.png b/apps/opik-documentation/documentation/static/img/prompt_engineering/prompt_library.png index f30c9f7eda..f00b8dfd94 100644 Binary files a/apps/opik-documentation/documentation/static/img/prompt_engineering/prompt_library.png and b/apps/opik-documentation/documentation/static/img/prompt_engineering/prompt_library.png differ diff --git a/apps/opik-documentation/documentation/static/img/prompt_engineering/prompt_library_versions.png b/apps/opik-documentation/documentation/static/img/prompt_engineering/prompt_library_versions.png index b6445fab94..5f7e0d7287 100644 Binary files a/apps/opik-documentation/documentation/static/img/prompt_engineering/prompt_library_versions.png and b/apps/opik-documentation/documentation/static/img/prompt_engineering/prompt_library_versions.png differ diff --git a/apps/opik-documentation/documentation/static/img/testing/test_experiments.png b/apps/opik-documentation/documentation/static/img/testing/test_experiments.png index 299ac2dcdd..ae76e92a2d 100644 Binary files a/apps/opik-documentation/documentation/static/img/testing/test_experiments.png and b/apps/opik-documentation/documentation/static/img/testing/test_experiments.png differ diff --git a/apps/opik-documentation/documentation/static/img/tracing/agent_definition.png b/apps/opik-documentation/documentation/static/img/tracing/agent_definition.png index cb792e8da3..2a853346eb 100644 Binary files a/apps/opik-documentation/documentation/static/img/tracing/agent_definition.png and b/apps/opik-documentation/documentation/static/img/tracing/agent_definition.png differ diff --git a/apps/opik-documentation/documentation/static/img/tracing/agent_execution_flow.png b/apps/opik-documentation/documentation/static/img/tracing/agent_execution_flow.png index 09fc991f50..a96efa4395 100644 Binary files a/apps/opik-documentation/documentation/static/img/tracing/agent_execution_flow.png and b/apps/opik-documentation/documentation/static/img/tracing/agent_execution_flow.png differ diff --git a/apps/opik-documentation/documentation/static/img/tracing/annotate_traces.png b/apps/opik-documentation/documentation/static/img/tracing/annotate_traces.png index ebca15ccdd..b72f7fc268 100644 Binary files a/apps/opik-documentation/documentation/static/img/tracing/annotate_traces.png and b/apps/opik-documentation/documentation/static/img/tracing/annotate_traces.png differ diff --git a/apps/opik-documentation/documentation/static/img/tracing/cost_tracking_project.png b/apps/opik-documentation/documentation/static/img/tracing/cost_tracking_project.png index 764c9ba598..f8ed2bc9fb 100644 Binary files a/apps/opik-documentation/documentation/static/img/tracing/cost_tracking_project.png and b/apps/opik-documentation/documentation/static/img/tracing/cost_tracking_project.png differ diff --git a/apps/opik-documentation/documentation/static/img/tracing/cost_tracking_project_metrics.png b/apps/opik-documentation/documentation/static/img/tracing/cost_tracking_project_metrics.png index 9533d53809..4953bebb29 100644 Binary files a/apps/opik-documentation/documentation/static/img/tracing/cost_tracking_project_metrics.png and b/apps/opik-documentation/documentation/static/img/tracing/cost_tracking_project_metrics.png differ diff --git a/apps/opik-documentation/documentation/static/img/tracing/cost_tracking_span.png b/apps/opik-documentation/documentation/static/img/tracing/cost_tracking_span.png index ef5b162cf2..4917532cbe 100644 Binary files a/apps/opik-documentation/documentation/static/img/tracing/cost_tracking_span.png and b/apps/opik-documentation/documentation/static/img/tracing/cost_tracking_span.png differ diff --git a/apps/opik-documentation/documentation/static/img/tracing/cost_tracking_trace_view.png b/apps/opik-documentation/documentation/static/img/tracing/cost_tracking_trace_view.png index f7ef5716b4..72673d4122 100644 Binary files a/apps/opik-documentation/documentation/static/img/tracing/cost_tracking_trace_view.png and b/apps/opik-documentation/documentation/static/img/tracing/cost_tracking_trace_view.png differ diff --git a/apps/opik-documentation/documentation/static/img/tracing/dify_configuration.png b/apps/opik-documentation/documentation/static/img/tracing/dify_configuration.png index 92abc5c917..411fb40f81 100644 Binary files a/apps/opik-documentation/documentation/static/img/tracing/dify_configuration.png and b/apps/opik-documentation/documentation/static/img/tracing/dify_configuration.png differ diff --git a/apps/opik-documentation/documentation/static/img/tracing/dify_view_project.png b/apps/opik-documentation/documentation/static/img/tracing/dify_view_project.png index 936fb3e2bd..beb62bf635 100644 Binary files a/apps/opik-documentation/documentation/static/img/tracing/dify_view_project.png and b/apps/opik-documentation/documentation/static/img/tracing/dify_view_project.png differ diff --git a/apps/opik-documentation/documentation/static/img/tracing/download_traces.png b/apps/opik-documentation/documentation/static/img/tracing/download_traces.png index 850bac2fec..572a78c875 100644 Binary files a/apps/opik-documentation/documentation/static/img/tracing/download_traces.png and b/apps/opik-documentation/documentation/static/img/tracing/download_traces.png differ diff --git a/apps/opik-documentation/documentation/static/img/tracing/image_trace.png b/apps/opik-documentation/documentation/static/img/tracing/image_trace.png index 965a30b4fa..40df9598d7 100644 Binary files a/apps/opik-documentation/documentation/static/img/tracing/image_trace.png and b/apps/opik-documentation/documentation/static/img/tracing/image_trace.png differ diff --git a/apps/opik-documentation/documentation/static/img/tracing/introduction.png b/apps/opik-documentation/documentation/static/img/tracing/introduction.png index 109ede50cb..8d2edd143d 100644 Binary files a/apps/opik-documentation/documentation/static/img/tracing/introduction.png and b/apps/opik-documentation/documentation/static/img/tracing/introduction.png differ diff --git a/apps/opik-documentation/documentation/static/img/tracing/llama_index_integration.png b/apps/opik-documentation/documentation/static/img/tracing/llama_index_integration.png index ac25a43a36..17eff17e1c 100644 Binary files a/apps/opik-documentation/documentation/static/img/tracing/llama_index_integration.png and b/apps/opik-documentation/documentation/static/img/tracing/llama_index_integration.png differ diff --git a/apps/opik-documentation/documentation/static/img/tracing/opik_monitoring_dashboard.png b/apps/opik-documentation/documentation/static/img/tracing/opik_monitoring_dashboard.png index 850803c92f..6bfce257db 100644 Binary files a/apps/opik-documentation/documentation/static/img/tracing/opik_monitoring_dashboard.png and b/apps/opik-documentation/documentation/static/img/tracing/opik_monitoring_dashboard.png differ diff --git a/apps/opik-documentation/documentation/static/img/tracing/predibase_opik_trace.png b/apps/opik-documentation/documentation/static/img/tracing/predibase_opik_trace.png index a63424a651..bcc2e6f320 100644 Binary files a/apps/opik-documentation/documentation/static/img/tracing/predibase_opik_trace.png and b/apps/opik-documentation/documentation/static/img/tracing/predibase_opik_trace.png differ diff --git a/apps/opik-documentation/documentation/static/img/tracing/ragas_opik_trace.png b/apps/opik-documentation/documentation/static/img/tracing/ragas_opik_trace.png index f5f53e0fe9..94fba3f03f 100644 Binary files a/apps/opik-documentation/documentation/static/img/tracing/ragas_opik_trace.png and b/apps/opik-documentation/documentation/static/img/tracing/ragas_opik_trace.png differ diff --git a/apps/opik-documentation/documentation/tsconfig.json b/apps/opik-documentation/documentation/tsconfig.json deleted file mode 100644 index 314eab8a41..0000000000 --- a/apps/opik-documentation/documentation/tsconfig.json +++ /dev/null @@ -1,7 +0,0 @@ -{ - // This file is not used in compilation. It is here just for a nice editor experience. - "extends": "@docusaurus/tsconfig", - "compilerOptions": { - "baseUrl": "." - } -} diff --git a/apps/opik-documentation/documentation/update_cookbooks.sh b/apps/opik-documentation/documentation/update_cookbooks.sh new file mode 100644 index 0000000000..557e22cf38 --- /dev/null +++ b/apps/opik-documentation/documentation/update_cookbooks.sh @@ -0,0 +1,5 @@ +#!/bin/bash + +# Convert the files to markdown and move to the correct directory +jupyter nbconvert -ClearOutputPreprocessor.enabled=True --output-dir=fern/docs/cookbook docs/cookbook/*.ipynb --to markdown +for file in fern/docs/cookbook/*.md; do mv "$file" "${file%.md}.mdx"; done diff --git a/apps/opik-documentation/python-sdk-docs/source/Objects/DistributedTraceHeadersDict.rst b/apps/opik-documentation/python-sdk-docs/source/Objects/DistributedTraceHeadersDict.rst new file mode 100644 index 0000000000..000f20149f --- /dev/null +++ b/apps/opik-documentation/python-sdk-docs/source/Objects/DistributedTraceHeadersDict.rst @@ -0,0 +1,7 @@ +DistributedTraceHeadersDict +========================== + +.. autoclass:: opik.types.DistributedTraceHeadersDict + :members: + :undoc-members: + :show-inheritance: diff --git a/apps/opik-documentation/python-sdk-docs/source/index.rst b/apps/opik-documentation/python-sdk-docs/source/index.rst index 32c8d69427..c07dd8e5a7 100644 --- a/apps/opik-documentation/python-sdk-docs/source/index.rst +++ b/apps/opik-documentation/python-sdk-docs/source/index.rst @@ -215,6 +215,7 @@ You can learn more about the `opik` python SDK in the following sections: Objects/Prompt.rst Objects/OpikBaseModel.rst Objects/LiteLLMChatModel.rst + Objects/DistributedTraceHeadersDict.rst .. toctree:: :maxdepth: 1 :caption: Command Line Interface diff --git a/apps/opik-frontend/src/api/api.ts b/apps/opik-frontend/src/api/api.ts index 81f2519765..28fb8ba8e1 100644 --- a/apps/opik-frontend/src/api/api.ts +++ b/apps/opik-frontend/src/api/api.ts @@ -25,7 +25,7 @@ export const COMPARE_EXPERIMENTS_KEY = "compare-experiments"; export const SPANS_KEY = "spans"; export const TRACES_KEY = "traces"; export const TRACE_KEY = "trace"; -export const PROVIDERS_KEYS_KEY = "providerKeys"; +export const PROVIDERS_KEYS_KEY = "provider-keys"; export const AUTOMATIONS_KEY = "automations"; export const PROJECTS_KEY = "projects"; export const PROJECT_STATISTICS_KEY = "project-statistics"; diff --git a/apps/opik-frontend/src/api/playground/createLogPlaygroundProcessor.ts b/apps/opik-frontend/src/api/playground/createLogPlaygroundProcessor.ts index abc606768f..5bd3b2f460 100644 --- a/apps/opik-frontend/src/api/playground/createLogPlaygroundProcessor.ts +++ b/apps/opik-frontend/src/api/playground/createLogPlaygroundProcessor.ts @@ -16,10 +16,13 @@ import api, { TRACES_REST_ENDPOINT, } from "@/api/api"; import { snakeCaseObj } from "@/lib/utils"; -import { getModelProvider } from "@/lib/llm"; import { createBatchProcessor } from "@/lib/batches"; import { RunStreamingReturn } from "@/api/playground/useCompletionProxyStreaming"; -import { LLMPromptConfigsType, PROVIDER_MODEL_TYPE } from "@/types/providers"; +import { + LLMPromptConfigsType, + PROVIDER_MODEL_TYPE, + PROVIDER_TYPE, +} from "@/types/providers"; import { ProviderMessageType } from "@/types/llm"; export interface LogQueueParams extends RunStreamingReturn { @@ -27,6 +30,7 @@ export interface LogQueueParams extends RunStreamingReturn { datasetItemId?: string; datasetName: string | null; model: PROVIDER_MODEL_TYPE | ""; + provider: PROVIDER_TYPE | ""; providerMessages: ProviderMessageType[]; configs: LLMPromptConfigsType; } @@ -98,7 +102,7 @@ const getSpanFromRun = (run: LogQueueParams, traceId: string): LogSpan => { output: { choices: run.choices ? run.choices : [] }, usage: !run.usage ? undefined : pick(run.usage, USAGE_FIELDS_TO_SEND), metadata: { - created_from: run.model ? getModelProvider(run.model) : "", + created_from: run.provider, usage: run.usage, model: run.model, parameters: run.configs, diff --git a/apps/opik-frontend/src/api/playground/useCompletionProxyStreaming.ts b/apps/opik-frontend/src/api/playground/useCompletionProxyStreaming.ts index b266e95ba8..58b3b3ad8f 100644 --- a/apps/opik-frontend/src/api/playground/useCompletionProxyStreaming.ts +++ b/apps/opik-frontend/src/api/playground/useCompletionProxyStreaming.ts @@ -1,6 +1,7 @@ import { useCallback } from "react"; - import dayjs from "dayjs"; +import isObject from "lodash/isObject"; + import { UsageType } from "@/types/shared"; import { ChatCompletionMessageChoiceType, @@ -8,6 +9,7 @@ import { ChatCompletionProviderErrorMessageType, ChatCompletionSuccessMessageType, ChatCompletionOpikErrorMessageType, + ChatCompletionPythonProxyErrorMessageType, } from "@/types/playground"; import { isValidJsonObject, safelyParseJSON, snakeCaseObj } from "@/lib/utils"; import { BASE_API_URL } from "@/api/api"; @@ -19,6 +21,7 @@ const getNowUtcTimeISOString = (): string => { }; interface GetCompletionProxyStreamParams { + url?: string; model: PROVIDER_MODEL_TYPE | ""; messages: ProviderMessageType[]; signal: AbortSignal; @@ -26,6 +29,12 @@ interface GetCompletionProxyStreamParams { workspaceName: string; } +const isPythonProxyError = ( + response: ChatCompletionResponse, +): response is ChatCompletionPythonProxyErrorMessageType => { + return "detail" in response; +}; + const isOpikError = ( response: ChatCompletionResponse, ): response is ChatCompletionOpikErrorMessageType => { @@ -42,13 +51,14 @@ const isProviderError = ( }; const getCompletionProxyStream = async ({ + url = `${BASE_API_URL}/v1/private/chat/completions`, model, messages, signal, configs, workspaceName, }: GetCompletionProxyStreamParams) => { - return fetch(`${BASE_API_URL}/v1/private/chat/completions`, { + return fetch(url, { method: "POST", headers: { "Content-Type": "application/json", @@ -67,6 +77,7 @@ const getCompletionProxyStream = async ({ }; export interface RunStreamingArgs { + url?: string; model: PROVIDER_MODEL_TYPE | ""; messages: ProviderMessageType[]; configs: LLMPromptConfigsType; @@ -82,6 +93,7 @@ export interface RunStreamingReturn { choices: ChatCompletionMessageChoiceType[] | null; providerError: null | string; opikError: null | string; + pythonProxyError: null | string; } interface UseCompletionProxyStreamingParameters { @@ -91,8 +103,9 @@ interface UseCompletionProxyStreamingParameters { const useCompletionProxyStreaming = ({ workspaceName, }: UseCompletionProxyStreamingParameters) => { - const runStreaming = useCallback( + return useCallback( async ({ + url, model, messages, configs, @@ -106,11 +119,13 @@ const useCompletionProxyStreaming = ({ let choices: ChatCompletionMessageChoiceType[] = []; // errors + let pythonProxyError = null; let opikError = null; let providerError = null; try { const response = await getCompletionProxyStream({ + url, model, messages, configs, @@ -156,12 +171,25 @@ const useCompletionProxyStreaming = ({ opikError = parsedMessage.errors.join(" "); }; + const handlePythonProxyErrorMessage = ( + parsedMessage: ChatCompletionPythonProxyErrorMessageType, + ) => { + if ( + isObject(parsedMessage.detail) && + "error" in parsedMessage.detail + ) { + pythonProxyError = parsedMessage.detail.error; + } else { + pythonProxyError = parsedMessage.detail ?? "Python proxy error"; + } + }; + // an analogue of true && reader // we need it to wait till the stream is closed while (reader) { const { done, value } = await reader.read(); - if (done || opikError || providerError) { + if (done || opikError || pythonProxyError || providerError) { break; } @@ -169,10 +197,17 @@ const useCompletionProxyStreaming = ({ const lines = chunk.split("\n").filter((line) => line.trim() !== ""); for (const line of lines) { - const parsed = safelyParseJSON(line) as ChatCompletionResponse; + const ollamaDataPrefix = "data:"; + const JSONData = line.startsWith(ollamaDataPrefix) + ? line.split(ollamaDataPrefix)[1] + : line; + + const parsed = safelyParseJSON(JSONData) as ChatCompletionResponse; // handle different message types - if (isOpikError(parsed)) { + if (isPythonProxyError(parsed)) { + handlePythonProxyErrorMessage(parsed); + } else if (isOpikError(parsed)) { handleOpikErrorMessage(parsed); } else if (isProviderError(parsed)) { handleAIPlatformErrorMessage(parsed); @@ -188,6 +223,7 @@ const useCompletionProxyStreaming = ({ result: accumulatedValue, providerError, opikError, + pythonProxyError, usage, choices, }; @@ -205,6 +241,7 @@ const useCompletionProxyStreaming = ({ result: accumulatedValue, providerError, opikError: opikError || defaultErrorMessage, + pythonProxyError, usage: null, choices, }; @@ -212,8 +249,6 @@ const useCompletionProxyStreaming = ({ }, [workspaceName], ); - - return runStreaming; }; export default useCompletionProxyStreaming; diff --git a/apps/opik-frontend/src/api/provider-keys/useProviderKeys.tsx b/apps/opik-frontend/src/api/provider-keys/useProviderKeys.ts similarity index 62% rename from apps/opik-frontend/src/api/provider-keys/useProviderKeys.tsx rename to apps/opik-frontend/src/api/provider-keys/useProviderKeys.ts index 47e3b3c669..31b4d559bf 100644 --- a/apps/opik-frontend/src/api/provider-keys/useProviderKeys.tsx +++ b/apps/opik-frontend/src/api/provider-keys/useProviderKeys.ts @@ -5,6 +5,7 @@ import api, { QueryConfig, } from "@/api/api"; import { ProviderKey } from "@/types/providers"; +import useLocalAIProviderData from "@/hooks/useLocalAIProviderData"; type UseProviderKeysListParams = { workspaceName: string; @@ -15,21 +16,28 @@ type UseProviderKeysListResponse = { total: number; }; -const getProviderKeys = async ({ signal }: QueryFunctionContext) => { +const getProviderKeys = async ( + { signal }: QueryFunctionContext, + extendWithLocalData: ( + data: UseProviderKeysListResponse, + ) => UseProviderKeysListResponse, +) => { const { data } = await api.get(PROVIDER_KEYS_REST_ENDPOINT, { signal, }); - return data; + return extendWithLocalData(data); }; export default function useProviderKeys( params: UseProviderKeysListParams, options?: QueryConfig, ) { + const { extendWithLocalData } = useLocalAIProviderData(); + return useQuery({ queryKey: [PROVIDERS_KEYS_KEY, params], - queryFn: (context) => getProviderKeys(context), + queryFn: (context) => getProviderKeys(context, extendWithLocalData), ...options, }); } diff --git a/apps/opik-frontend/src/api/traces/useCreateSpanCommentMutation.ts b/apps/opik-frontend/src/api/traces/useCreateSpanCommentMutation.ts new file mode 100644 index 0000000000..d3b67b6549 --- /dev/null +++ b/apps/opik-frontend/src/api/traces/useCreateSpanCommentMutation.ts @@ -0,0 +1,51 @@ +import { useMutation, useQueryClient } from "@tanstack/react-query"; +import { AxiosError } from "axios"; +import get from "lodash/get"; + +import api, { SPANS_KEY, SPANS_REST_ENDPOINT } from "@/api/api"; +import { useToast } from "@/components/ui/use-toast"; + +type UseCreateSpanCommentMutationParams = { + spanId: string; + projectId: string; + text: string; +}; + +const useCreateSpanCommentMutation = () => { + const queryClient = useQueryClient(); + const { toast } = useToast(); + + return useMutation({ + mutationFn: async ({ + text, + spanId, + }: UseCreateSpanCommentMutationParams) => { + const { data } = await api.post( + `${SPANS_REST_ENDPOINT}${spanId}/comments`, + { text }, + ); + + return data; + }, + onError: (error: AxiosError) => { + const message = get( + error, + ["response", "data", "message"], + error.message, + ); + + toast({ + title: "Error", + description: message, + variant: "destructive", + }); + }, + onSettled: (data, error, variables) => { + queryClient.invalidateQueries({ + queryKey: [SPANS_KEY, { projectId: variables.projectId }], + }); + }, + }); +}; + +export default useCreateSpanCommentMutation; diff --git a/apps/opik-frontend/src/api/traces/useCreateTraceCommentMutation.ts b/apps/opik-frontend/src/api/traces/useCreateTraceCommentMutation.ts new file mode 100644 index 0000000000..76e3f1211d --- /dev/null +++ b/apps/opik-frontend/src/api/traces/useCreateTraceCommentMutation.ts @@ -0,0 +1,50 @@ +import { useMutation, useQueryClient } from "@tanstack/react-query"; +import { AxiosError } from "axios"; +import get from "lodash/get"; + +import api, { TRACE_KEY, TRACES_REST_ENDPOINT } from "@/api/api"; +import { useToast } from "@/components/ui/use-toast"; + +type UseCreateTraceCommentMutationParams = { + traceId: string; + text: string; +}; + +const useCreateTraceCommentMutation = () => { + const queryClient = useQueryClient(); + const { toast } = useToast(); + + return useMutation({ + mutationFn: async ({ + text, + traceId, + }: UseCreateTraceCommentMutationParams) => { + const { data } = await api.post( + `${TRACES_REST_ENDPOINT}${traceId}/comments`, + { text }, + ); + + return data; + }, + onError: (error: AxiosError) => { + const message = get( + error, + ["response", "data", "message"], + error.message, + ); + + toast({ + title: "Error", + description: message, + variant: "destructive", + }); + }, + onSettled: (data, error, variables) => { + queryClient.invalidateQueries({ + queryKey: [TRACE_KEY, { traceId: variables.traceId }], + }); + }, + }); +}; + +export default useCreateTraceCommentMutation; diff --git a/apps/opik-frontend/src/api/traces/useSpanCommentsBatchDeleteMutation.ts b/apps/opik-frontend/src/api/traces/useSpanCommentsBatchDeleteMutation.ts new file mode 100644 index 0000000000..940675a299 --- /dev/null +++ b/apps/opik-frontend/src/api/traces/useSpanCommentsBatchDeleteMutation.ts @@ -0,0 +1,51 @@ +import { useMutation, useQueryClient } from "@tanstack/react-query"; +import get from "lodash/get"; +import { useToast } from "@/components/ui/use-toast"; +import api, { SPANS_KEY, SPANS_REST_ENDPOINT } from "@/api/api"; + +type UseSpanCommentsBatchDeleteMutationParams = { + ids: string[]; + projectId: string; +}; + +const useSpanCommentsBatchDeleteMutation = () => { + const queryClient = useQueryClient(); + const { toast } = useToast(); + + return useMutation({ + mutationFn: async ({ ids }: UseSpanCommentsBatchDeleteMutationParams) => { + const { data } = await api.post( + `${SPANS_REST_ENDPOINT}/comments/delete`, + { + ids: ids, + }, + ); + return data; + }, + onError: (error) => { + const message = get( + error, + ["response", "data", "message"], + error.message, + ); + + toast({ + title: "Error", + description: message, + variant: "destructive", + }); + }, + onSettled: (data, error, variables) => { + queryClient.invalidateQueries({ + queryKey: [ + SPANS_KEY, + { + projectId: variables.projectId, + }, + ], + }); + }, + }); +}; + +export default useSpanCommentsBatchDeleteMutation; diff --git a/apps/opik-frontend/src/api/traces/useTraceCommentsBatchDeleteMutation.ts b/apps/opik-frontend/src/api/traces/useTraceCommentsBatchDeleteMutation.ts new file mode 100644 index 0000000000..bca00d3215 --- /dev/null +++ b/apps/opik-frontend/src/api/traces/useTraceCommentsBatchDeleteMutation.ts @@ -0,0 +1,46 @@ +import { useMutation, useQueryClient } from "@tanstack/react-query"; +import get from "lodash/get"; +import { useToast } from "@/components/ui/use-toast"; +import api, { TRACE_KEY, TRACES_REST_ENDPOINT } from "@/api/api"; + +type UseTraceBatchDeleteMutationParams = { + ids: string[]; + traceId: string; +}; + +const useTraceCommentsBatchDeleteMutation = () => { + const queryClient = useQueryClient(); + const { toast } = useToast(); + + return useMutation({ + mutationFn: async ({ ids }: UseTraceBatchDeleteMutationParams) => { + const { data } = await api.post( + `${TRACES_REST_ENDPOINT}/comments/delete`, + { + ids: ids, + }, + ); + return data; + }, + onError: (error) => { + const message = get( + error, + ["response", "data", "message"], + error.message, + ); + + toast({ + title: "Error", + description: message, + variant: "destructive", + }); + }, + onSettled: (data, error, variables) => { + queryClient.invalidateQueries({ + queryKey: [TRACE_KEY, { traceId: variables.traceId }], + }); + }, + }); +}; + +export default useTraceCommentsBatchDeleteMutation; diff --git a/apps/opik-frontend/src/api/traces/useUpdateSpanCommentMutation.ts b/apps/opik-frontend/src/api/traces/useUpdateSpanCommentMutation.ts new file mode 100644 index 0000000000..1de3388a7f --- /dev/null +++ b/apps/opik-frontend/src/api/traces/useUpdateSpanCommentMutation.ts @@ -0,0 +1,51 @@ +import { useMutation, useQueryClient } from "@tanstack/react-query"; +import { AxiosError } from "axios"; +import get from "lodash/get"; + +import api, { SPANS_KEY, SPANS_REST_ENDPOINT } from "@/api/api"; +import { useToast } from "@/components/ui/use-toast"; + +type UseUpdateSpanCommentMutationParams = { + commentId: string; + projectId: string; + text: string; +}; + +const useUpdateSpanCommentMutation = () => { + const queryClient = useQueryClient(); + const { toast } = useToast(); + + return useMutation({ + mutationFn: async ({ + text, + commentId, + }: UseUpdateSpanCommentMutationParams) => { + const { data } = await api.patch( + `${SPANS_REST_ENDPOINT}comments/${commentId}`, + { text }, + ); + + return data; + }, + onError: (error: AxiosError) => { + const message = get( + error, + ["response", "data", "message"], + error.message, + ); + + toast({ + title: "Error", + description: message, + variant: "destructive", + }); + }, + onSettled: (data, error, variables) => { + queryClient.invalidateQueries({ + queryKey: [SPANS_KEY, { projectId: variables.projectId }], + }); + }, + }); +}; + +export default useUpdateSpanCommentMutation; diff --git a/apps/opik-frontend/src/api/traces/useUpdateTraceCommentMutation.ts b/apps/opik-frontend/src/api/traces/useUpdateTraceCommentMutation.ts new file mode 100644 index 0000000000..12530c8f0a --- /dev/null +++ b/apps/opik-frontend/src/api/traces/useUpdateTraceCommentMutation.ts @@ -0,0 +1,51 @@ +import { useMutation, useQueryClient } from "@tanstack/react-query"; +import { AxiosError } from "axios"; +import get from "lodash/get"; + +import api, { TRACE_KEY, TRACES_REST_ENDPOINT } from "@/api/api"; +import { useToast } from "@/components/ui/use-toast"; + +type UseUpdateTraceCommentMutationParams = { + commentId: string; + traceId: string; + text: string; +}; + +const useUpdateTraceCommentMutation = () => { + const queryClient = useQueryClient(); + const { toast } = useToast(); + + return useMutation({ + mutationFn: async ({ + text, + commentId, + }: UseUpdateTraceCommentMutationParams) => { + const { data } = await api.patch( + `${TRACES_REST_ENDPOINT}comments/${commentId}`, + { text }, + ); + + return data; + }, + onError: (error: AxiosError) => { + const message = get( + error, + ["response", "data", "message"], + error.message, + ); + + toast({ + title: "Error", + description: message, + variant: "destructive", + }); + }, + onSettled: (data, error, variables) => { + queryClient.invalidateQueries({ + queryKey: [TRACE_KEY, { traceId: variables.traceId }], + }); + }, + }); +}; + +export default useUpdateTraceCommentMutation; diff --git a/apps/opik-frontend/src/components/pages-shared/llm/PromptModelSelect/PromptModelSelect.tsx b/apps/opik-frontend/src/components/pages-shared/llm/PromptModelSelect/PromptModelSelect.tsx index 6a0a3001ed..47c28e06b4 100644 --- a/apps/opik-frontend/src/components/pages-shared/llm/PromptModelSelect/PromptModelSelect.tsx +++ b/apps/opik-frontend/src/components/pages-shared/llm/PromptModelSelect/PromptModelSelect.tsx @@ -2,7 +2,6 @@ import React, { useCallback, useMemo, useRef, useState } from "react"; import isNull from "lodash/isNull"; import pick from "lodash/pick"; -import { PROVIDER_MODELS } from "@/constants/llm"; import { PROVIDERS } from "@/constants/providers"; import { @@ -29,11 +28,12 @@ import { PROVIDER_MODEL_TYPE, PROVIDER_TYPE } from "@/types/providers"; import useProviderKeys from "@/api/provider-keys/useProviderKeys"; import AddEditAIProviderDialog from "@/components/shared/AddEditAIProviderDialog/AddEditAIProviderDialog"; import { areAllProvidersConfigured } from "@/lib/provider"; +import useLLMProviderModelsData from "@/hooks/useLLMProviderModelsData"; interface PromptModelSelectProps { value: PROVIDER_MODEL_TYPE | ""; workspaceName: string; - onChange: (value: PROVIDER_MODEL_TYPE) => void; + onChange: (value: PROVIDER_MODEL_TYPE, provider: PROVIDER_TYPE) => void; hasError?: boolean; provider: PROVIDER_TYPE | ""; onAddProvider?: (provider: PROVIDER_TYPE) => void; @@ -57,6 +57,7 @@ const PromptModelSelect = ({ const [openConfigDialog, setOpenConfigDialog] = React.useState(false); const [filterValue, setFilterValue] = useState(""); const [openProviderMenu, setOpenProviderMenu] = useState(null); + const { getProviderModels } = useLLMProviderModelsData(); const { data } = useProviderKeys( { @@ -74,7 +75,7 @@ const PromptModelSelect = ({ const groupOptions = useMemo(() => { const filteredByConfiguredProviders = pick( - PROVIDER_MODELS, + getProviderModels(), configuredProviderKeys, ); @@ -97,10 +98,11 @@ const PromptModelSelect = ({ label: PROVIDERS[providerName].label, options, icon: PROVIDERS[providerName].icon, + provider: providerName, }; }) .filter((g): g is NonNullable => !isNull(g)); - }, [configuredProviderKeys, onlyWithStructuredOutput]); + }, [configuredProviderKeys, onlyWithStructuredOutput, getProviderModels]); const filteredOptions = useMemo(() => { if (filterValue === "") { @@ -131,9 +133,9 @@ const PromptModelSelect = ({ const handleOnChange = useCallback( (value: PROVIDER_MODEL_TYPE) => { - onChange(value); + onChange(value, openProviderMenu as PROVIDER_TYPE); }, - [onChange], + [onChange, openProviderMenu], ); const handleSelectOpenChange = useCallback((open: boolean) => { @@ -191,16 +193,17 @@ const PromptModelSelect = ({ return (
{groupOptions.map((group) => ( - +
setOpenProviderMenu(group.label)} + onMouseEnter={() => setOpenProviderMenu(group.provider)} onMouseLeave={() => setOpenProviderMenu(null)} className={cn( "comet-body-s flex h-10 w-full items-center rounded-sm p-0 pl-2 hover:bg-primary-foreground justify-center", { - "bg-primary-foreground": group.label === openProviderMenu, + "bg-primary-foreground": + group.provider === openProviderMenu, }, )} > @@ -215,7 +218,7 @@ const PromptModelSelect = ({ align="start" className="max-h-[400px] overflow-y-auto p-1" sideOffset={-5} - onMouseEnter={() => setOpenProviderMenu(group.label)} + onMouseEnter={() => setOpenProviderMenu(group.provider)} hideWhenDetached > {group.options.map((option) => { @@ -308,6 +311,7 @@ const PromptModelSelect = ({ - diff --git a/apps/opik-frontend/src/components/pages/ConfigurationPage/AIProvidersTab/AIProvidersRowActionsCell.tsx b/apps/opik-frontend/src/components/pages/ConfigurationPage/AIProvidersTab/AIProvidersRowActionsCell.tsx index c05b1fefa8..c16d80cbe5 100644 --- a/apps/opik-frontend/src/components/pages/ConfigurationPage/AIProvidersTab/AIProvidersRowActionsCell.tsx +++ b/apps/opik-frontend/src/components/pages/ConfigurationPage/AIProvidersTab/AIProvidersRowActionsCell.tsx @@ -12,9 +12,10 @@ import { Button } from "@/components/ui/button"; import ConfirmDialog from "@/components/shared/ConfirmDialog/ConfirmDialog"; import CellWrapper from "@/components/shared/DataTableCells/CellWrapper"; import AddEditAIProviderDialog from "@/components/shared/AddEditAIProviderDialog/AddEditAIProviderDialog"; -import { ProviderKey } from "@/types/providers"; +import { PROVIDER_LOCATION_TYPE, ProviderKey } from "@/types/providers"; import useProviderKeysDeleteMutation from "@/api/provider-keys/useProviderKeysDeleteMutation"; import { PROVIDERS } from "@/constants/providers"; +import useLocalAIProviderData from "@/hooks/useLocalAIProviderData"; const AIProvidersRowActionsCell: React.FunctionComponent< CellContext @@ -23,13 +24,25 @@ const AIProvidersRowActionsCell: React.FunctionComponent< const providerKey = context.row.original; const [open, setOpen] = useState(false); + const { deleteLocalAIProviderData } = useLocalAIProviderData(); + const { mutate: deleteProviderKey } = useProviderKeysDeleteMutation(); const deleteProviderKeyHandler = useCallback(() => { - deleteProviderKey({ - providerId: providerKey.id, - }); - }, [providerKey.id, deleteProviderKey]); + const config = PROVIDERS[providerKey.provider]; + if (config.locationType === PROVIDER_LOCATION_TYPE.local) { + deleteLocalAIProviderData(providerKey.provider); + } else { + deleteProviderKey({ + providerId: providerKey.id, + }); + } + }, [ + providerKey.provider, + providerKey.id, + deleteLocalAIProviderData, + deleteProviderKey, + ]); return ( { const providerKeys = useMemo(() => data?.content ?? [], [data?.content]); + const configuredProviderKeys = useMemo( + () => providerKeys.map((p) => p.provider), + [providerKeys], + ); + const filteredProviderKeys = useMemo(() => { if (providerKeys?.length === 0 || search === "") { return providerKeys; @@ -140,6 +145,7 @@ const AIProvidersTab = () => { />
= ({ chartData, className, }) => { - const [hiddenLines, setHiddenLines] = useState([]); + const [activeLine, setActiveLine] = useState(null); const config = useMemo(() => { return getDefaultHashedColorsChartConfig(chartData.lines); @@ -105,12 +111,17 @@ const ExperimentChartContainer: React.FC = ({ [], ); + const isSinglePoint = chartData.data.length === 1; + return ( - - - {name} + + + {name} + + Average scores + - + {noData ? ( = ({ domain={domain} /> } /> @@ -144,7 +154,7 @@ const ExperimentChartContainer: React.FC = ({ align="right" content={ } @@ -152,19 +162,29 @@ const ExperimentChartContainer: React.FC = ({ height={128} /> {chartData.lines.map((line) => { - const hide = hiddenLines.includes(line); + const isActive = line === activeLine; + + let strokeOpacity = 1; + + if (activeLine) { + strokeOpacity = isActive ? 1 : 0.4; + } return ( record.scores[line]} name={config[line].label as string} stroke={config[line].color as string} - dot={{ strokeWidth: 1, r: 1 }} - activeDot={{ strokeWidth: 1, r: 3 }} - hide={hide} + dot={ + isSinglePoint + ? { fill: config[line].color, strokeWidth: 0 } + : false + } + activeDot={{ strokeWidth: 1.5, r: 4, stroke: "white" }} + strokeWidth={1.5} + strokeOpacity={strokeOpacity} /> ); })} diff --git a/apps/opik-frontend/src/components/pages/ExperimentsPage/charts/ExperimentChartLegendContent.tsx b/apps/opik-frontend/src/components/pages/ExperimentsPage/charts/ExperimentChartLegendContent.tsx index dce117546b..132e920474 100644 --- a/apps/opik-frontend/src/components/pages/ExperimentsPage/charts/ExperimentChartLegendContent.tsx +++ b/apps/opik-frontend/src/components/pages/ExperimentsPage/charts/ExperimentChartLegendContent.tsx @@ -8,10 +8,18 @@ const ExperimentChartLegendContent = React.forwardRef< HTMLDivElement, React.ComponentProps & React.ComponentProps<"div"> & { - setHideState: OnChangeFn; + setActiveLine: OnChangeFn; chartId: string; } ->(({ payload, color, setHideState }, ref) => { +>(({ payload, color, setActiveLine }, ref) => { + const handleMouseEnter = (id: string) => { + setActiveLine(id); + }; + + const handleMouseLeave = () => { + setActiveLine(null); + }; + if (!payload?.length) { return null; } @@ -19,7 +27,8 @@ const ExperimentChartLegendContent = React.forwardRef< return (
{payload.map((item) => { const key = `${item.value || "value"}`; @@ -29,24 +38,17 @@ const ExperimentChartLegendContent = React.forwardRef<
{ - setHideState((state) => { - return item.inactive - ? state.filter((value) => value !== item.value) - : [...state, item.value]; - }); - }} + onMouseEnter={() => handleMouseEnter(item.value)} > -
+
{item.value}
= ({ ? "w-full" : chartsData.length === 2 ? "basis-1/2" - : "basis-2/5"; + : "basis-[520px]"; return (
0 && "mb-6", + "flex items-center gap-4 overflow-y-auto", + chartsData.length > 0 && "mb-4", )} > {chartsData.map((data) => ( diff --git a/apps/opik-frontend/src/components/pages/PlaygroundPage/PlaygroundOutputs/PlaygroundOutput.tsx b/apps/opik-frontend/src/components/pages/PlaygroundPage/PlaygroundOutputs/PlaygroundOutput.tsx index 36a67e8301..e1ed354522 100644 --- a/apps/opik-frontend/src/components/pages/PlaygroundPage/PlaygroundOutputs/PlaygroundOutput.tsx +++ b/apps/opik-frontend/src/components/pages/PlaygroundPage/PlaygroundOutputs/PlaygroundOutput.tsx @@ -1,7 +1,7 @@ import React from "react"; import ReactMarkdown from "react-markdown"; -import { getAlphabetLetter } from "@/lib/utils"; +import { cn, getAlphabetLetter } from "@/lib/utils"; import PlaygroundOutputLoader from "@/components/pages/PlaygroundPage/PlaygroundOutputs/PlaygroundOutputLoader/PlaygroundOutputLoader"; import { useOutputLoadingByPromptDatasetItemId, @@ -25,7 +25,11 @@ const PlaygroundOutput = ({ promptId, index }: PlaygroundOutputProps) => { } return ( - + {value} ); diff --git a/apps/opik-frontend/src/components/pages/PlaygroundPage/PlaygroundOutputs/PlaygroundOutputActions/usePromptDatasetItemCombination.ts b/apps/opik-frontend/src/components/pages/PlaygroundPage/PlaygroundOutputs/PlaygroundOutputActions/usePromptDatasetItemCombination.ts index 75197e8bca..00681d2ca7 100644 --- a/apps/opik-frontend/src/components/pages/PlaygroundPage/PlaygroundOutputs/PlaygroundOutputActions/usePromptDatasetItemCombination.ts +++ b/apps/opik-frontend/src/components/pages/PlaygroundPage/PlaygroundOutputs/PlaygroundOutputActions/usePromptDatasetItemCombination.ts @@ -16,6 +16,7 @@ import mustache from "mustache"; import cloneDeep from "lodash/cloneDeep"; import set from "lodash/set"; import isObject from "lodash/isObject"; +import useLocalAIProviderData from "@/hooks/useLocalAIProviderData"; export interface DatasetItemPromptCombination { datasetItem?: DatasetItem; @@ -85,6 +86,8 @@ const usePromptDatasetItemCombination = ({ // the prop is just taken as the value on the moment of creation const isToStopRef = useRef(isToStop); + const { getLocalIAProviderURL } = useLocalAIProviderData(); + const runStreaming = useCompletionProxyStreaming({ workspaceName, }); @@ -138,6 +141,7 @@ const usePromptDatasetItemCombination = ({ ); const run = await runStreaming({ + url: getLocalIAProviderURL(prompt.provider), model: prompt.model, messages: providerMessages, configs: prompt.configs, @@ -149,7 +153,8 @@ const usePromptDatasetItemCombination = ({ }, }); - const error = run.opikError || run.providerError; + const error = + run.opikError || run.providerError || run.pythonProxyError; updateOutput(prompt.id, datasetItemId, { isLoading: false, @@ -160,7 +165,7 @@ const usePromptDatasetItemCombination = ({ providerMessages, configs: prompt.configs, model: prompt.model, - + provider: prompt.provider, promptId: prompt.id, datasetName, datasetItemId: datasetItemId, @@ -182,10 +187,11 @@ const usePromptDatasetItemCombination = ({ }, [ - datasetName, - runStreaming, - updateOutput, addAbortController, + updateOutput, + runStreaming, + getLocalIAProviderURL, + datasetName, deleteAbortController, ], ); diff --git a/apps/opik-frontend/src/components/pages/PlaygroundPage/PlaygroundOutputs/PlaygroundOutputTable/PlaygroundOutputCell.tsx b/apps/opik-frontend/src/components/pages/PlaygroundPage/PlaygroundOutputs/PlaygroundOutputTable/PlaygroundOutputCell.tsx index 626b16a7d3..17a48cbe09 100644 --- a/apps/opik-frontend/src/components/pages/PlaygroundPage/PlaygroundOutputs/PlaygroundOutputTable/PlaygroundOutputCell.tsx +++ b/apps/opik-frontend/src/components/pages/PlaygroundPage/PlaygroundOutputs/PlaygroundOutputTable/PlaygroundOutputCell.tsx @@ -9,6 +9,7 @@ import { } from "@/store/PlaygroundStore"; import ReactMarkdown from "react-markdown"; import PlaygroundOutputLoader from "@/components/pages/PlaygroundPage/PlaygroundOutputs/PlaygroundOutputLoader/PlaygroundOutputLoader"; +import { cn } from "@/lib/utils"; interface PlaygroundOutputCellData { dataItemId: string; @@ -46,7 +47,11 @@ const PlaygroundOutputCell: React.FunctionComponent< } return ( - + {value} ); diff --git a/apps/opik-frontend/src/components/pages/PlaygroundPage/PlaygroundPrompts/PlaygroundPrompt.tsx b/apps/opik-frontend/src/components/pages/PlaygroundPage/PlaygroundPrompts/PlaygroundPrompt.tsx index 8b6bbfc8d6..523add9792 100644 --- a/apps/opik-frontend/src/components/pages/PlaygroundPage/PlaygroundPrompts/PlaygroundPrompt.tsx +++ b/apps/opik-frontend/src/components/pages/PlaygroundPage/PlaygroundPrompts/PlaygroundPrompt.tsx @@ -15,11 +15,7 @@ import { generateDefaultPrompt, getDefaultConfigByProvider, } from "@/lib/playground"; -import { - generateDefaultLLMPromptMessage, - getModelProvider, - getNextMessageType, -} from "@/lib/llm"; +import { generateDefaultLLMPromptMessage, getNextMessageType } from "@/lib/llm"; import LLMPromptMessages from "@/components/pages-shared/llm/LLMPromptMessages/LLMPromptMessages"; import PromptModelSelect from "@/components/pages-shared/llm/PromptModelSelect/PromptModelSelect"; import { getAlphabetLetter } from "@/lib/utils"; @@ -33,9 +29,11 @@ import { useUpdateOutput, useUpdatePrompt, } from "@/store/PlaygroundStore"; -import { getDefaultProviderKey } from "@/lib/provider"; -import { PROVIDERS } from "@/constants/providers"; import useLastPickedModel from "@/components/pages/PlaygroundPage/PlaygroundPrompts/useLastPickedModel"; +import { + ModelResolver, + ProviderResolver, +} from "@/hooks/useLLMProviderModelsData"; interface PlaygroundPromptProps { workspaceName: string; @@ -43,6 +41,8 @@ interface PlaygroundPromptProps { promptId: string; providerKeys: PROVIDER_TYPE[]; isPendingProviderKeys: boolean; + providerResolver: ProviderResolver; + modelResolver: ModelResolver; } const PlaygroundPrompt = ({ @@ -51,6 +51,8 @@ const PlaygroundPrompt = ({ index, providerKeys, isPendingProviderKeys, + providerResolver, + modelResolver, }: PlaygroundPromptProps) => { const checkedIfModelIsValidRef = useRef(false); @@ -66,7 +68,7 @@ const PlaygroundPrompt = ({ const deletePrompt = useDeletePrompt(); const updateOutput = useUpdateOutput(); - const provider = model ? getModelProvider(model) : ""; + const provider = providerResolver(model); const hintMessage = datasetVariables?.length ? `Reference dataset variables using mustache syntax: ${datasetVariables @@ -91,6 +93,8 @@ const PlaygroundPrompt = ({ const newPrompt = generateDefaultPrompt({ initPrompt: prompt, setupProviders: providerKeys, + providerResolver: providerResolver, + modelResolver: modelResolver, }); addPrompt(newPrompt, index + 1); @@ -116,32 +120,40 @@ const PlaygroundPrompt = ({ ); const handleUpdateModel = useCallback( - (model: PROVIDER_MODEL_TYPE) => { - updatePrompt(promptId, { model }); - setLastPickedModel(model); + (newModel: PROVIDER_MODEL_TYPE, newProvider: PROVIDER_TYPE) => { + updatePrompt(promptId, { + model: newModel, + provider: newProvider, + ...(newProvider !== provider && { + configs: getDefaultConfigByProvider(newProvider), + }), + }); + setLastPickedModel(newModel); }, - [updatePrompt, promptId, setLastPickedModel], + [updatePrompt, promptId, provider, setLastPickedModel], ); const handleAddProvider = useCallback( (provider: PROVIDER_TYPE) => { - const modelProvider = model ? getModelProvider(model) : ""; - const noCurrentModel = !modelProvider; - - if (noCurrentModel) { - const newModel = PROVIDERS[provider]?.defaultModel || ""; - - const newDefaultConfigs = provider - ? getDefaultConfigByProvider(provider) - : {}; + const newModel = modelResolver(model, providerKeys, provider); + if (newModel !== model) { + const newProvider = providerResolver(newModel); updatePrompt(promptId, { model: newModel, - configs: newDefaultConfigs, + provider: newProvider, + configs: getDefaultConfigByProvider(newProvider), }); } }, - [model, promptId, updatePrompt], + [ + modelResolver, + model, + providerKeys, + providerResolver, + updatePrompt, + promptId, + ], ); useEffect(() => { @@ -149,40 +161,24 @@ const PlaygroundPrompt = ({ if (!checkedIfModelIsValidRef.current && !isPendingProviderKeys) { checkedIfModelIsValidRef.current = true; - const modelProvider = model ? getModelProvider(model) : ""; + const newModel = modelResolver(model, providerKeys); - const noModelProviderWhenProviderKeysSet = - !modelProvider && providerKeys.length > 0; - const modelProviderIsNotFromProviderKeys = - modelProvider && !providerKeys.includes(modelProvider); - - const needToChangeProvider = - noModelProviderWhenProviderKeysSet || - modelProviderIsNotFromProviderKeys; + if (newModel !== model) { + const newProvider = providerResolver(newModel); + updatePrompt(promptId, { + model: newModel, + provider: newProvider, + configs: getDefaultConfigByProvider(newProvider), + }); - if (!needToChangeProvider) { - return; + updateOutput(promptId, "", { value: "" }); } - - const newProvider = getDefaultProviderKey(providerKeys); - const newModel = newProvider - ? PROVIDERS[newProvider]?.defaultModel || "" - : ""; - - const newDefaultConfigs = newProvider - ? getDefaultConfigByProvider(newProvider) - : {}; - - updatePrompt(promptId, { - model: newModel, - configs: newDefaultConfigs, - }); - - updateOutput(promptId, "", { value: "" }); } }, [ providerKeys, isPendingProviderKeys, + providerResolver, + modelResolver, updateOutput, updatePrompt, promptId, diff --git a/apps/opik-frontend/src/components/pages/PlaygroundPage/PlaygroundPrompts/PlaygroundPrompts.tsx b/apps/opik-frontend/src/components/pages/PlaygroundPage/PlaygroundPrompts/PlaygroundPrompts.tsx index c14df24854..8d7eae76d2 100644 --- a/apps/opik-frontend/src/components/pages/PlaygroundPage/PlaygroundPrompts/PlaygroundPrompts.tsx +++ b/apps/opik-frontend/src/components/pages/PlaygroundPage/PlaygroundPrompts/PlaygroundPrompts.tsx @@ -11,6 +11,7 @@ import { useSetPromptMap, } from "@/store/PlaygroundStore"; import useLastPickedModel from "@/components/pages/PlaygroundPage/PlaygroundPrompts/useLastPickedModel"; +import useLLMProviderModelsData from "@/hooks/useLLMProviderModelsData"; interface PlaygroundPromptsState { workspaceName: string; @@ -32,11 +33,15 @@ const PlaygroundPrompts = ({ const promptIds = usePromptIds(); const [lastPickedModel] = useLastPickedModel(); + const { calculateModelProvider, calculateDefaultModel } = + useLLMProviderModelsData(); const handleAddPrompt = () => { const newPrompt = generateDefaultPrompt({ setupProviders: providerKeys, lastPickedModel, + providerResolver: calculateModelProvider, + modelResolver: calculateDefaultModel, }); addPrompt(newPrompt); }; @@ -45,10 +50,19 @@ const PlaygroundPrompts = ({ const newPrompt = generateDefaultPrompt({ setupProviders: providerKeys, lastPickedModel, + providerResolver: calculateModelProvider, + modelResolver: calculateDefaultModel, }); setPromptMap([newPrompt.id], { [newPrompt.id]: newPrompt }); onResetHeight(); - }, [setPromptMap, providerKeys, lastPickedModel, onResetHeight]); + }, [ + providerKeys, + lastPickedModel, + calculateModelProvider, + calculateDefaultModel, + setPromptMap, + onResetHeight, + ]); useEffect(() => { // hasn't been initialized yet or the last prompt is removed @@ -84,6 +98,8 @@ const PlaygroundPrompts = ({ key={promptId} providerKeys={providerKeys} isPendingProviderKeys={isPendingProviderKeys} + providerResolver={calculateModelProvider} + modelResolver={calculateDefaultModel} /> ))}
diff --git a/apps/opik-frontend/src/components/pages/ProjectsPage/ProjectsPage.tsx b/apps/opik-frontend/src/components/pages/ProjectsPage/ProjectsPage.tsx index 137f698962..80ae01ffe5 100644 --- a/apps/opik-frontend/src/components/pages/ProjectsPage/ProjectsPage.tsx +++ b/apps/opik-frontend/src/components/pages/ProjectsPage/ProjectsPage.tsx @@ -1,6 +1,13 @@ import React, { useCallback, useMemo, useRef, useState } from "react"; import { keepPreviousData } from "@tanstack/react-query"; +import { + JsonParam, + NumberParam, + StringParam, + useQueryParam, +} from "use-query-params"; import isNumber from "lodash/isNumber"; +import get from "lodash/get"; import { formatNumericData } from "@/lib/utils"; import DataTable from "@/components/shared/DataTable/DataTable"; @@ -30,18 +37,13 @@ import { } from "@/types/shared"; import { convertColumnDataToColumn, mapColumnDataFields } from "@/lib/table"; import useLocalStorageState from "use-local-storage-state"; -import { - ColumnPinningState, - ColumnSort, - RowSelectionState, -} from "@tanstack/react-table"; +import { ColumnPinningState, ColumnSort } from "@tanstack/react-table"; import { generateActionsColumDef, generateSelectColumDef, } from "@/components/shared/DataTable/utils"; import { RESOURCE_TYPE } from "@/components/shared/ResourceLink/ResourceLink"; import FeedbackScoreListCell from "@/components/shared/DataTableCells/FeedbackScoreListCell"; -import { get } from "lodash"; export const getRowId = (p: ProjectWithStatistic) => p.id; @@ -175,12 +177,22 @@ const ProjectsPage: React.FunctionComponent = () => { const resetDialogKeyRef = useRef(0); const [openDialog, setOpenDialog] = useState(false); - - const [search, setSearch] = useState(""); - const [page, setPage] = useState(1); - const [size, setSize] = useState(10); - - const [rowSelection, setRowSelection] = useState({}); + const [search = "", setSearch] = useQueryParam("search", StringParam, { + updateType: "replaceIn", + }); + const [page = 1, setPage] = useQueryParam("page", NumberParam, { + updateType: "replaceIn", + }); + const [size = 10, setSize] = useQueryParam("size", NumberParam, { + updateType: "replaceIn", + }); + const [rowSelection = {}, setRowSelection] = useQueryParam( + "selection", + JsonParam, + { + updateType: "replaceIn", + }, + ); const [sortedColumns, setSortedColumns] = useLocalStorageState( COLUMNS_SORT_KEY, @@ -192,7 +204,7 @@ const ProjectsPage: React.FunctionComponent = () => { const { data, isPending } = useProjectWithStatisticsList( { workspaceName, - search, + search: search!, sorting: sortedColumns.map((column) => { if (column.id === "last_updated_at") { return { @@ -202,8 +214,8 @@ const ProjectsPage: React.FunctionComponent = () => { } return column; }), - page, - size, + page: page!, + size: size!, }, { placeholderData: keepPreviousData, @@ -292,7 +304,7 @@ const ProjectsPage: React.FunctionComponent = () => {
{ />
diff --git a/apps/opik-frontend/src/components/pages/TracesPage/MetricsTab/MetricChart/MetricChart.tsx b/apps/opik-frontend/src/components/pages/TracesPage/MetricsTab/MetricChart/MetricChart.tsx index 1767d61245..c93c018b8f 100644 --- a/apps/opik-frontend/src/components/pages/TracesPage/MetricsTab/MetricChart/MetricChart.tsx +++ b/apps/opik-frontend/src/components/pages/TracesPage/MetricsTab/MetricChart/MetricChart.tsx @@ -1,15 +1,26 @@ -import React, { useCallback, useMemo } from "react"; -import { Card, CardContent, CardHeader, CardTitle } from "@/components/ui/card"; +import React, { useCallback, useMemo, useState } from "react"; import { + Card, + CardContent, + CardDescription, + CardHeader, + CardTitle, +} from "@/components/ui/card"; +import { + Area, CartesianGrid, + ComposedChart, Line, - LineChart, Tooltip, XAxis, YAxis, } from "recharts"; import { ProjectMetricValue } from "@/types/projects"; -import { ChartContainer, ChartTooltip } from "@/components/ui/chart"; +import { + ChartContainer, + ChartLegend, + ChartTooltip, +} from "@/components/ui/chart"; import dayjs from "dayjs"; import { DEFAULT_CHART_TICK } from "@/constants/chart"; import { getDefaultHashedColorsChartConfig } from "@/lib/charts"; @@ -25,12 +36,15 @@ import ChartTooltipContent, { import { formatDate } from "@/lib/date"; import { ValueType } from "recharts/types/component/DefaultTooltipContent"; import useChartTickDefaultConfig from "@/hooks/charts/useChartTickDefaultConfig"; +import MetricChartLegendContent from "./MetricChartLegendContent"; +import { TAG_VARIANTS_COLOR_MAP } from "@/components/ui/tag"; const renderTooltipValue = ({ value }: ChartTooltipRenderValueArguments) => value; interface MetricChartProps { name: string; + description: string; projectId: string; interval: INTERVAL_TYPE; intervalStart: string; @@ -40,13 +54,26 @@ interface MetricChartProps { renderValue?: (data: ChartTooltipRenderValueArguments) => ValueType; labelsMap?: Record; customYTickFormatter?: (value: number, maxDecimalLength?: number) => string; + chartId: string; } type TransformedDataValueType = null | number | string; type TransformedData = { [key: string]: TransformedDataValueType }; +const predefinedColorMap = { + traces: TAG_VARIANTS_COLOR_MAP.purple, + cost: TAG_VARIANTS_COLOR_MAP.purple, + "duration.p50": TAG_VARIANTS_COLOR_MAP.turquoise, + "duration.p90": TAG_VARIANTS_COLOR_MAP.burgundy, + "duration.p99": TAG_VARIANTS_COLOR_MAP.purple, + completion_tokens: TAG_VARIANTS_COLOR_MAP.turquoise, + prompt_tokens: TAG_VARIANTS_COLOR_MAP.burgundy, + total_tokens: TAG_VARIANTS_COLOR_MAP.purple, +}; + const MetricChart = ({ name, + description, metricName, projectId, interval, @@ -56,7 +83,9 @@ const MetricChart = ({ renderValue = renderTooltipValue, labelsMap, customYTickFormatter, + chartId, }: MetricChartProps) => { + const [activeLine, setActiveLine] = useState(null); const { data: traces, isPending } = useProjectMetric( { projectId, @@ -72,7 +101,7 @@ const MetricChart = ({ ); const [data, lines, values] = useMemo(() => { - if (!traces?.length) { + if (!traces?.filter((trace) => !!trace.name).length) { return [[], [], []]; } @@ -96,7 +125,11 @@ const MetricChart = ({ }, [traces]); const config = useMemo(() => { - return getDefaultHashedColorsChartConfig(lines, labelsMap); + return getDefaultHashedColorsChartConfig( + lines, + labelsMap, + predefinedColorMap, + ); }, [lines, labelsMap]); const { @@ -132,6 +165,15 @@ const MetricChart = ({ ); const renderContent = () => { + const isSingleLine = lines.length === 1; + const isSinglePoint = + data.filter((point) => lines.every((line) => point[line] !== null)) + .length === 1; + + const [firstLine] = lines; + + const activeDot = { strokeWidth: 1.5, r: 4, stroke: "white" }; + if (isPending) { return (
@@ -145,7 +187,7 @@ const MetricChart = ({ config={config} className="h-[var(--chart-height)] w-full" > - - {lines.map((line) => ( - - ))} - + + } + /> + + {isSingleLine ? ( + <> + + + + + + + + + ) : ( + lines.map((line) => { + const isActive = line === activeLine; + + let strokeOpacity = 1; + + if (activeLine) { + strokeOpacity = isActive ? 1 : 0.4; + } + + return ( + + ); + }) + )} + ); }; return ( - - {name} + + {name} + + {description} + - {renderContent()} + {renderContent()} ); }; diff --git a/apps/opik-frontend/src/components/pages/TracesPage/MetricsTab/MetricChart/MetricChartLegendContent.tsx b/apps/opik-frontend/src/components/pages/TracesPage/MetricsTab/MetricChart/MetricChartLegendContent.tsx new file mode 100644 index 0000000000..adb12c2e7b --- /dev/null +++ b/apps/opik-frontend/src/components/pages/TracesPage/MetricsTab/MetricChart/MetricChartLegendContent.tsx @@ -0,0 +1,66 @@ +import React from "react"; +import * as RechartsPrimitive from "recharts"; +import { OnChangeFn } from "@/types/shared"; +import TooltipWrapper from "@/components/shared/TooltipWrapper/TooltipWrapper"; + +const MetricChartLegendContent = React.forwardRef< + HTMLDivElement, + React.ComponentProps & + React.ComponentProps<"div"> & { + setActiveLine: OnChangeFn; + chartId: string; + } +>(({ payload, color, setActiveLine }, ref) => { + const handleMouseEnter = (id: string) => { + setActiveLine(id); + }; + + const handleMouseLeave = () => { + setActiveLine(null); + }; + + if (!payload?.length) { + return null; + } + + return ( +
+
+ {payload.map((item) => { + const key = `${item.value || "value"}`; + const indicatorColor = color || item.color; + + return ( +
handleMouseEnter(item.value)} + > + +
+ {item.value} +
+
+
+
+ ); + })} +
+
+ ); +}); +MetricChartLegendContent.displayName = "MetricChartLegendContent"; + +export default MetricChartLegendContent; diff --git a/apps/opik-frontend/src/components/pages/TracesPage/MetricsTab/MetricsTab.tsx b/apps/opik-frontend/src/components/pages/TracesPage/MetricsTab/MetricsTab.tsx index 1bc0213d2e..1c797a2c48 100644 --- a/apps/opik-frontend/src/components/pages/TracesPage/MetricsTab/MetricsTab.tsx +++ b/apps/opik-frontend/src/components/pages/TracesPage/MetricsTab/MetricsTab.tsx @@ -146,7 +146,9 @@ const MetricsTab = ({ projectId }: MetricsTabProps) => {
{
{
{
{
= ({ value={field.value} onChange={field.onChange} id="sampling_rate" - label="Samping rate" + label="Sampling rate" tooltip="Percentage of traces to evaluate" /> )} diff --git a/apps/opik-frontend/src/components/pages/TracesPage/RulesTab/AddEditRuleDialog/LLMJudgeRuleDetails.tsx b/apps/opik-frontend/src/components/pages/TracesPage/RulesTab/AddEditRuleDialog/LLMJudgeRuleDetails.tsx index 0d8a7d5536..7c6be7cc0c 100644 --- a/apps/opik-frontend/src/components/pages/TracesPage/RulesTab/AddEditRuleDialog/LLMJudgeRuleDetails.tsx +++ b/apps/opik-frontend/src/components/pages/TracesPage/RulesTab/AddEditRuleDialog/LLMJudgeRuleDetails.tsx @@ -25,10 +25,11 @@ import { LLMMessage, LLMPromptTemplate, } from "@/types/llm"; -import { generateDefaultLLMPromptMessage, getModelProvider } from "@/lib/llm"; +import { generateDefaultLLMPromptMessage } from "@/lib/llm"; import { PROVIDER_MODEL_TYPE } from "@/types/providers"; import { safelyGetPromptMustacheTags } from "@/lib/prompt"; import { EvaluationRuleFormType } from "@/components/pages/TracesPage/RulesTab/AddEditRuleDialog/schema"; +import useLLMProviderModelsData from "@/hooks/useLLMProviderModelsData"; const MESSAGE_TYPE_OPTIONS = [ { @@ -61,6 +62,7 @@ const LLMJudgeRuleDetails: React.FC = ({ form, }) => { const cache = useRef>({}); + const { calculateModelProvider } = useLLMProviderModelsData(); return ( <> @@ -69,7 +71,7 @@ const LLMJudgeRuleDetails: React.FC = ({ name="llmJudgeDetails.model" render={({ field, formState }) => { const model = field.value as PROVIDER_MODEL_TYPE | ""; - const provider = model ? getModelProvider(model) : ""; + const provider = calculateModelProvider(model); const validationErrors = get(formState.errors, [ "llmJudgeDetails", "model", diff --git a/apps/opik-frontend/src/components/shared/AddEditAIProviderDialog/AddEditAIProviderDialog.tsx b/apps/opik-frontend/src/components/shared/AddEditAIProviderDialog/AddEditAIProviderDialog.tsx index 47ac3aef21..d4e042f282 100644 --- a/apps/opik-frontend/src/components/shared/AddEditAIProviderDialog/AddEditAIProviderDialog.tsx +++ b/apps/opik-frontend/src/components/shared/AddEditAIProviderDialog/AddEditAIProviderDialog.tsx @@ -1,4 +1,12 @@ -import React, { useCallback, useState } from "react"; +import React, { useCallback, useMemo } from "react"; +import { useForm, UseFormReturn } from "react-hook-form"; +import { zodResolver } from "@hookform/resolvers/zod"; +import { z } from "zod"; +import get from "lodash/get"; +import isFunction from "lodash/isFunction"; +import isArray from "lodash/isArray"; + +import { cn } from "@/lib/utils"; import { Button } from "@/components/ui/button"; import { Dialog, @@ -8,22 +16,40 @@ import { DialogHeader, DialogTitle, } from "@/components/ui/dialog"; +import { + Form, + FormControl, + FormField, + FormItem, + FormMessage, +} from "@/components/ui/form"; import { Label } from "@/components/ui/label"; -import { ProviderKey, PROVIDER_TYPE } from "@/types/providers"; +import { + LocalAIProviderData, + PROVIDER_LOCATION_TYPE, + PROVIDER_TYPE, + ProviderKey, +} from "@/types/providers"; +import SelectBox from "@/components/shared/SelectBox/SelectBox"; import useProviderKeysUpdateMutation from "@/api/provider-keys/useProviderKeysUpdateMutation"; import useProviderKeysCreateMutation from "@/api/provider-keys/useProviderKeysCreateMutation"; -import SelectBox from "@/components/shared/SelectBox/SelectBox"; +import useLocalAIProviderData from "@/hooks/useLocalAIProviderData"; import { PROVIDERS, PROVIDERS_OPTIONS } from "@/constants/providers"; import { SelectItem } from "@/components/ui/select"; import { DropdownOption } from "@/types/shared"; -import EyeInput from "@/components/shared/EyeInput/EyeInput"; -import isFunction from "lodash/isFunction"; +import { + AIProviderFormSchema, + AIProviderFormType, +} from "@/components/shared/AddEditAIProviderDialog/schema"; +import CloudAIProviderDetails from "@/components/shared/AddEditAIProviderDialog/CloudAIProviderDetails"; +import LocalAIProviderDetails from "@/components/shared/AddEditAIProviderDialog/LocalAIProviderDetails"; type AddEditAIProviderDialogProps = { providerKey?: ProviderKey; open: boolean; setOpen: (open: boolean) => void; onAddProvider?: (provider: PROVIDER_TYPE) => void; + excludedProviders?: PROVIDER_TYPE[]; }; const AddEditAIProviderDialog: React.FC = ({ @@ -31,18 +57,40 @@ const AddEditAIProviderDialog: React.FC = ({ open, setOpen, onAddProvider, + excludedProviders, }) => { + const { getLocalAIProviderData, setLocalAIProviderData } = + useLocalAIProviderData(); const { mutate: createMutate } = useProviderKeysCreateMutation(); const { mutate: updateMutate } = useProviderKeysUpdateMutation(); - const [provider, setProvider] = useState( - providerKey?.provider || "", - ); - const [apiKey, setApiKey] = useState(""); - const isEdit = Boolean(providerKey); - const isValid = Boolean(apiKey.length); + const localData = useMemo(() => { + return providerKey?.provider + ? getLocalAIProviderData(providerKey.provider) + : undefined; + }, [getLocalAIProviderData, providerKey]); + + const form: UseFormReturn = useForm< + z.infer + >({ + resolver: zodResolver(AIProviderFormSchema), + defaultValues: { + provider: providerKey?.provider || "", + locationType: providerKey?.provider + ? PROVIDERS[providerKey.provider]?.locationType + : PROVIDER_LOCATION_TYPE.cloud, + apiKey: "", + url: localData?.url ?? "", + models: localData?.models ?? "", + }, + }); - const providerName = (provider && PROVIDERS[provider]?.label) || ""; + const provider = form.watch("provider") as PROVIDER_TYPE | ""; + + const isEdit = Boolean(providerKey); + const isCloudProvider = + provider === "" || + PROVIDERS[provider].locationType === PROVIDER_LOCATION_TYPE.cloud; const title = isEdit ? "Edit AI provider configuration" @@ -50,9 +98,33 @@ const AddEditAIProviderDialog: React.FC = ({ const buttonText = isEdit ? "Update configuration" : "Save configuration"; - const apiKeyLabel = provider ? `${providerName} API Key` : "API Key"; + const localConfigHandler = useCallback(() => { + const data: LocalAIProviderData = { + created_at: new Date().toISOString(), + ...localData, + url: form.getValues("url"), + models: form.getValues("models"), + }; + + if (provider) { + setLocalAIProviderData(provider, data); + if (isFunction(onAddProvider)) { + onAddProvider(provider); + } + } - const submitHandler = useCallback(() => { + setOpen(false); + }, [ + localData, + form, + provider, + setOpen, + setLocalAIProviderData, + onAddProvider, + ]); + + const cloudConfigHandler = useCallback(() => { + const apiKey = form.getValues("apiKey"); if (isEdit) { updateMutate({ providerKey: { @@ -72,21 +144,41 @@ const AddEditAIProviderDialog: React.FC = ({ }, }); } + setOpen(false); }, [ - createMutate, + form, isEdit, - apiKey, - updateMutate, provider, + setOpen, + updateMutate, providerKey, onAddProvider, + createMutate, ]); + const onSubmit = useCallback( + () => (isCloudProvider ? cloudConfigHandler() : localConfigHandler()), + [isCloudProvider, cloudConfigHandler, localConfigHandler], + ); + + const options = useMemo(() => { + return isArray(excludedProviders) + ? PROVIDERS_OPTIONS.filter( + ({ value }) => !excludedProviders.includes(value), + ) + : PROVIDERS_OPTIONS; + }, [excludedProviders]); + const renderOption = (option: DropdownOption) => { const Icon = PROVIDERS[option.value as PROVIDER_TYPE]?.icon; return ( - + {option.description}
} + withoutCheck + >
{option.label} @@ -101,50 +193,61 @@ const AddEditAIProviderDialog: React.FC = ({ {title} -
- - setProvider(v as PROVIDER_TYPE)} - options={PROVIDERS_OPTIONS} - placeholder="Select a provider" - /> -
-
- - setApiKey(e.target.value)} - /> - {provider && ( - - Get your {providerName} API key{" "} - - . - - )} -
+
+ + { + const validationErrors = get(formState.errors, ["provider"]); + + return ( + + + + { + const p = v as PROVIDER_TYPE; + form.setValue( + "locationType", + PROVIDERS[p].locationType, + ); + field.onChange(p); + }} + options={options} + placeholder="Select a provider" + className={cn({ + "border-destructive": Boolean( + validationErrors?.message, + ), + })} + /> + + + + ); + }} + /> + {isCloudProvider ? ( + + ) : ( + + )} + + - - - + diff --git a/apps/opik-frontend/src/components/shared/AddEditAIProviderDialog/CloudAIProviderDetails.tsx b/apps/opik-frontend/src/components/shared/AddEditAIProviderDialog/CloudAIProviderDetails.tsx new file mode 100644 index 0000000000..016aeb573c --- /dev/null +++ b/apps/opik-frontend/src/components/shared/AddEditAIProviderDialog/CloudAIProviderDetails.tsx @@ -0,0 +1,78 @@ +import React from "react"; +import { UseFormReturn } from "react-hook-form"; +import { Button } from "@/components/ui/button"; +import { Label } from "@/components/ui/label"; +import { PROVIDER_TYPE } from "@/types/providers"; +import { CLOUD_PROVIDER_OPTION_TYPE, PROVIDERS } from "@/constants/providers"; +import EyeInput from "@/components/shared/EyeInput/EyeInput"; +import { AIProviderFormType } from "@/components/shared/AddEditAIProviderDialog/schema"; +import get from "lodash/get"; +import { + FormControl, + FormField, + FormItem, + FormMessage, +} from "@/components/ui/form"; +import { cn } from "@/lib/utils"; + +type CloudAIProviderDetailsProps = { + provider: PROVIDER_TYPE | ""; + form: UseFormReturn; +}; + +const CloudAIProviderDetails: React.FC = ({ + provider, + form, +}) => { + const providerName = (provider && PROVIDERS[provider]?.label + " ") || ""; + const apiKeyLabel = `${providerName}API Key`; + + return ( +
+ { + const validationErrors = get(formState.errors, ["apiKey"]); + + return ( + + + + field.onChange(e.target.value)} + className={cn({ + "border-destructive": Boolean(validationErrors?.message), + })} + /> + + + + ); + }} + /> + {provider && ( + + Get your {providerName} API key{" "} + + . + + )} +
+ ); +}; + +export default CloudAIProviderDetails; diff --git a/apps/opik-frontend/src/components/shared/AddEditAIProviderDialog/LocalAIProviderDetails.tsx b/apps/opik-frontend/src/components/shared/AddEditAIProviderDialog/LocalAIProviderDetails.tsx new file mode 100644 index 0000000000..2053afb3de --- /dev/null +++ b/apps/opik-frontend/src/components/shared/AddEditAIProviderDialog/LocalAIProviderDetails.tsx @@ -0,0 +1,113 @@ +import React from "react"; +import { UseFormReturn } from "react-hook-form"; +import { Label } from "@/components/ui/label"; +import { PROVIDER_TYPE } from "@/types/providers"; +import { PROVIDERS } from "@/constants/providers"; +import { AIProviderFormType } from "@/components/shared/AddEditAIProviderDialog/schema"; +import get from "lodash/get"; +import { + FormControl, + FormField, + FormItem, + FormMessage, +} from "@/components/ui/form"; +import { buildDocsUrl, cn } from "@/lib/utils"; +import { Button } from "@/components/ui/button"; +import { Input } from "@/components/ui/input"; +import { Description } from "@/components/ui/description"; + +type LocalAIProviderDetailsProps = { + provider: PROVIDER_TYPE | ""; + form: UseFormReturn; +}; + +const LocalAIProviderDetails: React.FC = ({ + provider, + form, +}) => { + const providerName = (provider && PROVIDERS[provider]?.label + " ") || ""; + const urlLabel = `${providerName}URL`; + + return ( + <> +
+ { + const validationErrors = get(formState.errors, ["url"]); + + return ( + + + + To use {providerName}you will need to configure the Opik proxy + to avoid network issues, learn more in the{" "} + + . + + + field.onChange(e.target.value)} + className={cn({ + "border-destructive": Boolean(validationErrors?.message), + })} + /> + + + + ); + }} + /> +
+
+ { + const validationErrors = get(formState.errors, ["models"]); + + return ( + + + + Comma separated list of available models + + + field.onChange(e.target.value)} + className={cn({ + "border-destructive": Boolean(validationErrors?.message), + })} + /> + + + + ); + }} + /> +
+ + ); +}; + +export default LocalAIProviderDetails; diff --git a/apps/opik-frontend/src/components/shared/AddEditAIProviderDialog/schema.ts b/apps/opik-frontend/src/components/shared/AddEditAIProviderDialog/schema.ts new file mode 100644 index 0000000000..9b42d0db24 --- /dev/null +++ b/apps/opik-frontend/src/components/shared/AddEditAIProviderDialog/schema.ts @@ -0,0 +1,43 @@ +import { z } from "zod"; +import { PROVIDER_LOCATION_TYPE, PROVIDER_TYPE } from "@/types/providers"; +import uniq from "lodash/uniq"; + +const ProviderSchema = z + .union([z.nativeEnum(PROVIDER_TYPE), z.string().length(0)], { + required_error: "Provider is required", + }) + .refine((model) => model.length >= 1, { message: "Provider is required" }); + +export const CloudAIProviderDetailsFormSchema = z.object({ + provider: ProviderSchema, + locationType: z.literal(PROVIDER_LOCATION_TYPE.cloud), + apiKey: z + .string({ + required_error: "API key is required", + }) + .min(1, { message: "API key is required" }), +}); + +export const LocalAIProviderDetailsFormSchema = z.object({ + provider: ProviderSchema, + locationType: z.literal(PROVIDER_LOCATION_TYPE.local), + url: z.string().url(), + models: z + .string() + .min(1, { message: "Models is required" }) + .refine( + (models) => { + const modelsArray = models.split(","); + + return modelsArray.length === uniq(modelsArray).length; + }, + { message: "All model names should be unique" }, + ), +}); + +export const AIProviderFormSchema = z.discriminatedUnion("locationType", [ + CloudAIProviderDetailsFormSchema, + LocalAIProviderDetailsFormSchema, +]); + +export type AIProviderFormType = z.infer; diff --git a/apps/opik-frontend/src/components/shared/ChartTooltipContent/ChartTooltipContent.tsx b/apps/opik-frontend/src/components/shared/ChartTooltipContent/ChartTooltipContent.tsx index ec0b98f893..77a0cf8191 100644 --- a/apps/opik-frontend/src/components/shared/ChartTooltipContent/ChartTooltipContent.tsx +++ b/apps/opik-frontend/src/components/shared/ChartTooltipContent/ChartTooltipContent.tsx @@ -84,7 +84,7 @@ const ChartTooltipContent = React.forwardRef< className="flex h-6 w-full flex-wrap items-center gap-1.5 px-2" >
{!isUndefined(item.value) && ( - + {renderValue(item.value)} )} diff --git a/apps/opik-frontend/src/components/ui/select.tsx b/apps/opik-frontend/src/components/ui/select.tsx index 6d8d40637a..4844b3c89c 100644 --- a/apps/opik-frontend/src/components/ui/select.tsx +++ b/apps/opik-frontend/src/components/ui/select.tsx @@ -112,7 +112,7 @@ SelectLabel.displayName = SelectPrimitive.Label.displayName; interface SelectItemProps extends React.ComponentPropsWithoutRef { withoutCheck?: boolean; - description?: string; + description?: React.ReactNode; } const SelectItem = React.forwardRef< @@ -143,7 +143,7 @@ const SelectItem = React.forwardRef< {children}
{description && ( -
+
{description}
)} diff --git a/apps/opik-frontend/src/constants/chart.ts b/apps/opik-frontend/src/constants/chart.ts index 9eea2cb2eb..b4e48aeacc 100644 --- a/apps/opik-frontend/src/constants/chart.ts +++ b/apps/opik-frontend/src/constants/chart.ts @@ -1,5 +1,5 @@ export const DEFAULT_CHART_TICK = { - stroke: "#94A3B8", + stroke: "#373D4D", fontWeight: 200, letterSpacing: "0.05rem", fontSize: "10px", diff --git a/apps/opik-frontend/src/constants/llm.ts b/apps/opik-frontend/src/constants/llm.ts index c218dc8990..2cb67307f9 100644 --- a/apps/opik-frontend/src/constants/llm.ts +++ b/apps/opik-frontend/src/constants/llm.ts @@ -1,4 +1,3 @@ -import { PROVIDER_MODEL_TYPE, PROVIDER_TYPE } from "@/types/providers"; import { LLM_JUDGE, LLM_MESSAGE_ROLE, @@ -6,127 +5,6 @@ import { LLM_SCHEMA_TYPE, } from "@/types/llm"; -type PROVIDER_MODELS_TYPE = { - [key in PROVIDER_TYPE]: { - value: PROVIDER_MODEL_TYPE; - label: string; - structuredOutput?: boolean; - }[]; -}; - -export const PROVIDER_MODELS: PROVIDER_MODELS_TYPE = { - [PROVIDER_TYPE.OPEN_AI]: [ - // GPT-4.0 Models - { - value: PROVIDER_MODEL_TYPE.GPT_4O, - label: "GPT 4o", - structuredOutput: true, - }, - { - value: PROVIDER_MODEL_TYPE.GPT_4O_MINI, - label: "GPT 4o Mini", - structuredOutput: true, - }, - { - value: PROVIDER_MODEL_TYPE.GPT_4O_MINI_2024_07_18, - label: "GPT 4o Mini 2024-07-18", - structuredOutput: true, - }, - { - value: PROVIDER_MODEL_TYPE.GPT_4O_2024_08_06, - label: "GPT 4o 2024-08-06", - structuredOutput: true, - }, - { - value: PROVIDER_MODEL_TYPE.GPT_4O_2024_05_13, - label: "GPT 4o 2024-05-13", - }, - - // GPT-4 Models - { - value: PROVIDER_MODEL_TYPE.GPT_4_TURBO, - label: "GPT 4 Turbo", - }, - { - value: PROVIDER_MODEL_TYPE.GPT_4, - label: "GPT 4", - }, - { - value: PROVIDER_MODEL_TYPE.GPT_4_TURBO_PREVIEW, - label: "GPT 4 Turbo Preview", - }, - { - value: PROVIDER_MODEL_TYPE.GPT_4_TURBO_2024_04_09, - label: "GPT 4 Turbo 2024-04-09", - }, - { - value: PROVIDER_MODEL_TYPE.GPT_4_1106_PREVIEW, - label: "GPT 4 1106 Preview", - }, - { - value: PROVIDER_MODEL_TYPE.GPT_4_0613, - label: "GPT 4 0613", - }, - { - value: PROVIDER_MODEL_TYPE.GPT_4_0125_PREVIEW, - label: "GPT 4 0125 Preview", - }, - - // GPT-3.5 Models - { - value: PROVIDER_MODEL_TYPE.GPT_3_5_TURBO, - label: "GPT 3.5 Turbo", - }, - { - value: PROVIDER_MODEL_TYPE.GPT_3_5_TURBO_1106, - label: "GPT 3.5 Turbo 1106", - }, - { - value: PROVIDER_MODEL_TYPE.GPT_3_5_TURBO_0125, - label: "GPT 3.5 Turbo 0125", - }, - ], - - [PROVIDER_TYPE.ANTHROPIC]: [ - { - value: PROVIDER_MODEL_TYPE.CLAUDE_3_5_SONNET_20241022, - label: "Claude 3.5 Sonnet 2024-10-22", - }, - { - value: PROVIDER_MODEL_TYPE.CLAUDE_3_5_HAIKU_20241022, - label: "Claude 3.5 Haiku 2024-10-22", - }, - { - value: PROVIDER_MODEL_TYPE.CLAUDE_3_5_SONNET_20240620, - label: "Claude 3.5 Sonnet 2024-06-20", - }, - { - value: PROVIDER_MODEL_TYPE.CLAUDE_3_OPUS_20240229, - label: "Claude 3 Opus 2024-02-29", - }, - { - value: PROVIDER_MODEL_TYPE.CLAUDE_3_SONNET_20240229, - label: "Claude 3 Sonnet 2024-02-29", - }, - { - value: PROVIDER_MODEL_TYPE.CLAUDE_3_HAIKU_20240307, - label: "Claude 3 Haiku 2024-03-07", - }, - { - value: PROVIDER_MODEL_TYPE.CLAUDE_3_5_SONNET_LATEST, - label: "Claude 3.5 Sonnet Latest", - }, - { - value: PROVIDER_MODEL_TYPE.CLAUDE_3_5_HAIKU_LATEST, - label: "Claude 3.5 Haiku Latest", - }, - { - value: PROVIDER_MODEL_TYPE.CLAUDE_3_OPUS_LATEST, - label: "Claude 3 Opus Latest", - }, - ], -}; - export const DEFAULT_OPEN_AI_CONFIGS = { TEMPERATURE: 0, MAX_COMPLETION_TOKENS: 1024, diff --git a/apps/opik-frontend/src/constants/providers.ts b/apps/opik-frontend/src/constants/providers.ts index ec0ef44ca7..2c9fc78585 100644 --- a/apps/opik-frontend/src/constants/providers.ts +++ b/apps/opik-frontend/src/constants/providers.ts @@ -1,23 +1,42 @@ import OpenAIIcon from "@/icons/integrations/openai.svg?react"; import AnthropicIcon from "@/icons/integrations/anthropic.svg?react"; +import OllamaIcon from "@/icons/integrations/ollama.svg?react"; -import { PROVIDER_MODEL_TYPE, PROVIDER_TYPE } from "@/types/providers"; +import { + PROVIDER_LOCATION_TYPE, + PROVIDER_MODEL_TYPE, + PROVIDER_TYPE, +} from "@/types/providers"; type IconType = typeof OpenAIIcon; -export type PROVIDER_OPTION_TYPE = { +type PROVIDER_OPTION_TYPE = { label: string; value: PROVIDER_TYPE; icon: IconType; apiKeyName: string; + defaultModel: PROVIDER_MODEL_TYPE | ""; + description?: string; +}; + +export type CLOUD_PROVIDER_OPTION_TYPE = PROVIDER_OPTION_TYPE & { + locationType: PROVIDER_LOCATION_TYPE.cloud; apiKeyURL: string; - defaultModel: PROVIDER_MODEL_TYPE; +}; + +export type LOCAL_PROVIDER_OPTION_TYPE = PROVIDER_OPTION_TYPE & { + locationType: PROVIDER_LOCATION_TYPE.local; + lsKey: string; }; type PROVIDERS_TYPE = { - [key in PROVIDER_TYPE]: PROVIDER_OPTION_TYPE; + [key in PROVIDER_TYPE]: + | CLOUD_PROVIDER_OPTION_TYPE + | LOCAL_PROVIDER_OPTION_TYPE; }; +export const OLLAMA_LS_KEY = "provider_ollama"; + export const PROVIDERS: PROVIDERS_TYPE = { [PROVIDER_TYPE.OPEN_AI]: { label: "OpenAI", @@ -26,6 +45,7 @@ export const PROVIDERS: PROVIDERS_TYPE = { apiKeyName: "OPENAI_API_KEY", apiKeyURL: "https://platform.openai.com/account/api-keys", defaultModel: PROVIDER_MODEL_TYPE.GPT_4O, + locationType: PROVIDER_LOCATION_TYPE.cloud, }, [PROVIDER_TYPE.ANTHROPIC]: { label: "Anthropic", @@ -34,6 +54,18 @@ export const PROVIDERS: PROVIDERS_TYPE = { apiKeyName: "ANTHROPIC_API_KEY", apiKeyURL: "https://console.anthropic.com/settings/keys", defaultModel: PROVIDER_MODEL_TYPE.CLAUDE_3_5_SONNET_LATEST, + locationType: PROVIDER_LOCATION_TYPE.cloud, + }, + [PROVIDER_TYPE.OLLAMA]: { + label: "Ollama (Experimental)", + value: PROVIDER_TYPE.OLLAMA, + icon: OllamaIcon, + apiKeyName: "OLLAMA_LOCAL_EXPERIMENTAL", + description: + "All configuration for this provider is saved locally, and will not \nbe accessible in different browsers", + locationType: PROVIDER_LOCATION_TYPE.local, + lsKey: OLLAMA_LS_KEY, + defaultModel: "", }, }; diff --git a/apps/opik-frontend/src/hooks/useLLMProviderModelsData.ts b/apps/opik-frontend/src/hooks/useLLMProviderModelsData.ts new file mode 100644 index 0000000000..e227269784 --- /dev/null +++ b/apps/opik-frontend/src/hooks/useLLMProviderModelsData.ts @@ -0,0 +1,216 @@ +import { useCallback } from "react"; +import first from "lodash/first"; +import { + PROVIDER_LOCATION_TYPE, + PROVIDER_MODEL_TYPE, + PROVIDER_MODELS_TYPE, + PROVIDER_TYPE, +} from "@/types/providers"; +import useLocalAIProviderData from "@/hooks/useLocalAIProviderData"; +import { getDefaultProviderKey } from "@/lib/provider"; +import { PROVIDERS } from "@/constants/providers"; + +export type ProviderResolver = ( + modelName?: PROVIDER_MODEL_TYPE | "", +) => PROVIDER_TYPE | ""; + +export type ModelResolver = ( + lastPickedModel: PROVIDER_MODEL_TYPE | "", + setupProviders: PROVIDER_TYPE[], + preferredProvider?: PROVIDER_TYPE | "", +) => PROVIDER_MODEL_TYPE | ""; + +export const PROVIDER_MODELS: PROVIDER_MODELS_TYPE = { + [PROVIDER_TYPE.OPEN_AI]: [ + // GPT-4.0 Models + { + value: PROVIDER_MODEL_TYPE.GPT_4O, + label: "GPT 4o", + structuredOutput: true, + }, + { + value: PROVIDER_MODEL_TYPE.GPT_4O_MINI, + label: "GPT 4o Mini", + structuredOutput: true, + }, + { + value: PROVIDER_MODEL_TYPE.GPT_4O_MINI_2024_07_18, + label: "GPT 4o Mini 2024-07-18", + structuredOutput: true, + }, + { + value: PROVIDER_MODEL_TYPE.GPT_4O_2024_08_06, + label: "GPT 4o 2024-08-06", + structuredOutput: true, + }, + { + value: PROVIDER_MODEL_TYPE.GPT_4O_2024_05_13, + label: "GPT 4o 2024-05-13", + }, + + // GPT-4 Models + { + value: PROVIDER_MODEL_TYPE.GPT_4_TURBO, + label: "GPT 4 Turbo", + }, + { + value: PROVIDER_MODEL_TYPE.GPT_4, + label: "GPT 4", + }, + { + value: PROVIDER_MODEL_TYPE.GPT_4_TURBO_PREVIEW, + label: "GPT 4 Turbo Preview", + }, + { + value: PROVIDER_MODEL_TYPE.GPT_4_TURBO_2024_04_09, + label: "GPT 4 Turbo 2024-04-09", + }, + { + value: PROVIDER_MODEL_TYPE.GPT_4_1106_PREVIEW, + label: "GPT 4 1106 Preview", + }, + { + value: PROVIDER_MODEL_TYPE.GPT_4_0613, + label: "GPT 4 0613", + }, + { + value: PROVIDER_MODEL_TYPE.GPT_4_0125_PREVIEW, + label: "GPT 4 0125 Preview", + }, + + // GPT-3.5 Models + { + value: PROVIDER_MODEL_TYPE.GPT_3_5_TURBO, + label: "GPT 3.5 Turbo", + }, + { + value: PROVIDER_MODEL_TYPE.GPT_3_5_TURBO_1106, + label: "GPT 3.5 Turbo 1106", + }, + { + value: PROVIDER_MODEL_TYPE.GPT_3_5_TURBO_0125, + label: "GPT 3.5 Turbo 0125", + }, + ], + + [PROVIDER_TYPE.ANTHROPIC]: [ + { + value: PROVIDER_MODEL_TYPE.CLAUDE_3_5_SONNET_20241022, + label: "Claude 3.5 Sonnet 2024-10-22", + }, + { + value: PROVIDER_MODEL_TYPE.CLAUDE_3_5_HAIKU_20241022, + label: "Claude 3.5 Haiku 2024-10-22", + }, + { + value: PROVIDER_MODEL_TYPE.CLAUDE_3_5_SONNET_20240620, + label: "Claude 3.5 Sonnet 2024-06-20", + }, + { + value: PROVIDER_MODEL_TYPE.CLAUDE_3_OPUS_20240229, + label: "Claude 3 Opus 2024-02-29", + }, + { + value: PROVIDER_MODEL_TYPE.CLAUDE_3_SONNET_20240229, + label: "Claude 3 Sonnet 2024-02-29", + }, + { + value: PROVIDER_MODEL_TYPE.CLAUDE_3_HAIKU_20240307, + label: "Claude 3 Haiku 2024-03-07", + }, + { + value: PROVIDER_MODEL_TYPE.CLAUDE_3_5_SONNET_LATEST, + label: "Claude 3.5 Sonnet Latest", + }, + { + value: PROVIDER_MODEL_TYPE.CLAUDE_3_5_HAIKU_LATEST, + label: "Claude 3.5 Haiku Latest", + }, + { + value: PROVIDER_MODEL_TYPE.CLAUDE_3_OPUS_LATEST, + label: "Claude 3 Opus Latest", + }, + ], + [PROVIDER_TYPE.OLLAMA]: [ + // the list will be full filled base on data in localstorage + ], +}; + +const useLLMProviderModelsData = () => { + const { localModels, getLocalAIProviderData } = useLocalAIProviderData(); + + const getProviderModels = useCallback(() => { + return { ...PROVIDER_MODELS, ...localModels }; + }, [localModels]); + + const calculateModelProvider = useCallback( + (modelName?: PROVIDER_MODEL_TYPE | ""): PROVIDER_TYPE | "" => { + if (!modelName) { + return ""; + } + + const provider = Object.entries(getProviderModels()).find( + ([providerName, providerModels]) => { + if (providerModels.find((pm) => modelName === pm.value)) { + return providerName; + } + + return false; + }, + ); + + if (!provider) { + return ""; + } + + const [providerName] = provider; + + return providerName as PROVIDER_TYPE; + }, + [getProviderModels], + ); + + const calculateDefaultModel = useCallback( + ( + lastPickedModel: PROVIDER_MODEL_TYPE | "", + setupProviders: PROVIDER_TYPE[], + preferredProvider?: PROVIDER_TYPE | "", + ) => { + const lastPickedModelProvider = calculateModelProvider(lastPickedModel); + + const isLastPickedModelValid = + !!lastPickedModelProvider && + setupProviders.includes(lastPickedModelProvider); + + if (isLastPickedModelValid) { + return lastPickedModel; + } + + const provider = + preferredProvider ?? getDefaultProviderKey(setupProviders); + + if (provider) { + if (PROVIDERS[provider].locationType === PROVIDER_LOCATION_TYPE.local) { + return ( + (first( + (getLocalAIProviderData(provider)?.models || "").split(","), + )?.trim() as PROVIDER_MODEL_TYPE) ?? "" + ); + } else { + return PROVIDERS[provider].defaultModel; + } + } + + return ""; + }, + [calculateModelProvider, getLocalAIProviderData], + ); + + return { + getProviderModels, + calculateModelProvider, + calculateDefaultModel, + }; +}; + +export default useLLMProviderModelsData; diff --git a/apps/opik-frontend/src/hooks/useLocalAIProviderData.ts b/apps/opik-frontend/src/hooks/useLocalAIProviderData.ts new file mode 100644 index 0000000000..9892d77910 --- /dev/null +++ b/apps/opik-frontend/src/hooks/useLocalAIProviderData.ts @@ -0,0 +1,147 @@ +import { useCallback } from "react"; +import { useQuery, useQueryClient } from "@tanstack/react-query"; +import isEmpty from "lodash/isEmpty"; +import isNumber from "lodash/isNumber"; +import isArray from "lodash/isArray"; + +import { safelyParseJSON } from "@/lib/utils"; +import { + LOCAL_PROVIDER_OPTION_TYPE, + PROVIDERS, + PROVIDERS_OPTIONS, +} from "@/constants/providers"; +import { + LocalAIProviderData, + PROVIDER_LOCATION_TYPE, + PROVIDER_MODEL_TYPE, + PROVIDER_MODELS_TYPE, + PROVIDER_TYPE, + ProviderKey, +} from "@/types/providers"; +import { PROVIDERS_KEYS_KEY } from "@/api/api"; + +const useLocalAIProviderData = () => { + const queryClient = useQueryClient(); + + // workaround to recalculate list of local models every type we have any change in PROVIDERS_KEYS_KEY + const { data: localModels } = useQuery({ + queryKey: [PROVIDERS_KEYS_KEY], + queryFn: () => { + const retVal: Partial = {}; + + PROVIDERS_OPTIONS.forEach((option) => { + if (option.locationType === PROVIDER_LOCATION_TYPE.local) { + const providerData: LocalAIProviderData | undefined = + getLocalAIProviderData(option.value); + + if (providerData) { + retVal[option.value] = providerData.models.split(",").map((m) => ({ + value: m.trim() as PROVIDER_MODEL_TYPE, + label: m.trim(), + })); + } + } + }); + + return retVal; + }, + }); + + const setLocalAIProviderData = useCallback( + (provider: PROVIDER_TYPE, data: LocalAIProviderData) => { + const config = PROVIDERS[provider] as LOCAL_PROVIDER_OPTION_TYPE; + localStorage.setItem(config.lsKey, JSON.stringify(data)); + queryClient.invalidateQueries({ queryKey: [PROVIDERS_KEYS_KEY] }); + }, + [queryClient], + ); + + const deleteLocalAIProviderData = useCallback( + (provider: PROVIDER_TYPE) => { + const config = PROVIDERS[provider] as LOCAL_PROVIDER_OPTION_TYPE; + localStorage.removeItem(config.lsKey); + queryClient.invalidateQueries({ queryKey: [PROVIDERS_KEYS_KEY] }); + }, + [queryClient], + ); + + const getLocalAIProviderData = useCallback((provider: PROVIDER_TYPE) => { + let retVal: LocalAIProviderData | undefined = undefined; + const config = PROVIDERS[provider] as LOCAL_PROVIDER_OPTION_TYPE; + const lsData = localStorage.getItem(config.lsKey); + + if (lsData) { + const providerData: LocalAIProviderData | undefined = safelyParseJSON( + lsData, + true, + ); + + retVal = isEmpty(providerData) ? undefined : providerData; + } + + return retVal; + }, []); + + const extendWithLocalData = useCallback( + (data: { total: number; content: ProviderKey[] }) => { + const localData: ProviderKey[] = []; + + PROVIDERS_OPTIONS.forEach((option) => { + if (option.locationType === PROVIDER_LOCATION_TYPE.local) { + const providerData: LocalAIProviderData | undefined = + getLocalAIProviderData(option.value); + + if (providerData) { + localData.push({ + id: option.lsKey, + keyName: option.apiKeyName, + created_at: providerData.created_at, + provider: option.value, + }); + } + } + }); + + return localData.length > 0 && + isNumber(data.total) && + isArray(data.content) + ? { + content: [...data.content, ...localData], + total: data.total + localData.length, + } + : data; + }, + [getLocalAIProviderData], + ); + + const getLocalIAProviderURL = useCallback( + (provider: PROVIDER_TYPE | "") => { + let retVal: string | undefined = undefined; + + if ( + provider && + PROVIDERS[provider].locationType === PROVIDER_LOCATION_TYPE.local + ) { + const providerData = getLocalAIProviderData(provider); + + if (providerData) { + retVal = providerData.url; + } + } + + return retVal; + }, + [getLocalAIProviderData], + ); + + return { + localModels, + extendWithLocalData, + getLocalAIProviderData, + setLocalAIProviderData, + deleteLocalAIProviderData, + getLocalIAProviderURL, + }; +}; + +export default useLocalAIProviderData; diff --git a/apps/opik-frontend/src/icons/integrations/ollama.svg b/apps/opik-frontend/src/icons/integrations/ollama.svg new file mode 100644 index 0000000000..4ad94d2a46 --- /dev/null +++ b/apps/opik-frontend/src/icons/integrations/ollama.svg @@ -0,0 +1,17 @@ + + + + + + + diff --git a/apps/opik-frontend/src/lib/charts.ts b/apps/opik-frontend/src/lib/charts.ts index 0fcf975584..57bb185149 100644 --- a/apps/opik-frontend/src/lib/charts.ts +++ b/apps/opik-frontend/src/lib/charts.ts @@ -5,11 +5,14 @@ import { generateTagVariant } from "@/lib/traces"; export const getDefaultHashedColorsChartConfig = ( lines: string[], labelsMap?: Record, + predefinedColorMap: Record = {}, ) => { return lines.reduce((acc, line) => { acc[line] = { label: labelsMap?.[line] ?? line, - color: TAG_VARIANTS_COLOR_MAP[generateTagVariant(line)!], + color: + predefinedColorMap[line] || + TAG_VARIANTS_COLOR_MAP[generateTagVariant(line)!], }; return acc; }, {}); diff --git a/apps/opik-frontend/src/lib/llm.ts b/apps/opik-frontend/src/lib/llm.ts index 47522d9298..a6e6d3d968 100644 --- a/apps/opik-frontend/src/lib/llm.ts +++ b/apps/opik-frontend/src/lib/llm.ts @@ -1,7 +1,5 @@ import { LLM_MESSAGE_ROLE, LLMMessage } from "@/types/llm"; import { generateRandomString } from "@/lib/utils"; -import { PROVIDER_MODEL_TYPE, PROVIDER_TYPE } from "@/types/providers"; -import { PROVIDER_MODELS } from "@/constants/llm"; export const generateDefaultLLMPromptMessage = ( message: Partial = {}, @@ -13,27 +11,6 @@ export const generateDefaultLLMPromptMessage = ( id: generateRandomString(), }; }; -export const getModelProvider = ( - modelName: PROVIDER_MODEL_TYPE, -): PROVIDER_TYPE | "" => { - const provider = Object.entries(PROVIDER_MODELS).find( - ([providerName, providerModels]) => { - if (providerModels.find((pm) => modelName === pm.value)) { - return providerName; - } - - return false; - }, - ); - - if (!provider) { - return ""; - } - - const [providerName] = provider; - - return providerName as PROVIDER_TYPE; -}; export const getNextMessageType = ( previousMessage: LLMMessage, diff --git a/apps/opik-frontend/src/lib/playground.ts b/apps/opik-frontend/src/lib/playground.ts index e4454dcfab..a80863525e 100644 --- a/apps/opik-frontend/src/lib/playground.ts +++ b/apps/opik-frontend/src/lib/playground.ts @@ -11,12 +11,14 @@ import { PROVIDER_MODEL_TYPE, PROVIDER_TYPE, } from "@/types/providers"; -import { getDefaultProviderKey } from "@/lib/provider"; -import { PROVIDERS } from "@/constants/providers"; -import { generateDefaultLLMPromptMessage, getModelProvider } from "@/lib/llm"; +import { generateDefaultLLMPromptMessage } from "@/lib/llm"; +import { + ModelResolver, + ProviderResolver, +} from "@/hooks/useLLMProviderModelsData"; export const getDefaultConfigByProvider = ( - provider: PROVIDER_TYPE, + provider?: PROVIDER_TYPE | "", ): LLMPromptConfigsType => { if (provider === PROVIDER_TYPE.OPEN_AI) { return { @@ -39,59 +41,30 @@ export const getDefaultConfigByProvider = ( return {}; }; -const getDefaultModel = ( - lastPickedModel: PROVIDER_MODEL_TYPE | "", - setupProviders: PROVIDER_TYPE[], -) => { - const lastPickedModelProvider = lastPickedModel - ? getModelProvider(lastPickedModel) - : ""; - - const isLastPickedModelValid = - !!lastPickedModelProvider && - setupProviders.includes(lastPickedModelProvider); - - if (isLastPickedModelValid) { - return lastPickedModel; - } - - const defaultProviderKey = getDefaultProviderKey(setupProviders); - - if (defaultProviderKey) { - return PROVIDERS[defaultProviderKey]?.defaultModel || ""; - } - - return ""; -}; - -const getDefaultModelConfigs = (model: PROVIDER_MODEL_TYPE | "") => { - if (!model) { - return {}; - } - - const modelProvider = getModelProvider(model); - - return modelProvider ? getDefaultConfigByProvider(modelProvider) : {}; -}; - interface GenerateDefaultPromptParams { initPrompt?: Partial; setupProviders: PROVIDER_TYPE[]; lastPickedModel?: PROVIDER_MODEL_TYPE | ""; + providerResolver: ProviderResolver; + modelResolver: ModelResolver; } export const generateDefaultPrompt = ({ initPrompt = {}, setupProviders = [], lastPickedModel, + providerResolver, + modelResolver, }: GenerateDefaultPromptParams): PlaygroundPromptType => { - const modelByDefault = getDefaultModel(lastPickedModel || "", setupProviders); + const modelByDefault = modelResolver(lastPickedModel || "", setupProviders); + const provider = providerResolver(modelByDefault); return { name: "Prompt", messages: [generateDefaultLLMPromptMessage()], model: modelByDefault, - configs: getDefaultModelConfigs(modelByDefault), + provider, + configs: getDefaultConfigByProvider(provider), ...initPrompt, id: generateRandomString(), }; diff --git a/apps/opik-frontend/src/lib/utils.ts b/apps/opik-frontend/src/lib/utils.ts index 10c9adbb51..89c59b04b1 100644 --- a/apps/opik-frontend/src/lib/utils.ts +++ b/apps/opik-frontend/src/lib/utils.ts @@ -34,11 +34,11 @@ export const isValidJsonObject = (string: string) => { return json && isObject(json); }; -export const safelyParseJSON = (string: string) => { +export const safelyParseJSON = (string: string, silent = false) => { try { return JSON.parse(string); } catch (e) { - console.error(e); + if (!silent) console.error(e); return {}; } }; diff --git a/apps/opik-frontend/src/main.scss b/apps/opik-frontend/src/main.scss index 941ff09300..1eb8630f83 100644 --- a/apps/opik-frontend/src/main.scss +++ b/apps/opik-frontend/src/main.scss @@ -274,3 +274,11 @@ background: hsl(var(--secondary)); } } + +.comet-markdown ul { + @apply list-disc pl-6; +} + +.comet-markdown ol { + @apply list-decimal pl-6; +} diff --git a/apps/opik-frontend/src/plugins/comet/UserMenu.tsx b/apps/opik-frontend/src/plugins/comet/UserMenu.tsx index 868ea652fc..a29295731c 100644 --- a/apps/opik-frontend/src/plugins/comet/UserMenu.tsx +++ b/apps/opik-frontend/src/plugins/comet/UserMenu.tsx @@ -94,6 +94,10 @@ const UserMenu = () => { const organizationWorkspaces = workspaces.filter( (workspace) => workspace.organizationId === organization?.id, ); + const teamNames = user.getTeams.teams.map((team) => team.teamName); + const organizationWorkspacesAsMember = organizationWorkspaces.filter( + (workspace) => teamNames.includes(workspace.workspaceName), + ); const isOrganizationAdmin = organization?.role === ORGANIZATION_ROLE_TYPE.admin; const workspacePermissions = userPermissions.find( @@ -189,24 +193,25 @@ const UserMenu = () => {
- {sortBy(organizationWorkspaces, "workspaceName").map( - (workspace) => ( - ( + + - - - - {workspace.workspaceName} - - - - - ), - )} + + + {workspace.workspaceName} + + + + + ))}
{ + modifySelectors(({ className }) => { + return `.group:hover .${e( + `group-hover-except-self${separator}${className}`, + )}:not(:hover)`; + }); + }, + ); + }, + ], }; diff --git a/readme-thumbnail.png b/readme-thumbnail.png index 3ea5f70e1a..997c3cde26 100644 Binary files a/readme-thumbnail.png and b/readme-thumbnail.png differ diff --git a/scripts/generate_openapi.sh b/scripts/generate_openapi.sh index a3926db282..e21b5d93a9 100755 --- a/scripts/generate_openapi.sh +++ b/scripts/generate_openapi.sh @@ -19,7 +19,7 @@ cd - cp $OPENAPI_YML_PATH sdks/code_generation/fern/openapi/ # Copy openapi.yaml for the documentation -cp $OPENAPI_YML_PATH apps/opik-documentation/documentation/rest_api/opik.yaml +cp $OPENAPI_YML_PATH apps/opik-documentation/documentation/fern/openapi/opik.yaml # Generate SDKs with Fern from copied openapi.yaml cd sdks/code_generation diff --git a/sdks/python/examples/langchain_integration_example.py b/sdks/python/examples/langchain_integration_example.py index 5e694748ce..9a9ff59176 100644 --- a/sdks/python/examples/langchain_integration_example.py +++ b/sdks/python/examples/langchain_integration_example.py @@ -12,7 +12,7 @@ def f(test_prompts, chain, callback): llm = fake.FakeListLLM( responses=["I'm sorry, I don't think I'm talented enough to write a synopsis"] ) -template = "Given the title of play, right a synopsys for that. Title: {title}." +template = "Given the title of play, write a synopsys for that. Title: {title}." prompt_template = PromptTemplate(input_variables=["title"], template=template) synopsis_chain = prompt_template | llm callback = OpikTracer(tags=["tag1", "tag2"], metadata={"a": "b"}) diff --git a/sdks/python/setup.py b/sdks/python/setup.py index 48e5819ff2..61ed26387b 100644 --- a/sdks/python/setup.py +++ b/sdks/python/setup.py @@ -53,6 +53,12 @@ "tqdm", "uuid6", ], + extras_require={ + "proxy": [ + "fastapi>=0.100.0", + "uvicorn>=0.23.0", + ], + }, entry_points={ "pytest11": [ "opik = opik.plugins.pytest.hooks", diff --git a/sdks/python/src/opik/_logging.py b/sdks/python/src/opik/_logging.py index 5a4d5d3ad8..db618c6c2b 100644 --- a/sdks/python/src/opik/_logging.py +++ b/sdks/python/src/opik/_logging.py @@ -1,7 +1,6 @@ -from typing import Callable, Any, Optional import functools import logging - +from typing import Any, Callable, Optional, Set from . import config @@ -11,6 +10,8 @@ # when batches are big and payloads are heavy (e.g. base64 encoded data) MAX_MESSAGE_LENGTH = 1024 * 1024 +LOG_ONCE_CACHE: Set[str] = set() + class TruncateFormatter(logging.Formatter): def __init__( @@ -79,3 +80,25 @@ def wrapper(*args: Any, **kwargs: Any) -> Any: return wrapper return decorator + + +def log_once_at_level( + logging_level: int, + message: str, + logger: logging.Logger, + *args: Any, + **kwargs: Any, +) -> None: + """ + Log the given message once at the given level then at the DEBUG + level on further calls. + + This is a global log-once-per-session + """ + global LOG_ONCE_CACHE + + if message not in LOG_ONCE_CACHE: + LOG_ONCE_CACHE.add(message) + logger.log(logging_level, message, *args, **kwargs) + else: + logger.debug(message, *args, **kwargs) diff --git a/sdks/python/src/opik/api_objects/constants.py b/sdks/python/src/opik/api_objects/constants.py index b0881edd5c..b943550cc7 100644 --- a/sdks/python/src/opik/api_objects/constants.py +++ b/sdks/python/src/opik/api_objects/constants.py @@ -4,3 +4,4 @@ FEEDBACK_SCORES_MAX_BATCH_SIZE = 1000 EXPERIMENT_ITEMS_MAX_BATCH_SIZE = 1000 DATASET_ITEMS_MAX_BATCH_SIZE = 1000 +DELETE_TRACE_BATCH_SIZE = 1000 diff --git a/sdks/python/src/opik/api_objects/feedback_score/__init__.py b/sdks/python/src/opik/api_objects/feedback_score/__init__.py new file mode 100644 index 0000000000..94f5775b2a --- /dev/null +++ b/sdks/python/src/opik/api_objects/feedback_score/__init__.py @@ -0,0 +1,3 @@ +from .converters import feedback_scores_public_to_feedback_scores_dict + +__all__ = ["feedback_scores_public_to_feedback_scores_dict"] diff --git a/sdks/python/src/opik/api_objects/feedback_score/converters.py b/sdks/python/src/opik/api_objects/feedback_score/converters.py new file mode 100644 index 0000000000..5c63c59000 --- /dev/null +++ b/sdks/python/src/opik/api_objects/feedback_score/converters.py @@ -0,0 +1,21 @@ +from typing import List +from ...rest_api.types import feedback_score_public +from ... import types + + +def feedback_scores_public_to_feedback_scores_dict( + feedback_scores_public: List[feedback_score_public.FeedbackScorePublic], +) -> List[types.FeedbackScoreDict]: + feedback_scores: List[types.FeedbackScoreDict] = [] + + for feedback_score in feedback_scores_public: + feedback_score_dict = types.FeedbackScoreDict( + name=feedback_score.name, + value=feedback_score.value, + category_name=feedback_score.category_name, + reason=feedback_score.reason, + ) + + feedback_scores.append(feedback_score_dict) + + return feedback_scores diff --git a/sdks/python/src/opik/api_objects/helpers.py b/sdks/python/src/opik/api_objects/helpers.py index bf5245bdcf..fea5913332 100644 --- a/sdks/python/src/opik/api_objects/helpers.py +++ b/sdks/python/src/opik/api_objects/helpers.py @@ -2,17 +2,12 @@ import logging from typing import Optional -import uuid6 - from .. import config, datetime_helpers, logging_messages +from ..id_helpers import generate_id # noqa: F401 , keep it here for backward compatibility with external dependants LOGGER = logging.getLogger(__name__) -def generate_id() -> str: - return str(uuid6.uuid7()) - - def datetime_to_iso8601_if_not_None( value: Optional[datetime.datetime], ) -> Optional[str]: diff --git a/sdks/python/src/opik/api_objects/opik_client.py b/sdks/python/src/opik/api_objects/opik_client.py index eb638981c5..625474214a 100644 --- a/sdks/python/src/opik/api_objects/opik_client.py +++ b/sdks/python/src/opik/api_objects/opik_client.py @@ -15,10 +15,10 @@ trace, dataset, experiment, - helpers, constants, validation_helpers, ) +from .trace import migration as trace_migration from .experiment import helpers as experiment_helpers from .experiment import rest_operations as experiment_rest_operations from .dataset import rest_operations as dataset_rest_operations @@ -35,6 +35,7 @@ httpx_client, url_helpers, rest_client_configurator, + id_helpers, ) LOGGER = logging.getLogger(__name__) @@ -76,6 +77,7 @@ def __init__( self._project_name: str = config_.project_name self._flush_timeout: Optional[int] = config_.default_flush_timeout self._project_name_most_recent_trace: Optional[str] = None + self._use_batching = _use_batching self._initialize_streamer( base_url=config_.url_override, @@ -183,7 +185,7 @@ def trace( Returns: trace.Trace: The created trace object. """ - id = id if id is not None else helpers.generate_id() + id = id if id is not None else id_helpers.generate_id() start_time = ( start_time if start_time is not None else datetime_helpers.local_timestamp() ) @@ -218,6 +220,73 @@ def trace( project_name=project_name, ) + def copy_traces( + self, + project_name: str, + destination_project_name: str, + delete_original_project: bool = False, + ) -> None: + """ + Copy traces from one project to another. This method will copy all traces in a source project + to the destination project. Optionally, you can also delete these traces from the source project. + + As the traces are copied, the IDs for both traces and spans will be updated as part of the copy + process. + + Note: This method is not optimized for large projects, if you run into any issues please raise + an issue on GitHub. In addition, be aware that deleting traces that are linked to experiments + will lead to inconsistancies in the UI. + + Args: + project_name: The name of the project to copy traces from. + destination_project_name: The name of the project to copy traces to. + delete_original_project: Whether to delete the original project. Defaults to False. + + Returns: + None + """ + + if not self._use_batching: + raise exceptions.OpikException( + "In order to use this method, you must enable batching using opik.Opik(_use_batching=True)." + ) + + traces_public = self.search_traces(project_name=project_name) + spans_public = self.search_spans(project_name=project_name) + + trace_data = [ + trace.trace_public_to_trace_data( + project_name=project_name, trace_public=trace_public_ + ) + for trace_public_ in traces_public + ] + span_data = [ + span.span_public_to_span_data( + project_name=project_name, span_public_=span_public_ + ) + for span_public_ in spans_public + ] + + new_trace_data, new_span_data = ( + trace_migration.prepare_traces_and_spans_for_copy( + destination_project_name, trace_data, span_data + ) + ) + + for trace_data_ in new_trace_data: + self.trace(**trace_data_.__dict__) + + for span_data_ in new_span_data: + self.span(**span_data_.__dict__) + + if delete_original_project: + trace_ids = [trace_.id for trace_ in trace_data] + for batch in sequence_splitter.split_into_batches( + trace_ids, + max_length=constants.DELETE_TRACE_BATCH_SIZE, + ): + self._rest_client.traces.delete_traces(ids=batch) + def span( self, trace_id: Optional[str] = None, @@ -266,12 +335,16 @@ def span( Returns: span.Span: The created span object. """ - id = id if id is not None else helpers.generate_id() + id = id if id is not None else id_helpers.generate_id() start_time = ( start_time if start_time is not None else datetime_helpers.local_timestamp() ) - parsed_usage = validation_helpers.validate_and_parse_usage(usage, LOGGER) + parsed_usage = validation_helpers.validate_and_parse_usage( + usage=usage, + logger=LOGGER, + provider=provider, + ) if parsed_usage.full_usage is not None: metadata = ( {"usage": parsed_usage.full_usage} @@ -283,7 +356,7 @@ def span( project_name = self._project_name if trace_id is None: - trace_id = helpers.generate_id() + trace_id = id_helpers.generate_id() # TODO: decide what needs to be passed to CreateTraceMessage. # This version is likely not final. create_trace_message = messages.CreateTraceMessage( @@ -313,9 +386,7 @@ def span( output=output, metadata=metadata, tags=tags, - usage=parsed_usage.full_usage - if provider == "google_vertexai" - else parsed_usage.supported_usage, + usage=parsed_usage.supported_usage, model=model, provider=provider, error_info=error_info, @@ -569,7 +640,7 @@ def create_experiment( Returns: experiment.Experiment: The newly created experiment object. """ - id = helpers.generate_id() + id = id_helpers.generate_id() checked_prompts = experiment_helpers.handle_prompt_args( prompt=prompt, diff --git a/sdks/python/src/opik/api_objects/opik_query_language.py b/sdks/python/src/opik/api_objects/opik_query_language.py index 1d589d76c9..60ba3deb48 100644 --- a/sdks/python/src/opik/api_objects/opik_query_language.py +++ b/sdks/python/src/opik/api_objects/opik_query_language.py @@ -5,7 +5,7 @@ import json -from typing import Any, Dict, Optional +from typing import Any, Dict, Optional, Tuple COLUMNS = { "name": "string", @@ -63,6 +63,9 @@ def __init__(self, query_string: Optional[str]): def _is_valid_field_char(self, char: str) -> bool: return char.isalnum() or char == "_" + def _is_valid_connector_char(self, char: str) -> bool: + return char.isalpha() + def _skip_whitespace(self) -> None: while ( self._cursor < len(self.query_string) @@ -70,6 +73,47 @@ def _skip_whitespace(self) -> None: ): self._cursor += 1 + def _check_escaped_key(self) -> Tuple[bool, str]: + if self.query_string[self._cursor] in ('"', "'"): + is_quoted_key = True + quote_type = self.query_string[self._cursor] + self._cursor += 1 + else: + is_quoted_key = False + quote_type = "" + + return is_quoted_key, quote_type + + def _is_valid_escaped_key_char(self, quote_type: str, start: int) -> bool: + if self.query_string[self._cursor] != quote_type: + # Check this isn't the end of the string (means we missed the closing quote) + if self._cursor + 2 >= len(self.query_string): + raise ValueError( + "Missing closing quote for: " + self.query_string[start - 1 :] + ) + + return True + + # Check if it's an escaped quote (doubled quote) + if ( + self._cursor + 1 < len(self.query_string) + and self.query_string[self._cursor + 1] == quote_type + ): + # Skip the second quote + self._cursor += 1 + return True + + return False + + def _parse_connector(self) -> str: + start = self._cursor + while self._cursor < len(self.query_string) and self._is_valid_connector_char( + self.query_string[self._cursor] + ): + self._cursor += 1 + connector = self.query_string[start : self._cursor] + return connector + def _parse_field(self) -> Dict[str, Any]: # Skip whitespace self._skip_whitespace() @@ -84,14 +128,30 @@ def _parse_field(self) -> Dict[str, Any]: # Parse the key if it exists if self.query_string[self._cursor] == ".": + # Skip the "." self._cursor += 1 + + # Check if the key is quoted + is_quoted_key, quote_type = self._check_escaped_key() + start = self._cursor - while self._cursor < len(self.query_string) and self._is_valid_field_char( - self.query_string[self._cursor] + while self._cursor < len(self.query_string) and ( + self._is_valid_field_char(self.query_string[self._cursor]) + or ( + is_quoted_key and self._is_valid_escaped_key_char(quote_type, start) + ) ): self._cursor += 1 + key = self.query_string[start : self._cursor] + # If escaped key, skip the closing quote + if is_quoted_key: + key = key.replace( + quote_type * 2, quote_type + ) # Replace doubled quotes with single quotes + self._cursor += 1 + # Keys are only supported for usage, feedback_scores and metadata if field not in ["usage", "feedback_scores", "metadata"]: raise ValueError( @@ -168,6 +228,8 @@ def _parse_value(self) -> Dict[str, Any]: if self.query_string[self._cursor] == '"': self._cursor += 1 start = self._cursor + + # TODO: replace with new quote parser used in field parser while ( self._cursor < len(self.query_string) and self.query_string[self._cursor] != '"' @@ -201,20 +263,37 @@ def _parse(self) -> Optional[str]: if len(self.query_string) == 0: return None - # Parse fields - parsed_field = self._parse_field() + expressions = [] - # Parse operators - parsed_operator = self._parse_operator(parsed_field["field"]) + while True: + # Parse fields + parsed_field = self._parse_field() - # Parse values - parsed_value = self._parse_value() + # Parse operators + parsed_operator = self._parse_operator(parsed_field["field"]) - # Check for any trailing characters - self._skip_whitespace() - if self._cursor < len(self.query_string): - raise ValueError( - f"Invalid filter string, trailing characters {self.query_string[self._cursor:]}" - ) + # Parse values + parsed_value = self._parse_value() + + expressions.append({**parsed_field, **parsed_operator, **parsed_value}) + + self._skip_whitespace() + + if self._cursor < len(self.query_string): + position = self._cursor + connector = self._parse_connector() + + if connector.lower() == "and": + continue + elif connector.lower() == "or": + raise ValueError( + "Invalid filter string, OR is not currently supported" + ) + else: + raise ValueError( + f"Invalid filter string, trailing characters {self.query_string[position:]}" + ) + else: + break - return json.dumps([{**parsed_field, **parsed_operator, **parsed_value}]) + return json.dumps(expressions) diff --git a/sdks/python/src/opik/api_objects/span/__init__.py b/sdks/python/src/opik/api_objects/span/__init__.py new file mode 100644 index 0000000000..935d2cc9a6 --- /dev/null +++ b/sdks/python/src/opik/api_objects/span/__init__.py @@ -0,0 +1,4 @@ +from .span import Span, SpanData +from .converters import span_public_to_span_data + +__all__ = ["Span", "SpanData", "span_public_to_span_data"] diff --git a/sdks/python/src/opik/api_objects/span/converters.py b/sdks/python/src/opik/api_objects/span/converters.py new file mode 100644 index 0000000000..1b034387e6 --- /dev/null +++ b/sdks/python/src/opik/api_objects/span/converters.py @@ -0,0 +1,34 @@ +from ...rest_api.types import span_public +from .. import feedback_score +from . import span + + +# TODO: project_name has to be passed as only the project_id is part of TracePublic and +# we want to avoid an API call to get it. This should be improved +def span_public_to_span_data( + project_name: str, span_public_: span_public.SpanPublic +) -> span.SpanData: + feedback_scores = span_public_.feedback_scores or [] + feedback_scores_dict = ( + feedback_score.feedback_scores_public_to_feedback_scores_dict(feedback_scores) + ) + + return span.SpanData( + project_name=project_name, + id=span_public_.id, + trace_id=span_public_.trace_id, + parent_span_id=span_public_.parent_span_id, + name=span_public_.name, + type=span_public_.type, + start_time=span_public_.start_time, + end_time=span_public_.end_time, + metadata=span_public_.metadata, + input=span_public_.input, + output=span_public_.output, + tags=span_public_.tags, + usage=span_public_.usage, + feedback_scores=feedback_scores_dict, + model=span_public_.model, + provider=span_public_.provider, + error_info=span_public_.error_info, + ) diff --git a/sdks/python/src/opik/api_objects/span.py b/sdks/python/src/opik/api_objects/span/span.py similarity index 97% rename from sdks/python/src/opik/api_objects/span.py rename to sdks/python/src/opik/api_objects/span/span.py index a136a74dc9..2ba461d021 100644 --- a/sdks/python/src/opik/api_objects/span.py +++ b/sdks/python/src/opik/api_objects/span/span.py @@ -3,7 +3,7 @@ import logging from typing import Optional, Any, List, Dict -from ..types import ( +from ...types import ( SpanType, UsageDict, DistributedTraceHeadersDict, @@ -11,9 +11,9 @@ ErrorInfoDict, ) -from ..message_processing import streamer, messages -from .. import datetime_helpers -from . import helpers, validation_helpers, constants +from ...message_processing import streamer, messages +from ... import datetime_helpers, id_helpers +from .. import helpers, validation_helpers, constants from opik import dict_utils LOGGER = logging.getLogger(__name__) @@ -113,7 +113,9 @@ def update( Returns: None """ - parsed_usage = validation_helpers.validate_and_parse_usage(usage, LOGGER) + parsed_usage = validation_helpers.validate_and_parse_usage( + usage, LOGGER, provider + ) if parsed_usage.full_usage is not None: metadata = ( {"usage": parsed_usage.full_usage} @@ -178,11 +180,13 @@ def span( Returns: Span: The created child span object. """ - span_id = id if id is not None else helpers.generate_id() + span_id = id if id is not None else id_helpers.generate_id() start_time = ( start_time if start_time is not None else datetime_helpers.local_timestamp() ) - parsed_usage = validation_helpers.validate_and_parse_usage(usage, LOGGER) + parsed_usage = validation_helpers.validate_and_parse_usage( + usage, LOGGER, provider + ) if parsed_usage.full_usage is not None: metadata = ( {"usage": parsed_usage.full_usage} diff --git a/sdks/python/src/opik/api_objects/trace/__init__.py b/sdks/python/src/opik/api_objects/trace/__init__.py new file mode 100644 index 0000000000..37623fa322 --- /dev/null +++ b/sdks/python/src/opik/api_objects/trace/__init__.py @@ -0,0 +1,8 @@ +from .trace import Trace, TraceData +from .converters import trace_public_to_trace_data + +__all__ = [ + "Trace", + "TraceData", + "trace_public_to_trace_data", +] diff --git a/sdks/python/src/opik/api_objects/trace/converters.py b/sdks/python/src/opik/api_objects/trace/converters.py new file mode 100644 index 0000000000..25c5bf4eb4 --- /dev/null +++ b/sdks/python/src/opik/api_objects/trace/converters.py @@ -0,0 +1,29 @@ +from ...rest_api.types import trace_public +from . import trace +from .. import feedback_score + + +# TODO: project_name has to be passed as only the project_id is part of TracePublic and +# we want to avoid an API call to get it. This should be improved. +def trace_public_to_trace_data( + project_name: str, trace_public: trace_public.TracePublic +) -> trace.TraceData: + feedback_scores = trace_public.feedback_scores or [] + feedback_scores_dict = ( + feedback_score.feedback_scores_public_to_feedback_scores_dict(feedback_scores) + ) + + return trace.TraceData( + project_name=project_name, + id=trace_public.id, + name=trace_public.name, + start_time=trace_public.start_time, + end_time=trace_public.end_time, + metadata=trace_public.metadata, + input=trace_public.input, + output=trace_public.output, + tags=trace_public.tags, + feedback_scores=feedback_scores_dict, + created_by=trace_public.created_by, + error_info=trace_public.error_info, + ) diff --git a/sdks/python/src/opik/api_objects/trace/migration.py b/sdks/python/src/opik/api_objects/trace/migration.py new file mode 100644 index 0000000000..c477129caf --- /dev/null +++ b/sdks/python/src/opik/api_objects/trace/migration.py @@ -0,0 +1,48 @@ +from . import trace +from .. import span +from ... import id_helpers +from typing import List, Tuple +import logging + +LOGGER = logging.getLogger(__name__) + + +def prepare_traces_and_spans_for_copy( + destination_project_name: str, + traces_data: List[trace.TraceData], + spans_data: List[span.SpanData], +) -> Tuple[List[trace.TraceData], List[span.SpanData]]: + trace_id_mapping = {} + traces_copy = [] + for trace_ in traces_data: + id = id_helpers.generate_id(trace_.start_time) + trace_id_mapping[trace_.id] = id + + trace_.id = id + trace_.project_name = destination_project_name + traces_copy.append(trace_) + + span_id_mapping = {} + for span_ in spans_data: + id = id_helpers.generate_id(span_.start_time) + span_id_mapping[span_.id] = id + + spans_copy = [] + for span_ in spans_data: + if span_.trace_id not in trace_id_mapping: + LOGGER.debug( + "While copying a span to a new project, found orphan span that will not be copied with id: %s and trace id: %s", + span_.id, + span_.trace_id, + ) + continue + + span_.project_name = destination_project_name + span_.trace_id = trace_id_mapping[span_.trace_id] + if span_.parent_span_id: + span_.parent_span_id = trace_id_mapping.get(span_.parent_span_id) + + span_.id = span_id_mapping[span_.id] + spans_copy.append(span_) + + return traces_copy, spans_copy diff --git a/sdks/python/src/opik/api_objects/trace.py b/sdks/python/src/opik/api_objects/trace/trace.py similarity index 95% rename from sdks/python/src/opik/api_objects/trace.py rename to sdks/python/src/opik/api_objects/trace/trace.py index a01e637b8c..14aae3098f 100644 --- a/sdks/python/src/opik/api_objects/trace.py +++ b/sdks/python/src/opik/api_objects/trace/trace.py @@ -3,10 +3,16 @@ import logging from typing import Any, Dict, List, Optional -from . import constants, helpers, span, validation_helpers -from .. import datetime_helpers -from ..message_processing import messages, streamer -from ..types import CreatedByType, FeedbackScoreDict, SpanType, UsageDict, ErrorInfoDict +from .. import constants, span, validation_helpers +from ... import datetime_helpers, id_helpers +from ...message_processing import messages, streamer +from ...types import ( + CreatedByType, + FeedbackScoreDict, + SpanType, + UsageDict, + ErrorInfoDict, +) from opik import dict_utils LOGGER = logging.getLogger(__name__) @@ -141,11 +147,13 @@ def span( Returns: span.Span: The created span object. """ - span_id = id if id is not None else helpers.generate_id() + span_id = id if id is not None else id_helpers.generate_id() start_time = ( start_time if start_time is not None else datetime_helpers.local_timestamp() ) - parsed_usage = validation_helpers.validate_and_parse_usage(usage, LOGGER) + parsed_usage = validation_helpers.validate_and_parse_usage( + usage, LOGGER, provider + ) if parsed_usage.full_usage is not None: metadata = ( {"usage": parsed_usage.full_usage} @@ -231,7 +239,7 @@ class TraceData: The TraceData object is returned when calling :func:`opik.opik_context.get_current_trace_data` from a tracked function. """ - id: str = dataclasses.field(default_factory=helpers.generate_id) + id: str = dataclasses.field(default_factory=id_helpers.generate_id) name: Optional[str] = None start_time: Optional[datetime.datetime] = dataclasses.field( default_factory=datetime_helpers.local_timestamp diff --git a/sdks/python/src/opik/api_objects/validation_helpers.py b/sdks/python/src/opik/api_objects/validation_helpers.py index 6b1ff55f59..91f40acfcc 100644 --- a/sdks/python/src/opik/api_objects/validation_helpers.py +++ b/sdks/python/src/opik/api_objects/validation_helpers.py @@ -8,12 +8,17 @@ def validate_and_parse_usage( - usage: Any, logger: logging.Logger + usage: Any, + logger: logging.Logger, + provider: Optional[str], ) -> usage_validator.ParsedUsage: if usage is None: return usage_validator.ParsedUsage() - usage_validator_ = usage_validator.UsageValidator(usage) + usage_validator_ = usage_validator.UsageValidator( + usage=usage, + provider=provider, + ) if usage_validator_.validate().failed(): logger.warning( logging_messages.INVALID_USAGE_WILL_NOT_BE_LOGGED, diff --git a/sdks/python/src/opik/cli.py b/sdks/python/src/opik/cli.py index 37b68b8d4d..8430f08e57 100644 --- a/sdks/python/src/opik/cli.py +++ b/sdks/python/src/opik/cli.py @@ -1,6 +1,7 @@ """CLI tool for Opik.""" import logging +import sys from importlib import metadata import click @@ -25,17 +26,29 @@ def cli() -> None: @cli.command(context_settings={"ignore_unknown_options": True}) @click.option( "--use_local", + "--use-local", is_flag=True, default=False, help="Flag to configure the Opik Python SDK for local Opik deployments.", ) -def configure(use_local: bool) -> None: +@click.option( + "-y", + "--yes", + is_flag=True, + default=False, + help="Flag to automatically answer `yes` whenever a user approval might be required", +) +def configure(use_local: bool, yes: bool) -> None: """ Create a configuration file for the Opik Python SDK, if a configuration file already exists, it will be overwritten. This is also available as a function in the Python SDK. """ + automatic_approvals = yes + if use_local: - opik_configure.configure(use_local=True, force=True) + opik_configure.configure( + use_local=True, force=True, automatic_approvals=automatic_approvals + ) else: deployment_type_choice = interactive_helpers.ask_user_for_deployment_type() @@ -45,18 +58,21 @@ def configure(use_local: bool) -> None: use_local=False, force=True, self_hosted_comet=False, + automatic_approvals=automatic_approvals, ) elif deployment_type_choice == interactive_helpers.DeploymentType.SELF_HOSTED: configurator = opik_configure.OpikConfigurator( use_local=False, force=True, self_hosted_comet=True, + automatic_approvals=automatic_approvals, ) elif deployment_type_choice == interactive_helpers.DeploymentType.LOCAL: configurator = opik_configure.OpikConfigurator( use_local=True, force=True, self_hosted_comet=False, + automatic_approvals=automatic_approvals, ) else: LOGGER.error("Unknown deployment type was selected. Exiting.") @@ -65,5 +81,93 @@ def configure(use_local: bool) -> None: configurator.configure() +@cli.command(context_settings={"ignore_unknown_options": True}) +@click.option( + "--ollama", + is_flag=True, + help="Run as a proxy server for Ollama", +) +@click.option( + "--ollama-host", + default="http://localhost:11434", + help="Ollama server URL when using --ollama-proxy", + show_default=True, +) +@click.option( + "--lm-studio", + is_flag=True, + help="Run as a proxy server for LM Studio", +) +@click.option( + "--lm-studio-host", + default="http://localhost:1234", + help="LM Studio server URL when using --lm-studio-proxy", + show_default=True, +) +@click.option( + "--host", + default="localhost", + help="Host to bind to", + show_default=True, +) +@click.option( + "--port", + default=7860, + help="Port to bind to", + show_default=True, +) +def proxy( + ollama: bool, + ollama_host: str, + lm_studio: bool, + lm_studio_host: str, + host: str, + port: int, +) -> None: + """Start the Opik server.""" + try: + import fastapi # noqa + import uvicorn # noqa + import httpx # noqa + import rich # noqa + except ImportError: + raise click.ClickException( + "Proxy server dependencies not found. Please install them with: pip install opik[proxy]" + ) + + if not ollama and not lm_studio: + click.echo( + "Error: Either --ollama or --lm-studio must be specified", + err=True, + ) + sys.exit(1) + + if ollama and lm_studio: + click.echo("Error: Cannot specify both --ollama and --lm-studio", err=True) + sys.exit(1) + + if ollama: + llm_server_host = ollama_host + llm_server_type = "Ollama" + else: # lm_studio_proxy + llm_server_host = lm_studio_host + llm_server_type = "LM Studio" + + from opik.forwarding_server.app import create_app + from opik.forwarding_server.utils import print_server_startup_message + import uvicorn + + app = create_app(llm_server_host) + print_server_startup_message( + host=host, + port=port, + llm_server_type=llm_server_type, + llm_server_host=llm_server_host, + ) + uvicorn.run( + app, host=host, port=port, log_level="error" + ) # Reduce uvicorn logging to keep output clean + + if __name__ == "__main__": cli() diff --git a/sdks/python/src/opik/configurator/configure.py b/sdks/python/src/opik/configurator/configure.py index 91635e02de..c75b519ee6 100644 --- a/sdks/python/src/opik/configurator/configure.py +++ b/sdks/python/src/opik/configurator/configure.py @@ -31,6 +31,7 @@ def __init__( use_local: bool = False, force: bool = False, self_hosted_comet: bool = False, + automatic_approvals: bool = False, ): self.api_key = api_key self.workspace = workspace @@ -38,6 +39,7 @@ def __init__( self.force = force self.current_config = opik.config.OpikConfig() self.self_hosted_comet = self_hosted_comet + self.automatic_approvals = automatic_approvals # Handle URL # @@ -124,14 +126,19 @@ def _configure_local(self) -> None: return # Step 3: Ask user if they want to use the found local instance - if not is_interactive(): + if not is_interactive() and not self.automatic_approvals: raise ConfigurationError( f"Opik URL is not specified - A local Opik instance was detected at {OPIK_BASE_URL_LOCAL}, to use it set your URL using the environment variable OPIK_URL_OVERRIDE or provide it as an argument. For more details, refer to the documentation: https://www.comet.com/docs/opik/tracing/sdk_configuration." ) - use_url = ask_user_for_approval( - f"Found local Opik instance on: {OPIK_BASE_URL_LOCAL}, do you want to use it? (Y/n)" + use_url = ( + True + if self.automatic_approvals + else ask_user_for_approval( + f"Found local Opik instance on: {OPIK_BASE_URL_LOCAL}, do you want to use it? (Y/n)" + ) ) + if use_url: self.base_url = OPIK_BASE_URL_LOCAL self._update_config() @@ -272,8 +279,12 @@ def _set_workspace(self) -> bool: # Case 3: No workspace provided, prompt the user default_workspace = self._get_default_workspace() - use_default_workspace = ask_user_for_approval( - f'Do you want to use "{default_workspace}" workspace? (Y/n)' + use_default_workspace = ( + True + if self.automatic_approvals + else ask_user_for_approval( + f'Do you want to use "{default_workspace}" workspace? (Y/n)' + ) ) if use_default_workspace: @@ -447,6 +458,7 @@ def configure( url: Optional[str] = None, use_local: bool = False, force: bool = False, + automatic_approvals: bool = False, ) -> None: """ Create a local configuration file for the Python SDK. If a configuration file already exists, @@ -459,6 +471,7 @@ def configure( use_local: Whether to use a local deployment. force: If true, the configuration file will be recreated and existing settings will be overwritten with passed parameters. + automatic_approvals: if True, `yes` will automatically be answered whenever a user approval is required Raises: ConfigurationError @@ -469,5 +482,6 @@ def configure( url=url, use_local=use_local, force=force, + automatic_approvals=automatic_approvals, ) client.configure() diff --git a/sdks/python/src/opik/context_storage.py b/sdks/python/src/opik/context_storage.py index f899ea6fbe..f3926dd819 100644 --- a/sdks/python/src/opik/context_storage.py +++ b/sdks/python/src/opik/context_storage.py @@ -1,6 +1,7 @@ import contextvars +import contextlib -from typing import List, Optional +from typing import List, Optional, Generator from opik.api_objects import span, trace _current_trace_data_context: contextvars.ContextVar[Optional[trace.TraceData]] = ( @@ -76,3 +77,25 @@ def set_trace_data(trace: Optional[trace.TraceData]) -> None: def clear_all() -> None: _current_trace_data_context.set(None) _spans_data_stack_context.set([]) + + +@contextlib.contextmanager +def temporary_context( + span_data: span.SpanData, trace_data: Optional[trace.TraceData] +) -> Generator[None, None, None]: + """ + Temporary adds span and trace data to the context. + If trace_data is None, it has no effect on the current trace in the context. + """ + try: + original_trace = get_trace_data() + + if trace_data is not None: + set_trace_data(trace=trace_data) + + add_span_data(span_data) + + yield + finally: + set_trace_data(original_trace) + pop_span_data() diff --git a/sdks/python/src/opik/decorator/base_track_decorator.py b/sdks/python/src/opik/decorator/base_track_decorator.py index 9105263413..573ad597bc 100644 --- a/sdks/python/src/opik/decorator/base_track_decorator.py +++ b/sdks/python/src/opik/decorator/base_track_decorator.py @@ -11,9 +11,7 @@ Optional, Callable, Tuple, - Generator, Union, - AsyncGenerator, ) from ..types import SpanType, DistributedTraceHeadersDict, ErrorInfoDict @@ -23,8 +21,9 @@ inspect_helpers, error_info_collector, ) -from ..api_objects import opik_client, helpers, span, trace -from .. import context_storage, logging_messages, datetime_helpers, config +from ..api_objects import opik_client, span, trace +from .. import context_storage, logging_messages, config +from . import span_creation_handler LOGGER = logging.getLogger(__name__) @@ -134,17 +133,144 @@ def _decorate( func: Callable, track_options: arguments_helpers.TrackOptions, ) -> Callable: - if not inspect_helpers.is_async(func): - return self._tracked_sync( + """ + Tracking strategies: + + * Regular sync and async functions/methods: start the span when the + function is called, end the span when the function is finished. While the + function is working, span is kept in opik context, so it can be a parent for the + spans created by nested tracked functions. + + * Generators and async generators: start the span when generator started + yielding values, end the trace when generator finished yielding values. + Span is kept in the opik context only while __next__ or __anext__ method is working. + It means that the span can be a parent only for spans created by tracked functions + called inside __next__ or __anext__. + + * Sync and async functions that return a stream or stream manager object + recognizable by `_streams_handler`: span is started when the function is called, + finished when the stream chunks are exhausted. Span is NOT kept inside the opik context. + So these spans can't be parents for other spans. This is usually the case LLM API calls + with `stream=True`. + """ + if inspect.isgeneratorfunction(func): + return self._tracked_sync_generator(func=func, track_options=track_options) + + if inspect.isasyncgenfunction(func): + return self._tracked_async_generator( + func=func, + track_options=track_options, + ) + + if inspect_helpers.is_async(func): + return self._tracked_async( func=func, track_options=track_options, ) - return self._tracked_async( + return self._tracked_sync( func=func, track_options=track_options, ) + def _tracked_sync_generator( + self, func: Callable, track_options: arguments_helpers.TrackOptions + ) -> Callable: + @functools.wraps(func) + def wrapper(*args, **kwargs) -> Any: # type: ignore + try: + opik_distributed_trace_headers: Optional[ + DistributedTraceHeadersDict + ] = kwargs.pop("opik_distributed_trace_headers", None) + + start_span_arguments = self._start_span_inputs_preprocessor( + func=func, + track_options=track_options, + args=args, + kwargs=kwargs, + ) + except Exception as exception: + LOGGER.error( + logging_messages.UNEXPECTED_EXCEPTION_ON_SPAN_CREATION_FOR_TRACKED_FUNCTION, + func.__name__, + (args, kwargs), + str(exception), + exc_info=True, + ) + + result = None + try: + result = generator_wrappers.SyncTrackedGenerator( + func(*args, **kwargs), + start_span_arguments=start_span_arguments, + opik_distributed_trace_headers=opik_distributed_trace_headers, + track_options=track_options, + finally_callback=self._after_call, + ) + return result + except Exception as exception: + LOGGER.debug( + logging_messages.EXCEPTION_RAISED_FROM_TRACKED_FUNCTION, + func.__name__, + (args, kwargs), + str(exception), + exc_info=True, + ) + raise exception + + wrapper.opik_tracked = True # type: ignore + + return wrapper + + def _tracked_async_generator( + self, func: Callable, track_options: arguments_helpers.TrackOptions + ) -> Callable: + @functools.wraps(func) + def wrapper(*args, **kwargs) -> Any: # type: ignore + try: + opik_distributed_trace_headers: Optional[ + DistributedTraceHeadersDict + ] = kwargs.pop("opik_distributed_trace_headers", None) + + start_span_arguments = self._start_span_inputs_preprocessor( + func=func, + track_options=track_options, + args=args, + kwargs=kwargs, + ) + except Exception as exception: + LOGGER.error( + logging_messages.UNEXPECTED_EXCEPTION_ON_SPAN_CREATION_FOR_TRACKED_FUNCTION, + func.__name__, + (args, kwargs), + str(exception), + exc_info=True, + ) + + result = None + try: + result = generator_wrappers.AsyncTrackedGenerator( + func(*args, **kwargs), + start_span_arguments=start_span_arguments, + opik_distributed_trace_headers=opik_distributed_trace_headers, + track_options=track_options, + finally_callback=self._after_call, + ) + return result + except Exception as exception: + LOGGER.debug( + logging_messages.EXCEPTION_RAISED_FROM_TRACKED_FUNCTION, + func.__name__, + (args, kwargs), + str(exception), + exc_info=True, + ) + raise exception + + wrapper.opik_tracked = True # type: ignore + + return wrapper + def _tracked_sync( self, func: Callable, track_options: arguments_helpers.TrackOptions ) -> Callable: @@ -172,13 +298,13 @@ def wrapper(*args, **kwargs) -> Any: # type: ignore error_info = error_info_collector.collect(exception) raise exception finally: - generator_or_generator_container = self._generators_handler( + stream_or_stream_manager = self._streams_handler( result, track_options.capture_output, track_options.generations_aggregator, ) - if generator_or_generator_container is not None: - return generator_or_generator_container + if stream_or_stream_manager is not None: + return stream_or_stream_manager self._after_call( output=result, @@ -211,7 +337,7 @@ async def wrapper(*args, **kwargs) -> Any: # type: ignore try: result = await func(*args, **kwargs) except Exception as exception: - LOGGER.error( + LOGGER.debug( logging_messages.EXCEPTION_RAISED_FROM_TRACKED_FUNCTION, func.__name__, (args, kwargs), @@ -221,13 +347,13 @@ async def wrapper(*args, **kwargs) -> Any: # type: ignore error_info = error_info_collector.collect(exception) raise exception finally: - generator = self._generators_handler( + stream_or_stream_manager = self._streams_handler( result, track_options.capture_output, track_options.generations_aggregator, ) - if generator is not None: # TODO: test this flow for async generators - return generator + if stream_or_stream_manager is not None: + return stream_or_stream_manager self._after_call( output=result, @@ -260,10 +386,17 @@ def _before_call( kwargs=kwargs, ) - self._create_span( - start_span_arguments, - opik_distributed_trace_headers, + created_trace_data, created_span_data = ( + span_creation_handler.create_span_for_current_context( + start_span_arguments=start_span_arguments, + distributed_trace_headers=opik_distributed_trace_headers, + ) ) + if created_trace_data is not None: + context_storage.set_trace_data(created_trace_data) + TRACES_CREATED_BY_DECORATOR.add(created_trace_data.id) + + context_storage.add_span_data(created_span_data) except Exception as exception: LOGGER.error( @@ -274,96 +407,6 @@ def _before_call( exc_info=True, ) - def _create_span( - self, - start_span_arguments: arguments_helpers.StartSpanParameters, - distributed_trace_headers: Optional[DistributedTraceHeadersDict] = None, - ) -> None: - """ - Handles different span creation flows. - """ - span_data: span.SpanData - trace_data: trace.TraceData - - if distributed_trace_headers: - span_data = arguments_helpers.create_span_data( - start_span_arguments=start_span_arguments, - parent_span_id=distributed_trace_headers["opik_parent_span_id"], - trace_id=distributed_trace_headers["opik_trace_id"], - ) - context_storage.add_span_data(span_data) - return - - current_span_data = context_storage.top_span_data() - current_trace_data = context_storage.get_trace_data() - - if current_span_data is not None: - # There is already at least one span in current context. - # Simply attach a new span to it. - assert current_trace_data is not None - - project_name = helpers.resolve_child_span_project_name( - parent_project_name=current_span_data.project_name, - child_project_name=start_span_arguments.project_name, - show_warning=current_trace_data.created_by != "evaluation", - ) - - start_span_arguments.project_name = project_name - - span_data = arguments_helpers.create_span_data( - start_span_arguments=start_span_arguments, - parent_span_id=current_span_data.id, - trace_id=current_span_data.trace_id, - ) - context_storage.add_span_data(span_data) - return - - if current_trace_data is not None and current_span_data is None: - # By default, we expect trace to be created with a span. - # But there can be cases when trace was created and added - # to context manually (not via decorator). - # In that case decorator should just create a span for the existing trace. - - project_name = helpers.resolve_child_span_project_name( - parent_project_name=current_trace_data.project_name, - child_project_name=start_span_arguments.project_name, - show_warning=current_trace_data.created_by != "evaluation", - ) - - start_span_arguments.project_name = project_name - - span_data = arguments_helpers.create_span_data( - start_span_arguments=start_span_arguments, - parent_span_id=None, - trace_id=current_trace_data.id, - ) - context_storage.add_span_data(span_data) - return - - if current_span_data is None and current_trace_data is None: - # Create a trace and root span because it is - # the first decorated function run in current context. - trace_data = trace.TraceData( - id=helpers.generate_id(), - start_time=datetime_helpers.local_timestamp(), - name=start_span_arguments.name, - input=start_span_arguments.input, - metadata=start_span_arguments.metadata, - tags=start_span_arguments.tags, - project_name=start_span_arguments.project_name, - ) - TRACES_CREATED_BY_DECORATOR.add(trace_data.id) - - span_data = arguments_helpers.create_span_data( - start_span_arguments=start_span_arguments, - parent_span_id=None, - trace_id=trace_data.id, - ) - - context_storage.set_trace_data(trace_data) - context_storage.add_span_data(span_data) - return - def _after_call( self, output: Optional[Any], @@ -424,50 +467,24 @@ def _after_call( ) @abc.abstractmethod - def _generators_handler( + def _streams_handler( self, output: Any, capture_output: bool, generations_aggregator: Optional[Callable[[List[Any]], str]], - ) -> Optional[Union[Generator, AsyncGenerator]]: + ) -> Optional[Any]: """ - Subclasses must override this method to customize generator objects handling - This is the implementation for regular generators and async generators that - uses aggregator function passed to track. - - However, sometimes the function might return an instance of some specific class which - is not a python generator itself, but implements some API for iterating through data chunks. - In that case `_generators_handler` must be fully overridden in the subclass. + Subclasses must override this method to customize stream-like objects handling. + Stream objects are usually the objects returned by LLM providers when invoking their API with + `stream=True` option. - This is usually the case when creating an integration with some LLM library. + Opik's approach for such stream objects is to start the span when the API call is made and + finish the span when the stream chunks are exhausted. """ - if inspect.isgenerator(output): - span_to_end, trace_to_end = pop_end_candidates() - # For some reason mypy things wrap_sync_generator returns Any - return generator_wrappers.wrap_sync_generator( # type: ignore[no-any-return] - generator=output, - capture_output=capture_output, - span_to_end=span_to_end, - trace_to_end=trace_to_end, - generations_aggregator=generations_aggregator, - finally_callback=self._after_call, - ) - - if inspect.isasyncgen(output): - span_to_end, trace_to_end = pop_end_candidates() - # For some reason mypy things wrap_async_generator returns Any - return generator_wrappers.wrap_async_generator( # type: ignore[no-any-return] - generator=output, - capture_output=capture_output, - span_to_end=span_to_end, - trace_to_end=trace_to_end, - generations_aggregator=generations_aggregator, - finally_callback=self._after_call, - ) - NOT_A_GENERATOR = None + NO_STREAM_DETECTED = None - return NOT_A_GENERATOR + return NO_STREAM_DETECTED @abc.abstractmethod def _start_span_inputs_preprocessor( diff --git a/sdks/python/src/opik/decorator/generator_wrappers.py b/sdks/python/src/opik/decorator/generator_wrappers.py index 26cbac6a6b..58ab15e3b3 100644 --- a/sdks/python/src/opik/decorator/generator_wrappers.py +++ b/sdks/python/src/opik/decorator/generator_wrappers.py @@ -1,22 +1,28 @@ +import logging from typing import ( - Generator, - Protocol, Any, AsyncGenerator, - Optional, Callable, + Generator, List, + Optional, + Protocol, + TypeVar, + Generic, ) -from opik.types import ErrorInfoDict +from opik import context_storage, logging_messages from opik.api_objects import span, trace -import logging -from opik import logging_messages -from . import error_info_collector +from opik.types import DistributedTraceHeadersDict, ErrorInfoDict + +from . import arguments_helpers, error_info_collector, span_creation_handler LOGGER = logging.getLogger(__name__) +YieldType = TypeVar("YieldType") + + class FinishGeneratorCallback(Protocol): def __call__( self, @@ -28,83 +34,140 @@ def __call__( ) -> None: ... -def wrap_sync_generator( - generator: Generator, - capture_output: bool, - span_to_end: span.SpanData, - trace_to_end: Optional[trace.TraceData], - generations_aggregator: Optional[Callable[[List[Any]], str]], - finally_callback: FinishGeneratorCallback, -) -> Generator[Any, None, None]: - items = [] - error_info: Optional[ErrorInfoDict] = None - try: - for item in generator: - items.append(item) - - yield item - except Exception as exception: +class BaseTrackedGenerator(Generic[YieldType]): + def __init__( + self, + start_span_arguments: arguments_helpers.StartSpanParameters, + opik_distributed_trace_headers: Optional[DistributedTraceHeadersDict], + track_options: arguments_helpers.TrackOptions, + finally_callback: FinishGeneratorCallback, + ): + self._start_span_arguments = start_span_arguments + self._opik_distributed_trace_headers = opik_distributed_trace_headers + self._track_options = track_options + + self._created_span_data: Optional[span.SpanData] = None + self._created_trace_data: Optional[trace.TraceData] = None + + self._accumulated_values: List[YieldType] = [] + + self._finally_callback = finally_callback + + def _ensure_span_and_trace_created(self) -> None: + if self._created_span_data is not None: + return + + self._created_trace_data, self._created_span_data = ( + span_creation_handler.create_span_for_current_context( + self._start_span_arguments, self._opik_distributed_trace_headers + ) + ) + + def _handle_stop_iteration_before_raising(self) -> None: + output = _try_aggregate_items( + self._accumulated_values, + generations_aggregator=self._track_options.generations_aggregator, + ) + self._finally_callback( + output=output, + error_info=None, + capture_output=self._track_options.capture_output, + generators_span_to_end=self._created_span_data, + generators_trace_to_end=self._created_trace_data, + ) + + def _handle_generator_exception_before_raising(self, exception: Exception) -> None: LOGGER.debug( "Exception raised from tracked generator", str(exception), exc_info=True, ) error_info = error_info_collector.collect(exception) - raise exception - finally: - output = ( - _try_aggregate_items(items, generations_aggregator) - if error_info is None - else None - ) - - finally_callback( - output=output, + self._finally_callback( + output=None, error_info=error_info, - generators_span_to_end=span_to_end, - generators_trace_to_end=trace_to_end, - capture_output=capture_output, + capture_output=self._track_options.capture_output, + generators_span_to_end=self._created_span_data, + generators_trace_to_end=self._created_trace_data, ) -async def wrap_async_generator( - generator: AsyncGenerator, - capture_output: bool, - span_to_end: span.SpanData, - trace_to_end: Optional[trace.TraceData], - generations_aggregator: Optional[Callable[[List[Any]], str]], - finally_callback: FinishGeneratorCallback, -) -> AsyncGenerator[Any, None]: - items = [] - error_info: Optional[ErrorInfoDict] = None +class SyncTrackedGenerator(BaseTrackedGenerator[YieldType]): + def __init__( + self, + generator: Generator[YieldType, None, None], + start_span_arguments: arguments_helpers.StartSpanParameters, + opik_distributed_trace_headers: Optional[DistributedTraceHeadersDict], + track_options: arguments_helpers.TrackOptions, + finally_callback: FinishGeneratorCallback, + ) -> None: + super().__init__( + start_span_arguments=start_span_arguments, + opik_distributed_trace_headers=opik_distributed_trace_headers, + track_options=track_options, + finally_callback=finally_callback, + ) + self._generator = generator - try: - async for item in generator: - items.append(item) + def __iter__(self) -> "SyncTrackedGenerator": + return self - yield item - except Exception as exception: - LOGGER.debug( - "Exception raised from tracked async generator", - str(exception), - exc_info=True, - ) - error_info = error_info_collector.collect(exception) - raise exception - finally: - output = ( - _try_aggregate_items(items, generations_aggregator) - if error_info is None - else None + def __next__(self) -> YieldType: + try: + self._ensure_span_and_trace_created() + assert self._created_span_data is not None + + with context_storage.temporary_context( + self._created_span_data, self._created_trace_data + ): + value = next(self._generator) + self._accumulated_values.append(value) + return value + except StopIteration: + self._handle_stop_iteration_before_raising() + raise + except Exception as exception: + self._handle_generator_exception_before_raising(exception) + raise + + +class AsyncTrackedGenerator(BaseTrackedGenerator[YieldType]): + def __init__( + self, + generator: AsyncGenerator[YieldType, None], + start_span_arguments: arguments_helpers.StartSpanParameters, + opik_distributed_trace_headers: Optional[DistributedTraceHeadersDict], + track_options: arguments_helpers.TrackOptions, + finally_callback: FinishGeneratorCallback, + ) -> None: + super().__init__( + start_span_arguments=start_span_arguments, + opik_distributed_trace_headers=opik_distributed_trace_headers, + track_options=track_options, + finally_callback=finally_callback, ) + self._generator = generator - finally_callback( - output=output, - error_info=error_info, - generators_span_to_end=span_to_end, - generators_trace_to_end=trace_to_end, - capture_output=capture_output, - ) + def __aiter__(self) -> "AsyncTrackedGenerator": + return self + + async def __anext__(self) -> YieldType: + try: + self._ensure_span_and_trace_created() + assert self._created_span_data is not None + + with context_storage.temporary_context( + self._created_span_data, self._created_trace_data + ): + value = await self._generator.__anext__() + self._accumulated_values.append(value) + return value + except StopAsyncIteration: + self._handle_stop_iteration_before_raising() + raise + except Exception as exception: + self._handle_generator_exception_before_raising(exception) + raise def _try_aggregate_items( @@ -122,6 +185,6 @@ def _try_aggregate_items( ) output = str(items) else: - output = str(items) # TODO: decide how to convert to string + output = "".join([str(item) for item in items]) return output diff --git a/sdks/python/src/opik/decorator/inspect_helpers.py b/sdks/python/src/opik/decorator/inspect_helpers.py index 12ce11c20b..d534d7180c 100644 --- a/sdks/python/src/opik/decorator/inspect_helpers.py +++ b/sdks/python/src/opik/decorator/inspect_helpers.py @@ -30,6 +30,10 @@ def is_generator(obj: Any) -> bool: return inspect.isgenerator(obj) +def is_generator_function(obj: Any) -> bool: + return inspect.isgeneratorfunction(obj) + + def is_async(func: Callable) -> bool: if inspect.iscoroutinefunction(func): return True diff --git a/sdks/python/src/opik/decorator/span_creation_handler.py b/sdks/python/src/opik/decorator/span_creation_handler.py new file mode 100644 index 0000000000..60cb85f7ba --- /dev/null +++ b/sdks/python/src/opik/decorator/span_creation_handler.py @@ -0,0 +1,97 @@ +from typing import ( + Optional, + Tuple, +) + +from opik import context_storage, datetime_helpers +from opik.api_objects import helpers, span, trace +from opik.types import DistributedTraceHeadersDict + +from . import arguments_helpers + + +def create_span_for_current_context( + start_span_arguments: arguments_helpers.StartSpanParameters, + distributed_trace_headers: Optional[DistributedTraceHeadersDict], +) -> Tuple[Optional[trace.TraceData], span.SpanData]: + """ + Handles different span creation flows. + """ + span_data: span.SpanData + trace_data: trace.TraceData + + if distributed_trace_headers: + span_data = arguments_helpers.create_span_data( + start_span_arguments=start_span_arguments, + parent_span_id=distributed_trace_headers["opik_parent_span_id"], + trace_id=distributed_trace_headers["opik_trace_id"], + ) + + return None, span_data + + current_span_data = context_storage.top_span_data() + current_trace_data = context_storage.get_trace_data() + + if current_span_data is not None: + # There is already at least one span in current context. + # Simply attach a new span to it. + assert current_trace_data is not None + + project_name = helpers.resolve_child_span_project_name( + parent_project_name=current_span_data.project_name, + child_project_name=start_span_arguments.project_name, + show_warning=current_trace_data.created_by != "evaluation", + ) + + start_span_arguments.project_name = project_name + + span_data = arguments_helpers.create_span_data( + start_span_arguments=start_span_arguments, + parent_span_id=current_span_data.id, + trace_id=current_span_data.trace_id, + ) + + return None, span_data + + if current_trace_data is not None and current_span_data is None: + # By default, we expect trace to be created with a span. + # But there can be cases when trace was created and added + # to context manually (not via decorator). + # In that case decorator should just create a span for the existing trace. + + project_name = helpers.resolve_child_span_project_name( + parent_project_name=current_trace_data.project_name, + child_project_name=start_span_arguments.project_name, + show_warning=current_trace_data.created_by != "evaluation", + ) + + start_span_arguments.project_name = project_name + + span_data = arguments_helpers.create_span_data( + start_span_arguments=start_span_arguments, + parent_span_id=None, + trace_id=current_trace_data.id, + ) + + return None, span_data + + if current_span_data is None and current_trace_data is None: + # Create a trace and root span because it is + # the first decorated function run in current context. + trace_data = trace.TraceData( + id=helpers.generate_id(), + start_time=datetime_helpers.local_timestamp(), + name=start_span_arguments.name, + input=start_span_arguments.input, + metadata=start_span_arguments.metadata, + tags=start_span_arguments.tags, + project_name=start_span_arguments.project_name, + ) + + span_data = arguments_helpers.create_span_data( + start_span_arguments=start_span_arguments, + parent_span_id=None, + trace_id=trace_data.id, + ) + + return trace_data, span_data diff --git a/sdks/python/src/opik/decorator/tracker.py b/sdks/python/src/opik/decorator/tracker.py index 711375e0db..79bd98d615 100644 --- a/sdks/python/src/opik/decorator/tracker.py +++ b/sdks/python/src/opik/decorator/tracker.py @@ -1,6 +1,6 @@ import logging -from typing import List, Any, Dict, Optional, Callable, Tuple, Union +from typing import List, Any, Dict, Optional, Callable, Tuple from . import inspect_helpers, arguments_helpers @@ -57,19 +57,13 @@ def _end_span_inputs_preprocessor( return result - def _generators_handler( + def _streams_handler( self, output: Any, capture_output: bool, generations_aggregator: Optional[Callable[[List[Any]], str]], - ) -> Union[ - base_track_decorator.Generator[Any, None, None], - base_track_decorator.AsyncGenerator[Any, None], - None, - ]: - return super()._generators_handler( - output, capture_output, generations_aggregator - ) + ) -> Optional[Any]: + return super()._streams_handler(output, capture_output, generations_aggregator) def flush_tracker(timeout: Optional[int] = None) -> None: diff --git a/apps/opik-documentation/documentation/docs/prompt_engineering/overview.md b/sdks/python/src/opik/forwarding_server/__init__.py similarity index 100% rename from apps/opik-documentation/documentation/docs/prompt_engineering/overview.md rename to sdks/python/src/opik/forwarding_server/__init__.py diff --git a/sdks/python/src/opik/forwarding_server/app.py b/sdks/python/src/opik/forwarding_server/app.py new file mode 100644 index 0000000000..5c870cc0b6 --- /dev/null +++ b/sdks/python/src/opik/forwarding_server/app.py @@ -0,0 +1,284 @@ +"""FastAPI server for forwarding requests to Ollama.""" + +from fastapi import FastAPI, Request, HTTPException +from fastapi.middleware.cors import CORSMiddleware +from fastapi.responses import StreamingResponse, JSONResponse +from typing import AsyncGenerator, Dict, Callable, Any +import json +import logging +from openai import AsyncOpenAI, APIError, APIConnectionError, APITimeoutError +import time +from rich.logging import RichHandler +from rich.console import Console +import uuid + +# Configure rich console +console = Console() + +# Create a new logger for the forwarding server +forward_logger = logging.getLogger("forward-server") +forward_logger.setLevel(logging.INFO) + +# Remove any existing handlers +for handler in forward_logger.handlers: + forward_logger.removeHandler(handler) + +# Add rich handler +rich_handler = RichHandler( + rich_tracebacks=True, + omit_repeated_times=False, + show_path=False, + show_time=True, + markup=True, +) +rich_handler.setFormatter(logging.Formatter("%(message)s")) +forward_logger.addHandler(rich_handler) + + +def log_response( + method: str, url: str, status: int, duration: float, request_id: str +) -> None: + """Log response with color formatting.""" + method_color = { + "GET": "green", + "POST": "yellow", + "PUT": "blue", + "DELETE": "red", + }.get(method, "white") + + status_color = {2: "green", 3: "yellow", 4: "red", 5: "red bold"}.get( + status // 100, "white" + ) + + forward_logger.info( + f"[dim]{request_id}[/] - [{method_color}]{method}[/] {url} [{status_color}]{status}[/] ({duration:.2f}s)" + ) + + +async def log_request_middleware( + request: Request, call_next: Callable[[Request], Any] +) -> Any: + """Middleware to log request details.""" + start_time = time.time() + request_id = str(uuid.uuid4())[:8] + request.state.request_id = request_id + + # Log request details + method = request.method + url = request.url.path + query_params = request.url.query + method_color = { + "GET": "green", + "POST": "yellow", + "PUT": "blue", + "DELETE": "red", + }.get(method, "white") + + forward_logger.info( + f"[dim]{request_id}[/] - [{method_color}]{method}[/] {url}{f' ?{query_params}' if query_params else ''}" + ) + + response = await call_next(request) + + if isinstance(response, StreamingResponse): + original_iterator = response.body_iterator + + async def logged_iterator() -> AsyncGenerator[bytes, None]: + try: + async for chunk in original_iterator: + yield chunk + finally: + duration = time.time() - start_time + log_response( + request.method, + request.url.path, + response.status_code, + duration, + request_id, + ) + + response.body_iterator = logged_iterator() + else: + duration = time.time() - start_time + log_response( + request.method, request.url.path, response.status_code, duration, request_id + ) + + return response + + +async def stream_generator( + stream: AsyncGenerator[Any, None], +) -> AsyncGenerator[str, None]: + """Convert OpenAI stream to SSE format.""" + async for chunk in stream: + yield f"data: {json.dumps(chunk.model_dump())}\n\n" + + +def create_app(llm_server_host: str) -> FastAPI: + app = FastAPI(title="Opik Ollama Proxy") + + # Add middleware + app.middleware("http")(log_request_middleware) + + # Configure CORS + app.add_middleware( + CORSMiddleware, + allow_origins=[ + "https://dev.comet.com", + "https://staging.dev.comet.com", + "https://comet.com", + "http://localhost:5173", + "https://www.comet.com", + "http://localhost:5174", + ], + allow_credentials=True, + allow_methods=["*"], + allow_headers=["*"], + ) + + # Create OpenAI client + client = AsyncOpenAI( + base_url=f"{llm_server_host}/v1", + api_key="", # required but unused + ) + + @app.post("/v1/chat/completions", response_model=None) + async def chat_completions(request: Request) -> Any: + try: + try: + body = await request.json() + except json.JSONDecodeError as e: + # Don't log the full traceback for expected errors + forward_logger.info( + f"[dim]{request.state.request_id}[/] Invalid JSON received: {str(e)}" + ) + raise HTTPException( + status_code=400, + detail={ + "error": f"Invalid JSON: {str(e)}", + "request_id": request.state.request_id, + }, + ) + + stream = body.get("stream", False) + + try: + if stream: + forward_logger.debug( + f"[dim]{request.state.request_id}[/] Starting streaming chat completion" + ) + stream = await client.chat.completions.create(**body) + return StreamingResponse( + stream_generator(stream), media_type="text/event-stream" + ) + else: + forward_logger.debug( + f"[dim]{request.state.request_id}[/] Starting chat completion" + ) + response = await client.chat.completions.create(**body) + return JSONResponse(response.model_dump()) + except APIConnectionError as e: + forward_logger.error( + f"[dim]{request.state.request_id}[/] Failed to connect to LLM server: {str(e)}" + ) + raise HTTPException( + status_code=503, + detail={ + "error": f"Failed to connect to LLM server. Is it running at {llm_server_host}?", + "request_id": request.state.request_id, + }, + ) + except APITimeoutError as e: + forward_logger.error( + f"[dim]{request.state.request_id}[/] LLM server timeout: {str(e)}" + ) + raise HTTPException( + status_code=504, + detail={ + "error": "LLM server took too long to respond", + "request_id": request.state.request_id, + }, + ) + except APIError as e: + forward_logger.error( + f"[dim]{request.state.request_id}[/] LLM server error: {str(e)}" + ) + raise HTTPException( + status_code=e.status_code if hasattr(e, "status_code") else 500, + detail={ + "error": f"LLM server error: {str(e)}", + "request_id": request.state.request_id, + }, + ) + + except HTTPException: + raise + except Exception as e: + # Only log full traceback for unexpected errors + forward_logger.exception( + f"[dim]{request.state.request_id}[/] Error in chat completions endpoint" + ) + raise HTTPException( + status_code=500, + detail={"error": str(e), "request_id": request.state.request_id}, + ) + + @app.get("/v1/models", response_model=None) + async def models(request: Request) -> Dict[str, Any]: + """List available Ollama models.""" + try: + try: + response = await client.models.list() + return JSONResponse(response.model_dump()) + except APIConnectionError as e: + forward_logger.error( + f"[dim]{request.state.request_id}[/] Failed to connect to LLM server: {str(e)}" + ) + raise HTTPException( + status_code=503, + detail={ + "error": f"Failed to connect to LLM server. Is it running at {llm_server_host}?", + "request_id": request.state.request_id, + }, + ) + except APITimeoutError as e: + forward_logger.error( + f"[dim]{request.state.request_id}[/] LLM server timeout: {str(e)}" + ) + raise HTTPException( + status_code=504, + detail={ + "error": "LLM server took too long to respond", + "request_id": request.state.request_id, + }, + ) + except APIError as e: + forward_logger.error( + f"[dim]{request.state.request_id}[/] LLM server error: {str(e)}" + ) + raise HTTPException( + status_code=e.status_code if hasattr(e, "status_code") else 500, + detail={ + "error": f"LLM server error: {str(e)}", + "request_id": request.state.request_id, + }, + ) + + except HTTPException: + raise + except Exception as e: + forward_logger.exception( + f"[dim]{request.state.request_id}[/] Unexpected error in list models endpoint" + ) + raise HTTPException( + status_code=500, + detail={"error": str(e), "request_id": request.state.request_id}, + ) + + @app.get("/health", response_model=None) + async def health() -> Dict[str, str]: + """Health check endpoint.""" + return {"status": "ok"} + + return app diff --git a/sdks/python/src/opik/forwarding_server/utils.py b/sdks/python/src/opik/forwarding_server/utils.py new file mode 100644 index 0000000000..14b205901d --- /dev/null +++ b/sdks/python/src/opik/forwarding_server/utils.py @@ -0,0 +1,93 @@ +"""Utilities for the Opik forwarding server.""" + +from rich.console import Console +from rich.panel import Panel +from rich.text import Text +from rich import box +from rich.align import Align +import httpx +from typing import List + +console = Console() + + +def check_llm_server_running(url: str) -> bool: + """Check if the LLM server is accessible.""" + try: + with httpx.Client() as client: + client.get(f"{url}", timeout=2.0) + return True + except Exception: + return False + + +def get_model_list(local_url: str) -> List[str]: + """Get a list of available models.""" + try: + with httpx.Client() as client: + response = client.get(f"{local_url}/v1/models", timeout=2.0) + res = response.json() + models = [model["id"] for model in res["data"]] + return models + except Exception: + return [] + + +def print_server_startup_message( + host: str, + port: int, + llm_server_type: str, + llm_server_host: str, +) -> None: + """Print a nicely formatted server startup message.""" + # Create main content with improved styling + local_url = f"http://{host if host != '0.0.0.0' else '127.0.0.1'}:{port}" + models = get_model_list(llm_server_host) + + # Status section with improved formatting + content = Text() + if not check_llm_server_running(llm_server_host): + content.append("\n") + content.append( + f"⚠️ The {llm_server_type} server is not running at {llm_server_host}, all LLM calls will fail.\n", + style="bold red", + ) + + content.append( + "\n───────────────────────────────────────────────────────────────────────────────────────────────\n" + ) + + content.append("\n") + content.append( + "The Opik proxy server is now running, you can now navigate to Opik and setup up\n\n" + ) + content.append("🚀 Proxy server running:\n") + content.append(f" - URL: {local_url}/v1/chat/completions\n") + if len(models) > 0: + content.append(f" - Models: {', '.join(models)}\n") + else: + content.append(" - No models available\n") + content.append("\n") + content.append("📚 Documentation:\n") + content.append(" - https://www.comet.com/docs/opik/playground\n") + content.append("\n") + content.append("Note:", style="bold yellow") + content.append( + f"\n This server is meant only for development purposes, for production we recommend deploying {llm_server_type}\n" + "in a scalable and secure way.\n" + ) + + # Create the main panel with rounded corners and title + main_panel = Panel( + Align.left(content), + box=box.ROUNDED, + border_style="cyan", + padding=(0, 2), + title="Opik Proxy Server", + title_align="center", + ) + + # Print everything with proper spacing + console.print() + console.print(main_panel) + console.print() diff --git a/sdks/python/src/opik/id_helpers.py b/sdks/python/src/opik/id_helpers.py index d14982686a..92953f57d6 100644 --- a/sdks/python/src/opik/id_helpers.py +++ b/sdks/python/src/opik/id_helpers.py @@ -1,5 +1,15 @@ from datetime import datetime +from typing import Optional import uuid +import uuid6 + + +def generate_id(timestamp: Optional[datetime] = None) -> str: + if timestamp: + uuid4 = str(uuid.uuid4()) + return str(uuid4_to_uuid7(timestamp, uuid4)) + + return str(uuid6.uuid7()) def uuid4_to_uuid7(user_datetime: datetime, user_uuid: str) -> uuid.UUID: diff --git a/sdks/python/src/opik/integrations/aisuite/aisuite_decorator.py b/sdks/python/src/opik/integrations/aisuite/aisuite_decorator.py index 560b9b8625..3e3878a9cc 100644 --- a/sdks/python/src/opik/integrations/aisuite/aisuite_decorator.py +++ b/sdks/python/src/opik/integrations/aisuite/aisuite_decorator.py @@ -136,12 +136,10 @@ def _end_span_inputs_preprocessor( return result - def _generators_handler( + def _streams_handler( self, output: Any, capture_output: bool, generations_aggregator: Optional[Callable[[List[Any]], str]], ) -> Optional[Union[Generator, AsyncGenerator]]: - return super()._generators_handler( - output, capture_output, generations_aggregator - ) + return super()._streams_handler(output, capture_output, generations_aggregator) diff --git a/sdks/python/src/opik/integrations/anthropic/messages_create_decorator.py b/sdks/python/src/opik/integrations/anthropic/messages_create_decorator.py index 267c40f347..c1c9aa581d 100644 --- a/sdks/python/src/opik/integrations/anthropic/messages_create_decorator.py +++ b/sdks/python/src/opik/integrations/anthropic/messages_create_decorator.py @@ -77,7 +77,7 @@ def _end_span_inputs_preprocessor( return result - def _generators_handler( + def _streams_handler( self, output: Any, capture_output: bool, diff --git a/sdks/python/src/opik/integrations/bedrock/converse_decorator.py b/sdks/python/src/opik/integrations/bedrock/converse_decorator.py index 2cafbfadfe..db9d2013de 100644 --- a/sdks/python/src/opik/integrations/bedrock/converse_decorator.py +++ b/sdks/python/src/opik/integrations/bedrock/converse_decorator.py @@ -70,7 +70,7 @@ def _end_span_inputs_preprocessor( return result - def _generators_handler( # type: ignore + def _streams_handler( # type: ignore self, output: Any, capture_output: bool, diff --git a/sdks/python/src/opik/integrations/bedrock/invoke_agent_decorator.py b/sdks/python/src/opik/integrations/bedrock/invoke_agent_decorator.py index b2aa5086c4..083b3ad2fc 100644 --- a/sdks/python/src/opik/integrations/bedrock/invoke_agent_decorator.py +++ b/sdks/python/src/opik/integrations/bedrock/invoke_agent_decorator.py @@ -62,7 +62,7 @@ def _end_span_inputs_preprocessor( return result - def _generators_handler( # type: ignore + def _streams_handler( # type: ignore self, output: Any, capture_output: bool, diff --git a/sdks/python/src/opik/integrations/crewai/crewai_decorator.py b/sdks/python/src/opik/integrations/crewai/crewai_decorator.py index 5295d19b6c..b838a8724c 100644 --- a/sdks/python/src/opik/integrations/crewai/crewai_decorator.py +++ b/sdks/python/src/opik/integrations/crewai/crewai_decorator.py @@ -200,12 +200,10 @@ def _parse_outputs( return model, provider, output_dict, usage - def _generators_handler( + def _streams_handler( self, output: Any, capture_output: bool, generations_aggregator: Optional[Callable[[List[Any]], str]], ) -> Optional[Union[Generator, AsyncGenerator]]: - return super()._generators_handler( - output, capture_output, generations_aggregator - ) + return super()._streams_handler(output, capture_output, generations_aggregator) diff --git a/sdks/python/src/opik/integrations/dspy/callback.py b/sdks/python/src/opik/integrations/dspy/callback.py index 52b8fdc340..39e0746325 100644 --- a/sdks/python/src/opik/integrations/dspy/callback.py +++ b/sdks/python/src/opik/integrations/dspy/callback.py @@ -4,7 +4,7 @@ import dspy from dspy.utils.callback import BaseCallback -from opik import opik_context +from opik import opik_context, types from opik.api_objects import helpers, span, trace from opik.api_objects.opik_client import get_client_cached from opik.decorator import error_info_collector @@ -238,7 +238,7 @@ def _callback_context_set(self, value: ContextType) -> None: token = self._current_callback_context.set(value) self._map_span_id_or_trace_id_to_token[value.id] = token - def _get_span_type(self, instance: Any) -> span.SpanType: + def _get_span_type(self, instance: Any) -> types.SpanType: if isinstance(instance, dspy.Predict): return "llm" elif isinstance(instance, dspy.LM): diff --git a/sdks/python/src/opik/integrations/guardrails/guardrails_decorator.py b/sdks/python/src/opik/integrations/guardrails/guardrails_decorator.py index fc3afd38fa..007389a23c 100644 --- a/sdks/python/src/opik/integrations/guardrails/guardrails_decorator.py +++ b/sdks/python/src/opik/integrations/guardrails/guardrails_decorator.py @@ -75,12 +75,10 @@ def _end_span_inputs_preprocessor( return result - def _generators_handler( + def _streams_handler( self, output: Any, capture_output: bool, generations_aggregator: Optional[Callable[[List[Any]], str]], ) -> Optional[Union[Generator, AsyncGenerator]]: - return super()._generators_handler( - output, capture_output, generations_aggregator - ) + return super()._streams_handler(output, capture_output, generations_aggregator) diff --git a/sdks/python/src/opik/integrations/langchain/google_run_helpers.py b/sdks/python/src/opik/integrations/langchain/google_run_helpers.py index 45e8d5896c..4f259ad417 100644 --- a/sdks/python/src/opik/integrations/langchain/google_run_helpers.py +++ b/sdks/python/src/opik/integrations/langchain/google_run_helpers.py @@ -1,8 +1,8 @@ import logging -from typing import Any, Dict, Optional, TYPE_CHECKING, Tuple, cast +from typing import Any, Dict, Final, Optional, TYPE_CHECKING, Tuple from opik import logging_messages -from opik.types import LLMUsageInfo, UsageDict +from opik.types import LLMProvider, LLMUsageInfo, UsageDictVertexAI from opik.validation import usage as usage_validator if TYPE_CHECKING: @@ -10,6 +10,8 @@ LOGGER = logging.getLogger(__name__) +PROVIDER_NAME: Final[LLMProvider] = "google_vertexai" + def get_llm_usage_info(run_dict: Optional[Dict[str, Any]] = None) -> LLMUsageInfo: if run_dict is None: @@ -21,21 +23,30 @@ def get_llm_usage_info(run_dict: Optional[Dict[str, Any]] = None) -> LLMUsageInf return LLMUsageInfo(provider=provider, model=model, usage=usage_dict) -def _try_get_token_usage(run_dict: Dict[str, Any]) -> Optional[UsageDict]: +def _try_get_token_usage(run_dict: Dict[str, Any]) -> Optional[UsageDictVertexAI]: try: + provider, _ = _get_provider_and_model(run_dict) + usage_metadata = run_dict["outputs"]["generations"][-1][-1]["generation_info"][ "usage_metadata" ] - token_usage = UsageDict( + token_usage = UsageDictVertexAI( completion_tokens=usage_metadata["candidates_token_count"], prompt_tokens=usage_metadata["prompt_token_count"], total_tokens=usage_metadata["total_token_count"], - ) - token_usage.update(usage_metadata) - - if usage_validator.UsageValidator(token_usage).validate().ok(): - return cast(UsageDict, token_usage) + **usage_metadata, + ) # type: ignore + + if ( + usage_validator.UsageValidator( + usage=token_usage, + provider=provider, + ) + .validate() + .ok() + ): + return token_usage return None except Exception: @@ -77,7 +88,7 @@ def _get_provider_and_model( if invocation_params := run_dict["extra"].get("invocation_params"): provider = invocation_params.get("_type") if provider == "vertexai": - provider = "google_vertexai" + provider = PROVIDER_NAME model = invocation_params.get("model_name") return provider, model diff --git a/sdks/python/src/opik/integrations/langchain/openai_run_helpers.py b/sdks/python/src/opik/integrations/langchain/openai_run_helpers.py index 898f7842fa..2301f76e5d 100644 --- a/sdks/python/src/opik/integrations/langchain/openai_run_helpers.py +++ b/sdks/python/src/opik/integrations/langchain/openai_run_helpers.py @@ -1,7 +1,7 @@ import logging from typing import Any, Dict, Optional, TYPE_CHECKING, Tuple, cast -from opik import logging_messages +from opik import _logging as opik_logging, logging_messages from opik.types import LLMUsageInfo, UsageDict from opik.validation import usage as usage_validator @@ -30,23 +30,36 @@ def _try_get_token_usage(run_dict: Dict[str, Any]) -> Optional[UsageDict]: token usage info might be in different places, different formats or completely missing. """ try: + provider, _ = _get_provider_and_model(run_dict) + if run_dict["outputs"]["llm_output"] is not None: token_usage = run_dict["outputs"]["llm_output"]["token_usage"] - # streaming mode handling (token usage data will be available at the end of streaming) - else: - token_usage_full = run_dict["outputs"]["generations"][-1][-1]["message"][ - "kwargs" - ]["usage_metadata"] - + # streaming mode handling + # token usage data MAY be available at the end of streaming + # in async mode may not provide token usage info + elif token_usage_full := run_dict["outputs"]["generations"][-1][-1]["message"][ + "kwargs" + ].get("usage_metadata"): token_usage = UsageDict( completion_tokens=token_usage_full["output_tokens"], prompt_tokens=token_usage_full["input_tokens"], total_tokens=token_usage_full["total_tokens"], ) token_usage.update(token_usage_full) + else: + opik_logging.log_once_at_level( + logging_level=logging.WARNING, + message=logging_messages.WARNING_TOKEN_USAGE_DATA_IS_NOT_AVAILABLE, + logger=LOGGER, + ) + return None - if usage_validator.UsageValidator(token_usage).validate().ok(): + if ( + usage_validator.UsageValidator(usage=token_usage, provider=provider) + .validate() + .ok() + ): return cast(UsageDict, token_usage) return None @@ -89,13 +102,23 @@ def _get_provider_and_model( provider = None model = None + # here will be always provider and model + # but model name may not be full (model+version) if metadata := run_dict["extra"].get("metadata"): provider = metadata.get("ls_provider") model = metadata.get("ls_model_name") + # try to detect model+version more precise way if possible + # .invoke() mode if llm_output := run_dict["outputs"].get("llm_output"): model = llm_output.get("model_name", model) + # streaming mode + elif generation_info := run_dict["outputs"]["generations"][-1][-1][ + "generation_info" + ]: + model = generation_info.get("model_name", model) + # provider: check base url if base_url := run_dict["extra"].get("invocation_params", {}).get("base_url"): if base_url.host != "api.openai.com": provider = base_url.host diff --git a/sdks/python/src/opik/integrations/langchain/opik_tracer.py b/sdks/python/src/opik/integrations/langchain/opik_tracer.py index e4fde92a0c..0d87310689 100644 --- a/sdks/python/src/opik/integrations/langchain/opik_tracer.py +++ b/sdks/python/src/opik/integrations/langchain/opik_tracer.py @@ -5,15 +5,15 @@ from langchain_core.tracers import BaseTracer from opik import dict_utils, opik_context -from opik.api_objects import opik_client, span, trace -from opik.types import ErrorInfoDict, LLMUsageInfo +from opik.api_objects import span, trace +from opik.types import DistributedTraceHeadersDict, ErrorInfoDict, LLMUsageInfo from . import ( base_llm_patcher, google_run_helpers, openai_run_helpers, opik_encoder_extension, ) -from ...api_objects import helpers +from ...api_objects import helpers, opik_client if TYPE_CHECKING: from uuid import UUID @@ -34,6 +34,9 @@ def _get_span_type(run: Dict[str, Any]) -> SpanType: if run.get("run_type") in ["llm", "tool"]: return cast(SpanType, run.get("run_type")) + if run.get("run_type") in ["prompt"]: + return cast(SpanType, "tool") + return cast(SpanType, "general") @@ -53,6 +56,7 @@ def __init__( metadata: Optional[Dict[str, Any]] = None, graph: Optional["Graph"] = None, project_name: Optional[str] = None, + distributed_headers: Optional[DistributedTraceHeadersDict] = None, **kwargs: Any, ) -> None: super().__init__(**kwargs) @@ -78,9 +82,9 @@ def __init__( self._project_name = project_name - self._opik_client = opik_client.Opik( - _use_batching=True, project_name=project_name - ) + self._distributed_headers = distributed_headers + + self._opik_client = opik_client.get_client_cached() def _persist_run(self, run: "Run") -> None: run_dict: Dict[str, Any] = run.dict() @@ -137,6 +141,14 @@ def _process_start_span(self, run: "Run") -> None: def _track_root_run(self, run_dict: Dict[str, Any]) -> None: run_metadata = run_dict["extra"].get("metadata", {}) root_metadata = dict_utils.deepmerge(self._trace_default_metadata, run_metadata) + + if self._distributed_headers: + self._attach_span_to_distributed_headers( + run_dict=run_dict, + root_metadata=root_metadata, + ) + return + current_span_data = opik_context.get_current_span_data() if current_span_data is not None: self._attach_span_to_existing_span( @@ -233,6 +245,27 @@ def _attach_span_to_existing_trace( self._span_data_map[run_dict["id"]] = span_data self._externally_created_traces_ids.add(current_trace_data.id) + def _attach_span_to_distributed_headers( + self, + run_dict: Dict[str, Any], + root_metadata: Dict[str, Any], + ) -> None: + if self._distributed_headers is None: + raise ValueError("Distributed headers are not set") + + span_data = span.SpanData( + trace_id=self._distributed_headers["opik_trace_id"], + parent_span_id=self._distributed_headers["opik_parent_span_id"], + name=run_dict["name"], + input=run_dict["inputs"], + metadata=root_metadata, + tags=self._trace_default_tags, + project_name=self._project_name, + type=_get_span_type(run_dict), + ) + self._span_data_map[run_dict["id"]] = span_data + self._externally_created_traces_ids.add(span_data.trace_id) + def _process_end_span(self, run: "Run") -> None: run_dict: Dict[str, Any] = run.dict() span_data = self._span_data_map[run.id] diff --git a/sdks/python/src/opik/integrations/openai/openai_decorator.py b/sdks/python/src/opik/integrations/openai/openai_decorator.py index f329f67e3c..e95a59fdbf 100644 --- a/sdks/python/src/opik/integrations/openai/openai_decorator.py +++ b/sdks/python/src/opik/integrations/openai/openai_decorator.py @@ -110,7 +110,7 @@ def _end_span_inputs_preprocessor( return result - def _generators_handler( # type: ignore + def _streams_handler( # type: ignore self, output: Any, capture_output: bool, diff --git a/sdks/python/src/opik/logging_messages.py b/sdks/python/src/opik/logging_messages.py index d2a4b7037a..0ba7216d5b 100644 --- a/sdks/python/src/opik/logging_messages.py +++ b/sdks/python/src/opik/logging_messages.py @@ -56,3 +56,5 @@ PARSE_API_KEY_TOO_MANY_PARTS = "Too many parts (%d) found in the Opik API key: %r" LLM_PROVIDER_RATE_LIMIT_ERROR_DETECTED_IN_EVALUATE_FUNCTION = "LLM provider rate limit error detected. We recommend reducing the amount of parallel requests by setting `task_threads` evaluation parameter to a smaller number" + +WARNING_TOKEN_USAGE_DATA_IS_NOT_AVAILABLE = "You didn't specify argument `stream_usage`=True during LLM initialization. Token usage data is not available for .stream() or .astream() methods." diff --git a/sdks/python/src/opik/plugins/pytest/experiment_runner.py b/sdks/python/src/opik/plugins/pytest/experiment_runner.py index e124a306e5..9afadb4d24 100644 --- a/sdks/python/src/opik/plugins/pytest/experiment_runner.py +++ b/sdks/python/src/opik/plugins/pytest/experiment_runner.py @@ -6,7 +6,7 @@ from opik.api_objects import opik_client from opik.api_objects.experiment import experiment_item from opik.api_objects.dataset import dataset_item -from opik.api_objects import helpers +from opik import id_helpers from opik import datetime_helpers, dict_utils from . import test_runs_storage, test_run_content @@ -59,7 +59,7 @@ def run(client: opik_client.Opik, test_items: List[Item]) -> None: dataset_item_id = dataset_item_id_finder(test_run_content) if dataset_item_id is None: - dataset_item_id = helpers.generate_id() + dataset_item_id = id_helpers.generate_id() filtered_test_run_content_dict = dict_utils.remove_none_from_dict( test_run_content.__dict__ ) diff --git a/sdks/python/src/opik/types.py b/sdks/python/src/opik/types.py index 886fc01a4e..60e362a31f 100644 --- a/sdks/python/src/opik/types.py +++ b/sdks/python/src/opik/types.py @@ -1,7 +1,7 @@ import dataclasses import sys -from typing import Literal, Optional +from typing import Literal, Optional, Union from typing_extensions import TypedDict if sys.version_info < (3, 11): @@ -12,6 +12,7 @@ SpanType = Literal["general", "tool", "llm"] FeedbackType = Literal["numerical", "categorical"] CreatedByType = Literal["evaluation"] +LLMProvider = Literal["openai", "google_vertexai"] class UsageDict(TypedDict): @@ -32,7 +33,32 @@ class UsageDict(TypedDict): """The total number of tokens used, including both prompt and completion.""" +class UsageDictVertexAI(UsageDict): + """ + A TypedDict representing token usage information for Google Vertex AI. + + This class defines the structure for token usage, including fields + for completion tokens, prompt tokens, and the total number of tokens used. + """ + + cached_content_token_count: NotRequired[int] + """The number of tokens cached.""" + + candidates_token_count: int + """The number of tokens used for the completion.""" + + prompt_token_count: int + """The number of tokens used for the prompt.""" + + total_token_count: int + """The total number of tokens used, including both prompt and completion.""" + + class DistributedTraceHeadersDict(TypedDict): + """ + Contains headers for distributed tracing, returned by the :py:func:`opik.opik_context.get_distributed_trace_headers` function. + """ + opik_trace_id: str opik_parent_span_id: str @@ -84,4 +110,4 @@ class ErrorInfoDict(TypedDict): class LLMUsageInfo: provider: Optional[str] = None model: Optional[str] = None - usage: Optional[UsageDict] = None + usage: Optional[Union[UsageDict, UsageDictVertexAI]] = None diff --git a/sdks/python/src/opik/validation/usage.py b/sdks/python/src/opik/validation/usage.py index cc43f31d24..e16a9de94d 100644 --- a/sdks/python/src/opik/validation/usage.py +++ b/sdks/python/src/opik/validation/usage.py @@ -1,20 +1,21 @@ -import pydantic import dataclasses +from typing import Any, Dict, Optional, Union + +import pydantic -from typing import Any, Dict, Optional -from ..types import UsageDict -from . import validator, result +from . import result, validator +from ..types import UsageDict, UsageDictVertexAI class PydanticWrapper(pydantic.BaseModel): model_config = pydantic.ConfigDict(extra="forbid") - usage: UsageDict + usage: Union[UsageDict, UsageDictVertexAI] @dataclasses.dataclass class ParsedUsage: full_usage: Optional[Dict[str, Any]] = None - supported_usage: Optional[UsageDict] = None + supported_usage: Optional[Union[UsageDict, UsageDictVertexAI]] = None EXPECTED_TYPES = "{'completion_tokens': int, 'prompt_tokens': int, 'total_tokens': int}" @@ -25,17 +26,23 @@ class UsageValidator(validator.Validator): Validator for span token usage """ - def __init__(self, usage: Any): + def __init__(self, usage: Any, provider: Optional[str]): self.usage = usage - + self.provider = provider self.parsed_usage = ParsedUsage() def validate(self) -> result.ValidationResult: try: if isinstance(self.usage, dict): - filtered_usage = _keep_supported_keys(self.usage) + filtered_usage = self.supported_keys + + # run validation PydanticWrapper(usage=filtered_usage) - supported_usage = UsageDict(**filtered_usage) # type: ignore + + if self.provider == "google_vertexai": + supported_usage = UsageDictVertexAI(**filtered_usage) # type: ignore + else: + supported_usage = UsageDict(**filtered_usage) # type: ignore self.parsed_usage = ParsedUsage( full_usage=self.usage, supported_usage=supported_usage ) @@ -67,13 +74,18 @@ def failure_reason_message(self) -> str: ), "validate() must be called before accessing failure reason message" return self.validation_result.failure_reasons[0] + @property + def supported_keys(self) -> Dict[str, Any]: + if self.provider == "google_vertexai": + supported_keys = UsageDictVertexAI.__annotations__.keys() + # `openai` and all other + else: + supported_keys = UsageDict.__annotations__.keys() -def _keep_supported_keys(usage: Dict[str, Any]) -> Dict[str, Any]: - supported_keys = UsageDict.__annotations__.keys() - filtered_usage = {} + filtered_usage = {} - for key in supported_keys: - if key in usage: - filtered_usage[key] = usage[key] + for key in supported_keys: + if key in self.usage: + filtered_usage[key] = self.usage[key] - return filtered_usage + return filtered_usage diff --git a/sdks/python/tests/e2e/test_tracing.py b/sdks/python/tests/e2e/test_tracing.py index 1e8be094cb..bcde084604 100644 --- a/sdks/python/tests/e2e/test_tracing.py +++ b/sdks/python/tests/e2e/test_tracing.py @@ -1,3 +1,4 @@ +import time import pytest import uuid @@ -516,6 +517,91 @@ def test_search_spans__happyflow(opik_client): assert spans[0].id == matching_span.id, "Expected to find the matching span" +def test_copy_traces__happyflow(opik_client): + # Log traces + unique_identifier = str(uuid.uuid4())[-6:] + ID_STORAGE = {} + + project_name = f"e2e-tests-copy-traces-project - {unique_identifier}" + for i in range(2): + trace = opik_client.trace( + name="trace", + project_name=project_name, + input={"input": f"test input - {i}"}, + output={"output": f"test output - {i}"}, + feedback_scores=[ + { + "name": "score_trace", + "value": i, + "category_name": "category_", + "reason": "reason_", + } + ], + metadata={"value": i}, + tags=["a", "b"], + ) + ID_STORAGE[f"trace-{i}-id"] = trace.id + + trace.span( + name="span - 0", + input={"input": f"test input - {i} - 0"}, + ) + + # Sleep so span timestamps are ordered due to uuid7 + time.sleep(0.001) + + trace.span( + name="span - 1", + input={"input": f"test input - {i} - 1"}, + ) + + opik_client.flush() + + new_project_name = project_name + "_v2" + opik_client.copy_traces( + project_name=project_name, + destination_project_name=new_project_name, + ) + + opik_client.flush() + + traces = opik_client.search_traces(project_name=new_project_name) + for i, trace in enumerate(reversed(traces)): + verifiers.verify_trace( + opik_client=opik_client, + trace_id=trace.id, + name="trace", + input={"input": f"test input - {i}"}, + output={"output": f"test output - {i}"}, + feedback_scores=[ + { + "id": trace.id, + "name": "score_trace", + "value": i, + "category_name": "category_", + "reason": "reason_", + } + ], + metadata={"value": i}, + tags=["a", "b"], + project_name=new_project_name, + ) + + trace_spans = opik_client.search_spans( + project_name=new_project_name, trace_id=trace.id + ) + for j, span in enumerate(reversed(trace_spans)): + verifiers.verify_span( + opik_client=opik_client, + span_id=span.id, + trace_id=trace.id, + name=f"span - {j}", + input={"input": f"test input - {i} - {j}"}, + parent_span_id=span.parent_span_id, + project_name=new_project_name, + ) + + def test_tracked_function__update_current_span_used_to_update_cost__happyflow( opik_client, ): diff --git a/sdks/python/tests/library_integration/haystack/test_haystack.py b/sdks/python/tests/library_integration/haystack/test_haystack.py index 4890b4c971..c9b9e6c53a 100644 --- a/sdks/python/tests/library_integration/haystack/test_haystack.py +++ b/sdks/python/tests/library_integration/haystack/test_haystack.py @@ -15,6 +15,7 @@ ) +@pytest.mark.skip @pytest.fixture(autouse=True, scope="module") def enable_haystack_content_tracing(): assert ( @@ -24,6 +25,7 @@ def enable_haystack_content_tracing(): yield +@pytest.mark.skip @pytest.mark.parametrize( "project_name, expected_project_name", [ diff --git a/sdks/python/tests/library_integration/langchain/test_langchain.py b/sdks/python/tests/library_integration/langchain/test_langchain.py index 4808a8a7fb..3d689bf34d 100644 --- a/sdks/python/tests/library_integration/langchain/test_langchain.py +++ b/sdks/python/tests/library_integration/langchain/test_langchain.py @@ -1,3 +1,5 @@ +import asyncio + import langchain_google_vertexai import langchain_openai import pytest @@ -9,6 +11,7 @@ from opik.api_objects import opik_client, span, trace from opik.config import OPIK_PROJECT_DEFAULT_NAME from opik.integrations.langchain.opik_tracer import OpikTracer +from opik.types import DistributedTraceHeadersDict from ...testlib import ( ANY_BUT_NONE, ANY_DICT, @@ -76,7 +79,7 @@ def test_langchain__happyflow( spans=[ SpanModel( id=ANY_BUT_NONE, - type="general", + type="tool", name="PromptTemplate", input={"title": "Documentary about Bigfoot in Paris"}, output=ANY_DICT, @@ -123,6 +126,149 @@ def test_langchain__happyflow( assert_equal(EXPECTED_TRACE_TREE, fake_backend.trace_trees[0]) +def test_langchain__distributed_headers__happyflow( + fake_backend, +): + project_name = "langchain-integration-test--distributed-headers" + client = opik_client.get_client_cached() + + # PREPARE DISTRIBUTED HEADERS + trace_data = trace.TraceData( + name="custom-distributed-headers--trace", + input={ + "key1": 1, + "key2": "val2", + }, + project_name=project_name, + tags=["tag_d1", "tag_d2"], + ) + trace_data.init_end_time() + client.trace(**trace_data.__dict__) + + span_data = span.SpanData( + trace_id=trace_data.id, + parent_span_id=None, + name="custom-distributed-headers--span", + input={ + "input": "custom-distributed-headers--input", + }, + project_name=project_name, + tags=["tag_d3", "tag_d4"], + ) + span_data.init_end_time().update( + output={"output": "custom-distributed-headers--output"}, + ) + client.span(**span_data.__dict__) + + distributed_headers = DistributedTraceHeadersDict( + opik_trace_id=span_data.trace_id, + opik_parent_span_id=span_data.id, + ) + + # CALL LLM + llm = fake.FakeListLLM( + responses=["I'm sorry, I don't think I'm talented enough to write a synopsis"] + ) + + template = "Given the title of play, write a synopsys for that. Title: {title}." + + prompt_template = PromptTemplate(input_variables=["title"], template=template) + + synopsis_chain = prompt_template | llm + test_prompts = {"title": "Documentary about Bigfoot in Paris"} + + callback = OpikTracer( + project_name=project_name, + tags=["tag1", "tag2"], + metadata={"a": "b"}, + distributed_headers=distributed_headers, + ) + synopsis_chain.invoke(input=test_prompts, config={"callbacks": [callback]}) + + callback.flush() + + EXPECTED_TRACE_TREE = TraceModel( + id=ANY_BUT_NONE, + name="custom-distributed-headers--trace", + input={"key1": 1, "key2": "val2"}, + output=None, + tags=["tag_d1", "tag_d2"], + start_time=ANY_BUT_NONE, + end_time=ANY_BUT_NONE, + project_name=project_name, + spans=[ + SpanModel( + id=ANY_BUT_NONE, + name="custom-distributed-headers--span", + input={"input": "custom-distributed-headers--input"}, + output={"output": "custom-distributed-headers--output"}, + tags=["tag_d3", "tag_d4"], + start_time=ANY_BUT_NONE, + end_time=ANY_BUT_NONE, + project_name=project_name, + spans=[ + SpanModel( + id=ANY_BUT_NONE, + name="RunnableSequence", + input={"title": "Documentary about Bigfoot in Paris"}, + output=ANY_DICT, + tags=["tag1", "tag2"], + start_time=ANY_BUT_NONE, + end_time=ANY_BUT_NONE, + metadata={"a": "b"}, + project_name=project_name, + spans=[ + SpanModel( + id=ANY_BUT_NONE, + type="tool", + name="PromptTemplate", + input={"title": "Documentary about Bigfoot in Paris"}, + output=ANY_DICT, + metadata={}, + start_time=ANY_BUT_NONE, + end_time=ANY_BUT_NONE, + project_name=project_name, + spans=[], + ), + SpanModel( + id=ANY_BUT_NONE, + type="llm", + name="FakeListLLM", + input={ + "prompts": [ + "Given the title of play, write a synopsys for that. Title: Documentary about Bigfoot in Paris." + ] + }, + output=ANY_DICT, + metadata={ + "invocation_params": { + "responses": [ + "I'm sorry, I don't think I'm talented enough to write a synopsis" + ], + "_type": "fake-list", + "stop": None, + }, + "options": {"stop": None}, + "batch_size": 1, + "metadata": ANY_BUT_NONE, + }, + start_time=ANY_BUT_NONE, + end_time=ANY_BUT_NONE, + project_name=project_name, + spans=[], + ), + ], + ) + ], + ) + ], + ) + + assert len(fake_backend.trace_trees) == 1 + assert len(callback.created_traces()) == 0 + assert_equal(EXPECTED_TRACE_TREE, fake_backend.trace_trees[0]) + + @pytest.mark.parametrize( "llm_model, expected_input_prompt, stream_usage", [ @@ -193,7 +339,7 @@ def test_langchain__openai_llm_is_used__token_usage_is_logged__happyflow( spans=[ SpanModel( id=ANY_BUT_NONE, - type="general", + type="tool", name="PromptTemplate", input={"title": "Documentary about Bigfoot in Paris"}, output={"output": ANY_BUT_NONE}, @@ -239,23 +385,22 @@ def test_langchain__openai_llm_is_used__streaming_mode__token_usage_is_logged__h callback = OpikTracer( tags=["tag3", "tag4"], metadata={"c": "d"}, - project_name="878", ) model = langchain_openai.ChatOpenAI( max_tokens=10, name="custom-openai-llm-name", callbacks=[callback], + # THIS PARAM IS VERY IMPORTANT! + # if it is explicitly set to True - token usage data will be available stream_usage=True, ) chunks = [] - # for chunk in model.stream("what color is the sky?"): for chunk in model.stream( "Given the title of play, write a synopsys for that. Title: Documentary about Bigfoot in Paris." ): chunks.append(chunk) - # print(chunk.content, end="|", flush=True) callback.flush() @@ -330,6 +475,120 @@ def test_langchain__openai_llm_is_used__streaming_mode__token_usage_is_logged__h assert_equal(EXPECTED_TRACE_TREE, fake_backend.trace_trees[0]) +def test_langchain__openai_llm_is_used__async_astream__no_token_usage_is_logged__happyflow( + fake_backend, + ensure_openai_configured, +): + """ + In `astream` mode, the `token_usage` is not provided by langchain. + For trace `input` always will be = {"input": ""} + """ + callback = OpikTracer( + tags=["tag3", "tag4"], + metadata={"c": "d"}, + ) + + model = langchain_openai.ChatOpenAI( + model="gpt-4o", + max_tokens=10, + name="custom-openai-llm-name", + callbacks=[callback], + # `stream_usage` param is VERY IMPORTANT! + # if it is explicitly set to True - token usage data will be available + # "stream_usage": True, + ) + + template = "Given the title of play, write a synopsys for that. Title: {title}." + prompt_template = PromptTemplate(input_variables=["title"], template=template) + + chain = prompt_template | model + + async def stream_generator(chain, inputs): + async for chunk in chain.astream(inputs, config={"callbacks": [callback]}): + yield chunk + + async def invoke_generator(chain, inputs): + async for chunk in stream_generator(chain, inputs): + print(chunk) + + inputs = {"title": "The Hobbit"} + + asyncio.run(invoke_generator(chain, inputs)) + + callback.flush() + + EXPECTED_TRACE_TREE = TraceModel( + id=ANY_BUT_NONE, + name="RunnableSequence", + input={"input": ""}, + output=ANY_DICT, + tags=["tag3", "tag4"], + metadata={ + "c": "d", + }, + start_time=ANY_BUT_NONE, + end_time=ANY_BUT_NONE, + spans=[ + SpanModel( + id=ANY_BUT_NONE, + name="RunnableSequence", + input={"input": ""}, + output=ANY_BUT_NONE, + tags=["tag3", "tag4"], + metadata={ + "c": "d", + }, + start_time=ANY_BUT_NONE, + end_time=ANY_BUT_NONE, + type="general", + model=None, + provider=None, + usage=None, + spans=[ + SpanModel( + id=ANY_BUT_NONE, + name="PromptTemplate", + input={"title": "The Hobbit"}, + output=ANY_BUT_NONE, + tags=None, + metadata={}, + start_time=ANY_BUT_NONE, + end_time=ANY_BUT_NONE, + type="tool", + model=None, + provider=None, + usage=None, + spans=[], + ), + SpanModel( + id=ANY_BUT_NONE, + name="custom-openai-llm-name", + input={ + "prompts": [ + "Human: Given the title of play, write a synopsys for that. Title: The Hobbit." + ] + }, + output=ANY_BUT_NONE, + tags=None, + metadata=ANY_DICT, + start_time=ANY_BUT_NONE, + end_time=ANY_BUT_NONE, + type="llm", + model=ANY_STRING(startswith="gpt-4o"), + provider="openai", + usage=None, + spans=[], + ), + ], + ) + ], + ) + + assert len(fake_backend.trace_trees) == 1 + assert len(callback.created_traces()) == 1 + assert_equal(EXPECTED_TRACE_TREE, fake_backend.trace_trees[0]) + + @pytest.mark.skip @pytest.mark.parametrize( "llm_model, expected_input_prompt, metadata_usage", @@ -413,7 +672,7 @@ def test_langchain__google_vertexai_llm_is_used__token_usage_is_logged__happyflo spans=[ SpanModel( id=ANY_BUT_NONE, - type="general", + type="tool", name="PromptTemplate", input={"title": "Documentary about Bigfoot in Paris"}, output={"output": ANY_BUT_NONE}, @@ -502,7 +761,7 @@ def test_langchain__openai_llm_is_used__error_occurred_during_openai_call__error spans=[ SpanModel( id=ANY_BUT_NONE, - type="general", + type="tool", name="PromptTemplate", input={"title": "Documentary about Bigfoot in Paris"}, output={"output": ANY_BUT_NONE}, @@ -608,7 +867,7 @@ def f(x): spans=[ SpanModel( id=ANY_BUT_NONE, - type="general", + type="tool", name="PromptTemplate", input={"title": "Documentary about Bigfoot in Paris"}, output={"output": ANY_BUT_NONE}, @@ -720,7 +979,7 @@ def f(): spans=[ SpanModel( id=ANY_BUT_NONE, - type="general", + type="tool", name="PromptTemplate", input={"title": "Documentary about Bigfoot in Paris"}, output=ANY_DICT, @@ -826,7 +1085,7 @@ def f(): spans=[ SpanModel( id=ANY_BUT_NONE, - type="general", + type="tool", name="PromptTemplate", input={"title": "Documentary about Bigfoot in Paris"}, output={"output": ANY_BUT_NONE}, diff --git a/sdks/python/tests/unit/api_objects/test_opik_query_language.py b/sdks/python/tests/unit/api_objects/test_opik_query_language.py index e3f4e11210..a96b2ed937 100644 --- a/sdks/python/tests/unit/api_objects/test_opik_query_language.py +++ b/sdks/python/tests/unit/api_objects/test_opik_query_language.py @@ -6,33 +6,76 @@ @pytest.mark.parametrize( "filter_string, expected", [ - ('name = "test"', {"field": "name", "operator": "=", "value": "test"}), + ('name = "test"', [{"field": "name", "operator": "=", "value": "test"}]), ( "usage.total_tokens > 100", - {"field": "usage.total_tokens", "operator": ">", "value": "100"}, + [{"field": "usage.total_tokens", "operator": ">", "value": "100"}], ), ( 'tags contains "important"', - {"field": "tags", "operator": "contains", "value": "important"}, + [{"field": "tags", "operator": "contains", "value": "important"}], ), ( 'output not_contains "error"', - {"field": "output", "operator": "not_contains", "value": "error"}, + [{"field": "output", "operator": "not_contains", "value": "error"}], ), ( "feedback_scores >= 4.5", - {"field": "feedback_scores", "operator": ">=", "value": "4.5"}, + [{"field": "feedback_scores", "operator": ">=", "value": "4.5"}], + ), + # New test cases for quoted identifiers + ( + 'feedback_scores."Answer Relevance" < 0.8', + [ + { + "field": "feedback_scores", + "key": "Answer Relevance", + "operator": "<", + "value": "0.8", + } + ], + ), + ( + 'feedback_scores."Escaped ""Quote""" < 0.8', + [ + { + "field": "feedback_scores", + "key": 'Escaped "Quote"', + "operator": "<", + "value": "0.8", + } + ], + ), + # Test cases for AND: + ( + 'name = "test" AND tags contains "important" ', + [ + {"field": "name", "operator": "=", "value": "test"}, + {"field": "tags", "operator": "contains", "value": "important"}, + ], + ), + ( + 'feedback_scores."Escaped ""Quote""" < 0.8 and feedback_scores >= 4.5', + [ + { + "field": "feedback_scores", + "key": 'Escaped "Quote"', + "operator": "<", + "value": "0.8", + }, + {"field": "feedback_scores", "operator": ">=", "value": "4.5"}, + ], ), ], ) def test_valid_oql_expressions(filter_string, expected): oql = OpikQueryLanguage(filter_string) parsed = json.loads(oql.parsed_filters) - assert len(parsed) == 1 - parsed_result = parsed[0] + assert len(parsed) == len(expected) - for key, value in expected.items(): - assert parsed_result[key] == value + for i, line in enumerate(expected): + for key, value in line.items(): + assert parsed[i][key] == value @pytest.mark.parametrize( @@ -46,6 +89,19 @@ def test_valid_oql_expressions(filter_string, expected): r"When querying usage, invalid_metric is not supported.*", ), ('name = "test" extra_stuff', r"Invalid filter string, trailing characters.*"), + ( + 'feedback_scores."Unterminated Quote < 0.8', + r'Missing closing quote for: "Unterminated Quote < 0.8', + ), + # Tests with AND + ( + 'name = "test" and name = "other" extra_stuff', + r"Invalid filter string, trailing characters.*", + ), + ( + 'name = "test" OR name = "other"', + r"Invalid filter string, OR is not currently supported", + ), ], ) def test_invalid_oql_expressions(filter_string, error_pattern): diff --git a/sdks/python/tests/unit/configurator/test_configure.py b/sdks/python/tests/unit/configurator/test_configure.py index 18ef1806f4..bfbc9d80df 100644 --- a/sdks/python/tests/unit/configurator/test_configure.py +++ b/sdks/python/tests/unit/configurator/test_configure.py @@ -742,6 +742,34 @@ def test_get_workspace_accept_default( 'Do you want to use "default_workspace" workspace? (Y/n)' ) + @patch("opik.configurator.configure.opik.config.OpikConfig") + @patch( + "opik.configurator.configure.OpikConfigurator._get_default_workspace", + return_value="default_workspace", + ) + @patch("opik.configurator.configure.ask_user_for_approval", return_value=True) + def test_get_workspace_accept_default__automatic_approvals_enabled__no_approval_questions_asked( + self, mock_ask_user_for_approval, mock_get_default_workspace, mock_opik_config + ): + """ + Test that the user accepts the default workspace. + """ + current_config = OpikConfig(workspace=OPIK_WORKSPACE_DEFAULT_NAME) + mock_opik_config.return_value = current_config + + configurator = OpikConfigurator( + workspace=None, + force=False, + api_key="valid_api_key", + automatic_approvals=True, + ) + needs_update = configurator._set_workspace() + + assert configurator.workspace == "default_workspace" + assert needs_update is True + mock_get_default_workspace.assert_called_once_with() + mock_ask_user_for_approval.assert_not_called() + @patch("opik.configurator.configure.opik.config.OpikConfig") @patch( "opik.configurator.configure.OpikConfigurator._get_default_workspace", @@ -1087,6 +1115,33 @@ def test_configure_local_uses_local_instance( assert configurator.base_url == OPIK_BASE_URL_LOCAL assert configurator.workspace == OPIK_WORKSPACE_DEFAULT_NAME + @patch("opik.configurator.configure.is_interactive", return_value=True) + @patch("opik.configurator.configure.ask_user_for_approval") + @patch( + "opik.configurator.configure.opik_rest_helpers.is_instance_active", + return_value=True, + ) + @patch("opik.configurator.configure.OpikConfigurator._update_config") + def test_configure_local_uses_local_instance__automatic_approvals_enabled__no_approval_questions_asked( + self, + mock_update_config, + mock_is_instance_active, + mock_ask_user_for_approval, + mock_is_interactive, + ): + """ + Test that the function configures the local instance when found and user approves. + """ + configurator = OpikConfigurator(url=None, force=False, automatic_approvals=True) + configurator._configure_local() + + mock_ask_user_for_approval.assert_not_called() + mock_update_config.assert_called_once_with() + + assert configurator.api_key is None + assert configurator.base_url == OPIK_BASE_URL_LOCAL + assert configurator.workspace == OPIK_WORKSPACE_DEFAULT_NAME + @patch("opik.configurator.configure.is_interactive", return_value=False) @patch("opik.configurator.configure.ask_user_for_approval", return_value=True) @patch( @@ -1111,6 +1166,33 @@ def test_configure_local_uses_local_instance__non_interactive( mock_ask_user_for_approval.assert_not_called() mock_update_config.assert_not_called() + @patch("opik.configurator.configure.is_interactive", return_value=False) + @patch("opik.configurator.configure.ask_user_for_approval") + @patch( + "opik.configurator.configure.opik_rest_helpers.is_instance_active", + return_value=True, + ) + @patch("opik.configurator.configure.OpikConfigurator._update_config") + def test_configure_local_uses_local_instance__non_interactive__automatic_approvals_enabled__no_error_raised( + self, + mock_update_config, + mock_is_instance_active, + mock_ask_user_for_approval, + mock_is_interactive, + ): + """ + Test that the function configures the local instance when found and user approves. + """ + configurator = OpikConfigurator(url=None, force=False, automatic_approvals=True) + configurator._configure_local() + + mock_ask_user_for_approval.assert_not_called() + mock_update_config.assert_called_once_with() + + assert configurator.api_key is None + assert configurator.base_url == OPIK_BASE_URL_LOCAL + assert configurator.workspace == OPIK_WORKSPACE_DEFAULT_NAME + @patch("opik.configurator.configure.is_interactive", return_value=True) @patch("opik.configurator.configure.ask_user_for_approval", return_value=False) @patch("opik.configurator.configure.OpikConfigurator._ask_for_url") diff --git a/sdks/python/tests/unit/decorator/test_tracker_outputs.py b/sdks/python/tests/unit/decorator/test_tracker_outputs.py index 2cedc30640..2706d6b021 100644 --- a/sdks/python/tests/unit/decorator/test_tracker_outputs.py +++ b/sdks/python/tests/unit/decorator/test_tracker_outputs.py @@ -19,11 +19,11 @@ def test_track__one_nested_function__happyflow(fake_backend): - @tracker.track(capture_output=True) + @tracker.track def f_inner(x): return "inner-output" - @tracker.track(capture_output=True) + @tracker.track def f_outer(x): f_inner("inner-input") return "outer-output" @@ -137,16 +137,16 @@ def f(x): def test_track__two_nested_functions__happyflow(fake_backend): - @tracker.track(capture_output=True) + @tracker.track def f_inner(z): return "inner-output" - @tracker.track(capture_output=True) + @tracker.track def f_middle(y): f_inner("inner-input") return "middle-output" - @tracker.track(capture_output=True) + @tracker.track def f_outer(x): f_middle("middle-input") return "outer-output" @@ -202,15 +202,15 @@ def f_outer(x): def test_track__outer_function_has_two_separate_nested_function__happyflow( fake_backend, ): - @tracker.track(capture_output=True) + @tracker.track def f_inner_1(y): return "inner-output-1" - @tracker.track(capture_output=True) + @tracker.track def f_inner_2(y): return "inner-output-2" - @tracker.track(capture_output=True) + @tracker.track def f_outer(x): f_inner_1("inner-input-1") f_inner_2("inner-input-2") @@ -264,11 +264,11 @@ def f_outer(x): def test_track__two_traces__happyflow(fake_backend): - @tracker.track(capture_output=True) + @tracker.track def f_1(x): return "f1-output" - @tracker.track(capture_output=True) + @tracker.track def f_2(x): return "f2-output" @@ -327,7 +327,7 @@ def f_2(x): def test_track__one_function__error_raised__trace_and_span_finished_correctly__outputs_are_None( fake_backend, ): - @tracker.track(capture_output=True) + @tracker.track def f(x): raise Exception("error message") @@ -432,7 +432,7 @@ def f_inner(): def test_track__one_async_function__error_raised__trace_and_span_finished_correctly__outputs_are_None__error_info_is_added( fake_backend, ): - @tracker.track(capture_output=True) + @tracker.track async def async_f(x): await asyncio.sleep(0.01) raise Exception("error message") @@ -480,7 +480,7 @@ async def async_f(x): def test_track__nested_calls_in_separate_threads__3_traces_in_result(fake_backend): ID_STORAGE: Dict[str, str] = {} - @tracker.track(capture_output=True) + @tracker.track def f_inner(y, thread_id): ID_STORAGE[f"f_inner-trace-id-{thread_id}"] = ( opik_context.get_current_trace_data().id @@ -490,7 +490,7 @@ def f_inner(y, thread_id): ) return f"inner-output-from-{thread_id}" - @tracker.track(capture_output=True) + @tracker.track def f_outer(x): ID_STORAGE["f_outer-trace-id"] = opik_context.get_current_trace_data().id ID_STORAGE["f_outer-span-id"] = opik_context.get_current_span_data().id @@ -595,9 +595,9 @@ def f_outer(x): def test_track__single_generator_function_tracked__generator_exhausted__happyflow( fake_backend, ): - @tracker.track(capture_output=True) + @tracker.track def f(x): - values = ["yielded-1", "yielded-2", "yielded-3"] + values = ["yielded-1", " yielded-2", " yielded-3"] for value in values: yield value @@ -611,7 +611,7 @@ def f(x): id=ANY_BUT_NONE, name="f", input={"x": "generator-input"}, - output={"output": "['yielded-1', 'yielded-2', 'yielded-3']"}, + output={"output": "yielded-1 yielded-2 yielded-3"}, start_time=ANY_BUT_NONE, end_time=ANY_BUT_NONE, spans=[ @@ -619,7 +619,7 @@ def f(x): id=ANY_BUT_NONE, name="f", input={"x": "generator-input"}, - output={"output": "['yielded-1', 'yielded-2', 'yielded-3']"}, + output={"output": "yielded-1 yielded-2 yielded-3"}, start_time=ANY_BUT_NONE, end_time=ANY_BUT_NONE, spans=[], @@ -683,23 +683,23 @@ def f(x): assert_equal(EXPECTED_TRACE_TREE, fake_backend.trace_trees[0]) -def test_track__generator_function_tracked__generator_exhausted_in_another_tracked_function__trace_tree_remains_correct( +def test_track__generator_function_tracked__generator_exhausted_in_another_tracked_function__generator_span_started_and_ended_with_generator_exhausting( fake_backend, ): - @tracker.track(capture_output=True) + @tracker.track def f_inner(z, generator): for _ in generator: pass return "inner-output" - @tracker.track(capture_output=True) + @tracker.track def gen_f(y): - values = ["yielded-1", "yielded-2", "yielded-3"] + values = ["yielded-1", " yielded-2", " yielded-3"] for value in values: yield value - @tracker.track(capture_output=True) + @tracker.track def f_outer(x): generator = gen_f("generator-input") f_inner("inner-input", generator) @@ -726,13 +726,79 @@ def f_outer(x): spans=[ SpanModel( id=ANY_BUT_NONE, - name="gen_f", - input={"y": "generator-input"}, - output={"output": "['yielded-1', 'yielded-2', 'yielded-3']"}, + name="f_inner", + input={"z": "inner-input", "generator": ANY_BUT_NONE}, + output={"output": "inner-output"}, start_time=ANY_BUT_NONE, end_time=ANY_BUT_NONE, - spans=[], + spans=[ + SpanModel( + id=ANY_BUT_NONE, + name="gen_f", + input={"y": "generator-input"}, + output={"output": "yielded-1 yielded-2 yielded-3"}, + start_time=ANY_BUT_NONE, + end_time=ANY_BUT_NONE, + spans=[], + ), + ], ), + ], + ), + ], + ) + + assert len(fake_backend.trace_trees) == 1 + + assert_equal(EXPECTED_TRACE_TREE, fake_backend.trace_trees[0]) + + +def test_track__generator_function_tracked__generator_exhausted_in_another_tracked_function__generator_span_started_and_ended_with_generator_exhausting__span_from_tracked_function_inside_generator_attached_to_generator_span( + fake_backend, +): + @tracker.track + def f_inner(z, generator): + for _ in generator: + pass + + return "inner-output" + + @tracker.track + def f_called_inside_generator(): + return "f-called-inside-generator-output" + + @tracker.track + def gen_f(y): + f_called_inside_generator() + values = ["yielded-1", " yielded-2", " yielded-3"] + for value in values: + yield value + + @tracker.track + def f_outer(x): + generator = gen_f("generator-input") + f_inner("inner-input", generator) + return "outer-output" + + f_outer("outer-input") + tracker.flush_tracker() + + EXPECTED_TRACE_TREE = TraceModel( + id=ANY_BUT_NONE, + name="f_outer", + input={"x": "outer-input"}, + output={"output": "outer-output"}, + start_time=ANY_BUT_NONE, + end_time=ANY_BUT_NONE, + spans=[ + SpanModel( + id=ANY_BUT_NONE, + name="f_outer", + input={"x": "outer-input"}, + output={"output": "outer-output"}, + start_time=ANY_BUT_NONE, + end_time=ANY_BUT_NONE, + spans=[ SpanModel( id=ANY_BUT_NONE, name="f_inner", @@ -740,7 +806,29 @@ def f_outer(x): output={"output": "inner-output"}, start_time=ANY_BUT_NONE, end_time=ANY_BUT_NONE, - spans=[], + spans=[ + SpanModel( + id=ANY_BUT_NONE, + name="gen_f", + input={"y": "generator-input"}, + output={"output": "yielded-1 yielded-2 yielded-3"}, + start_time=ANY_BUT_NONE, + end_time=ANY_BUT_NONE, + spans=[ + SpanModel( + id=ANY_BUT_NONE, + name="f_called_inside_generator", + input={}, + output={ + "output": "f-called-inside-generator-output" + }, + start_time=ANY_BUT_NONE, + end_time=ANY_BUT_NONE, + spans=[], + ), + ], + ), + ], ), ], ), @@ -755,7 +843,7 @@ def f_outer(x): def test_track__single_async_function_tracked__happyflow( fake_backend, ): - @tracker.track(capture_output=True) + @tracker.track async def async_f(x): await asyncio.sleep(0.01) return "the-output" @@ -792,12 +880,12 @@ async def async_f(x): def test_track__nested_async_function_tracked__happyflow( fake_backend, ): - @tracker.track(capture_output=True) + @tracker.track async def async_f_inner(y): await asyncio.sleep(0.01) return "inner-output" - @tracker.track(capture_output=True) + @tracker.track async def async_f_outer(x): await async_f_inner("inner-input") return "outer-output" @@ -841,18 +929,19 @@ async def async_f_outer(x): assert_equal(EXPECTED_TRACE_TREE, fake_backend.trace_trees[0]) -def test_track__single_async_generator_function_tracked__generator_exhausted__happyflow( +def test_track__top_level_single_async_generator_function_tracked__generator_exhausted__happyflow( fake_backend, ): - @tracker.track(capture_output=True) + @tracker.track async def async_generator(x): await asyncio.sleep(0.01) - for item in ["yielded-1", "yielded-2", "yielded-3"]: + for item in ["yielded-1", " yielded-2", " yielded-3"]: yield item async def async_generator_user(): - async for _ in async_generator("generator-input"): + gen = async_generator("generator-input") + async for _ in gen: pass asyncio.run(async_generator_user()) @@ -863,7 +952,7 @@ async def async_generator_user(): id=ANY_BUT_NONE, name="async_generator", input={"x": "generator-input"}, - output={"output": "['yielded-1', 'yielded-2', 'yielded-3']"}, + output={"output": "yielded-1 yielded-2 yielded-3"}, start_time=ANY_BUT_NONE, end_time=ANY_BUT_NONE, spans=[ @@ -871,7 +960,7 @@ async def async_generator_user(): id=ANY_BUT_NONE, name="async_generator", input={"x": "generator-input"}, - output={"output": "['yielded-1', 'yielded-2', 'yielded-3']"}, + output={"output": "yielded-1 yielded-2 yielded-3"}, start_time=ANY_BUT_NONE, end_time=ANY_BUT_NONE, spans=[], @@ -884,17 +973,74 @@ async def async_generator_user(): assert_equal(EXPECTED_TRACE_TREE, fake_backend.trace_trees[0]) +def test_track__top_level_async_generator_function_tracked__generator_has_another_tracked_function_inside__nested_function_attached_to_generator_span_and_trace( + fake_backend, +): + @tracker.track + async def some_async_work(): + await asyncio.sleep(0.001) + + @tracker.track + async def async_generator(x): + await some_async_work() + + for item in ["yielded-1", " yielded-2", " yielded-3"]: + yield item + + async def async_generator_user(): + gen = async_generator("generator-input") + async for _ in gen: + pass + + asyncio.run(async_generator_user()) + + tracker.flush_tracker() + + EXPECTED_TRACE_TREE = TraceModel( + id=ANY_BUT_NONE, + name="async_generator", + input={"x": "generator-input"}, + output={"output": "yielded-1 yielded-2 yielded-3"}, + start_time=ANY_BUT_NONE, + end_time=ANY_BUT_NONE, + spans=[ + SpanModel( + id=ANY_BUT_NONE, + name="async_generator", + input={"x": "generator-input"}, + output={"output": "yielded-1 yielded-2 yielded-3"}, + start_time=ANY_BUT_NONE, + end_time=ANY_BUT_NONE, + spans=[ + SpanModel( + id=ANY_BUT_NONE, + name="some_async_work", + input={}, + start_time=ANY_BUT_NONE, + end_time=ANY_BUT_NONE, + spans=[], + ) + ], + ) + ], + ) + + assert len(fake_backend.trace_trees) == 1 + + assert_equal(EXPECTED_TRACE_TREE, fake_backend.trace_trees[0]) + + def test_track__async_generator_inside_another_tracked_function__happyflow( fake_backend, ): - @tracker.track(capture_output=True) + @tracker.track async def async_generator(y): await asyncio.sleep(0.01) - for item in ["yielded-1", "yielded-2", "yielded-3"]: + for item in ["yielded-1", " yielded-2", " yielded-3"]: yield item - @tracker.track(capture_output=True) + @tracker.track async def async_generator_user(x): async for _ in async_generator("generator-input"): pass @@ -925,7 +1071,7 @@ async def async_generator_user(x): id=ANY_BUT_NONE, name="async_generator", input={"y": "generator-input"}, - output={"output": "['yielded-1', 'yielded-2', 'yielded-3']"}, + output={"output": "yielded-1 yielded-2 yielded-3"}, start_time=ANY_BUT_NONE, end_time=ANY_BUT_NONE, spans=[], @@ -940,10 +1086,80 @@ async def async_generator_user(x): assert_equal(EXPECTED_TRACE_TREE, fake_backend.trace_trees[0]) +def test_track__async_generator_inside_another_tracked_function__another_tracked_function_called_inside_generator_and_attached_to_its_span( + fake_backend, +): + @tracker.track + async def some_async_work(): + await asyncio.sleep(0.001) + + @tracker.track + async def async_generator(y): + await some_async_work() + + for item in ["yielded-1", " yielded-2", " yielded-3"]: + yield item + + @tracker.track + async def async_generator_user(x): + async for _ in async_generator("generator-input"): + pass + + return "generator-user-output" + + asyncio.run(async_generator_user("generator-user-input")) + + tracker.flush_tracker() + + EXPECTED_TRACE_TREE = TraceModel( + id=ANY_BUT_NONE, + name="async_generator_user", + input={"x": "generator-user-input"}, + output={"output": "generator-user-output"}, + start_time=ANY_BUT_NONE, + end_time=ANY_BUT_NONE, + spans=[ + SpanModel( + id=ANY_BUT_NONE, + name="async_generator_user", + input={"x": "generator-user-input"}, + output={"output": "generator-user-output"}, + start_time=ANY_BUT_NONE, + end_time=ANY_BUT_NONE, + spans=[ + SpanModel( + id=ANY_BUT_NONE, + name="async_generator", + input={"y": "generator-input"}, + output={"output": "yielded-1 yielded-2 yielded-3"}, + start_time=ANY_BUT_NONE, + end_time=ANY_BUT_NONE, + spans=[ + SpanModel( + id=ANY_BUT_NONE, + name="some_async_work", + input={}, + output=None, + start_time=ANY_BUT_NONE, + end_time=ANY_BUT_NONE, + spans=[], + ) + ], + ) + ], + ) + ], + ) + + assert len(fake_backend.trace_trees) == 1 + + assert_equal(EXPECTED_TRACE_TREE, fake_backend.trace_trees[0]) + + def test_track__distributed_tracing_with_headers__tracing_is_performed_in_2_threads__all_data_is_saved_in_1_trace_tree( fake_backend, ): - @tracker.track(capture_output=True) + @tracker.track def f_remote(y, thread_id): return f"f-remote-output-from-{thread_id}" @@ -951,7 +1167,7 @@ def distributed_node_runner(y, thread_id, opik_headers): f_remote(y, thread_id, opik_distributed_trace_headers=opik_headers) return "result-from-node-runner" - @tracker.track(capture_output=True) + @tracker.track def f_outer(x): distributed_trace_headers = opik_context.get_distributed_trace_headers() t1 = threading.Thread( @@ -1004,7 +1220,7 @@ def f_outer(x): def test_track__trace_already_created_not_by_decorator__decorator_just_attaches_new_span_to_it__trace_is_not_popped_from_context_in_the_end( fake_backend, ): - @tracker.track(capture_output=True) + @tracker.track def f(x): return "f-output" diff --git a/sdks/python/tests/unit/validation/test_usage_validator.py b/sdks/python/tests/unit/validation/test_usage_validator.py index 91e509c127..48dfc1b2f0 100644 --- a/sdks/python/tests/unit/validation/test_usage_validator.py +++ b/sdks/python/tests/unit/validation/test_usage_validator.py @@ -53,7 +53,7 @@ ], ) def test_usage_validator(usage_dict, is_valid): - tested = usage.UsageValidator(usage_dict) + tested = usage.UsageValidator(usage_dict, provider="some-provider") assert tested.validate().ok() is is_valid, f"Failed with {usage_dict}" diff --git a/sdks/typescript/package-lock.json b/sdks/typescript/package-lock.json index 0e4bbff002..f2876eb78c 100644 --- a/sdks/typescript/package-lock.json +++ b/sdks/typescript/package-lock.json @@ -1,12 +1,12 @@ { "name": "opik", - "version": "0.1.1", + "version": "0.2.0", "lockfileVersion": 3, "requires": true, "packages": { "": { "name": "opik", - "version": "0.1.1", + "version": "0.2.0", "license": "Apache-2.0", "dependencies": { "node-fetch": "^3.3.2", diff --git a/sdks/typescript/package.json b/sdks/typescript/package.json index a32deeed9f..97412740b6 100644 --- a/sdks/typescript/package.json +++ b/sdks/typescript/package.json @@ -1,7 +1,7 @@ { "name": "opik", "description": "Opik TypeScript and JavaScript SDK", - "version": "0.1.1", + "version": "0.2.0", "repository": { "type": "git", "url": "git+https://github.com/comet-ml/opik.git", diff --git a/tests_end_to_end/page_objects/ExperimentItemsPage.py b/tests_end_to_end/page_objects/ExperimentItemsPage.py index 6c3ae84bf7..9f63893e4f 100644 --- a/tests_end_to_end/page_objects/ExperimentItemsPage.py +++ b/tests_end_to_end/page_objects/ExperimentItemsPage.py @@ -25,7 +25,7 @@ def get_total_number_of_items_in_experiment(self): def get_id_of_nth_experiment_item(self, n: int): row = self.page.locator("tr").nth(n + 1) - cell = row.locator("td").first + cell = row.locator("td").nth(1) cell.hover() cell.get_by_role("button").nth(1).click() id = self.page.evaluate("navigator.clipboard.readText()") @@ -35,7 +35,7 @@ def get_all_item_ids_on_current_page(self): ids = [] rows = self.page.locator("tr").all() for row_index, row in enumerate(rows[2:]): - cell = row.locator("td").first + cell = row.locator("td").nth(1) cell.hover() cell.get_by_role("button").nth(1).click() id = self.page.evaluate("navigator.clipboard.readText()") diff --git a/tests_end_to_end/page_objects/ProjectsPage.py b/tests_end_to_end/page_objects/ProjectsPage.py index ee1dd44df4..0475953067 100644 --- a/tests_end_to_end/page_objects/ProjectsPage.py +++ b/tests_end_to_end/page_objects/ProjectsPage.py @@ -18,7 +18,7 @@ def search_project(self, project_name): def check_project_exists_on_current_page(self, project_name): expect( self.page.get_by_role("cell", name=project_name, exact=True) - ).to_be_visible() + ).to_be_visible(timeout=3) def check_project_not_exists_on_current_page(self, project_name): expect( @@ -39,7 +39,7 @@ def check_project_exists_on_current_page_with_retry(self, project_name, timeout) ) def create_new_project(self, project_name): - self.page.get_by_role("button", name="Create new project").click() + self.page.get_by_role("button", name="Create new project").first.click() project_name_fill_box = self.page.get_by_placeholder("Project name") project_name_fill_box.click() @@ -57,3 +57,4 @@ def delete_project_by_name(self, project_name): row.get_by_role("button").click() self.page.get_by_role("menuitem", name="Delete").click() self.page.get_by_role("button", name="Delete project").click() + self.check_project_not_exists_on_current_page(project_name) diff --git a/tests_end_to_end/page_objects/PromptPage.py b/tests_end_to_end/page_objects/PromptPage.py index af6c5e45bd..a0aadf78a0 100644 --- a/tests_end_to_end/page_objects/PromptPage.py +++ b/tests_end_to_end/page_objects/PromptPage.py @@ -31,7 +31,7 @@ def get_all_prompt_versions_with_commit_ids_on_page(self): rows: list[Locator] = self.page.get_by_role("row").all()[1:] versions = {} for row in rows: - prompt = row.get_by_role("cell").nth(1).inner_text() + prompt = row.get_by_role("cell").nth(2).inner_text() commit_id = row.get_by_role("link").first.inner_text() versions[prompt] = commit_id diff --git a/tests_end_to_end/test_requirements.txt b/tests_end_to_end/test_requirements.txt index 9c5d36765a..c4e25bf0d4 100644 --- a/tests_end_to_end/test_requirements.txt +++ b/tests_end_to_end/test_requirements.txt @@ -1,3 +1,3 @@ pytest -playwright +playwright==1.49.0 pytest-playwright diff --git a/tests_end_to_end/tests/Datasets/conftest.py b/tests_end_to_end/tests/Datasets/conftest.py index 280fe2ef3d..9425946e72 100644 --- a/tests_end_to_end/tests/Datasets/conftest.py +++ b/tests_end_to_end/tests/Datasets/conftest.py @@ -4,6 +4,6 @@ @pytest.fixture -def insert_dataset_items_sdk(client: Opik, create_delete_dataset_sdk): - dataset = client.get_dataset(create_delete_dataset_sdk) +def insert_dataset_items_sdk(client: Opik, create_dataset_sdk): + dataset = client.get_dataset(create_dataset_sdk) dataset.insert(TEST_ITEMS) diff --git a/tests_end_to_end/tests/Datasets/test_dataset_items_crud_operations.py b/tests_end_to_end/tests/Datasets/test_dataset_items_crud_operations.py index 9cd3d383f5..72e7f47493 100644 --- a/tests_end_to_end/tests/Datasets/test_dataset_items_crud_operations.py +++ b/tests_end_to_end/tests/Datasets/test_dataset_items_crud_operations.py @@ -23,7 +23,7 @@ class TestDatasetItemsCrud: ) # add insert_via_ui once flakiness is figured out @pytest.mark.parametrize( "dataset_creation_fixture", - ["create_delete_dataset_sdk", "create_delete_dataset_ui"], + ["create_dataset_sdk", "create_dataset_ui"], ) @pytest.mark.browser_context_args(permissions=["clipboard-read"]) @pytest.mark.sanity @@ -82,7 +82,7 @@ def test_dataset_item_update( request, page: Page, client: opik.Opik, - create_delete_dataset_sdk, + create_dataset_sdk, insert_dataset_items_sdk, ): """ @@ -93,7 +93,7 @@ def test_dataset_item_update( 4. Check that the new data is correct on both the UI and the SDK """ dataset = wait_for_dataset_to_be_visible( - client=client, dataset_name=create_delete_dataset_sdk, timeout=10 + client=client, dataset_name=create_dataset_sdk, timeout=10 ) wait_for_number_of_items_in_dataset( @@ -127,7 +127,7 @@ def test_dataset_item_deletion( request, page: Page, client: opik.Opik, - create_delete_dataset_sdk, + create_dataset_sdk, insert_dataset_items_sdk, item_deletion, ): @@ -139,7 +139,7 @@ def test_dataset_item_deletion( 4. Check that the item with that data no longer exists in both the SDK and the UI and that the length of the item list is updated """ dataset = wait_for_dataset_to_be_visible( - client=client, dataset_name=create_delete_dataset_sdk, timeout=10 + client=client, dataset_name=create_dataset_sdk, timeout=10 ) item_deleted = {} @@ -186,7 +186,7 @@ def test_dataset_clear( request, page: Page, client: opik.Opik, - create_delete_dataset_sdk, + create_dataset_sdk, insert_dataset_items_sdk, ): """ @@ -197,7 +197,7 @@ def test_dataset_clear( 4. Check that no items exist in the dataset when trying to get them via both the SDK and the UI """ dataset = wait_for_dataset_to_be_visible( - client=client, dataset_name=create_delete_dataset_sdk, timeout=10 + client=client, dataset_name=create_dataset_sdk, timeout=10 ) dataset.clear() diff --git a/tests_end_to_end/tests/Datasets/test_datasets_crud_operations.py b/tests_end_to_end/tests/Datasets/test_datasets_crud_operations.py index 6405b6ccd1..d17c009718 100644 --- a/tests_end_to_end/tests/Datasets/test_datasets_crud_operations.py +++ b/tests_end_to_end/tests/Datasets/test_datasets_crud_operations.py @@ -14,7 +14,7 @@ class TestDatasetsCrud: def test_create_dataset_ui_add_traces_to_new_dataset( - self, page: Page, create_delete_project_sdk, create_10_test_traces + self, page: Page, create_project, create_10_test_traces ): """ Basic test to check dataset creation via "add to new dataset" functionality in the traces page. Uses the UI after creation to check the project exists @@ -24,7 +24,7 @@ def test_create_dataset_ui_add_traces_to_new_dataset( 4. If no errors raised and dataset exists, test passes """ dataset_name = "automated_tests_dataset" - proj_name = create_delete_project_sdk + proj_name = create_project projects_page = ProjectsPage(page) projects_page.go_to_page() projects_page.click_project(project_name=proj_name) @@ -45,7 +45,7 @@ def test_create_dataset_ui_add_traces_to_new_dataset( delete_dataset_by_name_if_exists(dataset_name=dataset_name) @pytest.mark.parametrize( - "dataset_fixture", ["create_delete_dataset_ui", "create_delete_dataset_sdk"] + "dataset_fixture", ["create_dataset_ui", "create_dataset_sdk"] ) @pytest.mark.sanity def test_dataset_visibility( @@ -69,7 +69,7 @@ def test_dataset_visibility( @pytest.mark.parametrize( "dataset_fixture", - ["create_dataset_sdk_no_cleanup", "create_dataset_ui_no_cleanup"], + ["create_dataset_sdk", "create_dataset_ui"], ) def test_dataset_name_update( self, request, page: Page, client: opik.Opik, dataset_fixture @@ -114,7 +114,7 @@ def test_dataset_name_update( @pytest.mark.parametrize( "dataset_fixture", - ["create_dataset_sdk_no_cleanup", "create_dataset_ui_no_cleanup"], + ["create_dataset_sdk", "create_dataset_ui"], ) def test_dataset_deletion_in_sdk( self, request, page: Page, client: opik.Opik, dataset_fixture @@ -142,7 +142,7 @@ def test_dataset_deletion_in_sdk( @pytest.mark.parametrize( "dataset_fixture", - ["create_dataset_sdk_no_cleanup", "create_dataset_ui_no_cleanup"], + ["create_dataset_sdk", "create_dataset_ui"], ) def test_dataset_deletion_in_ui( self, request, page: Page, client: opik.Opik, dataset_fixture diff --git a/tests_end_to_end/tests/Experiments/conftest.py b/tests_end_to_end/tests/Experiments/conftest.py index 5356699b42..c7804ceab1 100644 --- a/tests_end_to_end/tests/Experiments/conftest.py +++ b/tests_end_to_end/tests/Experiments/conftest.py @@ -10,8 +10,8 @@ def eval_task(item: dict): @pytest.fixture() -def mock_experiment(client: Opik, create_delete_dataset_sdk, insert_dataset_items_sdk): - dataset = client.get_dataset(create_delete_dataset_sdk) +def mock_experiment(client: Opik, create_dataset_sdk, insert_dataset_items_sdk): + dataset = client.get_dataset(create_dataset_sdk) experiment_name = "test_experiment" eval = evaluate( experiment_name=experiment_name, diff --git a/tests_end_to_end/tests/Projects/test_projects_crud_operations.py b/tests_end_to_end/tests/Projects/test_projects_crud_operations.py index b109f318e4..9f4ad7ac15 100644 --- a/tests_end_to_end/tests/Projects/test_projects_crud_operations.py +++ b/tests_end_to_end/tests/Projects/test_projects_crud_operations.py @@ -10,9 +10,7 @@ class TestProjectsCrud: - @pytest.mark.parametrize( - "project_fixture", ["create_delete_project_ui", "create_delete_project_sdk"] - ) + @pytest.mark.parametrize("project_fixture", ["create_project", "create_project_ui"]) @pytest.mark.sanity def test_project_visibility(self, request, page: Page, project_fixture): """ @@ -37,7 +35,7 @@ def test_project_visibility(self, request, page: Page, project_fixture): @pytest.mark.parametrize( "project_fixture", - ["create_project_sdk_no_cleanup", "create_project_ui_no_cleanup"], + ["create_project", "create_project_ui"], ) def test_project_name_update(self, request, page: Page, project_fixture): """ @@ -74,7 +72,7 @@ def test_project_name_update(self, request, page: Page, project_fixture): ) except Exception as e: - print(f"Error occured during update of project name: {e}") + print(f"Error occurred during update of project name: {e}") raise finally: @@ -85,7 +83,7 @@ def test_project_name_update(self, request, page: Page, project_fixture): @pytest.mark.parametrize( "project_fixture", - ["create_project_sdk_no_cleanup", "create_project_ui_no_cleanup"], + ["create_project", "create_project_ui"], ) def test_project_deletion_in_sdk(self, request, page: Page, project_fixture): """ @@ -108,7 +106,7 @@ def test_project_deletion_in_sdk(self, request, page: Page, project_fixture): @pytest.mark.parametrize( "project_fixture", - ["create_project_sdk_no_cleanup", "create_project_ui_no_cleanup"], + ["create_project", "create_project_ui"], ) def test_project_deletion_in_ui(self, request, page: Page, project_fixture): """ diff --git a/tests_end_to_end/tests/Traces/test_trace_spans.py b/tests_end_to_end/tests/Traces/test_trace_spans.py index aacf58225a..4e78d885ce 100644 --- a/tests_end_to_end/tests/Traces/test_trace_spans.py +++ b/tests_end_to_end/tests/Traces/test_trace_spans.py @@ -11,16 +11,14 @@ class TestTraceSpans: ["log_traces_with_spans_low_level", "log_traces_with_spans_decorator"], ) @pytest.mark.sanity - def test_spans_of_traces( - self, page, request, create_delete_project_sdk, traces_fixture - ): + def test_spans_of_traces(self, page, request, create_project, traces_fixture): """ Checks that every trace has the correct number and names of spans defined in the sanity_config.yaml file 1. Open the traces page of the project 2. Go through each trace and click it 3. Check that the spans are present in each trace """ - project_name = create_delete_project_sdk + project_name = create_project _, span_config = request.getfixturevalue(traces_fixture) projects_page = ProjectsPage(page) projects_page.go_to_page() @@ -42,7 +40,7 @@ def test_spans_of_traces( ) @pytest.mark.sanity def test_trace_and_span_details( - self, page, request, create_delete_project_sdk, traces_fixture + self, page, request, create_project, traces_fixture ): """ Checks that for each trace and spans, the attributes defined in sanity_config.yaml are present @@ -52,7 +50,7 @@ def test_trace_and_span_details( 4. Check the defined metadata is present 5. Go through each span of the traces and repeat 2-4 """ - project_name = create_delete_project_sdk + project_name = create_project trace_config, span_config = request.getfixturevalue(traces_fixture) projects_page = ProjectsPage(page) projects_page.go_to_page() diff --git a/tests_end_to_end/tests/Traces/test_traces_crud_operations.py b/tests_end_to_end/tests/Traces/test_traces_crud_operations.py index 03f51a2542..e14739e879 100644 --- a/tests_end_to_end/tests/Traces/test_traces_crud_operations.py +++ b/tests_end_to_end/tests/Traces/test_traces_crud_operations.py @@ -23,7 +23,7 @@ class TestTracesCrud: ) @pytest.mark.sanity def test_trace_creation( - self, page: Page, traces_number, create_delete_project_sdk, create_traces + self, page: Page, traces_number, create_project, create_traces ): """Testing basic creation of traces via both decorator and low-level client. Test case is split into 4, creating 1 and then 15 traces using both the decorator and the client respectively @@ -32,7 +32,7 @@ def test_trace_creation( 2. Create the traces using one of the creation methods, following the naming convention of "test-trace-X", where X is from 1 to 25 (so all have unique names) - no errors should occur 3. In the UI, check that the presented number of traces in the project matches the number of traces created in the test case """ - project_name = create_delete_project_sdk + project_name = create_project projects_page = ProjectsPage(page) projects_page.go_to_page() projects_page.click_project(project_name) @@ -52,7 +52,7 @@ def test_trace_creation( indirect=True, ) def test_traces_visibility( - self, page: Page, traces_number, create_delete_project_sdk, create_traces + self, page: Page, traces_number, create_project, create_traces ): """ Testing visibility within the UI and SDK of traces created via both the decorator and the client @@ -67,7 +67,7 @@ def test_traces_visibility( - Fetch all traces of the project via the API client (OpikApi.traces.get_traces_by_project) - Check that the list of names present in the result is exactly equal to the list of names of the traces created (exactly the same elements on both sides) """ - project_name = create_delete_project_sdk + project_name = create_project projects_page = ProjectsPage(page) projects_page.go_to_page() projects_page.click_project(project_name) @@ -94,7 +94,7 @@ def test_traces_visibility( indirect=True, ) def test_delete_traces_sdk( - self, page: Page, traces_number, create_delete_project_sdk, create_traces + self, page: Page, traces_number, create_project, create_traces ): """ Testing trace deletion via the SDK API client (v1/private/traces/delete endpoint) @@ -106,7 +106,7 @@ def test_delete_traces_sdk( 4. Check in the UI that the deleted traces are no longer present in the project page 5. Check in the SDK that the deleted traces are no longer present in the fetch request (v1/private/traces endpoint, with project_name parameter) """ - project_name = create_delete_project_sdk + project_name = create_project _ = create_traces wait_for_traces_to_be_visible(project_name=project_name, size=traces_number) @@ -148,7 +148,7 @@ def test_delete_traces_sdk( indirect=True, ) def test_delete_traces_ui( - self, page: Page, traces_number, create_delete_project_sdk, create_traces + self, page: Page, traces_number, create_project, create_traces ): """ Testing trace deletion via the UI @@ -160,7 +160,7 @@ def test_delete_traces_ui( 4. Check in the UI that the deleted traces are no longer present in the project page 5. Check in the SDK that the deleted traces are no longer present in the fetch request (v1/private/traces endpoint, with project_name parameter) """ - project_name = create_delete_project_sdk + project_name = create_project projects_page = ProjectsPage(page) projects_page.go_to_page() projects_page.click_project(project_name) diff --git a/tests_end_to_end/tests/conftest.py b/tests_end_to_end/tests/conftest.py index 8eb539ad42..1e7f753351 100644 --- a/tests_end_to_end/tests/conftest.py +++ b/tests_end_to_end/tests/conftest.py @@ -3,7 +3,7 @@ import opik from opik import track, opik_context from tests.config import EnvConfig, get_environment_config -from playwright.sync_api import Page, Browser +from playwright.sync_api import Page, Browser, Playwright from page_objects.ProjectsPage import ProjectsPage from page_objects.TracesPage import TracesPage from page_objects.DatasetsPage import DatasetsPage @@ -11,13 +11,14 @@ from page_objects.PromptLibraryPage import PromptLibraryPage from page_objects.FeedbackDefinitionsPage import FeedbackDefinitionsPage from tests.sdk_helpers import ( - create_project_sdk, + create_project_api, delete_project_by_name_sdk, wait_for_number_of_traces_to_be_visible, client_get_prompt_retries, + find_project_by_name_sdk, + wait_for_project_to_not_be_visible, ) from utils import TEST_ITEMS -import time import re import json @@ -26,6 +27,17 @@ def pytest_configure(config): config.addinivalue_line("markers", "sanity: mark test as a sanity test") +@pytest.fixture(scope="session") +def browser(playwright: Playwright, request) -> Browser: + browser_name = request.config.getoption("--browser", default="chromium") + if isinstance(browser_name, list): + browser_name = browser_name[0] + browser_type = getattr(playwright, browser_name) + browser = browser_type.launch(slow_mo=200) + yield browser + browser.close() + + @pytest.fixture(scope="session") def browser_context(browser: Browser, env_config: EnvConfig): """Create a browser context with required permissions and authentication""" @@ -147,22 +159,50 @@ def experiments_page(page): @pytest.fixture(scope="function") -def create_project_sdk_no_cleanup(): - proj_name = "projects_crud_tests_sdk" - - create_project_sdk(name=proj_name) +def create_project(page: Page): + """ + Create a project via SDK and handle cleanup. + Checks if project exists before attempting deletion. + """ + proj_name = os.environ["OPIK_PROJECT_NAME"] + if find_project_by_name_sdk(proj_name): + delete_project_by_name_sdk(proj_name) + create_project_api(name=proj_name) yield proj_name + projects_page = ProjectsPage(page) + projects_page.go_to_page() + try: + projects_page.search_project(proj_name) + projects_page.check_project_not_exists_on_current_page(project_name=proj_name) + except AssertionError as _: + projects_page.delete_project_by_name(proj_name) + wait_for_project_to_not_be_visible(proj_name) + @pytest.fixture(scope="function") -def create_project_ui_no_cleanup(page: Page): - proj_name = "projects_crud_tests_ui" +def create_project_ui(page: Page): + """ + Create a project via UI and handle cleanup. + Checks if project exists before attempting deletion. + """ + proj_name = os.environ["OPIK_PROJECT_NAME"] + if find_project_by_name_sdk(proj_name): + delete_project_by_name_sdk(proj_name) projects_page = ProjectsPage(page) projects_page.go_to_page() projects_page.create_new_project(project_name=proj_name) yield proj_name + projects_page.go_to_page() + try: + projects_page.search_project(proj_name) + projects_page.check_project_not_exists_on_current_page(project_name=proj_name) + except AssertionError as _: + projects_page.delete_project_by_name(proj_name) + wait_for_project_to_not_be_visible(proj_name) + @pytest.fixture(scope="function") def log_traces_with_spans_low_level(client: opik.Opik): @@ -284,43 +324,30 @@ def make_trace(x): @pytest.fixture(scope="function") -def create_delete_project_sdk(): - proj_name = "automated_tests_project" - os.environ["OPIK_PROJECT_NAME"] = proj_name - time.sleep(1) - create_project_sdk(name=proj_name) - yield proj_name - delete_project_by_name_sdk(name=proj_name) - - -@pytest.fixture -def create_delete_project_ui(page: Page): - proj_name = "automated_tests_project" - projects_page = ProjectsPage(page) - projects_page.go_to_page() - projects_page.create_new_project(project_name=proj_name) - - yield proj_name - delete_project_by_name_sdk(name=proj_name) - - -@pytest.fixture(scope="function") -def create_delete_dataset_sdk(client: opik.Opik): +def create_dataset_sdk(client: opik.Opik): dataset_name = "automated_tests_dataset" client.create_dataset(name=dataset_name) yield dataset_name - client.delete_dataset(name=dataset_name) + try: + client.get_dataset(name=dataset_name) + client.delete_dataset(name=dataset_name) + except Exception as _: + pass @pytest.fixture(scope="function") -def create_delete_dataset_ui(page: Page, client: opik.Opik): +def create_dataset_ui(page: Page, client: opik.Opik): dataset_name = "automated_tests_dataset" datasets_page = DatasetsPage(page) datasets_page.go_to_page() datasets_page.create_dataset_by_name(dataset_name=dataset_name) yield dataset_name - client.delete_dataset(name=dataset_name) + try: + client.get_dataset(name=dataset_name) + client.delete_dataset(name=dataset_name) + except Exception as _: + pass @pytest.fixture(scope="function") @@ -340,8 +367,8 @@ def create_dataset_ui_no_cleanup(page: Page): @pytest.fixture -def insert_dataset_items_sdk(client: opik.Opik, create_delete_dataset_sdk): - dataset = client.get_dataset(create_delete_dataset_sdk) +def insert_dataset_items_sdk(client: opik.Opik, create_dataset_sdk): + dataset = client.get_dataset(create_dataset_sdk) dataset.insert(TEST_ITEMS) @@ -381,8 +408,8 @@ def create_prompt_ui(client: opik.Opik, page: Page): @pytest.fixture -def create_10_test_traces(page: Page, client, create_delete_project_sdk): - proj_name = create_delete_project_sdk +def create_10_test_traces(page: Page, client, create_project): + proj_name = create_project for i in range(10): _ = client.trace( name=f"trace{i}", diff --git a/tests_end_to_end/tests/sdk_helpers.py b/tests_end_to_end/tests/sdk_helpers.py index e7569726ee..6396b0f568 100644 --- a/tests_end_to_end/tests/sdk_helpers.py +++ b/tests_end_to_end/tests/sdk_helpers.py @@ -4,21 +4,30 @@ from typing import Optional import json import opik +import os -def create_project_sdk(name: str): - client = OpikApi() +def get_opik_api_client(): + return OpikApi( + base_url=os.getenv("OPIK_URL_OVERRIDE", None), + workspace_name=os.getenv("OPIK_WORKSPACE", None), + api_key=os.getenv("OPIK_API_KEY", None), + ) + + +def create_project_api(name: str): + client = get_opik_api_client() client.projects.create_project(name=name) def find_project_by_name_sdk(name: str): - client = OpikApi() + client = get_opik_api_client() proj_page = client.projects.find_projects(name=name, page=1, size=1) return proj_page.dict()["content"] def delete_project_by_name_sdk(name: str): - client = OpikApi() + client = get_opik_api_client() project = find_project_by_name_sdk(name=name) client.projects.delete_project_by_id(project[0]["id"]) @@ -29,7 +38,7 @@ def wait_for_project_to_be_visible(project_name, timeout=10, initial_delay=1): while time.time() - start_time < timeout: if find_project_by_name_sdk(project_name): - return True + return time.sleep(delay) delay = min(delay * 2, timeout - (time.time() - start_time)) @@ -39,8 +48,24 @@ def wait_for_project_to_be_visible(project_name, timeout=10, initial_delay=1): ) +def wait_for_project_to_not_be_visible(project_name, timeout=10, initial_delay=1): + start_time = time.time() + delay = initial_delay + + while time.time() - start_time < timeout: + if not find_project_by_name_sdk(project_name): + return + + time.sleep(delay) + delay = min(delay * 2, timeout - (time.time() - start_time)) + + raise TimeoutError( + f"{project_name} has not been deleted via API within {timeout} seconds" + ) + + def update_project_by_name_sdk(name: str, new_name: str): - client = OpikApi() + client = get_opik_api_client() wait_for_project_to_be_visible(name, timeout=10) projects_match = find_project_by_name_sdk(name) project_id = projects_match[0]["id"] @@ -51,7 +76,7 @@ def update_project_by_name_sdk(name: str, new_name: str): def create_traces_sdk(prefix: str, project_name: str, qty: int): - client = OpikApi() + client = get_opik_api_client() for i in range(qty): client.traces.create_trace( name=prefix + str(i), @@ -66,7 +91,7 @@ def wait_for_traces_to_be_visible(project_name, size, timeout=10, initial_delay= while time.time() - start_time < timeout: if get_traces_of_project_sdk(project_name=project_name, size=size): - return True + return time.sleep(delay) delay = min(delay * 2, timeout - (time.time() - start_time)) @@ -87,7 +112,7 @@ def wait_for_number_of_traces_to_be_visible( project_name=project_name, size=number_of_traces ) if len(traces) >= number_of_traces: - return True + return time.sleep(delay) delay = min(delay * 2, timeout - (time.time() - start_time)) @@ -98,31 +123,31 @@ def wait_for_number_of_traces_to_be_visible( def get_traces_of_project_sdk(project_name: str, size: int): - client = OpikApi() + client = get_opik_api_client() traces = client.traces.get_traces_by_project(project_name=project_name, size=size) return traces.dict()["content"] def delete_list_of_traces_sdk(ids: list[str]): - client = OpikApi() + client = get_opik_api_client() client.traces.delete_traces(ids=ids) def update_trace_by_id(id: str): - client = OpikApi() + client = get_opik_api_client() client.traces.update_trace( id=id, ) def get_dataset_by_name(dataset_name: str): - client = OpikApi() + client = get_opik_api_client() dataset = client.datasets.get_dataset_by_identifier(dataset_name=dataset_name) return dataset.dict() def update_dataset_name(name: str, new_name: str): - client = OpikApi() + client = get_opik_api_client() dataset = get_dataset_by_name(dataset_name=name) dataset_id = dataset["id"] @@ -132,7 +157,7 @@ def update_dataset_name(name: str, new_name: str): def delete_dataset_by_name_if_exists(dataset_name: str): - client = OpikApi() + client = get_opik_api_client() dataset = None try: dataset = get_dataset_by_name(dataset_name) @@ -144,23 +169,23 @@ def delete_dataset_by_name_if_exists(dataset_name: str): def get_experiment_by_id(exp_id: str): - client = OpikApi() + client = get_opik_api_client() exp = client.experiments.get_experiment_by_id(exp_id) return exp def delete_experiment_by_id(exp_id: str): - client = OpikApi() + client = get_opik_api_client() client.experiments.delete_experiments_by_id(ids=[exp_id]) def delete_experiment_items_by_id(ids: list[str]): - client = OpikApi() + client = get_opik_api_client() client.experiments.delete_experiment_items(ids=ids) def experiment_items_stream(exp_name: str, limit: Optional[int] = None): - client = OpikApi() + client = get_opik_api_client() data = b"".join( client.experiments.stream_experiment_items( experiment_name=exp_name, request_options={"chunk_size": 100} diff --git a/version.txt b/version.txt index acd81d7f2c..04e0d3f14f 100644 --- a/version.txt +++ b/version.txt @@ -1 +1 @@ -1.4.13 +1.4.17