"""Pydantic schemas for the Knowledge Base feature.""" from pydantic import BaseModel from typing import Optional, List from datetime import datetime # -------------------------------------------------------------------------- # Knowledge Base # -------------------------------------------------------------------------- class KnowledgeBaseBase(BaseModel): title: str description: Optional[str] = None class KnowledgeBaseCreate(KnowledgeBaseBase): pass class KnowledgeBaseUpdate(BaseModel): title: Optional[str] = None description: Optional[str] = None class KnowledgeBaseResponse(BaseModel): id: int knowledge_base_code: Optional[str] = None title: str description: Optional[str] = None created_by: int created_at: Optional[datetime] = None last_updated_at: Optional[datetime] = None class Config: from_attributes = True # -------------------------------------------------------------------------- # Topic # -------------------------------------------------------------------------- class KnowledgeTopicBase(BaseModel): topic: str description: Optional[str] = None class KnowledgeTopicCreate(KnowledgeTopicBase): pass class KnowledgeTopicUpdate(BaseModel): topic: Optional[str] = None description: Optional[str] = None class KnowledgeTopicResponse(BaseModel): id: int topic: str knowledge_base_id: int description: Optional[str] = None created_by: int created_at: Optional[datetime] = None last_updated_at: Optional[datetime] = None class Config: from_attributes = True # -------------------------------------------------------------------------- # Category # -------------------------------------------------------------------------- class KnowledgeCategoryBase(BaseModel): name: str description: Optional[str] = None class KnowledgeCategoryCreate(KnowledgeCategoryBase): topic_id: int parent: Optional[int] = None class KnowledgeCategoryUpdate(BaseModel): name: Optional[str] = None description: Optional[str] = None parent: Optional[int] = None class KnowledgeCategoryResponse(BaseModel): id: int name: str parent: Optional[int] = None topic_id: int description: Optional[str] = None created_by: Optional[int] = None last_updated_by: Optional[int] = None class Config: from_attributes = True # -------------------------------------------------------------------------- # Fact # -------------------------------------------------------------------------- class KnowledgeFactBase(BaseModel): fact: str class KnowledgeFactCreate(KnowledgeFactBase): topic_id: int category_id: Optional[int] = None class KnowledgeFactUpdate(BaseModel): fact: Optional[str] = None category_id: Optional[int] = None class KnowledgeFactResponse(BaseModel): id: int category_id: Optional[int] = None topic_id: int fact: str last_updated_at: Optional[datetime] = None class Config: from_attributes = True # -------------------------------------------------------------------------- # Project <-> KnowledgeBase link # -------------------------------------------------------------------------- class ProjectKnowledgeBaseLink(BaseModel): # Accept either a numeric id or a knowledge_base_code (mirrors how # projects are referenced elsewhere). knowledge_base: str # -------------------------------------------------------------------------- # Nested tree (read-only aggregate) # -------------------------------------------------------------------------- class CategoryTreeNode(BaseModel): id: int name: str parent: Optional[int] = None topic_id: int description: Optional[str] = None categories: List["CategoryTreeNode"] = [] facts: List[KnowledgeFactResponse] = [] class TopicTreeNode(BaseModel): id: int topic: str knowledge_base_id: int description: Optional[str] = None categories: List[CategoryTreeNode] = [] facts: List[KnowledgeFactResponse] = [] class KnowledgeBaseTree(BaseModel): id: int knowledge_base_code: Optional[str] = None title: str description: Optional[str] = None topics: List[TopicTreeNode] = [] CategoryTreeNode.model_rebuild()