node.js - 从后端下载 csv 文件
问题描述
我正在尝试创建一个 csv 文件并插入我的数据并从浏览器下载它。我正在 express js 后端中创建 csv 文件,并将链接发送到 react js 前端以通过浏览器下载。
我正在使用快速 csv 插件将数据写入 csv。这是我的代码。
async function dataToCSV(data) {
var fileName = "report.csv";
var ws = await fileSystem.createWriteStream('../' + fileName);
var csv;
await fastcsv.write(data, { headers: true }).on("finish", function () {
console.log(ws);
csv = "<a href='../report.csv' download='report.csv' id='download-link'></a>";
}).pipe(ws);
return csv;
}
从该方法获得输出后,我将其发送到前端。
return dataToCSV(jsonData).then((response) => {
return {
headers,
statusCode: 200,
body: response,
type: 'binary'
};
}).catch((e) => {
return {
headers,
statusCode: 400,
body: {
error: e.message
}
};
})
前端得到如下给出的响应。
<a href='report.csv' download='report.csv' id='download-link'></a>
然后我使用以下代码通过浏览器使用 react js 下载它。
var div = document.createElement('div');
div.innerHTML = response.trim();
document.body.appendChild(div);
var downloadLink = document.getElementById('download-link');
if (downloadLink !== null) {
downloadLink.click();
}
document.body.removeChild(div);
文件是在后端创建的,我可以确认。但是当它从浏览器下载时,它会失败。日志中没有错误。浏览器说
失败 - 没有文件
我不明白为什么它会失败。我认为响应是在创建文件之前发送到前端的,或者它无法识别创建文件的路径。但我不确定。请帮我找到解决方案。
解决方案
.pipe()
不会返回 Promise,因此您await
不会做预期的事情。如果您想使用 Promises 等待流完成,请参阅stream.pipeline。
可能还有其他因素在起作用 - 例如,您的 HTTP 处理程序看起来一点也不像express
处理程序(即使您的问题包含“express”标签)。如果是无服务器函数(AWS Lambda?),您可能需要修改策略;根据平台,函数可能无法提供文件。
无论如何,最好构建一个 CSV 文件并将其直接发送到客户端,而不用写入文件系统,使用流(尽管在 AWS Lambda 上的 Node 中似乎不可能)。否则,始终可以将文件流式传输到云存储解决方案并为客户端提供预签名的 URL。
推荐阅读
- python - %H:%M:%S.%f 格式在我的熊猫数据框中不一致
- jspdf - jsPDF图像在错误的页面上一直以错误的顺序显示
- java - 每当我在色轮外滑动时,我的应用程序就会崩溃
- python - PyAudio 如何将频率范围分组在一起
- php - 客户使用礼品卡付款时绕过“计费”部分 - woocommerce
- objective-c - 在 Objective-C 中公开 Swift 枚举数组
- sql - 我想在每个相同的日期汇总数据
- javascript - 在云中存储变量的最佳方法是什么?
- sql - 如何从 db2 中的 xml 字符串中读取值
- prometheus - Prometheus 查询计算 avg_over_time up-time,但想忽略 down-time 小于 1 分钟