这种方法类似浏览器传统的表单提交方式 application/x-www-form-urlencoded,可用到两种组合数据的方法,一是直接传递数据到 data 对象,二是组合键/值对类型的数据到 parameters 对象,方法内会优先选择 data 对象所带的参数,如果想要以键/值对的方式传递,将 data 对象的值填为空字符串即可,这两个二选一;获取返回值的方法中加入了异常处理,这使得即使在遇到请求服务器发生服务器错误(如 404 等 HTTP 状态)时也可正常获得返回的异常信息:
using System;
using System.Net;
using System.Text;
using System.IO;
using System.Collections.Generic;
public string HttpPost(string url, string data = "", IDictionary<string, string> parameters = null, int timeout = 5000, CookieCollection cookies = null)
{
HttpWebRequest request = null;
request = WebRequest.Create(url) as HttpWebRequest;
request.Method = "POST";
request.ContentType = "application/x-www-form-urlencoded";
request.Timeout = timeout;
if (cookies != null)
{
request.CookieContainer = new CookieContainer();
request.CookieContainer.Add(cookies);
}
if (!string.IsNullOrWhiteSpace(data))
{
byte[] databytes = Encoding.UTF8.GetBytes(data);
using (Stream stream = request.GetRequestStream())
{
stream.Write(databytes, 0, databytes.Length);
}
}
else 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[] kvdata = Encoding.UTF8.GetBytes(buffer.ToString());
using (Stream stream = request.GetRequestStream())
{
stream.Write(kvdata, 0, kvdata.Length);
}
}
try
{
using (Stream stream = request.GetResponse().GetResponseStream())
{
using (StreamReader reader = new StreamReader(stream, Encoding.UTF8))
{
return reader.ReadToEnd();
}
}
}
catch (WebException ex)
{
using (Stream stream = ex.Response.GetResponseStream())
{
using (StreamReader reader = new StreamReader(stream, Encoding.UTF8))
{
return reader.ReadToEnd();
}
}
}
}
注意这里面的 Timeout 属性并不是指的整个请求时间,似乎指的是请求方回应请求的时间,比如第一次响应,此方法能够很好地传递普通参数,但对于传输大数据、文件等却很无力。