Skip to content

Docker 环境下私聊文件发送失败:download_file/base64 可落盘,但 upload_private_file 返回 rich media transfer failed #755

@under-the-ocean

Description

@under-the-ocean

问题描述

在 Docker 部署的 llbot + PMHQ 环境中,OneBot v11 的文件发送相关接口无法成功发送私聊文件。

现象:

  • download_file 可以把文件下载到 llbot 容器内 /app/llbot/data/temp/...
  • upload_private_file 能识别 base64 输入并落盘到 /app/llbot/data/temp/...
  • 但最终发送到 QQ 时失败,报错 rich media transfer failed
  • 直接传 llbot 容器路径给 upload_private_file 时,也可能返回 未知文件类型或路径不存在

已尝试过的方案

我看到其他 issue 中提到过通过修改 Docker volume 映射解决文件路径问题,因此已经按该思路调整过 Docker 映射,使 llbotpmhq 共享关键目录,但问题仍然存在。

当前 compose 关键配置如下:

services:
  pmhq:
    image: docker.1ms.run/linyuchen/pmhq:7.3.2
    privileged: true
    environment:
      - ENABLE_HEADLESS=false
    networks:
      - app_network
    volumes:
      - qq_volume:/root/.config/QQ
      - ./llbot_config:/app/llbot/data:rw
    restart: unless-stopped
    healthcheck:
      test: ["CMD", "curl", "-f", "http://localhost:13000/health"]
      interval: 30s
      timeout: 10s
      retries: 3
      start_period: 40s

  llbot:
    image: linyuchen/llbot:7.12.10
    ports:
      - "3080:3080"
    extra_hosts:
      - "host.docker.internal:host-gateway"
    environment:
      - PMHQ_HOST=pmhq
      - WEBUI_PORT=3080
    networks:
      - app_network
    volumes:
      - qq_volume:/root/.config/QQ
      - ./llbot_config:/app/llbot/data:rw
    depends_on:
      - pmhq
    restart: unless-stopped
    healthcheck:
      test: ["CMD", "sh", "-c", "ps | grep '[n]ode'"]
      interval: 30s
      timeout: 10s
      retries: 3
      start_period: 40s

volumes:
  qq_volume:

networks:
  app_network:
    driver: bridge

也就是说,pmhqllbot 已经共享:

/root/.config/QQ
/app/llbot/data

但仍然无法发送文件。

环境信息

  • llbot 镜像:linyuchen/llbot:7.12.10
  • PMHQ 镜像:docker.1ms.run/linyuchen/pmhq:7.3.2
  • OneBot 版本接口返回:
{
  "app_name": "LLOneBot",
  "protocol_version": "v11",
  "app_version": "7.12.10"
}

复现步骤

1. 使用 base64 发送小文本文件

调用:

{
  "action": "upload_private_file",
  "params": {
    "user_id": 3791129086,
    "file": "base64://SGVsbG8gZnJvbSBBc3RyQm90IGZpbGUgdGVzdC4K",
    "name": "astrbot_file_test.txt"
  }
}

返回失败,但可以看到 llbot 已经把 base64 内容落到本地临时文件:

filePath: /app/llbot/data/temp/fd5a1b91-d8d9-433e-b994-e1b36981271f
fileSize: 30

错误摘要:

rich media transfer failed

2. 使用 download_file 下载文件后再 upload_private_file

先调用:

{
  "action": "download_file",
  "params": {
    "url": "http://192.168.10.11:6185/api/file/send/xxx?download_token=xxx",
    "thread_count": 1
  }
}

返回成功:

{
  "file": "/app/llbot/data/temp/33bb8a19088a4ed77c3ca9f1e6d32e71"
}

然后调用:

{
  "action": "upload_private_file",
  "params": {
    "user_id": 3791129086,
    "file": "/app/llbot/data/temp/33bb8a19088a4ed77c3ca9f1e6d32e71",
    "name": "astrbot_plugin_napcat_llm_tools_v0.3.0.zip"
  }
}

返回失败:

rich media transfer failed

错误中显示 filePath 指向 llbot 本地临时文件,但最终 rich media 发送失败。

3. 直接发送 llbot 侧路径

尝试过以下路径:

/app/llbot/data/temp/webqq-uploads/7cca478a-ab3a-400e-b5a8-a1d3b037cc79.zip
/app/llbot/data/temp/webqq-uploads/7cca478a-ab3a-400e-b5a8-a1d3b037cc79
/app/llbot/data/temp/7cca478a-ab3a-400e-b5a8-a1d3b037cc79.zip
/app/llbot/data/temp/7cca478a-ab3a-400e-b5a8-a1d3b037cc79

返回类似:

未知文件类型或路径不存在

期望行为

在 Docker 环境下,upload_private_file 应该可以发送以下来源的文件:

  1. base64://... 解码后的临时文件
  2. download_file 下载到 /app/llbot/data/temp/... 的文件
  3. llbot 与 pmhq 共享卷中的文件路径

实际行为

文件可以落盘,但发送 QQ 私聊文件时失败:

rich media transfer failed

或者路径检查阶段失败:

未知文件类型或路径不存在

备注

这个问题和上层 Bot 框架无关。上层已经验证:

  • 图片发送正常
  • OCR 正常
  • download_file 能调用并返回 llbot 本地路径
  • base64 输入可被 llbot 解码到本地临时路径

失败集中在 llbot / PMHQ / QQNT 文件富媒体发送阶段。

请问在当前 Docker 架构下,upload_private_file 是否还有额外的路径要求、权限要求,或 PMHQ 侧需要额外挂载/配置?

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions