API 文档

阅读当前文档内容。

文档
本页目录

API 接口文档

目录

基础信息

  • 基础地址https://qw.minapp.xin
  • 鉴权参数secret,统一放在 query string 中。后台会同时提供机器人级 secret 和会话级 send_secretmessage_secret
  • 请求格式:请求 body 使用 Content-Type: application/json
  • 时间格式:接口返回的时间为 ISO 8601 格式。
  • 会话 ID:使用会话列表接口返回的 conversation_id;私聊通常以 S: 开头,群聊通常以 R: 开头。
  • 独立开关:后台可分别开启或关闭发送消息接口、消息查询接口,也可按会话单独开关;使用机器人级 secret 时只受账号级开关影响,不受会话级开关影响;使用会话级密钥时还需要开启对应会话接口。会话级接口默认关闭,机器人后台设置的运营者微信可在对应会话发送“开启接口”开启。
  • 媒体转存:默认关闭。后台可为单个机器人选择“客户按需获取”或“收到后自动转存”;支持图片、语音和文件,转存后的媒体保存在服务器本地持久目录,并按配置的保留时间自动删除。

消息通知

在后台配置 Webhook 地址并启用 API 服务后,机器人收到的会话消息会以 HTTP POST 请求通知到该地址。

  • 通知范围:文本、图片、语音、文件、小程序、链接、名片、地理位置、视频号等消息。
  • 鉴别字段:用 msgtype 区分消息类型;不同类型携带对应对象。
  • 安全建议:回调中的 secret 可用于校验通知来源。

文本消息


{

    "secret": "-",

    "msgtype": "text",

    "conversation_id": "S:16888xxx328682_7881302xx12998",

    "sender": "78813xx98",

    "text": {

        "content": "你好"

    }

}

图片消息


{

    "secret": "-",

    "event": "message.created",

    "msgtype": "image",

    "conversation_id": "",

    "sender": "",

    "image": {

        "media_id": "media_01...",

        "status": "available_on_demand"

    }

}

开启媒体转存后,图片回调不会向客户暴露微信 CDN、file_idaes_key。客户按需调用媒体解析接口;文件写入本服务器后会收到 media.ready 回调。


{

    "secret": "-",

    "event": "media.ready",

    "conversation_id": "S:16888xxx328682_7881302xx12998",

    "media_id": "media_01...",

    "media_type": "image",

    "image": {

        "media_id": "media_01...",

        "status": "ready",

        "url": "https://socket.example.com/media/media_01...",

        "mime": "image/jpeg",

        "size": 182736

    }

}

语音消息


{

    "secret": "-",

    "event": "message.created",

    "msgtype": "voice",

    "conversation_id": "S:16888xxx328682_7881302xx12998",

    "sender": "78813xx98",

    "voice": {

        "media_id": "media_01...",

        "status": "available_on_demand",

        "duration": 10

    }

}

语音消息复用媒体转存接口。开启转存后,回调不会向客户暴露 c2c_cdnfile_idaes_key;客户按需调用媒体解析接口,文件写入本服务器后会收到 media.ready 回调。


{

    "secret": "-",

    "event": "media.ready",

    "conversation_id": "S:16888xxx328682_7881302xx12998",

    "media_id": "media_01...",

    "media_type": "voice",

    "voice": {

        "media_id": "media_01...",

        "status": "ready",

        "url": "https://socket.example.com/media/media_01...",

        "mime": "audio/amr",

        "size": 18308,

        "duration": 10

    }

}

文件消息


{

    "secret": "-",

    "event": "message.created",

    "msgtype": "file",

    "conversation_id": "S:16888xxx328682_7881302xx12998",

    "sender": "78813xx98",

    "file": {

        "media_id": "media_01...",

        "status": "available_on_demand",

        "file_name": "HttpCanary.apk.1",

        "size": 9957248

    }

}

文件消息复用媒体转存接口。开启转存后,回调不会向客户暴露微信 CDN 下载地址、auth_keyfile_idaes_key;客户按需调用媒体解析接口,文件写入本服务器后会收到 media.ready 回调。


{

    "secret": "-",

    "event": "media.ready",

    "conversation_id": "S:16888xxx328682_7881302xx12998",

    "media_id": "media_01...",

    "media_type": "file",

    "file": {

        "media_id": "media_01...",

        "status": "ready",

        "url": "https://socket.example.com/media/media_01...",

        "mime": "application/vnd.android.package-archive",

        "size": 9957248,

        "file_name": "HttpCanary.apk.1"

    }

}

小程序消息


{

    "secret": "-",

    "msgtype": "miniprogram",

    "conversation_id": "",

    "sender": "",

    "miniprogram": {

        "appicon": "",

        "appid": "",

        "appname": "",

        "username": "",

        "page_path": "",

        "title": "",

        "file_id": "",

        "aes_key": "",

        "md5": "",

        "size": 0,

        "cdn_type": 2,

        "cdn": {

            "file_id": "",

            "aes_key": "",

            "md5": "",

            "size": 0

        }

    }

}

链接消息


{

    "secret": "-",

    "msgtype": "link",

    "conversation_id": "",

    "sender": "",

    "link": {

        "title": "",

        "url": ""

    }

}

地理位置消息


{

    "secret": "-",

    "msgtype": "location",

    "conversation_id": "S:16888xxx328682_7881302xx12998",

    "sender": "78813xx98",

    "sender_name": "小邪",

    "location": {

        "title": "北京天安门广场",

        "address": "北京市东城区东长安街",

        "latitude": 39.903739928999997,

        "longitude": 116.397827148,

        "zoom": 15

    }

}

视频号消息


{

    "secret": "-",

    "msgtype": "vlog",

    "conversation_id": "S:16888xxx328682_7881302xx12998",

    "sender": "78813xx98",

    "sender_name": "小邪",

    "vlog": {

        "avatar": "https://wx.qlogo.cn/finderhead/example/0",

        "cover_url": "https://wxapp.tc.qq.com/example-cover",

        "thumb_url": "https://wxapp.tc.qq.com/example-thumb",

        "nickname": "视频号名称",

        "desc": "视频号描述",

        "url": "https://channels.weixin.qq.com/web/pages/feed?eid=example",

        "feed_type": 4,

        "extras": "视频号协议数据"

    }

}


消息发送

  • 接口地址:POST /api/send
  • 必填参数secretconversation_id
  • 权限范围:支持机器人级 secret 和会话级 send_secret。机器人级 secret 只受账号级发送开关影响;会话级 send_secret 只能向对应 conversation_id 发送消息,且需要先开启该会话接口。
  • 说明:消息内容放在 JSON body 中,msgtype 表示消息类型。

curl 'https://qw.minapp.xin/api/send?secret=#{secret}&conversation_id=#{conversation_id}' \

  -H 'Content-Type: application/json' \

  -d '

{

  "msgtype": "text",

  "text": {

    "content": "hello world"

  }

}'

文本


{

    "msgtype": "text",

    "text": {

        "content": "hello world"

    }

}

链接卡片


{

    "msgtype": "link",

    "link": {

        "title": "标题",

        "url": "https://x.com",

        "image_url": "https://x.com/logo.png",

        "desc": "描述"

    }

}

图片


{

    "msgtype": "image",

    "image": {

        "url": "https://tuiguangdashi.com/template/eyou/pc/skin/images/logo.png"

    }

}

小程序

发送小程序卡片时,基础字段为 appidappnamepage_pathtitle;封面图建议直接复用消息查询接口返回的 miniprogram 对象。封面图参数支持顶层 file_id/aes_key/md5/size,也支持 cdn: { file_id, aes_key, md5, size }


{

    "msgtype": "miniprogram",

    "miniprogram": {

        "appid": "wx123",

        "appname": "示例小程序",

        "username": "gh_xxx@app",

        "appicon": "https://example.com/icon.png",

        "page_path": "pages/index/index.html",

        "title": "小程序标题",

        "file_id": "306b...",

        "aes_key": "6C75...",

        "md5": "059b34e084cf19a38a92a677177863d2",

        "size": 11122,

        "cdn_type": 2,

        "cdn": {

            "file_id": "306b...",

            "aes_key": "6C75...",

            "md5": "059b34e084cf19a38a92a677177863d2",

            "size": 11122

        }

    }

}

名片


{

    "msgtype": "contact",

    "contact": {

        "share_user_id": "7881300xxx093"

    }

}

也兼容 msgtype: "card" 和顶层 share_user_id


消息查询

查询指定会话已归档的双向消息,按消息时间倒序返回。只有开启会话消息存档后收到或发送的消息可被查询。

  • 接口地址:GET /api/messages
  • 必填参数secretconversation_id
  • 可选参数page(默认 1)、page_size(默认 50,范围 1100)。
  • 权限范围:支持机器人级 secret 和会话级 message_secret。推荐使用会话列表返回的 message_secret;它只能查询对应 conversation_id 的消息,且需要先开启该会话接口。

curl 'https://qw.minapp.xin/api/messages?secret=#{secret}&conversation_id=#{conversation_id}&page=1&page_size=50'

成功响应:


{

    "list": [

        {

            "id": "66c01234567890abcdef1234",

            "conversation_id": "S:16888xxx328682_7881302xx12998",

            "chat_type": "private",

            "role": "user",

            "type": 11001,

            "sender": "78813xx98",

            "receiver": "",

            "content": "你好",

            "raw_data": {

                "content": "你好"

            },

            "msgtype": "text",

            "text": {

                "content": "你好"

            },

            "message_at": "2026-07-13T08:30:00.000Z"

        },

        {

            "id": "66c01234567890abcdef1235",

            "conversation_id": "S:16888xxx328682_7881302xx12998",

            "chat_type": "private",

            "role": "user",

            "type": 11042,

            "sender": "78813xx98",

            "receiver": "",

            "content": "",

            "raw_data": {

                "media_id": "media_01...",

                "media_status": "available_on_demand"

            },

            "msgtype": "image",

            "image": {

                "url": "",

                "media_id": "media_01...",

                "status": "available_on_demand"

            },

            "message_at": "2026-07-13T08:31:00.000Z"

        },

        {

            "id": "66c01234567890abcdef1236",

            "conversation_id": "S:16888xxx328682_7881302xx12998",

            "chat_type": "private",

            "role": "user",

            "type": 11044,

            "sender": "78813xx98",

            "receiver": "",

            "content": "",

            "raw_data": {

                "media_id": "media_02...",

                "media_status": "available_on_demand",

                "duration": 10

            },

            "msgtype": "voice",

            "voice": {

                "url": "",

                "duration": 10,

                "media_id": "media_02...",

                "status": "available_on_demand"

            },

            "message_at": "2026-07-13T08:32:00.000Z"

        },

        {

            "id": "66c01234567890abcdef1237",

            "conversation_id": "S:16888xxx328682_7881302xx12998",

            "chat_type": "private",

            "role": "user",

            "type": 11045,

            "sender": "78813xx98",

            "receiver": "",

            "content": "",

            "raw_data": {

                "media_id": "media_03...",

                "media_status": "available_on_demand",

                "file_name": "HttpCanary.apk.1",

                "size": 9957248

            },

            "msgtype": "file",

            "file": {

                "url": "",

                "file_name": "HttpCanary.apk.1",

                "size": 9957248,

                "media_id": "media_03...",

                "status": "available_on_demand"

            },

            "message_at": "2026-07-13T08:33:00.000Z"

        },

        {

            "id": "66c01234567890abcdef1238",

            "conversation_id": "S:16888xxx328682_7881302xx12998",

            "chat_type": "private",

            "role": "user",

            "type": 11066,

            "sender": "78813xx98",

            "receiver": "",

            "content": "小程序标题",

            "raw_data": {

                "appid": "wx123",

                "appname": "示例小程序",

                "appicon": "https://example.com/icon.png",

                "username": "gh_xxx@app",

                "page_path": "pages/index/index.html",

                "title": "小程序标题",

                "cdn_type": 2,

                "cdn": {

                    "file_id": "306b...",

                    "aes_key": "6C75...",

                    "md5": "059b34e084cf19a38a92a677177863d2",

                    "size": 11122

                }

            },

            "msgtype": "miniprogram",

            "miniprogram": {

                "appid": "wx123",

                "appname": "示例小程序",

                "appicon": "https://example.com/icon.png",

                "username": "gh_xxx@app",

                "page_path": "pages/index/index.html",

                "title": "小程序标题",

                "file_id": "306b...",

                "aes_key": "6C75...",

                "md5": "059b34e084cf19a38a92a677177863d2",

                "size": 11122,

                "cdn_type": 2,

                "cdn": {

                    "file_id": "306b...",

                    "aes_key": "6C75...",

                    "md5": "059b34e084cf19a38a92a677177863d2",

                    "size": 11122

                }

            },

            "message_at": "2026-07-13T08:34:00.000Z"

        }

    ],

    "pagination": {

        "page": 1,

        "page_size": 50,

        "total": 1,

        "total_pages": 1

    }

}

字段说明:

  • roleuser 表示对方发送,assistant 表示机器人发送。
  • type:消息类型编号;可结合 content 展示文本、标题或描述。
  • raw_data:归档时保存的原始消息数据。
  • msgtype 及同名对象:结构化消息内容,例如 textimagevoicefilelinkminiprogramcontact。其中 imagevoicefile 可能只返回 media_idstatus,需要调用媒体按需转存接口后才会返回可访问的 url
  • message_at:消息发生时间。

媒体按需转存

  • 接口地址:POST /api/media/:media_id/resolve
  • 必填参数secretmedia_id
  • 权限范围:需要对应会话的消息查询权限。
  • 前提:机器人开放接口配置中的“媒体转存”必须开启,且机器人客户端已上报 media_upload_v1 能力。

curl -X POST 'https://qw.minapp.xin/api/media/media_01.../resolve?secret=#{message_secret}'

首次调用会要求在线机器人客户端下载并解密原图、语音或文件,然后流式上传到本服务器。接口通常返回 processing,表示转存任务已下发:


{

    "media_id": "media_01...",

    "status": "processing",

    "expires_at": "2026-08-20T00:00:00.000Z"

}

完成后,Webhook 会收到 media.ready;再次调用该接口会直接返回 ready 和可访问 URL:


{

    "media_id": "media_01...",

    "status": "ready",

    "url": "https://socket.example.com/media/media_01...",

    "expires_at": "2026-08-20T00:00:00.000Z"

}

机器人客户端必须在进入 Socket 房间后发送能力声明;新版 bot-gateway 会自动上报:


{

    "capabilities": ["media_upload_v1"]

}

服务端会通过 Socket media.resolve 事件下发微信媒体元数据、media_type、一次性上传令牌及上传地址。客户端下载并解密原图、语音或文件后,使用 PUT 将二进制内容上传至该地址,并在 X-Media-Upload-Token 请求头携带一次性令牌。旧客户端会得到 CLIENT_UPGRADE_REQUIRED,不会影响现有文本、图片、语音和文件消息链路。

状态说明:

  • available_on_demand:媒体已记录,等待客户调用解析接口。
  • processing:解析任务已下发给在线客户端,稍后等待 media.ready 回调或再次调用查询。
  • ready:媒体已转存完成,响应中的 url 可下载文件。
  • failed:转存失败,响应或 media.failed 回调会包含 error_code。常见值为 CLIENT_UPGRADE_REQUIRED,表示客户端未上报 media_upload_v1

常见 HTTP 错误:

  • 400:缺少 media_id
  • 404:媒体不存在、无权限访问,或媒体转存服务未开启。
  • 410:媒体已过期。
  • 409:媒体解析失败,例如客户端能力不足。
  • 503:Socket 媒体服务暂不可用。

会话列表

先调用会话列表接口获取 conversation_id,再用于消息发送或消息查询。

获取用户会话

  • 接口地址:GET /api/users
  • 必填参数secret

curl 'https://qw.minapp.xin/api/users?secret=#{secret}'

  • 返回数据:包含用户名称、conversation_idsend_secretmessage_secret 的列表。

获取群组会话

  • 接口地址:GET /api/groups
  • 必填参数secret

curl 'https://qw.minapp.xin/api/groups?secret=#{secret}'

  • 返回数据:包含群组名称、conversation_idsend_secretmessage_secret 的列表。