nodeJS prevent timeout on res.download

纵然是瞬间 提交于 2020-01-23 08:07:26

问题


I have a POST call to my nodeJS server that searches for some data on the mongo database and returns a CSV file with the requested data. The problem is that the data search and processing exceeds the 2 minute nodeJS default timeout.

On a diferent scenario y used:

res.writeHeader(200,'application/json');            
res.write('starting fetch .... ');

to keep alive the request and prevent the timeout from the client by sending some res.write(''); from time to time.

Now Im using res.download() to download the resulting csv file, so not just sending JSON as response.

Tried to use this solution like this:

res.writeHeader(200,'application/json');            
res.write('starting fetch .... ');
res.download()

But i get the "headers already sent" error.

Any idea on how to prevent the timeout until the data is processed and the file download is done ?

Thanks in advance


回答1:


A few small things first of all, i think it's supposed to be res.writeHead() instead of res.writeHeader(). Secondly once you send the headers you can not send them again. You are getting the error because res.download() uses res.sendFile() which re-sends the headers. You can't use res.download() or res.sendFile() or res.send() because all of these three methods implicitly set the headers and send as part of the response. You'll need to use a combination of res.writeHead() ,res.write() and res.end(). I am just GET so i can test it from the browser, you can use post obviously.

router.get('/test', function (req,res,next) {
 res.writeHead(200, {'Content-Type': 'application/json',
         'Content-Disposition': 'attachment',
         'filename':'package.json'
 });

 fs.readFile("package.json",function (err,data) {
     if (err) {
         throw err;
     }else{
         setTimeout(function () {
             res.write(data);
             res.end()
         },200000);

     }


 });

 function keepBusy(){
     if(!res.finished){
         res.writeProcessing();
         setTimeout(keepBusy,1000)
     }

 }

 setTimeout(keepBusy,1000);

});

This works fine for me. res.writeProcessing() sends the 102 status code. It is recommended for requests that last greater than 20 second but this blog post says that

102 has been left out more recent revisions of HTTP specifications

but it works fine for me in most browsers. If you have some control over the client as well there can be a much better and reliable solution.



来源:https://stackoverflow.com/questions/37317781/nodejs-prevent-timeout-on-res-download

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!