From 60e6dd56bff055aaa3e8288da21fbc16955bc2a2 Mon Sep 17 00:00:00 2001 From: Victor Marin <36818606+mdvictor@users.noreply.github.com> Date: Fri, 19 Apr 2024 13:21:40 +0300 Subject: [PATCH] Change folder breadcrumb on folder change in general settings (#86342) * Change folder breadcrumb on folder change in general settings * tests and refactor * refactor to fix broken tests * fix test --- .../pages/DashboardScenePageStateManager.ts | 24 +++----------- .../dashboard-scene/pages/utils.test.ts | 32 +++++++++++++++++++ .../features/dashboard-scene/pages/utils.ts | 13 ++++++++ .../settings/GeneralSettingsEditView.test.tsx | 8 +++-- .../settings/GeneralSettingsEditView.tsx | 7 +++- 5 files changed, 62 insertions(+), 22 deletions(-) create mode 100644 public/app/features/dashboard-scene/pages/utils.test.ts create mode 100644 public/app/features/dashboard-scene/pages/utils.ts diff --git a/public/app/features/dashboard-scene/pages/DashboardScenePageStateManager.ts b/public/app/features/dashboard-scene/pages/DashboardScenePageStateManager.ts index e878af98383..c9132a9415e 100644 --- a/public/app/features/dashboard-scene/pages/DashboardScenePageStateManager.ts +++ b/public/app/features/dashboard-scene/pages/DashboardScenePageStateManager.ts @@ -1,8 +1,6 @@ import { locationUtil } from '@grafana/data'; import { config, getBackendSrv, isFetchError, locationService } from '@grafana/runtime'; -import { updateNavIndex } from 'app/core/actions'; import { StateManagerBase } from 'app/core/services/StateManagerBase'; -import { backendSrv } from 'app/core/services/backend_srv'; import { default as localStorageStore } from 'app/core/store'; import { dashboardLoaderSrv } from 'app/features/dashboard/services/DashboardLoaderSrv'; import { getDashboardSrv } from 'app/features/dashboard/services/DashboardSrv'; @@ -10,8 +8,6 @@ import { DASHBOARD_FROM_LS_KEY, removeDashboardToFetchFromLocalStorage, } from 'app/features/dashboard/state/initDashboard'; -import { buildNavModel } from 'app/features/folders/state/navModel'; -import { store } from 'app/store/store'; import { DashboardDTO, DashboardRoutes } from 'app/types'; import { PanelEditor } from '../panel-edit/PanelEditor'; @@ -19,6 +15,8 @@ import { DashboardScene } from '../scene/DashboardScene'; import { buildNewDashboardSaveModel } from '../serialization/buildNewDashboardSaveModel'; import { transformSaveModelToScene } from '../serialization/transformSaveModelToScene'; +import { updateNavModel } from './utils'; + export interface DashboardScenePageState { dashboard?: DashboardScene; panelEditor?: PanelEditor; @@ -127,7 +125,9 @@ export class DashboardScenePageStateManager extends StateManagerBase { + it('Should update nav model', async () => { + const reduxStore = configureStore(); + + jest.spyOn(backendSrv, 'getFolderByUid').mockResolvedValue({ + id: 1, + uid: 'new-folder', + title: 'NewFolder', + url: '', + canAdmin: true, + canDelete: true, + canEdit: true, + canSave: true, + created: '', + createdBy: '', + hasAcl: false, + updated: '', + updatedBy: '', + }); + + expect(reduxStore.getState().navIndex[`folder-dashboards-new-folder`]).toBeUndefined(); + + await updateNavModel('new-folder'); + + expect(reduxStore.getState().navIndex[`folder-dashboards-new-folder`]).not.toBeUndefined(); + }); +}); diff --git a/public/app/features/dashboard-scene/pages/utils.ts b/public/app/features/dashboard-scene/pages/utils.ts new file mode 100644 index 00000000000..2e06429589f --- /dev/null +++ b/public/app/features/dashboard-scene/pages/utils.ts @@ -0,0 +1,13 @@ +import { updateNavIndex } from 'app/core/actions'; +import { backendSrv } from 'app/core/services/backend_srv'; +import { buildNavModel } from 'app/features/folders/state/navModel'; +import { store } from 'app/store/store'; + +export async function updateNavModel(folderUid: string) { + try { + const folder = await backendSrv.getFolderByUid(folderUid); + store.dispatch(updateNavIndex(buildNavModel(folder))); + } catch (err) { + console.warn('Error fetching parent folder', folderUid, 'for dashboard', err); + } +} diff --git a/public/app/features/dashboard-scene/settings/GeneralSettingsEditView.test.tsx b/public/app/features/dashboard-scene/settings/GeneralSettingsEditView.test.tsx index e1e55da7e44..e2f343c383c 100644 --- a/public/app/features/dashboard-scene/settings/GeneralSettingsEditView.test.tsx +++ b/public/app/features/dashboard-scene/settings/GeneralSettingsEditView.test.tsx @@ -1,6 +1,7 @@ import { behaviors, SceneGridLayout, SceneTimeRange } from '@grafana/scenes'; import { DashboardCursorSync } from '@grafana/schema'; +import * as utils from '../pages/utils'; import { DashboardControls } from '../scene/DashboardControls'; import { DashboardScene } from '../scene/DashboardScene'; import { activateFullSceneTree } from '../utils/test-utils'; @@ -89,11 +90,14 @@ describe('GeneralSettingsEditView', () => { expect(settings.getRefreshPicker()?.state?.intervals).toEqual(['5s']); }); - it('A change to folder updates the dashboard state', () => { - settings.onFolderChange('folder-2', 'folder 2'); + it('A change to folder updates the dashboard state', async () => { + const updateNavModel = jest.spyOn(utils, 'updateNavModel').mockImplementation(jest.fn()); + + await settings.onFolderChange('folder-2', 'folder 2'); expect(dashboard.state.meta.folderUid).toBe('folder-2'); expect(dashboard.state.meta.folderTitle).toBe('folder 2'); + expect(updateNavModel).toHaveBeenCalledWith('folder-2'); }); it('A change to tooltip settings updates the dashboard state', () => { diff --git a/public/app/features/dashboard-scene/settings/GeneralSettingsEditView.tsx b/public/app/features/dashboard-scene/settings/GeneralSettingsEditView.tsx index 8c787cda9cb..669dcc109d8 100644 --- a/public/app/features/dashboard-scene/settings/GeneralSettingsEditView.tsx +++ b/public/app/features/dashboard-scene/settings/GeneralSettingsEditView.tsx @@ -23,6 +23,7 @@ import { DeleteDashboardButton } from 'app/features/dashboard/components/DeleteD import { GenAIDashDescriptionButton } from 'app/features/dashboard/components/GenAI/GenAIDashDescriptionButton'; import { GenAIDashTitleButton } from 'app/features/dashboard/components/GenAI/GenAIDashTitleButton'; +import { updateNavModel } from '../pages/utils'; import { DashboardScene } from '../scene/DashboardScene'; import { NavToolbarActions } from '../scene/NavToolbarActions'; import { dashboardSceneGraph } from '../utils/dashboardSceneGraph'; @@ -96,13 +97,17 @@ export class GeneralSettingsEditView this._dashboard.setState({ tags: value }); }; - public onFolderChange = (newUID: string | undefined, newTitle: string | undefined) => { + public onFolderChange = async (newUID: string | undefined, newTitle: string | undefined) => { const newMeta = { ...this._dashboard.state.meta, folderUid: newUID || this._dashboard.state.meta.folderUid, folderTitle: newTitle || this._dashboard.state.meta.folderTitle, }; + if (newMeta.folderUid) { + await updateNavModel(newMeta.folderUid); + } + this._dashboard.setState({ meta: newMeta }); };