--- title: GAIA 问答 Agent 评测 emoji: 🕵🏻‍♂️ colorFrom: indigo colorTo: indigo sdk: gradio sdk_version: 5.25.2 app_file: app.py pinned: false hf_oauth: true # 可选配置。默认有效期为 8 小时/480 分钟,最长为 30 天/43200 分钟。 hf_oauth_expiration_minutes: 480 --- 这是 Hugging Face Agents Course Final Assignment 的基础 Space,用于运行并提交 GAIA 风格问题的 Agent 作答结果。 当前版本已经改成 LangGraph 类型工作流 Agent: - `app.py` 会通过课程评测接口拉取问题并提交答案。 - `agent.py` 中的 `GaiaAgent` 会先让 LLM 判断问题类型,再由 LangGraph 路由到对应工具节点。 - `tools/executor.py` 和 `tools/tool_specs.py` 负责注册、描述并执行工具。 - `tools/` 目录包含规则题、附件下载、Python 执行、Excel 计算、结构化网页、网页检索和体育数据工具。 - 登录 Hugging Face 后,界面会使用当前 HF 用户名提交答案。 - 提交时会携带当前 Space 的代码仓库链接,便于评测系统记录实现来源。 Space 配置参考:https://huggingface.co/docs/hub/spaces-config-reference ## 本地 GAIA 测试设计 本地测试不要直接等同于官方评分。课程评分接口的 `/questions` 可以返回问题列表,但不会返回标准答案;带附件的问题还需要额外处理文件。因此,本地测试应该拆成两层: 1. 流程测试:验证 Agent 能稳定读取问题、处理附件路径、调用工具、生成答案、记录日志,并输出符合提交接口要求的 JSON。 2. 正确率测试:使用你自己维护的本地 gold 数据,或公开/可访问的 GAIA 数据子集,对 Agent 的答案做离线比对。 建议的本地目录结构: ```text . ├── app.py ├── agent.py ├── gaia_local_eval.py ├── tools/ │ ├── direct_rules.py │ ├── attachment_loader.py │ ├── code_runner.py │ ├── spreadsheet_solver.py │ ├── structured_web_tools.py │ ├── sports_solver.py │ ├── tool_specs.py │ └── executor.py ├── data/ │ ├── questions.json │ ├── gold_local.jsonl │ └── attachments/ │ └── / │ └── └── runs/ └── .jsonl ``` 建议的执行流程: 1. 缓存题目:从 `https://agents-course-unit4-scoring.hf.space/questions` 拉取当前题目,保存为 `data/questions.json`,避免频繁请求接口导致限流或不稳定。 2. 准备附件:如果题目有 `file_name`,优先尝试用裸 `task_id` 请求 `/files/{task_id}`;如果接口不可用,就把附件手动放到 `data/attachments//` 下。 3. 抽离 Agent:把真实作答逻辑放入 `agent.py`,提供统一入口,例如 `answer(question: str, file_path: str | None = None) -> str`。 4. 编写本地 runner:`gaia_local_eval.py` 只负责读取 `questions.json`、定位附件、调用 Agent、保存每题的答案、耗时、错误、工具轨迹和置信度。 5. 编写答案规整器:对数字、货币、日期、大小写、逗号分隔列表、空格和标点做标准化,避免因为格式差异误判。 6. 维护 gold 文件:`gold_local.jsonl` 每行包含 `task_id`、`expected_answer`、`match_type` 和备注。没有标准答案的问题只做流程测试,不纳入正确率统计。 7. 分层运行:先跑 1 到 3 道 smoke test,再跑全部本地题;确认稳定后再通过 Space 按官方流程提交。 当前代码采用 LangGraph 三段式工作流: 1. `classify`:LLM 只判断问题类型,例如 `direct_text`、`python_code`、`spreadsheet`、`wikipedia`、`sports`、`web_url`、`web_search`、`attachment_text`、`audio_media`、`video_media`、`vision_image`、`unknown`。 2. 类型节点:LangGraph 根据问题类型调用对应工具节点,例如 `direct_answer_tool`、`python_tool`、`spreadsheet_tool`、`wikipedia_tool`、`sports_tool`、`web_read_tool`、`web_search_tool`。 3. `finalize`:LLM 只把工具结果格式化为题目要求的最终答案;如果 LLM 调用失败,则使用工具候选答案兜底。 分类输出格式: ```json {"question_type":"wikipedia","confidence":"high","reason":"Wikipedia structured table question","query":"1928 Summer Olympics athletes"} ``` 最终答案格式: ```json {"answer":"CUB","confidence":"high"} ``` 当前仍采用 40% 优先策略:为了先冲过最低分,不处理音频和视频题,只集中处理文本、网页、Python、Excel、体育统计和少量确定性规则题。 当前优先覆盖的题型: - 反向句子题。 - 非交换表题。 - 植物学蔬菜分类题。 - Python 附件最终输出题。 - Excel 食品销售合计题。 - Mercedes Sosa Wikipedia 专辑计数题。 - Wikipedia Featured Article 恐龙提名人题。 - 1928 Summer Olympics 最少运动员 IOC 代码题。 - 1977 Yankees walks leader at-bats 题。 本地回归测试: ```bash python3 gaia_local_eval.py ``` 注意:现在本地回归会优先调用 LLM 做题型分类,并在最后调用 LLM 做答案格式化,因此需要 `HF_TOKEN`,并会消耗少量 Hugging Face Inference Providers 额度。这个 token 必须具备 `Make calls to Inference Providers` 权限,否则 LLM 请求会返回 403。分类失败或格式化失败时,工作流会进入兜底逻辑,尽量使用已有工具候选答案。`MAX_AGENT_STEPS` 可用于限制兜底阶段最多尝试的工具数。 默认不启用 `response_format={"type":"json_object"}`,因为 HF Router 的部分 provider 对这个参数支持不稳定,可能返回空 `message.content`。如果你确认当前模型/provider 支持 JSON mode,可以设置 `HF_PLANNER_USE_RESPONSE_FORMAT=1` 再启用。 如果本地没有安装依赖,先执行: ```bash python3 -m pip install -r requirements.txt ``` 如果以后要追求更高分,真实 Agent 至少应该补齐这些工具能力: - 网页检索和网页阅读,用于维基、论文、新闻、体育数据等开放网络问题。 - Python 执行沙箱,用于数学、表格、代码题和可复现计算。 - 文件解析能力,包括图片、音频、Excel、CSV、Python 文件和普通文本。 - 音频转写能力,用于 `.mp3` 附件。 - 视频处理能力,用于 YouTube 问题,可结合字幕、抽帧和视觉模型。 - 棋类分析能力,用于棋盘图像和最优走法题。 - 答案格式控制能力,严格输出题目要求的最终答案,不输出推理过程。 本地 runner 的目标不是替代官方评分,而是在提交前暴露三类问题:Agent 崩溃、工具链缺失、答案格式错误。最终分数仍以官方 `/submit` 返回结果为准。