Azure函数应用中Blob存储PDF下载后Octet Stream转PDF问题求助
解决Azure Blob存储PDF上传后下载无法解析的问题
我来帮你排查这个问题,核心问题出在下载时的HTTP响应头设置以及临时文件的写入模式上,咱们一步步来解决:
问题根源分析
- 上传环节其实大概率是正常的(你能在Storage Explorer里打开PDF说明Blob本身没问题),但下载时返回的二进制数据没有告诉浏览器它是PDF类型,导致浏览器默认识别为
application/octet-stream,无法正确解析。 - 保存临时文件时如果用了文本模式写入二进制数据,会破坏PDF的字节结构,导致文件损坏。
解决方案
1. 优化上传代码(可选,避免重复上传报错)
虽然上传功能正常,但可以加上overwrite=True避免重复上传同文件名文件时报错,同时确保以二进制读取文件内容:
blob_service_client = BlobServiceClient.from_connection_string(connect_str) container_name = 'testblobstore123' file = req.files['file'] try: blob_client = blob_service_client.get_blob_client(container=container_name, blob=file.filename) # 以二进制读取文件内容并上传,开启覆盖模式 blob_client.upload_blob(file.read(), overwrite=True) except Exception as e: print(e) return "Unspecified Error"
2. 修复下载逻辑:设置正确的响应头
在下载Blob后返回给客户端时,必须设置Content-Type为application/pdf,同时通过Content-Disposition指定文件名和打开方式(在线预览或下载)。以Azure Functions的HTTP触发为例:
from flask import make_response blob_service_client = BlobServiceClient.from_connection_string(connect_str) container_name = 'testblobstore123' file_name = req.form['file'] blob_client = blob_service_client.get_blob_client(container=container_name, blob=file_name) # 获取Blob的二进制数据 data = blob_client.download_blob().readall() # 构建正确的HTTP响应 response = make_response(data) # 告诉浏览器这是PDF文件 response.headers['Content-Type'] = 'application/pdf' # 可选:设置为inline则在线预览,attachment则触发下载 response.headers['Content-Disposition'] = f'inline; filename="{file_name}"' return response
3. 修复临时文件保存:用二进制模式写入
如果要将下载的二进制数据保存为本地临时文件,必须使用wb(二进制写入)模式,否则会损坏文件:
# 保存临时PDF文件 with open('temp.pdf', 'wb') as temp_file: temp_file.write(data)
这样修改后,浏览器就能正确识别PDF文件,临时文件也不会损坏了。
内容的提问来源于stack exchange,提问作者IrtzaSuhail
相关产品推荐
相关产品推荐

