C# 中使用System.Net.Http.HttpClient 模拟登陆博客园 (GET/POST)

1、 System.Net.Http .HttpClient简介

System.Net.Http 是微软.net4.5中推出的HTTP 应用程序的编程接口, 微软称之为“现代化的 HTTP 编程接口”, 主要提供以下内容:html

1. 用户经过 HTTP 使用现代化的 Web Service 的客户端组件;apache

2. 可以同时在客户端与服务端同时使用的 HTTP 组件(好比处理 HTTP 标头和消息), 为客户端和服务端提供一致的编程模型。编程

我的看来是抄袭 apache http client ,目前网上用的人好像很少, 我的认为使用httpclient最大的好处是:不用本身管理cookie,只要负责写好请求便可。 api

因为网上资料很少,这里借登陆博客园网站作个简单的总结其get和post请求的用法。浏览器

查看微软的api能够发现其属性方法: http://msdn.microsoft.com/zh-cn/library/system.net.http.httpclient.aspx cookie

由其api能够看出若是想 设置请求头 只须要在 DefaultRequestHeaders 里进行设置 框架

建立httpcliet能够直接new HttpClient() 函数

发送请求 能够按发送方式分别调用其方法,如 get调用 GetAsync(Uri) , post调用 PostAsync(Uri, HttpContent) ,其它依此类推。。。 post

2、实例(模拟post登陆博客园)

首先,须要说明的是, 本实例环境是win7 64位+vs 2013+ .net 4.5框架。 网站

1.使用vs2013新建一个控制台程序,或者窗体程序,以下图所示:

2.必须引入System.Net.Http框架,不然将不能使用httpclient

3.实现代码

using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Net.Http;
using System.Text;
using System.Text.RegularExpressions;
using System.Threading.Tasks;

namespace ClassLibrary1
{
 public class Class1
 {
  private static String dir = @"C:\work\";

  /// <summary>
    /// 写文件到本地
  /// </summary>
    /// <param name="fileName"></param>
    /// <param name="html"></param>
    public static void Write(string fileName, string html)
  {
   try
   {
    FileStream fs = new FileStream(dir + fileName, FileMode.Create);
    StreamWriter sw = new StreamWriter(fs, Encoding.Default);
    sw.Write(html);
    sw.Close();
    fs.Close();

   }catch(Exception ex){
    Console.WriteLine(ex.StackTrace);
   }
     
  }

  /// <summary>
    /// 写文件到本地
  /// </summary>
    /// <param name="fileName"></param>
    /// <param name="html"></param>
    public static void Write(string fileName, byte[] html)
  {
   try
   {
    File.WriteAllBytes(dir + fileName, html);
   }
   catch (Exception ex)
   {
    Console.WriteLine(ex.StackTrace);
   }
   
  }

  /// <summary>
    /// 登陆博客园
  /// </summary>
    public static void LoginCnblogs()
  {
   HttpClient httpClient = new HttpClient();
   httpClient.MaxResponseContentBufferSize = 256000;
   httpClient.DefaultRequestHeaders.Add("user-agent", "Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/36.0.1985.143 Safari/537.36");
   String url = "http://passport.cnblogs.com/login.aspx";
   HttpResponseMessage response = httpClient.GetAsync(new Uri(url)).Result;
   String result = response.Content.ReadAsStringAsync().Result;

   String username = "hi_amos";
   String password = "密码";

   do
   {
    String __EVENTVALIDATION = new Regex("id=\"__EVENTVALIDATION\" value=\"(.*?)\"").Match(result).Groups[1].Value;
    String __VIEWSTATE = new Regex("id=\"__VIEWSTATE\" value=\"(.*?)\"").Match(result).Groups[1].Value;
    String LBD_VCID_c_login_logincaptcha = new Regex("id=\"LBD_VCID_c_login_logincaptcha\" value=\"(.*?)\"").Match(result).Groups[1].Value;

    //图片验证码
        url = "http://passport.cnblogs.com" + new Regex("id=\"c_login_logincaptcha_CaptchaImage\" src=\"(.*?)\"").Match(result).Groups[1].Value;
    response = httpClient.GetAsync(new Uri(url)).Result;
    Write("amosli.png", response.Content.ReadAsByteArrayAsync().Result);
    
    Console.WriteLine("输入图片验证码:");
    String imgCode = "wupve";//验证码写到本地了,须要手动填写
        imgCode =  Console.ReadLine();

    //开始登陆
        url = "http://passport.cnblogs.com/login.aspx";
    List<KeyValuePair<String, String>> paramList = new List<KeyValuePair<String, String>>();
    paramList.Add(new KeyValuePair<string, string>("__EVENTTARGET", ""));
    paramList.Add(new KeyValuePair<string, string>("__EVENTARGUMENT", ""));
    paramList.Add(new KeyValuePair<string, string>("__VIEWSTATE", __VIEWSTATE));
    paramList.Add(new KeyValuePair<string, string>("__EVENTVALIDATION", __EVENTVALIDATION));
    paramList.Add(new KeyValuePair<string, string>("tbUserName", username));
    paramList.Add(new KeyValuePair<string, string>("tbPassword", password));
    paramList.Add(new KeyValuePair<string, string>("LBD_VCID_c_login_logincaptcha", LBD_VCID_c_login_logincaptcha));
    paramList.Add(new KeyValuePair<string, string>("LBD_BackWorkaround_c_login_logincaptcha", "1"));
    paramList.Add(new KeyValuePair<string, string>("CaptchaCodeTextBox", imgCode));
    paramList.Add(new KeyValuePair<string, string>("btnLogin", "登 录"));
    paramList.Add(new KeyValuePair<string, string>("txtReturnUrl", "http://home.cnblogs.com/"));
    response = httpClient.PostAsync(new Uri(url), new FormUrlEncodedContent(paramList)).Result;
    result = response.Content.ReadAsStringAsync().Result;
    Write("myCnblogs.html",result);
   } while (result.Contains("验证码错误,麻烦您从新输入"));

   Console.WriteLine("登陆成功!");
   
   //用完要记得释放
   httpClient.Dispose();
  }

  public static void Main()
  {
     LoginCnblogs();
  }

}

代码分析:

首先,从Main函数开始,调用LoginCnblogs方法;

其次,使用GET方法:

HttpResponseMessage response = httpClient.GetAsync(new Uri(url)).Result;
 String result = response.Content.ReadAsStringAsync().Result;

再者,使用POST方法:

  List<KeyValuePair<String, String>> paramList = new List<KeyValuePair<String, String>>(); paramList.Add(new KeyValuePair<string, string>("__EVENTTARGET", ""));
  ....
                response = httpClient.PostAsync(new Uri(url), new FormUrlEncodedContent(paramList)).Result;
                result = response.Content.ReadAsStringAsync().Result;

最后, 注意其返回值能够是string,也能够是byte[],和stream的方式,这里看你须要什么吧。

4.登陆成功后的截图

1).使用浏览器登陆后的截图:

2).使用Httpcliet登陆后的截图:

总结,能够发现C#中HttpClient的用法和Java中很是类似,因此,说其抄袭确实不为过。

相关文章
相关标签/搜索