summaryrefslogtreecommitdiffstatshomepage
diff options
context:
space:
mode:
authorAngie Byron <webchick@24967.no-reply.drupal.org>2009-10-24 05:13:44 +0000
committerAngie Byron <webchick@24967.no-reply.drupal.org>2009-10-24 05:13:44 +0000
commitcd7b8f099996c46a58b354ae262852d222306e74 (patch)
tree1e7725d67472a1c203ce418f90e2fb48716efd37
parentdec6514c3b2d889c3a9fb19731e49e83d554392c (diff)
downloaddrupal-cd7b8f099996c46a58b354ae262852d222306e74.tar.gz
drupal-cd7b8f099996c46a58b354ae262852d222306e74.zip
#320331 by Dave Reid, dww, John Morahan, cwgordon7, moshe weitzman, c960657, and smoothify: Turn custom_url_rewrite_inbound() and custom_url_rewrite_outbound() into hooks.
-rw-r--r--authorize.php12
-rw-r--r--includes/bootstrap.inc14
-rw-r--r--includes/common.inc28
-rw-r--r--includes/language.inc41
-rw-r--r--includes/path.inc25
-rw-r--r--modules/forum/forum.module19
-rw-r--r--modules/forum/forum.test2
-rw-r--r--modules/locale/locale.module38
-rw-r--r--modules/path/path.admin.inc5
-rw-r--r--modules/simpletest/tests/path.test109
-rw-r--r--modules/simpletest/tests/url_alter_test.info9
-rw-r--r--modules/simpletest/tests/url_alter_test.install13
-rw-r--r--modules/simpletest/tests/url_alter_test.module43
-rw-r--r--modules/statistics/statistics.module2
-rw-r--r--modules/system/system.api.php56
-rw-r--r--modules/taxonomy/taxonomy.module19
-rw-r--r--modules/taxonomy/taxonomy.pages.inc2
-rw-r--r--modules/taxonomy/taxonomy.tokens.inc2
18 files changed, 326 insertions, 113 deletions
diff --git a/authorize.php b/authorize.php
index ffe49ef09f7..140c5a02762 100644
--- a/authorize.php
+++ b/authorize.php
@@ -96,8 +96,16 @@ if (authorize_access_allowed()) {
// Load the code that drives the authorize process.
require_once DRUPAL_ROOT . '/includes/authorize.inc';
- // Initialize the URL path, but not via raising our bootstrap level.
- drupal_path_initialize();
+ // For the sake of Batch API and a few other low-level functions, we need to
+ // initialize the URL path into $_GET['q']. However, we do not want to raise
+ // our bootstrap level, nor do we want to call drupal_initialize_path(),
+ // since that is assuming that modules are loaded and invoking hooks.
+ // However, all we really care is if we're in the middle of a batch, in which
+ // case $_GET['q'] will already be set, we just initialize it to an empty
+ // string if it's not already defined.
+ if (!isset($_GET['q'])) {
+ $_GET['q'] = '';
+ }
if (isset($_SESSION['authorize_operation']['page_title'])) {
drupal_set_title(check_plain($_SESSION['authorize_operation']['page_title']));
diff --git a/includes/bootstrap.inc b/includes/bootstrap.inc
index b4f683840f2..8cc52c69e56 100644
--- a/includes/bootstrap.inc
+++ b/includes/bootstrap.inc
@@ -127,15 +127,10 @@ define('DRUPAL_BOOTSTRAP_PAGE_HEADER', 5);
define('DRUPAL_BOOTSTRAP_LANGUAGE', 6);
/**
- * Eighth bootstrap phase: set $_GET['q'] to Drupal path of request.
- */
-define('DRUPAL_BOOTSTRAP_PATH', 7);
-
-/**
* Final bootstrap phase: Drupal is fully loaded; validate and fix
* input data.
*/
-define('DRUPAL_BOOTSTRAP_FULL', 8);
+define('DRUPAL_BOOTSTRAP_FULL', 7);
/**
* Role ID for anonymous users; should match what's in the "role" table.
@@ -1405,7 +1400,6 @@ function drupal_bootstrap($phase = NULL, $new_phase = TRUE) {
DRUPAL_BOOTSTRAP_SESSION,
DRUPAL_BOOTSTRAP_PAGE_HEADER,
DRUPAL_BOOTSTRAP_LANGUAGE,
- DRUPAL_BOOTSTRAP_PATH,
DRUPAL_BOOTSTRAP_FULL,
));
$completed_phase = &drupal_static(__FUNCTION__ . '_completed_phase', -1);
@@ -1541,12 +1535,6 @@ function _drupal_bootstrap($phase) {
drupal_language_initialize();
break;
- case DRUPAL_BOOTSTRAP_PATH:
- require_once DRUPAL_ROOT . '/includes/path.inc';
- // Initialize $_GET['q'] prior to loading modules and invoking hook_init().
- drupal_path_initialize();
- break;
-
case DRUPAL_BOOTSTRAP_FULL:
require_once DRUPAL_ROOT . '/includes/common.inc';
_drupal_bootstrap_full();
diff --git a/includes/common.inc b/includes/common.inc
index aa0a08a9c54..90be49c5ac2 100644
--- a/includes/common.inc
+++ b/includes/common.inc
@@ -2379,6 +2379,7 @@ function url($path = NULL, array $options = array()) {
'https' => FALSE,
'prefix' => ''
);
+
if (!isset($options['external'])) {
// Return an external link if $path contains an allowed absolute URL.
// Only call the slow filter_xss_bad_protocol if $path contains a ':' before
@@ -2387,10 +2388,12 @@ function url($path = NULL, array $options = array()) {
$options['external'] = ($colonpos !== FALSE && !preg_match('![/?#]!', substr($path, 0, $colonpos)) && filter_xss_bad_protocol($path, FALSE) == check_plain($path));
}
- // May need language dependent rewriting if language.inc is present.
- if (function_exists('language_url_rewrite')) {
- language_url_rewrite($path, $options);
- }
+ // Preserve the original path before altering or aliasing.
+ $original_path = $path;
+
+ // Allow other modules to alter the outbound URL and options.
+ drupal_alter('url_outbound', $path, $options, $original_path);
+
if ($options['fragment']) {
$options['fragment'] = '#' . $options['fragment'];
}
@@ -2439,21 +2442,16 @@ function url($path = NULL, array $options = array()) {
}
}
- // Preserve the original path before aliasing.
- $original_path = $path;
-
// The special path '<front>' links to the default front page.
if ($path == '<front>') {
$path = '';
}
elseif (!empty($path) && !$options['alias']) {
$language = isset($options['language']) && isset($options['language']->language) ? $options['language']->language : '';
- $path = drupal_get_path_alias($path, $language);
- }
-
- if (function_exists('custom_url_rewrite_outbound')) {
- // Modules may alter outbound links by reference.
- custom_url_rewrite_outbound($path, $options, $original_path);
+ $alias = drupal_get_path_alias($original_path, $language);
+ if ($alias != $original_path) {
+ $path = $alias;
+ }
}
$base = $options['absolute'] ? $options['base_url'] . '/' : base_path();
@@ -4223,6 +4221,7 @@ function _drupal_bootstrap_full() {
return;
}
$called = 1;
+ require_once DRUPAL_ROOT . '/includes/path.inc';
require_once DRUPAL_ROOT . '/includes/theme.inc';
require_once DRUPAL_ROOT . '/includes/pager.inc';
require_once DRUPAL_ROOT . '/includes/menu.inc';
@@ -4256,6 +4255,8 @@ function _drupal_bootstrap_full() {
ini_set('log_errors', 1);
ini_set('error_log', file_directory_path() . '/error.log');
}
+ // Initialize $_GET['q'] prior to invoking hook_init().
+ drupal_path_initialize();
// Set a custom theme for the current page, if there is one. We need to run
// this before invoking hook_init(), since any modules which initialize the
// theme system will prevent a custom theme from being correctly set later.
@@ -6115,4 +6116,3 @@ function drupal_get_updaters() {
}
return $updaters;
}
-
diff --git a/includes/language.inc b/includes/language.inc
index 77b8146be1d..bb4802df5aa 100644
--- a/includes/language.inc
+++ b/includes/language.inc
@@ -325,47 +325,6 @@ function language_from_default() {
}
/**
- * Rewrite URLs allowing modules to hook in.
- *
- * @param $path
- * The path to rewrite.
- * @param $options
- * An associative array of additional options as in url().
- */
-function language_url_rewrite(&$path, &$options) {
- // Only modify relative (insite) URLs.
- if (!$options['external']) {
- static $callbacks;
-
- if (!isset($callbacks)) {
- $callbacks = array();
-
- foreach (language_types_configurable() as $type) {
- // Get url rewriter callbacks only from enabled language providers.
- $negotiation = variable_get("language_negotiation_$type", array());
-
- foreach ($negotiation as $id => $provider) {
- if (isset($provider['file'])) {
- require_once DRUPAL_ROOT . '/' . $provider['file'];
- }
-
- // Avoid duplicate callback entries.
- if (isset($provider['callbacks']['url_rewrite'])) {
- $callbacks[$provider['callbacks']['url_rewrite']] = NULL;
- }
- }
- }
-
- $callbacks = array_keys($callbacks);
- }
-
- foreach ($callbacks as $callback) {
- $callback($path, $options);
- }
- }
-}
-
-/**
* Split the given path into prefix and actual path.
*
* Parse the given path and return the language object identified by the
diff --git a/includes/path.inc b/includes/path.inc
index f1542323ee6..19d52df38d7 100644
--- a/includes/path.inc
+++ b/includes/path.inc
@@ -6,8 +6,8 @@
* Functions to handle paths in Drupal, including path aliasing.
*
* These functions are not loaded for cached pages, but modules that need
- * to use them in hook_init() or hook exit() can make them available, by
- * executing "drupal_bootstrap(DRUPAL_BOOTSTRAP_PATH);".
+ * to use them in hook_boot() or hook exit() can make them available, by
+ * executing "drupal_bootstrap(DRUPAL_BOOTSTRAP_FULL);".
*/
/**
@@ -204,15 +204,22 @@ function drupal_get_path_alias($path = NULL, $path_language = '') {
* internal path was found.
*/
function drupal_get_normal_path($path, $path_language = '') {
- $result = $path;
+ $original_path = $path;
+
+ // Lookup the path alias first.
if ($source = drupal_lookup_path('source', $path, $path_language)) {
- $result = $source;
+ $path = $source;
}
- if (function_exists('custom_url_rewrite_inbound')) {
- // Modules may alter the inbound request path by reference.
- custom_url_rewrite_inbound($result, $path, $path_language);
+
+ // Allow other modules to alter the inbound URL. We cannot use drupal_alter()
+ // here because we need to run hook_url_inbound_alter() in the reverse order
+ // of hook_url_outbound_alter().
+ foreach (array_reverse(module_implements('url_inbound_alter')) as $module) {
+ $function = $module . '_url_inbound_alter';
+ $function($path, $original_path, $path_language);
}
- return $result;
+
+ return $path;
}
/**
@@ -347,7 +354,7 @@ function drupal_match_path($path, $patterns) {
* This function is not available in hook_boot() so use $_GET['q'] instead.
* However, be careful when doing that because in the case of Example #3
* $_GET['q'] will contain "path/alias". If "node/306" is needed, calling
- * drupal_bootstrap(DRUPAL_BOOTSTRAP_PATH) makes this function available.
+ * drupal_bootstrap(DRUPAL_BOOTSTRAP_FULL) makes this function available.
*
* @return
* The current Drupal URL path.
diff --git a/modules/forum/forum.module b/modules/forum/forum.module
index 72653dfe5d4..7ecd00e4c35 100644
--- a/modules/forum/forum.module
+++ b/modules/forum/forum.module
@@ -115,12 +115,6 @@ function forum_menu() {
'parent' => 'admin/structure/forum',
'file' => 'forum.admin.inc',
);
- $items['admin/structure/forum/edit/%taxonomy_term'] = array(
- 'page callback' => 'forum_form_main',
- 'access arguments' => array('administer forums'),
- 'type' => MENU_CALLBACK,
- 'file' => 'forum.admin.inc',
- );
$items['admin/structure/forum/edit/container/%taxonomy_term'] = array(
'title' => 'Edit container',
'page callback' => 'forum_form_main',
@@ -610,7 +604,7 @@ function forum_block_view_pre_render($elements) {
*/
function forum_form($node, $form_state) {
$type = node_type_get_type($node);
-
+
if (!empty($node->nid)) {
$forum_terms = $node->taxonomy_forums;
// If editing, give option to leave shadows
@@ -626,10 +620,15 @@ function forum_form($node, $form_state) {
}
/**
- * Implement hook_term_path().
+ * Implement hook_url_outbound_alter().
*/
-function forum_term_path($term) {
- return 'forum/' . $term->tid;
+function forum_url_outbound_alter(&$path, &$options, $original_path) {
+ if (preg_match('!^taxonomy/term/(\d+)!', $path, $matches)) {
+ $term = taxonomy_term_load($matches[1]);
+ if ($term && $term->vocabulary_machine_name == 'forums') {
+ $path = 'forum/' . $matches[1];
+ }
+ }
}
/**
diff --git a/modules/forum/forum.test b/modules/forum/forum.test
index 5bf8501cc1f..8a4e6ed1463 100644
--- a/modules/forum/forum.test
+++ b/modules/forum/forum.test
@@ -211,7 +211,7 @@ class ForumTestCase extends DrupalWebTestCase {
function deleteForum($tid) {
// Delete the forum.
$this->drupalPost('admin/structure/forum/edit/forum/' . $tid, array(), t('Delete'));
- $this->drupalPost(NULL, NULL, t('Delete'));
+ $this->drupalPost(NULL, array(), t('Delete'));
// Assert that the forum no longer exists.
$this->drupalGet('forum/' . $tid);
diff --git a/modules/locale/locale.module b/modules/locale/locale.module
index 45cd6523a84..e35fe9ca9c2 100644
--- a/modules/locale/locale.module
+++ b/modules/locale/locale.module
@@ -1067,3 +1067,41 @@ function locale_date_format_reset_form_submit($form, &$form_state) {
$form_state['redirect'] = 'admin/config/regional/date-time/locale';
}
+/**
+ * Implement hook_url_outbound_alter().
+ *
+ * Rewrite outbound URLs with language based prefixes.
+ */
+function locale_url_outbound_alter(&$path, &$options, $original_path) {
+ // Only modify internal URLs.
+ if (!$options['external']) {
+ static $callbacks;
+
+ if (!isset($callbacks)) {
+ $callbacks = array();
+ include_once DRUPAL_ROOT . '/includes/language.inc';
+
+ foreach (language_types_configurable() as $type) {
+ // Get url rewriter callbacks only from enabled language providers.
+ $negotiation = variable_get("language_negotiation_$type", array());
+
+ foreach ($negotiation as $id => $provider) {
+ if (isset($provider['file'])) {
+ require_once DRUPAL_ROOT . '/' . $provider['file'];
+ }
+
+ // Avoid duplicate callback entries.
+ if (isset($provider['callbacks']['url_rewrite'])) {
+ $callbacks[$provider['callbacks']['url_rewrite']] = NULL;
+ }
+ }
+ }
+
+ $callbacks = array_keys($callbacks);
+ }
+
+ foreach ($callbacks as $callback) {
+ $callback($path, $options);
+ }
+ }
+}
diff --git a/modules/path/path.admin.inc b/modules/path/path.admin.inc
index dd9e3e0adab..b1fd47c00e2 100644
--- a/modules/path/path.admin.inc
+++ b/modules/path/path.admin.inc
@@ -105,7 +105,7 @@ function path_admin_form($form, &$form_state, $path = array('source' => '', 'ali
'#default_value' => $path['source'],
'#maxlength' => 255,
'#size' => 45,
- '#description' => t('Specify the existing path you wish to alias. For example: node/28, forum/1, taxonomy/term/1+2.'),
+ '#description' => t('Specify the existing path you wish to alias. For example: node/28, forum/1, taxonomy/term/1.'),
'#field_prefix' => url(NULL, array('absolute' => TRUE)) . (variable_get('clean_url', 0) ? '' : '?q='),
'#required' => TRUE,
);
@@ -150,7 +150,8 @@ function path_admin_form($form, &$form_state, $path = array('source' => '', 'ali
* Verify that a URL alias is valid
*/
function path_admin_form_validate($form, &$form_state) {
- $source = $form_state['values']['source'];
+ $source = &$form_state['values']['source'];
+ $source = drupal_get_normal_path($source);
$alias = $form_state['values']['alias'];
$pid = isset($form_state['values']['pid']) ? $form_state['values']['pid'] : 0;
// Language is only set if locale module is enabled, otherwise save for all languages.
diff --git a/modules/simpletest/tests/path.test b/modules/simpletest/tests/path.test
index f76ea4089c4..519be543d74 100644
--- a/modules/simpletest/tests/path.test
+++ b/modules/simpletest/tests/path.test
@@ -126,3 +126,112 @@ class DrupalMatchPathTestCase extends DrupalWebTestCase {
);
}
}
+
+/**
+ * Tests hook_url_alter functions.
+ */
+class UrlAlterFunctionalTest extends DrupalWebTestCase {
+ public static function getInfo() {
+ return array(
+ 'name' => t('URL altering'),
+ 'description' => t('Tests hook_url_inbound_alter() and hook_url_outbound_alter().'),
+ 'group' => t('Path API'),
+ );
+ }
+
+ function setUp() {
+ parent::setUp('path', 'forum', 'url_alter_test');
+ }
+
+ /**
+ * Test that URL altering works and that it occurs in the correct order.
+ */
+ function testUrlAlter() {
+ $account = $this->drupalCreateUser(array('administer url aliases'));
+ $this->drupalLogin($account);
+
+ $uid = $account->uid;
+ $name = $account->name;
+
+ // Test a single altered path.
+ $this->assertUrlInboundAlter("user/$name", "user/$uid");
+ $this->assertUrlOutboundAlter("user/$uid", "user/$name");
+
+ // Test that a path always uses its alias.
+ $path = array('source' => "user/$uid/test1", 'alias' => 'alias/test1');
+ path_save($path);
+ $this->assertUrlInboundAlter('alias/test1', "user/$uid/test1");
+ $this->assertUrlOutboundAlter("user/$uid/test1", 'alias/test1');
+
+ // Test that alias source paths are normalized in the interface.
+ $edit = array('source' => "user/$name/edit", 'alias' => 'alias/test2');
+ $this->drupalPost('admin/config/search/path/add', $edit, t('Create new alias'));
+ $this->assertText(t('The alias has been saved.'));
+
+ // Test that a path always uses its alias.
+ $this->assertUrlInboundAlter('alias/test2', "user/$uid/edit");
+ $this->assertUrlOutboundAlter("user/$uid/edit", 'alias/test2');
+
+ // Test a non-existant user is not altered.
+ $uid++;
+ $this->assertUrlInboundAlter("user/$uid", "user/$uid");
+ $this->assertUrlOutboundAlter("user/$uid", "user/$uid");
+
+ // Test that 'forum' is altered to 'community' correctly.
+ $this->assertUrlInboundAlter('community', 'forum');
+ $this->assertUrlOutboundAlter('forum', 'community');
+
+ // Add a forum to test url altering.
+ $forum_vid = db_query("SELECT vid FROM {taxonomy_vocabulary} WHERE module = 'forum'")->fetchField();
+ $tid = db_insert('taxonomy_term_data')
+ ->fields(array(
+ 'name' => $this->randomName(),
+ 'vid' => $forum_vid,
+ ))
+ ->execute();
+
+ // Test that a existing forum URL is altered.
+ $this->assertUrlInboundAlter("community/$tid", "forum/$tid");
+ $this->assertUrlOutboundAlter("taxonomy/term/$tid", "community/$tid");
+
+ // Test that a non-existant forum URL is not altered.
+ $tid++;
+ $this->assertUrlInboundAlter("taxonomy/term/$tid", "taxonomy/term/$tid");
+ $this->assertUrlOutboundAlter("taxonomy/term/$tid", "taxonomy/term/$tid");
+ }
+
+ /**
+ * Assert that an outbound path is altered to an expected value.
+ *
+ * @param $original
+ * A string with the original path that is run through url().
+ * @param $final
+ * A string with the expected result after url().
+ * @return
+ * TRUE if $original was correctly altered to $final, FALSE otherwise.
+ */
+ protected function assertUrlOutboundAlter($original, $final) {
+ // Test outbound altering.
+ $result = url($original);
+ $base_path = base_path() . (variable_get('clean_url', '0') ? '' : '?q=');
+ $result = substr($result, strlen($base_path));
+ $this->assertIdentical($result, $final, t('Altered outbound URL %original, expected %final, and got %result.', array('%original' => $original, '%final' => $final, '%result' => $result)));
+ }
+
+ /**
+ * Assert that a inbound path is altered to an expected value.
+ *
+ * @param $original
+ * A string with the aliased or un-normal path that is run through
+ * drupal_get_normal_path().
+ * @param $final
+ * A string with the expected result after url().
+ * @return
+ * TRUE if $original was correctly altered to $final, FALSE otherwise.
+ */
+ protected function assertUrlInboundAlter($original, $final) {
+ // Test inbound altering.
+ $result = drupal_get_normal_path($original);
+ $this->assertIdentical($result, $final, t('Altered inbound URL %original, expected %final, and got %result.', array('%original' => $original, '%final' => $final, '%result' => $result)));
+ }
+}
diff --git a/modules/simpletest/tests/url_alter_test.info b/modules/simpletest/tests/url_alter_test.info
new file mode 100644
index 00000000000..7e72b4f1b45
--- /dev/null
+++ b/modules/simpletest/tests/url_alter_test.info
@@ -0,0 +1,9 @@
+; $Id$
+name = Url_alter tests
+description = A support modules for url_alter hook testing.
+core = 7.x
+package = Testing
+version = VERSION
+files[] = url_alter_test.module
+files[] = url_alter_test.install
+hidden = TRUE
diff --git a/modules/simpletest/tests/url_alter_test.install b/modules/simpletest/tests/url_alter_test.install
new file mode 100644
index 00000000000..89454f37e31
--- /dev/null
+++ b/modules/simpletest/tests/url_alter_test.install
@@ -0,0 +1,13 @@
+<?php
+// $Id$
+
+/**
+ * Impelement hook_install().
+ */
+function url_alter_test_install() {
+ // Set the weight of this module to one higher than forum.module.
+ db_update('system')
+ ->fields(array('weight' => 2))
+ ->condition('name', 'url_alter_test')
+ ->execute();
+}
diff --git a/modules/simpletest/tests/url_alter_test.module b/modules/simpletest/tests/url_alter_test.module
new file mode 100644
index 00000000000..a6841ae393e
--- /dev/null
+++ b/modules/simpletest/tests/url_alter_test.module
@@ -0,0 +1,43 @@
+<?php
+// $Id$
+
+/**
+ * @file
+ * Module to help test hook_url_inbound_alter() and hook_url_outbound_alter().
+ */
+
+/**
+ * Implement hook_url_inbound_alter().
+ */
+function url_alter_test_url_inbound_alter(&$path, $original_path, $path_language) {
+ // Rewrite user/username to user/uid.
+ if (preg_match('!^user/([^/]+)(/.*)?!', $path, $matches)) {
+ if ($account = user_load_by_name($matches[1])) {
+ $matches += array(2 => '');
+ $path = 'user/' . $account->uid . $matches[2];
+ }
+ }
+
+ // Rewrite community/ to forum/.
+ if ($path == 'community' || strpos($path, 'community/') === 0) {
+ $path = 'forum' . substr($path, 9);
+ }
+}
+
+/**
+ * Implement hook_url_outbound_alter().
+ */
+function url_alter_test_url_outbound_alter(&$path, &$options, $original_path) {
+ // Rewrite user/uid to user/username.
+ if (preg_match('!^user/([0-9]+)(/.*)?!', $path, $matches)) {
+ if ($account = user_load($matches[1])) {
+ $matches += array(2 => '');
+ $path = 'user/' . $account->name . $matches[2];
+ }
+ }
+
+ // Rewrite forum/ to community/.
+ if ($path == 'forum' || strpos($path, 'forum/') === 0) {
+ $path = 'community' . substr($path, 5);
+ }
+}
diff --git a/modules/statistics/statistics.module b/modules/statistics/statistics.module
index e8a5247a033..a8dd9ef385c 100644
--- a/modules/statistics/statistics.module
+++ b/modules/statistics/statistics.module
@@ -45,7 +45,7 @@ function statistics_help($path, $arg) {
function statistics_exit() {
global $user;
- drupal_bootstrap(DRUPAL_BOOTSTRAP_PATH);
+ drupal_bootstrap(DRUPAL_BOOTSTRAP_FULL);
if (variable_get('statistics_count_content_views', 0)) {
// We are counting content views.
diff --git a/modules/system/system.api.php b/modules/system/system.api.php
index b379649a636..02c69ee3698 100644
--- a/modules/system/system.api.php
+++ b/modules/system/system.api.php
@@ -2667,5 +2667,61 @@ function hook_page_delivery_callback_alter(&$callback) {
}
/**
+ * Alters inbound URL requests.
+ *
+ * @param $path
+ * The path being constructed, which, if a path alias, has been resolved to a
+ * Drupal path by the database, and which also may have been altered by other
+ * modules before this one.
+ * @param $original_path
+ * The original path, before being checked for path aliases or altered by any
+ * modules.
+ * @param $path_language
+ * The language of the path.
+ *
+ * @see drupal_get_normal_path()
+ */
+function hook_url_inbound_alter(&$path, $original_path, $path_language) {
+ // Create the path user/me/edit, which allows a user to edit their account.
+ if (preg_match('|^user/me/edit(/.*)?|', $path, $matches)) {
+ global $user;
+ $path = 'user/' . $user->uid . '/edit' . $matches[1];
+ }
+}
+
+/**
+ * Alters outbound URLs.
+ *
+ * @param $path
+ * The outbound path to alter, not adjusted for path aliases yet. It won't be
+ * adjusted for path aliases until all modules are finished altering it, thus
+ * being consistent with hook_url_alter_inbound(), which adjusts for all path
+ * aliases before allowing modules to alter it. This may have been altered by
+ * other modules before this one.
+ * @param $options
+ * A set of URL options for the URL so elements such as a fragment or a query
+ * string can be added to the URL.
+ * @param $original_path
+ * The original path, before being altered by any modules.
+ *
+ * @see url()
+ */
+function hook_url_outbound_alter(&$path, &$options, $original_path) {
+ // Use an external RSS feed rather than the Drupal one.
+ if ($path == 'rss.xml') {
+ $path = 'http://example.com/rss.xml';
+ $options['external'] = TRUE;
+ }
+
+ // Instead of pointing to user/[uid]/edit, point to user/me/edit.
+ if (preg_match('|^user/([0-9]*)/edit(/.*)?|', $path, $matches)) {
+ global $user;
+ if ($user->uid == $matches[1]) {
+ $path = 'user/me/edit' . $matches[2];
+ }
+ }
+}
+
+/**
* @} End of "addtogroup hooks".
*/
diff --git a/modules/taxonomy/taxonomy.module b/modules/taxonomy/taxonomy.module
index b04336fa0ec..613383a90bd 100644
--- a/modules/taxonomy/taxonomy.module
+++ b/modules/taxonomy/taxonomy.module
@@ -164,23 +164,6 @@ function taxonomy_theme() {
}
/**
- * For vocabularies not maintained by taxonomy.module, give the maintaining
- * module a chance to provide a path for terms in that vocabulary.
- *
- * @param $term
- * A term object.
- * @return
- * An internal Drupal path.
- */
-function taxonomy_term_path($term) {
- $vocabulary = taxonomy_vocabulary_load($term->vid);
- if ($vocabulary->module != 'taxonomy' && $path = module_invoke($vocabulary->module, 'term_path', $term)) {
- return $path;
- }
- return 'taxonomy/term/' . $term->tid;
-}
-
-/**
* Implement hook_menu().
*/
function taxonomy_menu() {
@@ -1103,7 +1086,7 @@ function taxonomy_field_formatter_info() {
function theme_field_formatter_taxonomy_term_link($variables) {
$term = $variables['element']['#item']['taxonomy_term'];
$attributes = empty($variables['link_options']) ? array() : $variables['link_options'];
- return l($term->name, taxonomy_term_path($term), $attributes);
+ return l($term->name, 'taxonomy/term/' . $term->tid, $attributes);
}
/**
diff --git a/modules/taxonomy/taxonomy.pages.inc b/modules/taxonomy/taxonomy.pages.inc
index eadbd9cf337..90ff994f05b 100644
--- a/modules/taxonomy/taxonomy.pages.inc
+++ b/modules/taxonomy/taxonomy.pages.inc
@@ -22,7 +22,7 @@ function taxonomy_term_page($term) {
$breadcrumb = array();
while ($parents = taxonomy_get_parents($current->tid)) {
$current = array_shift($parents);
- $breadcrumb[] = l($current->name, taxonomy_term_path($current));
+ $breadcrumb[] = l($current->name, 'taxonomy/term/' . $current->tid);
}
$breadcrumb[] = l(t('Home'), NULL);
$breadcrumb = array_reverse($breadcrumb);
diff --git a/modules/taxonomy/taxonomy.tokens.inc b/modules/taxonomy/taxonomy.tokens.inc
index f2ee1aac9f4..c7d92ce46d1 100644
--- a/modules/taxonomy/taxonomy.tokens.inc
+++ b/modules/taxonomy/taxonomy.tokens.inc
@@ -119,7 +119,7 @@ function taxonomy_tokens($type, $tokens, array $data = array(), array $options =
break;
case 'url':
- $replacements[$original] = url(taxonomy_term_path($term), array('absolute' => TRUE));
+ $replacements[$original] = url('taxonomy/term/' . $term, array('absolute' => TRUE));
break;
case 'node-count':