From: Pawel Kowalczyk Date: Wed, 21 Nov 2018 11:37:51 +0000 (+0100) Subject: fixed conflicts + link to ssh-keys panel X-Git-Tag: 1.3.0~19^2~1 X-Git-Url: https://git.arvados.org/arvados-workbench2.git/commitdiff_plain/aed25c0fef7e65b307d702e8ee515567d6c2a7c1 fixed conflicts + link to ssh-keys panel Feature #13865 Arvados-DCO-1.1-Signed-off-by: Pawel Kowalczyk --- aed25c0fef7e65b307d702e8ee515567d6c2a7c1 diff --cc src/routes/route-change-handlers.ts index a4a53d70,fb6f5e20..c7f3555b --- a/src/routes/route-change-handlers.ts +++ b/src/routes/route-change-handlers.ts @@@ -4,8 -4,8 +4,8 @@@ import { History, Location } from 'history'; import { RootStore } from '~/store/store'; - import { matchProcessRoute, matchProcessLogRoute, matchProjectRoute, matchCollectionRoute, matchFavoritesRoute, matchTrashRoute, matchRootRoute, matchSharedWithMeRoute, matchRunProcessRoute, matchWorkflowRoute, matchSearchResultsRoute, matchRepositoriesRoute } from './routes'; - import { loadProject, loadCollection, loadFavorites, loadTrash, loadProcess, loadProcessLog, loadRepositories } from '~/store/workbench/workbench-actions'; -import { matchProcessRoute, matchProcessLogRoute, matchProjectRoute, matchCollectionRoute, matchFavoritesRoute, matchTrashRoute, matchRootRoute, matchSharedWithMeRoute, matchRunProcessRoute, matchWorkflowRoute, matchSearchResultsRoute, matchSshKeysRoute } from './routes'; -import { loadProject, loadCollection, loadFavorites, loadTrash, loadProcess, loadProcessLog, loadSshKeys } from '~/store/workbench/workbench-actions'; ++import { matchProcessRoute, matchProcessLogRoute, matchProjectRoute, matchCollectionRoute, matchFavoritesRoute, matchTrashRoute, matchRootRoute, matchSharedWithMeRoute, matchRunProcessRoute, matchWorkflowRoute, matchSearchResultsRoute, matchSshKeysRoute, matchRepositoriesRoute } from './routes'; ++import { loadProject, loadCollection, loadFavorites, loadTrash, loadProcess, loadProcessLog, loadSshKeys, loadRepositories } from '~/store/workbench/workbench-actions'; import { navigateToRootProject } from '~/store/navigation/navigation-action'; import { loadSharedWithMe, loadRunProcess, loadWorkflow, loadSearchResults } from '~//store/workbench/workbench-actions'; @@@ -51,7 -51,7 +52,9 @@@ const handleLocationChange = (store: Ro store.dispatch(loadWorkflow); } else if (searchResultsMatch) { store.dispatch(loadSearchResults); + } else if(repositoryMatch) { + store.dispatch(loadRepositories); + } else if (sshKeysMatch) { + store.dispatch(loadSshKeys); } }; diff --cc src/routes/routes.ts index 5dbecb45,b00b9fe2..c9c2ae20 --- a/src/routes/routes.ts +++ b/src/routes/routes.ts @@@ -78,5 -78,5 +79,8 @@@ export const matchWorkflowRoute = (rout export const matchSearchResultsRoute = (route: string) => matchPath(route, { path: Routes.SEARCH_RESULTS }); +export const matchRepositoriesRoute = (route: string) => - matchPath(route, { path: Routes.REPOSITORIES }); ++ matchPath(route, { path: Routes.REPOSITORIES }); ++ + export const matchSshKeysRoute = (route: string) => - matchPath(route, { path: Routes.SSH_KEYS }); ++ matchPath(route, { path: Routes.SSH_KEYS }); diff --cc src/services/services.ts index 2bc955f2,aeeb9556..308505c5 --- a/src/services/services.ts +++ b/src/services/services.ts @@@ -24,7 -24,7 +24,8 @@@ import { ApiActions } from "~/services/ import { WorkflowService } from "~/services/workflow-service/workflow-service"; import { SearchService } from '~/services/search-service/search-service'; import { PermissionService } from "~/services/permission-service/permission-service"; +import { RepositoriesService } from '~/services/repositories-service/repositories-service'; + import { AuthorizedKeysService } from '~/services/authorized-keys-service/authorized-keys-service'; export type ServiceRepository = ReturnType; diff --cc src/store/navigation/navigation-action.ts index ce599699,57967c7d..fc08f3ac --- a/src/store/navigation/navigation-action.ts +++ b/src/store/navigation/navigation-action.ts @@@ -62,4 -62,4 +62,6 @@@ export const navigateToRunProcess = pus export const navigateToSearchResults = push(Routes.SEARCH_RESULTS); -export const navigateToSshKeys= push(Routes.SSH_KEYS); +export const navigateToRepositories = push(Routes.REPOSITORIES); ++ ++export const navigateToSshKeys= push(Routes.SSH_KEYS); diff --cc src/store/workbench/workbench-actions.ts index c6440fd9,5cc9ea34..5e33661c --- a/src/store/workbench/workbench-actions.ts +++ b/src/store/workbench/workbench-actions.ts @@@ -33,15 -33,16 +33,16 @@@ import * as processUpdateActions from ' import * as processCopyActions from '~/store/processes/process-copy-actions'; import { trashPanelColumns } from "~/views/trash-panel/trash-panel"; import { loadTrashPanel, trashPanelActions } from "~/store/trash-panel/trash-panel-action"; -import { initProcessLogsPanel } from '../process-logs-panel/process-logs-panel-actions'; +import { initProcessLogsPanel } from '~/store/process-logs-panel/process-logs-panel-actions'; import { loadProcessPanel } from '~/store/process-panel/process-panel-actions'; import { sharedWithMePanelActions } from '~/store/shared-with-me-panel/shared-with-me-panel-actions'; -import { loadSharedWithMePanel } from '../shared-with-me-panel/shared-with-me-panel-actions'; +import { loadSharedWithMePanel } from '~/store/shared-with-me-panel/shared-with-me-panel-actions'; import { CopyFormDialogData } from '~/store/copy-dialog/copy-dialog'; import { loadWorkflowPanel, workflowPanelActions } from '~/store/workflow-panel/workflow-panel-actions'; + import { loadSshKeysPanel } from '~/store/auth/auth-action'; import { workflowPanelColumns } from '~/views/workflow-panel/workflow-panel-view'; import { progressIndicatorActions } from '~/store/progress-indicator/progress-indicator-actions'; -import { getProgressIndicator } from '../progress-indicator/progress-indicator-reducer'; +import { getProgressIndicator } from '~/store/progress-indicator/progress-indicator-reducer'; import { ResourceKind, extractUuidKind } from '~/models/resource'; import { FilterBuilder } from '~/services/api/filter-builder'; import { GroupContentsResource } from '~/services/groups-service/groups-service'; @@@ -391,12 -391,11 +392,17 @@@ export const loadSearchResults = handle await dispatch(loadSearchResultsPanel()); }); +export const loadRepositories = handleFirstTimeLoad( + async (dispatch: Dispatch) => { + await dispatch(loadRepositoriesPanel()); + dispatch(setBreadcrumbs([{ label: 'Repositories' }])); + }); + + export const loadSshKeys = handleFirstTimeLoad( + async (dispatch: Dispatch) => { + await dispatch(loadSshKeysPanel()); + }); + const finishLoadingProject = (project: GroupContentsResource | string) => async (dispatch: Dispatch) => { const uuid = typeof project === 'string' ? project : project.uuid; diff --cc src/validators/validators.tsx index 37c1bd37,1980ed80..c601df17 --- a/src/validators/validators.tsx +++ b/src/validators/validators.tsx @@@ -21,4 -22,5 +22,7 @@@ export const MOVE_TO_VALIDATION = [requ export const PROCESS_NAME_VALIDATION = [require, maxLength(255)]; - export const REPOSITORY_NAME_VALIDATION = [require, maxLength(255)]; ++export const REPOSITORY_NAME_VALIDATION = [require, maxLength(255)]; ++ + export const SSH_KEY_PUBLIC_VALIDATION = [require, isRsaKey, maxLength(1024)]; -export const SSH_KEY_NAME_VALIDATION = [require, maxLength(255)]; ++export const SSH_KEY_NAME_VALIDATION = [require, maxLength(255)]; diff --cc src/views-components/main-app-bar/account-menu.tsx index c643fef2,ee863a29..f00c678e --- a/src/views-components/main-app-bar/account-menu.tsx +++ b/src/views-components/main-app-bar/account-menu.tsx @@@ -8,10 -8,10 +8,11 @@@ import { User, getUserFullname } from " import { DropdownMenu } from "~/components/dropdown-menu/dropdown-menu"; import { UserPanelIcon } from "~/components/icon/icon"; import { DispatchProp, connect } from 'react-redux'; - import { logout } from "~/store/auth/auth-action"; + import { logout } from '~/store/auth/auth-action'; import { RootState } from "~/store/store"; -import { openCurrentTokenDialog } from '../../store/current-token-dialog/current-token-dialog-actions'; +import { openCurrentTokenDialog } from '~/store/current-token-dialog/current-token-dialog-actions'; +import { openRepositoriesPanel } from "~/store/repositories/repositories-actions"; + import { navigateToSshKeys } from '~/store/navigation/navigation-action'; interface AccountMenuProps { user?: User; @@@ -31,8 -31,8 +32,9 @@@ export const AccountMenu = connect(mapS {getUserFullname(user)} + dispatch(openRepositoriesPanel())}>Repositories dispatch(openCurrentTokenDialog)}>Current token + dispatch(navigateToSshKeys)}>Ssh Keys My account dispatch(logout())}>Logout diff --cc src/views/repositories-panel/repositories-panel.tsx index 262f3cc3,00000000..cfe59f0d mode 100644,000000..100644 --- a/src/views/repositories-panel/repositories-panel.tsx +++ b/src/views/repositories-panel/repositories-panel.tsx @@@ -1,153 -1,0 +1,154 @@@ +// Copyright (C) The Arvados Authors. All rights reserved. +// +// SPDX-License-Identifier: AGPL-3.0 + +import * as React from 'react'; +import { connect } from 'react-redux'; +import { Grid, Typography, Button, Card, CardContent, TableBody, TableCell, TableHead, TableRow, Table, Tooltip, IconButton } from '@material-ui/core'; +import { StyleRulesCallback, WithStyles, withStyles } from '@material-ui/core/styles'; +import { ArvadosTheme } from '~/common/custom-theme'; +import { Link } from 'react-router-dom'; +import { Dispatch, compose } from 'redux'; +import { RootState } from '~/store/store'; +import { HelpIcon, AddIcon, MoreOptionsIcon } from '~/components/icon/icon'; +import { loadRepositoriesData, openRepositoriesSampleGitDialog, openRepositoryCreateDialog } from '~/store/repositories/repositories-actions'; +import { RepositoryResource } from '~/models/repositories'; +import { openRepositoryContextMenu } from '~/store/context-menu/context-menu-actions'; ++import { Routes } from '~/routes/routes'; + + +type CssRules = 'link' | 'button' | 'icon' | 'iconRow' | 'moreOptionsButton' | 'moreOptions' | 'cloneUrls'; + +const styles: StyleRulesCallback = (theme: ArvadosTheme) => ({ + link: { + textDecoration: 'none', + color: theme.palette.primary.main, + "&:hover": { + color: theme.palette.primary.dark, + transition: 'all 0.5s ease' + } + }, + button: { + textAlign: 'right', + alignSelf: 'center' + }, + icon: { + cursor: 'pointer', + color: theme.palette.grey["500"], + "&:hover": { + color: theme.palette.common.black, + transition: 'all 0.5s ease' + } + }, + iconRow: { + paddingTop: theme.spacing.unit * 2, + textAlign: 'right' + }, + moreOptionsButton: { + padding: 0 + }, + moreOptions: { + textAlign: 'right', + '&:last-child': { + paddingRight: 0 + } + }, + cloneUrls: { + whiteSpace: 'pre-wrap' + } +}); + +const mapStateToProps = (state: RootState) => { + return { + repositories: state.repositories.items + }; +}; + +const mapDispatchToProps = (dispatch: Dispatch): Pick => ({ + loadRepositories: () => dispatch(loadRepositoriesData()), + onOptionsMenuOpen: (event, index, repository) => { + dispatch(openRepositoryContextMenu(event, index, repository)); + }, + openRepositoriesSampleGitDialog: () => dispatch(openRepositoriesSampleGitDialog()), + openRepositoryCreateDialog: () => dispatch(openRepositoryCreateDialog()) +}); + +interface RepositoriesActionProps { + loadRepositories: () => void; + onOptionsMenuOpen: (event: React.MouseEvent, index: number, repository: RepositoryResource) => void; + openRepositoriesSampleGitDialog: () => void; + openRepositoryCreateDialog: () => void; +} + +interface RepositoriesDataProps { + repositories: RepositoryResource[]; +} + + +type RepositoriesProps = RepositoriesDataProps & RepositoriesActionProps & WithStyles; + +export const RepositoriesPanel = compose( + withStyles(styles), + connect(mapStateToProps, mapDispatchToProps))( + class extends React.Component { + componentDidMount() { + this.props.loadRepositories(); + } + render() { + const { classes, repositories, onOptionsMenuOpen, openRepositoriesSampleGitDialog, openRepositoryCreateDialog } = this.props; + return ( + + + + + + When you are using an Arvados virtual machine, you should clone the https:// URLs. This will authenticate automatically using your API token.
- In order to clone git repositories using SSH, add an SSH key to your account and clone the git@ URLs. ++ In order to clone git repositories using SSH, add an SSH key to your account and clone the git@ URLs. +
+
+ + + +
+ +
+ + + + + +
+
+ + {repositories && + + + Name + URL + + + + + {repositories.map((repository, index) => + + {repository.name} + {repository.cloneUrls.join("\n")} + + + onOptionsMenuOpen(event, index, repository)} className={classes.moreOptionsButton}> + + + + + )} + +
} +
+
+
+ ); + } + } + ); diff --cc src/views/workbench/workbench.tsx index eee9911c,3a63ea37..ebdf57c3 --- a/src/views/workbench/workbench.tsx +++ b/src/views/workbench/workbench.tsx @@@ -48,11 -49,7 +49,12 @@@ import { SharingDialog } from '~/views- import { AdvancedTabDialog } from '~/views-components/advanced-tab-dialog/advanced-tab-dialog'; import { ProcessInputDialog } from '~/views-components/process-input-dialog/process-input-dialog'; import { ProjectPropertiesDialog } from '~/views-components/project-properties-dialog/project-properties-dialog'; +import { RepositoriesPanel } from '~/views/repositories-panel/repositories-panel'; +import { RepositoriesSampleGitDialog } from '~/views-components/repositories-sample-git-dialog/repositories-sample-git-dialog'; +import { RepositoryAttributesDialog } from '~/views-components/repository-attributes-dialog/repository-attributes-dialog'; +import { CreateRepositoryDialog } from '~/views-components/dialog-forms/create-repository-dialog'; +import { RemoveRepositoryDialog } from '~/views-components/repository-remove-dialog/repository-remove-dialog'; + import { CreateSshKeyDialog } from '~/views-components/dialog-forms/create-ssh-key-dialog'; type CssRules = 'root' | 'container' | 'splitter' | 'asidePanel' | 'contentWrapper' | 'content'; @@@ -122,7 -119,7 +124,8 @@@ export const WorkbenchPanel + + @@@ -138,7 -135,7 +141,8 @@@ + +