(1)FTP的服务器部署相对来说更麻烦一些,设置权限出问题的话,会产生一系列的安全问题;
(2)如果双方都还有防火墙,又不想开发FTP相关的一些端口时,HTTP就简单一些,就像WEB Services一样能穿透防火墙。
(3)当然HTTP也存在自己本身的缺点,例如HTTP不支持断点续传,大文件上传比较困难,速度比较慢,因此在使用HTTP协议上传文件时要保证上传的文件不要太大。
在上传和下载文件的时候采用的方式很多,这里描述一种相对比较简单的方式,就是通过WebClient和HttpWebRequest来实现下载文件的功能和上传文件的功能。本博客中上传和下载均以Excel为例子。
一、首先是通过WebClient方式来模拟下载文件:
private void download_button_Click(object sender, EventArgs e)
{
WebClient client = new WebClient();
client.Headers.Add("Cookie", GlobalFunction.m_Session);//确认已经在线
string Svr_url = "http://.................. ";
//string post_data_str = "";
//string responseText = GlobalFunction.HttpGet(Svr_url, post_data_str);
SaveFileDialog saveFD = new SaveFileDialog();
saveFD.Filter = "Excel文件(*.xls,*.xlsx)|*.xlsx;*.xls";
saveFD.FileName = "template";
try
{
if (saveFD.ShowDialog() == DialogResult.OK)
{
string localFilePath = saveFD.FileName.ToString(); //获得对话框选定在文件路径
client.DownloadFile(Svr_url, localFilePath);//下载文件到本地
}
MessageBox.Show("下载模板成功", "系统提示", MessageBoxButtons.OK, MessageBoxIcon.None);
}
catch(Exception ex)
{
MessageBox.Show(ex.Message);
}
}
说明:代码中必须使用client.Headers.Add("Cookie",GlobalFunction.m_Session); 方法来确定已经实现通信。这样才能从相应的url地址中下载文件。WebClient方式主要是采用的DownloadFile()方法来下载文件,其必要参数是url和path(要存放文件的地址)。
二、上传文件时,首先要选中文件,其实就是为了获取文件的所属路径。如下代码是获取文件路径:
OpenFileDialog openFileDialog = new OpenFileDialog();
String path;
private void selectFile_button_Click(object sender, EventArgs e)
{
openFileDialog.Title = "请选择导入文件";
openFileDialog.Filter = "Excel文件|*.xlsx";
//openFileDialog.Title = "打开Excel文件";
if (openFileDialog.ShowDialog() == DialogResult.OK)
{
path = openFileDialog.FileName;//通过选择窗口找到文件的路径
}
//Console.WriteLine(path + "00000000000000000000");
}
在获取文件路径path之后,接下来就是上传文件到服务器,采用的是HttpWebRequest来模拟HTTP的POST方式。控制界面如下所示,其中“选择文件”的按钮名为:selectFile_button_Click ,接下就是要提交文件,提交文件时间的按钮名为:submit_button_Click ,方法实现如下所示:
private void submit_button_Click(object sender, EventArgs e)
{
string url = "http://。。。。。。。。。。。。 ";//发送到的页面的地址
FileStream fs = new FileStream(path, System.IO.FileMode.Open, System.IO.FileAccess.Read);
//对进度条的控制
int size = (int)fs.Length;
skinProgressBar1.Maximum = size;
skinProgressBar1.Minimum = 0;
skinProgressBar1.Step = 1;
for (int i = 0; i <= skinProgressBar1.Maximum; i++)
{
skinProgressBar1.PerformStep();
}
//将表格数据写到fileBytes数组中
byte[] fileBytes = new byte[fs.Length];
fs.Read(fileBytes, 0, fileBytes.Length);
fs.Close();
fs.Dispose();
HttpRequestClient httpRequestClient = new HttpRequestClient();
httpRequestClient.SetFieldValue("parentDeptId", "0");//设置表单数据字段,公司的父节点的权限为:0
httpRequestClient.SetFieldValue("companyExcel", "company.xlsx", "application/octet-stream", fileBytes);//设置表单数据字段,companyExcel
string responseText;//无效参数
try
{
bool uploaded = httpRequestClient.Upload(url, out responseText);
MessageBox.Show("上传成功", "系统提示", MessageBoxButtons.OK, MessageBoxIcon.None);
}
catch(Exception ex)
{
MessageBox.Show(ex.Message);
}
}
在提交事件(submit_button_Click)中,主要涉及的两个方法是httpRequestClient.Upload() 和httpRequestClient.SetFieldValue() 。在项目开发过程中将这两个方法单独写在我们自己创建的httpRequestClient类中,便于其他数据管理模块中客户端和服务器的交互操作。其中httpRequestClient.SetFieldValue() 方法主要是设置要提交文件的表单信息,为表单添加新的字段名,字段值,内容类型和字节流等信息。而httpRequestClient.Upload() 方法主要是请求URL,响应请求并上传。该方法中关键的代码是要确认是否通信,确认方式为:webClient.Headers.Add("Cookie", m_Session);//确认是否在线
httpRequestClient类的代码下载地址:http://download.csdn.net/detail/qq_30507287/9610872附:httpRequestClient类的代码:
namespace XXX
{
/// <summary>
/// 创建人:崔洪振
/// 创建时间:2016-08-20
/// 定义一个HttpReauest服务客户端类
/// 作用:自定义一个上传文件的方法,用于上传文件,设置cookie,并且可以手动设置或添加表单数据字段
/// </summary>
public class HttpRequestClient
{
#region //字段
private ArrayList bytesArray;
private Encoding encoding = Encoding.UTF8;
private string boundary = String.Empty;
#endregion
#region //构造方法
public HttpRequestClient()
{
bytesArray = new ArrayList();
string flag = DateTime.Now.Ticks.ToString("x");
boundary = "---------------------------" + flag;
}
#endregion
#region //方法
/// <summary>
/// 上传文件——合并请求数据
/// </summary>
/// <returns></returns>
private byte[] MergeContent()
{
int length = 0;
int readLength = 0;
string endBoundary = "--" + boundary + "--\r\n";
byte[] endBoundaryBytes = encoding.GetBytes(endBoundary);
bytesArray.Add(endBoundaryBytes);
foreach (byte[] b in bytesArray)
{
length += b.Length;
}
byte[] bytes = new byte[length];
foreach (byte[] b in bytesArray)
{
b.CopyTo(bytes, readLength);
readLength += b.Length;
}
return bytes;
}
/// <summary>
/// 上传文件
/// </summary>
/// <param name="requestUrl">请求url</param>
/// <param name="responseText">响应</param>
/// <returns></returns>
public bool Upload(String requestUrl, out String responseText)
{
WebClient webClient = new WebClient();
webClient.Headers.Add("Cookie", GlobalFunction.m_Session);//确认已经在线
webClient.Headers.Add("Content-Type", "multipart/form-data; boundary=" + boundary);
byte[] responseBytes;
byte[] bytes = MergeContent();
try
{
responseBytes = webClient.UploadData(requestUrl, bytes);
responseText = System.Text.Encoding.UTF8.GetString(responseBytes);
return true;
}
catch (WebException ex)
{
Stream responseStream = ex.Response.GetResponseStream();
responseBytes = new byte[ex.Response.ContentLength];
responseStream.Read(responseBytes, 0, responseBytes.Length);
}
responseText = System.Text.Encoding.UTF8.GetString(responseBytes);
return false;
}
/// <summary>
/// 设置表单数据字段
/// </summary>
/// <param name="fieldName">字段名</param>
/// <param name="fieldValue">字段值</param>
/// <returns></returns>
public void SetFieldValue(String fieldName, String fieldValue)
{
string httpRow = "--" + boundary + "\r\nContent-Disposition: form-data; name=\"{0}\"\r\n\r\n{1}\r\n";
string httpRowData = String.Format(httpRow, fieldName, fieldValue);
bytesArray.Add(encoding.GetBytes(httpRowData));
}
/// <summary>
/// 设置表单文件数据
/// </summary>
/// <param name="fieldName">字段名</param>
/// <param name="filename">字段值</param>
/// <param name="contentType">内容内型</param>
/// <param name="fileBytes">文件字节流</param>
/// <returns></returns>
public void SetFieldValue(String fieldName, String filename, String contentType, Byte[] fileBytes)
{
string end = "\r\n";
string httpRow = "--" + boundary + "\r\nContent-Disposition: form-data; name=\"{0}\"; filename=\"{1}\"\r\nContent-Type: {2}\r\n\r\n";
string httpRowData = String.Format(httpRow, fieldName, filename, contentType);
byte[] headerBytes = encoding.GetBytes(httpRowData);
byte[] endBytes = encoding.GetBytes(end);
byte[] fileDataBytes = new byte[headerBytes.Length + fileBytes.Length + endBytes.Length];
headerBytes.CopyTo(fileDataBytes, 0);
fileBytes.CopyTo(fileDataBytes, headerBytes.Length);
endBytes.CopyTo(fileDataBytes, headerBytes.Length + fileBytes.Length);
bytesArray.Add(fileDataBytes);
}
#endregion
}
}
附:本文档下载地址:
http://download.csdn.net/detail/qq_30507287/9610895