POST请求触发django.utils.datastructures.MultiValueDictKeyError: 'email_id'问题排查
解决django.utils.datastructures.MultiValueDictKeyError: 'email_id'问题
这个错误的核心原因是你发起POST请求时,没有正确构造multipart/form-data格式的请求——这也是Postman能正常工作但你的upload.py不行的关键区别。Postman会自动处理文件上传的请求格式,而你手动写的代码用错了requests的参数传递方式。
问题出在哪?
你把表单字段(email_id)和文件对象(media_file)都塞进了data参数里:
data = {"email_id": "email@email.com", "media_file": open(video.file_path, "rb")} response = requests.post("/api/url", headers=headers, data=data)
这种写法下,requests不会把请求正确封装成multipart格式,导致后端Django无法解析出email_id字段,直接抛出MultiValueDictKeyError。另外你的headers里还有个拼写错误:"Authorizarion"应该是"Authorization",这可能还会引发认证相关的潜在问题。
正确的写法
你需要把表单数据和文件分开传递:表单字段用data参数,文件用files参数。requests会自动帮你设置正确的Content-Type: multipart/form-data请求头。修改后的upload.py代码如下:
# 修正拼写错误的Authorization头 headers = {"Authorization": "auth/key"} # 表单数据单独放在data字典里 data = {"email_id": "email@email.com"} # 文件单独放在files字典里,键名要和后端接收的字段名一致 files = {"media_file": open(video.file_path, "rb")} # 分别传递data和files参数 response = requests.post("/api/url", headers=headers, data=data, files=files)
额外优化建议
为了避免以后再遇到类似的KeyError,后端views里可以用.get()方法来获取参数,这样即使字段不存在也不会直接抛出错误,而是返回None或你指定的默认值,方便做参数校验:
def post(self, request): video_file = self.request.data.get('media_file') user_email_id = self.request.data.get('email_id') # 校验必填参数 if not video_file or not user_email_id: return Response({"error": "Missing required parameters: email_id or media_file"}, status=status.HTTP_400_BAD_REQUEST) file_storage = FileSystemStorage() saved_file_name = file_storage.save(str(uuid.uuid4()), video_file) # 后续业务逻辑...
内容的提问来源于stack exchange,提问作者Krish V
相关产品推荐
相关产品推荐

