From dd405700568acdc893358ef239e8f8637da66307 Mon Sep 17 00:00:00 2001 From: Csaba Tuncsik Date: Tue, 12 Mar 2024 11:32:34 +0100 Subject: [PATCH] fix(editor): Fix workflow card open action (#8839) --- .../editor-ui/src/components/WorkflowCard.vue | 14 +-- .../components/__tests__/WorkflowCard.test.ts | 98 +++++++++++++++++++ 2 files changed, 101 insertions(+), 11 deletions(-) create mode 100644 packages/editor-ui/src/components/__tests__/WorkflowCard.test.ts diff --git a/packages/editor-ui/src/components/WorkflowCard.vue b/packages/editor-ui/src/components/WorkflowCard.vue index 1270a22205..b6705e0373 100644 --- a/packages/editor-ui/src/components/WorkflowCard.vue +++ b/packages/editor-ui/src/components/WorkflowCard.vue @@ -29,7 +29,7 @@ @@ -169,15 +168,8 @@ export default defineComponent({ }, }, methods: { - async onClick(event: Event) { - if ( - this.$refs.cardActions === event.target || - this.$refs.cardActions?.contains(event.target) - ) { - return; - } - - if (event.metaKey || event.ctrlKey) { + async onClick(event?: KeyboardEvent | PointerEvent) { + if (event?.ctrlKey || event?.metaKey) { const route = this.$router.resolve({ name: VIEWS.WORKFLOW, params: { name: this.data.id }, diff --git a/packages/editor-ui/src/components/__tests__/WorkflowCard.test.ts b/packages/editor-ui/src/components/__tests__/WorkflowCard.test.ts new file mode 100644 index 0000000000..7e68c3c002 --- /dev/null +++ b/packages/editor-ui/src/components/__tests__/WorkflowCard.test.ts @@ -0,0 +1,98 @@ +import type { MockInstance } from 'vitest'; +import { setActivePinia, createPinia } from 'pinia'; +import { waitFor, within } from '@testing-library/vue'; +import userEvent from '@testing-library/user-event'; +import { createComponentRenderer } from '@/__tests__/render'; +import { VIEWS } from '@/constants'; +import WorkflowCard from '@/components/WorkflowCard.vue'; + +const $router = { + push: vi.fn(), + resolve: vi.fn().mockImplementation(() => ({ href: '' })), +}; + +const renderComponent = createComponentRenderer(WorkflowCard, { + global: { + mocks: { + $router, + }, + }, +}); + +const createWorkflow = (overrides = {}) => ({ + id: '1', + name: 'My Workflow', + createdAt: '2021-01-01T00:00:00.000Z', + ...overrides, +}); + +describe('WorkflowCard', () => { + let pinia: ReturnType; + let windowOpenSpy: MockInstance; + + beforeEach(async () => { + pinia = createPinia(); + setActivePinia(pinia); + windowOpenSpy = vi.spyOn(window, 'open'); + }); + + afterEach(() => { + vi.clearAllMocks(); + }); + + it('should render a card with the workflow name and open workflow clicking on it', async () => { + const data = createWorkflow(); + const { getByRole } = renderComponent({ props: { data } }); + const cardTitle = getByRole('heading', { level: 2, name: data.name }); + + expect(cardTitle).toBeInTheDocument(); + + await userEvent.click(cardTitle); + await waitFor(() => { + expect($router.push).toHaveBeenCalledWith({ + name: VIEWS.WORKFLOW, + params: { name: data.id }, + }); + }); + + // Opens in new tab if meta key is used + const user = userEvent.setup(); + + await user.keyboard('[ControlLeft>]'); + await user.click(cardTitle); + await waitFor(() => { + expect($router.push).toHaveBeenCalledTimes(1); + }); + expect(windowOpenSpy).toHaveBeenCalled(); + }); + + it('should open card actions menu and not open workflow, open only on card action', async () => { + const data = createWorkflow(); + const { getByTestId } = renderComponent({ props: { data } }); + const cardActions = getByTestId('workflow-card-actions'); + + expect(cardActions).toBeInTheDocument(); + + const cardActionsOpener = within(cardActions).getByRole('button'); + expect(cardActionsOpener).toBeInTheDocument(); + + const controllingId = cardActionsOpener.getAttribute('aria-controls'); + + await userEvent.click(cardActions); + await waitFor(() => { + expect($router.push).not.toHaveBeenCalled(); + }); + + const actions = document.querySelector(`#${controllingId}`); + await waitFor(() => { + expect(actions).toBeInTheDocument(); + }); + await userEvent.click(actions!.querySelectorAll('li')[0]); + await waitFor(() => { + expect($router.push).toHaveBeenCalledWith({ + name: VIEWS.WORKFLOW, + params: { name: data.id }, + }); + }); + }); +});