127 lines
4.4 KiB
JavaScript
127 lines
4.4 KiB
JavaScript
import { Meteor } from 'meteor/meteor';
|
|
import { OHIF } from 'meteor/ohif:core';
|
|
|
|
/**
|
|
* Imports selected studies from local into studylist
|
|
* @param filesToImport Files located in the client machine to import
|
|
*/
|
|
OHIF.studylist.importStudies = filesToImport => {
|
|
const numberOfFiles = filesToImport && filesToImport.length;
|
|
if (!numberOfFiles) {
|
|
return new Promise((resolve, reject) => reject('No files to upload'));
|
|
}
|
|
|
|
const uploadMessage = ({ processed, total }) => `Uploaded files: ${processed} / ${total}`;
|
|
|
|
const taskRunHandler = dialog => {
|
|
const uploadErrorHandler = fileNames => {
|
|
const names = fileNames.join('; ');
|
|
dialog.setMessage(`Failed to upload files: ${names}`);
|
|
};
|
|
|
|
const uploadSuccessHandler = studiesToImport => {
|
|
importStudiesInternal(studiesToImport, dialog).then(() => {
|
|
dialog.done();
|
|
}).catch(errorMessage => {
|
|
dialog.setMessage(errorMessage);
|
|
});
|
|
};
|
|
|
|
uploadFiles(filesToImport, dialog).then(uploadSuccessHandler).catch(uploadErrorHandler);
|
|
};
|
|
|
|
return OHIF.ui.showDialog('dialogProgress', {
|
|
title: 'Importing Studies...',
|
|
message: uploadMessage,
|
|
total: numberOfFiles,
|
|
task: { run: taskRunHandler }
|
|
});
|
|
};
|
|
|
|
const uploadFiles = (files, dialog) => {
|
|
let processed = 0;
|
|
|
|
const promise = new Promise((resolve, reject) => {
|
|
const promises = [];
|
|
|
|
// Upload files to the server
|
|
files.forEach(file => {
|
|
const filePromise = uploadFile(file, dialog);
|
|
filePromise.then(() => dialog.update(++processed));
|
|
promises.push(filePromise);
|
|
});
|
|
|
|
Promise.all(promises).then(resolve).catch(reject);
|
|
});
|
|
|
|
return promise;
|
|
};
|
|
|
|
const uploadFile = file => {
|
|
return new Promise((resolve, reject) => {
|
|
const xhr = new XMLHttpRequest();
|
|
xhr.open('POST', '/uploadFilesToImport', true);
|
|
xhr.setRequestHeader('filename', file.name);
|
|
|
|
xhr.onload = () => {
|
|
if (xhr.readyState === 4 && xhr.status !== 200) {
|
|
// Failed to upload the file
|
|
reject(file.name);
|
|
} else {
|
|
// Success uploading the file
|
|
resolve(xhr.responseText);
|
|
}
|
|
};
|
|
|
|
// Failed to upload the file
|
|
xhr.onerror = () => reject(file.name);
|
|
|
|
xhr.send(file);
|
|
});
|
|
};
|
|
|
|
const importStudiesInternal = (studiesToImport, dialog) => {
|
|
const numberOfStudies = studiesToImport && studiesToImport.length;
|
|
if (!numberOfStudies) {
|
|
return new Promise((resolve, reject) => reject('No studies to import'));
|
|
}
|
|
|
|
let processed = 0;
|
|
dialog.update(processed);
|
|
dialog.setTotal(numberOfStudies);
|
|
dialog.setMessage(({ processed, total }) => `Imported: ${processed} / ${total}`);
|
|
|
|
return new Promise((resolve, reject) => {
|
|
// Create/Insert a new study import status item
|
|
Meteor.call('createStudyImportStatus', (error, studyImportStatusId) => {
|
|
if (error) {
|
|
return reject(error.message);
|
|
}
|
|
|
|
// Handle when StudyImportStatus collection is updated
|
|
OHIF.studylist.collections.StudyImportStatus.find(studyImportStatusId).observe({
|
|
changed(studyImportStatus) {
|
|
const { numberOfStudiesImported, numberOfStudiesFailed } = studyImportStatus;
|
|
dialog.update(numberOfStudiesImported);
|
|
|
|
if (numberOfStudiesImported === numberOfStudies) {
|
|
// The entire import operation is completed, so remove the study import status item
|
|
Meteor.call('removeStudyImportStatus', studyImportStatus._id);
|
|
|
|
// Show number of failed files if there is at least one failed file
|
|
if (studyImportStatus.numberOfStudiesFailed > 0) {
|
|
const failed = numberOfStudiesFailed;
|
|
reject(`Failed to import ${failed} of ${numberOfStudies} studies`);
|
|
} else {
|
|
resolve();
|
|
}
|
|
}
|
|
}
|
|
});
|
|
|
|
// Import studies with study import status id to get callbacks
|
|
Meteor.call('importStudies', studiesToImport, studyImportStatusId);
|
|
});
|
|
});
|
|
};
|