Skip to content

Observables 과 updatables

Youngchan edited this page Apr 22, 2016 · 12 revisions

이전 페이지에서 언급했듯이 observable은 이벤트 소스를 나타내고 updatable은 이벤트들을 관찰합니다. updatable은 Observable.addUpdatable(Updatable)을 사용하여 등록하고 Observable.removeUpdatable(Updatable)을 사용하여 등록해제 합니다. 이벤트는 Updatable.update()를 호출하는 형태로 updatable에게 전달 됩니다. Activity에서는 이와 같이 Observable에서 이벤트를 관찰 할 수 있습니다:

    public class MyUpdatableActivity extends Activity implements Updatable {
      private Observable observable;
      
      @Override
      protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        observable = new MyObservable();
      }
      
      @Override
      public void update() {
        // Act on the event
      }
      
      @Override
      protected void onResume() {
        super.onResume();
        observable.addUpdatable(this);
        update();
      }
      
      @Override
      protected void onPause() {
        super.onPause();
        observable.removeUpdatable(this);
      }
    }

Updatable 등록과 등록해지는 반드시 쌍으로 쓰여야 합니다. 한번 이상 observable에 동일한 updatable을 추가하거나 등록 되기 전에 observable에서 updatable을 제거 하거나 이미 등록해지 된 상태에서 제거 할 경우 위반입니다.

생명주기 활성화 그리고 이벤트 체인

observable은 관찰됨(observed)으로써 _활성화(active)_됩니다.(적어도 하나의 등록된 updatable을 가지고 있음), 그리고 관찰하지 않음으로써 _비활성화(inactive)_됩니다.(등록된 updatables이 없음). 다른 각도에서 말하면, 비활성화(inactive)상태의 observable을 등록하는 것을 _활성화(activate)_라고 합니다. 그리고 observable을 등록해지하는 것을 _비활성화(deactivate)_라고 합니다.

(Phrased from another angle, an updatable is said to activate an observable by registering onto that observable while it was inactive, and deactivate an observable by unregistering from it while being its only observer.)

observable은 (이벤트 전달 방식의 관점에서)“상위"의 observable을 관찰할 수 있습니다. 그리고 그것의 이벤트들을 자신의 이벤트로 변형합니다.일반적인 예제에서 저장소의 데이타는 다른 저장소들에서 제공된 데이타에 의존적이다. 올바른 연결을 위해 중간의 observable은 보통 상위의 observable들과 강한 참조를 유지하고 있습니다. 그러나 일반적으로 중간 observable의 활성화를 하기 위한 등록은 상위 observable 내부의 updatable에서 이루어지고 비활성화를 위한 등록해지 또한 그렇습니다. 즉 강한 참조는 아랫방향으로 updatable들을 등록하기 위해서만 존재하는 것을 의미합니다. 또한 이것은 이벤트 체인에서 최하단의 updatable들이(중간 observable들이 관리되지 않을 경우) 궁극적으로 모든 observable의 활성화와 비활성화를 제어하는 것을 의미합니다.

UI 생명주기

이벤트 체인 기능은 UI 생명주기에 대한 인식과 Reactive 아키텍처를 구축하기위해 가장 유용합니다. Activity, Fragment 또는 View 내부에 UI요소가 있다고 하면 그것의 활성화 된 라이프사이클은 안드로이드 생명주기 이벤트 쌍에 의해 정의 될 수 있다. 예를들면 onStart에서 onStop까지, onResume에서 onPause까지, onAttachedToWindow에서 onDetachedFromWindow까지 기타등등. 이것은 특정한 케이스에서 합리적입니다. UI요소가 있거나 저장소에서 제공받은 데이타를 사용하여 UI를 업데이트를 하는 updatable이 있다고 하면 저장소는 데이타를 계산하기 위해 차례대로 다른 이벤트 소스들과 데이타 소스들(반드시 저장소가 필요한 것은 아님)을 사용합니다.

UI요소의 생명주기의 시작해서 상기의 updatable이 등록되면 저장소가 활성화됩니다. 이것은 이벤트 체인으로 연결되고 모든 관련된 데이타 처리흐름을 활성화하고 데이타와 UI를 최신으로 유지합니다.

UI 요소의 생명주기의 끝에서 다른 updatable들도 어떤 관찰 활동을 유지하지 않는다고 가정하면 updatable은 같은 저장소에서 등록해지 되고 만약 UI요소가 다시 활성화가 되지 않는다고 한다면 이벤트 체인에서 계단식으로 해제될 것입니다.(예를 들면 엑티비티는 Destroyed됩니다.), 시스템이 비활성인 경우에는 하단 참조가 없으므로 UI요소는 가비지 컬렉팅에 자유롭습니다. 엑티비티의 누수를 쉽게 방지 할 수 있습니다.

스레딩

Agera 명시적 스레딩을 지지합니다. 그리고 스레딩 계약을 정의하기 위해 Looper을 사용합니다. (app의 메인 Looper나 인텐트서비스의 작업 스레드를 위한 루퍼같이 다양하게 이용됩니다.)

내부 활성화 생명주기의 처리의 경우 각각의 observable는 _작업자 Looper_와 _observable 인스턴스화하는 스레드에 대한 Looper_가 수명이 연관되어 있습니다. 작업 Looper에서 observable이 활성화와 비활성화가 됩니다. 만약 observable가 다른 observable들을 활성화 시키면 이 작업자 Looper 스레드에서 상위 observable의 내부 updatable에 등록 시킵니다.

updatable는 반드시 Looper 스레드에서 observable을 등록해야 합니다. observable의 작업자 Looper를 실행하기 위해서 같은 스레드가 필요하진 않습니다. observable는 Updatable.update()호출을 updatable에 전달하기 위해 같은 Looper 스레드를 사용합니다.

updatable의 등록해제는 아무 스레드에서 가능합니만 등록이 취소된 후 이벤트가 updatable에 전달되는 경쟁 상태(race condition)를 예방하기 위해 등록이 발생한 동일한 Looper 스레드에서 updatable을 취소하는 것을 추천합니다.

코더는 Looper를 observable들 또는 등록된 updatable들 때문에 길게 유지해야 할 책임이 있습니다. Looper가 죽음으로써 생기는 예외나 메모리 누수는 코더의 책임입니다. 실제로는 메인 Looper가 아니라 다른 Looper를 항상 활성화 하기 위해 사용됩니다.