UploadServices.js
Home
/
FileServer /
Web /
Scripts /
Services /
UploadServices.js
class UploadServices {
constructor() {
this.URL_Start = "/UploadFiles/StartUpload";
this.URL_Upload = "/UploadFiles/UploadBlob";
this.URL_Cansel = "/UploadFiles/Cansel";
this.upload_chunk_size = 102400;
this.ID = -1;
this._ContinueDownload = false;
this._file = null;
this._ParentID = null;
//Callback события
//(number progresse)
this.OnProggresseChange = null;
//(number id)
this.OnIDReceived = null;
//(string Msg)
this.OnError = null;
}
//Считывает часть файла
//startByte - int позиция начала чтения
//stopByte - int позиция окончания чтения
async _ReadBlobAsync(startByte, stopByte) {
return new Promise(function (resolve, reject) {
//Считываем часть файла
let blob = this._file.slice(startByte, stopByte);
let reader = new FileReader();
reader.onload = function () {
resolve(reader.result);
};
reader.onerror = reject;
reader.readAsDataURL(blob);
}.bind(this));
}
//Сообщает серверу о начале загрузки файла, получает ID загрузки
async _StartUploadAsync() {
let res;
await fetch(
this.URL_Start,
{
method: "Post",
headers: {
'Content-Type': 'application/json'
},
body: JSON.stringify({
//ID папки
ParentID: this._ParentID,
//Имя файла
Name: this._file.name,
//Размеры
Size: this._file.size
})
}
).then(function (response) {
return response.json();
}).then(function (data) {
res = data;
}.bind(this));
return res;
}
//Выполняет загрузка блока
async _UploadBlobAsync(bin_data, ChunkNumb) {
console.log("_UploadBlobAsync");
if (!this._ContinueDownload)
return { State: true };
if (bin_data != '') {
console.log(this.URL_Upload + ChunkNumb);
let res;
await fetch(
this.URL_Upload,
{
method: "Post",
headers: {
'Content-Type': 'application/json'
},
body: JSON.stringify({
//ID загрузки
ID: this.ID,
//Кусок файла
chunk: bin_data
//Номер куска
//'ChunkNumb': ChunkNumb
})
}
).then(function (response) {
return response.json();
}).then(function (data) {
res = data;
}.bind(this));
return res;
}
}
//Инициирует загрузку файла
//parent_id - int ID папки для загрузки
async UploadFileAsync(file, parent_id) {
this._file = file;
this._ParentID = parent_id;
let start_info = await this._StartUploadAsync();
if (!start_info.State) {
if (this.OnError != null)
this.OnError(start_info.Msg);
return;
}
this._ContinueDownload = true;
this.ID = start_info.ID;
if (this.OnIDReceived != null)
this.OnIDReceived(this.ID);
for (let pos = 0, ChunkNumb = 0; pos < this._file.size; pos += this.upload_chunk_size, ChunkNumb++) {
if (!this._ContinueDownload)
return;
let bin_data = await this._ReadBlobAsync(pos, pos + this.upload_chunk_size);
let state = await this._UploadBlobAsync(bin_data, ChunkNumb);
if (!state.State) {
//alert('Загрузка прервана');
if (this.OnError != null)
this.OnError(state.Msg);
return;
}
// Вычисляем процент отправленного
let p = Math.round(pos * 100 / file.size);
console.log('p = ' + p);
if (this.OnProggresseChange != null)
this.OnProggresseChange(p);
}
this._ContinueDownload = false;
}
Cansel() {
this._ContinueDownload = false;
//Костыль задержка, чтобы асинхронный загрузчик точно прервал работу
//и не попытался получить доступ к ужаленному проекту загрузки
//Возможно зависит от размера блока
setTimeout(function () {
fetch(
this.URL_Cansel,
{
method: "Post",
headers: {
'Content-Type': 'application/json'
},
body: JSON.stringify({
//ID файла
ID: this.ID,
})
}
);
}.bind(this),
500);
}
}