From 3371102bb4e7c9b4227cdb4374f051dd00282a9e Mon Sep 17 00:00:00 2001 From: Brian Canini <canini.16@osu.edu> Date: Tue, 24 Mar 2020 15:36:15 -0400 Subject: [PATCH] Updating drupal/admin_toolbar (2.0.0 => 2.2.0) --- composer.json | 4 +- composer.lock | 21 +- vendor/composer/installed.json | 18 +- .../admin_toolbar/admin_toolbar.info.yml | 8 +- .../admin_toolbar/admin_toolbar.libraries.yml | 11 - .../admin_toolbar/admin_toolbar.module | 73 +--- ...admin_toolbar_links_access_filter.info.yml | 8 +- .../composer.json | 5 +- .../admin_toolbar_search.info.yml | 14 + .../admin_toolbar_search.libraries.yml | 11 + .../admin_toolbar_search.module | 79 ++++ .../admin_toolbar_search.permissions.yml | 2 + .../admin_toolbar_search.routing.yml | 6 + .../admin_toolbar_search.services.yml | 9 + .../admin_toolbar_search/composer.json | 39 ++ .../css/admin.toolbar_search.css | 33 ++ .../js/admin_toolbar_search.js | 188 ++++++++++ .../AdminToolbarSearchController.php | 50 +++ .../src/SearchLinks.php | 34 +- .../AdminToolbarSearchTest.php | 47 +++ .../AdminToolbarSearchTestBase.php | 192 ++++++++++ .../AdminToolbarToolsSearchTest.php | 213 +++++++++++ .../admin_toolbar_tools.info.yml | 9 +- .../admin_toolbar_tools.install | 14 + .../admin_toolbar_tools.links.menu.yml | 6 + .../admin_toolbar_tools.module | 6 +- .../admin_toolbar_tools.routing.yml | 16 +- .../admin_toolbar_tools.services.yml | 8 +- .../admin_toolbar_tools/composer.json | 4 +- .../src/AdminToolbarToolsHelper.php | 62 ++++ .../src/Controller/ToolbarController.php | 69 ++-- .../src/Plugin/Derivative/ExtraLinks.php | 17 +- .../Functional/AdminToolbarToolsAlterTest.php | 5 + web/modules/admin_toolbar/composer.json | 5 +- .../src/Render/Element/AdminToolbar.php | 51 +++ .../src/Functional/AdminToolbarAlterTest.php | 5 + .../Functional/AdminToolbarToolsSortTest.php | 12 +- .../AdminToolbarSearchTest.php | 339 ------------------ 38 files changed, 1149 insertions(+), 544 deletions(-) create mode 100644 web/modules/admin_toolbar/admin_toolbar_search/admin_toolbar_search.info.yml create mode 100644 web/modules/admin_toolbar/admin_toolbar_search/admin_toolbar_search.libraries.yml create mode 100755 web/modules/admin_toolbar/admin_toolbar_search/admin_toolbar_search.module create mode 100644 web/modules/admin_toolbar/admin_toolbar_search/admin_toolbar_search.permissions.yml create mode 100755 web/modules/admin_toolbar/admin_toolbar_search/admin_toolbar_search.routing.yml create mode 100644 web/modules/admin_toolbar/admin_toolbar_search/admin_toolbar_search.services.yml create mode 100755 web/modules/admin_toolbar/admin_toolbar_search/composer.json create mode 100755 web/modules/admin_toolbar/admin_toolbar_search/css/admin.toolbar_search.css create mode 100755 web/modules/admin_toolbar/admin_toolbar_search/js/admin_toolbar_search.js create mode 100755 web/modules/admin_toolbar/admin_toolbar_search/src/Controller/AdminToolbarSearchController.php rename web/modules/admin_toolbar/{admin_toolbar_tools => admin_toolbar_search}/src/SearchLinks.php (92%) create mode 100755 web/modules/admin_toolbar/admin_toolbar_search/tests/src/FunctionalJavascript/AdminToolbarSearchTest.php create mode 100755 web/modules/admin_toolbar/admin_toolbar_search/tests/src/FunctionalJavascript/AdminToolbarSearchTestBase.php create mode 100755 web/modules/admin_toolbar/admin_toolbar_search/tests/src/FunctionalJavascript/AdminToolbarToolsSearchTest.php create mode 100644 web/modules/admin_toolbar/admin_toolbar_tools/admin_toolbar_tools.install create mode 100644 web/modules/admin_toolbar/admin_toolbar_tools/src/AdminToolbarToolsHelper.php create mode 100644 web/modules/admin_toolbar/src/Render/Element/AdminToolbar.php delete mode 100755 web/modules/admin_toolbar/tests/src/FunctionalJavascript/AdminToolbarSearchTest.php diff --git a/composer.json b/composer.json index 1a392f6d64..b09a831a65 100644 --- a/composer.json +++ b/composer.json @@ -88,7 +88,7 @@ "drupal-composer/drupal-scaffold": "2.5.4", "drupal/address": "1.1", "drupal/addtocalendar": "3.1", - "drupal/admin_toolbar": "2.0", + "drupal/admin_toolbar": "2.2", "drupal/administerusersbyrole": "2.0-beta1", "drupal/allowed_formats": "1.2", "drupal/anchor_link": "1.6", @@ -318,4 +318,4 @@ "php": "7.0.8" } } -} \ No newline at end of file +} diff --git a/composer.lock b/composer.lock index fd58f43968..4750865f8d 100644 --- a/composer.lock +++ b/composer.lock @@ -4,7 +4,7 @@ "Read more about it at https://getcomposer.org/doc/01-basic-usage.md#installing-dependencies", "This file is @generated automatically" ], - "content-hash": "f3f9a51e6c09cc6554fa012dbf1ad64d", + "content-hash": "efa9a31671a248c25e142792e159ae55", "packages": [ { "name": "alchemy/zippy", @@ -2113,20 +2113,20 @@ }, { "name": "drupal/admin_toolbar", - "version": "2.0.0", + "version": "2.2.0", "source": { "type": "git", "url": "https://git.drupalcode.org/project/admin_toolbar.git", - "reference": "8.x-2.0" + "reference": "8.x-2.2" }, "dist": { "type": "zip", - "url": "https://ftp.drupal.org/files/projects/admin_toolbar-8.x-2.0.zip", - "reference": "8.x-2.0", - "shasum": "568de63dbaa8046a82d327dbd0b892ab79fb87aa" + "url": "https://ftp.drupal.org/files/projects/admin_toolbar-8.x-2.2.zip", + "reference": "8.x-2.2", + "shasum": "41ea0e3321e6d1e190c486be49a99e60446d8dd7" }, "require": { - "drupal/core": "*" + "drupal/core": "^8.8.0 || ^9.0" }, "type": "drupal-module", "extra": { @@ -2134,8 +2134,8 @@ "dev-2.x": "2.x-dev" }, "drupal": { - "version": "8.x-2.0", - "datestamp": "1573751237", + "version": "8.x-2.2", + "datestamp": "1585017179", "security-coverage": { "status": "covered", "message": "Covered by Drupal's security advisory policy" @@ -6064,8 +6064,7 @@ "homepage": "https://www.drupal.org/project/migrate_devel", "support": { "source": "http://cgit.drupalcode.org/migrate_devel" - }, - "time": "2017-06-25T23:46:13+00:00" + } }, { "name": "drupal/migrate_plus", diff --git a/vendor/composer/installed.json b/vendor/composer/installed.json index 1dcf950ce4..ac54b84366 100644 --- a/vendor/composer/installed.json +++ b/vendor/composer/installed.json @@ -2178,21 +2178,21 @@ }, { "name": "drupal/admin_toolbar", - "version": "2.0.0", - "version_normalized": "2.0.0.0", + "version": "2.2.0", + "version_normalized": "2.2.0.0", "source": { "type": "git", "url": "https://git.drupalcode.org/project/admin_toolbar.git", - "reference": "8.x-2.0" + "reference": "8.x-2.2" }, "dist": { "type": "zip", - "url": "https://ftp.drupal.org/files/projects/admin_toolbar-8.x-2.0.zip", - "reference": "8.x-2.0", - "shasum": "568de63dbaa8046a82d327dbd0b892ab79fb87aa" + "url": "https://ftp.drupal.org/files/projects/admin_toolbar-8.x-2.2.zip", + "reference": "8.x-2.2", + "shasum": "41ea0e3321e6d1e190c486be49a99e60446d8dd7" }, "require": { - "drupal/core": "*" + "drupal/core": "^8.8.0 || ^9.0" }, "type": "drupal-module", "extra": { @@ -2200,8 +2200,8 @@ "dev-2.x": "2.x-dev" }, "drupal": { - "version": "8.x-2.0", - "datestamp": "1573751237", + "version": "8.x-2.2", + "datestamp": "1585017179", "security-coverage": { "status": "covered", "message": "Covered by Drupal's security advisory policy" diff --git a/web/modules/admin_toolbar/admin_toolbar.info.yml b/web/modules/admin_toolbar/admin_toolbar.info.yml index b55a509cff..382e37ffb6 100644 --- a/web/modules/admin_toolbar/admin_toolbar.info.yml +++ b/web/modules/admin_toolbar/admin_toolbar.info.yml @@ -3,12 +3,12 @@ description: Provides an improved drop-down menu interface to the site Toolbar. package: Administration type: module -core: 8.x +core_version_requirement: ^8.8.0 || ^9.0 dependencies: - drupal:toolbar -# Information added by Drupal.org packaging script on 2019-10-29 -version: '8.x-2.0' +# Information added by Drupal.org packaging script on 2020-03-24 +version: '8.x-2.2' project: 'admin_toolbar' -datestamp: 1572370993 +datestamp: 1585017182 diff --git a/web/modules/admin_toolbar/admin_toolbar.libraries.yml b/web/modules/admin_toolbar/admin_toolbar.libraries.yml index 34306becdb..85b322a4e6 100755 --- a/web/modules/admin_toolbar/admin_toolbar.libraries.yml +++ b/web/modules/admin_toolbar/admin_toolbar.libraries.yml @@ -8,14 +8,3 @@ toolbar.tree: dependencies: - core/jquery - core/drupal -search: - css: - theme: - css/admin.toolbar_search.css: {} - js: - js/admin_toolbar_search.js: {} - dependencies: - - core/jquery - - core/drupal - - core/jquery.once - - core/jquery.ui.autocomplete diff --git a/web/modules/admin_toolbar/admin_toolbar.module b/web/modules/admin_toolbar/admin_toolbar.module index 3c5e81bda0..c02c3f4868 100755 --- a/web/modules/admin_toolbar/admin_toolbar.module +++ b/web/modules/admin_toolbar/admin_toolbar.module @@ -5,57 +5,17 @@ * This is the module to create a drop-down menu for the core toolbar. */ -use Drupal\Core\Menu\MenuTreeParameters; +use Drupal\admin_toolbar\Render\Element\AdminToolbar; use Drupal\Core\Routing\RouteMatchInterface; use Drupal\Core\Url; use Drupal\Component\Utility\Html; -use Drupal\Core\StringTranslation\TranslatableMarkup; /** * Implements hook_toolbar_alter(). */ function admin_toolbar_toolbar_alter(&$items) { - $items['administration']['tray']['toolbar_administration']['#pre_render'] = ['admin_toolbar_prerender_toolbar_administration_tray']; + $items['administration']['tray']['toolbar_administration']['#pre_render'] = [[AdminToolbar::class, 'preRenderTray']]; $items['administration']['#attached']['library'][] = 'admin_toolbar/toolbar.tree'; - $admin_toolbar_tools = \Drupal::service('module_handler') - ->moduleExists('admin_toolbar_tools'); - $items['administration_search'] = [ - "#type" => "toolbar_item", - 'tab' => [ - '#type' => 'link', - '#title' => new TranslatableMarkup('Search'), - '#url' => URL::fromRoute('system.admin'), - '#attributes' => [ - 'class' => [ - 'toolbar-icon', - ], - ], - ], - 'tray' => [ - 'search' => [ - '#title' => 'Search', - '#type' => 'textfield', - '#size' => 60, - '#attributes' => [ - 'id' => 'admin-toolbar-search-input', - 'aria-labelledby' => 'toolbar-item-administration-search', - ], - ], - ], - '#attached' => [ - 'library' => [ - 'admin_toolbar/search', - ], - 'drupalSettings' => [ - 'adminToolbarSearch' => [ - 'loadExtraLinks' => $admin_toolbar_tools, - ], - ], - ], - '#wrapper_attributes' => [ - "id" => "admin-toolbar-search-tab", - ], - ]; } /** @@ -77,35 +37,6 @@ function admin_toolbar_help($route_name, RouteMatchInterface $route_match) { } } -/** - * Renders the toolbar's administration tray. - * - * This is a clone of core's toolbar_prerender_toolbar_administration_tray() - * function, which uses setMaxDepth(4) instead of setTopLevelOnly(). - * - * @param array $element - * A renderable array. - * - * @return array - * The updated renderable array. - * - * @see toolbar_prerender_toolbar_administration_tray() - */ -function admin_toolbar_prerender_toolbar_administration_tray(array $element) { - $menu_tree = \Drupal::service('toolbar.menu_tree'); - $parameters = new MenuTreeParameters(); - $parameters->setRoot('system.admin')->excludeRoot()->setMaxDepth(4)->onlyEnabledLinks(); - $tree = $menu_tree->load(NULL, $parameters); - $manipulators = [ - ['callable' => 'menu.default_tree_manipulators:checkAccess'], - ['callable' => 'menu.default_tree_manipulators:generateIndexAndSort'], - ['callable' => 'toolbar_tools_menu_navigation_links'], - ]; - $tree = $menu_tree->transform($tree, $manipulators); - $element['administration_menu'] = $menu_tree->build($tree); - return $element; -} - /** * Adds toolbar-specific attributes to the menu link tree. * diff --git a/web/modules/admin_toolbar/admin_toolbar_links_access_filter/admin_toolbar_links_access_filter.info.yml b/web/modules/admin_toolbar/admin_toolbar_links_access_filter/admin_toolbar_links_access_filter.info.yml index 9ac6cdb5a3..1b8b648077 100644 --- a/web/modules/admin_toolbar/admin_toolbar_links_access_filter/admin_toolbar_links_access_filter.info.yml +++ b/web/modules/admin_toolbar/admin_toolbar_links_access_filter/admin_toolbar_links_access_filter.info.yml @@ -3,12 +3,12 @@ description: Provides a workaround for the common problem that users with 'Use t package: Administration type: module -core: 8.x +core_version_requirement: ^8.8.0 || ^9.0 dependencies: - admin_toolbar:admin_toolbar -# Information added by Drupal.org packaging script on 2019-10-29 -version: '8.x-2.0' +# Information added by Drupal.org packaging script on 2020-03-24 +version: '8.x-2.2' project: 'admin_toolbar' -datestamp: 1572370993 +datestamp: 1585017182 diff --git a/web/modules/admin_toolbar/admin_toolbar_links_access_filter/composer.json b/web/modules/admin_toolbar/admin_toolbar_links_access_filter/composer.json index d75f3b0c68..b7a007d7be 100755 --- a/web/modules/admin_toolbar/admin_toolbar_links_access_filter/composer.json +++ b/web/modules/admin_toolbar/admin_toolbar_links_access_filter/composer.json @@ -26,13 +26,14 @@ "name": "Mohamed Anis Taktak (matio89)", "homepage": "https://www.drupal.org/u/matio89", "role": "Maintainer" - } + } ], "support": { "issues": "https://www.drupal.org/project/issues/admin_toolbar", "source": "http://cgit.drupalcode.org/admin_toolbar" }, "require": { - "drupal/admin_toolbar": "^1" + "drupal/admin_toolbar": "^2", + "drupal/core": "^8.8.0 || ^9.0" } } diff --git a/web/modules/admin_toolbar/admin_toolbar_search/admin_toolbar_search.info.yml b/web/modules/admin_toolbar/admin_toolbar_search/admin_toolbar_search.info.yml new file mode 100644 index 0000000000..3dcad3ac3c --- /dev/null +++ b/web/modules/admin_toolbar/admin_toolbar_search/admin_toolbar_search.info.yml @@ -0,0 +1,14 @@ +name: Admin Toolbar Search +description: Provides search of admin toolbar items. +package: Administration + +type: module +core_version_requirement: ^8.8.0 || ^9.0 + +dependencies: + - admin_toolbar:admin_toolbar + +# Information added by Drupal.org packaging script on 2020-03-24 +version: '8.x-2.2' +project: 'admin_toolbar' +datestamp: 1585017182 diff --git a/web/modules/admin_toolbar/admin_toolbar_search/admin_toolbar_search.libraries.yml b/web/modules/admin_toolbar/admin_toolbar_search/admin_toolbar_search.libraries.yml new file mode 100644 index 0000000000..4f3bedac46 --- /dev/null +++ b/web/modules/admin_toolbar/admin_toolbar_search/admin_toolbar_search.libraries.yml @@ -0,0 +1,11 @@ +search: + css: + theme: + css/admin.toolbar_search.css: {} + js: + js/admin_toolbar_search.js: {} + dependencies: + - core/jquery + - core/drupal + - core/jquery.once + - core/jquery.ui.autocomplete diff --git a/web/modules/admin_toolbar/admin_toolbar_search/admin_toolbar_search.module b/web/modules/admin_toolbar/admin_toolbar_search/admin_toolbar_search.module new file mode 100755 index 0000000000..acad2f23cf --- /dev/null +++ b/web/modules/admin_toolbar/admin_toolbar_search/admin_toolbar_search.module @@ -0,0 +1,79 @@ +<?php + +/** + * @file + * Functionality for search of Admin Toolbar. + */ + +use Drupal\Core\StringTranslation\TranslatableMarkup; +use Drupal\Core\Url; +use Drupal\Core\Routing\RouteMatchInterface; + +/** + * Implements hook_help(). + */ +function admin_toolbar_search_help($route_name, RouteMatchInterface $route_match) { + switch ($route_name) { + // Main module help. + case 'help.page.admin_toolbar_search': + $output = ''; + $output .= '<h3>' . t('About') . '</h3>'; + $output .= '<p>' . t('The Admin Toolbar Search module add a search option to the toolbar for site administrative tasks.') . '</p>'; + + return $output; + } +} + +/** + * Implements hook_toolbar_alter(). + */ +function admin_toolbar_search_toolbar_alter(&$items) { + $access = \Drupal::currentUser()->hasPermission('use admin toolbar search'); + $admin_toolbar_tools_enabled = \Drupal::service('module_handler') + ->moduleExists('admin_toolbar_tools'); + + $items['administration_search'] = [ + "#type" => "toolbar_item", + '#access' => $access, + 'tab' => [ + '#type' => 'link', + '#title' => new TranslatableMarkup('Search'), + '#url' => URL::fromRoute('system.admin'), + '#attributes' => [ + 'class' => [ + 'toolbar-icon', + ], + ], + ], + 'tray' => [ + 'search' => [ + '#title' => 'Search', + '#type' => 'textfield', + '#size' => 60, + '#attributes' => [ + 'id' => 'admin-toolbar-search-input', + 'aria-labelledby' => 'toolbar-item-administration-search', + ], + ], + ], + '#attached' => [ + 'library' => [ + 'admin_toolbar_search/search', + ], + 'drupalSettings' => [ + 'adminToolbarSearch' => [ + 'loadExtraLinks' => $admin_toolbar_tools_enabled, + ], + ], + ], + '#wrapper_attributes' => [ + 'id' => 'admin-toolbar-search-tab', + ], + '#cache' => [ + 'contexts' => [ + 'user.permissions', + ], + ], + ]; + +} diff --git a/web/modules/admin_toolbar/admin_toolbar_search/admin_toolbar_search.permissions.yml b/web/modules/admin_toolbar/admin_toolbar_search/admin_toolbar_search.permissions.yml new file mode 100644 index 0000000000..b0d7ec73c5 --- /dev/null +++ b/web/modules/admin_toolbar/admin_toolbar_search/admin_toolbar_search.permissions.yml @@ -0,0 +1,2 @@ +use admin toolbar search: + title: 'Use Admin Toolbar search' diff --git a/web/modules/admin_toolbar/admin_toolbar_search/admin_toolbar_search.routing.yml b/web/modules/admin_toolbar/admin_toolbar_search/admin_toolbar_search.routing.yml new file mode 100755 index 0000000000..14adc55159 --- /dev/null +++ b/web/modules/admin_toolbar/admin_toolbar_search/admin_toolbar_search.routing.yml @@ -0,0 +1,6 @@ +admin_toolbar.search: + path: '/admin/admin-toolbar-search' + defaults: + _controller: '\Drupal\admin_toolbar_search\Controller\AdminToolbarSearchController::search' + requirements: + _permission: 'use admin toolbar search' diff --git a/web/modules/admin_toolbar/admin_toolbar_search/admin_toolbar_search.services.yml b/web/modules/admin_toolbar/admin_toolbar_search/admin_toolbar_search.services.yml new file mode 100644 index 0000000000..977e6ce2c3 --- /dev/null +++ b/web/modules/admin_toolbar/admin_toolbar_search/admin_toolbar_search.services.yml @@ -0,0 +1,9 @@ +services: + admin_toolbar_search.search_links: + class: Drupal\admin_toolbar_search\SearchLinks + arguments: + - '@entity_type.manager' + - '@module_handler' + - '@router.route_provider' + - '@cache_contexts_manager' + - '@cache.toolbar' diff --git a/web/modules/admin_toolbar/admin_toolbar_search/composer.json b/web/modules/admin_toolbar/admin_toolbar_search/composer.json new file mode 100755 index 0000000000..919f43f82b --- /dev/null +++ b/web/modules/admin_toolbar/admin_toolbar_search/composer.json @@ -0,0 +1,39 @@ +{ + "name": "drupal/admin_toolbar_search", + "description": "Provides search of admin toolbar items.", + "type": "drupal-module", + "keywords": ["Drupal", "Toolbar", "Search"], + "homepage": "http://drupal.org/project/admin_toolbar", + "license": "GPL-2.0+", + "authors": [ + { + "name": "Wilfrid Roze (eme)", + "homepage": "https://www.drupal.org/u/eme", + "role": "Maintainer" + }, + { + "name": "Romain Jarraud (romainj)", + "homepage": "https://www.drupal.org/u/romainj", + "role": "Maintainer" + }, + { + "name": "Adrian Cid Almaguer (adriancid)", + "email": "adriancid@gmail.com", + "homepage": "https://www.drupal.org/u/adriancid", + "role": "Maintainer" + }, + { + "name": "Mohamed Anis Taktak (matio89)", + "homepage": "https://www.drupal.org/u/matio89", + "role": "Maintainer" + } + ], + "support": { + "issues": "https://www.drupal.org/project/issues/admin_toolbar", + "source": "http://cgit.drupalcode.org/admin_toolbar" + }, + "require": { + "drupal/admin_toolbar": "^2", + "drupal/core": "^8.8.0 || ^9.0" + } +} diff --git a/web/modules/admin_toolbar/admin_toolbar_search/css/admin.toolbar_search.css b/web/modules/admin_toolbar/admin_toolbar_search/css/admin.toolbar_search.css new file mode 100755 index 0000000000..6215d9b625 --- /dev/null +++ b/web/modules/admin_toolbar/admin_toolbar_search/css/admin.toolbar_search.css @@ -0,0 +1,33 @@ +#toolbar-item-administration-search-tray { + padding-left: 1em; +} + +#admin-toolbar-search-tab .toolbar-item:before { + background-image: url('../../misc/icons/bebebe/loupe.svg'); +} + +#admin-toolbar-search-tab .toolbar-item:active:before, +#admin-toolbar-search-tab .toolbar-item.is-active:before { + background-image: url('../../misc/icons/ffffff/loupe.svg'); +} + +#toolbar-item-administration-search-tray label { + display: inline-block; + color: #000000; + margin-right: .5em; + font-weight: bold; +} + +#toolbar-item-administration-search-tray div.form-item { + margin: 0.75em 0; +} + +#toolbar-item-administration-search-tray input { + display: inline-block; + padding: 0.3em 0.4em 0.3em 0.5em; + font-size: 1em; +} + +.ui-autocomplete .ui-menu-item span.admin-toolbar-search-url { + color: rgba(0, 0, 0, 0.50); +} diff --git a/web/modules/admin_toolbar/admin_toolbar_search/js/admin_toolbar_search.js b/web/modules/admin_toolbar/admin_toolbar_search/js/admin_toolbar_search.js new file mode 100755 index 0000000000..701d76fb6c --- /dev/null +++ b/web/modules/admin_toolbar/admin_toolbar_search/js/admin_toolbar_search.js @@ -0,0 +1,188 @@ +/** + * @file + * Behaviors for the search widget in the admin toolbar. + */ + +(function ($, Drupal) { + + 'use strict'; + + Drupal.behaviors.adminToolbarSearch = { + + // If extra links have been fetched. + extraFetched: false, + + attach: function (context) { + if (context != document) { + return; + } + + var getUrl = window.location; + var baseUrl = getUrl.protocol + "//" + getUrl.host + "/"; + var $self = this; + this.links = []; + $('.toolbar-tray a[data-drupal-link-system-path]').each(function () { + if (this.href != baseUrl) { + var label = $self.getItemLabel(this); + $self.links.push({ + 'value': $(this).attr('href'), + 'label': label + ' ' + $(this).attr('href'), + 'labelRaw': label + }); + } + }); + + $("#admin-toolbar-search-input").autocomplete({ + minLength: 2, + source: function (request, response) { + var data = $self.handleAutocomplete(request.term); + if (!$self.extraFetched && drupalSettings.adminToolbarSearch.loadExtraLinks) { + $.getJSON( "/admin/admin-toolbar-search", function( data ) { + $(data).each(function() { + var item = this; + item.label = this.labelRaw + ' ' + this.value; + $self.links.push(item); + }); + + $self.extraFetched = true; + + var results = $self.handleAutocomplete(request.term); + response(results); + }); + } + else { + response(data); + } + }, + open: function () { + var zIndex = $('#toolbar-item-administration-search-tray') + .css("z-index") + 1; + $(this).autocomplete('widget').css('z-index', zIndex); + + return false; + }, + select: function (event, ui) { + if (ui.item.value) { + location.href = ui.item.value; + return false; + } + } + }).data("ui-autocomplete")._renderItem = (function (ul, item) { + return $("<li>") + .append('<div>' + item.labelRaw + ' <span class="admin-toolbar-search-url">' + item.value + '</span></div>') + .appendTo(ul); + }); + + // Focus on search field when tab is clicked, or enter is pressed. + $(context).find('#toolbar-item-administration-search') + .once('admin_toolbar_search') + .each(function () { + if (Drupal.behaviors.adminToolbarSearch.isSearchVisible()) { + $('#admin-toolbar-search-input').focus(); + } + $(this).on('click', function () { + $self.focusOnSearchElement(); + }); + }); + + // Initialize hotkey / keyboard shortcut. + this.initHotkey(); + }, + focusOnSearchElement: function () { + var waitforVisible = function () { + if ($('#toolbar-item-administration-search-tray:visible').length) { + $('#admin-toolbar-search-input').focus(); + } + else { + setTimeout(function () { + waitforVisible(); + }, 1); + } + }; + waitforVisible(); + }, + getItemLabel: function (item) { + var breadcrumbs = []; + $(item).parents().each(function () { + if ($(this).hasClass('menu-item')) { + var $link = $(this).find('a:first'); + if ($link.length && !$link.hasClass('admin-toolbar-search-ignore')) { + breadcrumbs.unshift($link.text()); + } + } + }); + return breadcrumbs.join(' > '); + }, + handleAutocomplete: function (term) { + var $self = this; + var keywords = term.split(" "); // Split search terms into list. + + var suggestions = []; + $self.links.forEach(function (element) { + var label = element.label.toLowerCase(); + + // Add exact matches. + if (label.indexOf(term.toLowerCase()) >= 0) { + suggestions.push(element); + } + else { + // Add suggestions where it matches all search terms. + var matchCount = 0; + keywords.forEach(function (keyword) { + if (label.indexOf(keyword.toLowerCase()) >= 0) { + matchCount++; + } + }); + if (matchCount == keywords.length) { + suggestions.push(element); + } + } + }); + return suggestions; + }, + /** + * Whether the search is visible or not. + * + * @returns {boolean} + * True if visible, false otherwise. + */ + isSearchVisible: function () { + return $('#toolbar-item-administration-search-tray').is(':visible'); + }, + /** + * Toggles the toolbar search tray. + */ + toggleSearch: function () { + $('#toolbar-item-administration-search').trigger('click'); + }, + /** + * Binds a keyboard shortcut to toggle the search. + */ + initHotkey: function () { + $(document) + .once('admin_toolbar_search') + .keydown(function (event) { + // Show the form with alt + S. + if (!Drupal.behaviors.adminToolbarSearch.isSearchVisible()) { + // 83 = s. + if (event.altKey === true && event.keyCode === 83) { + Drupal.behaviors.adminToolbarSearch.toggleSearch(); + event.preventDefault(); + } + } + // Hide the search with alt + S or ESC. + else { + // 83 = s. + if ( + (event.altKey === true && event.keyCode === 83) || + event.key === 'Escape' + ) { + Drupal.behaviors.adminToolbarSearch.toggleSearch(); + event.preventDefault(); + } + } + }); + } + }; + +})(jQuery, Drupal); diff --git a/web/modules/admin_toolbar/admin_toolbar_search/src/Controller/AdminToolbarSearchController.php b/web/modules/admin_toolbar/admin_toolbar_search/src/Controller/AdminToolbarSearchController.php new file mode 100755 index 0000000000..d3ae3325b7 --- /dev/null +++ b/web/modules/admin_toolbar/admin_toolbar_search/src/Controller/AdminToolbarSearchController.php @@ -0,0 +1,50 @@ +<?php + +namespace Drupal\admin_toolbar_search\Controller; + +use Drupal\admin_toolbar_search\SearchLinks; +use Drupal\Core\Controller\ControllerBase; +use Symfony\Component\DependencyInjection\ContainerInterface; +use Symfony\Component\HttpFoundation\JsonResponse; + +/** + * Class AdminToolbarSearchController. + * + * @package Drupal\admin_toolbar_tools\Controller + */ +class AdminToolbarSearchController extends ControllerBase { + + /** + * The search links service. + * + * @var \Drupal\admin_toolbar_search\SearchLinks + */ + protected $links; + + /** + * Constructs an AdminToolbarSearchController object. + * + * @param \Drupal\admin_toolbar_search\SearchLinks $links + * The search links service. + */ + public function __construct(SearchLinks $links) { + $this->links = $links; + } + + /** + * {@inheritdoc} + */ + public static function create(ContainerInterface $container) { + return new static( + $container->get('admin_toolbar_search.search_links') + ); + } + + /** + * Return additional search links. + */ + public function search() { + return new JsonResponse($this->links->getLinks()); + } + +} diff --git a/web/modules/admin_toolbar/admin_toolbar_tools/src/SearchLinks.php b/web/modules/admin_toolbar/admin_toolbar_search/src/SearchLinks.php similarity index 92% rename from web/modules/admin_toolbar/admin_toolbar_tools/src/SearchLinks.php rename to web/modules/admin_toolbar/admin_toolbar_search/src/SearchLinks.php index 703edbee53..e36dba37a9 100644 --- a/web/modules/admin_toolbar/admin_toolbar_tools/src/SearchLinks.php +++ b/web/modules/admin_toolbar/admin_toolbar_search/src/SearchLinks.php @@ -1,6 +1,6 @@ <?php -namespace Drupal\admin_toolbar_tools; +namespace Drupal\admin_toolbar_search; use Drupal\admin_toolbar_tools\Plugin\Derivative\ExtraLinks; use Drupal\Core\Cache\Cache; @@ -57,7 +57,18 @@ class SearchLinks { protected $toolbarCache; /** - * {@inheritdoc} + * Constructs a SearchLinks object. + * + * @param \Drupal\Core\Entity\EntityTypeManagerInterface $entity_type_manager + * The entity type manager. + * @param \Drupal\Core\Extension\ModuleHandlerInterface $module_handler + * The module handler. + * @param \Drupal\Core\Routing\RouteProviderInterface $route_provider + * The route provider. + * @param \Drupal\Core\Cache\Context\CacheContextsManager $cache_context_manager + * The cache contexts manager. + * @param \Drupal\Core\Cache\CacheBackendInterface $toolbar_cache + * Cache backend instance to use. */ public function __construct(EntityTypeManagerInterface $entity_type_manager, ModuleHandlerInterface $module_handler, RouteProviderInterface $route_provider, CacheContextsManager $cache_context_manager, CacheBackendInterface $toolbar_cache) { $this->entityTypeManager = $entity_type_manager; @@ -68,10 +79,10 @@ public function __construct(EntityTypeManagerInterface $entity_type_manager, Mod } /** - * Get extra links for admin toolbar search feature. + * Gets extra links for admin toolbar search feature. * * @return array - * An array of link data. + * An array of link data for the JSON used for search. * * @throws \Drupal\Component\Plugin\Exception\InvalidPluginDefinitionException * @throws \Drupal\Component\Plugin\Exception\PluginNotFoundException @@ -239,7 +250,7 @@ public function getLinks() { } /** - * Get a list of content entities. + * Gets a list of content entities. * * @return array * An array of metadata about content entities. @@ -258,19 +269,6 @@ protected function getBundleableEntitiesList() { return $content_entities; } - /** - * Get an array of entity types that should trigger a menu rebuild. - * - * @return array - * An array of entity machine names. - */ - public function getRebuildEntityTypes() { - $types = ['menu']; - $content_entities = $this->getBundleableEntitiesList(); - $types = array_merge($types, array_column($content_entities, 'content_entity_bundle')); - return $types; - } - /** * Determine if a route exists by name. * diff --git a/web/modules/admin_toolbar/admin_toolbar_search/tests/src/FunctionalJavascript/AdminToolbarSearchTest.php b/web/modules/admin_toolbar/admin_toolbar_search/tests/src/FunctionalJavascript/AdminToolbarSearchTest.php new file mode 100755 index 0000000000..f12b8f8543 --- /dev/null +++ b/web/modules/admin_toolbar/admin_toolbar_search/tests/src/FunctionalJavascript/AdminToolbarSearchTest.php @@ -0,0 +1,47 @@ +<?php + +namespace Drupal\Tests\admin_toolbar_search\FunctionalJavascript; + +/** + * Test the functionality of admin toolbar search. + * + * @group admin_toolbar + * @group admin_toolbar_search + */ +class AdminToolbarSearchTest extends AdminToolbarSearchTestBase { + + /** + * Tests search functionality without admin_toolbar_tools enabled. + */ + public function testToolbarSearch() { + $search_tab = '#toolbar-item-administration-search'; + $search_tray = '#toolbar-item-administration-search-tray'; + + $this->drupalLogin($this->userWithAccess); + $assert_session = $this->assertSession(); + $assert_session->responseContains('admin.toolbar_search.css'); + $assert_session->responseContains('admin_toolbar_search.js'); + $assert_session->waitForElementVisible('css', $search_tab)->click(); + $assert_session->waitForElementVisible('css', $search_tray); + + $this->assertSuggestionContains('perfor', 'admin/config/development/performance'); + $this->assertSuggestionContains('develop', 'admin/config/development/maintenance'); + $this->assertSuggestionContains('types', 'admin/structure/types'); + } + + /** + * Tests a user without the search permission can't use search. + */ + public function testNoAccess() { + $search_tab = '#toolbar-item-administration-search'; + $search_tray = '#toolbar-item-administration-search-tray'; + + $this->drupalLogin($this->noAccessUser); + $assert_session = $this->assertSession(); + $assert_session->responseNotContains('admin.toolbar_search.css'); + $assert_session->responseNotContains('admin_toolbar_search.js'); + $assert_session->elementNotExists('css', $search_tab); + $assert_session->elementNotExists('css', $search_tray); + } + +} diff --git a/web/modules/admin_toolbar/admin_toolbar_search/tests/src/FunctionalJavascript/AdminToolbarSearchTestBase.php b/web/modules/admin_toolbar/admin_toolbar_search/tests/src/FunctionalJavascript/AdminToolbarSearchTestBase.php new file mode 100755 index 0000000000..6a16c5882e --- /dev/null +++ b/web/modules/admin_toolbar/admin_toolbar_search/tests/src/FunctionalJavascript/AdminToolbarSearchTestBase.php @@ -0,0 +1,192 @@ +<?php + +namespace Drupal\Tests\admin_toolbar_search\FunctionalJavascript; + +use Drupal\FunctionalJavascriptTests\WebDriverTestBase; +use Drupal\system\Entity\Menu; + +/** + * Base class for testing the functionality of admin toolbar search. + * + * @group admin_toolbar + * @group admin_toolbar_search + */ +abstract class AdminToolbarSearchTestBase extends WebDriverTestBase { + + /** + * {@inheritdoc} + */ + protected $defaultTheme = 'stark'; + + /** + * {@inheritdoc} + */ + public static $modules = [ + 'admin_toolbar_search', + 'node', + 'media', + 'field_ui', + 'menu_ui', + 'block', + ]; + + /** + * A user with the 'Use Admin Toolbar search' permission. + * + * @var \Drupal\user\UserInterface + */ + protected $userWithAccess; + + /** + * A test user without the 'Use Admin Toolbar search' permission.. + * + * @var \Drupal\user\UserInterface + */ + protected $noAccessUser; + + /** + * {@inheritdoc} + */ + public function setUp() { + parent::setUp(); + + $baby_names = [ + 'ada' => 'Ada', + 'amara' => 'Amara', + 'amelia' => 'Amelia', + 'arabella' => 'Arabella', + 'asher' => 'Asher', + 'astrid' => 'Astrid', + 'atticus' => 'Atticus', + 'aurora' => 'Aurora', + 'ava' => 'Ava', + 'cora' => 'Cora', + 'eleanor' => 'Eleanor', + 'eloise' => 'Eloise', + 'felix' => 'Felix', + 'freya' => 'Freya', + 'genevieve' => 'Genevieve', + 'isla' => 'Isla', + 'jasper' => 'Jasper', + 'luna' => 'Luna', + 'maeve' => 'Maeve', + 'milo' => 'Milo', + 'nora' => 'Nora', + 'olivia' => 'Olivia', + 'ophelia' => 'Ophelia', + 'posie' => 'Posie', + 'rose' => 'Rose', + 'silas' => 'Silas', + 'soren' => 'Soren', + ]; + + foreach ($baby_names as $id => $label) { + $menu = Menu::create([ + 'id' => $id, + 'label' => $label, + ]); + $menu->save(); + } + + $this->drupalPlaceBlock('local_tasks_block'); + + $permissions = [ + 'access toolbar', + 'administer menu', + 'access administration pages', + 'administer site configuration', + 'administer content types', + ]; + $this->noAccessUser = $this->drupalCreateUser($permissions); + $permissions[] = 'use admin toolbar search'; + $this->userWithAccess = $this->drupalCreateUser($permissions); + } + + /** + * Assert that the search suggestions contain a given string with given input. + * + * @param string $search + * The string to search for. + * @param string $contains + * Some HTML that is expected to be within the suggestions element. + */ + protected function assertSuggestionContains($search, $contains) { + $this->resetSearch(); + $page = $this->getSession()->getPage(); + $page->fillField('admin-toolbar-search-input', $search); + $this->getSession()->getDriver()->keyDown('//input[@id="admin-toolbar-search-input"]', ' '); + $page->waitFor(3, function () use ($page) { + return ($page->find('css', 'ul.ui-autocomplete')->isVisible() === TRUE); + }); + $suggestions_markup = $page->find('css', 'ul.ui-autocomplete')->getHtml(); + $this->assertContains($contains, $suggestions_markup); + } + + /** + * Assert that the search suggestions does not contain a given string. + * + * Assert that the search suggestions does not contain a given string with a + * given input. + * + * @param string $search + * The string to search for. + * @param string $contains + * Some HTML that is not expected to be within the suggestions element. + */ + protected function assertSuggestionNotContains($search, $contains) { + $this->resetSearch(); + $page = $this->getSession()->getPage(); + $page->fillField('admin-toolbar-search-input', $search); + $this->getSession()->getDriver()->keyDown('//input[@id="admin-toolbar-search-input"]', ' '); + $page->waitFor(3, function () use ($page) { + return ($page->find('css', 'ul.ui-autocomplete')->isVisible() === TRUE); + }); + if ($page->find('css', 'ul.ui-autocomplete')->isVisible() === FALSE) { + return; + } + else { + $suggestions_markup = $page->find('css', 'ul.ui-autocomplete')->getHtml(); + $this->assertNotContains($contains, $suggestions_markup); + } + } + + /** + * Search for an empty string to clear out the autocomplete suggestions. + */ + protected function resetSearch() { + $page = $this->getSession()->getPage(); + // Empty out the suggestions. + $page->fillField('admin-toolbar-search-input', ''); + $this->getSession()->getDriver()->keyDown('//input[@id="admin-toolbar-search-input"]', ' '); + $page->waitFor(3, function () use ($page) { + return ($page->find('css', 'ul.ui-autocomplete')->isVisible() === FALSE); + }); + } + + /** + * Checks that there is a link with the specified url in the admin toolbar. + * + * @param string $url + * The url to assert exists in the admin menu. + * + * @throws \Behat\Mink\Exception\ElementNotFoundException + */ + protected function assertMenuHasHref($url) { + $this->assertSession() + ->elementExists('xpath', '//div[@id="toolbar-item-administration-tray"]//a[contains(@href, "' . $url . '")]'); + } + + /** + * Checks that there is no link with the specified url in the admin toolbar. + * + * @param string $url + * The url to assert exists in the admin menu. + * + * @throws \Behat\Mink\Exception\ExpectationException + */ + protected function assertMenuDoesNotHaveHref($url) { + $this->assertSession() + ->elementNotExists('xpath', '//div[@id="toolbar-item-administration-tray"]//a[contains(@href, "' . $url . '")]'); + } + +} diff --git a/web/modules/admin_toolbar/admin_toolbar_search/tests/src/FunctionalJavascript/AdminToolbarToolsSearchTest.php b/web/modules/admin_toolbar/admin_toolbar_search/tests/src/FunctionalJavascript/AdminToolbarToolsSearchTest.php new file mode 100755 index 0000000000..239b6ef332 --- /dev/null +++ b/web/modules/admin_toolbar/admin_toolbar_search/tests/src/FunctionalJavascript/AdminToolbarToolsSearchTest.php @@ -0,0 +1,213 @@ +<?php + +namespace Drupal\Tests\admin_toolbar_search\FunctionalJavascript; + +use Drupal\media\Entity\MediaType; +use Drupal\Tests\media\Traits\MediaTypeCreationTrait; + +/** + * Test the functionality of admin toolbar search. + * + * @group admin_toolbar + * @group admin_toolbar_search + */ +class AdminToolbarToolsSearchTest extends AdminToolbarSearchTestBase { + + use MediaTypeCreationTrait; + + /** + * {@inheritdoc} + */ + public static $modules = [ + 'admin_toolbar_tools', + 'admin_toolbar_search', + 'node', + 'media', + 'field_ui', + 'menu_ui', + 'block', + ]; + + /** + * The admin user for tests. + * + * @var \Drupal\user\UserInterface + */ + protected $adminUser; + + /** + * {@inheritdoc} + */ + public function setUp() { + parent::setUp(); + + $this->drupalCreateContentType([ + 'type' => 'article', + 'name' => 'Article', + ]); + + $dog_names = [ + 'archie' => 'Archie', + 'bailey' => 'Bailey', + 'bella' => 'Bella', + 'buddy' => 'Buddy', + 'charlie' => 'Charlie', + 'coco' => 'Coco', + 'daisy' => 'Daisy', + 'frankie' => 'Frankie', + 'jack' => 'Jack', + 'lola' => 'Lola', + 'lucy' => 'Lucy', + 'max' => 'Max', + 'milo' => 'Milo', + 'molly' => 'Molly', + 'ollie' => 'Ollie', + 'oscar' => 'Oscar', + 'rosie' => 'Rosie', + 'ruby' => 'Ruby', + 'teddy' => 'Teddy', + 'toby' => 'Toby', + ]; + + foreach ($dog_names as $machine_name => $label) { + $this->createMediaType('image', [ + 'id' => $machine_name, + 'label' => $label, + ]); + } + + $this->adminUser = $this->drupalCreateUser([ + 'access toolbar', + 'administer menu', + 'access administration pages', + 'administer site configuration', + 'administer content types', + 'administer node fields', + 'access media overview', + 'administer media', + 'administer media fields', + 'administer media form display', + 'administer media display', + 'administer media types', + 'use admin toolbar search', + ]); + } + + /** + * Tests search functionality with admin_toolbar_tools enabled. + */ + public function testToolbarSearch() { + $search_tab = '#toolbar-item-administration-search'; + $search_tray = '#toolbar-item-administration-search-tray'; + + $this->drupalLogin($this->adminUser); + $assert_session = $this->assertSession(); + $assert_session->responseContains('admin.toolbar_search.css'); + $assert_session->responseContains('admin_toolbar_search.js'); + $assert_session->waitForElementVisible('css', $search_tab)->click(); + $assert_session->waitForElementVisible('css', $search_tray); + + $this->assertSuggestionContains('basic', 'admin/config/system/site-information'); + + // Rebuild menu items. + drupal_flush_all_caches(); + + // Test that the route admin_toolbar.search returns expected json. + $this->drupalGet('/admin/admin-toolbar-search'); + + $search_menus = [ + 'cora', + 'eleanor', + 'eloise', + 'felix', + 'freya', + 'genevieve', + 'isla', + 'jasper', + 'luna', + 'maeve', + 'milo', + 'nora', + 'olivia', + 'ophelia', + 'posie', + 'rose', + 'silas', + 'soren', + ]; + + $toolbar_menus = [ + 'ada', + 'amara', + 'amelia', + 'arabella', + 'asher', + 'astrid', + 'atticus', + 'aurora', + 'ava', + ]; + + foreach ($search_menus as $menu_id) { + $assert_session->responseContains('\/admin\/structure\/menu\/manage\/' . $menu_id); + } + + foreach ($toolbar_menus as $menu_id) { + $assert_session->responseNotContains('\/admin\/structure\/menu\/manage\/' . $menu_id); + } + + $this->drupalGet('/admin'); + + foreach ($search_menus as $menu_id) { + $this->assertMenuDoesNotHaveHref('/admin/structure/menu/manage/' . $menu_id); + } + + foreach ($toolbar_menus as $menu_id) { + $this->assertMenuHasHref('/admin/structure/menu/manage/' . $menu_id); + } + + $this->drupalGet('admin/structure/types/manage/article/fields'); + $assert_session->waitForElementVisible('css', $search_tray); + + $this->assertSuggestionContains('article manage fields', '/admin/structure/types/manage/article/fields'); + + $suggestions = $assert_session + ->waitForElementVisible('css', 'ul.ui-autocomplete'); + + // Assert there is only one suggestion with a link to + // /admin/structure/types/manage/article/fields. + $count = count($suggestions->findAll('xpath', '//span[contains(text(), "/admin/structure/types/manage/article/fields")]')); + $this->assertEquals(1, $count); + + // Test that bundle within admin toolbar appears in search. + $this->assertSuggestionContains('lola', 'admin/structure/media/manage/lola/fields'); + + // Assert that a link after the limit (10) doesn't appear in admin toolbar. + $toby_url = '/admin/structure/media/manage/toby/fields'; + $assert_session->elementNotContains('css', '#toolbar-administration', $toby_url); + + // Assert that a link excluded from admin toolbar appears in search. + $this->assertSuggestionContains('toby', $toby_url); + + // Test that adding a new bundle updates the extra links loaded from + // admin_toolbar.search route. + $this->createMediaType('image', [ + 'id' => 'zuzu', + 'label' => 'Zuzu', + ]); + + $this->drupalGet('admin'); + $assert_session->waitForElementVisible('css', $search_tray); + $this->assertSuggestionContains('zuzu', '/admin/structure/media/manage/zuzu/fields'); + + // Test that deleting a bundle updates the extra links loaded from + // admin_toolbar.search route. + $toby = MediaType::load('toby'); + $toby->delete(); + + $this->getSession()->reload(); + $assert_session->waitForElementVisible('css', $search_tray); + $this->assertSuggestionNotContains('toby', $toby_url); + } + +} diff --git a/web/modules/admin_toolbar/admin_toolbar_tools/admin_toolbar_tools.info.yml b/web/modules/admin_toolbar/admin_toolbar_tools/admin_toolbar_tools.info.yml index 7b7728100e..89eedeafa0 100644 --- a/web/modules/admin_toolbar/admin_toolbar_tools/admin_toolbar_tools.info.yml +++ b/web/modules/admin_toolbar/admin_toolbar_tools/admin_toolbar_tools.info.yml @@ -3,13 +3,12 @@ description: Adds menu links to the Admin Toolbar. package: Administration type: module -core: 8.x +core_version_requirement: ^8.8.0 || ^9.0 dependencies: - admin_toolbar:admin_toolbar - - drupal:system (>=8.6) -# Information added by Drupal.org packaging script on 2019-10-29 -version: '8.x-2.0' +# Information added by Drupal.org packaging script on 2020-03-24 +version: '8.x-2.2' project: 'admin_toolbar' -datestamp: 1572370993 +datestamp: 1585017182 diff --git a/web/modules/admin_toolbar/admin_toolbar_tools/admin_toolbar_tools.install b/web/modules/admin_toolbar/admin_toolbar_tools/admin_toolbar_tools.install new file mode 100644 index 0000000000..1cc14c73d3 --- /dev/null +++ b/web/modules/admin_toolbar/admin_toolbar_tools/admin_toolbar_tools.install @@ -0,0 +1,14 @@ +<?php + +/** + * @file + * Install, update and uninstall functions for the Admin Toolbar Tools module. + */ + +/** + * Install the Admin Toolbar Search module. + */ +function admin_toolbar_tools_update_8001() { + // Installing the Admin Toolbar Search module. + \Drupal::service('module_installer')->install(['admin_toolbar_search']); +} diff --git a/web/modules/admin_toolbar/admin_toolbar_tools/admin_toolbar_tools.links.menu.yml b/web/modules/admin_toolbar/admin_toolbar_tools/admin_toolbar_tools.links.menu.yml index 567e32d16e..670a4f76c6 100755 --- a/web/modules/admin_toolbar/admin_toolbar_tools/admin_toolbar_tools.links.menu.yml +++ b/web/modules/admin_toolbar/admin_toolbar_tools/admin_toolbar_tools.links.menu.yml @@ -75,6 +75,12 @@ admin_toolbar_tools.flush_rendercache: parent: admin_toolbar_tools.flush menu_name: admin +admin_toolbar_tools.theme_rebuild: + title: 'Rebuild theme registry' + route_name: admin_toolbar_tools.theme_rebuild + parent: admin_toolbar_tools.flush + menu_name: admin + admin_toolbar_tools.extra_links: deriver: \Drupal\admin_toolbar_tools\Plugin\Derivative\ExtraLinks menu_name: admin diff --git a/web/modules/admin_toolbar/admin_toolbar_tools/admin_toolbar_tools.module b/web/modules/admin_toolbar/admin_toolbar_tools/admin_toolbar_tools.module index ec4e682fa2..6958a86297 100755 --- a/web/modules/admin_toolbar/admin_toolbar_tools/admin_toolbar_tools.module +++ b/web/modules/admin_toolbar/admin_toolbar_tools/admin_toolbar_tools.module @@ -48,7 +48,7 @@ function admin_toolbar_tools_help($route_name, RouteMatchInterface $route_match) * Implements hook_entity_insert(). */ function admin_toolbar_tools_entity_insert(EntityInterface $entity) { - $entities = \Drupal::service('admin_toolbar_tools.search_links')->getRebuildEntityTypes(); + $entities = \Drupal::service('admin_toolbar_tools.helper')->getRebuildEntityTypes(); if (in_array($entity->getEntityTypeId(), $entities)) { \Drupal::service('plugin.manager.menu.link')->rebuild(); } @@ -58,7 +58,7 @@ function admin_toolbar_tools_entity_insert(EntityInterface $entity) { * Implements hook_entity_update(). */ function admin_toolbar_tools_entity_update(EntityInterface $entity) { - $entities = \Drupal::service('admin_toolbar_tools.search_links')->getRebuildEntityTypes(); + $entities = \Drupal::service('admin_toolbar_tools.helper')->getRebuildEntityTypes(); if (in_array($entity->getEntityTypeId(), $entities)) { \Drupal::service('plugin.manager.menu.link')->rebuild(); } @@ -68,7 +68,7 @@ function admin_toolbar_tools_entity_update(EntityInterface $entity) { * Implements hook_entity_delete(). */ function admin_toolbar_tools_entity_delete(EntityInterface $entity) { - $entities = \Drupal::service('admin_toolbar_tools.search_links')->getRebuildEntityTypes(); + $entities = \Drupal::service('admin_toolbar_tools.helper')->getRebuildEntityTypes(); if (in_array($entity->getEntityTypeId(), $entities)) { \Drupal::service('plugin.manager.menu.link')->rebuild(); } diff --git a/web/modules/admin_toolbar/admin_toolbar_tools/admin_toolbar_tools.routing.yml b/web/modules/admin_toolbar/admin_toolbar_tools/admin_toolbar_tools.routing.yml index ee4eb23a2c..bcae9db1b7 100755 --- a/web/modules/admin_toolbar/admin_toolbar_tools/admin_toolbar_tools.routing.yml +++ b/web/modules/admin_toolbar/admin_toolbar_tools/admin_toolbar_tools.routing.yml @@ -70,18 +70,20 @@ admin_toolbar_tools.flush_twig: _permission: 'administer site configuration' _csrf_token: 'TRUE' -admin_toolbar.run.cron: - path: '/run-cron' +admin_toolbar_tools.theme_rebuild: + path: '/admin/flush/theme_rebuild' defaults: - _controller: '\Drupal\admin_toolbar_tools\Controller\ToolbarController::runCron' - _title: 'Run cron' + _controller: '\Drupal\admin_toolbar_tools\Controller\ToolbarController::themeRebuild' + _title: 'Theme Rebuild' requirements: _permission: 'administer site configuration' _csrf_token: 'TRUE' -admin_toolbar.search: - path: '/admin/admin-toolbar-search' +admin_toolbar.run.cron: + path: '/run-cron' defaults: - _controller: '\Drupal\admin_toolbar_tools\Controller\ToolbarController::search' + _controller: '\Drupal\admin_toolbar_tools\Controller\ToolbarController::runCron' + _title: 'Run cron' requirements: _permission: 'administer site configuration' + _csrf_token: 'TRUE' diff --git a/web/modules/admin_toolbar/admin_toolbar_tools/admin_toolbar_tools.services.yml b/web/modules/admin_toolbar/admin_toolbar_tools/admin_toolbar_tools.services.yml index f772cffaae..aa533c7871 100644 --- a/web/modules/admin_toolbar/admin_toolbar_tools/admin_toolbar_tools.services.yml +++ b/web/modules/admin_toolbar/admin_toolbar_tools/admin_toolbar_tools.services.yml @@ -1,9 +1,5 @@ services: - admin_toolbar_tools.search_links: - class: Drupal\admin_toolbar_tools\SearchLinks + admin_toolbar_tools.helper: + class: Drupal\admin_toolbar_tools\AdminToolbarToolsHelper arguments: - '@entity_type.manager' - - '@module_handler' - - '@router.route_provider' - - '@cache_contexts_manager' - - '@cache.toolbar' diff --git a/web/modules/admin_toolbar/admin_toolbar_tools/composer.json b/web/modules/admin_toolbar/admin_toolbar_tools/composer.json index bb568793a3..fad275ff53 100755 --- a/web/modules/admin_toolbar/admin_toolbar_tools/composer.json +++ b/web/modules/admin_toolbar/admin_toolbar_tools/composer.json @@ -26,7 +26,7 @@ "name": "Mohamed Anis Taktak (matio89)", "homepage": "https://www.drupal.org/u/matio89", "role": "Maintainer" - } + } ], "support": { "issues": "https://www.drupal.org/project/issues/admin_toolbar", @@ -34,6 +34,6 @@ }, "require": { "drupal/admin_toolbar": "^2", - "drupal/core": "~8.7" + "drupal/core": "^8.8.0 || ^9.0" } } diff --git a/web/modules/admin_toolbar/admin_toolbar_tools/src/AdminToolbarToolsHelper.php b/web/modules/admin_toolbar/admin_toolbar_tools/src/AdminToolbarToolsHelper.php new file mode 100644 index 0000000000..b270e679e9 --- /dev/null +++ b/web/modules/admin_toolbar/admin_toolbar_tools/src/AdminToolbarToolsHelper.php @@ -0,0 +1,62 @@ +<?php + +namespace Drupal\admin_toolbar_tools; + +use Drupal\Core\Entity\EntityTypeManagerInterface; + +/** + * Admin Toolbar Tools helper service. + */ +class AdminToolbarToolsHelper { + + /** + * The entity type manager. + * + * @var \Drupal\Core\Entity\EntityTypeManagerInterface + */ + protected $entityTypeManager; + + /** + * Create an AdminToolbarToolsHelper object. + * + * @param \Drupal\Core\Entity\EntityTypeManagerInterface $entity_type_manager + * The entity type manager. + */ + public function __construct(EntityTypeManagerInterface $entity_type_manager) { + $this->entityTypeManager = $entity_type_manager; + } + + /** + * Gets a list of content entities. + * + * @return array + * An array of metadata about content entities. + */ + public function getBundleableEntitiesList() { + $entity_types = $this->entityTypeManager->getDefinitions(); + $content_entities = []; + foreach ($entity_types as $key => $entity_type) { + if ($entity_type->getBundleEntityType() && ($entity_type->get('field_ui_base_route') != '')) { + $content_entities[$key] = [ + 'content_entity' => $key, + 'content_entity_bundle' => $entity_type->getBundleEntityType(), + ]; + } + } + return $content_entities; + } + + /** + * Gets an array of entity types that should trigger a menu rebuild. + * + * @return array + * An array of entity machine names. + */ + public function getRebuildEntityTypes() { + $types = ['menu']; + $content_entities = $this->getBundleableEntitiesList(); + $types = array_merge($types, array_column($content_entities, 'content_entity_bundle')); + return $types; + } + +} diff --git a/web/modules/admin_toolbar/admin_toolbar_tools/src/Controller/ToolbarController.php b/web/modules/admin_toolbar/admin_toolbar_tools/src/Controller/ToolbarController.php index 7677f2af67..22ccded1fc 100755 --- a/web/modules/admin_toolbar/admin_toolbar_tools/src/Controller/ToolbarController.php +++ b/web/modules/admin_toolbar/admin_toolbar_tools/src/Controller/ToolbarController.php @@ -2,21 +2,20 @@ namespace Drupal\admin_toolbar_tools\Controller; -use Drupal\admin_toolbar_tools\SearchLinks; use Drupal\Component\Datetime\TimeInterface; use Drupal\Core\Cache\CacheBackendInterface; use Drupal\Core\Controller\ControllerBase; use Drupal\Core\CronInterface; -use Drupal\Core\Menu\ContextualLinkManagerInterface; -use Drupal\Core\Menu\LocalActionManagerInterface; -use Drupal\Core\Menu\LocalTaskManagerInterface; +use Drupal\Core\Menu\ContextualLinkManager; +use Drupal\Core\Menu\LocalActionManager; +use Drupal\Core\Menu\LocalTaskManager; use Drupal\Core\Menu\MenuLinkManagerInterface; use Drupal\Core\Plugin\CachedDiscoveryClearerInterface; use Symfony\Component\DependencyInjection\ContainerInterface; -use Symfony\Component\HttpFoundation\JsonResponse; use Symfony\Component\HttpFoundation\RedirectResponse; use Symfony\Component\HttpFoundation\RequestStack; use Drupal\Core\Template\TwigEnvironment; +use Drupal\Core\Theme\Registry; /** * Class ToolbarController. @@ -42,21 +41,21 @@ class ToolbarController extends ControllerBase { /** * A context link manager instance. * - * @var \Drupal\Core\Menu\ContextualLinkManagerInterface + * @var \Drupal\Core\Menu\ContextualLinkManager */ protected $contextualLinkManager; /** * A local task manager instance. * - * @var \Drupal\Core\Menu\LocalTaskManagerInterface + * @var \Drupal\Core\Menu\LocalTaskManager */ protected $localTaskLinkManager; /** * A local action manager instance. * - * @var \Drupal\Core\Menu\LocalActionManagerInterface + * @var \Drupal\Core\Menu\LocalActionManager */ protected $localActionLinkManager; @@ -103,11 +102,11 @@ class ToolbarController extends ControllerBase { protected $twig; /** - * The search links service. + * The search theme.registry service. * - * @var \Drupal\admin_toolbar_tools\SearchLinks + * @var \Drupal\Core\Theme\Registry */ - protected $links; + protected $themeRegistry; /** * Constructs a ToolbarController object. @@ -116,11 +115,11 @@ class ToolbarController extends ControllerBase { * A cron instance. * @param \Drupal\Core\Menu\MenuLinkManagerInterface $menuLinkManager * A menu link manager instance. - * @param \Drupal\Core\Menu\ContextualLinkManagerInterface $contextualLinkManager + * @param \Drupal\Core\Menu\ContextualLinkManager $contextualLinkManager * A context link manager instance. - * @param \Drupal\Core\Menu\LocalTaskManagerInterface $localTaskLinkManager + * @param \Drupal\Core\Menu\LocalTaskManager $localTaskLinkManager * A local task manager instance. - * @param \Drupal\Core\Menu\LocalActionManagerInterface $localActionLinkManager + * @param \Drupal\Core\Menu\LocalActionManager $localActionLinkManager * A local action manager instance. * @param \Drupal\Core\Cache\CacheBackendInterface $cacheRender * A cache backend interface instance. @@ -134,21 +133,23 @@ class ToolbarController extends ControllerBase { * A cache menu instance. * @param \Drupal\Core\Template\TwigEnvironment $twig * A TwigEnvironment instance. - * @param \Drupal\admin_toolbar_tools\SearchLinks $links - * The search links service. + * @param \Drupal\Core\Theme\Registry $theme_registry + * The theme.registry service. */ - public function __construct(CronInterface $cron, - MenuLinkManagerInterface $menuLinkManager, - ContextualLinkManagerInterface $contextualLinkManager, - LocalTaskManagerInterface $localTaskLinkManager, - LocalActionManagerInterface $localActionLinkManager, - CacheBackendInterface $cacheRender, - TimeInterface $time, - RequestStack $request_stack, - CachedDiscoveryClearerInterface $plugin_cache_clearer, - CacheBackendInterface $cache_menu, - TwigEnvironment $twig, - SearchLinks $links) { + public function __construct( + CronInterface $cron, + MenuLinkManagerInterface $menuLinkManager, + ContextualLinkManager $contextualLinkManager, + LocalTaskManager $localTaskLinkManager, + LocalActionManager $localActionLinkManager, + CacheBackendInterface $cacheRender, + TimeInterface $time, + RequestStack $request_stack, + CachedDiscoveryClearerInterface $plugin_cache_clearer, + CacheBackendInterface $cache_menu, + TwigEnvironment $twig, + Registry $theme_registry + ) { $this->cron = $cron; $this->menuLinkManager = $menuLinkManager; $this->contextualLinkManager = $contextualLinkManager; @@ -160,7 +161,7 @@ public function __construct(CronInterface $cron, $this->pluginCacheClearer = $plugin_cache_clearer; $this->cacheMenu = $cache_menu; $this->twig = $twig; - $this->links = $links; + $this->themeRegistry = $theme_registry; } /** @@ -179,7 +180,7 @@ public static function create(ContainerInterface $container) { $container->get('plugin.cache_clearer'), $container->get('cache.menu'), $container->get('twig'), - $container->get('admin_toolbar_tools.search_links') + $container->get('theme.registry') ); } @@ -283,10 +284,12 @@ public function cacheRender() { } /** - * Return additional search links. + * Rebuild the theme registry. */ - public function search() { - return new JsonResponse($this->links->getLinks()); + public function themeRebuild() { + $this->themeRegistry->reset(); + $this->messenger()->addMessage($this->t('Theme registry rebuilded.')); + return new RedirectResponse($this->reloadPage()); } } diff --git a/web/modules/admin_toolbar/admin_toolbar_tools/src/Plugin/Derivative/ExtraLinks.php b/web/modules/admin_toolbar/admin_toolbar_tools/src/Plugin/Derivative/ExtraLinks.php index c667b6b38b..e3d62177c4 100755 --- a/web/modules/admin_toolbar/admin_toolbar_tools/src/Plugin/Derivative/ExtraLinks.php +++ b/web/modules/admin_toolbar/admin_toolbar_tools/src/Plugin/Derivative/ExtraLinks.php @@ -52,7 +52,7 @@ class ExtraLinks extends DeriverBase implements ContainerDeriverInterface { /** * {@inheritdoc} */ - public function __construct($base_plugin_id, EntityTypeManagerInterface $entity_type_manager, ModuleHandlerInterface $module_handler, RouteProviderInterface $route_provider, ThemeHandlerInterface $theme_handler) { + public function __construct(EntityTypeManagerInterface $entity_type_manager, ModuleHandlerInterface $module_handler, RouteProviderInterface $route_provider, ThemeHandlerInterface $theme_handler) { $this->entityTypeManager = $entity_type_manager; $this->moduleHandler = $module_handler; $this->routeProvider = $route_provider; @@ -64,7 +64,6 @@ public function __construct($base_plugin_id, EntityTypeManagerInterface $entity_ */ public static function create(ContainerInterface $container, $base_plugin_id) { return new static( - $base_plugin_id, $container->get('entity_type.manager'), $container->get('module_handler'), $container->get('router.route_provider'), @@ -96,7 +95,7 @@ public function getDerivativeDefinitions($base_plugin_definition) { $content_entity_bundle_storage = $this->entityTypeManager->getStorage($content_entity_bundle); $bundles_ids = $content_entity_bundle_storage->getQuery()->pager(self::MAX_BUNDLE_NUMBER)->execute(); $bundles = $this->entityTypeManager->getStorage($content_entity_bundle)->loadMultiple($bundles_ids); - if (count($bundles) == self::MAX_BUNDLE_NUMBER) { + if (count($bundles) == self::MAX_BUNDLE_NUMBER && $this->routeExists('entity.' . $content_entity_bundle . '.collection')) { $links[$content_entity_bundle . '.collection'] = [ 'title' => $this->t('All types'), 'route_name' => 'entity.' . $content_entity_bundle . '.collection', @@ -130,8 +129,8 @@ public function getDerivativeDefinitions($base_plugin_definition) { $content_entity_bundle_root = $key; } else { - $links[$key]['parent'] = $content_entity_bundle_root; - $links[$key]['title'] = t('Edit'); + $links[$key]['parent'] = $base_plugin_definition['id'] . ':' . $content_entity_bundle_root; + $links[$key]['title'] = $this->t('Edit'); } } if ($this->moduleHandler->moduleExists('field_ui')) { @@ -191,23 +190,23 @@ public function getDerivativeDefinitions($base_plugin_definition) { 'parent' => 'entity.user.collection', ] + $base_plugin_definition; $links['user.admin_permissions'] = [ - 'title' => t('Permissions'), + 'title' => $this->t('Permissions'), 'route_name' => 'user.admin_permissions', 'parent' => 'entity.user.collection', ] + $base_plugin_definition; $links['entity.user_role.collection'] = [ - 'title' => t('Roles'), + 'title' => $this->t('Roles'), 'route_name' => 'entity.user_role.collection', 'parent' => 'entity.user.collection', ] + $base_plugin_definition; $links['user.logout'] = [ - 'title' => t('Logout'), + 'title' => $this->t('Logout'), 'route_name' => 'user.logout', 'parent' => 'admin_toolbar_tools.help', 'weight' => 10, ] + $base_plugin_definition; $links['user.role_add'] = [ - 'title' => t('Add role'), + 'title' => $this->t('Add role'), 'route_name' => 'user.role_add', 'parent' => $base_plugin_definition['id'] . ':entity.user_role.collection', 'weight' => -5, diff --git a/web/modules/admin_toolbar/admin_toolbar_tools/tests/src/Functional/AdminToolbarToolsAlterTest.php b/web/modules/admin_toolbar/admin_toolbar_tools/tests/src/Functional/AdminToolbarToolsAlterTest.php index 94c27cd59e..9669a49a5f 100755 --- a/web/modules/admin_toolbar/admin_toolbar_tools/tests/src/Functional/AdminToolbarToolsAlterTest.php +++ b/web/modules/admin_toolbar/admin_toolbar_tools/tests/src/Functional/AdminToolbarToolsAlterTest.php @@ -22,6 +22,11 @@ class AdminToolbarToolsAlterTest extends BrowserTestBase { 'admin_toolbar_tools', ]; + /** + * {@inheritdoc} + */ + protected $defaultTheme = 'stark'; + /** * A test user with permission to access the administrative toolbar. * diff --git a/web/modules/admin_toolbar/composer.json b/web/modules/admin_toolbar/composer.json index a97caac9b0..650ed769fb 100755 --- a/web/modules/admin_toolbar/composer.json +++ b/web/modules/admin_toolbar/composer.json @@ -26,10 +26,13 @@ "name": "Mohamed Anis Taktak (matio89)", "homepage": "https://www.drupal.org/u/matio89", "role": "Maintainer" - } + } ], "support": { "issues": "https://www.drupal.org/project/issues/admin_toolbar", "source": "http://cgit.drupalcode.org/admin_toolbar" + }, + "require": { + "drupal/core": "^8.8.0 || ^9.0" } } diff --git a/web/modules/admin_toolbar/src/Render/Element/AdminToolbar.php b/web/modules/admin_toolbar/src/Render/Element/AdminToolbar.php new file mode 100644 index 0000000000..5d0000011f --- /dev/null +++ b/web/modules/admin_toolbar/src/Render/Element/AdminToolbar.php @@ -0,0 +1,51 @@ +<?php + +namespace Drupal\admin_toolbar\Render\Element; + +use Drupal\Core\Menu\MenuTreeParameters; +use Drupal\Core\Security\TrustedCallbackInterface; + +/** + * Class AdminToolbar. + * + * @package Drupal\admin_toolbar\Render\Element + */ +class AdminToolbar implements TrustedCallbackInterface { + + /** + * {@inheritdoc} + */ + public static function trustedCallbacks() { + return ['preRenderTray']; + } + + /** + * Renders the toolbar's administration tray. + * + * This is a clone of core's toolbar_prerender_toolbar_administration_tray() + * function, which uses setMaxDepth(4) instead of setTopLevelOnly(). + * + * @param array $build + * A renderable array. + * + * @return array + * The updated renderable array. + * + * @see toolbar_prerender_toolbar_administration_tray() + */ + public static function preRenderTray(array $build) { + $menu_tree = \Drupal::service('toolbar.menu_tree'); + $parameters = new MenuTreeParameters(); + $parameters->setRoot('system.admin')->excludeRoot()->setMaxDepth(4)->onlyEnabledLinks(); + $tree = $menu_tree->load(NULL, $parameters); + $manipulators = [ + ['callable' => 'menu.default_tree_manipulators:checkAccess'], + ['callable' => 'menu.default_tree_manipulators:generateIndexAndSort'], + ['callable' => 'toolbar_tools_menu_navigation_links'], + ]; + $tree = $menu_tree->transform($tree, $manipulators); + $build['administration_menu'] = $menu_tree->build($tree); + return $build; + } + +} diff --git a/web/modules/admin_toolbar/tests/src/Functional/AdminToolbarAlterTest.php b/web/modules/admin_toolbar/tests/src/Functional/AdminToolbarAlterTest.php index bd57d502b3..c17f575ee5 100755 --- a/web/modules/admin_toolbar/tests/src/Functional/AdminToolbarAlterTest.php +++ b/web/modules/admin_toolbar/tests/src/Functional/AdminToolbarAlterTest.php @@ -22,6 +22,11 @@ class AdminToolbarAlterTest extends BrowserTestBase { 'admin_toolbar', ]; + /** + * {@inheritdoc} + */ + protected $defaultTheme = 'stark'; + /** * A test user with permission to access the administrative toolbar. * diff --git a/web/modules/admin_toolbar/tests/src/Functional/AdminToolbarToolsSortTest.php b/web/modules/admin_toolbar/tests/src/Functional/AdminToolbarToolsSortTest.php index 88a6261b1c..8da6ca9ae2 100644 --- a/web/modules/admin_toolbar/tests/src/Functional/AdminToolbarToolsSortTest.php +++ b/web/modules/admin_toolbar/tests/src/Functional/AdminToolbarToolsSortTest.php @@ -28,6 +28,11 @@ class AdminToolbarToolsSortTest extends BrowserTestBase { 'field_ui', ]; + /** + * {@inheritdoc} + */ + protected $defaultTheme = 'stark'; + /** * A test user with permission to access the administrative toolbar. * @@ -35,13 +40,6 @@ class AdminToolbarToolsSortTest extends BrowserTestBase { */ protected $adminUser; - /** - * {@inheritdoc} - */ - protected function setUp() { - parent::setUp(); - } - /** * Tests that menu updates on entity add/update/delete. */ diff --git a/web/modules/admin_toolbar/tests/src/FunctionalJavascript/AdminToolbarSearchTest.php b/web/modules/admin_toolbar/tests/src/FunctionalJavascript/AdminToolbarSearchTest.php deleted file mode 100755 index 5bd143f470..0000000000 --- a/web/modules/admin_toolbar/tests/src/FunctionalJavascript/AdminToolbarSearchTest.php +++ /dev/null @@ -1,339 +0,0 @@ -<?php - -namespace Drupal\Tests\admin_toolbar\FunctionalJavascript; - -use Drupal\FunctionalJavascriptTests\WebDriverTestBase; -use Drupal\media\Entity\MediaType; -use Drupal\system\Entity\Menu; -use Drupal\Tests\media\Traits\MediaTypeCreationTrait; - -/** - * Test the functionality of admin toolbar search. - * - * @group admin_toolbar - */ -class AdminToolbarSearchTest extends WebDriverTestBase { - - use MediaTypeCreationTrait; - - /** - * {@inheritdoc} - */ - public static $modules = [ - 'admin_toolbar', - 'admin_toolbar_tools', - 'node', - 'media', - 'field_ui', - 'menu_ui', - 'block', - ]; - - /** - * The admin user for tests. - * - * @var \Drupal\user\UserInterface - */ - protected $adminUser; - - /** - * {@inheritdoc} - */ - public function setUp() { - parent::setUp(); - - $this->drupalCreateContentType([ - 'type' => 'article', - 'name' => 'Article', - ]); - - $dog_names = [ - 'archie' => 'Archie', - 'bailey' => 'Bailey', - 'bella' => 'Bella', - 'buddy' => 'Buddy', - 'charlie' => 'Charlie', - 'coco' => 'Coco', - 'daisy' => 'Daisy', - 'frankie' => 'Frankie', - 'jack' => 'Jack', - 'lola' => 'Lola', - 'lucy' => 'Lucy', - 'max' => 'Max', - 'milo' => 'Milo', - 'molly' => 'Molly', - 'ollie' => 'Ollie', - 'oscar' => 'Oscar', - 'rosie' => 'Rosie', - 'ruby' => 'Ruby', - 'teddy' => 'Teddy', - 'toby' => 'Toby', - ]; - - foreach ($dog_names as $machine_name => $label) { - $this->createMediaType('image', [ - 'id' => $machine_name, - 'label' => $label, - ]); - } - - $baby_names = [ - 'ada' => 'Ada', - 'amara' => 'Amara', - 'amelia' => 'Amelia', - 'arabella' => 'Arabella', - 'asher' => 'Asher', - 'astrid' => 'Astrid', - 'atticus' => 'Atticus', - 'aurora' => 'Aurora', - 'ava' => 'Ava', - 'cora' => 'Cora', - 'eleanor' => 'Eleanor', - 'eloise' => 'Eloise', - 'felix' => 'Felix', - 'freya' => 'Freya', - 'genevieve' => 'Genevieve', - 'isla' => 'Isla', - 'jasper' => 'Jasper', - 'luna' => 'Luna', - 'maeve' => 'Maeve', - 'milo' => 'Milo', - 'nora' => 'Nora', - 'olivia' => 'Olivia', - 'ophelia' => 'Ophelia', - 'posie' => 'Posie', - 'rose' => 'Rose', - 'silas' => 'Silas', - 'soren' => 'Soren', - ]; - - foreach ($baby_names as $id => $label) { - $menu = Menu::create([ - 'id' => $id, - 'label' => $label, - ]); - $menu->save(); - } - - $this->drupalPlaceBlock('local_tasks_block'); - - $this->adminUser = $this->drupalCreateUser([ - 'access toolbar', - 'administer menu', - 'access administration pages', - 'administer site configuration', - 'administer content types', - 'administer node fields', - 'access media overview', - 'administer media', - 'administer media fields', - 'administer media form display', - 'administer media display', - 'administer media types', - ]); - } - - /** - * Tests search functionality. - */ - public function testSearchFunctionality() { - - $search_tab = '#toolbar-item-administration-search'; - $search_tray = '#toolbar-item-administration-search-tray'; - - $this->drupalLogin($this->adminUser); - $this->assertSession()->responseContains('admin.toolbar_search.css'); - $this->assertSession()->responseContains('admin_toolbar_search.js'); - $this->assertSession()->waitForElementVisible('css', $search_tab)->click(); - $this->assertSession()->waitForElementVisible('css', $search_tray); - - $this->assertSuggestionContains('basic', 'admin/config/system/site-information'); - - // Rebuild menu items. - drupal_flush_all_caches(); - - // Test that the route admin_toolbar.search returns expected json. - $this->drupalGet('/admin/admin-toolbar-search'); - - $search_menus = [ - 'cora', - 'eleanor', - 'eloise', - 'felix', - 'freya', - 'genevieve', - 'isla', - 'jasper', - 'luna', - 'maeve', - 'milo', - 'nora', - 'olivia', - 'ophelia', - 'posie', - 'rose', - 'silas', - 'soren', - ]; - - $toolbar_menus = [ - 'ada', - 'amara', - 'amelia', - 'arabella', - 'asher', - 'astrid', - 'atticus', - 'aurora', - 'ava', - ]; - - foreach ($search_menus as $menu_id) { - $this->assertSession()->responseContains('\/admin\/structure\/menu\/manage\/' . $menu_id); - } - - foreach ($toolbar_menus as $menu_id) { - $this->assertSession()->responseNotContains('\/admin\/structure\/menu\/manage\/' . $menu_id); - } - - $this->drupalGet('/admin'); - - foreach ($search_menus as $menu_id) { - $this->assertMenuDoesNotHaveHref('/admin/structure/menu/manage/' . $menu_id); - } - - foreach ($toolbar_menus as $menu_id) { - $this->assertMenuHasHref('/admin/structure/menu/manage/' . $menu_id); - } - - $this->drupalGet('admin/structure/types/manage/article/fields'); - $this->assertSession()->waitForElementVisible('css', $search_tray); - - $this->assertSuggestionContains('article manage fields', '/admin/structure/types/manage/article/fields'); - - $suggestions = $this->assertSession() - ->waitForElementVisible('css', 'ul.ui-autocomplete'); - - // Assert there is only one suggestion with a link to - // /admin/structure/types/manage/article/fields. - $count = count($suggestions->findAll('xpath', '//span[contains(text(), "/admin/structure/types/manage/article/fields")]')); - $this->assertEquals(1, $count); - - // Test that bundle within admin toolbar appears in search. - $this->assertSuggestionContains('lola', 'admin/structure/media/manage/lola/fields'); - - // Assert that a link after the limit (10) doesn't appear in admin toolbar. - $toby_url = '/admin/structure/media/manage/toby/fields'; - $this->assertSession() - ->elementNotContains('css', '#toolbar-administration', $toby_url); - - // Assert that a link excluded from admin toolbar appears in search. - $this->assertSuggestionContains('toby', $toby_url); - - // Test that adding a new bundle updates the extra links loaded from - // admin_toolbar.search route. - $this->createMediaType('image', [ - 'id' => 'zuzu', - 'label' => 'Zuzu', - ]); - - $this->drupalGet('admin'); - $this->assertSession()->waitForElementVisible('css', $search_tray); - $this->assertSuggestionContains('zuzu', '/admin/structure/media/manage/zuzu/fields'); - - // Test that deleting a bundle updates the extra links loaded from - // admin_toolbar.search route. - $toby = MediaType::load('toby'); - $toby->delete(); - - $this->getSession()->reload(); - $this->assertSession()->waitForElementVisible('css', $search_tray); - $this->assertSuggestionNotContains('toby', $toby_url); - - } - - /** - * Assert that the search suggestions contain a given string with given input. - * - * @param string $search - * The string to search for. - * @param string $contains - * Some HTML that is expected to be within the suggestions element. - */ - protected function assertSuggestionContains($search, $contains) { - $this->resetSearch(); - $page = $this->getSession()->getPage(); - $page->fillField('admin-toolbar-search-input', $search); - $page->waitFor(3, function () use ($page) { - return ($page->find('css', 'ul.ui-autocomplete')->isVisible() === TRUE); - }); - $suggestions_markup = $page->find('css', 'ul.ui-autocomplete')->getHtml(); - $this->assertContains($contains, $suggestions_markup); - } - - /** - * Assert that the search suggestions does not contain a given string. - * - * Assert that the search suggestions does not contain a given string with a - * given input. - * - * @param string $search - * The string to search for. - * @param string $contains - * Some HTML that is not expected to be within the suggestions element. - */ - protected function assertSuggestionNotContains($search, $contains) { - $this->resetSearch(); - $page = $this->getSession()->getPage(); - $page->fillField('admin-toolbar-search-input', $search); - $page->waitFor(3, function () use ($page) { - return ($page->find('css', 'ul.ui-autocomplete')->isVisible() === TRUE); - }); - if ($page->find('css', 'ul.ui-autocomplete')->isVisible() === FALSE) { - return; - } - else { - $suggestions_markup = $page->find('css', 'ul.ui-autocomplete')->getHtml(); - $this->assertNotContains($contains, $suggestions_markup); - } - } - - /** - * Search for an empty string to clear out the autocomplete suggestions. - */ - protected function resetSearch() { - $page = $this->getSession()->getPage(); - // Empty out the suggestions. - $page->fillField('admin-toolbar-search-input', ''); - $page->waitFor(3, function () use ($page) { - return ($page->find('css', 'ul.ui-autocomplete')->isVisible() === FALSE); - }); - } - - /** - * Checks that there is a link with the specified url in the admin toolbar. - * - * @param string $url - * The url to assert exists in the admin menu. - * - * @throws \Behat\Mink\Exception\ElementNotFoundException - */ - protected function assertMenuHasHref($url) { - $this->assertSession() - ->elementExists('xpath', '//div[@id="toolbar-item-administration-tray"]//a[contains(@href, "' . $url . '")]'); - } - - /** - * Checks that there is no link with the specified url in the admin toolbar. - * - * @param string $url - * The url to assert exists in the admin menu. - * - * @throws \Behat\Mink\Exception\ExpectationException - */ - protected function assertMenuDoesNotHaveHref($url) { - $this->assertSession() - ->elementNotExists('xpath', '//div[@id="toolbar-item-administration-tray"]//a[contains(@href, "' . $url . '")]'); - } - -} -- GitLab