Firebase에 대해 간단한 개념을 우선 정리해보자.
Firebase : 실시간 DB, 인증, 스토리지, 분석 등 다양한 기능을 제공하는 모바일/웹앱 개발 플랫폼
1) Authentication: 간편한 다중 플랫폼 로그인
- 이메일 인증, 소셜미디어 계정 인증, 전화번호 인증방식 제공
- 보안강화, 사용자 인증 과정 안전하게 처리
2) FireStore: NoSQL DB
- Firebase에서 제공하는 NoSQL형식의 클라우드 DB
- 실시간 데이터 동기화 지원 (ex. 실시간 채팅)
3) Storage: 사진 및 동영상 저장
- 사용자 파일 저장 및 공유, 강력한 보안
4) Hosting: 웹앱 호스팅
- 정적 및 동적 콘텐츠 모두 호스팅 가능, 웹앱 간단 배포
.env
에 따로 저장해두었다.import { initializeApp, FirebaseApp, getApp } from "firebase/app";
import "firebase/auth";
export let app: FirebaseApp;
const firebaseConfig = {
apiKey: process.env.REACT_APP_API_KEY,
authDomain: process.env.REACT_APP_AUTH_DOMAIN,
projectId: process.env.REACT_APP_PROJECT_ID,
storageBucket: process.env.REACT_APP_STORE_BUCKET,
messagingSenderId: process.env.REACT_APP_MESSAGING_SENDER_ID,
appId: process.env.REACT_APP_ID,
};
try {
app = getApp("app");
} catch (e) {
app = initializeApp(firebaseConfig, "app");
}
const firebase = initializeApp(firebaseConfig);
export default firebase;
app
이라는 이름의 Firebase 앱이 존재하지 않는 경우, initializeApp
을 통해 Firebase 앱 초기화try {
app = getApp("app");
} catch (e) {
app = initializeApp(firebaseConfig, "app");
}
login
인 상태: 로그인 상태임을 콘솔에 띄움logout
인 상태: 로그아웃 상태임을 콘솔에 띄움import {getAuth, onAuthStateChanged} from "firebase/auth"
//mount시 useEffect를 통해 초기 사용자 로그인 상태 확인
useEffect(()=>{
onAuthStateChanged(auth, (user)=>{
if(user) {
console.log("로그인 상태")
}else {
console.log("로그아웃 상태")
}
setInit(true)
})
}, [auth]);
//회원가입 입력값 관리
const onChange = (e: React.ChangeEvent<HTMLInputElement>) => {
const {
target: { name, value },
} = e;
if (name === "email") {
setEmail(value);
console.log(value);
//email 정규식
const emailRegex = /^[a-zA-Z0-9-_]+@[a-zA-Z.]+$/;
if (!value?.match(emailRegex)) {
setError(
"이메일 형식이 올바르지 않습니다. 영문 대소문자, 숫자와 특수기호(_),(-),(@)만 사용 가능합니다."
);
} else {
setError("");
}
}
if (name === "password") {
setPassword(value);
if (value?.length < 8) {
setError("비밀번호는 8자리 이상으로 입력해주세요.");
} else if (passwordConfirm?.length > 0 && value !== passwordConfirm) {
setError("비밀번호와 비밀번호 확인 값이 다릅니다.");
} else {
setError("");
}
}
// 비밀번호 확인 (passwordConfirm)도 위와 비슷한 형태
//'회원가입하기' 버튼 클릭 시
const onSubmit = async (e: React.FormEvent<HTMLFormElement>) => {
e.preventDefault();
try {
const auth = getAuth(app);
await createUserWithEmailAndPassword(auth, email, password);
toast.success("회원가입에 성공하였습니다.");
navigate("/");
} catch (error: any) {
toast.error(error?.code);
console.log(error);
}
};
e: React.ChangeEvent<HTMLInputElement>
e
로부터 taget
속성 추출name
과 input의 value
(현재 입력값)const {
target: { name, value },
} = e;
비구조화 할당
: JS나 TypeScript와 같은 프로그래밍언어에서 변수를 객체나 배열에서 추출하여 사용하는 문법
-> 객체나 배열의 내부 속성이나 요소를 간편하게 변수에 할당. 할당하려는 변수의 이름과 일치하는 속성이나 요소를 추출하여 할당const person = {name: "John", age: 30} const {name, age} = person; console.log(name) //John console.log(age) //30
name
이 email
인 경우setEmail
if (name === "email") {
setEmail(value);
const emailRegex = /^[a-zA-Z0-9-_]+@[a-zA-Z.]+$/;
if (!value?.match(emailRegex)) {
setError(
"이메일 형식이 올바르지 않습니다. 영문 대소문자, 숫자와 특수기호(_),(-),(@)만 사용 가능합니다."
);
} else {
setError("");
}
}
const onSubmit = async (e: React.FormEvent<HTMLFormElement>) => {}
toast.success
를 띄우고, useNavigate
를 통해 홈화면으로 가도록 구현await createUserWithEmailAndPassword(auth, email, password);
toast.success("회원가입에 성공하였습니다.");
navigate("/");
onSubmit
const onSubmit = async (e: React.FormEvent<HTMLFormElement>) => {
e.preventDefault();
try {
const auth = getAuth(app);
await signInWithEmailAndPassword(auth, email, password);
toast.success("로그인에 성공하였습니다.");
} catch (error: any) {
toast.error(error?.code);
console.log(error);
}
};
const onSignOut = async () => {
try {
const auth = getAuth(app);
await signOut(auth);
toast.success("로그아웃 되었습니다.");
} catch (error: any) {
console.log(error);
toast.error(error?.code);
}
};