Skip to content

Commit

Permalink
[APM] Add “Analyze Data” button (#103485)
Browse files Browse the repository at this point in the history
Co-authored-by: Shahzad <[email protected]>
  • Loading branch information
sorenlouv and shahzad31 authored Jun 30, 2021
1 parent 21858a5 commit 4aca0b7
Show file tree
Hide file tree
Showing 10 changed files with 282 additions and 11 deletions.
60 changes: 60 additions & 0 deletions x-pack/plugins/apm/common/__snapshots__/apm_telemetry.test.ts.snap

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

34 changes: 30 additions & 4 deletions x-pack/plugins/apm/common/agent_name.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@
* 2.0.
*/

import { isJavaAgentName, isRumAgentName } from './agent_name';
import { isJavaAgentName, isRumAgentName, isIosAgentName } from './agent_name';

describe('agent name helpers', () => {
describe('isJavaAgentName', () => {
Expand All @@ -22,7 +22,7 @@ describe('agent name helpers', () => {
});

describe('when the agent name is not java', () => {
it('returns true', () => {
it('returns false', () => {
expect(isJavaAgentName('not java')).toEqual(false);
});
});
Expand All @@ -47,9 +47,35 @@ describe('agent name helpers', () => {
});
});

describe('when the agent name something else', () => {
describe('when the agent name is something else', () => {
it('returns false', () => {
expect(isRumAgentName('not rum')).toEqual(false);
});
});
});

describe('isIosAgentName', () => {
describe('when the agent name is js-base', () => {
it('returns true', () => {
expect(isIosAgentName('iOS/swift')).toEqual(true);
});
});

describe('when the agent name is rum-js', () => {
it('returns true', () => {
expect(isRumAgentName('java')).toEqual(false);
expect(isIosAgentName('ios/swift')).toEqual(true);
});
});

describe('when the agent name is opentelemetry/swift', () => {
it('returns true', () => {
expect(isIosAgentName('opentelemetry/swift')).toEqual(true);
});
});

describe('when the agent name is something else', () => {
it('returns false', () => {
expect(isIosAgentName('not ios')).toEqual(false);
});
});
});
Expand Down
15 changes: 14 additions & 1 deletion x-pack/plugins/apm/common/agent_name.ts
Original file line number Diff line number Diff line change
Expand Up @@ -26,12 +26,14 @@ export const OPEN_TELEMETRY_AGENT_NAMES: AgentName[] = [
'opentelemetry/php',
'opentelemetry/python',
'opentelemetry/ruby',
'opentelemetry/swift',
'opentelemetry/webjs',
];

export const AGENT_NAMES: AgentName[] = [
'dotnet',
'go',
'iOS/swift',
'java',
'js-base',
'nodejs',
Expand Down Expand Up @@ -62,7 +64,9 @@ export function isRumAgentName(
return RUM_AGENT_NAMES.includes(agentName! as AgentName);
}

export function normalizeAgentName(agentName: string | undefined) {
export function normalizeAgentName<T extends string | undefined>(
agentName: T
): T | string {
if (isRumAgentName(agentName)) {
return 'rum-js';
}
Expand All @@ -71,5 +75,14 @@ export function normalizeAgentName(agentName: string | undefined) {
return 'java';
}

if (isIosAgentName(agentName)) {
return 'ios';
}

return agentName;
}

export function isIosAgentName(agentName?: string) {
const lowercased = agentName && agentName.toLowerCase();
return lowercased === 'ios/swift' || lowercased === 'opentelemetry/swift';
}
Original file line number Diff line number Diff line change
Expand Up @@ -131,6 +131,7 @@ export function Correlations() {
return (
<>
<EuiButton
fill
onClick={() => {
setIsFlyoutVisible(true);
}}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@
import { EuiFlexGroup, EuiFlexItem, EuiPanel } from '@elastic/eui';
import React from 'react';
import { useTrackPageview } from '../../../../../observability/public';
import { isRumAgentName } from '../../../../common/agent_name';
import { isRumAgentName, isIosAgentName } from '../../../../common/agent_name';
import { AnnotationsContextProvider } from '../../../context/annotations/annotations_context';
import { useApmServiceContext } from '../../../context/apm_service/use_apm_service_context';
import { ChartPointerEventContextProvider } from '../../../context/chart_pointer_event/chart_pointer_event_context';
Expand Down Expand Up @@ -43,6 +43,7 @@ export function ServiceOverview({ serviceName }: ServiceOverviewProps) {
const { isMedium } = useBreakPoints();
const rowDirection = isMedium ? 'column' : 'row';
const isRumAgent = isRumAgentName(agentName);
const isIosAgent = isIosAgentName(agentName);

return (
<AnnotationsContextProvider>
Expand Down Expand Up @@ -110,7 +111,7 @@ export function ServiceOverview({ serviceName }: ServiceOverviewProps) {
)}
</EuiFlexGroup>
</EuiFlexItem>
{!isRumAgent && (
{!isRumAgent && !isIosAgent && (
<EuiFlexItem>
<EuiFlexGroup
direction="column"
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -13,11 +13,18 @@ import {
EuiPageHeaderProps,
EuiTitle,
EuiBetaBadge,
EuiToolTip,
EuiButtonEmpty,
} from '@elastic/eui';
import { ApmMainTemplate } from './apm_main_template';
import { useKibana } from '../../../../../../../src/plugins/kibana_react/public';
import { ApmServiceContextProvider } from '../../../context/apm_service/apm_service_context';
import { enableServiceOverview } from '../../../../common/ui_settings_keys';
import { isJavaAgentName, isRumAgentName } from '../../../../common/agent_name';
import {
isJavaAgentName,
isRumAgentName,
isIosAgentName,
} from '../../../../common/agent_name';
import { ServiceIcons } from '../../shared/service_icons';
import { useApmPluginContext } from '../../../context/apm_plugin/use_apm_plugin_context';
import { useApmServiceContext } from '../../../context/apm_service/use_apm_service_context';
Expand All @@ -29,8 +36,17 @@ import { useServiceOverviewHref } from '../../shared/Links/apm/service_overview_
import { useServiceProfilingHref } from '../../shared/Links/apm/service_profiling_link';
import { useTransactionsOverviewHref } from '../../shared/Links/apm/transaction_overview_link';
import { useUrlParams } from '../../../context/url_params_context/use_url_params';
import { ENVIRONMENT_NOT_DEFINED } from '../../../../common/environment_filter_values';
import {
SERVICE_NAME,
SERVICE_ENVIRONMENT,
} from '../../../../common/elasticsearch_fieldnames';
import { Correlations } from '../../app/correlations';
import { SearchBar } from '../../shared/search_bar';
import {
createExploratoryViewUrl,
SeriesUrl,
} from '../../../../../observability/public';

type Tab = NonNullable<EuiPageHeaderProps['tabs']>[0] & {
key:
Expand All @@ -54,12 +70,12 @@ interface Props {
export function ApmServiceTemplate(props: Props) {
return (
<ApmServiceContextProvider>
<Template {...props} />
<TemplateWithContext {...props} />
</ApmServiceContextProvider>
);
}

function Template({
function TemplateWithContext({
children,
serviceName,
selectedTab,
Expand All @@ -86,6 +102,10 @@ function Template({
</EuiFlexGroup>
</EuiFlexItem>

<EuiFlexItem grow={false}>
<AnalyzeDataButton serviceName={serviceName} />
</EuiFlexItem>

<EuiFlexItem grow={false}>
<Correlations />
</EuiFlexItem>
Expand All @@ -100,6 +120,53 @@ function Template({
);
}

function AnalyzeDataButton({ serviceName }: { serviceName: string }) {
const { agentName } = useApmServiceContext();
const { services } = useKibana();
const { urlParams } = useUrlParams();
const { rangeTo, rangeFrom, environment } = urlParams;
const basepath = services.http?.basePath.get();

if (isRumAgentName(agentName) || isIosAgentName(agentName)) {
const href = createExploratoryViewUrl(
{
'apm-series': {
dataType: isRumAgentName(agentName) ? 'ux' : 'mobile',
time: { from: rangeFrom, to: rangeTo },
reportType: 'kpi-over-time',
reportDefinitions: {
[SERVICE_NAME]: [serviceName],
...(!!environment && ENVIRONMENT_NOT_DEFINED.value !== environment
? { [SERVICE_ENVIRONMENT]: [environment] }
: {}),
},
operationType: 'average',
isNew: true,
} as SeriesUrl,
},
basepath
);

return (
<EuiToolTip
position="top"
content={i18n.translate('xpack.apm.analyzeDataButton.tooltip', {
defaultMessage:
'EXPERIMENTAL - Analyze Data allows you to select and filter result data in any dimension, and look for the cause or impact of performance problems',
})}
>
<EuiButtonEmpty href={href} iconType="visBarVerticalStacked">
{i18n.translate('xpack.apm.analyzeDataButton.label', {
defaultMessage: 'Analyze data',
})}
</EuiButtonEmpty>
</EuiToolTip>
);
}

return null;
}

function useTabs({
serviceName,
selectedTab,
Expand Down Expand Up @@ -153,7 +220,10 @@ function useTabs({
defaultMessage: 'Metrics',
}),
hidden:
!agentName || isRumAgentName(agentName) || isJavaAgentName(agentName),
!agentName ||
isRumAgentName(agentName) ||
isJavaAgentName(agentName) ||
isIosAgentName(agentName),
},
{
key: 'service-map',
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@
*/

import {
isIosAgentName,
isRumAgentName,
isJavaAgentName,
OPEN_TELEMETRY_AGENT_NAMES,
Expand Down Expand Up @@ -70,6 +71,10 @@ export function getAgentIconKey(agentName: string) {
return 'java';
}

if (isIosAgentName(lowercasedAgentName)) {
return 'ios';
}

// Remove "opentelemetry/" prefix
const agentNameWithoutPrefix = lowercasedAgentName.replace(
/^opentelemetry\//,
Expand Down
3 changes: 3 additions & 0 deletions x-pack/plugins/apm/server/lib/apm_telemetry/schema.ts
Original file line number Diff line number Diff line change
Expand Up @@ -74,6 +74,7 @@ const apmPerAgentSchema: Pick<
// In the meanwhile, we'll have to maintain these lists up to date (TS will remind us to update)
services_per_agent: {
dotnet: long,
'iOS/swift': long,
go: long,
java: long,
'js-base': long,
Expand All @@ -92,10 +93,12 @@ const apmPerAgentSchema: Pick<
'opentelemetry/php': long,
'opentelemetry/python': long,
'opentelemetry/ruby': long,
'opentelemetry/swift': long,
'opentelemetry/webjs': long,
},
agents: {
dotnet: agentSchema,
'iOS/swift': agentSchema,
go: agentSchema,
java: agentSchema,
'js-base': agentSchema,
Expand Down
2 changes: 2 additions & 0 deletions x-pack/plugins/apm/typings/es_schemas/ui/fields/agent.ts
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@ export type ElasticAgentName =
| 'go'
| 'java'
| 'js-base'
| 'iOS/swift'
| 'rum-js'
| 'nodejs'
| 'python'
Expand All @@ -27,6 +28,7 @@ export type OpenTelemetryAgentName =
| 'opentelemetry/php'
| 'opentelemetry/python'
| 'opentelemetry/ruby'
| 'opentelemetry/swift'
| 'opentelemetry/webjs';

/*
Expand Down
Loading

0 comments on commit 4aca0b7

Please sign in to comment.