Цепочка обещаний узловых выражений и общее выражение catch - PullRequest
0 голосов
/ 20 января 2019

У меня есть код, где я делаю несколько в базу данных

 FirebaseHelper.getDataFromDB("users", profileSort.email )
    .then(response => {
        if (response.exists) {
          FirebaseHelper.updateDataInDb("authentication", profileSort.email, TokenToStore)
          .then(() => {
            console.log("here")
               //User signs in, check if we have tokens for meetup, eventbrite
            FirebaseHelper.getDataFromDB("authenticat", profileSort.email)
            .then(response => {
              //if yes, store them in session
              if (response.exists)   {
                req.session.contextToken = response.data()
                  if (req.session.contextToken["meetupAccessToken"]) profileSort["meetup"] = true
                  if (req.session.contextToken["meetupAccessToken"]) profileSort["eventbrite"] = true
              //Replace the token with currret store token
              req.session.contextToken = {...req.session.contextToken, ...TokenToStore}
              }
              return done(null, profileSort)
            })
            .catch(error =>  {  done(error) })
          })
          .catch(error =>  done(error))
         } else {
        //adding user and storing authentication information
         FirebaseHelper.setDataToDb("users", profileSort.email, profileSort)
         .then(() => {
            FirebaseHelper.setDataToDb("authentication", profileSort.email, TokenToStore)
            .catch(error =>  done(error))
         })
         .catch(error =>  done(error))
          return done(null, profileSort)
        }
    })
  .catch(error =>  done(error))
}

Несмотря на то, что этот код работает, просто так много вложенных операторов .then() находятся внутри друг друга

Кроме того, существует очень много операторов catch, которые просто возвращают ошибки.

Теперь, хотя этот код работает, но он также выглядит очень неопрятно.

Может ли кто-нибудь помочь мне разобраться, как сделать приведенный выше код аккуратным и аккуратным? Вероятно, удалив нежелательный оператор .catch()

Ps: это внутри паспортная стратегия

Ответы [ 2 ]

0 голосов
/ 20 января 2019

Поскольку процесс входа в систему требует умеренного количества кода, рассмотрите возможность помещения его в свою собственную автономную функцию, которая возвращает Promise.Сделайте то же самое для добавления пользователя, и тогда вы можете использовать single .catch в конце, если есть ошибка, возвращая все Обещания, чтобы они были правильно соединены воедино, избегая обещанияанти-шаблон обратного вызова:

FirebaseHelper.getDataFromDB("users", profileSort.email )
  .then(({ exists }) => (
    exists
    ? updateData()
    : addUser()
  ))
  .then((profileSort) => {
    done(null, profileSort);
  })
  .catch((err) => {
    done(err);
  });

  function updateData() {
  return FirebaseHelper.updateDataInDb("authentication", profileSort.email, TokenToStore)
  //User signs in, check if we have tokens for meetup, eventbrite
    .then(() => {
      return FirebaseHelper.getDataFromDB("authenticat", profileSort.email);
    })
    .then(response => {
    //if yes, store them in session
    if (response.exists) {
      req.session.contextToken = response.data();
      if (req.session.contextToken.meetupAccessToken) {
        profileSort.meetup = true;
        profileSort.eventbrite = true;
      }
      //Replace the token with currret store token
      req.session.contextToken = {...req.session.contextToken, ...TokenToStore}
    }
    return profileSort;
  });
}
function addUser() {
  //adding user and storing authentication information
  return FirebaseHelper.setDataToDb("users", profileSort.email, profileSort)
    .then(() => {
      return FirebaseHelper.setDataToDb("authentication", profileSort.email, TokenToStore)
  })
    .then(() => profileSort);
  return done(null, profileSort)
}

Было бы даже лучше, если бы содержащая функция возвращала Promise вместо принятия обратного вызова done - с обещаниями работать гораздо лучше, чем с обратными вызовами,в конце концов:

function doStuff() {
  return FirebaseHelper.getDataFromDB("users", profileSort.email )
    .then(({ exists }) => (
      exists
      ? updateData()
      : addUser()
    ));
  // ...

Тогда вместо

doStuff((err, profileSort) => {
  // ...

вы можете сделать

doStuff()
  .then((profileSort) => {
    // handle success
  })
  .catch((err) => {
    // handle errors
  })

, используя async / await вместо .thens может сделать код еще короче, хотя не знаю, поддерживает ли это ваша среда.

0 голосов
/ 20 января 2019

Если вы находитесь на узле 8 или выше, вы можете использовать асинхронные функции, чтобы сделать его более многословным / читабельным и обернуть его в блок trycatch, чтобы вам не приходилось связывать цепочку с каждым обещаемым обещанием:

async function login() {
  try {
    const users = await FirebaseHelper.getDataFromDB("users", profileSort.email);

    if (users.exists) {
      await FirebaseHelper.updateDataInDb("authentication", profileSort.email, TokenToStore);
      const authenticat = await FirebaseHelper.getDataFromDB("authenticat", profileSort.email);

      if (authenticat.exists) {
        req.session.contextToken = response.data();
        if (req.session.contextToken["meetupAccessToken"]) profileSort["meetup"] = true;
        if (req.session.contextToken["meetupAccessToken"]) profileSort["eventbrite"] = true;
        req.session.contextToken = {...req.session.contextToken, ...TokenToStore};

        return done(null, profileSort);
      }
    } else {
      await FirebaseHelper.setDataToDb("users", profileSort.email, profileSort);
      await FirebaseHelper.setDataToDb("authentication", profileSort.email, TokenToStore);
      return done(null, profileSort);
    }
  } catch (error) {
    return done(error);
  }
}
...