Почему Promise возвращается и разрешается при отклонении - PullRequest
0 голосов
/ 30 апреля 2018

Может кто-нибудь объяснить, почему Promise запускает функцию then () (а также функцию catch ()) при вызове reject?

Когда вызывается разрешение, только тогда () запускается - ОК

Когда вызывается reject, вызываются функции then () и catch () - Проблема

static logIn(email, password) {

    async function getSession () {

        let data = new FormData();
        data.append('email', email);
        data.append('password', password);

        const response = await fetch(
            url,
            {
                method: 'POST',
                mode:   'cors',
                body:   data,
                cache:  'no-cache',
                headers: {
                    'Accept': 'application/json',
                },
            }
        );

        const json = await response.json();

        return json;
    }

    return new Promise((resolve, reject) => {
        getSession()
            .then(json => {
                if (json.status === 'ok') {
                    resolve('OK');
                } else {
                    reject('LogIn failed.');
                }
            })
            .catch(error => reject('LogIn failed.'))

    });

};

logIn()
    .then(console.log('logged in'))
    .catch(error => console.log('not logged in'));

Ответы [ 3 ]

0 голосов
/ 30 апреля 2018

Обратите внимание на эту строку:

.then(console.log('logged in'))

then метод ожидает обратного вызова , но вы вызываете функцию и передаете значение return в качестве параметра. Если console.log вернул функцию, эта функция будет вызываться изнутри then в случае, если обещание было разрешено. Но это не так, поскольку console.log не имеет возвращаемого значения! (Он просто печатает и выходит).

В javascript никакое возвращаемое значение не равно undefined. Итак, вы делаете , вызывая console.log в любом случае и передавая undefined в качестве параметра. Ваш код, таким образом, эквивалентен:

console.log('logged in');
...
  .then(undefined)
  ...

Вероятно, вы имели в виду передать обратный вызов журналирования в качестве параметра и позволить Promise вызвать этот обратный вызов при его разрешении:

.then(() => console.log('logged in'));

Или, чтобы быть более ясным в том, что происходит, вы можете увидеть это следующим образом:

function log() {
  console.log('logged in');
}

...
  .then(log);

Мы не вызываем функцию, просто передаем ссылку!

0 голосов
/ 30 апреля 2018

Обещания продолжаются после улова , хотя вы пытаетесь обернуть обещание в обещание, чтобы вы могли вручную изменить его поведение, что является анти-паттерном. Лучше было бы объединить в цепочку обещание, чтобы вы могли обрабатывать ошибки в цепочке обещаний, а затем продолжать выполнение (так, чтобы за промежуточным звеном все еще мог последовать то).

Нет необходимости в .catch(error => reject('LogIn failed.')) , потому что ваш оператор catch внизу поймает ошибку, если вы просто вернете обещание из getSession(). Вы пытаетесь создать свое собственное Обещание, но так как обещание уже возвращается из getSession(), то, что вы действительно хотите сделать, это вернуть обещание непосредственно из этого.

Наконец, вы пишете console.log внизу, не заключая его в функцию обратного вызова, поэтому он запускается синхронно, когда вызывается обещание, а не когда запускается .then.

Более аккуратное решение:

....

    // return the promise from getSession, why wrap it in another?
    return getSession()
        .then(json => {
            if (json.status === 'ok') {
                return 'OK';
            } else {
                // Throwing an error in a then callback will trigger the catch block below
                throw new Error('LogIn failed.');
            }
        });
}

logIn()
    .then(() => console.log('logged in'))
    .catch(error => console.log('not logged in'));
0 голосов
/ 30 апреля 2018

Вызывает onFulfilled или onRejected со значением выполнения или причиной отклонения обещания (в зависимости от ситуации) и возвращает новое обещание, разрешающееся до возвращаемого значения вызываемого обработчика.

...