diff --git a/.github/pull_request_template.md b/.github/pull_request_template.md index e57283f0377..8287f9b5300 100644 --- a/.github/pull_request_template.md +++ b/.github/pull_request_template.md @@ -6,20 +6,24 @@ [Describe the tests you ran to verify your changes] -## Accepted Risk -[Any know risks or failure modes to point out to reviewers] +## Accepted Risk (provide if relevant) +N/A -## Related Issue(s) -[If applicable, link to the issue(s) this PR addresses] +## Related Issue(s) (provide if relevant) +N/A -## Checklist: -- [ ] All of the automated tests pass -- [ ] All PR comments are addressed and marked resolved -- [ ] If there are migrations, they have been rebased to latest main -- [ ] If there are new dependencies, they are added to the requirements -- [ ] If there are new environment variables, they are added to all of the deployment methods -- [ ] If there are new APIs that don't require auth, they are added to PUBLIC_ENDPOINT_SPECS -- [ ] Docker images build and basic functionalities work -- [ ] Author has done a final read through of the PR right before merge +## Mental Checklist: +- All of the automated tests pass +- All PR comments are addressed and marked resolved +- If there are migrations, they have been rebased to latest main +- If there are new dependencies, they are added to the requirements +- If there are new environment variables, they are added to all of the deployment methods +- If there are new APIs that don't require auth, they are added to PUBLIC_ENDPOINT_SPECS +- Docker images build and basic functionalities work +- Author has done a final read through of the PR right before merge + +## Backporting (check the box to trigger backport action) +Note: You have to check that the action passes, otherwise resolve the conflicts manually and tag the patches. +- [ ] This PR should be backported (make sure to check that the backport attempt succeeds) diff --git a/.github/workflows/nightly-close-stale-issues.yml b/.github/workflows/nightly-close-stale-issues.yml index 393d3ec950f..a7d296e0a92 100644 --- a/.github/workflows/nightly-close-stale-issues.yml +++ b/.github/workflows/nightly-close-stale-issues.yml @@ -1,8 +1,13 @@ -name: 'Close stale issues and PRs' +name: 'Nightly - Close stale issues and PRs' on: schedule: - cron: '0 11 * * *' # Runs every day at 3 AM PST / 4 AM PDT / 11 AM UTC +permissions: + # contents: write # only for delete-branch option + issues: write + pull-requests: write + jobs: stale: runs-on: ubuntu-latest diff --git a/.github/workflows/pr-backport-autotrigger.yml b/.github/workflows/pr-backport-autotrigger.yml new file mode 100644 index 00000000000..2d49c39402e --- /dev/null +++ b/.github/workflows/pr-backport-autotrigger.yml @@ -0,0 +1,92 @@ +name: Backport on Merge + +on: + pull_request: + types: [closed] + +jobs: + backport: + if: github.event.pull_request.merged == true + runs-on: ubuntu-latest + steps: + - name: Checkout code + uses: actions/checkout@v3 + with: + fetch-depth: 0 # Fetch all history for all branches and tags + + - name: Set up Git + run: | + git config user.name "github-actions[bot]" + git config user.email "github-actions[bot]@users.noreply.github.com" + + - name: Check for Backport Checkbox + id: checkbox-check + run: | + PR_BODY="${{ github.event.pull_request.body }}" + if [[ "$PR_BODY" == *"[x] This PR should be backported"* ]]; then + echo "backport=true" >> $GITHUB_OUTPUT + else + echo "backport=false" >> $GITHUB_OUTPUT + fi + + - name: List and sort release branches + id: list-branches + run: | + git fetch --all --tags + BRANCHES=$(git for-each-ref --format='%(refname:short)' refs/remotes/origin/release/* | sed 's|origin/release/||' | sort -Vr) + BETA=$(echo "$BRANCHES" | head -n 1) + STABLE=$(echo "$BRANCHES" | head -n 2 | tail -n 1) + echo "beta=$BETA" >> $GITHUB_OUTPUT + echo "stable=$STABLE" >> $GITHUB_OUTPUT + # Fetch latest tags for beta and stable + LATEST_BETA_TAG=$(git tag -l "v*.*.0-beta.*" | sort -Vr | head -n 1) + LATEST_STABLE_TAG=$(git tag -l "v*.*.*" | grep -v -- "-beta" | sort -Vr | head -n 1) + # Increment latest beta tag + NEW_BETA_TAG=$(echo $LATEST_BETA_TAG | awk -F '[.-]' '{print $1 "." $2 ".0-beta." ($NF+1)}') + # Increment latest stable tag + NEW_STABLE_TAG=$(echo $LATEST_STABLE_TAG | awk -F '.' '{print $1 "." $2 "." ($3+1)}') + echo "latest_beta_tag=$LATEST_BETA_TAG" >> $GITHUB_OUTPUT + echo "latest_stable_tag=$LATEST_STABLE_TAG" >> $GITHUB_OUTPUT + echo "new_beta_tag=$NEW_BETA_TAG" >> $GITHUB_OUTPUT + echo "new_stable_tag=$NEW_STABLE_TAG" >> $GITHUB_OUTPUT + + - name: Echo branch and tag information + run: | + echo "Beta branch: ${{ steps.list-branches.outputs.beta }}" + echo "Stable branch: ${{ steps.list-branches.outputs.stable }}" + echo "Latest beta tag: ${{ steps.list-branches.outputs.latest_beta_tag }}" + echo "Latest stable tag: ${{ steps.list-branches.outputs.latest_stable_tag }}" + echo "New beta tag: ${{ steps.list-branches.outputs.new_beta_tag }}" + echo "New stable tag: ${{ steps.list-branches.outputs.new_stable_tag }}" + + - name: Trigger Backport + if: steps.checkbox-check.outputs.backport == 'true' + run: | + set -e + echo "Backporting to beta ${{ steps.list-branches.outputs.beta }} and stable ${{ steps.list-branches.outputs.stable }}" + # Fetch all history for all branches and tags + git fetch --prune --unshallow + # Checkout the beta branch + git checkout ${{ steps.list-branches.outputs.beta }} + # Cherry-pick the merge commit from the merged PR + git cherry-pick -m 1 ${{ github.event.pull_request.merge_commit_sha }} || { + echo "Cherry-pick to beta failed due to conflicts." + exit 1 + } + # Create new beta tag + git tag ${{ steps.list-branches.outputs.new_beta_tag }} + # Push the changes and tag to the beta branch + git push origin ${{ steps.list-branches.outputs.beta }} + git push origin ${{ steps.list-branches.outputs.new_beta_tag }} + # Checkout the stable branch + git checkout ${{ steps.list-branches.outputs.stable }} + # Cherry-pick the merge commit from the merged PR + git cherry-pick -m 1 ${{ github.event.pull_request.merge_commit_sha }} || { + echo "Cherry-pick to stable failed due to conflicts." + exit 1 + } + # Create new stable tag + git tag ${{ steps.list-branches.outputs.new_stable_tag }} + # Push the changes and tag to the stable branch + git push origin ${{ steps.list-branches.outputs.stable }} + git push origin ${{ steps.list-branches.outputs.new_stable_tag }} diff --git a/README.md b/README.md index 087b0df531f..1ff4338c530 100644 --- a/README.md +++ b/README.md @@ -68,7 +68,7 @@ We also have built-in support for deployment on Kubernetes. Files for that can b ## 🚧 Roadmap * Chat/Prompt sharing with specific teammates and user groups. -* Multi-Model model support, chat with images, video etc. +* Multimodal model support, chat with images, video etc. * Choosing between LLMs and parameters during chat session. * Tool calling and agent configurations options. * Organizational understanding and ability to locate and suggest experts from your team. diff --git a/backend/alembic/env.py b/backend/alembic/env.py index b4b0ecb4665..7ccd04cf16a 100644 --- a/backend/alembic/env.py +++ b/backend/alembic/env.py @@ -14,6 +14,7 @@ from danswer.db.models import Base from celery.backends.database.session import ResultModelBase # type: ignore from danswer.db.engine import get_all_tenant_ids +from shared_configs.configs import POSTGRES_DEFAULT_SCHEMA # Alembic Config object config = context.config @@ -57,11 +58,15 @@ def get_schema_options() -> tuple[str, bool, bool]: if "=" in pair: key, value = pair.split("=", 1) x_args[key.strip()] = value.strip() - schema_name = x_args.get("schema", "public") + schema_name = x_args.get("schema", POSTGRES_DEFAULT_SCHEMA) create_schema = x_args.get("create_schema", "true").lower() == "true" upgrade_all_tenants = x_args.get("upgrade_all_tenants", "false").lower() == "true" - if MULTI_TENANT and schema_name == "public" and not upgrade_all_tenants: + if ( + MULTI_TENANT + and schema_name == POSTGRES_DEFAULT_SCHEMA + and not upgrade_all_tenants + ): raise ValueError( "Cannot run default migrations in public schema when multi-tenancy is enabled. " "Please specify a tenant-specific schema." diff --git a/backend/danswer/__init__.py b/backend/danswer/__init__.py index e2d480be4e6..ea33fd83292 100644 --- a/backend/danswer/__init__.py +++ b/backend/danswer/__init__.py @@ -1,3 +1,3 @@ import os -__version__ = os.environ.get("DANSWER_VERSION", "") or "0.3-dev" +__version__ = os.environ.get("DANSWER_VERSION", "") or "Development" diff --git a/backend/danswer/access/models.py b/backend/danswer/access/models.py index af5a021ca97..46b9c0efa93 100644 --- a/backend/danswer/access/models.py +++ b/backend/danswer/access/models.py @@ -70,3 +70,12 @@ def build( user_groups=set(user_groups), is_public=is_public, ) + + +default_public_access = DocumentAccess( + external_user_emails=set(), + external_user_group_ids=set(), + user_emails=set(), + user_groups=set(), + is_public=True, +) diff --git a/backend/danswer/auth/users.py b/backend/danswer/auth/users.py index 5abf2ac8116..f4f069a5bac 100644 --- a/backend/danswer/auth/users.py +++ b/backend/danswer/auth/users.py @@ -93,7 +93,8 @@ from danswer.utils.telemetry import optional_telemetry from danswer.utils.telemetry import RecordType from danswer.utils.variable_functionality import fetch_versioned_implementation -from shared_configs.configs import current_tenant_id +from shared_configs.configs import CURRENT_TENANT_ID_CONTEXTVAR +from shared_configs.configs import POSTGRES_DEFAULT_SCHEMA logger = setup_logger() @@ -187,7 +188,7 @@ def verify_email_domain(email: str) -> None: def get_tenant_id_for_email(email: str) -> str: if not MULTI_TENANT: - return "public" + return POSTGRES_DEFAULT_SCHEMA # Implement logic to get tenant_id from the mapping table with Session(get_sqlalchemy_engine()) as db_session: result = db_session.execute( @@ -233,35 +234,62 @@ async def create( safe: bool = False, request: Optional[Request] = None, ) -> User: - verify_email_is_invited(user_create.email) - verify_email_domain(user_create.email) - if hasattr(user_create, "role"): - user_count = await get_user_count() - if user_count == 0 or user_create.email in get_default_admin_user_emails(): - user_create.role = UserRole.ADMIN - else: - user_create.role = UserRole.BASIC - user = None try: - user = await super().create(user_create, safe=safe, request=request) # type: ignore - except exceptions.UserAlreadyExists: - user = await self.get_by_email(user_create.email) - # Handle case where user has used product outside of web and is now creating an account through web - if ( - not user.has_web_login - and hasattr(user_create, "has_web_login") - and user_create.has_web_login - ): - user_update = UserUpdate( - password=user_create.password, - has_web_login=True, - role=user_create.role, - is_verified=user_create.is_verified, - ) - user = await self.update(user_update, user) - else: - raise exceptions.UserAlreadyExists() - return user + tenant_id = ( + get_tenant_id_for_email(user_create.email) + if MULTI_TENANT + else POSTGRES_DEFAULT_SCHEMA + ) + except exceptions.UserNotExists: + raise HTTPException(status_code=401, detail="User not found") + + if not tenant_id: + raise HTTPException( + status_code=401, detail="User does not belong to an organization" + ) + + async with get_async_session_with_tenant(tenant_id) as db_session: + token = CURRENT_TENANT_ID_CONTEXTVAR.set(tenant_id) + + verify_email_is_invited(user_create.email) + verify_email_domain(user_create.email) + if MULTI_TENANT: + tenant_user_db = SQLAlchemyUserAdminDB(db_session, User, OAuthAccount) + self.user_db = tenant_user_db + self.database = tenant_user_db + + if hasattr(user_create, "role"): + user_count = await get_user_count() + if ( + user_count == 0 + or user_create.email in get_default_admin_user_emails() + ): + user_create.role = UserRole.ADMIN + else: + user_create.role = UserRole.BASIC + user = None + try: + user = await super().create(user_create, safe=safe, request=request) # type: ignore + except exceptions.UserAlreadyExists: + user = await self.get_by_email(user_create.email) + # Handle case where user has used product outside of web and is now creating an account through web + if ( + not user.has_web_login + and hasattr(user_create, "has_web_login") + and user_create.has_web_login + ): + user_update = UserUpdate( + password=user_create.password, + has_web_login=True, + role=user_create.role, + is_verified=user_create.is_verified, + ) + user = await self.update(user_update, user) + else: + raise exceptions.UserAlreadyExists() + + CURRENT_TENANT_ID_CONTEXTVAR.reset(token) + return user async def on_after_login( self, @@ -302,7 +330,9 @@ async def oauth_callback( # Get tenant_id from mapping table try: tenant_id = ( - get_tenant_id_for_email(account_email) if MULTI_TENANT else "public" + get_tenant_id_for_email(account_email) + if MULTI_TENANT + else POSTGRES_DEFAULT_SCHEMA ) except exceptions.UserNotExists: raise HTTPException(status_code=401, detail="User not found") @@ -312,7 +342,7 @@ async def oauth_callback( token = None async with get_async_session_with_tenant(tenant_id) as db_session: - token = current_tenant_id.set(tenant_id) + token = CURRENT_TENANT_ID_CONTEXTVAR.set(tenant_id) verify_email_in_whitelist(account_email, tenant_id) verify_email_domain(account_email) @@ -320,7 +350,7 @@ async def oauth_callback( if MULTI_TENANT: tenant_user_db = SQLAlchemyUserAdminDB(db_session, User, OAuthAccount) self.user_db = tenant_user_db - self.database = tenant_user_db + self.database = tenant_user_db # type: ignore oauth_account_dict = { "oauth_name": oauth_name, @@ -402,7 +432,7 @@ async def oauth_callback( user.oidc_expiry = None # type: ignore if token: - current_tenant_id.reset(token) + CURRENT_TENANT_ID_CONTEXTVAR.reset(token) return user diff --git a/backend/danswer/background/celery/apps/app_base.py b/backend/danswer/background/celery/apps/app_base.py index 2a52abde5d1..b74cba1dfe6 100644 --- a/backend/danswer/background/celery/apps/app_base.py +++ b/backend/danswer/background/celery/apps/app_base.py @@ -5,9 +5,11 @@ import sentry_sdk from celery import Task +from celery.app import trace from celery.exceptions import WorkerShutdown from celery.states import READY_STATES from celery.utils.log import get_task_logger +from celery.worker import strategy # type: ignore from sentry_sdk.integrations.celery import CeleryIntegration from danswer.background.celery.apps.task_formatters import CeleryTaskColoredFormatter @@ -19,6 +21,7 @@ from danswer.background.celery.celery_redis import RedisUserGroup from danswer.background.celery.celery_utils import celery_is_worker_primary from danswer.configs.constants import DanswerRedisLocks +from danswer.db.engine import get_all_tenant_ids from danswer.redis.redis_pool import get_redis_client from danswer.utils.logger import ColoredFormatter from danswer.utils.logger import PlainFormatter @@ -56,7 +59,7 @@ def on_task_postrun( task_id: str | None = None, task: Task | None = None, args: tuple | None = None, - kwargs: dict | None = None, + kwargs: dict[str, Any] | None = None, retval: Any | None = None, state: str | None = None, **kwds: Any, @@ -83,7 +86,19 @@ def on_task_postrun( if not task_id: return - r = get_redis_client() + # Get tenant_id directly from kwargs- each celery task has a tenant_id kwarg + if not kwargs: + logger.error(f"Task {task.name} (ID: {task_id}) is missing kwargs") + tenant_id = None + else: + tenant_id = kwargs.get("tenant_id") + + task_logger.debug( + f"Task {task.name} (ID: {task_id}) completed with state: {state} " + f"{f'for tenant_id={tenant_id}' if tenant_id else ''}" + ) + + r = get_redis_client(tenant_id=tenant_id) if task_id.startswith(RedisConnectorCredentialPair.PREFIX): r.srem(RedisConnectorCredentialPair.get_taskset_key(), task_id) @@ -124,7 +139,7 @@ def on_celeryd_init(sender: Any = None, conf: Any = None, **kwargs: Any) -> None def wait_for_redis(sender: Any, **kwargs: Any) -> None: - r = get_redis_client() + r = get_redis_client(tenant_id=None) WAIT_INTERVAL = 5 WAIT_LIMIT = 60 @@ -157,26 +172,44 @@ def wait_for_redis(sender: Any, **kwargs: Any) -> None: def on_secondary_worker_init(sender: Any, **kwargs: Any) -> None: - r = get_redis_client() - WAIT_INTERVAL = 5 WAIT_LIMIT = 60 logger.info("Running as a secondary celery worker.") - logger.info("Waiting for primary worker to be ready...") + logger.info("Waiting for all tenant primary workers to be ready...") time_start = time.monotonic() + while True: - if r.exists(DanswerRedisLocks.PRIMARY_WORKER): + tenant_ids = get_all_tenant_ids() + # Check if we have a primary worker lock for each tenant + all_tenants_ready = all( + get_redis_client(tenant_id=tenant_id).exists( + DanswerRedisLocks.PRIMARY_WORKER + ) + for tenant_id in tenant_ids + ) + + if all_tenants_ready: break - time.monotonic() time_elapsed = time.monotonic() - time_start + ready_tenants = sum( + 1 + for tenant_id in tenant_ids + if get_redis_client(tenant_id=tenant_id).exists( + DanswerRedisLocks.PRIMARY_WORKER + ) + ) + logger.info( - f"Primary worker is not ready yet. elapsed={time_elapsed:.1f} timeout={WAIT_LIMIT:.1f}" + f"Not all tenant primary workers are ready yet. " + f"Ready tenants: {ready_tenants}/{len(tenant_ids)} " + f"elapsed={time_elapsed:.1f} timeout={WAIT_LIMIT:.1f}" ) + if time_elapsed > WAIT_LIMIT: msg = ( - f"Primary worker was not ready within the timeout. " + f"Not all tenant primary workers were ready within the timeout " f"({WAIT_LIMIT} seconds). Exiting..." ) logger.error(msg) @@ -184,7 +217,7 @@ def on_secondary_worker_init(sender: Any, **kwargs: Any) -> None: time.sleep(WAIT_INTERVAL) - logger.info("Wait for primary worker completed successfully. Continuing...") + logger.info("All tenant primary workers are ready. Continuing...") return @@ -196,14 +229,26 @@ def on_worker_shutdown(sender: Any, **kwargs: Any) -> None: if not celery_is_worker_primary(sender): return - if not sender.primary_worker_lock: + if not hasattr(sender, "primary_worker_locks"): return - logger.info("Releasing primary worker lock.") - lock = sender.primary_worker_lock - if lock.owned(): - lock.release() - sender.primary_worker_lock = None + for tenant_id, lock in sender.primary_worker_locks.items(): + try: + if lock and lock.owned(): + logger.debug(f"Attempting to release lock for tenant {tenant_id}") + try: + lock.release() + logger.debug(f"Successfully released lock for tenant {tenant_id}") + except Exception as e: + logger.error( + f"Failed to release lock for tenant {tenant_id}. Error: {str(e)}" + ) + finally: + sender.primary_worker_locks[tenant_id] = None + except Exception as e: + logger.error( + f"Error checking lock status for tenant {tenant_id}. Error: {str(e)}" + ) def on_setup_logging( @@ -254,3 +299,11 @@ def on_setup_logging( task_logger.setLevel(loglevel) task_logger.propagate = False + + # hide celery task received spam + # e.g. "Task check_for_pruning[a1e96171-0ba8-4e00-887b-9fbf7442eab3] received" + strategy.logger.setLevel(logging.WARNING) + + # hide celery task succeeded/failed spam + # e.g. "Task check_for_pruning[a1e96171-0ba8-4e00-887b-9fbf7442eab3] succeeded in 0.03137450001668185s: None" + trace.logger.setLevel(logging.WARNING) diff --git a/backend/danswer/background/celery/apps/beat.py b/backend/danswer/background/celery/apps/beat.py index 47be61e36be..8ddc17efc52 100644 --- a/backend/danswer/background/celery/apps/beat.py +++ b/backend/danswer/background/celery/apps/beat.py @@ -88,7 +88,7 @@ def on_setup_logging( "task": task["task"], "schedule": task["schedule"], "options": task["options"], - "args": (tenant_id,), # Must pass tenant_id as an argument + "kwargs": {"tenant_id": tenant_id}, # Must pass tenant_id as an argument } # Include any existing beat schedules diff --git a/backend/danswer/background/celery/apps/primary.py b/backend/danswer/background/celery/apps/primary.py index c99607f4bc3..983b76773ed 100644 --- a/backend/danswer/background/celery/apps/primary.py +++ b/backend/danswer/background/celery/apps/primary.py @@ -1,7 +1,6 @@ import multiprocessing from typing import Any -import redis from celery import bootsteps # type: ignore from celery import Celery from celery import signals @@ -11,19 +10,21 @@ from celery.signals import worker_init from celery.signals import worker_ready from celery.signals import worker_shutdown -from celery.utils.log import get_task_logger import danswer.background.celery.apps.app_base as app_base +from danswer.background.celery.apps.app_base import task_logger from danswer.background.celery.celery_redis import RedisConnectorCredentialPair from danswer.background.celery.celery_redis import RedisConnectorDeletion from danswer.background.celery.celery_redis import RedisConnectorIndexing from danswer.background.celery.celery_redis import RedisConnectorPruning +from danswer.background.celery.celery_redis import RedisConnectorStop from danswer.background.celery.celery_redis import RedisDocumentSet from danswer.background.celery.celery_redis import RedisUserGroup from danswer.background.celery.celery_utils import celery_is_worker_primary from danswer.configs.constants import CELERY_PRIMARY_WORKER_LOCK_TIMEOUT from danswer.configs.constants import DanswerRedisLocks from danswer.configs.constants import POSTGRES_CELERY_WORKER_PRIMARY_APP_NAME +from danswer.db.engine import get_all_tenant_ids from danswer.db.engine import SqlEngine from danswer.redis.redis_pool import get_redis_client from danswer.utils.logger import setup_logger @@ -31,9 +32,6 @@ logger = setup_logger() -# use this within celery tasks to get celery task specific logging -task_logger = get_task_logger(__name__) - celery_app = Celery(__name__) celery_app.config_from_object("danswer.background.celery.configs.primary") @@ -81,82 +79,90 @@ def on_worker_init(sender: Any, **kwargs: Any) -> None: logger.info("Running as the primary celery worker.") + sender.primary_worker_locks = {} + # This is singleton work that should be done on startup exactly once # by the primary worker - r = get_redis_client() - - # For the moment, we're assuming that we are the only primary worker - # that should be running. - # TODO: maybe check for or clean up another zombie primary worker if we detect it - r.delete(DanswerRedisLocks.PRIMARY_WORKER) - - # this process wide lock is taken to help other workers start up in order. - # it is planned to use this lock to enforce singleton behavior on the primary - # worker, since the primary worker does redis cleanup on startup, but this isn't - # implemented yet. - lock = r.lock( - DanswerRedisLocks.PRIMARY_WORKER, - timeout=CELERY_PRIMARY_WORKER_LOCK_TIMEOUT, - ) - - logger.info("Primary worker lock: Acquire starting.") - acquired = lock.acquire(blocking_timeout=CELERY_PRIMARY_WORKER_LOCK_TIMEOUT / 2) - if acquired: - logger.info("Primary worker lock: Acquire succeeded.") - else: - logger.error("Primary worker lock: Acquire failed!") - raise WorkerShutdown("Primary worker lock could not be acquired!") - - sender.primary_worker_lock = lock - - # As currently designed, when this worker starts as "primary", we reinitialize redis - # to a clean state (for our purposes, anyway) - r.delete(DanswerRedisLocks.CHECK_VESPA_SYNC_BEAT_LOCK) - r.delete(DanswerRedisLocks.MONITOR_VESPA_SYNC_BEAT_LOCK) - - r.delete(RedisConnectorCredentialPair.get_taskset_key()) - r.delete(RedisConnectorCredentialPair.get_fence_key()) - - for key in r.scan_iter(RedisDocumentSet.TASKSET_PREFIX + "*"): - r.delete(key) + tenant_ids = get_all_tenant_ids() + for tenant_id in tenant_ids: + r = get_redis_client(tenant_id=tenant_id) + + # For the moment, we're assuming that we are the only primary worker + # that should be running. + # TODO: maybe check for or clean up another zombie primary worker if we detect it + r.delete(DanswerRedisLocks.PRIMARY_WORKER) + + # this process wide lock is taken to help other workers start up in order. + # it is planned to use this lock to enforce singleton behavior on the primary + # worker, since the primary worker does redis cleanup on startup, but this isn't + # implemented yet. + lock = r.lock( + DanswerRedisLocks.PRIMARY_WORKER, + timeout=CELERY_PRIMARY_WORKER_LOCK_TIMEOUT, + ) - for key in r.scan_iter(RedisDocumentSet.FENCE_PREFIX + "*"): - r.delete(key) + logger.info("Primary worker lock: Acquire starting.") + acquired = lock.acquire(blocking_timeout=CELERY_PRIMARY_WORKER_LOCK_TIMEOUT / 2) + if acquired: + logger.info("Primary worker lock: Acquire succeeded.") + else: + logger.error("Primary worker lock: Acquire failed!") + raise WorkerShutdown("Primary worker lock could not be acquired!") - for key in r.scan_iter(RedisUserGroup.TASKSET_PREFIX + "*"): - r.delete(key) + # tacking on our own user data to the sender + sender.primary_worker_locks[tenant_id] = lock - for key in r.scan_iter(RedisUserGroup.FENCE_PREFIX + "*"): - r.delete(key) + # As currently designed, when this worker starts as "primary", we reinitialize redis + # to a clean state (for our purposes, anyway) + r.delete(DanswerRedisLocks.CHECK_VESPA_SYNC_BEAT_LOCK) + r.delete(DanswerRedisLocks.MONITOR_VESPA_SYNC_BEAT_LOCK) - for key in r.scan_iter(RedisConnectorDeletion.TASKSET_PREFIX + "*"): - r.delete(key) + r.delete(RedisConnectorCredentialPair.get_taskset_key()) + r.delete(RedisConnectorCredentialPair.get_fence_key()) - for key in r.scan_iter(RedisConnectorDeletion.FENCE_PREFIX + "*"): - r.delete(key) + for key in r.scan_iter(RedisDocumentSet.TASKSET_PREFIX + "*"): + r.delete(key) - for key in r.scan_iter(RedisConnectorPruning.TASKSET_PREFIX + "*"): - r.delete(key) + for key in r.scan_iter(RedisDocumentSet.FENCE_PREFIX + "*"): + r.delete(key) - for key in r.scan_iter(RedisConnectorPruning.GENERATOR_COMPLETE_PREFIX + "*"): - r.delete(key) + for key in r.scan_iter(RedisUserGroup.TASKSET_PREFIX + "*"): + r.delete(key) - for key in r.scan_iter(RedisConnectorPruning.GENERATOR_PROGRESS_PREFIX + "*"): - r.delete(key) + for key in r.scan_iter(RedisUserGroup.FENCE_PREFIX + "*"): + r.delete(key) - for key in r.scan_iter(RedisConnectorPruning.FENCE_PREFIX + "*"): - r.delete(key) + for key in r.scan_iter(RedisConnectorDeletion.TASKSET_PREFIX + "*"): + r.delete(key) - for key in r.scan_iter(RedisConnectorIndexing.TASKSET_PREFIX + "*"): - r.delete(key) + for key in r.scan_iter(RedisConnectorDeletion.FENCE_PREFIX + "*"): + r.delete(key) - for key in r.scan_iter(RedisConnectorIndexing.GENERATOR_COMPLETE_PREFIX + "*"): - r.delete(key) + for key in r.scan_iter(RedisConnectorPruning.TASKSET_PREFIX + "*"): + r.delete(key) - for key in r.scan_iter(RedisConnectorIndexing.GENERATOR_PROGRESS_PREFIX + "*"): - r.delete(key) + for key in r.scan_iter(RedisConnectorPruning.GENERATOR_COMPLETE_PREFIX + "*"): + r.delete(key) + + for key in r.scan_iter(RedisConnectorPruning.GENERATOR_PROGRESS_PREFIX + "*"): + r.delete(key) + + for key in r.scan_iter(RedisConnectorPruning.FENCE_PREFIX + "*"): + r.delete(key) + + for key in r.scan_iter(RedisConnectorIndexing.TASKSET_PREFIX + "*"): + r.delete(key) - for key in r.scan_iter(RedisConnectorIndexing.FENCE_PREFIX + "*"): + for key in r.scan_iter(RedisConnectorIndexing.GENERATOR_COMPLETE_PREFIX + "*"): + r.delete(key) + + for key in r.scan_iter(RedisConnectorIndexing.GENERATOR_PROGRESS_PREFIX + "*"): + r.delete(key) + + for key in r.scan_iter(RedisConnectorIndexing.FENCE_PREFIX + "*"): + r.delete(key) + + for key in r.scan_iter(RedisConnectorStop.FENCE_PREFIX + "*"): r.delete(key) @@ -220,42 +226,58 @@ def start(self, worker: Any) -> None: def run_periodic_task(self, worker: Any) -> None: try: - if not worker.primary_worker_lock: + if not celery_is_worker_primary(worker): return - if not hasattr(worker, "primary_worker_lock"): + if not hasattr(worker, "primary_worker_locks"): return - r = get_redis_client() - - lock: redis.lock.Lock = worker.primary_worker_lock - - if lock.owned(): - task_logger.debug("Reacquiring primary worker lock.") - lock.reacquire() - else: - task_logger.warning( - "Full acquisition of primary worker lock. " - "Reasons could be computer sleep or a clock change." - ) - lock = r.lock( - DanswerRedisLocks.PRIMARY_WORKER, - timeout=CELERY_PRIMARY_WORKER_LOCK_TIMEOUT, - ) - - task_logger.info("Primary worker lock: Acquire starting.") - acquired = lock.acquire( - blocking_timeout=CELERY_PRIMARY_WORKER_LOCK_TIMEOUT / 2 - ) - if acquired: - task_logger.info("Primary worker lock: Acquire succeeded.") + # Retrieve all tenant IDs + tenant_ids = get_all_tenant_ids() + + for tenant_id in tenant_ids: + lock = worker.primary_worker_locks.get(tenant_id) + if not lock: + continue # Skip if no lock for this tenant + + r = get_redis_client(tenant_id=tenant_id) + + if lock.owned(): + task_logger.debug( + f"Reacquiring primary worker lock for tenant {tenant_id}." + ) + lock.reacquire() else: - task_logger.error("Primary worker lock: Acquire failed!") - raise TimeoutError("Primary worker lock could not be acquired!") + task_logger.warning( + f"Full acquisition of primary worker lock for tenant {tenant_id}. " + "Reasons could be worker restart or lock expiration." + ) + lock = r.lock( + DanswerRedisLocks.PRIMARY_WORKER, + timeout=CELERY_PRIMARY_WORKER_LOCK_TIMEOUT, + ) + + task_logger.info( + f"Primary worker lock for tenant {tenant_id}: Acquire starting." + ) + acquired = lock.acquire( + blocking_timeout=CELERY_PRIMARY_WORKER_LOCK_TIMEOUT / 2 + ) + if acquired: + task_logger.info( + f"Primary worker lock for tenant {tenant_id}: Acquire succeeded." + ) + worker.primary_worker_locks[tenant_id] = lock + else: + task_logger.error( + f"Primary worker lock for tenant {tenant_id}: Acquire failed!" + ) + raise TimeoutError( + f"Primary worker lock for tenant {tenant_id} could not be acquired!" + ) - worker.primary_worker_lock = lock except Exception: - task_logger.exception("HubPeriodicTask.run_periodic_task exceptioned.") + task_logger.exception("Periodic task failed.") def stop(self, worker: Any) -> None: # Cancel the scheduled task when the worker stops diff --git a/backend/danswer/background/celery/celery_redis.py b/backend/danswer/background/celery/celery_redis.py index f1a5697e246..e412b0bf733 100644 --- a/backend/danswer/background/celery/celery_redis.py +++ b/backend/danswer/background/celery/celery_redis.py @@ -313,6 +313,8 @@ def generate_tasks( lock: redis.lock.Lock, tenant_id: str | None, ) -> int | None: + """Returns None if the cc_pair doesn't exist. + Otherwise, returns an int with the number of generated tasks.""" last_lock_time = time.monotonic() async_results = [] @@ -465,14 +467,8 @@ def generate_tasks( return len(async_results) - def is_pruning(self, db_session: Session, redis_client: Redis) -> bool: + def is_pruning(self, redis_client: Redis) -> bool: """A single example of a helper method being refactored into the redis helper""" - cc_pair = get_connector_credential_pair_from_id( - cc_pair_id=int(self._id), db_session=db_session - ) - if not cc_pair: - raise ValueError(f"cc_pair_id {self._id} does not exist.") - if redis_client.exists(self.fence_key): return True @@ -538,6 +534,36 @@ def generate_tasks( ) -> int | None: return None + def is_indexing(self, redis_client: Redis) -> bool: + """A single example of a helper method being refactored into the redis helper""" + if redis_client.exists(self.fence_key): + return True + + return False + + +class RedisConnectorStop(RedisObjectHelper): + """Used to signal any running tasks for a connector to stop. We should refactor + connector related redis helpers into a single class. + """ + + PREFIX = "connectorstop" + FENCE_PREFIX = PREFIX + "_fence" # a fence for the entire indexing process + TASKSET_PREFIX = PREFIX + "_taskset" # stores a list of prune tasks id's + + def __init__(self, id: int) -> None: + super().__init__(str(id)) + + def generate_tasks( + self, + celery_app: Celery, + db_session: Session, + redis_client: Redis, + lock: redis.lock.Lock | None, + tenant_id: str | None, + ) -> int | None: + return None + def celery_get_queue_length(queue: str, r: Redis) -> int: """This is a redis specific way to get the length of a celery queue. diff --git a/backend/danswer/background/celery/celery_utils.py b/backend/danswer/background/celery/celery_utils.py index 794f89232c5..18038a349de 100644 --- a/backend/danswer/background/celery/celery_utils.py +++ b/backend/danswer/background/celery/celery_utils.py @@ -1,4 +1,3 @@ -from collections.abc import Callable from datetime import datetime from datetime import timezone from typing import Any @@ -6,6 +5,7 @@ from sqlalchemy.orm import Session from danswer.background.celery.celery_redis import RedisConnectorDeletion +from danswer.background.indexing.run_indexing import RunIndexingCallbackInterface from danswer.configs.app_configs import MAX_PRUNING_DOCUMENT_RETRIEVAL_PER_MINUTE from danswer.connectors.cross_connector_utils.rate_limit_wrapper import ( rate_limit_builder, @@ -27,7 +27,10 @@ def _get_deletion_status( - connector_id: int, credential_id: int, db_session: Session + connector_id: int, + credential_id: int, + db_session: Session, + tenant_id: str | None = None, ) -> TaskQueueState | None: """We no longer store TaskQueueState in the DB for a deletion attempt. This function populates TaskQueueState by just checking redis. @@ -40,7 +43,7 @@ def _get_deletion_status( rcd = RedisConnectorDeletion(cc_pair.id) - r = get_redis_client() + r = get_redis_client(tenant_id=tenant_id) if not r.exists(rcd.fence_key): return None @@ -50,9 +53,14 @@ def _get_deletion_status( def get_deletion_attempt_snapshot( - connector_id: int, credential_id: int, db_session: Session + connector_id: int, + credential_id: int, + db_session: Session, + tenant_id: str | None = None, ) -> DeletionAttemptSnapshot | None: - deletion_task = _get_deletion_status(connector_id, credential_id, db_session) + deletion_task = _get_deletion_status( + connector_id, credential_id, db_session, tenant_id + ) if not deletion_task: return None @@ -71,7 +79,7 @@ def document_batch_to_ids( def extract_ids_from_runnable_connector( runnable_connector: BaseConnector, - progress_callback: Callable[[int], None] | None = None, + callback: RunIndexingCallbackInterface | None = None, ) -> set[str]: """ If the PruneConnector hasnt been implemented for the given connector, just pull @@ -102,8 +110,10 @@ def extract_ids_from_runnable_connector( max_calls=MAX_PRUNING_DOCUMENT_RETRIEVAL_PER_MINUTE, period=60 )(document_batch_to_ids) for doc_batch in doc_batch_generator: - if progress_callback: - progress_callback(len(doc_batch)) + if callback: + if callback.should_stop(): + raise RuntimeError("Stop signal received") + callback.progress(len(doc_batch)) all_connector_doc_ids.update(doc_batch_processing_func(doc_batch)) return all_connector_doc_ids diff --git a/backend/danswer/background/celery/tasks/connector_deletion/tasks.py b/backend/danswer/background/celery/tasks/connector_deletion/tasks.py index bfca8793ba0..0b8c98c18c6 100644 --- a/backend/danswer/background/celery/tasks/connector_deletion/tasks.py +++ b/backend/danswer/background/celery/tasks/connector_deletion/tasks.py @@ -1,3 +1,6 @@ +from datetime import datetime +from datetime import timezone + import redis from celery import Celery from celery import shared_task @@ -8,6 +11,12 @@ from danswer.background.celery.apps.app_base import task_logger from danswer.background.celery.celery_redis import RedisConnectorDeletion +from danswer.background.celery.celery_redis import RedisConnectorIndexing +from danswer.background.celery.celery_redis import RedisConnectorPruning +from danswer.background.celery.celery_redis import RedisConnectorStop +from danswer.background.celery.tasks.shared.RedisConnectorDeletionFenceData import ( + RedisConnectorDeletionFenceData, +) from danswer.configs.app_configs import JOB_TIMEOUT from danswer.configs.constants import CELERY_VESPA_SYNC_BEAT_LOCK_TIMEOUT from danswer.configs.constants import DanswerRedisLocks @@ -15,17 +24,23 @@ from danswer.db.connector_credential_pair import get_connector_credential_pairs from danswer.db.engine import get_session_with_tenant from danswer.db.enums import ConnectorCredentialPairStatus +from danswer.db.search_settings import get_all_search_settings from danswer.redis.redis_pool import get_redis_client +class TaskDependencyError(RuntimeError): + """Raised to the caller to indicate dependent tasks are running that would interfere + with connector deletion.""" + + @shared_task( name="check_for_connector_deletion_task", soft_time_limit=JOB_TIMEOUT, trail=False, bind=True, ) -def check_for_connector_deletion_task(self: Task, tenant_id: str | None) -> None: - r = get_redis_client() +def check_for_connector_deletion_task(self: Task, *, tenant_id: str | None) -> None: + r = get_redis_client(tenant_id=tenant_id) lock_beat = r.lock( DanswerRedisLocks.CHECK_CONNECTOR_DELETION_BEAT_LOCK, @@ -37,17 +52,30 @@ def check_for_connector_deletion_task(self: Task, tenant_id: str | None) -> None if not lock_beat.acquire(blocking=False): return + # collect cc_pair_ids cc_pair_ids: list[int] = [] with get_session_with_tenant(tenant_id) as db_session: cc_pairs = get_connector_credential_pairs(db_session) for cc_pair in cc_pairs: cc_pair_ids.append(cc_pair.id) + # try running cleanup on the cc_pair_ids for cc_pair_id in cc_pair_ids: with get_session_with_tenant(tenant_id) as db_session: - try_generate_document_cc_pair_cleanup_tasks( - self.app, cc_pair_id, db_session, r, lock_beat, tenant_id - ) + rcs = RedisConnectorStop(cc_pair_id) + try: + try_generate_document_cc_pair_cleanup_tasks( + self.app, cc_pair_id, db_session, r, lock_beat, tenant_id + ) + except TaskDependencyError as e: + # this means we wanted to start deleting but dependent tasks were running + # Leave a stop signal to clear indexing and pruning tasks more quickly + task_logger.info(str(e)) + r.set(rcs.fence_key, cc_pair_id) + else: + # clear the stop signal if it exists ... no longer needed + r.delete(rcs.fence_key) + except SoftTimeLimitExceeded: task_logger.info( "Soft time limit exceeded, task is being terminated gracefully." @@ -70,6 +98,10 @@ def try_generate_document_cc_pair_cleanup_tasks( """Returns an int if syncing is needed. The int represents the number of sync tasks generated. Note that syncing can still be required even if the number of sync tasks generated is zero. Returns None if no syncing is required. + + Will raise TaskDependencyError if dependent tasks such as indexing and pruning are + still running. In our case, the caller reacts by setting a stop signal in Redis to + exit those tasks as quickly as possible. """ lock_beat.reacquire() @@ -90,28 +122,63 @@ def try_generate_document_cc_pair_cleanup_tasks( if cc_pair.status != ConnectorCredentialPairStatus.DELETING: return None - # add tasks to celery and build up the task set to monitor in redis - r.delete(rcd.taskset_key) - - # Add all documents that need to be updated into the queue - task_logger.info( - f"RedisConnectorDeletion.generate_tasks starting. cc_pair={cc_pair.id}" + # set a basic fence to start + fence_value = RedisConnectorDeletionFenceData( + num_tasks=None, + submitted=datetime.now(timezone.utc), ) - tasks_generated = rcd.generate_tasks(app, db_session, r, lock_beat, tenant_id) - if tasks_generated is None: + r.set(rcd.fence_key, fence_value.model_dump_json()) + + try: + # do not proceed if connector indexing or connector pruning are running + search_settings_list = get_all_search_settings(db_session) + for search_settings in search_settings_list: + rci = RedisConnectorIndexing(cc_pair_id, search_settings.id) + if r.get(rci.fence_key): + raise TaskDependencyError( + f"Connector deletion - Delayed (indexing in progress): " + f"cc_pair={cc_pair_id} " + f"search_settings={search_settings.id}" + ) + + rcp = RedisConnectorPruning(cc_pair_id) + if r.get(rcp.fence_key): + raise TaskDependencyError( + f"Connector deletion - Delayed (pruning in progress): " + f"cc_pair={cc_pair_id}" + ) + + # add tasks to celery and build up the task set to monitor in redis + r.delete(rcd.taskset_key) + + # Add all documents that need to be updated into the queue + task_logger.info( + f"RedisConnectorDeletion.generate_tasks starting. cc_pair={cc_pair_id}" + ) + tasks_generated = rcd.generate_tasks(app, db_session, r, lock_beat, tenant_id) + if tasks_generated is None: + raise ValueError("RedisConnectorDeletion.generate_tasks returned None") + except TaskDependencyError: + r.delete(rcd.fence_key) + raise + except Exception: + task_logger.exception("Unexpected exception") + r.delete(rcd.fence_key) return None + else: + # Currently we are allowing the sync to proceed with 0 tasks. + # It's possible for sets/groups to be generated initially with no entries + # and they still need to be marked as up to date. + # if tasks_generated == 0: + # return 0 - # Currently we are allowing the sync to proceed with 0 tasks. - # It's possible for sets/groups to be generated initially with no entries - # and they still need to be marked as up to date. - # if tasks_generated == 0: - # return 0 + task_logger.info( + f"RedisConnectorDeletion.generate_tasks finished. " + f"cc_pair={cc_pair_id} tasks_generated={tasks_generated}" + ) - task_logger.info( - f"RedisConnectorDeletion.generate_tasks finished. " - f"cc_pair={cc_pair.id} tasks_generated={tasks_generated}" - ) + # set this only after all tasks have been added + fence_value.num_tasks = tasks_generated + r.set(rcd.fence_key, fence_value.model_dump_json()) - # set this only after all tasks have been added - r.set(rcd.fence_key, tasks_generated) return tasks_generated diff --git a/backend/danswer/background/celery/tasks/indexing/tasks.py b/backend/danswer/background/celery/tasks/indexing/tasks.py index 00a769da053..293a18404d7 100644 --- a/backend/danswer/background/celery/tasks/indexing/tasks.py +++ b/backend/danswer/background/celery/tasks/indexing/tasks.py @@ -5,6 +5,7 @@ from typing import cast from uuid import uuid4 +import redis from celery import Celery from celery import shared_task from celery import Task @@ -13,12 +14,15 @@ from sqlalchemy.orm import Session from danswer.background.celery.apps.app_base import task_logger +from danswer.background.celery.celery_redis import RedisConnectorDeletion from danswer.background.celery.celery_redis import RedisConnectorIndexing +from danswer.background.celery.celery_redis import RedisConnectorStop from danswer.background.celery.tasks.shared.RedisConnectorIndexingFenceData import ( RedisConnectorIndexingFenceData, ) from danswer.background.indexing.job_client import SimpleJobClient from danswer.background.indexing.run_indexing import run_indexing_entrypoint +from danswer.background.indexing.run_indexing import RunIndexingCallbackInterface from danswer.configs.app_configs import DISABLE_INDEX_UPDATE_ON_SWAP from danswer.configs.constants import CELERY_INDEXING_LOCK_TIMEOUT from danswer.configs.constants import CELERY_VESPA_SYNC_BEAT_LOCK_TIMEOUT @@ -50,15 +54,39 @@ logger = setup_logger() +class RunIndexingCallback(RunIndexingCallbackInterface): + def __init__( + self, + stop_key: str, + generator_progress_key: str, + redis_lock: redis.lock.Lock, + redis_client: Redis, + ): + super().__init__() + self.redis_lock: redis.lock.Lock = redis_lock + self.stop_key: str = stop_key + self.generator_progress_key: str = generator_progress_key + self.redis_client = redis_client + + def should_stop(self) -> bool: + if self.redis_client.exists(self.stop_key): + return True + return False + + def progress(self, amount: int) -> None: + self.redis_lock.reacquire() + self.redis_client.incrby(self.generator_progress_key, amount) + + @shared_task( name="check_for_indexing", soft_time_limit=300, bind=True, ) -def check_for_indexing(self: Task, tenant_id: str | None) -> int | None: +def check_for_indexing(self: Task, *, tenant_id: str | None) -> int | None: tasks_created = 0 - r = get_redis_client() + r = get_redis_client(tenant_id=tenant_id) lock_beat = r.lock( DanswerRedisLocks.CHECK_INDEXING_BEAT_LOCK, @@ -262,6 +290,10 @@ def try_creating_indexing_task( return None # skip indexing if the cc_pair is deleting + rcd = RedisConnectorDeletion(cc_pair.id) + if r.exists(rcd.fence_key): + return None + db_session.refresh(cc_pair) if cc_pair.status == ConnectorCredentialPairStatus.DELETING: return None @@ -308,13 +340,8 @@ def try_creating_indexing_task( raise RuntimeError("send_task for connector_indexing_proxy_task failed.") # now fill out the fence with the rest of the data - fence_value = RedisConnectorIndexingFenceData( - index_attempt_id=index_attempt_id, - started=None, - submitted=datetime.now(timezone.utc), - celery_task_id=result.id, - ) - + fence_value.index_attempt_id = index_attempt_id + fence_value.celery_task_id = result.id r.set(rci.fence_key, fence_value.model_dump_json()) except Exception: r.delete(rci.fence_key) @@ -403,7 +430,23 @@ def connector_indexing_task( attempt = None n_final_progress = 0 - r = get_redis_client() + r = get_redis_client(tenant_id=tenant_id) + + rcd = RedisConnectorDeletion(cc_pair_id) + if r.exists(rcd.fence_key): + raise RuntimeError( + f"Indexing will not start because connector deletion is in progress: " + f"cc_pair={cc_pair_id} " + f"fence={rcd.fence_key}" + ) + + rcs = RedisConnectorStop(cc_pair_id) + if r.exists(rcs.fence_key): + raise RuntimeError( + f"Indexing will not start because a connector stop signal was detected: " + f"cc_pair={cc_pair_id} " + f"fence={rcs.fence_key}" + ) rci = RedisConnectorIndexing(cc_pair_id, search_settings_id) @@ -447,17 +490,20 @@ def connector_indexing_task( if not acquired: task_logger.warning( f"Indexing task already running, exiting...: " - f"cc_pair_id={cc_pair_id} search_settings_id={search_settings_id}" + f"cc_pair={cc_pair_id} search_settings={search_settings_id}" ) # r.set(rci.generator_complete_key, HTTPStatus.CONFLICT.value) return None + fence_data.started = datetime.now(timezone.utc) + r.set(rci.fence_key, fence_data.model_dump_json()) + try: with get_session_with_tenant(tenant_id) as db_session: attempt = get_index_attempt(db_session, index_attempt_id) if not attempt: raise ValueError( - f"Index attempt not found: index_attempt_id={index_attempt_id}" + f"Index attempt not found: index_attempt={index_attempt_id}" ) cc_pair = get_connector_credential_pair_from_id( @@ -466,31 +512,31 @@ def connector_indexing_task( ) if not cc_pair: - raise ValueError(f"cc_pair not found: cc_pair_id={cc_pair_id}") + raise ValueError(f"cc_pair not found: cc_pair={cc_pair_id}") if not cc_pair.connector: raise ValueError( - f"Connector not found: connector_id={cc_pair.connector_id}" + f"Connector not found: cc_pair={cc_pair_id} connector={cc_pair.connector_id}" ) if not cc_pair.credential: raise ValueError( - f"Credential not found: credential_id={cc_pair.credential_id}" + f"Credential not found: cc_pair={cc_pair_id} credential={cc_pair.credential_id}" ) rci = RedisConnectorIndexing(cc_pair_id, search_settings_id) - # Define the callback function - def redis_increment_callback(amount: int) -> None: - lock.reacquire() - r.incrby(rci.generator_progress_key, amount) + # define a callback class + callback = RunIndexingCallback( + rcs.fence_key, rci.generator_progress_key, lock, r + ) run_indexing_entrypoint( index_attempt_id, tenant_id, cc_pair_id, is_ee, - progress_callback=redis_increment_callback, + callback=callback, ) # get back the total number of indexed docs and return it @@ -503,9 +549,10 @@ def redis_increment_callback(amount: int) -> None: r.set(rci.generator_complete_key, HTTPStatus.OK.value) except Exception as e: - task_logger.exception(f"Failed to run indexing for cc_pair_id={cc_pair_id}.") + task_logger.exception(f"Indexing failed: cc_pair={cc_pair_id}") if attempt: - mark_attempt_failed(attempt, db_session, failure_reason=str(e)) + with get_session_with_tenant(tenant_id) as db_session: + mark_attempt_failed(attempt, db_session, failure_reason=str(e)) r.delete(rci.generator_lock_key) r.delete(rci.generator_progress_key) diff --git a/backend/danswer/background/celery/tasks/pruning/tasks.py b/backend/danswer/background/celery/tasks/pruning/tasks.py index 7e73c24cd68..d9579ccf93c 100644 --- a/backend/danswer/background/celery/tasks/pruning/tasks.py +++ b/backend/danswer/background/celery/tasks/pruning/tasks.py @@ -11,8 +11,11 @@ from sqlalchemy.orm import Session from danswer.background.celery.apps.app_base import task_logger +from danswer.background.celery.celery_redis import RedisConnectorDeletion from danswer.background.celery.celery_redis import RedisConnectorPruning +from danswer.background.celery.celery_redis import RedisConnectorStop from danswer.background.celery.celery_utils import extract_ids_from_runnable_connector +from danswer.background.celery.tasks.indexing.tasks import RunIndexingCallback from danswer.configs.app_configs import ALLOW_SIMULTANEOUS_PRUNING from danswer.configs.app_configs import JOB_TIMEOUT from danswer.configs.constants import CELERY_PRUNING_LOCK_TIMEOUT @@ -41,8 +44,8 @@ soft_time_limit=JOB_TIMEOUT, bind=True, ) -def check_for_pruning(self: Task, tenant_id: str | None) -> None: - r = get_redis_client() +def check_for_pruning(self: Task, *, tenant_id: str | None) -> None: + r = get_redis_client(tenant_id=tenant_id) lock_beat = r.lock( DanswerRedisLocks.CHECK_PRUNE_BEAT_LOCK, @@ -168,6 +171,10 @@ def try_creating_prune_generator_task( return None # skip pruning if the cc_pair is deleting + rcd = RedisConnectorDeletion(cc_pair.id) + if r.exists(rcd.fence_key): + return None + db_session.refresh(cc_pair) if cc_pair.status == ConnectorCredentialPairStatus.DELETING: return None @@ -222,7 +229,7 @@ def connector_pruning_generator_task( and compares those IDs to locally stored documents and deletes all locally stored IDs missing from the most recently pulled document ID list""" - r = get_redis_client() + r = get_redis_client(tenant_id=tenant_id) rcp = RedisConnectorPruning(cc_pair_id) @@ -252,11 +259,6 @@ def connector_pruning_generator_task( ) return - # Define the callback function - def redis_increment_callback(amount: int) -> None: - lock.reacquire() - r.incrby(rcp.generator_progress_key, amount) - runnable_connector = instantiate_connector( db_session, cc_pair.connector.source, @@ -265,9 +267,14 @@ def redis_increment_callback(amount: int) -> None: cc_pair.credential, ) + rcs = RedisConnectorStop(cc_pair_id) + + callback = RunIndexingCallback( + rcs.fence_key, rcp.generator_progress_key, lock, r + ) # a list of docs in the source all_connector_doc_ids: set[str] = extract_ids_from_runnable_connector( - runnable_connector, redis_increment_callback + runnable_connector, callback ) # a list of docs in our local index @@ -285,7 +292,7 @@ def redis_increment_callback(amount: int) -> None: task_logger.info( f"Pruning set collected: " - f"cc_pair={cc_pair.id} " + f"cc_pair={cc_pair_id} " f"docs_to_remove={len(doc_ids_to_remove)} " f"doc_source={cc_pair.connector.source}" ) @@ -308,7 +315,9 @@ def redis_increment_callback(amount: int) -> None: r.set(rcp.generator_complete_key, tasks_generated) except Exception as e: - task_logger.exception(f"Failed to run pruning for connector id {connector_id}.") + task_logger.exception( + f"Failed to run pruning: cc_pair={cc_pair_id} connector={connector_id}" + ) r.delete(rcp.generator_progress_key) r.delete(rcp.taskset_key) diff --git a/backend/danswer/background/celery/tasks/shared/RedisConnectorDeletionFenceData.py b/backend/danswer/background/celery/tasks/shared/RedisConnectorDeletionFenceData.py new file mode 100644 index 00000000000..1c664d14b4b --- /dev/null +++ b/backend/danswer/background/celery/tasks/shared/RedisConnectorDeletionFenceData.py @@ -0,0 +1,8 @@ +from datetime import datetime + +from pydantic import BaseModel + + +class RedisConnectorDeletionFenceData(BaseModel): + num_tasks: int | None + submitted: datetime diff --git a/backend/danswer/background/celery/tasks/shared/tasks.py b/backend/danswer/background/celery/tasks/shared/tasks.py index 4e3ff2e267b..116e7e1ff7e 100644 --- a/backend/danswer/background/celery/tasks/shared/tasks.py +++ b/backend/danswer/background/celery/tasks/shared/tasks.py @@ -1,11 +1,9 @@ -from datetime import datetime from http import HTTPStatus import httpx from celery import shared_task from celery import Task from celery.exceptions import SoftTimeLimitExceeded -from pydantic import BaseModel from tenacity import RetryError from danswer.access.access import get_access_for_document @@ -15,6 +13,7 @@ from danswer.db.document import delete_documents_complete__no_commit from danswer.db.document import get_document from danswer.db.document import get_document_connector_count +from danswer.db.document import mark_document_as_modified from danswer.db.document import mark_document_as_synced from danswer.db.document_set import fetch_document_sets_for_document from danswer.db.engine import get_session_with_tenant @@ -23,12 +22,7 @@ from danswer.document_index.interfaces import VespaDocumentFields from danswer.server.documents.models import ConnectorCredentialPairIdentifier - -class RedisConnectorIndexingFenceData(BaseModel): - index_attempt_id: int | None - started: datetime | None - submitted: datetime - celery_task_id: str | None +DOCUMENT_BY_CC_PAIR_CLEANUP_MAX_RETRIES = 3 # 5 seconds more than RetryDocumentIndex STOP_AFTER+MAX_WAIT @@ -40,7 +34,7 @@ class RedisConnectorIndexingFenceData(BaseModel): name="document_by_cc_pair_cleanup_task", soft_time_limit=LIGHT_SOFT_TIME_LIMIT, time_limit=LIGHT_TIME_LIMIT, - max_retries=3, + max_retries=DOCUMENT_BY_CC_PAIR_CLEANUP_MAX_RETRIES, bind=True, ) def document_by_cc_pair_cleanup_task( @@ -65,7 +59,7 @@ def document_by_cc_pair_cleanup_task( connector / credential pair from the access list (6) delete all relevant entries from postgres """ - task_logger.info(f"doc={document_id}") + task_logger.info(f"tenant={tenant_id} doc={document_id}") try: with get_session_with_tenant(tenant_id) as db_session: @@ -131,6 +125,8 @@ def document_by_cc_pair_cleanup_task( else: pass + db_session.commit() + task_logger.info( f"tenant={tenant_id} " f"doc={document_id} " @@ -138,7 +134,6 @@ def document_by_cc_pair_cleanup_task( f"refcount={count} " f"chunks={chunks_affected}" ) - db_session.commit() except SoftTimeLimitExceeded: task_logger.info( f"SoftTimeLimitExceeded exception. tenant={tenant_id} doc={document_id}" @@ -169,9 +164,19 @@ def document_by_cc_pair_cleanup_task( f"Unexpected exception: tenant={tenant_id} doc={document_id}" ) - # Exponential backoff from 2^4 to 2^6 ... i.e. 16, 32, 64 - countdown = 2 ** (self.request.retries + 4) - self.retry(exc=e, countdown=countdown) + if self.request.retries < DOCUMENT_BY_CC_PAIR_CLEANUP_MAX_RETRIES: + # Still retrying. Exponential backoff from 2^4 to 2^6 ... i.e. 16, 32, 64 + countdown = 2 ** (self.request.retries + 4) + self.retry(exc=e, countdown=countdown) + else: + # This is the last attempt! mark the document as dirty in the db so that it + # eventually gets fixed out of band via stale document reconciliation + task_logger.info( + f"Max retries reached. Marking doc as dirty for reconciliation: " + f"tenant={tenant_id} doc={document_id}" + ) + with get_session_with_tenant(tenant_id): + mark_document_as_modified(document_id, db_session) return False return True diff --git a/backend/danswer/background/celery/tasks/vespa/tasks.py b/backend/danswer/background/celery/tasks/vespa/tasks.py index 7945cff1595..b058a97e1bc 100644 --- a/backend/danswer/background/celery/tasks/vespa/tasks.py +++ b/backend/danswer/background/celery/tasks/vespa/tasks.py @@ -25,6 +25,9 @@ from danswer.background.celery.celery_redis import RedisConnectorPruning from danswer.background.celery.celery_redis import RedisDocumentSet from danswer.background.celery.celery_redis import RedisUserGroup +from danswer.background.celery.tasks.shared.RedisConnectorDeletionFenceData import ( + RedisConnectorDeletionFenceData, +) from danswer.background.celery.tasks.shared.RedisConnectorIndexingFenceData import ( RedisConnectorIndexingFenceData, ) @@ -65,6 +68,7 @@ from danswer.document_index.factory import get_default_document_index from danswer.document_index.interfaces import VespaDocumentFields from danswer.redis.redis_pool import get_redis_client +from danswer.utils.logger import setup_logger from danswer.utils.variable_functionality import fetch_versioned_implementation from danswer.utils.variable_functionality import ( fetch_versioned_implementation_with_fallback, @@ -72,6 +76,8 @@ from danswer.utils.variable_functionality import global_version from danswer.utils.variable_functionality import noop_fallback +logger = setup_logger() + # celery auto associates tasks created inside another task, # which bloats the result metadata considerably. trail=False prevents this. @@ -81,11 +87,11 @@ trail=False, bind=True, ) -def check_for_vespa_sync_task(self: Task, tenant_id: str | None) -> None: +def check_for_vespa_sync_task(self: Task, *, tenant_id: str | None) -> None: """Runs periodically to check if any document needs syncing. Generates sets of tasks for Celery if syncing is needed.""" - r = get_redis_client() + r = get_redis_client(tenant_id=tenant_id) lock_beat = r.lock( DanswerRedisLocks.CHECK_VESPA_SYNC_BEAT_LOCK, @@ -370,7 +376,7 @@ def monitor_document_set_taskset( count = cast(int, r.scard(rds.taskset_key)) task_logger.info( - f"Document set sync progress: document_set_id={document_set_id} " + f"Document set sync progress: document_set={document_set_id} " f"remaining={count} initial={initial_count}" ) if count > 0: @@ -385,12 +391,12 @@ def monitor_document_set_taskset( # if there are no connectors, then delete the document set. delete_document_set(document_set_row=document_set, db_session=db_session) task_logger.info( - f"Successfully deleted document set with ID: '{document_set_id}'!" + f"Successfully deleted document set: document_set={document_set_id}" ) else: mark_document_set_as_synced(document_set_id, db_session) task_logger.info( - f"Successfully synced document set with ID: '{document_set_id}'!" + f"Successfully synced document set: document_set={document_set_id}" ) r.delete(rds.taskset_key) @@ -410,19 +416,29 @@ def monitor_connector_deletion_taskset( rcd = RedisConnectorDeletion(cc_pair_id) - fence_value = r.get(rcd.fence_key) + # read related data and evaluate/print task progress + fence_value = cast(bytes, r.get(rcd.fence_key)) if fence_value is None: return try: - initial_count = int(cast(int, fence_value)) + fence_json = fence_value.decode("utf-8") + fence_data = RedisConnectorDeletionFenceData.model_validate_json( + cast(str, fence_json) + ) except ValueError: - task_logger.error("The value is not an integer.") + task_logger.exception( + "monitor_ccpair_indexing_taskset: fence_data not decodeable." + ) + raise + + # the fence is setting up but isn't ready yet + if fence_data.num_tasks is None: return count = cast(int, r.scard(rcd.taskset_key)) task_logger.info( - f"Connector deletion progress: cc_pair={cc_pair_id} remaining={count} initial={initial_count}" + f"Connector deletion progress: cc_pair={cc_pair_id} remaining={count} initial={fence_data.num_tasks}" ) if count > 0: return @@ -485,7 +501,7 @@ def monitor_connector_deletion_taskset( ) if not connector or not len(connector.credentials): task_logger.info( - "Found no credentials left for connector, deleting connector" + "Connector deletion - Found no credentials left for connector, deleting connector" ) db_session.delete(connector) db_session.commit() @@ -495,17 +511,17 @@ def monitor_connector_deletion_taskset( error_message = f"Error: {str(e)}\n\nStack Trace:\n{stack_trace}" add_deletion_failure_message(db_session, cc_pair_id, error_message) task_logger.exception( - f"Failed to run connector_deletion. " + f"Connector deletion exceptioned: " f"cc_pair={cc_pair_id} connector={cc_pair.connector_id} credential={cc_pair.credential_id}" ) raise e task_logger.info( - f"Successfully deleted cc_pair: " + f"Connector deletion succeeded: " f"cc_pair={cc_pair_id} " f"connector={cc_pair.connector_id} " f"credential={cc_pair.credential_id} " - f"docs_deleted={initial_count}" + f"docs_deleted={fence_data.num_tasks}" ) r.delete(rcd.taskset_key) @@ -620,6 +636,7 @@ def monitor_ccpair_indexing_taskset( return # Read result state BEFORE generator_complete_key to avoid a race condition + # never use any blocking methods on the result from inside a task! result: AsyncResult = AsyncResult(fence_data.celery_task_id) result_state = result.state @@ -685,7 +702,7 @@ def monitor_vespa_sync(self: Task, tenant_id: str | None) -> bool: Returns True if the task actually did work, False """ - r = get_redis_client() + r = get_redis_client(tenant_id=tenant_id) lock_beat: redis.lock.Lock = r.lock( DanswerRedisLocks.MONITOR_VESPA_SYNC_BEAT_LOCK, diff --git a/backend/danswer/background/indexing/run_indexing.py b/backend/danswer/background/indexing/run_indexing.py index cb507390452..d95a6a70d57 100644 --- a/backend/danswer/background/indexing/run_indexing.py +++ b/backend/danswer/background/indexing/run_indexing.py @@ -1,6 +1,7 @@ import time import traceback -from collections.abc import Callable +from abc import ABC +from abc import abstractmethod from datetime import datetime from datetime import timedelta from datetime import timezone @@ -41,6 +42,19 @@ INDEXING_TRACER_NUM_PRINT_ENTRIES = 5 +class RunIndexingCallbackInterface(ABC): + """Defines a callback interface to be passed to + to run_indexing_entrypoint.""" + + @abstractmethod + def should_stop(self) -> bool: + """Signal to stop the looping function in flight.""" + + @abstractmethod + def progress(self, amount: int) -> None: + """Send progress updates to the caller.""" + + def _get_connector_runner( db_session: Session, attempt: IndexAttempt, @@ -92,7 +106,7 @@ def _run_indexing( db_session: Session, index_attempt: IndexAttempt, tenant_id: str | None, - progress_callback: Callable[[int], None] | None = None, + callback: RunIndexingCallbackInterface | None = None, ) -> None: """ 1. Get documents which are either new or updated from specified application @@ -206,6 +220,11 @@ def _run_indexing( # index being built. We want to populate it even for paused connectors # Often paused connectors are sources that aren't updated frequently but the # contents still need to be initially pulled. + if callback: + if callback.should_stop(): + raise RuntimeError("Connector stop signal detected") + + # TODO: should we move this into the above callback instead? db_session.refresh(db_cc_pair) if ( ( @@ -263,8 +282,8 @@ def _run_indexing( # be inaccurate db_session.commit() - if progress_callback: - progress_callback(len(doc_batch)) + if callback: + callback.progress(len(doc_batch)) # This new value is updated every batch, so UI can refresh per batch update update_docs_indexed( @@ -394,7 +413,7 @@ def run_indexing_entrypoint( tenant_id: str | None, connector_credential_pair_id: int, is_ee: bool = False, - progress_callback: Callable[[int], None] | None = None, + callback: RunIndexingCallbackInterface | None = None, ) -> None: try: if is_ee: @@ -417,7 +436,7 @@ def run_indexing_entrypoint( f"credentials='{attempt.connector_credential_pair.connector_id}'" ) - _run_indexing(db_session, attempt, tenant_id, progress_callback) + _run_indexing(db_session, attempt, tenant_id, callback) logger.info( f"Indexing finished for tenant {tenant_id}: " diff --git a/backend/danswer/chat/process_message.py b/backend/danswer/chat/process_message.py index ea4e7be93d4..f58a34c3243 100644 --- a/backend/danswer/chat/process_message.py +++ b/backend/danswer/chat/process_message.py @@ -672,6 +672,7 @@ def stream_chat_message_objects( all_docs_useful=selected_db_search_docs is not None ), document_pruning_config=document_pruning_config, + structured_response_format=new_msg_req.structured_response_format, ), prompt_config=prompt_config, llm=( diff --git a/backend/danswer/configs/constants.py b/backend/danswer/configs/constants.py index 9858f2354b9..caa903af71d 100644 --- a/backend/danswer/configs/constants.py +++ b/backend/danswer/configs/constants.py @@ -46,7 +46,6 @@ POSTGRES_CELERY_WORKER_INDEXING_CHILD_APP_NAME = "celery_worker_indexing_child" POSTGRES_PERMISSIONS_APP_NAME = "permissions" POSTGRES_UNKNOWN_APP_NAME = "unknown" -POSTGRES_DEFAULT_SCHEMA = "public" # API Keys DANSWER_API_KEY_PREFIX = "API_KEY__" @@ -71,6 +70,7 @@ KV_INSTANCE_DOMAIN_KEY = "instance_domain" KV_ENTERPRISE_SETTINGS_KEY = "danswer_enterprise_settings" KV_CUSTOM_ANALYTICS_SCRIPT_KEY = "__custom_analytics_script__" +KV_DOCUMENTS_SEEDED_KEY = "documents_seeded" CELERY_VESPA_SYNC_BEAT_LOCK_TIMEOUT = 60 CELERY_PRIMARY_WORKER_LOCK_TIMEOUT = 120 @@ -136,6 +136,7 @@ class DocumentSource(str, Enum): class NotificationType(str, Enum): REINDEX = "reindex" PERSONA_SHARED = "persona_shared" + TRIAL_ENDS_TWO_DAYS = "two_day_trial_ending" # 2 days left in trial class BlobType(str, Enum): @@ -160,6 +161,9 @@ class AuthType(str, Enum): OIDC = "oidc" SAML = "saml" + # google auth and basic + CLOUD = "cloud" + class SessionType(str, Enum): CHAT = "Chat" diff --git a/backend/danswer/connectors/axero/connector.py b/backend/danswer/connectors/axero/connector.py index a4d5162b6ce..000151209de 100644 --- a/backend/danswer/connectors/axero/connector.py +++ b/backend/danswer/connectors/axero/connector.py @@ -15,7 +15,6 @@ from danswer.connectors.cross_connector_utils.rate_limit_wrapper import ( rate_limit_builder, ) -from danswer.connectors.cross_connector_utils.retry_wrapper import retry_builder from danswer.connectors.interfaces import GenerateDocumentsOutput from danswer.connectors.interfaces import PollConnector from danswer.connectors.interfaces import SecondsSinceUnixEpoch @@ -24,6 +23,7 @@ from danswer.connectors.models import Section from danswer.file_processing.html_utils import parse_html_page_basic from danswer.utils.logger import setup_logger +from danswer.utils.retry_wrapper import retry_builder logger = setup_logger() diff --git a/backend/danswer/connectors/clickup/connector.py b/backend/danswer/connectors/clickup/connector.py index 78d572af413..6ef60763baf 100644 --- a/backend/danswer/connectors/clickup/connector.py +++ b/backend/danswer/connectors/clickup/connector.py @@ -10,7 +10,6 @@ from danswer.connectors.cross_connector_utils.rate_limit_wrapper import ( rate_limit_builder, ) -from danswer.connectors.cross_connector_utils.retry_wrapper import retry_builder from danswer.connectors.interfaces import GenerateDocumentsOutput from danswer.connectors.interfaces import LoadConnector from danswer.connectors.interfaces import PollConnector @@ -19,6 +18,7 @@ from danswer.connectors.models import ConnectorMissingCredentialError from danswer.connectors.models import Document from danswer.connectors.models import Section +from danswer.utils.retry_wrapper import retry_builder CLICKUP_API_BASE_URL = "https://api.clickup.com/api/v2" diff --git a/backend/danswer/connectors/confluence/utils.py b/backend/danswer/connectors/confluence/utils.py index 029e35e6538..beb0465be60 100644 --- a/backend/danswer/connectors/confluence/utils.py +++ b/backend/danswer/connectors/confluence/utils.py @@ -37,7 +37,7 @@ def get_user_email_from_username__server( _USER_NOT_FOUND = "Unknown Confluence User" -_USER_ID_TO_DISPLAY_NAME_CACHE: dict[str, str] = {} +_USER_ID_TO_DISPLAY_NAME_CACHE: dict[str, str | None] = {} def _get_user(confluence_client: OnyxConfluence, user_id: str) -> str: @@ -67,7 +67,7 @@ def _get_user(confluence_client: OnyxConfluence, user_id: str) -> str: _USER_ID_TO_DISPLAY_NAME_CACHE[user_id] = found_display_name - return _USER_ID_TO_DISPLAY_NAME_CACHE.get(user_id, _USER_NOT_FOUND) + return _USER_ID_TO_DISPLAY_NAME_CACHE.get(user_id) or _USER_NOT_FOUND def extract_text_from_confluence_html( diff --git a/backend/danswer/connectors/discourse/connector.py b/backend/danswer/connectors/discourse/connector.py index d74aad0f276..d1b6395a189 100644 --- a/backend/danswer/connectors/discourse/connector.py +++ b/backend/danswer/connectors/discourse/connector.py @@ -14,7 +14,6 @@ from danswer.connectors.cross_connector_utils.rate_limit_wrapper import ( rate_limit_builder, ) -from danswer.connectors.cross_connector_utils.retry_wrapper import retry_builder from danswer.connectors.interfaces import GenerateDocumentsOutput from danswer.connectors.interfaces import PollConnector from danswer.connectors.interfaces import SecondsSinceUnixEpoch @@ -24,6 +23,7 @@ from danswer.connectors.models import Section from danswer.file_processing.html_utils import parse_html_page_basic from danswer.utils.logger import setup_logger +from danswer.utils.retry_wrapper import retry_builder logger = setup_logger() diff --git a/backend/danswer/connectors/document360/connector.py b/backend/danswer/connectors/document360/connector.py index 6a9f4ba6a56..7ccf3c92e62 100644 --- a/backend/danswer/connectors/document360/connector.py +++ b/backend/danswer/connectors/document360/connector.py @@ -11,7 +11,6 @@ from danswer.connectors.cross_connector_utils.rate_limit_wrapper import ( rate_limit_builder, ) -from danswer.connectors.cross_connector_utils.retry_wrapper import retry_builder from danswer.connectors.document360.utils import flatten_child_categories from danswer.connectors.interfaces import GenerateDocumentsOutput from danswer.connectors.interfaces import LoadConnector @@ -22,6 +21,7 @@ from danswer.connectors.models import Document from danswer.connectors.models import Section from danswer.file_processing.html_utils import parse_html_page_basic +from danswer.utils.retry_wrapper import retry_builder # Limitations and Potential Improvements # 1. The "Categories themselves contain potentially relevant information" but they're not pulled in diff --git a/backend/danswer/connectors/file/connector.py b/backend/danswer/connectors/file/connector.py index 9992159eb35..d07a224478e 100644 --- a/backend/danswer/connectors/file/connector.py +++ b/backend/danswer/connectors/file/connector.py @@ -10,7 +10,6 @@ from danswer.configs.app_configs import INDEX_BATCH_SIZE from danswer.configs.constants import DocumentSource -from danswer.configs.constants import POSTGRES_DEFAULT_SCHEMA from danswer.connectors.cross_connector_utils.miscellaneous_utils import time_str_to_utc from danswer.connectors.interfaces import GenerateDocumentsOutput from danswer.connectors.interfaces import LoadConnector @@ -28,7 +27,8 @@ from danswer.file_processing.extract_file_text import read_text_file from danswer.file_store.file_store import get_default_file_store from danswer.utils.logger import setup_logger -from shared_configs.configs import current_tenant_id +from shared_configs.configs import CURRENT_TENANT_ID_CONTEXTVAR +from shared_configs.configs import POSTGRES_DEFAULT_SCHEMA logger = setup_logger() @@ -175,7 +175,7 @@ def load_credentials(self, credentials: dict[str, Any]) -> dict[str, Any] | None def load_from_state(self) -> GenerateDocumentsOutput: documents: list[Document] = [] - token = current_tenant_id.set(self.tenant_id) + token = CURRENT_TENANT_ID_CONTEXTVAR.set(self.tenant_id) with get_session_with_tenant(self.tenant_id) as db_session: for file_path in self.file_locations: @@ -199,7 +199,7 @@ def load_from_state(self) -> GenerateDocumentsOutput: if documents: yield documents - current_tenant_id.reset(token) + CURRENT_TENANT_ID_CONTEXTVAR.reset(token) if __name__ == "__main__": diff --git a/backend/danswer/connectors/google_drive/connector.py b/backend/danswer/connectors/google_drive/connector.py index 9f8c6fbfda8..c48df5bb741 100644 --- a/backend/danswer/connectors/google_drive/connector.py +++ b/backend/danswer/connectors/google_drive/connector.py @@ -19,7 +19,6 @@ from danswer.configs.app_configs import INDEX_BATCH_SIZE from danswer.configs.constants import DocumentSource from danswer.configs.constants import IGNORE_FOR_QA -from danswer.connectors.cross_connector_utils.retry_wrapper import retry_builder from danswer.connectors.google_drive.connector_auth import get_google_drive_creds from danswer.connectors.google_drive.constants import ( DB_CREDENTIALS_DICT_DELEGATED_USER_KEY, @@ -40,6 +39,7 @@ from danswer.file_processing.unstructured import unstructured_to_text from danswer.utils.batching import batch_generator from danswer.utils.logger import setup_logger +from danswer.utils.retry_wrapper import retry_builder logger = setup_logger() diff --git a/backend/danswer/connectors/loopio/connector.py b/backend/danswer/connectors/loopio/connector.py index e10bed87617..d3bdfe503f7 100644 --- a/backend/danswer/connectors/loopio/connector.py +++ b/backend/danswer/connectors/loopio/connector.py @@ -161,7 +161,7 @@ def _process_entries( ] doc_batch.append( Document( - id=entry["id"], + id=str(entry["id"]), sections=[Section(link=link, text=content_text)], source=DocumentSource.LOOPIO, semantic_identifier=questions[0], diff --git a/backend/danswer/connectors/slack/utils.py b/backend/danswer/connectors/slack/utils.py index 20e859a6d44..78bc42a0926 100644 --- a/backend/danswer/connectors/slack/utils.py +++ b/backend/danswer/connectors/slack/utils.py @@ -10,9 +10,9 @@ from slack_sdk.errors import SlackApiError from slack_sdk.web import SlackResponse -from danswer.connectors.cross_connector_utils.retry_wrapper import retry_builder from danswer.connectors.models import BasicExpertInfo from danswer.utils.logger import setup_logger +from danswer.utils.retry_wrapper import retry_builder logger = setup_logger() diff --git a/backend/danswer/danswerbot/slack/listener.py b/backend/danswer/danswerbot/slack/listener.py index e3b2d213e83..a40dbe9a9b9 100644 --- a/backend/danswer/danswerbot/slack/listener.py +++ b/backend/danswer/danswerbot/slack/listener.py @@ -57,7 +57,7 @@ from danswer.server.manage.models import SlackBotTokens from danswer.utils.logger import setup_logger from danswer.utils.variable_functionality import set_is_ee_based_on_env_variable -from shared_configs.configs import current_tenant_id +from shared_configs.configs import CURRENT_TENANT_ID_CONTEXTVAR from shared_configs.configs import MODEL_SERVER_HOST from shared_configs.configs import MODEL_SERVER_PORT from shared_configs.configs import SLACK_CHANNEL_ID @@ -363,7 +363,7 @@ def process_message( # Set the current tenant ID at the beginning for all DB calls within this thread if client.tenant_id: logger.info(f"Setting tenant ID to {client.tenant_id}") - token = current_tenant_id.set(client.tenant_id) + token = CURRENT_TENANT_ID_CONTEXTVAR.set(client.tenant_id) try: with get_session_with_tenant(client.tenant_id) as db_session: slack_bot_config = get_slack_bot_config_for_channel( @@ -412,7 +412,7 @@ def process_message( apologize_for_fail(details, client) finally: if client.tenant_id: - current_tenant_id.reset(token) + CURRENT_TENANT_ID_CONTEXTVAR.reset(token) def acknowledge_message(req: SocketModeRequest, client: TenantSocketModeClient) -> None: @@ -510,9 +510,9 @@ def _initialize_socket_client(socket_client: TenantSocketModeClient) -> None: for tenant_id in tenant_ids: with get_session_with_tenant(tenant_id) as db_session: try: - token = current_tenant_id.set(tenant_id or "public") + token = CURRENT_TENANT_ID_CONTEXTVAR.set(tenant_id or "public") latest_slack_bot_tokens = fetch_tokens() - current_tenant_id.reset(token) + CURRENT_TENANT_ID_CONTEXTVAR.reset(token) if ( tenant_id not in slack_bot_tokens diff --git a/backend/danswer/db/connector_credential_pair.py b/backend/danswer/db/connector_credential_pair.py index b3e1de7647a..b333dd78603 100644 --- a/backend/danswer/db/connector_credential_pair.py +++ b/backend/danswer/db/connector_credential_pair.py @@ -341,6 +341,8 @@ def add_credential_to_connector( access_type: AccessType, groups: list[int] | None, auto_sync_options: dict | None = None, + initial_status: ConnectorCredentialPairStatus = ConnectorCredentialPairStatus.ACTIVE, + last_successful_index_time: datetime | None = None, ) -> StatusResponse: connector = fetch_connector_by_id(connector_id, db_session) credential = fetch_credential_by_id(credential_id, user, db_session) @@ -384,9 +386,10 @@ def add_credential_to_connector( connector_id=connector_id, credential_id=credential_id, name=cc_pair_name, - status=ConnectorCredentialPairStatus.ACTIVE, + status=initial_status, access_type=access_type, auto_sync_options=auto_sync_options, + last_successful_index_time=last_successful_index_time, ) db_session.add(association) db_session.flush() # make sure the association has an id diff --git a/backend/danswer/db/credentials.py b/backend/danswer/db/credentials.py index abab904cc48..80ebe1b1538 100644 --- a/backend/danswer/db/credentials.py +++ b/backend/danswer/db/credentials.py @@ -40,6 +40,8 @@ DocumentSource.MEDIAWIKI, } +PUBLIC_CREDENTIAL_ID = 0 + def _add_user_filters( stmt: Select, @@ -242,7 +244,6 @@ def create_credential( ) db_session.add(credential) db_session.flush() # This ensures the credential gets an ID - _relate_credential_to_user_groups__no_commit( db_session=db_session, credential_id=credential.id, @@ -385,12 +386,11 @@ def delete_credential( def create_initial_public_credential(db_session: Session) -> None: - public_cred_id = 0 error_msg = ( "DB is not in a valid initial state." "There must exist an empty public credential for data connectors that do not require additional Auth." ) - first_credential = fetch_credential_by_id(public_cred_id, None, db_session) + first_credential = fetch_credential_by_id(PUBLIC_CREDENTIAL_ID, None, db_session) if first_credential is not None: if first_credential.credential_json != {} or first_credential.user is not None: @@ -398,7 +398,7 @@ def create_initial_public_credential(db_session: Session) -> None: return credential = Credential( - id=public_cred_id, + id=PUBLIC_CREDENTIAL_ID, credential_json={}, user_id=None, ) @@ -406,6 +406,24 @@ def create_initial_public_credential(db_session: Session) -> None: db_session.commit() +def cleanup_gmail_credentials(db_session: Session) -> None: + gmail_credentials = fetch_credentials_by_source( + db_session=db_session, user=None, document_source=DocumentSource.GMAIL + ) + for credential in gmail_credentials: + db_session.delete(credential) + db_session.commit() + + +def cleanup_google_drive_credentials(db_session: Session) -> None: + google_drive_credentials = fetch_credentials_by_source( + db_session=db_session, user=None, document_source=DocumentSource.GOOGLE_DRIVE + ) + for credential in google_drive_credentials: + db_session.delete(credential) + db_session.commit() + + def delete_gmail_service_account_credentials( user: User | None, db_session: Session ) -> None: diff --git a/backend/danswer/db/document.py b/backend/danswer/db/document.py index 8aee28aef05..2e142a2c0b5 100644 --- a/backend/danswer/db/document.py +++ b/backend/danswer/db/document.py @@ -375,6 +375,20 @@ def update_docs_last_modified__no_commit( doc.last_modified = now +def mark_document_as_modified( + document_id: str, + db_session: Session, +) -> None: + stmt = select(DbDocument).where(DbDocument.id == document_id) + doc = db_session.scalar(stmt) + if doc is None: + raise ValueError(f"No document with ID: {document_id}") + + # update last_synced + doc.last_modified = datetime.now(timezone.utc) + db_session.commit() + + def mark_document_as_synced(document_id: str, db_session: Session) -> None: stmt = select(DbDocument).where(DbDocument.id == document_id) doc = db_session.scalar(stmt) diff --git a/backend/danswer/db/engine.py b/backend/danswer/db/engine.py index 625c36435cd..b071a41e8c3 100644 --- a/backend/danswer/db/engine.py +++ b/backend/danswer/db/engine.py @@ -36,11 +36,11 @@ from danswer.configs.app_configs import POSTGRES_PORT from danswer.configs.app_configs import POSTGRES_USER from danswer.configs.app_configs import SECRET_JWT_KEY -from danswer.configs.constants import POSTGRES_DEFAULT_SCHEMA from danswer.configs.constants import POSTGRES_UNKNOWN_APP_NAME from danswer.configs.constants import TENANT_ID_PREFIX from danswer.utils.logger import setup_logger -from shared_configs.configs import current_tenant_id +from shared_configs.configs import CURRENT_TENANT_ID_CONTEXTVAR +from shared_configs.configs import POSTGRES_DEFAULT_SCHEMA logger = setup_logger() @@ -192,13 +192,13 @@ def get_app_name(cls) -> str: def get_all_tenant_ids() -> list[str] | list[None]: if not MULTI_TENANT: return [None] - with get_session_with_tenant(tenant_id="public") as session: + with get_session_with_tenant(tenant_id=POSTGRES_DEFAULT_SCHEMA) as session: result = session.execute( text( - """ - SELECT schema_name - FROM information_schema.schemata - WHERE schema_name NOT IN ('pg_catalog', 'information_schema', 'public')""" + f""" + SELECT schema_name + FROM information_schema.schemata + WHERE schema_name NOT IN ('pg_catalog', 'information_schema', '{POSTGRES_DEFAULT_SCHEMA}')""" ) ) tenant_ids = [row[0] for row in result] @@ -260,12 +260,12 @@ def get_current_tenant_id(request: Request) -> str: """Dependency that extracts the tenant ID from the JWT token in the request and sets the context variable.""" if not MULTI_TENANT: tenant_id = POSTGRES_DEFAULT_SCHEMA - current_tenant_id.set(tenant_id) + CURRENT_TENANT_ID_CONTEXTVAR.set(tenant_id) return tenant_id token = request.cookies.get("tenant_details") if not token: - current_value = current_tenant_id.get() + current_value = CURRENT_TENANT_ID_CONTEXTVAR.get() # If no token is present, use the default schema or handle accordingly return current_value @@ -273,14 +273,14 @@ def get_current_tenant_id(request: Request) -> str: payload = jwt.decode(token, SECRET_JWT_KEY, algorithms=["HS256"]) tenant_id = payload.get("tenant_id") if not tenant_id: - return current_tenant_id.get() + return CURRENT_TENANT_ID_CONTEXTVAR.get() if not is_valid_schema_name(tenant_id): raise HTTPException(status_code=400, detail="Invalid tenant ID format") - current_tenant_id.set(tenant_id) + CURRENT_TENANT_ID_CONTEXTVAR.set(tenant_id) return tenant_id except jwt.InvalidTokenError: - return current_tenant_id.get() + return CURRENT_TENANT_ID_CONTEXTVAR.get() except Exception as e: logger.error(f"Unexpected error in get_current_tenant_id: {str(e)}") raise HTTPException(status_code=500, detail="Internal server error") @@ -291,7 +291,7 @@ async def get_async_session_with_tenant( tenant_id: str | None = None, ) -> AsyncGenerator[AsyncSession, None]: if tenant_id is None: - tenant_id = current_tenant_id.get() + tenant_id = CURRENT_TENANT_ID_CONTEXTVAR.get() if not is_valid_schema_name(tenant_id): logger.error(f"Invalid tenant ID: {tenant_id}") @@ -319,30 +319,32 @@ async def get_async_session_with_tenant( def get_session_with_tenant( tenant_id: str | None = None, ) -> Generator[Session, None, None]: - """Generate a database session with the appropriate tenant schema set.""" + """Generate a database session bound to a connection with the appropriate tenant schema set.""" engine = get_sqlalchemy_engine() + if tenant_id is None: - tenant_id = current_tenant_id.get() + tenant_id = CURRENT_TENANT_ID_CONTEXTVAR.get() + else: + CURRENT_TENANT_ID_CONTEXTVAR.set(tenant_id) + + event.listen(engine, "checkout", set_search_path_on_checkout) if not is_valid_schema_name(tenant_id): raise HTTPException(status_code=400, detail="Invalid tenant ID") - # Establish a raw connection without starting a transaction + # Establish a raw connection with engine.connect() as connection: - # Access the raw DBAPI connection + # Access the raw DBAPI connection and set the search_path dbapi_connection = connection.connection - # Execute SET search_path outside of any transaction + # Set the search_path outside of any transaction cursor = dbapi_connection.cursor() try: - cursor.execute(f'SET search_path TO "{tenant_id}"') - # Optionally verify the search_path was set correctly - cursor.execute("SHOW search_path") - cursor.fetchone() + cursor.execute(f'SET search_path = "{tenant_id}"') finally: cursor.close() - # Proceed to create a session using the connection + # Bind the session to the connection with Session(bind=connection, expire_on_commit=False) as session: try: yield session @@ -356,16 +358,25 @@ def get_session_with_tenant( cursor.close() +def set_search_path_on_checkout( + dbapi_conn: Any, connection_record: Any, connection_proxy: Any +) -> None: + tenant_id = CURRENT_TENANT_ID_CONTEXTVAR.get() + if tenant_id and is_valid_schema_name(tenant_id): + with dbapi_conn.cursor() as cursor: + cursor.execute(f'SET search_path TO "{tenant_id}"') + + def get_session_generator_with_tenant() -> Generator[Session, None, None]: - tenant_id = current_tenant_id.get() + tenant_id = CURRENT_TENANT_ID_CONTEXTVAR.get() with get_session_with_tenant(tenant_id) as session: yield session def get_session() -> Generator[Session, None, None]: """Generate a database session with the appropriate tenant schema set.""" - tenant_id = current_tenant_id.get() - if tenant_id == "public" and MULTI_TENANT: + tenant_id = CURRENT_TENANT_ID_CONTEXTVAR.get() + if tenant_id == POSTGRES_DEFAULT_SCHEMA and MULTI_TENANT: raise HTTPException(status_code=401, detail="User must authenticate") engine = get_sqlalchemy_engine() @@ -381,7 +392,7 @@ def get_session() -> Generator[Session, None, None]: async def get_async_session() -> AsyncGenerator[AsyncSession, None]: """Generate an async database session with the appropriate tenant schema set.""" - tenant_id = current_tenant_id.get() + tenant_id = CURRENT_TENANT_ID_CONTEXTVAR.get() engine = get_sqlalchemy_async_engine() async with AsyncSession(engine, expire_on_commit=False) as async_session: if MULTI_TENANT: diff --git a/backend/danswer/db/index_attempt.py b/backend/danswer/db/index_attempt.py index fbbbef1bbfc..45a07387949 100644 --- a/backend/danswer/db/index_attempt.py +++ b/backend/danswer/db/index_attempt.py @@ -1,5 +1,6 @@ from collections.abc import Sequence from datetime import datetime +from datetime import timedelta from datetime import timezone from sqlalchemy import and_ @@ -66,6 +67,32 @@ def create_index_attempt( return new_attempt.id +def mock_successful_index_attempt( + connector_credential_pair_id: int, + search_settings_id: int, + docs_indexed: int, + db_session: Session, +) -> int: + """Should not be used in any user triggered flows""" + db_time = func.now() + new_attempt = IndexAttempt( + connector_credential_pair_id=connector_credential_pair_id, + search_settings_id=search_settings_id, + from_beginning=True, + status=IndexingStatus.SUCCESS, + total_docs_indexed=docs_indexed, + new_docs_indexed=docs_indexed, + # Need this to be some convincing random looking value and it can't be 0 + # or the indexing rate would calculate out to infinity + time_started=db_time - timedelta(seconds=1.92), + time_updated=db_time, + ) + db_session.add(new_attempt) + db_session.commit() + + return new_attempt.id + + def get_in_progress_index_attempts( connector_id: int | None, db_session: Session, diff --git a/backend/danswer/db/notification.py b/backend/danswer/db/notification.py index bd58add14a0..a6cdf989177 100644 --- a/backend/danswer/db/notification.py +++ b/backend/danswer/db/notification.py @@ -4,6 +4,7 @@ from sqlalchemy.orm import Session from sqlalchemy.sql import func +from danswer.auth.schemas import UserRole from danswer.configs.constants import NotificationType from danswer.db.models import Notification from danswer.db.models import User @@ -54,7 +55,9 @@ def get_notification_by_id( notif = db_session.get(Notification, notification_id) if not notif: raise ValueError(f"No notification found with id {notification_id}") - if notif.user_id != user_id: + if notif.user_id != user_id and not ( + notif.user_id is None and user is not None and user.role == UserRole.ADMIN + ): raise PermissionError( f"User {user_id} is not authorized to access notification {notification_id}" ) diff --git a/backend/danswer/db/persona.py b/backend/danswer/db/persona.py index 36d2d25c402..f23b3f6d071 100644 --- a/backend/danswer/db/persona.py +++ b/backend/danswer/db/persona.py @@ -328,7 +328,6 @@ def update_all_personas_display_priority( for persona in personas: persona.display_priority = display_priority_map[persona.id] - db_session.commit() diff --git a/backend/danswer/indexing/embedder.py b/backend/danswer/indexing/embedder.py index 3e9383cb828..1c11a01b390 100644 --- a/backend/danswer/indexing/embedder.py +++ b/backend/danswer/indexing/embedder.py @@ -103,6 +103,9 @@ def embed_chunks( self, chunks: list[DocAwareChunk], ) -> list[IndexChunk]: + """Adds embeddings to the chunks, the title and metadata suffixes are added to the chunk as well + if they exist. If there is no space for it, it would have been thrown out at the chunking step. + """ # All chunks at this point must have some non-empty content flat_chunk_texts: list[str] = [] large_chunks_present = False @@ -121,6 +124,11 @@ def embed_chunks( flat_chunk_texts.append(chunk_text) if chunk.mini_chunk_texts: + if chunk.large_chunk_reference_ids: + # A large chunk does not contain mini chunks, if it matches the large chunk + # with a high score, then mini chunks would not be used anyway + # otherwise it should match the normal chunk + raise RuntimeError("Large chunk contains mini chunks") flat_chunk_texts.extend(chunk.mini_chunk_texts) embeddings = self.embedding_model.encode( diff --git a/backend/danswer/indexing/indexing_pipeline.py b/backend/danswer/indexing/indexing_pipeline.py index d40bd341fdf..507956ff40f 100644 --- a/backend/danswer/indexing/indexing_pipeline.py +++ b/backend/danswer/indexing/indexing_pipeline.py @@ -195,6 +195,8 @@ def index_doc_batch_prepare( db_session: Session, ignore_time_skip: bool = False, ) -> DocumentBatchPrepareContext | None: + """This sets up the documents in the relational DB (source of truth) for permissions, metadata, etc. + This preceeds indexing it into the actual document index.""" documents = [] for document in document_batch: empty_contents = not any(section.text.strip() for section in document.sections) diff --git a/backend/danswer/key_value_store/factory.py b/backend/danswer/key_value_store/factory.py index 7b52fdabef8..142e9031b77 100644 --- a/backend/danswer/key_value_store/factory.py +++ b/backend/danswer/key_value_store/factory.py @@ -3,5 +3,6 @@ def get_kv_store() -> KeyValueStore: - # this is the only one supported currently + # In the Multi Tenant case, the tenant context is picked up automatically, it does not need to be passed in + # It's read from the global thread level variable return PgRedisKVStore() diff --git a/backend/danswer/key_value_store/interface.py b/backend/danswer/key_value_store/interface.py index 190c53189dd..aa815171f06 100644 --- a/backend/danswer/key_value_store/interface.py +++ b/backend/danswer/key_value_store/interface.py @@ -14,6 +14,8 @@ class KvKeyNotFoundError(Exception): class KeyValueStore: + # In the Multi Tenant case, the tenant context is picked up automatically, it does not need to be passed in + # It's read from the global thread level variable @abc.abstractmethod def store(self, key: str, val: JSON_ro, encrypt: bool = False) -> None: raise NotImplementedError diff --git a/backend/danswer/key_value_store/store.py b/backend/danswer/key_value_store/store.py index 98f3d7ec1cb..d0a17b26565 100644 --- a/backend/danswer/key_value_store/store.py +++ b/backend/danswer/key_value_store/store.py @@ -4,6 +4,7 @@ from typing import cast from fastapi import HTTPException +from redis.client import Redis from sqlalchemy import text from sqlalchemy.orm import Session @@ -16,7 +17,8 @@ from danswer.key_value_store.interface import KvKeyNotFoundError from danswer.redis.redis_pool import get_redis_client from danswer.utils.logger import setup_logger -from shared_configs.configs import current_tenant_id +from shared_configs.configs import CURRENT_TENANT_ID_CONTEXTVAR +from shared_configs.configs import POSTGRES_DEFAULT_SCHEMA logger = setup_logger() @@ -26,16 +28,23 @@ class PgRedisKVStore(KeyValueStore): - def __init__(self) -> None: - self.redis_client = get_redis_client() + def __init__( + self, redis_client: Redis | None = None, tenant_id: str | None = None + ) -> None: + # If no redis_client is provided, fall back to the context var + if redis_client is not None: + self.redis_client = redis_client + else: + tenant_id = tenant_id or CURRENT_TENANT_ID_CONTEXTVAR.get() + self.redis_client = get_redis_client(tenant_id=tenant_id) @contextmanager def get_session(self) -> Iterator[Session]: engine = get_sqlalchemy_engine() with Session(engine, expire_on_commit=False) as session: if MULTI_TENANT: - tenant_id = current_tenant_id.get() - if tenant_id == "public": + tenant_id = CURRENT_TENANT_ID_CONTEXTVAR.get() + if tenant_id == POSTGRES_DEFAULT_SCHEMA: raise HTTPException( status_code=401, detail="User must authenticate" ) diff --git a/backend/danswer/llm/answering/models.py b/backend/danswer/llm/answering/models.py index fb5fa9c313e..87c1297fe92 100644 --- a/backend/danswer/llm/answering/models.py +++ b/backend/danswer/llm/answering/models.py @@ -116,6 +116,10 @@ class AnswerStyleConfig(BaseModel): document_pruning_config: DocumentPruningConfig = Field( default_factory=DocumentPruningConfig ) + # forces the LLM to return a structured response, see + # https://platform.openai.com/docs/guides/structured-outputs/introduction + # right now, only used by the simple chat API + structured_response_format: dict | None = None @model_validator(mode="after") def check_quotes_and_citation(self) -> "AnswerStyleConfig": diff --git a/backend/danswer/llm/chat_llm.py b/backend/danswer/llm/chat_llm.py index d50f8253182..d450fff0a63 100644 --- a/backend/danswer/llm/chat_llm.py +++ b/backend/danswer/llm/chat_llm.py @@ -280,6 +280,7 @@ def _completion( tools: list[dict] | None, tool_choice: ToolChoiceOptions | None, stream: bool, + structured_response_format: dict | None = None, ) -> litellm.ModelResponse | litellm.CustomStreamWrapper: if isinstance(prompt, list): prompt = [ @@ -313,6 +314,11 @@ def _completion( # NOTE: we can't pass this in if tools are not specified # or else OpenAI throws an error **({"parallel_tool_calls": False} if tools else {}), + **( + {"response_format": structured_response_format} + if structured_response_format + else {} + ), **self._model_kwargs, ) except Exception as e: @@ -336,12 +342,16 @@ def _invoke_implementation( prompt: LanguageModelInput, tools: list[dict] | None = None, tool_choice: ToolChoiceOptions | None = None, + structured_response_format: dict | None = None, ) -> BaseMessage: if LOG_DANSWER_MODEL_INTERACTIONS: self.log_model_configs() response = cast( - litellm.ModelResponse, self._completion(prompt, tools, tool_choice, False) + litellm.ModelResponse, + self._completion( + prompt, tools, tool_choice, False, structured_response_format + ), ) choice = response.choices[0] if hasattr(choice, "message"): @@ -354,18 +364,21 @@ def _stream_implementation( prompt: LanguageModelInput, tools: list[dict] | None = None, tool_choice: ToolChoiceOptions | None = None, + structured_response_format: dict | None = None, ) -> Iterator[BaseMessage]: if LOG_DANSWER_MODEL_INTERACTIONS: self.log_model_configs() if DISABLE_LITELLM_STREAMING: - yield self.invoke(prompt) + yield self.invoke(prompt, tools, tool_choice, structured_response_format) return output = None response = cast( litellm.CustomStreamWrapper, - self._completion(prompt, tools, tool_choice, True), + self._completion( + prompt, tools, tool_choice, True, structured_response_format + ), ) try: for part in response: diff --git a/backend/danswer/llm/custom_llm.py b/backend/danswer/llm/custom_llm.py index 4a5ba7857c3..6b80406cf2f 100644 --- a/backend/danswer/llm/custom_llm.py +++ b/backend/danswer/llm/custom_llm.py @@ -80,6 +80,7 @@ def _invoke_implementation( prompt: LanguageModelInput, tools: list[dict] | None = None, tool_choice: ToolChoiceOptions | None = None, + structured_response_format: dict | None = None, ) -> BaseMessage: return self._execute(prompt) @@ -88,5 +89,6 @@ def _stream_implementation( prompt: LanguageModelInput, tools: list[dict] | None = None, tool_choice: ToolChoiceOptions | None = None, + structured_response_format: dict | None = None, ) -> Iterator[BaseMessage]: yield self._execute(prompt) diff --git a/backend/danswer/llm/factory.py b/backend/danswer/llm/factory.py index f930c3d3358..eedf7ccc763 100644 --- a/backend/danswer/llm/factory.py +++ b/backend/danswer/llm/factory.py @@ -51,6 +51,7 @@ def _create_llm(model: str) -> LLM: return get_llm( provider=llm_provider.provider, model=model, + deployment_name=llm_provider.deployment_name, api_key=llm_provider.api_key, api_base=llm_provider.api_base, api_version=llm_provider.api_version, @@ -104,7 +105,7 @@ def _create_llm(model: str) -> LLM: def get_llm( provider: str, model: str, - deployment_name: str | None = None, + deployment_name: str | None, api_key: str | None = None, api_base: str | None = None, api_version: str | None = None, @@ -116,6 +117,7 @@ def get_llm( return DefaultMultiLLM( model_provider=provider, model_name=model, + deployment_name=deployment_name, api_key=api_key, api_base=api_base, api_version=api_version, diff --git a/backend/danswer/llm/interfaces.py b/backend/danswer/llm/interfaces.py index 6cb58e46c6b..7deee11dfa6 100644 --- a/backend/danswer/llm/interfaces.py +++ b/backend/danswer/llm/interfaces.py @@ -88,11 +88,14 @@ def invoke( prompt: LanguageModelInput, tools: list[dict] | None = None, tool_choice: ToolChoiceOptions | None = None, + structured_response_format: dict | None = None, ) -> BaseMessage: self._precall(prompt) # TODO add a postcall to log model outputs independent of concrete class # implementation - return self._invoke_implementation(prompt, tools, tool_choice) + return self._invoke_implementation( + prompt, tools, tool_choice, structured_response_format + ) @abc.abstractmethod def _invoke_implementation( @@ -100,6 +103,7 @@ def _invoke_implementation( prompt: LanguageModelInput, tools: list[dict] | None = None, tool_choice: ToolChoiceOptions | None = None, + structured_response_format: dict | None = None, ) -> BaseMessage: raise NotImplementedError @@ -108,11 +112,14 @@ def stream( prompt: LanguageModelInput, tools: list[dict] | None = None, tool_choice: ToolChoiceOptions | None = None, + structured_response_format: dict | None = None, ) -> Iterator[BaseMessage]: self._precall(prompt) # TODO add a postcall to log model outputs independent of concrete class # implementation - return self._stream_implementation(prompt, tools, tool_choice) + return self._stream_implementation( + prompt, tools, tool_choice, structured_response_format + ) @abc.abstractmethod def _stream_implementation( @@ -120,5 +127,6 @@ def _stream_implementation( prompt: LanguageModelInput, tools: list[dict] | None = None, tool_choice: ToolChoiceOptions | None = None, + structured_response_format: dict | None = None, ) -> Iterator[BaseMessage]: raise NotImplementedError diff --git a/backend/danswer/main.py b/backend/danswer/main.py index fe563c7c695..a6a338b4c4c 100644 --- a/backend/danswer/main.py +++ b/backend/danswer/main.py @@ -269,7 +269,7 @@ def get_application() -> FastAPI: # Server logs this during auth setup verification step pass - elif AUTH_TYPE == AuthType.BASIC: + if AUTH_TYPE == AuthType.BASIC or AUTH_TYPE == AuthType.CLOUD: include_router_with_global_prefix_prepended( application, fastapi_users.get_auth_router(auth_backend), @@ -301,7 +301,7 @@ def get_application() -> FastAPI: tags=["users"], ) - elif AUTH_TYPE == AuthType.GOOGLE_OAUTH: + if AUTH_TYPE == AuthType.GOOGLE_OAUTH or AUTH_TYPE == AuthType.CLOUD: oauth_client = GoogleOAuth2(OAUTH_CLIENT_ID, OAUTH_CLIENT_SECRET) include_router_with_global_prefix_prepended( application, diff --git a/backend/danswer/redis/redis_pool.py b/backend/danswer/redis/redis_pool.py index fd08b9157bd..3f2ec03d77f 100644 --- a/backend/danswer/redis/redis_pool.py +++ b/backend/danswer/redis/redis_pool.py @@ -1,4 +1,7 @@ +import functools import threading +from collections.abc import Callable +from typing import Any from typing import Optional import redis @@ -14,6 +17,98 @@ from danswer.configs.app_configs import REDIS_SSL_CA_CERTS from danswer.configs.app_configs import REDIS_SSL_CERT_REQS from danswer.configs.constants import REDIS_SOCKET_KEEPALIVE_OPTIONS +from danswer.utils.logger import setup_logger + +logger = setup_logger() + + +class TenantRedis(redis.Redis): + def __init__(self, tenant_id: str, *args: Any, **kwargs: Any) -> None: + super().__init__(*args, **kwargs) + self.tenant_id: str = tenant_id + + def _prefixed(self, key: str | bytes | memoryview) -> str | bytes | memoryview: + prefix: str = f"{self.tenant_id}:" + if isinstance(key, str): + if key.startswith(prefix): + return key + else: + return prefix + key + elif isinstance(key, bytes): + prefix_bytes = prefix.encode() + if key.startswith(prefix_bytes): + return key + else: + return prefix_bytes + key + elif isinstance(key, memoryview): + key_bytes = key.tobytes() + prefix_bytes = prefix.encode() + if key_bytes.startswith(prefix_bytes): + return key + else: + return memoryview(prefix_bytes + key_bytes) + else: + raise TypeError(f"Unsupported key type: {type(key)}") + + def _prefix_method(self, method: Callable) -> Callable: + @functools.wraps(method) + def wrapper(*args: Any, **kwargs: Any) -> Any: + if "name" in kwargs: + kwargs["name"] = self._prefixed(kwargs["name"]) + elif len(args) > 0: + args = (self._prefixed(args[0]),) + args[1:] + return method(*args, **kwargs) + + return wrapper + + def _prefix_scan_iter(self, method: Callable) -> Callable: + @functools.wraps(method) + def wrapper(*args: Any, **kwargs: Any) -> Any: + # Prefix the match pattern if provided + if "match" in kwargs: + kwargs["match"] = self._prefixed(kwargs["match"]) + elif len(args) > 0: + args = (self._prefixed(args[0]),) + args[1:] + + # Get the iterator + iterator = method(*args, **kwargs) + + # Remove prefix from returned keys + prefix = f"{self.tenant_id}:".encode() + prefix_len = len(prefix) + + for key in iterator: + if isinstance(key, bytes) and key.startswith(prefix): + yield key[prefix_len:] + else: + yield key + + return wrapper + + def __getattribute__(self, item: str) -> Any: + original_attr = super().__getattribute__(item) + methods_to_wrap = [ + "lock", + "unlock", + "get", + "set", + "delete", + "exists", + "incrby", + "hset", + "hget", + "getset", + "owned", + "reacquire", + "create_lock", + "startswith", + ] # Regular methods that need simple prefixing + + if item == "scan_iter": + return self._prefix_scan_iter(original_attr) + elif item in methods_to_wrap and callable(original_attr): + return self._prefix_method(original_attr) + return original_attr class RedisPool: @@ -32,8 +127,10 @@ def __new__(cls) -> "RedisPool": def _init_pool(self) -> None: self._pool = RedisPool.create_pool(ssl=REDIS_SSL) - def get_client(self) -> Redis: - return redis.Redis(connection_pool=self._pool) + def get_client(self, tenant_id: str | None) -> Redis: + if tenant_id is None: + tenant_id = "public" + return TenantRedis(tenant_id, connection_pool=self._pool) @staticmethod def create_pool( @@ -84,8 +181,8 @@ def create_pool( redis_pool = RedisPool() -def get_redis_client() -> Redis: - return redis_pool.get_client() +def get_redis_client(*, tenant_id: str | None) -> Redis: + return redis_pool.get_client(tenant_id) # # Usage example diff --git a/backend/danswer/search/preprocessing/preprocessing.py b/backend/danswer/search/preprocessing/preprocessing.py index aa3124617e5..10832ae7cbf 100644 --- a/backend/danswer/search/preprocessing/preprocessing.py +++ b/backend/danswer/search/preprocessing/preprocessing.py @@ -10,7 +10,7 @@ from danswer.configs.chat_configs import HYBRID_ALPHA_KEYWORD from danswer.configs.chat_configs import NUM_POSTPROCESSED_RESULTS from danswer.configs.chat_configs import NUM_RETURNED_HITS -from danswer.db.engine import current_tenant_id +from danswer.db.engine import CURRENT_TENANT_ID_CONTEXTVAR from danswer.db.models import User from danswer.db.search_settings import get_current_search_settings from danswer.llm.interfaces import LLM @@ -162,7 +162,7 @@ def retrieval_preprocessing( time_cutoff=time_filter or predicted_time_cutoff, tags=preset_filters.tags, # Tags are never auto-extracted access_control_list=user_acl_filters, - tenant_id=current_tenant_id.get() if MULTI_TENANT else None, + tenant_id=CURRENT_TENANT_ID_CONTEXTVAR.get() if MULTI_TENANT else None, ) llm_evaluation_type = LLMEvaluationType.BASIC diff --git a/backend/danswer/seeding/__init__.py b/backend/danswer/seeding/__init__.py new file mode 100644 index 00000000000..e69de29bb2d diff --git a/backend/danswer/seeding/initial_docs.json b/backend/danswer/seeding/initial_docs.json new file mode 100644 index 00000000000..cded36721b3 --- /dev/null +++ b/backend/danswer/seeding/initial_docs.json @@ -0,0 +1,10824 @@ +[ + { + "url": "https://docs.danswer.dev/more/use_cases/overview", + "title": "Use Cases Overview", + "content": "How to leverage Danswer in your organization\n\nDanswer Overview\nDanswer is the AI Assistant connected to your organization's docs, apps, and people. Danswer makes Generative AI more versatile for work by enabling new types of questions like \"What is the most common feature request we've heard from customers this month\". Whereas other AI systems have no context of your team and are generally unhelpful with work related questions, Danswer makes it possible to ask these questions in natural language and get back answers in seconds.\n\nDanswer can connect to +30 different tools and the use cases are not limited to the ones in the following pages. The highlighted use cases are for inspiration and come from feedback gathered from our users and customers.\n\n\nCommon Getting Started Questions:\n\nWhy are these docs connected in my Danswer deployment?\nAnswer: This is just an example of how connectors work in Danswer. You can connect up your own team's knowledge and you will be able to ask questions unique to your organization. Danswer will keep all of the knowledge up to date and in sync with your connected applications.\n\nIs my data being sent anywhere when I connect it up to Danswer?\nAnswer: No! Danswer is built with data security as our highest priority. We open sourced it so our users can know exactly what is going on with their data. By default all of the document processing happens within Danswer. The only time it is sent outward is for the GenAI call to generate answers.\n\nWhere is the feature for auto sync-ing document level access permissions from all connected sources?\nAnswer: This falls under the Enterprise Edition set of Danswer features built on top of the MIT/community edition. If you are on Danswer Cloud, you have access to them by default. If you're running it yourself, reach out to the Danswer team to receive access.", + "title_embedding": [ + 0.013585364446043968, + 0.06531507521867752, + -0.0001728831703076139, + -0.003940831869840622, + 0.044078364968299866, + -0.006206007208675146, + -0.008377128280699253, + -0.0193742997944355, + -0.018904175609350204, + 0.00868070125579834, + -0.005770757794380188, + 0.018564216792583466, + 0.030414527282118797, + 0.0327068567276001, + -0.0336286760866642, + -0.0517829954624176, + 0.0029869426507502794, + -3.836356700048782e-05, + -0.006240167189389467, + 0.011168955825269222, + -0.04732134938240051, + -0.05257624015212059, + 0.017937077209353447, + -0.029843101277947426, + 0.03417196497321129, + 0.008637758903205395, + -0.016427641734480858, + 0.017053034156560898, + -0.02532368339598179, + -0.016002299264073372, + 0.04696495085954666, + 0.03518024459481239, + 0.02884317748248577, + -0.06098122522234917, + -0.024405447766184807, + -0.07693222165107727, + 0.026796545833349228, + -0.01345108263194561, + 0.030546706169843674, + 0.00011662459291983396, + 0.0362892709672451, + 0.020864704623818398, + -0.0030571012757718563, + -0.014566082507371902, + 0.056138113141059875, + -0.01727251335978508, + 0.05477291718125343, + 0.019774138927459717, + 0.01646329089999199, + -0.020768629387021065, + -0.025477997958660126, + 0.010012250393629074, + 0.0037975965533405542, + -0.076152004301548, + 0.032632406800985336, + -0.00799622479826212, + 0.029365766793489456, + 0.02749769017100334, + 0.030807621777057648, + -0.031911835074424744, + 0.029850834980607033, + 0.05788583680987358, + -0.07022606581449509, + 0.057270754128694534, + -0.012120618484914303, + -0.0351836234331131, + 0.002640453167259693, + 0.01869964227080345, + 0.010610891506075859, + -0.06439802795648575, + 0.06629050523042679, + 0.00746738538146019, + 0.01690092496573925, + -0.025001635774970055, + -0.04047262296080589, + -0.04058482125401497, + 0.01863245666027069, + -0.021404679864645004, + -0.006766777019947767, + 0.05071299150586128, + 0.02962121181190014, + -0.06122489646077156, + 0.019276190549135208, + -0.03599821403622627, + 0.07253828644752502, + -0.001938252942636609, + -0.00785142183303833, + -0.015793368220329285, + -0.06096868962049484, + -0.022668933495879173, + 0.014094856567680836, + 0.03107546642422676, + 0.030937792733311653, + 0.04295564815402031, + -0.06191089749336243, + 0.010305442847311497, + 0.006790813058614731, + -0.05027518793940544, + 0.026334501802921295, + -0.03490821272134781, + -0.03132909536361694, + 0.00332127814181149, + 0.03326006978750229, + 0.05009974539279938, + 0.05102463811635971, + 0.080863356590271, + 0.008220085874199867, + 0.015490916557610035, + -0.029478086158633232, + 0.004051747731864452, + -0.05233829841017723, + 0.032338161021471024, + 0.016430383548140526, + 0.033909399062395096, + -0.0069341897033154964, + -0.01092524453997612, + 0.08201614767313004, + -0.061916135251522064, + -0.0202189888805151, + 0.06966497749090195, + 0.01732165738940239, + 0.020277557894587517, + 0.005021766293793917, + 0.03159264847636223, + 0.027503052726387978, + -0.03912171721458435, + -0.03356969729065895, + 0.018767613917589188, + 0.02705945260822773, + -0.06412986665964127, + 0.01829575188457966, + 0.030256258323788643, + 0.0074773263186216354, + -0.059738945215940475, + 0.042067185044288635, + 0.05707620456814766, + -0.02195868454873562, + -0.018797017633914948, + 0.07043126970529556, + -0.007300470490008593, + 0.04988619685173035, + -0.01761087030172348, + 0.024358391761779785, + 0.00520830973982811, + 0.007853846065700054, + -0.040487151592969894, + 0.013271456584334373, + 0.01356235146522522, + -0.07054886221885681, + 0.046908896416425705, + 0.0032781255431473255, + 0.022826792672276497, + 0.016794828698039055, + -0.0015572791453450918, + -0.03220144659280777, + -0.05249498412013054, + -0.023642878979444504, + -0.0013240000698715448, + 0.020749850198626518, + -0.032788924872875214, + 0.01523237768560648, + 0.03563430905342102, + -0.011741658672690392, + 0.08171892166137695, + -0.04966546595096588, + -0.02209051325917244, + 0.005958004854619503, + 0.02892436273396015, + 0.03561494126915932, + 0.02638504095375538, + 0.041660238057374954, + -0.05757247656583786, + 0.027456382289528847, + -0.011119958013296127, + 0.05332427844405174, + 0.03419065102934837, + 0.09803897142410278, + -0.0104225380346179, + 0.06645305454730988, + 0.02061033807694912, + -0.0188175980001688, + -0.03409148380160332, + -0.010915222577750683, + 0.016926083713769913, + -0.01010509766638279, + -0.031197063624858856, + 0.064297154545784, + -0.047280170023441315, + -0.022006161510944366, + 0.04089798405766487, + 0.0013760487781837583, + 0.0012917317217215896, + -0.010142299346625805, + -0.05629380792379379, + -0.058489665389060974, + -0.06434599310159683, + 0.04390622675418854, + 0.03466123342514038, + -0.002495409222319722, + -0.01867988333106041, + -0.012142776511609554, + 0.025940915569663048, + -0.05517507344484329, + 0.026919366791844368, + -0.05310383439064026, + 0.0020175466779619455, + 0.0407392643392086, + -0.0055900681763887405, + 0.028038354590535164, + 0.10158932954072952, + 0.056325044482946396, + 0.016724230721592903, + 0.005659179296344519, + 0.04764577001333237, + -0.03514963388442993, + 0.03311126306653023, + -0.05855907127261162, + -0.007677929475903511, + -0.0368916280567646, + 0.02390834502875805, + 0.021506410092115402, + -0.022855432704091072, + 0.02669590339064598, + 0.03190927952528, + 0.026299884542822838, + 0.04545223340392113, + -0.04817903786897659, + 0.08401483297348022, + -0.0017600113060325384, + -0.0026402128860354424, + -0.06519021838903427, + -0.08366627246141434, + 0.025473223999142647, + -0.03265143185853958, + -0.026078224182128906, + -0.014162144623696804, + -0.024846363812685013, + 0.042588867247104645, + -0.00620845053344965, + 0.0341552197933197, + -0.005032224114984274, + 0.039284951984882355, + 0.02678983099758625, + -0.02592509239912033, + -0.0334317646920681, + -0.017748532816767693, + -0.03175748512148857, + -0.03699929639697075, + -0.0009614137816242874, + 0.029971860349178314, + 0.03400350362062454, + 0.03034038282930851, + 0.005932188127189875, + 0.05225752666592598, + -0.032566532492637634, + -0.04808121547102928, + -0.023166747763752937, + 0.02398361638188362, + -0.03062198869884014, + -0.046609822660684586, + 0.019089654088020325, + 0.0017758660251274705, + 0.015751969069242477, + -0.029143214225769043, + 0.0024112602695822716, + -0.02520643174648285, + 0.023578567430377007, + -0.023457514122128487, + 0.013982303440570831, + -0.016386305913329124, + -0.002706830855458975, + -0.016093457117676735, + -0.037887830287218094, + 0.06287679821252823, + 0.00989477802067995, + -0.026199528947472572, + 0.0037161086220294237, + -0.027242952957749367, + -0.03319230675697327, + -0.026061702519655228, + 0.015717124566435814, + -0.055130068212747574, + -0.02499731443822384, + -0.014253406785428524, + 0.046770382672548294, + 0.008143531158566475, + 0.005510109476745129, + -0.02712511457502842, + -0.03787349909543991, + 0.013756319880485535, + 0.00579818757250905, + 0.008403831161558628, + 0.029755474999547005, + -0.0032762265764176846, + 0.0044027529656887054, + 0.03601987659931183, + 0.0909135565161705, + -0.007387327961623669, + -0.005328672006726265, + -0.03983118385076523, + -0.045495130121707916, + 0.022088482975959778, + -0.04040846228599548, + -0.0028130451682955027, + 0.03781481459736824, + 0.03704448416829109, + 0.03319826349616051, + 0.0018484846223145723, + 0.0547247938811779, + 0.019755663350224495, + -0.07568438351154327, + 0.05122718587517738, + -0.02555399388074875, + 0.06782808154821396, + -0.0756291076540947, + 0.05646894872188568, + 0.06156547740101814, + -0.0010290262289345264, + 0.02769431658089161, + 0.003549074986949563, + 0.02812255173921585, + -0.016937678679823875, + 0.018674779683351517, + -0.037636883556842804, + -0.002664038445800543, + 0.023414231836795807, + 0.040655869990587234, + 0.027929119765758514, + 0.03510269895195961, + -0.012380925938487053, + 0.024845607578754425, + 0.027425218373537064, + -0.05437726899981499, + 0.015804018825292587, + 0.05077793449163437, + -0.0003959169262088835, + 0.016312288120388985, + -0.007089096121490002, + -0.018367605283856392, + 0.02974492497742176, + 0.08662278950214386, + -0.021586472168564796, + -0.01729869470000267, + -0.04846135899424553, + -0.03031736984848976, + 0.002749247709289193, + 0.02350122295320034, + -0.0211945790797472, + 0.03907554969191551, + -0.023193899542093277, + -0.017260679975152016, + -0.03159818798303604, + -0.03952740877866745, + 0.010126064531505108, + -0.04888703301548958, + 0.06297406554222107, + 0.03254289552569389, + 0.004272142890840769, + -0.03231256827712059, + -0.04512784630060196, + 0.0043722353875637054, + -0.02994321472942829, + 0.05848870426416397, + 0.003534652292728424, + 0.007630845997482538, + 0.017482444643974304, + 0.04071490466594696, + 0.008809284307062626, + -0.03566472604870796, + -0.029327288269996643, + -0.017241651192307472, + -0.012668757699429989, + 0.05879855155944824, + 0.05893324315547943, + 0.09900359064340591, + 0.028096094727516174, + -0.036374326795339584, + 0.06244330108165741, + -0.03114512376487255, + -0.028666621074080467, + 0.06343588978052139, + 0.025132114067673683, + -0.01625697687268257, + 0.019650116562843323, + -0.049646493047475815, + -0.03520796075463295, + 0.03757908195257187, + 0.002519423607736826, + 0.03556838259100914, + -0.017592694610357285, + 0.0010467531392350793, + -0.06738362461328506, + -0.025265797972679138, + 0.008135112002491951, + -0.01762012392282486, + -0.024728305637836456, + -0.03567385673522949, + 0.018016908317804337, + 0.06866948306560516, + 0.03130311518907547, + -0.0297296904027462, + -0.006176969967782497, + 0.04329727590084076, + 0.044129278510808945, + -0.020673662424087524, + 0.06023940071463585, + -0.004932863637804985, + -0.050380971282720566, + -0.034760732203722, + 0.00199303706176579, + 0.05686243996024132, + -0.0148441381752491, + -0.012425840832293034, + -0.011634211987257004, + 0.022722775116562843, + -0.008717222139239311, + 0.020749682560563087, + -0.0277851615101099, + 0.0007777228020131588, + 0.013342801481485367, + 0.03622204810380936, + -0.023042850196361542, + -0.026700101792812347, + -0.034892451018095016, + -0.028433026745915413, + 0.06670085340738297, + 0.013445812277495861, + 0.03833755850791931, + 0.01010140310972929, + -0.03759188950061798, + -0.05855119228363037, + 0.00781426765024662, + -0.04906706139445305, + 0.03342912718653679, + -0.05243462324142456, + 0.040698058903217316, + 0.06868159025907516, + 0.022752607241272926, + -0.005430352408438921, + -0.006812892388552427, + -0.04902511462569237, + -0.006551826372742653, + -0.03979682922363281, + -0.013956423848867416, + -0.06136368587613106, + 0.0740000531077385, + 0.05603933334350586, + 0.02190348319709301, + -0.043786339461803436, + -0.0392116904258728, + -0.01866808719933033, + 0.01707339473068714, + -0.026303859427571297, + -0.01817542500793934, + 0.03552285581827164, + 0.0276781152933836, + 0.05265122279524803, + -0.03358357027173042, + -0.020007848739624023, + 0.04865119233727455, + 0.02959197200834751, + -0.0032693049870431423, + 0.02495887503027916, + 0.03446371853351593, + -0.011217310093343258, + -0.09030335396528244, + 0.014422472566366196, + -0.008989378809928894, + -0.011282369494438171, + 0.049398381263017654, + -0.01687331311404705, + 0.025424139574170113, + 0.024985041469335556, + -0.009084195829927921, + 0.004050575662404299, + 0.0007717382395640016, + -0.03172731399536133, + -0.017505444586277008, + -0.014687484130263329, + 0.03803866356611252, + 0.016156280413269997, + -0.010017951019108295, + -0.026353944092988968, + 0.019050614908337593, + -0.03580506518483162, + 0.02924525737762451, + 0.02443450316786766, + -0.01770329475402832, + 0.04581848904490471, + -0.01908605918288231, + 0.012714254669845104, + 0.08363562822341919, + 0.037286512553691864, + -0.003420531051233411, + -0.06909038126468658, + -0.0591881163418293, + -0.007654525339603424, + 0.053144630044698715, + 0.03045589104294777, + -0.04600578546524048, + 0.026682959869503975, + -0.0019753179512917995, + -0.017073772847652435, + -0.012071357108652592, + 0.028171954676508904, + 0.00024773634504526854, + -0.03256797045469284, + -0.09742321819067001, + 0.040483273565769196, + -0.025031624361872673, + 0.03650636970996857, + 0.0011886897264048457, + 0.016929153352975845, + 0.054483890533447266, + 0.03752107173204422, + 0.019491281360387802, + 0.006253591738641262, + 0.02451430633664131, + -0.05976274237036705, + 0.060739971697330475, + -0.04400366172194481, + 0.028709039092063904, + -0.02141660451889038, + 0.08152823895215988, + -0.00450171809643507, + -0.03484562411904335, + -0.00046958858729340136, + -0.017397938296198845, + 0.07823023945093155, + -0.011110293678939342, + 0.004524719901382923, + 0.03619854897260666, + -0.02478216402232647, + -0.011563056148588657, + -0.012815544381737709, + -0.03503820300102234, + -0.04771020635962486, + -0.030619489029049873, + 0.0669066309928894, + 0.030025487765669823, + -0.011697783134877682, + -0.006708705797791481, + -0.0061534675769507885, + 0.0365905724465847, + -0.006860053166747093, + -0.07040797173976898, + -0.057646144181489944, + 0.04284966364502907, + -0.01533683855086565, + -0.06859996914863586, + 0.009425769560039043, + -9.838528785621747e-05, + 0.010796179063618183, + -0.06541100144386292, + 0.01059884112328291, + -0.028843343257904053, + 0.029019653797149658, + -0.005446962546557188, + -0.0120149040594697, + -0.0471968911588192, + 0.008648250252008438, + 0.021961573511362076, + -0.010606558993458748, + 0.0008718566386960447, + -0.014988702721893787, + -0.11522816866636276, + -0.023671753704547882, + -0.004968483000993729, + 0.0307041984051466, + -0.0020613274537026882, + -0.03271760419011116, + -0.04547363147139549, + -0.00812614057213068, + -0.013890305534005165, + 0.048099175095558167, + -0.015408700332045555, + 0.06658884882926941, + 0.012633614242076874, + -0.05337975174188614, + 0.0033035692758858204, + 0.03610198199748993, + -0.0405871607363224, + 0.008806376717984676, + -0.017653945833444595, + -0.05865860357880592, + 0.03825455904006958, + -0.00478429114446044, + -0.04127506911754608, + 0.01231306791305542, + 0.0008735111332498491, + 0.02923770435154438, + 0.005922738928347826, + -0.01829770766198635, + -0.00685579888522625, + -0.03903493285179138, + 0.009158597327768803, + -0.03491708263754845, + 0.04114120453596115, + -0.0014327293029055, + -0.019274454563856125, + 0.02704671025276184, + 0.01738886535167694, + -0.02327372133731842, + -0.03135831654071808, + -0.01305293757468462, + 0.04163745418190956, + 0.01710107922554016, + 0.06454417109489441, + 0.020267069339752197, + -0.08408207446336746, + -0.010505065321922302, + -0.0073319086804986, + 0.004039655905216932, + -0.01633611135184765, + -0.02889716438949108, + -0.0806351900100708, + -0.023603465408086777, + -0.06304290890693665, + 0.007231221999973059, + -0.038828227669000626, + 0.014790577813982964, + -0.03915632143616676, + 0.05616161227226257, + 0.00311578088440001, + -0.02434428222477436, + 0.006431886460632086, + -0.06326194852590561, + -0.0166602972894907, + 0.03630464896559715, + 0.01622965931892395, + 0.026233987882733345, + 0.06605540215969086, + -0.05635184794664383, + -0.08930846303701401, + -0.05207853391766548, + 0.027004040777683258, + -0.031913693994283676, + -0.009139630943536758, + -0.028410566970705986, + 0.06700566411018372, + 0.0423152893781662, + -0.010422738268971443, + -0.04085265100002289, + 0.029382970184087753, + 0.052883222699165344, + 0.02239867113530636, + -0.0012815282680094242, + 0.014223611913621426, + 0.02597920596599579, + -0.015063034370541573, + 0.0828455239534378, + 0.03366050869226456, + -0.022025907412171364, + -0.0019613192416727543, + -0.02539178729057312, + 0.0399317741394043, + -0.006493750028312206, + -0.0013236093800514936, + -0.02036309242248535, + -0.0065197269432246685, + -0.030695058405399323, + -0.03585388883948326, + -0.045742426067590714, + 0.015121972188353539, + 0.08081705123186111, + 0.007906812243163586, + 0.059827424585819244, + -0.04740464314818382, + -0.0743480697274208, + -0.025416050106287003, + -0.05693193897604942, + -0.001481675892136991, + -0.017177585512399673, + -0.03311903402209282, + 0.022755322977900505, + -0.003895542584359646, + 0.02692737802863121, + -0.0032731543760746717, + -0.0031116430182009935, + -0.030539495870471, + -0.006427450571209192, + -0.0015021534636616707, + 0.0017666849307715893, + -0.03059082292020321, + 0.0005832729511894286, + -0.05637278035283089, + 0.04087543487548828, + 0.00220437441021204, + 0.0021564762573689222, + -0.0314127579331398, + -0.025518659502267838, + -0.07314060628414154, + -0.014426291920244694, + -0.08714891970157623, + -0.02331671305000782, + 0.013582085259258747, + -0.0025384915061295033, + -0.01540769450366497, + -0.0110056446865201, + 0.04654880613088608, + 0.010653696954250336, + 0.0018328200094401836, + 0.007387213874608278, + 0.07984212785959244, + -0.02893732860684395, + -0.04140201583504677, + -0.07618758082389832, + -0.00793982483446598, + -0.0377434641122818, + 0.032935332506895065, + -0.013259266503155231, + 0.02015708014369011, + 0.09388656169176102, + 0.0017843206878751516, + 0.034253206104040146, + -0.017240997403860092, + 0.009084933437407017, + -0.048595622181892395, + -0.03737767040729523, + -0.04036621376872063, + -0.009442481212317944, + 0.01705838553607464, + -0.03709835931658745, + 0.004579882137477398, + -0.02558705396950245, + -0.010287507437169552, + -0.00969093106687069, + 0.012930587865412235, + -0.0026530276518315077, + -0.055302973836660385, + -0.0007084248936735094, + 0.0027114865370094776, + -0.022337302565574646, + 0.049817051738500595, + -0.015339787118136883, + -0.01575980708003044, + -0.0211472287774086, + -0.041779227554798126, + -0.00043109135003760457, + -0.002638365374878049, + 0.0003785403096117079, + 0.04666115716099739, + -0.031109463423490524, + 0.03951709344983101, + 0.007409846410155296, + 0.032062821090221405, + -0.019406728446483612, + -0.03020879067480564, + 0.06802312284708023, + 0.018488138914108276, + -0.053909264504909515, + -0.007893281057476997, + 0.02533031813800335, + 0.03132852911949158, + -0.053483180701732635, + 0.025661734864115715, + 0.002397680189460516, + 0.04062856733798981, + 0.02830035611987114, + -0.00479720626026392, + -0.008729430846869946, + -0.0034766148310154676, + 0.03173350542783737, + 0.0071125393733382225, + -0.03040342777967453, + -0.006032709032297134, + -0.06926627457141876, + -0.0381772480905056 + ], + "content_embedding": [ + -0.02845170348882675, + 0.020628532394766808, + 0.003312832210212946, + -0.029765071347355843, + 0.016959644854068756, + -0.004110109526664019, + 0.054954126477241516, + -0.03696386516094208, + -0.06003747880458832, + -0.016737867146730423, + -0.04143841937184334, + 0.010524315759539604, + 0.01846286654472351, + 0.012900668196380138, + -0.01821877434849739, + -0.022333195433020592, + 0.016231827437877655, + -0.00692401546984911, + -0.009705417789518833, + 0.0043431734666228294, + -0.01035444438457489, + -0.03510449081659317, + -0.01101984828710556, + -0.029713021591305733, + 0.08172306418418884, + -0.008759400807321072, + -0.040999725461006165, + 0.04106973484158516, + -0.05768377706408501, + -0.008512589149177074, + 0.05944962799549103, + -0.012553821317851543, + 0.013645646162331104, + -0.02660560794174671, + -0.057905036956071854, + -0.054687026888132095, + 0.003909541759639978, + -0.04956740885972977, + -0.042125821113586426, + 0.06187684088945389, + 0.06303229182958603, + -0.012631679885089397, + -0.004673871211707592, + -0.02207319252192974, + 0.052802763879299164, + 0.014762785285711288, + 0.04115021601319313, + -0.006632254458963871, + 0.03773806244134903, + -0.03468457981944084, + -0.014101233333349228, + 0.013350501656532288, + -0.024982236325740814, + -0.009867328219115734, + -0.007960042916238308, + 0.005127797368913889, + 0.002303300891071558, + -0.004433336202055216, + 0.03658096119761467, + -0.04504770040512085, + 0.027889715507626534, + 0.05441499873995781, + -0.04908447712659836, + 0.041611816734075546, + -0.00782090611755848, + -0.05460766702890396, + 0.0005653056432493031, + 0.0009949197992682457, + 0.013009139336645603, + 0.004702548962086439, + -0.0066951001062989235, + -0.009612455032765865, + 0.027976926416158676, + 0.013144126161932945, + -0.009398404508829117, + -0.009249510243535042, + 0.02228953316807747, + -0.05003415420651436, + -0.03484565392136574, + 0.039622433483600616, + 0.03127755597233772, + -0.07711455225944519, + 0.026068583130836487, + -0.03025561012327671, + 0.03434577211737633, + 0.02756066806614399, + -0.016127552837133408, + 0.0031622813548892736, + -0.011191527359187603, + 0.10279087722301483, + 0.07508235424757004, + 0.014161021448671818, + 0.04303860291838646, + 0.02421264722943306, + -0.060081642121076584, + 0.08023173362016678, + -0.016117870807647705, + -0.040795255452394485, + -0.006737033370882273, + -0.02539793588221073, + -0.005812298972159624, + 0.027351481840014458, + 0.02652551420032978, + 0.034308984875679016, + 0.07952407002449036, + 0.012120738625526428, + -0.002102786907926202, + 0.02581837773323059, + 0.0036945617757737637, + 0.03335866704583168, + -0.05533025786280632, + -0.029806576669216156, + 0.014511525630950928, + 0.028494026511907578, + -0.028353745117783546, + -0.0015628034016117454, + 0.0542825423181057, + -0.06842301040887833, + 0.013071774505078793, + 0.035904042422771454, + -0.060427047312259674, + -0.010712354443967342, + -0.010741145350039005, + 0.00589279318228364, + 0.03916572034358978, + 0.0011838098289445043, + -0.04358551278710365, + -0.02426866628229618, + -0.02629699930548668, + -0.016508616507053375, + 0.0038987575098872185, + 0.00010461249621585011, + -0.06473322957754135, + 0.027538873255252838, + 0.03787471354007721, + 0.024383891373872757, + -0.04171127453446388, + -0.03238093852996826, + 0.007360804360359907, + -0.014501902274787426, + 0.014242740347981453, + -0.0012311796890571713, + -0.013716178946197033, + -0.009915472939610481, + 0.026615049690008163, + -0.07398053258657455, + 0.0030485496390610933, + 0.025813661515712738, + -0.022065768018364906, + 0.0349227599799633, + 0.0045135351829230785, + -0.053763143718242645, + -0.013968654908239841, + 0.016600387170910835, + 0.029198968783020973, + -0.03825172409415245, + -0.03900526836514473, + 0.02822844497859478, + 0.052716661244630814, + -0.00427692336961627, + 0.029389938339591026, + 0.01127107534557581, + -0.02288925088942051, + 0.06506737321615219, + -0.011876849457621574, + -0.009232635609805584, + 0.059180255979299545, + 0.060491811484098434, + 0.04768436402082443, + 0.04782063513994217, + -0.007591789122670889, + -0.012142209336161613, + -0.00854392908513546, + -0.03645598515868187, + 0.02366817742586136, + 0.028424806892871857, + 0.03254731744527817, + -0.0650848001241684, + 0.05803924798965454, + -0.006124107167124748, + 0.007514724973589182, + -0.06995245814323425, + 0.03610721975564957, + -0.025534681975841522, + -0.047099191695451736, + 0.0024543125182390213, + 0.013705895282328129, + -0.08660408854484558, + 0.013458521105349064, + -0.05938595533370972, + 0.025314588099718094, + -0.06279927492141724, + -0.008528811857104301, + -0.04051665961742401, + -0.02572588622570038, + -0.05028638243675232, + 0.029650729149580002, + 0.03656933456659317, + 0.027842504903674126, + -0.017784448340535164, + -0.06566111743450165, + -0.016097936779260635, + -0.07754653692245483, + 0.02611452341079712, + -0.012319186702370644, + 0.03830364719033241, + 0.05927351489663124, + -0.0005797847989015281, + 0.05858585610985756, + 0.013468705117702484, + 0.08553440123796463, + 0.010187739506363869, + -0.023877883329987526, + 0.027608737349510193, + -0.04135579988360405, + -0.004526825156062841, + 0.01695535145699978, + -0.043227668851614, + -0.03456792235374451, + 0.06477289646863937, + 0.031624119728803635, + -0.04087601602077484, + 0.0010430653346702456, + 0.017958510667085648, + 0.009248117916285992, + 0.010219916701316833, + -0.05485055223107338, + -0.01347501389682293, + -0.015884561464190483, + -0.008806952275335789, + -0.04478437826037407, + -0.09141774475574493, + 0.07184188067913055, + 0.02080371417105198, + 0.03414024040102959, + 0.02681431546807289, + -0.02171824313700199, + 0.023230157792568207, + 0.0034705817233771086, + 0.023832201957702637, + 0.04260754957795143, + -0.023710861802101135, + 0.017519451677799225, + -0.023114347830414772, + -0.07241662591695786, + 0.043135177344083786, + -0.03519831597805023, + 0.01728164590895176, + -0.007306656800210476, + 0.029966725036501884, + 0.005133960861712694, + 0.010730396956205368, + 0.014178331010043621, + 0.02290872484445572, + 0.04147600382566452, + -0.0711970180273056, + 0.011968120001256466, + 0.012014097534120083, + -0.00941413827240467, + -0.048221614211797714, + 0.02721494808793068, + -0.036967791616916656, + 0.03305060788989067, + -0.023104682564735413, + -0.0021078407298773527, + 0.01056760549545288, + 0.003825176041573286, + -0.02744617499411106, + -0.011484067887067795, + -0.019249368458986282, + 0.012087506242096424, + 0.016815317794680595, + 0.008888418786227703, + 0.09483875334262848, + 0.005403030198067427, + -0.006538084242492914, + -0.00812787376344204, + 0.010251098312437534, + 0.025141935795545578, + -0.016502706333994865, + -0.07583127170801163, + -0.059361476451158524, + -0.03975491225719452, + 0.005571363028138876, + 0.025980276986956596, + 0.06575164198875427, + -0.022391004487872124, + -0.0014668750809505582, + 0.0309857539832592, + -0.01333113107830286, + 0.024967554956674576, + 0.008801382035017014, + 0.004801678936928511, + 0.011097696609795094, + -0.02484068274497986, + 0.07475821673870087, + 0.06004296988248825, + 0.008063849061727524, + -0.007297527976334095, + -0.0225421991199255, + -0.020057078450918198, + 0.04824424162507057, + 0.019114485010504723, + -0.024972988292574883, + -0.013590608723461628, + -0.026848217472434044, + 0.013158710673451424, + 0.03205424174666405, + 0.06152794137597084, + 0.06059333309531212, + -0.03528637811541557, + 0.03574252501130104, + 0.011881774291396141, + -0.014821416698396206, + -0.03766554221510887, + 0.02960871160030365, + 0.043620847165584564, + -0.0008511713240295649, + -0.012452763505280018, + -0.008131926879286766, + 0.02682739496231079, + -0.027776895090937614, + -0.017724614590406418, + -0.074460469186306, + 0.007388352416455746, + 0.052085623145103455, + 0.005944994743913412, + 0.05980602651834488, + 0.004958854056894779, + 0.004315464291721582, + 0.009470906108617783, + 0.08363069593906403, + -0.06266297399997711, + -0.02252691425383091, + -0.0047216094098985195, + 0.01363289449363947, + 0.00803599413484335, + 0.017915869131684303, + 0.01683986745774746, + 0.0054694474674761295, + 0.00690553430467844, + -0.033289551734924316, + -0.041059620678424835, + -0.05957230553030968, + -0.07026804983615875, + 0.0026692922692745924, + 0.01784949004650116, + -0.0003522790502756834, + 0.044131647795438766, + 0.05823194235563278, + -0.01914701797068119, + 0.012501074001193047, + -0.0076722633093595505, + -0.040374498814344406, + 0.010002685710787773, + -0.006841403432190418, + 0.024179449304938316, + 0.01219668984413147, + -0.005650076549500227, + 0.010313056409358978, + 0.0951242670416832, + -0.012245064601302147, + 0.02261069230735302, + -0.02354615181684494, + 0.04120791703462601, + 0.03377315774559975, + 0.03468254953622818, + 0.033613745123147964, + 0.03305840864777565, + -0.033862534910440445, + 0.034367989748716354, + -0.022536078467965126, + 0.04874858632683754, + 0.0415329709649086, + 0.06666682660579681, + 0.0036932802759110928, + -0.09809356927871704, + -0.0017088145250454545, + 0.0024299651850014925, + -0.018637090921401978, + 0.06801039725542068, + 0.02409985661506653, + 0.009735392406582832, + -0.02749275043606758, + 0.030437270179390907, + -0.00898370798677206, + -0.020128484815359116, + -0.009687880054116249, + 0.01668565906584263, + -0.04497738555073738, + -0.019772959873080254, + -0.022632960230112076, + -0.02253716252744198, + 0.010271976701915264, + -0.00696501974016428, + 0.030849630013108253, + -0.04239751771092415, + 0.03944450616836548, + -0.013430316932499409, + 0.032022625207901, + -0.05952562019228935, + -0.043423160910606384, + -0.0024594010319560766, + -0.0009159342152997851, + -0.01097820233553648, + 0.02963317185640335, + -0.02188674546778202, + -0.048581305891275406, + 0.03341398760676384, + -0.011065436527132988, + 0.047042280435562134, + 0.04042183235287666, + -0.02600206807255745, + -0.05695529654622078, + 0.05499875172972679, + -0.03984459489583969, + 0.0649806335568428, + 0.02108422853052616, + -0.07841797918081284, + -0.02946053445339203, + -0.01747039519250393, + -0.013214156962931156, + 0.008581981062889099, + -0.0022455912549048662, + -0.022153383120894432, + 0.011744811199605465, + 0.017487658187747, + 0.008825760334730148, + 0.025580866262316704, + 0.0082536730915308, + 0.03269948437809944, + 0.012900054454803467, + 0.04077104851603508, + 0.0378829762339592, + -0.06819288432598114, + 0.02784581482410431, + 0.06434649229049683, + 0.03351795673370361, + 0.011211752891540527, + 0.01894824393093586, + 0.004370532464236021, + -0.014345336705446243, + 0.006097803357988596, + -0.08543102443218231, + -0.02757532149553299, + 0.06072119623422623, + 0.10378460586071014, + 0.009428516030311584, + -0.04370144382119179, + -0.01193047035485506, + 0.04444314166903496, + 0.011696353554725647, + -0.030421355739235878, + -0.014331959187984467, + 0.04900198057293892, + 0.027842359617352486, + -0.009193948470056057, + -0.06911113113164902, + -0.011863719671964645, + 0.035546496510505676, + 0.022603457793593407, + 0.017083479091525078, + 0.015593679621815681, + 0.021234845742583275, + 0.004202473908662796, + -0.0537634901702404, + 0.04333661124110222, + -0.025838447734713554, + -0.024251429364085197, + 0.03204401955008507, + -0.002707387087866664, + 0.03231189027428627, + -0.0030726506374776363, + 0.024067431688308716, + -0.03183548524975777, + 0.007890576496720314, + 0.054388418793678284, + -0.017090266570448875, + 0.01572081632912159, + 0.04539618268609047, + 0.01960766315460205, + 0.009962057694792747, + -0.06782109290361404, + 0.03449762612581253, + -0.004095849581062794, + 0.011451792903244495, + 0.01291556004434824, + 0.009039049968123436, + -0.023024702444672585, + -0.019358525052666664, + 0.004383507184684277, + 0.01303566712886095, + 0.008749599568545818, + -0.0019463954959064722, + -0.05059671401977539, + -0.03929319232702255, + -0.038611579686403275, + -0.0004830050456803292, + 0.03260226547718048, + -0.0484665147960186, + 0.04194365814328194, + 0.028087828308343887, + 0.0015577803133055568, + -0.0020338960457593203, + 0.00992380827665329, + 0.029156159609556198, + 0.013400931842625141, + -0.08322624862194061, + 0.03542347997426987, + 0.029148025438189507, + 0.03978026285767555, + 0.012040375731885433, + -0.015034311451017857, + 0.016610056161880493, + 0.030412640422582626, + -0.051336318254470825, + 0.057814277708530426, + -0.009117085486650467, + -0.055816203355789185, + 0.05705805867910385, + -0.013596060685813427, + 0.07485361397266388, + 0.04783453419804573, + 0.03237048164010048, + -0.1252431571483612, + -0.024511752650141716, + 0.009948192164301872, + -0.001071324571967125, + 0.03724309056997299, + 0.0011626302730292082, + -0.024294020608067513, + 0.09550263732671738, + 0.001125041046179831, + -0.032950934022665024, + 0.03814041614532471, + -0.015817970037460327, + -0.042719099670648575, + 0.02066672407090664, + 0.03320891037583351, + 0.04236403852701187, + 0.026531731709837914, + -0.026540761813521385, + 0.018515214323997498, + -0.0034993020817637444, + -0.019887158647179604, + -0.03968263417482376, + -0.048776015639305115, + 0.058169975876808167, + -0.033802736550569534, + -0.06506575644016266, + 0.06649087369441986, + -0.0008670967072248459, + 0.03118874505162239, + -0.04512554034590721, + 0.017889900133013725, + -0.0688585713505745, + -0.005668118130415678, + -0.04627913981676102, + -0.005911638960242271, + -0.004173378925770521, + 0.030776705592870712, + -0.003502912586554885, + 0.06485340744256973, + -0.002432354027405381, + 0.016381509602069855, + -0.11775369197130203, + -0.03817284479737282, + -0.0002618363650981337, + 0.020635321736335754, + -0.00496688112616539, + -0.025879040360450745, + -0.03508525341749191, + 0.03343107923865318, + 0.0065256268717348576, + 0.03733794391155243, + -0.05374712869524956, + 0.06329557299613953, + -0.012232488952577114, + -0.07295915484428406, + -0.03410065174102783, + -0.036963820457458496, + -0.040072306990623474, + 0.08864720910787582, + -0.025265397503972054, + 0.006373850163072348, + 0.03589979186654091, + -0.04953531548380852, + -0.014813058078289032, + 0.03135038912296295, + -0.045539740473032, + -0.013331865891814232, + -0.0077253468334674835, + 0.02402244322001934, + -0.01973932422697544, + -0.07107116281986237, + 0.029835300520062447, + 0.027613440528512, + 0.027596186846494675, + 0.0323333777487278, + -0.059915486723184586, + -0.03399650380015373, + -0.011191067285835743, + 0.04654889553785324, + 0.02089870348572731, + -0.02999742142856121, + 0.03440370410680771, + 0.007507022004574537, + 0.040571920573711395, + -0.03278252109885216, + -0.06050700321793556, + 0.021276405081152916, + -0.016155162826180458, + 0.00010897620086325333, + -0.0010203487472608685, + -0.03746471554040909, + -0.025609171018004417, + 0.005009123589843512, + -0.08643782883882523, + 0.031217029318213463, + -0.0032753287814557552, + -0.025097588077187538, + -0.03903978690505028, + 0.04100614786148071, + -0.015351627953350544, + -0.027274904772639275, + 0.03702486678957939, + -0.08083852380514145, + 0.005576241761445999, + -0.006957546342164278, + 0.09723483771085739, + 0.018242431804537773, + 0.05415903404355049, + -0.06101224571466446, + -0.025462020188570023, + -0.05338318645954132, + -0.014500913210213184, + 0.017682785168290138, + -0.017082780599594116, + 0.028426188975572586, + 0.039222750812768936, + 0.02545572631061077, + -0.03942421078681946, + -0.06022893264889717, + 0.04819706454873085, + 0.06749513745307922, + 0.01035595778375864, + 0.011470649391412735, + -0.0024080125149339437, + -0.033233992755413055, + 0.028164777904748917, + 0.0553852841258049, + 0.06263226270675659, + -0.016413886100053787, + 0.021145500242710114, + 0.01179521344602108, + 0.033495236188173294, + -0.013982322998344898, + 0.015615278854966164, + -0.04715987294912338, + 0.029921408742666245, + 0.00394752062857151, + -0.028457310050725937, + 0.018736237660050392, + -0.02897241711616516, + -0.006964333355426788, + 0.001459103194065392, + 0.020680002868175507, + -0.045486945658922195, + -0.0186879001557827, + 0.006018372252583504, + -0.005646763369441032, + 0.031949128955602646, + 0.015718143433332443, + -0.0680442824959755, + -0.040316201746463776, + 0.027103520929813385, + 0.007122257724404335, + -0.02554631046950817, + -0.015084164217114449, + -0.05808757618069649, + -0.01925673894584179, + -0.030870718881487846, + 0.04750153049826622, + -0.05464727431535721, + -0.03634507954120636, + -0.022956492379307747, + -0.001869303290732205, + 0.009947973303496838, + -0.0452248640358448, + -0.05064425989985466, + 0.0033088859636336565, + 0.032645225524902344, + 0.011128626763820648, + -0.07038814574480057, + -0.00398398470133543, + -0.029936205595731735, + -0.037302739918231964, + -0.026515178382396698, + -0.005808456335216761, + 0.011362303048372269, + 0.013931548222899437, + 0.053531426936388016, + -0.017702942714095116, + 0.04049023985862732, + 0.0490780733525753, + -0.0034894803538918495, + 0.0072046807035803795, + 0.05128946155309677, + -0.02248883992433548, + -0.016904350370168686, + -0.007111264392733574, + 0.013148962520062923, + 0.04168686643242836, + -0.011360356584191322, + -0.01462612859904766, + 0.036358367651700974, + -0.000562329194508493, + -0.037175074219703674, + 0.002623690525069833, + -0.04284300655126572, + 0.045784976333379745, + 0.017441436648368835, + -0.09851012378931046, + 0.06095545366406441, + -0.0374034121632576, + -0.02720695361495018, + -0.007703973911702633, + 0.03689894452691078, + 0.008105777204036713, + 0.019800135865807533, + -0.02071499079465866, + -0.022336198017001152, + -0.009109229780733585, + 0.02298821695148945, + -0.04302436485886574, + -0.023912018164992332, + 0.007846477441489697, + -0.04115860536694527, + -0.052512455731630325, + -0.0262643713504076, + 0.00893806479871273, + -0.032936349511146545, + -0.015261095948517323, + 0.005558508913964033, + -0.008528356440365314, + -0.023201653733849525, + -0.056550297886133194, + 0.025247847661376, + 0.04831540212035179, + -0.019267458468675613, + -0.03474835306406021, + -0.001712511875666678, + -0.04063638299703598, + -0.01707102544605732, + -0.01384702231734991, + -0.0023981977719813585, + 0.03153757378458977, + 0.030312344431877136, + 0.040820326656103134, + -0.013783353380858898, + 0.012157448567450047, + -0.015558870509266853, + -0.056085314601659775, + 0.03875841945409775, + 0.021351536735892296, + -0.021598603576421738, + -0.01058109663426876, + 0.001237297197803855 + ], + "chunk_ind": 0 + }, + { + "url": "https://docs.danswer.dev/more/use_cases/enterprise_search", + "title": "Enterprise Search", + "content": "Value of Enterprise Search with Danswer\n\nWhat is Enterprise Search and why is it Important?\nAn Enterprise Search system gives team members a single place to access all of the disparate knowledge of an organization. Critical information is saved across a host of channels like call transcripts with prospects, engineering design docs, IT runbooks, customer support email exchanges, project management tickets, and more. As fast moving teams scale up, information gets spread out and more disorganized.\n\nSince it quickly becomes infeasible to check across every source, decisions get made on incomplete information, employee satisfaction decreases, and the most valuable members of your team are tied up with constant distractions as junior teammates are unable to unblock themselves. Danswer solves this problem by letting anyone on the team access all of the knowledge across your organization in a permissioned and secure way. Users can ask questions in natural language and get back answers and documents across all of the connected sources instantly.\n\nWhat's the real cost?\nA typical knowledge worker spends over 2 hours a week on search, but more than that, the cost of incomplete or incorrect information can be extremely high. Customer support/success that isn't able to find the reference to similar cases could cause hours or even days of delay leading to lower customer satisfaction or in the worst case - churn. An account exec not realizing that a prospect had previously mentioned a specific need could lead to lost deals. An engineer not realizing a similar feature had previously been built could result in weeks of wasted development time and tech debt with duplicate implementation. With a lack of knowledge, your whole organization is navigating in the dark - inefficient and mistake prone.", + "title_embedding": [ + -0.011060578748583794, + 0.05994883179664612, + 0.008845113217830658, + 0.011364905163645744, + 0.03147757425904274, + 0.04506697878241539, + -0.025942707434296608, + -0.011002028360962868, + -0.03507396578788757, + -0.01727098599076271, + -0.016820134595036507, + 0.04671240597963333, + 0.023456331342458725, + -0.005752791650593281, + -0.011421029455959797, + -0.04169125109910965, + 0.0652366429567337, + -0.011136278510093689, + -0.013501451350748539, + -0.006273901090025902, + 0.0012236927868798375, + -0.030771249905228615, + 0.010098040103912354, + -0.02360220067203045, + 0.006734110414981842, + 0.001379420980811119, + -0.0047225081361830235, + -0.013901330530643463, + 0.014645840041339397, + -0.02156134508550167, + -0.026707857847213745, + -0.00676271365955472, + 0.056067030876874924, + -0.0455806590616703, + -0.02762053906917572, + -0.0965149849653244, + 0.04567359760403633, + 0.053895801305770874, + 0.029093541204929352, + 0.0199823547154665, + 0.047089505940675735, + 0.026028119027614594, + -0.0034626282285898924, + -0.021002190187573433, + 0.04217635095119476, + -0.015198000706732273, + 0.047393105924129486, + 0.008588545024394989, + 0.07058116048574448, + -0.09135723114013672, + -0.009591161273419857, + 0.014971816912293434, + -8.222273208957631e-07, + -0.05534408614039421, + -0.029965048655867577, + -0.028381407260894775, + 0.025547217577695847, + 0.038583844900131226, + 0.01984122209250927, + -0.02435469813644886, + 0.04955849424004555, + 0.0128632802516222, + -0.022573867812752724, + 0.025284791365265846, + 0.04496009647846222, + 0.0004200333496555686, + -0.0015001222491264343, + 0.02609623409807682, + 0.023677939549088478, + -0.05961468443274498, + 0.06799754500389099, + -0.014409428462386131, + -0.010374268516898155, + 0.019634529948234558, + -0.03720257058739662, + -0.04654879495501518, + 0.0056068566627800465, + -0.021244503557682037, + -0.03198164328932762, + 0.05707596614956856, + 0.043927326798439026, + -0.033356692641973495, + 0.015723733231425285, + -0.027493512257933617, + 0.04525380581617355, + 0.025808652862906456, + -0.007083983160555363, + -0.011038954369723797, + -0.004390218295156956, + -0.006583297159522772, + 0.003319315379485488, + 0.061810243874788284, + 0.05887124314904213, + 0.07722297310829163, + -0.06601747870445251, + 0.036486171185970306, + 0.05119618400931358, + 0.00945530366152525, + -0.03005358576774597, + -0.047870855778455734, + -0.0359003059566021, + -0.005699747242033482, + 0.053807053714990616, + -0.001554036163724959, + 0.060548700392246246, + 0.05476829782128334, + 0.00426551653072238, + -0.005215689539909363, + -0.0352163203060627, + -0.03284529969096184, + -0.03373449295759201, + 0.021254340186715126, + -0.010481598787009716, + 0.02651101164519787, + -0.00481840968132019, + 0.045160870999097824, + 0.09704204648733139, + -0.03473421558737755, + 0.015584945678710938, + 0.06579536944627762, + 0.0651017278432846, + 0.007380738854408264, + 0.00624364148825407, + 0.07893780618906021, + -0.019876087084412575, + 0.006619091611355543, + -0.030776498839259148, + -0.016426965594291687, + 0.014603338204324245, + -0.03326896205544472, + 0.003784433240070939, + 0.025205042213201523, + 0.03047170303761959, + -0.03364298865199089, + 0.005974944215267897, + 0.015994269400835037, + -0.10205432027578354, + -0.026497431099414825, + 0.07166463136672974, + -0.007370935752987862, + 0.034912627190351486, + -0.004656887147575617, + 0.03219066560268402, + -0.02239271067082882, + 0.012679396197199821, + -0.07867992669343948, + -0.026638884097337723, + -0.008346030488610268, + -0.027243634685873985, + 0.012043806724250317, + 0.024078860878944397, + 0.0006219774950295687, + 0.0032065671402961016, + -0.008564895950257778, + -0.03275461867451668, + -0.05791788548231125, + -0.044815272092819214, + 0.006680188700556755, + 0.04072298854589462, + 0.016144724562764168, + -0.0008583687013015151, + 0.03699830546975136, + -0.04675738513469696, + 0.06570404022932053, + -0.011776894330978394, + -0.011386243626475334, + -0.0003363603027537465, + 0.039485324174165726, + 0.014156803488731384, + 0.018139634281396866, + -0.014710970222949982, + -0.052651647478342056, + 0.02912742830812931, + 0.024101730436086655, + 0.0413704477250576, + 0.03631320223212242, + 0.046750932931900024, + -0.017062805593013763, + 0.017990263178944588, + -0.03954370319843292, + -0.006972718983888626, + -0.03784368559718132, + 0.02746269851922989, + 0.04107878357172012, + -0.005694024730473757, + -0.03896583244204521, + 0.026265999302268028, + -0.035318680107593536, + -0.018394622951745987, + 0.013594037853181362, + 0.0381510891020298, + -0.010223937220871449, + 0.032417282462120056, + 0.01610656827688217, + -0.013205642811954021, + -0.03757423907518387, + 0.03799910470843315, + -0.039449408650398254, + -0.011290505528450012, + -0.016824476420879364, + 0.007128347177058458, + 0.030213234946131706, + -0.09385695308446884, + 0.014417118392884731, + -0.021249795332551003, + -0.021371016278862953, + 0.031582340598106384, + -0.015021033585071564, + 0.03207740932703018, + 0.04465494304895401, + 0.051139406859874725, + -0.004539252258837223, + -0.004026447422802448, + 0.036198731511831284, + 0.002513982355594635, + -0.022555746138095856, + -0.023142442107200623, + 0.026506206020712852, + -0.0208470169454813, + 0.01958189532160759, + 0.02606782503426075, + -0.050900157541036606, + 0.001175468903966248, + 0.0026185859460383654, + 0.01644700951874256, + 0.047048378735780716, + -0.006155692040920258, + 0.013264120556414127, + -0.004277337808161974, + 0.022337032482028008, + -0.030710609629750252, + -0.06784506887197495, + 0.010662010870873928, + -0.020733945071697235, + -0.01206474844366312, + -0.0005046974983997643, + -0.004159707576036453, + 0.028128545731306076, + -0.011551725678145885, + 0.057953692972660065, + 0.028500419110059738, + 0.02070418931543827, + 0.029373178258538246, + -0.053878165781497955, + -0.03885475918650627, + -0.011427262797951698, + -0.040592946112155914, + 0.019192807376384735, + -0.013966009952127934, + 0.002324307570233941, + 0.027266129851341248, + 0.02721570059657097, + -0.013851913623511791, + 0.06292124837636948, + -0.019983768463134766, + -0.06498263776302338, + -0.014787066727876663, + 0.07545251399278641, + 0.009921795688569546, + -0.02266773208975792, + -0.0174646507948637, + -0.0037801002617925406, + 0.037214070558547974, + -0.033669255673885345, + -0.0033054312225431204, + -0.004362864885479212, + -0.010861773043870926, + -0.041649043560028076, + 0.02711806818842888, + -0.001099557732231915, + 0.0007163260015659034, + 0.01317980233579874, + -0.011158796027302742, + 0.03966476768255234, + 0.023275790736079216, + -0.011645027436316013, + 0.0030634249560534954, + -0.01243121363222599, + 0.01271719578653574, + 0.003938829991966486, + -0.00769989937543869, + -0.039121564477682114, + 0.0005735178128816187, + 0.02157283015549183, + 0.005828005261719227, + 0.03934130072593689, + 0.015216797590255737, + 0.017237801104784012, + -0.037648268043994904, + -0.007132838945835829, + -0.018956882879137993, + -0.0597093440592289, + 0.058341480791568756, + -0.0008284997311420739, + 0.02095271646976471, + 0.043099164962768555, + 0.09887702018022537, + -0.01221393421292305, + -0.02239784225821495, + 0.016775032505393028, + 0.013331425376236439, + -0.004451168701052666, + -0.02870352193713188, + -0.020854242146015167, + 0.05349724739789963, + 0.03315908834338188, + 0.018541062250733376, + -0.03136591613292694, + 0.03549784794449806, + -0.0076525891199707985, + -0.06454484909772873, + 0.049847088754177094, + 0.012184737250208855, + 0.03575005754828453, + -0.050804175436496735, + 0.09406977146863937, + 0.05103312432765961, + -0.0036910600028932095, + 0.10705005377531052, + 0.011394658125936985, + -0.014218435622751713, + -0.042272791266441345, + 0.018426422029733658, + -0.08213183283805847, + -0.010240674018859863, + 0.051353540271520615, + 0.016103247180581093, + 0.04293083772063255, + -0.00462630670517683, + 0.001971749123185873, + -0.05101824551820755, + -0.017815101891756058, + -0.0788436159491539, + -0.019784294068813324, + 0.006863154470920563, + 0.04096531495451927, + 0.016416994854807854, + 0.018884461373090744, + -0.03645262494683266, + -0.02363709919154644, + 0.08447448164224625, + 0.027652855962514877, + -0.005039512179791927, + -0.05533800646662712, + 0.006148343440145254, + -0.03248206898570061, + -0.015117023140192032, + -0.056908346712589264, + 0.057090409100055695, + 0.02987913228571415, + -0.0642392635345459, + -0.01212853193283081, + -0.04195745661854744, + -0.008033841848373413, + -0.05249612778425217, + 0.05965931713581085, + 0.08591161668300629, + -0.012983623892068863, + 0.002055486897006631, + -0.002928174799308181, + -0.023014886304736137, + -0.05307631567120552, + 0.0325687900185585, + -0.008586175739765167, + -0.005393583793193102, + 0.009566529653966427, + 0.06500132381916046, + -0.02100509963929653, + -0.018470296636223793, + 0.001247459789738059, + 0.007388024125248194, + 0.012469757348299026, + 0.08475572615861893, + 0.06918514519929886, + 0.054265547543764114, + 0.03292711451649666, + -0.08437038213014603, + 0.07744771242141724, + -0.0004291488730814308, + -0.020394261926412582, + 0.039096955209970474, + 0.015851527452468872, + -0.009922537952661514, + 0.02087295800447464, + -0.019477976486086845, + -0.06510577350854874, + 0.008559669367969036, + 0.015032066963613033, + -0.022979427129030228, + -0.017166415229439735, + -0.014456263743340969, + -0.034205030649900436, + -0.04903494939208031, + 0.073653943836689, + -0.041798241436481476, + 0.0035302129108458757, + 0.031043095514178276, + 0.038764648139476776, + 0.03582717105746269, + -0.003121789079159498, + 0.03909862041473389, + -0.03283870965242386, + 0.06343409419059753, + 0.085169717669487, + 0.0037416887935250998, + 0.043896209448575974, + -0.02215113304555416, + -0.04062772914767265, + -0.029482074081897736, + 0.0013964198296889663, + 0.04621904715895653, + 0.030072476714849472, + -0.023583346977829933, + -0.016047311946749687, + -0.04016166180372238, + -0.026690224185585976, + 0.034725841134786606, + -0.08011004328727722, + -0.023635270074009895, + -0.01675681211054325, + 0.02217511460185051, + -0.018720457330346107, + 0.0413116030395031, + -0.0045730252750217915, + -0.08402986079454422, + 0.03641941770911217, + 0.028000695630908012, + 0.042173273861408234, + 0.024761751294136047, + -0.051845893263816833, + -0.07877497375011444, + -0.020710380747914314, + -0.035789184272289276, + 0.04824375733733177, + -0.04493764415383339, + -0.0014088008319959044, + 0.09272980690002441, + -0.030772028490900993, + 0.027623610571026802, + -0.0008853759500198066, + -0.015347420237958431, + -0.0006863650633022189, + 0.02924676053225994, + 0.03864092007279396, + -0.043402496725320816, + 0.11410719156265259, + 0.01606914773583412, + 0.03158045932650566, + -0.049648500978946686, + -0.026801105588674545, + 0.013934214599430561, + -0.04582132399082184, + -0.02133217453956604, + 0.013296819292008877, + 0.030687933787703514, + 0.0014671665849164128, + 0.005454834550619125, + -0.024595070630311966, + 0.036868833005428314, + -0.003586424048990011, + -0.007300499361008406, + 0.00619609747081995, + 0.004614396020770073, + 0.06406176835298538, + 0.010256785899400711, + -0.050202082842588425, + -0.013155301101505756, + -0.04005127400159836, + -0.027943719178438187, + 0.05738724395632744, + -0.002920332597568631, + -0.00731270294636488, + 0.04419538751244545, + 0.024069754406809807, + 0.012176074087619781, + 0.004615467507392168, + -0.04112132638692856, + -0.04844773933291435, + -0.012684458866715431, + 0.0071298484690487385, + -0.010914848186075687, + -0.03592529892921448, + -0.05016973987221718, + -0.011797907762229443, + -0.043843258172273636, + -0.03715396672487259, + 0.016528192907571793, + 0.024301515892148018, + 0.01335576456040144, + 0.021006477996706963, + -0.021391959860920906, + 0.05299517139792442, + 0.0070807491429150105, + -0.08096124231815338, + -0.07334060221910477, + -0.034530941396951675, + -0.04421507194638252, + 0.010524646379053593, + 0.009575314819812775, + -0.031711090356111526, + 0.023479584604501724, + -0.04212309420108795, + 0.016264619305729866, + 0.03907531499862671, + -0.0011187525233253837, + -0.03998023644089699, + -0.027464834973216057, + -0.07113838940858841, + -0.028915319591760635, + -0.01282753050327301, + -0.0033073138911277056, + 0.026715606451034546, + -0.002769897459074855, + 0.020033732056617737, + 0.014502385631203651, + -0.017903830856084824, + 0.06932531297206879, + 0.0432068407535553, + 0.01685408502817154, + 0.04834728315472603, + -0.009553197771310806, + 0.019799189642071724, + 0.01173039898276329, + 0.04158413037657738, + -0.018829666078090668, + -0.008410722948610783, + 0.008009687066078186, + 0.034592460840940475, + 0.07790639251470566, + -0.022050900384783745, + 0.04081638529896736, + 0.046872470527887344, + 0.0010260086273774505, + -0.05322079360485077, + 0.009096509777009487, + -0.06831686198711395, + -0.01390997413545847, + -0.020475609228014946, + 0.017393099144101143, + -0.007532020565122366, + -0.06435851007699966, + -0.014785194769501686, + 0.02654031664133072, + 0.004753720946609974, + 0.026440177112817764, + -0.028890414163470268, + -0.011440729722380638, + 0.003554105758666992, + -0.0022926912643015385, + -0.02393224649131298, + 0.03711748123168945, + -0.06023703143000603, + -0.008778683841228485, + -0.05984162166714668, + -0.024247022345662117, + -0.036919932812452316, + 0.05249374359846115, + 0.03022468276321888, + -0.011348876170814037, + 0.0008303995127789676, + 0.001597013440914452, + -0.015491127036511898, + -0.035073015838861465, + -0.024477796629071236, + -0.030328145250678062, + -0.09301470220088959, + -0.046440113335847855, + 0.036719027906656265, + -0.021899227052927017, + 0.04666316881775856, + -0.07481305301189423, + -0.04928148165345192, + -0.01480096485465765, + 0.0014140848070383072, + 0.016779841855168343, + -0.04318199306726456, + 0.011910341680049896, + -0.04019855335354805, + -0.027363713830709457, + 0.006433602888137102, + 0.023732252418994904, + -0.013081788085401058, + 0.02489032782614231, + 0.005415213759988546, + -0.058724161237478256, + 0.032487478107213974, + -0.014332194812595844, + -0.020952431485056877, + 0.055405858904123306, + -0.02239573374390602, + 0.016315918415784836, + 0.04710645601153374, + 0.006866136100143194, + -0.019589263945817947, + -0.046199049800634384, + 0.04977096989750862, + -0.03211359679698944, + 0.06759121268987656, + -0.007805021945387125, + 0.009877636097371578, + -0.003194598713889718, + -0.0014034705236554146, + 0.024012917652726173, + 0.0007609894964843988, + 0.04028927534818649, + 0.047299597412347794, + 0.04644732549786568, + 0.06253348290920258, + -0.03101237863302231, + -0.04797065258026123, + -0.02459110878407955, + -0.06663094460964203, + -0.012946722097694874, + -0.046321313828229904, + -0.03617801144719124, + -0.06608668714761734, + 0.01371682621538639, + -0.040183935314416885, + 0.027353622019290924, + -0.013125114142894745, + 0.020482128486037254, + -0.10186963528394699, + 0.03741387277841568, + -0.048566944897174835, + 0.0017904090927913785, + 0.0444694422185421, + -0.02355058304965496, + -0.04245513305068016, + 0.01599632203578949, + -0.00974870752543211, + -0.02246273122727871, + 0.011107604950666428, + -0.006354854442179203, + -0.08260829746723175, + -0.054969724267721176, + -0.038703542202711105, + -0.02590899169445038, + -0.012424441985785961, + 0.033952418714761734, + 0.032632969319820404, + 0.03585505858063698, + -0.027734532952308655, + -0.05185376852750778, + 0.005663866177201271, + 0.01415393128991127, + 0.007472912315279245, + -0.0325092077255249, + -0.0008526426972821355, + 0.05909401550889015, + -0.006496420595794916, + 0.06674317270517349, + 0.06033811718225479, + -0.04705937206745148, + 0.01221691444516182, + -0.005195186473429203, + 0.017006050795316696, + 0.015768419951200485, + -0.02346021682024002, + -0.04318040981888771, + -0.00965888798236847, + -0.012831253930926323, + -0.023086808621883392, + -0.043478451669216156, + 0.02215973101556301, + 0.01018955372273922, + -0.0029477940406650305, + -0.026364397257566452, + -0.04219489544630051, + -0.0690244510769844, + 0.0017003740649670362, + -0.03498053178191185, + -0.01891854591667652, + -0.020380523055791855, + -0.07183944433927536, + 0.01474913302809, + 0.012818068265914917, + 0.02298390306532383, + 0.006645163521170616, + -0.014497633092105389, + -0.05751577392220497, + -0.01127719134092331, + 0.014469895511865616, + 0.039319343864917755, + -0.002891098614782095, + 0.0038161359261721373, + -0.0176107045263052, + -0.02695712260901928, + 0.023520348593592644, + 0.053624920547008514, + -0.0472102165222168, + -0.021724319085478783, + -0.04204733297228813, + 0.004941252060234547, + -0.07744265347719193, + -0.028974706307053566, + -6.1493665270973e-05, + -0.020630594342947006, + -0.014794640243053436, + -0.045572925359010696, + 0.03233763575553894, + 0.00969443004578352, + 0.03665856271982193, + 0.027483846992254257, + 0.074271060526371, + -0.07454165071249008, + -0.034101732075214386, + -0.07216823101043701, + -0.001424514572136104, + -0.0025912360288202763, + -0.002444307319819927, + -0.012540637515485287, + 0.009027975611388683, + 0.06855443120002747, + -0.0013480151537805796, + 0.027303414419293404, + -0.019723499193787575, + 0.033644214272499084, + -0.04313155263662338, + -0.016152892261743546, + -0.020085612311959267, + 0.029526935890316963, + 0.0004591972683556378, + -0.013712934218347073, + 0.015895912423729897, + -0.046559300273656845, + -0.00015638815239071846, + 0.0015497541753575206, + -0.0015048328787088394, + 0.06692329794168472, + 0.0013934546150267124, + 0.008921030908823013, + -0.010347972624003887, + -0.039798807352781296, + 0.06892028450965881, + 0.021145053207874298, + 0.007431029342114925, + -0.05281573906540871, + 0.015844792127609253, + 0.014578046277165413, + -0.0020482230465859175, + 0.03509555384516716, + -0.021227506920695305, + -0.03619229048490524, + 0.004116897005587816, + 0.02835669554769993, + -0.0028248224407434464, + 0.00836214143782854, + -0.004688165616244078, + 0.04566347226500511, + -0.0352579727768898, + -0.007859165780246258, + -0.003958444111049175, + 0.023938892409205437, + 0.04262895882129669, + -0.02836589328944683, + 0.0456448458135128, + -0.062015753239393234, + 0.03518408164381981, + 0.06333593279123306, + -0.0155468275770545, + 0.013991734012961388, + 0.02207978442311287, + 0.0032898876816034317, + 0.05948015674948692, + 0.010670959949493408, + -0.00624996330589056, + -0.04401599243283272, + -0.0022705462761223316 + ], + "content_embedding": [ + -0.02403288148343563, + 0.08599621057510376, + -0.003520619124174118, + -0.002186001278460026, + -0.002845448674634099, + 0.005484029185026884, + 0.016410797834396362, + -0.02119613252580166, + -0.04811510443687439, + -0.013274849392473698, + -0.043441254645586014, + 0.009376521222293377, + 0.019551504403352737, + 0.0036566888447850943, + 0.004842979833483696, + -0.006052782759070396, + 0.025645455345511436, + -0.012315846979618073, + -0.027703408151865005, + 0.02152254432439804, + 0.011010917834937572, + -0.012258552014827728, + -0.01729186624288559, + -0.02833859808743, + 0.04027653858065605, + -0.009032614529132843, + -0.017036406323313713, + 0.003077560570091009, + -0.04315951466560364, + 0.029963837936520576, + 0.01716647669672966, + -0.02696092799305916, + -0.006828296463936567, + -0.026644738391041756, + -0.0889354720711708, + -0.05207673832774162, + 0.05015599727630615, + -0.019386274740099907, + -0.03684607893228531, + 0.046758152544498444, + 0.05076799914240837, + 0.007221075240522623, + 0.016260067000985146, + -0.03850802034139633, + 0.054756514728069305, + -0.012776038609445095, + 0.036689598113298416, + -0.02616005390882492, + 0.033269986510276794, + -0.05991198495030403, + -0.00043452056706883013, + -0.004230191465467215, + -0.008319171145558357, + 0.0068639665842056274, + -0.016133679077029228, + 0.005670355167239904, + -0.005839305464178324, + 0.027315128594636917, + 0.04275438189506531, + -0.05024448782205582, + 0.05199997127056122, + 0.05441230162978172, + -0.049353599548339844, + -0.008365850895643234, + 0.0066192797385156155, + -0.055218830704689026, + 0.01654958724975586, + 0.013456150889396667, + -0.01148252934217453, + -0.014086110517382622, + 0.024422504007816315, + -0.001102397684007883, + -0.022180721163749695, + 0.022023402154445648, + -0.03140854462981224, + 0.0038229606579989195, + 0.01081792451441288, + -0.006220541428774595, + -0.02462770976126194, + 0.051595576107501984, + 0.04433179274201393, + -0.05173564329743385, + 0.00422016903758049, + 0.01004322525113821, + 0.01985878124833107, + 0.028202056884765625, + -0.0016253730282187462, + 0.01617475040256977, + 0.010118816047906876, + 0.0603351853787899, + 0.0140571603551507, + 0.0029350141994655132, + 0.04240429773926735, + 0.06991686671972275, + -0.10119865089654922, + 0.08219177275896072, + 0.02891121245920658, + 0.00130809610709548, + -0.016763439401984215, + -0.00509023480117321, + -0.0035567383747547865, + 0.02000737562775612, + -0.002168829319998622, + 0.01889166608452797, + 0.04547121003270149, + 0.04019659012556076, + 0.024593960493803024, + 0.017190879210829735, + 0.007603269536048174, + 0.007314966060221195, + -0.06791973859071732, + -0.036731328815221786, + 0.007499238010495901, + 0.02694091759622097, + -0.02129160799086094, + 0.021507520228624344, + 0.09310256689786911, + -0.03434507176280022, + 0.006634920369833708, + 0.03453971818089485, + 0.0155464056879282, + 0.003056582296267152, + -0.004192651715129614, + 0.03274714946746826, + 0.04909229651093483, + 0.025430802255868912, + -0.01268640998750925, + -0.047261349856853485, + 0.0018452038057148457, + -0.0002589405339676887, + -0.07050265371799469, + 0.004126655403524637, + -0.07842830568552017, + 0.00013916153693571687, + 0.047662656754255295, + 0.01362426858395338, + -0.07088430225849152, + -0.026547620072960854, + 0.010091855190694332, + -0.015962867066264153, + 0.03528159111738205, + 0.011798265390098095, + 0.020107097923755646, + -0.013524978421628475, + 0.016901858150959015, + -0.08753035962581635, + -0.062227677553892136, + -0.028078285977244377, + -0.03297634422779083, + 0.008013743907213211, + 0.018041228875517845, + -0.022115394473075867, + 0.00595641927793622, + 0.019160043448209763, + 0.008510938845574856, + -0.0474565215408802, + -0.038813307881355286, + -0.016643475741147995, + 0.06800767034292221, + 0.041471801698207855, + 0.03696686029434204, + 0.03421548008918762, + -0.03440884128212929, + 0.06769654899835587, + -0.01683412306010723, + 0.028133966028690338, + 0.018801912665367126, + 0.015075244940817356, + 0.012032945640385151, + 0.03569433093070984, + -0.021484674885869026, + -0.01213730126619339, + 0.023888660594820976, + -0.03447817265987396, + 0.03329891338944435, + -0.007350335828959942, + 0.06528840214014053, + -0.03317185863852501, + 0.024836916476488113, + -0.061747901141643524, + -0.01068184245377779, + -0.021780723705887794, + 0.06678029894828796, + 0.03825325518846512, + -0.02603997103869915, + 0.0200904980301857, + 0.025599440559744835, + -0.05657019838690758, + 0.028341008350253105, + -0.0439138226211071, + 0.05886855348944664, + -0.049358345568180084, + 0.014541592448949814, + 0.005707047879695892, + 0.008378228172659874, + -0.030232897028326988, + 0.06261618435382843, + -0.013355602510273457, + -0.036993358284235, + -0.028917213901877403, + -0.0680958554148674, + -0.027451951056718826, + -0.07567653805017471, + 0.014718701131641865, + -0.009075576439499855, + 0.013478180393576622, + 0.03208685666322708, + 0.031021032482385635, + 0.016195151954889297, + 0.008199494332075119, + 0.08357387781143188, + -0.01200099941343069, + 0.022620532661676407, + 0.05445336923003197, + -0.018056273460388184, + -0.04719870164990425, + 0.04062207415699959, + 0.0009855915559455752, + -0.0462096631526947, + 0.05879806727170944, + 0.03913828358054161, + -0.05726383253931999, + 0.02152623049914837, + 0.002137464936822653, + 0.01444965973496437, + -0.019534891471266747, + -0.0375588983297348, + -0.03905639797449112, + -0.027474306523799896, + -0.001400938956066966, + -0.033295221626758575, + -0.06691068410873413, + 0.0620984211564064, + 0.020130982622504234, + 0.027853885665535927, + 0.028353361412882805, + 0.007000260055065155, + -0.015244328416883945, + 0.028457706794142723, + 0.05079026147723198, + 0.0265045203268528, + -0.008008715696632862, + 0.011166643351316452, + -0.02545643411576748, + -0.09122578054666519, + -0.000896137673407793, + 0.0055070980452001095, + 0.023860882967710495, + -0.056958671659231186, + 0.002000730484724045, + 0.000531299039721489, + 0.01964678056538105, + 0.02459172159433365, + 0.010496687144041061, + 0.032775767147541046, + -0.040455516427755356, + -0.01898832432925701, + 0.048115238547325134, + 0.008294769562780857, + -0.02248159423470497, + -0.0020450311712920666, + -0.02413240633904934, + 0.0423247255384922, + -0.02917350083589554, + -0.0197658222168684, + 0.009233975782990456, + -0.02438087947666645, + -0.057745061814785004, + 0.020396480336785316, + -0.028454614803195, + -0.007276479620486498, + -0.0060751899145543575, + 0.016126802191138268, + 0.07733260095119476, + 0.0055052717216312885, + -0.0241200253367424, + -0.009856182150542736, + -0.01288821641355753, + 0.021394196897745132, + -0.0027394252829253674, + -0.057746946811676025, + -0.055244673043489456, + -0.03518827632069588, + 0.020108383148908615, + -0.037429675459861755, + 0.06402620673179626, + 0.014570947736501694, + 0.0011715830769389868, + 0.04670550301671028, + -0.03730842098593712, + -0.002726265462115407, + -0.03393309563398361, + 0.03357642516493797, + 0.006151925306767225, + 0.027046309784054756, + 0.06079886853694916, + 0.08915705978870392, + -0.040912795811891556, + -0.009531376883387566, + -0.008656186051666737, + -0.010746185667812824, + 0.011325616389513016, + 0.00910742674022913, + -0.00870103295892477, + -0.02257593534886837, + -0.008474824018776417, + -0.01126043125987053, + -0.006183316465467215, + 0.03318650647997856, + -0.005288233514875174, + -0.031032271683216095, + 0.02630523219704628, + 0.02767125330865383, + -0.01024201512336731, + -0.02395681105554104, + 0.07798302173614502, + 0.06453987956047058, + -0.005852920934557915, + 0.08618523925542831, + -0.009387078694999218, + 0.007869970984756947, + -0.03182069584727287, + -0.022106602787971497, + -0.0868132933974266, + 0.028115050867199898, + 0.07332660257816315, + -0.0037628302816301584, + 0.03760993853211403, + -0.027132470160722733, + 0.030093027278780937, + -0.037918947637081146, + 0.039932165294885635, + -0.07345228642225266, + -0.046965666115283966, + -0.0013359235599637032, + 0.00791996717453003, + 0.03006441704928875, + 0.04222951829433441, + -0.0141807422041893, + -0.021912341937422752, + -0.0065930006094276905, + -0.0038735137786716223, + -0.038659993559122086, + -0.057126715779304504, + 0.006521300878375769, + -0.030727874487638474, + -0.022539950907230377, + -0.06316803395748138, + 0.06865260004997253, + 0.031939368695020676, + -0.055947039276361465, + 0.0066061182878911495, + -0.014607742428779602, + -0.02204318344593048, + -0.05172397196292877, + 0.02495967596769333, + 0.07759078592061996, + 0.0027070387732237577, + 0.008220532909035683, + 0.02342107705771923, + 0.03180982172489166, + -0.03099866956472397, + 0.03512701019644737, + -0.03168865293264389, + 0.012847676873207092, + 0.06514899432659149, + 0.08987598121166229, + 0.0024377063382416964, + 0.02394464798271656, + -0.041963983327150345, + -0.004438851028680801, + 0.015682004392147064, + 0.0410960391163826, + 0.05460710451006889, + 0.057952240109443665, + 0.020986247807741165, + -0.08822161704301834, + 0.01074486318975687, + 0.014192330650985241, + -0.025726256892085075, + 0.0719577744603157, + 0.0021957557182759047, + 0.022048326209187508, + -0.04020603001117706, + 0.0014428661670535803, + -0.0357256680727005, + -0.030243121087551117, + -0.0376482829451561, + -0.020463477820158005, + -0.022432789206504822, + -0.03096373938024044, + -0.01816924288868904, + -0.05358648672699928, + 0.07382772862911224, + -0.014173741452395916, + 0.0201816875487566, + 0.006632740143686533, + 0.0025384302716702223, + 0.04055432602763176, + 0.0069578299298882484, + -0.019879184663295746, + -0.059168167412281036, + 0.028969064354896545, + 0.05784929171204567, + -0.002147398190572858, + 0.043272342532873154, + -0.004542165901511908, + -0.0482858382165432, + -0.004174860659986734, + 0.020621255040168762, + 0.04293094202876091, + 0.0292718093842268, + -0.00980047881603241, + -0.021710650995373726, + -0.02639775723218918, + -0.019148416817188263, + 0.09012293070554733, + -0.045379895716905594, + -0.023026002570986748, + -0.030370570719242096, + 0.008383749052882195, + 0.014925302006304264, + -0.0011008139699697495, + 0.006763918325304985, + -0.025421440601348877, + -0.004525069613009691, + 0.03806034475564957, + 0.005547006148844957, + 0.05000557750463486, + -0.005488873925060034, + 0.021936720237135887, + 0.020678924396634102, + -0.004737663082778454, + 0.040749210864305496, + -0.0533074289560318, + 0.025417080149054527, + 0.08257681876420975, + -0.005508026573807001, + -0.009805315174162388, + 0.07595512270927429, + -0.0018210643902420998, + -0.029579052701592445, + 0.009883117862045765, + -0.015399829484522343, + -0.017134232446551323, + 0.03538937494158745, + 0.0827752947807312, + 0.012051745317876339, + -0.07159247249364853, + -0.02079680748283863, + 0.03473742678761482, + 0.018268825486302376, + 0.023407628759741783, + -0.036390434950590134, + 0.07932467013597488, + 0.004754354711622, + -0.012676632963120937, + -0.06851805001497269, + 0.02255256660282612, + 0.03780437260866165, + 0.04691546410322189, + 0.018480120226740837, + 0.0005508657777681947, + 0.05573705583810806, + -0.009221675805747509, + -0.06587770581245422, + 0.015470701269805431, + -0.012271493673324585, + -0.025784730911254883, + 0.022757982835173607, + -0.01213389914482832, + 0.017422374337911606, + 0.012241406366229057, + 0.04379018396139145, + 0.01124424859881401, + 0.002584748901426792, + 0.02793707512319088, + -0.04307323694229126, + 0.03207562863826752, + 0.05286982282996178, + 0.01086041983217001, + 0.009665313176810741, + -0.054988693445920944, + 0.01324005052447319, + -0.04261464625597, + -0.02707112766802311, + -0.002658748533576727, + 0.03499991446733475, + -0.005491453222930431, + 0.006562606431543827, + 0.018722862005233765, + 0.07151596993207932, + -0.003824777202680707, + -0.04148973524570465, + -0.06528852880001068, + -0.018773429095745087, + -0.023220594972372055, + 0.021337825804948807, + 0.003552130190655589, + -0.07254927605390549, + 0.030997687950730324, + 0.009675328619778156, + -0.007739027962088585, + -0.001004970632493496, + -0.0009698161156848073, + -0.03183043375611305, + -0.003764253342524171, + -0.06521959602832794, + 0.0077109793201088905, + 0.008421109057962894, + 0.02024395577609539, + 0.06566902250051498, + 0.011374534107744694, + 0.040655992925167084, + 0.0274888314306736, + -0.0748000368475914, + 0.06930309534072876, + 0.014980202540755272, + -0.03328235074877739, + 0.07670122385025024, + -0.013236696831882, + 0.09516690671443939, + 0.0004450292617548257, + 0.01539886835962534, + -0.11376772075891495, + -0.0004633136559277773, + -0.023844275623559952, + 0.023186970502138138, + 0.0542912632226944, + 0.006978484336286783, + 0.03704620897769928, + 0.0761408805847168, + 0.0018389171455055475, + -0.02292831614613533, + 0.035566531121730804, + -0.06125196814537048, + -0.01740599237382412, + -0.03189321979880333, + -0.023606419563293457, + 0.0002929234178736806, + -0.032161861658096313, + -0.02417462132871151, + 0.007371667306870222, + 0.01384897343814373, + 0.0011207011993974447, + -0.054523780941963196, + -0.03664090484380722, + 0.012376014143228531, + 0.005946264136582613, + -0.05214802548289299, + 0.06363234668970108, + -0.01850913278758526, + 0.03264418616890907, + -0.08298838883638382, + 0.028580913320183754, + -0.06874261051416397, + 0.04560680687427521, + -0.01221420057117939, + -0.015291322953999043, + 0.011163976043462753, + -0.01707146316766739, + -0.021233493462204933, + 0.0009499920415692031, + -0.011884773150086403, + 0.031535957008600235, + -0.07693900167942047, + -0.030928723514080048, + 0.02938068099319935, + 0.013103127479553223, + 0.009228850714862347, + -0.04399878904223442, + -0.038614701479673386, + 0.021263988688588142, + 0.0270336102694273, + -0.0022124540992081165, + -0.032499391585588455, + 0.029354240745306015, + -0.028516946360468864, + -0.03277367725968361, + -0.04755333065986633, + -0.03938357159495354, + -0.029368583112955093, + 0.06943269073963165, + 0.017946777865290642, + -0.01990826241672039, + 0.014896579086780548, + -0.06675421446561813, + -0.04962918534874916, + 0.10290152579545975, + -0.05442032590508461, + 0.0268304031342268, + 0.01750801131129265, + 0.0006768505554646254, + -0.007724875118583441, + -0.05064627528190613, + 0.03560181334614754, + 0.005476392339915037, + 0.008490868844091892, + -0.005553610157221556, + -0.04698188602924347, + -0.025146158412098885, + 0.0026807712856680155, + 0.0254969522356987, + 0.005350390914827585, + 0.004036207217723131, + 0.02843003161251545, + 0.008211316540837288, + 0.03748054802417755, + -0.05300099402666092, + -0.012365839444100857, + -0.0130928261205554, + -0.03939966484904289, + -0.026050617918372154, + -0.04415596276521683, + -0.03128521516919136, + -0.0388399139046669, + 0.05186399444937706, + -0.049164481461048126, + 0.043122462928295135, + -0.0315178819000721, + 0.012280933558940887, + -0.0792573019862175, + 0.05075725167989731, + -0.04304235801100731, + 0.018651138991117477, + 0.03076835162937641, + -0.060538437217473984, + -0.023055853322148323, + 0.01177286822348833, + 0.058492839336395264, + 0.025716299191117287, + 0.009599392302334309, + -0.012054546736180782, + -0.027742642909288406, + -0.05367058888077736, + -0.026801493018865585, + -0.014112668111920357, + -0.006383270025253296, + 1.2056754712830298e-05, + 0.039540693163871765, + 0.02213987335562706, + -0.08540242910385132, + -0.04058465361595154, + 0.008699232712388039, + 0.031218260526657104, + 0.0021884969901293516, + 0.011582552455365658, + 0.025049764662981033, + 0.04276714473962784, + 0.009781924076378345, + 0.05123818293213844, + 0.07441077381372452, + -0.029336893931031227, + 0.02714505046606064, + 0.041163086891174316, + -0.006217346992343664, + 0.025060802698135376, + 0.023126818239688873, + -0.07503696531057358, + -0.0020585027523338795, + 0.005981603171676397, + -0.027166299521923065, + -0.020568007603287697, + 0.005853605456650257, + -0.006091856863349676, + -0.033637579530477524, + -0.039759427309036255, + -0.06260950118303299, + -0.024897020310163498, + 0.02462431788444519, + 0.01859314925968647, + 0.010398009791970253, + -0.00020126033632550389, + -0.06035298481583595, + -0.019108809530735016, + 0.042335279285907745, + -0.03559218347072601, + -0.02529655024409294, + -0.02809930220246315, + -0.05607590824365616, + -0.026691321283578873, + -0.026792382821440697, + 0.04120280221104622, + -0.015540994703769684, + -0.005803580395877361, + 0.020203134045004845, + -0.05952906608581543, + -0.004206392448395491, + -0.011308858171105385, + -0.037488050758838654, + 0.007830106653273106, + -0.009608179330825806, + 0.00015318443183787167, + -0.0684049054980278, + 0.0018899703864008188, + -0.023107590153813362, + -0.015158215537667274, + -0.030714333057403564, + 0.025599345564842224, + 0.018543586134910583, + -0.0075812251307070255, + 0.04323196783661842, + -0.005424505099654198, + 0.06189188361167908, + -0.01650432124733925, + 0.0035911088343709707, + 0.01841658726334572, + 0.012203766033053398, + -0.015994010493159294, + -0.0018007376929745078, + 0.011197488754987717, + -0.01184547133743763, + 0.06119342893362045, + -0.04449119791388512, + -0.010956074111163616, + 0.015267443843185902, + 0.03397256135940552, + -0.022375188767910004, + -0.010562969371676445, + -0.030176721513271332, + 0.0649082288146019, + -0.026252834126353264, + -0.043264783918857574, + 0.020383840426802635, + -0.014332938008010387, + -0.019906938076019287, + 0.002487052930518985, + 0.016441592946648598, + 0.05937374755740166, + 0.029459767043590546, + -0.03393784165382385, + -0.016614725813269615, + -0.03633803129196167, + 0.04786395654082298, + -0.014543719589710236, + 0.0030611655674874783, + -0.03296193480491638, + 0.024570109322667122, + -0.08628548681735992, + -0.008082202635705471, + 0.05895440652966499, + -0.05567137897014618, + -0.05882163718342781, + -0.005672273691743612, + -0.022155780345201492, + -0.03165644034743309, + -0.04472680389881134, + 0.025338545441627502, + 0.053867027163505554, + -0.020717058330774307, + -0.019026240333914757, + -0.03037080727517605, + -0.005734192673116922, + -0.014109884388744831, + -0.005240253172814846, + 0.056925658136606216, + 0.006881027482450008, + 0.006321505177766085, + 0.025533199310302734, + 0.0066923401318490505, + 0.014867548830807209, + 0.01877731829881668, + -0.03573253005743027, + 0.05504361167550087, + 0.044875118881464005, + 0.008996511809527874, + -0.020861415192484856, + 0.0196152962744236 + ], + "chunk_ind": 0 + }, + { + "url": "https://docs.danswer.dev/more/use_cases/enterprise_search", + "title": "Enterprise Search", + "content": "More than Search\nWhen analyzing the entire corpus of knowledge within your company is as easy as asking a question in a search bar, your entire team can stay informed and up to date. Danswer also makes it trivial to identify where knowledge is well documented and where it is lacking. Team members who are centers of knowledge can begin to effectively document their expertise since it is no longer being thrown into a black hole. All of this allows the organization to achieve higher efficiency and drive business outcomes.\n\nWith Generative AI, the entire user experience has evolved as well. For example, instead of just finding similar cases for your customer support team to reference, Danswer breaks down the issue and explains it so that even the most junior members can understand it. This in turn lets them give the most holistic and technically accurate response possible to your customers. On the other end, even the super stars of your sales team will not be able to review 10 hours of transcripts before hopping on that critical call, but Danswer can easily parse through it in mere seconds and give crucial context to help your team close.", + "title_embedding": [ + -0.011060578748583794, + 0.05994883179664612, + 0.008845113217830658, + 0.011364905163645744, + 0.03147757425904274, + 0.04506697878241539, + -0.025942707434296608, + -0.011002028360962868, + -0.03507396578788757, + -0.01727098599076271, + -0.016820134595036507, + 0.04671240597963333, + 0.023456331342458725, + -0.005752791650593281, + -0.011421029455959797, + -0.04169125109910965, + 0.0652366429567337, + -0.011136278510093689, + -0.013501451350748539, + -0.006273901090025902, + 0.0012236927868798375, + -0.030771249905228615, + 0.010098040103912354, + -0.02360220067203045, + 0.006734110414981842, + 0.001379420980811119, + -0.0047225081361830235, + -0.013901330530643463, + 0.014645840041339397, + -0.02156134508550167, + -0.026707857847213745, + -0.00676271365955472, + 0.056067030876874924, + -0.0455806590616703, + -0.02762053906917572, + -0.0965149849653244, + 0.04567359760403633, + 0.053895801305770874, + 0.029093541204929352, + 0.0199823547154665, + 0.047089505940675735, + 0.026028119027614594, + -0.0034626282285898924, + -0.021002190187573433, + 0.04217635095119476, + -0.015198000706732273, + 0.047393105924129486, + 0.008588545024394989, + 0.07058116048574448, + -0.09135723114013672, + -0.009591161273419857, + 0.014971816912293434, + -8.222273208957631e-07, + -0.05534408614039421, + -0.029965048655867577, + -0.028381407260894775, + 0.025547217577695847, + 0.038583844900131226, + 0.01984122209250927, + -0.02435469813644886, + 0.04955849424004555, + 0.0128632802516222, + -0.022573867812752724, + 0.025284791365265846, + 0.04496009647846222, + 0.0004200333496555686, + -0.0015001222491264343, + 0.02609623409807682, + 0.023677939549088478, + -0.05961468443274498, + 0.06799754500389099, + -0.014409428462386131, + -0.010374268516898155, + 0.019634529948234558, + -0.03720257058739662, + -0.04654879495501518, + 0.0056068566627800465, + -0.021244503557682037, + -0.03198164328932762, + 0.05707596614956856, + 0.043927326798439026, + -0.033356692641973495, + 0.015723733231425285, + -0.027493512257933617, + 0.04525380581617355, + 0.025808652862906456, + -0.007083983160555363, + -0.011038954369723797, + -0.004390218295156956, + -0.006583297159522772, + 0.003319315379485488, + 0.061810243874788284, + 0.05887124314904213, + 0.07722297310829163, + -0.06601747870445251, + 0.036486171185970306, + 0.05119618400931358, + 0.00945530366152525, + -0.03005358576774597, + -0.047870855778455734, + -0.0359003059566021, + -0.005699747242033482, + 0.053807053714990616, + -0.001554036163724959, + 0.060548700392246246, + 0.05476829782128334, + 0.00426551653072238, + -0.005215689539909363, + -0.0352163203060627, + -0.03284529969096184, + -0.03373449295759201, + 0.021254340186715126, + -0.010481598787009716, + 0.02651101164519787, + -0.00481840968132019, + 0.045160870999097824, + 0.09704204648733139, + -0.03473421558737755, + 0.015584945678710938, + 0.06579536944627762, + 0.0651017278432846, + 0.007380738854408264, + 0.00624364148825407, + 0.07893780618906021, + -0.019876087084412575, + 0.006619091611355543, + -0.030776498839259148, + -0.016426965594291687, + 0.014603338204324245, + -0.03326896205544472, + 0.003784433240070939, + 0.025205042213201523, + 0.03047170303761959, + -0.03364298865199089, + 0.005974944215267897, + 0.015994269400835037, + -0.10205432027578354, + -0.026497431099414825, + 0.07166463136672974, + -0.007370935752987862, + 0.034912627190351486, + -0.004656887147575617, + 0.03219066560268402, + -0.02239271067082882, + 0.012679396197199821, + -0.07867992669343948, + -0.026638884097337723, + -0.008346030488610268, + -0.027243634685873985, + 0.012043806724250317, + 0.024078860878944397, + 0.0006219774950295687, + 0.0032065671402961016, + -0.008564895950257778, + -0.03275461867451668, + -0.05791788548231125, + -0.044815272092819214, + 0.006680188700556755, + 0.04072298854589462, + 0.016144724562764168, + -0.0008583687013015151, + 0.03699830546975136, + -0.04675738513469696, + 0.06570404022932053, + -0.011776894330978394, + -0.011386243626475334, + -0.0003363603027537465, + 0.039485324174165726, + 0.014156803488731384, + 0.018139634281396866, + -0.014710970222949982, + -0.052651647478342056, + 0.02912742830812931, + 0.024101730436086655, + 0.0413704477250576, + 0.03631320223212242, + 0.046750932931900024, + -0.017062805593013763, + 0.017990263178944588, + -0.03954370319843292, + -0.006972718983888626, + -0.03784368559718132, + 0.02746269851922989, + 0.04107878357172012, + -0.005694024730473757, + -0.03896583244204521, + 0.026265999302268028, + -0.035318680107593536, + -0.018394622951745987, + 0.013594037853181362, + 0.0381510891020298, + -0.010223937220871449, + 0.032417282462120056, + 0.01610656827688217, + -0.013205642811954021, + -0.03757423907518387, + 0.03799910470843315, + -0.039449408650398254, + -0.011290505528450012, + -0.016824476420879364, + 0.007128347177058458, + 0.030213234946131706, + -0.09385695308446884, + 0.014417118392884731, + -0.021249795332551003, + -0.021371016278862953, + 0.031582340598106384, + -0.015021033585071564, + 0.03207740932703018, + 0.04465494304895401, + 0.051139406859874725, + -0.004539252258837223, + -0.004026447422802448, + 0.036198731511831284, + 0.002513982355594635, + -0.022555746138095856, + -0.023142442107200623, + 0.026506206020712852, + -0.0208470169454813, + 0.01958189532160759, + 0.02606782503426075, + -0.050900157541036606, + 0.001175468903966248, + 0.0026185859460383654, + 0.01644700951874256, + 0.047048378735780716, + -0.006155692040920258, + 0.013264120556414127, + -0.004277337808161974, + 0.022337032482028008, + -0.030710609629750252, + -0.06784506887197495, + 0.010662010870873928, + -0.020733945071697235, + -0.01206474844366312, + -0.0005046974983997643, + -0.004159707576036453, + 0.028128545731306076, + -0.011551725678145885, + 0.057953692972660065, + 0.028500419110059738, + 0.02070418931543827, + 0.029373178258538246, + -0.053878165781497955, + -0.03885475918650627, + -0.011427262797951698, + -0.040592946112155914, + 0.019192807376384735, + -0.013966009952127934, + 0.002324307570233941, + 0.027266129851341248, + 0.02721570059657097, + -0.013851913623511791, + 0.06292124837636948, + -0.019983768463134766, + -0.06498263776302338, + -0.014787066727876663, + 0.07545251399278641, + 0.009921795688569546, + -0.02266773208975792, + -0.0174646507948637, + -0.0037801002617925406, + 0.037214070558547974, + -0.033669255673885345, + -0.0033054312225431204, + -0.004362864885479212, + -0.010861773043870926, + -0.041649043560028076, + 0.02711806818842888, + -0.001099557732231915, + 0.0007163260015659034, + 0.01317980233579874, + -0.011158796027302742, + 0.03966476768255234, + 0.023275790736079216, + -0.011645027436316013, + 0.0030634249560534954, + -0.01243121363222599, + 0.01271719578653574, + 0.003938829991966486, + -0.00769989937543869, + -0.039121564477682114, + 0.0005735178128816187, + 0.02157283015549183, + 0.005828005261719227, + 0.03934130072593689, + 0.015216797590255737, + 0.017237801104784012, + -0.037648268043994904, + -0.007132838945835829, + -0.018956882879137993, + -0.0597093440592289, + 0.058341480791568756, + -0.0008284997311420739, + 0.02095271646976471, + 0.043099164962768555, + 0.09887702018022537, + -0.01221393421292305, + -0.02239784225821495, + 0.016775032505393028, + 0.013331425376236439, + -0.004451168701052666, + -0.02870352193713188, + -0.020854242146015167, + 0.05349724739789963, + 0.03315908834338188, + 0.018541062250733376, + -0.03136591613292694, + 0.03549784794449806, + -0.0076525891199707985, + -0.06454484909772873, + 0.049847088754177094, + 0.012184737250208855, + 0.03575005754828453, + -0.050804175436496735, + 0.09406977146863937, + 0.05103312432765961, + -0.0036910600028932095, + 0.10705005377531052, + 0.011394658125936985, + -0.014218435622751713, + -0.042272791266441345, + 0.018426422029733658, + -0.08213183283805847, + -0.010240674018859863, + 0.051353540271520615, + 0.016103247180581093, + 0.04293083772063255, + -0.00462630670517683, + 0.001971749123185873, + -0.05101824551820755, + -0.017815101891756058, + -0.0788436159491539, + -0.019784294068813324, + 0.006863154470920563, + 0.04096531495451927, + 0.016416994854807854, + 0.018884461373090744, + -0.03645262494683266, + -0.02363709919154644, + 0.08447448164224625, + 0.027652855962514877, + -0.005039512179791927, + -0.05533800646662712, + 0.006148343440145254, + -0.03248206898570061, + -0.015117023140192032, + -0.056908346712589264, + 0.057090409100055695, + 0.02987913228571415, + -0.0642392635345459, + -0.01212853193283081, + -0.04195745661854744, + -0.008033841848373413, + -0.05249612778425217, + 0.05965931713581085, + 0.08591161668300629, + -0.012983623892068863, + 0.002055486897006631, + -0.002928174799308181, + -0.023014886304736137, + -0.05307631567120552, + 0.0325687900185585, + -0.008586175739765167, + -0.005393583793193102, + 0.009566529653966427, + 0.06500132381916046, + -0.02100509963929653, + -0.018470296636223793, + 0.001247459789738059, + 0.007388024125248194, + 0.012469757348299026, + 0.08475572615861893, + 0.06918514519929886, + 0.054265547543764114, + 0.03292711451649666, + -0.08437038213014603, + 0.07744771242141724, + -0.0004291488730814308, + -0.020394261926412582, + 0.039096955209970474, + 0.015851527452468872, + -0.009922537952661514, + 0.02087295800447464, + -0.019477976486086845, + -0.06510577350854874, + 0.008559669367969036, + 0.015032066963613033, + -0.022979427129030228, + -0.017166415229439735, + -0.014456263743340969, + -0.034205030649900436, + -0.04903494939208031, + 0.073653943836689, + -0.041798241436481476, + 0.0035302129108458757, + 0.031043095514178276, + 0.038764648139476776, + 0.03582717105746269, + -0.003121789079159498, + 0.03909862041473389, + -0.03283870965242386, + 0.06343409419059753, + 0.085169717669487, + 0.0037416887935250998, + 0.043896209448575974, + -0.02215113304555416, + -0.04062772914767265, + -0.029482074081897736, + 0.0013964198296889663, + 0.04621904715895653, + 0.030072476714849472, + -0.023583346977829933, + -0.016047311946749687, + -0.04016166180372238, + -0.026690224185585976, + 0.034725841134786606, + -0.08011004328727722, + -0.023635270074009895, + -0.01675681211054325, + 0.02217511460185051, + -0.018720457330346107, + 0.0413116030395031, + -0.0045730252750217915, + -0.08402986079454422, + 0.03641941770911217, + 0.028000695630908012, + 0.042173273861408234, + 0.024761751294136047, + -0.051845893263816833, + -0.07877497375011444, + -0.020710380747914314, + -0.035789184272289276, + 0.04824375733733177, + -0.04493764415383339, + -0.0014088008319959044, + 0.09272980690002441, + -0.030772028490900993, + 0.027623610571026802, + -0.0008853759500198066, + -0.015347420237958431, + -0.0006863650633022189, + 0.02924676053225994, + 0.03864092007279396, + -0.043402496725320816, + 0.11410719156265259, + 0.01606914773583412, + 0.03158045932650566, + -0.049648500978946686, + -0.026801105588674545, + 0.013934214599430561, + -0.04582132399082184, + -0.02133217453956604, + 0.013296819292008877, + 0.030687933787703514, + 0.0014671665849164128, + 0.005454834550619125, + -0.024595070630311966, + 0.036868833005428314, + -0.003586424048990011, + -0.007300499361008406, + 0.00619609747081995, + 0.004614396020770073, + 0.06406176835298538, + 0.010256785899400711, + -0.050202082842588425, + -0.013155301101505756, + -0.04005127400159836, + -0.027943719178438187, + 0.05738724395632744, + -0.002920332597568631, + -0.00731270294636488, + 0.04419538751244545, + 0.024069754406809807, + 0.012176074087619781, + 0.004615467507392168, + -0.04112132638692856, + -0.04844773933291435, + -0.012684458866715431, + 0.0071298484690487385, + -0.010914848186075687, + -0.03592529892921448, + -0.05016973987221718, + -0.011797907762229443, + -0.043843258172273636, + -0.03715396672487259, + 0.016528192907571793, + 0.024301515892148018, + 0.01335576456040144, + 0.021006477996706963, + -0.021391959860920906, + 0.05299517139792442, + 0.0070807491429150105, + -0.08096124231815338, + -0.07334060221910477, + -0.034530941396951675, + -0.04421507194638252, + 0.010524646379053593, + 0.009575314819812775, + -0.031711090356111526, + 0.023479584604501724, + -0.04212309420108795, + 0.016264619305729866, + 0.03907531499862671, + -0.0011187525233253837, + -0.03998023644089699, + -0.027464834973216057, + -0.07113838940858841, + -0.028915319591760635, + -0.01282753050327301, + -0.0033073138911277056, + 0.026715606451034546, + -0.002769897459074855, + 0.020033732056617737, + 0.014502385631203651, + -0.017903830856084824, + 0.06932531297206879, + 0.0432068407535553, + 0.01685408502817154, + 0.04834728315472603, + -0.009553197771310806, + 0.019799189642071724, + 0.01173039898276329, + 0.04158413037657738, + -0.018829666078090668, + -0.008410722948610783, + 0.008009687066078186, + 0.034592460840940475, + 0.07790639251470566, + -0.022050900384783745, + 0.04081638529896736, + 0.046872470527887344, + 0.0010260086273774505, + -0.05322079360485077, + 0.009096509777009487, + -0.06831686198711395, + -0.01390997413545847, + -0.020475609228014946, + 0.017393099144101143, + -0.007532020565122366, + -0.06435851007699966, + -0.014785194769501686, + 0.02654031664133072, + 0.004753720946609974, + 0.026440177112817764, + -0.028890414163470268, + -0.011440729722380638, + 0.003554105758666992, + -0.0022926912643015385, + -0.02393224649131298, + 0.03711748123168945, + -0.06023703143000603, + -0.008778683841228485, + -0.05984162166714668, + -0.024247022345662117, + -0.036919932812452316, + 0.05249374359846115, + 0.03022468276321888, + -0.011348876170814037, + 0.0008303995127789676, + 0.001597013440914452, + -0.015491127036511898, + -0.035073015838861465, + -0.024477796629071236, + -0.030328145250678062, + -0.09301470220088959, + -0.046440113335847855, + 0.036719027906656265, + -0.021899227052927017, + 0.04666316881775856, + -0.07481305301189423, + -0.04928148165345192, + -0.01480096485465765, + 0.0014140848070383072, + 0.016779841855168343, + -0.04318199306726456, + 0.011910341680049896, + -0.04019855335354805, + -0.027363713830709457, + 0.006433602888137102, + 0.023732252418994904, + -0.013081788085401058, + 0.02489032782614231, + 0.005415213759988546, + -0.058724161237478256, + 0.032487478107213974, + -0.014332194812595844, + -0.020952431485056877, + 0.055405858904123306, + -0.02239573374390602, + 0.016315918415784836, + 0.04710645601153374, + 0.006866136100143194, + -0.019589263945817947, + -0.046199049800634384, + 0.04977096989750862, + -0.03211359679698944, + 0.06759121268987656, + -0.007805021945387125, + 0.009877636097371578, + -0.003194598713889718, + -0.0014034705236554146, + 0.024012917652726173, + 0.0007609894964843988, + 0.04028927534818649, + 0.047299597412347794, + 0.04644732549786568, + 0.06253348290920258, + -0.03101237863302231, + -0.04797065258026123, + -0.02459110878407955, + -0.06663094460964203, + -0.012946722097694874, + -0.046321313828229904, + -0.03617801144719124, + -0.06608668714761734, + 0.01371682621538639, + -0.040183935314416885, + 0.027353622019290924, + -0.013125114142894745, + 0.020482128486037254, + -0.10186963528394699, + 0.03741387277841568, + -0.048566944897174835, + 0.0017904090927913785, + 0.0444694422185421, + -0.02355058304965496, + -0.04245513305068016, + 0.01599632203578949, + -0.00974870752543211, + -0.02246273122727871, + 0.011107604950666428, + -0.006354854442179203, + -0.08260829746723175, + -0.054969724267721176, + -0.038703542202711105, + -0.02590899169445038, + -0.012424441985785961, + 0.033952418714761734, + 0.032632969319820404, + 0.03585505858063698, + -0.027734532952308655, + -0.05185376852750778, + 0.005663866177201271, + 0.01415393128991127, + 0.007472912315279245, + -0.0325092077255249, + -0.0008526426972821355, + 0.05909401550889015, + -0.006496420595794916, + 0.06674317270517349, + 0.06033811718225479, + -0.04705937206745148, + 0.01221691444516182, + -0.005195186473429203, + 0.017006050795316696, + 0.015768419951200485, + -0.02346021682024002, + -0.04318040981888771, + -0.00965888798236847, + -0.012831253930926323, + -0.023086808621883392, + -0.043478451669216156, + 0.02215973101556301, + 0.01018955372273922, + -0.0029477940406650305, + -0.026364397257566452, + -0.04219489544630051, + -0.0690244510769844, + 0.0017003740649670362, + -0.03498053178191185, + -0.01891854591667652, + -0.020380523055791855, + -0.07183944433927536, + 0.01474913302809, + 0.012818068265914917, + 0.02298390306532383, + 0.006645163521170616, + -0.014497633092105389, + -0.05751577392220497, + -0.01127719134092331, + 0.014469895511865616, + 0.039319343864917755, + -0.002891098614782095, + 0.0038161359261721373, + -0.0176107045263052, + -0.02695712260901928, + 0.023520348593592644, + 0.053624920547008514, + -0.0472102165222168, + -0.021724319085478783, + -0.04204733297228813, + 0.004941252060234547, + -0.07744265347719193, + -0.028974706307053566, + -6.1493665270973e-05, + -0.020630594342947006, + -0.014794640243053436, + -0.045572925359010696, + 0.03233763575553894, + 0.00969443004578352, + 0.03665856271982193, + 0.027483846992254257, + 0.074271060526371, + -0.07454165071249008, + -0.034101732075214386, + -0.07216823101043701, + -0.001424514572136104, + -0.0025912360288202763, + -0.002444307319819927, + -0.012540637515485287, + 0.009027975611388683, + 0.06855443120002747, + -0.0013480151537805796, + 0.027303414419293404, + -0.019723499193787575, + 0.033644214272499084, + -0.04313155263662338, + -0.016152892261743546, + -0.020085612311959267, + 0.029526935890316963, + 0.0004591972683556378, + -0.013712934218347073, + 0.015895912423729897, + -0.046559300273656845, + -0.00015638815239071846, + 0.0015497541753575206, + -0.0015048328787088394, + 0.06692329794168472, + 0.0013934546150267124, + 0.008921030908823013, + -0.010347972624003887, + -0.039798807352781296, + 0.06892028450965881, + 0.021145053207874298, + 0.007431029342114925, + -0.05281573906540871, + 0.015844792127609253, + 0.014578046277165413, + -0.0020482230465859175, + 0.03509555384516716, + -0.021227506920695305, + -0.03619229048490524, + 0.004116897005587816, + 0.02835669554769993, + -0.0028248224407434464, + 0.00836214143782854, + -0.004688165616244078, + 0.04566347226500511, + -0.0352579727768898, + -0.007859165780246258, + -0.003958444111049175, + 0.023938892409205437, + 0.04262895882129669, + -0.02836589328944683, + 0.0456448458135128, + -0.062015753239393234, + 0.03518408164381981, + 0.06333593279123306, + -0.0155468275770545, + 0.013991734012961388, + 0.02207978442311287, + 0.0032898876816034317, + 0.05948015674948692, + 0.010670959949493408, + -0.00624996330589056, + -0.04401599243283272, + -0.0022705462761223316 + ], + "content_embedding": [ + -0.01892169564962387, + 0.0662541389465332, + 0.008976679295301437, + -0.03809165209531784, + 0.02344459854066372, + 0.012984057888388634, + 0.016158411279320717, + 0.0040777078829705715, + -0.0321662537753582, + -0.0026544055435806513, + -0.03179372847080231, + 0.019741656258702278, + 0.049423426389694214, + 0.019327590242028236, + 0.01367267221212387, + -0.042058881372213364, + 0.023155249655246735, + -0.015003002248704433, + 0.01056167297065258, + 0.0032619787380099297, + -0.014582481235265732, + -0.01262009609490633, + -0.009695992805063725, + -0.025683948770165443, + 0.010330218821763992, + -0.043577518314123154, + -0.03799012303352356, + 0.03159527853131294, + -0.046592168509960175, + 0.03461733087897301, + 0.029929379001259804, + -0.02696100063621998, + 0.01958872564136982, + -0.04882275313138962, + -0.04835181683301926, + -0.07444816827774048, + 0.0615590400993824, + -0.018079139292240143, + -0.02907492406666279, + 0.03256160393357277, + 0.052772294729948044, + 0.0014335751766338944, + 0.02048010565340519, + -0.01859121397137642, + 0.0436980240046978, + -0.028847631067037582, + 0.06271578371524811, + -0.04908007010817528, + 0.04021253436803818, + -0.07390867173671722, + 0.0029745057690888643, + -0.01733274944126606, + -0.005066753830760717, + -0.006927797570824623, + -0.01495048776268959, + 0.020951012149453163, + -0.02161789871752262, + 0.004997345618903637, + 0.02517000213265419, + -0.03955457732081413, + 0.038905348628759384, + 0.008108963258564472, + -0.04058837890625, + 0.03415047749876976, + -0.004129728768020868, + -0.07600218057632446, + -0.008998502045869827, + 0.012445643544197083, + -0.005613638553768396, + -0.015701062977313995, + 0.010493642650544643, + -0.01511659286916256, + -0.007434363476932049, + 0.04920893907546997, + -0.044436678290367126, + -0.015229232609272003, + -0.009392009116709232, + -0.004889432340860367, + -0.03250344097614288, + 0.05671893432736397, + 0.03468514233827591, + -0.04985000938177109, + 0.021073583513498306, + 0.005558345932513475, + 0.04397028684616089, + -0.011105467565357685, + -0.0010204907739534974, + -0.0013343892060220242, + 0.010888955555856228, + 0.11187340319156647, + 0.05144372954964638, + 0.014714346267282963, + 0.03652629256248474, + 0.08354610204696655, + -0.050587598234415054, + 0.07670528441667557, + 0.022823045030236244, + -0.010303523391485214, + -0.00016479991609230638, + -0.015029380097985268, + -0.010333288460969925, + 0.03660477325320244, + 0.013327172957360744, + -0.008142965845763683, + 0.04656663164496422, + 0.043171610683202744, + 0.027440473437309265, + 0.011585040017962456, + -0.008035292848944664, + -0.0008554590749554336, + -0.04715310037136078, + -0.013419345021247864, + -0.034535810351371765, + 0.028465399518609047, + -0.030552269890904427, + 0.02954002656042576, + 0.11263657361268997, + -0.060091886669397354, + -0.004718341864645481, + 0.02276463434100151, + -0.029855655506253242, + 1.136395258072298e-05, + 0.01254600752145052, + 0.030318304896354675, + 0.04609473794698715, + 0.04090471565723419, + -0.015202691778540611, + -0.025406358763575554, + 0.01403091847896576, + -0.01206378173083067, + -0.034794360399246216, + 0.021181223914027214, + -0.041345320641994476, + 0.026389217004179955, + 0.04634319990873337, + 0.05973498523235321, + -0.0791369080543518, + -0.018549518659710884, + 0.009269041940569878, + 0.005099988542497158, + 0.016017470508813858, + 0.016928445547819138, + 0.004272987134754658, + -0.03169683367013931, + 0.008137955330312252, + -0.07982300966978073, + -0.037415798753499985, + -0.0016467635286971927, + -0.016258487477898598, + 0.01855027861893177, + 0.012749083340168, + -0.015595809556543827, + 0.009437683038413525, + 0.005881224758923054, + 0.009153603576123714, + -0.035431332886219025, + -0.03822671249508858, + -0.007053021341562271, + 0.07195861637592316, + 0.03834277018904686, + 0.025282155722379684, + 0.03235918655991554, + -0.040675584226846695, + 0.06914123892784119, + -0.014681060798466206, + 0.04182145744562149, + 0.016547678038477898, + 0.0302575696259737, + 0.027968881651759148, + 0.028392894193530083, + -0.03601876646280289, + 0.011166741140186787, + 0.013932433910667896, + -0.024813517928123474, + 0.04876561462879181, + 0.03280804678797722, + 0.020525190979242325, + -0.04888831451535225, + 0.05333299934864044, + -0.01227282639592886, + 0.009397462010383606, + -0.062118303030729294, + 0.020511150360107422, + 0.03606007248163223, + -0.011546325869858265, + 0.02632950246334076, + 0.03558770939707756, + -0.04729287326335907, + -0.00040853474638424814, + -0.05594595894217491, + 0.03343893215060234, + -0.03624171018600464, + -0.01565496437251568, + 0.03419746086001396, + -0.014939344488084316, + -0.0346553735435009, + 0.02617849037051201, + -0.018064821138978004, + 0.00044916238402947783, + -0.029752276837825775, + -0.06982599943876266, + -0.01529014203697443, + -0.10238753259181976, + 0.056908924132585526, + -0.018579944968223572, + 0.032441046088933945, + 0.02623467892408371, + 0.0005816647899337113, + 0.024393916130065918, + -0.0010619793320074677, + 0.09054756909608841, + 0.012866330333054066, + 0.0110749127343297, + 0.060603830963373184, + -0.04485912621021271, + -0.035673510283231735, + 0.00880404282361269, + -0.0236192774027586, + -0.04651271551847458, + 0.04936773329973221, + 0.016861658543348312, + -0.026910705491900444, + 0.02507326751947403, + 0.0018011556239798665, + -0.01599423959851265, + 0.007061067037284374, + -0.028597962111234665, + -0.005096979904919863, + -0.003091734368354082, + -0.008610324002802372, + -0.03941959887742996, + -0.07249880582094193, + 0.07896454632282257, + -0.01282701175659895, + 0.03806105628609657, + -0.01628866419196129, + -0.00032510326127521694, + 0.007600210607051849, + 0.012463843449950218, + 0.07028777152299881, + 0.024854836985468864, + 0.00597741175442934, + 0.012146051973104477, + -0.04252159595489502, + -0.08857864141464233, + 0.005069843493402004, + -0.002303875982761383, + 0.007218160200864077, + -0.054320499300956726, + 0.01721455715596676, + -0.012323171831667423, + 0.029316846281290054, + 0.010660098865628242, + 0.01619168184697628, + 0.024796800687909126, + -0.06043343245983124, + -0.009076021611690521, + 0.05426326394081116, + 0.024232488125562668, + -0.025832876563072205, + 0.024366402998566628, + -0.04501958563923836, + 0.04263340309262276, + -0.01757700741291046, + 0.0240378025919199, + 0.007873878814280033, + -0.019204245880246162, + -0.04099274054169655, + -0.0028695412911474705, + -0.02336733788251877, + -0.009908018633723259, + 0.01244357880204916, + 0.014616346918046474, + 0.07263968884944916, + -0.006017595529556274, + 0.006593986880034208, + -0.017023928463459015, + -0.0008568437770009041, + 0.0393415242433548, + -0.03193742036819458, + -0.07265064865350723, + -0.056716252118349075, + -0.06321432441473007, + 0.0014871162129566073, + 0.015271728858351707, + 0.06799189001321793, + 0.002235528314486146, + 0.015148743987083435, + 0.029075419530272484, + -0.036075517535209656, + 0.03699851781129837, + 0.002699150936678052, + 0.029273545369505882, + 0.024833064526319504, + 0.02166113816201687, + 0.07822758704423904, + 0.0907154381275177, + -0.015422212891280651, + -0.004725399427115917, + -0.013691544532775879, + 0.00014949020987842232, + 0.003309824038296938, + 0.019388742744922638, + -0.01792132295668125, + -0.005919941700994968, + -0.009184692986309528, + -0.00453580915927887, + -0.017324700951576233, + 0.020368218421936035, + 0.007512629963457584, + -0.05764073505997658, + 0.01584697514772415, + -0.016094518825411797, + -0.0366678424179554, + -0.02194156125187874, + 0.053442906588315964, + 0.04864593967795372, + -0.009642759338021278, + 0.06584249436855316, + 0.017993653193116188, + 0.02838297188282013, + -0.02758033573627472, + -0.018208689987659454, + -0.08217029273509979, + 0.001340706367045641, + 0.07344162464141846, + -0.0014725526561960578, + 0.027256185188889503, + -0.03795681148767471, + 0.03496084362268448, + -0.009351355955004692, + 0.03554052114486694, + -0.0647641122341156, + -0.018092816695570946, + -0.0003290708118584007, + -0.008958869613707066, + -0.0006743986159563065, + 0.02749652974307537, + -0.005728874355554581, + -0.00014254855341278017, + 0.02650611102581024, + -0.007747439201921225, + -0.036285076290369034, + -0.04723037779331207, + -0.01256555411964655, + -0.015652446076273918, + -0.0033896011300385, + -0.027379868552088737, + 0.06606956571340561, + 0.001414530212059617, + -0.03816799819469452, + 0.005582350306212902, + -0.0037654521875083447, + -0.03315531834959984, + -0.03833584487438202, + 0.005306297447532415, + 0.06055983901023865, + 0.017386972904205322, + 0.017846958711743355, + 0.002940434729680419, + 0.06065093353390694, + -0.033751003444194794, + 0.02014659158885479, + -0.026745468378067017, + 0.02349875122308731, + 0.06887564063072205, + 0.08784544467926025, + 0.0348343662917614, + 0.017027992755174637, + 0.007463646121323109, + 0.010731169953942299, + -0.015452216379344463, + 0.0697169378399849, + 0.06115807220339775, + 0.05587253347039223, + 0.0035254100803285837, + -0.06922555714845657, + -0.00895272009074688, + 0.04390031844377518, + 0.003160918829962611, + 0.0734192356467247, + -0.012384983710944653, + 0.00778034096583724, + -0.06225632503628731, + 0.01105977687984705, + -0.019027134403586388, + -0.01744268462061882, + -0.03861316666007042, + -0.026121554896235466, + -0.03796643018722534, + -0.02607419341802597, + -0.00727757578715682, + -0.04364367574453354, + 0.027054548263549805, + 0.001148495590314269, + -0.0051346817053854465, + -0.014047800563275814, + 0.033344950526952744, + 0.016461240127682686, + 0.033907197415828705, + -0.052207209169864655, + -0.058969806879758835, + 0.019914019852876663, + 0.04874560981988907, + 0.0043409536592662334, + 0.014156220480799675, + -0.025425465777516365, + -0.03806624561548233, + 0.027224158868193626, + -8.918229286791757e-05, + 0.04550011456012726, + 0.02069287933409214, + -0.006964664440602064, + -0.05213857442140579, + 0.03515300899744034, + -0.02322443015873432, + 0.07085354626178741, + 0.010733392089605331, + -0.04821530729532242, + -0.024944474920630455, + 0.01349271647632122, + 0.0064827692694962025, + 0.021682681515812874, + 0.03466835618019104, + -0.023484358564019203, + -0.004177657887339592, + 0.019195759668946266, + 0.021642865613102913, + 0.03591984510421753, + -6.837025284767151e-05, + 0.003064215648919344, + 0.0067205713130533695, + 0.024574855342507362, + 0.03467808663845062, + -0.07038415223360062, + 0.020557953044772148, + 0.05572228878736496, + 0.024007081985473633, + 0.008300675079226494, + 0.05382058024406433, + -0.008657778613269329, + -0.04247821494936943, + -0.02082398161292076, + -0.030047548934817314, + -0.0042150202207267284, + 0.0643019825220108, + 0.08603832125663757, + -0.0032497297506779432, + -0.05890907347202301, + -0.017683515325188637, + -0.0017970707267522812, + 0.030202442780137062, + -0.004163889214396477, + -0.005693267099559307, + 0.07439851015806198, + -0.007623215671628714, + -0.014011486433446407, + -0.06531509011983871, + -0.012002935633063316, + 0.05098460614681244, + 0.018368106335401535, + 0.044709816575050354, + -0.034841395914554596, + 0.04669453203678131, + -0.006633058190345764, + -0.06744810938835144, + 0.00022071562125347555, + -0.02252846583724022, + -0.008146141655743122, + 0.04570293799042702, + -0.017073389142751694, + 0.033481452614068985, + 0.02024919167160988, + -0.00039372473838739097, + -0.015125994570553303, + 0.0035840750206261873, + 0.03293292224407196, + -0.023488696664571762, + 0.02769201435148716, + 0.03366998955607414, + 0.013383373618125916, + -0.0062416414730250835, + -0.05436183512210846, + -0.007013875991106033, + -0.0343070924282074, + 0.008950931020081043, + -0.0007773659308440983, + 0.01631912775337696, + -0.01733097992837429, + 0.007631183601915836, + 0.022811884060502052, + 0.05997275933623314, + -0.025991076603531837, + -0.06607384979724884, + -0.0873650386929512, + -0.05788758397102356, + -0.020700229331851006, + 0.00862400233745575, + 0.008653292432427406, + -0.05257308855652809, + -0.01877412386238575, + 0.001132996054366231, + 0.007562611252069473, + 0.007040517870336771, + -0.03939346596598625, + -0.0012852386571466923, + 0.03364014998078346, + -0.08792895078659058, + 0.0003337061498314142, + 0.04566165804862976, + 0.022397097200155258, + 0.07704627513885498, + 0.011688907630741596, + 0.06875491887331009, + 0.031596384942531586, + -0.07542278617620468, + 0.06929827481508255, + 0.03525209799408913, + -0.05507253482937813, + 0.06310203671455383, + 0.009202172048389912, + 0.08802317827939987, + 0.015267971903085709, + 0.01631786674261093, + -0.08159693330526352, + 0.011958948336541653, + -0.022956276312470436, + -0.0045707738026976585, + 0.06590449810028076, + -0.025062261149287224, + 0.05683448538184166, + 0.08174461871385574, + 0.018841996788978577, + -0.02901572361588478, + 0.04103256016969681, + -0.06138996779918671, + -0.02983909286558628, + -0.03850552439689636, + -0.018056459724903107, + 0.00292590050958097, + -0.0737059935927391, + 0.00898703932762146, + -0.012909052893519402, + -0.00488039618358016, + 0.019017860293388367, + -0.037835441529750824, + -0.05031483247876167, + 0.025473300367593765, + -0.009489303454756737, + -0.08405261486768723, + 0.06039801985025406, + -0.028819533064961433, + 0.01564796455204487, + -0.07851359248161316, + 0.00776974530890584, + -0.0627446398139, + 0.043354298919439316, + -0.0447402149438858, + 0.008833021856844425, + -0.0005271312547847629, + -0.03740326315164566, + -0.033597033470869064, + 0.02730080671608448, + -0.030516251921653748, + 0.03767557814717293, + -0.10619816929101944, + -0.038678478449583054, + 0.02232091873884201, + 0.03868230804800987, + 0.018831931054592133, + -0.05178656801581383, + -0.05465080961585045, + 0.03249572589993477, + 0.009297838434576988, + -0.003563723061233759, + -0.04144677892327309, + 0.0509132519364357, + -0.02094709314405918, + -0.022470436990261078, + -0.04437573254108429, + -0.03695523366332054, + -0.075083889067173, + 0.07801777124404907, + 0.007801617495715618, + -0.005376672837883234, + 0.020604871213436127, + -0.06675189733505249, + 0.0027014226652681828, + 0.08348087221384048, + -0.031110215932130814, + -0.02220381610095501, + 0.021845143288373947, + 0.03032352775335312, + -0.0012008004123345017, + -0.03200481832027435, + 0.049666762351989746, + 0.005313111934810877, + -0.020655009895563126, + 0.007201225031167269, + -0.05322100222110748, + -0.03385355696082115, + 0.010354285128414631, + 0.04187091067433357, + 0.006058192811906338, + 0.005469379480928183, + 0.041591376066207886, + -0.023555509746074677, + 0.043303441256284714, + -0.04954344779253006, + -0.033017441630363464, + -0.01149839162826538, + -0.012791389599442482, + 0.001670036930590868, + -0.012347050942480564, + 0.0004881276981905103, + -0.031120697036385536, + 0.022906621918082237, + -0.050669725984334946, + 0.04269399866461754, + -0.011447146534919739, + -0.017906805500388145, + -0.06953153014183044, + 0.04467186704277992, + -0.04761233553290367, + -0.013187393546104431, + 0.05690088868141174, + -0.042590390890836716, + -0.01746809110045433, + 0.020567748695611954, + 0.05125907063484192, + 0.020307395607233047, + 0.03492629528045654, + -0.04882863909006119, + -0.03183748573064804, + -0.06539574265480042, + -0.01744089275598526, + -0.02758834883570671, + 0.0050849285908043385, + -0.00035606700112111866, + 0.023614611476659775, + 0.01930573768913746, + -0.05899752303957939, + -0.04627015441656113, + 0.0068423328921198845, + 0.03920449689030647, + -0.007687605917453766, + 0.016464397311210632, + 0.04807426780462265, + 0.0023120716214179993, + 0.01973593607544899, + 0.07794646173715591, + 0.07625434547662735, + -0.03674965724349022, + -0.0012999586760997772, + 0.009016714058816433, + 0.03811555355787277, + 0.017517905682325363, + 0.004926901776343584, + -0.07054422050714493, + -0.01442575640976429, + 0.01330371480435133, + -0.008963101543486118, + -0.009463613852858543, + 0.0017095000948756933, + -0.016330784186720848, + -0.017924489453434944, + -0.042089130729436874, + -0.06883884966373444, + -0.042998943477869034, + 0.014172191731631756, + -0.0023317155428230762, + -0.027441971004009247, + 0.004573931451886892, + -0.07700463384389877, + -0.013737251050770283, + 0.025464439764618874, + -0.02619084157049656, + -0.008323452435433865, + -0.03393486887216568, + -0.04159104451537132, + -0.004442669451236725, + -0.008337379433214664, + 0.05703001841902733, + -0.05177110433578491, + 0.002210760721936822, + 0.005930258426815271, + -0.0369490347802639, + -0.013454861007630825, + -0.004840550944209099, + -0.04600533843040466, + -0.010599354282021523, + -0.008193885907530785, + -0.029226260259747505, + -0.06824758648872375, + 0.002242376795038581, + -0.00545460032299161, + -0.016073163598775864, + -0.02212926186621189, + 0.014335459098219872, + 0.02033282071352005, + -0.01998221129179001, + 0.06560437381267548, + -0.007302496116608381, + 0.037101101130247116, + -0.015349503606557846, + -0.0149971479550004, + -0.003208655398339033, + 0.01065454725176096, + -0.010318529792129993, + 0.005211932118982077, + -0.007634020410478115, + 0.007333737798035145, + 0.04658440127968788, + -0.017371229827404022, + -0.02044561877846718, + 0.021157968789339066, + -0.005675977561622858, + -0.016465574502944946, + 0.001816042698919773, + -0.022665906697511673, + 0.04769016057252884, + -0.02464037574827671, + -0.05675514042377472, + 0.05963050201535225, + -0.01688731089234352, + -0.05340677872300148, + 0.010052076540887356, + 0.02069842256605625, + 0.028715714812278748, + 0.009125969372689724, + -0.02970687672495842, + -0.010313224978744984, + -0.03552298620343208, + 0.04363728687167168, + -0.03991911932826042, + -0.004784241318702698, + -0.044753339141607285, + 0.01931679993867874, + -0.056493211537599564, + -0.006617037579417229, + 0.035743631422519684, + -0.053424812853336334, + -0.02699253521859646, + -0.007951406762003899, + -0.009088664315640926, + -0.018690962344408035, + -0.04115553945302963, + 0.02701025828719139, + 0.0571308434009552, + -0.029878465458750725, + -0.03173048421740532, + -0.01149672456085682, + -0.0105333486571908, + -0.005241425707936287, + -0.02809373289346695, + 0.05968040972948074, + 0.0010212024208158255, + 0.042596235871315, + 0.04825957119464874, + -0.003983878996223211, + 0.016225650906562805, + 0.015263753943145275, + -0.023301145061850548, + 0.041719190776348114, + 0.028326746076345444, + 0.026445787400007248, + -0.022935770452022552, + 0.03078318201005459 + ], + "chunk_ind": 1 + }, + { + "url": "https://docs.danswer.dev/more/use_cases/ai_platform", + "title": "AI Platform", + "content": "Build AI Agents powered by the knowledge and workflows specific to your organization.\n\nBeyond Answers\nAgents enabled by generative AI and reasoning capable models are helping teams to automate their work. Danswer is helping teams make it happen. Danswer provides out of the box user chat sessions, attaching custom tools, handling LLM reasoning, code execution, data analysis, referencing internal knowledge, and much more.\n\nDanswer as a platform is not a no-code agent builder. We are made by developers for developers and this gives your team the full flexibility and power to create agents not constrained by blocks and simple logic paths.\n\nFlexibility and Extensibility\nDanswer is open source and completely whitebox. This not only gives transparency to what happens within the system but also means that your team can directly modify the source code to suit your unique needs.", + "title_embedding": [ + 0.032763753086328506, + 0.049961112439632416, + 0.00777681777253747, + -0.009621717967092991, + 0.03860695660114288, + 0.035656899213790894, + -0.029095029458403587, + -0.030549267306923866, + -0.028131460770964622, + -0.023247526958584785, + -0.030750803649425507, + 0.04233109578490257, + 0.044790223240852356, + 0.020764602348208427, + -0.011113415472209454, + -0.052699606865644455, + 0.05441703647375107, + -0.027375519275665283, + 0.03858301043510437, + 0.0015289749717339873, + -0.0007870558765716851, + -0.013234086334705353, + -0.008892231620848179, + -0.0269540473818779, + 0.032256800681352615, + 0.028824904933571815, + 0.021423548460006714, + 0.0196831077337265, + 0.004699843470007181, + 0.01062865275889635, + -0.03573931008577347, + -0.01450167316943407, + 0.06177164614200592, + -0.004766061902046204, + -0.011502844281494617, + -0.059983331710100174, + 0.03794373199343681, + 0.003160010790452361, + 0.05785837396979332, + -0.016349520534276962, + 0.048589278012514114, + 0.03928593918681145, + -0.027400294318795204, + -0.007712628226727247, + 0.044047582894563675, + 0.03514353185892105, + 0.050972215831279755, + -0.027322333306074142, + 0.08146621286869049, + -0.041862014681100845, + 0.034794293344020844, + 0.0064093489199876785, + -0.05552367866039276, + -0.06472223997116089, + -0.0006224742392078042, + 0.010324635542929173, + -0.00513586075976491, + 0.006625971291214228, + -0.03121061436831951, + -0.02010185271501541, + 0.024356791749596596, + 0.04554779455065727, + -0.04365985095500946, + 0.038004688918590546, + 0.026826566085219383, + -0.0002007065195357427, + 0.0025419823359698057, + 0.022517988458275795, + 0.004520556423813105, + -0.04712541028857231, + 0.042386990040540695, + 0.0317973829805851, + 0.022796982899308205, + 0.03537650406360626, + -0.024706847965717316, + -0.05100490525364876, + 0.013296891935169697, + -0.027389265596866608, + -0.022103115916252136, + 0.07237043976783752, + 0.022473221644759178, + -0.08428098261356354, + 0.0284805316478014, + 0.014994120225310326, + 0.0647200271487236, + -0.0013714460656046867, + -0.02798375114798546, + 0.004889763426035643, + -0.02891303412616253, + 0.06638259440660477, + -0.015550877898931503, + 0.01490933820605278, + 0.03998437523841858, + 0.031558796763420105, + -0.09123710542917252, + 0.03090553544461727, + -0.027405250817537308, + 0.0028605929110199213, + -0.01660272665321827, + -0.024673976004123688, + -0.03330164775252342, + 0.019906772300601006, + 0.020785389468073845, + -0.02234416827559471, + 0.0711885541677475, + 0.010001438669860363, + -0.007417359855026007, + -0.03474368155002594, + 0.0117587149143219, + -0.030912458896636963, + -0.04288865998387337, + 0.004992801230400801, + -0.011203224770724773, + 0.026435980573296547, + -0.019328005611896515, + -0.01772245578467846, + 0.05772961303591728, + -0.018587617203593254, + 0.03977040946483612, + 0.0511898435652256, + 0.02799198590219021, + -0.021339384838938713, + 0.016965094953775406, + 0.08415205776691437, + 0.010289170779287815, + -0.02373247779905796, + -0.06358940154314041, + 0.03165338188409805, + -0.013218379579484463, + -0.041016921401023865, + 0.052579861134290695, + 0.016211217269301414, + 0.012958381325006485, + -0.029191715642809868, + -0.0013247805181890726, + 0.05056416615843773, + -0.05472686141729355, + -0.05397220700979233, + 0.07864602655172348, + 0.044400643557310104, + 0.011529057286679745, + -0.0056294528767466545, + 0.0019877285230904818, + -0.01892041228711605, + 0.031235355883836746, + -0.06018691137433052, + 0.015224655158817768, + 0.0035034629981964827, + -0.04407024383544922, + 0.03802705183625221, + 0.016176624223589897, + 0.05680167302489281, + -0.017375409603118896, + -0.01676156371831894, + -0.017084985971450806, + -0.042274024337530136, + -0.07406415045261383, + 0.020823167636990547, + 0.04484682157635689, + -0.023108867928385735, + 0.02925572544336319, + 0.06840821355581284, + -0.027610015124082565, + 0.04234248027205467, + -0.02915036305785179, + -0.004962626378983259, + -0.0017270881216973066, + 0.023044373840093613, + 0.037656962871551514, + 0.04789644852280617, + -0.0027900487184524536, + 0.0004090967122465372, + 0.014888445846736431, + 0.009237252175807953, + 0.036635007709264755, + 0.015078885480761528, + 0.046658437699079514, + -0.025920215994119644, + 0.014571646228432655, + -0.053589239716529846, + 0.024663543328642845, + -0.0388394258916378, + 0.0037244234699755907, + 0.007817366160452366, + -0.03352022543549538, + -0.0609428733587265, + 0.04179045185446739, + -0.05036167427897453, + -0.04099080711603165, + 0.02920934371650219, + -0.037300609052181244, + 0.010041946545243263, + 0.025091813877224922, + -0.032656773924827576, + -0.05137333646416664, + -0.038329657167196274, + 0.03855415806174278, + 0.006781625561416149, + 0.02984003536403179, + -0.06467068940401077, + 0.02395613305270672, + 0.018539344891905785, + -0.0718475878238678, + 0.031203489750623703, + -0.057184506207704544, + 0.02436862140893936, + 0.02837834134697914, + -0.010054084472358227, + -0.02551312930881977, + 0.021066943183541298, + 0.06444599479436874, + 0.01263453345745802, + -0.018358737230300903, + 0.010503370314836502, + -0.023012487217783928, + 0.009831788949668407, + 0.0049070375971496105, + -0.022574082016944885, + -0.0049112942069768906, + -0.01014224998652935, + 0.055648382753133774, + -0.016490083187818527, + -0.012448773719370365, + -0.014511270448565483, + 0.027931246906518936, + 0.024195006117224693, + -0.005839435383677483, + 0.029669128358364105, + -0.007521398831158876, + 0.03150096535682678, + -0.01941276341676712, + -0.06204359978437424, + 0.01095200888812542, + 0.0023097621742635965, + 0.008341503329575062, + 0.0100992601364851, + -0.039239075034856796, + 0.04388657584786415, + 0.015824418514966965, + 0.06830465793609619, + 0.009663422591984272, + -0.00038048860733397305, + 0.035620324313640594, + -0.011668454855680466, + -0.06677736341953278, + 0.008154943585395813, + -0.03417421504855156, + -0.022497251629829407, + 0.01800542138516903, + 0.0010614683851599693, + 0.00842749048024416, + 0.020196812227368355, + -0.005975049454718828, + 0.024395788088440895, + -0.01633184403181076, + -0.004018640611320734, + -0.0018627216340973973, + 0.058719366788864136, + -0.024047864601016045, + -0.0032275430858135223, + 0.07045131176710129, + -0.03221508115530014, + 0.0352499820291996, + 0.02055438607931137, + 0.02973576821386814, + 0.0017980994889512658, + 0.05022549629211426, + 0.03819788247346878, + -0.005316003691405058, + 0.011116476729512215, + 0.019071733579039574, + 0.03500362113118172, + -0.03451540693640709, + 0.09197302162647247, + 0.008307289332151413, + 0.015847783535718918, + -0.003909585066139698, + -0.04707544669508934, + 0.01712993159890175, + -0.026143768802285194, + -0.007809836883097887, + -0.02002348005771637, + -0.03528841957449913, + -0.012745876796543598, + 0.016280299052596092, + 0.005661313887685537, + 0.022872695699334145, + 0.016736241057515144, + -0.048460669815540314, + 0.012391538359224796, + -0.04375111311674118, + -0.06501554697751999, + -0.0159616582095623, + 0.009163076989352703, + -0.008098017424345016, + 0.03997795283794403, + 0.09088447690010071, + -0.025736957788467407, + -0.01334838755428791, + 0.015781259164214134, + 0.010901914909482002, + 0.021588636562228203, + 0.011131210252642632, + -0.034338608384132385, + 0.053609222173690796, + 0.018425501883029938, + 0.03827910125255585, + -0.003314226632937789, + 0.010824226774275303, + 0.020308859646320343, + -0.11467628926038742, + 0.04042372852563858, + 0.01810252107679844, + 0.03511713072657585, + -0.0987866222858429, + 0.016760295256972313, + 0.007829226553440094, + -0.011888569220900536, + 0.034833233803510666, + -0.009197549894452095, + 0.005588896572589874, + -0.07932842522859573, + -0.02078017219901085, + -0.03448954597115517, + 0.0152775589376688, + 0.08626428246498108, + 0.03126169368624687, + 0.04502886161208153, + -0.026686420664191246, + -0.028234312310814857, + 0.0049273171462118626, + 0.023110508918762207, + -0.08400018513202667, + 0.017200743779540062, + 0.02693784609436989, + 0.0036261421628296375, + -0.018591655418276787, + 0.005189367104321718, + 0.0002512435312382877, + -0.01673535816371441, + 0.06507309526205063, + 0.02960938587784767, + 0.0194547139108181, + -0.045088544487953186, + -0.01410599984228611, + -0.001771911047399044, + 0.042333200573921204, + -0.015243434347212315, + 0.027360277250409126, + -0.02644488774240017, + -0.059026844799518585, + 0.0013204477727413177, + -0.005272903945297003, + -0.03697441890835762, + -0.03736754506826401, + 0.06495915353298187, + 0.004548369906842709, + 0.004532824270427227, + -0.005509661976248026, + 0.013331729918718338, + 0.005671144928783178, + -0.043852198868989944, + 0.06886028498411179, + -0.0020801422651857138, + 0.014272121712565422, + -0.02358032390475273, + 0.010091368108987808, + -0.013035510666668415, + -0.009768063202500343, + -0.024086249992251396, + 0.04728090390563011, + -0.024031780660152435, + 0.032426923513412476, + 0.06455196440219879, + 0.08759471774101257, + 0.009270765818655491, + -0.0936349406838417, + -0.012462696991860867, + -0.019188350066542625, + -0.06805568188428879, + 0.01794586144387722, + -0.0007348881918005645, + 0.0024105070624500513, + -0.016566181555390358, + 0.012622764334082603, + -0.03900640457868576, + 0.010342570021748543, + 0.011543489061295986, + 0.01152091845870018, + -0.05232607573270798, + 0.004903953988105059, + -0.05708310753107071, + -0.04076048359274864, + 0.016818160191178322, + -0.020741824060678482, + 0.01609313301742077, + -0.022479360923171043, + 0.03654901310801506, + 0.022170664742588997, + 0.01575297676026821, + -0.011484816670417786, + -0.025103436782956123, + 0.05906060338020325, + 0.02779274433851242, + 0.028078753501176834, + 0.04629473015666008, + -0.005719225853681564, + -0.06190178170800209, + 0.006866101641207933, + -0.002305209171026945, + 0.03215618431568146, + 0.007546067703515291, + -0.02738751657307148, + -0.04539818689227104, + 0.04683874174952507, + -0.0208493173122406, + 0.03900844231247902, + -0.027456291019916534, + -0.028509290888905525, + 0.013289637863636017, + 0.0017003221437335014, + -0.0198791716247797, + 0.014913729391992092, + 0.005401032045483589, + -0.04071260988712311, + 0.02060793526470661, + -0.003016189206391573, + 0.03800947219133377, + -0.019319988787174225, + -0.024961907416582108, + -0.02498740889132023, + -0.04191872850060463, + -0.042030803859233856, + 0.013421737588942051, + -0.045663248747587204, + 0.024831216782331467, + 0.06314653903245926, + 0.013705547899007797, + 0.025637097656726837, + -0.006122317630797625, + 0.0041285231709480286, + 0.050409767776727676, + 0.007197089493274689, + -0.01965370774269104, + -0.04048306494951248, + 0.11998444050550461, + 0.029942067340016365, + 0.02599455416202545, + -0.057833291590213776, + 0.0033883019350469112, + 0.00468824477866292, + -0.01925582066178322, + -0.01766190119087696, + 0.011122050695121288, + 0.04823627695441246, + 0.018773270770907402, + -0.020368080586194992, + -0.009206349961459637, + 0.031074542552232742, + 0.02497885189950466, + 0.0031681342516094446, + 0.015077338553965092, + -0.022211533039808273, + 0.058754149824380875, + -0.016073331236839294, + -0.014968045987188816, + -0.0051240865141153336, + -0.06383436918258667, + -0.0280417762696743, + 0.013401271775364876, + -0.006949563976377249, + -0.009025825187563896, + 0.03748825564980507, + 0.04152849316596985, + -0.03703063353896141, + 0.0006073106196708977, + -0.019878407940268517, + -0.059219732880592346, + 0.03231174871325493, + -0.012458872981369495, + -0.0006862205918878317, + -0.029703414067626, + -0.011737367138266563, + -0.01565374620258808, + -0.002873011166229844, + 0.035379018634557724, + -0.025712305679917336, + 0.027225548401474953, + -0.011701708659529686, + -0.020186487585306168, + -0.013381940312683582, + 0.044779565185308456, + 0.027129901573061943, + -0.03770675137639046, + -0.06656532734632492, + -0.04852313920855522, + -0.07922673970460892, + 0.042464420199394226, + 0.08760115504264832, + -0.01756269298493862, + 0.025902874767780304, + -0.049739014357328415, + 0.015325409360229969, + 0.04406426474452019, + 0.012947683222591877, + -0.022557666525244713, + -0.033376943320035934, + -0.12034522742033005, + 0.019998058676719666, + 0.04397791251540184, + 0.024618806317448616, + -0.013922464102506638, + 0.031511057168245316, + 0.03906194865703583, + 0.011382625438272953, + -0.027103818953037262, + 0.04971625655889511, + 0.051205385476350784, + -0.08501561731100082, + 0.011972213163971901, + -0.018331818282604218, + -0.00884521659463644, + -0.0015008534537628293, + 0.0827648937702179, + -0.03979771211743355, + 0.0015674568712711334, + -0.014266063459217548, + -0.03932151570916176, + 0.04269920662045479, + -0.059784602373838425, + 0.01841970533132553, + 0.06251460313796997, + -0.02819698490202427, + -0.040344759821891785, + 0.0010407248046249151, + -0.034333355724811554, + -0.029237672686576843, + -0.0001084851028281264, + 0.06710729002952576, + 0.019469408318400383, + -0.01640215329825878, + 0.019526075571775436, + 0.007778842933475971, + 0.03379968926310539, + 0.030870657414197922, + -0.059688691049814224, + -0.05436835065484047, + 0.053333111107349396, + 0.004061849322170019, + -0.08632408827543259, + 0.014255499467253685, + -0.05555962026119232, + 0.010840730741620064, + -0.05179913341999054, + -0.007342956960201263, + 0.0011719957692548633, + 0.022990427911281586, + 0.013041576370596886, + -0.026316920295357704, + -0.022087475284934044, + -0.02786962315440178, + 0.013592005707323551, + 0.021783264353871346, + -0.059460774064064026, + -0.029133567586541176, + -0.06166587024927139, + -0.055512115359306335, + 0.004256486427038908, + 0.0341678261756897, + 0.011773993261158466, + -0.029188869521021843, + -0.021346861496567726, + -0.036212995648384094, + 0.025272972881793976, + 0.02215636521577835, + -0.03782811760902405, + 0.01701144315302372, + -0.05073560029268265, + -0.06574195623397827, + 0.012947561219334602, + 0.003303218400105834, + -0.05047185719013214, + 0.010198806412518024, + -0.04323785379528999, + -0.04194899648427963, + 0.02726336568593979, + -0.015397109091281891, + -0.02849482372403145, + 0.058862827718257904, + -0.0026129265315830708, + 0.006432596128433943, + 0.04382907226681709, + -0.05114292353391647, + -0.02147330716252327, + -0.05826929211616516, + 0.046473387628793716, + -0.09205549210309982, + 0.04540986940264702, + -0.006234755739569664, + -0.05360054224729538, + -0.012155161239206791, + -0.030249077826738358, + 0.02822766825556755, + 0.013851269148290157, + 0.027002329006791115, + 0.09613272547721863, + 0.035666726529598236, + 0.03504599630832672, + -0.00038134161150082946, + -0.06922309845685959, + 0.016433153301477432, + -0.031455833464860916, + -0.018132444471120834, + -0.02008064091205597, + -0.015955988317728043, + -0.04022971913218498, + -0.00230028061196208, + -0.06941505521535873, + 0.0230435561388731, + -0.026967540383338928, + 0.0354134738445282, + -0.08307641744613647, + 0.055718302726745605, + 0.0012352125486359, + 0.017340224236249924, + 0.02709241770207882, + -0.009195402264595032, + 0.020474854856729507, + 0.0016901030903682113, + 0.05093026161193848, + -0.02238425612449646, + 0.011796950362622738, + -0.007241291459649801, + -0.0334753580391407, + -0.04778272658586502, + -0.030247407034039497, + -0.012979192659258842, + 0.004056413192301989, + 0.015001167543232441, + 0.06737781316041946, + 0.028164206072688103, + 0.0028011424001306295, + -0.049282923340797424, + 0.06260383874177933, + 0.04237203299999237, + -0.026161646470427513, + 0.02427232824265957, + 0.021224258467555046, + 0.002963172970339656, + -0.049155037850141525, + 0.033326923847198486, + 0.07168576121330261, + -0.04409810155630112, + -0.012802177108824253, + 0.011941076256334782, + 0.005057428497821093, + -0.04857957363128662, + -0.011230324395000935, + 0.009986268356442451, + 0.010389930568635464, + -0.013448627665638924, + -0.04319113492965698, + -0.02839748188853264, + 0.011157489381730556, + 0.015462666749954224, + -0.014774681068956852, + -0.035400133579969406, + 0.003983446396887302, + -0.06980624049901962, + -0.0019868735689669847, + -0.0014860559022054076, + -0.017261963337659836, + 0.03138411417603493, + -0.07367079704999924, + 0.025024767965078354, + 0.037335801869630814, + 0.04612639173865318, + -0.018027080222964287, + -0.015578734688460827, + -0.05632679536938667, + -0.01690700650215149, + 0.023824671283364296, + 0.003364108270034194, + -0.0478903129696846, + 0.014160525053739548, + 0.0023307709489017725, + 0.028807908296585083, + 0.0053710732609033585, + -0.007223619148135185, + -0.09570229798555374, + 0.013001752085983753, + -0.03882845118641853, + -0.018106481060385704, + -0.08351759612560272, + -0.01296163722872734, + -0.0017098417738452554, + -0.042986027896404266, + 0.02120766043663025, + -0.00032761419424787164, + 0.059994783252477646, + 0.00795682892203331, + 0.025746053084731102, + 0.026430919766426086, + 0.10314885526895523, + -0.042013708502054214, + -0.01044819038361311, + -0.06457454711198807, + 0.04287077486515045, + -0.0233222134411335, + -0.011595506221055984, + 0.008520099334418774, + 0.021662304177880287, + 0.04874734953045845, + 0.03213977813720703, + -0.03502868860960007, + -0.013689175248146057, + 0.007175855804234743, + -0.06394322961568832, + -0.03230760619044304, + -0.0520993173122406, + 0.03424723073840141, + -0.01675051636993885, + -0.04967552423477173, + 0.03324288874864578, + -0.03822193667292595, + -0.015012933872640133, + -0.02746376395225525, + -0.015637405216693878, + 0.040449269115924835, + -0.0027442676946520805, + 0.008192671462893486, + 0.013573664240539074, + -0.0065663764253258705, + 0.07001614570617676, + -0.00289558875374496, + 0.004224210977554321, + -0.05637960880994797, + -0.010168599896132946, + -0.02271331660449505, + 0.0014612390659749508, + 0.06994854658842087, + -0.00733678275719285, + -0.0025255896616727114, + 0.03514084219932556, + 0.02634606696665287, + -0.016171403229236603, + -0.02692556194961071, + 0.015410004183650017, + 0.07382199913263321, + 0.01444800104945898, + -0.020071715116500854, + 0.030701540410518646, + 0.0056877885945141315, + 0.011047931388020515, + -0.05641033127903938, + 0.03570398688316345, + -0.06379767507314682, + 0.09488129615783691, + 0.015704551711678505, + -0.0008733674185350537, + 0.009907273575663567, + 0.004910382442176342, + 0.050873469561338425, + 0.01800096221268177, + -0.027450138702988625, + -0.001498246449045837, + -0.027504686266183853, + -0.019632702693343163 + ], + "content_embedding": [ + -0.0417482890188694, + 0.0512668639421463, + 0.0012354102218523622, + -0.035204555839300156, + 0.028333576396107674, + 0.006138786673545837, + 0.017678435891866684, + 0.004378852900117636, + -0.022564459592103958, + -0.03274708241224289, + -0.06855575740337372, + 0.03446828946471214, + 0.03136003389954567, + -0.016096506267786026, + -0.007832110859453678, + 0.01546874176710844, + 0.025302864611148834, + -0.01542437169700861, + 0.009685760363936424, + 0.025153761729598045, + 0.01136286836117506, + -0.03678102046251297, + 0.01742858625948429, + -0.04800569638609886, + 0.052324045449495316, + -0.0188713688403368, + -0.017203466966748238, + 0.04401639476418495, + -0.05147295445203781, + -0.005816930439323187, + 0.04151167348027229, + 0.0020627069752663374, + 0.008849645033478737, + -0.03293370082974434, + -0.030744211748242378, + -0.025762831792235374, + 0.07024409621953964, + -0.029683783650398254, + -0.02081390842795372, + 0.034864746034145355, + 0.057659171521663666, + 0.009455090388655663, + -0.001964752795174718, + -0.028249403461813927, + 0.045469045639038086, + 0.010203365236520767, + 0.039163172245025635, + -0.01693413034081459, + 0.03357663378119469, + -0.016916338354349136, + 0.007125346455723047, + -0.02135808765888214, + -0.007920235395431519, + -0.014657854102551937, + -0.0023566402960568666, + 0.026274284347891808, + -0.0449351891875267, + 0.006130301393568516, + 0.0021915079560130835, + -0.05063489079475403, + 0.010083623230457306, + 0.03967271372675896, + -0.047972869127988815, + 0.011878297664225101, + -0.02869013138115406, + -0.06947814673185349, + 0.012776396237313747, + -0.022227533161640167, + -0.021391209214925766, + -0.0071424199268221855, + -0.010884602554142475, + 0.0022353651002049446, + 0.04208262637257576, + 0.04585080221295357, + -0.028864840045571327, + 0.014383035711944103, + 0.0006865983596071601, + -0.003945623058825731, + -0.024596840143203735, + 0.02039221115410328, + 0.05236830934882164, + -0.06231372430920601, + 0.0006878590793348849, + 0.005045242141932249, + 0.04543100297451019, + -0.022787010297179222, + -0.0323825404047966, + 0.0060617332346737385, + -0.0009496629354543984, + 0.1132081151008606, + 0.021422259509563446, + -0.008516624569892883, + 0.011941758915781975, + 0.06050655618309975, + -0.06464048475027084, + 0.0715012326836586, + -0.04892478510737419, + -0.014262699522078037, + 0.02197115309536457, + -0.02258905954658985, + -0.03329572454094887, + 0.0733470693230629, + 0.01521797850728035, + -0.02922399342060089, + 0.05403874069452286, + -0.0024076823610812426, + -0.005156014114618301, + -0.0004758739669341594, + -0.0009397549438290298, + 0.022768890485167503, + -0.06273472309112549, + -0.013565277680754662, + -0.038060612976551056, + 0.03901419788599014, + -0.025413114577531815, + -0.031085047870874405, + 0.062427643686532974, + -0.05666875094175339, + 0.018170330673456192, + 0.03758049011230469, + -0.005046131554991007, + -0.03363005071878433, + 0.0071977670304477215, + -0.007294844835996628, + 0.04950850084424019, + 0.05829211696982384, + -0.028599455952644348, + -0.00011273028212599456, + -0.027114247903227806, + -0.04813091829419136, + 0.03546503558754921, + -0.0017865434056147933, + -0.06174362823367119, + 0.015936153009533882, + 0.05498664081096649, + 0.06208323314785957, + -0.06043750047683716, + -0.07075081020593643, + 0.03265148773789406, + 0.01779918558895588, + -0.004657578654587269, + 0.013401461765170097, + -0.031561195850372314, + -0.010674675926566124, + 0.02138788439333439, + -0.059565648436546326, + 0.003320328425616026, + -0.0016824831254780293, + -0.021733451634645462, + 0.048551496118307114, + -0.003053524298593402, + 0.011647860519587994, + -0.0014629715587943792, + 0.059308186173439026, + 0.0077448501251637936, + -0.01239799801260233, + -0.039145924150943756, + 0.016731932759284973, + 0.062229979783296585, + -0.029277512803673744, + 0.05666857957839966, + 0.021947506815195084, + -0.027742277830839157, + 0.05703498050570488, + -0.02114000730216503, + -0.0011631653178483248, + 0.04833010211586952, + 0.013655254617333412, + 0.042764052748680115, + 0.04422000050544739, + -0.010796190239489079, + -0.0081519465893507, + 0.0005064443103037775, + -0.007894535548985004, + 0.01271637249737978, + 0.0280605535954237, + 0.023104701191186905, + -0.05545410141348839, + 0.03579716384410858, + -0.01674344576895237, + 0.011995082721114159, + -0.04967891052365303, + 0.018647905439138412, + -0.0025427585933357477, + -0.05248319357633591, + -0.004207089077681303, + 0.0029677890706807375, + -0.08436138927936554, + 0.011933421716094017, + -0.046401966363191605, + 0.004982754122465849, + -0.03336072713136673, + 0.007464535068720579, + -0.02536672353744507, + -0.02103051170706749, + -0.0247516930103302, + 0.03470923379063606, + 0.008188062347471714, + 0.04575216770172119, + -0.04027656093239784, + -0.028462760150432587, + -0.00641157990321517, + -0.1032537892460823, + 0.015407266095280647, + -0.017259350046515465, + 0.057880233973264694, + 0.02970932051539421, + 0.003135938895866275, + 0.04052228853106499, + 0.006307818461209536, + 0.09373948723077774, + 0.012201530858874321, + 0.01518191210925579, + 0.005055180750787258, + -0.00017229207151103765, + -0.008860277943313122, + -0.0009321855613961816, + -0.024702103808522224, + -0.02220877818763256, + 0.018036337569355965, + 0.0461902916431427, + -2.3178456103778444e-05, + -0.021639293059706688, + -0.009496558457612991, + -0.0069047678261995316, + -0.005369818769395351, + -0.038412243127822876, + 0.0376049242913723, + -0.02614714205265045, + 0.010913437232375145, + -0.02533271722495556, + -0.08659890294075012, + 0.05744393169879913, + 0.012141053564846516, + 0.060547053813934326, + -0.0005550469504669309, + -0.01619824767112732, + -0.0022558700293302536, + 0.01814994402229786, + 0.06237058714032173, + 0.055474210530519485, + -0.02512912079691887, + 0.010455053299665451, + -0.023948650807142258, + -0.07459914684295654, + -0.006999264471232891, + -0.006154322065412998, + -0.014305580407381058, + -0.042501892894506454, + 0.04605546593666077, + -0.007378050591796637, + 0.013837042264640331, + 0.005601659417152405, + -0.02454686351120472, + 0.0228840634226799, + -0.010892537422478199, + 0.0011435768101364374, + 0.027678560465574265, + 0.015353331342339516, + -0.03731193020939827, + 0.05862969905138016, + -0.02842552959918976, + 0.03124571032822132, + 0.02315538190305233, + 0.012950807809829712, + 0.026965327560901642, + 0.009465894661843777, + -0.010829408653080463, + -0.008594458922743797, + 0.014982074499130249, + 0.021298887208104134, + -0.018343189731240273, + 0.01739460788667202, + 0.07865084707736969, + 0.02205476351082325, + 0.015017225407063961, + -0.011981618590652943, + -0.02248695306479931, + 0.017631210386753082, + -0.02025180496275425, + -0.05385996773838997, + -0.05477667227387428, + -0.042989905923604965, + 0.004830287769436836, + 0.03188111260533333, + 0.048253823071718216, + 0.0027890182100236416, + -0.01684093475341797, + 0.029284454882144928, + -0.014463928528130054, + 0.029999280348420143, + 0.013334669172763824, + -0.030123639851808548, + 0.007939296774566174, + -0.015909308567643166, + 0.03652086481451988, + 0.043923694640398026, + -0.03349898010492325, + 0.016639679670333862, + 0.007404185365885496, + -0.023147881031036377, + 0.004568914417177439, + 0.008112411946058273, + -0.021877270191907883, + -0.0072467140853405, + -0.024027734994888306, + 0.022522028535604477, + 0.03248016908764839, + 0.04624137282371521, + 0.03288194164633751, + -0.0706077441573143, + 0.00647892989218235, + -0.013711459934711456, + -0.00910367164760828, + -0.06070556864142418, + 0.013195404782891273, + 0.02949078381061554, + -0.04314878582954407, + 0.03952472656965256, + -0.039313577115535736, + 0.01958983577787876, + -0.04745025932788849, + 0.011169768869876862, + -0.07735665887594223, + 0.012919869273900986, + 0.08162245899438858, + 0.04961969330906868, + 0.02261139266192913, + -0.01081178616732359, + -0.022089937701821327, + 0.036029793322086334, + 0.07065453380346298, + -0.050287678837776184, + 0.009584897197782993, + -0.005743148736655712, + -0.03252799063920975, + -0.029911693185567856, + -0.0031824579928070307, + -0.0022875897120684385, + 0.010553253814578056, + -0.005088122095912695, + -0.019103137776255608, + -0.029758833348751068, + -0.03040270134806633, + -0.05643913522362709, + -0.0183008573949337, + 0.0036066959146410227, + -0.010227258317172527, + 0.03830184414982796, + 0.008860573172569275, + -0.04022029787302017, + 0.016092464327812195, + -0.007906369864940643, + -0.0206406619399786, + -0.01545781921595335, + 0.011720928363502026, + 0.030331697314977646, + 0.020348263904452324, + 0.013491041027009487, + 0.015015012584626675, + 0.0757412239909172, + -0.013692211359739304, + 0.0554184690117836, + -0.03535052016377449, + 0.027659131214022636, + 0.062012042850255966, + 0.05365491285920143, + 0.02611374668776989, + 0.03400697186589241, + -0.0187185350805521, + 0.030734656378626823, + -0.04378894716501236, + 0.04222285747528076, + 0.06321597844362259, + 0.0926889032125473, + 0.06395434588193893, + -0.045033425092697144, + -0.02227518893778324, + -0.018914448097348213, + -0.024137776345014572, + 0.06653360277414322, + 0.03000609017908573, + 0.016536613926291466, + -0.05106441304087639, + 0.009556908160448074, + -0.003165673930197954, + -0.02989509329199791, + -0.008909299969673157, + -0.002428715117275715, + -0.038857024163007736, + -0.014716073870658875, + -0.02291145734488964, + -0.03815469145774841, + 0.018349675461649895, + -0.001724440953694284, + 0.024225711822509766, + -0.038882117718458176, + 0.013145080767571926, + 0.013105038553476334, + 0.033219680190086365, + -0.04639777913689613, + -0.044315461069345474, + -0.012929159216582775, + 0.003259071381762624, + 0.012331360019743443, + -1.7462354662711732e-05, + -0.02317662350833416, + -0.042660780251026154, + 0.001802539685741067, + -0.041100095957517624, + 0.04925210401415825, + 0.047337062656879425, + -0.01313596311956644, + -0.048633869737386703, + 0.06100405752658844, + -0.024509647861123085, + 0.06903672963380814, + 0.026338376104831696, + -0.05955340713262558, + -0.013524221256375313, + -0.007072206120938063, + -0.0004094979085493833, + 0.02331911027431488, + 0.006079655606299639, + -0.027727166190743446, + 0.01562763936817646, + 0.011910749599337578, + -0.010385152883827686, + 0.02091721072793007, + -0.030102524906396866, + -0.014945127069950104, + 0.007444288115948439, + -0.009210431948304176, + 0.01587914675474167, + -0.07968660444021225, + 0.034870292991399765, + 0.04423568770289421, + 0.05101220682263374, + -0.0018310192972421646, + 0.04378198832273483, + 0.008875945582985878, + -0.018744593486189842, + -0.010748499073088169, + -0.05976865068078041, + -0.024797234684228897, + 0.02921747788786888, + 0.08715134114027023, + -0.014189728535711765, + -0.05772070586681366, + -0.00013612159818876535, + 0.034182313829660416, + 0.02940666675567627, + -0.007551911287009716, + 0.005196248646825552, + 0.09129910916090012, + 0.03463520109653473, + -0.028487645089626312, + -0.054952532052993774, + -0.019425109028816223, + 0.04267658665776253, + -0.010463536716997623, + -0.022979862987995148, + 0.003282969817519188, + 0.032446060329675674, + -0.03184691444039345, + -0.01494336687028408, + 0.027125416323542595, + -0.03301938623189926, + -0.021615097299218178, + 0.01919432356953621, + -0.018361948430538177, + 0.0440165251493454, + 0.018785251304507256, + 0.05379289388656616, + -0.06103529781103134, + -0.04040123522281647, + 0.06767034530639648, + -0.04255857691168785, + 0.059002116322517395, + 0.06269264966249466, + 0.04158494248986244, + 0.016211502254009247, + -0.046843864023685455, + -0.028105739504098892, + 0.007073850836604834, + 0.052667438983917236, + 0.00735336821526289, + 0.017733542248606682, + -0.023568013682961464, + -0.007077949587255716, + 0.01566276140511036, + 0.048224493861198425, + -0.0003875133115798235, + -0.046327680349349976, + -0.08656812459230423, + -0.025123324245214462, + -0.034193720668554306, + 0.03014206700026989, + 0.05021859332919121, + -0.0026385232340544462, + 0.023799851536750793, + -0.009769299067556858, + -0.01290298905223608, + 0.004491783678531647, + -0.012223453260958195, + -0.00033618492307141423, + 0.0233011394739151, + -0.08696971833705902, + 0.058488454669713974, + 0.000664825493004173, + 0.039359770715236664, + 0.014214815571904182, + 0.03424450755119324, + 0.05592956021428108, + 0.016471324488520622, + -0.059732481837272644, + 0.06536833196878433, + 0.024387361481785774, + -0.10856911540031433, + 0.06828989833593369, + 0.0036337117198854685, + 0.05830007046461105, + 0.016170067712664604, + 0.013002794235944748, + -0.11607159674167633, + 0.0019640743266791105, + 0.026027854532003403, + -0.028382647782564163, + 0.041647832840681076, + -0.005042455159127712, + -0.0010717103723436594, + 0.09709432721138, + 0.018342554569244385, + -0.03699033707380295, + 0.03425338864326477, + -0.07419072836637497, + -0.05410637706518173, + 0.013680101372301579, + -0.007827416993677616, + -0.007252392824739218, + 0.016606653109192848, + 0.015743359923362732, + -0.007168450392782688, + 0.030557913705706596, + 0.010715801268815994, + -0.03387424722313881, + -0.059598296880722046, + 0.061636339873075485, + -0.024311335757374763, + -0.08930302411317825, + 0.04300369694828987, + -0.052911426872015, + 0.048922792077064514, + -0.07488273829221725, + 0.0253959558904171, + -0.057005614042282104, + -0.010324039496481419, + -0.03382004797458649, + 0.01331509929150343, + -0.0060559725388884544, + 0.021830739453434944, + 0.0004554805636871606, + 0.06132755056023598, + -0.04885099083185196, + 0.01681993156671524, + -0.09306737780570984, + -0.03891037777066231, + 0.03394221141934395, + 0.03513973951339722, + 9.119489550357684e-05, + -0.009680265560746193, + -0.018936453387141228, + 0.002022465690970421, + 0.03725491091609001, + -0.007916543632745743, + -0.05493376404047012, + 0.06674706935882568, + -0.04586830735206604, + -0.05310272425413132, + -0.002019708277657628, + -0.03419820964336395, + -0.08405481278896332, + 0.044505130499601364, + -0.022271662950515747, + 0.008551442995667458, + 0.024632176384329796, + -0.057307109236717224, + -0.025764044374227524, + 0.05102856457233429, + -0.01996302232146263, + -0.003182733431458473, + 0.010233199223876, + -0.005380541551858187, + -0.033068619668483734, + -0.038329556584358215, + 0.041149478405714035, + -0.038474202156066895, + 0.03263046592473984, + 0.043984752148389816, + -0.06405626237392426, + -0.04378855600953102, + -0.017724154517054558, + -0.00023550254991278052, + -0.006340715568512678, + 0.008379276841878891, + 0.06068692356348038, + -0.023048071190714836, + 0.04665880277752876, + -0.026433007791638374, + -0.04106089845299721, + 0.008102682419121265, + -0.02919689752161503, + -0.002803279785439372, + 0.00115284975618124, + -0.007610488682985306, + -0.009425876662135124, + 0.014759095385670662, + -0.07407978177070618, + 0.040522702038288116, + -0.028428586199879646, + -0.015484650619328022, + -0.08971428871154785, + 0.04541322588920593, + 0.01523630227893591, + -0.02159152925014496, + 0.06348283588886261, + -0.0762605369091034, + 0.008550439029932022, + -0.0010396456345915794, + 0.09191705286502838, + 0.01919129304587841, + 0.012690366245806217, + -0.032078325748443604, + -0.03879883140325546, + -0.06354136019945145, + -0.016241934150457382, + -0.013353055343031883, + 0.013797549530863762, + 0.03027600795030594, + 0.05205754190683365, + 0.018223397433757782, + -0.02529638260602951, + -0.012619049288332462, + 0.05183516442775726, + 0.04441876709461212, + -0.0014240458840504289, + -0.004662310238927603, + 0.007740246132016182, + -0.023739585652947426, + 0.008351752534508705, + 0.04186442866921425, + 0.06846421957015991, + -0.03302106633782387, + -0.019061105325818062, + 0.03688846528530121, + 0.027123648673295975, + -0.008548760786652565, + 0.006452383007854223, + -0.05057734623551369, + 0.009094422683119774, + -0.003088460536673665, + -0.01042612362653017, + 0.03579631447792053, + -0.008917502127587795, + 0.010444638319313526, + -0.023657843470573425, + -0.03254014626145363, + -0.0009533764678053558, + 0.00684812106192112, + 0.01948300190269947, + 0.00943666510283947, + -0.010625068098306656, + 0.02385423146188259, + -0.05145318806171417, + -0.03215208277106285, + 0.007343036122620106, + 0.01264273189008236, + 0.036680057644844055, + 0.022073568776249886, + -0.06296181678771973, + -0.008569572120904922, + -0.012322318740189075, + 0.021164294332265854, + -0.051289938390254974, + 0.0010486009996384382, + 0.0021613994613289833, + 0.030476249754428864, + 0.01092084776610136, + -0.054112132638692856, + -0.06015515327453613, + 0.023149874061346054, + 0.03427460417151451, + -0.019571471959352493, + -0.07272381335496902, + 0.009794066660106182, + -0.04319072142243385, + -0.04802769050002098, + -0.0024639740586280823, + 0.01276618055999279, + 0.030480578541755676, + -0.007069519720971584, + 0.026940204203128815, + -0.013154259882867336, + 0.05308559536933899, + 0.0008981192368082702, + -0.012286764569580555, + -0.010251149535179138, + 0.056114789098501205, + -0.027719540521502495, + -0.06385437399148941, + -0.01707690954208374, + 0.03182663023471832, + 0.04629168286919594, + 0.003105542855337262, + -0.035991836339235306, + 0.030695278197526932, + -0.01389816403388977, + 0.005694018676877022, + 0.024141885340213776, + -0.056052565574645996, + 0.07325056940317154, + -0.052376989275217056, + -0.0827232152223587, + 0.07083716243505478, + -0.011363365687429905, + -0.049301743507385254, + 0.01282532885670662, + 0.029815899208188057, + 0.0025471607223153114, + 0.014735412783920765, + -0.017929038032889366, + -0.017711512744426727, + -0.03859850764274597, + 0.020923320204019547, + -0.024983150884509087, + -0.009905354119837284, + -0.033428773283958435, + 0.0033264297526329756, + -0.057740144431591034, + 0.0011588952038437128, + 0.05510108917951584, + -0.042752135545015335, + 0.00023805272940080613, + 0.02830038219690323, + -0.0023612258955836296, + 0.004450241569429636, + -0.09065061807632446, + 0.05099336430430412, + 0.050836946815252304, + 0.002225160365924239, + -0.02620827779173851, + -0.0017080202233046293, + -0.006798254791647196, + -0.06735426932573318, + -0.012160968966782093, + 0.0198799017816782, + -0.005785979796200991, + 0.030539529398083687, + 0.03791653737425804, + -0.01715696230530739, + -0.013931870460510254, + -0.026593970134854317, + 0.015033211559057236, + 0.04166087508201599, + -0.0009548550006002188, + 0.002680635079741478, + -0.005521025042980909, + -0.005426781252026558 + ], + "chunk_ind": 0 + }, + { + "url": "https://docs.danswer.dev/more/use_cases/customer_support", + "title": "Customer Support", + "content": "Help your customer support team instantly answer any question across your entire product.\n\nAI Enabled Support\nCustomer support agents have one of the highest breadth jobs. They field requests that cover the entire surface area of the product and need to help your users find success on extremely short timelines. Because they're not the same people who designed or built the system, they often lack the depth of understanding needed - resulting in delays and escalations to other teams. Modern teams are leveraging AI to help their CS team optimize the speed and quality of these critical customer-facing interactions.\n\nThe Importance of Context\nThere are two critical components of AI copilots for customer support. The first is that the AI system needs to be connected with as much information as possible (not just support tools like Zendesk or Intercom) and that the knowledge needs to be as fresh as possible. Sometimes a fix might even be in places rarely checked by CS such as pull requests in a code repository. The second critical component is the ability of the AI system to break down difficult concepts and convoluted processes into more digestible descriptions and for your team members to be able to chat back and forth with the system to build a better understanding.\n\nDanswer takes care of both of these. The system connects up to over 30+ different applications and the knowledge is pulled in constantly so that the information access is always up to date.", + "title_embedding": [ + 0.029702378436923027, + 0.04087577760219574, + 0.011759690940380096, + -0.015867559239268303, + 0.051922496408224106, + 0.04818926751613617, + -0.051036059856414795, + -0.000768028199672699, + -0.011680016294121742, + -0.04731091484427452, + -0.06819964945316315, + 0.02706378884613514, + 0.012011447921395302, + -0.0162456426769495, + 0.00561815220862627, + -0.060200855135917664, + 0.011203722096979618, + 0.011659571900963783, + 0.005986262112855911, + 0.010378050617873669, + -0.02058245800435543, + -0.007857420481741428, + -0.011501888744533062, + -0.06029190123081207, + -0.005981787107884884, + 0.02316387929022312, + -0.003978169988840818, + 0.014874234795570374, + -0.02605351060628891, + 0.015183809213340282, + 0.024635987356305122, + 0.009090029634535313, + 0.02292451448738575, + -0.051132138818502426, + -0.01627650111913681, + -0.04312199354171753, + 0.055974528193473816, + -0.007541665807366371, + 0.05875417962670326, + 0.014909300021827221, + 0.04143260419368744, + 0.013145966455340385, + -0.0019000619649887085, + -0.014630978927016258, + 0.036174625158309937, + -0.009382152929902077, + 0.0129568912088871, + -0.01105422992259264, + 0.05389830842614174, + -0.05418487638235092, + -0.019787268713116646, + 0.021062593907117844, + -0.004908672533929348, + -0.05889728665351868, + 0.005012272857129574, + -0.032561108469963074, + 0.045741673558950424, + 0.0023587732575833797, + -0.029787305742502213, + -0.016032742336392403, + -7.657184141862672e-06, + 0.06451895087957382, + -0.061427876353263855, + 0.05008486285805702, + 0.013032016344368458, + -0.008349837735295296, + -0.023183466866612434, + 0.028445789590477943, + 0.013328451663255692, + 0.002017433987930417, + 0.08471205830574036, + 0.02884836308658123, + 0.03370589017868042, + 0.02926166169345379, + -0.019738871604204178, + -0.06608780473470688, + -0.024426797404885292, + -0.008213629014790058, + -0.017787031829357147, + 0.02045559138059616, + 0.04079979658126831, + -0.03456271439790726, + 0.011362932622432709, + -0.022804994136095047, + 0.06335528194904327, + 0.007143533322960138, + -0.038967471569776535, + 0.01895124651491642, + -0.021929487586021423, + 0.020517535507678986, + -0.005601715296506882, + 0.048027630895376205, + 0.05165044218301773, + 0.021509770303964615, + -0.05171488970518112, + 0.022959010675549507, + 0.008313633501529694, + -0.033466871827840805, + -0.00873673614114523, + -0.07275433838367462, + -0.01826190948486328, + -0.0008458571974188089, + 0.03251243755221367, + 0.0027185927610844374, + 0.03351648896932602, + 0.050253089517354965, + 0.03931482136249542, + 0.011611105874180794, + 0.0006847226177342236, + -0.018391452729701996, + -0.04876922070980072, + 0.0032669915817677975, + 0.002616048092022538, + 0.018911289051175117, + 0.0035516773350536823, + 0.04444553330540657, + 0.0874137431383133, + -0.06154795363545418, + -0.0007547208806499839, + 0.05003364384174347, + 0.047423556447029114, + 0.010614278726279736, + -0.002085448009893298, + 0.028551766648888588, + -0.00320938928052783, + -0.0028788738418370485, + -0.032166119664907455, + 0.032534729689359665, + 0.05165233090519905, + -0.02726086415350437, + 0.032850414514541626, + 0.021426480263471603, + 0.008582738228142262, + -0.05970913544297218, + -0.013117690570652485, + 0.0327497161924839, + -0.04084235802292824, + -0.034347862005233765, + 0.08484583348035812, + -0.007416227832436562, + 0.0817202478647232, + 0.013180759735405445, + 0.01752362586557865, + -0.011748716235160828, + 0.006734360009431839, + -0.05940733850002289, + -0.01464597787708044, + 0.021172411739826202, + 0.015961064025759697, + 0.013145568780601025, + -0.03292446956038475, + 0.05433695763349533, + -0.04581886902451515, + -0.011024394072592258, + -0.013903305865824223, + -0.04525483399629593, + -0.009453397244215012, + -0.01541796326637268, + 0.024864252656698227, + 0.016035286709666252, + 0.04684724658727646, + 0.04711056500673294, + -0.08100881427526474, + 0.07197079807519913, + -0.00942996796220541, + -0.04369058832526207, + 0.02740531787276268, + 0.027486257255077362, + 0.035378992557525635, + 0.05205152928829193, + 0.000229495475650765, + -0.015225332230329514, + 0.018225882202386856, + 0.019075268879532814, + 0.05653514340519905, + 0.00206256122328341, + 0.04172705486416817, + 0.025263279676437378, + 0.02995399944484234, + -0.02344629354774952, + -0.00580610940232873, + -0.03100346215069294, + 0.024410588666796684, + 0.05101815611124039, + -0.044721707701683044, + -0.03469102457165718, + 0.015877151861786842, + -0.05606666952371597, + -0.04264648258686066, + 8.914931095205247e-05, + 0.005455580540001392, + 0.02580810897052288, + 0.03810019791126251, + -0.005504349246621132, + -0.03873325511813164, + -0.06938246637582779, + 0.06987633556127548, + -0.0071804821491241455, + 0.025614110752940178, + -0.04443173483014107, + 0.014129945077002048, + 0.04964412376284599, + -0.06445024162530899, + 0.03494735807180405, + 0.00042216022848151624, + 0.03607922047376633, + 0.014481625519692898, + -0.03348603844642639, + 0.04130083695054054, + 0.03306325525045395, + 0.0670546144247055, + -0.004632187075912952, + -0.02899966388940811, + 0.028892826288938522, + -0.02801397442817688, + -0.009044334292411804, + -0.0299741979688406, + 0.006851669866591692, + -0.051097121089696884, + 0.041360609233379364, + 0.040426693856716156, + -0.04066675901412964, + 0.01568625681102276, + -0.016009517014026642, + -0.004742924124002457, + 0.048653047531843185, + -0.010993007570505142, + 0.039591673761606216, + 0.0007891886634752154, + 0.0280364528298378, + -0.029024146497249603, + -0.07559369504451752, + 0.020083241164684296, + -0.02160985954105854, + 0.00466573191806674, + 0.017442384734749794, + -0.02421753853559494, + 0.05211988091468811, + 0.0016645005671307445, + 0.08051992207765579, + 0.02786155417561531, + 0.022991932928562164, + 0.04568661376833916, + -0.03650546818971634, + -0.061528630554676056, + 0.026744728907942772, + -0.029581749811768532, + -0.04499091953039169, + 0.002152943518012762, + -0.015043909661471844, + 0.047530874609947205, + 0.041445743292570114, + 0.041881438344717026, + 0.03457123413681984, + -0.023201758041977882, + -0.05317879468202591, + -0.020216727629303932, + 0.050812073051929474, + 0.0008769077248871326, + -0.01832399144768715, + 0.026449931785464287, + -0.00376958679407835, + 0.04373340308666229, + -0.015004824846982956, + 0.02940281480550766, + -0.028869349509477615, + -0.02610083483159542, + -0.0077619897201657295, + 0.03147227317094803, + -0.0032539069652557373, + 0.02559952437877655, + 0.02357475273311138, + 0.0001173858399852179, + 0.047926079481840134, + 0.03721074387431145, + -0.019753489643335342, + 0.017013119533658028, + -0.028762344270944595, + -0.005848998669534922, + -0.006997200194746256, + 0.05184704810380936, + -0.05036364868283272, + 0.002436417154967785, + 0.0003822402795776725, + 0.003277599113062024, + 0.03293520584702492, + -0.0045876270160079, + -0.004722336772829294, + -0.019277948886156082, + 0.0012148021487519145, + -0.023630889132618904, + -0.011700155213475227, + -0.006263254676014185, + 0.02274380624294281, + 0.004808057565242052, + 0.03601561859250069, + 0.1043647825717926, + -0.014201398938894272, + -0.016617566347122192, + -0.02272864058613777, + -0.030905725434422493, + 0.0010793384863063693, + -0.049122776836156845, + -0.005753105040639639, + 0.01338914968073368, + 0.027050666511058807, + 0.04214894399046898, + -0.023005545139312744, + 0.031917206943035126, + 0.015109232626855373, + -0.07634111493825912, + 0.024369796738028526, + -0.00647472171112895, + 0.043127499520778656, + -0.0673207938671112, + 0.0822305828332901, + 0.06597486138343811, + 0.004127069376409054, + 0.06724239140748978, + 0.004546293988823891, + 0.03501193970441818, + -0.03256544470787048, + 0.02815675362944603, + -0.018141930922865868, + 0.008695757016539574, + 0.030166303738951683, + -0.009897452779114246, + 0.03613714128732681, + -0.013987270183861256, + -0.02539311721920967, + -0.06444346904754639, + -0.01528739370405674, + -0.06564117968082428, + -0.029204169288277626, + 0.03283213824033737, + -0.018580380827188492, + 0.026825398206710815, + -0.012654704041779041, + -0.0018552436958998442, + -0.01754637062549591, + 0.08191259950399399, + 0.0534062460064888, + -0.027856973931193352, + -0.053807660937309265, + -0.02944841794669628, + -0.014591488987207413, + -0.0004364093765616417, + -0.01691609062254429, + 0.0792316198348999, + 0.004102316685020924, + -0.03579891845583916, + -0.0108651639893651, + -0.00966869480907917, + -0.00033933919621631503, + -0.026145832613110542, + -0.016428470611572266, + 0.030308935791254044, + -0.02421530708670616, + -0.01272093690931797, + 0.0026039716321974993, + 0.029183251783251762, + -0.015125368721783161, + 0.07109745591878891, + 0.02079625427722931, + 0.018054857850074768, + -0.00201214081607759, + 0.028579678386449814, + -0.011699595488607883, + 0.010970978997647762, + -0.008872047066688538, + 0.03169122710824013, + -0.06434084475040436, + 0.03283708542585373, + 0.002920384518802166, + 0.1117773950099945, + 0.0207917969673872, + -0.07546871900558472, + -0.0013152466854080558, + -0.009336701594293118, + 0.00034176796907559037, + 0.06051360070705414, + -0.0378379300236702, + -0.01082307007163763, + -0.009045763872563839, + -0.042135000228881836, + -0.04675054922699928, + 0.0008745589875616133, + 0.022651556879281998, + 0.016891758888959885, + -0.06758315861225128, + 0.03011692874133587, + -0.0689280554652214, + -0.0287728663533926, + -0.016613522544503212, + 0.009947648271918297, + -0.009978469461202621, + 0.016907479614019394, + 0.00691134762018919, + 0.04193537309765816, + -0.0010126983979716897, + -0.01135191135108471, + -0.04884914308786392, + 0.05164073780179024, + 0.06193321943283081, + -0.01663290709257126, + 0.0512203685939312, + 0.00277346046641469, + -0.0766502171754837, + 0.0011106275487691164, + -0.008470023050904274, + 0.03819086030125618, + -0.006837388966232538, + -0.03457418084144592, + -0.06866854429244995, + 0.05483240634202957, + -0.016624240204691887, + 0.028569897636771202, + -0.01400308683514595, + 0.0378500260412693, + 0.007686481345444918, + 0.030080482363700867, + -0.05881612002849579, + 0.015524756163358688, + 0.030225753784179688, + -0.02950134687125683, + 0.01465617585927248, + 0.0009167538373731077, + 0.056613512337207794, + -0.02706410363316536, + -0.0473414771258831, + -0.006343611981719732, + 0.011811802163720131, + 0.007573770359158516, + 0.021041858941316605, + -0.014327406883239746, + 0.01859954372048378, + 0.06863977015018463, + -0.002199358306825161, + -0.03532129153609276, + 0.009050965309143066, + 0.02409159019589424, + -0.0025098449550569057, + -0.00499211298301816, + 0.00033862097188830376, + -0.059937484562397, + 0.10898157954216003, + 0.0318506620824337, + 0.0058680190704762936, + -0.03671310096979141, + -0.03349997103214264, + -0.0349581353366375, + -0.023411044850945473, + -0.011138128116726875, + 0.00608166866004467, + 0.08696430921554565, + -0.008161027915775776, + 0.045368045568466187, + -0.01864445023238659, + 0.035301174968481064, + 0.003979773260653019, + 0.016739632934331894, + 0.011675872839987278, + 0.025817174464464188, + 0.03272102400660515, + 0.013721601106226444, + -0.04690241813659668, + 0.05665350705385208, + -0.05676185339689255, + 0.013739561662077904, + 0.020678944885730743, + -0.03532474488019943, + 0.013464651070535183, + 0.04246523231267929, + 0.017674343660473824, + -0.005077862646430731, + -0.019556084647774696, + -0.009594413451850414, + -0.04825031757354736, + 0.00016230896289926022, + 0.003143883077427745, + 0.031157106161117554, + -0.0332491435110569, + -0.010140872560441494, + -0.04249225929379463, + -0.028256090357899666, + -0.008995918557047844, + 0.021160980686545372, + 0.03130994364619255, + -0.001629085629247129, + 0.02819039300084114, + 0.009931858628988266, + 0.05051739886403084, + 0.006850008387118578, + -0.018732454627752304, + -0.09201951324939728, + -0.042829085141420364, + -0.054845187813043594, + 0.021562401205301285, + 0.05139476805925369, + -0.011137720197439194, + 0.021749140694737434, + -0.01837606355547905, + 0.017083071172237396, + 0.023444999009370804, + -0.009212017990648746, + -0.011377239599823952, + -0.018595905974507332, + -0.09953112155199051, + 0.0019816216081380844, + -0.004408092238008976, + -0.027098996564745903, + -0.002341427141800523, + 0.029412943869829178, + 0.041135817766189575, + 0.015357858501374722, + 0.0017108122119680047, + 0.028364799916744232, + 0.004185053985565901, + -0.04822831228375435, + 0.0948278158903122, + -0.0414741188287735, + 0.03572544828057289, + 0.04517536610364914, + 0.009942572563886642, + -0.025769881904125214, + -0.017749540507793427, + -0.03137620911002159, + -0.00617972994223237, + 0.04517003893852234, + -0.03762981668114662, + 0.0358721986413002, + 0.11737086623907089, + 0.0004563555121421814, + -0.06275733560323715, + -0.011418106034398079, + -0.08354005962610245, + -0.048093460500240326, + -0.030154218897223473, + -0.010961515828967094, + 0.007697841618210077, + -0.08613990992307663, + 0.01947987824678421, + 0.017181523144245148, + 0.02698543854057789, + 0.040134966373443604, + -0.03223738074302673, + -0.03745822235941887, + 0.054219458252191544, + -0.03571298345923424, + -0.035921428352594376, + 0.04604002833366394, + -0.04030536487698555, + -0.032255616039037704, + -0.06959861516952515, + 0.032114237546920776, + -0.027767114341259003, + 0.019928939640522003, + 0.022700339555740356, + -0.04375129193067551, + -0.05712258815765381, + -0.02559071220457554, + 0.006574000231921673, + -0.025430524721741676, + -0.028035728260874748, + -0.04453514888882637, + -0.10015997290611267, + -0.0672021210193634, + 0.012007188983261585, + 0.014830735512077808, + 0.00970692653208971, + -0.051091041415929794, + -0.031854890286922455, + -0.025864001363515854, + -0.016826078295707703, + -0.0026011785957962275, + -0.05528291314840317, + 0.04440443217754364, + -0.03783581778407097, + -0.09876326471567154, + 0.029767369851469994, + -0.0023010883014649153, + -0.05689188838005066, + 0.007344242185354233, + 0.009551416151225567, + -0.08018877357244492, + 0.007934950292110443, + -0.03663663938641548, + -0.0009275389602407813, + 0.026911364868283272, + -0.001246148720383644, + 0.054533813148736954, + 0.009721122682094574, + 0.005318093113601208, + -0.00535608222708106, + 0.008591657504439354, + 0.04166155681014061, + -0.03877246752381325, + 0.01399280782788992, + 0.01457316055893898, + -0.02407732978463173, + -0.006206234451383352, + 0.07004162669181824, + 0.01619933731853962, + -0.004103302024304867, + 0.045894261449575424, + 0.03686122968792915, + 0.04804258793592453, + 0.05579492822289467, + -0.0030228029936552048, + -0.07259590923786163, + 0.023546412587165833, + -0.0011336577590554953, + 0.04003886505961418, + -0.0139979999512434, + -0.00017333473078906536, + -0.05454326048493385, + -0.021969035267829895, + -0.03901325911283493, + 0.012417349964380264, + -0.05304381251335144, + 0.004690664820373058, + -0.06269649416208267, + 0.037584088742733, + -0.039430856704711914, + 0.01138926949352026, + 0.024504829198122025, + -0.023247476667165756, + -0.001942053553648293, + 0.01666364073753357, + 0.005435148254036903, + -0.026095639914274216, + -0.002955301431939006, + -0.043733760714530945, + -0.06700831651687622, + -0.06828623265028, + 0.045247308909893036, + -0.02567214146256447, + -0.03503000736236572, + 0.0028738975524902344, + 0.007734893821179867, + 0.041422292590141296, + -0.01760552078485489, + -0.016545895487070084, + -0.007150533143430948, + 0.02324298955500126, + 0.009319701232016087, + 0.003866465063765645, + 0.025515582412481308, + 0.03634219616651535, + -0.033345021307468414, + 0.020966341719031334, + 0.07540836185216904, + -0.0002573730598669499, + 0.05161430686712265, + 0.0003421941655687988, + -0.016416313126683235, + -0.018457459285855293, + -0.04053647443652153, + -0.008631067350506783, + 0.011850157752633095, + 0.014364494942128658, + -0.029469167813658714, + -0.0497945100069046, + 0.008882390335202217, + 0.04006727412343025, + 0.010511534288525581, + -0.03620539978146553, + -0.030285054817795753, + -0.10150802135467529, + -0.01594187133014202, + -0.05266118794679642, + -0.017643682658672333, + 0.017300395295023918, + -0.080828458070755, + 0.027883851900696754, + 0.0260021835565567, + -0.013791227713227272, + 0.01261923462152481, + 0.02038010023534298, + -0.04244862496852875, + 0.011010567657649517, + 0.011758117005228996, + 0.0030098427087068558, + 0.003606629790738225, + 0.0020418025087565184, + -0.0004243037255946547, + 0.03312380611896515, + 0.02103457599878311, + 0.03972248733043671, + -0.07605717331171036, + -0.039676181972026825, + -0.07193399965763092, + -0.030211182311177254, + -0.0786738321185112, + -0.025149084627628326, + -0.0017661137972027063, + -0.017345670610666275, + 0.027870142832398415, + -0.003350367769598961, + 0.060104407370090485, + 0.020051708444952965, + 0.014986025169491768, + 0.0056610992178320885, + 0.0593392550945282, + -0.0053368182852864265, + -0.025954807177186012, + -0.07451668381690979, + -0.0021227921824902296, + -0.03457536920905113, + 0.010495556518435478, + -0.0450577586889267, + -0.016477687284350395, + 0.05702868103981018, + 0.025161782279610634, + 0.016737932339310646, + -0.00856244657188654, + 0.01180358324199915, + -0.04093103110790253, + -0.03350433334708214, + -0.01662720926105976, + 0.002310116309672594, + 0.0026625224854797125, + -0.04226106405258179, + 0.02971433289349079, + -0.07220850884914398, + -0.0009123267373070121, + -0.02786707505583763, + -0.025111757218837738, + 0.033243875950574875, + 0.03572067618370056, + -0.0019114067545160651, + -0.030592206865549088, + -0.021260922774672508, + 0.06805034726858139, + 0.00013317271077539772, + 0.006557960994541645, + -0.0329759456217289, + 0.006780629511922598, + 0.00866342056542635, + -0.01449753437191248, + 0.028198137879371643, + 0.019570309668779373, + -0.036116212606430054, + 0.058676715940237045, + 0.021564209833741188, + -0.026323653757572174, + -0.02302497997879982, + 0.02744974195957184, + 0.05593085661530495, + 0.02073318511247635, + -0.074001245200634, + -0.0184424240142107, + 0.031868427991867065, + 0.018198778852820396, + -0.0450170636177063, + 0.030543111264705658, + -0.06377965956926346, + 0.04590768367052078, + -0.005907150451093912, + -0.01748581975698471, + 0.006950956769287586, + 0.05506323277950287, + 0.04594920575618744, + -0.015593858435750008, + -0.017087753862142563, + 0.029356854036450386, + -0.06531023979187012, + 0.005519233178347349 + ], + "content_embedding": [ + 0.019554156810045242, + 0.04886673390865326, + 0.00547438021749258, + -0.02931770123541355, + 0.024625789374113083, + 0.008072949014604092, + 0.03052533231675625, + -0.006179450079798698, + -0.0333777479827404, + -0.021061548963189125, + -0.05983448028564453, + 0.025203319266438484, + 0.032834798097610474, + 0.013029776513576508, + -0.011046950705349445, + -0.031452618539333344, + -8.028985030250624e-05, + 0.0007977305795066059, + -0.009920830838382244, + -0.0018231356516480446, + -0.006695937365293503, + -0.014926698990166187, + -0.009614776819944382, + -0.05784115567803383, + 0.02651236765086651, + -0.011027690954506397, + -0.009276495315134525, + 0.04284600168466568, + -0.05643690750002861, + 0.04219788312911987, + 0.05048283189535141, + 0.004557965788990259, + -0.01679980754852295, + -0.040684137493371964, + -0.044776126742362976, + -0.018855446949601173, + 0.06871335208415985, + -0.014481916092336178, + -0.024082450196146965, + 0.04807353392243385, + 0.04378245398402214, + -0.0010759941069409251, + 0.014099782332777977, + -0.037625934928655624, + 0.05659622326493263, + 0.01868855021893978, + 0.025368744507431984, + -0.03537469357252121, + 0.014213587157428265, + -0.0705343633890152, + -0.016253503039479256, + -0.005150542128831148, + -0.017522070556879044, + -0.03862348571419716, + 0.00953003577888012, + 0.016891248524188995, + -0.007589798420667648, + 0.006262748036533594, + 0.01169696543365717, + -0.05435675010085106, + 0.03128333017230034, + 0.07449059188365936, + -0.043514277786016464, + 0.022657765075564384, + 0.01074683852493763, + -0.051405169069767, + 0.00816179346293211, + -0.014555123634636402, + -0.01839461177587509, + -0.00691940588876605, + 0.009614893235266209, + -0.0071630412712693214, + 0.02593475580215454, + 0.07137756794691086, + -0.049324654042720795, + -0.04460940882563591, + -0.004007663112133741, + -0.018305329605937004, + -0.029537511989474297, + 0.03624692186713219, + 0.04646339640021324, + -0.053126320242881775, + -0.008358806371688843, + -0.001911070430651307, + 0.05718495324254036, + -0.02093559131026268, + -0.028956729918718338, + 0.005082732532173395, + -0.028617851436138153, + 0.1116873174905777, + 0.006924519315361977, + 0.05388922244310379, + 0.04239538311958313, + 0.03629518672823906, + -0.07756507396697998, + 0.08572934567928314, + -0.034708015620708466, + -0.052686456590890884, + -0.03376411274075508, + -0.011243571527302265, + -0.028565097600221634, + 0.03532436862587929, + 0.025328388437628746, + -0.009712263941764832, + 0.0416463203728199, + 0.02975877933204174, + 0.04073808714747429, + 0.045180853456258774, + 0.01522457879036665, + 0.0021614122670143843, + -0.0602865032851696, + -0.024015003815293312, + -0.032889459282159805, + 0.020978014916181564, + -0.04493942856788635, + 0.012820002622902393, + 0.0644337609410286, + -0.019941547885537148, + -0.004083186853677034, + 0.018924430012702942, + -0.017330998554825783, + 0.0008878704975359142, + 0.02702835015952587, + -0.026265576481819153, + 0.04109559580683708, + -0.009575187228620052, + -0.020085688680410385, + -5.433974365587346e-05, + 0.018562229350209236, + -0.02393198385834694, + -0.030048735439777374, + 0.01821220852434635, + -0.029501279816031456, + -0.01944204978644848, + -0.01614498719573021, + 0.03840102627873421, + -0.04210539907217026, + -0.050642915070056915, + 0.026918280869722366, + -0.008575397543609142, + 0.011357792653143406, + 0.015665695071220398, + 0.01620817743241787, + -0.0165872685611248, + 0.028748027980327606, + -0.10036404430866241, + -0.04525408893823624, + 0.010306733660399914, + -0.04815903678536415, + 0.025287121534347534, + -0.010369544848799706, + 0.023846469819545746, + 0.016379185020923615, + 0.019874077290296555, + 0.004489564802497625, + -0.009458004496991634, + -0.032719556242227554, + -0.0319439135491848, + 0.06740261614322662, + 0.005906871519982815, + 0.024023521691560745, + 0.04657802730798721, + -0.08182766288518906, + 0.062149085104465485, + -0.0061394101940095425, + 0.014895983040332794, + 0.029691752046346664, + 0.0031379619613289833, + 0.04791149124503136, + 0.06459061801433563, + -0.012314707040786743, + 0.016569096595048904, + -0.01054114755243063, + -0.027581606060266495, + 0.02896907925605774, + 0.0048512346111238, + 0.04427911341190338, + -0.026665540412068367, + 0.07613496482372284, + -0.023571502417325974, + -0.004409146960824728, + -0.036679890006780624, + 0.0016537840710952878, + 0.024527747184038162, + -0.02983722649514675, + 0.0021592022385448217, + 0.005430649966001511, + -0.08198896050453186, + -0.017340485006570816, + -0.014370240271091461, + 0.012875599786639214, + -0.008910057134926319, + -0.013228043913841248, + -0.0023926664143800735, + -0.015292157419025898, + -0.03927253186702728, + 0.07715654373168945, + -0.012554320506751537, + 0.03217530623078346, + -0.042463112622499466, + -0.03743144869804382, + 0.008893481455743313, + -0.0666876956820488, + 0.02818153239786625, + -0.009054000489413738, + 0.03337392210960388, + 0.03328379616141319, + 0.009759150445461273, + 0.01269217487424612, + -0.02173757553100586, + 0.07456912100315094, + 0.006997218355536461, + 0.007162875030189753, + 0.040701836347579956, + -0.04538433253765106, + -0.0032951829489320517, + 0.002400761004537344, + -0.04169681295752525, + -0.05523253232240677, + 0.06444490700960159, + 0.03810356929898262, + -0.035072412341833115, + 0.04415622353553772, + -0.02322838269174099, + -0.009917438961565495, + 0.008140898309648037, + -0.02388846129179001, + 0.0034457307774573565, + -0.0054973880760371685, + 0.024084730073809624, + -0.007739664521068335, + -0.06571771949529648, + 0.07359053194522858, + -0.011194998398423195, + 0.0211270023137331, + 0.017875710502266884, + -0.01821357198059559, + 0.03745369240641594, + 0.023267023265361786, + 0.07556653767824173, + 0.042081139981746674, + 0.01543054636567831, + 0.038234904408454895, + -0.019599558785557747, + -0.08676281571388245, + -0.013498742133378983, + -0.011986842378973961, + -0.014071784913539886, + -0.03772296756505966, + 0.009192361496388912, + -0.020469751209020615, + -0.004528891295194626, + 0.003913218155503273, + 0.013755199499428272, + 0.009065939113497734, + -0.049990858882665634, + 0.030110390856862068, + 0.05044790729880333, + 0.020461000502109528, + -0.036168310791254044, + 0.04875757917761803, + -0.023571951314806938, + 0.04313709959387779, + 0.02649555914103985, + 0.0055029122158885, + 0.0138795655220747, + -0.0009625149541534483, + -0.019915221258997917, + -0.0024100886657834053, + -0.00426845159381628, + 0.0008668623049743474, + 0.014360995963215828, + 0.01953921653330326, + 0.05843087658286095, + 0.010600714012980461, + -0.01941727101802826, + 0.016723858192563057, + -0.027911949902772903, + 0.011009825393557549, + -0.0070054735988378525, + -0.02280472218990326, + -0.0902462899684906, + -0.029843643307685852, + -0.005726281087845564, + -0.007387514691799879, + 0.05724000930786133, + -0.016834275797009468, + 0.015216480940580368, + 0.02209043875336647, + 0.004264513496309519, + 0.019342858344316483, + 0.018849363550543785, + -0.04794900864362717, + 0.02397482842206955, + -0.007828679867088795, + 0.020298736169934273, + 0.09897984564304352, + -0.04056645929813385, + -0.011319068260490894, + 0.0034366592299193144, + -0.0073711141012609005, + -0.005176732316613197, + 0.022680383175611496, + -0.01522906869649887, + 0.002589346142485738, + -0.016521241515874863, + 0.021019242703914642, + -0.004480182658880949, + 0.009419859386980534, + 0.013903859071433544, + -0.05053260177373886, + 0.0012486587511375546, + 0.017442021518945694, + -0.016688739880919456, + -0.034772295504808426, + 0.03298048675060272, + 0.04604269936680794, + -0.008270222693681717, + 0.024096740409731865, + 0.022777941077947617, + 0.03941553831100464, + -0.030161242932081223, + -0.01781023107469082, + -0.03533001244068146, + 0.02088671736419201, + 0.0896298736333847, + 0.0061553712002933025, + 0.054883576929569244, + -0.04094908386468887, + 0.04382561892271042, + -0.003113290062174201, + 0.015607516281306744, + -0.04469290003180504, + -0.013229981996119022, + -0.0026423041708767414, + -0.017652839422225952, + 0.005086386110633612, + 0.035375673323869705, + 9.725322161102667e-05, + -0.026332346722483635, + 0.01958891935646534, + 0.041558533906936646, + -0.02570311166346073, + -0.04806942865252495, + -0.035452235490083694, + -0.015692519024014473, + -0.0027702273800969124, + 0.022831231355667114, + 0.05247980356216431, + 0.0010726081673055887, + -0.025438379496335983, + 0.006880710367113352, + 0.009276037104427814, + -0.021758491173386574, + -0.008571256883442402, + 0.003312689019367099, + 0.032590776681900024, + 0.02640446089208126, + 0.0034450399689376354, + 0.028627941384911537, + 0.07457757741212845, + -0.012303084135055542, + 0.045139290392398834, + -3.2679530704626814e-05, + 0.024825602769851685, + 0.04402294382452965, + 0.025363540276885033, + 0.03840187191963196, + 0.019677763804793358, + -0.03521053493022919, + 0.036523785442113876, + -0.06001857668161392, + 0.006586587987840176, + 0.022668125107884407, + 0.06063239648938179, + 0.015586800873279572, + -0.08306828886270523, + -0.04289577156305313, + -0.0050475094467401505, + -0.0309798214584589, + 0.05810924991965294, + -0.017818300053477287, + -0.01088999304920435, + -0.017884155735373497, + 0.04356890171766281, + -0.023094575852155685, + -0.04477296397089958, + -0.0007801170577295125, + 0.018146106973290443, + -0.05633535981178284, + 0.006709645502269268, + -0.037334758788347244, + -0.055724598467350006, + 0.00994165986776352, + -0.009849119931459427, + -0.027259083464741707, + -0.02565668150782585, + 0.005235382355749607, + 0.016267497092485428, + 0.00393668282777071, + -0.05648971349000931, + -0.05955129489302635, + 0.026542942970991135, + 0.040565431118011475, + -0.02225298061966896, + 0.0017030639573931694, + -0.02689032256603241, + -0.029025251045823097, + 0.030817490071058273, + -0.007936912588775158, + 0.05566547438502312, + 0.0174697358161211, + -0.014709461480379105, + -0.07380940765142441, + 0.07026955485343933, + -0.024563433602452278, + 0.05333513021469116, + 0.020963717252016068, + -0.015575055032968521, + -0.04304461553692818, + 0.00822180975228548, + -0.013204170390963554, + -0.0028262599371373653, + 0.015431943349540234, + -0.025627007707953453, + 0.0006762628327123821, + -0.02078782208263874, + 0.009704814292490482, + -0.006950112525373697, + -0.020425891503691673, + 0.044901806861162186, + 0.020927794277668, + 0.009534145705401897, + 0.004958992823958397, + -0.037563592195510864, + 0.03806327283382416, + 0.0783824622631073, + 0.011150919832289219, + -0.024385575205087662, + 0.03461897745728493, + 0.02127663977444172, + -0.012272517196834087, + -0.01546854991465807, + -0.06705902516841888, + -0.01649612747132778, + 0.06068763509392738, + 0.07799869775772095, + 0.0014717800077050924, + -0.04836009815335274, + -0.026833070442080498, + 0.013509837910532951, + 0.04280327260494232, + 0.009658309631049633, + -0.007854060269892216, + 0.09166036546230316, + -0.00760420598089695, + 0.024465130642056465, + -0.041591379791498184, + 0.007116211112588644, + 0.05567977577447891, + 0.01807284727692604, + 0.028304288163781166, + -0.014866949990391731, + 0.026369474828243256, + 0.008983064442873001, + -0.02317068539559841, + 0.03937782347202301, + -0.01901034638285637, + -0.0021325594279915094, + 0.030924763530492783, + -0.020755570381879807, + 0.030001072213053703, + 0.03809978440403938, + 0.0334426648914814, + -0.042968180030584335, + -0.012311535887420177, + 0.03697645664215088, + -0.041293930262327194, + 0.01696925237774849, + 0.03560850769281387, + 0.03847989812493324, + -0.037730954587459564, + -0.05352506786584854, + -0.02746652066707611, + -0.05294184759259224, + -0.017248092219233513, + -0.005418767221271992, + 0.01951681822538376, + -0.017932193353772163, + -0.007422131486237049, + 0.03827866166830063, + 0.05701953545212746, + -0.02210610918700695, + 0.010034722276031971, + -0.07954911887645721, + -0.0485968291759491, + -0.028629625216126442, + 0.009054362773895264, + 0.02398092858493328, + -0.009973667562007904, + 0.0011409823782742023, + -0.011182617396116257, + 0.0020028105936944485, + 0.006942914333194494, + -0.039862822741270065, + -0.0066703930497169495, + -0.004236259963363409, + -0.1050848662853241, + 0.025538505986332893, + 0.029989799484610558, + 0.01211432833224535, + 0.04559238627552986, + 0.050545401871204376, + 0.05476491525769234, + 0.01163802482187748, + -0.054837070405483246, + 0.07410066574811935, + 0.0024028397165238857, + -0.10432479530572891, + 0.07078853249549866, + -0.012614017352461815, + 0.06030529364943504, + 0.054839566349983215, + 0.014005501754581928, + -0.1118561178445816, + 0.009275965392589569, + -0.023663705214858055, + -0.028527697548270226, + 0.0584726445376873, + -0.045622922480106354, + 0.03320262208580971, + 0.11574956774711609, + 0.007655338849872351, + -0.07191741466522217, + 0.03859880194067955, + -0.06297247856855392, + -0.018405890092253685, + -0.028816718608140945, + -0.0126464469358325, + 0.0202946774661541, + -0.03483844920992851, + 0.024250855669379234, + -0.006263037212193012, + 0.02315174601972103, + -0.0037849699147045612, + -0.0359908789396286, + -0.037620242685079575, + 0.05056930333375931, + -0.006831671576946974, + -0.10494183748960495, + 0.07645728439092636, + -0.028021620586514473, + 0.009692930616438389, + -0.10232461243867874, + 0.05202733352780342, + -0.05352945625782013, + 0.02073156274855137, + -0.017188169062137604, + 0.0020886484999209642, + -0.04133611172437668, + -0.044309552758932114, + 0.018564041703939438, + 0.026704275980591774, + -0.055197130888700485, + 0.007287430576980114, + -0.1245347261428833, + -0.037194203585386276, + 0.06665091216564178, + 0.061706364154815674, + 0.01804385520517826, + -0.013962237164378166, + -0.024994580075144768, + -0.011294208467006683, + -0.009245212189853191, + 0.029879143461585045, + -0.046995047479867935, + 0.02158532105386257, + -0.002750945743173361, + -0.08373189717531204, + 0.006320012733340263, + -0.029947226867079735, + -0.09511808305978775, + 0.03186006098985672, + 0.0028628590516746044, + -0.02251911163330078, + 0.03152289241552353, + -0.07237773388624191, + 0.013269931077957153, + 0.09650041908025742, + -0.045900944620370865, + -0.006541605107486248, + 0.006844623479992151, + 0.03238837793469429, + -0.020313216373324394, + -0.013520441018044949, + 0.000403873244067654, + -0.024447409436106682, + -0.014962681569159031, + 0.006884200032800436, + -0.04582136869430542, + -0.02838127687573433, + 0.02936256304383278, + 0.04077419266104698, + 0.02266734093427658, + 0.013416043482720852, + 0.0345231331884861, + 0.052821315824985504, + 0.028492338955402374, + -0.01292923279106617, + -0.03745116665959358, + 0.0028044944629073143, + 0.006625712383538485, + 0.017212992534041405, + -0.00239459122531116, + -0.002529381774365902, + -0.029911531135439873, + 0.029142336919903755, + -0.07905209809541702, + 0.01719854585826397, + -0.03854485601186752, + -0.0116807846352458, + -0.046873632818460464, + 0.05275706946849823, + -0.04152297228574753, + -0.03727864846587181, + 0.048614900559186935, + -0.010790652595460415, + -0.0024877521209418774, + 0.012286793440580368, + 0.08292551338672638, + 0.03208302706480026, + 0.02867130935192108, + -0.039545897394418716, + -0.02800118923187256, + -0.07673710584640503, + 0.005896291229873896, + -0.030191265046596527, + -0.0187264122068882, + -0.03647911176085472, + 0.0371234230697155, + 0.05115009844303131, + -0.04013253375887871, + -0.03304912894964218, + 0.05173036456108093, + 0.04860515147447586, + -0.00717319268733263, + 0.045631736516952515, + 0.04671349748969078, + 0.004948618821799755, + 0.009837846271693707, + 0.04381090775132179, + 0.0918705016374588, + -0.005869758781045675, + 0.02249985560774803, + 0.010875782929360867, + 0.02956228516995907, + 0.0036174776032567024, + 0.011353887617588043, + -0.05186513066291809, + 0.0173268411308527, + 0.011808891780674458, + -0.00798418466001749, + -0.00929324608296156, + -0.004763087723404169, + 0.010464239865541458, + -0.001494695316068828, + -0.024331238120794296, + -0.042497288435697556, + -0.049635156989097595, + 0.006581253372132778, + -0.05040008947253227, + -0.01882144808769226, + -0.02419630065560341, + -0.06420613825321198, + 0.020046783611178398, + 0.024303266778588295, + -0.009806456044316292, + -0.003666533390060067, + 0.0018573087872937322, + -0.02440156601369381, + 0.0059090061113238335, + -0.03926969692111015, + 0.011777290143072605, + -0.032393939793109894, + -0.0015500712906941772, + 0.019816264510154724, + 0.0037668957374989986, + -0.0033931683283299208, + -0.01164526678621769, + -0.07331964373588562, + -0.008798380382359028, + -0.016916625201702118, + -0.034663647413253784, + -0.05818398669362068, + 0.015174336731433868, + -0.010697754099965096, + -0.04179975762963295, + 0.0064012641087174416, + 0.01987038180232048, + 0.019733907654881477, + -0.0013441460905596614, + 0.05315450206398964, + -0.021319502964615822, + 0.05351290851831436, + 0.052106473594903946, + -0.010152475908398628, + -0.017445174977183342, + 0.030323222279548645, + 0.02796917036175728, + 0.0026626174803823233, + -0.03001641295850277, + 0.014342408627271652, + 0.03061019256711006, + -0.00294340867549181, + -0.018154315650463104, + 0.02443081885576248, + 0.003663803683593869, + -0.023388244211673737, + -0.0018819351680576801, + 0.0010939103085547686, + 0.03557095676660538, + -0.053037356585264206, + -0.06498610228300095, + 0.04878298565745354, + -0.03413922339677811, + -0.02763182483613491, + 0.0009715812630020082, + 0.00486012501642108, + 0.03292006626725197, + 0.023539533838629723, + 0.011763699352741241, + -0.026951594278216362, + -0.03602864220738411, + 0.04788520559668541, + -0.04133124649524689, + -0.013166938908398151, + -0.037222955375909805, + 0.014670289121568203, + -0.056680355221033096, + -0.008314837701618671, + 0.04227377846837044, + -0.04986898973584175, + -0.03443481773138046, + -0.00174588686786592, + 0.0027100981678813696, + -0.001079584937542677, + -0.06199319660663605, + 0.03100454993546009, + 0.06752201914787292, + 0.028809374198317528, + -0.06289442628622055, + -0.005715612787753344, + -0.052428603172302246, + -0.01548265665769577, + -0.048164043575525284, + 0.04651368409395218, + 0.00703784916549921, + 0.0493292361497879, + 0.024252086877822876, + -0.03811171278357506, + 0.030049748718738556, + 0.02749229036271572, + -0.0005660666502080858, + 0.009821311570703983, + 0.01306783128529787, + 0.01775788515806198, + -0.051085181534290314, + 0.028779184445738792 + ], + "chunk_ind": 0 + }, + { + "url": "https://docs.danswer.dev/more/use_cases/sales", + "title": "Sales", + "content": "Keep your team up to date on every conversation and update so they can close.\n\nRecall Every Detail\nBeing able to instantly revisit every detail of any call without reading transcripts is helping Sales teams provide more tailored pitches, build stronger relationships, and close more deals. Instead of searching and reading through hours of transcripts in preparation for a call, your team can now ask Danswer \"What specific features was ACME interested in seeing for the demo\". Since your team doesn't have time to read every transcript prior to a call, Danswer provides a more thorough summary because it can instantly parse hundreds of pages and distill out the relevant information. Even for fast lookups it becomes much more convenient - for example to brush up on connection building topics by asking \"What rapport building topic did we chat about in the last call with ACME\".\n\nKnow Every Product Update\nIt is impossible for Sales teams to keep up with every product update. Because of this, when a prospect has a question that the Sales team does not know, they have no choice but to rely on the Product and Engineering orgs to get an authoritative answer. Not only is this distracting to the other teams, it also slows down the time to respond to the prospect (and as we know, time is the biggest killer of deals). With Danswer, it is even possible to get answers live on call because of how fast accessing information becomes. A question like \"Have we shipped the Microsoft AD integration yet?\" can now be answered in seconds meaning that prospects can get answers while on the call instead of asynchronously and sales cycles are reduced as a result.", + "title_embedding": [ + 0.008453648537397385, + 0.049128592014312744, + 0.0009390072082169354, + -0.011420674622058868, + 0.009472657926380634, + 0.05824451148509979, + -0.04129518195986748, + -0.018892904743552208, + -0.007598293945193291, + -0.03804052621126175, + -0.003747896058484912, + 0.005537204910069704, + 0.026590371504426003, + -0.02672540210187435, + 0.02651272714138031, + -0.033856429159641266, + 0.03809495270252228, + -0.013283955864608288, + -0.00013869917893316597, + 0.020309027284383774, + -0.011650309897959232, + -0.02103874459862709, + 0.01066586747765541, + -0.057243604212999344, + 0.031903959810733795, + -0.012924387119710445, + -0.012852400541305542, + 0.01951044611632824, + 0.018149282783269882, + -0.01314238179475069, + 0.01411629281938076, + -0.009169652126729488, + 0.017607972025871277, + -0.0685962364077568, + -0.03812728449702263, + -0.06783904880285263, + 0.009403989650309086, + 0.0073580555617809296, + 0.024488259106874466, + 0.0005618860013782978, + 0.0418679341673851, + 0.01953919045627117, + -0.05312833935022354, + -0.024998614564538002, + 0.017944931983947754, + -0.004367160610854626, + 0.023977765813469887, + 0.012059491127729416, + 0.049591515213251114, + -0.05067070946097374, + 0.001997043378651142, + 0.0024496091064065695, + -0.029425427317619324, + -0.01783224567770958, + 0.0016368982614949346, + 0.006662128958851099, + 0.0406189002096653, + 0.011542750522494316, + 0.023075561970472336, + -0.012605642899870872, + 0.010134617798030376, + 0.054372530430555344, + -0.008662662468850613, + 0.016197390854358673, + 0.015719175338745117, + -0.024816671386361122, + -0.006610441952943802, + 0.015418685972690582, + -0.011234346777200699, + -0.003028685925528407, + 0.09540237486362457, + 0.026426734402775764, + 0.03904794156551361, + 0.025213684886693954, + -0.01716603711247444, + -0.03701924905180931, + 0.0097318384796381, + 0.003443458816036582, + -0.022713838145136833, + 0.029555244371294975, + -0.0012461059959605336, + -0.02693314291536808, + 0.027585584670305252, + 0.00919498410075903, + 0.0784342810511589, + -0.004147294908761978, + 0.0058822669088840485, + -0.03257093206048012, + -0.0194808728992939, + -0.015468079596757889, + -0.007020206656306982, + 0.017711102962493896, + 0.09179206192493439, + 0.07245390862226486, + -0.08327075839042664, + -0.01777547225356102, + -0.0036551833618432283, + 0.005220785271376371, + -0.013074155896902084, + -0.05137576162815094, + -0.03984086588025093, + -0.001254269853234291, + 0.0388508178293705, + -0.026559771969914436, + 0.0941508412361145, + 0.028184799477458, + 0.030329154804348946, + -0.015901995822787285, + -0.05033569037914276, + -0.040444258600473404, + -0.08671051263809204, + 0.016047460958361626, + -0.015745067968964577, + 0.036006249487400055, + -0.019317714497447014, + 0.0028998597990721464, + 0.08916892111301422, + -0.06901372224092484, + 0.05473657324910164, + 0.06781236082315445, + 0.016306273639202118, + 0.0011640831362456083, + 0.0008445090497843921, + 0.06246241182088852, + -0.020153285935521126, + -0.011525464244186878, + -0.043366242200136185, + 0.036528658121824265, + 0.012839822098612785, + -0.0585474967956543, + 0.04394524171948433, + 0.017970293760299683, + 0.0273651871830225, + -0.006580607499927282, + 0.04960521310567856, + 0.04129025712609291, + -0.039038222283124924, + -0.007922167889773846, + 0.06417153030633926, + 0.00870921928435564, + 0.04419026896357536, + 0.03394830971956253, + 0.04194091632962227, + -0.009943729266524315, + -0.026762165129184723, + -0.06321611255407333, + 0.018493760377168655, + 0.02112971432507038, + -0.008362037129700184, + 0.0030741533264517784, + 0.02977512590587139, + 0.007839385420084, + -0.030427763238549232, + -0.005435082130134106, + -0.023782288655638695, + -0.06198855862021446, + -0.006325197406113148, + 0.03481286019086838, + 0.01096314936876297, + -0.008224114775657654, + 0.016886647790670395, + 0.018134206533432007, + -0.02693709172308445, + 0.08969569951295853, + -0.03854775056242943, + -0.036120977252721786, + 0.003924157004803419, + 0.05902013182640076, + 0.02604551427066326, + 0.04082872346043587, + -0.006722352001816034, + -0.011970511637628078, + -0.014307579025626183, + 0.0019104834645986557, + 0.05876787751913071, + -0.002502535469830036, + 0.027572669088840485, + 0.027537895366549492, + -0.026239819824695587, + -0.02237943559885025, + 0.026839105412364006, + -0.04806261509656906, + 0.022188611328601837, + 0.05301826074719429, + -0.017422696575522423, + -0.04489205405116081, + 0.04667934030294418, + -0.03202678635716438, + -0.022968970239162445, + 0.019313516095280647, + -0.06724600493907928, + 0.023997649550437927, + 0.02574523165822029, + -0.021134337410330772, + -0.018166225403547287, + -0.02959403023123741, + 0.038194961845874786, + 0.009773771278560162, + 0.026523802429437637, + -0.014497771859169006, + 0.009200031869113445, + 0.01488631684333086, + -0.10185936093330383, + 0.018728939816355705, + -0.01575741171836853, + 0.02251303941011429, + 0.02899281494319439, + -0.04970388114452362, + 0.007716581225395203, + 0.06781720370054245, + 0.07015375792980194, + -0.02934109978377819, + -0.006221897434443235, + 0.012976646423339844, + -0.00737345777451992, + -0.02422930672764778, + -0.03612032160162926, + 0.003943525720387697, + -0.02053997851908207, + 0.01488402672111988, + -0.016384800896048546, + -0.02631048858165741, + 0.0029128696769475937, + 0.0012878051493316889, + 0.029553934931755066, + 0.06647666543722153, + -0.014463554136455059, + 0.04724975302815437, + 0.01416710950434208, + 0.0259545985609293, + -0.019878843799233437, + -0.04123354330658913, + -0.003678504843264818, + -0.015237071551382542, + -0.037017468363046646, + -0.014126508496701717, + 0.037044424563646317, + 0.041153766214847565, + 0.034035731106996536, + 0.0518031120300293, + -0.004720885772258043, + -0.01163511723279953, + 0.07213476300239563, + -0.06036211922764778, + -0.03499453514814377, + -0.006943386513739824, + -0.06392820924520493, + -0.013479998335242271, + 0.01668090932071209, + 0.030153054744005203, + 0.04787909612059593, + 0.042566943913698196, + 0.01869821362197399, + 0.05060578137636185, + -0.005738548934459686, + 0.0004935020115226507, + -0.04920157790184021, + 0.05485580489039421, + -0.02717270515859127, + -0.026000261306762695, + 0.017413917928934097, + 0.00194182014092803, + 0.06368009001016617, + -0.021680809557437897, + 0.011896755546331406, + 0.008441813290119171, + -0.009322874248027802, + 0.004058067686855793, + 0.003404452698305249, + -0.0070596663281321526, + -0.01350175030529499, + 0.027827585116028786, + -0.017853371798992157, + 0.05100760981440544, + -0.01331804133951664, + -0.021219315007328987, + 0.012195413932204247, + -0.04513333737850189, + 0.022477995604276657, + 0.004410626832395792, + 0.033304695039987564, + 0.023220136761665344, + 0.00041832958231680095, + 0.007724999450147152, + 0.0359807088971138, + 0.010411631315946579, + 0.0007441110792569816, + -0.018354782834649086, + -0.030612032860517502, + 0.04444800317287445, + -0.004541076719760895, + -0.012099254876375198, + 0.03223736584186554, + -0.017639242112636566, + 0.012390367686748505, + 0.055463794618844986, + 0.09133724123239517, + -0.028237899765372276, + -0.026783155277371407, + -0.029024433344602585, + 0.014482105150818825, + 0.05629871413111687, + -0.03724139928817749, + 0.008170249871909618, + 0.06597549468278885, + 0.051776643842458725, + 0.042193781584501266, + -0.01338224858045578, + 0.03543481230735779, + 0.0065676262602210045, + -0.04679378867149353, + 0.048750247806310654, + -0.01348006259649992, + 0.06560897082090378, + -0.10058096796274185, + 0.06226775795221329, + 0.06525543332099915, + -0.020321687683463097, + 0.05926727131009102, + -0.023439910262823105, + 0.00998155027627945, + -0.04136430844664574, + 0.04513855278491974, + -0.07410337775945663, + -0.0032536713406443596, + 0.022534336894750595, + -0.0035887588746845722, + 0.018703486770391464, + -0.023037323728203773, + -0.03570957109332085, + -0.03149940446019173, + 0.01058092713356018, + -0.08196881413459778, + -0.012937279418110847, + 0.02611234411597252, + 0.03242015466094017, + 0.00964296329766512, + -0.03003847971558571, + -0.02878165803849697, + 0.005552087444812059, + 0.11100566387176514, + 0.006707212887704372, + 0.007847320288419724, + -0.04757271707057953, + -0.010918735526502132, + 0.007332456298172474, + -0.04022597521543503, + -0.03945135325193405, + 0.08289318531751633, + -0.049061018973588943, + -0.04947024583816528, + -0.030500037595629692, + -0.03648613020777702, + 0.007221090141683817, + -0.023051844909787178, + 0.06497090309858322, + 0.024345578625798225, + -0.0074218385852873325, + -0.04062318801879883, + -0.020212918519973755, + -0.009461181238293648, + -0.04491201415657997, + 0.05126942694187164, + -0.005242756102234125, + 0.024492694064974785, + -0.02291315235197544, + 0.06517285853624344, + -0.006112807895988226, + 0.004548671655356884, + 0.009358521550893784, + 0.0066603804007172585, + -0.005717182531952858, + 0.046729590743780136, + 0.04008319228887558, + 0.09077014029026031, + 0.03511488437652588, + -0.05282759666442871, + 0.020438214763998985, + -0.01378707680851221, + -0.005117158405482769, + 0.07433145493268967, + 0.0034097072202712297, + -0.011192821897566319, + 0.0009265196276828647, + -0.03159809112548828, + -0.033578045666217804, + -0.012528836727142334, + -0.006292750593274832, + 0.0452519953250885, + -0.025647340342402458, + -0.026395585387945175, + -0.044332105666399, + -0.0012870433274656534, + 0.016866305842995644, + -0.00726186903193593, + -0.014325585216283798, + 0.02150380238890648, + 0.05446008965373039, + 0.01817481219768524, + 0.017272990196943283, + 7.192481280071661e-05, + -0.021787019446492195, + 0.03518282249569893, + 0.04129958152770996, + 0.005599076859652996, + 0.07016170769929886, + 0.0068466924130916595, + -0.038150086998939514, + 0.022464951500296593, + -0.007263584528118372, + 0.04023060202598572, + -0.006662019528448582, + -0.03398700803518295, + -0.027063554152846336, + -0.014334858395159245, + 0.00031888100784271955, + 0.03320762887597084, + -0.0263507217168808, + -0.01863865926861763, + 0.018559059128165245, + 0.06845609098672867, + -0.0037615702021867037, + 0.023087816312909126, + -0.019276361912488937, + -0.03351914510130882, + 0.021971892565488815, + 0.041575655341148376, + 0.05621027201414108, + -0.003078967332839966, + -0.06297048181295395, + -0.05009821802377701, + -0.026463210582733154, + 0.0035874273162335157, + 0.021911393851041794, + -0.074904665350914, + -0.0012849566992372274, + 0.06580246239900589, + -0.0096419183537364, + -0.01183160487562418, + 0.002244731178507209, + -0.02129410021007061, + -0.004490557126700878, + 0.006305266637355089, + 0.020787451416254044, + -0.028946323320269585, + 0.09907153993844986, + 0.06419308483600616, + -0.018514622002840042, + -0.03974919393658638, + -0.055583421140909195, + -0.04144161939620972, + -0.01479779276996851, + -0.015063298866152763, + -0.05278000980615616, + 0.056262142956256866, + 0.0039010541513562202, + 0.025815758854150772, + -0.01457720622420311, + 0.017469312995672226, + 0.032789044082164764, + 0.010338534601032734, + 0.009348046034574509, + -0.002339842962101102, + 0.023598607629537582, + 0.01676766760647297, + -0.03503762558102608, + 0.033228978514671326, + -0.03216487169265747, + -0.027531251311302185, + 0.05846886709332466, + -0.00979926623404026, + 0.011551604606211185, + 0.026247017085552216, + 0.00776244793087244, + -0.042052820324897766, + 0.003744697431102395, + -0.013622709549963474, + -0.021054048091173172, + -0.022621311247348785, + 0.03077824041247368, + 0.019676415249705315, + -0.02765408344566822, + -0.013561422936618328, + -0.015634974464774132, + -0.03614448755979538, + 0.014710169285535812, + 0.00825627613812685, + 0.014769040048122406, + 0.006793464533984661, + -0.010395821183919907, + -0.0022474846336990595, + 0.033902380615472794, + 0.003390782279893756, + -0.04533020406961441, + -0.09353062510490417, + -0.027594659477472305, + -0.026893651112914085, + 0.00822615996003151, + 0.03448451682925224, + -0.013120760209858418, + 0.03301888331770897, + -0.03717275336384773, + -0.017613839358091354, + 0.03131122142076492, + 0.01355862244963646, + -0.016891464591026306, + -0.005221182014793158, + -0.09999044984579086, + -0.0072242445312440395, + 0.023685455322265625, + -0.006333169527351856, + 0.05389386788010597, + 0.0006377844838425517, + 0.06066382676362991, + -0.010544034652411938, + -0.03069271147251129, + 0.046539101749658585, + 0.04315992072224617, + -0.04527072235941887, + 0.08369841426610947, + -0.05231470242142677, + -0.02663319930434227, + -0.017284002155065536, + 0.05720992013812065, + -0.02959314174950123, + -0.053442198783159256, + -0.055300384759902954, + -0.0034046657383441925, + 0.058179739862680435, + -0.0067557781003415585, + 0.048700254410505295, + 0.06980213522911072, + 0.0022220234386622906, + -0.02891203574836254, + -0.03402455151081085, + -0.07090416550636292, + -0.02885468490421772, + -0.033339668065309525, + 0.057542525231838226, + 0.035563718527555466, + -0.0376402772963047, + 0.01505962759256363, + 0.025728864595294, + 0.001696597901172936, + 0.04947248846292496, + -0.0798964574933052, + -0.02692596986889839, + -0.012759744189679623, + -0.02195296436548233, + -0.014371627941727638, + 0.02381875552237034, + -0.01423177681863308, + -0.014195146039128304, + -0.09804418683052063, + -0.0008884363924153149, + -0.0418919213116169, + 0.015419455245137215, + -0.0015723679680377245, + -0.008167393505573273, + -0.027652231976389885, + -0.01364823617041111, + 0.042369287461042404, + -0.020887810736894608, + -0.01855718344449997, + -0.030453767627477646, + -0.08889546990394592, + -0.042489275336265564, + -0.003145430004224181, + -0.0007042307406663895, + 0.016261309385299683, + -0.04196145758032799, + -0.02786160260438919, + 0.00031149861752055585, + 0.0020716730505228043, + -0.018168985843658447, + -0.035522907972335815, + 0.06329862773418427, + -0.06277810037136078, + -0.04981480538845062, + 0.05988100543618202, + 0.0031491960398852825, + -0.03463412821292877, + -0.010109111666679382, + -0.013390148058533669, + -0.08232187479734421, + 0.018557677045464516, + -0.023832205682992935, + -0.021515224128961563, + 0.03051081858575344, + -0.021489854902029037, + 0.009503633715212345, + 0.025148555636405945, + -0.023579541593790054, + -0.035016197711229324, + -0.022730164229869843, + 0.04465099051594734, + -0.04341805726289749, + 0.011980813927948475, + 0.024123655632138252, + -0.026239709928631783, + -0.017752202227711678, + 0.027042675763368607, + 0.023839112371206284, + 0.01306204218417406, + 0.039557792246341705, + 0.07731491327285767, + 0.02771804668009281, + 0.07320678234100342, + -0.008236434310674667, + -0.025150621309876442, + 0.0035144551657140255, + -0.045307569205760956, + -0.004989498760551214, + 0.006890833377838135, + 0.013798183761537075, + -0.04717986658215523, + 0.00230599008500576, + -0.06974467635154724, + 0.013648996129631996, + -0.05875125527381897, + -0.0020281318575143814, + -0.07060255855321884, + 0.04474693909287453, + -0.010507912375032902, + 0.01920556277036667, + 0.037952445447444916, + -0.04831290617585182, + -0.030323892831802368, + 0.017083611339330673, + 0.01788332499563694, + -0.019379939883947372, + 0.0296696275472641, + -0.0202578566968441, + -0.05725785344839096, + -0.07489712536334991, + 0.023742130026221275, + -0.07134415209293365, + -0.011462788097560406, + 0.0046195476315915585, + 0.04435937851667404, + 0.01344655267894268, + -0.003911314997822046, + -0.03020038641989231, + -0.0032732610125094652, + 0.03007005713880062, + 0.006368617527186871, + -0.03210403770208359, + 0.00835089199244976, + 0.05988067761063576, + -0.03537531942129135, + 0.05247778445482254, + 0.03723180294036865, + -0.008693824522197247, + 0.04847349226474762, + 0.016112500801682472, + 0.011540782637894154, + -0.0065521071664988995, + -0.03243750333786011, + -0.011966057121753693, + 0.017163656651973724, + -0.0029253605753183365, + -0.053153038024902344, + 0.0018134346464648843, + 0.01733018085360527, + 0.029417017474770546, + 0.030433885753154755, + 0.0021621473133563995, + -0.027712296694517136, + -0.05925380811095238, + -0.022185055539011955, + -0.0350322499871254, + -0.02007930353283882, + 0.010399214923381805, + -0.055177975445985794, + 0.0007819311576895416, + 0.024769598618149757, + 0.03780986741185188, + 0.03521614894270897, + -0.01817735843360424, + -0.08278614282608032, + -0.021156983450055122, + 0.03359638899564743, + -0.023659229278564453, + -0.007879458367824554, + 0.0292595736682415, + -0.035273004323244095, + 0.032482825219631195, + 0.02688293345272541, + 0.023407144472002983, + -0.047480449080467224, + 0.0006359686376526952, + -0.04895651713013649, + 0.011627614498138428, + -0.07718108594417572, + 0.010565578006207943, + -0.01866811513900757, + 0.01029923651367426, + -0.023772811517119408, + -0.032370492815971375, + 0.05088132247328758, + 0.011682837270200253, + 0.03289812430739403, + 0.017765464261174202, + 0.0604407899081707, + -0.03875206410884857, + -0.05453289672732353, + -0.05849386751651764, + -0.008108421228826046, + -0.036137521266937256, + -0.003845603670924902, + -0.010756440460681915, + 0.01515593845397234, + 0.09156721830368042, + 0.02919408679008484, + 0.024247899651527405, + -0.020837178453803062, + 0.04395196586847305, + -0.10095755755901337, + -0.07707840204238892, + -0.04705304652452469, + 0.007648217957466841, + -0.015342561528086662, + -0.02814168483018875, + 0.039529476314783096, + -0.06335531175136566, + -0.03782089054584503, + -0.032349780201911926, + -0.011073637753725052, + 0.03126451373100281, + 0.01734590344130993, + -0.0038809722755104303, + 0.013081631623208523, + -0.03124905936419964, + 0.0832752138376236, + -0.007435368373990059, + 0.00989855732768774, + 0.004071374889463186, + -0.021534224972128868, + -0.022376252338290215, + 0.0033940861467272043, + 0.01537957414984703, + -0.01530678290873766, + -0.006626737304031849, + 0.0722239539027214, + 0.023105483502149582, + -0.048958491533994675, + -0.031564872711896896, + 0.020468993112444878, + 0.02797403372824192, + 0.02208004891872406, + -0.06905028969049454, + -0.0069040716625750065, + 0.05185015872120857, + 0.020353762432932854, + -0.059334978461265564, + 0.019217371940612793, + -0.06793943047523499, + 0.052697695791721344, + 0.039136022329330444, + -0.03286914899945259, + 0.0017800497589632869, + 0.031667277216911316, + 0.0455632358789444, + -0.028096599504351616, + 0.007715262472629547, + 0.005349942483007908, + -0.051207322627305984, + -0.04513049125671387 + ], + "content_embedding": [ + 0.018702084198594093, + 0.03602918982505798, + -0.0030462138820439577, + -0.044632311910390854, + -0.00032779801404103637, + 0.013867323286831379, + 0.028261501342058182, + -0.0397375151515007, + -0.04266185685992241, + -0.01854686811566353, + -0.00980929471552372, + 0.005383333191275597, + 0.025814494118094444, + 0.020457584410905838, + -0.01165740005671978, + -0.02068958804011345, + 0.024463720619678497, + -0.029769178479909897, + 0.00032462665694765747, + 0.020778311416506767, + -0.009875921532511711, + -0.03926593065261841, + -0.007392906118184328, + -0.02128470689058304, + 0.020180456340312958, + -0.007395976223051548, + -0.01573384366929531, + 0.01813557744026184, + -0.04103250429034233, + 0.025176111608743668, + 0.07708748430013657, + -0.03301733359694481, + -0.00411647092550993, + -0.03946784511208534, + -0.06054544821381569, + -0.040751539170742035, + 0.01922212913632393, + -0.027164554223418236, + -0.07051867246627808, + 0.03071393072605133, + 0.07258772104978561, + -0.026042146608233452, + 0.00869719311594963, + -0.028085211291909218, + 0.0623227022588253, + -0.018381644040346146, + 0.07613946497440338, + -0.037470318377017975, + 0.022420862689614296, + -0.05576684698462486, + 0.008394862525165081, + -0.032719686627388, + -0.01822705753147602, + -0.0010964440880343318, + 0.01320287398993969, + 0.03199688717722893, + 0.02982492372393608, + 0.013676099479198456, + 0.04192396625876427, + -0.007906809449195862, + 0.009779189713299274, + 0.014214487746357918, + -0.0091244550421834, + 0.0358707420527935, + 0.003965431824326515, + -0.10266417264938354, + 0.007566090207546949, + 0.001176235033199191, + -0.027059122920036316, + -0.011146960780024529, + 0.010613090358674526, + 0.0269278846681118, + 0.00038031316944397986, + 0.024177612736821175, + -0.004191671498119831, + 0.005235857795923948, + 0.018077049404382706, + -0.04018911346793175, + -0.05125276744365692, + 0.01798614114522934, + 0.022944867610931396, + -0.04374289512634277, + 0.003367446828633547, + 0.026103869080543518, + 0.03640212118625641, + -0.006004476919770241, + 0.011275619268417358, + 0.016332507133483887, + 0.0004818506713490933, + 0.04315895587205887, + 0.022076765075325966, + -0.004544341471046209, + 0.03210305795073509, + 0.0906452164053917, + -0.07215604186058044, + 0.08494149893522263, + 0.006179131101816893, + -0.004107883665710688, + -0.012479269877076149, + -0.034221433103084564, + -0.017944667488336563, + 0.04593302682042122, + 0.019292891025543213, + -0.0031508891843259335, + 0.06966886669397354, + 0.062235988676548004, + 0.01879720948636532, + -6.745052814949304e-05, + 0.013703186996281147, + -0.003644032636657357, + -0.04458186402916908, + -0.0017342075007036328, + -0.033848460763692856, + 0.019645417109131813, + -0.02943187765777111, + 0.001105084316805005, + 0.11609244346618652, + -0.05156521871685982, + 0.009876714088022709, + 0.005161592271178961, + -0.032977450639009476, + -0.04834079369902611, + 0.021944768726825714, + -0.012638481333851814, + 0.04569210857152939, + 0.015415391884744167, + -0.03170562908053398, + -0.0031294531654566526, + 0.015164556913077831, + -0.034650497138500214, + 0.006696060299873352, + 0.006991597358137369, + -0.05405446141958237, + 0.002478727139532566, + 0.03736428543925285, + 0.006255546119064093, + -0.023612871766090393, + -0.04719111695885658, + 0.019092371687293053, + -0.007389509119093418, + 0.005412441678345203, + 0.0032002630177885294, + 0.014097358100116253, + 0.0011166664771735668, + -0.0012068386422470212, + -0.0596468411386013, + 0.0030182863119989634, + 0.018532730638980865, + 0.020043276250362396, + -0.0014203430619090796, + 0.03718654438853264, + -0.04137871786952019, + 0.003067273646593094, + 0.060497768223285675, + -0.002445906400680542, + -0.05149608850479126, + -0.011358898133039474, + -0.0057965232990682125, + 0.04786103963851929, + 0.05521485581994057, + 0.03300704434514046, + 0.01832137256860733, + -0.03220272436738014, + 0.05887257307767868, + -0.04280361905694008, + 0.030713768675923347, + 0.031198250129818916, + 0.018273506313562393, + 0.021060051396489143, + 0.018141141161322594, + -0.01044323481619358, + 0.012220986187458038, + 0.011005178093910217, + -0.008985857479274273, + 0.05407913029193878, + -0.010373812168836594, + 0.015498371794819832, + -0.04114103317260742, + 0.02436467818915844, + -0.033720944076776505, + 0.04162474721670151, + -0.03209234029054642, + 0.007773025427013636, + 0.03150646388530731, + -0.042852289974689484, + -0.0062582893297076225, + 0.04668346792459488, + -0.06638985872268677, + -0.005832660011947155, + -0.022002393379807472, + -0.015554124489426613, + -0.017163358628749847, + -0.04198216274380684, + -0.01709570921957493, + 0.026661567389965057, + -0.049418482929468155, + 0.06740570068359375, + 0.0159238763153553, + 0.0023050543386489153, + -0.031238939613103867, + -0.03321292996406555, + -0.004760078154504299, + -0.07937376946210861, + 0.03254229202866554, + -0.023319443687796593, + 0.04906806722283363, + 0.05458753556013107, + -0.013899387791752815, + 0.03574313595890999, + 0.011882249265909195, + 0.11678190529346466, + 0.0007563747349195182, + 0.025212422013282776, + 0.023760458454489708, + -0.021716047078371048, + -0.017915191128849983, + -0.02478560246527195, + -0.028406206518411636, + -0.06178540363907814, + 0.044959306716918945, + -0.003325885394588113, + -0.02079332433640957, + -0.010518986731767654, + -0.00242405547760427, + -0.0030814141500741243, + 0.0010505993850529194, + 0.0034556719474494457, + 0.005322635173797607, + -0.02364535629749298, + -0.0034255431964993477, + -0.04123266786336899, + -0.09191295504570007, + 0.03907715901732445, + 0.017849568277597427, + 0.003202608088031411, + -0.009892004542052746, + 0.00447180075570941, + 0.02633223496377468, + 0.010955878533422947, + 0.08653970807790756, + 0.020712584257125854, + 0.0020712309051305056, + 0.02159838192164898, + -0.03148637339472771, + -0.1106131300330162, + -0.0034493962302803993, + 0.008495570160448551, + 0.025898300111293793, + -0.01585080474615097, + 0.047963947057724, + 0.03191608935594559, + 0.05672791600227356, + 0.017725899815559387, + -0.011000119149684906, + 0.05266193300485611, + -0.02026527188718319, + -0.0076444013975560665, + 0.04474569857120514, + 0.0030594514682888985, + -0.04981522262096405, + -0.0012618869077414274, + -0.028191188350319862, + 0.06203592196106911, + -0.04548441618680954, + -0.01024117786437273, + 0.012013573199510574, + -0.03531227633357048, + -0.0303136445581913, + 0.01046642567962408, + -0.029064299538731575, + -0.015392802655696869, + 0.02021191082894802, + 0.015328207053244114, + 0.07215247303247452, + -0.024603676050901413, + -0.0021844934672117233, + 0.01121720764786005, + -0.03952696546912193, + 0.057082369923591614, + -0.007885781116783619, + -0.05230427160859108, + -0.0490812249481678, + -0.031762074679136276, + -0.009603463113307953, + -0.008093117736279964, + 0.030981115996837616, + -0.0013626269064843655, + -0.019603300839662552, + 0.025847315788269043, + 0.012290321290493011, + 0.007945788092911243, + 0.011359087191522121, + 0.01893901824951172, + 0.03544235974550247, + 0.01802144944667816, + 0.07854204624891281, + 0.07568025588989258, + -0.05122705176472664, + 0.008560816757380962, + -0.03897644579410553, + 0.024606050923466682, + 0.03792334720492363, + 0.01617903634905815, + -0.04735874757170677, + 0.003156541381031275, + -0.011881450191140175, + -0.026287615299224854, + 0.030718199908733368, + 0.04659629613161087, + -0.006789658684283495, + -0.03779527172446251, + -0.0030539771541953087, + -0.05919982120394707, + -0.03511202707886696, + -0.079665407538414, + 0.0580061711370945, + 0.07525473088026047, + 0.02381243370473385, + 0.04075026884675026, + 0.011406723409891129, + 0.020479097962379456, + -0.004844597075134516, + -0.012301536276936531, + -0.07029860466718674, + 0.0063995844684541225, + 0.03451430797576904, + 0.023998068645596504, + 0.03119623102247715, + -0.0481903962790966, + 0.03359334170818329, + 0.02563287690281868, + 0.04894624277949333, + -0.05896732583642006, + -0.020169634371995926, + 0.01319917943328619, + 0.00783664919435978, + 0.0051937587559223175, + 0.0014421058585867286, + -0.026831623166799545, + -0.0031287523452192545, + 0.024796785786747932, + -0.0008400659426115453, + -0.03314085304737091, + -0.038561608642339706, + -0.013552311807870865, + -0.012201554141938686, + -0.010810038074851036, + -0.025452986359596252, + 0.058491192758083344, + -0.017493925988674164, + -0.04302553832530975, + 0.00978845451027155, + 0.0001076174812624231, + -0.042208705097436905, + -0.011103725992143154, + 0.019692320376634598, + 0.035941820591688156, + 0.02046988718211651, + -0.013415461406111717, + 0.013622494414448738, + 0.03867186978459358, + -0.019314907491207123, + 0.018686568364501, + -0.026298167183995247, + 0.052582357078790665, + 0.027494613081216812, + 0.046435534954071045, + 0.03811647742986679, + 0.0486551970243454, + 0.0019721186254173517, + -0.017199190333485603, + -0.006901210639625788, + 0.025136850774288177, + 0.0804467722773552, + 0.061168037354946136, + 0.017717817798256874, + -0.06603220850229263, + -0.05064086616039276, + 0.039705704897642136, + -0.024581512436270714, + 0.09781734645366669, + -0.030609596520662308, + 0.006824797950685024, + -0.004317844286561012, + 0.0027715987525880337, + 0.000943489489145577, + -0.013181749731302261, + -0.025556521490216255, + -0.028432460501790047, + -0.03751988708972931, + -0.019560452550649643, + -0.0136410528793931, + -0.024382753297686577, + 0.02857314422726631, + -0.011391760781407356, + -0.0005634031840600073, + 0.03159620240330696, + -0.005198314320296049, + -0.006265239790081978, + 0.025611309334635735, + -0.058613672852516174, + -0.04532675817608833, + -0.021873218938708305, + 0.02903951145708561, + -0.0121288001537323, + 0.04538734629750252, + -0.027941465377807617, + -0.07353822141885757, + 0.03773269057273865, + -0.00512319291010499, + 0.028662901371717453, + 0.04792957380414009, + -0.01053295936435461, + -0.035430196672677994, + 0.009273026138544083, + 0.004318219143897295, + 0.08100441098213196, + 0.014380274340510368, + -0.03378414362668991, + -0.01987980492413044, + 0.021573858335614204, + 0.02855539321899414, + -0.007542841136455536, + 0.004633236676454544, + 0.008639613166451454, + 0.006394797004759312, + 0.019281607121229172, + -0.015256315469741821, + -0.00148143304977566, + -0.02985287643969059, + 0.025533605366945267, + -0.011111553758382797, + 0.01765139028429985, + 0.05442074313759804, + -0.09088895469903946, + 0.032542143017053604, + 0.0574481226503849, + 0.027539772912859917, + 0.028780700638890266, + 0.04139337316155434, + -0.014601831324398518, + -0.04883953556418419, + -0.015341846272349358, + -0.03965975344181061, + -0.000157194648636505, + 0.0576823353767395, + 0.0886307954788208, + 0.008708767592906952, + -0.03148962929844856, + 0.00118768191896379, + -0.009285139851272106, + 0.0349595844745636, + 0.00010961518273688853, + -0.007748626638203859, + 0.08073285222053528, + -0.026761949062347412, + 0.008831962943077087, + -0.04131530225276947, + -0.00733856251463294, + 0.06809361279010773, + 0.03708426281809807, + 0.06835067272186279, + 0.006261076312512159, + 0.015920374542474747, + -0.004048558417707682, + -0.02677253447473049, + 0.07650309801101685, + -0.023148853331804276, + -0.057494066655635834, + 0.014478741213679314, + -0.007499868981540203, + 0.02524508722126484, + 0.04229635000228882, + 0.017856169492006302, + -0.048948079347610474, + -0.014559978619217873, + 0.05829133093357086, + -0.007394919637590647, + 0.008901085704565048, + 0.03540206328034401, + 0.011715879663825035, + 0.03447958827018738, + -0.05490283668041229, + -0.0033728398848325014, + -0.029942180961370468, + -0.0025663028936833143, + 0.02124219387769699, + 0.02587033249437809, + -0.03495795652270317, + -0.01766275428235531, + 0.05129474401473999, + 0.050688110291957855, + -0.04483504965901375, + -0.01242926623672247, + -0.10075337439775467, + -0.039148375391960144, + -0.01708081364631653, + 0.022980742156505585, + 0.0012766321888193488, + -0.05624091997742653, + 0.02920171432197094, + -0.0004628047754522413, + -0.012556084431707859, + -0.004911895841360092, + -0.006203844211995602, + 0.011994684115052223, + -0.005147894844412804, + -0.0653131902217865, + 0.021533435210585594, + 0.027332814410328865, + 0.010824107564985752, + 0.06882979720830917, + 0.002402055310085416, + 0.06736285239458084, + 0.007376556750386953, + -0.09907388687133789, + 0.0738959014415741, + 0.011251496151089668, + -0.089520663022995, + 0.07383604347705841, + -0.02708776667714119, + 0.039623651653528214, + 0.001983445603400469, + 0.034104056656360626, + -0.10747380554676056, + -0.01417585276067257, + -0.04512251541018486, + 0.001210794085636735, + 0.05437818914651871, + -0.004397509153932333, + 0.03336326405405998, + 0.06369500607252121, + 0.014758906327188015, + -0.009938295930624008, + 0.027304060757160187, + -0.025614865124225616, + -0.019298158586025238, + -0.03774742782115936, + -0.021663375198841095, + 0.004094315692782402, + -0.05966729298233986, + 0.025774789974093437, + 0.004207789432257414, + 0.03211497142910957, + 0.0222456231713295, + -0.07142850011587143, + -0.02816791646182537, + 0.008917749859392643, + -0.03328888863325119, + -0.04815923050045967, + 0.055692847818136215, + 0.005043115001171827, + 0.007406118791550398, + -0.10431766510009766, + 0.003935595508664846, + -0.07654271274805069, + 0.018002459779381752, + -0.026796353980898857, + -0.01480060163885355, + -0.003071046667173505, + -0.031164491549134254, + -0.004783581010997295, + 0.028996651992201805, + -0.00432590302079916, + 0.03827083855867386, + -0.10670920461416245, + -0.009844367392361164, + 0.05061553791165352, + 0.044921379536390305, + -0.021305931732058525, + -0.010570063255727291, + -0.037161700427532196, + 0.03244778513908386, + -0.026579100638628006, + -0.021481862291693687, + -0.0803975760936737, + 0.0602957159280777, + -0.030482472851872444, + -0.016915978863835335, + -0.03414126858115196, + -0.07902093976736069, + -0.05861777812242508, + 0.02578902617096901, + -0.006971773691475391, + 0.021272379904985428, + 0.004250700585544109, + -0.04617677628993988, + -0.025576869025826454, + 0.09362083673477173, + -0.02747775986790657, + -0.010427952744066715, + -0.005847673863172531, + 0.03786874935030937, + -0.023494398221373558, + -0.03599749505519867, + 0.06915943324565887, + -0.0005259242025204003, + -0.020210636779665947, + 0.012060794048011303, + -0.03892034292221069, + -0.03120974451303482, + 0.03798247501254082, + 0.08222217112779617, + -0.03596770018339157, + -0.001334474771283567, + 0.06480739265680313, + 0.016418466344475746, + 0.017459729686379433, + -0.05252225697040558, + -0.05017365887761116, + -0.013104243203997612, + -0.023724595084786415, + 0.006762322038412094, + -0.005946440156549215, + 0.006083739455789328, + -0.014293180778622627, + 0.041052985936403275, + -0.02417348138988018, + 0.03206375241279602, + -0.05389661714434624, + 0.0052835363894701, + -0.038879118859767914, + 0.0735245794057846, + -0.004067298024892807, + -0.007775747217237949, + 0.03442619740962982, + -0.013299554586410522, + -0.01858234964311123, + 0.015830783173441887, + 0.050536882132291794, + 0.039121512323617935, + 0.025488585233688354, + -0.083254374563694, + -0.0376444049179554, + -0.03673558309674263, + 0.02858356013894081, + -0.0017373028676956892, + -0.029856612905859947, + -0.020456591621041298, + 0.014330082572996616, + 0.026495426893234253, + -0.029473086819052696, + -0.05005846545100212, + 0.036553170531988144, + 0.03604103624820709, + -0.014557436108589172, + 0.0075491974130272865, + 0.02816123701632023, + 0.022223982959985733, + -0.010599660687148571, + 0.0738152265548706, + 0.09043020755052567, + -0.0195071529597044, + 0.03981706127524376, + 0.04508437216281891, + 0.03942303732037544, + 0.016333166509866714, + -0.007340291049331427, + -0.041841596364974976, + -0.014305119402706623, + -0.005970897153019905, + -0.04999639838933945, + -0.00753607414662838, + -0.026936067268252373, + 0.02390979416668415, + -0.02593693509697914, + -0.015126893296837807, + -0.035575494170188904, + -0.01576480083167553, + 0.01482314057648182, + 0.01960604451596737, + 0.012122674845159054, + 0.018187053501605988, + -0.04843643680214882, + -0.032472606748342514, + -0.002006485592573881, + -0.003907614853233099, + 0.012371492572128773, + -0.03494970500469208, + -0.04294227808713913, + 0.004812099505215883, + -0.02547234669327736, + 0.028849929571151733, + -0.021960295736789703, + -0.0013683459255844355, + 0.030571121722459793, + -0.04714812710881233, + -0.0034763696603477, + -0.03908781707286835, + -0.04101671278476715, + 0.013097001239657402, + 0.004385901615023613, + -0.033829864114522934, + -0.04254792630672455, + 0.015273491851985455, + -0.040665704756975174, + -0.00920754112303257, + -0.041413065046072006, + -0.013588172383606434, + -0.0017439010553061962, + -0.030785854905843735, + 0.07103034108877182, + -0.01929519884288311, + 0.025452272966504097, + -0.022381870076060295, + -0.028560174629092216, + -0.011340905912220478, + -0.008002392016351223, + -0.013147140853106976, + 0.021906575188040733, + -0.04703265056014061, + 0.00766343716531992, + 0.06170996278524399, + -0.004122643731534481, + -0.01931242272257805, + 0.03596718981862068, + 0.0322248749434948, + -0.026486199349164963, + -0.03052559122443199, + -0.03129229322075844, + 0.024310404434800148, + -0.029317326843738556, + -0.07851212471723557, + 0.04514205455780029, + -0.020682433620095253, + -0.04681077226996422, + 0.008951415307819843, + 0.04007868468761444, + 0.028472354635596275, + 0.009118284098803997, + -0.013431325554847717, + -0.020488806068897247, + -0.027376288548111916, + 0.035840798169374466, + -0.03870074450969696, + -0.002007996430620551, + -0.017398731783032417, + 0.031902845948934555, + -0.07956399768590927, + -0.04125808924436569, + 0.01867605932056904, + -0.08004764467477798, + -0.005094117484986782, + 0.03083234466612339, + -0.01335862372070551, + -0.04482260346412659, + -0.033836718648672104, + 0.02282416820526123, + 0.06287918239831924, + 0.010162614285945892, + -0.05158773064613342, + 0.0008301119669340551, + -0.03881796821951866, + 0.002004651352763176, + -0.022358564659953117, + 0.022438282147049904, + 0.04948568344116211, + 0.03556858375668526, + 0.04151606187224388, + -0.03065376915037632, + 0.0035080660600215197, + -0.004210236947983503, + -0.02430005557835102, + 0.02775806188583374, + 0.0647825375199318, + 0.003446039743721485, + -0.015345090068876743, + -0.004865385591983795 + ], + "chunk_ind": 0 + }, + { + "url": "https://docs.danswer.dev/more/use_cases/operations", + "title": "Operations", + "content": "Double the productivity of your Ops teams like IT, HR, etc.\n\nAutomatically Resolve Tickets\nModern teams are leveraging AI to auto-resolve up to 50% of tickets. Whether it is an employee asking about benefits details or how to set up the VPN for remote work, Danswer can help your team help themselves. This frees up your team to do the real impactful work of landing star candidates or improving your internal processes.\n\nAI Aided Onboarding\nOne of the periods where your team needs the most help is when they're just ramping up. Instead of feeling lost in dozens of new tools, Danswer gives them a single place where they can ask about anything in natural language. Whether it's how to set up their work environment or what their onboarding goals are, Danswer can walk them through every step with the help of Generative AI. This lets your team feel more empowered and gives time back to the more seasoned members of your team to focus on moving the needle.", + "title_embedding": [ + 0.010730741545557976, + 0.018373621627688408, + -0.0013679212424904108, + 0.0001091610174626112, + 0.034599218517541885, + 0.038814906030893326, + -0.03269535303115845, + -0.015120825730264187, + -0.011999477632343769, + -0.023377608507871628, + -0.003536652075126767, + 0.019120972603559494, + 0.032052282243967056, + -0.03316797688603401, + 0.002971385605633259, + -0.06660863012075424, + 0.015637297183275223, + -0.004499480128288269, + -0.01167437992990017, + 0.024017684161663055, + 0.011193061247467995, + 0.02649473212659359, + 0.04822992533445358, + -0.022897351533174515, + 0.04229900613427162, + 0.004849326331168413, + -0.0013035786105319858, + -0.022214103490114212, + -0.03940191864967346, + -0.010781657882034779, + 0.049329955130815506, + -0.010857120156288147, + 0.04519270732998848, + -0.025993647053837776, + -0.03483803570270538, + -0.08306694775819778, + 0.023532472550868988, + 0.01766788400709629, + 0.07221196591854095, + -0.001823332509957254, + 0.003104567062109709, + 0.05640452727675438, + -0.04483344778418541, + -0.04334229975938797, + 0.019754929468035698, + -0.011862428858876228, + 0.03863349184393883, + 0.01501200906932354, + 0.03863223269581795, + -0.05570034310221672, + -0.0267505943775177, + 0.03793827444314957, + -0.015061624348163605, + -0.025455573573708534, + 0.015559123829007149, + -0.01849287934601307, + 0.04038143530488014, + 0.026783155277371407, + 0.0023170525673776865, + -0.005963196512311697, + 0.04137548804283142, + 0.01764686405658722, + -0.02246052585542202, + -0.012901525013148785, + -0.017714571207761765, + -0.01027537789195776, + -0.016164785251021385, + -0.007979510352015495, + 0.021984701976180077, + -0.009949913248419762, + 0.08931540697813034, + 0.019962448626756668, + 0.03341870754957199, + 0.028858954086899757, + 0.0011826930567622185, + -0.00010822620242834091, + 0.021924806758761406, + -0.009182920679450035, + -0.018256863579154015, + 0.04718794673681259, + 0.020425673574209213, + 0.0002538118860684335, + 0.05454721301794052, + 0.019339540973305702, + 0.09129136055707932, + -0.010062575340270996, + 0.011977903544902802, + -0.022689297795295715, + -0.02022380940616131, + 0.013067576102912426, + 0.005217134952545166, + 0.037848640233278275, + 0.09128513187170029, + 0.052562836557626724, + -0.08711232244968414, + -0.0015501821180805564, + 0.00441542686894536, + -0.025076182559132576, + -0.014110158197581768, + -0.06030100956559181, + -0.0010345132322981954, + 0.018056612461805344, + 0.03524528071284294, + -0.01293126679956913, + 0.04700767621397972, + 0.06564126163721085, + 0.010113431140780449, + 0.018003467470407486, + -0.05646204203367233, + -0.02047823928296566, + -0.048007529228925705, + 0.05380301922559738, + -0.01607179455459118, + 0.0008504731231369078, + -0.015249709598720074, + -0.005599239841103554, + 0.054663073271512985, + -0.036346085369586945, + 0.024314023554325104, + 0.0768347755074501, + 0.03234424442052841, + 0.008295328356325626, + -0.0015371616464108229, + 0.043760448694229126, + -0.0018124273046851158, + -0.017262862995266914, + -0.042646538466215134, + 0.025395702570676804, + 0.03709862381219864, + -0.03921937197446823, + 0.050630342215299606, + 0.024703586474061012, + 0.022064829245209694, + -0.008263661526143551, + 0.03165263310074806, + 0.017121389508247375, + -0.06672775000333786, + -0.06984685361385345, + 0.11498068273067474, + -0.02806312032043934, + 0.025353405624628067, + 0.006591377779841423, + -0.011244958266615868, + -0.014589745551347733, + 0.031125560402870178, + -0.06834094226360321, + -0.015911657363176346, + 0.0176913570612669, + -0.022801805287599564, + 0.01242455281317234, + 0.001349485362879932, + 0.05671858787536621, + -0.024975799024105072, + -0.019439268857240677, + -0.0038488772697746754, + -0.057438429445028305, + -0.004414469934999943, + 0.018468070775270462, + 0.006111294496804476, + 0.018633801490068436, + 0.04350016638636589, + 0.04317209869623184, + -0.058885347098112106, + 0.06605420261621475, + -0.060788847506046295, + -0.059009939432144165, + 0.003782198065891862, + 0.04133265092968941, + 0.019440937787294388, + 0.0046022264286875725, + 0.010991339571774006, + -0.0554840974509716, + 0.04083068668842316, + 0.007237149402499199, + 0.04218628630042076, + 0.015044232830405235, + 0.0565854087471962, + 0.03397437930107117, + 0.017036354169249535, + -0.02862199954688549, + -0.0019827275536954403, + -0.04851892590522766, + 0.020672423765063286, + 0.029321348294615746, + -0.04698231443762779, + -0.06201909855008125, + 0.01672869734466076, + -0.06657315790653229, + -0.061089128255844116, + -0.006803641561418772, + -0.041214216500520706, + 0.025210469961166382, + 0.03659403696656227, + -0.056864507496356964, + -0.017966432496905327, + -0.04572960361838341, + 0.03334927558898926, + 0.0010855993023142219, + 0.009142755530774593, + -0.045417286455631256, + 0.0508459098637104, + -0.0020350103732198477, + -0.08134196698665619, + -0.014234581962227821, + -0.018346119672060013, + 0.027286984026432037, + 0.01077864971011877, + 0.025067729875445366, + -0.0010993028990924358, + 0.055933188647031784, + 0.08128975331783295, + -0.00964485201984644, + 0.02629624865949154, + 0.02482009492814541, + -0.004299841821193695, + -0.02121540531516075, + -0.012340475805103779, + -0.010211183689534664, + -0.033044300973415375, + 0.01627231389284134, + 0.0025289515033364296, + -0.024867739528417587, + -0.02439618855714798, + 0.031935419887304306, + 0.015503033064305782, + 0.058931007981300354, + 0.0018315770430490375, + 0.05652814358472824, + -0.01652582921087742, + -0.009255263954401016, + -0.03914093226194382, + -0.015466556884348392, + 0.04188372567296028, + -0.027017222717404366, + -0.022300412878394127, + 0.016426892951130867, + 0.017171800136566162, + 0.07701553404331207, + 0.043874118477106094, + 0.07433117181062698, + 0.026014234870672226, + 0.013816924765706062, + 0.014636811800301075, + -0.036465343087911606, + -0.03994021564722061, + 0.003269175998866558, + -0.03902558237314224, + -0.0039056213572621346, + 0.01340826041996479, + -0.012667474336922169, + 0.013740241527557373, + 0.014225244522094727, + -0.01617649756371975, + 0.045204829424619675, + 0.0021076719276607037, + -0.03156042471528053, + -0.051285773515701294, + 0.050252512097358704, + -0.03781714290380478, + 0.017089596018195152, + 0.028835022822022438, + 0.005575904157012701, + 0.05654308199882507, + -0.004466162994503975, + 0.05050184950232506, + 0.011318539269268513, + -0.049033407121896744, + 0.022067567333579063, + 0.011711984872817993, + 0.005116294138133526, + -0.02025405503809452, + -0.010977067984640598, + -0.030916348099708557, + 0.05374428257346153, + 0.00808737613260746, + -0.044140078127384186, + 0.030092595145106316, + -0.01702306419610977, + -0.020538438111543655, + 0.00427399855107069, + 0.002780117094516754, + -0.005801517982035875, + -0.04212724789977074, + 0.024279015138745308, + -6.510222738143057e-05, + -0.020652174949645996, + -0.006957880686968565, + 0.0016846335493028164, + -0.0663430467247963, + -0.0335371308028698, + 2.869481068046298e-05, + -0.037348829209804535, + 0.039201609790325165, + -0.000545984017662704, + 0.02819826453924179, + 0.04861782118678093, + 0.08528425544500351, + 0.012239249423146248, + 0.014359706081449986, + -0.019882500171661377, + -0.03053932823240757, + 0.04383694753050804, + -0.05820803344249725, + -0.0014366158284246922, + 0.06986244767904282, + 0.06611118465662003, + 0.024454524740576744, + -0.02059408277273178, + -0.016752762719988823, + -0.01459463406354189, + -0.02889612317085266, + 0.04970743879675865, + -0.028303874656558037, + 0.03978912904858589, + -0.07312510907649994, + 0.05429210141301155, + 0.00571118388324976, + -0.02056923136115074, + 0.053339049220085144, + -0.018249599263072014, + -0.021281961351633072, + -0.05355891212821007, + 0.0478244312107563, + -0.06067035347223282, + -0.0008842060924507678, + 0.04420148581266403, + 0.000588231545407325, + 0.056371595710515976, + 0.014279269613325596, + -0.05001707002520561, + -0.037117116153240204, + 0.030044561251997948, + -0.05617158114910126, + 0.02152038738131523, + 0.017715860158205032, + 0.02034214325249195, + 0.021688375622034073, + -0.024712584912776947, + -0.03572659194469452, + -0.03006441332399845, + 0.11338905245065689, + 0.029146766290068626, + -0.01698526367545128, + -0.05355465039610863, + -0.0036588346119970083, + -0.0032888834830373526, + -0.022690337151288986, + -0.05653419718146324, + 0.053955987095832825, + -0.010936236009001732, + -0.05121518298983574, + -0.04233774170279503, + -0.0650610476732254, + -0.009094701148569584, + -0.00337587739340961, + 0.05269891023635864, + 0.05860234051942825, + 0.015521558932960033, + -0.038103096187114716, + -0.029688136652112007, + -0.011934547685086727, + -0.05070113763213158, + 0.025371648371219635, + 0.03601797670125961, + 0.021862944588065147, + -0.020703352987766266, + 0.05289195850491524, + -0.004169228952378035, + -0.03900706395506859, + -0.0029100535903126, + 0.003359412308782339, + -0.03696342185139656, + 0.007729679811745882, + 0.005611894652247429, + 0.04680318757891655, + 0.002203753450885415, + -0.057359859347343445, + 0.0586426742374897, + 0.027003217488527298, + -0.030223455280065536, + 0.06817735731601715, + 0.03476058319211006, + -0.011411039158701897, + -5.9986756241414696e-05, + -0.03633617237210274, + -0.016408616676926613, + 0.00833839550614357, + 0.0022074412554502487, + 0.048158638179302216, + -0.031786687672138214, + -0.028205247595906258, + -0.056731242686510086, + -0.023744143545627594, + -0.00782334990799427, + 0.03123593144118786, + -0.016950296238064766, + 0.01794753596186638, + 0.04291892051696777, + 0.0099559361115098, + -0.0012914348626509309, + -0.004629518836736679, + -0.05153423175215721, + 0.058259084820747375, + 0.056788213551044464, + -0.0333746112883091, + 0.030548732727766037, + 0.01471715047955513, + -0.002818142296746373, + -0.013207555748522282, + 0.022568998858332634, + 0.025705108419060707, + -0.014197800308465958, + -0.02527414821088314, + 0.0009442049195058644, + 0.005861984565854073, + 0.00919109396636486, + 0.012627449817955494, + 0.017443764954805374, + -0.0162491612136364, + 0.05474800989031792, + 0.02047792077064514, + 0.0003552198759280145, + 0.0005291366251185536, + 0.003957713954150677, + -0.073692187666893, + 0.044466596096754074, + 0.02759671024978161, + 0.03048691712319851, + 0.024890316650271416, + -0.04379572719335556, + -0.004758962895721197, + -0.012311465106904507, + 0.003943922929465771, + 0.035470347851514816, + -0.06701556593179703, + -0.0010001214686781168, + 0.06592956185340881, + 0.008649672381579876, + 0.005259859841316938, + -0.00453479727730155, + -0.026313234120607376, + 0.0128184137865901, + -0.04696577414870262, + 0.0357656292617321, + -0.007445288822054863, + 0.10806939005851746, + 0.0789022147655487, + -0.01642726920545101, + -0.042041581124067307, + -0.015044954605400562, + -0.020660532638430595, + -0.01043805480003357, + -0.011654903180897236, + -0.05754747614264488, + 0.06964936852455139, + 0.03990045189857483, + -0.0017825361574068666, + -0.0382373072206974, + 0.005986799951642752, + 0.022415796294808388, + -0.011907496489584446, + -0.015296644531190395, + 0.005779241677373648, + 0.051009099930524826, + -0.013554011471569538, + -0.036914244294166565, + -0.018791811540722847, + -0.03514847159385681, + -0.050969723612070084, + 0.07429437339305878, + -0.014117387123405933, + 0.01858820766210556, + 0.029953083023428917, + 0.013503451831638813, + 0.024872425943613052, + -0.01447504572570324, + -0.03305073082447052, + -0.03757826238870621, + 0.009820172563195229, + 0.004212466534227133, + 0.009773447178304195, + -0.03176327049732208, + -0.00981978140771389, + -0.018437808379530907, + -0.016843365505337715, + 0.04063236713409424, + 0.03664008155465126, + -0.017759712412953377, + 0.017491042613983154, + 0.017961829900741577, + -0.007718573324382305, + 0.08410634845495224, + 0.04713455215096474, + -0.030763784423470497, + -0.07868245244026184, + -0.04293506219983101, + -0.02663402259349823, + 0.06502995640039444, + 0.04134368151426315, + -0.0075789024122059345, + 0.037559330463409424, + -0.022960234433412552, + -0.03559660166501999, + 0.02433147467672825, + 0.004160139709711075, + -0.006933990400284529, + -0.018853498622775078, + -0.07674053311347961, + -0.015214351005852222, + -0.0031465317588299513, + -0.0032662826124578714, + 0.020626401528716087, + -0.023296812549233437, + 0.01533068809658289, + -0.018831759691238403, + -0.013347934931516647, + 0.05832105129957199, + 0.016617508605122566, + -0.06054726615548134, + 0.020946228876709938, + -0.05081603676080704, + 0.0005762121290899813, + -0.013293956406414509, + 0.05424816533923149, + -0.028400346636772156, + -0.008744322694838047, + -0.027219830080866814, + -0.009028765372931957, + 0.08349941670894623, + -0.02220912277698517, + -0.0035634897649288177, + 0.039803411811590195, + -0.009209544397890568, + -0.05272921174764633, + -0.03965644910931587, + -0.05518830195069313, + -0.0076417475938797, + 0.011989743448793888, + 0.07631900161504745, + 0.03853122144937515, + -0.03482687100768089, + 0.010916730388998985, + -0.012828757055103779, + 0.04919871687889099, + 0.05019025877118111, + -0.04743821546435356, + -0.024848056957125664, + 0.03214584290981293, + -0.03514641523361206, + -0.030496522784233093, + -0.005360030569136143, + -0.03538995608687401, + -0.016368992626667023, + -0.07339470833539963, + 0.022023534402251244, + -0.012556820176541805, + 0.018365638330578804, + 0.025001555681228638, + -0.029118210077285767, + -0.046666670590639114, + 0.008231466636061668, + 0.015543444082140923, + -0.018029138445854187, + 0.007146908901631832, + -0.009827123954892159, + -0.09648268669843674, + -0.03867226839065552, + -0.0066386335529387, + -0.03292228281497955, + 0.022209322080016136, + -0.048995133489370346, + -0.03118632733821869, + -0.017475144937634468, + 0.005314778070896864, + -0.010616753250360489, + -0.04724809527397156, + 0.027169331908226013, + 0.003503959160298109, + -0.06886278837919235, + 0.022409209981560707, + 0.008452179841697216, + -0.024392019957304, + -0.020817982032895088, + -0.004606961738318205, + -0.08660633116960526, + 0.031076667830348015, + 0.020726440474390984, + -0.011223231442272663, + 0.05015091598033905, + 0.021451715379953384, + 0.049609262496232986, + 0.05560477077960968, + -0.05192512646317482, + -0.016848105937242508, + 0.009753277525305748, + 0.03756638243794441, + -0.03334583342075348, + 0.040159404277801514, + 0.01897178590297699, + -0.056337252259254456, + 0.018127072602510452, + 8.343596709892154e-05, + 0.02721443772315979, + -0.037742555141448975, + 0.01802193559706211, + 0.09791397303342819, + -0.025166938081383705, + 0.07462649047374725, + -0.027766922488808632, + -0.06332777440547943, + -0.005818391218781471, + -0.018811773508787155, + -0.03425326570868492, + 0.003983109258115292, + -0.034356050193309784, + -0.04613350331783295, + 0.006219684612005949, + -0.02750561013817787, + 0.03812394291162491, + -0.029214290902018547, + -0.008362852968275547, + -0.046344004571437836, + 0.015400147996842861, + -0.027044160291552544, + 0.019668098539114, + 0.01860121265053749, + -0.02408520132303238, + -0.07096672058105469, + -0.0003313044144306332, + 0.024360060691833496, + -0.02565479651093483, + 0.033272501081228256, + -0.009740769863128662, + -0.07754906266927719, + -0.005022569093853235, + 0.01834244467318058, + -0.0670025572180748, + 0.0031950040720403194, + 0.016223441809415817, + 0.05652153119444847, + 0.05896124988794327, + -0.05402825400233269, + -0.007856715470552444, + 0.010221654549241066, + -0.005885730497539043, + 0.01112558413296938, + -0.03978840634226799, + -0.008038174360990524, + 0.048503343015909195, + -0.04076062887907028, + 0.05717281252145767, + 0.02310008741915226, + -0.015716947615146637, + 0.00578808831050992, + 0.005534487310796976, + 0.01627301797270775, + 0.012666025198996067, + -0.037932366132736206, + -0.02889685146510601, + 0.00509311119094491, + -0.015608384273946285, + -0.059495046734809875, + -0.02494220808148384, + 0.024446364492177963, + 0.03732331097126007, + -0.006206210236996412, + 0.03822293132543564, + -0.030338769778609276, + -0.10873781144618988, + -0.021372010931372643, + -0.04941859468817711, + -0.0004265901807229966, + -0.011848388239741325, + -0.040232446044683456, + 0.02904931642115116, + -0.0006163326324895024, + 0.04501201957464218, + -0.0009105035569518805, + -0.034277040511369705, + -0.028672119602560997, + 0.0012552812695503235, + 0.04327942058444023, + 0.0058600720949471, + 0.007959491573274136, + -0.0052106245420873165, + -0.01613856852054596, + 0.029123952612280846, + 0.007203509099781513, + 0.006210403982549906, + -0.053780049085617065, + -0.003420298220589757, + -0.03657878562808037, + 0.019055450335144997, + -0.07376986742019653, + -0.019189076498150826, + -0.007890082895755768, + -0.022230826318264008, + 0.006225301884114742, + 0.01237472239881754, + 0.06595351547002792, + 0.04492981359362602, + 0.01869170181453228, + 0.012387770228087902, + 0.05166162550449371, + -0.06800039112567902, + -0.03918451815843582, + -0.056165844202041626, + 0.02326592244207859, + -0.015541363507509232, + 0.033293239772319794, + -0.007216084748506546, + -0.012664951384067535, + 0.05342225730419159, + 0.009652439504861832, + 0.027964351698756218, + -0.016909338533878326, + 0.03330600634217262, + -0.060126710683107376, + -0.07517267763614655, + -0.025813739746809006, + -0.024271255359053612, + 0.011216769926249981, + -0.020943764597177505, + 0.01686793565750122, + -0.06828945130109787, + -0.018023250624537468, + -0.004829781129956245, + -0.022270847111940384, + 0.030936313793063164, + -0.013894669711589813, + 0.0368037149310112, + -0.05242981016635895, + -0.05051284283399582, + 0.06604990363121033, + 0.009301775135099888, + -0.014957845211029053, + -0.04281012713909149, + -0.0006833449588157237, + -0.005769087467342615, + -0.010068363510072231, + 0.058508969843387604, + 0.01898365654051304, + -0.018636951223015785, + 0.04689044877886772, + 0.056091975420713425, + -0.03881967067718506, + -0.019658103585243225, + -0.0003990831028204411, + 0.07142409682273865, + 0.012017408385872841, + -0.04087359085679054, + 0.03531723469495773, + 0.030207011848688126, + 0.005139552056789398, + -0.07084347307682037, + 0.009759706445038319, + -0.074960857629776, + 0.05481172725558281, + 0.028797954320907593, + -0.016217226162552834, + 0.03127933293581009, + 0.06848310679197311, + 0.0331764742732048, + -0.007261150050908327, + -0.023036431521177292, + -0.015215406194329262, + -0.056041885167360306, + -0.05146646127104759 + ], + "content_embedding": [ + -0.035467296838760376, + 0.05443365499377251, + 0.004722591955214739, + -0.022551164031028748, + 0.013528825715184212, + -0.01865273527801037, + 0.02473974972963333, + -0.0093984454870224, + -0.04820428788661957, + -0.011309967376291752, + -0.041853927075862885, + 0.02753269486129284, + 0.023483864963054657, + 0.0086299953982234, + -0.004760670010000467, + -0.011422916315495968, + 0.02231433242559433, + -0.018113020807504654, + 0.027575815096497536, + 0.008628769777715206, + 0.031078867614269257, + -0.022500742226839066, + 0.011097921058535576, + -0.020555853843688965, + 0.041947007179260254, + 0.007781036198139191, + -0.03356451168656349, + 0.05067972093820572, + -0.05009249970316887, + 0.013387891463935375, + 0.04737459868192673, + -0.02956528402864933, + -0.012283756397664547, + -0.02492530830204487, + -0.051903702318668365, + -0.020648062229156494, + 0.07008657604455948, + -0.05525917932391167, + -0.005968133453279734, + 0.042117420583963394, + 0.04600752145051956, + -0.023857053369283676, + 0.024955181404948235, + -0.019478371366858482, + 0.027009692043066025, + -0.0035888778511434793, + 0.050264179706573486, + -0.026319395750761032, + 0.02974606677889824, + -0.03574950620532036, + -0.0011404261458665133, + 0.00908538419753313, + -0.026853032410144806, + -0.01625720039010048, + -0.011155915446579456, + 0.012969470582902431, + -0.03395452722907066, + 0.004224491771310568, + 0.027397319674491882, + -0.02826162986457348, + 0.042576149106025696, + 0.04274202510714531, + -0.023343440145254135, + 0.031393349170684814, + 0.003865004051476717, + -0.068922258913517, + 0.021687647327780724, + -0.006593589670956135, + 0.014760294929146767, + -0.007734894752502441, + -0.0031233499757945538, + -0.014138679951429367, + 0.01479700393974781, + 0.05785622447729111, + -0.04781193286180496, + -0.02295715920627117, + -0.02882302924990654, + -0.018427176401019096, + -0.018964029848575592, + 0.06096252053976059, + 0.05383418872952461, + -0.0870966985821724, + 0.0031813366804271936, + 0.01873805560171604, + 0.046315208077430725, + -0.016668183729052544, + 0.007771935313940048, + -0.008389935828745365, + -0.03101789578795433, + 0.12752030789852142, + 0.03457779064774513, + 0.03240315988659859, + 0.048814207315444946, + 0.05700814723968506, + -0.06329526007175446, + 0.057182129472494125, + -0.027157682925462723, + -0.008035550825297832, + -0.02922128140926361, + -0.033899255096912384, + -0.013119292445480824, + 0.05552409961819649, + 0.04266372323036194, + -0.003065067809075117, + 0.03790399059653282, + 0.01804651878774166, + 0.018934324383735657, + 0.04061003401875496, + 0.03233874961733818, + 0.017353640869259834, + -0.045026157051324844, + 0.0002423059631837532, + 0.00812580157071352, + 0.017658300697803497, + -0.007964730262756348, + 0.01015512179583311, + 0.04046032205224037, + -0.06913582980632782, + 0.004168798215687275, + 0.03317571058869362, + 0.012463781051337719, + -0.020389260724186897, + -0.022882815450429916, + -0.015693804249167442, + 0.0500093474984169, + 0.05442529916763306, + -0.05275300145149231, + -0.0008568991324864328, + -0.009641895070672035, + -0.003380047157406807, + -0.019793419167399406, + 0.0063031697645783424, + -0.03327865153551102, + 0.016263391822576523, + 0.03218098729848862, + 0.022281551733613014, + -0.06236790120601654, + -0.06712637841701508, + 0.013925489969551563, + 0.01688770391047001, + 0.01467123068869114, + 0.029035737738013268, + -0.013510127551853657, + -0.0371820330619812, + 0.01489016879349947, + -0.05226032808423042, + -0.021125929430127144, + -0.002014611614868045, + -0.05400311201810837, + 0.019783688709139824, + -0.0014786357060074806, + -0.01895768567919731, + 0.01083068735897541, + -0.005890357308089733, + 0.003382777562364936, + -0.04273455590009689, + -0.0478648841381073, + 0.006365248002111912, + 0.04027433693408966, + 0.022969869896769524, + 0.06722807139158249, + 0.02113204449415207, + -0.03740633279085159, + 0.0656556561589241, + -0.014887429773807526, + 0.022357333451509476, + 0.036207813769578934, + 0.009992213919758797, + 0.03665810078382492, + 0.07260408997535706, + -0.005702183116227388, + -0.00880548357963562, + 0.033025965094566345, + -0.017093362286686897, + 0.039024271070957184, + 0.04158668965101242, + 0.008214588277041912, + -0.017436640337109566, + 0.05074054002761841, + -0.021646566689014435, + 0.0577220693230629, + -0.06182146817445755, + 0.03490613400936127, + 0.009574614465236664, + -0.05135552957653999, + -0.016593866050243378, + 0.001374077401123941, + -0.0582745335996151, + 0.009521838277578354, + -0.04114346206188202, + 0.05998831242322922, + -0.017294712364673615, + -0.017998410388827324, + -0.036417942494153976, + -0.014111478812992573, + -0.035168007016181946, + 0.04580182209610939, + 0.006420421414077282, + 0.012049577198922634, + -0.03691839054226875, + -0.041549112647771835, + -0.02593182772397995, + -0.07608001679182053, + -0.004325924441218376, + -0.029293090105056763, + 0.05871257558465004, + 0.04561365023255348, + -0.018353786319494247, + 0.018815817311406136, + -0.02768997848033905, + 0.10190171003341675, + 0.05626858025789261, + -0.006779504008591175, + 0.005354198161512613, + -0.053908295929431915, + -0.03453999012708664, + 0.02781379222869873, + -0.04989396408200264, + -0.03950505331158638, + 0.02282608300447464, + 0.006389955058693886, + -0.007375086657702923, + -0.016243990510702133, + 0.028544900938868523, + -0.020701216533780098, + 0.012176213786005974, + -0.019373498857021332, + 0.023940887302160263, + -0.03986368328332901, + -0.0040043736808001995, + -0.02535220980644226, + -0.08186554163694382, + 0.07860240340232849, + 0.004978376906365156, + 0.06400016695261002, + -0.02991490252315998, + -0.03288387134671211, + 0.03286135569214821, + 0.0247455183416605, + 0.08134172111749649, + 0.062203265726566315, + 0.017080431804060936, + -0.003969072364270687, + -0.024894852191209793, + -0.07480036467313766, + 0.03882874175906181, + -0.0074541885405778885, + -0.011322571896016598, + -0.06285038590431213, + 0.004618136677891016, + -0.019962741062045097, + 0.01853892207145691, + 0.002305575180798769, + 0.023541608825325966, + 0.017216432839632034, + -0.044929757714271545, + -0.022532327100634575, + 0.05122198164463043, + 0.0008766956743784249, + -0.025474006310105324, + 0.04030180349946022, + -0.013362268917262554, + 0.049265045672655106, + 0.001589711057022214, + 0.014848759397864342, + 0.0022126054391264915, + -0.028914116322994232, + -0.009881545789539814, + -0.010318109765648842, + 0.006385906133800745, + 0.010556558147072792, + 0.007666149642318487, + 0.016665013507008553, + 0.09090837836265564, + 0.008256189525127411, + -0.006583006586879492, + 0.0044986652210354805, + -0.0336960032582283, + 0.047732625156641006, + -0.007069372106343508, + -0.044969744980335236, + -0.0907006487250328, + -0.04223865643143654, + 0.007469010539352894, + 0.006147805601358414, + 0.04827409237623215, + 0.03519561514258385, + 0.032267000526189804, + 0.05173507332801819, + -0.016001909971237183, + 0.034578241407871246, + -0.02854917198419571, + -0.01587686315178871, + 0.03134807571768761, + -0.010930678807199001, + 0.044245973229408264, + 0.1186295673251152, + -0.031642355024814606, + 0.01669827103614807, + -0.026775898411870003, + -0.002936996053904295, + -0.013815718702971935, + -0.009453569538891315, + -0.035879991948604584, + -0.02232815884053707, + -0.009286822751164436, + -0.01117252279073, + 0.014098073355853558, + 0.023366371169686317, + 0.022420832887291908, + -0.029833031818270683, + 0.0013570807641372085, + -0.0211170744150877, + -0.027633074671030045, + -0.02915397845208645, + 0.023663034662604332, + 0.04199281334877014, + -0.0311698317527771, + 0.025238486006855965, + -0.00992826372385025, + 0.005087476689368486, + -0.050041183829307556, + -0.018602682277560234, + -0.06774407625198364, + -0.019117988646030426, + 0.08245334029197693, + 0.030311768874526024, + 0.020432988181710243, + -0.03738946095108986, + 0.04251522198319435, + 0.002886879490688443, + 0.0938342958688736, + -0.05836429446935654, + -0.0232597254216671, + 0.0074686286970973015, + -0.0020157117396593094, + -0.013439277186989784, + 0.02590363286435604, + 0.0034541902132332325, + 0.002955070696771145, + -0.0020802158396691084, + -0.011827156879007816, + -0.06622112542390823, + -0.05226997658610344, + -0.031827233731746674, + 0.0012936017010360956, + 0.01702217012643814, + -0.016136569902300835, + 0.04939497634768486, + 0.006943605840206146, + -0.05098084360361099, + 0.03143058344721794, + -0.004094736184924841, + -0.011557313613593578, + 0.000757173984311521, + -0.01120754610747099, + 0.036905039101839066, + 0.02395678497850895, + 0.009881307370960712, + 0.05312298238277435, + 0.05778184533119202, + 0.02520277164876461, + 0.020175758749246597, + -0.025740133598446846, + 0.04891965910792351, + 0.05155428871512413, + 0.04089348018169403, + 0.06249197572469711, + 0.02368168905377388, + -0.03247880935668945, + 0.019493652507662773, + -0.06181112304329872, + 0.019057979807257652, + 0.037210095673799515, + 0.02910085767507553, + 0.02495957538485527, + -0.08179862797260284, + -0.007498551160097122, + 0.036072876304388046, + -0.016061626374721527, + 0.0725645050406456, + 0.005645937751978636, + 0.0032921379897743464, + -0.029446475207805634, + 0.020205944776535034, + 0.002388844033703208, + -0.029442399740219116, + -0.031475961208343506, + 0.024486446753144264, + -0.038434699177742004, + -0.05131153389811516, + 0.00129043054766953, + -0.01692604087293148, + -0.007422945462167263, + -0.02433120459318161, + 0.004650108516216278, + -0.04251663386821747, + -0.009143602102994919, + 0.017507102340459824, + 0.042100246995687485, + -0.06103592365980148, + -0.0508011095225811, + -0.000937039265409112, + 0.025160834193229675, + -0.048878248780965805, + 0.010422220453619957, + -0.014773974195122719, + -0.06574267894029617, + 0.0027621325571089983, + -0.0019821953028440475, + 0.006184928119182587, + 0.024707674980163574, + -0.022308405488729477, + -0.06509386748075485, + 0.04186487942934036, + 0.0023416660260409117, + 0.0650840550661087, + 0.03807358071208, + -0.024585191160440445, + -0.017596496269106865, + 0.005341595038771629, + 0.03675152733922005, + 0.06293662637472153, + 0.010854244232177734, + -0.050199203193187714, + -0.037359531968832016, + 0.017929432913661003, + 0.023822667077183723, + 0.019726712256669998, + -0.00759292533621192, + 0.043509598821401596, + -0.0014670701930299401, + -0.0006681938539259136, + -0.0055070724338293076, + -0.07182206958532333, + 0.037307076156139374, + 0.06350742280483246, + 0.049223095178604126, + 0.017340589314699173, + 0.05529596656560898, + 0.023639194667339325, + -0.02478986792266369, + -0.02248029224574566, + -0.042737238109111786, + -0.0018032155930995941, + 0.05576873943209648, + 0.12722158432006836, + 0.004959811456501484, + -0.033451229333877563, + -0.007337609305977821, + 0.018852578476071358, + 0.031502317637205124, + 0.013375848531723022, + -0.0066598327830433846, + 0.07771285623311996, + -0.017693838104605675, + -0.030503049492836, + -0.04393269121646881, + 0.013323146849870682, + 0.010107941925525665, + 0.02004137821495533, + 0.0377974770963192, + 0.013478322885930538, + 0.024949608370661736, + -0.01634461060166359, + -0.015226340852677822, + 0.013924108818173409, + 0.0038409747648984194, + -0.00358059024438262, + -0.005057516973465681, + -0.008272752165794373, + 0.04373026266694069, + -0.0014998909318819642, + 0.009924792684614658, + -0.040317751467227936, + -0.04541180655360222, + 0.06625904142856598, + -0.028080880641937256, + 0.04732294753193855, + 0.0047000702470541, + 0.02857903018593788, + 0.004553706850856543, + -0.04188435524702072, + 0.023083623498678207, + -0.060619525611400604, + 0.01963491179049015, + -0.008608276024460793, + 0.0034778753761202097, + -0.016133952885866165, + 0.009059683419764042, + -0.0009118590969592333, + 0.08675801753997803, + 0.004535067826509476, + -0.021998068317770958, + -0.0789642184972763, + -0.033289894461631775, + -0.04486677423119545, + 0.014945252798497677, + 0.04513613134622574, + -0.05311649665236473, + 0.009399711154401302, + 0.004345519933849573, + -0.004021052736788988, + 0.01709410734474659, + -0.020986782386898994, + -0.011685016565024853, + -0.02048366330564022, + -0.08524532616138458, + -0.004114300478249788, + 0.040531281381845474, + -0.0005771859432570636, + 0.02984555996954441, + -0.0002479814866092056, + 0.04756562039256096, + -0.013039377517998219, + -0.09513615071773529, + 0.07444311678409576, + 0.0044719018042087555, + -0.09768522530794144, + 0.04403488337993622, + 0.013910059817135334, + 0.06657753884792328, + 0.026994489133358, + 0.03657658398151398, + -0.11561834812164307, + 0.02878704108297825, + -0.012593223713338375, + -0.01532658003270626, + 0.06045927479863167, + -0.04569881781935692, + -0.0029045850969851017, + 0.06762480735778809, + 0.012874988839030266, + -0.011422640644013882, + 0.025211291387677193, + -0.07570745050907135, + -0.018061399459838867, + -0.033531878143548965, + -0.010049374774098396, + 0.02582205832004547, + -0.015443898737430573, + 0.029427431523799896, + -0.02071801945567131, + 0.02054932527244091, + 0.017246615141630173, + -0.07276910543441772, + -0.053859222680330276, + 0.060189153999090195, + -0.04336293414235115, + -0.06396458297967911, + 0.08002400398254395, + -0.041166432201862335, + 0.000430541840614751, + -0.10547704994678497, + -0.014112395234405994, + -0.06070064380764961, + 0.01796649396419525, + -0.045275188982486725, + -0.0018861661665141582, + -0.0022482818458229303, + 0.004191190470010042, + 6.745498831151053e-05, + 0.07350871711969376, + -0.01797996647655964, + 0.03183342143893242, + -0.10409794747829437, + -0.0291685052216053, + 0.02071727253496647, + 0.021267961710691452, + -0.021560702472925186, + -0.05026571452617645, + -0.013422243297100067, + -0.0011607048800215125, + 0.016948888078331947, + -0.01588856242597103, + -0.05063013359904289, + 0.05952488258481026, + -0.05575632303953171, + -0.06906414031982422, + -0.004353572614490986, + -0.02773641049861908, + -0.043097492307424545, + 0.03103402815759182, + 0.02164989709854126, + 0.0013185666175559163, + 0.02606332302093506, + -0.059723641723394394, + -0.008657965809106827, + 0.06580374389886856, + -0.020771000534296036, + -0.022305399179458618, + 0.008068420924246311, + -0.004975682124495506, + -0.033461254090070724, + -0.040884874761104584, + 0.052932899445295334, + -0.0054899416863918304, + -0.03155453875660896, + 0.002439886098727584, + -0.0361575223505497, + -0.03652369976043701, + -0.010043974034488201, + 0.01681465655565262, + 3.9381829992635176e-05, + 0.011527255177497864, + 0.06904088705778122, + -0.005501871462911367, + 0.0259085800498724, + -0.021282166242599487, + -0.03796657174825668, + -0.002881726250052452, + -0.018672630190849304, + -0.003463461296632886, + -0.008101037703454494, + -0.019035371020436287, + -0.0025111068971455097, + 0.03926572576165199, + -0.0513470396399498, + 0.04829537495970726, + -0.001188569120131433, + -0.0121685229241848, + -0.059901442378759384, + 0.07364466786384583, + 0.006562754046171904, + 0.00707247294485569, + 0.028408123180270195, + -0.02494397945702076, + -0.04187498614192009, + 0.0066386316902935505, + 0.06244710460305214, + 0.02900586649775505, + 0.04932861402630806, + -0.04402685537934303, + -0.006739918142557144, + -0.0502609983086586, + -0.0015801729168742895, + -0.026301531121134758, + -0.024203499779105186, + -0.019028285518288612, + 0.055076178163290024, + 0.009030332788825035, + -0.04907704144716263, + -0.019399652257561684, + 0.009713590145111084, + 0.05042042210698128, + -0.00020382895309012383, + -0.010405965149402618, + 0.01872927136719227, + 0.002546734409406781, + 0.020958390086889267, + 0.0634453296661377, + 0.04931068792939186, + -0.014592095278203487, + 0.0075549716129899025, + 0.02017839439213276, + 0.03344761207699776, + -0.005005223676562309, + 0.01818416453897953, + -0.05528895929455757, + 0.03879536688327789, + 0.018610917031764984, + -0.029319677501916885, + -0.00493574095889926, + 0.01762193627655506, + 0.008898349478840828, + -0.017192110419273376, + -0.03400791808962822, + -0.026591692119836807, + -0.03768239915370941, + 0.007602880708873272, + -0.020310858264565468, + -0.0036565649788826704, + -0.00616755336523056, + -0.057577136904001236, + 0.008387535810470581, + 0.021555650979280472, + -0.01923108845949173, + -0.019822189584374428, + -0.03861076384782791, + -0.04258895292878151, + 0.0005390863516367972, + -0.009946192614734173, + 0.04911184310913086, + -0.05009220167994499, + 0.00297548552043736, + 0.019344164058566093, + 0.005506082437932491, + 0.018321573734283447, + -0.027131471782922745, + -0.052699681371450424, + -0.02292790077626705, + 0.0568309910595417, + -0.008538461290299892, + -0.05772045999765396, + 0.018903164193034172, + -0.03690820932388306, + -0.034110669046640396, + -0.008381159976124763, + 0.03926640748977661, + 0.04370100051164627, + -0.007475440856069326, + 0.06952399015426636, + -0.0031064660288393497, + 0.040785301476716995, + -0.008955440483987331, + -0.016698094084858894, + -0.007412049453705549, + 0.022290483117103577, + 0.006028760224580765, + -0.019992463290691376, + -0.04154061898589134, + -0.023284243419766426, + 0.04972238838672638, + 0.0008079080143943429, + -0.0057194954715669155, + 0.037808094173669815, + -0.00983867421746254, + -0.030191699042916298, + 0.014910571277141571, + 0.0004001195775344968, + 0.08586109429597855, + -0.014850648120045662, + -0.07815773040056229, + 0.05393945425748825, + -0.019953783601522446, + 0.0016224493738263845, + 0.018219690769910812, + 0.014311570674180984, + 0.05567210912704468, + 0.004363455809652805, + 0.01872050203382969, + -0.05933142080903053, + -0.04872509092092514, + 0.02652469463646412, + -0.04346488043665886, + -0.027931908145546913, + -0.03355146571993828, + 0.004589339718222618, + -0.05587214604020119, + -0.015419036149978638, + 0.04789341986179352, + -0.059666525572538376, + 0.00552733987569809, + 0.012681040912866592, + 0.007240649312734604, + -0.0045613935217261314, + -0.060716547071933746, + 0.03223521634936333, + 0.024270178750157356, + -0.025784391909837723, + -0.01736401580274105, + -0.0014227400533854961, + -0.011367680504918098, + -0.035415612161159515, + -0.01793254353106022, + 0.033805977553129196, + -0.0080083217471838, + 0.021929381415247917, + 0.012236963026225567, + 0.002641203347593546, + 0.0067292568273842335, + -0.007680798415094614, + -0.02231515571475029, + 0.023524953052401543, + 0.010132606141269207, + 0.0030864113941788673, + -0.03816894069314003, + -0.0007171767647378147 + ], + "chunk_ind": 0 + } +] \ No newline at end of file diff --git a/backend/danswer/seeding/load_docs.py b/backend/danswer/seeding/load_docs.py new file mode 100644 index 00000000000..2756e7ddf61 --- /dev/null +++ b/backend/danswer/seeding/load_docs.py @@ -0,0 +1,212 @@ +import datetime +import json +import os +from typing import cast + +from sqlalchemy.orm import Session + +from danswer.access.models import default_public_access +from danswer.configs.constants import DEFAULT_BOOST +from danswer.configs.constants import DocumentSource +from danswer.configs.constants import KV_DOCUMENTS_SEEDED_KEY +from danswer.configs.model_configs import DEFAULT_DOCUMENT_ENCODER_MODEL +from danswer.connectors.models import Document +from danswer.connectors.models import IndexAttemptMetadata +from danswer.connectors.models import InputType +from danswer.connectors.models import Section +from danswer.db.connector import check_connectors_exist +from danswer.db.connector import create_connector +from danswer.db.connector_credential_pair import add_credential_to_connector +from danswer.db.credentials import PUBLIC_CREDENTIAL_ID +from danswer.db.document import check_docs_exist +from danswer.db.enums import AccessType +from danswer.db.enums import ConnectorCredentialPairStatus +from danswer.db.index_attempt import mock_successful_index_attempt +from danswer.db.search_settings import get_current_search_settings +from danswer.document_index.factory import get_default_document_index +from danswer.indexing.indexing_pipeline import index_doc_batch_prepare +from danswer.indexing.models import ChunkEmbedding +from danswer.indexing.models import DocMetadataAwareIndexChunk +from danswer.key_value_store.factory import get_kv_store +from danswer.key_value_store.interface import KvKeyNotFoundError +from danswer.server.documents.models import ConnectorBase +from danswer.utils.logger import setup_logger +from danswer.utils.retry_wrapper import retry_builder + + +logger = setup_logger() + + +def _create_indexable_chunks( + preprocessed_docs: list[dict], +) -> tuple[list[Document], list[DocMetadataAwareIndexChunk]]: + ids_to_documents = {} + chunks = [] + for preprocessed_doc in preprocessed_docs: + document = Document( + id=preprocessed_doc["url"], # For Web connector, the URL is the ID + # The section is not really used past this point since we have already done the other processing + # for the chunking and embedding. + sections=[ + Section(text=preprocessed_doc["content"], link=preprocessed_doc["url"]) + ], + source=DocumentSource.WEB, + semantic_identifier=preprocessed_doc["title"], + metadata={}, + doc_updated_at=None, + primary_owners=[], + secondary_owners=[], + ) + if preprocessed_doc["chunk_ind"] == 0: + ids_to_documents[document.id] = document + + chunk = DocMetadataAwareIndexChunk( + chunk_id=preprocessed_doc["chunk_ind"], + blurb=preprocessed_doc["content"] + .split(".", 1)[0] + .split("!", 1)[0] + .split("?", 1)[0], + content=preprocessed_doc["content"], + source_links={0: preprocessed_doc["url"]}, + section_continuation=False, + source_document=document, + title_prefix=preprocessed_doc["title"], + metadata_suffix_semantic="", + metadata_suffix_keyword="", + mini_chunk_texts=None, + large_chunk_reference_ids=[], + embeddings=ChunkEmbedding( + full_embedding=preprocessed_doc["content_embedding"], + mini_chunk_embeddings=[], + ), + title_embedding=preprocessed_doc["title_embedding"], + tenant_id=None, + access=default_public_access, + document_sets=set(), + boost=DEFAULT_BOOST, + ) + chunks.append(chunk) + + return list(ids_to_documents.values()), chunks + + +def seed_initial_documents(db_session: Session) -> None: + """ + Seed initial documents so users don't have an empty index to start + + Documents are only loaded if: + - This is the first setup (if the user deletes the docs, we don't load them again) + - The index is empty, there are no docs and no (non-default) connectors + - The user has not updated the embedding models + - If they do, then we have to actually index the website + - If the embedding model is already updated on server startup, they're not a new user + + Note that regardless of any search settings, the default documents are always loaded with + the predetermined chunk sizes and single pass embedding. + + Steps are as follows: + - Check if this needs to run + - Create the connector representing this + - Create the cc-pair (attaching the public credential) and mocking values like the last success + - Indexing the documents into Postgres + - Indexing the documents into Vespa + - Create a fake index attempt with fake times + """ + logger.info("Seeding initial documents") + + kv_store = get_kv_store() + try: + kv_store.load(KV_DOCUMENTS_SEEDED_KEY) + logger.info("Documents already seeded, skipping") + return + except KvKeyNotFoundError: + pass + + if check_docs_exist(db_session): + logger.info("Documents already exist, skipping") + return + + if check_connectors_exist(db_session): + logger.info("Connectors already exist, skipping") + return + + search_settings = get_current_search_settings(db_session) + if search_settings.model_name != DEFAULT_DOCUMENT_ENCODER_MODEL: + logger.info("Embedding model has been updated, skipping") + return + + document_index = get_default_document_index( + primary_index_name=search_settings.index_name, secondary_index_name=None + ) + + # Create a connector so the user can delete it if they want + # or reindex it with a new search model if they want + connector_data = ConnectorBase( + name="Sample Use Cases", + source=DocumentSource.WEB, + input_type=InputType.LOAD_STATE, + connector_specific_config={ + "base_url": "https://docs.danswer.dev/more/use_cases", + "web_connector_type": "recursive", + }, + refresh_freq=None, # Never refresh by default + prune_freq=None, + indexing_start=None, + ) + + connector = create_connector(db_session, connector_data) + connector_id = cast(int, connector.id) + + last_index_time = datetime.datetime.now(datetime.timezone.utc) + + result = add_credential_to_connector( + db_session=db_session, + user=None, + connector_id=connector_id, + credential_id=PUBLIC_CREDENTIAL_ID, + access_type=AccessType.PUBLIC, + cc_pair_name=connector_data.name, + groups=None, + initial_status=ConnectorCredentialPairStatus.PAUSED, + last_successful_index_time=last_index_time, + ) + cc_pair_id = cast(int, result.data) + + initial_docs_path = os.path.join( + os.getcwd(), "danswer", "seeding", "initial_docs.json" + ) + processed_docs = json.load(open(initial_docs_path)) + + docs, chunks = _create_indexable_chunks(processed_docs) + + index_doc_batch_prepare( + document_batch=docs, + index_attempt_metadata=IndexAttemptMetadata( + connector_id=connector_id, + credential_id=PUBLIC_CREDENTIAL_ID, + ), + db_session=db_session, + ignore_time_skip=True, # Doesn't actually matter here + ) + + # In this case since there are no other connectors running in the background + # and this is a fresh deployment, there is no need to grab any locks + logger.info( + "Indexing seeding documents into Vespa " + "(Vespa may take a few seconds to become ready after receiving the schema)" + ) + + # Retries here because the index may take a few seconds to become ready + # as we just sent over the Vespa schema and there is a slight delay + index_with_retries = retry_builder()(document_index.index) + index_with_retries(chunks=chunks) + + # Mock a run for the UI even though it did not actually call out to anything + mock_successful_index_attempt( + connector_credential_pair_id=cc_pair_id, + search_settings_id=search_settings.id, + docs_indexed=len(docs), + db_session=db_session, + ) + + kv_store.store(KV_DOCUMENTS_SEEDED_KEY, True) diff --git a/backend/danswer/server/documents/cc_pair.py b/backend/danswer/server/documents/cc_pair.py index db35807ad54..ddc084498ba 100644 --- a/backend/danswer/server/documents/cc_pair.py +++ b/backend/danswer/server/documents/cc_pair.py @@ -11,6 +11,7 @@ from danswer.auth.users import current_curator_or_admin_user from danswer.auth.users import current_user +from danswer.background.celery.celery_redis import RedisConnectorIndexing from danswer.background.celery.celery_redis import RedisConnectorPruning from danswer.background.celery.celery_utils import get_deletion_attempt_snapshot from danswer.background.celery.tasks.pruning.tasks import ( @@ -24,7 +25,8 @@ update_connector_credential_pair_from_id, ) from danswer.db.document import get_document_counts_for_cc_pairs -from danswer.db.engine import current_tenant_id +from danswer.db.engine import CURRENT_TENANT_ID_CONTEXTVAR +from danswer.db.engine import get_current_tenant_id from danswer.db.engine import get_session from danswer.db.enums import AccessType from danswer.db.enums import ConnectorCredentialPairStatus @@ -34,6 +36,7 @@ from danswer.db.index_attempt import get_latest_index_attempt_for_cc_pair_id from danswer.db.index_attempt import get_paginated_index_attempts_for_cc_pair_id from danswer.db.models import User +from danswer.db.search_settings import get_current_search_settings from danswer.db.tasks import check_task_is_live_and_not_timed_out from danswer.db.tasks import get_latest_task from danswer.redis.redis_pool import get_redis_client @@ -92,7 +95,10 @@ def get_cc_pair_full_info( cc_pair_id: int, user: User | None = Depends(current_curator_or_admin_user), db_session: Session = Depends(get_session), + tenant_id: str | None = Depends(get_current_tenant_id), ) -> CCPairFullInfo: + r = get_redis_client(tenant_id=tenant_id) + cc_pair = get_connector_credential_pair_from_id( cc_pair_id, db_session, user, get_editable=False ) @@ -122,11 +128,16 @@ def get_cc_pair_full_info( latest_attempt = get_latest_index_attempt_for_cc_pair_id( db_session=db_session, - connector_credential_pair_id=cc_pair.id, + connector_credential_pair_id=cc_pair_id, secondary_index=False, only_finished=False, ) + search_settings = get_current_search_settings(db_session) + rci = RedisConnectorIndexing( + cc_pair_id=cc_pair_id, search_settings_id=search_settings.id + ) + return CCPairFullInfo.from_models( cc_pair_model=cc_pair, number_of_index_attempts=count_index_attempts_for_connector( @@ -138,9 +149,11 @@ def get_cc_pair_full_info( connector_id=cc_pair.connector_id, credential_id=cc_pair.credential_id, db_session=db_session, + tenant_id=tenant_id, ), num_docs_indexed=documents_indexed, is_editable_for_current_user=is_editable_for_current_user, + indexing=rci.is_indexing(r), ) @@ -233,6 +246,7 @@ def prune_cc_pair( cc_pair_id: int, user: User = Depends(current_curator_or_admin_user), db_session: Session = Depends(get_session), + tenant_id: str | None = Depends(get_current_tenant_id), ) -> StatusResponse[list[int]]: """Triggers pruning on a particular cc_pair immediately""" @@ -248,9 +262,9 @@ def prune_cc_pair( detail="Connection not found for current user's permissions", ) - r = get_redis_client() + r = get_redis_client(tenant_id=tenant_id) rcp = RedisConnectorPruning(cc_pair_id) - if rcp.is_pruning(db_session, r): + if rcp.is_pruning(r): raise HTTPException( status_code=HTTPStatus.CONFLICT, detail="Pruning task already in progress.", @@ -263,7 +277,7 @@ def prune_cc_pair( f"{cc_pair.connector.name} connector." ) tasks_created = try_creating_prune_generator_task( - primary_app, cc_pair, db_session, r, current_tenant_id.get() + primary_app, cc_pair, db_session, r, CURRENT_TENANT_ID_CONTEXTVAR.get() ) if not tasks_created: raise HTTPException( @@ -349,7 +363,9 @@ def sync_cc_pair( logger.info(f"Syncing the {cc_pair.connector.name} connector.") sync_external_doc_permissions_task.apply_async( - kwargs=dict(cc_pair_id=cc_pair_id, tenant_id=current_tenant_id.get()), + kwargs=dict( + cc_pair_id=cc_pair_id, tenant_id=CURRENT_TENANT_ID_CONTEXTVAR.get() + ), ) return StatusResponse( diff --git a/backend/danswer/server/documents/connector.py b/backend/danswer/server/documents/connector.py index 54d11e867bd..1ba0ab13e2c 100644 --- a/backend/danswer/server/documents/connector.py +++ b/backend/danswer/server/documents/connector.py @@ -60,6 +60,8 @@ from danswer.db.connector_credential_pair import get_cc_pair_groups_for_ids from danswer.db.connector_credential_pair import get_connector_credential_pair from danswer.db.connector_credential_pair import get_connector_credential_pairs +from danswer.db.credentials import cleanup_gmail_credentials +from danswer.db.credentials import cleanup_google_drive_credentials from danswer.db.credentials import create_credential from danswer.db.credentials import delete_gmail_service_account_credentials from danswer.db.credentials import delete_google_drive_service_account_credentials @@ -143,9 +145,11 @@ def upsert_google_app_gmail_credentials( @router.delete("/admin/connector/gmail/app-credential") def delete_google_app_gmail_credentials( _: User = Depends(current_admin_user), + db_session: Session = Depends(get_session), ) -> StatusResponse: try: delete_google_app_gmail_cred() + cleanup_gmail_credentials(db_session=db_session) except KvKeyNotFoundError as e: raise HTTPException(status_code=400, detail=str(e)) @@ -181,9 +185,11 @@ def upsert_google_app_credentials( @router.delete("/admin/connector/google-drive/app-credential") def delete_google_app_credentials( _: User = Depends(current_admin_user), + db_session: Session = Depends(get_session), ) -> StatusResponse: try: delete_google_app_cred() + cleanup_google_drive_credentials(db_session=db_session) except KvKeyNotFoundError as e: raise HTTPException(status_code=400, detail=str(e)) @@ -221,9 +227,11 @@ def upsert_google_service_gmail_account_key( @router.delete("/admin/connector/gmail/service-account-key") def delete_google_service_gmail_account_key( _: User = Depends(current_admin_user), + db_session: Session = Depends(get_session), ) -> StatusResponse: try: delete_gmail_service_account_key() + cleanup_gmail_credentials(db_session=db_session) except KvKeyNotFoundError as e: raise HTTPException(status_code=400, detail=str(e)) @@ -261,9 +269,11 @@ def upsert_google_service_account_key( @router.delete("/admin/connector/google-drive/service-account-key") def delete_google_service_account_key( _: User = Depends(current_admin_user), + db_session: Session = Depends(get_session), ) -> StatusResponse: try: delete_service_account_key() + cleanup_google_drive_credentials(db_session=db_session) except KvKeyNotFoundError as e: raise HTTPException(status_code=400, detail=str(e)) @@ -483,10 +493,11 @@ def get_connector_indexing_status( get_editable: bool = Query( False, description="If true, return editable document sets" ), + tenant_id: str | None = Depends(get_current_tenant_id), ) -> list[ConnectorIndexingStatus]: indexing_statuses: list[ConnectorIndexingStatus] = [] - r = get_redis_client() + r = get_redis_client(tenant_id=tenant_id) # NOTE: If the connector is deleting behind the scenes, # accessing cc_pairs can be inconsistent and members like @@ -607,6 +618,7 @@ def get_connector_indexing_status( connector_id=connector.id, credential_id=credential.id, db_session=db_session, + tenant_id=tenant_id, ), is_deletable=check_deletion_attempt_is_allowed( connector_credential_pair=cc_pair, @@ -684,15 +696,18 @@ def create_connector_with_mock_credential( connector_response = create_connector( db_session=db_session, connector_data=connector_data ) + mock_credential = CredentialBase( credential_json={}, admin_public=True, source=connector_data.source ) credential = create_credential( mock_credential, user=user, db_session=db_session ) + access_type = ( AccessType.PUBLIC if connector_data.is_public else AccessType.PRIVATE ) + response = add_credential_to_connector( db_session=db_session, user=user, @@ -776,7 +791,7 @@ def connector_run_once( """Used to trigger indexing on a set of cc_pairs associated with a single connector.""" - r = get_redis_client() + r = get_redis_client(tenant_id=tenant_id) connector_id = run_info.connector_id specified_credential_ids = run_info.credential_ids diff --git a/backend/danswer/server/documents/credential.py b/backend/danswer/server/documents/credential.py index 3d965481bf5..2c6e41bf968 100644 --- a/backend/danswer/server/documents/credential.py +++ b/backend/danswer/server/documents/credential.py @@ -8,6 +8,8 @@ from danswer.auth.users import current_curator_or_admin_user from danswer.auth.users import current_user from danswer.db.credentials import alter_credential +from danswer.db.credentials import cleanup_gmail_credentials +from danswer.db.credentials import cleanup_google_drive_credentials from danswer.db.credentials import create_credential from danswer.db.credentials import CREDENTIAL_PERMISSIONS_TO_IGNORE from danswer.db.credentials import delete_credential @@ -138,6 +140,12 @@ def create_credential_from_model( object_is_public=credential_info.curator_public, ) + # Temporary fix for empty Google App credentials + if credential_info.source == DocumentSource.GMAIL: + cleanup_gmail_credentials(db_session=db_session) + if credential_info.source == DocumentSource.GOOGLE_DRIVE: + cleanup_google_drive_credentials(db_session=db_session) + credential = create_credential(credential_info, user, db_session) return ObjectCreationIdResponse( id=credential.id, diff --git a/backend/danswer/server/documents/models.py b/backend/danswer/server/documents/models.py index 780d8a3f28e..fcbc0a76a12 100644 --- a/backend/danswer/server/documents/models.py +++ b/backend/danswer/server/documents/models.py @@ -222,6 +222,7 @@ class CCPairFullInfo(BaseModel): access_type: AccessType is_editable_for_current_user: bool deletion_failure_message: str | None + indexing: bool @classmethod def from_models( @@ -232,6 +233,7 @@ def from_models( last_index_attempt: IndexAttempt | None, num_docs_indexed: int, # not ideal, but this must be computed separately is_editable_for_current_user: bool, + indexing: bool, ) -> "CCPairFullInfo": # figure out if we need to artificially deflate the number of docs indexed. # This is required since the total number of docs indexed by a CC Pair is @@ -265,6 +267,7 @@ def from_models( access_type=cc_pair_model.access_type, is_editable_for_current_user=is_editable_for_current_user, deletion_failure_message=cc_pair_model.deletion_failure_message, + indexing=indexing, ) diff --git a/backend/danswer/server/manage/administrative.py b/backend/danswer/server/manage/administrative.py index d16aa59c4cb..1ceeb776abc 100644 --- a/backend/danswer/server/manage/administrative.py +++ b/backend/danswer/server/manage/administrative.py @@ -19,7 +19,6 @@ from danswer.db.connector_credential_pair import ( update_connector_credential_pair_from_id, ) -from danswer.db.deletion_attempt import check_deletion_attempt_is_allowed from danswer.db.engine import get_current_tenant_id from danswer.db.engine import get_session from danswer.db.enums import ConnectorCredentialPairStatus @@ -175,15 +174,19 @@ def create_deletion_attempt_for_connector_id( cc_pair_id=cc_pair.id, db_session=db_session, include_secondary_index=True ) + # TODO(rkuo): 2024-10-24 - check_deletion_attempt_is_allowed shouldn't be necessary + # any more due to background locking improvements. + # Remove the below permanently if everything is behaving for 30 days. + # Check if the deletion attempt should be allowed - deletion_attempt_disallowed_reason = check_deletion_attempt_is_allowed( - connector_credential_pair=cc_pair, db_session=db_session - ) - if deletion_attempt_disallowed_reason: - raise HTTPException( - status_code=400, - detail=deletion_attempt_disallowed_reason, - ) + # deletion_attempt_disallowed_reason = check_deletion_attempt_is_allowed( + # connector_credential_pair=cc_pair, db_session=db_session + # ) + # if deletion_attempt_disallowed_reason: + # raise HTTPException( + # status_code=400, + # detail=deletion_attempt_disallowed_reason, + # ) # mark as deleting update_connector_credential_pair_from_id( diff --git a/backend/danswer/server/manage/llm/api.py b/backend/danswer/server/manage/llm/api.py index 06501d6834c..9cac96236b0 100644 --- a/backend/danswer/server/manage/llm/api.py +++ b/backend/danswer/server/manage/llm/api.py @@ -54,6 +54,7 @@ def test_llm_configuration( api_base=test_llm_request.api_base, api_version=test_llm_request.api_version, custom_config=test_llm_request.custom_config, + deployment_name=test_llm_request.deployment_name, ) functions_with_args: list[tuple[Callable, tuple]] = [(test_llm, (llm,))] @@ -70,6 +71,7 @@ def test_llm_configuration( api_base=test_llm_request.api_base, api_version=test_llm_request.api_version, custom_config=test_llm_request.custom_config, + deployment_name=test_llm_request.deployment_name, ) functions_with_args.append((test_llm, (fast_llm,))) diff --git a/backend/danswer/server/manage/llm/models.py b/backend/danswer/server/manage/llm/models.py index 2e3b3844807..9b371099c57 100644 --- a/backend/danswer/server/manage/llm/models.py +++ b/backend/danswer/server/manage/llm/models.py @@ -21,6 +21,7 @@ class TestLLMRequest(BaseModel): # model level default_model_name: str fast_default_model_name: str | None = None + deployment_name: str | None = None class LLMProviderDescriptor(BaseModel): diff --git a/backend/danswer/server/manage/users.py b/backend/danswer/server/manage/users.py index ae2ab8c6e8c..cd2ffe08422 100644 --- a/backend/danswer/server/manage/users.py +++ b/backend/danswer/server/manage/users.py @@ -38,7 +38,7 @@ from danswer.configs.app_configs import VALID_EMAIL_DOMAINS from danswer.configs.constants import AuthType from danswer.db.auth import get_total_users -from danswer.db.engine import current_tenant_id +from danswer.db.engine import CURRENT_TENANT_ID_CONTEXTVAR from danswer.db.engine import get_session from danswer.db.models import AccessToken from danswer.db.models import DocumentSet__User @@ -188,7 +188,7 @@ def bulk_invite_users( status_code=400, detail="Auth is disabled, cannot invite users" ) - tenant_id = current_tenant_id.get() + tenant_id = CURRENT_TENANT_ID_CONTEXTVAR.get() normalized_emails = [] try: @@ -222,7 +222,9 @@ def bulk_invite_users( return number_of_invited_users try: logger.info("Registering tenant users") - register_tenant_users(current_tenant_id.get(), get_total_users(db_session)) + register_tenant_users( + CURRENT_TENANT_ID_CONTEXTVAR.get(), get_total_users(db_session) + ) if ENABLE_EMAIL_INVITES: try: for email in all_emails: @@ -250,13 +252,15 @@ def remove_invited_user( user_emails = get_invited_users() remaining_users = [user for user in user_emails if user != user_email.user_email] - tenant_id = current_tenant_id.get() + tenant_id = CURRENT_TENANT_ID_CONTEXTVAR.get() remove_users_from_tenant([user_email.user_email], tenant_id) number_of_invited_users = write_invited_users(remaining_users) try: if MULTI_TENANT: - register_tenant_users(current_tenant_id.get(), get_total_users(db_session)) + register_tenant_users( + CURRENT_TENANT_ID_CONTEXTVAR.get(), get_total_users(db_session) + ) except Exception: logger.error( "Request to update number of seats taken in control plane failed. " diff --git a/backend/danswer/server/query_and_chat/models.py b/backend/danswer/server/query_and_chat/models.py index 42f4100a24b..1ca14f9283f 100644 --- a/backend/danswer/server/query_and_chat/models.py +++ b/backend/danswer/server/query_and_chat/models.py @@ -108,6 +108,10 @@ class CreateChatMessageRequest(ChunkContext): # used for seeded chats to kick off the generation of an AI answer use_existing_user_message: bool = False + # forces the LLM to return a structured response, see + # https://platform.openai.com/docs/guides/structured-outputs/introduction + structured_response_format: dict | None = None + @model_validator(mode="after") def check_search_doc_ids_or_retrieval_options(self) -> "CreateChatMessageRequest": if self.search_doc_ids is None and self.retrieval_options is None: diff --git a/backend/danswer/server/query_and_chat/token_limit.py b/backend/danswer/server/query_and_chat/token_limit.py index 6221eae3346..ec94e2ece4d 100644 --- a/backend/danswer/server/query_and_chat/token_limit.py +++ b/backend/danswer/server/query_and_chat/token_limit.py @@ -21,7 +21,7 @@ from danswer.utils.logger import setup_logger from danswer.utils.variable_functionality import fetch_versioned_implementation from ee.danswer.db.token_limit import fetch_all_global_token_rate_limits -from shared_configs.configs import current_tenant_id +from shared_configs.configs import CURRENT_TENANT_ID_CONTEXTVAR logger = setup_logger() @@ -41,7 +41,7 @@ def check_token_rate_limits( versioned_rate_limit_strategy = fetch_versioned_implementation( "danswer.server.query_and_chat.token_limit", "_check_token_rate_limits" ) - return versioned_rate_limit_strategy(user, current_tenant_id.get()) + return versioned_rate_limit_strategy(user, CURRENT_TENANT_ID_CONTEXTVAR.get()) def _check_token_rate_limits(_: User | None, tenant_id: str | None) -> None: diff --git a/backend/danswer/server/settings/api.py b/backend/danswer/server/settings/api.py index 35ab0b12c6d..7ff4de55c2a 100644 --- a/backend/danswer/server/settings/api.py +++ b/backend/danswer/server/settings/api.py @@ -53,7 +53,7 @@ def fetch_settings( """Settings and notifications are stuffed into this single endpoint to reduce number of Postgres calls""" general_settings = load_settings() - user_notifications = get_reindex_notification(user, db_session) + settings_notifications = get_settings_notifications(user, db_session) try: kv_store = get_kv_store() @@ -63,20 +63,29 @@ def fetch_settings( return UserSettings( **general_settings.model_dump(), - notifications=user_notifications, + notifications=settings_notifications, needs_reindexing=needs_reindexing, ) -def get_reindex_notification( +def get_settings_notifications( user: User | None, db_session: Session ) -> list[Notification]: - """Get notifications for the user, currently the logic is very specific to the reindexing flag""" + """Get notifications for settings page, including product gating and reindex notifications""" + # Check for product gating notification + product_notif = get_notifications( + user=None, + notif_type=NotificationType.TRIAL_ENDS_TWO_DAYS, + db_session=db_session, + ) + notifications = [Notification.from_model(product_notif[0])] if product_notif else [] + + # Only show reindex notifications to admins is_admin = is_user_admin(user) if not is_admin: - # Reindexing flag should only be shown to admins, basic users can't trigger it anyway - return [] + return notifications + # Check if reindexing is needed kv_store = get_kv_store() try: needs_index = cast(bool, kv_store.load(KV_REINDEX_KEY)) @@ -84,12 +93,12 @@ def get_reindex_notification( dismiss_all_notifications( notif_type=NotificationType.REINDEX, db_session=db_session ) - return [] + return notifications except KvKeyNotFoundError: # If something goes wrong and the flag is gone, better to not start a reindexing # it's a heavyweight long running job and maybe this flag is cleaned up later logger.warning("Could not find reindex flag") - return [] + return notifications try: # Need a transaction in order to prevent under-counting current notifications @@ -107,7 +116,9 @@ def get_reindex_notification( ) db_session.flush() db_session.commit() - return [Notification.from_model(notif)] + + notifications.append(Notification.from_model(notif)) + return notifications if len(reindex_notifs) > 1: logger.error("User has multiple reindex notifications") @@ -118,8 +129,9 @@ def get_reindex_notification( ) db_session.commit() - return [Notification.from_model(reindex_notif)] + notifications.append(Notification.from_model(reindex_notif)) + return notifications except SQLAlchemyError: logger.exception("Error while processing notifications") db_session.rollback() - return [] + return notifications diff --git a/backend/danswer/setup.py b/backend/danswer/setup.py index 747fe809451..a27580a2b15 100644 --- a/backend/danswer/setup.py +++ b/backend/danswer/setup.py @@ -40,6 +40,7 @@ from danswer.natural_language_processing.search_nlp_models import warm_up_cross_encoder from danswer.search.models import SavedSearchSettings from danswer.search.retrieval.search_runner import download_nltk_data +from danswer.seeding.load_docs import seed_initial_documents from danswer.server.manage.llm.models import LLMProviderUpsertRequest from danswer.server.settings.store import load_settings from danswer.server.settings.store import store_settings @@ -58,6 +59,12 @@ def setup_danswer(db_session: Session) -> None: + """ + Setup Danswer for a particular tenant. In the Single Tenant case, it will set it up for the default schema + on server startup. In the MT case, it will be called when the tenant is created. + + The Tenant Service calls the tenants/create endpoint which runs this. + """ check_index_swap(db_session=db_session) search_settings = get_current_search_settings(db_session) secondary_search_settings = get_secondary_search_settings(db_session) @@ -107,7 +114,8 @@ def setup_danswer(db_session: Session) -> None: if not MULTI_TENANT: mark_reindex_flag(db_session) - # ensure Vespa is setup correctly + # Ensure Vespa is setup correctly, this step is relatively near the end because Vespa + # takes a bit of time to start up logger.notice("Verifying Document Index(s) is/are available.") document_index = get_default_document_index( primary_index_name=search_settings.index_name, @@ -139,6 +147,8 @@ def setup_danswer(db_session: Session) -> None: # update multipass indexing setting based on GPU availability update_default_multipass_indexing(db_session) + seed_initial_documents(db_session) + def translate_saved_search_settings(db_session: Session) -> None: kv_store = get_kv_store() @@ -311,11 +321,13 @@ def update_default_multipass_indexing(db_session: Session) -> None: def setup_multitenant_danswer() -> None: + # For Managed Vespa, the schema is sent over via the Vespa Console manually. if not MANAGED_VESPA: setup_vespa_multitenant(SUPPORTED_EMBEDDING_MODELS) def setup_vespa_multitenant(supported_indices: list[SupportedEmbeddingModel]) -> bool: + # This is for local testing WAIT_SECONDS = 5 VESPA_ATTEMPTS = 5 for x in range(VESPA_ATTEMPTS): diff --git a/backend/danswer/utils/logger.py b/backend/danswer/utils/logger.py index 065d6282cbf..2aadbe379d6 100644 --- a/backend/danswer/utils/logger.py +++ b/backend/danswer/utils/logger.py @@ -61,10 +61,10 @@ def process( cc_pair_id = IndexAttemptSingleton.get_connector_credential_pair_id() if attempt_id is not None: - msg = f"[Attempt ID: {attempt_id}] {msg}" + msg = f"[Attempt: {attempt_id}] {msg}" if cc_pair_id is not None: - msg = f"[CC Pair ID: {cc_pair_id}] {msg}" + msg = f"[CC Pair: {cc_pair_id}] {msg}" # For Slack Bot, logs the channel relevant to the request channel_id = self.extra.get(SLACK_CHANNEL_ID) if self.extra else None @@ -185,6 +185,7 @@ def setup_logger( def print_loggers() -> None: + """Print information about all loggers. Use to debug logging issues.""" root_logger = logging.getLogger() loggers: list[logging.Logger | logging.PlaceHolder] = [root_logger] loggers.extend(logging.Logger.manager.loggerDict.values()) diff --git a/backend/danswer/connectors/cross_connector_utils/retry_wrapper.py b/backend/danswer/utils/retry_wrapper.py similarity index 79% rename from backend/danswer/connectors/cross_connector_utils/retry_wrapper.py rename to backend/danswer/utils/retry_wrapper.py index 7312d1349f7..2d6d79ca5eb 100644 --- a/backend/danswer/connectors/cross_connector_utils/retry_wrapper.py +++ b/backend/danswer/utils/retry_wrapper.py @@ -22,18 +22,18 @@ def retry_builder( jitter: tuple[float, float] | float = 1, ) -> Callable[[F], F]: """Builds a generic wrapper/decorator for calls to external APIs that - may fail due to rate limiting, flakes, or other reasons. Applies expontential + may fail due to rate limiting, flakes, or other reasons. Applies exponential backoff with jitter to retry the call.""" - @retry( - tries=tries, - delay=delay, - max_delay=max_delay, - backoff=backoff, - jitter=jitter, - logger=cast(Logger, logger), - ) def retry_with_default(func: F) -> F: + @retry( + tries=tries, + delay=delay, + max_delay=max_delay, + backoff=backoff, + jitter=jitter, + logger=cast(Logger, logger), + ) def wrapped_func(*args: list, **kwargs: dict[str, Any]) -> Any: return func(*args, **kwargs) diff --git a/backend/ee/danswer/background/celery/apps/beat.py b/backend/ee/danswer/background/celery/apps/beat.py index 20325e77df6..bee219e2471 100644 --- a/backend/ee/danswer/background/celery/apps/beat.py +++ b/backend/ee/danswer/background/celery/apps/beat.py @@ -41,7 +41,7 @@ beat_schedule[task_name] = { "task": task["task"], "schedule": task["schedule"], - "args": (tenant_id,), # Must pass tenant_id as an argument + "kwargs": {"tenant_id": tenant_id}, # Must pass tenant_id as an argument } # Include any existing beat schedules diff --git a/backend/ee/danswer/background/celery/apps/primary.py b/backend/ee/danswer/background/celery/apps/primary.py index 97c5b0221ca..be27d22868e 100644 --- a/backend/ee/danswer/background/celery/apps/primary.py +++ b/backend/ee/danswer/background/celery/apps/primary.py @@ -29,7 +29,7 @@ run_external_group_permission_sync, ) from ee.danswer.server.reporting.usage_export_generation import create_new_usage_report -from shared_configs.configs import current_tenant_id +from shared_configs.configs import CURRENT_TENANT_ID_CONTEXTVAR logger = setup_logger() @@ -39,7 +39,9 @@ @build_celery_task_wrapper(name_sync_external_doc_permissions_task) @celery_app.task(soft_time_limit=JOB_TIMEOUT) -def sync_external_doc_permissions_task(cc_pair_id: int, tenant_id: str | None) -> None: +def sync_external_doc_permissions_task( + cc_pair_id: int, *, tenant_id: str | None +) -> None: with get_session_with_tenant(tenant_id) as db_session: run_external_doc_permission_sync(db_session=db_session, cc_pair_id=cc_pair_id) @@ -47,7 +49,7 @@ def sync_external_doc_permissions_task(cc_pair_id: int, tenant_id: str | None) - @build_celery_task_wrapper(name_sync_external_group_permissions_task) @celery_app.task(soft_time_limit=JOB_TIMEOUT) def sync_external_group_permissions_task( - cc_pair_id: int, tenant_id: str | None + cc_pair_id: int, *, tenant_id: str | None ) -> None: with get_session_with_tenant(tenant_id) as db_session: run_external_group_permission_sync(db_session=db_session, cc_pair_id=cc_pair_id) @@ -56,7 +58,7 @@ def sync_external_group_permissions_task( @build_celery_task_wrapper(name_chat_ttl_task) @celery_app.task(soft_time_limit=JOB_TIMEOUT) def perform_ttl_management_task( - retention_limit_days: int, tenant_id: str | None + retention_limit_days: int, *, tenant_id: str | None ) -> None: with get_session_with_tenant(tenant_id) as db_session: delete_chat_sessions_older_than(retention_limit_days, db_session) @@ -69,7 +71,7 @@ def perform_ttl_management_task( name="check_sync_external_doc_permissions_task", soft_time_limit=JOB_TIMEOUT, ) -def check_sync_external_doc_permissions_task(tenant_id: str | None) -> None: +def check_sync_external_doc_permissions_task(*, tenant_id: str | None) -> None: """Runs periodically to sync external permissions""" with get_session_with_tenant(tenant_id) as db_session: cc_pairs = get_all_auto_sync_cc_pairs(db_session) @@ -86,7 +88,7 @@ def check_sync_external_doc_permissions_task(tenant_id: str | None) -> None: name="check_sync_external_group_permissions_task", soft_time_limit=JOB_TIMEOUT, ) -def check_sync_external_group_permissions_task(tenant_id: str | None) -> None: +def check_sync_external_group_permissions_task(*, tenant_id: str | None) -> None: """Runs periodically to sync external group permissions""" with get_session_with_tenant(tenant_id) as db_session: cc_pairs = get_all_auto_sync_cc_pairs(db_session) @@ -103,12 +105,12 @@ def check_sync_external_group_permissions_task(tenant_id: str | None) -> None: name="check_ttl_management_task", soft_time_limit=JOB_TIMEOUT, ) -def check_ttl_management_task(tenant_id: str | None) -> None: +def check_ttl_management_task(*, tenant_id: str | None) -> None: """Runs periodically to check if any ttl tasks should be run and adds them to the queue""" token = None if MULTI_TENANT and tenant_id is not None: - token = current_tenant_id.set(tenant_id) + token = CURRENT_TENANT_ID_CONTEXTVAR.set(tenant_id) settings = load_settings() retention_limit_days = settings.maximum_chat_retention_days @@ -120,14 +122,14 @@ def check_ttl_management_task(tenant_id: str | None) -> None: ), ) if token is not None: - current_tenant_id.reset(token) + CURRENT_TENANT_ID_CONTEXTVAR.reset(token) @celery_app.task( name="autogenerate_usage_report_task", soft_time_limit=JOB_TIMEOUT, ) -def autogenerate_usage_report_task(tenant_id: str | None) -> None: +def autogenerate_usage_report_task(*, tenant_id: str | None) -> None: """This generates usage report under the /admin/generate-usage/report endpoint""" with get_session_with_tenant(tenant_id) as db_session: create_new_usage_report( diff --git a/backend/ee/danswer/external_permissions/google_drive/doc_sync.py b/backend/ee/danswer/external_permissions/google_drive/doc_sync.py index 19dbb845323..f1e805d46d7 100644 --- a/backend/ee/danswer/external_permissions/google_drive/doc_sync.py +++ b/backend/ee/danswer/external_permissions/google_drive/doc_sync.py @@ -9,7 +9,6 @@ from sqlalchemy.orm import Session from danswer.access.models import ExternalAccess -from danswer.connectors.cross_connector_utils.retry_wrapper import retry_builder from danswer.connectors.factory import instantiate_connector from danswer.connectors.google_drive.connector_auth import ( get_google_drive_creds, @@ -19,6 +18,7 @@ from danswer.db.models import ConnectorCredentialPair from danswer.db.users import batch_add_non_web_user_if_not_exists__no_commit from danswer.utils.logger import setup_logger +from danswer.utils.retry_wrapper import retry_builder from ee.danswer.db.document import upsert_document_external_perms__no_commit # Google Drive APIs are quite flakey and may 500 for an diff --git a/backend/ee/danswer/external_permissions/google_drive/group_sync.py b/backend/ee/danswer/external_permissions/google_drive/group_sync.py index 7bb919d4686..ab0f62a886b 100644 --- a/backend/ee/danswer/external_permissions/google_drive/group_sync.py +++ b/backend/ee/danswer/external_permissions/google_drive/group_sync.py @@ -7,7 +7,6 @@ from googleapiclient.errors import HttpError # type: ignore from sqlalchemy.orm import Session -from danswer.connectors.cross_connector_utils.retry_wrapper import retry_builder from danswer.connectors.google_drive.connector_auth import ( get_google_drive_creds, ) @@ -15,6 +14,7 @@ from danswer.db.models import ConnectorCredentialPair from danswer.db.users import batch_add_non_web_user_if_not_exists__no_commit from danswer.utils.logger import setup_logger +from danswer.utils.retry_wrapper import retry_builder from ee.danswer.db.external_perm import ExternalUserGroup from ee.danswer.db.external_perm import replace_user__ext_group_for_cc_pair__no_commit diff --git a/backend/ee/danswer/server/middleware/tenant_tracking.py b/backend/ee/danswer/server/middleware/tenant_tracking.py index f564a4fc683..eba02d0428b 100644 --- a/backend/ee/danswer/server/middleware/tenant_tracking.py +++ b/backend/ee/danswer/server/middleware/tenant_tracking.py @@ -10,9 +10,9 @@ from danswer.configs.app_configs import MULTI_TENANT from danswer.configs.app_configs import SECRET_JWT_KEY -from danswer.configs.constants import POSTGRES_DEFAULT_SCHEMA from danswer.db.engine import is_valid_schema_name -from shared_configs.configs import current_tenant_id +from shared_configs.configs import CURRENT_TENANT_ID_CONTEXTVAR +from shared_configs.configs import POSTGRES_DEFAULT_SCHEMA def add_tenant_id_middleware(app: FastAPI, logger: logging.LoggerAdapter) -> None: @@ -49,7 +49,7 @@ async def set_tenant_id( else: tenant_id = POSTGRES_DEFAULT_SCHEMA - current_tenant_id.set(tenant_id) + CURRENT_TENANT_ID_CONTEXTVAR.set(tenant_id) logger.info(f"Middleware set current_tenant_id to: {tenant_id}") response = await call_next(request) diff --git a/backend/ee/danswer/server/query_and_chat/chat_backend.py b/backend/ee/danswer/server/query_and_chat/chat_backend.py index dd637dcf081..b25ed8357d9 100644 --- a/backend/ee/danswer/server/query_and_chat/chat_backend.py +++ b/backend/ee/danswer/server/query_and_chat/chat_backend.py @@ -176,6 +176,7 @@ def handle_simplified_chat_message( chunks_above=0, chunks_below=0, full_doc=chat_message_req.full_doc, + structured_response_format=chat_message_req.structured_response_format, ) packets = stream_chat_message_objects( @@ -202,7 +203,7 @@ def handle_send_message_simple_with_history( raise HTTPException(status_code=400, detail="Messages cannot be zero length") # This is a sanity check to make sure the chat history is valid - # It must start with a user message and alternate between user and assistant + # It must start with a user message and alternate beteen user and assistant expected_role = MessageType.USER for msg in req.messages: if not msg.message: @@ -296,6 +297,7 @@ def handle_send_message_simple_with_history( chunks_above=0, chunks_below=0, full_doc=req.full_doc, + structured_response_format=req.structured_response_format, ) packets = stream_chat_message_objects( diff --git a/backend/ee/danswer/server/query_and_chat/models.py b/backend/ee/danswer/server/query_and_chat/models.py index 052be683e9e..4baf17ac8ce 100644 --- a/backend/ee/danswer/server/query_and_chat/models.py +++ b/backend/ee/danswer/server/query_and_chat/models.py @@ -48,6 +48,9 @@ class BasicCreateChatMessageRequest(ChunkContext): query_override: str | None = None # If search_doc_ids provided, then retrieval options are unused search_doc_ids: list[int] | None = None + # only works if using an OpenAI model. See the following for more details: + # https://platform.openai.com/docs/guides/structured-outputs/introduction + structured_response_format: dict | None = None class BasicCreateChatMessageWithHistoryRequest(ChunkContext): @@ -60,6 +63,9 @@ class BasicCreateChatMessageWithHistoryRequest(ChunkContext): skip_rerank: bool | None = None # If search_doc_ids provided, then retrieval options are unused search_doc_ids: list[int] | None = None + # only works if using an OpenAI model. See the following for more details: + # https://platform.openai.com/docs/guides/structured-outputs/introduction + structured_response_format: dict | None = None class SimpleDoc(BaseModel): diff --git a/backend/ee/danswer/server/query_history/api.py b/backend/ee/danswer/server/query_history/api.py index 1411f973e36..f50b9cc5230 100644 --- a/backend/ee/danswer/server/query_history/api.py +++ b/backend/ee/danswer/server/query_history/api.py @@ -20,10 +20,13 @@ from danswer.configs.constants import QAFeedbackType from danswer.configs.constants import SessionType from danswer.db.chat import get_chat_session_by_id +from danswer.db.chat import get_chat_sessions_by_user from danswer.db.engine import get_session from danswer.db.models import ChatMessage from danswer.db.models import ChatSession from danswer.db.models import User +from danswer.server.query_and_chat.models import ChatSessionDetails +from danswer.server.query_and_chat.models import ChatSessionsResponse from ee.danswer.db.query_history import fetch_chat_sessions_eagerly_by_time router = APIRouter() @@ -330,6 +333,36 @@ def snapshot_from_chat_session( ) +@router.get("/admin/chat-sessions") +def get_user_chat_sessions( + user_id: UUID, + _: User | None = Depends(current_admin_user), + db_session: Session = Depends(get_session), +) -> ChatSessionsResponse: + try: + chat_sessions = get_chat_sessions_by_user( + user_id=user_id, deleted=False, db_session=db_session, limit=0 + ) + + except ValueError: + raise ValueError("Chat session does not exist or has been deleted") + + return ChatSessionsResponse( + sessions=[ + ChatSessionDetails( + id=chat.id, + name=chat.description, + persona_id=chat.persona_id, + time_created=chat.time_created.isoformat(), + shared_status=chat.shared_status, + folder_id=chat.folder_id, + current_alternate_model=chat.current_alternate_model, + ) + for chat in chat_sessions + ] + ) + + @router.get("/admin/chat-session-history") def get_chat_session_history( feedback_type: QAFeedbackType | None = None, diff --git a/backend/ee/danswer/server/tenants/api.py b/backend/ee/danswer/server/tenants/api.py index 0438772486a..342554c1c43 100644 --- a/backend/ee/danswer/server/tenants/api.py +++ b/backend/ee/danswer/server/tenants/api.py @@ -8,6 +8,7 @@ from danswer.configs.app_configs import MULTI_TENANT from danswer.configs.app_configs import WEB_DOMAIN from danswer.db.engine import get_session_with_tenant +from danswer.db.notification import create_notification from danswer.server.settings.store import load_settings from danswer.server.settings.store import store_settings from danswer.setup import setup_danswer @@ -23,7 +24,7 @@ from ee.danswer.server.tenants.provisioning import ensure_schema_exists from ee.danswer.server.tenants.provisioning import run_alembic_migrations from ee.danswer.server.tenants.provisioning import user_owns_a_tenant -from shared_configs.configs import current_tenant_id +from shared_configs.configs import CURRENT_TENANT_ID_CONTEXTVAR stripe.api_key = STRIPE_SECRET_KEY @@ -54,7 +55,7 @@ def create_tenant( else: logger.info(f"Schema already exists for tenant {tenant_id}") - token = current_tenant_id.set(tenant_id) + token = CURRENT_TENANT_ID_CONTEXTVAR.set(tenant_id) run_alembic_migrations(tenant_id) with get_session_with_tenant(tenant_id) as db_session: @@ -73,7 +74,7 @@ def create_tenant( ) finally: if token is not None: - current_tenant_id.reset(token) + CURRENT_TENANT_ID_CONTEXTVAR.reset(token) @router.post("/product-gating") @@ -87,14 +88,19 @@ def gate_product( 1) User has ended free trial without adding payment method 2) User's card has declined """ - token = current_tenant_id.set(current_tenant_id.get()) + tenant_id = product_gating_request.tenant_id + token = CURRENT_TENANT_ID_CONTEXTVAR.set(tenant_id) settings = load_settings() settings.product_gating = product_gating_request.product_gating store_settings(settings) + if product_gating_request.notification: + with get_session_with_tenant(tenant_id) as db_session: + create_notification(None, product_gating_request.notification, db_session) + if token is not None: - current_tenant_id.reset(token) + CURRENT_TENANT_ID_CONTEXTVAR.reset(token) @router.get("/billing-information", response_model=BillingInformation) @@ -102,14 +108,16 @@ async def billing_information( _: User = Depends(current_admin_user), ) -> BillingInformation: logger.info("Fetching billing information") - return BillingInformation(**fetch_billing_information(current_tenant_id.get())) + return BillingInformation( + **fetch_billing_information(CURRENT_TENANT_ID_CONTEXTVAR.get()) + ) @router.post("/create-customer-portal-session") async def create_customer_portal_session(_: User = Depends(current_admin_user)) -> dict: try: # Fetch tenant_id and current tenant's information - tenant_id = current_tenant_id.get() + tenant_id = CURRENT_TENANT_ID_CONTEXTVAR.get() stripe_info = fetch_tenant_stripe_information(tenant_id) stripe_customer_id = stripe_info.get("stripe_customer_id") if not stripe_customer_id: diff --git a/backend/ee/danswer/server/tenants/billing.py b/backend/ee/danswer/server/tenants/billing.py index 5dcd96713de..681ac835e5f 100644 --- a/backend/ee/danswer/server/tenants/billing.py +++ b/backend/ee/danswer/server/tenants/billing.py @@ -8,7 +8,6 @@ from ee.danswer.configs.app_configs import STRIPE_PRICE_ID from ee.danswer.configs.app_configs import STRIPE_SECRET_KEY from ee.danswer.server.tenants.access import generate_data_plane_token -from shared_configs.configs import current_tenant_id stripe.api_key = STRIPE_SECRET_KEY @@ -50,7 +49,6 @@ def register_tenant_users(tenant_id: str, number_of_users: int) -> stripe.Subscr if not STRIPE_PRICE_ID: raise Exception("STRIPE_PRICE_ID is not set") - tenant_id = current_tenant_id.get() response = fetch_tenant_stripe_information(tenant_id) stripe_subscription_id = cast(str, response.get("stripe_subscription_id")) diff --git a/backend/ee/danswer/server/tenants/models.py b/backend/ee/danswer/server/tenants/models.py index 32642ecfcda..30f656c0824 100644 --- a/backend/ee/danswer/server/tenants/models.py +++ b/backend/ee/danswer/server/tenants/models.py @@ -1,5 +1,6 @@ from pydantic import BaseModel +from danswer.configs.constants import NotificationType from danswer.server.settings.models import GatingType @@ -15,6 +16,7 @@ class CreateTenantRequest(BaseModel): class ProductGatingRequest(BaseModel): tenant_id: str product_gating: GatingType + notification: NotificationType | None = None class BillingInformation(BaseModel): diff --git a/backend/ee/danswer/server/tenants/provisioning.py b/backend/ee/danswer/server/tenants/provisioning.py index 9ec7b8061aa..311698e6a3d 100644 --- a/backend/ee/danswer/server/tenants/provisioning.py +++ b/backend/ee/danswer/server/tenants/provisioning.py @@ -12,6 +12,7 @@ from danswer.db.engine import get_sqlalchemy_engine from danswer.db.models import UserTenantMapping from danswer.utils.logger import setup_logger +from shared_configs.configs import POSTGRES_DEFAULT_SCHEMA logger = setup_logger() @@ -71,7 +72,7 @@ def ensure_schema_exists(tenant_id: str) -> bool: # For now, we're implementing a primitive mapping between users and tenants. # This function is only used to determine a user's relationship to a tenant upon creation (implying ownership). def user_owns_a_tenant(email: str) -> bool: - with get_session_with_tenant("public") as db_session: + with get_session_with_tenant(POSTGRES_DEFAULT_SCHEMA) as db_session: result = ( db_session.query(UserTenantMapping) .filter(UserTenantMapping.email == email) @@ -81,7 +82,7 @@ def user_owns_a_tenant(email: str) -> bool: def add_users_to_tenant(emails: list[str], tenant_id: str) -> None: - with get_session_with_tenant("public") as db_session: + with get_session_with_tenant(POSTGRES_DEFAULT_SCHEMA) as db_session: try: for email in emails: db_session.add(UserTenantMapping(email=email, tenant_id=tenant_id)) @@ -91,7 +92,7 @@ def add_users_to_tenant(emails: list[str], tenant_id: str) -> None: def remove_users_from_tenant(emails: list[str], tenant_id: str) -> None: - with get_session_with_tenant("public") as db_session: + with get_session_with_tenant(POSTGRES_DEFAULT_SCHEMA) as db_session: try: mappings_to_delete = ( db_session.query(UserTenantMapping) diff --git a/backend/requirements/model_server.txt b/backend/requirements/model_server.txt index 2ea6df66d8b..6160555f7b1 100644 --- a/backend/requirements/model_server.txt +++ b/backend/requirements/model_server.txt @@ -1,5 +1,5 @@ -cohere==5.6.1 einops==0.8.0 +cohere==5.6.1 fastapi==0.109.2 google-cloud-aiplatform==1.58.0 numpy==1.26.4 @@ -13,4 +13,4 @@ transformers==4.39.2 uvicorn==0.21.1 voyageai==0.2.3 litellm==1.49.5 -sentry-sdk[fastapi,celery,starlette]==2.14.0 +sentry-sdk[fastapi,celery,starlette]==2.14.0 \ No newline at end of file diff --git a/backend/scripts/add_connector_creation_script.py b/backend/scripts/add_connector_creation_script.py new file mode 100644 index 00000000000..9a1944080c0 --- /dev/null +++ b/backend/scripts/add_connector_creation_script.py @@ -0,0 +1,148 @@ +from typing import Any +from typing import Dict + +import requests + +API_SERVER_URL = "http://localhost:3000" # Adjust this to your Danswer server URL +HEADERS = {"Content-Type": "application/json"} +API_KEY = "danswer-api-key" # API key here, if auth is enabled + + +def create_connector( + name: str, + source: str, + input_type: str, + connector_specific_config: Dict[str, Any], + is_public: bool = True, + groups: list[int] | None = None, +) -> Dict[str, Any]: + connector_update_request = { + "name": name, + "source": source, + "input_type": input_type, + "connector_specific_config": connector_specific_config, + "is_public": is_public, + "groups": groups or [], + } + + response = requests.post( + url=f"{API_SERVER_URL}/api/manage/admin/connector", + json=connector_update_request, + headers=HEADERS, + ) + response.raise_for_status() + return response.json() + + +def create_credential( + name: str, + source: str, + credential_json: Dict[str, Any], + is_public: bool = True, + groups: list[int] | None = None, +) -> Dict[str, Any]: + credential_request = { + "name": name, + "source": source, + "credential_json": credential_json, + "admin_public": is_public, + "groups": groups or [], + } + + response = requests.post( + url=f"{API_SERVER_URL}/api/manage/credential", + json=credential_request, + headers=HEADERS, + ) + response.raise_for_status() + return response.json() + + +def create_cc_pair( + connector_id: int, + credential_id: int, + name: str, + access_type: str = "public", + groups: list[int] | None = None, +) -> Dict[str, Any]: + cc_pair_request = { + "name": name, + "access_type": access_type, + "groups": groups or [], + } + + response = requests.put( + url=f"{API_SERVER_URL}/api/manage/connector/{connector_id}/credential/{credential_id}", + json=cc_pair_request, + headers=HEADERS, + ) + response.raise_for_status() + return response.json() + + +def main() -> None: + # Create a Web connector + web_connector = create_connector( + name="Example Web Connector", + source="web", + input_type="load_state", + connector_specific_config={ + "base_url": "https://example.com", + "web_connector_type": "recursive", + }, + ) + print(f"Created Web Connector: {web_connector}") + + # Create a credential for the Web connector + web_credential = create_credential( + name="Example Web Credential", + source="web", + credential_json={}, # Web connectors typically don't need credentials + is_public=True, + ) + print(f"Created Web Credential: {web_credential}") + + # Create CC pair for Web connector + web_cc_pair = create_cc_pair( + connector_id=web_connector["id"], + credential_id=web_credential["id"], + name="Example Web CC Pair", + access_type="public", + ) + print(f"Created Web CC Pair: {web_cc_pair}") + + # Create a GitHub connector + github_connector = create_connector( + name="Example GitHub Connector", + source="github", + input_type="poll", + connector_specific_config={ + "repo_owner": "example-owner", + "repo_name": "example-repo", + "include_prs": True, + "include_issues": True, + }, + ) + print(f"Created GitHub Connector: {github_connector}") + + # Create a credential for the GitHub connector + github_credential = create_credential( + name="Example GitHub Credential", + source="github", + credential_json={"github_access_token": "your_github_access_token_here"}, + is_public=True, + ) + print(f"Created GitHub Credential: {github_credential}") + + # Create CC pair for GitHub connector + github_cc_pair = create_cc_pair( + connector_id=github_connector["id"], + credential_id=github_credential["id"], + name="Example GitHub CC Pair", + access_type="public", + ) + print(f"Created GitHub CC Pair: {github_cc_pair}") + + +if __name__ == "__main__": + main() diff --git a/backend/scripts/chat_feedback_dump.py b/backend/scripts/chat_feedback_dump.py new file mode 100644 index 00000000000..f0d6d3cbb37 --- /dev/null +++ b/backend/scripts/chat_feedback_dump.py @@ -0,0 +1,239 @@ +# This file is used to demonstrate how to use the backend APIs directly +# to query out feedback for all messages +import argparse +import logging +from logging import getLogger +from typing import Any +from uuid import UUID + +import requests + +from danswer.server.manage.models import AllUsersResponse +from danswer.server.query_and_chat.models import ChatSessionsResponse +from ee.danswer.server.query_history.api import ChatSessionSnapshot + +# Configure the logger +logging.basicConfig( + level=logging.INFO, # Set the log level (DEBUG, INFO, WARNING, ERROR, CRITICAL) + format="%(asctime)s - %(name)s - %(levelname)s - %(message)s", # Log format + handlers=[logging.StreamHandler()], # Output logs to console +) + +logger = getLogger(__name__) + +# uncomment the following pydantic models if you need the script to be independent +# from pydantic import BaseModel +# from datetime import datetime +# from enum import Enum + +# class UserRole(str, Enum): +# """ +# User roles +# - Basic can't perform any admin actions +# - Admin can perform all admin actions +# - Curator can perform admin actions for +# groups they are curators of +# - Global Curator can perform admin actions +# for all groups they are a member of +# """ + +# BASIC = "basic" +# ADMIN = "admin" +# CURATOR = "curator" +# GLOBAL_CURATOR = "global_curator" + + +# class UserStatus(str, Enum): +# LIVE = "live" +# INVITED = "invited" +# DEACTIVATED = "deactivated" + + +# class FullUserSnapshot(BaseModel): +# id: UUID +# email: str +# role: UserRole +# status: UserStatus + + +# class InvitedUserSnapshot(BaseModel): +# email: str + + +# class AllUsersResponse(BaseModel): +# accepted: list[FullUserSnapshot] +# invited: list[InvitedUserSnapshot] +# accepted_pages: int +# invited_pages: int + + +# class ChatSessionSharedStatus(str, Enum): +# PUBLIC = "public" +# PRIVATE = "private" + + +# class ChatSessionDetails(BaseModel): +# id: UUID +# name: str +# persona_id: int | None = None +# time_created: str +# shared_status: ChatSessionSharedStatus +# folder_id: int | None = None +# current_alternate_model: str | None = None + + +# class ChatSessionsResponse(BaseModel): +# sessions: list[ChatSessionDetails] + + +# class SessionType(str, Enum): +# CHAT = "Chat" +# SEARCH = "Search" +# SLACK = "Slack" + + +# class AbridgedSearchDoc(BaseModel): +# """A subset of the info present in `SearchDoc`""" + +# document_id: str +# semantic_identifier: str +# link: str | None + + +# class QAFeedbackType(str, Enum): +# LIKE = "like" # User likes the answer, used for metrics +# DISLIKE = "dislike" # User dislikes the answer, used for metrics + + +# class MessageType(str, Enum): +# # Using OpenAI standards, Langchain equivalent shown in comment +# # System message is always constructed on the fly, not saved +# SYSTEM = "system" # SystemMessage +# USER = "user" # HumanMessage +# ASSISTANT = "assistant" # AIMessage + + +# class MessageSnapshot(BaseModel): +# message: str +# message_type: MessageType +# documents: list[AbridgedSearchDoc] +# feedback_type: QAFeedbackType | None +# feedback_text: str | None +# time_created: datetime + + +# class ChatSessionSnapshot(BaseModel): +# id: UUID +# user_email: str +# name: str | None +# messages: list[MessageSnapshot] +# persona_name: str | None +# time_created: datetime +# flow_type: SessionType + + +def create_new_chat_session(danswer_url: str, api_key: str | None) -> int: + headers = {"Authorization": f"Bearer {api_key}"} if api_key else None + session_endpoint = danswer_url + "/api/chat/create-chat-session" + + response = requests.get(session_endpoint, headers=headers) + response.raise_for_status() + + new_session_id = response.json()["chat_session_id"] + return new_session_id + + +def manage_users(danswer_url: str, headers: dict[str, str] | None) -> AllUsersResponse: + endpoint = danswer_url + "/manage/users" + + response = requests.get( + endpoint, + headers=headers, + ) + response.raise_for_status() + + all_users = AllUsersResponse(**response.json()) + return all_users + + +def get_chat_sessions( + danswer_url: str, headers: dict[str, str] | None, user_id: UUID +) -> ChatSessionsResponse: + endpoint = danswer_url + "/admin/chat-sessions" + + params: dict[str, Any] = {"user_id": user_id} + response = requests.get( + endpoint, + params=params, + headers=headers, + ) + response.raise_for_status() + + sessions = ChatSessionsResponse(**response.json()) + return sessions + + +def get_session_history( + danswer_url: str, headers: dict[str, str] | None, session_id: UUID +) -> ChatSessionSnapshot: + endpoint = danswer_url + f"/admin/chat-session-history/{session_id}" + + response = requests.get( + endpoint, + headers=headers, + ) + response.raise_for_status() + + sessions = ChatSessionSnapshot(**response.json()) + return sessions + + +def process_all_chat_feedback(danswer_url: str, api_key: str | None) -> None: + headers = {"Authorization": f"Bearer {api_key}"} if api_key else None + + all_users = manage_users(danswer_url, headers) + if not all_users: + raise RuntimeError("manage_users returned None") + + logger.info(f"Accepted users: {len(all_users.accepted)}") + + user_ids: list[UUID] = [user.id for user in all_users.accepted] + + for user_id in user_ids: + r_sessions = get_chat_sessions(danswer_url, headers, user_id) + logger.info(f"user={user_id} num_sessions={len(r_sessions.sessions)}") + for session in r_sessions.sessions: + try: + s = get_session_history(danswer_url, headers, session.id) + except requests.exceptions.HTTPError: + logger.exception("get_session_history failed.") + + for m in s.messages: + logger.info( + f"user={user_id} " + f"session={session.id} " + f"message={m.message} " + f"feedback_type={m.feedback_type} " + f"feedback_text={m.feedback_text}" + ) + + +if __name__ == "__main__": + parser = argparse.ArgumentParser(description="Sample API Usage - Chat Feedback") + parser.add_argument( + "--url", + type=str, + default="http://localhost:8080", + help="Danswer URL, should point to Danswer nginx.", + ) + + # Not needed if Auth is disabled? + # Or for Danswer MIT Edition API key must be replaced with session cookie + parser.add_argument( + "--api-key", + type=str, + help="Danswer Admin Level API key", + ) + + args = parser.parse_args() + process_all_chat_feedback(danswer_url=args.url, api_key=args.api_key) diff --git a/backend/scripts/document_seeding_prep.py b/backend/scripts/document_seeding_prep.py new file mode 100644 index 00000000000..d853b68ccb4 --- /dev/null +++ b/backend/scripts/document_seeding_prep.py @@ -0,0 +1,240 @@ +# This script preps the documents used for initially seeding the index. It handles the embedding so that the +# documents can be added to the index with minimal processing. +import json + +from pydantic import BaseModel +from sentence_transformers import SentenceTransformer # type: ignore + + +class SeedPresaveDocument(BaseModel): + url: str + title: str + content: str + title_embedding: list[float] + content_embedding: list[float] + chunk_ind: int = 0 + + +# Be sure to use the default embedding model +model = SentenceTransformer("nomic-ai/nomic-embed-text-v1", trust_remote_code=True) +tokenizer = model.tokenizer + +# This is easier than cleaning up the crawl, needs to be updated if the sites are changed +overview_title = "Use Cases Overview" +overview = ( + "How to leverage Danswer in your organization\n\n" + "Danswer Overview\n" + "Danswer is the AI Assistant connected to your organization's docs, apps, and people. " + "Danswer makes Generative AI more versatile for work by enabling new types of questions like " + '"What is the most common feature request we\'ve heard from customers this month". ' + "Whereas other AI systems have no context of your team and are generally unhelpful with work related questions, " + "Danswer makes it possible to ask these questions in natural language and get back answers in seconds.\n\n" + "Danswer can connect to +30 different tools and the use cases are not limited to the ones in the following pages. " + "The highlighted use cases are for inspiration and come from feedback gathered from our users and customers.\n\n\n" + "Common Getting Started Questions:\n\n" + "Why are these docs connected in my Danswer deployment?\n" + "Answer: This is just an example of how connectors work in Danswer. You can connect up your own team's knowledge " + "and you will be able to ask questions unique to your organization. Danswer will keep all of the knowledge up to date " + "and in sync with your connected applications.\n\n" + "Is my data being sent anywhere when I connect it up to Danswer?\n" + "Answer: No! Danswer is built with data security as our highest priority. We open sourced it so our users can know " + "exactly what is going on with their data. By default all of the document processing happens within Danswer. " + "The only time it is sent outward is for the GenAI call to generate answers.\n\n" + "Where is the feature for auto sync-ing document level access permissions from all connected sources?\n" + "Answer: This falls under the Enterprise Edition set of Danswer features built on top of the MIT/community edition. " + "If you are on Danswer Cloud, you have access to them by default. If you're running it yourself, reach out to the " + "Danswer team to receive access." +) + +enterprise_search_title = "Enterprise Search" +enterprise_search_1 = ( + "Value of Enterprise Search with Danswer\n\n" + "What is Enterprise Search and why is it Important?\n" + "An Enterprise Search system gives team members a single place to access all of the disparate knowledge " + "of an organization. Critical information is saved across a host of channels like call transcripts with " + "prospects, engineering design docs, IT runbooks, customer support email exchanges, project management " + "tickets, and more. As fast moving teams scale up, information gets spread out and more disorganized.\n\n" + "Since it quickly becomes infeasible to check across every source, decisions get made on incomplete " + "information, employee satisfaction decreases, and the most valuable members of your team are tied up " + "with constant distractions as junior teammates are unable to unblock themselves. Danswer solves this " + "problem by letting anyone on the team access all of the knowledge across your organization in a " + "permissioned and secure way. Users can ask questions in natural language and get back answers and " + "documents across all of the connected sources instantly.\n\n" + "What's the real cost?\n" + "A typical knowledge worker spends over 2 hours a week on search, but more than that, the cost of " + "incomplete or incorrect information can be extremely high. Customer support/success that isn't able " + "to find the reference to similar cases could cause hours or even days of delay leading to lower " + "customer satisfaction or in the worst case - churn. An account exec not realizing that a prospect had " + "previously mentioned a specific need could lead to lost deals. An engineer not realizing a similar " + "feature had previously been built could result in weeks of wasted development time and tech debt with " + "duplicate implementation. With a lack of knowledge, your whole organization is navigating in the dark " + "- inefficient and mistake prone." +) + +enterprise_search_2 = ( + "More than Search\n" + "When analyzing the entire corpus of knowledge within your company is as easy as asking a question " + "in a search bar, your entire team can stay informed and up to date. Danswer also makes it trivial " + "to identify where knowledge is well documented and where it is lacking. Team members who are centers " + "of knowledge can begin to effectively document their expertise since it is no longer being thrown into " + "a black hole. All of this allows the organization to achieve higher efficiency and drive business outcomes.\n\n" + "With Generative AI, the entire user experience has evolved as well. For example, instead of just finding similar " + "cases for your customer support team to reference, Danswer breaks down the issue and explains it so that even " + "the most junior members can understand it. This in turn lets them give the most holistic and technically accurate " + "response possible to your customers. On the other end, even the super stars of your sales team will not be able " + "to review 10 hours of transcripts before hopping on that critical call, but Danswer can easily parse through it " + "in mere seconds and give crucial context to help your team close." +) + +ai_platform_title = "AI Platform" +ai_platform = ( + "Build AI Agents powered by the knowledge and workflows specific to your organization.\n\n" + "Beyond Answers\n" + "Agents enabled by generative AI and reasoning capable models are helping teams to automate their work. " + "Danswer is helping teams make it happen. Danswer provides out of the box user chat sessions, attaching custom tools, " + "handling LLM reasoning, code execution, data analysis, referencing internal knowledge, and much more.\n\n" + "Danswer as a platform is not a no-code agent builder. We are made by developers for developers and this gives your " + "team the full flexibility and power to create agents not constrained by blocks and simple logic paths.\n\n" + "Flexibility and Extensibility\n" + "Danswer is open source and completely whitebox. This not only gives transparency to what happens within the system " + "but also means that your team can directly modify the source code to suit your unique needs." +) + +customer_support_title = "Customer Support" +customer_support = ( + "Help your customer support team instantly answer any question across your entire product.\n\n" + "AI Enabled Support\n" + "Customer support agents have one of the highest breadth jobs. They field requests that cover the entire surface " + "area of the product and need to help your users find success on extremely short timelines. " + "Because they're not the same people who designed or built the system, they often lack the depth of understanding " + "needed - resulting in delays and escalations to other teams. Modern teams are leveraging AI to help their CS team " + "optimize the speed and quality of these critical customer-facing interactions.\n\n" + "The Importance of Context\n" + "There are two critical components of AI copilots for customer support. The first is that the AI system needs to be " + "connected with as much information as possible (not just support tools like Zendesk or Intercom) and that the " + "knowledge needs to be as fresh as possible. Sometimes a fix might even be in places rarely checked by CS such as " + "pull requests in a code repository. The second critical component is the ability of the AI system to break down " + "difficult concepts and convoluted processes into more digestible descriptions and for your team members to be able " + "to chat back and forth with the system to build a better understanding.\n\n" + "Danswer takes care of both of these. The system connects up to over 30+ different applications and the knowledge is " + "pulled in constantly so that the information access is always up to date." +) + +sales_title = "Sales" +sales = ( + "Keep your team up to date on every conversation and update so they can close.\n\n" + "Recall Every Detail\n" + "Being able to instantly revisit every detail of any call without reading transcripts is helping Sales teams provide " + "more tailored pitches, build stronger relationships, and close more deals. Instead of searching and reading through " + 'hours of transcripts in preparation for a call, your team can now ask Danswer "What specific features was ACME ' + "interested in seeing for the demo\". Since your team doesn't have time to read every transcript prior to a call, " + "Danswer provides a more thorough summary because it can instantly parse hundreds of pages and distill out the relevant " + "information. Even for fast lookups it becomes much more convenient - for example to brush up on connection building " + 'topics by asking "What rapport building topic did we chat about in the last call with ACME".\n\n' + "Know Every Product Update\n" + "It is impossible for Sales teams to keep up with every product update. Because of this, when a prospect has a question " + "that the Sales team does not know, they have no choice but to rely on the Product and Engineering orgs to get an " + "authoritative answer. Not only is this distracting to the other teams, it also slows down the time to respond to the " + "prospect (and as we know, time is the biggest killer of deals). With Danswer, it is even possible to get answers live " + 'on call because of how fast accessing information becomes. A question like "Have we shipped the Microsoft AD ' + 'integration yet?" can now be answered in seconds meaning that prospects can get answers while on the call instead of ' + "asynchronously and sales cycles are reduced as a result." +) + +operations_title = "Operations" +operations = ( + "Double the productivity of your Ops teams like IT, HR, etc.\n\n" + "Automatically Resolve Tickets\n" + "Modern teams are leveraging AI to auto-resolve up to 50% of tickets. Whether it is an employee asking about benefits " + "details or how to set up the VPN for remote work, Danswer can help your team help themselves. This frees up your team to " + "do the real impactful work of landing star candidates or improving your internal processes.\n\n" + "AI Aided Onboarding\n" + "One of the periods where your team needs the most help is when they're just ramping up. Instead of feeling lost in dozens " + "of new tools, Danswer gives them a single place where they can ask about anything in natural language. Whether it's how to " + "set up their work environment or what their onboarding goals are, Danswer can walk them through every step with the help " + "of Generative AI. This lets your team feel more empowered and gives time back to the more seasoned members of your team to " + "focus on moving the needle." +) + +# For simplicity, we're not adding any metadata suffix here. Generally there is none for the Web connector anyway +overview_doc = SeedPresaveDocument( + url="https://docs.danswer.dev/more/use_cases/overview", + title=overview_title, + content=overview, + title_embedding=model.encode(f"search_document: {overview_title}"), + content_embedding=model.encode(f"search_document: {overview_title}\n{overview}"), +) + +enterprise_search_doc = SeedPresaveDocument( + url="https://docs.danswer.dev/more/use_cases/enterprise_search", + title=enterprise_search_title, + content=enterprise_search_1, + title_embedding=model.encode(f"search_document: {enterprise_search_title}"), + content_embedding=model.encode( + f"search_document: {enterprise_search_title}\n{enterprise_search_1}" + ), +) + +enterprise_search_doc_2 = SeedPresaveDocument( + url="https://docs.danswer.dev/more/use_cases/enterprise_search", + title=enterprise_search_title, + content=enterprise_search_2, + title_embedding=model.encode(f"search_document: {enterprise_search_title}"), + content_embedding=model.encode( + f"search_document: {enterprise_search_title}\n{enterprise_search_2}" + ), + chunk_ind=1, +) + +ai_platform_doc = SeedPresaveDocument( + url="https://docs.danswer.dev/more/use_cases/ai_platform", + title=ai_platform_title, + content=ai_platform, + title_embedding=model.encode(f"search_document: {ai_platform_title}"), + content_embedding=model.encode( + f"search_document: {ai_platform_title}\n{ai_platform}" + ), +) + +customer_support_doc = SeedPresaveDocument( + url="https://docs.danswer.dev/more/use_cases/customer_support", + title=customer_support_title, + content=customer_support, + title_embedding=model.encode(f"search_document: {customer_support_title}"), + content_embedding=model.encode( + f"search_document: {customer_support_title}\n{customer_support}" + ), +) + +sales_doc = SeedPresaveDocument( + url="https://docs.danswer.dev/more/use_cases/sales", + title=sales_title, + content=sales, + title_embedding=model.encode(f"search_document: {sales_title}"), + content_embedding=model.encode(f"search_document: {sales_title}\n{sales}"), +) + +operations_doc = SeedPresaveDocument( + url="https://docs.danswer.dev/more/use_cases/operations", + title=operations_title, + content=operations, + title_embedding=model.encode(f"search_document: {operations_title}"), + content_embedding=model.encode( + f"search_document: {operations_title}\n{operations}" + ), +) + +documents = [ + overview_doc, + enterprise_search_doc, + enterprise_search_doc_2, + ai_platform_doc, + customer_support_doc, + sales_doc, + operations_doc, +] + +documents_dict = [doc.model_dump() for doc in documents] + +with open("./backend/danswer/seeding/initial_docs.json", "w") as json_file: + json.dump(documents_dict, json_file, indent=4) diff --git a/backend/scripts/query_time_check/seed_dummy_docs.py b/backend/scripts/query_time_check/seed_dummy_docs.py index 70cb2a4a6a8..e7aa65fba76 100644 --- a/backend/scripts/query_time_check/seed_dummy_docs.py +++ b/backend/scripts/query_time_check/seed_dummy_docs.py @@ -21,6 +21,7 @@ from danswer.indexing.models import DocMetadataAwareIndexChunk from danswer.indexing.models import IndexChunk from danswer.utils.timing import log_function_time +from shared_configs.configs import POSTGRES_DEFAULT_SCHEMA from shared_configs.model_server_models import Embedding @@ -94,7 +95,7 @@ def generate_dummy_chunk( ), document_sets={document_set for document_set in document_set_names}, boost=random.randint(-1, 1), - tenant_id="public", + tenant_id=POSTGRES_DEFAULT_SCHEMA, ) diff --git a/backend/shared_configs/configs.py b/backend/shared_configs/configs.py index f10855f103f..5c24aebe749 100644 --- a/backend/shared_configs/configs.py +++ b/backend/shared_configs/configs.py @@ -128,7 +128,12 @@ def validate_cors_origin(origin: str) -> None: # If the environment variable is empty, allow all origins CORS_ALLOWED_ORIGIN = ["*"] -current_tenant_id = contextvars.ContextVar("current_tenant_id", default="public") + +POSTGRES_DEFAULT_SCHEMA = os.environ.get("POSTGRES_DEFAULT_SCHEMA") or "public" + +CURRENT_TENANT_ID_CONTEXTVAR = contextvars.ContextVar( + "current_tenant_id", default=POSTGRES_DEFAULT_SCHEMA +) SUPPORTED_EMBEDDING_MODELS = [ diff --git a/backend/tests/integration/conftest.py b/backend/tests/integration/conftest.py index 77d9e0e7022..f3d194e22b1 100644 --- a/backend/tests/integration/conftest.py +++ b/backend/tests/integration/conftest.py @@ -6,7 +6,9 @@ from danswer.db.engine import get_session_context_manager from danswer.db.search_settings import get_current_search_settings +from tests.integration.common_utils.managers.user import UserManager from tests.integration.common_utils.reset import reset_all +from tests.integration.common_utils.test_models import DATestUser from tests.integration.common_utils.vespa import vespa_fixture @@ -44,3 +46,11 @@ def vespa_client(db_session: Session) -> vespa_fixture: @pytest.fixture def reset() -> None: reset_all() + + +@pytest.fixture +def new_admin_user(reset: None) -> DATestUser | None: + try: + return UserManager.create(name="admin_user") + except Exception: + return None diff --git a/backend/tests/integration/connector_job_tests/slack/slack_api_utils.py b/backend/tests/integration/connector_job_tests/slack/slack_api_utils.py index db399328917..f17c4211066 100644 --- a/backend/tests/integration/connector_job_tests/slack/slack_api_utils.py +++ b/backend/tests/integration/connector_job_tests/slack/slack_api_utils.py @@ -73,9 +73,7 @@ def _clear_slack_conversation_members( if member_id == admin_user_id: continue try: - make_slack_api_call_w_retries( - slack_client.conversations_kick, channel=channel_id, user=member_id - ) + slack_client.conversations_kick(channel=channel_id, user=member_id) print(f"Kicked member: {member_id}") except Exception as e: if "cant_kick_self" in str(e): @@ -83,9 +81,7 @@ def _clear_slack_conversation_members( print(f"Error kicking member: {e}") print(member_id) try: - make_slack_api_call_w_retries( - slack_client.conversations_unarchive, channel=channel_id - ) + slack_client.conversations_unarchive(channel=channel_id) channel["is_archived"] = False except Exception: # Channel is already unarchived @@ -98,11 +94,7 @@ def _add_slack_conversation_members( channel_id = _get_slack_channel_id(channel) for user_id in member_ids: try: - make_slack_api_call_w_retries( - slack_client.conversations_invite, - channel=channel_id, - users=user_id, - ) + slack_client.conversations_invite(channel=channel_id, users=user_id) except Exception as e: if "already_in_channel" in str(e): continue @@ -129,11 +121,7 @@ def _delete_slack_conversation_messages( try: if not (ts := message.get("ts")): raise ValueError("Message timestamp is missing") - make_slack_api_call_w_retries( - slack_client.chat_delete, - channel=channel_id, - ts=ts, - ) + slack_client.chat_delete(channel=channel_id, ts=ts) except Exception as e: print(f"Error deleting message: {e}") print(message) @@ -165,16 +153,12 @@ def _build_slack_channel_from_name( ) try: - channel_response = make_slack_api_call_w_retries( - slack_client.conversations_unarchive, - channel=channel_response["channel"]["id"], - ) + slack_client.conversations_unarchive(channel=channel_response["channel"]["id"]) except Exception: # Channel is already unarchived pass try: - channel_response = make_slack_api_call_w_retries( - slack_client.conversations_invite, + slack_client.conversations_invite( channel=channel_response["channel"]["id"], users=[admin_user_id], ) @@ -302,10 +286,6 @@ def cleanup_after_test( # "done" in the channel name indicates that this channel is free to be used for a new test new_name = f"done_{str(uuid4())}" try: - make_slack_api_call_w_retries( - slack_client.conversations_rename, - channel=channel["id"], - name=new_name, - ) + slack_client.conversations_rename(channel=channel["id"], name=new_name) except SlackApiError as e: print(f"Error renaming channel {channel['id']}: {e}") diff --git a/backend/tests/integration/tests/dev_apis/test_simple_chat_api.py b/backend/tests/integration/tests/dev_apis/test_simple_chat_api.py index 0a4e7b40b57..fd7db7098bd 100644 --- a/backend/tests/integration/tests/dev_apis/test_simple_chat_api.py +++ b/backend/tests/integration/tests/dev_apis/test_simple_chat_api.py @@ -1,7 +1,10 @@ +import json + import requests from danswer.configs.constants import MessageType from tests.integration.common_utils.constants import API_SERVER_URL +from tests.integration.common_utils.constants import GENERAL_HEADERS from tests.integration.common_utils.constants import NUM_DOCS from tests.integration.common_utils.managers.api_key import APIKeyManager from tests.integration.common_utils.managers.cc_pair import CCPairManager @@ -145,3 +148,86 @@ def test_using_reference_docs_with_simple_with_history_api_flow(reset: None) -> # This ensures the the document we think we are referencing when we send the search_doc_ids in the second # message is the document that we expect it to be assert response_json["top_documents"][0]["document_id"] == cc_pair_1.documents[2].id + + +def test_send_message_simple_with_history_strict_json( + new_admin_user: DATestUser | None, +) -> None: + # create connectors + cc_pair_1: DATestCCPair = CCPairManager.create_from_scratch( + user_performing_action=new_admin_user, + ) + api_key: DATestAPIKey = APIKeyManager.create( + user_performing_action=new_admin_user, + ) + LLMProviderManager.create(user_performing_action=new_admin_user) + cc_pair_1.documents = DocumentManager.seed_dummy_docs( + cc_pair=cc_pair_1, + num_docs=NUM_DOCS, + api_key=api_key, + ) + + response = requests.post( + f"{API_SERVER_URL}/chat/send-message-simple-with-history", + json={ + "messages": [ + { + "message": "List the names of the first three US presidents in JSON format", + "role": MessageType.USER.value, + } + ], + "persona_id": 0, + "prompt_id": 0, + "structured_response_format": { + "type": "json_object", + "schema": { + "type": "object", + "properties": { + "presidents": { + "type": "array", + "items": {"type": "string"}, + "description": "List of the first three US presidents", + } + }, + "required": ["presidents"], + }, + }, + }, + headers=new_admin_user.headers if new_admin_user else GENERAL_HEADERS, + ) + assert response.status_code == 200 + + response_json = response.json() + + # Check that the answer is present + assert "answer" in response_json + assert response_json["answer"] is not None + + # helper + def clean_json_string(json_string: str) -> str: + return json_string.strip().removeprefix("```json").removesuffix("```").strip() + + # Attempt to parse the answer as JSON + try: + clean_answer = clean_json_string(response_json["answer"]) + parsed_answer = json.loads(clean_answer) + assert isinstance(parsed_answer, dict) + assert "presidents" in parsed_answer + assert isinstance(parsed_answer["presidents"], list) + assert len(parsed_answer["presidents"]) == 3 + for president in parsed_answer["presidents"]: + assert isinstance(president, str) + except json.JSONDecodeError: + assert False, "The answer is not a valid JSON object" + + # Check that the answer_citationless is also valid JSON + assert "answer_citationless" in response_json + assert response_json["answer_citationless"] is not None + try: + clean_answer_citationless = clean_json_string( + response_json["answer_citationless"] + ) + parsed_answer_citationless = json.loads(clean_answer_citationless) + assert isinstance(parsed_answer_citationless, dict) + except json.JSONDecodeError: + assert False, "The answer_citationless is not a valid JSON object" diff --git a/deployment/docker_compose/docker-compose.dev.yml b/deployment/docker_compose/docker-compose.dev.yml index d22bde5b465..7b31689c8f3 100644 --- a/deployment/docker_compose/docker-compose.dev.yml +++ b/deployment/docker_compose/docker-compose.dev.yml @@ -63,6 +63,7 @@ services: - QA_PROMPT_OVERRIDE=${QA_PROMPT_OVERRIDE:-} # Other services - POSTGRES_HOST=relational_db + - POSTGRES_DEFAULT_SCHEMA=${POSTGRES_DEFAULT_SCHEMA:-} - VESPA_HOST=index - REDIS_HOST=cache - WEB_DOMAIN=${WEB_DOMAIN:-} # For frontend redirect auth purpose @@ -147,6 +148,7 @@ services: - POSTGRES_USER=${POSTGRES_USER:-} - POSTGRES_PASSWORD=${POSTGRES_PASSWORD:-} - POSTGRES_DB=${POSTGRES_DB:-} + - POSTGRES_DEFAULT_SCHEMA=${POSTGRES_DEFAULT_SCHEMA:-} - VESPA_HOST=index - REDIS_HOST=cache - WEB_DOMAIN=${WEB_DOMAIN:-} # For frontend redirect auth purpose for OAuth2 connectors diff --git a/deployment/kubernetes/env-configmap.yaml b/deployment/kubernetes/env-configmap.yaml index 1d4bf1cffd7..e1eefaeca90 100644 --- a/deployment/kubernetes/env-configmap.yaml +++ b/deployment/kubernetes/env-configmap.yaml @@ -32,6 +32,7 @@ data: QA_PROMPT_OVERRIDE: "" # Other Services POSTGRES_HOST: "relational-db-service" + POSTGRES_DEFAULT_SCHEMA: "" VESPA_HOST: "document-index-service" REDIS_HOST: "redis-service" # Internet Search Tool diff --git a/web/src/app/admin/assistants/AssistantEditor.tsx b/web/src/app/admin/assistants/AssistantEditor.tsx index 7ca1d087641..2eec9632c66 100644 --- a/web/src/app/admin/assistants/AssistantEditor.tsx +++ b/web/src/app/admin/assistants/AssistantEditor.tsx @@ -61,6 +61,7 @@ import { import { AdvancedOptionsToggle } from "@/components/AdvancedOptionsToggle"; import { buildImgUrl } from "@/app/chat/files/images/utils"; import { LlmList } from "@/components/llm/LLMList"; +import { useAssistants } from "@/components/context/AssistantsContext"; function findSearchTool(tools: ToolSnapshot[]) { return tools.find((tool) => tool.in_code_tool_id === "SearchTool"); @@ -105,6 +106,7 @@ export function AssistantEditor({ shouldAddAssistantToUserPreferences?: boolean; admin?: boolean; }) { + const { refreshAssistants } = useAssistants(); const router = useRouter(); const { popup, setPopup } = usePopup(); @@ -433,6 +435,7 @@ export function AssistantEditor({ }); } } + await refreshAssistants(); router.push( redirectType === SuccessfulPersonaUpdateRedirectType.ADMIN ? `/admin/assistants?u=${Date.now()}` diff --git a/web/src/app/admin/assistants/PersonaTable.tsx b/web/src/app/admin/assistants/PersonaTable.tsx index 15775c7cdfb..6adf22a525e 100644 --- a/web/src/app/admin/assistants/PersonaTable.tsx +++ b/web/src/app/admin/assistants/PersonaTable.tsx @@ -5,7 +5,7 @@ import { Persona } from "./interfaces"; import { useRouter } from "next/navigation"; import { CustomCheckbox } from "@/components/CustomCheckbox"; import { usePopup } from "@/components/admin/connectors/Popup"; -import { useState, useMemo } from "react"; +import { useState, useMemo, useEffect } from "react"; import { UniqueIdentifier } from "@dnd-kit/core"; import { DraggableTable } from "@/components/table/DraggableTable"; import { @@ -16,6 +16,7 @@ import { import { FiEdit2 } from "react-icons/fi"; import { TrashIcon } from "@/components/icons/icons"; import { useUser } from "@/components/user/UserProvider"; +import { useAssistants } from "@/components/context/AssistantsContext"; function PersonaTypeDisplay({ persona }: { persona: Persona }) { if (persona.builtin_persona) { @@ -37,43 +38,36 @@ function PersonaTypeDisplay({ persona }: { persona: Persona }) { return Personal {persona.owner && <>({persona.owner.email})}; } -export function PersonasTable({ - allPersonas, - editablePersonas, -}: { - allPersonas: Persona[]; - editablePersonas: Persona[]; -}) { +export function PersonasTable() { const router = useRouter(); const { popup, setPopup } = usePopup(); - - const { isLoadingUser, isAdmin } = useUser(); + const { refreshUser, isLoadingUser, isAdmin } = useUser(); + const { + allAssistants: assistants, + refreshAssistants, + editablePersonas, + } = useAssistants(); const editablePersonaIds = useMemo(() => { return new Set(editablePersonas.map((p) => p.id.toString())); }, [editablePersonas]); - const sortedPersonas = useMemo(() => { + const [finalPersonas, setFinalPersonas] = useState([]); + + useEffect(() => { const editable = editablePersonas.sort(personaComparator); - const nonEditable = allPersonas + const nonEditable = assistants .filter((p) => !editablePersonaIds.has(p.id.toString())) .sort(personaComparator); - return [...editable, ...nonEditable]; - }, [allPersonas, editablePersonas]); - - const [finalPersonas, setFinalPersonas] = useState( - sortedPersonas.map((persona) => persona.id.toString()) - ); - const finalPersonaValues = finalPersonas - .filter((id) => new Set(allPersonas.map((p) => p.id.toString())).has(id)) - .map((id) => { - return sortedPersonas.find( - (persona) => persona.id.toString() === id - ) as Persona; - }); + setFinalPersonas([...editable, ...nonEditable]); + }, [editablePersonas, assistants, editablePersonaIds]); const updatePersonaOrder = async (orderedPersonaIds: UniqueIdentifier[]) => { - setFinalPersonas(orderedPersonaIds.map((id) => id.toString())); + const reorderedAssistants = orderedPersonaIds.map( + (id) => assistants.find((assistant) => assistant.id.toString() === id)! + ); + + setFinalPersonas(reorderedAssistants); const displayPriorityMap = new Map(); orderedPersonaIds.forEach((personaId, ind) => { @@ -89,13 +83,19 @@ export function PersonasTable({ display_priority_map: Object.fromEntries(displayPriorityMap), }), }); + if (!response.ok) { setPopup({ type: "error", message: `Failed to update persona order - ${await response.text()}`, }); + setFinalPersonas(assistants); router.refresh(); + return; } + + await refreshAssistants(); + await refreshUser(); }; if (isLoadingUser) { @@ -115,8 +115,8 @@ export function PersonasTable({ { - const isEditable = editablePersonaIds.has(persona.id.toString()); + rows={finalPersonas.map((persona) => { + const isEditable = editablePersonas.includes(persona); return { id: persona.id.toString(), cells: [ diff --git a/web/src/app/admin/assistants/page.tsx b/web/src/app/admin/assistants/page.tsx index 7f3922ac4a7..6c13bbb66dd 100644 --- a/web/src/app/admin/assistants/page.tsx +++ b/web/src/app/admin/assistants/page.tsx @@ -2,33 +2,10 @@ import { PersonasTable } from "./PersonaTable"; import { FiPlusSquare } from "react-icons/fi"; import Link from "next/link"; import { Divider, Text, Title } from "@tremor/react"; -import { fetchSS } from "@/lib/utilsSS"; -import { ErrorCallout } from "@/components/ErrorCallout"; -import { Persona } from "./interfaces"; import { AssistantsIcon } from "@/components/icons/icons"; import { AdminPageTitle } from "@/components/admin/Title"; export default async function Page() { - const allPersonaResponse = await fetchSS("/admin/persona"); - const editablePersonaResponse = await fetchSS( - "/admin/persona?get_editable=true" - ); - - if (!allPersonaResponse.ok || !editablePersonaResponse.ok) { - return ( - - ); - } - - const allPersonas = (await allPersonaResponse.json()) as Persona[]; - const editablePersonas = (await editablePersonaResponse.json()) as Persona[]; - return (
} title="Assistants" /> @@ -64,10 +41,7 @@ export default async function Page() { Existing Assistants - +
); diff --git a/web/src/app/admin/connector/[ccPairId]/ReIndexButton.tsx b/web/src/app/admin/connector/[ccPairId]/ReIndexButton.tsx index dced8811a3f..75bb2eca95d 100644 --- a/web/src/app/admin/connector/[ccPairId]/ReIndexButton.tsx +++ b/web/src/app/admin/connector/[ccPairId]/ReIndexButton.tsx @@ -94,12 +94,14 @@ export function ReIndexButton({ connectorId, credentialId, isDisabled, + isIndexing, isDeleting, }: { ccPairId: number; connectorId: number; credentialId: number; isDisabled: boolean; + isIndexing: boolean; isDeleting: boolean; }) { const { popup, setPopup } = usePopup(); @@ -128,9 +130,11 @@ export function ReIndexButton({ tooltip={ isDeleting ? "Cannot index while connector is deleting" - : isDisabled - ? "Connector must be re-enabled before indexing" - : undefined + : isIndexing + ? "Indexing is already in progress" + : isDisabled + ? "Connector must be re-enabled before indexing" + : undefined } > Index diff --git a/web/src/app/admin/connector/[ccPairId]/page.tsx b/web/src/app/admin/connector/[ccPairId]/page.tsx index 9cdf7c83ec2..e2576cc9b81 100644 --- a/web/src/app/admin/connector/[ccPairId]/page.tsx +++ b/web/src/app/admin/connector/[ccPairId]/page.tsx @@ -188,8 +188,10 @@ function Main({ ccPairId }: { ccPairId: number }) { connectorId={ccPair.connector.id} credentialId={ccPair.credential.id} isDisabled={ + ccPair.indexing || ccPair.status === ConnectorCredentialPairStatus.PAUSED } + isIndexing={ccPair.indexing} isDeleting={isDeleting} /> )} diff --git a/web/src/app/admin/connector/[ccPairId]/types.ts b/web/src/app/admin/connector/[ccPairId]/types.ts index 55bbe955730..5e9cec428c1 100644 --- a/web/src/app/admin/connector/[ccPairId]/types.ts +++ b/web/src/app/admin/connector/[ccPairId]/types.ts @@ -25,6 +25,7 @@ export interface CCPairFullInfo { is_public: boolean; is_editable_for_current_user: boolean; deletion_failure_message: string | null; + indexing: boolean; } export interface PaginatedIndexAttempts { diff --git a/web/src/app/admin/connectors/[connector]/AddConnectorPage.tsx b/web/src/app/admin/connectors/[connector]/AddConnectorPage.tsx index cc8173082da..c2e903e2776 100644 --- a/web/src/app/admin/connectors/[connector]/AddConnectorPage.tsx +++ b/web/src/app/admin/connectors/[connector]/AddConnectorPage.tsx @@ -1,6 +1,6 @@ "use client"; -import { FetchError, errorHandlingFetcher } from "@/lib/fetcher"; +import { errorHandlingFetcher } from "@/lib/fetcher"; import useSWR, { mutate } from "swr"; import { HealthCheckBanner } from "@/components/health/healthcheck"; @@ -40,8 +40,6 @@ import { useGoogleDriveCredentials, } from "./pages/utils/hooks"; import { Formik } from "formik"; -import { AccessTypeForm } from "@/components/admin/connectors/AccessTypeForm"; -import { AccessTypeGroupSelector } from "@/components/admin/connectors/AccessTypeGroupSelector"; import NavigationRow from "./NavigationRow"; import { useRouter } from "next/navigation"; export interface AdvancedConfig { diff --git a/web/src/app/admin/embeddings/RerankingFormPage.tsx b/web/src/app/admin/embeddings/RerankingFormPage.tsx index 1e0aae06594..67f5fc1614b 100644 --- a/web/src/app/admin/embeddings/RerankingFormPage.tsx +++ b/web/src/app/admin/embeddings/RerankingFormPage.tsx @@ -90,9 +90,10 @@ const RerankingDetailsForm = forwardRef< return (
-

- Post-processing -

+

+ Select from cloud, self-hosted models, or use no reranking + model. +

{originalRerankingDetails.rerank_model_name && (