ReactiveObjC icon indicating copy to clipboard operation
ReactiveObjC copied to clipboard

a delayed signal may not enter subscribeNext block!!!

Open leirenbaobao opened this issue 7 years ago • 1 comments

Recently, we found and proved a bug when use rac delay method in OC version. a delayed signal may not enter subscribeNext block, which cause great effect on followed up process.

As we can see from the source code, a delayed signal's "subcribeNext" and "completed" block was setted in RACQueueScheduler, which supported by GCD.

void (^schedule)(dispatch_block_t) = ^(dispatch_block_t block) {
			RACScheduler *delayScheduler = RACScheduler.currentScheduler ?: scheduler;
			RACDisposable *schedulerDisposable = [delayScheduler afterDelay:interval schedule:block];
			[disposable addDisposable:schedulerDisposable];
		};

		RACDisposable *subscriptionDisposable = [self subscribeNext:^(id x) {
			schedule(^{
				[subscriber sendNext:x];
			});
		} error:^(NSError *error) {
			[subscriber sendError:error];
		} completed:^{
			schedule(^{
				[subscriber sendCompleted];
			});
		}];

In "RACQueueScheduler.m Line:80", we could see clearly that dispatch_after realizes the delay function:

dispatch_after([self.class wallTimeWithDate:date], self.queue, ^{
	if (disposable.disposed) return;
	[self performAsCurrentScheduler:block];
});

The problem is, when delayed taskes are handled by dispatch_after, the GCD can not dispatch these taskes serially. which causing a delayed signal completed firstly and without enter subcribeNext.

we can prove it by code blow:

for (NSInteger i = 0; i < 10000; i++) {
        dispatch_after([self wallTimeWithDate:[NSDate dateWithTimeIntervalSinceNow:0.0]], dispatch_get_main_queue(), ^{
        NSLog(@"index = %@", @(i));
    });
}

from console Log: index is not progressive increasing.

One more thing, if give up the dispatch_walltime paramter in dispatch_after, using dispatch_time instead, it will work normally.

Hope it will fix soon.

Best wishes.

leirenbaobao avatar Oct 29 '17 14:10 leirenbaobao

How large is the delay interval?

andersio avatar Oct 30 '17 05:10 andersio