From 42daa83c5e87334c00712b38e385d34a2620b55a Mon Sep 17 00:00:00 2001 From: Alex Pott Date: Wed, 5 Jun 2013 08:47:39 +0100 Subject: [PATCH] Issue #1911728 by ParisLiakos, Xano, dawehner, jibran, David_Rothstein: Remove hook_init(). --- core/authorize.php | 5 +- core/core.services.yml | 4 + core/includes/common.inc | 35 +++---- .../LegacyRequestSubscriber.php | 8 -- .../SlaveDatabaseIgnoreSubscriber.php | 60 ++++++++++++ .../action_loop_test/action_loop_test.module | 7 +- .../tests/language_test/language_test.module | 4 +- .../EventSubscriber/OverlaySubscriber.php | 94 ++++++++++++++++++- core/modules/overlay/overlay.module | 63 +------------ core/modules/overlay/overlay.services.yml | 1 + .../System/IgnoreSlaveSubscriberTest.php | 51 ++++++++++ .../system/Tests/System/SystemInitTest.php | 44 --------- .../system/Tests/Theme/HookInitTest.php | 43 --------- .../Theme/ThemeEarlyInitializationTest.php | 43 +++++++++ core/modules/system/system.api.php | 17 ---- core/modules/system/system.module | 29 ------ .../tests/modules/menu_test/menu_test.module | 18 ++-- .../modules/system_test/system_test.module | 16 +--- .../EventSubscriber/ThemeTestSubscriber.php | 54 +++++++++++ .../modules/theme_test/theme_test.module | 30 +----- .../theme_test/theme_test.services.yml | 5 + core/modules/update/update.module | 4 +- core/update.php | 4 +- 23 files changed, 358 insertions(+), 281 deletions(-) create mode 100644 core/lib/Drupal/Core/EventSubscriber/SlaveDatabaseIgnoreSubscriber.php create mode 100644 core/modules/system/lib/Drupal/system/Tests/System/IgnoreSlaveSubscriberTest.php delete mode 100644 core/modules/system/lib/Drupal/system/Tests/System/SystemInitTest.php delete mode 100644 core/modules/system/lib/Drupal/system/Tests/Theme/HookInitTest.php create mode 100644 core/modules/system/lib/Drupal/system/Tests/Theme/ThemeEarlyInitializationTest.php create mode 100644 core/modules/system/tests/modules/theme_test/lib/Drupal/theme_test/EventSubscriber/ThemeTestSubscriber.php create mode 100644 core/modules/system/tests/modules/theme_test/theme_test.services.yml diff --git a/core/authorize.php b/core/authorize.php index e146cfc9607..f347ba5afeb 100644 --- a/core/authorize.php +++ b/core/authorize.php @@ -27,9 +27,8 @@ chdir('..'); * Global flag to identify update.php and authorize.php runs. * * Identifies update.php and authorize.php runs, avoiding unwanted operations - * such as hook_init() invocations, css/js preprocessing and - * translation, and solves some theming issues. The flag is checked in other - * places in Drupal code (not just authorize.php). + * such as css/js preprocessing and translation, and solves some theming issues. + * The flag is checked in other places in Drupal code (not just authorize.php). */ const MAINTENANCE_MODE = 'update'; diff --git a/core/core.services.yml b/core/core.services.yml index 55d5b343ffd..856c1982d9c 100644 --- a/core/core.services.yml +++ b/core/core.services.yml @@ -427,3 +427,7 @@ services: batch.storage: class: Drupal\Core\Utility\BatchStorage arguments: ['@database'] + slave_database_ignore__subscriber: + class: Drupal\Core\EventSubscriber\SlaveDatabaseIgnoreSubscriber + tags: + - {name: event_subscriber} diff --git a/core/includes/common.inc b/core/includes/common.inc index aedb94e3df5..15e672e839d 100644 --- a/core/includes/common.inc +++ b/core/includes/common.inc @@ -1888,7 +1888,7 @@ function drupal_add_html_head_link($attributes, $header = FALSE) { * all typical visitors and most pages of a site. It is critical that all * preprocessed files are added unconditionally on every page, even if the * files do not happen to be needed on a page. This is normally done by calling - * drupal_add_css() in a hook_init() implementation. + * drupal_add_css() in a hook_page_build() implementation. * * Non-preprocessed files should only be added to the page when they are * actually needed. @@ -1943,14 +1943,15 @@ function drupal_add_html_head_link($attributes, $header = FALSE) { * enabled, this should be set to TRUE if the stylesheet is present on every * page of the website for users for whom it is present at all. This * defaults to FALSE. It is set to TRUE for stylesheets added via module and - * theme .info.yml files. Modules that add stylesheets within hook_init() - * implementations, or from other code that ensures that the stylesheet is - * added to all website pages, should also set this flag to TRUE. All - * stylesheets within the same group that have the 'every_page' flag set to - * TRUE and do not have 'preprocess' set to FALSE are aggregated together - * into a single aggregate file, and that aggregate file can be reused - * across a user's entire site visit, leading to faster navigation between - * pages. However, stylesheets that are only needed on pages less frequently + * theme .info.yml files. Modules that add stylesheets within + * hook_page_build() implementations, or from other code that ensures that + * the stylesheet is added to all website pages, should also set this flag + * to TRUE. All stylesheets within the same group that have the 'every_page' + * flag set to TRUE and do not have 'preprocess' set to FALSE are aggregated + * together into a single aggregate file, and that aggregate file can be + * reused across a user's entire site visit, leading to faster navigation + * between pages. + * However, stylesheets that are only needed on pages less frequently * visited, can be added by code that only runs for those particular pages, * and that code should not set the 'every_page' flag. This minimizes the * size of the aggregate file that the user needs to download when first @@ -3036,7 +3037,7 @@ function drupal_region_class($region) { * all typical visitors and most pages of a site. It is critical that all * preprocessed files are added unconditionally on every page, even if the * files are not needed on a page. This is normally done by calling - * drupal_add_js() in a hook_init() implementation. + * drupal_add_js() in a hook_page_build() implementation. * * Non-preprocessed files should only be added to the page when they are * actually needed. @@ -3079,9 +3080,9 @@ function drupal_region_class($region) { * page of the website for users for whom it is present at all. This * defaults to FALSE. It is set to TRUE for JavaScript files that are added * via module and theme .info.yml files. Modules that add JavaScript within - * hook_init() implementations, or from other code that ensures that the - * JavaScript is added to all website pages, should also set this flag to - * TRUE. All JavaScript files within the same group and that have the + * hook_page_build() implementations, or from other code that ensures that + * the JavaScript is added to all website pages, should also set this flag + * to TRUE. All JavaScript files within the same group and that have the * 'every_page' flag set to TRUE and do not have 'preprocess' set to FALSE * are aggregated together into a single aggregate file, and that aggregate * file can be reused across a user's entire site visit, leading to faster @@ -4365,16 +4366,8 @@ function _drupal_bootstrap_full($skip = FALSE) { // Let all modules take action before the menu system handles the request. // We do not want this while running update.php. if (!defined('MAINTENANCE_MODE') || MAINTENANCE_MODE != 'update') { - // Prior to invoking hook_init(), initialize the theme (potentially a custom - // one for this page), so that: - // - Modules with hook_init() implementations that call theme() or - // theme_get_registry() don't initialize the incorrect theme. - // - The theme can have hook_*_alter() implementations affect page building - // (e.g., hook_form_alter(), hook_node_view_alter(), hook_page_alter()), - // ahead of when rendering starts. menu_set_custom_theme(); drupal_theme_initialize(); - module_invoke_all('init'); } } diff --git a/core/lib/Drupal/Core/EventSubscriber/LegacyRequestSubscriber.php b/core/lib/Drupal/Core/EventSubscriber/LegacyRequestSubscriber.php index 242f9352cc4..39828ef352f 100644 --- a/core/lib/Drupal/Core/EventSubscriber/LegacyRequestSubscriber.php +++ b/core/lib/Drupal/Core/EventSubscriber/LegacyRequestSubscriber.php @@ -27,16 +27,8 @@ class LegacyRequestSubscriber implements EventSubscriberInterface { */ public function onKernelRequestLegacy(GetResponseEvent $event) { if ($event->getRequestType() == HttpKernelInterface::MASTER_REQUEST) { - // Prior to invoking hook_init(), initialize the theme (potentially a - // custom one for this page), so that: - // - Modules with hook_init() implementations that call theme() or - // theme_get_registry() don't initialize the incorrect theme. - // - The theme can have hook_*_alter() implementations affect page - // building (e.g., hook_form_alter(), hook_node_view_alter(), - // hook_page_alter()), ahead of when rendering starts. menu_set_custom_theme(); drupal_theme_initialize(); - module_invoke_all('init'); // Tell Drupal it is now fully bootstrapped (for the benefit of code that // calls drupal_get_bootstrap_phase()), but without having diff --git a/core/lib/Drupal/Core/EventSubscriber/SlaveDatabaseIgnoreSubscriber.php b/core/lib/Drupal/Core/EventSubscriber/SlaveDatabaseIgnoreSubscriber.php new file mode 100644 index 00000000000..e10ce040885 --- /dev/null +++ b/core/lib/Drupal/Core/EventSubscriber/SlaveDatabaseIgnoreSubscriber.php @@ -0,0 +1,60 @@ += REQUEST_TIME) { + Database::ignoreTarget('default', 'slave'); + } + else { + unset($_SESSION['ignore_slave_server']); + } + } + } + + /** + * {@inheritdoc} + */ + static function getSubscribedEvents() { + $events[KernelEvents::REQUEST][] = array('checkSlaveServer'); + return $events; + } + +} diff --git a/core/modules/action/tests/action_loop_test/action_loop_test.module b/core/modules/action/tests/action_loop_test/action_loop_test.module index 36f6d9bfc23..97dd8d9ce10 100644 --- a/core/modules/action/tests/action_loop_test/action_loop_test.module +++ b/core/modules/action/tests/action_loop_test/action_loop_test.module @@ -20,9 +20,12 @@ function action_loop_test_watchdog(array $log_entry) { } /** - * Implements hook_init(). + * Implements hook_custom_theme(). + * + * We need to check wheter a loop should be triggered and we do this as early + * possible, in the first hook that fires. */ -function action_loop_test_init() { +function action_loop_test_custom_theme() { if (!empty($_GET['trigger_action_on_watchdog'])) { watchdog_skip_semaphore('action_loop_test', 'Triggering action loop'); } diff --git a/core/modules/language/tests/language_test/language_test.module b/core/modules/language/tests/language_test/language_test.module index b83373a9e18..4877606b77e 100644 --- a/core/modules/language/tests/language_test/language_test.module +++ b/core/modules/language/tests/language_test/language_test.module @@ -11,9 +11,9 @@ use Symfony\Component\HttpKernel\HttpKernelInterface; use Drupal\Core\Language\Language; /** - * Implements hook_init(). + * Implements hook_page_build(). */ -function language_test_init() { +function language_test_page_build() { language_test_store_language_negotiation(); if (isset(language(Language::TYPE_INTERFACE)->langcode) && isset(language(Language::TYPE_INTERFACE)->method_id)) { drupal_set_message(t('Language negotiation method: @name', array('@name' => language(Language::TYPE_INTERFACE)->method_id))); diff --git a/core/modules/overlay/lib/Drupal/overlay/EventSubscriber/OverlaySubscriber.php b/core/modules/overlay/lib/Drupal/overlay/EventSubscriber/OverlaySubscriber.php index e2e02e9c91d..da15be13905 100644 --- a/core/modules/overlay/lib/Drupal/overlay/EventSubscriber/OverlaySubscriber.php +++ b/core/modules/overlay/lib/Drupal/overlay/EventSubscriber/OverlaySubscriber.php @@ -2,13 +2,17 @@ /** * @file - * Contains Drupal\overlay\EventSubscriber\OverlaySubscriber. + * Contains \Drupal\overlay\EventSubscriber\OverlaySubscriber. */ namespace Drupal\overlay\EventSubscriber; +use Drupal\Core\ContentNegotiation; +use Drupal\user\UserData; use Symfony\Component\EventDispatcher\EventSubscriberInterface; +use Symfony\Component\HttpFoundation\RedirectResponse; use Symfony\Component\HttpKernel\Event\FilterResponseEvent; +use Symfony\Component\HttpKernel\Event\GetResponseEvent; use Symfony\Component\HttpKernel\KernelEvents; /** @@ -16,6 +20,93 @@ use Symfony\Component\HttpKernel\KernelEvents; */ class OverlaySubscriber implements EventSubscriberInterface { + /** + * The content negotiation service. + * + * @var \Drupal\Core\ContentNegotiation + */ + protected $negotiation; + + /** + * The user.data service. + * + * @var \Drupal\user\UserData + */ + protected $userData; + + /** + * Constructs an OverlaySubscriber object. + * + * @param \Drupal\Core\ContentNegotiation $negotiation + * The content negotiation service. + * @param \Drupal\user\UserData $user_data + * The user.data service. + */ + public function __construct(ContentNegotiation $negotiation, UserData $user_data) { + $this->negotiation = $negotiation; + $this->userData = $user_data; + } + + /** + * Performs check on the beginning of a request. + * + * Determine whether the current page request is destined to appear in the + * parent window or in the overlay window, and format the page accordingly. + * + * @see overlay_set_mode() + */ + public function onRequest(GetResponseEvent $event) { + $request = $event->getRequest(); + if ($this->negotiation->getContentType($request) != 'html') { + // Only act on html pages. + return; + } + global $user; + + $mode = overlay_get_mode(); + + // Only act if the user has access to the overlay and a mode was not already + // set. Other modules can also enable the overlay directly for other uses. + $user_data = $this->userData->get('overlay', $user->uid, 'enabled'); + $use_overlay = !isset($user_data) || $user_data; + if (empty($mode) && user_access('access overlay') && $use_overlay) { + $current_path = $request->attributes->get('system_path'); + // After overlay is enabled on the modules page, redirect to + // #overlay=admin/modules to actually enable the overlay. + if (isset($_SESSION['overlay_enable_redirect']) && $_SESSION['overlay_enable_redirect']) { + unset($_SESSION['overlay_enable_redirect']); + $response = new RedirectResponse(url('', array('fragment' => 'overlay=' . $current_path, 'absolute' => TRUE))); + $event->setResponse($response); + } + + if ($request->query->get('render') == 'overlay') { + // If a previous page requested that we close the overlay, close it and + // redirect to the final destination. + if (isset($_SESSION['overlay_close_dialog'])) { + call_user_func_array('overlay_close_dialog', $_SESSION['overlay_close_dialog']); + unset($_SESSION['overlay_close_dialog']); + } + // If this page shouldn't be rendered inside the overlay, redirect to + // the parent. + elseif (!path_is_admin($current_path)) { + overlay_close_dialog($current_path, array('query' => drupal_get_query_parameters(NULL, array('render')))); + } + + // Indicate that we are viewing an overlay child page. + overlay_set_mode('child'); + + // Unset the render parameter to avoid it being included in URLs on the + // page. + $request->query->remove('render'); + } + // Do not enable the overlay if we already are on an admin page. + elseif (!path_is_admin($current_path)) { + // Otherwise add overlay parent code and our behavior. + overlay_set_mode('parent'); + } + } + } + /** * Performs end of request tasks. * @@ -48,6 +139,7 @@ class OverlaySubscriber implements EventSubscriberInterface { * {@inheritdoc} */ static function getSubscribedEvents() { + $events[KernelEvents::REQUEST][] = array('onRequest'); $events[KernelEvents::RESPONSE][] = array('onResponse'); return $events; diff --git a/core/modules/overlay/overlay.module b/core/modules/overlay/overlay.module index d400a32829d..d34f17524b3 100644 --- a/core/modules/overlay/overlay.module +++ b/core/modules/overlay/overlay.module @@ -125,59 +125,6 @@ function overlay_user_update($account) { } } -/** - * Implements hook_init(). - * - * Determine whether the current page request is destined to appear in the - * parent window or in the overlay window, and format the page accordingly. - * - * @see overlay_set_mode() - */ -function overlay_init() { - global $user; - - $mode = overlay_get_mode(); - - // Only act if the user has access to the overlay and a mode was not already - // set. Other modules can also enable the overlay directly for other uses. - $user_data = drupal_container()->get('user.data')->get('overlay', $user->uid, 'enabled'); - $use_overlay = !isset($user_data) || $user_data; - if (empty($mode) && user_access('access overlay') && $use_overlay) { - $current_path = current_path(); - // After overlay is enabled on the modules page, redirect to - // #overlay=admin/modules to actually enable the overlay. - if (isset($_SESSION['overlay_enable_redirect']) && $_SESSION['overlay_enable_redirect']) { - unset($_SESSION['overlay_enable_redirect']); - drupal_goto('', array('fragment' => 'overlay=' . $current_path)); - } - - if (isset($_GET['render']) && $_GET['render'] == 'overlay') { - // If a previous page requested that we close the overlay, close it and - // redirect to the final destination. - if (isset($_SESSION['overlay_close_dialog'])) { - call_user_func_array('overlay_close_dialog', $_SESSION['overlay_close_dialog']); - unset($_SESSION['overlay_close_dialog']); - } - // If this page shouldn't be rendered inside the overlay, redirect to the - // parent. - elseif (!path_is_admin($current_path)) { - overlay_close_dialog($current_path, array('query' => drupal_get_query_parameters(NULL, array('render')))); - } - - // Indicate that we are viewing an overlay child page. - overlay_set_mode('child'); - - // Unset the render parameter to avoid it being included in URLs on the page. - unset($_GET['render']); - } - // Do not enable the overlay if we already are on an admin page. - elseif (!path_is_admin($current_path)) { - // Otherwise add overlay parent code and our behavior. - overlay_set_mode('parent'); - } - } -} - /** * Implements hook_library_info(). */ @@ -602,10 +549,10 @@ function overlay_get_mode() { * - 'none': This is used to avoid adding any overlay-related code to the * page at all. Modules can set this to explicitly prevent the overlay from * being used. For example, since the overlay module itself sets the mode - * to 'parent' or 'child' in overlay_init() when certain conditions are - * met, other modules which want to override that behavior can do so by - * setting the mode to 'none' earlier in the page request - e.g., in their - * own hook_init() implementations, if they have a lower weight. + * to 'parent' or 'child' in the overlay event subscriber when certain + * conditions are met, other modules which want to override that behavior + * can do so by setting the mode to 'none' earlier in the page request - + * e.g., in their own event subscribers, if they have a higher priority. * This parameter is optional, and if omitted, the current mode will be * returned with no action taken. * @@ -613,7 +560,7 @@ function overlay_get_mode() { * The current mode, if any has been set, or NULL if no mode has been set. * * @ingroup overlay_api - * @see overlay_init() + * @see \Drupal\overlay\EventSubscriber\OverlaySubscriber::onRequest() */ function overlay_set_mode($mode = NULL) { global $base_path; diff --git a/core/modules/overlay/overlay.services.yml b/core/modules/overlay/overlay.services.yml index c64df816db6..7ab943f7858 100644 --- a/core/modules/overlay/overlay.services.yml +++ b/core/modules/overlay/overlay.services.yml @@ -3,3 +3,4 @@ services: class: Drupal\overlay\EventSubscriber\OverlaySubscriber tags: - { name: event_subscriber } + arguments: ['@content_negotiation', '@user.data'] diff --git a/core/modules/system/lib/Drupal/system/Tests/System/IgnoreSlaveSubscriberTest.php b/core/modules/system/lib/Drupal/system/Tests/System/IgnoreSlaveSubscriberTest.php new file mode 100644 index 00000000000..bf004f9444a --- /dev/null +++ b/core/modules/system/lib/Drupal/system/Tests/System/IgnoreSlaveSubscriberTest.php @@ -0,0 +1,51 @@ + 'Slave database ignoring event listener', + 'description' => 'Tests that SlaveDatabaseIgnoreSubscriber functions correctly.', + 'group' => 'System', + ); + } + + /** + * Tests \Drupal\Core\EventSubscriber\SlaveDatabaseIgnoreSubscriber::checkSlaveServer(). + */ + function testSystemInitIgnoresSlaves() { + // Clone the master credentials to a slave connection. + // Note this will result in two independent connection objects that happen + // to point to the same place. + $connection_info = Database::getConnectionInfo('default'); + Database::addConnectionInfo('default', 'slave', $connection_info['default']); + + db_ignore_slave(); + $kernel = new DrupalKernel('testing', FALSE, drupal_classloader(), FALSE); + $event = new GetResponseEvent($kernel, Request::create('http://example.com'), HttpKernelInterface::MASTER_REQUEST); + $subscriber = new SlaveDatabaseIgnoreSubscriber(); + $subscriber->checkSlaveServer($event); + + $db1 = Database::getConnection('default', 'default'); + $db2 = Database::getConnection('slave', 'default'); + + $this->assertIdentical($db1, $db2, 'System Init ignores slaves when requested.'); + } +} diff --git a/core/modules/system/lib/Drupal/system/Tests/System/SystemInitTest.php b/core/modules/system/lib/Drupal/system/Tests/System/SystemInitTest.php deleted file mode 100644 index 715764791f8..00000000000 --- a/core/modules/system/lib/Drupal/system/Tests/System/SystemInitTest.php +++ /dev/null @@ -1,44 +0,0 @@ - 'System Init', - 'description' => 'Tests the system_init function in system.module.', - 'group' => 'System', - ); - } - - /** - * Tests that system_init properly ignores slaves when requested. - */ - function testSystemInitIgnoresSlaves() { - // Clone the master credentials to a slave connection. - // Note this will result in two independent connection objects that happen - // to point to the same place. - $connection_info = Database::getConnectionInfo('default'); - Database::addConnectionInfo('default', 'slave', $connection_info['default']); - - db_ignore_slave(); - system_init(); - - $db1 = Database::getConnection('default', 'default'); - $db2 = Database::getConnection('slave', 'default'); - - $this->assertIdentical($db1, $db2, 'System Init ignores slaves when requested.'); - } -} diff --git a/core/modules/system/lib/Drupal/system/Tests/Theme/HookInitTest.php b/core/modules/system/lib/Drupal/system/Tests/Theme/HookInitTest.php deleted file mode 100644 index 3863d22f165..00000000000 --- a/core/modules/system/lib/Drupal/system/Tests/Theme/HookInitTest.php +++ /dev/null @@ -1,43 +0,0 @@ - 'Theme initialization in hook_init()', - 'description' => 'Tests that the theme system can be correctly initialized in hook_init().', - 'group' => 'Theme', - ); - } - - /** - * Test that the theme system can generate output when called by hook_init(). - */ - function testThemeInitializationHookInit() { - $this->drupalGet('theme-test/hook-init'); - // Verify that themed output generated in hook_init() appears. - $this->assertRaw('Themed output generated in hook_init()'); - // Verify that the default theme's CSS still appears when the theme system - // is initialized in hook_init(). - $this->assertRaw('stark/css/layout.css'); - } -} diff --git a/core/modules/system/lib/Drupal/system/Tests/Theme/ThemeEarlyInitializationTest.php b/core/modules/system/lib/Drupal/system/Tests/Theme/ThemeEarlyInitializationTest.php new file mode 100644 index 00000000000..b2d1b45137e --- /dev/null +++ b/core/modules/system/lib/Drupal/system/Tests/Theme/ThemeEarlyInitializationTest.php @@ -0,0 +1,43 @@ + 'Early theme initialization', + 'description' => 'Tests that the theme system can be correctly initialized early in the page request.', + 'group' => 'Theme', + ); + } + + /** + * Test that the theme system can generate output in a request listener. + */ + function testRequestListener() { + $this->drupalGet('theme-test/request-listener'); + // Verify that themed output generated in the request listener appears. + $this->assertRaw('Themed output generated in a KernelEvents::REQUEST listener'); + // Verify that the default theme's CSS still appears even though the theme + // system was initialized early. + $this->assertRaw('stark/css/layout.css'); + } +} diff --git a/core/modules/system/system.api.php b/core/modules/system/system.api.php index 18bcac37173..32e4efc5ea5 100644 --- a/core/modules/system/system.api.php +++ b/core/modules/system/system.api.php @@ -1347,23 +1347,6 @@ function hook_forms($form_id, $args) { return $forms; } -/** - * Perform setup tasks for non-cached page requests. - * - * This hook is run at the beginning of the page request. It is typically - * used to set up global parameters that are needed later in the request. - * When this hook is called, the theme and all modules are already loaded in - * memory. - * - * This hook is not run on cached pages. - * - * Do not use this hook to add CSS/JS to pages, use hook_page_build() instead. - * - * @see hook_page_build() - */ -function hook_init() { -} - /** * Alter an email message created with the drupal_mail() function. * diff --git a/core/modules/system/system.module b/core/modules/system/system.module index 6f84d166f57..cf877acc165 100644 --- a/core/modules/system/system.module +++ b/core/modules/system/system.module @@ -8,7 +8,6 @@ use Drupal\Core\Cache\CacheBackendInterface; use Drupal\Core\Cache\Cache; use Drupal\Core\Language\Language; -use Drupal\Core\Database\Database; use Drupal\Core\Utility\ModuleInfo; use Drupal\Core\TypedData\Primitive; use Drupal\system\Plugin\Block\SystemMenuBlock; @@ -2503,34 +2502,6 @@ function system_filetransfer_info() { return $backends; } -/** - * Implements hook_init(). - */ -function system_init() { - // Ignore slave database servers for this request. - // - // In Drupal's distributed database structure, new data is written to the - // master and then propagated to the slave servers. This means there is a - // lag between when data is written to the master and when it is available on - // the slave. At these times, we will want to avoid using a slave server - // temporarily. For example, if a user posts a new node then we want to - // disable the slave server for that user temporarily to allow the slave - // server to catch up. That way, that user will see their changes immediately - // while for other users we still get the benefits of having a slave server, - // just with slightly stale data. Code that wants to disable the slave - // server should use the db_ignore_slave() function to set - // $_SESSION['ignore_slave_server'] to the timestamp after which the slave - // can be re-enabled. - if (isset($_SESSION['ignore_slave_server'])) { - if ($_SESSION['ignore_slave_server'] >= REQUEST_TIME) { - Database::ignoreTarget('default', 'slave'); - } - else { - unset($_SESSION['ignore_slave_server']); - } - } -} - /** * Implements hook_page_build(). */ diff --git a/core/modules/system/tests/modules/menu_test/menu_test.module b/core/modules/system/tests/modules/menu_test/menu_test.module index c5a0be6ae5d..fec466b2a84 100644 --- a/core/modules/system/tests/modules/menu_test/menu_test.module +++ b/core/modules/system/tests/modules/menu_test/menu_test.module @@ -531,18 +531,6 @@ function menu_test_menu_trail_callback() { return 'This is menu_test_menu_trail_callback().'; } -/** - * Implements hook_init(). - */ -function menu_test_init() { - // When requested by one of the MenuTrailTestCase tests, record the initial - // active trail during Drupal's bootstrap (before the user is redirected to a - // custom 403 or 404 page). See menu_test_custom_403_404_callback(). - if (state()->get('menu_test.record_active_trail') ?: FALSE) { - state()->set('menu_test.active_trail_initial', menu_get_active_trail()); - } -} - /** * Callback for our custom 403 and 404 pages. */ @@ -614,6 +602,12 @@ function menu_test_theme_callback($argument) { * The name of the custom theme to use for the current page. */ function menu_test_custom_theme() { + // When requested by one of the MenuTrailTestCase tests, record the initial + // active trail during Drupal's bootstrap (before the user is redirected to a + // custom 403 or 404 page). See menu_test_custom_403_404_callback(). + if (state()->get('menu_test.record_active_trail') ?: FALSE) { + state()->set('menu_test.active_trail_initial', menu_get_active_trail()); + } // If an appropriate variable has been set in the database, request the theme // that is stored there. Otherwise, do not attempt to dynamically set the // theme. diff --git a/core/modules/system/tests/modules/system_test/system_test.module b/core/modules/system/tests/modules/system_test/system_test.module index 31352d66b83..6afb8acb60e 100644 --- a/core/modules/system/tests/modules/system_test/system_test.module +++ b/core/modules/system/tests/modules/system_test/system_test.module @@ -128,17 +128,6 @@ function system_test_modules_uninstalled($modules) { } } -/** - * Implements hook_init(). - */ -function system_test_init() { - // Used by FrontPageTestCase to get the results of drupal_is_front_page(). - $frontpage = state()->get('system_test.front_page_output') ?: 0; - if ($frontpage && drupal_is_front_page()) { - drupal_set_message(t('On front page.')); - } -} - /** * Implements hook_system_info_alter(). */ @@ -220,6 +209,11 @@ function system_test_page_build(&$page) { elseif ($menu_item['path'] == 'system-test/main-content-duplication') { drupal_set_page_content(); } + // Used by FrontPageTestCase to get the results of drupal_is_front_page(). + $frontpage = state()->get('system_test.front_page_output') ?: 0; + if ($frontpage && drupal_is_front_page()) { + drupal_set_message(t('On front page.')); + } } /** diff --git a/core/modules/system/tests/modules/theme_test/lib/Drupal/theme_test/EventSubscriber/ThemeTestSubscriber.php b/core/modules/system/tests/modules/theme_test/lib/Drupal/theme_test/EventSubscriber/ThemeTestSubscriber.php new file mode 100644 index 00000000000..bea8b1305d8 --- /dev/null +++ b/core/modules/system/tests/modules/theme_test/lib/Drupal/theme_test/EventSubscriber/ThemeTestSubscriber.php @@ -0,0 +1,54 @@ +getRequest(); + $current_path = $request->attributes->get('system_path'); + if ($current_path == 'theme-test/request-listener') { + // First, force the theme registry to be rebuilt on this page request. + // This allows us to test a full initialization of the theme system in + // the code below. + drupal_theme_rebuild(); + // Next, initialize the theme system by storing themed text in a global + // variable. We will use this later in + // theme_test_request_listener_page_callback() to test that even when the + // theme system is initialized this early, it is still capable of + // returning output and theming the page as a whole. + $GLOBALS['theme_test_output'] = theme('more_link', array('url' => 'user', 'title' => 'Themed output generated in a KernelEvents::REQUEST listener')); + } + if (strpos($current_path, 'user/autocomplete') === 0) { + // Register a fake registry loading callback. If it gets called by + // theme_get_registry(), the registry has not been initialized yet. + _theme_registry_callback('_theme_test_load_registry', array()); + } + } + + /** + * {@inheritdoc} + */ + static function getSubscribedEvents() { + $events[KernelEvents::REQUEST][] = array('onRequest'); + return $events; + } + +} diff --git a/core/modules/system/tests/modules/theme_test/theme_test.module b/core/modules/system/tests/modules/theme_test/theme_test.module index 42040774650..e2cf6bdf169 100644 --- a/core/modules/system/tests/modules/theme_test/theme_test.module +++ b/core/modules/system/tests/modules/theme_test/theme_test.module @@ -52,8 +52,8 @@ function theme_test_menu() { 'theme callback' => '_theme_custom_theme', 'type' => MENU_CALLBACK, ); - $items['theme-test/hook-init'] = array( - 'page callback' => 'theme_test_hook_init_page_callback', + $items['theme-test/request-listener'] = array( + 'page callback' => 'theme_test_request_listener_page_callback', 'access callback' => TRUE, 'type' => MENU_CALLBACK, ); @@ -70,28 +70,6 @@ function theme_test_menu() { return $items; } -/** - * Implements hook_init(). - */ -function theme_test_init() { - if (arg(0) == 'theme-test' && arg(1) == 'hook-init') { - // First, force the theme registry to be rebuilt on this page request. This - // allows us to test a full initialization of the theme system in the code - // below. - drupal_theme_rebuild(); - // Next, initialize the theme system by storing themed text in a global - // variable. We will use this later in theme_test_hook_init_page_callback() - // to test that even when the theme system is initialized this early, it is - // still capable of returning output and theming the page as a whole. - $GLOBALS['theme_test_output'] = theme('more_link', array('url' => 'user', 'title' => 'Themed output generated in hook_init()')); - } - if (arg(0) == 'user' && arg(1) == 'autocomplete') { - // Register a fake registry loading callback. If it gets called by - // theme_get_registry(), the registry has not been initialized yet. - _theme_registry_callback('_theme_test_load_registry', array()); - } -} - /** * Fake registry loading callback. */ @@ -101,9 +79,9 @@ function _theme_test_load_registry() { } /** - * Menu callback for testing themed output generated in hook_init(). + * Menu callback for testing themed output generated in a request listener. */ -function theme_test_hook_init_page_callback() { +function theme_test_request_listener_page_callback() { return $GLOBALS['theme_test_output']; } diff --git a/core/modules/system/tests/modules/theme_test/theme_test.services.yml b/core/modules/system/tests/modules/theme_test/theme_test.services.yml new file mode 100644 index 00000000000..8e442df9695 --- /dev/null +++ b/core/modules/system/tests/modules/theme_test/theme_test.services.yml @@ -0,0 +1,5 @@ +services: + theme_test.subscriber: + class: Drupal\theme_test\EventSubscriber\ThemeTestSubscriber + tags: + - { name: event_subscriber } diff --git a/core/modules/update/update.module b/core/modules/update/update.module index ddbc398fc2d..7ab224938c1 100644 --- a/core/modules/update/update.module +++ b/core/modules/update/update.module @@ -96,9 +96,9 @@ function update_help($path, $arg) { } /** - * Implements hook_init(). + * Implements hook_page_build(). */ -function update_init() { +function update_page_build() { if (arg(0) == 'admin' && user_access('administer site configuration')) { switch (current_path()) { // These pages don't need additional nagging. diff --git a/core/update.php b/core/update.php index b19f0cbb03b..823ac27cdd0 100644 --- a/core/update.php +++ b/core/update.php @@ -33,8 +33,8 @@ if (version_compare(PHP_VERSION, '5.3.10') < 0) { /** * Global flag indicating that update.php is being run. * - * When this flag is set, various operations do not take place, such as invoking - * hook_init(), css/js preprocessing, and translation. + * When this flag is set, various operations do not take place, such as css/js + * preprocessing and translation. * * This constant is defined using define() instead of const so that PHP * versions older than 5.3 can display the proper PHP requirements instead of