mirror of
https://github.com/elastic/kibana.git
synced 2025-04-24 09:48:58 -04:00
parent
ef7bf84503
commit
e34ee17574
11 changed files with 86 additions and 22 deletions
|
@ -441,14 +441,6 @@ function VisualizeAppController(
|
|||
})
|
||||
);
|
||||
|
||||
subscriptions.add(
|
||||
subscribeWithScope($scope, timefilter.getAutoRefreshFetch$(), {
|
||||
next: () => {
|
||||
$scope.vis.forceReload();
|
||||
},
|
||||
})
|
||||
);
|
||||
|
||||
$scope.$on('$destroy', () => {
|
||||
if ($scope._handler) {
|
||||
$scope._handler.destroy();
|
||||
|
|
|
@ -34,6 +34,7 @@ import {
|
|||
esFilters,
|
||||
Filter,
|
||||
ISearchSource,
|
||||
TimefilterContract,
|
||||
} from '../../../../../plugins/data/public';
|
||||
import {
|
||||
EmbeddableInput,
|
||||
|
@ -106,8 +107,10 @@ export class VisualizeEmbeddable extends Embeddable<VisualizeInput, VisualizeOut
|
|||
private vis: Vis;
|
||||
private domNode: any;
|
||||
public readonly type = VISUALIZE_EMBEDDABLE_TYPE;
|
||||
private autoRefreshFetchSubscription: Subscription;
|
||||
|
||||
constructor(
|
||||
timefilter: TimefilterContract,
|
||||
{
|
||||
savedVisualization,
|
||||
editUrl,
|
||||
|
@ -151,6 +154,10 @@ export class VisualizeEmbeddable extends Embeddable<VisualizeInput, VisualizeOut
|
|||
|
||||
this.vis._setUiState(this.uiState);
|
||||
|
||||
this.autoRefreshFetchSubscription = timefilter
|
||||
.getAutoRefreshFetch$()
|
||||
.subscribe(this.updateHandler.bind(this));
|
||||
|
||||
this.subscriptions.push(
|
||||
Rx.merge(this.getOutput$(), this.getInput$()).subscribe(() => {
|
||||
this.handleChanges();
|
||||
|
@ -345,6 +352,7 @@ export class VisualizeEmbeddable extends Embeddable<VisualizeInput, VisualizeOut
|
|||
this.handler.destroy();
|
||||
this.handler.getElement().remove();
|
||||
}
|
||||
this.autoRefreshFetchSubscription.unsubscribe();
|
||||
}
|
||||
|
||||
public reload = () => {
|
||||
|
|
|
@ -38,6 +38,7 @@ import { VISUALIZE_EMBEDDABLE_TYPE } from './constants';
|
|||
|
||||
import { getCapabilities, getHttp, getTypes, getUISettings } from '../np_ready/public/services';
|
||||
import { showNewVisModal } from '../np_ready/public/wizard';
|
||||
import { TimefilterContract } from '../../../../../plugins/data/public';
|
||||
|
||||
interface VisualizationAttributes extends SavedObjectAttributes {
|
||||
visState: string;
|
||||
|
@ -51,7 +52,10 @@ export class VisualizeEmbeddableFactory extends EmbeddableFactory<
|
|||
> {
|
||||
public readonly type = VISUALIZE_EMBEDDABLE_TYPE;
|
||||
|
||||
constructor(private getSavedVisualizationsLoader: () => SavedVisualizations) {
|
||||
constructor(
|
||||
private timefilter: TimefilterContract,
|
||||
private getSavedVisualizationsLoader: () => SavedVisualizations
|
||||
) {
|
||||
super({
|
||||
savedObjectMetaData: {
|
||||
name: i18n.translate('visualizations.savedObjectName', { defaultMessage: 'Visualization' }),
|
||||
|
@ -114,6 +118,7 @@ export class VisualizeEmbeddableFactory extends EmbeddableFactory<
|
|||
const indexPattern = await getIndexPattern(savedObject);
|
||||
const indexPatterns = indexPattern ? [indexPattern] : [];
|
||||
return new VisualizeEmbeddable(
|
||||
this.timefilter,
|
||||
{
|
||||
savedVisualization: savedObject,
|
||||
indexPatterns,
|
||||
|
|
|
@ -56,6 +56,7 @@ const createInstance = async () => {
|
|||
const plugin = new VisualizationsPlugin({} as PluginInitializerContext);
|
||||
|
||||
const setup = plugin.setup(coreMock.createSetup(), {
|
||||
data: dataPluginMock.createSetupContract(),
|
||||
expressions: expressionsPluginMock.createSetupContract(),
|
||||
embeddable: embeddablePluginMock.createStartContract(),
|
||||
usageCollection: usageCollectionPluginMock.createSetupContract(),
|
||||
|
|
|
@ -36,7 +36,10 @@ import { ExpressionsSetup } from '../../../../../../plugins/expressions/public';
|
|||
import { IEmbeddableSetup } from '../../../../../../plugins/embeddable/public';
|
||||
import { visualization as visualizationFunction } from './expressions/visualization_function';
|
||||
import { visualization as visualizationRenderer } from './expressions/visualization_renderer';
|
||||
import { DataPublicPluginStart } from '../../../../../../plugins/data/public';
|
||||
import {
|
||||
DataPublicPluginSetup,
|
||||
DataPublicPluginStart,
|
||||
} from '../../../../../../plugins/data/public';
|
||||
import { UsageCollectionSetup } from '../../../../../../plugins/usage_collection/public';
|
||||
import {
|
||||
createSavedVisLoader,
|
||||
|
@ -65,6 +68,7 @@ export interface VisualizationsSetupDeps {
|
|||
expressions: ExpressionsSetup;
|
||||
embeddable: IEmbeddableSetup;
|
||||
usageCollection: UsageCollectionSetup;
|
||||
data: DataPublicPluginSetup;
|
||||
}
|
||||
|
||||
export interface VisualizationsStartDeps {
|
||||
|
@ -95,7 +99,7 @@ export class VisualizationsPlugin
|
|||
|
||||
public setup(
|
||||
core: CoreSetup,
|
||||
{ expressions, embeddable, usageCollection }: VisualizationsSetupDeps
|
||||
{ expressions, embeddable, usageCollection, data }: VisualizationsSetupDeps
|
||||
): VisualizationsSetup {
|
||||
setUISettings(core.uiSettings);
|
||||
setUsageCollector(usageCollection);
|
||||
|
@ -103,7 +107,10 @@ export class VisualizationsPlugin
|
|||
expressions.registerFunction(visualizationFunction);
|
||||
expressions.registerRenderer(visualizationRenderer);
|
||||
|
||||
const embeddableFactory = new VisualizeEmbeddableFactory(this.getSavedVisualizationsLoader);
|
||||
const embeddableFactory = new VisualizeEmbeddableFactory(
|
||||
data.query.timefilter.timefilter,
|
||||
this.getSavedVisualizationsLoader
|
||||
);
|
||||
embeddable.registerEmbeddableFactory(VISUALIZE_EMBEDDABLE_TYPE, embeddableFactory);
|
||||
|
||||
return {
|
||||
|
|
|
@ -18,6 +18,7 @@
|
|||
*/
|
||||
|
||||
import { TimefilterService, TimeHistoryContract, TimefilterContract } from '.';
|
||||
import { Observable } from 'rxjs';
|
||||
|
||||
export type TimefilterServiceClientContract = PublicMethodsOf<TimefilterService>;
|
||||
|
||||
|
@ -28,7 +29,7 @@ const createSetupContractMock = () => {
|
|||
getEnabledUpdated$: jest.fn(),
|
||||
getTimeUpdate$: jest.fn(),
|
||||
getRefreshIntervalUpdate$: jest.fn(),
|
||||
getAutoRefreshFetch$: jest.fn(),
|
||||
getAutoRefreshFetch$: jest.fn(() => new Observable<unknown>()),
|
||||
getFetch$: jest.fn(),
|
||||
getTime: jest.fn(),
|
||||
setTime: jest.fn(),
|
||||
|
|
|
@ -4,10 +4,12 @@
|
|||
* you may not use this file except in compliance with the Elastic License.
|
||||
*/
|
||||
|
||||
import { Subject } from 'rxjs';
|
||||
import { Embeddable } from './embeddable';
|
||||
import { ReactExpressionRendererProps } from 'src/plugins/expressions/public';
|
||||
import { Query, TimeRange, Filter } from 'src/plugins/data/public';
|
||||
import { Query, TimeRange, Filter, TimefilterContract } from 'src/plugins/data/public';
|
||||
import { Document } from '../../persistence';
|
||||
import { dataPluginMock } from '../../../../../../../src/plugins/data/public/mocks';
|
||||
|
||||
jest.mock('../../../../../../../src/plugins/inspector/public/', () => ({
|
||||
isAvailable: false,
|
||||
|
@ -44,6 +46,7 @@ describe('embeddable', () => {
|
|||
|
||||
it('should render expression with expression renderer', () => {
|
||||
const embeddable = new Embeddable(
|
||||
dataPluginMock.createSetupContract().query.timefilter.timefilter,
|
||||
expressionRenderer,
|
||||
{
|
||||
editUrl: '',
|
||||
|
@ -64,6 +67,7 @@ describe('embeddable', () => {
|
|||
const filters: Filter[] = [{ meta: { alias: 'test', negate: false, disabled: false } }];
|
||||
|
||||
const embeddable = new Embeddable(
|
||||
dataPluginMock.createSetupContract().query.timefilter.timefilter,
|
||||
expressionRenderer,
|
||||
{
|
||||
editUrl: '',
|
||||
|
@ -89,6 +93,7 @@ describe('embeddable', () => {
|
|||
const filters: Filter[] = [{ meta: { alias: 'test', negate: false, disabled: false } }];
|
||||
|
||||
const embeddable = new Embeddable(
|
||||
dataPluginMock.createSetupContract().query.timefilter.timefilter,
|
||||
expressionRenderer,
|
||||
{
|
||||
editUrl: '',
|
||||
|
@ -112,6 +117,7 @@ describe('embeddable', () => {
|
|||
const filters: Filter[] = [{ meta: { alias: 'test', negate: false, disabled: true } }];
|
||||
|
||||
const embeddable = new Embeddable(
|
||||
dataPluginMock.createSetupContract().query.timefilter.timefilter,
|
||||
expressionRenderer,
|
||||
{
|
||||
editUrl: '',
|
||||
|
@ -130,4 +136,31 @@ describe('embeddable', () => {
|
|||
|
||||
expect(expressionRenderer).toHaveBeenCalledTimes(1);
|
||||
});
|
||||
|
||||
it('should re-render on auto refresh fetch observable', () => {
|
||||
const timeRange: TimeRange = { from: 'now-15d', to: 'now' };
|
||||
const query: Query = { language: 'kquery', query: '' };
|
||||
const filters: Filter[] = [{ meta: { alias: 'test', negate: false, disabled: true } }];
|
||||
|
||||
const autoRefreshFetchSubject = new Subject();
|
||||
const timefilter = ({
|
||||
getAutoRefreshFetch$: () => autoRefreshFetchSubject.asObservable(),
|
||||
} as unknown) as TimefilterContract;
|
||||
|
||||
const embeddable = new Embeddable(
|
||||
timefilter,
|
||||
expressionRenderer,
|
||||
{
|
||||
editUrl: '',
|
||||
editable: true,
|
||||
savedVis,
|
||||
},
|
||||
{ id: '123', timeRange, query, filters }
|
||||
);
|
||||
embeddable.render(mountpoint);
|
||||
|
||||
autoRefreshFetchSubject.next();
|
||||
|
||||
expect(expressionRenderer).toHaveBeenCalledTimes(2);
|
||||
});
|
||||
});
|
||||
|
|
|
@ -7,7 +7,13 @@
|
|||
import _ from 'lodash';
|
||||
import React from 'react';
|
||||
import { render, unmountComponentAtNode } from 'react-dom';
|
||||
import { Query, TimeRange, Filter, IIndexPattern } from 'src/plugins/data/public';
|
||||
import {
|
||||
Query,
|
||||
TimeRange,
|
||||
Filter,
|
||||
IIndexPattern,
|
||||
TimefilterContract,
|
||||
} from 'src/plugins/data/public';
|
||||
import { Subscription } from 'rxjs';
|
||||
import { ReactExpressionRendererType } from '../../../../../../../src/plugins/expressions/public';
|
||||
import {
|
||||
|
@ -43,6 +49,7 @@ export class Embeddable extends AbstractEmbeddable<LensEmbeddableInput, LensEmbe
|
|||
private savedVis: Document;
|
||||
private domNode: HTMLElement | Element | undefined;
|
||||
private subscription: Subscription;
|
||||
private autoRefreshFetchSubscription: Subscription;
|
||||
|
||||
private currentContext: {
|
||||
timeRange?: TimeRange;
|
||||
|
@ -52,6 +59,7 @@ export class Embeddable extends AbstractEmbeddable<LensEmbeddableInput, LensEmbe
|
|||
} = {};
|
||||
|
||||
constructor(
|
||||
timefilter: TimefilterContract,
|
||||
expressionRenderer: ReactExpressionRendererType,
|
||||
{ savedVis, editUrl, editable, indexPatterns }: LensEmbeddableConfiguration,
|
||||
initialInput: LensEmbeddableInput,
|
||||
|
@ -76,6 +84,10 @@ export class Embeddable extends AbstractEmbeddable<LensEmbeddableInput, LensEmbe
|
|||
this.savedVis = savedVis;
|
||||
this.subscription = this.getInput$().subscribe(input => this.onContainerStateChanged(input));
|
||||
this.onContainerStateChanged(initialInput);
|
||||
|
||||
this.autoRefreshFetchSubscription = timefilter
|
||||
.getAutoRefreshFetch$()
|
||||
.subscribe(this.reload.bind(this));
|
||||
}
|
||||
|
||||
onContainerStateChanged(containerState: LensEmbeddableInput) {
|
||||
|
@ -125,6 +137,7 @@ export class Embeddable extends AbstractEmbeddable<LensEmbeddableInput, LensEmbe
|
|||
if (this.subscription) {
|
||||
this.subscription.unsubscribe();
|
||||
}
|
||||
this.autoRefreshFetchSubscription.unsubscribe();
|
||||
}
|
||||
|
||||
reload() {
|
||||
|
|
|
@ -11,7 +11,11 @@ import {
|
|||
SavedObjectsClientContract,
|
||||
} from 'kibana/public';
|
||||
import { i18n } from '@kbn/i18n';
|
||||
import { IndexPatternsContract, IndexPattern } from '../../../../../../../src/plugins/data/public';
|
||||
import {
|
||||
IndexPatternsContract,
|
||||
IndexPattern,
|
||||
TimefilterContract,
|
||||
} from '../../../../../../../src/plugins/data/public';
|
||||
import { ReactExpressionRendererType } from '../../../../../../../src/plugins/expressions/public';
|
||||
import {
|
||||
EmbeddableFactory as AbstractEmbeddableFactory,
|
||||
|
@ -27,6 +31,7 @@ export class EmbeddableFactory extends AbstractEmbeddableFactory {
|
|||
type = DOC_TYPE;
|
||||
|
||||
constructor(
|
||||
private timefilter: TimefilterContract,
|
||||
private coreHttp: HttpSetup,
|
||||
private capabilities: RecursiveReadonly<Capabilities>,
|
||||
private savedObjectsClient: SavedObjectsClientContract,
|
||||
|
@ -85,6 +90,7 @@ export class EmbeddableFactory extends AbstractEmbeddableFactory {
|
|||
);
|
||||
|
||||
return new Embeddable(
|
||||
this.timefilter,
|
||||
this.expressionRenderer,
|
||||
{
|
||||
savedVis,
|
||||
|
|
|
@ -14,6 +14,7 @@ import { embeddablePluginMock } from '../../../../../../src/plugins/embeddable/p
|
|||
import { expressionsPluginMock } from '../../../../../../src/plugins/expressions/public/mocks';
|
||||
import { DatasourcePublicAPI, FramePublicAPI, Datasource, Visualization } from '../types';
|
||||
import { EditorFrameSetupPlugins, EditorFrameStartPlugins } from './service';
|
||||
import { dataPluginMock } from '../../../../../../src/plugins/data/public/mocks';
|
||||
|
||||
export function createMockVisualization(): jest.Mocked<Visualization> {
|
||||
return {
|
||||
|
@ -103,7 +104,7 @@ export function createExpressionRendererMock(): jest.Mock<
|
|||
|
||||
export function createMockSetupDependencies() {
|
||||
return ({
|
||||
data: {},
|
||||
data: dataPluginMock.createSetupContract(),
|
||||
embeddable: embeddablePluginMock.createSetupContract(),
|
||||
expressions: expressionsPluginMock.createSetupContract(),
|
||||
} as unknown) as MockedSetupDependencies;
|
||||
|
@ -111,11 +112,7 @@ export function createMockSetupDependencies() {
|
|||
|
||||
export function createMockStartDependencies() {
|
||||
return ({
|
||||
data: {
|
||||
indexPatterns: {
|
||||
indexPatterns: {},
|
||||
},
|
||||
},
|
||||
data: dataPluginMock.createSetupContract(),
|
||||
embeddable: embeddablePluginMock.createStartContract(),
|
||||
expressions: expressionsPluginMock.createStartContract(),
|
||||
} as unknown) as MockedStartDependencies;
|
||||
|
|
|
@ -79,6 +79,7 @@ export class EditorFrameService {
|
|||
plugins.embeddable.registerEmbeddableFactory(
|
||||
'lens',
|
||||
new EmbeddableFactory(
|
||||
plugins.data.query.timefilter.timefilter,
|
||||
core.http,
|
||||
core.application.capabilities,
|
||||
core.savedObjects.client,
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue