Retrieve the file from the REST API without using the window.open method

I'm looking for a method to download files from an API without using window.open(). I want the download process to start immediately upon calling the API.

Currently, I am downloading an .xls file generated by a REST API using window.open()

API Endpoint

@GetMapping("/applications/export")
    @Timed
    public ResponseEntity<byte[]> exportApplicationsList() {
        log.debug("REST request to export applications list");

        byte[] result = applicationService.generateApplicationsListAsExcel();

        if (result == null) {
            return ResponseEntity.status(500).build();
        }

        String date = LocalDateTime.now().format(DateTimeFormatter.ofPattern("dd_MM_yyyy_HH_mm"));

        return ResponseEntity.ok()
            .header("Content-Disposition", "attachment; filename=liste_applications_" + date + ".xls")
            .contentLength(result.length)
            .contentType(MediaType.APPLICATION_OCTET_STREAM)
            .body(result);
    }

Service

/**
     * Generate xls file from applications list.
     *
     * @param applications list of applications
     */
    public byte[] generateApplicationsListAsExcel() {

        log.info("Generating xls file of the applications list");

        List<Application> applications = applicationRepository.findAll();
        Collections.sort(applications);

        try (InputStream is = new FileInputStream(ResourceUtils.getFile("classpath:jxls-templates/liste_applications_template.xls"))) {

            try (ByteArrayOutputStream os = new ByteArrayOutputStream()) {
                Context context = new Context();
                context.putVar("applications", applications);
                JxlsHelper.getInstance().processTemplate(is, os, context);
                return os.toByteArray();
            } catch (IOException e) {
                log.error(e.toString());
            }

        } catch (IOException e) {
            log.error(e.toString());
        }

        return null;
    }

Invocation

exportApplicationsList(): void {
        window.open('/api/applications/export');
    }

Answer №1

If you need to retrieve a file as a blob from the backend and then download it, you can achieve this by using thefile-saver library.

this.http.get(`/api/applications/export`, params, { responseType: 'blob' })
  .subscribe((resp: any) => {
    saveAs(resp, `filename}.xlsx`)
});

Answer №2

Simple fix :

Redirect the user to the specified URL using window.location.href

Answer №3

If you are looking for a solution, I recommend using the file-saver package.

this.utilityService.fetchFile(id).subscribe(
  response => {
    saveAs(response, filename);
  },
  error => {
    console.error(error);
  });

For handling the backend:

@GetMapping("download-file/{id}")
public ResponseEntity<?> downloadRequestedFile(@PathVariable(value = "id") Long fileId) {

    final Optional<FileEntity> requestedFile = fileRepository.findById(fileId);
    if (!requestedFile.isPresent()) {
        return ResponseEntity.badRequest().body(getErrorResponse("Dfile not found"));
    }

    ByteArrayOutputStream downloadedInputStream = cloudStorage.downloadFile(requestedFile.get().getLink());

    return ResponseEntity.ok()
            .contentType(contentType(requestedFile.get().getName()))
            .header(HttpHeaders.CONTENT_DISPOSITION, "attachment; filename=\"" + requestedFile.get().getName() + "\"")
            .body(downloadedInputStream.toByteArray());
}

Similar questions

If you have not found the answer to your question or you are interested in this topic, then look at other similar questions below or use the search

Is there a way to compile my Angular application using `npm run build : production` instead of the conventional `npm run build --production` command?

Greetings! My Angular application is currently being built using the following command: npm run build --production Alternatively, it can be built using the command: npm run build -- --c production However, I am interested in building my application using ...

The Chart.js graph fails to appear when placed within an ngIf directive

I have encountered an issue with my simple scatter line chart created using Chart.js within a bootstrap panel. It works perfectly fine until I place it inside an ngIf div. Has anyone faced this problem before? Is there a solution to make the chart display ...

Having trouble achieving the desired effect with inline block

I'm having some trouble creating a simple store page. One of the products is supposed to look like this: However, it's currently showing up like this: I've been attempting to use inline block so that I can have the negotiate button and pro ...

Error in Protractor Typescript: The 'By' type does not share any properties with the 'Locator' type

https://i.stack.imgur.com/8j2PR.png All the different versions Error. Protractor version : 5.2.0 npm : 3.10.10 node :6.9.5 typescript :2.6.0 The 'By' type does not share any properties with the 'Locator' type What is the solution to ...

Can we potentially extract shared components of a template?

As an example, I have numerous components designed for paged collections. Here is a template showcasing this: <div *ngIf="!isFormVisible"> <button class="btn" [ngClass]="{'btn-info': filtered, 'btn-default': !filtered}" (c ...

A guide on verifying the static characteristics of a class with an interface

When it comes to converting a constructor function in JavaScript to TypeScript, there are some important considerations to keep in mind. function C() { this.x = 100; } C.prototype = { constructor: C, m() {} }; C.staticM = function () {}; Here ...

An error occurs with webpack during postinstall when trying to load TypeScript

I have created a custom package that includes a postinstall webpack script as specified in my package.json file: "scripts": { ... "postinstall": "webpack" } The webpack configuration looks like this: const path = require('path'); ...

The TypeScript compiler is indicating that the Observable HttpEvent cannot be assigned to the type Observable

Utilizing REST API in my angular application requires me to create a service class in typescript. The goal is to dynamically switch between different url endpoints and pass specific headers based on the selected environment. For instance: if the environmen ...

The type 'Data' is lacking the following attributes from its definition

Being a newcomer to Angular 8, I can't figure out why this error is popping up. If you have any suggestions on how to improve the code below, please feel free to share your tips. The error message reads: Type 'Data' is missing the follo ...

Switching services in test cases with ReflectiveInjector

Can the provider be changed using ReflectiveInjector in the same context? I require B to utilize a different value for the second test. A & B are both services... let injector: ReflectiveInjector; beforeEach(() => { injector = ReflectiveInjec ...

Deciphering Route Parameters within Angular 2

Recently diving into Angular 2, I stumbled upon this resource, which details various methods for creating route links. 1. <a [routerLink]="[ '/path', routeParam ]"> 2. <a [routerLink]="[ '/path', { matrixParam: 'value&ap ...

Modifying Views on the Fly with Ionic 2

When the toggle button on the page is clicked, the current page view will switch to a different HTML layout. I attempted to modify @Page, but after it loads once, I am unable to change it again. @Page({ templateUrl: isTrue ? 'build/pages/detail/ ...

Guide on invoking JSP located in a subdirectory using a servlet that is also situated in a subdirectory

In my Netbeans project, I have a servlet named myServlet.java in the "Source Packages" directory within the com.login.controller folders. In the "Web Pages" section, there are two JSPs - login.jsp located inside the folder "jsp/login/login.jsp" and home.js ...

Is it necessary to have a Test Adapter in VSTS in order to include a code coverage report?

Currently, I am producing code coverage using Karma-coverage and hosting my output coverage folder on an http-server for local viewing. My question is: How can I display this report on the VSTS code coverage tab? Do I need to re-format my coverage result ...

The current project does not support the feature you are trying to use when calling getWindowHandles()

Currently, I am utilizing Appium version 1.4.16.1, Selenium 2.53.0, and java-client 2.1.0 An issue has arisen where an error message is displayed: "org.openqa.selenium.WebDriverException: Not yet implemented. To assist us in resolving this issue, plea ...

Having trouble obtaining React 15.6.1 type definitions: "ERROR: Repository not found."

Trying to set up the type definitions for React 15.6.1, but encountering an error: $ npm install --save @types/react npm ERR! git clone <a href="/cdn-cgi/l/email-protection" class="__cf_email__" data-cfemail="88efe1fcc8efe1fce0fdeaa6ebe7e5">[email&# ...

Is there a method to make changes to files on a deployed Angular application without the need to rebuild?

After deploying my Angular application on a production environment using the command npm run build --prod --base -href, I now need to make changes to some static HTML and TypeScript files. However, since the app is already bundled and deployed, I'm un ...

Excluding the "id" attribute in a JSON schema while generating it from a POJO with the help of Jackson

Is there a way to delete the id field ("id" : "urn:jsonschema:org:gradle:Person") from a JSON schema that was created using Jackson? Here is the Generated Schema: { "type" : "object", "id" : "urn:jsonschema:org:gradle:Person", "properties" : { ...

Angular's ngbdatepicker encountering RangeError: Call stack size has surpassed maximum limit

Below is the code snippet used in my angular component template. <input type="text" (click)="dp.toggle()" ngbDatepicker #dp="ngbDatepicker" id="myDatePicker" autocomplete="off" placeholder= ...

Incorporating a Link/Template Column into Your Unique Table Design

I built a table component following the guidelines from this article: Creating an Angular2 Datatable from Scratch. While I have added features like sorting and paging to suit my app's needs, I am struggling with implementing a "Template column" to al ...