You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何使用Scrapy向API提交multipart/form-data类型POST请求?

搞定Scrapy提交multipart/form-data返回400的问题

嘿,我看你用requests能成功提交,但Scrapy就返回400,核心问题其实出在请求头的设置遗漏上,咱们一步步来解决:

先看你Scrapy代码的问题所在

你在requests代码里特意设置了Content-Type为MultipartEncoder的content_type(这个值包含了关键的boundary信息,API靠它解析multipart格式),但在Scrapy代码里只加了Content-Length,完全没加这个Content-Type头!这肯定会让API看不懂你的请求格式,直接返回400。

另外,Scrapy会自动计算并添加Content-Length,手动设置反而可能因为编码细节出现长度不匹配,建议直接删掉手动设置的Content-Length。

修正你的现有代码

把Scrapy代码改成这样,就能和requests一样成功了:

from requests_toolbelt.multipart.encoder import MultipartEncoder

# 替换成你的实际表单数据
data = {
    'client_id': 'c3cef7c66a1843f8b3a9e6a1e3160e20',
    'grant_type': 'password'
}

encoder = MultipartEncoder(
    data, boundary='-----------------------------265001916915724')
headers = {}
# 重点:必须添加这个包含boundary的Content-Type
headers['Content-Type'] = encoder.content_type

yield scrapy.Request(
    url=urls,
    method='POST',
    headers=headers,
    body=encoder.to_string(),
    callback=self.your_callback  # 记得换成你自己的回调函数
)

更省心的Scrapy原生写法

其实Scrapy本身就支持生成multipart/form-data请求,不用依赖requests_toolbelt,代码更简洁:

# 普通表单字段
formdata = {
    'client_id': 'c3cef7c66a1843f8b3a9e6a1e3160e20',
    'grant_type': 'password'
}

# 只要传个空的files参数,Scrapy就会自动用multipart/form-data编码请求
yield scrapy.FormRequest(
    url=urls,
    formdata=formdata,
    files={},
    callback=self.your_callback
)

这个写法不需要手动处理encoder和boundary,Scrapy会帮你搞定一切,适合没有文件上传的场景。

总结下为啥requests能成

因为requests里你完整传递了API需要的Content-Type头,而Scrapy代码里漏掉了这个关键信息,导致API无法解析你的请求格式。补上之后就能正常工作啦!

内容的提问来源于stack exchange,提问作者mtianyan

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.15 03:45:59