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

如何用Django和boto3下载AWS S3文件?遇问题求助

解决Django中付费用户下载AWS S3文件的问题

一、修复FileResponse方法的AttributeError错误

原代码直接使用open(file, 'rb')读取文件是错误的——当Django用AWS S3作为存储后端时,obj.file是S3存储的文件对象,并非本地文件,Python内置open()无法直接读取。

修改views.py的下载函数:

def download_file(request, id, order_id):
    obj = Product.objects.get(id=id)
    order = Order.objects.get(order_id=order_id)
    # 先完成订单有效性校验(如确认已支付、用户匹配等)
    file_stream = obj.file.open('rb')
    response = FileResponse(file_stream)
    # 设置响应头触发浏览器下载动作
    response['Content-Disposition'] = f'attachment; filename="{obj.file.name.split("/")[-1]}"'
    response['Content-Type'] = 'application/octet-stream'
    return response

核心说明:

  • obj.file.open('rb')通过Django的S3存储后端直接获取文件二进制流,无需本地缓存
  • 添加Content-Disposition头可强制浏览器弹出下载框,而非直接打开文件

二、修复boto3预签名URL的NoSuchKey错误

问题原因

错误提示Key: files/it_report_edited.docx不存在,说明你传入的S3文件Key与实际存储路径不符。通常Django配置S3时,文件会自动添加media/前缀,实际Key应为media/files/it_report_edited.docx。

修复代码

def download_file(request, id, order_id): 
    obj = Product.objects.get(id=id)
    order = Order.objects.get(order_id=order_id)
    # 订单有效性校验(必须步骤)
    
    client = boto3.client(
        's3',
        aws_access_key_id=os.environ.get('AWS_ACCESS_KEY_ID'),
        aws_secret_access_key=os.environ.get('AWS_SECRET_ACCESS_KEY')
    )
    bucket_name = os.environ.get('AWS_STORAGE_BUCKET_NAME')
    
    # 从Django存储后端获取文件的实际S3 Key(自动适配配置的前缀)
    file_key = obj.file.storage.object_name(obj.file.name)
    
    url = client.generate_presigned_url(
        'get_object',
        Params={'Bucket': bucket_name, 'Key': file_key},
        ExpiresIn=600
    )
    return HttpResponseRedirect(url)

额外检查项

  1. 登录AWS S3控制台确认文件的实际Key,是否包含media/前缀
  2. 检查Django的S3配置是否正确:
    # settings.py示例
    AWS_STORAGE_BUCKET_NAME = '你的存储桶名称'
    AWS_LOCATION = 'media'
    DEFAULT_FILE_STORAGE = 'storages.backends.s3boto3.S3Boto3Storage'
    
  3. 确保boto3使用的IAM用户拥有s3:GetObject权限

两种方法的适用场景

  • FileResponse方法:适合需要在Django层处理文件流的场景(如添加自定义校验、修改文件内容),但会占用服务器带宽和内存
  • 预签名URL方法:更高效,直接引导用户从S3下载,减轻Django服务器压力,适合大文件下载

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.26 12:47:42