Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Downloading and saving files from server using AngularJS

I've got following issue and I can't find resolution. I created endpoint with Spring Boot and when I'm using Postman I'm getting response with image on body request.

But when I'm trying download and save file on computer using Angular and Blob and FileSaver my saved file is unable to read.

This is my angular controller:

vm.download = function (filename) {
    console.log("Start download. File name:", filename);
    $http.get('api/files/download/' + filename)
        .then(function (response) {
            console.log(data);
            var data = new Blob([response.data], {type: 'image/jpeg;charset=UTF-8'});
            FileSaver.saveAs(data, filename);
        })
}

and here's my endpoint:

@RequestMapping(value = "/files/download/{id:.*}", method = RequestMethod.GET)
@ResponseBody
@Timed
public void DownloadFiles(@PathVariable String id, HttpServletRequest request, HttpServletResponse response) throws IOException {

    MongoClient mongoClient = new MongoClient();
    DB mongoDB = mongoClient.getDB("angularspingproject");


    BasicDBObject query = new BasicDBObject();
    query.put("filename", id);

    GridFS fileStore = new GridFS(mongoDB, "fs");
    GridFSDBFile gridFSDBFile = fileStore.findOne(query);

    if (gridFSDBFile != null && id.equalsIgnoreCase((String) gridFSDBFile.getFilename())) {
        try {
            response.setContentType(gridFSDBFile.getContentType());
            response.setContentLength((new Long(gridFSDBFile.getLength()).intValue()));
            response.setHeader("content-Disposition", "attachment; filename=" + gridFSDBFile.getFilename());

            IOUtils.copyLarge(gridFSDBFile.getInputStream(), response.getOutputStream());
        } catch (IOException e) {
            throw new RuntimeException("IOError writting file to output stream");
        }
    }
}

My header:

Cache-Control: no-cache, no-store, max-age=0, must-revalidate
Content-Length: 316707
Content-Type: image/jpeg;charset=UTF-8
Pragma: no-cache
Server:Apache-Coyote/1.1
X-Application-Context : angularspingproject:8080
X-Content-Type-Options : nosniff
X-XSS-Protection: 1; mode=block
content-Disposition: attachment; filename=main_page.jpg

@Edit Problem resolved

    vm.download = function (filename) {
        $http.get('api/files/download/' + filename, {responseType:'blob'})
            .then(function (response) {
                console.log(response);
                var data = new Blob([response.data], {type: 'image/jpeg;charset=UTF-8'});
                FileSaver.saveAs(data, filename);
            })
    }

I added responseType: 'blob' to $http

like image 213
Michał Styś Avatar asked Jun 01 '16 15:06

Michał Styś


1 Answers

I'd guess that you're not getting a byte array back from your $http.get call. Try adding:

vm.download = function (filename) {
var config = {headers: {
        'Accept': "image/jpeg"
    }
};
$http.get('api/files/download/' + filename, config).then(function (response)             { 
       var myBuffer= new Uint8Array( response.data );

    var data = new Blob([myBuffer], {type: 'image/jpeg;charset=UTF-8'});
    FileSaver.saveAs(data, filename);
        })
}
like image 107
Mike Feltman Avatar answered Oct 22 '22 09:10

Mike Feltman