Skip to content

Commit

Permalink
Merge branch 'main' of github.com:elastic/kibana into shared-common-e…
Browse files Browse the repository at this point in the history
…verywhere
  • Loading branch information
afharo committed Jul 29, 2024
2 parents a5854ae + 0c45b11 commit 313612a
Show file tree
Hide file tree
Showing 62 changed files with 760 additions and 1,071 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -116,7 +116,9 @@ function initChromiumOptions(browserType: Browsers, acceptInsecureCerts: boolean
// Use fake device for Media Stream to replace actual camera and microphone.
'use-fake-device-for-media-stream',
// Bypass the media stream infobar by selecting the default device for media streams (e.g. WebRTC). Works with --use-fake-device-for-media-stream.
'use-fake-ui-for-media-stream'
'use-fake-ui-for-media-stream',
// Do not show "Choose your search engine" dialog (> Chrome v127)
'disable-search-engine-choice-screen'
);

if (process.platform === 'linux') {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -41,6 +41,8 @@ export async function runCheckFtrConfigsCli() {
.split('\n')
.map((file) => Path.resolve(REPO_ROOT, file));

const loadingConfigs = [];

const possibleConfigs = files.filter((file) => {
if (IGNORED_PATHS.includes(file)) {
return false;
Expand All @@ -66,24 +68,45 @@ export async function runCheckFtrConfigsCli() {
return false;
}

if (file.match(/mocks.ts$/)) {
// No FTR configs in /packages/
if (file.match(/\/packages\//)) {
return false;
}

if (file.match(/(mock|mocks).ts$/)) {
return false;
}

const fileContent = readFileSync(file).toString();

if (fileContent.match(/(testRunner)|(testFiles)/)) {
if (
// explicitly define 'testRunner' or 'testFiles'
fileContent.match(/(testRunner)|(testFiles)/) ||
// export default createTestConfig
fileContent.match(/export\s+default\s+createTestConfig/) ||
// export default async function ({ readConfigFile }: FtrConfigProviderContext)
// async function config({ readConfigFile }: FtrConfigProviderContext)
// export default async function (ftrConfigProviderContext: FtrConfigProviderContext)
fileContent.match(
/(?:export\s+default\s+)?async\s+function(?:\s+\w+)?\s*\(\s*(?:\{\s*readConfigFile\s*\}|\w+)\s*(?::\s*FtrConfigProviderContext\s*)?\)/
)
) {
// test config
return true;
}

if (fileContent.match(/(describe)|(defineCypressConfig)/)) {
if (file.match(/config.ts$/) && fileContent.match(/export\s+default\s+configs\./)) {
return true;
}

if (fileContent.match(/(describe)|(defineCypressConfig)|(cy\.)/)) {
// test file or Cypress config
return false;
}

// FTR config file should have default export
try {
loadingConfigs.push(file);
// eslint-disable-next-line @typescript-eslint/no-var-requires
const exports = require(file);
const defaultExport = exports.__esModule ? exports.default : exports;
Expand All @@ -94,6 +117,10 @@ export async function runCheckFtrConfigsCli() {
}
});

if (loadingConfigs.length) {
log.info(`${loadingConfigs.length} files were loaded as FTR configs for validation`);
}

const { allFtrConfigs, manifestPaths } = getAllFtrConfigsAndManifests();

const invalid = possibleConfigs.filter((path) => !allFtrConfigs.includes(path));
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -107,7 +107,7 @@ export const MessageList = ({
closePopover={closePopover}
>
<ul className="lnsWorkspaceWarningList">
{messages.map((message, index) => (
{messages.map(({ hidePopoverIcon = false, ...message }, index) => (
<li
key={index}
className="lnsWorkspaceWarningList__item"
Expand All @@ -121,13 +121,15 @@ export const MessageList = ({
responsive={false}
className="lnsWorkspaceWarningList__textItem"
>
<EuiFlexItem grow={false}>
{message.severity === 'error' ? (
<EuiIcon type="error" color="danger" />
) : (
<EuiIcon type="alert" color="warning" />
)}
</EuiFlexItem>
{!hidePopoverIcon && (
<EuiFlexItem grow={false}>
{message.severity === 'error' ? (
<EuiIcon type="error" color="danger" />
) : (
<EuiIcon type="alert" color="warning" />
)}
</EuiFlexItem>
)}
<EuiFlexItem grow={1} className="lnsWorkspaceWarningList__description">
<EuiText size="s">{message.longMessage}</EuiText>
</EuiFlexItem>
Expand Down
85 changes: 85 additions & 0 deletions x-pack/plugins/lens/public/embeddable/embeddable.test.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -32,6 +32,7 @@ import { act } from 'react-dom/test-utils';
import { inspectorPluginMock } from '@kbn/inspector-plugin/public/mocks';
import { Visualization } from '../types';
import { createMockDatasource, createMockVisualization } from '../mocks';
import { FIELD_NOT_FOUND, FIELD_WRONG_TYPE } from '../user_messages_ids';

jest.mock('@kbn/inspector-plugin/public', () => ({
isAvailable: false,
Expand Down Expand Up @@ -272,6 +273,90 @@ describe('embeddable', () => {
expect(expressionRenderer).toHaveBeenCalledTimes(0);
});

it('should override embeddableBadge message', async () => {
const getBadgeMessage = jest.fn(
(): ReturnType<NonNullable<LensEmbeddableInput['onBeforeBadgesRender']>> => [
{
uniqueId: FIELD_NOT_FOUND,
severity: 'warning',
fixableInEditor: true,
displayLocations: [
{ id: 'embeddableBadge' },
{ id: 'dimensionButton', dimensionId: '1' },
],
longMessage: 'custom',
shortMessage: '',
hidePopoverIcon: true,
},
]
);

const embeddable = new Embeddable(
getEmbeddableProps({
datasourceMap: {
...defaultDatasourceMap,
[defaultDatasourceId]: {
...defaultDatasourceMap[defaultDatasourceId],
getUserMessages: jest.fn(() => [
{
uniqueId: FIELD_NOT_FOUND,
severity: 'error',
fixableInEditor: true,
displayLocations: [
{ id: 'embeddableBadge' },
{ id: 'dimensionButton', dimensionId: '1' },
],
longMessage: 'original',
shortMessage: '',
},
{
uniqueId: FIELD_WRONG_TYPE,
severity: 'error',
fixableInEditor: true,
displayLocations: [{ id: 'visualization' }],
longMessage: 'original',
shortMessage: '',
},
]),
},
},
}),
{
onBeforeBadgesRender: getBadgeMessage as LensEmbeddableInput['onBeforeBadgesRender'],
} as LensEmbeddableInput
);

const getUserMessagesSpy = jest.spyOn(embeddable, 'getUserMessages');
await embeddable.initializeSavedVis({} as LensEmbeddableInput);

embeddable.render(mountpoint);

expect(getUserMessagesSpy.mock.results.flatMap((r) => r.value)).toEqual(
expect.arrayContaining([
{
uniqueId: FIELD_WRONG_TYPE,
severity: 'error',
fixableInEditor: true,
displayLocations: [{ id: 'visualization' }],
longMessage: 'original',
shortMessage: '',
},
{
uniqueId: FIELD_NOT_FOUND,
severity: 'warning',
fixableInEditor: true,
displayLocations: [
{ id: 'embeddableBadge' },
{ id: 'dimensionButton', dimensionId: '1' },
],
longMessage: 'custom',
shortMessage: '',
hidePopoverIcon: true,
},
])
);
});

it('should not render the vis if loaded saved object conflicts', async () => {
attributeService.unwrapAttributes = jest.fn(
(_input: LensByValueInput | LensByReferenceInput) => {
Expand Down
30 changes: 25 additions & 5 deletions x-pack/plugins/lens/public/embeddable/embeddable.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -185,6 +185,7 @@ interface LensBaseEmbeddableInput extends EmbeddableInput {
data: Simplify<LensTableRowContextMenuEvent['data'] & PreventableEvent>
) => void;
abortController?: AbortController;
onBeforeBadgesRender?: (userMessages: UserMessage[]) => UserMessage[];
}

export type LensByValueInput = {
Expand Down Expand Up @@ -610,6 +611,22 @@ export class Embeddable

private fullAttributes: LensSavedObjectAttributes | undefined;

private handleExternalUserMessage = (messages: UserMessage[]) => {
if (this.input.onBeforeBadgesRender) {
// we need something else to better identify those errors
const [messagesToHandle, originalMessages] = partition(messages, (message) =>
message.displayLocations.some((location) => location.id === 'embeddableBadge')
);

if (messagesToHandle.length > 0) {
const customBadgeMessages = this.input.onBeforeBadgesRender(messagesToHandle);
return [...originalMessages, ...customBadgeMessages];
}
}

return messages;
};

public getUserMessages: UserMessagesGetter = (locationId, filters) => {
const userMessages: UserMessage[] = [];
userMessages.push(
Expand Down Expand Up @@ -637,8 +654,9 @@ export class Embeddable
);

if (!this.savedVis) {
return userMessages;
return this.handleExternalUserMessage(userMessages);
}

const mergedSearchContext = this.getMergedSearchContext();

const framePublicAPI: FramePublicAPI = {
Expand Down Expand Up @@ -683,10 +701,12 @@ export class Embeddable
}) ?? [])
);

return filterAndSortUserMessages(
[...userMessages, ...Object.values(this.additionalUserMessages)],
locationId,
filters ?? {}
return this.handleExternalUserMessage(
filterAndSortUserMessages(
[...userMessages, ...Object.values(this.additionalUserMessages)],
locationId,
filters ?? {}
)
);
};

Expand Down
1 change: 1 addition & 0 deletions x-pack/plugins/lens/public/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -33,6 +33,7 @@ export type {
Visualization,
VisualizationSuggestion,
Suggestion,
UserMessage,
} from './types';
export type {
LegacyMetricState as MetricState,
Expand Down
1 change: 1 addition & 0 deletions x-pack/plugins/lens/public/types.ts
Original file line number Diff line number Diff line change
Expand Up @@ -300,6 +300,7 @@ export type UserMessagesDisplayLocationId = UserMessageDisplayLocation['id'];
export interface UserMessage {
uniqueId: string;
severity: 'error' | 'warning' | 'info';
hidePopoverIcon?: boolean;
shortMessage: string;
longMessage: string | React.ReactNode | ((closePopover: () => void) => React.ReactNode);
fixableInEditor: boolean;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -16,8 +16,8 @@ export enum SignalTypes {
export interface EntityMetrics {
latency: number | null;
throughput: number | null;
failedTransactionRate: number;
logRate: number;
failedTransactionRate: number | null;
logRate: number | null;
logErrorRate: number | null;
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,13 @@
* 2.0.
*/

export const ENTITY = 'entity';
export const LAST_SEEN = 'entity.lastSeenTimestamp';
export const FIRST_SEEN = 'entity.firstSeenTimestamp';

export const ENTITY = 'entity';
export const ENTITY_ID = 'entity.id';
export const ENTITY_METRICS_LATENCY = 'entity.metrics.latency';
export const ENTITY_METRICS_LOG_ERROR_RATE = 'entity.metrics.logErrorRate';
export const ENTITY_METRICS_LOG_RATE = 'entity.metrics.logRate';
export const ENTITY_METRICS_THROUGHPUT = 'entity.metrics.throughput';
export const ENTITY_METRICS_FAILED_TRANSACTION_RATE = 'entity.metrics.failedTransactionRate';
export const ENTITY_TYPE = 'entity.type';
Original file line number Diff line number Diff line change
Expand Up @@ -71,6 +71,12 @@ describe('formatters', () => {
expect(asDecimalOrInteger(0.25435632645, 1)).toEqual('0.3');
});
});

it('returns fallback when valueNaN', () => {
expect(asDecimalOrInteger(NaN)).toEqual('N/A');
expect(asDecimalOrInteger(null)).toEqual('N/A');
expect(asDecimalOrInteger(undefined)).toEqual('N/A');
});
});
});

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -56,7 +56,11 @@ export function asPercent(
return numeral(decimal).format('0.0%');
}

export function asDecimalOrInteger(value: number, threshold = 10) {
export function asDecimalOrInteger(value: Maybe<number>, threshold = 10) {
if (!isFiniteNumber(value)) {
return NOT_AVAILABLE_LABEL;
}

// exact 0 or above threshold should not have decimal
if (value === 0 || value >= threshold) {
return asInteger(value);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -124,7 +124,6 @@ describe('Service inventory', () => {
cy.get('[data-test-subj="tableSearchInput"]').should('not.exist');
cy.contains('Enable fast filter').click();
cy.get('[data-test-subj="tableSearchInput"]').should('exist');
cy.contains('Try it').should('not.exist');
cy.contains('opbeans-node');
cy.contains('opbeans-java');
cy.contains('opbeans-rum');
Expand All @@ -137,7 +136,6 @@ describe('Service inventory', () => {
cy.contains('opbeans-java');
cy.contains('opbeans-rum');
cy.contains('Disable fast filter').click();
cy.contains('Try it').should('exist');
cy.get('[data-test-subj="tableSearchInput"]').should('not.exist');
});
});
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -121,8 +121,8 @@ describe('Agent configuration', () => {

cy.get('mark').contains('All').click({ force: true });
cy.contains('Next step').click();
cy.contains('Service name All');
cy.contains('Environment All');
cy.get('[data-test-subj="settingsPage_serviceName"]').contains('All');
cy.get('[data-test-subj="settingsPage_environmentName"]').contains('All');
cy.contains('Edit').click();
cy.wait('@serviceEnvironmentApi');
cy.getByTestSubj('serviceEnviromentComboBox')
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -132,7 +132,15 @@ export function SettingsPage({
<EuiFlexItem>
<EuiStat
titleSize="xs"
title={isLoading ? '-' : getOptionLabel(newConfig.service.name)}
title={
isLoading ? (
'-'
) : (
<span data-test-subj="settingsPage_serviceName">
{getOptionLabel(newConfig.service.name)}
</span>
)
}
description={i18n.translate(
'xpack.apm.agentConfig.chooseService.service.name.label',
{ defaultMessage: 'Service name' }
Expand All @@ -142,7 +150,15 @@ export function SettingsPage({
<EuiFlexItem>
<EuiStat
titleSize="xs"
title={isLoading ? '-' : getOptionLabel(newConfig.service.environment)}
title={
isLoading ? (
'-'
) : (
<span data-test-subj="settingsPage_environmentName">
{getOptionLabel(newConfig.service.environment)}
</span>
)
}
description={i18n.translate(
'xpack.apm.agentConfig.chooseService.service.environment.label',
{ defaultMessage: 'Environment' }
Expand Down
Loading

0 comments on commit 313612a

Please sign in to comment.