From: Stephen Smith Date: Mon, 21 Aug 2023 17:34:00 +0000 (-0400) Subject: Merge branch '19991-breadcrumbs-missing-bug' into main. Closes #19991 X-Git-Tag: 2.7.0~16 X-Git-Url: https://git.arvados.org/arvados-workbench2.git/commitdiff_plain/3cd7b7d270c0dc66df2ada32cf17d37efecc3feb?hp=f6f88d9ca9cdeeeebfadcfe999789bfb9f69e5c6 Merge branch '19991-breadcrumbs-missing-bug' into main. Closes #19991 Arvados-DCO-1.1-Signed-off-by: Stephen Smith --- diff --git a/cypress/integration/collection.spec.js b/cypress/integration/collection.spec.js index d5b1b9eb..a2841eb8 100644 --- a/cypress/integration/collection.spec.js +++ b/cypress/integration/collection.spec.js @@ -876,6 +876,7 @@ describe('Collection panel tests', function () { .should('contain', '3').and('contain', '3 B'); // Check context menus on version browser + cy.waitForDom(); cy.get('[data-cy=collection-version-browser-select-3]').rightclick() cy.get('[data-cy=context-menu]') .should('contain', 'Add to favorites') @@ -932,7 +933,7 @@ describe('Collection panel tests', function () { cy.waitForDom().get('.layout-pane-primary', { timeout: 12000 }).contains('Projects').click(); - cy.get('main').contains(`Files extracted from: ${this.collection.name}`).click(); + cy.waitForDom().get('main').contains(`Files extracted from: ${this.collection.name}`).click(); cy.get('[data-cy=collection-files-panel]') .and('contain', 'bar'); }); diff --git a/cypress/integration/project.spec.js b/cypress/integration/project.spec.js index eff4d4e9..fd14cc42 100644 --- a/cypress/integration/project.spec.js +++ b/cypress/integration/project.spec.js @@ -554,7 +554,7 @@ describe('Project tests', function() { cy.get('[data-cy=context-menu]').contains('Copy to clipboard').click(); cy.window().then((win) => ( win.navigator.clipboard.readText().then((text) => { - expect(text).to.match(/https\:\/\/localhost\:[0-9]+\/projects\/[a-z0-9]{5}-[a-z0-9]{5}-[a-z0-9]{15}/,); + expect(text).to.match(/https\:\/\/127\.0\.0\.1\:[0-9]+\/projects\/[a-z0-9]{5}-[a-z0-9]{5}-[a-z0-9]{15}/,); }) )); diff --git a/cypress/integration/search.spec.js b/cypress/integration/search.spec.js index c8e262f0..085298dc 100644 --- a/cypress/integration/search.spec.js +++ b/cypress/integration/search.spec.js @@ -161,12 +161,12 @@ describe('Search tests', function() { }); it('shows search context menu', function() { - const colName = `Collection ${Math.floor(Math.random() * Math.floor(999999))}`; - const federatedColName = `Collection ${Math.floor(Math.random() * Math.floor(999999))}`; + const colName = `Home Collection ${Math.floor(Math.random() * Math.floor(999999))}`; + const federatedColName = `Federated Collection ${Math.floor(Math.random() * Math.floor(999999))}`; const federatedColUuid = "xxxxx-4zz18-000000000000000"; // Intercept config to insert remote cluster - cy.intercept({method: 'GET', hostname: 'localhost', url: '**/arvados/v1/config?nocache=*'}, (req) => { + cy.intercept({method: 'GET', hostname: '127.0.0.1', url: '**/arvados/v1/config?nocache=*'}, (req) => { req.reply((res) => { res.body.RemoteClusters = { "*": res.body.RemoteClusters["*"], @@ -280,6 +280,7 @@ describe('Search tests', function() { cy.contains('View details'); cy.contains('Copy to clipboard').click(); + cy.waitForDom(); cy.window().then((win) => ( win.navigator.clipboard.readText().then((text) => { expect(text).to.match(new RegExp(`/collections/${testCollection.uuid}$`)); @@ -291,6 +292,7 @@ describe('Search tests', function() { cy.get('[data-cy=search-results]').contains(colName).rightclick(); cy.get('[data-cy=context-menu]').within(() => { cy.contains('Open in new tab').click(); + cy.waitForDom(); cy.get('@Open').should('have.been.calledOnceWith', `${window.location.origin}/collections/${testCollection.uuid}`) }); @@ -298,6 +300,7 @@ describe('Search tests', function() { cy.get('[data-cy=search-results]').contains(federatedColName).rightclick(); cy.get('[data-cy=context-menu]').within(() => { cy.contains('Copy to clipboard').click(); + cy.waitForDom(); cy.window().then((win) => ( win.navigator.clipboard.readText().then((text) => { expect(text).to.equal(`https://wb2.xxxxx.fakecluster.tld/collections/${federatedColUuid}`); @@ -308,6 +311,7 @@ describe('Search tests', function() { cy.get('[data-cy=search-results]').contains(federatedColName).rightclick(); cy.get('[data-cy=context-menu]').within(() => { cy.contains('Open in new tab').click(); + cy.waitForDom(); cy.get('@Open').should('have.been.calledWith', `https://wb2.xxxxx.fakecluster.tld/collections/${federatedColUuid}`) }); diff --git a/cypress/integration/side-panel.spec.js b/cypress/integration/side-panel.spec.js index e187d533..92181150 100644 --- a/cypress/integration/side-panel.spec.js +++ b/cypress/integration/side-panel.spec.js @@ -65,7 +65,7 @@ describe('Side panel tests', function() { {url: '/all_processes', label: 'All Processes'}, {url: '/trash', label: 'Trash'}, ].map(function(section) { - cy.goToPath(section.url); + cy.waitForDom().goToPath(section.url); cy.get('[data-cy=breadcrumb-first]') .should('contain', section.label); cy.get('[data-cy=side-panel-button]') diff --git a/cypress/integration/virtual-machine-admin.spec.js b/cypress/integration/virtual-machine-admin.spec.js index 49cb1239..80d64977 100644 --- a/cypress/integration/virtual-machine-admin.spec.js +++ b/cypress/integration/virtual-machine-admin.spec.js @@ -50,7 +50,7 @@ describe('Virtual machine login manage tests', function() { cy.get('input').type('VMAdmin'); }) }); - cy.get('[role=tooltip]').click(); + cy.waitForDom().get('[role=tooltip]').click(); cy.get('[data-cy=form-dialog]').as('add-login-dialog') .should('contain', 'Add login permission') .within(() => { @@ -269,11 +269,11 @@ describe('Virtual machine login manage tests', function() { cy.get('@removeButton').click(); cy.get('[data-cy=confirmation-dialog-ok-btn]').click(); - cy.get('[data-cy=vm-admin-table]') + cy.waitForDom().get('[data-cy=vm-admin-table]') .contains(vmHost) .parents('tr') .within(() => { - cy.get('div[role=button]').should('not.contain', 'admin'); + cy.get('div[role=button]').should('not.exist'); }); // Check admin's vm page for login diff --git a/src/store/breadcrumbs/breadcrumbs-actions.ts b/src/store/breadcrumbs/breadcrumbs-actions.ts index a7e42510..9c9baf08 100644 --- a/src/store/breadcrumbs/breadcrumbs-actions.ts +++ b/src/store/breadcrumbs/breadcrumbs-actions.ts @@ -6,8 +6,6 @@ import { Dispatch } from 'redux'; import { RootState } from 'store/store'; import { getUserUuid } from "common/getuser"; import { getResource } from 'store/resources/resources'; -import { TreePicker } from '../tree-picker/tree-picker'; -import { getSidePanelTreeBranch, getSidePanelTreeNodeAncestorsIds } from '../side-panel-tree/side-panel-tree-actions'; import { propertiesActions } from '../properties/properties-actions'; import { getProcess } from 'store/processes/process'; import { ServiceRepository } from 'services/services'; @@ -57,25 +55,40 @@ const resourceToBreadcrumb = (resource: CollectionResource | ContainerRequestRes icon: resourceToBreadcrumbIcon(resource), }) -const getSidePanelTreeBreadcrumbs = (uuid: string) => (treePicker: TreePicker): Breadcrumb[] => { - const nodes = getSidePanelTreeBranch(uuid)(treePicker); - return nodes.map(node => - typeof node.value === 'string' - ? { - label: node.value, - uuid: node.id, - icon: getSidePanelIcon(node.value) - } - : resourceToBreadcrumb(node.value)); -}; - export const setSidePanelBreadcrumbs = (uuid: string) => async (dispatch: Dispatch, getState: () => RootState, services: ServiceRepository) => { - const { treePicker, collectionPanel: { item } } = getState(); - const breadcrumbs = getSidePanelTreeBreadcrumbs(uuid)(treePicker); + const ancestors = await services.ancestorsService.ancestors(uuid, ''); + dispatch(updateResources(ancestors)); + + let breadcrumbs: Breadcrumb[] = []; + const { collectionPanel: { item } } = getState(); + const path = getState().router.location!.pathname; const currentUuid = path.split('/')[2]; const uuidKind = extractUuidKind(currentUuid); + const rootUuid = getUserUuid(getState()); + + if (ancestors.find(ancestor => ancestor.uuid === rootUuid)) { + // Handle home project uuid root + breadcrumbs.push({ + label: SidePanelTreeCategory.PROJECTS, + uuid: SidePanelTreeCategory.PROJECTS, + icon: getSidePanelIcon(SidePanelTreeCategory.PROJECTS) + }); + } else if (Object.values(SidePanelTreeCategory).includes(uuid as SidePanelTreeCategory)) { + // Handle SidePanelTreeCategory root + breadcrumbs.push({ + label: uuid, + uuid: uuid, + icon: getSidePanelIcon(uuid) + }); + } + + breadcrumbs = ancestors.reduce((breadcrumbs, ancestor) => + ancestor.kind === ResourceKind.GROUP + ? [...breadcrumbs, resourceToBreadcrumb(ancestor)] + : breadcrumbs, + breadcrumbs); if (uuidKind === ResourceKind.COLLECTION) { const collectionItem = item ? item : await services.collectionService.get(currentUuid); @@ -189,10 +202,10 @@ const getCollectionParent = (collection: CollectionResource) => export const setProjectBreadcrumbs = (uuid: string) => - (dispatch: Dispatch, getState: () => RootState, services: ServiceRepository) => { - const ancestors = getSidePanelTreeNodeAncestorsIds(uuid)(getState().treePicker); + async (dispatch: Dispatch, getState: () => RootState, services: ServiceRepository) => { + const ancestors = await services.ancestorsService.ancestors(uuid, ''); const rootUuid = getUserUuid(getState()); - if (uuid === rootUuid || ancestors.find(uuid => uuid === rootUuid)) { + if (uuid === rootUuid || ancestors.find(ancestor => ancestor.uuid === rootUuid)) { dispatch(setSidePanelBreadcrumbs(uuid)); } else { dispatch(setSharedWithMeBreadcrumbs(uuid)); diff --git a/tools/run-integration-tests.sh b/tools/run-integration-tests.sh index 367ccecd..1f2b7c5e 100755 --- a/tools/run-integration-tests.sh +++ b/tools/run-integration-tests.sh @@ -139,10 +139,10 @@ exec 8<&"${wb2[0]}"; coproc consume_wb2_stdout (cat <&8 >&2) # Wait for workbench2 to be up. # Using https-get to avoid false positive 'ready' detection. -yarn run wait-on --timeout 300000 https-get://localhost:${WB2_PORT} || exit 1 +yarn run wait-on --timeout 300000 https-get://127.0.0.1:${WB2_PORT} || exit 1 echo "Running tests..." CYPRESS_system_token=systemusertesttoken1234567890aoeuidhtnsqjkxbmwvzpy \ CYPRESS_controller_url=${controllerURL} \ - CYPRESS_BASE_URL=https://localhost:${WB2_PORT} \ + CYPRESS_BASE_URL=https://127.0.0.1:${WB2_PORT} \ yarn run cypress ${CYPRESS_MODE}