-
-
Notifications
You must be signed in to change notification settings - Fork 4.6k
feat(insights): Add prebuilt dashboard rendering for queues landing page #109610
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: master
Are you sure you want to change the base?
Changes from 2 commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,41 @@ | ||
| import {t} from 'sentry/locale'; | ||
| import {DisplayType, WidgetType, type Widget} from 'sentry/views/dashboards/types'; | ||
| import {SpanFields} from 'sentry/views/insights/types'; | ||
|
|
||
| export const QUEUE_CHARTS: Widget[] = [ | ||
| { | ||
| id: 'average-duration-widget', | ||
| title: t('Average Duration'), | ||
| displayType: DisplayType.AREA, | ||
| widgetType: WidgetType.SPANS, | ||
| interval: '5m', | ||
| queries: [ | ||
| { | ||
| name: '', | ||
| aggregates: [ | ||
| `avg(${SpanFields.MESSAGING_MESSAGE_RECEIVE_LATENCY})`, | ||
| `avg(${SpanFields.SPAN_DURATION})`, | ||
| ], | ||
| columns: [], | ||
| conditions: `${SpanFields.SPAN_OP}:queue.process`, | ||
| orderby: `avg(${SpanFields.SPAN_DURATION})`, | ||
| }, | ||
| ], | ||
| }, | ||
| { | ||
| id: 'throughput-widget', | ||
| title: t('Published vs Processed'), | ||
| displayType: DisplayType.LINE, | ||
| widgetType: WidgetType.SPANS, | ||
| interval: '5m', | ||
| queries: [ | ||
| { | ||
| name: '', | ||
| aggregates: ['epm()'], | ||
| columns: [SpanFields.SPAN_OP], | ||
| conditions: `${SpanFields.SPAN_OP}:[queue.publish, queue.process]`, | ||
| orderby: 'epm()', | ||
| }, | ||
| ], | ||
| }, | ||
| ]; | ||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -1,10 +1,191 @@ | ||
| import {t} from 'sentry/locale'; | ||
| import {DisplayType, WidgetType, type Widget} from 'sentry/views/dashboards/types'; | ||
| import type {PrebuiltDashboard} from 'sentry/views/dashboards/utils/prebuiltConfigs'; | ||
| import {QUEUE_CHARTS} from 'sentry/views/dashboards/utils/prebuiltConfigs/queues/queueCharts'; | ||
| import {SUMMARY_DASHBOARD_TITLE} from 'sentry/views/dashboards/utils/prebuiltConfigs/queues/settings'; | ||
| import {spaceWidgetsEquallyOnRow} from 'sentry/views/dashboards/utils/prebuiltConfigs/utils/spaceWidgetsEquallyOnRow'; | ||
| import {SpanFields} from 'sentry/views/insights/types'; | ||
|
|
||
| const SPAN_OP_FILTER = `${SpanFields.SPAN_OP}:[queue.publish, queue.process]`; | ||
|
|
||
| const FIRST_ROW_WIDGTS = spaceWidgetsEquallyOnRow( | ||
| [ | ||
| { | ||
| id: 'avg-time-in-queue-widget', | ||
| title: t('Avg Time in Queue'), | ||
| displayType: DisplayType.BIG_NUMBER, | ||
| widgetType: WidgetType.SPANS, | ||
| interval: '5m', | ||
| queries: [ | ||
| { | ||
| name: '', | ||
| fields: [`avg(${SpanFields.MESSAGING_MESSAGE_RECEIVE_LATENCY})`], | ||
| aggregates: [`avg(${SpanFields.MESSAGING_MESSAGE_RECEIVE_LATENCY})`], | ||
| columns: [], | ||
| conditions: SPAN_OP_FILTER, | ||
| orderby: `avg(${SpanFields.MESSAGING_MESSAGE_RECEIVE_LATENCY})`, | ||
| }, | ||
| ], | ||
| }, | ||
| { | ||
| id: 'avg-processing-time-widget', | ||
| title: t('Avg Processing Time'), | ||
| displayType: DisplayType.BIG_NUMBER, | ||
| widgetType: WidgetType.SPANS, | ||
| interval: '5m', | ||
| queries: [ | ||
| { | ||
| name: '', | ||
| fields: [`avg(${SpanFields.SPAN_DURATION})`], | ||
| aggregates: [`avg(${SpanFields.SPAN_DURATION})`], | ||
| columns: [], | ||
| conditions: SPAN_OP_FILTER, | ||
| orderby: `avg(${SpanFields.SPAN_DURATION})`, | ||
| }, | ||
| ], | ||
| }, | ||
| { | ||
| id: 'error-rate-widget', | ||
| title: t('Error Rate'), | ||
| displayType: DisplayType.BIG_NUMBER, | ||
| widgetType: WidgetType.SPANS, | ||
| interval: '5m', | ||
| queries: [ | ||
| { | ||
| name: '', | ||
| fields: [ | ||
| `equation|1 - (count_if(${SpanFields.TRACE_STATUS},equals,ok) / count(${SpanFields.SPAN_DURATION}))`, | ||
| ], | ||
| aggregates: [ | ||
| `equation|1 - (count_if(${SpanFields.TRACE_STATUS},equals,ok) / count(${SpanFields.SPAN_DURATION}))`, | ||
| ], | ||
| columns: [], | ||
| conditions: SPAN_OP_FILTER, | ||
| orderby: `equation|1 - (count_if(${SpanFields.TRACE_STATUS},equals,ok) / count(${SpanFields.SPAN_DURATION}))`, | ||
| }, | ||
| ], | ||
| }, | ||
| { | ||
| id: 'published-widget', | ||
| title: t('Published'), | ||
| displayType: DisplayType.BIG_NUMBER, | ||
| widgetType: WidgetType.SPANS, | ||
| interval: '5m', | ||
| queries: [ | ||
| { | ||
| name: '', | ||
| fields: [`count_if(${SpanFields.SPAN_OP},equals,queue.publish)`], | ||
| aggregates: [`count_if(${SpanFields.SPAN_OP},equals,queue.publish)`], | ||
| columns: [], | ||
| conditions: SPAN_OP_FILTER, | ||
| orderby: `count_if(${SpanFields.SPAN_OP},equals,queue.publish)`, | ||
| }, | ||
| ], | ||
| }, | ||
| { | ||
| id: 'processed-widget', | ||
| title: t('Processed'), | ||
| displayType: DisplayType.BIG_NUMBER, | ||
| widgetType: WidgetType.SPANS, | ||
| interval: '5m', | ||
| queries: [ | ||
| { | ||
| name: '', | ||
| fields: [`count_if(${SpanFields.SPAN_OP},equals,queue.process)`], | ||
| aggregates: [`count_if(${SpanFields.SPAN_OP},equals,queue.process)`], | ||
| columns: [], | ||
| conditions: SPAN_OP_FILTER, | ||
| orderby: `count_if(${SpanFields.SPAN_OP},equals,queue.process)`, | ||
| }, | ||
| ], | ||
| }, | ||
| { | ||
| id: 'time-spent-widget', | ||
| title: t('Time Spent'), | ||
| displayType: DisplayType.BIG_NUMBER, | ||
| widgetType: WidgetType.SPANS, | ||
| interval: '5m', | ||
| queries: [ | ||
| { | ||
| name: '', | ||
| fields: [`sum(${SpanFields.SPAN_DURATION})`], | ||
| aggregates: [`sum(${SpanFields.SPAN_DURATION})`], | ||
| columns: [], | ||
| conditions: SPAN_OP_FILTER, | ||
| orderby: `sum(${SpanFields.SPAN_DURATION})`, | ||
| }, | ||
| ], | ||
| }, | ||
| ], | ||
| 0, | ||
| {h: 1, minH: 1} | ||
| ); | ||
|
|
||
| const SECOND_ROW_WIDGETS = spaceWidgetsEquallyOnRow([...QUEUE_CHARTS], 1); | ||
|
|
||
| const TRANSACTIONS_TABLE: Widget = { | ||
| id: 'transactions-table', | ||
| title: t('Transactions Interacting with Destination'), | ||
| displayType: DisplayType.TABLE, | ||
| widgetType: WidgetType.SPANS, | ||
| interval: '5m', | ||
| queries: [ | ||
| { | ||
| name: '', | ||
| fields: [ | ||
| SpanFields.TRANSACTION, | ||
| `avg(${SpanFields.MESSAGING_MESSAGE_RECEIVE_LATENCY})`, | ||
| `avg_if(${SpanFields.SPAN_DURATION},${SpanFields.SPAN_OP},equals,queue.process)`, | ||
| `equation|1 - (count_if(${SpanFields.TRACE_STATUS},equals,ok) / count(${SpanFields.SPAN_DURATION}))`, | ||
| `count_if(${SpanFields.SPAN_OP},equals,queue.publish)`, | ||
| `count_if(${SpanFields.SPAN_OP},equals,queue.process)`, | ||
| `sum(${SpanFields.SPAN_DURATION})`, | ||
| ], | ||
| aggregates: [ | ||
| `avg(${SpanFields.MESSAGING_MESSAGE_RECEIVE_LATENCY})`, | ||
| `avg_if(${SpanFields.SPAN_DURATION},${SpanFields.SPAN_OP},equals,queue.process)`, | ||
| `equation|1 - (count_if(${SpanFields.TRACE_STATUS},equals,ok) / count(${SpanFields.SPAN_DURATION}))`, | ||
| `count_if(${SpanFields.SPAN_OP},equals,queue.publish)`, | ||
| `count_if(${SpanFields.SPAN_OP},equals,queue.process)`, | ||
| `sum(${SpanFields.SPAN_DURATION})`, | ||
| ], | ||
| columns: [SpanFields.MESSAGING_MESSAGE_DESTINATION_NAME, SpanFields.TRANSACTION], | ||
| fieldAliases: [ | ||
| t('Transaction'), | ||
| t('Avg time in queue'), | ||
| t('Avg processing time'), | ||
| t('Error rate'), | ||
| t('Published'), | ||
| t('Processed'), | ||
| t('Time spent'), | ||
| ], | ||
cursor[bot] marked this conversation as resolved.
Show resolved
Hide resolved
DominikB2014 marked this conversation as resolved.
Outdated
Show resolved
Hide resolved
|
||
| fieldMeta: [ | ||
| null, | ||
| null, | ||
| null, | ||
| null, | ||
| {valueType: 'percentage', valueUnit: null}, | ||
| null, | ||
| null, | ||
| null, | ||
| ], | ||
cursor[bot] marked this conversation as resolved.
Show resolved
Hide resolved
|
||
| conditions: SPAN_OP_FILTER, | ||
| orderby: `-sum(${SpanFields.SPAN_DURATION})`, | ||
| }, | ||
| ], | ||
| layout: { | ||
| x: 0, | ||
| y: 4, | ||
| w: 6, | ||
| h: 6, | ||
DominikB2014 marked this conversation as resolved.
Show resolved
Hide resolved
|
||
| minH: 6, | ||
| }, | ||
| }; | ||
|
|
||
| export const QUEUE_SUMMARY_PREBUILT_CONFIG: PrebuiltDashboard = { | ||
| dateCreated: '', | ||
| projects: [], | ||
| title: SUMMARY_DASHBOARD_TITLE, | ||
| filters: {}, | ||
| widgets: [], | ||
| widgets: [...FIRST_ROW_WIDGTS, ...SECOND_ROW_WIDGETS, TRANSACTIONS_TABLE], | ||
| }; | ||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -1,10 +1,95 @@ | ||
| import {t} from 'sentry/locale'; | ||
| import {FieldKind} from 'sentry/utils/fields'; | ||
| import {DisplayType, WidgetType, type Widget} from 'sentry/views/dashboards/types'; | ||
| import type {PrebuiltDashboard} from 'sentry/views/dashboards/utils/prebuiltConfigs'; | ||
| import {QUEUE_CHARTS} from 'sentry/views/dashboards/utils/prebuiltConfigs/queues/queueCharts'; | ||
| import {DASHBOARD_TITLE} from 'sentry/views/dashboards/utils/prebuiltConfigs/queues/settings'; | ||
| import {spaceWidgetsEquallyOnRow} from 'sentry/views/dashboards/utils/prebuiltConfigs/utils/spaceWidgetsEquallyOnRow'; | ||
| import {SpanFields} from 'sentry/views/insights/types'; | ||
|
|
||
| const FIRST_ROW_WIDGETS = spaceWidgetsEquallyOnRow([...QUEUE_CHARTS], 0); | ||
|
|
||
| const DESTINATION_TABLE: Widget = { | ||
| id: 'destination-table', | ||
| title: t('Destinations'), | ||
| displayType: DisplayType.TABLE, | ||
| widgetType: WidgetType.SPANS, | ||
| interval: '5m', | ||
| queries: [ | ||
| { | ||
| name: '', | ||
| fields: [ | ||
| SpanFields.MESSAGING_MESSAGE_DESTINATION_NAME, | ||
| `avg(${SpanFields.MESSAGING_MESSAGE_RECEIVE_LATENCY})`, | ||
| `avg(${SpanFields.SPAN_DURATION})`, | ||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Destination table uses wrong aggregate for processing timeHigh Severity The Additional Locations (1) |
||
| `equation|1 - (count_if(${SpanFields.TRACE_STATUS},equals,ok) / count(${SpanFields.SPAN_DURATION}))`, | ||
| `count_if(${SpanFields.SPAN_OP},equals,queue.publish)`, | ||
| `count_if(${SpanFields.SPAN_OP},equals,queue.process)`, | ||
| `sum(${SpanFields.SPAN_DURATION})`, | ||
| ], | ||
| columns: [SpanFields.MESSAGING_MESSAGE_DESTINATION_NAME], | ||
| aggregates: [ | ||
| `avg(${SpanFields.MESSAGING_MESSAGE_RECEIVE_LATENCY})`, | ||
| `avg(${SpanFields.SPAN_DURATION})`, | ||
| `equation|1 - (count_if(${SpanFields.TRACE_STATUS},equals,ok) / count(${SpanFields.SPAN_DURATION}))`, | ||
| `count_if(${SpanFields.SPAN_OP},equals,queue.publish)`, | ||
| `count_if(${SpanFields.SPAN_OP},equals,queue.process)`, | ||
| `sum(${SpanFields.SPAN_DURATION})`, | ||
| ], | ||
DominikB2014 marked this conversation as resolved.
Show resolved
Hide resolved
|
||
| fieldAliases: [ | ||
| t('Destination'), | ||
| t('Avg time in queue'), | ||
| t('Avg processing time'), | ||
| t('Error rate'), | ||
| t('Published'), | ||
| t('Processed'), | ||
| t('Time spent'), | ||
| ], | ||
| fieldMeta: [ | ||
| null, | ||
| null, | ||
| null, | ||
| {valueType: 'percentage', valueUnit: null}, | ||
| null, | ||
| null, | ||
| null, | ||
| ], | ||
| linkedDashboards: [ | ||
| { | ||
| dashboardId: '-1', | ||
| field: SpanFields.MESSAGING_MESSAGE_DESTINATION_NAME, | ||
| staticDashboardId: 27, | ||
| }, | ||
| ], | ||
| conditions: `${SpanFields.SPAN_OP}:[queue.publish, queue.process]`, | ||
| orderby: `-sum(${SpanFields.SPAN_DURATION})`, | ||
| }, | ||
| ], | ||
| layout: { | ||
| x: 0, | ||
| y: 3, | ||
| w: 6, | ||
| h: 6, | ||
| minH: 6, | ||
| }, | ||
| }; | ||
|
|
||
| export const QUEUES_PREBUILT_CONFIG: PrebuiltDashboard = { | ||
| dateCreated: '', | ||
| projects: [], | ||
| title: DASHBOARD_TITLE, | ||
| filters: {}, | ||
| widgets: [], | ||
| filters: { | ||
| globalFilter: [ | ||
| { | ||
| dataset: WidgetType.SPANS, | ||
| tag: { | ||
| key: SpanFields.MESSAGING_MESSAGE_DESTINATION_NAME, | ||
| name: SpanFields.MESSAGING_MESSAGE_DESTINATION_NAME, | ||
| kind: FieldKind.TAG, | ||
| }, | ||
| value: '', | ||
| }, | ||
| ], | ||
| }, | ||
| widgets: [...FIRST_ROW_WIDGETS, DESTINATION_TABLE], | ||
| }; | ||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,7 @@ | ||
| import useOrganization from 'sentry/utils/useOrganization'; | ||
|
|
||
| export function useHasPlatformizedQueues() { | ||
| const organization = useOrganization(); | ||
|
|
||
| return organization.features.includes('insights-queue-dashboard-migration'); | ||
| } |
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,20 @@ | ||
| import {DataCategory} from 'sentry/types/core'; | ||
| import {useMaxPickableDays} from 'sentry/utils/useMaxPickableDays'; | ||
| import {PrebuiltDashboardRenderer} from 'sentry/views/dashboards/prebuiltDashboardRenderer'; | ||
| import {PrebuiltDashboardId} from 'sentry/views/dashboards/utils/prebuiltConfigs'; | ||
| import {ModulePageProviders} from 'sentry/views/insights/common/components/modulePageProviders'; | ||
|
|
||
| export function PlatformizedQueuesOverview() { | ||
| const maxPickableDays = useMaxPickableDays({ | ||
| dataCategories: [DataCategory.SPANS], | ||
| }); | ||
|
|
||
| return ( | ||
| <ModulePageProviders | ||
| moduleName="queue" | ||
| maxPickableDays={maxPickableDays.maxPickableDays} | ||
| > | ||
| <PrebuiltDashboardRenderer prebuiltId={PrebuiltDashboardId.BACKEND_QUEUES} /> | ||
| </ModulePageProviders> | ||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Missing analytics event in platformized queues overviewMedium Severity
Additional Locations (1) |
||
| ); | ||
| } | ||


There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Bug: The new AREA and LINE widgets in
queueCharts.tsare missing thefieldsproperty. Other similar widgets in the codebase includefieldsthat mirroraggregates.Severity: MEDIUM
Suggested Fix
Add a
fieldsproperty to both theaverage-duration-widgetandthroughput-widgetinqueueCharts.ts. The value of thefieldsarray should be identical to theaggregatesarray to maintain consistency with other prebuilt chart widgets.Prompt for AI Agent