RX.Net: Try again but log any exception

I am new to RX and have been learning about error handling and using Retry; I have the following (yes, I know this is not a "real" unit test, but it gives me room for a fiddle !!) and was wondering how I can keep repeating but be able to log any exception?

    [Test]
    public void Test()
    {
        var scheduler = new TestScheduler();

        var source = scheduler.CreateHotObservable(
            new Recorded<Notification<long>>(10000000, Notification.CreateOnNext(0L)),
            new Recorded<Notification<long>>(20000000, Notification.CreateOnNext(1L)),
            new Recorded<Notification<long>>(30000000, Notification.CreateOnNext(2L)),
            new Recorded<Notification<long>>(30000001, Notification.CreateOnError<long>(new Exception("Fail"))),
            new Recorded<Notification<long>>(40000000, Notification.CreateOnNext(3L)),
            new Recorded<Notification<long>>(40000000, Notification.CreateOnCompleted<long>())
        );

        source.Retry().Subscribe(
            l => Console.WriteLine($"OnNext {l}"), 
            exception => Console.WriteLine(exception.ToString()), // Would be logging this in production
            () => Console.WriteLine("OnCompleted"));

       scheduler.Start(
            () => source,
            0,
            TimeSpan.FromSeconds(1).Ticks,
            TimeSpan.FromSeconds(5).Ticks);
    }

      

As a result ...

OnNext 0
OnNext 1
OnNext 2
OnNext 3
OnCompleted

      

... which is exactly what I want to do, other than the fact I would like to log an Exception that occurs between 2 and 3.

Is there a way to allow the subscriber to see the exception in OnError (and log it) and then re-subscribe so that it sees 3?

thank!

+3


source to share


1 answer


You can achieve this with this:

source
    .Do(_ => { }, exception => Console.WriteLine(exception.ToString()), () => {})
    .Retry()
    .Subscribe(
        l => Console.WriteLine($"OnNext {l}"),
        //      exception => Console.WriteLine(exception.ToString()), // Would be logging this in production
        () => Console.WriteLine("OnCompleted")
    );

      

Just to clarify what's going on here: OnError

is the closing signal. If the error reached the subscription, it will terminate the rest of the stream. .Retry

completes the subscription, swallows OnError

, and then re-subscribes, merging the two subscriptions together. For example, look at this:

source
    .StartWith(-1)
    .Retry()
    .Subscribe(
        l => Console.WriteLine($"OnNext {l}"),
        () => Console.WriteLine("OnCompleted")
    );

      

Your result will be



OnNext -1
OnNext 0
OnNext 1
OnNext 2
OnNext -1
OnNext 3
OnCompleted

      

OnNext -1

appears twice because it appears when you subscribe (which Retry

does after OnError

.

Your observable test is a frankly bad test. It breaks down the "Rx Contract", which is that notifications follow the following pattern:

OnNext* (OnCompleted | OnError)? 

      

That is, 0 or more notifications OnNext

followed by optional OnError

or optional OnCompleted

. No notices of any type should follow either OnError

or OnCompleted

.

+4


source







All Articles