使用多智能体人工智能和语言图构建人工智能驱动的智能旅行规划器(一)

103 阅读7分钟

​​

在当今快速发展的人工智能领域,将多样化信息综合成个性化、可执行旅行计划的能力比以往任何时候都更具价值。无论是一次即兴的周末短途旅行,还是一份精心策划的假期安排,旅行者越来越渴望智能系统能够从网络获取实时数据,并将其转化为有意义的行程表、活动建议和旅行洞见。

本文将介绍一个多智能体旅行行程规划器,该规划器基于LangGraph构建,并由LLaMA 3.x模型提供支持。该系统汇聚了一组协作智能体,每个智能体承担特定职责:

  • 行程生成智能体—— 根据用户偏好制定逐日旅行计划

  • 活动推荐智能体—— 推荐独特的本地体验

  • 实用链接获取智能体—— 使用 Google Serper API 检索相关旅行指南

  • 天气预测智能体—— 提供行程期间的天气预期

  • 行李清单生成智能体—— 定制个性化打包清单

  • 饮食文化推荐智能体—— 分享当地美食与礼仪洞察

  • 聊天智能体—— 以对话形式解答后续问题

该系统采用用户友好的Streamlit 界面,展示了现代大语言模型(LLM)与基于智能体的工作流如何协同提供无缝的旅行规划体验。

请跟随我们逐步学习如何构建此项目 —— 从环境搭建到多智能体编排 —— 并探索如何根据自身旅行需求定制该系统。

运行项目的前置条件

以下是针对您基于 LangGraph 和 LLaMA 3.2 的 Streamlit 旅行规划器项目的 “运行前置条件” 部分,已优化结构和表述:

1. Python 3.10+

确保系统已安装 Python 3.10 或更高版本。您可以通过以下命令验证版本:

python --version

2. 安装所需的 Python 库

项目依赖多个 Python 库。使用以下命令安装所有依赖项:

pip install -r requirements.txt

主要依赖库包括:

  • streamlit — 用于构建交互式 Web 界面

  • langgraph — 用于构建多智能体图工作流

  • langchain-community — 用于集成 Ollama 和外部工具

  • python-dotenv — 安全管理环境变量

  • fpdf — 生成可下载的 PDF 行程表

  • serper-wrapper — 通过 Google Serper API 获取网页搜索结果

3. Ollama + LLaMA 3.x 模型

本规划器的核心依赖 LLaMA 3.x 模型,通过 Ollama 运行。请确保:

  • ollama.com 安装 Ollama

  • 启动本地 Ollama 服务器

  • 使用以下命令下载并运行 LLaMA 3.x 模型:

    ollama run llama3

这将为您的智能体提供强大的本地大语言模型能力。

4. API 密钥

实用链接获取智能体 使用 Serper.dev API 从网络检索实时旅行提示和指南。配置步骤如下:

  • Serper.dev 注册账号

  • 生成 API 密钥

  • 在项目根目录创建 .env 文件,并添加以下内容:

    SERPER_API_KEY=your_api_key_here

5. 项目结构(模块化代码)

智能体按功能拆分到独立模块,目录结构示例如下:

.
├── travel_agent.py
├── agents/
│   ├── generate_itinerary.py
│   ├── recommend_activities.py
│   ├── fetch_useful_links.py
│   ├── weather_forecaster.py
│   ├── packing_list_generator.py
│   ├── food_culture_recommender.py
│   └── chat_agent.py
├── utils_export.py
├── .env
├── requirements.txt
└── README.md

代码分步解析

1. 导入依赖与环境配置

项目首先导入必要的 Python 库并加载环境变量,包括jsondotenvtempfile等核心库,以及 LangChain 组件(如用于连接本地 LLaMA 3.2 模型的ChatOllama)。敏感配置(如 API 密钥)存储在.env文件中。

import streamlit as st
import json
from typing import TypedDict, Annotated
from langgraph.graph import StateGraph, END
from langchain_core.messages import HumanMessage
from langchain_community.chat_models import ChatOllama
from langchain_community.utilities import GoogleSerperAPIWrapper
from dotenv import load_dotenv
import os

# 加载环境变量
load_dotenv()

# 初始化大语言模型
llm = ChatOllama(model="llama3.2", base_url="http://localhost:11434")

# 初始化谷歌搜索工具
search = GoogleSerperAPIWrapper()

2. 导入智能体

环境配置完成后,导入模块化智能体,每个智能体负责旅行规划流程的特定环节。这种设计让各智能体专注单一职责(如生成行程、推荐活动、预测天气),便于系统扩展与调试。

from agents import (
    generate_itinerary, 
    recommend_activities, 
    fetch_useful_links, 
    weather_forecaster, 
    packing_list_generator, 
    food_culture_recommender, 
    chat_agent
)

2.1 行程生成智能体

该智能体基于用户偏好(目的地、预算、月份、时长、旅行类型)创建逐日旅行计划。

from langchain_core.messages import HumanMessage
from langchain_community.chat_models import ChatOllama
import json 

def generate_itinerary(state):
    llm = ChatOllama(model="llama3.2", base_url="http://localhost:11434")
    prompt = f"""
    Using the following preferences, create a detailed itinerary:
    {json.dumps(state['preferences'], indent=2)}

    Include sections for each day, dining options, and downtime.
    """
    try:
        result = llm.invoke([HumanMessage(content=prompt)]).content
        return {"itinerary": result.strip()}
    except Exception as e:
        return {"itinerary": "", "warning": str(e)}

它通过 Ollama 运行本地 LLaMA 3.x 模型,将结构化偏好转化为可读性强、可执行的多日行程。

2.2 活动推荐智能体

该智能体通过推荐独特的本地化活动丰富基础行程,结合用户偏好与生成的行程,推荐文化相关或小众体验。

from langchain_core.messages import HumanMessage
from langchain_community.chat_models import ChatOllama
import json 

def recommend_activities(state):
    llm = ChatOllama(model="llama3.2", base_url="http://localhost:11434")
    prompt = f"""
    Based on the following preferences and itinerary, suggest unique local activities:
    Preferences: {json.dumps(state['preferences'], indent=2)}
    Itinerary: {state['itinerary']}

    Provide suggestions in bullet points for each day if possible.
    """
    try:
        result = llm.invoke([HumanMessage(content=prompt)]).content
        return {"activity_suggestions": result.strip()}
    except Exception as e:
        return {"activity_suggestions": "", "warning": str(e)}

2.3实用链接智能体

该智能体借助 Serper API 获取最新博客、旅行建议和指南,通过链接可信网络内容增强用户信任。

from langchain_community.utilities import GoogleSerperAPIWrapper

def fetch_useful_links(state):
    search = GoogleSerperAPIWrapper()
    destination = state['preferences'].get('destination', '')
    month = state['preferences'].get('month', '')
    query = f"Travel tips and guides for {destination} in {month}"
    try:
        search_results = search.results(query)
        organic_results = search_results.get("organic", [])
        links = [
            {"title": result.get("title", "No title"), "link": result.get("link", "")}
            for result in organic_results[:5]
        ]
        return {"useful_links": links}
    except Exception as e:
        return {"useful_links": [], "warning": f"Failed to fetch links: {str(e)}"}

它抓取前 5 个相关结果,返回可点击标题供用户深入阅读。

2.4 天气预测智能体

该智能体预测选定目的地和旅行月份的气候,通过提示词生成自然语言摘要并提供建议(如携带雨伞或防晒霜)。

from langchain_core.messages import HumanMessage
from langchain_community.chat_models import ChatOllama

def weather_forecaster(state):
    llm = ChatOllama(model="llama3.2", base_url="http://localhost:11434")
    prompt = f"""
    Based on the destination and month, provide a detailed weather forecast including temperature, precipitation, and advice for travelers:
    Destination: {state['preferences'].get('destination', '')}
    Month: {state['preferences'].get('month', '')}
    """
    try:
        result = llm.invoke([HumanMessage(content=prompt)]).content
        return {"weather_forecast": result.strip()}
    except Exception as e:
        return {"weather_forecast": "", "warning": str(e)}

确保旅行者为实际天气状况做好准备。

2.5 行李清单智能体

该智能体基于目的地、时长、天气和假期类型,生成全面的打包清单,支持季节性和上下文感知。

from langchain_core.messages import HumanMessage
from langchain_community.chat_models import ChatOllama

def packing_list_generator(state):
    llm = ChatOllama(model="llama3.2", base_url="http://localhost:11434")
    prompt = f"""
    Generate a comprehensive packing list for a {state['preferences'].get('holiday_type', 'general')} holiday in {state['preferences'].get('destination', '')} during {state['preferences'].get('month', '')} for {state['preferences'].get('duration', 0)} days.
    Include essentials based on expected weather and trip type.
    """
    try:
        result = llm.invoke([HumanMessage(content=prompt)]).content
        return {"packing_list": result.strip()}
    except Exception as e:
        return {"packing_list": "", "warning": str(e)}

2.6 饮食文化推荐智能体

该智能体融合美食探索与文化体验,推荐必尝的当地菜肴、餐厅,并提供礼仪提示,帮助旅行者避免失礼并享受当地款待。

from langchain_core.messages import HumanMessage
from langchain_community.chat_models import ChatOllama

def food_culture_recommender(state):
    llm = ChatOllama(model="llama3.2", base_url="http://localhost:11434")
    prompt = f"""
    For a trip to {state['preferences'].get('destination', '')} with a {state['preferences'].get('budget_type', 'mid-range')} budget:
    1. Suggest popular local dishes and recommended dining options.
    2. Provide important cultural norms, etiquette tips, and things travelers should be aware of.
    Format the response with clear sections for 'Food & Dining' and 'Culture & Etiquette'.
    """
    try:
        result = llm.invoke([HumanMessage(content=prompt)]).content
        return {"food_culture_info": result.strip()}
    except Exception as e:
        return {"food_culture_info": "", "warning": str(e)}

2.7 对话聊天智能体

该智能体驱动界面上的交互式问答聊天功能。用户可提问、请求澄清或调整计划,并即时获得类人回答。

from langchain_core.messages import HumanMessage
from langchain_community.chat_models import ChatOllama
import json

def chat_node(state):
    llm = ChatOllama(model="llama3.2", base_url="http://localhost:11434")
    prompt = f"""
    Context:
    Preferences: {json.dumps(state['preferences'], indent=2)}
    Itinerary: {state['itinerary']}

    User Question:
    {state['user_question']}

    Respond conversationally with insights or suggestions : keep your response brief
    {{ "chat_response": "Your response here" }}
    """
    try:
        result = llm.invoke([HumanMessage(content=prompt)]).content
        try:
            parsed = json.loads(result.strip())
            response = parsed.get("chat_response", result.strip())
        except json.JSONDecodeError:
            response = result.strip()
        chat_entry = {"question": state['user_question'], "response": response}
        chat_history = state.get('chat_history', []) + [chat_entry]
        return {"chat_response": response, "chat_history": chat_history}
    except Exception as e:
        return {"chat_response": "", "warning": str(e)}

它存储聊天历史并基于完整上下文(用户偏好 + 行程)回复,使对话连贯且智能。

本文暂且介绍到这里,后续内容请继续关注我们的博客!