def test_asynchronous_ack_from_selectors(self):
        """
                         ack.on_next
        WaitOnLeftRight ------------> WaitOnLeftRight
        """

        sink = TObserver(immediate_continue=0)
        left_sel_sink = TObserver(immediate_continue=0)
        right_sel_sink = TObserver(immediate_continue=0)
        obs = ControlledZipObservable(
            left=self.left, right=self.right, scheduler=self.scheduler,
            request_left=lambda left, right: left <= right,
            request_right=lambda left, right: right <= left,
            match_func=lambda left, right: left == right,
        )
        obs.observe(init_observer_info(sink))
        obs.left_selector.observe(init_observer_info(left_sel_sink))
        obs.right_selector.observe(init_observer_info(right_sel_sink))
        ack1 = AckSubject()
        ack2 = AckSubject()
        self.left.on_next_single(1).subscribe(ack1)
        self.right.on_next_single(1).subscribe(ack2)
        sink.ack.on_next(continue_ack)

        self.assertFalse(ack1.has_value)

        left_sel_sink.ack.on_next(continue_ack)

        self.assertTrue(ack1.has_value)
        self.assertFalse(ack2.has_value)

        right_sel_sink.ack.on_next(continue_ack)

        self.assertTrue(ack1.has_value)
        self.assertTrue(ack2.has_value)
    def test_select_message_if_no_two_elements_match(self):
        """
                         ack.on_next
        WaitOnLeftRight ------------> WaitOnLeft
        """

        sink = TObserver(immediate_continue=0)
        left_sel_sink = TObserver(immediate_continue=0)
        right_sel_sink = TObserver(immediate_continue=0)
        ack1 = AckSubject()
        ack2 = AckSubject()
        obs = ControlledZipObservable(
            left=self.left, right=self.right, scheduler=self.scheduler,
            request_left=lambda left, right: left <= right,
            request_right=lambda left, right: right <= left,
            match_func=lambda left, right: left == right,
        )
        obs.observe(init_observer_info(sink))
        obs.left_selector.observe(init_observer_info(left_sel_sink))
        obs.right_selector.observe(init_observer_info(right_sel_sink))

        self.left.on_next_single(1).subscribe(ack1)
        self.right.on_next_single(2).subscribe(ack2)

        self.assertIsInstance(self.measure_state(obs), ControlledZipStates.WaitOnLeft)
        self.assertIsInstance(left_sel_sink.received[0], SelectCompleted)

        self.left.on_next_single(2).subscribe(ack1)

        self.assertIsInstance(self.measure_state(obs), ControlledZipStates.WaitOnLeftRight)

        for instance_obj, class_obj in zip(left_sel_sink.received, [SelectCompleted, SelectNext, SelectCompleted]):
            self.assertIsInstance(instance_obj, class_obj)
    def test_on_error_two_subscribers_asynchronously(self):
        o1 = TObserver()
        o2 = TObserver(immediate_continue=0)
        self.subject.observe(init_observer_info(o1))
        self.subject.observe(init_observer_info(o2))
        self.source.on_next_single(1)

        self.source.on_error(self.exc)

        self.assertEqual(self.exc, o1.exception)
        self.assertEqual(self.exc, o2.exception)
Esempio n. 4
0
    def on_next(self, elem: ElementType):
        try:
            obs_list: List[Observable] = [self.selector(e) for e in elem]
        except Exception as exc:
            self.on_error(exc)
            return stop_ack

        if len(obs_list) == 0:
            return continue_ack

        # generate a connectable observer for each observer
        def gen_connectable_observer():
            for _ in obs_list:
                conn_observer = ConnectableObserver(
                    underlying=self.inner_observer,
                    # scheduler=self.scheduler,
                )
                yield conn_observer

        conn_observers = list(gen_connectable_observer())

        with self.lock:
            prev_conn_observers = self.inner_observer.conn_observers
            self.inner_observer.conn_observers = self.inner_observer.conn_observers + conn_observers

        if len(prev_conn_observers) == 0:
            # conn_observers[0] is not used in this case
            first_conn_observer = self.inner_observer

        else:
            first_conn_observer = conn_observers[0]

        first_obs = obs_list[0]
        other_obs = obs_list[1:]
        other_conn_observers = conn_observers[1:]

        # def observe_on_subscribe_scheduler(_, __):
        disposable = first_obs.observe(
            init_observer_info(observer=first_conn_observer, ))
        self.composite_disposable.add(disposable)

        for obs, conn_observer in zip(other_obs, other_conn_observers):
            disposable = obs.observe(
                init_observer_info(observer=conn_observer, ))
            self.composite_disposable.add(disposable)

        # if self.subscribe_scheduler.idle:
        #     disposable = self.subscribe_scheduler.schedule(observe_on_subscribe_scheduler)
        #     self.composite_disposable.add(disposable)
        # else:
        #     observe_on_subscribe_scheduler(None, None)

        return continue_ack
    def test_on_next_enter_fast_loop_two_subscribers_asynchronously(self):
        o1 = TObserver(immediate_continue=0)
        o2 = TObserver(immediate_continue=0)
        self.subject.observe(init_observer_info(o1))
        self.subject.observe(init_observer_info(o2))
        self.source.on_next_single(1)
        self.source.on_next_single(2)

        o1.ack.on_next(continue_ack)
        self.scheduler.advance_by(1)

        self.assertEqual([1, 2], o1.received)
        self.assertEqual([1], o2.received)
    def test_backpressure_on_outer_observer(self):
        observer = FlatMapObserver(
            composite_disposable=self.composite_disposable,
            func=lambda v: v,
            scheduler=self.scheduler,
            subscribe_scheduler=self.scheduler,
            observer_info=init_observer_info(observer=self.sink),
        )
        self.source.observe(init_observer_info(observer))

        ack1 = self.source.on_next_single(self.inner_source_1)
        self.scheduler.advance_by(1)

        self.assertFalse(ack1.is_sync)
    def test_on_next_on_error_asynchronously(self):
        o1 = TObserver(immediate_continue=0)
        o2 = TObserver(immediate_continue=0)
        self.subject.observe(init_observer_info(o1))
        self.subject.observe(init_observer_info(o2))

        ack = self.source.on_next_single(1)
        self.source.on_error(self.exc)

        # o2.ack.on_next(continue_ack)
        # self.scheduler.advance_by(1)

        # verification
        self.assertEqual(self.exc, o1.exception)
        self.assertEqual(self.exc, o2.exception)
    def test_first_multiple_elem(self):
        obs = PairwiseObserver(self.sink)
        self.source.observe(init_observer_info(observer=obs))

        self.source.on_next_list([1, 2, 3])

        self.assertEqual([(1, 2), (2, 3)], self.sink.received)
    def test_send_element_on_inner_observer(self):
        observer = FlatMapObserver(
            composite_disposable=self.composite_disposable,
            func=lambda v: v,
            scheduler=self.scheduler,
            subscribe_scheduler=self.scheduler,
            observer_info=init_observer_info(observer=self.sink),
        )
        self.source.observe(init_observer_info(observer))
        self.source.on_next_single(self.inner_source_1)
        self.scheduler.advance_by(1)

        ack2 = self.inner_source_1.on_next_iter([1, 2])

        self.assertIsInstance(ack2, ContinueAck)
        self.assertListEqual(self.sink.received, [1, 2])
Esempio n. 10
0
    def test_multiple_left_select_complete_should_not_wait_on_right(self):
        """
                           left.on_next
        WaitOnLeftRight -----------------> WaitOnLeftRight
         InitState                             InitState
        """

        sink = TObserver()
        obs = MergeSelectorObservable(
            left=self.left,
            right=self.right,
            # scheduler=self.scheduler,
        )
        obs.observe(init_observer_info(sink))

        ack = self.left.on_next_list(
            [select_completed, select_completed, select_completed])

        self.assertIsInstance(self.measure_termination_state(obs),
                              TerminationStates.InitState)
        self.assertIsInstance(self.measure_state(obs),
                              ControlledZipStates.WaitOnLeftRight)
        self.assertEqual(
            [select_completed, select_completed, select_completed],
            sink.received)
        self.assertIsInstance(ack, ContinueAck)
Esempio n. 11
0
    def test_state_waitonleft_to_waitonleft(self):
        """
                        left.on_next
        WaitOnLeft ---------------------> WaitOnLeft
         InitState                          InitState
        """

        sink = TObserver()
        obs = MergeSelectorObservable(
            left=self.left,
            right=self.right,
            # scheduler=self.scheduler,
        )
        obs.observe(init_observer_info(sink))
        ack_right = self.right.on_next_list([select_next, select_completed])

        ack_left = self.left.on_next_list([select_completed, select_completed])

        self.assertIsInstance(self.measure_termination_state(obs),
                              TerminationStates.InitState)
        self.assertIsInstance(self.measure_state(obs),
                              ControlledZipStates.WaitOnLeft)
        self.assertEqual([select_completed, select_completed], sink.received)
        self.assertIsInstance(ack_left, ContinueAck)
        self.assertFalse(ack_right.has_value)
    def subscribe_to(self, source: Flowable, scheduler: Scheduler = None):
        scheduler = scheduler or self.scheduler

        subscription = source.unsafe_subscribe(
            init_subscriber(
                scheduler=scheduler,
                subscribe_scheduler=self.subscribe_scheduler,
            ))

        outer_self = self

        class SafeFlowableObserver(Observer):
            def on_next(self, elem: Any):
                if not outer_self.is_stopped:
                    outer_self.is_first = False

                    if outer_self._observable_subject is not None:
                        return outer_self._observable_subject.on_next(elem)

                return continue_ack

            def on_error(self, exc: Exception):
                outer_self.on_error(exc)

            def on_completed(self):
                outer_self.on_completed()

        observer = SafeFlowableObserver()

        disposable = subscription.observable.observe(
            init_observer_info(observer=observer, ))

        self.composite_diposable.add(disposable)
    def test_complete_first_source2(self):
        sink = TObserver()
        observer = FlatConcatNoBackpressureObserver(
            next_observer=sink,
            selector=lambda v: v,
            scheduler=self.scheduler,
            subscribe_scheduler=self.scheduler,
            composite_disposable=self.composite_disposable,
        )
        self.source.observe(init_observer_info(observer=observer))
        self.source.on_next_single(self.source1)
        self.scheduler.advance_by(1)
        self.source1.on_next_single(1)
        self.source.on_next_single(self.source2)
        self.scheduler.advance_by(1)
        self.source.on_completed()
        self.source2.on_next_single('a')
        self.source1.on_next_single(2)
        self.source1.on_completed()
        self.source2.on_next_single('b')

        self.source2.on_completed()

        self.assertEqual([1, 2, 'a', 'b'], sink.received)
        self.assertTrue(sink.is_completed)
    def test_on_completed(self):
        obs = PairwiseObserver(self.sink)
        self.source.observe(init_observer_info(observer=obs))

        self.source.on_completed()

        self.assertTrue(self.sink.is_completed)
 def setUp(self):
     self.scheduler = TScheduler()
     self.source = TObservable()
     self.subject = CacheServeFirstObservableSubject(
         scheduler=self.scheduler)
     self.source.observe(init_observer_info(self.subject))
     self.exc = Exception()
    def test_release_backpressure_on_completed(self):
        observer = FlatMapObserver(
            composite_disposable=self.composite_disposable,
            func=lambda v: v,
            scheduler=self.scheduler,
            subscribe_scheduler=self.scheduler,
            observer_info=init_observer_info(observer=self.sink),
        )
        self.source.observe(init_observer_info(observer))

        ack1 = self.source.on_next_single(self.inner_source_1)
        self.scheduler.advance_by(1)

        self.inner_source_1.on_completed()

        self.assertIsInstance(ack1.value, ContinueAck)
Esempio n. 17
0
    def on_next(self, elem: ElementType):
        obs_list: List[Observable] = [self.selector(e) for e in elem]

        for observable in obs_list:
            place_holder = self.PlaceHolder(
                observer=None,
            )

            merge_obs = MergeObservable(
                left=observable,
                right=place_holder,
            )

            parent, other = self.place_holders

            # def observe_on_subscribe_scheduler(_, __, merge_obs=merge_obs, parent=parent):
            #     return merge_obs.observe(self.observer_info.copy(observer=parent.observer))

            # # # make sure that Trampoline Scheduler is active
            # if self.subscribe_scheduler.idle:
            # disposable = self.subscribe_scheduler.schedule(observe_on_subscribe_scheduler)
            # else:
            #     disposable = observe_on_subscribe_scheduler(None, None)

            disposable = merge_obs.observe(init_observer_info(
                observer=parent.observer,
            ))
            self.composite_disposable.add(disposable)

            self.place_holders = (other, place_holder)

        return continue_ack
Esempio n. 18
0
    def test_on_error(self):
        sink = TObserver()
        self.obs.observe(init_observer_info(sink))

        self.sources[0].on_error(self.exception)

        self.assertEqual(self.exception, sink.exception)
Esempio n. 19
0
    def test_init_state(self):
        sink = TObserver()
        obs = ZipObservable(self.left, self.right)
        obs.observe(init_observer_info(sink))

        self.assertIsInstance(self.measure_termination_state(obs), TerminationStates.InitState)
        self.assertIsInstance(self.measure_state(obs), ZipStates.WaitOnLeftRight)
Esempio n. 20
0
    def test_subscribe_after_complete_should_complete_immediately(self):
        subject = PublishObservableSubject(self.scheduler)
        subject.on_completed()

        o1 = TObserver()
        subject.observe(init_observer_info(o1))
        self.assertTrue(o1.is_completed)
Esempio n. 21
0
    def test_on_error_on_next(self):
        sink = TObserver()
        self.obs.observe(init_observer_info(sink))
        self.sources[0].on_error(self.exception)

        ack = self.sources[1].on_next_single(0)

        self.assertIsInstance(ack, StopAck)
Esempio n. 22
0
    def test_on_next_second(self):
        sink = TObserver()
        self.obs.observe(init_observer_info(sink))

        ack = self.sources[1].on_next_single(1)

        self.assertFalse(ack.is_sync)
        self.assertEqual([], sink.received)
Esempio n. 23
0
    def test_on_next_first(self):
        sink = TObserver()
        self.obs.observe(init_observer_info(sink))

        ack = self.sources[0].on_next_single(1)

        self.assertIsInstance(ack, ContinueAck)
        self.assertEqual([1], sink.received)
    def test_second_single_elem(self):
        obs = PairwiseObserver(self.sink)
        self.source.observe(init_observer_info(observer=obs))
        self.source.on_next_single(1)

        self.source.on_next_single(2)

        self.assertEqual([(1, 2)], self.sink.received)
    def test_on_error(self):
        obs = PairwiseObserver(self.sink)
        self.source.observe(init_observer_info(observer=obs))
        exc = Exception()

        self.source.on_error(exc)

        self.assertEqual(exc, self.sink.exception)
    def test_on_error(self):
        sink = TObserver()
        observer = ToListObserver(observer=sink, )
        self.source.observe(init_observer_info(observer))

        self.source.on_error(self.exc)

        self.assertEqual(self.exc, sink.exception)
 def test_initialize(self):
     observer = FlatMapObserver(
         composite_disposable=self.composite_disposable,
         func=lambda v: v,
         scheduler=self.scheduler,
         subscribe_scheduler=self.scheduler,
         observer_info=init_observer_info(observer=self.sink),
     )
Esempio n. 28
0
    def __post_init__(self):
        self.place_holders = (self.PlaceHolder(observer=None), self.PlaceHolder(observer=None))

        disposable = MergeObservable(
            left=self.place_holders[0],
            right=self.place_holders[1],
        ).observe(init_observer_info(observer=self.observer))
        self.composite_disposable.add(disposable)
Esempio n. 29
0
    def test_use_case(self):
        sink = TObserver(immediate_continue=0)
        subscription = rxbp.return_value(1).unsafe_subscribe(self.subscriber)
        subscription.observable.observe(init_observer_info(observer=sink))

        self.scheduler.advance_by(1)

        self.assertEqual([1], sink.received)
    def test_first_single_elem(self):
        obs = PairwiseObserver(self.sink)
        self.source.observe(init_observer_info(observer=obs))

        self.source.on_next_single(1)

        self.assertEqual(1, obs.last_elem)
        self.assertEqual([], self.sink.received)