您的位置:首页 > 教育 > 锐评 > 网上购物平台怎么建立_ai绘图网页版免费_网站交易_济南seo外包服务

网上购物平台怎么建立_ai绘图网页版免费_网站交易_济南seo外包服务

2024/10/7 4:33:08 来源:https://blog.csdn.net/fenglingguitar/article/details/142531831  浏览:    关键词:网上购物平台怎么建立_ai绘图网页版免费_网站交易_济南seo外包服务
网上购物平台怎么建立_ai绘图网页版免费_网站交易_济南seo外包服务

前提条件

本文假定你已经熟悉以下概念:

  • Chaining runnables(可运行的链)
  • Chat models(聊天模型)
  • Tools(工具)
  • Agents(代理)

在本教程中,我们将使用Python来创建一个可以对SQL数据库中的表格数据进行自然语言问答的系统。我们将通过链(Chain)和代理(Agent)来实现这个系统。

数据库设置

首先,我们需要设置一个SQLite数据库来存储数据,并创建表和插入一些初始数据。

from langchain_community.utilities import SQLDatabasedb = SQLDatabase.from_uri("sqlite:///Chinook.db")# 执行建表语句
create_table_sql = '''
CREATE TABLE Employee (EmployeeId INTEGER NOT NULL,LastName NVARCHAR(20) NOT NULL,FirstName NVARCHAR(20) NOT NULL,Title NVARCHAR(30),ReportsTo INTEGER,BirthDate DATETIME,HireDate DATETIME,Address NVARCHAR(70),City NVARCHAR(40),State NVARCHAR(40),Country NVARCHAR(40),PostalCode NVARCHAR(10),Phone NVARCHAR(24),Fax NVARCHAR(24),Email NVARCHAR(60),CONSTRAINT PK_Employee PRIMARY KEY (EmployeeId),FOREIGN KEY (ReportsTo) REFERENCES Employee (EmployeeId) ON DELETE NO ACTION ON UPDATE NO ACTION
);
'''db.run(create_table_sql)# 插入初始化数据
insert_data_sql = '''
INSERT INTO [Employee] ([EmployeeId], [LastName], [FirstName], [Title], [ReportsTo], [BirthDate], [HireDate], [Address], [City], [State], [Country], [PostalCode], [Phone], [Fax], [Email]) VALUES(1, 'Adams', 'Andrew', 'General Manager', NULL, '1962-02-18', '2002-08-14', '11120 Jasper Ave NW', 'Edmonton', 'AB', 'Canada', 'T5K 2N1', '+1 (780) 428-9482', '+1 (780) 428-3457', 'andrew@chinookcorp.com'),(2, 'Edwards', 'Nancy', 'Sales Manager', 1, '1958-12-08', '2002-05-01', '825 8 Ave SW', 'Calgary', 'AB', 'Canada', 'T2P 2T3', '+1 (403) 262-3443', '+1 (403) 262-3322', 'nancy@chinookcorp.com'),(3, 'Peacock', 'Jane', 'Sales Support Agent', 2, '1973-08-29', '2002-04-01', '1111 6 Ave SW', 'Calgary', 'AB', 'Canada', 'T2P 5M5', '+1 (403) 262-3443', '+1 (403) 262-6712', 'jane@chinookcorp.com'),(4, 'Park', 'Margaret', 'Sales Support Agent', 2, '1947-09-19', '2003-05-03', '683 10 Street SW', 'Calgary', 'AB', 'Canada', 'T2P 5G3', '+1 (403) 263-4423', '+1 (403) 263-4289', 'margaret@chinookcorp.com'),(5, 'Johnson', 'Steve', 'Sales Support Agent', 2, '1965-03-03', '2003-10-17', '7727B 41 Ave', 'Calgary', 'AB', 'Canada', 'T3B 1Y7', '1 (780) 836-9987', '1 (780) 836-9543', 'steve@chinookcorp.com'),(6, 'Mitchell', 'Michael', 'IT Manager', 1, '1973-07-01', '2003-10-17', '5827 Bowness Road NW', 'Calgary', 'AB', 'Canada', 'T3B 0C5', '+1 (403) 246-9887', '+1 (403) 246-9899', 'michael@chinookcorp.com'),(7, 'King', 'Robert', 'IT Staff', 6, '1970-05-29', '2004-01-02', '590 Columbia Boulevard West', 'Lethbridge', 'AB', 'Canada', 'T1K 5N8', '+1 (403) 456-9986', '+1 (403) 456-8485', 'robert@chinookcorp.com'),(8, 'Callahan', 'Laura', 'IT Staff', 6, '1968-01-09', '2004-03-04', '923 7 ST NW', 'Lethbridge', 'AB', 'Canada', 'T1H 1Y8', '+1 (403) 467-3351', '+1 (403) 467-8772', 'laura@chinookcorp.com');
'''db.run(insert_data_sql)

通过上面的代码,我们创建了Employee表并插入了一些初始员工数据。通过下面代码测试:

from langchain_community.utilities import SQLDatabasedb = SQLDatabase.from_uri("sqlite:///Chinook.db")
print(db.dialect)
print(db.get_usable_table_names())
db.run("SELECT * FROM Artist LIMIT 10;")

使用链来实现

链支持那些步骤明确且可预测的应用场景。在这个场景下,我们可以创建一个简单的链,来执行以下操作:

  1. 将问题转换为SQL查询:我们可以利用LangChain的create_sql_query_chain方法将用户问题转换为SQL查询。
  2. 执行查询:通过SQL查询数据库获取结果。
  3. 根据结果回答问题:生成用户问题的最终回答。

将问题转换为SQL查询

首先,我们导入OpenAI模型并创建SQL查询链:

from langchain_openai import ChatOpenAI
from langchain.chains import create_sql_query_chainllm = ChatOpenAI(model="gpt-4o-mini")
chain = create_sql_query_chain(llm, db)response = chain.invoke({"question": "How many employees are there"})
print(response)

在这个步骤中,用户问题被转换成了SQL查询:

SQLQuery: SELECT COUNT("EmployeeId") AS "TotalEmployees" FROM "Employee";

执行SQL查询

生成SQL查询后,我们需要执行它,并返回结果:

db.run(response[9:])

使用链(Chains)实现问答系统

接下来我们将构建一个链来处理SQL查询并返回结果。该链的步骤如下:

  1. 将用户问题转换为SQL查询
  2. 执行查询
  3. 使用查询结果回答问题

创建并执行SQL查询链

我们使用LangChain提供的create_sql_query_chain来将用户问题转换为SQL查询。

from operator import itemgetter
from langchain_core.output_parsers import StrOutputParser
from langchain_core.prompts import PromptTemplate
from langchain_core.runnables import RunnablePassthrough
from langchain_community.tools.sql_database.tool import QuerySQLDataBaseTool# 定义用于回答问题的模板
answer_prompt = PromptTemplate.from_template("""Given the following user question, corresponding SQL query, and SQL result, answer the user question.Question: {question}
SQL Query: {query}
SQL Result: {result}
Answer: """
)# 将问题转换为SQL查询
write_query = create_sql_query_chain(llm, db)
execute_query = QuerySQLDataBaseTool(db=db)# 清理查询语句结果
def clean_query(query_result):return query_result.get("query", "").replace("SQLQuery:", "").strip()# 使用 assign + itemgetter 进行数据流转
chain = (RunnablePassthrough.assign(query=write_query).assign(result=lambda x: execute_query.invoke({"query": clean_query(x)}))| answer_prompt| llm| StrOutputParser()
)# 执行链并回答问题
chain.invoke({"question": "How many employees are there"})

在上面的代码中,我们首先定义了问题模板answer_prompt,并通过create_sql_query_chain将用户的问题转换为SQL查询。然后我们使用QuerySQLDataBaseTool执行查询并通过链(Chain)将查询结果返回给用户。

使用代理(Agents)实现问答系统

代理提供了比链更灵活的方式,允许多次查询数据库,并根据需要生成答案。

初始化SQL代理

我们可以通过SQLDatabaseToolkit来创建工具集,并结合LangChain的create_react_agent代理系统来处理SQL查询。

from langchain_community.agent_toolkits import SQLDatabaseToolkit
from langchain_core.messages import SystemMessagetoolkit = SQLDatabaseToolkit(db=db, llm=llm)
tools = toolkit.get_tools()# 定义代理系统提示信息
SQL_PREFIX = """You are an agent designed to interact with a SQL database.
Given an input question, create a syntactically correct SQLite query to run, then look at the results of the query and return the answer."""system_message = SystemMessage(content=SQL_PREFIX)from langgraph.prebuilt import create_react_agent
agent_executor = create_react_agent(llm, tools, state_modifier=system_message)

使用代理执行查询

接下来我们使用代理来执行更复杂的SQL查询并返回结果:

from langchain_core.messages import HumanMessagefor s in agent_executor.stream({"messages": [HumanMessage(content="Who is the oldest employee?")]}
):print(s)

通过上述代码,代理会自动分析数据库中的表结构,生成正确的SQL查询,最终回答问题。比如在这个例子中,代理会根据Employee表中的出生日期找到年龄最大的员工。

完整代码实例

# 安装必要的库
# %pip install langchain langchain-community langchain-openai faiss-cpu sqlite3import os
import getpass
from langchain_community.utilities import SQLDatabase
from langchain_openai import ChatOpenAI
from langchain.chains import create_sql_query_chain
from langchain_core.output_parsers import StrOutputParser
from langchain_core.prompts import PromptTemplate
from langchain_core.runnables import RunnablePassthrough
from langchain_community.tools.sql_database.tool import QuerySQLDataBaseTool
from langchain_community.agent_toolkits import SQLDatabaseToolkit
from langchain_core.messages import SystemMessage
from langgraph.prebuilt import create_react_agent
from langchain_core.messages import HumanMessage# 设置 API 密钥
os.environ["OPENAI_API_KEY"] = getpass.getpass("请输入您的 OpenAI API 密钥: ")# 初始化数据库并插入数据
db = SQLDatabase.from_uri("sqlite:///Chinook.db")# 检查表是否已经存在
table_check_sql = '''
SELECT name FROM sqlite_master WHERE type='table' AND name='Employee';
'''
table_exists = db.run(table_check_sql)# 如果表不存在,则创建表并插入数据
if not table_exists:# 执行建表语句create_table_sql = '''CREATE TABLE Employee (EmployeeId INTEGER NOT NULL,LastName NVARCHAR(20) NOT NULL,FirstName NVARCHAR(20) NOT NULL,Title NVARCHAR(30),ReportsTo INTEGER,BirthDate DATETIME,HireDate DATETIME,Address NVARCHAR(70),City NVARCHAR(40),State NVARCHAR(40),Country NVARCHAR(40),PostalCode NVARCHAR(10),Phone NVARCHAR(24),Fax NVARCHAR(24),Email NVARCHAR(60),CONSTRAINT PK_Employee PRIMARY KEY (EmployeeId),FOREIGN KEY (ReportsTo) REFERENCES Employee (EmployeeId) ON DELETE NO ACTION ON UPDATE NO ACTION);'''db.run(create_table_sql)# 插入初始化数据insert_data_sql = '''INSERT INTO [Employee] ([EmployeeId], [LastName], [FirstName], [Title], [ReportsTo], [BirthDate], [HireDate], [Address], [City], [State], [Country], [PostalCode], [Phone], [Fax], [Email]) VALUES(1, 'Adams', 'Andrew', 'General Manager', NULL, '1962-02-18', '2002-08-14', '11120 Jasper Ave NW', 'Edmonton', 'AB', 'Canada', 'T5K 2N1', '+1 (780) 428-9482', '+1 (780) 428-3457', 'andrew@chinookcorp.com'),(2, 'Edwards', 'Nancy', 'Sales Manager', 1, '1958-12-08', '2002-05-01', '825 8 Ave SW', 'Calgary', 'AB', 'Canada', 'T2P 2T3', '+1 (403) 262-3443', '+1 (403) 262-3322', 'nancy@chinookcorp.com'),(3, 'Peacock', 'Jane', 'Sales Support Agent', 2, '1973-08-29', '2002-04-01', '1111 6 Ave SW', 'Calgary', 'AB', 'Canada', 'T2P 5M5', '+1 (403) 262-3443', '+1 (403) 262-6712', 'jane@chinookcorp.com'),(4, 'Park', 'Margaret', 'Sales Support Agent', 2, '1947-09-19', '2003-05-03', '683 10 Street SW', 'Calgary', 'AB', 'Canada', 'T2P 5G3', '+1 (403) 263-4423', '+1 (403) 263-4289', 'margaret@chinookcorp.com'),(5, 'Johnson', 'Steve', 'Sales Support Agent', 2, '1965-03-03', '2003-10-17', '7727B 41 Ave', 'Calgary', 'AB', 'Canada', 'T3B 1Y7', '1 (780) 836-9987', '1 (780) 836-9543', 'steve@chinookcorp.com'),(6, 'Mitchell', 'Michael', 'IT Manager', 1, '1973-07-01', '2003-10-17', '5827 Bowness Road NW', 'Calgary', 'AB', 'Canada', 'T3B 0C5', '+1 (403) 246-9887', '+1 (403) 246-9899', 'michael@chinookcorp.com'),(7, 'King', 'Robert', 'IT Staff', 6, '1970-05-29', '2004-01-02', '590 Columbia Boulevard West', 'Lethbridge', 'AB', 'Canada', 'T1K 5N8', '+1 (403) 456-9986', '+1 (403) 456-8485', 'robert@chinookcorp.com'),(8, 'Callahan', 'Laura', 'IT Staff', 6, '1968-01-09', '2004-03-04', '923 7 ST NW', 'Lethbridge', 'AB', 'Canada', 'T1H 1Y8', '+1 (403) 467-3351', '+1 (403) 467-8772', 'laura@chinookcorp.com');'''db.run(insert_data_sql)# 初始化OpenAI LLM模型
llm = ChatOpenAI(model="gpt-4o-mini")# ------------------------
# 使用链(Chains)实现问答系统
# ------------------------# 定义用于回答问题的模板
answer_prompt = PromptTemplate.from_template("""Given the following user question, corresponding SQL query, and SQL result, answer the user question.Question: {question}
SQL Query: {query}
SQL Result: {result}
Answer: """
)# 将问题转换为SQL查询
write_query = create_sql_query_chain(llm, db)
execute_query = QuerySQLDataBaseTool(db=db)# 清理查询语句结果
def clean_query(query_result):return query_result.get("query", "").replace("SQLQuery:", "").strip()# 使用 assign + itemgetter 进行数据流转
chain = (RunnablePassthrough.assign(query=write_query).assign(result=lambda x: execute_query.invoke({"query": clean_query(x)}))| answer_prompt| llm| StrOutputParser()
)# 执行链并回答问题
print(chain.invoke({"question": "How many employees are there"}))# ------------------------
# 使用代理(Agents)实现问答系统
# ------------------------# 初始化SQL代理工具包
toolkit = SQLDatabaseToolkit(db=db, llm=llm)
tools = toolkit.get_tools()# 定义代理系统提示信息
SQL_PREFIX = """You are an agent designed to interact with a SQL database.
Given an input question, create a syntactically correct SQLite query to run, then look at the results of the query and return the answer."""
system_message = SystemMessage(content=SQL_PREFIX)# 创建代理
agent_executor = create_react_agent(llm, tools, state_modifier=system_message)# 使用代理执行查询并回答问题
for s in agent_executor.stream({"messages": [HumanMessage(content="Who is the oldest employee?")]}
):print(s)

总结

在本教程中,我们演示了如何通过链(Chains)和代理(Agents)实现基于SQL数据的问答系统。链适用于步骤明确、可预测的场景,而代理适合处理更加复杂和灵活的查询需求。在实际使用中,务必保证数据库的安全性,避免潜在的风险。

系列文章索引
LangChain教程 - 系列文章

版权声明:

本网仅为发布的内容提供存储空间,不对发表、转载的内容提供任何形式的保证。凡本网注明“来源:XXX网络”的作品,均转载自其它媒体,著作权归作者所有,商业转载请联系作者获得授权,非商业转载请注明出处。

我们尊重并感谢每一位作者,均已注明文章来源和作者。如因作品内容、版权或其它问题,请及时与我们联系,联系邮箱:809451989@qq.com,投稿邮箱:809451989@qq.com