* Heroku로 배포해서 자주 sleep mode에 있을 것이므로, 처음 접속시 잠시 기다려야 할 수 있습니다.
2021-07-10(토) ~ 16(금) 7일간의 교류전이 끝났다.
이번 프로젝트에서 가장 맘에 들었던 것은 팀원들과 정말 조직적(문서 정리, 코드 리뷰)이고, 적극적이고 재밌게 협업했다는 것이다. 우리 팀은 Sejong.GG라는 이름(처음엔 '엽록소'가 될 뻔했다ㅠ)으로 '롤 퀴즈' 웹 게임을 만들었다. 웹 게임인 이유는 개인적으로 이번엔 백엔드로서 서버 api를 만들기보단 새로운 시도를 하고 싶었고, 마침 6월 말에 op.gg의 써-비스 경진대회에 지원하면서(떨어졌다) 생각해 본 서비스를 여기서 구현해보면 재밌겠다고 생각했기 때문이었다. 이 팀에서 팀장을 맡는 동안 짧은 기간 동안 회의도 매일 하면서 회의를 어떻게 진행해야 할지, 아이디어 설명 방법, 개발에서 팀장의 역할 등을 생각해볼 수 있었다.
개발 준비, 일정 수립
개발 전 준비할 것이 많을 것 같아서 교류전 시작 1주일 전부터 팀원들과 소통을 시작했다. 첫 회의에서 아래의 것들을 정하고 이후부턴 바로 스터디를 진행했다.
- '롤 챔피언 팁을 크롤링해서 챔피언을 맞추는 게임'을 큰 줄기로 기획을 보완하고 필요한 기능들을 생각해서 제품 백로그, 와이어프레임을 짰다.
- 개발에 필요한 기술들을 종합해서 스터디 범위를 정했다.
- 소통은 디스코드, 카톡을 사용하기로 하고 이때부터 회의록, 간략한 스터디 기록을 노션에 남겼다.
- 아이디어 설명에 필요하면 ppt나 그림판을 사용했다.
기록한 일정들 | 협업 관리, 회의록 |
스터디
JS(ES6)
우린 다 ES6을 써본 적이 없거나 익숙하지 않았는데 문법 정도는 개인적으로 짬짬히 챙기기로 했다.
Git 실습
1차 스터디 후 갑자기 Git실습에 대한 필요성이 느껴져 갑자기 꽂혀서 ppt를 만들어 2차 스터디에서 진행했다. 내가 알고 있는 내용을 잘 정리해서 전달하고 듣는 사람이 이해될 때까지 설명해주고 실습하는 게 재밌었다
Node.js
'생활코딩' 강좌로 Node.js에서 db에 쿼리 보내는 방법을 실습하고, ping-pong예제 일부를 따라해보면서 Node.js에서 Socket.io을 사용하는 방법을 이해했다.
Soket.io
책 'Node.js 교과서' 채팅방 예제를 따라 해 보면서 프로젝트 디렉토리 구성 방법, 라우터 구성 방법, Socket.io 사용방법, Socket통신 중 axios로 HTTP 통신하는 방법을 실습했다.
개발
교류전 1일 차 때 각자 개발해보고 싶은 부분을 고르기로 했는데, 그 영역이 굉장히 모호해서 처음엔 방향을 잡기 어려웠다. 제품 백로그에 기술한 기능별로 분담할까 했는데, 생각보다 개발하면서 팀원들과 미리 공유할 '뭔가'가 정해지지 않은 느낌이었다. 팀원들에게 미안하게도 어리버리 하고 있었는데 한 팀원 분(간x민 고맙다)이 프로젝트 초기 설정, 처음 개발할 영역을 제안해주고, 이어서 팀원들에게 Github을 이용한 협업 흐름을 설명하고 같이 실습했다.
이후부턴 팀원들과 개발 우선순위를 정해서 미리 정할 부분들(소켓 이벤트 이름, 페이지 이름 등)은 정하면서 분담을 진행할 수 있었다. 최종적으론 FE, BE 각 두 명씩 맡아서 분담하되 간x민과 내가 기타 library, db, 인프라 설정 등을 하기로 했다.
FE : 페이지 디자인, client 소켓 통신 설정 (나, 김x호 담당)
- 같이 FE를 개발한 팀원 분(김x호)의 디자인 센스에 놀랐다! 와이어프레임이 디자인을 반영한 것은 아니라 명확한 요구사항이 없었음에도 알잘딱깔센을 잘 실천한다는 생각이 들면서 다음 디자인은 어떨지 기대되게 했다ㅋㅋ
- HTML 페이지에서 쓰인 {% %} 형태의 템플릿 언어 정체가 뭔지 한참 알아보다 Nunjuck인 걸 겨우 알게 됐다..
- 사용자가 정한 닉네임을 sessionStorage에 저장해서 만료될 때까지 싱글 게임, 랭크, 채팅방 client에서 사용할 수 있게 했다.
- Client 쪽 소켓 이벤트를 구현하다가 Server 쪽까지 작업해볼 기회가 있어서 소켓 통신이 잘 이해되었다. 소켓이 이벤트 기반으로 통신하므로 실시간 통신이 가능하다.
Server, Client 간 구분이 모호한 대신 차이점은 Client에서 처음 소켓 연결이 됐을 때 Server에서 먼저 이벤트를 송신할 수 없었고, Client에서 먼저 이벤트를 송신해야 했다.(클라이언트가 서버에 소켓 연결 성공하자마자 서버에서 이벤트를 emit 할 수 없었다ㅠ)https://github.com/kimhanui/chatting-demo/blob/main/socket.js 에선 서버에서 먼저 emit할 수 있었다. 롤 퀴즈에서 안됐던 데는 다른 이유가 있었던 것 같다.
추가
- 소켓통신을 더 자세히 알게되면 Namespace라는 개념이 등장하는데 같은 Namespace에 연결된 소켓끼리 통신이 가능하다. Namespace를 목적에 따라 잘 구분하면 해당 Namespace에서 발생하는 이벤트를 제어하기 용이해진다(예: 문제 채점, 서버에서 문제 가져오기 -> 싱글 게임에서만 발생하는 이벤트이므로 하나의 Namespace로 묶는다). 또한 서버에선 이 Namespace에 연결된 클라이언트 모두에게 이벤트를 전송(broadcasting)할 수 있고 다른 Namespace내에서 같은 이름의 이벤트를 사용할 경우 이벤트 구분이 가능하다.
- 구상하다보면 클라이언트를 하나의 방으로 묶고 싶다는 생각을 하게되는데 실제로 Socket.io에선 Room이란 개념을 설명한다. Room은 '클라이언트가 join 또는 leave할 수 있는 임의의 채널'이고, join 메서드로 클라이언트를 특정 채널에 subscribe하게한다. 서버에서 어떤 클라이언트가 연결됐을 때 특정 Room에 join하게 만들면 그 클라이언트는 해당 채널에서 broadcasting되는 이벤트를 받을 수 있고, 이런 기능을 사용하면 채팅의 입,퇴장문을 구현할 수 있다.
- Namespace와 Room의 차이는 종속관계에 있는데 Namespace하위에 Room을 구성한다고 생각하면 된다.
...
Rooms are part of namespaces where each namespace can be divided into several rooms
and a very room handles a certain type of sockets (Join & Leave) it basically works by a socket (user) sends a join request to one of the available rooms and the server joins it in the room (it could need authentication or invitation depending on your application).
기억에 남는 이슈
싱글 게임 클라이언트에서 확인 버튼을 누르면 서버에서 답을 채점하고 결과를 받아오면서 새로운 문제를 받아왔는데 확인 버튼을 누를 때마다 새로운 문제를 받는 이벤트가 한 번에 1번, 2번, 3번, 4번, 5번,... 식으로 중복 실행되는 버그가 있었다.
내 상황에서 원인은 버튼을 누를 때마다 이미 등록된 이벤트 리스너가 또 '추가'됐기때문에 새로운 문제를 받는 이벤트가 누적 수신된 것이었고, 이는 socket.off라는 기능을 이용해 이벤트 리스너가 중복 추가되지 않도록 해서 해결했다. (아래)
function addConfirmEvent(e) { // 확인 버튼에 적용할 이벤트
socket.emit('answer'); // 서버에 채점 요청
socket.on('correction', function(data) { // 채점 결과 반환
// ...
socket.off('correction'); // 소켓이벤트 중복 실행방지.
// 버튼 이벤트 발생시 해당 이벤트가 계속 추가되어 발생
// 다음 문제로 넘어감 or 게임 종료
}
}
BE : 라우터, server 소켓 통신 설정, mongoose 사용, crawling api 생성 (서x현 님, 간x민 담당)
- 페이지 리다이렉트 : 세션에 사용자의 닉네임이 없으면 닉네임을 정하는 페이지로 리다이렉트하게 했다.
- 싱글방, 채팅방, 랭크 : 소켓 이벤트 구현
- mongoose를 사용하여 랭크 페이지에 보여줄 사용자, 크롤링해 온 챔피언 정보, 채팅방에 입력한 채팅 내용을 저장했다.
- heroku에 서버 배포, mongodb 적용
발표 및 시연, 수상
ppt는 서x현 님이 깔끔한 템플릿을 직접 만들어서 제작해주셨다. 발표는 내가 했는데 긴장해서 전달력이 있었는진 모르겠다ㅋㅋ... 모든 팀 발표 및 시연 후 참여자들은 skribble.io를 하면서 대기했다. 평가는 각 학교 동아리 대표 분이 진행했고 우리 팀은 자아분열하다시피 "롤 퀴즈가 다른 사람들이 재미없대도 우리만은 재밌는 거야... 근데 우리 1등 감이야ㅋ" 하고 있었는데 수상해서 좋았다...!
회고
- 팀원 간x민 님이 '회고'라는 재밌는 시간을 제안해줘서 노션에 회고 기록까지 남길 수 있었다. 나를 포함해 다들 비슷하게 Node.js와 Socket.io를 사용해 본 것에 만족한 반면, 4인용 멀티 게임을 구현하지 못한 아쉬움이 있었다.
- 개발을 진행하기 전 개발 흐름을 설명하고, 이슈 템플릿, 브랜치 이름 정하기, 서로 pr을 올리면 2명 이상이 리뷰&어프로브해야 Merge할 수 있게 하는 등 협업 컨벤션을 정했다. 노션에 회외록, 개발 기획 문서, 일정 등도 깔끔히 정리한 것 같아서 내 기준 실제로 '조직적인 협업'을 실천한 프로젝트였다고 생각한다ㅋㅋ 또 개발 주기가 짧은 만큼 회의도 잦았는데(마지막 날엔 2시간, 1시간, 30분 간격으로 회의했다ㅋ) 각자 최대한 가능한 시간대를 맞춰서 시간을 투자해줘서 좋았다!
- 개발 기간 중간쯤 느낀 것인데 개발에서 팀장의 역할은 pr 올라오면 로컬에서 잘 실행되는지 확인해보는 것이었던 것 같다. pr이 너무 많거나 회의 시간 다 돼서 올라오면 화면 공유로 각자 작업했던 부분을 실행시켜서 로그로 확인시켜주거나 FE는 페이지 동작을 보여주는 식으로 하면 될 것 같다.(회의 시간이 결국 각자 작업 진행도를 확인하는 시간이었기 때문)
- 마지막으로 인터페이스 책 지원 감삼다^^
댓글