21224: user card admin menu up Arvados-DCO-1.1-Signed-off-by: Lisa Knox <lisa.knox...
[arvados.git] / services / workbench2 / src / components / multiselect-toolbar / MultiselectToolbar.tsx
index f92c0dcf4eb6147bd0d645532ca55c29e30d73cd..d10a6ba6158705eb26066d314701983c035595e8 100644 (file)
@@ -85,10 +85,11 @@ const styles: StyleRulesCallback<CssRules> = (theme: ArvadosTheme) => ({
 export type MultiselectToolbarProps = {
     checkedList: TCheckedList;
     singleSelectedUuid: string | null
+    inputSelectedUuid?: string
     iconProps: IconProps
     user: User | null
     disabledButtons: Set<string>
-    executeMulti: (action: ContextMenuAction, checkedList: TCheckedList, resources: ResourcesState) => void;
+    executeMulti: (action: ContextMenuAction, inputSelectedUuid: string | undefined, checkedList: TCheckedList, resources: ResourcesState) => void;
 };
 
 type IconProps = {
@@ -102,21 +103,27 @@ export const MultiselectToolbar = connect(
     mapDispatchToProps
 )(
     withStyles(styles)((props: MultiselectToolbarProps & WithStyles<CssRules>) => {
-        const { classes, checkedList, singleSelectedUuid, iconProps, user, disabledButtons } = props;
+        const { classes, checkedList, inputSelectedUuid, iconProps, user, disabledButtons } = props;
+        const singleSelectedUuid = inputSelectedUuid ?? props.singleSelectedUuid
         const singleResourceKind = singleSelectedUuid ? [resourceToMsResourceKind(singleSelectedUuid, iconProps.resources, user)] : null
         const currentResourceKinds = singleResourceKind ? singleResourceKind : Array.from(selectedToKindSet(checkedList));
         const currentPathIsTrash = window.location.pathname === "/trash";
         const [isTransitioning, setIsTransitioning] = useState(false);
+        let transitionTimeout;
         
         const handleTransition = () => {
             setIsTransitioning(true)
-            setTimeout(() => {
+            transitionTimeout = setTimeout(() => {
                 setIsTransitioning(false)
             }, WIDTH_TRANSITION);
         }
         
         useEffect(()=>{
                 handleTransition()
+                return () => {
+                    if(transitionTimeout) clearTimeout(transitionTimeout)
+                };
+            // eslint-disable-next-line
         }, [checkedList])
 
         const actions =
@@ -147,7 +154,7 @@ export const MultiselectToolbar = connect(
                                     <IconButton
                                         data-cy='multiselect-button'
                                         disabled={disabledButtons.has(name)}
-                                        onClick={() => props.executeMulti(action, checkedList, iconProps.resources)}
+                                        onClick={() => props.executeMulti(action, inputSelectedUuid, checkedList, iconProps.resources)}
                                     >
                                         {currentPathIsTrash || (useAlts && useAlts(singleSelectedUuid, iconProps)) ? altIcon && altIcon({}) : icon({})}
                                     </IconButton>
@@ -163,7 +170,7 @@ export const MultiselectToolbar = connect(
                                 <span className={classes.iconContainer}>
                                     <IconButton
                                         data-cy='multiselect-button'
-                                        onClick={() => props.executeMulti(action, checkedList, iconProps.resources)}
+                                        onClick={() => props.executeMulti(action, inputSelectedUuid, checkedList, iconProps.resources)}
                                     >
                                         {action.icon({})}
                                     </IconButton>
@@ -265,7 +272,7 @@ const resourceToMsResourceKind = (uuid: string, resources: ResourcesState, user:
                 ? msMenuResourceKind.RUNNING_PROCESS_RESOURCE
                 : msMenuResourceKind.PROCESS_RESOURCE;
         case ResourceKind.USER:
-            return msMenuResourceKind.ROOT_PROJECT;
+            return isAdmin ? msMenuResourceKind.ROOT_PROJECT_ADMIN : msMenuResourceKind.ROOT_PROJECT;
         case ResourceKind.LINK:
             return msMenuResourceKind.LINK;
         case ResourceKind.WORKFLOW:
@@ -337,17 +344,18 @@ function mapStateToProps({auth, multiselect, resources, favorites, publicFavorit
 
 function mapDispatchToProps(dispatch: Dispatch) {
     return {
-        executeMulti: (selectedAction: ContextMenuAction, checkedList: TCheckedList, resources: ResourcesState): void => {
-            const kindGroups = groupByKind(checkedList, resources);
+        executeMulti: (selectedAction: ContextMenuAction, inputSelectedUuid: string | undefined, checkedList: TCheckedList, resources: ResourcesState): void => {
+            const kindGroups = inputSelectedUuid ? groupByKind({[inputSelectedUuid]: true}, resources) : groupByKind(checkedList, resources);
+            const currentList = inputSelectedUuid ? [inputSelectedUuid] : selectedToArray(checkedList)
             switch (selectedAction.name) {
                 case MultiSelectMenuActionNames.MOVE_TO:
                 case MultiSelectMenuActionNames.REMOVE:
-                    const firstResource = getResource(selectedToArray(checkedList)[0])(resources) as ContainerRequestResource | Resource;
+                    const firstResource = getResource(currentList[0])(resources) as ContainerRequestResource | Resource;
                     const action = findActionByName(selectedAction.name as string, kindToActionSet[firstResource.kind]);
                     if (action) action.execute(dispatch, kindGroups[firstResource.kind]);
                     break;
                 case MultiSelectMenuActionNames.COPY_TO_CLIPBOARD:
-                    const selectedResources = selectedToArray(checkedList).map(uuid => getResource(uuid)(resources));
+                    const selectedResources = currentList.map(uuid => getResource(uuid)(resources));
                     dispatch<any>(copyToClipboardAction(selectedResources));
                     break;
                 default: