Commit c0073e0c authored by Riccardo Padovani's avatar Riccardo Padovani

Updated Drupal core to version 7.26

parent aecba058
Drupal 7.26, 2014-01-15
----------------------
- Fixed security issues (multiple vulnerabilities). See SA-CORE-2014-001.
Drupal 7.25, 2014-01-02
-----------------------
- Fixed a bug in node_save() which prevented the saved node from being updated
in hook_node_insert() and other similar hooks.
- Added a meta tag to install.php to prevent it from being indexed by search
engines even when Drupal is installed in a subfolder (minor markup change).
- Fixed a bug in the database API that caused frequent deadlock errors when
running merge queries on some servers.
- Performance improvement: Prevented block rehashing from writing blocks to the
database on every cache clear and cron run when the blocks have not changed.
This fix results in an extra 'saved' key which is added and set to TRUE for
each block returned by _block_rehash() that actually is saved to the database
(data structure change).
- Added an optional 'skip on cron' parameter to hook_cron_queue_info() to allow
queues to avoid being automatically processed on cron runs (API addition).
- Fixed a bug which caused hook_block_view_MODULE_DELTA_alter() to never be
invoked if the block delta had a hyphen in it. To implement the hook when the
block delta has a hyphen, modules should now replace hyphens with underscores
when constructing the function name for the hook implementation.
- Fixed a bug which caused cached pages to sometimes be sent to the browser
with incorrect compression. The fix adds a new 'page_compressed' key to the
$cache->data array returned by drupal_page_get_cache() (minor data structure
change).
- Fixed broken tests on PHP 5.5.
- Made the File and Image modules more robust when saving entities that have
deleted files attached. The code in file_field_presave() will now remove the
record of the deleted file from the entity before saving (minor data
structure change).
- Standardized menu callback functions throughout Drupal core to return
MENU_NOT_FOUND and MENU_ACCESS_DENIED rather than printing their own "page
not found" or "access denied" pages (minor API change in the return value of
these functions under some circumstances).
- Fixed a bug in which caches were not properly cleared when a node was deleted
via the administrative interface.
- Changed the Bartik theme to render content contained in <pre>, <code> and
similar tags in a larger font size, so it is easier to read.
- Fixed a bug in the Search module that caused exceptions to be thrown during
searches if the server was not configured to represent decimal points as a
period.
- Fixed a regression in the Image module that made image_style_url() not work
when a relative path (rather than a complete file URI) was passed to it.
- Added an optional feature to the Statistics module to allow node views to be
tracked by Ajax requests rather than during the server-side generation of the
page. This allows the node counter to work on sites that use external page
caches (string change and new administrative option:
https://drupal.org/node/2164069).
- Added a link to the drupal.org documentation page for cron to the Cron
settings page (string change).
- Added a 'drupal_anonymous_user_object' variable to allow the anonymous user
object returned by drupal_anonymous_user() to be overridden with a classed
object (API addition).
- Changed the database API to allow inserts based on a SELECT * query to work
correctly.
- Changed the database schema of the {file_managed} table to allow Drupal to
manage files larger than 4 GB.
- Changed the File module's hook_field_load() implementation to prevent file
entity properties which have the same name as file or image field properties
from overwriting the field properties (minor API change).
- Numerous small bug fixes.
- Numerous API documentation improvements.
- Additional automated test coverage.
Drupal 7.24, 2013-11-20
----------------------
- Fixed security issues (multiple vulnerabilities), see SA-CORE-2013-003.
......
All Drupal code is Copyright 2001 - 2012 by the original authors.
All Drupal code is Copyright 2001 - 2013 by the original authors.
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
......
......@@ -20,6 +20,8 @@ Drupal requires:
- MySQL 5.0.15 (or greater) (http://www.mysql.com/).
- MariaDB 5.1.44 (or greater) (http://mariadb.org/). MariaDB is a fully
compatible drop-in replacement for MySQL.
- Percona Server 5.1.70 (or greater) (http://www.percona.com/). Percona
Server is a backwards-compatible replacement for MySQL.
- PostgreSQL 8.3 (or greater) (http://www.postgresql.org/).
- SQLite 3.4.2 (or greater) (http://www.sqlite.org/).
......
File mode changed from 100644 to 100755
......@@ -8,7 +8,7 @@
/**
* The current system version.
*/
define('VERSION', '7.24');
define('VERSION', '7.26');
/**
* Core API compatibility.
......@@ -244,7 +244,7 @@ define('REGISTRY_WRITE_LOOKUP_CACHE', 2);
/**
* Regular expression to match PHP function names.
*
* @see http://php.net/manual/en/language.functions.php
* @see http://php.net/manual/language.functions.php
*/
define('DRUPAL_PHP_FUNCTION_PATTERN', '[a-zA-Z_\x7f-\xff][a-zA-Z0-9_\x7f-\xff]*');
......@@ -278,7 +278,7 @@ define('DRUPAL_PHP_FUNCTION_PATTERN', '[a-zA-Z_\x7f-\xff][a-zA-Z0-9_\x7f-\xff]*'
* error, and $var will be populated with the contents of $object['foo'], but
* that data will be passed by value, not reference. For more information on
* the PHP limitation, see the note in the official PHP documentation at·
* http://php.net/manual/en/arrayaccess.offsetget.php on
* http://php.net/manual/arrayaccess.offsetget.php on
* ArrayAccess::offsetGet().
*
* By default, the class accounts for caches where calling functions might
......@@ -683,7 +683,8 @@ function drupal_environment_initialize() {
ini_set('session.use_only_cookies', '1');
ini_set('session.use_trans_sid', '0');
// Don't send HTTP headers using PHP's session handler.
ini_set('session.cache_limiter', 'none');
// An empty string is used here to disable the cache limiter.
ini_set('session.cache_limiter', '');
// Use httponly session cookies.
ini_set('session.cookie_httponly', '1');
......@@ -1278,7 +1279,7 @@ function drupal_page_header() {
*/
function drupal_serve_page_from_cache(stdClass $cache) {
// Negotiate whether to use compression.
$page_compression = variable_get('page_compression', TRUE) && extension_loaded('zlib');
$page_compression = !empty($cache->data['page_compressed']);
$return_compressed = $page_compression && isset($_SERVER['HTTP_ACCEPT_ENCODING']) && strpos($_SERVER['HTTP_ACCEPT_ENCODING'], 'gzip') !== FALSE;
// Get headers set in hook_boot(). Keys are lower-case.
......@@ -2149,7 +2150,7 @@ function drupal_array_merge_deep_array($arrays) {
* @return Object - the user object.
*/
function drupal_anonymous_user() {
$user = new stdClass();
$user = variable_get('drupal_anonymous_user_object', new stdClass);
$user->uid = 0;
$user->hostname = ip_address();
$user->roles = array();
......@@ -3294,8 +3295,8 @@ function registry_update() {
* However, the above line of code does not work, because PHP only allows static
* variables to be initializied by literal values, and does not allow static
* variables to be assigned to references.
* - http://php.net/manual/en/language.variables.scope.php#language.variables.scope.static
* - http://php.net/manual/en/language.variables.scope.php#language.variables.scope.references
* - http://php.net/manual/language.variables.scope.php#language.variables.scope.static
* - http://php.net/manual/language.variables.scope.php#language.variables.scope.references
* The example below shows the syntax needed to work around both limitations.
* For benchmarks and more information, see http://drupal.org/node/619666.
*
......
......@@ -929,7 +929,7 @@ function drupal_http_request($url, array $options = array()) {
// If the server URL has a user then attempt to use basic authentication.
if (isset($uri['user'])) {
$options['headers']['Authorization'] = 'Basic ' . base64_encode($uri['user'] . (isset($uri['pass']) ? ':' . $uri['pass'] : ''));
$options['headers']['Authorization'] = 'Basic ' . base64_encode($uri['user'] . (isset($uri['pass']) ? ':' . $uri['pass'] : ':'));
}
// If the database prefix is being used by SimpleTest to run the tests in a copied
......@@ -1134,7 +1134,7 @@ function _fix_gpc_magic(&$item) {
* @param $key
* The key for the item within $_FILES.
*
* @see http://php.net/manual/en/features.file-upload.php#42280
* @see http://php.net/manual/features.file-upload.php#42280
*/
function _fix_gpc_magic_files(&$item, $key) {
if ($key != 'tmp_name') {
......@@ -1950,7 +1950,7 @@ function format_interval($interval, $granularity = 2, $langcode = NULL) {
* get interpreted as date format characters.
* @param $timezone
* (optional) Time zone identifier, as described at
* http://php.net/manual/en/timezones.php Defaults to the time zone used to
* http://php.net/manual/timezones.php Defaults to the time zone used to
* display the page.
* @param $langcode
* (optional) Language code to translate to. Defaults to the language used to
......@@ -3673,17 +3673,23 @@ function drupal_load_stylesheet($file, $optimize = NULL, $reset_basepath = TRUE)
if ($basepath && !file_uri_scheme($file)) {
$file = $basepath . '/' . $file;
}
// Store the parent base path to restore it later.
$parent_base_path = $basepath;
// Set the current base path to process possible child imports.
$basepath = dirname($file);
// Load the CSS stylesheet. We suppress errors because themes may specify
// stylesheets in their .info file that don't exist in the theme's path,
// but are merely there to disable certain module CSS files.
$content = '';
if ($contents = @file_get_contents($file)) {
// Return the processed stylesheet.
return drupal_load_stylesheet_content($contents, $_optimize);
$content = drupal_load_stylesheet_content($contents, $_optimize);
}
return '';
// Restore the parent base path as the file and its childen are processed.
$basepath = $parent_base_path;
return $content;
}
/**
......@@ -3700,7 +3706,7 @@ function drupal_load_stylesheet($file, $optimize = NULL, $reset_basepath = TRUE)
*/
function drupal_load_stylesheet_content($contents, $optimize = FALSE) {
// Remove multiple charset declarations for standards compliance (and fixing Safari problems).
$contents = preg_replace('/^@charset\s+[\'"](\S*)\b[\'"];/i', '', $contents);
$contents = preg_replace('/^@charset\s+[\'"](\S*?)\b[\'"];/i', '', $contents);
if ($optimize) {
// Perform some safe CSS optimizations.
......@@ -3719,7 +3725,7 @@ function drupal_load_stylesheet_content($contents, $optimize = FALSE) {
// Remove certain whitespace.
// There are different conditions for removing leading and trailing
// whitespace.
// @see http://php.net/manual/en/regexp.reference.subpatterns.php
// @see http://php.net/manual/regexp.reference.subpatterns.php
$contents = preg_replace('<
# Strip leading and trailing whitespace.
\s*([@{};,])\s*
......@@ -3833,7 +3839,14 @@ function drupal_clean_css_identifier($identifier, $filter = array(' ' => '-', '_
* The cleaned class name.
*/
function drupal_html_class($class) {
return drupal_clean_css_identifier(drupal_strtolower($class));
// The output of this function will never change, so this uses a normal
// static instead of drupal_static().
static $classes = array();
if (!isset($classes[$class])) {
$classes[$class] = drupal_clean_css_identifier(drupal_strtolower($class));
}
return $classes[$class];
}
/**
......@@ -4097,7 +4110,7 @@ function drupal_region_class($region) {
* else being the same, JavaScript added by a call to drupal_add_js() that
* happened later in the page request gets added to the page after one for
* which drupal_add_js() happened earlier in the page request.
* - defer: If set to TRUE, the defer attribute is set on the &lt;script&gt;
* - defer: If set to TRUE, the defer attribute is set on the <script>
* tag. Defaults to FALSE.
* - cache: If set to FALSE, the JavaScript file is loaded anew on every page
* call; in other words, it is not cached. Used only when 'type' references
......@@ -5155,7 +5168,7 @@ function _drupal_bootstrap_full() {
* client without gzip support.
*
* Page compression requires the PHP zlib extension
* (http://php.net/manual/en/ref.zlib.php).
* (http://php.net/manual/ref.zlib.php).
*
* @see drupal_page_header()
*/
......@@ -5163,6 +5176,10 @@ function drupal_page_set_cache() {
global $base_root;
if (drupal_page_is_cacheable()) {
// Check whether the current page might be compressed.
$page_compressed = variable_get('page_compression', TRUE) && extension_loaded('zlib');
$cache = (object) array(
'cid' => $base_root . request_uri(),
'data' => array(
......@@ -5170,6 +5187,9 @@ function drupal_page_set_cache() {
'body' => ob_get_clean(),
'title' => drupal_get_title(),
'headers' => array(),
// We need to store whether page was compressed or not,
// because by the time it is read, the configuration might change.
'page_compressed' => $page_compressed,
),
'expire' => CACHE_TEMPORARY,
'created' => REQUEST_TIME,
......@@ -5187,7 +5207,7 @@ function drupal_page_set_cache() {
}
if ($cache->data['body']) {
if (variable_get('page_compression', TRUE) && extension_loaded('zlib')) {
if ($page_compressed) {
$cache->data['body'] = gzencode($cache->data['body'], 9, FORCE_GZIP);
}
cache_set($cache->cid, $cache->data, 'cache_page', $cache->expire);
......@@ -5262,6 +5282,10 @@ function drupal_cron_run() {
}
foreach ($queues as $queue_name => $info) {
if (!empty($info['skip on cron'])) {
// Do not run if queue wants to skip.
continue;
}
$function = $info['worker callback'];
$end = time() + (isset($info['time']) ? $info['time'] : 15);
$queue = DrupalQueue::get($queue_name);
......
......@@ -179,7 +179,7 @@
* concrete implementation of it to support special handling required by that
* database.
*
* @see http://php.net/manual/en/book.pdo.php
* @see http://php.net/manual/book.pdo.php
*/
abstract class DatabaseConnection extends PDO {
......@@ -1986,7 +1986,7 @@ interface DatabaseStatementInterface extends Traversable {
/**
* Sets the default fetch mode for this statement.
*
* See http://php.net/manual/en/pdo.constants.php for the definition of the
* See http://php.net/manual/pdo.constants.php for the definition of the
* constants used.
*
* @param $mode
......@@ -2005,7 +2005,7 @@ interface DatabaseStatementInterface extends Traversable {
/**
* Fetches the next row from a result set.
*
* See http://php.net/manual/en/pdo.constants.php for the definition of the
* See http://php.net/manual/pdo.constants.php for the definition of the
* constants used.
*
* @param $mode
......
......@@ -51,7 +51,8 @@ class InsertQuery_mysql extends InsertQuery {
// If we're selecting from a SelectQuery, finish building the query and
// pass it back, as any remaining options are irrelevant.
if (!empty($this->fromQuery)) {
return $comments . 'INSERT INTO {' . $this->table . '} (' . implode(', ', $insert_fields) . ') ' . $this->fromQuery;
$insert_fields_string = $insert_fields ? ' (' . implode(', ', $insert_fields) . ') ' : ' ';
return $comments . 'INSERT INTO {' . $this->table . '}' . $insert_fields_string . $this->fromQuery;
}
$query = $comments . 'INSERT INTO {' . $this->table . '} (' . implode(', ', $insert_fields) . ') VALUES ';
......
......@@ -112,7 +112,8 @@ class InsertQuery_pgsql extends InsertQuery {
// If we're selecting from a SelectQuery, finish building the query and
// pass it back, as any remaining options are irrelevant.
if (!empty($this->fromQuery)) {
return $comments . 'INSERT INTO {' . $this->table . '} (' . implode(', ', $insert_fields) . ') ' . $this->fromQuery;
$insert_fields_string = $insert_fields ? ' (' . implode(', ', $insert_fields) . ') ' : ' ';
return $comments . 'INSERT INTO {' . $this->table . '}' . $insert_fields_string . $this->fromQuery;
}
$query = $comments . 'INSERT INTO {' . $this->table . '} (' . implode(', ', $insert_fields) . ') VALUES ';
......
......@@ -710,10 +710,11 @@ class InsertQuery extends Query {
// first call to fields() does have an effect.
$this->fields(array_merge(array_keys($this->fromQuery->getFields()), array_keys($this->fromQuery->getExpressions())));
}
// Don't execute query without fields.
if (count($this->insertFields) + count($this->defaultFields) == 0) {
throw new NoFieldsException('There are no fields available to insert with.');
else {
// Don't execute query without fields.
if (count($this->insertFields) + count($this->defaultFields) == 0) {
throw new NoFieldsException('There are no fields available to insert with.');
}
}
// If no values have been added, silently ignore this query. This can happen
......@@ -1605,55 +1606,43 @@ class MergeQuery extends Query implements QueryConditionInterface {
}
public function execute() {
// Wrap multiple queries in a transaction, if the database supports it.
$transaction = $this->connection->startTransaction();
try {
if (!count($this->condition)) {
throw new InvalidMergeQueryException(t('Invalid merge query: no conditions'));
}
$select = $this->connection->select($this->conditionTable)
->condition($this->condition)
->forUpdate();
$select->addExpression('1');
if (!$select->execute()->fetchField()) {
try {
$insert = $this->connection->insert($this->table)->fields($this->insertFields);
if ($this->defaultFields) {
$insert->useDefaults($this->defaultFields);
}
$insert->execute();
return MergeQuery::STATUS_INSERT;
}
catch (Exception $e) {
// The insert query failed, maybe it's because a racing insert query
// beat us in inserting the same row. Retry the select query, if it
// returns a row, ignore the error and continue with the update
// query below.
if (!$select->execute()->fetchField()) {
throw $e;
}
if (!count($this->condition)) {
throw new InvalidMergeQueryException(t('Invalid merge query: no conditions'));
}
$select = $this->connection->select($this->conditionTable)
->condition($this->condition);
$select->addExpression('1');
if (!$select->execute()->fetchField()) {
try {
$insert = $this->connection->insert($this->table)->fields($this->insertFields);
if ($this->defaultFields) {
$insert->useDefaults($this->defaultFields);
}
$insert->execute();
return self::STATUS_INSERT;
}
if ($this->needsUpdate) {
$update = $this->connection->update($this->table)
->fields($this->updateFields)
->condition($this->condition);
if ($this->expressionFields) {
foreach ($this->expressionFields as $field => $data) {
$update->expression($field, $data['expression'], $data['arguments']);
}
catch (Exception $e) {
// The insert query failed, maybe it's because a racing insert query
// beat us in inserting the same row. Retry the select query, if it
// returns a row, ignore the error and continue with the update
// query below.
if (!$select->execute()->fetchField()) {
throw $e;
}
$update->execute();
return MergeQuery::STATUS_UPDATE;
}
}
catch (Exception $e) {
// Something really wrong happened here, bubble up the exception to the
// caller.
$transaction->rollback();
throw $e;
}
// Transaction commits here where $transaction looses scope.
if ($this->needsUpdate) {
$update = $this->connection->update($this->table)
->fields($this->updateFields)
->condition($this->condition);
if ($this->expressionFields) {
foreach ($this->expressionFields as $field => $data) {
$update->expression($field, $data['expression'], $data['arguments']);
}
}
$update->execute();
return self::STATUS_UPDATE;
}
}
}
......
......@@ -41,7 +41,8 @@ class InsertQuery_sqlite extends InsertQuery {
// If we're selecting from a SelectQuery, finish building the query and
// pass it back, as any remaining options are irrelevant.
if (!empty($this->fromQuery)) {
return $comments . 'INSERT INTO {' . $this->table . '} (' . implode(', ', $this->insertFields) . ') ' . $this->fromQuery;
$insert_fields_string = $this->insertFields ? ' (' . implode(', ', $this->insertFields) . ') ' : ' ';
return $comments . 'INSERT INTO {' . $this->table . '}' . $insert_fields_string . $this->fromQuery;
}
return $comments . 'INSERT INTO {' . $this->table . '} (' . implode(', ', $this->insertFields) . ') VALUES (' . implode(', ', $placeholders) . ')';
......
......@@ -9,7 +9,7 @@
* Maps PHP error constants to watchdog severity levels.
*
* The error constants are documented at
* http://php.net/manual/en/errorfunc.constants.php
* http://php.net/manual/errorfunc.constants.php
*
* @ingroup logging_severity_levels
*/
......
......@@ -754,10 +754,11 @@ function file_usage_delete(stdClass $file, $module, $type = NULL, $id = NULL, $c
* stored in the database. This is a powerful function that in many ways
* performs like an advanced version of copy().
* - Checks if $source and $destination are valid and readable/writable.
* - Checks that $source is not equal to $destination; if they are an error
* is reported.
* - If file already exists in $destination either the call will error out,
* replace the file or rename the file based on the $replace parameter.
* - If the $source and $destination are equal, the behavior depends on the
* $replace parameter. FILE_EXISTS_REPLACE will error out. FILE_EXISTS_RENAME
* will rename the file until the $destination is unique.
* - Adds the new file to the files database. If the source file is a
* temporary file, the resulting file will also be a temporary file. See
* file_save_upload() for details on temporary files.
......@@ -852,10 +853,11 @@ function file_valid_uri($uri) {
* This is a powerful function that in many ways performs like an advanced
* version of copy().
* - Checks if $source and $destination are valid and readable/writable.
* - Checks that $source is not equal to $destination; if they are an error
* is reported.
* - If file already exists in $destination either the call will error out,
* replace the file or rename the file based on the $replace parameter.
* - If the $source and $destination are equal, the behavior depends on the
* $replace parameter. FILE_EXISTS_REPLACE will error out. FILE_EXISTS_RENAME
* will rename the file until the $destination is unique.
* - Provides a fallback using realpaths if the move fails using stream
* wrappers. This can occur because PHP's copy() function does not properly
* support streams if safe_mode or open_basedir are enabled. See
......@@ -1143,7 +1145,7 @@ function file_munge_filename($filename, $extensions, $alerts = TRUE) {
// Allow potentially insecure uploads for very savvy users and admin
if (!variable_get('allow_insecure_uploads', 0)) {
// Remove any null bytes. See http://php.net/manual/en/security.filesystem.nullbytes.php
// Remove any null bytes. See http://php.net/manual/security.filesystem.nullbytes.php
$filename = str_replace(chr(0), '', $filename);
$whitelist = array_unique(explode(' ', trim($extensions)));
......@@ -1449,7 +1451,7 @@ function file_save_upload($source, $validators = array(), $destination = FALSE,
// Check for file upload errors and return FALSE if a lower level system
// error occurred. For a complete list of errors:
// See http://php.net/manual/en/features.file-upload.errors.php.
// See http://php.net/manual/features.file-upload.errors.php.
switch ($_FILES['files']['error'][$source]) {
case UPLOAD_ERR_INI_SIZE:
case UPLOAD_ERR_FORM_SIZE:
......@@ -2212,7 +2214,7 @@ function drupal_chmod($uri, $mode = NULL) {
* @param $uri
* A URI or pathname.
* @param $context
* Refer to http://php.net/manual/en/ref.stream.php
* Refer to http://php.net/manual/ref.stream.php
*
* @return
* Boolean TRUE on success, or FALSE on failure.
......@@ -2345,7 +2347,7 @@ function drupal_basename($uri, $suffix = NULL) {
* @param $recursive
* Default to FALSE.
* @param $context
* Refer to http://php.net/manual/en/ref.stream.php
* Refer to http://php.net/manual/ref.stream.php
*
* @return
* Boolean TRUE on success, or FALSE on failure.
......@@ -2376,7 +2378,7 @@ function drupal_mkdir($uri, $mode = NULL, $recursive = FALSE, $context = NULL) {
* @param $uri
* A URI or pathname.
* @param $context
* Refer to http://php.net/manual/en/ref.stream.php
* Refer to http://php.net/manual/ref.stream.php
*
* @return
* Boolean TRUE on success, or FALSE on failure.
......
......@@ -82,11 +82,11 @@ class FileTransferFTPExtension extends FileTransferFTP implements FileTransferCh
if (!$list) {
$list = array();
}
foreach ($list as $item){
foreach ($list as $item) {
if ($item == '.' || $item == '..') {
continue;
}
if (@ftp_chdir($this->connection, $item)){
if (@ftp_chdir($this->connection, $item)) {
ftp_cdup($this->connection);
$this->removeDirectory(ftp_pwd($this->connection) . '/' . $item);
}
......@@ -122,7 +122,7 @@ class FileTransferFTPExtension extends FileTransferFTP implements FileTransferCh
function chmodJailed($path, $mode, $recursive) {
if (!ftp_chmod($this->connection, $mode, $path)) {
throw new FileTransferException("Unable to set permissions on %file", NULL, array ('%file' => $path));
throw new FileTransferException("Unable to set permissions on %file", NULL, array('%file' => $path));
}
if ($this->isDirectory($path) && $recursive) {
$filelist = @ftp_nlist($this->connection, $path);
......
......@@ -235,6 +235,12 @@ function drupal_get_form($form_id) {
* likely to occur during Ajax operations.
* - programmed: If TRUE, the form was submitted programmatically, usually
* invoked via drupal_form_submit(). Defaults to FALSE.
* - programmed_bypass_access_check: If TRUE, programmatic form submissions
* are processed without taking #access into account. Set this to FALSE
* when submitting a form programmatically with values that may have been
* input by the user executing the current request; this will cause #access
* to be respected as it would on a normal form submission. Defaults to
* TRUE.
* - process_input: Boolean flag. TRUE signifies correct form submission.
* This is always TRUE for programmed forms coming from drupal_form_submit()
* (see 'programmed' key), or if the form_id coming from the $_POST data is
......@@ -402,6 +408,7 @@ function form_state_defaults() {
'submitted' => FALSE,
'executed' => FALSE,
'programmed' => FALSE,
'programmed_bypass_access_check' => TRUE,
'cache'=> FALSE,
'method' => 'post',
'groups' => array(),
......@@ -1985,7 +1992,7 @@ function _form_builder_handle_input_element($form_id, &$element, &$form_state) {
// #access=FALSE on an element usually allow access for some users, so forms
// submitted with drupal_form_submit() may bypass access restriction and be
// treated as high-privilege users instead.
$process_input = empty($element['#disabled']) && ($form_state['programmed'] || ($form_state['process_input'] && (!isset($element['#access']) || $element['#access'])));
$process_input = empty($element['#disabled']) && (($form_state['programmed'] && $form_state['programmed_bypass_access_check']) || ($form_state['process_input'] && (!isset($element['#access']) || $element['#access'])));
// Set the element's #value property.
if (!isset($element['#value']) && !array_key_exists('#value', $element)) {
......
......@@ -692,6 +692,21 @@ function install_full_redirect_url($install_state) {
*/
function install_display_output($output, $install_state) {
drupal_page_header();
// Prevent install.php from being indexed when installed in a sub folder.
// robots.txt rules are not read if the site is within domain.com/subfolder
// resulting in /subfolder/install.php being found through search engines.
// When settings.php is writeable this can be used via an external database
// leading a malicious user to gain php access to the server.
$noindex_meta_tag = array(
'#tag' => 'meta',
'#attributes' => array(
'name' => 'robots',
'content' => 'noindex, nofollow',
),
);
drupal_add_html_head($noindex_meta_tag, 'install_meta_robots');
// Only show the task list if there is an active task; otherwise, the page
// request has ended before tasks have even been started, so there is nothing
// meaningful to show.
......
......@@ -1134,7 +1134,6 @@ function st($string, array $args = array(), array $options = array()) {
}
}
require_once DRUPAL_ROOT . '/includes/theme.inc';
// Transform arguments before inserting them
foreach ($args as $key => $value) {
switch ($key[0]) {
......
......@@ -78,7 +78,7 @@ define('LANGUAGE_NEGOTIATION_DEFAULT', 'language-default');
* function mymodule_language_negotiation_info_alter(&$negotiation_info) {
* // Replace the core function with our own function.
* module_load_include('language', 'inc', 'language.negotiation');
* $negotiation_info[LANGUAGE_NEGOTIATION_URL]['callbacks']['negotiation'] = 'mymodule_from_url';
* $negotiation_info[LANGUAGE_NEGOTIATION_URL]['callbacks']['language'] = 'mymodule_from_url';
* $negotiation_info[LANGUAGE_NEGOTIATION_URL]['file'] = drupal_get_path('module', 'mymodule') . '/mymodule.module';
* }
*
......@@ -94,7 +94,6 @@ define('LANGUAGE_NEGOTIATION_DEFAULT', 'language-default');
* }
* return $langcode;
* }
* ?>
* @endcode
*
* For more information, see
......@@ -314,7 +313,7 @@ function language_negotiation_get_switch_links($type, $path) {
}
/**
* Removes any unused language negotation providers from the configuration.
* Removes any unused language negotiation providers from the configuration.
*/
function language_negotiation_purge() {
// Ensure that we are getting the defined language negotiation information. An
......
......@@ -339,13 +339,13 @@ interface MailSystemInterface {
*
* We deliberately use LF rather than CRLF, see drupal_mail().
*
* @param $text
* @param string $text
* The plain text to process.
* @param $indent (optional)
* @param string $indent (optional)
* A string to indent the text with. Only '>' characters are repeated on
* subsequent wrapped lines. Others are replaced by spaces.
*
* @return
* @return string
* The content of the email as a string with formatting applied.
*/
function drupal_wrap_mail($text, $indent = '') {
......@@ -356,8 +356,9 @@ function drupal_wrap_mail($text, $indent = '') {
$soft = strpos($clean_indent, ' ') === FALSE;
// Check if the string has line breaks.
if (strpos($text, "\n") !== FALSE) {
// Remove trailing spaces to make existing breaks hard.
$text = preg_replace('/ +\n/m', "\n", $text);
// Remove trailing spaces to make existing breaks hard, but leave signature
// marker untouched (RFC 3676, Section 4.3).
$text = preg_replace('/(?(?<!^--) +\n| +\n)/m', "\n", $text);
// Wrap each line at the needed width.
$lines = explode("\n", $text);
array_walk($lines, '_drupal_wrap_mail_line', array('soft' => $soft, 'length' => strlen($indent)));
......@@ -563,7 +564,7 @@ function drupal_html_to_text($string, $allowed_tags = NULL) {
*/
function _drupal_wrap_mail_line(&$line, $key, $values) {
// Use soft-breaks only for purely quoted or unindented text.
$line = wordwrap($line, 77 - $values['length'], $values['soft'] ? " \n" : "\n");
$line = wordwrap($line, 77 - $values['length'], $values['soft'] ? " \n" : "\n");
// Break really long words at the maximum width allowed.
$line = wordwrap($line, 996 - $values['length'], $values['soft'] ? " \n" : "\n");
}
......
......@@ -1926,13 +1926,21 @@ function menu_local_tasks($level = 0) {
}
// Get all tabs (also known as local tasks) and the root page.
$result = db_select('menu_router', NULL, array('fetch' => PDO::FETCH_ASSOC))
->fields('menu_router')
->condition('tab_root', $router_item['tab_root'])
->condition('context', MENU_CONTEXT_INLINE, '<>')
->orderBy('weight')
->orderBy('title')
->execute();
$cid = 'local_tasks:' . $router_item['tab_root'];
if ($cache = cache_get($cid, 'cache_menu')) {
$result = $cache->data;
}
else {
$result = db_select('menu_router', NULL, array('fetch' => PDO::FETCH_ASSOC))
->fields('menu_router')
->condition('tab_root', $router_item['tab_root'])
->condition('context', MENU_CONTEXT_INLINE, '<>')
->orderBy('weight')
->orderBy('title')
->execute()
->fetchAll();
cache_set($cid, $result, 'cache_menu');
}
$map = $router_item['original_map'];
$children = array();
$tasks = array();
......
......@@ -93,7 +93,7 @@ define('STREAM_WRAPPERS_LOCAL_NORMAL', STREAM_WRAPPERS_LOCAL | STREAM_WRAPPERS_N
/**
* Generic PHP stream wrapper interface.
*
* @see http://www.php.net/manual/en/class.streamwrapper.php
* @see http://www.php.net/manual/class.streamwrapper.php
*/
interface StreamWrapperInterface {
public function stream_open($uri, $mode, $options, &$opened_url);
......@@ -401,7 +401,7 @@ abstract class DrupalLocalStreamWrapper implements DrupalStreamWrapperInterface
* @return
* Returns TRUE if file was opened successfully.
*
* @see http://php.net/manual/en/streamwrapper.stream-open.php
* @see http://php.net/manual/streamwrapper.stream-open.php
*/
public function stream_open($uri, $mode, $options, &$opened_path) {
$this->uri = $uri;
......@@ -429,7 +429,7 @@ abstract class DrupalLocalStreamWrapper implements DrupalStreamWrapperInterface
* @return
* Always returns TRUE at the present time.
*
* @see http://php.net/manual/en/streamwrapper.stream-lock.php
* @see http://php.net/manual/streamwrapper.stream-lock.php
*/
public function stream_lock($operation) {
if (in_array($operation, array(LOCK_SH, LOCK_EX, LOCK_UN, LOCK_NB))) {
......@@ -448,7 +448,7 @@ abstract class DrupalLocalStreamWrapper implements DrupalStreamWrapperInterface
* @return
* The string that was read, or FALSE in case of an error.
*
* @see http://php.net/manual/en/streamwrapper.stream-read.php
* @see http://php.net/manual/streamwrapper.stream-read.php
*/
public function stream_read($count) {
return fread($this->handle, $count);
......@@ -463,7 +463,7 @@ abstract class DrupalLocalStreamWrapper implements DrupalStreamWrapperInterface
* @return
* The number of bytes written (integer).
*
* @see http://php.net/manual/en/streamwrapper.stream-write.php
* @see http://php.net/manual/streamwrapper.stream-write.php
*/
public function stream_write($data) {
return fwrite($this->handle, $data);
......@@ -475,7 +475,7 @@ abstract class DrupalLocalStreamWrapper implements DrupalStreamWrapperInterface
* @return
* TRUE if end-of-file has been reached.
*
* @see http://php.net/manual/en/streamwrapper.stream-eof.php
* @see http://php.net/manual/streamwrapper.stream-eof.php
*/
public function stream_eof() {
return feof($this->handle);
......@@ -492,7 +492,7 @@ abstract class DrupalLocalStreamWrapper implements DrupalStreamWrapperInterface
* @return
* TRUE on success.
*
* @see http://php.net/manual/en/streamwrapper.stream-seek.php
* @see http://php.net/manual/streamwrapper.stream-seek.php
*/
public function stream_seek($offset, $whence) {
// fseek returns 0 on success and -1 on a failure.
......@@ -506,7 +506,7 @@ abstract class DrupalLocalStreamWrapper implements DrupalStreamWrapperInterface
* @return
* TRUE if data was successfully stored (or there was no data to store).
*
* @see http://php.net/manual/en/streamwrapper.stream-flush.php
* @see http://php.net/manual/streamwrapper.stream-flush.php
*/
public function stream_flush() {
return fflush($this->handle);
......@@ -518,7 +518,7 @@ abstract class DrupalLocalStreamWrapper implements DrupalStreamWrapperInterface
* @return
* The current offset in bytes from the beginning of file.
*
* @see http://php.net/manual/en/streamwrapper.stream-tell.php
* @see http://php.net/manual/streamwrapper.stream-tell.php
*/
public function stream_tell() {
return ftell($this->handle);
......@@ -531,7 +531,7 @@ abstract class DrupalLocalStreamWrapper implements DrupalStreamWrapperInterface
* An array with file status, or FALSE in case of an error - see fstat()
* for a description of this array.
*
* @see http://php.net/manual/en/streamwrapper.stream-stat.php
* @see http://php.net/manual/streamwrapper.stream-stat.php
*/
public function stream_stat() {
return fstat($this->handle);
......@@ -543,7 +543,7 @@ abstract class DrupalLocalStreamWrapper implements DrupalStreamWrapperInterface
* @return
* TRUE if stream was successfully closed.
*
* @see http://php.net/manual/en/streamwrapper.stream-close.php
* @see http://php.net/manual/streamwrapper.stream-close.php
*/
public function stream_close() {
return fclose($this->handle);
......@@ -558,7 +558,7 @@ abstract class DrupalLocalStreamWrapper implements DrupalStreamWrapperInterface
* @return
* TRUE if resource was successfully deleted.
*
* @see http://php.net/manual/en/streamwrapper.unlink.php
* @see http://php.net/manual/streamwrapper.unlink.php
*/
public function unlink($uri) {
$this->uri = $uri;
......@@ -576,7 +576,7 @@ abstract class DrupalLocalStreamWrapper implements DrupalStreamWrapperInterface
* @return
* TRUE if file was successfully renamed.
*
* @see http://php.net/manual/en/streamwrapper.rename.php
* @see http://php.net/manual/streamwrapper.rename.php
*/
public function rename($from_uri, $to_uri) {
return rename($this->getLocalPath($from_uri), $this->getLocalPath($to_uri));
......@@ -622,7 +622,7 @@ abstract class DrupalLocalStreamWrapper implements DrupalStreamWrapperInterface
* @return
* TRUE if directory was successfully created.
*
* @see http://php.net/manual/en/streamwrapper.mkdir.php
* @see http://php.net/manual/streamwrapper.mkdir.php
*/
public function mkdir($uri, $mode, $options) {
$this->uri = $uri;
......@@ -654,7 +654,7 @@ abstract class DrupalLocalStreamWrapper implements DrupalStreamWrapperInterface
* @return
* TRUE if directory was successfully removed.
*
* @see http://php.net/manual/en/streamwrapper.rmdir.php
* @see http://php.net/manual/streamwrapper.rmdir.php
*/
public function rmdir($uri, $options) {
$this->uri = $uri;
......@@ -678,7 +678,7 @@ abstract class DrupalLocalStreamWrapper implements DrupalStreamWrapperInterface
* An array with file status, or FALSE in case of an error - see fstat()
* for a description of this array.
*
* @see http://php.net/manual/en/streamwrapper.url-stat.php
* @see http://php.net/manual/streamwrapper.url-stat.php
*/
public function url_stat($uri, $flags) {
$this->uri = $uri;
......@@ -704,7 +704,7 @@ abstract class DrupalLocalStreamWrapper implements DrupalStreamWrapperInterface
* @return
* TRUE on success.
*
* @see http://php.net/manual/en/streamwrapper.dir-opendir.php
* @see http://php.net/manual/streamwrapper.dir-opendir.php
*/
public function dir_opendir($uri, $options) {
$this->uri = $uri;
......@@ -719,7 +719,7 @@ abstract class DrupalLocalStreamWrapper implements DrupalStreamWrapperInterface
* @return
* The next filename, or FALSE if there are no more files in the directory.
*
* @see http://php.net/manual/en/streamwrapper.dir-readdir.php
* @see http://php.net/manual/streamwrapper.dir-readdir.php
*/
public function dir_readdir() {
return readdir($this->handle);
......@@ -731,7 +731,7 @@ abstract class DrupalLocalStreamWrapper implements DrupalStreamWrapperInterface
* @return
* TRUE on success.
*
* @see http://php.net/manual/en/streamwrapper.dir-rewinddir.php
* @see http://php.net/manual/streamwrapper.dir-rewinddir.php
*/
public function dir_rewinddir() {
rewinddir($this->handle);
......@@ -747,7 +747,7 @@ abstract class DrupalLocalStreamWrapper implements DrupalStreamWrapperInterface
* @return
* TRUE on success.
*
* @see http://php.net/manual/en/streamwrapper.dir-closedir.php
* @see http://php.net/manual/streamwrapper.dir-closedir.php
*/
public function dir_closedir() {
closedir($this->handle);
......@@ -788,8 +788,6 @@ class DrupalPublicStreamWrapper extends DrupalLocalStreamWrapper {
*
* Provides support for storing privately accessible files with the Drupal file
* interface.
*
* Extends DrupalPublicStreamWrapper.
*/
class DrupalPrivateStreamWrapper extends DrupalLocalStreamWrapper {
/**
......
......@@ -373,7 +373,7 @@ states.Trigger.states = {
checked: {
'change': function () {
return this.attr('checked');
return this.is(':checked');
}
},
......
......@@ -7,8 +7,8 @@ files[] = aggregator.test
configure = admin/config/services/aggregator/settings
stylesheets[all][] = aggregator.css
; Information added by packaging script on 2013-11-20
version = "7.24"
; Information added by Drupal.org packaging script on 2014-01-15
version = "7.26"
project = "drupal"
datestamp = "1384983240"
datestamp = "1389815930"
......@@ -931,7 +931,7 @@ class AggregatorRenderingTestCase extends AggregatorTestCase {
// up.
$feed->block = 0;
aggregator_save_feed((array) $feed);
// It is nescessary to flush the cache after saving the number of items.
// It is necessary to flush the cache after saving the number of items.
drupal_flush_all_caches();
// Check that the block is no longer displayed.
$this->drupalGet('node');
......
......@@ -5,8 +5,8 @@ version = VERSION
core = 7.x
hidden = TRUE
; Information added by packaging script on 2013-11-20
version = "7.24"
; Information added by Drupal.org packaging script on 2014-01-15
version = "7.26"
project = "drupal"
datestamp = "1384983240"
datestamp = "1389815930"
......@@ -200,11 +200,13 @@ function hook_block_save($delta = '', $edit = array()) {
* within the module, defined in hook_block_info().
*
* @return
* An array containing the following elements:
* Either an empty array so the block will not be shown or an array containing
* the following elements:
* - subject: The default localized title of the block. If the block does not
* have a default title, this should be set to NULL.
* - content: The content of the block's body. This may be a renderable array
* (preferable) or a string containing rendered HTML content.
* (preferable) or a string containing rendered HTML content. If the content
* is empty the block will not be shown.
*
* For a detailed usage example, see block_example.module.
*
......@@ -253,8 +255,9 @@ function hook_block_view($delta = '') {
* specific block.
*
* @param $data
* An array of data, as returned from the hook_block_view() implementation of
* the module that defined the block:
* The data as returned from the hook_block_view() implementation of the
* module that defined the block. This could be an empty array or NULL value
* (if the block is empty) or an array containing:
* - subject: The default localized title of the block.
* - content: Either a string or a renderable array representing the content
* of the block. You should check that the content is an array before trying
......@@ -287,8 +290,9 @@ function hook_block_view_alter(&$data, $block) {
* specific block, rather than implementing hook_block_view_alter().
*
* @param $data
* An array of data, as returned from the hook_block_view() implementation of
* the module that defined the block:
* The data as returned from the hook_block_view() implementation of the
* module that defined the block. This could be an empty array or NULL value
* (if the block is empty) or an array containing:
* - subject: The localized title of the block.
* - content: Either a string or a renderable array representing the content
* of the block. You should check that the content is an array before trying
......
......@@ -6,8 +6,8 @@ core = 7.x
files[] = block.test
configure = admin/structure/block
; Information added by packaging script on 2013-11-20
version = "7.24"
; Information added by Drupal.org packaging script on 2014-01-15
version = "7.26"
project = "drupal"
datestamp = "1384983240"
datestamp = "1389815930"
......@@ -401,23 +401,27 @@ function _block_rehash($theme = NULL) {
}
// Save the blocks defined in code for alter context.
$code_blocks = $current_blocks;
$database_blocks = db_select('block', 'b')
$database_blocks = db_select('block', 'b', array('fetch' => PDO::FETCH_ASSOC))
->fields('b')
->condition($or)
->condition('theme', $theme)
->execute();
$original_database_blocks = array();
foreach ($database_blocks as $block) {
// Preserve info which is not in the database.
$block->info = $current_blocks[$block->module][$block->delta]['info'];
$module = $block['module'];
$delta = $block['delta'];
$original_database_blocks[$module][$delta] = $block;
// The cache mode can only by set from hook_block_info(), so that has
// precedence over the database's value.
if (isset($current_blocks[$block->module][$block->delta]['cache'])) {
$block->cache = $current_blocks[$block->module][$block->delta]['cache'];
if (isset($current_blocks[$module][$delta]['cache'])) {
$block['cache'] = $current_blocks[$module][$delta]['cache'];
}
// Preserve info which is not in the database.
$block['info'] = $current_blocks[$module][$delta]['info'];
// Blocks stored in the database override the blocks defined in code.
$current_blocks[$block->module][$block->delta] = get_object_vars($block);
$current_blocks[$module][$delta] = $block;
// Preserve this block.
$bids[$block->bid] = $block->bid;
$bids[$block['bid']] = $block['bid'];
}
drupal_alter('block_info', $current_blocks, $theme, $code_blocks);
foreach ($current_blocks as $module => $module_blocks) {
......@@ -456,7 +460,15 @@ function _block_rehash($theme = NULL) {
else {
$primary_keys = array();
}
drupal_write_record('block', $block, $primary_keys);
// If the block is new or differs from the original database block, save
// it. To determine whether there was a change it is enough to examine
// the values for the keys in the original database record as that
// contained every database field.
if (!$primary_keys || array_diff_assoc($original_database_blocks[$module][$delta], $block)) {
drupal_write_record('block', $block, $primary_keys);
// Make it possible to test this.
$block['saved'] = TRUE;
}
// Add to the list of blocks we return.
$blocks[] = $block;
}
......@@ -880,9 +892,11 @@ function _block_render_blocks($region_blocks) {
else {
$array = module_invoke($block->module, 'block_view', $block->delta);
// Valid PHP function names cannot contain hyphens.
$delta = str_replace('-', '_', $block->delta);
// Allow modules to modify the block before it is viewed, via either
// hook_block_view_alter() or hook_block_view_MODULE_DELTA_alter().
drupal_alter(array('block_view', "block_view_{$block->module}_{$block->delta}"), $array, $block);
drupal_alter(array('block_view', "block_view_{$block->module}_{$delta}"), $array, $block);
if (isset($cid)) {
cache_set($cid, $array, 'cache_block', CACHE_TEMPORARY);
......
......@@ -193,7 +193,7 @@ class BlockTestCase extends DrupalWebTestCase {
}
/**
* Test block visibility when using "pages" restriction but leaving
* Test block visibility when using "pages" restriction but leaving
* "pages" textarea empty
*/
function testBlockVisibilityListedEmpty() {
......@@ -752,6 +752,48 @@ class BlockTemplateSuggestionsUnitTest extends DrupalUnitTestCase {
}
}
/**
* Tests for hook_block_view_MODULE_DELTA_alter().
*/
class BlockViewModuleDeltaAlterWebTest extends DrupalWebTestCase {
public static function getInfo() {
return array(
'name' => 'Block view module delta alter',
'description' => 'Test the hook_block_view_MODULE_DELTA_alter() hook.',
'group' => 'Block',
);
}
public function setUp() {
parent::setUp(array('block_test'));
}
/**
* Tests that the alter hook is called, even if the delta contains a hyphen.
*/
public function testBlockViewModuleDeltaAlter() {
$block = new stdClass;
$block->module = 'block_test';
$block->delta = 'test_underscore';
$block->title = '';
$render_array = _block_render_blocks(array('region' => $block));
$render = array_pop($render_array);
$test_underscore = $render->content['#markup'];
$this->assertEqual($test_underscore, 'hook_block_view_MODULE_DELTA_alter', 'Found expected altered block content for delta with underscore');
$block = new stdClass;
$block->module = 'block_test';
$block->delta = 'test-hyphen';
$block->title = '';
$render_array = _block_render_blocks(array('region' => $block));
$render = array_pop($render_array);
$test_hyphen = $render->content['#markup'];
$this->assertEqual($test_hyphen, 'hook_block_view_MODULE_DELTA_alter', 'Hyphens (-) in block delta were replaced by underscore (_)');
}
}
/**
* Tests that hidden regions do not inherit blocks when a theme is enabled.
*/
......@@ -857,3 +899,81 @@ class BlockInvalidRegionTestCase extends DrupalWebTestCase {
$this->assertNoRaw($warning_message, 'Disabled block in the invalid region will not trigger the warning.');
}
}
/**
* Tests that block rehashing works correctly.
*/
class BlockHashTestCase extends DrupalWebTestCase {
public static function getInfo() {
return array(
'name' => 'Block rehash',
'description' => 'Checks _block_rehash() functionality.',
'group' => 'Block',
);
}
function setUp() {
parent::setUp(array('block'));
}
/**
* Tests that block rehashing does not write to the database too often.
*/
function testBlockRehash() {
// No hook_block_info_alter(), no save.
$this->doRehash();
module_enable(array('block_test'), FALSE);
// Save the new blocks, check that the new blocks exist by checking weight.
_block_rehash();
$this->assertWeight(0);
// Now hook_block_info_alter() exists but no blocks are saved on a second
// rehash.
$this->doRehash();
$this->assertWeight(0);
// Now hook_block_info_alter() exists and is changing one block which
// should be saved.
$GLOBALS['conf']['block_test_info_alter'] = 1;
$this->doRehash(TRUE);
$this->assertWeight(10000);
// Now hook_block_info_alter() exists but already changed the block's
// weight before, so it should not be saved again.
$this->doRehash();
$this->assertWeight(10000);
}
/**
* Performs a block rehash and checks several related assertions.
*
* @param $alter_active
* Set to TRUE if the block_test module's hook_block_info_alter()
* implementation is expected to make a change that results in an existing
* block needing to be resaved to the database. Defaults to FALSE.
*/
function doRehash($alter_active = FALSE) {
$saves = 0;
foreach (_block_rehash() as $block) {
$module = $block['module'];
$delta = $block['delta'];
if ($alter_active && $module == 'block_test' && $delta == 'test_html_id') {
$this->assertFalse(empty($block['saved']), "$module $delta saved");
$saves++;
}
else {
$this->assertTrue(empty($block['saved']), "$module $delta not saved");
}
}
$this->assertEqual($alter_active, $saves);
}
/**
* Asserts that the block_test module's block has a given weight.
*
* @param $weight
* The expected weight.
*/
function assertWeight($weight) {
$db_weight = db_query('SELECT weight FROM {block} WHERE module = :module AND delta = :delta', array(':module' => 'block_test', ':delta' => 'test_html_id'))->fetchField();
// By casting to string the assert fails on FALSE.
$this->assertIdentical((string) $db_weight, (string) $weight);
}
}
......@@ -5,8 +5,8 @@ version = VERSION
core = 7.x
hidden = TRUE
; Information added by packaging script on 2013-11-20
version = "7.24"
; Information added by Drupal.org packaging script on 2014-01-15
version = "7.26"
project = "drupal"
datestamp = "1384983240"
datestamp = "1389815930"
......@@ -22,6 +22,14 @@ function block_test_block_info() {
'cache' => variable_get('block_test_caching', DRUPAL_CACHE_PER_ROLE),
);
$blocks['test_underscore'] = array(
'info' => t('Test underscore'),
);
$blocks['test-hyphen'] = array(
'info' => t('Test hyphen'),
);
$blocks['test_html_id'] = array(
'info' => t('Test block html id'),
);
......@@ -34,3 +42,26 @@ function block_test_block_info() {
function block_test_block_view($delta = 0) {
return array('content' => variable_get('block_test_content', ''));
}
/**
* Implements hook_block_view_MODULE_DELTA_alter().
*/
function block_test_block_view_block_test_test_underscore_alter(&$data, $block) {
$data['content'] = 'hook_block_view_MODULE_DELTA_alter';
}
/**
* Implements hook_block_view_MODULE_DELTA_alter().
*/
function block_test_block_view_block_test_test_hyphen_alter(&$data, $block) {
$data['content'] = 'hook_block_view_MODULE_DELTA_alter';
}
/**
* Implements hook_block_info_alter().
*/
function block_test_block_info_alter(&$blocks) {
if (variable_get('block_test_info_alter')) {
$blocks['block_test']['test_html_id']['weight'] = 10000;
}
}
......@@ -13,8 +13,8 @@ regions[footer] = Footer
regions[highlighted] = Highlighted
regions[help] = Help
; Information added by packaging script on 2013-11-20
version = "7.24"
; Information added by Drupal.org packaging script on 2014-01-15
version = "7.26"
project = "drupal"
datestamp = "1384983240"
datestamp = "1389815930"
......@@ -5,8 +5,8 @@ version = VERSION
core = 7.x
files[] = blog.test
; Information added by packaging script on 2013-11-20
version = "7.24"
; Information added by Drupal.org packaging script on 2014-01-15
version = "7.26"
project = "drupal"
datestamp = "1384983240"
datestamp = "1389815930"
......@@ -42,8 +42,8 @@ class BlogTestCase extends DrupalWebTestCase {
$this->drupalGet('blog/' . $this->big_user->uid);
$this->assertResponse(200);
$this->assertTitle(t("@name's blog", array('@name' => format_username($this->big_user))) . ' | Drupal', t('Blog title was displayed'));
$this->assertText(t('You are not allowed to post a new blog entry.'), t('No new entries can be posted without the right permission'));
$this->assertTitle(t("@name's blog", array('@name' => format_username($this->big_user))) . ' | Drupal', 'Blog title was displayed');
$this->assertText(t('You are not allowed to post a new blog entry.'), 'No new entries can be posted without the right permission');
}
/**
......@@ -54,8 +54,8 @@ class BlogTestCase extends DrupalWebTestCase {
$this->drupalGet('blog/' . $this->own_user->uid);
$this->assertResponse(200);
$this->assertTitle(t("@name's blog", array('@name' => format_username($this->own_user))) . ' | Drupal', t('Blog title was displayed'));
$this->assertText(t('@author has not created any blog entries.', array('@author' => format_username($this->own_user))), t('Users blog displayed with no entries'));
$this->assertTitle(t("@name's blog", array('@name' => format_username($this->own_user))) . ' | Drupal', 'Blog title was displayed');
$this->assertText(t('@author has not created any blog entries.', array('@author' => format_username($this->own_user))), 'Users blog displayed with no entries');
}
/**
......@@ -73,7 +73,7 @@ class BlogTestCase extends DrupalWebTestCase {
$edit = array();
$edit['blog_block_count'] = 5;
$this->drupalPost('admin/structure/block/manage/blog/recent/configure', $edit, t('Save block'));
$this->assertEqual(variable_get('blog_block_count', 10), 5, t('Number of recent blog posts changed.'));
$this->assertEqual(variable_get('blog_block_count', 10), 5, 'Number of recent blog posts changed.');
// Do basic tests for each user.
$this->doBasicTests($this->any_user, TRUE);
......@@ -132,31 +132,31 @@ class BlogTestCase extends DrupalWebTestCase {
$this->drupalGet('admin/help/blog');
$this->assertResponse($response2);
if ($response2 == 200) {
$this->assertTitle(t('Blog | Drupal'), t('Blog help node was displayed'));
$this->assertText(t('Blog'), t('Blog help node was displayed'));
$this->assertTitle(t('Blog | Drupal'), 'Blog help node was displayed');
$this->assertText(t('Blog'), 'Blog help node was displayed');
}
// Verify the blog block was displayed.
$this->drupalGet('');
$this->assertResponse(200);
$this->assertText(t('Recent blog posts'), t('Blog block was displayed'));
$this->assertText(t('Recent blog posts'), 'Blog block was displayed');
// View blog node.
$this->drupalGet('node/' . $node->nid);
$this->assertResponse(200);
$this->assertTitle($node->title . ' | Drupal', t('Blog node was displayed'));
$this->assertTitle($node->title . ' | Drupal', 'Blog node was displayed');
$breadcrumb = array(
l(t('Home'), NULL),
l(t('Blogs'), 'blog'),
l(t("!name's blog", array('!name' => format_username($node_user))), 'blog/' . $node_user->uid),
);
$this->assertRaw(theme('breadcrumb', array('breadcrumb' => $breadcrumb)), t('Breadcrumbs were displayed'));
$this->assertRaw(theme('breadcrumb', array('breadcrumb' => $breadcrumb)), 'Breadcrumbs were displayed');
// View blog edit node.
$this->drupalGet('node/' . $node->nid . '/edit');
$this->assertResponse($response);
if ($response == 200) {
$this->assertTitle('Edit Blog entry ' . $node->title . ' | Drupal', t('Blog edit node was displayed'));
$this->assertTitle('Edit Blog entry ' . $node->title . ' | Drupal', 'Blog edit node was displayed');
}
if ($response == 200) {
......@@ -166,12 +166,12 @@ class BlogTestCase extends DrupalWebTestCase {
$edit["title"] = 'node/' . $node->nid;
$edit["body[$langcode][0][value]"] = $this->randomName(256);
$this->drupalPost('node/' . $node->nid . '/edit', $edit, t('Save'));
$this->assertRaw(t('Blog entry %title has been updated.', array('%title' => $edit["title"])), t('Blog node was edited'));
$this->assertRaw(t('Blog entry %title has been updated.', array('%title' => $edit["title"])), 'Blog node was edited');
// Delete blog node.
$this->drupalPost('node/' . $node->nid . '/delete', array(), t('Delete'));
$this->assertResponse($response);
$this->assertRaw(t('Blog entry %title has been deleted.', array('%title' => $edit["title"])), t('Blog node was deleted'));
$this->assertRaw(t('Blog entry %title has been deleted.', array('%title' => $edit["title"])), 'Blog node was deleted');
}
}
......@@ -185,29 +185,29 @@ class BlogTestCase extends DrupalWebTestCase {
// Confirm blog entries link exists on the user page.
$this->drupalGet('user/' . $user->uid);
$this->assertResponse(200);
$this->assertText(t('View recent blog entries'), t('View recent blog entries link was displayed'));
$this->assertText(t('View recent blog entries'), 'View recent blog entries link was displayed');
// Confirm the recent blog entries link goes to the user's blog page.
$this->clickLink('View recent blog entries');
$this->assertTitle(t("@name's blog | Drupal", array('@name' => format_username($user))), t('View recent blog entries link target was correct'));
$this->assertTitle(t("@name's blog | Drupal", array('@name' => format_username($user))), 'View recent blog entries link target was correct');
// Confirm a blog page was displayed.
$this->drupalGet('blog');
$this->assertResponse(200);
$this->assertTitle('Blogs | Drupal', t('Blog page was displayed'));
$this->assertText(t('Home'), t('Breadcrumbs were displayed'));
$this->assertTitle('Blogs | Drupal', 'Blog page was displayed');
$this->assertText(t('Home'), 'Breadcrumbs were displayed');
$this->assertLink(t('Create new blog entry'));
// Confirm a blog page was displayed per user.
$this->drupalGet('blog/' . $user->uid);
$this->assertTitle(t("@name's blog | Drupal", array('@name' => format_username($user))), t('User blog node was displayed'));
$this->assertTitle(t("@name's blog | Drupal", array('@name' => format_username($user))), 'User blog node was displayed');
// Confirm a blog feed was displayed.
$this->drupalGet('blog/feed');
$this->assertTitle(t('Drupal blogs'), t('Blog feed was displayed'));
$this->assertTitle(t('Drupal blogs'), 'Blog feed was displayed');
// Confirm a blog feed was displayed per user.
$this->drupalGet('blog/' . $user->uid . '/feed');
$this->assertTitle(t("@name's blog", array('@name' => format_username($user))), t('User blog feed was displayed'));
$this->assertTitle(t("@name's blog", array('@name' => format_username($user))), 'User blog feed was displayed');
}
}
......@@ -7,8 +7,8 @@ files[] = book.test
configure = admin/content/book/settings
stylesheets[all][] = book.css
; Information added by packaging script on 2013-11-20
version = "7.24"
; Information added by Drupal.org packaging script on 2014-01-15
version = "7.26"
project = "drupal"
datestamp = "1384983240"
datestamp = "1389815930"
......@@ -5,8 +5,8 @@ version = VERSION
core = 7.x
files[] = color.test
; Information added by packaging script on 2013-11-20
version = "7.24"
; Information added by Drupal.org packaging script on 2014-01-15
version = "7.26"
project = "drupal"
datestamp = "1384983240"
datestamp = "1389815930"
......@@ -9,8 +9,8 @@ files[] = comment.test
configure = admin/content/comment
stylesheets[all][] = comment.css
; Information added by packaging script on 2013-11-20
version = "7.24"
; Information added by Drupal.org packaging script on 2014-01-15
version = "7.26"
project = "drupal"
datestamp = "1384983240"
datestamp = "1389815930"
......@@ -490,7 +490,7 @@ function comment_permalink($cid) {
// Return the node view, this will show the correct comment in context.
return menu_execute_active_handler('node/' . $node->nid, FALSE);
}
drupal_not_found();
return MENU_NOT_FOUND;
}
/**
......
......@@ -155,7 +155,7 @@ class CommentHelperCase extends DrupalWebTestCase {
$mode_text = 'required';
break;
}
$this->setCommentSettings('comment_preview', $mode, 'Comment preview ' . $mode_text . '.');
$this->setCommentSettings('comment_preview', $mode, format_string('Comment preview @mode_text.', array('@mode_text' => $mode_text)));
}
/**
......@@ -175,7 +175,7 @@ class CommentHelperCase extends DrupalWebTestCase {
* Anonymous level.
*/
function setCommentAnonymous($level) {
$this->setCommentSettings('comment_anonymous', $level, 'Anonymous commenting set to level ' . $level . '.');
$this->setCommentSettings('comment_anonymous', $level, format_string('Anonymous commenting set to level @level.', array('@level' => $level)));
}
/**
......@@ -185,7 +185,7 @@ class CommentHelperCase extends DrupalWebTestCase {
* Comments per page value.
*/
function setCommentsPerPage($number) {
$this->setCommentSettings('comment_default_per_page', $number, 'Number of comments per page set to ' . $number . '.');
$this->setCommentSettings('comment_default_per_page', $number, format_string('Number of comments per page set to @number.', array('@number' => $number)));
}
/**
......@@ -201,7 +201,7 @@ class CommentHelperCase extends DrupalWebTestCase {
function setCommentSettings($name, $value, $message) {
variable_set($name . '_article', $value);
// Display status message.
$this->assertTrue(TRUE, $message);
$this->pass($message);
}
/**
......@@ -273,7 +273,7 @@ class CommentInterfaceTest extends CommentHelperCase {
$this->setCommentPreview(DRUPAL_DISABLED);
$this->setCommentForm(TRUE);
$this->setCommentSubject(FALSE);
$this->setCommentSettings('comment_default_mode', COMMENT_MODE_THREADED, t('Comment paging changed.'));
$this->setCommentSettings('comment_default_mode', COMMENT_MODE_THREADED, 'Comment paging changed.');
$this->drupalLogout();
// Post comment #1 without subject or preview.
......@@ -583,7 +583,7 @@ class CommentInterfaceTest extends CommentHelperCase {
$this->setCommentPreview(DRUPAL_DISABLED);
$this->setCommentForm(TRUE);
$this->setCommentSubject(FALSE);
$this->setCommentSettings('comment_default_mode', COMMENT_MODE_THREADED, t('Comment paging changed.'));
$this->setCommentSettings('comment_default_mode', COMMENT_MODE_THREADED, 'Comment paging changed.');
$this->drupalLogout();
// Creates a second user to post comments.
......@@ -954,7 +954,7 @@ class CommentPreviewTest extends CommentHelperCase {
$this->setCommentPreview(DRUPAL_OPTIONAL);
$this->setCommentForm(TRUE);
$this->setCommentSubject(TRUE);
$this->setCommentSettings('comment_default_mode', COMMENT_MODE_THREADED, t('Comment paging changed.'));
$this->setCommentSettings('comment_default_mode', COMMENT_MODE_THREADED, 'Comment paging changed.');
$this->drupalLogout();
// Login as web user and add a signature and a user picture.
......@@ -1000,7 +1000,7 @@ class CommentPreviewTest extends CommentHelperCase {
$this->setCommentPreview(DRUPAL_OPTIONAL);
$this->setCommentForm(TRUE);
$this->setCommentSubject(TRUE);
$this->setCommentSettings('comment_default_mode', COMMENT_MODE_THREADED, t('Comment paging changed.'));
$this->setCommentSettings('comment_default_mode', COMMENT_MODE_THREADED, 'Comment paging changed.');
$edit = array();
$edit['subject'] = $this->randomName(8);
......@@ -1238,7 +1238,7 @@ class CommentPagerTest extends CommentHelperCase {
$comments[] = $this->postComment($node, $this->randomName(), $this->randomName(), TRUE);
$comments[] = $this->postComment($node, $this->randomName(), $this->randomName(), TRUE);
$this->setCommentSettings('comment_default_mode', COMMENT_MODE_FLAT, t('Comment paging changed.'));
$this->setCommentSettings('comment_default_mode', COMMENT_MODE_FLAT, 'Comment paging changed.');
// Set comments to one per page so that we are able to test paging without
// needing to insert large numbers of comments.
......@@ -1279,7 +1279,7 @@ class CommentPagerTest extends CommentHelperCase {
// If we switch to threaded mode, the replies on the oldest comment
// should be bumped to the first page and comment 6 should be bumped
// to the second page.
$this->setCommentSettings('comment_default_mode', COMMENT_MODE_THREADED, t('Switched to threaded mode.'));
$this->setCommentSettings('comment_default_mode', COMMENT_MODE_THREADED, 'Switched to threaded mode.');
$this->drupalGet('node/' . $node->nid, array('query' => array('page' => 0)));
$this->assertTrue($this->commentExists($reply, TRUE), 'In threaded mode, reply appears on page 1.');
$this->assertFalse($this->commentExists($comments[1]), 'In threaded mode, comment 2 has been bumped off of page 1.');
......@@ -1339,7 +1339,7 @@ class CommentPagerTest extends CommentHelperCase {
// - 2
// - 5
$this->setCommentSettings('comment_default_mode', COMMENT_MODE_FLAT, t('Comment paging changed.'));
$this->setCommentSettings('comment_default_mode', COMMENT_MODE_FLAT, 'Comment paging changed.');
$expected_order = array(
0,
......@@ -1353,7 +1353,7 @@ class CommentPagerTest extends CommentHelperCase {
$this->drupalGet('node/' . $node->nid);
$this->assertCommentOrder($comments, $expected_order);
$this->setCommentSettings('comment_default_mode', COMMENT_MODE_THREADED, t('Switched to threaded mode.'));
$this->setCommentSettings('comment_default_mode', COMMENT_MODE_THREADED, 'Switched to threaded mode.');
$expected_order = array(
0,
......@@ -1435,7 +1435,7 @@ class CommentPagerTest extends CommentHelperCase {
// - 2
// - 5
$this->setCommentSettings('comment_default_mode', COMMENT_MODE_FLAT, t('Comment paging changed.'));
$this->setCommentSettings('comment_default_mode', COMMENT_MODE_FLAT, 'Comment paging changed.');
$expected_pages = array(
1 => 5, // Page of comment 5
......@@ -1453,7 +1453,7 @@ class CommentPagerTest extends CommentHelperCase {
$this->assertIdentical($expected_page, $returned_page, format_string('Flat mode, @new replies: expected page @expected, returned page @returned.', array('@new' => $new_replies, '@expected' => $expected_page, '@returned' => $returned_page)));
}
$this->setCommentSettings('comment_default_mode', COMMENT_MODE_THREADED, t('Switched to threaded mode.'));
$this->setCommentSettings('comment_default_mode', COMMENT_MODE_THREADED, 'Switched to threaded mode.');
$expected_pages = array(
1 => 5, // Page of comment 5
......@@ -1509,7 +1509,7 @@ class CommentNodeAccessTest extends CommentHelperCase {
$this->setCommentPreview(DRUPAL_DISABLED);
$this->setCommentForm(TRUE);
$this->setCommentSubject(TRUE);
$this->setCommentSettings('comment_default_mode', COMMENT_MODE_THREADED, t('Comment paging changed.'));
$this->setCommentSettings('comment_default_mode', COMMENT_MODE_THREADED, 'Comment paging changed.');
$this->drupalLogout();
// Post comment.
......@@ -2126,7 +2126,7 @@ class CommentThreadingTestCase extends CommentHelperCase {
$this->setCommentPreview(DRUPAL_DISABLED);
$this->setCommentForm(TRUE);
$this->setCommentSubject(TRUE);
$this->setCommentSettings('comment_default_mode', COMMENT_MODE_THREADED, t('Comment paging changed.'));
$this->setCommentSettings('comment_default_mode', COMMENT_MODE_THREADED, 'Comment paging changed.');
$this->drupalLogout();
// Create a node.
......
......@@ -6,8 +6,8 @@ core = 7.x
files[] = contact.test
configure = admin/structure/contact
; Information added by packaging script on 2013-11-20
version = "7.24"
; Information added by Drupal.org packaging script on 2014-01-15
version = "7.26"
project = "drupal"
datestamp = "1384983240"
datestamp = "1389815930"
......@@ -5,8 +5,8 @@ version = VERSION
core = 7.x
files[] = contextual.test
; Information added by packaging script on 2013-11-20
version = "7.24"
; Information added by Drupal.org packaging script on 2014-01-15
version = "7.26"
project = "drupal"
datestamp = "1384983240"
datestamp = "1389815930"
......@@ -32,7 +32,7 @@ function hook_dashboard_regions() {
* An array containing all dashboard regions, in the format provided by
* hook_dashboard_regions().
*/
function hook_dashboard_regions_alter($regions) {
function hook_dashboard_regions_alter(&$regions) {
// Remove the sidebar region defined by the core dashboard module.
unset($regions['dashboard_sidebar']);
}
......
......@@ -7,8 +7,8 @@ files[] = dashboard.test
dependencies[] = block
configure = admin/dashboard/customize
; Information added by packaging script on 2013-11-20
version = "7.24"
; Information added by Drupal.org packaging script on 2014-01-15
version = "7.26"
project = "drupal"
datestamp = "1384983240"
datestamp = "1389815930"
......@@ -49,15 +49,15 @@ class DashboardBlocksTestCase extends DrupalWebTestCase {
// Ensure admin access.
$this->drupalGet('admin/dashboard');
$this->assertResponse(200, t('Admin has access to the dashboard.'));
$this->assertRaw($custom_block['title'], t('Admin has access to a dashboard block.'));
$this->assertResponse(200, 'Admin has access to the dashboard.');
$this->assertRaw($custom_block['title'], 'Admin has access to a dashboard block.');
// Ensure non-admin access is denied.
$normal_user = $this->drupalCreateUser();
$this->drupalLogin($normal_user);
$this->drupalGet('admin/dashboard');
$this->assertResponse(403, t('Non-admin has no access to the dashboard.'));
$this->assertNoText($custom_block['title'], t('Non-admin has no access to a dashboard block.'));
$this->assertResponse(403, 'Non-admin has no access to the dashboard.');
$this->assertNoText($custom_block['title'], 'Non-admin has no access to a dashboard block.');
}
/**
......@@ -70,7 +70,7 @@ class DashboardBlocksTestCase extends DrupalWebTestCase {
$this->drupalGet('admin/dashboard/configure');
foreach ($dashboard_regions as $region => $description) {
$elements = $this->xpath('//option[@value=:region]', array(':region' => $region));
$this->assertTrue(!empty($elements), t('%region is an available choice on the dashboard block configuration page.', array('%region' => $region)));
$this->assertTrue(!empty($elements), format_string('%region is an available choice on the dashboard block configuration page.', array('%region' => $region)));
}
// Ensure blocks cannot be placed in dashboard regions on the standard
......@@ -78,7 +78,7 @@ class DashboardBlocksTestCase extends DrupalWebTestCase {
$this->drupalGet('admin/structure/block');
foreach ($dashboard_regions as $region => $description) {
$elements = $this->xpath('//option[@value=:region]', array(':region' => $region));
$this->assertTrue(empty($elements), t('%region is not an available choice on the block configuration page.', array('%region' => $region)));
$this->assertTrue(empty($elements), format_string('%region is not an available choice on the block configuration page.', array('%region' => $region)));
}
}
......@@ -94,24 +94,24 @@ class DashboardBlocksTestCase extends DrupalWebTestCase {
$custom_block['regions[stark]'] = 'dashboard_main';
$this->drupalPost('admin/structure/block/add', $custom_block, t('Save block'));
$this->drupalGet('admin/dashboard');
$this->assertRaw($custom_block['title'], t('Block appears on the dashboard.'));
$this->assertRaw($custom_block['title'], 'Block appears on the dashboard.');
$edit = array();
$edit['modules[Core][dashboard][enable]'] = FALSE;
$this->drupalPost('admin/modules', $edit, t('Save configuration'));
$this->assertText(t('The configuration options have been saved.'), t('Modules status has been updated.'));
$this->assertNoRaw('assigned to the invalid region', t('Dashboard blocks gracefully disabled.'));
$this->assertText(t('The configuration options have been saved.'), 'Modules status has been updated.');
$this->assertNoRaw('assigned to the invalid region', 'Dashboard blocks gracefully disabled.');
module_list(TRUE);
$this->assertFalse(module_exists('dashboard'), t('Dashboard disabled.'));
$this->assertFalse(module_exists('dashboard'), 'Dashboard disabled.');
$edit['modules[Core][dashboard][enable]'] = 'dashboard';
$this->drupalPost('admin/modules', $edit, t('Save configuration'));
$this->assertText(t('The configuration options have been saved.'), t('Modules status has been updated.'));
$this->assertText(t('The configuration options have been saved.'), 'Modules status has been updated.');
module_list(TRUE);
$this->assertTrue(module_exists('dashboard'), t('Dashboard enabled.'));
$this->assertTrue(module_exists('dashboard'), 'Dashboard enabled.');
$this->drupalGet('admin/dashboard');
$this->assertRaw($custom_block['title'], t('Block still appears on the dashboard.'));
$this->assertRaw($custom_block['title'], 'Block still appears on the dashboard.');
}
/**
......@@ -121,21 +121,21 @@ class DashboardBlocksTestCase extends DrupalWebTestCase {
// Test "Recent comments", which should be available (defined as
// "administrative") but not enabled.
$this->drupalGet('admin/dashboard');
$this->assertNoText(t('Recent comments'), t('"Recent comments" not on dashboard.'));
$this->assertNoText(t('Recent comments'), '"Recent comments" not on dashboard.');
$this->drupalGet('admin/dashboard/drawer');
$this->assertText(t('Recent comments'), t('Drawer of disabled blocks includes a block defined as "administrative".'));
$this->assertNoText(t('Syndicate'), t('Drawer of disabled blocks excludes a block not defined as "administrative".'));
$this->assertText(t('Recent comments'), 'Drawer of disabled blocks includes a block defined as "administrative".');
$this->assertNoText(t('Syndicate'), 'Drawer of disabled blocks excludes a block not defined as "administrative".');
$this->drupalGet('admin/dashboard/configure');
$elements = $this->xpath('//select[@id=:id]//option[@selected="selected"]', array(':id' => 'edit-blocks-comment-recent-region'));
$this->assertTrue($elements[0]['value'] == 'dashboard_inactive', t('A block defined as "administrative" defaults to dashboard_inactive.'));
$this->assertTrue($elements[0]['value'] == 'dashboard_inactive', 'A block defined as "administrative" defaults to dashboard_inactive.');
// Now enable the block on the dashboard.
$values = array();
$values['blocks[comment_recent][region]'] = 'dashboard_main';
$this->drupalPost('admin/dashboard/configure', $values, t('Save blocks'));
$this->drupalGet('admin/dashboard');
$this->assertText(t('Recent comments'), t('"Recent comments" was placed on dashboard.'));
$this->assertText(t('Recent comments'), '"Recent comments" was placed on dashboard.');
$this->drupalGet('admin/dashboard/drawer');
$this->assertNoText(t('Recent comments'), t('Drawer of disabled blocks excludes enabled blocks.'));
$this->assertNoText(t('Recent comments'), 'Drawer of disabled blocks excludes enabled blocks.');
}
}
......@@ -5,8 +5,8 @@ version = VERSION
core = 7.x
files[] = dblog.test
; Information added by packaging script on 2013-11-20
version = "7.24"
; Information added by Drupal.org packaging script on 2014-01-15
version = "7.26"
project = "drupal"
datestamp = "1384983240"
datestamp = "1389815930"
......@@ -11,7 +11,7 @@
class DBLogTestCase extends DrupalWebTestCase {
/**
* A user with some relevent administrative permissions.
* A user with some relevant administrative permissions.
*
* @var object
*/
......
......@@ -113,6 +113,9 @@ function hook_field_extra_fields_alter(&$info) {
/**
* Define Field API field types.
*
* Along with this hook, you also need to implement other hooks. See
* @link field_types Field Types API @endlink for more information.
*
* @return
* An array whose keys are field type names and whose values are arrays
* describing the field type, with the following key/value pairs:
......@@ -199,8 +202,11 @@ function hook_field_info_alter(&$info) {
/**
* Define the Field API schema for a field structure.
*
* This hook MUST be defined in .install for it to be detected during
* installation and upgrade.
* This is invoked when a field is created, in order to obtain the database
* schema from the module that defines the field's type.
*
* This hook must be defined in the module's .install file for it to be detected
* during installation and upgrade.
*
* @param $field
* A field structure.
......
......@@ -976,6 +976,12 @@ function field_attach_insert($entity_type, $entity) {
/**
* Save field data for an existing entity.
*
* When calling this function outside an entity save operation be sure to
* clear caches for the entity:
* @code
* entity_get_controller($entity_type)->resetCache(array($entity_id))
* @endcode
*
* @param $entity_type
* The type of $entity; e.g. 'node' or 'user'.
* @param $entity
......
......@@ -11,8 +11,8 @@ dependencies[] = field_sql_storage
required = TRUE
stylesheets[all][] = theme/field.css
; Information added by packaging script on 2013-11-20
version = "7.24"
; Information added by Drupal.org packaging script on 2014-01-15
version = "7.26"
project = "drupal"
datestamp = "1384983240"
datestamp = "1389815930"
......@@ -819,9 +819,9 @@ function field_view_value($entity_type, $entity, $field_name, $item, $display =
*
* This function can be used by third-party modules that need to output an
* isolated field.
* - Do not use inside node (or other entities) templates, use
* - Do not use inside node (or any other entity) templates; use
* render($content[FIELD_NAME]) instead.
* - Do not use to display all fields in an entity, use
* - Do not use to display all fields in an entity; use
* field_attach_prepare_view() and field_attach_view() instead.
* - The field_view_value() function can be used to output a single formatted
* field value, without label or wrapping field markup.
......
......@@ -7,8 +7,8 @@ dependencies[] = field
files[] = field_sql_storage.test
required = TRUE
; Information added by packaging script on 2013-11-20
version = "7.24"
; Information added by Drupal.org packaging script on 2014-01-15
version = "7.26"
project = "drupal"
datestamp = "1384983240"
datestamp = "1389815930"
......@@ -7,8 +7,8 @@ dependencies[] = field
dependencies[] = options
files[] = tests/list.test
; Information added by packaging script on 2013-11-20
version = "7.24"
; Information added by Drupal.org packaging script on 2014-01-15
version = "7.26"
project = "drupal"
datestamp = "1384983240"
datestamp = "1389815930"
......@@ -5,8 +5,8 @@ package = Testing
version = VERSION
hidden = TRUE
; Information added by packaging script on 2013-11-20
version = "7.24"
; Information added by Drupal.org packaging script on 2014-01-15
version = "7.26"
project = "drupal"
datestamp = "1384983240"
datestamp = "1389815930"
......@@ -6,8 +6,8 @@ core = 7.x
dependencies[] = field
files[] = number.test
; Information added by packaging script on 2013-11-20
version = "7.24"
; Information added by Drupal.org packaging script on 2014-01-15
version = "7.26"
project = "drupal"
datestamp = "1384983240"
datestamp = "1389815930"
......@@ -6,8 +6,8 @@ core = 7.x
dependencies[] = field
files[] = options.test
; Information added by packaging script on 2013-11-20
version = "7.24"
; Information added by Drupal.org packaging script on 2014-01-15
version = "7.26"
project = "drupal"
datestamp = "1384983240"
datestamp = "1389815930"
......@@ -359,7 +359,7 @@ class OptionsWidgetsTestCase extends FieldTestCase {
// Test the 'None' option.
// Check that the 'none' option has no efect if actual options are selected
// Check that the 'none' option has no effect if actual options are selected
// as well.
$edit = array("card_2[$langcode][]" => array('_none' => '_none', 0 => 0));
$this->drupalPost('test-entity/manage/' . $entity->ftid . '/edit', $edit, t('Save'));
......
......@@ -7,8 +7,8 @@ dependencies[] = field
files[] = text.test
required = TRUE
; Information added by packaging script on 2013-11-20
version = "7.24"
; Information added by Drupal.org packaging script on 2014-01-15
version = "7.26"
project = "drupal"
datestamp = "1384983240"
datestamp = "1389815930"
......@@ -6,8 +6,8 @@ files[] = field_test.entity.inc
version = VERSION
hidden = TRUE
; Information added by packaging script on 2013-11-20
version = "7.24"
; Information added by Drupal.org packaging script on 2014-01-15
version = "7.26"
project = "drupal"
datestamp = "1384983240"
datestamp = "1389815930"
......@@ -60,7 +60,7 @@ function field_test_schema() {
'description' => 'The base table for test entities with a bundle key.',
'fields' => array(
'ftid' => array(
'description' => 'The primary indentifier for a test_entity_bundle_key.',
'description' => 'The primary identifier for a test_entity_bundle_key.',
'type' => 'int',
'unsigned' => TRUE,
'not null' => TRUE,
......@@ -79,7 +79,7 @@ function field_test_schema() {
'description' => 'The base table for test entities with a bundle.',
'fields' => array(
'ftid' => array(
'description' => 'The primary indentifier for a test_entity_bundle.',
'description' => 'The primary identifier for a test_entity_bundle.',
'type' => 'int',
'unsigned' => TRUE,
'not null' => TRUE,
......
......@@ -6,8 +6,8 @@ core = 7.x
dependencies[] = field
files[] = field_ui.test
; Information added by packaging script on 2013-11-20
version = "7.24"
; Information added by Drupal.org packaging script on 2014-01-15
version = "7.26"
project = "drupal"
datestamp = "1384983240"
datestamp = "1389815930"
......@@ -318,7 +318,7 @@ function field_ui_field_attach_create_bundle($entity_type, $bundle) {
}
/**
* Determines the adminstration path for a bundle.
* Determines the administration path for a bundle.
*/
function _field_ui_bundle_admin_path($entity_type, $bundle_name) {
$bundles = field_info_bundles($entity_type);
......
......@@ -186,7 +186,7 @@ function file_field_load($entity_type, $entities, $field, $instances, $langcode,
$items[$id][$delta] = NULL;
}
else {
$items[$id][$delta] = array_merge($item, (array) $files[$item['fid']]);
$items[$id][$delta] = array_merge((array) $files[$item['fid']], $item);
}
}
}
......@@ -215,8 +215,16 @@ function file_field_presave($entity_type, $entity, $field, $instance, $langcode,
// Make sure that each file which will be saved with this object has a
// permanent status, so that it will not be removed when temporary files are
// cleaned up.
foreach ($items as $item) {
foreach ($items as $delta => $item) {
if (empty($item['fid'])) {
unset($items[$delta]);
continue;
}
$file = file_load($item['fid']);
if (empty($file)) {
unset($items[$delta]);
continue;
}
if (!$file->status) {
$file->status = FILE_STATUS_PERMANENT;
file_save($file);
......
......@@ -6,8 +6,8 @@ core = 7.x
dependencies[] = field
files[] = tests/file.test
; Information added by packaging script on 2013-11-20
version = "7.24"
; Information added by Drupal.org packaging script on 2014-01-15
version = "7.26"
project = "drupal"
datestamp = "1384983240"
datestamp = "1389815930"
......@@ -5,8 +5,8 @@ version = VERSION
core = 7.x
hidden = TRUE
; Information added by packaging script on 2013-11-20
version = "7.24"
; Information added by Drupal.org packaging script on 2014-01-15
version = "7.26"
project = "drupal"
datestamp = "1384983240"
datestamp = "1389815930"
......@@ -7,8 +7,8 @@ files[] = filter.test
required = TRUE
configure = admin/config/content/formats
; Information added by packaging script on 2013-11-20
version = "7.24"
; Information added by Drupal.org packaging script on 2014-01-15
version = "7.26"
project = "drupal"
datestamp = "1384983240"
datestamp = "1389815930"
......@@ -9,8 +9,8 @@ files[] = forum.test
configure = admin/structure/forum
stylesheets[all][] = forum.css
; Information added by packaging script on 2013-11-20
version = "7.24"
; Information added by Drupal.org packaging script on 2014-01-15
version = "7.26"
project = "drupal"
datestamp = "1384983240"
datestamp = "1389815930"
......@@ -5,8 +5,8 @@ version = VERSION
core = 7.x
files[] = help.test
; Information added by packaging script on 2013-11-20
version = "7.24"
; Information added by Drupal.org packaging script on 2014-01-15
version = "7.26"
project = "drupal"
datestamp = "1384983240"
datestamp = "1389815930"
......@@ -7,8 +7,8 @@ dependencies[] = file
files[] = image.test
configure = admin/config/media/image-styles
; Information added by packaging script on 2013-11-20
version = "7.24"
; Information added by Drupal.org packaging script on 2014-01-15
version = "7.26"
project = "drupal"
datestamp = "1384983240"
datestamp = "1389815930"
......@@ -835,7 +835,7 @@ function image_style_deliver($style, $scheme) {
else {
$headers = module_invoke_all('file_download', $image_uri);
if (in_array(-1, $headers) || empty($headers)) {
return drupal_access_denied();
return MENU_ACCESS_DENIED;
}
if (count($headers)) {
foreach ($headers as $name => $value) {
......@@ -972,7 +972,9 @@ function image_style_flush($style) {
// Delete the style directory in each registered wrapper.
$wrappers = file_get_stream_wrappers(STREAM_WRAPPERS_WRITE_VISIBLE);
foreach ($wrappers as $wrapper => $wrapper_data) {
file_unmanaged_delete_recursive($wrapper . '://styles/' . $style['name']);
if (file_exists($directory = $wrapper . '://styles/' . $style['name'])) {
file_unmanaged_delete_recursive($directory);
}
}
// Let other modules update as necessary on flush.
......@@ -1010,10 +1012,14 @@ function image_style_flush($style) {
*/
function image_style_url($style_name, $path) {
$uri = image_style_path($style_name, $path);
// The passed-in $path variable can be either a relative path or a full URI.
$original_uri = file_uri_scheme($path) ? file_stream_wrapper_uri_normalize($path) : file_build_uri($path);
// The token query is added even if the 'image_allow_insecure_derivatives'
// variable is TRUE, so that the emitted links remain valid if it is changed
// back to the default FALSE.
$token_query = array(IMAGE_DERIVATIVE_TOKEN => image_style_path_token($style_name, file_stream_wrapper_uri_normalize($path)));
$token_query = array(IMAGE_DERIVATIVE_TOKEN => image_style_path_token($style_name, $original_uri));
// If not using clean URLs, the image derivative callback is only available
// with the query string. If the file does not exist, use url() to ensure
......
......@@ -216,10 +216,20 @@ class ImageStylesPathAndUrlTestCase extends DrupalWebTestCase {
}
// Add some extra chars to the token.
$this->drupalGet(str_replace(IMAGE_DERIVATIVE_TOKEN . '=', IMAGE_DERIVATIVE_TOKEN . '=Zo', $generate_url));
$this->assertResponse(403, 'Image was inaccessible at the URL wih an invalid token.');
$this->assertResponse(403, 'Image was inaccessible at the URL with an invalid token.');
// Change the parameter name so the token is missing.
$this->drupalGet(str_replace(IMAGE_DERIVATIVE_TOKEN . '=', 'wrongparam=', $generate_url));
$this->assertResponse(403, 'Image was inaccessible at the URL wih a missing token.');
$this->assertResponse(403, 'Image was inaccessible at the URL with a missing token.');
// Check that the generated URL is the same when we pass in a relative path
// rather than a URI. We need to temporarily switch the default scheme to
// match the desired scheme before testing this, then switch it back to the
// "temporary" scheme used throughout this test afterwards.
variable_set('file_default_scheme', $scheme);
$relative_path = file_uri_target($original_uri);
$generate_url_from_relative_path = image_style_url($this->style_name, $relative_path);
$this->assertEqual($generate_url, $generate_url_from_relative_path, 'Generated URL is the same regardless of whether it came from a relative path or a file URI.');
variable_set('file_default_scheme', 'temporary');
// Fetch the URL that generates the file.
$this->drupalGet($generate_url);
......@@ -268,7 +278,7 @@ class ImageStylesPathAndUrlTestCase extends DrupalWebTestCase {
elseif ($clean_url) {
// Add some extra chars to the token.
$this->drupalGet(str_replace(IMAGE_DERIVATIVE_TOKEN . '=', IMAGE_DERIVATIVE_TOKEN . '=Zo', $generate_url));
$this->assertResponse(200, 'Existing image was accessible at the URL wih an invalid token.');
$this->assertResponse(200, 'Existing image was accessible at the URL with an invalid token.');
}
// Allow insecure image derivatives to be created for the remainder of this
......
......@@ -6,8 +6,8 @@ core = 7.x
files[] = image_module_test.module
hidden = TRUE
; Information added by packaging script on 2013-11-20
version = "7.24"
; Information added by Drupal.org packaging script on 2014-01-15
version = "7.26"
project = "drupal"
datestamp = "1384983240"
datestamp = "1389815930"
......@@ -1242,9 +1242,7 @@ function locale_translate_delete_page($lid) {
if ($source = db_query('SELECT lid, source FROM {locales_source} WHERE lid = :lid', array(':lid' => $lid))->fetchObject()) {
return drupal_get_form('locale_translate_delete_form', $source);
}
else {
return drupal_not_found();
}
return MENU_NOT_FOUND;
}
/**
......
......@@ -6,8 +6,8 @@ core = 7.x
files[] = locale.test
configure = admin/config/regional/language
; Information added by packaging script on 2013-11-20
version = "7.24"
; Information added by Drupal.org packaging script on 2014-01-15
version = "7.26"
project = "drupal"
datestamp = "1384983240"
datestamp = "1389815930"
......@@ -1685,7 +1685,7 @@ class LocaleBrowserDetectionTest extends DrupalUnitTestCase {
);
$test_cases = array(
// Equal qvalue for each language, choose the site prefered one.
// Equal qvalue for each language, choose the site preferred one.
'en,en-US,fr-CA,fr,es-MX' => 'en',
'en-US,en,fr-CA,fr,es-MX' => 'en',
'fr,en' => 'en',
......
......@@ -5,8 +5,8 @@ package = Testing
version = VERSION
hidden = TRUE
; Information added by packaging script on 2013-11-20
version = "7.24"
; Information added by Drupal.org packaging script on 2014-01-15
version = "7.26"
project = "drupal"
datestamp = "1384983240"
datestamp = "1389815930"
......@@ -512,8 +512,7 @@ function menu_delete_menu_page($menu) {
// System-defined menus may not be deleted.
$system_menus = menu_list_system_menus();
if (isset($system_menus[$menu['menu_name']])) {
drupal_access_denied();
return;
return MENU_ACCESS_DENIED;
}
return drupal_get_form('menu_delete_menu_confirm', $menu);
}
......@@ -622,8 +621,7 @@ function menu_item_delete_page($item) {
// Links defined via hook_menu may not be deleted. Updated items are an
// exception, as they can be broken.
if ($item['module'] == 'system' && !$item['updated']) {
drupal_access_denied();
return;
return MENU_ACCESS_DENIED;
}
return drupal_get_form('menu_item_delete_form', $item);
}
......
......@@ -6,8 +6,8 @@ core = 7.x
files[] = menu.test
configure = admin/structure/menu
; Information added by packaging script on 2013-11-20
version = "7.24"
; Information added by Drupal.org packaging script on 2014-01-15
version = "7.26"
project = "drupal"
datestamp = "1384983240"
datestamp = "1389815930"
......@@ -255,11 +255,11 @@ function _node_characters($length) {
*/
function node_type_form_validate($form, &$form_state) {
$type = new stdClass();
$type->type = trim($form_state['values']['type']);
$type->type = $form_state['values']['type'];
$type->name = trim($form_state['values']['name']);
// Work out what the type was before the user submitted this form
$old_type = trim($form_state['values']['old_type']);
$old_type = $form_state['values']['old_type'];
$types = node_type_get_names();
......@@ -288,7 +288,7 @@ function node_type_form_submit($form, &$form_state) {
$type = node_type_set_defaults();
$type->type = trim($form_state['values']['type']);
$type->type = $form_state['values']['type'];
$type->name = trim($form_state['values']['name']);
$type->orig_type = trim($form_state['values']['orig_type']);
$type->old_type = isset($form_state['values']['old_type']) ? $form_state['values']['old_type'] : $type->type;
......
......@@ -695,6 +695,7 @@ function node_multiple_delete_confirm($form, &$form_state, $nodes) {
function node_multiple_delete_confirm_submit($form, &$form_state) {
if ($form_state['values']['confirm']) {
node_delete_multiple(array_keys($form_state['values']['nodes']));
cache_clear_all();
$count = count($form_state['values']['nodes']);
watchdog('content', 'Deleted @count posts.', array('@count' => $count));
drupal_set_message(format_plural($count, 'Deleted 1 post.', 'Deleted @count posts.'));
......
......@@ -9,8 +9,8 @@ required = TRUE
configure = admin/structure/types
stylesheets[all][] = node.css
; Information added by packaging script on 2013-11-20
version = "7.24"
; Information added by Drupal.org packaging script on 2014-01-15
version = "7.26"
project = "drupal"
datestamp = "1384983240"
datestamp = "1389815930"
......@@ -114,6 +114,7 @@ function node_schema() {
'uid' => array('uid'),
'tnid' => array('tnid'),
'translate' => array('translate'),
'language' => array('language'),
),
'unique keys' => array(
'vid' => array('vid'),
......@@ -925,6 +926,13 @@ function node_update_7013() {
db_add_unique_key('node', 'vid', array('vid'));
}
/**
* Add an index on {node}.language.
*/
function node_update_7014() {
db_add_index('node', 'language', array('language'));
}
/**
* @} End of "addtogroup updates-7.x-extra".
*/
......@@ -1179,10 +1179,8 @@ function node_save($node) {
module_invoke_all('node_' . $op, $node);
module_invoke_all('entity_' . $op, $node, 'node');
// Update the node access table for this node. There's no need to delete
// existing records if the node is new.
$delete = $op == 'update';
node_access_acquire_grants($node, $delete);
// Update the node access table for this node.
node_access_acquire_grants($node);
// Clear internal properties.
unset($node->is_new);
......@@ -2224,8 +2222,8 @@ function node_last_changed($nid) {
/**
* Returns a list of all the existing revision numbers.
*
* @param Drupal\node\Node $node
* The node entity.
* @param $node
* The node object.
*
* @return
* An associative array keyed by node revision number.
......
......@@ -542,6 +542,7 @@ function node_delete_confirm_submit($form, &$form_state) {
if ($form_state['values']['confirm']) {
$node = node_load($form_state['values']['nid']);
node_delete($form_state['values']['nid']);
cache_clear_all();
watchdog('content', '@type: deleted %title.', array('@type' => $node->type, '%title' => $node->title));
drupal_set_message(t('@type %title has been deleted.', array('@type' => node_type_get_name($node), '%title' => $node->title)));
}
......
......@@ -1363,6 +1363,22 @@ class NodeSaveTestCase extends DrupalWebTestCase {
$node = node_load($node->nid);
$this->assertEqual($node->title, 'updated_presave', 'Static cache has been cleared.');
}
/**
* Tests saving a node on node insert.
*
* This test ensures that a node has been fully saved when hook_node_insert()
* is invoked, so that the node can be saved again in a hook implementation
* without errors.
*
* @see node_test_node_insert()
*/
function testNodeSaveOnInsert() {
// node_test_node_insert() tiggers a save on insert if the title equals
// 'new'.
$node = $this->drupalCreateNode(array('title' => 'new'));
$this->assertEqual($node->title, 'Node ' . $node->nid, 'Node saved on node insert.');
}
}
/**
......@@ -2755,3 +2771,78 @@ class NodeEntityViewModeAlterTest extends NodeWebTestCase {
$this->assertEqual($build['#view_mode'], 'teaser', 'The view mode has correctly been set to teaser.');
}
}
/**
* Tests the cache invalidation of node operations.
*/
class NodePageCacheTest extends NodeWebTestCase {
/**
* An admin user with administrative permissions for nodes.
*/
protected $admin_user;
public static function getInfo() {
return array(
'name' => 'Node page cache test',
'description' => 'Test cache invalidation of node operations.',
'group' => 'Node',
);
}
function setUp() {
parent::setUp();
variable_set('cache', 1);
variable_set('page_cache_maximum_age', 300);
$this->admin_user = $this->drupalCreateUser(array(
'bypass node access',
'access content overview',
'administer nodes',
));
}
/**
* Tests deleting nodes clears page cache.
*/
public function testNodeDelete() {
$node_path = 'node/' . $this->drupalCreateNode()->nid;
// Populate page cache.
$this->drupalGet($node_path);
// Login and delete the node.
$this->drupalLogin($this->admin_user);
$this->drupalPost($node_path . '/delete', array(), t('Delete'));
// Logout and check the node is not available.
$this->drupalLogout();
$this->drupalGet($node_path);
$this->assertResponse(404);
// Create two new nodes.
$nodes[0] = $this->drupalCreateNode();
$nodes[1] = $this->drupalCreateNode();
$node_path = 'node/' . $nodes[0]->nid;
// Populate page cache.
$this->drupalGet($node_path);
// Login and delete the nodes.
$this->drupalLogin($this->admin_user);
$this->drupalGet('admin/content');
$edit = array(
'operation' => 'delete',
'nodes[' . $nodes[0]->nid . ']' => TRUE,
'nodes[' . $nodes[1]->nid . ']' => TRUE,
);
$this->drupalPost(NULL, $edit, t('Update'));
$this->drupalPost(NULL, array(), t('Delete'));
// Logout and check the node is not available.
$this->drupalLogout();
$this->drupalGet($node_path);
$this->assertResponse(404);
}
}
......@@ -5,8 +5,8 @@ version = VERSION
core = 7.x
hidden = TRUE
; Information added by packaging script on 2013-11-20
version = "7.24"
; Information added by Drupal.org packaging script on 2014-01-15
version = "7.26"
project = "drupal"
datestamp = "1384983240"
datestamp = "1389815930"
......@@ -5,8 +5,8 @@ version = VERSION
core = 7.x
hidden = TRUE
; Information added by packaging script on 2013-11-20
version = "7.24"
; Information added by Drupal.org packaging script on 2014-01-15
version = "7.26"
project = "drupal"
datestamp = "1384983240"
datestamp = "1389815930"
......@@ -161,3 +161,21 @@ function node_test_entity_view_mode_alter(&$view_mode, $context) {
$view_mode = $change_view_mode;
}
}
/**
* Implements hook_node_insert().
*
* This tests saving a node on node insert.
*
* @see NodeSaveTest::testNodeSaveOnInsert()
*/
function node_test_node_insert($node) {
// Set the node title to the node ID and save.
if ($node->title == 'new') {
$node->title = 'Node '. $node->nid;
// Remove the is_new flag, so that the node is updated and not inserted
// again.
unset($node->is_new);
node_save($node);
}
}
......@@ -5,8 +5,8 @@ version = VERSION
core = 7.x
hidden = TRUE
; Information added by packaging script on 2013-11-20
version = "7.24"
; Information added by Drupal.org packaging script on 2014-01-15
version = "7.26"
project = "drupal"
datestamp = "1384983240"
datestamp = "1389815930"
......@@ -5,8 +5,8 @@ package = Core
core = 7.x
files[] = openid.test
; Information added by packaging script on 2013-11-20
version = "7.24"
; Information added by Drupal.org packaging script on 2014-01-15
version = "7.26"
project = "drupal"
datestamp = "1384983240"
datestamp = "1389815930"
......@@ -15,13 +15,14 @@ function openid_schema() {
'idp_endpoint_uri' => array(
'type' => 'varchar',
'length' => 255,
'description' => 'URI of the OpenID Provider endpoint.',
'not null' => TRUE,
'description' => 'Primary Key: URI of the OpenID Provider endpoint.',
),
'assoc_handle' => array(
'type' => 'varchar',
'length' => 255,
'not null' => TRUE,
'description' => 'Primary Key: Used to refer to this association in subsequent messages.',
'description' => 'Used to refer to this association in subsequent messages.',
),
'assoc_type' => array(
'type' => 'varchar',
......@@ -51,7 +52,10 @@ function openid_schema() {
'description' => 'The lifetime, in seconds, of this association.',
),
),
'primary key' => array('assoc_handle'),
'primary key' => array('idp_endpoint_uri'),
'unique keys' => array(
'assoc_handle' => array('assoc_handle'),
),
);
$schema['openid_nonce'] = array(
......@@ -158,3 +162,69 @@ function openid_update_6000() {
/**
* @} End of "addtogroup updates-6.x-to-7.x".
*/
/**
* @addtogroup updates-7.x-extra
* @{
*/
/**
* Bind associations to their providers.
*/
function openid_update_7000() {
db_drop_table('openid_association');
$schema = array(
'description' => 'Stores temporary shared key association information for OpenID authentication.',
'fields' => array(
'idp_endpoint_uri' => array(
'type' => 'varchar',
'length' => 255,
'not null' => TRUE,
'description' => 'Primary Key: URI of the OpenID Provider endpoint.',
),
'assoc_handle' => array(
'type' => 'varchar',
'length' => 255,
'not null' => TRUE,
'description' => 'Used to refer to this association in subsequent messages.',
),
'assoc_type' => array(
'type' => 'varchar',
'length' => 32,
'description' => 'The signature algorithm used: one of HMAC-SHA1 or HMAC-SHA256.',
),
'session_type' => array(
'type' => 'varchar',
'length' => 32,
'description' => 'Valid association session types: "no-encryption", "DH-SHA1", and "DH-SHA256".',
),
'mac_key' => array(
'type' => 'varchar',
'length' => 255,
'description' => 'The MAC key (shared secret) for this association.',
),
'created' => array(
'type' => 'int',
'not null' => TRUE,
'default' => 0,
'description' => 'UNIX timestamp for when the association was created.',
),
'expires_in' => array(
'type' => 'int',
'not null' => TRUE,
'default' => 0,
'description' => 'The lifetime, in seconds, of this association.',
),
),
'primary key' => array('idp_endpoint_uri'),
'unique keys' => array(
'assoc_handle' => array('assoc_handle'),
),
);
db_create_table('openid_association', $schema);
}
/**
* @} End of "addtogroup updates-7.x-extra".
*/
......@@ -839,7 +839,7 @@ function openid_verify_assertion($service, $response) {
// direct verification: ignore the openid.assoc_handle, even if present.
// See http://openid.net/specs/openid-authentication-2_0.html#rfc.section.11.4.1
if (!empty($response['openid.assoc_handle']) && empty($response['openid.invalidate_handle'])) {
$association = db_query("SELECT * FROM {openid_association} WHERE assoc_handle = :assoc_handle", array(':assoc_handle' => $response['openid.assoc_handle']))->fetchObject();
$association = db_query("SELECT * FROM {openid_association} WHERE idp_endpoint_uri = :endpoint AND assoc_handle = :assoc_handle", array(':endpoint' => $service['uri'], ':assoc_handle' => $response['openid.assoc_handle']))->fetchObject();
}
if ($association && isset($association->session_type)) {
......@@ -871,6 +871,7 @@ function openid_verify_assertion($service, $response) {
// database to avoid reusing it again on a subsequent authentication request.
// See http://openid.net/specs/openid-authentication-2_0.html#rfc.section.11.4.2.2
db_delete('openid_association')
->condition('idp_endpoint_uri', $service['uri'])
->condition('assoc_handle', $response['invalidate_handle'])
->execute();
}
......
......@@ -6,8 +6,8 @@ core = 7.x
dependencies[] = openid
hidden = TRUE
; Information added by packaging script on 2013-11-20
version = "7.24"
; Information added by Drupal.org packaging script on 2014-01-15
version = "7.26"
project = "drupal"
datestamp = "1384983240"
datestamp = "1389815930"
......@@ -4,8 +4,8 @@ package = Core
version = VERSION
core = 7.x
; Information added by packaging script on 2013-11-20
version = "7.24"
; Information added by Drupal.org packaging script on 2014-01-15
version = "7.26"
project = "drupal"
datestamp = "1384983240"
datestamp = "1389815930"
......@@ -6,8 +6,8 @@ core = 7.x
files[] = path.test
configure = admin/config/search/path
; Information added by packaging script on 2013-11-20
version = "7.24"
; Information added by Drupal.org packaging script on 2014-01-15
version = "7.26"
project = "drupal"
datestamp = "1384983240"
datestamp = "1389815930"
......@@ -5,8 +5,8 @@ version = VERSION
core = 7.x
files[] = php.test
; Information added by packaging script on 2013-11-20
version = "7.24"
; Information added by Drupal.org packaging script on 2014-01-15
version = "7.26"
project = "drupal"
datestamp = "1384983240"
datestamp = "1389815930"
......@@ -17,7 +17,7 @@ function php_help($path, $arg) {
$output .= '<h3>' . t('Uses') . '</h3>';
$output .= '<dl>';
$output .= '<dt>' . t('Enabling execution of PHP in text fields') . '</dt>';
$output .= '<dd>' . t('The PHP filter module allows users with the proper permissions to include custom PHP code that will get executed when pages of your site are processed. While this is a powerful and flexible feature if used by a trusted user with PHP experience, it is a significant and dangerous security risk in the hands of a malicious or inexperienced user. Even a trusted user may accidentally compromise the site by entering malformed or incorrect PHP code. Only the most trusted users should be granted permission to use the PHP filter, and all PHP code added through the PHP filter should be carefully examined before use. <a href="@php-snippets">Example PHP snippets</a> can be found on Drupal.org.', array('@php-snippets' => url('http://http://drupal.org/documentation/customization/php-snippets'))) . '</dd>';
$output .= '<dd>' . t('The PHP filter module allows users with the proper permissions to include custom PHP code that will get executed when pages of your site are processed. While this is a powerful and flexible feature if used by a trusted user with PHP experience, it is a significant and dangerous security risk in the hands of a malicious or inexperienced user. Even a trusted user may accidentally compromise the site by entering malformed or incorrect PHP code. Only the most trusted users should be granted permission to use the PHP filter, and all PHP code added through the PHP filter should be carefully examined before use. <a href="@php-snippets">Example PHP snippets</a> can be found on Drupal.org.', array('@php-snippets' => url('http://drupal.org/documentation/customization/php-snippets'))) . '</dd>';
$output .= '</dl>';
return $output;
}
......
......@@ -6,8 +6,8 @@ core = 7.x
files[] = poll.test
stylesheets[all][] = poll.css
; Information added by packaging script on 2013-11-20
version = "7.24"
; Information added by Drupal.org packaging script on 2014-01-15
version = "7.26"
project = "drupal"
datestamp = "1384983240"
datestamp = "1389815930"
......@@ -11,8 +11,8 @@ configure = admin/config/people/profile
; See user_system_info_alter().
hidden = TRUE
; Information added by packaging script on 2013-11-20
version = "7.24"
; Information added by Drupal.org packaging script on 2014-01-15
version = "7.26"
project = "drupal"
datestamp = "1384983240"
datestamp = "1389815930"
......@@ -571,6 +571,7 @@ function template_preprocess_profile_listing(&$variables) {
// Supply filtered version of $fields that have values.
foreach ($variables['fields'] as $field) {
if ($field->value) {
$variables['profile'][$field->name] = new stdClass();
$variables['profile'][$field->name]->title = $field->title;
$variables['profile'][$field->name]->value = $field->value;
$variables['profile'][$field->name]->type = $field->type;
......
......@@ -17,17 +17,15 @@ function profile_browse() {
if ($name && $field->fid) {
// Only allow browsing of fields that have a page title set.
if (empty($field->page)) {
drupal_not_found();
return;
return MENU_NOT_FOUND;
}
// Do not allow browsing of private and hidden fields by non-admins.
if (!user_access('administer users') && ($field->visibility == PROFILE_PRIVATE || $field->visibility == PROFILE_HIDDEN)) {
drupal_access_denied();
return;
return MENU_ACCESS_DENIED;
}
// Compile a list of fields to show.
$fields = db_query('SELECT name, title, type, weight, page FROM {profile_field} WHERE fid <> :fid AND visibility = :visibility ORDER BY weight', array(
$fields = db_query('SELECT name, title, type, weight, page, visibility FROM {profile_field} WHERE fid <> :fid AND visibility = :visibility ORDER BY weight', array(
':fid' => $field->fid,
':visibility' => PROFILE_PUBLIC_LISTINGS,
))->fetchAll();
......@@ -54,8 +52,7 @@ function profile_browse() {
$query->condition('v.value', '%' . db_like($value) . '%', 'LIKE');
break;
default:
drupal_not_found();
return;
return MENU_NOT_FOUND;
}
$uids = $query
......@@ -85,7 +82,7 @@ function profile_browse() {
return $output;
}
elseif ($name && !$field->fid) {
drupal_not_found();
return MENU_NOT_FOUND;
}
else {
// Compile a list of fields to show.
......
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
File mode changed from 100755 to 100644
File mode changed from 100755 to 100644
File mode changed from 100755 to 100644
File mode changed from 100755 to 100644
File mode changed from 100755 to 100644
File mode changed from 100755 to 100644
File mode changed from 100755 to 100644
File mode changed from 100755 to 100644
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment