use of reactor.core.Disposable in project reactor-core by reactor.
the class MonoCacheTimeTest method coordinatorCacheInnerDisposedOrNoReferenceNoLeak.
@Test
public void coordinatorCacheInnerDisposedOrNoReferenceNoLeak() throws InterruptedException {
TestPublisher<Integer> source = TestPublisher.create();
MonoCacheTime<Integer> cached = new MonoCacheTime<>(source.mono(), // short cache TTL should trigger state change if source is not never
Duration.ofMillis(100), Schedulers.parallel());
Disposable d1 = cached.subscribe();
cached.subscribe();
WeakReference<Signal<Integer>> refCoordinator = new WeakReference<>(cached.state);
assertThat(refCoordinator.get()).isInstanceOf(MonoCacheTime.CoordinatorSubscriber.class);
Thread.sleep(150);
source = null;
cached = null;
d1.dispose();
System.gc();
assertThat(refCoordinator.get()).isNull();
}
use of reactor.core.Disposable in project reactor-core by reactor.
the class MonoMetricsFuseableTest method subscribeToCancelFuseable.
@Test
public void subscribeToCancelFuseable() throws InterruptedException {
Mono<String> source = Mono.delay(Duration.ofMillis(200)).map(i -> "foo");
Disposable disposable = new MonoMetricsFuseable<>(source).subscribe();
Thread.sleep(100);
disposable.dispose();
Timer stcCompleteTimer = registry.find(REACTOR_DEFAULT_NAME + METER_FLOW_DURATION).tags(Tags.of(TAG_ON_COMPLETE)).timer();
Timer stcErrorTimer = registry.find(REACTOR_DEFAULT_NAME + METER_FLOW_DURATION).tags(Tags.of(TAG_ON_ERROR)).timer();
Timer stcCancelTimer = registry.find(REACTOR_DEFAULT_NAME + METER_FLOW_DURATION).tags(Tags.of(TAG_CANCEL)).timer();
SoftAssertions.assertSoftly(softly -> {
softly.assertThat(stcCompleteTimer).as("subscribe to complete timer").isNull();
softly.assertThat(stcErrorTimer).as("subscribe to error timer is lazily registered").isNull();
softly.assertThat(stcCancelTimer.max(TimeUnit.MILLISECONDS)).as("subscribe to cancel timer").isGreaterThanOrEqualTo(100);
});
}
use of reactor.core.Disposable in project reactor-core by reactor.
the class MonoMetricsTest method subscribeToCancel.
@Test
public void subscribeToCancel() throws InterruptedException {
Mono<Long> source = Mono.delay(Duration.ofMillis(200)).hide();
Disposable disposable = new MonoMetrics<>(source).subscribe();
Thread.sleep(100);
disposable.dispose();
Timer stcCompleteTimer = registry.find(REACTOR_DEFAULT_NAME + METER_FLOW_DURATION).tags(Tags.of(TAG_ON_COMPLETE)).timer();
Timer stcErrorTimer = registry.find(REACTOR_DEFAULT_NAME + METER_FLOW_DURATION).tags(Tags.of(TAG_ON_ERROR)).timer();
Timer stcCancelTimer = registry.find(REACTOR_DEFAULT_NAME + METER_FLOW_DURATION).tags(Tags.of(TAG_CANCEL)).timer();
SoftAssertions.assertSoftly(softly -> {
softly.assertThat(stcCompleteTimer).as("subscribe to complete timer").isNull();
softly.assertThat(stcErrorTimer).as("subscribe to error timer is lazily registered").isNull();
softly.assertThat(stcCancelTimer.max(TimeUnit.MILLISECONDS)).as("subscribe to cancel timer").isGreaterThanOrEqualTo(100);
});
}
use of reactor.core.Disposable in project reactor-core by reactor.
the class ReactorBlockHoundIntegrationTest method shouldNotReportScheduledFutureTask.
@Test
public void shouldNotReportScheduledFutureTask() {
for (int i = 0; i < 1_000; i++) {
Scheduler taskScheduler = Schedulers.newSingle("foo");
try {
Runnable dummyRunnable = () -> {
};
for (int j = 0; j < 257; j++) {
taskScheduler.schedule(dummyRunnable, 200, TimeUnit.MILLISECONDS);
}
Disposable disposable = taskScheduler.schedule(dummyRunnable, 1, TimeUnit.SECONDS);
RaceTestUtils.race(disposable::dispose, disposable::dispose);
} finally {
taskScheduler.dispose();
}
}
}
use of reactor.core.Disposable in project reactor-core by reactor.
the class FluxRefCountGrace method cancel.
void cancel(RefConnection rc) {
boolean replaceTimer = false;
Disposable dispose = null;
Disposable.Swap sd = null;
synchronized (this) {
if (rc.terminated) {
return;
}
long c = rc.subscriberCount - 1;
rc.subscriberCount = c;
if (c != 0L || !rc.connected) {
return;
}
if (!gracePeriod.isZero()) {
sd = Disposables.swap();
rc.timer = sd;
replaceTimer = true;
} else if (rc == connection) {
// emulate what a timeout would do without getting out of sync block
// capture the disposable for later disposal
connection = null;
dispose = RefConnection.SOURCE_DISCONNECTOR.getAndSet(rc, Disposables.disposed());
}
}
if (replaceTimer) {
sd.replace(scheduler.schedule(rc, gracePeriod.toNanos(), TimeUnit.NANOSECONDS));
} else if (dispose != null) {
dispose.dispose();
}
}
Aggregations