123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993 |
- <?php
- define('UPDATE_DEFAULT_URL', 'http://updates.drupal.org/release-history');
- define('UPDATE_NOT_SECURE', 1);
- define('UPDATE_REVOKED', 2);
- define('UPDATE_NOT_SUPPORTED', 3);
- define('UPDATE_NOT_CURRENT', 4);
- define('UPDATE_CURRENT', 5);
- define('UPDATE_NOT_CHECKED', -1);
- define('UPDATE_UNKNOWN', -2);
- define('UPDATE_NOT_FETCHED', -3);
- define('UPDATE_FETCH_PENDING', -4);
- define('UPDATE_MAX_FETCH_ATTEMPTS', 2);
- define('UPDATE_MAX_FETCH_TIME', 30);
- function update_help($path, $arg) {
- switch ($path) {
- case 'admin/reports/updates':
- return '<p>' . t('Here you can find information about available updates for your installed modules and themes. Note that each module or theme is part of a "project", which may or may not have the same name, and might include multiple modules or themes within it.') . '</p>';
- case 'admin/help#update':
- $output = '';
- $output .= '<h3>' . t('About') . '</h3>';
- $output .= '<p>' . t("The Update manager module periodically checks for new versions of your site's software (including contributed modules and themes), and alerts administrators to available updates. In order to provide update information, anonymous usage statistics are sent to Drupal.org. If desired, you may disable the Update manager module from the <a href='@modules'>Module administration page</a>. For more information, see the online handbook entry for <a href='@update'>Update manager module</a>.", array('@update' => 'http://drupal.org/documentation/modules/update', '@modules' => url('admin/modules'))) . '</p>';
-
- if (update_manager_access()) {
- $output .= '<p>' . t('The Update manager also allows administrators to update and install modules and themes through the administration interface.') . '</p>';
- }
- $output .= '<h3>' . t('Uses') . '</h3>';
- $output .= '<dl>';
- $output .= '<dt>' . t('Checking for available updates') . '</dt>';
- $output .= '<dd>' . t('A report of <a href="@update-report">available updates</a> will alert you when new releases are available for download. You may configure options for the frequency for checking updates (which are performed during <a href="@cron">cron</a> runs) and e-mail notifications at the <a href="@update-settings">Update manager settings</a> page.', array('@update-report' => url('admin/reports/updates'), '@cron' => 'http://drupal.org/cron', '@update-settings' => url('admin/reports/updates/settings'))) . '</dd>';
-
- if (update_manager_access()) {
- $output .= '<dt>' . t('Performing updates through the user interface') . '</dt>';
- $output .= '<dd>' . t('The Update manager module allows administrators to perform updates directly through the administration interface. At the top of the <a href="@modules_page">modules</a> and <a href="@themes_page">themes</a> pages you will see a link to update to new releases. This will direct you to the <a href="@update-page">update page</a> where you see a listing of all the missing updates and confirm which ones you want to upgrade. From there, you are prompted for your FTP/SSH password, which then transfers the files into your Drupal installation, overwriting your old files. More detailed instructions can be found in the <a href="@update">online handbook</a>.', array('@modules_page' => url('admin/modules'), '@themes_page' => url('admin/appearance'), '@update-page' => url('admin/reports/updates/update'), '@update' => 'http://drupal.org/documentation/modules/update')) . '</dd>';
- $output .= '<dt>' . t('Installing new modules and themes through the user interface') . '</dt>';
- $output .= '<dd>' . t('You can also install new modules and themes in the same fashion, through the <a href="@install">install page</a>, or by clicking the <em>Install new module/theme</em> link at the top of the <a href="@modules_page">modules</a> and <a href="@themes_page">themes</a> pages. In this case, you are prompted to provide either the URL to the download, or to upload a packaged release file from your local computer.', array('@modules_page' => url('admin/modules'), '@themes_page' => url('admin/appearance'), '@install' => url('admin/reports/updates/install'))) . '</dd>';
- }
- $output .= '</dl>';
- return $output;
- }
- }
- function update_init() {
- if (arg(0) == 'admin' && user_access('administer site configuration')) {
- switch ($_GET['q']) {
-
- case 'admin/appearance/update':
- case 'admin/appearance/install':
- case 'admin/modules/update':
- case 'admin/modules/install':
- case 'admin/reports/updates':
- case 'admin/reports/updates/update':
- case 'admin/reports/updates/install':
- case 'admin/reports/updates/settings':
- case 'admin/reports/status':
- case 'admin/update/ready':
- return;
-
-
- case 'admin/appearance':
- case 'admin/modules':
- $verbose = TRUE;
- break;
- }
- module_load_install('update');
- $status = update_requirements('runtime');
- foreach (array('core', 'contrib') as $report_type) {
- $type = 'update_' . $report_type;
- if (!empty($verbose)) {
- if (isset($status[$type]['severity'])) {
- if ($status[$type]['severity'] == REQUIREMENT_ERROR) {
- drupal_set_message($status[$type]['description'], 'error', FALSE);
- }
- elseif ($status[$type]['severity'] == REQUIREMENT_WARNING) {
- drupal_set_message($status[$type]['description'], 'warning', FALSE);
- }
- }
- }
-
-
- else {
- if (isset($status[$type])
- && isset($status[$type]['reason'])
- && $status[$type]['reason'] === UPDATE_NOT_SECURE) {
- drupal_set_message($status[$type]['description'], 'error', FALSE);
- }
- }
- }
- }
- }
- function update_menu() {
- $items = array();
- $items['admin/reports/updates'] = array(
- 'title' => 'Available updates',
- 'description' => 'Get a status report about available updates for your installed modules and themes.',
- 'page callback' => 'update_status',
- 'access arguments' => array('administer site configuration'),
- 'weight' => -50,
- 'file' => 'update.report.inc',
- );
- $items['admin/reports/updates/list'] = array(
- 'title' => 'List',
- 'access arguments' => array('administer site configuration'),
- 'type' => MENU_DEFAULT_LOCAL_TASK,
- );
- $items['admin/reports/updates/settings'] = array(
- 'title' => 'Settings',
- 'page callback' => 'drupal_get_form',
- 'page arguments' => array('update_settings'),
- 'access arguments' => array('administer site configuration'),
- 'file' => 'update.settings.inc',
- 'type' => MENU_LOCAL_TASK,
- 'weight' => 50,
- );
- $items['admin/reports/updates/check'] = array(
- 'title' => 'Manual update check',
- 'page callback' => 'update_manual_status',
- 'access arguments' => array('administer site configuration'),
- 'type' => MENU_CALLBACK,
- 'file' => 'update.fetch.inc',
- );
-
-
-
-
-
-
- $paths = array(
- 'report' => 'admin/reports/updates',
- 'module' => 'admin/modules',
- 'theme' => 'admin/appearance',
- );
- foreach ($paths as $context => $path) {
- $items[$path . '/install'] = array(
- 'page callback' => 'drupal_get_form',
- 'page arguments' => array('update_manager_install_form', $context),
- 'access callback' => 'update_manager_access',
- 'access arguments' => array(),
- 'weight' => 25,
- 'type' => MENU_LOCAL_ACTION,
- 'file' => 'update.manager.inc',
- );
- $items[$path . '/update'] = array(
- 'page callback' => 'drupal_get_form',
- 'page arguments' => array('update_manager_update_form', $context),
- 'access callback' => 'update_manager_access',
- 'access arguments' => array(),
- 'weight' => 10,
- 'title' => 'Update',
- 'type' => MENU_LOCAL_TASK,
- 'file' => 'update.manager.inc',
- );
- }
-
-
- $items['admin/reports/updates/install'] += array('title' => 'Install new module or theme');
- $items['admin/modules/install'] += array('title' => 'Install new module');
- $items['admin/appearance/install'] += array('title' => 'Install new theme');
-
-
- $items['admin/update/ready'] = array(
- 'title' => 'Ready to update',
- 'page callback' => 'drupal_get_form',
- 'page arguments' => array('update_manager_update_ready_form'),
- 'access callback' => 'update_manager_access',
- 'access arguments' => array(),
- 'type' => MENU_CALLBACK,
- 'file' => 'update.manager.inc',
- );
- return $items;
- }
- function update_manager_access() {
- return variable_get('allow_authorize_operations', TRUE) && user_access('administer software updates');
- }
- function update_theme() {
- return array(
- 'update_manager_update_form' => array(
- 'render element' => 'form',
- 'file' => 'update.manager.inc',
- ),
- 'update_last_check' => array(
- 'variables' => array('last' => NULL),
- ),
- 'update_report' => array(
- 'variables' => array('data' => NULL),
- ),
- 'update_version' => array(
- 'variables' => array('version' => NULL, 'tag' => NULL, 'class' => array()),
- ),
- 'update_status_label' => array(
- 'variables' => array('status' => NULL),
- ),
- );
- }
- function update_cron() {
- $frequency = variable_get('update_check_frequency', 1);
- $interval = 60 * 60 * 24 * $frequency;
- if ((REQUEST_TIME - variable_get('update_last_check', 0)) > $interval) {
-
-
-
- update_refresh();
- update_fetch_data();
- }
- else {
-
-
- update_get_available(TRUE);
- }
- if ((REQUEST_TIME - variable_get('update_last_email_notification', 0)) > $interval) {
-
-
- module_load_include('inc', 'update', 'update.fetch');
- _update_cron_notify();
- }
-
- update_clear_update_disk_cache();
- }
- function update_themes_enabled($themes) {
-
- _update_cache_clear();
- }
- function update_themes_disabled($themes) {
-
- _update_cache_clear();
- }
- function update_form_system_modules_alter(&$form, $form_state) {
- $form['#submit'][] = 'update_cache_clear_submit';
- }
- function update_cache_clear_submit($form, &$form_state) {
-
- _update_cache_clear();
- }
- function _update_no_data() {
- $destination = drupal_get_destination();
- return t('No update information available. <a href="@run_cron">Run cron</a> or <a href="@check_manually">check manually</a>.', array(
- '@run_cron' => url('admin/reports/status/run-cron', array('query' => $destination)),
- '@check_manually' => url('admin/reports/updates/check', array('query' => $destination)),
- ));
- }
- function update_get_available($refresh = FALSE) {
- module_load_include('inc', 'update', 'update.compare');
- $needs_refresh = FALSE;
-
- $available = _update_get_cached_available_releases();
- $num_avail = count($available);
- $projects = update_get_projects();
- foreach ($projects as $key => $project) {
-
- if (empty($available[$key])) {
- update_create_fetch_task($project);
- $needs_refresh = TRUE;
- continue;
- }
-
-
-
-
-
- if ($project['info']['_info_file_ctime'] > $available[$key]['last_fetch']) {
- $available[$key]['fetch_status'] = UPDATE_FETCH_PENDING;
- }
-
-
- if (empty($available[$key]['releases'])) {
- $available[$key]['fetch_status'] = UPDATE_FETCH_PENDING;
- }
-
-
- if (!empty($available[$key]['fetch_status']) && $available[$key]['fetch_status'] == UPDATE_FETCH_PENDING) {
- update_create_fetch_task($project);
- $needs_refresh = TRUE;
- }
- }
- if ($needs_refresh && $refresh) {
-
- update_fetch_data();
-
-
- $available = _update_get_cached_available_releases();
- }
- return $available;
- }
- function update_create_fetch_task($project) {
- module_load_include('inc', 'update', 'update.fetch');
- return _update_create_fetch_task($project);
- }
- function update_refresh() {
- module_load_include('inc', 'update', 'update.fetch');
- return _update_refresh();
- }
- function update_fetch_data() {
- module_load_include('inc', 'update', 'update.fetch');
- return _update_fetch_data();
- }
- function _update_get_cached_available_releases() {
- $data = array();
- $cache_items = _update_get_cache_multiple('available_releases');
- foreach ($cache_items as $cid => $cache) {
- $cache->data['last_fetch'] = $cache->created;
- if ($cache->expire < REQUEST_TIME) {
- $cache->data['fetch_status'] = UPDATE_FETCH_PENDING;
- }
-
-
-
- $parts = explode('::', $cid, 2);
- $data[$parts[1]] = $cache->data;
- }
- return $data;
- }
- function update_mail($key, &$message, $params) {
- $language = $message['language'];
- $langcode = $language->language;
- $message['subject'] .= t('New release(s) available for !site_name', array('!site_name' => variable_get('site_name', 'Drupal')), array('langcode' => $langcode));
- foreach ($params as $msg_type => $msg_reason) {
- $message['body'][] = _update_message_text($msg_type, $msg_reason, FALSE, $language);
- }
- $message['body'][] = t('See the available updates page for more information:', array(), array('langcode' => $langcode)) . "\n" . url('admin/reports/updates', array('absolute' => TRUE, 'language' => $language));
- if (update_manager_access()) {
- $message['body'][] = t('You can automatically install your missing updates using the Update manager:', array(), array('langcode' => $langcode)) . "\n" . url('admin/reports/updates/update', array('absolute' => TRUE, 'language' => $language));
- }
- $settings_url = url('admin/reports/updates/settings', array('absolute' => TRUE));
- if (variable_get('update_notification_threshold', 'all') == 'all') {
- $message['body'][] = t('Your site is currently configured to send these emails when any updates are available. To get notified only for security updates, !url.', array('!url' => $settings_url));
- }
- else {
- $message['body'][] = t('Your site is currently configured to send these emails only when security updates are available. To get notified for any available updates, !url.', array('!url' => $settings_url));
- }
- }
- function _update_message_text($msg_type, $msg_reason, $report_link = FALSE, $language = NULL) {
- $langcode = isset($language) ? $language->language : NULL;
- $text = '';
- switch ($msg_reason) {
- case UPDATE_NOT_SECURE:
- if ($msg_type == 'core') {
- $text = t('There is a security update available for your version of Drupal. To ensure the security of your server, you should update immediately!', array(), array('langcode' => $langcode));
- }
- else {
- $text = t('There are security updates available for one or more of your modules or themes. To ensure the security of your server, you should update immediately!', array(), array('langcode' => $langcode));
- }
- break;
- case UPDATE_REVOKED:
- if ($msg_type == 'core') {
- $text = t('Your version of Drupal has been revoked and is no longer available for download. Upgrading is strongly recommended!', array(), array('langcode' => $langcode));
- }
- else {
- $text = t('The installed version of at least one of your modules or themes has been revoked and is no longer available for download. Upgrading or disabling is strongly recommended!', array(), array('langcode' => $langcode));
- }
- break;
- case UPDATE_NOT_SUPPORTED:
- if ($msg_type == 'core') {
- $text = t('Your version of Drupal is no longer supported. Upgrading is strongly recommended!', array(), array('langcode' => $langcode));
- }
- else {
- $text = t('The installed version of at least one of your modules or themes is no longer supported. Upgrading or disabling is strongly recommended. See the project homepage for more details.', array(), array('langcode' => $langcode));
- }
- break;
- case UPDATE_NOT_CURRENT:
- if ($msg_type == 'core') {
- $text = t('There are updates available for your version of Drupal. To ensure the proper functioning of your site, you should update as soon as possible.', array(), array('langcode' => $langcode));
- }
- else {
- $text = t('There are updates available for one or more of your modules or themes. To ensure the proper functioning of your site, you should update as soon as possible.', array(), array('langcode' => $langcode));
- }
- break;
- case UPDATE_UNKNOWN:
- case UPDATE_NOT_CHECKED:
- case UPDATE_NOT_FETCHED:
- case UPDATE_FETCH_PENDING:
- if ($msg_type == 'core') {
- $text = t('There was a problem checking <a href="@update-report">available updates</a> for Drupal.', array('@update-report' => url('admin/reports/updates')), array('langcode' => $langcode));
- }
- else {
- $text = t('There was a problem checking <a href="@update-report">available updates</a> for your modules or themes.', array('@update-report' => url('admin/reports/updates')), array('langcode' => $langcode));
- }
- break;
- }
- if ($report_link) {
- if (update_manager_access()) {
- $text .= ' ' . t('See the <a href="@available_updates">available updates</a> page for more information and to install your missing updates.', array('@available_updates' => url('admin/reports/updates/update', array('language' => $language))), array('langcode' => $langcode));
- }
- else {
- $text .= ' ' . t('See the <a href="@available_updates">available updates</a> page for more information.', array('@available_updates' => url('admin/reports/updates', array('language' => $language))), array('langcode' => $langcode));
- }
- }
- return $text;
- }
- function _update_project_status_sort($a, $b) {
-
-
-
-
- $a_status = $a['status'] > 0 ? $a['status'] : (-10 * $a['status']);
- $b_status = $b['status'] > 0 ? $b['status'] : (-10 * $b['status']);
- return $a_status - $b_status;
- }
- function theme_update_last_check($variables) {
- $last = $variables['last'];
- $output = '<div class="update checked">';
- $output .= $last ? t('Last checked: @time ago', array('@time' => format_interval(REQUEST_TIME - $last))) : t('Last checked: never');
- $output .= ' <span class="check-manually">(' . l(t('Check manually'), 'admin/reports/updates/check', array('query' => drupal_get_destination())) . ')</span>';
- $output .= "</div>\n";
- return $output;
- }
- function update_verify_update_archive($project, $archive_file, $directory) {
- $errors = array();
-
- if (
- file_exists("$directory/$project/index.php")
- && file_exists("$directory/$project/update.php")
- && file_exists("$directory/$project/includes/bootstrap.inc")
- && file_exists("$directory/$project/modules/node/node.module")
- && file_exists("$directory/$project/modules/system/system.module")
- ) {
- return array(
- 'no-core' => t('Automatic updating of Drupal core is not supported. See the <a href="@upgrade-guide">upgrade guide</a> for information on how to update Drupal core manually.', array('@upgrade-guide' => 'http://drupal.org/upgrade')),
- );
- }
-
-
-
-
-
- $compatible_project = FALSE;
- $incompatible = array();
- $files = file_scan_directory("$directory/$project", '/^' . DRUPAL_PHP_FUNCTION_PATTERN . '\.info$/', array('key' => 'name', 'min_depth' => 0));
- foreach ($files as $key => $file) {
-
- $info = drupal_parse_info_file($file->uri);
-
- if (empty($info['core']) || $info['core'] != DRUPAL_CORE_COMPATIBILITY) {
- $incompatible[] = !empty($info['name']) ? $info['name'] : t('Unknown');
- }
- else {
- $compatible_project = TRUE;
- break;
- }
- }
- if (empty($files)) {
- $errors[] = t('%archive_file does not contain any .info files.', array('%archive_file' => drupal_basename($archive_file)));
- }
- elseif (!$compatible_project) {
- $errors[] = format_plural(
- count($incompatible),
- '%archive_file contains a version of %names that is not compatible with Drupal !version.',
- '%archive_file contains versions of modules or themes that are not compatible with Drupal !version: %names',
- array('!version' => DRUPAL_CORE_COMPATIBILITY, '%archive_file' => drupal_basename($archive_file), '%names' => implode(', ', $incompatible))
- );
- }
- return $errors;
- }
- function _update_cache_set($cid, $data, $expire) {
- $fields = array(
- 'created' => REQUEST_TIME,
- 'expire' => $expire,
- );
- if (!is_string($data)) {
- $fields['data'] = serialize($data);
- $fields['serialized'] = 1;
- }
- else {
- $fields['data'] = $data;
- $fields['serialized'] = 0;
- }
- db_merge('cache_update')
- ->key(array('cid' => $cid))
- ->fields($fields)
- ->execute();
- }
- function _update_cache_get($cid) {
- $cache = db_query("SELECT data, created, expire, serialized FROM {cache_update} WHERE cid = :cid", array(':cid' => $cid))->fetchObject();
- if (isset($cache->data)) {
- if ($cache->serialized) {
- $cache->data = unserialize($cache->data);
- }
- }
- return $cache;
- }
- function _update_get_cache_multiple($cid_prefix) {
- $data = array();
- $result = db_select('cache_update')
- ->fields('cache_update', array('cid', 'data', 'created', 'expire', 'serialized'))
- ->condition('cache_update.cid', $cid_prefix . '::%', 'LIKE')
- ->execute();
- foreach ($result as $cache) {
- if ($cache) {
- if ($cache->serialized) {
- $cache->data = unserialize($cache->data);
- }
- $data[$cache->cid] = $cache;
- }
- }
- return $data;
- }
- function _update_cache_clear($cid = NULL, $wildcard = FALSE) {
- if (empty($cid)) {
- db_delete('cache_update')
-
-
- ->condition('cid', 'fetch_task::%', 'NOT LIKE')
- ->execute();
- }
- else {
- $query = db_delete('cache_update');
- if ($wildcard) {
- $query->condition('cid', $cid . '%', 'LIKE');
- }
- else {
- $query->condition('cid', $cid);
- }
- $query->execute();
- }
- }
- function update_flush_caches() {
- if (defined('MAINTENANCE_MODE') && MAINTENANCE_MODE == 'update') {
- _update_cache_clear();
- }
- return array();
- }
- function _update_manager_unique_identifier() {
- $id = &drupal_static(__FUNCTION__, '');
- if (empty($id)) {
- $id = substr(hash('sha256', drupal_get_hash_salt()), 0, 8);
- }
- return $id;
- }
- function _update_manager_extract_directory($create = TRUE) {
- $directory = &drupal_static(__FUNCTION__, '');
- if (empty($directory)) {
- $directory = 'temporary://update-extraction-' . _update_manager_unique_identifier();
- if ($create && !file_exists($directory)) {
- mkdir($directory);
- }
- }
- return $directory;
- }
- function _update_manager_cache_directory($create = TRUE) {
- $directory = &drupal_static(__FUNCTION__, '');
- if (empty($directory)) {
- $directory = 'temporary://update-cache-' . _update_manager_unique_identifier();
- if ($create && !file_exists($directory)) {
- mkdir($directory);
- }
- }
- return $directory;
- }
- function update_clear_update_disk_cache() {
-
-
- $directories = array(
- _update_manager_cache_directory(FALSE),
- _update_manager_extract_directory(FALSE),
- );
-
- foreach ($directories as $directory) {
- file_scan_directory($directory, '/.*/', array('callback' => 'update_delete_file_if_stale', 'recurse' => FALSE));
- }
- }
- function update_delete_file_if_stale($path) {
- if (file_exists($path)) {
- $filectime = filectime($path);
- if (REQUEST_TIME - $filectime > DRUPAL_MAXIMUM_TEMP_FILE_AGE || (preg_match('/.*-dev\.(tar\.gz|zip)/i', $path) && REQUEST_TIME - $filectime > 300)) {
- file_unmanaged_delete_recursive($path);
- }
- }
- }
|