Droid Knights 2018

링크 : https://droidknights.github.io/2018/

일시 : 2018.04.22 09:00 ~ 18:00

장소 : 코엑스 컨퍼런스홀

간단하게 들었던 섹션 정리 및 자료 링크 취합입니다.

01. Track 1. No More Fragment, No More Activity

  • 발표자 : 정승욱 (GrabTaxi 안드로이드 개발자)
  • 발표자료 :

동남아 서비스로 국내보다 단말 저사양 및 파편화 현상이 심함.

해상도 대응이나 안드로이드 버전별 대응 등의 어려움이 있음.

각 국가별 개발팀이 분산되어 있으며, 30여명의 개발자로 팀 구성됨.

Activity나 Fragment 등의 사용없이 단일 Activity로 앱 구성.

서비스 모듈 별 관리를 위해 Router, Node 형태 도입.

Back키 처리나 스킴 처리 등의 대응 필요.

02. Track 1. Next Step Architecture

  • 발표자 : 남상균, 정현지 (NBT/캐시슬라이드 Chief Architect & 안드로이드 개발자)
  • 발표자료 :

오래된 앱을 유지하면서 시스템을 개선하기 위한 노력.

도메인 베이스의 의사결정이 개발 환경 등에도 영향을 미침.

안드로이드 API 최소버전도 최근에 들어서 상향 조정함.

Kotlin 전환 등의 노력들을 함.

03. Track 2. Best Practice on Android Instant Apps

  • 발표자 : 김종식 (원티드 안드로이드 개발자)
  • 발표자료 :

설치 없이 네이티브 앱 사용경험을 제공하는 인스턴트 앱 개발과정

Android Instant App FAQ (https://developer.android.com/topic/instant-apps/faqs.html?hl=ko)

  • 호환되는 기기 : Android 4.1(API 16) 이상 & Google Play서비스가 설치된 기기

  • 두 가지 다른 앱을 빌드해야 하나?

    하나의 프로젝트만 유지하면 가능. 두 가지 빌드 아티팩트인 설치 가능 APK와 인스턴트 버전을 생성하도록 프로젝트 구성하면 됨.

  • 어떤 Android API와 기능을 사용할 수 있나?

    Android Instant Apps 기능이 기존 Android 앱을 보완하기는 하나, 대체하지는 않음.

    동일한 Android API, 동일한 프로젝트, 동일한 소스코드를 사용하나 설치되지 않은 앱에 대한 사용자의 기대 사항에 맞지 않을 수 있는 일부 기능은 제한함. 예를 들어 백그라운드 서비스 사용이나 백그라운드 알림, 고유 기기 식별자에 액세스하지 못할 수 있음.

  • 사용자가 앱을 영구적으로 설치하도록 선택할 수 있나?

    Google Play 스토어에서 앱 다운로드하도록 허용 가능함. 다운로드 후에는 사용자가 그 환경을 떠난 후에도 앱이 휴대폰에 남아있음.

  • Permission은 어떤식으로 작동?

    Android 6.0 (API 23)에 새로 추가된 런타임 권한 모델을 사용함.

  • Instant Apps 게시는?

    기존의 Android 앱과 유사하게 Google Play Developer Console을 통해 게시 가능

참조 링크 : https://tech.wanted.co.kr/android/2018/01/30/android-instant-app.html

gradle 이나 AndroidManifest 설정은 위 링크를 참조하면 됨.

인스턴트 앱을 위해 InstantApps 라는 클래스가 추가되었으며, isInstantApp(Context context) 메서드로 현재 프로세스를 확인할 수 있음.

배포시 Holdback 설정을 통해 0과 1 사이의 값을 설정하여 인스턴트 앱 출시 비중을 정함.(0일 경우 전체를 인스턴트 앱으로 출시)

프로덕션 출시가 아니라면 10MB 까지 업로드가 가능했으나, 프로덕션 출시시에는 4MB를 넘기면 안됨.

기본 support 라이브러리들도 용량을 먹기 때문에 실제 사용 가능한 용량은 적을 수 있음.

04. Track 2. Kotlin 코루틴은 어떻게 동작하는가?

일반 subroutine

  • 단일 지점에서 시작 -> 특정 지점에서 종료

Coroutine

  • 단일 지점에서 시작 -> 임의 지점에서 멈춤 -> 해당 지점에서 재개 -> 특정 지점에서 종료

Sequencial code를 통해 non-blocking 코드를 작성하기 위한 수단으로 Coroutine 제공

suspend는 중단/재개 지점을 위한 continuation을 매핑하기 위한 키워드

호출한 대상/어디까지 실행했는지/어떤 값들을 가지고 있는지 등에 대한 상태를 Continuation Passing Style로 처리됨.

각 코드 라인은 Labeling되어 switch문을 통해 처리되며, Statemachine, Continuation, 상태 저장/복원 등으로 동작함.

UI 쓰레드에서 실행됨.

05. Track 2. Google Mobile Vision과 OpenCV로 card.io를 확장한 범용 카드번호인식 개발

LINE에서 사용 중인 신용카드 인식 오픈소스인 card.io가 양각되어 있는 신용카드만 인식하는 문제 해결 과정.

LINE 캐릭터 카드 같은 경우들을 인식을 못함.

Google Mobile Vision과 OpenCV를 활용하여 일반 프린팅된 카드 번호 및 멤버쉽 카드 그리고 바코드를 인식하는 라이브러리를 개발함.

card.io 관련 여러가지 이슈들

  • 작은 해상도(바코드 인식에 맞는 사이즈가 안나옴)
  • 양각 문자만 인식(Google Mobile Vision을 활용해보았으나, 너무 많은 문자열이 인지됨.)
  • 카드 스캔시 영역 설정시 퍼포먼스 이슈
  • 문자열 인지 후 카드번호 얻는 방식(여러 문자열이 나열되는 경우들. 예를들어 자동차 번호판 인식같이)
  • Java와 NDK 간 속도차이는 최소 5배 이상은 차이났음.

##06. Track 2. Travis-ci를 이용한 CI/CD와 도커를 이용한 Jenkins for Android 구성하기

CI(Continuous Integration) : Build, Test를 실시하는 프로세스를 상시로 실시해줌. 지속적 통합.

CD(Continuous Delivery or Continuous Deploy) : 소프트웨어를 빠르고 주기적으로 빌드하고 테스트하고 출시하는 것이 목표. 지속적 배포.

이를 수동으로 하는 것은 자동차 스틱을 운전하는 것이나 돌로 탑쌓기와 유사함.

CI툴들을 사용해 피드백을 받고 스크립트로 자동화까지 처리한다면 자율주행같이 사용할 수 있음.

Travis CI를 이용한 CI/CD

Travis-CI : Github에서 진행되는 오픈소스 프로젝트. Private repository는 유료.

  • 장점
    • 손쉬운 프로젝트 설정 및 서비스 연동(Github와 seamless한 통합)
    • 오픈소스 프로젝트시 무료
    • 전용 CI/CD 서버 필요하지 않음.
    • 모든 Job이 독립적 동작
    • 빌드 메트릭스 제공
  • 단점
    • 제한된 옵션 제공 (Site GUI 제한적)
    • 느린 속도
    • Private Repository는 유료

Jenkins for Android using Docker

Jenkins : 다양한 시스템에서 사용 가능. 다양한 플러그인. 다양한 작업 모드 및 조건의 빌드 가능

  • 장점
    • 무료
    • 사용자 정의 옵션
    • 방대한 양의 플러그인
    • 다양한 적용사례 및 풍부한 레퍼런스
    • Remote access API 제공
  • 단점
    • 별도 서버 필요
    • 시스템 구성 및 사용자 정의 시간이 오래 걸릴 수 있음

07. Track 1. Android Test

  • 발표자 : 정경호 (에그번 안드로이드/서버 개발)
  • 발표자료 :

개발자들은 테스트를 피할 수 없음.

유닛 테스트도 작성이 어려운 경우가 많음.

서비스 테스트부터라도 작성을 해야 함.

UI 테스트도 할 수 있음.

패턴도 적용해야 함.

아무튼 해야 함!!!!

08. Track 1. 내가 안드로이드 개발자가 되었을 때 아무도 알려주지 않은 것들

안드로이드 개발자가 걷는 길

초보 모바일 개발자일 때 어려움들

  • Device/version fragmentation
  • 비동기
  • Life Cycle
  • 구글의 신기능

안드로이드 개발자가 되었을때 아무도 알려주지 않았던 것들

  • Clean Architecture
    • 하라는 건 많지만 제대로 쓰는 사람은 별로 안보임.
  • MVVM
    • 쓰면 좋다는데 복잡하고 예제들이 제 각각임.
  • MVP
    • MVVM 보다는 쉬운 것 같지만 진행하다보니 또 다른 컨트롤러를 만드는 기분임.
  • RxJava
    • 어렵고 헷갈리고, 자매품 LiveData는 좀 쉽지만 애매함.
  • Dependency Injection
    • 처음엔 쉬운 것 같은데 끝없는 decision making의 연속. 특정 인스턴스에 대한 injection을 어떻게 해야 효과적인지 헷갈림.
  • TDD (Test-Driven Development)
    • 유닛 테스트 튜토리얼들 중 실제 상용 프로젝트 수준의 유닛 테스트를 만드는 법을 알려주는 건 없음.

위의 것들을 통해 나타나는 전형적 증상

  • 비관주의 : 이 또한 지나가리
  • 팔랑귀 증후군 : 당장 해보자
  • 툴 만능주의 : 툴과 라이브러리 사용능력이 실력이다?
  • Low-hanging fruit : 쉬운 문제에만 집착

중요한 스킬

  • Solution Provider

    • 알고리즘에 대한 깊은 이해
    • 개발 언어의 semantics의 깊은 원리와 언어 설계 철학에 대한 이해
    • Dalvik의 동작 원리 이해
    • Activity/Fragment 중요 동작을 플랫폼 코드 레벨에서의 이해
    • 안드로이드가 화면을 렌더링 하는 매커니즘의 이해
    • 등등등
  • Architect

    • 내 프로젝트를 간단한 README.md 파일 외에 다른 개발자에게 인수인계할 수 있음.

    • 코드를 1년 뒤에 봤을때 바로 이해 가능

    • 큰 규모의 구조 수정도 1~2일 내에 해낼 수 있을 정도로 유연한 구조

    • Jr 엔지니어에게 후속 코딩을 안심하고 몽땅 떠넘겨도 될 수준으로 기본 구조가 견고하게 작성.

      (잘못된 방식으로 구현하기가 매우 어렵도록 구조를 만듬)

중급 개발자를 위한 안내

  • 시작이 반
  • 공유의 힘 (주관이 들어가면 스스로에게도 독자에게도 도움이 됨)
  • 일본의 경우
    • 블로그를 통한 공유가 일상화
    • 주로 지역 단위의 세미나인 공부회
    • Moku-moku meeting(묵묵한 미팅?) : 그냥 각자 코딩 모임. 국내 모각코 같은...
    • Network Party : 자기가 구현한 아키텍처, 테스트 등 구체적인 부분에 대한 지식 교환.

패턴 사용에 따른 경험들

MVP & MVVM

  • MVC is not evil

    • 모바일 환경의 문제 : 비동기 처리, 라이프 사이클 처리
    • 안드로이드의 View-Controller 분리가 애매
    • 그로 인한 총체적 난국 : 최악의 가독성, 각 클래스들의 너무 많은 역할들.
  • MVP

    • 안드로이드 초기부터 구전으로 전해져 왔던 아키텍처
    • 장점
      • Fat activity/fragment 방지
      • 역할 분리로 인해 소스 가독성 및 품질 상승
      • 플랫폼 의존적인 UI 처리는 View쪽으로 분리하여 Presenter는 쉽게 테스트 작성 가능
      • Clean Architecture와 1:1 mapping 가능. CA 그대로 채용하면 설계 관련 노력도 최소화.
  • What is not MVVM?

    • MVVM의 특징이 Life Cycle은 아님.

    • Data Binding : 필수가 아님. 다만 사용하면 생산성에 확실한 도움이 됨.

    • RxMVVM : 역시 필수는 아니지만 없이는 매우 불편함.

    • ViewModel 용어에서 오는 혼란

      • Model과 같이 작은 단위로 쪼개져있지 않음. 통신에다 별게 다 들어간 형태임.
      • View를 위한 Model (Entity) 라는 개념 & 단방향 Presenter라는 두개의 개념임.
      • Presenter와 매우 유사하나 ViewModel은 View를 제어하지 않음.
      • View는 ViewModel을 호출하되, 결과는 Callback/Observable 형태로 받음.

MVVM vs MVP

둘 다 훌륭한 구조이며, 압도적 우위는 없음. 프로젝트 성격에 따라 다르게 받아들여질 수 있음.

MVP의 비교우위

  • 시작이 쉬우며, Legacy Code의 분량이 많거나 구조 개선에 주어진 시간이 짧은 경우 MVP가 유리
  • RxJava를 안 써도 훌륭한 구조를 만들 수 있음.

MVVM

  • 초기 진입장벽은 있음.
  • View 상태 관리가 복잡한 경우 ViewModel에서의 처리가 자연스러움
  • AAC (Android Architecture Component 후광 효과)
  • Cross Platform 구현에 좀 더 유리 (Kotlin을 Swift로 옮기는 것만으로도 View 이외의 소스의 70% 이상을 재사용 가능)

MVVM - MVP 공통의 장점

  • 개발 속도가 몇 배는 빨라짐 (단 개인차가 있으며, 초기 2~3주간 개발 속도는 몇 배는 느려질 수 있음)
  • 코드 변경에 대한 두려움이 거의 없어짐
  • 기획의 급격한 사양 변경에도 대응 가능
  • 1년 뒤에 코드를 다시 봐도 즉시 어디를 고쳐야할지 알 수 있음.
  • 다른 엔지니어에게 코드를 보여줘도 쪽팔리지 않음!!!

MVP/MVVM at Scale

프로젝트 사이즈가 점점 커지면서 위의 기대와는 달리 지저분해짐.

  • Fat Presenter
  • 테스트 케이스 만들기가 어려워짐
  • 코드가 지저분함. Activity Manager 같은 게 하나 늘어나기만 한 느낌
  • 주된 원인 중 하나는 Presenter를 View와 명확히 분리하지 않은 것

해결책

  • View와 Presenter를 잘못 구현하기 어렵도록 하는 장치 필요.
  • View는 이벤트를 발생시키고, UI를 그려주는 역할만 담당, 비즈니스 로직이나 모델이 끼어들 여지를 차단.
  • Presenter가 View의 세부 사항을 알 수 없도록 P는 View를 추상화 시킨 형태로만 참조하도록 만듦

MVP: Contract Pattern

  • View Interface를 통한 분리
  • 필요한 경우 Presenter까지 Interface화 시킴

MVVM Best Practice: Passive View

  • View는 (플랫폼 의존적인) 그리기 이외에는 아무것도 알 수 없도록 함
  • Lighter View, Fatter ViewModel이 되나 더 나은 구조로 가기 위한 중요한 가교

MVVM is not an architecture.

비즈니스 로직의 비대화

  • Presenter나 ViewModel의 도메인 로직이 감당할 수 없는 크기가 되는 상황

  • Single Responsibility Principle 적용

    • 모범 답안 : Clean Architecture!
    • Presenter에서 도메인 로직을 분리 가능
    • Data 계층의 세분화를 통해 더욱 추상화된 형태의 구조 가능

Clean Architecture

기승전CA?

장점

  • Presenter/Domain/Data 계층의 분리로 인해 전체 로직의 흐름이 일목요연해짐. 가독성 급상승.
  • 특정 클래스가 비대해지는 것을 방지
  • 각 Layer 간 구분이 명확하므로, 영향 범위도 명확
  • 단 클래스 량이 급격히 증가 -> 한번에 구현하려 하면 개발속도 저하와 버그 양산 야기
    • CA가 익숙하지 않거나 경험이 없는 경우 모든 걸 따라할 필요는 없음
    • 프리젠테이션 로직의 합리화부터 시작
      • View - ViewModel/Presenter - Repository - Model (Entity)
    • 도메인/데이터 로직은 필요에 의해 점진적으로 하는 것이 합리적
  • 자동 생성 플러그인 : https://github.com/kiuchikeisuke/Android-Studio-CleanArchitecture-template-forKotlin
    • RxJava, Dagger, Retrofit, AAC, Presenter/ViewModel 코드까지 몽땅 만들어 줌
    • Swagger 지원으로 REST API call 인터페이스도 자동으로 만들어 줌

몇 가지 난제들...

구조의 철학적 문제 : Presenter의 비즈니스 로직과 Use Case의 비즈니스 로직의 차이점?

  • 도메인 로직이 Use Case에 들어감
  • 사업부 사람들도 알고 있어야 하는 로직이라면 도메인 로직

RecyclerView in MVP

Presenter로 RecyclerView - Adapter 대하는 것은 까다로운 문제임

  • Activity/Fragment가 (Presenter의 명령을 받아) Adapter를 제어 - 단순한 패턴의 리스트에는 효과적
  • Adapter와 매핑되는 Presenter를 구현
  • 개별 item과 각각 1:1 매핑되는 작은 Presenter를 구현

RecyclerView in MVVM

Presenter에 비해선 단순한 문제. Data binding으로 그대로 ViewModel 연결 가능

  • 복잡한 경우가 아니라면 Adapter에 ViewModel 연결

  • 복잡하다면 각 Item과 매핑되는 작은 ViewModel 구현

    • 이 경우 ViewModel은 View를 위해 가공된 Model이기 때문에 어떤 의미에서 진정한 ViewModel
    • AAC를 이용해 small ViewModel을 생성시 provider에 파라미터를 별도 지정해야 함. 차라리 상위 ViewModel이 생성하는 게 더 좋을 수 있음.

경험

서비스 중인 앱을 단기간 내에 리뉴얼 개발하면서 얻은 결과

  • 비즈니스 관점에선 앱 구조 개선은 큰 가치가 없음. 새로운 기능들을 얼마나 빠른 속도로 넣느냐..
급한 일급하지 않은 일
중요한 일신 기능 구현
버그 수정 + 앱 안정화
Java -> Kotlin 변환
ViewModel or Presenter 전환
오래된 라이브러리 갈아타기
중요하지 않은 일각종 회의 참석이상한 변수명, 메소드명 변경
들여쓰기 변경
기타 스타일 수정

전리품

기본 : 출입태그, 티셔츠, 밀스 그레인, 그래놀라바, 에코백, 뱃지, 물, 스티커

네이버 : 노트 or 펜

쿠팡 : 수첩 커버 및 수첩 세트

하이퍼커넥트 : 티셔츠, 스티커

리멤버 : 샤오미 보조 배터리

참고자료

https://yands11.github.io/droid-knights/

https://blog.naver.com/PostView.nhn?blogId=cenodim&logNo=221258932085&redirect=Dlog&widgetTypeCall=true&directAccess=false

+ Recent posts