mirror of
https://github.com/grafana/grafana.git
synced 2025-02-25 18:55:37 -06:00
Chore: Clean up old navigation (#66287)
* remove code outside of the topnav feature flag * delete NavBar folder * remove topnav toggle from backend * restructure AppChrome folder * fix utils mock * fix applinks tests * remove tests since they're covered in e2e * fix 1 of the approotpage tests * Fix another dashboardpage test * remove reverse portalling + test for plugins using deprecated onNavChanged method * kick drone * handle correlations
This commit is contained in:
@@ -104,12 +104,7 @@ func (hs *HTTPServer) registerRoutes() {
|
||||
r.Get("/configuration", reqGrafanaAdmin, hs.Index)
|
||||
r.Get("/admin", reqOrgAdmin, hs.Index)
|
||||
r.Get("/admin/settings", authorize(reqGrafanaAdmin, ac.EvalPermission(ac.ActionSettingsRead)), hs.Index)
|
||||
// Show the combined users page for org admins if topnav is enabled
|
||||
if hs.Features.IsEnabled(featuremgmt.FlagTopnav) {
|
||||
r.Get("/admin/users", authorize(reqSignedIn, ac.EvalAny(ac.EvalPermission(ac.ActionOrgUsersRead), ac.EvalPermission(ac.ActionUsersRead, ac.ScopeGlobalUsersAll))), hs.Index)
|
||||
} else {
|
||||
r.Get("/admin/users", authorize(reqGrafanaAdmin, ac.EvalPermission(ac.ActionUsersRead, ac.ScopeGlobalUsersAll)), hs.Index)
|
||||
}
|
||||
r.Get("/admin/users", authorize(reqSignedIn, ac.EvalAny(ac.EvalPermission(ac.ActionOrgUsersRead), ac.EvalPermission(ac.ActionUsersRead, ac.ScopeGlobalUsersAll))), hs.Index)
|
||||
r.Get("/admin/users/create", authorize(reqGrafanaAdmin, ac.EvalPermission(ac.ActionUsersCreate)), hs.Index)
|
||||
r.Get("/admin/users/edit/:id", authorize(reqGrafanaAdmin, ac.EvalPermission(ac.ActionUsersRead)), hs.Index)
|
||||
r.Get("/admin/orgs", authorizeInOrg(reqGrafanaAdmin, ac.UseGlobalOrg, ac.OrgsAccessEvaluator), hs.Index)
|
||||
|
||||
@@ -166,8 +166,8 @@ func (hs *HTTPServer) setIndexViewData(c *contextmodel.ReqContext) (*dtos.IndexV
|
||||
|
||||
hs.HooksService.RunIndexDataHooks(&data, c)
|
||||
|
||||
// This will remove empty cfg or admin sections and move sections around if topnav is enabled
|
||||
data.NavTree.RemoveEmptySectionsAndApplyNewInformationArchitecture(hs.Features.IsEnabled(featuremgmt.FlagTopnav))
|
||||
// This will remove empty cfg or admin sections and move sections around
|
||||
data.NavTree.RemoveEmptySectionsAndApplyNewInformationArchitecture()
|
||||
data.NavTree.Sort()
|
||||
|
||||
return &data, nil
|
||||
|
||||
@@ -59,15 +59,7 @@ func ProvideService(cfg *setting.Cfg, hooksService *hooks.HooksService) *OSSLice
|
||||
return
|
||||
}
|
||||
|
||||
var adminNodeID string
|
||||
|
||||
if cfg.IsFeatureToggleEnabled("topnav") {
|
||||
adminNodeID = navtree.NavIDCfg
|
||||
} else {
|
||||
adminNodeID = navtree.NavIDAdmin
|
||||
}
|
||||
|
||||
if adminNode := indexData.NavTree.FindById(adminNodeID); adminNode != nil {
|
||||
if adminNode := indexData.NavTree.FindById(navtree.NavIDCfg); adminNode != nil {
|
||||
adminNode.Children = append(adminNode.Children, &navtree.NavLink{
|
||||
Text: "Stats and license",
|
||||
Id: "upgrading",
|
||||
|
||||
@@ -100,7 +100,7 @@ func (root *NavTreeRoot) FindById(id string) *NavLink {
|
||||
return FindById(root.Children, id)
|
||||
}
|
||||
|
||||
func (root *NavTreeRoot) RemoveEmptySectionsAndApplyNewInformationArchitecture(topNavEnabled bool) {
|
||||
func (root *NavTreeRoot) RemoveEmptySectionsAndApplyNewInformationArchitecture() {
|
||||
// Remove server admin node if it has no children or set the url to first child
|
||||
if node := root.FindById(NavIDAdmin); node != nil {
|
||||
if len(node.Children) == 0 {
|
||||
@@ -110,31 +110,26 @@ func (root *NavTreeRoot) RemoveEmptySectionsAndApplyNewInformationArchitecture(t
|
||||
}
|
||||
}
|
||||
|
||||
if topNavEnabled {
|
||||
ApplyAdminIA(root)
|
||||
ApplyAdminIA(root)
|
||||
|
||||
// Move reports into dashboards
|
||||
if reports := root.FindById(NavIDReporting); reports != nil {
|
||||
if dashboards := root.FindById(NavIDDashboards); dashboards != nil {
|
||||
reports.SortWeight = 0
|
||||
dashboards.Children = append(dashboards.Children, reports)
|
||||
root.RemoveSection(reports)
|
||||
}
|
||||
}
|
||||
|
||||
// Change id of dashboards
|
||||
// Move reports into dashboards
|
||||
if reports := root.FindById(NavIDReporting); reports != nil {
|
||||
if dashboards := root.FindById(NavIDDashboards); dashboards != nil {
|
||||
dashboards.Id = "dashboards/browse"
|
||||
reports.SortWeight = 0
|
||||
dashboards.Children = append(dashboards.Children, reports)
|
||||
root.RemoveSection(reports)
|
||||
}
|
||||
}
|
||||
|
||||
// Remove top level cfg / administration node if it has no children (needs to be after topnav new info archicture logic above that moves server admin into it)
|
||||
// Remove server admin node if it has no children or set the url to first child
|
||||
// Change id of dashboards
|
||||
if dashboards := root.FindById(NavIDDashboards); dashboards != nil {
|
||||
dashboards.Id = "dashboards/browse"
|
||||
}
|
||||
|
||||
// Remove top level cfg / administration node if it has no children
|
||||
if node := root.FindById(NavIDCfg); node != nil {
|
||||
if len(node.Children) == 0 {
|
||||
root.RemoveSection(node)
|
||||
} else if !topNavEnabled {
|
||||
node.Url = node.Children[0].Url
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -15,25 +15,12 @@ func TestNavTreeRoot(t *testing.T) {
|
||||
},
|
||||
}
|
||||
|
||||
treeRoot.RemoveEmptySectionsAndApplyNewInformationArchitecture(false)
|
||||
treeRoot.RemoveEmptySectionsAndApplyNewInformationArchitecture()
|
||||
|
||||
require.Equal(t, 0, len(treeRoot.Children))
|
||||
})
|
||||
|
||||
t.Run("Should not remove admin sections when they have children", func(t *testing.T) {
|
||||
treeRoot := NavTreeRoot{
|
||||
Children: []*NavLink{
|
||||
{Id: NavIDCfg, Children: []*NavLink{{Id: "child"}}},
|
||||
{Id: NavIDAdmin, Children: []*NavLink{{Id: "child"}}},
|
||||
},
|
||||
}
|
||||
|
||||
treeRoot.RemoveEmptySectionsAndApplyNewInformationArchitecture(false)
|
||||
|
||||
require.Equal(t, 2, len(treeRoot.Children))
|
||||
})
|
||||
|
||||
t.Run("Should create 3 new sections in the Admin node when topnav is enabled", func(t *testing.T) {
|
||||
t.Run("Should create 3 new sections in the Admin node", func(t *testing.T) {
|
||||
treeRoot := NavTreeRoot{
|
||||
Children: []*NavLink{
|
||||
{Id: NavIDCfg},
|
||||
@@ -41,7 +28,7 @@ func TestNavTreeRoot(t *testing.T) {
|
||||
},
|
||||
}
|
||||
|
||||
treeRoot.RemoveEmptySectionsAndApplyNewInformationArchitecture(true)
|
||||
treeRoot.RemoveEmptySectionsAndApplyNewInformationArchitecture()
|
||||
|
||||
require.Equal(t, "Administration", treeRoot.Children[0].Text)
|
||||
})
|
||||
@@ -54,7 +41,7 @@ func TestNavTreeRoot(t *testing.T) {
|
||||
},
|
||||
}
|
||||
|
||||
treeRoot.RemoveEmptySectionsAndApplyNewInformationArchitecture(true)
|
||||
treeRoot.RemoveEmptySectionsAndApplyNewInformationArchitecture()
|
||||
|
||||
require.Equal(t, NavIDReporting, treeRoot.Children[0].Children[0].Id)
|
||||
})
|
||||
|
||||
@@ -36,18 +36,6 @@ func (s *ServiceImpl) getOrgAdminNode(c *contextmodel.ReqContext) (*navtree.NavL
|
||||
})
|
||||
}
|
||||
|
||||
if !s.features.IsEnabled(featuremgmt.FlagTopnav) {
|
||||
if hasAccess(ac.ReqOrgAdmin, ac.EvalPermission(ac.ActionOrgUsersRead)) {
|
||||
configNodes = append(configNodes, &navtree.NavLink{
|
||||
Text: "Users",
|
||||
Id: "users",
|
||||
SubTitle: "Invite and assign roles to users",
|
||||
Icon: "user",
|
||||
Url: s.cfg.AppSubURL + "/org/users",
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
if hasAccess(s.ReqCanAdminTeams, ac.TeamsAccessEvaluator) {
|
||||
configNodes = append(configNodes, &navtree.NavLink{
|
||||
Text: "Teams",
|
||||
@@ -122,18 +110,10 @@ func (s *ServiceImpl) getServerAdminNode(c *contextmodel.ReqContext) *navtree.Na
|
||||
orgsAccessEvaluator := ac.EvalPermission(ac.ActionOrgsRead)
|
||||
adminNavLinks := []*navtree.NavLink{}
|
||||
|
||||
if s.features.IsEnabled(featuremgmt.FlagTopnav) {
|
||||
if hasAccess(ac.ReqSignedIn, ac.EvalAny(ac.EvalPermission(ac.ActionOrgUsersRead), ac.EvalPermission(ac.ActionUsersRead, ac.ScopeGlobalUsersAll))) {
|
||||
adminNavLinks = append(adminNavLinks, &navtree.NavLink{
|
||||
Text: "Users", SubTitle: "Manage users in Grafana", Id: "global-users", Url: s.cfg.AppSubURL + "/admin/users", Icon: "user",
|
||||
})
|
||||
}
|
||||
} else {
|
||||
if hasAccess(ac.ReqGrafanaAdmin, ac.EvalPermission(ac.ActionUsersRead, ac.ScopeGlobalUsersAll)) {
|
||||
adminNavLinks = append(adminNavLinks, &navtree.NavLink{
|
||||
Text: "Users", SubTitle: "Manage and create users across the whole Grafana server", Id: "global-users", Url: s.cfg.AppSubURL + "/admin/users", Icon: "user",
|
||||
})
|
||||
}
|
||||
if hasAccess(ac.ReqSignedIn, ac.EvalAny(ac.EvalPermission(ac.ActionOrgUsersRead), ac.EvalPermission(ac.ActionUsersRead, ac.ScopeGlobalUsersAll))) {
|
||||
adminNavLinks = append(adminNavLinks, &navtree.NavLink{
|
||||
Text: "Users", SubTitle: "Manage users in Grafana", Id: "global-users", Url: s.cfg.AppSubURL + "/admin/users", Icon: "user",
|
||||
})
|
||||
}
|
||||
|
||||
authConfigUIAvailable := s.license.FeatureEnabled("saml") && s.features.IsEnabled(featuremgmt.FlagAuthenticationConfigUI)
|
||||
|
||||
@@ -16,7 +16,6 @@ import (
|
||||
)
|
||||
|
||||
func (s *ServiceImpl) addAppLinks(treeRoot *navtree.NavTreeRoot, c *contextmodel.ReqContext) error {
|
||||
topNavEnabled := s.features.IsEnabled(featuremgmt.FlagTopnav)
|
||||
hasAccess := ac.HasAccess(s.accessControl, c)
|
||||
appLinks := []*navtree.NavLink{}
|
||||
|
||||
@@ -47,7 +46,7 @@ func (s *ServiceImpl) addAppLinks(treeRoot *navtree.NavTreeRoot, c *contextmodel
|
||||
continue
|
||||
}
|
||||
|
||||
if appNode := s.processAppPlugin(plugin, c, topNavEnabled, treeRoot); appNode != nil {
|
||||
if appNode := s.processAppPlugin(plugin, c, treeRoot); appNode != nil {
|
||||
appLinks = append(appLinks, appNode)
|
||||
}
|
||||
}
|
||||
@@ -65,7 +64,7 @@ func (s *ServiceImpl) addAppLinks(treeRoot *navtree.NavTreeRoot, c *contextmodel
|
||||
return nil
|
||||
}
|
||||
|
||||
func (s *ServiceImpl) processAppPlugin(plugin plugins.PluginDTO, c *contextmodel.ReqContext, topNavEnabled bool, treeRoot *navtree.NavTreeRoot) *navtree.NavLink {
|
||||
func (s *ServiceImpl) processAppPlugin(plugin plugins.PluginDTO, c *contextmodel.ReqContext, treeRoot *navtree.NavTreeRoot) *navtree.NavLink {
|
||||
hasAccessToInclude := s.hasAccessToInclude(c, plugin.ID)
|
||||
appLink := &navtree.NavLink{
|
||||
Text: plugin.Name,
|
||||
@@ -76,12 +75,7 @@ func (s *ServiceImpl) processAppPlugin(plugin plugins.PluginDTO, c *contextmodel
|
||||
SortWeight: navtree.WeightPlugin,
|
||||
IsSection: true,
|
||||
PluginID: plugin.ID,
|
||||
}
|
||||
|
||||
if topNavEnabled {
|
||||
appLink.Url = s.cfg.AppSubURL + "/a/" + plugin.ID
|
||||
} else {
|
||||
appLink.Url = path.Join(s.cfg.AppSubURL, plugin.DefaultNavURL)
|
||||
Url: s.cfg.AppSubURL + "/a/" + plugin.ID,
|
||||
}
|
||||
|
||||
for _, include := range plugin.Includes {
|
||||
@@ -159,10 +153,6 @@ func (s *ServiceImpl) processAppPlugin(plugin plugins.PluginDTO, c *contextmodel
|
||||
appLink.Children = []*navtree.NavLink{}
|
||||
}
|
||||
|
||||
if !topNavEnabled {
|
||||
return appLink
|
||||
}
|
||||
|
||||
// Remove default nav child
|
||||
childrenWithoutDefault := []*navtree.NavLink{}
|
||||
for _, child := range appLink.Children {
|
||||
|
||||
@@ -119,17 +119,7 @@ func TestAddAppLinks(t *testing.T) {
|
||||
},
|
||||
}
|
||||
|
||||
t.Run("Should add enabled apps with pages", func(t *testing.T) {
|
||||
treeRoot := navtree.NavTreeRoot{}
|
||||
err := service.addAppLinks(&treeRoot, reqCtx)
|
||||
require.NoError(t, err)
|
||||
require.Equal(t, "Test app1 name", treeRoot.Children[0].Text)
|
||||
require.Equal(t, "/a/test-app1/catalog", treeRoot.Children[0].Url)
|
||||
require.Equal(t, "/a/test-app1/page2", treeRoot.Children[0].Children[1].Url)
|
||||
})
|
||||
|
||||
t.Run("Should move apps to Apps category when topnav is enabled", func(t *testing.T) {
|
||||
service.features = featuremgmt.WithFeatures(featuremgmt.FlagTopnav)
|
||||
t.Run("Should move apps to Apps category", func(t *testing.T) {
|
||||
treeRoot := navtree.NavTreeRoot{}
|
||||
err := service.addAppLinks(&treeRoot, reqCtx)
|
||||
require.NoError(t, err)
|
||||
@@ -141,8 +131,17 @@ func TestAddAppLinks(t *testing.T) {
|
||||
require.Equal(t, testApp1.Name, appsNode.Children[0].Text)
|
||||
})
|
||||
|
||||
t.Run("Should remove the default nav child (DefaultNav=true) when topnav is enabled and should set its URL to the plugin nav root", func(t *testing.T) {
|
||||
service.features = featuremgmt.WithFeatures(featuremgmt.FlagTopnav)
|
||||
t.Run("Should add enabled apps with pages", func(t *testing.T) {
|
||||
treeRoot := navtree.NavTreeRoot{}
|
||||
err := service.addAppLinks(&treeRoot, reqCtx)
|
||||
require.NoError(t, err)
|
||||
appsNode := treeRoot.FindById(navtree.NavIDApps)
|
||||
require.Equal(t, "Test app1 name", appsNode.Children[0].Text)
|
||||
require.Equal(t, "/a/test-app1/catalog", appsNode.Children[0].Url)
|
||||
require.Equal(t, "/a/test-app1/page2", appsNode.Children[0].Children[0].Url)
|
||||
})
|
||||
|
||||
t.Run("Should remove the default nav child (DefaultNav=true) and should set its URL to the plugin nav root", func(t *testing.T) {
|
||||
treeRoot := navtree.NavTreeRoot{}
|
||||
err := service.addAppLinks(&treeRoot, reqCtx)
|
||||
require.NoError(t, err)
|
||||
@@ -155,7 +154,6 @@ func TestAddAppLinks(t *testing.T) {
|
||||
|
||||
// This can be done by using `[navigation.app_sections]` in the INI config
|
||||
t.Run("Should move apps that have root nav id configured to the root", func(t *testing.T) {
|
||||
service.features = featuremgmt.WithFeatures(featuremgmt.FlagTopnav)
|
||||
service.navigationAppConfig = map[string]NavigationAppConfig{
|
||||
"test-app1": {SectionID: navtree.NavIDRoot},
|
||||
}
|
||||
@@ -179,7 +177,6 @@ func TestAddAppLinks(t *testing.T) {
|
||||
|
||||
// This can be done by using `[navigation.app_sections]` in the INI config
|
||||
t.Run("Should move apps that have specific nav id configured to correct section", func(t *testing.T) {
|
||||
service.features = featuremgmt.WithFeatures(featuremgmt.FlagTopnav)
|
||||
service.navigationAppConfig = map[string]NavigationAppConfig{
|
||||
"test-app1": {SectionID: navtree.NavIDAdmin},
|
||||
}
|
||||
@@ -207,7 +204,6 @@ func TestAddAppLinks(t *testing.T) {
|
||||
})
|
||||
|
||||
t.Run("Should only add a 'Monitoring' section if a plugin exists that wants to live there", func(t *testing.T) {
|
||||
service.features = featuremgmt.WithFeatures(featuremgmt.FlagTopnav)
|
||||
service.navigationAppConfig = map[string]NavigationAppConfig{}
|
||||
|
||||
// Check if the Monitoring section is not there if no apps try to register to it
|
||||
@@ -231,7 +227,6 @@ func TestAddAppLinks(t *testing.T) {
|
||||
})
|
||||
|
||||
t.Run("Should add a 'Alerts and Incidents' section if a plugin exists that wants to live there", func(t *testing.T) {
|
||||
service.features = featuremgmt.WithFeatures(featuremgmt.FlagTopnav)
|
||||
service.navigationAppConfig = map[string]NavigationAppConfig{}
|
||||
|
||||
// Check if the 'Alerts and Incidents' section is not there if no apps try to register to it
|
||||
@@ -257,7 +252,6 @@ func TestAddAppLinks(t *testing.T) {
|
||||
})
|
||||
|
||||
t.Run("Should add a 'Alerts and Incidents' section if a plugin exists that wants to live there even without an alerting node", func(t *testing.T) {
|
||||
service.features = featuremgmt.WithFeatures(featuremgmt.FlagTopnav)
|
||||
service.navigationAppConfig = map[string]NavigationAppConfig{}
|
||||
|
||||
// Check if the 'Alerts and Incidents' section is not there if no apps try to register to it
|
||||
@@ -281,7 +275,6 @@ func TestAddAppLinks(t *testing.T) {
|
||||
})
|
||||
|
||||
t.Run("Should be able to control app sort order with SortWeight (smaller SortWeight displayed first)", func(t *testing.T) {
|
||||
service.features = featuremgmt.WithFeatures(featuremgmt.FlagTopnav)
|
||||
service.navigationAppConfig = map[string]NavigationAppConfig{
|
||||
"test-app2": {SectionID: navtree.NavIDMonitoring, SortWeight: 2},
|
||||
"test-app1": {SectionID: navtree.NavIDMonitoring, SortWeight: 3},
|
||||
@@ -300,7 +293,7 @@ func TestAddAppLinks(t *testing.T) {
|
||||
})
|
||||
|
||||
t.Run("Should replace page from plugin", func(t *testing.T) {
|
||||
service.features = featuremgmt.WithFeatures(featuremgmt.FlagTopnav, featuremgmt.FlagDataConnectionsConsole)
|
||||
service.features = featuremgmt.WithFeatures(featuremgmt.FlagDataConnectionsConsole)
|
||||
service.navigationAppConfig = map[string]NavigationAppConfig{}
|
||||
service.navigationAppPathConfig = map[string]NavigationAppConfig{
|
||||
"/connections/connect-data": {SectionID: "connections"},
|
||||
@@ -340,7 +333,7 @@ func TestAddAppLinks(t *testing.T) {
|
||||
})
|
||||
|
||||
t.Run("Should not register pages under the app plugin section unless AddToNav=true", func(t *testing.T) {
|
||||
service.features = featuremgmt.WithFeatures(featuremgmt.FlagTopnav, featuremgmt.FlagDataConnectionsConsole)
|
||||
service.features = featuremgmt.WithFeatures(featuremgmt.FlagDataConnectionsConsole)
|
||||
service.navigationAppPathConfig = map[string]NavigationAppConfig{} // We don't configure it as a standalone plugin page
|
||||
|
||||
treeRoot := navtree.NavTreeRoot{}
|
||||
@@ -466,11 +459,12 @@ func TestAddAppLinksAccessControl(t *testing.T) {
|
||||
|
||||
err := service.addAppLinks(&treeRoot, reqCtx)
|
||||
require.NoError(t, err)
|
||||
require.Len(t, treeRoot.Children, 1)
|
||||
require.Equal(t, "Test app1 name", treeRoot.Children[0].Text)
|
||||
require.Len(t, treeRoot.Children[0].Children, 2)
|
||||
require.Equal(t, "/a/test-app1/catalog", treeRoot.Children[0].Children[0].Url)
|
||||
require.Equal(t, "/a/test-app1/page2", treeRoot.Children[0].Children[1].Url)
|
||||
appsNode := treeRoot.FindById(navtree.NavIDApps)
|
||||
require.Len(t, appsNode.Children, 1)
|
||||
require.Equal(t, "Test app1 name", appsNode.Children[0].Text)
|
||||
require.Equal(t, "/a/test-app1/catalog", appsNode.Children[0].Url)
|
||||
require.Len(t, appsNode.Children[0].Children, 1)
|
||||
require.Equal(t, "/a/test-app1/page2", appsNode.Children[0].Children[0].Url)
|
||||
})
|
||||
t.Run("Should add one include when the user is a viewer", func(t *testing.T) {
|
||||
treeRoot := navtree.NavTreeRoot{}
|
||||
@@ -481,10 +475,11 @@ func TestAddAppLinksAccessControl(t *testing.T) {
|
||||
|
||||
err := service.addAppLinks(&treeRoot, reqCtx)
|
||||
require.NoError(t, err)
|
||||
require.Len(t, treeRoot.Children, 1)
|
||||
require.Equal(t, "Test app1 name", treeRoot.Children[0].Text)
|
||||
require.Len(t, treeRoot.Children[0].Children, 1)
|
||||
require.Equal(t, "/a/test-app1/page2", treeRoot.Children[0].Children[0].Url)
|
||||
appsNode := treeRoot.FindById(navtree.NavIDApps)
|
||||
require.Len(t, appsNode.Children, 1)
|
||||
require.Equal(t, "Test app1 name", appsNode.Children[0].Text)
|
||||
require.Len(t, appsNode.Children[0].Children, 1)
|
||||
require.Equal(t, "/a/test-app1/page2", appsNode.Children[0].Children[0].Url)
|
||||
})
|
||||
t.Run("Should add both includes when the user is a viewer with catalog read", func(t *testing.T) {
|
||||
treeRoot := navtree.NavTreeRoot{}
|
||||
@@ -496,11 +491,12 @@ func TestAddAppLinksAccessControl(t *testing.T) {
|
||||
|
||||
err := service.addAppLinks(&treeRoot, reqCtx)
|
||||
require.NoError(t, err)
|
||||
require.Len(t, treeRoot.Children, 1)
|
||||
require.Equal(t, "Test app1 name", treeRoot.Children[0].Text)
|
||||
require.Len(t, treeRoot.Children[0].Children, 2)
|
||||
require.Equal(t, "/a/test-app1/catalog", treeRoot.Children[0].Children[0].Url)
|
||||
require.Equal(t, "/a/test-app1/page2", treeRoot.Children[0].Children[1].Url)
|
||||
appsNode := treeRoot.FindById(navtree.NavIDApps)
|
||||
require.Len(t, appsNode.Children, 1)
|
||||
require.Equal(t, "Test app1 name", appsNode.Children[0].Text)
|
||||
require.Equal(t, "/a/test-app1/catalog", appsNode.Children[0].Url)
|
||||
require.Len(t, appsNode.Children[0].Children, 1)
|
||||
require.Equal(t, "/a/test-app1/page2", appsNode.Children[0].Children[0].Url)
|
||||
})
|
||||
t.Run("Should add one include when the user is an editor without catalog read", func(t *testing.T) {
|
||||
treeRoot := navtree.NavTreeRoot{}
|
||||
@@ -512,9 +508,10 @@ func TestAddAppLinksAccessControl(t *testing.T) {
|
||||
|
||||
err := service.addAppLinks(&treeRoot, reqCtx)
|
||||
require.NoError(t, err)
|
||||
require.Len(t, treeRoot.Children, 1)
|
||||
require.Equal(t, "Test app1 name", treeRoot.Children[0].Text)
|
||||
require.Len(t, treeRoot.Children[0].Children, 1)
|
||||
require.Equal(t, "/a/test-app1/page2", treeRoot.Children[0].Children[0].Url)
|
||||
appsNode := treeRoot.FindById(navtree.NavIDApps)
|
||||
require.Len(t, appsNode.Children, 1)
|
||||
require.Equal(t, "Test app1 name", appsNode.Children[0].Text)
|
||||
require.Len(t, appsNode.Children[0].Children, 1)
|
||||
require.Equal(t, "/a/test-app1/page2", appsNode.Children[0].Children[0].Url)
|
||||
})
|
||||
}
|
||||
|
||||
@@ -195,9 +195,6 @@ func (s *ServiceImpl) getHomeNode(c *contextmodel.ReqContext, prefs *pref.Prefer
|
||||
Section: navtree.NavSectionCore,
|
||||
SortWeight: navtree.WeightHome,
|
||||
}
|
||||
if !s.features.IsEnabled(featuremgmt.FlagTopnav) {
|
||||
homeNode.HideFromMenu = true
|
||||
}
|
||||
return homeNode
|
||||
}
|
||||
|
||||
@@ -345,12 +342,6 @@ func (s *ServiceImpl) buildDashboardNavLinks(c *contextmodel.ReqContext, hasEdit
|
||||
|
||||
dashboardChildNavs := []*navtree.NavLink{}
|
||||
|
||||
if !s.features.IsEnabled(featuremgmt.FlagTopnav) {
|
||||
dashboardChildNavs = append(dashboardChildNavs, &navtree.NavLink{
|
||||
Text: "Browse", Id: navtree.NavIDDashboardsBrowse, Url: s.cfg.AppSubURL + "/dashboards", Icon: "sitemap",
|
||||
})
|
||||
}
|
||||
|
||||
dashboardChildNavs = append(dashboardChildNavs, &navtree.NavLink{
|
||||
Text: "Playlists", SubTitle: "Groups of dashboards that are displayed in a sequence", Id: "dashboards/playlists", Url: s.cfg.AppSubURL + "/playlists", Icon: "presentation-play",
|
||||
})
|
||||
@@ -393,12 +384,6 @@ func (s *ServiceImpl) buildDashboardNavLinks(c *contextmodel.ReqContext, hasEdit
|
||||
})
|
||||
}
|
||||
|
||||
if hasEditPerm && !s.features.IsEnabled(featuremgmt.FlagTopnav) {
|
||||
dashboardChildNavs = append(dashboardChildNavs, &navtree.NavLink{
|
||||
Text: "Divider", Divider: true, Id: "divider", HideFromTabs: true,
|
||||
})
|
||||
}
|
||||
|
||||
if hasEditPerm {
|
||||
if hasAccess(hasEditPermInAnyFolder, ac.EvalPermission(dashboards.ActionDashboardsCreate)) {
|
||||
dashboardChildNavs = append(dashboardChildNavs, &navtree.NavLink{
|
||||
@@ -412,15 +397,6 @@ func (s *ServiceImpl) buildDashboardNavLinks(c *contextmodel.ReqContext, hasEdit
|
||||
}
|
||||
}
|
||||
|
||||
if hasEditPerm && !s.features.IsEnabled(featuremgmt.FlagTopnav) {
|
||||
if hasAccess(ac.ReqOrgAdminOrEditor, ac.EvalPermission(dashboards.ActionFoldersCreate)) {
|
||||
dashboardChildNavs = append(dashboardChildNavs, &navtree.NavLink{
|
||||
Text: "New folder", SubTitle: "Create a new folder to organize your dashboards", Id: "dashboards/folder/new",
|
||||
Icon: "plus", Url: s.cfg.AppSubURL + "/dashboards/folder/new", HideFromTabs: true, ShowIconInNavbar: true,
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
return dashboardChildNavs
|
||||
}
|
||||
|
||||
@@ -445,12 +421,7 @@ func (s *ServiceImpl) buildLegacyAlertNavLinks(c *contextmodel.ReqContext) *navt
|
||||
Children: alertChildNavs,
|
||||
Section: navtree.NavSectionCore,
|
||||
SortWeight: navtree.WeightAlerting,
|
||||
}
|
||||
|
||||
if s.features.IsEnabled(featuremgmt.FlagTopnav) {
|
||||
alertNav.Url = s.cfg.AppSubURL + "/alerting"
|
||||
} else {
|
||||
alertNav.Url = s.cfg.AppSubURL + "/alerting/list"
|
||||
Url: s.cfg.AppSubURL + "/alerting",
|
||||
}
|
||||
|
||||
return &alertNav
|
||||
@@ -460,15 +431,6 @@ func (s *ServiceImpl) buildAlertNavLinks(c *contextmodel.ReqContext, hasEditPerm
|
||||
hasAccess := ac.HasAccess(s.accessControl, c)
|
||||
var alertChildNavs []*navtree.NavLink
|
||||
|
||||
if !s.features.IsEnabled(featuremgmt.FlagTopnav) {
|
||||
alertChildNavs = append(alertChildNavs, &navtree.NavLink{
|
||||
Text: "Home",
|
||||
Id: "alert-home",
|
||||
Url: s.cfg.AppSubURL + "/alerting/home",
|
||||
Icon: "home",
|
||||
})
|
||||
}
|
||||
|
||||
if hasAccess(ac.ReqViewer, ac.EvalAny(ac.EvalPermission(ac.ActionAlertingRuleRead), ac.EvalPermission(ac.ActionAlertingRuleExternalRead))) {
|
||||
alertChildNavs = append(alertChildNavs, &navtree.NavLink{
|
||||
Text: "Alert rules", SubTitle: "Rules that determine whether an alert will fire", Id: "alert-list", Url: s.cfg.AppSubURL + "/alerting/list", Icon: "list-ul",
|
||||
@@ -498,12 +460,6 @@ func (s *ServiceImpl) buildAlertNavLinks(c *contextmodel.ReqContext, hasEditPerm
|
||||
fallbackHasEditPerm := func(*contextmodel.ReqContext) bool { return hasEditPerm }
|
||||
|
||||
if hasAccess(fallbackHasEditPerm, ac.EvalAny(ac.EvalPermission(ac.ActionAlertingRuleCreate), ac.EvalPermission(ac.ActionAlertingRuleExternalWrite))) {
|
||||
if !s.features.IsEnabled(featuremgmt.FlagTopnav) {
|
||||
alertChildNavs = append(alertChildNavs, &navtree.NavLink{
|
||||
Text: "Divider", Divider: true, Id: "divider", HideFromTabs: true,
|
||||
})
|
||||
}
|
||||
|
||||
alertChildNavs = append(alertChildNavs, &navtree.NavLink{
|
||||
Text: "Create alert rule", SubTitle: "Create an alert rule", Id: "alert",
|
||||
Icon: "plus", Url: s.cfg.AppSubURL + "/alerting/new", HideFromTabs: true, ShowIconInNavbar: true, IsCreateAction: true,
|
||||
@@ -519,12 +475,7 @@ func (s *ServiceImpl) buildAlertNavLinks(c *contextmodel.ReqContext, hasEditPerm
|
||||
Children: alertChildNavs,
|
||||
Section: navtree.NavSectionCore,
|
||||
SortWeight: navtree.WeightAlerting,
|
||||
}
|
||||
|
||||
if s.features.IsEnabled(featuremgmt.FlagTopnav) {
|
||||
alertNav.Url = s.cfg.AppSubURL + "/alerting"
|
||||
} else {
|
||||
alertNav.Url = s.cfg.AppSubURL + "/alerting/home"
|
||||
Url: s.cfg.AppSubURL + "/alerting",
|
||||
}
|
||||
|
||||
return &alertNav
|
||||
|
||||
Reference in New Issue
Block a user