最近的一个项目用到了.net 的HttpWebRequest,下面的文章解决了我遇到的问题。特此转载。
本文来自:http://blog.xuite.net/mslin1222/blog/20672243
---------------------------------------------------
最近改寫一支小程式關於C#程式要建立一個HTTP 連線 ,而
C#程式要建立一個HTTP 連線 因此一定會有底下這行程式碼
HttpWebRequest objRequest = (HttpWebRequest)WebRequest.Create(http://blog.xuite.com.tw);
........
.....
但是執行後卻發生超詭異的現象,就是出現底下錯誤訊息
遠端伺服器傳回一個錯誤: (403) 禁止。Auth Error
但是用IE 瀏覽器直接輸入網址http://blog.xuite.com.tw 去連 又一切正常,屢試不爽怪哉怪哉,又不是農曆七月。
後來生氣了透過抓網路封包的工具看就究竟,這裡真的要感謝Ethereal 軟體(現在變成wireshark) 確定一下封包的流向!!不看還好 一看就發現問題所在了
由Ethereal 的畫面得知程式並沒有去跟blog.xuite.net的IP 210.242.17.198 連線
倒是去跟一個很詭異的IP連線(這IP 從來沒看過)
且明明nslookup blog.xuite.net
得到的結果IP如下: 也是210.242.17.198
Non-authoritative answer:
Name: blog.xuite.net
Address: 210.242.17.198
而電腦裡的etc 檔也沒有額外設定
但是程式連結到的IP 卻是一個詭異!! 不是連到210.242.17.198
想破頭的觀察與仔細思考後都已經快要投降了 其中還找了一位博士與碩士前來解釋這怪異的現象....
最後才發現這個IP 是Proxy Server
怪了!
難道C# HttpWebRequest 程式會主動參考IE 裡面的Proxy 設定??
經過實驗!! 沒錯確實會參考
The Proxy property identifies the WebProxy object to use to process requests to Internet resources. To specify that no proxy should be used, set the Proxy property to the proxy instance returned by the GlobalProxySelection..::.GetEmptyWebProxy method.
The local computer or application config file may specify that a default proxy be used. If the Proxy property is specified, then the proxy settings from the Proxy property override the local computer or application config file and the HttpWebRequest instance will use the proxy settings specified. If no proxy is specified in a config file and the Proxy property is unspecified, the HttpWebRequest class uses the proxy settings inherited from Internet Explorer on the local computer. If there are no proxy settings in Internet Explorer, the request is sent directly to the server.
The HttpWebRequest class parses a proxy bypass list with wildcard characters inherited from Internet Explorer differently than the bypass list is parsed directly by Internet Explorer. For example, the HttpWebRequest class will parse a bypass list of "nt*" from Internet Explorer as a regular expression of "nt.$". This differs from the native behavior of Internet Explorer. So a URL of "http://intxxxxx" would bypass the proxy using the HttpWebRequest class, but would not bypass the proxy using Internet Explorer.
Changing the Proxy property after the request has been started by calling the GetRequestStream, BeginGetRequestStream, GetResponse, or BeginGetResponse method throws an InvalidOperationException. For information on the proxy element see
Proxy 屬性會識別用來處理網際網路資源要求的 WebProxy 物件。若要指定不使用任何 Proxy,請將 Proxy 屬性設定為 GlobalProxySelection..::.GetEmptyWebProxy 方法所傳回的 Proxy 執行個體。
本機電腦或應用程式組態檔可能會指定使用預設 Proxy。如果是指定 Proxy 屬性,Proxy 屬性中的 Proxy 屬性便會覆寫本機電腦或應用程式組態檔,而且 HttpWebRequest 執行個體將使用指定的 Proxy 設定。如果未在組態檔中指定 Proxy,而且也未指定 Proxy 屬性,HttpWebRequest 類別便會使用繼承自本機電腦之 Internet Explorer 的 Proxy 設定。如果未在 Internet Explorer 中設定 Proxy,要求便會直接傳送至伺服器。
HttpWebRequest 類別會以繼承自 Internet Explorer 的萬用字元來剖析 Proxy 略過清單,不同於由 Internet Explorer 直接剖析的略過清單。例如,HttpWebRequest 類別會將 Internet Explorer 的 "nt*" 略過清單剖析為 "nt.$" 規則運算式。這種行為不同於 Internet Explorer 的原生行為。因此 "http://intxxxxx" 這個 URL 會略過使用 HttpWebRequest 類別的 Proxy,卻不會略過使用 Internet Explorer 的 Proxy。
所以就中獎摟!!
因此寫了一段程式來驗證一下是不是有參考IE Proxy
IWebProxy proxy = objRequest.Proxy;
// Print the Proxy Url to the console.
if (proxy != null)
{
Console.WriteLine("Proxy: {0}", proxy.GetProxy(objRequest.RequestUri));
}
else
{
Console.WriteLine("Proxy is null; no proxy will be used");
}
結果確實把IE 裡面設定的Proxy 抓出來!!且程式確實會參考此Proxy,因此程式未來如果要透過Proxy上網應該只要把IE Proxy設定好就好
不用再透過程式HttpWebRequest.Proxy 屬性
objRequest.Proxy = new WebProxy( "your_proxy", "port");
但是如果我的程式不要被這IE 裡面設定的Proxy 打亂呢??
該怎麼辦??
還好Automatic Proxy Detection 這裡就有答案了!!!原來只要在程式裡面宣告request.Proxy = null;
就可以了
因此最後的程式就會變成
HttpWebRequest objRequest = (HttpWebRequest)WebRequest.Create(http://blog.xuite.com.tw);
objRequest.Proxy = null;
....
...
這樣程式就不會被IE Proxy 所影響摟!! 以上血淚分享的資訊供大家參考