11/08/2018, 20:25

Sự khác biệt của 2 cách sử dụng Resolve/Reject trong Promise

Về cơ bản có 2 cách sử dụng Resolve/Reject trong Promise của Javascript: Sử dụng hàm static của class Promise: return Promise.reject() & return Promise.resolve() Sử dụng trong intance của Promise: return new Promise(function(resolve, reject) { resolve(); //or reject(); }) Đối ...

Về cơ bản có 2 cách sử dụng Resolve/Reject trong Promise của Javascript:

  • Sử dụng hàm static của class Promise: return Promise.reject() & return Promise.resolve()
  • Sử dụng trong intance của Promise:
return new Promise(function(resolve, reject) {
    resolve(); //or reject();
})

Đối với anh em mới cập nhật ES6 thì cái Promise này là một trong những thứ đáng quan tâm và nên học vì nó có nhiều ưu điểm tốt hơn Callback. Và dĩ nhiên anh em sẽ gặp 2 trường hợp ở trên thường xuyên. Tựu chung thì 2 cách gọi này đều là làm cùng mục đích, nhưng vẫn có trường hợp nếu không sử dụng khéo léo thì bug vẫn chòi ra như thường.

Cách tốt nhất là cho ví dụ luôn, ta có đoạn code như sau:

function stepOne(arg) {
    if (arg === 1) {
        return Promise.resolve('Done step one!');
    } else {
        return Promise.reject('Params invalid');
    }
}

function exec(arg) {
    return new Promise(function(resolve, reject) {
        stepOne(arg)
            .then(function(stepOneMessage) {
                if (stepOneMessage !== 'Done step one!') {
                    return Promise.reject('Result not match');
                } else {
                    return Promise.resolve('Done step two');
                }
            })
            .then(function(stepTwoMessage) {
                if (stepTwoMessage === 'Done step two') {
                    return resolve('Process complete');
                } else {
                    return Promise.reject('Process failed');
                }
            })
            .catch(function(error) {
                reject(error);
            });
     });
}

Ở hàm stepOne() anh em có thể return bằng cách 1 hay cách 2 đều được miễn là return type Promise.

Ta sẽ đến hàm exec(). Hàm này anh em thấy mình sử dụng cả cách 1 và cách 2. Vậy chúng nó khác nhau như thế nào? Giờ phân tích code nhé.

Ở hàm exec khi gọi stepOne, phần catch sẽ hứng lỗi của stepOne trả về, nhưng chưa hết, nó sẽ hứng lỗi của Promise.reject ở các hàm then ở trên nữa. Bây giờ ở trong hàm catch nếu đặt reject() là một message khác, ví dụ là Exec error đi, và một cái console.log(error) ở ngay trên dòng này, anh em sẽ thấy là dù ở trên mấy cái then nó có Promise.reject cái của nợ gì đi nữa thì khi gọi hàm exec và catch nó thì anh em luôn nhận được một message lỗi duy nhất Exec error, trong khi log ở trên thì đc nhiều nội dung lỗi khác nhau từ mấy cái Promise.reject đó.

Vậy giờ tôi muốn bắt được mấy cái lỗi linh động như trong code của exec chứ không phải chỉ là một nội dung chung chung này thì như nào? Ez. Chỉ cần đổi Promise.reject thành reject là được. Khi đó gọi hàm exec và catch thì anh em sẽ nhận được nhiều nội dung lỗi hơn, và chỉ khi stepOnelỗi thì nó mới xuống và trả về Exec error.

Đó là Promise.reject và reject. Đối với Promise.resolve và resolve, tư duy cũng tương tự. Khi return Promise.resolve thì data sẽ được hứng ở hàm then tiếp theo, còn muốn khi gọi hàm exec mà nhận được kết quả đó ngay thì đổi từ Promise.resolve sang resolve là được.

Chốt

Khi sử dụng lồng ghép giữa 2 cách trên thì đám resolve và reject là mấy thanh niên chuyên đảm trách việc hứa hẹn giao tiếp với thế giới bên ngoài, còn đám Promise.resolve và Promise.reject thì đảm nhiệm việc deal với anh em trong nhà (scope) đó thôi không có tiếng nói với người ngoài.

Còn khi 2 cách này được sử dụng ngang hàng chỉ khác cái trước cái sau thì sao? Case này cũng giống như mấy đứa sinh đôi, thằng nào ra trước (return trước) thằng đó làm anh, không quan trọng là từ static hay instance chui ra, miễn là Promise là được.

0