Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[7.x] Drilldowns (#59632) #61032

Closed
wants to merge 2 commits into from
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion examples/ui_action_examples/public/plugin.ts
Original file line number Diff line number Diff line change
Expand Up @@ -46,7 +46,7 @@ export class UiActionExamplesPlugin
}));

uiActions.registerAction(helloWorldAction);
uiActions.attachAction(helloWorldTrigger.id, helloWorldAction);
uiActions.addTriggerAction(helloWorldTrigger.id, helloWorldAction);
}

public start() {}
Expand Down
3 changes: 1 addition & 2 deletions examples/ui_actions_explorer/public/app.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -95,8 +95,7 @@ const ActionsExplorer = ({ uiActionsApi, openModal }: Props) => {
);
},
});
uiActionsApi.registerAction(dynamicAction);
uiActionsApi.attachAction(HELLO_WORLD_TRIGGER_ID, dynamicAction);
uiActionsApi.addTriggerAction(HELLO_WORLD_TRIGGER_ID, dynamicAction);
setConfirmationText(
`You've successfully added a new action: ${dynamicAction.getDisplayName(
{}
Expand Down
16 changes: 8 additions & 8 deletions examples/ui_actions_explorer/public/plugin.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -79,21 +79,21 @@ export class UiActionsExplorerPlugin implements Plugin<void, void, {}, StartDeps

const startServices = core.getStartServices();

deps.uiActions.attachAction(
deps.uiActions.addTriggerAction(
USER_TRIGGER,
createPhoneUserAction(async () => (await startServices)[1].uiActions)
);
deps.uiActions.attachAction(
deps.uiActions.addTriggerAction(
USER_TRIGGER,
createEditUserAction(async () => (await startServices)[0].overlays.openModal)
);

deps.uiActions.attachAction(COUNTRY_TRIGGER, viewInMapsAction);
deps.uiActions.attachAction(COUNTRY_TRIGGER, lookUpWeatherAction);
deps.uiActions.attachAction(COUNTRY_TRIGGER, showcasePluggability);
deps.uiActions.attachAction(PHONE_TRIGGER, makePhoneCallAction);
deps.uiActions.attachAction(PHONE_TRIGGER, showcasePluggability);
deps.uiActions.attachAction(USER_TRIGGER, showcasePluggability);
deps.uiActions.addTriggerAction(COUNTRY_TRIGGER, viewInMapsAction);
deps.uiActions.addTriggerAction(COUNTRY_TRIGGER, lookUpWeatherAction);
deps.uiActions.addTriggerAction(COUNTRY_TRIGGER, showcasePluggability);
deps.uiActions.addTriggerAction(PHONE_TRIGGER, makePhoneCallAction);
deps.uiActions.addTriggerAction(PHONE_TRIGGER, showcasePluggability);
deps.uiActions.addTriggerAction(USER_TRIGGER, showcasePluggability);

core.application.register({
id: 'uiActionsExplorer',
Expand Down
1 change: 1 addition & 0 deletions src/core/public/overlays/flyout/flyout_service.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -91,6 +91,7 @@ export interface OverlayFlyoutStart {
export interface OverlayFlyoutOpenOptions {
className?: string;
closeButtonAriaLabel?: string;
ownFocus?: boolean;
'data-test-subj'?: string;
}

Expand Down
4 changes: 3 additions & 1 deletion src/dev/storybook/aliases.ts
Original file line number Diff line number Diff line change
Expand Up @@ -18,12 +18,14 @@
*/

export const storybookAliases = {
advanced_ui_actions: 'x-pack/plugins/advanced_ui_actions/scripts/storybook.js',
apm: 'x-pack/legacy/plugins/apm/scripts/storybook.js',
canvas: 'x-pack/legacy/plugins/canvas/scripts/storybook_new.js',
codeeditor: 'src/plugins/kibana_react/public/code_editor/scripts/storybook.ts',
dashboard_enhanced: 'x-pack/plugins/dashboard_enhanced/scripts/storybook.js',
drilldowns: 'x-pack/plugins/drilldowns/scripts/storybook.js',
embeddable: 'src/plugins/embeddable/scripts/storybook.js',
infra: 'x-pack/legacy/plugins/infra/scripts/storybook.js',
siem: 'x-pack/legacy/plugins/siem/scripts/storybook.js',
ui_actions: 'x-pack/plugins/advanced_ui_actions/scripts/storybook.js',
ui_actions: 'src/plugins/ui_actions/scripts/storybook.js',
};
Original file line number Diff line number Diff line change
Expand Up @@ -45,6 +45,7 @@ import { PersistedState } from '../../../../../../../plugins/visualizations/publ
import { buildPipeline } from '../legacy/build_pipeline';
import { Vis } from '../vis';
import { getExpressions, getUiActions } from '../services';
import { VisualizationsStartDeps } from '../plugin';
import { VIS_EVENT_TO_TRIGGER } from './events';

const getKeys = <T extends {}>(o: T): Array<keyof T> => Object.keys(o) as Array<keyof T>;
Expand All @@ -56,6 +57,7 @@ export interface VisualizeEmbeddableConfiguration {
editable: boolean;
appState?: { save(): void };
uiState?: PersistedState;
uiActions?: VisualizationsStartDeps['uiActions'];
}

export interface VisualizeInput extends EmbeddableInput {
Expand Down Expand Up @@ -94,7 +96,7 @@ export class VisualizeEmbeddable extends Embeddable<VisualizeInput, VisualizeOut

constructor(
timefilter: TimefilterContract,
{ vis, editUrl, indexPatterns, editable }: VisualizeEmbeddableConfiguration,
{ vis, editUrl, indexPatterns, editable, uiActions }: VisualizeEmbeddableConfiguration,
initialInput: VisualizeInput,
parent?: Container
) {
Expand All @@ -107,7 +109,8 @@ export class VisualizeEmbeddable extends Embeddable<VisualizeInput, VisualizeOut
editable,
visTypeName: vis.type.name,
},
parent
parent,
{ uiActions }
);
this.timefilter = timefilter;
this.vis = vis;
Expand Down Expand Up @@ -265,6 +268,7 @@ export class VisualizeEmbeddable extends Embeddable<VisualizeInput, VisualizeOut
timeFieldName: this.vis.data.indexPattern!.timeFieldName!,
data: event.data,
};

getUiActions()
.getTrigger(triggerId)
.exec(context);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -38,6 +38,7 @@ import {
getTimeFilter,
} from '../services';
import { showNewVisModal } from '../wizard';
import { VisualizationsStartDeps } from '../plugin';
import { convertToSerializedVis } from '../saved_visualizations/_saved_vis';

interface VisualizationAttributes extends SavedObjectAttributes {
Expand All @@ -52,7 +53,11 @@ export class VisualizeEmbeddableFactory extends EmbeddableFactory<
> {
public readonly type = VISUALIZE_EMBEDDABLE_TYPE;

constructor() {
constructor(
private readonly getUiActions: () => Promise<
Pick<VisualizationsStartDeps, 'uiActions'>['uiActions']
>
) {
super({
savedObjectMetaData: {
name: i18n.translate('visualizations.savedObjectName', { defaultMessage: 'Visualization' }),
Expand Down Expand Up @@ -114,6 +119,8 @@ export class VisualizeEmbeddableFactory extends EmbeddableFactory<

const indexPattern = vis.data.indexPattern;
const indexPatterns = indexPattern ? [indexPattern] : [];
const uiActions = await this.getUiActions();

const editable = await this.isEditable();
return new VisualizeEmbeddable(
getTimeFilter(),
Expand All @@ -124,6 +131,7 @@ export class VisualizeEmbeddableFactory extends EmbeddableFactory<
editable,
appState: input.appState,
uiState: input.uiState,
uiActions,
},
input,
parent
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,7 @@
* under the License.
*/

import { PluginInitializerContext } from '../../../../../../core/public';
import { CoreSetup, PluginInitializerContext } from '../../../../../../core/public';
import { VisualizationsSetup, VisualizationsStart } from './';
import { VisualizationsPlugin } from './plugin';
import { coreMock } from '../../../../../../core/public/mocks';
Expand All @@ -26,6 +26,7 @@ import { expressionsPluginMock } from '../../../../../../plugins/expressions/pub
import { dataPluginMock } from '../../../../../../plugins/data/public/mocks';
import { usageCollectionPluginMock } from '../../../../../../plugins/usage_collection/public/mocks';
import { uiActionsPluginMock } from '../../../../../../plugins/ui_actions/public/mocks';
import { VisualizationsStartDeps } from './plugin';

const createSetupContract = (): VisualizationsSetup => ({
createBaseVisualization: jest.fn(),
Expand All @@ -48,7 +49,7 @@ const createStartContract = (): VisualizationsStart => ({
const createInstance = async () => {
const plugin = new VisualizationsPlugin({} as PluginInitializerContext);

const setup = plugin.setup(coreMock.createSetup(), {
const setup = plugin.setup(coreMock.createSetup() as CoreSetup<VisualizationsStartDeps>, {
data: dataPluginMock.createSetupContract(),
expressions: expressionsPluginMock.createSetupContract(),
embeddable: embeddablePluginMock.createSetupContract(),
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -111,7 +111,7 @@ export class VisualizationsPlugin
constructor(initializerContext: PluginInitializerContext) {}

public setup(
core: CoreSetup,
core: CoreSetup<VisualizationsStartDeps>,
{ expressions, embeddable, usageCollection, data }: VisualizationsSetupDeps
): VisualizationsSetup {
setUISettings(core.uiSettings);
Expand All @@ -120,7 +120,9 @@ export class VisualizationsPlugin
expressions.registerFunction(visualizationFunction);
expressions.registerRenderer(visualizationRenderer);

const embeddableFactory = new VisualizeEmbeddableFactory();
const embeddableFactory = new VisualizeEmbeddableFactory(
async () => (await core.getStartServices())[1].uiActions
);
embeddable.registerEmbeddableFactory(VISUALIZE_EMBEDDABLE_TYPE, embeddableFactory);

return {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -37,7 +37,7 @@ export interface ReplacePanelActionContext {
export class ReplacePanelAction implements ActionByType<typeof ACTION_REPLACE_PANEL> {
public readonly type = ACTION_REPLACE_PANEL;
public readonly id = ACTION_REPLACE_PANEL;
public order = 11;
public order = 3;

constructor(
private core: CoreStart,
Expand Down
4 changes: 2 additions & 2 deletions src/plugins/dashboard/public/plugin.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -78,7 +78,7 @@ export class DashboardEmbeddableContainerPublicPlugin
): Setup {
const expandPanelAction = new ExpandPanelAction();
uiActions.registerAction(expandPanelAction);
uiActions.attachAction(CONTEXT_MENU_TRIGGER, expandPanelAction);
uiActions.attachAction(CONTEXT_MENU_TRIGGER, expandPanelAction.id);
const startServices = core.getStartServices();

if (share) {
Expand Down Expand Up @@ -134,7 +134,7 @@ export class DashboardEmbeddableContainerPublicPlugin
plugins.embeddable.getEmbeddableFactories
);
uiActions.registerAction(changeViewAction);
uiActions.attachAction(CONTEXT_MENU_TRIGGER, changeViewAction);
uiActions.addTriggerAction(CONTEXT_MENU_TRIGGER, changeViewAction);
}

public stop() {}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -49,7 +49,7 @@ test('DashboardContainer in edit mode shows edit mode actions', async () => {

const editModeAction = createEditModeAction();
uiActionsSetup.registerAction(editModeAction);
uiActionsSetup.attachAction(CONTEXT_MENU_TRIGGER, editModeAction);
uiActionsSetup.addTriggerAction(CONTEXT_MENU_TRIGGER, editModeAction);
setup.registerEmbeddableFactory(
CONTACT_CARD_EMBEDDABLE,
new ContactCardEmbeddableFactory({} as any, (() => null) as any, {} as any)
Expand Down
9 changes: 6 additions & 3 deletions src/plugins/data/public/plugin.ts
Original file line number Diff line number Diff line change
Expand Up @@ -109,12 +109,12 @@ export class DataPublicPlugin implements Plugin<DataPublicPluginSetup, DataPubli
createFilterAction(queryService.filterManager, queryService.timefilter.timefilter)
);

uiActions.attachAction(
uiActions.addTriggerAction(
SELECT_RANGE_TRIGGER,
selectRangeAction(queryService.filterManager, queryService.timefilter.timefilter)
);

uiActions.attachAction(
uiActions.addTriggerAction(
VALUE_CLICK_TRIGGER,
valueClickAction(queryService.filterManager, queryService.timefilter.timefilter)
);
Expand Down Expand Up @@ -146,7 +146,10 @@ export class DataPublicPlugin implements Plugin<DataPublicPluginSetup, DataPubli
const search = this.searchService.start(core);
setSearchService(search);

uiActions.attachAction(APPLY_FILTER_TRIGGER, uiActions.getAction(ACTION_GLOBAL_APPLY_FILTER));
uiActions.addTriggerAction(
APPLY_FILTER_TRIGGER,
uiActions.getAction(ACTION_GLOBAL_APPLY_FILTER)
);

const dataServices = {
actions: {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -33,7 +33,7 @@ interface ActionContext {
export class EditPanelAction implements Action<ActionContext> {
public readonly type = ACTION_EDIT_PANEL;
public readonly id = ACTION_EDIT_PANEL;
public order = 15;
public order = 50;

constructor(private readonly getEmbeddableFactory: EmbeddableStart['getEmbeddableFactory']) {}

Expand Down
73 changes: 65 additions & 8 deletions src/plugins/embeddable/public/lib/embeddables/embeddable.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -16,23 +16,35 @@
* specific language governing permissions and limitations
* under the License.
*/
import { isEqual, cloneDeep } from 'lodash';
import { cloneDeep, isEqual } from 'lodash';
import * as Rx from 'rxjs';
import { Adapters } from '../types';
import { Adapters, ViewMode } from '../types';
import { IContainer } from '../containers';
import { IEmbeddable, EmbeddableInput, EmbeddableOutput } from './i_embeddable';
import { ViewMode } from '../types';
import { EmbeddableInput, EmbeddableOutput, IEmbeddable } from './i_embeddable';
import { TriggerContextMapping } from '../ui_actions';
import { EmbeddableActionStorage } from './embeddable_action_storage';
import {
UiActionsDynamicActionManager,
UiActionsStart,
} from '../../../../../plugins/ui_actions/public';
import { EmbeddableContext } from '../triggers';

function getPanelTitle(input: EmbeddableInput, output: EmbeddableOutput) {
return input.hidePanelTitles ? '' : input.title === undefined ? output.defaultTitle : input.title;
}

export interface EmbeddableParams {
uiActions?: UiActionsStart;
}

export abstract class Embeddable<
TEmbeddableInput extends EmbeddableInput = EmbeddableInput,
TEmbeddableOutput extends EmbeddableOutput = EmbeddableOutput
> implements IEmbeddable<TEmbeddableInput, TEmbeddableOutput> {
static runtimeId: number = 0;

public readonly runtimeId = Embeddable.runtimeId++;

public readonly parent?: IContainer;
public readonly isContainer: boolean = false;
public abstract readonly type: string;
Expand All @@ -48,15 +60,34 @@ export abstract class Embeddable<
// to update input when the parent changes.
private parentSubscription?: Rx.Subscription;

private storageSubscription?: Rx.Subscription;

// TODO: Rename to destroyed.
private destoyed: boolean = false;

private __actionStorage?: EmbeddableActionStorage;
public get actionStorage(): EmbeddableActionStorage {
return this.__actionStorage || (this.__actionStorage = new EmbeddableActionStorage(this));
private storage = new EmbeddableActionStorage((this as unknown) as Embeddable);

private cachedDynamicActions?: UiActionsDynamicActionManager;
public get dynamicActions(): UiActionsDynamicActionManager | undefined {
if (!this.params.uiActions) return undefined;
if (!this.cachedDynamicActions) {
this.cachedDynamicActions = new UiActionsDynamicActionManager({
isCompatible: async (context: unknown) =>
(context as EmbeddableContext).embeddable.runtimeId === this.runtimeId,
storage: this.storage,
uiActions: this.params.uiActions,
});
}

return this.cachedDynamicActions;
}

constructor(input: TEmbeddableInput, output: TEmbeddableOutput, parent?: IContainer) {
constructor(
input: TEmbeddableInput,
output: TEmbeddableOutput,
parent?: IContainer,
public readonly params: EmbeddableParams = {}
) {
this.id = input.id;
this.output = {
title: getPanelTitle(input, output),
Expand All @@ -80,6 +111,18 @@ export abstract class Embeddable<
this.onResetInput(newInput);
});
}

if (this.dynamicActions) {
this.dynamicActions.start().catch(error => {
/* eslint-disable */
console.log('Failed to start embeddable dynamic actions', this);
console.error(error);
/* eslint-enable */
});
this.storageSubscription = this.input$.subscribe(() => {
this.storage.reload$.next();
});
}
}

public getIsContainer(): this is IContainer {
Expand Down Expand Up @@ -158,6 +201,20 @@ export abstract class Embeddable<
*/
public destroy(): void {
this.destoyed = true;

if (this.dynamicActions) {
this.dynamicActions.stop().catch(error => {
/* eslint-disable */
console.log('Failed to stop embeddable dynamic actions', this);
console.error(error);
/* eslint-enable */
});
}

if (this.storageSubscription) {
this.storageSubscription.unsubscribe();
}

if (this.parentSubscription) {
this.parentSubscription.unsubscribe();
}
Expand Down
Loading