UNPKG

synapse-react-client

Version:

[![Build Status](https://travis-ci.com/Sage-Bionetworks/Synapse-React-Client.svg?branch=main)](https://travis-ci.com/Sage-Bionetworks/Synapse-React-Client) [![npm version](https://badge.fury.io/js/synapse-react-client.svg)](https://badge.fury.io/js/synaps

428 lines 26.6 kB
"use strict"; Object.defineProperty(exports, "__esModule", { value: true }); exports.TESTING_CLEAR_BTN_CLASS = exports.TESTING_TRASH_BTN_CLASS = void 0; var tslib_1 = require("tslib"); var fontawesome_svg_core_1 = require("@fortawesome/fontawesome-svg-core"); var free_solid_svg_icons_1 = require("@fortawesome/free-solid-svg-icons"); var react_fontawesome_1 = require("@fortawesome/react-fontawesome"); var moment_1 = (0, tslib_1.__importDefault)(require("moment")); var react_1 = (0, tslib_1.__importStar)(require("react")); var ReactBootstrap = (0, tslib_1.__importStar)(require("react-bootstrap")); var calculateFriendlyFileSize_1 = require("../../utils/functions/calculateFriendlyFileSize"); var useGetInfoFromIds_1 = (0, tslib_1.__importDefault)(require("../../utils/hooks/useGetInfoFromIds")); var SynapseClient_1 = require("../../utils/SynapseClient"); var synapseTypes_1 = require("../../utils/synapseTypes"); var HasAccess_1 = (0, tslib_1.__importStar)(require("../HasAccess")); var UserCard_1 = (0, tslib_1.__importDefault)(require("../UserCard")); var CreatePackage_1 = require("./CreatePackage"); var DownloadDetails_1 = (0, tslib_1.__importDefault)(require("./DownloadDetails")); var AccessRequirementList_1 = (0, tslib_1.__importDefault)(require("../access_requirement_list/AccessRequirementList")); var SynapseContext_1 = require("../../utils/SynapseContext"); var getEndpoint_1 = require("../../utils/functions/getEndpoint"); fontawesome_svg_core_1.library.add(free_solid_svg_icons_1.faTrash); exports.TESTING_TRASH_BTN_CLASS = 'TESTING_TRASH_BTN_CLASS'; exports.TESTING_CLEAR_BTN_CLASS = 'TESTING_CLEAR_BTN_CLASS'; /** * Web-based download list. * * @deprecated Use the new Download List Services instead (that support the Download Cart). * http://rest-docs.synapse.org/rest/#org.sagebionetworks.repo.web.controller.DownloadListController */ function DownloadListTable(props) { var _this = this; var _a, _b; var accessToken = (0, SynapseContext_1.useSynapseContext)().accessToken; // https://reactjs.org/docs/hooks-faq.html#should-i-use-one-or-many-state-variables var _c = (0, react_1.useState)({ references: undefined, batchFileResult: undefined, downloadList: undefined, }), data = _c[0], setData = _c[1]; var _d = (0, react_1.useState)({ column: '', isDescending: false, }), sortedColumn = _d[0], setSortedColumn = _d[1]; var _e = (0, react_1.useState)(), arPropsFromHasAccess = _e[0], set_arPropsFromHasAccess = _e[1]; // https://reactjs.org/docs/hooks-faq.html#should-i-use-one-or-many-state-variables var _f = (0, react_1.useState)(true), isLoading = _f[0], setIsLoading = _f[1]; var _g = (0, react_1.useState)(''), fileBeingDeleted = _g[0], setFileBeingDeleted = _g[1]; var _h = props.forceSamePage, forceSamePage = _h === void 0 ? false : _h, _j = props.renderAsModal, renderAsModal = _j === void 0 ? false : _j, onHide = props.onHide, listUpdatedCallback = props.listUpdatedCallback; var references = data.references, batchFileResult = data.batchFileResult, downloadList = data.downloadList; var requestedFiles = (batchFileResult && batchFileResult.requestedFiles) || []; // Get owner ids from download list by filtering to items that have a file handle // then map to ownerIds var ownerIdsFromHeaders = references === null || references === void 0 ? void 0 : references.results.filter(function (el) { return el.createdBy; }).map(function (el) { return el.createdBy; }); var ownerIdsFromFileHandles = requestedFiles .filter(function (el) { var _a; return ((_a = el.fileHandle) === null || _a === void 0 ? void 0 : _a.createdBy) !== undefined; }) .map(function (el) { return el.fileHandle.createdBy; }); var ownerIds = []; if (ownerIdsFromFileHandles) { ownerIds.push.apply(ownerIds, ownerIdsFromFileHandles); } if (ownerIdsFromHeaders) { ownerIds.push.apply(ownerIds, ownerIdsFromHeaders); } // use bang operator because filter function guarentee's that file handle will be defined var userProfiles = (0, useGetInfoFromIds_1.default)({ ids: ownerIds, type: 'USER_PROFILE', }); var fetchData = (0, react_1.useCallback)(function () { return (0, tslib_1.__awaiter)(_this, void 0, void 0, function () { var currentDownloadList, currentFilesToDownload, batchFileRequest, currentBatchFileResult_1, referenceCall, currentReferences, e_1; return (0, tslib_1.__generator)(this, function (_a) { switch (_a.label) { case 0: if (!accessToken) { setIsLoading(false); // doesn't make sense with anonymous user! return [2 /*return*/]; } _a.label = 1; case 1: _a.trys.push([1, 5, 6, 7]); setIsLoading(true); return [4 /*yield*/, (0, SynapseClient_1.getDownloadList)(accessToken)]; case 2: currentDownloadList = _a.sent(); currentFilesToDownload = currentDownloadList.filesToDownload; if (currentFilesToDownload.length === 0) { setData({ downloadList: currentDownloadList, }); return [2 /*return*/]; } batchFileRequest = { requestedFiles: currentFilesToDownload, includeFileHandles: true, includePreSignedURLs: false, includePreviewPreSignedURLs: false, }; return [4 /*yield*/, (0, SynapseClient_1.getFiles)(batchFileRequest, accessToken) // Only make entity header calls to the files that the user doesn't have access to, // which can be determined by whether the batchFileResult has a failure code for the // corresponding download list item ]; case 3: currentBatchFileResult_1 = _a.sent(); referenceCall = currentFilesToDownload .filter(function (el) { return (currentBatchFileResult_1.requestedFiles.find(function (batchFile) { return batchFile.fileHandleId === el.fileHandleId; }).failureCode !== undefined); }) .map(function (el) { return { targetId: el.associateObjectId }; }); return [4 /*yield*/, (0, SynapseClient_1.getEntityHeaders)(referenceCall, accessToken)]; case 4: currentReferences = _a.sent(); setData({ references: currentReferences, batchFileResult: currentBatchFileResult_1, downloadList: currentDownloadList, }); return [3 /*break*/, 7]; case 5: e_1 = _a.sent(); console.error('Error in DownloadList API call : ', e_1); return [3 /*break*/, 7]; case 6: setIsLoading(false); return [7 /*endfinally*/]; case 7: return [2 /*return*/]; } }); }); }, [accessToken]); (0, react_1.useEffect)(function () { fetchData(); }, [fetchData]); var clearDownloadList = function (_event) { return (0, tslib_1.__awaiter)(_this, void 0, void 0, function () { var err_1; return (0, tslib_1.__generator)(this, function (_a) { switch (_a.label) { case 0: setIsLoading(true); _a.label = 1; case 1: _a.trys.push([1, 3, 4, 5]); return [4 /*yield*/, (0, SynapseClient_1.deleteDownloadList)(accessToken)]; case 2: _a.sent(); setData({ downloadList: undefined, }); listUpdatedCallback === null || listUpdatedCallback === void 0 ? void 0 : listUpdatedCallback(); return [3 /*break*/, 5]; case 3: err_1 = _a.sent(); console.error('Error on clearing download list: ', err_1); return [3 /*break*/, 5]; case 4: setIsLoading(false); return [7 /*endfinally*/]; case 5: return [2 /*return*/]; } }); }); }; var deleteFileFromList = function (fileHandleId, associateObjectId) { return (0, tslib_1.__awaiter)(_this, void 0, void 0, function () { var list, currentDownloadList, err_2; return (0, tslib_1.__generator)(this, function (_a) { switch (_a.label) { case 0: list = [ { fileHandleId: fileHandleId, associateObjectId: associateObjectId, associateObjectType: synapseTypes_1.FileHandleAssociateType.FileEntity, }, ]; setIsLoading(true); setFileBeingDeleted(fileHandleId); _a.label = 1; case 1: _a.trys.push([1, 3, 4, 5]); return [4 /*yield*/, (0, SynapseClient_1.deleteDownloadListFiles)(list, accessToken) // The current references and batchFileResult can be kept because the download // list drives the view, so the stale values in those two won't be viewed. ]; case 2: currentDownloadList = _a.sent(); // The current references and batchFileResult can be kept because the download // list drives the view, so the stale values in those two won't be viewed. setData({ downloadList: currentDownloadList, references: references, batchFileResult: batchFileResult, }); listUpdatedCallback === null || listUpdatedCallback === void 0 ? void 0 : listUpdatedCallback(); return [3 /*break*/, 5]; case 3: err_2 = _a.sent(); console.error('Error on delete from download list', err_2); return [3 /*break*/, 5]; case 4: setFileBeingDeleted(''); setIsLoading(false); return [7 /*endfinally*/]; case 5: return [2 /*return*/]; } }); }); }; var sortColumn = function (column) { return (0, tslib_1.__awaiter)(_this, void 0, void 0, function () { var isDescending_1, currentFilesToDownload; var _a; return (0, tslib_1.__generator)(this, function (_b) { try { setIsLoading(true); isDescending_1 = column === sortedColumn.column ? !sortedColumn.isDescending : false; setSortedColumn({ column: column, isDescending: isDescending_1, }); currentFilesToDownload = (_a = downloadList === null || downloadList === void 0 ? void 0 : downloadList.filesToDownload) !== null && _a !== void 0 ? _a : []; currentFilesToDownload.sort(function (itemA, itemB) { return sortDownLoadList(itemA, itemB, column, isDescending_1); }); setData((0, tslib_1.__assign)((0, tslib_1.__assign)({}, data), { downloadList: downloadList })); listUpdatedCallback === null || listUpdatedCallback === void 0 ? void 0 : listUpdatedCallback(); } catch (err) { console.error(err); } finally { setIsLoading(false); } return [2 /*return*/]; }); }); }; var getFileHandleInfo = function (item) { var _a; var fileResult = requestedFiles.find(function (fileRes) { return fileRes.fileHandleId === item.fileHandleId; }); var fileHandle = fileResult ? fileResult.fileHandle : undefined; var fileName = ''; var createdBy = ''; var createdOn = ''; var contentSize = undefined; if (fileHandle && item) { fileName = fileHandle.fileName; createdBy = fileHandle.createdBy; createdOn = fileHandle.createdOn; contentSize = fileHandle.contentSize; } else { var requestedFile = results.find(function (req) { return req.id === item.associateObjectId; }); if (requestedFiles) { fileName = requestedFile === null || requestedFile === void 0 ? void 0 : requestedFile.name; createdBy = requestedFile === null || requestedFile === void 0 ? void 0 : requestedFile.createdBy; createdOn = requestedFile === null || requestedFile === void 0 ? void 0 : requestedFile.createdOn; } } createdBy = (_a = userProfiles.find(function (el) { return el.ownerId === createdBy; })) === null || _a === void 0 ? void 0 : _a.userName; return { fileName: fileName, createdBy: createdBy, createdOn: createdOn, contentSize: contentSize }; }; var sortDownLoadList = function (itemA, itemB, column, isDescending) { var _a = getFileHandleInfo(itemA), fileName_A = _a.fileName, createdBy_A = _a.createdBy, createdOn_A = _a.createdOn, contentSize_A = _a.contentSize; var _b = getFileHandleInfo(itemB), fileName_B = _b.fileName, createdBy_B = _b.createdBy, createdOn_B = _b.createdOn, contentSize_B = _b.contentSize; var direction = isDescending ? 1 : -1; switch (column) { case 'file': return (fileName_B === null || fileName_B === void 0 ? void 0 : fileName_B.localeCompare(fileName_A)) * direction; case 'createdBy': return (createdBy_B === null || createdBy_B === void 0 ? void 0 : createdBy_B.localeCompare(createdBy_A)) * direction; case 'createdOn': return (createdOn_B === null || createdOn_B === void 0 ? void 0 : createdOn_B.localeCompare(createdOn_A)) * direction; case 'size': if (contentSize_A && !contentSize_B) { return -1; } else if (contentSize_B && !contentSize_A) { return 1; } else { return (contentSize_B - contentSize_A) * direction; } default: return 1; } }; var filesToDownload = (_a = downloadList === null || downloadList === void 0 ? void 0 : downloadList.filesToDownload) !== null && _a !== void 0 ? _a : []; var results = (_b = references === null || references === void 0 ? void 0 : references.results) !== null && _b !== void 0 ? _b : []; var numBytes = 0; var numFiles = 0; var content = (react_1.default.createElement("div", { className: "DownloadListTable" }, react_1.default.createElement("div", { style: { display: arPropsFromHasAccess ? 'none' : '' } }, react_1.default.createElement("div", { className: "SRC-split download-list-table-top SRC-primary-background-color SRC-border-bottom-only" }, react_1.default.createElement("span", { className: "create-package-text" }, "Download List \u00A0\u00A0", isLoading && react_1.default.createElement("span", { className: "spinner" })), react_1.default.createElement("button", { className: "SRC-underline-on-hover uppercase-text", onClick: clearDownloadList, id: exports.TESTING_CLEAR_BTN_CLASS }, "Clear list")), react_1.default.createElement(ReactBootstrap.Table, { striped: true, responsive: true }, react_1.default.createElement("thead", null, react_1.default.createElement("tr", null, react_1.default.createElement("th", null, "File", react_1.default.createElement("button", { className: "sort SRC-primary-background-color-hover " + (sortedColumn.column === 'file' ? 'SRC-primary-background-color' : ''), onClick: function () { sortColumn('file'); } }, react_1.default.createElement(react_fontawesome_1.FontAwesomeIcon, { icon: sortedColumn.column === 'file' ? sortedColumn.isDescending === false ? free_solid_svg_icons_1.faSortAmountDown : free_solid_svg_icons_1.faSortAmountUp : free_solid_svg_icons_1.faSortAmountDown, color: sortedColumn.column === 'file' ? 'white' : '' }))), react_1.default.createElement("th", null, "Access"), react_1.default.createElement("th", null, "Created By", react_1.default.createElement("button", { className: "sort SRC-primary-background-color-hover " + (sortedColumn.column === 'createdBy' ? 'SRC-primary-background-color' : ''), onClick: function () { sortColumn('createdBy'); } }, react_1.default.createElement(react_fontawesome_1.FontAwesomeIcon, { icon: sortedColumn.column === 'createdBy' ? sortedColumn.isDescending === false ? free_solid_svg_icons_1.faSortAmountDown : free_solid_svg_icons_1.faSortAmountUp : free_solid_svg_icons_1.faSortAmountDown, color: sortedColumn.column === 'createdBy' ? 'white' : '' }))), react_1.default.createElement("th", null, "Created On", react_1.default.createElement("button", { className: "sort SRC-primary-background-color-hover " + (sortedColumn.column === 'createdOn' ? 'SRC-primary-background-color' : ''), onClick: function () { sortColumn('createdOn'); } }, react_1.default.createElement(react_fontawesome_1.FontAwesomeIcon, { icon: sortedColumn.column === 'createdOn' ? sortedColumn.isDescending === false ? free_solid_svg_icons_1.faSortAmountDown : free_solid_svg_icons_1.faSortAmountUp : free_solid_svg_icons_1.faSortAmountDown, color: sortedColumn.column === 'createdOn' ? 'white' : '' }))), react_1.default.createElement("th", null, "Size", react_1.default.createElement("button", { className: "sort SRC-primary-background-color-hover " + (sortedColumn.column === 'size' ? 'SRC-primary-background-color' : ''), onClick: function () { sortColumn('size'); } }, react_1.default.createElement(react_fontawesome_1.FontAwesomeIcon, { icon: sortedColumn.column === 'size' ? sortedColumn.isDescending === false ? free_solid_svg_icons_1.faSortAmountDown : free_solid_svg_icons_1.faSortAmountUp : free_solid_svg_icons_1.faSortAmountDown, color: sortedColumn.column === 'size' ? 'white' : '' }))), react_1.default.createElement("th", null))), react_1.default.createElement("tbody", { className: "download-list-table" }, filesToDownload.map(function (item) { var createdBy = ''; var createdOn = ''; var fileName = ''; var contentSize = undefined; var synId = item.associateObjectId; var fileHandleId = item.fileHandleId; var isCurrentlyBeingDeletedClass = fileBeingDeleted === fileHandleId ? 'SRC-inactive-bg' : ''; // See if batch file results has this fileHandleId var fileResult = requestedFiles.find(function (fileRes) { return fileRes.fileHandleId === fileHandleId; }); var fileHandle = fileResult === null || fileResult === void 0 ? void 0 : fileResult.fileHandle; var canDownload = fileHandle !== undefined; if (fileHandle) { // fileHandle is defined, this file is downloadable, show its metadata ; (createdBy = fileHandle.createdBy, createdOn = fileHandle.createdOn, fileName = fileHandle.fileName, contentSize = fileHandle.contentSize); if ((0, HasAccess_1.getDownloadTypeForFileHandle)(fileHandle) === HasAccess_1.FileHandleDownloadTypeEnum.Accessible) { numBytes += contentSize; numFiles += 1; } } else { // file is not downloadable, only show its name from entity header info var requestedFile = results.find(function (req) { return req.id === item.associateObjectId; }); fileName = requestedFile === null || requestedFile === void 0 ? void 0 : requestedFile.name; createdBy = requestedFile === null || requestedFile === void 0 ? void 0 : requestedFile.createdBy; createdOn = requestedFile === null || requestedFile === void 0 ? void 0 : requestedFile.createdOn; } createdOn = (0, moment_1.default)(createdOn).format('L LT'); var userProfile = userProfiles.find(function (el) { return el.ownerId === createdBy; }); return (react_1.default.createElement("tr", { className: isCurrentlyBeingDeletedClass, key: fileHandleId }, react_1.default.createElement("td", null, react_1.default.createElement("a", { target: "_blank", rel: "noopener noreferrer", href: getEndpoint_1.PRODUCTION_ENDPOINT_CONFIG.PORTAL + "#!Synapse:" + synId }, fileName)), react_1.default.createElement("td", null, react_1.default.createElement(HasAccess_1.default, { onHide: onHide, fileHandle: fileHandle, set_arPropsFromHasAccess: set_arPropsFromHasAccess, entityId: synId, isInDownloadList: true, forceSamePage: forceSamePage })), react_1.default.createElement("td", null, userProfile && (react_1.default.createElement(UserCard_1.default, { size: 'SMALL USER CARD', userProfile: userProfile, preSignedURL: userProfile.clientPreSignedURL })), canDownload && !userProfile && (react_1.default.createElement("span", { className: "spinner" }))), react_1.default.createElement("td", null, createdOn), react_1.default.createElement("td", null, contentSize && (0, calculateFriendlyFileSize_1.calculateFriendlyFileSize)(contentSize)), react_1.default.createElement("td", null, react_1.default.createElement("button", { className: exports.TESTING_TRASH_BTN_CLASS, onClick: fileBeingDeleted === '' ? function () { return deleteFileFromList(fileHandleId, synId); } : undefined }, react_1.default.createElement(react_fontawesome_1.FontAwesomeIcon, { className: "SRC-primary-text-color", icon: "trash" }))))); }))), react_1.default.createElement(CreatePackage_1.CreatePackage, { updateDownloadList: fetchData }, react_1.default.createElement(DownloadDetails_1.default, { numBytes: numBytes, numFiles: numFiles }))), arPropsFromHasAccess && (react_1.default.createElement(AccessRequirementList_1.default, (0, tslib_1.__assign)({}, arPropsFromHasAccess, { onHide: function () { set_arPropsFromHasAccess(undefined); } }))))); var onHideModal = (0, react_1.useCallback)(function () { if (arPropsFromHasAccess) { set_arPropsFromHasAccess(undefined); } else { onHide === null || onHide === void 0 ? void 0 : onHide(); } }, [arPropsFromHasAccess, onHide]); if (renderAsModal) { var closeBtn = { position: 'absolute', top: 5, right: 20, zIndex: 10, }; return (react_1.default.createElement(ReactBootstrap.Modal, { centered: true, animation: false, size: 'lg', dialogClassName: 'download-list-modal-container', show: true }, react_1.default.createElement(ReactBootstrap.Modal.Header, null, react_1.default.createElement("button", { style: closeBtn, onClick: onHideModal }, react_1.default.createElement(react_fontawesome_1.FontAwesomeIcon, { style: { fontSize: '21px' }, icon: "times" }))), content)); } else { return content; } } exports.default = DownloadListTable; //# sourceMappingURL=DownloadListTable.js.map