TransWikia.com

Upgrade .then .catch to async await and try catch

Stack Overflow Asked by sonEtLumiere on January 20, 2021

I’m tryng to upgrade this code for a better maintenance, this code uploads two images to a server, i know it’s possible to get rid of those .catch, by applying async await functions, and try catch blocks, but it’s pretty confusing for me, any help will be apreciated.

this._uploadService.makeFileRequest(Global.url + "/upload-image1/" + response.product._id, [], this.filesToUpload1, 'image')
                .then((result: Product) => {
                  this.filesToUpload1 = null;          
                    this._uploadService.makeFileRequest(Global.url + "/upload-image/" + response.product._id, [], this.filesToUpload, 'image')
                    .then((result: Product) => {
                      this.filesToUpload = null;      
                      setTimeout( () => this._router.navigate(['/detail', this.saveProduct._id]), 800 );    
                    })
                    .catch(err => {
                      console.log(err);               
                      this._router.navigate(['/detail', this.saveProduct._id]);
                    })                                                                    
                })
                .catch(err => {
                  console.log(err);             
                  this._router.navigate(['/detail', this.saveProduct._id]);
                })

2 Answers

this._uploadService.makeFileRequest = function(){
    return new Promise(resolve => {
        // do logic of file request
        resolve(true);
    })
}
var waitForTime = function() {
    return new Promise(resolve => {
         setTimeout( () => {
            this._router.navigate(['/detail', this.saveProduct._id]),
            resolve(true)
        }, 800 );    
    })
}
var f = async function(){
  try {
    await this._uploadService.makeFileRequest(Global.url + "/upload-image1/" + response.product._id, [], this.filesToUpload1, 'image');
    await this.fileToUpload1 = null;
    await this._uploadService.makeFileRequest(Global.url + "/upload-image/" + response.product._id, [], this.filesToUpload, 'image')
    await this.fileToUpload = null;
    await waitForTime();
  }
  catch(e) {
    // error logic
  }
}
if (this.filesToUpload1 && this.filesToUpload) {
  f()
}

this might be another cleaner approach with async,await and promise

Answered by Kaustubh - KAY on January 20, 2021

I suggest using a pen and paper to draw a block diagram for the logic involved, i.e. which api gets called first, with what kind of data, then which api comes afterwards; also include any logical conditionals through branching.

After that, you should attempt to write something like

const aggregateFunction = async() => {
  try {
    const someResponse = await callFirstApi(); // return response
    await callSecondApi(someResponse); // use the response of the first api for the second api
    if (someConditional) {
      await callThirdApi(); // response not returned (i.e. when not required)
    }
  } catch (error) { // catch all errors from all await if they're not within another try-catch
    console.log(error);
  }
}

This pattern should eliminate all then and catch blocks. If you need more specific error handling for calling say a specific api, wrap function call inside another try-catch block, but everything should still be within the outer try-catch so that all errors will be caught regardless.

Answered by 98sean98 on January 20, 2021

Add your own answers!

Ask a Question

Get help from others!

© 2024 TransWikia.com. All rights reserved. Sites we Love: PCI Database, UKBizDB, Menu Kuliner, Sharing RPP