Skip to content

Commit

Permalink
Merge remote-tracking branch 'origin/master' into lens/fix-switching-…
Browse files Browse the repository at this point in the history
…with-layers
  • Loading branch information
wylieconlon committed Jul 15, 2020
2 parents 9819acb + 978c261 commit a32f4c1
Show file tree
Hide file tree
Showing 62 changed files with 1,564 additions and 630 deletions.
42 changes: 22 additions & 20 deletions .github/CODEOWNERS
Validating CODEOWNERS rules …
Original file line number Diff line number Diff line change
Expand Up @@ -24,29 +24,20 @@
/src/plugins/vis_type_xy/ @elastic/kibana-app
/src/plugins/visualize/ @elastic/kibana-app

# Core UI
# Exclude tutorials folder for now because they are not owned by Kibana app and most will move out soon
/src/plugins/home/public @elastic/kibana-core-ui
/src/plugins/home/server/*.ts @elastic/kibana-core-ui
/src/plugins/home/server/services/ @elastic/kibana-core-ui
# Exclude tutorial resources folder for now because they are not owned by Kibana app and most will move out soon
/src/legacy/core_plugins/kibana/public/home/*.ts @elastic/kibana-core-ui
/src/legacy/core_plugins/kibana/public/home/*.scss @elastic/kibana-core-ui
/src/legacy/core_plugins/kibana/public/home/np_ready/ @elastic/kibana-core-ui

# App Architecture
/examples/bfetch_explorer/ @elastic/kibana-app-arch
/examples/dashboard_embeddable_examples/ @elastic/kibana-app-arch
/examples/demo_search/ @elastic/kibana-app-arch
/examples/developer_examples/ @elastic/kibana-app-arch
/examples/embeddable_examples/ @elastic/kibana-app-arch
/examples/embeddable_explorer/ @elastic/kibana-app-arch
/examples/state_container_examples/ @elastic/kibana-app-arch
/examples/ui_actions_examples/ @elastic/kibana-app-arch
/examples/ui_actions_explorer/ @elastic/kibana-app-arch
/examples/url_generators_examples/ @elastic/kibana-app-arch
/examples/url_generators_explorer/ @elastic/kibana-app-arch
/packages/kbn-interpreter/ @elastic/kibana-app-arch
/packages/elastic-datemath/ @elastic/kibana-app-arch
/src/legacy/core_plugins/embeddable_api/ @elastic/kibana-app-arch
/src/legacy/core_plugins/interpreter/ @elastic/kibana-app-arch
/src/legacy/core_plugins/kibana_react/ @elastic/kibana-app-arch
/src/legacy/core_plugins/kibana/public/management/ @elastic/kibana-app-arch
/src/legacy/core_plugins/kibana/server/routes/api/management/ @elastic/kibana-app-arch
/src/legacy/core_plugins/visualizations/ @elastic/kibana-app-arch
/src/legacy/server/index_patterns/ @elastic/kibana-app-arch
/packages/kbn-interpreter/ @elastic/kibana-app-arch
/src/plugins/advanced_settings/ @elastic/kibana-app-arch
/src/plugins/bfetch/ @elastic/kibana-app-arch
/src/plugins/data/ @elastic/kibana-app-arch
Expand All @@ -61,9 +52,10 @@
/src/plugins/share/ @elastic/kibana-app-arch
/src/plugins/ui_actions/ @elastic/kibana-app-arch
/src/plugins/visualizations/ @elastic/kibana-app-arch
/x-pack/plugins/advanced_ui_actions/ @elastic/kibana-app-arch
/x-pack/examples/ui_actions_enhanced_examples/ @elastic/kibana-app-arch
/x-pack/plugins/data_enhanced/ @elastic/kibana-app-arch
/x-pack/plugins/drilldowns/ @elastic/kibana-app-arch
/x-pack/plugins/embeddable_enhanced/ @elastic/kibana-app-arch
/x-pack/plugins/ui_actions_enhanced/ @elastic/kibana-app-arch

# APM
/x-pack/plugins/apm/ @elastic/apm-ui
Expand All @@ -79,6 +71,16 @@
/x-pack/plugins/canvas/ @elastic/kibana-canvas
/x-pack/test/functional/apps/canvas/ @elastic/kibana-canvas

# Core UI
# Exclude tutorials folder for now because they are not owned by Kibana app and most will move out soon
/src/plugins/home/public @elastic/kibana-core-ui
/src/plugins/home/server/*.ts @elastic/kibana-core-ui
/src/plugins/home/server/services/ @elastic/kibana-core-ui
# Exclude tutorial resources folder for now because they are not owned by Kibana app and most will move out soon
/src/legacy/core_plugins/kibana/public/home/*.ts @elastic/kibana-core-ui
/src/legacy/core_plugins/kibana/public/home/*.scss @elastic/kibana-core-ui
/src/legacy/core_plugins/kibana/public/home/np_ready/ @elastic/kibana-core-ui

# Observability UIs
/x-pack/legacy/plugins/infra/ @elastic/logs-metrics-ui
/x-pack/plugins/infra/ @elastic/logs-metrics-ui
Expand Down
21 changes: 16 additions & 5 deletions packages/kbn-optimizer/src/report_optimizer_stats.ts
Original file line number Diff line number Diff line change
Expand Up @@ -35,6 +35,8 @@ interface Entry {
stats: Fs.Stats;
}

const IGNORED_EXTNAME = ['.map', '.br', '.gz'];

const getFiles = (dir: string, parent?: string) =>
flatten(
Fs.readdirSync(dir).map((name): Entry | Entry[] => {
Expand All @@ -51,7 +53,19 @@ const getFiles = (dir: string, parent?: string) =>
stats,
};
})
);
).filter((file) => {
const filename = Path.basename(file.relPath);
if (filename.startsWith('.')) {
return false;
}

const ext = Path.extname(filename);
if (IGNORED_EXTNAME.includes(ext)) {
return false;
}

return true;
});

export function reportOptimizerStats(reporter: CiStatsReporter, config: OptimizerConfig) {
return pipeClosure((update$: OptimizerUpdate$) => {
Expand All @@ -70,10 +84,7 @@ export function reportOptimizerStats(reporter: CiStatsReporter, config: Optimize
// make the cache read from the cache file since it was likely updated by the worker
bundle.cache.refresh();

const outputFiles = getFiles(bundle.outputDir).filter(
(file) => !(file.relPath.startsWith('.') || file.relPath.endsWith('.map'))
);

const outputFiles = getFiles(bundle.outputDir);
const entryName = `${bundle.id}.${bundle.type}.js`;
const entry = outputFiles.find((f) => f.relPath === entryName);
if (!entry) {
Expand Down
6 changes: 3 additions & 3 deletions src/plugins/data/common/field_formats/converters/url.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -167,8 +167,8 @@ describe('UrlFormat', () => {
});
});

describe('whitelist', () => {
test('should assume a relative url if the value is not in the whitelist without a base path', () => {
describe('allow-list', () => {
test('should assume a relative url if the value is not in the allow-list without a base path', () => {
const parsedUrl = {
origin: 'http://kibana',
basePath: '',
Expand All @@ -193,7 +193,7 @@ describe('UrlFormat', () => {
);
});

test('should assume a relative url if the value is not in the whitelist with a basepath', () => {
test('should assume a relative url if the value is not in the allow-list with a basepath', () => {
const parsedUrl = {
origin: 'http://kibana',
basePath: '/xyz',
Expand Down
6 changes: 3 additions & 3 deletions src/plugins/data/common/field_formats/converters/url.ts
Original file line number Diff line number Diff line change
Expand Up @@ -161,8 +161,8 @@ export class UrlFormat extends FieldFormat {

return this.generateImgHtml(url, imageLabel);
default:
const inWhitelist = allowedUrlSchemes.some((scheme) => url.indexOf(scheme) === 0);
if (!inWhitelist && !parsedUrl) {
const allowed = allowedUrlSchemes.some((scheme) => url.indexOf(scheme) === 0);
if (!allowed && !parsedUrl) {
return url;
}

Expand All @@ -178,7 +178,7 @@ export class UrlFormat extends FieldFormat {
* UNSUPPORTED
* - app/kibana
*/
if (!inWhitelist) {
if (!allowed) {
// Handles urls like: `#/discover`
if (url[0] === '#') {
prefix = `${origin}${pathname}`;
Expand Down
2 changes: 1 addition & 1 deletion src/plugins/dev_tools/public/plugin.ts
Original file line number Diff line number Diff line change
Expand Up @@ -61,7 +61,7 @@ export class DevToolsPlugin implements Plugin<DevToolsSetup, void> {
}),
updater$: this.appStateUpdater,
euiIconType: 'devToolsApp',
order: 9001,
order: 9010,
category: DEFAULT_APP_CATEGORIES.management,
mount: async (params: AppMountParameters) => {
const { element, history } = params;
Expand Down
2 changes: 1 addition & 1 deletion src/plugins/management/public/plugin.ts
Original file line number Diff line number Diff line change
Expand Up @@ -65,7 +65,7 @@ export class ManagementPlugin implements Plugin<ManagementSetup, ManagementStart
title: i18n.translate('management.stackManagement.title', {
defaultMessage: 'Stack Management',
}),
order: 9003,
order: 9040,
euiIconType: 'managementApp',
category: DEFAULT_APP_CATEGORIES.management,
async mount(params: AppMountParameters) {
Expand Down
1 change: 1 addition & 0 deletions x-pack/plugins/ingest_manager/public/plugin.ts
Original file line number Diff line number Diff line change
Expand Up @@ -72,6 +72,7 @@ export class IngestManagerPlugin
id: PLUGIN_ID,
category: DEFAULT_APP_CATEGORIES.management,
title: i18n.translate('xpack.ingestManager.appTitle', { defaultMessage: 'Ingest Manager' }),
order: 9020,
euiIconType: 'savedObjectsApp',
async mount(params: AppMountParameters) {
const [coreStart, startDeps] = (await core.getStartServices()) as [
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@
* you may not use this file except in compliance with the Elastic License.
*/

import { EuiButtonEmpty } from '@elastic/eui';
import { EuiButtonEmpty, EuiToolTip } from '@elastic/eui';
import React, { FC } from 'react';
import { isEqual, cloneDeep } from 'lodash';
import { i18n } from '@kbn/i18n';
Expand All @@ -20,7 +20,6 @@ import {
} from '../../hooks/use_create_analytics_form';
import { State } from '../../hooks/use_create_analytics_form/state';
import { DataFrameAnalyticsListRow } from '../analytics_list/common';
import { checkPermission } from '../../../../../capabilities/check_capabilities';
import { extractErrorMessage } from '../../../../../../../common/util/errors';

interface PropDefinition {
Expand Down Expand Up @@ -328,11 +327,11 @@ export function extractCloningConfig({
}) as unknown) as CloneDataFrameAnalyticsConfig;
}

export function getCloneAction(createAnalyticsForm: CreateAnalyticsFormProps) {
const buttonText = i18n.translate('xpack.ml.dataframe.analyticsList.cloneJobButtonLabel', {
defaultMessage: 'Clone job',
});
const buttonText = i18n.translate('xpack.ml.dataframe.analyticsList.cloneJobButtonLabel', {
defaultMessage: 'Clone job',
});

export function getCloneAction(createAnalyticsForm: CreateAnalyticsFormProps) {
const { actions } = createAnalyticsForm;

const onClick = async (item: DeepReadonly<DataFrameAnalyticsListRow>) => {
Expand All @@ -348,23 +347,7 @@ export function getCloneAction(createAnalyticsForm: CreateAnalyticsFormProps) {
};
}

interface CloneButtonProps {
item: DataFrameAnalyticsListRow;
createAnalyticsForm: CreateAnalyticsFormProps;
}

/**
* Temp component to have Clone job button with the same look as the other actions.
* Replace with {@link getCloneAction} as soon as all the actions are refactored
* to support EuiContext with a valid DOM structure without nested buttons.
*/
export const CloneButton: FC<CloneButtonProps> = ({ createAnalyticsForm, item }) => {
const canCreateDataFrameAnalytics: boolean = checkPermission('canCreateDataFrameAnalytics');

const buttonText = i18n.translate('xpack.ml.dataframe.analyticsList.cloneJobButtonLabel', {
defaultMessage: 'Clone job',
});

export const useNavigateToWizardWithClonedJob = () => {
const {
services: {
application: { navigateToUrl },
Expand All @@ -375,7 +358,7 @@ export const CloneButton: FC<CloneButtonProps> = ({ createAnalyticsForm, item })

const savedObjectsClient = savedObjects.client;

const onClick = async () => {
return async (item: DataFrameAnalyticsListRow) => {
const sourceIndex = Array.isArray(item.config.source.index)
? item.config.source.index[0]
: item.config.source.index;
Expand Down Expand Up @@ -419,18 +402,46 @@ export const CloneButton: FC<CloneButtonProps> = ({ createAnalyticsForm, item })
);
}
};
};

return (
interface CloneButtonProps {
isDisabled: boolean;
onClick: () => void;
}

/**
* Temp component to have Clone job button with the same look as the other actions.
* Replace with {@link getCloneAction} as soon as all the actions are refactored
* to support EuiContext with a valid DOM structure without nested buttons.
*/
export const CloneButton: FC<CloneButtonProps> = ({ isDisabled, onClick }) => {
const button = (
<EuiButtonEmpty
data-test-subj="mlAnalyticsJobCloneButton"
size="xs"
aria-label={buttonText}
color="text"
data-test-subj="mlAnalyticsJobCloneButton"
flush="left"
iconType="copy"
isDisabled={isDisabled}
onClick={onClick}
aria-label={buttonText}
disabled={canCreateDataFrameAnalytics === false}
size="s"
>
{buttonText}
</EuiButtonEmpty>
);

if (isDisabled) {
return (
<EuiToolTip
position="top"
content={i18n.translate('xpack.ml.dataframe.analyticsList.cloneActionPermissionTooltip', {
defaultMessage: 'You do not have permission to clone analytics jobs.',
})}
>
{button}
</EuiToolTip>
);
}

return button;
};
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@
export {
extractCloningConfig,
isAdvancedConfig,
useNavigateToWizardWithClonedJob,
CloneButton,
CloneDataFrameAnalyticsConfig,
} from './clone_button';
Original file line number Diff line number Diff line change
Expand Up @@ -49,37 +49,20 @@ describe('DeleteAction', () => {
jest.clearAllMocks();
});

test('When canDeleteDataFrameAnalytics permission is false, button should be disabled.', () => {
test('When isDisabled prop is true, inner button should be disabled.', () => {
const { getByTestId } = render(
<DeleteButton item={mockAnalyticsListItem} onClick={() => {}} />
<DeleteButton isDisabled={true} item={mockAnalyticsListItem} onClick={() => {}} />
);

expect(getByTestId('mlAnalyticsJobDeleteButton')).toHaveAttribute('disabled');
});

test('When canDeleteDataFrameAnalytics permission is true, button should not be disabled.', () => {
const mock = jest.spyOn(CheckPrivilige, 'checkPermission');
mock.mockImplementation((p) => p === 'canDeleteDataFrameAnalytics');
test('When isDisabled prop is true, inner button should not be disabled.', () => {
const { getByTestId } = render(
<DeleteButton item={mockAnalyticsListItem} onClick={() => {}} />
<DeleteButton isDisabled={false} item={mockAnalyticsListItem} onClick={() => {}} />
);

expect(getByTestId('mlAnalyticsJobDeleteButton')).not.toHaveAttribute('disabled');

mock.mockRestore();
});

test('When job is running, delete button should be disabled.', () => {
const { getByTestId } = render(
<DeleteButton
item={{
...mockAnalyticsListItem,
stats: { state: 'started' },
}}
onClick={() => {}}
/>
);

expect(getByTestId('mlAnalyticsJobDeleteButton')).toHaveAttribute('disabled');
});

describe('When delete model is open', () => {
Expand All @@ -93,7 +76,11 @@ describe('DeleteAction', () => {
return (
<>
{deleteAction.isModalVisible && <DeleteButtonModal {...deleteAction} />}
<DeleteButton item={mockAnalyticsListItem} onClick={deleteAction.openModal} />
<DeleteButton
isDisabled={false}
item={mockAnalyticsListItem}
onClick={() => deleteAction.openModal(mockAnalyticsListItem)}
/>
</>
);
};
Expand Down
Loading

0 comments on commit a32f4c1

Please sign in to comment.