Search in sources :

Example 6 with Subscriber

use of io.servicetalk.concurrent.PublisherSource.Subscriber in project servicetalk by apple.

the class PublisherFlatMapMergeTest method concurrentSkipQueueDoesNotDeadlock.

@Test
void concurrentSkipQueueDoesNotDeadlock() throws Throwable {
    assert executorService != null;
    List<TestSubscriptionPublisherPair<Integer>> mappedPublishers = new ArrayList<>();
    CountDownLatch onNextLatch = new CountDownLatch(1);
    CountDownLatch onNextSecondLatch = new CountDownLatch(2);
    CountDownLatch onNextThirdLatch = new CountDownLatch(3);
    CountDownLatch onNextWaitLatch = new CountDownLatch(1);
    CountDownLatch onCompleteLatch = new CountDownLatch(1);
    AtomicReference<Throwable> errorRef = new AtomicReference<>();
    TestSubscription upstreamSubscription = new TestSubscription();
    publisher = new TestPublisher.Builder<Integer>().disableAutoOnSubscribe().build(subscriber1 -> {
        subscriber1.onSubscribe(upstreamSubscription);
        return subscriber1;
    });
    toSource(publisher.flatMapMerge(i -> {
        TestSubscriptionPublisherPair<Integer> pair = new TestSubscriptionPublisherPair<>(i);
        mappedPublishers.add(pair);
        return pair.mappedPublisher;
    }, 3)).subscribe(new Subscriber<Integer>() {

        @Override
        public void onSubscribe(final Subscription subscription) {
            subscription.request(Long.MAX_VALUE);
        }

        @Override
        public void onNext(@Nullable final Integer integer) {
            onNextLatch.countDown();
            onNextSecondLatch.countDown();
            onNextThirdLatch.countDown();
            try {
                onNextWaitLatch.await();
            } catch (InterruptedException e) {
                Thread.currentThread().interrupt();
                throwException(e);
            }
        }

        @Override
        public void onError(final Throwable t) {
            errorRef.set(t);
            onCompleteLatch.countDown();
        }

        @Override
        public void onComplete() {
            onCompleteLatch.countDown();
        }
    });
    upstreamSubscription.awaitRequestN(2);
    publisher.onNext(1, 2);
    publisher.onComplete();
    assertThat(mappedPublishers, hasSize(2));
    TestSubscriptionPublisherPair<Integer> first = mappedPublishers.get(0);
    TestSubscriptionPublisherPair<Integer> second = mappedPublishers.get(1);
    Future<?> f = executorService.submit(() -> {
        try {
            first.doOnSubscribe(1);
            first.mappedSubscription.awaitRequestN(1);
            first.mappedPublisher.onNext(1);
        } catch (Throwable cause) {
            first.mappedPublisher.onError(cause);
            return;
        }
        first.mappedPublisher.onComplete();
    });
    // Wait for the executorService thread to be in onNext, we want to force concurrent delivery.
    onNextLatch.await();
    // Deliver the first signal, and allow the executorService thread to exit onNext.
    second.doOnSubscribe(2);
    second.mappedSubscription.awaitRequestN(2);
    second.mappedPublisher.onNext(2);
    onNextWaitLatch.countDown();
    // Wait for the onNext from this thread to be delivered in the executorService thread.
    onNextSecondLatch.await();
    // Wait for the executorService thread to deliver onComplete and release the lock in the operator.
    f.get();
    // The second mapped publisher previously had items queued, and there are no other thread holding the lock in
    // the operator, it should be delivered.
    second.mappedPublisher.onNext(3);
    onNextThirdLatch.await();
    // Deliver the last onComplete and verify normal termination.
    second.mappedPublisher.onComplete();
    onCompleteLatch.await();
    Throwable cause = errorRef.get();
    if (cause != null) {
        throw cause;
    }
}
Also used : PlatformDependent.throwException(io.servicetalk.utils.internal.PlatformDependent.throwException) AfterAll(org.junit.jupiter.api.AfterAll) SourceAdapters.fromSource(io.servicetalk.concurrent.api.SourceAdapters.fromSource) Future(java.util.concurrent.Future) Assertions.assertFalse(org.junit.jupiter.api.Assertions.assertFalse) BeforeAll(org.junit.jupiter.api.BeforeAll) EMPTY_SUBSCRIPTION(io.servicetalk.concurrent.internal.EmptySubscriptions.EMPTY_SUBSCRIPTION) Arrays.asList(java.util.Arrays.asList) Map(java.util.Map) Matchers.nullValue(org.hamcrest.Matchers.nullValue) Mockito.doAnswer(org.mockito.Mockito.doAnswer) TestPublisherSubscriber(io.servicetalk.concurrent.test.internal.TestPublisherSubscriber) PublisherSource(io.servicetalk.concurrent.PublisherSource) BlockingQueue(java.util.concurrent.BlockingQueue) Math.min(java.lang.Math.min) MILLISECONDS(java.util.concurrent.TimeUnit.MILLISECONDS) Test(org.junit.jupiter.api.Test) Matchers.instanceOf(org.hamcrest.Matchers.instanceOf) ArrayBlockingQueue(java.util.concurrent.ArrayBlockingQueue) CountDownLatch(java.util.concurrent.CountDownLatch) List(java.util.List) Matchers.contains(org.hamcrest.Matchers.contains) Matchers.containsInAnyOrder(org.hamcrest.Matchers.containsInAnyOrder) Assertions.assertTrue(org.junit.jupiter.api.Assertions.assertTrue) Matchers.is(org.hamcrest.Matchers.is) Queue(java.util.Queue) ConcurrentLinkedQueue(java.util.concurrent.ConcurrentLinkedQueue) Mockito.mock(org.mockito.Mockito.mock) IntStream(java.util.stream.IntStream) Publisher.never(io.servicetalk.concurrent.api.Publisher.never) ArgumentMatchers.any(org.mockito.ArgumentMatchers.any) Assertions.assertNotNull(org.junit.jupiter.api.Assertions.assertNotNull) Processor(io.servicetalk.concurrent.PublisherSource.Processor) DeliberateException(io.servicetalk.concurrent.internal.DeliberateException) Assertions.assertNull(org.junit.jupiter.api.Assertions.assertNull) HashMap(java.util.HashMap) AtomicReference(java.util.concurrent.atomic.AtomicReference) Function(java.util.function.Function) Publisher.range(io.servicetalk.concurrent.api.Publisher.range) Subscriber(io.servicetalk.concurrent.PublisherSource.Subscriber) ArrayList(java.util.ArrayList) Single.succeeded(io.servicetalk.concurrent.api.Single.succeeded) Matchers.hasSize(org.hamcrest.Matchers.hasSize) MatcherAssert.assertThat(org.hamcrest.MatcherAssert.assertThat) Assertions.assertEquals(org.junit.jupiter.api.Assertions.assertEquals) Publisher.from(io.servicetalk.concurrent.api.Publisher.from) DELIBERATE_EXCEPTION(io.servicetalk.concurrent.internal.DeliberateException.DELIBERATE_EXCEPTION) ExecutorService(java.util.concurrent.ExecutorService) Nullable(javax.annotation.Nullable) ValueSource(org.junit.jupiter.params.provider.ValueSource) Matchers.empty(org.hamcrest.Matchers.empty) Subscription(io.servicetalk.concurrent.PublisherSource.Subscription) Processors.newPublisherProcessor(io.servicetalk.concurrent.api.Processors.newPublisherProcessor) SourceAdapters.toSource(io.servicetalk.concurrent.api.SourceAdapters.toSource) Mockito.verify(org.mockito.Mockito.verify) ExecutionException(java.util.concurrent.ExecutionException) ParameterizedTest(org.junit.jupiter.params.ParameterizedTest) Publisher.failed(io.servicetalk.concurrent.api.Publisher.failed) Matchers.sameInstance(org.hamcrest.Matchers.sameInstance) ArrayDeque(java.util.ArrayDeque) SECONDS(java.util.concurrent.TimeUnit.SECONDS) ArrayList(java.util.ArrayList) AtomicReference(java.util.concurrent.atomic.AtomicReference) CountDownLatch(java.util.concurrent.CountDownLatch) Subscription(io.servicetalk.concurrent.PublisherSource.Subscription) Test(org.junit.jupiter.api.Test) ParameterizedTest(org.junit.jupiter.params.ParameterizedTest)

Example 7 with Subscriber

use of io.servicetalk.concurrent.PublisherSource.Subscriber in project servicetalk by apple.

the class PublisherFlatMapMergeTest method cancelPropagatedBeforeErrorButOriginalErrorPreserved.

@Test
void cancelPropagatedBeforeErrorButOriginalErrorPreserved() {
    CountDownLatch cancelledLatch = new CountDownLatch(1);
    publisher = new TestPublisher.Builder<Integer>().disableAutoOnSubscribe().build(subscriber1 -> {
        subscriber1.onSubscribe(new Subscription() {

            @Override
            public void request(final long n) {
            }

            @Override
            public void cancel() {
                try {
                    cancelledLatch.await();
                } catch (InterruptedException e) {
                    Thread.currentThread().interrupt();
                    throwException(e);
                }
                subscriber1.onError(new IllegalStateException("shouldn't reach the Subscriber!"));
            }
        });
        return subscriber1;
    });
    TestPublisher<Integer> mappedPublisher = new TestPublisher<>();
    toSource(publisher.flatMapMerge(i -> mappedPublisher, 1)).subscribe(subscriber);
    subscriber.awaitSubscription().request(1);
    publisher.onNext(1);
    assert executor != null;
    executor.execute(() -> mappedPublisher.onError(DELIBERATE_EXCEPTION));
    // Verify that cancel happens before terminal. This ensures that sources which allow for multiple sequential
    // Subscribers can clear out there current subscriber in preparation for the next Subscriber and avoid duplicate
    // subscribe related errors.
    assertThat(subscriber.pollTerminal(TERMINAL_POLL_MS, MILLISECONDS), is(nullValue()));
    cancelledLatch.countDown();
    assertThat(subscriber.awaitOnError(), sameInstance(DELIBERATE_EXCEPTION));
}
Also used : PlatformDependent.throwException(io.servicetalk.utils.internal.PlatformDependent.throwException) AfterAll(org.junit.jupiter.api.AfterAll) SourceAdapters.fromSource(io.servicetalk.concurrent.api.SourceAdapters.fromSource) Future(java.util.concurrent.Future) Assertions.assertFalse(org.junit.jupiter.api.Assertions.assertFalse) BeforeAll(org.junit.jupiter.api.BeforeAll) EMPTY_SUBSCRIPTION(io.servicetalk.concurrent.internal.EmptySubscriptions.EMPTY_SUBSCRIPTION) Arrays.asList(java.util.Arrays.asList) Map(java.util.Map) Matchers.nullValue(org.hamcrest.Matchers.nullValue) Mockito.doAnswer(org.mockito.Mockito.doAnswer) TestPublisherSubscriber(io.servicetalk.concurrent.test.internal.TestPublisherSubscriber) PublisherSource(io.servicetalk.concurrent.PublisherSource) BlockingQueue(java.util.concurrent.BlockingQueue) Math.min(java.lang.Math.min) MILLISECONDS(java.util.concurrent.TimeUnit.MILLISECONDS) Test(org.junit.jupiter.api.Test) Matchers.instanceOf(org.hamcrest.Matchers.instanceOf) ArrayBlockingQueue(java.util.concurrent.ArrayBlockingQueue) CountDownLatch(java.util.concurrent.CountDownLatch) List(java.util.List) Matchers.contains(org.hamcrest.Matchers.contains) Matchers.containsInAnyOrder(org.hamcrest.Matchers.containsInAnyOrder) Assertions.assertTrue(org.junit.jupiter.api.Assertions.assertTrue) Matchers.is(org.hamcrest.Matchers.is) Queue(java.util.Queue) ConcurrentLinkedQueue(java.util.concurrent.ConcurrentLinkedQueue) Mockito.mock(org.mockito.Mockito.mock) IntStream(java.util.stream.IntStream) Publisher.never(io.servicetalk.concurrent.api.Publisher.never) ArgumentMatchers.any(org.mockito.ArgumentMatchers.any) Assertions.assertNotNull(org.junit.jupiter.api.Assertions.assertNotNull) Processor(io.servicetalk.concurrent.PublisherSource.Processor) DeliberateException(io.servicetalk.concurrent.internal.DeliberateException) Assertions.assertNull(org.junit.jupiter.api.Assertions.assertNull) HashMap(java.util.HashMap) AtomicReference(java.util.concurrent.atomic.AtomicReference) Function(java.util.function.Function) Publisher.range(io.servicetalk.concurrent.api.Publisher.range) Subscriber(io.servicetalk.concurrent.PublisherSource.Subscriber) ArrayList(java.util.ArrayList) Single.succeeded(io.servicetalk.concurrent.api.Single.succeeded) Matchers.hasSize(org.hamcrest.Matchers.hasSize) MatcherAssert.assertThat(org.hamcrest.MatcherAssert.assertThat) Assertions.assertEquals(org.junit.jupiter.api.Assertions.assertEquals) Publisher.from(io.servicetalk.concurrent.api.Publisher.from) DELIBERATE_EXCEPTION(io.servicetalk.concurrent.internal.DeliberateException.DELIBERATE_EXCEPTION) ExecutorService(java.util.concurrent.ExecutorService) Nullable(javax.annotation.Nullable) ValueSource(org.junit.jupiter.params.provider.ValueSource) Matchers.empty(org.hamcrest.Matchers.empty) Subscription(io.servicetalk.concurrent.PublisherSource.Subscription) Processors.newPublisherProcessor(io.servicetalk.concurrent.api.Processors.newPublisherProcessor) SourceAdapters.toSource(io.servicetalk.concurrent.api.SourceAdapters.toSource) Mockito.verify(org.mockito.Mockito.verify) ExecutionException(java.util.concurrent.ExecutionException) ParameterizedTest(org.junit.jupiter.params.ParameterizedTest) Publisher.failed(io.servicetalk.concurrent.api.Publisher.failed) Matchers.sameInstance(org.hamcrest.Matchers.sameInstance) ArrayDeque(java.util.ArrayDeque) SECONDS(java.util.concurrent.TimeUnit.SECONDS) CountDownLatch(java.util.concurrent.CountDownLatch) Subscription(io.servicetalk.concurrent.PublisherSource.Subscription) Test(org.junit.jupiter.api.Test) ParameterizedTest(org.junit.jupiter.params.ParameterizedTest)

Example 8 with Subscriber

use of io.servicetalk.concurrent.PublisherSource.Subscriber in project servicetalk by apple.

the class PublisherFlatMapMergeTest method errorFromMappedSubscriberIsSequencedWithOnNextSignals.

@Test
void errorFromMappedSubscriberIsSequencedWithOnNextSignals() throws InterruptedException {
    List<TestSubscriptionPublisherPair<Integer>> mappedPublishers = new ArrayList<>();
    TestSubscription upstreamSubscription = new TestSubscription();
    publisher = new TestPublisher.Builder<Integer>().disableAutoOnSubscribe().build(subscriber1 -> {
        subscriber1.onSubscribe(upstreamSubscription);
        return subscriber1;
    });
    toSource(publisher.flatMapMerge(i -> {
        TestSubscriptionPublisherPair<Integer> pair = new TestSubscriptionPublisherPair<>(i);
        mappedPublishers.add(pair);
        return pair.mappedPublisher;
    }, 2)).subscribe(subscriber);
    Subscription subscription = subscriber.awaitSubscription();
    subscription.request(1);
    verifyCumulativeDemand(upstreamSubscription, 2);
    publisher.onNext(1, 2);
    assertThat(mappedPublishers, hasSize(2));
    TestSubscriptionPublisherPair<Integer> first = mappedPublishers.get(0);
    TestSubscriptionPublisherPair<Integer> second = mappedPublishers.get(1);
    first.doOnSubscribe(1);
    first.mappedSubscription.awaitRequestN(1);
    second.doOnSubscribe(2);
    second.mappedSubscription.awaitRequestN(1);
    // Exhaust outstanding requestN from downstream
    first.mappedPublisher.onNext(10);
    assertThat(subscriber.pollAllOnNext(), contains(10));
    // These signals should be queued, and the error shouldn't jump the queue.
    second.mappedPublisher.onNext(11);
    second.mappedPublisher.onError(DELIBERATE_EXCEPTION);
    assertThat(subscriber.pollAllOnNext(), is(empty()));
    assertTrue(upstreamSubscription.isCancelled());
    subscription.request(1);
    assertThat(subscriber.pollAllOnNext(), contains(11));
    assertThat(subscriber.awaitOnError(), sameInstance(DELIBERATE_EXCEPTION));
}
Also used : PlatformDependent.throwException(io.servicetalk.utils.internal.PlatformDependent.throwException) AfterAll(org.junit.jupiter.api.AfterAll) SourceAdapters.fromSource(io.servicetalk.concurrent.api.SourceAdapters.fromSource) Future(java.util.concurrent.Future) Assertions.assertFalse(org.junit.jupiter.api.Assertions.assertFalse) BeforeAll(org.junit.jupiter.api.BeforeAll) EMPTY_SUBSCRIPTION(io.servicetalk.concurrent.internal.EmptySubscriptions.EMPTY_SUBSCRIPTION) Arrays.asList(java.util.Arrays.asList) Map(java.util.Map) Matchers.nullValue(org.hamcrest.Matchers.nullValue) Mockito.doAnswer(org.mockito.Mockito.doAnswer) TestPublisherSubscriber(io.servicetalk.concurrent.test.internal.TestPublisherSubscriber) PublisherSource(io.servicetalk.concurrent.PublisherSource) BlockingQueue(java.util.concurrent.BlockingQueue) Math.min(java.lang.Math.min) MILLISECONDS(java.util.concurrent.TimeUnit.MILLISECONDS) Test(org.junit.jupiter.api.Test) Matchers.instanceOf(org.hamcrest.Matchers.instanceOf) ArrayBlockingQueue(java.util.concurrent.ArrayBlockingQueue) CountDownLatch(java.util.concurrent.CountDownLatch) List(java.util.List) Matchers.contains(org.hamcrest.Matchers.contains) Matchers.containsInAnyOrder(org.hamcrest.Matchers.containsInAnyOrder) Assertions.assertTrue(org.junit.jupiter.api.Assertions.assertTrue) Matchers.is(org.hamcrest.Matchers.is) Queue(java.util.Queue) ConcurrentLinkedQueue(java.util.concurrent.ConcurrentLinkedQueue) Mockito.mock(org.mockito.Mockito.mock) IntStream(java.util.stream.IntStream) Publisher.never(io.servicetalk.concurrent.api.Publisher.never) ArgumentMatchers.any(org.mockito.ArgumentMatchers.any) Assertions.assertNotNull(org.junit.jupiter.api.Assertions.assertNotNull) Processor(io.servicetalk.concurrent.PublisherSource.Processor) DeliberateException(io.servicetalk.concurrent.internal.DeliberateException) Assertions.assertNull(org.junit.jupiter.api.Assertions.assertNull) HashMap(java.util.HashMap) AtomicReference(java.util.concurrent.atomic.AtomicReference) Function(java.util.function.Function) Publisher.range(io.servicetalk.concurrent.api.Publisher.range) Subscriber(io.servicetalk.concurrent.PublisherSource.Subscriber) ArrayList(java.util.ArrayList) Single.succeeded(io.servicetalk.concurrent.api.Single.succeeded) Matchers.hasSize(org.hamcrest.Matchers.hasSize) MatcherAssert.assertThat(org.hamcrest.MatcherAssert.assertThat) Assertions.assertEquals(org.junit.jupiter.api.Assertions.assertEquals) Publisher.from(io.servicetalk.concurrent.api.Publisher.from) DELIBERATE_EXCEPTION(io.servicetalk.concurrent.internal.DeliberateException.DELIBERATE_EXCEPTION) ExecutorService(java.util.concurrent.ExecutorService) Nullable(javax.annotation.Nullable) ValueSource(org.junit.jupiter.params.provider.ValueSource) Matchers.empty(org.hamcrest.Matchers.empty) Subscription(io.servicetalk.concurrent.PublisherSource.Subscription) Processors.newPublisherProcessor(io.servicetalk.concurrent.api.Processors.newPublisherProcessor) SourceAdapters.toSource(io.servicetalk.concurrent.api.SourceAdapters.toSource) Mockito.verify(org.mockito.Mockito.verify) ExecutionException(java.util.concurrent.ExecutionException) ParameterizedTest(org.junit.jupiter.params.ParameterizedTest) Publisher.failed(io.servicetalk.concurrent.api.Publisher.failed) Matchers.sameInstance(org.hamcrest.Matchers.sameInstance) ArrayDeque(java.util.ArrayDeque) SECONDS(java.util.concurrent.TimeUnit.SECONDS) ArrayList(java.util.ArrayList) Subscription(io.servicetalk.concurrent.PublisherSource.Subscription) Test(org.junit.jupiter.api.Test) ParameterizedTest(org.junit.jupiter.params.ParameterizedTest)

Example 9 with Subscriber

use of io.servicetalk.concurrent.PublisherSource.Subscriber in project servicetalk by apple.

the class PublisherFlatMapMergeTest method requestLongMaxMultipleTimes.

@Test
void requestLongMaxMultipleTimes() throws InterruptedException {
    TestSubscription upstreamSubscription = new TestSubscription();
    publisher = new TestPublisher.Builder<Integer>().disableAutoOnSubscribe().build(subscriber1 -> {
        subscriber1.onSubscribe(upstreamSubscription);
        return subscriber1;
    });
    toSource(publisher.flatMapMerge(Publisher::from, 2)).subscribe(subscriber);
    Subscription subscription = subscriber.awaitSubscription();
    subscription.request(Long.MAX_VALUE);
    verifyCumulativeDemand(upstreamSubscription, 2);
    publisher.onNext(1);
    publisher.onNext(2);
    subscription.request(Long.MAX_VALUE);
    verifyCumulativeDemand(upstreamSubscription, 4);
    publisher.onNext(3);
    publisher.onNext(4);
    verifyCumulativeDemand(upstreamSubscription, 6);
}
Also used : PlatformDependent.throwException(io.servicetalk.utils.internal.PlatformDependent.throwException) AfterAll(org.junit.jupiter.api.AfterAll) SourceAdapters.fromSource(io.servicetalk.concurrent.api.SourceAdapters.fromSource) Future(java.util.concurrent.Future) Assertions.assertFalse(org.junit.jupiter.api.Assertions.assertFalse) BeforeAll(org.junit.jupiter.api.BeforeAll) EMPTY_SUBSCRIPTION(io.servicetalk.concurrent.internal.EmptySubscriptions.EMPTY_SUBSCRIPTION) Arrays.asList(java.util.Arrays.asList) Map(java.util.Map) Matchers.nullValue(org.hamcrest.Matchers.nullValue) Mockito.doAnswer(org.mockito.Mockito.doAnswer) TestPublisherSubscriber(io.servicetalk.concurrent.test.internal.TestPublisherSubscriber) PublisherSource(io.servicetalk.concurrent.PublisherSource) BlockingQueue(java.util.concurrent.BlockingQueue) Math.min(java.lang.Math.min) MILLISECONDS(java.util.concurrent.TimeUnit.MILLISECONDS) Test(org.junit.jupiter.api.Test) Matchers.instanceOf(org.hamcrest.Matchers.instanceOf) ArrayBlockingQueue(java.util.concurrent.ArrayBlockingQueue) CountDownLatch(java.util.concurrent.CountDownLatch) List(java.util.List) Matchers.contains(org.hamcrest.Matchers.contains) Matchers.containsInAnyOrder(org.hamcrest.Matchers.containsInAnyOrder) Assertions.assertTrue(org.junit.jupiter.api.Assertions.assertTrue) Matchers.is(org.hamcrest.Matchers.is) Queue(java.util.Queue) ConcurrentLinkedQueue(java.util.concurrent.ConcurrentLinkedQueue) Mockito.mock(org.mockito.Mockito.mock) IntStream(java.util.stream.IntStream) Publisher.never(io.servicetalk.concurrent.api.Publisher.never) ArgumentMatchers.any(org.mockito.ArgumentMatchers.any) Assertions.assertNotNull(org.junit.jupiter.api.Assertions.assertNotNull) Processor(io.servicetalk.concurrent.PublisherSource.Processor) DeliberateException(io.servicetalk.concurrent.internal.DeliberateException) Assertions.assertNull(org.junit.jupiter.api.Assertions.assertNull) HashMap(java.util.HashMap) AtomicReference(java.util.concurrent.atomic.AtomicReference) Function(java.util.function.Function) Publisher.range(io.servicetalk.concurrent.api.Publisher.range) Subscriber(io.servicetalk.concurrent.PublisherSource.Subscriber) ArrayList(java.util.ArrayList) Single.succeeded(io.servicetalk.concurrent.api.Single.succeeded) Matchers.hasSize(org.hamcrest.Matchers.hasSize) MatcherAssert.assertThat(org.hamcrest.MatcherAssert.assertThat) Assertions.assertEquals(org.junit.jupiter.api.Assertions.assertEquals) Publisher.from(io.servicetalk.concurrent.api.Publisher.from) DELIBERATE_EXCEPTION(io.servicetalk.concurrent.internal.DeliberateException.DELIBERATE_EXCEPTION) ExecutorService(java.util.concurrent.ExecutorService) Nullable(javax.annotation.Nullable) ValueSource(org.junit.jupiter.params.provider.ValueSource) Matchers.empty(org.hamcrest.Matchers.empty) Subscription(io.servicetalk.concurrent.PublisherSource.Subscription) Processors.newPublisherProcessor(io.servicetalk.concurrent.api.Processors.newPublisherProcessor) SourceAdapters.toSource(io.servicetalk.concurrent.api.SourceAdapters.toSource) Mockito.verify(org.mockito.Mockito.verify) ExecutionException(java.util.concurrent.ExecutionException) ParameterizedTest(org.junit.jupiter.params.ParameterizedTest) Publisher.failed(io.servicetalk.concurrent.api.Publisher.failed) Matchers.sameInstance(org.hamcrest.Matchers.sameInstance) ArrayDeque(java.util.ArrayDeque) SECONDS(java.util.concurrent.TimeUnit.SECONDS) Subscription(io.servicetalk.concurrent.PublisherSource.Subscription) Test(org.junit.jupiter.api.Test) ParameterizedTest(org.junit.jupiter.params.ParameterizedTest)

Example 10 with Subscriber

use of io.servicetalk.concurrent.PublisherSource.Subscriber in project servicetalk by apple.

the class PublisherFlatMapMergeTest method requestAndEmitConcurrency.

@Test
void requestAndEmitConcurrency() throws Exception {
    int totalToRequest = 1000;
    List<Integer> received = new ArrayList<>(totalToRequest);
    CountDownLatch requestingStarting = new CountDownLatch(1);
    TestSubscription upstreamSubscription = new TestSubscription();
    publisher = new TestPublisher.Builder<Integer>().disableAutoOnSubscribe().build(subscriber1 -> {
        subscriber1.onSubscribe(upstreamSubscription);
        return subscriber1;
    });
    toSource(publisher.flatMapMerge(Publisher::from, 2).beforeOnNext(received::add)).subscribe(subscriber);
    Subscription subscription = subscriber.awaitSubscription();
    assert executorService != null;
    Future<?> submitFuture = executorService.submit(() -> {
        requestingStarting.countDown();
        for (int i = 0; i < totalToRequest; i++) {
            subscription.request(1);
        }
    });
    // Just to make sure we have both threads running concurrently.
    requestingStarting.await();
    for (int i = 0; i < totalToRequest; i++) {
        upstreamSubscription.awaitRequestN(i + 1);
        publisher.onNext(i);
    }
    submitFuture.get();
    assertThat("Unexpected items emitted.", received, hasSize(totalToRequest));
    assertThat(received, containsInAnyOrder(IntStream.range(0, totalToRequest).boxed().toArray()));
}
Also used : PlatformDependent.throwException(io.servicetalk.utils.internal.PlatformDependent.throwException) AfterAll(org.junit.jupiter.api.AfterAll) SourceAdapters.fromSource(io.servicetalk.concurrent.api.SourceAdapters.fromSource) Future(java.util.concurrent.Future) Assertions.assertFalse(org.junit.jupiter.api.Assertions.assertFalse) BeforeAll(org.junit.jupiter.api.BeforeAll) EMPTY_SUBSCRIPTION(io.servicetalk.concurrent.internal.EmptySubscriptions.EMPTY_SUBSCRIPTION) Arrays.asList(java.util.Arrays.asList) Map(java.util.Map) Matchers.nullValue(org.hamcrest.Matchers.nullValue) Mockito.doAnswer(org.mockito.Mockito.doAnswer) TestPublisherSubscriber(io.servicetalk.concurrent.test.internal.TestPublisherSubscriber) PublisherSource(io.servicetalk.concurrent.PublisherSource) BlockingQueue(java.util.concurrent.BlockingQueue) Math.min(java.lang.Math.min) MILLISECONDS(java.util.concurrent.TimeUnit.MILLISECONDS) Test(org.junit.jupiter.api.Test) Matchers.instanceOf(org.hamcrest.Matchers.instanceOf) ArrayBlockingQueue(java.util.concurrent.ArrayBlockingQueue) CountDownLatch(java.util.concurrent.CountDownLatch) List(java.util.List) Matchers.contains(org.hamcrest.Matchers.contains) Matchers.containsInAnyOrder(org.hamcrest.Matchers.containsInAnyOrder) Assertions.assertTrue(org.junit.jupiter.api.Assertions.assertTrue) Matchers.is(org.hamcrest.Matchers.is) Queue(java.util.Queue) ConcurrentLinkedQueue(java.util.concurrent.ConcurrentLinkedQueue) Mockito.mock(org.mockito.Mockito.mock) IntStream(java.util.stream.IntStream) Publisher.never(io.servicetalk.concurrent.api.Publisher.never) ArgumentMatchers.any(org.mockito.ArgumentMatchers.any) Assertions.assertNotNull(org.junit.jupiter.api.Assertions.assertNotNull) Processor(io.servicetalk.concurrent.PublisherSource.Processor) DeliberateException(io.servicetalk.concurrent.internal.DeliberateException) Assertions.assertNull(org.junit.jupiter.api.Assertions.assertNull) HashMap(java.util.HashMap) AtomicReference(java.util.concurrent.atomic.AtomicReference) Function(java.util.function.Function) Publisher.range(io.servicetalk.concurrent.api.Publisher.range) Subscriber(io.servicetalk.concurrent.PublisherSource.Subscriber) ArrayList(java.util.ArrayList) Single.succeeded(io.servicetalk.concurrent.api.Single.succeeded) Matchers.hasSize(org.hamcrest.Matchers.hasSize) MatcherAssert.assertThat(org.hamcrest.MatcherAssert.assertThat) Assertions.assertEquals(org.junit.jupiter.api.Assertions.assertEquals) Publisher.from(io.servicetalk.concurrent.api.Publisher.from) DELIBERATE_EXCEPTION(io.servicetalk.concurrent.internal.DeliberateException.DELIBERATE_EXCEPTION) ExecutorService(java.util.concurrent.ExecutorService) Nullable(javax.annotation.Nullable) ValueSource(org.junit.jupiter.params.provider.ValueSource) Matchers.empty(org.hamcrest.Matchers.empty) Subscription(io.servicetalk.concurrent.PublisherSource.Subscription) Processors.newPublisherProcessor(io.servicetalk.concurrent.api.Processors.newPublisherProcessor) SourceAdapters.toSource(io.servicetalk.concurrent.api.SourceAdapters.toSource) Mockito.verify(org.mockito.Mockito.verify) ExecutionException(java.util.concurrent.ExecutionException) ParameterizedTest(org.junit.jupiter.params.ParameterizedTest) Publisher.failed(io.servicetalk.concurrent.api.Publisher.failed) Matchers.sameInstance(org.hamcrest.Matchers.sameInstance) ArrayDeque(java.util.ArrayDeque) SECONDS(java.util.concurrent.TimeUnit.SECONDS) ArrayList(java.util.ArrayList) CountDownLatch(java.util.concurrent.CountDownLatch) Subscription(io.servicetalk.concurrent.PublisherSource.Subscription) Test(org.junit.jupiter.api.Test) ParameterizedTest(org.junit.jupiter.params.ParameterizedTest)

Aggregations

Subscriber (io.servicetalk.concurrent.PublisherSource.Subscriber)31 Test (org.junit.jupiter.api.Test)29 Subscription (io.servicetalk.concurrent.PublisherSource.Subscription)27 DELIBERATE_EXCEPTION (io.servicetalk.concurrent.internal.DeliberateException.DELIBERATE_EXCEPTION)23 AtomicReference (java.util.concurrent.atomic.AtomicReference)22 TestPublisherSubscriber (io.servicetalk.concurrent.test.internal.TestPublisherSubscriber)20 CountDownLatch (java.util.concurrent.CountDownLatch)20 Mockito.mock (org.mockito.Mockito.mock)20 SourceAdapters.toSource (io.servicetalk.concurrent.api.SourceAdapters.toSource)19 MatcherAssert.assertThat (org.hamcrest.MatcherAssert.assertThat)19 Matchers.is (org.hamcrest.Matchers.is)19 ArgumentMatchers.any (org.mockito.ArgumentMatchers.any)19 Mockito.doAnswer (org.mockito.Mockito.doAnswer)19 Publisher.from (io.servicetalk.concurrent.api.Publisher.from)18 Arrays.asList (java.util.Arrays.asList)18 PlatformDependent.throwException (io.servicetalk.utils.internal.PlatformDependent.throwException)16 ArrayList (java.util.ArrayList)16 List (java.util.List)16 Function (java.util.function.Function)16 Mockito.verify (org.mockito.Mockito.verify)16