From ec1ace398e1ed3ae35a358e9dbbe7e6f50f67375 Mon Sep 17 00:00:00 2001 From: Alex Khomenko Date: Tue, 13 Jan 2026 17:22:20 +0200 Subject: [PATCH] Recent dashboards: Add experimental toggle (#116121) * Add experimentRecentlyViewedDashboards toggle * Emit dashboards_browse_list_viewed event * Move feature toggle to parent * merge --- .../src/types/featureToggles.gen.ts | 5 ++++ pkg/services/featuremgmt/registry.go | 9 +++++++ pkg/services/featuremgmt/toggles_gen.csv | 1 + pkg/services/featuremgmt/toggles_gen.json | 15 +++++++++++ .../BrowseDashboardsPage.tsx | 25 ++++++++++++++++--- .../components/RecentlyViewedDashboards.tsx | 6 +---- 6 files changed, 53 insertions(+), 8 deletions(-) diff --git a/packages/grafana-data/src/types/featureToggles.gen.ts b/packages/grafana-data/src/types/featureToggles.gen.ts index 4850555be08..aa0581004e1 100644 --- a/packages/grafana-data/src/types/featureToggles.gen.ts +++ b/packages/grafana-data/src/types/featureToggles.gen.ts @@ -984,6 +984,11 @@ export interface FeatureToggles { */ recentlyViewedDashboards?: boolean; /** + * A/A test for recently viewed dashboards feature + * @default false + */ + experimentRecentlyViewedDashboards?: boolean; + /** * Enable configuration of alert enrichments in Grafana Cloud. * @default false */ diff --git a/pkg/services/featuremgmt/registry.go b/pkg/services/featuremgmt/registry.go index 64511b3ccfa..a41e6804176 100644 --- a/pkg/services/featuremgmt/registry.go +++ b/pkg/services/featuremgmt/registry.go @@ -1625,6 +1625,15 @@ var ( FrontendOnly: true, Expression: "false", }, + { + Name: "experimentRecentlyViewedDashboards", + Description: "A/A test for recently viewed dashboards feature", + Stage: FeatureStageExperimental, + Owner: grafanaFrontendSearchNavOrganise, + FrontendOnly: true, + HideFromDocs: true, + Expression: "false", + }, { Name: "alertEnrichment", Description: "Enable configuration of alert enrichments in Grafana Cloud.", diff --git a/pkg/services/featuremgmt/toggles_gen.csv b/pkg/services/featuremgmt/toggles_gen.csv index 9f74c053697..94de5c790c3 100644 --- a/pkg/services/featuremgmt/toggles_gen.csv +++ b/pkg/services/featuremgmt/toggles_gen.csv @@ -223,6 +223,7 @@ kubernetesAuthnMutation,experimental,@grafana/identity-access-team,false,false,f kubernetesExternalGroupMapping,experimental,@grafana/identity-access-team,false,false,false restoreDashboards,experimental,@grafana/grafana-search-navigate-organise,false,false,false recentlyViewedDashboards,experimental,@grafana/grafana-search-navigate-organise,false,false,true +experimentRecentlyViewedDashboards,experimental,@grafana/grafana-search-navigate-organise,false,false,true alertEnrichment,experimental,@grafana/alerting-squad,false,false,false alertEnrichmentMultiStep,experimental,@grafana/alerting-squad,false,false,false alertEnrichmentConditional,experimental,@grafana/alerting-squad,false,false,false diff --git a/pkg/services/featuremgmt/toggles_gen.json b/pkg/services/featuremgmt/toggles_gen.json index d96eb8e8d5a..75e3ca69afe 100644 --- a/pkg/services/featuremgmt/toggles_gen.json +++ b/pkg/services/featuremgmt/toggles_gen.json @@ -1365,6 +1365,21 @@ "hideFromDocs": true } }, + { + "metadata": { + "name": "experimentRecentlyViewedDashboards", + "resourceVersion": "1768214542023", + "creationTimestamp": "2026-01-12T10:42:22Z" + }, + "spec": { + "description": "A/A test for recently viewed dashboards feature", + "stage": "experimental", + "codeowner": "@grafana/grafana-search-navigate-organise", + "frontend": true, + "hideFromDocs": true, + "expression": "false" + } + }, { "metadata": { "name": "exploreLogsAggregatedMetrics", diff --git a/public/app/features/browse-dashboards/BrowseDashboardsPage.tsx b/public/app/features/browse-dashboards/BrowseDashboardsPage.tsx index e177fcf9fa2..1a6b8c65011 100644 --- a/public/app/features/browse-dashboards/BrowseDashboardsPage.tsx +++ b/public/app/features/browse-dashboards/BrowseDashboardsPage.tsx @@ -1,11 +1,12 @@ import { css } from '@emotion/css'; -import { memo, useEffect, useMemo } from 'react'; +import { memo, useEffect, useMemo, useRef } from 'react'; import { useLocation, useParams } from 'react-router-dom-v5-compat'; import AutoSizer from 'react-virtualized-auto-sizer'; import { GrafanaTheme2 } from '@grafana/data'; import { Trans } from '@grafana/i18n'; import { config, reportInteraction } from '@grafana/runtime'; +import { evaluateBooleanFlag } from '@grafana/runtime/internal'; import { LinkButton, FilterInput, useStyles2, Text, Stack } from '@grafana/ui'; import { useGetFolderQueryFacade, useUpdateFolder } from 'app/api/clients/folder/v1beta1/hooks'; import { Page } from 'app/core/components/Page/Page'; @@ -44,6 +45,7 @@ const BrowseDashboardsPage = memo(({ queryParams }: { queryParams: Record new URLSearchParams(location.search), [location.search]); const { isReadOnlyRepo, repoType } = useGetResourceRepositoryView({ folderName: folderUID }); + const isRecentlyViewedEnabled = !folderUID && evaluateBooleanFlag('recentlyViewedDashboards', false); useEffect(() => { stateManager.initStateFromUrl(folderUID); @@ -73,6 +75,23 @@ const BrowseDashboardsPage = memo(({ queryParams }: { queryParams: Record { + if (!isRecentlyViewedEnabled || hasEmittedExposureEvent.current) { + return; + } + + hasEmittedExposureEvent.current = true; + const isExperimentTreatment = evaluateBooleanFlag('experimentRecentlyViewedDashboards', false); + + reportInteraction('dashboards_browse_list_viewed', { + experiment_dashboard_list_recently_viewed: isExperimentTreatment ? 'treatment' : 'control', + has_recently_viewed_component: isExperimentTreatment, + }); + }, [isRecentlyViewedEnabled]); + const { data: folderDTO } = useGetFolderQueryFacade(folderUID); const [saveFolder] = useUpdateFolder(); const navModel = useMemo(() => { @@ -179,8 +198,8 @@ const BrowseDashboardsPage = memo(({ queryParams }: { queryParams: Record - {/* only show recently viewed dashboards when in root */} - {!folderUID && } + {/* only show recently viewed dashboards when in root and flag is enabled */} + {isRecentlyViewedEnabled && }
{ - if (!evaluateBooleanFlag('recentlyViewedDashboards', false)) { - return []; - } return getRecentlyViewedDashboards(MAX_RECENT); }, []); const { foldersByUid } = useDashboardLocationInfo(recentDashboards.length > 0); @@ -48,7 +44,7 @@ export function RecentlyViewedDashboards() { setIsOpen(!isOpen); }; - if (!evaluateBooleanFlag('recentlyViewedDashboards', false) || recentDashboards.length === 0) { + if (recentDashboards.length === 0) { return null; }