我正在尝试将文件发送到我的API,并希望在选择多个文件并使用两个不同的Post调用时一个接一个地完成
在click
事件中,我获取文件并遍历它们,然后将文件数据传递给First()
函数调用,以获取唯一ID(VersionID
)并传递那个{{1 }}在第二次调用VersionID
函数时。
HTML
second()
JQuery
<div class="progress">
<div class="progress-bar">0%</div>
</div>
<div id="status"></div>
首次呼叫
$(function () {
var isChrome = navigator.userAgent.toLowerCase().indexOf('chrome') > -1;
var status = $('#status');
$('#btnUploadFile').on('click', function () {
$("#btnUploadFile").attr("disabled", true);
var files = $("#fileUpload").get(0).files;
var input = document.getElementById('fileUpload');
for (var i = 0; i < input.files.length; ++i) {
var file = input.files[i];
first(9, file.name, (file.size / 1000), file.name.split('.')[1], function (versionID) {
$.when(second(versionID, files[i])).done(function(){
status.html('Uploading ' + i + ' of ' + input.files.length)});
});
};
});
});
第二通电话
function first(libid, filename, filesize, fileextension, callback) {
var form = new FormData();
form.append("LibId", libid);
form.append("FileName", filename);
form.append("FileSize", filesize);
form.append("FileExtension", fileextension);
var settings = {
"async": false,
"crossDomain": true,
"url": "URL",
"method": "POST",
"processData": false,
"contentType": false,
"mimeType": "multipart/form-data",
"data": form
}
$.ajax(settings).done(function (response) {
callback(response);
});
};
问题是function second(versionId, fileData) {
var data = new FormData();
data.append('UploadedFiles', fileData);
var bar = $('.progress-bar');
var percent = $('.progress-bar');
$.ajax({
async: true,
crossDomain: true,
url: "URL" + Math.floor(versionId).toString(),
method: "POST",
processData: false,
contentType: false,
mimeType: "multipart/form-data",
data: data,
xhr: function () {
var xhr = $.ajaxSettings.xhr();
xhr.onprogress = function e() {
// For downloads
if (e.lengthComputable) {
console.log(e.loaded / e.total);
}
};
xhr.upload.onprogress = function (e) {
// For uploads
if (e.lengthComputable) {
var percentVal = parseInt((e.loaded / e.total * 100), 10);
console.log("Loaded " + parseInt((e.loaded / e.total * 100), 10) + "%");
var percentValue = percentVal + '%';
bar.width(percentValue);
percent.html(percentValue);
}
};
return xhr;
}
}).done(function (response) {
percent.html("Completed");
}).fail(function (e) {
console.log("failed");
});
};
似乎没有等待继续循环。
当前行为:
它等待
$.when(second(versionID, files[i])).done....
函数完成然后触发First()
函数,但不等待Sencond()
函数之前 启动新的Second()
函数。
预期行为
等待
First()
函数完全完成,然后等待First()
函数也可以完全完成,然后再返回到下一个 文件,然后再次调用Second()
函数。
我正在First()
函数中使用async: false
和在First()
函数中使用async: true
的另一件事,好像我在{{1 }}功能,我无法获得文件上传进度。
使用AJAX Second()
时是否可以等待async: true
函数完成然后继续循环?
答案 0 :(得分:2)
您有两个问题。
首先,when
需要传递一个或多个 thenable对象,但是您要传递undefined
。 second
没有返回声明。但是,使用when
是没有意义的,因为您不是并行运行多个函数。
第二个问题是,尽管when
不会调用done
回调,直到您传递给它的所有内容都完成了……for
循环不会等待以完成when
。
有两种方法可以解决此问题:
for
循环
var i
first
递增i
first
递归调用second
(直到i
为input.files.length
)async
/ await
管理从$.ajax
返回的承诺(这将使您保持循环)。如果要支持较旧的浏览器,后一种方法将需要使用Babel这样的编译器。