마인드 관리는 역시 중요하다. 푹 자고 맑은 정신으로 코딩.
하기에 앞서서 git 특강 녹화 영상을 시청했다. git을 이용한 기본적인 로컬 레포지토리 관리법부터 팀 프로젝트를 진행할때 발생할 수 있는 conflict, commit 꼬임 문제를 예방하고 안전하게 기능 개발에만 몰입할 수 있는 좋은 방법을 배웠다.
예전에 React를 공부할 때 다른 사람의 github repo를 fork
해와서 내 코드와 합치는 작업을 한 적이 있었다. 그 때에는 branch의 개념도 전혀 몰랐고 HEAD
가 뭔지, 심지어는 commit
도 그저 push
를 하기 위해서 해야하는 것 정도로만 알고있었다. 그런 나를 벌하듯 코드가 왕창 꼬여버렸고 나는 나름 스마트한 방법인 Mac의 타임머신 기능을 이용해 코드를 되돌렸었다. 그게 나와 merge
의 첫만남이었다.
이번에 팀프로젝트를 진행하면서 벌써 두 번의 Pull Request가 있었는데, 첫번째 PR에는 의미 없는 변경사항이 다수 있었다. 바로 들여쓰기 문제였다. 팀원 중 한 분이 Prettier를 사용하지 않아 들여쓰기 설정값이 달라 발생한 문제였다. 프로젝트 repo 생성 후 초기 세팅 과정에서 .prettierrc
파일을 추가해둬서 안심하고 있었는데 이런 변수가 또 있었다. 아마 앞으로는 없을 문제겠지만 비단 repo 내부 파일이나 git 관리 뿐 아니라 개발 환경을 맞추는 것도 프로젝트 초기에 아주 중요한 일이라는 걸 알 수 있었다.
일단 PR을 close 하고 코드 수정을 요청했다. 그리고 팀원이 수정한 commit
을 다시 push
했는데, 여기서 모르는 부분이 발생했다.
우리 모두는 PR을 닫으면 내용이 사라지고, 다시 push
하면 새로운 PR이 생성되는 줄 알고 있었는데, 생각한 것과 달랐다. 왜 이런 방식으로 PR이 진행되는지에 대해서는 내일 튜터님께 여쭤봐야 할 것 같아 계획표에 넣었다.
두 번째 PR은 기존의 코드베이스와 겹치는 부분이 없는 새로운 기능 추가에 관한 것이었기 때문에 해당 코드를 작성한 팀원과 코드 리뷰를 통해 원만히 merge
를 진행했다. 그러니 결국 우리 팀은 제대로 된 컨플릭트를 경험해 보지 못 한 것이다.
회의가 계속되고 뭔가 아이디어도 계속해서 나오는데 다 비슷한 내용을 말만 다르게 표현하고 있었다. 시각화 도구가 필요했다. Figma계정을 생성하고 내가 생각하는 레이아웃을 그렸다. 일러스트레이터랑 비슷하면서도 더 쉽고 편리했다.
viewport
높이에 맞춰 화면에 보여져야 할 요소들을 표현했고, 팀원들과 대화하며 메인화면과 상세페이지의 레이아웃을 구성했다. 역시 같은 말을 하면서도 머리속으로 다 다른 그림을 그리고 있었다. 우린 모두 개발하러 온 사람들이니까 UI는 나중에 생각하고 기능 구현에 집중하자고 이야기했었는데, UI와 프론트엔드는 뗄 수 없는 관계라는 걸 모두 깊이 느꼈다.
메인 페이지가 틀이 잡혔다!
내가 개발을 맡은 메인 페이지 부분은 모든 기능들이 뻗어나가는 대전 IC 같은 곳인데, 내가 섣불리 코드를 얹었다가 다른 부분에 끼칠 side effect가 걱정스러웠다. 일단 git pull origin dev
로 최신 레포지토리를 가져온 후 최대한 보수적으로 코드를 작성했다.
const makeCards = async (pageNum = 1, media = "movie", group = "top_rated") => {
const data = await fetchMovieData(pageNum, media, group);
const cardList =
media === "movie" ? document.querySelector(".card-list-movie") : document.querySelector(".card-list-tv");
const { results, page } = data; // results === 영화 리스트, page === 페이지
cardList.setAttribute("data-page", page);
cardList.innerHTML += results
.map((item) => {
// 영화 객체의 제목, 이미지경로, 내용, 평점 property를 구조 분해 및 할당을 이용해 저장한다
const { title, name, poster_path, overview, vote_average, id, genre_ids } = item;
const nameByMedia = media === "movie" ? title : name;
return `<li data-id=${id} data-genres="${genre_ids}" class="movie-card">
<img src="https://image.tmdb.org/t/p/w500${poster_path}" alt="${title}"/>
<div class="movie-card-content">
<h3 class="movie-title">${nameByMedia}</h3>
<p class="movie-overview">${overview}</p>
<p class="movie-rating">${vote_average} / <span>10</span>
</p>
</div>
</li>`;
})
.join("");
위의 코드블록에서 비동기함수 makeCards
의 파라미터에 기본값을 지정한게 그 예시가 될 수 있겠다. 개인 과제 당시 아무 아규먼트 없이 호출해서 가장 평점이 높은 영화로 이루어진 카드리스트를 생성하기 위해 만든 함수이다. 헌데 다른 부분에서 이 함수를 많이 사용하고 있었다. 새로 구상한 메인페이지에는 평점이 높은 영화가 아닌 인기작들을 보여줘야 했고, 영화 뿐 아니라 드라마도 보여줘야했다.
const makeCards = async (pageNum = 1, media = "movie", group = "top_rated") => {...}
그래서 함수 파라미터들에 기본값을 설정해 아규먼트 없이 호출할 시에도 문제가 없게 만들었다.
저 부분을 제외하고는 머릿속에 있는 코드를 적어내도 문제가 발생하는 부분이 없었다. 지난번에 첫번째 리팩토링을 할 때 전역변수를 최대한으로 줄이려고 했었는데, 그 노력이 빛을 발했다고 생각한다.
하지만 역시 여럿이 같이 개발을 진행하다보면 부딪칠 일은 생기기 마련이다. 다른 팀원이 작성중인 코드와 내가 작성한 코드의 접근법이 많이 다르다는 것을 화면 공유를 통해 알았다. 내일 서로 코드를 보고 push
를 하고 컨플릭트를 해결할지, 아니면 그 전에 미리 서로의 장단점을 합칠지 결정해야 할 것이다.
내일은 아마도 내 push
로 말미암아 거대한 컨플릭트가 있을 것 같다. 모쪼록 무사히 멋진 하나의 브랜치가 되기를.