"""Pydantic schemas for the cf-harvest knowledge ingest contract.""" from __future__ import annotations from typing import Any, Literal, Optional from pydantic import BaseModel, field_validator FactType = Literal[ "companion_planting", "soil_amendment", "propagation", "pest_diagnosis", "harvest_timing", "instruction", "medicinal", "history_context", ] class KnowledgeSourceSpec(BaseModel): video_path: str presenter: Optional[str] = None location: Optional[str] = None source_domain: Optional[str] = "gardening" class SegmentKnowledge(BaseModel): """One extracted fact from cf-harvest.""" fact_type: FactType confidence: float = 1.0 payload: dict[str, Any] @field_validator("confidence") @classmethod def clamp_confidence(cls, v: float) -> float: return max(0.0, min(1.0, v)) class KnowledgeIngestRequest(BaseModel): source: KnowledgeSourceSpec facts: list[SegmentKnowledge] class RejectedFact(BaseModel): index: int reason: str class IngestResponse(BaseModel): source_id: int video_path: str facts_received: int facts_inserted: int facts_skipped_duplicate: int rejected: list[RejectedFact] = [] class KnowledgeFactOut(BaseModel): id: int source_id: int fact_type: str subject: Optional[str] payload: dict[str, Any] presenter: Optional[str] confidence: Optional[float] fact_hash: str created_at: str video_path: Optional[str] = None location: Optional[str] = None