我遇到需要从方法返回IObservable<T>
的情况。只要它发生了变化,就会返回对象T
的新值。
对象已更改的触发器将来自actor系统,在我的示例中,我们使用的是Proto.Actor。
我已经为#34; work&#34;做了一个例子,但是我觉得它没有正确实现IObservable
并且不允许正确取消订阅等。
我的解决方案:
public IObservable<T> Watch<T>(long id)
{
var subscriber = _actorFactory.GetActor<ObjectChangedActor>();
var request = new ObjectWatchRequest(id);
return Observable.Create<T>(async (observer, cancellationToken) =>
{
await Task.Run(async () =>
{
while (true)
{
var response = await subscriber.RequestAsync<ObjectUpdatedResponse>(request, cancellationToken);
// once it gets past the above line, we have gotten notice that the object has been updated
var updatedObj = await Get<T>(id);
observer.OnNext(updatedObj);
}
}, cancellationToken);
// will this ever be called?
return Disposable.Create(() =>
{
Console.WriteLine("Disposal called");
});
});
}
我觉得,尽管它&#34;工作&#34;因为所有更新都被推送到订阅者,所以它永远无法准确处理,并且我不觉得while (true)
应该被放入代码中,即使它是在一个单独的线程上。 / p>
我如何才能最好地处理从演员系统返回的消息列表,并将其转换为用户可以处理的IObservable
(取消订阅)?
答案 0 :(得分:2)
您尚未提供代码的完整工作示例,这使您难以为您提供可以复制和粘贴的工作解决方案。但是,我已经制作了一个我认为你可以使用的简化版本。
你是对的,你的解决方案不是一个好的实现。
这是您的代码的基本版本,一旦您将对象放入其中就应该正常工作:
public IObservable<T> Watch<T>(long id)
{
return
Observable
.Defer(() =>
from x in Observable.FromAsync(() => RequestAsync())
from y in Observable.FromAsync(() => Get<T>(id))
select y)
.Repeat();
}
请告诉我这是否适合您。