1.클린아키텍처란
-2012년에 Uncle Bob이란 분이 제시한 소프트웨어 설계 방식
사용하는 이유
-계층(Layer)별로 역할(관심사)를 나누어 분리함으로써 다양한 요구(대규모 업데이트, 새로운 기능, 버그수정, 테스트, 고객의 요청)등에 유연하게 대처하기 위해 사용
- 이러한 계층간의 역할을 알기전에 의존성 규칙을 먼저 알아보겠습니다.
의존성 규칙(Dependency Rule)
-계층마다 경계를 나누어서 관심사를 분리하기 위해 사용하는 규칙
1)모든 소스코드 의존성은 반드시 바깥쪽에서 안쪽으로, 고수준 정책을 향해야 한다
-안쪽으로 갈수록 고수준에 해당하고, 고수준과 저수준은 추상화의 정도에 따라 분류됩니다.
-추상화가 많이 되어있을수록 안쪽에 위치해있고 고수준에 해당합니다.
2)고수준에 있는 계층은 저수준에 있는 계층에 대해 몰라야 한다.
-안쪽에 있는 Domain 계층은 DataLayer나 PresentationLayer에 의존하지 않고 독립적으로
실행되어야 한다는 규칙입니다.
2.안드로이드 클린아키텍처의 계층과 요소
1)Domain 계층(Layer)
-사업의 핵심적인 서비스와 관련된 잘 변하지 않는 비즈니스 로직들이 있음.
ex) 배달의민족 → 배달서비스(핵심서비스) 토스 → 금융 서비스(핵심서비스)
-순수한 영역(어떠한 계층에도 의존성을 갖지않음)으로 다른 외부 계층의 로직이 변경되어도 Domain에 있는 로직은 변경되지 않음
-Data, Presentation 계층이 하는일을 Domain 계층은 알지 못합니다.
1-1)Entity
-가장 핵심적인 고수준의 비즈니스 로직을 캡슐화 한 것이며 따라서 외부계층(Data, Presentation)의 변경사항이 생겨도 바뀌지 않음.
-UseCase에 필요한 데이터
-아래 그림은 비즈니스 로직을 캡슐화 한 예시이다.
1-2)UseCase
-Entity를 사용해서 서비스의 핵심적인 비즈니스 로직을 수행하기 위한 하나의 작은 단위.
ex)로그인하기, 게시물작성, 사진업로드
-다른 계층(Data, Presentation)에 영향을 받지 않는다.
-UseCase안에는 어떠한 Repository(인터페이스)를 사용(주로 DI로 주입)하느냐에 따라 수행하는 비즈니스 로직이
달라진다.
-UseCase에 Repository를 주입시 반드시 interface를 주입받아야 한다
-GetGithubReposUseCase안에 Repository(interface)객체가 DI로 주입받는 것을 확인할 수 있다.
1-3)Repository(interface)
-UseCase에 주입되는 인터페이스
-Data계층에 Repository 인터페이스의 구현체로 구현함으로써 Data계층의 로직이 수정되어도
Domain계층의 로직은 수정되지 않게 하기 위해 사용합니다.
Domain 계층이 Repository 인터페이스를 사용하는 이유
- Domain 계층은 단순하게 Data 계층에게 인터페이스만 제공하고 Data계층은 Domain계층의 인터페이스를 구현함으로써 Domain 계층은 Data나 Presentation 계층에 의존성을 갖지 않게 로직을 구성할 수 있음.
UseCase에 Repository 인터페이스를 주입(DI)받는 이유
-Data나 Presentation 계층의 로직이 수정되어도 핵심적인 고수준의 로직이 있는 Domain 계층의 수정을 피하기 위해서입니다.
ex) 만약 UseCase안에 Repository 인터페이스를 제공하는 것이 아닌 Data 계층의 가상의 클래스를 주입받아 바로 사용해버리면 이는 Domain계층안에 있는 UseCase가 Data계층에 영향을 받아 버립니다. 즉 Data 계층의 수정이 Domain 계층에 영향을 끼쳐버리므로 의존성을 갖게됩니다.
2)Data 계층
-Domain 계층의 Repository 인터페이스를 구현함으로써 (DB, 서버)와 상호작용을 수행하는 영역
-Domain 계층에 의존성을 가지며 Repository 패턴을 사용하기 때문에 Presentation 계층과는
의존성이 적다.
2-1)Repository(Implementaion)
-Domain 계층에 있는 Repository 인터페이스를 구현함으로써 Presentation계층과 상호작용을 할 수 있게 합니다.
-Presentation계층이 Domain계층에 있는 Repository 인터페이스의 추상메서드를 호출하면 실질적으로는 Data 계층에 있는 Repository 인터페이스 구현체의 로직을 수행합니다.
2-2)DataSource
-Data 계층의 Repository 인터페이스 구현체안에서 실행되며 인터페이스이다.
-DataSource의 변경이 Data 계층에 있는 Repository구현체에 영향을 주지 않기 위해서 사용합니다.
RemoteDataSource(외부 API 통신)와 LocalDataSource(내부 room이나 Realm과 통신)을 구분하는 등의 로직이 있다.
2-3)Model
-Data 계층에서 DB 통신에 필요한 데이터
ex) DB 통신(Retrofit, Room등등)에 필요한 데이터
2-4)Mapper
-Data 계층의 Model을 통해 가져온 데이터를 Entity에 맞게 바꿔주는 역할을 합니다.
ex) DB로 부터 받아온 데이터 Model을 Mapper클래스를 통해 Domain 계층에 Entity로 변환시킴으로써 UseCase를 수행하는데 사용
ex2) Domain계층의 Entity를 DB통신을 하기위해서 Mapper를 통해 Data계층의 Model로 변환시킨다.
-위의 그림을 보시면 mapperGithub() 메서드의 반환값으로 Domain계층의 Entity를 가진 리스트를 반환하는 것을 확인할 수 있습니다.
-위의 그림을 보시면 반환값에 사용하는 데이터가 GithubRepoEntity이고 이 Entity는 Mapper를 통해서 Data계층의 Model을 Domain 계층의 Entity로 변환시킨 것입니다.
3)Presentation 계층
-모든 UI와 관련된 컴포넌트 또는 안드로이드 프레임워크와 관련된 코드들이 이 계층에서
다뤄지며 다양한 요구에 의해 수정이 빈번하게 일어나는 계층입니다.
-Domain 레이어에 의존성을 가집니다.
3-1)Activity & Fragment
3-2)ViewModel
-MVVM 패턴을 사용하는 경우 ViewModel에서 비즈니스 로직이 수행되기 떄문에 Domain 계층의 UseCase를 사용해서 비즈니스 로직을 수행합니다.
-UseCase안에서는 Domain 계층의 Repository 인터페이스의 추상메서드를 통해서 Data 계층의 접근해서 필요한 작업을 수행하는 것을 확인할 수 있습니다.
참고자료
안드로이드에서 클린 아키텍쳐 구현하기
https://jungwoon.github.io/android/2021/04/12/Android-CleanArchitecture.html
Clean Architecture
https://velog.io/@hyenees/Clean-Architecture
안드로이드에 클린 아키텍처를 도입한다면 어떻게 될까?
https://www.charlezz.com/?p=45391
[안드로이드] Clean Architecture 를 도입하며
https://vagabond95.me/posts/clean-architecture-1/
Android의 Clean Architecture에 대해 알아보자 !
https://velog.io/@sery270/Android의-Clean-Architecture에-대해-알아보자-n9ihbaj4
[Android] Clean Architecture in Android[꾸준하게]
https://leveloper.tistory.com/205
Clean Architecture는 모바일 개발을 어떻게 도와주는가? - (1) 경계선: 계층 나누기
https://medium.com/@justfaceit/clean-architecture는-모바일-개발을-어떻게-도와주는가-1-경계선-계층을-정의해준다-b77496744616
안드로이드에 Clean Architecture 적용하기
https://academy.realm.io/kr/posts/clean-architecture-in-android/
[DroidKnights 2019 - Track 1]황성현 - Clean Architecture
'안드로이드 공부 & 앱' 카테고리의 다른 글
[안드로이드/Kotlin] 의존성 주입 및 Hilt 프레임워크 사용 과정 (0) | 2022.05.17 |
---|---|
[안드로이드/Kotlin] DiffUtill + RecyclerView 개념 정리 및 Tip (0) | 2022.05.14 |
[안드로이드] JetPack Navigation 개념 정리 및 예제 (0) | 2022.04.16 |
[안드로이드] 버튼 클릭 리스너로 확인하는 옵저버 패턴-1편 (0) | 2022.04.13 |
운동친구 어플 레이아웃 설계화면 (0) | 2022.02.12 |
댓글