Browse Source

feat(profiling): Add user misery to profiling landing (#45161)

Now that we can query the transactions dataset for profiling data, we
can pull in columns like user misery easily.
Tony Xiao 2 years ago
parent
commit
b0b586ac18

+ 20 - 0
static/app/components/profiling/profileEventsTable.tsx

@@ -11,6 +11,7 @@ import GridEditable, {
 import ProjectBadge from 'sentry/components/idBadge/projectBadge';
 import Link from 'sentry/components/links/link';
 import PerformanceDuration from 'sentry/components/performanceDuration';
+import UserMisery from 'sentry/components/userMisery';
 import Version from 'sentry/components/version';
 import {t} from 'sentry/locale';
 import {Organization, Project} from 'sentry/types';
@@ -200,6 +201,19 @@ function ProfileEventsCell<F extends FieldType>(props: ProfileEventsCellProps<F>
     }
   }
 
+  if (key === 'user_misery()') {
+    return (
+      <UserMisery
+        bars={10}
+        barHeight={20}
+        miserableUsers={undefined}
+        miseryLimit={undefined}
+        totalUsers={undefined}
+        userMisery={value || 0}
+      />
+    );
+  }
+
   switch (columnType) {
     case 'integer':
     case 'number':
@@ -274,6 +288,7 @@ const FIELDS = [
   'p95()',
   'p99()',
   'count()',
+  'user_misery()',
 ] as const;
 
 type FieldType = (typeof FIELDS)[number];
@@ -424,6 +439,11 @@ const COLUMN_ORDERS: Record<FieldType, GridColumnOrder<FieldType>> = {
     name: t('Count()'),
     width: COL_WIDTH_UNDEFINED,
   },
+  'user_misery()': {
+    key: 'user_misery()',
+    name: t('User Misery'),
+    width: COL_WIDTH_UNDEFINED,
+  },
 };
 
 function getColumnOrder<F extends FieldType>(field: F): GridColumnOrder<F> {

+ 15 - 10
static/app/views/profiling/content.tsx

@@ -53,15 +53,17 @@ function ProfilingContent({location}: ProfilingContentProps) {
   const cursor = decodeScalar(location.query.cursor);
   const query = decodeScalar(location.query.query, '');
 
-  const sort = formatSort<FieldType>(decodeScalar(location.query.sort), FIELDS, {
-    key: 'p99()',
-    order: 'desc',
-  });
-
   const profilingUsingTransactions = organization.features.includes(
     'profiling-using-transactions'
   );
 
+  const fields = profilingUsingTransactions ? ALL_FIELDS : BASE_FIELDS;
+
+  const sort = formatSort<FieldType>(decodeScalar(location.query.sort), fields, {
+    key: 'p99()',
+    order: 'desc',
+  });
+
   const profileFilters = useProfileFilters({
     query: '',
     selection,
@@ -71,7 +73,7 @@ function ProfilingContent({location}: ProfilingContentProps) {
 
   const transactions = useProfileEvents<FieldType>({
     cursor,
-    fields: FIELDS,
+    fields,
     query,
     sort,
     referrer: 'api.profiling.landing-table',
@@ -254,7 +256,7 @@ function ProfilingContent({location}: ProfilingContentProps) {
                     />
                   )}
                   <ProfileEventsTable
-                    columns={FIELDS.slice()}
+                    columns={fields.slice()}
                     data={transactions.status === 'success' ? transactions.data[0] : null}
                     error={
                       transactions.status === 'error'
@@ -263,7 +265,7 @@ function ProfilingContent({location}: ProfilingContentProps) {
                     }
                     isLoading={transactions.status === 'loading'}
                     sort={sort}
-                    sortableColumns={new Set(FIELDS)}
+                    sortableColumns={new Set(fields)}
                   />
                   <Pagination
                     pageLinks={
@@ -282,7 +284,7 @@ function ProfilingContent({location}: ProfilingContentProps) {
   );
 }
 
-const FIELDS = [
+const BASE_FIELDS = [
   'transaction',
   'project.id',
   'last_seen()',
@@ -292,7 +294,10 @@ const FIELDS = [
   'count()',
 ] as const;
 
-type FieldType = (typeof FIELDS)[number];
+// user misery is only available with the profiling-using-transactions feature
+const ALL_FIELDS = [...BASE_FIELDS, 'user_misery()'] as const;
+
+type FieldType = (typeof ALL_FIELDS)[number];
 
 const ActionBar = styled('div')`
   display: grid;