Skip to content

Commit 7c320ab

Browse files
authored
[Discovery] Hide "Selected only" toggle in pages that don't filter by value (elastic#215315) (elastic#220624)
## Summary The doc viewer table was always showing the "Selected only" toggle even if the user couldn't filter by value. With this change the toggle is only shown when that filter is available. | Before | After | |--------|------| | ![image](https://github.com/user-attachments/assets/55ce55ff-8c51-45f8-af5b-a3f1e0ef46f9) | ![image](https://github.com/user-attachments/assets/9588bfc8-96f2-40d3-96c7-d68668ea7b72) | Solves elastic#215315 ### Checklist Check the PR satisfies following conditions. Reviewers should verify this PR satisfies this list as well. - [ ] Any text added follows [EUI's writing guidelines](https://elastic.github.io/eui/#/guidelines/writing), uses sentence case text and includes [i18n support](https://github.com/elastic/kibana/blob/main/src/platform/packages/shared/kbn-i18n/README.md) - [ ] [Documentation](https://www.elastic.co/guide/en/kibana/master/development-documentation.html) was added for features that require explanation or tutorials - [ ] [Unit or functional tests](https://www.elastic.co/guide/en/kibana/master/development-tests.html) were updated or added to match the most common scenarios - [ ] If a plugin configuration key changed, check if it needs to be allowlisted in the cloud and added to the [docker list](https://github.com/elastic/kibana/blob/main/src/dev/build/tasks/os_packages/docker_generator/resources/base/bin/kibana-docker) - [ ] This was checked for breaking HTTP API changes, and any breaking changes have been approved by the breaking-change committee. The `release_note:breaking` label should be applied in these situations. - [ ] [Flaky Test Runner](https://ci-stats.kibana.dev/trigger_flaky_test_runner/1) was used on any tests changed - [ ] The PR description includes the appropriate Release Notes section, and the correct `release_note:*` label is applied per the [guidelines](https://www.elastic.co/guide/en/kibana/master/contributing.html#kibana-release-notes-process) ### Identify risks Does this PR introduce any risks? For example, consider risks like hard to test bugs, performance regression, potential of data loss. Describe the risk, its severity, and mitigation for each identified risk. Invite stakeholders and evaluate how to proceed before merging. - [ ] [See some risk examples](https://github.com/elastic/kibana/blob/main/RISK_MATRIX.mdx) - [ ] ...
1 parent b064e30 commit 7c320ab

2 files changed

Lines changed: 91 additions & 101 deletions

File tree

src/platform/plugins/shared/unified_doc_viewer/public/components/doc_viewer_table/table.test.tsx

Lines changed: 76 additions & 88 deletions
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@
88
*/
99

1010
import React from 'react';
11-
import { render, screen, act, fireEvent } from '@testing-library/react';
11+
import { render, screen } from '@testing-library/react';
1212
import { __IntlProvider as IntlProvider } from '@kbn/i18n-react';
1313
import { buildDataTableRecord } from '@kbn/discover-utils';
1414
import { createStubDataView } from '@kbn/data-views-plugin/common/data_view.stub';
@@ -17,6 +17,7 @@ import { generateEsHits } from '@kbn/discover-utils/src/__mocks__';
1717
import { DocViewerTable, SHOW_ONLY_SELECTED_FIELDS } from './table';
1818
import { mockUnifiedDocViewerServices } from '../../__mocks__';
1919
import { setUnifiedDocViewerServices } from '../../plugin';
20+
import { userEvent } from '@testing-library/user-event';
2021

2122
const storage = new Storage(window.localStorage);
2223

@@ -80,18 +81,26 @@ const dataView = createStubDataView({
8081
});
8182
const hit = buildDataTableRecord(generateEsHits(dataView, 1)[0], dataView);
8283

84+
const setupComponent = (props: Partial<React.ComponentProps<typeof DocViewerTable>> = {}) => {
85+
const user = userEvent.setup();
86+
87+
render(
88+
<IntlProvider locale="en">
89+
<DocViewerTable dataView={dataView} hit={hit} columns={[]} {...props} />
90+
</IntlProvider>
91+
);
92+
93+
return { user };
94+
};
95+
8396
describe('DocViewerTable', () => {
8497
afterEach(() => {
8598
storage.clear();
8699
});
87100

88101
describe('table cells', () => {
89102
it('should render cells', async () => {
90-
render(
91-
<IntlProvider locale="en">
92-
<DocViewerTable dataView={dataView} hit={hit} columns={[]} />
93-
</IntlProvider>
94-
);
103+
setupComponent();
95104

96105
expect(screen.getByText('@timestamp')).toBeInTheDocument();
97106
expect(screen.getByText(hit.flattened['@timestamp'] as string)).toBeInTheDocument();
@@ -108,43 +117,30 @@ describe('DocViewerTable', () => {
108117
});
109118

110119
it('should find by field name', async () => {
111-
render(
112-
<IntlProvider locale="en">
113-
<DocViewerTable dataView={dataView} hit={hit} columns={[]} />
114-
</IntlProvider>
115-
);
120+
const { user } = setupComponent();
116121

117122
expect(screen.getByText('@timestamp')).toBeInTheDocument();
118123
expect(screen.getByText('bytes')).toBeInTheDocument();
119124
expect(screen.getByText('extension.keyword')).toBeInTheDocument();
120125

121-
act(() => {
122-
fireEvent.change(screen.getByTestId('unifiedDocViewerFieldsSearchInput'), {
123-
target: { value: 'bytes' },
124-
});
125-
});
126+
await user.type(screen.getByTestId('unifiedDocViewerFieldsSearchInput'), 'bytes');
126127

127128
expect(screen.queryByText('@timestamp')).toBeNull();
128129
expect(screen.queryByText('bytes')).toBeInTheDocument();
129130
expect(screen.queryByText('extension.keyword')).toBeNull();
130131
});
131132

132133
it('should find by field value', async () => {
133-
render(
134-
<IntlProvider locale="en">
135-
<DocViewerTable dataView={dataView} hit={hit} columns={[]} />
136-
</IntlProvider>
137-
);
134+
const { user } = setupComponent();
138135

139136
expect(screen.getByText('@timestamp')).toBeInTheDocument();
140137
expect(screen.getByText('bytes')).toBeInTheDocument();
141138
expect(screen.getByText('extension.keyword')).toBeInTheDocument();
142139

143-
act(() => {
144-
fireEvent.change(screen.getByTestId('unifiedDocViewerFieldsSearchInput'), {
145-
target: { value: hit.flattened['extension.keyword'] as string },
146-
});
147-
});
140+
await user.type(
141+
screen.getByTestId('unifiedDocViewerFieldsSearchInput'),
142+
String(hit.flattened['extension.keyword'])
143+
);
148144

149145
expect(screen.queryByText('@timestamp')).toBeNull();
150146
expect(screen.queryByText('bytes')).toBeNull();
@@ -153,83 +149,75 @@ describe('DocViewerTable', () => {
153149
});
154150

155151
describe('switch - show only selected fields', () => {
156-
it('should disable the switch if columns is empty', async () => {
157-
render(
158-
<IntlProvider locale="en">
159-
<DocViewerTable dataView={dataView} hit={hit} columns={[]} />
160-
</IntlProvider>
161-
);
152+
describe('when there is a filter function', () => {
153+
it('should disable the switch if columns is empty', async () => {
154+
setupComponent({ filter: jest.fn() });
155+
156+
expect(screen.getByTestId('unifiedDocViewerShowOnlySelectedFieldsSwitch')).toBeDisabled();
157+
expect(screen.getByText('@timestamp')).toBeInTheDocument();
158+
expect(screen.getByText('bytes')).toBeInTheDocument();
159+
expect(screen.getByText('extension.keyword')).toBeInTheDocument();
160+
});
162161

163-
expect(screen.getByTestId('unifiedDocViewerShowOnlySelectedFieldsSwitch')).toBeDisabled();
164-
expect(screen.getByText('@timestamp')).toBeInTheDocument();
165-
expect(screen.getByText('bytes')).toBeInTheDocument();
166-
expect(screen.getByText('extension.keyword')).toBeInTheDocument();
167-
});
162+
it('should disable the switch even if it was previously switched on', async () => {
163+
storage.set(SHOW_ONLY_SELECTED_FIELDS, true);
168164

169-
it('should disable the switch even if it was previously switched on', async () => {
170-
storage.set(SHOW_ONLY_SELECTED_FIELDS, true);
165+
setupComponent({ filter: jest.fn() });
171166

172-
render(
173-
<IntlProvider locale="en">
174-
<DocViewerTable dataView={dataView} hit={hit} columns={[]} />
175-
</IntlProvider>
176-
);
167+
expect(screen.getByTestId('unifiedDocViewerShowOnlySelectedFieldsSwitch')).toBeDisabled();
168+
expect(screen.getByText('@timestamp')).toBeInTheDocument();
169+
expect(screen.getByText('bytes')).toBeInTheDocument();
170+
expect(screen.getByText('extension.keyword')).toBeInTheDocument();
171+
});
177172

178-
expect(screen.getByTestId('unifiedDocViewerShowOnlySelectedFieldsSwitch')).toBeDisabled();
179-
expect(screen.getByText('@timestamp')).toBeInTheDocument();
180-
expect(screen.getByText('bytes')).toBeInTheDocument();
181-
expect(screen.getByText('extension.keyword')).toBeInTheDocument();
182-
});
173+
it('should show only selected fields if it was previously switched on', async () => {
174+
storage.set(SHOW_ONLY_SELECTED_FIELDS, true);
183175

184-
it('should show only selected fields if it was previously switched on', async () => {
185-
storage.set(SHOW_ONLY_SELECTED_FIELDS, true);
176+
setupComponent({ columns: ['extension.keyword'], filter: jest.fn() });
186177

187-
render(
188-
<IntlProvider locale="en">
189-
<DocViewerTable dataView={dataView} hit={hit} columns={['extension.keyword']} />
190-
</IntlProvider>
191-
);
178+
expect(screen.getByTestId('unifiedDocViewerShowOnlySelectedFieldsSwitch')).toBeEnabled();
179+
expect(screen.getByText('@timestamp')).toBeInTheDocument();
180+
expect(screen.queryByText('bytes')).toBeNull();
181+
expect(screen.getByText('extension.keyword')).toBeInTheDocument();
182+
});
192183

193-
expect(screen.getByTestId('unifiedDocViewerShowOnlySelectedFieldsSwitch')).toBeEnabled();
194-
expect(screen.getByText('@timestamp')).toBeInTheDocument();
195-
expect(screen.queryByText('bytes')).toBeNull();
196-
expect(screen.getByText('extension.keyword')).toBeInTheDocument();
197-
});
184+
it('should allow toggling the switch', async () => {
185+
const { user } = setupComponent({ columns: ['bytes'], filter: jest.fn() });
198186

199-
it('should allow toggling the switch', async () => {
200-
render(
201-
<IntlProvider locale="en">
202-
<DocViewerTable dataView={dataView} hit={hit} columns={['bytes']} />
203-
</IntlProvider>
204-
);
187+
const showOnlySelectedFieldsSwitch = screen.getByTestId(
188+
'unifiedDocViewerShowOnlySelectedFieldsSwitch'
189+
);
205190

206-
const showOnlySelectedFieldsSwitch = screen.getByTestId(
207-
'unifiedDocViewerShowOnlySelectedFieldsSwitch'
208-
);
191+
expect(showOnlySelectedFieldsSwitch).toBeEnabled();
192+
expect(showOnlySelectedFieldsSwitch).toHaveValue('');
193+
expect(screen.getByText('@timestamp')).toBeInTheDocument();
194+
expect(screen.getByText('bytes')).toBeInTheDocument();
195+
expect(screen.getByText('extension.keyword')).toBeInTheDocument();
209196

210-
expect(showOnlySelectedFieldsSwitch).toBeEnabled();
211-
expect(showOnlySelectedFieldsSwitch).toHaveValue('');
212-
expect(screen.getByText('@timestamp')).toBeInTheDocument();
213-
expect(screen.getByText('bytes')).toBeInTheDocument();
214-
expect(screen.getByText('extension.keyword')).toBeInTheDocument();
197+
await user.click(showOnlySelectedFieldsSwitch);
215198

216-
act(() => {
217-
showOnlySelectedFieldsSwitch.click();
218-
});
199+
expect(screen.getByText('@timestamp')).toBeInTheDocument();
200+
expect(screen.getByText('bytes')).toBeInTheDocument();
201+
expect(screen.queryByText('extension.keyword')).toBeNull();
202+
expect(storage.get(SHOW_ONLY_SELECTED_FIELDS)).toBe(true);
219203

220-
expect(screen.getByText('@timestamp')).toBeInTheDocument();
221-
expect(screen.getByText('bytes')).toBeInTheDocument();
222-
expect(screen.queryByText('extension.keyword')).toBeNull();
223-
expect(storage.get(SHOW_ONLY_SELECTED_FIELDS)).toBe(true);
204+
await user.click(showOnlySelectedFieldsSwitch);
224205

225-
act(() => {
226-
showOnlySelectedFieldsSwitch.click();
206+
expect(screen.getByText('@timestamp')).toBeInTheDocument();
207+
expect(screen.getByText('bytes')).toBeInTheDocument();
208+
expect(screen.getByText('extension.keyword')).toBeInTheDocument();
209+
expect(storage.get(SHOW_ONLY_SELECTED_FIELDS)).toBe(false);
227210
});
211+
});
228212

229-
expect(screen.getByText('@timestamp')).toBeInTheDocument();
230-
expect(screen.getByText('bytes')).toBeInTheDocument();
231-
expect(screen.getByText('extension.keyword')).toBeInTheDocument();
232-
expect(storage.get(SHOW_ONLY_SELECTED_FIELDS)).toBe(false);
213+
describe('when there is no filter function', () => {
214+
it('should not render the switch', () => {
215+
setupComponent({ columns: ['bytes'] });
216+
217+
expect(
218+
screen.queryByTestId('unifiedDocViewerShowOnlySelectedFieldsSwitch')
219+
).not.toBeInTheDocument();
220+
});
233221
});
234222
});
235223
});

src/platform/plugins/shared/unified_doc_viewer/public/components/doc_viewer_table/table.tsx

Lines changed: 15 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -464,19 +464,21 @@ export const DocViewerTable = ({
464464
alignItems="center"
465465
gutterSize="m"
466466
>
467-
<EuiFlexItem grow={false}>
468-
<EuiSwitch
469-
label={i18n.translate('unifiedDocViewer.showOnlySelectedFields.switchLabel', {
470-
defaultMessage: 'Selected only',
471-
description: 'Switch label to show only selected fields in the table',
472-
})}
473-
checked={showOnlySelectedFields ?? false}
474-
disabled={isShowOnlySelectedFieldsDisabled}
475-
onChange={onShowOnlySelectedFieldsChange}
476-
compressed
477-
data-test-subj="unifiedDocViewerShowOnlySelectedFieldsSwitch"
478-
/>
479-
</EuiFlexItem>
467+
{filter && (
468+
<EuiFlexItem grow={false}>
469+
<EuiSwitch
470+
label={i18n.translate('unifiedDocViewer.showOnlySelectedFields.switchLabel', {
471+
defaultMessage: 'Selected only',
472+
description: 'Switch label to show only selected fields in the table',
473+
})}
474+
checked={showOnlySelectedFields ?? false}
475+
disabled={isShowOnlySelectedFieldsDisabled}
476+
onChange={onShowOnlySelectedFieldsChange}
477+
compressed
478+
data-test-subj="unifiedDocViewerShowOnlySelectedFieldsSwitch"
479+
/>
480+
</EuiFlexItem>
481+
)}
480482
{isEsqlMode && (
481483
<EuiFlexItem grow={false}>
482484
<EuiSwitch

0 commit comments

Comments
 (0)