Skip to content

Commit

Permalink
feat: chart gallery search improvement (#14484)
Browse files Browse the repository at this point in the history
* feat: chart gallery search improvement

* test: adding unit test for VizTypeControl

* fix: lint errors

Co-authored-by: einatnielsen <einat.bertenthal@nielsen.com>
  • Loading branch information
2 people authored and hughhhh committed May 26, 2021
1 parent 3408eac commit c19e315
Show file tree
Hide file tree
Showing 3 changed files with 128 additions and 5 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@
* specific language governing permissions and limitations
* under the License.
*/
@import '../../../../stylesheets/less/variables.less';
@import '../../../../../stylesheets/less/variables.less';

.viztype-label {
margin-top: 10px;
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,111 @@
/**
* 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 { Preset } from '@superset-ui/core';
import { render, cleanup, screen } from 'spec/helpers/testing-library';
import { Provider } from 'react-redux';
import {
getMockStore,
mockStore,
stateWithoutNativeFilters,
} from 'spec/fixtures/mockStore';
import React from 'react';
import userEvent from '@testing-library/user-event';
import { testWithId } from 'src/utils/testUtils';
import {
EchartsMixedTimeseriesChartPlugin,
EchartsTimeseriesChartPlugin,
} from '@superset-ui/plugin-chart-echarts/lib';
import { LineChartPlugin } from '@superset-ui/preset-chart-xy/lib';
import TimeTableChartPlugin from '../../../../visualizations/TimeTable/TimeTableChartPlugin';
import VizTypeControl, { VIZ_TYPE_CONTROL_TEST_ID } from './index';

jest.useFakeTimers();

class MainPreset extends Preset {
constructor() {
super({
name: 'Legacy charts',
plugins: [
new LineChartPlugin().configure({ key: 'line' }),
new EchartsTimeseriesChartPlugin().configure({
key: 'echarts_timeseries',
}),
new TimeTableChartPlugin().configure({ key: 'time_table' }),
new EchartsMixedTimeseriesChartPlugin().configure({
key: 'mixed_timeseries',
}),
],
});
}
}

const getTestId = testWithId<string>(VIZ_TYPE_CONTROL_TEST_ID, true);

describe('VizTypeControl', () => {
new MainPreset().register();
const newVizTypeControlProps = {
description: '',
label: '',
name: '',
value: '',
labelType: '',
onChange: jest.fn(),
};

const renderWrapper = (
props = newVizTypeControlProps,
state: object = stateWithoutNativeFilters,
) =>
render(
<Provider
store={state ? getMockStore(stateWithoutNativeFilters) : mockStore}
>
<VizTypeControl {...props} />
</Provider>,
);

afterEach(() => {
cleanup();
jest.clearAllMocks();
});

it('Search visualization type', async () => {
renderWrapper();

const visualizations = screen.getByTestId(getTestId('viz-row'));

expect(visualizations).toHaveTextContent(/Time-series Table/);
expect(visualizations).toHaveTextContent(/Time-series Chart/);
expect(visualizations).toHaveTextContent(/Mixed timeseries chart/);
expect(visualizations).toHaveTextContent(/Line Chart/);

const searchInputText = 'time series';

// search
userEvent.type(
screen.getByTestId(getTestId('search-input')),
searchInputText,
);

expect(visualizations).toHaveTextContent(/Time-series Table/);
expect(visualizations).toHaveTextContent(/Time-series Chart/);
expect(visualizations).toHaveTextContent(/Mixed timeseries chart/);
expect(visualizations).not.toHaveTextContent(/Line Chart/);
});
});
Original file line number Diff line number Diff line change
Expand Up @@ -93,6 +93,8 @@ const DEFAULT_ORDER = [

const typesWithDefaultOrder = new Set(DEFAULT_ORDER);

export const VIZ_TYPE_CONTROL_TEST_ID = 'viz-type-control';

function VizSupportValidation({ vizType }) {
const state = useDynamicPluginContext();
if (state.loading || registry.has(vizType)) {
Expand Down Expand Up @@ -153,7 +155,10 @@ const VizTypeControl = props => {
className={`viztype-selector ${isSelected ? 'selected' : ''}`}
src={type.thumbnail}
/>
<div className="viztype-label" data-test="viztype-label">
<div
className="viztype-label"
data-test={`${VIZ_TYPE_CONTROL_TEST_ID}__viztype-label`}
>
{type.name}
</div>
</div>
Expand All @@ -162,8 +167,10 @@ const VizTypeControl = props => {

const { value, labelType } = props;
const filterString = filter.toLowerCase();
const filterStringParts = filterString.split(' ');

const filteredTypes = DEFAULT_ORDER.filter(type => registry.has(type))
const a = DEFAULT_ORDER.filter(type => registry.has(type));
const filteredTypes = a
.filter(type => {
const behaviors = registry.get(type)?.behaviors || [];
return nativeFilterGate(behaviors);
Expand All @@ -181,7 +188,11 @@ const VizTypeControl = props => {
})
.filter(({ key }) => !typesWithDefaultOrder.has(key)),
)
.filter(entry => entry.value.name.toLowerCase().includes(filterString));
.filter(entry =>
filterStringParts.every(
part => entry.value.name.toLowerCase().indexOf(part) !== -1,
),
);

return (
<div>
Expand Down Expand Up @@ -217,9 +228,10 @@ const VizTypeControl = props => {
value={filter}
placeholder={t('Search')}
onChange={changeSearch}
data-test={`${VIZ_TYPE_CONTROL_TEST_ID}__search-input`}
/>
</div>
<Row data-test="viz-row" gutter={16}>
<Row data-test={`${VIZ_TYPE_CONTROL_TEST_ID}__viz-row`} gutter={16}>
{filteredTypes.map(entry => (
<Col xs={12} sm={8} md={6} lg={4} key={`grid-col-${entry.key}`}>
{renderItem(entry)}
Expand Down

0 comments on commit c19e315

Please sign in to comment.