2014-10-31 00:19:48 +00:00
< ? php
2015-04-15 09:02:19 +00:00
2014-10-31 00:19:48 +00:00
/**
* @ file
2015-04-15 09:02:19 +00:00
* Hooks related to module and update systems .
2014-10-31 00:19:48 +00:00
*/
use Drupal\Core\Utility\UpdateException ;
use Drupal\Core\Url ;
/**
* @ addtogroup hooks
* @ {
*/
/**
* Defines one or more hooks that are exposed by a module .
*
* Normally hooks do not need to be explicitly defined . However , by declaring a
* hook explicitly , a module may define a " group " for it . Modules that implement
* a hook may then place their implementation in either $module . module or in
* $module . $group . inc . If the hook is located in $module . $group . inc , then that
* file will be automatically loaded when needed .
* In general , hooks that are rarely invoked and / or are very large should be
* placed in a separate include file , while hooks that are very short or very
* frequently called should be left in the main module file so that they are
* always available .
*
* @ return
* An associative array whose keys are hook names and whose values are an
* associative array containing :
* - group : A string defining the group to which the hook belongs . The module
* system will determine whether a file with the name $module . $group . inc
* exists , and automatically load it when required .
*
* See system_hook_info () for all hook groups defined by Drupal core .
*
* @ see hook_hook_info_alter () .
*/
function hook_hook_info () {
$hooks [ 'token_info' ] = array (
'group' => 'tokens' ,
);
$hooks [ 'tokens' ] = array (
'group' => 'tokens' ,
);
return $hooks ;
}
/**
* Alter the registry of modules implementing a hook .
*
* This hook is invoked during \Drupal :: moduleHandler () -> getImplementations () .
* A module may implement this hook in order to reorder the implementing
* modules , which are otherwise ordered by the module ' s system weight .
*
* Note that hooks invoked using \Drupal :: moduleHandler -> alter () can have
* multiple variations ( such as hook_form_alter () and hook_form_FORM_ID_alter ()) .
* \Drupal :: moduleHandler -> alter () will call all such variants defined by a
* single module in turn . For the purposes of hook_module_implements_alter (),
* these variants are treated as a single hook . Thus , to ensure that your
* implementation of hook_form_FORM_ID_alter () is called at the right time ,
* you will have to change the order of hook_form_alter () implementation in
* hook_module_implements_alter () .
*
* @ param $implementations
* An array keyed by the module ' s name . The value of each item corresponds
* to a $group , which is usually FALSE , unless the implementation is in a
* file named $module . $group . inc .
* @ param $hook
* The name of the module hook being implemented .
*/
function hook_module_implements_alter ( & $implementations , $hook ) {
2015-02-28 13:40:06 +00:00
if ( $hook == 'form_alter' ) {
// Move my_module_form_alter() to the end of the list.
2014-10-31 00:19:48 +00:00
// \Drupal::moduleHandler()->getImplementations()
// iterates through $implementations with a foreach loop which PHP iterates
// in the order that the items were added, so to move an item to the end of
// the array, we remove it and then add it.
$group = $implementations [ 'my_module' ];
unset ( $implementations [ 'my_module' ]);
$implementations [ 'my_module' ] = $group ;
}
}
/**
* Alter the information parsed from module and theme . info . yml files
*
* This hook is invoked in _system_rebuild_module_data () and in
2015-01-13 10:17:01 +00:00
* \Drupal\Core\Extension\ThemeHandlerInterface :: rebuildThemeData () . A module
* may implement this hook in order to add to or alter the data generated by
* reading the . info . yml file with \Drupal\Core\Extension\InfoParser .
2014-10-31 00:19:48 +00:00
*
* @ param array $info
* The . info . yml file contents , passed by reference so that it can be altered .
* @ param \Drupal\Core\Extension\Extension $file
* Full information about the module or theme .
* @ param string $type
* Either 'module' or 'theme' , depending on the type of . info . yml file that
* was passed .
*/
function hook_system_info_alter ( array & $info , \Drupal\Core\Extension\Extension $file , $type ) {
// Only fill this in if the .info.yml file does not define a 'datestamp'.
if ( empty ( $info [ 'datestamp' ])) {
$info [ 'datestamp' ] = $file -> getMTime ();
}
}
/**
* Perform necessary actions before a module is installed .
*
* @ param string $module
* The name of the module about to be installed .
*/
function hook_module_preinstall ( $module ) {
mymodule_cache_clear ();
}
/**
* Perform necessary actions after modules are installed .
*
* This function differs from hook_install () in that it gives all other modules
* a chance to perform actions when a module is installed , whereas
* hook_install () is only called on the module actually being installed . See
* \Drupal\Core\Extension\ModuleHandler :: install () for a detailed description of
* the order in which install hooks are invoked .
*
* @ param $modules
* An array of the modules that were installed .
*
* @ see \Drupal\Core\Extension\ModuleHandler :: install ()
* @ see hook_install ()
*/
function hook_modules_installed ( $modules ) {
if ( in_array ( 'lousy_module' , $modules )) {
\Drupal :: state () -> set ( 'mymodule.lousy_module_compatibility' , TRUE );
}
}
/**
* Perform setup tasks when the module is installed .
*
* If the module implements hook_schema (), the database tables will
* be created before this hook is fired .
*
* Implementations of this hook are by convention declared in the module ' s
* . install file . The implementation can rely on the . module file being loaded .
* The hook will only be called when a module is installed . The module ' s schema
* version will be set to the module ' s greatest numbered update hook . Because of
* this , any time a hook_update_N () is added to the module , this function needs
* to be updated to reflect the current version of the database schema .
*
* See the @ link http :// drupal . org / node / 146843 Schema API documentation @ endlink
* for details on hook_schema and how database tables are defined .
*
* Note that since this function is called from a full bootstrap , all functions
* ( including those in modules enabled by the current page request ) are
* available when this hook is called . Use cases could be displaying a user
* message , or calling a module function necessary for initial setup , etc .
*
* Please be sure that anything added or modified in this function that can
* be removed during uninstall should be removed with hook_uninstall () .
*
* @ see hook_schema ()
* @ see \Drupal\Core\Extension\ModuleHandler :: install ()
* @ see hook_uninstall ()
* @ see hook_modules_installed ()
*/
function hook_install () {
// Create the styles directory and ensure it's writable.
$directory = file_default_scheme () . '://styles' ;
$mode = isset ( $GLOBALS [ 'install_state' ][ 'mode' ]) ? $GLOBALS [ 'install_state' ][ 'mode' ] : NULL ;
file_prepare_directory ( $directory , FILE_CREATE_DIRECTORY | FILE_MODIFY_PERMISSIONS , $mode );
}
/**
* Perform necessary actions before a module is uninstalled .
*
* @ param string $module
* The name of the module about to be uninstalled .
*/
function hook_module_preuninstall ( $module ) {
mymodule_cache_clear ();
}
/**
* Perform necessary actions after modules are uninstalled .
*
* This function differs from hook_uninstall () in that it gives all other
* modules a chance to perform actions when a module is uninstalled , whereas
* hook_uninstall () is only called on the module actually being uninstalled .
*
* It is recommended that you implement this hook if your module stores
* data that may have been set by other modules .
*
* @ param $modules
* An array of the modules that were uninstalled .
*
* @ see hook_uninstall ()
*/
function hook_modules_uninstalled ( $modules ) {
if ( in_array ( 'lousy_module' , $modules )) {
\Drupal :: state () -> delete ( 'mymodule.lousy_module_compatibility' );
}
mymodule_cache_rebuild ();
}
/**
* Remove any information that the module sets .
*
* The information that the module should remove includes :
* - state that the module has set using \Drupal :: state ()
* - modifications to existing tables
*
* The module should not remove its entry from the module configuration .
* Database tables defined by hook_schema () will be removed automatically .
*
* The uninstall hook must be implemented in the module ' s . install file . It
* will fire when the module gets uninstalled but before the module ' s database
* tables are removed , allowing your module to query its own tables during
* this routine .
*
* @ see hook_install ()
* @ see hook_schema ()
* @ see hook_modules_uninstalled ()
*/
function hook_uninstall () {
// Remove the styles directory and generated images.
file_unmanaged_delete_recursive ( file_default_scheme () . '://styles' );
}
/**
* Return an array of tasks to be performed by an installation profile .
*
* Any tasks you define here will be run , in order , after the installer has
* finished the site configuration step but before it has moved on to the
2015-03-31 14:44:31 +00:00
* final import of languages and the end of the installation . This is invoked
* by install_tasks () . You can have any number of custom tasks to perform
* during this phase .
2014-10-31 00:19:48 +00:00
*
* Each task you define here corresponds to a callback function which you must
* separately define and which is called when your task is run . This function
* will receive the global installation state variable , $install_state , as
* input , and has the opportunity to access or modify any of its settings . See
* the install_state_defaults () function in the installer for the list of
* $install_state settings used by Drupal core .
*
* At the end of your task function , you can indicate that you want the
* installer to pause and display a page to the user by returning any themed
* output that should be displayed on that page ( but see below for tasks that
* use the form API or batch API ; the return values of these task functions are
* handled differently ) . You should also use #title within the task
* callback function to set a custom page title . For some tasks , however , you
* may want to simply do some processing and pass control to the next task
* without ending the page request ; to indicate this , simply do not send back
* a return value from your task function at all . This can be used , for
* example , by installation profiles that need to configure certain site
* settings in the database without obtaining any input from the user .
*
* The task function is treated specially if it defines a form or requires
* batch processing ; in that case , you should return either the form API
* definition or batch API array , as appropriate . See below for more
* information on the 'type' key that you must define in the task definition
* to inform the installer that your task falls into one of those two
* categories . It is important to use these APIs directly , since the installer
* may be run non - interactively ( for example , via a command line script ), all
* in one page request ; in that case , the installer will automatically take
* care of submitting forms and processing batches correctly for both types of
* installations . You can inspect the $install_state [ 'interactive' ] boolean to
* see whether or not the current installation is interactive , if you need
* access to this information .
*
* Remember that a user installing Drupal interactively will be able to reload
* an installation page multiple times , so you should use \Drupal :: state () to
* store any data that you may need later in the installation process . Any
* temporary state must be removed using \Drupal :: state () -> delete () before
* your last task has completed and control is handed back to the installer .
*
* @ param array $install_state
* An array of information about the current installation state .
*
* @ return array
* A keyed array of tasks the profile will perform during the final stage of
* the installation . Each key represents the name of a function ( usually a
* function defined by this profile , although that is not strictly required )
* that is called when that task is run . The values are associative arrays
* containing the following key - value pairs ( all of which are optional ) :
* - display_name : The human - readable name of the task . This will be
* displayed to the user while the installer is running , along with a list
* of other tasks that are being run . Leave this unset to prevent the task
* from appearing in the list .
* - display : This is a boolean which can be used to provide finer - grained
* control over whether or not the task will display . This is mostly useful
* for tasks that are intended to display only under certain conditions ;
* for these tasks , you can set 'display_name' to the name that you want to
* display , but then use this boolean to hide the task only when certain
* conditions apply .
* - type : A string representing the type of task . This parameter has three
* possible values :
* - normal : ( default ) This indicates that the task will be treated as a
* regular callback function , which does its processing and optionally
* returns HTML output .
* - batch : This indicates that the task function will return a batch API
2015-01-05 14:17:42 +00:00
* definition suitable for batch_set () or an array of batch definitions
* suitable for consecutive batch_set () calls . The installer will then
* take care of automatically running the task via batch processing .
2014-10-31 00:19:48 +00:00
* - form : This indicates that the task function will return a standard
* form API definition ( and separately define validation and submit
* handlers , as appropriate ) . The installer will then take care of
* automatically directing the user through the form submission process .
* - run : A constant representing the manner in which the task will be run .
* This parameter has three possible values :
* - INSTALL_TASK_RUN_IF_NOT_COMPLETED : ( default ) This indicates that the
* task will run once during the installation of the profile .
* - INSTALL_TASK_SKIP : This indicates that the task will not run during
* the current installation page request . It can be used to skip running
* an installation task when certain conditions are met , even though the
* task may still show on the list of installation tasks presented to the
* user .
* - INSTALL_TASK_RUN_IF_REACHED : This indicates that the task will run on
* each installation page request that reaches it . This is rarely
* necessary for an installation profile to use ; it is primarily used by
* the Drupal installer for bootstrap - related tasks .
* - function : Normally this does not need to be set , but it can be used to
* force the installer to call a different function when the task is run
* ( rather than the function whose name is given by the array key ) . This
* could be used , for example , to allow the same function to be called by
* two different tasks .
*
* @ see install_state_defaults ()
* @ see batch_set ()
2015-03-31 14:44:31 +00:00
* @ see hook_install_tasks_alter ()
* @ see install_tasks ()
2014-10-31 00:19:48 +00:00
*/
function hook_install_tasks ( & $install_state ) {
// Here, we define a variable to allow tasks to indicate that a particular,
// processor-intensive batch process needs to be triggered later on in the
// installation.
$myprofile_needs_batch_processing = \Drupal :: state () -> get ( 'myprofile.needs_batch_processing' , FALSE );
$tasks = array (
// This is an example of a task that defines a form which the user who is
// installing the site will be asked to fill out. To implement this task,
// your profile would define a function named myprofile_data_import_form()
// as a normal form API callback function, with associated validation and
// submit handlers. In the submit handler, in addition to saving whatever
// other data you have collected from the user, you might also call
// \Drupal::state()->set('myprofile.needs_batch_processing', TRUE) if the
// user has entered data which requires that batch processing will need to
// occur later on.
'myprofile_data_import_form' => array (
'display_name' => t ( 'Data import options' ),
'type' => 'form' ,
),
// Similarly, to implement this task, your profile would define a function
// named myprofile_settings_form() with associated validation and submit
// handlers. This form might be used to collect and save additional
// information from the user that your profile needs. There are no extra
// steps required for your profile to act as an "installation wizard"; you
// can simply define as many tasks of type 'form' as you wish to execute,
// and the forms will be presented to the user, one after another.
'myprofile_settings_form' => array (
'display_name' => t ( 'Additional options' ),
'type' => 'form' ,
),
// This is an example of a task that performs batch operations. To
// implement this task, your profile would define a function named
// myprofile_batch_processing() which returns a batch API array definition
// that the installer will use to execute your batch operations. Due to the
// 'myprofile.needs_batch_processing' variable used here, this task will be
// hidden and skipped unless your profile set it to TRUE in one of the
// previous tasks.
'myprofile_batch_processing' => array (
'display_name' => t ( 'Import additional data' ),
'display' => $myprofile_needs_batch_processing ,
'type' => 'batch' ,
'run' => $myprofile_needs_batch_processing ? INSTALL_TASK_RUN_IF_NOT_COMPLETED : INSTALL_TASK_SKIP ,
),
// This is an example of a task that will not be displayed in the list that
// the user sees. To implement this task, your profile would define a
// function named myprofile_final_site_setup(), in which additional,
// automated site setup operations would be performed. Since this is the
// last task defined by your profile, you should also use this function to
// call \Drupal::state()->delete('myprofile.needs_batch_processing') and
// clean up the state that was used above. If you want the user to pass
// to the final Drupal installation tasks uninterrupted, return no output
// from this function. Otherwise, return themed output that the user will
// see (for example, a confirmation page explaining that your profile's
// tasks are complete, with a link to reload the current page and therefore
// pass on to the final Drupal installation tasks when the user is ready to
// do so).
'myprofile_final_site_setup' => array (
),
);
return $tasks ;
}
/**
* Alter the full list of installation tasks .
*
* You can use this hook to change or replace any part of the Drupal
* installation process that occurs after the installation profile is selected .
*
2015-03-31 14:44:31 +00:00
* This hook is invoked on the install profile in install_tasks () .
*
2014-10-31 00:19:48 +00:00
* @ param $tasks
* An array of all available installation tasks , including those provided by
* Drupal core . You can modify this array to change or replace individual
* steps within the installation process .
* @ param $install_state
* An array of information about the current installation state .
2015-03-31 14:44:31 +00:00
*
* @ see hook_install_tasks ()
* @ see install_tasks ()
2014-10-31 00:19:48 +00:00
*/
function hook_install_tasks_alter ( & $tasks , $install_state ) {
// Replace the entire site configuration form provided by Drupal core
// with a custom callback function defined by this installation profile.
$tasks [ 'install_configure_form' ][ 'function' ] = 'myprofile_install_configure_form' ;
}
/**
* Perform a single update .
*
* For each change that requires one or more actions to be performed when
* updating a site , add a new hook_update_N (), which will be called by
* update . php . The documentation block preceding this function is stripped of
* newlines and used as the description for the update on the pending updates
* task list . Schema updates should adhere to the
* @ link http :// drupal . org / node / 150215 Schema API . @ endlink
*
* Implementations of hook_update_N () are named ( module name ) _update_ ( number ) .
* The numbers are composed of three parts :
* - 1 digit for Drupal core compatibility .
* - 1 digit for your module ' s major release version ( e . g . , is this the 8. x - 1. *
* ( 1 ) or 8. x - 2. * ( 2 ) series of your module ) .
* - 2 digits for sequential counting , starting with 01.
*
* Examples :
* - mymodule_update_8100 () : This is the first update to get the database ready
* to run mymodule 8. x - 1. *.
* - mymodule_update_8200 () : This is the first update to get the database ready
* to run mymodule 8. x - 2. *.
*
* As of Drupal 8.0 , the database upgrade system no longer supports updating a
* database from an earlier major version of Drupal : update . php can be used to
* upgrade from 7. x - 1. x to 7. x - 2. x , or 8. x - 1. x to 8. x - 2. x , but not from 7. x to
* 8. x . Therefore , only update hooks numbered 8001 or later will run for
* Drupal 8. 8000 is reserved for the minimum core schema version and defining
* mymodule_update_8000 () will result in an exception . Use the
* @ link https :// drupal . org / node / 2127611 Migration API @ endlink instead to
* migrate data from an earlier major version of Drupal .
*
* For further information about releases and release numbers see :
* @ link http :// drupal . org / node / 711070 Maintaining a drupal . org project with Git @ endlink
*
* Never renumber update functions .
*
* Implementations of this hook should be placed in a mymodule . install file in
* the same directory as mymodule . module . Drupal core ' s updates are implemented
* using the system module as a name and stored in database / updates . inc .
*
* Not all module functions are available from within a hook_update_N () function .
* In order to call a function from your mymodule . module or an include file ,
* you need to explicitly load that file first .
*
* During database updates the schema of any module could be out of date . For
* this reason , caution is needed when using any API function within an update
* function - particularly CRUD functions , functions that depend on the schema
* ( for example by using drupal_write_record ()), and any functions that invoke
* hooks .
*
* The $sandbox parameter should be used when a multipass update is needed , in
* circumstances where running the whole update at once could cause PHP to
* timeout . Each pass is run in a way that avoids PHP timeouts , provided each
* pass remains under the timeout limit . To signify that an update requires
* at least one more pass , set $sandbox [ '#finished' ] to a number less than 1
* ( you need to do this each pass ) . The value of $sandbox [ '#finished' ] will be
* unset between passes but all other data in $sandbox will be preserved . The
* system will stop iterating this update when $sandbox [ '#finished' ] is left
* unset or set to a number higher than 1. It is recommended that
* $sandbox [ '#finished' ] is initially set to 0 , and then updated each pass to a
* number between 0 and 1 that represents the overall % completed for this
* update , finishing with 1.
*
* See the @ link batch Batch operations topic @ endlink for more information on
* how to use the Batch API .
*
* @ param array $sandbox
* Stores information for multipass updates . See above for more information .
*
* @ throws \Drupal\Core\Utility\UpdateException | PDOException
* In case of error , update hooks should throw an instance of
* Drupal\Core\Utility\UpdateException with a meaningful message for the user .
* If a database query fails for whatever reason , it will throw a
* PDOException .
*
* @ return string | null
* Optionally , update hooks may return a translated string that will be
* displayed to the user after the update has completed . If no message is
* returned , no message will be presented to the user .
*
* @ see batch
* @ see schemaapi
* @ see hook_update_last_removed ()
* @ see update_get_update_list ()
*/
function hook_update_N ( & $sandbox ) {
// For non-multipass updates, the signature can simply be;
// function hook_update_N() {
// For most updates, the following is sufficient.
db_add_field ( 'mytable1' , 'newcol' , array ( 'type' => 'int' , 'not null' => TRUE , 'description' => 'My new integer column.' ));
// However, for more complex operations that may take a long time,
// you may hook into Batch API as in the following example.
// Update 3 users at a time to have an exclamation point after their names.
// (They're really happy that we can do batch API in this hook!)
if ( ! isset ( $sandbox [ 'progress' ])) {
$sandbox [ 'progress' ] = 0 ;
$sandbox [ 'current_uid' ] = 0 ;
// We'll -1 to disregard the uid 0...
$sandbox [ 'max' ] = db_query ( 'SELECT COUNT(DISTINCT uid) FROM {users}' ) -> fetchField () - 1 ;
}
$users = db_select ( 'users' , 'u' )
-> fields ( 'u' , array ( 'uid' , 'name' ))
-> condition ( 'uid' , $sandbox [ 'current_uid' ], '>' )
-> range ( 0 , 3 )
-> orderBy ( 'uid' , 'ASC' )
-> execute ();
foreach ( $users as $user ) {
$user -> setUsername ( $user -> getUsername () . '!' );
db_update ( 'users' )
-> fields ( array ( 'name' => $user -> getUsername ()))
-> condition ( 'uid' , $user -> id ())
-> execute ();
$sandbox [ 'progress' ] ++ ;
$sandbox [ 'current_uid' ] = $user -> id ();
}
$sandbox [ '#finished' ] = empty ( $sandbox [ 'max' ]) ? 1 : ( $sandbox [ 'progress' ] / $sandbox [ 'max' ]);
if ( $some_error_condition_met ) {
// In case of an error, simply throw an exception with an error message.
throw new UpdateException ( 'Something went wrong; here is what you should do.' );
}
// To display a message to the user when the update is completed, return it.
// If you do not want to display a completion message, simply return nothing.
return t ( 'The update did what it was supposed to do.' );
}
/**
* Return an array of information about module update dependencies .
*
* This can be used to indicate update functions from other modules that your
* module ' s update functions depend on , or vice versa . It is used by the update
* system to determine the appropriate order in which updates should be run , as
* well as to search for missing dependencies .
*
* Implementations of this hook should be placed in a mymodule . install file in
* the same directory as mymodule . module .
*
* @ return
* A multidimensional array containing information about the module update
* dependencies . The first two levels of keys represent the module and update
* number ( respectively ) for which information is being returned , and the
* value is an array of information about that update ' s dependencies . Within
* this array , each key represents a module , and each value represents the
* number of an update function within that module . In the event that your
* update function depends on more than one update from a particular module ,
* you should always list the highest numbered one here ( since updates within
* a given module always run in numerical order ) .
*
* @ see update_resolve_dependencies ()
* @ see hook_update_N ()
*/
function hook_update_dependencies () {
// Indicate that the mymodule_update_8001() function provided by this module
// must run after the another_module_update_8003() function provided by the
// 'another_module' module.
$dependencies [ 'mymodule' ][ 8001 ] = array (
'another_module' => 8003 ,
);
// Indicate that the mymodule_update_8002() function provided by this module
// must run before the yet_another_module_update_8005() function provided by
// the 'yet_another_module' module. (Note that declaring dependencies in this
// direction should be done only in rare situations, since it can lead to the
// following problem: If a site has already run the yet_another_module
// module's database updates before it updates its codebase to pick up the
// newest mymodule code, then the dependency declared here will be ignored.)
$dependencies [ 'yet_another_module' ][ 8005 ] = array (
'mymodule' => 8002 ,
);
return $dependencies ;
}
/**
* Return a number which is no longer available as hook_update_N () .
*
* If you remove some update functions from your mymodule . install file , you
* should notify Drupal of those missing functions . This way , Drupal can
* ensure that no update is accidentally skipped .
*
* Implementations of this hook should be placed in a mymodule . install file in
* the same directory as mymodule . module .
*
* @ return
* An integer , corresponding to hook_update_N () which has been removed from
* mymodule . install .
*
* @ see hook_update_N ()
*/
function hook_update_last_removed () {
// We've removed the 8.x-1.x version of mymodule, including database updates.
// The next update function is mymodule_update_8200().
return 8103 ;
}
/**
* Provide information on Updaters ( classes that can update Drupal ) .
*
* Drupal\Core\Updater\Updater is a class that knows how to update various parts
* of the Drupal file system , for example to update modules that have newer
* releases , or to install a new theme .
*
* @ return
* An associative array of information about the updater ( s ) being provided .
* This array is keyed by a unique identifier for each updater , and the
* values are subarrays that can contain the following keys :
* - class : The name of the PHP class which implements this updater .
* - name : Human - readable name of this updater .
* - weight : Controls what order the Updater classes are consulted to decide
* which one should handle a given task . When an update task is being run ,
* the system will loop through all the Updater classes defined in this
* registry in weight order and let each class respond to the task and
* decide if each Updater wants to handle the task . In general , this
* doesn ' t matter , but if you need to override an existing Updater , make
* sure your Updater has a lighter weight so that it comes first .
*
* @ see drupal_get_updaters ()
* @ see hook_updater_info_alter ()
*/
function hook_updater_info () {
return array (
'module' => array (
'class' => 'Drupal\Core\Updater\Module' ,
'name' => t ( 'Update modules' ),
'weight' => 0 ,
),
'theme' => array (
'class' => 'Drupal\Core\Updater\Theme' ,
'name' => t ( 'Update themes' ),
'weight' => 0 ,
),
);
}
/**
* Alter the Updater information array .
*
* An Updater is a class that knows how to update various parts of the Drupal
* file system , for example to update modules that have newer releases , or to
* install a new theme .
*
* @ param array $updaters
* Associative array of updaters as defined through hook_updater_info () .
* Alter this array directly .
*
* @ see drupal_get_updaters ()
* @ see hook_updater_info ()
*/
function hook_updater_info_alter ( & $updaters ) {
// Adjust weight so that the theme Updater gets a chance to handle a given
// update task before module updaters.
$updaters [ 'theme' ][ 'weight' ] = - 1 ;
}
/**
* Check installation requirements and do status reporting .
*
* This hook has three closely related uses , determined by the $phase argument :
* - Checking installation requirements ( $phase == 'install' ) .
* - Checking update requirements ( $phase == 'update' ) .
* - Status reporting ( $phase == 'runtime' ) .
*
* Note that this hook , like all others dealing with installation and updates ,
* must reside in a module_name . install file , or it will not properly abort
* the installation of the module if a critical requirement is missing .
*
* During the 'install' phase , modules can for example assert that
* library or server versions are available or sufficient .
* Note that the installation of a module can happen during installation of
* Drupal itself ( by install . php ) with an installation profile or later by hand .
* As a consequence , install - time requirements must be checked without access
* to the full Drupal API , because it is not available during install . php .
* If a requirement has a severity of REQUIREMENT_ERROR , install . php will abort
* or at least the module will not install .
* Other severity levels have no effect on the installation .
* Module dependencies do not belong to these installation requirements ,
* but should be defined in the module ' s . info . yml file .
*
* The 'runtime' phase is not limited to pure installation requirements
* but can also be used for more general status information like maintenance
* tasks and security issues .
* The returned 'requirements' will be listed on the status report in the
* administration section , with indication of the severity level .
* Moreover , any requirement with a severity of REQUIREMENT_ERROR severity will
* result in a notice on the administration configuration page .
*
* @ param $phase
* The phase in which requirements are checked :
* - install : The module is being installed .
* - update : The module is enabled and update . php is run .
* - runtime : The runtime requirements are being checked and shown on the
* status report page .
*
* @ return
* An associative array where the keys are arbitrary but must be unique ( it
* is suggested to use the module short name as a prefix ) and the values are
* themselves associative arrays with the following elements :
* - title : The name of the requirement .
* - value : The current value ( e . g . , version , time , level , etc ) . During
* install phase , this should only be used for version numbers , do not set
* it if not applicable .
* - description : The description of the requirement / status .
* - severity : The requirement ' s result / severity level , one of :
* - REQUIREMENT_INFO : For info only .
* - REQUIREMENT_OK : The requirement is satisfied .
* - REQUIREMENT_WARNING : The requirement failed with a warning .
* - REQUIREMENT_ERROR : The requirement failed with an error .
*/
function hook_requirements ( $phase ) {
$requirements = array ();
// Report Drupal version
if ( $phase == 'runtime' ) {
$requirements [ 'drupal' ] = array (
'title' => t ( 'Drupal' ),
'value' => \Drupal :: VERSION ,
'severity' => REQUIREMENT_INFO
);
}
// Test PHP version
$requirements [ 'php' ] = array (
'title' => t ( 'PHP' ),
'value' => ( $phase == 'runtime' ) ? \Drupal :: l ( phpversion (), new Url ( 'system.php' )) : phpversion (),
);
if ( version_compare ( phpversion (), DRUPAL_MINIMUM_PHP ) < 0 ) {
$requirements [ 'php' ][ 'description' ] = t ( 'Your PHP installation is too old. Drupal requires at least PHP %version.' , array ( '%version' => DRUPAL_MINIMUM_PHP ));
$requirements [ 'php' ][ 'severity' ] = REQUIREMENT_ERROR ;
}
// Report cron status
if ( $phase == 'runtime' ) {
$cron_last = \Drupal :: state () -> get ( 'system.cron_last' );
if ( is_numeric ( $cron_last )) {
$requirements [ 'cron' ][ 'value' ] = t ( 'Last run !time ago' , array ( '!time' => \Drupal :: service ( 'date.formatter' ) -> formatInterval ( REQUEST_TIME - $cron_last )));
}
else {
$requirements [ 'cron' ] = array (
'description' => t ( 'Cron has not run. It appears cron jobs have not been setup on your system. Check the help pages for <a href="@url">configuring cron jobs</a>.' , array ( '@url' => 'http://drupal.org/cron' )),
'severity' => REQUIREMENT_ERROR ,
'value' => t ( 'Never run' ),
);
}
$requirements [ 'cron' ][ 'description' ] .= ' ' . t ( 'You can <a href="@cron">run cron manually</a>.' , array ( '@cron' => \Drupal :: url ( 'system.run_cron' )));
$requirements [ 'cron' ][ 'title' ] = t ( 'Cron maintenance tasks' );
}
return $requirements ;
}
/**
* @ } End of " addtogroup hooks " .
*/