简体   繁体   中英

Why does my JSON file from my express server not download when I request with ajax?

I would like to set up my express server such that I can get the browser to prompt the user to download a JSON file when I send an Ajax GET request. I am able to get the file to download when I request a test route from the browser bar, but when I send the request from Ajax, it won't download, though the request returns 200 and I can see the contents of the file when I look in dev tools.

In the process of trying to get it to work, I thought maybe Express's res.download() function required a GET request, so I set it up so that the first request is a POST that sends the JSON data and gets the filename back, and then sends the filename as a parameter in the GET request.

Any help is greatly appreciated and I would be happy to provide more information if necessary.

Here is the code for the download route:

app.get("/generated-files/download/:file", function(req, res){
    const fileName = req.params.file;
    console.log(fileName);
    const filepath = path.join(__dirname, 'generated-files', fileName);
    res.download(filepath, fileName, function(err){
        if(err){
            console.log(err);
        }
        /*
        fs.unlink(filepath, function(err){
            if(err){
                console.log(err);
            }
        });*/
    });
});

Here is the test route:

app.get("/download-test", function(req, res){
    res.download(path.join(__dirname, 'generated-files', '01a6cbe0-ce2d-11ea-86bc-092eb628bcba.json'), '01a6cbe0-ce2d-11ea-86bc-092eb628bcba.json');

});

And here is the Ajax request:

                //begin first ajax request
                $.ajax({
                    contentType: 'application/json',
                    data: JSON.stringify(serializedCharacter),
                    success: function(ret){
                        console.log("Response Received:");
                        console.log(typeof ret + ":" + ret);
                        // begin second ajax request
                        $.ajax({
                            method: 'GET',
                            url: '/generated-files/download/' + ret,
                            success: function (ret){
                                console.log("delete successful");
                            },
                            error: function (jqxhr, ts, err){
                                console.log("something is wrong in delete");
                                console.log(jqxhr);
                                console.log("\n"+ts);
                                console.log("\n"+err);
                            }
                        });
                        // end second ajax request
                    },
                    error: function(jqxhr, textStatus, errorThrown){
                        console.log("Something is not right");
                        console.log(jqxhr);
                        console.log("\n"+textStatus);
                        console.log("\n"+errorThrown);
                    },
                    method: 'POST',
                    url: '/generated-files'
                });
                //end first ajax request

EDIT: OK, so I figured something out. I replaced the second Ajax request with this line:

document.location.href = '/generated-files/download/'+ret;

I suspect the problem was the Accept request header. The default Ajax Accept header is */* , while both the browser bar and aforementioned line had an Accept header of text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,*/*;q=0.8 . I may be wrong, in fact I am doubting this somewhat because I was under the impression that */* was supposed signal that the requestor would accept a response of any content type. If anyone could confirm this, or tell me why I am wrong, I would appreciate it greatly.

Ajax purpose is updating a part of web page without reloading the page, using the response data provided by server side app as json or xml. Here the response data will come back to the page itself, and can be used to render the page contents.

In downloading and page redirection the control goes out of the page. So this is not an Ajax use case.We can achieve those directly using plain javascript as you mentioned in the final section of your description.

For downloading the file your approach is correct by using

document.location.href= url

alternatively we can use

window.location = url

For page redirection we can achieve by

window.location.href = url

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM