From d11caa1f7423b37474bc57338bbc3ec17e084a82 Mon Sep 17 00:00:00 2001 From: Ana Pacheco Date: Fri, 20 Sep 2024 11:22:22 -0600 Subject: [PATCH] Get Installed ollama models, set them and activate and deactivate --- apis/paios/openapi.yaml | 6 +++ backend/api/RagIndexingView.py | 4 +- backend/managers/RagManager.py | 3 -- backend/managers/ResourcesManager.py | 52 +++++++++++++++---- backend/models.py | 1 + backend/schemas.py | 1 + .../75aaaf2cd1a2_added_resource_table.py | 1 + 7 files changed, 52 insertions(+), 16 deletions(-) diff --git a/apis/paios/openapi.yaml b/apis/paios/openapi.yaml index a0154de..5d56f52 100644 --- a/apis/paios/openapi.yaml +++ b/apis/paios/openapi.yaml @@ -1178,6 +1178,9 @@ components: icon: nullable: true $ref: '#/components/schemas/uri' + active: + nullable: true + $ref: '#/components/schemas/boolean_str' ResourceCreate: type: object title: ResourceCreate @@ -1210,6 +1213,9 @@ components: example: assistant icon: $ref: '#/components/schemas/uri' + active: + nullable: true + $ref: '#/components/schemas/boolean_str' required: - name - kind diff --git a/backend/api/RagIndexingView.py b/backend/api/RagIndexingView.py index 66f24f2..d1a42a4 100644 --- a/backend/api/RagIndexingView.py +++ b/backend/api/RagIndexingView.py @@ -18,9 +18,7 @@ async def post(self, resource_id: str, files: List[UploadFile] = File(...)): file_info_list = await self.rm.upload_file(resource_id, files) return JSONResponse(status_code=200, content={"message": "Document added", "files": file_info_list}) - async def delete(self, resource_id: str, body: dict = Body(...)): - print(f"body ({resource_id}) ={body}") - + async def delete(self, resource_id: str, body: dict = Body(...)): file_ids = body.get("file_ids") success_chroma_db = await self.rm.delete_documents_from_chroma(resource_id, file_ids) success_db = await self.rm.delete_file_from_db(file_ids) diff --git a/backend/managers/RagManager.py b/backend/managers/RagManager.py index 9276edd..46e2805 100644 --- a/backend/managers/RagManager.py +++ b/backend/managers/RagManager.py @@ -129,12 +129,10 @@ async def update_file_num_chunks(self, file_id: str, num_chunks: int): await session.commit() async def update_file_status(self, file_id: str, status: str): - print(f"Updating status of file {file_id} to {status}") async with db_session_context() as session: stmt = select(File).filter(File.file_id == file_id) files = (await session.execute(stmt)).scalars().all() for file in files: - print("updated") file.indexing_status = status await session.commit() @@ -261,7 +259,6 @@ async def delete_documents_from_chroma(self, resource_id: str, file_ids=List[str chunk_id = f"{page_id}-{n}" list_chunks_id.append(chunk_id) - print(f"Deleting {len(list_chunks_id)} chunks for page {page_id}") vectorstore.delete(ids=list_chunks_id) else: return None diff --git a/backend/managers/ResourcesManager.py b/backend/managers/ResourcesManager.py index 3a4e5b4..6e9ca8b 100644 --- a/backend/managers/ResourcesManager.py +++ b/backend/managers/ResourcesManager.py @@ -50,7 +50,8 @@ async def create_resource(self, resource_data: ResourceCreateSchema) -> str: "uri": resource_data.get("uri"), "description": resource_data.get("description"), "kind": kind, - "icon": resource_data.get("icon") + "icon": resource_data.get("icon"), + "active": resource_data.get("active") } async with db_session_context() as session: @@ -114,7 +115,8 @@ async def retrieve_resource(self, id: str) -> Optional[ResourceSchema]: uri=resource.uri, description=resource.description, kind=resource.kind, - icon=resource.icon) + icon=resource.icon, + active=resource.active) return None async def retrieve_resources(self, offset: int = 0, limit: int = 100, sort_by: Optional[str] = None, @@ -127,20 +129,38 @@ async def retrieve_resources(self, offset: int = 0, limit: int = 100, sort_by: O if key == 'name': query = query.filter(Resource.name.ilike(f"%{value}%")) if key == 'kind' and value == 'llm': - llm_installed = self.map_llm_to_resource(ollama_model) + ollama_models = await self.get_ollama_installed_models() + llm_installed = self.map_llm_to_resource(ollama_models) db_llm_query = query.filter(Resource.kind == "llm") result = await session.execute(db_llm_query) - db_llm = result.scalars().all() - if db_llm == []: - for llm in llm_installed: - await self.create_resource(llm) + + llm_db = [ResourceSchema.from_orm(file) for file in result.scalars().all()] + llm_db_names = {resource.name for resource in llm_db} + + # Create new resources + new_resources = [llm for llm in llm_installed if llm['name'] not in llm_db_names] + for resource in new_resources: + await self.create_resource(resource) + + # Set active to True for items already in llm_db and present in llm_installed + active_resources = [resource for resource in llm_db if resource.name in {llm['name'] for llm in llm_installed}] + for resource in active_resources: + stmt = update(Resource).where(Resource.id == resource.id).values(active='True') + await session.execute(stmt) + + # Set active to False for items in llm_db but not present in llm_installed + inactive_resources = [resource for resource in llm_db if resource.name not in {llm['name'] for llm in llm_installed}] + for resource in inactive_resources: + stmt = update(Resource).where(Resource.id == resource.id).values(active='False') + await session.execute(stmt) + query = query.filter(Resource.kind == value) elif isinstance(value, list): query = query.filter(getattr(Resource, key).in_(value)) else: query = query.filter(getattr(Resource, key) == value) - if sort_by and sort_by in ['id', 'name', 'uri','status','allow_edit','kind']: + if sort_by and sort_by in ['id', 'name', 'uri','status','allow_edit','kind','active']: order_column = getattr(Resource, sort_by) query = query.order_by(order_column.desc() if sort_order.lower() == 'desc' else order_column) @@ -193,7 +213,19 @@ def map_llm_to_resource(self, installed_models: List[Dict]) -> List[Dict[str,Any "status": None, "allow_edit": None, "kind": "llm", - "icon": None + "icon": None, + "active": "True" } resources_llm.append(resource_llm) - return resources_llm \ No newline at end of file + return resources_llm + + async def get_ollama_installed_models(self) ->List: + async with httpx.AsyncClient() as client: + response = await client.get("http://localhost:11434/api/tags") + if response.status_code == 200: + data = response.json() + models = data.get("models", []) + print(models) + return models + else: + return [] \ No newline at end of file diff --git a/backend/models.py b/backend/models.py index c2bf067..a918cb8 100644 --- a/backend/models.py +++ b/backend/models.py @@ -18,6 +18,7 @@ class Resource(Base): allow_edit = Column(String, nullable=True) kind = Column(String, nullable=False) icon= Column(String, nullable=True) + active= Column(String, nullable=True) class User(Base): __tablename__ = "user" diff --git a/backend/schemas.py b/backend/schemas.py index 7715ff2..118d080 100644 --- a/backend/schemas.py +++ b/backend/schemas.py @@ -23,6 +23,7 @@ class ResourceBaseSchema(BaseModel): allow_edit : Optional[str] = None kind : str icon : Optional[str] = None + active : Optional[str] = None class Config: orm_mode = True from_attributes = True diff --git a/migrations/versions/75aaaf2cd1a2_added_resource_table.py b/migrations/versions/75aaaf2cd1a2_added_resource_table.py index 18c4f3f..512ef24 100644 --- a/migrations/versions/75aaaf2cd1a2_added_resource_table.py +++ b/migrations/versions/75aaaf2cd1a2_added_resource_table.py @@ -32,6 +32,7 @@ def upgrade() -> None: sa.Column('allow_edit', sqlmodel.sql.sqltypes.AutoString(), nullable=True), sa.Column('kind', sqlmodel.sql.sqltypes.AutoString(), nullable=True), sa.Column('icon', sqlmodel.sql.sqltypes.AutoString(), nullable=True), + sa.Column('active', sqlmodel.sql.sqltypes.AutoString(), nullable=True), sa.PrimaryKeyConstraint('id') ) # ### end Alembic commands ###