Search code examples
angularpromisees6-promise

Angular Promise with condition


I don't want to hit the endpoint (getUserInfo) if I already have value in my variable, I wrote a code like below but there is duplicate code and wanted to see if anyone has a better way of writing this:

let report;
if (this.userInfo) {
   report = {
    ReportType: reportType,
    ReportID: id,
    ReportFormat: format,
    ReportName: `${reportType}_${id}`,
    Filters: shouldNotParseFilters ? filterContent : [],
    ViewFields: columns || [],
    OrgName: this.userInfo[0].orgname,
    FullName: this.userInfo[0].fullname
  } as SavedReport;
  if (!shouldNotParseFilters) this.reportFilterService.mapReportFilters(<ReportFilterContext>filterContent, report);
  report.Filters.push({ 'maxitems': [-1] });
  this.nrcService.downloadReport(report, fileName).subscribe({ error: err => this.nrcService.handleError(err) });
}
else {
  this.nrcService.getUserInfo().then(data => {
    this.userInfo = data;
     report = {
      ReportType: reportType,
      ReportID: id,
      ReportFormat: format,
      ReportName: `${reportType}_${id}`,
      Filters: shouldNotParseFilters ? filterContent : [],
      ViewFields: columns || [],
      OrgName: data[0].orgname,
      FullName: data[0].fullname
    } as SavedReport;
    if (!shouldNotParseFilters) this.reportFilterService.mapReportFilters(<ReportFilterContext>filterContent, report);
    report.Filters.push({ 'maxitems': [-1] });
    this.nrcService.downloadReport(report, fileName).subscribe({ error: err => this.nrcService.handleError(err) });
  })
 }

Solution

  • In this case I would suggest to use async/await to solve your needs:

    // Add `async` here 
    async your_function_name () {
        ...
        let report;
        if (!this.userInfo) {
            // Waits until your user info is loaded
            this.userInfo = await this.nrcService.getUserInfo();
        }
        report = {
            ReportType: reportType,
            ReportID: id,
            ReportFormat: format,
            ReportName: `${reportType}_${id}`,
            Filters: shouldNotParseFilters ? filterContent : [],
            ViewFields: columns || [],
            OrgName: this.userInfo[0].orgname,
            FullName: this.userInfo[0].fullname
        } as SavedReport;
    
        if (!shouldNotParseFilters) {
            this.reportFilterService.mapReportFilters(<ReportFilterContext>filterContent, report);
        }
    
        report.Filters.push({ 'maxitems': [-1] });
        this.nrcService.downloadReport(report, fileName).subscribe({ error: err => this.nrcService.handleError(err) });
    
    }
    

    If you're not familiar with async/await see here ;-)

    Another option is to use Promises without async/await, but it does not look so nice:

    let report;
    // Create a new promise, which resolves directly
    let promise = new Promise(r => r());
    if (!this.userInfo) {
        // Assigns the loading promise to the promise variable
         promise = this.nrcService.getUserInfo().then(data => {
            this.userInfo = data;
        });
    }
    // Waits until the promise is resolved
    promise.then(() => {
        report = {
            ReportType: reportType,
            ReportID: id,
            ReportFormat: format,
            ReportName: `${reportType}_${id}`,
            Filters: shouldNotParseFilters ? filterContent : [],
            ViewFields: columns || [],
            OrgName: this.userInfo[0].orgname,
            FullName: this.userInfo[0].fullname
        } as SavedReport;
    
        if (!shouldNotParseFilters) {
            this.reportFilterService.mapReportFilters(<ReportFilterContext>filterContent, report);
        }
    
        report.Filters.push({ 'maxitems': [-1] });
        this.nrcService.downloadReport(report, fileName).subscribe({ error: err => this.nrcService.handleError(err) });
    
    });