求教HttpRequest总是从错误中吸取教训IO

用户名:周金桥
文章数:252
评论数:883
访问量:2346537
注册日期:
阅读量:1297
阅读量:3317
阅读量:583203
阅读量:468256
51CTO推荐博文
&这个需求来自于我最近练手的一个项目,在项目中我需要将一些自己发表的和收藏整理的网文集中到一个地方存放,如果全部采用手工操作工作量大而且繁琐,因此周公决定利用C#来实现。在很多地方都需要验证用户身份才可以进行下一步操作,这就免不了POST请求来登录,在实际过程中发现有些网站登录是HTTPS形式的,在解决过程中遇到了一些小问题,现在跟大家分享。
&通用辅助类
&下面是我编写的一个辅助类,在这个类中采用了HttpWebRequest中发送GET/HTTP/HTTPS请求,因为有的时候需要获取认证信息(如Cookie),所以返回的是HttpWebResponse对象,有了返回的HttpWebResponse实例,可以获取登录过程中返回的会话信息,也可以获取响应流。
&代码如下:
using&S &using&System.Collections.G &using&System.L &using&System.T &using&System.Net.S &using&System.Security.Cryptography.X509C &using&System.DirectoryServices.P &using&System.ServiceModel.S &using&System.N &using&System.IO; &using& &using&System.Text.RegularE &&&&&&&namespace&BaiduCang &{ &&&&&&&&&&&&&&&&&&&&public&class&HttpWebResponseUtility &&&&&{ &&&&&&&&&private&static&readonly&string&DefaultUserAgent&=&&Mozilla/4.0&(&MSIE&6.0;&Windows&NT&5.2;&SV1;&.NET&CLR&1.1.4322;&.NET&CLR&2.0.50727)&; &&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&public&static&HttpWebResponse&CreateGetHttpResponse(string&url,int?&timeout,&string&userAgent,CookieCollection&cookies) &&&&&&&&&{ &&&&&&&&&&&&&if&(string.IsNullOrEmpty(url)) &&&&&&&&&&&&&{ &&&&&&&&&&&&&&&&&throw&new&ArgumentNullException(&url&); &&&&&&&&&&&&&} &&&&&&&&&&&&&HttpWebRequest&request&=&WebRequest.Create(url)&as&HttpWebR &&&&&&&&&&&&&request.Method&=&&GET&; &&&&&&&&&&&&&request.UserAgent&=&DefaultUserA &&&&&&&&&&&&&if&(!string.IsNullOrEmpty(userAgent)) &&&&&&&&&&&&&{ &&&&&&&&&&&&&&&&&request.UserAgent&=&userA &&&&&&&&&&&&&} &&&&&&&&&&&&&if&(timeout.HasValue) &&&&&&&&&&&&&{ &&&&&&&&&&&&&&&&&request.Timeout&=&timeout.V &&&&&&&&&&&&&} &&&&&&&&&&&&&if&(cookies&!=&null) &&&&&&&&&&&&&{ &&&&&&&&&&&&&&&&&request.CookieContainer&=&new&CookieContainer(); &&&&&&&&&&&&&&&&&request.CookieContainer.Add(cookies); &&&&&&&&&&&&&} &&&&&&&&&&&&&return&request.GetResponse()&as&HttpWebR &&&&&&&&&} &&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&public&static&HttpWebResponse&CreatePostHttpResponse(string&url,IDictionary&string,string&&parameters,int?&timeout,&string&userAgent,Encoding&requestEncoding,CookieCollection&cookies) &&&&&&&&&{ &&&&&&&&&&&&&if&(string.IsNullOrEmpty(url)) &&&&&&&&&&&&&{ &&&&&&&&&&&&&&&&&throw&new&ArgumentNullException(&url&); &&&&&&&&&&&&&} &&&&&&&&&&&&&if(requestEncoding==null) &&&&&&&&&&&&&{ &&&&&&&&&&&&&&&&&throw&new&ArgumentNullException(&requestEncoding&); &&&&&&&&&&&&&} &&&&&&&&&&&&&HttpWebRequest&request=null; &&&&&&&&&&&&&&&&&&&&&&&&&&if(url.StartsWith(&https&,StringComparison.OrdinalIgnoreCase)) &&&&&&&&&&&&&{ &&&&&&&&&&&&&&&&&ServicePointManager.ServerCertificateValidationCallback&=&new&RemoteCertificateValidationCallback(CheckValidationResult); &&&&&&&&&&&&&&&&&request&=&WebRequest.Create(url)&as&HttpWebR &&&&&&&&&&&&&&&&&request.ProtocolVersion=HttpVersion.Version10; &&&&&&&&&&&&&} &&&&&&&&&&&&&else&&&&&&&&&&&&&{ &&&&&&&&&&&&&&&&&request&=&WebRequest.Create(url)&as&HttpWebR &&&&&&&&&&&&&} &&&&&&&&&&&&&request.Method&=&&POST&; &&&&&&&&&&&&&request.ContentType&=&&application/x-www-form-urlencoded&; &&&&&&&&&&&&& &&&&&&&&&&&&&if&(!string.IsNullOrEmpty(userAgent)) &&&&&&&&&&&&&{ &&&&&&&&&&&&&&&&&request.UserAgent&=&userA &&&&&&&&&&&&&} &&&&&&&&&&&&&else&&&&&&&&&&&&&{ &&&&&&&&&&&&&&&&&request.UserAgent&=&DefaultUserA &&&&&&&&&&&&&} &&&&&&&&&&&&&&if&(timeout.HasValue) &&&&&&&&&&&&&{ &&&&&&&&&&&&&&&&&request.Timeout&=&timeout.V &&&&&&&&&&&&&} &&&&&&&&&&&&&if&(cookies&!=&null) &&&&&&&&&&&&&{ &&&&&&&&&&&&&&&&&request.CookieContainer&=&new&CookieContainer(); &&&&&&&&&&&&&&&&&request.CookieContainer.Add(cookies); &&&&&&&&&&&&&} &&&&&&&&&&&&&&&&&&&&&&&&&&if(!(parameters==null||parameters.Count==0)) &&&&&&&&&&&&&{ &&&&&&&&&&&&&&&&&StringBuilder&buffer&=&new&StringBuilder(); &&&&&&&&&&&&&&&&&int&i&=&0; &&&&&&&&&&&&&&&&&foreach&(string&key&in&parameters.Keys) &&&&&&&&&&&&&&&&&{ &&&&&&&&&&&&&&&&&&&&&if&(i&&&0) &&&&&&&&&&&&&&&&&&&&&{ &&&&&&&&&&&&&&&&&&&&&&&&&buffer.AppendFormat(&&{0}={1}&,&key,&parameters[key]); &&&&&&&&&&&&&&&&&&&&&} &&&&&&&&&&&&&&&&&&&&&else&&&&&&&&&&&&&&&&&&&&&{ &&&&&&&&&&&&&&&&&&&&&&&&&buffer.AppendFormat(&{0}={1}&,&key,&parameters[key]); &&&&&&&&&&&&&&&&&&&&&} &&&&&&&&&&&&&&&&&&&&&i++; &&&&&&&&&&&&&&&&&} &&&&&&&&&&&&&&&&&byte[]&data&=&requestEncoding.GetBytes(buffer.ToString()); &&&&&&&&&&&&&&&&&using&(Stream&stream&=&request.GetRequestStream()) &&&&&&&&&&&&&&&&&{ &&&&&&&&&&&&&&&&&&&&&stream.Write(data,&0,&data.Length); &&&&&&&&&&&&&&&&&} &&&&&&&&&&&&&} &&&&&&&&&&&&&return&request.GetResponse()&as&HttpWebR &&&&&&&&&} &&&&&&&&&&private&static&bool&CheckValidationResult(object&sender,&X509Certificate&certificate,&X509Chain&chain,&SslPolicyErrors&errors) &&&&&&&&&{ &&&&&&&&&&&&&return&true;&&&&&&&&&&} &&&&&} &}&
&从上面的代码中可以看出POST数据到HTTP和HTTPS站点不同,POST数据到HTTPS站点的时候需要设置ServicePointManager类的ServerCertificateValidationCallback属性,并且在POST到时还需要将HttpWebResquest实例的ProtocolVersion属性设置为HttpVersion.Version10(这个未验证是否所有的HTTPS站点都需要设置),否则在调用GetResponse()方法时会抛出&基础连接已经关闭: 连接被意外关闭。&的异常。
&这个类用起来也很简单:
&(1)POST数据到HTTPS站点,用它来登录百度:
string&loginUrl&=&&/?login&; &string&userName&=&&userName&; &string&password&=&&password&; &string&tagUrl&=&&/&+userName+&/tags&; &Encoding&encoding&=&Encoding.GetEncoding(&gb2312&); &&IDictionary&string,&string&&parameters&=&new&Dictionary&string,&string&(); &parameters.Add(&tpl&,&&fa&); &parameters.Add(&tpl_reg&,&&fa&); &parameters.Add(&u&,&tagUrl); &parameters.Add(&psp_tt&,&&0&); &parameters.Add(&username&,&userName); &parameters.Add(&password&,&password); &parameters.Add(&mem_pass&,&&1&); &HttpWebResponse&response&=&HttpWebResponseUtility.CreatePostHttpResponse(loginUrl,&parameters,&null,&null,&encoding,&null); &string&cookieString&=&response.Headers[&Set-Cookie&];&
&(2)发送GET请求到HTTP站点
&在cookieString中包含了服务器端返回的会话信息数据,从中提取了之后可以设置Cookie下次登录时带上这个Cookie就可以以认证用户的信息,假设我们已经登录成功并且获取了Cookie,那么发送GET请求的代码如下:
string&userName&=&&userName&; &string&tagUrl&=&&/&+userName+&/tags&; &CookieCollection&cookies&=&new&CookieCollection();&response&=&HttpWebResponseUtility.CreateGetHttpResponse(tagUrl,&null,&null,&cookies); &
&(3)发送POST请求到HTTP站点
&以登录51CTO为例:
string&loginUrl&=&&/index.php?s=/Index/doLogin&; &string&userName&=&&userName&; &string&password&=&&password&; &&IDictionary&string,&string&&parameters&=&new&Dictionary&string,&string&(); &parameters.Add(&email&,&userName); &parameters.Add(&passwd&,&password); &&HttpWebResponse&response&=&HttpWebResponseUtility.CreatePostHttpResponse(loginUrl,&parameters,&null,&null,&Encoding.UTF8,&null); &
&在这里说句题外话,CSDN的登录处理是由这个Handler来处理的。
在本文只是讲解了在C#中发送请求到HTTP和HTTPS的用法,分GET/POST两种方式,为减少一些繁琐和机械的编码,周公将其封装为一个类,发送数据之后返回HttpWebResponse对象实例,利用这个实例我们可以获取服务器端返回的Cookie以便用认证用户的身份继续发送请求,或者读取服务器端响应的内容,不过在读取响应内容时要注意响应格式和编码,本来在这个类中还有读取HTML和WML内容的方法(包括服务器使用压缩方式传输的数据),但限于篇幅和其它方面的原因,此处省略掉了。如有机会,在以后的文章中会继续讲述这方面的内容。
&本文出自 “” 博客,请务必保留此出处
了这篇文章
类别:┆阅读(0)┆评论(0)
14:33:11 16:43:21 14:51:16 17:09:23 00:02:13 12:30:58 10:38:13 10:40:42 11:41:40 11:42:08 17:38:50 00:01:59 11:52:25 22:36:43 11:13:26 &&1&
&&页数 ( 1/2 ) &订阅你的位置: >
> 【已解决】Eclipse的java代码出错:The import org.apache cannot be resolved
【问题】Eclipse中,折腾java代码。把之前在android中的代码拿过来使用。结果出现The import org.apache cannot be resolved的错误: 【解决过程】1.这里:和都说到了,让去:project -& Build Path -& Configure Build Path -& Libraries -& Add External Jar’s但是坑爹的却是,没有说,此处的org.apache是属于哪个jar包。2.既然找不到org.apache那么,鉴于我此处,全部都是:import org.apache.http.HttpE
import org.apache.http.HttpR
import org.apache.http.HttpS
import org.apache.http.NameValueP
import org.apache.http.client.ClientProtocolE
import org.apache.http.client.CookieS
//import org.apache.http.client.HttpC
import org.apache.http.client.entity.UrlEncodedFormE
import org.apache.http.client.methods.HttpG
import org.apache.http.client.methods.HttpP
import org.apache.http.client.methods.HttpUriR
import org.apache.http.cookie.C
import org.apache.http.impl.client.BasicCookieS
import org.apache.http.impl.client.DefaultHttpC
//import org.apache.http.impl.cookie.BasicClientC
import org.apache.http.params.HttpP
import org.apache.http.protocol.BasicHttpC
import org.apache.http.protocol.HttpC
import org.apache.http.client.params.ClientPN
import org.apache.http.client.protocol.ClientC
import org.apache.http.util.EntityU即,全都是:org.apache.http那就先去找org.apache.http。3.参考:突然想到,貌似这个:org.apache.http是对应的android里面的,不是标准的java库中的。4.所以,去到别人说的,apache官网中找这个库。搜:download org.apache.http而找到,去下载HttpClient 解压后,得到:httpcomponents-client-4.2.5-bin\httpcomponents-client-4.2.5\lib下面有很多jar:先加进来试试:然后所有的org.apache.http就正常了: 【总结】org.apache,不是标准的java中的库。所以eclipse中,无法自动识别。org.apache下包括了一堆相关的库,此处用到的的是org.apache.http,所以: 需要找到对应的org.apache.http相关的jar包,然后加到当前的项目中。1.到哪里找org.apache.http去apache官网中的:去下载:HttpClient 即可,下载后,解压,可以在:httpcomponents-client-4.2.5-bin\httpcomponents-client-4.2.5\lib中看到对应的各个jar包:commons-codec-1.6.jar commons-logging-1.1.1.jarfluent-hc-4.2.5.jarhttpclient-4.2.5.jarhttpclient-cache-4.2.5.jarhttpcore-4.2.4.jarhttpmime-4.2.5.jar 2.如何把jar加到当前项目详见:转载请注明: & 与本文相关的文章
18 queries in 0.195 seconds, using 9.81MB memory

我要回帖

更多关于 警惕天主教的错误 的文章

 

随机推荐