From bf0b4f121fea3d38e809b9403e0295c1baf2025f Mon Sep 17 00:00:00 2001 From: Dan Fuller Date: Fri, 15 May 2026 13:58:17 -0700 Subject: [PATCH] ref(flags): Remove organizations:on-demand-metrics-extraction-experimental Registered Jun 2023, dev-only, never rolled out to customers. Co-Authored-By: Claude Opus 4.6 (1M context) --- .../api/endpoints/organization_events.py | 1 - .../serializers/rest_framework/dashboard.py | 24 ------------- src/sentry/features/temporary.py | 3 +- src/sentry/relay/config/metric_extraction.py | 1 - static/app/utils/onDemandMetrics/features.tsx | 3 +- .../metricsEnhancedPerformanceDataContext.tsx | 31 ++-------------- .../performance/contexts/onDemandControl.tsx | 36 ------------------- static/app/views/dashboards/filtersBar.tsx | 2 -- ...t_organization_dashboard_widget_details.py | 1 - 9 files changed, 4 insertions(+), 98 deletions(-) diff --git a/src/sentry/api/endpoints/organization_events.py b/src/sentry/api/endpoints/organization_events.py index 6c8869e27e75..17429fd1c0c3 100644 --- a/src/sentry/api/endpoints/organization_events.py +++ b/src/sentry/api/endpoints/organization_events.py @@ -117,7 +117,6 @@ def get_features(self, organization: Organization, request: Request) -> Mapping[ "organizations:dynamic-sampling", "organizations:on-demand-metrics-extraction", "organizations:on-demand-metrics-extraction-widgets", - "organizations:on-demand-metrics-extraction-experimental", ] batch_features = features.batch_has( feature_names, diff --git a/src/sentry/api/serializers/rest_framework/dashboard.py b/src/sentry/api/serializers/rest_framework/dashboard.py index c3e64ac5bef0..db6930c4c259 100644 --- a/src/sentry/api/serializers/rest_framework/dashboard.py +++ b/src/sentry/api/serializers/rest_framework/dashboard.py @@ -41,7 +41,6 @@ check_field_cardinality, set_or_create_on_demand_state, ) -from sentry.tasks.relay import schedule_invalidate_project_config from sentry.utils.dates import parse_stats_period from sentry.utils.strings import oxfordize_list @@ -823,8 +822,6 @@ def create(self, validated_data): self.update_permissions(self.instance, validated_data) - schedule_update_project_configs(self.instance) - return self.instance def update(self, instance, validated_data): @@ -848,8 +845,6 @@ def update(self, instance, validated_data): self.update_permissions(instance, validated_data) - schedule_update_project_configs(instance) - return instance def update_widgets(self, instance, widget_data): @@ -1255,22 +1250,3 @@ def validate_dashboard_ids(self, dashboard_ids): if len(dashboard_ids) != len(set(dashboard_ids)): raise serializers.ValidationError("Single dashboard cannot take up multiple positions") return dashboard_ids - - -def schedule_update_project_configs(dashboard: Dashboard): - """ - Schedule a task to update project configs for all projects of an organization when a dashboard is updated. - """ - org = dashboard.organization - - on_demand_metrics = features.has("organizations:on-demand-metrics-extraction", org) - dashboard_on_demand_metrics = features.has( - "organizations:on-demand-metrics-extraction-experimental", org - ) - - if not on_demand_metrics or not dashboard_on_demand_metrics: - return - - schedule_invalidate_project_config( - trigger="dashboards:create-on-demand-metric", organization_id=org.id - ) diff --git a/src/sentry/features/temporary.py b/src/sentry/features/temporary.py index 8d1751cc545a..0d77806f01ce 100644 --- a/src/sentry/features/temporary.py +++ b/src/sentry/features/temporary.py @@ -163,8 +163,7 @@ def register_temporary_features(manager: FeatureManager) -> None: manager.add("organizations:more-workflows", OrganizationFeature, FeatureHandlerStrategy.FLAGPOLE, api_expose=False) # Extract on demand metrics manager.add("organizations:on-demand-metrics-extraction", OrganizationFeature, FeatureHandlerStrategy.FLAGPOLE, api_expose=True) - # Extract on demand metrics (experimental features) - manager.add("organizations:on-demand-metrics-extraction-experimental", OrganizationFeature, FeatureHandlerStrategy.FLAGPOLE, api_expose=True) + # Extract on demand metrics (widget extraction) manager.add("organizations:on-demand-metrics-extraction-widgets", OrganizationFeature, FeatureHandlerStrategy.FLAGPOLE, api_expose=False) # Display on demand metrics related UI elements diff --git a/src/sentry/relay/config/metric_extraction.py b/src/sentry/relay/config/metric_extraction.py index 9083e5c05bbc..959f837159b6 100644 --- a/src/sentry/relay/config/metric_extraction.py +++ b/src/sentry/relay/config/metric_extraction.py @@ -159,7 +159,6 @@ def on_demand_metrics_feature_flags(organization: Organization) -> set[str]: feature_names = [ "organizations:on-demand-metrics-extraction", "organizations:on-demand-metrics-extraction-widgets", # Controls extraction for widgets - "organizations:on-demand-metrics-extraction-experimental", "organizations:on-demand-metrics-prefill", ] diff --git a/static/app/utils/onDemandMetrics/features.tsx b/static/app/utils/onDemandMetrics/features.tsx index 5b029f009842..a7d3c2c4a92d 100644 --- a/static/app/utils/onDemandMetrics/features.tsx +++ b/static/app/utils/onDemandMetrics/features.tsx @@ -15,7 +15,6 @@ export function shouldShowOnDemandMetricAlertUI(organization: Organization) { export function hasOnDemandMetricWidgetFeature(organization: Organization) { return ( organization.features.includes('on-demand-metrics-extraction') && - (organization.features.includes('on-demand-metrics-extraction-experimental') || - organization.features.includes('on-demand-metrics-ui-widgets')) + organization.features.includes('on-demand-metrics-ui-widgets') ); } diff --git a/static/app/utils/performance/contexts/metricsEnhancedPerformanceDataContext.tsx b/static/app/utils/performance/contexts/metricsEnhancedPerformanceDataContext.tsx index c596d7870c9f..6f362eb6515d 100644 --- a/static/app/utils/performance/contexts/metricsEnhancedPerformanceDataContext.tsx +++ b/static/app/utils/performance/contexts/metricsEnhancedPerformanceDataContext.tsx @@ -1,13 +1,11 @@ import type {ReactNode} from 'react'; import {createContext, useCallback, useContext, useState} from 'react'; -import {useOrganization} from 'sentry/utils/useOrganization'; import type {Widget} from 'sentry/views/dashboards/types'; import {WIDGET_MAP_DENY_LIST} from 'sentry/views/performance/landing/widgets/utils'; import type {PerformanceWidgetSetting} from 'sentry/views/performance/landing/widgets/widgetDefinitions'; import {AutoSampleState, useMEPSettingContext} from './metricsEnhancedSetting'; -import {useOnDemandControl} from './onDemandControl'; export type MetricsResultsMetaMapKey = Widget; type ExtractedDataMap = Map; @@ -119,33 +117,8 @@ export function getIsMetricsDataFromResults( type ExtractionStatus = 'extracted' | 'not-extracted' | null; -export function useExtractionStatus(props: { +export function useExtractionStatus(_props: { queryKey: MetricsResultsMetaMapKey; }): ExtractionStatus { - const resultsMeta = useMetricsResultsMeta(); - const organization = useOrganization(); - const _onDemandControl = useOnDemandControl(); - - if (!_onDemandControl) { - return null; - } - - const {forceOnDemand} = _onDemandControl; - - const isMetricsExtractedData = - resultsMeta?.metricsExtractedDataMap.get(props.queryKey.id ?? '') || undefined; - - if (!organization.features.includes('on-demand-metrics-extraction-experimental')) { - // Separate if for easier flag deletion - return null; - } - - if (!forceOnDemand || isMetricsExtractedData === undefined) { - return null; - } - - if (!isMetricsExtractedData) { - return 'not-extracted'; - } - return 'extracted'; + return null; } diff --git a/static/app/utils/performance/contexts/onDemandControl.tsx b/static/app/utils/performance/contexts/onDemandControl.tsx index ff2a035e51b7..2d313a45fb88 100644 --- a/static/app/utils/performance/contexts/onDemandControl.tsx +++ b/static/app/utils/performance/contexts/onDemandControl.tsx @@ -1,17 +1,11 @@ import type {ReactNode} from 'react'; import {createContext, useCallback, useContext, useState} from 'react'; -import {useTheme} from '@emotion/react'; import type {Location} from 'history'; -import {Switch} from '@sentry/scraps/switch'; - -import {t} from 'sentry/locale'; import type {Organization} from 'sentry/types/organization'; -import {FlexContainer} from 'sentry/utils/discover/styles'; import {isOnDemandQueryString} from 'sentry/utils/onDemandMetrics'; import {hasOnDemandMetricWidgetFeature} from 'sentry/utils/onDemandMetrics/features'; import {useNavigate} from 'sentry/utils/useNavigate'; -import {useOrganization} from 'sentry/utils/useOrganization'; import type {Widget} from 'sentry/views/dashboards/types'; import {WidgetType} from 'sentry/views/dashboards/types'; @@ -136,33 +130,3 @@ export const shouldUseOnDemandMetrics = ( return isOnDemandMetricWidget(widget); }; - -export function ToggleOnDemand() { - const theme = useTheme(); - const org = useOrganization(); - const onDemand = useOnDemandControl(); - - if (!onDemand) { - return null; - } - - const toggle = () => { - onDemand.setForceOnDemand(!onDemand.forceOnDemand); - }; - - if (!org.features.includes('on-demand-metrics-extraction-experimental')) { - return null; - } - - return ( - - {t('On-demand metrics')} - - - ); -} diff --git a/static/app/views/dashboards/filtersBar.tsx b/static/app/views/dashboards/filtersBar.tsx index 1113d027ada2..d1a21e48594e 100644 --- a/static/app/views/dashboards/filtersBar.tsx +++ b/static/app/views/dashboards/filtersBar.tsx @@ -27,7 +27,6 @@ import {DataCategory} from 'sentry/types/core'; import type {User} from 'sentry/types/user'; import {defined} from 'sentry/utils'; import {trackAnalytics} from 'sentry/utils/analytics'; -import {ToggleOnDemand} from 'sentry/utils/performance/contexts/onDemandControl'; import {useMaxPickableDays} from 'sentry/utils/useMaxPickableDays'; import {useOrganization} from 'sentry/utils/useOrganization'; import {useUser} from 'sentry/utils/useUser'; @@ -396,7 +395,6 @@ export function FiltersBar({ )} -