终于找到问题了,原来是.net framework2.0,3.0,3.5的CookieContainer的bug解决方法
2011-07-19 14:14
627 查看
找了 很久都发现不出问题,最后终于发现原来是微软的一个BUG
用HttpWebRequest发送请求,附上了CookieContainer(CookieContainer里面确定已经包含了所有需要的 Cookie),但是当发送请求后某些Cookie并没有发送出去,调试了两天,一直觉得是请求的网站设了什么古怪的限制,使请求老是发送不成功,最后用 SocketSniff抓包发现少发送了几个Cookie(因为这些cookie涉及到几个子域名),检查CookieContainer,里面确实有这 几个Cookie,最后只好反编译HttpWebRequest,在类CookieModule里发现方法OnSendingHeaders的如下代码, 这个是把cookie设置到headers里面的关键地方:
internal static void OnSendingHeaders(HttpWebRequest httpWebRequest) { try { if (httpWebRequest.CookieContainer != null) { string str; httpWebRequest.Headers.RemoveInternal("Cookie"); string cookieHeader = httpWebRequest.CookieContainer.GetCookieHeader(httpWebRequest.Address, out str); if (cookieHeader.Length > 0) { httpWebRequest.Headers["Cookie"] = cookieHeader; } } } catch { } } 问题出在GetCookieHeader这个方法里面,某些Cookie的domain判断错误导致没有附加上去。.Net framework4.0以下的都存在此问题。最后把程序框架调到4.0的,就没有这个问题了。当然4.0以下的框架版本可以用下面的方法处理一下 CookieContainer里面domain。 Don't use .Add(Cookie), Use only .Add(Uri, Cookie) method.
Call BugFix_CookieDomain each time you add a cookie to the container or before you use .GetCookie or before system use the container.
private void BugFix_CookieDomain(CookieContainer cookieContainer)
{
System.Type _ContainerType = typeof(CookieContainer);
Hashtable table = (Hashtable)_ContainerType.InvokeMember("m_domainTable",
System.Reflection.BindingFlags.NonPublic |
System.Reflection.BindingFlags.GetField |
System.Reflection.BindingFlags.Instance,
null,
cookieContainer,
new object[] { });
ArrayList keys = new ArrayList(table.Keys);
foreach (string keyObj in keys)
{
string key = (keyObj as string);
if (key[0] == '.')
{
string newKey = key.Remove(0, 1);
table[newKey] = table[keyObj];
}
}
}
用HttpWebRequest发送请求,附上了CookieContainer(CookieContainer里面确定已经包含了所有需要的 Cookie),但是当发送请求后某些Cookie并没有发送出去,调试了两天,一直觉得是请求的网站设了什么古怪的限制,使请求老是发送不成功,最后用 SocketSniff抓包发现少发送了几个Cookie(因为这些cookie涉及到几个子域名),检查CookieContainer,里面确实有这 几个Cookie,最后只好反编译HttpWebRequest,在类CookieModule里发现方法OnSendingHeaders的如下代码, 这个是把cookie设置到headers里面的关键地方:
internal static void OnSendingHeaders(HttpWebRequest httpWebRequest) { try { if (httpWebRequest.CookieContainer != null) { string str; httpWebRequest.Headers.RemoveInternal("Cookie"); string cookieHeader = httpWebRequest.CookieContainer.GetCookieHeader(httpWebRequest.Address, out str); if (cookieHeader.Length > 0) { httpWebRequest.Headers["Cookie"] = cookieHeader; } } } catch { } } 问题出在GetCookieHeader这个方法里面,某些Cookie的domain判断错误导致没有附加上去。.Net framework4.0以下的都存在此问题。最后把程序框架调到4.0的,就没有这个问题了。当然4.0以下的框架版本可以用下面的方法处理一下 CookieContainer里面domain。 Don't use .Add(Cookie), Use only .Add(Uri, Cookie) method.
Call BugFix_CookieDomain each time you add a cookie to the container or before you use .GetCookie or before system use the container.
private void BugFix_CookieDomain(CookieContainer cookieContainer)
{
System.Type _ContainerType = typeof(CookieContainer);
Hashtable table = (Hashtable)_ContainerType.InvokeMember("m_domainTable",
System.Reflection.BindingFlags.NonPublic |
System.Reflection.BindingFlags.GetField |
System.Reflection.BindingFlags.Instance,
null,
cookieContainer,
new object[] { });
ArrayList keys = new ArrayList(table.Keys);
foreach (string keyObj in keys)
{
string key = (keyObj as string);
if (key[0] == '.')
{
string newKey = key.Remove(0, 1);
table[newKey] = table[keyObj];
}
}
}
相关文章推荐
- .net framework2.0,3.0,3.5的CookieContainer的bug解决方法
- 常常遇到VC下面断点失效的问题,终于找到比较简单靠谱的解决方法了!
- 在连接mysql5.1时正常,连接sql2000时就是连不上,郁闷,终于在网上找到了解答,原来是sql驱动和hibernate的兼容 性问题,现问题已解决,留此文备查.
- ME525+/defy+,不能充满电的问题终于找到了解决的方法,在这里和大家分享一下!!!希望能帮助到大家!!!
- qt 在win8 win10下不能拖拽文件到程序的问题 终于找到答案了 因为把程序的权限设置太高了.解决方法,降低运行权限
- Jsp中存取Cookie的“中文”问题解决方法
- Visual Studio Setup项目“无法在磁盘上找到项‘Microsoft.Net.Framework.3.5.SP1’”的解决方法
- 解决Android中AsyncTask的多线程阻塞问题,android 3.0以后AsyncTask的execute ()方法发生了改变
- Map的keySet方法序列化BUG问题及其解决方法
- 关于二级域名Cookie的问题及解决方法
- 终于解决困扰我多年的问题 浙江绍兴这边 洋拉毛树 树名原来叫 毛白杨 春天种子满天飞
- Mantis Bug Tracker附件丢失和无法上传问题解决方法
- C#网页cookie中文乱码问题解决方法
- Delphi XE8中开发DataSnap程序常见问题和解决方法 (三)用TClientDataSet的“ProviderName”属性连接服务器时,无法找到服务器端的“DatasetProvier”
- unhandled event loop exception eclipse/An error has occurred.See the log file终于找到解决方法了
- 终于找到问题所在了,原来不是程序问题,而是数据质量问题
- 二级域名Cookie问题的解决方法
- 遇到问题时以图形化的界面画出来,理清思路,从中找到解决问题的方法
- 一个work around方法:解决Android 3.0~4.0下WebView 对锚点链接不支持的bug
- Delphi XE8中开发DataSnap程序常见问题和解决方法 (三)用TClientDataSet的“ProviderName”属性连接服务器时,无法找到服务器端的“DatasetProvier”