반응형
대부분의 애플리케이션은 데이터에 접근할 수 있는 유효한 사용자라는 것을 증명해야 하며, 인증 후 서비스를 이용할 수 있는 화면이 렌더링, 로그아웃 등으로 인증 상태를 해제하면 다시 인증을 위한 화면으로 이동함.
1. MainStack 내비게이션
const MainStack = () => {
const theme = useContext(ThemeContext);
return(
<Stack.Navigator
initialRouteName="Main"
screenOptions={{
headerTitleAlign: 'center',
headerTintColor: theme.headerTintColor,
cardStyle: {backgroundColor: theme.backgroundColor},
headerBackTitleVisible: false,
}}
>
<Stack.Screen name="Main" component={MainTab} />
<Stack.Screen name="Channel Creation" component={ChannelCreation} />
<Stack.Screen name="Channel" component={Channel} />
</Stack.Navigator>
);
};
export default MainStack;
MainStack 내비게이션은 채널 목록 화면, 프로필 화면으로 구성된 MainTab 내비게이션을 첫 번째 화면으로 가짐.
실행 화면
2. MainTab 내비게이션
MainTab 내비게이션을 구성하는 채널 목록 화면 ChannelList.js, 프로필 화면 Profile.js 작성
const ChannelList = ({navigation}) => {
return(
<Container>
<Text style={{fontSize: 24}}>Channel List</Text>
<Button
title="Channel Creation"
onPress={() => navigation.navigate('Channel Creation')}
/>
</Container>
);
};
export default ChannelList;
4. 인증 & 화면 전환
로그인 혹은 회원가입을 통해 인증을 성공했을 경우, 그렇지 않을 경우 각각 다른 내비게이션이 렌더링되도록 한다.
=> Context API 이용
UserContext를 만들고 인증 상태에 따라 적절한 내비게이션이 렌더링되도록함.
import React, {useState, createContext} from "react";
const UserContext = createContext({
user: {email: null, uid: null},
dispatch: () => {},
});
const UserProvider = ({children}) => {
const [user, setUser] = useState({});
const dispatch = ({email, uid}) => {
setUser({email, uid});
};
const value = {user, dispatch};
return <UserContext.Provider value={value}>{children}</UserContext.Provider>;
};
export {UserContext, UserProvider};
인증되면 UserContext의 user를 수정하도록 로그인 화면 수정
5. 로그아웃
로그아웃 함수 firebase.js에 추가
//로그아웃
export const logout = async() => {
return await authService.signOut();
};
프로필 화면에 로그아웃 버튼 생성 후 logout 함수 호출
- logout 함수 완료 시 UserContext의 dispatch 함수를 이용해 user의 상태 변경
- 사용자 인증과 마찬가지로 로그아웃을 통해 인증 해제 후에는 스와이프, 뒤로가기 버튼을 통해 다시 이전 내비게이션으로 돌아갈 수 없다.
const Profile = () => {
const {dispatch} = useContext(UserContext);
...
const _handleLogoutButtonPress = async () => {
try{
spinner.start();
await logout();
}catch(e){
console.log('[Profile] logout: ',e.message);
}finally{
dispatch({});
spinner.stop();
}
};
...
return (
<Container>
<Image>
...
<Button
title="logout"
onPress={_handleLogoutButtonPress}
containerStyle={{backgroundColor: theme.buttonLogout}}
/>
</Container>
);
};
export default Profile;
실행 화면
6. 프로필 화면
현재 접속한 사용자 정보 반환 함수
//현재 접속한 사용자 정보 반환
export const getCurrentUser = () => {
const {uid, displayName, email, photoURL} = authService.currentUser;
return {uid, name: displayName, email, photoUrl: photoURL};
};
사용자 사진 수정 함수
//사용자 사진 수정
export const updateUserPhoto = async photoUrl => {
const user = authService.currentUser;
const storageUrl = photoUrl.startsWith('https')
? photoUrl
: await uploadImage(photoUrl);
await user.updateProfile({photoURL: storageUrl});
return {name: user.displayName, email: user.email, photoUrl: user.photoURL};
};
현재 접속한 사용자 정보가 있는 currentUser에서 필요한 값을 받아오고, 스토리지에 선택된 사진을 업로드하는 함수를 이용해 사용자의 사진을 수정함.
Profile.js 수정
- 사용자의 사진은 현재 접속한 사용자의 사진이 렌더링되도록 getCurrentUser 함수를 통해 받아온 user의 photoUrl 사용
- getCurrentUser 함수가 반환한 내용으로 사용자의 이름, 이메일을 Input 컴포넌트로 렌더링
- 수정할 수 없도록 disabled 추가
const _handlePhotoChange = async url => {
try{
spinner.start();
const updatedUser = await updateUserPhoto(url);
setPhotoUrl(updatedUser.photoUrl);
}catch(e){
Alert.alert('Photo Error',e.message);
}finally{
spinner.stop();
}
};
return (
<Container>
<Image
url={photoUrl}
onChangeImage={_handlePhotoChange}
showButton
rounded
/>
<Input label="Name" value={user.name} disabled />
<Input label="Email" value={user.email} disabled />
<Button
title="logout"
onPress={_handleLogoutButtonPress}
containerStyle={{backgroundColor: theme.buttonLogout}}
/>
</Container>
);
};
export default Profile;
실행 화면
반응형
'💻 my code archive > ✨React-Native' 카테고리의 다른 글
[RN 프로젝트] #2 Expo 환경 React native webview 카카오 네이버 깃허브 소셜 로그인 화면 띄우기 (0) | 2022.10.05 |
---|---|
[리액트 네이티브] 채팅 애플리케이션 만들기 3. 채팅방 생성, 메시지 전송, GiftedChat 컴포넌트 (0) | 2022.07.22 |
[리액트 네이티브] 채팅 애플리케이션 만들기 1.파이어베이스 세팅, 로그인, 회원가입 (0) | 2022.07.21 |
[리액트 네이티브] 스택(stack) 내비게이션, 탭(tab) 내비게이션 (0) | 2022.07.15 |
[리액트 네이티브] ContextAPI, Consumer, Provider 실습 (0) | 2022.07.14 |