Skip to content

Commit fde9539

Browse files
[TextBased] Allow inline editing from dashboards (#161146)
## Summary Part of #158802 For panels created from Discover with text based languages, not navigate to Lens but open a flyout instead. ![sql](https://github.com/elastic/kibana/assets/17003240/489402ac-dcdb-468b-89b9-a84f4c4f2ca5) Follow up PR: - Remove the SQL option from Lens dataview picker and move the FTs in Discover/Dashboard Note: - Changing the query on the dashboard level is going to be added in 8.11 ### Checklist - [ ] 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/packages/kbn-i18n/README.md) - [ ] [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 - [ ] Any UI touched in this PR is usable by keyboard only (learn more about [keyboard accessibility](https://webaim.org/techniques/keyboard/)) - [ ] Any UI touched in this PR does not create any new axe failures (run axe in browser: [FF](https://addons.mozilla.org/en-US/firefox/addon/axe-devtools/), [Chrome](https://chrome.google.com/webstore/detail/axe-web-accessibility-tes/lhdoppojpmngadmnindnejefpokejbdd?hl=en-US)) - [ ] This renders correctly on smaller devices using a responsive layout. (You can test this [in your browser](https://www.browserstack.com/guide/responsive-testing-on-local-server)) - [ ] This was checked for [cross-browser compatibility](https://www.elastic.co/support/matrix#matrix_browsers) --------- Co-authored-by: kibanamachine <[email protected]>
1 parent 3495720 commit fde9539

File tree

19 files changed

+467
-69
lines changed

19 files changed

+467
-69
lines changed

packages/kbn-optimizer/limits.yml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -83,7 +83,7 @@ pageLoadAssetSize:
8383
kibanaUsageCollection: 16463
8484
kibanaUtils: 79713
8585
kubernetesSecurity: 77234
86-
lens: 37000
86+
lens: 38000
8787
licenseManagement: 41817
8888
licensing: 29004
8989
lists: 22900

src/plugins/dashboard/public/dashboard_actions/filters_notification_popover.tsx

Lines changed: 25 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -40,6 +40,7 @@ export function FiltersNotificationPopover({
4040
}: FiltersNotificationProps) {
4141
const { embeddable } = context;
4242
const [isPopoverOpen, setIsPopoverOpen] = useState(false);
43+
const [disableEditbutton, setDisableEditButton] = useState(false);
4344

4445
return (
4546
<EuiPopover
@@ -57,26 +58,31 @@ export function FiltersNotificationPopover({
5758
anchorPosition="upCenter"
5859
>
5960
<EuiPopoverTitle>{displayName}</EuiPopoverTitle>
60-
<FiltersNotificationPopoverContents context={context} />
61+
<FiltersNotificationPopoverContents
62+
context={context}
63+
setDisableEditButton={setDisableEditButton}
64+
/>
6165
<EuiPopoverFooter>
62-
<EuiFlexGroup
63-
gutterSize="s"
64-
alignItems="center"
65-
justifyContent="flexEnd"
66-
responsive={false}
67-
wrap={true}
68-
>
69-
<EuiFlexItem grow={false}>
70-
<EuiButton
71-
data-test-subj={'filtersNotificationModal__editButton'}
72-
size="s"
73-
fill
74-
onClick={() => editPanelAction.execute({ embeddable })}
75-
>
76-
{dashboardFilterNotificationActionStrings.getEditButtonTitle()}
77-
</EuiButton>
78-
</EuiFlexItem>
79-
</EuiFlexGroup>
66+
{!disableEditbutton && (
67+
<EuiFlexGroup
68+
gutterSize="s"
69+
alignItems="center"
70+
justifyContent="flexEnd"
71+
responsive={false}
72+
wrap={true}
73+
>
74+
<EuiFlexItem grow={false}>
75+
<EuiButton
76+
data-test-subj={'filtersNotificationModal__editButton'}
77+
size="s"
78+
fill
79+
onClick={() => editPanelAction.execute({ embeddable })}
80+
>
81+
{dashboardFilterNotificationActionStrings.getEditButtonTitle()}
82+
</EuiButton>
83+
</EuiFlexItem>
84+
</EuiFlexGroup>
85+
)}
8086
</EuiPopoverFooter>
8187
</EuiPopover>
8288
);

src/plugins/dashboard/public/dashboard_actions/filters_notification_popover_contents.tsx

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -26,9 +26,13 @@ import { DashboardContainer } from '../dashboard_container/embeddable/dashboard_
2626

2727
export interface FiltersNotificationProps {
2828
context: FiltersNotificationActionContext;
29+
setDisableEditButton: (flag: boolean) => void;
2930
}
3031

31-
export function FiltersNotificationPopoverContents({ context }: FiltersNotificationProps) {
32+
export function FiltersNotificationPopoverContents({
33+
context,
34+
setDisableEditButton,
35+
}: FiltersNotificationProps) {
3236
const { embeddable } = context;
3337
const [isLoading, setIsLoading] = useState(true);
3438
const [filters, setFilters] = useState<Filter[]>([]);
@@ -53,6 +57,7 @@ export function FiltersNotificationPopoverContents({ context }: FiltersNotificat
5357
const language = getAggregateQueryMode(embeddableQuery);
5458
setQueryLanguage(language);
5559
setQueryString(embeddableQuery[language as keyof AggregateQuery]);
60+
setDisableEditButton(true);
5661
}
5762
}
5863
setIsLoading(false);

src/plugins/unified_histogram/public/chart/hooks/use_chart_config_panel.tsx

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -67,7 +67,10 @@ export function useChartConfigPanel({
6767
dataView={dataView}
6868
adaptersTables={lensTablesAdapter}
6969
updateAll={updateSuggestion}
70-
setIsFlyoutVisible={setIsFlyoutVisible}
70+
closeFlyout={() => {
71+
setIsFlyoutVisible(false);
72+
}}
73+
wrapInFlyout
7174
datasourceId="textBased"
7275
/>
7376
);

src/plugins/unified_histogram/public/chart/utils/get_lens_attributes.test.ts

Lines changed: 37 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -740,6 +740,43 @@ describe('getLensAttributes', () => {
740740
`);
741741
});
742742

743+
it('should return correct attributes for text based languages with adhoc dataview', () => {
744+
const adHocDataview = {
745+
...dataView,
746+
isPersisted: () => false,
747+
} as DataView;
748+
const lensAttrs = getLensAttributes({
749+
title: 'test',
750+
filters,
751+
query,
752+
dataView: adHocDataview,
753+
timeInterval,
754+
breakdownField: undefined,
755+
suggestion: currentSuggestionMock,
756+
});
757+
expect(lensAttrs.attributes).toEqual({
758+
state: expect.objectContaining({
759+
adHocDataViews: {
760+
'index-pattern-with-timefield-id': {},
761+
},
762+
}),
763+
references: [
764+
{
765+
id: 'index-pattern-with-timefield-id',
766+
name: 'indexpattern-datasource-current-indexpattern',
767+
type: 'index-pattern',
768+
},
769+
{
770+
id: 'index-pattern-with-timefield-id',
771+
name: 'indexpattern-datasource-layer-unifiedHistogram',
772+
type: 'index-pattern',
773+
},
774+
],
775+
title: 'test',
776+
visualizationType: 'lnsHeatmap',
777+
});
778+
});
779+
743780
it('should return suggestion title if no title is given', () => {
744781
expect(
745782
getLensAttributes({

src/plugins/unified_histogram/public/chart/utils/get_lens_attributes.ts

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -205,6 +205,13 @@ export const getLensAttributes = ({
205205
filters,
206206
query,
207207
visualization,
208+
...(dataView &&
209+
dataView.id &&
210+
!dataView.isPersisted() && {
211+
adHocDataViews: {
212+
[dataView.id]: dataView.toSpec(false),
213+
},
214+
}),
208215
},
209216
visualizationType: suggestion ? suggestion.visualizationId : 'lnsXY',
210217
} as TypedLensByValueInput['attributes'];

x-pack/plugins/lens/public/app_plugin/shared/edit_on_the_fly/get_edit_lens_configuration.tsx

Lines changed: 32 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -51,7 +51,8 @@ export function getEditLensConfiguration(
5151
attributes,
5252
dataView,
5353
updateAll,
54-
setIsFlyoutVisible,
54+
closeFlyout,
55+
wrapInFlyout,
5556
datasourceId,
5657
adaptersTables,
5758
}: EditLensConfigurationProps) => {
@@ -88,15 +89,38 @@ export function getEditLensConfiguration(
8889
const lensStore: LensRootStore = makeConfigureStore(storeDeps, {
8990
lens: getPreloadedState(storeDeps) as LensAppState,
9091
} as unknown as PreloadedState<LensState>);
91-
const closeFlyout = () => {
92-
setIsFlyoutVisible?.(false);
92+
93+
const getWrapper = (children: JSX.Element) => {
94+
if (wrapInFlyout) {
95+
return (
96+
<EuiFlyout
97+
type="push"
98+
ownFocus
99+
onClose={() => {
100+
closeFlyout?.();
101+
}}
102+
aria-labelledby={i18n.translate('xpack.lens.config.editLabel', {
103+
defaultMessage: 'Edit configuration',
104+
})}
105+
size="s"
106+
hideCloseButton
107+
css={css`
108+
background: none;
109+
`}
110+
>
111+
{children}
112+
</EuiFlyout>
113+
);
114+
} else {
115+
return children;
116+
}
93117
};
94118

95119
const configPanelProps = {
96120
attributes,
97121
dataView,
98122
updateAll,
99-
setIsFlyoutVisible,
123+
closeFlyout,
100124
datasourceId,
101125
adaptersTables,
102126
coreStart,
@@ -105,25 +129,10 @@ export function getEditLensConfiguration(
105129
datasourceMap,
106130
};
107131

108-
return (
109-
<EuiFlyout
110-
type="push"
111-
ownFocus
112-
onClose={closeFlyout}
113-
aria-labelledby={i18n.translate('xpack.lens.config.editLabel', {
114-
defaultMessage: 'Edit configuration',
115-
})}
116-
size="s"
117-
className="lnsEditConfigurationFlyout"
118-
css={css`
119-
background: none;
120-
`}
121-
hideCloseButton
122-
>
123-
<Provider store={lensStore}>
124-
<LensEditConfigurationFlyout {...configPanelProps} />
125-
</Provider>
126-
</EuiFlyout>
132+
return getWrapper(
133+
<Provider store={lensStore}>
134+
<LensEditConfigurationFlyout {...configPanelProps} />
135+
</Provider>
127136
);
128137
};
129138
}

x-pack/plugins/lens/public/app_plugin/shared/edit_on_the_fly/lens_configuration_flyout.test.tsx

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -120,22 +120,22 @@ describe('LensEditConfigurationFlyout', () => {
120120
startDependencies,
121121
visualizationMap,
122122
datasourceMap,
123-
setIsFlyoutVisible: jest.fn(),
123+
closeFlyout: jest.fn(),
124124
datasourceId: 'testDatasource',
125125
} as unknown as EditConfigPanelProps;
126126
}
127127

128-
it('should call the setIsFlyout callback if collapse button is clicked', async () => {
129-
const setIsFlyoutVisibleSpy = jest.fn();
128+
it('should call the closeFlyout callback if collapse button is clicked', async () => {
129+
const closeFlyoutSpy = jest.fn();
130130
const props = getDefaultProps();
131131
const newProps = {
132132
...props,
133-
setIsFlyoutVisible: setIsFlyoutVisibleSpy,
133+
closeFlyout: closeFlyoutSpy,
134134
};
135135
const { instance } = await prepareAndMountComponent(newProps);
136136
expect(instance.find(EuiFlyoutBody).exists()).toBe(true);
137137
instance.find('[data-test-subj="collapseFlyoutButton"]').at(1).simulate('click');
138-
expect(setIsFlyoutVisibleSpy).toHaveBeenCalled();
138+
expect(closeFlyoutSpy).toHaveBeenCalled();
139139
});
140140

141141
it('should compute the frame public api correctly', async () => {

x-pack/plugins/lens/public/app_plugin/shared/edit_on_the_fly/lens_configuration_flyout.tsx

Lines changed: 3 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -43,7 +43,8 @@ export interface EditConfigPanelProps {
4343
startDependencies: LensPluginStartDependencies;
4444
visualizationMap: VisualizationMap;
4545
datasourceMap: DatasourceMap;
46-
setIsFlyoutVisible?: (flag: boolean) => void;
46+
closeFlyout?: () => void;
47+
wrapInFlyout?: boolean;
4748
datasourceId: 'formBased' | 'textBased';
4849
adaptersTables?: Record<string, Datatable>;
4950
}
@@ -57,7 +58,7 @@ export function LensEditConfigurationFlyout({
5758
datasourceMap,
5859
datasourceId,
5960
updateAll,
60-
setIsFlyoutVisible,
61+
closeFlyout,
6162
adaptersTables,
6263
}: EditConfigPanelProps) {
6364
const currentDataViewId = dataView.id ?? '';
@@ -112,10 +113,6 @@ export function LensEditConfigurationFlyout({
112113
};
113114
}, [activeData, dataViews, datasourceLayers, dateRange]);
114115

115-
const closeFlyout = () => {
116-
setIsFlyoutVisible?.(false);
117-
};
118-
119116
const layerPanelsProps = {
120117
framePublicAPI,
121118
datasourceMap,

x-pack/plugins/lens/public/async_services.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -50,3 +50,4 @@ export * from './app_plugin/save_modal_container';
5050
export * from './chart_info_api';
5151

5252
export * from './trigger_actions/open_in_discover_helpers';
53+
export * from './trigger_actions/open_lens_config/helpers';

0 commit comments

Comments
 (0)