{"record":{"id":"b53a7d590ffd2c11","repo":"datawhalechina/hello-agents","slug":"llm-str-e-b53a7d","errorCode":null,"errorMessage":"LLM调用失败: {str(e)}","messagePattern":"LLM调用失败: (.+?)","errorType":"exception","errorClass":"HelloAgentsException","httpStatus":null,"severity":"error","filePath":"Co-creation-projects/lcyting-StockSage-agent/HelloAgents Optimized/hello_agents/core/llm.py","lineNumber":385,"sourceCode":"                temperature=temperature\n                if temperature is not None\n                else self.temperature,\n                max_tokens=self.max_tokens,\n                stream=True,\n            )\n\n            # 处理流式响应\n            print(\"✅ 大语言模型响应成功:\")\n            for chunk in response:\n                content = chunk.choices[0].delta.content or \"\"\n                if content:\n                    print(content, end=\"\", flush=True)\n                    yield content\n            print()  # 在流式输出结束后换行\n\n        except Exception as e:\n            print(f\"❌ 调用LLM API时发生错误: {e}\")\n            raise HelloAgentsException(f\"LLM调用失败: {str(e)}\")\n\n    def invoke(self, messages: list[dict[str, str]], **kwargs) -> str:\n        \"\"\"\n        非流式调用LLM，返回完整响应。\n        适用于不需要流式输出的场景。\n        \"\"\"\n        try:\n            response = self._client.chat.completions.create(\n                model=self.model,\n                messages=messages,\n                temperature=kwargs.get(\"temperature\", self.temperature),\n                max_tokens=kwargs.get(\"max_tokens\", self.max_tokens),\n                **{\n                    k: v\n                    for k, v in kwargs.items()\n                    if k not in [\"temperature\", \"max_tokens\"]\n                },\n            )","sourceCodeStart":367,"sourceCodeEnd":403,"githubUrl":"https://github.com/datawhalechina/hello-agents/blob/606a07d341a47be773fab7f4b71177f53f96b2c3/Co-creation-projects/lcyting-StockSage-agent/HelloAgents Optimized/hello_agents/core/llm.py#L367-L403","documentation":"The streaming path (think) wraps any exception raised during a chat.completions streaming call into HelloAgentsException(\"LLM call failed: ...\"), after printing an error line. Typical underlying causes are auth failures, rate limits, model-not-found, timeouts, and network errors from the OpenAI-compatible client; the original message is preserved in str(e).","triggerScenarios":"Calling think()/stream_invoke() with an invalid model name, expired API key, rate-limited account, unreachable base_url, or a mid-stream disconnect; note the generator only raises when iterated.","commonSituations":"Long streaming sessions hitting provider timeouts; wrong base_url for the provider; quota exhaustion; proxies/firewalls cutting SSE streams.","solutions":["Read the embedded original error in the message — it names the real cause (401 vs 429 vs timeout).","For 401/403: fix the API key; for 429: back off and retry; for model errors: correct LLM_MODEL_ID.","Verify base_url is reachable and OpenAI-compatible (curl a minimal completion).","Increase the client timeout for long generations, and consume the generator inside try/except since streaming errors surface lazily."],"exampleFix":"# before\nfor chunk in llm.think(messages):  # raises mid-iteration on provider error\n    print(chunk)\n\n# after\ntry:\n    for chunk in llm.think(messages):\n        print(chunk)\nexcept HelloAgentsException as e:\n    logger.error(\"stream failed: %s\", e)  # str(e) contains provider detail\n    raise","handlingStrategy":"retry","validationCode":"from dotenv import load_dotenv\nload_dotenv()\nassert os.getenv(\"LLM_API_KEY\"), \"LLM_API_KEY missing before streaming\"\nassert llm._client is not None  # client constructed successfully","typeGuard":null,"tryCatchPattern":"try:\n    for chunk in llm.think(messages):\n        handle(chunk)\nexcept HelloAgentsException as e:\n    msg = str(e)\n    if \"429\" in msg or \"timeout\" in msg.lower():\n        time.sleep(2); continue_outer_retry  # backoff and retry stream\n    raise  # auth/model errors are not retryable","preventionTips":["Wrap stream consumption in try/except — generator errors surface lazily mid-iteration.","Distinguish retryable (429/timeout/network) from fatal (401/model) causes in the wrapped message.","Set generous timeouts for long streamed generations."],"tags":["llm-client","streaming","error-wrapping","python"],"backgroundTag":null,"analyzedSha":"606a07d341a47be773fab7f4b71177f53f96b2c3","analyzedAt":"2026-08-14T22:57:27.446Z","schemaVersion":2},"datasetVersion":"2026-08-15T17:31:12.345Z"}