环境:Visual Studio 2015,.NET Framework 4.5.2,ASP.NET MVC5,Vue.js,Element UI
本文主要介绍基于element的el-upload的两种批量上传文件的方法
1、el-upload原生的批量上传操作,这种方法是一个文件对应一个HTTP请求
2、在el-upload的基础上,用Ajax+FormData一个HTTP请求上传多个文件
1、el-upload批量上传文件
在el-upload控件添加multiple属性
<el-upload class="upload-demo"
action="UploadFile"
:on-preview="handlePreview"
:on-remove="(file, fileList) => {handleRemove(file, fileList, 'DEImage')}"
:before-remove="beforeRemove"
:limit="50"
:on-exceed="handleExceed"
:on-success="(response, file, fileList) => {handleSuccess(response, file, fileList, 'DEImage',0)}"
:file-list="filelistPCBAImage" style="float:left;" :disabled="IsReadonly" multiple>
<el-button size="small" type="primary" v-if="!IsReadonly">点击上传</el-button>
</el-upload>
因为是el-upload批量上传是一个一个上传,所以上传成功的回调函数要把返回的数据保存起来。保存返回数据的数组不能跟file-list的一致,否则会报错
handleSuccess: function (response, file, fileList, attaType, index) {
if (this.ReBuyOffForm[attaType]) {
this.ReBuyOffForm[attaType].push({ name: response.Data.Name, url: response.Data.Url });
} else {
this.ReBuyOffForm[attaType] = [{ name: response.Data.Name, url: response.Data.Url }];
}
},
删除上传文件的时候,要注意区分数据库读出来的文件(pThis.filelistPCBAImage)和新上传的文件(pThis.ReBuyOffForm[attaType]),因为他们保存在不同的地方,所以删除的时候要注意这个问题,保存表单的时候也要记得把他们合起来。
handleRemove: function (file, fileList, attaType) {
var pThis = this;
var path = file.info ? file.info.url : file.url;
var action = jp.createRpc('DeleteFile');
action({ Path: path })
.done(function (data) {
pThis.$message({
message: pThis.$t('lpa.msg.OperationComplete'),
type: 'success'
});
//删掉上传的文件
for (var i = 0; i < pThis.ReBuyOffForm[attaType].length; i++) {
if (pThis.ReBuyOffForm[attaType][i].url == path) {
pThis.ReBuyOffForm[attaType].splice(pThis.ReBuyOffForm[attaType].indexOf(pThis.ReBuyOffForm[attaType][i]), 1);
}
}
//这个地方如果直接删除file-list绑定的数组元素,会对新上传的文件有影响
for (var i = 0; i < pThis.filelistPCBAImage.length; i++) {
if (pThis.filelistPCBAImage[i].url == path) {
pThis.filelistPCBAImage[i].status = "delete";
}
}
});
},
后台Action不需要参数,直接在HTTP上下文里面拿
[HttpPost]
public virtual JsonResult UploadFile()
{
HttpPostedFileBase file = Request.Files[0];
string directoryPath = ConfigurationManager.AppSettings["UploadPath"] + "/" + DateTime.Now.ToString("yyyy-MM-dd") + "/";
if (!System.IO.Directory.Exists(AppDomain.CurrentDomain.BaseDirectory + directoryPath))
{
System.IO.Directory.CreateDirectory(AppDomain.CurrentDomain.BaseDirectory + directoryPath);
}
var strExt = System.IO.Path.GetExtension(file.FileName);
var strGuidName = CommonLibrary.Helpers.GUID.Create();
string strRealName = strGuidName + strExt;
string savePath = AppDomain.CurrentDomain.BaseDirectory + directoryPath + strRealName;
file.SaveAs(savePath);
return CustomJson(new { Url = directoryPath + strRealName, Name = file.FileName });
}
2、AJAX一个HTTP请求批量上传文件
element的el-upload是一个一个的往后台发请求上传文件的,就是说你选N个文件就会发起N个HTTP请求。
如果想要一个请求把所有的文件都上传到服务器,需要用ajax手动批量上传文件。
实现代码也很简单,创建一个FormData,利用el-upload的http-request事件把文件加到FormData,用ajax把FormData提交到服务器,后台Action直接在HTTP上下文就能拿到FormData数据。
具体参照代码
--------------------
下面是el-upload控件属性设置
<el-upload class="upload-demo"
ref="upload"
action="aaa"
:on-preview="handlePreview"
:on-remove="(file, fileList) => {handleRemove(file, fileList, 'FilmImage')}"
:before-remove="beforeRemove"
:limit="50"
:on-exceed="handleExceed"
:http-request="uploadFilmImageFile"
:auto-upload="false"
:file-list="ReBuyOffForm.FilmImage" style="float:left;" :disabled="IsReadonly" multiple>
<el-button size="small" type="primary" style="float:left;" v-if="!IsReadonly">选择文件</el-button>
<el-button size="small" type="success" @@click="submitFilmImageUpload" v-if="!IsReadonly">上传到服务器</el-button>
</el-upload>
el-upload控件的事件处理代码 ,submitFilmImageUpload就是上传文件事件,注意ajax的参数
handlePreview: function (file) {
window.open("@ViewBag.SiteUrl" + "/" + (file.info ? file.info.url : file.url));
},
handleExceed: function (files, fileList) {
this.$message.warning(`当前限制选择 1 个文件,本次选择了 ${files.length} 个文件,共选择了 ${files.length + fileList.length} 个文件`);
},
beforeRemove: function (file, fileList) {
return this.$confirm(`确定移除 ${file.name}?`);
},
uploadFilmImageFile: function (file) {
this.FilmImageFileData.append("file-" + file.file.name, file.file);
},
submitFilmImageUpload: function () {
this.FilmImageFileData = new FormData();
this.$refs.upload.submit();
var pThis = this;
$.ajax({
type: "post",
url: '@Url.Action("BatchUploadFile")',
data: this.FilmImageFileData,
dataType: "json",
processData: false,
contentType: false,
success: function (result) {
if (result.Data && result.Data.length > 0) {
for (var i = 0; i < result.Data.length; i++) {
pThis.ReBuyOffForm.FilmImage.push({ name: result.Data[i].Name, url: result.Data[i].Url })
}
}
},
error: function (e) {
console.log(e);
}
});
},
handleRemove: function (file, fileList, attaType) {
var pThis = this;
var path = file.info ? file.info.url : file.url;
var action = jp.createRpc('DeleteFile');
action({ Path: path })
.done(function (data) {
pThis.$message({
message: pThis.$t('lpa.msg.OperationComplete'),
type: 'success'
});
for (var i = 0; i < pThis.ReBuyOffForm[attaType].length; i++) {
if (pThis.ReBuyOffForm[attaType][i].url == path) {
pThis.ReBuyOffForm[attaType].splice(pThis.ReBuyOffForm[attaType].indexOf(pThis.ReBuyOffForm[attaType][i]), 1);
}
}
});
},
Action里面通过Request.Files能拿到上传的文件集合,然后把文件保存起来,用一个数组把文件信息返回给前端
[HttpPost]
public virtual JsonResult BatchUploadFile()
{
var uploadFiles = Request.Files;
string directoryPath = ConfigurationManager.AppSettings["UploadPath"] + "/" + DateTime.Now.ToString("yyyy-MM-dd") + "/";
if (!System.IO.Directory.Exists(AppDomain.CurrentDomain.BaseDirectory + directoryPath))
{
System.IO.Directory.CreateDirectory(AppDomain.CurrentDomain.BaseDirectory + directoryPath);
}
JArray array = new JArray();
foreach (string uploadFile in uploadFiles)
{
HttpPostedFileBase file = Request.Files[uploadFile] as HttpPostedFileBase;
var strExt = System.IO.Path.GetExtension(file.FileName);
var strGuidName = CommonLibrary.Helpers.GUID.Create();
string strRealName = strGuidName + strExt;
string savePath = AppDomain.CurrentDomain.BaseDirectory + directoryPath + strRealName;
file.SaveAs(savePath);
array.Add(JObject.FromObject(new { Url = directoryPath + strRealName, Name = file.FileName }));
}
return CustomJson(array);
}