All ContentsCategoryAbout

2022년 회고

01 January, 2023 - think - 12 min read

edward hopper - office in a small city

1분기


주요 이슈

  • 쇼핑몰 개편
  • 유료회원 정기결제 프로세스 고도화
  • 알림톡, 푸쉬알림 점검
  • 쿠폰 시스템 개발
  • api 서버와 크론서버 분리
  • 풀필먼트 업체 변경
  • 외주 프로젝트 개발



1분기에는 쇼핑몰 개편이 가장 큰 이슈였다. 특히 기존에 하드코딩으로 작업하여 한 번 변경하려면 앱 업데이트를 해야했던 메인화면의 레이아웃을 어드민에서 설정값만 수정해도 추가/수정/삭제가 가능하도록 모듈시스템을 도입하는 것이 관건이었다. 이것을 어떻게 구현하는 게 좋을까 오랜 기간 고민한 끝에 상품목록의 스크롤 방향, 썸네일의 크기, 보여지는 상품 수 등을 설정하는 '테마'와 이런 테마들을 리스트로 저장하고 저장된 순서대로 한 화면에 보여주는 '스크린'으로 스키마를 구성했다. 테마의 타입은 상품 썸네일을 보여주는 item, 쿠폰을 발급할 수 있는 button, 특정 페이지로 이동하거나 정보를 제공하는 banner 등으로 나누었고, 이러한 여러 테마들을 스크린의 각 row마다 리스트 형태로 저장하는 column이 존재한다. 이를 통해 각 화면에 보여지는 요소들을 DB 조작만으로 추가/수정/삭제할 수 있도록 하였다. 초기에는 심플하게 설계하였는데, 기획 단계에는 없던 컬러설정, 카테고리 노출 여부, 상품 정렬 순서 등의 추가 요청들로 테마 테이블에 다수의 column이 추가되어 현재는 상당히 복잡한 구조가 되어버렸다. 1년이 다 되도록 우선순위에 밀려 여태 어드민은 개발하지 못했고, 매번 내가 직접 쿼리를 작성하여 수정하는데... 아직 어드민 개발 계획도 잡혀있지 않지만 언젠가 개발하게 될 그날이 벌써 조금 두렵다.

기존에 이용하던 풀필먼트 업체와의 계약이 종료되고 다른 업체의 api를 이용하게 되었다. 처음에 생각했던 것과는 달리 막상 작업해보니 상당히 손이 많이 가는 작업이었는데, 단순히 api 연동만 하면 되는 게 아니었다. 결제 이후에 주문이 들어가는 프로세스나, 주문취소 요청 후 결과 확인 후 환불 프로세스를 진행해야 하는 등 트랜잭션을 고려해야 하는 부분들도 같이 수정되어야 했기 때문이다. 무엇보다도 상품의 PK가 다르기 때문에 신규 테이블에 상품데이터를 추가해야 했는데, 당연히 필드명도 기존과 상이했고 그동안 쌓인 데이터들에 대한 무결성을 유지하기가 상당히 힘이 들었다. 테이블과 필드를 하나하나 대조하며 쿼리실행계획을 세우고 신중하게 진행해야만 했다. 그럼에도 불구하고 이후에 지속적으로 누락된 부분을 발견하고 그때마다 수정해야만 했다.

대표님을 통해 외주개발을 하나 하게 되었다. 재밌게도 프론트와 백으로 나누어 한 게 아니라 프로세스별로 나누어 각 프로세스에 필요한 프론트와 백을 모두 개발하게 되었다. 이게 되나 싶었지만 막상 해보니 장점도 있고 단점도 있었다. 장점이라면 화면을 만들며 필요한 api를 그때그때 직접 제작하고 붙일 수 있다는 점이었고, 단점이라면 프로세스 단위로 나누어 급하게 작업하다 보니 프론트나 백이나 일관성이 다소 떨어진다는 점이다. 꽤 오랜만에 리액트를 하기도 했고, react-router-dom v6는 처음 사용하다 보니 초반에는 상당히 헤맸던 기억이 난다.



2분기


주요이슈

  • 쇼핑몰 기능 추가

    • 최소구매수량 적용
    • 쿠폰팩
    • 쿠폰 발급 및 사용 조건 적용
  • FCM 적용
  • SQL 세션 진행
  • amplify
  • 트랜잭션 점검
  • 트릿(앱 내 재화) 기능 개발
  • UTC 이슈
  • 개발자 면접

    • JD 작성



2분기에도 쇼핑몰 기능을 대거 개발하고 수정했다. 매번 느끼는 게 있다면 역시 커머스는 손이 많이 간다는 것이다. 만약 이직을 하게 된다면 커머스를 하는 회사 혹은 팀으로는 가고 싶지 않다.

기존에 AWS SNS를 이용하던 push notification을 파이어베이스 기반의 FCM으로 교체했다. 하는 김에 이를 모듈로 만들어 기존보다는 편하게 추가할 수 있도록 수정했다. 교체하게 된 이유로는 AWS SNS가 ios과 android에 각각 발급하는 토큰이 다르다는 점과 테스트가 용이하지 않다는 점에 있었다. 전자는 사실 큰 문제가 될 건 없지만 후자는 충분한 이유가 되었다.

사내 임직원을 대상으로 매주 1시간씩 4주간 SQL 세션을 진행했다. 비록 자발적인 건 아니었지만 나로서도 나름 얻는 바가 있던 시간이었다. 나 또한 SQL을 제대로 배운 게 아니라 입사 후에 독학 반, 실무 반으로 익혔기 때문에 지식에 공백이 많았는데, 세션을 준비하고 질문에 답을 하는 과정에서 기존에 알고 있던 것들을 점검하고 공백을 메울 수 있는 계기가 되었다. 여건 상 join까지밖에 진행하지 못 한 점이 조금 아쉬웠다. 그리고 나는 아니라고 생각했는데, 어느새 나도 지식의 저주에 걸렸다는 것을 깨닫게 된 시간이기도 했다. 이때부터 최대한 배경지식이 전무하다는 가정 하에 설명하려 노력하고 있다.

프로모션 페이지를 개발하고 배포해야 하는 일이 생겼었는데, 기존 DNS로 배포할 수 없는 상황이었다. 그래서 간단한 배포 방안을 찾다가 Amplify라는 도구를 발견했다. 기존에는 EB(Elastic Beanstalk)만 사용해왔기에 호기심이 동하였다. 특히, 프로모션 페이지는 정적페이지이기에 가볍게 배포하기 좋은 도구라는 생각이 들어 문서를 찾아보며 배포를 진행했다. 최초 설정이 가장 복잡했을 정도로 이후 작업은 신속하고 간편했다. 기존에 내 블로그를 netlify로 호스팅하고 있었는데 이와 별반 다르지 않아 비교적 수월했던 것 같기도 하다.

5월부터 6월까지 한달 반 정도 4시에 기상하여 첫차를 타고 6시에 출근을 했다. 이 시기에 기획회의가 많아서 코딩을 할 수 있는 시간을 확보하기가 어려웠고, 그래서 아예 일찍 와서 3~4시간 정도 시간을 가졌다. 부족한 공부도 하고, 해야할 업무도 미리 하는 시간으로 이용했다. 확실히 아침일찍 조용한 사무실에서 혼자 작업을 하니 집중이 잘 되었는데, 문제는 퇴근시간은 일찍 나오기 전과 동일했다는 것이다. 이렇게 한달 반을 했더니 몸이 축나서 도저히 지속할 수 있는 컨디션이 아니었다. 만약 추후에 재택을 할 수 있는 여건이 되거나 자율 출퇴근이 가능한 상황이라면 다시 도전해보고 싶다.



3분기


주요이슈



2022년을 돌이켜 볼때 가장 임팩트가 큰 사건사고는 하반기에 일어났던 것 같다. 데이터베이스를 날려버린 대형사고는 4분기 파트에서 후술할 것이며, 3분기에는 무려 해킹을 당해버렸지 뭔가! 지금 다시 떠올려봐도 상당히 아찔한데, 심지어 사건발생일은 내가 연차였다. 모처럼의 휴가를 만끽하고 있었는데 점심 이후에 AWS로부터 메일이 한 통 도착했다. 대충 우리 계정에서 수상한 움직임이 감지되었다는 내용이었다. 처음 받아보는 내용에 이게 뭔가 싶어 콘솔에 접속했더니 아니나 다를까 모든 리전에서 수백여개의 인스턴스가 생성되어 활발히 작동 중이었다. 연차고 나발이고 오후 5시쯤 급하게 출근을 했다. 다행이랄까 AWS 측에서 이미 추가 리소스가 생성되는 것은 제한해둔 상태였고, 이미 생성된 리소스들만 작동하고 있었다. 새롭게 생성된 리소스를 하나하나 살펴보니 주요 리소스는 EC2와 Lambda인 것 같았고, CloudFormation에서 템플릿을 이용하여 대량으로 생성한 것으로 보였다. 템플릿을 보니 이더리움을 채굴하는 코드로 보였고, 역시나 EC2의 CPU 사용량이 90%대까지 치솟고 있었다.
기존 리소스가 아닌 신규 생성 리소스들을 리스팅하여 제거하고 AWS support를 통해 회신을 보냈다. 짧은 영어실력으로 파파고를 십분 활용하여 작성했던 기억이 난다. 이때까지만 하더라도 이정도로 일단락될 줄 알았다. 그런데 AWS에서 돌아온 답변은 보안수칙을 모두 적용하기 전까지는 신규 리소스 제한을 풀어줄 수 없다는 것이었고, AWS의 답변은 매우 느렸고, 심지어 시차도 있었다. 신규 리소스 제한이 풀리지 않으면 오토스케일링이 제대로 동작하지 않을 것이고, AWS에서 제시한 보안수칙을 정해진 기한 내에 수행하지 않으면 최악의 경우 계정이 삭제될 가능성도 있었다. 그래서 우선 보안수칙을 하나하나 확인하여 적용했다. MFA(multi-factor authentication)와 IAM이 대표적이었는데, 소 잃고 외양간 고친다는 말을 몸소 겪게 될줄은 꿈에도 몰랐다. 이 간단한 걸 왜 진즉에 하지 않았던가... 후회해도 이미 늦기에 문서를 참고하여 꼼꼼하게 설정했다. 그리고 회신을 하였으나 답이 없었다.
AWS의 답변이 오기만을 마냥 기다리기엔 여유가 없었기에 플랜B를 동시에 실행했다. 플랜B는 새로운 계정을 만들어 서버를 생성하는 것이었다. 오토스케일링이 필요한 것은 인스턴스뿐이었기에 기존 계정의 RDS와 S3는 그대로 둔채 EB(Elastic Beanstalk)으로 서버만 만든다는 계획이었다. 기존 설정을 참고하여 금방 만들 수 있었고, Route53으로 도메인을 연결했다. HTTPS 적용을 위한 인증서 발급에 약간 시간이 걸렸지만 다행히 자정 무렵엔 급한 불은 끌 수 있었다.
또한, 기존 클라이언트에서 S3 key를 갖고 직접 접근하여 이미지를 업로드하고 있었는데, 이부분도 보안에 취약할 것으로 판단하여 AWS cognito와 s3 multer를 이용하여 api 형태로 만들어 서버를 거쳐 업로드 되도록 수정하였다.

AWS 이슈가 마무리될 즈음 포인트 차감 오류가 발견되었다. 심지어 매번 발생하는 오류가 아니라 드문드문 발생하여 원인을 찾기 힘들었는데, 디버깅 모드로 한줄한줄 실행해보며 문제가 발생하는 구간을 찾을 수 있었다. 구매 시 사용한 총 포인트를 구매한 상품별 금액에 따라 총금액 대비 해당 상품의 금액의 비율로 나누어서 차감하는 프로세스로 forEach로 처리하고 있었다. 그런데 이게 문제였다. forEach는 배열을 순회하며 콜백을 호출하기만 할뿐 다음 콜백을 기다려주지 않기 때문이다. 다시말해 async/await이 통하지 않는다. 우선은 for..of로 변경하여 문제는 해결하였으나 이를 통해 내가 아직 자바스크립트에 대한 이해가 많이 부족하다는 것을 절실히 느꼈다. 겸손하게 공부하자...

개발자가 되고나서 처음으로 오프라인 컨퍼런스를 참석했다. 역삼역 마루180에서 진행되었는데, 나와 비슷한 연차의 주니어 개발자들이 연사로 나온다는 것에 흥미가 생겨 참석했다. 개중에는 나와 유사한 환경에서 성장한 개발자도 있었고, 전혀 다른 환경과 전혀 다른 분야에서 성장한 개발자도 있었다. 여러모로 자극을 받을 수 있는 기회가 되었다.

새롭게 진행 중인 프로젝트에서 크롤링과 머신러닝 등의 기술이 필요하게 되어 갑작스럽게 파이썬을 익히게 되었다. 기본적인 문법들만 우선적으로 훑어보고 레퍼런스를 참고하여 리뷰 크롤러를 만들었다. 그리고 EC2 인스턴스를 하나 생성하여 crontab을 설정하여 반복되도록 하였다. 다만, selenium을 사용하기 때문에 가상디스플레이를 띄워야 했는데 이게 EC2 환경에서는 너무 느리다는 게 문제였다. 로컬에서는 6초 걸리는 작업이 EC2에서는 10분이 걸리는 게 웬말인가... 이 부분에 대한 대책은 아직도 강구하는 중이다. 도

4분기


주요이슈



확실히 스타트업 혹한기를 체감하게 된 시기다. 우리도 인원을 감축하고 사무실 이전을 했지만, 힘든 건 우리 뿐만이 아니라는 것을 절실히 느낄 수 있었다. 우리가 이용하던 외부 서비스들 중에도 서비스 종료 공지를 하거나 축소되는 경우가 심심치 않게 나왔기 때문이다. 특히, 전혀 신경도 안 쓰고 있던 알림톡 딜러사가 서비스 종료를 공지하여 부랴부랴 다른 업체를 알아보게 되었다. 선례가 있었기 때문에 되도록 탄탄해 보이는 업체로 선정하였고 한달 가량의 시간밖에 없기에 빠르게 SDK 교체 작업을 진행했다. 그런데 여기서도 예상치 못한 문제가 발생했는데, 기존 우리 서버의 Node.js 버전과 SDK의 최소 요구 버전이 맞지 않는 것이다. 그래서 Node.js 버전을 올렸더니 이번엔 기존에 사용하던 다른 라이브러리들의 호환성 문제가 불거졌다. 결국 계획을 체계적으로 세워 대대적인 버전업 작업을 진행해야만 했다. 우선 EB(elastic beanstalk)의 플랫폼 버전에 따라 지원하는 Node.js 버전이 다르기에 환경을 우선 생성하고 점진적인 테스트 후에 도메인을 옮기기로 하였다. dev, batch, production 서버 순으로 진행을 했고 결과적으로는 기한 내에 완료할 수 있었다. 이전까지는 버전문제가 딱히 없었기에 간과하고 있었던 부분이라 여러모로 느끼는 바가 있었다.

두 번째 오프라인 컨퍼런스를 참석했다. 그린랩스에서 주최하는 함수형 프로그래밍 관련 컨퍼런스였는데 대기번호를 받고 있다가 운 좋게 참석할 수 있었다. 특정 회사에서 주최하는 오프라인 컨퍼런스는 처음이라 상당히 설레는 기분으로 참석했는데 컨퍼런스의 꽃이라는 티셔츠와 스티커 등의 굿즈와 더불어 최근 흥미를 갖고 있던 함수형 프로그래밍에 대한 이야기까지 들을 수 있는 좋은 기회였다. 다만 내가 주력으로 사용하는 자바스크립트를 사용한 케이스는 없어서 살짝 아쉬웠다.

그린랩스 컨퍼런스



2022년 최악의 실수를 꼽는다면 단연코 production DB 삭제썰을 이야기할 수 있다. 일전에 해킹사건으로 인하여 사용 중인 계정이 둘로 나뉜 상황이었다. 여느날처럼 출근 후 각각의 계정에 접속하여 문제는 없는 지 체크하고 있었더랬다. 그런데 유난히 그날따라 지금은 사용하지 않는 예전 EB환경이 거슬리는 게 아닌가. 이젠 삭제해도 되겠다 싶어 삭제를 진행했다. 그리고 삭제되는 과정을 로그로 지켜보고 있는데 그중에 RDS가 눈에 띄었다. "어?"

어 금지

충분히 놀랄만한 상황이었기에 자연스럽게 탄식이 흘러나왔다. 머리가 쭈뼛 서고, 머리 끝부터 발 끝까지 온몸의 모공이 열리는 기분이었다. 뒤늦게 심각성을 느끼고 중단을 시도했으나 되지 않았다. 그저 DB가 제거되는 과정을 바라볼 수밖에 없었다. 지금 생각해도 정말 배가 싸르르 아파지는 것 같다. 해당 EB환경과 RDS가 연동되어 있었던 것이다.
어쨌든 이미 돌이킬 수 없는 상황이 되어버렸고, 결국 DB는 그렇게 날아갔다. 혹시나 싶어 앱을 켜봤는데 역시나 앱은 실행이 되지만 DB에서 받아와 보여줘야할 데이터들은 하나도 보이지 않았다. 마냥 넋을 놓고 있을 수는 없기에 즉시 대표님과 동료들에게 이 상황을 알렸고, 대책을 찾기 시작했다. 백업은 한참 이전의 날짜였기 때문에 다른 방법을 찾았고 다행히 삭제되던 당시의 스냅샷이 남아있었다.
스냅샷을 통해 동일한 버전과 설정으로 DB를 생성했다. 심장이 아플 정도로 DB가 생성되는 시간이 길게 느껴졌다. 이윽고 DB가 생성되었고 변경된 host를 서버 코드에 반영하여 배포했다. DB가 다시 작동하기까지 약 1시간 정도의 시간이 걸렸다. 더 최악이 될 수 있었는데 이정도로 수습이 된 게 천만다행이었다. 만약 스냅샷이 없었다면...😱 아, 상상도 하기 싫다.
리소스를 삭제할 때에는 최소 3번은 다시 생각해보고, 삭제 전에는 백업을 하자!



크롤링을 해야 하는 데이터가 웹에는 없고 특정 앱 내에만 존재하는 케이스를 만나게 되었다. 앱 크롤링 방법을 일주일 정도 찾아보다가 proxy를 이용하는 방법을 찾아 진행했다. mitm-proxy라는 프로그램으로 프록시 서버를 열고 안드로이드스튜디오 AVD를 실행하면 앱 내에서 호출하는 api들의 정보가 출력되는데 이를 통해 api 호출방법을 확인하고 데이터를 가져오는 방식이었다. 이 과정에서 그동안 몰랐던 개념들을 익히고 프록시에 대한 이해가 조금 더 생겼다.



2022년 총평


열심히 하는 걸로는 부족하다는 것을 느낀 해였다. 열심히는 당연하고, 잘해야 하며, 운도 따라줘야 한다. 그런데 과연 열심히는 했는가? 스스로를 돌아봤을 때 당당하게 그렇다고 하긴 어렵다고 생각한다. 물론 '일'만 놓고 봤을 때에는 그 상황에서 내가 할 수 있는 최선을 했다. 새로운 문제는 가능한 레퍼런스를 최대한 찾아 해결하고, 경험해본 문제는 이전보다 능숙하게 해결했다. 그러나 '개인'의 성장을 놓고 봤을 때에는 조금 허탈해진다. 실무를 통해 전방위적인 지식과 스킬은 얻었으나 뾰족한 하나를 얻지 못했다. 2023년은 내가 개발자로 벌어 먹고 산지 3년이 되는 해다. 이젠 단순히 '맡은 업무만' 잘해서는 안 된다고 생각한다. 보다 넓은 시야로 보고 깊게 생각하며 오랫동안 키워나갈 비장의 무기를 다듬을 때가 아닌가 싶다. 지금이 나의 '영광의 시대' 라는 마음으로 살아야 할 때다.

영광의 시대 영광의 시대



2023년 목표


  • vim 익숙해지기
  • DB 깊은 공부

    • 작동원리
    • 설계
    • 쿼리 최적화
  • 매월 일반서적 1권, 기술서적 1권 읽기
  • Nest.js로 토이프로젝트



vim을 꾸준히 사용하며 익숙해질 것이다. 왜냐하면 키보드로만 작업하는 개발자는 멋있으니까... 매번 vim 확장프로그램을 설치하여 써보려다가 막상 업무가 급해지면 답답해서 지우곤 했는데, 올해는 꾸준히 사용해볼 것이다. 간단한 단축키부터 차근차근 익숙하게 쓰고 필요한 동작이 있으면 단축키를 찾아보며 사용할 것이다.

재작년에도 느끼고 작년에도 느꼈지만 데이터베이스는 정말 파도 파도 끝이 없다. 어느 정도 안다고 싶었지만 막상 해보면 어줍잖은 실력이 여실히 드러난다. 올해도 역시 데이터베이스를 공부할 것이다. 최소한 MySQL만이라도 작동원리와 무결성을 확보한 설계방법을 다시 한 번 공부해야 한다는 것을 느낀 2022년이었다. 그리고, 가능하다면 기존 쿼리들을 최적화하고 싶다.

2022년은 정말 책을 안 읽었다. 5권은 읽었으려나? 기술서적은 그럭저럭 필요에 의해 읽었으나, 일반서적을 정말 안 읽었다. 스타트업이라는 게 개발자가 개발만 해서는 도저히 서비스가 굴러갈 수가 없는 구조다. 그리고 개발 외적인 일들에는 잡다한 지식들이 두루 필요함을 느꼈다. 우선 매월 일반서적 1권, 개발서적 1권으로 목표를 정하긴 했으나, 사실상 중요한 것은 '얼마나 읽었는가 아니라 어떻게 읽었는가'이기 때문에 숫자에 크게 연연하지는 않을 것이다. 그보다는 책을 읽고 그 내용을 내 삶과 일에 어떻게 적용할 것인지를 깊게 생각하는 해가 되길 바란다.

최근 신규 프로젝트의 구조와 기술스택을 정하며 Nest.js에 관심이 생겼다. 안타깝게도 시간적인 한계로 익숙한 Express.js를 그대로 쓰게 되었지만, Nest.js는 개인적으로도 관심이 생겼기에 별도로 토이프로젝트를 진행해볼 생각이다.

© 2023 intzzzero, Built with

Gatsby