У меня есть небольшая загадка в моем приложении Vue / vuex / vue-router + Firebase. Код начальной загрузки должен инициализировать Firebase, а также зарегистрированного пользователя (если есть) в Vuex:
new Vue({
el: '#app', router, store, template: '<App/>', components: { App },
beforeCreate() {
firebase.initializeApp(firebaseConfig)
// Because the code below is async, the app gets created before user is returned...
.auth().onAuthStateChanged(user => {
this.$store.commit('syncAuthUser', user) // this executes too late...
})
}
})
В моих маршрутах у меня есть
{ path: '/home', name: 'Home', component: Home, meta: { requiresAuth: true } }
а также
router.beforeEach((to, from, next) => {
let authUser = store.getters.authUser // this is not set just yet...
if (to.matched.some(record => record.meta.requiresAuth)) {
if (!authUser) {
next('signin') // /home will always hit here...
}
next()
}
else {
next()
}
})
Проблема
Как упоминалось в комментариях, приложение слишком поздно получает аутентифицированного пользователя. Итак, когда вы перейдете к /home
во время входа в систему, приложение запустит beforeEach
check в маршрутах ... И пользовательский экземпляр пока не будет доступен, поэтому он будет думать, что вы не вошли в систему, когда в на самом деле вы являетесь (это видно из моих вычисленных свойств, которые были правильно обновлены через несколько мгновений).
Вопрос
Итак, как мне изменить свой код, чтобы приложение Vue инициализировалось только после того, как Firebase вернет пользователя и после того, как этот пользователь будет передан в хранилище Vuex? Пожалуйста, дайте мне знать, если я делаю что-то совершенно не так.
Попытки
- Я пробовал использовать подход «отказаться от подписки»; однако его проблема в том, что
onAuthStateChanged
сработает только один раз. Итак, если я помещу туда свой критическийthis.$store.commit('syncAuthUser', user)
, то этот код будет выполняться только при создании приложения, а не при выходе пользователя, например. - Я также попробовал более подходящий подход здесь . Я действительно работал на себя, но мне было плохо, завертывая
onAuthStateChanged
в другойPromise
, наверняка должен быть лучший способ; плюс, кажется неправильным помещать логин инициализации пользователя auth в файл маршрутов.