diff --git a/x-pack/plugins/apm/common/environment_filter_values.ts b/x-pack/plugins/apm/common/environment_filter_values.ts
index e231f37a170ed..8f5b6456b8c92 100644
--- a/x-pack/plugins/apm/common/environment_filter_values.ts
+++ b/x-pack/plugins/apm/common/environment_filter_values.ts
@@ -33,3 +33,27 @@ export const ENVIRONMENT_NOT_DEFINED = {
export function getEnvironmentLabel(environment: string) {
return environmentLabels[environment] || environment;
}
+
+// returns the environment url param that should be used
+// based on the requested environment. If the requested
+// environment is different from the URL parameter, we'll
+// return ENVIRONMENT_ALL. If it's not, we'll just return
+// the current environment URL param
+export function getNextEnvironmentUrlParam({
+ requestedEnvironment,
+ currentEnvironmentUrlParam,
+}: {
+ requestedEnvironment?: string;
+ currentEnvironmentUrlParam?: string;
+}) {
+ const normalizedRequestedEnvironment =
+ requestedEnvironment || ENVIRONMENT_NOT_DEFINED.value;
+ const normalizedQueryEnvironment =
+ currentEnvironmentUrlParam || ENVIRONMENT_ALL.value;
+
+ if (normalizedRequestedEnvironment === normalizedQueryEnvironment) {
+ return currentEnvironmentUrlParam;
+ }
+
+ return ENVIRONMENT_ALL.value;
+}
diff --git a/x-pack/plugins/apm/public/components/app/TransactionDetails/WaterfallWithSummmary/MaybeViewTraceLink.tsx b/x-pack/plugins/apm/public/components/app/TransactionDetails/WaterfallWithSummmary/MaybeViewTraceLink.tsx
index 49a016f338888..fec14ccf76c93 100644
--- a/x-pack/plugins/apm/public/components/app/TransactionDetails/WaterfallWithSummmary/MaybeViewTraceLink.tsx
+++ b/x-pack/plugins/apm/public/components/app/TransactionDetails/WaterfallWithSummmary/MaybeViewTraceLink.tsx
@@ -7,6 +7,7 @@
import { EuiButton, EuiFlexItem, EuiToolTip } from '@elastic/eui';
import { i18n } from '@kbn/i18n';
import React from 'react';
+import { getNextEnvironmentUrlParam } from '../../../../../common/environment_filter_values';
import { useUrlParams } from '../../../../context/url_params_context/use_url_params';
import { Transaction as ITransaction } from '../../../../../typings/es_schemas/ui/transaction';
import { TransactionDetailLink } from '../../../shared/Links/apm/transaction_detail_link';
@@ -20,8 +21,9 @@ export const MaybeViewTraceLink = ({
waterfall: IWaterfall;
}) => {
const {
- urlParams: { latencyAggregationType },
+ urlParams: { environment, latencyAggregationType },
} = useUrlParams();
+
const viewFullTraceButtonLabel = i18n.translate(
'xpack.apm.transactionDetails.viewFullTraceButtonLabel',
{
@@ -73,6 +75,11 @@ export const MaybeViewTraceLink = ({
// the user is viewing a zoomed in version of the trace. Link to the full trace
} else {
+ const nextEnvironment = getNextEnvironmentUrlParam({
+ requestedEnvironment: rootTransaction?.service.environment,
+ currentEnvironmentUrlParam: environment,
+ });
+
return (
{viewFullTraceButtonLabel}
diff --git a/x-pack/plugins/apm/public/components/app/TransactionDetails/WaterfallWithSummmary/WaterfallContainer/Waterfall/FlyoutTopLevelProperties.tsx b/x-pack/plugins/apm/public/components/app/TransactionDetails/WaterfallWithSummmary/WaterfallContainer/Waterfall/FlyoutTopLevelProperties.tsx
index a67ec0a69ed87..6b6d54b6cbad6 100644
--- a/x-pack/plugins/apm/public/components/app/TransactionDetails/WaterfallWithSummmary/WaterfallContainer/Waterfall/FlyoutTopLevelProperties.tsx
+++ b/x-pack/plugins/apm/public/components/app/TransactionDetails/WaterfallWithSummmary/WaterfallContainer/Waterfall/FlyoutTopLevelProperties.tsx
@@ -7,6 +7,7 @@
import { i18n } from '@kbn/i18n';
import React from 'react';
import { useUrlParams } from '../../../../../../context/url_params_context/use_url_params';
+import { getNextEnvironmentUrlParam } from '../../../../../../../common/environment_filter_values';
import {
SERVICE_NAME,
TRANSACTION_NAME,
@@ -22,13 +23,18 @@ interface Props {
export function FlyoutTopLevelProperties({ transaction }: Props) {
const {
- urlParams: { latencyAggregationType },
+ urlParams: { environment, latencyAggregationType },
} = useUrlParams();
if (!transaction) {
return null;
}
+ const nextEnvironment = getNextEnvironmentUrlParam({
+ requestedEnvironment: transaction.service.environment,
+ currentEnvironmentUrlParam: environment,
+ });
+
const stickyProperties = [
{
label: i18n.translate('xpack.apm.transactionDetails.serviceLabel', {
@@ -38,6 +44,7 @@ export function FlyoutTopLevelProperties({ transaction }: Props) {
val: (
{transaction.service.name}
@@ -56,6 +63,7 @@ export function FlyoutTopLevelProperties({ transaction }: Props) {
traceId={transaction.trace.id}
transactionName={transaction.transaction.name}
transactionType={transaction.transaction.type}
+ environment={nextEnvironment}
latencyAggregationType={latencyAggregationType}
>
{transaction.transaction.name}
diff --git a/x-pack/plugins/apm/public/components/app/TransactionDetails/WaterfallWithSummmary/WaterfallContainer/Waterfall/SpanFlyout/StickySpanProperties.tsx b/x-pack/plugins/apm/public/components/app/TransactionDetails/WaterfallWithSummmary/WaterfallContainer/Waterfall/SpanFlyout/StickySpanProperties.tsx
index 5a1f6e3d2a24d..82b43b3dce99a 100644
--- a/x-pack/plugins/apm/public/components/app/TransactionDetails/WaterfallWithSummmary/WaterfallContainer/Waterfall/SpanFlyout/StickySpanProperties.tsx
+++ b/x-pack/plugins/apm/public/components/app/TransactionDetails/WaterfallWithSummmary/WaterfallContainer/Waterfall/SpanFlyout/StickySpanProperties.tsx
@@ -7,6 +7,7 @@
import { i18n } from '@kbn/i18n';
import React from 'react';
import { useUrlParams } from '../../../../../../../context/url_params_context/use_url_params';
+import { getNextEnvironmentUrlParam } from '../../../../../../../../common/environment_filter_values';
import {
SERVICE_NAME,
SPAN_NAME,
@@ -26,8 +27,14 @@ interface Props {
export function StickySpanProperties({ span, transaction }: Props) {
const {
- urlParams: { latencyAggregationType },
+ urlParams: { environment, latencyAggregationType },
} = useUrlParams();
+
+ const nextEnvironment = getNextEnvironmentUrlParam({
+ requestedEnvironment: transaction?.service.environment,
+ currentEnvironmentUrlParam: environment,
+ });
+
const spanName = span.span.name;
const transactionStickyProperties = transaction
? [
@@ -39,6 +46,7 @@ export function StickySpanProperties({ span, transaction }: Props) {
val: (
{transaction.service.name}
@@ -60,6 +68,7 @@ export function StickySpanProperties({ span, transaction }: Props) {
traceId={transaction.trace.id}
transactionName={transaction.transaction.name}
transactionType={transaction.transaction.type}
+ environment={nextEnvironment}
latencyAggregationType={latencyAggregationType}
>
{transaction.transaction.name}
diff --git a/x-pack/plugins/apm/public/components/app/service_overview/service_overview_dependencies_table/index.tsx b/x-pack/plugins/apm/public/components/app/service_overview/service_overview_dependencies_table/index.tsx
index 079c599f8f7ba..1bd7310e3251d 100644
--- a/x-pack/plugins/apm/public/components/app/service_overview/service_overview_dependencies_table/index.tsx
+++ b/x-pack/plugins/apm/public/components/app/service_overview/service_overview_dependencies_table/index.tsx
@@ -13,7 +13,10 @@ import {
} from '@elastic/eui';
import { i18n } from '@kbn/i18n';
import React from 'react';
-import { ENVIRONMENT_ALL } from '../../../../../common/environment_filter_values';
+import {
+ ENVIRONMENT_ALL,
+ getNextEnvironmentUrlParam,
+} from '../../../../../common/environment_filter_values';
import {
asMillisecondDuration,
asPercent,
@@ -40,6 +43,10 @@ interface Props {
}
export function ServiceOverviewDependenciesTable({ serviceName }: Props) {
+ const {
+ urlParams: { start, end, environment },
+ } = useUrlParams();
+
const columns: Array> = [
{
field: 'name',
@@ -64,7 +71,13 @@ export function ServiceOverviewDependenciesTable({ serviceName }: Props) {
{item.type === 'service' ? (
-
+
{item.name}
) : (
@@ -154,10 +167,6 @@ export function ServiceOverviewDependenciesTable({ serviceName }: Props) {
},
];
- const {
- urlParams: { start, end, environment },
- } = useUrlParams();
-
const { data = [], status } = useFetcher(() => {
if (!start || !end) {
return;
diff --git a/x-pack/plugins/apm/public/components/shared/Links/apm/APMLink.tsx b/x-pack/plugins/apm/public/components/shared/Links/apm/APMLink.tsx
index 7acc2542a65f3..fe5bfc6c4679b 100644
--- a/x-pack/plugins/apm/public/components/shared/Links/apm/APMLink.tsx
+++ b/x-pack/plugins/apm/public/components/shared/Links/apm/APMLink.tsx
@@ -36,16 +36,24 @@ export const PERSISTENT_APM_PARAMS: Array = [
/**
* Hook to get a link for a path with persisted filters
*/
-export function useAPMHref(
- path: string,
- persistentFilters: Array = []
-) {
+export function useAPMHref({
+ path,
+ persistedFilters,
+ query,
+}: {
+ path: string;
+ persistedFilters?: Array;
+ query?: APMQueryParams;
+}) {
const { urlParams } = useUrlParams();
const { basePath } = useApmPluginContext().core.http;
const { search } = useLocation();
- const query = pickKeys(urlParams as APMQueryParams, ...persistentFilters);
+ const nextQuery = {
+ ...pickKeys(urlParams as APMQueryParams, ...(persistedFilters ?? [])),
+ ...query,
+ };
- return getAPMHref({ basePath, path, query, search });
+ return getAPMHref({ basePath, path, query: nextQuery, search });
}
/**
diff --git a/x-pack/plugins/apm/public/components/shared/Links/apm/ErrorOverviewLink.tsx b/x-pack/plugins/apm/public/components/shared/Links/apm/ErrorOverviewLink.tsx
index dcf21de7dca8d..506787c0fe62f 100644
--- a/x-pack/plugins/apm/public/components/shared/Links/apm/ErrorOverviewLink.tsx
+++ b/x-pack/plugins/apm/public/components/shared/Links/apm/ErrorOverviewLink.tsx
@@ -17,7 +17,10 @@ const persistedFilters: Array = [
];
export function useErrorOverviewHref(serviceName: string) {
- return useAPMHref(`/services/${serviceName}/errors`, persistedFilters);
+ return useAPMHref({
+ path: `/services/${serviceName}/errors`,
+ persistedFilters,
+ });
}
interface Props extends APMLinkExtendProps {
diff --git a/x-pack/plugins/apm/public/components/shared/Links/apm/MetricOverviewLink.tsx b/x-pack/plugins/apm/public/components/shared/Links/apm/MetricOverviewLink.tsx
index 8031b6088d420..e369e920a4b82 100644
--- a/x-pack/plugins/apm/public/components/shared/Links/apm/MetricOverviewLink.tsx
+++ b/x-pack/plugins/apm/public/components/shared/Links/apm/MetricOverviewLink.tsx
@@ -16,7 +16,10 @@ const persistedFilters: Array = [
];
export function useMetricOverviewHref(serviceName: string) {
- return useAPMHref(`/services/${serviceName}/metrics`, persistedFilters);
+ return useAPMHref({
+ path: `/services/${serviceName}/metrics`,
+ persistedFilters,
+ });
}
interface Props extends APMLinkExtendProps {
diff --git a/x-pack/plugins/apm/public/components/shared/Links/apm/ServiceMapLink.tsx b/x-pack/plugins/apm/public/components/shared/Links/apm/ServiceMapLink.tsx
index 670b7137219e1..b5b74f06d65ba 100644
--- a/x-pack/plugins/apm/public/components/shared/Links/apm/ServiceMapLink.tsx
+++ b/x-pack/plugins/apm/public/components/shared/Links/apm/ServiceMapLink.tsx
@@ -8,10 +8,10 @@ import React from 'react';
import { APMLinkExtendProps, useAPMHref } from './APMLink';
export function useServiceMapHref(serviceName?: string) {
- const pathFor = serviceName
+ const path = serviceName
? `/services/${serviceName}/service-map`
: '/service-map';
- return useAPMHref(pathFor);
+ return useAPMHref({ path });
}
interface ServiceMapLinkProps extends APMLinkExtendProps {
diff --git a/x-pack/plugins/apm/public/components/shared/Links/apm/ServiceNodeOverviewLink.tsx b/x-pack/plugins/apm/public/components/shared/Links/apm/ServiceNodeOverviewLink.tsx
index 279c038d95a80..b2382ef99e982 100644
--- a/x-pack/plugins/apm/public/components/shared/Links/apm/ServiceNodeOverviewLink.tsx
+++ b/x-pack/plugins/apm/public/components/shared/Links/apm/ServiceNodeOverviewLink.tsx
@@ -14,5 +14,8 @@ const persistedFilters: Array = [
];
export function useServiceNodeOverviewHref(serviceName: string) {
- return useAPMHref(`/services/${serviceName}/nodes`, persistedFilters);
+ return useAPMHref({
+ path: `/services/${serviceName}/nodes`,
+ persistedFilters,
+ });
}
diff --git a/x-pack/plugins/apm/public/components/shared/Links/apm/TraceOverviewLink.tsx b/x-pack/plugins/apm/public/components/shared/Links/apm/TraceOverviewLink.tsx
index 3cb0009a12c94..a5f7b3f2b28e4 100644
--- a/x-pack/plugins/apm/public/components/shared/Links/apm/TraceOverviewLink.tsx
+++ b/x-pack/plugins/apm/public/components/shared/Links/apm/TraceOverviewLink.tsx
@@ -20,5 +20,5 @@ const persistedFilters: Array = [
];
export function useTraceOverviewHref() {
- return useAPMHref('/traces', persistedFilters);
+ return useAPMHref({ path: '/traces', persistedFilters });
}
diff --git a/x-pack/plugins/apm/public/components/shared/Links/apm/service_inventory_link.tsx b/x-pack/plugins/apm/public/components/shared/Links/apm/service_inventory_link.tsx
index c3b80cbeb701b..1d879f86dff3d 100644
--- a/x-pack/plugins/apm/public/components/shared/Links/apm/service_inventory_link.tsx
+++ b/x-pack/plugins/apm/public/components/shared/Links/apm/service_inventory_link.tsx
@@ -15,5 +15,5 @@ import { useAPMHref } from './APMLink';
const persistedFilters: Array = ['host', 'agentName'];
export function useServiceInventoryHref() {
- return useAPMHref('/services', persistedFilters);
+ return useAPMHref({ path: '/services', persistedFilters });
}
diff --git a/x-pack/plugins/apm/public/components/shared/Links/apm/service_overview_link.tsx b/x-pack/plugins/apm/public/components/shared/Links/apm/service_overview_link.tsx
index ba53243a6bc75..31ce04cf23fbc 100644
--- a/x-pack/plugins/apm/public/components/shared/Links/apm/service_overview_link.tsx
+++ b/x-pack/plugins/apm/public/components/shared/Links/apm/service_overview_link.tsx
@@ -15,20 +15,34 @@ import { APMLinkExtendProps, useAPMHref } from './APMLink';
interface ServiceOverviewLinkProps extends APMLinkExtendProps {
serviceName: string;
+ environment?: string;
}
const persistedFilters: Array = [
'latencyAggregationType',
];
-export function useServiceOverviewHref(serviceName: string) {
- return useAPMHref(`/services/${serviceName}/overview`, persistedFilters);
+export function useServiceOverviewHref(
+ serviceName: string,
+ environment?: string
+) {
+ const query = environment
+ ? {
+ environment,
+ }
+ : {};
+ return useAPMHref({
+ path: `/services/${serviceName}/overview`,
+ persistedFilters,
+ query,
+ });
}
export function ServiceOverviewLink({
serviceName,
+ environment,
...rest
}: ServiceOverviewLinkProps) {
- const href = useServiceOverviewHref(serviceName);
+ const href = useServiceOverviewHref(serviceName, environment);
return ;
}
diff --git a/x-pack/plugins/apm/public/components/shared/Links/apm/service_transactions_overview_link.tsx b/x-pack/plugins/apm/public/components/shared/Links/apm/service_transactions_overview_link.tsx
index 8b96ba8ab233a..c4ea99030d87c 100644
--- a/x-pack/plugins/apm/public/components/shared/Links/apm/service_transactions_overview_link.tsx
+++ b/x-pack/plugins/apm/public/components/shared/Links/apm/service_transactions_overview_link.tsx
@@ -17,18 +17,28 @@ const persistedFilters: Array = [
'latencyAggregationType',
];
-export function useServiceOrTransactionsOverviewHref(serviceName: string) {
- return useAPMHref(`/services/${serviceName}`, persistedFilters);
+export function useServiceOrTransactionsOverviewHref(
+ serviceName: string,
+ environment?: string
+) {
+ const query = environment ? { environment } : {};
+ return useAPMHref({
+ path: `/services/${serviceName}`,
+ persistedFilters,
+ query,
+ });
}
interface Props extends APMLinkExtendProps {
serviceName: string;
+ environment?: string;
}
export function ServiceOrTransactionsOverviewLink({
serviceName,
+ environment,
...rest
}: Props) {
- const href = useServiceOrTransactionsOverviewHref(serviceName);
+ const href = useServiceOrTransactionsOverviewHref(serviceName, environment);
return ;
}
diff --git a/x-pack/plugins/apm/public/components/shared/Links/apm/transaction_detail_link.tsx b/x-pack/plugins/apm/public/components/shared/Links/apm/transaction_detail_link.tsx
index 8108dcf41321f..a97d860d99798 100644
--- a/x-pack/plugins/apm/public/components/shared/Links/apm/transaction_detail_link.tsx
+++ b/x-pack/plugins/apm/public/components/shared/Links/apm/transaction_detail_link.tsx
@@ -7,6 +7,7 @@
import React from 'react';
import { useLocation } from 'react-router-dom';
import { EuiLink } from '@elastic/eui';
+import { pickBy, identity } from 'lodash';
import { getAPMHref, APMLinkExtendProps } from './APMLink';
import { useUrlParams } from '../../../../context/url_params_context/use_url_params';
import { pickKeys } from '../../../../../common/utils/pick_keys';
@@ -20,6 +21,7 @@ interface Props extends APMLinkExtendProps {
transactionName: string;
transactionType: string;
latencyAggregationType?: string;
+ environment?: string;
}
const persistedFilters: Array = [
@@ -34,6 +36,7 @@ export function TransactionDetailLink({
transactionName,
transactionType,
latencyAggregationType,
+ environment,
...rest
}: Props) {
const { urlParams } = useUrlParams();
@@ -47,8 +50,8 @@ export function TransactionDetailLink({
transactionId,
transactionName,
transactionType,
- ...(latencyAggregationType ? { latencyAggregationType } : {}),
...pickKeys(urlParams as APMQueryParams, ...persistedFilters),
+ ...pickBy({ latencyAggregationType, environment }, identity),
},
search: location.search,
});
diff --git a/x-pack/plugins/apm/typings/es_schemas/raw/span_raw.ts b/x-pack/plugins/apm/typings/es_schemas/raw/span_raw.ts
index e152ed23af1b3..3938a9b54d913 100644
--- a/x-pack/plugins/apm/typings/es_schemas/raw/span_raw.ts
+++ b/x-pack/plugins/apm/typings/es_schemas/raw/span_raw.ts
@@ -18,6 +18,7 @@ export interface SpanRaw extends APMBaseDoc {
trace: { id: string }; // trace is required
service: {
name: string;
+ environment?: string;
};
span: {
destination?: {