From 5423e75bf38eec5756f4ff2a1edf43edaf4018d6 Mon Sep 17 00:00:00 2001 From: Laura Benz <48948963+L-M-K-B@users.noreply.github.com> Date: Mon, 16 Oct 2023 12:03:35 +0200 Subject: [PATCH] Nav: Replace cloneDeep() in MegaMenu (#76607) * refactor: remove deep clone of nav tree * refactor: fix mutation issue --- .../AppChrome/DockedMegaMenu/MegaMenu.tsx | 5 +---- .../components/AppChrome/DockedMegaMenu/utils.ts | 14 ++++++++------ 2 files changed, 9 insertions(+), 10 deletions(-) diff --git a/public/app/core/components/AppChrome/DockedMegaMenu/MegaMenu.tsx b/public/app/core/components/AppChrome/DockedMegaMenu/MegaMenu.tsx index 0c7b5ce2f07..89978940c2f 100644 --- a/public/app/core/components/AppChrome/DockedMegaMenu/MegaMenu.tsx +++ b/public/app/core/components/AppChrome/DockedMegaMenu/MegaMenu.tsx @@ -1,6 +1,5 @@ import { css } from '@emotion/css'; import { DOMAttributes } from '@react-types/shared'; -import { cloneDeep } from 'lodash'; import React, { forwardRef } from 'react'; import { useLocation } from 'react-router-dom'; @@ -22,14 +21,12 @@ export interface Props extends DOMAttributes { export const MegaMenu = React.memo( forwardRef(({ onClose, ...restProps }, ref) => { - const navBarTree = useSelector((state) => state.navBarTree); + const navTree = useSelector((state) => state.navBarTree); const styles = useStyles2(getStyles); const location = useLocation(); const { chrome } = useGrafana(); const state = chrome.useState(); - const navTree = cloneDeep(navBarTree); - // Remove profile + help from tree const navItems = navTree .filter((item) => item.id !== 'profile' && item.id !== 'help') diff --git a/public/app/core/components/AppChrome/DockedMegaMenu/utils.ts b/public/app/core/components/AppChrome/DockedMegaMenu/utils.ts index 2f180c5e674..89384f0eb6c 100644 --- a/public/app/core/components/AppChrome/DockedMegaMenu/utils.ts +++ b/public/app/core/components/AppChrome/DockedMegaMenu/utils.ts @@ -30,18 +30,20 @@ export const enrichHelpItem = (helpItem: NavModelItem) => { }; export const enrichWithInteractionTracking = (item: NavModelItem, expandedState: boolean) => { - const onClick = item.onClick; - item.onClick = () => { + // creating a new object here to not mutate the original item object + const newItem = { ...item }; + const onClick = newItem.onClick; + newItem.onClick = () => { reportInteraction('grafana_navigation_item_clicked', { - path: item.url ?? item.id, + path: newItem.url ?? newItem.id, state: expandedState ? 'expanded' : 'collapsed', }); onClick?.(); }; - if (item.children) { - item.children = item.children.map((item) => enrichWithInteractionTracking(item, expandedState)); + if (newItem.children) { + newItem.children = newItem.children.map((item) => enrichWithInteractionTracking(item, expandedState)); } - return item; + return newItem; }; export const isMatchOrChildMatch = (itemToCheck: NavModelItem, searchItem?: NavModelItem) => {