mongodb 无法使用React JS从Mongo-db下载pdf文件(以二进制数据格式存储)

kq0g1dla  于 2023-01-08  发布在  Go
关注(0)|答案(1)|浏览(108)

我用express-fileuplod上传Mongodb上的pdf文件。我在前端下载该pdf文件时遇到了问题。
下载PDF后,我收到以下提示:"Error. Failed to load PDF document"
MongoDB上的表格数据:

_id: ObjectId('63b7494295b850d0452a6a81')                                     
username: "sita"                                                                 
email: "sita@gmail.com"                                                            
dob: 2023-01-01T00:00:00.000+00:00                                                
city: "city"                                                                  
address: "add"                                                                   
services: Array                                                                     
0: "Demat"                                                                            
pancard: Object                                                                 
    Data:BinData(0,'JVBERi0xLjcKCjQgMCBvYmoKPDwKL0ZpbHRlciAvRmxhdGVEZWNvZGUKL0xlbmd0aCAzMDEzNQo+PgpzdHJlYW0KeJztvU1247gS…')                                                
    ContentType: "application/pdf"                                                   
createdAt: 2023-01-05T22:03:46.893+00:00                                       
updatedAt: 2023-01-05T22:03:46.893+00:00                                             
__v: 0

[React代码:]

React.useEffect(()=>{
    const fetchClient = async () =>{
        const res = await axios.get('/users/sita@gmail.com');
        setData(res.data.pancard.Data.data);
        setContentType(res.data.pancard.contentType)
    }

   fetchClient()       
},[userdetail]);

const downloadPdf = (filename, contentType) => {
      const file = new Blob([data], { type: contentType });
      saveAs(file, "pancard.pdf") 
      //const fileURL = URL.createObjectURL(file);
      //window.open(fileURL);       
  };

在JSX中调用downloadpdf()方法
〈button class=“btn btn-primary button”onClick={下载页面('pancard',内容类型)}〉下载
该文件还在循环中被无限次下载

2lpgd968

2lpgd9681#

    • 溶液1**

data只是一个数组,我们需要转换为Uint8Array

const file = new Blob([new Uint8Array(data)], { type: contentType });
saveAs(file, "pancard.pdf")
    • 溶液2**

我们必须在另一个路径上提供文件,它不能与json数据一起发送
后端

// Example in Express
app.get('/get_file', (req, res) => {
  // Query user
  res.set('Content-Disposition', 'attachment; filename="test.pdf"');
  res.set('Content-Type', 'application/pdf');
  res.send(user.pancard);
}

前端

fetch('http://localhost:8000/get_file')
      .then(res => res.blob())
      .then(data => {
        saveAs(data, 'test.pdf');
      })

对于大文件,由于Content-Disposition头文件,解决方案2更好。文件数据通过此头文件安全传输(我不太了解底层机制,请进一步研究)
另外注意两件事:

  • 不建议将文件数据直接保存到数据库中,而是保存为静态文件,并且只保存数据库路径。
  • 如果文件大小超过16MB,我们需要使用GridFS for Mongo。更多详细信息:https://www.mongodb.com/docs/manual/core/gridfs/

相关问题