From 1dbc1496b28b95e9a7e08fb3cf9b39208e30de26 Mon Sep 17 00:00:00 2001 From: Bruno Motta Date: Thu, 1 Apr 2021 03:08:20 -0300 Subject: [PATCH] test: DisplayQueryButton (#13750) * Tests for DisplayQueryButton component * add factories to props and fetch-mock * Update superset-frontend/src/explore/components/DisplayQueryButton/DisplayQueryButton.test.tsx Co-authored-by: Michael S. Molina <70410625+michael-s-molina@users.noreply.github.com> * Update superset-frontend/src/explore/components/DisplayQueryButton/DisplayQueryButton.test.tsx Co-authored-by: Michael S. Molina <70410625+michael-s-molina@users.noreply.github.com> Co-authored-by: Michael S. Molina <70410625+michael-s-molina@users.noreply.github.com> --- .../DisplayQueryButton.test.tsx | 181 ++++++++++++++++++ .../index.jsx} | 19 +- 2 files changed, 190 insertions(+), 10 deletions(-) create mode 100644 superset-frontend/src/explore/components/DisplayQueryButton/DisplayQueryButton.test.tsx rename superset-frontend/src/explore/components/{DisplayQueryButton.jsx => DisplayQueryButton/index.jsx} (91%) diff --git a/superset-frontend/src/explore/components/DisplayQueryButton/DisplayQueryButton.test.tsx b/superset-frontend/src/explore/components/DisplayQueryButton/DisplayQueryButton.test.tsx new file mode 100644 index 0000000000000..ea2390ef79992 --- /dev/null +++ b/superset-frontend/src/explore/components/DisplayQueryButton/DisplayQueryButton.test.tsx @@ -0,0 +1,181 @@ +/** + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ + +import React from 'react'; +import { render, screen, waitFor } from 'spec/helpers/testing-library'; +import userEvent from '@testing-library/user-event'; +import * as chartAction from 'src/chart/chartAction'; +import * as downloadAsImage from 'src/utils/downloadAsImage'; +import fetchMock from 'fetch-mock'; +import ConectedDisplayQueryButton from '.'; + +const createProps = () => ({ + latestQueryFormData: { + viz_type: 'histogram', + datasource: '49__table', + slice_id: 318, + url_params: {}, + time_range_endpoints: ['inclusive', 'exclusive'], + granularity_sqla: 'time_start', + time_range: 'No filter', + all_columns_x: ['age'], + adhoc_filters: [], + row_limit: 10000, + groupby: null, + color_scheme: 'supersetColors', + label_colors: {}, + link_length: '25', + x_axis_label: 'age', + y_axis_label: 'count', + }, + slice: { + cache_timeout: null, + changed_on: '2021-03-19T16:30:56.750230', + changed_on_humanized: '3 days ago', + datasource: 'FCC 2018 Survey', + description: null, + description_markeddown: '', + edit_url: '/chart/edit/318', + form_data: { + adhoc_filters: [], + all_columns_x: ['age'], + color_scheme: 'supersetColors', + datasource: '49__table', + granularity_sqla: 'time_start', + groupby: null, + label_colors: {}, + link_length: '25', + queryFields: { groupby: 'groupby' }, + row_limit: 10000, + slice_id: 318, + time_range: 'No filter', + time_range_endpoints: ['inclusive', 'exclusive'], + url_params: {}, + viz_type: 'histogram', + x_axis_label: 'age', + y_axis_label: 'count', + }, + modified: '3 days ago', + owners: [], + slice_id: 318, + slice_name: 'Age distribution of respondents', + slice_url: '/superset/explore/?form_data=%7B%22slice_id%22%3A%20318%7D', + }, + chartStatus: 'rendered', + onOpenPropertiesModal: jest.fn(), + onOpenInEditor: jest.fn(), +}); + +fetchMock.post( + 'http://api/v1/chart/data?form_data=%7B%22slice_id%22%3A318%7D', + { body: {} }, + { + sendAsJson: false, + }, +); + +test('Shoud render a button', () => { + const props = createProps(); + render(, { useRedux: true }); + expect(screen.getByRole('button')).toBeInTheDocument(); +}); + +test('Shoud open a menu', () => { + const props = createProps(); + render(, { + useRedux: true, + }); + + expect(props.onOpenInEditor).toBeCalledTimes(0); + expect(props.onOpenPropertiesModal).toBeCalledTimes(0); + userEvent.click(screen.getByRole('button')); + expect(props.onOpenInEditor).toBeCalledTimes(0); + expect(props.onOpenPropertiesModal).toBeCalledTimes(0); + + expect( + screen.getByRole('menuitem', { name: 'Edit properties' }), + ).toBeInTheDocument(); + expect( + screen.getByRole('menuitem', { name: 'View query' }), + ).toBeInTheDocument(); + expect( + screen.getByRole('menuitem', { name: 'Run in SQL Lab' }), + ).toBeInTheDocument(); + expect( + screen.getByRole('menuitem', { name: 'Download as image' }), + ).toBeInTheDocument(); +}); + +test('Shoud call onOpenPropertiesModal when click on "Edit properties"', () => { + const props = createProps(); + render(, { + useRedux: true, + }); + expect(props.onOpenInEditor).toBeCalledTimes(0); + userEvent.click(screen.getByRole('button')); + userEvent.click(screen.getByRole('menuitem', { name: 'Edit properties' })); + expect(props.onOpenPropertiesModal).toBeCalledTimes(1); +}); + +test('Shoud call getChartDataRequest when click on "View query"', async () => { + const props = createProps(); + const getChartDataRequest = jest.spyOn(chartAction, 'getChartDataRequest'); + render(, { + useRedux: true, + }); + + expect(getChartDataRequest).toBeCalledTimes(0); + userEvent.click(screen.getByRole('button')); + expect(getChartDataRequest).toBeCalledTimes(0); + + const menuItem = screen.getByText('View query').parentElement!; + userEvent.click(menuItem); + + await waitFor(() => expect(getChartDataRequest).toBeCalledTimes(1)); +}); + +test('Shoud call onOpenInEditor when click on "Run in SQL Lab"', () => { + const props = createProps(); + render(, { + useRedux: true, + }); + + expect(props.onOpenInEditor).toBeCalledTimes(0); + userEvent.click(screen.getByRole('button')); + expect(props.onOpenInEditor).toBeCalledTimes(0); + + userEvent.click(screen.getByRole('menuitem', { name: 'Run in SQL Lab' })); + expect(props.onOpenInEditor).toBeCalledTimes(1); +}); + +test('Shoud call downloadAsImage when click on "Download as image"', () => { + const props = createProps(); + const spy = jest.spyOn(downloadAsImage, 'default'); + render(, { + useRedux: true, + }); + + expect(spy).toBeCalledTimes(0); + userEvent.click(screen.getByRole('button')); + expect(spy).toBeCalledTimes(0); + + userEvent.click(screen.getByRole('menuitem', { name: 'Download as image' })); + + expect(spy).toBeCalledTimes(1); +}); diff --git a/superset-frontend/src/explore/components/DisplayQueryButton.jsx b/superset-frontend/src/explore/components/DisplayQueryButton/index.jsx similarity index 91% rename from superset-frontend/src/explore/components/DisplayQueryButton.jsx rename to superset-frontend/src/explore/components/DisplayQueryButton/index.jsx index b3f001f337754..56f74d6e3a5e3 100644 --- a/superset-frontend/src/explore/components/DisplayQueryButton.jsx +++ b/superset-frontend/src/explore/components/DisplayQueryButton/index.jsx @@ -27,16 +27,15 @@ import sqlSyntax from 'react-syntax-highlighter/dist/cjs/languages/hljs/sql'; import jsonSyntax from 'react-syntax-highlighter/dist/cjs/languages/hljs/json'; import github from 'react-syntax-highlighter/dist/cjs/styles/hljs/github'; import { styled, t } from '@superset-ui/core'; - import { Dropdown, Menu } from 'src/common/components'; -import { getClientErrorObject } from '../../utils/getClientErrorObject'; -import CopyToClipboard from '../../components/CopyToClipboard'; -import { getChartDataRequest } from '../../chart/chartAction'; -import downloadAsImage from '../../utils/downloadAsImage'; -import Loading from '../../components/Loading'; -import ModalTrigger from '../../components/ModalTrigger'; -import { sliceUpdated } from '../actions/exploreActions'; -import { CopyButton } from './DataTableControl'; +import { getClientErrorObject } from 'src/utils/getClientErrorObject'; +import CopyToClipboard from 'src/components/CopyToClipboard'; +import { getChartDataRequest } from 'src/chart/chartAction'; +import downloadAsImage from 'src/utils/downloadAsImage'; +import Loading from 'src/components/Loading'; +import ModalTrigger from 'src/components/ModalTrigger'; +import { sliceUpdated } from 'src/explore/actions/exploreActions'; +import { CopyButton } from 'src/explore/components/DataTableControl'; SyntaxHighlighter.registerLanguage('markdown', markdownSyntax); SyntaxHighlighter.registerLanguage('html', htmlSyntax); @@ -193,7 +192,7 @@ export const DisplayQueryButton = props => { tabIndex={0} className="btn btn-default btn-sm" > - + );