【问题标题】:Why won't my file download with nodejs?为什么我的文件不能用 nodejs 下载?
【发布时间】:2016-06-29 09:16:34
【问题描述】:

我从网页向 nodejs 路由器发送一个 xmlhttprequest,如下所示:

var name = $(this).find('td:eq(0)').html();
        var docNum = $('#docNum').val();
        //alert("fileName=" + name + "&docNum=" + docNum);
        xhttp = new XMLHttpRequest();
        xhttp.onreadystatechange = function() {
            if (xhttp.readyState == 4 && xhttp.status == 200) {
                isUnique = xhttp.responseText;
                if(isUnique == "false"){
                    alert("ID is not unique please pick another document ID ");
                }else{
                    $("form#docForm").submit();
                }
            }
        };
        xhttp.open("POST", "/downloadDocument", true);
        xhttp.setRequestHeader("Content-type", "application/x-www-form-urlencoded");
        var params = "fileName=" + name + "&docNum=" + docNum;
        xhttp.send(params);

这工作正常,请求到达路由器并且路由器能够正确读取这两个变量。

这是路由器代码中不能正常工作的部分:

router.post("/downloadDocument", function(req, res){
        var doc = req.body.docNum;
        var fileName = req.body.fileName;
        var document = Document.findOne({Name: fileName, Dossier: doc}, function(err, obj){
            var path = obj.Name;
            console.log(path);
            fs.writeFile(obj.Name, obj.File);
            res.download("./" + obj.Name);
        });
    });

它所做的只是将我重定向到上一页,它不下载文件,即使文件存在,我也不知道为什么。

我也尝试过使用

  var filestream = fs.createReadStream(obj.File);
  filestream.pipe(res); 

而不是 res.download

这是此请求的控制台输出:

Apples.jpg
POST /downloadDocument 200 4.814 ms - -
POST /dossierEdit 302 12.898 ms - 62 #This part concerns me and redirects me while i do not ask for this page in my code
GET /dossiers 304 20.793 ms - -
GET /public/stylesheets/css/bootstrap.min.css 304 2.737 ms - -
GET /public/stylesheets/css/simple-sidebar.css 304 2.921 ms - -
GET /public/stylesheets/style.css 304 2.327 ms - -
GET /public/stylesheets/css/font-awesome.min.css 404 3.502 ms - 56
GET /public/css/style.css 404 1.097 ms - 33
GET /public/stylesheets/css/font-awesome.min.css 404 0.492 ms - 56
GET /public/css/style.css 404 1.107 ms - 33

澄清一下,我的目标是将文件发送到客户端,而不是保存到服务器。

【问题讨论】:

  • Document.findOne()的回调函数执行了吗?你看到日志中的路径了吗? (由于 console.log(path) )
  • 是的,回调被执行,我看到了路径,它显示为我输入的文件名,如果我尝试下载不存在的文件,我也会收到控制台错误跨度>
  • findOne 是一个使用 Mongoose 的 mongoDB 请求,我将文件存储在 mongo 数据库中,使用 findOne 函数请求我想要下载的文件,然后使用 fs.writeFile 创建一个本地文件(它可以工作因为我看到文件出现在本地,我可以打开它们)现在我尝试做的是下载它们,这是行不通的。
  • 澄清一下,我的目标是将文件发送到客户端,而不是保存到服务器。

标签: javascript node.js download


【解决方案1】:

我认为有几个问题。

  1. Files cannot be downloaded via an ajax call
  2. fs.writeFile(obj.Name, obj.File) 调用是异步的,因此即使 (1) 不是问题,文件也可能不会 在调用res.download("./" + obj.Name) 时出现。请改用fs.writeFileSync
  3. 您可能会被重定向到上一页,因为在 ajax 调用返回时发生了 $("form#docForm").submit() 调用,这会将表单提交到其他页面。

要解决您的问题,请尝试将包含发布数据的实​​际表单提交到“/downloadDocument”端点,而不是进行 ajax 调用。

希望对你有帮助。

【讨论】:

  • 我现在使用 $,post from jquery 发送一个发布请求,它可以工作,并将数据发送回页面,我可以使用回调函数打印它,但它没有下载文件,它只是流回数据,我现在使用 createReadStream 和 filestream.pipe(res) 将数据发回。关于如何解决这个问题的任何想法?
  • 我猜只是做一个普通的帖子不是一种选择,在这里?看看download.js,您可以使用它从您发回的数据中创建一个 blob 并将其下载到客户端站点上。它不适用于旧版浏览器,因此如果您需要更多浏览器支持,请考虑其他选项。
  • 我可以尝试一个普通的帖子,但这需要一个不必要的隐藏表单,我认为这很丑陋而且很难做到,因为我让表格行可点击以下载文件,但首先我会检查download.js,谢谢你的帮助,对我帮助很大:)
  • 这解决了它,使用 jquery 将页面附加到一个表单,并且只是该表单的常规发布提交,非常感谢:D
猜你喜欢
  • 2016-05-11
  • 2011-09-13
  • 2022-01-10
  • 1970-01-01
  • 1970-01-01
  • 2019-02-07
  • 1970-01-01
  • 2022-09-29
  • 2016-10-10
相关资源
最近更新 更多