C#上传(修改表单数据),下载文件到服务器

        由于项目的需要,需要将文件上传到服务器,并且冲服务器下载文件到客户端,采用的是HTTP协议,有人认为使用FTP协议更简单一些,并且效率更高一些。这里简单描述一些对比二者的一些特点:
        (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


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值