好风凭借力,送我上青云!
什么是LangSmith
LangSmith is a platform for building production-grade LLM applications.
It lets you debug, test, evaluate, and monitor chains and intelligent agents built on any LLM framework and seamlessly integrates with LangChain, the go-to open source framework for building with LLMs.
LangSmith is developed by LangChain, the company behind the open source LangChain framework.
LangSmith 是一个用于构建生产级 LLM 应用程序的平台。
它允许您调试、测试、评估和监控基于任何 LLM 框架构建的链和智能代理,并无缝集成 LangChain(用于构建 LLM 的首选开源框架)。
LangSmith 由 LangChain 开发,LangChain 是开源 LangChain 框架背后的公司。
LangSmith的目标很宏大,但是实际上还是处于早期阶段,目前最实用的功能还是调试、跟踪LangChain应用,但是单是这一项的价值都已经无可估量,可以大大缩减你学习LangChain的时间,提高用LangChain开发LLM应用的效率。
用LangChain来完成大语言模型的应用原型/代理很简单,但是,要交付实际的大语言应用异常困难:可能要大量定制、迭代Prompt、链和其他组件。LangSmith可以帮你快速调试链、代理或者一组工具,可视化各种组件(链、llms、检索器retrievers等)如何交互及使用,评估不同的Prompts等等。
注册与设置
注册
登录 https://smith.langchain.com/ 可以直接用Discord、GitHub、Google账号登录,也可以用自己邮箱注册。现在已经不需要邀请码。
生成API Key
注意生成Key的时候就复制下来,后面丢了就只能重新生成。
设置环境变量
Linux用下面的命令设置环境变量:
export LANGCHAIN_TRACING_V2=true
export LANGCHAIN_ENDPOINT="https://api.smith.langchain.com"
export LANGCHAIN_API_KEY="<your-api-key>"
export LANGCHAIN_PROJECT="langchain_for_llm_application_development"
Windows可以用下面的命令:
setx LANGCHAIN_TRACING_V2 true
setx LANGCHAIN_ENDPOINT "https://api.smith.langchain.com"
setx LANGCHAIN_API_KEY <your-api-key>
setx LANGCHAIN_PROJECT langchain_for_llm_application_development
LANGCHAIN_TRACING_V2是设置LangChain是否开启日志跟踪模式。
LANGCHAIN_PROJECT 是要跟踪的项目名称,如果LangSmith平台上还没有这个项目,会自动创建。如果不设置这个环境变量,会把相关信息写到default项目。这里的项目不一定要跟你实际的项目一一对应,可以理解为分类或者标签。你只要在运行某个应用前改变这一项,就会把相关的日志写到这个下面。可以按开发、生产环境分,也可以按日期分等等。
LANGCHAIN_API_KEY就是上面生成的LangSmith的key。
设置好环境变量就可以了,代码无需任何变动!完全没有侵入性的感觉真好。当然,如果要较真的话,引入LangChain的时候代码就已经侵入了,但是我们本来就要用LangChain,那就不用管这个了。
使用
我们可以使用LangSmith调试:出乎意料的最终结果、代理为何一直在循环、链为何比预期慢、代理使用了多少个令牌等等。
我们来看一个RouterChain的例子(源码来自黄佳老师的课程):
'''欢迎来到LangChain实战课
https://time.geekbang.org/column/intro/100617601
作者 黄佳'''
import warnings
warnings.filterwarnings('ignore')
# 设置OpenAI API密钥
# import os
# os.environ["OPENAI_API_KEY"] = 'Your Key'
from dotenv import load_dotenv, find_dotenv
_ = load_dotenv(find_dotenv()) # read local .env file
from langchain.chat_models import AzureChatOpenAI
# 构建两个场景的模板
flower_care_template = """
你是一个经验丰富的园丁,擅长解答关于养花育花的问题。
下面是需要你来回答的问题:
{input}
"""
flower_deco_template = """
你是一位网红插花大师,擅长解答关于鲜花装饰的问题。
下面是需要你来回答的问题:
{input}
"""
# 构建提示信息
prompt_infos = [
{
"key": "flower_care",
"description": "适合回答关于鲜花护理的问题",
"template": flower_care_template,
},
{
"key": "flower_decoration",
"description": "适合回答关于鲜花装饰的问题",
"template": flower_deco_template,
}
]
# 初始化语言模型
# from langchain.llms import OpenAI
# llm = OpenAI()
llm = AzureChatOpenAI(deployment_name="GPT-4", temperature=0)
# 构建目标链
from langchain.chains.llm import LLMChain
from langchain.prompts import PromptTemplate
chain_map = {}
for info in prompt_infos:
prompt = PromptTemplate(
template=info['template'],
input_variables=["input"]
)
print("目标提示:\n", prompt)
chain = LLMChain(
llm=llm,
prompt=prompt,
verbose=True
)
chain_map[info["key"]] = chain
# 构建路由链
from langchain.chains.router.llm_router import LLMRouterChain, RouterOutputParser
from langchain.chains.router.multi_prompt_prompt import MULTI_PROMPT_ROUTER_TEMPLATE as RounterTemplate
destinations = [f"{p['key']}: {p['description']}" for p in prompt_infos]
router_template = RounterTemplate.format(destinations="\n".join(destinations))
print("路由模板:\n", router_template)
router_prompt = PromptTemplate(
template=router_template,
input_variables=["input"],
output_parser=RouterOutputParser(),
)
print("路由提示:\n", router_prompt)
router_chain = LLMRouterChain.from_llm(
llm,
router_prompt,
verbose=True
)
# 构建默认链
from langchain.chains import ConversationChain
default_chain = ConversationChain(
llm=llm,
output_key="text",
verbose=True
)
# 构建多提示链
from langchain.chains.router import MultiPromptChain
chain = MultiPromptChain(
router_chain=router_chain,
destination_chains=chain_map,
default_chain=default_chain,
verbose=True
)
# 测试1
print(chain.run("如何为玫瑰浇水?"))
虽然黄佳老师加了很多print输出信息,但是代码的逻辑还是不容易看清楚。
查看运行情况
运行一次上面的程序,然后打开LangSmith,找到最近一次的运行:
从图中,我们可以很直观的看到LangChain组件的调用顺序(如果有用过微服务的Zipkin,对这个界面应该不陌生)、每一步耗费的时间、调用OpenAI消耗的Token数。
使用Playground
面向LLM编程,很多时候就是要迭代Prompt。在LangSmith里除了可以直接看到输入给LLM的Prompt和输出结果,更方便的是里面还集成了Playground,可以直接修改Prompt来看输出的结果。
点击上图右上角的Playground,进去后你会发现你调用LLM的各种参数、Prompt都帮你设置好了(OpenAI的Key还要设置,只保存在本地浏览器)。
这样,你就可以修改你的Prompt,重新运行,观察Prompt改变引起的结果变化。
在Playground里执行的过程会记录到“playground”这个项目。
添加到数据集
在查看运行情况的界面,点击右上角的“Add to Dataset”,可以把对应的输入、输出添加到数据集,后面大模型或者Prompt有了调整,可以用数据集来测试、评估。
Hub
LangSmith里面还有一个有趣的功能是Hub。在Hub里,可以发现、分享和对Prompt进行版本控制。Hub感觉是借用GitHub的概念,也可以叫PromptHub?
对别人分享出来的Prompt,你可以点爱心收藏(收藏了之后没找到相应的入口 😅),也可以Fork、试运行。
总的来说,LangSmith还处于快速开发的阶段(LangChain本身也才0.0.348版),某些功能还比较简陋。从另一方面来说,我们可以和它一起成长,更快速掌握LangChain,打造自己的LLM应用。
参考
- LangSmith文档:https://docs.smith.langchain.com/