我正在尝试使用React Navigation v5,v4和switchNavigator进行身份验证,我的代码可以正常工作,但是现在我知道了遇到的问题,但不知道如何解决。
此功能组件在首次打开应用程序时呈现,并确定导航器显示的内容。这可以按预期方式显示,当打开应用程序时显示authnav或homenav,当我尝试登录(从authnav)然后导航到内部homenav的“主页”屏幕时出现问题,但我知道IsAuth不会重新呈现,因此我收到此错误,因此我的问题是如何在发生更改时使IsAuth呈现。
export type isAuthProps = ThemedComponentProps & ComponentProps;
const IsAuth: React.FC<RoutesProps> = (props: isAuthProps) => {
let navigator: any;
const { themedStyle, theme, ...rest } = props;
const [user, setUser] = useState(null);
const [loading, setLoading] = useState(true);
const onAuthStateChanged = (currentUser: any) => {
console.log("TCL: onAuthStateChanged -> currentUser", currentUser);
if (!currentUser) {
setUser(currentUser);
setLoading(false);
} else {
if (!currentUser.emailVerified) {
console.log("TCL: onAuthStateChanged -> currentUser.emailVerified", currentUser.emailVerified)
setUser(null);
setLoading(false);
} else {
setUser(currentUser);
setLoading(false);
}
}
};
useEffect(() => {
NavigationService.setNavigator(navigator);
const subscriber = firebase.auth().onAuthStateChanged(onAuthStateChanged);
return () => {
subscriber();
}; // unsubscribe on unmount
}, []);
if (loading) {
return (<View style={themedStyle.container} >
<LoadingIndicator size='large' />
</View>);
}
return (
<NavigationContainer theme={navigatorTheme} ref={(nav: any) => {
navigator = nav;
}}
>
{user ? <HomeTabsNavigator /> : <AuthNavigator />}
</NavigationContainer>
);
};
导航器
export const HomeTabsNavigator = (): React.ReactElement => {
return (
<BottomTab.Navigator
screenOptions={TabBarVisibleOnRootScreenOptions}
initialRouteName={'Home'}
tabBar={props => <HomeBottom {...props} />}>
<BottomTab.Screen name='Home' component={LayoutsNavigator} />
<BottomTab.Screen name='Post' component={PostNavigator} />
<BottomTab.Screen name='Favorites' component={FavoritesNavigator} />
<BottomTab.Screen name='Themes' component={ThemesNavigator} />
<BottomTab.Screen name='Settings' component={SettingsNavigator} />
</BottomTab.Navigator>
)
};
export const AuthNavigator = () => {
return (
<Stack.Navigator headerMode='none'>
<Stack.Screen name='Signin' component={SigninContainer}></Stack.Screen>
<Stack.Screen name='Signup' component={SignupContainer}></Stack.Screen>
<Stack.Screen name='ForgotPassword' component={ForgotPasswordContainer}></Stack.Screen>
<Stack.Screen name='SigninGoogle' component={SigninGoogleContainer}></Stack.Screen>
</Stack.Navigator>
);
};
我的登录按钮称为“传奇”
export function* signinSaga(action: Signin) {
try {
const payload = action.payload;
const response = yield firebase.auth().signInWithEmailAndPassword(payload.email, payload.password);
const user = response.user;
const token = yield firebase.auth().currentUser?.getIdToken();
yield put(new SigninSuccess({ token, uid: user.uid }));
yield NavigationService.navigate('Explore');
yield showMessageSuccess({ code: 'Successfully login', message: 'Welcome to XXXX!' });
} catch (e) {
const error = errorParser(e);
yield put(new SigninFail(error));
yield showMessageDanger(error);
}
}
答案 0 :(得分:0)
终于有了redux了 此导航器用于App.tsx
const AppNavigator = () => {
const isAuth = useSelector(selectAuthUser);
console.log("AppNavigator -> isAuth", isAuth);
const didTryAutoLogin = useSelector(selectAuthDidTryLogin);
console.log("AppNavigator -> didTryAutoLogin", didTryAutoLogin);
return (
<NavigationContainer>
{isAuth && <HomeTabsNavigator />}
{!isAuth && didTryAutoLogin && <AuthNavigator />}
{!isAuth && !didTryAutoLogin && <IsAuthScreen />}
</NavigationContainer>
);
};
export default AppNavigator;
我创建了一个新的屏幕组件,我在Angular Typescript中使用了Action clases inspirit,因此,如果您使用的是Plan js,则只需正常调用该动作即可。
interface RoutesProps {
}
interface ComponentProps {
}
export type isAuthProps = ThemedComponentProps & ComponentProps;
const IsAuth: React.FC<RoutesProps> = (props: isAuthProps) => {
const { themedStyle, theme, ...rest } = props;
const dispatch = useDispatch();
const onAuthStateChanged = (currentUser: any) => {
if (!currentUser) {
dispatch(new authActions.DidTryLogin());
} else {
if (!currentUser.emailVerified) {
dispatch(new authActions.DidTryLogin());
} else {
dispatch(new authActions.SigninSuccess(currentUser));
}
}
};
useEffect(() => {
const subscriber = firebase.auth().onAuthStateChanged(onAuthStateChanged);
return () => {
subscriber();
}; // unsubscribe on unmount
}, [dispatch]);
return (<View style={themedStyle.container} >
<LoadingIndicator size='large' />
</View>);
};
export const IsAuthScreen = withStyles(IsAuth, (theme: ThemeType) => ({
container: {
flex: 1,
justifyContent: 'center',
alignItems: 'center',
},
}));
减速器
case AuthActionTypes.SIGNIN_SUCCESS: {
return {
...state,
loading: false,
error: null,
user: action.payload,
didTryLogin: true,
};
}
case AuthActionTypes.DID_TRY_LOGIN: {
return {
...state,
didTryLogin: true,
};
}
case AuthActionTypes.LOGOUT: {
return { ...INIT_STATE, didTryLogin: true }
}
佐贺
export function* signinSaga(action: Signin) {
try {
const payload = action.payload;
const response = yield firebase.auth().signInWithEmailAndPassword(payload.email, payload.password);
const user = response.user;
if (user.emailVerified) {
yield put(new SigninSuccess({ user }));
yield showMessageSuccess({ code: 'Successfully login', message: 'Welcome to XXXX!' });
} else {
const error = { code: 'Something go wrong', message: 'You need to verify your email first.' };
yield put(new SigninFail(error));
yield showMessageDanger(error);
}
} catch (e) {
const error = errorParser(e);
yield put(new SigninFail(error));
yield showMessageDanger(error);
}
}