domain.py 2.5 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788
  1. """Framework-free domain values for planning search queries."""
  2. from __future__ import annotations
  3. from dataclasses import dataclass, field
  4. from enum import StrEnum
  5. from typing import Any
  6. class GeneratorKind(StrEnum):
  7. CARTESIAN = "cartesian"
  8. MANUAL = "manual"
  9. TOPIC_TABLE = "topic_table"
  10. AGENT_PLAN = "agent_plan"
  11. HISTORY_GAP = "history_gap"
  12. @dataclass(frozen=True)
  13. class GenerationRequest:
  14. generator_kind: GeneratorKind
  15. payload: dict[str, Any]
  16. name: str
  17. target_platforms: tuple[str, ...] = ("xiaohongshu", "weixin", "douyin")
  18. max_queries: int | None = None
  19. metadata: dict[str, Any] = field(default_factory=dict)
  20. def __post_init__(self) -> None:
  21. if not self.name.strip():
  22. raise ValueError("generation request name must not be empty")
  23. if not self.target_platforms:
  24. raise ValueError("at least one target platform is required")
  25. if self.max_queries is not None and self.max_queries < 0:
  26. raise ValueError("max_queries must be non-negative or None")
  27. @dataclass(frozen=True)
  28. class KnowledgeNeedDraft:
  29. need_key: str
  30. decision_context: str
  31. unknown_information: str
  32. source_ref: dict[str, Any] = field(default_factory=dict)
  33. priority: int = 0
  34. metadata: dict[str, Any] = field(default_factory=dict)
  35. @dataclass
  36. class QueryCandidate:
  37. query_text: str
  38. axes: dict[str, Any] = field(default_factory=dict)
  39. priority: int = 0
  40. original_position: int = 0
  41. source_refs: list[dict[str, Any]] = field(default_factory=list)
  42. knowledge_need_keys: list[str] = field(default_factory=list)
  43. metadata: dict[str, Any] = field(default_factory=dict)
  44. filter_reason: str | None = None
  45. dedupe_key: str = ""
  46. @dataclass(frozen=True)
  47. class GeneratorOutput:
  48. candidates: tuple[QueryCandidate, ...]
  49. knowledge_needs: tuple[KnowledgeNeedDraft, ...] = ()
  50. generator_config: dict[str, Any] = field(default_factory=dict)
  51. @dataclass(frozen=True)
  52. class GenerationPlanDraft:
  53. generator_kind: GeneratorKind
  54. input_snapshot: dict[str, Any]
  55. generator_config: dict[str, Any]
  56. metadata: dict[str, Any]
  57. @dataclass(frozen=True)
  58. class GenerationStats:
  59. generated_count: int
  60. normalized_count: int
  61. unique_count: int
  62. selected_count: int
  63. dropped_count: int
  64. @dataclass(frozen=True)
  65. class GenerationResult:
  66. request: GenerationRequest
  67. plan: GenerationPlanDraft
  68. knowledge_needs: tuple[KnowledgeNeedDraft, ...]
  69. selected_queries: tuple[QueryCandidate, ...]
  70. stats: GenerationStats