限制并发上传

Limit concurrent uploads

我的 .NET Core 站点中有一个文件上传系统,允许用户一次将任意数量的文件直接上传到 S3 存储桶。用户可以上传 1 个或多个文件。我遇到的问题是,当上传时,比方说 1,000 个文件,浏览器不喜欢创建那么多连接,而且通常情况下,文件通常无法上传。即使启用了重试,这些重试也往往会失败,因为浏览器只允许一定数量的并发连接。更糟糕的是浏览器会锁定。

我想要做的是将文件放入队列中,并且在任何给定时间只允许实际上传 20 个文件(想想 FileZilla 如何对要上传的项目进行排队)。文件完成后,将添加新文件,直到队列耗尽。这样浏览器只创建它需要的连接。我已经有了它,所以 AutoUpload 设置为 False 我可以将文件放入数组中进行处理,但是 uploadSelectEvent.sender.upload() 方法可以上传所有内容。

有没有办法在启用上传之前暂停所有上传,以便我可以根据需要恢复它们?有没有更好的方法来处理这个问题?

我能够自己解决这个问题。以下是方法(请注意,这需要进行一些修改才能适用于您自己的代码,我不是纯粹的复制和粘贴答案):

创建一个数组来保存一些数据:

/** Files currently uploading */
const uploadQueue: any[] = [];

捕获 FileSuccess 事件并添加这个

    // Check the size of the queue
    if (uploadQueue.length < 20) {
        const that = (uploadSuccessEvent.sender as any);
        const module = that._module;
        const upload = module.upload;

        $(".k-file").each((i, x) => {
            //console.log(i, x);
            if (uploadQueue.length < 20) {
                const fileEntry = $(x);
                const started = fileEntry.is(".k-file-progress, .k-file-success, .k-file-error");
                const hasValidationErrors = upload._filesContainValidationErrors(fileEntry.data("fileNames"));

                if (!started && !hasValidationErrors) {
                    uploadQueue.push(fileEntry.data("fileNames")[0].uid);
                    //console.log("fileEntry", fileEntry.data("fileNames")[0].uid);

                    // Start the upload process
                    module.performUpload(fileEntry);
                }
            }
            else { return; }
        });
    }

创建一个新函数来处理上传队列:

/**
 * Adds the file to the upload queue and starts the upload.
 * Other files will be loaded via the on success event.
 * @param uploadSelectEvent Select event object.
 */
function queueUpload(uploadSelectEvent: kendo.ui.UploadSelectEvent) {
    //console.log("uploadSelectEvent", uploadSelectEvent);

    // Check the size of the queue
    if (uploadQueue.length < 20) {
        // Start the upload process
        const that = (uploadSelectEvent.sender as any);
        const module = that._module;
        const upload = module.upload;

        //uploadSelectEvent.files.forEach((file, i) => { console.log(i, file); if (uploadQueue.length < 20) { uploadQueue.push(file.uid); } });

        $(".k-file").each((i, x) => {
            //console.log(i, x);
            if (uploadQueue.length < 20) {
                const fileEntry = $(x);
                const started = fileEntry.is(".k-file-progress, .k-file-success, .k-file-error");
                const hasValidationErrors = upload._filesContainValidationErrors(fileEntry.data("fileNames"));

                if (!started && !hasValidationErrors) {
                    uploadQueue.push(fileEntry.data("fileNames")[0].uid);
                    module.performUpload(fileEntry);
                }
            }
            else { return; }
        });
    }
}

捕获FileSelect事件并将事件传递给queueUpload

最后,您应该将并发上传限制在 20 个以内。它仍然允许将 100 或 1000 个文件拖到浏览器中(它可能仍会锁定一秒钟)但一次最多只能创建 20 个连接。这可能不是最理想的代码,但它适用于我的情况。