让我们假设我们具有可观察到的序列(Rx(和匹配订阅:
var behaviorSubject = new BehaviorSubject<int>(3);
var sequence = behaviorSubject.Select(x => this.webservice.Call(x)).Switch();
var subscription = this.sequence.Subscribe(this.Subject.OnNext, this.OnSequenceFaulted);
序列旨在每次behaviorSubject
发出新值时,在取消以前的请求时进行Web服务调用。如果在网络服务呼叫期间发生异常,则将终止订阅(调用OnSequenceFaulted
方法之后(。
实现这样的OnSequenceFaulted
方法是一个好习惯吗?鉴于异常起源于sequence
内的可观察到的异常,我们是否需要重新启动(重新分配sequence
和订阅(?是否需要明确处理故障的订阅?
public void OnSequenceFaulted(Exception e)
{
subscription?.Dispose();
subscription = sequence.Subscribe(this.Subject.OnNext, this.OnSequenceFaulted);
}
就好的实践而言,这实际上取决于您的用例,以及如果WebService.call抛出异常。
虽然在RX附近解决问题的特定部分,但这里有一些很好的参考可观察的可观察订阅处置
如果可观察到的完成 - on completed或onerror-- 然后订阅已经为您处置。
Introtorx在这里有很好的描述,描述了各种错误处理技术以及您的方案中可能适用的内容
http://www.introtorx.com/content/v1.0.10621.0/11_advancederrorhandling.html
至于如何处理您的特定方案,有一些选择,这里只是几个想法
-
您可以在WebCall本身上处理异常,以免它过渡到OnErrorhttp://www.introtorx.com/content/v1.0.10621.0/11_advancederrorhandling.html#catchswallowingexception
var sequence = behaviorSubject.Select(x => this.webservice.Call(x) .Catch((Exception exc) => //do something with exception, //maybe just return an empty observable and log the exception ).Switch();
-
您也可以告诉它重试http://www.introtorx.com/content/v1.0.10621.0/11_advancederrhandling.html#retry
var subscription = this.sequence.Retry().Subscribe(this.Subject.OnNext, this.OnSequenceFaulted);
实际上没有特定的RX最佳实践AFAIK。如果发生异常,这实际上只是您想发生的事情。如果您根本不在乎,只是希望它能继续生存,那么重试就可以了。如果您想捕获和日志,则可以将捕获量放在Web服务调用中。如果您想检查异常,然后有不同的例外,导致不同的出现,则可以在Web服务呼叫上放置不同的捕获量。