Search code examples
javascriptecmascript-6promisees6-promise

Nested promises not resolving properly, only returning promise when using decomposed promise handlers


There are similar questions like this, this, and this, but none help.

We have nested promises, but they aren't resolving. Instead of returning data from the innermost promise, the outermost promise returns a promise.

The goal is to decompose promise handlers into separate functions as illustrated below (e.g., requestDidSucceed, requestDidFail).

How can we do this while ensuring the outermost promise returns properly?

Codepen

https://codepen.io/Crashalot/pen/0ba95ebb26d0f68fb95ea065ef6af3dd?editors=0002

Code

class TestClass {
    translate() {
        // Create promise.
        let promise = $.Deferred();     

        let bm = new BatchManagerClass();

        bm.translate()
        .then( successResult => requestDidSucceed(promise, successResult) )
        .catch( errorResult => requestDidFail(promise, errorResult) );

        // Return promise.
        return promise;
    }

  
    requestDidSucceed(promise, successResult) {
        promise.resolve(successResult);
    }


    requestDidFail(promise, errorResult) {
        promise.reject(errorResult);
    }
}


class BatchManagerClass {
    translate() {
        // Create promise.
        let promise = $.Deferred();     

        let test = new ServiceClass();

        test.makeRequest()
        .then( successResult => requestDidSucceed(promise, successResult) )
        .catch( errorResult => requestDidFail(promise, errorResult) );

        // Return promise.
        return promise;
    }
    

     requestDidSucceed(promise, successResult) {
        promise.resolve(successResult);
     }


     requestDidFail(promise, errorResult) {
        promise.reject(errorResult);
     }
}


class ServiceClass {
    makeRequest() {
       let promise = $.Deferred();      

       promise.resolve('This works');

       return promise;
    }  
}


let test = new TestClass();

test.translate()
  .then( successResult => requestDidSucceed(successResult) )
  .catch( errorResult => requestDidFail(errorResult) );


function requestDidSucceed(successResult) {
  console.log('Success result: ' + successResult);
}


function requestDidFail(errorResult) {
  console.log('Failure result: ' + errorResult);
}

Solution

  • When calling a method of a class, this. must be added like this.requestDidSucceed().

    class TestClass {
        translate() {
            // Create promise.
            let promise = $.Deferred();     
    
            let bm = new BatchManagerClass();
    
            bm.translate()
            .then( successResult => this.requestDidSucceed(promise, successResult) )
            .catch( errorResult => this.requestDidFail(promise, errorResult) );
    
            // Return promise.
            return promise;
        }
    
      
        requestDidSucceed(promise, successResult) {
            promise.resolve(successResult);
        }
    
    
        requestDidFail(promise, errorResult) {
            promise.reject(errorResult);
        }
    }
    
    
    class BatchManagerClass {
        translate() {
            // Create promise.
            let promise = $.Deferred();     
    
            let test = new ServiceClass();
    
            test.makeRequest()
            .then( successResult => this.requestDidSucceed(promise, successResult) )
            .catch( errorResult => this.requestDidFail(promise, errorResult) );
    
            // Return promise.
            return promise;
        }
        
    
         requestDidSucceed(promise, successResult) {
            promise.resolve(successResult);
         }
    
    
         requestDidFail(promise, errorResult) {
            promise.reject(errorResult);
         }
    }
    
    
    class ServiceClass {
        makeRequest() {
           let promise = $.Deferred();      
    
           promise.resolve('This works');
    
           return promise;
        }  
    }
    
    
    let test = new TestClass();
    
    test.translate()
      .then( successResult => requestDidSucceed(successResult) )
      .catch( errorResult => requestDidFail(errorResult) );
    
    
    function requestDidSucceed(successResult) {
      console.log('Success result: ' + successResult);
    }
    
    
    function requestDidFail(errorResult) {
      console.log('Failure result: ' + errorResult);
    }