我正在嘗試使用Reactive Extensions來獲取一堆RSS項目。我基於Tim Greenfield的博客文章:Silverlight Rx DataClient within MVVM。Rx重試()未按預期工作
我在桌面應用程序中使用它,但代碼類似。
我遇到的問題是瞭解Retry()
函數。它似乎沒有做我期望的和我期待的。
var items = new List<RssItem>();
WebHelper.DownloadXmlFileAsync<RssItem>(new Uri(URI), "item")
.Retry(2)
.Finally(PublishResults)
.Subscribe(items.Add, ProcessError,() => ProcessCompleted(items));
當我通過一個有效的URI,這沒有任何問題。當我在URI中輸入拼寫錯誤時,它會通過ProcessError()
函數報告404錯誤,正如人們所期望的那樣,但它只報告一次。我預料它會兩次顯示這個錯誤。
因此,看起來Retry()
函數沒有在我的web請求中運行,但看起來它實際上應用於傳遞給Subscribe()
的函數。雖然我可能在這裏錯了。
如何確保Retry()
調用適用於Web請求?
額外的代碼:
public static class WebHelper
{
public static HttpWebRequest CreateHttp(Uri uri)
{
return CreateHttp(uri, "GET");
}
public static HttpWebRequest CreateHttp(Uri uri, string method)
{
if (uri.Scheme != Uri.UriSchemeHttp && uri.Scheme != Uri.UriSchemeHttps)
{
throw new ArgumentException("The specified URI does not use HTTP or HTTPS.", "uri");
}
var request = (HttpWebRequest)WebRequest.Create(uri);
request.Method = method;
return request;
}
public static IObservable<T> DownloadXmlFileAsync<T>(Uri uri, string elementName) where T : class
{
return (from request in Observable.Return(CreateHttp(uri))
from response in Observable.FromAsyncPattern<WebResponse>(request.BeginGetResponse, request.EndGetResponse)()
let stream = response.GetResponseStream()
where stream != null
from item in XmlReader.Create(stream).GetXmlItem<T>(elementName).ToObservable()
select item);
}
}
public static class XmlExtensions
{
public static IEnumerable<T> GetXmlItem<T>(this XmlReader reader, string elementName) where T : class
{
var serializer = new XmlSerializer(typeof (T));
while (reader.GoToElement(elementName))
{
yield return serializer.Deserialize(reader) as T;
}
}
public static bool GoToElement(this XmlReader reader, string elementName)
{
do
{
if (reader.NodeType == XmlNodeType.Element && reader.Name == elementName)
{
return true;
}
} while (reader.Read());
return false;
}
}
XmlRoot("item")]
public class RssItem
{
[XmlElement("description")]
public string Description { get; set; }
[XmlElement("link")]
public string Link { get; set; }
[XmlElement("pubDate")]
public string PublishDate { get; set; }
[XmlElement("title")]
public string Title { get; set; }
public override string ToString()
{
return string.Format("Title: {0}", Title);
}
}
你的答案提供了一些很好的見解,也讓我有導致http://social.msdn.microsoft.com/Forums/da-DK/rx/thread/96a06e27-9c02-4177一些特定的關鍵字搜索互聯網-ae6a-04b8a7f966e5,這讓我更加了解可觀察工作的方式。 – Jensen
@JensenSomers很高興我能幫上忙。抱歉,關於你的問題的確切原因不是非常具體。有關應用Rx的文檔很少,我希望這些常規答案可能對未來嘗試學習Rx的人有用。 – Asti
如果每個人都會像我一樣對Rx退出,我相信在不久的將來會出現適當的文檔和更大的用例示例。 :-) – Jensen