reactive android application architecture

Post on 21-Jan-2017

1.062 Views

Category:

Internet

12 Downloads

Preview:

Click to see full reader

TRANSCRIPT

Reactive Android Application Architecture

GDE Android 정승욱

발표자 소개

● 정승욱

● Google Developer Expert Android (2016)● TossLab - JANDI, Android 개발자● 블로그 : https://medium.com/@jsuch2362

FB : https://www.facebook.com/steve.SU.JGithub : https://github.com/ZeroBrainSlack : @nobrain_steve (http://gdgkr.slack.com)

● 기여 : Robolectric-Gradle, Socket.io-java-client 등● Android 기술 및 애자일 스크럼 활동 등 블로그 포스팅

Reactive 가 트렌드가 되었나?

데이터 변화에 대한 지금의 모습

수정 요청

수정 결과 전달

일반적인 케이스

EventBus 를 통해 사용자의 정보가 바뀌었다는 신호를 보냄

OnActivityResult 또는 LifeCycle 콜백을 이용해서 갱신을 함

데이터를 가져올 때는 저장소를 통해서 재접근

일반적인 케이스의 문제점

EventBus 를 통해 사용자의 정보가 바뀌었다는 신호를 보냄

Domain 과 상관없는 다수의 이벤트들과의 관리 문제

OnActivityResult 또는 LifeCycle 콜백을 이용해서 갱신을 함

복잡한 Stack 및 콜백 관리, 불필요한 Refresh 동작

데이터를 가져올 때는 저장소를 통해서 재접근

Query 나 데이터에 대한 재접근 요구

데이터의 변화를 스스로 알고 대응한다면?

Reactive Programming

Reactive Programming?

Reactive Programming

데이터 흐름과 변화에 대한 전달 을 기반으로 하는 프로그래밍 패러다임

“In computing, reactive programming is a programming paradigm oriented around data flows and the propagation of change”

wikipidiahttps://en.wikipedia.org/wiki/Reactive_programming

Reactive Programming

데이터 흐름과 변화에 대한 전달 을 기반으로 하는 프로그래밍 패러다임

“In computing, reactive programming is a programming paradigm oriented around data flows and the propagation of change”

wikipidiahttps://en.wikipedia.org/wiki/Reactive_programming

데이터의 흐름데이터의 변화를 전달

데이터의 흐름데이터의 변화를 전달

데이터의 흐름

데이터의 흐름

A

B

C

D

Listindex

데이터의 흐름

A

B

C

D

Listindex

데이터 변경

데이터 가공

A

데이터의 흐름

B

C

D

Listindex

데이터 변경

최종 처리

데이터 처리

A

데이터 가공

A

데이터의 흐름

B

C

D

Listindex

데이터 변경

최종 처리

데이터 처리

데이터 가공

B

데이터의 흐름

C

D

Listindex

데이터 변경

최종 처리

데이터 처리

데이터 가공

C

데이터의 흐름

D

Listindex

데이터 변경

최종 처리

데이터 처리

데이터 가공

D

데이터의 흐름List

index

데이터 변경 최종 처리

데이터의 흐름List

index

데이터 변경 최종 처리

D

B

C

A

모든 처리가 끝나면흐름 종료

데이터의 흐름↓

Stream 처리 or API

RxJava로 보는 Stream 처리

데이터의 흐름List

D

B

C

AObservable.just("A", "B", "C", "D");

데이터의 흐름

D

데이터 변경

데이터 가공

Observable.just("A", "B", "C", "D")

.map(charater -> new Data());

데이터의 흐름

최종 처리

데이터 처리

Observable.just("A", "B", "C", "D")

.map(charater -> new Data())

.subscribe(data -> {

doSome();

});

데이터의 변화 전달

데이터의 변화 전달

B

데이터 모니터

데이터의 변화 전달

B

데이터 변경

데이터 가공

B

데이터 모니터

데이터 감지

데이터의 변화 전달

B

데이터 변경

최종 처리

데이터 처리

데이터 가공

B

데이터 모니터

데이터 감지

데이터의 변화 전달

B

데이터 변경

최종 처리

데이터 처리

데이터 가공

B

데이터 모니터

데이터 감지

데이터의 변화 전달

B

데이터 모니터

Data.set(B’)

B’

데이터의 변화 전달

B`

데이터 변경

나`

데이터 가공

B

데이터 모니터

B’

데이터 변화

Data.set(B’)

데이터의 변화 전달

B`

데이터 변경

나`

나`

최종 처리

데이터 처리

데이터 가공

B

데이터 모니터

B’

데이터 변화

Data.set(B’)

데이터의 변화 전달

B`

데이터 변경

나`

나`

최종 처리

데이터 처리

데이터 가공

B

데이터 모니터

B’

데이터 변화

Data.set(B’)

데이터의 변화가 없으면 흐름이 시작되지 않는다.

데이터의 변화 감지↓

Observer 또는 Repository

Reactive 의 형태↓

Stream 처리를 통한 데이터 전달Observer 감시를 통한 변화 전달

Reactive 를 위해 고려해야 할 것

Reactive 를 위해 고려해야 할 것

● Reative 정보는 무엇이 될 것인가?

● 어떻게 Reactive 정보를 전달 할 것인가?

● Reactive 관리는 어떻게 할 것인가?

Reactive 를 위해 고려해야 할 것

● Reative 정보는 무엇이 될 것인가?

● 어떻게 Reactive 정보를 전달 할 것인가?

● Reactive 관리는 어떻게 할 것인가?

RxJava 를 이용 예시로 본 고려사항

RxBinding 예시

RxBinding

Android 의 View 상태 변화를 RxJava 를 이용해서 전달해주는 라이브러리

ex)

View 의 Click, TouchViewPager 의 PageChange 등

RxBinding - TextView.onTextChanged

EditText name;

RxTextView.textChanges(name)

.subscribe(text -> {

// do something

});

RxBinding - TextView.onTextChanged

EditText name;

RxTextView.textChanges(name)

.subscribe(text -> {

// do something

}); Reactive 감지 : Text 가 변경될 때

RxBinding - TextView.onTextChanged

EditText name;

RxTextView.textChanges(name)

.subscribe(text -> {

// do something

});Reactive 대상 : EditText 내의 Text

RxBinding - TextView.onTextChanged

EditText name;

RxTextView.textChanges(name)

.subscribe(text -> {

// do something

});RxBinding 내부의

RxViewTextOnSubscribe 클래스가 EditText 를 관리함.

그림으로 보는 RxBinding

최종 처리

데이터 처리

text

데이터 모니터

text’

데이터 변화

onTextChangedtext’

BehaviorSubject 예시

RxJava 의 Subject

외부에서 데이터를 비동기적으로 전달할 수 있도록 제공된 Interface

AsyncSubject - 연결이 완료된 시점의 마지막 정보 전달PublishSubject - 연결이 시작된 시점부터 정보 전달BahaviorSubject - 연결이 시작 직전에 마지막 정보부터 전달ReplaySubject - 연결이 시작되기 전 일정 구간의 정보를 모두 전달

BehaviorSubject

Subject subject = BehaviorSubject.create("default");

subject.distinctUntilchanged()

.subscribe(text -> {

// do something

});

subject.onNext("modified");

BehaviorSubject

Subject subject = BehaviorSubject.create("default");

subject.distinctUntilchanged()

.subscribe(text -> {

// do something

});

subject.onNext("modified");

Reactive 관리 : BehaviorSubject 내에서 관리

BehaviorSubject

Subject subject = BehaviorSubject.create("default");

subject.distinctUntilchanged()

.subscribe(text -> {

// do something

});

subject.onNext("modified");

Reactive 감지 : String 정보가 변경될 때

Reactive 변화 요인

BehaviorSubject

Subject subject = BehaviorSubject.create("default");

subject.distinctUntilchanged()

.subscribe(text -> {

// do something

});

subject.onNext("modified");

Reactive 대상 : String 형 객체

Advanced Reactive From Data

Reactive 대상 정의

↓객체 정의

Reactive 전달↓

RxJava 를 이용한 전달

전달에 용이한 객체로 전환

일반적인 데이터 관리

● 관리하지 않는다.

Activity 네트워크 요청 View.setXXX

일반적인 데이터 관리

● 관리하지 않는다.

● Activity 등에 일회성 저장

Activity 네트워크 요청 View.setXXXActivity 저장

일반적인 데이터 관리

● 관리하지 않는다.

● Activity 등에 일회성 저장

● Singleton, Database 에 저장

Activity 네트워크 요청 View.setXXXDB 저장

일반적인 데이터 관리

● 관리하지 않는다.

● Activity 등에 일회성 저장

● Singleton, Database 에 저장

Activity 네트워크 요청 View.setXXXDB 저장

Singleton, Database 의 변화

Database 의 변화 전달

Sqlite : ContentObserver 를 제공

Realm : RealmChangeListener 제공

데이터의 Create/Update/Delete 에 따라로직이나 View 의 정보가 변경된다

Database 의 변화

Sqlite : ContentObserver 를 제공

Realm : RealmChangeListener 제공

하지만 Data 의 Create/Update/Delete 상태를 제공하지 않는다.

데이터의 변화는 이미 외부에서 결정됨

public T insert(T t);

public int update(T t);

public int delete(T t);

예상 가능 Transaction ↓

이벤트에 정의하고 전달 가능

public class Result<T> {

T data; // 변화된 데이터

// 데이터 반영 상태

boolean added() {};

boolean updated() {};

boolean deleted() {};

}

public class Result<T> {

T data; // 변화된 데이터

// 데이터 반영 상태

boolean added() {};

boolean updated() {};

boolean deleted() {};

}

public class Result<T> {

T data; // 변화된 데이터

// 데이터 반영 상태

boolean added() {};

boolean updated() {};

boolean deleted() {};

}

데이터의 전달

1개의 도메인에 대해 N 곳에서 처리↓

Reactive 관리

N 곳에서 동시에 등록/해제 할 수 있는

인터페이스 필요

class DataObserver { // Singleton Class

Map<Object, List<Listener>> register;

Subject notifier;

// 데이터 감시 등록

void <T> register(Object invoker, Class klass, Listener listener);

// 데이터 감시 해제

void unregister(Object invoker);

// 데이터 변화 주입

void update(Result result);

}

등록/해제 방법

등록/해제 방법public class MainActivity {

public void onCreate() {

DataObserver.register(this,

Data.class,

result -> doSome());

}

public void onDestroy() {

DataObserver.unregister(this);

}

}

등록/해제 방법public class MainActivity {

public void onCreate() {

DataObserver.register(this,

Data.class,

result -> doSome());

}

public void onDestroy() {

DataObserver.unregister(this);

}

}

등록

해제

등록/해제 방법public class MainActivity {

public void onCreate() {

DataObserver.register(this,

Data.class,

result -> doSome());

}

public void onDestroy() {

DataObserver.unregister(this);

}

}

데이터 변화를 감지할 객체 정의

등록/해제 방법public class MainActivity {

public void onCreate() {

DataObserver.register(this,

Data.class,

result -> doSome());

}

public void onDestroy() {

DataObserver.unregister(this);

}

}

콜백 정의

실제 화면상의 모습

User.class

User.class사용자의 정보가 바뀐다면?

User 객체의 변화에만 반응

Database

DataObserver

NavigationDrawer ProfileView

ProfileLoader ProfileLoader

ProfileBinder ProfileBinder

Database

DataObserver

NavigationDrawer ProfileView

ProfileLoader ProfileLoader

User 감시 User 감시

ProfileBinder ProfileBinder

NavigationDrawer ProfileView

Database

DataObserver

NavigationDrawer ProfileView

ProfileLoader

ProfileBinder ProfileBinder

ProfileLoaderUser 로드 후 바인딩

NavigationDrawer ProfileView

사용자가 User 정보를 변경

Database

DataObserver

NavigationDrawer ProfileView

ProfileLoader ProfileLoader

ProfileBinder ProfileBinderUser 정보 갱신

NavigationDrawer ProfileView

User 정보 갱신

Database

DataObserver

NavigationDrawer ProfileView

ProfileLoader ProfileLoader

ProfileBinder ProfileBinder

NavigationDrawer ProfileView

Database 가 DataObserver 에게 갱신을 알림

User 정보 갱신

Database

DataObserver

NavigationDrawer ProfileView

ProfileLoader ProfileLoader

ProfileBinder ProfileBinder

NavigationDrawer ProfileView

User 정보 갱신

Database

DataObserver

NavigationDrawer ProfileView

ProfileLoader ProfileLoader

ProfileBinder ProfileBinder

NavigationDrawer ProfileView

User 정보 갱신

Database

DataObserver

NavigationDrawer ProfileView

ProfileLoader ProfileLoader

ProfileBinder ProfileBinder

NavigationDrawer ProfileView

기존 과의 차이

Data 에만 반응함

LifeCycle 등의 특정 콜백 으로부터 해방

Transactional Operator 에 대한 정확한 추정이 가능

결론

결론

객체 에 대한 공통된 정의

객체 을 이용해서 관리 할 수 있는 Observer 정의

객체 처리에 맞도록 리스너 정의

주의 사항

주의 사항객체 의 지나친 포괄/세분화는 중복적인 처리를 가져올 수 있음.

ex) ChatList (전체 채팅 리스트)1개의 뱃지만 바뀌는 updated 동작에 대해 전체의 갱신

객체 반응시 의존적 관계에 대한 Scope/처리 정의 필요

ex) User 는 Team / AccessInfo 에 의존적Team 정보가 없는 경우, 다른 Team 정보로 변경되는 경우

Q&A

워크샵 시작~!

top related