공부 연습장 :-)

마트쉬는날 프로젝트 회고

|

프로젝트 개요

  • 마트 휴무일을 검색하기 귀찮은 사람들을 위한 마트쉬는날 알리미 iOS앱
  • 팀프로젝트(iOS 1명 + 백엔드 1명)
  • 수행기간: 2018.08 ~
  • App Store

앱의 주요 기능

  • 브랜드별 마트 검색기능, 상세정보를 제공한다.
  • 즐겨찾는 마트를 저장할 수 있다.
  • 즐겨찾는 마트의 휴무일을 앱 메인 화면과 위젯에서 확인할 수 있다.
  • 즐겨찾는 마트의 휴무일 하루 전, 유저에게 푸시로 휴무일 알림을 보낸다.
    • 푸시 기능은 FCM(Firebase Cloud Messaging)과 Firebase DB를 사용하여 구현함

제 앱은 이렇게 생겼습니다

만들게 된 동기

  • 처음에 iOS시작할때, 때가 되면 내가 필요한 앱을 만들어보자는 목표가 있었다.
  • 사소한걸 깜빡하는 성격도 한몫했다. 마트 휴무일도 자주 까먹어서 쉬는날 마트 문 앞까지 갔다가 헛걸음한게 한두번이 아니었다.
  • 휴무일 주말이면 네이버 실검에 OO마트 휴무일이라는 검색어가 뜨는 경우를 발견했다. 어...나만 불편한게 아니네!? 라는 생각이 들었고
  • 결국, 만들어야겠다고 결심!

힘들었던 점 / 신경쓴 구현

1. 즐겨찾기 데이터 모델 설계

이슈

  • 앱 전체를 관할하는 핵심이 되는 객체(FavoriteList)를 최대한 효율적이고 간단하게 구현하고자 노력

해결

  • 한 유저당 하나의 즐겨찾기(FavoriteList객체)만 존재해야하므로 Singleton으로 구현
  • 즐겨찾기를 pop / push 한 후 성공여부를 전달하기위해 Bool값을 리턴하는 기능이 핵심인 즐겨찾기 전용 stack구조 구현
  • 즐겨찾는 마트정보는 마트객체의 속성중 id: IntSet<Int>타입으로 저장한다.
  • 유저의 즐겨찾기 설정값을 저장하기위해, NSCoding을 구현하고 UserDefaults와 NSKeyedArchiver를 사용해서 객체를 아카이빙하는 방식으로 저장

2. 중복 코드 제거(프로토콜 / 상속 등으로 추상화 된 객체 구현)

이슈

  • 중복코드를 만들어냈던 기능들: 정보 검색과 열람 / 즐겨찾기 추가 삭제 / 뷰 컨트롤러에서 인터넷 연결 확인
  • 정보를 제공하는 기능이 주가 되는 앱이다보니, 위와 같이 여러 뷰컨트롤러에서 사용하는 공통적인 뷰와 이벤트를 처리하는 기능이 중복되었고, 결국 커다란 중복코드 덩어리를 만들어냈다.

    해결

  • 뷰에서 발생한 이벤트를 처리하는 Custom Delegate객체를 구현하여 뷰컨트롤러의 중복코드를 제거했다.
  • 또한 커스텀 객체를 만들땐 최대한 프로토콜과 상속을 사용하여 기능확장성과 재사용성을 높였다.
  • 주로 Delegate객체는 프로토콜을 사용했으며, View나 ViewController는 상속을 사용하여 서브클래싱하여 구현했다.

앱스토어 Reject

  • 떨리는 마음으로 완성된 앱을 제출했는데, 이틀 후 결과가 날아왔다. Reject이라고. 이유가 더 충격이다. 이유는 App Completeness - We were unable to review your app as it crashed on launch.였다…
  • 여담이지만 이 시기에 나는 너무 정신적으로 체력적으로 약해져있어서, 저 문구는 마치 나에겐 앱이 런칭도 안돼서 내부 테스트도 못했다. 이런 허접을 만들어놓고 우리한테 리뷰를 바라는거임? 이라고 말하는 것 같았다 ㅠ_ㅠ

Crash 이유

  • Crash report 분석결과, AppDelegate내의 FCM푸시토큰을 받아오는 콜백함수에서 옵셔널 값에 접근하는 문제가 있었다.
  • Optional Forced-unwrapping으로 Bool!타입으로 선언된 변수가 있었고, 해당 변수에 값이 할당되기 전에 콜백함수 내에서 해당 변수에 접근한 문제였다.
  • 앱을 처음 설치하면 Push Notification 승인에 대한 alert가 화면에 나타나는데, 문제가 되는 변수에 값을 할당하기위해서는 해당 alert창의 버튼을 선택해야했다.
  • 하지만 만약 유저가 해당 alertallow / don't allow를 바로 선택하지 않고 기다리면 콜백함수가 먼저 실행되어, nil값에 접근하는 상황이 발생했다.

해결

  • 해당 변수를 Bool?타입으로 선언하고 바인딩 후 사용하는 방식으로 변경하여 해결했다.

회고

  • 실행 시점을 정확히 예측하기 힘든 콜백함수에서는 어떤 작업을 하든지 신중하게 해야함
  • 또한, 여러 상황을 가정해서 테스트해야함. 유저가 당연히 내가 예상하는 액션을 그대로 할 것이라고 예상하는 것은 굉장히 위험한 발상!!
  • 옵셔널처리같은 사소한 문제에서 정말 critical한 문제가 발생한다는 것을 깊이 새기게되었다..(배운대로만 코딩해야겠다)
  • 게다가 이것만 고쳐서 앱을 제출했더니 바로 승인됐다. 실수만 없었다면 한번에 승인됐을지도…

기술적인 부분 이외의 힘들었던 점

디자인

  • 핀터레스트에서 모바일UI / color palette 검색해서 아무리 보면 뭐하나. 디자이너 말고 개발자로 전향하길 잘했다고 느끼는 계기였다.
  • 그나마 여러 사람에게서 피드백을 들어서 앱 메인 색깔 정하고 테이블뷰 재구성하는 식으로 변경했다. 역시 협업과 수요조사의 힘이란!
  • Flaticon, 키노트, 나눔글꼴 만드신 분들 복받으세요!

일정

  • 고백하자면, 처음엔 이 프로젝트가 두 달이나 걸릴지 예상을 못했다. 한 달 정도에 끝내려는 프로젝트였는데 혼자서 처음부터 끝까지 진행하는 첫 프로젝트라서 예상치 못한 곳에서 시간이 많이 걸렸다.
  • 갑자기 잘되던 파이어베이스가 말을 안들어서 애플 개발자 사이트에서 프로비저닝 파일을 몇번이나 만들고, 그러다가 프로비저닝이 꼬여서 빌드 자체가 안되고, 중간에 개발자 계정을 바꾸느라 또 애플 개발자 사이트에서 한나절을 넘게 보낸 적도 있었고…App Extension과 프레임워크 디펜던시 문제로 몇 일동안 빌드가 안된 적도 있고..블라블라…
  • 사실 코딩 이외의 신경 쓸 것들이 많아서 시간이 많이 걸렸다ㅠ_ㅠ
  • 게다가 취준생의 신분이라 어떤날은 입사서류를 준비하다가 싱숭생숭해서 마음을 잘 다잡지 못한 날도 사실 많았다.

회고

  • 하지만 이 경험을 토대로 앞으로 다른 프로젝트를 할때 겪을 시행착오를 미리 겪었다고 생각한다. 이젠 프레임워크 디펜던시나, 앱 배포 과정에서 필요한 프로비저닝 파일생성, 프로젝트 빌드 세팅, Test Flight배포, 그리고 멘탈관리…등 여러 방면에서 어떤 것이 문제인지 파악하는 능력이 생긴 것 같고 배운 것을 토대로 앞으로 더 잘할 수 있을것 같다 : )
  • 앞으로 버전업을 계속해가면서 기능을 좀 더 추가할 예정인데, 개선점을 토대로 계속 코드도 개선해나갈 예정이다.

Comments