diff --git a/static/app/components/performance/spanSearchQueryBuilder.tsx b/static/app/components/performance/spanSearchQueryBuilder.tsx
index 81a03d59cde08e..9f52fa8bd30c4c 100644
--- a/static/app/components/performance/spanSearchQueryBuilder.tsx
+++ b/static/app/components/performance/spanSearchQueryBuilder.tsx
@@ -190,7 +190,7 @@ function IndexedSpanSearchQueryBuilder({
return ;
}
-function EapSpanSearchQueryBuilderWrapper(props: SpanSearchQueryBuilderProps) {
+export function EapSpanSearchQueryBuilderWrapper(props: SpanSearchQueryBuilderProps) {
const {tags: numberTags} = useTraceItemTags('number');
const {tags: stringTags} = useTraceItemTags('string');
diff --git a/static/app/views/insights/cache/components/charts/transactionDurationChartWithSamples.tsx b/static/app/views/insights/cache/components/charts/transactionDurationChartWithSamples.tsx
index d4bc0b3c1e73ad..1d65ccc2b8ca4d 100644
--- a/static/app/views/insights/cache/components/charts/transactionDurationChartWithSamples.tsx
+++ b/static/app/views/insights/cache/components/charts/transactionDurationChartWithSamples.tsx
@@ -7,14 +7,9 @@ import {Referrer} from 'sentry/views/insights/cache/referrers';
// TODO(release-drawer): Only used in cache/components/samplePanel
// eslint-disable-next-line no-restricted-imports
import {InsightsLineChartWidget} from 'sentry/views/insights/common/components/insightsLineChartWidget';
-import type {DiscoverSeries} from 'sentry/views/insights/common/queries/useDiscoverSeries';
-import {
- useEAPSeries,
- useMetricsSeries,
-} from 'sentry/views/insights/common/queries/useDiscoverSeries';
-import {useInsightsEap} from 'sentry/views/insights/common/utils/useEap';
-import type {SearchHook, SpanQueryFilters} from 'sentry/views/insights/types';
-import {MetricsFields, SpanFields} from 'sentry/views/insights/types';
+import {useEAPSeries} from 'sentry/views/insights/common/queries/useDiscoverSeries';
+import type {SpanQueryFilters} from 'sentry/views/insights/types';
+import {SpanFields} from 'sentry/views/insights/types';
type Props = {
samples: Samples;
@@ -28,10 +23,19 @@ export function TransactionDurationChartWithSamples({samples}: Props) {
},
});
- const {search} = useTransactionDurationSearch({transaction});
+ const search = MutableSearch.fromQueryObject({
+ transaction,
+ is_transaction: 'true',
+ } satisfies SpanQueryFilters);
const referrer = Referrer.SAMPLES_CACHE_TRANSACTION_DURATION_CHART;
- const {data, isPending, error} = useTransactionDurationSeries({search});
+ const {data, isPending, error} = useEAPSeries(
+ {
+ search,
+ yAxis: [`avg(${SpanFields.SPAN_DURATION})`],
+ },
+ Referrer.SAMPLES_CACHE_TRANSACTION_DURATION
+ );
return (
);
}
-
-const useTransactionDurationSearch = ({
- transaction,
-}: {
- transaction: string;
-}): SearchHook => {
- const useEap = useInsightsEap();
- const search = useEap
- ? MutableSearch.fromQueryObject({
- transaction,
- is_transaction: 'true',
- } satisfies SpanQueryFilters)
- : MutableSearch.fromQueryObject({transaction} satisfies SpanQueryFilters);
-
- return {search};
-};
-
-const useTransactionDurationSeries = ({search}: {search: MutableSearch}) => {
- const useEap = useInsightsEap();
-
- const metricsResult = useMetricsSeries(
- {
- yAxis: [`avg(${MetricsFields.TRANSACTION_DURATION})`],
- search,
- transformAliasToInputFormat: true,
- enabled: !useEap,
- },
- Referrer.SAMPLES_CACHE_TRANSACTION_DURATION_CHART
- );
-
- const eapResult = useEAPSeries(
- {
- search,
- yAxis: [`avg(${SpanFields.SPAN_DURATION})`],
- enabled: useEap,
- },
- Referrer.SAMPLES_CACHE_TRANSACTION_DURATION
- );
-
- const result = useEap ? eapResult : metricsResult;
- const finalData: {['avg(span.duration)']: DiscoverSeries} = useEap
- ? eapResult.data
- : {
- [`avg(${SpanFields.SPAN_DURATION})`]:
- metricsResult.data['avg(transaction.duration)'],
- };
-
- return {...result, data: finalData};
-};
diff --git a/static/app/views/insights/cache/components/samplePanel.tsx b/static/app/views/insights/cache/components/samplePanel.tsx
index de58f8775281a6..7352a17885654a 100644
--- a/static/app/views/insights/cache/components/samplePanel.tsx
+++ b/static/app/views/insights/cache/components/samplePanel.tsx
@@ -4,7 +4,7 @@ import keyBy from 'lodash/keyBy';
import {Button} from 'sentry/components/core/button';
import {CompactSelect} from 'sentry/components/core/compactSelect';
import {EventDrawerHeader} from 'sentry/components/events/eventDrawer';
-import {SpanSearchQueryBuilder} from 'sentry/components/performance/spanSearchQueryBuilder';
+import {EapSpanSearchQueryBuilderWrapper} from 'sentry/components/performance/spanSearchQueryBuilder';
import {t} from 'sentry/locale';
import {trackAnalytics} from 'sentry/utils/analytics';
import {DurationUnit, RateUnit, SizeUnit} from 'sentry/utils/discover/fields';
@@ -32,18 +32,15 @@ import {SampleDrawerHeaderTransaction} from 'sentry/views/insights/common/compon
import {
useDiscoverOrEap,
useEAPSpans,
- useMetrics,
useSpanMetrics,
useSpansIndexed,
} from 'sentry/views/insights/common/queries/useDiscover';
-import {useInsightsEap} from 'sentry/views/insights/common/utils/useEap';
import {
DataTitles,
getThroughputTitle,
} from 'sentry/views/insights/common/views/spans/types';
import {InsightsSpanTagProvider} from 'sentry/views/insights/pages/insightsSpanTagProvider';
import type {
- MetricsQueryFilters,
SpanIndexedQueryFilters,
SpanIndexedResponse,
SpanMetricsQueryFilters,
@@ -64,7 +61,6 @@ export function CacheSamplePanel() {
const location = useLocation();
const organization = useOrganization();
const {selection} = usePageFilters();
- const useEap = useInsightsEap();
const query = useLocationQuery({
fields: {
@@ -119,7 +115,16 @@ export function CacheSamplePanel() {
);
const {data: transactionDurationData, isPending: isTransactionDurationLoading} =
- useTransactionDuration({transaction: query.transaction});
+ useEAPSpans(
+ {
+ search: MutableSearch.fromQueryObject({
+ transaction: query.transaction,
+ is_transaction: 'true',
+ } satisfies SpanQueryFilters),
+ fields: [`avg(${SpanFields.SPAN_DURATION})`],
+ },
+ Referrer.SAMPLES_CACHE_TRANSACTION_DURATION
+ );
const sampleFilters: SpanIndexedQueryFilters = {
...BASE_FILTERS,
@@ -127,10 +132,6 @@ export function CacheSamplePanel() {
project_id: query.project,
};
- const transactionIdField = useEap
- ? SpanIndexedField.TRANSACTION_SPAN_ID
- : SpanIndexedField.TRANSACTION_ID;
-
const useIndexedCacheSpans = (
isCacheHit: SpanIndexedResponse['cache.hit'],
limit: number
@@ -153,7 +154,6 @@ export function CacheSamplePanel() {
SpanIndexedField.SPAN_OP,
SpanIndexedField.CACHE_ITEM_SIZE,
SpanIndexedField.TRACE,
- ...(useEap ? [] : ([SpanIndexedField.TRANSACTION_ID] as const)),
],
sorts: [SPAN_SAMPLES_SORT],
limit,
@@ -189,11 +189,10 @@ export function CacheSamplePanel() {
return [...(cacheHitSamples || []), ...(cacheMissSamples || [])];
}, [cacheHitSamples, cacheMissSamples]);
- const transactionIds = cacheSamples?.map(span => span[transactionIdField]) || [];
+ const transactionIds =
+ cacheSamples?.map(span => span[SpanIndexedField.TRANSACTION_SPAN_ID]) || [];
const traceIds = cacheSamples?.map(span => span.trace) || [];
- const transactionDurationSearch = useEap
- ? `${SpanIndexedField.TRANSACTION_SPAN_ID}:[${transactionIds.join(',')}] trace:[${traceIds.join(',')}] is_transaction:true`
- : `id:[${transactionIds.join(',')}]`;
+ const transactionDurationSearch = `${SpanIndexedField.TRANSACTION_SPAN_ID}:[${transactionIds.join(',')}] trace:[${traceIds.join(',')}] is_transaction:true`;
const {
data: transactionData,
@@ -213,9 +212,11 @@ export function CacheSamplePanel() {
return cacheSamples.map(span => ({
...span,
'transaction.duration':
- transactionDurationsMap[span[transactionIdField]]?.['span.duration']!,
+ transactionDurationsMap[span[SpanIndexedField.TRANSACTION_SPAN_ID]]?.[
+ 'span.duration'
+ ]!,
}));
- }, [cacheSamples, transactionData, transactionIdField]);
+ }, [cacheSamples, transactionData]);
const spanSamplesById = useMemo(() => {
return keyBy(spansWithDuration, 'id');
@@ -356,13 +357,12 @@ export function CacheSamplePanel() {
-
@@ -432,38 +432,3 @@ const CACHE_STATUS_OPTIONS = [
label: t('Miss'),
},
];
-
-const useTransactionDuration = ({transaction}: {transaction: string}) => {
- const useEap = useInsightsEap();
-
- const metricsResult = useMetrics(
- {
- enabled: !useEap && Boolean(transaction),
- search: MutableSearch.fromQueryObject({
- transaction,
- } satisfies MetricsQueryFilters),
- fields: [`avg(${MetricsFields.TRANSACTION_DURATION})`],
- },
- Referrer.SAMPLES_CACHE_TRANSACTION_DURATION
- );
-
- const eapResult = useEAPSpans(
- {
- search: MutableSearch.fromQueryObject({
- transaction,
- is_transaction: 'true',
- } satisfies SpanQueryFilters),
- fields: [`avg(${SpanFields.SPAN_DURATION})`],
- },
- Referrer.SAMPLES_CACHE_TRANSACTION_DURATION
- );
-
- const result = useEap ? eapResult : metricsResult;
- const finalData: Array<{[`avg(span.duration)`]: number}> = useEap
- ? eapResult.data
- : metricsResult.data.map(row => ({
- 'avg(span.duration)': row[`avg(${MetricsFields.TRANSACTION_DURATION})`],
- }));
-
- return {...result, data: finalData};
-};
diff --git a/static/app/views/insights/cache/views/cacheLandingPage.spec.tsx b/static/app/views/insights/cache/views/cacheLandingPage.spec.tsx
index 887c8434c26036..3a2972cad2b179 100644
--- a/static/app/views/insights/cache/views/cacheLandingPage.spec.tsx
+++ b/static/app/views/insights/cache/views/cacheLandingPage.spec.tsx
@@ -146,11 +146,11 @@ describe('CacheLandingPage', function () {
query: {
dataset: 'metrics',
environment: [],
- field: ['avg(transaction.duration)', 'transaction'],
+ field: ['avg(span.duration)', 'transaction'],
per_page: 50,
noPagination: true,
project: [],
- query: 'transaction:["my-transaction"]',
+ query: 'transaction:["my-transaction"] AND is_transaction:true',
referrer: 'api.performance.cache.landing-cache-transaction-duration',
statsPeriod: '10d',
},
@@ -206,11 +206,11 @@ describe('CacheLandingPage', function () {
query: {
dataset: 'metrics',
environment: [],
- field: ['avg(transaction.duration)', 'transaction'],
+ field: ['avg(span.duration)', 'transaction'],
noPagination: true,
per_page: 50,
project: [],
- query: 'transaction:["transaction with \\"quote\\""]',
+ query: 'transaction:["transaction with \\"quote\\""] AND is_transaction:true',
referrer: 'api.performance.cache.landing-cache-transaction-duration',
statsPeriod: '10d',
},
@@ -407,13 +407,13 @@ const setRequestMocks = (organization: Organization) => {
data: [
{
transaction: 'my-transaction',
- 'avg(transaction.duration)': 456,
+ 'avg(span.duration)': 456,
},
],
meta: {
fields: {
transaction: 'string',
- 'avg(transaction.duration)': 'duration',
+ 'avg(span.duration)': 'duration',
},
units: {},
},
diff --git a/static/app/views/insights/cache/views/cacheLandingPage.tsx b/static/app/views/insights/cache/views/cacheLandingPage.tsx
index 3f443b6aec03f1..9d4da021f0e0c8 100644
--- a/static/app/views/insights/cache/views/cacheLandingPage.tsx
+++ b/static/app/views/insights/cache/views/cacheLandingPage.tsx
@@ -36,16 +36,10 @@ import {useSpanMetricsSeries} from 'sentry/views/insights/common/queries/useDisc
import {useHasFirstSpan} from 'sentry/views/insights/common/queries/useHasFirstSpan';
import {useOnboardingProject} from 'sentry/views/insights/common/queries/useOnboardingProject';
import {combineMeta} from 'sentry/views/insights/common/utils/combineMeta';
-import {useInsightsEap} from 'sentry/views/insights/common/utils/useEap';
import {useSamplesDrawer} from 'sentry/views/insights/common/utils/useSamplesDrawer';
import {QueryParameterNames} from 'sentry/views/insights/common/views/queryParameters';
import {BackendHeader} from 'sentry/views/insights/pages/backend/backendPageHeader';
-import {
- type MetricsProperty,
- ModuleName,
- SpanFunction,
- SpanMetricsField,
-} from 'sentry/views/insights/types';
+import {ModuleName, SpanFunction, SpanMetricsField} from 'sentry/views/insights/types';
const {CACHE_MISS_RATE} = SpanFunction;
const {CACHE_ITEM_SIZE} = SpanMetricsField;
@@ -66,7 +60,6 @@ const CACHE_ERROR_MESSAGE = 'Column cache.hit was not found in metrics indexer';
export function CacheLandingPage() {
const location = useLocation();
const {setPageInfo, pageAlert} = usePageAlert();
- const useEap = useInsightsEap();
const sortField = decodeScalar(location.query?.[QueryParameterNames.TRANSACTIONS_SORT]);
@@ -113,13 +106,7 @@ export function CacheLandingPage() {
Referrer.LANDING_CACHE_TRANSACTION_LIST
);
- const search = useEap
- ? `transaction:[${transactionsList.map(({transaction}) => `"${transaction.replaceAll('"', '\\"')}"`).join(',')}] AND is_transaction:true`
- : `transaction:[${transactionsList.map(({transaction}) => `"${transaction.replaceAll('"', '\\"')}"`).join(',')}]`;
-
- const fields: MetricsProperty[] = useEap
- ? ['avg(span.duration)', 'transaction']
- : [`avg(transaction.duration)`, 'transaction'];
+ const search = `transaction:[${transactionsList.map(({transaction}) => `"${transaction.replaceAll('"', '\\"')}"`).join(',')}] AND is_transaction:true`;
const {
data: transactionDurationData,
@@ -129,7 +116,7 @@ export function CacheLandingPage() {
} = useMetrics(
{
search,
- fields,
+ fields: ['avg(span.duration)', 'transaction'],
enabled: !isTransactionsListFetching && transactionsList.length > 0,
noPagination: true,
},
@@ -168,11 +155,8 @@ export function CacheLandingPage() {
const transactionsListWithDuration =
transactionsList?.map(transaction => ({
...transaction,
- 'avg(span.duration)': useEap
- ? transactionDurationsMap[transaction.transaction]?.['avg(span.duration)']!
- : transactionDurationsMap[transaction.transaction]?.[
- 'avg(transaction.duration)'
- ]!,
+ 'avg(span.duration)':
+ transactionDurationsMap[transaction.transaction]?.['avg(span.duration)']!,
})) || [];
const meta = combineMeta(transactionsListMeta, transactionDurationMeta);
diff --git a/static/app/views/insights/common/components/fullSpanDescription.spec.tsx b/static/app/views/insights/common/components/fullSpanDescription.spec.tsx
index e74122a51d27f3..8d2f989a8c77af 100644
--- a/static/app/views/insights/common/components/fullSpanDescription.spec.tsx
+++ b/static/app/views/insights/common/components/fullSpanDescription.spec.tsx
@@ -4,7 +4,6 @@ import {ProjectFixture} from 'sentry-fixture/project';
import {render, screen, waitForElementToBeRemoved} from 'sentry-test/reactTestingLibrary';
-import {EntryType} from 'sentry/types/event';
import usePageFilters from 'sentry/utils/usePageFilters';
import {FullSpanDescription} from 'sentry/views/insights/common/components/fullSpanDescription';
import {ModuleName} from 'sentry/views/insights/types';
@@ -24,7 +23,6 @@ describe('FullSpanDescription', function () {
const groupId = '2ed2abf6ce7e3577';
const spanId = 'abfed2aabf';
- const eventId = '65c7d8647b8a76ef8f4c05d41deb7860';
it('uses the correct code formatting for SQL queries', async function () {
MockApiClient.addMockResponse({
@@ -32,27 +30,9 @@ describe('FullSpanDescription', function () {
body: {
data: [
{
- 'transaction.id': eventId,
project: project.slug,
span_id: spanId,
- },
- ],
- },
- });
-
- MockApiClient.addMockResponse({
- url: `/organizations/${organization.slug}/events/${project.slug}:${eventId}/`,
- body: {
- id: eventId,
- entries: [
- {
- type: EntryType.SPANS,
- data: [
- {
- span_id: spanId,
- description: 'SELECT users FROM my_table LIMIT 1;',
- },
- ],
+ 'span.description': 'SELECT users FROM my_table LIMIT 1;',
},
],
},
@@ -82,28 +62,10 @@ describe('FullSpanDescription', function () {
body: {
data: [
{
- 'transaction.id': eventId,
project: project.slug,
span_id: spanId,
- },
- ],
- },
- });
-
- MockApiClient.addMockResponse({
- url: `/organizations/${organization.slug}/events/${project.slug}:${eventId}/`,
- body: {
- id: eventId,
- entries: [
- {
- type: EntryType.SPANS,
- data: [
- {
- span_id: spanId,
- description: `{"insert": "my_cool_collection😎", "a": {}}`,
- data: {'db.system': 'mongodb'},
- },
- ],
+ 'span.description': `{"insert": "my_cool_collection😎", "a": {}}`,
+ 'db.system': 'mongodb',
},
],
},
@@ -128,28 +90,10 @@ describe('FullSpanDescription', function () {
body: {
data: [
{
- 'transaction.id': eventId,
project: project.slug,
span_id: spanId,
- },
- ],
- },
- });
-
- MockApiClient.addMockResponse({
- url: `/organizations/${organization.slug}/events/${project.slug}:${eventId}/`,
- body: {
- id: eventId,
- entries: [
- {
- type: EntryType.SPANS,
- data: [
- {
- span_id: spanId,
- description: `{"insert": "my_cool_collection😎", "a": {}, "uh_oh":"the_query_is_truncated", "ohno*`,
- data: {'db.system': 'mongodb'},
- },
- ],
+ 'span.description': `{"insert": "my_cool_collection😎", "a": {}, "uh_oh":"the_query_is_truncated", "ohno*`,
+ 'db.system': 'mongodb',
},
],
},
diff --git a/static/app/views/insights/common/components/fullSpanDescription.tsx b/static/app/views/insights/common/components/fullSpanDescription.tsx
index 2754d64f53a623..7b67eb4b21e6ce 100644
--- a/static/app/views/insights/common/components/fullSpanDescription.tsx
+++ b/static/app/views/insights/common/components/fullSpanDescription.tsx
@@ -12,18 +12,12 @@ import {MutableSearch} from 'sentry/utils/tokenizeSearch';
import {useLocation} from 'sentry/utils/useLocation';
import {useNavigate} from 'sentry/utils/useNavigate';
import {useSpansIndexed} from 'sentry/views/insights/common/queries/useDiscover';
-import {useFullSpanFromTrace} from 'sentry/views/insights/common/queries/useFullSpanFromTrace';
import {useModuleURL} from 'sentry/views/insights/common/utils/useModuleURL';
import {prettyPrintJsonString} from 'sentry/views/insights/database/utils/jsonUtils';
import {ModuleName, SpanIndexedField} from 'sentry/views/insights/types';
const formatter = new SQLishFormatter();
-const INDEXED_SPAN_SORT = {
- field: 'span.self_time',
- kind: 'desc' as const,
-};
-
interface Props {
moduleName: ModuleName;
filters?: Record;
@@ -39,30 +33,24 @@ export function FullSpanDescription({
}: Props) {
const {data: indexedSpans, isFetching: areIndexedSpansLoading} = useSpansIndexed(
{
- search: MutableSearch.fromQueryObject({'span.group': group}),
+ search: MutableSearch.fromQueryObject({'span.group': group, ...filters}),
limit: 1,
fields: [
SpanIndexedField.PROJECT_ID,
SpanIndexedField.TRANSACTION_ID,
SpanIndexedField.SPAN_DESCRIPTION,
+ SpanIndexedField.DB_SYSTEM,
],
},
'api.starfish.span-description'
);
- const indexedSpan = indexedSpans?.[0];
- // This is used as backup in case we don't have the necessary data available in the indexed span
- const {
- data: fullSpan,
- isLoading,
- isFetching,
- } = useFullSpanFromTrace(group, [INDEXED_SPAN_SORT], Boolean(indexedSpan), filters);
+ const indexedSpan = indexedSpans?.[0];
- const description =
- indexedSpan?.['span.description'] ?? fullSpan?.description ?? shortDescription;
- const system = fullSpan?.data?.['db.system'];
+ const description = indexedSpan?.['span.description'] ?? shortDescription;
+ const system = indexedSpan?.['db.system'];
- if (areIndexedSpansLoading || (isLoading && isFetching)) {
+ if (areIndexedSpansLoading) {
return (
@@ -83,10 +71,8 @@ export function FullSpanDescription({
result = prettyPrintJsonString(indexedSpan?.['span.description']);
} else if (description) {
result = prettyPrintJsonString(description);
- } else if (fullSpan?.sentry_tags?.description) {
- result = prettyPrintJsonString(fullSpan?.sentry_tags.description);
} else {
- stringifiedQuery = description || fullSpan?.sentry_tags?.description || 'N/A';
+ stringifiedQuery = description || 'N/A';
}
if (result) {
diff --git a/static/app/views/insights/common/components/spanDescription.spec.tsx b/static/app/views/insights/common/components/spanDescription.spec.tsx
index 9d3d034250b806..8f839929757b8e 100644
--- a/static/app/views/insights/common/components/spanDescription.spec.tsx
+++ b/static/app/views/insights/common/components/spanDescription.spec.tsx
@@ -5,7 +5,6 @@ import {ProjectFixture} from 'sentry-fixture/project';
import {render, screen, waitForElementToBeRemoved} from 'sentry-test/reactTestingLibrary';
import {textWithMarkupMatcher} from 'sentry-test/utils';
-import {EntryType} from 'sentry/types/event';
import usePageFilters from 'sentry/utils/usePageFilters';
import {DatabaseSpanDescription} from 'sentry/views/insights/common/components/spanDescription';
@@ -45,7 +44,7 @@ describe('DatabaseSpanDescription', function () {
expect(screen.getByText('SELECT USERS FRO*')).toBeInTheDocument();
});
- it('shows full query if full event is available', async function () {
+ it('shows full query from indexed span', async function () {
MockApiClient.addMockResponse({
url: `/organizations/${organization.slug}/events/`,
body: {
@@ -54,24 +53,7 @@ describe('DatabaseSpanDescription', function () {
'transaction.id': eventId,
project: project.slug,
span_id: spanId,
- },
- ],
- },
- });
-
- MockApiClient.addMockResponse({
- url: `/organizations/${organization.slug}/events/${project.slug}:${eventId}/`,
- body: {
- id: eventId,
- entries: [
- {
- type: EntryType.SPANS,
- data: [
- {
- span_id: spanId,
- description: 'SELECT users FROM my_table LIMIT 1;',
- },
- ],
+ 'span.description': 'SELECT users FROM my_table LIMIT 1;',
},
],
},
@@ -101,28 +83,9 @@ describe('DatabaseSpanDescription', function () {
'transaction.id': eventId,
project: project.slug,
span_id: spanId,
- },
- ],
- },
- });
-
- MockApiClient.addMockResponse({
- url: `/organizations/${organization.slug}/events/${project.slug}:${eventId}/`,
- body: {
- id: eventId,
- entries: [
- {
- type: EntryType.SPANS,
- data: [
- {
- span_id: spanId,
- description: 'SELECT users FROM my_table LIMIT 1;',
- data: {
- 'code.filepath': '/app/views/users.py',
- 'code.lineno': 78,
- },
- },
- ],
+ 'code.filepath': '/app/views/users.py',
+ 'code.lineno': 78,
+ 'span.description': 'SELECT users FROM my_table LIMIT 1;',
},
],
},
@@ -147,37 +110,18 @@ describe('DatabaseSpanDescription', function () {
});
it('correctly formats and displays MongoDB queries', async function () {
+ const sampleMongoDBQuery = `{"a": "?", "insert": "documents"}`;
+
MockApiClient.addMockResponse({
url: `/organizations/${organization.slug}/events/`,
body: {
data: [
{
- 'transaction.id': eventId,
+ 'transaction.span_id': eventId,
project: project.slug,
span_id: spanId,
- },
- ],
- },
- });
-
- const sampleMongoDBQuery = `{"a": "?", "insert": "documents"}`;
-
- MockApiClient.addMockResponse({
- url: `/organizations/${organization.slug}/events/${project.slug}:${eventId}/`,
- body: {
- id: eventId,
- entries: [
- {
- type: EntryType.SPANS,
- data: [
- {
- span_id: spanId,
- description: sampleMongoDBQuery,
- data: {
- 'db.system': 'mongodb',
- },
- },
- ],
+ 'span.description': sampleMongoDBQuery,
+ 'db.system': 'mongodb',
},
],
},
diff --git a/static/app/views/insights/common/components/spanDescription.tsx b/static/app/views/insights/common/components/spanDescription.tsx
index b0a70a4af51a30..609e3d04e63ba5 100644
--- a/static/app/views/insights/common/components/spanDescription.tsx
+++ b/static/app/views/insights/common/components/spanDescription.tsx
@@ -13,9 +13,6 @@ import useOrganization from 'sentry/utils/useOrganization';
import useProjects from 'sentry/utils/useProjects';
import {useRelease} from 'sentry/utils/useRelease';
import {useSpansIndexed} from 'sentry/views/insights/common/queries/useDiscover';
-import {useEventDetails} from 'sentry/views/insights/common/queries/useEventDetails';
-import {useFullSpanFromTrace} from 'sentry/views/insights/common/queries/useFullSpanFromTrace';
-import {useInsightsEap} from 'sentry/views/insights/common/utils/useEap';
import {
MissingFrame,
StackTraceMiniFrame,
@@ -52,7 +49,6 @@ export function DatabaseSpanDescription({
}: Omit) {
const navigate = useNavigate();
const location = useLocation();
- const useEap = useInsightsEap();
const {projects} = useProjects();
const organization = useOrganization();
@@ -62,7 +58,6 @@ export function DatabaseSpanDescription({
limit: 1,
fields: [
SpanIndexedField.PROJECT_ID,
- SpanIndexedField.TRANSACTION_ID, // TODO: remove this with `useInsightsEap`, it's only needed to get the full event when eap is off
SpanIndexedField.SPAN_DESCRIPTION,
SpanIndexedField.DB_SYSTEM,
SpanIndexedField.CODE_FILEPATH,
@@ -81,16 +76,11 @@ export function DatabaseSpanDescription({
const project = projects.find(p => p.id === indexedSpan?.project_id?.toString());
- const {data: eventDetailsData} = useEventDetails({
- eventId: indexedSpan?.['transaction.id'],
- projectSlug: project?.slug,
- });
-
const {data: release} = useRelease({
orgSlug: organization.slug,
projectSlug: project?.slug ?? '',
releaseVersion: indexedSpan?.release ?? '',
- enabled: useEap,
+ enabled: indexedSpan?.release !== undefined,
});
const sdk =
@@ -101,20 +91,11 @@ export function DatabaseSpanDescription({
}
: undefined;
- const event = useEap
- ? {
- platform: indexedSpan?.platform,
- release,
- sdk,
- }
- : eventDetailsData;
-
- // NOTE: We only need this for `span.data`! If this info existed in indexed spans, we could skip it
- const {data: rawSpan, isFetching: isRawSpanLoading} = useFullSpanFromTrace(
- groupId,
- [INDEXED_SPAN_SORT],
- Boolean(indexedSpan) && !useEap
- );
+ const event = {
+ platform: indexedSpan?.platform,
+ release,
+ sdk,
+ };
// isExpanded is a query param that is meant to be accessed only when clicking on the
// "View full query" button from the hover tooltip. It is removed from the query params
@@ -130,39 +111,24 @@ export function DatabaseSpanDescription({
// eslint-disable-next-line react-hooks/exhaustive-deps
}, [navigate]);
- const system = useEap ? indexedSpan?.['db.system'] : rawSpan?.data?.['db.system'];
- const codeFilepath = useEap
- ? indexedSpan?.['code.filepath']
- : rawSpan?.data?.['code.filepath'];
- const codeLineno = useEap
- ? indexedSpan?.['code.lineno']
- : rawSpan?.data?.['code.lineno'];
- const codeFunction = useEap
- ? indexedSpan?.['code.function']
- : rawSpan?.data?.['code.function'];
+ const system = indexedSpan?.['db.system'];
+ const codeFilepath = indexedSpan?.['code.filepath'];
+ const codeLineno = indexedSpan?.['code.lineno'];
+ const codeFunction = indexedSpan?.['code.function'];
const formattedDescription = useMemo(() => {
- const description = useEap ? indexedSpan?.['span.description'] : rawSpan?.description;
- const rawDescription =
- description || indexedSpan?.['span.description'] || preliminaryDescription;
+ const rawDescription = indexedSpan?.['span.description'] || preliminaryDescription;
if (system === SupportedDatabaseSystem.MONGODB) {
let bestDescription = '';
- if (
- rawSpan?.sentry_tags?.description &&
- isValidJson(rawSpan.sentry_tags.description)
- ) {
- bestDescription = rawSpan.sentry_tags.description;
- } else if (preliminaryDescription && isValidJson(preliminaryDescription)) {
+ if (preliminaryDescription && isValidJson(preliminaryDescription)) {
bestDescription = preliminaryDescription;
} else if (
indexedSpan?.['span.description'] &&
isValidJson(indexedSpan?.['span.description'])
) {
bestDescription = indexedSpan?.['span.description'];
- } else if (rawSpan?.description && isValidJson(rawSpan.description)) {
- bestDescription = rawSpan?.description;
} else {
return rawDescription ?? 'N/A';
}
@@ -171,11 +137,11 @@ export function DatabaseSpanDescription({
}
return formatter.toString(rawDescription ?? '');
- }, [preliminaryDescription, rawSpan, indexedSpan, system, useEap]);
+ }, [preliminaryDescription, indexedSpan, system]);
return (
- {areIndexedSpansLoading || isRawSpanLoading ? (
+ {areIndexedSpansLoading ? (
@@ -187,7 +153,7 @@ export function DatabaseSpanDescription({
)}
- {!areIndexedSpansLoading && !isRawSpanLoading && (
+ {!areIndexedSpansLoading && (
{codeFilepath ? (
;
}
-const INDEXED_SPAN_SORT = {
- field: 'span.self_time',
- kind: 'desc' as const,
-};
-
export const Frame = styled('div')`
border: solid 1px ${p => p.theme.border};
border-radius: ${p => p.theme.borderRadius};
diff --git a/static/app/views/insights/common/queries/useFullSpanFromTrace.tsx b/static/app/views/insights/common/queries/useFullSpanFromTrace.tsx
deleted file mode 100644
index c103652398fdd4..00000000000000
--- a/static/app/views/insights/common/queries/useFullSpanFromTrace.tsx
+++ /dev/null
@@ -1,68 +0,0 @@
-import type {Entry, EntrySpans} from 'sentry/types/event';
-import {EntryType} from 'sentry/types/event';
-import type {Sort} from 'sentry/utils/discover/fields';
-import {MutableSearch} from 'sentry/utils/tokenizeSearch';
-import {useSpansIndexed} from 'sentry/views/insights/common/queries/useDiscover';
-import {useEventDetails} from 'sentry/views/insights/common/queries/useEventDetails';
-import {SpanIndexedField, type SpanIndexedProperty} from 'sentry/views/insights/types';
-
-const DEFAULT_SORT: Sort[] = [{field: 'timestamp', kind: 'desc'}];
-
-// NOTE: Fetching the top one is a bit naive, but works for now. A better
-// approach might be to fetch several at a time, and let the hook consumer
-// decide how to display them
-export function useFullSpanFromTrace(
- group?: string,
- sorts?: Sort[],
- enabled = true,
- extraFilters: Record = {}
-) {
- const filters = {...extraFilters};
-
- if (group) {
- filters[SpanIndexedField.SPAN_GROUP] = group;
- }
-
- const indexedSpansResponse = useSpansIndexed(
- {
- search: MutableSearch.fromQueryObject(filters),
- sorts: sorts || DEFAULT_SORT,
- limit: 1,
- enabled,
- fields: [
- SpanIndexedField.TIMESTAMP,
- SpanIndexedField.TRANSACTION_ID,
- SpanIndexedField.PROJECT,
- SpanIndexedField.SPAN_ID,
- ...(sorts?.map(sort => sort.field as SpanIndexedProperty) || []),
- ],
- },
- 'api.starfish.full-span-from-trace'
- );
-
- const firstIndexedSpan = indexedSpansResponse.data?.[0];
-
- const eventDetailsResponse = useEventDetails({
- eventId: firstIndexedSpan?.[SpanIndexedField.TRANSACTION_ID],
- projectSlug: firstIndexedSpan?.[SpanIndexedField.PROJECT],
- });
-
- const spanEntry = eventDetailsResponse.data?.entries.find(
- (entry: Entry): entry is EntrySpans => {
- return entry.type === EntryType.SPANS;
- }
- );
-
- const fullSpan = spanEntry?.data?.find(
- span => span.span_id === firstIndexedSpan?.[SpanIndexedField.SPAN_ID]
- );
-
- // N.B. There isn't a great pattern for us to merge the responses together,
- // so we're only merging the three most important properties
- return {
- isLoading: indexedSpansResponse.isPending || eventDetailsResponse.isPending,
- isFetching: indexedSpansResponse.isFetching || eventDetailsResponse.isFetching,
- isError: indexedSpansResponse.isError || eventDetailsResponse.isError,
- data: fullSpan,
- };
-}
diff --git a/static/app/views/insights/database/views/databaseSpanSummaryPage.spec.tsx b/static/app/views/insights/database/views/databaseSpanSummaryPage.spec.tsx
index ad494653c10c17..36ea9fb498213b 100644
--- a/static/app/views/insights/database/views/databaseSpanSummaryPage.spec.tsx
+++ b/static/app/views/insights/database/views/databaseSpanSummaryPage.spec.tsx
@@ -166,6 +166,12 @@ describe('DatabaseSpanSummaryPage', function () {
},
});
+ MockApiClient.addMockResponse({
+ url: `/projects/org-slug//releases/1.0.0/`,
+ method: 'GET',
+ body: [],
+ });
+
const issuesRequestMock = MockApiClient.addMockResponse({
url: `/organizations/${organization.slug}/issues/`,
method: 'GET',
@@ -224,7 +230,6 @@ describe('DatabaseSpanSummaryPage', function () {
environment: [],
field: [
'project_id',
- 'transaction.id',
'span.description',
'db.system',
'code.filepath',
@@ -351,26 +356,6 @@ describe('DatabaseSpanSummaryPage', function () {
})
);
- // Span details for query source. This runs after the indexed span has loaded
- expect(eventsRequestMock).toHaveBeenNthCalledWith(
- 2,
- `/organizations/${organization.slug}/events/`,
- expect.objectContaining({
- method: 'GET',
- query: {
- dataset: 'spansIndexed',
- environment: [],
- field: ['timestamp', 'transaction.id', 'project', 'span_id', 'span.self_time'],
- per_page: 1,
- project: [],
- query: 'span.group:1756baf8fd19c116',
- sort: '-span.self_time',
- referrer: 'api.starfish.full-span-from-trace',
- statsPeriod: '10d',
- },
- })
- );
-
expect(screen.getByRole('table', {name: 'Transactions'})).toBeInTheDocument();
expect(screen.getByRole('columnheader', {name: 'Found In'})).toBeInTheDocument();
diff --git a/static/app/views/insights/database/views/databaseSpanSummaryPage.tsx b/static/app/views/insights/database/views/databaseSpanSummaryPage.tsx
index 8313b9c4a71670..1cdf9bfb439518 100644
--- a/static/app/views/insights/database/views/databaseSpanSummaryPage.tsx
+++ b/static/app/views/insights/database/views/databaseSpanSummaryPage.tsx
@@ -82,7 +82,6 @@ export function DatabaseSpanSummaryPage({params}: Props) {
sorts: [{field: SpanIndexedField.CODE_FILEPATH, kind: 'desc'}],
fields: [
SpanIndexedField.PROJECT_ID,
- SpanIndexedField.TRANSACTION_ID, // TODO: remove this with `useInsightsEap`, it's only needed to get the full event when eap is off
SpanIndexedField.SPAN_DESCRIPTION,
SpanIndexedField.DB_SYSTEM,
SpanIndexedField.CODE_FILEPATH,
diff --git a/static/app/views/insights/queues/components/messageSpanSamplesPanel.spec.tsx b/static/app/views/insights/queues/components/messageSpanSamplesPanel.spec.tsx
index 8eb16211f3f32f..121814489060bc 100644
--- a/static/app/views/insights/queues/components/messageSpanSamplesPanel.spec.tsx
+++ b/static/app/views/insights/queues/components/messageSpanSamplesPanel.spec.tsx
@@ -16,7 +16,7 @@ describe('messageSpanSamplesPanel', () => {
let eventsRequestMock: jest.Mock;
let eventsStatsRequestMock: jest.Mock;
let samplesRequestMock: jest.Mock;
- let spanFieldTagsMock: jest.Mock;
+ let traceItemAttributesMock: jest.Mock;
jest.mocked(usePageFilters).mockReturnValue(
PageFilterStateFixture({
@@ -124,8 +124,8 @@ describe('messageSpanSamplesPanel', () => {
},
});
- spanFieldTagsMock = MockApiClient.addMockResponse({
- url: `/organizations/${organization.slug}/spans/fields/`,
+ traceItemAttributesMock = MockApiClient.addMockResponse({
+ url: `/organizations/${organization.slug}/trace-items/attributes/`,
method: 'GET',
body: [
{
@@ -139,11 +139,6 @@ describe('messageSpanSamplesPanel', () => {
],
});
- MockApiClient.addMockResponse({
- url: '/organizations/org-slug/trace-items/attributes/',
- body: [],
- });
-
MockApiClient.addMockResponse({
url: `/organizations/${organization.slug}/recent-searches/`,
body: [],
@@ -230,15 +225,31 @@ describe('messageSpanSamplesPanel', () => {
}),
})
);
- expect(spanFieldTagsMock).toHaveBeenNthCalledWith(
+ expect(traceItemAttributesMock).toHaveBeenNthCalledWith(
1,
- `/organizations/${organization.slug}/spans/fields/`,
+ `/organizations/${organization.slug}/trace-items/attributes/`,
expect.objectContaining({
method: 'GET',
query: {
+ attributeType: 'number',
+ itemType: 'spans',
project: [],
- environment: [],
- statsPeriod: '1h',
+ statsPeriod: '10d',
+ substringMatch: undefined,
+ },
+ })
+ );
+ expect(traceItemAttributesMock).toHaveBeenNthCalledWith(
+ 2,
+ `/organizations/${organization.slug}/trace-items/attributes/`,
+ expect.objectContaining({
+ method: 'GET',
+ query: {
+ attributeType: 'string',
+ itemType: 'spans',
+ project: [],
+ statsPeriod: '10d',
+ substringMatch: undefined,
},
})
);
@@ -326,14 +337,31 @@ describe('messageSpanSamplesPanel', () => {
}),
})
);
- expect(spanFieldTagsMock).toHaveBeenCalledWith(
- `/organizations/${organization.slug}/spans/fields/`,
+ expect(traceItemAttributesMock).toHaveBeenNthCalledWith(
+ 1,
+ `/organizations/${organization.slug}/trace-items/attributes/`,
expect.objectContaining({
method: 'GET',
query: {
+ attributeType: 'number',
+ itemType: 'spans',
project: [],
- environment: [],
- statsPeriod: '1h',
+ statsPeriod: '10d',
+ substringMatch: undefined,
+ },
+ })
+ );
+ expect(traceItemAttributesMock).toHaveBeenNthCalledWith(
+ 2,
+ `/organizations/${organization.slug}/trace-items/attributes/`,
+ expect.objectContaining({
+ method: 'GET',
+ query: {
+ attributeType: 'string',
+ itemType: 'spans',
+ project: [],
+ statsPeriod: '10d',
+ substringMatch: undefined,
},
})
);
diff --git a/static/app/views/insights/queues/components/messageSpanSamplesPanel.tsx b/static/app/views/insights/queues/components/messageSpanSamplesPanel.tsx
index 09aa7f93999bbc..e5607a5508fa48 100644
--- a/static/app/views/insights/queues/components/messageSpanSamplesPanel.tsx
+++ b/static/app/views/insights/queues/components/messageSpanSamplesPanel.tsx
@@ -5,7 +5,7 @@ import keyBy from 'lodash/keyBy';
import {Button} from 'sentry/components/core/button';
import {CompactSelect, type SelectOption} from 'sentry/components/core/compactSelect';
import {EventDrawerHeader} from 'sentry/components/events/eventDrawer';
-import {SpanSearchQueryBuilder} from 'sentry/components/performance/spanSearchQueryBuilder';
+import {EapSpanSearchQueryBuilderWrapper} from 'sentry/components/performance/spanSearchQueryBuilder';
import {t} from 'sentry/locale';
import {space} from 'sentry/styles/space';
import {trackAnalytics} from 'sentry/utils/analytics';
@@ -31,7 +31,6 @@ import {ReadoutRibbon} from 'sentry/views/insights/common/components/ribbon';
import {SampleDrawerBody} from 'sentry/views/insights/common/components/sampleDrawerBody';
import {SampleDrawerHeaderTransaction} from 'sentry/views/insights/common/components/sampleDrawerHeaderTransaction';
import {useSpanMetricsSeries} from 'sentry/views/insights/common/queries/useDiscoverSeries';
-import {useInsightsEap} from 'sentry/views/insights/common/utils/useEap';
import {getDurationChartTitle} from 'sentry/views/insights/common/views/spans/types';
import {useSpanSamples} from 'sentry/views/insights/http/queries/useSpanSamples';
import {InsightsSpanTagProvider} from 'sentry/views/insights/pages/insightsSpanTagProvider';
@@ -69,7 +68,6 @@ export function MessageSpanSamplesPanel() {
});
const {projects} = useProjects();
const {selection} = usePageFilters();
- const useEap = useInsightsEap();
const project = projects.find(p => query.project === p.id);
@@ -324,13 +322,12 @@ export function MessageSpanSamplesPanel() {
-
diff --git a/static/app/views/insights/types.tsx b/static/app/views/insights/types.tsx
index 0e4f90afdc9596..b25cc2aea28053 100644
--- a/static/app/views/insights/types.tsx
+++ b/static/app/views/insights/types.tsx
@@ -727,10 +727,6 @@ export type DiscoverResponse = Flatten;
export type DiscoverProperty = keyof DiscoverResponse;
-export type MetricsQueryFilters = Partial> & {
- [SpanIndexedField.PROJECT_ID]?: string;
-};
-
export type SpanQueryFilters = Partial> & {
is_transaction?: 'true' | 'false';
[SpanIndexedField.PROJECT_ID]?: string;