import { Dispatch } from 'redux';
import { RootState } from '~/store/store';
import { getResource, getResourceWithEditableStatus } from '../resources/resources';
-import { ProjectResource } from '~/models/project';
import { UserResource } from '~/models/user';
import { isSidePanelTreeCategory } from '~/store/side-panel-tree/side-panel-tree-actions';
import { extractUuidKind, ResourceKind, EditableResource } from '~/models/resource';
import { VirtualMachinesResource } from '~/models/virtual-machines';
import { KeepServiceResource } from '~/models/keep-services';
import { ProcessResource } from '~/models/process';
+import { CollectionResource } from '~/models/collection';
+import { GroupResource } from '~/models/group';
+import { GroupContentsResource } from '~/services/groups-service/groups-service';
export const contextMenuActions = unionize({
OPEN_CONTEXT_MENU: ofType<{ position: ContextMenuPosition, resource: ContextMenuResource }>(),
export const openProjectContextMenu = (event: React.MouseEvent<HTMLElement>, resourceUuid: string) =>
(dispatch: Dispatch, getState: () => RootState) => {
- const { isAdmin, uuid: userUuid } = getState().auth.user!;
- const res = getResourceWithEditableStatus<ProjectResource & EditableResource>(resourceUuid, userUuid)(getState().resources);
- const menuKind = resourceKindToContextMenuKind(resourceUuid, isAdmin, (res || {} as EditableResource).isEditable);
+ const res = getResource<GroupContentsResource>(resourceUuid)(getState().resources);
+ const menuKind = dispatch<any>(resourceUuidToContextMenuKind(resourceUuid));
if (res && menuKind) {
dispatch<any>(openContextMenu(event, {
name: res.name,
kind: res.kind,
menuKind,
ownerUuid: res.ownerUuid,
- isTrashed: res.isTrashed
+ isTrashed: ('isTrashed' in res) ? res.isTrashed: false,
}));
}
};
}
};
-export const resourceKindToContextMenuKind = (uuid: string, isAdmin?: boolean, isEditable?: boolean) => {
- const kind = extractUuidKind(uuid);
- switch (kind) {
- case ResourceKind.PROJECT:
- return !isAdmin
- ? isEditable
- ? ContextMenuKind.PROJECT
- : ContextMenuKind.READONLY_PROJECT
- : ContextMenuKind.PROJECT_ADMIN;
- case ResourceKind.COLLECTION:
- return !isAdmin
- ? isEditable
- ? ContextMenuKind.COLLECTION
- : ContextMenuKind.READONLY_COLLECTION
- : ContextMenuKind.COLLECTION_ADMIN;
- case ResourceKind.PROCESS:
- return !isAdmin
- ? ContextMenuKind.PROCESS_RESOURCE
- : ContextMenuKind.PROCESS_ADMIN;
- case ResourceKind.USER:
- return ContextMenuKind.ROOT_PROJECT;
- case ResourceKind.LINK:
- return ContextMenuKind.LINK;
- default:
- return;
- }
-};
+export const resourceUuidToContextMenuKind = (uuid: string) =>
+ (dispatch: Dispatch, getState: () => RootState) => {
+ const { isAdmin, uuid: userUuid } = getState().auth.user!;
+ const kind = extractUuidKind(uuid);
+ const resource = getResourceWithEditableStatus<GroupResource & EditableResource>(uuid, userUuid)(getState().resources);
+ const isEditable = (resource || {} as EditableResource).isEditable;
+ switch (kind) {
+ case ResourceKind.PROJECT:
+ return !isAdmin
+ ? isEditable
+ ? ContextMenuKind.PROJECT
+ : ContextMenuKind.READONLY_PROJECT
+ : ContextMenuKind.PROJECT_ADMIN;
+ case ResourceKind.COLLECTION:
+ const c = getResource<CollectionResource>(uuid)(getState().resources);
+ if (c === undefined) { return; }
+ const isOldVersion = c.uuid !== c.currentVersionUuid;
+ const isTrashed = c.isTrashed;
+ return (isTrashed && isEditable)
+ ? ContextMenuKind.TRASHED_COLLECTION
+ : isOldVersion
+ ? ContextMenuKind.OLD_VERSION_COLLECTION
+ : isAdmin
+ ? ContextMenuKind.COLLECTION_ADMIN
+ : isEditable
+ ? ContextMenuKind.COLLECTION
+ : ContextMenuKind.READONLY_COLLECTION;
+ case ResourceKind.PROCESS:
+ return !isAdmin
+ ? ContextMenuKind.PROCESS_RESOURCE
+ : ContextMenuKind.PROCESS_ADMIN;
+ case ResourceKind.USER:
+ return ContextMenuKind.ROOT_PROJECT;
+ case ResourceKind.LINK:
+ return ContextMenuKind.LINK;
+ default:
+ return;
+ }
+ };
// SPDX-License-Identifier: AGPL-3.0
import * as React from 'react';
-import { StyleRulesCallback, WithStyles, withStyles, Grid, Button } from '@material-ui/core';
+import {
+ StyleRulesCallback,
+ WithStyles,
+ withStyles,
+ Grid,
+ Button
+} from '@material-ui/core';
import { CollectionIcon } from '~/components/icon/icon';
import { ArvadosTheme } from '~/common/custom-theme';
import { BackIcon } from '~/components/icon/icon';
import { COLLECTIONS_CONTENT_ADDRESS_PANEL_ID } from '~/store/collections-content-address-panel/collections-content-address-panel-actions';
import { DataExplorer } from "~/views-components/data-explorer/data-explorer";
import { Dispatch } from 'redux';
-import { getIsAdmin } from '~/store/public-favorites/public-favorites-actions';
-import { resourceKindToContextMenuKind, openContextMenu } from '~/store/context-menu/context-menu-actions';
+import {
+ resourceUuidToContextMenuKind,
+ openContextMenu
+} from '~/store/context-menu/context-menu-actions';
import { ResourceKind } from '~/models/resource';
import { loadDetailsPanel } from '~/store/details-panel/details-panel-action';
import { connect } from 'react-redux';
import { DataColumns } from '~/components/data-table/data-table';
import { SortDirection } from '~/components/data-table/data-column';
import { createTree } from '~/models/tree';
-import { ResourceName, ResourceOwnerName, ResourceLastModifiedDate, ResourceStatus } from '~/views-components/data-explorer/renderers';
+import {
+ ResourceName,
+ ResourceOwnerName,
+ ResourceLastModifiedDate,
+ ResourceStatus
+} from '~/views-components/data-explorer/renderers';
type CssRules = 'backLink' | 'backIcon' | 'card' | 'title' | 'iconHeader' | 'link';
const mapDispatchToProps = (dispatch: Dispatch): CollectionContentAddressPanelActionProps => ({
onContextMenu: (event, resourceUuid) => {
- const isAdmin = dispatch<any>(getIsAdmin());
- const kind = resourceKindToContextMenuKind(resourceUuid, isAdmin);
+ const kind = dispatch<any>(resourceUuidToContextMenuKind(resourceUuid));
if (kind) {
dispatch<any>(openContextMenu(event, {
name: '',
import { CollectionTagForm } from './collection-tag-form';
import { deleteCollectionTag, navigateToProcess, collectionPanelActions } from '~/store/collection-panel/collection-panel-action';
import { getResource } from '~/store/resources/resources';
-import { openContextMenu } from '~/store/context-menu/context-menu-actions';
-import { ContextMenuKind } from '~/views-components/context-menu/context-menu';
+import { openContextMenu, resourceUuidToContextMenuKind } from '~/store/context-menu/context-menu-actions';
import { formatDate, formatFileSize } from "~/common/formatters";
import { openDetailsPanel } from '~/store/details-panel/details-panel-action';
import { snackbarActions, SnackbarKind } from '~/store/snackbar/snackbar-actions';
}
handleContextMenu = (event: React.MouseEvent<any>) => {
- const { uuid, ownerUuid, name, description, kind, isTrashed } = this.props.item;
- const { isWritable } = this.props;
+ const { uuid, ownerUuid, name, description, kind } = this.props.item;
+ const menuKind = this.props.dispatch<any>(resourceUuidToContextMenuKind(uuid));
const resource = {
uuid,
ownerUuid,
name,
description,
kind,
- menuKind: isWritable
- ? isTrashed
- ? ContextMenuKind.TRASHED_COLLECTION
- : ContextMenuKind.COLLECTION
- : ContextMenuKind.READONLY_COLLECTION
+ menuKind,
};
// Avoid expanding/collapsing the panel
event.stopPropagation();
import { RouteComponentProps } from 'react-router';
import { DataTableFilterItem } from '~/components/data-table-filters/data-table-filters';
import { SortDirection } from '~/components/data-table/data-column';
-import { ResourceKind, EditableResource } from '~/models/resource';
+import { ResourceKind } from '~/models/resource';
import { ArvadosTheme } from '~/common/custom-theme';
import { FAVORITE_PANEL_ID } from "~/store/favorite-panel/favorite-panel-action";
import {
ResourceType
} from '~/views-components/data-explorer/renderers';
import { FavoriteIcon } from '~/components/icon/icon';
-import { openContextMenu, resourceKindToContextMenuKind } from '~/store/context-menu/context-menu-actions';
+import {
+ openContextMenu,
+ resourceUuidToContextMenuKind
+} from '~/store/context-menu/context-menu-actions';
import { loadDetailsPanel } from '~/store/details-panel/details-panel-action';
import { navigateTo } from '~/store/navigation/navigation-action';
import { ContainerRequestState } from "~/models/container-request";
import { DataTableDefaultView } from '~/components/data-table-default-view/data-table-default-view';
import { createTree } from '~/models/tree';
import { getSimpleObjectTypeFilters } from '~/store/resource-type-filters/resource-type-filters';
-import { getResourceWithEditableStatus, ResourcesState } from '~/store/resources/resources';
-import { ProjectResource } from '~/models/project';
+import { ResourcesState } from '~/store/resources/resources';
type CssRules = "toolbar" | "button";
interface FavoritePanelDataProps {
favorites: FavoritesState;
resources: ResourcesState;
- isAdmin: boolean;
userUuid: string;
}
const mapStateToProps = (state : RootState): FavoritePanelDataProps => ({
favorites: state.favorites,
resources: state.resources,
- isAdmin: state.auth.user!.isAdmin,
userUuid: state.auth.user!.uuid,
});
class extends React.Component<FavoritePanelProps> {
handleContextMenu = (event: React.MouseEvent<HTMLElement>, resourceUuid: string) => {
- const { isAdmin, userUuid, resources } = this.props;
- const resource = getResourceWithEditableStatus<ProjectResource & EditableResource>(resourceUuid, userUuid)(resources);
- const menuKind = resourceKindToContextMenuKind(resourceUuid, isAdmin, (resource || {} as EditableResource).isEditable);
+ const menuKind = this.props.dispatch<any>(resourceUuidToContextMenuKind(resourceUuid));
if (menuKind) {
this.props.dispatch<any>(openContextMenu(event, {
name: '',
import { Dispatch } from "redux";
import { connect } from "react-redux";
import { RootState } from '~/store/store';
-import { openContextMenu, resourceKindToContextMenuKind } from '~/store/context-menu/context-menu-actions';
-import { LinkPanelRoot, LinkPanelRootActionProps, LinkPanelRootDataProps } from '~/views/link-panel/link-panel-root';
+import {
+ openContextMenu,
+ resourceUuidToContextMenuKind
+} from '~/store/context-menu/context-menu-actions';
+import {
+ LinkPanelRoot,
+ LinkPanelRootActionProps,
+ LinkPanelRootDataProps
+} from '~/views/link-panel/link-panel-root';
import { ResourceKind } from '~/models/resource';
const mapStateToProps = (state: RootState): LinkPanelRootDataProps => {
const mapDispatchToProps = (dispatch: Dispatch): LinkPanelRootActionProps => ({
onContextMenu: (event, resourceUuid) => {
- const kind = resourceKindToContextMenuKind(resourceUuid);
+ const kind = dispatch<any>(resourceUuidToContextMenuKind(resourceUuid));
if (kind) {
dispatch<any>(openContextMenu(event, {
name: '',
import { DataTableFilterItem } from '~/components/data-table-filters/data-table-filters';
import { ContainerRequestState } from '~/models/container-request';
import { SortDirection } from '~/components/data-table/data-column';
-import { ResourceKind, Resource, EditableResource } from '~/models/resource';
+import { ResourceKind, Resource } from '~/models/resource';
import {
ResourceFileSize,
ResourceLastModifiedDate,
} from '~/views-components/data-explorer/renderers';
import { ProjectIcon } from '~/components/icon/icon';
import { ResourceName } from '~/views-components/data-explorer/renderers';
-import { ResourcesState, getResourceWithEditableStatus } from '~/store/resources/resources';
+import {
+ ResourcesState,
+ getResource
+} from '~/store/resources/resources';
import { loadDetailsPanel } from '~/store/details-panel/details-panel-action';
-import { resourceKindToContextMenuKind, openContextMenu } from '~/store/context-menu/context-menu-actions';
-import { ProjectResource } from '~/models/project';
+import {
+ openContextMenu,
+ resourceUuidToContextMenuKind
+} from '~/store/context-menu/context-menu-actions';
import { navigateTo } from '~/store/navigation/navigation-action';
import { getProperty } from '~/store/properties/properties';
import { PROJECT_PANEL_CURRENT_UUID } from '~/store/project-panel/project-panel-action';
import { DataTableDefaultView } from '~/components/data-table-default-view/data-table-default-view';
import { ArvadosTheme } from "~/common/custom-theme";
import { createTree } from '~/models/tree';
-import { getInitialResourceTypeFilters, getInitialProcessStatusFilters } from '~/store/resource-type-filters/resource-type-filters';
+import {
+ getInitialResourceTypeFilters,
+ getInitialProcessStatusFilters
+} from '~/store/resource-type-filters/resource-type-filters';
+import { GroupContentsResource } from '~/services/groups-service/groups-service';
type CssRules = 'root' | "button";
connect((state: RootState) => ({
currentItemId: getProperty(PROJECT_PANEL_CURRENT_UUID)(state.properties),
resources: state.resources,
- isAdmin: state.auth.user!.isAdmin,
userUuid: state.auth.user!.uuid,
}))(
class extends React.Component<ProjectPanelProps> {
}
handleContextMenu = (event: React.MouseEvent<HTMLElement>, resourceUuid: string) => {
- const { isAdmin, userUuid, resources } = this.props;
- const resource = getResourceWithEditableStatus<ProjectResource & EditableResource>(resourceUuid, userUuid)(resources);
- const menuKind = resourceKindToContextMenuKind(resourceUuid, isAdmin, (resource || {} as EditableResource).isEditable);
+ const { resources } = this.props;
+ const resource = getResource<GroupContentsResource>(resourceUuid)(resources);
+ const menuKind = this.props.dispatch<any>(resourceUuidToContextMenuKind(resourceUuid));
if (menuKind && resource) {
this.props.dispatch<any>(openContextMenu(event, {
name: resource.name,
uuid: resource.uuid,
ownerUuid: resource.ownerUuid,
- isTrashed: resource.isTrashed,
+ isTrashed: ('isTrashed' in resource) ? resource.isTrashed: false,
kind: resource.kind,
menuKind
}));
} from '~/views-components/data-explorer/renderers';
import { PublicFavoriteIcon } from '~/components/icon/icon';
import { Dispatch } from 'redux';
-import { openContextMenu, resourceKindToContextMenuKind } from '~/store/context-menu/context-menu-actions';
+import {
+ openContextMenu,
+ resourceUuidToContextMenuKind
+} from '~/store/context-menu/context-menu-actions';
import { loadDetailsPanel } from '~/store/details-panel/details-panel-action';
import { navigateTo } from '~/store/navigation/navigation-action';
import { ContainerRequestState } from "~/models/container-request";
import { getSimpleObjectTypeFilters } from '~/store/resource-type-filters/resource-type-filters';
import { PUBLIC_FAVORITE_PANEL_ID } from '~/store/public-favorites-panel/public-favorites-action';
import { PublicFavoritesState } from '~/store/public-favorites/public-favorites-reducer';
-import { getIsAdmin } from '~/store/public-favorites/public-favorites-actions';
type CssRules = "toolbar" | "button";
const mapDispatchToProps = (dispatch: Dispatch): PublicFavoritePanelActionProps => ({
onContextMenu: (event, resourceUuid) => {
- const isAdmin = dispatch<any>(getIsAdmin());
- const kind = resourceKindToContextMenuKind(resourceUuid, isAdmin);
+ const kind = dispatch<any>(resourceUuidToContextMenuKind(resourceUuid));
if (kind) {
dispatch<any>(openContextMenu(event, {
name: '',
import { RootState } from '~/store/store';
import { ArvadosTheme } from '~/common/custom-theme';
import { ShareMeIcon } from '~/components/icon/icon';
-import { ResourcesState, getResourceWithEditableStatus } from '~/store/resources/resources';
+import { ResourcesState, getResource } from '~/store/resources/resources';
import { navigateTo } from "~/store/navigation/navigation-action";
import { loadDetailsPanel } from "~/store/details-panel/details-panel-action";
import { DataTableDefaultView } from '~/components/data-table-default-view/data-table-default-view';
import { SHARED_WITH_ME_PANEL_ID } from '~/store/shared-with-me-panel/shared-with-me-panel-actions';
-import { openContextMenu, resourceKindToContextMenuKind } from '~/store/context-menu/context-menu-actions';
-import { GroupResource } from '~/models/group';
-import { EditableResource } from '~/models/resource';
+import {
+ openContextMenu,
+ resourceUuidToContextMenuKind
+} from '~/store/context-menu/context-menu-actions';
+import { GroupContentsResource } from '~/services/groups-service/groups-service';
type CssRules = "toolbar" | "button";
interface SharedWithMePanelDataProps {
resources: ResourcesState;
- isAdmin: boolean;
userUuid: string;
}
export const SharedWithMePanel = withStyles(styles)(
connect((state: RootState) => ({
resources: state.resources,
- isAdmin: state.auth.user!.isAdmin,
userUuid: state.auth.user!.uuid,
}))(
class extends React.Component<SharedWithMePanelProps> {
}
handleContextMenu = (event: React.MouseEvent<HTMLElement>, resourceUuid: string) => {
- const { isAdmin, userUuid, resources } = this.props;
- const resource = getResourceWithEditableStatus<GroupResource & EditableResource>(resourceUuid, userUuid)(resources);
- const menuKind = resourceKindToContextMenuKind(resourceUuid, isAdmin, (resource || {} as EditableResource).isEditable);
+ const { resources } = this.props;
+ const resource = getResource<GroupContentsResource>(resourceUuid)(resources);
+ const menuKind = this.props.dispatch<any>(resourceUuidToContextMenuKind(resourceUuid));
if (menuKind && resource) {
this.props.dispatch<any>(openContextMenu(event, {
name: '',
uuid: resource.uuid,
ownerUuid: resource.ownerUuid,
- isTrashed: resource.isTrashed,
+ isTrashed: ('isTrashed' in resource) ? resource.isTrashed: false,
kind: resource.kind,
menuKind
}));