1.upload.js
// 实例化 uploader = WebUploader.create({ pick: { id: '#filePicker', label: '点击选择图片' }, formData: { uid: 123 }, dnd: '#dndArea', paste: '#uploader', swf: 'Scripts/Uploader.swf', chunked: true, //分片处理大文件 chunkSize: 2 * 1024 * 1024, server: 'http://localhost:54987/Modules/Test/fileupload.ashx', //server:'fileupload2.ashx', disableGlobalDnd: true, threads: 1, //上传并发数 //由于Http的无状态特征,在往服务器发送数据过程传递一个进入当前页面是生成的GUID作为标示 formData: { guid: GUID }, fileNumLimit: 300, compress: false, //图片在上传前不进行压缩 fileSizeLimit: 200 * 1024 * 1024, // 200 M fileSingleSizeLimit: 50 * 1024 * 1024 // 50 M });
uploader.on("uploadBeforeSend", function (obj, data, headers) { _.extend(headers, { "Origin": "http://localhost:3504", "Access-Control-Request-Method": "POST" }); });
// 文件上传成功,合并文件。 uploader.on('uploadSuccess', function (file, response) { if (response.chunked) { $.post("http://localhost:54987/Modules/Test/MergeFiles.ashx", { guid: GUID, fileExt: response.f_ext }, function (data) { data = $.parseJSON(data); if (data.hasError) { alert('文件合并失败!'); } else { //alert(decodeURIComponent(data.savePath)); } }); } });
2.把 fileupload.ashx MergeFiles(合并) 文件放到另一个项目中
//如果进行了分片 if (context.Request.Form.AllKeys.Any(m => m == "chunk")) { //取得chunk和chunks int chunk = Convert.ToInt32(context.Request.Form["chunk"]);//当前分片在上传分片中的顺序(从0开始) int chunks = Convert.ToInt32(context.Request.Form["chunks"]);//总分片数 //根据GUID创建用该GUID命名的临时文件夹 string folder = context.Server.MapPath("~/1/" + context.Request["guid"] + "/"); string path = folder + chunk; //建立临时传输文件夹 if (!Directory.Exists(Path.GetDirectoryName(folder))) { Directory.CreateDirectory(folder); } FileStream addFile = new FileStream(path, FileMode.Append, FileAccess.Write); BinaryWriter AddWriter = new BinaryWriter(addFile); //获得上传的分片数据流 HttpPostedFile file = context.Request.Files[0]; Stream stream = file.InputStream; BinaryReader TempReader = new BinaryReader(stream); //将上传的分片追加到临时文件末尾 AddWriter.Write(TempReader.ReadBytes((int)stream.Length)); //关闭BinaryReader文件阅读器 TempReader.Close(); stream.Close(); AddWriter.Close(); addFile.Close(); TempReader.Dispose(); stream.Dispose(); AddWriter.Dispose(); addFile.Dispose(); context.Response.Write("{\"chunked\" : true, \"hasError\" : false, \"f_ext\" : \"" + Path.GetExtension(file.FileName) + "\"}"); } else//没有分片直接保存 { //根据GUID创建用该GUID命名的临时文件夹 string folder = context.Server.MapPath("~/1/"); //建立临时传输文件夹 if (!Directory.Exists(Path.GetDirectoryName(folder))) { Directory.CreateDirectory(folder); } context.Request.Files[0].SaveAs(context.Server.MapPath("~/1/" + DateTime.Now.ToFileTime() + Path.GetExtension(context.Request.Files[0].FileName))); context.Response.Write("{\"chunked\" : false, \"hasError\" : false}"); }
public class MergeFiles : IHttpHandler { public void ProcessRequest(HttpContext context) { context.Response.ContentType = "text/plain"; string guid = context.Request["guid"]; string fileExt = context.Request["fileExt"]; string root = context.Server.MapPath("~/1/"); string sourcePath = Path.Combine(root,guid + "/");//源数据文件夹 string targetPath = Path.Combine(root, Guid.NewGuid() + fileExt);//合并后的文件 DirectoryInfo dicInfo = new DirectoryInfo(sourcePath); if (Directory.Exists(Path.GetDirectoryName(sourcePath))) { FileInfo[] files = dicInfo.GetFiles(); foreach (FileInfo file in files.OrderBy(f => int.Parse(f.Name))) { FileStream addFile = new FileStream(targetPath, FileMode.Append, FileAccess.Write); BinaryWriter AddWriter = new BinaryWriter(addFile); //获得上传的分片数据流 Stream stream = file.Open(FileMode.Open); BinaryReader TempReader = new BinaryReader(stream); //将上传的分片追加到临时文件末尾 AddWriter.Write(TempReader.ReadBytes((int)stream.Length)); //关闭BinaryReader文件阅读器 TempReader.Close(); stream.Close(); AddWriter.Close(); addFile.Close(); TempReader.Dispose(); stream.Dispose(); AddWriter.Dispose(); addFile.Dispose(); } DeleteFolder(sourcePath); context.Response.Write("{\"chunked\" : true, \"hasError\" : false, \"savePath\" :\"" + System.Web.HttpUtility.UrlEncode(targetPath) + "\"}"); //context.Response.Write("{\"hasError\" : false}"); } else context.Response.Write("{\"hasError\" : true}"); } /// <summary> /// 删除文件夹及其内容 /// </summary> /// <param name="dir"></param> private static void DeleteFolder(string strPath) { //删除这个目录下的所有子目录 if (Directory.GetDirectories(strPath).Length > 0) { foreach (string fl in Directory.GetDirectories(strPath)) { Directory.Delete(fl, true); } } //删除这个目录下的所有文件 if (Directory.GetFiles(strPath).Length > 0) { foreach (string f in Directory.GetFiles(strPath)) { System.IO.File.Delete(f); } } Directory.Delete(strPath, true); } public bool IsReusable { get { return false; } } }
全局 跨域配置
<httpProtocol> <customHeaders> <add name="Access-Control-Allow-Origin" value="*"/> <add name="Access-Control-Allow-Headers" value="*"/> <add name="Access-Control-Allow-Methods" value="GET,POST,OPTIONS"/> </customHeaders> </httpProtocol> </system.webServer>
用 http://localhost:3504 代替 *,不安全。
地址是要上传的地方