move react/jsx-a11y rules into shared react preset (#49244)

* move react/jsx-a11y rules into shared react preset

* autofix react/jsx-closing-tag-location

* autofix react/no-unknown-property

* manually fix react/no-unescaped-entities

* maually fix react/jsx-pascal-case

* manually fix react/prefer-stateless-function

* disable known violations in specific plugins/areas

* remove code override
This commit is contained in:
Spencer 2019-10-29 06:15:33 -07:00 committed by GitHub
parent 75384e1bcd
commit 19ea92abb7
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
62 changed files with 632 additions and 504 deletions

View file

@ -55,6 +55,207 @@ module.exports = {
extends: ['@elastic/eslint-config-kibana', 'plugin:@elastic/eui/recommended'],
overrides: [
/**
* Temporarily disable some react rules for specific plugins, remove in separate PRs
*/
{
files: ['packages/kbn-ui-framework/**/*.{js,ts,tsx}'],
rules: {
'jsx-a11y/no-onchange': 'off',
},
},
{
files: ['src/core/public/application/**/*.{js,ts,tsx}'],
rules: {
'react/no-danger': 'off',
},
},
{
files: ['src/legacy/core_plugins/console/**/*.{js,ts,tsx}'],
rules: {
'react-hooks/exhaustive-deps': 'off',
},
},
{
files: ['src/legacy/core_plugins/data/**/*.{js,ts,tsx}'],
rules: {
'react-hooks/exhaustive-deps': 'off',
},
},
{
files: ['src/legacy/core_plugins/expressions/**/*.{js,ts,tsx}'],
rules: {
'react-hooks/exhaustive-deps': 'off',
},
},
{
files: ['src/legacy/core_plugins/kbn_vislib_vis_types/**/*.{js,ts,tsx}'],
rules: {
'react-hooks/exhaustive-deps': 'off',
},
},
{
files: ['src/legacy/core_plugins/kibana/**/*.{js,ts,tsx}'],
rules: {
'react-hooks/rules-of-hooks': 'off',
'react-hooks/exhaustive-deps': 'off',
},
},
{
files: ['src/legacy/core_plugins/tile_map/**/*.{js,ts,tsx}'],
rules: {
'react-hooks/exhaustive-deps': 'off',
},
},
{
files: ['src/legacy/core_plugins/vis_type_markdown/**/*.{js,ts,tsx}'],
rules: {
'react-hooks/exhaustive-deps': 'off',
},
},
{
files: ['src/legacy/core_plugins/vis_type_metric/**/*.{js,ts,tsx}'],
rules: {
'jsx-a11y/click-events-have-key-events': 'off',
},
},
{
files: ['src/legacy/core_plugins/vis_type_table/**/*.{js,ts,tsx}'],
rules: {
'react-hooks/exhaustive-deps': 'off',
},
},
{
files: ['src/legacy/core_plugins/vis_type_vega/**/*.{js,ts,tsx}'],
rules: {
'react-hooks/exhaustive-deps': 'off',
},
},
{
files: ['src/legacy/ui/public/vis/**/*.{js,ts,tsx}'],
rules: {
'react-hooks/exhaustive-deps': 'off',
},
},
{
files: ['src/plugins/es_ui_shared/**/*.{js,ts,tsx}'],
rules: {
'react-hooks/exhaustive-deps': 'off',
},
},
{
files: ['src/plugins/eui_utils/**/*.{js,ts,tsx}'],
rules: {
'react-hooks/exhaustive-deps': 'off',
},
},
{
files: ['src/plugins/kibana_react/**/*.{js,ts,tsx}'],
rules: {
'react-hooks/rules-of-hooks': 'off',
'react-hooks/exhaustive-deps': 'off',
},
},
{
files: ['src/plugins/kibana_utils/**/*.{js,ts,tsx}'],
rules: {
'react-hooks/exhaustive-deps': 'off',
},
},
{
files: ['x-pack/legacy/plugins/canvas/**/*.{js,ts,tsx}'],
rules: {
'react-hooks/exhaustive-deps': 'off',
'jsx-a11y/click-events-have-key-events': 'off',
},
},
{
files: ['x-pack/legacy/plugins/cross_cluster_replication/**/*.{js,ts,tsx}'],
rules: {
'jsx-a11y/click-events-have-key-events': 'off',
},
},
{
files: ['x-pack/legacy/plugins/graph/**/*.{js,ts,tsx}'],
rules: {
'react-hooks/exhaustive-deps': 'off',
},
},
{
files: ['x-pack/legacy/plugins/index_management/**/*.{js,ts,tsx}'],
rules: {
'react-hooks/exhaustive-deps': 'off',
'react-hooks/rules-of-hooks': 'off',
},
},
{
files: ['x-pack/legacy/plugins/infra/**/*.{js,ts,tsx}'],
rules: {
'react-hooks/exhaustive-deps': 'off',
'react-hooks/rules-of-hooks': 'off',
},
},
{
files: ['x-pack/legacy/plugins/lens/**/*.{js,ts,tsx}'],
rules: {
'react-hooks/exhaustive-deps': 'off',
'react-hooks/rules-of-hooks': 'off',
},
},
{
files: ['x-pack/legacy/plugins/ml/**/*.{js,ts,tsx}'],
rules: {
'react-hooks/exhaustive-deps': 'off',
'react-hooks/rules-of-hooks': 'off',
'jsx-a11y/click-events-have-key-events': 'off',
},
},
{
files: ['x-pack/legacy/plugins/monitoring/**/*.{js,ts,tsx}'],
rules: {
'jsx-a11y/click-events-have-key-events': 'off',
},
},
{
files: ['x-pack/legacy/plugins/siem/**/*.{js,ts,tsx}'],
rules: {
'react-hooks/exhaustive-deps': 'off',
'react-hooks/rules-of-hooks': 'off',
},
},
{
files: ['x-pack/legacy/plugins/snapshot_restore/**/*.{js,ts,tsx}'],
rules: {
'react-hooks/exhaustive-deps': 'off',
},
},
{
files: ['x-pack/legacy/plugins/spaces/**/*.{js,ts,tsx}'],
rules: {
'react-hooks/exhaustive-deps': 'off',
},
},
{
files: ['x-pack/legacy/plugins/transform/**/*.{js,ts,tsx}'],
rules: {
'react-hooks/exhaustive-deps': 'off',
},
},
{
files: ['x-pack/legacy/plugins/uptime/**/*.{js,ts,tsx}'],
rules: {
'react-hooks/exhaustive-deps': 'off',
'react-hooks/rules-of-hooks': 'off',
},
},
{
files: ['x-pack/legacy/plugins/watcher/**/*.{js,ts,tsx}'],
rules: {
'react-hooks/rules-of-hooks': 'off',
'react-hooks/exhaustive-deps': 'off',
},
},
/**
* Prettier
*/

View file

@ -3,6 +3,7 @@ module.exports = {
'./javascript.js',
'./typescript.js',
'./jest.js',
'./react.js',
],
plugins: ['@kbn/eslint-plugin-eslint'],

View file

@ -1,6 +1,3 @@
const semver = require('semver');
const { readdirSync } = require('fs');
const PKG = require('../../package.json');
const RESTRICTED_GLOBALS = require('./restricted_globals');
const RESTRICTED_MODULES = { paths: ['gulp-util'] };
@ -16,18 +13,12 @@ module.exports = {
plugins: [
'mocha',
'babel',
'react',
'react-hooks',
'import',
'no-unsanitized',
'prefer-object-spread',
'jsx-a11y',
],
settings: {
react: {
version: semver.valid(semver.coerce(PKG.dependencies.react)),
},
'import/resolver': {
'@kbn/eslint-import-resolver-kibana': {
forceNode: true,
@ -120,64 +111,6 @@ module.exports = {
'object-curly-spacing': 'off', // overridden with babel/object-curly-spacing
'babel/object-curly-spacing': [ 'error', 'always' ],
'jsx-quotes': ['error', 'prefer-double'],
'react/jsx-uses-react': 'error',
'react/react-in-jsx-scope': 'error',
'react/jsx-uses-vars': 'error',
'react/jsx-no-undef': 'error',
'react/jsx-pascal-case': 'error',
'react/jsx-closing-bracket-location': ['error', 'line-aligned'],
'react/jsx-closing-tag-location': 'error',
'react/jsx-curly-spacing': ['error', 'never', { allowMultiline: true }],
'react/jsx-indent-props': ['error', 2],
'react/jsx-max-props-per-line': ['error', { maximum: 1, when: 'multiline' }],
'react/jsx-no-duplicate-props': ['error', { ignoreCase: true }],
'react/no-danger': 'error',
'react/self-closing-comp': 'error',
'react/jsx-wrap-multilines': ['error', {
declaration: true,
assignment: true,
return: true,
arrow: true,
}],
'react/jsx-first-prop-new-line': ['error', 'multiline-multiprop'],
'react-hooks/rules-of-hooks': 'error', // Checks rules of Hooks
'react-hooks/exhaustive-deps': 'warn', // Checks effect dependencies
'jsx-a11y/accessible-emoji': 'error',
'jsx-a11y/alt-text': 'error',
'jsx-a11y/anchor-has-content': 'error',
'jsx-a11y/aria-activedescendant-has-tabindex': 'error',
'jsx-a11y/aria-props': 'error',
'jsx-a11y/aria-proptypes': 'error',
'jsx-a11y/aria-role': 'error',
'jsx-a11y/aria-unsupported-elements': 'error',
'jsx-a11y/heading-has-content': 'error',
'jsx-a11y/html-has-lang': 'error',
'jsx-a11y/iframe-has-title': 'error',
'jsx-a11y/interactive-supports-focus': 'error',
'jsx-a11y/media-has-caption': 'error',
'jsx-a11y/mouse-events-have-key-events': 'error',
'jsx-a11y/no-access-key': 'error',
'jsx-a11y/no-distracting-elements': 'error',
'jsx-a11y/no-interactive-element-to-noninteractive-role': 'error',
'jsx-a11y/no-noninteractive-element-interactions': 'error',
'jsx-a11y/no-noninteractive-element-to-interactive-role': 'error',
'jsx-a11y/no-redundant-roles': 'error',
'jsx-a11y/role-has-required-aria-props': 'error',
'jsx-a11y/role-supports-aria-props': 'error',
'jsx-a11y/scope': 'error',
'jsx-a11y/tabindex-no-positive': 'error',
'jsx-a11y/label-has-associated-control': 'error',
'react/jsx-equals-spacing': ['error', 'never'],
'react/jsx-indent': ['error', 2],
'react/no-will-update-set-state': 'error',
'react/no-is-mounted': 'error',
'react/no-multi-comp': ['error', { ignoreStateless: true }],
'react/no-unknown-property': 'error',
'react/prefer-es6-class': ['error', 'always'],
'react/prefer-stateless-function': ['error', { ignorePureComponents: true }],
'react/no-unescaped-entities': 'error',
'mocha/handle-done-callback': 'error',
'mocha/no-exclusive-tests': 'error',

84
packages/eslint-config-kibana/react.js vendored Normal file
View file

@ -0,0 +1,84 @@
const semver = require('semver')
const PKG = require('../../package.json')
module.exports = {
plugins: [
'react',
'react-hooks',
'jsx-a11y',
],
parserOptions: {
ecmaFeatures: {
jsx: true
}
},
settings: {
react: {
version: semver.valid(semver.coerce(PKG.dependencies.react)),
},
},
rules: {
'jsx-quotes': ['error', 'prefer-double'],
'react/jsx-uses-react': 'error',
'react/react-in-jsx-scope': 'error',
'react/jsx-uses-vars': 'error',
'react/jsx-no-undef': 'error',
'react/jsx-pascal-case': 'error',
'react/jsx-closing-bracket-location': ['error', 'line-aligned'],
'react/jsx-closing-tag-location': 'error',
'react/jsx-curly-spacing': ['error', 'never', { allowMultiline: true }],
'react/jsx-indent-props': ['error', 2],
'react/jsx-max-props-per-line': ['error', { maximum: 1, when: 'multiline' }],
'react/jsx-no-duplicate-props': ['error', { ignoreCase: true }],
'react/no-danger': 'error',
'react/self-closing-comp': 'error',
'react/jsx-wrap-multilines': ['error', {
declaration: true,
assignment: true,
return: true,
arrow: true,
}],
'react/jsx-first-prop-new-line': ['error', 'multiline-multiprop'],
'react-hooks/rules-of-hooks': 'error', // Checks rules of Hooks
'react-hooks/exhaustive-deps': 'error', // Checks effect dependencies
'jsx-a11y/accessible-emoji': 'error',
'jsx-a11y/alt-text': 'error',
'jsx-a11y/anchor-has-content': 'error',
'jsx-a11y/aria-activedescendant-has-tabindex': 'error',
'jsx-a11y/aria-props': 'error',
'jsx-a11y/aria-proptypes': 'error',
'jsx-a11y/aria-role': 'error',
'jsx-a11y/aria-unsupported-elements': 'error',
'jsx-a11y/click-events-have-key-events': 'error',
'jsx-a11y/heading-has-content': 'error',
'jsx-a11y/html-has-lang': 'error',
'jsx-a11y/iframe-has-title': 'error',
'jsx-a11y/interactive-supports-focus': 'error',
'jsx-a11y/label-has-associated-control': 'error',
'jsx-a11y/media-has-caption': 'error',
'jsx-a11y/mouse-events-have-key-events': 'error',
'jsx-a11y/no-access-key': 'error',
'jsx-a11y/no-distracting-elements': 'error',
'jsx-a11y/no-interactive-element-to-noninteractive-role': 'error',
'jsx-a11y/no-noninteractive-element-interactions': 'error',
'jsx-a11y/no-noninteractive-element-to-interactive-role': 'error',
'jsx-a11y/no-onchange': 'error',
'jsx-a11y/no-redundant-roles': 'error',
'jsx-a11y/role-has-required-aria-props': 'error',
'jsx-a11y/role-supports-aria-props': 'error',
'jsx-a11y/scope': 'error',
'jsx-a11y/tabindex-no-positive': 'error',
'react/jsx-equals-spacing': ['error', 'never'],
'react/jsx-indent': ['error', 2],
'react/no-will-update-set-state': 'error',
'react/no-is-mounted': 'error',
'react/no-multi-comp': ['error', { ignoreStateless: true }],
'react/no-unknown-property': 'error',
'react/prefer-es6-class': ['error', 'always'],
'react/prefer-stateless-function': ['error', { ignorePureComponents: true }],
'react/no-unescaped-entities': 'error',
},
}

View file

@ -18,7 +18,6 @@ module.exports = {
'@typescript-eslint',
'ban',
'import',
'jsx-a11y',
'prefer-object-spread',
],
@ -171,33 +170,6 @@ module.exports = {
{'name': ['test', 'only'], 'message': 'No exclusive tests.'},
],
'jsx-a11y/accessible-emoji': 'error',
'jsx-a11y/alt-text': 'error',
'jsx-a11y/anchor-has-content': 'error',
'jsx-a11y/aria-activedescendant-has-tabindex': 'error',
'jsx-a11y/aria-props': 'error',
'jsx-a11y/aria-proptypes': 'error',
'jsx-a11y/aria-role': 'error',
'jsx-a11y/aria-unsupported-elements': 'error',
'jsx-a11y/click-events-have-key-events': 'error',
'jsx-a11y/heading-has-content': 'error',
'jsx-a11y/html-has-lang': 'error',
'jsx-a11y/iframe-has-title': 'error',
'jsx-a11y/interactive-supports-focus': 'error',
'jsx-a11y/media-has-caption': 'error',
'jsx-a11y/mouse-events-have-key-events': 'error',
'jsx-a11y/no-access-key': 'error',
'jsx-a11y/no-distracting-elements': 'error',
'jsx-a11y/no-interactive-element-to-noninteractive-role': 'error',
'jsx-a11y/no-noninteractive-element-interactions': 'error',
'jsx-a11y/no-noninteractive-element-to-interactive-role': 'error',
'jsx-a11y/no-onchange': 'error',
'jsx-a11y/no-redundant-roles': 'error',
'jsx-a11y/role-has-required-aria-props': 'error',
'jsx-a11y/role-supports-aria-props': 'error',
'jsx-a11y/scope': 'error',
'jsx-a11y/tabindex-no-positive': 'error',
'jsx-a11y/label-has-associated-control': 'error',
'import/no-default-export': 'error',
},
eslintConfigPrettierTypescriptEslintRules

View file

@ -34,7 +34,7 @@ describe('RenderingService#start', () => {
const chrome = chromeServiceMock.createStartContract();
chrome.getHeaderComponent.mockReturnValue(<div>Hello chrome!</div>);
const overlays = overlayServiceMock.createStartContract();
overlays.banners.getComponent.mockReturnValue(<div>I'm a banner!</div>);
overlays.banners.getComponent.mockReturnValue(<div>I&apos;m a banner!</div>);
const injectedMetadata = injectedMetadataServiceMock.createStartContract();
injectedMetadata.getLegacyMode.mockReturnValue(legacyMode);

View file

@ -33,14 +33,14 @@ const timefilterSetupMock = timefilterServiceMock.createSetupContract();
jest.mock('../../../../../data/public', () => {
return {
FilterBar: () => <div className="filterBar"></div>,
QueryBarInput: () => <div className="queryBar"></div>,
FilterBar: () => <div className="filterBar" />,
QueryBarInput: () => <div className="queryBar" />,
};
});
jest.mock('../../../query/query_bar', () => {
return {
QueryBarTopRow: () => <div className="queryBar"></div>,
QueryBarTopRow: () => <div className="queryBar" />,
};
});

View file

@ -368,7 +368,7 @@ class SearchBarUI extends Component<SearchBarProps, State> {
onLoad={this.onLoadSavedQuery}
savedQueryService={this.savedQueryService}
onClearSavedQuery={this.props.onClearSavedQuery}
></SavedQueryManagementComponent>
/>
);
let queryBar;

View file

@ -100,6 +100,7 @@ export function DocViewTableRow({
* Justification for dangerouslySetInnerHTML:
* We just use values encoded by our field formatters
*/
// eslint-disable-next-line react/no-danger
dangerouslySetInnerHTML={{ __html: value as string }}
/>
</td>

View file

@ -34,7 +34,7 @@ export function ToolBarPagerButtons(props: Props) {
disabled={!props.hasPreviousPage}
data-test-subj="btnPrevPage"
>
<span className="kuiButton__icon kuiIcon fa-chevron-left"></span>
<span className="kuiButton__icon kuiIcon fa-chevron-left" />
</button>
<button
className="kuiButton kuiButton--basic kuiButton--icon"
@ -42,7 +42,7 @@ export function ToolBarPagerButtons(props: Props) {
disabled={!props.hasNextPage}
data-test-subj="btnNextPage"
>
<span className="kuiButton__icon kuiIcon fa-chevron-right"></span>
<span className="kuiButton__icon kuiIcon fa-chevron-right" />
</button>
</div>
);

View file

@ -29,7 +29,7 @@ jest.mock('ui/new_platform');
const dataShim = {
ui: {
SearchBar: () => <div className="searchBar"></div>,
SearchBar: () => <div className="searchBar" />,
},
};

View file

@ -77,6 +77,7 @@ describe('injectUICapabilities', () => {
uiCapabilities: UICapabilities;
}
// eslint-disable-next-line react/prefer-stateless-function
class MyClassComponent extends React.Component<ClassProps, {}> {
public render() {
return <span>{this.props.uiCapabilities.uiCapability2.nestedProp}</span>;

View file

@ -77,6 +77,7 @@ describe('injectUICapabilities', () => {
uiCapabilities: UICapabilities;
}
// eslint-disable-next-line react/prefer-stateless-function
class MyClassComponent extends React.Component<ClassProps, {}> {
public render() {
return <span>{this.props.uiCapabilities.uiCapability2.nestedProp}</span>;

View file

@ -17,22 +17,14 @@
* under the License.
*/
import React, { ReactNode } from 'react';
import React from 'react';
import { UICapabilitiesContext } from './ui_capabilities_context';
import { capabilities } from '..';
interface Props {
children: ReactNode;
}
export const UICapabilitiesProvider: React.SFC = props => (
<UICapabilitiesContext.Provider value={capabilities.get()}>
{props.children}
</UICapabilitiesContext.Provider>
);
export class UICapabilitiesProvider extends React.Component<Props, {}> {
public static displayName: string = 'UICapabilitiesProvider';
public render() {
return (
<UICapabilitiesContext.Provider value={capabilities.get()}>
{this.props.children}
</UICapabilitiesContext.Provider>
);
}
}
UICapabilitiesProvider.displayName = 'UICapabilitiesProvider';

View file

@ -156,7 +156,7 @@ describe('DefaultEditorAgg component', () => {
it('should add schema component', () => {
defaultProps.agg.schema = {
editorComponent: () => <div className="schemaComponent"></div>,
editorComponent: () => <div className="schemaComponent" />,
} as any;
const comp = mount(<DefaultEditorAgg {...defaultProps} />);

View file

@ -106,7 +106,7 @@ describe('useUiSetting', () => {
});
describe('useUiSetting$', () => {
const TestConsumer$: React.FC<{
const TestConsumer: React.FC<{
setting: string;
newValue?: string;
}> = ({ setting, newValue = '' }) => {
@ -126,7 +126,7 @@ describe('useUiSetting$', () => {
ReactDOM.render(
<Provider>
<TestConsumer$ setting="foo" />
<TestConsumer setting="foo" />
</Provider>,
container
);
@ -143,7 +143,7 @@ describe('useUiSetting$', () => {
ReactDOM.render(
<Provider>
<TestConsumer$ setting="non_existing" />
<TestConsumer setting="non_existing" />
</Provider>,
container
);
@ -159,7 +159,7 @@ describe('useUiSetting$', () => {
ReactDOM.render(
<Provider>
<TestConsumer$ setting="theme:darkMode" />
<TestConsumer setting="theme:darkMode" />
</Provider>,
container
);
@ -174,7 +174,7 @@ describe('useUiSetting$', () => {
ReactDOM.render(
<Provider>
<TestConsumer$ setting="a" newValue="c" />
<TestConsumer setting="a" newValue="c" />
</Provider>,
container
);

View file

@ -76,7 +76,7 @@ const PageA = () => (
</EuiTitle>
</EuiPageContentHeaderSection>
</EuiPageContentHeader>
<EuiPageContentBody>Page A's content goes here</EuiPageContentBody>
<EuiPageContentBody>Page A&apos;s content goes here</EuiPageContentBody>
</EuiPageContent>
</EuiPageBody>
);

View file

@ -17,7 +17,7 @@
* under the License.
*/
import React, { Component } from 'react';
import React from 'react';
import {
setup as navSetup,
start as navStart,
@ -33,22 +33,21 @@ const customExtension = {
navSetup.registerMenuItem(customExtension);
export class AppWithTopNav extends Component {
public render() {
const { TopNavMenu } = navStart.ui;
const config = [
{
id: 'new',
label: 'New Button',
description: 'New Demo',
run() {},
testId: 'demoNewButton',
},
];
return (
<TopNavMenu appName="demo-app" config={config}>
Hey
</TopNavMenu>
);
}
}
export const AppWithTopNav = () => {
const { TopNavMenu } = navStart.ui;
const config = [
{
id: 'new',
label: 'New Button',
description: 'New Demo',
run() {},
testId: 'demoNewButton',
},
];
return (
<TopNavMenu appName="demo-app" config={config}>
Hey
</TopNavMenu>
);
};

View file

@ -127,7 +127,7 @@ export class DemoStrategy extends React.Component<Props, State> {
},
]}
demo={this.renderDemo()}
></GuideSection>
/>
</EuiPageContentBody>
);
}

View file

@ -139,7 +139,7 @@ export class EsSearchTest extends React.Component<Props, State> {
},
]}
demo={this.renderDemo()}
></GuideSection>
/>
</EuiPageContentBody>
);
}

View file

@ -110,7 +110,7 @@ export class GuideSection extends React.Component<Props, State> {
return code.map((codeBlock, i) => (
<React.Fragment key={i}>
<EuiSpacer></EuiSpacer>
<EuiSpacer />
<h3>{codeBlock.description}</h3>
<EuiCodeBlock language="ts">{this.removeLicenseBlock(codeBlock.snippet)}</EuiCodeBlock>
<EuiHorizontalRule />

View file

@ -83,5 +83,5 @@ export const SearchApiPage = () => (
],
},
]}
></GuideSection>
/>
);

View file

@ -113,7 +113,7 @@ export function ServiceNodeMetrics() {
</ElasticDocsLink>
)
}}
></FormattedMessage>
/>
</EuiCallOut>
) : (
<EuiFlexGroup gutterSize="xl">
@ -129,7 +129,7 @@ export function ServiceNodeMetrics() {
<Truncate>{host}</Truncate>
</EuiToolTip>
}
></EuiStat>
/>
</EuiFlexItem>
<EuiFlexItem grow={false}>
<EuiStat
@ -146,7 +146,7 @@ export function ServiceNodeMetrics() {
<Truncate>{containerId}</Truncate>
</EuiToolTip>
}
></EuiStat>
/>
</EuiFlexItem>
</EuiFlexGroup>
)}

View file

@ -49,7 +49,7 @@ export function TraceOverview() {
return (
<EuiFlexGroup>
<EuiFlexItem grow={1}>
<LocalUIFilters {...localUIFiltersConfig}></LocalUIFilters>
<LocalUIFilters {...localUIFiltersConfig} />
</EuiFlexItem>
<EuiFlexItem grow={7}>
<EuiPanel>

View file

@ -32,7 +32,7 @@ const FilterBadgeList = ({ onRemove, value }: Props) => (
>
<EuiBadge color="hollow">
<BadgeText>{val}</BadgeText>
<EuiIcon type="cross"></EuiIcon>
<EuiIcon type="cross" />
</EuiBadge>
</button>
</EuiFlexItem>

View file

@ -168,7 +168,7 @@ const Filter = ({
}}
value={value}
/>
<EuiSpacer size="s"></EuiSpacer>
<EuiSpacer size="s" />
</>
) : null}
</>

View file

@ -24,29 +24,27 @@ interface Props {
vars: IStackframe['vars'];
}
export class Variables extends React.Component<Props> {
public render() {
if (!this.props.vars) {
return null;
}
return (
<React.Fragment>
<VariablesContainer>
<EuiAccordion
id="local-variables"
className="euiAccordion"
buttonContent={i18n.translate(
'xpack.apm.stacktraceTab.localVariablesToogleButtonLabel',
{ defaultMessage: 'Local variables' }
)}
>
<React.Fragment>
<DottedKeyValueTable data={this.props.vars} maxDepth={5} />
</React.Fragment>
</EuiAccordion>
</VariablesContainer>
</React.Fragment>
);
export const Variables: React.SFC<Props> = props => {
if (!props.vars) {
return null;
}
}
return (
<React.Fragment>
<VariablesContainer>
<EuiAccordion
id="local-variables"
className="euiAccordion"
buttonContent={i18n.translate(
'xpack.apm.stacktraceTab.localVariablesToogleButtonLabel',
{ defaultMessage: 'Local variables' }
)}
>
<React.Fragment>
<DottedKeyValueTable data={props.vars} maxDepth={5} />
</React.Fragment>
</EuiAccordion>
</VariablesContainer>
</React.Fragment>
);
};

View file

@ -61,7 +61,7 @@ const TransactionSummary = ({
) : null
];
return <Summary items={items}></Summary>;
return <Summary items={items} />;
};
export { TransactionSummary };

View file

@ -18,29 +18,23 @@ interface SuggestionItemProps {
suggestion: AutocompleteSuggestion;
}
export class SuggestionItem extends React.Component<SuggestionItemProps> {
public static defaultProps: Partial<SuggestionItemProps> = {
isSelected: false,
};
export const SuggestionItem: React.SFC<SuggestionItemProps> = props => {
const { isSelected, onClick, onMouseEnter, suggestion } = props;
public render() {
const { isSelected, onClick, onMouseEnter, suggestion } = this.props;
return (
<SuggestionItemContainer isSelected={isSelected} onClick={onClick} onMouseEnter={onMouseEnter}>
<SuggestionItemIconField suggestionType={suggestion.type}>
<EuiIcon type={getEuiIconType(suggestion.type)} />
</SuggestionItemIconField>
<SuggestionItemTextField>{suggestion.text}</SuggestionItemTextField>
<SuggestionItemDescriptionField>{suggestion.description}</SuggestionItemDescriptionField>
</SuggestionItemContainer>
);
};
return (
<SuggestionItemContainer
isSelected={isSelected}
onClick={onClick}
onMouseEnter={onMouseEnter}
>
<SuggestionItemIconField suggestionType={suggestion.type}>
<EuiIcon type={getEuiIconType(suggestion.type)} />
</SuggestionItemIconField>
<SuggestionItemTextField>{suggestion.text}</SuggestionItemTextField>
<SuggestionItemDescriptionField>{suggestion.description}</SuggestionItemDescriptionField>
</SuggestionItemContainer>
);
}
}
SuggestionItem.defaultProps = {
isSelected: false,
};
const SuggestionItemContainer = styled.div<{
isSelected?: boolean;

View file

@ -6,93 +6,90 @@
import { EuiBetaBadge, EuiButton, EuiFlexGroup, EuiFlexItem } from '@elastic/eui';
import { i18n } from '@kbn/i18n';
import { FormattedMessage, InjectedIntl, injectI18n } from '@kbn/i18n/react';
import React, { Component } from 'react';
import React from 'react';
import { NoDataLayout } from '../../../components/layouts/no_data';
import { WalkthroughLayout } from '../../../components/layouts/walkthrough';
import { ChildRoutes } from '../../../components/navigation/child_routes';
import { ConnectedLink } from '../../../components/navigation/connected_link';
import { AppPageProps } from '../../../frontend_types';
class InitialWalkthroughPageComponent extends Component<
AppPageProps & {
intl: InjectedIntl;
}
> {
public render() {
const { intl } = this.props;
type Props = AppPageProps & {
intl: InjectedIntl;
};
if (this.props.location.pathname === '/walkthrough/initial') {
return (
<NoDataLayout
title={
<EuiFlexGroup alignItems="center" gutterSize="m">
<EuiFlexItem grow={false}>{'Beats central management '}</EuiFlexItem>
<EuiFlexItem grow={false}>
<EuiBetaBadge
label={i18n.translate('xpack.beatsManagement.walkthrough.initial.betaBadgeText', {
defaultMessage: 'Beta',
})}
/>
</EuiFlexItem>
</EuiFlexGroup>
}
actionSection={
<ConnectedLink path="/walkthrough/initial/beat">
<EuiButton color="primary" fill>
<FormattedMessage
id="xpack.beatsManagement.enrollBeat.enrollBeatButtonLabel"
defaultMessage="Enroll Beat"
/>{' '}
</EuiButton>
</ConnectedLink>
}
>
<p>
<FormattedMessage
id="xpack.beatsManagement.enrollBeat.beatsCentralManagementDescription"
defaultMessage="Manage your configurations in a central location."
/>
</p>
</NoDataLayout>
);
}
const InitialWalkthroughPageComponent: React.SFC<Props> = props => {
if (props.location.pathname === '/walkthrough/initial') {
return (
<WalkthroughLayout
title={intl.formatMessage({
id: 'xpack.beatsManagement.enrollBeat.getStartedBeatsCentralManagementTitle',
defaultMessage: 'Get started with Beats central management',
})}
walkthroughSteps={[
{
id: '/walkthrough/initial/beat',
name: intl.formatMessage({
id: 'xpack.beatsManagement.enrollBeat.enrollBeatStepLabel',
defaultMessage: 'Enroll Beat',
}),
},
{
id: '/walkthrough/initial/tag',
name: intl.formatMessage({
id: 'xpack.beatsManagement.enrollBeat.createTagStepLabel',
defaultMessage: 'Create tag',
}),
},
{
id: '/walkthrough/initial/finish',
name: intl.formatMessage({
id: 'xpack.beatsManagement.enrollBeat.finishStepLabel',
defaultMessage: 'Finish',
}),
},
]}
goTo={() => {
// FIXME implament goto
}}
activePath={this.props.location.pathname}
<NoDataLayout
title={
<EuiFlexGroup alignItems="center" gutterSize="m">
<EuiFlexItem grow={false}>{'Beats central management '}</EuiFlexItem>
<EuiFlexItem grow={false}>
<EuiBetaBadge
label={i18n.translate('xpack.beatsManagement.walkthrough.initial.betaBadgeText', {
defaultMessage: 'Beta',
})}
/>
</EuiFlexItem>
</EuiFlexGroup>
}
actionSection={
<ConnectedLink path="/walkthrough/initial/beat">
<EuiButton color="primary" fill>
<FormattedMessage
id="xpack.beatsManagement.enrollBeat.enrollBeatButtonLabel"
defaultMessage="Enroll Beat"
/>{' '}
</EuiButton>
</ConnectedLink>
}
>
<ChildRoutes routes={this.props.routes} {...this.props} />
</WalkthroughLayout>
<p>
<FormattedMessage
id="xpack.beatsManagement.enrollBeat.beatsCentralManagementDescription"
defaultMessage="Manage your configurations in a central location."
/>
</p>
</NoDataLayout>
);
}
}
return (
<WalkthroughLayout
title={props.intl.formatMessage({
id: 'xpack.beatsManagement.enrollBeat.getStartedBeatsCentralManagementTitle',
defaultMessage: 'Get started with Beats central management',
})}
walkthroughSteps={[
{
id: '/walkthrough/initial/beat',
name: props.intl.formatMessage({
id: 'xpack.beatsManagement.enrollBeat.enrollBeatStepLabel',
defaultMessage: 'Enroll Beat',
}),
},
{
id: '/walkthrough/initial/tag',
name: props.intl.formatMessage({
id: 'xpack.beatsManagement.enrollBeat.createTagStepLabel',
defaultMessage: 'Create tag',
}),
},
{
id: '/walkthrough/initial/finish',
name: props.intl.formatMessage({
id: 'xpack.beatsManagement.enrollBeat.finishStepLabel',
defaultMessage: 'Finish',
}),
},
]}
goTo={() => {
// FIXME implament goto
}}
activePath={props.location.pathname}
>
<ChildRoutes routes={props.routes} {...props} />
</WalkthroughLayout>
);
};
export const InitialWalkthroughPage = injectI18n(InitialWalkthroughPageComponent);

View file

@ -58,7 +58,7 @@ export const SnippetsStep: FC<{ onCopy: OnCopyFn }> = ({ onCopy }) => (
<EuiHorizontalRule />
<EuiDescriptionList>
<EuiDescriptionListTitle>
<EuiCode>kbn-canvas-shareable="canvas"</EuiCode> ({strings.getRequiredLabel()})
<EuiCode>kbn-canvas-shareable=&quot;canvas&quot;</EuiCode> ({strings.getRequiredLabel()})
</EuiDescriptionListTitle>
<EuiDescriptionListDescription>
{strings.getShareableParameterDescription()}

View file

@ -32,7 +32,7 @@ describe('Canvas Shareable Workpad API', () => {
test('Placed successfully with default properties', async () => {
const container = document.createElement('div');
document.body.appendChild(container);
const wrapper = mount(<div kbn-canvas-shareable="canvas" kbn-canvas-url="workpad.json"></div>, {
const wrapper = mount(<div kbn-canvas-shareable="canvas" kbn-canvas-url="workpad.json" />, {
attachTo: container,
});
@ -46,11 +46,7 @@ describe('Canvas Shareable Workpad API', () => {
const container = document.createElement('div');
document.body.appendChild(container);
const wrapper = mount(
<div
kbn-canvas-shareable="canvas"
kbn-canvas-height="350"
kbn-canvas-url="workpad.json"
></div>,
<div kbn-canvas-shareable="canvas" kbn-canvas-height="350" kbn-canvas-url="workpad.json" />,
{
attachTo: container,
}
@ -69,11 +65,7 @@ describe('Canvas Shareable Workpad API', () => {
const container = document.createElement('div');
document.body.appendChild(container);
const wrapper = mount(
<div
kbn-canvas-shareable="canvas"
kbn-canvas-width="400"
kbn-canvas-url="workpad.json"
></div>,
<div kbn-canvas-shareable="canvas" kbn-canvas-width="400" kbn-canvas-url="workpad.json" />,
{
attachTo: container,
}
@ -97,7 +89,7 @@ describe('Canvas Shareable Workpad API', () => {
kbn-canvas-width="350"
kbn-canvas-height="350"
kbn-canvas-url="workpad.json"
></div>,
/>,
{
attachTo: container,
}
@ -116,7 +108,7 @@ describe('Canvas Shareable Workpad API', () => {
const container = document.createElement('div');
document.body.appendChild(container);
const wrapper = mount(
<div kbn-canvas-shareable="canvas" kbn-canvas-page="0" kbn-canvas-url="workpad.json"></div>,
<div kbn-canvas-shareable="canvas" kbn-canvas-page="0" kbn-canvas-url="workpad.json" />,
{
attachTo: container,
}

View file

@ -39,7 +39,7 @@ export function BlacklistForm({
<FormattedMessage
id="xpack.graph.blacklist.noEntriesDescription"
defaultMessage="You don't have any blocked terms. Select vertices and click {stopSign} in the control panel on the right to block them. Documents that match blocked terms are no longer explored and relationships to them are hidden."
values={{ stopSign: <span className="kuiIcon fa-ban"></span> }}
values={{ stopSign: <span className="kuiIcon fa-ban" /> }}
/>
}
/>

View file

@ -34,6 +34,6 @@ export const TabAliases: React.FunctionComponent<Props> = ({ templateDetails })
}
iconType="pin"
data-test-subj="noAliasesCallout"
></EuiCallOut>
/>
);
};

View file

@ -34,6 +34,6 @@ export const TabMappings: React.FunctionComponent<Props> = ({ templateDetails })
}
iconType="pin"
data-test-subj="noMappingsCallout"
></EuiCallOut>
/>
);
};

View file

@ -34,6 +34,6 @@ export const TabSettings: React.FunctionComponent<Props> = ({ templateDetails })
}
iconType="pin"
data-test-subj="noSettingsCallout"
></EuiCallOut>
/>
);
};

View file

@ -11,36 +11,30 @@ import React from 'react';
import { AutocompleteSuggestion } from '../../../../../../../src/plugins/data/public';
import euiStyled from '../../../../../common/eui_styled_components';
interface SuggestionItemProps {
interface Props {
isSelected?: boolean;
onClick?: React.MouseEventHandler<HTMLDivElement>;
onMouseEnter?: React.MouseEventHandler<HTMLDivElement>;
suggestion: AutocompleteSuggestion;
}
export class SuggestionItem extends React.Component<SuggestionItemProps> {
public static defaultProps: Partial<SuggestionItemProps> = {
isSelected: false,
};
export const SuggestionItem: React.SFC<Props> = props => {
const { isSelected, onClick, onMouseEnter, suggestion } = props;
public render() {
const { isSelected, onClick, onMouseEnter, suggestion } = this.props;
return (
<SuggestionItemContainer isSelected={isSelected} onClick={onClick} onMouseEnter={onMouseEnter}>
<SuggestionItemIconField suggestionType={suggestion.type}>
<EuiIcon type={getEuiIconType(suggestion.type)} />
</SuggestionItemIconField>
<SuggestionItemTextField>{suggestion.text}</SuggestionItemTextField>
<SuggestionItemDescriptionField>{suggestion.description}</SuggestionItemDescriptionField>
</SuggestionItemContainer>
);
};
return (
<SuggestionItemContainer
isSelected={isSelected}
onClick={onClick}
onMouseEnter={onMouseEnter}
>
<SuggestionItemIconField suggestionType={suggestion.type}>
<EuiIcon type={getEuiIconType(suggestion.type)} />
</SuggestionItemIconField>
<SuggestionItemTextField>{suggestion.text}</SuggestionItemTextField>
<SuggestionItemDescriptionField>{suggestion.description}</SuggestionItemDescriptionField>
</SuggestionItemContainer>
);
}
}
SuggestionItem.defaultProps = {
isSelected: false,
};
const SuggestionItemContainer = euiStyled.div<{
isSelected?: boolean;

View file

@ -114,29 +114,28 @@ interface ProgressEntryProps {
isLoading: boolean;
}
class ProgressEntry extends React.PureComponent<ProgressEntryProps, {}> {
public render() {
const { alignment, children, className, color, isLoading } = this.props;
// NOTE: styled-components seems to make all props in EuiProgress required, so this
// style attribute hacking replaces styled-components here for now until that can be fixed
// see: https://github.com/elastic/eui/issues/1655
const alignmentStyle =
alignment === 'top' ? { top: 0, bottom: 'initial' } : { top: 'initial', bottom: 0 };
const ProgressEntry: React.SFC<ProgressEntryProps> = props => {
const { alignment, children, className, color, isLoading } = props;
return (
<ProgressEntryWrapper className={className}>
<EuiProgress
style={alignmentStyle}
color={color}
size="xs"
position="absolute"
{...(!isLoading ? { max: 1, value: 1 } : {})}
/>
{children}
</ProgressEntryWrapper>
);
}
}
// NOTE: styled-components seems to make all props in EuiProgress required, so this
// style attribute hacking replaces styled-components here for now until that can be fixed
// see: https://github.com/elastic/eui/issues/1655
const alignmentStyle =
alignment === 'top' ? { top: 0, bottom: 'initial' } : { top: 'initial', bottom: 0 };
return (
<ProgressEntryWrapper className={className}>
<EuiProgress
style={alignmentStyle}
color={color}
size="xs"
position="absolute"
{...(!isLoading ? { max: 1, value: 1 } : {})}
/>
{children}
</ProgressEntryWrapper>
);
};
const ProgressEntryWrapper = euiStyled.div`
align-items: center;

View file

@ -16,27 +16,21 @@ interface LinkToPageProps {
match: RouteMatch<{}>;
}
export class LinkToPage extends React.Component<LinkToPageProps> {
public render() {
const { match } = this.props;
return (
<Switch>
<Route
path={`${match.url}/:sourceId?/:nodeType(host|container|pod)-logs/:nodeId`}
component={RedirectToNodeLogs}
/>
<Route
path={`${match.url}/:nodeType(host|container|pod)-detail/:nodeId`}
component={RedirectToNodeDetail}
/>
<Route
path={`${match.url}/host-detail-via-ip/:hostIp`}
component={RedirectToHostDetailViaIP}
/>
<Route path={`${match.url}/:sourceId?/logs`} component={RedirectToLogs} />
<Redirect to="/infrastructure" />
</Switch>
);
}
}
export const LinkToPage: React.SFC<LinkToPageProps> = props => (
<Switch>
<Route
path={`${props.match.url}/:sourceId?/:nodeType(host|container|pod)-logs/:nodeId`}
component={RedirectToNodeLogs}
/>
<Route
path={`${props.match.url}/:nodeType(host|container|pod)-detail/:nodeId`}
component={RedirectToNodeDetail}
/>
<Route
path={`${props.match.url}/host-detail-via-ip/:hostIp`}
component={RedirectToHostDetailViaIP}
/>
<Route path={`${props.match.url}/:sourceId?/logs`} component={RedirectToLogs} />
<Redirect to="/infrastructure" />
</Switch>
);

View file

@ -231,7 +231,7 @@ const AnnotationTooltip: React.FunctionComponent<{ details: string }> = ({ detai
const renderAnnotationTooltip = (details?: string) => {
// Note: Seems to be necessary to get things typed correctly all the way through to elastic-charts components
if (!details) {
return <div></div>;
return <div />;
}
return <AnnotationTooltip details={details} />;
};

View file

@ -354,7 +354,7 @@ export function PopoverEditor(props: PopoverEditorProps) {
defaultMessage: 'To use this function, select a field.',
})}
iconType="sortUp"
></EuiCallOut>
/>
)}
{!incompatibleSelectedOperationType && ParamEditor && (
<>

View file

@ -36,7 +36,7 @@ export const SeverityCell: FC<SeverityCellProps> = memo(({ score, multiBucketImp
<path
d="M-6.708203932499369,-2.23606797749979H-2.23606797749979V-6.708203932499369H2.23606797749979V-2.23606797749979H6.708203932499369V2.23606797749979H2.23606797749979V6.708203932499369H-2.23606797749979V2.23606797749979H-6.708203932499369Z"
transform="translate(8,8)"
></path>
/>
</svg>
</EuiFlexItem>
<EuiFlexItem grow={false}>{severity}</EuiFlexItem>

View file

@ -64,7 +64,7 @@ export const ActionsPanel: FC<Props> = ({ indexPattern }) => {
</EuiText>
<EuiSpacer size="m" />
<EuiFlexGroup gutterSize="l" responsive={true} wrap={true}>
<DataRecognizer indexPattern={indexPattern} results={recognizerResults}></DataRecognizer>
<DataRecognizer indexPattern={indexPattern} results={recognizerResults} />
</EuiFlexGroup>
<EuiSpacer size="l" />
</div>

View file

@ -31,7 +31,7 @@ export const AdditionalSection: FC<Props> = ({ additionalExpanded, setAdditional
<EuiFlexItem>
<CalendarsSelection />
</EuiFlexItem>
<EuiFlexItem></EuiFlexItem>
<EuiFlexItem />
</EuiFlexGroup>
</EuiAccordion>
</Fragment>

View file

@ -44,7 +44,7 @@ export const AdvancedSettings: FC<Props> = ({ setIsValid }) => {
<EuiFlexItem>
<ModelMemoryLimitInput />
</EuiFlexItem>
<EuiFlexItem></EuiFlexItem>
<EuiFlexItem />
</EuiFlexGroup>
</Fragment>
);

View file

@ -78,7 +78,7 @@ export const ValidationStep: FC<StepProps> = ({ setCurrentStep, isCurrentStep })
/>
</Fragment>
)}
{isCurrentStep === false && <Fragment></Fragment>}
{isCurrentStep === false && <Fragment />}
</Fragment>
);
};

View file

@ -5,32 +5,26 @@
*/
import { EuiIcon, EuiSpacer, EuiTitle } from '@elastic/eui';
import React, { Component } from 'react';
import React from 'react';
interface Props {
title: React.ReactNode;
}
export class AuthenticationStatePage extends Component<Props, {}> {
public render() {
return (
<div className="secAuthenticationStatePage">
<header className="secAuthenticationStatePage__header">
<div className="secAuthenticationStatePage__content eui-textCenter">
<EuiSpacer size="xxl" />
<span className="secAuthenticationStatePage__logo">
<EuiIcon type="logoKibana" size="xxl" />
</span>
<EuiTitle size="l" className="secAuthenticationStatePage__title">
<h1>{this.props.title}</h1>
</EuiTitle>
<EuiSpacer size="xl" />
</div>
</header>
<div className="secAuthenticationStatePage__content eui-textCenter">
{this.props.children}
</div>
export const AuthenticationStatePage: React.SFC<Props> = props => (
<div className="secAuthenticationStatePage">
<header className="secAuthenticationStatePage__header">
<div className="secAuthenticationStatePage__content eui-textCenter">
<EuiSpacer size="xxl" />
<span className="secAuthenticationStatePage__logo">
<EuiIcon type="logoKibana" size="xxl" />
</span>
<EuiTitle size="l" className="secAuthenticationStatePage__title">
<h1>{props.title}</h1>
</EuiTitle>
<EuiSpacer size="xl" />
</div>
);
}
}
</header>
<div className="secAuthenticationStatePage__content eui-textCenter">{props.children}</div>
</div>
);

View file

@ -4,7 +4,7 @@
* you may not use this file except in compliance with the Elastic License.
*/
import { EuiPage, EuiPageBody, EuiPanel, EuiSpacer, EuiText } from '@elastic/eui';
import React, { Component } from 'react';
import React from 'react';
import { getUserDisplayName, AuthenticatedUser } from '../../../../common/model';
import { ChangePassword } from './change_password';
import { PersonalInfo } from './personal_info';
@ -13,28 +13,20 @@ interface Props {
user: AuthenticatedUser;
}
export class AccountManagementPage extends Component<Props, {}> {
constructor(props: Props) {
super(props);
}
export const AccountManagementPage: React.SFC<Props> = props => (
<EuiPage>
<EuiPageBody restrictWidth>
<EuiPanel>
<EuiText data-test-subj={'userDisplayName'}>
<h1>{getUserDisplayName(props.user)}</h1>
</EuiText>
public render() {
return (
<EuiPage>
<EuiPageBody restrictWidth>
<EuiPanel>
<EuiText data-test-subj={'userDisplayName'}>
<h1>{getUserDisplayName(this.props.user)}</h1>
</EuiText>
<EuiSpacer size="xl" />
<EuiSpacer size="xl" />
<PersonalInfo user={props.user} />
<PersonalInfo user={this.props.user} />
<ChangePassword user={this.props.user} />
</EuiPanel>
</EuiPageBody>
</EuiPage>
);
}
}
<ChangePassword user={props.user} />
</EuiPanel>
</EuiPageBody>
</EuiPage>
);

View file

@ -5,24 +5,20 @@
*/
import { EuiPanel, EuiText } from '@elastic/eui';
import React, { Component, ReactNode } from 'react';
import React, { ReactNode } from 'react';
interface Props {
title: ReactNode;
message: ReactNode;
}
export class DisabledLoginForm extends Component<Props, {}> {
public render() {
return (
<EuiPanel>
<EuiText color="danger" style={{ textAlign: 'center' }}>
<p>{this.props.title}</p>
</EuiText>
<EuiText style={{ textAlign: 'center' }}>
<p>{this.props.message}</p>
</EuiText>
</EuiPanel>
);
}
}
export const DisabledLoginForm: React.SFC<Props> = props => (
<EuiPanel>
<EuiText color="danger" style={{ textAlign: 'center' }}>
<p>{props.title}</p>
</EuiText>
<EuiText style={{ textAlign: 'center' }}>
<p>{props.message}</p>
</EuiText>
</EuiPanel>
);

View file

@ -271,7 +271,7 @@ export const DefaultFieldRendererOverflow = React.memo<DefaultFieldRendererOverf
rowItems={rowItems}
moreMaxHeight={moreMaxHeight}
overflowIndexStart={overflowIndexStart}
></MoreContainer>
/>
</EuiPopover>
)}
</EuiFlexItem>

View file

@ -12,13 +12,13 @@ import { MatrixOverTimeHistogram } from '.';
jest.mock('@elastic/eui', () => {
return {
EuiPanel: (children: JSX.Element) => <>{children}</>,
EuiLoadingContent: () => <div className="euiLoadingContent"></div>,
EuiLoadingContent: () => <div className="euiLoadingContent" />,
};
});
jest.mock('../loader', () => {
return {
Loader: () => <div className="loader"></div>,
Loader: () => <div className="loader" />,
};
});
@ -28,13 +28,13 @@ jest.mock('../../lib/settings/use_kibana_ui_setting', () => {
jest.mock('../header_panel', () => {
return {
HeaderPanel: () => <div className="headerPanel"></div>,
HeaderPanel: () => <div className="headerPanel" />,
};
});
jest.mock('../charts/barchart', () => {
return {
BarChart: () => <div className="barchart"></div>,
BarChart: () => <div className="barchart" />,
};
});

View file

@ -54,7 +54,7 @@ export interface SkeletonRowProps extends CellProps, RowProps {
export const SkeletonRow = React.memo<SkeletonRowProps>(
({ cellColor, cellCount = 4, cellMargin, rowHeight, rowPadding, style }) => {
const cells = [...Array(cellCount)].map((_, i) => (
<Cell cellColor={cellColor} cellMargin={cellMargin} key={i}></Cell>
<Cell cellColor={cellColor} cellMargin={cellMargin} key={i} />
));
return (

View file

@ -38,11 +38,11 @@ const from = new Date('2019-06-15T06:00:00.000Z').valueOf();
const to = new Date('2019-06-18T06:00:00.000Z').valueOf();
jest.mock('../charts/areachart', () => {
return { AreaChart: () => <div className="areachart"></div> };
return { AreaChart: () => <div className="areachart" /> };
});
jest.mock('../charts/barchart', () => {
return { BarChart: () => <div className="barchart"></div> };
return { BarChart: () => <div className="barchart" /> };
});
describe('Stat Items Component', () => {

View file

@ -22,7 +22,7 @@ describe('FileDraggable', () => {
eventId="1"
fileName="[fileName]"
filePath="[filePath]"
></FileDraggable>
/>
</TestProviders>
);
expect(wrapper.text()).toEqual('[fileName]in[filePath]');
@ -38,7 +38,7 @@ describe('FileDraggable', () => {
eventId="1"
fileName={undefined}
filePath={undefined}
></FileDraggable>
/>
</TestProviders>
);
expect(wrapper.text()).toEqual('');

View file

@ -6,7 +6,7 @@
import { EuiConfirmModal, EuiOverlayMask } from '@elastic/eui';
import { FormattedMessage, InjectedIntl, injectI18n } from '@kbn/i18n/react';
import React, { Component } from 'react';
import React from 'react';
interface Props {
onCancel: () => void;
@ -14,39 +14,35 @@ interface Props {
intl: InjectedIntl;
}
class ConfirmAlterActiveSpaceModalUI extends Component<Props, {}> {
public render() {
return (
<EuiOverlayMask>
<EuiConfirmModal
onConfirm={this.props.onConfirm}
onCancel={this.props.onCancel}
title={
<FormattedMessage
id="xpack.spaces.management.confirmAlterActiveSpaceModal.title"
defaultMessage="Confirm update space"
/>
}
defaultFocusedButton={'confirm'}
cancelButtonText={this.props.intl.formatMessage({
id: 'xpack.spaces.management.confirmAlterActiveSpaceModal.cancelButton',
defaultMessage: 'Cancel',
})}
confirmButtonText={this.props.intl.formatMessage({
id: 'xpack.spaces.management.confirmAlterActiveSpaceModal.updateSpaceButton',
defaultMessage: 'Update space',
})}
>
<p>
<FormattedMessage
id="xpack.spaces.management.confirmAlterActiveSpaceModal.reloadWarningMessage"
defaultMessage="You have updated the visible features in this space. Your page will reload after saving."
/>
</p>
</EuiConfirmModal>
</EuiOverlayMask>
);
}
}
const ConfirmAlterActiveSpaceModalUI: React.SFC<Props> = props => (
<EuiOverlayMask>
<EuiConfirmModal
onConfirm={props.onConfirm}
onCancel={props.onCancel}
title={
<FormattedMessage
id="xpack.spaces.management.confirmAlterActiveSpaceModal.title"
defaultMessage="Confirm update space"
/>
}
defaultFocusedButton={'confirm'}
cancelButtonText={props.intl.formatMessage({
id: 'xpack.spaces.management.confirmAlterActiveSpaceModal.cancelButton',
defaultMessage: 'Cancel',
})}
confirmButtonText={props.intl.formatMessage({
id: 'xpack.spaces.management.confirmAlterActiveSpaceModal.updateSpaceButton',
defaultMessage: 'Update space',
})}
>
<p>
<FormattedMessage
id="xpack.spaces.management.confirmAlterActiveSpaceModal.reloadWarningMessage"
defaultMessage="You have updated the visible features in this space. Your page will reload after saving."
/>
</p>
</EuiConfirmModal>
</EuiOverlayMask>
);
export const ConfirmAlterActiveSpaceModal = injectI18n(ConfirmAlterActiveSpaceModalUI);

View file

@ -8,22 +8,18 @@ import {
// @ts-ignore
EuiHeaderSectionItemButton,
} from '@elastic/eui';
import React, { Component } from 'react';
import React from 'react';
import { ButtonProps } from '../types';
export class SpacesHeaderNavButton extends Component<ButtonProps> {
public render() {
return (
<EuiHeaderSectionItemButton
aria-controls="headerSpacesMenuList"
aria-expanded={this.props.spaceSelectorShown}
aria-haspopup="true"
aria-label={this.props.linkTitle}
title={this.props.linkTitle}
onClick={this.props.toggleSpaceSelector}
>
{this.props.linkIcon}
</EuiHeaderSectionItemButton>
);
}
}
export const SpacesHeaderNavButton: React.SFC<ButtonProps> = props => (
<EuiHeaderSectionItemButton
aria-controls="headerSpacesMenuList"
aria-expanded={props.spaceSelectorShown}
aria-haspopup="true"
aria-label={props.linkTitle}
title={props.linkTitle}
onClick={props.toggleSpaceSelector}
>
{props.linkIcon}
</EuiHeaderSectionItemButton>
);

View file

@ -5,7 +5,7 @@
*/
import { EuiAvatar, EuiPopover, PopoverAnchorPosition } from '@elastic/eui';
import React, { Component, ComponentClass } from 'react';
import React, { Component } from 'react';
import { Space } from '../../../common/model/space';
import { SpaceAvatar } from '../../components';
import { SpacesManager } from '../../lib/spaces_manager';
@ -21,7 +21,7 @@ interface Props {
space: Space;
};
anchorPosition: PopoverAnchorPosition;
buttonClass: ComponentClass<ButtonProps>;
buttonClass: React.ComponentType<ButtonProps>;
}
interface State {

View file

@ -195,8 +195,8 @@ export class WarningsFlyoutStep extends React.Component<
values={{
true: <EuiCode>true</EuiCode>,
false: <EuiCode>false</EuiCode>,
yes: <EuiCode>"yes"</EuiCode>,
on: <EuiCode>"on"</EuiCode>,
yes: <EuiCode>&quot;yes&quot;</EuiCode>,
on: <EuiCode>&quot;on&quot;</EuiCode>,
one: <EuiCode>1</EuiCode>,
}}
/>

View file

@ -21,6 +21,7 @@ export interface UpgradeAssistantTabProps {
setSelectedTabIndex: (tabIndex: number) => void;
}
// eslint-disable-next-line react/prefer-stateless-function
export class UpgradeAssistantTabComponent<
T extends UpgradeAssistantTabProps = UpgradeAssistantTabProps,
S = {}

View file

@ -36,7 +36,7 @@ describe('EmptyState component', () => {
it(`doesn't render child components when count is falsey`, () => {
const component = mountWithIntl(
<EmptyStateComponent basePath="" data={undefined} loading={false}>
<div>Shouldn't be rendered</div>
<div>Shouldn&apos;t be rendered</div>
</EmptyStateComponent>
);
expect(component).toMatchSnapshot();
@ -58,7 +58,7 @@ describe('EmptyState component', () => {
];
const component = mountWithIntl(
<EmptyStateComponent basePath="" data={undefined} errors={errors} loading={false}>
<div>Shouldn't appear...</div>
<div>Shouldn&apos;t appear...</div>
</EmptyStateComponent>
);
expect(component).toMatchSnapshot();

View file

@ -11,7 +11,7 @@ import React from 'react';
export const renderUptimeKibanaGlobalHelp = (docsSiteUrl: string, docLinkVersion: string) => (
<React.Fragment>
<EuiHorizontalRule margin="none"></EuiHorizontalRule>
<EuiHorizontalRule margin="none" />
<EuiSpacer />
<EuiText size="s">For Uptime specific information</EuiText>
<EuiSpacer />

View file

@ -21,7 +21,7 @@ export const getGeneralErrorToast = (errorText: string, err: Error): ToastInput
<FormattedMessage
id="xpack.reporting.publicNotifier.error.tryRefresh"
defaultMessage="Try refreshing the page."
></FormattedMessage>
/>
</Fragment>
),
iconType: undefined,