using System; using System.Collections.Generic; using System.Linq; using System.Text; using System.Net; using System.IO; namespace WpfApplication1 { public static class FormUpload { private static readonly Encoding encoding = Encoding.UTF8; public static HttpWebResponse MultipartFormDataPost(string postUrl, string userAgent, Dictionary<string, object> postParameters) { string formDataBoundary = String.Format("----------{0:N}", Guid.NewGuid()); //string contentType = "multipart/form-data; boundary=" + formDataBoundary; string contentType = "multipart/form-data; boundary=" + formDataBoundary; byte[] formData = GetMultipartFormData(postParameters, formDataBoundary); return PostForm(postUrl, userAgent, contentType, formData); } private static HttpWebResponse PostForm(string postUrl, string userAgent, string contentType, byte[] formData) { HttpWebRequest request = WebRequest.Create(postUrl) as HttpWebRequest; if (request == null) { throw new NullReferenceException("request is not a http request"); } // Set up the request properties. request.Method = "POST"; request.ContentType = contentType; request.UserAgent = userAgent; request.CookieContainer = new CookieContainer(); request.ContentLength = formData.Length; // You could add authentication here as well if needed: // request.PreAuthenticate = true; // request.AuthenticationLevel = System.Net.Security.AuthenticationLevel.MutualAuthRequested; // request.Headers.Add("Authorization", "Basic " + Convert.ToBase64String(System.Text.Encoding.Default.GetBytes("username" + ":" + "password"))); // Send the form data to the request. using (Stream requestStream = request.GetRequestStream()) { requestStream.Write(formData, 0, formData.Length); requestStream.Close(); } return request.GetResponse() as HttpWebResponse; } private static byte[] GetMultipartFormData(Dictionary<string, object> postParameters, string boundary) { Stream formDataStream = new System.IO.MemoryStream(); bool needsCLRF = false; foreach (var param in postParameters) { // Thanks to feedback from commenters, add a CRLF to allow multiple parameters to be added. // Skip it on the first parameter, add it to subsequent parameters. if (needsCLRF) formDataStream.Write(encoding.GetBytes("\r\n"), 0, encoding.GetByteCount("\r\n")); needsCLRF = true; if (param.Value is FileParameter) { FileParameter fileToUpload = (FileParameter)param.Value; // Add just the first part of this param, since we will write the file data directly to the Stream string header = string.Format("--{0}\r\nContent-Disposition: form-data; name=\"{1}\"; filename=\"{2}\"\r\nContent-Type: {3}\r\n\r\n", boundary, param.Key, fileToUpload.FileName ?? param.Key, fileToUpload.ContentType ?? "application/octet-stream"); formDataStream.Write(encoding.GetBytes(header), 0, encoding.GetByteCount(header)); // Write the file data directly to the Stream, rather than serializing it to a string. formDataStream.Write(fileToUpload.File, 0, fileToUpload.File.Length); } else { string postData = string.Format("--{0}\r\nContent-Disposition: form-data; name=\"{1}\"\r\n\r\n{2}", boundary, param.Key, param.Value); formDataStream.Write(encoding.GetBytes(postData), 0, encoding.GetByteCount(postData)); } } // Add the end of the request. Start with a newline string footer = "\r\n--" + boundary + "--\r\n"; formDataStream.Write(encoding.GetBytes(footer), 0, encoding.GetByteCount(footer)); // Dump the Stream into a byte[] formDataStream.Position = 0; byte[] formData = new byte[formDataStream.Length]; formDataStream.Read(formData, 0, formData.Length); formDataStream.Close(); return formData; } public class FileParameter { public byte[] File { get; set; } public string FileName { get; set; } public string ContentType { get; set; } public FileParameter(byte[] file) : this(file, null) { } public FileParameter(byte[] file, string filename) : this(file, filename, null) { } public FileParameter(byte[] file, string filename, string contenttype) { File = file; FileName = filename; ContentType = contenttype; } } } }
使用封装类进行提交
Dictionary<string, object> postParameters = new Dictionary<string, object>(); postParameters.Add("token", "123465789"); //postParameters.Add("paramB", "value2"); //postParameters.Add("paramC", "value3"); byte[] data = ReadImageFile("c:\\123456.png"); postParameters.Add("file1", new FormUpload.FileParameter(data, "123456.png", "image/png")); // Create request and receive response string postURL = "http://localhost:4806/WebApi/V1/Account/ChangeUserCard"; string userAgent = "Someone"; HttpWebResponse webResponse = FormUpload.MultipartFormDataPost(postURL, userAgent, postParameters); // Process response StreamReader responseReader = new StreamReader(webResponse.GetResponseStream()); string fullResponse = responseReader.ReadToEnd(); Console.WriteLine(fullResponse); Console.ReadKey();
服务端接受数据
HttpRequest request = System.Web.HttpContext.Current.Request; string token = request.Form["token"].ToString(); if (request.Files.Count <= 0) //如果file集合的数量小于等于0,则返回错误 return ResponseResult.GenFaildResponse(ResultCode.CodeTypeIsNull); foreach (string str in request.Files) { HttpPostedFile FileSave = request.Files[str]; //用key获取单个文件对象HttpPostedFile string AbsolutePath = "C:\\" + FileSave.FileName; //设置要存储的图片的绝对路径 try { FileSave.SaveAs(AbsolutePath); //将上传的东西保存 } catch { WebAPIHelper.RecordOperationLog("1111","1111"); } }
客户端form表单提交(不带图片参数)
string postData = "user=123&pass=456"; // 要发放的数据 byte[] byteArray = Encoding.UTF8.GetBytes(postData); string url = "http://localhost:4806/WebApi/V1/Account/ChangeUserCard"; //定义发送请求的地址 HttpWebRequest objWebRequest = (HttpWebRequest)WebRequest.Create(url); objWebRequest.Method = "POST"; objWebRequest.ContentType = "application/x-www-form-urlencoded"; objWebRequest.ContentLength = byteArray.Length; Stream newStream = objWebRequest.GetRequestStream(); // Send the data. newStream.Write(byteArray, 0, byteArray.Length); //写入参数 newStream.Close(); HttpWebResponse response = (HttpWebResponse)objWebRequest.GetResponse(); StreamReader sr = new StreamReader(response.GetResponseStream(), Encoding.Default); string textResponse = sr.ReadToEnd(); // 返回的数据
将图片转化为二进制
private static byte[] ReadImageFile(string path) { FileStream fs = File.OpenRead(path); //OpenRead int filelength = 0; filelength = (int)fs.Length; //获得文件长度 Byte[] image = new Byte[filelength]; //建立一个字节数组 fs.Read(image, 0, filelength); //按字节流读取 System.Drawing.Image img = System.Drawing.Image.FromStream(fs); return ImgHelper.ImageToBytes(img); //Console.WriteLine(array.ToString()); //Console.ReadKey(); }
备注:
1、封装类及发请求方法,参考自:http://blog.csdn.net/wangjijun0807/article/details/40053679?locationNum=15
2、服务端接收ResponseResult语句可忽略
3、带图片发送post请求的方法中,对图片的处理方法,放在了最后面