[ARVADOS-WORKBENCH2] updated: 1.1.4-119-g6e44781

Git user git at public.curoverse.com
Mon Jun 25 17:51:06 EDT 2018


Summary of changes:
 src/components/tree/tree.tsx                       |  8 +--
 src/index.tsx                                      |  6 +-
 src/models/resource.ts                             |  6 +-
 .../collection-service/collection-service.ts       |  3 +-
 src/services/project-service/project-service.ts    |  3 +-
 src/store/collection/collection-reducer.test.ts    |  5 +-
 src/store/navigation/navigation-action.ts          | 47 +++++++++++++
 src/store/project/project-reducer.test.ts          |  5 +-
 src/store/project/project-reducer.ts               | 45 ++++++++----
 .../data-explorer/data-explorer.tsx                |  4 +-
 src/views-components/data-explorer/data-item.ts    |  4 +-
 src/views-components/project-tree/project-tree.tsx |  2 +-
 src/views/data-explorer/data-explorer-selectors.ts | 18 +++--
 src/views/data-explorer/data-explorer.tsx          | 20 +++---
 src/views/workbench/workbench.tsx                  | 79 ++++++++++------------
 tslint.json                                        |  3 +-
 16 files changed, 163 insertions(+), 95 deletions(-)
 create mode 100644 src/store/navigation/navigation-action.ts

       via  6e44781d01db889030cc5f7819aa7f15fe837e19 (commit)
      from  969254757ab4c21840faedf2bd1e4297c35203ac (commit)

Those revisions listed above that are new to this repository have
not appeared on any other notification email; so we list those
revisions in full, below.


commit 6e44781d01db889030cc5f7819aa7f15fe837e19
Author: Daniel Kos <daniel.kos at contractors.roche.com>
Date:   Mon Jun 25 13:38:23 2018 +0200

    Added central action for navigation
    
    Feature #13666
    
    Arvados-DCO-1.1-Signed-off-by: Daniel Kos <daniel.kos at contractors.roche.com>

diff --git a/src/components/tree/tree.tsx b/src/components/tree/tree.tsx
index 6731950..0e69554 100644
--- a/src/components/tree/tree.tsx
+++ b/src/components/tree/tree.tsx
@@ -61,17 +61,17 @@ export interface TreeItem<T> {
 interface TreeProps<T> {
     items?: Array<TreeItem<T>>;
     render: (item: TreeItem<T>, level?: number) => ReactElement<{}>;
-    toggleItem: (id: string, status: TreeItemStatus) => any;
+    toggleItem: (itemId: string) => any;
     level?: number;
 }
 
 class Tree<T> extends React.Component<TreeProps<T> & WithStyles<CssRules>, {}> {
     renderArrow(status: TreeItemStatus, arrowClass: string, open: boolean, id: string) {
         return <i
-            onClick={() => this.props.toggleItem(id, status)}
+            onClick={() => this.props.toggleItem(id)}
             className={`
-                ${arrowClass} 
-                ${status === TreeItemStatus.Pending ? this.props.classes.arrowVisibility : ''} 
+                ${arrowClass}
+                ${status === TreeItemStatus.Pending ? this.props.classes.arrowVisibility : ''}
                 ${open ? `fas fa-caret-down ${this.props.classes.arrowTransition}` : `fas fa-caret-down ${this.props.classes.arrowRotate}`}`} />;
     }
     render(): ReactElement<any> {
diff --git a/src/index.tsx b/src/index.tsx
index 28f8300..0cd443b 100644
--- a/src/index.tsx
+++ b/src/index.tsx
@@ -19,8 +19,10 @@ import { getProjectList } from "./store/project/project-action";
 const history = createBrowserHistory();
 
 const store = configureStore({
-    projects: [
-    ],
+    projects: {
+        items: [],
+        currentItemId: ""
+    },
     collections: [
     ],
     router: {
diff --git a/src/models/resource.ts b/src/models/resource.ts
index 4c198fb..28bb349 100644
--- a/src/models/resource.ts
+++ b/src/models/resource.ts
@@ -1,3 +1,7 @@
+// Copyright (C) The Arvados Authors. All rights reserved.
+//
+// SPDX-License-Identifier: AGPL-3.0
+
 export interface Resource {
     name: string;
     createdAt: string;
@@ -5,7 +9,7 @@ export interface Resource {
     uuid: string;
     ownerUuid: string;
     href: string;
-    kind: string;
+    kind: ResourceKind;
 }
 
 export enum ResourceKind {
diff --git a/src/services/collection-service/collection-service.ts b/src/services/collection-service/collection-service.ts
index 171cd85..bc91281 100644
--- a/src/services/collection-service/collection-service.ts
+++ b/src/services/collection-service/collection-service.ts
@@ -6,6 +6,7 @@ import { serverApi } from "../../common/api/server-api";
 import FilterBuilder, { FilterField } from "../../common/api/filter-builder";
 import { ArvadosResource } from "../response";
 import { Collection } from "../../models/collection";
+import { getResourceKind } from "../../models/resource";
 
 interface CollectionResource extends ArvadosResource {
     name: string;
@@ -42,7 +43,7 @@ export default class CollectionService {
                     href: g.href,
                     uuid: g.uuid,
                     ownerUuid: g.owner_uuid,
-                    kind: g.kind
+                    kind: getResourceKind(g.kind)
                 } as Collection));
                 return collections;
             });
diff --git a/src/services/project-service/project-service.ts b/src/services/project-service/project-service.ts
index bc34081..5bfa544 100644
--- a/src/services/project-service/project-service.ts
+++ b/src/services/project-service/project-service.ts
@@ -7,6 +7,7 @@ import { Dispatch } from "redux";
 import { Project } from "../../models/project";
 import FilterBuilder, { FilterField } from "../../common/api/filter-builder";
 import { ArvadosResource } from "../response";
+import { getResourceKind } from "../../models/resource";
 
 interface GroupResource extends ArvadosResource {
     name: string;
@@ -39,7 +40,7 @@ export default class ProjectService {
                     href: g.href,
                     uuid: g.uuid,
                     ownerUuid: g.owner_uuid,
-                    kind: g.kind
+                    kind: getResourceKind(g.kind)
                 } as Project));
                 return projects;
             });
diff --git a/src/store/collection/collection-reducer.test.ts b/src/store/collection/collection-reducer.test.ts
index 7b57ba7..7bc1aec 100644
--- a/src/store/collection/collection-reducer.test.ts
+++ b/src/store/collection/collection-reducer.test.ts
@@ -4,6 +4,7 @@
 
 import collectionsReducer from "./collection-reducer";
 import actions from "./collection-action";
+import { ResourceKind } from "../../models/resource";
 
 describe('collection-reducer', () => {
     it('should add new collection to the list', () => {
@@ -15,7 +16,7 @@ describe('collection-reducer', () => {
             modifiedAt: '2018-01-01',
             ownerUuid: 'owner-test123',
             uuid: 'test123',
-            kind: ""
+            kind: ResourceKind.COLLECTION
         };
 
         const state = collectionsReducer(initialState, actions.CREATE_COLLECTION(collection));
@@ -31,7 +32,7 @@ describe('collection-reducer', () => {
             modifiedAt: '2018-01-01',
             ownerUuid: 'owner-test123',
             uuid: 'test123',
-            kind: ""
+            kind: ResourceKind.COLLECTION
         };
 
         const collections = [collection, collection];
diff --git a/src/store/navigation/navigation-action.ts b/src/store/navigation/navigation-action.ts
new file mode 100644
index 0000000..80318ec
--- /dev/null
+++ b/src/store/navigation/navigation-action.ts
@@ -0,0 +1,47 @@
+// Copyright (C) The Arvados Authors. All rights reserved.
+//
+// SPDX-License-Identifier: AGPL-3.0
+
+import { Dispatch } from "redux";
+import projectActions, { getProjectList } from "../project/project-action";
+import { push } from "react-router-redux";
+import { TreeItem, TreeItemStatus } from "../../components/tree/tree";
+import { getCollectionList } from "../collection/collection-action";
+import { findTreeItem } from "../project/project-reducer";
+import { Project } from "../../models/project";
+import { Resource, ResourceKind } from "../../models/resource";
+
+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 "#";
+    }
+};
+
+export const setProjectItem = (projects: Array<TreeItem<Project>>, itemId: string, itemKind: ResourceKind) => (dispatch: Dispatch) => {
+
+    const openProjectItem = (resource: Resource) => {
+        dispatch(projectActions.TOGGLE_PROJECT_TREE_ITEM(resource.uuid));
+        dispatch(push(getResourceUrl({...resource, kind: itemKind})));
+    };
+    const treeItem = findTreeItem(projects, itemId);
+
+    if (treeItem) {
+        if (treeItem.status === TreeItemStatus.Loaded) {
+            openProjectItem(treeItem.data);
+        } else {
+            dispatch<any>(getProjectList(itemId))
+                .then(() => openProjectItem(treeItem.data));
+        }
+        dispatch<any>(getCollectionList(itemId));
+
+        // if (item.type === ResourceKind.PROJECT || item.type === ResourceKind.LEVEL_UP) {
+        //     this.props.dispatch(projectActions.TOGGLE_PROJECT_TREE_ITEM(item.uuid));
+        // }
+        // this.props.dispatch<any>(getCollectionList(item.uuid));
+
+    }
+};
diff --git a/src/store/project/project-reducer.test.ts b/src/store/project/project-reducer.test.ts
index f964e0e..8082809 100644
--- a/src/store/project/project-reducer.test.ts
+++ b/src/store/project/project-reducer.test.ts
@@ -5,6 +5,7 @@
 import projectsReducer, { getTreePath } from "./project-reducer";
 import actions from "./project-action";
 import { TreeItem, TreeItemStatus } from "../../components/tree/tree";
+import { ResourceKind } from "../../models/resource";
 
 describe('project-reducer', () => {
     it('should add new project to the list', () => {
@@ -16,7 +17,7 @@ describe('project-reducer', () => {
             modifiedAt: '2018-01-01',
             ownerUuid: 'owner-test123',
             uuid: 'test123',
-            kind: ""
+            kind: ResourceKind.PROJECT
         };
 
         const state = projectsReducer(initialState, actions.CREATE_PROJECT(project));
@@ -32,7 +33,7 @@ describe('project-reducer', () => {
             modifiedAt: '2018-01-01',
             ownerUuid: 'owner-test123',
             uuid: 'test123',
-            kind: ""
+            kind: ResourceKind.PROJECT
         };
 
         const projects = [project, project];
diff --git a/src/store/project/project-reducer.ts b/src/store/project/project-reducer.ts
index 2c74eb2..a40d48d 100644
--- a/src/store/project/project-reducer.ts
+++ b/src/store/project/project-reducer.ts
@@ -7,7 +7,10 @@ import actions, { ProjectAction } from "./project-action";
 import { TreeItem, TreeItemStatus } from "../../components/tree/tree";
 import * as _ from "lodash";
 
-export type ProjectState = Array<TreeItem<Project>>;
+export type ProjectState = {
+    items: Array<TreeItem<Project>>,
+    currentItemId: string
+};
 
 export function findTreeItem<T>(tree: Array<TreeItem<T>>, itemId: string): TreeItem<T> | undefined {
     let item;
@@ -64,7 +67,7 @@ function updateProjectTree(tree: Array<TreeItem<Project>>, projects: Project[],
             treeItem.status = TreeItemStatus.Loaded;
         }
     }
-    const items = projects.map((p, idx) => ({
+    const items = projects.map(p => ({
         id: p.uuid,
         open: false,
         active: false,
@@ -81,31 +84,49 @@ function updateProjectTree(tree: Array<TreeItem<Project>>, projects: Project[],
     return items;
 }
 
-const projectsReducer = (state: ProjectState = [], action: ProjectAction) => {
+const projectsReducer = (state: ProjectState = { items: [], currentItemId: "" }, action: ProjectAction) => {
     return actions.match(action, {
-        CREATE_PROJECT: project => [...state, project],
+        CREATE_PROJECT: project => ({
+            ...state,
+            items: state.items.concat({
+                id: project.uuid,
+                open: false,
+                active: false,
+                status: TreeItemStatus.Loaded,
+                toggled: false,
+                items: [],
+                data: project
+            })
+        }),
         REMOVE_PROJECT: () => state,
         PROJECTS_REQUEST: itemId => {
-            const tree = _.cloneDeep(state);
-            const item = findTreeItem(tree, itemId);
+            const items = _.cloneDeep(state.items);
+            const item = findTreeItem(items, itemId);
             if (item) {
                 item.status = TreeItemStatus.Pending;
+                state.items = items;
             }
-            return tree;
+            return state;
         },
         PROJECTS_SUCCESS: ({ projects, parentItemId }) => {
-            return updateProjectTree(state, projects, parentItemId);
+            return {
+                ...state,
+                items: updateProjectTree(state.items, projects, parentItemId)
+            };
         },
         TOGGLE_PROJECT_TREE_ITEM: itemId => {
-            const tree = _.cloneDeep(state);
-            resetTreeActivity(tree);
-            const item = findTreeItem(tree, itemId);
+            const items = _.cloneDeep(state.items);
+            resetTreeActivity(items);
+            const item = findTreeItem(items, itemId);
             if (item) {
                 item.open = !item.open;
                 item.active = true;
                 item.toggled = true;
             }
-            return tree;
+            return {
+                items,
+                currentItemId: itemId
+            };
         },
         default: () => state
     });
diff --git a/src/views-components/data-explorer/data-explorer.tsx b/src/views-components/data-explorer/data-explorer.tsx
index 4ba0f87..d9e1f80 100644
--- a/src/views-components/data-explorer/data-explorer.tsx
+++ b/src/views-components/data-explorer/data-explorer.tsx
@@ -52,7 +52,7 @@ class DataExplorer extends React.Component<DataExplorerProps, DataExplorerState>
         }, {
             name: "Type",
             selected: true,
-            render: item => renderType(item.type)
+            render: item => renderType(item.kind)
         }, {
             name: "Owner",
             selected: true,
@@ -190,7 +190,7 @@ class DataExplorer extends React.Component<DataExplorerProps, DataExplorerState>
 }
 
 const renderIcon = (dataItem: DataItem) => {
-    switch (dataItem.type) {
+    switch (dataItem.kind) {
         case ResourceKind.LEVEL_UP:
             return <i className="icon-level-up" style={{fontSize: "1rem"}}/>;
         case ResourceKind.PROJECT:
diff --git a/src/views-components/data-explorer/data-item.ts b/src/views-components/data-explorer/data-item.ts
index ebff77d..cde2bd9 100644
--- a/src/views-components/data-explorer/data-item.ts
+++ b/src/views-components/data-explorer/data-item.ts
@@ -7,7 +7,7 @@ import { getResourceKind, Resource, ResourceKind } from "../../models/resource";
 export interface DataItem {
     uuid: string;
     name: string;
-    type: ResourceKind;
+    kind: ResourceKind;
     url: string;
     owner: string;
     lastModified: string;
@@ -19,7 +19,7 @@ function resourceToDataItem(r: Resource, kind?: ResourceKind) {
     return {
         uuid: r.uuid,
         name: r.name,
-        type: kind ? kind : getResourceKind(r.kind),
+        kind: kind ? kind : getResourceKind(r.kind),
         owner: r.ownerUuid,
         lastModified: r.modifiedAt
     };
diff --git a/src/views-components/project-tree/project-tree.tsx b/src/views-components/project-tree/project-tree.tsx
index fd32ff0..e417998 100644
--- a/src/views-components/project-tree/project-tree.tsx
+++ b/src/views-components/project-tree/project-tree.tsx
@@ -37,7 +37,7 @@ const styles: StyleRulesCallback<CssRules> = (theme: Theme) => ({
 
 export interface ProjectTreeProps {
     projects: Array<TreeItem<Project>>;
-    toggleProjectTreeItem: (id: string, status: TreeItemStatus) => void;
+    toggleProjectTreeItem: (itemId: string) => void;
 }
 
 class ProjectTree<T> extends React.Component<ProjectTreeProps & WithStyles<CssRules>> {
diff --git a/src/views/data-explorer/data-explorer-selectors.ts b/src/views/data-explorer/data-explorer-selectors.ts
index 73881fa..ceb87d2 100644
--- a/src/views/data-explorer/data-explorer-selectors.ts
+++ b/src/views/data-explorer/data-explorer-selectors.ts
@@ -1,10 +1,14 @@
+// Copyright (C) The Arvados Authors. All rights reserved.
+//
+// SPDX-License-Identifier: AGPL-3.0
+
 import { TreeItem } from "../../components/tree/tree";
 import { Project } from "../../models/project";
 import { DataItem } from "../../views-components/data-explorer/data-item";
 import { findTreeItem } from "../../store/project/project-reducer";
 import { ResourceKind } from "../../models/resource";
 import { Collection } from "../../models/collection";
-
+import { getResourceUrl } from "../../store/navigation/navigation-action";
 
 export const projectExplorerItems = (projects: Array<TreeItem<Project>>, treeItemId: string, collections: Array<Collection>): DataItem[] => {
     const dataItems: DataItem[] = [];
@@ -13,8 +17,8 @@ export const projectExplorerItems = (projects: Array<TreeItem<Project>>, treeIte
     if (treeItem) {
         dataItems.push({
             name: "..",
-            url: `/projects/${treeItem.data.ownerUuid}`,
-            type: ResourceKind.LEVEL_UP,
+            url: getResourceUrl(treeItem.data),
+            kind: ResourceKind.LEVEL_UP,
             owner: treeItem.data.ownerUuid,
             uuid: treeItem.data.uuid,
             lastModified: treeItem.data.modifiedAt
@@ -24,8 +28,8 @@ export const projectExplorerItems = (projects: Array<TreeItem<Project>>, treeIte
             treeItem.items.forEach(p => {
                 const item = {
                     name: p.data.name,
-                    type: ResourceKind.PROJECT,
-                    url: `/projects/${treeItem.data.uuid}`,
+                    kind: ResourceKind.PROJECT,
+                    url: getResourceUrl(treeItem.data),
                     owner: p.data.ownerUuid,
                     uuid: p.data.uuid,
                     lastModified: p.data.modifiedAt
@@ -39,8 +43,8 @@ export const projectExplorerItems = (projects: Array<TreeItem<Project>>, treeIte
     collections.forEach(c => {
         const item = {
             name: c.name,
-            type: ResourceKind.COLLECTION,
-            url: `/collections/${c.uuid}`,
+            kind: ResourceKind.COLLECTION,
+            url: getResourceUrl(c),
             owner: c.ownerUuid,
             uuid: c.uuid,
             lastModified: c.modifiedAt
diff --git a/src/views/data-explorer/data-explorer.tsx b/src/views/data-explorer/data-explorer.tsx
index a667469..8d225cd 100644
--- a/src/views/data-explorer/data-explorer.tsx
+++ b/src/views/data-explorer/data-explorer.tsx
@@ -8,15 +8,12 @@ import { Project } from '../../models/project';
 import { ProjectState } from '../../store/project/project-reducer';
 import { RootState } from '../../store/store';
 import { connect, DispatchProp } from 'react-redux';
-import { push } from 'react-router-redux';
 import { DataColumns } from "../../components/data-table/data-table";
 import DataExplorer, { DataExplorerContextActions } from "../../views-components/data-explorer/data-explorer";
 import { projectExplorerItems } from "./data-explorer-selectors";
 import { DataItem } from "../../views-components/data-explorer/data-item";
 import { CollectionState } from "../../store/collection/collection-reducer";
-import { ResourceKind } from "../../models/resource";
-import projectActions from "../../store/project/project-action";
-import { getCollectionList } from "../../store/collection/collection-action";
+import { setProjectItem } from "../../store/navigation/navigation-action";
 
 interface DataExplorerViewDataProps {
     projects: ProjectState;
@@ -28,8 +25,12 @@ type DataExplorerViewState = DataColumns<Project>;
 
 class DataExplorerView extends React.Component<DataExplorerViewProps, DataExplorerViewState> {
     render() {
-        const treeItemId = this.props.match.params.uuid;
-        const items = projectExplorerItems(this.props.projects, treeItemId, this.props.collections);
+        console.log('VIEW!');
+        const items = projectExplorerItems(
+            this.props.projects.items,
+            this.props.projects.currentItemId,
+            this.props.collections
+        );
         return (
             <DataExplorer
                 items={items}
@@ -50,12 +51,7 @@ class DataExplorerView extends React.Component<DataExplorerViewProps, DataExplor
     };
 
     goToItem = (item: DataItem) => {
-        // FIXME: Unify project tree switch action
-        this.props.dispatch(push(item.url));
-        if (item.type === ResourceKind.PROJECT || item.type === ResourceKind.LEVEL_UP) {
-            this.props.dispatch(projectActions.TOGGLE_PROJECT_TREE_ITEM(item.uuid));
-        }
-        this.props.dispatch<any>(getCollectionList(item.uuid));
+        this.props.dispatch<any>(setProjectItem(this.props.projects.items, item.uuid, item.kind));
     }
 }
 
diff --git a/src/views/workbench/workbench.tsx b/src/views/workbench/workbench.tsx
index c981c90..aed2815 100644
--- a/src/views/workbench/workbench.tsx
+++ b/src/views/workbench/workbench.tsx
@@ -11,16 +11,19 @@ import { Route, Switch } from "react-router";
 import authActions from "../../store/auth/auth-action";
 import { User } from "../../models/user";
 import { RootState } from "../../store/store";
-import MainAppBar, { MainAppBarActionProps, MainAppBarMenuItem } from '../../views-components/main-app-bar/main-app-bar';
+import MainAppBar, {
+    MainAppBarActionProps,
+    MainAppBarMenuItem
+} from '../../views-components/main-app-bar/main-app-bar';
 import { Breadcrumb } from '../../components/breadcrumbs/breadcrumbs';
 import { push } from 'react-router-redux';
-import projectActions, { getProjectList } from "../../store/project/project-action";
 import ProjectTree from '../../views-components/project-tree/project-tree';
-import { TreeItem, TreeItemStatus } from "../../components/tree/tree";
+import { TreeItem } from "../../components/tree/tree";
 import { Project } from "../../models/project";
 import { getTreePath } from '../../store/project/project-reducer';
 import DataExplorer from '../data-explorer/data-explorer';
-import { getCollectionList } from "../../store/collection/collection-action";
+import { setProjectItem } from "../../store/navigation/navigation-action";
+import { ResourceKind } from "../../models/resource";
 
 const drawerWidth = 240;
 const appBarHeight = 102;
@@ -64,6 +67,7 @@ const styles: StyleRulesCallback<CssRules> = (theme: Theme) => ({
 
 interface WorkbenchDataProps {
     projects: Array<TreeItem<Project>>;
+    currentProjectId: string;
     user?: User;
 }
 
@@ -74,7 +78,6 @@ type WorkbenchProps = WorkbenchDataProps & WorkbenchActionProps & DispatchProp &
 
 interface NavBreadcrumb extends Breadcrumb {
     itemId: string;
-    status: TreeItemStatus;
 }
 
 interface NavMenuItem extends MainAppBarMenuItem {
@@ -83,7 +86,6 @@ interface NavMenuItem extends MainAppBarMenuItem {
 
 interface WorkbenchState {
     anchorEl: any;
-    breadcrumbs: NavBreadcrumb[];
     searchText: string;
     menuItems: {
         accountMenu: NavMenuItem[],
@@ -124,8 +126,8 @@ class Workbench extends React.Component<WorkbenchProps, WorkbenchState> {
     };
 
     mainAppBarActions: MainAppBarActionProps = {
-        onBreadcrumbClick: ({ itemId, status }: NavBreadcrumb) => {
-            this.toggleProjectTreeItem(itemId, status);
+        onBreadcrumbClick: ({ itemId }: NavBreadcrumb) => {
+            // this.toggleProjectTreeItem(itemId, status);
         },
         onSearch: searchText => {
             this.setState({ searchText });
@@ -134,57 +136,43 @@ class Workbench extends React.Component<WorkbenchProps, WorkbenchState> {
         onMenuItemClick: (menuItem: NavMenuItem) => menuItem.action()
     };
 
-    toggleProjectTreeItem = (itemId: string, status: TreeItemStatus) => {
-        if (status === TreeItemStatus.Loaded) {
-            this.openProjectItem(itemId);
-        } else {
-            this.props.dispatch<any>(getProjectList(itemId))
-                .then(() => this.openProjectItem(itemId));
-        }
-        this.props.dispatch<any>(getCollectionList(itemId));
-    }
-
-    openProjectItem = (itemId: string) => {
-        const branch = getTreePath(this.props.projects, itemId);
-        this.setState({
-            breadcrumbs: branch.map(item => ({
-                label: item.data.name,
-                itemId: item.data.uuid,
-                status: item.status
-            }))
-        });
-        this.props.dispatch(projectActions.TOGGLE_PROJECT_TREE_ITEM(itemId));
-        this.props.dispatch(push(`/project/${itemId}`));
-    }
-
     render() {
+        const branch = getTreePath(this.props.projects, this.props.currentProjectId);
+        const breadcrumbs = branch.map(item => ({
+            label: item.data.name,
+            itemId: item.data.uuid,
+            status: item.status
+        }));
+
         const { classes, user } = this.props;
         return (
             <div className={classes.root}>
                 <div className={classes.appBar}>
                     <MainAppBar
-                        breadcrumbs={this.state.breadcrumbs}
+                        breadcrumbs={breadcrumbs}
                         searchText={this.state.searchText}
                         user={this.props.user}
                         menuItems={this.state.menuItems}
                         {...this.mainAppBarActions}
                     />
                 </div>
-                {user &&
-                    <Drawer
-                        variant="permanent"
-                        classes={{
-                            paper: classes.drawerPaper,
-                        }}>
-                        <div className={classes.toolbar} />
-                        <ProjectTree
-                            projects={this.props.projects}
-                            toggleProjectTreeItem={this.toggleProjectTreeItem} />
-                    </Drawer>}
+                {user && <Drawer
+                    variant="permanent"
+                    classes={{
+                        paper: classes.drawerPaper,
+                    }}>
+                    <div className={classes.toolbar} />
+                    <ProjectTree
+                        projects={this.props.projects}
+                        toggleProjectTreeItem={itemId =>
+                            this.props.dispatch<any>(
+                                setProjectItem(this.props.projects, itemId, ResourceKind.PROJECT)
+                            )}/>
+                </Drawer>}
                 <main className={classes.contentWrapper}>
                     <div className={classes.content}>
                         <Switch>
-                            <Route path="/project/:uuid" component={DataExplorer} />
+                            <Route path="/projects/:uuid" component={DataExplorer} />
                         </Switch>
                     </div>
                 </main>
@@ -195,7 +183,8 @@ class Workbench extends React.Component<WorkbenchProps, WorkbenchState> {
 
 export default connect<WorkbenchDataProps>(
     (state: RootState) => ({
-        projects: state.projects,
+        projects: state.projects.items,
+        currentProjectId: state.projects.currentItemId,
         user: state.auth.user
     })
 )(
diff --git a/tslint.json b/tslint.json
index 7f02975..0ddfc62 100644
--- a/tslint.json
+++ b/tslint.json
@@ -13,7 +13,8 @@
     "no-console": false,
     "no-shadowed-variable": false,
     "semicolon": true,
-    "array-type": false
+    "array-type": false,
+    "interface-over-type-literal": false
   },
   "linterOptions": {
     "exclude": [

-----------------------------------------------------------------------


hooks/post-receive
-- 




More information about the arvados-commits mailing list