前天我們讓 Agent 可以使用工具「思考 + 行動」。
今天,我們要讓使用者可以直接跟 Agent 對話,建立一個簡單的互動介面。
這時候就用到 Gradio,可以快速做 Web 聊天界面。
pip install gradio
我們使用前天的 Gemini LLM + Tools Agent。
用我們上次的code已經有:
import os, requests, time
import gradio as gr
from langchain.text_splitter import CharacterTextSplitter
from langchain_community.embeddings import HuggingFaceEmbeddings
from langchain.vectorstores import FAISS
from langchain.tools import Tool
from langchain_google_genai import ChatGoogleGenerativeAI
from langchain.agents import initialize_agent, AgentType
# -------------------------------
# 1. API Key 設定
# -------------------------------
os.environ["GOOGLE_API_KEY"] = "" # Gemini API Key
API_KEY = "" # OpenWeatherMap API Key
UNITS = "metric" # 攝氏溫度
LANG = "zh_tw"
### 建立文件知識庫(FAQ)
# 讀取 FAQ 文件
with open("faq.txt", "r", encoding="utf-8") as f:
text = f.read()
# 切分文字
text_splitter = CharacterTextSplitter(chunk_size=200, chunk_overlap=50)
docs = text_splitter.create_documents([text])
# 建立 Embeddings 與向量資料庫
embeddings = HuggingFaceEmbeddings(model_name="all-MiniLM-L6-v2")
vectorstore = FAISS.from_documents(docs, embeddings)
### Python 計算工具
#建立工具
def calculate(expression: str) -> str:
try:
return str(eval(expression))
except Exception as e:
return f"計算錯誤:{e}"
#建立工具(定義)
calc_tool = Tool(
name="Calculator",
func=calculate,
description="可以計算數學運算式,例如 2+3*5"
)
### Python 天氣查詢 API
# 查詢天氣
def get_weather(city: str, retries: int = 3, delay: int = 2) -> str:
"""
取得指定城市天氣資訊,若失敗會重試。
:param city: 城市名稱
:param retries: 最大重試次數
:param delay: 每次重試間隔秒數
"""
url = "https://api.openweathermap.org/data/2.5/weather"
params = {
"q": city,
"appid": API_KEY,
"units": UNITS,
"lang": LANG
}
for attempt in range(1, retries + 1):
try:
response = requests.get(url, params=params, timeout=10)
data = response.json()
if data.get("cod") == 200:
city_name = data["name"]
weather_desc = data["weather"][0]["description"]
temp = data["main"]["temp"]
temp_min = data["main"]["temp_min"]
temp_max = data["main"]["temp_max"]
return f"{city_name} 天氣:{weather_desc}, 現在 {temp}°C (範圍 {temp_min}°C ~ {temp_max}°C)"
else:
print(f"⚠️ 第 {attempt} 次失敗: {data.get('message', '未知錯誤')}")
except Exception as e:
print(f"⚠️ 第 {attempt} 次發生錯誤: {e}")
# 若還有剩餘重試次數,等待後重試
if attempt < retries:
time.sleep(delay)
return f"取得天氣資料失敗:重試 {retries} 次後仍無法獲取 {city} 的天氣"
#查詢天氣(定義)
weather_tool = Tool(
name="Weather",
func=get_weather,
description="查詢指定城市的天氣,例如:'台北' 或 'Tokyo',如果抓到的為中文請轉英文回傳結果時再轉中文"
)
### 取用知識庫(FAQ)
def search_faq(query: str) -> str:
docs = vectorstore.similarity_search(query, k=3)
if not docs:
return ""
return "\n".join([doc.page_content for doc in docs])
faq_tool = Tool(
name="FAQ",
func=search_faq,
description="查詢公司 FAQ 文件,用於回答技術或產品相關問題"
)
### 初始化 Gemini LLM & 初始化 Agent
llm = ChatGoogleGenerativeAI(model="gemini-2.5-flash", temperature=0)
#初始化 Agent
agent = initialize_agent(
tools=[calc_tool, weather_tool, faq_tool],
llm=llm,
agent=AgentType.ZERO_SHOT_REACT_DESCRIPTION,
verbose=True
)
#-------------------------------
#RAG + Agent 混合函數
#-------------------------------
# Hybrid agent
def hybrid_agent(query: str) -> str:
context = search_faq(query)
if context:
augmented_query = f"FAQ內容如下:\n{context}\n\n問題:{query}\n你可以使用 FAQ 或工具來回答。"
return agent.run(augmented_query)
return agent.run(query)
到目前為止除了一開始的import的部分都跟前天的內容一樣!
下面是我們要將這些功能放到Gradio UI,方便用web觀看
# Gradio
iface = gr.Interface(
fn=hybrid_agent,
inputs=gr.Textbox(lines=2, placeholder="請輸入問題或指令..."),
outputs="text",
title="FAQ + 計算 + 天氣 AI 助手",
description="這是一個可以查詢 FAQ、計算數學、查詢天氣的 AI Agent"
)
if __name__ == "__main__":
iface.launch()
範例指令:
"請幫我算 15 * 7"
→ Agent 自動用計算工具"你好,你能介紹一下 LangChain 嗎?"
→ Agent 用 LLM 回答今天你學會了:
恭喜你!🎉
到這裡,你已經完成一個可以 思考 + 行動 + 互動 的完整 AI Agent 系統。明天我們會做第二週總結,回顧規則型 Agent 與 LLM Agent 的差異,並分享一些心得與應用小技巧。