"""知识图谱数据模型""" import uuid from datetime import datetime import enum from sqlalchemy import String, Text, DateTime, ForeignKey, Index, Enum, func from sqlalchemy.dialects.postgresql import UUID from sqlalchemy.orm import Mapped, mapped_column, relationship from app.database import Base, JSONType class EntityType(str, enum.Enum): """实体类型""" ORGANIZATION = "ORGANIZATION" # 组织/公司 PRODUCT = "PRODUCT" # 产品 PERSON = "PERSON" # 人物 LOCATION = "LOCATION" # 地点 TECHNOLOGY = "TECHNOLOGY" # 技术 BRAND = "BRAND" # 品牌 EVENT = "EVENT" # 事件 CONCEPT = "CONCEPT" # 概念 OTHER = "OTHER" # 其他 class RelationType(str, enum.Enum): """关系类型""" # 组织关系 COMPETES_WITH = "COMPETES_WITH" # 竞争对手 PARTNERS_WITH = "PARTNERS_WITH" # 合作伙伴 ACQUIRES = "ACQUIRES" # 收购 SUBSIDIARY_OF = "SUBSIDIARY_OF" # 子公司 # 产品关系 PRODUCES = "PRODUCES" # 生产 USES_TECHNOLOGY = "USES_TECHNOLOGY" # 使用技术 PART_OF = "PART_OF" # 属于(产品线) # 地点关系 LOCATED_IN = "LOCATED_IN" # 位于 FOUNDED_IN = "FOUNDED_IN" # 成立于 # 人物关系 CEO_OF = "CEO_OF" # CEO FOUNDER_OF = "FOUNDER_OF" # 创始人 # 通用关系 RELATED_TO = "RELATED_TO" # 相关 MENTIONED_IN = "MENTIONED_IN" # 提及于 ALSO_KNOWN_AS = "ALSO_KNOWN_AS" # 又名 class KnowledgeEntity(Base): """知识实体""" __tablename__ = "knowledge_entities" id: Mapped[uuid.UUID] = mapped_column( UUID(as_uuid=True), primary_key=True, default=uuid.uuid4, ) knowledge_base_id: Mapped[uuid.UUID] = mapped_column( UUID(as_uuid=True), ForeignKey("knowledge_bases.id", ondelete="CASCADE"), nullable=False, ) # 实体信息 name: Mapped[str] = mapped_column(String(500), nullable=False, index=True) entity_type: Mapped[EntityType] = mapped_column(Enum(EntityType), nullable=False, index=True) description: Mapped[str | None] = mapped_column(Text, nullable=True) # 扩展属性(JSON) properties: Mapped[dict | None] = mapped_column(JSONType, default=dict) # 来源信息 source_chunk_id: Mapped[uuid.UUID | None] = mapped_column( UUID(as_uuid=True), ForeignKey("knowledge_chunks.id", ondelete="SET NULL"), nullable=True, ) confidence: Mapped[str | None] = mapped_column(String(20), nullable=True) # 置信度描述:high/medium/low # 元数据 created_at: Mapped[datetime] = mapped_column( server_default=func.now(), nullable=False, ) updated_at: Mapped[datetime] = mapped_column( server_default=func.now(), onupdate=func.now(), nullable=False, ) # 索引 __table_args__ = ( Index("ix_entities_kb_name", "knowledge_base_id", "name"), Index("ix_entities_kb_type", "knowledge_base_id", "entity_type"), ) # 关系 outgoing_relations: Mapped[list["KnowledgeRelation"]] = relationship( "KnowledgeRelation", foreign_keys="KnowledgeRelation.source_entity_id", back_populates="source_entity", cascade="all, delete-orphan", ) incoming_relations: Mapped[list["KnowledgeRelation"]] = relationship( "KnowledgeRelation", foreign_keys="KnowledgeRelation.target_entity_id", back_populates="target_entity", cascade="all, delete-orphan", ) class KnowledgeRelation(Base): """知识关系""" __tablename__ = "knowledge_relations" id: Mapped[uuid.UUID] = mapped_column( UUID(as_uuid=True), primary_key=True, default=uuid.uuid4, ) # 关系两端 source_entity_id: Mapped[uuid.UUID] = mapped_column( UUID(as_uuid=True), ForeignKey("knowledge_entities.id", ondelete="CASCADE"), nullable=False, ) target_entity_id: Mapped[uuid.UUID] = mapped_column( UUID(as_uuid=True), ForeignKey("knowledge_entities.id", ondelete="CASCADE"), nullable=False, ) # 关系信息 relation_type: Mapped[RelationType] = mapped_column(Enum(RelationType), nullable=False, index=True) # 扩展属性 properties: Mapped[dict | None] = mapped_column(JSONType, default=dict) # 来源信息 source_chunk_id: Mapped[uuid.UUID | None] = mapped_column( UUID(as_uuid=True), ForeignKey("knowledge_chunks.id", ondelete="SET NULL"), nullable=True, ) confidence: Mapped[str | None] = mapped_column(String(20), nullable=True) # 元数据 created_at: Mapped[datetime] = mapped_column( server_default=func.now(), nullable=False, ) # 关系 source_entity: Mapped["KnowledgeEntity"] = relationship( "KnowledgeEntity", foreign_keys=[source_entity_id], back_populates="outgoing_relations", ) target_entity: Mapped["KnowledgeEntity"] = relationship( "KnowledgeEntity", foreign_keys=[target_entity_id], back_populates="incoming_relations", ) # 索引 __table_args__ = ( Index("ix_relations_source", "source_entity_id"), Index("ix_relations_target", "target_entity_id"), Index("ix_relations_type", "relation_type"), )