LangChain 学习笔记(一):重构项目结构与百炼大模型深度思考模式接入指南
一、项目结构重构
在接入大模型之前,合理的项目结构是保证代码可维护性的基础。我们将原本杂乱的扁平结构,重构为了功能分明的模块化结构。
1.1 重构前后对比
重构前(扁平结构,容易越写越乱):
1 | |
重构后(模块化结构,适合工程化):
1 | |
1.2 重构收益与要点
- 依赖隔离:完善
requirements.txt,保证项目换电脑也能一键跑通。 - 信息安全:添加
.gitignore并忽略.env,彻底杜绝了 API Key 泄露到 GitHub 的风险。 - 代码复用:将零散的测试脚本封装为了规范的函数调用,统一了全局配置入口。
二、LangChain 调用百炼平台 API
阿里云百炼平台提供了极好的 OpenAI 兼容接口。这意味着我们在 LangChain 中,不需要去找特定的阿里云集成包,直接借用 langchain_openai.ChatOpenAI 即可完美调用。
2.1 环境变量配置(统一规范)
建议统一使用阿里云百炼官方文档推荐的命名:
1 | |
2.2 基础模型实例化
1 | |
2.3 🚨 踩坑预警:千万别用 ChatDeepSeek 调百炼的 DeepSeek
如果你想调用百炼平台上托管的 deepseek-r1 等模型,千万不要这样做:
1 | |
💡 根本原因: ChatDeepSeek 是 LangChain 专门为 DeepSeek 官方 API 设计的类,其底层网络请求认证机制和请求头与阿里云平台并不完全兼容。
正解: 只要是调用阿里云百炼(无论什么模型),一律使用通用且协议最标准的 ChatOpenAI 并修改 base_url 即可。
三、深度思考模式的正确打开方式(核心重点)
当前具备“深度思考(CoT)”能力的大模型越来越火,在百炼平台中,部分模型可以通过参数手动开启思考模式。
3.1 如何开启深度思考?
通过 extra_body 将专属参数传递给底层 API:
1 | |
3.2 为什么必须用流式(Stream)输出?
这是一个硬性限制! 对于开启了 enable_thinking=True 的模型:
- ❌ 调用
invoke():非流式调用不仅会丢失思考过程,在百炼的某些 API 版本中甚至会直接报错(提示你必须关闭 thinking 或者改用流式)。 - ✅ 调用
stream():流式调用可以实时且完整地拿到reasoning_content(思考链)。
3.3 实战:流式获取思考与回复的完整代码
在 LangChain 中获取非标准的响应字段,必须利用 additional_kwargs:
1 | |
3.4 Token 消耗的隐藏细节(💳 计费预警)
仔细观察返回的响应元数据(Response Metadata),你会发现计费维度的变化:
- 普通对话:
completion_tokens(补全输出量) - 深度思考对话:新增了
reasoning_tokens。注意:大模型“自言自语”的思考过程通常会非常长(动辄上千 Token),这部分是被归入输出计费的!在设计 C 端商业产品时,一定要考虑这部分产生的额外算力成本。
四、原始 API 调用对比(知其然,知其所以然)
为了搞明白 LangChain 底层干了什么,我们可以对比一下使用纯粹的 openai SDK 是怎么调用的:
1 | |
底层逻辑映射总结:
- 原始 SDK 中的
delta.reasoning_content👉 等价于 LangChain 封装后的chunk.additional_kwargs.get("reasoning_content")。LangChain 帮我们抹平了不同底层的差异,但遇到新特性时,多翻翻additional_kwargs准没错!
五、最佳实践复盘
- 项目隔离与解耦:坚持配置与业务逻辑分离,通过
.env管理敏感凭证,这是工程师的基本素养。 - “万能插座”法则:面对提供了“OpenAI兼容接口”的国产大模型平台,
ChatOpenAI就是最好的“万能插座”,别乱用专用 SDK 惹出一堆兼容性报错。 - 理解大模型流式思考:未来的大模型(如 O1、DeepSeek R1)必将标配思考过程。遇到思考过程拿不到的问题:一上 Stream,二查 additional_kwargs。
六、延伸阅读与参考资料
LangChain 学习笔记(一):重构项目结构与百炼大模型深度思考模式接入指南
https://yangfanbin.cn/代码笔记/LangChain 学习笔记(一):重构项目结构与百炼大模型深度思考模式接入指南/