【发布时间】:2020-07-28 17:01:53
【问题描述】:
我正在使用 Node 从服务器获取 PDF 并将其发送到我的 React 前端。然后我想在浏览器中的新选项卡中显示该 PDF。它工作得相当好,除了带有 PDF 的新选项卡的 URL 不理想。新标签的 URL 看起来像:blob:http://localhost:3000/71659,但我希望它看起来像 http://localhost:3000/71659.pdf。没有“blob”,并且带有 pdf 扩展名,就像我在网络上单击 pdf 时一样,就像这里的示例一样:https://file-examples.com/index.php/sample-documents-download/sample-pdf-download/
我当前处理 blob 保存和打开的代码是这样的:
.then((res) => {
console.log(res);
const file = new Blob([res.data], {
type: 'application/pdf'
});
//Build a URL from the file
const fileURL = URL.createObjectURL(file);
window.open(fileURL, '_blank');
});
这是我发送流的节点路由:
router.get('/openPDFFile', async (req, res) => {
console.log('we got to the server!! with: ', req.query);
const pdfFilename = req.query.pdf;
const pdfFilepath = `./path/to/pdf/${pdfFilename}`;
router.get();
const src = fs.createReadStream(pdfFilepath);
res.writeHead(200, {
'Content-Type': 'application/pdf',
'Content-Disposition': 'inline; filename=sample.pdf'
});
src.pipe(res);
});
现在我想知道是否可以简单地从 Node.js 创建到该 PDF 的路由,而不是通过网络发送流并将其转换为 blob。类似于/PDF/${pdfFilename}。然后我的 React 会在新标签页中打开那个 URL?
更新 - 这是我基于 x00 回答的最新节点路由:
router.get('/openPDFFile', async (req, res) => {
console.log('we got to the server!! with: ', req.query);
const pretty_PDF_name = req.query.pdf;
const pdfFilename = (await SDS.getPDFFileName({ pretty_PDF_name }))
.dataValues.sheet_file_name;
console.log('pdfFilename: ', pdfFilename);
const cleanPDFName =
pretty_PDF_name
.substring(0, pretty_PDF_name.length - 4)
.replace(/[ ,.]/g, '') + '.pdf';
const pdfFilepath = '\\path\\to\\file\\' + pdfFilename;
const fullFilePath = path.join(__dirname + '/../' + pdfFilepath);
console.log(cleanPDFName, fullFilePath);
router.get('/pdf/' + cleanPDFName, async (req, res) => {
res.sendFile(fullFilePath);
});
// router.get('/pdf/' + cleanPDFName, express.static(fullFilePath));
// const src = fs.createReadStream(pdfFilepath);
//
// res.writeHead(200, {
// 'Content-Type': 'application/pdf',
// 'Content-Disposition': 'inline; filename=sample.pdf'
// });
//
// src.pipe(res);
// return res.json({ fileuploaded: cleanPDFName });
});
我也看到了 express.static 方式,并且也在尝试。
【问题讨论】:
-
无法与反应部分对话,但我会在创建新资源(mime 类型“application/pdf”)时执行以下操作,该资源应该是 REST 可访问的:1. 将 fs 文件路径链接到一个身份证。 2. 将 ID 存储在数据库中,根据需要将 ID 与其他搜索/访问键关联 3. 从应用程序中,根据需要列出 IDS 4. 从应用程序通过重构解析为文件资源的 http URL 来获取特定 ID上面的 mime 类型
-
我想我实际上已经在做大部分事情了!! :) 我将唯一 ID 与数据库中的文件名一起保存。在前端,用户单击文件名并调用传递该文件名的节点服务器。所以我特别在节点代码上苦苦挣扎。我以为我在某个地方读到了可以在 Express 中创建到文件的路由。
app.get ('/pdf/filename.pdf')类似的东西... -
您真的需要
blob部分吗?为什么不只是window.open('/pdf/71659.pdf', '_blank');你想要某种预加载或错误处理之类的吗?那么有什么要求呢? -
看到这个答案:stackoverflow.com/a/14788331/560435 使用 req.ID 和一个只有 ID app.get('/openfile/:id' 的简单路由,你可以添加一个 fetch 到 DB ,解决路径,然后流式传输 pdf 或 http 302 以重定向到文件的完整 url
-
@x00 我不想要 blob 部分,这是我问题的全部基础。
/pdf/71659.pdf不是有效路径,但我想让它成为有效路径。
标签: javascript node.js pdf