C# 基于webuploader的文件分片上传

前台js

页面代码
<div>
	<table style="margin: 0 auto;width:100%">
        <tr>
            <td colspan="4" style="padding-top: 15px;">
                <div id="uploader" class="wu-example">
                    <!--用来存放文件信息-->
                    <div id="thelist" class="uploader-list"></div>
                    <div class="btns">
                        <div id="picker">选择文件</div>
                        <input id="ctlBtn" type="button" value="开始上传" class="btn btn-default" />
                    </div>
                </div>
                <br />
            </td>
        </tr>
    </table>
</div>
引入js文件
<script src="scripts/jquery-1.10.2.min.js"></script>
<script src="scripts/webuploader.js"></script>
<script src="scripts/bootstrap.min.js"></script>
<link href="../css/bootstrap.css" rel="stylesheet" />
<link href="../css/webuploader.css" rel="stylesheet" />
<script>
var applicationPath = window.applicationPath === "" ? "" : window.applicationPath || "..";
    var GUID = WebUploader.Base.guid();//一个GUID
    $(function () {
        ininnForm();
        var $ = jQuery;
        var $list = $('#thelist');
        var uploader = WebUploader.create({
            // 选完文件后,是否自动上传。
            auto: false,
            // swf文件路径
            //swf: applicationPath + '/scripts/Uploader.swf',
            swf: 'scripts/Uploader.swf',
            // 文件接收服务端。
            //server: applicationPath + '/Fileashx.ashx',
            server: 'Fileashx.ashx',
            //server:"/fileashx.ashx",

            // 选择文件的按钮。可选。
            // 内部根据当前运行是创建,可能是input元素,也可能是flash.
            pick: '#picker',

            chunked: true,//开始分片上传
            //chunkSize: 2048000,//每一片的大小
            chunkSize: 1024 * 1024,//每次上传1M
            formData: {
                guid: GUID, //自定义参数,待会儿解释
                saveFileName: FileUpload.CreatFileName(BiddingBody).value
            },
            // 不压缩image, 默认如果是jpeg,文件上传前会压缩一把再上传!
            resize: false
        });
        // 当有文件被添加进队列的时候
        uploader.on('fileQueued', function (file) {
            $list.append('<div id="' + file.id + '" class="item">' +
                '<h4 class="info">' + file.name + '</h4>' +
                '<div style="overflow:hidden;"><p style="float:left;" class="state">等待上传...</p><span class="text"></span></div>' +
                '</div>');
        });
        // 文件上传过程中创建进度条实时显示。
        uploader.on('uploadProgress', function (file, percentage) {
            var $li = $('#' + file.id),
                $percent = $li.find('.progress .progress-bar');

            // 避免重复创建
            if (!$percent.length) {
                $percent = $('<div class="progress progress-striped active">' +
                    '<span  class="percentage">' +
                    '<div class="progress-bar" role="progressbar" style="width: 0%">' +
                    '</div>' +
                    '</div>').appendTo($li).find('.progress-bar');
            }
            $li.find('p.state').text('上传中');

            $li.find("span.text").text(Math.round(percentage * 100) + '%');
            $percent.css('width', percentage * 100 + '%');
        });

        // 文件上传成功,给item添加成功class, 用样式标记上传成功。
        uploader.on('uploadSuccess', function (file, response) {
            console.log(response);
            $('#' + file.id).find('p.state').text('已上传');
            if (response.Flag != 1) {
                alert(response.FlagMessage);
            }
        });

        // 文件上传失败,显示上传出错。
        uploader.on('uploadError', function (file) {
            $('#' + file.id).find('p.state').text('上传出错');
        });

        // 完成上传完了,成功或者失败,先删除进度条。
        uploader.on('uploadComplete', function (file) {
            $('#' + file.id).find('.progress').fadeOut();
        });

        //所有文件上传完毕
        uploader.on("uploadFinished", function () {
            args.jsUpload();
            window.close();
        });
        //开始上传
        $("#ctlBtn").click(function () {
            $("#picker input").attr("disabled", true);
            uploader.upload();
        });
        uploader.on('uploadBeforeSend', function (obj, data, headers) {
            $.extend(headers, {
                Accept: "/*"
            });
        });

    });
</script>

一般处理程序代码

public class Fileashx : IHttpHandler, IRequiresSessionState
{

    public void ProcessRequest(HttpContext context)
    {
        context.Response.ContentType = "text/plain"
        try
        {
            string SaveRandfileName = context.Request["saveFileName"];//文件名称

            #endregion
           	string savePath =  "/upload/" + SaveRandfileName + "/";
            string fileUrl = "";//文件存储地址
            string fileExt = "";//后缀名
            string SavefileName = "";
            //定义允许上传的文件扩展名
            System.Collections.Hashtable extTable = new System.Collections.Hashtable();
            extTable.Add("image", "gif,jpg,jpeg,png,bmp");
            extTable.Add("flash", "swf,flv");
            extTable.Add("media", "swf,flv,mp3,wav,wma,wmv,mid,avi,mpg,asf,rm,rmvb");
            extTable.Add("file", "doc,docx,xls,xlsx,ppt,htm,html,txt,zip,rar,gz,bz2");
            //

            if (context.Request.Form.AllKeys.Any(m => m == "chunk"))
            {

                try
                {
                    string fileName = context.Request["name"];
                    fileExt = Path.GetExtension(fileName).ToLower();//文件扩展名
                    if (String.IsNullOrEmpty(fileExt))
                    {
                        context.Response.Write("error");
                    }
                    fileName = SaveRandfileName + fileExt;
                    string fileRelName = fileName.Substring(0, fileName.LastIndexOf('.'));//设置临时存放文件夹名称
                                                                                          //取得chunk和chunks
                    int chunk = Convert.ToInt32(context.Request.Form["chunk"]);//当前分片在上传分片中的顺序(从0开始)
                    int chunks = Convert.ToInt32(context.Request.Form["chunks"]);//总分片数


                    //var guid = context.Request["guid"];//前端传来的GUID号

                    var uploadDir = context.Server.MapPath("~/Upload/" + savePath + "/" + fileRelName + "/");//文件上传目录
                                                                                                             //string uploadDir = savePath + "/" + fileRelName + "/";
                    var dir = Path.Combine(uploadDir, fileRelName);//临时保存分块的目录
                    if (!System.IO.Directory.Exists(uploadDir))
                    {
                        System.IO.Directory.CreateDirectory(uploadDir);
                    }

                    string path = uploadDir + chunk;
                    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();


                    #region 文件合并
                    string targetPath = context.Server.MapPath("~/Upload/" + savePath + "/" + fileName);//合并后的文件
                                                                                                        //string targetPath = savePath + "/" + fileName;
                    DirectoryInfo dicInfo = new DirectoryInfo(uploadDir);
                    if (Directory.Exists(Path.GetDirectoryName(uploadDir)))
                    {
                        FileInfo[] Allfiles = dicInfo.GetFiles();
                        if (Allfiles.Length == chunks)
                        {
                            foreach (FileInfo Newfile in Allfiles.OrderBy(f => int.Parse(f.Name)))
                            {
                                FileStream addTargetFile = new FileStream(targetPath, FileMode.Append, FileAccess.Write);
                                BinaryWriter AddTargetWriter = new BinaryWriter(addTargetFile);

                                //获得上传的分片数据流
                                Stream Targetstream = Newfile.Open(FileMode.Open);
                                BinaryReader TempTargetReader = new BinaryReader(Targetstream);
                                //将上传的分片追加到临时文件末尾
                                AddTargetWriter.Write(TempTargetReader.ReadBytes((int)Targetstream.Length));
                                //关闭BinaryReader文件阅读器
                                TempTargetReader.Close();
                                Targetstream.Close();
                                AddTargetWriter.Close();
                                addTargetFile.Close();

                                TempTargetReader.Dispose();
                                Targetstream.Dispose();
                                AddTargetWriter.Dispose();
                                addTargetFile.Dispose();
                            }
                            DeleteFolder(uploadDir);
                            context.Response.Write("success");
                        }
                    }
                    else
                    {
                        context.Response.Write("error");
                    }
                    #endregion
                }
                catch (Exception ex)
                {
                    context.Response.Write("error");
                }
            }
            else // 没有分片直接保存
            {
                string fileName = context.Request.Files[0].FileName;//文件名                    
                fileExt = Path.GetExtension(fileName).ToLower();//文件扩展名
                if (String.IsNullOrEmpty(fileExt))
                {
                    context.Response.Write("上传文件扩展名是不允许的扩展名。");
                    return;
                }


                String dirPath = context.Server.MapPath("~/Upload/" + savePath);
                if (!Directory.Exists(dirPath))
                {
                    Directory.CreateDirectory(dirPath);
                }
                fileName = SaveRandfileName + fileExt;

                context.Request.Files[0].SaveAs(dirPath + fileName);

                context.Response.Write("success");
            }
        }
        catch (Exception e)
        {
            context.Response.Write("error");
        }
       context.Response.Write("success");
    }
    /// <summary>
    /// 合并文件
    /// </summary>
    /// <returns></returns>
    public void Merge(string fileName, string guid, string uploadDir)
    {
        //   var uploadDir = context.Server.MapPath("~/Upload");//Upload 文件夹

        string fileRelName = fileName.Substring(0, fileName.LastIndexOf('.'));
        var dir = Path.Combine(uploadDir, fileRelName);//临时文件夹  
        var files = System.IO.Directory.GetFiles(dir);//获得下面的所有文件
        var finalPath = Path.Combine(uploadDir, fileName);//最终的文件名(demo中保存的是它上传时候的文件名,实际操作肯定不能这样)
        var fs = new FileStream(finalPath, FileMode.Create);
        foreach (var part in files.OrderBy(x => x.Length).ThenBy(x => x))//排一下序,保证从0-N Write
        {
            var bytes = System.IO.File.ReadAllBytes(part);
            fs.Write(bytes, 0, bytes.Length);
            bytes = null;
            System.IO.File.Delete(part);//删除分块
        }
        fs.Flush();
        fs.Close();
        System.IO.Directory.Delete(dir);//删除文件夹


    }
    public bool IsReusable
    {
        get
        {
            return false;
        }
    }


    /// <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);
    }

}

发布了1 篇原创文章 · 获赞 0 · 访问量 30

猜你喜欢

转载自blog.csdn.net/weixin_38680315/article/details/104478659