{"record":{"id":"be1cc6a94c8648d2","repo":"ZhuLinsen/daily_stock_analysis","slug":"invalid-analysis-phase-requested-must-be-one-o","errorCode":null,"errorMessage":"invalid analysis_phase: {requested}. Must be one of {sorted(_SUPPORTED_ANALYSIS_PHASES)}","messagePattern":"invalid analysis_phase: (.+?)\\. Must be one of (.+?)","errorType":"validation","errorClass":"ValueError","httpStatus":null,"severity":"error","filePath":"src/core/trading_calendar.py","lineNumber":508,"sourceCode":"\n    return None, None, False\n\n\ndef _normalize_analysis_phase(\n    analysis_phase: Optional[str],\n    analysis_intent: Optional[str],\n) -> str:\n    def _coerce(value: Optional[str]) -> str:\n        if isinstance(value, MarketPhase):\n            return value.value\n        return str(value or \"\").strip().lower()\n\n    requested = _coerce(analysis_phase) or \"auto\"\n    legacy_intent = _coerce(analysis_intent)\n    if requested == \"auto\" and legacy_intent and legacy_intent != \"auto\":\n        requested = legacy_intent\n    if requested not in _SUPPORTED_ANALYSIS_PHASES:\n        raise ValueError(\n            f\"invalid analysis_phase: {requested}. \"\n            f\"Must be one of {sorted(_SUPPORTED_ANALYSIS_PHASES)}\"\n        )\n    return requested\n\n\ndef build_market_phase_context(\n    *,\n    market: Optional[str],\n    current_time: Optional[datetime] = None,\n    trigger_source: str = \"system\",\n    analysis_intent: str = \"auto\",\n    analysis_phase: str = \"auto\",\n) -> MarketPhaseContext:\n    \"\"\"\n    Build a JSON-safe runtime market-phase context for analysis plumbing.\n\n    ``analysis_phase=\"auto\"`` keeps calendar inference. Explicit supported","sourceCodeStart":490,"sourceCodeEnd":526,"githubUrl":"https://github.com/ZhuLinsen/daily_stock_analysis/blob/5159bd72e8373d215492dff122acc9d389e219c9/src/core/trading_calendar.py#L490-L526","documentation":"Trading-calendar phase resolver (_coerce/normalize step in src/core/trading_calendar.py): analysis_phase is normalized (MarketPhase enum value, else str().strip().lower(), defaulting 'auto'; legacy analysis_intent is honored when phase is 'auto') and must be one of _SUPPORTED_ANALYSIS_PHASES = {auto, premarket, intraday, postmarket}. Any other string is rejected with the allowed list embedded, because downstream market-phase context building branches on exactly these phases.","triggerScenarios":"Calling build_market_phase_context (or the resolver it fronts) with analysis_phase like 'pre-market', 'PRE', 'overnight', 'close', or a typo; also triggered by legacy analysis_intent values that are not phase names when phase is auto. MarketPhase enum instances pass via .value.","commonSituations":"Env/CLI passing a human label instead of the canonical token; new phase names added by callers before the engine supports them; mixing up analysis_intent vocabulary (e.g. 'daily') with phase vocabulary.","solutions":["Use one of the supported tokens exactly: auto, premarket, intraday, postmarket (lowercase after normalization; the error lists them sorted).","If you intended the legacy intent axis, pass analysis_intent only when phase is 'auto', and use phase-supported vocabulary.","Map custom labels to canonical phases at your call site before invoking the calendar API."],"exampleFix":"# before\nbuild_market_phase_context(market=\"US\", analysis_phase=\"pre-market\")\n\n# after\nbuild_market_phase_context(market=\"US\", analysis_phase=\"premarket\")","handlingStrategy":"type-guard","validationCode":"from src.core.trading_calendar import _SUPPORTED_ANALYSIS_PHASES\n\nphase = (analysis_phase or \"auto\").strip().lower()\nassert phase in _SUPPORTED_ANALYSIS_PHASES, f\"bad phase: {phase}\"","typeGuard":"SUPPORTED = {\"auto\", \"premarket\", \"intraday\", \"postmarket\"}\n\ndef is_analysis_phase(value: str) -> bool:\n    return value.strip().lower() in SUPPORTED","tryCatchPattern":"try:\n    ctx = build_market_phase_context(market=\"US\", analysis_phase=phase)\nexcept ValueError as exc:\n    logger.error(\"bad analysis_phase: %s\", exc)\n    phase = \"auto\"\n    ctx = build_market_phase_context(market=\"US\", analysis_phase=phase)","preventionTips":["Use only the four canonical phase tokens","Normalize (strip+lower) user input before passing","Keep legacy analysis_intent vocabulary separate from phase vocabulary"],"tags":["trading-calendar","validation","enum"],"backgroundTag":null,"analyzedSha":"5159bd72e8373d215492dff122acc9d389e219c9","analyzedAt":"2026-08-15T01:59:36.292Z","schemaVersion":2},"datasetVersion":"2026-08-15T22:17:37.221Z"}