C#中HttpWebRequest的GetRequestStream執行的效率太低,甚至偶爾死掉

來源:互聯網
上載者:User

【問題】

C#中,提交對應的POST類型http請求之前,會執行:

Stream postDataStream = req.GetRequestStream();

然後填充對應的post資料,再提交http的請求。

但是調試的時候,發現每次執行GetRequestStream都很慢。

慢也就算了,結果最近發現,某次,執行req.GetRequestStream();死掉。

【解決過程】

1.網上找了找,根據 GetRequestStream的效率為什麼這麼低? 的解釋,說是.NET每次會自動搜尋代理,所以很慢,此處沒有設定代理的話,應該直接複製為空白:

req.Proxy = null;

然後再去執行GetRequestStream,這樣就不會慢了。

然後去試了試,好像是這個效果。

2.結果第二天同樣的代碼,去調試,結果GetRequestStream的地方,還是死掉了。

原因暫未知。

3.後來的情況是,同樣的代碼,再次運行,就不死了,雖然也還是有時候效率低,反應慢,但是不會死了。具體根本原因,感覺還是沒有找到。

4. 後來的多次調試,發現對於:

req.Proxy = null;

好像也沒啥效果。

只是碰巧找到了,關於設定proxy為null的原始的官方的解釋:

”C# 3.0 in a Nutshell, Third Edition: A Desktop Quick Reference“的Chapter 14. Networking:

Warning

If you don’t have a proxy, you must set the Proxy property to null on all WebClient and WebRequest objects. Otherwise, the Framework may attempt to "auto-detect" your proxy settings, adding up to 30 seconds to your request. If you’re wondering why your web requests execute slowly, this is probably it!

但是此處,對於我所遇到的,執行GetRequestStream會死掉的問題,還是沒有啥協助。

5.多次調試得到的結果是,如果是對於:

Stream postDataStream = req.GetRequestStream();

是單步調試的話,好像很少會死掉.

而如果直接運行,沒有打斷點,那麼經常容易死掉.

6.參考:GetRequestStream throws Timeout exception randomly,去試了:

?
12345 using (Stream postDataStream = req.GetRequestStream()){    postDataStream.Write(postBytes, 0, postBytes.Length);    postDataStream.Close();}

還是會死掉。

7.網上看到:HttpWebRequest.GetRequestStream() hangs,看起來此問題,好像已經是官方承認的一個bug。

不過即使真的是bug,其解釋說是在.NET 4.0 beta2才解決掉,而我此處無法用.NET 4.0,只能用.NET 2.0/3.0/3.5,所以,如果真是bug的話,那就真的悲劇了。。。

還是先去看看,有沒有其他解決辦法再說吧。

8.試了如下代碼:

?
1234567891011 try{    Stream postDataStream = req.GetRequestStream();     postDataStream.Write(postBytes, 0, postBytes.Length);    postDataStream.Close();}catch (WebException ex){    MessageBox.Show(ex.Message);}

單步調試了:

Stream postDataStream = req.GetRequestStream();

發現經過很長的時間之後,捕獲到了異常WebException ex,出現了“Unable to connect to the remote server”錯誤,其詳細資料如下:

?
123456789101112131415161718192021222324252627282930313233343536 ex  {"Unable to connect to the remote server"}  System.Net.WebExceptionbase    {"Unable to connect to the remote server"}  System.InvalidOperationException {System.Net.WebException}base    {"Unable to connect to the remote server"}  System.SystemException {System.Net.WebException}base    {"Unable to connect to the remote server"}  System.Exception {System.Net.WebException}_className  null    string_data   null    System.Collections.IDictionary_dynamicMethods null    object_exceptionMethod    null    System.Reflection.MethodBase_exceptionMethodString  null    string_helpURL    null    string_HResult    -2146233079 int_innerException {"A connection attempt failed because the connected party did not properly respond after a period of time, or established connection failed because connected host has failed to respond 65.55.254.42:443"} System.Exception {System.Net.Sockets.SocketException}_message    "Unable to connect to the remote server"    string_remoteStackIndex   0   int_remoteStackTraceString null    string_source null    string_stackTrace {sbyte[96]} object {sbyte[]}_stackTraceString   null    string_xcode  -532459699  int_xptrs  0   System.IntPtrData    {System.Collections.ListDictionaryInternal} System.Collections.IDictionary {System.Collections.ListDictionaryInternal}HelpLink    null    stringHResult -2146233079 intInnerException  {"A connection attempt failed because the connected party did not properly respond after a period of time, or established connection failed because connected host has failed to respond 65.55.254.42:443"} System.Exception {System.Net.Sockets.SocketException}IsTransient false   boolMessage "Unable to connect to the remote server"    stringSource  "System"    stringStackTrace  "   at System.Net.HttpWebRequest.GetRequestStream(TransportContext& context)\r\n   at System.Net.HttpWebRequest.GetRequestStream()\r\n   at InsertSkydriveFiles.skydrive.beforeUploadFile()"    stringTargetSite  {System.IO.Stream GetRequestStream(System.Net.TransportContext ByRef)}  System.Reflection.MethodBase {System.Reflection.RuntimeMethodInfo}Static members     InternalStatus  ServicePointFatal   System.Net.WebExceptionInternalStatusm_InternalStatus    ServicePointFatal   System.Net.WebExceptionInternalStatusm_Response  null    System.Net.WebResponsem_Status    ConnectFailure  System.Net.WebExceptionStatusResponse    null    System.Net.WebResponseStatus  ConnectFailure  System.Net.WebExceptionStatus

此處覺得很不能理解的事情是,我只是調用GetRequestStream,獲得request的stream,又不是來自伺服器端的response,為何也要去連結remote server,而不是本地調用一個庫函數,獲得對應的stream???

 

【後記 2012-03-01】

後來發現,好像此問題,和GetResponse偶爾死掉,是同一個原因,然後也解決了這個問題,具體過程和辦法,請參考:

http://www.cnblogs.com/summer_adai/archive/2013/04/26/3045253.html

相關文章

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.