2014-03-01 111 views
0

我試圖從異步HttpWebRequest中捕獲WebException以從soap讀取soap:fault。但它會拋出AggregateException。有沒有辦法趕上WebException的異步HttpWebRequestAsync HttpWebRequest catch WebException

public async Task<XDocument> GetXmlSoapResponseAsync(string soapRequestURL, string xmlData) 
    { 
     try 
     { 
     //create xml doc 
     XmlDocument doc = new XmlDocument(); 

     //load xml document frtom xmlData 
     doc.LoadXml(xmlData); 
     //creta web request 
     HttpWebRequest req = (HttpWebRequest)WebRequest.Create(soapRequestURL); 
     req.ContentType = "text/xml"; 
     req.Accept = "text/xml"; 
     req.Method = "POST"; 

     //GetRequestStream from req 
     Stream stm = req.GetRequestStream(); 
     doc.Save(stm); 
     stm.Close(); 

     Task<WebResponse> task = Task.Factory.FromAsync(
     req.BeginGetResponse, 
     asyncResult => req.EndGetResponse(asyncResult), 
     (object)null); 

     var response = task.Result; 
     return await task.ContinueWith(t => ReadStreamFromResponse(response,stm, soapRequestURL,xmlData)); 
     } 
     catch (WebException webException) 
     { 
     LogWebException(webException, soapRequestURL, xmlData); 

     return null; 
     } 

    } 

回答

3

更改此

var response = task.Result; 

這個

var response = await task; 

await返回任務的結果解開了AggregateException,如果有的話。


此外,.Result阻止當前線程,直到結果可用,而這可能不是你想要的東西,否則你只是使用阻塞GetResponse,而不是異步BeginGetResponseEndGetResponse

,你甚至不需要這兩種方法。有一個更好的 - GetResponseAsync

使用此:

var response = await req.GetResponseAsync(); 

取而代之的是:

Task<WebResponse> task = Task.Factory.FromAsync(
req.BeginGetResponse, 
asyncResult => req.EndGetResponse(asyncResult), 
(object)null); 

var response = task.Result; 
+0

感謝快速完美的答案,並與優化我的代碼等待req.GetResponseAsync();.我對這個異步的東西很陌生,我必須閱讀更多才能正確理解它。非常感謝! – sanjeev

+1

@sanjeev沒問題。 「BeginXX」和「EndXX」方法對是[APM-異步編程模型]的一部分(http://msdn.microsoft.com/zh-cn/library/ms228963(v = vs.110).aspx ),它們在.NET 4.5之前非常有用。現在,隨着異步/等待的引入,在大多數情況下,你最好使用'XXAsync'對應。 – dcastro

+0

好的,謝謝dcastro! – sanjeev