Firebase 이용해보기

박진·2021년 4월 5일
1

리액트 프로젝트를 하던중 로그인기능을 구현할수있도록 도와주는 친구를 찾았다.
그친구는, Firebase 이다.

Firebase란?

서버측 코드를 작성하지 않고도 클라우드와 연동해 모바일 응용 프로그램을 효율적으로 개발할수있는 환경을 제공해주는 좋은 친구이다.

그러면 무엇을 할수있을까?

실시간 데이터베이스, 사용자 인증, 클라우, 호스팅, 오류보고, 에드워즈, 에드몹, 애널리스틱스 등 수많은 서비스를 제공한다.

나는 이중에서, 로그인 서비스를 구현하기위해서 사용자 인증이 필요했다.

firebase에 들어가서 로그인 및 프로젝트를 생성후, 필요한 서비스의 스크립트를 받아오면된다.

그전에 나는 React에서 사용하기위해서 먼저 추가를해줘야한다

터미널에 필요한 firebase를 추가해야한다.

yarn add firebase

그후 firebase.js라는 파일을 service폴더라는곳에 만들어 주었다.

<script>
  // Your web app's Firebase configuration
  // For Firebase JS SDK v7.20.0 and later, measurementId is optional
  const firebaseConfig = {
    apiKey: "-----",
    authDomain: "-----",
    projectId: "-----",
    storageBucket: "-----",
    messagingSenderId: "-----",
    appId: "-----",
    measurementId: "-----"
  };
  // Initialize Firebase
  firebase.initializeApp(firebaseConfig);
  firebase.analytics();
</script>

주어진 스크립트를 복사해서 붙여왔는데, 전부 사용하지 않아 필요한것만 남겨두기로했다.

  const firebaseConfig = {
    apiKey: "-----",
    authDomain: "-----",
    projectId: "-----",
    databaseURL : "-----",
  };

databaseURL은 따로 받아야하는데, firebase웹에서 Realtime Database에서 create database를해주어서 가져오면된다.

그리고, youtube 프로젝트와 마찬가지로 나의 api key가 같이 보여주면되지않기때문에 env에 따로 저장해야한다.

REACT_APP_FIREBASE_API_KEY = -----
REACT_APP_FIREBASE_AUTH_DOMAIN = -----
...
  const firebaseConfig = {
    apiKey: "process.env.REACT_APP_FIREBASE_API_KEY",
    authDomain: "-----",
    projectId: "-----",
    databaseURL : "-----",
  };

그후 나는 Github에 올리기떔누에 gitignore에 env를 숨기기위해서,

# API Keys
.env

이제부터 제대로 사용자가 로그인, 로그아웃을할때 담당을 해주는 역할 클래스를 만들어보자.

firebase 문서에서 로그인을 보면 잘 나와있다. service폴데에 auth_service.js를 만들어주었다.

import firebase form 'firebase';

class AuthService{
///providerName은 로그인이되어지는게 google인지 github인지 등을 알수있는 인자
	login(providerName){
    	const authProvider = new firebase.auth[`${providerName}AuthProvider`]();
        return firebase.auth().signinWithPopul(authProvider);
        //popup을 이요해서 로그인하기위한
    }
 }
 
 export default AuthService

이제 index.js에 porps로 전달해주면된다.

const authService = new AuthService();

ReactDOM.render(
	<React.StrictMode>
    	<App authService={authService}/>
    </React.StrictMode>

이제 Index에서 받은 인자를 app에서 다시 필요한 부분으로 전달해주면된다

function App({authService}){
	return <Login authService={authService}/>
}

이제 Login 컴포넌트로 전달되어진 인자를 이용해주면된다.

Const Login = ({authServcie}) =>{
	const onLogin = event =>{
    	authService
        .login(event.current.contentText)
        .then(console.log)
        //authService안에있는 providerName를 주기위한
    };
    return (
    	<section>
        	<button onClick={onLogin}>Google</button>
        </section>
        )}

이렇게만 했더니 오류가났다. 이유는 처음 authService에서 만들어진 firebase를 아무도호출을하지않았다.

import firebase from 'firebase'

  const firebaseConfig = {
    apiKey: "process.env.REACT_APP_FIREBASE_API_KEY",
    authDomain: "....",
    projectId: "....",
    databaseURL : "....",
  };
  // Initialize Firebase
  const firebase = firebase.initializeApp(firebaseConfig);
  export default firebase;

이런식으로 firebase를 Export해주면된다.

다시 authservice에와줘서

import firebase from 'firebase';
import firebaseApp from 'firebase

class AuthService{
///providerName은 로그인이되어지는게 google인지 github인지 등을 알수있는 인자
	login(providerName){
    	const authProvider = new firebase.auth[`${providerName}AuthProvider`]();
        return firebase.auth().signinWithPopul(authProvider);
        //popup을 이요해서 로그인하기위한
    }
 }

d이렇게 해주면 잘 작동되는걸 볼수있는데 그리고 firebase웹에서 인증페이지에서 원하는 로그인인증을 미리 clientid와 client secret셋업을 완성해줘야한다.

ex) github => developer setting > OAuth setup 해줘야한다.

이제 로그인을 한번해보자

Login컴포넌트에서, 로그인이 성공이 되면 성공컴포넌트로 넘어갈수있도록 구현해보자. 그럴려면 login에서 받은 데이터를 그페이지로 넘겨주기만하면끝이다. 쉽게 페이지가 전환할수있도록 create-router-dom을 이용하면된다.

Const Login = ({authServcie}) =>{
  const history = useHistory();
  
	const succeedLogin = (userId)=>{
    	history.push({
        	pathname : "/succeed",
            state: userId
            }
        )
    }

	const onLogin = event =>{
    	authService
        .login(event.current.contentText)
        .then((result)=>succeedLogin(result.userId))
    };
    return (
    	<section>
        	<button onClick={onLogin}>Google</button>
        </section>
        )}

로그인이 성공한 결과값 result를 succeedLogin함수에 인자로 보내주며 router를이용하여 그페이지로 이동하면서 state값을 전달해주면된다.

로그인을 했으면 로그아웃도 한번만들어보자. 로그아웃을 만들려면 사용자가 로그인이 되었는지 안되었는지를 먼저확인해야한다.

firebase에 callback함수를받는 함수인 onAuthChanged함수를 추가해줘야한다.

사용자가 바뀔때마다 전달받는 함수인자인 onUserChnaged를 받아서 user를받아 호출에주면된다.

class AuthService{
///providerName은 로그인이되어지는게 google인지 github인지 등을 알수있는 인자
	login(providerName){
    	const authProvider = new firebase.auth[`${providerName}AuthProvider`]();
        return firebase.auth().signinWithPopul(authProvider);
        //popup을 이요해서 로그인하기위한
        
onAuthChnage(onUserChanged){
	firebase.auth().onAuthChanged(user => {
    onUserChanged(user);
    })
}
    }
 }

그리고 다시 login에 돌아와, authService를 이용해서 onAuthChnage를 호출하여 콜백을 전달해야한다.

그래서 만약 user가 있으면 succeedLogin으로 이동하게 했다.

Const Login = ({authServcie}) =>{
  const history = useHistory();
  
	const succeedLogin = (userId)=>{
    	history.push({
        	pathname : "/succeed",
            state: userId
            }
        )
    }
    
    useEffect(()=>{
    authService.onAuthChnage(user => {
    user && succeedLogin(user.id)
    	})
    });

	const onLogin = event =>{
    	authService
        .login(event.current.contentText)
        .then((result)=>succeedLogin(result.userId))
    };
    return (
    	<section>
        	<button onClick={onLogin}>Google</button>
        </section>
        )}

succeedLogin 함수를 통해 이동어진 로그인페이지에서 이제 로그아웃을 실행하면된다

그전에 authservice에 돌아와 firebase에 signout함수를 등록해주면된다.

class AuthService{
///providerName은 로그인이되어지는게 google인지 github인지 등을 알수있는 인자
	login(providerName){
    	const authProvider = new firebase.auth[`${providerName}AuthProvider`]();
        return firebase.auth().signinWithPopul(authProvider);
        //popup을 이요해서 로그인하기위한
        
logout(){
	firebase.auth().signOut();
}

onAuthChnage(onUserChanged){
	firebase.auth().onAuthChanged(user => {
    onUserChanged(user);
    })
}
    }
 }

logOut 컴포턴틑를 생성하여, logOut안에 있는 logout버튼을 클릭시에, onLogout을 실행시키어, SucceedLogin에서 onLogout함수가 실행되어 authService.logout(); 함수를 실행시켜주면 된다.

그렇게되면 다시, useEffect를 통하여 authService.onAuthChange에 user인자가 false가 되어 다시 메인페이지로 이동시키면된다.

const SucceedLogin = ({authService}) =>{
	const history = useHistory();
    
	const onLogout = () =>{
    	authService.logout();
        };
        
    useEffect(()=> {
    	authService.onAuthChange(user => {
        	if(!user){
            	history.push('/')
            }
      	});
    });
        
        return (
        	<>
            	<h1>로그인 성공!</h1>
                <logOut onLogout={onLogout}/>
                <>
        );
}
                
const logOut = ({ onLogout }) => (
  <div>
    {onLogout && (
      <button className={styles.logout} onClick={onLogout}>
        Logout
      </button>
    )} />
  </div>
);
profile
Hello :)

0개의 댓글