티스토리 뷰

지난 이야기...

리액트를 공부했지만 리액트식(?) 사고방식에 익숙해지지 않았다.
때문에 개편할 토이 프로젝트가 리액트로 만드는 것이 편함을 직감했음에도 불구하고 바닐라 자바스크립트로 개발을 강행하게 되는데... (← 토이 프로젝트 개발기 0탄)
하지만 복잡해지는 코드 속에서 이건 망했다는 사실을 깨닫고 만다. (← 토이 프로젝트 개발기 1탄)

그리하여 리액트 프로젝트를 만들어보며 리액트 훈련을 시작한다.

- To Be Continued...

프로젝트 개요

  • 🎁 프로젝트 소개

    • 사이트 주소 : 친구 조각 모음

    • 인물 정보를 카드 형태로 저장하는 웹 서비스

      *"카톡, SNS, 게임 친구 창 등 이곳저곳 흩어져 있는 친구들을 한 곳에 모아 보세요!"*

    • 원래 드림 코딩 리액트 강의에서 'Business Card Maker'라는 이름의 프로젝트로 시작했는데 (명함을 만들어주는 웹 애플리케이션), 개인적인 기획을 더하며 새로운 결과물을 만들었다.

      여담이지만 강의가 정말 좋다.
      아직 강의를 끝까지 보지 않아서 강의 후기는 다른 포스팅에 작성하기로 한다.

  • ✨프로젝트 목표 (+ 신경 쓴 포인트)

    • 리액트에 익숙해지기
    • 프로젝트 관리 깔끔하게 하는 연습
  • 🔧 기술 스택

    • Front End : React JavaScript PostCSS
    • DataBase : Firebase
    • Image Storage : Cloudinary
    • Deploy : Firebase
  • 🎮 기능

    페이지 화면 페이지 설명 접근 권한
    메인 페이지 - 홈으로 돌아가는 로고, 로그인 버튼, 간단한 페이지 소개와 활용법, 친구 추가 화면으로 가는 링크로 구성
    - 친구 추가 화면은 비회원도 접근 가능
    비로그인,
    로그인
    친구 추가 페이지 - 비회원도 접근 가능 (단, 친구 등록 버튼을 누르면 모달 창으로 로그인 화면이 뜨고, 로그인을 해야 저장 기능 사용 가능. 모달 창에서 회원가입까지 진행할 수 있어 입력한 친구 추가 정보는 보존됨.)
    - 카테고리는 친구 리스트 화면에서 추가 기능
    - 이미지 미등록 시, 기본 썸네일로 표시
    로그인
    비로그인
    로그인 화면 (모달창) - 이메일 / 구글, GitHub 로그인
    - 이메일 회원가입
    모달 창
    (모든 페이지에서 띄울 수 있음)
    친구 리스트 페이지 - 추가한 친구 목록 확인 카테고리별로 목록 확인 기능
    - 카테고리 추가, 삭제 기능
    - 친구 수정, 삭제 기능
    - 카드 크기는 scale로 조정 (브라우저 너비에 따라 자동으로 크기 맞춤)
    로그인 only

진행 과정

  • 📖 기획

    • 기존 프로젝트

      • 페이지는 로그인 페이지와, 카드 메이커 페이지로 이뤄지며 로그인을 해야 카드 메이커 페이지로 갈 수 있음
        • (기능을 하나라도 써보려면 우선 회원가입부터 해야 함. 따라서 이탈률이 높을 것이라 생각)
      • 카드 메이커 페이지에서 카드 추가, 읽기, 삭제, 수정 기능
    • 수정 및 추가한 기능

      • 일단 기능을 써보게 하고, 주요 행동을 하는 타이밍에 로그인 요구
      • 카드를 카테고리로 분류하는 기능
      • 비회원이 링크를 통해 카드 리스트 페이지 접근 제한
        사실 이것도 하려고 했다.. (아직 적용 못함)
  • 🎨 스케치 / 레이아웃

    • 툴은 figma로 작업했다.
    • 퍼블리싱하면서 임의로 디자인을 수정한 부분도 꽤 있다.
  • 💻 코딩

    중간에 삽질한 것을 제외하면 대략 아래와 같은 순서로 작업했다.

    1. 퍼블리싱 작업

      이 포스팅에서 말하는 퍼블리싱은 디자인을 바탕으로 기능 없이 html, css 코딩한 것을 말한다. (정확히는 jsx지만 html로 변환되니까)

    2. 로그인 / 로그아웃 / 회원가입 기능 추가

      • 실시간 데이터가 반영되도록 FireStore에서 제공하는 리스너를 추가해서 작업했다.
    3. 친구, 카테고리 추가 기능

    4. 친구, 카테고리 삭제 기능

    5. 친구 수정 기능

프로젝트 관리 방식

  • GitHub의 이슈를 적극 활용했다.

    등록한 이슈들... 하나씩 해결해도 점점 늘어갔다...
    • 기능이 단순해 보여도 전부 구현하기 위해서는 여러 가지로 신경 쓸 것이 많았다. 해야 할 것을 작은 단위로 쪼개 놓고 하나씩 처리하며 작업을 진척시켰다.
  • 필요한 일을 작은 단위로 쪼개고 마일스톤으로 묶었다.

    기한을 설정해 일정관리를 할 수 있다는 점이 좋았다.
    • 만들고자 하는 기능을 이슈로 등록하다 보니 전부 하려면 시간이 너무 많이 걸릴 것 같았다. 그래서 중요한 이슈끼리 묶어서 우선 처리했다.
  • 커밋도 주로 이슈 단위로 했다.

    이슈 번호를 커밋 메세지에 적어놓으면 바로 이슈페이지로 이동할 수 있어 편하다.
    • 이슈 단위로 커밋하고, 커밋에서 바로 어떤 이슈인지 확인할 수 있도록 커밋 메시지를 작성했다.

어려웠던 점과 해결 방법

  • firestore의 데이터 구조

    • 어려웠던 점

      • 친구 조각 모음에서 추가한 기능이 친구의 정보를 저장하고 카테고리로 분류하는 것이었는데, 이 기능을 구현하기 위해 데이터의 구조를 어떻게 짤 것인지는 생각할 것이 많았다.

      • Firestore 같은 서비스로 데이터 구조를 생각하는 것이 처음이라 생소했다.

        Firestore의 데이터 탭 화면

        (Firestore의 데이터 탭을 확인해보면 컬렉션 > 문서( > 필드) > 컬렉션 > 문서( > 필드) > 컬렉션... 과 같은 식으로 계속 연결되어 있다.)

    • 해결 과정

      메모장으로 구조를 작성해보고 문제가 없는지 검토하며 구조를 수정했다.

      1. 첫 번째 구조

        1. 우선 회원별로 각자 자신이 저장한 정보를 보여줘야 하므로 최상단에는 users라는 컬렉션을 만들었다.
        2. users안에 들어가는 문서의 아이디는 유저 아이디로 만들었다.
        3. 유저 아이디 문서 안에 다시 '친구 목록'이라는 컬렉션을 만들고 그 안에 친구라는 문서를 만들어 친구의 정보와 카테고리 정보를 넣었다.

        💥 예상되는 문제

        • 카테고리를 친구라는 문서 하위에 있기 때문에, 따로 카테고리 리스트를 만들기 위해서는 모든 친구 문서의 카테고리 값을 검사해야 한다. (카테고리 리스트 별로 친구를 모아봐야 하기 때문에 카테고리 리스트를 뽑아서 버튼으로 만드는 중간 과정이 필요했다)
        • 카테고리 리스트를 얻어낸다 하더라도, 다시 그 바탕으로 특정 카테고리의 친구들을 한꺼번에 모아보려고 하면 친구 목록을 다시 검사해야 한다. (불필요한 작업)
        • 카테고리 정보를 하나 수정하려고 하면 모든 친구 문서 안에 들어가서 카테고리 값을 수정해줘야 한다. 즉, 카테고리 리스트를 관리하려면 불필요한 작업이 많아진다. 친구의 목록이 많아질수록 쓸 데 없는 작업이 많아질 것이다.
      2. 위의 문제 때문에 나는 다시 데이터 구조를 생각했다.

      3. 두 번째 구조

        1. 첫 번째 구조와 똑같이 만들되 유저 아이디 문서 안의 컬렉션을 친구 목록과 카테고리 목록으로 나눴다.

        💥 예상되는 문제

        • 카테고리는 삭제해도 친구 정보에는 삭제한 카테고리의 정보가 남아있다.

        • 다만 카테고리 목록 안의 카테고리 문서의 id를 카테고리 이름으로 할지 임의의 id로 만들고 필드 안에 카테고리 정보를 넣어야 할지 고민했다.

        • 문서의 id를 카테고리 이름으로 하면 최소한 카테고리의 이름이 겹칠 일은 없었다. 대신 카테고리의 이름을 변경하려면 친구의 정보를 수정해야 한다.

        • 문서의 id를 임의의 id로 지정하고 카테고리 이름을 필드에 저장하면 카테고리의 이름은 겹치지만, (카테고리의 이름이 겹치는지 확인할 방법이 없는 건 아니다) 카테고리의 이름을 변경이 수월하다.

  • 결론

    • 두 번째 구조도 예상되는 문제가 있었지만 첫 번째로 짠 구조와 비슷한 문제를 가지고 있었기 때문에, 적어도 첫 번째에서 예상되는 문제의 부분이라도 해결하는 두 번째로 결정했다. 카테고리 정보를 수정하기 편하게 만들기 위해 두 번째로 짠 구조에서 카테고리 컬렉션 안의 문제 id는 임의로 생성되는 id로 적용했다.
  • [#12] 친구 정보 저장 기능

    • 문제점

      • 친구 정보를 저장할 때는 다음과 같은 과정을 거친다.

        1. 썸네일 이미지를 Cloudinary에 업로드한다.
        2. 저장하고 난 뒤에 저장된 url을 기존 친구 정보 state를 업데이트해준다.
        3. 썸네일 정보가 추가된 뒤에 친구 정보 state를 Firestore에 저장한다.
      • 1번과 3번은 문제가 없었지만 2번 과정이 문제가 있었다.

        useState는 비동기라고 알고 있기 때문에 아래와 같은 방식으로 코드를 입력했다.

        const [friendInfo, setFriendInfo] = useState(초기친구정보);
        const 친구정보저장하기 = async () => {
            console.log('업로드 시작');
            const 썸네일url = await 이미지Cloudinary에업로드();
            await setFriendInfo({...friendInfo, thumb : 썸네일url });
            친구정보Firestore에저장(friendInfo);
            console.log('업로드 끝');
        }

        결과는? 분명 친구 정보를 업데이트 후에 Firestore에 저장했음에도 불과하고 Cloudinary에 업로드한 url이 반영이 되어 있지 않는 문제가 있었다.

    • 원인

    • 해결 방법

      • 생각해보면 2번째 과정에서 state를 업데이트해주는 것은 view를 바꾸기 위한 것이 아니라 데이터를 사용하기 위함이었다.
      • 그래서 friendInfo 오브젝트를 copy_info라는 새로운 오브젝트에 복사하는 방식으로 useState가 await을 쓸 수 없었던 문제를 해결했다.
  • [#22] 카테고리 리스트 클릭 시, 해당 카테고리에 해당하는 친구 리스트 출력

    • 문제점

      • 비동기로 불러온 친구 리스트의 정보를 friendList라는 상태에 저장을 하는데
      • 카테고리를 클릭해서 친구 카테고리에 따라 배열을 나누면 아예 friendList 상태가 바뀌어서 전체 친구 목록 정보를 잃어버리는 문제가 있었다.
    • 해결 방법

      • 컴포넌트 자체에서 필터 함수를 만들고, displayList를 보여주기용 상태를 따로 추가했다.

아쉬운 점

  • 상태 관리를 오직 컴포넌트 내부에서 useState 훅을 사용해서 관리했기 때문에... 복잡하다.

    • ContextAPI나 ContextAPI를 좀 더 쓰기 편하게 만들어 놓은 Redux나 MobX의 필요성이 느껴진다.
  • 컴포넌트는 최대한 멍청하게 만드는 것이 좋다고 하여, 오로지 view만 담당하는 컴포넌트와 로직이 만들어지는 컴포넌트를 컨테이너라고 이름 붙여 역할을 나누게 하고자 했다. 그러나 점점 섞여서.... 깔끔하게 나뉘지 못한 것 같다.

  • postCSS 사용이 아쉽다.

    • postCSS는 클래스 명을 고유의 이름으로 자동으로 고치기 때문에 아래와 같은 방식으로 공통 css를 작성했는데 바르게 했는지 모르겠다. 변수명이 겹치는 것을 신경 쓰지 않기 위해 postCSS를 사용하는 것인데 common.css를 쓰는 게 맞나? 좀 더 공부가 필요한 부분이다.

  • 프로젝트 후반에 신경 쓴 일정 관리

    • 일정은 약 3주 소요됐다. 초반에는 시간 되는대로 작업을 진행하다가 계속 늘어져서 일정 관리 도입의 필요성을 느끼고 마일스톤에 일정을 등록하기 시작했다. 다음 프로젝트부터는 처음부터 일정관리를 도입할 생각이다.

마무리하며

아직 처리해야 할 이슈들이 남아있다. (심지어 이슈에 등록하지 않은 문제점도 많다!)

등록된 이슈 이외에도 state를 Redux나 MobX 등으로 관리하는 것으로 바꾸는 등 여러 추가 작업이 필요하다. 여러모로 고칠 점이 많은 프로젝트지만 그래도 작업하며 처음에 목표로 했던 '리액트에 익숙해지기'는 이 정도면 성공이라고 볼 수 있겠다.

'회고 > 프로젝트' 카테고리의 다른 글

토이프로젝트 개편하기 ~1탄~  (0) 2021.02.11
토이프로젝트 개편하기 ~0탄~  (0) 2020.12.13
댓글
공지사항
최근에 올라온 글
최근에 달린 댓글
Total
Today
Yesterday
링크
«   2024/05   »
1 2 3 4
5 6 7 8 9 10 11
12 13 14 15 16 17 18
19 20 21 22 23 24 25
26 27 28 29 30 31
글 보관함