From a4e56ee7434c16d2d0d932f939a5eccdd29cb0d9 Mon Sep 17 00:00:00 2001 From: WD Date: Tue, 27 Aug 2024 09:51:48 +0800 Subject: [PATCH] feat(backend): support ollama llm; support ollama, jina, cohere embedding (#247) --- .env.example | 10 ++- backend/app/alembic/versions/00534dc350db_.py | 76 +++++++++++++++++++ backend/app/alembic/versions/2fc10c21bf88_.py | 13 ++-- backend/app/api/admin_routes/llm.py | 2 +- backend/app/core/config.py | 10 ++- backend/app/models/chunk.py | 5 +- backend/app/models/embed_model.py | 4 +- backend/app/models/knowledge_graph.py | 14 +++- backend/app/models/llm.py | 4 +- backend/app/models/reranker_model.py | 4 +- backend/app/models/semantic_cache.py | 10 ++- backend/app/rag/build.py | 9 ++- backend/app/rag/chat_config.py | 24 ++++++ backend/app/rag/embed_model_option.py | 38 +++++++++- backend/app/rag/llm_option.py | 12 +++ .../app/rag/vector_store/tidb_vector_store.py | 6 +- backend/app/types.py | 5 ++ backend/app/utils/dspy.py | 9 +++ backend/pyproject.toml | 6 +- backend/requirements-dev.lock | 53 ++++++++----- backend/requirements.lock | 53 ++++++++----- 21 files changed, 299 insertions(+), 68 deletions(-) create mode 100644 backend/app/alembic/versions/00534dc350db_.py diff --git a/.env.example b/.env.example index 9d6be5c65..29b441c58 100644 --- a/.env.example +++ b/.env.example @@ -18,5 +18,11 @@ TIDB_PASSWORD= TIDB_DATABASE= TIDB_SSL=true -# *** DO NOT CHANGE BELOW CONFIGURATIONS UNLESS YOU KNOW WHAT YOU ARE DOING -DSP_CACHEBOOL=false +# CAUTION: Do not change EMBEDDING_DIMS after initializing the database. +# Changing the embedding dimensions requires recreating the database and tables. +# The default EMBEDDING_DIMS and EMBEDDING_MAX_TOKENS are set for the OpenAI text-embedding-3-small model. +# If using a different embedding model, adjust these values according to the model's specifications. +# For example: +# maidalun1020/bce-embedding-base_v1: EMBEDDING_DIMS=768 EMBEDDING_MAX_TOKENS=512 +EMBEDDING_DIMS=1536 +EMBEDDING_MAX_TOKENS=8191 diff --git a/backend/app/alembic/versions/00534dc350db_.py b/backend/app/alembic/versions/00534dc350db_.py new file mode 100644 index 000000000..8c0d9e4dc --- /dev/null +++ b/backend/app/alembic/versions/00534dc350db_.py @@ -0,0 +1,76 @@ +"""empty message + +Revision ID: 00534dc350db +Revises: 10f36e8a25c4 +Create Date: 2024-08-26 12:46:00.203425 + +""" + +from alembic import op +import sqlalchemy as sa +from sqlalchemy.dialects import mysql + +# revision identifiers, used by Alembic. +revision = "00534dc350db" +down_revision = "10f36e8a25c4" +branch_labels = None +depends_on = None + + +def upgrade(): + # ### commands auto generated by Alembic - please adjust! ### + op.alter_column( + "embedding_models", + "provider", + existing_type=mysql.ENUM("OPENAI"), + type_=sa.String(length=32), + existing_nullable=False, + ) + op.alter_column( + "llms", + "provider", + existing_type=mysql.ENUM( + "OPENAI", "GEMINI", "ANTHROPIC_VERTEX", "OPENAI_LIKE", "BEDROCK" + ), + type_=sa.String(length=32), + existing_nullable=False, + ) + op.alter_column( + "reranker_models", + "provider", + existing_type=mysql.ENUM("JINA", "COHERE", "BAISHENG"), + type_=sa.String(length=32), + existing_nullable=False, + ) + op.execute("UPDATE embedding_models SET provider = lower(provider)") + op.execute("UPDATE llms SET provider = lower(provider)") + op.execute("UPDATE reranker_models SET provider = lower(provider)") + # ### end Alembic commands ### + + +def downgrade(): + # ### commands auto generated by Alembic - please adjust! ### + op.alter_column( + "reranker_models", + "provider", + existing_type=sa.String(length=32), + type_=mysql.ENUM("JINA", "COHERE", "BAISHENG"), + existing_nullable=False, + ) + op.alter_column( + "llms", + "provider", + existing_type=sa.String(length=32), + type_=mysql.ENUM( + "OPENAI", "GEMINI", "ANTHROPIC_VERTEX", "OPENAI_LIKE", "BEDROCK" + ), + existing_nullable=False, + ) + op.alter_column( + "embedding_models", + "provider", + existing_type=sa.String(length=32), + type_=mysql.ENUM("OPENAI"), + existing_nullable=False, + ) + # ### end Alembic commands ### diff --git a/backend/app/alembic/versions/2fc10c21bf88_.py b/backend/app/alembic/versions/2fc10c21bf88_.py index 877938673..2e742e144 100644 --- a/backend/app/alembic/versions/2fc10c21bf88_.py +++ b/backend/app/alembic/versions/2fc10c21bf88_.py @@ -11,6 +11,7 @@ import sqlmodel.sql.sqltypes from tidb_vector.sqlalchemy import VectorType from sqlalchemy.dialects import mysql +from app.core.config import settings # revision identifiers, used by Alembic. revision = "2fc10c21bf88" @@ -98,13 +99,13 @@ def upgrade(): sa.Column("id", sa.Integer(), nullable=False), sa.Column( "description_vec", - VectorType(dim=1536), + VectorType(dim=settings.EMBEDDING_DIMS), nullable=True, comment="hnsw(distance=cosine)", ), sa.Column( "meta_vec", - VectorType(dim=1536), + VectorType(dim=settings.EMBEDDING_DIMS), nullable=True, comment="hnsw(distance=cosine)", ), @@ -116,14 +117,14 @@ def upgrade(): sa.Column("query", sa.Text(), nullable=True), sa.Column( "query_vec", - VectorType(dim=1536), + VectorType(dim=settings.EMBEDDING_DIMS), nullable=True, comment="hnsw(distance=cosine)", ), sa.Column("value", sa.Text(), nullable=True), sa.Column( "value_vec", - VectorType(dim=1536), + VectorType(dim=settings.EMBEDDING_DIMS), nullable=True, comment="hnsw(distance=cosine)", ), @@ -289,7 +290,7 @@ def upgrade(): sa.Column("meta", sa.JSON(), nullable=True), sa.Column( "embedding", - VectorType(dim=1536), + VectorType(dim=settings.EMBEDDING_DIMS), nullable=True, comment="hnsw(distance=cosine)", ), @@ -329,7 +330,7 @@ def upgrade(): sa.Column("id", sa.Integer(), nullable=False), sa.Column( "description_vec", - VectorType(dim=1536), + VectorType(dim=settings.EMBEDDING_DIMS), nullable=True, comment="hnsw(distance=cosine)", ), diff --git a/backend/app/api/admin_routes/llm.py b/backend/app/api/admin_routes/llm.py index 1a673717c..d1f26b7df 100644 --- a/backend/app/api/admin_routes/llm.py +++ b/backend/app/api/admin_routes/llm.py @@ -151,7 +151,7 @@ def test_embedding_model( credentials=db_embed_model.credentials, ) embedding = embed_model.get_query_embedding("Hello, world!") - expected_length = settings.EMBEDDOMG_DIMS + expected_length = settings.EMBEDDING_DIMS if len(embedding) != expected_length: raise ValueError( f"Currently we only support {expected_length} dims embedding, got {len(embedding)} dims." diff --git a/backend/app/core/config.py b/backend/app/core/config.py index 46b858ec1..a4d255b1b 100644 --- a/backend/app/core/config.py +++ b/backend/app/core/config.py @@ -79,8 +79,14 @@ def server_host(self) -> str: COMPLIED_INTENT_ANALYSIS_PROGRAM_PATH: str | None = None - # Currently, we only support 1536 dims for the embedding model - EMBEDDOMG_DIMS: int = 1536 + # CAUTION: Do not change EMBEDDING_DIMS after initializing the database. + # Changing the embedding dimensions requires recreating the database and tables. + # The default EMBEDDING_DIMS and EMBEDDING_MAX_TOKENS are set for the OpenAI text-embedding-3-small model. + # If using a different embedding model, adjust these values according to the model's specifications. + # For example: + # maidalun1020/bce-embedding-base_v1: EMBEDDING_DIMS=768 EMBEDDING_MAX_TOKENS=512 + EMBEDDING_DIMS: int = 1536 + EMBEDDING_MAX_TOKENS: int = 8191 @computed_field # type: ignore[misc] @property diff --git a/backend/app/models/chunk.py b/backend/app/models/chunk.py index 988def35e..c19f4a76f 100644 --- a/backend/app/models/chunk.py +++ b/backend/app/models/chunk.py @@ -11,6 +11,7 @@ from tidb_vector.sqlalchemy import VectorType from llama_index.core.schema import TextNode +from app.core.config import settings from .base import UpdatableBaseModel, UUIDBaseModel @@ -27,7 +28,9 @@ class Chunk(UUIDBaseModel, UpdatableBaseModel, table=True): text: str = Field(sa_column=Column(Text)) meta: dict | list = Field(default={}, sa_column=Column(JSON)) embedding: Any = Field( - sa_column=Column(VectorType(1536), comment="hnsw(distance=cosine)") + sa_column=Column( + VectorType(settings.EMBEDDING_DIMS), comment="hnsw(distance=cosine)" + ) ) document_id: int = Field(foreign_key="documents.id", nullable=True) document: "Document" = SQLRelationship( diff --git a/backend/app/models/embed_model.py b/backend/app/models/embed_model.py index 15ba01ac1..ae696b938 100644 --- a/backend/app/models/embed_model.py +++ b/backend/app/models/embed_model.py @@ -1,6 +1,6 @@ from typing import Optional, Any -from sqlmodel import Field, Column, JSON +from sqlmodel import Field, Column, JSON, String from .base import UpdatableBaseModel, AESEncryptedColumn from app.types import EmbeddingProvider @@ -8,7 +8,7 @@ class BaseEmbeddingModel(UpdatableBaseModel): name: str = Field(max_length=64) - provider: EmbeddingProvider + provider: EmbeddingProvider = Field(sa_column=Column(String(32), nullable=False)) model: str = Field(max_length=256) config: dict | list | None = Field(sa_column=Column(JSON), default={}) is_default: bool = Field(default=False) diff --git a/backend/app/models/knowledge_graph.py b/backend/app/models/knowledge_graph.py index b3d41ae7c..b8ae3f9da 100644 --- a/backend/app/models/knowledge_graph.py +++ b/backend/app/models/knowledge_graph.py @@ -14,6 +14,8 @@ ) from tidb_vector.sqlalchemy import VectorType +from app.core.config import settings + class EntityType(str, enum.Enum): original = "original" @@ -34,10 +36,14 @@ class EntityBase(SQLModel): class Entity(EntityBase, table=True): id: Optional[int] = Field(default=None, primary_key=True) description_vec: Any = Field( - sa_column=Column(VectorType(1536), comment="hnsw(distance=cosine)") + sa_column=Column( + VectorType(settings.EMBEDDING_DIMS), comment="hnsw(distance=cosine)" + ) ) meta_vec: Any = Field( - sa_column=Column(VectorType(1536), comment="hnsw(distance=cosine)") + sa_column=Column( + VectorType(settings.EMBEDDING_DIMS), comment="hnsw(distance=cosine)" + ) ) __tablename__ = "entities" @@ -70,7 +76,9 @@ class RelationshipBase(SQLModel): class Relationship(RelationshipBase, table=True): id: Optional[int] = Field(default=None, primary_key=True) description_vec: Any = Field( - sa_column=Column(VectorType(1536), comment="hnsw(distance=cosine)") + sa_column=Column( + VectorType(settings.EMBEDDING_DIMS), comment="hnsw(distance=cosine)" + ) ) source_entity: Entity = SQLModelRelationship( sa_relationship_kwargs={ diff --git a/backend/app/models/llm.py b/backend/app/models/llm.py index e3f7aba21..360640067 100644 --- a/backend/app/models/llm.py +++ b/backend/app/models/llm.py @@ -1,6 +1,6 @@ from typing import Optional, Any -from sqlmodel import Field, Column, JSON +from sqlmodel import Field, Column, JSON, String from .base import UpdatableBaseModel, AESEncryptedColumn from app.types import LLMProvider @@ -8,7 +8,7 @@ class BaseLLM(UpdatableBaseModel): name: str = Field(max_length=64) - provider: LLMProvider + provider: LLMProvider = Field(sa_column=Column(String(32), nullable=False)) model: str = Field(max_length=256) config: dict | list | None = Field(sa_column=Column(JSON), default={}) is_default: bool = Field(default=False) diff --git a/backend/app/models/reranker_model.py b/backend/app/models/reranker_model.py index 2d451b140..020821a54 100644 --- a/backend/app/models/reranker_model.py +++ b/backend/app/models/reranker_model.py @@ -1,6 +1,6 @@ from typing import Optional, Any -from sqlmodel import Field, Column, JSON +from sqlmodel import Field, Column, JSON, String from .base import UpdatableBaseModel, AESEncryptedColumn from app.types import RerankerProvider @@ -8,7 +8,7 @@ class BaseRerankerModel(UpdatableBaseModel): name: str = Field(max_length=64) - provider: RerankerProvider + provider: RerankerProvider = Field(sa_column=Column(String(32), nullable=False)) model: str = Field(max_length=256) top_n: int = Field(default=10) config: dict | list | None = Field(sa_column=Column(JSON), default={}) diff --git a/backend/app/models/semantic_cache.py b/backend/app/models/semantic_cache.py index 45c91e9cc..f252d947c 100644 --- a/backend/app/models/semantic_cache.py +++ b/backend/app/models/semantic_cache.py @@ -12,16 +12,22 @@ ) from tidb_vector.sqlalchemy import VectorType +from app.core.config import settings + class SemanticCache(SQLModel, table=True): id: Optional[int] = Field(default=None, primary_key=True) query: str = Field(sa_column=Column(Text)) query_vec: Any = Field( - sa_column=Column(VectorType(1536), comment="hnsw(distance=cosine)") + sa_column=Column( + VectorType(settings.EMBEDDING_DIMS), comment="hnsw(distance=cosine)" + ) ) value: str = Field(sa_column=Column(Text)) value_vec: Any = Field( - sa_column=Column(VectorType(1536), comment="hnsw(distance=cosine)") + sa_column=Column( + VectorType(settings.EMBEDDING_DIMS), comment="hnsw(distance=cosine)" + ) ) meta: List | Dict = Field(default={}, sa_column=Column(JSON)) created_at: datetime = Field( diff --git a/backend/app/rag/build.py b/backend/app/rag/build.py index 39142d0bb..f6a196530 100644 --- a/backend/app/rag/build.py +++ b/backend/app/rag/build.py @@ -16,6 +16,7 @@ from app.rag.node_parser import MarkdownNodeParser from app.rag.vector_store.tidb_vector_store import TiDBVectorStore from app.rag.chat_config import get_default_embedding_model +from app.core.config import settings from app.models import ( Document as DBDocument, Chunk as DBChunk, @@ -45,9 +46,13 @@ def build_vector_index_from_document( if db_document.mime_type.lower() == "text/markdown": # spliter = MarkdownNodeParser() # TODO: FIX MarkdownNodeParser - spliter = SentenceSplitter() + spliter = SentenceSplitter( + chunk_size=settings.EMBEDDING_MAX_TOKENS, + ) else: - spliter = SentenceSplitter() + spliter = SentenceSplitter( + chunk_size=settings.EMBEDDING_MAX_TOKENS, + ) _transformations = [ spliter, diff --git a/backend/app/rag/chat_config.py b/backend/app/rag/chat_config.py index 3215f6109..25452fbeb 100644 --- a/backend/app/rag/chat_config.py +++ b/backend/app/rag/chat_config.py @@ -10,10 +10,14 @@ from llama_index.llms.openai_like import OpenAILike from llama_index.llms.gemini import Gemini from llama_index.llms.bedrock import Bedrock +from llama_index.llms.ollama import Ollama from llama_index.core.llms.llm import LLM from llama_index.core.base.embeddings.base import BaseEmbedding from llama_index.core.postprocessor.types import BaseNodePostprocessor from llama_index.embeddings.openai import OpenAIEmbedding +from llama_index.embeddings.jinaai import JinaEmbedding +from llama_index.embeddings.cohere import CohereEmbedding +from llama_index.embeddings.ollama import OllamaEmbedding from llama_index.postprocessor.jinaai_rerank import JinaRerank from llama_index.postprocessor.cohere_rerank import CohereRerank from sqlmodel import Session, select @@ -208,6 +212,10 @@ def get_llm( if "max_tokens" not in config: config.update(max_tokens=4096) return AnthropicVertex(model=model, credentials=google_creds, **config) + case LLMProvider.OLLAMA: + config.setdefault("request_timeout", 60 * 5) + config.setdefault("context_window", 4096) + return Ollama(model=model, **config) case _: raise ValueError(f"Got unknown LLM provider: {provider}") @@ -241,6 +249,22 @@ def get_embedding_model( api_key=credentials, **config, ) + case EmbeddingProvider.JINA: + return JinaEmbedding( + model=model, + api_key=credentials, + **config, + ) + case EmbeddingProvider.COHERE: + return CohereEmbedding( + model_name=model, + cohere_api_key=credentials, + ) + case EmbeddingProvider.OLLAMA: + return OllamaEmbedding( + model_name=model, + **config, + ) case _: raise ValueError(f"Got unknown embedding provider: {provider}") diff --git a/backend/app/rag/embed_model_option.py b/backend/app/rag/embed_model_option.py index f50136cb5..3db0991db 100644 --- a/backend/app/rag/embed_model_option.py +++ b/backend/app/rag/embed_model_option.py @@ -25,10 +25,46 @@ class EmbeddingModelOption(BaseModel): provider_description="The OpenAI API provides a simple interface for developers to create an intelligence layer in their applications, powered by OpenAI's state of the art models.", provider_url="https://platform.openai.com", default_embedding_model="text-embedding-3-small", - embedding_model_description=f"Currently, we only support the OpenAI text embedding model with {settings.EMBEDDOMG_DIMS} dimensions.", + embedding_model_description=f"Please select a text embedding model with {settings.EMBEDDING_DIMS} dimensions.", credentials_display_name="OpenAI API Key", credentials_description="The API key of OpenAI, you can find it in https://platform.openai.com/api-keys", credentials_type="str", default_credentials="sk-****", ), + EmbeddingModelOption( + provider=EmbeddingProvider.JINA, + provider_display_name="Jina", + provider_description="Jina AI provides multimodal, bilingual long-context embeddings for search and RAG", + provider_url="https://jina.ai/embeddings/", + default_embedding_model="jina-embeddings-v2-base-en", + embedding_model_description=f"Find more information about Jina AI Embeddings at https://jina.ai/embeddings/, we need a model with {settings.EMBEDDING_DIMS} dimensions.", + credentials_display_name="Jina API Key", + credentials_description="The API key of Jina, you can find it in https://jina.ai/embeddings/", + credentials_type="str", + default_credentials="jina_****", + ), + EmbeddingModelOption( + provider=EmbeddingProvider.COHERE, + provider_display_name="Cohere", + provider_description="Cohere provides industry-leading large language models (LLMs) and RAG capabilities tailored to meet the needs of enterprise use cases that solve real-world problems.", + provider_url="https://cohere.com/embeddings", + default_embedding_model="embed-multilingual-v3.0", + embedding_model_description=f"Documentation: https://docs.cohere.com/docs/cohere-embed, we need a model with {settings.EMBEDDING_DIMS} dimensions.", + credentials_display_name="Cohere API Key", + credentials_description="You can get one from https://dashboard.cohere.com/api-keys", + credentials_type="str", + default_credentials="*****", + ), + EmbeddingModelOption( + provider=EmbeddingProvider.OLLAMA, + provider_display_name="Ollama", + provider_description="Ollama is a lightweight framework for building and running large language models and embed models.", + provider_url="https://ollama.com", + default_embedding_model="nomic-embed-text", + embedding_model_description=f"https://ollama.com/blog/embedding-models, we need a model with {settings.EMBEDDING_DIMS} dimensions.", + credentials_display_name="Ollama API Key", + credentials_description="Ollama doesn't require an API key, set a dummy string here is ok", + credentials_type="str", + default_credentials="dummy", + ), ] diff --git a/backend/app/rag/llm_option.py b/backend/app/rag/llm_option.py index f58013397..fb70b7888 100644 --- a/backend/app/rag/llm_option.py +++ b/backend/app/rag/llm_option.py @@ -52,6 +52,18 @@ class LLMOption(BaseModel): credentials_type="str", default_credentials="AIza****", ), + LLMOption( + provider=LLMProvider.OLLAMA, + provider_display_name="Ollama", + provider_description="Ollama is a lightweight framework for building and running large language models.", + provider_url="https://ollama.com", + default_llm_model="llama3.1", + llm_model_description="Find more in https://ollama.com/library", + credentials_display_name="Ollama API Key", + credentials_description="Ollama doesn't require an API key, set a dummy string here is ok", + credentials_type="str", + default_credentials="dummy", + ), LLMOption( provider=LLMProvider.ANTHROPIC_VERTEX, provider_display_name="Anthropic Vertex AI", diff --git a/backend/app/rag/vector_store/tidb_vector_store.py b/backend/app/rag/vector_store/tidb_vector_store.py index 9590d9d8d..82954b4d6 100644 --- a/backend/app/rag/vector_store/tidb_vector_store.py +++ b/backend/app/rag/vector_store/tidb_vector_store.py @@ -36,15 +36,15 @@ class TiDBVectorStore(BasePydanticVectorStore): _session: Session = PrivateAttr() _owns_session: bool = PrivateAttr() - stores_text = True - flat_metadata = False + stores_text: bool = True + flat_metadata: bool = False def __init__(self, session: Optional[Session] = None, **kwargs: Any) -> None: + super().__init__(**kwargs) self._session = session self._owns_session = session is None if self._session is None: self._session = Session(engine) - super().__init__(**kwargs) def close_session(self) -> None: # Always call this method is necessary to make sure the session is closed diff --git a/backend/app/types.py b/backend/app/types.py index 03290854b..7c9022138 100644 --- a/backend/app/types.py +++ b/backend/app/types.py @@ -7,13 +7,18 @@ class LLMProvider(str, enum.Enum): ANTHROPIC_VERTEX = "anthropic_vertex" OPENAI_LIKE = "openai_like" BEDROCK = "bedrock" + OLLAMA = "ollama" class EmbeddingProvider(str, enum.Enum): OPENAI = "openai" + JINA = "jina" + COHERE = "cohere" + OLLAMA = "ollama" class RerankerProvider(str, enum.Enum): JINA = "jina" COHERE = "cohere" BAISHENG = "baisheng" + LLM = "llm" diff --git a/backend/app/utils/dspy.py b/backend/app/utils/dspy.py index 4111570ca..78eb7b020 100644 --- a/backend/app/utils/dspy.py +++ b/backend/app/utils/dspy.py @@ -7,6 +7,7 @@ from llama_index.llms.openai_like import OpenAILike from llama_index.llms.gemini import Gemini from llama_index.llms.bedrock import Bedrock +from llama_index.llms.ollama import Ollama from app.rag.llms.anthropic_vertex import AnthropicVertex @@ -67,6 +68,14 @@ def get_dspy_lm_by_llama_llm(llama_llm: BaseLLM) -> dspy.LM: ) elif isinstance(llama_llm, AnthropicVertex): raise ValueError("AnthropicVertex is not supported by dspy.") + elif isinstance(llama_llm, Ollama): + return dspy.OllamaLocal( + model=llama_llm.model, + base_url=llama_llm.base_url, + timeout_s=llama_llm.request_timeout, + temperature=llama_llm.temperature, + max_tokens=llama_llm.context_window, + ) else: raise ValueError(f"Got unknown LLM provider: {llama_llm.__class__.__name__}") diff --git a/backend/pyproject.toml b/backend/pyproject.toml index 2a4a18e0c..07ac7cf3a 100644 --- a/backend/pyproject.toml +++ b/backend/pyproject.toml @@ -12,7 +12,7 @@ dependencies = [ "celery>=5.4.0", "dspy-ai>=2.4.9", "langfuse>=2.42.0", - "llama-index>=0.10.59", + "llama-index==0.10.68", "alembic>=1.13.1", "pydantic>=2.8.2", "pydantic-settings>=2.3.3", @@ -45,6 +45,10 @@ dependencies = [ "llama-index-postprocessor-cohere-rerank>=0.1.7", "llama-index-llms-bedrock>=0.1.12", "pypdf>=4.3.1", + "llama-index-llms-ollama<=0.3.0", + "llama-index-embeddings-ollama<=0.3.0", + "llama-index-embeddings-jinaai<=0.3.0", + "llama-index-embeddings-cohere<=0.3.0", ] readme = "README.md" requires-python = ">= 3.8" diff --git a/backend/requirements-dev.lock b/backend/requirements-dev.lock index da8eb9e6e..8f782cea4 100644 --- a/backend/requirements-dev.lock +++ b/backend/requirements-dev.lock @@ -86,6 +86,7 @@ click-plugins==1.1.1 click-repl==0.3.0 # via celery cohere==5.6.2 + # via llama-index-embeddings-cohere # via llama-index-postprocessor-cohere-rerank colorlog==6.8.2 # via optuna @@ -233,6 +234,7 @@ httpx==0.27.0 # via llama-cloud # via llama-index-core # via llama-index-legacy + # via ollama # via openai httpx-oauth==0.14.1 httpx-sse==0.4.0 @@ -259,6 +261,7 @@ jinja2==3.1.4 # via fastapi jiter==0.5.0 # via anthropic + # via openai jmespath==1.0.1 # via boto3 # via botocore @@ -294,23 +297,27 @@ langsmith==0.1.88 # via langchain # via langchain-community # via langchain-core -llama-cloud==0.0.10 +llama-cloud==0.0.15 # via llama-index-indices-managed-llama-cloud -llama-index==0.10.59 -llama-index-agent-openai==0.2.7 +llama-index==0.10.68 +llama-index-agent-openai==0.2.9 # via llama-index # via llama-index-program-openai -llama-index-cli==0.1.12 +llama-index-cli==0.1.13 # via llama-index -llama-index-core==0.10.59 +llama-index-core==0.10.68.post1 # via llama-index # via llama-index-agent-openai # via llama-index-cli + # via llama-index-embeddings-cohere + # via llama-index-embeddings-jinaai + # via llama-index-embeddings-ollama # via llama-index-embeddings-openai # via llama-index-indices-managed-llama-cloud # via llama-index-llms-anthropic # via llama-index-llms-bedrock # via llama-index-llms-gemini + # via llama-index-llms-ollama # via llama-index-llms-openai # via llama-index-llms-openai-like # via llama-index-multi-modal-llms-openai @@ -321,18 +328,22 @@ llama-index-core==0.10.59 # via llama-index-readers-file # via llama-index-readers-llama-parse # via llama-parse -llama-index-embeddings-openai==0.1.10 +llama-index-embeddings-cohere==0.1.9 +llama-index-embeddings-jinaai==0.2.1 +llama-index-embeddings-ollama==0.2.0 +llama-index-embeddings-openai==0.1.11 # via llama-index # via llama-index-cli -llama-index-indices-managed-llama-cloud==0.2.5 +llama-index-indices-managed-llama-cloud==0.2.7 # via llama-index llama-index-legacy==0.9.48 # via llama-index -llama-index-llms-anthropic==0.1.16 +llama-index-llms-anthropic==0.1.17 # via llama-index-llms-bedrock -llama-index-llms-bedrock==0.1.12 -llama-index-llms-gemini==0.1.11 -llama-index-llms-openai==0.1.27 +llama-index-llms-bedrock==0.1.13 +llama-index-llms-gemini==0.2.0 +llama-index-llms-ollama==0.2.2 +llama-index-llms-openai==0.1.31 # via llama-index # via llama-index-agent-openai # via llama-index-cli @@ -341,18 +352,18 @@ llama-index-llms-openai==0.1.27 # via llama-index-program-openai # via llama-index-question-gen-openai llama-index-llms-openai-like==0.1.3 -llama-index-multi-modal-llms-openai==0.1.6 +llama-index-multi-modal-llms-openai==0.1.9 # via llama-index llama-index-postprocessor-cohere-rerank==0.1.7 -llama-index-postprocessor-jinaai-rerank==0.1.6 -llama-index-program-openai==0.1.6 +llama-index-postprocessor-jinaai-rerank==0.1.7 +llama-index-program-openai==0.1.7 # via llama-index # via llama-index-question-gen-openai llama-index-question-gen-openai==0.1.3 # via llama-index -llama-index-readers-file==0.1.25 +llama-index-readers-file==0.1.33 # via llama-index -llama-index-readers-llama-parse==0.1.4 +llama-index-readers-llama-parse==0.1.6 # via llama-index llama-parse==0.4.4 # via llama-index-readers-llama-parse @@ -384,7 +395,7 @@ nest-asyncio==1.6.0 networkx==3.3 # via llama-index-core # via llama-index-legacy -nltk==3.8.1 +nltk==3.9.1 # via llama-index-core # via llama-index-legacy numpy==1.26.4 @@ -400,12 +411,15 @@ numpy==1.26.4 # via shapely # via tidb-vector # via transformers -openai==1.34.0 +ollama==0.3.1 + # via llama-index-embeddings-ollama + # via llama-index-llms-ollama +openai==1.42.0 # via dspy-ai # via langchain-openai # via llama-index-agent-openai - # via llama-index-core # via llama-index-legacy + # via llama-index-llms-openai # via ragas opentelemetry-api==1.24.0 # via deepeval @@ -504,6 +518,7 @@ pydantic==2.8.2 # via langfuse # via langsmith # via llama-cloud + # via llama-index-core # via openai # via pydantic-settings # via sqlmodel diff --git a/backend/requirements.lock b/backend/requirements.lock index da8eb9e6e..8f782cea4 100644 --- a/backend/requirements.lock +++ b/backend/requirements.lock @@ -86,6 +86,7 @@ click-plugins==1.1.1 click-repl==0.3.0 # via celery cohere==5.6.2 + # via llama-index-embeddings-cohere # via llama-index-postprocessor-cohere-rerank colorlog==6.8.2 # via optuna @@ -233,6 +234,7 @@ httpx==0.27.0 # via llama-cloud # via llama-index-core # via llama-index-legacy + # via ollama # via openai httpx-oauth==0.14.1 httpx-sse==0.4.0 @@ -259,6 +261,7 @@ jinja2==3.1.4 # via fastapi jiter==0.5.0 # via anthropic + # via openai jmespath==1.0.1 # via boto3 # via botocore @@ -294,23 +297,27 @@ langsmith==0.1.88 # via langchain # via langchain-community # via langchain-core -llama-cloud==0.0.10 +llama-cloud==0.0.15 # via llama-index-indices-managed-llama-cloud -llama-index==0.10.59 -llama-index-agent-openai==0.2.7 +llama-index==0.10.68 +llama-index-agent-openai==0.2.9 # via llama-index # via llama-index-program-openai -llama-index-cli==0.1.12 +llama-index-cli==0.1.13 # via llama-index -llama-index-core==0.10.59 +llama-index-core==0.10.68.post1 # via llama-index # via llama-index-agent-openai # via llama-index-cli + # via llama-index-embeddings-cohere + # via llama-index-embeddings-jinaai + # via llama-index-embeddings-ollama # via llama-index-embeddings-openai # via llama-index-indices-managed-llama-cloud # via llama-index-llms-anthropic # via llama-index-llms-bedrock # via llama-index-llms-gemini + # via llama-index-llms-ollama # via llama-index-llms-openai # via llama-index-llms-openai-like # via llama-index-multi-modal-llms-openai @@ -321,18 +328,22 @@ llama-index-core==0.10.59 # via llama-index-readers-file # via llama-index-readers-llama-parse # via llama-parse -llama-index-embeddings-openai==0.1.10 +llama-index-embeddings-cohere==0.1.9 +llama-index-embeddings-jinaai==0.2.1 +llama-index-embeddings-ollama==0.2.0 +llama-index-embeddings-openai==0.1.11 # via llama-index # via llama-index-cli -llama-index-indices-managed-llama-cloud==0.2.5 +llama-index-indices-managed-llama-cloud==0.2.7 # via llama-index llama-index-legacy==0.9.48 # via llama-index -llama-index-llms-anthropic==0.1.16 +llama-index-llms-anthropic==0.1.17 # via llama-index-llms-bedrock -llama-index-llms-bedrock==0.1.12 -llama-index-llms-gemini==0.1.11 -llama-index-llms-openai==0.1.27 +llama-index-llms-bedrock==0.1.13 +llama-index-llms-gemini==0.2.0 +llama-index-llms-ollama==0.2.2 +llama-index-llms-openai==0.1.31 # via llama-index # via llama-index-agent-openai # via llama-index-cli @@ -341,18 +352,18 @@ llama-index-llms-openai==0.1.27 # via llama-index-program-openai # via llama-index-question-gen-openai llama-index-llms-openai-like==0.1.3 -llama-index-multi-modal-llms-openai==0.1.6 +llama-index-multi-modal-llms-openai==0.1.9 # via llama-index llama-index-postprocessor-cohere-rerank==0.1.7 -llama-index-postprocessor-jinaai-rerank==0.1.6 -llama-index-program-openai==0.1.6 +llama-index-postprocessor-jinaai-rerank==0.1.7 +llama-index-program-openai==0.1.7 # via llama-index # via llama-index-question-gen-openai llama-index-question-gen-openai==0.1.3 # via llama-index -llama-index-readers-file==0.1.25 +llama-index-readers-file==0.1.33 # via llama-index -llama-index-readers-llama-parse==0.1.4 +llama-index-readers-llama-parse==0.1.6 # via llama-index llama-parse==0.4.4 # via llama-index-readers-llama-parse @@ -384,7 +395,7 @@ nest-asyncio==1.6.0 networkx==3.3 # via llama-index-core # via llama-index-legacy -nltk==3.8.1 +nltk==3.9.1 # via llama-index-core # via llama-index-legacy numpy==1.26.4 @@ -400,12 +411,15 @@ numpy==1.26.4 # via shapely # via tidb-vector # via transformers -openai==1.34.0 +ollama==0.3.1 + # via llama-index-embeddings-ollama + # via llama-index-llms-ollama +openai==1.42.0 # via dspy-ai # via langchain-openai # via llama-index-agent-openai - # via llama-index-core # via llama-index-legacy + # via llama-index-llms-openai # via ragas opentelemetry-api==1.24.0 # via deepeval @@ -504,6 +518,7 @@ pydantic==2.8.2 # via langfuse # via langsmith # via llama-cloud + # via llama-index-core # via openai # via pydantic-settings # via sqlmodel