Navigation: Prevent app crash when importing a dashboard with a uid of home (#59874)

* change home id to be more unique, refactor so that home circular reference is never created

* prefix starred dashboards

* update reducer
This commit is contained in:
Ashley Harrison
2022-12-09 12:54:00 +00:00
committed by GitHub
parent 4730be8842
commit a589929c92
3 changed files with 14 additions and 10 deletions

View File

@@ -342,7 +342,7 @@ func (s *ServiceImpl) buildStarredItemsNavLinks(c *models.ReqContext) ([]*navtre
}) })
for _, starredItem := range starredDashboards { for _, starredItem := range starredDashboards {
starredItemsChildNavs = append(starredItemsChildNavs, &navtree.NavLink{ starredItemsChildNavs = append(starredItemsChildNavs, &navtree.NavLink{
Id: starredItem.Uid, Id: "starred/" + starredItem.Uid,
Text: starredItem.Title, Text: starredItem.Title,
Url: starredItem.GetUrl(), Url: starredItem.GetUrl(),
}) })

View File

@@ -5,6 +5,9 @@ import { config } from '@grafana/runtime';
export const initialState: NavModelItem[] = config.bootData?.navTree ?? []; export const initialState: NavModelItem[] = config.bootData?.navTree ?? [];
// this matches the prefix set in the backend navtree
export const ID_PREFIX = 'starred/';
const navTreeSlice = createSlice({ const navTreeSlice = createSlice({
name: 'navBarTree', name: 'navBarTree',
initialState, initialState,
@@ -18,14 +21,14 @@ const navTreeSlice = createSlice({
starredItems.children = []; starredItems.children = [];
} }
const newStarredItem: NavModelItem = { const newStarredItem: NavModelItem = {
id, id: ID_PREFIX + id,
text: title, text: title,
url, url,
}; };
starredItems.children.push(newStarredItem); starredItems.children.push(newStarredItem);
starredItems.children.sort((a, b) => a.text.localeCompare(b.text)); starredItems.children.sort((a, b) => a.text.localeCompare(b.text));
} else { } else {
const index = starredItems.children?.findIndex((item) => item.id === id) ?? -1; const index = starredItems.children?.findIndex((item) => item.id === ID_PREFIX + id) ?? -1;
if (index > -1) { if (index > -1) {
starredItems?.children?.splice(index, 1); starredItems?.children?.splice(index, 1);
} }

View File

@@ -10,14 +10,13 @@ export function buildInitialState(): NavIndex {
const navIndex: NavIndex = {}; const navIndex: NavIndex = {};
const rootNodes = cloneDeep(config.bootData.navTree); const rootNodes = cloneDeep(config.bootData.navTree);
const homeNav = rootNodes.find((node) => node.id === HOME_NAV_ID); const homeNav = rootNodes.find((node) => node.id === HOME_NAV_ID);
const otherRootNodes = rootNodes.filter((node) => node.id !== HOME_NAV_ID);
// set home as parent for the rootNodes if (homeNav) {
buildNavIndex(navIndex, rootNodes, homeNav); buildNavIndex(navIndex, [homeNav]);
// remove circular parent reference on the home node
if (navIndex[HOME_NAV_ID]) {
delete navIndex[HOME_NAV_ID].parentItem;
} }
// set home as parent for the other rootNodes
buildNavIndex(navIndex, otherRootNodes, homeNav);
return navIndex; return navIndex;
} }
@@ -26,7 +25,9 @@ function buildNavIndex(navIndex: NavIndex, children: NavModelItem[], parentItem?
for (const node of children) { for (const node of children) {
node.parentItem = parentItem; node.parentItem = parentItem;
navIndex[node.id!] = node; if (node.id) {
navIndex[node.id] = node;
}
if (node.children) { if (node.children) {
buildNavIndex(navIndex, node.children, node); buildNavIndex(navIndex, node.children, node);