Getting 'Uncaught' after catching error in firebase.auth() with async

天大地大妈咪最大 提交于 2020-03-19 05:14:11

问题


async login({ commit }, { email, password }) {
  let result
  try {
    result = await firebase.auth().signInWithEmailAndPassword(email, password)
    commit('setUser', result.user)
  } catch (err) {
    commit('setError', err)
  }
}

This is an action in Vuex. When this runs, I expect the commit('seteError', err) to be a valid error handler for the error returned from catch (err). Instead, I get an 'Uncaught' exception and execution stops.

Would appreciate any insights from anyone who managed to use async with firebase.auth()


回答1:


I ran into the same issue today - it appears to be due to the implementation of the Closure promise library that firebase auth uses. There is a closed issue in the firebase-js-sdk project here with some details on it. Ultimately, what is happening with this implantation is a timeout is getting set that throws an exception outside of the scope of the try/catch:

To avoid this, the exception needs to be handled by calling .catch() on the returned promise e.g.:

firebase.auth().signInWithEmailAndPassword(email, password)
  .catch((ex) => { /* handle exception */ });

As I have all of my firebase logic wrapped and centralized, what I ended up doing is wrapping the firebase Promise in one of my own:

export async function signIn(email, password) {
  return new Promise((resolve, reject) => {
    firebase.auth().signInWithEmailAndPassword(email, password)
      .then((userCreds) => resolve(userCreds))
      .catch((reason) => reject(reason));
  });
}

The wrapper function can then be called using async await:

try {
  const result = await signIn(email, password)
  // Do what you need to with the result
} catch (ex) {
  // Handle any exceptions
}



回答2:


This is how I managed to handle firebase authentication with async in Vuex. I needed to use onAuthStateChanged

async login({ commit, dispatch }, { email, password }) {
  try {
    await firebase.auth().signInWithEmailAndPassword(email, password)

    await dispatch('session')
  } catch (err) {
    commit('setError', err)
  }
}

Where the 'session' dispatch simply does:

async session({ commit }) {
  let user
  try {
    user = await userInSession()
    commit('setUser', user)
  } catch (err) {
    console.error(err)
    commit('setUser', {})
  }
}

and the userInSession function uses onAuthStateChanged:

const userInSession =  function () {
  return new Promise((resolve, reject) => {
    firebase.auth().onAuthStateChanged((user) => {
      if (user) {
        resolve(user.uid)
      } else {
        reject(Error('No user authenticated'))
      }
    })
  })
}


来源:https://stackoverflow.com/questions/51819349/getting-uncaught-after-catching-error-in-firebase-auth-with-async

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!