62 lines
2.2 KiB
Python
62 lines
2.2 KiB
Python
"""Sector and theme research agent."""
|
|
|
|
from __future__ import annotations
|
|
|
|
from typing import Any
|
|
|
|
from app.research.industry_chain_agent import (
|
|
load_theme_chain_library,
|
|
map_sector_to_chain,
|
|
map_sector_to_chain_from_library,
|
|
)
|
|
|
|
|
|
def build_theme_views(sectors: list[Any]) -> list[dict]:
|
|
return _build_theme_views_with_mapper(sectors, map_sector_to_chain)
|
|
|
|
|
|
async def build_theme_views_async(sectors: list[Any]) -> list[dict]:
|
|
library = await load_theme_chain_library()
|
|
|
|
def mapper(sector_name: str, leading_stocks: list[dict[str, Any]] | None = None) -> dict[str, Any]:
|
|
return map_sector_to_chain_from_library(sector_name, leading_stocks, library)
|
|
|
|
return _build_theme_views_with_mapper(sectors, mapper)
|
|
|
|
|
|
def _build_theme_views_with_mapper(sectors: list[Any], mapper) -> list[dict]:
|
|
views: list[dict] = []
|
|
for sector in sectors[:10]:
|
|
pct = getattr(sector, "realtime_pct_change", None)
|
|
if pct is None:
|
|
pct = getattr(sector, "pct_change", 0) or 0
|
|
leading = getattr(sector, "leading_stocks_realtime", None) or getattr(sector, "leading_stocks", None) or []
|
|
chain = mapper(getattr(sector, "sector_name", ""), leading)
|
|
stage = getattr(sector, "stage", "") or chain.get("stage") or "mid"
|
|
heat = float(getattr(sector, "heat_score", 0) or 0)
|
|
theme = chain["theme"]
|
|
logic = chain["logic"]
|
|
views.append({
|
|
"theme": theme,
|
|
"raw_sector": getattr(sector, "sector_name", ""),
|
|
"stage": stage,
|
|
"heat_score": round(heat, 1),
|
|
"pct_change": round(float(pct or 0), 2),
|
|
"limit_up_count": int(getattr(sector, "limit_up_count", 0) or 0),
|
|
"logic": logic,
|
|
"chain_nodes": chain["chain_nodes"],
|
|
"chain_items": chain.get("chain_items", []),
|
|
"leader_stocks": leading[:5],
|
|
"lifecycle_status": chain.get("lifecycle_status") or _lifecycle_label(stage),
|
|
})
|
|
return views
|
|
|
|
|
|
def _lifecycle_label(stage: str) -> str:
|
|
return {
|
|
"early": "启动期",
|
|
"mid": "扩散期",
|
|
"late": "后段",
|
|
"end": "退潮",
|
|
}.get(stage, "观察期")
|