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

如何解决Django上传图片转base64时出现的InMemoryUploadedFile类型错误

报错原因

TypeError: expected str, bytes or os.PathLike object, not InMemoryUploadedFile报错的核心是:request.FILES['propic']拿到的是Django封装的InMemoryUploadedFile内存上传文件对象,你直接把这个对象传给了open()函数,但open()仅接受文件路径、字节、类路径对象作为入参,无法识别这个Django自定义的上传文件类。
实际上Django的上传文件对象本身就支持直接读取字节内容,完全不需要调用open()走读取本地文件的逻辑。

修复后的视图代码

你需要修改两处逻辑:一是去掉open()调用直接读取文件内容,二是存数据库时传入转换完成的base64字符串,而非原上传文件对象:

import base64
from django.shortcuts import render
from django.http import HttpResponseRedirect
from django.urls import reverse
from django.contrib.auth import login
from django.db import IntegrityError

def signup(request):
    if request.method == "POST":
        username = request.POST["username"]
        fullname = request.POST["fullname"]
        password = request.POST["password"]
        email = request.POST["email"]
        area = request.POST["area"]
        school = request.POST["school"]
        propic = request.FILES["propic"]

        # 直接读取上传文件对象的字节内容
        binary_file_data = propic.read()
        base64_encoded_data = base64.b64encode(binary_file_data)
        # 可选:补充图片类型前缀,方便前端直接用该字符串渲染图片,不需要可以删除前缀拼接逻辑
        base64_message = f"data:{propic.content_type};base64,{base64_encoded_data.decode('utf-8')}"

        try:
            # propic字段传入转换好的base64字符串,不要传原上传文件对象
            user = User.objects.create_user(
                username=username, 
                email=email, 
                password=password, 
                area=area, 
                school=school, 
                propic=base64_message
            )
            user.save()
        except IntegrityError:
            return render(request, "alumnas/register.html", {
                'message':"Username taken"
            })
        login(request, user)
        return HttpResponseRedirect(reverse("index"))
    else:
        return render(request, "alumnas/register.html")

注意事项

  • 请确认你扩展的User模型中propic字段为TextField类型:base64编码后的图片字符串长度很长,CharField的最大长度限制无法满足存储需求。
  • 可根据需求增加上传校验逻辑,避免非法文件提交:
    # 仅允许图片格式上传
    ALLOWED_IMG_TYPES = ["image/jpeg", "image/png", "image/gif"]
    if propic.content_type not in ALLOWED_IMG_TYPES:
        return render(request, "alumnas/register.html", {"message": "仅支持上传JPG、PNG、GIF格式的图片"})
    # 限制图片大小不超过2M
    if propic.size > 2 * 1024 * 1024:
        return render(request, "alumnas/register.html", {"message": "图片大小不能超过2M"})
    
  • 非特殊需求不建议将base64图片直接存储在数据库中,会占用大量存储空间、降低查询效率,更推荐将图片存到本地静态目录或对象存储服务,数据库仅存储图片的访问路径。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.10.05 19:09:00