2010-12-10 54 views
1

我剛開始使用System.Reactive並且非常喜歡它的簡單性,但是我遇到了似乎它必須有一個優雅的解決方案的東西,但我沒有創建任何類似於雅緻的解決如何在System.Reactive中管理Webservice超時

這種情況是,我想去第三方Web服務獲取一些信息(在一個單獨的線程中),同時在本地進行搜索。然後合併結果,除非Web服務超時,我將僅從本地結果中獲取信息。

所以我想介紹一個超時可觀察的部分在這裏:

using System; 
using System.Linq; 
using System.Threading; 

namespace ConsoleApplication1 
{ 
    class Program 
    { 
     static void Main(string[] args) 
     { 
      Console.WriteLine("Starting"); 
      var o = Observable.Start(DoSeparateThreadCall); 

      DoCallInThisThread(); 

      o.First(); 

      Console.WriteLine("the End"); 
      Console.ReadLine(); 
     } 

     private static void DoSeparateThreadCall() 
     { 
      Console.WriteLine("Started in separate thread call"); 
      Thread.Sleep(3000); 
      Console.WriteLine("Ended in separate thread call"); 
     } 

     static void DoCallInThisThread() 
     { 
      Console.WriteLine("Started in this thread call"); 
      Thread.Sleep(2000); 
      Console.WriteLine("Ended in this thread call"); 
     } 
    } 
} 

任何人做過類似的事情?這似乎是一個相當普遍的事情,即如果第三方電話超時做X?

回答

4

無論你想如何要超時發生器(Rx控制或客戶代理),你可能想使用Catch

public IObservable<IList<SearchResult>> GetSearchResults() 
{ 
    return Observable.ForkJoin(
     GetRemoteSearchResults(), 
     GetLocalSearchResults() 
     ) 
     .Select(MergeSearchResults); 
} 

private IObservable<IList<SearchResult>> GetRemoteSearchResults() 
{ 
    return GetSearchResultsFromWebService() 
     .Timeout(RemoteTimeOut) 
     .Catch<IList<SearchResult>, TimeoutException>(
      Observable.Return((IList<SearchResult>)new List<SearchResult>()) 
     ); 
} 

private IObservable<IList<SearchResult>> MergeSearchResults(
    IList<SearchResult>[] allResults) 
{ 
    var localResults = allResults[0]; 
    var remoteResults = allResults[1]; 

    if (remoteResults.Count == 0) 
    { 
     return localResults; 
    } 
    else 
    { 
     var mergedResults = new List<SearchResult>(); 
     // merge 

     return mergedResults; 
    } 
} 

如果你想使用你的Web服務的超時,只捕獲了異常改爲輸入。

+0

謝謝理查德,看起來像一個很好的解決方案。我明天早上會檢查一下! – ArtificialGold 2010-12-12 21:02:59

+1

沒問題。我只注意到你正在使用.NET 3.5,所以沒有協變。爲了解決這個問題,我在'Observable.Return'調用中添加了一個表演。 – 2010-12-12 21:12:11