Index: modules/system/system.module =================================================================== RCS file: /cvs/drupal/drupal/modules/system/system.module,v retrieving revision 1.654 diff -u -p -r1.654 system.module --- modules/system/system.module 28 Dec 2008 19:11:31 -0000 1.654 +++ modules/system/system.module 31 Dec 2008 00:36:28 -0000 @@ -425,7 +425,8 @@ function system_menu() { 'position' => 'left', 'weight' => -10, 'page callback' => 'system_admin_menu_block_page', - 'access arguments' => array('access administration pages'), + 'access callback' => 'system_admin_menu_block_access', + 'access arguments' => array('admin/content', 'access administration pages'), ); // menu items that are basically just menu blocks @@ -435,7 +436,8 @@ function system_menu() { 'position' => 'right', 'weight' => -5, 'page callback' => 'system_settings_overview', - 'access arguments' => array('access administration pages'), + 'access callback' => 'system_admin_menu_block_access', + 'access arguments' => array('admin/settings', 'access administration pages'), ); $items['admin/build'] = array( 'title' => 'Site building', @@ -443,7 +445,8 @@ function system_menu() { 'position' => 'right', 'weight' => -10, 'page callback' => 'system_admin_menu_block_page', - 'access arguments' => array('access administration pages'), + 'access callback' => 'system_admin_menu_block_access', + 'access arguments' => array('admin/build', 'access administration pages'), ); $items['admin/settings/admin'] = array( 'title' => 'Administration theme', @@ -667,7 +670,8 @@ function system_menu() { 'title' => 'Reports', 'description' => 'View reports from system logs and other status information.', 'page callback' => 'system_admin_menu_block_page', - 'access arguments' => array('access site reports'), + 'access callback' => 'system_admin_menu_block_access', + 'access arguments' => array('admin/reports', 'access site reports'), 'weight' => 5, 'position' => 'left', ); @@ -727,6 +731,25 @@ function _system_themes_access($theme) { } /** + * Menu item access callback - hides empty system settings overview pages. + * + * @param $path + * The path of the menu item to check for child menu entries. + * @param $string + * The permission, such as "administer nodes", being checked for. + * @return + * Boolean TRUE if the current user has the requested permission and the + * current menu item has children. + */ +function system_admin_menu_block_access($path, $permission) { + if (!user_access($permission)) { + return FALSE; + } + $content = system_admin_menu_block(array('path' => $path)); + return !empty($content); +} + +/** * Implementation of hook_init(). */ function system_init() { @@ -895,10 +918,14 @@ function system_block_view($delta = '') * The menu item to be displayed. */ function system_admin_menu_block($item) { - $content = array(); + static $cache; if (!isset($item['mlid'])) { $item += db_fetch_array(db_query("SELECT mlid, menu_name FROM {menu_links} ml WHERE ml.router_path = '%s' AND module = 'system'", $item['path'])); } + else if (isset($cache[$item['mlid']])) { + return $cache[$item['mlid']]; + } + $content = array(); $result = db_query(" SELECT m.load_functions, m.to_arg_functions, m.access_callback, m.access_arguments, m.page_callback, m.page_arguments, m.title, m.title_callback, m.title_arguments, m.type, m.description, ml.* FROM {menu_links} ml @@ -919,6 +946,7 @@ function system_admin_menu_block($item) $content[(50000 + $item['weight']) . ' ' . $item['title'] . ' ' . $item['mlid']] = $item; } ksort($content); + $cache[$item['mlid']] = $content; return $content; } Index: modules/system/system.test =================================================================== RCS file: /cvs/drupal/drupal/modules/system/system.test,v retrieving revision 1.33 diff -u -p -r1.33 system.test --- modules/system/system.test 30 Dec 2008 16:43:19 -0000 1.33 +++ modules/system/system.test 31 Dec 2008 01:37:09 -0000 @@ -289,10 +289,10 @@ class CronRunTestCase extends DrupalWebT } } +/** + * Test administration pages and categories. + */ class AdminOverviewTestCase extends DrupalWebTestCase { - /** - * Implementation of getInfo(). - */ function getInfo() { return array( 'name' => t('Admin overview'), @@ -354,6 +354,26 @@ class AdminOverviewTestCase extends Drup $this->assertFalse($extra, t('No extra panels found.')); } } + + /** + * Test administrative menu categories. + */ + function testHideEmptyCategories() { + $user = $this->drupalCreateUser(array('administer nodes', 'access administration pages')); + $this->drupalLogin($user); + + $this->drupalGet('admin'); + + // Assert that menu items with children are displayed. + $this->assertLink(t('Administer')); + $this->assertLink(t('Content management')); + + // Assert that menu items without children are hidden. + $this->assertNoLink(t('Site building')); + $this->assertNoLink(t('Site configuration')); + $this->assertNoLink(t('User management')); + $this->assertNoLink(t('Reports')); + } } class AdminMetaTagTestCase extends DrupalWebTestCase { Index: modules/user/user.module =================================================================== RCS file: /cvs/drupal/drupal/modules/user/user.module,v retrieving revision 1.951 diff -u -p -r1.951 user.module --- modules/user/user.module 30 Dec 2008 16:43:20 -0000 1.951 +++ modules/user/user.module 31 Dec 2008 00:48:04 -0000 @@ -1015,7 +1015,8 @@ function user_menu() { 'description' => "Manage your site's users, groups and access to site features.", 'position' => 'left', 'page callback' => 'system_admin_menu_block_page', - 'access arguments' => array('access administration pages'), + 'access callback' => 'system_admin_menu_block_access', + 'access arguments' => array('admin/user', 'access administration pages'), ); $items['admin/user/user'] = array( 'title' => 'Users',