From: Michal Klobukowski Date: Fri, 29 Jun 2018 14:41:35 +0000 (+0200) Subject: Replace go back item with browser back button support X-Git-Tag: 1.2.0~63^2~4 X-Git-Url: https://git.arvados.org/arvados-workbench2.git/commitdiff_plain/2d37867eccb0a76df1a285e7b7e32bbb13db99a1 Replace go back item with browser back button support Feature #13678 Arvados-DCO-1.1-Signed-off-by: Michal Klobukowski --- diff --git a/src/models/resource.ts b/src/models/resource.ts index 0f5fbc28..1dd5979b 100644 --- a/src/models/resource.ts +++ b/src/models/resource.ts @@ -16,15 +16,18 @@ export enum ResourceKind { PROJECT = "project", COLLECTION = "collection", PIPELINE = "pipeline", - LEVEL_UP = "", UNKNOWN = "unknown" } export function getResourceKind(itemKind: string) { switch (itemKind) { - case "arvados#project": return ResourceKind.PROJECT; - case "arvados#collection": return ResourceKind.COLLECTION; - case "arvados#pipeline": return ResourceKind.PIPELINE; + case "arvados#project": + case "arvados#group": + return ResourceKind.PROJECT; + case "arvados#collection": + return ResourceKind.COLLECTION; + case "arvados#pipeline": + return ResourceKind.PIPELINE; default: return ResourceKind.UNKNOWN; } diff --git a/src/store/navigation/navigation-action.ts b/src/store/navigation/navigation-action.ts index b811f9a2..a4b9a8f6 100644 --- a/src/store/navigation/navigation-action.ts +++ b/src/store/navigation/navigation-action.ts @@ -17,11 +17,9 @@ import { RootState } from "../store"; export const getResourceUrl = (resource: Resource): string => { switch (resource.kind) { - case ResourceKind.LEVEL_UP: return `/projects/${resource.ownerUuid}`; case ResourceKind.PROJECT: return `/projects/${resource.uuid}`; case ResourceKind.COLLECTION: return `/collections/${resource.uuid}`; - default: - return "#"; + default: return ""; } }; @@ -31,50 +29,45 @@ export enum ItemMode { ACTIVE } -export const setProjectItem = (itemId: string, itemKind = ResourceKind.PROJECT, itemMode = ItemMode.OPEN) => +export const setProjectItem = (itemId: string, itemMode: ItemMode) => (dispatch: Dispatch, getState: () => RootState) => { - const { projects } = getState(); - - let treeItem = findTreeItem(projects.items, itemId); - if (treeItem && itemKind === ResourceKind.LEVEL_UP) { - treeItem = findTreeItem(projects.items, treeItem.data.ownerUuid); - } + const { projects, router } = getState(); + const treeItem = findTreeItem(projects.items, itemId); if (treeItem) { - dispatch(projectActions.TOGGLE_PROJECT_TREE_ITEM_ACTIVE(treeItem.data.uuid)); - if (treeItem.status === TreeItemStatus.Loaded) { - dispatch(openProjectItem(treeItem.data, itemKind, itemMode)); - } else { - dispatch(getProjectList(itemId)) - .then(() => dispatch(openProjectItem(treeItem!.data, itemKind, itemMode))); + dispatch(sidePanelActions.RESET_SIDE_PANEL_ACTIVITY()); + + if (itemMode === ItemMode.OPEN || itemMode === ItemMode.BOTH) { + dispatch(projectActions.TOGGLE_PROJECT_TREE_ITEM_OPEN(treeItem.data.uuid)); } + + const resourceUrl = getResourceUrl({ ...treeItem.data }); + if (itemMode === ItemMode.ACTIVE || itemMode === ItemMode.BOTH) { - dispatch(getCollectionList(itemId)); + if (router.location && !router.location.pathname.includes(resourceUrl)) { + dispatch(push(resourceUrl)); + } + dispatch(projectActions.TOGGLE_PROJECT_TREE_ITEM_ACTIVE(treeItem.data.uuid)); } - } - }; -const openProjectItem = (resource: Resource, itemKind: ResourceKind, itemMode: ItemMode) => - (dispatch: Dispatch, getState: () => RootState) => { + const promise = treeItem.status === TreeItemStatus.Loaded + ? Promise.resolve() + : dispatch(getProjectList(itemId)); - const { collections, projects } = getState(); + promise + .then(() => dispatch(getCollectionList(itemId))) + .then(() => dispatch(() => { + const { projects, collections } = getState(); + dispatch(dataExplorerActions.SET_ITEMS({ + id: PROJECT_PANEL_ID, + items: projectPanelItems( + projects.items, + treeItem.data.uuid, + collections + ) + })); + })); - if (itemMode === ItemMode.OPEN || itemMode === ItemMode.BOTH) { - dispatch(projectActions.TOGGLE_PROJECT_TREE_ITEM_OPEN(resource.uuid)); } - - if (itemMode === ItemMode.ACTIVE || itemMode === ItemMode.BOTH) { - dispatch(sidePanelActions.RESET_SIDE_PANEL_ACTIVITY(resource.uuid)); - } - - dispatch(push(getResourceUrl({ ...resource, kind: itemKind }))); - dispatch(dataExplorerActions.SET_ITEMS({ - id: PROJECT_PANEL_ID, - items: projectPanelItems( - projects.items, - resource.uuid, - collections - ) - })); }; diff --git a/src/store/project/project-action.ts b/src/store/project/project-action.ts index 3c264d3e..35ff445e 100644 --- a/src/store/project/project-action.ts +++ b/src/store/project/project-action.ts @@ -14,7 +14,7 @@ const actions = unionize({ PROJECTS_SUCCESS: ofType<{ projects: Project[], parentItemId?: string }>(), TOGGLE_PROJECT_TREE_ITEM_OPEN: ofType(), TOGGLE_PROJECT_TREE_ITEM_ACTIVE: ofType(), - RESET_PROJECT_TREE_ACTIVITY: ofType(), + RESET_PROJECT_TREE_ACTIVITY: ofType() }, { tag: 'type', value: 'payload' diff --git a/src/store/project/project-reducer.ts b/src/store/project/project-reducer.ts index 0e2018b4..efef8099 100644 --- a/src/store/project/project-reducer.ts +++ b/src/store/project/project-reducer.ts @@ -132,6 +132,7 @@ const projectsReducer = (state: ProjectState = { items: [], currentItemId: "" }, resetTreeActivity(items); const item = findTreeItem(items, itemId); if (item) { + item.toggled = true; item.active = true; } return { diff --git a/src/store/side-panel/side-panel-action.ts b/src/store/side-panel/side-panel-action.ts index 32fa653b..6a83946c 100644 --- a/src/store/side-panel/side-panel-action.ts +++ b/src/store/side-panel/side-panel-action.ts @@ -7,7 +7,7 @@ import { default as unionize, ofType, UnionOf } from "unionize"; const actions = unionize({ TOGGLE_SIDE_PANEL_ITEM_OPEN: ofType(), TOGGLE_SIDE_PANEL_ITEM_ACTIVE: ofType(), - RESET_SIDE_PANEL_ACTIVITY: ofType(), + RESET_SIDE_PANEL_ACTIVITY: ofType<{}>(), }, { tag: 'type', value: 'payload' diff --git a/src/views/project-panel/project-panel-selectors.ts b/src/views/project-panel/project-panel-selectors.ts index 5571e912..ee039a80 100644 --- a/src/views/project-panel/project-panel-selectors.ts +++ b/src/views/project-panel/project-panel-selectors.ts @@ -15,15 +15,6 @@ export const projectPanelItems = (projects: Array>, treeItemId const treeItem = findTreeItem(projects, treeItemId); if (treeItem) { - dataItems.push({ - name: "..", - url: getResourceUrl(treeItem.data), - kind: ResourceKind.LEVEL_UP, - owner: "", - uuid: treeItem.data.uuid, - lastModified: "" - }); - if (treeItem.items) { treeItem.items.forEach(p => { const item = { diff --git a/src/views/project-panel/project-panel.tsx b/src/views/project-panel/project-panel.tsx index dbff20e1..0cd74ff9 100644 --- a/src/views/project-panel/project-panel.tsx +++ b/src/views/project-panel/project-panel.tsx @@ -12,12 +12,18 @@ import { DataTableFilterItem } from '../../components/data-table-filters/data-ta import { ContextMenuAction } from '../../components/context-menu/context-menu'; import { DispatchProp, connect } from 'react-redux'; import actions from "../../store/data-explorer/data-explorer-action"; -import { setProjectItem } from "../../store/navigation/navigation-action"; +import { setProjectItem, ItemMode } from "../../store/navigation/navigation-action"; import { DataColumns } from '../../components/data-table/data-table'; import { ResourceKind } from "../../models/resource"; +import { RouteComponentProps } from 'react-router'; export const PROJECT_PANEL_ID = "projectPanel"; -class ProjectPanel extends React.Component> { + +type ProjectPanelProps = { onItemOpen: (itemId: string) => void } + & DispatchProp + & WithStyles + & RouteComponentProps<{ id: string }>; +class ProjectPanel extends React.Component { render() { return
@@ -49,6 +55,12 @@ class ProjectPanel extends React.Component> this.props.dispatch(actions.SET_COLUMNS({ id: PROJECT_PANEL_ID, columns })); } + componentWillReceiveProps(nextProps: ProjectPanelProps) { + if (this.props.match.params.id !== nextProps.match.params.id) { + this.props.onItemOpen(nextProps.match.params.id); + } + } + toggleColumn = (toggledColumn: DataColumn) => { this.props.dispatch(actions.TOGGLE_COLUMN({ id: PROJECT_PANEL_ID, columnName: toggledColumn.name })); } @@ -78,7 +90,7 @@ class ProjectPanel extends React.Component> } openProject = (item: ProjectPanelItem) => { - this.props.dispatch(setProjectItem(item.uuid)); + this.props.onItemOpen(item.uuid); } } @@ -113,8 +125,6 @@ const renderName = (item: ProjectPanelItem) => const renderIcon = (item: ProjectPanelItem) => { switch (item.kind) { - case ResourceKind.LEVEL_UP: - return ; case ResourceKind.PROJECT: return ; case ResourceKind.COLLECTION: diff --git a/src/views/workbench/workbench.tsx b/src/views/workbench/workbench.tsx index 72eb0ddc..c095868f 100644 --- a/src/views/workbench/workbench.tsx +++ b/src/views/workbench/workbench.tsx @@ -6,7 +6,7 @@ import * as React from 'react'; import { StyleRulesCallback, Theme, WithStyles, withStyles } from '@material-ui/core/styles'; import Drawer from '@material-ui/core/Drawer'; import { connect, DispatchProp } from "react-redux"; -import { Route, Switch } from "react-router"; +import { Route, Switch, RouteComponentProps } from "react-router"; import authActions from "../../store/auth/auth-action"; import dataExplorerActions from "../../store/data-explorer/data-explorer-action"; import { User } from "../../models/user"; @@ -133,7 +133,7 @@ class Workbench extends React.Component { mainAppBarActions: MainAppBarActionProps = { onBreadcrumbClick: ({ itemId }: NavBreadcrumb) => { - this.props.dispatch(setProjectItem(itemId, ResourceKind.PROJECT, ItemMode.BOTH)); + this.props.dispatch(setProjectItem(itemId, ItemMode.BOTH)); }, onSearch: searchText => { this.setState({ searchText }); @@ -152,12 +152,12 @@ class Workbench extends React.Component { } render() { - const branch = getTreePath(this.props.projects, this.props.currentProjectId); - const breadcrumbs = branch.map(item => ({ + const path = getTreePath(this.props.projects, this.props.currentProjectId); + const breadcrumbs = path.map(item => ({ label: item.data.name, itemId: item.data.uuid, status: item.status - })); + })); const { classes, user } = this.props; return ( @@ -186,11 +186,11 @@ class Workbench extends React.Component { projects={this.props.projects} toggleOpen={itemId => this.props.dispatch( - setProjectItem(itemId, ResourceKind.PROJECT, ItemMode.OPEN) + setProjectItem(itemId, ItemMode.OPEN) )} toggleActive={itemId => this.props.dispatch( - setProjectItem(itemId, ResourceKind.PROJECT, ItemMode.ACTIVE) + setProjectItem(itemId, ItemMode.ACTIVE) )} /> @@ -198,13 +198,20 @@ class Workbench extends React.Component {
- +
); } + + renderProjectPanel = (props: RouteComponentProps) => + this.props.dispatch( + setProjectItem(itemId, ItemMode.ACTIVE) + )} + {...props} /> } export default connect(